mirror of
https://github.com/Card-Forge/forge.git
synced 2025-11-20 12:48:00 +00:00
Clean up (#2025)
This commit is contained in:
@@ -2961,7 +2961,7 @@ public class ComputerUtil {
|
||||
return false;
|
||||
}
|
||||
|
||||
public static boolean targetPlayableSpellCard(final Player ai, CardCollection options, final SpellAbility sa, final boolean withoutPayingManaCost, boolean mandatory) {
|
||||
public static boolean targetPlayableSpellCard(final Player ai, Iterable<Card> options, final SpellAbility sa, final boolean withoutPayingManaCost, boolean mandatory) {
|
||||
// determine and target a card with a SA that the AI can afford and will play
|
||||
AiController aic = ((PlayerControllerAi) ai.getController()).getAi();
|
||||
sa.resetTargets();
|
||||
@@ -2993,8 +2993,8 @@ public class ComputerUtil {
|
||||
}
|
||||
|
||||
if (targets.isEmpty()) {
|
||||
if (mandatory && !options.isEmpty()) {
|
||||
targets = options;
|
||||
if (mandatory && !Iterables.isEmpty(options)) {
|
||||
targets.addAll(options);
|
||||
} else {
|
||||
return false;
|
||||
}
|
||||
|
||||
@@ -131,7 +131,7 @@ public class CopyPermanentAi extends SpellAbilityAi {
|
||||
if (sa.usesTargeting()) {
|
||||
sa.resetTargets();
|
||||
|
||||
CardCollection list = new CardCollection(CardUtil.getValidCardsToTarget(sa.getTargetRestrictions(), sa));
|
||||
List<Card> list = CardUtil.getValidCardsToTarget(sa.getTargetRestrictions(), sa);
|
||||
|
||||
//Nothing to target
|
||||
if (list.isEmpty()) {
|
||||
|
||||
@@ -68,7 +68,6 @@ public class DebuffAi extends SpellAbilityAi {
|
||||
if (!sa.usesTargeting()) {
|
||||
List<Card> cards = AbilityUtils.getDefinedCards(source, sa.getParam("Defined"), sa);
|
||||
|
||||
|
||||
final Combat combat = game.getCombat();
|
||||
return Iterables.any(cards, new Predicate<Card>() {
|
||||
@Override
|
||||
@@ -121,7 +120,6 @@ public class DebuffAi extends SpellAbilityAi {
|
||||
final TargetRestrictions tgt = sa.getTargetRestrictions();
|
||||
sa.resetTargets();
|
||||
CardCollection list = getCurseCreatures(ai, sa, kws == null ? Lists.newArrayList() : kws);
|
||||
list = CardLists.getValidCards(list, tgt.getValidTgts(), sa.getActivatingPlayer(), sa.getHostCard(), sa);
|
||||
|
||||
// several uses here:
|
||||
// 1. make human creatures lose evasion when they are attacking
|
||||
@@ -205,9 +203,7 @@ public class DebuffAi extends SpellAbilityAi {
|
||||
}
|
||||
|
||||
// Remove anything that's already been targeted
|
||||
for (final Card c : sa.getTargets().getTargetCards()) {
|
||||
list.remove(c);
|
||||
}
|
||||
list.removeAll(sa.getTargets().getTargetCards());
|
||||
|
||||
final CardCollection pref = CardLists.filterControlledBy(list, ai.getOpponents());
|
||||
final CardCollection forced = CardLists.filterControlledBy(list, ai);
|
||||
|
||||
@@ -40,7 +40,7 @@ public class PlayAi extends SpellAbilityAi {
|
||||
return false; // prevent infinite loop
|
||||
}
|
||||
|
||||
CardCollection cards = getPlayableCards(sa, ai);
|
||||
List<Card> cards = getPlayableCards(sa, ai);
|
||||
if (cards.isEmpty()) {
|
||||
return false;
|
||||
}
|
||||
@@ -188,14 +188,14 @@ public class PlayAi extends SpellAbilityAi {
|
||||
});
|
||||
return ComputerUtilCard.getBestAI(tgtCards);
|
||||
}
|
||||
|
||||
private static CardCollection getPlayableCards(SpellAbility sa, Player ai) {
|
||||
CardCollection cards = new CardCollection();
|
||||
|
||||
private static List<Card> getPlayableCards(SpellAbility sa, Player ai) {
|
||||
List<Card> cards = null;
|
||||
final TargetRestrictions tgt = sa.getTargetRestrictions();
|
||||
final Card source = sa.getHostCard();
|
||||
|
||||
if (tgt != null) {
|
||||
cards = CardLists.getValidCards(ai.getGame().getCardsIn(tgt.getZone()), tgt.getValidTgts(), ai, source, sa);
|
||||
cards = CardUtil.getValidCardsToTarget(tgt, sa);
|
||||
} else if (!sa.hasParam("Valid")) {
|
||||
cards = AbilityUtils.getDefinedCards(source, sa.getParam("Defined"), sa);
|
||||
}
|
||||
|
||||
@@ -518,7 +518,7 @@ public class PumpAi extends PumpAiBase {
|
||||
}
|
||||
}
|
||||
|
||||
list = CardLists.getValidCards(list, tgt.getValidTgts(), ai, source, sa);
|
||||
list = CardLists.getTargetableCards(list, sa);
|
||||
if (game.getStack().isEmpty()) {
|
||||
// If the cost is tapping, don't activate before declare attack/block
|
||||
if (sa.getPayCosts().hasTapCost()) {
|
||||
|
||||
@@ -2918,8 +2918,7 @@ public class AbilityUtils {
|
||||
sas.add(s);
|
||||
}
|
||||
} else {
|
||||
final Spell newSA = (Spell) s.copy();
|
||||
newSA.setActivatingPlayer(controller);
|
||||
final Spell newSA = (Spell) s.copy(controller);
|
||||
SpellAbilityRestriction res = new SpellAbilityRestriction();
|
||||
// timing restrictions still apply
|
||||
res.setPlayerTurn(s.getRestrictions().getPlayerTurn());
|
||||
|
||||
@@ -237,10 +237,7 @@ public class CharmEffect extends SpellAbilityEffect {
|
||||
|
||||
for (AbilitySub sub : chosen) {
|
||||
// Clone the chosen, just in case the same subAb gets chosen multiple times
|
||||
AbilitySub clone = (AbilitySub)sub.copy();
|
||||
|
||||
// update ActivatingPlayer
|
||||
clone.setActivatingPlayer(sa.getActivatingPlayer());
|
||||
AbilitySub clone = (AbilitySub)sub.copy(sa.getActivatingPlayer());
|
||||
|
||||
// make StackDescription be the SpellDescription if it doesn't already have one
|
||||
if (!clone.hasParam("StackDescription")) {
|
||||
|
||||
@@ -20,6 +20,7 @@ import forge.game.card.CardLists;
|
||||
import forge.game.player.Player;
|
||||
import forge.game.spellability.SpellAbility;
|
||||
import forge.util.Aggregates;
|
||||
import forge.util.Lang;
|
||||
import forge.util.Localizer;
|
||||
|
||||
public class ChooseCardNameEffect extends SpellAbilityEffect {
|
||||
@@ -28,9 +29,7 @@ public class ChooseCardNameEffect extends SpellAbilityEffect {
|
||||
protected String getStackDescription(SpellAbility sa) {
|
||||
final StringBuilder sb = new StringBuilder();
|
||||
|
||||
for (final Player p : getTargetPlayers(sa)) {
|
||||
sb.append(p).append(" ");
|
||||
}
|
||||
sb.append(Lang.joinHomogenous(getTargetPlayers(sa)));
|
||||
sb.append("names a card.");
|
||||
|
||||
return sb.toString();
|
||||
|
||||
@@ -21,9 +21,8 @@ public class ChooseColorEffect extends SpellAbilityEffect {
|
||||
protected String getStackDescription(SpellAbility sa) {
|
||||
final StringBuilder sb = new StringBuilder();
|
||||
|
||||
for (final Player p : getTargetPlayers(sa)) {
|
||||
sb.append(p).append(" ");
|
||||
}
|
||||
sb.append(Lang.joinHomogenous(getTargetPlayers(sa)));
|
||||
|
||||
sb.append("chooses a color");
|
||||
if (sa.hasParam("OrColors")) {
|
||||
sb.append(" or colors");
|
||||
|
||||
@@ -6,6 +6,7 @@ import forge.game.card.Card;
|
||||
import forge.game.player.Player;
|
||||
import forge.game.player.PlayerController.BinaryChoiceType;
|
||||
import forge.game.spellability.SpellAbility;
|
||||
import forge.util.Lang;
|
||||
import forge.util.Localizer;
|
||||
|
||||
public class ChooseEvenOddEffect extends SpellAbilityEffect {
|
||||
@@ -17,9 +18,7 @@ public class ChooseEvenOddEffect extends SpellAbilityEffect {
|
||||
protected String getStackDescription(SpellAbility sa) {
|
||||
final StringBuilder sb = new StringBuilder();
|
||||
|
||||
for (final Player p : getTargetPlayers(sa)) {
|
||||
sb.append(p).append(" ");
|
||||
}
|
||||
sb.append(Lang.joinHomogenous(getTargetPlayers(sa)));
|
||||
sb.append("chooses even or odd.");
|
||||
|
||||
return sb.toString();
|
||||
|
||||
@@ -13,6 +13,7 @@ import forge.game.event.GameEventCardModeChosen;
|
||||
import forge.game.player.Player;
|
||||
import forge.game.spellability.SpellAbility;
|
||||
import forge.util.Aggregates;
|
||||
import forge.util.Lang;
|
||||
|
||||
public class ChooseGenericEffect extends SpellAbilityEffect {
|
||||
|
||||
@@ -20,9 +21,7 @@ public class ChooseGenericEffect extends SpellAbilityEffect {
|
||||
protected String getStackDescription(SpellAbility sa) {
|
||||
final StringBuilder sb = new StringBuilder();
|
||||
|
||||
for (final Player p : getTargetPlayers(sa)) {
|
||||
sb.append(p).append(" ");
|
||||
}
|
||||
sb.append(Lang.joinHomogenous(getDefinedPlayersOrTargeted(sa)));
|
||||
sb.append("chooses from a list.");
|
||||
|
||||
return sb.toString();
|
||||
|
||||
@@ -12,6 +12,7 @@ import forge.game.ability.SpellAbilityEffect;
|
||||
import forge.game.card.Card;
|
||||
import forge.game.player.Player;
|
||||
import forge.game.spellability.SpellAbility;
|
||||
import forge.util.Lang;
|
||||
import forge.util.Localizer;
|
||||
import forge.util.MyRandom;
|
||||
|
||||
@@ -24,9 +25,8 @@ public class ChooseNumberEffect extends SpellAbilityEffect {
|
||||
protected String getStackDescription(SpellAbility sa) {
|
||||
final StringBuilder sb = new StringBuilder();
|
||||
|
||||
for (final Player p : getTargetPlayers(sa)) {
|
||||
sb.append(p).append(" ");
|
||||
}
|
||||
sb.append(Lang.joinHomogenous(getTargetPlayers(sa)));
|
||||
|
||||
sb.append("chooses a number.");
|
||||
|
||||
return sb.toString();
|
||||
|
||||
@@ -18,6 +18,7 @@ import forge.game.player.Player;
|
||||
import forge.game.spellability.SpellAbility;
|
||||
import forge.game.zone.ZoneType;
|
||||
import forge.util.Aggregates;
|
||||
import forge.util.Lang;
|
||||
import forge.util.Localizer;
|
||||
|
||||
public class MultiplePilesEffect extends SpellAbilityEffect {
|
||||
@@ -29,15 +30,13 @@ public class MultiplePilesEffect extends SpellAbilityEffect {
|
||||
protected String getStackDescription(SpellAbility sa) {
|
||||
final StringBuilder sb = new StringBuilder();
|
||||
|
||||
final List<Player> tgtPlayers = getTargetPlayers(sa);
|
||||
String piles = sa.getParam("Piles");
|
||||
final String valid = sa.getParamOrDefault("ValidCards", "");
|
||||
|
||||
sb.append("Separate all ").append(valid).append(" cards ");
|
||||
|
||||
for (final Player p : tgtPlayers) {
|
||||
sb.append(p).append(" ");
|
||||
}
|
||||
sb.append(Lang.joinHomogenous(getTargetPlayers(sa)));
|
||||
|
||||
sb.append("controls into ").append(piles).append(" piles.");
|
||||
return sb.toString();
|
||||
}
|
||||
|
||||
@@ -153,7 +153,7 @@ public class SacrificeEffect extends SpellAbilityEffect {
|
||||
|
||||
boolean isStrict = sa.hasParam("StrictAmount");
|
||||
int minTargets = optional && !isStrict ? 0 : amount;
|
||||
boolean notEnoughTargets = validTargets.size() < minTargets;
|
||||
boolean notEnoughTargets = isStrict && validTargets.size() < minTargets;
|
||||
|
||||
if (sa.hasParam("Random")) {
|
||||
choosenToSacrifice = new CardCollection(Aggregates.random(validTargets, Math.min(amount, validTargets.size())));
|
||||
|
||||
@@ -243,21 +243,21 @@ public final class CardUtil {
|
||||
|
||||
newCopy.setDamageHistory(in.getDamageHistory());
|
||||
newCopy.setDamageReceivedThisTurn(in.getDamageReceivedThisTurn());
|
||||
for (Card c : in.getBlockedThisTurn()) {
|
||||
newCopy.addBlockedThisTurn(c);
|
||||
}
|
||||
for (Card c : in.getBlockedByThisTurn()) {
|
||||
newCopy.addBlockedByThisTurn(c);
|
||||
}
|
||||
|
||||
// these are LKI already
|
||||
newCopy.getBlockedThisTurn().addAll(in.getBlockedThisTurn());
|
||||
newCopy.getBlockedByThisTurn().addAll(in.getBlockedByThisTurn());
|
||||
|
||||
newCopy.setAttachedCards(getLKICopyList(in.getAttachedCards(), cachedMap));
|
||||
newCopy.setEntityAttachedTo(getLKICopy(in.getEntityAttachedTo(), cachedMap));
|
||||
|
||||
newCopy.setHaunting(in.getHaunting());
|
||||
newCopy.setCopiedPermanent(in.getCopiedPermanent());
|
||||
|
||||
newCopy.setHaunting(in.getHaunting());
|
||||
for (final Card haunter : in.getHauntedBy()) {
|
||||
newCopy.addHauntedBy(haunter, false);
|
||||
}
|
||||
|
||||
newCopy.addRemembered(in.getRemembered());
|
||||
newCopy.addImprintedCards(in.getImprintedCards());
|
||||
newCopy.setChosenCards(new CardCollection(in.getChosenCards()));
|
||||
@@ -278,6 +278,8 @@ public final class CardUtil {
|
||||
|
||||
newCopy.copyChangedTextFrom(in);
|
||||
|
||||
newCopy.setTimestamp(in.getTimestamp());
|
||||
|
||||
newCopy.setBestowTimestamp(in.getBestowTimestamp());
|
||||
|
||||
newCopy.setForetold(in.isForetold());
|
||||
@@ -286,8 +288,6 @@ public final class CardUtil {
|
||||
|
||||
newCopy.setMeldedWith(getLKICopy(in.getMeldedWith(), cachedMap));
|
||||
|
||||
newCopy.setTimestamp(in.getTimestamp());
|
||||
|
||||
// update keyword cache on all states
|
||||
for (CardStateName s : newCopy.getStates()) {
|
||||
newCopy.updateKeywordsCache(newCopy.getState(s));
|
||||
|
||||
@@ -1141,7 +1141,7 @@ public abstract class SpellAbility extends CardTraitBase implements ISpellAbilit
|
||||
clone.payingMana.addAll(payingMana);
|
||||
}
|
||||
clone.paidAbilities = Lists.newArrayList();
|
||||
clone.setPaidHash(Maps.newHashMap(getPaidHash()));
|
||||
clone.setPaidHash(getPaidHash());
|
||||
|
||||
// copy last chapter flag for Trigger
|
||||
clone.lastChapter = this.lastChapter;
|
||||
|
||||
@@ -4,5 +4,5 @@ Types:Legendary Creature Human Advisor
|
||||
PT:2/3
|
||||
K:Flying
|
||||
S:Mode$ CantTarget | AffectedZone$ Battlefield,Graveyard | ValidCard$ Land | Activator$ Opponent | Description$ Lands on the battlefield and land cards in graveyards can't be the targets of spells or abilities your opponents control.
|
||||
S:Mode$ CantPlayLand | ValidCard$ Land.OppCtrl | Origin$ Graveyard | Description$ Your opponents can't play land cards from graveyards.
|
||||
S:Mode$ CantPlayLand | ValidCard$ Land | Player$ Opponent | Origin$ Graveyard | Description$ Your opponents can't play land cards from graveyards.
|
||||
Oracle:Flying\nLands on the battlefield and land cards in graveyards can't be the targets of spells or abilities your opponents control.\nYour opponents can't play land cards from graveyards.
|
||||
|
||||
Reference in New Issue
Block a user