diff --git a/forge-ai/src/main/java/forge/ai/AiCostDecision.java b/forge-ai/src/main/java/forge/ai/AiCostDecision.java index 138b3864374..87603e59988 100644 --- a/forge-ai/src/main/java/forge/ai/AiCostDecision.java +++ b/forge-ai/src/main/java/forge/ai/AiCostDecision.java @@ -214,7 +214,7 @@ public class AiCostDecision extends CostDecisionMakerBase { return null; } else { - CardCollectionView chosen = ComputerUtil.chooseExileFrom(player, cost.getFrom(), cost.getType(), source, ability.getTargetCard(), c); + CardCollectionView chosen = ComputerUtil.chooseExileFrom(player, cost.getFrom(), cost.getType(), source, ability.getTargetCard(), c, ability); return null == chosen ? null : PaymentDecision.card(chosen); } } @@ -421,7 +421,7 @@ public class AiCostDecision extends CostDecisionMakerBase { chosen = chosen.subList(0, c); } else { - chosen = ComputerUtil.choosePutToLibraryFrom(player, cost.getFrom(), cost.getType(), source, ability.getTargetCard(), c); + chosen = ComputerUtil.choosePutToLibraryFrom(player, cost.getFrom(), cost.getType(), source, ability.getTargetCard(), c, ability); } return chosen.isEmpty() ? null : PaymentDecision.card(chosen); } @@ -493,7 +493,7 @@ public class AiCostDecision extends CostDecisionMakerBase { type = TextUtil.fastReplace(type, "+withTotalPowerGE", ""); totap = ComputerUtil.chooseTapTypeAccumulatePower(player, type, ability, !cost.canTapSource, Integer.parseInt(totalP), exclude); } else { - totap = ComputerUtil.chooseTapType(player, type, source, !cost.canTapSource, c, exclude); + totap = ComputerUtil.chooseTapType(player, type, source, !cost.canTapSource, c, exclude, ability); } if (totap == null) { @@ -536,7 +536,7 @@ public class AiCostDecision extends CostDecisionMakerBase { c = AbilityUtils.calculateAmount(source, cost.getAmount(), ability); } - CardCollectionView res = ComputerUtil.chooseReturnType(player, cost.getType(), source, ability.getTargetCard(), c); + CardCollectionView res = ComputerUtil.chooseReturnType(player, cost.getType(), source, ability.getTargetCard(), c, ability); return res.isEmpty() ? null : PaymentDecision.card(res); } @@ -854,7 +854,7 @@ public class AiCostDecision extends CostDecisionMakerBase { c = AbilityUtils.calculateAmount(source, amount, ability); } - CardCollectionView list = ComputerUtil.chooseUntapType(player, cost.getType(), source, cost.canUntapSource, c); + CardCollectionView list = ComputerUtil.chooseUntapType(player, cost.getType(), source, cost.canUntapSource, c, ability); if (list == null) { System.out.println("Couldn't find a valid card to untap for: " + source.getName()); diff --git a/forge-ai/src/main/java/forge/ai/ComputerUtil.java b/forge-ai/src/main/java/forge/ai/ComputerUtil.java index 66855252408..309ce371d07 100644 --- a/forge-ai/src/main/java/forge/ai/ComputerUtil.java +++ b/forge-ai/src/main/java/forge/ai/ComputerUtil.java @@ -539,7 +539,7 @@ public class ComputerUtil { public static CardCollection chooseSacrificeType(final Player ai, final String type, final SpellAbility ability, final Card target, final int amount) { final Card source = ability.getHostCard(); - CardCollection typeList = CardLists.getValidCards(ai.getCardsIn(ZoneType.Battlefield), type.split(";"), source.getController(), source, null); + CardCollection typeList = CardLists.getValidCards(ai.getCardsIn(ZoneType.Battlefield), type.split(";"), source.getController(), source, ability); typeList = CardLists.filter(typeList, CardPredicates.canBeSacrificedBy(ability)); @@ -570,8 +570,8 @@ public class ComputerUtil { } public static CardCollection chooseExileFrom(final Player ai, final ZoneType zone, final String type, final Card activate, - final Card target, final int amount) { - CardCollection typeList = CardLists.getValidCards(ai.getCardsIn(zone), type.split(";"), activate.getController(), activate, null); + final Card target, final int amount, SpellAbility sa) { + CardCollection typeList = CardLists.getValidCards(ai.getCardsIn(zone), type.split(";"), activate.getController(), activate, sa); if ((target != null) && target.getController() == ai) { typeList.remove(target); // don't exile the card we're pumping @@ -591,8 +591,8 @@ public class ComputerUtil { } public static CardCollection choosePutToLibraryFrom(final Player ai, final ZoneType zone, final String type, final Card activate, - final Card target, final int amount) { - CardCollection typeList = CardLists.getValidCards(ai.getCardsIn(zone), type.split(";"), activate.getController(), activate, null); + final Card target, final int amount, SpellAbility sa) { + CardCollection typeList = CardLists.getValidCards(ai.getCardsIn(zone), type.split(";"), activate.getController(), activate, sa); if ((target != null) && target.getController() == ai) { typeList.remove(target); // don't move the card we're pumping @@ -615,14 +615,11 @@ public class ComputerUtil { return list; } - public static CardCollection chooseTapType(final Player ai, final String type, final Card activate, final boolean tap, final int amount) { - return chooseTapType(ai, type, activate, tap, amount, CardCollection.EMPTY); - } - public static CardCollection chooseTapType(final Player ai, final String type, final Card activate, final boolean tap, final int amount, final CardCollectionView exclude) { + public static CardCollection chooseTapType(final Player ai, final String type, final Card activate, final boolean tap, final int amount, final CardCollectionView exclude, SpellAbility sa) { CardCollection all = new CardCollection(ai.getCardsIn(ZoneType.Battlefield)); all.removeAll(exclude); CardCollection typeList = - CardLists.getValidCards(all, type.split(";"), activate.getController(), activate, null); + CardLists.getValidCards(all, type.split(";"), activate.getController(), activate, sa); // is this needed? typeList = CardLists.filter(typeList, Presets.UNTAPPED); @@ -695,9 +692,9 @@ public class ComputerUtil { return tapList; } - public static CardCollection chooseUntapType(final Player ai, final String type, final Card activate, final boolean untap, final int amount) { + public static CardCollection chooseUntapType(final Player ai, final String type, final Card activate, final boolean untap, final int amount, SpellAbility sa) { CardCollection typeList = - CardLists.getValidCards(ai.getCardsIn(ZoneType.Battlefield), type.split(";"), activate.getController(), activate, null); + CardLists.getValidCards(ai.getCardsIn(ZoneType.Battlefield), type.split(";"), activate.getController(), activate, sa); // is this needed? typeList = CardLists.filter(typeList, Presets.TAPPED); @@ -720,9 +717,9 @@ public class ComputerUtil { return untapList; } - public static CardCollection chooseReturnType(final Player ai, final String type, final Card activate, final Card target, final int amount) { + public static CardCollection chooseReturnType(final Player ai, final String type, final Card activate, final Card target, final int amount, SpellAbility sa) { final CardCollection typeList = - CardLists.getValidCards(ai.getCardsIn(ZoneType.Battlefield), type.split(";"), activate.getController(), activate, null); + CardLists.getValidCards(ai.getCardsIn(ZoneType.Battlefield), type.split(";"), activate.getController(), activate, sa); if ((target != null) && target.getController() == ai) { // don't bounce the card we're pumping typeList.remove(target); @@ -970,7 +967,7 @@ public class ComputerUtil { } final TargetRestrictions tgt = sa.getTargetRestrictions(); if (tgt != null) { - if (CardLists.getValidCards(game.getCardsIn(ZoneType.Battlefield), tgt.getValidTgts(), controller, sa.getHostCard(), null).contains(card)) { + if (CardLists.getValidCards(game.getCardsIn(ZoneType.Battlefield), tgt.getValidTgts(), controller, sa.getHostCard(), sa).contains(card)) { prevented += AbilityUtils.calculateAmount(sa.getHostCard(), sa.getParam("Amount"), sa); } @@ -1586,9 +1583,8 @@ public class ComputerUtil { if (threatApi == null) { return threatened; } - final TargetRestrictions tgt = topStack.getTargetRestrictions(); - if (tgt == null) { + if (!topStack.usesTargeting()) { if (topStack.hasParam("Defined")) { objects = AbilityUtils.getDefinedObjects(source, topStack.getParam("Defined"), topStack); } else if (topStack.hasParam("ValidCards")) { @@ -1685,7 +1681,7 @@ public class ComputerUtil { if (saviourApi == ApiType.Pump || saviourApi == ApiType.PumpAll) { boolean canSave = ComputerUtilCombat.predictDamageTo(c, dmg - toughness, source, false) < ComputerUtilCombat.getDamageToKill(c); - if ((tgt == null && !grantIndestructible && !canSave) + if ((!topStack.usesTargeting() && !grantIndestructible && !canSave) || (!grantIndestructible && !grantShroud && !canSave)) { continue; } @@ -1745,7 +1741,7 @@ public class ComputerUtil { final boolean cantSave = c.getNetToughness() + toughness <= dmg || (!c.hasKeyword(Keyword.INDESTRUCTIBLE) && c.getShieldCount() == 0 && !grantIndestructible && (dmg >= toughness + ComputerUtilCombat.getDamageToKill(c))); - if (cantSave && (tgt == null || !grantShroud)) { + if (cantSave && (!topStack.usesTargeting() || !grantShroud)) { continue; } } @@ -1758,7 +1754,7 @@ public class ComputerUtil { } if (saviourApi == ApiType.Protection) { - if (tgt == null || (ProtectAi.toProtectFrom(source, saviour) == null)) { + if (!topStack.usesTargeting() || (ProtectAi.toProtectFrom(source, saviour) == null)) { continue; } } @@ -1795,13 +1791,13 @@ public class ComputerUtil { if (saviourApi == ApiType.Pump || saviourApi == ApiType.PumpAll || saviorWithSubsApi == ApiType.Pump || saviorWithSubsApi == ApiType.PumpAll) { - if ((tgt == null && !grantIndestructible) + if ((!topStack.usesTargeting() && !grantIndestructible) || (!grantShroud && !grantIndestructible)) { continue; } } if (saviourApi == ApiType.Protection) { - if (tgt == null || (ProtectAi.toProtectFrom(source, saviour) == null)) { + if (!topStack.usesTargeting() || (ProtectAi.toProtectFrom(source, saviour) == null)) { continue; } } @@ -1830,11 +1826,11 @@ public class ComputerUtil { if (o instanceof Card) { final Card c = (Card) o; // give Shroud to targeted creatures - if ((saviourApi == ApiType.Pump || saviourApi == ApiType.PumpAll) && (tgt == null || !grantShroud)) { + if ((saviourApi == ApiType.Pump || saviourApi == ApiType.PumpAll) && (!topStack.usesTargeting() || !grantShroud)) { continue; } if (saviourApi == ApiType.Protection) { - if (tgt == null || (ProtectAi.toProtectFrom(source, saviour) == null)) { + if (!topStack.usesTargeting() || (ProtectAi.toProtectFrom(source, saviour) == null)) { continue; } } @@ -1858,11 +1854,11 @@ public class ComputerUtil { if (o instanceof Card) { final Card c = (Card) o; // give Shroud to targeted creatures - if ((saviourApi == ApiType.Pump || saviourApi == ApiType.PumpAll && tgt == null) && !grantShroud) { + if ((saviourApi == ApiType.Pump || saviourApi == ApiType.PumpAll && !topStack.usesTargeting()) && !grantShroud) { continue; } if (saviourApi == ApiType.Protection) { - if (tgt == null || (ProtectAi.toProtectFrom(source, saviour) == null)) { + if (!topStack.usesTargeting() || (ProtectAi.toProtectFrom(source, saviour) == null)) { continue; } } @@ -1879,11 +1875,11 @@ public class ComputerUtil { if (o instanceof Card) { final Card c = (Card) o; // give Shroud to targeted creatures - if ((saviourApi == ApiType.Pump || saviourApi == ApiType.PumpAll && tgt == null) && !grantShroud) { + if ((saviourApi == ApiType.Pump || saviourApi == ApiType.PumpAll && !topStack.usesTargeting()) && !grantShroud) { continue; } if (saviourApi == ApiType.Protection) { - if (tgt == null || (ProtectAi.toProtectFrom(source, saviour) == null)) { + if (!topStack.usesTargeting() || (ProtectAi.toProtectFrom(source, saviour) == null)) { continue; } } diff --git a/forge-ai/src/main/java/forge/ai/ComputerUtilCard.java b/forge-ai/src/main/java/forge/ai/ComputerUtilCard.java index 4078d93981c..45be82de490 100644 --- a/forge-ai/src/main/java/forge/ai/ComputerUtilCard.java +++ b/forge-ai/src/main/java/forge/ai/ComputerUtilCard.java @@ -1913,7 +1913,7 @@ public class ComputerUtilCard { CardCollectionView list = game.getCardsIn(ZoneType.Battlefield); - list = CardLists.getValidCards(list, needsToPlay.split(","), card.getController(), card, null); + list = CardLists.getValidCards(list, needsToPlay.split(","), card.getController(), card, sa); if (list.isEmpty()) { return AiPlayDecision.MissingNeededCards; } diff --git a/forge-ai/src/main/java/forge/ai/ComputerUtilCost.java b/forge-ai/src/main/java/forge/ai/ComputerUtilCost.java index cb56ec9fd46..51d282c40a9 100644 --- a/forge-ai/src/main/java/forge/ai/ComputerUtilCost.java +++ b/forge-ai/src/main/java/forge/ai/ComputerUtilCost.java @@ -137,7 +137,7 @@ public class ComputerUtilCost { * the source * @return true, if successful */ - public static boolean checkDiscardCost(final Player ai, final Cost cost, final Card source) { + public static boolean checkDiscardCost(final Player ai, final Cost cost, final Card source, SpellAbility sa) { if (cost == null) { return true; } @@ -152,7 +152,7 @@ public class ComputerUtilCost { if (type.equals("CARDNAME") && source.getAbilityText().contains("Bloodrush")) { continue; } - final CardCollection typeList = CardLists.getValidCards(hand, type.split(","), source.getController(), source, null); + final CardCollection typeList = CardLists.getValidCards(hand, type.split(","), source.getController(), source, sa); if (typeList.size() > ai.getMaxHandSize()) { continue; } @@ -270,7 +270,7 @@ public class ComputerUtilCost { } final CardCollection sacList = new CardCollection(); - final CardCollection typeList = CardLists.getValidCards(ai.getCardsIn(ZoneType.Battlefield), type.split(";"), source.getController(), source, null); + final CardCollection typeList = CardLists.getValidCards(ai.getCardsIn(ZoneType.Battlefield), type.split(";"), source.getController(), source, sourceAbility); int count = 0; while (count < amount) { @@ -320,7 +320,7 @@ public class ComputerUtilCost { } final CardCollection sacList = new CardCollection(); - final CardCollection typeList = CardLists.getValidCards(ai.getCardsIn(ZoneType.Battlefield), type.split(";"), source.getController(), source, null); + final CardCollection typeList = CardLists.getValidCards(ai.getCardsIn(ZoneType.Battlefield), type.split(";"), source.getController(), source, sourceAbility); int count = 0; while (count < amount) { @@ -641,7 +641,7 @@ public class ComputerUtilCost { return checkLifeCost(payer, cost, source, 4, sa) && checkDamageCost(payer, cost, source, 4) && (isMine || checkSacrificeCost(payer, cost, source, sa)) - && (isMine || checkDiscardCost(payer, cost, source)) + && (isMine || checkDiscardCost(payer, cost, source, sa)) && (!source.getName().equals("Tyrannize") || payer.getCardsIn(ZoneType.Hand).size() > 2) && (!source.getName().equals("Perplex") || payer.getCardsIn(ZoneType.Hand).size() < 2) && (!source.getName().equals("Breaking Point") || payer.getCreaturesInPlay().size() > 1) @@ -722,7 +722,7 @@ public class ComputerUtilCost { continue; } - final CardCollection typeList = CardLists.getValidCards(ai.getCardsIn(ZoneType.Battlefield), part.getType().split(";"), source.getController(), source, null); + final CardCollection typeList = CardLists.getValidCards(ai.getCardsIn(ZoneType.Battlefield), part.getType().split(";"), source.getController(), source, sa); int count = 0; while (count < val) { diff --git a/forge-ai/src/main/java/forge/ai/SpellAbilityAi.java b/forge-ai/src/main/java/forge/ai/SpellAbilityAi.java index 841ea538387..bf17cb7df54 100644 --- a/forge-ai/src/main/java/forge/ai/SpellAbilityAi.java +++ b/forge-ai/src/main/java/forge/ai/SpellAbilityAi.java @@ -127,7 +127,7 @@ public abstract class SpellAbilityAi { if (!ComputerUtilCost.checkLifeCost(ai, cost, source, 4, sa)) { return false; } - if (!ComputerUtilCost.checkDiscardCost(ai, cost, source)) { + if (!ComputerUtilCost.checkDiscardCost(ai, cost, source, sa)) { return false; } if (!ComputerUtilCost.checkSacrificeCost(ai, cost, source, sa)) { diff --git a/forge-ai/src/main/java/forge/ai/ability/ChangeZoneAi.java b/forge-ai/src/main/java/forge/ai/ability/ChangeZoneAi.java index 33508f046d9..0a86c7e1018 100644 --- a/forge-ai/src/main/java/forge/ai/ability/ChangeZoneAi.java +++ b/forge-ai/src/main/java/forge/ai/ability/ChangeZoneAi.java @@ -288,7 +288,7 @@ public class ChangeZoneAi extends SpellAbilityAi { return false; } - if (!ComputerUtilCost.checkDiscardCost(ai, abCost, source)) { + if (!ComputerUtilCost.checkDiscardCost(ai, abCost, source, sa)) { for (final CostPart part : abCost.getCostParts()) { if (part instanceof CostDiscard) { CostDiscard cd = (CostDiscard) part; diff --git a/forge-ai/src/main/java/forge/ai/ability/ChangeZoneAllAi.java b/forge-ai/src/main/java/forge/ai/ability/ChangeZoneAllAi.java index 2c3ab5706a1..68b672e49b8 100644 --- a/forge-ai/src/main/java/forge/ai/ability/ChangeZoneAllAi.java +++ b/forge-ai/src/main/java/forge/ai/ability/ChangeZoneAllAi.java @@ -51,7 +51,7 @@ public class ChangeZoneAllAi extends SpellAbilityAi { return false; } - if (!ComputerUtilCost.checkDiscardCost(ai, abCost, source)) { + if (!ComputerUtilCost.checkDiscardCost(ai, abCost, source, sa)) { boolean aiLogicAllowsDiscard = sa.hasParam("AILogic") && sa.getParam("AILogic").startsWith("DiscardAll"); if (!aiLogicAllowsDiscard) { diff --git a/forge-ai/src/main/java/forge/ai/ability/ChooseSourceAi.java b/forge-ai/src/main/java/forge/ai/ability/ChooseSourceAi.java index 8d2bf970e0e..519863776c9 100644 --- a/forge-ai/src/main/java/forge/ai/ability/ChooseSourceAi.java +++ b/forge-ai/src/main/java/forge/ai/ability/ChooseSourceAi.java @@ -10,7 +10,6 @@ import com.google.common.collect.Lists; import forge.ai.ComputerUtilCard; import forge.ai.ComputerUtilCombat; -import forge.ai.ComputerUtilCost; import forge.ai.SpellAbilityAi; import forge.game.Game; import forge.game.GameObject; @@ -47,20 +46,7 @@ public class ChooseSourceAi extends SpellAbilityAi { final Card source = sa.getHostCard(); if (abCost != null) { - // AI currently disabled for these costs - if (!ComputerUtilCost.checkLifeCost(ai, abCost, source, 4, sa)) { - return false; - } - - if (!ComputerUtilCost.checkDiscardCost(ai, abCost, source)) { - return false; - } - - if (!ComputerUtilCost.checkSacrificeCost(ai, abCost, source, sa)) { - return false; - } - - if (!ComputerUtilCost.checkRemoveCounterCost(abCost, source, sa)) { + if (!willPayCosts(ai, sa, abCost, source)) { return false; } } diff --git a/forge-ai/src/main/java/forge/ai/ability/CountersPutAllAi.java b/forge-ai/src/main/java/forge/ai/ability/CountersPutAllAi.java index ace8c07c457..6e776717a8a 100644 --- a/forge-ai/src/main/java/forge/ai/ability/CountersPutAllAi.java +++ b/forge-ai/src/main/java/forge/ai/ability/CountersPutAllAi.java @@ -52,7 +52,7 @@ public class CountersPutAllAi extends SpellAbilityAi { return false; } - if (!ComputerUtilCost.checkDiscardCost(ai, abCost, source)) { + if (!ComputerUtilCost.checkDiscardCost(ai, abCost, source, sa)) { return false; } diff --git a/forge-ai/src/main/java/forge/ai/ability/DamageDealAi.java b/forge-ai/src/main/java/forge/ai/ability/DamageDealAi.java index 220e06c0876..f1d44f504bd 100644 --- a/forge-ai/src/main/java/forge/ai/ability/DamageDealAi.java +++ b/forge-ai/src/main/java/forge/ai/ability/DamageDealAi.java @@ -245,7 +245,7 @@ public class DamageDealAi extends DamageAiBase { return false; } - if ("DiscardLands".equals(sa.getParam("AILogic")) && !ComputerUtilCost.checkDiscardCost(ai, abCost, source)) { + if ("DiscardLands".equals(sa.getParam("AILogic")) && !ComputerUtilCost.checkDiscardCost(ai, abCost, source, sa)) { return false; } diff --git a/forge-ai/src/main/java/forge/ai/ability/DamagePreventAi.java b/forge-ai/src/main/java/forge/ai/ability/DamagePreventAi.java index 447a187df2d..4936049e622 100644 --- a/forge-ai/src/main/java/forge/ai/ability/DamagePreventAi.java +++ b/forge-ai/src/main/java/forge/ai/ability/DamagePreventAi.java @@ -6,7 +6,6 @@ import java.util.List; import forge.ai.ComputerUtil; import forge.ai.ComputerUtilCard; import forge.ai.ComputerUtilCombat; -import forge.ai.ComputerUtilCost; import forge.ai.SpellAbilityAi; import forge.game.Game; import forge.game.GameObject; @@ -37,20 +36,7 @@ public class DamagePreventAi extends SpellAbilityAi { final Cost cost = sa.getPayCosts(); - // temporarily disabled until better AI - if (!ComputerUtilCost.checkLifeCost(ai, cost, hostCard, 4, sa)) { - return false; - } - - if (!ComputerUtilCost.checkDiscardCost(ai, cost, hostCard)) { - return false; - } - - if (!ComputerUtilCost.checkSacrificeCost(ai, cost, hostCard, sa)) { - return false; - } - - if (!ComputerUtilCost.checkRemoveCounterCost(cost, hostCard, sa)) { + if (!willPayCosts(ai, sa, cost, hostCard)) { return false; } diff --git a/forge-ai/src/main/java/forge/ai/ability/DamagePreventAllAi.java b/forge-ai/src/main/java/forge/ai/ability/DamagePreventAllAi.java index f62a7b51c25..1124a72e9be 100644 --- a/forge-ai/src/main/java/forge/ai/ability/DamagePreventAllAi.java +++ b/forge-ai/src/main/java/forge/ai/ability/DamagePreventAllAi.java @@ -1,7 +1,5 @@ package forge.ai.ability; - -import forge.ai.ComputerUtilCost; import forge.ai.SpellAbilityAi; import forge.game.card.Card; import forge.game.cost.Cost; @@ -22,19 +20,7 @@ public class DamagePreventAllAi extends SpellAbilityAi { final Cost cost = sa.getPayCosts(); // temporarily disabled until better AI - if (!ComputerUtilCost.checkLifeCost(ai, cost, hostCard, 4, sa)) { - return false; - } - - if (!ComputerUtilCost.checkDiscardCost(ai, cost, hostCard)) { - return false; - } - - if (!ComputerUtilCost.checkSacrificeCost(ai, cost, hostCard, sa)) { - return false; - } - - if (!ComputerUtilCost.checkRemoveCounterCost(cost, hostCard, sa)) { + if (!willPayCosts(ai, sa, cost, hostCard)) { return false; } diff --git a/forge-ai/src/main/java/forge/ai/ability/DiscardAi.java b/forge-ai/src/main/java/forge/ai/ability/DiscardAi.java index 102089f06e6..dd1e0fc35d6 100644 --- a/forge-ai/src/main/java/forge/ai/ability/DiscardAi.java +++ b/forge-ai/src/main/java/forge/ai/ability/DiscardAi.java @@ -32,26 +32,11 @@ public class DiscardAi extends SpellAbilityAi { final Cost abCost = sa.getPayCosts(); final String aiLogic = sa.getParamOrDefault("AILogic", ""); - if (abCost != null) { - // AI currently disabled for these costs - if (!ComputerUtilCost.checkSacrificeCost(ai, abCost, source, sa)) { - return false; - } - - if (!ComputerUtilCost.checkLifeCost(ai, abCost, source, 4, sa)) { - return false; - } - - if (!ComputerUtilCost.checkDiscardCost(ai, abCost, source)) { - return false; - } - - if (!ComputerUtilCost.checkRemoveCounterCost(abCost, source, sa)) { - return false; - } - + // temporarily disabled until better AI + if (!willPayCosts(ai, sa, abCost, source)) { + return false; } - + if ("Chandra, Flamecaller".equals(sourceName)) { final int hand = ai.getCardsIn(ZoneType.Hand).size(); return MyRandom.getRandom().nextFloat() < (1.0 / (1 + hand)); diff --git a/forge-ai/src/main/java/forge/ai/ability/DrawAi.java b/forge-ai/src/main/java/forge/ai/ability/DrawAi.java index 3f664109774..aa9a78c9398 100644 --- a/forge-ai/src/main/java/forge/ai/ability/DrawAi.java +++ b/forge-ai/src/main/java/forge/ai/ability/DrawAi.java @@ -100,7 +100,7 @@ public class DrawAi extends SpellAbilityAi { return false; } - if (!ComputerUtilCost.checkDiscardCost(ai, cost, source)) { + if (!ComputerUtilCost.checkDiscardCost(ai, cost, source,sa)) { AiCostDecision aiDecisions = new AiCostDecision(ai, sa); for (final CostPart part : cost.getCostParts()) { if (part instanceof CostDiscard) { diff --git a/forge-ai/src/main/java/forge/ai/ability/LifeGainAi.java b/forge-ai/src/main/java/forge/ai/ability/LifeGainAi.java index daf8d04d7bc..f00d8b18d31 100644 --- a/forge-ai/src/main/java/forge/ai/ability/LifeGainAi.java +++ b/forge-ai/src/main/java/forge/ai/ability/LifeGainAi.java @@ -43,14 +43,14 @@ public class LifeGainAi extends SpellAbilityAi { if (!lifeCritical) { // return super.willPayCosts(ai, sa, cost, source); - if (!ComputerUtilCost.checkSacrificeCost(ai, cost, source, sa,false)) { + if (!ComputerUtilCost.checkSacrificeCost(ai, cost, source, sa, false)) { return false; } if (!ComputerUtilCost.checkLifeCost(ai, cost, source, 4, sa)) { return false; } - if (!ComputerUtilCost.checkDiscardCost(ai, cost, source)) { + if (!ComputerUtilCost.checkDiscardCost(ai, cost, source, sa)) { return false; } diff --git a/forge-ai/src/main/java/forge/ai/ability/ProtectAllAi.java b/forge-ai/src/main/java/forge/ai/ability/ProtectAllAi.java index 8e60b3d397c..5a3db7be5fa 100644 --- a/forge-ai/src/main/java/forge/ai/ability/ProtectAllAi.java +++ b/forge-ai/src/main/java/forge/ai/ability/ProtectAllAi.java @@ -1,7 +1,5 @@ package forge.ai.ability; - -import forge.ai.ComputerUtilCost; import forge.ai.SpellAbilityAi; import forge.game.card.Card; import forge.game.cost.Cost; @@ -21,19 +19,7 @@ public class ProtectAllAi extends SpellAbilityAi { final Cost cost = sa.getPayCosts(); // temporarily disabled until better AI - if (!ComputerUtilCost.checkLifeCost(ai, cost, hostCard, 4, sa)) { - return false; - } - - if (!ComputerUtilCost.checkDiscardCost(ai, cost, hostCard)) { - return false; - } - - if (!ComputerUtilCost.checkSacrificeCost(ai, cost, hostCard, sa)) { - return false; - } - - if (!ComputerUtilCost.checkRemoveCounterCost(cost, hostCard, sa)) { + if (!willPayCosts(ai, sa, cost, hostCard)) { return false; } diff --git a/forge-ai/src/main/java/forge/ai/ability/TapAi.java b/forge-ai/src/main/java/forge/ai/ability/TapAi.java index 0224fb3d910..cb6428ee193 100644 --- a/forge-ai/src/main/java/forge/ai/ability/TapAi.java +++ b/forge-ai/src/main/java/forge/ai/ability/TapAi.java @@ -48,10 +48,9 @@ public class TapAi extends TapAiBase { final Card source = sa.getHostCard(); final Cost abCost = sa.getPayCosts(); - if (abCost != null) { - if (!ComputerUtilCost.checkDiscardCost(ai, abCost, source)) { - return false; - } + + if (!ComputerUtilCost.checkDiscardCost(ai, abCost, source, sa)) { + return false; } if (!sa.usesTargeting()) { diff --git a/forge-ai/src/main/java/forge/ai/ability/UntapAi.java b/forge-ai/src/main/java/forge/ai/ability/UntapAi.java index fe3480cec7a..00c4837c82b 100644 --- a/forge-ai/src/main/java/forge/ai/ability/UntapAi.java +++ b/forge-ai/src/main/java/forge/ai/ability/UntapAi.java @@ -52,7 +52,7 @@ public class UntapAi extends SpellAbilityAi { return false; } - return ComputerUtilCost.checkDiscardCost(ai, cost, sa.getHostCard()); + return ComputerUtilCost.checkDiscardCost(ai, cost, sa.getHostCard(), sa); } @Override diff --git a/forge-game/src/main/java/forge/game/ability/AbilityUtils.java b/forge-game/src/main/java/forge/game/ability/AbilityUtils.java index 31e85809eb7..8831f22a348 100644 --- a/forge-game/src/main/java/forge/game/ability/AbilityUtils.java +++ b/forge-game/src/main/java/forge/game/ability/AbilityUtils.java @@ -1606,7 +1606,7 @@ public class AbilityUtils { final String s2 = AbilityUtils.applyAbilityTextChangeEffects(s, ctb); final String[] l = s2.split("/"); final String expr = CardFactoryUtil.extractOperators(s2); - final Player player = ctb instanceof SpellAbility ? ((SpellAbility)ctb).getActivatingPlayer() : ctb.getHostCard().getController(); + final Player player = ctb == null ? null : ctb instanceof SpellAbility ? ((SpellAbility)ctb).getActivatingPlayer() : ctb.getHostCard().getController(); final String[] sq; sq = l[0].split("\\.");