diff --git a/lib/CTownHandler.cpp b/lib/CTownHandler.cpp index b1d5f240c..5f614aa24 100644 --- a/lib/CTownHandler.cpp +++ b/lib/CTownHandler.cpp @@ -627,6 +627,12 @@ void CTownHandler::loadBuilding(CTown * town, const std::string & stringID, cons for(auto & bonus : ret->onVisitBonuses) bonus->sid = Bonus::getSid32(ret->town->faction->getIndex(), ret->bid); } + + if(!source["rewards"].isNull() && ret->subId == BuildingSubID::NONE) + { + ret->subId = BuildingSubID::CONFIGURABLE_REWARD; + ret->rewardableObjectInfo.init(source["rewards"]); + } } //MODS COMPATIBILITY FOR 0.96 if(!ret->produce.nonZero()) diff --git a/lib/CTownHandler.h b/lib/CTownHandler.h index 7bc7a6d43..04799875b 100644 --- a/lib/CTownHandler.h +++ b/lib/CTownHandler.h @@ -21,6 +21,7 @@ #include "battle/BattleHex.h" #include "HeroBonus.h" #include "Point.h" +#include "mapObjects/CRewardableConstructor.h" VCMI_LIB_NAMESPACE_BEGIN @@ -56,6 +57,8 @@ public: std::set overrideBids; /// the building which bonuses should be overridden with bonuses of the current building BonusList buildingBonuses; BonusList onVisitBonuses; + + CRandomRewardObjectInfo rewardableObjectInfo; ///configurable rewards for special buildings enum EBuildMode { @@ -134,6 +137,7 @@ public: h & overrideBids; h & buildingBonuses; h & onVisitBonuses; + h & rewardableObjectInfo; } friend class CTownHandler; diff --git a/lib/GameConstants.h b/lib/GameConstants.h index 2e006abfb..5e8d84614 100644 --- a/lib/GameConstants.h +++ b/lib/GameConstants.h @@ -581,7 +581,8 @@ namespace BuildingSubID EXPERIENCE_VISITING_BONUS, LIGHTHOUSE, TREASURY, - CUSTOM_VISITING_BONUS + CUSTOM_VISITING_BONUS, + CONFIGURABLE_REWARD }; } diff --git a/lib/mapObjects/CGTownBuilding.h b/lib/mapObjects/CGTownBuilding.h index 39233f532..713cad6e1 100644 --- a/lib/mapObjects/CGTownBuilding.h +++ b/lib/mapObjects/CGTownBuilding.h @@ -11,6 +11,7 @@ #pragma once #include "CObjectHandler.h" +#include "CRewardableObject.h" VCMI_LIB_NAMESPACE_BEGIN @@ -104,4 +105,20 @@ private: void applyBonuses(CGHeroInstance * h, const BonusList & bonuses) const; }; +class DLL_LINKAGE CTownRewardableBuilding : public CGTownBuilding, public Rewardable::Interface +{ +public: + void setProperty(ui8 what, ui32 val) override; + void onHeroVisit (const CGHeroInstance * h) const override; + + CTownRewardableBuilding(CGTownInstance * TOWN); + CTownRewardableBuilding() = default; + + template void serialize(Handler &h, const int version) + { + h & static_cast(*this); + h & static_cast(*this); + } +}; + VCMI_LIB_NAMESPACE_END diff --git a/lib/mapObjects/CGTownInstance.cpp b/lib/mapObjects/CGTownInstance.cpp index 7107d80e5..386834741 100644 --- a/lib/mapObjects/CGTownInstance.cpp +++ b/lib/mapObjects/CGTownInstance.cpp @@ -365,7 +365,7 @@ bool CGTownInstance::isBonusingBuildingAdded(BuildingID::EBuildingID bid) const return present != bonusingBuildings.end(); } -void CGTownInstance::addTownBonuses() +void CGTownInstance::addTownBonuses(CRandomGenerator & rand) { for(const auto & kvp : town->buildings) { @@ -377,6 +377,13 @@ void CGTownInstance::addTownBonuses() if(kvp.second->IsWeekBonus()) bonusingBuildings.push_back(new COPWBonus(kvp.second->bid, kvp.second->subId, this)); + + if(kvp.second->subId == BuildingSubID::CONFIGURABLE_REWARD) + { + auto * newBuilding = new CTownRewardableBuilding(this); + kvp.second->rewardableObjectInfo.configureObject(newBuilding->configuration(), rand); + bonusingBuildings.push_back(newBuilding); + } } } @@ -465,7 +472,7 @@ void CGTownInstance::initObj(CRandomGenerator & rand) ///initialize town structu } } initOverriddenBids(); - addTownBonuses(); //add special bonuses from buildings to the bonusingBuildings vector. + addTownBonuses(rand); //add special bonuses from buildings to the bonusingBuildings vector. recreateBuildingsBonuses(); updateAppearance(); } diff --git a/lib/mapObjects/CGTownInstance.h b/lib/mapObjects/CGTownInstance.h index dbc40e1af..fd9c9dd95 100644 --- a/lib/mapObjects/CGTownInstance.h +++ b/lib/mapObjects/CGTownInstance.h @@ -214,7 +214,7 @@ private: bool townEnvisagesBuilding(BuildingSubID::EBuildingSubID bid) const; bool isBonusingBuildingAdded(BuildingID::EBuildingID bid) const; void initOverriddenBids(); - void addTownBonuses(); + void addTownBonuses(CRandomGenerator & rand); }; VCMI_LIB_NAMESPACE_END