diff --git a/Mage.Sets/src/mage/cards/s/StartTheTARDIS.java b/Mage.Sets/src/mage/cards/s/StartTheTARDIS.java new file mode 100644 index 00000000000..51f0571d21e --- /dev/null +++ b/Mage.Sets/src/mage/cards/s/StartTheTARDIS.java @@ -0,0 +1,38 @@ +package mage.cards.s; + +import mage.abilities.effects.common.DrawCardSourceControllerEffect; +import mage.abilities.effects.common.PlaneswalkEffect; +import mage.abilities.effects.keyword.SurveilEffect; +import mage.abilities.keyword.JumpStartAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; + +import java.util.UUID; + +/** + * @author Susucr + */ +public final class StartTheTARDIS extends CardImpl { + + public StartTheTARDIS(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.SORCERY}, "{1}{U}"); + + // Surveil 2, then draw a card. You may planeswalk. + this.getSpellAbility().addEffect(new SurveilEffect(2, false)); + this.getSpellAbility().addEffect(new DrawCardSourceControllerEffect(1).concatBy(", then")); + this.getSpellAbility().addEffect(new PlaneswalkEffect(true)); + + // Jump-start + this.addAbility(new JumpStartAbility(this)); + } + + private StartTheTARDIS(final StartTheTARDIS card) { + super(card); + } + + @Override + public StartTheTARDIS copy() { + return new StartTheTARDIS(this); + } +} diff --git a/Mage.Sets/src/mage/sets/DoctorWho.java b/Mage.Sets/src/mage/sets/DoctorWho.java index aca7e25d55b..9591680c7d8 100644 --- a/Mage.Sets/src/mage/sets/DoctorWho.java +++ b/Mage.Sets/src/mage/sets/DoctorWho.java @@ -176,6 +176,7 @@ public final class DoctorWho extends ExpansionSet { cards.add(new SetCardInfo("Solemn Simulacrum", 246, Rarity.RARE, mage.cards.s.SolemnSimulacrum.class)); cards.add(new SetCardInfo("Sonic Screwdriver", 184, Rarity.UNCOMMON, mage.cards.s.SonicScrewdriver.class)); cards.add(new SetCardInfo("Star Whale", 55, Rarity.UNCOMMON, mage.cards.s.StarWhale.class)); + cards.add(new SetCardInfo("Start the TARDIS", 56, Rarity.UNCOMMON, mage.cards.s.StartTheTARDIS.class)); cards.add(new SetCardInfo("Stormcarved Coast", 308, Rarity.RARE, mage.cards.s.StormcarvedCoast.class)); cards.add(new SetCardInfo("Sunbaked Canyon", 309, Rarity.RARE, mage.cards.s.SunbakedCanyon.class)); cards.add(new SetCardInfo("Sundown Pass", 310, Rarity.RARE, mage.cards.s.SundownPass.class)); diff --git a/Mage/src/main/java/mage/abilities/effects/common/PlaneswalkEffect.java b/Mage/src/main/java/mage/abilities/effects/common/PlaneswalkEffect.java new file mode 100644 index 00000000000..951e555f317 --- /dev/null +++ b/Mage/src/main/java/mage/abilities/effects/common/PlaneswalkEffect.java @@ -0,0 +1,95 @@ +package mage.abilities.effects.common; + +import mage.abilities.Ability; +import mage.abilities.effects.ContinuousEffect; +import mage.abilities.effects.Effect; +import mage.abilities.effects.OneShotEffect; +import mage.constants.Outcome; +import mage.constants.Planes; +import mage.game.Game; +import mage.game.command.CommandObject; +import mage.game.command.Plane; +import mage.players.Player; + +import java.util.List; + +/** + * @author Susucr + */ +public class PlaneswalkEffect extends OneShotEffect { + + private final boolean optional; + + public PlaneswalkEffect(boolean optional) { + super(Outcome.Neutral); + this.optional = optional; + staticText = optional ? "you may planeswalk" : "you planeswalk"; + } + + protected PlaneswalkEffect(final PlaneswalkEffect effect) { + super(effect); + this.optional = effect.optional; + } + + @Override + public boolean apply(Game game, Ability source) { + Player controller = game.getPlayer(source.getControllerId()); + if (controller == null) { + return false; + } + + // As of now, a player may planeswalk iff there are planes in the command zone. + boolean canPlaneswalk = game.getState().getCommand().stream().anyMatch(obj -> obj instanceof Plane); + if (!canPlaneswalk) { + return true; // Not playing with planeswalk enabled. + } + + if (optional && !controller.chooseUse(outcome, "Planeswalk?", source, game)) { + return true; + } + + // Steps: 1) Remove the last plane and set its effects to discarded + for (CommandObject cobject : game.getState().getCommand()) { + if (cobject instanceof Plane) { + if (cobject.getAbilities() != null) { + for (Ability ability : cobject.getAbilities()) { + for (Effect effect : ability.getEffects()) { + if (effect instanceof ContinuousEffect) { + ((ContinuousEffect) effect).discard(); + } + } + } + } + game.getState().removeTriggersOfSourceId(cobject.getId()); + game.getState().getCommand().remove(cobject); + break; + } + } + + // 2) Choose a new random plane we haven't been to, or reset if we've been everywhere + List planesVisited = game.getState().getSeenPlanes(); + if (game.getState().getSeenPlanes() != null) { + if (planesVisited.size() == Planes.values().length) { + game.getState().resetSeenPlanes(); + } + } + + boolean foundNextPlane = false; + while (!foundNextPlane) { + Plane plane = Plane.createRandomPlane(); + try { + if (plane != null && !planesVisited.contains(plane.getName())) { + foundNextPlane = true; + game.addPlane(plane, controller.getId()); + } + } catch (Exception ex) { + } + } + return true; + } + + @Override + public PlaneswalkEffect copy() { + return new PlaneswalkEffect(this); + } +} diff --git a/Mage/src/main/java/mage/abilities/effects/common/RollPlanarDieEffect.java b/Mage/src/main/java/mage/abilities/effects/common/RollPlanarDieEffect.java index 784f31f96d7..b0378d78153 100644 --- a/Mage/src/main/java/mage/abilities/effects/common/RollPlanarDieEffect.java +++ b/Mage/src/main/java/mage/abilities/effects/common/RollPlanarDieEffect.java @@ -8,10 +8,7 @@ import mage.abilities.effects.Effect; import mage.abilities.effects.OneShotEffect; import mage.constants.Outcome; import mage.constants.PlanarDieRollResult; -import mage.constants.Planes; import mage.game.Game; -import mage.game.command.CommandObject; -import mage.game.command.Plane; import mage.players.Player; import mage.target.Target; import mage.target.targetpointer.FixedTarget; @@ -96,43 +93,7 @@ public class RollPlanarDieEffect extends OneShotEffect { } } } else if (planarRoll == PlanarDieRollResult.PLANAR_ROLL) { - // Steps: 1) Remove the last plane and set its effects to discarded - for (CommandObject cobject : game.getState().getCommand()) { - if (cobject instanceof Plane) { - if (cobject.getAbilities() != null) { - for (Ability ability : cobject.getAbilities()) { - for (Effect effect : ability.getEffects()) { - if (effect instanceof ContinuousEffect) { - ((ContinuousEffect) effect).discard(); - } - } - } - } - game.getState().removeTriggersOfSourceId(cobject.getId()); - game.getState().getCommand().remove(cobject); - break; - } - } - - // 2) Choose a new random plane we haven't been to, or reset if we've been everywhere - List planesVisited = game.getState().getSeenPlanes(); - if (game.getState().getSeenPlanes() != null) { - if (planesVisited.size() == Planes.values().length) { - game.getState().resetSeenPlanes(); - } - } - - boolean foundNextPlane = false; - while (!foundNextPlane) { - Plane plane = Plane.createRandomPlane(); - try { - if (plane != null && !planesVisited.contains(plane.getName())) { - foundNextPlane = true; - game.addPlane(plane, controller.getId()); - } - } catch (Exception ex) { - } - } + return new PlaneswalkEffect(false).apply(game, source); } return true; }