1
0
mirror of https://github.com/vcmi/vcmi.git synced 2025-08-13 19:54:17 +02:00

Do not ban heroes in Prisons, they might be rehired after they are defeated.

Restore hero to pool if Prison fails to be placed.
This commit is contained in:
Tomasz Zieliński
2024-01-15 07:41:29 +01:00
parent ee6c331bad
commit 285bafdbf4
6 changed files with 12 additions and 21 deletions

View File

@@ -509,17 +509,6 @@ void CMapGenerator::banQuestArt(const ArtifactID & id)
map->getMap(this).allowedArtifact.erase(id);
}
void CMapGenerator::banHero(const HeroTypeID & id)
{
map->getMap(this).banHero(id);
}
void CMapGenerator::unbanHero(const HeroTypeID & id)
{
map->getMap(this).unbanHero(id);
}
Zone * CMapGenerator::getZoneWater() const
{
for(auto & z : map->getZones())

View File

@@ -65,8 +65,6 @@ public:
const std::vector<ArtifactID> & getAllPossibleQuestArtifacts() const;
const std::vector<HeroTypeID> getAllPossibleHeroes() const;
void banQuestArt(const ArtifactID & id);
void banHero(const HeroTypeID& id);
void unbanHero(const HeroTypeID & id);
Zone * getZoneWater() const;
void addWaterTreasuresInfo();

View File

@@ -56,20 +56,18 @@ HeroTypeID PrisonHeroPlacer::drawRandomHero()
RandomGeneratorUtil::randomShuffle(allowedHeroes, zone.getRand());
HeroTypeID ret = allowedHeroes.back();
allowedHeroes.pop_back();
generator.banHero(ret);
return ret;
}
else
{
throw rmgException("No quest heroes left for prisons!");
throw rmgException("No unused heroes left for prisons!");
}
}
void PrisonHeroPlacer::unbanHero(const HeroTypeID & hid)
void PrisonHeroPlacer::restoreDrawnHero(const HeroTypeID & hid)
{
RecursiveLock lock(externalAccessMutex);
generator.unbanHero(hid);
allowedHeroes.push_back(hid);
}
VCMI_LIB_NAMESPACE_END

View File

@@ -27,7 +27,7 @@ public:
int getPrisonsRemaning() const;
HeroTypeID drawRandomHero();
void unbanHero(const HeroTypeID & hid);
void restoreDrawnHero(const HeroTypeID & hid);
private:
void getAllowedHeroes();

View File

@@ -130,7 +130,8 @@ void TreasurePlacer::addAllPossibleObjects()
HeroTypeID hid = prisonHeroPlacer->drawRandomHero();
oi.destroyObject = [hid, prisonHeroPlacer]()
{
prisonHeroPlacer->unbanHero(hid);
// Hero can be used again
prisonHeroPlacer->restoreDrawnHero(hid);
};
auto factory = VLC->objtypeh->getHandlerFor(Obj::PRISON, 0);

View File

@@ -131,7 +131,12 @@ void MapController::repairMap(CMap * map) const
//fix hero instance
if(auto * nih = dynamic_cast<CGHeroInstance*>(obj.get()))
{
// All heroes present on map or in prisons need to be allowed to rehire them after they are defeated
// FIXME: How about custom scenarios where defeated hero cannot be hired again?
map->allowedHeroes.insert(nih->getHeroType());
auto type = VLC->heroh->objects[nih->subID];
assert(type->heroClass);
//TODO: find a way to get proper type name