ChooseGenericEffectAi: add logic for Fabricate

in most cases it should prefer tokens if able
This commit is contained in:
Hanmac
2016-09-17 07:05:14 +00:00
parent a52ae52b6a
commit 4204334359

View File

@@ -1,10 +1,15 @@
package forge.ai.ability;
import forge.ai.ComputerUtilCard;
import forge.ai.ComputerUtilCost;
import forge.ai.SpellAbilityAi;
import forge.card.MagicColor;
import forge.game.Game;
import forge.game.card.Card;
import forge.game.card.CardCollection;
import forge.game.card.CardUtil;
import forge.game.card.CounterType;
import forge.game.combat.Combat;
import forge.game.cost.Cost;
import forge.game.player.Player;
import forge.game.spellability.SpellAbility;
@@ -43,8 +48,12 @@ public class ChooseGenericEffectAi extends SpellAbilityAi {
@Override
public SpellAbility chooseSingleSpellAbility(Player player, SpellAbility sa, List<SpellAbility> spells) {
Card host = sa.getHostCard();
final Game game = host.getGame();
final Combat combat = game.getCombat();
final String logic = sa.getParam("AILogic");
if ("Random".equals(logic)) {
if (logic == null) {
return spells.get(0);
} else if ("Random".equals(logic)) {
return Aggregates.random(spells);
} else if ("Phasing".equals(logic)) { // Teferi's Realm : keep aggressive
List<SpellAbility> filtered = Lists.newArrayList(Iterables.filter(spells, new Predicate<SpellAbility>() {
@@ -191,6 +200,57 @@ public class ChooseGenericEffectAi extends SpellAbilityAi {
}
// if unsure, random?
return Aggregates.random(spells);
} else if (logic.startsWith("Fabricate")) {
final int n = Integer.valueOf(logic.substring("Fabricate".length()));
SpellAbility counterSA = spells.get(0), tokenSA = spells.get(1);
// check for something which might prevent the counters to be placed on host
if (!host.canReceiveCounters(CounterType.P1P1)) {
return tokenSA;
}
// if host would leave the play or if host is useless, create tokens
if (host.hasSVar("EndOfTurnLeavePlay") || isUselessCreature(player, host)) {
return tokenSA;
}
// need a copy for one with extra +1/+1 counter boost,
// without causing triggers to run
final Card copy = CardUtil.getLKICopy(host);
copy.setCounters(CounterType.P1P1, copy.getCounters(CounterType.P1P1) + n);
copy.setZone(host.getZone());
// if host would put into the battlefield attacking
if (combat != null && combat.isAttacking(host)) {
final Player defender = combat.getDefenderPlayerByAttacker(host);
if (!ComputerUtilCard.canBeBlockedProfitably(defender, copy)) {
return counterSA;
}
return tokenSA;
}
// TODO check for trigger to turn token ETB into +1/+1 counter for host
// TODO check for trigger to turn token ETB into damage or life loss for opponent
// in this cases Token might be prefered even if they would not survive
final Card tokenCard = TokenAi.spawnToken(player, tokenSA, true);
// Token would not survive
if (tokenCard.getNetToughness() < 1) {
return counterSA;
}
// evaluate Creature with +1/+1
int evalCounter = ComputerUtilCard.evaluateCreature(copy);
final CardCollection tokenList = new CardCollection(host);
for (int i = 0; i < n; ++i) {
tokenList.add(TokenAi.spawnToken(player, tokenSA));
}
// evaluate Host with Tokens
int evalToken = ComputerUtilCard.evaluateCreatureList(tokenList);
return evalToken >= evalCounter ? tokenSA : counterSA;
}
return spells.get(0); // return first choice if no logic found
}