From 8a8eecd06382d1916d2d6a5b69018acc52fb2071 Mon Sep 17 00:00:00 2001 From: mateuszb Date: Mon, 11 Feb 2013 19:11:34 +0000 Subject: [PATCH] * refactoring --- AI/VCAI/VCAI.cpp | 58 +++++++++++++++-------------- AI/VCAI/VCAI.h | 8 ++-- CCallback.cpp | 2 +- CCallback.h | 4 +- client/CCastleInterface.cpp | 46 +++++++++++------------ client/CCastleInterface.h | 18 ++++----- client/CPlayerInterface.cpp | 6 ++- client/CPlayerInterface.h | 2 +- client/CPreGame.cpp | 2 +- client/GUIClasses.cpp | 8 ++-- client/NetPacksClient.cpp | 8 ++-- lib/CBuildingHandler.cpp | 19 +++++----- lib/CBuildingHandler.h | 4 +- lib/CGameState.cpp | 63 ++++++++++++++++---------------- lib/CObjectHandler.cpp | 26 ++++++------- lib/CObjectHandler.h | 22 +++++------ lib/CTownHandler.cpp | 26 ++++++------- lib/CTownHandler.h | 20 +++++----- lib/GameConstants.cpp | 2 + lib/GameConstants.h | 10 ++++- lib/IGameCallback.cpp | 12 +++--- lib/IGameCallback.h | 6 +-- lib/IGameEventsReceiver.h | 2 +- lib/Mapping/CCampaignHandler.cpp | 2 +- lib/Mapping/CCampaignHandler.h | 2 +- lib/Mapping/CMap.h | 2 +- lib/Mapping/MapFormatH3M.cpp | 16 ++++---- lib/Mapping/MapFormatH3M.h | 2 +- lib/NetPacks.h | 9 +++-- lib/NetPacksLib.cpp | 4 +- lib/RMG/CMapGenerator.cpp | 2 +- server/CGameHandler.cpp | 14 ++++--- server/CGameHandler.h | 4 +- 33 files changed, 224 insertions(+), 207 deletions(-) diff --git a/AI/VCAI/VCAI.cpp b/AI/VCAI/VCAI.cpp index 4f58451af..258e8c34a 100644 --- a/AI/VCAI/VCAI.cpp +++ b/AI/VCAI/VCAI.cpp @@ -844,7 +844,7 @@ void VCAI::objectPropertyChanged(const SetObjectProperty * sop) } } -void VCAI::buildChanged(const CGTownInstance *town, int buildingID, int what) +void VCAI::buildChanged(const CGTownInstance *town, BuildingID buildingID, int what) { NET_EVENT_HANDLER; LOG_ENTRY; @@ -1256,7 +1256,7 @@ void VCAI::recruitCreatures(const CGDwelling * d) } } -bool VCAI::tryBuildStructure(const CGTownInstance * t, int building, unsigned int maxDays) +bool VCAI::tryBuildStructure(const CGTownInstance * t, BuildingID building, unsigned int maxDays) { if (!vstd::contains(t->town->buildings, building)) return false; // no such building in town @@ -1264,7 +1264,7 @@ bool VCAI::tryBuildStructure(const CGTownInstance * t, int building, unsigned in if (t->hasBuilt(building)) //Already built? Shouldn't happen in general return true; - std::set toBuild = cb->getBuildingRequiments(t, building); + std::set toBuild = cb->getBuildingRequiments(t, building); //erase all already built buildings for (auto buildIter = toBuild.begin(); buildIter != toBuild.end();) @@ -1277,7 +1277,7 @@ bool VCAI::tryBuildStructure(const CGTownInstance * t, int building, unsigned in toBuild.insert(building); - BOOST_FOREACH(int buildID, toBuild) + BOOST_FOREACH(BuildingID buildID, toBuild) { EBuildingState::EBuildingState canBuild = cb->canBuildStructure(t, buildID); if (canBuild == EBuildingState::HAVE_CAPITAL @@ -1293,7 +1293,7 @@ bool VCAI::tryBuildStructure(const CGTownInstance * t, int building, unsigned in TResources income = estimateIncome(); //TODO: calculate if we have enough resources to build it in maxDays - BOOST_FOREACH(int buildID, toBuild) + BOOST_FOREACH(const auto & buildID, toBuild) { const CBuilding *b = t->town->buildings[buildID]; @@ -1323,9 +1323,9 @@ bool VCAI::tryBuildStructure(const CGTownInstance * t, int building, unsigned in return false; } -bool VCAI::tryBuildAnyStructure(const CGTownInstance * t, std::vector buildList, unsigned int maxDays) +bool VCAI::tryBuildAnyStructure(const CGTownInstance * t, std::vector buildList, unsigned int maxDays) { - BOOST_FOREACH(int building, buildList) + BOOST_FOREACH(const auto & building, buildList) { if(t->hasBuilt(building)) continue; @@ -1335,9 +1335,9 @@ bool VCAI::tryBuildAnyStructure(const CGTownInstance * t, std::vector build return false; //Can't build anything } -bool VCAI::tryBuildNextStructure(const CGTownInstance * t, std::vector buildList, unsigned int maxDays) +bool VCAI::tryBuildNextStructure(const CGTownInstance * t, std::vector buildList, unsigned int maxDays) { - BOOST_FOREACH(int building, buildList) + BOOST_FOREACH(const auto & building, buildList) { if(t->hasBuilt(building)) continue; @@ -1354,37 +1354,39 @@ void VCAI::buildStructure(const CGTownInstance * t) //Possible - allow "locking" on specific building (build prerequisites and then building itself) //Set of buildings for different goals. Does not include any prerequisites. - const int essential[] = {BuildingID::TAVERN, BuildingID::TOWN_HALL}; - const int goldSource[] = {BuildingID::TOWN_HALL, BuildingID::CITY_HALL, BuildingID::CAPITOL}; - const int unitsSource[] = { 30, 31, 32, 33, 34, 35, 36}; - const int unitsUpgrade[] = { 37, 38, 39, 40, 41, 42, 43}; - const int unitGrowth[] = { BuildingID::FORT, BuildingID::CITADEL, BuildingID::CASTLE, BuildingID::HORDE_1, + const BuildingID essential[] = {BuildingID::TAVERN, BuildingID::TOWN_HALL}; + const BuildingID goldSource[] = {BuildingID::TOWN_HALL, BuildingID::CITY_HALL, BuildingID::CAPITOL}; + const BuildingID unitsSource[] = { BuildingID::DWELL_LVL_1, BuildingID::DWELL_LVL_2, BuildingID::DWELL_LVL_3, + BuildingID::DWELL_LVL_4, BuildingID::DWELL_LVL_5, BuildingID::DWELL_LVL_6, BuildingID::DWELL_LVL_7}; + const BuildingID unitsUpgrade[] = { BuildingID::DWELL_LVL_1_UP, BuildingID::DWELL_LVL_2_UP, BuildingID::DWELL_LVL_3_UP, + BuildingID::DWELL_LVL_4_UP, BuildingID::DWELL_LVL_5_UP, BuildingID::DWELL_LVL_6_UP, BuildingID::DWELL_LVL_7_UP}; + const BuildingID unitGrowth[] = { BuildingID::FORT, BuildingID::CITADEL, BuildingID::CASTLE, BuildingID::HORDE_1, BuildingID::HORDE_1_UPGR, BuildingID::HORDE_2, BuildingID::HORDE_2_UPGR}; - const int spells[] = {BuildingID::MAGES_GUILD_1, BuildingID::MAGES_GUILD_2, BuildingID::MAGES_GUILD_3, + const BuildingID spells[] = {BuildingID::MAGES_GUILD_1, BuildingID::MAGES_GUILD_2, BuildingID::MAGES_GUILD_3, BuildingID::MAGES_GUILD_4, BuildingID::MAGES_GUILD_5}; - const int extra[] = {BuildingID::RESOURCE_SILO, BuildingID::SPECIAL_1, BuildingID::SPECIAL_2, BuildingID::SPECIAL_3, + const BuildingID extra[] = {BuildingID::RESOURCE_SILO, BuildingID::SPECIAL_1, BuildingID::SPECIAL_2, BuildingID::SPECIAL_3, BuildingID::SPECIAL_4, BuildingID::SHIPYARD}; // all remaining buildings TResources currentRes = cb->getResourceAmount(); TResources income = estimateIncome(); - if (tryBuildAnyStructure(t, std::vector(essential, essential + ARRAY_COUNT(essential)))) + if (tryBuildAnyStructure(t, std::vector(essential, essential + ARRAY_COUNT(essential)))) return; //we're running out of gold - try to build something gold-producing. Multiplier can be tweaked, 6 is minimum due to buildings costs if (currentRes[Res::GOLD] < income[Res::GOLD] * 6) - if (tryBuildNextStructure(t, std::vector(goldSource, goldSource + ARRAY_COUNT(goldSource)))) + if (tryBuildNextStructure(t, std::vector(goldSource, goldSource + ARRAY_COUNT(goldSource)))) return; if (cb->getDate(Date::DAY_OF_WEEK) > 6)// last 2 days of week - try to focus on growth { - if (tryBuildNextStructure(t, std::vector(unitGrowth, unitGrowth + ARRAY_COUNT(unitGrowth)), 2)) + if (tryBuildNextStructure(t, std::vector(unitGrowth, unitGrowth + ARRAY_COUNT(unitGrowth)), 2)) return; } // first in-game week or second half of any week: try build dwellings if (cb->getDate(Date::DAY) < 7 || cb->getDate(Date::DAY_OF_WEEK) > 3) - if (tryBuildAnyStructure(t, std::vector(unitsSource, unitsSource + ARRAY_COUNT(unitsSource)), 8 - cb->getDate(Date::DAY_OF_WEEK))) + if (tryBuildAnyStructure(t, std::vector(unitsSource, unitsSource + ARRAY_COUNT(unitsSource)), 8 - cb->getDate(Date::DAY_OF_WEEK))) return; //try to upgrade dwelling @@ -1398,11 +1400,11 @@ void VCAI::buildStructure(const CGTownInstance * t) } //remaining tasks - if (tryBuildNextStructure(t, std::vector(goldSource, goldSource + ARRAY_COUNT(goldSource)))) + if (tryBuildNextStructure(t, std::vector(goldSource, goldSource + ARRAY_COUNT(goldSource)))) return; - if (tryBuildNextStructure(t, std::vector(spells, spells + ARRAY_COUNT(spells)))) + if (tryBuildNextStructure(t, std::vector(spells, spells + ARRAY_COUNT(spells)))) return; - if (tryBuildAnyStructure(t, std::vector(extra, extra + ARRAY_COUNT(extra)))) + if (tryBuildAnyStructure(t, std::vector(extra, extra + ARRAY_COUNT(extra)))) return; } @@ -1928,19 +1930,19 @@ void VCAI::tryRealize(CGoal g) { BOOST_FOREACH(const CGTownInstance *t, cb->getTownsInfo()) { - switch(cb->canBuildStructure(t, g.bid)) + switch(cb->canBuildStructure(t, BuildingID(g.bid))) { case EBuildingState::ALLOWED: - cb->buildBuilding(t, g.bid); + cb->buildBuilding(t, BuildingID(g.bid)); return; default: break; } } } - else if(cb->canBuildStructure(t, g.bid) == EBuildingState::ALLOWED) + else if(cb->canBuildStructure(t, BuildingID(g.bid)) == EBuildingState::ALLOWED) { - cb->buildBuilding(t, g.bid); + cb->buildBuilding(t, BuildingID(g.bid)); return; } throw cannotFulfillGoalException("Cannot build a given structure!"); @@ -3204,7 +3206,7 @@ TSubgoal CGoal::whatToDoToAchieve() auto creatures = t->town->creatures[creature->level]; int upgradeNumber = std::find(creatures.begin(), creatures.end(), creature->idNumber) - creatures.begin(); - int bid = BuildingID::DWELL_FIRST + creature->level + upgradeNumber * GameConstants::CREATURES_PER_TOWN; + BuildingID bid(BuildingID::DWELL_FIRST + creature->level + upgradeNumber * GameConstants::CREATURES_PER_TOWN); if (t->hasBuilt(bid)) //this assumes only creatures with dwellings are assigned to faction { dwellings.push_back(t); diff --git a/AI/VCAI/VCAI.h b/AI/VCAI/VCAI.h index 9ccce7fd8..1da93aaf1 100644 --- a/AI/VCAI/VCAI.h +++ b/AI/VCAI/VCAI.h @@ -241,11 +241,11 @@ class VCAI : public CAdventureAI //internal methods for town development //try build an unbuilt structure in maxDays at most (0 = indefinite) - bool tryBuildStructure(const CGTownInstance * t, int building, unsigned int maxDays=0); + bool tryBuildStructure(const CGTownInstance * t, BuildingID building, unsigned int maxDays=0); //try build ANY unbuilt structure - bool tryBuildAnyStructure(const CGTownInstance * t, std::vector buildList, unsigned int maxDays=0); + bool tryBuildAnyStructure(const CGTownInstance * t, std::vector buildList, unsigned int maxDays=0); //try build first unbuilt structure - bool tryBuildNextStructure(const CGTownInstance * t, std::vector buildList, unsigned int maxDays=0); + bool tryBuildNextStructure(const CGTownInstance * t, std::vector buildList, unsigned int maxDays=0); public: friend class FuzzyHelper; @@ -337,7 +337,7 @@ public: virtual void heroSecondarySkillChanged(const CGHeroInstance * hero, int which, int val) OVERRIDE; virtual void battleResultsApplied() OVERRIDE; virtual void objectPropertyChanged(const SetObjectProperty * sop) OVERRIDE; - virtual void buildChanged(const CGTownInstance *town, int buildingID, int what) OVERRIDE; + virtual void buildChanged(const CGTownInstance *town, BuildingID buildingID, int what) OVERRIDE; virtual void heroBonusChanged(const CGHeroInstance *hero, const Bonus &bonus, bool gain) OVERRIDE; virtual void showMarketWindow(const IMarket *market, const CGHeroInstance *visitor) OVERRIDE; diff --git a/CCallback.cpp b/CCallback.cpp index cee38516d..304e7548d 100644 --- a/CCallback.cpp +++ b/CCallback.cpp @@ -164,7 +164,7 @@ bool CCallback::assembleArtifacts (const CGHeroInstance * hero, ArtifactPosition return true; } -bool CCallback::buildBuilding(const CGTownInstance *town, si32 buildingID) +bool CCallback::buildBuilding(const CGTownInstance *town, BuildingID buildingID) { if(town->tempOwner!=player) return false; diff --git a/CCallback.h b/CCallback.h index f7fb9d135..3ee0d6a9b 100644 --- a/CCallback.h +++ b/CCallback.h @@ -49,7 +49,7 @@ public: //town virtual void recruitHero(const CGObjectInstance *townOrTavern, const CGHeroInstance *hero)=0; - virtual bool buildBuilding(const CGTownInstance *town, si32 buildingID)=0; + virtual bool buildBuilding(const CGTownInstance *town, BuildingID buildingID)=0; virtual void recruitCreatures(const CGObjectInstance *obj, CreatureID ID, ui32 amount, si32 level=-1)=0; virtual bool upgradeCreature(const CArmedInstance *obj, int stackPos, CreatureID newID=CreatureID::NONE)=0; //if newID==-1 then best possible upgrade will be made virtual void swapGarrisonHero(const CGTownInstance *town)=0; @@ -127,7 +127,7 @@ public: //bool moveArtifact(const CGHeroInstance * hero, ui16 src, const CStackInstance * stack, ui16 dest); // TODO: unify classes //bool moveArtifact(const CStackInstance * stack, ui16 src , const CGHeroInstance * hero, ui16 dest); // TODO: unify classes bool assembleArtifacts(const CGHeroInstance * hero, ArtifactPosition::ArtifactPosition artifactSlot, bool assemble, ui32 assembleTo); - bool buildBuilding(const CGTownInstance *town, si32 buildingID); + bool buildBuilding(const CGTownInstance *town, BuildingID buildingID) OVERRIDE; void recruitCreatures(const CGObjectInstance *obj, CreatureID ID, ui32 amount, si32 level=-1); bool dismissCreature(const CArmedInstance *obj, int stackPos); bool upgradeCreature(const CArmedInstance *obj, int stackPos, CreatureID newID=CreatureID::NONE) OVERRIDE; diff --git a/client/CCastleInterface.cpp b/client/CCastleInterface.cpp index 11288a9eb..a1ccd2036 100644 --- a/client/CCastleInterface.cpp +++ b/client/CCastleInterface.cpp @@ -105,7 +105,7 @@ void CBuildingRect::clickRight(tribool down, bool previousState) return; if( !CSDL_Ext::isTransparent(area, GH.current->motion.x-pos.x, GH.current->motion.y-pos.y) ) //inside building image { - int bid = str->building->bid; + BuildingID bid = str->building->bid; const CBuilding *bld = town->town->buildings[bid]; if (bid < BuildingID::DWELL_FIRST) { @@ -516,10 +516,10 @@ CCastleBuildings::~CCastleBuildings() { } -void CCastleBuildings::addBuilding(int building) +void CCastleBuildings::addBuilding(BuildingID building) { //FIXME: implement faster method without complete recreation of town - int base = town->town->buildings[building]->getBase(); + BuildingID base = town->town->buildings[building]->getBase(); recreate(); @@ -539,7 +539,7 @@ void CCastleBuildings::addBuilding(int building) } } -void CCastleBuildings::removeBuilding(int building) +void CCastleBuildings::removeBuilding(BuildingID building) { //FIXME: implement faster method without complete recreation of town recreate(); @@ -568,7 +568,7 @@ const CGHeroInstance* CCastleBuildings::getHero() return NULL; } -void CCastleBuildings::buildingClicked(int building) +void CCastleBuildings::buildingClicked(BuildingID building) { tlog5<<"You've clicked on "<town->buildings.find(building)->second; @@ -715,7 +715,7 @@ void CCastleBuildings::enterBlacksmith(ArtifactID artifactID) const CGHeroInstance *hero = town->visitingHero; if(!hero) { - LOCPLINT->showInfoDialog(boost::str(boost::format(CGI->generaltexth->allTexts[273]) % town->town->buildings.find(16)->second->Name())); + LOCPLINT->showInfoDialog(boost::str(boost::format(CGI->generaltexth->allTexts[273]) % town->town->buildings.find(BuildingID::BLACKSMITH)->second->Name())); return; } int price = CGI->arth->artifacts[artifactID]->price; @@ -723,7 +723,7 @@ void CCastleBuildings::enterBlacksmith(ArtifactID artifactID) GH.pushInt(new CBlacksmithDialog(possible, CArtHandler::machineIDToCreature(artifactID), artifactID, hero->id)); } -void CCastleBuildings::enterBuilding(int building) +void CCastleBuildings::enterBuilding(BuildingID building) { std::vector comps(1, new CComponent(CComponent::building, town->subID, building)); @@ -760,7 +760,7 @@ void CCastleBuildings::enterDwelling(int level) GH.pushInt(new CRecruitmentWindow(town, level, town, boost::bind(&CCallback::recruitCreatures,LOCPLINT->cb,town,_1,_2,level), -87)); } -void CCastleBuildings::enterFountain(int building) +void CCastleBuildings::enterFountain(BuildingID building) { std::vector comps(1, new CComponent(CComponent::building,town->subID,building)); @@ -923,7 +923,7 @@ void CCastleInterface::townChange() GH.pushInt(new CCastleInterface(dest, town)); } -void CCastleInterface::addBuilding(int bid) +void CCastleInterface::addBuilding(BuildingID bid) { deactivate(); builds->addBuilding(bid); @@ -931,7 +931,7 @@ void CCastleInterface::addBuilding(int bid) activate(); } -void CCastleInterface::removeBuilding(int bid) +void CCastleInterface::removeBuilding(BuildingID bid) { deactivate(); builds->removeBuilding(bid); @@ -1101,7 +1101,7 @@ CTownInfo::CTownInfo(int posX, int posY, const CGTownInstance* Town, bool townHa return; picture = new CAnimImage("ITMCL.DEF", town->fortLevel()-1); } - building = town->town->buildings[buildID]; + building = town->town->buildings[BuildingID(buildID)]; pos = picture->pos; } @@ -1285,7 +1285,7 @@ CHallInterface::CHallInterface(const CGTownInstance *Town): Rect barRect(5, 556, 740, 18); statusBar = new CGStatusBar(new CPicture(*background, barRect, 5, 556, false)); - title = new CLabel(399, 12, FONT_MEDIUM, CENTER, Colors::WHITE, town->town->buildings[town->hallLevel()+BuildingID::VILLAGE_HALL]->Name()); + title = new CLabel(399, 12, FONT_MEDIUM, CENTER, Colors::WHITE, town->town->buildings[BuildingID(town->hallLevel()+BuildingID::VILLAGE_HALL)]->Name()); exit = new CAdventureMapButton(CGI->generaltexth->hcommands[8], "", boost::bind(&CHallInterface::close,this), 748, 556, "TPMAGE1.DEF", SDLK_RETURN); exit->assignedKeys.insert(SDLK_ESCAPE); @@ -1299,7 +1299,7 @@ CHallInterface::CHallInterface(const CGTownInstance *Town): const CBuilding *building = NULL; for(size_t item=0; itemtown->buildings[buildingID]; if(!vstd::contains(town->builtBuildings,buildingID)) @@ -1335,13 +1335,13 @@ std::string CBuildWindow::getTextForState(int state) case 8: { ret = CGI->generaltexth->allTexts[52]; - std::set reqs= LOCPLINT->cb->getBuildingRequiments(town, building->bid); + std::set reqs= LOCPLINT->cb->getBuildingRequiments(town, building->bid); - for(std::set::iterator i=reqs.begin();i!=reqs.end();i++) + BOOST_FOREACH(const auto & i, reqs) { - if (vstd::contains(town->builtBuildings, *i)) + if (vstd::contains(town->builtBuildings, i)) continue;//skipping constructed buildings - ret+= town->town->buildings[*i]->Name() + ", "; + ret+= town->town->buildings[i]->Name() + ", "; } ret.erase(ret.size()-2); } @@ -1413,7 +1413,7 @@ CFortScreen::CFortScreen(const CGTownInstance * town): if (fortSize > GameConstants::CREATURES_PER_TOWN && town->creatures.back().second.empty()) fortSize--; - const CBuilding *fortBuilding = town->town->buildings[town->fortLevel()+6]; + const CBuilding *fortBuilding = town->town->buildings[BuildingID(town->fortLevel()+6)]; title = new CLabel(400, 12, FONT_BIG, CENTER, Colors::WHITE, fortBuilding->Name()); std::string text = boost::str(boost::format(CGI->generaltexth->fcommands[6]) % fortBuilding->Name()); @@ -1432,16 +1432,16 @@ CFortScreen::CFortScreen(const CGTownInstance * town): for (ui32 i=0; ibuiltBuildings, BuildingID::DWELL_UP_FIRST+i)) - buildingID = BuildingID::DWELL_UP_FIRST+i; + buildingID = BuildingID(BuildingID::DWELL_UP_FIRST+i); else - buildingID = BuildingID::DWELL_FIRST+i; + buildingID = BuildingID(BuildingID::DWELL_FIRST+i); } else - buildingID = 22; + buildingID = BuildingID::SPECIAL_3; recAreas.push_back(new RecruitArea(positions[i].x, positions[i].y, town, buildingID, i)); } @@ -1504,7 +1504,7 @@ void LabeledValue::hover(bool on) } } -CFortScreen::RecruitArea::RecruitArea(int posX, int posY, const CGTownInstance *Town, int buildingID, int Level): +CFortScreen::RecruitArea::RecruitArea(int posX, int posY, const CGTownInstance *Town, BuildingID buildingID, int Level): town(Town), level(Level), availableCount(NULL) diff --git a/client/CCastleInterface.h b/client/CCastleInterface.h index d5e5098e4..da3c45005 100644 --- a/client/CCastleInterface.h +++ b/client/CCastleInterface.h @@ -115,7 +115,7 @@ class CCastleBuildings : public CIntObject { CPicture *background; //List of buildings and structures that can represent them - std::map< si32, std::vector > groups; + std::map< BuildingID, std::vector > groups; // actual IntObject's visible on screen std::vector< CBuildingRect * > buildings; @@ -124,9 +124,9 @@ class CCastleBuildings : public CIntObject const CGHeroInstance* getHero();//Select hero for buildings usage void enterBlacksmith(ArtifactID artifactID);//support for blacksmith + ballista yard - void enterBuilding(int building);//for buildings with simple description + pic left-click messages + void enterBuilding(BuildingID building);//for buildings with simple description + pic left-click messages void enterCastleGate(); - void enterFountain(int building);//Rampart's fountains + void enterFountain(BuildingID building);//Rampart's fountains void enterMagesGuild(); void enterTownHall(); @@ -142,9 +142,9 @@ public: void enterDwelling(int level); - void buildingClicked(int building); - void addBuilding(int building); - void removeBuilding(int building);//FIXME: not tested!!! + void buildingClicked(BuildingID building); + void addBuilding(BuildingID building); + void removeBuilding(BuildingID building);//FIXME: not tested!!! void show(SDL_Surface * to); void showAll(SDL_Surface * to); @@ -224,8 +224,8 @@ public: void townChange(); void keyPressed(const SDL_KeyboardEvent & key); void close(); - void addBuilding(int bid); - void removeBuilding(int bid); + void addBuilding(BuildingID bid); + void removeBuilding(BuildingID bid); void recreateIcons(); }; @@ -312,7 +312,7 @@ class CFortScreen : public CWindowObject CCreaturePic *creatureAnim; public: - RecruitArea(int posX, int posY, const CGTownInstance *town, int buildingID, int level); + RecruitArea(int posX, int posY, const CGTownInstance *town, BuildingID buildingID, int level); void creaturesChanged(); void hover(bool on); diff --git a/client/CPlayerInterface.cpp b/client/CPlayerInterface.cpp index c6df8115f..1bf6fc401 100644 --- a/client/CPlayerInterface.cpp +++ b/client/CPlayerInterface.cpp @@ -563,12 +563,14 @@ void CPlayerInterface::garrisonChanged( const CGObjectInstance * obj) garrisonsChanged(std::vector(1, obj)); } -void CPlayerInterface::buildChanged(const CGTownInstance *town, int buildingID, int what) //what: 1 - built, 2 - demolished +void CPlayerInterface::buildChanged(const CGTownInstance *town, BuildingID buildingID, int what) //what: 1 - built, 2 - demolished { EVENT_HANDLER_CALLED_BY_CLIENT; switch (buildingID) { - case 7: case 8: case 9: case 10: case 11: case 12: case 13: case 15: + case BuildingID::FORT: case BuildingID::CITADEL: case BuildingID::CASTLE: + case BuildingID::VILLAGE_HALL: case BuildingID::TOWN_HALL: case BuildingID::CITY_HALL: case BuildingID::CAPITOL: + case BuildingID::RESOURCE_SILO: updateInfo(town); break; } diff --git a/client/CPlayerInterface.h b/client/CPlayerInterface.h index 5d9f4ff87..65123c67f 100644 --- a/client/CPlayerInterface.h +++ b/client/CPlayerInterface.h @@ -128,7 +128,7 @@ public: int getLastIndex(std::string namePrefix); //overridden funcs from CGameInterface - void buildChanged(const CGTownInstance *town, int buildingID, int what) OVERRIDE; //what: 1 - built, 2 - demolished + void buildChanged(const CGTownInstance *town, BuildingID buildingID, int what) OVERRIDE; //what: 1 - built, 2 - demolished void stackChagedCount(const StackLocation &location, const TQuantity &change, bool isAbsolute) OVERRIDE; //if absolute, change is the new count; otherwise count was modified by adding change void stackChangedType(const StackLocation &location, const CCreature &newType) OVERRIDE; //used eg. when upgrading creatures void stacksErased(const StackLocation &location) OVERRIDE; //stack removed from previously filled slot diff --git a/client/CPreGame.cpp b/client/CPreGame.cpp index 7710b7085..bb424dec8 100644 --- a/client/CPreGame.cpp +++ b/client/CPreGame.cpp @@ -3443,7 +3443,7 @@ void CBonusSelection::updateBonusSelection() } assert(faction != -1); - int buildID = CBuildingHandler::campToERMU(bonDescs[i].info1, faction, std::set()); + BuildingID buildID = CBuildingHandler::campToERMU(bonDescs[i].info1, faction, std::set()); picName = graphics->ERMUtoPicture[faction][buildID]; picNumber = -1; diff --git a/client/GUIClasses.cpp b/client/GUIClasses.cpp index 95c89dd98..2ec9b3c18 100644 --- a/client/GUIClasses.cpp +++ b/client/GUIClasses.cpp @@ -964,7 +964,7 @@ std::string CComponent::getDescription() case spell: return CGI->spellh->spells[subtype]->descriptions[val]; case morale: return CGI->generaltexth->heroscrn[ 4 - (val>0) + (val<0)]; case luck: return CGI->generaltexth->heroscrn[ 7 - (val>0) + (val<0)]; - case building: return CGI->townh->towns[subtype].buildings[val]->Description(); + case building: return CGI->townh->towns[subtype].buildings[BuildingID(val)]->Description(); case hero: return CGI->heroh->heroes[subtype]->name; case flag: return ""; } @@ -996,7 +996,7 @@ std::string CComponent::getSubtitleInternal() case spell: return CGI->spellh->spells[subtype]->name; case morale: return ""; case luck: return ""; - case building: return CGI->townh->towns[subtype].buildings[val]->Name(); + case building: return CGI->townh->towns[subtype].buildings[BuildingID(val)]->Name(); case hero: return CGI->heroh->heroes[subtype]->name; case flag: return CGI->generaltexth->capColors[subtype]; } @@ -4497,9 +4497,9 @@ void LRClickableAreaOpenTown::clickLeft(tribool down, bool previousState) { LOCPLINT->openTownWindow(town); if ( type == 2 ) - LOCPLINT->castleInt->builds->buildingClicked(10); + LOCPLINT->castleInt->builds->buildingClicked(BuildingID::VILLAGE_HALL); else if ( type == 3 && town->fortLevel() ) - LOCPLINT->castleInt->builds->buildingClicked(7); + LOCPLINT->castleInt->builds->buildingClicked(BuildingID::FORT); } } diff --git a/client/NetPacksClient.cpp b/client/NetPacksClient.cpp index 833aff65d..d6e32e981 100644 --- a/client/NetPacksClient.cpp +++ b/client/NetPacksClient.cpp @@ -404,9 +404,9 @@ void TryMoveHero::applyCl( CClient *cl ) void NewStructures::applyCl( CClient *cl ) { CGTownInstance *town = GS(cl)->getTown(tid); - BOOST_FOREACH(si32 id, bid) + BOOST_FOREACH(const auto & id, bid) { - if(id== BuildingID::CAPITOL) //fort or capitol + if(id == BuildingID::CAPITOL) //fort or capitol { town->defInfo = const_cast(CGI->dobjinfo->capitols[town->subID].get()); } @@ -421,9 +421,9 @@ void NewStructures::applyCl( CClient *cl ) void RazeStructures::applyCl (CClient *cl) { CGTownInstance *town = GS(cl)->getTown(tid); - BOOST_FOREACH(si32 id, bid) + BOOST_FOREACH(const auto & id, bid) { - if (id == 13) //fort or capitol + if (id == BuildingID::CAPITOL) //fort or capitol { town->defInfo = const_cast(CGI->dobjinfo->gobjs[Obj::TOWN][town->subID].get()); } diff --git a/lib/CBuildingHandler.cpp b/lib/CBuildingHandler.cpp index 5142a2393..fd82f89ac 100644 --- a/lib/CBuildingHandler.cpp +++ b/lib/CBuildingHandler.cpp @@ -1,7 +1,6 @@ #include "StdInc.h" #include "CBuildingHandler.h" -#include "GameConstants.h" /* * CBuildingHandler.cpp, part of VCMI engine @@ -13,7 +12,7 @@ * */ -int CBuildingHandler::campToERMU( int camp, int townType, std::set builtBuildings ) +BuildingID CBuildingHandler::campToERMU( int camp, int townType, std::set builtBuildings ) { using namespace boost::assign; static const std::vector campToERMU = list_of(11)(12)(13)(7)(8)(9)(5)(16)(14)(15)(-1)(0)(1)(2)(3)(4) @@ -21,7 +20,7 @@ int CBuildingHandler::campToERMU( int camp, int townType, std::set builtBu ; //creature generators with banks - handled separately if (camp < campToERMU.size()) { - return campToERMU[camp]; + return BuildingID(campToERMU[camp]); } static const std::vector hordeLvlsPerTType[GameConstants::F_NUMBER] = {list_of(2), list_of(1), list_of(1)(4), list_of(0)(2), @@ -31,10 +30,10 @@ int CBuildingHandler::campToERMU( int camp, int townType, std::set builtBu for (int i=0; i<7; ++i) { if(camp == curPos) //non-upgraded - return 30 + i; + return BuildingID(30 + i); curPos++; if(camp == curPos) //upgraded - return 37 + i; + return BuildingID(37 + i); curPos++; //horde building if (vstd::contains(hordeLvlsPerTType[townType], i)) @@ -44,18 +43,18 @@ int CBuildingHandler::campToERMU( int camp, int townType, std::set builtBu if (hordeLvlsPerTType[townType][0] == i) { if(vstd::contains(builtBuildings, 37 + hordeLvlsPerTType[townType][0])) //if upgraded dwelling is built - return 19; + return BuildingID::HORDE_1_UPGR; else //upgraded dwelling not presents - return 18; + return BuildingID::HORDE_1; } else { if(hordeLvlsPerTType[townType].size() > 1) { if(vstd::contains(builtBuildings, 37 + hordeLvlsPerTType[townType][1])) //if upgraded dwelling is built - return 25; + return BuildingID::HORDE_2_UPGR; else //upgraded dwelling not presents - return 24; + return BuildingID::HORDE_2; } } } @@ -64,6 +63,6 @@ int CBuildingHandler::campToERMU( int camp, int townType, std::set builtBu } assert(0); - return -1; //not found + return BuildingID::NONE; //not found } diff --git a/lib/CBuildingHandler.h b/lib/CBuildingHandler.h index 5228940fa..20e470582 100644 --- a/lib/CBuildingHandler.h +++ b/lib/CBuildingHandler.h @@ -1,5 +1,7 @@ #pragma once +#include "GameConstants.h" + /* * CBuildingHandler.h, part of VCMI engine * @@ -13,5 +15,5 @@ class DLL_LINKAGE CBuildingHandler { public: - static int campToERMU(int camp, int townType, std::set builtBuildings); + static BuildingID campToERMU(int camp, int townType, std::set builtBuildings); }; diff --git a/lib/CGameState.cpp b/lib/CGameState.cpp index e6fe0d66f..c02a93f63 100644 --- a/lib/CGameState.cpp +++ b/lib/CGameState.cpp @@ -1442,6 +1442,33 @@ void CGameState::init(StartInfo * si) } /****************************TOWNS************************************************/ tlog4 << "\tTowns"; + + //campaign bonuses for towns + if (scenarioOps->mode == StartInfo::CAMPAIGN) + { + auto chosenBonus = scenarioOps->campState->getBonusForCurrentMap(); + + if (chosenBonus.is_initialized() && chosenBonus->type == CScenarioTravel::STravelBonus::BUILDING) + { + for (int g=0; gtowns.size(); ++g) + { + PlayerState * owner = getPlayer(map->towns[g]->getOwner()); + if (owner) + { + PlayerInfo & pi = map->players[owner->color]; + + if (owner->human && //human-owned + map->towns[g]->pos == pi.posOfMainTown + int3(2, 0, 0)) + { + map->towns[g]->builtBuildings.insert( + CBuildingHandler::campToERMU(chosenBonus->info1, map->towns[g]->town->typeID, map->towns[g]->builtBuildings)); + break; + } + } + } + } + } + CGTownInstance::universitySkills.clear(); for ( int i=0; i<4; i++) CGTownInstance::universitySkills.push_back(14+i);//skills for university @@ -1455,14 +1482,14 @@ void CGameState::init(StartInfo * si) vti->name = vti->town->names[ran()%vti->town->names.size()]; //init buildings - if(vti->builtBuildings.find(-50)!=vti->builtBuildings.end()) //give standard set of buildings + if(vstd::contains(vti->builtBuildings, BuildingID::DEFAULT)) //give standard set of buildings { - vti->builtBuildings.erase(-50); + vti->builtBuildings.erase(BuildingID::DEFAULT); vti->builtBuildings.insert(BuildingID::VILLAGE_HALL); vti->builtBuildings.insert(BuildingID::TAVERN); vti->builtBuildings.insert(BuildingID::DWELL_FIRST); if(ran()%2) - vti->builtBuildings.insert(BuildingID::DWELL_FIRST+1); + vti->builtBuildings.insert(BuildingID::DWELL_LVL_2); } if (vstd::contains(vti->builtBuildings, BuildingID::SHIPYARD) && vti->state()==IBoatGenerator::TILE_BLOCKED) @@ -1472,7 +1499,7 @@ void CGameState::init(StartInfo * si) for (int i = 0; ibuiltBuildings,(-31-i))) //if we have horde for this level { - vti->builtBuildings.erase(-31-i);//remove old ID + vti->builtBuildings.erase(BuildingID(-31-i));//remove old ID if (vti->town->hordeLvl[0] == i)//if town first horde is this one { vti->builtBuildings.insert(BuildingID::HORDE_1);//add it @@ -1493,7 +1520,7 @@ void CGameState::init(StartInfo * si) for (int i = 0; ibuildings,(-31-i))) //if we have horde for this level { - ev->buildings.erase(-31-i); + ev->buildings.erase(BuildingID(-31-i)); if (vti->town->hordeLvl[0] == i) ev->buildings.insert(BuildingID::HORDE_1); if (vti->town->hordeLvl[1] == i) @@ -1542,32 +1569,6 @@ void CGameState::init(StartInfo * si) getPlayer(vti->getOwner())->towns.push_back(vti); } - //campaign bonuses for towns - if (scenarioOps->mode == StartInfo::CAMPAIGN) - { - auto chosenBonus = scenarioOps->campState->getBonusForCurrentMap(); - - if (chosenBonus.is_initialized() && chosenBonus->type == CScenarioTravel::STravelBonus::BUILDING) - { - for (int g=0; gtowns.size(); ++g) - { - PlayerState * owner = getPlayer(map->towns[g]->getOwner()); - if (owner) - { - PlayerInfo & pi = map->players[owner->color]; - - if (owner->human && //human-owned - map->towns[g]->pos == pi.posOfMainTown + int3(2, 0, 0)) - { - map->towns[g]->builtBuildings.insert( - CBuildingHandler::campToERMU(chosenBonus->info1, map->towns[g]->town->typeID, map->towns[g]->builtBuildings)); - break; - } - } - } - } - - } tlog4 << "\tObject initialization"; objCaller->preInit(); BOOST_FOREACH(CGObjectInstance *obj, map->objects) diff --git a/lib/CObjectHandler.cpp b/lib/CObjectHandler.cpp index 4472e2382..0aefa6651 100644 --- a/lib/CObjectHandler.cpp +++ b/lib/CObjectHandler.cpp @@ -1938,7 +1938,7 @@ int CGTownInstance::creatureDwellingLevel(int dwelling) const return -1; for (int i=0; ; i++) { - if (!hasBuilt(BuildingID::DWELL_FIRST+dwelling+i*GameConstants::CREATURES_PER_TOWN)) + if (!hasBuilt(BuildingID(BuildingID::DWELL_FIRST+dwelling+i*GameConstants::CREATURES_PER_TOWN))) return i-1; } } @@ -1957,7 +1957,7 @@ GrowthInfo CGTownInstance::getGrowthInfo(int level) const if (level<0 || level >=GameConstants::CREATURES_PER_TOWN) return ret; - if (!hasBuilt(BuildingID::DWELL_FIRST+level)) + if (!hasBuilt(BuildingID(BuildingID::DWELL_FIRST+level))) return ret; //no dwelling const CCreature *creature = VLC->creh->creatures[creatures[level].second.back()]; @@ -2132,15 +2132,15 @@ void CGTownInstance::initObj() switch (subID) { //add new visitable objects case 0: - bonusingBuildings.push_back (new COPWBonus(21, this)); //Stables + bonusingBuildings.push_back (new COPWBonus(BuildingID::STABLES, this)); break; case 5: - bonusingBuildings.push_back (new COPWBonus(21, this)); //Vortex + bonusingBuildings.push_back (new COPWBonus(BuildingID::MANA_VORTEX, this)); case 2: case 3: case 6: - bonusingBuildings.push_back (new CTownBonus(23, this)); + bonusingBuildings.push_back (new CTownBonus(BuildingID::SPECIAL_4, this)); break; case 7: - bonusingBuildings.push_back (new CTownBonus(17, this)); + bonusingBuildings.push_back (new CTownBonus(BuildingID::SPECIAL_1, this)); break; } //add special bonuses from buildings @@ -2272,7 +2272,7 @@ void CGTownInstance::removeCapitols (ui8 owner) const { RazeStructures rs; rs.tid = id; - rs.bid.insert(13); + rs.bid.insert(BuildingID::CAPITOL); rs.destroyed = destroyed; cb->sendAndApply(&rs); return; @@ -2426,12 +2426,12 @@ void CGTownInstance::recreateBuildingsBonuses() } } -bool CGTownInstance::addBonusIfBuilt(int building, int type, int val, int subtype /*= -1*/) +bool CGTownInstance::addBonusIfBuilt(BuildingID building, int type, int val, int subtype /*= -1*/) { return addBonusIfBuilt(building, type, val, TPropagatorPtr(), subtype); } -bool CGTownInstance::addBonusIfBuilt(int building, int type, int val, TPropagatorPtr prop, int subtype /*= -1*/) +bool CGTownInstance::addBonusIfBuilt(BuildingID building, int type, int val, TPropagatorPtr prop, int subtype /*= -1*/) { if(hasBuilt(building)) { @@ -2517,14 +2517,14 @@ const CArmedInstance * CGTownInstance::getUpperArmy() const return this; } -bool CGTownInstance::hasBuilt(int buildingID, int townID) const +bool CGTownInstance::hasBuilt(BuildingID buildingID, int townID) const { if (townID == town->typeID || townID == ETownType::ANY) return hasBuilt(buildingID); return false; } -bool CGTownInstance::hasBuilt(int buildingID) const +bool CGTownInstance::hasBuilt(BuildingID buildingID) const { return vstd::contains(builtBuildings, buildingID); } @@ -2846,7 +2846,7 @@ void CGVisitableOPH::schoolSelected(int heroID, ui32 which) const cb->changePrimSkill(cb->getHero(heroID), static_cast(base + which-1), +1); //give appropriate skill } -COPWBonus::COPWBonus (int index, CGTownInstance *TOWN) +COPWBonus::COPWBonus (BuildingID index, CGTownInstance *TOWN) { ID = index; town = TOWN; @@ -2897,7 +2897,7 @@ void COPWBonus::onHeroVisit (const CGHeroInstance * h) const } } } -CTownBonus::CTownBonus (int index, CGTownInstance *TOWN) +CTownBonus::CTownBonus (BuildingID index, CGTownInstance *TOWN) { ID = index; town = TOWN; diff --git a/lib/CObjectHandler.h b/lib/CObjectHandler.h index 15a969095..11ecb7279 100644 --- a/lib/CObjectHandler.h +++ b/lib/CObjectHandler.h @@ -511,7 +511,7 @@ class DLL_LINKAGE CGTownBuilding : public IObjectInterface { ///basic class for town structures handled as map objects public: - si32 ID; //from buildig list + BuildingID ID; //from buildig list si32 id; //identifies its index on towns vector CGTownInstance *town; @@ -527,8 +527,8 @@ public: void setProperty(ui8 what, ui32 val) override; void onHeroVisit (const CGHeroInstance * h) const override; - COPWBonus (int index, CGTownInstance *TOWN); - COPWBonus (){ID = 0; town = NULL;}; + COPWBonus (BuildingID index, CGTownInstance *TOWN); + COPWBonus (){ID = BuildingID::NONE; town = NULL;}; template void serialize(Handler &h, const int version) { h & static_cast(*this); @@ -545,8 +545,8 @@ public: void setProperty(ui8 what, ui32 val) override; void onHeroVisit (const CGHeroInstance * h) const override; - CTownBonus (int index, CGTownInstance *TOWN); - CTownBonus (){ID = 0; town = NULL;}; + CTownBonus (BuildingID index, CGTownInstance *TOWN); + CTownBonus (){ID = BuildingID::NONE; town = NULL;}; template void serialize(Handler &h, const int version) { h & static_cast(*this); @@ -587,9 +587,9 @@ public: ConstTransitivePtr garrisonHero, visitingHero; ui32 identifier; //special identifier from h3m (only > RoE maps) si32 alignment; - std::set forbiddenBuildings, builtBuildings; + std::set forbiddenBuildings, builtBuildings; std::vector bonusingBuildings; - std::vector possibleSpells, obligatorySpells; + std::vector possibleSpells, obligatorySpells; std::vector > spells; //spells[level] -> vector of spells, first will be available in guild std::list events; std::pair bonusValue;//var to store town bonuses (rampart = resources from mystic pond); @@ -617,8 +617,8 @@ public: std::string nodeName() const override; void deserializationFix(); void recreateBuildingsBonuses(); - bool addBonusIfBuilt(int building, int type, int val, TPropagatorPtr prop, int subtype = -1); //returns true if building is built and bonus has been added - bool addBonusIfBuilt(int building, int type, int val, int subtype = -1); //convienence version of above + bool addBonusIfBuilt(BuildingID building, int type, int val, TPropagatorPtr prop, int subtype = -1); //returns true if building is built and bonus has been added + bool addBonusIfBuilt(BuildingID building, int type, int val, int subtype = -1); //convienence version of above void setVisitingHero(CGHeroInstance *h); void setGarrisonedHero(CGHeroInstance *h); const CArmedInstance *getUpperArmy() const; //garrisoned hero if present or the town itself @@ -649,8 +649,8 @@ public: bool hasFort() const; bool hasCapitol() const; //checks if building is constructed and town has same subID - bool hasBuilt(int buildingID) const; - bool hasBuilt(int buildingID, int townID) const; + bool hasBuilt(BuildingID buildingID) const; + bool hasBuilt(BuildingID buildingID, int townID) const; int dailyIncome() const; //calculates daily income of this town int spellsAtLevel(int level, bool checkGuild) const; //levels are counted from 1 (1 - 5) void removeCapitols (ui8 owner) const; diff --git a/lib/CTownHandler.cpp b/lib/CTownHandler.cpp index 39e102ebe..110f3cce4 100644 --- a/lib/CTownHandler.cpp +++ b/lib/CTownHandler.cpp @@ -31,7 +31,7 @@ const std::string & CBuilding::Description() const return description; } -CBuilding::BuildingType CBuilding::getBase() const +BuildingID CBuilding::getBase() const { const CBuilding * build = this; while (build->upgrade >= 0) @@ -40,7 +40,7 @@ CBuilding::BuildingType CBuilding::getBase() const return build->bid; } -si32 CBuilding::getDistance(CBuilding::BuildingType buildID) const +si32 CBuilding::getDistance(BuildingID buildID) const { const CBuilding * build = VLC->townh->towns[tid].buildings[buildID]; int distance = 0; @@ -237,24 +237,24 @@ void CTownHandler::loadBuilding(CTown &town, const JsonNode & source) static const std::string modes [] = {"normal", "auto", "special", "grail"}; - ret->mode = boost::find(modes, source["mode"].String()) - modes; + ret->mode = static_cast(boost::find(modes, source["mode"].String()) - modes); ret->tid = town.typeID; - ret->bid = source["id"].Float(); + ret->bid = BuildingID(source["id"].Float()); ret->name = source["name"].String(); ret->description = source["description"].String(); ret->resources = TResources(source["cost"]); BOOST_FOREACH(const JsonNode &building, source["requires"].Vector()) - ret->requirements.insert(building.Float()); + ret->requirements.insert(BuildingID(building.Float())); if (!source["upgrades"].isNull()) { - ret->requirements.insert(source["upgrades"].Float()); - ret->upgrade = source["upgrades"].Float(); + ret->requirements.insert(BuildingID(source["upgrades"].Float())); + ret->upgrade = BuildingID(source["upgrades"].Float()); } else - ret->upgrade = -1; + ret->upgrade = BuildingID::NONE; town.buildings[ret->bid] = ret; } @@ -278,12 +278,12 @@ void CTownHandler::loadStructure(CTown &town, const JsonNode & source) } else { - ret->building = town.buildings[source["id"].Float()]; + ret->building = town.buildings[BuildingID(source["id"].Float())]; if (source["builds"].isNull()) ret->buildable = ret->building; else - ret->buildable = town.buildings[source["builds"].Float()]; + ret->buildable = town.buildings[BuildingID(source["builds"].Float())]; } ret->pos.x = source["x"].Float(); @@ -310,15 +310,15 @@ void CTownHandler::loadTownHall(CTown &town, const JsonNode & source) { BOOST_FOREACH(const JsonNode &row, source.Vector()) { - std::vector< std::vector > hallRow; + std::vector< std::vector > hallRow; BOOST_FOREACH(const JsonNode &box, row.Vector()) { - std::vector hallBox; + std::vector hallBox; BOOST_FOREACH(const JsonNode &value, box.Vector()) { - hallBox.push_back(value.Float()); + hallBox.push_back(BuildingID(value.Float())); } hallRow.push_back(hallBox); } diff --git a/lib/CTownHandler.h b/lib/CTownHandler.h index 26f28f1d9..0169e4292 100644 --- a/lib/CTownHandler.h +++ b/lib/CTownHandler.h @@ -23,18 +23,17 @@ class JsonNode; /// contains all mechanics-related data about town structures class DLL_LINKAGE CBuilding { - typedef si32 BuildingType;//TODO: replace int with pointer? std::string name; std::string description; public: - TFaction tid; - si32 bid; //town ID and structure ID + TFaction tid; //town ID + BuildingID bid; //structure ID TResources resources; - std::set requirements; /// set of required buildings, includes upgradeOf; - BuildingType upgrade; /// indicates that building "upgrade" can be improved by this, -1 = empty + std::set requirements; /// set of required buildings, includes upgradeOf; + BuildingID upgrade; /// indicates that building "upgrade" can be improved by this, -1 = empty enum EBuildMode { @@ -42,17 +41,16 @@ public: BUILD_AUTO, // 1 - auto - building appears when all requirements are built BUILD_SPECIAL, // 2 - special - building can not be built normally BUILD_GRAIL // 3 - grail - building reqires grail to be built - }; - ui32 mode; + } mode; const std::string &Name() const; const std::string &Description() const; //return base of upgrade(s) or this - BuildingType getBase() const; + BuildingID getBase() const; // returns how many times build has to be upgraded to become build - si32 getDistance(BuildingType build) const; + si32 getDistance(BuildingID build) const; template void serialize(Handler &h, const int version) { @@ -92,7 +90,7 @@ public: // TODO: replace with pointers to CCreature std::vector > creatures; - bmap > buildings; + bmap > buildings; std::vector dwellings; //defs for adventure map dwellings for new towns, [0] means tier 1 creatures etc. std::vector dwellingNames; @@ -125,7 +123,7 @@ public: std::string buildingsIcons; std::string hallBackground; /// vector[row][column] = list of buildings in this slot - std::vector< std::vector< std::vector > > hallSlots; + std::vector< std::vector< std::vector > > hallSlots; /// list of town screen structures. /// NOTE: index in vector is meaningless. Vector used instead of list for a bit faster access diff --git a/lib/GameConstants.cpp b/lib/GameConstants.cpp index d243edb27..03320b6d1 100644 --- a/lib/GameConstants.cpp +++ b/lib/GameConstants.cpp @@ -46,6 +46,8 @@ ID_LIKE_OPERATORS(CreatureID, CreatureID::ECreatureID) ID_LIKE_OPERATORS(SpellID, SpellID::ESpellID) +ID_LIKE_OPERATORS(BuildingID, BuildingID::EBuildingID) + bmap > & Obj::toDefObjInfo() const { diff --git a/lib/GameConstants.h b/lib/GameConstants.h index 0a276b7ce..a40512c87 100644 --- a/lib/GameConstants.h +++ b/lib/GameConstants.h @@ -196,6 +196,7 @@ public: // NOTE: all building with completely configurable mechanics will be removed from list enum EBuildingID { + DEFAULT = -50, NONE = -1, MAGES_GUILD_1 = 0, MAGES_GUILD_2, MAGES_GUILD_3, MAGES_GUILD_4, MAGES_GUILD_5, TAVERN, SHIPYARD, FORT, CITADEL, CASTLE, @@ -203,7 +204,14 @@ public: RESOURCE_SILO, BLACKSMITH, SPECIAL_1, HORDE_1, HORDE_1_UPGR, SHIP, SPECIAL_2, SPECIAL_3, SPECIAL_4, HORDE_2, HORDE_2_UPGR, GRAIL, EXTRA_TOWN_HALL, EXTRA_CITY_HALL, EXTRA_CAPITOL, - DWELL_FIRST=30, DWELL_LAST=36, DWELL_UP_FIRST=37, DWELL_UP_LAST=43, + DWELL_FIRST=30, DWELL_LVL_2, DWELL_LVL_3, DWELL_LVL_4, DWELL_LVL_5, DWELL_LVL_6, DWELL_LAST=36, + DWELL_UP_FIRST=37, DWELL_LVL_2_UP, DWELL_LVL_3_UP, DWELL_LVL_4_UP, DWELL_LVL_5_UP, + DWELL_LVL_6_UP, DWELL_UP_LAST=43, + + DWELL_LVL_1 = DWELL_FIRST, + DWELL_LVL_7 = DWELL_LAST, + DWELL_LVL_1_UP = DWELL_UP_FIRST, + DWELL_LVL_7_UP = DWELL_UP_LAST, //Special buildings for towns. LIGHTHOUSE = SPECIAL_1, diff --git a/lib/IGameCallback.cpp b/lib/IGameCallback.cpp index 5a3ed1608..900fc8baf 100644 --- a/lib/IGameCallback.cpp +++ b/lib/IGameCallback.cpp @@ -525,7 +525,7 @@ const TerrainTile * CGameInfoCallback::getTile( int3 tile, bool verbose) const return &gs->map->getTile(tile); } -EBuildingState::EBuildingState CGameInfoCallback::canBuildStructure( const CGTownInstance *t, int ID ) +EBuildingState::EBuildingState CGameInfoCallback::canBuildStructure( const CGTownInstance *t, BuildingID ID ) { ERROR_RET_VAL_IF(!canGetFullInfo(t), "Town is not owned!", EBuildingState::TOWN_NOT_OWNED); @@ -538,14 +538,14 @@ EBuildingState::EBuildingState CGameInfoCallback::canBuildStructure( const CGTow return EBuildingState::ALREADY_PRESENT; //can we build it? - if(t->forbiddenBuildings.find(ID)!=t->forbiddenBuildings.end()) + if(vstd::contains(t->forbiddenBuildings, ID)) return EBuildingState::FORBIDDEN; //forbidden //checking for requirements - std::set reqs = getBuildingRequiments(t, ID);//getting all requirements + std::set reqs = getBuildingRequiments(t, ID);//getting all requirements bool notAllBuilt = false; - for( std::set::iterator ri = reqs.begin(); ri != reqs.end(); ri++ ) + for( std::set::iterator ri = reqs.begin(); ri != reqs.end(); ri++ ) { if(!t->hasBuilt(*ri)) //lack of requirements - cannot build { @@ -591,9 +591,9 @@ EBuildingState::EBuildingState CGameInfoCallback::canBuildStructure( const CGTow return EBuildingState::ALLOWED; } -std::set CGameInfoCallback::getBuildingRequiments( const CGTownInstance *t, int ID ) +std::set CGameInfoCallback::getBuildingRequiments( const CGTownInstance *t, BuildingID ID ) { - ERROR_RET_VAL_IF(!canGetFullInfo(t), "Town is not owned!", std::set()); + ERROR_RET_VAL_IF(!canGetFullInfo(t), "Town is not owned!", std::set()); std::set used; used.insert(ID); diff --git a/lib/IGameCallback.h b/lib/IGameCallback.h index 4c3834c29..d61ea21ed 100644 --- a/lib/IGameCallback.h +++ b/lib/IGameCallback.h @@ -127,8 +127,8 @@ public: const CGTownInstance * getTownInfo(int val, bool mode)const; //mode = 0 -> val = player town serial; mode = 1 -> val = object id (serial) std::vector getAvailableHeroes(const CGObjectInstance * townOrTavern) const; //heroes that can be recruited std::string getTavernGossip(const CGObjectInstance * townOrTavern) const; - EBuildingState::EBuildingState canBuildStructure(const CGTownInstance *t, int ID);//// 0 - no more than one capitol, 1 - lack of water, 2 - forbidden, 3 - Add another level to Mage Guild, 4 - already built, 5 - cannot build, 6 - cannot afford, 7 - build, 8 - lack of requirements - std::set getBuildingRequiments(const CGTownInstance *t, int ID); + EBuildingState::EBuildingState canBuildStructure(const CGTownInstance *t, BuildingID ID);//// 0 - no more than one capitol, 1 - lack of water, 2 - forbidden, 3 - Add another level to Mage Guild, 4 - already built, 5 - cannot build, 6 - cannot afford, 7 - build, 8 - lack of requirements + std::set getBuildingRequiments(const CGTownInstance *t, BuildingID ID); virtual bool getTownInfo(const CGObjectInstance *town, InfoAboutTown &dest) const; const CTown *getNativeTown(TPlayerColor color) const; @@ -136,7 +136,7 @@ public: const TeamState *getTeam(ui8 teamID) const; const TeamState *getPlayerTeam(TPlayerColor color) const; std::set getBuildingRequiments(const CGTownInstance *t, int ID) const; - EBuildingState::EBuildingState canBuildStructure(const CGTownInstance *t, int ID) const;// 0 - no more than one capitol, 1 - lack of water, 2 - forbidden, 3 - Add another level to Mage Guild, 4 - already built, 5 - cannot build, 6 - cannot afford, 7 - build, 8 - lack of requirements + EBuildingState::EBuildingState canBuildStructure(const CGTownInstance *t, BuildingID ID) const;// 0 - no more than one capitol, 1 - lack of water, 2 - forbidden, 3 - Add another level to Mage Guild, 4 - already built, 5 - cannot build, 6 - cannot afford, 7 - build, 8 - lack of requirements }; diff --git a/lib/IGameEventsReceiver.h b/lib/IGameEventsReceiver.h index 5fea733b0..365d4c227 100644 --- a/lib/IGameEventsReceiver.h +++ b/lib/IGameEventsReceiver.h @@ -72,7 +72,7 @@ public: class DLL_LINKAGE IGameEventsReceiver { public: - virtual void buildChanged(const CGTownInstance *town, int buildingID, int what){}; //what: 1 - built, 2 - demolished + virtual void buildChanged(const CGTownInstance *town, BuildingID buildingID, int what){}; //what: 1 - built, 2 - demolished virtual void battleResultsApplied(){}; //called when all effects of last battle are applied diff --git a/lib/Mapping/CCampaignHandler.cpp b/lib/Mapping/CCampaignHandler.cpp index b526f4445..f2e7aa291 100644 --- a/lib/Mapping/CCampaignHandler.cpp +++ b/lib/Mapping/CCampaignHandler.cpp @@ -173,7 +173,7 @@ CScenarioTravel CCampaignHandler::readScenarioTravelFromMemory( const ui8 * buff for (int g=0; g(buffer[outIt++]); //hero: FFFD means 'most powerful' and FFFE means 'generated' switch(bonus.type) { diff --git a/lib/Mapping/CCampaignHandler.h b/lib/Mapping/CCampaignHandler.h index ba5d9edf2..710e59cf6 100644 --- a/lib/Mapping/CCampaignHandler.h +++ b/lib/Mapping/CCampaignHandler.h @@ -60,7 +60,7 @@ public: { enum EBonusType {SPELL, MONSTER, BUILDING, ARTIFACT, SPELL_SCROLL, PRIMARY_SKILL, SECONDARY_SKILL, RESOURCE, PLAYER_PREV_SCENARIO, HERO}; - ui8 type; //uses EBonusType + EBonusType type; //uses EBonusType si32 info1, info2, info3; //purpose depends on type bool isBonusForHero() const; diff --git a/lib/Mapping/CMap.h b/lib/Mapping/CMap.h index 4c557d5d4..779530541 100644 --- a/lib/Mapping/CMap.h +++ b/lib/Mapping/CMap.h @@ -361,7 +361,7 @@ public: CCastleEvent(); /** build specific buildings */ - std::set buildings; + std::set buildings; /** additional creatures in i-th level dwelling */ std::vector creatures; diff --git a/lib/Mapping/MapFormatH3M.cpp b/lib/Mapping/MapFormatH3M.cpp index 552748ad5..d926d9a4a 100644 --- a/lib/Mapping/MapFormatH3M.cpp +++ b/lib/Mapping/MapFormatH3M.cpp @@ -1908,7 +1908,7 @@ CGTownInstance * CMapLoaderH3M::readTown(int castleID) } //means that set of standard building should be included - nt->builtBuildings.insert(-50); + nt->builtBuildings.insert(BuildingID::DEFAULT); } if(map->version > EMapFormat::ROE) @@ -1922,7 +1922,7 @@ CGTownInstance * CMapLoaderH3M::readTown(int castleID) { if(c == (c | static_cast(std::pow(2., yy)))) { - nt->obligatorySpells.push_back(i * 8 + yy); + nt->obligatorySpells.push_back(SpellID(i * 8 + yy)); } } } @@ -1938,7 +1938,7 @@ CGTownInstance * CMapLoaderH3M::readTown(int castleID) { if(c != (c | static_cast(std::pow(2., yy)))) { - nt->possibleSpells.push_back(i * 8 + yy); + nt->possibleSpells.push_back(SpellID(i * 8 + yy)); } } } @@ -1996,10 +1996,10 @@ CGTownInstance * CMapLoaderH3M::readTown(int castleID) return nt; } -std::set CMapLoaderH3M::convertBuildings(const std::set h3m, int castleID, bool addAuxiliary /*= true*/) +std::set CMapLoaderH3M::convertBuildings(const std::set h3m, int castleID, bool addAuxiliary /*= true*/) { - std::map mapa; - std::set ret; + std::map mapa; + std::set ret; // Note: this file is parsed many times. const JsonNode config(ResourceID("config/buildings5.json")); @@ -2010,7 +2010,7 @@ std::set CMapLoaderH3M::convertBuildings(const std::set h3m, int cas if (town == castleID || town == -1) { - mapa[entry["h3"].Float()] = entry["vcmi"].Float(); + mapa[entry["h3"].Float()] = BuildingID((si32)entry["vcmi"].Float()); } } @@ -2026,7 +2026,7 @@ std::set CMapLoaderH3M::convertBuildings(const std::set h3m, int cas int level = (mapa[*i]); //(-30)..(-36) - horde buildings (for game loading only), don't see other way to handle hordes in random towns - ret.insert(level - 30); + ret.insert(BuildingID(level - 30)); } else { diff --git a/lib/Mapping/MapFormatH3M.h b/lib/Mapping/MapFormatH3M.h index 2def5ffdb..4bfddeb18 100644 --- a/lib/Mapping/MapFormatH3M.h +++ b/lib/Mapping/MapFormatH3M.h @@ -203,7 +203,7 @@ private: * @param addAuxiliary true if the village hall should be added * @return the converted buildings */ - std::set convertBuildings(const std::set h3m, int castleID, bool addAuxiliary = true); + std::set convertBuildings(const std::set h3m, int castleID, bool addAuxiliary = true); /** * Reads events. diff --git a/lib/NetPacks.h b/lib/NetPacks.h index 738233735..6c649ec05 100644 --- a/lib/NetPacks.h +++ b/lib/NetPacks.h @@ -644,7 +644,7 @@ struct NewStructures : public CPackForClient //504 DLL_LINKAGE void applyGs(CGameState *gs); si32 tid; - std::set bid; + std::set bid; si16 builded; template void serialize(Handler &h, const int version) @@ -659,7 +659,7 @@ struct RazeStructures : public CPackForClient //505 DLL_LINKAGE void applyGs(CGameState *gs); si32 tid; - std::set bid; + std::set bid; si16 destroyed; template void serialize(Handler &h, const int version) @@ -1838,8 +1838,9 @@ struct DisbandCreature : public CPackForServer struct BuildStructure : public CPackForServer { BuildStructure(){}; - BuildStructure(si32 TID, si32 BID):bid(BID),tid(TID){}; - si32 bid, tid; //structure and town ids + BuildStructure(si32 TID, BuildingID BID):bid(BID),tid(TID){}; + si32 tid; //town id + BuildingID bid; //structure id bool applyGh(CGameHandler *gh); template void serialize(Handler &h, const int version) diff --git a/lib/NetPacksLib.cpp b/lib/NetPacksLib.cpp index 0dcae2664..c2e7d8e1e 100644 --- a/lib/NetPacksLib.cpp +++ b/lib/NetPacksLib.cpp @@ -414,7 +414,7 @@ void TryMoveHero::applyGs( CGameState *gs ) DLL_LINKAGE void NewStructures::applyGs( CGameState *gs ) { CGTownInstance *t = gs->getTown(tid); - BOOST_FOREACH(si32 id,bid) + BOOST_FOREACH(const auto & id, bid) { t->builtBuildings.insert(id); } @@ -424,7 +424,7 @@ DLL_LINKAGE void NewStructures::applyGs( CGameState *gs ) DLL_LINKAGE void RazeStructures::applyGs( CGameState *gs ) { CGTownInstance *t = gs->getTown(tid); - BOOST_FOREACH(si32 id,bid) + BOOST_FOREACH(const auto & id, bid) { t->builtBuildings.erase(id); } diff --git a/lib/RMG/CMapGenerator.cpp b/lib/RMG/CMapGenerator.cpp index 8a10fecdd..d06ce2119 100644 --- a/lib/RMG/CMapGenerator.cpp +++ b/lib/RMG/CMapGenerator.cpp @@ -317,7 +317,7 @@ void CMapGenerator::genTowns() town->tempOwner = owner; town->defInfo = VLC->dobjinfo->gobjs[town->ID][town->subID]; town->builtBuildings.insert(BuildingID::FORT); - town->builtBuildings.insert(-50); + town->builtBuildings.insert(BuildingID::DEFAULT); mapMgr->insertObject(town, townPos[side].x, townPos[side].y + (pos / 2) * 5, false); // Update player info diff --git a/server/CGameHandler.cpp b/server/CGameHandler.cpp index 0df8af13f..1365d4801 100644 --- a/server/CGameHandler.cpp +++ b/server/CGameHandler.cpp @@ -2462,7 +2462,7 @@ bool CGameHandler::disbandCreature( si32 id, ui8 pos ) return true; } -bool CGameHandler::buildStructure( si32 tid, si32 bid, bool force /*=false*/ ) +bool CGameHandler::buildStructure( si32 tid, BuildingID bid, bool force /*=false*/ ) { CGTownInstance * t = static_cast(gs->map->objects[tid].get()); CBuilding * b = t->town->buildings[bid]; @@ -2574,7 +2574,7 @@ bool CGameHandler::buildStructure( si32 tid, si32 bid, bool force /*=false*/ ) checkLossVictory(t->tempOwner); return true; } -bool CGameHandler::razeStructure (si32 tid, si32 bid) +bool CGameHandler::razeStructure (si32 tid, BuildingID bid) { ///incomplete, simply erases target building CGTownInstance * t = static_cast(gs->map->objects[tid].get()); @@ -4783,12 +4783,14 @@ void CGameHandler::handleTownEvents(CGTownInstance * town, NewTurn &n, std::map< } - for(std::set::iterator i = ev->buildings.begin(); i!=ev->buildings.end();i++) - if ( town->hasBuilt(*i)) + BOOST_FOREACH(auto & i, ev->buildings) + { + if ( town->hasBuilt(i)) { - buildStructure(town->id, *i, true); - iw.components.push_back(Component(Component::BUILDING, town->subID, *i, 0)); + buildStructure(town->id, i, true); + iw.components.push_back(Component(Component::BUILDING, town->subID, i, 0)); } + } for(si32 i=0;icreatures.size();i++) //creature growths { diff --git a/server/CGameHandler.h b/server/CGameHandler.h index d7b5dd321..87a1b2640 100644 --- a/server/CGameHandler.h +++ b/server/CGameHandler.h @@ -222,8 +222,8 @@ public: bool garrisonSwap(si32 tid); bool upgradeCreature( ui32 objid, ui8 pos, ui32 upgID ); bool recruitCreatures(si32 objid, CreatureID crid, ui32 cram, si32 level); - bool buildStructure(si32 tid, si32 bid, bool force=false);//force - for events: no cost, no checkings - bool razeStructure(si32 tid, si32 bid); + bool buildStructure(si32 tid, BuildingID bid, bool force=false);//force - for events: no cost, no checkings + bool razeStructure(si32 tid, BuildingID bid); bool disbandCreature( si32 id, ui8 pos ); bool arrangeStacks( si32 id1, si32 id2, ui8 what, ui8 p1, ui8 p2, si32 val, TPlayerColor player); void save(const std::string &fname);