From 9ce81dca3af2faacd3641a2c3acad20c5a265632 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sun, 18 Jul 2021 11:02:09 -0400 Subject: [PATCH] [AFC] Implemented Prosper, Tome-Bound --- .../src/mage/cards/p/ProsperTomeBound.java | 87 +++++++++++++++++++ .../mage/sets/ForgottenRealmsCommander.java | 1 + .../ExileTopXMayPlayUntilEndOfTurnEffect.java | 42 +++++---- 3 files changed, 114 insertions(+), 16 deletions(-) create mode 100644 Mage.Sets/src/mage/cards/p/ProsperTomeBound.java diff --git a/Mage.Sets/src/mage/cards/p/ProsperTomeBound.java b/Mage.Sets/src/mage/cards/p/ProsperTomeBound.java new file mode 100644 index 00000000000..30bb123887e --- /dev/null +++ b/Mage.Sets/src/mage/cards/p/ProsperTomeBound.java @@ -0,0 +1,87 @@ +package mage.cards.p; + +import mage.MageInt; +import mage.abilities.TriggeredAbilityImpl; +import mage.abilities.common.BeginningOfEndStepTriggeredAbility; +import mage.abilities.effects.common.CreateTokenEffect; +import mage.abilities.effects.common.ExileTopXMayPlayUntilEndOfTurnEffect; +import mage.abilities.keyword.DeathtouchAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.*; +import mage.game.Game; +import mage.game.events.GameEvent; +import mage.game.permanent.token.TreasureToken; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class ProsperTomeBound extends CardImpl { + + public ProsperTomeBound(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{2}{B}{R}"); + + this.addSuperType(SuperType.LEGENDARY); + this.subtype.add(SubType.TIEFLING); + this.subtype.add(SubType.WARLOCK); + this.power = new MageInt(1); + this.toughness = new MageInt(4); + + // Deathtouch + this.addAbility(DeathtouchAbility.getInstance()); + + // Mystic Arcanum — At the beginning of your end step, exile the top card of your library. Until the end of your next turn, you may play that card. + this.addAbility(new BeginningOfEndStepTriggeredAbility( + new ExileTopXMayPlayUntilEndOfTurnEffect( + 1, false, Duration.UntilEndOfYourNextTurn + ), TargetController.YOU, false + ).withFlavorWord("Mystic Arcanum")); + + // Pact Boon — Whenever you play a card from exile, create a Treasure token. + this.addAbility(new ProsperTomeBoundTriggeredAbility()); + } + + private ProsperTomeBound(final ProsperTomeBound card) { + super(card); + } + + @Override + public ProsperTomeBound copy() { + return new ProsperTomeBound(this); + } +} + +class ProsperTomeBoundTriggeredAbility extends TriggeredAbilityImpl { + + ProsperTomeBoundTriggeredAbility() { + super(Zone.BATTLEFIELD, new CreateTokenEffect(new TreasureToken())); + this.flavorWord = "Pact Boon"; + } + + private ProsperTomeBoundTriggeredAbility(final ProsperTomeBoundTriggeredAbility ability) { + super(ability); + } + + @Override + public boolean checkEventType(GameEvent event, Game game) { + return event.getType() == GameEvent.EventType.SPELL_CAST + || event.getType() == GameEvent.EventType.LAND_PLAYED; + } + + @Override + public boolean checkTrigger(GameEvent event, Game game) { + return isControlledBy(event.getPlayerId()) && event.getZone() == Zone.EXILED; + } + + @Override + public ProsperTomeBoundTriggeredAbility copy() { + return new ProsperTomeBoundTriggeredAbility(this); + } + + @Override + public String getTriggerPhrase() { + return "Whenever you play a card from exile, "; + } +} diff --git a/Mage.Sets/src/mage/sets/ForgottenRealmsCommander.java b/Mage.Sets/src/mage/sets/ForgottenRealmsCommander.java index e1a656faf86..0c90ab43882 100644 --- a/Mage.Sets/src/mage/sets/ForgottenRealmsCommander.java +++ b/Mage.Sets/src/mage/sets/ForgottenRealmsCommander.java @@ -168,6 +168,7 @@ public final class ForgottenRealmsCommander extends ExpansionSet { cards.add(new SetCardInfo("Prairie Stream", 256, Rarity.RARE, mage.cards.p.PrairieStream.class)); cards.add(new SetCardInfo("Prognostic Sphinx", 90, Rarity.RARE, mage.cards.p.PrognosticSphinx.class)); cards.add(new SetCardInfo("Propaganda", 91, Rarity.UNCOMMON, mage.cards.p.Propaganda.class)); + cards.add(new SetCardInfo("Prosper, Tome-Bound", 2, Rarity.MYTHIC, mage.cards.p.ProsperTomeBound.class)); cards.add(new SetCardInfo("Psychic Impetus", 92, Rarity.UNCOMMON, mage.cards.p.PsychicImpetus.class)); cards.add(new SetCardInfo("Puresteel Paladin", 69, Rarity.RARE, mage.cards.p.PuresteelPaladin.class)); cards.add(new SetCardInfo("Radiant Solar", 9, Rarity.RARE, mage.cards.r.RadiantSolar.class)); diff --git a/Mage/src/main/java/mage/abilities/effects/common/ExileTopXMayPlayUntilEndOfTurnEffect.java b/Mage/src/main/java/mage/abilities/effects/common/ExileTopXMayPlayUntilEndOfTurnEffect.java index 02696d2bc47..2f7bf62e9f9 100644 --- a/Mage/src/main/java/mage/abilities/effects/common/ExileTopXMayPlayUntilEndOfTurnEffect.java +++ b/Mage/src/main/java/mage/abilities/effects/common/ExileTopXMayPlayUntilEndOfTurnEffect.java @@ -3,7 +3,6 @@ package mage.abilities.effects.common; import mage.MageObject; import mage.abilities.Ability; import mage.abilities.Mode; -import mage.abilities.effects.ContinuousEffect; import mage.abilities.effects.OneShotEffect; import mage.abilities.effects.common.asthought.PlayFromNotOwnHandZoneTargetEffect; import mage.cards.Card; @@ -21,21 +20,28 @@ public class ExileTopXMayPlayUntilEndOfTurnEffect extends OneShotEffect { private final int amount; private final boolean showHint; + private final Duration duration; public ExileTopXMayPlayUntilEndOfTurnEffect(int amount) { this(amount, false); } public ExileTopXMayPlayUntilEndOfTurnEffect(int amount, boolean showHint) { + this(amount, showHint, Duration.EndOfTurn); + } + + public ExileTopXMayPlayUntilEndOfTurnEffect(int amount, boolean showHint, Duration duration) { super(Outcome.Benefit); this.amount = amount; this.showHint = showHint; + this.duration = duration; } private ExileTopXMayPlayUntilEndOfTurnEffect(final ExileTopXMayPlayUntilEndOfTurnEffect effect) { super(effect); this.amount = effect.amount; this.showHint = effect.showHint; + this.duration = effect.duration; } @Override @@ -47,21 +53,21 @@ public class ExileTopXMayPlayUntilEndOfTurnEffect extends OneShotEffect { public boolean apply(Game game, Ability source) { Player controller = game.getPlayer(source.getControllerId()); MageObject sourceObject = game.getObject(source.getSourceId()); - if (controller != null && sourceObject != null) { - Set cards = controller.getLibrary().getTopCards(game, amount); - if (!cards.isEmpty()) { - controller.moveCardsToExile(cards, source, game, true, source.getSourceId(), sourceObject.getIdName()); - // remove cards that could not be moved to exile - cards.removeIf(card -> !Zone.EXILED.equals(game.getState().getZone(card.getId()))); - if (!cards.isEmpty()) { - ContinuousEffect effect = new PlayFromNotOwnHandZoneTargetEffect(Zone.EXILED, Duration.EndOfTurn); - effect.setTargetPointer(new FixedTargets(cards, game)); - game.addEffect(effect, source); - } - } + if (controller == null || sourceObject == null) { + return false; + } + Set cards = controller.getLibrary().getTopCards(game, amount); + if (cards.isEmpty()) { return true; } - return false; + controller.moveCardsToExile(cards, source, game, true, source.getSourceId(), sourceObject.getIdName()); + // remove cards that could not be moved to exile + cards.removeIf(card -> !Zone.EXILED.equals(game.getState().getZone(card.getId()))); + if (!cards.isEmpty()) { + game.addEffect(new PlayFromNotOwnHandZoneTargetEffect(Zone.EXILED, duration) + .setTargetPointer(new FixedTargets(cards, game)), source); + } + return true; } @Override @@ -71,11 +77,15 @@ public class ExileTopXMayPlayUntilEndOfTurnEffect extends OneShotEffect { } StringBuilder sb = new StringBuilder(); if (amount == 1) { - sb.append("exile the top card of your library. You may play that card this turn"); + sb.append("exile the top card of your library. "); + sb.append(CardUtil.getTextWithFirstCharUpperCase(duration.toString())); + sb.append(", you may play that card"); } else { sb.append("exile the top "); sb.append(CardUtil.numberToText(amount)); - sb.append(" cards of your library. Until end of turn, you may play cards exiled this way"); + sb.append(" cards of your library. "); + sb.append(CardUtil.getTextWithFirstCharUpperCase(duration.toString())); + sb.append(", you may play cards exiled this way"); } if (showHint) { sb.append(". (You still pay its costs. You can play a land this way only if you have an available land play remaining.)");