1
0
mirror of https://github.com/vcmi/vcmi.git synced 2024-12-02 09:02:03 +02:00
vcmi/lib/gameState/InfoAboutArmy.cpp
Ivan Savenko 037efdf5fc Improvements to type safety of Identifier class
- Constructor of Identifier from integer is now explicit
- Lobby hero/town selection now uses Identifiers instead of int's
- Removed serialization workaround for hero portraits
- Added dummy objects for custom heroes portraits for ID resolver to use
- HeroInstance now stores portrait ID only in case of custom portrait
- Fixed loading of campaign heroes portraits on RoE maps
2023-10-04 18:05:23 +03:00

189 lines
4.1 KiB
C++

/*
* InfoAboutArmy.cpp, part of VCMI engine
*
* Authors: listed in file AUTHORS in main folder
*
* License: GNU General Public License v2.0 or later
* Full text of license available in license.txt file, in main folder
*
*/
#include "StdInc.h"
#include "InfoAboutArmy.h"
#include "../mapObjects/CGHeroInstance.h"
#include "../mapObjects/CGTownInstance.h"
#include "../CHeroHandler.h"
VCMI_LIB_NAMESPACE_BEGIN
ArmyDescriptor::ArmyDescriptor(const CArmedInstance *army, bool detailed)
: isDetailed(detailed)
{
for(const auto & elem : army->Slots())
{
if(detailed)
(*this)[elem.first] = *elem.second;
else
(*this)[elem.first] = CStackBasicDescriptor(elem.second->type, (int)elem.second->getQuantityID());
}
}
ArmyDescriptor::ArmyDescriptor()
: isDetailed(false)
{
}
int ArmyDescriptor::getStrength() const
{
ui64 ret = 0;
if(isDetailed)
{
for(const auto & elem : *this)
ret += elem.second.type->getAIValue() * elem.second.count;
}
else
{
for(const auto & elem : *this)
ret += elem.second.type->getAIValue() * CCreature::estimateCreatureCount(elem.second.count);
}
return static_cast<int>(ret);
}
InfoAboutArmy::InfoAboutArmy():
owner(PlayerColor::NEUTRAL)
{}
InfoAboutArmy::InfoAboutArmy(const CArmedInstance *Army, bool detailed)
{
initFromArmy(Army, detailed);
}
void InfoAboutArmy::initFromArmy(const CArmedInstance *Army, bool detailed)
{
army = ArmyDescriptor(Army, detailed);
owner = Army->tempOwner;
name = Army->getObjectName();
}
void InfoAboutHero::assign(const InfoAboutHero & iah)
{
vstd::clear_pointer(details);
InfoAboutArmy::operator = (iah);
details = (iah.details ? new Details(*iah.details) : nullptr);
hclass = iah.hclass;
portraitSource = iah.portraitSource;
}
InfoAboutHero::InfoAboutHero()
{}
InfoAboutHero::InfoAboutHero(const InfoAboutHero & iah): InfoAboutArmy(iah)
{
assign(iah);
}
InfoAboutHero::InfoAboutHero(const CGHeroInstance * h, InfoAboutHero::EInfoLevel infoLevel)
{
initFromHero(h, infoLevel);
}
InfoAboutHero::~InfoAboutHero()
{
vstd::clear_pointer(details);
}
InfoAboutHero & InfoAboutHero::operator=(const InfoAboutHero & iah)
{
assign(iah);
return *this;
}
int32_t InfoAboutHero::getIconIndex() const
{
return VLC->heroTypes()->getById(portraitSource)->getIconIndex();
}
void InfoAboutHero::initFromHero(const CGHeroInstance *h, InfoAboutHero::EInfoLevel infoLevel)
{
vstd::clear_pointer(details);
if(!h)
return;
bool detailed = ( (infoLevel == EInfoLevel::DETAILED) || (infoLevel == EInfoLevel::INBATTLE) );
initFromArmy(h, detailed);
hclass = h->type->heroClass;
name = h->getNameTranslated();
portraitSource = h->getPortraitSource();
if(detailed)
{
//include details about hero
details = new Details();
details->luck = h->luckVal();
details->morale = h->moraleVal();
details->mana = h->mana;
details->primskills.resize(GameConstants::PRIMARY_SKILLS);
for (int i = 0; i < GameConstants::PRIMARY_SKILLS ; i++)
{
details->primskills[i] = h->getPrimSkillLevel(static_cast<PrimarySkill>(i));
}
if (infoLevel == EInfoLevel::INBATTLE)
details->manaLimit = h->manaLimit();
else
details->manaLimit = -1; //we do not want to leak max mana info outside battle so set to meaningless value
}
}
InfoAboutTown::InfoAboutTown():
details(nullptr),
tType(nullptr),
built(0),
fortLevel(0)
{
}
InfoAboutTown::InfoAboutTown(const CGTownInstance *t, bool detailed):
details(nullptr),
tType(nullptr),
built(0),
fortLevel(0)
{
initFromTown(t, detailed);
}
InfoAboutTown::~InfoAboutTown()
{
vstd::clear_pointer(details);
}
void InfoAboutTown::initFromTown(const CGTownInstance *t, bool detailed)
{
initFromArmy(t, detailed);
army = ArmyDescriptor(t->getUpperArmy(), detailed);
built = t->builded;
fortLevel = t->fortLevel();
name = t->getNameTranslated();
tType = t->getTown();
vstd::clear_pointer(details);
if(detailed)
{
//include details about hero
details = new Details();
TResources income = t->dailyIncome();
details->goldIncome = income[EGameResID::GOLD];
details->customRes = t->hasBuilt(BuildingID::RESOURCE_SILO);
details->hallLevel = t->hallLevel();
details->garrisonedHero = t->garrisonHero;
}
}
VCMI_LIB_NAMESPACE_END