AI logic for Veil of Summer (#4149)

* - AI logic for Veil of Summer.

* - Simplify implementation.
This commit is contained in:
Agetian
2023-11-13 19:56:15 +03:00
committed by GitHub
parent 2d71f3415d
commit daff36b64e
3 changed files with 47 additions and 14 deletions

View File

@@ -1683,6 +1683,41 @@ public class SpecialCardAi {
}
}
// Veil of Summer
public static class VeilOfSummer {
public static boolean consider(final Player ai, final SpellAbility sa) {
// check the top ability on stack if it's (a) an opponent's counterspell targeting the AI's spell;
// (b) a black or a blue spell targeting something that belongs to the AI
Game game = ai.getGame();
if (game.getStack().isEmpty()) {
return false;
}
SpellAbility topSA = game.getStack().peekAbility();
if (topSA.usesTargeting() && topSA.getActivatingPlayer().isOpponentOf(ai)) {
if (topSA.getApi() == ApiType.Counter) {
SpellAbility tgtSpell = topSA.getTargets().getFirstTargetedSpell();
if (tgtSpell != null && tgtSpell.getActivatingPlayer().equals(ai)) {
return true;
}
} else if (topSA.getHostCard().isBlack() || topSA.getHostCard().isBlue()) {
for (Player tgtP : topSA.getTargets().getTargetPlayers()) {
if (tgtP.equals(ai)) {
return true;
}
}
for (Card tgtC : topSA.getTargets().getTargetCards()) {
if (tgtC.getController().equals(ai)) {
return true;
}
}
}
}
return false;
}
}
// Volrath's Shapeshifter
public static class VolrathsShapeshifter {
public static boolean consider(final Player ai, final SpellAbility sa) {

View File

@@ -132,18 +132,6 @@ public class DrawAi extends SpellAbilityAi {
*/
@Override
protected boolean checkPhaseRestrictions(Player ai, SpellAbility sa, PhaseHandler ph) {
String logic = sa.getParamOrDefault("AILogic", "");
if (logic.startsWith("LifeLessThan.")) {
// LifeLessThan logic presupposes activation as soon as possible in an
// attempt to save the AI from dying
return true;
} else if (logic.equals("AtOppEOT")) {
return ph.is(PhaseType.END_OF_TURN) && ph.getNextTurn().equals(ai);
} else if (logic.equals("RespondToOwnActivation")) {
return !ai.getGame().getStack().isEmpty() && ai.getGame().getStack().peekAbility().getHostCard().equals(sa.getHostCard());
}
// Sacrificing a creature in response to something dangerous is generally good in any phase
boolean isSacCost = false;
if (sa.getPayCosts() != null && sa.getPayCosts().hasSpecificCostType(CostSacrifice.class)) {
@@ -169,7 +157,17 @@ public class DrawAi extends SpellAbilityAi {
*/
@Override
protected boolean checkPhaseRestrictions(Player ai, SpellAbility sa, PhaseHandler ph, String logic) {
if ((!ph.getNextTurn().equals(ai) || ph.getPhase().isBefore(PhaseType.END_OF_TURN))
if (logic.equals("VeilOfSummer")) {
return SpecialCardAi.VeilOfSummer.consider(ai, sa); // this is more of a counterspell than a true draw card, so it's timed by the card-specific logic
} else if (logic.startsWith("LifeLessThan.")) {
// LifeLessThan logic presupposes activation as soon as possible in an
// attempt to save the AI from dying
return true;
} else if (logic.equals("AtOppEOT")) {
return ph.is(PhaseType.END_OF_TURN) && ph.getNextTurn().equals(ai);
} else if (logic.equals("RespondToOwnActivation")) {
return !ai.getGame().getStack().isEmpty() && ai.getGame().getStack().peekAbility().getHostCard().equals(sa.getHostCard());
} else if ((!ph.getNextTurn().equals(ai) || ph.getPhase().isBefore(PhaseType.END_OF_TURN))
&& !sa.hasParam("PlayerTurn") && !isSorcerySpeed(sa, ai)
&& ai.getCardsIn(ZoneType.Hand).size() > 1 && !ComputerUtil.activateForCost(sa, ai)
&& !"YawgmothsBargain".equals(logic)) {