diff --git a/Mage.Sets/src/mage/cards/b/BagOfDevouring.java b/Mage.Sets/src/mage/cards/b/BagOfDevouring.java index 296d47c9c7c..dbe2fb57f50 100644 --- a/Mage.Sets/src/mage/cards/b/BagOfDevouring.java +++ b/Mage.Sets/src/mage/cards/b/BagOfDevouring.java @@ -13,9 +13,7 @@ import mage.abilities.effects.common.ExileTargetForSourceEffect; import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.cards.CardsImpl; -import mage.constants.CardType; -import mage.constants.Outcome; -import mage.constants.Zone; +import mage.constants.*; import mage.filter.FilterPermanent; import mage.filter.StaticFilters; import mage.filter.common.FilterControlledPermanent; @@ -26,7 +24,6 @@ import mage.game.Game; import mage.players.Player; import mage.target.TargetCard; import mage.target.common.TargetCardInExile; -import mage.target.common.TargetControlledPermanent; import mage.util.CardUtil; import java.util.UUID; @@ -59,7 +56,9 @@ public final class BagOfDevouring extends CardImpl { super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT}, "{B}"); // Whenever you sacrifice another nontoken artifact or creature, exile it. - this.addAbility(new SacrificePermanentTriggeredAbility(new ExileTargetForSourceEffect().setText("exile it"), filter, true)); + this.addAbility(new SacrificePermanentTriggeredAbility(Zone.BATTLEFIELD, + new ExileTargetForSourceEffect().setText("exile it"), filter, + TargetController.YOU, SetTargetPointer.PERMANENT, false)); // {2}, {T}, Sacrifice another artifact or creature: Draw a card. Ability ability = new SimpleActivatedAbility(new DrawCardSourceControllerEffect(1), new GenericManaCost(2)); diff --git a/Mage.Sets/src/mage/cards/b/BloodAspirant.java b/Mage.Sets/src/mage/cards/b/BloodAspirant.java index 16a32fbfec3..9aa5fce17a4 100644 --- a/Mage.Sets/src/mage/cards/b/BloodAspirant.java +++ b/Mage.Sets/src/mage/cards/b/BloodAspirant.java @@ -2,7 +2,7 @@ package mage.cards.b; import mage.MageInt; import mage.abilities.Ability; -import mage.abilities.TriggeredAbilityImpl; +import mage.abilities.common.SacrificePermanentTriggeredAbility; import mage.abilities.common.SimpleActivatedAbility; import mage.abilities.costs.common.SacrificeTargetCost; import mage.abilities.costs.common.TapSourceCost; @@ -15,13 +15,10 @@ import mage.cards.CardSetInfo; import mage.constants.CardType; import mage.constants.Duration; import mage.constants.SubType; -import mage.constants.Zone; import mage.counters.CounterType; +import mage.filter.StaticFilters; import mage.filter.common.FilterControlledPermanent; import mage.filter.predicate.Predicates; -import mage.game.Game; -import mage.game.events.GameEvent; -import mage.target.common.TargetControlledPermanent; import mage.target.common.TargetCreaturePermanent; import java.util.UUID; @@ -49,7 +46,10 @@ public final class BloodAspirant extends CardImpl { this.toughness = new MageInt(1); // Whenever you sacrifice a permanent, put a +1/+1 counter on Blood Aspirant. - this.addAbility(new BloodAspirantAbility()); + this.addAbility(new SacrificePermanentTriggeredAbility( + new AddCountersSourceEffect(CounterType.P1P1.createInstance()), + StaticFilters.FILTER_PERMANENT + )); // {1}{R}, {T}, Sacrifice a creature or enchantment: Blood Aspirant deals 1 damage to target creature. That creature can't block this turn. Ability ability = new SimpleActivatedAbility( @@ -72,34 +72,3 @@ public final class BloodAspirant extends CardImpl { return new BloodAspirant(this); } } - -class BloodAspirantAbility extends TriggeredAbilityImpl { - - BloodAspirantAbility() { - super(Zone.BATTLEFIELD, new AddCountersSourceEffect(CounterType.P1P1.createInstance())); - } - - private BloodAspirantAbility(final BloodAspirantAbility ability) { - super(ability); - } - - @Override - public BloodAspirantAbility copy() { - return new BloodAspirantAbility(this); - } - - @Override - public boolean checkEventType(GameEvent event, Game game) { - return event.getType() == GameEvent.EventType.SACRIFICED_PERMANENT; - } - - @Override - public boolean checkTrigger(GameEvent event, Game game) { - return event.getPlayerId().equals(this.getControllerId()); - } - - @Override - public String getRule() { - return "Whenever you sacrifice a permanent, put a +1/+1 counter on {this}."; - } -} diff --git a/Mage.Sets/src/mage/cards/b/Bloodbriar.java b/Mage.Sets/src/mage/cards/b/Bloodbriar.java index ed3c14c8197..c6792f5d9cb 100644 --- a/Mage.Sets/src/mage/cards/b/Bloodbriar.java +++ b/Mage.Sets/src/mage/cards/b/Bloodbriar.java @@ -1,19 +1,19 @@ package mage.cards.b; -import java.util.UUID; import mage.MageInt; -import mage.abilities.common.SacrificeAllTriggeredAbility; +import mage.abilities.common.SacrificePermanentTriggeredAbility; import mage.abilities.effects.common.counter.AddCountersSourceEffect; import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.CardType; import mage.constants.SubType; -import mage.constants.TargetController; import mage.counters.CounterType; import mage.filter.FilterPermanent; import mage.filter.predicate.mageobject.AnotherPredicate; +import java.util.UUID; + /** * * @author LevelX2 @@ -23,7 +23,6 @@ public final class Bloodbriar extends CardImpl { private static final FilterPermanent filter = new FilterPermanent("another permanent"); static { - filter.add(TargetController.YOU.getControllerPredicate()); filter.add(AnotherPredicate.instance); } @@ -34,7 +33,9 @@ public final class Bloodbriar extends CardImpl { this.toughness = new MageInt(3); // Whenever you sacrifice another permanent, put a +1/+1 counter on Bloodbriar. - this.addAbility(new SacrificeAllTriggeredAbility(new AddCountersSourceEffect(CounterType.P1P1.createInstance()), filter, TargetController.YOU, false)); + this.addAbility(new SacrificePermanentTriggeredAbility( + new AddCountersSourceEffect(CounterType.P1P1.createInstance()), filter + )); } private Bloodbriar(final Bloodbriar card) { diff --git a/Mage.Sets/src/mage/cards/c/CarmenCruelSkymarcher.java b/Mage.Sets/src/mage/cards/c/CarmenCruelSkymarcher.java index 3be5c0fd216..4577ef54ce9 100644 --- a/Mage.Sets/src/mage/cards/c/CarmenCruelSkymarcher.java +++ b/Mage.Sets/src/mage/cards/c/CarmenCruelSkymarcher.java @@ -2,24 +2,20 @@ package mage.cards.c; import mage.MageInt; import mage.abilities.Ability; -import mage.abilities.TriggeredAbilityImpl; import mage.abilities.common.AttacksTriggeredAbility; +import mage.abilities.common.SacrificePermanentTriggeredAbility; import mage.abilities.effects.common.GainLifeEffect; import mage.abilities.effects.common.ReturnFromGraveyardToBattlefieldTargetEffect; import mage.abilities.effects.common.counter.AddCountersSourceEffect; import mage.abilities.keyword.FlyingAbility; import mage.cards.CardImpl; import mage.cards.CardSetInfo; -import mage.constants.CardType; -import mage.constants.SubType; -import mage.constants.SuperType; -import mage.constants.Zone; +import mage.constants.*; import mage.counters.CounterType; import mage.filter.FilterCard; +import mage.filter.StaticFilters; import mage.filter.common.FilterPermanentCard; import mage.filter.predicate.card.ManaValueLessThanOrEqualToSourcePowerPredicate; -import mage.game.Game; -import mage.game.events.GameEvent; import mage.target.common.TargetCardInYourGraveyard; import java.util.UUID; @@ -48,7 +44,11 @@ public final class CarmenCruelSkymarcher extends CardImpl { this.addAbility(FlyingAbility.getInstance()); // Whenever a player sacrifices a permanent, put a +1/+1 counter on Carmen, Cruel Skymarcher and you gain 1 life. - this.addAbility(new CarmenTriggeredAbility()); + Ability sacTrigger = new SacrificePermanentTriggeredAbility(Zone.BATTLEFIELD, + new AddCountersSourceEffect(CounterType.P1P1.createInstance()), + StaticFilters.FILTER_PERMANENT, TargetController.ANY, SetTargetPointer.NONE, false); + sacTrigger.addEffect(new GainLifeEffect(1).concatBy("and")); + this.addAbility(sacTrigger); // Whenever Carmen attacks, return up to one target permanent card with mana value less than or equal to Carmen's power from your graveyard to the battlefield. Ability ability = new AttacksTriggeredAbility(new ReturnFromGraveyardToBattlefieldTargetEffect()); @@ -65,35 +65,3 @@ public final class CarmenCruelSkymarcher extends CardImpl { return new CarmenCruelSkymarcher(this); } } - -class CarmenTriggeredAbility extends TriggeredAbilityImpl { - - CarmenTriggeredAbility() { - super(Zone.BATTLEFIELD, new AddCountersSourceEffect(CounterType.P1P1.createInstance())); - this.addEffect(new GainLifeEffect(1)); - } - - private CarmenTriggeredAbility(final CarmenTriggeredAbility ability) { - super(ability); - } - - @Override - public boolean checkEventType(GameEvent event, Game game) { - return event.getType() == GameEvent.EventType.SACRIFICED_PERMANENT; - } - - @Override - public boolean checkTrigger(GameEvent event, Game game) { - return true; - } - - @Override - public CarmenTriggeredAbility copy() { - return new CarmenTriggeredAbility(this); - } - - @Override - public String getRule() { - return "Whenever a player sacrifices a permanent, put a +1/+1 counter on {this} and you gain 1 life."; - } -} diff --git a/Mage.Sets/src/mage/cards/c/CuriousCadaver.java b/Mage.Sets/src/mage/cards/c/CuriousCadaver.java index 82192240280..bb5dbcf71ff 100644 --- a/Mage.Sets/src/mage/cards/c/CuriousCadaver.java +++ b/Mage.Sets/src/mage/cards/c/CuriousCadaver.java @@ -6,9 +6,7 @@ import mage.abilities.effects.common.ReturnSourceFromGraveyardToHandEffect; import mage.abilities.keyword.FlyingAbility; import mage.cards.CardImpl; import mage.cards.CardSetInfo; -import mage.constants.CardType; -import mage.constants.SubType; -import mage.constants.Zone; +import mage.constants.*; import mage.filter.FilterPermanent; import mage.filter.common.FilterControlledPermanent; @@ -34,7 +32,8 @@ public final class CuriousCadaver extends CardImpl { // When you sacrifice a Clue, return Curious Cadaver from your graveyard to your hand. this.addAbility(new SacrificePermanentTriggeredAbility( - Zone.GRAVEYARD, new ReturnSourceFromGraveyardToHandEffect(), filter, false, false + Zone.GRAVEYARD, new ReturnSourceFromGraveyardToHandEffect(), filter, + TargetController.YOU, SetTargetPointer.NONE, false )); } diff --git a/Mage.Sets/src/mage/cards/d/DaringSleuth.java b/Mage.Sets/src/mage/cards/d/DaringSleuth.java index 17b46b4c60f..546e0a48ad4 100644 --- a/Mage.Sets/src/mage/cards/d/DaringSleuth.java +++ b/Mage.Sets/src/mage/cards/d/DaringSleuth.java @@ -1,17 +1,14 @@ - package mage.cards.d; import mage.MageInt; -import mage.abilities.TriggeredAbilityImpl; +import mage.abilities.common.SacrificePermanentTriggeredAbility; import mage.abilities.effects.common.TransformSourceEffect; import mage.abilities.keyword.TransformAbility; import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.CardType; import mage.constants.SubType; -import mage.constants.Zone; -import mage.game.Game; -import mage.game.events.GameEvent; +import mage.filter.FilterPermanent; import java.util.UUID; @@ -20,6 +17,8 @@ import java.util.UUID; */ public final class DaringSleuth extends CardImpl { + private static final FilterPermanent filter = new FilterPermanent(SubType.CLUE, "a Clue"); + public DaringSleuth(UUID ownerId, CardSetInfo setInfo) { super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{1}{U}"); this.subtype.add(SubType.HUMAN); @@ -31,7 +30,8 @@ public final class DaringSleuth extends CardImpl { // When you sacrifice a Clue, transform Daring Sleuth. this.addAbility(new TransformAbility()); - this.addAbility(new DaringSleuthTriggeredAbility()); + this.addAbility(new SacrificePermanentTriggeredAbility(new TransformSourceEffect(), filter) + .setTriggerPhrase("When you sacrifice a Clue, ")); } private DaringSleuth(final DaringSleuth card) { @@ -43,31 +43,3 @@ public final class DaringSleuth extends CardImpl { return new DaringSleuth(this); } } - -class DaringSleuthTriggeredAbility extends TriggeredAbilityImpl { - - public DaringSleuthTriggeredAbility() { - super(Zone.BATTLEFIELD, new TransformSourceEffect()); - setTriggerPhrase("When you sacrifice a Clue, "); - } - - private DaringSleuthTriggeredAbility(final DaringSleuthTriggeredAbility ability) { - super(ability); - } - - @Override - public DaringSleuthTriggeredAbility copy() { - return new DaringSleuthTriggeredAbility(this); - } - - @Override - public boolean checkEventType(GameEvent event, Game game) { - return event.getType() == GameEvent.EventType.SACRIFICED_PERMANENT; - } - - @Override - public boolean checkTrigger(GameEvent event, Game game) { - return event.getPlayerId().equals(this.getControllerId()) - && game.getLastKnownInformation(event.getTargetId(), Zone.BATTLEFIELD).hasSubtype(SubType.CLUE, game); - } -} diff --git a/Mage.Sets/src/mage/cards/d/DragonAppeasement.java b/Mage.Sets/src/mage/cards/d/DragonAppeasement.java index 557beeac7a8..f2ed52d82f5 100644 --- a/Mage.Sets/src/mage/cards/d/DragonAppeasement.java +++ b/Mage.Sets/src/mage/cards/d/DragonAppeasement.java @@ -1,17 +1,18 @@ - package mage.cards.d; -import java.util.UUID; -import mage.abilities.TriggeredAbilityImpl; +import mage.abilities.common.SacrificePermanentTriggeredAbility; import mage.abilities.common.SimpleStaticAbility; import mage.abilities.effects.common.DrawCardSourceControllerEffect; import mage.abilities.effects.common.SkipDrawStepEffect; import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.CardType; +import mage.constants.SetTargetPointer; +import mage.constants.TargetController; import mage.constants.Zone; -import mage.game.Game; -import mage.game.events.GameEvent; +import mage.filter.StaticFilters; + +import java.util.UUID; /** * @@ -26,7 +27,9 @@ public final class DragonAppeasement extends CardImpl { this.addAbility(new SimpleStaticAbility(Zone.BATTLEFIELD, new SkipDrawStepEffect())); // Whenever you sacrifice a creature, you may draw a card. - this.addAbility(new DragonAppeasementTriggeredAbility()); + this.addAbility(new SacrificePermanentTriggeredAbility(Zone.BATTLEFIELD, + new DrawCardSourceControllerEffect(1), StaticFilters.FILTER_PERMANENT_CREATURE, + TargetController.YOU, SetTargetPointer.NONE, true)); } @@ -39,32 +42,3 @@ public final class DragonAppeasement extends CardImpl { return new DragonAppeasement(this); } } - -class DragonAppeasementTriggeredAbility extends TriggeredAbilityImpl { - - public DragonAppeasementTriggeredAbility() { - super(Zone.BATTLEFIELD, new DrawCardSourceControllerEffect(1), true); - setLeavesTheBattlefieldTrigger(true); - setTriggerPhrase("Whenever you sacrifice a creature, "); - } - - private DragonAppeasementTriggeredAbility(final DragonAppeasementTriggeredAbility ability) { - super(ability); - } - - @Override - public DragonAppeasementTriggeredAbility copy() { - return new DragonAppeasementTriggeredAbility(this); - } - - @Override - public boolean checkEventType(GameEvent event, Game game) { - return event.getType() == GameEvent.EventType.SACRIFICED_PERMANENT; - } - - @Override - public boolean checkTrigger(GameEvent event, Game game) { - return event.getPlayerId().equals(this.getControllerId()) - && game.getLastKnownInformation(event.getTargetId(), Zone.BATTLEFIELD).isCreature(game); - } -} diff --git a/Mage.Sets/src/mage/cards/f/FleetingMemories.java b/Mage.Sets/src/mage/cards/f/FleetingMemories.java index 412197315ba..1a8009946da 100644 --- a/Mage.Sets/src/mage/cards/f/FleetingMemories.java +++ b/Mage.Sets/src/mage/cards/f/FleetingMemories.java @@ -1,23 +1,19 @@ - package mage.cards.f; -import java.util.UUID; import mage.abilities.Ability; -import mage.abilities.TriggeredAbilityImpl; import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.common.SacrificePermanentTriggeredAbility; import mage.abilities.effects.common.MillCardsTargetEffect; import mage.abilities.effects.keyword.InvestigateEffect; import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.CardType; import mage.constants.SubType; -import mage.constants.Zone; import mage.filter.common.FilterControlledPermanent; -import mage.game.Game; -import mage.game.events.GameEvent; -import mage.game.events.GameEvent.EventType; import mage.target.TargetPlayer; +import java.util.UUID; + /** * * @author LevelX2 @@ -37,7 +33,7 @@ public final class FleetingMemories extends CardImpl { this.addAbility(new EntersBattlefieldTriggeredAbility(new InvestigateEffect(), false)); // Whenever you sacrifice a Clue, target player puts the top three cards of their graveyard into their graveyard. - Ability ability = new FleetingMemoriesTriggeredAbility(); + Ability ability = new SacrificePermanentTriggeredAbility(new MillCardsTargetEffect(3), filter); ability.addTarget(new TargetPlayer()); this.addAbility(ability); } @@ -51,32 +47,3 @@ public final class FleetingMemories extends CardImpl { return new FleetingMemories(this); } } - -class FleetingMemoriesTriggeredAbility extends TriggeredAbilityImpl { - - public FleetingMemoriesTriggeredAbility() { - super(Zone.BATTLEFIELD, new MillCardsTargetEffect(3)); - setLeavesTheBattlefieldTrigger(true); - setTriggerPhrase("Whenever you sacrifice a Clue, "); - } - - private FleetingMemoriesTriggeredAbility(final FleetingMemoriesTriggeredAbility ability) { - super(ability); - } - - @Override - public FleetingMemoriesTriggeredAbility copy() { - return new FleetingMemoriesTriggeredAbility(this); - } - - @Override - public boolean checkEventType(GameEvent event, Game game) { - return event.getType() == GameEvent.EventType.SACRIFICED_PERMANENT; - } - - @Override - public boolean checkTrigger(GameEvent event, Game game) { - return event.getPlayerId().equals(this.getControllerId()) - && game.getLastKnownInformation(event.getTargetId(), Zone.BATTLEFIELD).hasSubtype(SubType.CLUE, game); - } -} \ No newline at end of file diff --git a/Mage.Sets/src/mage/cards/f/ForgeBoss.java b/Mage.Sets/src/mage/cards/f/ForgeBoss.java index 966591abf2a..30550b18158 100644 --- a/Mage.Sets/src/mage/cards/f/ForgeBoss.java +++ b/Mage.Sets/src/mage/cards/f/ForgeBoss.java @@ -1,17 +1,18 @@ package mage.cards.f; -import java.util.UUID; import mage.MageInt; -import mage.abilities.common.SacrificeAllTriggeredAbility; +import mage.abilities.common.SacrificePermanentTriggeredAbility; import mage.abilities.effects.common.DamagePlayersEffect; -import mage.constants.SubType; import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.CardType; +import mage.constants.SubType; import mage.constants.TargetController; import mage.filter.common.FilterCreaturePermanent; import mage.filter.predicate.mageobject.AnotherPredicate; +import java.util.UUID; + /** * * @author weirddan455 @@ -33,9 +34,8 @@ public final class ForgeBoss extends CardImpl { this.toughness = new MageInt(4); // Whenever you sacrifice one or more other creatures, Forge Boss deals 2 damage to each opponent. This ability triggers only once each turn. - this.addAbility(new SacrificeAllTriggeredAbility( - new DamagePlayersEffect(2, TargetController.OPPONENT), - filter, TargetController.YOU, false + this.addAbility(new SacrificePermanentTriggeredAbility( + new DamagePlayersEffect(2, TargetController.OPPONENT), filter ).setTriggersOnceEachTurn(true)); } diff --git a/Mage.Sets/src/mage/cards/f/ForgeNeverwinterCharlatan.java b/Mage.Sets/src/mage/cards/f/ForgeNeverwinterCharlatan.java index d81a70e87ce..aff0a0fd204 100644 --- a/Mage.Sets/src/mage/cards/f/ForgeNeverwinterCharlatan.java +++ b/Mage.Sets/src/mage/cards/f/ForgeNeverwinterCharlatan.java @@ -1,7 +1,7 @@ package mage.cards.f; import mage.MageInt; -import mage.abilities.common.SacrificeAllTriggeredAbility; +import mage.abilities.common.SacrificePermanentTriggeredAbility; import mage.abilities.common.SimpleStaticAbility; import mage.abilities.costs.common.SacrificeTargetCost; import mage.abilities.dynamicvalue.DynamicValue; @@ -53,9 +53,9 @@ public final class ForgeNeverwinterCharlatan extends CardImpl { ).setText("{this} gets +2/+0 for each Treasure you control")).addHint(hint)); // Whenever one or more players sacrifice one or more creatures, you create a tapped Treasure token. This ability triggers only once each turn. - this.addAbility(new SacrificeAllTriggeredAbility( + this.addAbility(new SacrificePermanentTriggeredAbility(Zone.BATTLEFIELD, new CreateTokenEffect(new TreasureToken(), 1, true), - StaticFilters.FILTER_PERMANENT_CREATURE, TargetController.ANY, false + StaticFilters.FILTER_PERMANENT_CREATURE, TargetController.ANY, SetTargetPointer.NONE, false ).setTriggersOnceEachTurn(true).setTriggerPhrase("Whenever one or more players sacrifice one or more creatures, ")); } diff --git a/Mage.Sets/src/mage/cards/f/FurnaceCelebration.java b/Mage.Sets/src/mage/cards/f/FurnaceCelebration.java index c2f378c7472..484a37433a5 100644 --- a/Mage.Sets/src/mage/cards/f/FurnaceCelebration.java +++ b/Mage.Sets/src/mage/cards/f/FurnaceCelebration.java @@ -1,30 +1,39 @@ - package mage.cards.f; -import java.util.UUID; -import mage.abilities.TriggeredAbilityImpl; -import mage.abilities.costs.mana.ManaCostsImpl; +import mage.abilities.Ability; +import mage.abilities.common.SacrificePermanentTriggeredAbility; +import mage.abilities.costs.mana.GenericManaCost; import mage.abilities.effects.common.DamageTargetEffect; import mage.abilities.effects.common.DoIfCostPaid; import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.CardType; -import mage.constants.Zone; -import mage.game.Game; -import mage.game.events.GameEvent; -import mage.game.events.GameEvent.EventType; +import mage.filter.FilterPermanent; +import mage.filter.predicate.mageobject.AnotherPredicate; import mage.target.common.TargetAnyTarget; +import java.util.UUID; + /** * * @author BetaSteward_at_googlemail.com */ public final class FurnaceCelebration extends CardImpl { + private static final FilterPermanent filter = new FilterPermanent("another permanent"); + + static { + filter.add(AnotherPredicate.instance); + } + public FurnaceCelebration(UUID ownerId, CardSetInfo setInfo) { super(ownerId,setInfo,new CardType[]{CardType.ENCHANTMENT},"{1}{R}{R}"); - this.addAbility(new FurnaceCelebrationAbility()); + // Whenever you sacrifice another permanent, you may pay {2}. If you do, Furnace Celebration deals 2 damage to any target. + Ability ability = new SacrificePermanentTriggeredAbility(new DoIfCostPaid( + new DamageTargetEffect(2), new GenericManaCost(2)), filter); + ability.addTarget(new TargetAnyTarget()); + this.addAbility(ability); } private FurnaceCelebration(final FurnaceCelebration card) { @@ -37,31 +46,3 @@ public final class FurnaceCelebration extends CardImpl { } } - -class FurnaceCelebrationAbility extends TriggeredAbilityImpl { - - public FurnaceCelebrationAbility() { - super(Zone.BATTLEFIELD, new DoIfCostPaid(new DamageTargetEffect(2), new ManaCostsImpl<>("{2}"))); - this.addTarget(new TargetAnyTarget()); - setTriggerPhrase("Whenever you sacrifice another permanent, "); - } - - private FurnaceCelebrationAbility(final FurnaceCelebrationAbility ability) { - super(ability); - } - - @Override - public FurnaceCelebrationAbility copy() { - return new FurnaceCelebrationAbility(this); - } - - @Override - public boolean checkEventType(GameEvent event, Game game) { - return event.getType() == GameEvent.EventType.SACRIFICED_PERMANENT; - } - - @Override - public boolean checkTrigger(GameEvent event, Game game) { - return event.getPlayerId().equals(this.getControllerId()) && !event.getTargetId().equals(sourceId); - } -} \ No newline at end of file diff --git a/Mage.Sets/src/mage/cards/g/GrafMole.java b/Mage.Sets/src/mage/cards/g/GrafMole.java index 282e31ce219..a18271cc000 100644 --- a/Mage.Sets/src/mage/cards/g/GrafMole.java +++ b/Mage.Sets/src/mage/cards/g/GrafMole.java @@ -1,18 +1,15 @@ - package mage.cards.g; -import java.util.UUID; import mage.MageInt; -import mage.abilities.TriggeredAbilityImpl; +import mage.abilities.common.SacrificePermanentTriggeredAbility; import mage.abilities.effects.common.GainLifeEffect; import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.CardType; import mage.constants.SubType; -import mage.constants.Zone; -import mage.game.Game; -import mage.game.events.GameEvent; -import mage.game.events.GameEvent.EventType; +import mage.filter.FilterPermanent; + +import java.util.UUID; /** * @@ -20,6 +17,8 @@ import mage.game.events.GameEvent.EventType; */ public final class GrafMole extends CardImpl { + private static final FilterPermanent filter = new FilterPermanent(SubType.CLUE, "a Clue"); + public GrafMole(UUID ownerId, CardSetInfo setInfo) { super(ownerId,setInfo,new CardType[]{CardType.CREATURE},"{2}{G}"); this.subtype.add(SubType.MOLE); @@ -28,7 +27,7 @@ public final class GrafMole extends CardImpl { this.toughness = new MageInt(4); // Whenever you sacrifice a Clue, you gain 3 life. - this.addAbility(new GrafMoleTriggeredAbility()); + this.addAbility(new SacrificePermanentTriggeredAbility(new GainLifeEffect(3), filter)); } private GrafMole(final GrafMole card) { @@ -40,32 +39,3 @@ public final class GrafMole extends CardImpl { return new GrafMole(this); } } - -class GrafMoleTriggeredAbility extends TriggeredAbilityImpl { - - public GrafMoleTriggeredAbility() { - super(Zone.BATTLEFIELD, new GainLifeEffect(3)); - setLeavesTheBattlefieldTrigger(true); - setTriggerPhrase("Whenever you sacrifice a Clue, "); - } - - private GrafMoleTriggeredAbility(final GrafMoleTriggeredAbility ability) { - super(ability); - } - - @Override - public GrafMoleTriggeredAbility copy() { - return new GrafMoleTriggeredAbility(this); - } - - @Override - public boolean checkEventType(GameEvent event, Game game) { - return event.getType() == GameEvent.EventType.SACRIFICED_PERMANENT; - } - - @Override - public boolean checkTrigger(GameEvent event, Game game) { - return event.getPlayerId().equals(this.getControllerId()) - && game.getLastKnownInformation(event.getTargetId(), Zone.BATTLEFIELD).hasSubtype(SubType.CLUE, game); - } -} diff --git a/Mage.Sets/src/mage/cards/h/HavocJester.java b/Mage.Sets/src/mage/cards/h/HavocJester.java index ffa1ab353ec..736585edefe 100644 --- a/Mage.Sets/src/mage/cards/h/HavocJester.java +++ b/Mage.Sets/src/mage/cards/h/HavocJester.java @@ -1,15 +1,14 @@ package mage.cards.h; import mage.MageInt; -import mage.abilities.TriggeredAbilityImpl; +import mage.abilities.Ability; +import mage.abilities.common.SacrificePermanentTriggeredAbility; import mage.abilities.effects.common.DamageTargetEffect; import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.CardType; import mage.constants.SubType; -import mage.constants.Zone; -import mage.game.Game; -import mage.game.events.GameEvent; +import mage.filter.StaticFilters; import mage.target.common.TargetAnyTarget; import java.util.UUID; @@ -27,7 +26,9 @@ public final class HavocJester extends CardImpl { this.toughness = new MageInt(5); // Whenever you sacrifice a permanent, Havoc Jester deals 1 damage to any target. - this.addAbility(new HavocJesterTriggeredAbility()); + Ability ability = new SacrificePermanentTriggeredAbility(new DamageTargetEffect(1), StaticFilters.FILTER_PERMANENT); + ability.addTarget(new TargetAnyTarget()); + this.addAbility(ability); } private HavocJester(final HavocJester card) { @@ -39,35 +40,3 @@ public final class HavocJester extends CardImpl { return new HavocJester(this); } } - -class HavocJesterTriggeredAbility extends TriggeredAbilityImpl { - - HavocJesterTriggeredAbility() { - super(Zone.BATTLEFIELD, new DamageTargetEffect(1)); - this.addTarget(new TargetAnyTarget()); - } - - private HavocJesterTriggeredAbility(final HavocJesterTriggeredAbility ability) { - super(ability); - } - - @Override - public boolean checkEventType(GameEvent event, Game game) { - return event.getType() == GameEvent.EventType.SACRIFICED_PERMANENT; - } - - @Override - public boolean checkTrigger(GameEvent event, Game game) { - return event.getPlayerId().equals(getControllerId()); - } - - @Override - public HavocJesterTriggeredAbility copy() { - return new HavocJesterTriggeredAbility(this); - } - - @Override - public String getRule() { - return "Whenever you sacrifice a permanent, {this} deals 1 damage to any target."; - } -} diff --git a/Mage.Sets/src/mage/cards/i/ItThatBetrays.java b/Mage.Sets/src/mage/cards/i/ItThatBetrays.java index 866c8b2165c..52e1e58bec5 100644 --- a/Mage.Sets/src/mage/cards/i/ItThatBetrays.java +++ b/Mage.Sets/src/mage/cards/i/ItThatBetrays.java @@ -1,13 +1,12 @@ package mage.cards.i; import mage.MageInt; -import mage.abilities.common.OpponentSacrificesNonTokenPermanentTriggeredAbility; +import mage.abilities.common.SacrificePermanentTriggeredAbility; import mage.abilities.effects.common.ReturnToBattlefieldUnderYourControlTargetEffect; import mage.abilities.keyword.AnnihilatorAbility; import mage.cards.CardImpl; import mage.cards.CardSetInfo; -import mage.constants.CardType; -import mage.constants.SubType; +import mage.constants.*; import mage.filter.FilterPermanent; import mage.filter.predicate.permanent.TokenPredicate; @@ -18,10 +17,10 @@ import java.util.UUID; */ public final class ItThatBetrays extends CardImpl { - private static final FilterPermanent FILTER = new FilterPermanent("nontoken permanent"); + private static final FilterPermanent filter = new FilterPermanent("nontoken permanent"); static { - FILTER.add(TokenPredicate.FALSE); + filter.add(TokenPredicate.FALSE); } public ItThatBetrays(UUID ownerId, CardSetInfo setInfo) { @@ -35,9 +34,10 @@ public final class ItThatBetrays extends CardImpl { this.addAbility(new AnnihilatorAbility(2)); // Whenever an opponent sacrifices a nontoken permanent, put that card onto the battlefield under your control. - this.addAbility(new OpponentSacrificesNonTokenPermanentTriggeredAbility( + this.addAbility(new SacrificePermanentTriggeredAbility(Zone.BATTLEFIELD, new ReturnToBattlefieldUnderYourControlTargetEffect() - .setText("put that card onto the battlefield under your control") + .setText("put that card onto the battlefield under your control"), + filter, TargetController.OPPONENT, SetTargetPointer.PERMANENT, false )); } diff --git a/Mage.Sets/src/mage/cards/j/JuriMasterOfTheRevue.java b/Mage.Sets/src/mage/cards/j/JuriMasterOfTheRevue.java index 63f29e2cca1..8721932fedb 100644 --- a/Mage.Sets/src/mage/cards/j/JuriMasterOfTheRevue.java +++ b/Mage.Sets/src/mage/cards/j/JuriMasterOfTheRevue.java @@ -14,6 +14,7 @@ import mage.constants.CardType; import mage.constants.SubType; import mage.constants.SuperType; import mage.counters.CounterType; +import mage.filter.StaticFilters; import mage.game.Game; import mage.game.permanent.Permanent; import mage.target.common.TargetAnyTarget; @@ -36,7 +37,7 @@ public final class JuriMasterOfTheRevue extends CardImpl { // Whenever you sacrifice a permanent, put a +1/+1 counter on Juri, Master of the Revue. this.addAbility(new SacrificePermanentTriggeredAbility( - new AddCountersSourceEffect(CounterType.P1P1.createInstance()) + new AddCountersSourceEffect(CounterType.P1P1.createInstance()), StaticFilters.FILTER_PERMANENT_A )); // When Juri dies, it deals damage equal its power to any target. @@ -74,4 +75,4 @@ enum JuriMasterOfTheRevueValue implements DynamicValue { public String getMessage() { return ""; } -} \ No newline at end of file +} diff --git a/Mage.Sets/src/mage/cards/k/KelsFightFixer.java b/Mage.Sets/src/mage/cards/k/KelsFightFixer.java index e4b8e278ccb..da1e6ce36b7 100644 --- a/Mage.Sets/src/mage/cards/k/KelsFightFixer.java +++ b/Mage.Sets/src/mage/cards/k/KelsFightFixer.java @@ -2,7 +2,7 @@ package mage.cards.k; import mage.MageInt; import mage.abilities.Ability; -import mage.abilities.TriggeredAbilityImpl; +import mage.abilities.common.SacrificePermanentTriggeredAbility; import mage.abilities.common.SimpleActivatedAbility; import mage.abilities.costs.common.SacrificeTargetCost; import mage.abilities.costs.mana.GenericManaCost; @@ -14,11 +14,11 @@ import mage.abilities.keyword.IndestructibleAbility; import mage.abilities.keyword.MenaceAbility; import mage.cards.CardImpl; import mage.cards.CardSetInfo; -import mage.constants.*; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; +import mage.constants.SuperType; import mage.filter.StaticFilters; -import mage.game.Game; -import mage.game.events.GameEvent; -import mage.target.common.TargetControlledPermanent; import java.util.UUID; @@ -40,7 +40,10 @@ public final class KelsFightFixer extends CardImpl { this.addAbility(new MenaceAbility(false)); // Whenever you sacrifice a creature, you may pay {U/B}. If you do, draw a card. - this.addAbility(new KelsFightFixerTriggeredAbility()); + this.addAbility(new SacrificePermanentTriggeredAbility( + new DoIfCostPaid(new DrawCardSourceControllerEffect(1), new ManaCostsImpl<>("{U/B}")), + StaticFilters.FILTER_PERMANENT_CREATURE + )); // {1}, Sacrifice a creature: Kels, Fight Fixer gains indestructible until end of turn. Ability ability = new SimpleActivatedAbility(new GainAbilitySourceEffect( @@ -59,32 +62,3 @@ public final class KelsFightFixer extends CardImpl { return new KelsFightFixer(this); } } - -class KelsFightFixerTriggeredAbility extends TriggeredAbilityImpl { - - KelsFightFixerTriggeredAbility() { - super(Zone.BATTLEFIELD, new DoIfCostPaid(new DrawCardSourceControllerEffect(1), new ManaCostsImpl<>("{U/B}")), false); - setLeavesTheBattlefieldTrigger(true); - setTriggerPhrase("Whenever you sacrifice a creature, "); - } - - private KelsFightFixerTriggeredAbility(final KelsFightFixerTriggeredAbility ability) { - super(ability); - } - - @Override - public KelsFightFixerTriggeredAbility copy() { - return new KelsFightFixerTriggeredAbility(this); - } - - @Override - public boolean checkEventType(GameEvent event, Game game) { - return event.getType() == GameEvent.EventType.SACRIFICED_PERMANENT; - } - - @Override - public boolean checkTrigger(GameEvent event, Game game) { - return event.getPlayerId().equals(this.getControllerId()) - && game.getLastKnownInformation(event.getTargetId(), Zone.BATTLEFIELD).isCreature(game); - } -} diff --git a/Mage.Sets/src/mage/cards/k/KorvoldFaeCursedKing.java b/Mage.Sets/src/mage/cards/k/KorvoldFaeCursedKing.java index 7b1a60d8ace..f2fd40b4b93 100644 --- a/Mage.Sets/src/mage/cards/k/KorvoldFaeCursedKing.java +++ b/Mage.Sets/src/mage/cards/k/KorvoldFaeCursedKing.java @@ -1,8 +1,9 @@ package mage.cards.k; import mage.MageInt; -import mage.abilities.TriggeredAbilityImpl; +import mage.abilities.Ability; import mage.abilities.common.EntersBattlefieldOrAttacksSourceTriggeredAbility; +import mage.abilities.common.SacrificePermanentTriggeredAbility; import mage.abilities.effects.common.DrawCardSourceControllerEffect; import mage.abilities.effects.common.SacrificeControllerEffect; import mage.abilities.effects.common.counter.AddCountersSourceEffect; @@ -12,12 +13,10 @@ import mage.cards.CardSetInfo; import mage.constants.CardType; import mage.constants.SubType; import mage.constants.SuperType; -import mage.constants.Zone; import mage.counters.CounterType; import mage.filter.FilterPermanent; +import mage.filter.StaticFilters; import mage.filter.predicate.mageobject.AnotherPredicate; -import mage.game.Game; -import mage.game.events.GameEvent; import java.util.UUID; @@ -50,7 +49,11 @@ public final class KorvoldFaeCursedKing extends CardImpl { )); // Whenever you sacrifice a permanent, put a +1/+1 counter on Korvold and draw a card. - this.addAbility(new KorvoldFaeCursedKingAbility()); + Ability ability = new SacrificePermanentTriggeredAbility( + new AddCountersSourceEffect(CounterType.P1P1.createInstance()), + StaticFilters.FILTER_PERMANENT); + ability.addEffect(new DrawCardSourceControllerEffect(1).concatBy("and")); + this.addAbility(ability); } private KorvoldFaeCursedKing(final KorvoldFaeCursedKing card) { @@ -62,35 +65,3 @@ public final class KorvoldFaeCursedKing extends CardImpl { return new KorvoldFaeCursedKing(this); } } - -class KorvoldFaeCursedKingAbility extends TriggeredAbilityImpl { - - KorvoldFaeCursedKingAbility() { - super(Zone.BATTLEFIELD, new AddCountersSourceEffect(CounterType.P1P1.createInstance())); - this.addEffect(new DrawCardSourceControllerEffect(1)); - } - - private KorvoldFaeCursedKingAbility(final KorvoldFaeCursedKingAbility ability) { - super(ability); - } - - @Override - public KorvoldFaeCursedKingAbility copy() { - return new KorvoldFaeCursedKingAbility(this); - } - - @Override - public boolean checkEventType(GameEvent event, Game game) { - return event.getType() == GameEvent.EventType.SACRIFICED_PERMANENT; - } - - @Override - public boolean checkTrigger(GameEvent event, Game game) { - return this.isControlledBy(event.getPlayerId()); - } - - @Override - public String getRule() { - return "Whenever you sacrifice a permanent, put a +1/+1 counter on {this} and draw a card."; - } -} \ No newline at end of file diff --git a/Mage.Sets/src/mage/cards/m/MalikGrimManipulator.java b/Mage.Sets/src/mage/cards/m/MalikGrimManipulator.java index acdeffa60a7..cdf735b6276 100644 --- a/Mage.Sets/src/mage/cards/m/MalikGrimManipulator.java +++ b/Mage.Sets/src/mage/cards/m/MalikGrimManipulator.java @@ -3,7 +3,7 @@ package mage.cards.m; import mage.MageInt; import mage.abilities.Ability; import mage.abilities.common.EntersBattlefieldTriggeredAbility; -import mage.abilities.common.SacrificeAllTriggeredAbility; +import mage.abilities.common.SacrificePermanentTriggeredAbility; import mage.abilities.effects.OneShotEffect; import mage.abilities.effects.common.CreateTokenEffect; import mage.cards.CardImpl; @@ -20,7 +20,10 @@ import mage.players.Player; import mage.target.TargetPermanent; import mage.target.common.TargetOpponent; -import java.util.*; +import java.util.LinkedHashSet; +import java.util.Objects; +import java.util.Set; +import java.util.UUID; /** * @author TheElk801 @@ -42,10 +45,10 @@ public final class MalikGrimManipulator extends CardImpl { this.addAbility(ability); // Whenever an opponent sacrifices a creature, you create a Treasure token. - this.addAbility(new SacrificeAllTriggeredAbility( + this.addAbility(new SacrificePermanentTriggeredAbility(Zone.BATTLEFIELD, new CreateTokenEffect(new TreasureToken()).setText("you create a Treasure token"), StaticFilters.FILTER_PERMANENT_A_CREATURE, - TargetController.OPPONENT, false + TargetController.OPPONENT, SetTargetPointer.NONE, false )); } diff --git a/Mage.Sets/src/mage/cards/m/MayhemDevil.java b/Mage.Sets/src/mage/cards/m/MayhemDevil.java index 0e4a5fa4807..2e112117296 100644 --- a/Mage.Sets/src/mage/cards/m/MayhemDevil.java +++ b/Mage.Sets/src/mage/cards/m/MayhemDevil.java @@ -1,15 +1,13 @@ package mage.cards.m; import mage.MageInt; -import mage.abilities.TriggeredAbilityImpl; +import mage.abilities.Ability; +import mage.abilities.common.SacrificePermanentTriggeredAbility; import mage.abilities.effects.common.DamageTargetEffect; import mage.cards.CardImpl; import mage.cards.CardSetInfo; -import mage.constants.CardType; -import mage.constants.SubType; -import mage.constants.Zone; -import mage.game.Game; -import mage.game.events.GameEvent; +import mage.constants.*; +import mage.filter.StaticFilters; import mage.target.common.TargetAnyTarget; import java.util.UUID; @@ -27,7 +25,11 @@ public final class MayhemDevil extends CardImpl { this.toughness = new MageInt(3); // Whenever a player sacrifices a permanent, Mayhem Devil deals 1 damage to any target. - this.addAbility(new MayhemDevilTriggeredAbility()); + Ability ability = new SacrificePermanentTriggeredAbility(Zone.BATTLEFIELD, + new DamageTargetEffect(1), StaticFilters.FILTER_PERMANENT, + TargetController.ANY, SetTargetPointer.NONE, false); + ability.addTarget(new TargetAnyTarget()); + this.addAbility(ability); } private MayhemDevil(final MayhemDevil card) { @@ -39,35 +41,3 @@ public final class MayhemDevil extends CardImpl { return new MayhemDevil(this); } } - -class MayhemDevilTriggeredAbility extends TriggeredAbilityImpl { - - MayhemDevilTriggeredAbility() { - super(Zone.BATTLEFIELD, new DamageTargetEffect(1)); - this.addTarget(new TargetAnyTarget()); - } - - private MayhemDevilTriggeredAbility(final MayhemDevilTriggeredAbility ability) { - super(ability); - } - - @Override - public boolean checkEventType(GameEvent event, Game game) { - return event.getType() == GameEvent.EventType.SACRIFICED_PERMANENT; - } - - @Override - public boolean checkTrigger(GameEvent event, Game game) { - return true; - } - - @Override - public MayhemDevilTriggeredAbility copy() { - return new MayhemDevilTriggeredAbility(this); - } - - @Override - public String getRule() { - return "Whenever a player sacrifices a permanent, {this} deals 1 damage to any target."; - } -} \ No newline at end of file diff --git a/Mage.Sets/src/mage/cards/m/MazirekKraulDeathPriest.java b/Mage.Sets/src/mage/cards/m/MazirekKraulDeathPriest.java index 76953d86528..111ba402199 100644 --- a/Mage.Sets/src/mage/cards/m/MazirekKraulDeathPriest.java +++ b/Mage.Sets/src/mage/cards/m/MazirekKraulDeathPriest.java @@ -1,24 +1,18 @@ - package mage.cards.m; -import java.util.UUID; import mage.MageInt; -import mage.MageObject; -import mage.abilities.TriggeredAbilityImpl; -import mage.abilities.effects.Effect; +import mage.abilities.common.SacrificePermanentTriggeredAbility; import mage.abilities.effects.common.counter.AddCountersAllEffect; import mage.abilities.keyword.FlyingAbility; import mage.cards.CardImpl; import mage.cards.CardSetInfo; -import mage.constants.CardType; -import mage.constants.SubType; -import mage.constants.SuperType; -import mage.constants.Zone; +import mage.constants.*; import mage.counters.CounterType; -import mage.filter.common.FilterControlledCreaturePermanent; -import mage.game.Game; -import mage.game.events.GameEvent; -import mage.game.events.GameEvent.EventType; +import mage.filter.FilterPermanent; +import mage.filter.StaticFilters; +import mage.filter.predicate.mageobject.AnotherPredicate; + +import java.util.UUID; /** * @@ -26,6 +20,12 @@ import mage.game.events.GameEvent.EventType; */ public final class MazirekKraulDeathPriest extends CardImpl { + private static final FilterPermanent filter = new FilterPermanent("another permanent"); + + static { + filter.add(AnotherPredicate.instance); + } + public MazirekKraulDeathPriest(UUID ownerId, CardSetInfo setInfo) { super(ownerId,setInfo,new CardType[]{CardType.CREATURE},"{3}{B}{G}"); this.supertype.add(SuperType.LEGENDARY); @@ -38,7 +38,9 @@ public final class MazirekKraulDeathPriest extends CardImpl { this.addAbility(FlyingAbility.getInstance()); // Whenever a player sacrifices another permanent, put a +1/+1 counter on each creature you control. - this.addAbility(new PlayerSacrificesPermanentTriggeredAbility(new AddCountersAllEffect(CounterType.P1P1.createInstance(), new FilterControlledCreaturePermanent()), false)); + this.addAbility(new SacrificePermanentTriggeredAbility(Zone.BATTLEFIELD, + new AddCountersAllEffect(CounterType.P1P1.createInstance(), StaticFilters.FILTER_CONTROLLED_CREATURE), + filter, TargetController.ANY, SetTargetPointer.NONE, false)); } private MazirekKraulDeathPriest(final MazirekKraulDeathPriest card) { @@ -50,31 +52,3 @@ public final class MazirekKraulDeathPriest extends CardImpl { return new MazirekKraulDeathPriest(this); } } - -class PlayerSacrificesPermanentTriggeredAbility extends TriggeredAbilityImpl { - - public PlayerSacrificesPermanentTriggeredAbility(Effect effect, boolean optional) { - super(Zone.BATTLEFIELD, effect, optional); - setTriggerPhrase("Whenever a player sacrifices another permanent, "); - } - - private PlayerSacrificesPermanentTriggeredAbility(final PlayerSacrificesPermanentTriggeredAbility ability) { - super(ability); - } - - @Override - public boolean checkEventType(GameEvent event, Game game) { - return event.getType() == GameEvent.EventType.SACRIFICED_PERMANENT; - } - - @Override - public boolean checkTrigger(GameEvent event, Game game) { - MageObject mageObject = game.getLastKnownInformation(event.getTargetId(), Zone.BATTLEFIELD); - return mageObject != null && !event.getTargetId().equals(this.getSourceId()); - } - - @Override - public PlayerSacrificesPermanentTriggeredAbility copy() { - return new PlayerSacrificesPermanentTriggeredAbility(this); - } -} diff --git a/Mage.Sets/src/mage/cards/m/MorticianBeetle.java b/Mage.Sets/src/mage/cards/m/MorticianBeetle.java index c2acf110d14..26e5cfafe21 100644 --- a/Mage.Sets/src/mage/cards/m/MorticianBeetle.java +++ b/Mage.Sets/src/mage/cards/m/MorticianBeetle.java @@ -1,20 +1,15 @@ - package mage.cards.m; -import java.util.UUID; import mage.MageInt; -import mage.MageObject; -import mage.abilities.TriggeredAbilityImpl; -import mage.abilities.effects.Effect; +import mage.abilities.common.SacrificePermanentTriggeredAbility; import mage.abilities.effects.common.counter.AddCountersSourceEffect; import mage.cards.CardImpl; import mage.cards.CardSetInfo; -import mage.constants.CardType; -import mage.constants.SubType; -import mage.constants.Zone; +import mage.constants.*; import mage.counters.CounterType; -import mage.game.Game; -import mage.game.events.GameEvent; +import mage.filter.StaticFilters; + +import java.util.UUID; /** * @@ -30,7 +25,9 @@ public final class MorticianBeetle extends CardImpl { this.toughness = new MageInt(1); // Whenever a player sacrifices a creature, you may put a +1/+1 counter on Mortician Beetle. - this.addAbility(new PlayerSacrificesCreatureTriggeredAbility(new AddCountersSourceEffect(CounterType.P1P1.createInstance()), true)); + this.addAbility(new SacrificePermanentTriggeredAbility(Zone.BATTLEFIELD, + new AddCountersSourceEffect(CounterType.P1P1.createInstance()), StaticFilters.FILTER_PERMANENT_CREATURE, + TargetController.ANY, SetTargetPointer.NONE, true)); } private MorticianBeetle(final MorticianBeetle card) { @@ -42,34 +39,3 @@ public final class MorticianBeetle extends CardImpl { return new MorticianBeetle(this); } } - -class PlayerSacrificesCreatureTriggeredAbility extends TriggeredAbilityImpl { - - public PlayerSacrificesCreatureTriggeredAbility(Effect effect, boolean optional) { - super(Zone.BATTLEFIELD, effect, optional); - setTriggerPhrase("Whenever a player sacrifices a creature, "); - } - - private PlayerSacrificesCreatureTriggeredAbility(final PlayerSacrificesCreatureTriggeredAbility ability) { - super(ability); - } - - @Override - public boolean checkEventType(GameEvent event, Game game) { - return event.getType() == GameEvent.EventType.SACRIFICED_PERMANENT; - } - - @Override - public boolean checkTrigger(GameEvent event, Game game) { - MageObject mageObject = game.getLastKnownInformation(event.getTargetId(), Zone.BATTLEFIELD); - if (mageObject != null && mageObject.isCreature(game)) { - return true; - } - return false; - } - - @Override - public PlayerSacrificesCreatureTriggeredAbility copy() { - return new PlayerSacrificesCreatureTriggeredAbility(this); - } -} \ No newline at end of file diff --git a/Mage.Sets/src/mage/cards/n/NazgulBattleMace.java b/Mage.Sets/src/mage/cards/n/NazgulBattleMace.java index 1c286b23c81..71530e1acd0 100644 --- a/Mage.Sets/src/mage/cards/n/NazgulBattleMace.java +++ b/Mage.Sets/src/mage/cards/n/NazgulBattleMace.java @@ -1,7 +1,7 @@ package mage.cards.n; import mage.abilities.Ability; -import mage.abilities.common.OpponentSacrificesNonTokenPermanentTriggeredAbility; +import mage.abilities.common.SacrificePermanentTriggeredAbility; import mage.abilities.common.SimpleStaticAbility; import mage.abilities.costs.common.PayLifeCost; import mage.abilities.effects.common.DoUnlessTargetPlayerOrTargetsControllerPaysEffect; @@ -13,10 +13,9 @@ import mage.abilities.keyword.EquipAbility; import mage.abilities.keyword.MenaceAbility; import mage.cards.CardImpl; import mage.cards.CardSetInfo; -import mage.constants.AttachmentType; -import mage.constants.CardType; -import mage.constants.SubType; -import mage.constants.Zone; +import mage.constants.*; +import mage.filter.FilterPermanent; +import mage.filter.predicate.permanent.TokenPredicate; import java.util.UUID; @@ -26,25 +25,33 @@ import java.util.UUID; */ public final class NazgulBattleMace extends CardImpl { + private static final FilterPermanent filter = new FilterPermanent("nontoken permanent"); + + static { + filter.add(TokenPredicate.FALSE); + } + public NazgulBattleMace(UUID ownerId, CardSetInfo setInfo) { super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT}, "{5}"); this.subtype.add(SubType.EQUIPMENT); - //String abilityText = "Whenever an opponent sacrifices a nontoken permanent, put that card onto the battlefield under your control unless that player pays 3 life"; // Equipped creature has menace, deathtouch, annihilator 1, and // "Whenever an opponent sacrifices a nontoken permanent, put that card onto the battlefield under your control unless that player pays 3 life." Ability ability = new SimpleStaticAbility(Zone.BATTLEFIELD, new GainAbilityAttachedEffect(new MenaceAbility(false), AttachmentType.EQUIPMENT)); ability.addEffect(new GainAbilityAttachedEffect(DeathtouchAbility.getInstance(), AttachmentType.EQUIPMENT).setText(", deathtouch")); ability.addEffect(new GainAbilityAttachedEffect(new AnnihilatorAbility(1), AttachmentType.EQUIPMENT).setText(", annihilator 1")); - Ability sacTriggerAbility = new OpponentSacrificesNonTokenPermanentTriggeredAbility( + Ability sacTriggerAbility = new SacrificePermanentTriggeredAbility(Zone.BATTLEFIELD, new DoUnlessTargetPlayerOrTargetsControllerPaysEffect( new ReturnToBattlefieldUnderYourControlTargetEffect(), new PayLifeCost(3) - ).setText("put that card onto the battlefield under your control unless that player pays 3 life")); + ).setText("put that card onto the battlefield under your control unless that player pays 3 life"), + filter, TargetController.OPPONENT, SetTargetPointer.PERMANENT, false + ); ability.addEffect(new GainAbilityAttachedEffect(sacTriggerAbility, AttachmentType.EQUIPMENT) - .setText(", and \""+sacTriggerAbility.getRule()+"\"") + .setText(", and \"" + sacTriggerAbility.getRule() + "\"") ); this.addAbility(ability); + // Equip {3} this.addAbility(new EquipAbility(3, false)); } diff --git a/Mage.Sets/src/mage/cards/p/ProwlingGeistcatcher.java b/Mage.Sets/src/mage/cards/p/ProwlingGeistcatcher.java index d59beb73a90..093c234e451 100644 --- a/Mage.Sets/src/mage/cards/p/ProwlingGeistcatcher.java +++ b/Mage.Sets/src/mage/cards/p/ProwlingGeistcatcher.java @@ -8,10 +8,7 @@ import mage.abilities.effects.common.ExileTargetForSourceEffect; import mage.abilities.effects.common.ReturnFromExileForSourceEffect; import mage.cards.CardImpl; import mage.cards.CardSetInfo; -import mage.constants.CardType; -import mage.constants.Outcome; -import mage.constants.SubType; -import mage.constants.Zone; +import mage.constants.*; import mage.counters.CounterType; import mage.filter.StaticFilters; import mage.game.Game; @@ -34,9 +31,9 @@ public final class ProwlingGeistcatcher extends CardImpl { this.toughness = new MageInt(4); // Whenever you sacrifice another creature, exile it. If that creature was a token, put a +1/+1 counter on Prowling Geistcatcher. - this.addAbility(new SacrificePermanentTriggeredAbility( + this.addAbility(new SacrificePermanentTriggeredAbility(Zone.BATTLEFIELD, new ProwlingGeistcatcherExileEffect(), - StaticFilters.FILTER_CONTROLLED_ANOTHER_CREATURE, true + StaticFilters.FILTER_CONTROLLED_ANOTHER_CREATURE, TargetController.YOU, SetTargetPointer.PERMANENT, false )); // When Prowling Geistcatcher leaves the battlefield, return each card exiled with it to the battlefield under your control. diff --git a/Mage.Sets/src/mage/cards/r/RuthlessDeathfang.java b/Mage.Sets/src/mage/cards/r/RuthlessDeathfang.java index 614fb8392d2..a47c7e6b43c 100644 --- a/Mage.Sets/src/mage/cards/r/RuthlessDeathfang.java +++ b/Mage.Sets/src/mage/cards/r/RuthlessDeathfang.java @@ -1,22 +1,19 @@ - package mage.cards.r; -import java.util.UUID; import mage.MageInt; import mage.abilities.Ability; -import mage.abilities.TriggeredAbilityImpl; +import mage.abilities.common.SacrificePermanentTriggeredAbility; import mage.abilities.effects.common.SacrificeEffect; import mage.abilities.keyword.FlyingAbility; import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.CardType; import mage.constants.SubType; -import mage.constants.Zone; import mage.filter.StaticFilters; -import mage.game.Game; -import mage.game.events.GameEvent; import mage.target.common.TargetOpponent; +import java.util.UUID; + /** * * @author fireshoes @@ -33,7 +30,10 @@ public final class RuthlessDeathfang extends CardImpl { this.addAbility(FlyingAbility.getInstance()); // Whenever you sacrifice a creature, target opponent sacrifices a creature. - Ability ability = new RuthlessDeathfangTriggeredAbility(); + Ability ability = new SacrificePermanentTriggeredAbility( + new SacrificeEffect(StaticFilters.FILTER_PERMANENT_CREATURE, 1, "target opponent"), + StaticFilters.FILTER_PERMANENT_CREATURE + ); ability.addTarget(new TargetOpponent()); this.addAbility(ability); } @@ -47,32 +47,3 @@ public final class RuthlessDeathfang extends CardImpl { return new RuthlessDeathfang(this); } } - -class RuthlessDeathfangTriggeredAbility extends TriggeredAbilityImpl { - - public RuthlessDeathfangTriggeredAbility() { - super(Zone.BATTLEFIELD, new SacrificeEffect(StaticFilters.FILTER_PERMANENT_CREATURE, 1, "target opponent"), false); - setLeavesTheBattlefieldTrigger(true); - setTriggerPhrase("Whenever you sacrifice a creature, "); - } - - private RuthlessDeathfangTriggeredAbility(final RuthlessDeathfangTriggeredAbility ability) { - super(ability); - } - - @Override - public RuthlessDeathfangTriggeredAbility copy() { - return new RuthlessDeathfangTriggeredAbility(this); - } - - @Override - public boolean checkEventType(GameEvent event, Game game) { - return event.getType() == GameEvent.EventType.SACRIFICED_PERMANENT; - } - - @Override - public boolean checkTrigger(GameEvent event, Game game) { - return event.getPlayerId().equals(this.getControllerId()) - && game.getLastKnownInformation(event.getTargetId(), Zone.BATTLEFIELD).isCreature(game); - } -} diff --git a/Mage.Sets/src/mage/cards/s/SanguineStatuette.java b/Mage.Sets/src/mage/cards/s/SanguineStatuette.java index 270575fb1e2..e4f3f10dbbe 100644 --- a/Mage.Sets/src/mage/cards/s/SanguineStatuette.java +++ b/Mage.Sets/src/mage/cards/s/SanguineStatuette.java @@ -7,9 +7,7 @@ import mage.abilities.effects.common.continuous.BecomesCreatureSourceEffect; import mage.abilities.keyword.HasteAbility; import mage.cards.CardImpl; import mage.cards.CardSetInfo; -import mage.constants.CardType; -import mage.constants.Duration; -import mage.constants.SubType; +import mage.constants.*; import mage.filter.FilterPermanent; import mage.filter.common.FilterControlledPermanent; import mage.filter.predicate.permanent.TokenPredicate; @@ -36,13 +34,14 @@ public final class SanguineStatuette extends CardImpl { this.addAbility(new EntersBattlefieldTriggeredAbility(new CreateTokenEffect(new BloodToken()))); // Whenever you sacrifice a Blood token, you may have Sanguine Statuette become a 3/3 Vampire artifact creature with haste until end of turn. - this.addAbility(new SacrificePermanentTriggeredAbility(new BecomesCreatureSourceEffect( + this.addAbility(new SacrificePermanentTriggeredAbility(Zone.BATTLEFIELD, new BecomesCreatureSourceEffect( new CreatureToken(3, 3, "3/3 Vampire artifact creature with haste") .withType(CardType.ARTIFACT) .withSubType(SubType.VAMPIRE) .withAbility(HasteAbility.getInstance()), CardType.ARTIFACT, Duration.EndOfTurn - ).setText("have {this} become a 3/3 Vampire artifact creature with haste until end of turn"), filter, false, true)); + ).setText("have {this} become a 3/3 Vampire artifact creature with haste until end of turn"), + filter, TargetController.YOU, SetTargetPointer.NONE, true)); } private SanguineStatuette(final SanguineStatuette card) { diff --git a/Mage.Sets/src/mage/cards/s/SavraQueenOfTheGolgari.java b/Mage.Sets/src/mage/cards/s/SavraQueenOfTheGolgari.java index 17d90c2af3f..83c226df1b6 100644 --- a/Mage.Sets/src/mage/cards/s/SavraQueenOfTheGolgari.java +++ b/Mage.Sets/src/mage/cards/s/SavraQueenOfTheGolgari.java @@ -1,37 +1,41 @@ - package mage.cards.s; -import java.util.ArrayList; -import java.util.List; -import java.util.UUID; import mage.MageInt; +import mage.ObjectColor; import mage.abilities.Ability; -import mage.abilities.TriggeredAbilityImpl; +import mage.abilities.common.SacrificePermanentTriggeredAbility; import mage.abilities.costs.common.PayLifeCost; import mage.abilities.effects.OneShotEffect; import mage.abilities.effects.common.DoIfCostPaid; import mage.abilities.effects.common.GainLifeEffect; import mage.cards.CardImpl; import mage.cards.CardSetInfo; -import mage.constants.CardType; -import mage.constants.SubType; -import mage.constants.Outcome; -import mage.constants.SuperType; -import mage.constants.Zone; +import mage.constants.*; import mage.filter.StaticFilters; +import mage.filter.common.FilterCreaturePermanent; +import mage.filter.predicate.mageobject.ColorPredicate; import mage.game.Game; -import mage.game.events.GameEvent; import mage.game.permanent.Permanent; import mage.players.Player; -import mage.target.common.TargetControlledCreaturePermanent; import mage.target.common.TargetSacrifice; +import java.util.ArrayList; +import java.util.List; +import java.util.UUID; + /** * * @author fireshoes */ public final class SavraQueenOfTheGolgari extends CardImpl { + private static final FilterCreaturePermanent filterBlack = new FilterCreaturePermanent("a black creature"); + private static final FilterCreaturePermanent filterGreen = new FilterCreaturePermanent("a green creature"); + static { + filterBlack.add(new ColorPredicate(ObjectColor.BLACK)); + filterGreen.add(new ColorPredicate(ObjectColor.GREEN)); + } + public SavraQueenOfTheGolgari(UUID ownerId, CardSetInfo setInfo) { super(ownerId,setInfo,new CardType[]{CardType.CREATURE},"{2}{B}{G}"); this.supertype.add(SuperType.LEGENDARY); @@ -41,10 +45,15 @@ public final class SavraQueenOfTheGolgari extends CardImpl { this.toughness = new MageInt(2); // Whenever you sacrifice a black creature, you may pay 2 life. If you do, each other player sacrifices a creature. - this.addAbility(new SavraSacrificeBlackCreatureAbility()); + this.addAbility(new SacrificePermanentTriggeredAbility( + new DoIfCostPaid(new SavraSacrificeEffect(), new PayLifeCost(2)), + filterBlack + )); // Whenever you sacrifice a green creature, you may gain 2 life. - this.addAbility(new SavraSacrificeGreenCreatureAbility()); + this.addAbility(new SacrificePermanentTriggeredAbility(Zone.BATTLEFIELD, new GainLifeEffect(2), + filterGreen, TargetController.YOU, SetTargetPointer.NONE, true + )); } private SavraQueenOfTheGolgari(final SavraQueenOfTheGolgari card) { @@ -57,36 +66,6 @@ public final class SavraQueenOfTheGolgari extends CardImpl { } } -class SavraSacrificeBlackCreatureAbility extends TriggeredAbilityImpl { - - public SavraSacrificeBlackCreatureAbility() { - super(Zone.BATTLEFIELD, new DoIfCostPaid(new SavraSacrificeEffect(), new PayLifeCost(2))); - this.setLeavesTheBattlefieldTrigger(true); - setTriggerPhrase("Whenever you sacrifice a black creature, "); - } - - private SavraSacrificeBlackCreatureAbility(final SavraSacrificeBlackCreatureAbility ability) { - super(ability); - } - - @Override - public SavraSacrificeBlackCreatureAbility copy() { - return new SavraSacrificeBlackCreatureAbility(this); - } - - @Override - public boolean checkEventType(GameEvent event, Game game) { - return event.getType() == GameEvent.EventType.SACRIFICED_PERMANENT; - } - - @Override - public boolean checkTrigger(GameEvent event, Game game) { - return event.getPlayerId().equals(this.getControllerId()) - && game.getLastKnownInformation(event.getTargetId(), Zone.BATTLEFIELD).isCreature(game) - && game.getLastKnownInformation(event.getTargetId(), Zone.BATTLEFIELD).getColor(game).isBlack(); - } -} - class SavraSacrificeEffect extends OneShotEffect { SavraSacrificeEffect() { @@ -129,32 +108,3 @@ class SavraSacrificeEffect extends OneShotEffect { return false; } } - -class SavraSacrificeGreenCreatureAbility extends TriggeredAbilityImpl { - - public SavraSacrificeGreenCreatureAbility() { - super(Zone.BATTLEFIELD, new GainLifeEffect(2), true); - setTriggerPhrase("Whenever you sacrifice a green creature, "); - } - - private SavraSacrificeGreenCreatureAbility(final SavraSacrificeGreenCreatureAbility ability) { - super(ability); - } - - @Override - public SavraSacrificeGreenCreatureAbility copy() { - return new SavraSacrificeGreenCreatureAbility(this); - } - - @Override - public boolean checkEventType(GameEvent event, Game game) { - return event.getType() == GameEvent.EventType.SACRIFICED_PERMANENT; - } - - @Override - public boolean checkTrigger(GameEvent event, Game game) { - return event.getPlayerId().equals(this.getControllerId()) - && game.getLastKnownInformation(event.getTargetId(), Zone.BATTLEFIELD).isCreature(game) - && game.getLastKnownInformation(event.getTargetId(), Zone.BATTLEFIELD).getColor(game).isGreen(); - } -} diff --git a/Mage.Sets/src/mage/cards/s/SlaughterPriestOfMogis.java b/Mage.Sets/src/mage/cards/s/SlaughterPriestOfMogis.java index 3c3591cb8ff..97e63216d77 100644 --- a/Mage.Sets/src/mage/cards/s/SlaughterPriestOfMogis.java +++ b/Mage.Sets/src/mage/cards/s/SlaughterPriestOfMogis.java @@ -2,7 +2,7 @@ package mage.cards.s; import mage.MageInt; import mage.abilities.Ability; -import mage.abilities.TriggeredAbilityImpl; +import mage.abilities.common.SacrificePermanentTriggeredAbility; import mage.abilities.common.SimpleActivatedAbility; import mage.abilities.costs.common.SacrificeTargetCost; import mage.abilities.costs.mana.GenericManaCost; @@ -14,13 +14,10 @@ import mage.cards.CardSetInfo; import mage.constants.CardType; import mage.constants.Duration; import mage.constants.SubType; -import mage.constants.Zone; +import mage.filter.StaticFilters; import mage.filter.common.FilterControlledPermanent; import mage.filter.predicate.Predicates; import mage.filter.predicate.mageobject.AnotherPredicate; -import mage.game.Game; -import mage.game.events.GameEvent; -import mage.target.common.TargetControlledPermanent; import java.util.UUID; @@ -49,7 +46,9 @@ public final class SlaughterPriestOfMogis extends CardImpl { this.toughness = new MageInt(2); // Whenever you sacrifice a permanent, Slaughter-Priest of Mogis gets +2/+0 until end of turn. - this.addAbility(new SlaughterPriestOfMogisAbility()); + this.addAbility(new SacrificePermanentTriggeredAbility( + new BoostSourceEffect(2, 0, Duration.EndOfTurn), StaticFilters.FILTER_PERMANENT + )); // {2}, Sacrifice another creature or enchantment: Slaughter-Priest of Mogis gains first strike until end of turn. Ability ability = new SimpleActivatedAbility( @@ -68,34 +67,3 @@ public final class SlaughterPriestOfMogis extends CardImpl { return new SlaughterPriestOfMogis(this); } } - -class SlaughterPriestOfMogisAbility extends TriggeredAbilityImpl { - - SlaughterPriestOfMogisAbility() { - super(Zone.BATTLEFIELD, new BoostSourceEffect(2, 0, Duration.EndOfTurn)); - } - - private SlaughterPriestOfMogisAbility(final SlaughterPriestOfMogisAbility ability) { - super(ability); - } - - @Override - public SlaughterPriestOfMogisAbility copy() { - return new SlaughterPriestOfMogisAbility(this); - } - - @Override - public boolean checkEventType(GameEvent event, Game game) { - return event.getType() == GameEvent.EventType.SACRIFICED_PERMANENT; - } - - @Override - public boolean checkTrigger(GameEvent event, Game game) { - return event.getPlayerId().equals(this.getControllerId()); - } - - @Override - public String getRule() { - return "Whenever you sacrifice a permanent, {this} gets +2/+0 until end of turn."; - } -} diff --git a/Mage.Sets/src/mage/cards/s/SmotheringAbomination.java b/Mage.Sets/src/mage/cards/s/SmotheringAbomination.java index 0ec9f24affa..e77d99911a0 100644 --- a/Mage.Sets/src/mage/cards/s/SmotheringAbomination.java +++ b/Mage.Sets/src/mage/cards/s/SmotheringAbomination.java @@ -1,10 +1,8 @@ - package mage.cards.s; -import java.util.UUID; import mage.MageInt; -import mage.abilities.TriggeredAbilityImpl; import mage.abilities.common.BeginningOfUpkeepTriggeredAbility; +import mage.abilities.common.SacrificePermanentTriggeredAbility; import mage.abilities.effects.common.DrawCardSourceControllerEffect; import mage.abilities.effects.common.SacrificeControllerEffect; import mage.abilities.keyword.DevoidAbility; @@ -14,10 +12,9 @@ import mage.cards.CardSetInfo; import mage.constants.CardType; import mage.constants.SubType; import mage.constants.TargetController; -import mage.constants.Zone; import mage.filter.StaticFilters; -import mage.game.Game; -import mage.game.events.GameEvent; + +import java.util.UUID; /** * @@ -42,7 +39,9 @@ public final class SmotheringAbomination extends CardImpl { StaticFilters.FILTER_PERMANENT_CREATURE, 1, null), TargetController.YOU, false)); // Whenever you sacrifice a creature, draw a card. - this.addAbility(new SmotheringAbominationTriggeredAbility()); + this.addAbility(new SacrificePermanentTriggeredAbility( + new DrawCardSourceControllerEffect(1), StaticFilters.FILTER_PERMANENT_CREATURE + )); } private SmotheringAbomination(final SmotheringAbomination card) { @@ -54,32 +53,3 @@ public final class SmotheringAbomination extends CardImpl { return new SmotheringAbomination(this); } } - -class SmotheringAbominationTriggeredAbility extends TriggeredAbilityImpl { - - public SmotheringAbominationTriggeredAbility() { - super(Zone.BATTLEFIELD, new DrawCardSourceControllerEffect(1)); - setLeavesTheBattlefieldTrigger(true); - setTriggerPhrase("Whenever you sacrifice a creature, "); - } - - private SmotheringAbominationTriggeredAbility(final SmotheringAbominationTriggeredAbility ability) { - super(ability); - } - - @Override - public SmotheringAbominationTriggeredAbility copy() { - return new SmotheringAbominationTriggeredAbility(this); - } - - @Override - public boolean checkEventType(GameEvent event, Game game) { - return event.getType() == GameEvent.EventType.SACRIFICED_PERMANENT; - } - - @Override - public boolean checkTrigger(GameEvent event, Game game) { - return event.getPlayerId().equals(this.getControllerId()) - && game.getLastKnownInformation(event.getTargetId(), Zone.BATTLEFIELD).isCreature(game); - } -} diff --git a/Mage.Sets/src/mage/cards/s/SorcerersBroom.java b/Mage.Sets/src/mage/cards/s/SorcerersBroom.java index dd40797e1da..e4511c9179c 100644 --- a/Mage.Sets/src/mage/cards/s/SorcerersBroom.java +++ b/Mage.Sets/src/mage/cards/s/SorcerersBroom.java @@ -1,7 +1,7 @@ package mage.cards.s; import mage.MageInt; -import mage.abilities.TriggeredAbilityImpl; +import mage.abilities.common.SacrificePermanentTriggeredAbility; import mage.abilities.costs.mana.GenericManaCost; import mage.abilities.effects.CreateTokenCopySourceEffect; import mage.abilities.effects.common.DoIfCostPaid; @@ -9,9 +9,8 @@ import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.CardType; import mage.constants.SubType; -import mage.constants.Zone; -import mage.game.Game; -import mage.game.events.GameEvent; +import mage.filter.FilterPermanent; +import mage.filter.predicate.mageobject.AnotherPredicate; import java.util.UUID; @@ -20,6 +19,12 @@ import java.util.UUID; */ public final class SorcerersBroom extends CardImpl { + private static final FilterPermanent filter = new FilterPermanent("another permanent"); + + static { + filter.add(AnotherPredicate.instance); + } + public SorcerersBroom(UUID ownerId, CardSetInfo setInfo) { super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT, CardType.CREATURE}, "{2}"); @@ -28,7 +33,10 @@ public final class SorcerersBroom extends CardImpl { this.toughness = new MageInt(1); // Whenever you sacrifice another permanent, you may pay {3}. If you do, create a token that's a copy of Sorcerer's Broom. - this.addAbility(new SorcerersBroomTriggeredAbility()); + this.addAbility(new SacrificePermanentTriggeredAbility( + new DoIfCostPaid(new CreateTokenCopySourceEffect(), new GenericManaCost(3)), + filter + )); } private SorcerersBroom(final SorcerersBroom card) { @@ -40,36 +48,3 @@ public final class SorcerersBroom extends CardImpl { return new SorcerersBroom(this); } } - -class SorcerersBroomTriggeredAbility extends TriggeredAbilityImpl { - - SorcerersBroomTriggeredAbility() { - super(Zone.BATTLEFIELD, new DoIfCostPaid(new CreateTokenCopySourceEffect(), new GenericManaCost(3))); - } - - private SorcerersBroomTriggeredAbility(final SorcerersBroomTriggeredAbility ability) { - super(ability); - } - - @Override - public SorcerersBroomTriggeredAbility copy() { - return new SorcerersBroomTriggeredAbility(this); - } - - @Override - public boolean checkEventType(GameEvent event, Game game) { - return event.getType() == GameEvent.EventType.SACRIFICED_PERMANENT; - } - - @Override - public boolean checkTrigger(GameEvent event, Game game) { - return event.getPlayerId().equals(this.getControllerId()) - && !event.getTargetId().equals(sourceId); - } - - @Override - public String getRule() { - return "Whenever you sacrifice another permanent, you may pay {3}. " + - "If you do, create a token that's a copy of {this}."; - } -} \ No newline at end of file diff --git a/Mage.Sets/src/mage/cards/t/Thraximundar.java b/Mage.Sets/src/mage/cards/t/Thraximundar.java index a41990b75c0..f658b1cbf61 100644 --- a/Mage.Sets/src/mage/cards/t/Thraximundar.java +++ b/Mage.Sets/src/mage/cards/t/Thraximundar.java @@ -1,25 +1,18 @@ - package mage.cards.t; -import java.util.UUID; import mage.MageInt; -import mage.MageObject; -import mage.abilities.TriggeredAbilityImpl; -import mage.abilities.effects.Effect; +import mage.abilities.common.AttacksTriggeredAbility; +import mage.abilities.common.SacrificePermanentTriggeredAbility; import mage.abilities.effects.common.SacrificeEffect; import mage.abilities.effects.common.counter.AddCountersSourceEffect; import mage.abilities.keyword.HasteAbility; import mage.cards.CardImpl; import mage.cards.CardSetInfo; -import mage.constants.CardType; -import mage.constants.SubType; -import mage.constants.SuperType; -import mage.constants.Zone; +import mage.constants.*; import mage.counters.CounterType; -import mage.filter.common.FilterControlledPermanent; -import mage.game.Game; -import mage.game.events.GameEvent; -import mage.target.targetpointer.FixedTarget; +import mage.filter.StaticFilters; + +import java.util.UUID; /** * @@ -40,10 +33,16 @@ public final class Thraximundar extends CardImpl { this.addAbility(HasteAbility.getInstance()); // Whenever Thraximundar attacks, defending player sacrifices a creature. - this.addAbility(new ThraximundarTriggeredAbility()); + this.addAbility(new AttacksTriggeredAbility( + new SacrificeEffect(StaticFilters.FILTER_PERMANENT_CREATURE, 1, "defending player"), + false, null, SetTargetPointer.PLAYER + )); // Whenever a player sacrifices a creature, you may put a +1/+1 counter on Thraximundar. - this.addAbility(new PlayerSacrificesCreatureTriggeredAbility(new AddCountersSourceEffect(CounterType.P1P1.createInstance()), true)); + this.addAbility(new SacrificePermanentTriggeredAbility(Zone.BATTLEFIELD, + new AddCountersSourceEffect(CounterType.P1P1.createInstance()), StaticFilters.FILTER_PERMANENT_CREATURE, + TargetController.ANY, SetTargetPointer.NONE, true + )); } @@ -56,75 +55,3 @@ public final class Thraximundar extends CardImpl { return new Thraximundar(this); } } - -class ThraximundarTriggeredAbility extends TriggeredAbilityImpl { - - private static final FilterControlledPermanent filter; - - static { - filter = new FilterControlledPermanent(" a creature"); - filter.add(CardType.CREATURE.getPredicate()); - } - - public ThraximundarTriggeredAbility() { - super(Zone.BATTLEFIELD, new SacrificeEffect(filter, 1, "defending player")); - } - - private ThraximundarTriggeredAbility(final ThraximundarTriggeredAbility ability) { - super(ability); - } - - @Override - public ThraximundarTriggeredAbility copy() { - return new ThraximundarTriggeredAbility(this); - } - - @Override - public boolean checkEventType(GameEvent event, Game game) { - return event.getType() == GameEvent.EventType.ATTACKER_DECLARED; - } - - @Override - public boolean checkTrigger(GameEvent event, Game game) { - if (event.getSourceId() != null - && event.getSourceId().equals(this.getSourceId())) { - UUID defender = game.getCombat().getDefendingPlayerId(this.getSourceId(), game); - this.getEffects().get(0).setTargetPointer(new FixedTarget(defender)); - return true; - } - return false; - } - - @Override - public String getRule() { - return "Whenever {this} attacks, defending player sacrifices a creature."; - } -} - -class PlayerSacrificesCreatureTriggeredAbility extends TriggeredAbilityImpl { - - public PlayerSacrificesCreatureTriggeredAbility(Effect effect, boolean optional) { - super(Zone.BATTLEFIELD, effect, optional); - setTriggerPhrase("Whenever a player sacrifices a creature, "); - } - - private PlayerSacrificesCreatureTriggeredAbility(final PlayerSacrificesCreatureTriggeredAbility ability) { - super(ability); - } - - @Override - public boolean checkEventType(GameEvent event, Game game) { - return event.getType() == GameEvent.EventType.SACRIFICED_PERMANENT; - } - - @Override - public boolean checkTrigger(GameEvent event, Game game) { - MageObject mageObject = game.getLastKnownInformation(event.getTargetId(), Zone.BATTLEFIELD); - return mageObject != null && mageObject.isCreature(game); - } - - @Override - public PlayerSacrificesCreatureTriggeredAbility copy() { - return new PlayerSacrificesCreatureTriggeredAbility(this); - } -} diff --git a/Mage.Sets/src/mage/cards/t/TrailOfCrumbs.java b/Mage.Sets/src/mage/cards/t/TrailOfCrumbs.java index 7f6ba0f9ead..26aa2578fb9 100644 --- a/Mage.Sets/src/mage/cards/t/TrailOfCrumbs.java +++ b/Mage.Sets/src/mage/cards/t/TrailOfCrumbs.java @@ -1,7 +1,7 @@ package mage.cards.t; -import mage.abilities.TriggeredAbilityImpl; import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.common.SacrificePermanentTriggeredAbility; import mage.abilities.costs.mana.GenericManaCost; import mage.abilities.effects.common.CreateTokenEffect; import mage.abilities.effects.common.DoIfCostPaid; @@ -10,12 +10,7 @@ import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.CardType; import mage.constants.PutCards; -import mage.constants.SubType; -import mage.constants.Zone; import mage.filter.StaticFilters; -import mage.game.Game; -import mage.game.events.GameEvent; -import mage.game.permanent.Permanent; import mage.game.permanent.token.FoodToken; import java.util.UUID; @@ -34,7 +29,12 @@ public final class TrailOfCrumbs extends CardImpl { // Whenever you sacrifice a Food, you may pay {1}. If you do, look at the top two cards of your library. // You may reveal a permanent card from among them and put it into your hand. // Put the rest on the bottom of your library in any order. - this.addAbility(new TrailOfCrumbsTriggeredAbility()); + this.addAbility(new SacrificePermanentTriggeredAbility( + new DoIfCostPaid(new LookLibraryAndPickControllerEffect( + 2, 1, StaticFilters.FILTER_CARD_PERMANENT, PutCards.HAND, PutCards.BOTTOM_ANY + ), new GenericManaCost(1)), + StaticFilters.FILTER_CONTROLLED_FOOD + )); } private TrailOfCrumbs(final TrailOfCrumbs card) { @@ -46,35 +46,3 @@ public final class TrailOfCrumbs extends CardImpl { return new TrailOfCrumbs(this); } } - -class TrailOfCrumbsTriggeredAbility extends TriggeredAbilityImpl { - - TrailOfCrumbsTriggeredAbility() { - super(Zone.BATTLEFIELD, new DoIfCostPaid(new LookLibraryAndPickControllerEffect( - 2, 1, StaticFilters.FILTER_CARD_PERMANENT, PutCards.HAND, PutCards.BOTTOM_ANY - ), new GenericManaCost(1))); - setTriggerPhrase("Whenever you sacrifice a Food, "); - } - - private TrailOfCrumbsTriggeredAbility(final TrailOfCrumbsTriggeredAbility ability) { - super(ability); - } - - @Override - public TrailOfCrumbsTriggeredAbility copy() { - return new TrailOfCrumbsTriggeredAbility(this); - } - - @Override - public boolean checkEventType(GameEvent event, Game game) { - return event.getType() == GameEvent.EventType.SACRIFICED_PERMANENT; - } - - @Override - public boolean checkTrigger(GameEvent event, Game game) { - Permanent permanent = game.getPermanentOrLKIBattlefield(event.getTargetId()); - return permanent != null - && event.getPlayerId().equals(this.getControllerId()) - && permanent.hasSubtype(SubType.FOOD, game); - } -} diff --git a/Mage.Sets/src/mage/cards/u/UlvenwaldMysteries.java b/Mage.Sets/src/mage/cards/u/UlvenwaldMysteries.java index d0eb4729e4b..a2632f44c6d 100644 --- a/Mage.Sets/src/mage/cards/u/UlvenwaldMysteries.java +++ b/Mage.Sets/src/mage/cards/u/UlvenwaldMysteries.java @@ -1,25 +1,19 @@ - package mage.cards.u; -import java.util.UUID; -import mage.abilities.TriggeredAbilityImpl; import mage.abilities.common.DiesCreatureTriggeredAbility; +import mage.abilities.common.SacrificePermanentTriggeredAbility; import mage.abilities.effects.common.CreateTokenEffect; import mage.abilities.effects.keyword.InvestigateEffect; 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.StaticFilters; import mage.filter.common.FilterControlledPermanent; -import mage.filter.common.FilterCreaturePermanent; -import mage.filter.predicate.permanent.TokenPredicate; -import mage.game.Game; -import mage.game.events.GameEvent; import mage.game.permanent.token.HumanSoldierToken; +import java.util.UUID; + /** * * @author fireshoes @@ -39,7 +33,7 @@ public final class UlvenwaldMysteries extends CardImpl { this.addAbility(new DiesCreatureTriggeredAbility(new InvestigateEffect(), false, StaticFilters.FILTER_CONTROLLED_CREATURE_NON_TOKEN)); // Whenever you sacrifice a Clue, create a 1/1 white Human Soldier creature token. - this.addAbility(new UlvenwaldMysteriesTriggeredAbility()); + this.addAbility(new SacrificePermanentTriggeredAbility(new CreateTokenEffect(new HumanSoldierToken()), filterClue)); } private UlvenwaldMysteries(final UlvenwaldMysteries card) { @@ -51,32 +45,3 @@ public final class UlvenwaldMysteries extends CardImpl { return new UlvenwaldMysteries(this); } } - -class UlvenwaldMysteriesTriggeredAbility extends TriggeredAbilityImpl { - - public UlvenwaldMysteriesTriggeredAbility() { - super(Zone.BATTLEFIELD, new CreateTokenEffect(new HumanSoldierToken())); - setLeavesTheBattlefieldTrigger(true); - setTriggerPhrase("Whenever you sacrifice a Clue, "); - } - - private UlvenwaldMysteriesTriggeredAbility(final UlvenwaldMysteriesTriggeredAbility ability) { - super(ability); - } - - @Override - public UlvenwaldMysteriesTriggeredAbility copy() { - return new UlvenwaldMysteriesTriggeredAbility(this); - } - - @Override - public boolean checkEventType(GameEvent event, Game game) { - return event.getType() == GameEvent.EventType.SACRIFICED_PERMANENT; - } - - @Override - public boolean checkTrigger(GameEvent event, Game game) { - return event.getPlayerId().equals(this.getControllerId()) - && game.getLastKnownInformation(event.getTargetId(), Zone.BATTLEFIELD).hasSubtype(SubType.CLUE, game); - } -} \ No newline at end of file diff --git a/Mage/src/main/java/mage/abilities/common/OpponentSacrificesNonTokenPermanentTriggeredAbility.java b/Mage/src/main/java/mage/abilities/common/OpponentSacrificesNonTokenPermanentTriggeredAbility.java deleted file mode 100644 index 536dd681496..00000000000 --- a/Mage/src/main/java/mage/abilities/common/OpponentSacrificesNonTokenPermanentTriggeredAbility.java +++ /dev/null @@ -1,46 +0,0 @@ - -package mage.abilities.common; - -import mage.abilities.TriggeredAbilityImpl; -import mage.abilities.effects.Effect; -import mage.constants.Zone; -import mage.game.Game; -import mage.game.events.GameEvent; -import mage.game.permanent.Permanent; -import mage.game.permanent.PermanentToken; -import mage.target.targetpointer.FixedTarget; - -public class OpponentSacrificesNonTokenPermanentTriggeredAbility extends TriggeredAbilityImpl { - - public OpponentSacrificesNonTokenPermanentTriggeredAbility(Effect effect) { - super(Zone.BATTLEFIELD, effect, false); - setTriggerPhrase("Whenever an opponent sacrifices a nontoken permanent, "); - } - - protected OpponentSacrificesNonTokenPermanentTriggeredAbility(final OpponentSacrificesNonTokenPermanentTriggeredAbility ability) { - super(ability); - } - - @Override - public boolean checkEventType(GameEvent event, Game game) { - return event.getType() == GameEvent.EventType.SACRIFICED_PERMANENT; - } - - @Override - public boolean checkTrigger(GameEvent event, Game game) { - if (game.getPlayer(getControllerId()).hasOpponent(event.getPlayerId(), game)) { - Permanent permanent = (Permanent) game.getLastKnownInformation(event.getTargetId(), Zone.BATTLEFIELD); - if (permanent != null && !(permanent instanceof PermanentToken)) { - getEffects().setTargetPointer(new FixedTarget(event.getTargetId(), game.getState().getZoneChangeCounter(event.getTargetId()))); - return true; - } - } - return false; - } - - @Override - public OpponentSacrificesNonTokenPermanentTriggeredAbility copy() { - return new OpponentSacrificesNonTokenPermanentTriggeredAbility(this); - } - -} diff --git a/Mage/src/main/java/mage/abilities/common/OpponentSacrificesPermanentTriggeredAbility.java b/Mage/src/main/java/mage/abilities/common/OpponentSacrificesPermanentTriggeredAbility.java deleted file mode 100644 index 4d9ee59f736..00000000000 --- a/Mage/src/main/java/mage/abilities/common/OpponentSacrificesPermanentTriggeredAbility.java +++ /dev/null @@ -1,48 +0,0 @@ - -package mage.abilities.common; - -import mage.MageObject; -import mage.abilities.TriggeredAbilityImpl; -import mage.abilities.effects.Effect; -import mage.constants.Zone; -import mage.game.Game; -import mage.game.events.GameEvent; -import mage.game.permanent.Permanent; -import mage.target.targetpointer.FixedTarget; - -public class OpponentSacrificesPermanentTriggeredAbility extends TriggeredAbilityImpl { - - public OpponentSacrificesPermanentTriggeredAbility(Effect effect) { - super(Zone.BATTLEFIELD, effect, false); - setTriggerPhrase("Whenever an opponent sacrifices a nontoken permanent, "); - } - - protected OpponentSacrificesPermanentTriggeredAbility(final OpponentSacrificesPermanentTriggeredAbility ability) { - super(ability); - } - - @Override - public boolean checkEventType(GameEvent event, Game game) { - return event.getType() == GameEvent.EventType.SACRIFICED_PERMANENT; - } - - @Override - public boolean checkTrigger(GameEvent event, Game game) { - if (game.getPlayer(this.getControllerId()).hasOpponent(event.getPlayerId(), game)) { - MageObject object = game.getLastKnownInformation(event.getTargetId(), Zone.BATTLEFIELD); - if (object instanceof Permanent) { - for (Effect effect : getEffects()) { - effect.setTargetPointer(new FixedTarget(event.getTargetId(), game)); - } - return true; - } - } - return false; - } - - @Override - public OpponentSacrificesPermanentTriggeredAbility copy() { - return new OpponentSacrificesPermanentTriggeredAbility(this); - } - -} \ No newline at end of file diff --git a/Mage/src/main/java/mage/abilities/common/SacrificeAllTriggeredAbility.java b/Mage/src/main/java/mage/abilities/common/SacrificeAllTriggeredAbility.java deleted file mode 100644 index 493a9be4e57..00000000000 --- a/Mage/src/main/java/mage/abilities/common/SacrificeAllTriggeredAbility.java +++ /dev/null @@ -1,82 +0,0 @@ -package mage.abilities.common; - -import mage.abilities.TriggeredAbilityImpl; -import mage.abilities.effects.Effect; -import mage.constants.TargetController; -import mage.constants.Zone; -import mage.filter.FilterPermanent; -import mage.game.Game; -import mage.game.events.GameEvent; -import mage.game.permanent.Permanent; -import mage.players.Player; - -/** - * @author LevelX2 - */ -public class SacrificeAllTriggeredAbility extends TriggeredAbilityImpl { - - private final FilterPermanent filter; - private final TargetController sacrificingPlayer; - - public SacrificeAllTriggeredAbility(Effect effect, FilterPermanent filter, TargetController sacrificingPlayer, boolean optional) { - super(Zone.BATTLEFIELD, effect, optional); - this.filter = filter; - this.sacrificingPlayer = sacrificingPlayer; - setTriggerPhrase(generateTriggerPhrase()); - } - - protected SacrificeAllTriggeredAbility(final SacrificeAllTriggeredAbility ability) { - super(ability); - this.filter = ability.filter; - this.sacrificingPlayer = ability.sacrificingPlayer; - } - - @Override - public SacrificeAllTriggeredAbility copy() { - return new SacrificeAllTriggeredAbility(this); - } - - @Override - public boolean checkEventType(GameEvent event, Game game) { - return event.getType() == GameEvent.EventType.SACRIFICED_PERMANENT; - } - - @Override - public boolean checkTrigger(GameEvent event, Game game) { - switch (sacrificingPlayer) { - case YOU: - if (!event.getPlayerId().equals(getControllerId())) { - return false; - } - break; - case OPPONENT: - Player controller = game.getPlayer(getControllerId()); - if (controller == null || !controller.hasOpponent(event.getPlayerId(), game)) { - return false; - } - break; - case ANY: - break; - default: - return false; - } - Permanent sacrificedPermanent = game.getPermanentOrLKIBattlefield(event.getTargetId()); - return sacrificedPermanent != null && filter.match(sacrificedPermanent, getControllerId(), this, game); - } - - private String generateTriggerPhrase() { - String targetControllerText; - switch (sacrificingPlayer) { - case YOU: - targetControllerText = "you sacrifice "; - break; - case OPPONENT: - targetControllerText = "an opponent sacrifices "; - break; - default: - targetControllerText = "a player sacrifices "; - break; - } - return "Whenever " + targetControllerText + filter.getMessage() + ", "; - } -} diff --git a/Mage/src/main/java/mage/abilities/common/SacrificePermanentTriggeredAbility.java b/Mage/src/main/java/mage/abilities/common/SacrificePermanentTriggeredAbility.java index 09ed0aa4cf8..cc6a23bef9d 100644 --- a/Mage/src/main/java/mage/abilities/common/SacrificePermanentTriggeredAbility.java +++ b/Mage/src/main/java/mage/abilities/common/SacrificePermanentTriggeredAbility.java @@ -2,53 +2,53 @@ package mage.abilities.common; import mage.abilities.TriggeredAbilityImpl; import mage.abilities.effects.Effect; +import mage.constants.SetTargetPointer; +import mage.constants.TargetController; import mage.constants.Zone; import mage.filter.FilterPermanent; -import mage.filter.StaticFilters; import mage.game.Game; import mage.game.events.GameEvent; import mage.game.permanent.Permanent; +import mage.players.Player; import mage.target.targetpointer.FixedTarget; import mage.util.CardUtil; /** - * @author TheElk801 + * @author TheElk801, xenohedron */ public class SacrificePermanentTriggeredAbility extends TriggeredAbilityImpl { private final FilterPermanent filter; - private final boolean setTargetPointer; + private final SetTargetPointer setTargetPointer; - public SacrificePermanentTriggeredAbility(Effect effect) { - this(effect, StaticFilters.FILTER_PERMANENT_A); - } + private final TargetController sacrificingPlayer; + /** + * Whenever you sacrifice a "[filter]", "[effect]". + * zone = battlefield, setTargetPointer = NONE, optional = false + */ public SacrificePermanentTriggeredAbility(Effect effect, FilterPermanent filter) { - this(effect, filter, false); + this(Zone.BATTLEFIELD, effect, filter, TargetController.YOU, SetTargetPointer.NONE, false); } - public SacrificePermanentTriggeredAbility(Effect effect, FilterPermanent filter, boolean setTargetPointer) { - this(effect, filter, setTargetPointer, false); - } - - public SacrificePermanentTriggeredAbility(Effect effect, FilterPermanent filter, boolean setTargetPointer, boolean optional) { - this(Zone.BATTLEFIELD, effect, filter, setTargetPointer, optional); - } - - public SacrificePermanentTriggeredAbility(Zone zone, Effect effect, FilterPermanent filter, boolean setTargetPointer, boolean optional) { + public SacrificePermanentTriggeredAbility(Zone zone, Effect effect, FilterPermanent filter, + TargetController sacrificingPlayer, + SetTargetPointer setTargetPointer, boolean optional) { super(zone, effect, optional); if (Zone.BATTLEFIELD.match(zone)) { setLeavesTheBattlefieldTrigger(true); } this.filter = filter; this.setTargetPointer = setTargetPointer; - setTriggerPhrase("Whenever you sacrifice " + CardUtil.addArticle(filter.getMessage()) + ", "); + this.sacrificingPlayer = sacrificingPlayer; + setTriggerPhrase(generateTriggerPhrase()); } protected SacrificePermanentTriggeredAbility(final SacrificePermanentTriggeredAbility ability) { super(ability); this.filter = ability.filter; this.setTargetPointer = ability.setTargetPointer; + this.sacrificingPlayer = ability.sacrificingPlayer; } @Override @@ -63,15 +63,59 @@ public class SacrificePermanentTriggeredAbility extends TriggeredAbilityImpl { @Override public boolean checkTrigger(GameEvent event, Game game) { + switch (sacrificingPlayer) { + case YOU: + if (!event.getPlayerId().equals(getControllerId())) { + return false; + } + break; + case OPPONENT: + Player controller = game.getPlayer(getControllerId()); + if (controller == null || !controller.hasOpponent(event.getPlayerId(), game)) { + return false; + } + break; + case ANY: + break; + default: + throw new IllegalArgumentException("Unsupported TargetController in SacrificePermanentTriggeredAbility: " + sacrificingPlayer); + } Permanent permanent = game.getPermanentOrLKIBattlefield(event.getTargetId()); - if (!isControlledBy(event.getPlayerId()) || permanent == null - || !filter.match(permanent, getControllerId(), this, game)) { + if (permanent == null || !filter.match(permanent, getControllerId(), this, game)) { return false; } this.getEffects().setValue("sacrificedPermanent", permanent); - if (setTargetPointer) { - this.getEffects().setTargetPointer(new FixedTarget(event.getTargetId(), game)); + switch (setTargetPointer) { + case PERMANENT: + this.getEffects().setTargetPointer(new FixedTarget(event.getTargetId(), game)); + break; + case PLAYER: + this.getEffects().setTargetPointer(new FixedTarget(event.getPlayerId(), game)); + break; + case NONE: + break; + default: + throw new IllegalArgumentException("Unsupported SetTargetPointer in SacrificePermanentTriggeredAbility: " + setTargetPointer); } return true; } + + private String generateTriggerPhrase() { + String targetControllerText; + switch (sacrificingPlayer) { + case YOU: + targetControllerText = "you sacrifice "; + break; + case OPPONENT: + targetControllerText = "an opponent sacrifices "; + break; + case ANY: + targetControllerText = "a player sacrifices "; + break; + default: + throw new IllegalArgumentException("Unsupported TargetController in SacrificePermanentTriggeredAbility: " + sacrificingPlayer); + } + return getWhen() + targetControllerText + CardUtil.addArticle(filter.getMessage()) + ", "; + } + }