1
0
mirror of https://github.com/vcmi/vcmi.git synced 2025-01-12 02:28:11 +02:00

Handle HYPNOTIZE effect in case of mana drain

This commit is contained in:
AlexVinS 2016-09-29 21:47:41 +03:00
parent 688dc4c189
commit 83b3c700dd
5 changed files with 25 additions and 14 deletions

View File

@ -95,7 +95,7 @@ std::pair< std::vector<BattleHex>, int > BattleInfo::getPath(BattleHex start, Ba
return std::make_pair(path, reachability.distances[dest]);
}
ui32 BattleInfo::calculateDmg( const CStack* attacker, const CStack* defender, const CGHeroInstance * attackerHero, const CGHeroInstance * defendingHero,
ui32 BattleInfo::calculateDmg( const CStack* attacker, const CStack* defender,
bool shooting, ui8 charge, bool lucky, bool unlucky, bool deathBlow, bool ballistaDoubleDmg, CRandomGenerator & rand )
{
TDmgRange range = calculateDmgRange(attacker, defender, shooting, charge, lucky, unlucky, deathBlow, ballistaDoubleDmg);
@ -150,11 +150,6 @@ CStack * BattleInfo::generateNewStack(const CStackBasicDescriptor &base, bool at
return ret;
}
const CGHeroInstance * BattleInfo::battleGetOwner(const CStack * stack) const
{
return sides[!stack->attackerOwned].hero;
}
void BattleInfo::localInit()
{
for(int i = 0; i < 2; i++)

View File

@ -129,7 +129,7 @@ struct DLL_LINKAGE BattleInfo : public CBonusSystemNode, public CBattleInfoCallb
std::shared_ptr<CObstacleInstance> getObstacleOnTile(BattleHex tile) const;
std::set<BattleHex> getStoppers(bool whichSidePerspective) const;
ui32 calculateDmg(const CStack* attacker, const CStack* defender, const CGHeroInstance * attackerHero, const CGHeroInstance * defendingHero, bool shooting, ui8 charge, bool lucky, bool unlucky, bool deathBlow, bool ballistaDoubleDmg, CRandomGenerator & rand); //charge - number of hexes travelled before attack (for champion's jousting)
ui32 calculateDmg(const CStack * attacker, const CStack * defender, bool shooting, ui8 charge, bool lucky, bool unlucky, bool deathBlow, bool ballistaDoubleDmg, CRandomGenerator & rand); //charge - number of hexes travelled before attack (for champion's jousting)
void calculateCasualties(std::map<ui32,si32> *casualties) const; //casualties are array of maps size 2 (attacker, defeneder), maps are (crid => amount)
//void getPotentiallyAttackableHexes(AttackableTiles &at, const CStack* attacker, BattleHex destinationTile, BattleHex attackerPos); //hexes around target that could be attacked in melee
@ -142,7 +142,6 @@ struct DLL_LINKAGE BattleInfo : public CBonusSystemNode, public CBattleInfoCallb
const CGHeroInstance * getHero(PlayerColor player) const; //returns fighting hero that belongs to given player
const CGHeroInstance * battleGetOwner(const CStack * stack) const; //returns hero that owns given stack; nullptr if none
void localInit();
void localInitStack(CStack * s);

View File

@ -429,7 +429,7 @@ bool CBattleInfoEssentials::playerHasAccessToHeroInfo(PlayerColor player, const
{
RETURN_IF_NOT_BATTLE(false);
ui8 playerSide = playerToSide(player);
if (playerSide >= 0)
if (playerSide != (ui8)-1)
{
if (getBattle()->sides[!playerSide].hero == h)
return true;
@ -478,6 +478,22 @@ EGateState CBattleInfoEssentials::battleGetGateState() const
return getBattle()->si.gateState;
}
PlayerColor CBattleInfoEssentials::battleGetOwner(const CStack * stack) const
{
RETURN_IF_NOT_BATTLE(PlayerColor::CANNOT_DETERMINE);
if(stack->hasBonusOfType(Bonus::HYPNOTIZED))
return getBattle()->theOtherPlayer(stack->owner);
else
return stack->owner;
}
const CGHeroInstance * CBattleInfoEssentials::battleGetOwnerHero(const CStack * stack) const
{
RETURN_IF_NOT_BATTLE(nullptr);
return getBattle()->sides.at(playerToSide(battleGetOwner(stack))).hero;
}
si8 CBattleInfoCallback::battleHasWallPenalty( const CStack * stack, BattleHex destHex ) const
{
return battleHasWallPenalty(stack, stack->position, destHex);
@ -862,7 +878,6 @@ bool CBattleInfoCallback::battleCanShoot(const CStack * stack, BattleHex dest) c
if(stack->getCreature()->idNumber == CreatureID::CATAPULT && dst) //catapult cannot attack creatures
return false;
//const CGHeroInstance * stackHero = battleGetOwner(stack);
if(stack->hasBonusOfType(Bonus::SHOOTER)//it's shooter
&& stack->owner != dst->owner
&& dst->alive()

View File

@ -213,6 +213,9 @@ public:
TStacks battleAliveStacks(ui8 side) const;
const CStack * battleGetStackByID(int ID, bool onlyAlive = true) const; //returns stack info by given ID
bool battleIsObstacleVisibleForSide(const CObstacleInstance & coi, BattlePerspective::BattlePerspective side) const;
PlayerColor battleGetOwner(const CStack * stack) const; //returns player that controls given stack; mind control included
const CGHeroInstance * battleGetOwnerHero(const CStack * stack) const; //returns hero that controls given stack; nullptr if none; mind control included
};
struct DLL_LINKAGE BattleAttackInfo

View File

@ -875,8 +875,7 @@ void CGameHandler::applyBattleEffects(BattleAttack &bat, const CStack *att, cons
bsa.flags |= BattleStackAttacked::SECONDARY; //all other targets do not suffer from spells & spell-like abilities
bsa.attackerID = att->ID;
bsa.stackAttacked = def->ID;
bsa.damageAmount = gs->curB->calculateDmg(att, def, gs->curB->battleGetOwner(att), gs->curB->battleGetOwner(def),
bat.shot(), distance, bat.lucky(), bat.unlucky(), bat.deathBlow(), bat.ballistaDoubleDmg(), getRandomGenerator());
bsa.damageAmount = gs->curB->calculateDmg(att, def, bat.shot(), distance, bat.lucky(), bat.unlucky(), bat.deathBlow(), bat.ballistaDoubleDmg(), getRandomGenerator());
def->prepareAttacked(bsa, getRandomGenerator()); //calculate casualties
//life drain handling
@ -4537,7 +4536,7 @@ void CGameHandler::stackTurnTrigger(const CStack * st)
}
if (st->hasBonusOfType(Bonus::MANA_DRAIN) && !vstd::contains(st->state, EBattleStackState::DRAINED_MANA))
{
const PlayerColor opponent = gs->curB->theOtherPlayer(st->owner);
const PlayerColor opponent = gs->curB->theOtherPlayer(gs->curB->battleGetOwner(st));
const CGHeroInstance * opponentHero = gs->curB->getHero(opponent);
if (opponentHero)
{
@ -5727,7 +5726,7 @@ void CGameHandler::runBattle()
continue;
}
const CGHeroInstance * curOwner = gs->curB->battleGetOwner(next);
const CGHeroInstance * curOwner = gs->curB->battleGetOwnerHero(next);
if( (next->position < 0 || next->getCreature()->idNumber == CreatureID::BALLISTA) //arrow turret or ballista
&& (!curOwner || curOwner->getSecSkillLevel(SecondarySkill::ARTILLERY) == 0)) //hero has no artillery