mirror of
https://github.com/OpenMW/openmw.git
synced 2025-03-03 03:39:42 +00:00
Feature #161 (In Progress) Load REC_PGRD records
now using vector instead of C arrays fixed path grid edge loading added path grid to cell store implemented dedicated storage class for path grids
This commit is contained in:
parent
08db70e137
commit
fda5b59eb6
5 changed files with 115 additions and 34 deletions
|
@ -3,25 +3,14 @@
|
|||
namespace ESM
|
||||
{
|
||||
|
||||
PathGrid::~PathGrid() {
|
||||
if (points != NULL) {
|
||||
delete[] points;
|
||||
points = NULL;
|
||||
}
|
||||
if (edges != NULL) {
|
||||
delete[] edges;
|
||||
edges = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
void PathGrid::load(ESMReader &esm)
|
||||
void Pathgrid::load(ESMReader &esm)
|
||||
{
|
||||
esm.getHNT(data, "DATA", 12);
|
||||
cell = esm.getHNString("NAME");
|
||||
//std::cout << "loading PGRD for " << cell << " x=" << data.x << " y=" << data.y << std::endl;
|
||||
|
||||
// Remember this file position
|
||||
context = esm.getContext();
|
||||
// std::cout << "loading PGRD for " <<
|
||||
// cell << " x=" << data.x << " y=" << data.y <<
|
||||
// " " << data.s1
|
||||
// << std::endl;
|
||||
|
||||
// Check that the sizes match up. Size = 16 * s2 (path points?)
|
||||
if (esm.isNextSub("PGRP"))
|
||||
|
@ -35,8 +24,13 @@ void PathGrid::load(ESMReader &esm)
|
|||
{
|
||||
pointCount = data.s2;
|
||||
//std::cout << "Path grid points count is " << data.s2 << std::endl;
|
||||
points = new Point[pointCount];
|
||||
esm.getExact(points, size);
|
||||
points.reserve(pointCount);
|
||||
for (int i = 0; i < pointCount; ++i)
|
||||
{
|
||||
Point p;
|
||||
esm.getExact(&p, sizeof(Point));
|
||||
points.push_back(p);
|
||||
}
|
||||
// for (int i = 0; i < pointCount; ++i)
|
||||
// {
|
||||
// std::cout << i << "'s point: " << points[i].x;
|
||||
|
@ -53,16 +47,30 @@ void PathGrid::load(ESMReader &esm)
|
|||
if (esm.isNextSub("PGRC"))
|
||||
{
|
||||
esm.getSubHeader();
|
||||
//esm.skipHSub();
|
||||
int size = esm.getSubSize();
|
||||
//std::cout << "PGRC size is " << size << std::endl;
|
||||
if (size % 4 != 0)
|
||||
esm.fail("PGRC size not a multiple of 4");
|
||||
if (size % sizeof(int) != 0)
|
||||
esm.fail("PGRC size not a multiple of 8");
|
||||
else
|
||||
{
|
||||
edgeCount = size / sizeof(Edge);
|
||||
edgeCount = size / sizeof(int) - 1;
|
||||
//std::cout << "Path grid edge count is " << edgeCount << std::endl;
|
||||
edges = new Edge[edgeCount];
|
||||
esm.getExact(edges, size);
|
||||
edges.reserve(edgeCount);
|
||||
int prevValue;
|
||||
esm.getT(prevValue);
|
||||
//esm.getExact(&prevValue, sizeof(int));
|
||||
for (int i = 0; i < edgeCount; ++i)
|
||||
{
|
||||
int nextValue;
|
||||
esm.getT(nextValue);
|
||||
//esm.getExact(&nextValue, sizeof(int));
|
||||
Edge e;
|
||||
e.v0 = prevValue;
|
||||
e.v1 = nextValue;
|
||||
edges.push_back(e);
|
||||
prevValue = nextValue;
|
||||
}
|
||||
// for (int i = 0; i < edgeCount; ++i)
|
||||
// {
|
||||
// std::cout << i << "'s edge: " << edges[i].v0 << " "
|
||||
|
|
|
@ -9,7 +9,7 @@ namespace ESM
|
|||
/*
|
||||
* Path grid.
|
||||
*/
|
||||
struct PathGrid
|
||||
struct Pathgrid
|
||||
{
|
||||
struct DATAstruct
|
||||
{
|
||||
|
@ -19,7 +19,6 @@ struct PathGrid
|
|||
short s2; // Number of path points? Size of PGRP block is always 16 * s2;
|
||||
}; // 12 bytes
|
||||
|
||||
#pragma pack(push, 1)
|
||||
struct Point // path grid point
|
||||
{
|
||||
int x, y, z; // Location of point
|
||||
|
@ -30,22 +29,17 @@ struct PathGrid
|
|||
{
|
||||
int v0, v1; // index of points connected with this edge
|
||||
}; // 8 bytes
|
||||
#pragma pack(pop)
|
||||
|
||||
std::string cell; // Cell name
|
||||
DATAstruct data;
|
||||
|
||||
Point *points;
|
||||
std::vector<Point> points;
|
||||
int pointCount;
|
||||
|
||||
Edge *edges;
|
||||
|
||||
std::vector<Edge> edges;
|
||||
int edgeCount;
|
||||
|
||||
ESM_Context context; // Context so we can return here later and
|
||||
// finish the job
|
||||
void load(ESMReader &esm);
|
||||
|
||||
~PathGrid();
|
||||
};
|
||||
}
|
||||
#endif
|
||||
|
|
|
@ -123,6 +123,8 @@ namespace ESMS
|
|||
CellRefList<Static, D> statics;
|
||||
CellRefList<Weapon, D> weapons;
|
||||
|
||||
ESM::Pathgrid *pathgrid;
|
||||
|
||||
void load (const ESMStore &store, ESMReader &esm)
|
||||
{
|
||||
if (mState!=State_Loaded)
|
||||
|
@ -134,6 +136,8 @@ namespace ESMS
|
|||
|
||||
loadRefs (store, esm);
|
||||
|
||||
pathgrid = store.pathgrids.search(cell->data.gridX, cell->data.gridY, cell->name);
|
||||
|
||||
mState = State_Loaded;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -390,6 +390,80 @@ namespace ESMS
|
|||
}
|
||||
};
|
||||
|
||||
struct PathgridList : RecList
|
||||
{
|
||||
int count;
|
||||
|
||||
// List of grids for interior cells. Indexed by cell name.
|
||||
typedef std::map<std::string,ESM::Pathgrid*, ciLessBoost> IntGrids;
|
||||
IntGrids intGrids;
|
||||
|
||||
// List of grids for exterior cells. Indexed as extCells[gridX][gridY].
|
||||
typedef std::map<std::pair<int, int>, ESM::Pathgrid*> ExtGrids;
|
||||
ExtGrids extGrids;
|
||||
|
||||
PathgridList() : count(0) {}
|
||||
|
||||
~PathgridList()
|
||||
{
|
||||
for (IntGrids::iterator it = intGrids.begin(); it!=intGrids.end(); ++it)
|
||||
delete it->second;
|
||||
|
||||
for (ExtGrids::iterator it = extGrids.begin(); it!=extGrids.end(); ++it)
|
||||
delete it->second;
|
||||
}
|
||||
|
||||
int getSize() { return count; }
|
||||
|
||||
virtual void listIdentifier (std::vector<std::string>& identifier) const
|
||||
{
|
||||
// do nothing
|
||||
}
|
||||
|
||||
void load(ESMReader &esm, const std::string &id)
|
||||
{
|
||||
count++;
|
||||
ESM::Pathgrid *grid = new ESM::Pathgrid;
|
||||
grid->load(esm);
|
||||
if (grid->data.x == 0 && grid->data.y)
|
||||
{
|
||||
intGrids[grid->cell] = grid;
|
||||
}
|
||||
else
|
||||
{
|
||||
extGrids[std::make_pair(grid->data.x, grid->data.y)] = grid;
|
||||
}
|
||||
}
|
||||
|
||||
Pathgrid *find(int cellX, int cellY, std::string cellName) const
|
||||
{
|
||||
Pathgrid *result = search(cellX, cellY, cellName);
|
||||
if (!result)
|
||||
{
|
||||
throw std::runtime_error("no pathgrid found for cell " + cellName);
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
Pathgrid *search(int cellX, int cellY, std::string cellName) const
|
||||
{
|
||||
Pathgrid *result = NULL;
|
||||
if (cellX == 0 && cellY == 0) // possibly interior
|
||||
{
|
||||
IntGrids::const_iterator it = intGrids.find(cellName);
|
||||
if (it != intGrids.end())
|
||||
result = it->second;
|
||||
}
|
||||
else
|
||||
{
|
||||
ExtGrids::const_iterator it = extGrids.find(std::make_pair(cellX, cellY));
|
||||
if (it != extGrids.end())
|
||||
result = it->second;
|
||||
}
|
||||
return result;
|
||||
}
|
||||
};
|
||||
|
||||
template <typename X>
|
||||
struct ScriptListT : RecList
|
||||
{
|
||||
|
|
|
@ -74,7 +74,8 @@ namespace ESMS
|
|||
ScriptListT<Script> scripts;
|
||||
IndexListT<MagicEffect> magicEffects;
|
||||
IndexListT<Skill> skills;
|
||||
RecListT<PathGrid> pathgrids;
|
||||
//RecListT<Pathgrid> pathgrids;
|
||||
PathgridList pathgrids;
|
||||
|
||||
// Special entry which is hardcoded and not loaded from an ESM
|
||||
IndexListT<Attribute> attributes;
|
||||
|
|
Loading…
Reference in a new issue