mirror of
https://github.com/vcmi/vcmi.git
synced 2025-07-17 01:32:21 +02:00
fix problems
This commit is contained in:
@ -406,14 +406,20 @@ void BattleSpellMechanics::beforeCast(BattleSpellCast & sc, vstd::RNG & rng, con
|
||||
affectedUnits.push_back(unit);
|
||||
};
|
||||
|
||||
if (!target.empty())
|
||||
{
|
||||
const battle::Unit * targetedUnit = battle()->battleGetUnitByPos(target.front().hexValue, true);
|
||||
if (isReflected(targetedUnit, rng)) {
|
||||
reflect(sc, rng, targetedUnit);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
//prepare targets
|
||||
effectsToApply = effects->prepare(this, target, spellTarget);
|
||||
|
||||
std::set<const battle::Unit *> unitTargets = collectTargets();
|
||||
|
||||
if (unitTargets.size()==1 && isReflected(*(unitTargets.begin()), rng))
|
||||
return reflect(sc, rng, *(unitTargets.begin()));
|
||||
|
||||
//process them
|
||||
for(const auto * unit : unitTargets)
|
||||
filterUnit(unit);
|
||||
@ -435,13 +441,10 @@ void BattleSpellMechanics::beforeCast(BattleSpellCast & sc, vstd::RNG & rng, con
|
||||
|
||||
bool BattleSpellMechanics::isReflected(const battle::Unit * unit, vstd::RNG & rng)
|
||||
{
|
||||
auto range = owner -> getLevelInfo(getRangeLevel()).range;
|
||||
const std::vector<int> directSpellRange = { 0 };
|
||||
const std::string magicMirrorCacheStr = "type_MAGIC_MIRROR";
|
||||
static const auto magicMirrorSelector = Selector::type()(BonusType::MAGIC_MIRROR);
|
||||
|
||||
bool spellIsDirect = !isMassive() && owner -> getLevelInfo(getRangeLevel()).range == directSpellRange;
|
||||
bool spellIsReflectable = spellIsDirect && (mode == Mode::HERO || mode == Mode::MAGIC_MIRROR) && isNegativeSpell();
|
||||
if (unit == nullptr)
|
||||
return false;
|
||||
bool isDirectSpell = owner->getTargetType() == AimType::CREATURE && !isMassive();
|
||||
bool spellIsReflectable = isDirectSpell && (mode == Mode::HERO || mode == Mode::MAGIC_MIRROR) && isNegativeSpell();
|
||||
bool targetCanReflectSpell = spellIsReflectable && unit->getAllBonuses(Selector::type()(BonusType::MAGIC_MIRROR))->size()>0;
|
||||
return targetCanReflectSpell && rng.nextInt(0, 99) < unit->valOfBonuses(BonusType::MAGIC_MIRROR);
|
||||
}
|
||||
@ -450,6 +453,8 @@ void BattleSpellMechanics::reflect(BattleSpellCast & sc, vstd::RNG & rng, const
|
||||
{
|
||||
auto otherSide = battle()->otherSide(unit->unitSide());
|
||||
auto newTarget = getRandomUnit(rng, otherSide);
|
||||
if (newTarget == nullptr)
|
||||
throw std::runtime_error("Failed to find random unit to reflect spell!");
|
||||
auto reflectedTo = newTarget->getPosition();
|
||||
|
||||
mode = Mode::MAGIC_MIRROR;
|
||||
@ -459,7 +464,7 @@ void BattleSpellMechanics::reflect(BattleSpellCast & sc, vstd::RNG & rng, const
|
||||
if (!isReceptive(newTarget))
|
||||
sc.resistedCres.insert(newTarget->unitId()); //A spell can be reflected to then resisted by an immune unit. Consistent with the original game.
|
||||
|
||||
beforeCast(sc, rng, { reflectedTo });
|
||||
beforeCast(sc, rng, { Destination(reflectedTo) });
|
||||
}
|
||||
|
||||
const battle::Unit * BattleSpellMechanics::getRandomUnit(vstd::RNG & rng, const BattleSide & side)
|
||||
|
@ -78,7 +78,7 @@ private:
|
||||
void beforeCast(BattleSpellCast & sc, vstd::RNG & rng, const Target & target);
|
||||
bool isReflected(const battle::Unit * unit, vstd::RNG & rng);
|
||||
void reflect(BattleSpellCast & sc, vstd::RNG & rng, const battle::Unit * unit);
|
||||
const battle::Unit * getRandomUnit(vstd::RNG & rng, BattleSide & side);
|
||||
const battle::Unit * getRandomUnit(vstd::RNG & rng, const BattleSide & side);
|
||||
|
||||
std::set<const battle::Unit *> collectTargets() const;
|
||||
|
||||
|
Reference in New Issue
Block a user