From 68b3fc80e9ff2d7758511fe0e22bd0b178a18427 Mon Sep 17 00:00:00 2001 From: xenohedron Date: Thu, 20 Apr 2023 18:22:59 -0400 Subject: [PATCH] Fix Vapor Snare effect (#10188) * Fix Vapor Snare and refactor "unless you return a land" effects to use correct static filter * Fix capitalization of return to hand cost * Fix capitalization of sacrifice unless pays effect --- Mage.Sets/src/mage/cards/l/LivingTsunami.java | 17 ++--- Mage.Sets/src/mage/cards/t/TragicLesson.java | 12 +--- Mage.Sets/src/mage/cards/v/VaporSnare.java | 67 +++---------------- ...rnToHandChosenControlledPermanentCost.java | 2 +- .../SacrificeSourceUnlessPaysEffect.java | 14 ++-- 5 files changed, 28 insertions(+), 84 deletions(-) diff --git a/Mage.Sets/src/mage/cards/l/LivingTsunami.java b/Mage.Sets/src/mage/cards/l/LivingTsunami.java index 3a1597d7fe9..75963f9076b 100644 --- a/Mage.Sets/src/mage/cards/l/LivingTsunami.java +++ b/Mage.Sets/src/mage/cards/l/LivingTsunami.java @@ -5,15 +5,13 @@ import java.util.UUID; import mage.MageInt; import mage.abilities.common.BeginningOfUpkeepTriggeredAbility; import mage.abilities.costs.common.ReturnToHandChosenControlledPermanentCost; +import mage.abilities.effects.Effect; import mage.abilities.effects.common.SacrificeSourceUnlessPaysEffect; import mage.abilities.keyword.FlyingAbility; import mage.cards.CardImpl; import mage.cards.CardSetInfo; -import mage.constants.CardType; -import mage.constants.SubType; -import mage.constants.TargetController; -import mage.constants.Zone; -import mage.filter.common.FilterControlledPermanent; +import mage.constants.*; +import mage.filter.StaticFilters; import mage.target.common.TargetControlledPermanent; /** @@ -21,12 +19,6 @@ import mage.target.common.TargetControlledPermanent; * @author jeffwadsworth */ public final class LivingTsunami extends CardImpl { - - static final private FilterControlledPermanent filter = new FilterControlledPermanent("a land"); - - static { - filter.add(CardType.LAND.getPredicate()); - } public LivingTsunami(UUID ownerId, CardSetInfo setInfo) { super(ownerId,setInfo,new CardType[]{CardType.CREATURE},"{2}{U}{U}"); @@ -39,7 +31,8 @@ public final class LivingTsunami extends CardImpl { this.addAbility(FlyingAbility.getInstance()); // At the beginning of your upkeep, sacrifice Living Tsunami unless you return a land you control to its owner's hand. - this.addAbility(new BeginningOfUpkeepTriggeredAbility(Zone.BATTLEFIELD, new SacrificeSourceUnlessPaysEffect(new ReturnToHandChosenControlledPermanentCost(new TargetControlledPermanent(1, 1, filter, true))), TargetController.YOU, false)); + Effect effect = new SacrificeSourceUnlessPaysEffect(new ReturnToHandChosenControlledPermanentCost(new TargetControlledPermanent(1, 1, StaticFilters.FILTER_CONTROLLED_PERMANENT_A_LAND, true))); + this.addAbility(new BeginningOfUpkeepTriggeredAbility(Zone.BATTLEFIELD, effect, TargetController.YOU, false)); } private LivingTsunami(final LivingTsunami card) { diff --git a/Mage.Sets/src/mage/cards/t/TragicLesson.java b/Mage.Sets/src/mage/cards/t/TragicLesson.java index e702f7269c8..54189a8866b 100644 --- a/Mage.Sets/src/mage/cards/t/TragicLesson.java +++ b/Mage.Sets/src/mage/cards/t/TragicLesson.java @@ -11,7 +11,7 @@ import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.CardType; import mage.constants.Outcome; -import mage.filter.common.FilterControlledPermanent; +import mage.filter.StaticFilters; import mage.game.Game; import mage.players.Player; import mage.target.common.TargetControlledPermanent; @@ -42,12 +42,6 @@ public final class TragicLesson extends CardImpl { class TragicLessonEffect extends OneShotEffect { - private static final FilterControlledPermanent filter = new FilterControlledPermanent("a land you control"); - - static { - filter.add(CardType.LAND.getPredicate()); - } - public TragicLessonEffect() { super(Outcome.Discard); staticText = "Then discard a card unless you return a land you control to its owner's hand."; @@ -67,8 +61,8 @@ class TragicLessonEffect extends OneShotEffect { Player controller = game.getPlayer(source.getControllerId()); if (controller != null - && controller.chooseUse(Outcome.Discard, "Do you want to return a land you control to its owner's hand? If you don't, you must discard 1 card", source, game)) { - Cost cost = new ReturnToHandChosenControlledPermanentCost(new TargetControlledPermanent(filter)); + && controller.chooseUse(Outcome.Discard, "Return a land you control to its owner's hand?", source, game)) { + Cost cost = new ReturnToHandChosenControlledPermanentCost(new TargetControlledPermanent(StaticFilters.FILTER_CONTROLLED_PERMANENT_A_LAND)); if (cost.canPay(source, source, controller.getId(), game)) { if (cost.pay(source, game, source, controller.getId(), false, null)) { return true; diff --git a/Mage.Sets/src/mage/cards/v/VaporSnare.java b/Mage.Sets/src/mage/cards/v/VaporSnare.java index 8a222ff08fa..9eda923767c 100644 --- a/Mage.Sets/src/mage/cards/v/VaporSnare.java +++ b/Mage.Sets/src/mage/cards/v/VaporSnare.java @@ -5,28 +5,23 @@ import java.util.UUID; import mage.abilities.Ability; import mage.abilities.common.BeginningOfUpkeepTriggeredAbility; import mage.abilities.common.SimpleStaticAbility; -import mage.abilities.effects.OneShotEffect; +import mage.abilities.costs.common.ReturnToHandChosenControlledPermanentCost; +import mage.abilities.effects.Effect; import mage.abilities.effects.common.AttachEffect; -import mage.abilities.effects.common.SacrificeSourceEffect; +import mage.abilities.effects.common.SacrificeSourceUnlessPaysEffect; import mage.abilities.effects.common.continuous.ControlEnchantedEffect; import mage.abilities.keyword.EnchantAbility; import mage.cards.CardImpl; import mage.cards.CardSetInfo; -import mage.constants.CardType; -import mage.constants.SubType; -import mage.constants.Outcome; -import mage.constants.TargetController; -import mage.constants.Zone; -import mage.filter.common.FilterControlledPermanent; -import mage.game.Game; -import mage.game.permanent.Permanent; -import mage.players.Player; +import mage.constants.*; +import mage.filter.StaticFilters; import mage.target.TargetPermanent; +import mage.target.common.TargetControlledPermanent; import mage.target.common.TargetCreaturePermanent; /** * - * @author jeffwadsworth + * @author jeffwadsworth, xenohedron */ public final class VaporSnare extends CardImpl { @@ -34,7 +29,6 @@ public final class VaporSnare extends CardImpl { super(ownerId,setInfo,new CardType[]{CardType.ENCHANTMENT},"{4}{U}"); this.subtype.add(SubType.AURA); - // Enchant creature TargetPermanent auraTarget = new TargetCreaturePermanent(); this.getSpellAbility().addTarget(auraTarget); @@ -46,7 +40,8 @@ public final class VaporSnare extends CardImpl { this.addAbility(new SimpleStaticAbility(Zone.BATTLEFIELD, new ControlEnchantedEffect())); // At the beginning of your upkeep, sacrifice Vapor Snare unless you return a land you control to its owner's hand. - this.addAbility(new BeginningOfUpkeepTriggeredAbility(new VaporSnareEffect(), TargetController.YOU, false)); + Effect effect = new SacrificeSourceUnlessPaysEffect(new ReturnToHandChosenControlledPermanentCost(new TargetControlledPermanent(1, 1, StaticFilters.FILTER_CONTROLLED_PERMANENT_A_LAND, true))); + this.addAbility(new BeginningOfUpkeepTriggeredAbility(Zone.BATTLEFIELD, effect, TargetController.YOU, false)); } private VaporSnare(final VaporSnare card) { @@ -58,47 +53,3 @@ public final class VaporSnare extends CardImpl { return new VaporSnare(this); } } - -class VaporSnareEffect extends OneShotEffect { - - private static final FilterControlledPermanent filter = new FilterControlledPermanent(); - private static final String effectText = "sacrifice {this} unless you return a land you control to its owner's hand"; - - VaporSnareEffect( ) { - super(Outcome.Sacrifice); - staticText = effectText; - } - - VaporSnareEffect(VaporSnareEffect effect ) { - super(effect); - } - - @Override - public boolean apply(Game game, Ability source) { - boolean targetChosen = false; - Player controller = game.getPlayer(source.getControllerId()); - TargetPermanent target = new TargetPermanent(1, 1, filter, false); - - if (controller != null - && target.canChoose(controller.getId(), source, game)) { - controller.choose(Outcome.Sacrifice, target, source, game); - Permanent permanent = game.getPermanent(target.getFirstTarget()); - - if ( permanent != null ) { - targetChosen = true; - controller.moveCards(permanent, Zone.HAND, source, game); - } - } - - if ( !targetChosen ) { - new SacrificeSourceEffect().apply(game, source); - } - - return false; - } - - @Override - public VaporSnareEffect copy() { - return new VaporSnareEffect(this); - } -} diff --git a/Mage/src/main/java/mage/abilities/costs/common/ReturnToHandChosenControlledPermanentCost.java b/Mage/src/main/java/mage/abilities/costs/common/ReturnToHandChosenControlledPermanentCost.java index dd91a8ef466..72b099e1b20 100644 --- a/Mage/src/main/java/mage/abilities/costs/common/ReturnToHandChosenControlledPermanentCost.java +++ b/Mage/src/main/java/mage/abilities/costs/common/ReturnToHandChosenControlledPermanentCost.java @@ -26,7 +26,7 @@ public class ReturnToHandChosenControlledPermanentCost extends CostImpl { target.setNotTarget(true); this.addTarget(target); if (target.getMaxNumberOfTargets() > 1 && target.getMaxNumberOfTargets() == target.getNumberOfTargets()) { - this.text = "Return " + CardUtil.numberToText(target.getMaxNumberOfTargets()) + ' ' + this.text = "return " + CardUtil.numberToText(target.getMaxNumberOfTargets()) + ' ' + target.getTargetName() + (target.getTargetName().endsWith(" you control") ? "" : " you control") + " to their owner's hand"; diff --git a/Mage/src/main/java/mage/abilities/effects/common/SacrificeSourceUnlessPaysEffect.java b/Mage/src/main/java/mage/abilities/effects/common/SacrificeSourceUnlessPaysEffect.java index 8b62985126e..d99d23cbf2c 100644 --- a/Mage/src/main/java/mage/abilities/effects/common/SacrificeSourceUnlessPaysEffect.java +++ b/Mage/src/main/java/mage/abilities/effects/common/SacrificeSourceUnlessPaysEffect.java @@ -57,20 +57,26 @@ public class SacrificeSourceUnlessPaysEffect extends OneShotEffect { costValueMessage = "{" + genericMana.calculate(game, source, this) + "}"; } String message = ""; + String logMessage = ""; if (costToPay instanceof ManaCost) { - message += "Pay "; + message += "Pay " + costValueMessage; + logMessage += "pay " + costValueMessage; } - message += costValueMessage + '?'; + else if (costValueMessage.length() > 1) { + message += costValueMessage.substring(0,1).toUpperCase() + costValueMessage.substring(1); + logMessage += costValueMessage; + } + message += '?'; costToPay.clearPaid(); if (costToPay.canPay(source, source, source.getControllerId(), game) && player.chooseUse(Outcome.Benefit, message, source, game) && costToPay.pay(source, game, source, source.getControllerId(), false, null)) { - game.informPlayers(player.getLogName() + " chooses to pay " + costValueMessage + " to prevent sacrifice effect"); + game.informPlayers(player.getLogName() + " chooses to " + logMessage + " to prevent sacrifice effect"); return true; } - game.informPlayers(player.getLogName() + " chooses not to pay " + costValueMessage + " to prevent sacrifice effect"); + game.informPlayers(player.getLogName() + " chooses not to " + logMessage + " to prevent sacrifice effect"); if (source.getSourceObjectZoneChangeCounter() == game.getState().getZoneChangeCounter(source.getSourceId()) && game.getState().getZone(source.getSourceId()) == Zone.BATTLEFIELD) { sourcePermanent.sacrifice(source, game);