diff --git a/Mage.Sets/src/mage/cards/e/EntanglingTrap.java b/Mage.Sets/src/mage/cards/e/EntanglingTrap.java index 6a8ef4e7b2..cad90ab7d7 100644 --- a/Mage.Sets/src/mage/cards/e/EntanglingTrap.java +++ b/Mage.Sets/src/mage/cards/e/EntanglingTrap.java @@ -1,44 +1,28 @@ - package mage.cards.e; -import java.util.ArrayList; -import java.util.List; -import java.util.UUID; -import mage.abilities.Ability; import mage.abilities.TriggeredAbilityImpl; -import mage.abilities.effects.Effect; import mage.abilities.effects.common.DontUntapInControllersNextUntapStepTargetEffect; import mage.abilities.effects.common.TapTargetEffect; import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.CardType; -import mage.constants.TargetController; import mage.constants.Zone; -import mage.filter.common.FilterCreaturePermanent; import mage.game.Game; import mage.game.events.GameEvent; -import mage.game.events.GameEvent.EventType; -import mage.target.common.TargetCreaturePermanent; +import mage.target.common.TargetOpponentsCreaturePermanent; + +import java.util.UUID; /** - * * @author LevelX2 */ public final class EntanglingTrap extends CardImpl { - private static final FilterCreaturePermanent filter = new FilterCreaturePermanent("creature an opponent controls"); - - static { - filter.add(TargetController.OPPONENT.getControllerPredicate()); - } - public EntanglingTrap(UUID ownerId, CardSetInfo setInfo) { - super(ownerId,setInfo,new CardType[]{CardType.ENCHANTMENT},"{1}{W}"); + super(ownerId, setInfo, new CardType[]{CardType.ENCHANTMENT}, "{1}{W}"); // Whenever you clash, tap target creature an opponent controls. If you won, that creature doesn't untap during its controller's next untap step. - Ability ability = new EntanglingTrapTriggeredAbility(); - ability.addTarget(new TargetCreaturePermanent(filter)); - this.addAbility(ability); + this.addAbility(new EntanglingTrapTriggeredAbility()); } private EntanglingTrap(final EntanglingTrap card) { @@ -53,11 +37,12 @@ public final class EntanglingTrap extends CardImpl { class EntanglingTrapTriggeredAbility extends TriggeredAbilityImpl { - public EntanglingTrapTriggeredAbility() { - super(Zone.BATTLEFIELD, new TapTargetEffect()); + EntanglingTrapTriggeredAbility() { + super(Zone.BATTLEFIELD, null); + this.addTarget(new TargetOpponentsCreaturePermanent()); } - public EntanglingTrapTriggeredAbility(final EntanglingTrapTriggeredAbility ability) { + private EntanglingTrapTriggeredAbility(final EntanglingTrapTriggeredAbility ability) { super(ability); } @@ -73,28 +58,20 @@ class EntanglingTrapTriggeredAbility extends TriggeredAbilityImpl { @Override public boolean checkTrigger(GameEvent event, Game game) { - //remove effects from previous triggers - List effects = getEffects(); - List effectsToRemove = new ArrayList<>(); - for (Effect effect : effects) { - if (effect instanceof DontUntapInControllersNextUntapStepTargetEffect) { - effectsToRemove.add(effect); - } + if (!isControlledBy(event.getPlayerId())) { + return false; } - for (Effect effect : effectsToRemove) { - effects.remove(effect); + this.getEffects().clear(); + this.addEffect(new TapTargetEffect()); + if (event.getFlag()) { + this.addEffect(new DontUntapInControllersNextUntapStepTargetEffect()); } - - if (event.getData().equals("controller") && event.getPlayerId().equals(getControllerId()) - || event.getData().equals("opponent") && event.getTargetId().equals(getControllerId())) { - addEffect(new DontUntapInControllersNextUntapStepTargetEffect()); - } - return true; } @Override public String getRule() { - return "Whenever you clash, tap target creature an opponent controls. If you won, that creature doesn't untap during its controller's next untap step."; + return "Whenever you clash, tap target creature an opponent controls. " + + "If you won, that creature doesn't untap during its controller's next untap step."; } } diff --git a/Mage.Sets/src/mage/cards/r/RebellionOfTheFlamekin.java b/Mage.Sets/src/mage/cards/r/RebellionOfTheFlamekin.java index 54ceeaa63a..62b6d42475 100644 --- a/Mage.Sets/src/mage/cards/r/RebellionOfTheFlamekin.java +++ b/Mage.Sets/src/mage/cards/r/RebellionOfTheFlamekin.java @@ -1,39 +1,34 @@ - package mage.cards.r; -import java.util.UUID; import mage.abilities.Ability; import mage.abilities.TriggeredAbilityImpl; -import mage.abilities.costs.mana.ManaCostsImpl; -import mage.abilities.effects.ContinuousEffect; -import mage.abilities.effects.Effect; +import mage.abilities.costs.mana.GenericManaCost; import mage.abilities.effects.OneShotEffect; -import mage.abilities.effects.common.CreateTokenEffect; import mage.abilities.effects.common.DoIfCostPaid; import mage.abilities.effects.common.continuous.GainAbilityTargetEffect; import mage.abilities.keyword.HasteAbility; import mage.cards.CardImpl; import mage.cards.CardSetInfo; -import mage.constants.CardType; -import mage.constants.SubType; -import mage.constants.Duration; -import mage.constants.Outcome; -import mage.constants.Zone; +import mage.constants.*; import mage.game.Game; import mage.game.events.GameEvent; import mage.game.permanent.Permanent; import mage.game.permanent.token.ElementalShamanToken; -import mage.players.Player; -import mage.target.targetpointer.FixedTarget; +import mage.game.permanent.token.Token; +import mage.target.targetpointer.FixedTargets; + +import java.util.List; +import java.util.Objects; +import java.util.UUID; +import java.util.stream.Collectors; /** - * * @author Styxo */ public final class RebellionOfTheFlamekin extends CardImpl { public RebellionOfTheFlamekin(UUID ownerId, CardSetInfo setInfo) { - super(ownerId,setInfo,new CardType[]{CardType.TRIBAL,CardType.ENCHANTMENT},"{3}{R}"); + super(ownerId, setInfo, new CardType[]{CardType.TRIBAL, CardType.ENCHANTMENT}, "{3}{R}"); this.subtype.add(SubType.ELEMENTAL); // Whenever you clash, you may pay {1}. If you do create a 3/1 Red Elemental Shaman creature token in play. If you won that token gains haste @@ -52,11 +47,11 @@ public final class RebellionOfTheFlamekin extends CardImpl { class RebellionOfTheFlamekinTriggeredAbility extends TriggeredAbilityImpl { - public RebellionOfTheFlamekinTriggeredAbility() { - super(Zone.BATTLEFIELD, new RebellionOfTheFlamekinEffect()); + RebellionOfTheFlamekinTriggeredAbility() { + super(Zone.BATTLEFIELD, new DoIfCostPaid(new RebellionOfTheFlamekinEffect(), new GenericManaCost(1))); } - public RebellionOfTheFlamekinTriggeredAbility(final RebellionOfTheFlamekinTriggeredAbility ability) { + private RebellionOfTheFlamekinTriggeredAbility(final RebellionOfTheFlamekinTriggeredAbility ability) { super(ability); } @@ -72,32 +67,29 @@ class RebellionOfTheFlamekinTriggeredAbility extends TriggeredAbilityImpl { @Override public boolean checkTrigger(GameEvent event, Game game) { - boolean youWonTheClash = false; - if (event.getData().equals("controller") && event.getPlayerId().equals(getControllerId()) - || event.getData().equals("opponent") && event.getTargetId().equals(getControllerId())) { - youWonTheClash = true; - } - for (Effect effect : getEffects()) { - if (effect instanceof RebellionOfTheFlamekinEffect) { - effect.setValue("clash", youWonTheClash); - } + if (!isControlledBy(event.getPlayerId())) { + return false; } + this.getEffects().setValue("clash", event.getFlag()); return true; } @Override public String getRule() { - return "Whenever you clash, you may pay {1}. If you do create a 3/1 Red Elemental Shaman creature token. If you won that token gains haste until end of turn"; + return "Whenever you clash, you may pay {1}. If you do, " + + "create a 3/1 red Elemental Shaman creature token. " + + "If you won, that token gains haste until end of turn. " + + "(This ability triggers after the clash ends.)"; } } class RebellionOfTheFlamekinEffect extends OneShotEffect { - public RebellionOfTheFlamekinEffect() { + RebellionOfTheFlamekinEffect() { super(Outcome.PutCreatureInPlay); } - public RebellionOfTheFlamekinEffect(final RebellionOfTheFlamekinEffect effect) { + private RebellionOfTheFlamekinEffect(final RebellionOfTheFlamekinEffect effect) { super(effect); } @@ -108,21 +100,20 @@ class RebellionOfTheFlamekinEffect extends OneShotEffect { @Override public boolean apply(Game game, Ability source) { - Player controller = game.getPlayer(source.getControllerId()); - if (controller != null) { - CreateTokenEffect createTokenEffect = new CreateTokenEffect(new ElementalShamanToken("LRW")); - DoIfCostPaid doIfCostPaid = new DoIfCostPaid(createTokenEffect, new ManaCostsImpl("{1}")); - doIfCostPaid.apply(game, source); - Permanent token = game.getPermanent(createTokenEffect.getLastAddedTokenId()); - if (token != null && (boolean) (this.getValue("clash"))) { - ContinuousEffect continuousEffect = new GainAbilityTargetEffect(HasteAbility.getInstance(), Duration.EndOfTurn); - continuousEffect.setTargetPointer(new FixedTarget(createTokenEffect.getLastAddedTokenId())); - game.addEffect(continuousEffect, source); - } - return true; + Token token = new ElementalShamanToken("LRW"); + token.putOntoBattlefield(1, game, source, source.getControllerId()); + List permanents = token + .getLastAddedTokenIds() + .stream() + .map(game::getPermanent) + .filter(Objects::nonNull) + .collect(Collectors.toList()); + if (!permanents.isEmpty() && (boolean) this.getValue("clash")) { + game.addEffect(new GainAbilityTargetEffect( + HasteAbility.getInstance(), Duration.EndOfTurn + ).setTargetPointer(new FixedTargets(permanents, game)), source); } - return false; - + return true; } } diff --git a/Mage.Sets/src/mage/cards/s/SylvanEchoes.java b/Mage.Sets/src/mage/cards/s/SylvanEchoes.java index ea38df297b..f181a73156 100644 --- a/Mage.Sets/src/mage/cards/s/SylvanEchoes.java +++ b/Mage.Sets/src/mage/cards/s/SylvanEchoes.java @@ -1,7 +1,5 @@ - package mage.cards.s; -import java.util.UUID; import mage.abilities.TriggeredAbilityImpl; import mage.abilities.effects.common.DrawCardSourceControllerEffect; import mage.cards.CardImpl; @@ -11,14 +9,15 @@ import mage.constants.Zone; import mage.game.Game; import mage.game.events.GameEvent; +import java.util.UUID; + /** - * * @author Styxo */ public final class SylvanEchoes extends CardImpl { public SylvanEchoes(UUID ownerId, CardSetInfo setInfo) { - super(ownerId,setInfo,new CardType[]{CardType.ENCHANTMENT},"{G}"); + super(ownerId, setInfo, new CardType[]{CardType.ENCHANTMENT}, "{G}"); // Whenever you clahs and you win, you may draw a card this.addAbility(new SylvanEchoesTriggeredAbility()); @@ -36,11 +35,11 @@ public final class SylvanEchoes extends CardImpl { class SylvanEchoesTriggeredAbility extends TriggeredAbilityImpl { - public SylvanEchoesTriggeredAbility() { + SylvanEchoesTriggeredAbility() { super(Zone.BATTLEFIELD, new DrawCardSourceControllerEffect(1), true); } - public SylvanEchoesTriggeredAbility(final SylvanEchoesTriggeredAbility ability) { + private SylvanEchoesTriggeredAbility(final SylvanEchoesTriggeredAbility ability) { super(ability); } @@ -56,12 +55,11 @@ class SylvanEchoesTriggeredAbility extends TriggeredAbilityImpl { @Override public boolean checkTrigger(GameEvent event, Game game) { - return event.getData().equals("controller") && event.getPlayerId().equals(getControllerId()) - || event.getData().equals("opponent") && event.getTargetId().equals(getControllerId()); + return isControlledBy(event.getPlayerId()) && event.getFlag(); } @Override public String getRule() { - return "Whenever you clash and you win, " + super.getRule(); + return "Whenever you clash and win, you may draw a card"; } } diff --git a/Mage/src/main/java/mage/abilities/effects/common/ClashEffect.java b/Mage/src/main/java/mage/abilities/effects/common/ClashEffect.java index 0fb8233495..b4c03d3009 100644 --- a/Mage/src/main/java/mage/abilities/effects/common/ClashEffect.java +++ b/Mage/src/main/java/mage/abilities/effects/common/ClashEffect.java @@ -12,7 +12,6 @@ import mage.constants.Outcome; import mage.constants.Zone; import mage.game.Game; import mage.game.events.GameEvent; -import mage.game.events.GameEvent.EventType; import mage.players.Player; import mage.players.PlayerList; import mage.target.Target; @@ -85,100 +84,104 @@ public class ClashEffect extends OneShotEffect implements MageSingleton { public boolean apply(Game game, Ability source) { Player controller = game.getPlayer(source.getControllerId()); MageObject sourceObject = source.getSourceObject(game); - if (controller != null && sourceObject != null - && !game.replaceEvent(GameEvent.getEvent(GameEvent.EventType.CLASH, controller.getId(), source, controller.getId()))) { - // choose opponent - Target target = new TargetOpponent(true); - target.setTargetName("an opponent to clash with"); - if (controller.choose(Outcome.Benefit, target, source.getSourceId(), game)) { - Player opponent = game.getPlayer(target.getFirstTarget()); - if (opponent != null) { - int cmcController = Integer.MIN_VALUE; - Card cardController = null; - boolean topController = true; - int cmcOpponent = Integer.MIN_VALUE; - Card cardOpponent = null; - boolean topOpponent = true; - // Reveal top cards of involved players - StringBuilder message = new StringBuilder("Clash: "); - message.append(controller.getLogName()); - if (controller.getLibrary().hasCards()) { - Cards cards = new CardsImpl(); - cardController = controller.getLibrary().getFromTop(game); - cards.add(cardController); - controller.revealCards(sourceObject.getIdName() + ": Clash card of " + controller.getName(), cards, game); - cmcController = cardController.getConvertedManaCost(); - message.append(" (").append(cmcController).append(')'); - } else { - message.append(" no card"); - } - message.append(" vs. ").append(opponent.getLogName()); - if (opponent.getLibrary().hasCards()) { - Cards cards = new CardsImpl(); - cardOpponent = opponent.getLibrary().getFromTop(game); - cards.add(cardOpponent); - opponent.revealCards(sourceObject.getIdName() + ": Clash card of " + opponent.getName(), cards, game); - cmcOpponent = cardOpponent.getConvertedManaCost(); - message.append(" (").append(cmcOpponent).append(')'); - } else { - message.append(" no card"); - } - message.append(" - "); - if (!game.isSimulation()) { - if (cmcController > cmcOpponent) { - message.append(controller.getLogName()).append(" won the clash"); - game.informPlayer(controller, "You won the clash!"); - } else if (cmcController < cmcOpponent) { - message.append(opponent.getLogName()).append(" won the clash"); - game.informPlayer(controller, opponent.getLogName() + " won the clash!"); - } else { - message.append(" no winner "); - } - game.informPlayers(message.toString()); - } - // decide to put the cards on top or on the buttom of library in turn order beginning with the active player in turn order - PlayerList playerList = game.getPlayerList().copy(); - playerList.setCurrent(game.getActivePlayerId()); - Player nextPlayer; - do { - Player current = playerList.getCurrent(game); - if (cardController != null && current.getId().equals(controller.getId())) { - topController = current.chooseUse(Outcome.Detriment, "Put " + cardController.getLogName() + " back on top of your library? (otherwise it goes to bottom)", source, game); - } - if (cardOpponent != null && current.getId().equals(opponent.getId())) { - topOpponent = current.chooseUse(Outcome.Detriment, "Put " + cardOpponent.getLogName() + " back on top of your library? (otherwise it goes to bottom)", source, game); - } - nextPlayer = playerList.getNext(game, false); - } while (nextPlayer != null && !nextPlayer.getId().equals(game.getActivePlayerId())); - // put the cards back to library - if (cardController != null) { - controller.moveCardToLibraryWithInfo(cardController, source, game, Zone.LIBRARY, topController, true); - } - if (cardOpponent != null) { - opponent.moveCardToLibraryWithInfo(cardOpponent, source, game, Zone.LIBRARY, topOpponent, true); - } - // fire CLASHED event with info about who won - String winner = "draw"; - if (cmcController > cmcOpponent) { - winner = "controller"; - } - if (cmcOpponent > cmcController) { - winner = "opponent"; - } - GameEvent gameEvent = new GameEvent(GameEvent.EventType.CLASHED, opponent.getId(), source, controller.getId()); - gameEvent.setData(winner); - game.fireEvent(gameEvent); + if (controller == null + || sourceObject == null + || game.replaceEvent(GameEvent.getEvent( + GameEvent.EventType.CLASH, controller.getId(), source, controller.getId() + ))) { + return false; + } + // choose opponent + Target target = new TargetOpponent(true); + target.setTargetName("an opponent to clash with"); + target.setNotTarget(true); + if (!controller.choose(Outcome.Benefit, target, source.getSourceId(), game)) { + return false; + } + Player opponent = game.getPlayer(target.getFirstTarget()); + if (opponent == null) { + return false; + } + int cmcController = Integer.MIN_VALUE; + Card cardController = null; + boolean topController = true; + int cmcOpponent = Integer.MIN_VALUE; + Card cardOpponent = null; + boolean topOpponent = true; + // Reveal top cards of involved players + StringBuilder message = new StringBuilder("Clash: "); + message.append(controller.getLogName()); + if (controller.getLibrary().hasCards()) { + Cards cards = new CardsImpl(); + cardController = controller.getLibrary().getFromTop(game); + cards.add(cardController); + controller.revealCards(sourceObject.getIdName() + ": Clash card of " + controller.getName(), cards, game); + cmcController = cardController.getConvertedManaCost(); + message.append(" (").append(cmcController).append(')'); + } else { + message.append(" no card"); + } + message.append(" vs. ").append(opponent.getLogName()); + if (opponent.getLibrary().hasCards()) { + Cards cards = new CardsImpl(); + cardOpponent = opponent.getLibrary().getFromTop(game); + cards.add(cardOpponent); + opponent.revealCards(sourceObject.getIdName() + ": Clash card of " + opponent.getName(), cards, game); + cmcOpponent = cardOpponent.getConvertedManaCost(); + message.append(" (").append(cmcOpponent).append(')'); + } else { + message.append(" no card"); + } + message.append(" - "); + if (!game.isSimulation()) { + if (cmcController > cmcOpponent) { + message.append(controller.getLogName()).append(" won the clash"); + game.informPlayer(controller, "You won the clash!"); + } else if (cmcController < cmcOpponent) { + message.append(opponent.getLogName()).append(" won the clash"); + game.informPlayer(controller, opponent.getLogName() + " won the clash!"); + } else { + message.append(" no winner "); + } + game.informPlayers(message.toString()); + } + // decide to put the cards on top or on the buttom of library in turn order beginning with the active player in turn order + PlayerList playerList = game.getPlayerList().copy(); + playerList.setCurrent(game.getActivePlayerId()); + Player nextPlayer; + do { + Player current = playerList.getCurrent(game); + if (cardController != null && current.getId().equals(controller.getId())) { + topController = current.chooseUse(Outcome.Detriment, "Put " + cardController.getLogName() + " back on top of your library? (otherwise it goes to bottom)", source, game); + } + if (cardOpponent != null && current.getId().equals(opponent.getId())) { + topOpponent = current.chooseUse(Outcome.Detriment, "Put " + cardOpponent.getLogName() + " back on top of your library? (otherwise it goes to bottom)", source, game); + } + nextPlayer = playerList.getNext(game, false); + } while (nextPlayer != null && !nextPlayer.getId().equals(game.getActivePlayerId())); + // put the cards back to library + if (cardController != null) { + controller.moveCardToLibraryWithInfo(cardController, source, game, Zone.LIBRARY, topController, true); + } + if (cardOpponent != null) { + opponent.moveCardToLibraryWithInfo(cardOpponent, source, game, Zone.LIBRARY, topOpponent, true); + } + // fire CLASHED event with info about who won + game.fireEvent(new GameEvent( + GameEvent.EventType.CLASHED, controller.getId(), source, + opponent.getId(), 0, cmcController > cmcOpponent + )); + game.fireEvent(new GameEvent( + GameEvent.EventType.CLASHED, opponent.getId(), source, + controller.getId(), 0, cmcOpponent > cmcController + )); - // set opponent to DoIfClashWonEffect - for (Effect effect : source.getEffects()) { - if (effect instanceof DoIfClashWonEffect) { - effect.setValue("clashOpponent", opponent); - } - } - return cmcController > cmcOpponent; - } + // set opponent to DoIfClashWonEffect + for (Effect effect : source.getEffects()) { + if (effect instanceof DoIfClashWonEffect) { + effect.setValue("clashOpponent", opponent); } } - return false; + return cmcController > cmcOpponent; } }