diff --git a/Global.h b/Global.h index 7c4f0a535..da3afddd7 100644 --- a/Global.h +++ b/Global.h @@ -79,6 +79,7 @@ #include #include #include +#include #include #include #include diff --git a/client/CPreGame.cpp b/client/CPreGame.cpp index 5cb3350bc..7710b7085 100644 --- a/client/CPreGame.cpp +++ b/client/CPreGame.cpp @@ -3409,7 +3409,7 @@ void CBonusSelection::updateBonusSelection() bonuses->buttons.clear(); static const char *bonusPics[] = {"SPELLBON.DEF", "TWCRPORT.DEF", "", "ARTIFBON.DEF", "SPELLBON.DEF", - "PSKILBON.DEF", "SSKILBON.DEF", "BORES.DEF", "CREST58.DEF", "PORTRAITSLARGE"}; + "PSKILBON.DEF", "SSKILBON.DEF", "BORES.DEF", "PORTRAITSLARGE", "PORTRAITSLARGE"}; for(int i = 0; i < bonDescs.size(); i++) { @@ -3531,11 +3531,14 @@ void CBonusSelection::updateBonusSelection() } break; case CScenarioTravel::STravelBonus::PLAYER_PREV_SCENARIO: - picNumber = bonDescs[i].info1; - desc = CGI->generaltexth->allTexts[718]; + { + auto superhero = ourCampaign->camp->scenarios[bonDescs[i].info2].strongestHero(bonDescs[i].info1); + if (!superhero) tlog5 << "No superhero! How could it be transfered?\n"; + picNumber = superhero ? superhero->portrait : 0; + desc = CGI->generaltexth->allTexts[719]; - boost::algorithm::replace_first(desc, "%s", CGI->generaltexth->capColors[bonDescs[i].info1]); //player color - boost::algorithm::replace_first(desc, "%s", ourCampaign->camp->scenarios[bonDescs[i].info2].mapName); //scenario + boost::algorithm::replace_first(desc, "%s", ourCampaign->camp->scenarios[bonDescs[i].info2].scenarioName); //scenario + } break; case CScenarioTravel::STravelBonus::HERO: diff --git a/lib/Mapping/CCampaignHandler.cpp b/lib/Mapping/CCampaignHandler.cpp index 61af510ee..b526f4445 100644 --- a/lib/Mapping/CCampaignHandler.cpp +++ b/lib/Mapping/CCampaignHandler.cpp @@ -10,6 +10,8 @@ #include "../CArtHandler.h" //for hero crossover #include "../CObjectHandler.h" //for hero crossover #include "../CHeroHandler.h" +#include "CMapService.h" +#include "CMap.h" namespace fs = boost::filesystem; @@ -64,6 +66,7 @@ unique_ptr CCampaignHandler::getCampaign( const std::string & name ) //set map piece appropriately, convert vector to string ret->mapPieces[scenarioID].assign(reinterpret_cast< const char* >(file[g].data()), file[g].size()); + ret->scenarios[scenarioID].scenarioName = CMapService::loadMapHeader((const ui8*)ret->mapPieces[scenarioID].c_str(), ret->mapPieces[scenarioID].size())->name; scenarioID++; } @@ -397,6 +400,17 @@ void CCampaignScenario::prepareCrossoverHeroes( std::vector he } } +const CGHeroInstance * CCampaignScenario::strongestHero( TPlayerColor owner ) const +{ + using boost::adaptors::filtered; + std::function isOwned = [=](const CGHeroInstance *h){ return h->tempOwner == owner; }; + auto ownedHeroes = crossoverHeroes | filtered(isOwned); + + auto i = vstd::maxElementByFun(ownedHeroes, + [](const CGHeroInstance * h) {return h->getTotalStrength();}); + return i == ownedHeroes.end() ? nullptr : *i; +} + bool CScenarioTravel::STravelBonus::isBonusForHero() const { return type == SPELL || type == MONSTER || type == ARTIFACT || type == SPELL_SCROLL || type == PRIMARY_SKILL diff --git a/lib/Mapping/CCampaignHandler.h b/lib/Mapping/CCampaignHandler.h index 2145096c2..ba5d9edf2 100644 --- a/lib/Mapping/CCampaignHandler.h +++ b/lib/Mapping/CCampaignHandler.h @@ -83,7 +83,8 @@ public: class DLL_LINKAGE CCampaignScenario { public: - std::string mapName; + std::string mapName; //*.h3m + std::string scenarioName; //from header. human-readble ui32 packedMapSize; //generally not used std::set preconditionRegions; //what we need to conquer to conquer this one (stored as bitfield in h3c) ui8 regionColor; @@ -111,6 +112,8 @@ public: std::vector crossoverHeroes; + const CGHeroInstance * strongestHero(TPlayerColor owner) const; + void loadPreconditionRegions(ui32 regions); void prepareCrossoverHeroes(std::vector heroes); @@ -118,7 +121,7 @@ public: template void serialize(Handler &h, const int formatVersion) { - h & mapName & packedMapSize & preconditionRegions & regionColor & difficulty & conquered & regionText & + h & mapName & scenarioName & packedMapSize & preconditionRegions & regionColor & difficulty & conquered & regionText & prolog & epilog & travelOptions & crossoverHeroes; } }; diff --git a/lib/Mapping/MapFormatH3M.cpp b/lib/Mapping/MapFormatH3M.cpp index b2b3abfc9..0c1c87488 100644 --- a/lib/Mapping/MapFormatH3M.cpp +++ b/lib/Mapping/MapFormatH3M.cpp @@ -1329,8 +1329,7 @@ void CMapLoaderH3M::readObjects() CGHeroPlaceholder * hp = new CGHeroPlaceholder(); nobj = hp; - int a = reader.readUInt8();//unknown byte, seems to be always 0 (if not - scream!) - tlog2 << "Unhandled Hero Placeholder detected: " << a << std::endl; + hp->setOwner(reader.readUInt8()); int htid = reader.readUInt8();; //hero type id nobj->subID = htid;