diff --git a/Mage.Sets/src/mage/sets/battleforzendikar/CallTheScions.java b/Mage.Sets/src/mage/sets/battleforzendikar/CallTheScions.java index ee853f0190..439dbe84a3 100644 --- a/Mage.Sets/src/mage/sets/battleforzendikar/CallTheScions.java +++ b/Mage.Sets/src/mage/sets/battleforzendikar/CallTheScions.java @@ -28,6 +28,7 @@ package mage.sets.battleforzendikar; import java.util.UUID; +import mage.abilities.Ability; import mage.abilities.effects.Effect; import mage.abilities.effects.common.CreateTokenEffect; import mage.abilities.keyword.DevoidAbility; @@ -47,7 +48,9 @@ public class CallTheScions extends CardImpl { this.expansionSetCode = "BFZ"; // Devoid - this.addAbility(new DevoidAbility(this.color)); + Ability ability = new DevoidAbility(this.color); + ability.setRuleAtTheTop(true); + this.addAbility(ability); // Put two 1/1 colorless Eldrazi Scion creature tokens onto the battlefield. They have "Sacrifice this creature: add {1} to your mana pool." Effect effect = new CreateTokenEffect(new EldraziScionToken(), 2); effect.setText("put two 1/1 colorless Eldrazi Scion creature tokens onto the battlefield. They have \"Sacrifice this creature: Add {1} to your mana pool.\""); diff --git a/Mage.Sets/src/mage/sets/battleforzendikar/CompleteDisregard.java b/Mage.Sets/src/mage/sets/battleforzendikar/CompleteDisregard.java index 28a73d38eb..9a923541d9 100644 --- a/Mage.Sets/src/mage/sets/battleforzendikar/CompleteDisregard.java +++ b/Mage.Sets/src/mage/sets/battleforzendikar/CompleteDisregard.java @@ -28,6 +28,7 @@ package mage.sets.battleforzendikar; import java.util.UUID; +import mage.abilities.Ability; import mage.abilities.effects.common.ExileTargetEffect; import mage.abilities.keyword.DevoidAbility; import mage.cards.CardImpl; @@ -55,7 +56,9 @@ public class CompleteDisregard extends CardImpl { this.expansionSetCode = "BFZ"; // Devoid - this.addAbility(new DevoidAbility(this.color)); + Ability ability = new DevoidAbility(this.color); + ability.setRuleAtTheTop(true); + this.addAbility(ability); // Exile target creature with power 3 or less. this.getSpellAbility().addEffect(new ExileTargetEffect()); diff --git a/Mage.Sets/src/mage/sets/battleforzendikar/CrumbleToDust.java b/Mage.Sets/src/mage/sets/battleforzendikar/CrumbleToDust.java index c0e0d8f507..fcbcf0a1c0 100644 --- a/Mage.Sets/src/mage/sets/battleforzendikar/CrumbleToDust.java +++ b/Mage.Sets/src/mage/sets/battleforzendikar/CrumbleToDust.java @@ -28,6 +28,7 @@ package mage.sets.battleforzendikar; import java.util.UUID; +import mage.abilities.Ability; import mage.abilities.effects.common.ExileTargetAndSearchGraveyardHandLibraryEffect; import mage.abilities.keyword.DevoidAbility; import mage.cards.CardImpl; @@ -46,11 +47,13 @@ public class CrumbleToDust extends CardImpl { this.expansionSetCode = "BFZ"; // Devoid - this.addAbility(new DevoidAbility(this.color)); + Ability ability = new DevoidAbility(this.color); + ability.setRuleAtTheTop(true); + this.addAbility(ability); // Exile target nonbasic land. Search its controller's graveyard, hand, and library for any number of cards with the same name as that land and exile them. Then that player shuffles his or her library. this.getSpellAbility().addTarget(new TargetNonBasicLandPermanent()); - this.getSpellAbility().addEffect(new ExileTargetAndSearchGraveyardHandLibraryEffect(false, "its controller's","any number of cards with the same name as that land")); + this.getSpellAbility().addEffect(new ExileTargetAndSearchGraveyardHandLibraryEffect(false, "its controller's", "any number of cards with the same name as that land")); } public CrumbleToDust(final CrumbleToDust card) { diff --git a/Mage.Sets/src/mage/sets/battleforzendikar/ExertInfluence.java b/Mage.Sets/src/mage/sets/battleforzendikar/ExertInfluence.java index e408f80f98..479fdb7709 100644 --- a/Mage.Sets/src/mage/sets/battleforzendikar/ExertInfluence.java +++ b/Mage.Sets/src/mage/sets/battleforzendikar/ExertInfluence.java @@ -34,6 +34,7 @@ import mage.abilities.dynamicvalue.common.ColorsOfManaSpentToCastCount; import mage.abilities.effects.OneShotEffect; import mage.abilities.effects.common.continuous.GainControlTargetEffect; import mage.cards.CardImpl; +import mage.constants.AbilityWord; import mage.constants.CardType; import mage.constants.Duration; import mage.constants.Outcome; @@ -54,6 +55,7 @@ public class ExertInfluence extends CardImpl { this.expansionSetCode = "BFZ"; // Converge-Gain control of target creature if its power is less than or equal to the number of colors spent to cast Exert Influence. + getSpellAbility().setAbilityWord(AbilityWord.CONVERGE); getSpellAbility().addEffect(new ExertInfluenceEffect()); getSpellAbility().addTarget(new TargetCreaturePermanent()); @@ -73,7 +75,7 @@ class ExertInfluenceEffect extends OneShotEffect { public ExertInfluenceEffect() { super(Outcome.GainControl); - this.staticText = "Converge-Gain control of target creature if its power is less than or equal to the number of colors spent to cast {this}"; + this.staticText = "Gain control of target creature if its power is less than or equal to the number of colors spent to cast {this}"; } public ExertInfluenceEffect(final ExertInfluenceEffect effect) { diff --git a/Mage.Sets/src/mage/sets/battleforzendikar/HorriblyAwry.java b/Mage.Sets/src/mage/sets/battleforzendikar/HorriblyAwry.java index ab9c0d95da..793c186d79 100644 --- a/Mage.Sets/src/mage/sets/battleforzendikar/HorriblyAwry.java +++ b/Mage.Sets/src/mage/sets/battleforzendikar/HorriblyAwry.java @@ -28,6 +28,7 @@ package mage.sets.battleforzendikar; import java.util.UUID; +import mage.abilities.Ability; import mage.abilities.effects.common.CounterTargetWithReplacementEffect; import mage.abilities.keyword.DevoidAbility; import mage.cards.CardImpl; @@ -56,7 +57,9 @@ public class HorriblyAwry extends CardImpl { this.expansionSetCode = "BFZ"; // Devoid - this.addAbility(new DevoidAbility(this.color)); + Ability ability = new DevoidAbility(this.color); + ability.setRuleAtTheTop(true); + this.addAbility(ability); // Counter target creature spell with converted mana cost 4 or less. If that spell is countered this way, exile it instead of putting it into its owner's graveyard. this.getSpellAbility().addEffect(new CounterTargetWithReplacementEffect(Zone.EXILED)); this.getSpellAbility().addTarget(new TargetSpell(filter)); diff --git a/Mage.Sets/src/mage/sets/battleforzendikar/IncubatorDrone.java b/Mage.Sets/src/mage/sets/battleforzendikar/IncubatorDrone.java index c6e27dff96..aeba4330a7 100644 --- a/Mage.Sets/src/mage/sets/battleforzendikar/IncubatorDrone.java +++ b/Mage.Sets/src/mage/sets/battleforzendikar/IncubatorDrone.java @@ -30,6 +30,7 @@ package mage.sets.battleforzendikar; import java.util.UUID; import mage.MageInt; import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.effects.Effect; import mage.abilities.effects.common.CreateTokenEffect; import mage.abilities.keyword.DevoidAbility; import mage.cards.CardImpl; @@ -53,9 +54,11 @@ public class IncubatorDrone extends CardImpl { // Devoid this.addAbility(new DevoidAbility(this.color)); - + // Whenever Incubator Drone enters the battlefield, put a 1/1 colorless Eldrazi Scion creature token onto the battlefield. It has "Sacrifice this creature: Add {1} to your mana pool." - this.addAbility(new EntersBattlefieldTriggeredAbility(new CreateTokenEffect(new EldraziScionToken()))); + Effect effect = new CreateTokenEffect(new EldraziScionToken()); + effect.setText("put a 1/1 colorless Eldrazi Scion creature token onto the battlefield. It has \"Sacrifice this creature: Add {1} to your mana pool.\""); + this.addAbility(new EntersBattlefieldTriggeredAbility(effect, false)); } public IncubatorDrone(final IncubatorDrone card) { diff --git a/Mage.Sets/src/mage/sets/battleforzendikar/InfuseWithTheElements.java b/Mage.Sets/src/mage/sets/battleforzendikar/InfuseWithTheElements.java index 2a5dd29f42..656f335ff6 100644 --- a/Mage.Sets/src/mage/sets/battleforzendikar/InfuseWithTheElements.java +++ b/Mage.Sets/src/mage/sets/battleforzendikar/InfuseWithTheElements.java @@ -53,10 +53,12 @@ public class InfuseWithTheElements extends CardImpl { // Converge - Put X +1/+1 counters on target creature, where X is the number of colors of mana spent to cast Infuse with the Elements. this.getSpellAbility().setAbilityWord(AbilityWord.CONVERGE); - this.getSpellAbility().addEffect(new AddCountersTargetEffect(CounterType.P1P1.createInstance(), ColorsOfManaSpentToCastCount.getInstance())); + Effect effect = new AddCountersTargetEffect(CounterType.P1P1.createInstance(), ColorsOfManaSpentToCastCount.getInstance()); + effect.setText("Put X +1/+1 counters on target creature, where X is the number of colors of mana spent to cast {this}"); + this.getSpellAbility().addEffect(effect); this.getSpellAbility().addTarget(new TargetCreaturePermanent()); // That creature gains trample until end of turn. - Effect effect = new GainAbilityTargetEffect(HasteAbility.getInstance(), Duration.EndOfTurn); + effect = new GainAbilityTargetEffect(HasteAbility.getInstance(), Duration.EndOfTurn); effect.setText("That creature gains trample until end of turn"); this.getSpellAbility().addEffect(effect); } diff --git a/Mage.Sets/src/mage/sets/battleforzendikar/MindRaker.java b/Mage.Sets/src/mage/sets/battleforzendikar/MindRaker.java index a452f219ff..c3db5959c7 100644 --- a/Mage.Sets/src/mage/sets/battleforzendikar/MindRaker.java +++ b/Mage.Sets/src/mage/sets/battleforzendikar/MindRaker.java @@ -29,25 +29,15 @@ package mage.sets.battleforzendikar; import java.util.UUID; import mage.MageInt; -import mage.abilities.Ability; import mage.abilities.common.EntersBattlefieldTriggeredAbility; -import mage.abilities.effects.OneShotEffect; +import mage.abilities.costs.common.ExileOpponentsCardFromExileToGraveyardCost; +import mage.abilities.effects.common.DoIfCostPaid; import mage.abilities.effects.common.discard.DiscardEachPlayerEffect; import mage.abilities.keyword.DevoidAbility; import mage.cards.CardImpl; -import mage.cards.Cards; -import mage.cards.CardsImpl; import mage.constants.CardType; -import mage.constants.Outcome; import mage.constants.Rarity; import mage.constants.TargetController; -import mage.constants.Zone; -import mage.filter.FilterCard; -import mage.filter.predicate.other.OwnerPredicate; -import mage.game.Game; -import mage.players.Player; -import mage.target.Target; -import mage.target.common.TargetCardInExile; /** * @@ -67,7 +57,8 @@ public class MindRaker extends CardImpl { this.addAbility(new DevoidAbility(this.color)); // When Mind Raker enters the battlefield, you may put a card an opponent owns from exile into that player's graveyard. If you do, each opponent discards a card. - this.addAbility(new EntersBattlefieldTriggeredAbility(new MindRakerEffect(), true)); + this.addAbility(new EntersBattlefieldTriggeredAbility( + new DoIfCostPaid(new DiscardEachPlayerEffect(TargetController.OPPONENT), new ExileOpponentsCardFromExileToGraveyardCost(true)), true)); } public MindRaker(final MindRaker card) { @@ -79,43 +70,3 @@ public class MindRaker extends CardImpl { return new MindRaker(this); } } - -class MindRakerEffect extends OneShotEffect { - - private final static FilterCard filter = new FilterCard("card an opponent owns from exile"); - - static { - filter.add(new OwnerPredicate(TargetController.OPPONENT)); - } - - public MindRakerEffect() { - super(Outcome.Discard); - this.staticText = "you may put a card an opponent owns from exile into that player's graveyard. If you do, each opponent discards a card."; - } - - public MindRakerEffect(final MindRakerEffect effect) { - super(effect); - } - - @Override - public MindRakerEffect copy() { - return new MindRakerEffect(this); - } - - @Override - public boolean apply(Game game, Ability source) { - Player controller = game.getPlayer(source.getControllerId()); - if (controller != null) { - Target target = new TargetCardInExile(1, 1, filter, null); - if (target.canChoose(source.getSourceId(), source.getControllerId(), game)) { - if (controller.chooseTarget(outcome, target, source, game)) { - Cards cardsToGraveyard = new CardsImpl(target.getTargets()); - controller.moveCards(cardsToGraveyard, null, Zone.GRAVEYARD, source, game); - return new DiscardEachPlayerEffect(TargetController.OPPONENT).apply(game, source); - } - } - return true; - } - return false; - } -} diff --git a/Mage.Sets/src/mage/sets/battleforzendikar/MurkStrider.java b/Mage.Sets/src/mage/sets/battleforzendikar/MurkStrider.java index fc7edd52c3..0cc67d861b 100644 --- a/Mage.Sets/src/mage/sets/battleforzendikar/MurkStrider.java +++ b/Mage.Sets/src/mage/sets/battleforzendikar/MurkStrider.java @@ -31,23 +31,13 @@ import java.util.UUID; import mage.MageInt; import mage.abilities.Ability; import mage.abilities.common.EntersBattlefieldTriggeredAbility; -import mage.abilities.effects.OneShotEffect; +import mage.abilities.costs.common.ExileOpponentsCardFromExileToGraveyardCost; +import mage.abilities.effects.common.DoIfCostPaid; import mage.abilities.effects.common.ReturnToHandTargetEffect; import mage.abilities.keyword.DevoidAbility; import mage.cards.CardImpl; -import mage.cards.Cards; -import mage.cards.CardsImpl; import mage.constants.CardType; -import mage.constants.Outcome; import mage.constants.Rarity; -import mage.constants.TargetController; -import mage.constants.Zone; -import mage.filter.FilterCard; -import mage.filter.predicate.other.OwnerPredicate; -import mage.game.Game; -import mage.players.Player; -import mage.target.Target; -import mage.target.common.TargetCardInExile; import mage.target.common.TargetCreaturePermanent; /** @@ -68,7 +58,8 @@ public class MurkStrider extends CardImpl { this.addAbility(new DevoidAbility(this.color)); // When Murk Strider enters the battlefield, you may put a card an opponent owns from exile into that player's graveyard. If you do, return target creature to its owner's hand. - Ability ability = new EntersBattlefieldTriggeredAbility(new MurkStriderEffect(), true); + Ability ability = new EntersBattlefieldTriggeredAbility( + new DoIfCostPaid(new ReturnToHandTargetEffect(), new ExileOpponentsCardFromExileToGraveyardCost(true)), true); ability.addTarget(new TargetCreaturePermanent()); this.addAbility(ability); } @@ -82,43 +73,3 @@ public class MurkStrider extends CardImpl { return new MurkStrider(this); } } - -class MurkStriderEffect extends OneShotEffect { - - private final static FilterCard filter = new FilterCard("card an opponent owns from exile"); - - static { - filter.add(new OwnerPredicate(TargetController.OPPONENT)); - } - - public MurkStriderEffect() { - super(Outcome.Discard); - this.staticText = "you may put a card an opponent owns from exile into that player's graveyard. If you do, return target creature to its owner's hand."; - } - - public MurkStriderEffect(final MurkStriderEffect effect) { - super(effect); - } - - @Override - public MurkStriderEffect copy() { - return new MurkStriderEffect(this); - } - - @Override - public boolean apply(Game game, Ability source) { - Player controller = game.getPlayer(source.getControllerId()); - if (controller != null) { - Target target = new TargetCardInExile(1, 1, filter, null); - if (target.canChoose(source.getSourceId(), source.getControllerId(), game)) { - if (controller.chooseTarget(outcome, target, source, game)) { - Cards cardsToGraveyard = new CardsImpl(target.getTargets()); - controller.moveCards(cardsToGraveyard, null, Zone.GRAVEYARD, source, game); - return new ReturnToHandTargetEffect().apply(game, source); - } - } - return true; - } - return false; - } -} diff --git a/Mage.Sets/src/mage/sets/battleforzendikar/PainfulTruths.java b/Mage.Sets/src/mage/sets/battleforzendikar/PainfulTruths.java index d4b561b056..92a547499c 100644 --- a/Mage.Sets/src/mage/sets/battleforzendikar/PainfulTruths.java +++ b/Mage.Sets/src/mage/sets/battleforzendikar/PainfulTruths.java @@ -29,6 +29,7 @@ package mage.sets.battleforzendikar; import java.util.UUID; import mage.abilities.dynamicvalue.common.ColorsOfManaSpentToCastCount; +import mage.abilities.effects.Effect; import mage.abilities.effects.common.DrawCardSourceControllerEffect; import mage.abilities.effects.common.LoseLifeSourceControllerEffect; import mage.cards.CardImpl; @@ -48,8 +49,12 @@ public class PainfulTruths extends CardImpl { // Converge - Draw X cards and lose X life, where X is the number of colors of mana spent to cast Painful Truths. getSpellAbility().setAbilityWord(AbilityWord.CONVERGE); - getSpellAbility().addEffect(new DrawCardSourceControllerEffect(ColorsOfManaSpentToCastCount.getInstance())); - getSpellAbility().addEffect(new LoseLifeSourceControllerEffect(ColorsOfManaSpentToCastCount.getInstance())); + Effect effect = new DrawCardSourceControllerEffect(ColorsOfManaSpentToCastCount.getInstance()); + effect.setText("Draw X cards"); + getSpellAbility().addEffect(effect); + effect = new LoseLifeSourceControllerEffect(ColorsOfManaSpentToCastCount.getInstance()); + effect.setText("and lose X life, where X is the number of colors of mana spent to cast {this}"); + getSpellAbility().addEffect(effect); } public PainfulTruths(final PainfulTruths card) { diff --git a/Mage.Sets/src/mage/sets/battleforzendikar/ProcessorAssault.java b/Mage.Sets/src/mage/sets/battleforzendikar/ProcessorAssault.java index a198f06232..dbcf4c0b8d 100644 --- a/Mage.Sets/src/mage/sets/battleforzendikar/ProcessorAssault.java +++ b/Mage.Sets/src/mage/sets/battleforzendikar/ProcessorAssault.java @@ -29,22 +29,12 @@ package mage.sets.battleforzendikar; import java.util.UUID; import mage.abilities.Ability; -import mage.abilities.costs.CostImpl; +import mage.abilities.costs.common.ExileOpponentsCardFromExileToGraveyardCost; import mage.abilities.effects.common.DamageTargetEffect; import mage.abilities.keyword.DevoidAbility; -import mage.cards.Card; import mage.cards.CardImpl; import mage.constants.CardType; -import mage.constants.Outcome; import mage.constants.Rarity; -import mage.constants.TargetController; -import mage.constants.Zone; -import mage.filter.FilterCard; -import mage.filter.predicate.other.OwnerPredicate; -import mage.game.Game; -import mage.players.Player; -import mage.target.Target; -import mage.target.common.TargetCardInExile; import mage.target.common.TargetCreaturePermanent; /** @@ -58,10 +48,12 @@ public class ProcessorAssault extends CardImpl { this.expansionSetCode = "BFZ"; // Devoid - this.addAbility(new DevoidAbility(this.color)); + Ability ability = new DevoidAbility(this.color); + ability.setRuleAtTheTop(true); + this.addAbility(ability); // As an additional cost to cast Processor Assault, put a card an opponent owns from exile into its owner's graveyard. - this.getSpellAbility().addCost(new PutOpponentExileCardToGraveyardCost()); + this.getSpellAbility().addCost(new ExileOpponentsCardFromExileToGraveyardCost(false)); // Processor Assault deals 5 damage to target creature. this.getSpellAbility().addEffect(new DamageTargetEffect(5)); @@ -77,51 +69,3 @@ public class ProcessorAssault extends CardImpl { return new ProcessorAssault(this); } } - -class PutOpponentExileCardToGraveyardCost extends CostImpl { - - public PutOpponentExileCardToGraveyardCost() { - this.text = "put a card an opponent owns from exile into its owner's graveyard"; - } - - public PutOpponentExileCardToGraveyardCost(PutOpponentExileCardToGraveyardCost cost) { - super(cost); - } - - @Override - public boolean pay(Ability ability, Game game, UUID sourceId, UUID controllerId, boolean noMana) { - Player controller = game.getPlayer(controllerId); - if (controller != null) { - FilterCard filter = new FilterCard(); - filter.add(new OwnerPredicate(TargetController.OPPONENT)); - Target target = new TargetCardInExile(filter); - if (controller.chooseTarget(Outcome.Damage, target, ability, game)) { - Card card = game.getCard(target.getFirstTarget()); - if (card != null) { - paid = true; - controller.moveCards(card, null, Zone.GRAVEYARD, ability, game); - } - } - } - return paid; - } - - @Override - public boolean canPay(Ability ability, UUID sourceId, UUID controllerId, Game game) { - Player controller = game.getPlayer(controllerId); - if (controller != null) { - for (Card card : game.getExile().getAllCards(game)) { - if (controller.hasOpponent(card.getOwnerId(), game)) { - return true; - } - } - } - return false; - } - - @Override - public PutOpponentExileCardToGraveyardCost copy() { - return new PutOpponentExileCardToGraveyardCost(this); - } - -} diff --git a/Mage.Sets/src/mage/sets/battleforzendikar/RuinProcessor.java b/Mage.Sets/src/mage/sets/battleforzendikar/RuinProcessor.java index 96200d7cb4..32c73d263f 100644 --- a/Mage.Sets/src/mage/sets/battleforzendikar/RuinProcessor.java +++ b/Mage.Sets/src/mage/sets/battleforzendikar/RuinProcessor.java @@ -29,23 +29,13 @@ package mage.sets.battleforzendikar; import java.util.UUID; import mage.MageInt; -import mage.abilities.Ability; -import mage.abilities.effects.OneShotEffect; +import mage.abilities.costs.common.ExileOpponentsCardFromExileToGraveyardCost; import mage.abilities.effects.common.CastSourceTriggeredAbility; +import mage.abilities.effects.common.DoIfCostPaid; +import mage.abilities.effects.common.GainLifeEffect; import mage.cards.CardImpl; -import mage.cards.Cards; -import mage.cards.CardsImpl; import mage.constants.CardType; -import mage.constants.Outcome; import mage.constants.Rarity; -import mage.constants.TargetController; -import mage.constants.Zone; -import mage.filter.FilterCard; -import mage.filter.predicate.other.OwnerPredicate; -import mage.game.Game; -import mage.players.Player; -import mage.target.Target; -import mage.target.common.TargetCardInExile; /** * @@ -62,7 +52,8 @@ public class RuinProcessor extends CardImpl { this.toughness = new MageInt(8); // When you cast Ruin Processor, you may put a card an opponent owns from exile into that player's graveyard. If you do, you gain 5 life. - this.addAbility(new CastSourceTriggeredAbility(new RuinProcessorEffect())); + this.addAbility(new CastSourceTriggeredAbility( + new DoIfCostPaid(new GainLifeEffect(5), new ExileOpponentsCardFromExileToGraveyardCost(true)), true)); } @@ -75,44 +66,3 @@ public class RuinProcessor extends CardImpl { return new RuinProcessor(this); } } - -class RuinProcessorEffect extends OneShotEffect { - - private final static FilterCard filter = new FilterCard("card an opponent owns from exile"); - - static { - filter.add(new OwnerPredicate(TargetController.OPPONENT)); - } - - public RuinProcessorEffect() { - super(Outcome.Discard); - this.staticText = "you may put a card an opponent owns from exile into that player's graveyard. If you do, you gain 5 life"; - } - - public RuinProcessorEffect(final RuinProcessorEffect effect) { - super(effect); - } - - @Override - public RuinProcessorEffect copy() { - return new RuinProcessorEffect(this); - } - - @Override - public boolean apply(Game game, Ability source) { - Player controller = game.getPlayer(source.getControllerId()); - if (controller != null) { - Target target = new TargetCardInExile(1, 1, filter, null); - if (target.canChoose(source.getSourceId(), source.getControllerId(), game)) { - if (controller.chooseTarget(outcome, target, source, game)) { - Cards cardsToGraveyard = new CardsImpl(target.getTargets()); - controller.moveCards(cardsToGraveyard, null, Zone.GRAVEYARD, source, game); - controller.gainLife(5, game); - return true; - } - } - return true; - } - return false; - } -} diff --git a/Mage.Sets/src/mage/sets/battleforzendikar/SerpentineSpike.java b/Mage.Sets/src/mage/sets/battleforzendikar/SerpentineSpike.java index ee803053c4..b6de1e9f1a 100644 --- a/Mage.Sets/src/mage/sets/battleforzendikar/SerpentineSpike.java +++ b/Mage.Sets/src/mage/sets/battleforzendikar/SerpentineSpike.java @@ -55,7 +55,9 @@ public class SerpentineSpike extends CardImpl { this.expansionSetCode = "BFZ"; // Devoid - this.addAbility(new DevoidAbility(this.color)); + Ability ability = new DevoidAbility(this.color); + ability.setRuleAtTheTop(true); + this.addAbility(ability); // Serpentine Spike deals 2 damage to target creature, 3 damage to another target creature, and 4 damage to a third target creature. If a creature dealt damage this way would die this turn, exile it instead. this.getSpellAbility().addEffect(new SerpentineSpikeEffect()); this.getSpellAbility().addTarget(new TargetCreaturePermanent(new FilterCreaturePermanent("creature (2 damage)"))); diff --git a/Mage.Sets/src/mage/sets/battleforzendikar/TouchOfTheVoid.java b/Mage.Sets/src/mage/sets/battleforzendikar/TouchOfTheVoid.java index e762dd6c31..3ade709aab 100644 --- a/Mage.Sets/src/mage/sets/battleforzendikar/TouchOfTheVoid.java +++ b/Mage.Sets/src/mage/sets/battleforzendikar/TouchOfTheVoid.java @@ -28,6 +28,7 @@ package mage.sets.battleforzendikar; import java.util.UUID; +import mage.abilities.Ability; import mage.abilities.effects.Effect; import mage.abilities.effects.common.DamageTargetEffect; import mage.abilities.effects.common.replacement.DealtDamageToCreatureBySourceDies; @@ -50,7 +51,9 @@ public class TouchOfTheVoid extends CardImpl { this.expansionSetCode = "BFZ"; // Devoid - this.addAbility(new DevoidAbility(this.color)); + Ability ability = new DevoidAbility(this.color); + ability.setRuleAtTheTop(true); + this.addAbility(ability); // Touch of the Void deals 3 damage to target creature or player. If a creature dealt damage this way would die this turn, exile it instead. this.getSpellAbility().addEffect(new DamageTargetEffect(3)); this.getSpellAbility().addTarget(new TargetCreatureOrPlayer()); diff --git a/Mage.Sets/src/mage/sets/battleforzendikar/TransgressTheMind.java b/Mage.Sets/src/mage/sets/battleforzendikar/TransgressTheMind.java index 3f865e205c..aaaef82e6c 100644 --- a/Mage.Sets/src/mage/sets/battleforzendikar/TransgressTheMind.java +++ b/Mage.Sets/src/mage/sets/battleforzendikar/TransgressTheMind.java @@ -28,6 +28,7 @@ package mage.sets.battleforzendikar; import java.util.UUID; +import mage.abilities.Ability; import mage.abilities.effects.Effect; import mage.abilities.effects.common.ExileCardYouChooseTargetOpponentEffect; import mage.abilities.keyword.DevoidAbility; @@ -56,7 +57,9 @@ public class TransgressTheMind extends CardImpl { this.expansionSetCode = "BFZ"; // Devoid - this.addAbility(new DevoidAbility(this.color)); + Ability ability = new DevoidAbility(this.color); + ability.setRuleAtTheTop(true); + this.addAbility(ability); // Target player reveals his or her hand. You may choose a card from it with converted mana cost 3 or greater and exile that card. Effect effect = new ExileCardYouChooseTargetOpponentEffect(filter); @@ -73,4 +76,4 @@ public class TransgressTheMind extends CardImpl { public TransgressTheMind copy() { return new TransgressTheMind(this); } -} \ No newline at end of file +} diff --git a/Mage.Sets/src/mage/sets/battleforzendikar/TurnAgainst.java b/Mage.Sets/src/mage/sets/battleforzendikar/TurnAgainst.java index 890f78f181..50defaa5d0 100644 --- a/Mage.Sets/src/mage/sets/battleforzendikar/TurnAgainst.java +++ b/Mage.Sets/src/mage/sets/battleforzendikar/TurnAgainst.java @@ -28,6 +28,7 @@ package mage.sets.battleforzendikar; import java.util.UUID; +import mage.abilities.Ability; import mage.abilities.effects.common.UntapTargetEffect; import mage.abilities.effects.common.continuous.GainAbilityTargetEffect; import mage.abilities.effects.common.continuous.GainControlTargetEffect; @@ -50,7 +51,9 @@ public class TurnAgainst extends CardImpl { this.expansionSetCode = "BFZ"; // Devoid - this.addAbility(new DevoidAbility(this.color)); + Ability ability = new DevoidAbility(this.color); + ability.setRuleAtTheTop(true); + this.addAbility(ability); // Gain control of target creature until end of turn. Untap that creature. It gains haste until end of turn. this.getSpellAbility().addTarget(new TargetCreaturePermanent()); this.getSpellAbility().addEffect(new GainControlTargetEffect(Duration.EndOfTurn)); diff --git a/Mage.Sets/src/mage/sets/battleforzendikar/UnifiedFront.java b/Mage.Sets/src/mage/sets/battleforzendikar/UnifiedFront.java index bff442256c..a80690b650 100644 --- a/Mage.Sets/src/mage/sets/battleforzendikar/UnifiedFront.java +++ b/Mage.Sets/src/mage/sets/battleforzendikar/UnifiedFront.java @@ -49,6 +49,7 @@ public class UnifiedFront extends CardImpl { // Converge — Put a 1/1 white Kor Ally creature token onto the battlefield for each color of mana spent to cast Unified Front. getSpellAbility().setAbilityWord(AbilityWord.CONVERGE); Effect effect = new CreateTokenEffect(new KorAllyToken(), ColorsOfManaSpentToCastCount.getInstance()); + effect.setText("Put a 1/1 white Kor Ally creature token onto the battlefield for each color of mana spent to cast {this}"); getSpellAbility().addEffect(effect); } diff --git a/Mage.Sets/src/mage/sets/battleforzendikar/UnnaturalAggression.java b/Mage.Sets/src/mage/sets/battleforzendikar/UnnaturalAggression.java index e652480395..2bc63e6fee 100644 --- a/Mage.Sets/src/mage/sets/battleforzendikar/UnnaturalAggression.java +++ b/Mage.Sets/src/mage/sets/battleforzendikar/UnnaturalAggression.java @@ -68,7 +68,9 @@ public class UnnaturalAggression extends CardImpl { this.expansionSetCode = "BFZ"; // Devoid - this.addAbility(new DevoidAbility(this.color)); + Ability ability = new DevoidAbility(this.color); + ability.setRuleAtTheTop(true); + this.addAbility(ability); // Target creature you control fights target creature an opponent controls. this.getSpellAbility().addEffect(new FightTargetsEffect()); this.getSpellAbility().addTarget(new TargetControlledCreaturePermanent()); diff --git a/Mage.Sets/src/mage/sets/battleforzendikar/VoidAttendant.java b/Mage.Sets/src/mage/sets/battleforzendikar/VoidAttendant.java index 6bda7350b3..44baa72841 100644 --- a/Mage.Sets/src/mage/sets/battleforzendikar/VoidAttendant.java +++ b/Mage.Sets/src/mage/sets/battleforzendikar/VoidAttendant.java @@ -31,25 +31,16 @@ import java.util.UUID; import mage.MageInt; import mage.abilities.Ability; import mage.abilities.common.SimpleActivatedAbility; -import mage.abilities.costs.CostImpl; +import mage.abilities.costs.common.ExileOpponentsCardFromExileToGraveyardCost; import mage.abilities.costs.mana.ManaCostsImpl; import mage.abilities.effects.Effect; import mage.abilities.effects.common.CreateTokenEffect; import mage.abilities.keyword.DevoidAbility; -import mage.cards.Card; import mage.cards.CardImpl; import mage.constants.CardType; -import mage.constants.Outcome; import mage.constants.Rarity; -import mage.constants.TargetController; import mage.constants.Zone; -import mage.filter.FilterCard; -import mage.filter.predicate.other.OwnerPredicate; -import mage.game.Game; import mage.game.permanent.token.EldraziScionToken; -import mage.players.Player; -import mage.target.Target; -import mage.target.common.TargetCardInExile; /** * @@ -72,7 +63,7 @@ public class VoidAttendant extends CardImpl { Effect effect = new CreateTokenEffect(new EldraziScionToken()); effect.setText("put a 1/1 colorless Eldrazi Scion creature token onto the battlefield. It has \"Sacrifice this creature: Add {1} to your mana pool.\""); Ability ability = new SimpleActivatedAbility(Zone.BATTLEFIELD, effect, new ManaCostsImpl("{1}{G}")); - ability.addCost(new VoidAttendantPutOpponentExileCardToGraveyardCost()); + ability.addCost(new ExileOpponentsCardFromExileToGraveyardCost(true)); this.addAbility(ability); } @@ -86,51 +77,3 @@ public class VoidAttendant extends CardImpl { return new VoidAttendant(this); } } - -class VoidAttendantPutOpponentExileCardToGraveyardCost extends CostImpl { - - public VoidAttendantPutOpponentExileCardToGraveyardCost() { - this.text = "Put a card an opponent owns from exile into that player's graveyard"; - } - - public VoidAttendantPutOpponentExileCardToGraveyardCost(VoidAttendantPutOpponentExileCardToGraveyardCost cost) { - super(cost); - } - - @Override - public boolean pay(Ability ability, Game game, UUID sourceId, UUID controllerId, boolean noMana) { - Player controller = game.getPlayer(controllerId); - if (controller != null) { - FilterCard filter = new FilterCard(); - filter.add(new OwnerPredicate(TargetController.OPPONENT)); - Target target = new TargetCardInExile(filter); - if (controller.chooseTarget(Outcome.Damage, target, ability, game)) { - Card card = game.getCard(target.getFirstTarget()); - if (card != null) { - paid = true; - controller.moveCards(card, null, Zone.GRAVEYARD, ability, game); - } - } - } - return paid; - } - - @Override - public boolean canPay(Ability ability, UUID sourceId, UUID controllerId, Game game) { - Player controller = game.getPlayer(controllerId); - if (controller != null) { - for (Card card : game.getExile().getAllCards(game)) { - if (controller.hasOpponent(card.getOwnerId(), game)) { - return true; - } - } - } - return false; - } - - @Override - public VoidAttendantPutOpponentExileCardToGraveyardCost copy() { - return new VoidAttendantPutOpponentExileCardToGraveyardCost(this); - } - -} diff --git a/Mage.Sets/src/mage/sets/battleforzendikar/WastelandStrangler.java b/Mage.Sets/src/mage/sets/battleforzendikar/WastelandStrangler.java index 0b98f9db22..739f0d2772 100644 --- a/Mage.Sets/src/mage/sets/battleforzendikar/WastelandStrangler.java +++ b/Mage.Sets/src/mage/sets/battleforzendikar/WastelandStrangler.java @@ -31,24 +31,14 @@ import java.util.UUID; import mage.MageInt; import mage.abilities.Ability; import mage.abilities.common.EntersBattlefieldTriggeredAbility; -import mage.abilities.effects.OneShotEffect; +import mage.abilities.costs.common.ExileOpponentsCardFromExileToGraveyardCost; +import mage.abilities.effects.common.DoIfCostPaid; import mage.abilities.effects.common.continuous.BoostTargetEffect; import mage.abilities.keyword.DevoidAbility; import mage.cards.CardImpl; -import mage.cards.Cards; -import mage.cards.CardsImpl; import mage.constants.CardType; import mage.constants.Duration; -import mage.constants.Outcome; import mage.constants.Rarity; -import mage.constants.TargetController; -import mage.constants.Zone; -import mage.filter.FilterCard; -import mage.filter.predicate.other.OwnerPredicate; -import mage.game.Game; -import mage.players.Player; -import mage.target.Target; -import mage.target.common.TargetCardInExile; import mage.target.common.TargetCreaturePermanent; /** @@ -69,7 +59,8 @@ public class WastelandStrangler extends CardImpl { this.addAbility(new DevoidAbility(this.color)); // When Wasteland Strangler enters the battlefield, you may put a card an opponent owns from exile into that player's graveyard. If you do, target creature gets -3/-3 until end of turn. - Ability ability = new EntersBattlefieldTriggeredAbility(new WastelandStranglerEffect(), true); + Ability ability = new EntersBattlefieldTriggeredAbility( + new DoIfCostPaid(new BoostTargetEffect(-3, -3, Duration.EndOfTurn), new ExileOpponentsCardFromExileToGraveyardCost(true)), true); ability.addTarget(new TargetCreaturePermanent()); this.addAbility(ability); } @@ -83,43 +74,3 @@ public class WastelandStrangler extends CardImpl { return new WastelandStrangler(this); } } - -class WastelandStranglerEffect extends OneShotEffect { - - private final static FilterCard filter = new FilterCard("card an opponent owns from exile"); - - static { - filter.add(new OwnerPredicate(TargetController.OPPONENT)); - } - - public WastelandStranglerEffect() { - super(Outcome.Discard); - this.staticText = "you may put a card an opponent owns from exile into that player's graveyard. If you do, target creature gets -3/-3 until end of turn."; - } - - public WastelandStranglerEffect(final WastelandStranglerEffect effect) { - super(effect); - } - - @Override - public WastelandStranglerEffect copy() { - return new WastelandStranglerEffect(this); - } - - @Override - public boolean apply(Game game, Ability source) { - Player controller = game.getPlayer(source.getControllerId()); - if (controller != null) { - Target target = new TargetCardInExile(1, 1, filter, null); - if (target.canChoose(source.getSourceId(), source.getControllerId(), game)) { - if (controller.chooseTarget(outcome, target, source, game)) { - Cards cardsToGraveyard = new CardsImpl(target.getTargets()); - controller.moveCards(cardsToGraveyard, null, Zone.GRAVEYARD, source, game); - game.addEffect(new BoostTargetEffect(-3, -3, Duration.EndOfTurn), source); - } - } - return true; - } - return false; - } -} diff --git a/Mage.Sets/src/mage/sets/returntoravnica/Syncopate.java b/Mage.Sets/src/mage/sets/returntoravnica/Syncopate.java index e275c8a853..aa20cacdeb 100644 --- a/Mage.Sets/src/mage/sets/returntoravnica/Syncopate.java +++ b/Mage.Sets/src/mage/sets/returntoravnica/Syncopate.java @@ -40,7 +40,6 @@ import mage.abilities.Ability; import mage.abilities.Mode; import mage.abilities.costs.mana.GenericManaCost; import mage.abilities.effects.OneShotEffect; -import mage.cards.Card; import mage.game.Game; import mage.game.events.GameEvent; import mage.game.stack.Spell; @@ -56,7 +55,6 @@ public class Syncopate extends CardImpl { super(ownerId, 54, "Syncopate", Rarity.UNCOMMON, new CardType[]{CardType.INSTANT}, "{X}{U}"); this.expansionSetCode = "RTR"; - // Counter target spell unless its controller pays {X}. If that spell is countered this way, exile it instead of putting it into its owner's graveyard. this.getSpellAbility().addEffect(new SyncopateCounterUnlessPaysEffect()); this.getSpellAbility().addTarget(new TargetSpell()); @@ -90,27 +88,19 @@ class SyncopateCounterUnlessPaysEffect extends OneShotEffect { @Override public boolean apply(Game game, Ability source) { StackObject spell = game.getStack().getStackObject(targetPointer.getFirst(game, source)); - if (spell != null) { - Player player = game.getPlayer(spell.getControllerId()); + MageObject sourceObject = source.getSourceObject(game); + if (spell != null && (spell instanceof Spell) && sourceObject != null) { Player controller = game.getPlayer(source.getControllerId()); - if (player != null && controller != null) { - + if (controller != null) { int amount = source.getManaCostsToPay().getX(); if (amount > 0) { GenericManaCost cost = new GenericManaCost(amount); if (!cost.pay(source, game, spell.getControllerId(), spell.getControllerId(), false)) { - StackObject stackObject = game.getStack().getStackObject(source.getFirstTarget()); if (stackObject != null && !game.replaceEvent(GameEvent.getEvent(GameEvent.EventType.COUNTER, source.getFirstTarget(), source.getSourceId(), stackObject.getControllerId()))) { - game.informPlayers("Syncopate: cost wasn't payed - countering " + stackObject.getName()); - if (stackObject instanceof Spell) { - game.rememberLKI(source.getFirstTarget(), Zone.STACK, (Spell) stackObject); - } - game.getStack().remove(stackObject); - MageObject card = game.getObject(stackObject.getSourceId()); - if (card instanceof Card) { - ((Card) card).moveToZone(Zone.EXILED, source.getSourceId(), game, false); - } + game.informPlayers(sourceObject.getIdName() + ": cost wasn't payed - countering " + stackObject.getName()); + game.rememberLKI(source.getFirstTarget(), Zone.STACK, (Spell) stackObject); + controller.moveCards((Spell) spell, null, Zone.EXILED, source, game); game.fireEvent(GameEvent.getEvent(GameEvent.EventType.COUNTERED, source.getFirstTarget(), source.getSourceId(), stackObject.getControllerId())); return true; } @@ -127,4 +117,4 @@ class SyncopateCounterUnlessPaysEffect extends OneShotEffect { return "Counter target spell unless its controller pays {X}. If that spell is countered this way, exile it instead of putting it into its owner's graveyard"; } -} \ No newline at end of file +} diff --git a/Mage/src/mage/abilities/AbilityImpl.java b/Mage/src/mage/abilities/AbilityImpl.java index 838204cfa0..5074663605 100644 --- a/Mage/src/mage/abilities/AbilityImpl.java +++ b/Mage/src/mage/abilities/AbilityImpl.java @@ -759,9 +759,7 @@ public abstract class AbilityImpl implements Ability { sbRule.append(": "); } } - if (abilityWord != null) { - sbRule.insert(0, new StringBuilder("").append(abilityWord.toString()).append(" — ")); - } + String ruleStart = sbRule.toString(); String text = modes.getText(); String rule; @@ -779,6 +777,9 @@ public abstract class AbilityImpl implements Ability { } else { rule = ruleStart; } + if (abilityWord != null) { + rule = "" + abilityWord + " — " + Character.toUpperCase(rule.charAt(0)) + rule.substring(1); + } return rule; } diff --git a/Mage/src/mage/abilities/effects/common/DoIfCostPaid.java b/Mage/src/mage/abilities/effects/common/DoIfCostPaid.java index 35ff9555c6..2d33c3d748 100644 --- a/Mage/src/mage/abilities/effects/common/DoIfCostPaid.java +++ b/Mage/src/mage/abilities/effects/common/DoIfCostPaid.java @@ -94,6 +94,7 @@ public class DoIfCostPaid extends OneShotEffect { StringBuilder sb = new StringBuilder(); String costText = cost.getText(); if (costText != null + && !costText.toLowerCase().startsWith("put") && !costText.toLowerCase().startsWith("exile") && !costText.toLowerCase().startsWith("discard") && !costText.toLowerCase().startsWith("sacrifice") diff --git a/Mage/src/mage/abilities/effects/common/DrawCardSourceControllerEffect.java b/Mage/src/mage/abilities/effects/common/DrawCardSourceControllerEffect.java index 00ce366db9..2a152eebc1 100644 --- a/Mage/src/mage/abilities/effects/common/DrawCardSourceControllerEffect.java +++ b/Mage/src/mage/abilities/effects/common/DrawCardSourceControllerEffect.java @@ -1,16 +1,16 @@ /* * Copyright 2010 BetaSteward_at_googlemail.com. All rights reserved. - * + * * Redistribution and use in source and binary forms, with or without modification, are * permitted provided that the following conditions are met: - * + * * 1. Redistributions of source code must retain the above copyright notice, this list of * conditions and the following disclaimer. - * + * * 2. Redistributions in binary form must reproduce the above copyright notice, this list * of conditions and the following disclaimer in the documentation and/or other materials * provided with the distribution. - * + * * THIS SOFTWARE IS PROVIDED BY BetaSteward_at_googlemail.com ``AS IS'' AND ANY EXPRESS OR IMPLIED * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND * FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL BetaSteward_at_googlemail.com OR @@ -20,20 +20,19 @@ * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. - * + * * The views and conclusions contained in the software and documentation are those of the * authors and should not be interpreted as representing official policies, either expressed * or implied, of BetaSteward_at_googlemail.com. */ - package mage.abilities.effects.common; -import mage.constants.Outcome; import mage.abilities.Ability; import mage.abilities.dynamicvalue.DynamicValue; import mage.abilities.dynamicvalue.common.PermanentsOnBattlefieldCount; import mage.abilities.dynamicvalue.common.StaticValue; import mage.abilities.effects.OneShotEffect; +import mage.constants.Outcome; import mage.game.Game; import mage.players.Player; import mage.util.CardUtil; @@ -78,7 +77,7 @@ public class DrawCardSourceControllerEffect extends OneShotEffect { private void setText() { StringBuilder sb = new StringBuilder(); boolean oneCard = (amount instanceof StaticValue && amount.calculate(null, null, this) == 1) - || amount instanceof PermanentsOnBattlefieldCount || amount.toString().equals("1"); + || amount instanceof PermanentsOnBattlefieldCount || amount.toString().equals("1"); sb.append("draw ").append(oneCard ? "a" : CardUtil.numberToText(amount.toString())).append(" card"); if (!oneCard) { sb.append("s"); @@ -91,5 +90,4 @@ public class DrawCardSourceControllerEffect extends OneShotEffect { staticText = sb.toString(); } - } diff --git a/Mage/src/mage/abilities/effects/common/DrawDiscardControllerEffect.java b/Mage/src/mage/abilities/effects/common/DrawDiscardControllerEffect.java index 811addcd58..a710d9aff7 100644 --- a/Mage/src/mage/abilities/effects/common/DrawDiscardControllerEffect.java +++ b/Mage/src/mage/abilities/effects/common/DrawDiscardControllerEffect.java @@ -57,10 +57,12 @@ public class DrawDiscardControllerEffect extends OneShotEffect { this.cardsToDraw = cardsToDraw; this.cardsToDiscard = cardsToDiscard; this.optional = optional; - staticText = new StringBuilder("Draw ") + staticText = new StringBuilder(optional ? "you may " : "") + .append("draw ") .append(cardsToDraw == 1 ? "a" : CardUtil.numberToText(cardsToDraw)) .append(" card").append(cardsToDraw == 1 ? "" : "s") - .append(", then discard ") + .append(optional ? ", if you do" : ", then") + .append(" discard ") .append(cardsToDiscard == 1 ? "a" : CardUtil.numberToText(cardsToDiscard)) .append(" card").append(cardsToDiscard == 1 ? "" : "s").toString(); } diff --git a/Mage/src/mage/abilities/effects/keyword/ScryEffect.java b/Mage/src/mage/abilities/effects/keyword/ScryEffect.java index dec42b05da..ab35b3dfdd 100644 --- a/Mage/src/mage/abilities/effects/keyword/ScryEffect.java +++ b/Mage/src/mage/abilities/effects/keyword/ScryEffect.java @@ -71,7 +71,7 @@ public class ScryEffect extends OneShotEffect { } private void setText() { - StringBuilder sb = new StringBuilder("Scry ").append(scryNumber); + StringBuilder sb = new StringBuilder("scry ").append(scryNumber); if (scryNumber == 1) { sb.append(". (Look at the top card of your library. You may put that card on the bottom of your library.)"); } else {