1
0
mirror of https://github.com/vcmi/vcmi.git synced 2026-05-22 09:55:17 +02:00

BattleAI: avoid standing in moat

This commit is contained in:
Andrii Danylchenko
2024-09-02 14:24:22 +03:00
parent ee64928454
commit f9442208da
5 changed files with 126 additions and 9 deletions
+28 -3
View File
@@ -226,11 +226,36 @@ BattleAction BattleEvaluator::selectStackAction(const CStack * stack)
{
return BattleAction::makeDefend(stack);
}
else
auto enemyMellee = hb->getUnitsIf([this](const battle::Unit * u) -> bool
{
return u->unitSide() == BattleSide::ATTACKER && !hb->battleCanShoot(u);
});
bool isTargetOutsideFort = bestAttack.dest.getY() < GameConstants::BFIELD_WIDTH - 4;
bool siegeDefense = stack->unitSide() == BattleSide::DEFENDER
&& !bestAttack.attack.shooting
&& hb->battleGetFortifications().hasMoat
&& !enemyMellee.empty()
&& isTargetOutsideFort;
if(siegeDefense)
{
activeActionMade = true;
return BattleAction::makeMeleeAttack(stack, bestAttack.attack.defenderPos, bestAttack.from);
logAi->trace("Evaluating exchange at %d self-defense", stack->getPosition().hex);
BattleAttackInfo bai(stack, stack, 0, false);
AttackPossibility apDefend(stack->getPosition(), stack->getPosition(), bai);
float defenseValue = scoreEvaluator.evaluateExchange(apDefend, 0, *targets, damageCache, hb);
if((defenseValue > score && score <= 0) || (defenseValue > 2 * score && score > 0))
{
return BattleAction::makeDefend(stack);
}
}
activeActionMade = true;
return BattleAction::makeMeleeAttack(stack, bestAttack.attack.defenderPos, bestAttack.from);
}
}
}