From 1468f6aded05c37ec92c97b3435050ef10d7ec01 Mon Sep 17 00:00:00 2001 From: Ivan Savenko Date: Tue, 20 Dec 2022 16:14:06 +0200 Subject: [PATCH] Converted terrainTypeHandler into proper handler class --- client/CMusicHandler.cpp | 31 +- client/CPlayerInterface.cpp | 2 +- client/mapHandler.cpp | 16 +- client/widgets/AdventureMapClasses.cpp | 16 +- config/terrains.json | 20 +- lib/CCreatureHandler.cpp | 4 +- lib/CGeneralTextHandler.cpp | 2 - lib/CGeneralTextHandler.h | 1 - lib/CHeroHandler.cpp | 13 - lib/CHeroHandler.h | 1 - lib/CModHandler.cpp | 3 + lib/CPathfinder.cpp | 4 +- lib/CStack.cpp | 2 +- lib/CTownHandler.cpp | 6 +- lib/GameConstants.h | 70 ++-- lib/HeroBonus.cpp | 10 +- lib/NetPacksLib.cpp | 6 +- lib/Terrain.cpp | 445 ++++++------------------- lib/Terrain.h | 149 +++++---- lib/VCMI_Lib.cpp | 2 + lib/VCMI_Lib.h | 8 + lib/mapObjects/CGHeroInstance.cpp | 10 +- lib/mapObjects/ObjectTemplate.cpp | 32 +- lib/mapping/CDrawRoadsOperation.cpp | 4 +- lib/mapping/CMap.cpp | 4 +- lib/mapping/CMapOperation.cpp | 10 +- lib/mapping/MapEditUtils.cpp | 2 +- lib/mapping/MapFormatH3M.cpp | 11 +- lib/mapping/MapFormatJson.cpp | 6 +- lib/rmg/CRmgTemplate.cpp | 12 +- lib/rmg/CZonePlacer.cpp | 8 +- lib/rmg/ConnectionsPlacer.cpp | 6 +- lib/rmg/Functions.cpp | 16 +- lib/rmg/RiverPlacer.cpp | 14 +- lib/rmg/RmgMap.cpp | 2 +- lib/rmg/RmgObject.cpp | 2 +- lib/rmg/RoadPlacer.cpp | 4 +- lib/rmg/RockPlacer.cpp | 4 +- lib/rmg/Zone.cpp | 2 +- mapeditor/mainwindow.cpp | 22 +- mapeditor/maphandler.cpp | 12 +- mapeditor/objectbrowser.cpp | 4 +- server/CGameHandler.cpp | 2 +- 43 files changed, 410 insertions(+), 590 deletions(-) diff --git a/client/CMusicHandler.cpp b/client/CMusicHandler.cpp index 053876cad..4291dcd12 100644 --- a/client/CMusicHandler.cpp +++ b/client/CMusicHandler.cpp @@ -94,30 +94,29 @@ CSoundHandler::CSoundHandler(): //TODO: support custom sounds for new terrains and load from json horseSounds = { - {Terrain::DIRT, soundBase::horseDirt}, - {Terrain::SAND, soundBase::horseSand}, - {Terrain::GRASS, soundBase::horseGrass}, - {Terrain::SNOW, soundBase::horseSnow}, - {Terrain::SWAMP, soundBase::horseSwamp}, - {Terrain::ROUGH, soundBase::horseRough}, - {Terrain::SUBTERRANEAN, soundBase::horseSubterranean}, - {Terrain::LAVA, soundBase::horseLava}, - {Terrain::WATER, soundBase::horseWater}, - {Terrain::ROCK, soundBase::horseRock} + {TerrainId::DIRT, soundBase::horseDirt}, + {TerrainId::SAND, soundBase::horseSand}, + {TerrainId::GRASS, soundBase::horseGrass}, + {TerrainId::SNOW, soundBase::horseSnow}, + {TerrainId::SWAMP, soundBase::horseSwamp}, + {TerrainId::ROUGH, soundBase::horseRough}, + {TerrainId::SUBTERRANEAN, soundBase::horseSubterranean}, + {TerrainId::LAVA, soundBase::horseLava}, + {TerrainId::WATER, soundBase::horseWater}, + {TerrainId::ROCK, soundBase::horseRock} }; } void CSoundHandler::loadHorseSounds() { - const auto & terrains = CGI->terrainTypeHandler->terrains(); - for(const auto & terrain : terrains) + for(const auto & terrain : CGI->terrainTypeHandler->objects) { //since all sounds are hardcoded, let's keep it - if(vstd::contains(horseSounds, terrain.id)) + if(vstd::contains(horseSounds, terrain->id)) continue; //Use already existing horse sound - horseSounds[terrain.id] = horseSounds.at(terrains[terrain.id].horseSoundId); + horseSounds[terrain->id] = horseSounds.at(static_cast(CGI->terrainTypeHandler->getById(terrain->id)->horseSoundId)); } } @@ -368,9 +367,9 @@ CMusicHandler::CMusicHandler(): void CMusicHandler::loadTerrainMusicThemes() { - for (const auto & terrain : CGI->terrainTypeHandler->terrains()) + for (const auto & terrain : CGI->terrainTypeHandler->objects) { - addEntryToSet("terrain_" + terrain.name, "Music/" + terrain.musicFilename); + addEntryToSet("terrain_" + terrain->name, "Music/" + terrain->musicFilename); } } diff --git a/client/CPlayerInterface.cpp b/client/CPlayerInterface.cpp index 20c0be95f..62ffc5335 100644 --- a/client/CPlayerInterface.cpp +++ b/client/CPlayerInterface.cpp @@ -2372,7 +2372,7 @@ void CPlayerInterface::doMoveHero(const CGHeroInstance * h, CGPath path) for (auto & elem : path.nodes) elem.coord = h->convertFromVisitablePos(elem.coord); - TerrainId currentTerrain = Terrain::BORDER; // not init yet + TerrainId currentTerrain = TerrainId::BORDER; // not init yet TerrainId newTerrain; int sh = -1; diff --git a/client/mapHandler.cpp b/client/mapHandler.cpp index 05fb0d797..2395d90cc 100644 --- a/client/mapHandler.cpp +++ b/client/mapHandler.cpp @@ -175,17 +175,17 @@ void CMapHandler::initTerrainGraphics() std::map terrainFiles; std::map riverFiles; std::map roadFiles; - for(const auto & terrain : VLC->terrainTypeHandler->terrains()) + for(const auto & terrain : VLC->terrainTypeHandler->objects) { - terrainFiles[terrain.name] = terrain.tilesFilename; + terrainFiles[terrain->name] = terrain->tilesFilename; } - for(const auto & river : VLC->terrainTypeHandler->rivers()) + for(const auto & river : VLC->riverTypeHandler->objects) { - riverFiles[river.fileName] = river.fileName; + riverFiles[river->fileName] = river->fileName; } - for(const auto & road : VLC->terrainTypeHandler->roads()) + for(const auto & road : VLC->roadTypeHandler->objects) { - roadFiles[road.fileName] = road.fileName; + roadFiles[road->fileName] = road->fileName; } loadFlipped(terrainAnimations, terrainImages, terrainFiles); @@ -1388,8 +1388,8 @@ void CMapHandler::getTerrainDescr(const int3 & pos, std::string & out, bool isRM break; } } - if(!isTile2Terrain || out.empty()) - out = CGI->generaltexth->terrainNames[t.terType->id]; + + VLC->terrainTypeHandler->getById(t.terType->id)->terrainText; if(t.getDiggingStatus(false) == EDiggingStatus::CAN_DIG) { diff --git a/client/widgets/AdventureMapClasses.cpp b/client/widgets/AdventureMapClasses.cpp index 17023a650..d9856e882 100644 --- a/client/widgets/AdventureMapClasses.cpp +++ b/client/widgets/AdventureMapClasses.cpp @@ -499,25 +499,25 @@ std::map > CMinimap::loadColors() { std::map > ret; - for(const auto & terrain : CGI->terrainTypeHandler->terrains()) + for(const auto & terrain : CGI->terrainTypeHandler->objects) { SDL_Color normal = { - ui8(terrain.minimapUnblocked[0]), - ui8(terrain.minimapUnblocked[1]), - ui8(terrain.minimapUnblocked[2]), + ui8(terrain->minimapUnblocked[0]), + ui8(terrain->minimapUnblocked[1]), + ui8(terrain->minimapUnblocked[2]), ui8(255) }; SDL_Color blocked = { - ui8(terrain.minimapBlocked[0]), - ui8(terrain.minimapBlocked[1]), - ui8(terrain.minimapBlocked[2]), + ui8(terrain->minimapBlocked[0]), + ui8(terrain->minimapBlocked[1]), + ui8(terrain->minimapBlocked[2]), ui8(255) }; - ret[terrain.id] = std::make_pair(normal, blocked); + ret[terrain->id] = std::make_pair(normal, blocked); } return ret; } diff --git a/config/terrains.json b/config/terrains.json index 149ca98c3..7968cfcac 100644 --- a/config/terrains.json +++ b/config/terrains.json @@ -1,7 +1,7 @@ { "dirt" : { - "originalTerrainId": 0, + "index": 0, "moveCost" : 100, "minimapUnblocked" : [ 82, 56, 8 ], "minimapBlocked" : [ 57, 40, 8 ], @@ -15,7 +15,7 @@ }, "sand" : { - "originalTerrainId": 1, + "index": 1, "moveCost" : 150, "minimapUnblocked" : [ 222, 207, 140 ], "minimapBlocked" : [ 165, 158, 107 ], @@ -30,7 +30,7 @@ }, "grass" : { - "originalTerrainId": 2, + "index": 2, "moveCost" : 100, "minimapUnblocked" : [ 0, 65, 0 ], "minimapBlocked" : [ 0, 48, 0 ], @@ -43,7 +43,7 @@ }, "snow" : { - "originalTerrainId": 3, + "index": 3, "moveCost" : 150, "minimapUnblocked" : [ 181, 199, 198 ], "minimapBlocked" : [ 140, 158, 156 ], @@ -56,7 +56,7 @@ }, "swamp" : { - "originalTerrainId": 4, + "index": 4, "moveCost" : 175, "minimapUnblocked" : [ 74, 134, 107 ], "minimapBlocked" : [ 33, 89, 66 ], @@ -69,7 +69,7 @@ }, "rough" : { - "originalTerrainId": 5, + "index": 5, "moveCost" : 125, "minimapUnblocked" : [ 132, 113, 49 ], "minimapBlocked" : [ 99, 81, 33 ], @@ -82,7 +82,7 @@ }, "subterra" : { - "originalTerrainId": 6, + "index": 6, "moveCost" : 100, "minimapUnblocked" : [ 132, 48, 0 ], "minimapBlocked" : [ 90, 8, 0 ], @@ -97,7 +97,7 @@ }, "lava" : { - "originalTerrainId": 7, + "index": 7, "moveCost" : 100, "minimapUnblocked" : [ 74, 73, 74 ], "minimapBlocked" : [ 41, 40, 41 ], @@ -112,7 +112,7 @@ }, "water" : { - "originalTerrainId": 8, + "index": 8, "moveCost" : 100, "minimapUnblocked" : [ 8, 81, 148 ], "minimapBlocked" : [ 8, 81, 148 ], @@ -130,7 +130,7 @@ }, "rock" : { - "originalTerrainId": 9, + "index": 9, "moveCost" : -1, "minimapUnblocked" : [ 0, 0, 0 ], "minimapBlocked" : [ 0, 0, 0 ], diff --git a/lib/CCreatureHandler.cpp b/lib/CCreatureHandler.cpp index ac50e96c5..c2dc8878d 100644 --- a/lib/CCreatureHandler.cpp +++ b/lib/CCreatureHandler.cpp @@ -288,7 +288,7 @@ std::string CCreature::nodeName() const bool CCreature::isItNativeTerrain(TerrainId terrain) const { auto native = getNativeTerrain(); - return native == terrain || native == Terrain::ANY_TERRAIN; + return native == terrain || native == TerrainId::ANY_TERRAIN; } TerrainId CCreature::getNativeTerrain() const @@ -299,7 +299,7 @@ TerrainId CCreature::getNativeTerrain() const //this code is used in the CreatureTerrainLimiter::limit to setup battle bonuses //and in the CGHeroInstance::getNativeTerrain() to setup mevement bonuses or/and penalties. return hasBonus(selectorNoTerrainPenalty, selectorNoTerrainPenalty) - ? TerrainId(Terrain::ANY_TERRAIN) + ? TerrainId(TerrainId::ANY_TERRAIN) : (*VLC->townh)[faction]->nativeTerrain; } diff --git a/lib/CGeneralTextHandler.cpp b/lib/CGeneralTextHandler.cpp index 08746da4f..923b9a91c 100644 --- a/lib/CGeneralTextHandler.cpp +++ b/lib/CGeneralTextHandler.cpp @@ -343,7 +343,6 @@ CGeneralTextHandler::CGeneralTextHandler(): advobtxt (*this, "core.advevent" ), xtrainfo (*this, "core.xtrainfo" ), restypes (*this, "core.restypes" ), - terrainNames (*this, "core.terrname" ), randsign (*this, "core.randsign" ), overview (*this, "core.overview" ), arraytxt (*this, "core.arraytxt" ), @@ -372,7 +371,6 @@ CGeneralTextHandler::CGeneralTextHandler(): readToVector("core.advevent", "DATA/ADVEVENT.TXT" ); readToVector("core.xtrainfo", "DATA/XTRAINFO.TXT" ); readToVector("core.restypes", "DATA/RESTYPES.TXT" ); - readToVector("core.terrname", "DATA/TERRNAME.TXT" ); readToVector("core.randsign", "DATA/RANDSIGN.TXT" ); readToVector("core.overview", "DATA/OVERVIEW.TXT" ); readToVector("core.arraytxt", "DATA/ARRAYTXT.TXT" ); diff --git a/lib/CGeneralTextHandler.h b/lib/CGeneralTextHandler.h index bad392794..0e25fd38e 100644 --- a/lib/CGeneralTextHandler.h +++ b/lib/CGeneralTextHandler.h @@ -207,7 +207,6 @@ public: LegacyTextContainer advobtxt; LegacyTextContainer xtrainfo; LegacyTextContainer restypes; //names of resources - LegacyTextContainer terrainNames; LegacyTextContainer randsign; LegacyTextContainer seerEmpty; LegacyTextContainer seerNames; diff --git a/lib/CHeroHandler.cpp b/lib/CHeroHandler.cpp index 72bc7ce37..155d0b993 100644 --- a/lib/CHeroHandler.cpp +++ b/lib/CHeroHandler.cpp @@ -345,11 +345,6 @@ CHeroHandler::~CHeroHandler() = default; CHeroHandler::CHeroHandler() { - loadTerrains(); - for(const auto & terrain : VLC->terrainTypeHandler->terrains()) - { - VLC->modh->identifiers.registerObject(CModHandler::scopeBuiltin(), "terrain", terrain.name, terrain.id); - } loadBallistics(); loadExperience(); } @@ -972,14 +967,6 @@ ui64 CHeroHandler::reqExp (ui32 level) const } } -void CHeroHandler::loadTerrains() -{ - for(const auto & terrain : VLC->terrainTypeHandler->terrains()) - { - terrCosts[terrain.id] = terrain.moveCost; - } -} - std::vector CHeroHandler::getDefaultAllowed() const { // Look Data/HOTRAITS.txt for reference diff --git a/lib/CHeroHandler.h b/lib/CHeroHandler.h index 023015705..6f9e8be68 100644 --- a/lib/CHeroHandler.h +++ b/lib/CHeroHandler.h @@ -260,7 +260,6 @@ class DLL_LINKAGE CHeroHandler : public CHandlerBasescriptHandler, "script"))); #endif handlers.insert(std::make_pair("battlefields", ContentTypeHandler(VLC->battlefieldsHandler, "battlefield"))); + handlers.insert(std::make_pair("terrains", ContentTypeHandler(VLC->terrainTypeHandler, "terrain"))); + handlers.insert(std::make_pair("rivers", ContentTypeHandler(VLC->riverTypeHandler, "river"))); + handlers.insert(std::make_pair("roads", ContentTypeHandler(VLC->roadTypeHandler, "road"))); handlers.insert(std::make_pair("obstacles", ContentTypeHandler(VLC->obstacleHandler, "obstacle"))); //TODO: any other types of moddables? } diff --git a/lib/CPathfinder.cpp b/lib/CPathfinder.cpp index ba3813139..4fff7bac5 100644 --- a/lib/CPathfinder.cpp +++ b/lib/CPathfinder.cpp @@ -1000,10 +1000,10 @@ bool CPathfinderHelper::passOneTurnLimitCheck(const PathNodeInfo & source) const TurnInfo::BonusCache::BonusCache(TConstBonusListPtr bl) { - for(const auto & terrain : VLC->terrainTypeHandler->terrains()) + for(const auto & terrain : VLC->terrainTypeHandler->objects) { noTerrainPenalty.push_back(static_cast( - bl->getFirst(Selector::type()(Bonus::NO_TERRAIN_PENALTY).And(Selector::subtype()(terrain.id))))); + bl->getFirst(Selector::type()(Bonus::NO_TERRAIN_PENALTY).And(Selector::subtype()(terrain->id))))); } freeShipBoarding = static_cast(bl->getFirst(Selector::type()(Bonus::FREE_SHIP_BOARDING))); diff --git a/lib/CStack.cpp b/lib/CStack.cpp index 63046dfaa..f0c01bbc8 100644 --- a/lib/CStack.cpp +++ b/lib/CStack.cpp @@ -333,7 +333,7 @@ bool CStack::canBeHealed() const bool CStack::isOnNativeTerrain() const { //this code is called from CreatureTerrainLimiter::limit on battle start - auto res = nativeTerrain == Terrain::ANY_TERRAIN || nativeTerrain == battle->getTerrainType(); + auto res = nativeTerrain == TerrainId::ANY_TERRAIN || nativeTerrain == battle->getTerrainType(); return res; } diff --git a/lib/CTownHandler.cpp b/lib/CTownHandler.cpp index 6cda5f1e9..3727c0a9a 100644 --- a/lib/CTownHandler.cpp +++ b/lib/CTownHandler.cpp @@ -28,9 +28,9 @@ VCMI_LIB_NAMESPACE_BEGIN const int NAMES_PER_TOWN=16; // number of town names per faction in H3 files. Json can define any number -const TerrainId CTownHandler::defaultGoodTerrain(Terrain::GRASS); -const TerrainId CTownHandler::defaultEvilTerrain(Terrain::LAVA); -const TerrainId CTownHandler::defaultNeutralTerrain(Terrain::ROUGH); +const TerrainId CTownHandler::defaultGoodTerrain(TerrainId::GRASS); +const TerrainId CTownHandler::defaultEvilTerrain(TerrainId::LAVA); +const TerrainId CTownHandler::defaultNeutralTerrain(TerrainId::ROUGH); const std::map CBuilding::MODES = { diff --git a/lib/GameConstants.h b/lib/GameConstants.h index b995bc089..e119ee5bf 100644 --- a/lib/GameConstants.h +++ b/lib/GameConstants.h @@ -830,29 +830,6 @@ public: ID_LIKE_OPERATORS(Obj, Obj::EObj) -namespace Terrain -{ - enum ETerrain : si8 - { - NATIVE_TERRAIN = -4, - ANY_TERRAIN = -3, - WRONG = -2, - BORDER = -1, - FIRST_REGULAR_TERRAIN = 0, - DIRT = 0, - SAND, - GRASS, - SNOW, - SWAMP, - ROUGH, - SUBTERRANEAN, - LAVA, - WATER, - ROCK, - ORIGINAL_TERRAIN_COUNT - }; -} - namespace Road { enum ERoad : ui8 @@ -1181,7 +1158,50 @@ class BattleField : public BaseForID DLL_LINKAGE static BattleField fromString(std::string identifier); }; - + +class TerrainId +{ +public: + enum ETerrainID { + NATIVE_TERRAIN = -4, + ANY_TERRAIN = -3, + WRONG = -2, + BORDER = -1, + FIRST_REGULAR_TERRAIN = 0, + DIRT, + SAND, + GRASS, + SNOW, + SWAMP, + ROUGH, + SUBTERRANEAN, + LAVA, + WATER, + ROCK, + ORIGINAL_TERRAIN_COUNT + }; + + TerrainId(ETerrainID _num = WRONG) : num(_num) + {} + + ETerrainID num; + + ID_LIKE_CLASS_COMMON(TerrainId, ETerrainID) + + DLL_LINKAGE operator std::string() const; + DLL_LINKAGE const TerrainId * getInfo() const; + + DLL_LINKAGE static ETerrainID fromString(std::string identifier); + + TerrainId & operator++() + { + num = static_cast(static_cast(num) + 1); + return *this; + } +}; + +ID_LIKE_OPERATORS(TerrainId, TerrainId::ETerrainID) + class ObstacleInfo; class Obstacle : public BaseForID { @@ -1239,7 +1259,7 @@ typedef si64 TExpType; typedef std::pair TDmgRange; typedef si32 TBonusSubtype; typedef si32 TQuantity; -typedef si8 TerrainId; +//typedef si8 TerrainId; typedef si8 RoadId; typedef si8 RiverId; diff --git a/lib/HeroBonus.cpp b/lib/HeroBonus.cpp index 575e7c35a..333e59dba 100644 --- a/lib/HeroBonus.cpp +++ b/lib/HeroBonus.cpp @@ -2106,7 +2106,7 @@ bool CPropagatorNodeType::shouldBeAttached(CBonusSystemNode *dest) } CreatureTerrainLimiter::CreatureTerrainLimiter() - : terrainType(Terrain::NATIVE_TERRAIN) + : terrainType(TerrainId::NATIVE_TERRAIN) { } @@ -2120,7 +2120,7 @@ int CreatureTerrainLimiter::limit(const BonusLimitationContext &context) const const CStack *stack = retrieveStackBattle(&context.node); if(stack) { - if (terrainType == Terrain::NATIVE_TERRAIN)//terrainType not specified = native + if (terrainType == TerrainId::NATIVE_TERRAIN)//terrainType not specified = native { return !stack->isOnNativeTerrain(); } @@ -2136,8 +2136,8 @@ int CreatureTerrainLimiter::limit(const BonusLimitationContext &context) const std::string CreatureTerrainLimiter::toString() const { boost::format fmt("CreatureTerrainLimiter(terrainType=%s)"); - auto terrainName = VLC->terrainTypeHandler->terrains()[terrainType].name; - fmt % (terrainType == Terrain::NATIVE_TERRAIN ? "native" : terrainName); + auto terrainName = VLC->terrainTypeHandler->getById(terrainType)->name; + fmt % (terrainType == TerrainId::NATIVE_TERRAIN ? "native" : terrainName); return fmt.str(); } @@ -2146,7 +2146,7 @@ JsonNode CreatureTerrainLimiter::toJsonNode() const JsonNode root(JsonNode::JsonType::DATA_STRUCT); root["type"].String() = "CREATURE_TERRAIN_LIMITER"; - auto terrainName = VLC->terrainTypeHandler->terrains()[terrainType].name; + auto terrainName = VLC->terrainTypeHandler->getById(terrainType)->name; root["parameters"].Vector().push_back(JsonUtils::stringNode(terrainName)); return root; diff --git a/lib/NetPacksLib.cpp b/lib/NetPacksLib.cpp index 5e4e869ea..ddd1113a9 100644 --- a/lib/NetPacksLib.cpp +++ b/lib/NetPacksLib.cpp @@ -720,13 +720,13 @@ DLL_LINKAGE void GiveHero::applyGs(CGameState *gs) DLL_LINKAGE void NewObject::applyGs(CGameState *gs) { - TerrainId terrainType = Terrain::BORDER; + TerrainId terrainType = TerrainId::BORDER; if(ID == Obj::BOAT && !gs->isInTheMap(pos)) //special handling for bug #3060 - pos outside map but visitablePos is not { CGObjectInstance testObject = CGObjectInstance(); testObject.pos = pos; - testObject.appearance = VLC->objtypeh->getHandlerFor(ID, subID)->getTemplates(Terrain::WATER).front(); + testObject.appearance = VLC->objtypeh->getHandlerFor(ID, subID)->getTemplates(TerrainId::WATER).front(); const int3 previousXAxisTile = int3(pos.x - 1, pos.y, pos.z); assert(gs->isInTheMap(previousXAxisTile) && (testObject.visitablePos() == previousXAxisTile)); @@ -743,7 +743,7 @@ DLL_LINKAGE void NewObject::applyGs(CGameState *gs) { case Obj::BOAT: o = new CGBoat(); - terrainType = Terrain::WATER; //TODO: either boat should only spawn on water, or all water objects should be handled this way + terrainType = TerrainId::WATER; //TODO: either boat should only spawn on water, or all water objects should be handled this way break; case Obj::MONSTER: //probably more options will be needed o = new CGCreature(); diff --git a/lib/Terrain.cpp b/lib/Terrain.cpp index 5237a5c35..b1df78159 100644 --- a/lib/Terrain.cpp +++ b/lib/Terrain.cpp @@ -19,6 +19,7 @@ VCMI_LIB_NAMESPACE_BEGIN //("allowedTerrain"\s*:\s*\[.*)9(.*\],\n) //\1"rock"\2 +/* TerrainTypeHandler::TerrainTypeHandler() { auto allConfigs = VLC->modh->getActiveMods(); @@ -29,377 +30,168 @@ TerrainTypeHandler::TerrainTypeHandler() initRoads(allConfigs); recreateRoadMaps(); initTerrains(allConfigs); //maps will be populated inside -} +}*/ -void TerrainTypeHandler::initTerrains(const std::vector & allConfigs) +TerrainType * TerrainTypeHandler::loadFromJson( const std::string & scope, const JsonNode & json, const std::string & identifier, size_t index) { - std::vector> resolveLater; + TerrainType * info = new TerrainType; - objects.resize(Terrain::ORIGINAL_TERRAIN_COUNT); //make space for original terrains + info->id = TerrainId(index); - for(auto & mod : allConfigs) + info->moveCost = static_cast(json["moveCost"].Integer()); + info->musicFilename = json["music"].String(); + info->tilesFilename = json["tiles"].String(); + info->horseSoundId = static_cast(json["horseSoundId"].Float()); + info->transitionRequired = json["transitionRequired"].Bool(); + info->terrainViewPatterns = json["terrainViewPatterns"].String(); + info->terrainText = json["text"].String(); + + const JsonVector & unblockedVec = json["minimapUnblocked"].Vector(); + info->minimapUnblocked = { - if(!CResourceHandler::get(mod)->existsResource(ResourceID("config/terrains.json"))) - continue; - - JsonNode terrs(mod, ResourceID("config/terrains.json")); - for(auto & terr : terrs.Struct()) + ui8(unblockedVec[0].Float()), + ui8(unblockedVec[1].Float()), + ui8(unblockedVec[2].Float()) + }; + + const JsonVector &blockedVec = json["minimapBlocked"].Vector(); + info->minimapBlocked = + { + ui8(blockedVec[0].Float()), + ui8(blockedVec[1].Float()), + ui8(blockedVec[2].Float()) + }; + + for(const auto& node : json["type"].Vector()) + { + //Set bits + auto s = node.String(); + if (s == "LAND") info->passabilityType |= TerrainType::PassabilityType::LAND; + if (s == "WATER") info->passabilityType |= TerrainType::PassabilityType::WATER; + if (s == "ROCK") info->passabilityType |= TerrainType::PassabilityType::ROCK; + if (s == "SURFACE") info->passabilityType |= TerrainType::PassabilityType::SURFACE; + if (s == "SUB") info->passabilityType |= TerrainType::PassabilityType::SUBTERRANEAN; + } + +// if(json["river"].isNull()) +// info->river = River::NO_RIVER; +// else +// info->river = getRiverByCode(json["river"].String())->id; + + info->typeCode = json["code"].String(); + assert(info->typeCode.length() == 2); + + for(auto & t : json["battleFields"].Vector()) + info->battleFields.emplace_back(t.String()); + + + //Update terrain with this id in the future, after all terrain types are populated + + for(auto & t : json["prohibitTransitions"].Vector()) + { + VLC->modh->identifiers.requestIdentifier("terrain", t, [info](int32_t identifier) { - TerrainType info(terr.first); //set name - - info.moveCost = static_cast(terr.second["moveCost"].Integer()); - const JsonVector &unblockedVec = terr.second["minimapUnblocked"].Vector(); - info.minimapUnblocked = - { - ui8(unblockedVec[0].Float()), - ui8(unblockedVec[1].Float()), - ui8(unblockedVec[2].Float()) - }; - - const JsonVector &blockedVec = terr.second["minimapBlocked"].Vector(); - info.minimapBlocked = - { - ui8(blockedVec[0].Float()), - ui8(blockedVec[1].Float()), - ui8(blockedVec[2].Float()) - }; - info.musicFilename = terr.second["music"].String(); - info.tilesFilename = terr.second["tiles"].String(); - - if(terr.second["type"].isNull()) - { - info.passabilityType = TerrainType::PassabilityType::LAND | TerrainType::PassabilityType::SURFACE; - } - else if (terr.second["type"].getType() == JsonNode::JsonType::DATA_VECTOR) - { - for(const auto& node : terr.second["type"].Vector()) - { - //Set bits - auto s = node.String(); - if (s == "LAND") info.passabilityType |= TerrainType::PassabilityType::LAND; - if (s == "WATER") info.passabilityType |= TerrainType::PassabilityType::WATER; - if (s == "ROCK") info.passabilityType |= TerrainType::PassabilityType::ROCK; - if (s == "SURFACE") info.passabilityType |= TerrainType::PassabilityType::SURFACE; - if (s == "SUB") info.passabilityType |= TerrainType::PassabilityType::SUBTERRANEAN; - } - } - else //should be string - one option only - { - auto s = terr.second["type"].String(); - if (s == "LAND") info.passabilityType = TerrainType::PassabilityType::LAND; - if (s == "WATER") info.passabilityType = TerrainType::PassabilityType::WATER; - if (s == "ROCK") info.passabilityType = TerrainType::PassabilityType::ROCK; - if (s == "SURFACE") info.passabilityType = TerrainType::PassabilityType::SURFACE; - if (s == "SUB") info.passabilityType = TerrainType::PassabilityType::SUBTERRANEAN; - } - - if(terr.second["river"].isNull()) - { - info.river = River::NO_RIVER; - } - else - { - info.river = getRiverByCode(terr.second["river"].String())->id; - } - - if(terr.second["horseSoundId"].isNull()) - { - info.horseSoundId = Terrain::ROCK; //rock sound as default - } - else - { - info.horseSoundId = static_cast(terr.second["horseSoundId"].Float()); - } - - if(!terr.second["text"].isNull()) - { - info.terrainText = terr.second["text"].String(); - } - - if(terr.second["code"].isNull()) - { - info.typeCode = terr.first.substr(0, 2); - } - else - { - info.typeCode = terr.second["code"].String(); - assert(info.typeCode.length() == 2); - } - - if(!terr.second["battleFields"].isNull()) - { - for(auto & t : terr.second["battleFields"].Vector()) - { - info.battleFields.emplace_back(t.String()); - } - } - - info.transitionRequired = false; - if(!terr.second["transitionRequired"].isNull()) - { - info.transitionRequired = terr.second["transitionRequired"].Bool(); - } - - info.terrainViewPatterns = "normal"; - if(!terr.second["terrainViewPatterns"].isNull()) - { - info.terrainViewPatterns = terr.second["terrainViewPatterns"].String(); - } - - if(!terr.second["originalTerrainId"].isNull()) - { - //place in reserved slot - info.id = (TerrainId)(terr.second["originalTerrainId"].Float()); - objects[info.id] = info; - } - else - { - //append at the end - info.id = static_cast(objects.size()); - objects.push_back(info); - } - TerrainId id = info.id; - - //Update terrain with this id in the future, after all terrain types are populated - - if(!terr.second["prohibitTransitions"].isNull()) - { - for(auto & t : terr.second["prohibitTransitions"].Vector()) - { - std::string prohibitedTerrainName = t.String(); - resolveLater.push_back([this, prohibitedTerrainName, id]() - { - //FIXME: is that reference to the element in vector? - objects[id].prohibitTransitions.emplace_back(getInfoByName(prohibitedTerrainName)->id); - }); - } - } - - if(terr.second["rockTerrain"].isNull()) - { - objects[id].rockTerrain = Terrain::ROCK; - } - else - { - auto rockTerrainName = terr.second["rockTerrain"].String(); - resolveLater.push_back([this, rockTerrainName, id]() - { - //FIXME: is that reference to the element in vector? - objects[id].rockTerrain = getInfoByName(rockTerrainName)->id; - }); - } - } + info->prohibitTransitions.push_back(TerrainId(identifier)); + }); } - for(size_t i = Terrain::FIRST_REGULAR_TERRAIN; i < Terrain::ORIGINAL_TERRAIN_COUNT; i++) + info->rockTerrain = TerrainId::ROCK; + + if(!json["rockTerrain"].isNull()) { - //Make sure that original terrains are loaded - assert(objects[i].id != Terrain::WRONG); - } - - recreateTerrainMaps(); - - for(auto& functor : resolveLater) - { - functor(); - } -} - -void TerrainTypeHandler::initRivers(const std::vector & allConfigs) -{ - riverTypes.resize(River::ORIGINAL_RIVER_COUNT); //make space for original rivers - //First object will be default NO_RIVER - - for(auto & mod : allConfigs) - { - if (!CResourceHandler::get(mod)->existsResource(ResourceID("config/rivers.json"))) - continue; - - JsonNode rivs(mod, ResourceID("config/rivers.json")); - for(auto & river : rivs.Struct()) + auto rockTerrainName = json["rockTerrain"].String(); + VLC->modh->identifiers.requestIdentifier("terrain", rockTerrainName, [info](int32_t identifier) { - RiverType info; - - info.name = river.first; - info.fileName = river.second["animation"].String(); - info.code = river.second["code"].String(); - info.deltaName = river.second["delta"].String(); - - if (!river.second["originalRiverId"].isNull()) - { - info.id = static_cast(river.second["originalRiverId"].Float()); - riverTypes[info.id] = info; - } - else - { - info.id = static_cast(riverTypes.size()); - riverTypes.push_back(info); - } - } + info->rockTerrain = TerrainId(identifier); + }); } - recreateRiverMaps(); + return info; } -void TerrainTypeHandler::initRoads(const std::vector & allConfigs) +const std::vector & TerrainTypeHandler::getTypeNames() const { - roadTypes.resize(Road::ORIGINAL_ROAD_COUNT); //make space for original rivers - //first object will be default NO_ROAD - - for(auto & mod : allConfigs) - { - if (!CResourceHandler::get(mod)->existsResource(ResourceID("config/roads.json"))) - continue; - - JsonNode rds(mod, ResourceID("config/roads.json")); - for(auto & road : rds.Struct()) - { - RoadType info; - - info.name = road.first; - info.fileName = road.second["animation"].String(); - info.code = road.second["code"].String(); - info.movementCost = static_cast(road.second["moveCost"].Float()); - - if (!road.second["originalRoadId"].isNull()) - { - info.id = static_cast(road.second["originalRoadId"].Float()); - roadTypes[info.id] = info; - } - else - { - info.id = static_cast(roadTypes.size()); - roadTypes.push_back(info); - } - } - } - - recreateRoadMaps(); + static const std::vector typeNames = { "terrain" }; + return typeNames; } -void TerrainTypeHandler::recreateTerrainMaps() +std::vector TerrainTypeHandler::loadLegacyData(size_t dataSize) { - //This assumes the vector will never be updated or reallocated in the future - - for(size_t i = 0; i < objects.size(); i++) - { - const auto * terrainInfo = &objects[i]; - - terrainInfoByName[terrainInfo->name] = terrainInfo; - terrainInfoByCode[terrainInfo->typeCode] = terrainInfo; - terrainInfoById[terrainInfo->id] = terrainInfo; - } + return {}; } -void TerrainTypeHandler::recreateRiverMaps() +std::vector TerrainTypeHandler::getDefaultAllowed() const { - for(size_t i = River::FIRST_REGULAR_RIVER ; i < riverTypes.size(); i++) - { - const auto * riverInfo = &riverTypes[i]; - - riverInfoByName[riverInfo->name] = riverInfo; - riverInfoByCode[riverInfo->code] = riverInfo; - riverInfoById[riverInfo->id] = riverInfo; - } + return {}; } -void TerrainTypeHandler::recreateRoadMaps() +RiverType * RiverTypeHandler::loadFromJson( + const std::string & scope, + const JsonNode & json, + const std::string & identifier, + size_t index) { - for(size_t i = Road::FIRST_REGULAR_ROAD ; i < roadTypes.size(); i++) - { - const auto * roadInfo = &roadTypes[i]; + RiverType * info = new RiverType; - roadInfoByName[roadInfo->name] = roadInfo; - roadInfoByCode[roadInfo->code] = roadInfo; - roadInfoById[roadInfo->id] = roadInfo; - } + info->fileName = json["animation"].String(); + info->code = json["code"].String(); + info->deltaName = json["delta"].String(); + + return info; } -const std::vector & TerrainTypeHandler::terrains() const +const std::vector & RiverTypeHandler::getTypeNames() const { - //FIXME: somehow make it non-copyable? Pointers must point to original data and not its copy - return objects; + static const std::vector typeNames = { "river" }; + return typeNames; } -const std::vector& TerrainTypeHandler::rivers() const +std::vector RiverTypeHandler::loadLegacyData(size_t dataSize) { - return riverTypes; + return {}; } -const std::vector& TerrainTypeHandler::roads() const +std::vector RiverTypeHandler::getDefaultAllowed() const { - return roadTypes; + return {}; } -const TerrainType* TerrainTypeHandler::getInfoByName(const std::string& terrainName) const +RoadType * RoadTypeHandler::loadFromJson( + const std::string & scope, + const JsonNode & json, + const std::string & identifier, + size_t index) { - return terrainInfoByName.at(terrainName); + RoadType * info = new RoadType; + + info->fileName = json["animation"].String(); + info->code = json["code"].String(); + info->movementCost = json["moveCost"].Integer(); + + return info; } -const TerrainType* TerrainTypeHandler::getInfoByCode(const std::string& terrainCode) const +const std::vector & RoadTypeHandler::getTypeNames() const { - return terrainInfoByCode.at(terrainCode); + static const std::vector typeNames = { "river" }; + return typeNames; } -const TerrainType* TerrainTypeHandler::getInfoById(TerrainId id) const +std::vector RoadTypeHandler::loadLegacyData(size_t dataSize) { - return terrainInfoById.at(id); + return {}; } -const RiverType* TerrainTypeHandler::getRiverByName(const std::string& riverName) const +std::vector RoadTypeHandler::getDefaultAllowed() const { - return riverInfoByName.at(riverName); + return {}; } -const RiverType* TerrainTypeHandler::getRiverByCode(const std::string& riverCode) const -{ - return riverInfoByCode.at(riverCode); -} - -const RiverType* TerrainTypeHandler::getRiverById(RiverId id) const -{ - return riverInfoById.at(id); -} - -const RoadType* TerrainTypeHandler::getRoadByName(const std::string& roadName) const -{ - return roadInfoByName.at(roadName); -} - -const RoadType* TerrainTypeHandler::getRoadByCode(const std::string& roadCode) const -{ - return roadInfoByCode.at(roadCode); -} - -const RoadType* TerrainTypeHandler::getRoadById(RoadId id) const -{ - return roadInfoById.at(id); -} - -std::ostream & operator<<(std::ostream & os, const TerrainType & terrainType) -{ - return os << static_cast(terrainType); -} - TerrainType::operator std::string() const { return name; } - -TerrainType::TerrainType(const std::string& _name): - minimapBlocked({0,0,0}), //black - minimapUnblocked({ 128,128,128 }), //grey - name(_name), - river(River::NO_RIVER), - id(Terrain::WRONG), - rockTerrain(Terrain::ROCK), - moveCost(GameConstants::BASE_MOVEMENT_COST), - horseSoundId(0), - passabilityType(0), - transitionRequired(false) -{ -} - + bool TerrainType::operator==(const TerrainType& other) { return id == other.id; @@ -455,19 +247,4 @@ bool TerrainType::isTransitionRequired() const return transitionRequired; } -RiverType::RiverType(const std::string & fileName, const std::string & code, RiverId id): - fileName(fileName), - code(code), - id(id) -{ -} - -RoadType::RoadType(const std::string& fileName, const std::string& code, RoadId id): - fileName(fileName), - code(code), - id(id), - movementCost(GameConstants::BASE_MOVEMENT_COST) -{ -} - VCMI_LIB_NAMESPACE_END diff --git a/lib/Terrain.h b/lib/Terrain.h index 818d70e9e..29df6877d 100644 --- a/lib/Terrain.h +++ b/lib/Terrain.h @@ -10,16 +10,25 @@ #pragma once +#include +#include #include "ConstTransitivePtr.h" #include "GameConstants.h" #include "JsonNode.h" +#include "IHandlerBase.h" VCMI_LIB_NAMESPACE_BEGIN -class DLL_LINKAGE TerrainType +class DLL_LINKAGE TerrainType : public EntityT { public: - + int32_t getIndex() const override; + int32_t getIconIndex() const override; + const std::string & getName() const override; + const std::string & getJsonKey() const override; + void registerIcons(const IconRegistar & cb) const override; + TerrainId getId() const override; + enum PassabilityType : ui8 { LAND = 1, @@ -88,10 +97,16 @@ public: } }; -class DLL_LINKAGE RiverType +class DLL_LINKAGE RiverType : public EntityT { public: - std::string name; + int32_t getIndex() const override; + int32_t getIconIndex() const override; + const std::string & getName() const override; + const std::string & getJsonKey() const override; + void registerIcons(const IconRegistar & cb) const override; + TerrainId getId() const override; + std::string fileName; std::string code; std::string deltaName; @@ -101,10 +116,6 @@ public: template void serialize(Handler& h, const int version) { - if(version >= 806) - { - h & name; - } h & fileName; h & code; h & deltaName; @@ -112,10 +123,16 @@ public: } }; -class DLL_LINKAGE RoadType +class DLL_LINKAGE RoadType : public EntityT { public: - std::string name; + int32_t getIndex() const override; + int32_t getIconIndex() const override; + const std::string & getName() const override; + const std::string & getJsonKey() const override; + void registerIcons(const IconRegistar & cb) const override; + TerrainId getId() const override; + std::string fileName; std::string code; RoadId id; @@ -125,10 +142,6 @@ public: template void serialize(Handler& h, const int version) { - if(version >= 806) - { - h & name; - } h & fileName; h & code; h & id; @@ -136,69 +149,85 @@ public: } }; -DLL_LINKAGE std::ostream & operator<<(std::ostream & os, const TerrainType & terrainType); - -class DLL_LINKAGE TerrainTypeHandler //TODO: public IHandlerBase ? +class DLL_LINKAGE TerrainTypeService : public EntityServiceT { public: +}; - TerrainTypeHandler(); - ~TerrainTypeHandler() {}; +class DLL_LINKAGE RiverTypeService : public EntityServiceT +{ +public: +}; - const std::vector & terrains() const; - const TerrainType * getInfoByName(const std::string & terrainName) const; - const TerrainType * getInfoByCode(const std::string & terrainCode) const; - const TerrainType * getInfoById(TerrainId id) const; +class DLL_LINKAGE RoadTypeService : public EntityServiceT +{ +public: +}; - const std::vector & rivers() const; - const RiverType * getRiverByName(const std::string & riverName) const; - const RiverType * getRiverByCode(const std::string & riverCode) const; - const RiverType * getRiverById(RiverId id) const; +class DLL_LINKAGE TerrainTypeHandler : public CHandlerBase +{ +public: + virtual TerrainType * loadFromJson( + const std::string & scope, + const JsonNode & json, + const std::string & identifier, + size_t index) override; - const std::vector & roads() const; - const RoadType * getRoadByName(const std::string & roadName) const; - const RoadType * getRoadByCode(const std::string & roadCode) const; - const RoadType * getRoadById(RoadId id) const; + virtual const std::vector & getTypeNames() const override; + virtual std::vector loadLegacyData(size_t dataSize) override; + virtual std::vector getDefaultAllowed() const override; - template void serialize(Handler &h, const int version) + TerrainType * getInfoByCode(const std::string & identifier); + TerrainType * getInfoByName(const std::string & identifier); + + template void serialize(Handler & h, const int version) { h & objects; - h & riverTypes; - h & roadTypes; - - if (!h.saving) - { - recreateTerrainMaps(); - recreateRiverMaps(); - recreateRoadMaps(); - } } +}; -private: +class DLL_LINKAGE RiverTypeHandler : public CHandlerBase +{ +public: + virtual RiverType * loadFromJson( + const std::string & scope, + const JsonNode & json, + const std::string & identifier, + size_t index) override; - std::vector objects; - std::vector riverTypes; - std::vector roadTypes; + virtual const std::vector & getTypeNames() const override; + virtual std::vector loadLegacyData(size_t dataSize) override; + virtual std::vector getDefaultAllowed() const override; - std::unordered_map terrainInfoByName; - std::unordered_map terrainInfoByCode; - std::unordered_map terrainInfoById; + RiverType * getInfoByCode(const std::string & identifier); + RiverType * getInfoByName(const std::string & identifier); - std::unordered_map riverInfoByName; - std::unordered_map riverInfoByCode; - std::unordered_map riverInfoById; + template void serialize(Handler & h, const int version) + { + h & objects; + } +}; - std::unordered_map roadInfoByName; - std::unordered_map roadInfoByCode; - std::unordered_map roadInfoById; +class DLL_LINKAGE RoadTypeHandler : public CHandlerBase +{ +public: + virtual RoadType * loadFromJson( + const std::string & scope, + const JsonNode & json, + const std::string & identifier, + size_t index) override; - void initTerrains(const std::vector & allConfigs); - void initRivers(const std::vector & allConfigs); - void initRoads(const std::vector & allConfigs); - void recreateTerrainMaps(); - void recreateRiverMaps(); - void recreateRoadMaps(); + virtual const std::vector & getTypeNames() const override; + virtual std::vector loadLegacyData(size_t dataSize) override; + virtual std::vector getDefaultAllowed() const override; + RoadType * getInfoByCode(const std::string & identifier); + RoadType * getInfoByName(const std::string & identifier); + + template void serialize(Handler & h, const int version) + { + h & objects; + } }; VCMI_LIB_NAMESPACE_END diff --git a/lib/VCMI_Lib.cpp b/lib/VCMI_Lib.cpp index 4b74bf86f..19d8785a6 100644 --- a/lib/VCMI_Lib.cpp +++ b/lib/VCMI_Lib.cpp @@ -197,6 +197,8 @@ void LibClasses::init(bool onlyEssential) createHandler(bth, "Bonus type", pomtime); + createHandler(roadTypeHandler, "Road", pomtime); + createHandler(riverTypeHandler, "River", pomtime); createHandler(terrainTypeHandler, "Terrain", pomtime); createHandler(generaltexth, "General text", pomtime); diff --git a/lib/VCMI_Lib.h b/lib/VCMI_Lib.h index 738743aba..55e58712b 100644 --- a/lib/VCMI_Lib.h +++ b/lib/VCMI_Lib.h @@ -30,6 +30,8 @@ class BattleFieldHandler; class IBonusTypeHandler; class CBonusTypeHandler; class TerrainTypeHandler; +class RoadTypeHandler; +class RiverTypeHandler; class ObstacleHandler; class CTerrainViewPatternConfig; class CRmgTemplateStorage; @@ -86,7 +88,11 @@ public: CTownHandler * townh; CGeneralTextHandler * generaltexth; CModHandler * modh; + TerrainTypeHandler * terrainTypeHandler; + RoadTypeHandler * roadTypeHandler; + RiverTypeHandler * riverTypeHandler; + CTerrainViewPatternConfig * terviewh; CRmgTemplateStorage * tplh; BattleFieldHandler * battlefieldsHandler; @@ -127,6 +133,8 @@ public: h & skillh; h & battlefieldsHandler; h & obstacleHandler; + h & roadTypeHandler; + h & riverTypeHandler; h & terrainTypeHandler; if(!h.saving) diff --git a/lib/mapObjects/CGHeroInstance.cpp b/lib/mapObjects/CGHeroInstance.cpp index 6b5301732..d30d663df 100644 --- a/lib/mapObjects/CGHeroInstance.cpp +++ b/lib/mapObjects/CGHeroInstance.cpp @@ -86,7 +86,7 @@ ui32 CGHeroInstance::getTileCost(const TerrainTile & dest, const TerrainTile & f ret = std::max(dest.roadType->movementCost, from.roadType->movementCost); } else if(ti->nativeTerrain != from.terType->id &&//the terrain is not native - ti->nativeTerrain != Terrain::ANY_TERRAIN && //no special creature bonus + ti->nativeTerrain != TerrainId::ANY_TERRAIN && //no special creature bonus !ti->hasBonusOfType(Bonus::NO_TERRAIN_PENALTY, from.terType->id)) //no special movement bonus { @@ -106,18 +106,18 @@ TerrainId CGHeroInstance::getNativeTerrain() const // will always have best penalty without any influence from player-defined stacks order // TODO: What should we do if all hero stacks are neutral creatures? - TerrainId nativeTerrain = Terrain::BORDER; + TerrainId nativeTerrain = TerrainId::BORDER; for(auto stack : stacks) { TerrainId stackNativeTerrain = stack.second->type->getNativeTerrain(); //consider terrain bonuses e.g. Lodestar. - if(stackNativeTerrain == Terrain::BORDER) //where does this value come from? + if(stackNativeTerrain == TerrainId::BORDER) //where does this value come from? continue; - if(nativeTerrain == Terrain::BORDER) + if(nativeTerrain == TerrainId::BORDER) nativeTerrain = stackNativeTerrain; else if(nativeTerrain != stackNativeTerrain) - return Terrain::BORDER; + return TerrainId::BORDER; } return nativeTerrain; } diff --git a/lib/mapObjects/ObjectTemplate.cpp b/lib/mapObjects/ObjectTemplate.cpp index d91536542..4822058fd 100644 --- a/lib/mapObjects/ObjectTemplate.cpp +++ b/lib/mapObjects/ObjectTemplate.cpp @@ -157,20 +157,20 @@ void ObjectTemplate::readTxt(CLegacyConfigParser & parser) // so these two fields can be interpreted as "strong affinity" and "weak affinity" towards terrains std::string & terrStr = strings[4]; // allowed terrains, 1 = object can be placed on this terrain - assert(terrStr.size() == Terrain::ROCK); // all terrains but rock - counting from 0 - for(TerrainId i = Terrain::FIRST_REGULAR_TERRAIN; i < Terrain::ROCK; i++) + assert(terrStr.size() == TerrainId::ROCK); // all terrains but rock - counting from 0 + for(TerrainId i = TerrainId(0); i < TerrainId::ROCK; ++i) { if (terrStr[8-i] == '1') allowedTerrains.insert(i); } //assuming that object can be placed on other land terrains - if(allowedTerrains.size() >= 8 && !allowedTerrains.count(Terrain::WATER)) + if(allowedTerrains.size() >= 8 && !allowedTerrains.count(TerrainId::WATER)) { - for(const auto & terrain : VLC->terrainTypeHandler->terrains()) + for(const auto & terrain : VLC->terrainTypeHandler->objects) { - if(terrain.isLand() && terrain.isPassable()) - allowedTerrains.insert(terrain.id); + if(terrain->isLand() && terrain->isPassable()) + allowedTerrains.insert(terrain->id); } } @@ -231,19 +231,19 @@ void ObjectTemplate::readMap(CBinaryReader & reader) reader.readUInt16(); ui16 terrMask = reader.readUInt16(); - for(size_t i = Terrain::FIRST_REGULAR_TERRAIN; i < Terrain::ROCK; i++) + for(TerrainId i = TerrainId::FIRST_REGULAR_TERRAIN; i < TerrainId::ORIGINAL_TERRAIN_COUNT; ++i) { if (((terrMask >> i) & 1 ) != 0) allowedTerrains.insert(i); } //assuming that object can be placed on other land terrains - if(allowedTerrains.size() >= 8 && !allowedTerrains.count(Terrain::WATER)) + if(allowedTerrains.size() >= 8 && !allowedTerrains.count(TerrainId::WATER)) { - for(const auto & terrain : VLC->terrainTypeHandler->terrains()) + for(const auto & terrain : VLC->terrainTypeHandler->objects) { - if(terrain.isLand() && terrain.isPassable()) - allowedTerrains.insert(terrain.id); + if(terrain->isLand() && terrain->isPassable()) + allowedTerrains.insert(terrain->id); } } @@ -299,11 +299,11 @@ void ObjectTemplate::readJson(const JsonNode &node, const bool withTerrain) } else { - for(const auto & terrain : VLC->terrainTypeHandler->terrains()) + for(const auto & terrain : VLC->terrainTypeHandler->objects) { - if(!terrain.isPassable() || terrain.isWater()) + if(!terrain->isPassable() || terrain->isWater()) continue; - allowedTerrains.insert(terrain.id); + allowedTerrains.insert(terrain->id); } } @@ -378,14 +378,14 @@ void ObjectTemplate::writeJson(JsonNode & node, const bool withTerrain) const if(withTerrain) { //assumed that ROCK and WATER terrains are not included - if(allowedTerrains.size() < (VLC->terrainTypeHandler->terrains().size() - 2)) + if(allowedTerrains.size() < (VLC->terrainTypeHandler->objects.size() - 2)) { JsonVector & data = node["allowedTerrains"].Vector(); for(auto type : allowedTerrains) { JsonNode value(JsonNode::JsonType::DATA_STRING); - value.String() = type; + value.String() = VLC->terrainTypeHandler->getById(type)->name; data.push_back(value); } } diff --git a/lib/mapping/CDrawRoadsOperation.cpp b/lib/mapping/CDrawRoadsOperation.cpp index 4c529b17f..727037a3d 100644 --- a/lib/mapping/CDrawRoadsOperation.cpp +++ b/lib/mapping/CDrawRoadsOperation.cpp @@ -338,12 +338,12 @@ std::string CDrawRiversOperation::getLabel() const void CDrawRoadsOperation::executeTile(TerrainTile & tile) { - tile.roadType = const_cast(&VLC->terrainTypeHandler->roads()[roadType]); + tile.roadType = const_cast(VLC->roadTypeHandler->getByIndex(roadType)); } void CDrawRiversOperation::executeTile(TerrainTile & tile) { - tile.riverType = const_cast(&VLC->terrainTypeHandler->rivers()[riverType]); + tile.riverType = const_cast(VLC->riverTypeHandler->getByIndex(riverType)); } bool CDrawRoadsOperation::canApplyPattern(const LinePattern & pattern) const diff --git a/lib/mapping/CMap.cpp b/lib/mapping/CMap.cpp index 490653924..90ef2802b 100644 --- a/lib/mapping/CMap.cpp +++ b/lib/mapping/CMap.cpp @@ -128,9 +128,9 @@ CCastleEvent::CCastleEvent() : town(nullptr) TerrainTile::TerrainTile(): terType(nullptr), terView(0), - riverType(const_cast(&VLC->terrainTypeHandler->rivers()[River::NO_RIVER])), + riverType(nullptr), riverDir(0), - roadType(const_cast(&VLC->terrainTypeHandler->roads()[Road::NO_ROAD])), + roadType(nullptr), roadDir(0), extTileFlags(0), visitable(false), diff --git a/lib/mapping/CMapOperation.cpp b/lib/mapping/CMapOperation.cpp index 6f7798741..acc0c85c8 100644 --- a/lib/mapping/CMapOperation.cpp +++ b/lib/mapping/CMapOperation.cpp @@ -97,7 +97,7 @@ void CDrawTerrainOperation::execute() for(const auto & pos : terrainSel.getSelectedItems()) { auto & tile = map->getTile(pos); - tile.terType = const_cast(&VLC->terrainTypeHandler->terrains()[terType]); + tile.terType = const_cast(VLC->terrainTypeHandler->getById(terType)); invalidateTerrainViews(pos); } @@ -422,14 +422,14 @@ CDrawTerrainOperation::ValidationResult CDrawTerrainOperation::validateTerrainVi bool nativeTestOk, nativeTestStrongOk; nativeTestOk = nativeTestStrongOk = (rule.isNativeStrong() || rule.isNativeRule()) && !isAlien; - if(centerTerType->id == Terrain::DIRT) + if(centerTerType->id == TerrainId::DIRT) { nativeTestOk = rule.isNativeRule() && !terType->isTransitionRequired(); bool sandTestOk = (rule.isSandRule() || rule.isTransition()) && terType->isTransitionRequired(); applyValidationRslt(rule.isAnyRule() || sandTestOk || nativeTestOk || nativeTestStrongOk); } - else if(centerTerType->id == Terrain::SAND) + else if(centerTerType->id == TerrainId::SAND) { applyValidationRslt(true); } @@ -551,12 +551,12 @@ CClearTerrainOperation::CClearTerrainOperation(CMap* map, CRandomGenerator* gen) { CTerrainSelection terrainSel(map); terrainSel.selectRange(MapRect(int3(0, 0, 0), map->width, map->height)); - addOperation(std::make_unique(map, terrainSel, Terrain::WATER, gen)); + addOperation(std::make_unique(map, terrainSel, TerrainId::WATER, gen)); if(map->twoLevel) { terrainSel.clearSelection(); terrainSel.selectRange(MapRect(int3(0, 0, 1), map->width, map->height)); - addOperation(std::make_unique(map, terrainSel, Terrain::ROCK, gen)); + addOperation(std::make_unique(map, terrainSel, TerrainId::ROCK, gen)); } } diff --git a/lib/mapping/MapEditUtils.cpp b/lib/mapping/MapEditUtils.cpp index b0e9dc822..8845a0f94 100644 --- a/lib/mapping/MapEditUtils.cpp +++ b/lib/mapping/MapEditUtils.cpp @@ -272,7 +272,7 @@ CTerrainViewPatternConfig::~CTerrainViewPatternConfig() const std::vector & CTerrainViewPatternConfig::getTerrainViewPatterns(TerrainId terrain) const { - auto iter = terrainViewPatterns.find(VLC->terrainTypeHandler->terrains()[terrain].terrainViewPatterns); + auto iter = terrainViewPatterns.find(VLC->terrainTypeHandler->getById(terrain)->terrainViewPatterns); if (iter == terrainViewPatterns.end()) return terrainViewPatterns.at("normal"); return iter->second; diff --git a/lib/mapping/MapFormatH3M.cpp b/lib/mapping/MapFormatH3M.cpp index 719a8eb1e..d3984bc20 100644 --- a/lib/mapping/MapFormatH3M.cpp +++ b/lib/mapping/MapFormatH3M.cpp @@ -923,9 +923,6 @@ bool CMapLoaderH3M::loadArtifactToSlot(CGHeroInstance * hero, int slot) void CMapLoaderH3M::readTerrain() { map->initTerrain(); - const auto & terrains = VLC->terrainTypeHandler->terrains(); - const auto & rivers = VLC->terrainTypeHandler->rivers(); - const auto & roads = VLC->terrainTypeHandler->roads(); // Read terrain int3 pos; @@ -937,14 +934,14 @@ void CMapLoaderH3M::readTerrain() for(pos.x = 0; pos.x < map->width; pos.x++) { auto & tile = map->getTile(pos); - tile.terType = const_cast(&terrains[reader.readUInt8()]); + tile.terType = const_cast(VLC->terrainTypeHandler->getByIndex(reader.readUInt8())); tile.terView = reader.readUInt8(); - tile.riverType = const_cast(&rivers[reader.readUInt8()]); + tile.riverType = const_cast(VLC->riverTypeHandler->getByIndex(reader.readUInt8())); tile.riverDir = reader.readUInt8(); - tile.roadType = const_cast(&roads[reader.readUInt8()]); + tile.roadType = const_cast(VLC->roadTypeHandler->getByIndex(reader.readUInt8())); tile.roadDir = reader.readUInt8(); tile.extTileFlags = reader.readUInt8(); - tile.blocked = ((!tile.terType->isPassable() || tile.terType->id == Terrain::BORDER ) ? true : false); //underground tiles are always blocked + tile.blocked = ((!tile.terType->isPassable() || tile.terType->id == TerrainId::BORDER ) ? true : false); //underground tiles are always blocked tile.visitable = 0; } } diff --git a/lib/mapping/MapFormatJson.cpp b/lib/mapping/MapFormatJson.cpp index 158e94d10..ddb095a98 100644 --- a/lib/mapping/MapFormatJson.cpp +++ b/lib/mapping/MapFormatJson.cpp @@ -979,13 +979,13 @@ void CMapLoaderJson::readTerrainTile(const std::string & src, TerrainTile & tile startPos += 2; try { - tile.roadType = const_cast(VLC->terrainTypeHandler->getRoadByCode(typeCode)); + tile.roadType = const_cast(VLC->roadTypeHandler->getInfoByCode(typeCode)); } catch (const std::exception&) //it's not a road, it's a river { try { - tile.riverType = const_cast(VLC->terrainTypeHandler->getRiverByCode(typeCode)); + tile.riverType = const_cast(VLC->riverTypeHandler->getInfoByCode(typeCode)); hasRoad = false; } catch (const std::exception&) @@ -1021,7 +1021,7 @@ void CMapLoaderJson::readTerrainTile(const std::string & src, TerrainTile & tile {//river type const std::string typeCode = src.substr(startPos, 2); startPos += 2; - tile.riverType = const_cast(VLC->terrainTypeHandler->getRiverByCode(typeCode)); + tile.riverType = const_cast(VLC->riverTypeHandler->getInfoByCode(typeCode)); } {//river dir int pos = startPos; diff --git a/lib/rmg/CRmgTemplate.cpp b/lib/rmg/CRmgTemplate.cpp index 4e54e413a..235b7a658 100644 --- a/lib/rmg/CRmgTemplate.cpp +++ b/lib/rmg/CRmgTemplate.cpp @@ -74,8 +74,8 @@ public: static std::string encode(const si32 index) { - const auto& terrains = VLC->terrainTypeHandler->terrains(); - return (index >=0 && index < terrains.size()) ? terrains[index].name : ""; + const auto& terrains = VLC->terrainTypeHandler->objects; + return (index >=0 && index < terrains.size()) ? terrains[index]->name : ""; } }; @@ -152,9 +152,9 @@ ZoneOptions::ZoneOptions() terrainTypeLikeZone(NO_ZONE), treasureLikeZone(NO_ZONE) { - for(const auto & terr : VLC->terrainTypeHandler->terrains()) - if(terr.isLand() && terr.isPassable()) - terrainTypes.insert(terr.id); + for(const auto & terr : VLC->terrainTypeHandler->objects) + if(terr->isLand() && terr->isPassable()) + terrainTypes.insert(terr->id); } ZoneOptions & ZoneOptions::operator=(const ZoneOptions & other) @@ -365,7 +365,7 @@ void ZoneOptions::serializeJson(JsonSerializeFormat & handler) for(auto & ttype : terrainTypes) { JsonNode n; - n.String() = ttype; + n.String() = VLC->terrainTypeHandler->getById(ttype)->name; node.Vector().push_back(n); } } diff --git a/lib/rmg/CZonePlacer.cpp b/lib/rmg/CZonePlacer.cpp index 03616a48f..b09f83a9f 100644 --- a/lib/rmg/CZonePlacer.cpp +++ b/lib/rmg/CZonePlacer.cpp @@ -194,15 +194,15 @@ void CZonePlacer::prepareZones(TZoneMap &zones, TZoneVector &zonesVector, const else { auto & tt = (*VLC->townh)[faction]->nativeTerrain; - if(tt == Terrain::DIRT) + if(tt == TerrainId::DIRT) { //any / random zonesToPlace.push_back(zone); } else { - const auto & terrainType = VLC->terrainTypeHandler->terrains()[tt]; - if(terrainType.isUnderground() && !terrainType.isSurface()) + const auto & terrainType = VLC->terrainTypeHandler->getById(tt); + if(terrainType->isUnderground() && !terrainType->isSurface()) { //underground only zonesOnLevel[1]++; @@ -580,7 +580,7 @@ void CZonePlacer::assignZones(CRandomGenerator * rand) //make sure that terrain inside zone is not a rock //FIXME: reorder actions? - paintZoneTerrain(*zone.second, *rand, map, Terrain::SUBTERRANEAN); + paintZoneTerrain(*zone.second, *rand, map, TerrainId::SUBTERRANEAN); } } logGlobal->info("Finished zone colouring"); diff --git a/lib/rmg/ConnectionsPlacer.cpp b/lib/rmg/ConnectionsPlacer.cpp index ddcd5ebfe..4bf47a7ef 100644 --- a/lib/rmg/ConnectionsPlacer.cpp +++ b/lib/rmg/ConnectionsPlacer.cpp @@ -84,9 +84,9 @@ void ConnectionsPlacer::selfSideDirectConnection(const rmg::ZoneConnection & con //1. Try to make direct connection //Do if it's not prohibited by terrain settings - const auto& terrains = VLC->terrainTypeHandler->terrains(); - bool directProhibited = vstd::contains(terrains[zone.getTerrainType()].prohibitTransitions, otherZone->getTerrainType()) - || vstd::contains(terrains[otherZone->getTerrainType()].prohibitTransitions, zone.getTerrainType()); + const auto& terrains = VLC->terrainTypeHandler->objects; + bool directProhibited = vstd::contains(terrains[zone.getTerrainType()]->prohibitTransitions, otherZone->getTerrainType()) + || vstd::contains(terrains[otherZone->getTerrainType()]->prohibitTransitions, zone.getTerrainType()); auto directConnectionIterator = dNeighbourZones.find(otherZoneId); if(!directProhibited && directConnectionIterator != dNeighbourZones.end()) { diff --git a/lib/rmg/Functions.cpp b/lib/rmg/Functions.cpp index 04846ebe4..3b12e3668 100644 --- a/lib/rmg/Functions.cpp +++ b/lib/rmg/Functions.cpp @@ -119,9 +119,9 @@ void initTerrainType(Zone & zone, CMapGenerator & gen) { //collect all water terrain types std::vector waterTerrains; - for(const auto & terrain : VLC->terrainTypeHandler->terrains()) - if(terrain.isWater()) - waterTerrains.push_back(terrain.id); + for(const auto & terrain : VLC->terrainTypeHandler->objects) + if(terrain->isWater()) + waterTerrains.push_back(terrain->id); zone.setTerrainType(*RandomGeneratorUtil::nextItem(waterTerrains, gen.rand)); } @@ -137,20 +137,20 @@ void initTerrainType(Zone & zone, CMapGenerator & gen) } //Now, replace disallowed terrains on surface and in the underground - const auto & terrainType = VLC->terrainTypeHandler->terrains()[zone.getTerrainType()]; + const auto & terrainType = VLC->terrainTypeHandler->getById(zone.getTerrainType()); if(zone.isUnderground()) { - if(!terrainType.isUnderground()) + if(!terrainType->isUnderground()) { - zone.setTerrainType(Terrain::SUBTERRANEAN); + zone.setTerrainType(TerrainId::SUBTERRANEAN); } } else { - if (!terrainType.isSurface()) + if (!terrainType->isSurface()) { - zone.setTerrainType(Terrain::DIRT); + zone.setTerrainType(TerrainId::DIRT); } } } diff --git a/lib/rmg/RiverPlacer.cpp b/lib/rmg/RiverPlacer.cpp index 64ba549e5..3d5826e5e 100644 --- a/lib/rmg/RiverPlacer.cpp +++ b/lib/rmg/RiverPlacer.cpp @@ -86,7 +86,7 @@ void RiverPlacer::init() void RiverPlacer::drawRivers() { map.getEditManager()->getTerrainSelection().setSelection(rivers.getTilesVector()); - map.getEditManager()->drawRiver(VLC->terrainTypeHandler->terrains()[zone.getTerrainType()].river, &generator.rand); + map.getEditManager()->drawRiver(VLC->terrainTypeHandler->getById(zone.getTerrainType())->river, &generator.rand); } char RiverPlacer::dump(const int3 & t) @@ -195,7 +195,7 @@ void RiverPlacer::preprocess() //calculate delta positions if(connectedToWaterZoneId > -1) { - auto river = VLC->terrainTypeHandler->terrains()[zone.getTerrainType()].river; + auto river = VLC->terrainTypeHandler->getById(zone.getTerrainType())->river; auto & a = neighbourZonesTiles[connectedToWaterZoneId]; auto availableArea = zone.areaPossible() + zone.freePaths(); for(auto & tileToProcess : availableArea.getTilesVector()) @@ -321,9 +321,9 @@ void RiverPlacer::preprocess() void RiverPlacer::connectRiver(const int3 & tile) { - auto riverType = VLC->terrainTypeHandler->terrains()[zone.getTerrainType()].river; - const auto & river = VLC->terrainTypeHandler->rivers()[riverType]; - if(river.id == River::NO_RIVER) + auto riverType = VLC->terrainTypeHandler->getById(zone.getTerrainType())->river; + const auto * river = VLC->riverTypeHandler->getByIndex(riverType); + if(river->id == River::NO_RIVER) return; rmg::Area roads; @@ -381,9 +381,9 @@ void RiverPlacer::connectRiver(const int3 & tile) { if(tmplates.size() % 4 != 0) throw rmgException(boost::to_string(boost::format("River templates for (%d,%d) at terrain %s, river %s are incorrect") % - RIVER_DELTA_ID % RIVER_DELTA_SUBTYPE % zone.getTerrainType() % river.code)); + RIVER_DELTA_ID % RIVER_DELTA_SUBTYPE % zone.getTerrainType() % river->code)); - std::string targetTemplateName = river.deltaName + std::to_string(deltaOrientations[pos]) + ".def"; + std::string targetTemplateName = river->deltaName + std::to_string(deltaOrientations[pos]) + ".def"; for(auto & templ : tmplates) { if(templ->animationFile == targetTemplateName) diff --git a/lib/rmg/RmgMap.cpp b/lib/rmg/RmgMap.cpp index c1aac566e..834a8160a 100644 --- a/lib/rmg/RmgMap.cpp +++ b/lib/rmg/RmgMap.cpp @@ -84,7 +84,7 @@ void RmgMap::initTiles(CMapGenerator & generator) getEditManager()->clearTerrain(&generator.rand); getEditManager()->getTerrainSelection().selectRange(MapRect(int3(0, 0, 0), mapGenOptions.getWidth(), mapGenOptions.getHeight())); - getEditManager()->drawTerrain(Terrain::GRASS, &generator.rand); + getEditManager()->drawTerrain(TerrainId::GRASS, &generator.rand); auto tmpl = mapGenOptions.getMapTemplate(); zones.clear(); diff --git a/lib/rmg/RmgObject.cpp b/lib/rmg/RmgObject.cpp index 6c1e27574..e54664fdc 100644 --- a/lib/rmg/RmgObject.cpp +++ b/lib/rmg/RmgObject.cpp @@ -121,7 +121,7 @@ void Object::Instance::setTemplate(TerrainId terrain) auto templates = VLC->objtypeh->getHandlerFor(dObject.ID, dObject.subID)->getTemplates(terrain); if (templates.empty()) { - auto terrainName = VLC->terrainTypeHandler->terrains()[terrain].name; + auto terrainName = VLC->terrainTypeHandler->getById(terrain)->name; throw rmgException(boost::to_string(boost::format("Did not find graphics for object (%d,%d) at %s") % dObject.ID % dObject.subID % terrainName)); } dObject.appearance = templates.front(); diff --git a/lib/rmg/RoadPlacer.cpp b/lib/rmg/RoadPlacer.cpp index b8a037135..385f51d2c 100644 --- a/lib/rmg/RoadPlacer.cpp +++ b/lib/rmg/RoadPlacer.cpp @@ -78,8 +78,10 @@ void RoadPlacer::drawRoads(bool secondary) zone.areaPossible().subtract(roads); zone.freePaths().unite(roads); map.getEditManager()->getTerrainSelection().setSelection(roads.getTilesVector()); + std::string roadName = (secondary ? generator.getConfig().secondaryRoadType : generator.getConfig().defaultRoadType); - RoadId roadType = VLC->terrainTypeHandler->getRoadByName(roadName)->id; + RoadId roadType = VLC->roadTypeHandler->getInfoByName(roadName)->id; + map.getEditManager()->drawRoad(roadType, &generator.rand); } diff --git a/lib/rmg/RockPlacer.cpp b/lib/rmg/RockPlacer.cpp index 3cf9fbc25..980e35f0b 100644 --- a/lib/rmg/RockPlacer.cpp +++ b/lib/rmg/RockPlacer.cpp @@ -24,8 +24,8 @@ VCMI_LIB_NAMESPACE_BEGIN void RockPlacer::process() { - rockTerrain = VLC->terrainTypeHandler->terrains()[zone.getTerrainType()].rockTerrain; - assert(!VLC->terrainTypeHandler->terrains()[rockTerrain].isPassable()); + rockTerrain = VLC->terrainTypeHandler->getById(zone.getTerrainType())->rockTerrain; + assert(!VLC->terrainTypeHandler->getById(rockTerrain)->isPassable()); accessibleArea = zone.freePaths() + zone.areaUsed(); if(auto * m = zone.getModificator()) diff --git a/lib/rmg/Zone.cpp b/lib/rmg/Zone.cpp index fef80250f..8c6f500b7 100644 --- a/lib/rmg/Zone.cpp +++ b/lib/rmg/Zone.cpp @@ -28,7 +28,7 @@ std::function AREA_NO_FILTER = [](const int3 & t) Zone::Zone(RmgMap & map, CMapGenerator & generator) : ZoneOptions(), townType(ETownType::NEUTRAL), - terrainType(Terrain::GRASS), + terrainType(TerrainId::GRASS), map(map), generator(generator) { diff --git a/mapeditor/mainwindow.cpp b/mapeditor/mainwindow.cpp index 4b831be65..3396c801c 100644 --- a/mapeditor/mainwindow.cpp +++ b/mapeditor/mainwindow.cpp @@ -542,32 +542,32 @@ void MainWindow::loadObjectsTree() { ui->terrainFilterCombo->addItem(""); //adding terrains - for(auto & terrain : VLC->terrainTypeHandler->terrains()) + for(auto & terrain : VLC->terrainTypeHandler->objects) { - QPushButton *b = new QPushButton(QString::fromStdString(terrain.name)); + QPushButton *b = new QPushButton(QString::fromStdString(terrain->name)); ui->terrainLayout->addWidget(b); - connect(b, &QPushButton::clicked, this, [this, terrain]{ terrainButtonClicked(terrain.id); }); + connect(b, &QPushButton::clicked, this, [this, terrain]{ terrainButtonClicked(terrain->id); }); //filter - ui->terrainFilterCombo->addItem(QString::fromStdString(terrain)); + ui->terrainFilterCombo->addItem(QString::fromStdString(terrain->name)); } //add spacer to keep terrain button on the top ui->terrainLayout->addItem(new QSpacerItem(20, 20, QSizePolicy::Minimum, QSizePolicy::Expanding)); //adding roads - for(auto & road : VLC->terrainTypeHandler->roads()) + for(auto & road : VLC->roadTypeHandler->objects) { - QPushButton *b = new QPushButton(QString::fromStdString(road.fileName)); + QPushButton *b = new QPushButton(QString::fromStdString(road->fileName)); ui->roadLayout->addWidget(b); - connect(b, &QPushButton::clicked, this, [this, road]{ roadOrRiverButtonClicked(road.id, true); }); + connect(b, &QPushButton::clicked, this, [this, road]{ roadOrRiverButtonClicked(road->id, true); }); } //add spacer to keep terrain button on the top ui->roadLayout->addItem(new QSpacerItem(20, 20, QSizePolicy::Minimum, QSizePolicy::Expanding)); //adding rivers - for(auto & river : VLC->terrainTypeHandler->rivers()) + for(auto & river : VLC->riverTypeHandler->objects) { - QPushButton *b = new QPushButton(QString::fromStdString(river.fileName)); + QPushButton *b = new QPushButton(QString::fromStdString(river->fileName)); ui->riverLayout->addWidget(b); - connect(b, &QPushButton::clicked, this, [this, river]{ roadOrRiverButtonClicked(river.id, false); }); + connect(b, &QPushButton::clicked, this, [this, river]{ roadOrRiverButtonClicked(river->id, false); }); } //add spacer to keep terrain button on the top ui->riverLayout->addItem(new QSpacerItem(20, 20, QSizePolicy::Minimum, QSizePolicy::Expanding)); @@ -914,7 +914,7 @@ void MainWindow::on_terrainFilterCombo_currentTextChanged(const QString &arg1) if(!objectBrowser) return; - objectBrowser->terrain = arg1.isEmpty() ? TerrainId(Terrain::ANY_TERRAIN) : VLC->terrainTypeHandler->getInfoByName(arg1.toStdString())->id; + objectBrowser->terrain = arg1.isEmpty() ? TerrainId(TerrainId::ANY_TERRAIN) : VLC->terrainTypeHandler->getInfoByName(arg1.toStdString())->id; objectBrowser->invalidate(); objectBrowser->sort(0); } diff --git a/mapeditor/maphandler.cpp b/mapeditor/maphandler.cpp index 1a49915ba..589ecc8ab 100644 --- a/mapeditor/maphandler.cpp +++ b/mapeditor/maphandler.cpp @@ -78,17 +78,17 @@ void MapHandler::initTerrainGraphics() std::map terrainFiles; std::map roadFiles; std::map riverFiles; - for(const auto & terrain : VLC->terrainTypeHandler->terrains()) + for(const auto & terrain : VLC->terrainTypeHandler->objects) { - terrainFiles[terrain.name] = terrain.tilesFilename; + terrainFiles[terrain->name] = terrain->tilesFilename; } - for(const auto & river : VLC->terrainTypeHandler->rivers()) + for(const auto & river : VLC->riverTypeHandler->objects) { - riverFiles[river.fileName] = river.fileName; + riverFiles[river->fileName] = river->fileName; } - for(const auto & road : VLC->terrainTypeHandler->roads()) + for(const auto & road : VLC->roadTypeHandler->objects) { - roadFiles[road.fileName] = road.fileName; + roadFiles[road->fileName] = road->fileName; } loadFlipped(terrainAnimations, terrainImages, terrainFiles); diff --git a/mapeditor/objectbrowser.cpp b/mapeditor/objectbrowser.cpp index e7bbdc8c7..e8f8ac826 100644 --- a/mapeditor/objectbrowser.cpp +++ b/mapeditor/objectbrowser.cpp @@ -13,7 +13,7 @@ #include "../lib/mapObjects/CObjectClassesHandler.h" ObjectBrowserProxyModel::ObjectBrowserProxyModel(QObject *parent) - : QSortFilterProxyModel{parent}, terrain(Terrain::ANY_TERRAIN) + : QSortFilterProxyModel{parent}, terrain(TerrainId::ANY_TERRAIN) { } @@ -33,7 +33,7 @@ bool ObjectBrowserProxyModel::filterAcceptsRow(int source_row, const QModelIndex if(!filterAcceptsRowText(source_row, source_parent)) return false; - if(terrain == Terrain::ANY_TERRAIN) + if(terrain == TerrainId::ANY_TERRAIN) return result; auto data = item->data().toJsonObject(); diff --git a/server/CGameHandler.cpp b/server/CGameHandler.cpp index ddbf5fd92..a8dca3798 100644 --- a/server/CGameHandler.cpp +++ b/server/CGameHandler.cpp @@ -2244,7 +2244,7 @@ void CGameHandler::setupBattle(int3 tile, const CArmedInstance *armies[2], const const auto & t = *getTile(tile); TerrainId terrain = t.terType->id; if (gs->map->isCoastalTile(tile)) //coastal tile is always ground - terrain = Terrain::SAND; + terrain = TerrainId::SAND; BattleField terType = gs->battleGetBattlefieldType(tile, getRandomGenerator()); if (heroes[0] && heroes[0]->boat && heroes[1] && heroes[1]->boat)