From 5e7e440c5dfdcf41e7a1b702725d13ff11eb193c Mon Sep 17 00:00:00 2001 From: Mark Vejvoda Date: Wed, 13 Nov 2013 18:05:47 +0000 Subject: [PATCH] attempt to see if this improves performance --- source/glest_game/type_instances/faction.h | 11 ++++ source/glest_game/type_instances/unit.cpp | 34 +++++++--- source/glest_game/type_instances/unit.h | 3 + source/glest_game/world/world.cpp | 74 +++++++++++----------- source/glest_game/world/world.h | 14 +--- 5 files changed, 78 insertions(+), 58 deletions(-) diff --git a/source/glest_game/type_instances/faction.h b/source/glest_game/type_instances/faction.h index b3ea97ba..47c6852d 100644 --- a/source/glest_game/type_instances/faction.h +++ b/source/glest_game/type_instances/faction.h @@ -50,6 +50,7 @@ class ScriptManager; class World; class Faction; class GameSettings; +class SurfaceCell; class FowAlphaCellsLookupItem { public: @@ -57,6 +58,16 @@ public: std::map surfPosAlphaList; }; +class ExploredCellsLookupItem { +public: + + int ExploredCellsLookupItemCacheTimerCountIndex; + std::vector exploredCellList; + std::vector visibleCellList; + + static time_t lastDebug; +}; + // ===================================================== // class Faction // diff --git a/source/glest_game/type_instances/unit.cpp b/source/glest_game/type_instances/unit.cpp index 69dfa08a..ccc5216b 100644 --- a/source/glest_game/type_instances/unit.cpp +++ b/source/glest_game/type_instances/unit.cpp @@ -1251,25 +1251,29 @@ void Unit::refreshPos() { } FowAlphaCellsLookupItem Unit::getFogOfWarRadius(bool useCache) const { - //if(useCache == true && Config::getInstance().getBool("EnableFowCache","true") == true) { if(useCache == true) { return cachedFow; } - FowAlphaCellsLookupItem result; //iterate through all cells int sightRange= this->getType()->getSight(); - PosCircularIterator pci(map, this->getPosNotThreadSafe(), sightRange + World::indirectSightRange); + int radius = sightRange + World::indirectSightRange; + PosCircularIterator pci(map, this->getPosNotThreadSafe(), radius); + FowAlphaCellsLookupItem result; while(pci.next()){ const Vec2i sightpos= pci.getPos(); Vec2i surfPos= Map::toSurfCoords(sightpos); //compute max alpha float maxAlpha= 0.0f; - if(surfPos.x > 1 && surfPos.y > 1 && surfPos.x < map->getSurfaceW() -2 && surfPos.y < map->getSurfaceH() -2) { + if(surfPos.x > 1 && surfPos.y > 1 && + surfPos.x < map->getSurfaceW() -2 && + surfPos.y < map->getSurfaceH() -2) { maxAlpha= 1.f; } - else if(surfPos.x > 0 && surfPos.y > 0 && surfPos.x < map->getSurfaceW() -1 && surfPos.y < map->getSurfaceH() -1) { + else if(surfPos.x > 0 && surfPos.y > 0 && + surfPos.x < map->getSurfaceW() -1 && + surfPos.y < map->getSurfaceH() -1) { maxAlpha= 0.3f; } @@ -3927,10 +3931,10 @@ uint32 Unit::getFrameCount() const { } void Unit::exploreCells() { - if(this->isOperative()) { + if(this->isOperative() == true) { const Vec2i &newPos = this->getCenteredPos(); - int sightRange = this->getType()->getSight(); - int teamIndex = this->getTeam(); + int sightRange = this->getType()->getSight(); + int teamIndex = this->getTeam(); if(game == NULL) { throw megaglest_runtime_error("game == NULL"); @@ -3939,7 +3943,19 @@ void Unit::exploreCells() { throw megaglest_runtime_error("game->getWorld() == NULL"); } - game->getWorld()->exploreCells(newPos, sightRange, teamIndex); + // Try the local unit exploration cache + if(cacheExploredCellsKey.first == newPos && + cacheExploredCellsKey.second == sightRange) { + game->getWorld()->exploreCells(teamIndex, cacheExploredCells); + } + else { + // Try the world exploration scan or possible cache + cacheExploredCells = game->getWorld()->exploreCells(newPos, sightRange, teamIndex); + + // Cache the result for this unit + cacheExploredCellsKey.first = newPos; + cacheExploredCellsKey.second = sightRange; + } } } diff --git a/source/glest_game/type_instances/unit.h b/source/glest_game/type_instances/unit.h index 1cfd7274..44882363 100644 --- a/source/glest_game/type_instances/unit.h +++ b/source/glest_game/type_instances/unit.h @@ -474,6 +474,9 @@ private: FowAlphaCellsLookupItem cachedFow; Vec2i cachedFowPos; + ExploredCellsLookupItem cacheExploredCells; + std::pair cacheExploredCellsKey; + Vec2i lastHarvestedResourcePos; string networkCRCLogInfo; diff --git a/source/glest_game/world/world.cpp b/source/glest_game/world/world.cpp index 3888156b..757996f5 100644 --- a/source/glest_game/world/world.cpp +++ b/source/glest_game/world/world.cpp @@ -2273,18 +2273,26 @@ void World::initMap() { if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",__FILE__,__FUNCTION__,__LINE__); } +void World::exploreCells(int teamIndex, ExploredCellsLookupItem &exploredCellsCache) { + std::vector &cellList = exploredCellsCache.exploredCellList; + for (int idx2 = 0; idx2 < cellList.size(); ++idx2) { + SurfaceCell* sc = cellList[idx2]; + sc->setExplored(teamIndex, true); + } + cellList = exploredCellsCache.visibleCellList; + for (int idx2 = 0; idx2 < cellList.size(); ++idx2) { + SurfaceCell* sc = cellList[idx2]; + sc->setVisible(teamIndex, true); + } +} + // ==================== exploration ==================== -void World::exploreCells(const Vec2i &newPos, int sightRange, int teamIndex) { - //bool cacheLookupPosResult = false; - //bool cacheLookupSightResult = false; - +ExploredCellsLookupItem World::exploreCells(const Vec2i &newPos, int sightRange, int teamIndex) { // cache lookup of previously calculated cells + sight range - //if(MaxExploredCellsLookupItemCache > 0 && game->isMasterserverMode() == false) { if(MaxExploredCellsLookupItemCache > 0) { if(difftime(time(NULL),ExploredCellsLookupItem::lastDebug) >= 10) { ExploredCellsLookupItem::lastDebug = time(NULL); - //printf("In [%s::%s Line: %d] ExploredCellsLookupItemCache.size() = %d\n",__FILE__,__FUNCTION__,__LINE__,ExploredCellsLookupItemCache.size()); if(SystemFlags::getSystemSettingType(SystemFlags::debugSystem).enabled) SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d] ExploredCellsLookupItemCache.size() = %d\n",__FILE__,__FUNCTION__,__LINE__,ExploredCellsLookupItemCache.size()); if(SystemFlags::getSystemSettingType(SystemFlags::debugPerformance).enabled) SystemFlags::OutputDebug(SystemFlags::debugPerformance,"In [%s::%s Line: %d] ExploredCellsLookupItemCache.size() = %d\n",__FILE__,__FUNCTION__,__LINE__,ExploredCellsLookupItemCache.size()); } @@ -2299,7 +2307,7 @@ void World::exploreCells(const Vec2i &newPos, int sightRange, int teamIndex) { ExploredCellsLookupItemCache[purgeItem->second.pos].erase(purgeItem->second.sightRange); - if(ExploredCellsLookupItemCache[purgeItem->second.pos].size() == 0) { + if(ExploredCellsLookupItemCache[purgeItem->second.pos].empty() == true) { ExploredCellsLookupItemCache.erase(purgeItem->second.pos); } @@ -2310,57 +2318,49 @@ void World::exploreCells(const Vec2i &newPos, int sightRange, int teamIndex) { // cache if already found std::map >::iterator iterFind = ExploredCellsLookupItemCache.find(newPos); if(iterFind != ExploredCellsLookupItemCache.end()) { - //cacheLookupPosResult = true; std::map::iterator iterFind2 = iterFind->second.find(sightRange); if(iterFind2 != iterFind->second.end()) { - //cacheLookupSightResult = true; - std::vector &cellList = iterFind2->second.exploredCellList; - for(int idx2 = 0; idx2 < cellList.size(); ++idx2) { - SurfaceCell *sc = cellList[idx2]; - sc->setExplored(teamIndex, true); - } - cellList = iterFind2->second.visibleCellList; - for(int idx2 = 0; idx2 < cellList.size(); ++idx2) { - SurfaceCell *sc = cellList[idx2]; - sc->setVisible(teamIndex, true); - } + ExploredCellsLookupItem &exploredCellsCache = iterFind2->second; + exploreCells(teamIndex, exploredCellsCache); // Only start worrying about updating the cache timer if we // have hit the threshold if(MaxExploredCellsLookupItemCacheTriggered == true) { // Remove the old timer entry since the search key id is stale - ExploredCellsLookupItemCacheTimer.erase(iterFind2->second.ExploredCellsLookupItemCacheTimerCountIndex); - iterFind2->second.ExploredCellsLookupItemCacheTimerCountIndex = ExploredCellsLookupItemCacheTimerCount++; + ExploredCellsLookupItemCacheTimer.erase(exploredCellsCache.ExploredCellsLookupItemCacheTimerCountIndex); + exploredCellsCache.ExploredCellsLookupItemCacheTimerCountIndex = ExploredCellsLookupItemCacheTimerCount++; ExploredCellsLookupKey lookupKey; lookupKey.pos = newPos; lookupKey.sightRange = sightRange; lookupKey.teamIndex = teamIndex; - // Add a new search key since we just used this item - ExploredCellsLookupItemCacheTimer[iterFind2->second.ExploredCellsLookupItemCacheTimerCountIndex] = lookupKey; + // Add a new search key since we just used this exploredCellsCache + ExploredCellsLookupItemCacheTimer[exploredCellsCache.ExploredCellsLookupItemCacheTimerCountIndex] = lookupKey; } - return; + return exploredCellsCache; } } } Vec2i newSurfPos= Map::toSurfCoords(newPos); - int surfSightRange= sightRange/Map::cellScale+1; + int surfSightRange= sightRange / Map::cellScale+1; // Explore, this code is quite expensive when we have lots of units - ExploredCellsLookupItem item; + ExploredCellsLookupItem exploredCellsCache; + exploredCellsCache.exploredCellList.reserve(surfSightRange + indirectSightRange * 4); + exploredCellsCache.visibleCellList.reserve(surfSightRange + indirectSightRange * 4); - int loopCount = 0; + //int loopCount = 0; for(int i = -surfSightRange - indirectSightRange -1; i <= surfSightRange + indirectSightRange +1; ++i) { for(int j = -surfSightRange - indirectSightRange -1; j <= surfSightRange + indirectSightRange +1; ++j) { - loopCount++; + //loopCount++; Vec2i currRelPos= Vec2i(i, j); Vec2i currPos= newSurfPos + currRelPos; - if(map.isInsideSurface(currPos)){ + if(map.isInsideSurface(currPos) == true){ SurfaceCell *sc= map.getSurfaceCell(currPos); if(sc == NULL) { throw megaglest_runtime_error("sc == NULL"); @@ -2368,17 +2368,15 @@ void World::exploreCells(const Vec2i &newPos, int sightRange, int teamIndex) { //explore float posLength = currRelPos.length(); - //if(Vec2i(0).dist(currRelPos) < surfSightRange + indirectSightRange + 1) { if(posLength < surfSightRange + indirectSightRange + 1) { sc->setExplored(teamIndex, true); - item.exploredCellList.push_back(sc); + exploredCellsCache.exploredCellList.push_back(sc); } //visible - //if(Vec2i(0).dist(currRelPos) < surfSightRange) { if(posLength < surfSightRange) { sc->setVisible(teamIndex, true); - item.visibleCellList.push_back(sc); + exploredCellsCache.visibleCellList.push_back(sc); } } } @@ -2386,18 +2384,18 @@ void World::exploreCells(const Vec2i &newPos, int sightRange, int teamIndex) { // Ok update our caches with the latest info for this position, sight and team if(MaxExploredCellsLookupItemCache > 0) { - if(item.exploredCellList.empty() == false || item.visibleCellList.empty() == false) { - //ExploredCellsLookupItemCache.push_back(item); - item.ExploredCellsLookupItemCacheTimerCountIndex = ExploredCellsLookupItemCacheTimerCount++; - ExploredCellsLookupItemCache[newPos][sightRange] = item; + if(exploredCellsCache.exploredCellList.empty() == false || exploredCellsCache.visibleCellList.empty() == false) { + exploredCellsCache.ExploredCellsLookupItemCacheTimerCountIndex = ExploredCellsLookupItemCacheTimerCount++; + ExploredCellsLookupItemCache[newPos][sightRange] = exploredCellsCache; ExploredCellsLookupKey lookupKey; lookupKey.pos = newPos; lookupKey.sightRange = sightRange; lookupKey.teamIndex = teamIndex; - ExploredCellsLookupItemCacheTimer[item.ExploredCellsLookupItemCacheTimerCountIndex] = lookupKey; + ExploredCellsLookupItemCacheTimer[exploredCellsCache.ExploredCellsLookupItemCacheTimerCountIndex] = lookupKey; } } + return exploredCellsCache; } bool World::showWorldForPlayer(int factionIndex, bool excludeFogOfWarCheck) const { diff --git a/source/glest_game/world/world.h b/source/glest_game/world/world.h index a59f8c57..91f0f6e6 100644 --- a/source/glest_game/world/world.h +++ b/source/glest_game/world/world.h @@ -66,16 +66,6 @@ public: int teamIndex; }; -class ExploredCellsLookupItem { -public: - - int ExploredCellsLookupItemCacheTimerCountIndex; - std::vector exploredCellList; - std::vector visibleCellList; - - static time_t lastDebug; -}; - class World { private: typedef vector Factions; @@ -298,7 +288,8 @@ public: } bool canTickWorld() const; - void exploreCells(const Vec2i &newPos, int sightRange, int teamIndex); + ExploredCellsLookupItem exploreCells(const Vec2i &newPos, int sightRange, int teamIndex); + void exploreCells(int teamIndex,ExploredCellsLookupItem &exploredCellsCache); bool showWorldForPlayer(int factionIndex, bool excludeFogOfWarCheck=false) const; inline UnitUpdater * getUnitUpdater() { return &unitUpdater; } @@ -341,6 +332,7 @@ private: void underTakeDeadFactionUnits(); void updateAllFactionConsumableCosts(); void restoreExploredFogOfWarCells(); + }; }}//end namespace