* fixed setting MapMgr to loading state to fix problems with GUI thread trying to access not yet loaded maps
217 lines
5.3 KiB
C++
217 lines
5.3 KiB
C++
#include "common.h"
|
|
#include "log.h"
|
|
#include "MapTile.h"
|
|
#include "MapMgr.h"
|
|
|
|
void MakeMapFilename(char *fn, uint32 m, uint32 x, uint32 y)
|
|
{
|
|
sprintf(fn,"./data/maps/%u_%u_%u.adt",m,x,y);
|
|
}
|
|
|
|
bool TileExistsInFile(uint32 m, uint32 x, uint32 y)
|
|
{
|
|
char buf[50];
|
|
MakeMapFilename(buf,m,x,y);
|
|
return GetFileSize(buf);
|
|
}
|
|
|
|
|
|
MapMgr::MapMgr()
|
|
{
|
|
DEBUG(logdebug("Creating MapMgr with TILESIZE=%.3f CHUNKSIZE=%.3f UNITSIZE=%.3f",TILESIZE,CHUNKSIZE,UNITSIZE));
|
|
_tiles = new MapTileStorage();
|
|
_gridx = _gridy = _mapid = (-1);
|
|
_mapsLoaded = false;
|
|
}
|
|
|
|
MapMgr::~MapMgr()
|
|
{
|
|
Flush();
|
|
delete _tiles;
|
|
}
|
|
|
|
void MapMgr::Update(float x, float y, uint32 m)
|
|
{
|
|
if(m != _mapid)
|
|
{
|
|
Flush(); // we teleported to a new map, drop all loaded maps
|
|
WDTFile *wdt = new WDTFile();
|
|
char buf[100];
|
|
sprintf(buf,"data/maps/%u.wdt",m);
|
|
if(!wdt->Load(buf))
|
|
{
|
|
logerror("MAPMGR: Could not load WDT file '%s'",buf);
|
|
}
|
|
_tiles->ImportTileMap(wdt);
|
|
delete wdt;
|
|
_mapid = m;
|
|
_gridx = _gridy = (-1); // must load tiles now
|
|
}
|
|
GridCoordPair gcoords = GetTransformGridCoordPair(x,y);
|
|
if(gcoords.x != _gridx || gcoords.y != _gridy)
|
|
{
|
|
_gridx = gcoords.x;
|
|
_gridy = gcoords.y;
|
|
_LoadNearTiles(_gridx,_gridy,m);
|
|
_UnloadOldTiles();
|
|
}
|
|
_mapsLoaded = true; // at this point, everything should be loaded (if maps existing)
|
|
}
|
|
|
|
void MapMgr::Flush(void)
|
|
{
|
|
_mapsLoaded = false;
|
|
for(uint32 i = 0; i < 4096; i++)
|
|
_tiles->UnloadMapTile(i);
|
|
logdebug("MAPMGR: Flushed all maps");
|
|
}
|
|
|
|
void MapMgr::_LoadNearTiles(uint32 gx, uint32 gy, uint32 m)
|
|
{
|
|
_mapsLoaded = false;
|
|
logdebug("MAPMGR: Loading near tiles for (%u, %u) map %u",gx,gy,m);
|
|
for(uint32 v = gy-1; v <= gy+1; v++)
|
|
{
|
|
for(uint32 h = gx-1; h <= gx+1; h++)
|
|
{
|
|
_LoadTile(h,v,m);
|
|
}
|
|
}
|
|
}
|
|
|
|
void MapMgr::_LoadTile(uint32 gx, uint32 gy, uint32 m)
|
|
{
|
|
_mapsLoaded = false;
|
|
if(!_tiles->TileExists(gx,gy))
|
|
{
|
|
if(TileExistsInFile(m,gx,gy))
|
|
{
|
|
logerror("MapMgr: Tile (%u, %u) exists not in WDT, but as file?!",gx,gy);
|
|
// continue loading...
|
|
}
|
|
else
|
|
{
|
|
logerror("MAPMGR: Not loading MapTile (%u, %u) map %u, no entry in WDT tile map",gx,gy,m);
|
|
return;
|
|
}
|
|
}
|
|
|
|
if( !_tiles->GetTile(gx,gy) )
|
|
{
|
|
ADTFile *adt = new ADTFile();
|
|
char buf[300];
|
|
MakeMapFilename(buf,m,gx,gy);
|
|
if(adt->Load(buf))
|
|
{
|
|
logdebug("MAPMGR: Loaded ADT '%s'",buf);
|
|
MapTile *tile = new MapTile();
|
|
tile->ImportFromADT(adt);
|
|
_tiles->SetTile(tile,gx,gy);
|
|
logdebug("MAPMGR: Imported MapTile (%u, %u) for map %u",gx,gy,m);
|
|
}
|
|
else
|
|
{
|
|
logerror("MAPMGR: Loading ADT '%s' failed!",buf);
|
|
}
|
|
delete adt;
|
|
}
|
|
else
|
|
{
|
|
logdebug("MAPMGR: No need to load MapTile (%u, %u) map %u",gx,gy,m);
|
|
}
|
|
}
|
|
|
|
void MapMgr::_UnloadOldTiles(void)
|
|
{
|
|
for(int32 gy=0; gy<64; gy++)
|
|
{
|
|
for(int32 gx=0; gx<64; gx++)
|
|
{
|
|
if( (int32(_gridx) < gx-1 || int32(_gridx) > gx+1) && (int32(_gridy) < gy-1 || int32(_gridy) > gy+1) )
|
|
{
|
|
if(_tiles->GetTile(gx,gy))
|
|
{
|
|
logdebug("MAPMGR: Unloading old MapTile (%u, %u) map %u",gx,gy,_mapid);
|
|
_tiles->UnloadMapTile(gx,gy);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
// Using forceLoad is VERY ineffective here, because the tile is removed again after the next Update() call!
|
|
MapTile *MapMgr::GetTile(uint32 xg, uint32 yg, bool forceLoad)
|
|
{
|
|
MapTile *tile = _tiles->GetTile(xg,yg);
|
|
if(!tile && forceLoad)
|
|
{
|
|
_LoadTile(xg,yg,_mapid);
|
|
tile = _tiles->GetTile(xg,yg);
|
|
}
|
|
return tile;
|
|
}
|
|
|
|
MapTile *MapMgr::GetCurrentTile(void)
|
|
{
|
|
return GetTile(_gridx,_gridy);
|
|
}
|
|
|
|
MapTile *MapMgr::GetNearTile(int32 xoffs, int32 yoffs)
|
|
{
|
|
return GetTile(_gridx + xoffs, _gridy + yoffs);
|
|
}
|
|
|
|
uint32 MapMgr::GetGridCoord(float f)
|
|
{
|
|
return (ZEROPOINT - f) / TILESIZE;
|
|
}
|
|
|
|
GridCoordPair MapMgr::GetTransformGridCoordPair(float x, float y)
|
|
{
|
|
return GridCoordPair(GetGridCoord(y), GetGridCoord(x)); // yes, they are reversed. definitely.
|
|
}
|
|
|
|
uint32 MapMgr::GetLoadedMapsCount(void)
|
|
{
|
|
uint32 counter = 0;
|
|
for(uint32 i = 0; i < 4096; i++)
|
|
{
|
|
if(_tiles->GetTile(i))
|
|
{
|
|
counter++;
|
|
}
|
|
}
|
|
return counter;
|
|
}
|
|
|
|
float MapMgr::GetZ(float x, float y)
|
|
{
|
|
return -99999.0f; // for now return lowest possible number, GetZ() will be implemented correctly later
|
|
/* GridCoordPair gcoords = GetTransformGridCoordPair(x,y);
|
|
MapTile *tile = _tiles->GetTile(gcoords.x,gcoords.y);
|
|
if(tile)
|
|
{
|
|
#ifdef _DEBUG
|
|
tile->DebugDumpToFile();
|
|
logdebug("DEBUG: tile dumped");
|
|
#endif
|
|
return tile->GetZ(x,y);
|
|
}
|
|
|
|
logerror("MapMgr::GetZ() called for not loaded MapTile (%u, %u) for (%f, %f)",gcoords.x,gcoords.y,x,y);
|
|
return 0;*/
|
|
}
|
|
|
|
std::string MapMgr::GetLoadedTilesString(void)
|
|
{
|
|
std::stringstream s;
|
|
for(uint32 x = 0; x < 64; x++)
|
|
{
|
|
for(uint32 y = 0; y < 64; y++)
|
|
if(_tiles->GetTile(x,y))
|
|
s << "(" << x << "|" << y << ") ";
|
|
}
|
|
return s.str();
|
|
}
|
|
|