mirror of
				https://github.com/vcmi/vcmi.git
				synced 2025-10-31 00:07:39 +02:00 
			
		
		
		
	Broken CHealth dependency on CStack
This commit is contained in:
		| @@ -108,7 +108,7 @@ void CRetaliations::reset() | ||||
| } | ||||
|  | ||||
| ///CHealth | ||||
| CHealth::CHealth(const CStack * Owner): | ||||
| CHealth::CHealth(const IUnitHealthInfo * Owner): | ||||
| 	owner(Owner) | ||||
| { | ||||
| 	reset(); | ||||
| @@ -123,11 +123,11 @@ CHealth::CHealth(const CHealth & other): | ||||
|  | ||||
| } | ||||
|  | ||||
| void CHealth::init(const int32_t baseAmount) | ||||
| void CHealth::init() | ||||
| { | ||||
| 	reset(); | ||||
| 	fullUnits = baseAmount > 1 ? baseAmount - 1 : 0; | ||||
| 	firstHPleft = baseAmount > 0 ? owner->MaxHealth() : 0; | ||||
| 	fullUnits = owner->unitBaseAmount() > 1 ? owner->unitBaseAmount() - 1 : 0; | ||||
| 	firstHPleft = owner->unitBaseAmount() > 0 ? owner->unitMaxHealth() : 0; | ||||
| } | ||||
|  | ||||
| void CHealth::addResurrected(int32_t amount) | ||||
| @@ -138,24 +138,16 @@ void CHealth::addResurrected(int32_t amount) | ||||
|  | ||||
| int64_t CHealth::available() const | ||||
| { | ||||
| 	return static_cast<int64_t>(firstHPleft) + owner->MaxHealth() * fullUnits; | ||||
| 	return static_cast<int64_t>(firstHPleft) + owner->unitMaxHealth() * fullUnits; | ||||
| } | ||||
|  | ||||
| int64_t CHealth::total() const | ||||
| { | ||||
| 	return static_cast<int64_t>(owner->MaxHealth()) * owner->baseAmount; | ||||
| 	return static_cast<int64_t>(owner->unitMaxHealth()) * owner->unitBaseAmount(); | ||||
| } | ||||
|  | ||||
| void CHealth::damage(int32_t & amount) | ||||
| { | ||||
| 	if(owner->isClone()) | ||||
| 	{ | ||||
| 		// block ability should not kill clone (0 damage) | ||||
| 		if(amount > 0) | ||||
| 			reset(); | ||||
| 		return; | ||||
| 	} | ||||
|  | ||||
| 	const int32_t oldCount = getCount(); | ||||
|  | ||||
| 	const bool withKills = amount >= firstHPleft; | ||||
| @@ -186,7 +178,7 @@ void CHealth::damage(int32_t & amount) | ||||
|  | ||||
| void CHealth::heal(int32_t & amount, EHealLevel level, EHealPower power) | ||||
| { | ||||
| 	const int32_t unitHealth = owner->MaxHealth(); | ||||
| 	const int32_t unitHealth = owner->unitMaxHealth(); | ||||
| 	const int32_t oldCount = getCount(); | ||||
|  | ||||
| 	int32_t maxHeal = std::numeric_limits<int32_t>::max(); | ||||
| @@ -223,7 +215,7 @@ void CHealth::heal(int32_t & amount, EHealLevel level, EHealPower power) | ||||
|  | ||||
| void CHealth::setFromTotal(const int64_t totalHealth) | ||||
| { | ||||
| 	const int32_t unitHealth = owner->MaxHealth(); | ||||
| 	const int32_t unitHealth = owner->unitMaxHealth(); | ||||
| 	firstHPleft = totalHealth % unitHealth; | ||||
| 	fullUnits = totalHealth / unitHealth; | ||||
|  | ||||
| @@ -265,7 +257,6 @@ void CHealth::fromInfo(const CHealthInfo & info) | ||||
|  | ||||
| void CHealth::toInfo(CHealthInfo & info) const | ||||
| { | ||||
| 	info.stackId = owner->ID; | ||||
| 	info.firstHPleft = firstHPleft; | ||||
| 	info.fullUnits = fullUnits; | ||||
| 	info.resurrected = resurrected; | ||||
| @@ -275,7 +266,7 @@ void CHealth::takeResurrected() | ||||
| { | ||||
| 	int64_t totalHealth = total(); | ||||
|  | ||||
| 	totalHealth -= resurrected * owner->MaxHealth(); | ||||
| 	totalHealth -= resurrected * owner->unitMaxHealth(); | ||||
| 	vstd::amax(totalHealth, 0); | ||||
| 	setFromTotal(totalHealth); | ||||
| 	resurrected = 0; | ||||
| @@ -290,7 +281,7 @@ CStack::CStack(const CStackInstance * Base, PlayerColor O, int I, ui8 Side, Slot | ||||
| 	assert(base); | ||||
| 	type = base->type; | ||||
| 	baseAmount = base->count; | ||||
| 	health.init(baseAmount); //??? | ||||
| 	health.init(); //??? | ||||
| 	setNodeType(STACK_BATTLE); | ||||
| } | ||||
|  | ||||
| @@ -308,7 +299,7 @@ CStack::CStack(const CStackBasicDescriptor * stack, PlayerColor O, int I, ui8 Si | ||||
| { | ||||
| 	type = stack->type; | ||||
| 	baseAmount = stack->count; | ||||
| 	health.init(baseAmount); //??? | ||||
| 	health.init(); //??? | ||||
| 	setNodeType(STACK_BATTLE); | ||||
| } | ||||
|  | ||||
| @@ -350,6 +341,7 @@ void CStack::init() | ||||
| void CStack::localInit(BattleInfo * battleInfo) | ||||
| { | ||||
| 	battle = battleInfo; | ||||
| 	cloneID = -1; | ||||
| 	assert(type); | ||||
|  | ||||
| 	exportBonuses(); | ||||
| @@ -367,8 +359,7 @@ void CStack::localInit(BattleInfo * battleInfo) | ||||
| 	shots.reset(); | ||||
| 	counterAttacks.reset(); | ||||
| 	casts.reset(); | ||||
| 	health.init(baseAmount); | ||||
| 	cloneID = -1; | ||||
| 	health.init(); | ||||
| } | ||||
|  | ||||
| ui32 CStack::level() const | ||||
| @@ -620,8 +611,27 @@ std::string CStack::nodeName() const | ||||
|  | ||||
| CHealth CStack::healthAfterAttacked(int32_t & damage) const | ||||
| { | ||||
| 	CHealth res = health; | ||||
| 	res.damage(damage); | ||||
| 	return healthAfterAttacked(damage, health); | ||||
| } | ||||
|  | ||||
| CHealth CStack::healthAfterAttacked(int32_t & damage, const CHealth & customHealth) const | ||||
| { | ||||
| 	CHealth res = customHealth; | ||||
|  | ||||
| 	if(isClone()) | ||||
| 	{ | ||||
| 		// block ability should not kill clone (0 damage) | ||||
| 		if(damage > 0) | ||||
| 		{ | ||||
| 			damage = 1;//??? what should be actual damage against clone? | ||||
| 			res.reset(); | ||||
| 		} | ||||
| 	} | ||||
| 	else | ||||
| 	{ | ||||
| 		res.damage(damage); | ||||
| 	} | ||||
|  | ||||
| 	return res; | ||||
| } | ||||
|  | ||||
| @@ -646,11 +656,11 @@ void CStack::prepareAttacked(BattleStackAttacked & bsa, CRandomGenerator & rand) | ||||
|  | ||||
| void CStack::prepareAttacked(BattleStackAttacked & bsa, CRandomGenerator & rand, const CHealth & customHealth) const | ||||
| { | ||||
| 	CHealth afterAttack = customHealth; | ||||
| 	afterAttack.damage(bsa.damageAmount); | ||||
| 	CHealth afterAttack = healthAfterAttacked(bsa.damageAmount, customHealth); | ||||
|  | ||||
| 	bsa.killedAmount = customHealth.getCount() - afterAttack.getCount(); | ||||
| 	afterAttack.toInfo(bsa.newHealth); | ||||
| 	bsa.newHealth.stackId = ID; | ||||
| 	bsa.newHealth.delta = -bsa.damageAmount; | ||||
|  | ||||
| 	if(afterAttack.available() <= 0 && isClone()) | ||||
| @@ -824,6 +834,16 @@ void CStack::getCastDescription(const CSpell * spell, const std::vector<const CS | ||||
| 	text.addReplacement(MetaString::SPELL_NAME, spell->id.toEnum()); | ||||
| } | ||||
|  | ||||
| int32_t CStack::unitMaxHealth() const | ||||
| { | ||||
| 	return MaxHealth(); | ||||
| } | ||||
|  | ||||
| int32_t CStack::unitBaseAmount() const | ||||
| { | ||||
| 	return baseAmount; | ||||
| } | ||||
|  | ||||
| void CStack::addText(MetaString & text, ui8 type, int32_t serial, const boost::logic::tribool & plural) const | ||||
| { | ||||
| 	if(boost::logic::indeterminate(plural)) | ||||
|   | ||||
							
								
								
									
										22
									
								
								lib/CStack.h
									
									
									
									
									
								
							
							
						
						
									
										22
									
								
								lib/CStack.h
									
									
									
									
									
								
							| @@ -81,13 +81,20 @@ private: | ||||
| 	mutable int32_t totalCache; | ||||
| }; | ||||
|  | ||||
| class DLL_LINKAGE IUnitHealthInfo | ||||
| { | ||||
| public: | ||||
| 	virtual int32_t unitMaxHealth() const = 0; | ||||
| 	virtual int32_t unitBaseAmount() const = 0; | ||||
| }; | ||||
|  | ||||
| class DLL_LINKAGE CHealth | ||||
| { | ||||
| public: | ||||
| 	CHealth(const CStack * Owner); | ||||
| 	CHealth(const IUnitHealthInfo * Owner); | ||||
| 	CHealth(const CHealth & other); | ||||
|  | ||||
| 	void init(const int32_t baseAmount); | ||||
| 	void init(); | ||||
| 	void reset(); | ||||
|  | ||||
| 	void damage(int32_t & amount); | ||||
| @@ -114,14 +121,14 @@ public: | ||||
| private: | ||||
| 	void addResurrected(int32_t amount); | ||||
| 	void setFromTotal(const int64_t totalHealth); | ||||
| 	const CStack * owner; | ||||
| 	const IUnitHealthInfo * owner; | ||||
|  | ||||
| 	int32_t firstHPleft; | ||||
| 	int32_t fullUnits; | ||||
| 	int32_t resurrected; | ||||
| }; | ||||
|  | ||||
| class DLL_LINKAGE CStack : public CBonusSystemNode, public ISpellCaster | ||||
| class DLL_LINKAGE CStack : public CBonusSystemNode, public ISpellCaster, public IUnitHealthInfo | ||||
| { | ||||
| public: | ||||
| 	const CStackInstance * base; //garrison slot from which stack originates (nullptr for war machines, summoned cres, etc) | ||||
| @@ -195,6 +202,8 @@ public: | ||||
| 	BattleHex::EDir destShiftDir() const; | ||||
|  | ||||
| 	CHealth healthAfterAttacked(int32_t & damage) const; | ||||
| 	CHealth healthAfterAttacked(int32_t & damage, const CHealth & customHealth) const; | ||||
|  | ||||
| 	CHealth healthAfterHealed(int32_t & toHeal, EHealLevel level, EHealPower power) const; | ||||
|  | ||||
| 	void prepareAttacked(BattleStackAttacked & bsa, CRandomGenerator & rand) const; //requires bsa.damageAmout filled | ||||
| @@ -221,6 +230,11 @@ public: | ||||
| 	void getCasterName(MetaString & text) const override; | ||||
| 	void getCastDescription(const CSpell * spell, const std::vector<const CStack *> & attacked, MetaString & text) const override; | ||||
|  | ||||
| 	///IUnitHealthInfo | ||||
|  | ||||
| 	int32_t unitMaxHealth() const override; | ||||
| 	int32_t unitBaseAmount() const override; | ||||
|  | ||||
| 	///MetaStrings | ||||
|  | ||||
| 	void addText(MetaString & text, ui8 type, int32_t serial, const boost::logic::tribool & plural = boost::logic::indeterminate) const; | ||||
|   | ||||
| @@ -43,6 +43,7 @@ void HealingSpellMechanics::applyBattleEffects(const SpellCastEnvironment * env, | ||||
|  | ||||
| 		CHealthInfo hi; | ||||
| 		health.toInfo(hi); | ||||
| 		hi.stackId = attackedCre->ID; | ||||
| 		hi.delta = stackHPgained; | ||||
| 		shr.healedStacks.push_back(hi); | ||||
| 	} | ||||
|   | ||||
| @@ -965,6 +965,7 @@ void CGameHandler::applyBattleEffects(BattleAttack &bat, const CStack *att, cons | ||||
|  | ||||
| 		CHealthInfo hi; | ||||
| 		health.toInfo(hi); | ||||
| 		hi.stackId = att->ID; | ||||
| 		hi.delta = toHeal; | ||||
| 		shi.healedStacks.push_back(hi); | ||||
|  | ||||
| @@ -989,6 +990,7 @@ void CGameHandler::applyBattleEffects(BattleAttack &bat, const CStack *att, cons | ||||
| 				CHealth health = att->healthAfterHealed(toHeal, EHealLevel::OVERHEAL, ((i == 0) ? EHealPower::ONE_BATTLE : EHealPower::PERMANENT)); | ||||
| 				CHealthInfo hi; | ||||
| 				health.toInfo(hi); | ||||
| 				hi.stackId = att->ID; | ||||
| 				hi.delta = toHeal; | ||||
| 				if(hi.delta > 0) | ||||
| 					shi.healedStacks.push_back(hi); | ||||
| @@ -4242,7 +4244,8 @@ bool CGameHandler::makeBattleAction(BattleAction &ba) | ||||
|  | ||||
| 					CHealthInfo hi; | ||||
| 					health.toInfo(hi); | ||||
|  | ||||
| 					hi.stackId = destStack->ID; | ||||
| 					hi.delta = toHeal; | ||||
| 					shr.healedStacks.push_back(hi); | ||||
| 					sendAndApply(&shr); | ||||
| 				} | ||||
|   | ||||
		Reference in New Issue
	
	Block a user