From 23276a4e8d7a50646ea691cfab5f27f07f4218ed Mon Sep 17 00:00:00 2001 From: jmharmon <37360760+jmharmon@users.noreply.github.com> Date: Mon, 9 Sep 2019 07:01:18 -0700 Subject: [PATCH 001/373] Implement Faerie Vandal --- Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 1 file changed, 1 insertion(+) diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index ac1778d5aa..cbe805a785 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -47,6 +47,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Embereth Skyblazer", 321, Rarity.RARE, mage.cards.e.EmberethSkyblazer.class)); cards.add(new SetCardInfo("Eye Collector", 86, Rarity.COMMON, mage.cards.e.EyeCollector.class)); cards.add(new SetCardInfo("Faerie Formation", 316, Rarity.RARE, mage.cards.f.FaerieFormation.class)); + cards.add(new SetCardInfo("Faerie Vandal", 45, Rarity.UNCOMMON, mage.cards.f.FaerieVandal.class)); cards.add(new SetCardInfo("Fireborn Knight", 210, Rarity.UNCOMMON, mage.cards.f.FirebornKnight.class)); cards.add(new SetCardInfo("Flaxen Intruder", 155, Rarity.UNCOMMON, mage.cards.f.FlaxenIntruder.class)); cards.add(new SetCardInfo("Foulmire Knight", 90, Rarity.UNCOMMON, mage.cards.f.FoulmireKnight.class)); From 0f24c6664b31ccf81a5de4826c3c9f5e570f30e3 Mon Sep 17 00:00:00 2001 From: jmharmon <37360760+jmharmon@users.noreply.github.com> Date: Mon, 9 Sep 2019 07:02:55 -0700 Subject: [PATCH 002/373] Implement Faerie Vandal --- Mage.Sets/src/mage/cards/f/FaerieVandal.java | 107 +++++++++++++++++++ 1 file changed, 107 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/f/FaerieVandal.java diff --git a/Mage.Sets/src/mage/cards/f/FaerieVandal.java b/Mage.Sets/src/mage/cards/f/FaerieVandal.java new file mode 100644 index 0000000000..7f45e7d8b9 --- /dev/null +++ b/Mage.Sets/src/mage/cards/f/FaerieVandal.java @@ -0,0 +1,107 @@ +package mage.cards.f; + +import mage.MageInt; +import mage.abilities.TriggeredAbilityImpl; +import mage.abilities.effects.common.counter.AddCountersSourceEffect; +import mage.abilities.keyword.FlashAbility; +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.counters.CounterType; +import mage.game.Game; +import mage.game.events.GameEvent; + +import java.util.UUID; + +/** + * @author jmharmon + */ + + +public final class FaerieVandal extends CardImpl { + + public FaerieVandal(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{1}{U}"); + this.subtype.add(SubType.FAERIE); + this.subtype.add(SubType.ROGUE); + + this.power = new MageInt(1); + this.toughness = new MageInt(2); + + // Flash + this.addAbility(FlashAbility.getInstance()); + + // Flying + this.addAbility(FlyingAbility.getInstance()); + + // Whenever you draw your second card each turn, put a +1/+1 counter on Faerie Vandal. + this.addAbility(new FaerieVandalTriggeredAbility()); + } + + public FaerieVandal(final FaerieVandal card) { + super(card); + } + + @Override + public FaerieVandal copy() { + return new FaerieVandal(this); + } +} + +class FaerieVandalTriggeredAbility extends TriggeredAbilityImpl { + + private boolean triggeredOnce = false; + private boolean triggeredTwice = false; + + FaerieVandalTriggeredAbility() { + super(Zone.BATTLEFIELD, new AddCountersSourceEffect(CounterType.P1P1.createInstance()), false); + } + + private FaerieVandalTriggeredAbility(final FaerieVandalTriggeredAbility ability) { + super(ability); + this.triggeredOnce = ability.triggeredOnce; + this.triggeredTwice = ability.triggeredTwice; + } + + @Override + public boolean checkEventType(GameEvent event, Game game) { + return event.getType() == GameEvent.EventType.DREW_CARD + || event.getType() == GameEvent.EventType.END_PHASE_POST; + } + + @Override + public boolean checkTrigger(GameEvent event, Game game) { + if (event.getType() == GameEvent.EventType.END_PHASE_POST) { + triggeredOnce = triggeredTwice = false; + return false; + } + if (event.getType() == GameEvent.EventType.DREW_CARD + && event.getPlayerId().equals(controllerId)) { + if (triggeredOnce) { + if (triggeredTwice) { + return false; + } else { + triggeredTwice = true; + return true; + } + } else { + triggeredOnce = true; + return false; + } + } + return false; + } + + @Override + public String getRule() { + return "Whenever you draw your second card each turn, put a +1/+1 counter on {this}."; + } + + @Override + public FaerieVandalTriggeredAbility copy() { + return new FaerieVandalTriggeredAbility(this); + } +} From 487d010b2a6eb49e55b77704742bd4466070a0b4 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 9 Sep 2019 12:34:47 -0400 Subject: [PATCH 003/373] updated ELD spoiler and reprints --- Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + Utils/mtg-cards-data.txt | 20 ++++++++++++++++++- 2 files changed, 20 insertions(+), 1 deletion(-) diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index cbe805a785..670612c027 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -69,6 +69,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Order of Midnight", 99, Rarity.UNCOMMON, mage.cards.o.OrderOfMidnight.class)); cards.add(new SetCardInfo("Piper of the Swarm", 100, Rarity.RARE, mage.cards.p.PiperOfTheSwarm.class)); cards.add(new SetCardInfo("Rankle, Master of Pranks", 101, Rarity.MYTHIC, mage.cards.r.RankleMasterOfPranks.class)); + cards.add(new SetCardInfo("Return to Nature", 173, Rarity.COMMON, mage.cards.r.ReturnToNature.class)); cards.add(new SetCardInfo("Rosethorn Acolyte", 174, Rarity.COMMON, mage.cards.r.RosethornAcolyte.class)); cards.add(new SetCardInfo("Run Away Together", 62, Rarity.COMMON, mage.cards.r.RunAwayTogether.class)); cards.add(new SetCardInfo("Savvy Hunter", 200, Rarity.UNCOMMON, mage.cards.s.SavvyHunter.class)); diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index 34afcae8be..b43bf6e179 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -35995,6 +35995,8 @@ Mountain|Commander 2019|297|C||Basic Land - Mountain|||({T}: Add {R}.)| Forest|Commander 2019|300|C||Basic Land - Forest|||({T}: Add {G}.)| All That Glitters|Throne of Eldraine|2|U|{1}{W}|Enchantment - Aura|||Enchant creature$Enchanted creature gets +1/+1 for each artifact and/or enchantment you control.| The Circle of Loyalty|Throne of Eldraine|9|M|{4}{W}{W}|Legendary Artifact|||This spell costs {1} less to cast for each Knight you control.$Creatures you control get +1/+1.$Whenever you cast a legendary spell, create a 2/2 white Knight creature token with vigilance.${3}{W}, {T}: Create a 2/2 white Knight creature token with vigilance.| +Faerie Guidemother|Throne of Eldraine|11|C|{W}|Creature - Faerie|1|1|Flying| +Gift of the Fae|Throne of Eldraine|11|C|{1}{W}|Sorcery - Adventure|1|1|Target creature gets +2/+1 and gains flying until end of turn.| Shining Armor|Throne of Eldraine|29|C|{1}{W}|Artifact - Equipment|||Flash$When Shining Armor enters the battlefield, attach it to target Knight you control.$Equipped creature gets +0/+2 and has vigilance.$Equip {3}| Silverflame Ritual|Throne of Eldraine|30|C|{3}{W}|Sorcery|||Put a +1/+1 counter on each creature you control.$Adamant — If at least three white mana was spent to cast this spell, creatures you control gain vigilance until end of turn.| Animating Faerie|Throne of Eldraine|38|U|{2}{U}|Creature - Faerie|2|2|Flying| @@ -36003,8 +36005,10 @@ Corridor Monitor|Throne of Eldraine|41|C|{1}{U}|Artifact Creature - Construct|1| Faerie Vandal|Throne of Eldraine|45|U|{1}{U}|Creature - Faerie Rogue|1|2|Flash$Flying$Whenever you draw your second card each turn, put a +1/+1 counter on Faerie Vandal.| Frogify|Throne of Eldraine|47|U|{1}{U}|Enchantment - Aura|||Enchant creature$Enchanted creature loses all abilities and is a blue Frog creature with base power and toughness 1/1.| Midnight Clock|Throne of Eldraine|54|R|{2}{U}|Artifact|||{T}: Add {U}.${2}{U}: Put an hour counter on Midnight Clock.$At the beginning of each upkeep, put an hour counter on Midnight Clock.$When the twelfth hour counter is put on Midnight Clock, shuffle your hand and graveyard into your library, then draw seven cards. Exile Midnight Clock.| +Mystical Dispute|Throne of Eldraine|58|U|{2}{U}|Instant|||This spell costs {2} less to cast if it targets a blue spell.$Counter target spell unless its controller pays {3}.| Run Away Together|Throne of Eldraine|62|C|{1}{U}|Instant|||Choose two target creatures controlled by different players. Return those creatures to their owners' hands.| Tome Raider|Throne of Eldraine|68|C|{2}{U}|Creature - Faerie|1|1|Flying$When Tome Raider enters the battlefield, draw a card.| +Turn into a Pumpkin|Throne of Eldraine|69|U|{3}{U}|Instant|||Return target nonland permanent to its owner's hand. Draw a card.$Adamant — If at least three blue mana was spent to cast this spell, create a Food token.| Wishful Merfolk|Throne of Eldraine|73|C|{1}{U}|Creature - Merfolk|3|2|Defender${1}{U}: Wishful Merfolk loses defender and becomes a Human until end of turn.| Witching Well|Throne of Eldraine|74|C|{U}|Artifact|||When Witching Well enters the battlefield, scry 2.${3}{U}, Sacrifice Witching Well: Draw two cards.| Bake into a Pie|Throne of Eldraine|76|C|{2}{B}{B}|Instant|||Destroy target creature. Create a Food token.| @@ -36019,6 +36023,7 @@ Rankle, Master of Pranks|Throne of Eldraine|101|M|{2}{B}{B}|Legendary Creature - Curry Favor|Throne of Eldraine|105|C|{B}|Sorcery - Adventure|2|1|You gain X life and each opponent loses X life, where X is the number of Knights you control.| Smitten Swordmaster|Throne of Eldraine|105|C|{1}{B}|Creature - Human Knight|2|1|Lifelink| Syr Konrad, the Grim|Throne of Eldraine|107|U|{3}{B}{B}|Legendary Creature - Human Knight|5|4|Whenever another creature dies, or a creature card is put into a graveyard from anywhere other than the battlefield, or a creature card leaves your graveyard, Syr Konrad, the Grim deals 1 damage to each opponent.${1}{B}: Each player puts the top card of their library into their graveyard.| +Wicked Guardian|Throne of Eldraine|109|C|{3}{B}|Creature - Human Noble|4|2|When Wicked Guardian enters the battlefield, you may have it deal 2 damage to another creature you control. If you do, draw a card.| Crystal Slipper|Throne of Eldraine|119|C|{1}{R}|Artifact - Equipment|||Equipped creature gets +1/+0 and has haste.$Equip {1}| Embereth Paladin|Throne of Eldraine|121|C|{3}{R}|Creature - Human Knight|4|1|Haste$Adamant — If at least three red mana was spent to cast this spell, Embereth Paladin enters the battlefield with a +1/+1 counter on it.| Battle Display|Throne of Eldraine|122|U|{R}|Sorcery - Adventure|2|1|Destroy target artifact.| @@ -36032,23 +36037,36 @@ Gilded Goose|Throne of Eldraine|160|R|{G}|Creature - Bird|0|2|Flying$When Gilded Keeper of Fables|Throne of Eldraine|163|U|{3}{G}{G}|Creature - Cat|4|5|Whenever one or more non-Human creatures you control deal combat damage to a player, draw a card.| Heart's Desire|Throne of Eldraine|165|R|{G}|Sorcery - Adventure|5|5|Create a 1/1 white Human creature token.| Lovestruck Beast|Throne of Eldraine|165|R|{2}{G}|Creature - Beast Noble|5|5|Lovestruck Beast can't attack unless you control a 1/1 creature.| +Once Upon a Time|Throne of Eldraine|169|R|{1}{G}|Instant|||If this spell is the first spell you've cast this game, you may cast it without paying its mana cost.$Look at the top five cards of your library. You may reveal a creature or land card from among them and put it into your hand. Put the rest on the bottom of your library in a random order.| +Questing Beast|Throne of Eldraine|171|M|{2}{G}{G}|Legendary Creature - Beast|4|4|Vigilance, deathtouch, haste$Questing Beast can't be blocked by creatures with power 2 or less.$Combat damage that would be dealt by creatures you control can't be prevented.$Whenever Questing Beast deals combat damage to an opponent, it deals that much damage to target planeswalker that player controls.| +Return to Nature|Throne of Eldraine|173|C|{1}{G}|Instant|||Choose one —$• Destroy target artifact.$• Destroy target enchantment.$• Exile target card from a graveyard.| Rosethorn Acolyte|Throne of Eldraine|174|C|{2}{G}|Creature - Elf Druid|2|3|{T}: Add one mana of any color.| Seasonal Ritual|Throne of Eldraine|174|C|{G}|Sorcery - Adventure|2|3|Add one mana of any color.| +Wildwood Tracker|Throne of Eldraine|183|C|{G}|Creature - Elf Warrior|1|1|Whenever Wildwood Tracker attacks or blocks, if you control another non-Human creature, Wildwood Tracker gets +1/+1 until end of turn.| Garruk, Cursed Huntsman|Throne of Eldraine|191|M|{4}{B}{G}|Legendary Planeswalker - Garruk|5|0: Create two 2/2 black and green Wolf creature tokens with "When this creature dies, put a loyalty counter on each Garruk you control."$−3: Destroy target creature. Draw a card.$−6: You get an emblem with "Creatures you control get +3/+3 and have trample."| Inspiring Veteran|Throne of Eldraine|194|U|{R}{W}|Creature - Human Knight|2|2|Other Knights you control get +1/+1.| Maraleaf Pixie|Throne of Eldraine|196|U|{G}{U}|Creature - Faerie|2|2|Flying${T}: Add {G} or {U}.| Oko, Thief of Crowns|Throne of Eldraine|197|M|{1}{G}{U}|Legendary Planeswalker - Oko|4|+2: Create a Food token.$+1: Target artifact or creature loses all abilities and becomes a green Elk creature with base power and toughness 3/3.$−5: Exchange control of target artifact or creature you control and target creature an opponent controls with power 3 or less.| +The Royal Scions|Throne of Eldraine|199|M|{1}{U}{R}|Legendary Planeswalker - Will Rowan|5|+1: Draw a card, then discard a card.$+1: Target creature gets +2/+0 and gains first strike until end of turn.$−8: Draw four cards. When you do, The Royal Scions deals damage to any target equal to the number of cards in your hand.| Savvy Hunter|Throne of Eldraine|200|U|{1}{B}{G}|Creature - Human Warrior|3|3|Whenever Savvy Hunter attacks or blocks, create a Food token.$Sacrifice two Foods: Draw a card.| Shinechaser|Throne of Eldraine|201|U|{1}{W}{U}|Creature - Faerie|1|1|Flying, vigilance$Shinechaser gets +1/+1 as long as you control an artifact.$Shinechaser gets +1/+1 as long as you control an enchantment.| Steelclaw Lance|Throne of Eldraine|202|U|{B}{R}|Artifact - Equipment|||Equipped creature gets +2/+2.$Equip Knight {1}$Equip {3}| Wintermoor Commander|Throne of Eldraine|205|U|{W}{B}|Creature - Human Knight|2|*|Deathtouch$Wintermoor Commander's toughness is equal to the number of Knights you control.$Whenever Wintermoor Commander attacks, another target Knight you control gains indestructible until end of turn.| Arcanist's Owl|Throne of Eldraine|206|U|{W/U}{W/U}{W/U}{W/U}|Artifact Creature - Bird|3|3|Flying$When Arcanist's Owl enters the battlefield, look at the top four cards of your library. You may reveal an artifact or enchantment card from among them and put it into your hand. Put the rest on the bottom of your library in a random order.| Fireborn Knight|Throne of Eldraine|210|U|{R/W}{R/W}{R/W}{R/W}|Creature - Human Knight|2|3|Double strike${R/W}{R/W}{R/W}{R/W}: Fireborn Knight gets +1/+1 until end of turn.| -Golden Egg|Throne of Eldraine|220|C|{2}|Artifact - Food|||When Golden Egg enters the battlefield, draw a card.${1}, {T}: Sacrifice Golden Egg: Add one mana of any color.${2}, {T}, Sacrifice Golden Egg: You gain 3 life.| +Enchanted Carriage|Throne of Eldraine|218|U|{5}|Artifact - Vehicle|4|4|When Enchanted Carriage enters the battlefield, create two 1/1 white Mouse creature tokens.$Crew 2| +Golden Egg|Throne of Eldraine|220|C|{2}|Artifact - Food|||When Golden Egg enters the battlefield, draw a card.${1}, {T}, Sacrifice Golden Egg: Add one mana of any color.${2}, {T}, Sacrifice Golden Egg: You gain 3 life.| Heraldic Banner|Throne of Eldraine|222|U|{3}|Artifact|||As Heraldic Banner enters the battlefield, choose a color.$Creatures you control of the chosen color get +1/+0.${T}: Add one mana of the chosen color.| Tournament Grounds|Throne of Eldraine|248|U||Land|||{T}: Add {C}.${T}: Add {R}, {W}, or {B}. Spend this mana only to cast a Knight or Equipment spell.| Witch's Cottage|Throne of Eldraine|249|C||Land - Swamp|||({T}: Add {B}.)$Witch's Cottage enters the battlefield tapped unless you control three or more other Swamps.$When Witch's Cottage enters the battlefield untapped, you may put target creature card from your graveyard on top of your library.| +Rowan, Fearless Sparkmage|Throne of Eldraine|304|M|{3}{R}{R}|Legendary Planeswalker - Rowan|5|+1: Up to one target creature gets +3/+0 and gains first strike until end of turn.$−2: Rowan, Fearless Sparkmage deals 1 damage to each of up to two target creatures. Those creatures can't block this turn.$−9: Gain control of all creatures until end of turn. Untap them. They gain haste until end of turn.| +Garrison Griffin|Throne of Eldraine|305|C|{2}{W}|Creature - Griffin|2|2|Flying$Whenever Garrison Griffin attacks, target Knight you control gains flying until end of turn.| +Rowan's Battleguard|Throne of Eldraine|306|U|{3}{R}|Creature - Human Knight|3|3|First strike$As long as you control a Rowan planeswalker, Rowan's Battleguard gets +3/+0.| +Rowan's Stalwarts|Throne of Eldraine|307|R|{4}{R}|Creature - Human Knight|5|2|When Rowan's Stalwarts enters the battlefield, you may search your library and/or graveyard for a card named Rowan, Fearless Sparkmage, reveal it, and put it into your hand. If you search your library this way, shuffle it.| Wind-Scarred Crag|Throne of Eldraine|308|C||Land|||Wind-Scarred Crag enters the battlefield tapped.$When Wind-Scarred Crag enters the battlefield, you gain 1 life.${T}: Add {R} or {W}.| +Oko, the Trickster|Throne of Eldraine|309|M|{4}{G}{U}|Legendary Planeswalker - Oko|4|+1: Put two +1/+1 counters on up to one target creature you control.$0: Until end of turn, Oko, the Trickster becomes a copy of target creature you control. Prevent all damage that would be dealt to him this turn.$−7: Until end of turn, each creature you control has base power and toughness 10/10 and gains trample.| +Oko's Accomplices|Throne of Eldraine|310|C|{2}{U}|Creature - Faerie|2|3|Flying| +Bramblefort Fink|Throne of Eldraine|311|U|{1}{G}|Creature - Ouphe|2|2|{8}: Bramblefort Fink has base power and toughness 10/10 until end of turn. Activate this ability only if you control an Oko planeswalker.| Thornwood Falls|Throne of Eldraine|313|C||Land|||Thornwood Falls enters the battlefield tapped.$When Thornwood Falls enters the battlefield, you gain 1 life.${T}: Add {G} or {U}.| Mace of the Valiant|Throne of Eldraine|314|R|{2}{W}|Artifact - Equipment|||Equipped creature gets +1/+1 for each charge counter on Mace of the Valiant and has vigilance.$Whenever a creature enters the battlefield under your control, put a charge counter on Mace of the Valiant.$Equip {3}| Silverwing Squadron|Throne of Eldraine|315|R|{5}{W}|Creature - Human Knight|*|*|Flying, vigilance$Silverwing Squadron's power and toughness are each equal to the number of creatures you control.$Whenever Silverwing Squadron attacks, create a number of 2/2 white Knight creature tokens with vigilance equal to the number of opponents you have.| From 793f0cff6737f67913e53ca3df5fe85a9c89cf57 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 9 Sep 2019 12:42:00 -0400 Subject: [PATCH 004/373] Implemented Enchanted Carriage --- .../src/mage/cards/e/EnchantedCarriage.java | 42 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + .../src/main/java/mage/constants/SubType.java | 1 + .../mage/game/permanent/token/MouseToken.java | 29 +++++++++++++ 4 files changed, 73 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/e/EnchantedCarriage.java create mode 100644 Mage/src/main/java/mage/game/permanent/token/MouseToken.java diff --git a/Mage.Sets/src/mage/cards/e/EnchantedCarriage.java b/Mage.Sets/src/mage/cards/e/EnchantedCarriage.java new file mode 100644 index 0000000000..5a4b3011fc --- /dev/null +++ b/Mage.Sets/src/mage/cards/e/EnchantedCarriage.java @@ -0,0 +1,42 @@ +package mage.cards.e; + +import java.util.UUID; +import mage.MageInt; +import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.effects.common.CreateTokenEffect; +import mage.constants.SubType; +import mage.abilities.keyword.CrewAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.game.permanent.token.MouseToken; + +/** + * + * @author TheElk801 + */ +public final class EnchantedCarriage extends CardImpl { + + public EnchantedCarriage(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT}, "{5}"); + + this.subtype.add(SubType.VEHICLE); + this.power = new MageInt(4); + this.toughness = new MageInt(4); + + // When Enchanted Carriage enters the battlefield, create two 1/1 white Mouse creature tokens. + this.addAbility(new EntersBattlefieldTriggeredAbility(new CreateTokenEffect(new MouseToken(),2))); + + // Crew 2 + this.addAbility(new CrewAbility(2)); + } + + private EnchantedCarriage(final EnchantedCarriage card) { + super(card); + } + + @Override + public EnchantedCarriage copy() { + return new EnchantedCarriage(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 670612c027..394e31a3fa 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -45,6 +45,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Embereth Paladin", 121, Rarity.COMMON, mage.cards.e.EmberethPaladin.class)); cards.add(new SetCardInfo("Embereth Shieldbreaker", 122, Rarity.UNCOMMON, mage.cards.e.EmberethShieldbreaker.class)); cards.add(new SetCardInfo("Embereth Skyblazer", 321, Rarity.RARE, mage.cards.e.EmberethSkyblazer.class)); + cards.add(new SetCardInfo("Enchanted Carriage", 218, Rarity.UNCOMMON, mage.cards.e.EnchantedCarriage.class)); cards.add(new SetCardInfo("Eye Collector", 86, Rarity.COMMON, mage.cards.e.EyeCollector.class)); cards.add(new SetCardInfo("Faerie Formation", 316, Rarity.RARE, mage.cards.f.FaerieFormation.class)); cards.add(new SetCardInfo("Faerie Vandal", 45, Rarity.UNCOMMON, mage.cards.f.FaerieVandal.class)); diff --git a/Mage/src/main/java/mage/constants/SubType.java b/Mage/src/main/java/mage/constants/SubType.java index d11656ccc5..6b6e1660be 100644 --- a/Mage/src/main/java/mage/constants/SubType.java +++ b/Mage/src/main/java/mage/constants/SubType.java @@ -228,6 +228,7 @@ public enum SubType { MONK("Monk", SubTypeSet.CreatureType), MONKEY("Monkey", SubTypeSet.CreatureType), MOONFOLK("Moonfolk", SubTypeSet.CreatureType), + MOUSE("Mouse", SubTypeSet.CreatureType), MUTANT("Mutant", SubTypeSet.CreatureType), MYR("Myr", SubTypeSet.CreatureType), MYSTIC("Mystic", SubTypeSet.CreatureType), diff --git a/Mage/src/main/java/mage/game/permanent/token/MouseToken.java b/Mage/src/main/java/mage/game/permanent/token/MouseToken.java new file mode 100644 index 0000000000..5f7428f9b9 --- /dev/null +++ b/Mage/src/main/java/mage/game/permanent/token/MouseToken.java @@ -0,0 +1,29 @@ +package mage.game.permanent.token; + +import mage.MageInt; +import mage.constants.CardType; +import mage.constants.SubType; + +/** + * @author TheElk801 + */ +public final class MouseToken extends TokenImpl { + + public MouseToken() { + super("Mouse", "1/1 white Mouse creature token"); + cardType.add(CardType.CREATURE); + color.setWhite(true); + subtype.add(SubType.MOUSE); + power = new MageInt(1); + toughness = new MageInt(1); + } + + private MouseToken(final MouseToken token) { + super(token); + } + + @Override + public MouseToken copy() { + return new MouseToken(this); + } +} From 2f3a8e8c4af76364da0e15bee223889ef1372701 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 9 Sep 2019 12:42:33 -0400 Subject: [PATCH 005/373] Implemented Oko's Accomplices --- .../src/mage/cards/o/OkosAccomplices.java | 36 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 37 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/o/OkosAccomplices.java diff --git a/Mage.Sets/src/mage/cards/o/OkosAccomplices.java b/Mage.Sets/src/mage/cards/o/OkosAccomplices.java new file mode 100644 index 0000000000..65134616d9 --- /dev/null +++ b/Mage.Sets/src/mage/cards/o/OkosAccomplices.java @@ -0,0 +1,36 @@ +package mage.cards.o; + +import mage.MageInt; +import mage.abilities.keyword.FlyingAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class OkosAccomplices extends CardImpl { + + public OkosAccomplices(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{2}{U}"); + + this.subtype.add(SubType.FAERIE); + this.power = new MageInt(2); + this.toughness = new MageInt(3); + + // Flying + this.addAbility(FlyingAbility.getInstance()); + } + + private OkosAccomplices(final OkosAccomplices card) { + super(card); + } + + @Override + public OkosAccomplices copy() { + return new OkosAccomplices(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 394e31a3fa..100097e88e 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -66,6 +66,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Mace of the Valiant", 314, Rarity.RARE, mage.cards.m.MaceOfTheValiant.class)); cards.add(new SetCardInfo("Maraleaf Pixie", 196, Rarity.UNCOMMON, mage.cards.m.MaraleafPixie.class)); cards.add(new SetCardInfo("Midnight Clock", 54, Rarity.RARE, mage.cards.m.MidnightClock.class)); + cards.add(new SetCardInfo("Oko's Accomplices", 310, Rarity.COMMON, mage.cards.o.OkosAccomplices.class)); cards.add(new SetCardInfo("Oko, Thief of Crowns", 197, Rarity.MYTHIC, mage.cards.o.OkoThiefOfCrowns.class)); cards.add(new SetCardInfo("Order of Midnight", 99, Rarity.UNCOMMON, mage.cards.o.OrderOfMidnight.class)); cards.add(new SetCardInfo("Piper of the Swarm", 100, Rarity.RARE, mage.cards.p.PiperOfTheSwarm.class)); From 77516b7e71d87b5b8bb20c24cb6a95ee844f5789 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 9 Sep 2019 12:45:57 -0400 Subject: [PATCH 006/373] Implemented Garrison Griffin --- .../src/mage/cards/g/GarrisonGriffin.java | 52 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 53 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/g/GarrisonGriffin.java diff --git a/Mage.Sets/src/mage/cards/g/GarrisonGriffin.java b/Mage.Sets/src/mage/cards/g/GarrisonGriffin.java new file mode 100644 index 0000000000..5a1849faf3 --- /dev/null +++ b/Mage.Sets/src/mage/cards/g/GarrisonGriffin.java @@ -0,0 +1,52 @@ +package mage.cards.g; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.AttacksTriggeredAbility; +import mage.abilities.effects.common.continuous.GainAbilityTargetEffect; +import mage.abilities.keyword.FlyingAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterControlledPermanent; +import mage.target.TargetPermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class GarrisonGriffin extends CardImpl { + + private static final FilterPermanent filter = new FilterControlledPermanent(SubType.KNIGHT); + + public GarrisonGriffin(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{2}{W}"); + + this.subtype.add(SubType.GRIFFIN); + this.power = new MageInt(2); + this.toughness = new MageInt(2); + + // Flying + this.addAbility(FlyingAbility.getInstance()); + + // Whenever Garrison Griffin attacks, target Knight you control gains flying until end of turn. + Ability ability = new AttacksTriggeredAbility(new GainAbilityTargetEffect( + FlyingAbility.getInstance(), Duration.EndOfTurn + ), false); + ability.addTarget(new TargetPermanent(filter)); + this.addAbility(ability); + } + + private GarrisonGriffin(final GarrisonGriffin card) { + super(card); + } + + @Override + public GarrisonGriffin copy() { + return new GarrisonGriffin(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 100097e88e..0d5c6226df 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -53,6 +53,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Flaxen Intruder", 155, Rarity.UNCOMMON, mage.cards.f.FlaxenIntruder.class)); cards.add(new SetCardInfo("Foulmire Knight", 90, Rarity.UNCOMMON, mage.cards.f.FoulmireKnight.class)); cards.add(new SetCardInfo("Frogify", 47, Rarity.UNCOMMON, mage.cards.f.Frogify.class)); + cards.add(new SetCardInfo("Garrison Griffin", 305, Rarity.COMMON, mage.cards.g.GarrisonGriffin.class)); cards.add(new SetCardInfo("Garruk, Cursed Huntsman", 191, Rarity.MYTHIC, mage.cards.g.GarrukCursedHuntsman.class)); cards.add(new SetCardInfo("Gilded Goose", 160, Rarity.RARE, mage.cards.g.GildedGoose.class)); cards.add(new SetCardInfo("Gluttonous Troll", 327, Rarity.RARE, mage.cards.g.GluttonousTroll.class)); From ce5e61e612bf65fd5cec6c4c75b63435fe5f087a Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 9 Sep 2019 12:54:48 -0400 Subject: [PATCH 007/373] Implemented Mystical Dispute --- .../src/mage/cards/m/MysticalDispute.java | 73 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 74 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/m/MysticalDispute.java diff --git a/Mage.Sets/src/mage/cards/m/MysticalDispute.java b/Mage.Sets/src/mage/cards/m/MysticalDispute.java new file mode 100644 index 0000000000..f2c290d95e --- /dev/null +++ b/Mage.Sets/src/mage/cards/m/MysticalDispute.java @@ -0,0 +1,73 @@ +package mage.cards.m; + +import mage.abilities.Ability; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.condition.Condition; +import mage.abilities.costs.mana.GenericManaCost; +import mage.abilities.effects.common.CounterUnlessPaysEffect; +import mage.abilities.effects.common.cost.SpellCostReductionSourceEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Zone; +import mage.game.Game; +import mage.game.stack.StackObject; +import mage.target.Target; +import mage.target.TargetSpell; + +import java.util.Collection; +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class MysticalDispute extends CardImpl { + + public MysticalDispute(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.INSTANT}, "{2}{U}"); + + // This spell costs {2} less to cast if it targets a blue spell. + this.addAbility(new SimpleStaticAbility( + Zone.STACK, new SpellCostReductionSourceEffect(2, MysticalDisputeCondition.instance) + ).setRuleAtTheTop(true)); + + // Counter target spell unless its controller pays {3}. + this.getSpellAbility().addEffect(new CounterUnlessPaysEffect(new GenericManaCost(3))); + this.getSpellAbility().addTarget(new TargetSpell()); + } + + private MysticalDispute(final MysticalDispute card) { + super(card); + } + + @Override + public MysticalDispute copy() { + return new MysticalDispute(this); + } +} + +enum MysticalDisputeCondition implements Condition { + instance; + + @Override + public boolean apply(Game game, Ability source) { + StackObject sourceSpell = game.getStack().getStackObject(source.getSourceId()); + if (sourceSpell == null) { + return false; + } + return sourceSpell + .getStackAbility() + .getTargets() + .stream() + .map(Target::getTargets) + .flatMap(Collection::stream) + .map(game::getSpell) + .anyMatch(spell -> spell != null && spell.getColor(game).isBlue()); + } + + @Override + public String toString() { + return "it targets a blue spell"; + } + +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 0d5c6226df..7696dbf967 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -67,6 +67,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Mace of the Valiant", 314, Rarity.RARE, mage.cards.m.MaceOfTheValiant.class)); cards.add(new SetCardInfo("Maraleaf Pixie", 196, Rarity.UNCOMMON, mage.cards.m.MaraleafPixie.class)); cards.add(new SetCardInfo("Midnight Clock", 54, Rarity.RARE, mage.cards.m.MidnightClock.class)); + cards.add(new SetCardInfo("Mystical Dispute", 58, Rarity.UNCOMMON, mage.cards.m.MysticalDispute.class)); cards.add(new SetCardInfo("Oko's Accomplices", 310, Rarity.COMMON, mage.cards.o.OkosAccomplices.class)); cards.add(new SetCardInfo("Oko, Thief of Crowns", 197, Rarity.MYTHIC, mage.cards.o.OkoThiefOfCrowns.class)); cards.add(new SetCardInfo("Order of Midnight", 99, Rarity.UNCOMMON, mage.cards.o.OrderOfMidnight.class)); From 127af504272f26f1bd87294f040b04eca271f2c6 Mon Sep 17 00:00:00 2001 From: Oleg Agafonov Date: Mon, 9 Sep 2019 23:40:22 +0400 Subject: [PATCH 008/373] Prepare next release --- Mage.Common/src/main/java/mage/utils/MageVersion.java | 6 +++--- .../src/main/java/mage/cards/repository/CardRepository.java | 2 +- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/Mage.Common/src/main/java/mage/utils/MageVersion.java b/Mage.Common/src/main/java/mage/utils/MageVersion.java index 330229ae5f..ae105f28dc 100644 --- a/Mage.Common/src/main/java/mage/utils/MageVersion.java +++ b/Mage.Common/src/main/java/mage/utils/MageVersion.java @@ -11,11 +11,11 @@ public class MageVersion implements Serializable, Comparable { public static final int MAGE_VERSION_MAJOR = 1; public static final int MAGE_VERSION_MINOR = 4; - public static final int MAGE_VERSION_PATCH = 37; + public static final int MAGE_VERSION_PATCH = 38; public static final String MAGE_EDITION_INFO = ""; // set "-beta" for 1.4.32-betaV0 - public static final String MAGE_VERSION_MINOR_PATCH = "V4"; // default + public static final String MAGE_VERSION_MINOR_PATCH = "V0"; // default // strict mode - private static final boolean MAGE_VERSION_MINOR_PATCH_MUST_BE_SAME = true; // set true on uncompatible github changes, set false after new major release (after MAGE_VERSION_PATCH changes) + private static final boolean MAGE_VERSION_MINOR_PATCH_MUST_BE_SAME = false; // set true on uncompatible github changes, set false after new major release (after MAGE_VERSION_PATCH changes) public static final boolean MAGE_VERSION_SHOW_BUILD_TIME = true; private final int major; diff --git a/Mage/src/main/java/mage/cards/repository/CardRepository.java b/Mage/src/main/java/mage/cards/repository/CardRepository.java index 4e57a12ddd..3d58cbefb4 100644 --- a/Mage/src/main/java/mage/cards/repository/CardRepository.java +++ b/Mage/src/main/java/mage/cards/repository/CardRepository.java @@ -35,7 +35,7 @@ public enum CardRepository { // raise this if db structure was changed private static final long CARD_DB_VERSION = 51; // raise this if new cards were added to the server - private static final long CARD_CONTENT_VERSION = 222; + private static final long CARD_CONTENT_VERSION = 226; private Dao cardDao; private Set classNames; private RepositoryEventSource eventSource = new RepositoryEventSource(); From 2838437dd897413882aa327b4ec68c609b024f5e Mon Sep 17 00:00:00 2001 From: Oleg Agafonov Date: Tue, 10 Sep 2019 00:12:37 +0400 Subject: [PATCH 009/373] Added us server --- .../mage/client/dialog/ConnectDialog.form | 5 +- .../mage/client/dialog/ConnectDialog.java | 261 +++++++++--------- 2 files changed, 131 insertions(+), 135 deletions(-) diff --git a/Mage.Client/src/main/java/mage/client/dialog/ConnectDialog.form b/Mage.Client/src/main/java/mage/client/dialog/ConnectDialog.form index 4028425331..4b0dae2a96 100644 --- a/Mage.Client/src/main/java/mage/client/dialog/ConnectDialog.form +++ b/Mage.Client/src/main/java/mage/client/dialog/ConnectDialog.form @@ -422,11 +422,10 @@ - - + + - diff --git a/Mage.Client/src/main/java/mage/client/dialog/ConnectDialog.java b/Mage.Client/src/main/java/mage/client/dialog/ConnectDialog.java index 9846764b5a..33d1b75b29 100644 --- a/Mage.Client/src/main/java/mage/client/dialog/ConnectDialog.java +++ b/Mage.Client/src/main/java/mage/client/dialog/ConnectDialog.java @@ -283,11 +283,10 @@ public class ConnectDialog extends MageDialog { }); btnFindUs.setIcon(new javax.swing.ImageIcon(getClass().getResource("/flags/us.png"))); // NOI18N - btnFindUs.setText("P"); - btnFindUs.setToolTipText("Connect to mtg.powersofwar.com (USA, use any username without registration)"); + btnFindUs.setText("US"); + btnFindUs.setToolTipText("Connect to us.xmage.today (USA, use any username without registration)"); btnFindUs.setActionCommand("connectXmageus"); btnFindUs.setAlignmentY(0.0F); - btnFindUs.setEnabled(false); btnFindUs.setMargin(new java.awt.Insets(2, 2, 2, 2)); btnFindUs.setName("connectXmageusBtn"); // NOI18N btnFindUs.setPreferredSize(new java.awt.Dimension(23, 23)); @@ -310,36 +309,34 @@ public class ConnectDialog extends MageDialog { javax.swing.GroupLayout panelFastLayout = new javax.swing.GroupLayout(panelFast); panelFast.setLayout(panelFastLayout); panelFastLayout.setHorizontalGroup( - panelFastLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) - .addGroup(panelFastLayout.createSequentialGroup() - .addGap(0, 0, 0) - .addComponent(btnFindMain, javax.swing.GroupLayout.PREFERRED_SIZE, 90, javax.swing.GroupLayout.PREFERRED_SIZE) - .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) - .addComponent(btnFindUs, javax.swing.GroupLayout.PREFERRED_SIZE, 90, javax.swing.GroupLayout.PREFERRED_SIZE) - .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) - .addComponent(btnFindBeta, javax.swing.GroupLayout.PREFERRED_SIZE, 90, javax.swing.GroupLayout.PREFERRED_SIZE) - .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) - .addComponent(btnFindLocal, javax.swing.GroupLayout.PREFERRED_SIZE, 90, javax.swing.GroupLayout.PREFERRED_SIZE) - .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) - .addComponent(btnFindOther, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE) - .addGap(0, 0, 0)) + panelFastLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) + .addGroup(panelFastLayout.createSequentialGroup() + .addGap(0, 0, 0) + .addComponent(btnFindMain, javax.swing.GroupLayout.PREFERRED_SIZE, 90, javax.swing.GroupLayout.PREFERRED_SIZE) + .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) + .addComponent(btnFindUs, javax.swing.GroupLayout.PREFERRED_SIZE, 90, javax.swing.GroupLayout.PREFERRED_SIZE) + .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) + .addComponent(btnFindBeta, javax.swing.GroupLayout.PREFERRED_SIZE, 90, javax.swing.GroupLayout.PREFERRED_SIZE) + .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) + .addComponent(btnFindLocal, javax.swing.GroupLayout.PREFERRED_SIZE, 90, javax.swing.GroupLayout.PREFERRED_SIZE) + .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) + .addComponent(btnFindOther, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE) + .addGap(0, 0, 0)) ); panelFastLayout.setVerticalGroup( - panelFastLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) - .addGroup(panelFastLayout.createSequentialGroup() - .addGap(0, 0, 0) - .addGroup(panelFastLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE) - .addComponent(btnFindMain, javax.swing.GroupLayout.PREFERRED_SIZE, 30, javax.swing.GroupLayout.PREFERRED_SIZE) - .addComponent(btnFindLocal, javax.swing.GroupLayout.PREFERRED_SIZE, 30, javax.swing.GroupLayout.PREFERRED_SIZE) - .addComponent(btnFindUs, javax.swing.GroupLayout.PREFERRED_SIZE, 30, javax.swing.GroupLayout.PREFERRED_SIZE) - .addComponent(btnFindBeta, javax.swing.GroupLayout.PREFERRED_SIZE, 30, javax.swing.GroupLayout.PREFERRED_SIZE) - .addComponent(btnFindOther, javax.swing.GroupLayout.PREFERRED_SIZE, 30, javax.swing.GroupLayout.PREFERRED_SIZE)) - .addGap(0, 0, 0)) + panelFastLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) + .addGroup(panelFastLayout.createSequentialGroup() + .addGap(0, 0, 0) + .addGroup(panelFastLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE) + .addComponent(btnFindMain, javax.swing.GroupLayout.PREFERRED_SIZE, 30, javax.swing.GroupLayout.PREFERRED_SIZE) + .addComponent(btnFindLocal, javax.swing.GroupLayout.PREFERRED_SIZE, 30, javax.swing.GroupLayout.PREFERRED_SIZE) + .addComponent(btnFindUs, javax.swing.GroupLayout.PREFERRED_SIZE, 30, javax.swing.GroupLayout.PREFERRED_SIZE) + .addComponent(btnFindBeta, javax.swing.GroupLayout.PREFERRED_SIZE, 30, javax.swing.GroupLayout.PREFERRED_SIZE) + .addComponent(btnFindOther, javax.swing.GroupLayout.PREFERRED_SIZE, 30, javax.swing.GroupLayout.PREFERRED_SIZE)) + .addGap(0, 0, 0)) ); txtPort.addKeyListener(new java.awt.event.KeyAdapter() { - - @Override public void keyTyped(java.awt.event.KeyEvent evt) { ConnectDialog.this.keyTyped(evt); } @@ -363,26 +360,26 @@ public class ConnectDialog extends MageDialog { javax.swing.GroupLayout panelServerLayout = new javax.swing.GroupLayout(panelServer); panelServer.setLayout(panelServerLayout); panelServerLayout.setHorizontalGroup( - panelServerLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) - .addGroup(panelServerLayout.createSequentialGroup() - .addComponent(txtServer, javax.swing.GroupLayout.PREFERRED_SIZE, 212, javax.swing.GroupLayout.PREFERRED_SIZE) - .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) - .addComponent(lblPort) - .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) - .addComponent(txtPort, javax.swing.GroupLayout.PREFERRED_SIZE, 75, javax.swing.GroupLayout.PREFERRED_SIZE) - .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) - .addComponent(btnCheckStatus, javax.swing.GroupLayout.DEFAULT_SIZE, 205, Short.MAX_VALUE) - .addGap(0, 0, 0)) + panelServerLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) + .addGroup(panelServerLayout.createSequentialGroup() + .addComponent(txtServer, javax.swing.GroupLayout.PREFERRED_SIZE, 212, javax.swing.GroupLayout.PREFERRED_SIZE) + .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) + .addComponent(lblPort) + .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) + .addComponent(txtPort, javax.swing.GroupLayout.PREFERRED_SIZE, 75, javax.swing.GroupLayout.PREFERRED_SIZE) + .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) + .addComponent(btnCheckStatus, javax.swing.GroupLayout.DEFAULT_SIZE, 205, Short.MAX_VALUE) + .addGap(0, 0, 0)) ); panelServerLayout.setVerticalGroup( - panelServerLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) - .addGroup(panelServerLayout.createSequentialGroup() - .addGap(0, 0, 0) - .addGroup(panelServerLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE) - .addComponent(txtServer, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE) - .addComponent(txtPort, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE) - .addComponent(lblPort) - .addComponent(btnCheckStatus, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE))) + panelServerLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) + .addGroup(panelServerLayout.createSequentialGroup() + .addGap(0, 0, 0) + .addGroup(panelServerLayout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE) + .addComponent(txtServer, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE) + .addComponent(txtPort, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE) + .addComponent(lblPort) + .addComponent(btnCheckStatus, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE))) ); btnWhatsNew.setText("Show what's new"); @@ -397,92 +394,92 @@ public class ConnectDialog extends MageDialog { javax.swing.GroupLayout layout = new javax.swing.GroupLayout(getContentPane()); getContentPane().setLayout(layout); layout.setHorizontalGroup( - layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) - .addGroup(layout.createSequentialGroup() - .addContainerGap() - .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING, false) - .addComponent(lblUserName, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE) - .addComponent(lblServer, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE) - .addComponent(lblFastConnect, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE) - .addComponent(lblPassword, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE) - .addComponent(lblFlag, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)) - .addGap(18, 18, 18) - .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) - .addComponent(lblStatus, javax.swing.GroupLayout.Alignment.TRAILING, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE) - .addComponent(chkForceUpdateDB, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE) - .addComponent(chkAutoConnect, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE) - .addComponent(txtUserName) - .addComponent(panelFlag, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE) - .addGroup(layout.createSequentialGroup() - .addComponent(btnConnect, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE) - .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) - .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING, false) - .addComponent(btnRegister, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE) - .addComponent(btnForgotPassword, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)) - .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) - .addComponent(btnCancel, javax.swing.GroupLayout.PREFERRED_SIZE, 77, javax.swing.GroupLayout.PREFERRED_SIZE)) - .addComponent(panelFast, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE) - .addComponent(panelServer, javax.swing.GroupLayout.Alignment.TRAILING, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE) - .addGroup(layout.createSequentialGroup() - .addComponent(jProxySettingsButton) - .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) - .addComponent(btnWhatsNew) - .addGap(0, 0, Short.MAX_VALUE)) - .addGroup(layout.createSequentialGroup() - .addComponent(txtPassword) - .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) - .addComponent(jLabel1))) - .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) - .addComponent(filler2, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE) - .addContainerGap()) + layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) + .addGroup(layout.createSequentialGroup() + .addContainerGap() + .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING, false) + .addComponent(lblUserName, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE) + .addComponent(lblServer, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE) + .addComponent(lblFastConnect, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE) + .addComponent(lblPassword, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE) + .addComponent(lblFlag, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)) + .addGap(18, 18, 18) + .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) + .addComponent(lblStatus, javax.swing.GroupLayout.Alignment.TRAILING, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE) + .addComponent(chkForceUpdateDB, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE) + .addComponent(chkAutoConnect, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE) + .addComponent(txtUserName) + .addComponent(panelFlag, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE) + .addGroup(layout.createSequentialGroup() + .addComponent(btnConnect, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE) + .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) + .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING, false) + .addComponent(btnRegister, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE) + .addComponent(btnForgotPassword, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)) + .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) + .addComponent(btnCancel, javax.swing.GroupLayout.PREFERRED_SIZE, 77, javax.swing.GroupLayout.PREFERRED_SIZE)) + .addComponent(panelFast, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE) + .addComponent(panelServer, javax.swing.GroupLayout.Alignment.TRAILING, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE) + .addGroup(layout.createSequentialGroup() + .addComponent(jProxySettingsButton) + .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) + .addComponent(btnWhatsNew) + .addGap(0, 0, Short.MAX_VALUE)) + .addGroup(layout.createSequentialGroup() + .addComponent(txtPassword) + .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) + .addComponent(jLabel1))) + .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) + .addComponent(filler2, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE) + .addContainerGap()) ); layout.setVerticalGroup( - layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) - .addGroup(javax.swing.GroupLayout.Alignment.TRAILING, layout.createSequentialGroup() - .addContainerGap() - .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) - .addComponent(panelFast, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE) - .addComponent(lblFastConnect, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)) - .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) - .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) - .addComponent(panelServer, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE) - .addComponent(lblServer, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)) - .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) - .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) - .addGroup(layout.createSequentialGroup() - .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) - .addComponent(txtUserName, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE) - .addComponent(lblUserName, javax.swing.GroupLayout.PREFERRED_SIZE, 20, javax.swing.GroupLayout.PREFERRED_SIZE)) - .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) - .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING, false) - .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE) - .addComponent(txtPassword) - .addComponent(jLabel1)) - .addComponent(lblPassword, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE))) - .addComponent(filler2, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)) - .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) - .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) - .addComponent(panelFlag, javax.swing.GroupLayout.PREFERRED_SIZE, 20, javax.swing.GroupLayout.PREFERRED_SIZE) - .addComponent(lblFlag, javax.swing.GroupLayout.PREFERRED_SIZE, 18, javax.swing.GroupLayout.PREFERRED_SIZE)) - .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.UNRELATED) - .addComponent(chkAutoConnect) - .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) - .addComponent(chkForceUpdateDB) - .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) - .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE) - .addComponent(jProxySettingsButton, javax.swing.GroupLayout.PREFERRED_SIZE, 30, javax.swing.GroupLayout.PREFERRED_SIZE) - .addComponent(btnWhatsNew, javax.swing.GroupLayout.PREFERRED_SIZE, 30, javax.swing.GroupLayout.PREFERRED_SIZE)) - .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.UNRELATED) - .addComponent(lblStatus, javax.swing.GroupLayout.PREFERRED_SIZE, 24, javax.swing.GroupLayout.PREFERRED_SIZE) - .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.UNRELATED) - .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.TRAILING, false) - .addGroup(layout.createSequentialGroup() - .addComponent(btnRegister, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE) - .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) - .addComponent(btnForgotPassword, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)) - .addComponent(btnConnect, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE) - .addComponent(btnCancel, javax.swing.GroupLayout.Alignment.LEADING, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)) - .addGap(23, 23, 23)) + layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) + .addGroup(javax.swing.GroupLayout.Alignment.TRAILING, layout.createSequentialGroup() + .addContainerGap() + .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) + .addComponent(panelFast, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE) + .addComponent(lblFastConnect, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)) + .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) + .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) + .addComponent(panelServer, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE) + .addComponent(lblServer, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)) + .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) + .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) + .addGroup(layout.createSequentialGroup() + .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) + .addComponent(txtUserName, javax.swing.GroupLayout.PREFERRED_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.PREFERRED_SIZE) + .addComponent(lblUserName, javax.swing.GroupLayout.PREFERRED_SIZE, 20, javax.swing.GroupLayout.PREFERRED_SIZE)) + .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) + .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING, false) + .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE) + .addComponent(txtPassword) + .addComponent(jLabel1)) + .addComponent(lblPassword, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE))) + .addComponent(filler2, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)) + .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) + .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) + .addComponent(panelFlag, javax.swing.GroupLayout.PREFERRED_SIZE, 20, javax.swing.GroupLayout.PREFERRED_SIZE) + .addComponent(lblFlag, javax.swing.GroupLayout.PREFERRED_SIZE, 18, javax.swing.GroupLayout.PREFERRED_SIZE)) + .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.UNRELATED) + .addComponent(chkAutoConnect) + .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) + .addComponent(chkForceUpdateDB) + .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) + .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.BASELINE) + .addComponent(jProxySettingsButton, javax.swing.GroupLayout.PREFERRED_SIZE, 30, javax.swing.GroupLayout.PREFERRED_SIZE) + .addComponent(btnWhatsNew, javax.swing.GroupLayout.PREFERRED_SIZE, 30, javax.swing.GroupLayout.PREFERRED_SIZE)) + .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.UNRELATED) + .addComponent(lblStatus, javax.swing.GroupLayout.PREFERRED_SIZE, 24, javax.swing.GroupLayout.PREFERRED_SIZE) + .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.UNRELATED) + .addGroup(layout.createParallelGroup(javax.swing.GroupLayout.Alignment.TRAILING, false) + .addGroup(layout.createSequentialGroup() + .addComponent(btnRegister, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE) + .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) + .addComponent(btnForgotPassword, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)) + .addComponent(btnConnect, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE) + .addComponent(btnCancel, javax.swing.GroupLayout.Alignment.LEADING, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)) + .addGap(23, 23, 23)) ); lblFastConnect.getAccessibleContext().setAccessibleName("Fast connect to:"); @@ -768,7 +765,7 @@ public class ConnectDialog extends MageDialog { }//GEN-LAST:event_btnFind2findPublicServerActionPerformed private void connectXmageus(java.awt.event.ActionEvent evt) { - String serverAddress = "mtg.powersofwar.com"; + String serverAddress = "us.xmage.today"; this.txtServer.setText(serverAddress); this.txtPort.setText("17171"); // Update userName and password according to the chosen server. @@ -777,7 +774,7 @@ public class ConnectDialog extends MageDialog { } private void connectBeta(java.awt.event.ActionEvent evt) { - String serverAddress = "xmage.today"; + String serverAddress = "beta.xmage.today"; this.txtServer.setText(serverAddress); this.txtPort.setText("17171"); // Update userName and password according to the chosen server. From 8dc6e152af0a05ffadbd82eec8d25e62f26020db Mon Sep 17 00:00:00 2001 From: Oleg Agafonov Date: Tue, 10 Sep 2019 00:33:47 +0400 Subject: [PATCH 010/373] Prepare next release --- Mage.Client/pom.xml | 2 +- Mage.Common/pom.xml | 2 +- Mage.Plugins/Mage.Counter.Plugin/pom.xml | 2 +- Mage.Plugins/pom.xml | 2 +- Mage.Server.Console/pom.xml | 2 +- Mage.Server.Plugins/Mage.Deck.Constructed/pom.xml | 2 +- Mage.Server.Plugins/Mage.Deck.Limited/pom.xml | 2 +- Mage.Server.Plugins/Mage.Game.BrawlDuel/pom.xml | 2 +- Mage.Server.Plugins/Mage.Game.BrawlFreeForAll/pom.xml | 2 +- Mage.Server.Plugins/Mage.Game.CanadianHighlanderDuel/pom.xml | 2 +- Mage.Server.Plugins/Mage.Game.CommanderDuel/pom.xml | 2 +- Mage.Server.Plugins/Mage.Game.CommanderFreeForAll/pom.xml | 2 +- Mage.Server.Plugins/Mage.Game.FreeForAll/pom.xml | 2 +- Mage.Server.Plugins/Mage.Game.FreeformCommanderDuel/pom.xml | 2 +- .../Mage.Game.FreeformCommanderFreeForAll/pom.xml | 2 +- Mage.Server.Plugins/Mage.Game.MomirDuel/pom.xml | 2 +- Mage.Server.Plugins/Mage.Game.MomirGame/pom.xml | 2 +- Mage.Server.Plugins/Mage.Game.OathbreakerDuel/pom.xml | 4 ++-- Mage.Server.Plugins/Mage.Game.OathbreakerFreeForAll/pom.xml | 2 +- .../Mage.Game.PennyDreadfulCommanderFreeForAll/pom.xml | 2 +- Mage.Server.Plugins/Mage.Game.TinyLeadersDuel/pom.xml | 2 +- Mage.Server.Plugins/Mage.Game.TwoPlayerDuel/pom.xml | 2 +- Mage.Server.Plugins/Mage.Player.AI.DraftBot/pom.xml | 2 +- Mage.Server.Plugins/Mage.Player.AI.MA/pom.xml | 2 +- Mage.Server.Plugins/Mage.Player.AI/pom.xml | 2 +- Mage.Server.Plugins/Mage.Player.AIMCTS/pom.xml | 2 +- Mage.Server.Plugins/Mage.Player.AIMinimax/pom.xml | 2 +- Mage.Server.Plugins/Mage.Player.Human/pom.xml | 2 +- Mage.Server.Plugins/Mage.Tournament.BoosterDraft/pom.xml | 2 +- Mage.Server.Plugins/Mage.Tournament.Constructed/pom.xml | 2 +- Mage.Server.Plugins/Mage.Tournament.Sealed/pom.xml | 2 +- Mage.Server.Plugins/pom.xml | 2 +- Mage.Server/pom.xml | 2 +- Mage.Sets/pom.xml | 2 +- Mage.Tests/pom.xml | 2 +- Mage.Verify/pom.xml | 4 ++-- Mage/pom.xml | 2 +- pom.xml | 4 ++-- 38 files changed, 41 insertions(+), 41 deletions(-) diff --git a/Mage.Client/pom.xml b/Mage.Client/pom.xml index fe209e15e5..399d2d8a35 100644 --- a/Mage.Client/pom.xml +++ b/Mage.Client/pom.xml @@ -6,7 +6,7 @@ org.mage mage-root - 1.4.37 + 1.4.38 mage-client diff --git a/Mage.Common/pom.xml b/Mage.Common/pom.xml index 2791a46b63..c70174e465 100644 --- a/Mage.Common/pom.xml +++ b/Mage.Common/pom.xml @@ -7,7 +7,7 @@ org.mage mage-root - 1.4.37 + 1.4.38 mage-common diff --git a/Mage.Plugins/Mage.Counter.Plugin/pom.xml b/Mage.Plugins/Mage.Counter.Plugin/pom.xml index 451e8c6767..5c784e951a 100644 --- a/Mage.Plugins/Mage.Counter.Plugin/pom.xml +++ b/Mage.Plugins/Mage.Counter.Plugin/pom.xml @@ -7,7 +7,7 @@ org.mage mage-plugins - 1.4.37 + 1.4.38 mage-counter-plugin diff --git a/Mage.Plugins/pom.xml b/Mage.Plugins/pom.xml index 130037cdfc..3758ccc807 100644 --- a/Mage.Plugins/pom.xml +++ b/Mage.Plugins/pom.xml @@ -7,7 +7,7 @@ org.mage mage-root - 1.4.37 + 1.4.38 mage-plugins diff --git a/Mage.Server.Console/pom.xml b/Mage.Server.Console/pom.xml index 13a2ee42eb..cdb5f300a8 100644 --- a/Mage.Server.Console/pom.xml +++ b/Mage.Server.Console/pom.xml @@ -6,7 +6,7 @@ org.mage mage-root - 1.4.37 + 1.4.38 mage.server.console diff --git a/Mage.Server.Plugins/Mage.Deck.Constructed/pom.xml b/Mage.Server.Plugins/Mage.Deck.Constructed/pom.xml index 584bfe3d3f..3ac439742f 100644 --- a/Mage.Server.Plugins/Mage.Deck.Constructed/pom.xml +++ b/Mage.Server.Plugins/Mage.Deck.Constructed/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.37 + 1.4.38 mage-deck-constructed diff --git a/Mage.Server.Plugins/Mage.Deck.Limited/pom.xml b/Mage.Server.Plugins/Mage.Deck.Limited/pom.xml index 3bc05c16a5..13841539ed 100644 --- a/Mage.Server.Plugins/Mage.Deck.Limited/pom.xml +++ b/Mage.Server.Plugins/Mage.Deck.Limited/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.37 + 1.4.38 mage-deck-limited diff --git a/Mage.Server.Plugins/Mage.Game.BrawlDuel/pom.xml b/Mage.Server.Plugins/Mage.Game.BrawlDuel/pom.xml index ccd689bdb9..76b6ad42a3 100644 --- a/Mage.Server.Plugins/Mage.Game.BrawlDuel/pom.xml +++ b/Mage.Server.Plugins/Mage.Game.BrawlDuel/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.37 + 1.4.38 mage-game-brawlduel diff --git a/Mage.Server.Plugins/Mage.Game.BrawlFreeForAll/pom.xml b/Mage.Server.Plugins/Mage.Game.BrawlFreeForAll/pom.xml index 361659397c..738d8a5ff5 100644 --- a/Mage.Server.Plugins/Mage.Game.BrawlFreeForAll/pom.xml +++ b/Mage.Server.Plugins/Mage.Game.BrawlFreeForAll/pom.xml @@ -6,7 +6,7 @@ org.mage mage-server-plugins - 1.4.37 + 1.4.38 mage-game-brawlfreeforall diff --git a/Mage.Server.Plugins/Mage.Game.CanadianHighlanderDuel/pom.xml b/Mage.Server.Plugins/Mage.Game.CanadianHighlanderDuel/pom.xml index b45bc7a4c4..a3111d63f6 100644 --- a/Mage.Server.Plugins/Mage.Game.CanadianHighlanderDuel/pom.xml +++ b/Mage.Server.Plugins/Mage.Game.CanadianHighlanderDuel/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.37 + 1.4.38 mage-game-canadianhighlanderduel diff --git a/Mage.Server.Plugins/Mage.Game.CommanderDuel/pom.xml b/Mage.Server.Plugins/Mage.Game.CommanderDuel/pom.xml index 00ff1eefa5..51bf17613c 100644 --- a/Mage.Server.Plugins/Mage.Game.CommanderDuel/pom.xml +++ b/Mage.Server.Plugins/Mage.Game.CommanderDuel/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.37 + 1.4.38 mage-game-commanderduel diff --git a/Mage.Server.Plugins/Mage.Game.CommanderFreeForAll/pom.xml b/Mage.Server.Plugins/Mage.Game.CommanderFreeForAll/pom.xml index 0b56915db6..3bce053074 100644 --- a/Mage.Server.Plugins/Mage.Game.CommanderFreeForAll/pom.xml +++ b/Mage.Server.Plugins/Mage.Game.CommanderFreeForAll/pom.xml @@ -6,7 +6,7 @@ org.mage mage-server-plugins - 1.4.37 + 1.4.38 mage-game-commanderfreeforall diff --git a/Mage.Server.Plugins/Mage.Game.FreeForAll/pom.xml b/Mage.Server.Plugins/Mage.Game.FreeForAll/pom.xml index 8570bbca78..8627c42417 100644 --- a/Mage.Server.Plugins/Mage.Game.FreeForAll/pom.xml +++ b/Mage.Server.Plugins/Mage.Game.FreeForAll/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.37 + 1.4.38 mage-game-freeforall diff --git a/Mage.Server.Plugins/Mage.Game.FreeformCommanderDuel/pom.xml b/Mage.Server.Plugins/Mage.Game.FreeformCommanderDuel/pom.xml index 07ef467487..c5ba60eb28 100644 --- a/Mage.Server.Plugins/Mage.Game.FreeformCommanderDuel/pom.xml +++ b/Mage.Server.Plugins/Mage.Game.FreeformCommanderDuel/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.37 + 1.4.38 mage-game-freeformcommanderduel diff --git a/Mage.Server.Plugins/Mage.Game.FreeformCommanderFreeForAll/pom.xml b/Mage.Server.Plugins/Mage.Game.FreeformCommanderFreeForAll/pom.xml index 656ea15123..0d4a4abedf 100644 --- a/Mage.Server.Plugins/Mage.Game.FreeformCommanderFreeForAll/pom.xml +++ b/Mage.Server.Plugins/Mage.Game.FreeformCommanderFreeForAll/pom.xml @@ -6,7 +6,7 @@ org.mage mage-server-plugins - 1.4.37 + 1.4.38 mage-game-freeformcommanderfreeforall diff --git a/Mage.Server.Plugins/Mage.Game.MomirDuel/pom.xml b/Mage.Server.Plugins/Mage.Game.MomirDuel/pom.xml index 3cb630bf94..b1587dc6f5 100644 --- a/Mage.Server.Plugins/Mage.Game.MomirDuel/pom.xml +++ b/Mage.Server.Plugins/Mage.Game.MomirDuel/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.37 + 1.4.38 mage-game-momirduel diff --git a/Mage.Server.Plugins/Mage.Game.MomirGame/pom.xml b/Mage.Server.Plugins/Mage.Game.MomirGame/pom.xml index 1d671df0b8..138e2c121b 100644 --- a/Mage.Server.Plugins/Mage.Game.MomirGame/pom.xml +++ b/Mage.Server.Plugins/Mage.Game.MomirGame/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.37 + 1.4.38 mage-game-momirfreeforall diff --git a/Mage.Server.Plugins/Mage.Game.OathbreakerDuel/pom.xml b/Mage.Server.Plugins/Mage.Game.OathbreakerDuel/pom.xml index ce0e6aec0c..f58c13f4ff 100644 --- a/Mage.Server.Plugins/Mage.Game.OathbreakerDuel/pom.xml +++ b/Mage.Server.Plugins/Mage.Game.OathbreakerDuel/pom.xml @@ -6,7 +6,7 @@ org.mage mage-server-plugins - 1.4.37 + 1.4.38 mage-game-oathbreakerduel @@ -22,7 +22,7 @@ org.mage mage-game-oathbreakerfreeforall - 1.4.37 + 1.4.38 compile diff --git a/Mage.Server.Plugins/Mage.Game.OathbreakerFreeForAll/pom.xml b/Mage.Server.Plugins/Mage.Game.OathbreakerFreeForAll/pom.xml index 902049f967..f3bc0fc572 100644 --- a/Mage.Server.Plugins/Mage.Game.OathbreakerFreeForAll/pom.xml +++ b/Mage.Server.Plugins/Mage.Game.OathbreakerFreeForAll/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.37 + 1.4.38 mage-game-oathbreakerfreeforall diff --git a/Mage.Server.Plugins/Mage.Game.PennyDreadfulCommanderFreeForAll/pom.xml b/Mage.Server.Plugins/Mage.Game.PennyDreadfulCommanderFreeForAll/pom.xml index 942b63e711..4d81776e12 100644 --- a/Mage.Server.Plugins/Mage.Game.PennyDreadfulCommanderFreeForAll/pom.xml +++ b/Mage.Server.Plugins/Mage.Game.PennyDreadfulCommanderFreeForAll/pom.xml @@ -6,7 +6,7 @@ org.mage mage-server-plugins - 1.4.37 + 1.4.38 mage-game-pennydreadfulcommanderfreeforall diff --git a/Mage.Server.Plugins/Mage.Game.TinyLeadersDuel/pom.xml b/Mage.Server.Plugins/Mage.Game.TinyLeadersDuel/pom.xml index c38ad44ed2..befe91a990 100644 --- a/Mage.Server.Plugins/Mage.Game.TinyLeadersDuel/pom.xml +++ b/Mage.Server.Plugins/Mage.Game.TinyLeadersDuel/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.37 + 1.4.38 mage-game-tinyleadersduel diff --git a/Mage.Server.Plugins/Mage.Game.TwoPlayerDuel/pom.xml b/Mage.Server.Plugins/Mage.Game.TwoPlayerDuel/pom.xml index 8c99266e0e..ceb330bd4e 100644 --- a/Mage.Server.Plugins/Mage.Game.TwoPlayerDuel/pom.xml +++ b/Mage.Server.Plugins/Mage.Game.TwoPlayerDuel/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.37 + 1.4.38 mage-game-twoplayerduel diff --git a/Mage.Server.Plugins/Mage.Player.AI.DraftBot/pom.xml b/Mage.Server.Plugins/Mage.Player.AI.DraftBot/pom.xml index 92b12f18e1..ad088fb549 100644 --- a/Mage.Server.Plugins/Mage.Player.AI.DraftBot/pom.xml +++ b/Mage.Server.Plugins/Mage.Player.AI.DraftBot/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.37 + 1.4.38 mage-player-ai-draftbot diff --git a/Mage.Server.Plugins/Mage.Player.AI.MA/pom.xml b/Mage.Server.Plugins/Mage.Player.AI.MA/pom.xml index 4cd66cab77..fa4ad1a121 100644 --- a/Mage.Server.Plugins/Mage.Player.AI.MA/pom.xml +++ b/Mage.Server.Plugins/Mage.Player.AI.MA/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.37 + 1.4.38 mage-player-ai-ma diff --git a/Mage.Server.Plugins/Mage.Player.AI/pom.xml b/Mage.Server.Plugins/Mage.Player.AI/pom.xml index 1faa9b3f92..71d893bcd2 100644 --- a/Mage.Server.Plugins/Mage.Player.AI/pom.xml +++ b/Mage.Server.Plugins/Mage.Player.AI/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.37 + 1.4.38 mage-player-ai diff --git a/Mage.Server.Plugins/Mage.Player.AIMCTS/pom.xml b/Mage.Server.Plugins/Mage.Player.AIMCTS/pom.xml index b3a9a5435c..0a2eb8b997 100644 --- a/Mage.Server.Plugins/Mage.Player.AIMCTS/pom.xml +++ b/Mage.Server.Plugins/Mage.Player.AIMCTS/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.37 + 1.4.38 mage-player-ai-mcts diff --git a/Mage.Server.Plugins/Mage.Player.AIMinimax/pom.xml b/Mage.Server.Plugins/Mage.Player.AIMinimax/pom.xml index 9ad8a71e08..87acc59bb0 100644 --- a/Mage.Server.Plugins/Mage.Player.AIMinimax/pom.xml +++ b/Mage.Server.Plugins/Mage.Player.AIMinimax/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.37 + 1.4.38 mage-player-aiminimax diff --git a/Mage.Server.Plugins/Mage.Player.Human/pom.xml b/Mage.Server.Plugins/Mage.Player.Human/pom.xml index 95e743bba2..f62a0362c5 100644 --- a/Mage.Server.Plugins/Mage.Player.Human/pom.xml +++ b/Mage.Server.Plugins/Mage.Player.Human/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.37 + 1.4.38 mage-player-human diff --git a/Mage.Server.Plugins/Mage.Tournament.BoosterDraft/pom.xml b/Mage.Server.Plugins/Mage.Tournament.BoosterDraft/pom.xml index 4cc129d679..e10e6f3804 100644 --- a/Mage.Server.Plugins/Mage.Tournament.BoosterDraft/pom.xml +++ b/Mage.Server.Plugins/Mage.Tournament.BoosterDraft/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.37 + 1.4.38 mage-tournament-boosterdraft diff --git a/Mage.Server.Plugins/Mage.Tournament.Constructed/pom.xml b/Mage.Server.Plugins/Mage.Tournament.Constructed/pom.xml index 50eefc4743..bc41290a61 100644 --- a/Mage.Server.Plugins/Mage.Tournament.Constructed/pom.xml +++ b/Mage.Server.Plugins/Mage.Tournament.Constructed/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.37 + 1.4.38 mage-tournament-constructed diff --git a/Mage.Server.Plugins/Mage.Tournament.Sealed/pom.xml b/Mage.Server.Plugins/Mage.Tournament.Sealed/pom.xml index 43727030e5..44cb2749a2 100644 --- a/Mage.Server.Plugins/Mage.Tournament.Sealed/pom.xml +++ b/Mage.Server.Plugins/Mage.Tournament.Sealed/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.37 + 1.4.38 mage-tournament-sealed diff --git a/Mage.Server.Plugins/pom.xml b/Mage.Server.Plugins/pom.xml index 12c74d9094..ecc291cabc 100644 --- a/Mage.Server.Plugins/pom.xml +++ b/Mage.Server.Plugins/pom.xml @@ -7,7 +7,7 @@ org.mage mage-root - 1.4.37 + 1.4.38 mage-server-plugins diff --git a/Mage.Server/pom.xml b/Mage.Server/pom.xml index 47e27da1f6..7400d723f3 100644 --- a/Mage.Server/pom.xml +++ b/Mage.Server/pom.xml @@ -6,7 +6,7 @@ org.mage mage-root - 1.4.37 + 1.4.38 mage-server diff --git a/Mage.Sets/pom.xml b/Mage.Sets/pom.xml index 185cde6f19..1274851f79 100644 --- a/Mage.Sets/pom.xml +++ b/Mage.Sets/pom.xml @@ -7,7 +7,7 @@ org.mage mage-root - 1.4.37 + 1.4.38 mage-sets diff --git a/Mage.Tests/pom.xml b/Mage.Tests/pom.xml index eab8881662..6939dccfec 100644 --- a/Mage.Tests/pom.xml +++ b/Mage.Tests/pom.xml @@ -6,7 +6,7 @@ org.mage mage-root - 1.4.37 + 1.4.38 mage-tests diff --git a/Mage.Verify/pom.xml b/Mage.Verify/pom.xml index a4fb3c8fcd..59ac81ced7 100644 --- a/Mage.Verify/pom.xml +++ b/Mage.Verify/pom.xml @@ -6,7 +6,7 @@ org.mage mage-root - 1.4.37 + 1.4.38 mage-verify @@ -49,7 +49,7 @@ org.mage mage-client - 1.4.37 + 1.4.38 diff --git a/Mage/pom.xml b/Mage/pom.xml index d23f0dc18d..494a5a3a18 100644 --- a/Mage/pom.xml +++ b/Mage/pom.xml @@ -6,7 +6,7 @@ org.mage mage-root - 1.4.37 + 1.4.38 mage diff --git a/pom.xml b/pom.xml index 8375161005..a7b6eb9414 100644 --- a/pom.xml +++ b/pom.xml @@ -6,7 +6,7 @@ org.mage mage-root - 1.4.37 + 1.4.38 pom Mage Root Mage Root POM @@ -86,7 +86,7 @@ - 1.4.37 + 1.4.38 UTF-8 yyyy-MM-dd'T'HH:mm:ss'Z' From 0ce54320692e391eb26c9840c6840424a4c0aeae Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 9 Sep 2019 16:09:39 -0400 Subject: [PATCH 011/373] updated ELD spoiler --- Utils/mtg-cards-data.txt | 13 +++++++++++++ 1 file changed, 13 insertions(+) diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index b43bf6e179..fbde76ea2a 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -35997,6 +35997,8 @@ All That Glitters|Throne of Eldraine|2|U|{1}{W}|Enchantment - Aura|||Enchant cre The Circle of Loyalty|Throne of Eldraine|9|M|{4}{W}{W}|Legendary Artifact|||This spell costs {1} less to cast for each Knight you control.$Creatures you control get +1/+1.$Whenever you cast a legendary spell, create a 2/2 white Knight creature token with vigilance.${3}{W}, {T}: Create a 2/2 white Knight creature token with vigilance.| Faerie Guidemother|Throne of Eldraine|11|C|{W}|Creature - Faerie|1|1|Flying| Gift of the Fae|Throne of Eldraine|11|C|{1}{W}|Sorcery - Adventure|1|1|Target creature gets +2/+1 and gains flying until end of turn.| +Chop Down|Throne of Eldraine|14|R|{2}{W}|Instant - Adventure|1|2|Destroy target creature with power 4 or greater.| +Giant Killer|Throne of Eldraine|14|R|{W}|Creature - Human Peasant|1|2|{1}{W}, {T}: Tap target creature.| Shining Armor|Throne of Eldraine|29|C|{1}{W}|Artifact - Equipment|||Flash$When Shining Armor enters the battlefield, attach it to target Knight you control.$Equipped creature gets +0/+2 and has vigilance.$Equip {3}| Silverflame Ritual|Throne of Eldraine|30|C|{3}{W}|Sorcery|||Put a +1/+1 counter on each creature you control.$Adamant — If at least three white mana was spent to cast this spell, creatures you control gain vigilance until end of turn.| Animating Faerie|Throne of Eldraine|38|U|{2}{U}|Creature - Faerie|2|2|Flying| @@ -36016,6 +36018,8 @@ Belle of the Brawl|Throne of Eldraine|78|U|{2}{B}|Creature - Human Knight|3|2|Me Eye Collector|Throne of Eldraine|86|C|{B}|Creature - Faerie|1|1|Flying$Whenever Eye Collector deals combat damage to a player, each player puts the top card of their library into their graveyard.| Foulmire Knight|Throne of Eldraine|90|U|{B}|Creature - Zombie Knight|1|1|Deathtouch| Profane Insight|Throne of Eldraine|90|U|{2}{B}|Instant - Adventure|1|1|You draw a card and you lose 1 life.| +Murderous Rider|Throne of Eldraine|97|R|{1}{B}{B}|Creature - Zombie Knight|2|3|Lifelink$When Murderous Rider dies, put it on the bottom of its owner's library.| +Swift End|Throne of Eldraine|97|R|{1}{B}{B}|Instant - Adventure|2|3|Destroy target creature or planeswalker. You lose 2 life.| Alter Fate|Throne of Eldraine|99|U|{1}{B}|Sorcery - Adventure|2|2|Return target creature card from your graveyard to your hand.| Order of Midnight|Throne of Eldraine|99|U|{1}{B}|Creature - Human Knight|2|2|Flying$Order of Midnight can't block.| Piper of the Swarm|Throne of Eldraine|100|R|{1}{B}|Creature - Human Warlock|1|3|Rats you control have menace.${1}{B}, {T}: Create a 1/1 black Rat creature token.${2}{B}{B}, {T}, Sacrifice three Rats: Gain control of target creature.| @@ -36024,10 +36028,17 @@ Curry Favor|Throne of Eldraine|105|C|{B}|Sorcery - Adventure|2|1|You gain X life Smitten Swordmaster|Throne of Eldraine|105|C|{1}{B}|Creature - Human Knight|2|1|Lifelink| Syr Konrad, the Grim|Throne of Eldraine|107|U|{3}{B}{B}|Legendary Creature - Human Knight|5|4|Whenever another creature dies, or a creature card is put into a graveyard from anywhere other than the battlefield, or a creature card leaves your graveyard, Syr Konrad, the Grim deals 1 damage to each opponent.${1}{B}: Each player puts the top card of their library into their graveyard.| Wicked Guardian|Throne of Eldraine|109|C|{3}{B}|Creature - Human Noble|4|2|When Wicked Guardian enters the battlefield, you may have it deal 2 damage to another creature you control. If you do, draw a card.| +Wishclaw Talisman|Throne of Eldraine|110|R|{1}{B}|Artifact|||Wishclaw Talisman enters the battlefield with three wish counters on it.${1}, {T}, Remove a wish counter from Wishclaw Talisman: Search your library for a card, put it into your hand, then shuffle your library. An opponent gains control of Wishclaw Talisman. Activate this ability only during your turn.| +Witch's Vengeance|Throne of Eldraine|111|R|{1}{B}{B}|Sorcery|||Creatures of the creature type of your choice get -3/-3 until end of turn.| +Blow Your House Down|Throne of Eldraine|114|C|{2}{R}|Sorcery|||Up to three target creatures can't block this turn. Destroy any of them that are Walls.| +Brimstone Trebuchet|Throne of Eldraine|116|C|{2}{R}|Artifact Creature - Wall|1|3|Defender, reach${T}: Brimstone Trebuchet deals 1 damage to each opponent.$Whenever a Knight enters the battlefield under your control, untap Brimstone Trebuchet.| +Burning-Yard Trainer|Throne of Eldraine|117|U|{4}{R}|Creature - Human Knight|3|3|Trample, haste$When Burning-Yard Trainer enters the battlefield, another target Knight you control gets +2/+2 and gains trample and haste until end of turn.| Crystal Slipper|Throne of Eldraine|119|C|{1}{R}|Artifact - Equipment|||Equipped creature gets +1/+0 and has haste.$Equip {1}| +Embercleave|Throne of Eldraine|120|M|{4}{R}{R}|Legendary Artifact - Equipment|||Flash$This spell costs {1} less for each attacking creature you control.$When Embercleave enters the battlefield, attach it to target creature you control.$Equipped creature gets +1/+1 and has double strike and trample.$Equip {3}| Embereth Paladin|Throne of Eldraine|121|C|{3}{R}|Creature - Human Knight|4|1|Haste$Adamant — If at least three red mana was spent to cast this spell, Embereth Paladin enters the battlefield with a +1/+1 counter on it.| Battle Display|Throne of Eldraine|122|U|{R}|Sorcery - Adventure|2|1|Destroy target artifact.| Embereth Shieldbreaker|Throne of Eldraine|122|U|{1}{R}|Creature - Human Knight|2|1|| +Joust|Throne of Eldraine|129|U|{1}{R}|Sorcery|||Choose target creature you control and target creature you don't control. The creature you control gets +2/+1 until end of turn if it's a Knight. Then those creatures fight each other.| Slaying Fire|Throne of Eldraine|143|U|{2}{R}|Instant|||Slaying Fire deals 3 damage to any target.$Adamant — If at least three red mana was spent to cast this spell, it deals 4 damage instead.| Beanstalk Giant|Throne of Eldraine|149|U|{6}{G}|Creature - Giant|*|*|Beanstalk Giant's power and toughness are each equal to the number of lands you control.| Fertile Footsteps|Throne of Eldraine|149|U|{2}{G}|Sorcery - Adventure|*|*|Search your library for a basic land card, put it onto the battlefield, then shuffle your library.| @@ -36042,6 +36053,7 @@ Questing Beast|Throne of Eldraine|171|M|{2}{G}{G}|Legendary Creature - Beast|4|4 Return to Nature|Throne of Eldraine|173|C|{1}{G}|Instant|||Choose one —$• Destroy target artifact.$• Destroy target enchantment.$• Exile target card from a graveyard.| Rosethorn Acolyte|Throne of Eldraine|174|C|{2}{G}|Creature - Elf Druid|2|3|{T}: Add one mana of any color.| Seasonal Ritual|Throne of Eldraine|174|C|{G}|Sorcery - Adventure|2|3|Add one mana of any color.| +Wicked Wolf|Throne of Eldraine|181|R|{2}{G}{G}|Creature - Wolf|3|3|When Wicked Wolf enters the battlefield, it fights up to one target creature you don't control.$Sacrifice a Food: Put a +1/+1 counter on Wicked Wolf. It gains indestructible until end of turn. Tap it.| Wildwood Tracker|Throne of Eldraine|183|C|{G}|Creature - Elf Warrior|1|1|Whenever Wildwood Tracker attacks or blocks, if you control another non-Human creature, Wildwood Tracker gets +1/+1 until end of turn.| Garruk, Cursed Huntsman|Throne of Eldraine|191|M|{4}{B}{G}|Legendary Planeswalker - Garruk|5|0: Create two 2/2 black and green Wolf creature tokens with "When this creature dies, put a loyalty counter on each Garruk you control."$−3: Destroy target creature. Draw a card.$−6: You get an emblem with "Creatures you control get +3/+3 and have trample."| Inspiring Veteran|Throne of Eldraine|194|U|{R}{W}|Creature - Human Knight|2|2|Other Knights you control get +1/+1.| @@ -36057,6 +36069,7 @@ Fireborn Knight|Throne of Eldraine|210|U|{R/W}{R/W}{R/W}{R/W}|Creature - Human K Enchanted Carriage|Throne of Eldraine|218|U|{5}|Artifact - Vehicle|4|4|When Enchanted Carriage enters the battlefield, create two 1/1 white Mouse creature tokens.$Crew 2| Golden Egg|Throne of Eldraine|220|C|{2}|Artifact - Food|||When Golden Egg enters the battlefield, draw a card.${1}, {T}, Sacrifice Golden Egg: Add one mana of any color.${2}, {T}, Sacrifice Golden Egg: You gain 3 life.| Heraldic Banner|Throne of Eldraine|222|U|{3}|Artifact|||As Heraldic Banner enters the battlefield, choose a color.$Creatures you control of the chosen color get +1/+0.${T}: Add one mana of the chosen color.| +Jousting Dummy|Throne of Eldraine|224|C|{2}|Artifact Creature - Scarecrow Knight|2|1|{3}: Jousting Dummy gets +1/+0 until end of turn.| Tournament Grounds|Throne of Eldraine|248|U||Land|||{T}: Add {C}.${T}: Add {R}, {W}, or {B}. Spend this mana only to cast a Knight or Equipment spell.| Witch's Cottage|Throne of Eldraine|249|C||Land - Swamp|||({T}: Add {B}.)$Witch's Cottage enters the battlefield tapped unless you control three or more other Swamps.$When Witch's Cottage enters the battlefield untapped, you may put target creature card from your graveyard on top of your library.| Rowan, Fearless Sparkmage|Throne of Eldraine|304|M|{3}{R}{R}|Legendary Planeswalker - Rowan|5|+1: Up to one target creature gets +3/+0 and gains first strike until end of turn.$−2: Rowan, Fearless Sparkmage deals 1 damage to each of up to two target creatures. Those creatures can't block this turn.$−9: Gain control of all creatures until end of turn. Untap them. They gain haste until end of turn.| From bf46b8e8ffa301c6fd9693f8693de72e9cd354e5 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 9 Sep 2019 16:10:43 -0400 Subject: [PATCH 012/373] Implemented Jousting Dummy --- Mage.Sets/src/mage/cards/j/JoustingDummy.java | 42 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 43 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/j/JoustingDummy.java diff --git a/Mage.Sets/src/mage/cards/j/JoustingDummy.java b/Mage.Sets/src/mage/cards/j/JoustingDummy.java new file mode 100644 index 0000000000..a6a4d73cdc --- /dev/null +++ b/Mage.Sets/src/mage/cards/j/JoustingDummy.java @@ -0,0 +1,42 @@ +package mage.cards.j; + +import mage.MageInt; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.costs.mana.GenericManaCost; +import mage.abilities.effects.common.continuous.BoostSourceEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class JoustingDummy extends CardImpl { + + public JoustingDummy(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT, CardType.CREATURE}, "{2}"); + + this.subtype.add(SubType.SCARECROW); + this.subtype.add(SubType.KNIGHT); + this.power = new MageInt(2); + this.toughness = new MageInt(1); + + // {3}: Jousting Dummy gets +1/+0 until end of turn. + this.addAbility(new SimpleActivatedAbility( + new BoostSourceEffect(1, 0, Duration.EndOfTurn), new GenericManaCost(3) + )); + } + + private JoustingDummy(final JoustingDummy card) { + super(card); + } + + @Override + public JoustingDummy copy() { + return new JoustingDummy(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 7696dbf967..3b472e8c2e 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -60,6 +60,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Golden Egg", 220, Rarity.COMMON, mage.cards.g.GoldenEgg.class)); cards.add(new SetCardInfo("Heraldic Banner", 222, Rarity.UNCOMMON, mage.cards.h.HeraldicBanner.class)); cards.add(new SetCardInfo("Inspiring Veteran", 194, Rarity.UNCOMMON, mage.cards.i.InspiringVeteran.class)); + cards.add(new SetCardInfo("Jousting Dummy", 224, Rarity.COMMON, mage.cards.j.JoustingDummy.class)); cards.add(new SetCardInfo("Keeper of Fables", 163, Rarity.UNCOMMON, mage.cards.k.KeeperOfFables.class)); cards.add(new SetCardInfo("Knights' Charge", 328, Rarity.RARE, mage.cards.k.KnightsCharge.class)); cards.add(new SetCardInfo("Korvold, Fae-Cursed King", 329, Rarity.MYTHIC, mage.cards.k.KorvoldFaeCursedKing.class)); From 76cba37b7ccb829b43257541907f55742158dac6 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 9 Sep 2019 16:24:34 -0400 Subject: [PATCH 013/373] Implemented Once Upon a Time --- Mage.Sets/src/mage/cards/o/OnceUponATime.java | 106 ++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 107 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/o/OnceUponATime.java diff --git a/Mage.Sets/src/mage/cards/o/OnceUponATime.java b/Mage.Sets/src/mage/cards/o/OnceUponATime.java new file mode 100644 index 0000000000..3a3559d9fa --- /dev/null +++ b/Mage.Sets/src/mage/cards/o/OnceUponATime.java @@ -0,0 +1,106 @@ +package mage.cards.o; + +import mage.abilities.Ability; +import mage.abilities.condition.Condition; +import mage.abilities.costs.AlternativeCostSourceAbility; +import mage.abilities.dynamicvalue.common.StaticValue; +import mage.abilities.effects.common.LookLibraryAndPickControllerEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.WatcherScope; +import mage.constants.Zone; +import mage.filter.FilterCard; +import mage.filter.predicate.Predicates; +import mage.filter.predicate.mageobject.CardTypePredicate; +import mage.game.Game; +import mage.game.events.GameEvent; +import mage.watchers.Watcher; + +import java.util.HashSet; +import java.util.Set; +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class OnceUponATime extends CardImpl { + + private static final FilterCard filter = new FilterCard("a creature or land card"); + + static { + filter.add(Predicates.or( + new CardTypePredicate(CardType.CREATURE), + new CardTypePredicate(CardType.LAND) + )); + } + + public OnceUponATime(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.INSTANT}, "{1}{G}"); + + // If this spell is the first spell you've cast this game, you may cast it without paying its mana cost. + this.addAbility(new AlternativeCostSourceAbility( + null, OnceUponATimeCondition.instance, "If this spell is the first spell " + + "you've cast this game, you may cast it without paying its mana cost." + ), new OnceUponATimeWatcher()); + + // Look at the top five cards of your library. You may reveal a creature or land card from among them and put it into your hand. Put the rest on the bottom of your library in a random order. + this.getSpellAbility().addEffect(new LookLibraryAndPickControllerEffect( + new StaticValue(5), false, new StaticValue(1), filter, + Zone.LIBRARY, false, true, false, Zone.HAND, + true, false, false + ).setBackInRandomOrder(true).setText("Look at the top five cards of your library. " + + "You may reveal a creature or land card from among them and put it into your hand. " + + "Put the rest on the bottom of your library in a random order." + )); + } + + private OnceUponATime(final OnceUponATime card) { + super(card); + } + + @Override + public OnceUponATime copy() { + return new OnceUponATime(this); + } +} + +enum OnceUponATimeCondition implements Condition { + instance; + + @Override + public boolean apply(Game game, Ability source) { + OnceUponATimeWatcher watcher = game.getState().getWatcher(OnceUponATimeWatcher.class); + return watcher != null && watcher.getSpellsCastThisTurn(source.getControllerId()); + } +} + +class OnceUponATimeWatcher extends Watcher { + + private final Set castSpells = new HashSet(); + + OnceUponATimeWatcher() { + super(WatcherScope.GAME); + } + + private OnceUponATimeWatcher(final OnceUponATimeWatcher watcher) { + super(watcher); + this.castSpells.addAll(watcher.castSpells); + } + + @Override + public OnceUponATimeWatcher copy() { + return new OnceUponATimeWatcher(this); + } + + @Override + public void watch(GameEvent event, Game game) { + if (GameEvent.EventType.SPELL_CAST == event.getType()) { + castSpells.add(event.getPlayerId()); + } + } + + public boolean getSpellsCastThisTurn(UUID playerId) { + return !castSpells.contains(playerId); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 3b472e8c2e..02c84a95a8 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -71,6 +71,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Mystical Dispute", 58, Rarity.UNCOMMON, mage.cards.m.MysticalDispute.class)); cards.add(new SetCardInfo("Oko's Accomplices", 310, Rarity.COMMON, mage.cards.o.OkosAccomplices.class)); cards.add(new SetCardInfo("Oko, Thief of Crowns", 197, Rarity.MYTHIC, mage.cards.o.OkoThiefOfCrowns.class)); + cards.add(new SetCardInfo("Once Upon a Time", 169, Rarity.RARE, mage.cards.o.OnceUponATime.class)); cards.add(new SetCardInfo("Order of Midnight", 99, Rarity.UNCOMMON, mage.cards.o.OrderOfMidnight.class)); cards.add(new SetCardInfo("Piper of the Swarm", 100, Rarity.RARE, mage.cards.p.PiperOfTheSwarm.class)); cards.add(new SetCardInfo("Rankle, Master of Pranks", 101, Rarity.MYTHIC, mage.cards.r.RankleMasterOfPranks.class)); From 6ad29ab2d656a821807f408d50100efabd5e4f24 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 9 Sep 2019 16:33:45 -0400 Subject: [PATCH 014/373] Implemented Turn into a Pumpkin --- .../src/mage/cards/t/TurnIntoAPumpkin.java | 47 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 48 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/t/TurnIntoAPumpkin.java diff --git a/Mage.Sets/src/mage/cards/t/TurnIntoAPumpkin.java b/Mage.Sets/src/mage/cards/t/TurnIntoAPumpkin.java new file mode 100644 index 0000000000..9324626581 --- /dev/null +++ b/Mage.Sets/src/mage/cards/t/TurnIntoAPumpkin.java @@ -0,0 +1,47 @@ +package mage.cards.t; + +import mage.abilities.condition.common.AdamantCondition; +import mage.abilities.decorator.ConditionalOneShotEffect; +import mage.abilities.effects.common.CreateTokenEffect; +import mage.abilities.effects.common.DrawCardSourceControllerEffect; +import mage.abilities.effects.common.ReturnToHandTargetEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.game.permanent.token.FoodToken; +import mage.target.common.TargetNonlandPermanent; +import mage.watchers.common.ManaSpentToCastWatcher; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class TurnIntoAPumpkin extends CardImpl { + + public TurnIntoAPumpkin(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.INSTANT}, "{3}{U}"); + + // Return target nonland permanent to its owner's hand. Draw a card. + this.getSpellAbility().addEffect(new ReturnToHandTargetEffect()); + this.getSpellAbility().addEffect(new DrawCardSourceControllerEffect(1).setText("Draw a card.")); + this.getSpellAbility().addTarget(new TargetNonlandPermanent()); + + // Adamant — If at least three blue mana was spent to cast this spell, create a Food token. + this.getSpellAbility().addEffect(new ConditionalOneShotEffect( + new CreateTokenEffect(new FoodToken()), AdamantCondition.BLUE, + "
Adamant — If at least three blue mana " + + "was spent to cast this spell, create a Food token." + )); + this.getSpellAbility().addWatcher(new ManaSpentToCastWatcher()); + } + + private TurnIntoAPumpkin(final TurnIntoAPumpkin card) { + super(card); + } + + @Override + public TurnIntoAPumpkin copy() { + return new TurnIntoAPumpkin(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 02c84a95a8..3551493e21 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -97,6 +97,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Tome Raider", 68, Rarity.COMMON, mage.cards.t.TomeRaider.class)); cards.add(new SetCardInfo("Tome of Legends", 332, Rarity.RARE, mage.cards.t.TomeOfLegends.class)); cards.add(new SetCardInfo("Tournament Grounds", 248, Rarity.UNCOMMON, mage.cards.t.TournamentGrounds.class)); + cards.add(new SetCardInfo("Turn into a Pumpkin", 69, Rarity.UNCOMMON, mage.cards.t.TurnIntoAPumpkin.class)); cards.add(new SetCardInfo("Wind-Scarred Crag", 308, Rarity.COMMON, mage.cards.w.WindScarredCrag.class)); cards.add(new SetCardInfo("Wintermoor Commander", 205, Rarity.UNCOMMON, mage.cards.w.WintermoorCommander.class)); cards.add(new SetCardInfo("Wishful Merfolk", 73, Rarity.COMMON, mage.cards.w.WishfulMerfolk.class)); From b6fe81206139e3578fbe7e8fe15e79cdd0310691 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 9 Sep 2019 16:57:28 -0400 Subject: [PATCH 015/373] Implemented Blow Your House Down --- .../src/mage/cards/b/BlowYourHouseDown.java | 70 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 71 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/b/BlowYourHouseDown.java diff --git a/Mage.Sets/src/mage/cards/b/BlowYourHouseDown.java b/Mage.Sets/src/mage/cards/b/BlowYourHouseDown.java new file mode 100644 index 0000000000..4c8bc31c28 --- /dev/null +++ b/Mage.Sets/src/mage/cards/b/BlowYourHouseDown.java @@ -0,0 +1,70 @@ +package mage.cards.b; + +import mage.abilities.Ability; +import mage.abilities.effects.OneShotEffect; +import mage.abilities.effects.common.combat.CantBlockTargetEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.Outcome; +import mage.constants.SubType; +import mage.game.Game; +import mage.target.Target; +import mage.target.common.TargetCreaturePermanent; + +import java.util.Collection; +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class BlowYourHouseDown extends CardImpl { + + public BlowYourHouseDown(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.SORCERY}, "{2}{R}"); + + // Up to three target creatures can't block this turn. Destroy any of them that are Walls. + this.getSpellAbility().addEffect(new CantBlockTargetEffect(Duration.EndOfTurn)); + this.getSpellAbility().addEffect(new BlowYourHouseDownEffect()); + this.getSpellAbility().addTarget(new TargetCreaturePermanent(0, 3)); + } + + private BlowYourHouseDown(final BlowYourHouseDown card) { + super(card); + } + + @Override + public BlowYourHouseDown copy() { + return new BlowYourHouseDown(this); + } +} + +class BlowYourHouseDownEffect extends OneShotEffect { + + BlowYourHouseDownEffect() { + super(Outcome.Benefit); + staticText = "Destroy any of them that are Walls"; + } + + private BlowYourHouseDownEffect(final BlowYourHouseDownEffect effect) { + super(effect); + } + + @Override + public BlowYourHouseDownEffect copy() { + return new BlowYourHouseDownEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + source.getTargets() + .stream() + .map(Target::getTargets) + .flatMap(Collection::stream) + .map(game::getPermanent) + .filter(permanent -> permanent != null && permanent.hasSubtype(SubType.WALL, game)) + .forEach(permanent -> permanent.destroy(source.getSourceId(), game, false)); + return true; + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 3551493e21..f7d7dcb09b 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -37,6 +37,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Banish into Fable", 325, Rarity.RARE, mage.cards.b.BanishIntoFable.class)); cards.add(new SetCardInfo("Beanstalk Giant", 149, Rarity.UNCOMMON, mage.cards.b.BeanstalkGiant.class)); cards.add(new SetCardInfo("Belle of the Brawl", 78, Rarity.UNCOMMON, mage.cards.b.BelleOfTheBrawl.class)); + cards.add(new SetCardInfo("Blow Your House Down", 114, Rarity.COMMON, mage.cards.b.BlowYourHouseDown.class)); cards.add(new SetCardInfo("Chittering Witch", 319, Rarity.RARE, mage.cards.c.ChitteringWitch.class)); cards.add(new SetCardInfo("Chulane, Teller of Tales", 326, Rarity.MYTHIC, mage.cards.c.ChulaneTellerOfTales.class)); cards.add(new SetCardInfo("Command Tower", 333, Rarity.COMMON, mage.cards.c.CommandTower.class)); From e29dd87824f09e36d3872627972801d365fd47b6 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 9 Sep 2019 17:57:11 -0400 Subject: [PATCH 016/373] Implemented Brimstone Trebuchet --- .../src/mage/cards/b/BrimstoneTrebuchet.java | 57 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 58 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/b/BrimstoneTrebuchet.java diff --git a/Mage.Sets/src/mage/cards/b/BrimstoneTrebuchet.java b/Mage.Sets/src/mage/cards/b/BrimstoneTrebuchet.java new file mode 100644 index 0000000000..e36f61c957 --- /dev/null +++ b/Mage.Sets/src/mage/cards/b/BrimstoneTrebuchet.java @@ -0,0 +1,57 @@ +package mage.cards.b; + +import mage.MageInt; +import mage.abilities.common.EntersBattlefieldControlledTriggeredAbility; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.costs.common.TapSourceCost; +import mage.abilities.effects.common.DamagePlayersEffect; +import mage.abilities.effects.common.UntapSourceEffect; +import mage.abilities.keyword.DefenderAbility; +import mage.abilities.keyword.ReachAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.constants.TargetController; +import mage.filter.FilterPermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class BrimstoneTrebuchet extends CardImpl { + + private static final FilterPermanent filter = new FilterPermanent(SubType.KNIGHT, "a Knight"); + + public BrimstoneTrebuchet(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT, CardType.CREATURE}, "{2}{R}"); + + this.subtype.add(SubType.WALL); + this.power = new MageInt(1); + this.toughness = new MageInt(3); + + // Defender + this.addAbility(DefenderAbility.getInstance()); + + // Reach + this.addAbility(ReachAbility.getInstance()); + + // {T}: Brimstone Trebuchet deals 1 damage to each opponent. + this.addAbility(new SimpleActivatedAbility( + new DamagePlayersEffect(1, TargetController.OPPONENT), new TapSourceCost() + )); + + // Whenever a Knight enters the battlefield under your control, untap Brimstone Trebuchet. + this.addAbility(new EntersBattlefieldControlledTriggeredAbility(new UntapSourceEffect(), filter)); + } + + private BrimstoneTrebuchet(final BrimstoneTrebuchet card) { + super(card); + } + + @Override + public BrimstoneTrebuchet copy() { + return new BrimstoneTrebuchet(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index f7d7dcb09b..fdebe86bf5 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -38,6 +38,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Beanstalk Giant", 149, Rarity.UNCOMMON, mage.cards.b.BeanstalkGiant.class)); cards.add(new SetCardInfo("Belle of the Brawl", 78, Rarity.UNCOMMON, mage.cards.b.BelleOfTheBrawl.class)); cards.add(new SetCardInfo("Blow Your House Down", 114, Rarity.COMMON, mage.cards.b.BlowYourHouseDown.class)); + cards.add(new SetCardInfo("Brimstone Trebuchet", 116, Rarity.COMMON, mage.cards.b.BrimstoneTrebuchet.class)); cards.add(new SetCardInfo("Chittering Witch", 319, Rarity.RARE, mage.cards.c.ChitteringWitch.class)); cards.add(new SetCardInfo("Chulane, Teller of Tales", 326, Rarity.MYTHIC, mage.cards.c.ChulaneTellerOfTales.class)); cards.add(new SetCardInfo("Command Tower", 333, Rarity.COMMON, mage.cards.c.CommandTower.class)); From abeb6ec9d02c0e26a521447d944f2775ca638922 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 9 Sep 2019 18:04:42 -0400 Subject: [PATCH 017/373] Implemented Bramblefort Fink --- .../src/mage/cards/b/BramblefortFink.java | 47 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 48 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/b/BramblefortFink.java diff --git a/Mage.Sets/src/mage/cards/b/BramblefortFink.java b/Mage.Sets/src/mage/cards/b/BramblefortFink.java new file mode 100644 index 0000000000..8356669ee0 --- /dev/null +++ b/Mage.Sets/src/mage/cards/b/BramblefortFink.java @@ -0,0 +1,47 @@ +package mage.cards.b; + +import mage.MageInt; +import mage.abilities.common.ActivateIfConditionActivatedAbility; +import mage.abilities.condition.Condition; +import mage.abilities.condition.common.PermanentsOnTheBattlefieldCondition; +import mage.abilities.costs.mana.GenericManaCost; +import mage.abilities.effects.common.continuous.SetPowerToughnessSourceEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.*; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterControlledPlaneswalkerPermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class BramblefortFink extends CardImpl { + + private static final FilterPermanent filter + = new FilterControlledPlaneswalkerPermanent(SubType.OKO, "you control an Oko planeswalker"); + private static final Condition condition = new PermanentsOnTheBattlefieldCondition(filter); + + public BramblefortFink(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{1}{G}"); + + this.subtype.add(SubType.OUPHE); + this.power = new MageInt(2); + this.toughness = new MageInt(2); + + // {8}: Bramblefort Fink has base power and toughness 10/10 until end of turn. Activate this ability only if you control an Oko planeswalker. + this.addAbility(new ActivateIfConditionActivatedAbility(Zone.BATTLEFIELD, new SetPowerToughnessSourceEffect( + 10, 10, Duration.EndOfTurn, SubLayer.SetPT_7b + ).setText("{this} has base power and toughness 10/10 until end of turn"), new GenericManaCost(8), condition)); + } + + private BramblefortFink(final BramblefortFink card) { + super(card); + } + + @Override + public BramblefortFink copy() { + return new BramblefortFink(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index fdebe86bf5..68150be72b 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -38,6 +38,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Beanstalk Giant", 149, Rarity.UNCOMMON, mage.cards.b.BeanstalkGiant.class)); cards.add(new SetCardInfo("Belle of the Brawl", 78, Rarity.UNCOMMON, mage.cards.b.BelleOfTheBrawl.class)); cards.add(new SetCardInfo("Blow Your House Down", 114, Rarity.COMMON, mage.cards.b.BlowYourHouseDown.class)); + cards.add(new SetCardInfo("Bramblefort Fink", 311, Rarity.UNCOMMON, mage.cards.b.BramblefortFink.class)); cards.add(new SetCardInfo("Brimstone Trebuchet", 116, Rarity.COMMON, mage.cards.b.BrimstoneTrebuchet.class)); cards.add(new SetCardInfo("Chittering Witch", 319, Rarity.RARE, mage.cards.c.ChitteringWitch.class)); cards.add(new SetCardInfo("Chulane, Teller of Tales", 326, Rarity.MYTHIC, mage.cards.c.ChulaneTellerOfTales.class)); From c60b56b2a1c25d1e4dbeb2baa16a7df2e910535a Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 9 Sep 2019 18:12:52 -0400 Subject: [PATCH 018/373] Implemented Burning-Yard Trainer --- .../src/mage/cards/b/BurningYardTrainer.java | 70 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 71 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/b/BurningYardTrainer.java diff --git a/Mage.Sets/src/mage/cards/b/BurningYardTrainer.java b/Mage.Sets/src/mage/cards/b/BurningYardTrainer.java new file mode 100644 index 0000000000..3d37d2b461 --- /dev/null +++ b/Mage.Sets/src/mage/cards/b/BurningYardTrainer.java @@ -0,0 +1,70 @@ +package mage.cards.b; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.effects.common.continuous.BoostTargetEffect; +import mage.abilities.effects.common.continuous.GainAbilityTargetEffect; +import mage.abilities.keyword.HasteAbility; +import mage.abilities.keyword.TrampleAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterControlledPermanent; +import mage.filter.predicate.permanent.AnotherPredicate; +import mage.target.TargetPermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class BurningYardTrainer extends CardImpl { + + private static final FilterPermanent filter = new FilterControlledPermanent(SubType.KNIGHT); + + static { + filter.add(AnotherPredicate.instance); + } + + public BurningYardTrainer(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{4}{R}"); + + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.KNIGHT); + this.power = new MageInt(3); + this.toughness = new MageInt(3); + + // Trample + this.addAbility(TrampleAbility.getInstance()); + + // Haste + this.addAbility(HasteAbility.getInstance()); + + // When Burning-Yard Trainer enters the battlefield, another target Knight you control gets +2/+2 and gains trample and haste until end of turn. + Ability ability = new EntersBattlefieldTriggeredAbility( + new BoostTargetEffect(2, 2, Duration.EndOfTurn) + .setText("another target Knight you control gets +2/+2") + ); + ability.addEffect(new GainAbilityTargetEffect( + TrampleAbility.getInstance(), Duration.EndOfTurn + ).setText("and gains trample")); + ability.addEffect(new GainAbilityTargetEffect( + HasteAbility.getInstance(), Duration.EndOfTurn + ).setText("and haste until end of turn")); + ability.addTarget(new TargetPermanent(filter)); + this.addAbility(ability); + } + + private BurningYardTrainer(final BurningYardTrainer card) { + super(card); + } + + @Override + public BurningYardTrainer copy() { + return new BurningYardTrainer(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 68150be72b..d7fe3fafdf 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -40,6 +40,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Blow Your House Down", 114, Rarity.COMMON, mage.cards.b.BlowYourHouseDown.class)); cards.add(new SetCardInfo("Bramblefort Fink", 311, Rarity.UNCOMMON, mage.cards.b.BramblefortFink.class)); cards.add(new SetCardInfo("Brimstone Trebuchet", 116, Rarity.COMMON, mage.cards.b.BrimstoneTrebuchet.class)); + cards.add(new SetCardInfo("Burning-Yard Trainer", 117, Rarity.UNCOMMON, mage.cards.b.BurningYardTrainer.class)); cards.add(new SetCardInfo("Chittering Witch", 319, Rarity.RARE, mage.cards.c.ChitteringWitch.class)); cards.add(new SetCardInfo("Chulane, Teller of Tales", 326, Rarity.MYTHIC, mage.cards.c.ChulaneTellerOfTales.class)); cards.add(new SetCardInfo("Command Tower", 333, Rarity.COMMON, mage.cards.c.CommandTower.class)); From c870f32b3118c92b4cf407026ba5a67333e88fa8 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 9 Sep 2019 18:17:52 -0400 Subject: [PATCH 019/373] Implemented Faerie Guidemother --- .../src/mage/cards/f/FaerieGuidemother.java | 50 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 51 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/f/FaerieGuidemother.java diff --git a/Mage.Sets/src/mage/cards/f/FaerieGuidemother.java b/Mage.Sets/src/mage/cards/f/FaerieGuidemother.java new file mode 100644 index 0000000000..03d51364ce --- /dev/null +++ b/Mage.Sets/src/mage/cards/f/FaerieGuidemother.java @@ -0,0 +1,50 @@ +package mage.cards.f; + +import mage.MageInt; +import mage.abilities.effects.common.continuous.BoostTargetEffect; +import mage.abilities.effects.common.continuous.GainAbilityTargetEffect; +import mage.abilities.keyword.FlyingAbility; +import mage.cards.AdventureCard; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; +import mage.target.common.TargetCreaturePermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class FaerieGuidemother extends AdventureCard { + + public FaerieGuidemother(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, new CardType[]{CardType.SORCERY}, "{W}", "Gift of the Fae", "{1}{W}"); + + this.subtype.add(SubType.FAERIE); + this.power = new MageInt(1); + this.toughness = new MageInt(1); + + // Flying + this.addAbility(FlyingAbility.getInstance()); + + // Gift of the Fae + // Target creature gets +2/+1 and gains flying until end of turn. + this.getAdventureSpellAbility().addEffect(new BoostTargetEffect( + 2, 1, Duration.EndOfTurn + ).setText("Target creature gets +2/+1")); + this.getAdventureSpellAbility().addEffect(new GainAbilityTargetEffect( + FlyingAbility.getInstance(), Duration.EndOfTurn + ).setText("and gains flying until end of turn")); + this.getAdventureSpellAbility().addTarget(new TargetCreaturePermanent()); + } + + private FaerieGuidemother(final FaerieGuidemother card) { + super(card); + } + + @Override + public FaerieGuidemother copy() { + return new FaerieGuidemother(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index d7fe3fafdf..be7aac6be7 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -52,6 +52,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Enchanted Carriage", 218, Rarity.UNCOMMON, mage.cards.e.EnchantedCarriage.class)); cards.add(new SetCardInfo("Eye Collector", 86, Rarity.COMMON, mage.cards.e.EyeCollector.class)); cards.add(new SetCardInfo("Faerie Formation", 316, Rarity.RARE, mage.cards.f.FaerieFormation.class)); + cards.add(new SetCardInfo("Faerie Guidemother", 11, Rarity.COMMON, mage.cards.f.FaerieGuidemother.class)); cards.add(new SetCardInfo("Faerie Vandal", 45, Rarity.UNCOMMON, mage.cards.f.FaerieVandal.class)); cards.add(new SetCardInfo("Fireborn Knight", 210, Rarity.UNCOMMON, mage.cards.f.FirebornKnight.class)); cards.add(new SetCardInfo("Flaxen Intruder", 155, Rarity.UNCOMMON, mage.cards.f.FlaxenIntruder.class)); From f7ebf806278b8d4bf16367ff39272df9509c7835 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 9 Sep 2019 18:23:35 -0400 Subject: [PATCH 020/373] Implemented Giant Killer --- Mage.Sets/src/mage/cards/g/GiantKiller.java | 62 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + .../src/main/java/mage/constants/SubType.java | 1 + 3 files changed, 64 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/g/GiantKiller.java diff --git a/Mage.Sets/src/mage/cards/g/GiantKiller.java b/Mage.Sets/src/mage/cards/g/GiantKiller.java new file mode 100644 index 0000000000..27ea004156 --- /dev/null +++ b/Mage.Sets/src/mage/cards/g/GiantKiller.java @@ -0,0 +1,62 @@ +package mage.cards.g; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.costs.common.TapSourceCost; +import mage.abilities.costs.mana.ManaCostsImpl; +import mage.abilities.effects.common.DestroyTargetEffect; +import mage.abilities.effects.common.TapTargetEffect; +import mage.cards.AdventureCard; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.ComparisonType; +import mage.constants.SubType; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterCreaturePermanent; +import mage.filter.predicate.mageobject.PowerPredicate; +import mage.target.TargetPermanent; +import mage.target.common.TargetCreaturePermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class GiantKiller extends AdventureCard { + + private static final FilterPermanent filter = new FilterCreaturePermanent("creature with power 4 or greater"); + + static { + filter.add(new PowerPredicate(ComparisonType.MORE_THAN, 3)); + } + + public GiantKiller(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, new CardType[]{CardType.INSTANT}, "{W}", "Chop Down", "{2}{W}"); + + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.PEASANT); + this.power = new MageInt(1); + this.toughness = new MageInt(2); + + // {1}{W}, {T}: Tap target creature. + Ability ability = new SimpleActivatedAbility(new TapTargetEffect(), new ManaCostsImpl("{1}{W}")); + ability.addCost(new TapSourceCost()); + ability.addTarget(new TargetCreaturePermanent()); + this.addAbility(ability); + + // Chop Down + // Destroy target creature with power 4 or greater. + this.getAdventureSpellAbility().addEffect(new DestroyTargetEffect()); + this.getAdventureSpellAbility().addTarget(new TargetPermanent(filter)); + } + + private GiantKiller(final GiantKiller card) { + super(card); + } + + @Override + public GiantKiller copy() { + return new GiantKiller(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index be7aac6be7..2661cfe45f 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -60,6 +60,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Frogify", 47, Rarity.UNCOMMON, mage.cards.f.Frogify.class)); cards.add(new SetCardInfo("Garrison Griffin", 305, Rarity.COMMON, mage.cards.g.GarrisonGriffin.class)); cards.add(new SetCardInfo("Garruk, Cursed Huntsman", 191, Rarity.MYTHIC, mage.cards.g.GarrukCursedHuntsman.class)); + cards.add(new SetCardInfo("Giant Killer", 14, Rarity.RARE, mage.cards.g.GiantKiller.class)); cards.add(new SetCardInfo("Gilded Goose", 160, Rarity.RARE, mage.cards.g.GildedGoose.class)); cards.add(new SetCardInfo("Gluttonous Troll", 327, Rarity.RARE, mage.cards.g.GluttonousTroll.class)); cards.add(new SetCardInfo("Golden Egg", 220, Rarity.COMMON, mage.cards.g.GoldenEgg.class)); diff --git a/Mage/src/main/java/mage/constants/SubType.java b/Mage/src/main/java/mage/constants/SubType.java index 6b6e1660be..da6b5bc629 100644 --- a/Mage/src/main/java/mage/constants/SubType.java +++ b/Mage/src/main/java/mage/constants/SubType.java @@ -258,6 +258,7 @@ public enum SubType { OYSTER("Oyster", SubTypeSet.CreatureType), // P PANGOLIN("Pangolin", SubTypeSet.CreatureType), + PEASANT("Peasant", SubTypeSet.CreatureType), PEGASUS("Pegasus", SubTypeSet.CreatureType), PENTAVITE("Pentavite", SubTypeSet.CreatureType), PEST("Pest", SubTypeSet.CreatureType), From fbafdb099844c9ece550df887619b8919ee2bbb4 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 9 Sep 2019 18:33:51 -0400 Subject: [PATCH 021/373] Implemented Rowan's Stalwarts --- .../src/mage/cards/r/RowansStalwarts.java | 48 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 49 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/r/RowansStalwarts.java diff --git a/Mage.Sets/src/mage/cards/r/RowansStalwarts.java b/Mage.Sets/src/mage/cards/r/RowansStalwarts.java new file mode 100644 index 0000000000..1dbb4762f2 --- /dev/null +++ b/Mage.Sets/src/mage/cards/r/RowansStalwarts.java @@ -0,0 +1,48 @@ +package mage.cards.r; + +import mage.MageInt; +import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.effects.common.search.SearchLibraryGraveyardPutInHandEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.filter.FilterCard; +import mage.filter.predicate.mageobject.NamePredicate; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class RowansStalwarts extends CardImpl { + + private static final FilterCard filter = new FilterCard("Rowan, Fearless Sparkmage"); + + static { + filter.add(new NamePredicate("Rowan, Fearless Sparkmage")); + } + + public RowansStalwarts(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{4}{R}"); + + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.KNIGHT); + this.power = new MageInt(5); + this.toughness = new MageInt(2); + + // When Rowan's Stalwarts enters the battlefield, you may search your library and/or graveyard for a card named Rowan, Fearless Sparkmage, reveal it, and put it into your hand. If you search your library this way, shuffle it. + this.addAbility(new EntersBattlefieldTriggeredAbility( + new SearchLibraryGraveyardPutInHandEffect(filter, false, true) + )); + } + + private RowansStalwarts(final RowansStalwarts card) { + super(card); + } + + @Override + public RowansStalwarts copy() { + return new RowansStalwarts(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 2661cfe45f..2d2d131a7b 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -83,6 +83,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Rankle, Master of Pranks", 101, Rarity.MYTHIC, mage.cards.r.RankleMasterOfPranks.class)); cards.add(new SetCardInfo("Return to Nature", 173, Rarity.COMMON, mage.cards.r.ReturnToNature.class)); cards.add(new SetCardInfo("Rosethorn Acolyte", 174, Rarity.COMMON, mage.cards.r.RosethornAcolyte.class)); + cards.add(new SetCardInfo("Rowan's Stalwarts", 307, Rarity.RARE, mage.cards.r.RowansStalwarts.class)); cards.add(new SetCardInfo("Run Away Together", 62, Rarity.COMMON, mage.cards.r.RunAwayTogether.class)); cards.add(new SetCardInfo("Savvy Hunter", 200, Rarity.UNCOMMON, mage.cards.s.SavvyHunter.class)); cards.add(new SetCardInfo("Shimmer Dragon", 317, Rarity.RARE, mage.cards.s.ShimmerDragon.class)); From 7b692b1f23fa9acf4f9bb1e431e00b274778a3ee Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 9 Sep 2019 18:38:15 -0400 Subject: [PATCH 022/373] Implemented Rowan's Battleguard --- .../src/mage/cards/r/RowansBattleguard.java | 56 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 57 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/r/RowansBattleguard.java diff --git a/Mage.Sets/src/mage/cards/r/RowansBattleguard.java b/Mage.Sets/src/mage/cards/r/RowansBattleguard.java new file mode 100644 index 0000000000..5b2c730cf8 --- /dev/null +++ b/Mage.Sets/src/mage/cards/r/RowansBattleguard.java @@ -0,0 +1,56 @@ +package mage.cards.r; + +import mage.MageInt; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.condition.Condition; +import mage.abilities.condition.common.PermanentsOnTheBattlefieldCondition; +import mage.abilities.decorator.ConditionalContinuousEffect; +import mage.abilities.effects.common.continuous.BoostSourceEffect; +import mage.abilities.keyword.FirstStrikeAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterControlledPlaneswalkerPermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class RowansBattleguard extends CardImpl { + + private static final FilterPermanent filter + = new FilterControlledPlaneswalkerPermanent(SubType.ROWAN); + private static final Condition condition + = new PermanentsOnTheBattlefieldCondition(filter); + + public RowansBattleguard(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{3}{R}"); + + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.KNIGHT); + this.power = new MageInt(3); + this.toughness = new MageInt(3); + + // First strike + this.addAbility(FirstStrikeAbility.getInstance()); + + // As long as you control a Rowan planeswalker, Rowan's Battleguard gets +3/+0. + this.addAbility(new SimpleStaticAbility(new ConditionalContinuousEffect( + new BoostSourceEffect(3, 0, Duration.WhileOnBattlefield), condition, + "As long as you control a Rowan planeswalker, {this} gets +3/+0" + ))); + } + + private RowansBattleguard(final RowansBattleguard card) { + super(card); + } + + @Override + public RowansBattleguard copy() { + return new RowansBattleguard(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 2d2d131a7b..74a22d4f49 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -83,6 +83,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Rankle, Master of Pranks", 101, Rarity.MYTHIC, mage.cards.r.RankleMasterOfPranks.class)); cards.add(new SetCardInfo("Return to Nature", 173, Rarity.COMMON, mage.cards.r.ReturnToNature.class)); cards.add(new SetCardInfo("Rosethorn Acolyte", 174, Rarity.COMMON, mage.cards.r.RosethornAcolyte.class)); + cards.add(new SetCardInfo("Rowan's Battleguard", 306, Rarity.UNCOMMON, mage.cards.r.RowansBattleguard.class)); cards.add(new SetCardInfo("Rowan's Stalwarts", 307, Rarity.RARE, mage.cards.r.RowansStalwarts.class)); cards.add(new SetCardInfo("Run Away Together", 62, Rarity.COMMON, mage.cards.r.RunAwayTogether.class)); cards.add(new SetCardInfo("Savvy Hunter", 200, Rarity.UNCOMMON, mage.cards.s.SavvyHunter.class)); From 3f804a4121301dd61d129a376af4683d492318f1 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 9 Sep 2019 18:45:45 -0400 Subject: [PATCH 023/373] Implemented Wicked Wolf --- Mage.Sets/src/mage/cards/w/WickedWolf.java | 77 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 78 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/w/WickedWolf.java diff --git a/Mage.Sets/src/mage/cards/w/WickedWolf.java b/Mage.Sets/src/mage/cards/w/WickedWolf.java new file mode 100644 index 0000000000..3888da8973 --- /dev/null +++ b/Mage.Sets/src/mage/cards/w/WickedWolf.java @@ -0,0 +1,77 @@ +package mage.cards.w; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.costs.common.SacrificeTargetCost; +import mage.abilities.effects.common.FightTargetSourceEffect; +import mage.abilities.effects.common.TapSourceEffect; +import mage.abilities.effects.common.continuous.GainAbilitySourceEffect; +import mage.abilities.effects.common.counter.AddCountersSourceEffect; +import mage.abilities.keyword.IndestructibleAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; +import mage.constants.TargetController; +import mage.counters.CounterType; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterControlledPermanent; +import mage.filter.common.FilterCreaturePermanent; +import mage.filter.predicate.permanent.ControllerPredicate; +import mage.target.TargetPermanent; +import mage.target.common.TargetControlledPermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class WickedWolf extends CardImpl { + + private static final FilterPermanent filter + = new FilterCreaturePermanent("creature you don't control"); + private static final FilterControlledPermanent filter2 + = new FilterControlledPermanent(SubType.FOOD, "a Food"); + + static { + filter.add(new ControllerPredicate(TargetController.NOT_YOU)); + } + + public WickedWolf(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{2}{G}{G}"); + + this.subtype.add(SubType.WOLF); + this.power = new MageInt(3); + this.toughness = new MageInt(3); + + // When Wicked Wolf enters the battlefield, it fights up to one target creature you don't control. + Ability ability = new EntersBattlefieldTriggeredAbility( + new FightTargetSourceEffect().setText("it fights up to one target creature you don't control") + ); + ability.addTarget(new TargetPermanent(0, 1, filter, false)); + this.addAbility(ability); + + // Sacrifice a Food: Put a +1/+1 counter on Wicked Wolf. It gains indestructible until end of turn. Tap it. + ability = new SimpleActivatedAbility( + new AddCountersSourceEffect(CounterType.P1P1.createInstance()), + new SacrificeTargetCost(new TargetControlledPermanent(filter2)) + ); + ability.addEffect(new GainAbilitySourceEffect( + IndestructibleAbility.getInstance(), Duration.EndOfTurn + ).setText("it gains indestructible until end of turn.")); + ability.addEffect(new TapSourceEffect().setText("Tap it")); + this.addAbility(ability); + } + + private WickedWolf(final WickedWolf card) { + super(card); + } + + @Override + public WickedWolf copy() { + return new WickedWolf(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 74a22d4f49..c19e20e027 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -106,6 +106,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Tome of Legends", 332, Rarity.RARE, mage.cards.t.TomeOfLegends.class)); cards.add(new SetCardInfo("Tournament Grounds", 248, Rarity.UNCOMMON, mage.cards.t.TournamentGrounds.class)); cards.add(new SetCardInfo("Turn into a Pumpkin", 69, Rarity.UNCOMMON, mage.cards.t.TurnIntoAPumpkin.class)); + cards.add(new SetCardInfo("Wicked Wolf", 181, Rarity.RARE, mage.cards.w.WickedWolf.class)); cards.add(new SetCardInfo("Wind-Scarred Crag", 308, Rarity.COMMON, mage.cards.w.WindScarredCrag.class)); cards.add(new SetCardInfo("Wintermoor Commander", 205, Rarity.UNCOMMON, mage.cards.w.WintermoorCommander.class)); cards.add(new SetCardInfo("Wishful Merfolk", 73, Rarity.COMMON, mage.cards.w.WishfulMerfolk.class)); From 07516081c3b3cb724a78b63ddbb51de2dc52f65a Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 9 Sep 2019 18:57:13 -0400 Subject: [PATCH 024/373] Implemented Witch's Vengeance --- .../src/mage/cards/w/WitchsVengeance.java | 75 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 76 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/w/WitchsVengeance.java diff --git a/Mage.Sets/src/mage/cards/w/WitchsVengeance.java b/Mage.Sets/src/mage/cards/w/WitchsVengeance.java new file mode 100644 index 0000000000..c75558b519 --- /dev/null +++ b/Mage.Sets/src/mage/cards/w/WitchsVengeance.java @@ -0,0 +1,75 @@ +package mage.cards.w; + +import mage.abilities.Ability; +import mage.abilities.effects.OneShotEffect; +import mage.abilities.effects.common.continuous.BoostAllEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.choices.ChoiceCreatureType; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.Outcome; +import mage.constants.SubType; +import mage.filter.common.FilterCreaturePermanent; +import mage.filter.predicate.mageobject.SubtypePredicate; +import mage.game.Game; +import mage.players.Player; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class WitchsVengeance extends CardImpl { + + public WitchsVengeance(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.SORCERY}, "{1}{B}{B}"); + + // Creatures of the creature type of your choice get -3/-3 until end of turn. + this.getSpellAbility().addEffect(new WitchsVengeanceEffect()); + } + + private WitchsVengeance(final WitchsVengeance card) { + super(card); + } + + @Override + public WitchsVengeance copy() { + return new WitchsVengeance(this); + } +} + +class WitchsVengeanceEffect extends OneShotEffect { + + WitchsVengeanceEffect() { + super(Outcome.Benefit); + staticText = "Creatures of the creature type of your choice get -3/-3 until end of turn."; + } + + private WitchsVengeanceEffect(final WitchsVengeanceEffect effect) { + super(effect); + } + + @Override + public WitchsVengeanceEffect copy() { + return new WitchsVengeanceEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + Player player = game.getPlayer(source.getControllerId()); + if (player == null) { + return false; + } + ChoiceCreatureType choice = new ChoiceCreatureType(); + if (!player.choose(outcome, choice, game)) { + return false; + } + FilterCreaturePermanent filter = new FilterCreaturePermanent(); + filter.add(new SubtypePredicate(SubType.byDescription(choice.getChoice()))); + game.addEffect(new BoostAllEffect( + -3, -3, Duration.EndOfTurn, filter, false + ), source); + return true; + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index c19e20e027..39ada437ef 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -111,6 +111,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Wintermoor Commander", 205, Rarity.UNCOMMON, mage.cards.w.WintermoorCommander.class)); cards.add(new SetCardInfo("Wishful Merfolk", 73, Rarity.COMMON, mage.cards.w.WishfulMerfolk.class)); cards.add(new SetCardInfo("Witch's Cottage", 249, Rarity.COMMON, mage.cards.w.WitchsCottage.class)); + cards.add(new SetCardInfo("Witch's Vengeance", 111, Rarity.RARE, mage.cards.w.WitchsVengeance.class)); cards.add(new SetCardInfo("Witching Well", 74, Rarity.COMMON, mage.cards.w.WitchingWell.class)); cards.add(new SetCardInfo("Workshop Elders", 318, Rarity.RARE, mage.cards.w.WorkshopElders.class)); From 6d2aa423ac97cf4ef483c0efcacfe1d0a347b390 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 9 Sep 2019 19:30:41 -0400 Subject: [PATCH 025/373] Implemented Joust --- Mage.Sets/src/mage/cards/j/Joust.java | 88 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 89 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/j/Joust.java diff --git a/Mage.Sets/src/mage/cards/j/Joust.java b/Mage.Sets/src/mage/cards/j/Joust.java new file mode 100644 index 0000000000..813bb56ac0 --- /dev/null +++ b/Mage.Sets/src/mage/cards/j/Joust.java @@ -0,0 +1,88 @@ +package mage.cards.j; + +import mage.abilities.Ability; +import mage.abilities.effects.ContinuousEffect; +import mage.abilities.effects.OneShotEffect; +import mage.abilities.effects.common.continuous.BoostTargetEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.*; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterCreaturePermanent; +import mage.filter.predicate.permanent.ControllerPredicate; +import mage.game.Game; +import mage.game.permanent.Permanent; +import mage.target.TargetPermanent; +import mage.target.common.TargetControlledCreaturePermanent; +import mage.target.targetpointer.FixedTarget; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class Joust extends CardImpl { + + private static final FilterPermanent filter + = new FilterCreaturePermanent("creature you don't control"); + + static { + filter.add(new ControllerPredicate(TargetController.NOT_YOU)); + } + + public Joust(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.SORCERY}, "{1}{R}"); + + // Choose target creature you control and target creature you don't control. The creature you control gets +2/+1 until end of turn if it's a Knight. Then those creatures fight each other. + this.getSpellAbility().addEffect(new JoustEffect()); + this.getSpellAbility().addTarget(new TargetControlledCreaturePermanent()); + this.getSpellAbility().addTarget(new TargetPermanent(filter)); + } + + private Joust(final Joust card) { + super(card); + } + + @Override + public Joust copy() { + return new Joust(this); + } +} + +class JoustEffect extends OneShotEffect { + + JoustEffect() { + super(Outcome.Benefit); + staticText = "Choose target creature you control and target creature you don't control. " + + "The creature you control gets +2/+1 until end of turn if it's a Knight. " + + "Then those creatures fight each other."; + } + + private JoustEffect(final JoustEffect effect) { + super(effect); + } + + @Override + public JoustEffect copy() { + return new JoustEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + Permanent creature1 = game.getPermanent(source.getTargets().get(0).getFirstTarget()); + Permanent creature2 = game.getPermanent(source.getTargets().get(0).getFirstTarget()); + if (creature1 == null) { + return false; + } + if (creature1.hasSubtype(SubType.KNIGHT, game)) { + ContinuousEffect effect = new BoostTargetEffect(2, 1, Duration.EndOfTurn); + effect.setTargetPointer(new FixedTarget(creature1.getId(), game)); + game.addEffect(effect, source); + } + if (creature2 == null) { + return true; + } + game.applyEffects(); + return creature1.fight(creature2, source, game); + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 39ada437ef..84b07947a6 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -66,6 +66,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Golden Egg", 220, Rarity.COMMON, mage.cards.g.GoldenEgg.class)); cards.add(new SetCardInfo("Heraldic Banner", 222, Rarity.UNCOMMON, mage.cards.h.HeraldicBanner.class)); cards.add(new SetCardInfo("Inspiring Veteran", 194, Rarity.UNCOMMON, mage.cards.i.InspiringVeteran.class)); + cards.add(new SetCardInfo("Joust", 129, Rarity.UNCOMMON, mage.cards.j.Joust.class)); cards.add(new SetCardInfo("Jousting Dummy", 224, Rarity.COMMON, mage.cards.j.JoustingDummy.class)); cards.add(new SetCardInfo("Keeper of Fables", 163, Rarity.UNCOMMON, mage.cards.k.KeeperOfFables.class)); cards.add(new SetCardInfo("Knights' Charge", 328, Rarity.RARE, mage.cards.k.KnightsCharge.class)); From 91e3fee5d43680d331897083133657d4c16e5992 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 9 Sep 2019 19:52:51 -0400 Subject: [PATCH 026/373] Implemented Rowan, Fearless Sparkmage --- .../mage/cards/r/RowanFearlessSparkmage.java | 76 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 77 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/r/RowanFearlessSparkmage.java diff --git a/Mage.Sets/src/mage/cards/r/RowanFearlessSparkmage.java b/Mage.Sets/src/mage/cards/r/RowanFearlessSparkmage.java new file mode 100644 index 0000000000..ade68c0c67 --- /dev/null +++ b/Mage.Sets/src/mage/cards/r/RowanFearlessSparkmage.java @@ -0,0 +1,76 @@ +package mage.cards.r; + +import mage.abilities.Ability; +import mage.abilities.LoyaltyAbility; +import mage.abilities.common.PlaneswalkerEntersWithLoyaltyCountersAbility; +import mage.abilities.effects.common.DamageTargetEffect; +import mage.abilities.effects.common.UntapAllEffect; +import mage.abilities.effects.common.combat.CantBlockTargetEffect; +import mage.abilities.effects.common.continuous.BoostTargetEffect; +import mage.abilities.effects.common.continuous.GainAbilityAllEffect; +import mage.abilities.effects.common.continuous.GainAbilityTargetEffect; +import mage.abilities.effects.common.continuous.GainControlAllEffect; +import mage.abilities.keyword.FirstStrikeAbility; +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.SuperType; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterCreaturePermanent; +import mage.target.common.TargetCreaturePermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class RowanFearlessSparkmage extends CardImpl { + + private static final FilterPermanent filter = new FilterCreaturePermanent("all creatures"); + + public RowanFearlessSparkmage(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.PLANESWALKER}, "{3}{R}{R}"); + + this.addSuperType(SuperType.LEGENDARY); + this.subtype.add(SubType.ROWAN); + this.addAbility(new PlaneswalkerEntersWithLoyaltyCountersAbility(5)); + + // +1: Up to one target creature gets +3/+0 and gains first strike until end of turn. + Ability ability = new LoyaltyAbility(new BoostTargetEffect( + 3, 0, Duration.EndOfTurn + ).setText("Up to one target creature gets +3/+0"), 1); + ability.addEffect(new GainAbilityTargetEffect( + FirstStrikeAbility.getInstance(), Duration.EndOfTurn + ).setText("and gains first strike until end of turn")); + ability.addTarget(new TargetCreaturePermanent(0, 1)); + this.addAbility(ability); + + // −2: Rowan, Fearless Sparkmage deals 1 damage to each of up to two target creatures. Those creatures can't block this turn. + ability = new LoyaltyAbility(new DamageTargetEffect(1) + .setText("deals 1 damage to each of up to two target creatures."), -2); + ability.addEffect(new CantBlockTargetEffect(Duration.EndOfTurn) + .setText("Those creatures can't block this turn.")); + ability.addTarget(new TargetCreaturePermanent(0, 2)); + this.addAbility(ability); + + // −9: Gain control of all creatures until end of turn. Untap them. They gain haste until end of turn. + ability = new LoyaltyAbility(new GainControlAllEffect(Duration.EndOfTurn, filter), -9); + ability.addEffect(new UntapAllEffect(filter).setText("until end of turn. Untap them.")); + ability.addEffect(new GainAbilityAllEffect( + HasteAbility.getInstance(), Duration.EndOfTurn, filter + ).setText("They gain haste until end of turn")); + this.addAbility(ability); + } + + private RowanFearlessSparkmage(final RowanFearlessSparkmage card) { + super(card); + } + + @Override + public RowanFearlessSparkmage copy() { + return new RowanFearlessSparkmage(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 84b07947a6..1c63610986 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -86,6 +86,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Rosethorn Acolyte", 174, Rarity.COMMON, mage.cards.r.RosethornAcolyte.class)); cards.add(new SetCardInfo("Rowan's Battleguard", 306, Rarity.UNCOMMON, mage.cards.r.RowansBattleguard.class)); cards.add(new SetCardInfo("Rowan's Stalwarts", 307, Rarity.RARE, mage.cards.r.RowansStalwarts.class)); + cards.add(new SetCardInfo("Rowan, Fearless Sparkmage", 304, Rarity.MYTHIC, mage.cards.r.RowanFearlessSparkmage.class)); cards.add(new SetCardInfo("Run Away Together", 62, Rarity.COMMON, mage.cards.r.RunAwayTogether.class)); cards.add(new SetCardInfo("Savvy Hunter", 200, Rarity.UNCOMMON, mage.cards.s.SavvyHunter.class)); cards.add(new SetCardInfo("Shimmer Dragon", 317, Rarity.RARE, mage.cards.s.ShimmerDragon.class)); From 46b0f0770d9013ddf6130f9ad05b72ac97fecbd0 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 9 Sep 2019 20:09:43 -0400 Subject: [PATCH 027/373] Implemented Oko's Hospitality --- .../src/mage/cards/o/OkosHospitality.java | 46 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + Utils/mtg-cards-data.txt | 1 + 3 files changed, 48 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/o/OkosHospitality.java diff --git a/Mage.Sets/src/mage/cards/o/OkosHospitality.java b/Mage.Sets/src/mage/cards/o/OkosHospitality.java new file mode 100644 index 0000000000..02cb47d377 --- /dev/null +++ b/Mage.Sets/src/mage/cards/o/OkosHospitality.java @@ -0,0 +1,46 @@ +package mage.cards.o; + +import mage.abilities.effects.common.continuous.SetPowerToughnessAllEffect; +import mage.abilities.effects.common.search.SearchLibraryGraveyardPutInHandEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.filter.FilterCard; +import mage.filter.StaticFilters; +import mage.filter.predicate.mageobject.NamePredicate; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class OkosHospitality extends CardImpl { + + private static final FilterCard filter = new FilterCard("Oko, the Trickster"); + + static { + filter.add(new NamePredicate("Oko, the Trickster")); + } + + public OkosHospitality(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.INSTANT}, "{3}{G}{U}"); + + // Creatures you control have base power and toughness 3/3 until end of turn. You may search your library and/or graveyard for a card named Oko, the Trickster, reveal it, and put it into your hand. If you search your library this way, shuffle it. + this.getSpellAbility().addEffect(new SetPowerToughnessAllEffect( + 3, 3, Duration.EndOfTurn, StaticFilters.FILTER_CONTROLLED_CREATURES, true + )); + this.getSpellAbility().addEffect( + new SearchLibraryGraveyardPutInHandEffect(filter, false, true) + ); + } + + private OkosHospitality(final OkosHospitality card) { + super(card); + } + + @Override + public OkosHospitality copy() { + return new OkosHospitality(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 1c63610986..377cb73c92 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -77,6 +77,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Midnight Clock", 54, Rarity.RARE, mage.cards.m.MidnightClock.class)); cards.add(new SetCardInfo("Mystical Dispute", 58, Rarity.UNCOMMON, mage.cards.m.MysticalDispute.class)); cards.add(new SetCardInfo("Oko's Accomplices", 310, Rarity.COMMON, mage.cards.o.OkosAccomplices.class)); + cards.add(new SetCardInfo("Oko's Hospitality", 312, Rarity.RARE, mage.cards.o.OkosHospitality.class)); cards.add(new SetCardInfo("Oko, Thief of Crowns", 197, Rarity.MYTHIC, mage.cards.o.OkoThiefOfCrowns.class)); cards.add(new SetCardInfo("Once Upon a Time", 169, Rarity.RARE, mage.cards.o.OnceUponATime.class)); cards.add(new SetCardInfo("Order of Midnight", 99, Rarity.UNCOMMON, mage.cards.o.OrderOfMidnight.class)); diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index fbde76ea2a..929cddaeb2 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -36080,6 +36080,7 @@ Wind-Scarred Crag|Throne of Eldraine|308|C||Land|||Wind-Scarred Crag enters the Oko, the Trickster|Throne of Eldraine|309|M|{4}{G}{U}|Legendary Planeswalker - Oko|4|+1: Put two +1/+1 counters on up to one target creature you control.$0: Until end of turn, Oko, the Trickster becomes a copy of target creature you control. Prevent all damage that would be dealt to him this turn.$−7: Until end of turn, each creature you control has base power and toughness 10/10 and gains trample.| Oko's Accomplices|Throne of Eldraine|310|C|{2}{U}|Creature - Faerie|2|3|Flying| Bramblefort Fink|Throne of Eldraine|311|U|{1}{G}|Creature - Ouphe|2|2|{8}: Bramblefort Fink has base power and toughness 10/10 until end of turn. Activate this ability only if you control an Oko planeswalker.| +Oko's Hospitality|Throne of Eldraine|312|R|{3}{G}{U}|Instant|||Creatures you control have base power and toughness 3/3 until end of turn. You may search your library and/or graveyard for a card named Oko, the Trickster, reveal it, and put it into your hand. If you search your library this way, shuffle it.| Thornwood Falls|Throne of Eldraine|313|C||Land|||Thornwood Falls enters the battlefield tapped.$When Thornwood Falls enters the battlefield, you gain 1 life.${T}: Add {G} or {U}.| Mace of the Valiant|Throne of Eldraine|314|R|{2}{W}|Artifact - Equipment|||Equipped creature gets +1/+1 for each charge counter on Mace of the Valiant and has vigilance.$Whenever a creature enters the battlefield under your control, put a charge counter on Mace of the Valiant.$Equip {3}| Silverwing Squadron|Throne of Eldraine|315|R|{5}{W}|Creature - Human Knight|*|*|Flying, vigilance$Silverwing Squadron's power and toughness are each equal to the number of creatures you control.$Whenever Silverwing Squadron attacks, create a number of 2/2 white Knight creature tokens with vigilance equal to the number of opponents you have.| From c2ed868787bb9c248de24eaa0ff4714c8bfa1a7a Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 9 Sep 2019 20:22:22 -0400 Subject: [PATCH 028/373] Implemented Embercleave --- Mage.Sets/src/mage/cards/e/Embercleave.java | 111 ++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 112 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/e/Embercleave.java diff --git a/Mage.Sets/src/mage/cards/e/Embercleave.java b/Mage.Sets/src/mage/cards/e/Embercleave.java new file mode 100644 index 0000000000..a5a6c6936b --- /dev/null +++ b/Mage.Sets/src/mage/cards/e/Embercleave.java @@ -0,0 +1,111 @@ +package mage.cards.e; + +import mage.abilities.Ability; +import mage.abilities.SpellAbility; +import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.effects.common.AttachEffect; +import mage.abilities.effects.common.continuous.BoostEquippedEffect; +import mage.abilities.effects.common.continuous.GainAbilityAttachedEffect; +import mage.abilities.effects.common.cost.CostModificationEffectImpl; +import mage.abilities.keyword.DoubleStrikeAbility; +import mage.abilities.keyword.EquipAbility; +import mage.abilities.keyword.FlashAbility; +import mage.abilities.keyword.TrampleAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.*; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterControlledCreaturePermanent; +import mage.filter.predicate.permanent.AttackingPredicate; +import mage.game.Game; +import mage.target.common.TargetControlledCreaturePermanent; +import mage.util.CardUtil; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class Embercleave extends CardImpl { + + public Embercleave(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT}, "{4}{R}{R}"); + + this.addSuperType(SuperType.LEGENDARY); + this.subtype.add(SubType.EQUIPMENT); + + // Flash + this.addAbility(FlashAbility.getInstance()); + + // This spell costs {1} less to cast for each attacking creature you control. + this.addAbility(new SimpleStaticAbility(Zone.ALL, new AncientStoneIdolCostReductionEffect())); + + // When Embercleave enters the battlefield, attach it to target creature you control. + Ability ability = new EntersBattlefieldTriggeredAbility(new AttachEffect( + Outcome.BoostCreature, "attach it to target creature you control" + ), false); + ability.addTarget(new TargetControlledCreaturePermanent()); + this.addAbility(ability); + + // Equipped creature gets +1/+1 and has double strike and trample. + ability = new SimpleStaticAbility(new BoostEquippedEffect(1, 1)); + ability.addEffect(new GainAbilityAttachedEffect( + DoubleStrikeAbility.getInstance(), AttachmentType.EQUIPMENT + ).setText("and has first strike")); + ability.addEffect(new GainAbilityAttachedEffect( + TrampleAbility.getInstance(), AttachmentType.EQUIPMENT + ).setText("and trample")); + this.addAbility(ability); + + // Equip {3} + this.addAbility(new EquipAbility(3)); + } + + private Embercleave(final Embercleave card) { + super(card); + } + + @Override + public Embercleave copy() { + return new Embercleave(this); + } +} + +class AncientStoneIdolCostReductionEffect extends CostModificationEffectImpl { + + private static final FilterPermanent filter = new FilterControlledCreaturePermanent(); + + static { + filter.add(AttackingPredicate.instance); + } + + AncientStoneIdolCostReductionEffect() { + super(Duration.WhileOnStack, Outcome.Benefit, CostModificationType.REDUCE_COST); + staticText = "This spell costs {1} less to cast for each attacking creature you control"; + } + + private AncientStoneIdolCostReductionEffect(AncientStoneIdolCostReductionEffect effect) { + super(effect); + } + + @Override + public boolean apply(Game game, Ability source, Ability abilityToModify) { + int reductionAmount = game.getBattlefield().count(filter, source.getSourceId(), source.getControllerId(), game); + CardUtil.reduceCost(abilityToModify, reductionAmount); + return true; + } + + @Override + public boolean applies(Ability abilityToModify, Ability source, Game game) { + if ((abilityToModify instanceof SpellAbility) && abilityToModify.getSourceId().equals(source.getSourceId())) { + return game.getCard(abilityToModify.getSourceId()) != null; + } + return false; + } + + @Override + public AncientStoneIdolCostReductionEffect copy() { + return new AncientStoneIdolCostReductionEffect(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 377cb73c92..6169ee9ded 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -46,6 +46,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Command Tower", 333, Rarity.COMMON, mage.cards.c.CommandTower.class)); cards.add(new SetCardInfo("Corridor Monitor", 41, Rarity.COMMON, mage.cards.c.CorridorMonitor.class)); cards.add(new SetCardInfo("Crystal Slipper", 119, Rarity.COMMON, mage.cards.c.CrystalSlipper.class)); + cards.add(new SetCardInfo("Embercleave", 120, Rarity.MYTHIC, mage.cards.e.Embercleave.class)); cards.add(new SetCardInfo("Embereth Paladin", 121, Rarity.COMMON, mage.cards.e.EmberethPaladin.class)); cards.add(new SetCardInfo("Embereth Shieldbreaker", 122, Rarity.UNCOMMON, mage.cards.e.EmberethShieldbreaker.class)); cards.add(new SetCardInfo("Embereth Skyblazer", 321, Rarity.RARE, mage.cards.e.EmberethSkyblazer.class)); From 4a3cced7281992c22538f87f10aae795df1ff62a Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 9 Sep 2019 20:35:17 -0400 Subject: [PATCH 029/373] Implemented The Royal Scions --- .../src/mage/cards/t/TheRoyalScions.java | 125 ++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 126 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/t/TheRoyalScions.java diff --git a/Mage.Sets/src/mage/cards/t/TheRoyalScions.java b/Mage.Sets/src/mage/cards/t/TheRoyalScions.java new file mode 100644 index 0000000000..337d87e5f7 --- /dev/null +++ b/Mage.Sets/src/mage/cards/t/TheRoyalScions.java @@ -0,0 +1,125 @@ +package mage.cards.t; + +import mage.abilities.Ability; +import mage.abilities.DelayedTriggeredAbility; +import mage.abilities.LoyaltyAbility; +import mage.abilities.common.PlaneswalkerEntersWithLoyaltyCountersAbility; +import mage.abilities.dynamicvalue.common.CardsInControllerHandCount; +import mage.abilities.effects.Effect; +import mage.abilities.effects.OneShotEffect; +import mage.abilities.effects.common.DamageTargetEffect; +import mage.abilities.effects.common.DrawCardSourceControllerEffect; +import mage.abilities.effects.common.DrawDiscardControllerEffect; +import mage.abilities.effects.common.continuous.BoostTargetEffect; +import mage.abilities.effects.common.continuous.GainAbilityTargetEffect; +import mage.abilities.keyword.FirstStrikeAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.*; +import mage.game.Game; +import mage.game.events.GameEvent; +import mage.target.common.TargetAnyTarget; +import mage.target.common.TargetCreaturePermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class TheRoyalScions extends CardImpl { + + public TheRoyalScions(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.PLANESWALKER}, "{1}{U}{R}"); + + this.addSuperType(SuperType.LEGENDARY); + this.subtype.add(SubType.WILL); + this.subtype.add(SubType.ROWAN); + this.addAbility(new PlaneswalkerEntersWithLoyaltyCountersAbility(5)); + + // +1: Draw a card, then discard a card. + this.addAbility(new LoyaltyAbility(new DrawDiscardControllerEffect(1, 1), 1)); + + // +1: Target creature gets +2/+0 and gains first strike until end of turn. + Ability ability = new LoyaltyAbility(new BoostTargetEffect( + 2, 0, Duration.EndOfTurn + ).setText("Target creature gets +2/+0"), 1); + ability.addEffect(new GainAbilityTargetEffect( + FirstStrikeAbility.getInstance(), Duration.EndOfTurn + ).setText("and gains first strike until end of turn")); + ability.addTarget(new TargetCreaturePermanent()); + this.addAbility(ability); + + // −8: Draw four cards. When you do, The Royal Scions deals damage to any target equal to the number of cards in your hand. + this.addAbility(new LoyaltyAbility(new TheRoyalScionsCreateReflexiveTriggerEffect(), -8)); + } + + private TheRoyalScions(final TheRoyalScions card) { + super(card); + } + + @Override + public TheRoyalScions copy() { + return new TheRoyalScions(this); + } +} + +class TheRoyalScionsCreateReflexiveTriggerEffect extends OneShotEffect { + + private static final Effect effect = new DrawCardSourceControllerEffect(4); + + TheRoyalScionsCreateReflexiveTriggerEffect() { + super(Outcome.Benefit); + staticText = "Draw four cards. When you do, {this} deals damage " + + "to any target equal to the number of cards in your hand."; + } + + private TheRoyalScionsCreateReflexiveTriggerEffect(final TheRoyalScionsCreateReflexiveTriggerEffect effect) { + super(effect); + } + + @Override + public TheRoyalScionsCreateReflexiveTriggerEffect copy() { + return new TheRoyalScionsCreateReflexiveTriggerEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + effect.apply(game, source); + game.addDelayedTriggeredAbility(new TheRoyalScionsReflexiveTriggeredAbility(), source); + game.fireEvent(GameEvent.getEvent(GameEvent.EventType.OPTION_USED, source.getOriginalId(), source.getSourceId(), source.getControllerId(), 0)); + return true; + } +} + +class TheRoyalScionsReflexiveTriggeredAbility extends DelayedTriggeredAbility { + + TheRoyalScionsReflexiveTriggeredAbility() { + super(new DamageTargetEffect(CardsInControllerHandCount.instance), Duration.OneUse, true); + this.addTarget(new TargetAnyTarget()); + } + + private TheRoyalScionsReflexiveTriggeredAbility(final TheRoyalScionsReflexiveTriggeredAbility ability) { + super(ability); + } + + @Override + public TheRoyalScionsReflexiveTriggeredAbility copy() { + return new TheRoyalScionsReflexiveTriggeredAbility(this); + } + + @Override + public boolean checkEventType(GameEvent event, Game game) { + return event.getType() == GameEvent.EventType.OPTION_USED; + } + + @Override + public boolean checkTrigger(GameEvent event, Game game) { + return event.getPlayerId().equals(this.getControllerId()) + && event.getSourceId().equals(this.getSourceId()); + } + + @Override + public String getRule() { + return "When you do, {this} deals damage to any target equal to the number of cards in your hand."; + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 6169ee9ded..64377bfebf 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -104,6 +104,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Syr Konrad, the Grim", 107, Rarity.UNCOMMON, mage.cards.s.SyrKonradTheGrim.class)); cards.add(new SetCardInfo("Taste of Death", 320, Rarity.RARE, mage.cards.t.TasteOfDeath.class)); cards.add(new SetCardInfo("The Circle of Loyalty", 9, Rarity.MYTHIC, mage.cards.t.TheCircleOfLoyalty.class)); + cards.add(new SetCardInfo("The Royal Scions", 199, Rarity.MYTHIC, mage.cards.t.TheRoyalScions.class)); cards.add(new SetCardInfo("Thorn Mammoth", 323, Rarity.RARE, mage.cards.t.ThornMammoth.class)); cards.add(new SetCardInfo("Thornwood Falls", 313, Rarity.COMMON, mage.cards.t.ThornwoodFalls.class)); cards.add(new SetCardInfo("Tome Raider", 68, Rarity.COMMON, mage.cards.t.TomeRaider.class)); From 98f26e5b3de3bd53b12ada1f41bc43f885e4e3c6 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 9 Sep 2019 21:04:05 -0400 Subject: [PATCH 030/373] Implemented Wicked Guardian --- .../src/mage/cards/w/WickedGuardian.java | 92 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 93 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/w/WickedGuardian.java diff --git a/Mage.Sets/src/mage/cards/w/WickedGuardian.java b/Mage.Sets/src/mage/cards/w/WickedGuardian.java new file mode 100644 index 0000000000..3309300daa --- /dev/null +++ b/Mage.Sets/src/mage/cards/w/WickedGuardian.java @@ -0,0 +1,92 @@ +package mage.cards.w; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.effects.OneShotEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Outcome; +import mage.constants.SubType; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterControlledCreaturePermanent; +import mage.filter.predicate.permanent.AnotherPredicate; +import mage.game.Game; +import mage.game.permanent.Permanent; +import mage.players.Player; +import mage.target.TargetPermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class WickedGuardian extends CardImpl { + + public WickedGuardian(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{3}{B}"); + + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.NOBLE); + this.power = new MageInt(4); + this.toughness = new MageInt(2); + + // When Wicked Guardian enters the battlefield, you may have it deal 2 damage to another creature you control. If you do, draw a card. + this.addAbility(new EntersBattlefieldTriggeredAbility(new WickedGuardianEffect(), true)); + } + + private WickedGuardian(final WickedGuardian card) { + super(card); + } + + @Override + public WickedGuardian copy() { + return new WickedGuardian(this); + } +} + +class WickedGuardianEffect extends OneShotEffect { + + private static final FilterPermanent filter + = new FilterControlledCreaturePermanent("another creature you control"); + + static { + filter.add(AnotherPredicate.instance); + } + + WickedGuardianEffect() { + super(Outcome.Benefit); + staticText = "have it deal 2 damage to another creature you control. If you do, draw a card"; + } + + private WickedGuardianEffect(final WickedGuardianEffect effect) { + super(effect); + } + + @Override + public WickedGuardianEffect copy() { + return new WickedGuardianEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + Player player = game.getPlayer(source.getControllerId()); + if (player == null) { + return false; + } + if (game.getBattlefield().count(filter, source.getSourceId(), source.getControllerId(), game) == 0) { + return false; + } + TargetPermanent target = new TargetPermanent(0, 1, filter, true); + if (!player.choose(outcome, target, source.getSourceId(), game)) { + return false; + } + Permanent permanent = game.getPermanent(target.getFirstTarget()); + if (permanent == null) { + return false; + } + permanent.damage(2, source.getSourceId(), game); + return player.drawCards(2, game) > 0; + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 64377bfebf..b464470748 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -111,6 +111,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Tome of Legends", 332, Rarity.RARE, mage.cards.t.TomeOfLegends.class)); cards.add(new SetCardInfo("Tournament Grounds", 248, Rarity.UNCOMMON, mage.cards.t.TournamentGrounds.class)); cards.add(new SetCardInfo("Turn into a Pumpkin", 69, Rarity.UNCOMMON, mage.cards.t.TurnIntoAPumpkin.class)); + cards.add(new SetCardInfo("Wicked Guardian", 109, Rarity.COMMON, mage.cards.w.WickedGuardian.class)); cards.add(new SetCardInfo("Wicked Wolf", 181, Rarity.RARE, mage.cards.w.WickedWolf.class)); cards.add(new SetCardInfo("Wind-Scarred Crag", 308, Rarity.COMMON, mage.cards.w.WindScarredCrag.class)); cards.add(new SetCardInfo("Wintermoor Commander", 205, Rarity.UNCOMMON, mage.cards.w.WintermoorCommander.class)); From 2b7d30477f8ab9a6bd4f8f811fc20697a78546cb Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 9 Sep 2019 21:12:13 -0400 Subject: [PATCH 031/373] Implemented Wildwood Tracker --- .../src/mage/cards/w/WildwoodTracker.java | 61 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 62 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/w/WildwoodTracker.java diff --git a/Mage.Sets/src/mage/cards/w/WildwoodTracker.java b/Mage.Sets/src/mage/cards/w/WildwoodTracker.java new file mode 100644 index 0000000000..8722bc8248 --- /dev/null +++ b/Mage.Sets/src/mage/cards/w/WildwoodTracker.java @@ -0,0 +1,61 @@ +package mage.cards.w; + +import mage.MageInt; +import mage.abilities.common.AttacksOrBlocksTriggeredAbility; +import mage.abilities.condition.Condition; +import mage.abilities.condition.common.PermanentsOnTheBattlefieldCondition; +import mage.abilities.decorator.ConditionalInterveningIfTriggeredAbility; +import mage.abilities.effects.common.continuous.BoostSourceEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterControlledCreaturePermanent; +import mage.filter.predicate.Predicates; +import mage.filter.predicate.mageobject.SubtypePredicate; +import mage.filter.predicate.permanent.AnotherPredicate; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class WildwoodTracker extends CardImpl { + + private static final FilterPermanent filter = new FilterControlledCreaturePermanent(); + + static { + filter.add(AnotherPredicate.instance); + filter.add(Predicates.not(new SubtypePredicate(SubType.HUMAN))); + } + + private static final Condition condition = new PermanentsOnTheBattlefieldCondition(filter); + + public WildwoodTracker(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{G}"); + + this.subtype.add(SubType.ELF); + this.subtype.add(SubType.WARRIOR); + this.power = new MageInt(1); + this.toughness = new MageInt(1); + + // Whenever Wildwood Tracker attacks or blocks, if you control another non-Human creature, Wildwood Tracker gets +1/+1 until end of turn. + this.addAbility(new ConditionalInterveningIfTriggeredAbility( + new AttacksOrBlocksTriggeredAbility( + new BoostSourceEffect(1, 1, Duration.EndOfTurn), false + ), condition, "Whenever {this} attacks or blocks, if you control another non-Human creature, " + + "{this} gets +1/+1 until end of turn." + )); + } + + private WildwoodTracker(final WildwoodTracker card) { + super(card); + } + + @Override + public WildwoodTracker copy() { + return new WildwoodTracker(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index b464470748..937aababb6 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -113,6 +113,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Turn into a Pumpkin", 69, Rarity.UNCOMMON, mage.cards.t.TurnIntoAPumpkin.class)); cards.add(new SetCardInfo("Wicked Guardian", 109, Rarity.COMMON, mage.cards.w.WickedGuardian.class)); cards.add(new SetCardInfo("Wicked Wolf", 181, Rarity.RARE, mage.cards.w.WickedWolf.class)); + cards.add(new SetCardInfo("Wildwood Tracker", 183, Rarity.COMMON, mage.cards.w.WildwoodTracker.class)); cards.add(new SetCardInfo("Wind-Scarred Crag", 308, Rarity.COMMON, mage.cards.w.WindScarredCrag.class)); cards.add(new SetCardInfo("Wintermoor Commander", 205, Rarity.UNCOMMON, mage.cards.w.WintermoorCommander.class)); cards.add(new SetCardInfo("Wishful Merfolk", 73, Rarity.COMMON, mage.cards.w.WishfulMerfolk.class)); From 308334b65bd9dd6e207cd7a19a81b3badf5165f6 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 9 Sep 2019 21:24:33 -0400 Subject: [PATCH 032/373] Implemented Wishclaw Talisman --- .../src/mage/cards/w/WishclawTalisman.java | 102 ++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 103 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/w/WishclawTalisman.java diff --git a/Mage.Sets/src/mage/cards/w/WishclawTalisman.java b/Mage.Sets/src/mage/cards/w/WishclawTalisman.java new file mode 100644 index 0000000000..ea39ffbac2 --- /dev/null +++ b/Mage.Sets/src/mage/cards/w/WishclawTalisman.java @@ -0,0 +1,102 @@ +package mage.cards.w; + +import mage.abilities.Ability; +import mage.abilities.common.ActivateIfConditionActivatedAbility; +import mage.abilities.common.EntersBattlefieldAbility; +import mage.abilities.condition.common.MyTurnCondition; +import mage.abilities.costs.common.RemoveCountersSourceCost; +import mage.abilities.costs.common.TapSourceCost; +import mage.abilities.costs.mana.GenericManaCost; +import mage.abilities.effects.ContinuousEffect; +import mage.abilities.effects.Effect; +import mage.abilities.effects.OneShotEffect; +import mage.abilities.effects.common.continuous.GainControlTargetEffect; +import mage.abilities.effects.common.counter.AddCountersSourceEffect; +import mage.abilities.effects.common.search.SearchLibraryPutInHandEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.Outcome; +import mage.constants.Zone; +import mage.counters.CounterType; +import mage.game.Game; +import mage.players.Player; +import mage.target.TargetPlayer; +import mage.target.common.TargetCardInLibrary; +import mage.target.common.TargetOpponent; +import mage.target.targetpointer.FixedTarget; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class WishclawTalisman extends CardImpl { + + public WishclawTalisman(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT}, "{1}{B}"); + + // Wishclaw Talisman enters the battlefield with three wish counters on it. + this.addAbility(new EntersBattlefieldAbility( + new AddCountersSourceEffect(CounterType.WISH.createInstance(3)), + "{this} enters the battlefield with three wish counters on it" + )); + + // {1}, {T}, Remove a wish counter from Wishclaw Talisman: Search your library for a card, put it into your hand, then shuffle your library. An opponent gains control of Wishclaw Talisman. Activate this ability only during your turn. + Ability ability = new ActivateIfConditionActivatedAbility( + Zone.BATTLEFIELD, new WishclawTalismanEffect(), new GenericManaCost(1), MyTurnCondition.instance + ); + ability.addCost(new TapSourceCost()); + ability.addCost(new RemoveCountersSourceCost(CounterType.WISH.createInstance(3))); + this.addAbility(ability); + } + + private WishclawTalisman(final WishclawTalisman card) { + super(card); + } + + @Override + public WishclawTalisman copy() { + return new WishclawTalisman(this); + } +} + +class WishclawTalismanEffect extends OneShotEffect { + + private static final Effect effect = new SearchLibraryPutInHandEffect(new TargetCardInLibrary()); + + WishclawTalismanEffect() { + super(Outcome.Benefit); + staticText = "Search your library for a card, put it into your hand, then shuffle your library. " + + "An opponent gains control of {this}"; + } + + private WishclawTalismanEffect(final WishclawTalismanEffect effect) { + super(effect); + } + + @Override + public WishclawTalismanEffect copy() { + return new WishclawTalismanEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + effect.apply(game, source); + Player player = game.getPlayer(source.getControllerId()); + if (player == null) { + return false; + } + TargetPlayer target = new TargetOpponent(); + target.setNotTarget(true); + if (!player.choose(outcome, target, source.getSourceId(), game)) { + return false; + } + ContinuousEffect continuousEffect + = new GainControlTargetEffect(Duration.Custom, true, target.getFirstTarget()); + continuousEffect.setTargetPointer(new FixedTarget(source.getSourceId(), game)); + game.addEffect(continuousEffect, source); + return true; + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 937aababb6..1f624867de 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -116,6 +116,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Wildwood Tracker", 183, Rarity.COMMON, mage.cards.w.WildwoodTracker.class)); cards.add(new SetCardInfo("Wind-Scarred Crag", 308, Rarity.COMMON, mage.cards.w.WindScarredCrag.class)); cards.add(new SetCardInfo("Wintermoor Commander", 205, Rarity.UNCOMMON, mage.cards.w.WintermoorCommander.class)); + cards.add(new SetCardInfo("Wishclaw Talisman", 110, Rarity.RARE, mage.cards.w.WishclawTalisman.class)); cards.add(new SetCardInfo("Wishful Merfolk", 73, Rarity.COMMON, mage.cards.w.WishfulMerfolk.class)); cards.add(new SetCardInfo("Witch's Cottage", 249, Rarity.COMMON, mage.cards.w.WitchsCottage.class)); cards.add(new SetCardInfo("Witch's Vengeance", 111, Rarity.RARE, mage.cards.w.WitchsVengeance.class)); From 811e1b4cd0e0af49d84e79774d6f19dde5d6a7fc Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 9 Sep 2019 21:40:54 -0400 Subject: [PATCH 033/373] Implemented Questing Beast --- Mage.Sets/src/mage/cards/b/BlindZealot.java | 27 +-- Mage.Sets/src/mage/cards/q/QuestingBeast.java | 157 ++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 3 files changed, 173 insertions(+), 12 deletions(-) create mode 100644 Mage.Sets/src/mage/cards/q/QuestingBeast.java diff --git a/Mage.Sets/src/mage/cards/b/BlindZealot.java b/Mage.Sets/src/mage/cards/b/BlindZealot.java index c1de1d9731..4fb163cab2 100644 --- a/Mage.Sets/src/mage/cards/b/BlindZealot.java +++ b/Mage.Sets/src/mage/cards/b/BlindZealot.java @@ -1,6 +1,5 @@ package mage.cards.b; -import java.util.UUID; import mage.MageInt; import mage.abilities.Ability; import mage.abilities.TriggeredAbilityImpl; @@ -16,13 +15,15 @@ import mage.constants.Zone; import mage.filter.common.FilterCreaturePermanent; import mage.filter.predicate.permanent.ControllerIdPredicate; import mage.game.Game; +import mage.game.events.DamagedEvent; import mage.game.events.GameEvent; import mage.game.events.GameEvent.EventType; import mage.players.Player; import mage.target.common.TargetCreaturePermanent; +import java.util.UUID; + /** - * * @author North */ public final class BlindZealot extends CardImpl { @@ -42,7 +43,7 @@ public final class BlindZealot extends CardImpl { this.addAbility(ability); } - public BlindZealot(final BlindZealot card) { + private BlindZealot(final BlindZealot card) { super(card); } @@ -54,11 +55,11 @@ public final class BlindZealot extends CardImpl { class BlindZealotTriggeredAbility extends TriggeredAbilityImpl { - public BlindZealotTriggeredAbility() { + BlindZealotTriggeredAbility() { super(Zone.BATTLEFIELD, new DoIfCostPaid(new DestroyTargetEffect(), new SacrificeSourceCost()), true); } - public BlindZealotTriggeredAbility(final BlindZealotTriggeredAbility ability) { + private BlindZealotTriggeredAbility(final BlindZealotTriggeredAbility ability) { super(ability); } @@ -75,14 +76,16 @@ class BlindZealotTriggeredAbility extends TriggeredAbilityImpl { @Override public boolean checkTrigger(GameEvent event, Game game) { Player opponent = game.getPlayer(event.getPlayerId()); - if (opponent != null && event.getSourceId().equals(this.sourceId)) { - FilterCreaturePermanent filter = new FilterCreaturePermanent("creature " + opponent.getLogName() + " controls"); - filter.add(new ControllerIdPredicate(opponent.getId())); - this.getTargets().clear(); - this.addTarget(new TargetCreaturePermanent(filter)); - return true; + if (opponent == null + || !event.getSourceId().equals(this.sourceId) + || !((DamagedEvent) event).isCombatDamage()) { + return false; } - return false; + FilterCreaturePermanent filter = new FilterCreaturePermanent("creature " + opponent.getLogName() + " controls"); + filter.add(new ControllerIdPredicate(opponent.getId())); + this.getTargets().clear(); + this.addTarget(new TargetCreaturePermanent(filter)); + return true; } @Override diff --git a/Mage.Sets/src/mage/cards/q/QuestingBeast.java b/Mage.Sets/src/mage/cards/q/QuestingBeast.java new file mode 100644 index 0000000000..0a4193b7ef --- /dev/null +++ b/Mage.Sets/src/mage/cards/q/QuestingBeast.java @@ -0,0 +1,157 @@ +package mage.cards.q; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.TriggeredAbilityImpl; +import mage.abilities.common.SimpleEvasionAbility; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.effects.ContinuousRuleModifyingEffectImpl; +import mage.abilities.effects.common.DamageTargetEffect; +import mage.abilities.effects.common.combat.CantBeBlockedByCreaturesSourceEffect; +import mage.abilities.keyword.DeathtouchAbility; +import mage.abilities.keyword.HasteAbility; +import mage.abilities.keyword.VigilanceAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.*; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterCreaturePermanent; +import mage.filter.common.FilterPlaneswalkerPermanent; +import mage.filter.predicate.mageobject.PowerPredicate; +import mage.filter.predicate.permanent.ControllerIdPredicate; +import mage.game.Game; +import mage.game.events.DamageEvent; +import mage.game.events.DamagedEvent; +import mage.game.events.GameEvent; +import mage.game.permanent.Permanent; +import mage.players.Player; +import mage.target.TargetPermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class QuestingBeast extends CardImpl { + + private static final FilterCreaturePermanent filter + = new FilterCreaturePermanent("creatures with power 2 or less"); + + static { + filter.add(new PowerPredicate(ComparisonType.FEWER_THAN, 3)); + } + + public QuestingBeast(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{2}{G}{G}"); + + this.addSuperType(SuperType.LEGENDARY); + this.subtype.add(SubType.BEAST); + this.power = new MageInt(4); + this.toughness = new MageInt(4); + + // Vigilance + this.addAbility(VigilanceAbility.getInstance()); + + // Deathtouch + this.addAbility(DeathtouchAbility.getInstance()); + + // Haste + this.addAbility(HasteAbility.getInstance()); + + // Questing Beast can't be blocked by creatures with power 2 or less. + this.addAbility(new SimpleEvasionAbility(new CantBeBlockedByCreaturesSourceEffect(filter, Duration.WhileOnBattlefield))); + + // Combat damage that would be dealt by creatures you control can't be prevented. + this.addAbility(new SimpleStaticAbility(new QuestingBeastPreventionEffect())); + + // Whenever Questing Beast deals combat damage to an opponent, it deals that much damage to target planeswalker that player controls. + this.addAbility(new QuestingBeastTriggeredAbility()); + } + + private QuestingBeast(final QuestingBeast card) { + super(card); + } + + @Override + public QuestingBeast copy() { + return new QuestingBeast(this); + } +} + +class QuestingBeastPreventionEffect extends ContinuousRuleModifyingEffectImpl { + + QuestingBeastPreventionEffect() { + super(Duration.WhileOnBattlefield, Outcome.Benefit); + staticText = "Combat damage that would be dealt by creatures you control can't be prevented."; + } + + private QuestingBeastPreventionEffect(final QuestingBeastPreventionEffect effect) { + super(effect); + } + + @Override + public QuestingBeastPreventionEffect copy() { + return new QuestingBeastPreventionEffect(this); + } + + @Override + public boolean checksEventType(GameEvent event, Game game) { + return event.getType() == GameEvent.EventType.PREVENT_DAMAGE; + } + + @Override + public boolean applies(GameEvent event, Ability source, Game game) { + if (!((DamageEvent) event).isCombatDamage()) { + return false; + } + Permanent permanent = game.getPermanent(event.getSourceId()); + return permanent != null + && permanent.isCreature() + && permanent.isControlledBy(source.getControllerId()); + } +} + +class QuestingBeastTriggeredAbility extends TriggeredAbilityImpl { + + QuestingBeastTriggeredAbility() { + super(Zone.BATTLEFIELD, null, true); + } + + private QuestingBeastTriggeredAbility(final QuestingBeastTriggeredAbility ability) { + super(ability); + } + + @Override + public QuestingBeastTriggeredAbility copy() { + return new QuestingBeastTriggeredAbility(this); + } + + @Override + public boolean checkEventType(GameEvent event, Game game) { + return event.getType() == GameEvent.EventType.DAMAGED_PLAYER; + } + + @Override + public boolean checkTrigger(GameEvent event, Game game) { + Player opponent = game.getPlayer(event.getPlayerId()); + if (opponent == null + || !event.getSourceId().equals(this.getSourceId()) + || !opponent.hasOpponent(this.getControllerId(), game) + || !((DamagedEvent) event).isCombatDamage()) { + return false; + } + this.getEffects().clear(); + this.addEffect(new DamageTargetEffect(event.getAmount())); + FilterPermanent filter = new FilterPlaneswalkerPermanent("planeswalker " + opponent.getLogName() + " controls"); + filter.add(new ControllerIdPredicate(opponent.getId())); + this.getTargets().clear(); + this.addTarget(new TargetPermanent(filter)); + return true; + } + + @Override + public String getRule() { + return "Whenever {this} deals combat damage to an opponent, " + + "it deals that much damage to target planeswalker that player controls"; + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 1f624867de..8952a54148 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -83,6 +83,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Once Upon a Time", 169, Rarity.RARE, mage.cards.o.OnceUponATime.class)); cards.add(new SetCardInfo("Order of Midnight", 99, Rarity.UNCOMMON, mage.cards.o.OrderOfMidnight.class)); cards.add(new SetCardInfo("Piper of the Swarm", 100, Rarity.RARE, mage.cards.p.PiperOfTheSwarm.class)); + cards.add(new SetCardInfo("Questing Beast", 171, Rarity.MYTHIC, mage.cards.q.QuestingBeast.class)); cards.add(new SetCardInfo("Rankle, Master of Pranks", 101, Rarity.MYTHIC, mage.cards.r.RankleMasterOfPranks.class)); cards.add(new SetCardInfo("Return to Nature", 173, Rarity.COMMON, mage.cards.r.ReturnToNature.class)); cards.add(new SetCardInfo("Rosethorn Acolyte", 174, Rarity.COMMON, mage.cards.r.RosethornAcolyte.class)); From 17acd7064daf3670c75ebc1d3776e34d8851cbf8 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Tue, 10 Sep 2019 09:11:34 -0400 Subject: [PATCH 034/373] fixed Sevinne, the Chronoclasm error --- Mage.Sets/src/mage/cards/s/SevinneTheChronoclasm.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Mage.Sets/src/mage/cards/s/SevinneTheChronoclasm.java b/Mage.Sets/src/mage/cards/s/SevinneTheChronoclasm.java index 0c4600499d..79b6f7f918 100644 --- a/Mage.Sets/src/mage/cards/s/SevinneTheChronoclasm.java +++ b/Mage.Sets/src/mage/cards/s/SevinneTheChronoclasm.java @@ -54,7 +54,7 @@ public final class SevinneTheChronoclasm extends CardImpl { class SevinneTheChronoclasmTriggeredAbility extends SpellCastControllerTriggeredAbility { SevinneTheChronoclasmTriggeredAbility() { - super(Zone.BATTLEFIELD, null, StaticFilters.FILTER_SPELL_INSTANT_OR_SORCERY, false, true); + super(Zone.BATTLEFIELD, null, StaticFilters.FILTER_SPELL_INSTANT_OR_SORCERY, false, false); } private SevinneTheChronoclasmTriggeredAbility(final SevinneTheChronoclasmTriggeredAbility ability) { From 7da0ef80721e1bf00049fedd4487bc2466167b6c Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Tue, 10 Sep 2019 09:20:04 -0400 Subject: [PATCH 035/373] updated ELD spoiler --- Utils/mtg-cards-data.txt | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index 929cddaeb2..288e9a6f3b 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -36004,6 +36004,7 @@ Silverflame Ritual|Throne of Eldraine|30|C|{3}{W}|Sorcery|||Put a +1/+1 counter Animating Faerie|Throne of Eldraine|38|U|{2}{U}|Creature - Faerie|2|2|Flying| Bring to Life|Throne of Eldraine|38|U|{2}{U}|Sorcery - Adventure|2|2|Target noncreature artifact you control becomes a 0/0 artifact creature. Put four +1/+1 counters on it.| Corridor Monitor|Throne of Eldraine|41|C|{1}{U}|Artifact Creature - Construct|1|4|When Corridor Monitor enters the battlefield, untap target artifact or creature you control.| +Emry, Lurker of the Loch|Throne of Eldraine|43|R|{2}{U}|Legendary Creature - Merfolk Wizard|1|2|This spell costs {1} less to cast for each artifact you control.$When Emry, Lurker of the Loch enters the battlefield, put the top four cards of your library into your graveyard.${T}: Choose target artifact card in your graveyard. You may cast that card this turn.| Faerie Vandal|Throne of Eldraine|45|U|{1}{U}|Creature - Faerie Rogue|1|2|Flash$Flying$Whenever you draw your second card each turn, put a +1/+1 counter on Faerie Vandal.| Frogify|Throne of Eldraine|47|U|{1}{U}|Enchantment - Aura|||Enchant creature$Enchanted creature loses all abilities and is a blue Frog creature with base power and toughness 1/1.| Midnight Clock|Throne of Eldraine|54|R|{2}{U}|Artifact|||{T}: Add {U}.${2}{U}: Put an hour counter on Midnight Clock.$At the beginning of each upkeep, put an hour counter on Midnight Clock.$When the twelfth hour counter is put on Midnight Clock, shuffle your hand and graveyard into your library, then draw seven cards. Exile Midnight Clock.| @@ -36015,6 +36016,7 @@ Wishful Merfolk|Throne of Eldraine|73|C|{1}{U}|Creature - Merfolk|3|2|Defender${ Witching Well|Throne of Eldraine|74|C|{U}|Artifact|||When Witching Well enters the battlefield, scry 2.${3}{U}, Sacrifice Witching Well: Draw two cards.| Bake into a Pie|Throne of Eldraine|76|C|{2}{B}{B}|Instant|||Destroy target creature. Create a Food token.| Belle of the Brawl|Throne of Eldraine|78|U|{2}{B}|Creature - Human Knight|3|2|Menace$Whenever Belle of the Brawl attacks, other Knights you control get +1/+0 until end of turn.| +Clackbridge Troll|Throne of Eldraine|84|R|{3}{B}{B}|Creature - Troll|8|8|Trample, haste$When Clackbridge Troll enters the battlefield, target opponent creates three 0/1 white Goat creature tokens.$At the beginning of combat on your turn, any opponent may sacrifice a creature. If that player does, tap Clackbridge Troll, you gain 3 life, and you draw a card.| Eye Collector|Throne of Eldraine|86|C|{B}|Creature - Faerie|1|1|Flying$Whenever Eye Collector deals combat damage to a player, each player puts the top card of their library into their graveyard.| Foulmire Knight|Throne of Eldraine|90|U|{B}|Creature - Zombie Knight|1|1|Deathtouch| Profane Insight|Throne of Eldraine|90|U|{2}{B}|Instant - Adventure|1|1|You draw a card and you lose 1 life.| @@ -36034,14 +36036,16 @@ Blow Your House Down|Throne of Eldraine|114|C|{2}{R}|Sorcery|||Up to three targe Brimstone Trebuchet|Throne of Eldraine|116|C|{2}{R}|Artifact Creature - Wall|1|3|Defender, reach${T}: Brimstone Trebuchet deals 1 damage to each opponent.$Whenever a Knight enters the battlefield under your control, untap Brimstone Trebuchet.| Burning-Yard Trainer|Throne of Eldraine|117|U|{4}{R}|Creature - Human Knight|3|3|Trample, haste$When Burning-Yard Trainer enters the battlefield, another target Knight you control gets +2/+2 and gains trample and haste until end of turn.| Crystal Slipper|Throne of Eldraine|119|C|{1}{R}|Artifact - Equipment|||Equipped creature gets +1/+0 and has haste.$Equip {1}| -Embercleave|Throne of Eldraine|120|M|{4}{R}{R}|Legendary Artifact - Equipment|||Flash$This spell costs {1} less for each attacking creature you control.$When Embercleave enters the battlefield, attach it to target creature you control.$Equipped creature gets +1/+1 and has double strike and trample.$Equip {3}| +Embercleave|Throne of Eldraine|120|M|{4}{R}{R}|Legendary Artifact - Equipment|||Flash$This spell costs {1} less to cast for each attacking creature you control.$When Embercleave enters the battlefield, attach it to target creature you control.$Equipped creature gets +1/+1 and has double strike and trample.$Equip {3}| Embereth Paladin|Throne of Eldraine|121|C|{3}{R}|Creature - Human Knight|4|1|Haste$Adamant — If at least three red mana was spent to cast this spell, Embereth Paladin enters the battlefield with a +1/+1 counter on it.| Battle Display|Throne of Eldraine|122|U|{R}|Sorcery - Adventure|2|1|Destroy target artifact.| Embereth Shieldbreaker|Throne of Eldraine|122|U|{1}{R}|Creature - Human Knight|2|1|| Joust|Throne of Eldraine|129|U|{1}{R}|Sorcery|||Choose target creature you control and target creature you don't control. The creature you control gets +2/+1 until end of turn if it's a Knight. Then those creatures fight each other.| +Robber of the Rich|Throne of Eldraine|138|M|{1}{R}|Creature - Human Archer Rogue|2|2|Reach, haste$Whenever Robber of the Rich attacks, if defending player has more cards in hand than you, exile the top card of their library. During any turn you attacked with a Rogue, you may cast that card and you may spend mana as though it were mana of any color to cast that spell.| Slaying Fire|Throne of Eldraine|143|U|{2}{R}|Instant|||Slaying Fire deals 3 damage to any target.$Adamant — If at least three red mana was spent to cast this spell, it deals 4 damage instead.| Beanstalk Giant|Throne of Eldraine|149|U|{6}{G}|Creature - Giant|*|*|Beanstalk Giant's power and toughness are each equal to the number of lands you control.| Fertile Footsteps|Throne of Eldraine|149|U|{2}{G}|Sorcery - Adventure|*|*|Search your library for a basic land card, put it onto the battlefield, then shuffle your library.| +Feasting Troll King|Throne of Eldraine|152|R|{2}{G}{G}{G}{G}|Creature - Troll Noble|7|6|Vigilance, trample$When Feasting Troll King enters the battlefield, if you cast it from your hand, create three Food tokens.$Sacrifice three Foods: Return Feasting Troll King from your graveyard to the battlefield. Activate this ability only during your turn.| Flaxen Intruder|Throne of Eldraine|155|U|{G}|Creature - Human Berserker|1|2|Whenever Flaxen Intruder deals combat damage to a player, you may sacrifice it. When you do, destroy target artifact or enchantment.| Welcome Home|Throne of Eldraine|155|U|{5}{G}{G}|Sorcery - Adventure|1|2|Create three 2/2 green Bear creature tokens.| Gilded Goose|Throne of Eldraine|160|R|{G}|Creature - Bird|0|2|Flying$When Gilded Goose enters the battlefield, create a Food token.${1}{G}, {T}: Create a Food token.${T}, Sacrifice a Food: Add one mana of any color.| @@ -36057,6 +36061,7 @@ Wicked Wolf|Throne of Eldraine|181|R|{2}{G}{G}|Creature - Wolf|3|3|When Wicked W Wildwood Tracker|Throne of Eldraine|183|C|{G}|Creature - Elf Warrior|1|1|Whenever Wildwood Tracker attacks or blocks, if you control another non-Human creature, Wildwood Tracker gets +1/+1 until end of turn.| Garruk, Cursed Huntsman|Throne of Eldraine|191|M|{4}{B}{G}|Legendary Planeswalker - Garruk|5|0: Create two 2/2 black and green Wolf creature tokens with "When this creature dies, put a loyalty counter on each Garruk you control."$−3: Destroy target creature. Draw a card.$−6: You get an emblem with "Creatures you control get +3/+3 and have trample."| Inspiring Veteran|Throne of Eldraine|194|U|{R}{W}|Creature - Human Knight|2|2|Other Knights you control get +1/+1.| +Lochmere Serpent|Throne of Eldraine|195|R|{4}{U}{B}|Creature - Serpent|7|7|Flash${U}, Sacrifice an Island: Lochmere Serpent can't be blocked this turn.${B}, Sacrifice a Swamp: You gain 1 life and draw a card.${U}{B}: Exile five target cards from an opponent's graveyard. Return Lochmere Serpent from your graveyard to your hand. Activate this ability only any time you could cast a sorcery.| Maraleaf Pixie|Throne of Eldraine|196|U|{G}{U}|Creature - Faerie|2|2|Flying${T}: Add {G} or {U}.| Oko, Thief of Crowns|Throne of Eldraine|197|M|{1}{G}{U}|Legendary Planeswalker - Oko|4|+2: Create a Food token.$+1: Target artifact or creature loses all abilities and becomes a green Elk creature with base power and toughness 3/3.$−5: Exchange control of target artifact or creature you control and target creature an opponent controls with power 3 or less.| The Royal Scions|Throne of Eldraine|199|M|{1}{U}{R}|Legendary Planeswalker - Will Rowan|5|+1: Draw a card, then discard a card.$+1: Target creature gets +2/+0 and gains first strike until end of turn.$−8: Draw four cards. When you do, The Royal Scions deals damage to any target equal to the number of cards in your hand.| @@ -36070,6 +36075,7 @@ Enchanted Carriage|Throne of Eldraine|218|U|{5}|Artifact - Vehicle|4|4|When Ench Golden Egg|Throne of Eldraine|220|C|{2}|Artifact - Food|||When Golden Egg enters the battlefield, draw a card.${1}, {T}, Sacrifice Golden Egg: Add one mana of any color.${2}, {T}, Sacrifice Golden Egg: You gain 3 life.| Heraldic Banner|Throne of Eldraine|222|U|{3}|Artifact|||As Heraldic Banner enters the battlefield, choose a color.$Creatures you control of the chosen color get +1/+0.${T}: Add one mana of the chosen color.| Jousting Dummy|Throne of Eldraine|224|C|{2}|Artifact Creature - Scarecrow Knight|2|1|{3}: Jousting Dummy gets +1/+0 until end of turn.| +Witch's Oven|Throne of Eldraine|237|U|{1}|Artifact|||{T}, Sacrifice a creature: Create a Food token. If the sacrificed creature's toughness was 4 or greater, create two Food tokens instead.| Tournament Grounds|Throne of Eldraine|248|U||Land|||{T}: Add {C}.${T}: Add {R}, {W}, or {B}. Spend this mana only to cast a Knight or Equipment spell.| Witch's Cottage|Throne of Eldraine|249|C||Land - Swamp|||({T}: Add {B}.)$Witch's Cottage enters the battlefield tapped unless you control three or more other Swamps.$When Witch's Cottage enters the battlefield untapped, you may put target creature card from your graveyard on top of your library.| Rowan, Fearless Sparkmage|Throne of Eldraine|304|M|{3}{R}{R}|Legendary Planeswalker - Rowan|5|+1: Up to one target creature gets +3/+0 and gains first strike until end of turn.$−2: Rowan, Fearless Sparkmage deals 1 damage to each of up to two target creatures. Those creatures can't block this turn.$−9: Gain control of all creatures until end of turn. Untap them. They gain haste until end of turn.| From 236b393a31665a6b4c1313bcdb671a4cf03e4e58 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Tue, 10 Sep 2019 17:19:05 -0400 Subject: [PATCH 036/373] updated ELD spoiler --- Utils/mtg-cards-data.txt | 11 ++++++++++- 1 file changed, 10 insertions(+), 1 deletion(-) diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index 288e9a6f3b..b2eee97cf4 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -36001,12 +36001,16 @@ Chop Down|Throne of Eldraine|14|R|{2}{W}|Instant - Adventure|1|2|Destroy target Giant Killer|Throne of Eldraine|14|R|{W}|Creature - Human Peasant|1|2|{1}{W}, {T}: Tap target creature.| Shining Armor|Throne of Eldraine|29|C|{1}{W}|Artifact - Equipment|||Flash$When Shining Armor enters the battlefield, attach it to target Knight you control.$Equipped creature gets +0/+2 and has vigilance.$Equip {3}| Silverflame Ritual|Throne of Eldraine|30|C|{3}{W}|Sorcery|||Put a +1/+1 counter on each creature you control.$Adamant — If at least three white mana was spent to cast this spell, creatures you control gain vigilance until end of turn.| +Venerable Knight|Throne of Eldraine|35|U|{W}|Creature - Human Knight|2|1|When Venerable Knight dies, put a +1/+1 counter on target Knight you control.| +Worthy Knight|Throne of Eldraine|36|R|{1}{W}|Creature - Human Knight|2|2|Whenever you cast a Knight spell, create a 1/1 white Human creature token.| Animating Faerie|Throne of Eldraine|38|U|{2}{U}|Creature - Faerie|2|2|Flying| Bring to Life|Throne of Eldraine|38|U|{2}{U}|Sorcery - Adventure|2|2|Target noncreature artifact you control becomes a 0/0 artifact creature. Put four +1/+1 counters on it.| Corridor Monitor|Throne of Eldraine|41|C|{1}{U}|Artifact Creature - Construct|1|4|When Corridor Monitor enters the battlefield, untap target artifact or creature you control.| Emry, Lurker of the Loch|Throne of Eldraine|43|R|{2}{U}|Legendary Creature - Merfolk Wizard|1|2|This spell costs {1} less to cast for each artifact you control.$When Emry, Lurker of the Loch enters the battlefield, put the top four cards of your library into your graveyard.${T}: Choose target artifact card in your graveyard. You may cast that card this turn.| Faerie Vandal|Throne of Eldraine|45|U|{1}{U}|Creature - Faerie Rogue|1|2|Flash$Flying$Whenever you draw your second card each turn, put a +1/+1 counter on Faerie Vandal.| Frogify|Throne of Eldraine|47|U|{1}{U}|Enchantment - Aura|||Enchant creature$Enchanted creature loses all abilities and is a blue Frog creature with base power and toughness 1/1.| +Hypnotic Sprite|Throne of Eldraine|49|U|{U}{U}|Creature - Faerie|2|1|Flying| +Mesmeric Glare|Throne of Eldraine|49|U|{2}{U}|Instant - Adventure|2|1|Counter target spell with converted mana cost 3 or less.| Midnight Clock|Throne of Eldraine|54|R|{2}{U}|Artifact|||{T}: Add {U}.${2}{U}: Put an hour counter on Midnight Clock.$At the beginning of each upkeep, put an hour counter on Midnight Clock.$When the twelfth hour counter is put on Midnight Clock, shuffle your hand and graveyard into your library, then draw seven cards. Exile Midnight Clock.| Mystical Dispute|Throne of Eldraine|58|U|{2}{U}|Instant|||This spell costs {2} less to cast if it targets a blue spell.$Counter target spell unless its controller pays {3}.| Run Away Together|Throne of Eldraine|62|C|{1}{U}|Instant|||Choose two target creatures controlled by different players. Return those creatures to their owners' hands.| @@ -36016,7 +36020,7 @@ Wishful Merfolk|Throne of Eldraine|73|C|{1}{U}|Creature - Merfolk|3|2|Defender${ Witching Well|Throne of Eldraine|74|C|{U}|Artifact|||When Witching Well enters the battlefield, scry 2.${3}{U}, Sacrifice Witching Well: Draw two cards.| Bake into a Pie|Throne of Eldraine|76|C|{2}{B}{B}|Instant|||Destroy target creature. Create a Food token.| Belle of the Brawl|Throne of Eldraine|78|U|{2}{B}|Creature - Human Knight|3|2|Menace$Whenever Belle of the Brawl attacks, other Knights you control get +1/+0 until end of turn.| -Clackbridge Troll|Throne of Eldraine|84|R|{3}{B}{B}|Creature - Troll|8|8|Trample, haste$When Clackbridge Troll enters the battlefield, target opponent creates three 0/1 white Goat creature tokens.$At the beginning of combat on your turn, any opponent may sacrifice a creature. If that player does, tap Clackbridge Troll, you gain 3 life, and you draw a card.| +Clackbridge Troll|Throne of Eldraine|84|R|{3}{B}{B}|Creature - Troll|8|8|Trample, haste$When Clackbridge Troll enters the battlefield, target opponent creates three 0/1 white Goat creature tokens.$At the beginning of combat on your turn, any opponent may sacrifice a creature. If a player does, tap Clackbridge Troll, you gain 3 life, and you draw a card.| Eye Collector|Throne of Eldraine|86|C|{B}|Creature - Faerie|1|1|Flying$Whenever Eye Collector deals combat damage to a player, each player puts the top card of their library into their graveyard.| Foulmire Knight|Throne of Eldraine|90|U|{B}|Creature - Zombie Knight|1|1|Deathtouch| Profane Insight|Throne of Eldraine|90|U|{2}{B}|Instant - Adventure|1|1|You draw a card and you lose 1 life.| @@ -36043,6 +36047,7 @@ Embereth Shieldbreaker|Throne of Eldraine|122|U|{1}{R}|Creature - Human Knight|2 Joust|Throne of Eldraine|129|U|{1}{R}|Sorcery|||Choose target creature you control and target creature you don't control. The creature you control gets +2/+1 until end of turn if it's a Knight. Then those creatures fight each other.| Robber of the Rich|Throne of Eldraine|138|M|{1}{R}|Creature - Human Archer Rogue|2|2|Reach, haste$Whenever Robber of the Rich attacks, if defending player has more cards in hand than you, exile the top card of their library. During any turn you attacked with a Rogue, you may cast that card and you may spend mana as though it were mana of any color to cast that spell.| Slaying Fire|Throne of Eldraine|143|U|{2}{R}|Instant|||Slaying Fire deals 3 damage to any target.$Adamant — If at least three red mana was spent to cast this spell, it deals 4 damage instead.| +Weaselback Redcap|Throne of Eldraine|148|C|{R}|Creature - Goblin Knight|1|1|{1}{R}: Weaselback Redcap gets +2/+0 until end of turn.| Beanstalk Giant|Throne of Eldraine|149|U|{6}{G}|Creature - Giant|*|*|Beanstalk Giant's power and toughness are each equal to the number of lands you control.| Fertile Footsteps|Throne of Eldraine|149|U|{2}{G}|Sorcery - Adventure|*|*|Search your library for a basic land card, put it onto the battlefield, then shuffle your library.| Feasting Troll King|Throne of Eldraine|152|R|{2}{G}{G}{G}{G}|Creature - Troll Noble|7|6|Vigilance, trample$When Feasting Troll King enters the battlefield, if you cast it from your hand, create three Food tokens.$Sacrifice three Foods: Return Feasting Troll King from your graveyard to the battlefield. Activate this ability only during your turn.| @@ -36058,7 +36063,9 @@ Return to Nature|Throne of Eldraine|173|C|{1}{G}|Instant|||Choose one —$• De Rosethorn Acolyte|Throne of Eldraine|174|C|{2}{G}|Creature - Elf Druid|2|3|{T}: Add one mana of any color.| Seasonal Ritual|Throne of Eldraine|174|C|{G}|Sorcery - Adventure|2|3|Add one mana of any color.| Wicked Wolf|Throne of Eldraine|181|R|{2}{G}{G}|Creature - Wolf|3|3|When Wicked Wolf enters the battlefield, it fights up to one target creature you don't control.$Sacrifice a Food: Put a +1/+1 counter on Wicked Wolf. It gains indestructible until end of turn. Tap it.| +Wildborn Preserver|Throne of Eldraine|182|R|{1}{G}|Creature - Elf Archer|2|2|Flash$Reach$Whenever another non-Human creature enters the battlefield under your control, you may pay {X}. When you do, put X +1/+1 counters on Wildborn Preserver.| Wildwood Tracker|Throne of Eldraine|183|C|{G}|Creature - Elf Warrior|1|1|Whenever Wildwood Tracker attacks or blocks, if you control another non-Human creature, Wildwood Tracker gets +1/+1 until end of turn.| +Doom Foretold|Throne of Eldraine|187|R|{2}{W}{B}|Enchantment|||At the beginning of each player's upkeep, that player sacrifices a nonland, nontoken permanent. If that player can't, they discard a card, they lose 2 life, you draw a card, you gain 2 life, you create a 2/2 white Knight creature token with vigilance, then you sacrifice Doom Foretold.| Garruk, Cursed Huntsman|Throne of Eldraine|191|M|{4}{B}{G}|Legendary Planeswalker - Garruk|5|0: Create two 2/2 black and green Wolf creature tokens with "When this creature dies, put a loyalty counter on each Garruk you control."$−3: Destroy target creature. Draw a card.$−6: You get an emblem with "Creatures you control get +3/+3 and have trample."| Inspiring Veteran|Throne of Eldraine|194|U|{R}{W}|Creature - Human Knight|2|2|Other Knights you control get +1/+1.| Lochmere Serpent|Throne of Eldraine|195|R|{4}{U}{B}|Creature - Serpent|7|7|Flash${U}, Sacrifice an Island: Lochmere Serpent can't be blocked this turn.${B}, Sacrifice a Swamp: You gain 1 life and draw a card.${U}{B}: Exile five target cards from an opponent's graveyard. Return Lochmere Serpent from your graveyard to your hand. Activate this ability only any time you could cast a sorcery.| @@ -36071,6 +36078,8 @@ Steelclaw Lance|Throne of Eldraine|202|U|{B}{R}|Artifact - Equipment|||Equipped Wintermoor Commander|Throne of Eldraine|205|U|{W}{B}|Creature - Human Knight|2|*|Deathtouch$Wintermoor Commander's toughness is equal to the number of Knights you control.$Whenever Wintermoor Commander attacks, another target Knight you control gains indestructible until end of turn.| Arcanist's Owl|Throne of Eldraine|206|U|{W/U}{W/U}{W/U}{W/U}|Artifact Creature - Bird|3|3|Flying$When Arcanist's Owl enters the battlefield, look at the top four cards of your library. You may reveal an artifact or enchantment card from among them and put it into your hand. Put the rest on the bottom of your library in a random order.| Fireborn Knight|Throne of Eldraine|210|U|{R/W}{R/W}{R/W}{R/W}|Creature - Human Knight|2|3|Double strike${R/W}{R/W}{R/W}{R/W}: Fireborn Knight gets +1/+1 until end of turn.| +Bring Back|Throne of Eldraine|212|U|{G/W}{G/W}{G/W}{G/W}|Sorcery - Adventure|2|2|Create two 1/1 white Human creature tokens.| +Oakhame Ranger|Throne of Eldraine|212|U|{G/W}{G/W}{G/W}{G/W}|Creature - Elf Knight|2|2|{T}: Creatures you control get +1/+1 until end of turn.| Enchanted Carriage|Throne of Eldraine|218|U|{5}|Artifact - Vehicle|4|4|When Enchanted Carriage enters the battlefield, create two 1/1 white Mouse creature tokens.$Crew 2| Golden Egg|Throne of Eldraine|220|C|{2}|Artifact - Food|||When Golden Egg enters the battlefield, draw a card.${1}, {T}, Sacrifice Golden Egg: Add one mana of any color.${2}, {T}, Sacrifice Golden Egg: You gain 3 life.| Heraldic Banner|Throne of Eldraine|222|U|{3}|Artifact|||As Heraldic Banner enters the battlefield, choose a color.$Creatures you control of the chosen color get +1/+0.${T}: Add one mana of the chosen color.| From 71fd51ec2b746d35486448e5b3967ab2281e1f10 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Tue, 10 Sep 2019 17:20:17 -0400 Subject: [PATCH 037/373] Implemented Weaselback Redcap --- .../src/mage/cards/w/WeaselbackRedcap.java | 42 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 43 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/w/WeaselbackRedcap.java diff --git a/Mage.Sets/src/mage/cards/w/WeaselbackRedcap.java b/Mage.Sets/src/mage/cards/w/WeaselbackRedcap.java new file mode 100644 index 0000000000..3526c27452 --- /dev/null +++ b/Mage.Sets/src/mage/cards/w/WeaselbackRedcap.java @@ -0,0 +1,42 @@ +package mage.cards.w; + +import mage.MageInt; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.costs.mana.ManaCostsImpl; +import mage.abilities.effects.common.continuous.BoostSourceEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class WeaselbackRedcap extends CardImpl { + + public WeaselbackRedcap(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{R}"); + + this.subtype.add(SubType.GOBLIN); + this.subtype.add(SubType.KNIGHT); + this.power = new MageInt(1); + this.toughness = new MageInt(1); + + // {1}{R}: Weaselback Redcap gets +2/+0 until end of turn. + this.addAbility(new SimpleActivatedAbility( + new BoostSourceEffect(2, 0, Duration.EndOfTurn), new ManaCostsImpl("{1}{R}") + )); + } + + private WeaselbackRedcap(final WeaselbackRedcap card) { + super(card); + } + + @Override + public WeaselbackRedcap copy() { + return new WeaselbackRedcap(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 8952a54148..0face6239d 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -112,6 +112,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Tome of Legends", 332, Rarity.RARE, mage.cards.t.TomeOfLegends.class)); cards.add(new SetCardInfo("Tournament Grounds", 248, Rarity.UNCOMMON, mage.cards.t.TournamentGrounds.class)); cards.add(new SetCardInfo("Turn into a Pumpkin", 69, Rarity.UNCOMMON, mage.cards.t.TurnIntoAPumpkin.class)); + cards.add(new SetCardInfo("Weaselback Redcap", 148, Rarity.COMMON, mage.cards.w.WeaselbackRedcap.class)); cards.add(new SetCardInfo("Wicked Guardian", 109, Rarity.COMMON, mage.cards.w.WickedGuardian.class)); cards.add(new SetCardInfo("Wicked Wolf", 181, Rarity.RARE, mage.cards.w.WickedWolf.class)); cards.add(new SetCardInfo("Wildwood Tracker", 183, Rarity.COMMON, mage.cards.w.WildwoodTracker.class)); From 10daaa390619b05ae8e158089f42c5a6a171fa2c Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Tue, 10 Sep 2019 17:23:51 -0400 Subject: [PATCH 038/373] Implemented Worthy Knight --- Mage.Sets/src/mage/cards/w/WorthyKnight.java | 49 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 50 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/w/WorthyKnight.java diff --git a/Mage.Sets/src/mage/cards/w/WorthyKnight.java b/Mage.Sets/src/mage/cards/w/WorthyKnight.java new file mode 100644 index 0000000000..d3521c5897 --- /dev/null +++ b/Mage.Sets/src/mage/cards/w/WorthyKnight.java @@ -0,0 +1,49 @@ +package mage.cards.w; + +import mage.MageInt; +import mage.abilities.common.SpellCastControllerTriggeredAbility; +import mage.abilities.effects.common.CreateTokenEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.filter.FilterSpell; +import mage.filter.predicate.mageobject.SubtypePredicate; +import mage.game.permanent.token.HumanToken; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class WorthyKnight extends CardImpl { + + private static final FilterSpell filter = new FilterSpell("a Knight spell"); + + static { + filter.add(new SubtypePredicate(SubType.HUMAN)); + } + + public WorthyKnight(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{1}{W}"); + + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.KNIGHT); + this.power = new MageInt(2); + this.toughness = new MageInt(2); + + // Whenever you cast a Knight spell, create a 1/1 white Human creature token. + this.addAbility(new SpellCastControllerTriggeredAbility( + new CreateTokenEffect(new HumanToken()), filter, false + )); + } + + private WorthyKnight(final WorthyKnight card) { + super(card); + } + + @Override + public WorthyKnight copy() { + return new WorthyKnight(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 0face6239d..c939d1b31c 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -124,6 +124,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Witch's Vengeance", 111, Rarity.RARE, mage.cards.w.WitchsVengeance.class)); cards.add(new SetCardInfo("Witching Well", 74, Rarity.COMMON, mage.cards.w.WitchingWell.class)); cards.add(new SetCardInfo("Workshop Elders", 318, Rarity.RARE, mage.cards.w.WorkshopElders.class)); + cards.add(new SetCardInfo("Worthy Knight", 36, Rarity.RARE, mage.cards.w.WorthyKnight.class)); // This is here to prevent the incomplete adventure implementation from causing problems and will be removed cards.removeIf(setCardInfo -> AdventureCard.class.isAssignableFrom(setCardInfo.getCardClass())); From e1136743e01da75e8f5cdcd3fbcca55684aa8abd Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Tue, 10 Sep 2019 17:31:27 -0400 Subject: [PATCH 039/373] Implemented Oakhame Ranger --- Mage.Sets/src/mage/cards/o/OakhameRanger.java | 48 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 49 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/o/OakhameRanger.java diff --git a/Mage.Sets/src/mage/cards/o/OakhameRanger.java b/Mage.Sets/src/mage/cards/o/OakhameRanger.java new file mode 100644 index 0000000000..ce7ff7ddd5 --- /dev/null +++ b/Mage.Sets/src/mage/cards/o/OakhameRanger.java @@ -0,0 +1,48 @@ +package mage.cards.o; + +import mage.MageInt; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.costs.common.TapSourceCost; +import mage.abilities.effects.common.CreateTokenEffect; +import mage.abilities.effects.common.continuous.BoostControlledEffect; +import mage.cards.AdventureCard; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; +import mage.game.permanent.token.HumanToken; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class OakhameRanger extends AdventureCard { + + public OakhameRanger(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, new CardType[]{CardType.SORCERY}, "{G/W}{G/W}{G/W}{G/W}", "Bring Back", "{G/W}{G/W}{G/W}{G/W}"); + + this.subtype.add(SubType.ELF); + this.subtype.add(SubType.KNIGHT); + this.power = new MageInt(2); + this.toughness = new MageInt(2); + + // {T}: Creatures you control get +1/+1 until end of turn. + this.addAbility(new SimpleActivatedAbility( + new BoostControlledEffect(1, 1, Duration.EndOfTurn), new TapSourceCost() + )); + + // Bring Back + // Create two 1/1 white Human creature tokens. + this.getAdventureSpellAbility().addEffect(new CreateTokenEffect(new HumanToken(), 2)); + } + + private OakhameRanger(final OakhameRanger card) { + super(card); + } + + @Override + public OakhameRanger copy() { + return new OakhameRanger(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index c939d1b31c..fab6084785 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -77,6 +77,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Maraleaf Pixie", 196, Rarity.UNCOMMON, mage.cards.m.MaraleafPixie.class)); cards.add(new SetCardInfo("Midnight Clock", 54, Rarity.RARE, mage.cards.m.MidnightClock.class)); cards.add(new SetCardInfo("Mystical Dispute", 58, Rarity.UNCOMMON, mage.cards.m.MysticalDispute.class)); + cards.add(new SetCardInfo("Oakhame Ranger", 212, Rarity.UNCOMMON, mage.cards.o.OakhameRanger.class)); cards.add(new SetCardInfo("Oko's Accomplices", 310, Rarity.COMMON, mage.cards.o.OkosAccomplices.class)); cards.add(new SetCardInfo("Oko's Hospitality", 312, Rarity.RARE, mage.cards.o.OkosHospitality.class)); cards.add(new SetCardInfo("Oko, Thief of Crowns", 197, Rarity.MYTHIC, mage.cards.o.OkoThiefOfCrowns.class)); From 8855ba9efda2c9a1dc94967b22ae9a33845ab2ae Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Tue, 10 Sep 2019 17:48:52 -0400 Subject: [PATCH 040/373] Implemented Hypnotic Sprite --- .../src/mage/cards/h/HypnoticSprite.java | 52 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 53 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/h/HypnoticSprite.java diff --git a/Mage.Sets/src/mage/cards/h/HypnoticSprite.java b/Mage.Sets/src/mage/cards/h/HypnoticSprite.java new file mode 100644 index 0000000000..40868c5afb --- /dev/null +++ b/Mage.Sets/src/mage/cards/h/HypnoticSprite.java @@ -0,0 +1,52 @@ +package mage.cards.h; + +import mage.MageInt; +import mage.abilities.effects.common.CounterTargetEffect; +import mage.abilities.keyword.FlyingAbility; +import mage.cards.AdventureCard; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.ComparisonType; +import mage.constants.SubType; +import mage.filter.FilterSpell; +import mage.filter.predicate.mageobject.ConvertedManaCostPredicate; +import mage.target.TargetSpell; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class HypnoticSprite extends AdventureCard { + + private static final FilterSpell filter = new FilterSpell("spell with converted mana cost 3 or less"); + + static { + filter.add(new ConvertedManaCostPredicate(ComparisonType.FEWER_THAN, 4)); + } + + public HypnoticSprite(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, new CardType[]{CardType.INSTANT}, "{U}{U}", "Mesmeric Glare", "{2}{U}"); + + this.subtype.add(SubType.FAERIE); + this.power = new MageInt(2); + this.toughness = new MageInt(1); + + // Flying + this.addAbility(FlyingAbility.getInstance()); + + // Mesmeric Glare + // Counter target spell with converted mana cost 3 or less. + this.getAdventureSpellAbility().addEffect(new CounterTargetEffect()); + this.getAdventureSpellAbility().addTarget(new TargetSpell(filter)); + } + + private HypnoticSprite(final HypnoticSprite card) { + super(card); + } + + @Override + public HypnoticSprite copy() { + return new HypnoticSprite(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index fab6084785..b0cea07dec 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -66,6 +66,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Gluttonous Troll", 327, Rarity.RARE, mage.cards.g.GluttonousTroll.class)); cards.add(new SetCardInfo("Golden Egg", 220, Rarity.COMMON, mage.cards.g.GoldenEgg.class)); cards.add(new SetCardInfo("Heraldic Banner", 222, Rarity.UNCOMMON, mage.cards.h.HeraldicBanner.class)); + cards.add(new SetCardInfo("Hypnotic Sprite", 49, Rarity.UNCOMMON, mage.cards.h.HypnoticSprite.class)); cards.add(new SetCardInfo("Inspiring Veteran", 194, Rarity.UNCOMMON, mage.cards.i.InspiringVeteran.class)); cards.add(new SetCardInfo("Joust", 129, Rarity.UNCOMMON, mage.cards.j.Joust.class)); cards.add(new SetCardInfo("Jousting Dummy", 224, Rarity.COMMON, mage.cards.j.JoustingDummy.class)); From 44946b3e026a8c6dca0d2919227577e2ba054904 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Tue, 10 Sep 2019 17:52:50 -0400 Subject: [PATCH 041/373] Implemented Venerable Knight --- .../src/mage/cards/v/VenerableKnight.java | 47 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 48 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/v/VenerableKnight.java diff --git a/Mage.Sets/src/mage/cards/v/VenerableKnight.java b/Mage.Sets/src/mage/cards/v/VenerableKnight.java new file mode 100644 index 0000000000..dc14f248f3 --- /dev/null +++ b/Mage.Sets/src/mage/cards/v/VenerableKnight.java @@ -0,0 +1,47 @@ +package mage.cards.v; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.DiesTriggeredAbility; +import mage.abilities.effects.common.counter.AddCountersTargetEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.counters.CounterType; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterControlledPermanent; +import mage.target.TargetPermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class VenerableKnight extends CardImpl { + + private static final FilterPermanent filter = new FilterControlledPermanent(SubType.KNIGHT); + + public VenerableKnight(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{W}"); + + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.KNIGHT); + this.power = new MageInt(2); + this.toughness = new MageInt(1); + + // When Venerable Knight dies, put a +1/+1 counter on target Knight you control. + Ability ability = new DiesTriggeredAbility(new AddCountersTargetEffect(CounterType.P1P1.createInstance())); + ability.addTarget(new TargetPermanent(filter)); + this.addAbility(ability); + } + + private VenerableKnight(final VenerableKnight card) { + super(card); + } + + @Override + public VenerableKnight copy() { + return new VenerableKnight(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index b0cea07dec..23714b1556 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -114,6 +114,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Tome of Legends", 332, Rarity.RARE, mage.cards.t.TomeOfLegends.class)); cards.add(new SetCardInfo("Tournament Grounds", 248, Rarity.UNCOMMON, mage.cards.t.TournamentGrounds.class)); cards.add(new SetCardInfo("Turn into a Pumpkin", 69, Rarity.UNCOMMON, mage.cards.t.TurnIntoAPumpkin.class)); + cards.add(new SetCardInfo("Venerable Knight", 35, Rarity.UNCOMMON, mage.cards.v.VenerableKnight.class)); cards.add(new SetCardInfo("Weaselback Redcap", 148, Rarity.COMMON, mage.cards.w.WeaselbackRedcap.class)); cards.add(new SetCardInfo("Wicked Guardian", 109, Rarity.COMMON, mage.cards.w.WickedGuardian.class)); cards.add(new SetCardInfo("Wicked Wolf", 181, Rarity.RARE, mage.cards.w.WickedWolf.class)); From 274dd79c290f8801c4f44f39817500d0cfb805c1 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Tue, 10 Sep 2019 18:12:09 -0400 Subject: [PATCH 042/373] Implemented Oko, the Trickster --- .../src/mage/cards/o/OkoTheTrickster.java | 97 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 98 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/o/OkoTheTrickster.java diff --git a/Mage.Sets/src/mage/cards/o/OkoTheTrickster.java b/Mage.Sets/src/mage/cards/o/OkoTheTrickster.java new file mode 100644 index 0000000000..fba45954e1 --- /dev/null +++ b/Mage.Sets/src/mage/cards/o/OkoTheTrickster.java @@ -0,0 +1,97 @@ +package mage.cards.o; + +import mage.abilities.Ability; +import mage.abilities.LoyaltyAbility; +import mage.abilities.common.PlaneswalkerEntersWithLoyaltyCountersAbility; +import mage.abilities.effects.OneShotEffect; +import mage.abilities.effects.common.PreventAllDamageToSourceEffect; +import mage.abilities.effects.common.continuous.GainAbilityAllEffect; +import mage.abilities.effects.common.continuous.SetPowerToughnessAllEffect; +import mage.abilities.effects.common.counter.AddCountersTargetEffect; +import mage.abilities.keyword.TrampleAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.*; +import mage.counters.CounterType; +import mage.filter.StaticFilters; +import mage.game.Game; +import mage.game.permanent.Permanent; +import mage.target.common.TargetControlledCreaturePermanent; +import mage.util.functions.EmptyApplyToPermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class OkoTheTrickster extends CardImpl { + + public OkoTheTrickster(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.PLANESWALKER}, "{4}{G}{U}"); + + this.addSuperType(SuperType.LEGENDARY); + this.subtype.add(SubType.OKO); + this.addAbility(new PlaneswalkerEntersWithLoyaltyCountersAbility(4)); + + // +1: Put two +1/+1 counters on up to one target creature you control. + Ability ability = new LoyaltyAbility( + new AddCountersTargetEffect(CounterType.P1P1.createInstance(2)), 1 + ); + ability.addTarget(new TargetControlledCreaturePermanent(0, 1)); + this.addAbility(ability); + + // 0: Until end of turn, Oko, the Trickster becomes a copy of target creature you control. Prevent all damage that would be dealt to him this turn. + ability = new LoyaltyAbility(new OkoTheTricksterCopyEffect(), 0); + ability.addEffect(new PreventAllDamageToSourceEffect(Duration.EndOfTurn) + .setText("Prevent all damage that would be dealt to him this turn.")); + ability.addTarget(new TargetControlledCreaturePermanent()); + this.addAbility(ability); + + // −7: Until end of turn, each creature you control has base power and toughness 10/10 and gains trample. + ability = new LoyaltyAbility(new SetPowerToughnessAllEffect( + 10, 10, Duration.EndOfTurn, StaticFilters.FILTER_CONTROLLED_CREATURE, true + ).setText("Until end of turn, each creature you control has base power and toughness 10/10"), -7); + ability.addEffect(new GainAbilityAllEffect( + TrampleAbility.getInstance(), Duration.EndOfTurn, + StaticFilters.FILTER_CONTROLLED_CREATURE + ).setText("and gains trample")); + this.addAbility(ability); + } + + private OkoTheTrickster(final OkoTheTrickster card) { + super(card); + } + + @Override + public OkoTheTrickster copy() { + return new OkoTheTrickster(this); + } +} + +class OkoTheTricksterCopyEffect extends OneShotEffect { + + OkoTheTricksterCopyEffect() { + super(Outcome.Copy); + this.staticText = "Until end of turn, {this} becomes a copy of target creature you control."; + } + + private OkoTheTricksterCopyEffect(final OkoTheTricksterCopyEffect effect) { + super(effect); + } + + @Override + public OkoTheTricksterCopyEffect copy() { + return new OkoTheTricksterCopyEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + Permanent sourcePermanent = game.getPermanent(source.getSourceId()); + Permanent copyFromPermanent = game.getPermanent(getTargetPointer().getFirst(game, source)); + if (sourcePermanent == null || copyFromPermanent == null) { + return false; + } + game.copyPermanent(Duration.EndOfTurn, copyFromPermanent, sourcePermanent.getId(), source, new EmptyApplyToPermanent()); + return true; + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 23714b1556..80aeceacd2 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -82,6 +82,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Oko's Accomplices", 310, Rarity.COMMON, mage.cards.o.OkosAccomplices.class)); cards.add(new SetCardInfo("Oko's Hospitality", 312, Rarity.RARE, mage.cards.o.OkosHospitality.class)); cards.add(new SetCardInfo("Oko, Thief of Crowns", 197, Rarity.MYTHIC, mage.cards.o.OkoThiefOfCrowns.class)); + cards.add(new SetCardInfo("Oko, the Trickster", 309, Rarity.MYTHIC, mage.cards.o.OkoTheTrickster.class)); cards.add(new SetCardInfo("Once Upon a Time", 169, Rarity.RARE, mage.cards.o.OnceUponATime.class)); cards.add(new SetCardInfo("Order of Midnight", 99, Rarity.UNCOMMON, mage.cards.o.OrderOfMidnight.class)); cards.add(new SetCardInfo("Piper of the Swarm", 100, Rarity.RARE, mage.cards.p.PiperOfTheSwarm.class)); From 21d8570097a00fcb748ec1ccb22111917bfcb690 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Tue, 10 Sep 2019 18:41:37 -0400 Subject: [PATCH 043/373] updated ELD spoiler --- Utils/mtg-cards-data.txt | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index b2eee97cf4..24abe59b1d 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -36046,6 +36046,7 @@ Battle Display|Throne of Eldraine|122|U|{R}|Sorcery - Adventure|2|1|Destroy targ Embereth Shieldbreaker|Throne of Eldraine|122|U|{1}{R}|Creature - Human Knight|2|1|| Joust|Throne of Eldraine|129|U|{1}{R}|Sorcery|||Choose target creature you control and target creature you don't control. The creature you control gets +2/+1 until end of turn if it's a Knight. Then those creatures fight each other.| Robber of the Rich|Throne of Eldraine|138|M|{1}{R}|Creature - Human Archer Rogue|2|2|Reach, haste$Whenever Robber of the Rich attacks, if defending player has more cards in hand than you, exile the top card of their library. During any turn you attacked with a Rogue, you may cast that card and you may spend mana as though it were mana of any color to cast that spell.| +Skullknocker Ogre|Throne of Eldraine|142|U|{3}{R}|Creature - Ogre|4|3|Whenever Skullknocker Ogre deals damage to an opponent, that player discards a card at random. If the player does, they draw a card.| Slaying Fire|Throne of Eldraine|143|U|{2}{R}|Instant|||Slaying Fire deals 3 damage to any target.$Adamant — If at least three red mana was spent to cast this spell, it deals 4 damage instead.| Weaselback Redcap|Throne of Eldraine|148|C|{R}|Creature - Goblin Knight|1|1|{1}{R}: Weaselback Redcap gets +2/+0 until end of turn.| Beanstalk Giant|Throne of Eldraine|149|U|{6}{G}|Creature - Giant|*|*|Beanstalk Giant's power and toughness are each equal to the number of lands you control.| @@ -36071,6 +36072,7 @@ Inspiring Veteran|Throne of Eldraine|194|U|{R}{W}|Creature - Human Knight|2|2|Ot Lochmere Serpent|Throne of Eldraine|195|R|{4}{U}{B}|Creature - Serpent|7|7|Flash${U}, Sacrifice an Island: Lochmere Serpent can't be blocked this turn.${B}, Sacrifice a Swamp: You gain 1 life and draw a card.${U}{B}: Exile five target cards from an opponent's graveyard. Return Lochmere Serpent from your graveyard to your hand. Activate this ability only any time you could cast a sorcery.| Maraleaf Pixie|Throne of Eldraine|196|U|{G}{U}|Creature - Faerie|2|2|Flying${T}: Add {G} or {U}.| Oko, Thief of Crowns|Throne of Eldraine|197|M|{1}{G}{U}|Legendary Planeswalker - Oko|4|+2: Create a Food token.$+1: Target artifact or creature loses all abilities and becomes a green Elk creature with base power and toughness 3/3.$−5: Exchange control of target artifact or creature you control and target creature an opponent controls with power 3 or less.| +Outlaws' Merriment|Throne of Eldraine|198|M|{1}{R}{W}{W}|Enchantment|||At the beginning of your upkeep, choose one at random. Create a red and white creature token with those characteristics.$• 3/1 Human Warrior with trample and haste.$• 2/1 Human Cleric with lifelink and haste.$• 1/2 Human Rogue with haste and "When this creature enters the battlefield, it deals 1 damage to any target."| The Royal Scions|Throne of Eldraine|199|M|{1}{U}{R}|Legendary Planeswalker - Will Rowan|5|+1: Draw a card, then discard a card.$+1: Target creature gets +2/+0 and gains first strike until end of turn.$−8: Draw four cards. When you do, The Royal Scions deals damage to any target equal to the number of cards in your hand.| Savvy Hunter|Throne of Eldraine|200|U|{1}{B}{G}|Creature - Human Warrior|3|3|Whenever Savvy Hunter attacks or blocks, create a Food token.$Sacrifice two Foods: Draw a card.| Shinechaser|Throne of Eldraine|201|U|{1}{W}{U}|Creature - Faerie|1|1|Flying, vigilance$Shinechaser gets +1/+1 as long as you control an artifact.$Shinechaser gets +1/+1 as long as you control an enchantment.| @@ -36084,9 +36086,11 @@ Enchanted Carriage|Throne of Eldraine|218|U|{5}|Artifact - Vehicle|4|4|When Ench Golden Egg|Throne of Eldraine|220|C|{2}|Artifact - Food|||When Golden Egg enters the battlefield, draw a card.${1}, {T}, Sacrifice Golden Egg: Add one mana of any color.${2}, {T}, Sacrifice Golden Egg: You gain 3 life.| Heraldic Banner|Throne of Eldraine|222|U|{3}|Artifact|||As Heraldic Banner enters the battlefield, choose a color.$Creatures you control of the chosen color get +1/+0.${T}: Add one mana of the chosen color.| Jousting Dummy|Throne of Eldraine|224|C|{2}|Artifact Creature - Scarecrow Knight|2|1|{3}: Jousting Dummy gets +1/+0 until end of turn.| +Roving Keep|Throne of Eldraine|228|C|{7}|Artifact Creature - Wall|5|7|Defender${7}: Roving Keep gets +2/+0 and gains trample until end of turn. It can attack this turn as though it didn't have defender.| Witch's Oven|Throne of Eldraine|237|U|{1}|Artifact|||{T}, Sacrifice a creature: Create a Food token. If the sacrificed creature's toughness was 4 or greater, create two Food tokens instead.| Tournament Grounds|Throne of Eldraine|248|U||Land|||{T}: Add {C}.${T}: Add {R}, {W}, or {B}. Spend this mana only to cast a Knight or Equipment spell.| Witch's Cottage|Throne of Eldraine|249|C||Land - Swamp|||({T}: Add {B}.)$Witch's Cottage enters the battlefield tapped unless you control three or more other Swamps.$When Witch's Cottage enters the battlefield untapped, you may put target creature card from your graveyard on top of your library.| +Kenrith, the Returned King|Throne of Eldraine|303|M|{4}{W}|Legendary Creature - Human Noble|5|5|{R}: All creatures gain trample and haste until end of turn.${1}{G}: Put a +1/+1 counter on target creature.${2}{W}: Target player gains 5 life.${3}{U}: Target player draws a card.${4}{B}: Put target creature card from a graveyard onto the battlefield under its owner's control.| Rowan, Fearless Sparkmage|Throne of Eldraine|304|M|{3}{R}{R}|Legendary Planeswalker - Rowan|5|+1: Up to one target creature gets +3/+0 and gains first strike until end of turn.$−2: Rowan, Fearless Sparkmage deals 1 damage to each of up to two target creatures. Those creatures can't block this turn.$−9: Gain control of all creatures until end of turn. Untap them. They gain haste until end of turn.| Garrison Griffin|Throne of Eldraine|305|C|{2}{W}|Creature - Griffin|2|2|Flying$Whenever Garrison Griffin attacks, target Knight you control gains flying until end of turn.| Rowan's Battleguard|Throne of Eldraine|306|U|{3}{R}|Creature - Human Knight|3|3|First strike$As long as you control a Rowan planeswalker, Rowan's Battleguard gets +3/+0.| @@ -36117,3 +36121,4 @@ Syr Gwyn, Hero of Ashvale|Throne of Eldraine|330|M|{3}{R}{W}{B}|Legendary Creatu Arcane Signet|Throne of Eldraine|331|C|{2}|Artifact|||{T}: Add one mana of any color in your commander's color identity.| Tome of Legends|Throne of Eldraine|332|R|{2}|Artifact|||Tome of Legends enters the battlefield with a page counter on it.$Whenever your commander enters the battlefield or attacks, put a page counter on Tome of Legends.${1}, {T}, Remove a page counter from Tome of Legends: Draw a card.| Command Tower|Throne of Eldraine|333|C||Land|||{T}: Add one mana of any color in your commander's color identity.| +Charming Prince|Throne of Eldraine|335|R|{1}{W}|Creature - Human Noble|2|2|When Charming Prince enters the battlefield, choose one —$• Scry 2.$• You gain 3 life.$• Exile another target creature you own. Return it to the battlefield under your control at the beginning of the next end step.| From ed1929f0e616960198d8d64d389d8b81f608fc68 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Tue, 10 Sep 2019 20:37:34 -0400 Subject: [PATCH 044/373] Implemented Wildborn Preserver --- .../src/mage/cards/w/WildbornPreserver.java | 141 ++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 142 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/w/WildbornPreserver.java diff --git a/Mage.Sets/src/mage/cards/w/WildbornPreserver.java b/Mage.Sets/src/mage/cards/w/WildbornPreserver.java new file mode 100644 index 0000000000..b6429ccdda --- /dev/null +++ b/Mage.Sets/src/mage/cards/w/WildbornPreserver.java @@ -0,0 +1,141 @@ +package mage.cards.w; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.DelayedTriggeredAbility; +import mage.abilities.common.EntersBattlefieldControlledTriggeredAbility; +import mage.abilities.costs.mana.GenericManaCost; +import mage.abilities.costs.mana.ManaCosts; +import mage.abilities.costs.mana.ManaCostsImpl; +import mage.abilities.effects.OneShotEffect; +import mage.abilities.effects.common.counter.AddCountersSourceEffect; +import mage.abilities.keyword.FlashAbility; +import mage.abilities.keyword.ReachAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.Outcome; +import mage.constants.SubType; +import mage.counters.CounterType; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterCreaturePermanent; +import mage.filter.predicate.Predicates; +import mage.filter.predicate.mageobject.SubtypePredicate; +import mage.filter.predicate.permanent.AnotherPredicate; +import mage.game.Game; +import mage.game.events.GameEvent; +import mage.players.Player; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class WildbornPreserver extends CardImpl { + + private static final FilterPermanent filter = new FilterCreaturePermanent("another non-Human creature"); + + static { + filter.add(AnotherPredicate.instance); + filter.add(Predicates.not(new SubtypePredicate(SubType.HUMAN))); + } + + public WildbornPreserver(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{1}{G}"); + + this.subtype.add(SubType.ELF); + this.subtype.add(SubType.ARCHER); + this.power = new MageInt(2); + this.toughness = new MageInt(2); + + // Flash + this.addAbility(FlashAbility.getInstance()); + + // Reach + this.addAbility(ReachAbility.getInstance()); + + // Whenever another non-Human creature enters the battlefield under your control, you may pay {X}. When you do, put X +1/+1 counters on Wildborn Preserver. + this.addAbility(new EntersBattlefieldControlledTriggeredAbility( + new WildbornPreserverCreateReflexiveTriggerEffect(), filter + )); + } + + private WildbornPreserver(final WildbornPreserver card) { + super(card); + } + + @Override + public WildbornPreserver copy() { + return new WildbornPreserver(this); + } +} + +class WildbornPreserverCreateReflexiveTriggerEffect extends OneShotEffect { + + WildbornPreserverCreateReflexiveTriggerEffect() { + super(Outcome.Benefit); + } + + private WildbornPreserverCreateReflexiveTriggerEffect(final WildbornPreserverCreateReflexiveTriggerEffect effect) { + super(effect); + staticText = "you may pay {X}. When you do, put X +1/+1 counters on {this}"; + } + + @Override + public WildbornPreserverCreateReflexiveTriggerEffect copy() { + return new WildbornPreserverCreateReflexiveTriggerEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + Player player = game.getPlayer(source.getControllerId()); + ManaCosts cost = new ManaCostsImpl("{X}"); + if (player == null) { + return false; + } + if (!player.chooseUse(outcome, "Pay " + cost.getText() + "?", source, game)) { + return false; + } + int costX = player.announceXMana(0, Integer.MAX_VALUE, "Announce the value for {X}", game, source); + cost.add(new GenericManaCost(costX)); + if (!cost.pay(source, game, source.getSourceId(), source.getControllerId(), false, null)) { + return false; + } + game.addDelayedTriggeredAbility(new WildbornPreserverReflexiveTriggeredAbility(costX), source); + game.fireEvent(GameEvent.getEvent(GameEvent.EventType.OPTION_USED, source.getOriginalId(), source.getSourceId(), source.getControllerId(), 0)); + return true; + } +} + +class WildbornPreserverReflexiveTriggeredAbility extends DelayedTriggeredAbility { + + WildbornPreserverReflexiveTriggeredAbility(int counters) { + super(new AddCountersSourceEffect(CounterType.P1P1.createInstance(counters)), Duration.OneUse, true); + } + + private WildbornPreserverReflexiveTriggeredAbility(final WildbornPreserverReflexiveTriggeredAbility ability) { + super(ability); + } + + @Override + public WildbornPreserverReflexiveTriggeredAbility copy() { + return new WildbornPreserverReflexiveTriggeredAbility(this); + } + + @Override + public boolean checkEventType(GameEvent event, Game game) { + return event.getType() == GameEvent.EventType.OPTION_USED; + } + + @Override + public boolean checkTrigger(GameEvent event, Game game) { + return event.getPlayerId().equals(this.getControllerId()) + && event.getSourceId().equals(this.getSourceId()); + } + + @Override + public String getRule() { + return "When you do, put X +1/+1 counters on {this}."; + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 80aeceacd2..974f6bf30f 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -119,6 +119,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Weaselback Redcap", 148, Rarity.COMMON, mage.cards.w.WeaselbackRedcap.class)); cards.add(new SetCardInfo("Wicked Guardian", 109, Rarity.COMMON, mage.cards.w.WickedGuardian.class)); cards.add(new SetCardInfo("Wicked Wolf", 181, Rarity.RARE, mage.cards.w.WickedWolf.class)); + cards.add(new SetCardInfo("Wildborn Preserver", 182, Rarity.RARE, mage.cards.w.WildbornPreserver.class)); cards.add(new SetCardInfo("Wildwood Tracker", 183, Rarity.COMMON, mage.cards.w.WildwoodTracker.class)); cards.add(new SetCardInfo("Wind-Scarred Crag", 308, Rarity.COMMON, mage.cards.w.WindScarredCrag.class)); cards.add(new SetCardInfo("Wintermoor Commander", 205, Rarity.UNCOMMON, mage.cards.w.WintermoorCommander.class)); From 31730c5352e7ffa9093702196b4707687ae468c4 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Tue, 10 Sep 2019 20:46:33 -0400 Subject: [PATCH 045/373] Implemented Roving Keep --- Mage.Sets/src/mage/cards/h/HexplateGolem.java | 14 ++--- Mage.Sets/src/mage/cards/r/RovingKeep.java | 57 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 3 files changed, 64 insertions(+), 8 deletions(-) create mode 100644 Mage.Sets/src/mage/cards/r/RovingKeep.java diff --git a/Mage.Sets/src/mage/cards/h/HexplateGolem.java b/Mage.Sets/src/mage/cards/h/HexplateGolem.java index 34b9e6a5c8..ff6ec9671b 100644 --- a/Mage.Sets/src/mage/cards/h/HexplateGolem.java +++ b/Mage.Sets/src/mage/cards/h/HexplateGolem.java @@ -1,28 +1,27 @@ - - package mage.cards.h; -import java.util.UUID; import mage.MageInt; import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.CardType; import mage.constants.SubType; +import java.util.UUID; + /** - * * @author Loki */ public final class HexplateGolem extends CardImpl { - public HexplateGolem (UUID ownerId, CardSetInfo setInfo) { - super(ownerId,setInfo,new CardType[]{CardType.ARTIFACT,CardType.CREATURE},"{7}"); + public HexplateGolem(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT, CardType.CREATURE}, "{7}"); + this.subtype.add(SubType.GOLEM); this.power = new MageInt(5); this.toughness = new MageInt(7); } - public HexplateGolem (final HexplateGolem card) { + private HexplateGolem(final HexplateGolem card) { super(card); } @@ -30,5 +29,4 @@ public final class HexplateGolem extends CardImpl { public HexplateGolem copy() { return new HexplateGolem(this); } - } diff --git a/Mage.Sets/src/mage/cards/r/RovingKeep.java b/Mage.Sets/src/mage/cards/r/RovingKeep.java new file mode 100644 index 0000000000..05f9af99ad --- /dev/null +++ b/Mage.Sets/src/mage/cards/r/RovingKeep.java @@ -0,0 +1,57 @@ +package mage.cards.r; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.costs.mana.GenericManaCost; +import mage.abilities.effects.common.combat.CanAttackAsThoughItDidntHaveDefenderSourceEffect; +import mage.abilities.effects.common.continuous.BoostSourceEffect; +import mage.abilities.effects.common.continuous.GainAbilitySourceEffect; +import mage.abilities.keyword.DefenderAbility; +import mage.abilities.keyword.TrampleAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class RovingKeep extends CardImpl { + + public RovingKeep(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT, CardType.CREATURE}, "{7}"); + + this.subtype.add(SubType.WALL); + this.power = new MageInt(5); + this.toughness = new MageInt(7); + + // Defender + this.addAbility(DefenderAbility.getInstance()); + + // {7}: Roving Keep gets +2/+0 and gains trample until end of turn. It can attack this turn as though it didn't have defender. + Ability ability = new SimpleActivatedAbility( + new BoostSourceEffect(2, 0, Duration.EndOfTurn) + .setText("{this} gets +2/+0"), new GenericManaCost(7) + ); + ability.addEffect(new GainAbilitySourceEffect( + TrampleAbility.getInstance(), Duration.EndOfTurn + ).setText("and gains trample until end of turn.")); + ability.addEffect(new CanAttackAsThoughItDidntHaveDefenderSourceEffect(Duration.EndOfTurn) + .setText("It can attack this turn as though it didn't have defender")); + this.addAbility(ability); + } + + private RovingKeep(final RovingKeep card) { + super(card); + } + + @Override + public RovingKeep copy() { + return new RovingKeep(this); + } +} +// sexy hexy is back, baby! diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 974f6bf30f..b59cbbad27 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -90,6 +90,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Rankle, Master of Pranks", 101, Rarity.MYTHIC, mage.cards.r.RankleMasterOfPranks.class)); cards.add(new SetCardInfo("Return to Nature", 173, Rarity.COMMON, mage.cards.r.ReturnToNature.class)); cards.add(new SetCardInfo("Rosethorn Acolyte", 174, Rarity.COMMON, mage.cards.r.RosethornAcolyte.class)); + cards.add(new SetCardInfo("Roving Keep", 228, Rarity.COMMON, mage.cards.r.RovingKeep.class)); cards.add(new SetCardInfo("Rowan's Battleguard", 306, Rarity.UNCOMMON, mage.cards.r.RowansBattleguard.class)); cards.add(new SetCardInfo("Rowan's Stalwarts", 307, Rarity.RARE, mage.cards.r.RowansStalwarts.class)); cards.add(new SetCardInfo("Rowan, Fearless Sparkmage", 304, Rarity.MYTHIC, mage.cards.r.RowanFearlessSparkmage.class)); From efffc5355214b128a8cfa5f6902df2960e1efe88 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Tue, 10 Sep 2019 20:53:43 -0400 Subject: [PATCH 046/373] Implemented Feasting Troll King --- .../src/mage/cards/f/FeastingTrollKing.java | 71 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 72 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/f/FeastingTrollKing.java diff --git a/Mage.Sets/src/mage/cards/f/FeastingTrollKing.java b/Mage.Sets/src/mage/cards/f/FeastingTrollKing.java new file mode 100644 index 0000000000..7ceaa6025c --- /dev/null +++ b/Mage.Sets/src/mage/cards/f/FeastingTrollKing.java @@ -0,0 +1,71 @@ +package mage.cards.f; + +import mage.MageInt; +import mage.abilities.common.ActivateIfConditionActivatedAbility; +import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.condition.common.CastFromHandSourceCondition; +import mage.abilities.condition.common.MyTurnCondition; +import mage.abilities.costs.common.SacrificeTargetCost; +import mage.abilities.decorator.ConditionalInterveningIfTriggeredAbility; +import mage.abilities.effects.common.CreateTokenEffect; +import mage.abilities.effects.common.ReturnSourceFromGraveyardToHandEffect; +import mage.abilities.keyword.TrampleAbility; +import mage.abilities.keyword.VigilanceAbility; +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.permanent.token.FoodToken; +import mage.target.common.TargetControlledPermanent; +import mage.watchers.common.CastFromHandWatcher; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class FeastingTrollKing extends CardImpl { + + private static final FilterControlledPermanent filter = new FilterControlledPermanent(SubType.FOOD, "Foods"); + + public FeastingTrollKing(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{2}{G}{G}{G}{G}"); + + this.subtype.add(SubType.TROLL); + this.subtype.add(SubType.NOBLE); + this.power = new MageInt(7); + this.toughness = new MageInt(6); + + // Vigilance + this.addAbility(VigilanceAbility.getInstance()); + + // Trample + this.addAbility(TrampleAbility.getInstance()); + + // When Feasting Troll King enters the battlefield, if you cast it from your hand, create three Food tokens. + this.addAbility(new ConditionalInterveningIfTriggeredAbility( + new EntersBattlefieldTriggeredAbility(new CreateTokenEffect(new FoodToken(), 3)), + CastFromHandSourceCondition.instance, "When {this} enters the battlefield, " + + "if you cast it from your hand, create three Food tokens." + ), new CastFromHandWatcher()); + + // Sacrifice three Foods: Return Feasting Troll King from your graveyard to the battlefield. Activate this ability only during your turn. + this.addAbility(new ActivateIfConditionActivatedAbility( + Zone.BATTLEFIELD, + new ReturnSourceFromGraveyardToHandEffect(), + new SacrificeTargetCost(new TargetControlledPermanent(3, filter)), + MyTurnCondition.instance + )); + } + + private FeastingTrollKing(final FeastingTrollKing card) { + super(card); + } + + @Override + public FeastingTrollKing copy() { + return new FeastingTrollKing(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index b59cbbad27..c947fc7809 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -55,6 +55,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Faerie Formation", 316, Rarity.RARE, mage.cards.f.FaerieFormation.class)); cards.add(new SetCardInfo("Faerie Guidemother", 11, Rarity.COMMON, mage.cards.f.FaerieGuidemother.class)); cards.add(new SetCardInfo("Faerie Vandal", 45, Rarity.UNCOMMON, mage.cards.f.FaerieVandal.class)); + cards.add(new SetCardInfo("Feasting Troll King", 152, Rarity.RARE, mage.cards.f.FeastingTrollKing.class)); cards.add(new SetCardInfo("Fireborn Knight", 210, Rarity.UNCOMMON, mage.cards.f.FirebornKnight.class)); cards.add(new SetCardInfo("Flaxen Intruder", 155, Rarity.UNCOMMON, mage.cards.f.FlaxenIntruder.class)); cards.add(new SetCardInfo("Foulmire Knight", 90, Rarity.UNCOMMON, mage.cards.f.FoulmireKnight.class)); From d7d376cf06b5a60a9d92d7a10824c35a6a8866ee Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Tue, 10 Sep 2019 21:12:28 -0400 Subject: [PATCH 047/373] Implemented Witch's Oven --- Mage.Sets/src/mage/cards/w/WitchsOven.java | 87 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 88 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/w/WitchsOven.java diff --git a/Mage.Sets/src/mage/cards/w/WitchsOven.java b/Mage.Sets/src/mage/cards/w/WitchsOven.java new file mode 100644 index 0000000000..aa1d4807d8 --- /dev/null +++ b/Mage.Sets/src/mage/cards/w/WitchsOven.java @@ -0,0 +1,87 @@ +package mage.cards.w; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.costs.common.SacrificeTargetCost; +import mage.abilities.costs.common.TapSourceCost; +import mage.abilities.effects.Effect; +import mage.abilities.effects.OneShotEffect; +import mage.abilities.effects.common.CreateTokenEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Outcome; +import mage.filter.StaticFilters; +import mage.game.Game; +import mage.game.permanent.Permanent; +import mage.game.permanent.token.FoodToken; +import mage.target.common.TargetControlledCreaturePermanent; + +import java.util.Collection; +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class WitchsOven extends CardImpl { + + public WitchsOven(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT}, "{1}"); + + // {T}, Sacrifice a creature: Create a Food token. If the sacrificed creature's toughness was 4 or greater, create two Food tokens instead. + Ability ability = new SimpleActivatedAbility(new WitchsOvenEffect(), new TapSourceCost()); + ability.addCost(new SacrificeTargetCost( + new TargetControlledCreaturePermanent(StaticFilters.FILTER_CONTROLLED_CREATURE_SHORT_TEXT) + )); + this.addAbility(ability); + } + + private WitchsOven(final WitchsOven card) { + super(card); + } + + @Override + public WitchsOven copy() { + return new WitchsOven(this); + } +} + +class WitchsOvenEffect extends OneShotEffect { + + private static final Effect effect1 = new CreateTokenEffect(new FoodToken(), 1); + private static final Effect effect2 = new CreateTokenEffect(new FoodToken(), 2); + + WitchsOvenEffect() { + super(Outcome.Benefit); + staticText = "Create a Food token. If the sacrificed creature's toughness " + + "was 4 or greater, create two Food tokens instead"; + } + + private WitchsOvenEffect(final WitchsOvenEffect effect) { + super(effect); + } + + @Override + public WitchsOvenEffect copy() { + return new WitchsOvenEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + boolean big = source + .getCosts() + .stream() + .filter(SacrificeTargetCost.class::isInstance) + .map(SacrificeTargetCost.class::cast) + .map(SacrificeTargetCost::getPermanents) + .flatMap(Collection::stream) + .map(Permanent::getToughness) + .mapToInt(MageInt::getValue) + .anyMatch(i -> i > 3); + if (big) { + return effect2.apply(game, source); + } + return effect1.apply(game, source); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index c947fc7809..703a64688c 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -128,6 +128,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Wishclaw Talisman", 110, Rarity.RARE, mage.cards.w.WishclawTalisman.class)); cards.add(new SetCardInfo("Wishful Merfolk", 73, Rarity.COMMON, mage.cards.w.WishfulMerfolk.class)); cards.add(new SetCardInfo("Witch's Cottage", 249, Rarity.COMMON, mage.cards.w.WitchsCottage.class)); + cards.add(new SetCardInfo("Witch's Oven", 237, Rarity.UNCOMMON, mage.cards.w.WitchsOven.class)); cards.add(new SetCardInfo("Witch's Vengeance", 111, Rarity.RARE, mage.cards.w.WitchsVengeance.class)); cards.add(new SetCardInfo("Witching Well", 74, Rarity.COMMON, mage.cards.w.WitchingWell.class)); cards.add(new SetCardInfo("Workshop Elders", 318, Rarity.RARE, mage.cards.w.WorkshopElders.class)); From 53b918d9ed85f8c5602009a480e5ef339778599f Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Tue, 10 Sep 2019 21:35:47 -0400 Subject: [PATCH 048/373] Implemented Kenrith, the Returned King --- .../mage/cards/k/KenrithTheReturnedKing.java | 114 ++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 115 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/k/KenrithTheReturnedKing.java diff --git a/Mage.Sets/src/mage/cards/k/KenrithTheReturnedKing.java b/Mage.Sets/src/mage/cards/k/KenrithTheReturnedKing.java new file mode 100644 index 0000000000..3c22dcbf21 --- /dev/null +++ b/Mage.Sets/src/mage/cards/k/KenrithTheReturnedKing.java @@ -0,0 +1,114 @@ +package mage.cards.k; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.costs.mana.ManaCostsImpl; +import mage.abilities.effects.OneShotEffect; +import mage.abilities.effects.common.DrawCardTargetEffect; +import mage.abilities.effects.common.GainLifeTargetEffect; +import mage.abilities.effects.common.continuous.GainAbilityAllEffect; +import mage.abilities.effects.common.counter.AddCountersTargetEffect; +import mage.abilities.keyword.HasteAbility; +import mage.abilities.keyword.TrampleAbility; +import mage.cards.Card; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.*; +import mage.counters.CounterType; +import mage.filter.StaticFilters; +import mage.game.Game; +import mage.players.Player; +import mage.target.TargetPlayer; +import mage.target.common.TargetCardInGraveyard; +import mage.target.common.TargetCreaturePermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class KenrithTheReturnedKing extends CardImpl { + + public KenrithTheReturnedKing(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{4}{W}"); + + this.addSuperType(SuperType.LEGENDARY); + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.NOBLE); + this.power = new MageInt(5); + this.toughness = new MageInt(5); + + // {R}: All creatures gain trample and haste until end of turn. + Ability ability = new SimpleActivatedAbility(new GainAbilityAllEffect( + TrampleAbility.getInstance(), Duration.EndOfTurn, + StaticFilters.FILTER_PERMANENT_CREATURE + ).setText("all creatures gain trample"), new ManaCostsImpl("{R}")); + ability.addEffect(new GainAbilityAllEffect( + HasteAbility.getInstance(), Duration.EndOfTurn, + StaticFilters.FILTER_PERMANENT_CREATURE + ).setText("and haste until end of turn")); + this.addAbility(ability); + + // {1}{G}: Put a +1/+1 counter on target creature. + ability = new SimpleActivatedAbility( + new AddCountersTargetEffect(CounterType.P1P1.createInstance()), new ManaCostsImpl("{1}{G}") + ); + ability.addTarget(new TargetCreaturePermanent()); + this.addAbility(ability); + + // {2}{W}: Target player gains 5 life. + ability = new SimpleActivatedAbility(new GainLifeTargetEffect(5), new ManaCostsImpl("{2}{W}")); + ability.addTarget(new TargetPlayer()); + this.addAbility(ability); + + // {3}{U}: Target player draws a card. + ability = new SimpleActivatedAbility(new DrawCardTargetEffect(1), new ManaCostsImpl("{3}{U}")); + ability.addTarget(new TargetPlayer()); + this.addAbility(ability); + + // {4}{B}: Put target creature card from a graveyard onto the battlefield under its owner's control. + ability = new SimpleActivatedAbility(new GainLifeTargetEffect(5), new ManaCostsImpl("{4}{B}")); + ability.addTarget(new TargetCardInGraveyard(StaticFilters.FILTER_CARD_CREATURE)); + this.addAbility(ability); + } + + private KenrithTheReturnedKing(final KenrithTheReturnedKing card) { + super(card); + } + + @Override + public KenrithTheReturnedKing copy() { + return new KenrithTheReturnedKing(this); + } +} + +class KenrithTheReturnedKingEffect extends OneShotEffect { + + KenrithTheReturnedKingEffect() { + super(Outcome.Benefit); + staticText = "put target creature card from a graveyard onto the battlefield under its owner's control"; + } + + private KenrithTheReturnedKingEffect(final KenrithTheReturnedKingEffect effect) { + super(effect); + } + + @Override + public KenrithTheReturnedKingEffect copy() { + return new KenrithTheReturnedKingEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + Card card = game.getCard(source.getFirstTarget()); + if (card == null) { + return false; + } + Player player = game.getPlayer(card.getOwnerId()); + if (player == null) { + return false; + } + return player.moveCards(card, Zone.BATTLEFIELD, source, game); + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 703a64688c..ce3602dcb3 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -72,6 +72,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Joust", 129, Rarity.UNCOMMON, mage.cards.j.Joust.class)); cards.add(new SetCardInfo("Jousting Dummy", 224, Rarity.COMMON, mage.cards.j.JoustingDummy.class)); cards.add(new SetCardInfo("Keeper of Fables", 163, Rarity.UNCOMMON, mage.cards.k.KeeperOfFables.class)); + cards.add(new SetCardInfo("Kenrith, the Returned King", 303, Rarity.MYTHIC, mage.cards.k.KenrithTheReturnedKing.class)); cards.add(new SetCardInfo("Knights' Charge", 328, Rarity.RARE, mage.cards.k.KnightsCharge.class)); cards.add(new SetCardInfo("Korvold, Fae-Cursed King", 329, Rarity.MYTHIC, mage.cards.k.KorvoldFaeCursedKing.class)); cards.add(new SetCardInfo("Lovestruck Beast", 165, Rarity.RARE, mage.cards.l.LovestruckBeast.class)); From 4474e8650ffd352f10cf86d4c1652a3dc97ca20c Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Tue, 10 Sep 2019 21:42:37 -0400 Subject: [PATCH 049/373] Implemented Claim the Firstborn --- .../src/mage/cards/c/ClaimTheFirstborn.java | 51 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + Utils/mtg-cards-data.txt | 1 + 3 files changed, 53 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/c/ClaimTheFirstborn.java diff --git a/Mage.Sets/src/mage/cards/c/ClaimTheFirstborn.java b/Mage.Sets/src/mage/cards/c/ClaimTheFirstborn.java new file mode 100644 index 0000000000..8d328a6427 --- /dev/null +++ b/Mage.Sets/src/mage/cards/c/ClaimTheFirstborn.java @@ -0,0 +1,51 @@ +package mage.cards.c; + +import mage.abilities.effects.common.UntapTargetEffect; +import mage.abilities.effects.common.continuous.GainAbilityTargetEffect; +import mage.abilities.effects.common.continuous.GainControlTargetEffect; +import mage.abilities.keyword.HasteAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.ComparisonType; +import mage.constants.Duration; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterCreaturePermanent; +import mage.filter.predicate.mageobject.ConvertedManaCostPredicate; +import mage.target.TargetPermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class ClaimTheFirstborn extends CardImpl { + + private static final FilterPermanent filter + = new FilterCreaturePermanent("creature with converted mana cost 3 or less"); + + static { + filter.add(new ConvertedManaCostPredicate(ComparisonType.FEWER_THAN, 4)); + } + + public ClaimTheFirstborn(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.SORCERY}, "{R}"); + + // Gain control of target creature with converted mana cost 3 or less until end of turn. Untap that creature. It gains haste until end of turn. + this.getSpellAbility().addEffect(new GainControlTargetEffect(Duration.EndOfTurn)); + this.getSpellAbility().addEffect(new UntapTargetEffect() + .setText("Untap that creature")); + this.getSpellAbility().addEffect(new GainAbilityTargetEffect(HasteAbility.getInstance(), Duration.EndOfTurn) + .setText("It gains haste until end of turn.")); + this.getSpellAbility().addTarget(new TargetPermanent(filter)); + } + + private ClaimTheFirstborn(final ClaimTheFirstborn card) { + super(card); + } + + @Override + public ClaimTheFirstborn copy() { + return new ClaimTheFirstborn(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index ce3602dcb3..9147dc0166 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -43,6 +43,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Burning-Yard Trainer", 117, Rarity.UNCOMMON, mage.cards.b.BurningYardTrainer.class)); cards.add(new SetCardInfo("Chittering Witch", 319, Rarity.RARE, mage.cards.c.ChitteringWitch.class)); cards.add(new SetCardInfo("Chulane, Teller of Tales", 326, Rarity.MYTHIC, mage.cards.c.ChulaneTellerOfTales.class)); + cards.add(new SetCardInfo("Claim the Firstborn", 118, Rarity.UNCOMMON, mage.cards.c.ClaimTheFirstborn.class)); cards.add(new SetCardInfo("Command Tower", 333, Rarity.COMMON, mage.cards.c.CommandTower.class)); cards.add(new SetCardInfo("Corridor Monitor", 41, Rarity.COMMON, mage.cards.c.CorridorMonitor.class)); cards.add(new SetCardInfo("Crystal Slipper", 119, Rarity.COMMON, mage.cards.c.CrystalSlipper.class)); diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index 24abe59b1d..950e42004b 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -36039,6 +36039,7 @@ Witch's Vengeance|Throne of Eldraine|111|R|{1}{B}{B}|Sorcery|||Creatures of the Blow Your House Down|Throne of Eldraine|114|C|{2}{R}|Sorcery|||Up to three target creatures can't block this turn. Destroy any of them that are Walls.| Brimstone Trebuchet|Throne of Eldraine|116|C|{2}{R}|Artifact Creature - Wall|1|3|Defender, reach${T}: Brimstone Trebuchet deals 1 damage to each opponent.$Whenever a Knight enters the battlefield under your control, untap Brimstone Trebuchet.| Burning-Yard Trainer|Throne of Eldraine|117|U|{4}{R}|Creature - Human Knight|3|3|Trample, haste$When Burning-Yard Trainer enters the battlefield, another target Knight you control gets +2/+2 and gains trample and haste until end of turn.| +Claim the Firstborn|Throne of Eldraine|118|U|{R}|Sorcery|||Gain control of target creature with converted mana cost 3 or less until end of turn. Untap that creature. It gains haste until end of turn.| Crystal Slipper|Throne of Eldraine|119|C|{1}{R}|Artifact - Equipment|||Equipped creature gets +1/+0 and has haste.$Equip {1}| Embercleave|Throne of Eldraine|120|M|{4}{R}{R}|Legendary Artifact - Equipment|||Flash$This spell costs {1} less to cast for each attacking creature you control.$When Embercleave enters the battlefield, attach it to target creature you control.$Equipped creature gets +1/+1 and has double strike and trample.$Equip {3}| Embereth Paladin|Throne of Eldraine|121|C|{3}{R}|Creature - Human Knight|4|1|Haste$Adamant — If at least three red mana was spent to cast this spell, Embereth Paladin enters the battlefield with a +1/+1 counter on it.| From a2f463a37ff9dd0c9b1e7e529d452fdb4368065a Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 11 Sep 2019 09:56:02 -0400 Subject: [PATCH 050/373] updated ELD spoiler --- Mage.Sets/src/mage/cards/t/TheRoyalScions.java | 8 ++++++-- Utils/mtg-cards-data.txt | 5 ++++- 2 files changed, 10 insertions(+), 3 deletions(-) diff --git a/Mage.Sets/src/mage/cards/t/TheRoyalScions.java b/Mage.Sets/src/mage/cards/t/TheRoyalScions.java index 337d87e5f7..83fda327c0 100644 --- a/Mage.Sets/src/mage/cards/t/TheRoyalScions.java +++ b/Mage.Sets/src/mage/cards/t/TheRoyalScions.java @@ -13,6 +13,7 @@ import mage.abilities.effects.common.DrawDiscardControllerEffect; import mage.abilities.effects.common.continuous.BoostTargetEffect; import mage.abilities.effects.common.continuous.GainAbilityTargetEffect; import mage.abilities.keyword.FirstStrikeAbility; +import mage.abilities.keyword.TrampleAbility; import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.*; @@ -39,13 +40,16 @@ public final class TheRoyalScions extends CardImpl { // +1: Draw a card, then discard a card. this.addAbility(new LoyaltyAbility(new DrawDiscardControllerEffect(1, 1), 1)); - // +1: Target creature gets +2/+0 and gains first strike until end of turn. + // +1: Target creature gets +2/+0 and gains first strike and trample until end of turn. Ability ability = new LoyaltyAbility(new BoostTargetEffect( 2, 0, Duration.EndOfTurn ).setText("Target creature gets +2/+0"), 1); ability.addEffect(new GainAbilityTargetEffect( FirstStrikeAbility.getInstance(), Duration.EndOfTurn - ).setText("and gains first strike until end of turn")); + ).setText("and gains first strike")); + ability.addEffect(new GainAbilityTargetEffect( + TrampleAbility.getInstance(), Duration.EndOfTurn + ).setText("and trample until end of turn")); ability.addTarget(new TargetCreaturePermanent()); this.addAbility(ability); diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index 950e42004b..a32852a21f 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -36014,10 +36014,12 @@ Mesmeric Glare|Throne of Eldraine|49|U|{2}{U}|Instant - Adventure|2|1|Counter ta Midnight Clock|Throne of Eldraine|54|R|{2}{U}|Artifact|||{T}: Add {U}.${2}{U}: Put an hour counter on Midnight Clock.$At the beginning of each upkeep, put an hour counter on Midnight Clock.$When the twelfth hour counter is put on Midnight Clock, shuffle your hand and graveyard into your library, then draw seven cards. Exile Midnight Clock.| Mystical Dispute|Throne of Eldraine|58|U|{2}{U}|Instant|||This spell costs {2} less to cast if it targets a blue spell.$Counter target spell unless its controller pays {3}.| Run Away Together|Throne of Eldraine|62|C|{1}{U}|Instant|||Choose two target creatures controlled by different players. Return those creatures to their owners' hands.| +Syr Elenora the Discerning|Throne of Eldraine|67|U|{3}{U}{U}|Legendary Creature - Human Knight|*|4|Syr Elenora the Discerning's power is equal to the number of cards in your hand.$When Syr Elenora enters the battlefield, draw a card.$Spells your opponents cast that target Syr Elenora cost {2} more to cast.| Tome Raider|Throne of Eldraine|68|C|{2}{U}|Creature - Faerie|1|1|Flying$When Tome Raider enters the battlefield, draw a card.| Turn into a Pumpkin|Throne of Eldraine|69|U|{3}{U}|Instant|||Return target nonland permanent to its owner's hand. Draw a card.$Adamant — If at least three blue mana was spent to cast this spell, create a Food token.| Wishful Merfolk|Throne of Eldraine|73|C|{1}{U}|Creature - Merfolk|3|2|Defender${1}{U}: Wishful Merfolk loses defender and becomes a Human until end of turn.| Witching Well|Throne of Eldraine|74|C|{U}|Artifact|||When Witching Well enters the battlefield, scry 2.${3}{U}, Sacrifice Witching Well: Draw two cards.| +Ayara, First of Locthwain|Throne of Eldraine|75|R|{B}{B}{B}|Legendary Creature - Elf Noble|||Whenever Ayara, First of Locthwain or another black creature enters the battlefield under your control, each opponent loses 1 life and you gain 1 life.${T}, Sacrifice another black creature: Draw a card.| Bake into a Pie|Throne of Eldraine|76|C|{2}{B}{B}|Instant|||Destroy target creature. Create a Food token.| Belle of the Brawl|Throne of Eldraine|78|U|{2}{B}|Creature - Human Knight|3|2|Menace$Whenever Belle of the Brawl attacks, other Knights you control get +1/+0 until end of turn.| Clackbridge Troll|Throne of Eldraine|84|R|{3}{B}{B}|Creature - Troll|8|8|Trample, haste$When Clackbridge Troll enters the battlefield, target opponent creates three 0/1 white Goat creature tokens.$At the beginning of combat on your turn, any opponent may sacrifice a creature. If a player does, tap Clackbridge Troll, you gain 3 life, and you draw a card.| @@ -36047,6 +36049,7 @@ Battle Display|Throne of Eldraine|122|U|{R}|Sorcery - Adventure|2|1|Destroy targ Embereth Shieldbreaker|Throne of Eldraine|122|U|{1}{R}|Creature - Human Knight|2|1|| Joust|Throne of Eldraine|129|U|{1}{R}|Sorcery|||Choose target creature you control and target creature you don't control. The creature you control gets +2/+1 until end of turn if it's a Knight. Then those creatures fight each other.| Robber of the Rich|Throne of Eldraine|138|M|{1}{R}|Creature - Human Archer Rogue|2|2|Reach, haste$Whenever Robber of the Rich attacks, if defending player has more cards in hand than you, exile the top card of their library. During any turn you attacked with a Rogue, you may cast that card and you may spend mana as though it were mana of any color to cast that spell.| +Scorching Dragonfire|Throne of Eldraine|139|C|{1}{R}|Instant|||Scorching Dragonfire deals 3 damage to target creature or planeswalker. If that creature or planeswalker would die this turn, exile it instead.| Skullknocker Ogre|Throne of Eldraine|142|U|{3}{R}|Creature - Ogre|4|3|Whenever Skullknocker Ogre deals damage to an opponent, that player discards a card at random. If the player does, they draw a card.| Slaying Fire|Throne of Eldraine|143|U|{2}{R}|Instant|||Slaying Fire deals 3 damage to any target.$Adamant — If at least three red mana was spent to cast this spell, it deals 4 damage instead.| Weaselback Redcap|Throne of Eldraine|148|C|{R}|Creature - Goblin Knight|1|1|{1}{R}: Weaselback Redcap gets +2/+0 until end of turn.| @@ -36074,7 +36077,7 @@ Lochmere Serpent|Throne of Eldraine|195|R|{4}{U}{B}|Creature - Serpent|7|7|Flash Maraleaf Pixie|Throne of Eldraine|196|U|{G}{U}|Creature - Faerie|2|2|Flying${T}: Add {G} or {U}.| Oko, Thief of Crowns|Throne of Eldraine|197|M|{1}{G}{U}|Legendary Planeswalker - Oko|4|+2: Create a Food token.$+1: Target artifact or creature loses all abilities and becomes a green Elk creature with base power and toughness 3/3.$−5: Exchange control of target artifact or creature you control and target creature an opponent controls with power 3 or less.| Outlaws' Merriment|Throne of Eldraine|198|M|{1}{R}{W}{W}|Enchantment|||At the beginning of your upkeep, choose one at random. Create a red and white creature token with those characteristics.$• 3/1 Human Warrior with trample and haste.$• 2/1 Human Cleric with lifelink and haste.$• 1/2 Human Rogue with haste and "When this creature enters the battlefield, it deals 1 damage to any target."| -The Royal Scions|Throne of Eldraine|199|M|{1}{U}{R}|Legendary Planeswalker - Will Rowan|5|+1: Draw a card, then discard a card.$+1: Target creature gets +2/+0 and gains first strike until end of turn.$−8: Draw four cards. When you do, The Royal Scions deals damage to any target equal to the number of cards in your hand.| +The Royal Scions|Throne of Eldraine|199|M|{1}{U}{R}|Legendary Planeswalker - Will Rowan|5|+1: Draw a card, then discard a card.$+1: Target creature gets +2/+0 and gains first strike and trample until end of turn.$−8: Draw four cards. When you do, The Royal Scions deals damage to any target equal to the number of cards in your hand.| Savvy Hunter|Throne of Eldraine|200|U|{1}{B}{G}|Creature - Human Warrior|3|3|Whenever Savvy Hunter attacks or blocks, create a Food token.$Sacrifice two Foods: Draw a card.| Shinechaser|Throne of Eldraine|201|U|{1}{W}{U}|Creature - Faerie|1|1|Flying, vigilance$Shinechaser gets +1/+1 as long as you control an artifact.$Shinechaser gets +1/+1 as long as you control an enchantment.| Steelclaw Lance|Throne of Eldraine|202|U|{B}{R}|Artifact - Equipment|||Equipped creature gets +2/+2.$Equip Knight {1}$Equip {3}| From 524dc1c36c09914eb5b2ef724e986f35d015f7be Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 11 Sep 2019 09:58:09 -0400 Subject: [PATCH 051/373] Implemented Scorching Dragonfire --- .../src/mage/cards/s/ScorchingDragonfire.java | 35 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 36 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/s/ScorchingDragonfire.java diff --git a/Mage.Sets/src/mage/cards/s/ScorchingDragonfire.java b/Mage.Sets/src/mage/cards/s/ScorchingDragonfire.java new file mode 100644 index 0000000000..c0ca25806e --- /dev/null +++ b/Mage.Sets/src/mage/cards/s/ScorchingDragonfire.java @@ -0,0 +1,35 @@ +package mage.cards.s; + +import mage.abilities.effects.common.DamageTargetEffect; +import mage.abilities.effects.common.ExileTargetIfDiesEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.target.common.TargetCreatureOrPlaneswalker; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class ScorchingDragonfire extends CardImpl { + + public ScorchingDragonfire(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.INSTANT}, "{1}{R}"); + + // Scorching Dragonfire deals 3 damage to target creature or planeswalker. If that creature or planeswalker would die this turn, exile it instead. + this.getSpellAbility().addEffect(new DamageTargetEffect(3)); + this.getSpellAbility().addEffect(new ExileTargetIfDiesEffect() + .setText("If that creature or planeswalker would die this turn, exile it instead.")); + this.getSpellAbility().addTarget(new TargetCreatureOrPlaneswalker()); + } + + private ScorchingDragonfire(final ScorchingDragonfire card) { + super(card); + } + + @Override + public ScorchingDragonfire copy() { + return new ScorchingDragonfire(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 9147dc0166..6ad290e190 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -99,6 +99,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Rowan, Fearless Sparkmage", 304, Rarity.MYTHIC, mage.cards.r.RowanFearlessSparkmage.class)); cards.add(new SetCardInfo("Run Away Together", 62, Rarity.COMMON, mage.cards.r.RunAwayTogether.class)); cards.add(new SetCardInfo("Savvy Hunter", 200, Rarity.UNCOMMON, mage.cards.s.SavvyHunter.class)); + cards.add(new SetCardInfo("Scorching Dragonfire", 139, Rarity.COMMON, mage.cards.s.ScorchingDragonfire.class)); cards.add(new SetCardInfo("Shimmer Dragon", 317, Rarity.RARE, mage.cards.s.ShimmerDragon.class)); cards.add(new SetCardInfo("Shinechaser", 201, Rarity.UNCOMMON, mage.cards.s.Shinechaser.class)); cards.add(new SetCardInfo("Shining Armor", 29, Rarity.COMMON, mage.cards.s.ShiningArmor.class)); From 370de750f4992449d68e0c6084481554c708ac42 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 11 Sep 2019 13:06:00 -0400 Subject: [PATCH 052/373] fixed Oko, Thief of Crowns first ability (fixes #5974) --- Mage.Sets/src/mage/cards/o/OkoThiefOfCrowns.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Mage.Sets/src/mage/cards/o/OkoThiefOfCrowns.java b/Mage.Sets/src/mage/cards/o/OkoThiefOfCrowns.java index a87c2fd372..79e5881224 100644 --- a/Mage.Sets/src/mage/cards/o/OkoThiefOfCrowns.java +++ b/Mage.Sets/src/mage/cards/o/OkoThiefOfCrowns.java @@ -39,7 +39,7 @@ public final class OkoThiefOfCrowns extends CardImpl { this.addAbility(new PlaneswalkerEntersWithLoyaltyCountersAbility(4)); // +2: Create a Food token. - this.addAbility(new LoyaltyAbility(new CreateTokenEffect(new FoodToken(), 2))); + this.addAbility(new LoyaltyAbility(new CreateTokenEffect(new FoodToken()), 2)); // +1: Target artifact or creature loses all abilities and becomes a green Elk creature with base power and toughness 3/3. Ability ability = new LoyaltyAbility(new BecomesCreatureTargetEffect( From d9a934ac4f6f4fc15164f6f230c2b41d470b2393 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 11 Sep 2019 13:27:18 -0400 Subject: [PATCH 053/373] Implemented Doom Foretold --- Mage.Sets/src/mage/cards/d/DoomForetold.java | 104 ++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + .../BeginningOfUpkeepTriggeredAbility.java | 7 +- 3 files changed, 110 insertions(+), 2 deletions(-) create mode 100644 Mage.Sets/src/mage/cards/d/DoomForetold.java diff --git a/Mage.Sets/src/mage/cards/d/DoomForetold.java b/Mage.Sets/src/mage/cards/d/DoomForetold.java new file mode 100644 index 0000000000..b472cde979 --- /dev/null +++ b/Mage.Sets/src/mage/cards/d/DoomForetold.java @@ -0,0 +1,104 @@ +package mage.cards.d; + +import mage.abilities.Ability; +import mage.abilities.common.BeginningOfUpkeepTriggeredAbility; +import mage.abilities.effects.Effect; +import mage.abilities.effects.OneShotEffect; +import mage.abilities.effects.common.CreateTokenEffect; +import mage.abilities.effects.common.SacrificeSourceEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Outcome; +import mage.constants.TargetController; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterNonlandPermanent; +import mage.filter.predicate.Predicates; +import mage.filter.predicate.permanent.ControllerIdPredicate; +import mage.filter.predicate.permanent.TokenPredicate; +import mage.game.Game; +import mage.game.permanent.Permanent; +import mage.game.permanent.token.KnightToken; +import mage.players.Player; +import mage.target.TargetPermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class DoomForetold extends CardImpl { + + public DoomForetold(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ENCHANTMENT}, "{2}{W}{B}"); + + // At the beginning of each player's upkeep, that player sacrifices a nonland, nontoken permanent. If that player can't, they discard a card, they lose 2 life, you draw a card, you gain 2 life, you create a 2/2 white Knight creature token with vigilance, then you sacrifice Doom Foretold. + this.addAbility(new BeginningOfUpkeepTriggeredAbility( + new DoomForetoldEffect(), TargetController.ACTIVE, false + )); + } + + private DoomForetold(final DoomForetold card) { + super(card); + } + + @Override + public DoomForetold copy() { + return new DoomForetold(this); + } +} + +class DoomForetoldEffect extends OneShotEffect { + + private static final FilterPermanent filter = new FilterNonlandPermanent("nonland, nontoken permanent"); + + static { + filter.add(Predicates.not(TokenPredicate.instance)); + } + + private static final Effect effect1 = new CreateTokenEffect(new KnightToken()); + private static final Effect effect2 = new SacrificeSourceEffect(); + + DoomForetoldEffect() { + super(Outcome.Benefit); + staticText = "that player sacrifices a nonland, nontoken permanent. " + + "If that player can't, they discard a card, they lose 2 life, you draw a card, you gain 2 life, " + + "you create a 2/2 white Knight creature token with vigilance, then you sacrifice {this}"; + } + + private DoomForetoldEffect(final DoomForetoldEffect effect) { + super(effect); + } + + @Override + public DoomForetoldEffect copy() { + return new DoomForetoldEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + Player controller = game.getPlayer(source.getControllerId()); + Player player = game.getPlayer(game.getActivePlayerId()); + if (controller == null || player == null) { + return false; + } + FilterPermanent filter2 = filter.copy(); + filter2.add(new ControllerIdPredicate(player.getId())); + if (game.getBattlefield().contains(filter2, 1, game)) { + TargetPermanent target = new TargetPermanent(filter2); + target.setNotTarget(true); + if (player.choose(outcome, target, source.getSourceId(), game)) { + Permanent permanent = game.getPermanent(target.getFirstTarget()); + if (permanent != null && permanent.sacrifice(source.getSourceId(), game)) { + return true; + } + } + } + player.discard(1, false, source, game); + player.loseLife(2, game, false); + controller.drawCards(1, game); + controller.gainLife(2, game, source); + effect1.apply(game, source); + return effect2.apply(game, source); + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 6ad290e190..3329890474 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -47,6 +47,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Command Tower", 333, Rarity.COMMON, mage.cards.c.CommandTower.class)); cards.add(new SetCardInfo("Corridor Monitor", 41, Rarity.COMMON, mage.cards.c.CorridorMonitor.class)); cards.add(new SetCardInfo("Crystal Slipper", 119, Rarity.COMMON, mage.cards.c.CrystalSlipper.class)); + cards.add(new SetCardInfo("Doom Foretold", 187, Rarity.RARE, mage.cards.d.DoomForetold.class)); cards.add(new SetCardInfo("Embercleave", 120, Rarity.MYTHIC, mage.cards.e.Embercleave.class)); cards.add(new SetCardInfo("Embereth Paladin", 121, Rarity.COMMON, mage.cards.e.EmberethPaladin.class)); cards.add(new SetCardInfo("Embereth Shieldbreaker", 122, Rarity.UNCOMMON, mage.cards.e.EmberethShieldbreaker.class)); diff --git a/Mage/src/main/java/mage/abilities/common/BeginningOfUpkeepTriggeredAbility.java b/Mage/src/main/java/mage/abilities/common/BeginningOfUpkeepTriggeredAbility.java index 87ed534a99..7969e308b5 100644 --- a/Mage/src/main/java/mage/abilities/common/BeginningOfUpkeepTriggeredAbility.java +++ b/Mage/src/main/java/mage/abilities/common/BeginningOfUpkeepTriggeredAbility.java @@ -1,7 +1,6 @@ package mage.abilities.common; -import java.util.Locale; import mage.abilities.TriggeredAbilityImpl; import mage.abilities.effects.Effect; import mage.constants.TargetController; @@ -11,8 +10,9 @@ import mage.game.events.GameEvent; import mage.game.permanent.Permanent; import mage.target.targetpointer.FixedTarget; +import java.util.Locale; + /** - * * @author Loki */ public class BeginningOfUpkeepTriggeredAbility extends TriggeredAbilityImpl { @@ -91,6 +91,7 @@ public class BeginningOfUpkeepTriggeredAbility extends TriggeredAbilityImpl { } break; case ANY: + case ACTIVE: if (setTargetPointer && getTargets().isEmpty()) { for (Effect effect : this.getEffects()) { effect.setTargetPointer(new FixedTarget(event.getPlayerId())); @@ -137,6 +138,8 @@ public class BeginningOfUpkeepTriggeredAbility extends TriggeredAbilityImpl { return sb.insert(0, generateZoneString()).insert(0, "At the beginning of each opponent's upkeep, ").toString(); case ANY: return sb.insert(0, generateZoneString()).insert(0, "At the beginning of each upkeep, ").toString(); + case ACTIVE: + return sb.insert(0, generateZoneString()).insert(0, "At the beginning of each player's upkeep, ").toString(); case CONTROLLER_ATTACHED_TO: return sb.insert(0, generateZoneString()).insert(0, "At the beginning of the upkeep of enchanted creature's controller, ").toString(); } From d9487e5cb81c5aa1be1def81e15d30b2a826b97b Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 11 Sep 2019 13:48:20 -0400 Subject: [PATCH 054/373] Implemented Skullknocker Ogre --- .../src/mage/cards/s/SkullknockerOgre.java | 72 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 73 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/s/SkullknockerOgre.java diff --git a/Mage.Sets/src/mage/cards/s/SkullknockerOgre.java b/Mage.Sets/src/mage/cards/s/SkullknockerOgre.java new file mode 100644 index 0000000000..c4d453f514 --- /dev/null +++ b/Mage.Sets/src/mage/cards/s/SkullknockerOgre.java @@ -0,0 +1,72 @@ +package mage.cards.s; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.DealsDamageToOpponentTriggeredAbility; +import mage.abilities.effects.OneShotEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Outcome; +import mage.constants.SubType; +import mage.game.Game; +import mage.players.Player; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class SkullknockerOgre extends CardImpl { + + public SkullknockerOgre(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{3}{R}"); + + this.subtype.add(SubType.OGRE); + this.power = new MageInt(4); + this.toughness = new MageInt(3); + + // Whenever Skullknocker Ogre deals damage to an opponent, that player discards a card at random. If the player does, they draw a card. + this.addAbility(new DealsDamageToOpponentTriggeredAbility( + new SkullknockerOgreEffect(), false, false, true + )); + } + + private SkullknockerOgre(final SkullknockerOgre card) { + super(card); + } + + @Override + public SkullknockerOgre copy() { + return new SkullknockerOgre(this); + } +} + +class SkullknockerOgreEffect extends OneShotEffect { + + SkullknockerOgreEffect() { + super(Outcome.Benefit); + staticText = "that player discards a card at random. If the player does, they draw a card"; + } + + private SkullknockerOgreEffect(final SkullknockerOgreEffect effect) { + super(effect); + } + + @Override + public SkullknockerOgreEffect copy() { + return new SkullknockerOgreEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + Player player = game.getPlayer(this.getTargetPointer().getFirst(game, source)); + if (player == null) { + return false; + } + if (player.discard(1, true, source, game).size() > 0) { + player.drawCards(1, game); + } + return true; + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 3329890474..3d8bb4af41 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -106,6 +106,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Shining Armor", 29, Rarity.COMMON, mage.cards.s.ShiningArmor.class)); cards.add(new SetCardInfo("Silverflame Ritual", 30, Rarity.COMMON, mage.cards.s.SilverflameRitual.class)); cards.add(new SetCardInfo("Silverwing Squadron", 315, Rarity.RARE, mage.cards.s.SilverwingSquadron.class)); + cards.add(new SetCardInfo("Skullknocker Ogre", 142, Rarity.UNCOMMON, mage.cards.s.SkullknockerOgre.class)); cards.add(new SetCardInfo("Slaying Fire", 143, Rarity.UNCOMMON, mage.cards.s.SlayingFire.class)); cards.add(new SetCardInfo("Smitten Swordmaster", 105, Rarity.COMMON, mage.cards.s.SmittenSwordmaster.class)); cards.add(new SetCardInfo("Steelbane Hydra", 322, Rarity.RARE, mage.cards.s.SteelbaneHydra.class)); From 09895e55f63fd3b679ea30787cd9a584a0a2f54b Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 11 Sep 2019 14:01:20 -0400 Subject: [PATCH 055/373] Implemented Clackbridge Troll --- .../src/mage/cards/c/ClackbridgeTroll.java | 123 ++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 124 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/c/ClackbridgeTroll.java diff --git a/Mage.Sets/src/mage/cards/c/ClackbridgeTroll.java b/Mage.Sets/src/mage/cards/c/ClackbridgeTroll.java new file mode 100644 index 0000000000..b8be5017bc --- /dev/null +++ b/Mage.Sets/src/mage/cards/c/ClackbridgeTroll.java @@ -0,0 +1,123 @@ +package mage.cards.c; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.BeginningOfCombatTriggeredAbility; +import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.effects.OneShotEffect; +import mage.abilities.effects.common.CreateTokenTargetEffect; +import mage.abilities.keyword.HasteAbility; +import mage.abilities.keyword.TrampleAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Outcome; +import mage.constants.SubType; +import mage.constants.TargetController; +import mage.filter.common.FilterControlledPermanent; +import mage.filter.predicate.mageobject.CardTypePredicate; +import mage.filter.predicate.permanent.ControllerPredicate; +import mage.game.Game; +import mage.game.permanent.Permanent; +import mage.game.permanent.token.GoatToken; +import mage.players.Player; +import mage.target.common.TargetControlledPermanent; +import mage.target.common.TargetOpponent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class ClackbridgeTroll extends CardImpl { + + public ClackbridgeTroll(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{3}{B}{B}"); + + this.subtype.add(SubType.TROLL); + this.power = new MageInt(8); + this.toughness = new MageInt(8); + + // Trample + this.addAbility(TrampleAbility.getInstance()); + + // Haste + this.addAbility(HasteAbility.getInstance()); + + // When Clackbridge Troll enters the battlefield, target opponent creates three 0/1 white Goat creature tokens. + Ability ability = new EntersBattlefieldTriggeredAbility(new CreateTokenTargetEffect(new GoatToken(), 3)); + ability.addTarget(new TargetOpponent()); + this.addAbility(ability); + + // At the beginning of combat on your turn, any opponent may sacrifice a creature. If a player does, tap Clackbridge Troll, you gain 3 life, and you draw a card. + this.addAbility(new BeginningOfCombatTriggeredAbility( + new ClackbridgeTrollEffect(), TargetController.YOU, false) + ); + } + + private ClackbridgeTroll(final ClackbridgeTroll card) { + super(card); + } + + @Override + public ClackbridgeTroll copy() { + return new ClackbridgeTroll(this); + } +} + +class ClackbridgeTrollEffect extends OneShotEffect { + + ClackbridgeTrollEffect() { + super(Outcome.Benefit); + staticText = "any opponent may sacrifice a creature. If a player does, " + + "tap {this}, you gain 3 life, and you draw a card."; + } + + private ClackbridgeTrollEffect(final ClackbridgeTrollEffect effect) { + super(effect); + } + + @Override + public ClackbridgeTrollEffect copy() { + return new ClackbridgeTrollEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + Player controller = game.getPlayer(source.getControllerId()); + Permanent sourcePerm = game.getPermanent(source.getSourceId()); + if (controller == null) { + return false; + } + boolean flag = false; + for (UUID opponentId : game.getOpponents(controller.getId())) { + Player opponent = game.getPlayer(opponentId); + if (opponent == null) { + continue; + } + FilterControlledPermanent filter = new FilterControlledPermanent("creature to sacrifice"); + filter.add(new CardTypePredicate(CardType.CREATURE)); + filter.add(new ControllerPredicate(TargetController.YOU)); + TargetControlledPermanent target = new TargetControlledPermanent(filter); + target.setNotTarget(true); + if (!target.canChoose(opponent.getId(), game) + || !opponent.chooseUse(Outcome.AIDontUseIt, "Sacrifice a creature?", source, game) + || !opponent.choose(Outcome.Sacrifice, target, source.getSourceId(), game)) { + continue; + } + Permanent permanent = game.getPermanent(target.getFirstTarget()); + if (permanent == null || !permanent.sacrifice(source.getSourceId(), game)) { + continue; + } + flag = true; + } + if (flag) { + if (sourcePerm != null) { + sourcePerm.tap(game); + } + controller.gainLife(3, game, source); + controller.drawCards(1, game); + } + return true; + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 3d8bb4af41..1282ad281a 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -43,6 +43,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Burning-Yard Trainer", 117, Rarity.UNCOMMON, mage.cards.b.BurningYardTrainer.class)); cards.add(new SetCardInfo("Chittering Witch", 319, Rarity.RARE, mage.cards.c.ChitteringWitch.class)); cards.add(new SetCardInfo("Chulane, Teller of Tales", 326, Rarity.MYTHIC, mage.cards.c.ChulaneTellerOfTales.class)); + cards.add(new SetCardInfo("Clackbridge Troll", 84, Rarity.RARE, mage.cards.c.ClackbridgeTroll.class)); cards.add(new SetCardInfo("Claim the Firstborn", 118, Rarity.UNCOMMON, mage.cards.c.ClaimTheFirstborn.class)); cards.add(new SetCardInfo("Command Tower", 333, Rarity.COMMON, mage.cards.c.CommandTower.class)); cards.add(new SetCardInfo("Corridor Monitor", 41, Rarity.COMMON, mage.cards.c.CorridorMonitor.class)); From fa9835db34ba581cf9d4b23851fb133e1328ed4d Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 11 Sep 2019 14:32:57 -0400 Subject: [PATCH 056/373] Implemented Charming Prince --- .../src/mage/cards/c/CharmingPrince.java | 113 ++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 114 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/c/CharmingPrince.java diff --git a/Mage.Sets/src/mage/cards/c/CharmingPrince.java b/Mage.Sets/src/mage/cards/c/CharmingPrince.java new file mode 100644 index 0000000000..a1b2419257 --- /dev/null +++ b/Mage.Sets/src/mage/cards/c/CharmingPrince.java @@ -0,0 +1,113 @@ +package mage.cards.c; + +import mage.MageInt; +import mage.MageObject; +import mage.abilities.Ability; +import mage.abilities.Mode; +import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.common.delayed.AtTheBeginOfNextEndStepDelayedTriggeredAbility; +import mage.abilities.effects.Effect; +import mage.abilities.effects.OneShotEffect; +import mage.abilities.effects.common.GainLifeEffect; +import mage.abilities.effects.common.ReturnToBattlefieldUnderYourControlTargetEffect; +import mage.abilities.effects.keyword.ScryEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.*; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterCreaturePermanent; +import mage.filter.predicate.other.OwnerPredicate; +import mage.filter.predicate.permanent.AnotherPredicate; +import mage.game.Game; +import mage.game.permanent.Permanent; +import mage.players.Player; +import mage.target.TargetPermanent; +import mage.target.targetpointer.FixedTarget; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class CharmingPrince extends CardImpl { + + + private static final FilterPermanent filter = new FilterCreaturePermanent("another creature you own"); + + static { + filter.add(new OwnerPredicate(TargetController.YOU)); + filter.add(AnotherPredicate.instance); + } + + public CharmingPrince(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{1}{W}"); + + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.NOBLE); + this.power = new MageInt(2); + this.toughness = new MageInt(2); + + // When Charming Prince enters the battlefield, choose one — + // • Scry 2. + Ability ability = new EntersBattlefieldTriggeredAbility(new ScryEffect(2)); + + // • You gain 3 life. + ability.addMode(new Mode(new GainLifeEffect(3))); + + // • Exile another target creature you own. Return it to the battlefield under your control at the beginning of the next end step. + Mode mode = new Mode(new CharmingPrinceEffect()); + mode.addTarget(new TargetPermanent(filter)); + ability.addMode(mode); + this.addAbility(ability); + } + + private CharmingPrince(final CharmingPrince card) { + super(card); + } + + @Override + public CharmingPrince copy() { + return new CharmingPrince(this); + } +} + +class CharmingPrinceEffect extends OneShotEffect { + + CharmingPrinceEffect() { + super(Outcome.Benefit); + staticText = "Exile another target creature you own. " + + "Return it to the battlefield under your control at the beginning of the next end step."; + } + + private CharmingPrinceEffect(final CharmingPrinceEffect effect) { + super(effect); + } + + @Override + public CharmingPrinceEffect copy() { + return new CharmingPrinceEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + Player controller = game.getPlayer(source.getControllerId()); + MageObject sourceObject = game.getObject(source.getSourceId()); + if (controller == null || sourceObject == null) { + return false; + } + Permanent permanent = game.getPermanent(source.getFirstTarget()); + if (permanent == null) { + return false; + } + if (!controller.moveCardToExileWithInfo(permanent, source.getSourceId(), sourceObject.getIdName(), source.getSourceId(), game, Zone.BATTLEFIELD, true)) { + return false; + } + //create delayed triggered ability + Effect effect = new ReturnToBattlefieldUnderYourControlTargetEffect(); + effect.setText("Return it to the battlefield under your control at the beginning of the next end step"); + effect.setTargetPointer(new FixedTarget(permanent.getId(), game)); + game.addDelayedTriggeredAbility(new AtTheBeginOfNextEndStepDelayedTriggeredAbility(effect), source); + return true; + + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 1282ad281a..1fa672606f 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -41,6 +41,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Bramblefort Fink", 311, Rarity.UNCOMMON, mage.cards.b.BramblefortFink.class)); cards.add(new SetCardInfo("Brimstone Trebuchet", 116, Rarity.COMMON, mage.cards.b.BrimstoneTrebuchet.class)); cards.add(new SetCardInfo("Burning-Yard Trainer", 117, Rarity.UNCOMMON, mage.cards.b.BurningYardTrainer.class)); + cards.add(new SetCardInfo("Charming Prince", 335, Rarity.RARE, mage.cards.c.CharmingPrince.class)); cards.add(new SetCardInfo("Chittering Witch", 319, Rarity.RARE, mage.cards.c.ChitteringWitch.class)); cards.add(new SetCardInfo("Chulane, Teller of Tales", 326, Rarity.MYTHIC, mage.cards.c.ChulaneTellerOfTales.class)); cards.add(new SetCardInfo("Clackbridge Troll", 84, Rarity.RARE, mage.cards.c.ClackbridgeTroll.class)); From f02ab1edaed793bf7edaf93e270acd4df4e42133 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 11 Sep 2019 14:48:45 -0400 Subject: [PATCH 057/373] Implemented Emry, Lurker of the Loch --- .../src/mage/cards/e/EmryLurkerOfTheLoch.java | 129 ++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 130 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/e/EmryLurkerOfTheLoch.java diff --git a/Mage.Sets/src/mage/cards/e/EmryLurkerOfTheLoch.java b/Mage.Sets/src/mage/cards/e/EmryLurkerOfTheLoch.java new file mode 100644 index 0000000000..428efcfb49 --- /dev/null +++ b/Mage.Sets/src/mage/cards/e/EmryLurkerOfTheLoch.java @@ -0,0 +1,129 @@ +package mage.cards.e; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.SpellAbility; +import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.costs.common.TapSourceCost; +import mage.abilities.effects.AsThoughEffectImpl; +import mage.abilities.effects.common.PutTopCardOfLibraryIntoGraveControllerEffect; +import mage.abilities.effects.common.cost.CostModificationEffectImpl; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.*; +import mage.filter.StaticFilters; +import mage.game.Game; +import mage.target.common.TargetCardInYourGraveyard; +import mage.util.CardUtil; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class EmryLurkerOfTheLoch extends CardImpl { + + public EmryLurkerOfTheLoch(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{2}{U}"); + + this.addSuperType(SuperType.LEGENDARY); + this.subtype.add(SubType.MERFOLK); + this.subtype.add(SubType.WIZARD); + this.power = new MageInt(1); + this.toughness = new MageInt(2); + + // This spell costs {1} less to cast for each artifact you control. + this.addAbility(new SimpleStaticAbility(Zone.STACK, new EmryLurkerOfTheLochCostReductionEffect())); + + // When Emry, Lurker of the Loch enters the battlefield, put the top four cards of your library into your graveyard. + this.addAbility(new EntersBattlefieldTriggeredAbility( + new PutTopCardOfLibraryIntoGraveControllerEffect(4) + )); + + // {T}: Choose target artifact card in your graveyard. You may cast that card this turn. + Ability ability = new SimpleActivatedAbility(new EmryLurkerOfTheLochPlayEffect(), new TapSourceCost()); + ability.addTarget(new TargetCardInYourGraveyard(StaticFilters.FILTER_CARD_ARTIFACT)); + this.addAbility(ability); + } + + private EmryLurkerOfTheLoch(final EmryLurkerOfTheLoch card) { + super(card); + } + + @Override + public EmryLurkerOfTheLoch copy() { + return new EmryLurkerOfTheLoch(this); + } +} + +class EmryLurkerOfTheLochCostReductionEffect extends CostModificationEffectImpl { + + EmryLurkerOfTheLochCostReductionEffect() { + super(Duration.WhileOnStack, Outcome.Benefit, CostModificationType.REDUCE_COST); + staticText = "This spell costs {1} less to cast for each artifact you control"; + } + + private EmryLurkerOfTheLochCostReductionEffect(final EmryLurkerOfTheLochCostReductionEffect effect) { + super(effect); + } + + @Override + public boolean apply(Game game, Ability source, Ability abilityToModify) { + int reductionAmount = game.getBattlefield().count( + StaticFilters.FILTER_CONTROLLED_PERMANENT_ARTIFACT, + source.getSourceId(), source.getControllerId(), game + ); + CardUtil.reduceCost(abilityToModify, reductionAmount); + return true; + } + + @Override + public boolean applies(Ability abilityToModify, Ability source, Game game) { + return abilityToModify instanceof SpellAbility + && abilityToModify.getSourceId().equals(source.getSourceId()) + && game.getCard(abilityToModify.getSourceId()) != null; + } + + @Override + public EmryLurkerOfTheLochCostReductionEffect copy() { + return new EmryLurkerOfTheLochCostReductionEffect(this); + } +} + +class EmryLurkerOfTheLochPlayEffect extends AsThoughEffectImpl { + + EmryLurkerOfTheLochPlayEffect() { + super(AsThoughEffectType.PLAY_FROM_NOT_OWN_HAND_ZONE, Duration.EndOfTurn, Outcome.Benefit); + staticText = "Choose target artifact card in your graveyard. You may cast that card this turn."; + } + + private EmryLurkerOfTheLochPlayEffect(final EmryLurkerOfTheLochPlayEffect effect) { + super(effect); + } + + @Override + public boolean apply(Game game, Ability source) { + return true; + } + + @Override + public EmryLurkerOfTheLochPlayEffect copy() { + return new EmryLurkerOfTheLochPlayEffect(this); + } + + @Override + public boolean applies(UUID objectId, Ability source, UUID affectedControllerId, Game game) { + UUID targetId = getTargetPointer().getFirst(game, source); + if (targetId != null) { + return targetId.equals(objectId) + && source.isControlledBy(affectedControllerId) + && Zone.GRAVEYARD == game.getState().getZone(objectId); + } else { + // the target card has changed zone meanwhile, so the effect is no longer needed + discard(); + return false; + } + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 1fa672606f..caf3745b36 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -54,6 +54,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Embereth Paladin", 121, Rarity.COMMON, mage.cards.e.EmberethPaladin.class)); cards.add(new SetCardInfo("Embereth Shieldbreaker", 122, Rarity.UNCOMMON, mage.cards.e.EmberethShieldbreaker.class)); cards.add(new SetCardInfo("Embereth Skyblazer", 321, Rarity.RARE, mage.cards.e.EmberethSkyblazer.class)); + cards.add(new SetCardInfo("Emry, Lurker of the Loch", 43, Rarity.RARE, mage.cards.e.EmryLurkerOfTheLoch.class)); cards.add(new SetCardInfo("Enchanted Carriage", 218, Rarity.UNCOMMON, mage.cards.e.EnchantedCarriage.class)); cards.add(new SetCardInfo("Eye Collector", 86, Rarity.COMMON, mage.cards.e.EyeCollector.class)); cards.add(new SetCardInfo("Faerie Formation", 316, Rarity.RARE, mage.cards.f.FaerieFormation.class)); From f70c337e0de1aa9c05bee59be64125965e0f7385 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 11 Sep 2019 15:17:52 -0400 Subject: [PATCH 058/373] Implemented Syr Elenora the Discerning --- .../src/mage/cards/b/BorealElemental.java | 17 ++- .../mage/cards/s/SyrElenoraTheDiscerning.java | 100 ++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 3 files changed, 109 insertions(+), 9 deletions(-) create mode 100644 Mage.Sets/src/mage/cards/s/SyrElenoraTheDiscerning.java diff --git a/Mage.Sets/src/mage/cards/b/BorealElemental.java b/Mage.Sets/src/mage/cards/b/BorealElemental.java index e496ba4261..bd0f8fcada 100644 --- a/Mage.Sets/src/mage/cards/b/BorealElemental.java +++ b/Mage.Sets/src/mage/cards/b/BorealElemental.java @@ -2,6 +2,7 @@ package mage.cards.b; import mage.MageInt; import mage.abilities.Ability; +import mage.abilities.Mode; import mage.abilities.SpellAbility; import mage.abilities.common.SimpleStaticAbility; import mage.abilities.effects.common.cost.CostModificationEffectImpl; @@ -10,8 +11,10 @@ import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.*; import mage.game.Game; +import mage.target.Target; import mage.util.CardUtil; +import java.util.Collection; import java.util.UUID; /** @@ -72,15 +75,11 @@ class BorealElementalCostIncreaseEffect extends CostModificationEffectImpl { .getSelectedModes() .stream() .map(uuid -> abilityToModify.getModes().get(uuid)) - .anyMatch(mode -> mode - .getTargets() - .stream() - .anyMatch(target -> target - .getTargets() - .stream() - .anyMatch(uuid -> uuid.equals(source.getSourceId())) - ) - ); + .map(Mode::getTargets) + .flatMap(Collection::stream) + .map(Target::getTargets) + .flatMap(Collection::stream) + .anyMatch(uuid -> uuid.equals(source.getSourceId())); } @Override diff --git a/Mage.Sets/src/mage/cards/s/SyrElenoraTheDiscerning.java b/Mage.Sets/src/mage/cards/s/SyrElenoraTheDiscerning.java new file mode 100644 index 0000000000..0be6760519 --- /dev/null +++ b/Mage.Sets/src/mage/cards/s/SyrElenoraTheDiscerning.java @@ -0,0 +1,100 @@ +package mage.cards.s; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.Mode; +import mage.abilities.SpellAbility; +import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.dynamicvalue.common.CardsInControllerHandCount; +import mage.abilities.effects.common.DrawCardSourceControllerEffect; +import mage.abilities.effects.common.continuous.SetPowerSourceEffect; +import mage.abilities.effects.common.cost.CostModificationEffectImpl; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.*; +import mage.game.Game; +import mage.target.Target; +import mage.util.CardUtil; + +import java.util.Collection; +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class SyrElenoraTheDiscerning extends CardImpl { + + public SyrElenoraTheDiscerning(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{3}{U}{U}"); + + this.addSuperType(SuperType.LEGENDARY); + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.KNIGHT); + this.power = new MageInt(0); + this.toughness = new MageInt(4); + + // Syr Elenora the Discerning's power is equal to the number of cards in your hand. + this.addAbility(new SimpleStaticAbility( + Zone.ALL, new SetPowerSourceEffect(CardsInControllerHandCount.instance, Duration.EndOfGame) + )); + + // When Syr Elenora enters the battlefield, draw a card. + this.addAbility(new EntersBattlefieldTriggeredAbility(new DrawCardSourceControllerEffect(1))); + + // Spells your opponents cast that target Syr Elenora cost {2} more to cast. + this.addAbility(new SimpleStaticAbility(new SyrElenoraTheDiscerningCostIncreaseEffect())); + } + + private SyrElenoraTheDiscerning(final SyrElenoraTheDiscerning card) { + super(card); + } + + @Override + public SyrElenoraTheDiscerning copy() { + return new SyrElenoraTheDiscerning(this); + } +} + +class SyrElenoraTheDiscerningCostIncreaseEffect extends CostModificationEffectImpl { + + SyrElenoraTheDiscerningCostIncreaseEffect() { + super(Duration.WhileOnBattlefield, Outcome.Benefit, CostModificationType.INCREASE_COST); + staticText = "Spells your opponents cast that target {this} cost {2} more to cast"; + } + + private SyrElenoraTheDiscerningCostIncreaseEffect(SyrElenoraTheDiscerningCostIncreaseEffect effect) { + super(effect); + } + + @Override + public boolean apply(Game game, Ability source, Ability abilityToModify) { + SpellAbility spellAbility = (SpellAbility) abilityToModify; + CardUtil.adjustCost(spellAbility, -2); + return true; + } + + @Override + public boolean applies(Ability abilityToModify, Ability source, Game game) { + if (!(abilityToModify instanceof SpellAbility) + || !game.getOpponents(source.getControllerId()).contains(abilityToModify.getControllerId())) { + return false; + } + return abilityToModify + .getModes() + .getSelectedModes() + .stream() + .map(uuid -> abilityToModify.getModes().get(uuid)) + .map(Mode::getTargets) + .flatMap(Collection::stream) + .map(Target::getTargets) + .flatMap(Collection::stream) + .anyMatch(uuid -> uuid.equals(source.getSourceId())); + } + + @Override + public SyrElenoraTheDiscerningCostIncreaseEffect copy() { + return new SyrElenoraTheDiscerningCostIncreaseEffect(this); + } + +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index caf3745b36..518f67fe78 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -114,6 +114,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Smitten Swordmaster", 105, Rarity.COMMON, mage.cards.s.SmittenSwordmaster.class)); cards.add(new SetCardInfo("Steelbane Hydra", 322, Rarity.RARE, mage.cards.s.SteelbaneHydra.class)); cards.add(new SetCardInfo("Steelclaw Lance", 202, Rarity.UNCOMMON, mage.cards.s.SteelclawLance.class)); + cards.add(new SetCardInfo("Syr Elenora the Discerning", 67, Rarity.UNCOMMON, mage.cards.s.SyrElenoraTheDiscerning.class)); cards.add(new SetCardInfo("Syr Gwyn, Hero of Ashvale", 330, Rarity.MYTHIC, mage.cards.s.SyrGwynHeroOfAshvale.class)); cards.add(new SetCardInfo("Syr Konrad, the Grim", 107, Rarity.UNCOMMON, mage.cards.s.SyrKonradTheGrim.class)); cards.add(new SetCardInfo("Taste of Death", 320, Rarity.RARE, mage.cards.t.TasteOfDeath.class)); From 724417589cfe07a5a6995ade0ef2cbe04bb1cf00 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 11 Sep 2019 16:21:34 -0400 Subject: [PATCH 059/373] Implemented Murderous Rider --- .../src/mage/cards/m/MurderousRider.java | 55 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 56 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/m/MurderousRider.java diff --git a/Mage.Sets/src/mage/cards/m/MurderousRider.java b/Mage.Sets/src/mage/cards/m/MurderousRider.java new file mode 100644 index 0000000000..24cf1b16f9 --- /dev/null +++ b/Mage.Sets/src/mage/cards/m/MurderousRider.java @@ -0,0 +1,55 @@ +package mage.cards.m; + +import mage.MageInt; +import mage.abilities.common.DiesTriggeredAbility; +import mage.abilities.effects.common.DestroyTargetEffect; +import mage.abilities.effects.common.LoseLifeSourceControllerEffect; +import mage.abilities.effects.common.PutOnLibraryTargetEffect; +import mage.abilities.keyword.LifelinkAbility; +import mage.cards.AdventureCard; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.target.common.TargetCreatureOrPlaneswalker; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class MurderousRider extends AdventureCard { + + public MurderousRider(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, new CardType[]{CardType.INSTANT}, "{1}{B}{B}", "Swift End", "{1}{B}{B}"); + + this.subtype.add(SubType.ZOMBIE); + this.subtype.add(SubType.KNIGHT); + this.power = new MageInt(2); + this.toughness = new MageInt(3); + + // Lifelink + this.addAbility(LifelinkAbility.getInstance()); + + // When Murderous Rider dies, put it on the bottom of its owner's library. + this.addAbility(new DiesTriggeredAbility(new PutOnLibraryTargetEffect( + false, "put it on the bottom of its owner's library" + ), false)); + + // Swift End + // Destroy target creature or planeswalker. You lose 2 life. + this.getAdventureSpellAbility().addEffect(new DestroyTargetEffect()); + this.getAdventureSpellAbility().addEffect( + new LoseLifeSourceControllerEffect(2).setText("You lose 2 life.") + ); + this.getAdventureSpellAbility().addTarget(new TargetCreatureOrPlaneswalker()); + } + + private MurderousRider(final MurderousRider card) { + super(card); + } + + @Override + public MurderousRider copy() { + return new MurderousRider(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 518f67fe78..4f1f60b313 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -84,6 +84,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Mace of the Valiant", 314, Rarity.RARE, mage.cards.m.MaceOfTheValiant.class)); cards.add(new SetCardInfo("Maraleaf Pixie", 196, Rarity.UNCOMMON, mage.cards.m.MaraleafPixie.class)); cards.add(new SetCardInfo("Midnight Clock", 54, Rarity.RARE, mage.cards.m.MidnightClock.class)); + cards.add(new SetCardInfo("Murderous Rider", 97, Rarity.RARE, mage.cards.m.MurderousRider.class)); cards.add(new SetCardInfo("Mystical Dispute", 58, Rarity.UNCOMMON, mage.cards.m.MysticalDispute.class)); cards.add(new SetCardInfo("Oakhame Ranger", 212, Rarity.UNCOMMON, mage.cards.o.OakhameRanger.class)); cards.add(new SetCardInfo("Oko's Accomplices", 310, Rarity.COMMON, mage.cards.o.OkosAccomplices.class)); From a5fe53b2fc6cd5388c00a3eec90c371d74ae93be Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 11 Sep 2019 16:29:12 -0400 Subject: [PATCH 060/373] Implemented Lochmere Serpent --- .../src/mage/cards/l/LochmereSerpent.java | 77 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 78 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/l/LochmereSerpent.java diff --git a/Mage.Sets/src/mage/cards/l/LochmereSerpent.java b/Mage.Sets/src/mage/cards/l/LochmereSerpent.java new file mode 100644 index 0000000000..8bc41a7bfb --- /dev/null +++ b/Mage.Sets/src/mage/cards/l/LochmereSerpent.java @@ -0,0 +1,77 @@ +package mage.cards.l; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.ActivateAsSorceryActivatedAbility; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.costs.common.SacrificeTargetCost; +import mage.abilities.costs.mana.ManaCostsImpl; +import mage.abilities.effects.common.DrawCardSourceControllerEffect; +import mage.abilities.effects.common.ExileTargetEffect; +import mage.abilities.effects.common.GainLifeEffect; +import mage.abilities.effects.common.ReturnSourceFromGraveyardToHandEffect; +import mage.abilities.effects.common.combat.CantBeBlockedSourceEffect; +import mage.abilities.keyword.FlashAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; +import mage.constants.Zone; +import mage.filter.common.FilterControlledPermanent; +import mage.target.common.TargetControlledPermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class LochmereSerpent extends CardImpl { + + private static final FilterControlledPermanent filter1 + = new FilterControlledPermanent(SubType.ISLAND, "an Island"); + private static final FilterControlledPermanent filter2 + = new FilterControlledPermanent(SubType.SWAMP, "a Swamp"); + + public LochmereSerpent(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{4}{U}{B}"); + + this.subtype.add(SubType.SERPENT); + this.power = new MageInt(7); + this.toughness = new MageInt(7); + + // Flash + this.addAbility(FlashAbility.getInstance()); + + // {U}, Sacrifice an Island: Lochmere Serpent can't be blocked this turn. + Ability ability = new SimpleActivatedAbility( + new CantBeBlockedSourceEffect(Duration.EndOfTurn), new ManaCostsImpl("{U}") + ); + ability.addCost(new SacrificeTargetCost(new TargetControlledPermanent(filter1))); + this.addAbility(ability); + + // {B}, Sacrifice a Swamp: You gain 1 life and draw a card. + ability = new SimpleActivatedAbility(new GainLifeEffect(1), new ManaCostsImpl("{B}")); + ability.addEffect(new DrawCardSourceControllerEffect(1).concatBy("and")); + ability.addCost(new SacrificeTargetCost(new TargetControlledPermanent(filter2))); + this.addAbility(ability); + + // {U}{B}: Exile five target cards from an opponent's graveyard. Return Lochmere Serpent from your graveyard to your hand. Activate this ability only any time you could cast a sorcery. + ability = new ActivateAsSorceryActivatedAbility( + Zone.BATTLEFIELD, + new ExileTargetEffect().setText("Exile five target cards from an opponent's graveyard."), + new ManaCostsImpl("{U}{B}") + ); + ability.addEffect(new ReturnSourceFromGraveyardToHandEffect()); + this.addAbility(ability); + } + + private LochmereSerpent(final LochmereSerpent card) { + super(card); + } + + @Override + public LochmereSerpent copy() { + return new LochmereSerpent(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 4f1f60b313..be24c2f0b7 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -80,6 +80,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Kenrith, the Returned King", 303, Rarity.MYTHIC, mage.cards.k.KenrithTheReturnedKing.class)); cards.add(new SetCardInfo("Knights' Charge", 328, Rarity.RARE, mage.cards.k.KnightsCharge.class)); cards.add(new SetCardInfo("Korvold, Fae-Cursed King", 329, Rarity.MYTHIC, mage.cards.k.KorvoldFaeCursedKing.class)); + cards.add(new SetCardInfo("Lochmere Serpent", 195, Rarity.RARE, mage.cards.l.LochmereSerpent.class)); cards.add(new SetCardInfo("Lovestruck Beast", 165, Rarity.RARE, mage.cards.l.LovestruckBeast.class)); cards.add(new SetCardInfo("Mace of the Valiant", 314, Rarity.RARE, mage.cards.m.MaceOfTheValiant.class)); cards.add(new SetCardInfo("Maraleaf Pixie", 196, Rarity.UNCOMMON, mage.cards.m.MaraleafPixie.class)); From 6417c0f244afadc1bc2cba509bf4ba5b0097396e Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 11 Sep 2019 17:02:09 -0400 Subject: [PATCH 061/373] fixed Rayami, First of the Fallen replacement effect not applying --- .../mage/cards/r/RayamiFirstOfTheFallen.java | 40 +++++++++---------- 1 file changed, 20 insertions(+), 20 deletions(-) diff --git a/Mage.Sets/src/mage/cards/r/RayamiFirstOfTheFallen.java b/Mage.Sets/src/mage/cards/r/RayamiFirstOfTheFallen.java index 1aa9e4d039..dcdac69a32 100644 --- a/Mage.Sets/src/mage/cards/r/RayamiFirstOfTheFallen.java +++ b/Mage.Sets/src/mage/cards/r/RayamiFirstOfTheFallen.java @@ -18,6 +18,7 @@ import mage.game.permanent.Permanent; import mage.game.permanent.PermanentToken; import mage.players.Player; +import java.util.Collection; import java.util.UUID; /** @@ -76,25 +77,24 @@ class RayamiFirstOfTheFallenEffect extends ContinuousEffectImpl { .stream() .filter(Card::isCreature) .filter(card -> card.getCounters(game).getCount(CounterType.BLOOD) > 0) - .forEach(card -> { - card.getAbilities(game).stream().forEach(ability -> { - if (ability instanceof FlyingAbility - || ability instanceof FirstStrikeAbility - || ability instanceof DoubleStrikeAbility - || ability instanceof DeathtouchAbility - || ability instanceof HasteAbility - || ability instanceof HexproofAbility - || ability instanceof IndestructibleAbility - || ability instanceof LifelinkAbility - || ability instanceof MenaceAbility - || ability instanceof ReachAbility - || ability instanceof TrampleAbility - || ability instanceof VigilanceAbility) { - sourcePermanent.addAbility(ability, source.getSourceId(), game); - } else if (ability instanceof ProtectionAbility) { - sourcePermanent.addAbility(ability, source.getSourceId(), game); - } - }); + .map(card -> card.getAbilities(game)) + .flatMap(Collection::stream) + .forEach(ability -> { + if (ability instanceof FlyingAbility + || ability instanceof FirstStrikeAbility + || ability instanceof DoubleStrikeAbility + || ability instanceof DeathtouchAbility + || ability instanceof HasteAbility + || ability instanceof HexproofAbility + || ability instanceof IndestructibleAbility + || ability instanceof LifelinkAbility + || ability instanceof MenaceAbility + || ability instanceof ReachAbility + || ability instanceof TrampleAbility + || ability instanceof VigilanceAbility + || ability instanceof ProtectionAbility) { + sourcePermanent.addAbility(ability, source.getSourceId(), game); + } }); return true; } @@ -108,7 +108,7 @@ class RayamiFirstOfTheFallenEffect extends ContinuousEffectImpl { class RayamiFirstOfTheFallenReplacementEffect extends ReplacementEffectImpl { RayamiFirstOfTheFallenReplacementEffect() { - super(Duration.EndOfTurn, Outcome.Exile); + super(Duration.WhileOnBattlefield, Outcome.Exile); staticText = "If a nontoken creature would die, exile that card with a blood counter on it instead"; } From 30e767d80cacc3ea0aa685a705b5e0e46b73aeff Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 11 Sep 2019 18:07:43 -0400 Subject: [PATCH 062/373] Implemented Robber of the Rich --- .../src/mage/cards/r/RobberOfTheRich.java | 250 ++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 251 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/r/RobberOfTheRich.java diff --git a/Mage.Sets/src/mage/cards/r/RobberOfTheRich.java b/Mage.Sets/src/mage/cards/r/RobberOfTheRich.java new file mode 100644 index 0000000000..783d97b909 --- /dev/null +++ b/Mage.Sets/src/mage/cards/r/RobberOfTheRich.java @@ -0,0 +1,250 @@ +package mage.cards.r; + +import mage.MageInt; +import mage.MageObject; +import mage.abilities.Ability; +import mage.abilities.common.AttacksTriggeredAbility; +import mage.abilities.condition.Condition; +import mage.abilities.decorator.ConditionalInterveningIfTriggeredAbility; +import mage.abilities.effects.AsThoughEffectImpl; +import mage.abilities.effects.AsThoughManaEffect; +import mage.abilities.effects.ContinuousEffect; +import mage.abilities.effects.OneShotEffect; +import mage.abilities.keyword.HasteAbility; +import mage.abilities.keyword.ReachAbility; +import mage.cards.Card; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.*; +import mage.game.ExileZone; +import mage.game.Game; +import mage.game.events.GameEvent; +import mage.game.permanent.Permanent; +import mage.players.ManaPoolItem; +import mage.players.Player; +import mage.target.targetpointer.FixedTarget; +import mage.util.CardUtil; +import mage.watchers.Watcher; + +import java.util.HashSet; +import java.util.Objects; +import java.util.Set; +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class RobberOfTheRich extends CardImpl { + + public RobberOfTheRich(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{1}{R}"); + + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.ARCHER); + this.subtype.add(SubType.ROGUE); + this.power = new MageInt(2); + this.toughness = new MageInt(2); + + // Reach + this.addAbility(ReachAbility.getInstance()); + + // Haste + this.addAbility(HasteAbility.getInstance()); + + // Whenever Robber of the Rich attacks, if defending player has more cards in hand than you, exile the top card of their library. During any turn you attacked with a Rogue, you may cast that card and you may spend mana as though it were mana of any color to cast that spell. + this.addAbility(new ConditionalInterveningIfTriggeredAbility( + new AttacksTriggeredAbility( + new RobberOfTheRichEffect(), false, "", SetTargetPointer.PLAYER + ), RobberOfTheRichCondition.instance, "Whenever {this} attacks, " + + "if defending player has more cards in hand than you, exile the top card of their library. " + + "During any turn you attacked with a Rogue, you may cast that card and " + + "you may spend mana as though it were mana of any color to cast that spell." + ), new RobberOfTheRichWatcher()); + } + + private RobberOfTheRich(final RobberOfTheRich card) { + super(card); + } + + @Override + public RobberOfTheRich copy() { + return new RobberOfTheRich(this); + } +} + +enum RobberOfTheRichCondition implements Condition { + instance; + + @Override + public boolean apply(Game game, Ability source) { + Player controller = game.getPlayer(source.getControllerId()); + Player player = game.getPlayer(game.getCombat().getDefendingPlayerId(source.getSourceId(), game)); + return controller != null && player != null && controller.getHand().size() < player.getHand().size(); + } +} + +class RobberOfTheRichEffect extends OneShotEffect { + + RobberOfTheRichEffect() { + super(Outcome.PutCreatureInPlay); + } + + private RobberOfTheRichEffect(final RobberOfTheRichEffect effect) { + super(effect); + } + + @Override + public RobberOfTheRichEffect copy() { + return new RobberOfTheRichEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + Player controller = game.getPlayer(source.getControllerId()); + Player damagedPlayer = game.getPlayer(this.getTargetPointer().getFirst(game, source)); + if (controller == null || damagedPlayer == null) { + return false; + } + MageObject sourceObject = game.getObject(source.getSourceId()); + UUID exileId = CardUtil.getCardExileZoneId(game, source); + Card card = damagedPlayer.getLibrary().getFromTop(game); + if (card == null || sourceObject == null) { + return true; + } + // move card to exile + controller.moveCardToExileWithInfo(card, exileId, sourceObject.getIdName(), source.getSourceId(), game, Zone.LIBRARY, true); + // Add effects only if the card has a spellAbility (e.g. not for lands). + if (card.getSpellAbility() == null) { + return true; + } + // allow to cast the card + game.addEffect(new RobberOfTheRichCastFromExileEffect(card.getId(), exileId), source); + // and you may spend mana as though it were mana of any color to cast it + ContinuousEffect effect = new RobberOfTheRichSpendAnyManaEffect(); + effect.setTargetPointer(new FixedTarget(card.getId())); + game.addEffect(effect, source); + return true; + } +} + +class RobberOfTheRichCastFromExileEffect extends AsThoughEffectImpl { + + private UUID cardId; + private UUID exileId; + + RobberOfTheRichCastFromExileEffect(UUID cardId, UUID exileId) { + super(AsThoughEffectType.PLAY_FROM_NOT_OWN_HAND_ZONE, Duration.Custom, Outcome.Benefit); + this.cardId = cardId; + this.exileId = exileId; + } + + private RobberOfTheRichCastFromExileEffect(final RobberOfTheRichCastFromExileEffect effect) { + super(effect); + this.cardId = effect.cardId; + this.exileId = effect.exileId; + } + + @Override + public boolean apply(Game game, Ability source) { + return true; + } + + @Override + public RobberOfTheRichCastFromExileEffect copy() { + return new RobberOfTheRichCastFromExileEffect(this); + } + + @Override + public boolean applies(UUID sourceId, Ability source, UUID affectedControllerId, Game game) { + RobberOfTheRichWatcher watcher = game.getState().getWatcher(RobberOfTheRichWatcher.class); + if (watcher == null || !watcher.getAttackedWithRogue(source.getControllerId())) { + return false; + } + if (!sourceId.equals(cardId) || !source.isControlledBy(affectedControllerId)) { + return false; + } + ExileZone exileZone = game.getState().getExile().getExileZone(exileId); + if (exileZone != null && exileZone.contains(cardId)) { + return true; + } + discard(); + return false; + } +} + +class RobberOfTheRichSpendAnyManaEffect extends AsThoughEffectImpl implements AsThoughManaEffect { + + RobberOfTheRichSpendAnyManaEffect() { + super(AsThoughEffectType.SPEND_OTHER_MANA, Duration.Custom, Outcome.Benefit); + } + + private RobberOfTheRichSpendAnyManaEffect(final RobberOfTheRichSpendAnyManaEffect effect) { + super(effect); + } + + @Override + public boolean apply(Game game, Ability source) { + return true; + } + + @Override + public RobberOfTheRichSpendAnyManaEffect copy() { + return new RobberOfTheRichSpendAnyManaEffect(this); + } + + @Override + public boolean applies(UUID objectId, Ability source, UUID affectedControllerId, Game game) { + return source.isControlledBy(affectedControllerId) + && Objects.equals(objectId, ((FixedTarget) getTargetPointer()).getTarget()) + && ((FixedTarget) getTargetPointer()).getZoneChangeCounter() + 1 == game.getState().getZoneChangeCounter(objectId) + && (((FixedTarget) getTargetPointer()).getZoneChangeCounter() + 1 == game.getState().getZoneChangeCounter(objectId)) + && game.getState().getZone(objectId) == Zone.STACK; + } + + @Override + public ManaType getAsThoughManaType(ManaType manaType, ManaPoolItem mana, UUID affectedControllerId, Ability source, Game game) { + return mana.getFirstAvailable(); + } +} + +class RobberOfTheRichWatcher extends Watcher { + + private Set rogueAttackers = new HashSet(); + + RobberOfTheRichWatcher() { + super(WatcherScope.GAME); + } + + private RobberOfTheRichWatcher(final RobberOfTheRichWatcher watcher) { + super(watcher); + this.rogueAttackers.addAll(watcher.rogueAttackers); + } + + @Override + public RobberOfTheRichWatcher copy() { + return new RobberOfTheRichWatcher(this); + } + + @Override + public void watch(GameEvent event, Game game) { + if (event.getType() != GameEvent.EventType.ATTACKER_DECLARED) { + return; + } + Permanent permanent = game.getPermanent(event.getSourceId()); + if (permanent == null || !permanent.hasSubtype(SubType.ROGUE, game)) { + return; + } + rogueAttackers.add(event.getPlayerId()); + } + + @Override + public void reset() { + super.reset(); + rogueAttackers.clear(); + } + + boolean getAttackedWithRogue(UUID playerId) { + return rogueAttackers.contains(playerId); + } +} + diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index be24c2f0b7..28949b70a3 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -98,6 +98,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Questing Beast", 171, Rarity.MYTHIC, mage.cards.q.QuestingBeast.class)); cards.add(new SetCardInfo("Rankle, Master of Pranks", 101, Rarity.MYTHIC, mage.cards.r.RankleMasterOfPranks.class)); cards.add(new SetCardInfo("Return to Nature", 173, Rarity.COMMON, mage.cards.r.ReturnToNature.class)); + cards.add(new SetCardInfo("Robber of the Rich", 138, Rarity.MYTHIC, mage.cards.r.RobberOfTheRich.class)); cards.add(new SetCardInfo("Rosethorn Acolyte", 174, Rarity.COMMON, mage.cards.r.RosethornAcolyte.class)); cards.add(new SetCardInfo("Roving Keep", 228, Rarity.COMMON, mage.cards.r.RovingKeep.class)); cards.add(new SetCardInfo("Rowan's Battleguard", 306, Rarity.UNCOMMON, mage.cards.r.RowansBattleguard.class)); From c6e929694c79897e6b851df5bf13165c883b0353 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 11 Sep 2019 18:18:34 -0400 Subject: [PATCH 063/373] updated ELD spoiler and reprints --- Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 2 ++ Utils/mtg-cards-data.txt | 11 ++++++++++- 2 files changed, 12 insertions(+), 1 deletion(-) diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 28949b70a3..f69f0b22c6 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -93,11 +93,13 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Oko, Thief of Crowns", 197, Rarity.MYTHIC, mage.cards.o.OkoThiefOfCrowns.class)); cards.add(new SetCardInfo("Oko, the Trickster", 309, Rarity.MYTHIC, mage.cards.o.OkoTheTrickster.class)); cards.add(new SetCardInfo("Once Upon a Time", 169, Rarity.RARE, mage.cards.o.OnceUponATime.class)); + cards.add(new SetCardInfo("Opt", 59, Rarity.COMMON, mage.cards.o.Opt.class)); cards.add(new SetCardInfo("Order of Midnight", 99, Rarity.UNCOMMON, mage.cards.o.OrderOfMidnight.class)); cards.add(new SetCardInfo("Piper of the Swarm", 100, Rarity.RARE, mage.cards.p.PiperOfTheSwarm.class)); cards.add(new SetCardInfo("Questing Beast", 171, Rarity.MYTHIC, mage.cards.q.QuestingBeast.class)); cards.add(new SetCardInfo("Rankle, Master of Pranks", 101, Rarity.MYTHIC, mage.cards.r.RankleMasterOfPranks.class)); cards.add(new SetCardInfo("Return to Nature", 173, Rarity.COMMON, mage.cards.r.ReturnToNature.class)); + cards.add(new SetCardInfo("Righteousness", 27, Rarity.UNCOMMON, mage.cards.r.Righteousness.class)); cards.add(new SetCardInfo("Robber of the Rich", 138, Rarity.MYTHIC, mage.cards.r.RobberOfTheRich.class)); cards.add(new SetCardInfo("Rosethorn Acolyte", 174, Rarity.COMMON, mage.cards.r.RosethornAcolyte.class)); cards.add(new SetCardInfo("Roving Keep", 228, Rarity.COMMON, mage.cards.r.RovingKeep.class)); diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index a32852a21f..d32201ff29 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -35994,13 +35994,17 @@ Swamp|Commander 2019|294|C||Basic Land - Swamp|||({T}: Add {B}.)| Mountain|Commander 2019|297|C||Basic Land - Mountain|||({T}: Add {R}.)| Forest|Commander 2019|300|C||Basic Land - Forest|||({T}: Add {G}.)| All That Glitters|Throne of Eldraine|2|U|{1}{W}|Enchantment - Aura|||Enchant creature$Enchanted creature gets +1/+1 for each artifact and/or enchantment you control.| +Beloved Princess|Throne of Eldraine|7|C|{W}|Creature - Human Noble|1|1|Lifelink$Beloved Princess can't be blocked by creatures with power 3 or greater.| The Circle of Loyalty|Throne of Eldraine|9|M|{4}{W}{W}|Legendary Artifact|||This spell costs {1} less to cast for each Knight you control.$Creatures you control get +1/+1.$Whenever you cast a legendary spell, create a 2/2 white Knight creature token with vigilance.${3}{W}, {T}: Create a 2/2 white Knight creature token with vigilance.| Faerie Guidemother|Throne of Eldraine|11|C|{W}|Creature - Faerie|1|1|Flying| Gift of the Fae|Throne of Eldraine|11|C|{1}{W}|Sorcery - Adventure|1|1|Target creature gets +2/+1 and gains flying until end of turn.| Chop Down|Throne of Eldraine|14|R|{2}{W}|Instant - Adventure|1|2|Destroy target creature with power 4 or greater.| Giant Killer|Throne of Eldraine|14|R|{W}|Creature - Human Peasant|1|2|{1}{W}, {T}: Tap target creature.| +Harmoninous Archon|Throne of Eldraine|17|M|{4}{W}{W}|Creature - Archon|4|5|Flying$Non-Archon creatures have base power and toughness 3/3.$When Harmoninous Archon enters the battlefield, create two 1/1 white Human creature tokens.| +Righteousness|Throne of Eldraine|27|U|{W}|Instant|||Target blocking creature gets +7/+7 until end of turn.| Shining Armor|Throne of Eldraine|29|C|{1}{W}|Artifact - Equipment|||Flash$When Shining Armor enters the battlefield, attach it to target Knight you control.$Equipped creature gets +0/+2 and has vigilance.$Equip {3}| Silverflame Ritual|Throne of Eldraine|30|C|{3}{W}|Sorcery|||Put a +1/+1 counter on each creature you control.$Adamant — If at least three white mana was spent to cast this spell, creatures you control gain vigilance until end of turn.| +True Love's Kiss|Throne of Eldraine|34|C|{2}{W}{W}|Instant|||Exile target artifact or enchantment.$Draw a card| Venerable Knight|Throne of Eldraine|35|U|{W}|Creature - Human Knight|2|1|When Venerable Knight dies, put a +1/+1 counter on target Knight you control.| Worthy Knight|Throne of Eldraine|36|R|{1}{W}|Creature - Human Knight|2|2|Whenever you cast a Knight spell, create a 1/1 white Human creature token.| Animating Faerie|Throne of Eldraine|38|U|{2}{U}|Creature - Faerie|2|2|Flying| @@ -36013,13 +36017,14 @@ Hypnotic Sprite|Throne of Eldraine|49|U|{U}{U}|Creature - Faerie|2|1|Flying| Mesmeric Glare|Throne of Eldraine|49|U|{2}{U}|Instant - Adventure|2|1|Counter target spell with converted mana cost 3 or less.| Midnight Clock|Throne of Eldraine|54|R|{2}{U}|Artifact|||{T}: Add {U}.${2}{U}: Put an hour counter on Midnight Clock.$At the beginning of each upkeep, put an hour counter on Midnight Clock.$When the twelfth hour counter is put on Midnight Clock, shuffle your hand and graveyard into your library, then draw seven cards. Exile Midnight Clock.| Mystical Dispute|Throne of Eldraine|58|U|{2}{U}|Instant|||This spell costs {2} less to cast if it targets a blue spell.$Counter target spell unless its controller pays {3}.| +Opt|Throne of Eldraine|59|C|{U}|Instant|||Scry 1.$Draw a card.| Run Away Together|Throne of Eldraine|62|C|{1}{U}|Instant|||Choose two target creatures controlled by different players. Return those creatures to their owners' hands.| Syr Elenora the Discerning|Throne of Eldraine|67|U|{3}{U}{U}|Legendary Creature - Human Knight|*|4|Syr Elenora the Discerning's power is equal to the number of cards in your hand.$When Syr Elenora enters the battlefield, draw a card.$Spells your opponents cast that target Syr Elenora cost {2} more to cast.| Tome Raider|Throne of Eldraine|68|C|{2}{U}|Creature - Faerie|1|1|Flying$When Tome Raider enters the battlefield, draw a card.| Turn into a Pumpkin|Throne of Eldraine|69|U|{3}{U}|Instant|||Return target nonland permanent to its owner's hand. Draw a card.$Adamant — If at least three blue mana was spent to cast this spell, create a Food token.| Wishful Merfolk|Throne of Eldraine|73|C|{1}{U}|Creature - Merfolk|3|2|Defender${1}{U}: Wishful Merfolk loses defender and becomes a Human until end of turn.| Witching Well|Throne of Eldraine|74|C|{U}|Artifact|||When Witching Well enters the battlefield, scry 2.${3}{U}, Sacrifice Witching Well: Draw two cards.| -Ayara, First of Locthwain|Throne of Eldraine|75|R|{B}{B}{B}|Legendary Creature - Elf Noble|||Whenever Ayara, First of Locthwain or another black creature enters the battlefield under your control, each opponent loses 1 life and you gain 1 life.${T}, Sacrifice another black creature: Draw a card.| +Ayara, First of Locthwain|Throne of Eldraine|75|R|{B}{B}{B}|Legendary Creature - Elf Noble|2|3|Whenever Ayara, First of Locthwain or another black creature enters the battlefield under your control, each opponent loses 1 life and you gain 1 life.${T}, Sacrifice another black creature: Draw a card.| Bake into a Pie|Throne of Eldraine|76|C|{2}{B}{B}|Instant|||Destroy target creature. Create a Food token.| Belle of the Brawl|Throne of Eldraine|78|U|{2}{B}|Creature - Human Knight|3|2|Menace$Whenever Belle of the Brawl attacks, other Knights you control get +1/+0 until end of turn.| Clackbridge Troll|Throne of Eldraine|84|R|{3}{B}{B}|Creature - Troll|8|8|Trample, haste$When Clackbridge Troll enters the battlefield, target opponent creates three 0/1 white Goat creature tokens.$At the beginning of combat on your turn, any opponent may sacrifice a creature. If a player does, tap Clackbridge Troll, you gain 3 life, and you draw a card.| @@ -36050,6 +36055,7 @@ Embereth Shieldbreaker|Throne of Eldraine|122|U|{1}{R}|Creature - Human Knight|2 Joust|Throne of Eldraine|129|U|{1}{R}|Sorcery|||Choose target creature you control and target creature you don't control. The creature you control gets +2/+1 until end of turn if it's a Knight. Then those creatures fight each other.| Robber of the Rich|Throne of Eldraine|138|M|{1}{R}|Creature - Human Archer Rogue|2|2|Reach, haste$Whenever Robber of the Rich attacks, if defending player has more cards in hand than you, exile the top card of their library. During any turn you attacked with a Rogue, you may cast that card and you may spend mana as though it were mana of any color to cast that spell.| Scorching Dragonfire|Throne of Eldraine|139|C|{1}{R}|Instant|||Scorching Dragonfire deals 3 damage to target creature or planeswalker. If that creature or planeswalker would die this turn, exile it instead.| +Seven Dwarves|Throne of Eldraine|141|C|{1}{R}|Creature - Dwarf|2|2|Seven Dwarves gets +1/+1 for each other creature named Seven Dwarves you control.$A deck can have up to seven cards named Seven Dwarves.| Skullknocker Ogre|Throne of Eldraine|142|U|{3}{R}|Creature - Ogre|4|3|Whenever Skullknocker Ogre deals damage to an opponent, that player discards a card at random. If the player does, they draw a card.| Slaying Fire|Throne of Eldraine|143|U|{2}{R}|Instant|||Slaying Fire deals 3 damage to any target.$Adamant — If at least three red mana was spent to cast this spell, it deals 4 damage instead.| Weaselback Redcap|Throne of Eldraine|148|C|{R}|Creature - Goblin Knight|1|1|{1}{R}: Weaselback Redcap gets +2/+0 until end of turn.| @@ -36087,10 +36093,13 @@ Fireborn Knight|Throne of Eldraine|210|U|{R/W}{R/W}{R/W}{R/W}|Creature - Human K Bring Back|Throne of Eldraine|212|U|{G/W}{G/W}{G/W}{G/W}|Sorcery - Adventure|2|2|Create two 1/1 white Human creature tokens.| Oakhame Ranger|Throne of Eldraine|212|U|{G/W}{G/W}{G/W}{G/W}|Creature - Elf Knight|2|2|{T}: Creatures you control get +1/+1 until end of turn.| Enchanted Carriage|Throne of Eldraine|218|U|{5}|Artifact - Vehicle|4|4|When Enchanted Carriage enters the battlefield, create two 1/1 white Mouse creature tokens.$Crew 2| +Gingerbrute|Throne of Eldraine|219|C|{1}|Artifact Creature - Food Golem|1|1|Haste${1}: Gingerbrute can't be blocked this turn except by creatures with haste.${2}, {T}, Sacrifice Gingerbrute: You gain 3 life.| Golden Egg|Throne of Eldraine|220|C|{2}|Artifact - Food|||When Golden Egg enters the battlefield, draw a card.${1}, {T}, Sacrifice Golden Egg: Add one mana of any color.${2}, {T}, Sacrifice Golden Egg: You gain 3 life.| Heraldic Banner|Throne of Eldraine|222|U|{3}|Artifact|||As Heraldic Banner enters the battlefield, choose a color.$Creatures you control of the chosen color get +1/+0.${T}: Add one mana of the chosen color.| +Inquisitive Puppet|Throne of Eldraine|223|U|{1}|Artifact Creature - Construct|0|2|When Inquisitive Puppet enters the battlefield, scry 1.$Exile Inquisitive Puppet: Create a 1/1 white Human creature token.| Jousting Dummy|Throne of Eldraine|224|C|{2}|Artifact Creature - Scarecrow Knight|2|1|{3}: Jousting Dummy gets +1/+0 until end of turn.| Roving Keep|Throne of Eldraine|228|C|{7}|Artifact Creature - Wall|5|7|Defender${7}: Roving Keep gets +2/+0 and gains trample until end of turn. It can attack this turn as though it didn't have defender.| +Spinning Wheel|Throne of Eldraine|234|U|{3}|Artifact|||{T}: Add one mana of any color.${5}, {T}: Tap target creature.| Witch's Oven|Throne of Eldraine|237|U|{1}|Artifact|||{T}, Sacrifice a creature: Create a Food token. If the sacrificed creature's toughness was 4 or greater, create two Food tokens instead.| Tournament Grounds|Throne of Eldraine|248|U||Land|||{T}: Add {C}.${T}: Add {R}, {W}, or {B}. Spend this mana only to cast a Knight or Equipment spell.| Witch's Cottage|Throne of Eldraine|249|C||Land - Swamp|||({T}: Add {B}.)$Witch's Cottage enters the battlefield tapped unless you control three or more other Swamps.$When Witch's Cottage enters the battlefield untapped, you may put target creature card from your graveyard on top of your library.| From 329f6eae9017dc107ac6ff83cf427937d960943f Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 11 Sep 2019 18:20:37 -0400 Subject: [PATCH 064/373] Implemented Inquisitive Puppet --- .../src/mage/cards/i/InquisitivePuppet.java | 44 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 45 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/i/InquisitivePuppet.java diff --git a/Mage.Sets/src/mage/cards/i/InquisitivePuppet.java b/Mage.Sets/src/mage/cards/i/InquisitivePuppet.java new file mode 100644 index 0000000000..9de9edf129 --- /dev/null +++ b/Mage.Sets/src/mage/cards/i/InquisitivePuppet.java @@ -0,0 +1,44 @@ +package mage.cards.i; + +import mage.MageInt; +import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.costs.common.ExileSourceCost; +import mage.abilities.effects.common.CreateTokenEffect; +import mage.abilities.effects.keyword.ScryEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.game.permanent.token.HumanToken; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class InquisitivePuppet extends CardImpl { + + public InquisitivePuppet(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT, CardType.CREATURE}, "{1}"); + + this.subtype.add(SubType.CONSTRUCT); + this.power = new MageInt(0); + this.toughness = new MageInt(2); + + // When Inquisitive Puppet enters the battlefield, scry 1. + this.addAbility(new EntersBattlefieldTriggeredAbility(new ScryEffect(1))); + + // Exile Inquisitive Puppet: Create a 1/1 white Human creature token. + this.addAbility(new SimpleActivatedAbility(new CreateTokenEffect(new HumanToken()), new ExileSourceCost())); + } + + private InquisitivePuppet(final InquisitivePuppet card) { + super(card); + } + + @Override + public InquisitivePuppet copy() { + return new InquisitivePuppet(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index f69f0b22c6..772afdda02 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -73,6 +73,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Golden Egg", 220, Rarity.COMMON, mage.cards.g.GoldenEgg.class)); cards.add(new SetCardInfo("Heraldic Banner", 222, Rarity.UNCOMMON, mage.cards.h.HeraldicBanner.class)); cards.add(new SetCardInfo("Hypnotic Sprite", 49, Rarity.UNCOMMON, mage.cards.h.HypnoticSprite.class)); + cards.add(new SetCardInfo("Inquisitive Puppet", 223, Rarity.UNCOMMON, mage.cards.i.InquisitivePuppet.class)); cards.add(new SetCardInfo("Inspiring Veteran", 194, Rarity.UNCOMMON, mage.cards.i.InspiringVeteran.class)); cards.add(new SetCardInfo("Joust", 129, Rarity.UNCOMMON, mage.cards.j.Joust.class)); cards.add(new SetCardInfo("Jousting Dummy", 224, Rarity.COMMON, mage.cards.j.JoustingDummy.class)); From 1c17356a834ab97116dd00d7b41237bc32449ad7 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 11 Sep 2019 18:23:44 -0400 Subject: [PATCH 065/373] Implemented True Love's Kiss --- Mage.Sets/src/mage/cards/t/TrueLovesKiss.java | 37 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 38 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/t/TrueLovesKiss.java diff --git a/Mage.Sets/src/mage/cards/t/TrueLovesKiss.java b/Mage.Sets/src/mage/cards/t/TrueLovesKiss.java new file mode 100644 index 0000000000..98d92a92ab --- /dev/null +++ b/Mage.Sets/src/mage/cards/t/TrueLovesKiss.java @@ -0,0 +1,37 @@ +package mage.cards.t; + +import mage.abilities.effects.common.DrawCardSourceControllerEffect; +import mage.abilities.effects.common.ExileTargetEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.filter.StaticFilters; +import mage.target.TargetPermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class TrueLovesKiss extends CardImpl { + + public TrueLovesKiss(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.INSTANT}, "{2}{W}{W}"); + + // Exile target artifact or enchantment. + this.getSpellAbility().addEffect(new ExileTargetEffect()); + this.getSpellAbility().addTarget(new TargetPermanent(StaticFilters.FILTER_PERMANENT_ARTIFACT_OR_ENCHANTMENT)); + + // Draw a card + this.getSpellAbility().addEffect(new DrawCardSourceControllerEffect(1)); + } + + private TrueLovesKiss(final TrueLovesKiss card) { + super(card); + } + + @Override + public TrueLovesKiss copy() { + return new TrueLovesKiss(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 772afdda02..46aabff232 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -131,6 +131,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Tome Raider", 68, Rarity.COMMON, mage.cards.t.TomeRaider.class)); cards.add(new SetCardInfo("Tome of Legends", 332, Rarity.RARE, mage.cards.t.TomeOfLegends.class)); cards.add(new SetCardInfo("Tournament Grounds", 248, Rarity.UNCOMMON, mage.cards.t.TournamentGrounds.class)); + cards.add(new SetCardInfo("True Love's Kiss", 34, Rarity.COMMON, mage.cards.t.TrueLovesKiss.class)); cards.add(new SetCardInfo("Turn into a Pumpkin", 69, Rarity.UNCOMMON, mage.cards.t.TurnIntoAPumpkin.class)); cards.add(new SetCardInfo("Venerable Knight", 35, Rarity.UNCOMMON, mage.cards.v.VenerableKnight.class)); cards.add(new SetCardInfo("Weaselback Redcap", 148, Rarity.COMMON, mage.cards.w.WeaselbackRedcap.class)); From ced6baadd70ebbd41a19386c479a92a9211a096f Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 11 Sep 2019 18:28:48 -0400 Subject: [PATCH 066/373] Implemented Spinning Wheel --- Mage.Sets/src/mage/cards/s/SpinningWheel.java | 42 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 43 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/s/SpinningWheel.java diff --git a/Mage.Sets/src/mage/cards/s/SpinningWheel.java b/Mage.Sets/src/mage/cards/s/SpinningWheel.java new file mode 100644 index 0000000000..f74bb2d6c8 --- /dev/null +++ b/Mage.Sets/src/mage/cards/s/SpinningWheel.java @@ -0,0 +1,42 @@ +package mage.cards.s; + +import mage.abilities.Ability; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.costs.common.TapSourceCost; +import mage.abilities.costs.mana.GenericManaCost; +import mage.abilities.effects.common.TapTargetEffect; +import mage.abilities.mana.AnyColorManaAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.target.common.TargetCreaturePermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class SpinningWheel extends CardImpl { + + public SpinningWheel(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT}, "{3}"); + + // {T}: Add one mana of any color. + this.addAbility(new AnyColorManaAbility()); + + // {5}, {T}: Tap target creature. + Ability ability = new SimpleActivatedAbility(new TapTargetEffect(), new GenericManaCost(5)); + ability.addCost(new TapSourceCost()); + ability.addTarget(new TargetCreaturePermanent()); + this.addAbility(ability); + } + + private SpinningWheel(final SpinningWheel card) { + super(card); + } + + @Override + public SpinningWheel copy() { + return new SpinningWheel(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 46aabff232..b62120e017 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -118,6 +118,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Skullknocker Ogre", 142, Rarity.UNCOMMON, mage.cards.s.SkullknockerOgre.class)); cards.add(new SetCardInfo("Slaying Fire", 143, Rarity.UNCOMMON, mage.cards.s.SlayingFire.class)); cards.add(new SetCardInfo("Smitten Swordmaster", 105, Rarity.COMMON, mage.cards.s.SmittenSwordmaster.class)); + cards.add(new SetCardInfo("Spinning Wheel", 234, Rarity.UNCOMMON, mage.cards.s.SpinningWheel.class)); cards.add(new SetCardInfo("Steelbane Hydra", 322, Rarity.RARE, mage.cards.s.SteelbaneHydra.class)); cards.add(new SetCardInfo("Steelclaw Lance", 202, Rarity.UNCOMMON, mage.cards.s.SteelclawLance.class)); cards.add(new SetCardInfo("Syr Elenora the Discerning", 67, Rarity.UNCOMMON, mage.cards.s.SyrElenoraTheDiscerning.class)); From c0dbd38096895d904f156c927812700fe62381ac Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 11 Sep 2019 19:25:44 -0400 Subject: [PATCH 067/373] updated ELD spoiler --- Utils/mtg-cards-data.txt | 17 ++++++++++++++++- 1 file changed, 16 insertions(+), 1 deletion(-) diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index d32201ff29..adc0d1d684 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -36000,7 +36000,7 @@ Faerie Guidemother|Throne of Eldraine|11|C|{W}|Creature - Faerie|1|1|Flying| Gift of the Fae|Throne of Eldraine|11|C|{1}{W}|Sorcery - Adventure|1|1|Target creature gets +2/+1 and gains flying until end of turn.| Chop Down|Throne of Eldraine|14|R|{2}{W}|Instant - Adventure|1|2|Destroy target creature with power 4 or greater.| Giant Killer|Throne of Eldraine|14|R|{W}|Creature - Human Peasant|1|2|{1}{W}, {T}: Tap target creature.| -Harmoninous Archon|Throne of Eldraine|17|M|{4}{W}{W}|Creature - Archon|4|5|Flying$Non-Archon creatures have base power and toughness 3/3.$When Harmoninous Archon enters the battlefield, create two 1/1 white Human creature tokens.| +Harmonious Archon|Throne of Eldraine|17|M|{4}{W}{W}|Creature - Archon|4|5|Flying$Non-Archon creatures have base power and toughness 3/3.$When Harmonious Archon enters the battlefield, create two 1/1 white Human creature tokens.| Righteousness|Throne of Eldraine|27|U|{W}|Instant|||Target blocking creature gets +7/+7 until end of turn.| Shining Armor|Throne of Eldraine|29|C|{1}{W}|Artifact - Equipment|||Flash$When Shining Armor enters the battlefield, attach it to target Knight you control.$Equipped creature gets +0/+2 and has vigilance.$Equip {3}| Silverflame Ritual|Throne of Eldraine|30|C|{3}{W}|Sorcery|||Put a +1/+1 counter on each creature you control.$Adamant — If at least three white mana was spent to cast this spell, creatures you control gain vigilance until end of turn.| @@ -36013,6 +36013,7 @@ Corridor Monitor|Throne of Eldraine|41|C|{1}{U}|Artifact Creature - Construct|1| Emry, Lurker of the Loch|Throne of Eldraine|43|R|{2}{U}|Legendary Creature - Merfolk Wizard|1|2|This spell costs {1} less to cast for each artifact you control.$When Emry, Lurker of the Loch enters the battlefield, put the top four cards of your library into your graveyard.${T}: Choose target artifact card in your graveyard. You may cast that card this turn.| Faerie Vandal|Throne of Eldraine|45|U|{1}{U}|Creature - Faerie Rogue|1|2|Flash$Flying$Whenever you draw your second card each turn, put a +1/+1 counter on Faerie Vandal.| Frogify|Throne of Eldraine|47|U|{1}{U}|Enchantment - Aura|||Enchant creature$Enchanted creature loses all abilities and is a blue Frog creature with base power and toughness 1/1.| +Gadwick, the Wizened|Throne of Eldraine|48|R|{X}{U}{U}{U}|Legendary Creature - Human Wizard|3|3|When Gadwick, the Wizened enters the battlefield, draw X cards.$Whenever you cast a blue spell, tap target nonland permanent an opponent controls.| Hypnotic Sprite|Throne of Eldraine|49|U|{U}{U}|Creature - Faerie|2|1|Flying| Mesmeric Glare|Throne of Eldraine|49|U|{2}{U}|Instant - Adventure|2|1|Counter target spell with converted mana cost 3 or less.| Midnight Clock|Throne of Eldraine|54|R|{2}{U}|Artifact|||{T}: Add {U}.${2}{U}: Put an hour counter on Midnight Clock.$At the beginning of each upkeep, put an hour counter on Midnight Clock.$When the twelfth hour counter is put on Midnight Clock, shuffle your hand and graveyard into your library, then draw seven cards. Exile Midnight Clock.| @@ -36027,7 +36028,10 @@ Witching Well|Throne of Eldraine|74|C|{U}|Artifact|||When Witching Well enters t Ayara, First of Locthwain|Throne of Eldraine|75|R|{B}{B}{B}|Legendary Creature - Elf Noble|2|3|Whenever Ayara, First of Locthwain or another black creature enters the battlefield under your control, each opponent loses 1 life and you gain 1 life.${T}, Sacrifice another black creature: Draw a card.| Bake into a Pie|Throne of Eldraine|76|C|{2}{B}{B}|Instant|||Destroy target creature. Create a Food token.| Belle of the Brawl|Throne of Eldraine|78|U|{2}{B}|Creature - Human Knight|3|2|Menace$Whenever Belle of the Brawl attacks, other Knights you control get +1/+0 until end of turn.| +Bog Naughty|Throne of Eldraine|80|U|{3}{B}{B}|Creature - Faerie|||Flying${2}{B}, Sacrifice a Food: Target creature gets -3/-3 until end of turn.| +Cauldron Familiar|Throne of Eldraine|81|C|{B}|Creature - Cat|1|1|When Cauldron Familiar enters the battlefield, each opponent loses 1 life and you gain 1 life.$Sacrifice a Food: Return Cauldron Familiar from your graveyard to the battlefield.| Clackbridge Troll|Throne of Eldraine|84|R|{3}{B}{B}|Creature - Troll|8|8|Trample, haste$When Clackbridge Troll enters the battlefield, target opponent creates three 0/1 white Goat creature tokens.$At the beginning of combat on your turn, any opponent may sacrifice a creature. If a player does, tap Clackbridge Troll, you gain 3 life, and you draw a card.| +Epic Downfall|Throne of Eldraine|85|U|{1}{B}|Sorcery|||Exile target creature with converted mana cost 3 or greater.| Eye Collector|Throne of Eldraine|86|C|{B}|Creature - Faerie|1|1|Flying$Whenever Eye Collector deals combat damage to a player, each player puts the top card of their library into their graveyard.| Foulmire Knight|Throne of Eldraine|90|U|{B}|Creature - Zombie Knight|1|1|Deathtouch| Profane Insight|Throne of Eldraine|90|U|{2}{B}|Instant - Adventure|1|1|You draw a card and you lose 1 life.| @@ -36052,27 +36056,38 @@ Embercleave|Throne of Eldraine|120|M|{4}{R}{R}|Legendary Artifact - Equipment||| Embereth Paladin|Throne of Eldraine|121|C|{3}{R}|Creature - Human Knight|4|1|Haste$Adamant — If at least three red mana was spent to cast this spell, Embereth Paladin enters the battlefield with a +1/+1 counter on it.| Battle Display|Throne of Eldraine|122|U|{R}|Sorcery - Adventure|2|1|Destroy target artifact.| Embereth Shieldbreaker|Throne of Eldraine|122|U|{1}{R}|Creature - Human Knight|2|1|| +Fervent Champion|Throne of Eldraine|124|R|{R}|Creature - Human Knight|1|1|First strike, haste$Whenever Fervent Champion attacks, another target attacking Knight you control gets +1/+0 until end of turn.$Equip abilities you activate that target Fervent Champion cost {3} less to activate.| Joust|Throne of Eldraine|129|U|{1}{R}|Sorcery|||Choose target creature you control and target creature you don't control. The creature you control gets +2/+1 until end of turn if it's a Knight. Then those creatures fight each other.| +Opportunistic Dragon|Throne of Eldraine|133|R|{2}{R}{R}|Creature - Dragon|4|3|Flying$When Opportunistic Dragon enters the battlefield, choose target Human or artifact an opponent controls. For as long as Opportunistic Dragon remains on the battlefield, gain control of that permanent, it loses all abilities, and it can't attack or block.| Robber of the Rich|Throne of Eldraine|138|M|{1}{R}|Creature - Human Archer Rogue|2|2|Reach, haste$Whenever Robber of the Rich attacks, if defending player has more cards in hand than you, exile the top card of their library. During any turn you attacked with a Rogue, you may cast that card and you may spend mana as though it were mana of any color to cast that spell.| Scorching Dragonfire|Throne of Eldraine|139|C|{1}{R}|Instant|||Scorching Dragonfire deals 3 damage to target creature or planeswalker. If that creature or planeswalker would die this turn, exile it instead.| +Searing Barrage|Throne of Eldraine|140|C|{4}{R}|Instant|||Searing Barrage deals 5 damage to target creature.$Adamant — If at least three red mana was spent to cast this spell, Searing Barrage deals 3 damage to that creature's controller.| Seven Dwarves|Throne of Eldraine|141|C|{1}{R}|Creature - Dwarf|2|2|Seven Dwarves gets +1/+1 for each other creature named Seven Dwarves you control.$A deck can have up to seven cards named Seven Dwarves.| Skullknocker Ogre|Throne of Eldraine|142|U|{3}{R}|Creature - Ogre|4|3|Whenever Skullknocker Ogre deals damage to an opponent, that player discards a card at random. If the player does, they draw a card.| Slaying Fire|Throne of Eldraine|143|U|{2}{R}|Instant|||Slaying Fire deals 3 damage to any target.$Adamant — If at least three red mana was spent to cast this spell, it deals 4 damage instead.| +Syr Carah, the Bold|Throne of Eldraine|145|U|{3}{R}{R}|Legendary Creature - Human Knight|3|3|When Syr Carah, the Bold or an instant or sorcery spell you control deals damage to a player, exile the top card of your library. You may play that card this turn.${T}: Syr Carah deals 1 damage to any target.| Weaselback Redcap|Throne of Eldraine|148|C|{R}|Creature - Goblin Knight|1|1|{1}{R}: Weaselback Redcap gets +2/+0 until end of turn.| Beanstalk Giant|Throne of Eldraine|149|U|{6}{G}|Creature - Giant|*|*|Beanstalk Giant's power and toughness are each equal to the number of lands you control.| Fertile Footsteps|Throne of Eldraine|149|U|{2}{G}|Sorcery - Adventure|*|*|Search your library for a basic land card, put it onto the battlefield, then shuffle your library.| +Curious Pair|Throne of Eldraine|150|C|{1}{G}|Creature - Human Peasant|1|3|| Feasting Troll King|Throne of Eldraine|152|R|{2}{G}{G}{G}{G}|Creature - Troll Noble|7|6|Vigilance, trample$When Feasting Troll King enters the battlefield, if you cast it from your hand, create three Food tokens.$Sacrifice three Foods: Return Feasting Troll King from your graveyard to the battlefield. Activate this ability only during your turn.| Flaxen Intruder|Throne of Eldraine|155|U|{G}|Creature - Human Berserker|1|2|Whenever Flaxen Intruder deals combat damage to a player, you may sacrifice it. When you do, destroy target artifact or enchantment.| Welcome Home|Throne of Eldraine|155|U|{5}{G}{G}|Sorcery - Adventure|1|2|Create three 2/2 green Bear creature tokens.| +Garenbrig Paladin|Throne of Eldraine|157|C|{4}{G}|Creature - Giant Knight|4|4|Adamant — If at least three green mana was spent to cast this spell, Garenbrig Paladin enters the battlefield with a +1/+1 counter on it.$Garenbrig Paladin can't be blocked by creatures with power 2 or less.| Gilded Goose|Throne of Eldraine|160|R|{G}|Creature - Bird|0|2|Flying$When Gilded Goose enters the battlefield, create a Food token.${1}{G}, {T}: Create a Food token.${T}, Sacrifice a Food: Add one mana of any color.| +Insatiable Appetite|Throne of Eldraine|162|C|{1}{G}|Instant|||You may sacrifice a Food. If you do, target creature gets +5/+5 until end of turn. Otherwise, that creature gets +3/+3 until end of turn.| Keeper of Fables|Throne of Eldraine|163|U|{3}{G}{G}|Creature - Cat|4|5|Whenever one or more non-Human creatures you control deal combat damage to a player, draw a card.| Heart's Desire|Throne of Eldraine|165|R|{G}|Sorcery - Adventure|5|5|Create a 1/1 white Human creature token.| Lovestruck Beast|Throne of Eldraine|165|R|{2}{G}|Creature - Beast Noble|5|5|Lovestruck Beast can't attack unless you control a 1/1 creature.| +Maraleaf Rider|Throne of Eldraine|166|C|{1}{G}|Creature - Elf Knight|||Sacrifice a Food: Target creature blocks Maraleaf Rider this turn if able.| +Once and Future|Throne of Eldraine|168|U|{3}{G}|Instant|||Return target card from your graveyard to your hand. Put up to one other target card from your graveyard on top of your library. Exile Once and Future.$Adamant — If at least three green mana was spent to cast this spell, instead return those cards to your hand and exile Once and Future.| Once Upon a Time|Throne of Eldraine|169|R|{1}{G}|Instant|||If this spell is the first spell you've cast this game, you may cast it without paying its mana cost.$Look at the top five cards of your library. You may reveal a creature or land card from among them and put it into your hand. Put the rest on the bottom of your library in a random order.| +Outmuscle|Throne of Eldraine|170|C|{3}{G}|Sorcery|||Put a +1/+1 counter on target creature you control, then it fights another target creature you don't control.$Adamant — If at least three green mana was spent to cast this spell, the creature you control gains indestructible until end of turn.| Questing Beast|Throne of Eldraine|171|M|{2}{G}{G}|Legendary Creature - Beast|4|4|Vigilance, deathtouch, haste$Questing Beast can't be blocked by creatures with power 2 or less.$Combat damage that would be dealt by creatures you control can't be prevented.$Whenever Questing Beast deals combat damage to an opponent, it deals that much damage to target planeswalker that player controls.| Return to Nature|Throne of Eldraine|173|C|{1}{G}|Instant|||Choose one —$• Destroy target artifact.$• Destroy target enchantment.$• Exile target card from a graveyard.| Rosethorn Acolyte|Throne of Eldraine|174|C|{2}{G}|Creature - Elf Druid|2|3|{T}: Add one mana of any color.| Seasonal Ritual|Throne of Eldraine|174|C|{G}|Sorcery - Adventure|2|3|Add one mana of any color.| +Trail of Crumbs|Throne of Eldraine|179|U|{1}{G}|Enchantment|||When Trail of Crumbs enters the battlefield, create a Food token.$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.| Wicked Wolf|Throne of Eldraine|181|R|{2}{G}{G}|Creature - Wolf|3|3|When Wicked Wolf enters the battlefield, it fights up to one target creature you don't control.$Sacrifice a Food: Put a +1/+1 counter on Wicked Wolf. It gains indestructible until end of turn. Tap it.| Wildborn Preserver|Throne of Eldraine|182|R|{1}{G}|Creature - Elf Archer|2|2|Flash$Reach$Whenever another non-Human creature enters the battlefield under your control, you may pay {X}. When you do, put X +1/+1 counters on Wildborn Preserver.| Wildwood Tracker|Throne of Eldraine|183|C|{G}|Creature - Elf Warrior|1|1|Whenever Wildwood Tracker attacks or blocks, if you control another non-Human creature, Wildwood Tracker gets +1/+1 until end of turn.| From 0609e8b2e999253ba920de48efbcc0bf39259060 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 11 Sep 2019 19:28:30 -0400 Subject: [PATCH 068/373] Implemented Epic Downfall --- Mage.Sets/src/mage/cards/e/EpicDownfall.java | 43 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 44 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/e/EpicDownfall.java diff --git a/Mage.Sets/src/mage/cards/e/EpicDownfall.java b/Mage.Sets/src/mage/cards/e/EpicDownfall.java new file mode 100644 index 0000000000..79e307b008 --- /dev/null +++ b/Mage.Sets/src/mage/cards/e/EpicDownfall.java @@ -0,0 +1,43 @@ +package mage.cards.e; + +import mage.abilities.effects.common.ExileTargetEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.ComparisonType; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterCreaturePermanent; +import mage.filter.predicate.mageobject.ConvertedManaCostPredicate; +import mage.target.TargetPermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class EpicDownfall extends CardImpl { + + private static final FilterPermanent filter + = new FilterCreaturePermanent("creature with converted mana cost 3 or greater"); + + static { + filter.add(new ConvertedManaCostPredicate(ComparisonType.MORE_THAN, 2)); + } + + public EpicDownfall(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.SORCERY}, "{1}{B}"); + + // Exile target creature with converted mana cost 3 or greater. + this.getSpellAbility().addEffect(new ExileTargetEffect()); + this.getSpellAbility().addTarget(new TargetPermanent(filter)); + } + + private EpicDownfall(final EpicDownfall card) { + super(card); + } + + @Override + public EpicDownfall copy() { + return new EpicDownfall(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index b62120e017..6fa8714f6a 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -56,6 +56,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Embereth Skyblazer", 321, Rarity.RARE, mage.cards.e.EmberethSkyblazer.class)); cards.add(new SetCardInfo("Emry, Lurker of the Loch", 43, Rarity.RARE, mage.cards.e.EmryLurkerOfTheLoch.class)); cards.add(new SetCardInfo("Enchanted Carriage", 218, Rarity.UNCOMMON, mage.cards.e.EnchantedCarriage.class)); + cards.add(new SetCardInfo("Epic Downfall", 85, Rarity.UNCOMMON, mage.cards.e.EpicDownfall.class)); cards.add(new SetCardInfo("Eye Collector", 86, Rarity.COMMON, mage.cards.e.EyeCollector.class)); cards.add(new SetCardInfo("Faerie Formation", 316, Rarity.RARE, mage.cards.f.FaerieFormation.class)); cards.add(new SetCardInfo("Faerie Guidemother", 11, Rarity.COMMON, mage.cards.f.FaerieGuidemother.class)); From e32430bebf6afd67e15a5cfa9f82ceb6aad90221 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 11 Sep 2019 19:36:55 -0400 Subject: [PATCH 069/373] Implemented Curious Pair --- Mage.Sets/src/mage/cards/c/CuriousPair.java | 39 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 40 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/c/CuriousPair.java diff --git a/Mage.Sets/src/mage/cards/c/CuriousPair.java b/Mage.Sets/src/mage/cards/c/CuriousPair.java new file mode 100644 index 0000000000..f63363f9f3 --- /dev/null +++ b/Mage.Sets/src/mage/cards/c/CuriousPair.java @@ -0,0 +1,39 @@ +package mage.cards.c; + +import mage.MageInt; +import mage.abilities.effects.common.CreateTokenEffect; +import mage.cards.AdventureCard; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.game.permanent.token.FoodToken; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class CuriousPair extends AdventureCard { + + public CuriousPair(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, new CardType[]{CardType.SORCERY}, "{1}{G}", "Treats to Share", "{G}"); + + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.PEASANT); + this.power = new MageInt(1); + this.toughness = new MageInt(3); + + // Treats to Share + // Create a Food token. + this.getAdventureSpellAbility().addEffect(new CreateTokenEffect(new FoodToken())); + } + + private CuriousPair(final CuriousPair card) { + super(card); + } + + @Override + public CuriousPair copy() { + return new CuriousPair(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 6fa8714f6a..030f429326 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -49,6 +49,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Command Tower", 333, Rarity.COMMON, mage.cards.c.CommandTower.class)); cards.add(new SetCardInfo("Corridor Monitor", 41, Rarity.COMMON, mage.cards.c.CorridorMonitor.class)); cards.add(new SetCardInfo("Crystal Slipper", 119, Rarity.COMMON, mage.cards.c.CrystalSlipper.class)); + cards.add(new SetCardInfo("Curious Pair", 150, Rarity.COMMON, mage.cards.c.CuriousPair.class)); cards.add(new SetCardInfo("Doom Foretold", 187, Rarity.RARE, mage.cards.d.DoomForetold.class)); cards.add(new SetCardInfo("Embercleave", 120, Rarity.MYTHIC, mage.cards.e.Embercleave.class)); cards.add(new SetCardInfo("Embereth Paladin", 121, Rarity.COMMON, mage.cards.e.EmberethPaladin.class)); From 055632fa4f5383d414e9773f5203769516f1dfac Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 11 Sep 2019 19:42:24 -0400 Subject: [PATCH 070/373] Implemented Beloved Princess --- .../src/mage/cards/b/BelovedPrincess.java | 55 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 56 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/b/BelovedPrincess.java diff --git a/Mage.Sets/src/mage/cards/b/BelovedPrincess.java b/Mage.Sets/src/mage/cards/b/BelovedPrincess.java new file mode 100644 index 0000000000..ecba10b8ae --- /dev/null +++ b/Mage.Sets/src/mage/cards/b/BelovedPrincess.java @@ -0,0 +1,55 @@ +package mage.cards.b; + +import mage.MageInt; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.effects.common.combat.CantBeBlockedByCreaturesSourceEffect; +import mage.abilities.keyword.LifelinkAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.ComparisonType; +import mage.constants.Duration; +import mage.constants.SubType; +import mage.filter.common.FilterCreaturePermanent; +import mage.filter.predicate.mageobject.PowerPredicate; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class BelovedPrincess extends CardImpl { + + private static final FilterCreaturePermanent filter + = new FilterCreaturePermanent("creatures with power 3 or greater"); + + static { + filter.add(new PowerPredicate(ComparisonType.MORE_THAN, 2)); + } + + public BelovedPrincess(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{W}"); + + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.NOBLE); + this.power = new MageInt(1); + this.toughness = new MageInt(1); + + // Lifelink + this.addAbility(LifelinkAbility.getInstance()); + + // Beloved Princess can't be blocked by creatures with power 3 or greater. + this.addAbility(new SimpleStaticAbility( + new CantBeBlockedByCreaturesSourceEffect(filter, Duration.WhileOnBattlefield) + )); + } + + private BelovedPrincess(final BelovedPrincess card) { + super(card); + } + + @Override + public BelovedPrincess copy() { + return new BelovedPrincess(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 030f429326..1f6fbe309c 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -37,6 +37,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Banish into Fable", 325, Rarity.RARE, mage.cards.b.BanishIntoFable.class)); cards.add(new SetCardInfo("Beanstalk Giant", 149, Rarity.UNCOMMON, mage.cards.b.BeanstalkGiant.class)); cards.add(new SetCardInfo("Belle of the Brawl", 78, Rarity.UNCOMMON, mage.cards.b.BelleOfTheBrawl.class)); + cards.add(new SetCardInfo("Beloved Princess", 7, Rarity.COMMON, mage.cards.b.BelovedPrincess.class)); cards.add(new SetCardInfo("Blow Your House Down", 114, Rarity.COMMON, mage.cards.b.BlowYourHouseDown.class)); cards.add(new SetCardInfo("Bramblefort Fink", 311, Rarity.UNCOMMON, mage.cards.b.BramblefortFink.class)); cards.add(new SetCardInfo("Brimstone Trebuchet", 116, Rarity.COMMON, mage.cards.b.BrimstoneTrebuchet.class)); From d13a46bbf0628e3d3ee1eeaa555a4335bf450bc8 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 11 Sep 2019 19:48:21 -0400 Subject: [PATCH 071/373] Implemented Gingerbrute --- Mage.Sets/src/mage/cards/g/Gingerbrute.java | 66 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 67 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/g/Gingerbrute.java diff --git a/Mage.Sets/src/mage/cards/g/Gingerbrute.java b/Mage.Sets/src/mage/cards/g/Gingerbrute.java new file mode 100644 index 0000000000..2d65b3cad6 --- /dev/null +++ b/Mage.Sets/src/mage/cards/g/Gingerbrute.java @@ -0,0 +1,66 @@ +package mage.cards.g; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.costs.common.SacrificeSourceCost; +import mage.abilities.costs.common.TapSourceCost; +import mage.abilities.costs.mana.GenericManaCost; +import mage.abilities.effects.common.GainLifeEffect; +import mage.abilities.effects.common.combat.CantBeBlockedByCreaturesSourceEffect; +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.filter.common.FilterCreaturePermanent; +import mage.filter.predicate.Predicates; +import mage.filter.predicate.mageobject.AbilityPredicate; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class Gingerbrute extends CardImpl { + + private static final FilterCreaturePermanent filter + = new FilterCreaturePermanent("except by creatures with haste"); + + static { + filter.add(Predicates.not(new AbilityPredicate(HasteAbility.class))); + } + + public Gingerbrute(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT, CardType.CREATURE}, "{1}"); + + this.subtype.add(SubType.FOOD); + this.subtype.add(SubType.GOLEM); + this.power = new MageInt(1); + this.toughness = new MageInt(1); + + // Haste + this.addAbility(HasteAbility.getInstance()); + + // {1}: Gingerbrute can't be blocked this turn except by creatures with haste. + this.addAbility(new SimpleActivatedAbility( + new CantBeBlockedByCreaturesSourceEffect(filter, Duration.EndOfTurn), new GenericManaCost(1) + )); + + // {2}, {T}, Sacrifice Gingerbrute: You gain 3 life. + Ability ability = new SimpleActivatedAbility(new GainLifeEffect(3), new GenericManaCost(2)); + ability.addCost(new TapSourceCost()); + ability.addCost(new SacrificeSourceCost()); + this.addAbility(ability); + } + + private Gingerbrute(final Gingerbrute card) { + super(card); + } + + @Override + public Gingerbrute copy() { + return new Gingerbrute(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 1f6fbe309c..cbe95dced1 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -72,6 +72,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Garruk, Cursed Huntsman", 191, Rarity.MYTHIC, mage.cards.g.GarrukCursedHuntsman.class)); cards.add(new SetCardInfo("Giant Killer", 14, Rarity.RARE, mage.cards.g.GiantKiller.class)); cards.add(new SetCardInfo("Gilded Goose", 160, Rarity.RARE, mage.cards.g.GildedGoose.class)); + cards.add(new SetCardInfo("Gingerbrute", 219, Rarity.COMMON, mage.cards.g.Gingerbrute.class)); cards.add(new SetCardInfo("Gluttonous Troll", 327, Rarity.RARE, mage.cards.g.GluttonousTroll.class)); cards.add(new SetCardInfo("Golden Egg", 220, Rarity.COMMON, mage.cards.g.GoldenEgg.class)); cards.add(new SetCardInfo("Heraldic Banner", 222, Rarity.UNCOMMON, mage.cards.h.HeraldicBanner.class)); From 3d4613aa8a67d6ac508fb86a92765202d30e2173 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 11 Sep 2019 20:03:34 -0400 Subject: [PATCH 072/373] Implemented Harmonious Archon --- .../src/mage/cards/h/HarmoniousArchon.java | 59 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 60 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/h/HarmoniousArchon.java diff --git a/Mage.Sets/src/mage/cards/h/HarmoniousArchon.java b/Mage.Sets/src/mage/cards/h/HarmoniousArchon.java new file mode 100644 index 0000000000..71150b769b --- /dev/null +++ b/Mage.Sets/src/mage/cards/h/HarmoniousArchon.java @@ -0,0 +1,59 @@ +package mage.cards.h; + +import mage.MageInt; +import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.effects.common.CreateTokenEffect; +import mage.abilities.effects.common.continuous.SetPowerToughnessAllEffect; +import mage.abilities.keyword.FlyingAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; +import mage.filter.common.FilterCreaturePermanent; +import mage.filter.predicate.Predicates; +import mage.filter.predicate.mageobject.SubtypePredicate; +import mage.game.permanent.token.HumanToken; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class HarmoniousArchon extends CardImpl { + + private static final FilterCreaturePermanent filter = new FilterCreaturePermanent("non-Archon creatures"); + + static { + filter.add(Predicates.not(new SubtypePredicate(SubType.ARCHON))); + } + + public HarmoniousArchon(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{4}{W}{W}"); + + this.subtype.add(SubType.ARCHON); + this.power = new MageInt(4); + this.toughness = new MageInt(5); + + // Flying + this.addAbility(FlyingAbility.getInstance()); + + // Non-Archon creatures have base power and toughness 3/3. + this.addAbility(new SimpleStaticAbility(new SetPowerToughnessAllEffect( + 3, 3, Duration.WhileOnBattlefield, filter, true + ))); + + // When Harmonious Archon enters the battlefield, create two 1/1 white Human creature tokens. + this.addAbility(new EntersBattlefieldTriggeredAbility(new CreateTokenEffect(new HumanToken(), 2))); + } + + private HarmoniousArchon(final HarmoniousArchon card) { + super(card); + } + + @Override + public HarmoniousArchon copy() { + return new HarmoniousArchon(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index cbe95dced1..2a371d44ca 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -75,6 +75,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Gingerbrute", 219, Rarity.COMMON, mage.cards.g.Gingerbrute.class)); cards.add(new SetCardInfo("Gluttonous Troll", 327, Rarity.RARE, mage.cards.g.GluttonousTroll.class)); cards.add(new SetCardInfo("Golden Egg", 220, Rarity.COMMON, mage.cards.g.GoldenEgg.class)); + cards.add(new SetCardInfo("Harmonious Archon", 17, Rarity.MYTHIC, mage.cards.h.HarmoniousArchon.class)); cards.add(new SetCardInfo("Heraldic Banner", 222, Rarity.UNCOMMON, mage.cards.h.HeraldicBanner.class)); cards.add(new SetCardInfo("Hypnotic Sprite", 49, Rarity.UNCOMMON, mage.cards.h.HypnoticSprite.class)); cards.add(new SetCardInfo("Inquisitive Puppet", 223, Rarity.UNCOMMON, mage.cards.i.InquisitivePuppet.class)); From 2256cf7230c8f217bf57a3180518a83124e69cc5 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 11 Sep 2019 20:11:37 -0400 Subject: [PATCH 073/373] Implemented Insatiable Appetite --- .../src/mage/cards/i/InsatiableAppetite.java | 45 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 46 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/i/InsatiableAppetite.java diff --git a/Mage.Sets/src/mage/cards/i/InsatiableAppetite.java b/Mage.Sets/src/mage/cards/i/InsatiableAppetite.java new file mode 100644 index 0000000000..60bc2bfaad --- /dev/null +++ b/Mage.Sets/src/mage/cards/i/InsatiableAppetite.java @@ -0,0 +1,45 @@ +package mage.cards.i; + +import mage.abilities.costs.common.SacrificeTargetCost; +import mage.abilities.effects.common.DoIfCostPaid; +import mage.abilities.effects.common.continuous.BoostTargetEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; +import mage.filter.common.FilterControlledPermanent; +import mage.target.common.TargetControlledPermanent; +import mage.target.common.TargetCreaturePermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class InsatiableAppetite extends CardImpl { + + private static final FilterControlledPermanent filter = new FilterControlledPermanent(SubType.FOOD, "a Food"); + + public InsatiableAppetite(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.INSTANT}, "{1}{G}"); + + // You may sacrifice a Food. If you do, target creature gets +5/+5 until end of turn. Otherwise, that creature gets +3/+3 until end of turn. + this.getSpellAbility().addEffect(new DoIfCostPaid( + new BoostTargetEffect(5, 5, Duration.EndOfTurn), + new BoostTargetEffect(3, 3, Duration.EndOfTurn), + new SacrificeTargetCost(new TargetControlledPermanent(filter)) + ).setText("You may sacrifice a Food. If you do, target creature gets +5/+5 until end of turn. " + + "Otherwise, that creature gets +3/+3 until end of turn.")); + this.getSpellAbility().addTarget(new TargetCreaturePermanent()); + } + + private InsatiableAppetite(final InsatiableAppetite card) { + super(card); + } + + @Override + public InsatiableAppetite copy() { + return new InsatiableAppetite(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 2a371d44ca..5d7cf56b50 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -79,6 +79,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Heraldic Banner", 222, Rarity.UNCOMMON, mage.cards.h.HeraldicBanner.class)); cards.add(new SetCardInfo("Hypnotic Sprite", 49, Rarity.UNCOMMON, mage.cards.h.HypnoticSprite.class)); cards.add(new SetCardInfo("Inquisitive Puppet", 223, Rarity.UNCOMMON, mage.cards.i.InquisitivePuppet.class)); + cards.add(new SetCardInfo("Insatiable Appetite", 162, Rarity.COMMON, mage.cards.i.InsatiableAppetite.class)); cards.add(new SetCardInfo("Inspiring Veteran", 194, Rarity.UNCOMMON, mage.cards.i.InspiringVeteran.class)); cards.add(new SetCardInfo("Joust", 129, Rarity.UNCOMMON, mage.cards.j.Joust.class)); cards.add(new SetCardInfo("Jousting Dummy", 224, Rarity.COMMON, mage.cards.j.JoustingDummy.class)); From 4cad63e5d8e84864d99dc7e9c3949cfa26c22a54 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 11 Sep 2019 20:14:30 -0400 Subject: [PATCH 074/373] Implemented Maraleaf Rider --- Mage.Sets/src/mage/cards/m/MaraleafRider.java | 46 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 47 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/m/MaraleafRider.java diff --git a/Mage.Sets/src/mage/cards/m/MaraleafRider.java b/Mage.Sets/src/mage/cards/m/MaraleafRider.java new file mode 100644 index 0000000000..a431a9d080 --- /dev/null +++ b/Mage.Sets/src/mage/cards/m/MaraleafRider.java @@ -0,0 +1,46 @@ +package mage.cards.m; + +import mage.abilities.Ability; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.costs.common.SacrificeTargetCost; +import mage.abilities.effects.common.combat.MustBeBlockedByTargetSourceEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.filter.common.FilterControlledPermanent; +import mage.target.common.TargetControlledPermanent; +import mage.target.common.TargetCreaturePermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class MaraleafRider extends CardImpl { + + private static final FilterControlledPermanent filter = new FilterControlledPermanent(SubType.FOOD, "a Food"); + + public MaraleafRider(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{1}{G}"); + + this.subtype.add(SubType.ELF); + this.subtype.add(SubType.KNIGHT); + + // Sacrifice a Food: Target creature blocks Maraleaf Rider this turn if able. + Ability ability = new SimpleActivatedAbility( + new MustBeBlockedByTargetSourceEffect(), new SacrificeTargetCost(new TargetControlledPermanent(filter)) + ); + ability.addTarget(new TargetCreaturePermanent()); + this.addAbility(ability); + } + + private MaraleafRider(final MaraleafRider card) { + super(card); + } + + @Override + public MaraleafRider copy() { + return new MaraleafRider(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 5d7cf56b50..d32eac3bbc 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -91,6 +91,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Lovestruck Beast", 165, Rarity.RARE, mage.cards.l.LovestruckBeast.class)); cards.add(new SetCardInfo("Mace of the Valiant", 314, Rarity.RARE, mage.cards.m.MaceOfTheValiant.class)); cards.add(new SetCardInfo("Maraleaf Pixie", 196, Rarity.UNCOMMON, mage.cards.m.MaraleafPixie.class)); + cards.add(new SetCardInfo("Maraleaf Rider", 166, Rarity.COMMON, mage.cards.m.MaraleafRider.class)); cards.add(new SetCardInfo("Midnight Clock", 54, Rarity.RARE, mage.cards.m.MidnightClock.class)); cards.add(new SetCardInfo("Murderous Rider", 97, Rarity.RARE, mage.cards.m.MurderousRider.class)); cards.add(new SetCardInfo("Mystical Dispute", 58, Rarity.UNCOMMON, mage.cards.m.MysticalDispute.class)); From ce88062b9eeca0ba5e00967373a5dbc64ab82d5a Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 11 Sep 2019 20:19:19 -0400 Subject: [PATCH 075/373] Implemented Searing Barrage --- .../src/mage/cards/s/SearingBarrage.java | 44 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 45 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/s/SearingBarrage.java diff --git a/Mage.Sets/src/mage/cards/s/SearingBarrage.java b/Mage.Sets/src/mage/cards/s/SearingBarrage.java new file mode 100644 index 0000000000..f6912d1c9d --- /dev/null +++ b/Mage.Sets/src/mage/cards/s/SearingBarrage.java @@ -0,0 +1,44 @@ +package mage.cards.s; + +import mage.abilities.condition.common.AdamantCondition; +import mage.abilities.decorator.ConditionalOneShotEffect; +import mage.abilities.effects.common.DamageTargetControllerEffect; +import mage.abilities.effects.common.DamageTargetEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.target.common.TargetCreaturePermanent; +import mage.watchers.common.ManaSpentToCastWatcher; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class SearingBarrage extends CardImpl { + + public SearingBarrage(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.INSTANT}, "{4}{R}"); + + // Searing Barrage deals 5 damage to target creature. + this.getSpellAbility().addEffect(new DamageTargetEffect(5)); + this.getSpellAbility().addTarget(new TargetCreaturePermanent()); + + // Adamant — If at least three red mana was spent to cast this spell, Searing Barrage deals 3 damage to that creature's controller. + this.getSpellAbility().addEffect(new ConditionalOneShotEffect( + new DamageTargetControllerEffect(5), AdamantCondition.RED, + "
Adamant — If at least three red mana was spent to cast this spell, " + + "{this} deals 3 damage to that creature's controller." + )); + this.getSpellAbility().addWatcher(new ManaSpentToCastWatcher()); + } + + private SearingBarrage(final SearingBarrage card) { + super(card); + } + + @Override + public SearingBarrage copy() { + return new SearingBarrage(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index d32eac3bbc..e646ad67bc 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -117,6 +117,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Run Away Together", 62, Rarity.COMMON, mage.cards.r.RunAwayTogether.class)); cards.add(new SetCardInfo("Savvy Hunter", 200, Rarity.UNCOMMON, mage.cards.s.SavvyHunter.class)); cards.add(new SetCardInfo("Scorching Dragonfire", 139, Rarity.COMMON, mage.cards.s.ScorchingDragonfire.class)); + cards.add(new SetCardInfo("Searing Barrage", 140, Rarity.COMMON, mage.cards.s.SearingBarrage.class)); cards.add(new SetCardInfo("Shimmer Dragon", 317, Rarity.RARE, mage.cards.s.ShimmerDragon.class)); cards.add(new SetCardInfo("Shinechaser", 201, Rarity.UNCOMMON, mage.cards.s.Shinechaser.class)); cards.add(new SetCardInfo("Shining Armor", 29, Rarity.COMMON, mage.cards.s.ShiningArmor.class)); From 791b64675aaf71844f1dbb4a74d7a79c6749df27 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 11 Sep 2019 20:23:15 -0400 Subject: [PATCH 076/373] Implemented Bog Naughty --- Mage.Sets/src/mage/cards/b/BogNaughty.java | 55 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 56 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/b/BogNaughty.java diff --git a/Mage.Sets/src/mage/cards/b/BogNaughty.java b/Mage.Sets/src/mage/cards/b/BogNaughty.java new file mode 100644 index 0000000000..39aa74ef30 --- /dev/null +++ b/Mage.Sets/src/mage/cards/b/BogNaughty.java @@ -0,0 +1,55 @@ +package mage.cards.b; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.costs.common.SacrificeTargetCost; +import mage.abilities.costs.mana.ManaCostsImpl; +import mage.abilities.effects.common.continuous.BoostTargetEffect; +import mage.abilities.keyword.FlyingAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; +import mage.filter.common.FilterControlledPermanent; +import mage.target.common.TargetControlledPermanent; +import mage.target.common.TargetCreaturePermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class BogNaughty extends CardImpl { + + private static final FilterControlledPermanent filter = new FilterControlledPermanent(SubType.FOOD, "a Food"); + + public BogNaughty(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{3}{B}{B}"); + + this.subtype.add(SubType.FAERIE); + this.power = new MageInt(3); + this.toughness = new MageInt(3); + + // Flying + this.addAbility(FlyingAbility.getInstance()); + + // {2}{B}, Sacrifice a Food: Target creature gets -3/-3 until end of turn. + Ability ability = new SimpleActivatedAbility( + new BoostTargetEffect(-3, -3, Duration.EndOfTurn), new ManaCostsImpl("{2}{B}") + ); + ability.addCost(new SacrificeTargetCost(new TargetControlledPermanent(filter))); + ability.addTarget(new TargetCreaturePermanent()); + this.addAbility(ability); + } + + private BogNaughty(final BogNaughty card) { + super(card); + } + + @Override + public BogNaughty copy() { + return new BogNaughty(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index e646ad67bc..f22b80fbe2 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -39,6 +39,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Belle of the Brawl", 78, Rarity.UNCOMMON, mage.cards.b.BelleOfTheBrawl.class)); cards.add(new SetCardInfo("Beloved Princess", 7, Rarity.COMMON, mage.cards.b.BelovedPrincess.class)); cards.add(new SetCardInfo("Blow Your House Down", 114, Rarity.COMMON, mage.cards.b.BlowYourHouseDown.class)); + cards.add(new SetCardInfo("Bog Naughty", 80, Rarity.UNCOMMON, mage.cards.b.BogNaughty.class)); cards.add(new SetCardInfo("Bramblefort Fink", 311, Rarity.UNCOMMON, mage.cards.b.BramblefortFink.class)); cards.add(new SetCardInfo("Brimstone Trebuchet", 116, Rarity.COMMON, mage.cards.b.BrimstoneTrebuchet.class)); cards.add(new SetCardInfo("Burning-Yard Trainer", 117, Rarity.UNCOMMON, mage.cards.b.BurningYardTrainer.class)); From af37c27ba9eb9ba29e7b8cf46971e0416230dcfd Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 11 Sep 2019 20:30:40 -0400 Subject: [PATCH 077/373] Implemented Garenbrig Paladin --- .../src/mage/cards/g/GarenbrigPaladin.java | 63 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 64 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/g/GarenbrigPaladin.java diff --git a/Mage.Sets/src/mage/cards/g/GarenbrigPaladin.java b/Mage.Sets/src/mage/cards/g/GarenbrigPaladin.java new file mode 100644 index 0000000000..59db660707 --- /dev/null +++ b/Mage.Sets/src/mage/cards/g/GarenbrigPaladin.java @@ -0,0 +1,63 @@ +package mage.cards.g; + +import mage.MageInt; +import mage.abilities.common.EntersBattlefieldAbility; +import mage.abilities.common.SimpleEvasionAbility; +import mage.abilities.condition.common.AdamantCondition; +import mage.abilities.effects.common.combat.CantBeBlockedByCreaturesSourceEffect; +import mage.abilities.effects.common.counter.AddCountersSourceEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.ComparisonType; +import mage.constants.Duration; +import mage.constants.SubType; +import mage.counters.CounterType; +import mage.filter.common.FilterCreaturePermanent; +import mage.filter.predicate.mageobject.PowerPredicate; +import mage.watchers.common.ManaSpentToCastWatcher; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class GarenbrigPaladin extends CardImpl { + + private static final FilterCreaturePermanent filter + = new FilterCreaturePermanent("creatures with power 2 or less"); + + static { + filter.add(new PowerPredicate(ComparisonType.FEWER_THAN, 3)); + } + + public GarenbrigPaladin(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{4}{G}"); + + this.subtype.add(SubType.GIANT); + this.subtype.add(SubType.KNIGHT); + this.power = new MageInt(4); + this.toughness = new MageInt(4); + + // Adamant — If at least three green mana was spent to cast this spell, Garenbrig Paladin enters the battlefield with a +1/+1 counter on it. + this.addAbility(new EntersBattlefieldAbility(new AddCountersSourceEffect( + CounterType.P1P1.createInstance()), AdamantCondition.GREEN, + "
Adamant — If at least three green mana was spent to cast this spell, " + + "{this} enters the battlefield with a +1/+1 counter on it.", "" + ), new ManaSpentToCastWatcher()); + + // Garenbrig Paladin can't be blocked by creatures with power 2 or less. + this.addAbility(new SimpleEvasionAbility( + new CantBeBlockedByCreaturesSourceEffect(filter, Duration.WhileOnBattlefield) + )); + } + + private GarenbrigPaladin(final GarenbrigPaladin card) { + super(card); + } + + @Override + public GarenbrigPaladin copy() { + return new GarenbrigPaladin(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index f22b80fbe2..5ef0930b65 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -69,6 +69,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Flaxen Intruder", 155, Rarity.UNCOMMON, mage.cards.f.FlaxenIntruder.class)); cards.add(new SetCardInfo("Foulmire Knight", 90, Rarity.UNCOMMON, mage.cards.f.FoulmireKnight.class)); cards.add(new SetCardInfo("Frogify", 47, Rarity.UNCOMMON, mage.cards.f.Frogify.class)); + cards.add(new SetCardInfo("Garenbrig Paladin", 157, Rarity.COMMON, mage.cards.g.GarenbrigPaladin.class)); cards.add(new SetCardInfo("Garrison Griffin", 305, Rarity.COMMON, mage.cards.g.GarrisonGriffin.class)); cards.add(new SetCardInfo("Garruk, Cursed Huntsman", 191, Rarity.MYTHIC, mage.cards.g.GarrukCursedHuntsman.class)); cards.add(new SetCardInfo("Giant Killer", 14, Rarity.RARE, mage.cards.g.GiantKiller.class)); From 4aee68a8ed35401ddb99100f1f0eddd5fec0cb45 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 12 Sep 2019 07:27:00 -0400 Subject: [PATCH 078/373] updated ELD spoiler and reprints --- Mage.Sets/src/mage/cards/m/MaraleafRider.java | 3 +++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 4 +++- Utils/mtg-cards-data.txt | 14 ++++++++++---- 3 files changed, 16 insertions(+), 5 deletions(-) diff --git a/Mage.Sets/src/mage/cards/m/MaraleafRider.java b/Mage.Sets/src/mage/cards/m/MaraleafRider.java index a431a9d080..25f1baba2b 100644 --- a/Mage.Sets/src/mage/cards/m/MaraleafRider.java +++ b/Mage.Sets/src/mage/cards/m/MaraleafRider.java @@ -1,5 +1,6 @@ package mage.cards.m; +import mage.MageInt; import mage.abilities.Ability; import mage.abilities.common.SimpleActivatedAbility; import mage.abilities.costs.common.SacrificeTargetCost; @@ -26,6 +27,8 @@ public final class MaraleafRider extends CardImpl { this.subtype.add(SubType.ELF); this.subtype.add(SubType.KNIGHT); + this.power = new MageInt(3); + this.toughness = new MageInt(1); // Sacrifice a Food: Target creature blocks Maraleaf Rider this turn if able. Ability ability = new SimpleActivatedAbility( diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 5ef0930b65..3d96e496c4 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -43,7 +43,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Bramblefort Fink", 311, Rarity.UNCOMMON, mage.cards.b.BramblefortFink.class)); cards.add(new SetCardInfo("Brimstone Trebuchet", 116, Rarity.COMMON, mage.cards.b.BrimstoneTrebuchet.class)); cards.add(new SetCardInfo("Burning-Yard Trainer", 117, Rarity.UNCOMMON, mage.cards.b.BurningYardTrainer.class)); - cards.add(new SetCardInfo("Charming Prince", 335, Rarity.RARE, mage.cards.c.CharmingPrince.class)); + cards.add(new SetCardInfo("Charming Prince", 8, Rarity.RARE, mage.cards.c.CharmingPrince.class)); cards.add(new SetCardInfo("Chittering Witch", 319, Rarity.RARE, mage.cards.c.ChitteringWitch.class)); cards.add(new SetCardInfo("Chulane, Teller of Tales", 326, Rarity.MYTHIC, mage.cards.c.ChulaneTellerOfTales.class)); cards.add(new SetCardInfo("Clackbridge Troll", 84, Rarity.RARE, mage.cards.c.ClackbridgeTroll.class)); @@ -108,6 +108,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Piper of the Swarm", 100, Rarity.RARE, mage.cards.p.PiperOfTheSwarm.class)); cards.add(new SetCardInfo("Questing Beast", 171, Rarity.MYTHIC, mage.cards.q.QuestingBeast.class)); cards.add(new SetCardInfo("Rankle, Master of Pranks", 101, Rarity.MYTHIC, mage.cards.r.RankleMasterOfPranks.class)); + cards.add(new SetCardInfo("Reave Soul", 103, Rarity.COMMON, mage.cards.r.ReaveSoul.class)); cards.add(new SetCardInfo("Return to Nature", 173, Rarity.COMMON, mage.cards.r.ReturnToNature.class)); cards.add(new SetCardInfo("Righteousness", 27, Rarity.UNCOMMON, mage.cards.r.Righteousness.class)); cards.add(new SetCardInfo("Robber of the Rich", 138, Rarity.MYTHIC, mage.cards.r.RobberOfTheRich.class)); @@ -128,6 +129,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Skullknocker Ogre", 142, Rarity.UNCOMMON, mage.cards.s.SkullknockerOgre.class)); cards.add(new SetCardInfo("Slaying Fire", 143, Rarity.UNCOMMON, mage.cards.s.SlayingFire.class)); cards.add(new SetCardInfo("Smitten Swordmaster", 105, Rarity.COMMON, mage.cards.s.SmittenSwordmaster.class)); + cards.add(new SetCardInfo("Sorcerous Spyglass", 233, Rarity.RARE, mage.cards.s.SorcerousSpyglass.class)); cards.add(new SetCardInfo("Spinning Wheel", 234, Rarity.UNCOMMON, mage.cards.s.SpinningWheel.class)); cards.add(new SetCardInfo("Steelbane Hydra", 322, Rarity.RARE, mage.cards.s.SteelbaneHydra.class)); cards.add(new SetCardInfo("Steelclaw Lance", 202, Rarity.UNCOMMON, mage.cards.s.SteelclawLance.class)); diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index adc0d1d684..d2e655c136 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -35995,6 +35995,7 @@ Mountain|Commander 2019|297|C||Basic Land - Mountain|||({T}: Add {R}.)| Forest|Commander 2019|300|C||Basic Land - Forest|||({T}: Add {G}.)| All That Glitters|Throne of Eldraine|2|U|{1}{W}|Enchantment - Aura|||Enchant creature$Enchanted creature gets +1/+1 for each artifact and/or enchantment you control.| Beloved Princess|Throne of Eldraine|7|C|{W}|Creature - Human Noble|1|1|Lifelink$Beloved Princess can't be blocked by creatures with power 3 or greater.| +Charming Prince|Throne of Eldraine|8|R|{1}{W}|Creature - Human Noble|2|2|When Charming Prince enters the battlefield, choose one —$• Scry 2.$• You gain 3 life.$• Exile another target creature you own. Return it to the battlefield under your control at the beginning of the next end step.| The Circle of Loyalty|Throne of Eldraine|9|M|{4}{W}{W}|Legendary Artifact|||This spell costs {1} less to cast for each Knight you control.$Creatures you control get +1/+1.$Whenever you cast a legendary spell, create a 2/2 white Knight creature token with vigilance.${3}{W}, {T}: Create a 2/2 white Knight creature token with vigilance.| Faerie Guidemother|Throne of Eldraine|11|C|{W}|Creature - Faerie|1|1|Flying| Gift of the Fae|Throne of Eldraine|11|C|{1}{W}|Sorcery - Adventure|1|1|Target creature gets +2/+1 and gains flying until end of turn.| @@ -36016,6 +36017,7 @@ Frogify|Throne of Eldraine|47|U|{1}{U}|Enchantment - Aura|||Enchant creature$Enc Gadwick, the Wizened|Throne of Eldraine|48|R|{X}{U}{U}{U}|Legendary Creature - Human Wizard|3|3|When Gadwick, the Wizened enters the battlefield, draw X cards.$Whenever you cast a blue spell, tap target nonland permanent an opponent controls.| Hypnotic Sprite|Throne of Eldraine|49|U|{U}{U}|Creature - Faerie|2|1|Flying| Mesmeric Glare|Throne of Eldraine|49|U|{2}{U}|Instant - Adventure|2|1|Counter target spell with converted mana cost 3 or less.| +Into the Story|Throne of Eldraine|50|U|{5}{U}{U}|Instant|||This spell costs {3} less to cast if an opponent has seven or more cards in their graveyard.$Draw four cards.| Midnight Clock|Throne of Eldraine|54|R|{2}{U}|Artifact|||{T}: Add {U}.${2}{U}: Put an hour counter on Midnight Clock.$At the beginning of each upkeep, put an hour counter on Midnight Clock.$When the twelfth hour counter is put on Midnight Clock, shuffle your hand and graveyard into your library, then draw seven cards. Exile Midnight Clock.| Mystical Dispute|Throne of Eldraine|58|U|{2}{U}|Instant|||This spell costs {2} less to cast if it targets a blue spell.$Counter target spell unless its controller pays {3}.| Opt|Throne of Eldraine|59|C|{U}|Instant|||Scry 1.$Draw a card.| @@ -36028,8 +36030,8 @@ Witching Well|Throne of Eldraine|74|C|{U}|Artifact|||When Witching Well enters t Ayara, First of Locthwain|Throne of Eldraine|75|R|{B}{B}{B}|Legendary Creature - Elf Noble|2|3|Whenever Ayara, First of Locthwain or another black creature enters the battlefield under your control, each opponent loses 1 life and you gain 1 life.${T}, Sacrifice another black creature: Draw a card.| Bake into a Pie|Throne of Eldraine|76|C|{2}{B}{B}|Instant|||Destroy target creature. Create a Food token.| Belle of the Brawl|Throne of Eldraine|78|U|{2}{B}|Creature - Human Knight|3|2|Menace$Whenever Belle of the Brawl attacks, other Knights you control get +1/+0 until end of turn.| -Bog Naughty|Throne of Eldraine|80|U|{3}{B}{B}|Creature - Faerie|||Flying${2}{B}, Sacrifice a Food: Target creature gets -3/-3 until end of turn.| -Cauldron Familiar|Throne of Eldraine|81|C|{B}|Creature - Cat|1|1|When Cauldron Familiar enters the battlefield, each opponent loses 1 life and you gain 1 life.$Sacrifice a Food: Return Cauldron Familiar from your graveyard to the battlefield.| +Bog Naughty|Throne of Eldraine|80|U|{3}{B}{B}|Creature - Faerie|3|3|Flying${2}{B}, Sacrifice a Food: Target creature gets -3/-3 until end of turn.| +Cauldron Familiar|Throne of Eldraine|81|U|{B}|Creature - Cat|1|1|When Cauldron Familiar enters the battlefield, each opponent loses 1 life and you gain 1 life.$Sacrifice a Food: Return Cauldron Familiar from your graveyard to the battlefield.| Clackbridge Troll|Throne of Eldraine|84|R|{3}{B}{B}|Creature - Troll|8|8|Trample, haste$When Clackbridge Troll enters the battlefield, target opponent creates three 0/1 white Goat creature tokens.$At the beginning of combat on your turn, any opponent may sacrifice a creature. If a player does, tap Clackbridge Troll, you gain 3 life, and you draw a card.| Epic Downfall|Throne of Eldraine|85|U|{1}{B}|Sorcery|||Exile target creature with converted mana cost 3 or greater.| Eye Collector|Throne of Eldraine|86|C|{B}|Creature - Faerie|1|1|Flying$Whenever Eye Collector deals combat damage to a player, each player puts the top card of their library into their graveyard.| @@ -36041,6 +36043,7 @@ Alter Fate|Throne of Eldraine|99|U|{1}{B}|Sorcery - Adventure|2|2|Return target Order of Midnight|Throne of Eldraine|99|U|{1}{B}|Creature - Human Knight|2|2|Flying$Order of Midnight can't block.| Piper of the Swarm|Throne of Eldraine|100|R|{1}{B}|Creature - Human Warlock|1|3|Rats you control have menace.${1}{B}, {T}: Create a 1/1 black Rat creature token.${2}{B}{B}, {T}, Sacrifice three Rats: Gain control of target creature.| Rankle, Master of Pranks|Throne of Eldraine|101|M|{2}{B}{B}|Legendary Creature - Faerie Rogue|3|3|Flying, haste$Whenever Rankle, Master of Pranks deals combat damage to a player, choose any number —$• Each player discards a card.$• Each player loses 1 life and draws a card.$• Each player sacrifices a creature.| +Reave Soul|Throne of Eldraine|103|C|{1}{B}|Sorcery|||Destroy target creature with power 3 or less.| Curry Favor|Throne of Eldraine|105|C|{B}|Sorcery - Adventure|2|1|You gain X life and each opponent loses X life, where X is the number of Knights you control.| Smitten Swordmaster|Throne of Eldraine|105|C|{1}{B}|Creature - Human Knight|2|1|Lifelink| Syr Konrad, the Grim|Throne of Eldraine|107|U|{3}{B}{B}|Legendary Creature - Human Knight|5|4|Whenever another creature dies, or a creature card is put into a graveyard from anywhere other than the battlefield, or a creature card leaves your graveyard, Syr Konrad, the Grim deals 1 damage to each opponent.${1}{B}: Each player puts the top card of their library into their graveyard.| @@ -36070,6 +36073,7 @@ Weaselback Redcap|Throne of Eldraine|148|C|{R}|Creature - Goblin Knight|1|1|{1}{ Beanstalk Giant|Throne of Eldraine|149|U|{6}{G}|Creature - Giant|*|*|Beanstalk Giant's power and toughness are each equal to the number of lands you control.| Fertile Footsteps|Throne of Eldraine|149|U|{2}{G}|Sorcery - Adventure|*|*|Search your library for a basic land card, put it onto the battlefield, then shuffle your library.| Curious Pair|Throne of Eldraine|150|C|{1}{G}|Creature - Human Peasant|1|3|| +Treats to Share|Throne of Eldraine|150|C|{G}|Sorcery - Adventure|1|3|Create a Food token.| Feasting Troll King|Throne of Eldraine|152|R|{2}{G}{G}{G}{G}|Creature - Troll Noble|7|6|Vigilance, trample$When Feasting Troll King enters the battlefield, if you cast it from your hand, create three Food tokens.$Sacrifice three Foods: Return Feasting Troll King from your graveyard to the battlefield. Activate this ability only during your turn.| Flaxen Intruder|Throne of Eldraine|155|U|{G}|Creature - Human Berserker|1|2|Whenever Flaxen Intruder deals combat damage to a player, you may sacrifice it. When you do, destroy target artifact or enchantment.| Welcome Home|Throne of Eldraine|155|U|{5}{G}{G}|Sorcery - Adventure|1|2|Create three 2/2 green Bear creature tokens.| @@ -36079,7 +36083,7 @@ Insatiable Appetite|Throne of Eldraine|162|C|{1}{G}|Instant|||You may sacrifice Keeper of Fables|Throne of Eldraine|163|U|{3}{G}{G}|Creature - Cat|4|5|Whenever one or more non-Human creatures you control deal combat damage to a player, draw a card.| Heart's Desire|Throne of Eldraine|165|R|{G}|Sorcery - Adventure|5|5|Create a 1/1 white Human creature token.| Lovestruck Beast|Throne of Eldraine|165|R|{2}{G}|Creature - Beast Noble|5|5|Lovestruck Beast can't attack unless you control a 1/1 creature.| -Maraleaf Rider|Throne of Eldraine|166|C|{1}{G}|Creature - Elf Knight|||Sacrifice a Food: Target creature blocks Maraleaf Rider this turn if able.| +Maraleaf Rider|Throne of Eldraine|166|C|{1}{G}|Creature - Elf Knight|3|1|Sacrifice a Food: Target creature blocks Maraleaf Rider this turn if able.| Once and Future|Throne of Eldraine|168|U|{3}{G}|Instant|||Return target card from your graveyard to your hand. Put up to one other target card from your graveyard on top of your library. Exile Once and Future.$Adamant — If at least three green mana was spent to cast this spell, instead return those cards to your hand and exile Once and Future.| Once Upon a Time|Throne of Eldraine|169|R|{1}{G}|Instant|||If this spell is the first spell you've cast this game, you may cast it without paying its mana cost.$Look at the top five cards of your library. You may reveal a creature or land card from among them and put it into your hand. Put the rest on the bottom of your library in a random order.| Outmuscle|Throne of Eldraine|170|C|{3}{G}|Sorcery|||Put a +1/+1 counter on target creature you control, then it fights another target creature you don't control.$Adamant — If at least three green mana was spent to cast this spell, the creature you control gains indestructible until end of turn.| @@ -36104,6 +36108,8 @@ Shinechaser|Throne of Eldraine|201|U|{1}{W}{U}|Creature - Faerie|1|1|Flying, vig Steelclaw Lance|Throne of Eldraine|202|U|{B}{R}|Artifact - Equipment|||Equipped creature gets +2/+2.$Equip Knight {1}$Equip {3}| Wintermoor Commander|Throne of Eldraine|205|U|{W}{B}|Creature - Human Knight|2|*|Deathtouch$Wintermoor Commander's toughness is equal to the number of Knights you control.$Whenever Wintermoor Commander attacks, another target Knight you control gains indestructible until end of turn.| Arcanist's Owl|Throne of Eldraine|206|U|{W/U}{W/U}{W/U}{W/U}|Artifact Creature - Bird|3|3|Flying$When Arcanist's Owl enters the battlefield, look at the top four cards of your library. You may reveal an artifact or enchantment card from among them and put it into your hand. Put the rest on the bottom of your library in a random order.| +Covetous Urge|Throne of Eldraine|207|U|{U/B}{U/B}{U/B}{U/B}|Sorcery|||Target opponent reveals their hand. You choose a nonland card from that player's graveyard or hand and exile it. You may cast that card for as long as it remains exiled, and you may spend mana as though it were mana of any color to cast that spell.| +Elite Headhunter|Throne of Eldraine|209|U|{B/R}{B/R}{B/R}{B/R}|Creature - Human Knight|2|3|Menace${B/R}{B/R}{B/R}, Sacrifice another creature or an artifact: Elite Headhunter deals 2 damage to target creature or planeswalker.| Fireborn Knight|Throne of Eldraine|210|U|{R/W}{R/W}{R/W}{R/W}|Creature - Human Knight|2|3|Double strike${R/W}{R/W}{R/W}{R/W}: Fireborn Knight gets +1/+1 until end of turn.| Bring Back|Throne of Eldraine|212|U|{G/W}{G/W}{G/W}{G/W}|Sorcery - Adventure|2|2|Create two 1/1 white Human creature tokens.| Oakhame Ranger|Throne of Eldraine|212|U|{G/W}{G/W}{G/W}{G/W}|Creature - Elf Knight|2|2|{T}: Creatures you control get +1/+1 until end of turn.| @@ -36114,6 +36120,7 @@ Heraldic Banner|Throne of Eldraine|222|U|{3}|Artifact|||As Heraldic Banner enter Inquisitive Puppet|Throne of Eldraine|223|U|{1}|Artifact Creature - Construct|0|2|When Inquisitive Puppet enters the battlefield, scry 1.$Exile Inquisitive Puppet: Create a 1/1 white Human creature token.| Jousting Dummy|Throne of Eldraine|224|C|{2}|Artifact Creature - Scarecrow Knight|2|1|{3}: Jousting Dummy gets +1/+0 until end of turn.| Roving Keep|Throne of Eldraine|228|C|{7}|Artifact Creature - Wall|5|7|Defender${7}: Roving Keep gets +2/+0 and gains trample until end of turn. It can attack this turn as though it didn't have defender.| +Sorcerous Spyglass|Throne of Eldraine|233|R|{2}|Artifact|||As Sorcerous Spyglass enters the battlefield, look at an opponent's hand, then choose any card name.$Activated abilities of sources with the chosen name can't be activated unless they're mana abilities.| Spinning Wheel|Throne of Eldraine|234|U|{3}|Artifact|||{T}: Add one mana of any color.${5}, {T}: Tap target creature.| Witch's Oven|Throne of Eldraine|237|U|{1}|Artifact|||{T}, Sacrifice a creature: Create a Food token. If the sacrificed creature's toughness was 4 or greater, create two Food tokens instead.| Tournament Grounds|Throne of Eldraine|248|U||Land|||{T}: Add {C}.${T}: Add {R}, {W}, or {B}. Spend this mana only to cast a Knight or Equipment spell.| @@ -36149,4 +36156,3 @@ Syr Gwyn, Hero of Ashvale|Throne of Eldraine|330|M|{3}{R}{W}{B}|Legendary Creatu Arcane Signet|Throne of Eldraine|331|C|{2}|Artifact|||{T}: Add one mana of any color in your commander's color identity.| Tome of Legends|Throne of Eldraine|332|R|{2}|Artifact|||Tome of Legends enters the battlefield with a page counter on it.$Whenever your commander enters the battlefield or attacks, put a page counter on Tome of Legends.${1}, {T}, Remove a page counter from Tome of Legends: Draw a card.| Command Tower|Throne of Eldraine|333|C||Land|||{T}: Add one mana of any color in your commander's color identity.| -Charming Prince|Throne of Eldraine|335|R|{1}{W}|Creature - Human Noble|2|2|When Charming Prince enters the battlefield, choose one —$• Scry 2.$• You gain 3 life.$• Exile another target creature you own. Return it to the battlefield under your control at the beginning of the next end step.| From 7af23cbe23a0d7dcd8acca8b47ea3ab1018a38c3 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 12 Sep 2019 07:47:54 -0400 Subject: [PATCH 079/373] fixed Lochmere Serpent's third ability --- Mage.Sets/src/mage/cards/l/LochmereSerpent.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Mage.Sets/src/mage/cards/l/LochmereSerpent.java b/Mage.Sets/src/mage/cards/l/LochmereSerpent.java index 8bc41a7bfb..8e6c99faef 100644 --- a/Mage.Sets/src/mage/cards/l/LochmereSerpent.java +++ b/Mage.Sets/src/mage/cards/l/LochmereSerpent.java @@ -58,7 +58,7 @@ public final class LochmereSerpent extends CardImpl { // {U}{B}: Exile five target cards from an opponent's graveyard. Return Lochmere Serpent from your graveyard to your hand. Activate this ability only any time you could cast a sorcery. ability = new ActivateAsSorceryActivatedAbility( - Zone.BATTLEFIELD, + Zone.GRAVEYARD, new ExileTargetEffect().setText("Exile five target cards from an opponent's graveyard."), new ManaCostsImpl("{U}{B}") ); From 2816a516f3ce6b2e63b66b03f20997b2f5c75f05 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 12 Sep 2019 07:55:34 -0400 Subject: [PATCH 080/373] Implemented Into the Story --- Mage.Sets/src/mage/cards/i/IntoTheStory.java | 63 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 64 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/i/IntoTheStory.java diff --git a/Mage.Sets/src/mage/cards/i/IntoTheStory.java b/Mage.Sets/src/mage/cards/i/IntoTheStory.java new file mode 100644 index 0000000000..e48ef7bf07 --- /dev/null +++ b/Mage.Sets/src/mage/cards/i/IntoTheStory.java @@ -0,0 +1,63 @@ +package mage.cards.i; + +import mage.abilities.Ability; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.condition.Condition; +import mage.abilities.effects.common.DrawCardSourceControllerEffect; +import mage.abilities.effects.common.cost.SpellCostReductionSourceEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Zone; +import mage.game.Game; +import mage.game.Graveyard; +import mage.players.Player; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class IntoTheStory extends CardImpl { + + public IntoTheStory(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.INSTANT}, "{5}{U}{U}"); + + // This spell costs {3} less to cast if an opponent has seven or more cards in their graveyard. + this.addAbility(new SimpleStaticAbility( + Zone.STACK, new SpellCostReductionSourceEffect(3, IntoTheStoryCondition.instance) + ).setRuleAtTheTop(true)); + + // Draw four cards. + this.getSpellAbility().addEffect(new DrawCardSourceControllerEffect(4)); + } + + private IntoTheStory(final IntoTheStory card) { + super(card); + } + + @Override + public IntoTheStory copy() { + return new IntoTheStory(this); + } +} + +enum IntoTheStoryCondition implements Condition { + instance; + + @Override + public boolean apply(Game game, Ability source) { + return game + .getOpponents(source.getControllerId()) + .stream() + .map(game::getPlayer) + .map(Player::getGraveyard) + .mapToInt(Graveyard::size) + .anyMatch(i -> i >= 7); + } + + @Override + public String toString() { + return "an opponent has seven or more cards in their graveyard"; + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 3d96e496c4..136c955890 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -83,6 +83,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Inquisitive Puppet", 223, Rarity.UNCOMMON, mage.cards.i.InquisitivePuppet.class)); cards.add(new SetCardInfo("Insatiable Appetite", 162, Rarity.COMMON, mage.cards.i.InsatiableAppetite.class)); cards.add(new SetCardInfo("Inspiring Veteran", 194, Rarity.UNCOMMON, mage.cards.i.InspiringVeteran.class)); + cards.add(new SetCardInfo("Into the Story", 50, Rarity.UNCOMMON, mage.cards.i.IntoTheStory.class)); cards.add(new SetCardInfo("Joust", 129, Rarity.UNCOMMON, mage.cards.j.Joust.class)); cards.add(new SetCardInfo("Jousting Dummy", 224, Rarity.COMMON, mage.cards.j.JoustingDummy.class)); cards.add(new SetCardInfo("Keeper of Fables", 163, Rarity.UNCOMMON, mage.cards.k.KeeperOfFables.class)); From 5c58b605a27fe905388812de69901b9aeb329b98 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 12 Sep 2019 07:59:50 -0400 Subject: [PATCH 081/373] Implemented Cauldron Familiar --- .../src/mage/cards/c/CauldronFamiliar.java | 55 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 56 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/c/CauldronFamiliar.java diff --git a/Mage.Sets/src/mage/cards/c/CauldronFamiliar.java b/Mage.Sets/src/mage/cards/c/CauldronFamiliar.java new file mode 100644 index 0000000000..f9ba1ce582 --- /dev/null +++ b/Mage.Sets/src/mage/cards/c/CauldronFamiliar.java @@ -0,0 +1,55 @@ +package mage.cards.c; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.costs.common.SacrificeTargetCost; +import mage.abilities.effects.common.GainLifeEffect; +import mage.abilities.effects.common.LoseLifeOpponentsEffect; +import mage.abilities.effects.common.ReturnSourceFromGraveyardToBattlefieldEffect; +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.target.common.TargetControlledPermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class CauldronFamiliar extends CardImpl { + + private static final FilterControlledPermanent filter = new FilterControlledPermanent(SubType.FOOD, "a Food"); + + public CauldronFamiliar(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{B}"); + + this.subtype.add(SubType.CAT); + this.power = new MageInt(1); + this.toughness = new MageInt(1); + + // When Cauldron Familiar enters the battlefield, each opponent loses 1 life and you gain 1 life. + Ability ability = new EntersBattlefieldTriggeredAbility(new LoseLifeOpponentsEffect(1)); + ability.addEffect(new GainLifeEffect(1).concatBy("and")); + this.addAbility(ability); + + // Sacrifice a Food: Return Cauldron Familiar from your graveyard to the battlefield. + this.addAbility(new SimpleActivatedAbility( + Zone.GRAVEYARD, new ReturnSourceFromGraveyardToBattlefieldEffect(), + new SacrificeTargetCost(new TargetControlledPermanent(filter)) + )); + } + + private CauldronFamiliar(final CauldronFamiliar card) { + super(card); + } + + @Override + public CauldronFamiliar copy() { + return new CauldronFamiliar(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 136c955890..bcc29b90e9 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -43,6 +43,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Bramblefort Fink", 311, Rarity.UNCOMMON, mage.cards.b.BramblefortFink.class)); cards.add(new SetCardInfo("Brimstone Trebuchet", 116, Rarity.COMMON, mage.cards.b.BrimstoneTrebuchet.class)); cards.add(new SetCardInfo("Burning-Yard Trainer", 117, Rarity.UNCOMMON, mage.cards.b.BurningYardTrainer.class)); + cards.add(new SetCardInfo("Cauldron Familiar", 81, Rarity.UNCOMMON, mage.cards.c.CauldronFamiliar.class)); cards.add(new SetCardInfo("Charming Prince", 8, Rarity.RARE, mage.cards.c.CharmingPrince.class)); cards.add(new SetCardInfo("Chittering Witch", 319, Rarity.RARE, mage.cards.c.ChitteringWitch.class)); cards.add(new SetCardInfo("Chulane, Teller of Tales", 326, Rarity.MYTHIC, mage.cards.c.ChulaneTellerOfTales.class)); From 0083083ad595fed38e9ec8c121ebddc555ea4213 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 12 Sep 2019 08:21:18 -0400 Subject: [PATCH 082/373] Implemented Syr Carah, the Bold --- .../src/mage/cards/s/SyrCarahTheBold.java | 160 ++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 161 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/s/SyrCarahTheBold.java diff --git a/Mage.Sets/src/mage/cards/s/SyrCarahTheBold.java b/Mage.Sets/src/mage/cards/s/SyrCarahTheBold.java new file mode 100644 index 0000000000..1a7a682d00 --- /dev/null +++ b/Mage.Sets/src/mage/cards/s/SyrCarahTheBold.java @@ -0,0 +1,160 @@ +package mage.cards.s; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.TriggeredAbilityImpl; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.costs.common.TapSourceCost; +import mage.abilities.effects.AsThoughEffectImpl; +import mage.abilities.effects.ContinuousEffect; +import mage.abilities.effects.OneShotEffect; +import mage.abilities.effects.common.DamageTargetEffect; +import mage.abilities.effects.common.asthought.PlayFromNotOwnHandZoneTargetEffect; +import mage.cards.Card; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.*; +import mage.game.Game; +import mage.game.events.GameEvent; +import mage.game.permanent.Permanent; +import mage.game.stack.Spell; +import mage.players.Library; +import mage.players.Player; +import mage.target.common.TargetAnyTarget; +import mage.target.targetpointer.FixedTarget; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class SyrCarahTheBold extends CardImpl { + + public SyrCarahTheBold(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{3}{R}{R}"); + + this.addSuperType(SuperType.LEGENDARY); + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.KNIGHT); + this.power = new MageInt(3); + this.toughness = new MageInt(3); + + // When Syr Carah, the Bold or an instant or sorcery spell you control deals damage to a player, exile the top card of your library. You may play that card this turn. + this.addAbility(new SyrCarahTheBoldTriggeredAbility()); + + // {T}: Syr Carah deals 1 damage to any target. + Ability ability = new SimpleActivatedAbility(new DamageTargetEffect(1), new TapSourceCost()); + ability.addTarget(new TargetAnyTarget()); + this.addAbility(ability); + } + + private SyrCarahTheBold(final SyrCarahTheBold card) { + super(card); + } + + @Override + public SyrCarahTheBold copy() { + return new SyrCarahTheBold(this); + } +} + +class SyrCarahTheBoldTriggeredAbility extends TriggeredAbilityImpl { + + SyrCarahTheBoldTriggeredAbility() { + super(Zone.BATTLEFIELD, new SyrCarahTheBoldExileEffect(), false); + } + + private SyrCarahTheBoldTriggeredAbility(final SyrCarahTheBoldTriggeredAbility ability) { + super(ability); + } + + @Override + public SyrCarahTheBoldTriggeredAbility copy() { + return new SyrCarahTheBoldTriggeredAbility(this); + } + + @Override + public boolean checkEventType(GameEvent event, Game game) { + return event.getType() == GameEvent.EventType.DAMAGED_PLAYER; + } + + @Override + public boolean checkTrigger(GameEvent event, Game game) { + if (event.getSourceId().equals(this.getSourceId())) { + return true; + } + Spell spell = game.getSpellOrLKIStack(event.getSourceId()); + return spell != null && spell.isInstantOrSorcery() + && spell.isControlledBy(this.getControllerId()); + } + + @Override + public String getRule() { + return "Whenever {this} or an instant or sorcery spell you control deals damage to a player, " + + "exile the top card of your library. You may play that card this turn."; + } + +} + +class SyrCarahTheBoldExileEffect extends OneShotEffect { + + SyrCarahTheBoldExileEffect() { + super(Outcome.Detriment); + } + + private SyrCarahTheBoldExileEffect(final SyrCarahTheBoldExileEffect effect) { + super(effect); + } + + @Override + public SyrCarahTheBoldExileEffect copy() { + return new SyrCarahTheBoldExileEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + Player controller = game.getPlayer(source.getControllerId()); + Permanent sourcePermanent = game.getPermanentOrLKIBattlefield(source.getSourceId()); + if (sourcePermanent == null || controller == null || !controller.getLibrary().hasCards()) { + return false; + } + Library library = controller.getLibrary(); + Card card = library.getFromTop(game); + if (card == null) { + return true; + } + String exileName = sourcePermanent.getIdName() + " "; + controller.moveCardsToExile(card, source, game, true, source.getSourceId(), exileName); + ContinuousEffect effect = new PlayFromNotOwnHandZoneTargetEffect(Duration.EndOfTurn); + effect.setTargetPointer(new FixedTarget(card.getId(), card.getZoneChangeCounter(game))); + game.addEffect(effect, source); + return true; + } +} + +class SyrCarahTheBoldCastFromExileEffect extends AsThoughEffectImpl { + + SyrCarahTheBoldCastFromExileEffect() { + super(AsThoughEffectType.PLAY_FROM_NOT_OWN_HAND_ZONE, Duration.EndOfTurn, Outcome.Benefit); + } + + private SyrCarahTheBoldCastFromExileEffect(final SyrCarahTheBoldCastFromExileEffect effect) { + super(effect); + } + + @Override + public boolean apply(Game game, Ability source) { + return true; + } + + @Override + public SyrCarahTheBoldCastFromExileEffect copy() { + return new SyrCarahTheBoldCastFromExileEffect(this); + } + + @Override + public boolean applies(UUID objectId, Ability source, UUID affectedControllerId, Game game) { + return source.isControlledBy(affectedControllerId) + && objectId.equals(getTargetPointer().getFirst(game, source)); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index bcc29b90e9..23dade2d4a 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -135,6 +135,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Spinning Wheel", 234, Rarity.UNCOMMON, mage.cards.s.SpinningWheel.class)); cards.add(new SetCardInfo("Steelbane Hydra", 322, Rarity.RARE, mage.cards.s.SteelbaneHydra.class)); cards.add(new SetCardInfo("Steelclaw Lance", 202, Rarity.UNCOMMON, mage.cards.s.SteelclawLance.class)); + cards.add(new SetCardInfo("Syr Carah, the Bold", 145, Rarity.UNCOMMON, mage.cards.s.SyrCarahTheBold.class)); cards.add(new SetCardInfo("Syr Elenora the Discerning", 67, Rarity.UNCOMMON, mage.cards.s.SyrElenoraTheDiscerning.class)); cards.add(new SetCardInfo("Syr Gwyn, Hero of Ashvale", 330, Rarity.MYTHIC, mage.cards.s.SyrGwynHeroOfAshvale.class)); cards.add(new SetCardInfo("Syr Konrad, the Grim", 107, Rarity.UNCOMMON, mage.cards.s.SyrKonradTheGrim.class)); From 30195c05bb41f67556f5103364c4f607b0368ecc Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 12 Sep 2019 08:48:52 -0400 Subject: [PATCH 083/373] Implemented Outmuscle --- Mage.Sets/src/mage/cards/o/Outmuscle.java | 98 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 99 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/o/Outmuscle.java diff --git a/Mage.Sets/src/mage/cards/o/Outmuscle.java b/Mage.Sets/src/mage/cards/o/Outmuscle.java new file mode 100644 index 0000000000..bc799bba81 --- /dev/null +++ b/Mage.Sets/src/mage/cards/o/Outmuscle.java @@ -0,0 +1,98 @@ +package mage.cards.o; + +import mage.abilities.Ability; +import mage.abilities.condition.common.AdamantCondition; +import mage.abilities.effects.ContinuousEffect; +import mage.abilities.effects.OneShotEffect; +import mage.abilities.effects.common.continuous.GainAbilityTargetEffect; +import mage.abilities.keyword.IndestructibleAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.Outcome; +import mage.constants.TargetController; +import mage.counters.CounterType; +import mage.filter.common.FilterCreaturePermanent; +import mage.filter.predicate.permanent.ControllerPredicate; +import mage.game.Game; +import mage.game.permanent.Permanent; +import mage.target.TargetPermanent; +import mage.target.common.TargetControlledCreaturePermanent; +import mage.target.targetpointer.FixedTarget; +import mage.watchers.common.ManaSpentToCastWatcher; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class Outmuscle extends CardImpl { + + private static final FilterCreaturePermanent filter + = new FilterCreaturePermanent("creature you don't control"); + + static { + filter.add(new ControllerPredicate(TargetController.NOT_YOU)); + } + + public Outmuscle(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.SORCERY}, "{3}{G}"); + + // Put a +1/+1 counter on target creature you control, then it fights another target creature you don't control. + // Adamant — If at least three green mana was spent to cast this spell, the creature you control gains indestructible until end of turn. + this.getSpellAbility().addEffect(new OutmuscleEffect()); + this.getSpellAbility().addTarget(new TargetControlledCreaturePermanent()); + this.getSpellAbility().addTarget(new TargetPermanent(filter)); + this.getSpellAbility().addWatcher(new ManaSpentToCastWatcher()); + } + + private Outmuscle(final Outmuscle card) { + super(card); + } + + @Override + public Outmuscle copy() { + return new Outmuscle(this); + } +} + +class OutmuscleEffect extends OneShotEffect { + + OutmuscleEffect() { + super(Outcome.Benefit); + staticText = "Put a +1/+1 counter on target creature you control, " + + "then it fights another target creature you don't control." + + "
Adamant — If at least three green mana was spent to cast this spell, " + + "the creature you control gains indestructible until end of turn."; + } + + private OutmuscleEffect(final OutmuscleEffect effect) { + super(effect); + } + + @Override + public OutmuscleEffect copy() { + return new OutmuscleEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + Permanent permanent = game.getPermanent(source.getFirstTarget()); + if (permanent == null) { + return false; + } + if (AdamantCondition.GREEN.apply(game, source)) { + ContinuousEffect effect = new GainAbilityTargetEffect(IndestructibleAbility.getInstance(), Duration.EndOfTurn); + effect.setTargetPointer(new FixedTarget(permanent, game)); + game.addEffect(effect, source); + } + permanent.addCounters(CounterType.P1P1.createInstance(), source, game); + Permanent creature = game.getPermanent(source.getTargets().get(1).getFirstTarget()); + if (creature == null) { + return true; + } + game.applyEffects(); + return creature.fight(permanent, source, game); + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 23dade2d4a..efde2345e4 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -107,6 +107,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Once Upon a Time", 169, Rarity.RARE, mage.cards.o.OnceUponATime.class)); cards.add(new SetCardInfo("Opt", 59, Rarity.COMMON, mage.cards.o.Opt.class)); cards.add(new SetCardInfo("Order of Midnight", 99, Rarity.UNCOMMON, mage.cards.o.OrderOfMidnight.class)); + cards.add(new SetCardInfo("Outmuscle", 170, Rarity.COMMON, mage.cards.o.Outmuscle.class)); cards.add(new SetCardInfo("Piper of the Swarm", 100, Rarity.RARE, mage.cards.p.PiperOfTheSwarm.class)); cards.add(new SetCardInfo("Questing Beast", 171, Rarity.MYTHIC, mage.cards.q.QuestingBeast.class)); cards.add(new SetCardInfo("Rankle, Master of Pranks", 101, Rarity.MYTHIC, mage.cards.r.RankleMasterOfPranks.class)); From 6096787fdc8285f533b245721d6c97256229c742 Mon Sep 17 00:00:00 2001 From: Adrian Petrescu Date: Thu, 12 Sep 2019 09:28:30 -0400 Subject: [PATCH 084/373] Fix incorrect set numbers in IMA --- Mage.Sets/src/mage/sets/IconicMasters.java | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/Mage.Sets/src/mage/sets/IconicMasters.java b/Mage.Sets/src/mage/sets/IconicMasters.java index b4dcaf5e24..9dd0e680fe 100644 --- a/Mage.Sets/src/mage/sets/IconicMasters.java +++ b/Mage.Sets/src/mage/sets/IconicMasters.java @@ -120,8 +120,8 @@ public final class IconicMasters extends ExpansionSet { cards.add(new SetCardInfo("Festering Newt", 90, Rarity.COMMON, mage.cards.f.FesteringNewt.class)); cards.add(new SetCardInfo("Foul-Tongue Invocation", 91, Rarity.COMMON, mage.cards.f.FoulTongueInvocation.class)); cards.add(new SetCardInfo("Grisly Spectacle", 92, Rarity.COMMON, mage.cards.g.GrislySpectacle.class)); - cards.add(new SetCardInfo("Indulgent Tormentor", 93, Rarity.UNCOMMON, mage.cards.i.IndulgentTormentor.class)); - cards.add(new SetCardInfo("Haunting Hymn", 94, Rarity.UNCOMMON, mage.cards.h.HauntingHymn.class)); + cards.add(new SetCardInfo("Haunting Hymn", 93, Rarity.UNCOMMON, mage.cards.h.HauntingHymn.class)); + cards.add(new SetCardInfo("Indulgent Tormentor", 94, Rarity.UNCOMMON, mage.cards.i.IndulgentTormentor.class)); cards.add(new SetCardInfo("Kokusho, the Evening Star", 95, Rarity.RARE, mage.cards.k.KokushoTheEveningStar.class)); cards.add(new SetCardInfo("Lord of the Pit", 96, Rarity.RARE, mage.cards.l.LordOfThePit.class)); cards.add(new SetCardInfo("Mer-Ek Nightblade", 97, Rarity.UNCOMMON, mage.cards.m.MerEkNightblade.class)); @@ -139,9 +139,9 @@ public final class IconicMasters extends ExpansionSet { cards.add(new SetCardInfo("Tavern Swindler", 109, Rarity.UNCOMMON, mage.cards.t.TavernSwindler.class)); cards.add(new SetCardInfo("Thoughtseize", 110, Rarity.RARE, mage.cards.t.Thoughtseize.class)); cards.add(new SetCardInfo("Thrill-Kill Assassin", 111, Rarity.COMMON, mage.cards.t.ThrillKillAssassin.class)); - cards.add(new SetCardInfo("Virulent Swipe", 112, Rarity.COMMON, mage.cards.v.VirulentSwipe.class)); - cards.add(new SetCardInfo("Wight of Precinct Six", 113, Rarity.COMMON, mage.cards.w.WightOfPrecinctSix.class)); - cards.add(new SetCardInfo("Ulcerate", 114, Rarity.UNCOMMON, mage.cards.u.Ulcerate.class)); + cards.add(new SetCardInfo("Ulcerate", 112, Rarity.UNCOMMON, mage.cards.u.Ulcerate.class)); + cards.add(new SetCardInfo("Virulent Swipe", 113, Rarity.COMMON, mage.cards.v.VirulentSwipe.class)); + cards.add(new SetCardInfo("Wight of Precinct Six", 114, Rarity.COMMON, mage.cards.w.WightOfPrecinctSix.class)); cards.add(new SetCardInfo("Wrench Mind", 115, Rarity.COMMON, mage.cards.w.WrenchMind.class)); cards.add(new SetCardInfo("Anger of the Gods", 116, Rarity.RARE, mage.cards.a.AngerOfTheGods.class)); cards.add(new SetCardInfo("Battle-Rattle Shaman", 117, Rarity.COMMON, mage.cards.b.BattleRattleShaman.class)); @@ -165,8 +165,8 @@ public final class IconicMasters extends ExpansionSet { cards.add(new SetCardInfo("Keldon Halberdier", 135, Rarity.COMMON, mage.cards.k.KeldonHalberdier.class)); cards.add(new SetCardInfo("Kiki-Jiki, Mirror Breaker", 136, Rarity.MYTHIC, mage.cards.k.KikiJikiMirrorBreaker.class)); cards.add(new SetCardInfo("Kiln Fiend", 137, Rarity.COMMON, mage.cards.k.KilnFiend.class)); - cards.add(new SetCardInfo("Mark of Mutiny", 138, Rarity.COMMON, mage.cards.m.MarkOfMutiny.class)); - cards.add(new SetCardInfo("Magus of the Moon", 139, Rarity.RARE, mage.cards.m.MagusOfTheMoon.class)); + cards.add(new SetCardInfo("Magus of the Moon", 138, Rarity.RARE, mage.cards.m.MagusOfTheMoon.class)); + cards.add(new SetCardInfo("Mark of Mutiny", 139, Rarity.COMMON, mage.cards.m.MarkOfMutiny.class)); cards.add(new SetCardInfo("Monastery Swiftspear", 140, Rarity.UNCOMMON, mage.cards.m.MonasterySwiftspear.class)); cards.add(new SetCardInfo("Pillar of Flame", 141, Rarity.COMMON, mage.cards.p.PillarOfFlame.class)); cards.add(new SetCardInfo("Prodigal Pyromancer", 142, Rarity.UNCOMMON, mage.cards.p.ProdigalPyromancer.class)); @@ -194,8 +194,8 @@ public final class IconicMasters extends ExpansionSet { cards.add(new SetCardInfo("Genesis Wave", 164, Rarity.RARE, mage.cards.g.GenesisWave.class)); cards.add(new SetCardInfo("Greater Basilisk", 165, Rarity.COMMON, mage.cards.g.GreaterBasilisk.class)); cards.add(new SetCardInfo("Heroes' Bane", 166, Rarity.UNCOMMON, mage.cards.h.HeroesBane.class)); - cards.add(new SetCardInfo("Hunting Pack", 167, Rarity.UNCOMMON, mage.cards.h.HuntingPack.class)); - cards.add(new SetCardInfo("Hunt the Weak", 168, Rarity.COMMON, mage.cards.h.HuntTheWeak.class)); + cards.add(new SetCardInfo("Hunt the Weak", 167, Rarity.COMMON, mage.cards.h.HuntTheWeak.class)); + cards.add(new SetCardInfo("Hunting Pack", 168, Rarity.UNCOMMON, mage.cards.h.HuntingPack.class)); cards.add(new SetCardInfo("Inspiring Call", 169, Rarity.UNCOMMON, mage.cards.i.InspiringCall.class)); cards.add(new SetCardInfo("Ivy Elemental", 170, Rarity.COMMON, mage.cards.i.IvyElemental.class)); cards.add(new SetCardInfo("Jaddi Offshoot", 171, Rarity.COMMON, mage.cards.j.JaddiOffshoot.class)); From 234ef0261ba4ba754035a94224efbfcd76355f8e Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 12 Sep 2019 09:34:44 -0400 Subject: [PATCH 085/373] reorganized IMA set file --- Mage.Sets/src/mage/sets/IconicMasters.java | 393 ++++++++++----------- 1 file changed, 195 insertions(+), 198 deletions(-) diff --git a/Mage.Sets/src/mage/sets/IconicMasters.java b/Mage.Sets/src/mage/sets/IconicMasters.java index 9dd0e680fe..a211bac386 100644 --- a/Mage.Sets/src/mage/sets/IconicMasters.java +++ b/Mage.Sets/src/mage/sets/IconicMasters.java @@ -1,4 +1,3 @@ - package mage.sets; import mage.cards.ExpansionSet; @@ -6,7 +5,6 @@ import mage.constants.Rarity; import mage.constants.SetType; /** - * * @author MajorLazar */ public final class IconicMasters extends ExpansionSet { @@ -28,255 +26,254 @@ public final class IconicMasters extends ExpansionSet { this.numBoosterRare = 1; this.ratioBoosterMythic = 8; - cards.add(new SetCardInfo("Scion of Ugin", 1, Rarity.COMMON, mage.cards.s.ScionOfUgin.class)); + cards.add(new SetCardInfo("Abyssal Persecutor", 78, Rarity.RARE, mage.cards.a.AbyssalPersecutor.class)); cards.add(new SetCardInfo("Abzan Battle Priest", 2, Rarity.UNCOMMON, mage.cards.a.AbzanBattlePriest.class)); cards.add(new SetCardInfo("Abzan Falconer", 3, Rarity.UNCOMMON, mage.cards.a.AbzanFalconer.class)); + cards.add(new SetCardInfo("Aerial Predation", 154, Rarity.COMMON, mage.cards.a.AerialPredation.class)); + cards.add(new SetCardInfo("Aether Vial", 212, Rarity.RARE, mage.cards.a.AetherVial.class)); + cards.add(new SetCardInfo("Aetherize", 40, Rarity.UNCOMMON, mage.cards.a.Aetherize.class)); cards.add(new SetCardInfo("Ainok Bond-Kin", 4, Rarity.COMMON, mage.cards.a.AinokBondKin.class)); cards.add(new SetCardInfo("Ajani's Pridemate", 5, Rarity.UNCOMMON, mage.cards.a.AjanisPridemate.class)); + cards.add(new SetCardInfo("Amass the Components", 41, Rarity.COMMON, mage.cards.a.AmassTheComponents.class)); + cards.add(new SetCardInfo("Ancestral Vision", 42, Rarity.RARE, mage.cards.a.AncestralVision.class)); cards.add(new SetCardInfo("Angel of Mercy", 6, Rarity.COMMON, mage.cards.a.AngelOfMercy.class)); cards.add(new SetCardInfo("Angelic Accord", 7, Rarity.UNCOMMON, mage.cards.a.AngelicAccord.class)); + cards.add(new SetCardInfo("Anger of the Gods", 116, Rarity.RARE, mage.cards.a.AngerOfTheGods.class)); cards.add(new SetCardInfo("Archangel of Thune", 8, Rarity.MYTHIC, mage.cards.a.ArchangelOfThune.class)); + cards.add(new SetCardInfo("Assault Formation", 155, Rarity.UNCOMMON, mage.cards.a.AssaultFormation.class)); cards.add(new SetCardInfo("Auriok Champion", 9, Rarity.RARE, mage.cards.a.AuriokChampion.class)); cards.add(new SetCardInfo("Austere Command", 10, Rarity.RARE, mage.cards.a.AustereCommand.class)); cards.add(new SetCardInfo("Avacyn, Angel of Hope", 11, Rarity.MYTHIC, mage.cards.a.AvacynAngelOfHope.class)); + cards.add(new SetCardInfo("Azorius Chancery", 232, Rarity.UNCOMMON, mage.cards.a.AzoriusChancery.class)); + cards.add(new SetCardInfo("Azorius Charm", 192, Rarity.UNCOMMON, mage.cards.a.AzoriusCharm.class)); + cards.add(new SetCardInfo("Bala Ged Scorpion", 79, Rarity.COMMON, mage.cards.b.BalaGedScorpion.class)); + cards.add(new SetCardInfo("Balustrade Spy", 80, Rarity.COMMON, mage.cards.b.BalustradeSpy.class)); + cards.add(new SetCardInfo("Battle-Rattle Shaman", 117, Rarity.COMMON, mage.cards.b.BattleRattleShaman.class)); cards.add(new SetCardInfo("Benevolent Ancestor", 12, Rarity.COMMON, mage.cards.b.BenevolentAncestor.class)); - cards.add(new SetCardInfo("Blinding Mage", 13, Rarity.COMMON, mage.cards.b.BlindingMage.class)); - cards.add(new SetCardInfo("Burrenton Forge-Tender", 14, Rarity.UNCOMMON, mage.cards.b.BurrentonForgeTender.class)); - cards.add(new SetCardInfo("Disenchant", 15, Rarity.COMMON, mage.cards.d.Disenchant.class)); - cards.add(new SetCardInfo("Doomed Traveler", 16, Rarity.COMMON, mage.cards.d.DoomedTraveler.class)); - cards.add(new SetCardInfo("Dragon Bell Monk", 17, Rarity.COMMON, mage.cards.d.DragonBellMonk.class)); - cards.add(new SetCardInfo("Elesh Norn, Grand Cenobite", 18, Rarity.MYTHIC, mage.cards.e.EleshNornGrandCenobite.class)); - cards.add(new SetCardInfo("Emerge Unscathed", 19, Rarity.COMMON, mage.cards.e.EmergeUnscathed.class)); - cards.add(new SetCardInfo("Emeria Angel", 20, Rarity.RARE, mage.cards.e.EmeriaAngel.class)); - cards.add(new SetCardInfo("Great Teacher's Decree", 21, Rarity.UNCOMMON, mage.cards.g.GreatTeachersDecree.class)); - cards.add(new SetCardInfo("Guard Duty", 22, Rarity.COMMON, mage.cards.g.GuardDuty.class)); - cards.add(new SetCardInfo("Guided Strike", 23, Rarity.COMMON, mage.cards.g.GuidedStrike.class)); - cards.add(new SetCardInfo("Infantry Veteran", 24, Rarity.COMMON, mage.cards.i.InfantryVeteran.class)); - cards.add(new SetCardInfo("Iona's Judgment", 25, Rarity.COMMON, mage.cards.i.IonasJudgment.class)); - cards.add(new SetCardInfo("Path of Bravery", 26, Rarity.RARE, mage.cards.p.PathOfBravery.class)); - cards.add(new SetCardInfo("Pentarch Ward", 27, Rarity.COMMON, mage.cards.p.PentarchWard.class)); - cards.add(new SetCardInfo("Restoration Angel", 28, Rarity.RARE, mage.cards.r.RestorationAngel.class)); - cards.add(new SetCardInfo("Seeker of the Way", 29, Rarity.COMMON, mage.cards.s.SeekerOfTheWay.class)); - cards.add(new SetCardInfo("Serra Angel", 30, Rarity.UNCOMMON, mage.cards.s.SerraAngel.class)); - cards.add(new SetCardInfo("Serra Ascendant", 31, Rarity.RARE, mage.cards.s.SerraAscendant.class)); - cards.add(new SetCardInfo("Stalwart Aven", 32, Rarity.COMMON, mage.cards.s.StalwartAven.class)); - cards.add(new SetCardInfo("Student of Ojutai", 33, Rarity.COMMON, mage.cards.s.StudentOfOjutai.class)); - cards.add(new SetCardInfo("Survival Cache", 34, Rarity.COMMON, mage.cards.s.SurvivalCache.class)); - cards.add(new SetCardInfo("Sustainer of the Realm", 35, Rarity.COMMON, mage.cards.s.SustainerOfTheRealm.class)); - cards.add(new SetCardInfo("Swords to Plowshares", 36, Rarity.UNCOMMON, mage.cards.s.SwordsToPlowshares.class)); - cards.add(new SetCardInfo("Topan Freeblade", 37, Rarity.UNCOMMON, mage.cards.t.TopanFreeblade.class)); - cards.add(new SetCardInfo("Wing Shards", 38, Rarity.UNCOMMON, mage.cards.w.WingShards.class)); - cards.add(new SetCardInfo("Yosei, the Morning Star", 39, Rarity.RARE, mage.cards.y.YoseiTheMorningStar.class)); - cards.add(new SetCardInfo("Aetherize", 40, Rarity.UNCOMMON, mage.cards.a.Aetherize.class)); - cards.add(new SetCardInfo("Amass the Components", 41, Rarity.COMMON, mage.cards.a.AmassTheComponents.class)); - cards.add(new SetCardInfo("Ancestral Vision", 42, Rarity.RARE, mage.cards.a.AncestralVision.class)); cards.add(new SetCardInfo("Bewilder", 43, Rarity.COMMON, mage.cards.b.Bewilder.class)); + cards.add(new SetCardInfo("Bladewing the Risen", 193, Rarity.UNCOMMON, mage.cards.b.BladewingTheRisen.class)); + cards.add(new SetCardInfo("Bladewing's Thrall", 81, Rarity.UNCOMMON, mage.cards.b.BladewingsThrall.class)); + cards.add(new SetCardInfo("Blinding Mage", 13, Rarity.COMMON, mage.cards.b.BlindingMage.class)); + cards.add(new SetCardInfo("Blizzard Specter", 194, Rarity.UNCOMMON, mage.cards.b.BlizzardSpecter.class)); + cards.add(new SetCardInfo("Blood Baron of Vizkopa", 195, Rarity.RARE, mage.cards.b.BloodBaronOfVizkopa.class)); + cards.add(new SetCardInfo("Bloodghast", 82, Rarity.RARE, mage.cards.b.Bloodghast.class)); + cards.add(new SetCardInfo("Bogardan Hellkite", 118, Rarity.RARE, mage.cards.b.BogardanHellkite.class)); + cards.add(new SetCardInfo("Bogbrew Witch", 83, Rarity.UNCOMMON, mage.cards.b.BogbrewWitch.class)); + cards.add(new SetCardInfo("Borderland Marauder", 119, Rarity.COMMON, mage.cards.b.BorderlandMarauder.class)); + cards.add(new SetCardInfo("Boros Garrison", 233, Rarity.UNCOMMON, mage.cards.b.BorosGarrison.class)); + cards.add(new SetCardInfo("Bubbling Cauldron", 213, Rarity.UNCOMMON, mage.cards.b.BubblingCauldron.class)); + cards.add(new SetCardInfo("Burrenton Forge-Tender", 14, Rarity.UNCOMMON, mage.cards.b.BurrentonForgeTender.class)); + cards.add(new SetCardInfo("Butcher's Glee", 84, Rarity.COMMON, mage.cards.b.ButchersGlee.class)); + cards.add(new SetCardInfo("Carven Caryatid", 156, Rarity.UNCOMMON, mage.cards.c.CarvenCaryatid.class)); cards.add(new SetCardInfo("Cephalid Broker", 44, Rarity.UNCOMMON, mage.cards.c.CephalidBroker.class)); + cards.add(new SetCardInfo("Channel", 157, Rarity.MYTHIC, mage.cards.c.Channel.class)); + cards.add(new SetCardInfo("Charmbreaker Devils", 120, Rarity.RARE, mage.cards.c.CharmbreakerDevils.class)); + cards.add(new SetCardInfo("Child of Night", 85, Rarity.COMMON, mage.cards.c.ChildOfNight.class)); + cards.add(new SetCardInfo("Chronicler of Heroes", 196, Rarity.UNCOMMON, mage.cards.c.ChroniclerOfHeroes.class)); cards.add(new SetCardInfo("Claustrophobia", 45, Rarity.COMMON, mage.cards.c.Claustrophobia.class)); cards.add(new SetCardInfo("Condescend", 46, Rarity.UNCOMMON, mage.cards.c.Condescend.class)); cards.add(new SetCardInfo("Consecrated Sphinx", 47, Rarity.MYTHIC, mage.cards.c.ConsecratedSphinx.class)); + cards.add(new SetCardInfo("Coordinated Assault", 121, Rarity.UNCOMMON, mage.cards.c.CoordinatedAssault.class)); + cards.add(new SetCardInfo("Corpsejack Menace", 197, Rarity.UNCOMMON, mage.cards.c.CorpsejackMenace.class)); + cards.add(new SetCardInfo("Crowned Ceratok", 158, Rarity.COMMON, mage.cards.c.CrownedCeratok.class)); + cards.add(new SetCardInfo("Crucible of Fire", 122, Rarity.RARE, mage.cards.c.CrucibleOfFire.class)); cards.add(new SetCardInfo("Cryptic Command", 48, Rarity.RARE, mage.cards.c.CrypticCommand.class)); + cards.add(new SetCardInfo("Curse of Predation", 159, Rarity.RARE, mage.cards.c.CurseOfPredation.class)); + cards.add(new SetCardInfo("Darksteel Axe", 214, Rarity.COMMON, mage.cards.d.DarksteelAxe.class)); cards.add(new SetCardInfo("Day of the Dragons", 49, Rarity.RARE, mage.cards.d.DayOfTheDragons.class)); + cards.add(new SetCardInfo("Dead Reveler", 86, Rarity.COMMON, mage.cards.d.DeadReveler.class)); cards.add(new SetCardInfo("Diminish", 50, Rarity.COMMON, mage.cards.d.Diminish.class)); + cards.add(new SetCardInfo("Dimir Aqueduct", 234, Rarity.UNCOMMON, mage.cards.d.DimirAqueduct.class)); + cards.add(new SetCardInfo("Disenchant", 15, Rarity.COMMON, mage.cards.d.Disenchant.class)); cards.add(new SetCardInfo("Dissolve", 51, Rarity.COMMON, mage.cards.d.Dissolve.class)); cards.add(new SetCardInfo("Distortion Strike", 52, Rarity.UNCOMMON, mage.cards.d.DistortionStrike.class)); - cards.add(new SetCardInfo("Doorkeeper", 53, Rarity.COMMON, mage.cards.d.Doorkeeper.class)); - cards.add(new SetCardInfo("Elusive Spellfist", 54, Rarity.COMMON, mage.cards.e.ElusiveSpellfist.class)); - cards.add(new SetCardInfo("Flusterstorm", 55, Rarity.RARE, mage.cards.f.Flusterstorm.class)); - cards.add(new SetCardInfo("Fog Bank", 56, Rarity.UNCOMMON, mage.cards.f.FogBank.class)); - cards.add(new SetCardInfo("Frost Lynx", 57, Rarity.COMMON, mage.cards.f.FrostLynx.class)); - cards.add(new SetCardInfo("Illusory Ambusher", 58, Rarity.UNCOMMON, mage.cards.i.IllusoryAmbusher.class)); - cards.add(new SetCardInfo("Illusory Angel", 59, Rarity.UNCOMMON, mage.cards.i.IllusoryAngel.class)); - cards.add(new SetCardInfo("Jace's Phantasm", 60, Rarity.COMMON, mage.cards.j.JacesPhantasm.class)); - cards.add(new SetCardInfo("Jhessian Thief", 61, Rarity.COMMON, mage.cards.j.JhessianThief.class)); - cards.add(new SetCardInfo("Jin-Gitaxias, Core Augur", 62, Rarity.MYTHIC, mage.cards.j.JinGitaxiasCoreAugur.class)); - cards.add(new SetCardInfo("Keiga, the Tide Star", 63, Rarity.RARE, mage.cards.k.KeigaTheTideStar.class)); - cards.add(new SetCardInfo("Mahamoti Djinn", 64, Rarity.UNCOMMON, mage.cards.m.MahamotiDjinn.class)); - cards.add(new SetCardInfo("Mana Drain", 65, Rarity.MYTHIC, mage.cards.m.ManaDrain.class)); - cards.add(new SetCardInfo("Mana Leak", 66, Rarity.COMMON, mage.cards.m.ManaLeak.class)); - cards.add(new SetCardInfo("Mnemonic Wall", 67, Rarity.COMMON, mage.cards.m.MnemonicWall.class)); - cards.add(new SetCardInfo("Ojutai's Breath", 68, Rarity.COMMON, mage.cards.o.OjutaisBreath.class)); - cards.add(new SetCardInfo("Phantom Monster", 69, Rarity.COMMON, mage.cards.p.PhantomMonster.class)); - cards.add(new SetCardInfo("Repeal", 70, Rarity.COMMON, mage.cards.r.Repeal.class)); - cards.add(new SetCardInfo("Riverwheel Aerialists", 71, Rarity.COMMON, mage.cards.r.RiverwheelAerialists.class)); - cards.add(new SetCardInfo("Shriekgeist", 72, Rarity.COMMON, mage.cards.s.Shriekgeist.class)); - cards.add(new SetCardInfo("Skywise Teachings", 73, Rarity.UNCOMMON, mage.cards.s.SkywiseTeachings.class)); - cards.add(new SetCardInfo("Sphinx of Uthuun", 74, Rarity.RARE, mage.cards.s.SphinxOfUthuun.class)); - cards.add(new SetCardInfo("Teferi, Mage of Zhalfir", 75, Rarity.RARE, mage.cards.t.TeferiMageOfZhalfir.class)); - cards.add(new SetCardInfo("Thought Scour", 76, Rarity.COMMON, mage.cards.t.ThoughtScour.class)); - cards.add(new SetCardInfo("Windfall", 77, Rarity.UNCOMMON, mage.cards.w.Windfall.class)); - cards.add(new SetCardInfo("Abyssal Persecutor", 78, Rarity.RARE, mage.cards.a.AbyssalPersecutor.class)); - cards.add(new SetCardInfo("Bala Ged Scorpion", 79, Rarity.COMMON, mage.cards.b.BalaGedScorpion.class)); - cards.add(new SetCardInfo("Balustrade Spy", 80, Rarity.COMMON, mage.cards.b.BalustradeSpy.class)); - cards.add(new SetCardInfo("Bladewing's Thrall", 81, Rarity.UNCOMMON, mage.cards.b.BladewingsThrall.class)); - cards.add(new SetCardInfo("Bloodghast", 82, Rarity.RARE, mage.cards.b.Bloodghast.class)); - cards.add(new SetCardInfo("Bogbrew Witch", 83, Rarity.UNCOMMON, mage.cards.b.BogbrewWitch.class)); - cards.add(new SetCardInfo("Butcher's Glee", 84, Rarity.COMMON, mage.cards.b.ButchersGlee.class)); - cards.add(new SetCardInfo("Child of Night", 85, Rarity.COMMON, mage.cards.c.ChildOfNight.class)); - cards.add(new SetCardInfo("Dead Reveler", 86, Rarity.COMMON, mage.cards.d.DeadReveler.class)); cards.add(new SetCardInfo("Doom Blade", 87, Rarity.UNCOMMON, mage.cards.d.DoomBlade.class)); - cards.add(new SetCardInfo("Duress", 88, Rarity.COMMON, mage.cards.d.Duress.class)); - cards.add(new SetCardInfo("Eternal Thirst", 89, Rarity.COMMON, mage.cards.e.EternalThirst.class)); - cards.add(new SetCardInfo("Festering Newt", 90, Rarity.COMMON, mage.cards.f.FesteringNewt.class)); - cards.add(new SetCardInfo("Foul-Tongue Invocation", 91, Rarity.COMMON, mage.cards.f.FoulTongueInvocation.class)); - cards.add(new SetCardInfo("Grisly Spectacle", 92, Rarity.COMMON, mage.cards.g.GrislySpectacle.class)); - cards.add(new SetCardInfo("Haunting Hymn", 93, Rarity.UNCOMMON, mage.cards.h.HauntingHymn.class)); - cards.add(new SetCardInfo("Indulgent Tormentor", 94, Rarity.UNCOMMON, mage.cards.i.IndulgentTormentor.class)); - cards.add(new SetCardInfo("Kokusho, the Evening Star", 95, Rarity.RARE, mage.cards.k.KokushoTheEveningStar.class)); - cards.add(new SetCardInfo("Lord of the Pit", 96, Rarity.RARE, mage.cards.l.LordOfThePit.class)); - cards.add(new SetCardInfo("Mer-Ek Nightblade", 97, Rarity.UNCOMMON, mage.cards.m.MerEkNightblade.class)); - cards.add(new SetCardInfo("Necropotence", 98, Rarity.MYTHIC, mage.cards.n.Necropotence.class)); - cards.add(new SetCardInfo("Night of Souls' Betrayal", 99, Rarity.RARE, mage.cards.n.NightOfSoulsBetrayal.class)); - cards.add(new SetCardInfo("Noxious Dragon", 100, Rarity.UNCOMMON, mage.cards.n.NoxiousDragon.class)); - cards.add(new SetCardInfo("Ob Nixilis, the Fallen", 101, Rarity.MYTHIC, mage.cards.o.ObNixilisTheFallen.class)); - cards.add(new SetCardInfo("Phyrexian Rager", 102, Rarity.COMMON, mage.cards.p.PhyrexianRager.class)); - cards.add(new SetCardInfo("Rakdos Drake", 103, Rarity.COMMON, mage.cards.r.RakdosDrake.class)); - cards.add(new SetCardInfo("Reave Soul", 104, Rarity.COMMON, mage.cards.r.ReaveSoul.class)); - cards.add(new SetCardInfo("Rotfeaster Maggot", 105, Rarity.COMMON, mage.cards.r.RotfeasterMaggot.class)); - cards.add(new SetCardInfo("Rune-Scarred Demon", 106, Rarity.RARE, mage.cards.r.RuneScarredDemon.class)); - cards.add(new SetCardInfo("Sanguine Bond", 107, Rarity.UNCOMMON, mage.cards.s.SanguineBond.class)); - cards.add(new SetCardInfo("Sheoldred, Whispering One", 108, Rarity.MYTHIC, mage.cards.s.SheoldredWhisperingOne.class)); - cards.add(new SetCardInfo("Tavern Swindler", 109, Rarity.UNCOMMON, mage.cards.t.TavernSwindler.class)); - cards.add(new SetCardInfo("Thoughtseize", 110, Rarity.RARE, mage.cards.t.Thoughtseize.class)); - cards.add(new SetCardInfo("Thrill-Kill Assassin", 111, Rarity.COMMON, mage.cards.t.ThrillKillAssassin.class)); - cards.add(new SetCardInfo("Ulcerate", 112, Rarity.UNCOMMON, mage.cards.u.Ulcerate.class)); - cards.add(new SetCardInfo("Virulent Swipe", 113, Rarity.COMMON, mage.cards.v.VirulentSwipe.class)); - cards.add(new SetCardInfo("Wight of Precinct Six", 114, Rarity.COMMON, mage.cards.w.WightOfPrecinctSix.class)); - cards.add(new SetCardInfo("Wrench Mind", 115, Rarity.COMMON, mage.cards.w.WrenchMind.class)); - cards.add(new SetCardInfo("Anger of the Gods", 116, Rarity.RARE, mage.cards.a.AngerOfTheGods.class)); - cards.add(new SetCardInfo("Battle-Rattle Shaman", 117, Rarity.COMMON, mage.cards.b.BattleRattleShaman.class)); - cards.add(new SetCardInfo("Bogardan Hellkite", 118, Rarity.RARE, mage.cards.b.BogardanHellkite.class)); - cards.add(new SetCardInfo("Borderland Marauder", 119, Rarity.COMMON, mage.cards.b.BorderlandMarauder.class)); - cards.add(new SetCardInfo("Charmbreaker Devils", 120, Rarity.RARE, mage.cards.c.CharmbreakerDevils.class)); - cards.add(new SetCardInfo("Coordinated Assault", 121, Rarity.UNCOMMON, mage.cards.c.CoordinatedAssault.class)); - cards.add(new SetCardInfo("Crucible of Fire", 122, Rarity.RARE, mage.cards.c.CrucibleOfFire.class)); + cards.add(new SetCardInfo("Doomed Traveler", 16, Rarity.COMMON, mage.cards.d.DoomedTraveler.class)); + cards.add(new SetCardInfo("Doorkeeper", 53, Rarity.COMMON, mage.cards.d.Doorkeeper.class)); cards.add(new SetCardInfo("Draconic Roar", 123, Rarity.COMMON, mage.cards.d.DraconicRoar.class)); + cards.add(new SetCardInfo("Dragon Bell Monk", 17, Rarity.COMMON, mage.cards.d.DragonBellMonk.class)); cards.add(new SetCardInfo("Dragon Egg", 124, Rarity.COMMON, mage.cards.d.DragonEgg.class)); cards.add(new SetCardInfo("Dragon Tempest", 125, Rarity.UNCOMMON, mage.cards.d.DragonTempest.class)); + cards.add(new SetCardInfo("Dragonloft Idol", 215, Rarity.UNCOMMON, mage.cards.d.DragonloftIdol.class)); cards.add(new SetCardInfo("Dragonlord's Servant", 126, Rarity.COMMON, mage.cards.d.DragonlordsServant.class)); + cards.add(new SetCardInfo("Duress", 88, Rarity.COMMON, mage.cards.d.Duress.class)); + cards.add(new SetCardInfo("Durkwood Baloth", 160, Rarity.COMMON, mage.cards.d.DurkwoodBaloth.class)); + cards.add(new SetCardInfo("Duskdale Wurm", 161, Rarity.COMMON, mage.cards.d.DuskdaleWurm.class)); cards.add(new SetCardInfo("Earth Elemental", 127, Rarity.COMMON, mage.cards.e.EarthElemental.class)); + cards.add(new SetCardInfo("Electrolyze", 198, Rarity.UNCOMMON, mage.cards.e.Electrolyze.class)); + cards.add(new SetCardInfo("Elesh Norn, Grand Cenobite", 18, Rarity.MYTHIC, mage.cards.e.EleshNornGrandCenobite.class)); + cards.add(new SetCardInfo("Elusive Spellfist", 54, Rarity.COMMON, mage.cards.e.ElusiveSpellfist.class)); + cards.add(new SetCardInfo("Emerge Unscathed", 19, Rarity.COMMON, mage.cards.e.EmergeUnscathed.class)); + cards.add(new SetCardInfo("Emeria Angel", 20, Rarity.RARE, mage.cards.e.EmeriaAngel.class)); + cards.add(new SetCardInfo("Enlarge", 162, Rarity.UNCOMMON, mage.cards.e.Enlarge.class)); + cards.add(new SetCardInfo("Eternal Thirst", 89, Rarity.COMMON, mage.cards.e.EternalThirst.class)); + cards.add(new SetCardInfo("Evolving Wilds", 235, Rarity.COMMON, mage.cards.e.EvolvingWilds.class)); + cards.add(new SetCardInfo("Festering Newt", 90, Rarity.COMMON, mage.cards.f.FesteringNewt.class)); cards.add(new SetCardInfo("Fireball", 128, Rarity.UNCOMMON, mage.cards.f.Fireball.class)); + cards.add(new SetCardInfo("Firemane Angel", 199, Rarity.RARE, mage.cards.f.FiremaneAngel.class)); + cards.add(new SetCardInfo("Flusterstorm", 55, Rarity.RARE, mage.cards.f.Flusterstorm.class)); + cards.add(new SetCardInfo("Fog Bank", 56, Rarity.UNCOMMON, mage.cards.f.FogBank.class)); + cards.add(new SetCardInfo("Foul-Tongue Invocation", 91, Rarity.COMMON, mage.cards.f.FoulTongueInvocation.class)); + cards.add(new SetCardInfo("Frost Lynx", 57, Rarity.COMMON, mage.cards.f.FrostLynx.class)); cards.add(new SetCardInfo("Furnace Whelp", 129, Rarity.COMMON, mage.cards.f.FurnaceWhelp.class)); cards.add(new SetCardInfo("Fury Charm", 130, Rarity.COMMON, mage.cards.f.FuryCharm.class)); + cards.add(new SetCardInfo("Genesis Hydra", 163, Rarity.RARE, mage.cards.g.GenesisHydra.class)); + cards.add(new SetCardInfo("Genesis Wave", 164, Rarity.RARE, mage.cards.g.GenesisWave.class)); + cards.add(new SetCardInfo("Glimpse the Unthinkable", 200, Rarity.RARE, mage.cards.g.GlimpseTheUnthinkable.class)); + cards.add(new SetCardInfo("Golgari Rot Farm", 236, Rarity.UNCOMMON, mage.cards.g.GolgariRotFarm.class)); + cards.add(new SetCardInfo("Graven Cairns", 237, Rarity.RARE, mage.cards.g.GravenCairns.class)); + cards.add(new SetCardInfo("Great Teacher's Decree", 21, Rarity.UNCOMMON, mage.cards.g.GreatTeachersDecree.class)); + cards.add(new SetCardInfo("Greater Basilisk", 165, Rarity.COMMON, mage.cards.g.GreaterBasilisk.class)); + cards.add(new SetCardInfo("Grisly Spectacle", 92, Rarity.COMMON, mage.cards.g.GrislySpectacle.class)); + cards.add(new SetCardInfo("Grove of the Burnwillows", 238, Rarity.RARE, mage.cards.g.GroveOfTheBurnwillows.class)); + cards.add(new SetCardInfo("Gruul Turf", 239, Rarity.UNCOMMON, mage.cards.g.GruulTurf.class)); + cards.add(new SetCardInfo("Guard Duty", 22, Rarity.COMMON, mage.cards.g.GuardDuty.class)); + cards.add(new SetCardInfo("Guardian Idol", 216, Rarity.COMMON, mage.cards.g.GuardianIdol.class)); + cards.add(new SetCardInfo("Guided Strike", 23, Rarity.COMMON, mage.cards.g.GuidedStrike.class)); cards.add(new SetCardInfo("Guttersnipe", 131, Rarity.UNCOMMON, mage.cards.g.Guttersnipe.class)); cards.add(new SetCardInfo("Hammerhand", 132, Rarity.COMMON, mage.cards.h.Hammerhand.class)); + cards.add(new SetCardInfo("Haunting Hymn", 93, Rarity.UNCOMMON, mage.cards.h.HauntingHymn.class)); cards.add(new SetCardInfo("Heat Ray", 133, Rarity.COMMON, mage.cards.h.HeatRay.class)); + cards.add(new SetCardInfo("Heroes' Bane", 166, Rarity.UNCOMMON, mage.cards.h.HeroesBane.class)); cards.add(new SetCardInfo("Hoarding Dragon", 134, Rarity.UNCOMMON, mage.cards.h.HoardingDragon.class)); + cards.add(new SetCardInfo("Horizon Canopy", 240, Rarity.RARE, mage.cards.h.HorizonCanopy.class)); + cards.add(new SetCardInfo("Hunt the Weak", 167, Rarity.COMMON, mage.cards.h.HuntTheWeak.class)); + cards.add(new SetCardInfo("Hunting Pack", 168, Rarity.UNCOMMON, mage.cards.h.HuntingPack.class)); + cards.add(new SetCardInfo("Hypersonic Dragon", 201, Rarity.RARE, mage.cards.h.HypersonicDragon.class)); + cards.add(new SetCardInfo("Illusory Ambusher", 58, Rarity.UNCOMMON, mage.cards.i.IllusoryAmbusher.class)); + cards.add(new SetCardInfo("Illusory Angel", 59, Rarity.UNCOMMON, mage.cards.i.IllusoryAngel.class)); + cards.add(new SetCardInfo("Indulgent Tormentor", 94, Rarity.UNCOMMON, mage.cards.i.IndulgentTormentor.class)); + cards.add(new SetCardInfo("Infantry Veteran", 24, Rarity.COMMON, mage.cards.i.InfantryVeteran.class)); + cards.add(new SetCardInfo("Inspiring Call", 169, Rarity.UNCOMMON, mage.cards.i.InspiringCall.class)); + cards.add(new SetCardInfo("Iona's Judgment", 25, Rarity.COMMON, mage.cards.i.IonasJudgment.class)); + cards.add(new SetCardInfo("Ivy Elemental", 170, Rarity.COMMON, mage.cards.i.IvyElemental.class)); + cards.add(new SetCardInfo("Izzet Boilerworks", 241, Rarity.UNCOMMON, mage.cards.i.IzzetBoilerworks.class)); + cards.add(new SetCardInfo("Jace's Phantasm", 60, Rarity.COMMON, mage.cards.j.JacesPhantasm.class)); + cards.add(new SetCardInfo("Jaddi Offshoot", 171, Rarity.COMMON, mage.cards.j.JaddiOffshoot.class)); + cards.add(new SetCardInfo("Jhessian Thief", 61, Rarity.COMMON, mage.cards.j.JhessianThief.class)); + cards.add(new SetCardInfo("Jin-Gitaxias, Core Augur", 62, Rarity.MYTHIC, mage.cards.j.JinGitaxiasCoreAugur.class)); + cards.add(new SetCardInfo("Jugan, the Rising Star", 172, Rarity.RARE, mage.cards.j.JuganTheRisingStar.class)); + cards.add(new SetCardInfo("Jungle Barrier", 202, Rarity.UNCOMMON, mage.cards.j.JungleBarrier.class)); + cards.add(new SetCardInfo("Keiga, the Tide Star", 63, Rarity.RARE, mage.cards.k.KeigaTheTideStar.class)); cards.add(new SetCardInfo("Keldon Halberdier", 135, Rarity.COMMON, mage.cards.k.KeldonHalberdier.class)); cards.add(new SetCardInfo("Kiki-Jiki, Mirror Breaker", 136, Rarity.MYTHIC, mage.cards.k.KikiJikiMirrorBreaker.class)); cards.add(new SetCardInfo("Kiln Fiend", 137, Rarity.COMMON, mage.cards.k.KilnFiend.class)); - cards.add(new SetCardInfo("Magus of the Moon", 138, Rarity.RARE, mage.cards.m.MagusOfTheMoon.class)); - cards.add(new SetCardInfo("Mark of Mutiny", 139, Rarity.COMMON, mage.cards.m.MarkOfMutiny.class)); - cards.add(new SetCardInfo("Monastery Swiftspear", 140, Rarity.UNCOMMON, mage.cards.m.MonasterySwiftspear.class)); - cards.add(new SetCardInfo("Pillar of Flame", 141, Rarity.COMMON, mage.cards.p.PillarOfFlame.class)); - cards.add(new SetCardInfo("Prodigal Pyromancer", 142, Rarity.UNCOMMON, mage.cards.p.ProdigalPyromancer.class)); - cards.add(new SetCardInfo("Rift Bolt", 143, Rarity.UNCOMMON, mage.cards.r.RiftBolt.class)); - cards.add(new SetCardInfo("Ryusei, the Falling Star", 144, Rarity.RARE, mage.cards.r.RyuseiTheFallingStar.class)); - cards.add(new SetCardInfo("Scourge of Valkas", 145, Rarity.RARE, mage.cards.s.ScourgeOfValkas.class)); - cards.add(new SetCardInfo("Splatter Thug", 146, Rarity.COMMON, mage.cards.s.SplatterThug.class)); - cards.add(new SetCardInfo("Staggershock", 147, Rarity.UNCOMMON, mage.cards.s.Staggershock.class)); - cards.add(new SetCardInfo("Surreal Memoir", 148, Rarity.UNCOMMON, mage.cards.s.SurrealMemoir.class)); - cards.add(new SetCardInfo("Thundermaw Hellkite", 149, Rarity.MYTHIC, mage.cards.t.ThundermawHellkite.class)); - cards.add(new SetCardInfo("Tormenting Voice", 150, Rarity.COMMON, mage.cards.t.TormentingVoice.class)); - cards.add(new SetCardInfo("Trumpet Blast", 151, Rarity.COMMON, mage.cards.t.TrumpetBlast.class)); - cards.add(new SetCardInfo("Urabrask the Hidden", 152, Rarity.MYTHIC, mage.cards.u.UrabraskTheHidden.class)); - cards.add(new SetCardInfo("Vent Sentinel", 153, Rarity.COMMON, mage.cards.v.VentSentinel.class)); - cards.add(new SetCardInfo("Aerial Predation", 154, Rarity.COMMON, mage.cards.a.AerialPredation.class)); - cards.add(new SetCardInfo("Assault Formation", 155, Rarity.UNCOMMON, mage.cards.a.AssaultFormation.class)); - cards.add(new SetCardInfo("Carven Caryatid", 156, Rarity.UNCOMMON, mage.cards.c.CarvenCaryatid.class)); - cards.add(new SetCardInfo("Channel", 157, Rarity.MYTHIC, mage.cards.c.Channel.class)); - cards.add(new SetCardInfo("Crowned Ceratok", 158, Rarity.COMMON, mage.cards.c.CrownedCeratok.class)); - cards.add(new SetCardInfo("Curse of Predation", 159, Rarity.RARE, mage.cards.c.CurseOfPredation.class)); - cards.add(new SetCardInfo("Durkwood Baloth", 160, Rarity.COMMON, mage.cards.d.DurkwoodBaloth.class)); - cards.add(new SetCardInfo("Duskdale Wurm", 161, Rarity.COMMON, mage.cards.d.DuskdaleWurm.class)); - cards.add(new SetCardInfo("Enlarge", 162, Rarity.UNCOMMON, mage.cards.e.Enlarge.class)); - cards.add(new SetCardInfo("Genesis Hydra", 163, Rarity.RARE, mage.cards.g.GenesisHydra.class)); - cards.add(new SetCardInfo("Genesis Wave", 164, Rarity.RARE, mage.cards.g.GenesisWave.class)); - cards.add(new SetCardInfo("Greater Basilisk", 165, Rarity.COMMON, mage.cards.g.GreaterBasilisk.class)); - cards.add(new SetCardInfo("Heroes' Bane", 166, Rarity.UNCOMMON, mage.cards.h.HeroesBane.class)); - cards.add(new SetCardInfo("Hunt the Weak", 167, Rarity.COMMON, mage.cards.h.HuntTheWeak.class)); - cards.add(new SetCardInfo("Hunting Pack", 168, Rarity.UNCOMMON, mage.cards.h.HuntingPack.class)); - cards.add(new SetCardInfo("Inspiring Call", 169, Rarity.UNCOMMON, mage.cards.i.InspiringCall.class)); - cards.add(new SetCardInfo("Ivy Elemental", 170, Rarity.COMMON, mage.cards.i.IvyElemental.class)); - cards.add(new SetCardInfo("Jaddi Offshoot", 171, Rarity.COMMON, mage.cards.j.JaddiOffshoot.class)); - cards.add(new SetCardInfo("Jugan, the Rising Star", 172, Rarity.RARE, mage.cards.j.JuganTheRisingStar.class)); + cards.add(new SetCardInfo("Knight of the Reliquary", 203, Rarity.RARE, mage.cards.k.KnightOfTheReliquary.class)); + cards.add(new SetCardInfo("Kokusho, the Evening Star", 95, Rarity.RARE, mage.cards.k.KokushoTheEveningStar.class)); + cards.add(new SetCardInfo("Kolaghan Monument", 217, Rarity.UNCOMMON, mage.cards.k.KolaghanMonument.class)); cards.add(new SetCardInfo("Lead the Stampede", 173, Rarity.COMMON, mage.cards.l.LeadTheStampede.class)); + cards.add(new SetCardInfo("Lightning Helix", 204, Rarity.UNCOMMON, mage.cards.l.LightningHelix.class)); + cards.add(new SetCardInfo("Lord of the Pit", 96, Rarity.RARE, mage.cards.l.LordOfThePit.class)); cards.add(new SetCardInfo("Lotus Cobra", 174, Rarity.RARE, mage.cards.l.LotusCobra.class)); cards.add(new SetCardInfo("Lure", 175, Rarity.UNCOMMON, mage.cards.l.Lure.class)); - cards.add(new SetCardInfo("Nantuko Shaman", 176, Rarity.COMMON, mage.cards.n.NantukoShaman.class)); - cards.add(new SetCardInfo("Nature's Claim", 177, Rarity.COMMON, mage.cards.n.NaturesClaim.class)); - cards.add(new SetCardInfo("Netcaster Spider", 178, Rarity.COMMON, mage.cards.n.NetcasterSpider.class)); - cards.add(new SetCardInfo("Obstinate Baloth", 179, Rarity.RARE, mage.cards.o.ObstinateBaloth.class)); - cards.add(new SetCardInfo("Overgrown Battlement", 180, Rarity.UNCOMMON, mage.cards.o.OvergrownBattlement.class)); - cards.add(new SetCardInfo("Phantom Tiger", 181, Rarity.COMMON, mage.cards.p.PhantomTiger.class)); - cards.add(new SetCardInfo("Prey's Vengeance", 182, Rarity.COMMON, mage.cards.p.PreysVengeance.class)); - cards.add(new SetCardInfo("Primeval Titan", 183, Rarity.MYTHIC, mage.cards.p.PrimevalTitan.class)); - cards.add(new SetCardInfo("Rampaging Baloths", 184, Rarity.RARE, mage.cards.r.RampagingBaloths.class)); - cards.add(new SetCardInfo("Search for Tomorrow", 185, Rarity.COMMON, mage.cards.s.SearchForTomorrow.class)); - cards.add(new SetCardInfo("Sultai Flayer", 186, Rarity.UNCOMMON, mage.cards.s.SultaiFlayer.class)); - cards.add(new SetCardInfo("Timberland Guide", 187, Rarity.COMMON, mage.cards.t.TimberlandGuide.class)); - cards.add(new SetCardInfo("Undercity Troll", 188, Rarity.UNCOMMON, mage.cards.u.UndercityTroll.class)); - cards.add(new SetCardInfo("Vorinclex, Voice of Hunger", 189, Rarity.MYTHIC, mage.cards.v.VorinclexVoiceOfHunger.class)); - cards.add(new SetCardInfo("Wall of Roots", 190, Rarity.COMMON, mage.cards.w.WallOfRoots.class)); - cards.add(new SetCardInfo("Wildsize", 191, Rarity.COMMON, mage.cards.w.Wildsize.class)); - cards.add(new SetCardInfo("Azorius Charm", 192, Rarity.UNCOMMON, mage.cards.a.AzoriusCharm.class)); - cards.add(new SetCardInfo("Bladewing the Risen", 193, Rarity.UNCOMMON, mage.cards.b.BladewingTheRisen.class)); - cards.add(new SetCardInfo("Blizzard Specter", 194, Rarity.UNCOMMON, mage.cards.b.BlizzardSpecter.class)); - cards.add(new SetCardInfo("Blood Baron of Vizkopa", 195, Rarity.RARE, mage.cards.b.BloodBaronOfVizkopa.class)); - cards.add(new SetCardInfo("Chronicler of Heroes", 196, Rarity.UNCOMMON, mage.cards.c.ChroniclerOfHeroes.class)); - cards.add(new SetCardInfo("Corpsejack Menace", 197, Rarity.UNCOMMON, mage.cards.c.CorpsejackMenace.class)); - cards.add(new SetCardInfo("Electrolyze", 198, Rarity.UNCOMMON, mage.cards.e.Electrolyze.class)); - cards.add(new SetCardInfo("Firemane Angel", 199, Rarity.RARE, mage.cards.f.FiremaneAngel.class)); - cards.add(new SetCardInfo("Glimpse the Unthinkable", 200, Rarity.RARE, mage.cards.g.GlimpseTheUnthinkable.class)); - cards.add(new SetCardInfo("Hypersonic Dragon", 201, Rarity.RARE, mage.cards.h.HypersonicDragon.class)); - cards.add(new SetCardInfo("Jungle Barrier", 202, Rarity.UNCOMMON, mage.cards.j.JungleBarrier.class)); - cards.add(new SetCardInfo("Knight of the Reliquary", 203, Rarity.RARE, mage.cards.k.KnightOfTheReliquary.class)); - cards.add(new SetCardInfo("Lightning Helix", 204, Rarity.UNCOMMON, mage.cards.l.LightningHelix.class)); + cards.add(new SetCardInfo("Magus of the Moon", 138, Rarity.RARE, mage.cards.m.MagusOfTheMoon.class)); + cards.add(new SetCardInfo("Mahamoti Djinn", 64, Rarity.UNCOMMON, mage.cards.m.MahamotiDjinn.class)); cards.add(new SetCardInfo("Malfegor", 205, Rarity.RARE, mage.cards.m.Malfegor.class)); - cards.add(new SetCardInfo("Rosheen Meanderer", 206, Rarity.UNCOMMON, mage.cards.r.RosheenMeanderer.class)); - cards.add(new SetCardInfo("Savageborn Hydra", 207, Rarity.RARE, mage.cards.s.SavagebornHydra.class)); - cards.add(new SetCardInfo("Simic Sky Swallower", 208, Rarity.RARE, mage.cards.s.SimicSkySwallower.class)); - cards.add(new SetCardInfo("Spiritmonger", 209, Rarity.RARE, mage.cards.s.Spiritmonger.class)); - cards.add(new SetCardInfo("Supreme Verdict", 210, Rarity.RARE, mage.cards.s.SupremeVerdict.class)); - cards.add(new SetCardInfo("Vizkopa Guildmage", 211, Rarity.UNCOMMON, mage.cards.v.VizkopaGuildmage.class)); - cards.add(new SetCardInfo("Aether Vial", 212, Rarity.RARE, mage.cards.a.AetherVial.class)); - cards.add(new SetCardInfo("Bubbling Cauldron", 213, Rarity.UNCOMMON, mage.cards.b.BubblingCauldron.class)); - cards.add(new SetCardInfo("Darksteel Axe", 214, Rarity.COMMON, mage.cards.d.DarksteelAxe.class)); - cards.add(new SetCardInfo("Dragonloft Idol", 215, Rarity.UNCOMMON, mage.cards.d.DragonloftIdol.class)); - cards.add(new SetCardInfo("Guardian Idol", 216, Rarity.COMMON, mage.cards.g.GuardianIdol.class)); - cards.add(new SetCardInfo("Kolaghan Monument", 217, Rarity.UNCOMMON, mage.cards.k.KolaghanMonument.class)); + cards.add(new SetCardInfo("Mana Drain", 65, Rarity.MYTHIC, mage.cards.m.ManaDrain.class)); + cards.add(new SetCardInfo("Mana Leak", 66, Rarity.COMMON, mage.cards.m.ManaLeak.class)); cards.add(new SetCardInfo("Manakin", 218, Rarity.COMMON, mage.cards.m.Manakin.class)); + cards.add(new SetCardInfo("Mark of Mutiny", 139, Rarity.COMMON, mage.cards.m.MarkOfMutiny.class)); + cards.add(new SetCardInfo("Mer-Ek Nightblade", 97, Rarity.UNCOMMON, mage.cards.m.MerEkNightblade.class)); cards.add(new SetCardInfo("Mind Stone", 219, Rarity.COMMON, mage.cards.m.MindStone.class)); cards.add(new SetCardInfo("Mindcrank", 220, Rarity.UNCOMMON, mage.cards.m.Mindcrank.class)); cards.add(new SetCardInfo("Mishra's Bauble", 221, Rarity.UNCOMMON, mage.cards.m.MishrasBauble.class)); + cards.add(new SetCardInfo("Mnemonic Wall", 67, Rarity.COMMON, mage.cards.m.MnemonicWall.class)); + cards.add(new SetCardInfo("Monastery Swiftspear", 140, Rarity.UNCOMMON, mage.cards.m.MonasterySwiftspear.class)); cards.add(new SetCardInfo("Moonglove Extract", 222, Rarity.COMMON, mage.cards.m.MoongloveExtract.class)); - cards.add(new SetCardInfo("Oblivion Stone", 223, Rarity.RARE, mage.cards.o.OblivionStone.class)); - cards.add(new SetCardInfo("Palladium Myr", 224, Rarity.UNCOMMON, mage.cards.p.PalladiumMyr.class)); - cards.add(new SetCardInfo("Pristine Talisman", 225, Rarity.UNCOMMON, mage.cards.p.PristineTalisman.class)); - cards.add(new SetCardInfo("Runed Servitor", 226, Rarity.COMMON, mage.cards.r.RunedServitor.class)); - cards.add(new SetCardInfo("Sandstone Oracle", 227, Rarity.UNCOMMON, mage.cards.s.SandstoneOracle.class)); - cards.add(new SetCardInfo("Serum Powder", 228, Rarity.RARE, mage.cards.s.SerumPowder.class)); - cards.add(new SetCardInfo("Star Compass", 229, Rarity.COMMON, mage.cards.s.StarCompass.class)); - cards.add(new SetCardInfo("Thran Dynamo", 230, Rarity.UNCOMMON, mage.cards.t.ThranDynamo.class)); - cards.add(new SetCardInfo("Trepanation Blade", 231, Rarity.UNCOMMON, mage.cards.t.TrepanationBlade.class)); - cards.add(new SetCardInfo("Azorius Chancery", 232, Rarity.UNCOMMON, mage.cards.a.AzoriusChancery.class)); - cards.add(new SetCardInfo("Boros Garrison", 233, Rarity.UNCOMMON, mage.cards.b.BorosGarrison.class)); - cards.add(new SetCardInfo("Dimir Aqueduct", 234, Rarity.UNCOMMON, mage.cards.d.DimirAqueduct.class)); - cards.add(new SetCardInfo("Evolving Wilds", 235, Rarity.COMMON, mage.cards.e.EvolvingWilds.class)); - cards.add(new SetCardInfo("Golgari Rot Farm", 236, Rarity.UNCOMMON, mage.cards.g.GolgariRotFarm.class)); - cards.add(new SetCardInfo("Graven Cairns", 237, Rarity.RARE, mage.cards.g.GravenCairns.class)); - cards.add(new SetCardInfo("Grove of the Burnwillows", 238, Rarity.RARE, mage.cards.g.GroveOfTheBurnwillows.class)); - cards.add(new SetCardInfo("Gruul Turf", 239, Rarity.UNCOMMON, mage.cards.g.GruulTurf.class)); - cards.add(new SetCardInfo("Horizon Canopy", 240, Rarity.RARE, mage.cards.h.HorizonCanopy.class)); - cards.add(new SetCardInfo("Izzet Boilerworks", 241, Rarity.UNCOMMON, mage.cards.i.IzzetBoilerworks.class)); + cards.add(new SetCardInfo("Nantuko Shaman", 176, Rarity.COMMON, mage.cards.n.NantukoShaman.class)); + cards.add(new SetCardInfo("Nature's Claim", 177, Rarity.COMMON, mage.cards.n.NaturesClaim.class)); + cards.add(new SetCardInfo("Necropotence", 98, Rarity.MYTHIC, mage.cards.n.Necropotence.class)); + cards.add(new SetCardInfo("Netcaster Spider", 178, Rarity.COMMON, mage.cards.n.NetcasterSpider.class)); + cards.add(new SetCardInfo("Night of Souls' Betrayal", 99, Rarity.RARE, mage.cards.n.NightOfSoulsBetrayal.class)); cards.add(new SetCardInfo("Nimbus Maze", 242, Rarity.RARE, mage.cards.n.NimbusMaze.class)); + cards.add(new SetCardInfo("Noxious Dragon", 100, Rarity.UNCOMMON, mage.cards.n.NoxiousDragon.class)); + cards.add(new SetCardInfo("Ob Nixilis, the Fallen", 101, Rarity.MYTHIC, mage.cards.o.ObNixilisTheFallen.class)); + cards.add(new SetCardInfo("Oblivion Stone", 223, Rarity.RARE, mage.cards.o.OblivionStone.class)); + cards.add(new SetCardInfo("Obstinate Baloth", 179, Rarity.RARE, mage.cards.o.ObstinateBaloth.class)); + cards.add(new SetCardInfo("Ojutai's Breath", 68, Rarity.COMMON, mage.cards.o.OjutaisBreath.class)); cards.add(new SetCardInfo("Orzhov Basilica", 243, Rarity.UNCOMMON, mage.cards.o.OrzhovBasilica.class)); + cards.add(new SetCardInfo("Overgrown Battlement", 180, Rarity.UNCOMMON, mage.cards.o.OvergrownBattlement.class)); + cards.add(new SetCardInfo("Palladium Myr", 224, Rarity.UNCOMMON, mage.cards.p.PalladiumMyr.class)); + cards.add(new SetCardInfo("Path of Bravery", 26, Rarity.RARE, mage.cards.p.PathOfBravery.class)); + cards.add(new SetCardInfo("Pentarch Ward", 27, Rarity.COMMON, mage.cards.p.PentarchWard.class)); + cards.add(new SetCardInfo("Phantom Monster", 69, Rarity.COMMON, mage.cards.p.PhantomMonster.class)); + cards.add(new SetCardInfo("Phantom Tiger", 181, Rarity.COMMON, mage.cards.p.PhantomTiger.class)); + cards.add(new SetCardInfo("Phyrexian Rager", 102, Rarity.COMMON, mage.cards.p.PhyrexianRager.class)); + cards.add(new SetCardInfo("Pillar of Flame", 141, Rarity.COMMON, mage.cards.p.PillarOfFlame.class)); + cards.add(new SetCardInfo("Prey's Vengeance", 182, Rarity.COMMON, mage.cards.p.PreysVengeance.class)); + cards.add(new SetCardInfo("Primeval Titan", 183, Rarity.MYTHIC, mage.cards.p.PrimevalTitan.class)); + cards.add(new SetCardInfo("Pristine Talisman", 225, Rarity.UNCOMMON, mage.cards.p.PristineTalisman.class)); + cards.add(new SetCardInfo("Prodigal Pyromancer", 142, Rarity.UNCOMMON, mage.cards.p.ProdigalPyromancer.class)); cards.add(new SetCardInfo("Radiant Fountain", 244, Rarity.COMMON, mage.cards.r.RadiantFountain.class)); cards.add(new SetCardInfo("Rakdos Carnarium", 245, Rarity.UNCOMMON, mage.cards.r.RakdosCarnarium.class)); + cards.add(new SetCardInfo("Rakdos Drake", 103, Rarity.COMMON, mage.cards.r.RakdosDrake.class)); + cards.add(new SetCardInfo("Rampaging Baloths", 184, Rarity.RARE, mage.cards.r.RampagingBaloths.class)); + cards.add(new SetCardInfo("Reave Soul", 104, Rarity.COMMON, mage.cards.r.ReaveSoul.class)); + cards.add(new SetCardInfo("Repeal", 70, Rarity.COMMON, mage.cards.r.Repeal.class)); + cards.add(new SetCardInfo("Restoration Angel", 28, Rarity.RARE, mage.cards.r.RestorationAngel.class)); + cards.add(new SetCardInfo("Rift Bolt", 143, Rarity.UNCOMMON, mage.cards.r.RiftBolt.class)); cards.add(new SetCardInfo("River of Tears", 246, Rarity.RARE, mage.cards.r.RiverOfTears.class)); + cards.add(new SetCardInfo("Riverwheel Aerialists", 71, Rarity.COMMON, mage.cards.r.RiverwheelAerialists.class)); + cards.add(new SetCardInfo("Rosheen Meanderer", 206, Rarity.UNCOMMON, mage.cards.r.RosheenMeanderer.class)); + cards.add(new SetCardInfo("Rotfeaster Maggot", 105, Rarity.COMMON, mage.cards.r.RotfeasterMaggot.class)); + cards.add(new SetCardInfo("Rune-Scarred Demon", 106, Rarity.RARE, mage.cards.r.RuneScarredDemon.class)); + cards.add(new SetCardInfo("Runed Servitor", 226, Rarity.COMMON, mage.cards.r.RunedServitor.class)); + cards.add(new SetCardInfo("Ryusei, the Falling Star", 144, Rarity.RARE, mage.cards.r.RyuseiTheFallingStar.class)); + cards.add(new SetCardInfo("Sandstone Oracle", 227, Rarity.UNCOMMON, mage.cards.s.SandstoneOracle.class)); + cards.add(new SetCardInfo("Sanguine Bond", 107, Rarity.UNCOMMON, mage.cards.s.SanguineBond.class)); + cards.add(new SetCardInfo("Savageborn Hydra", 207, Rarity.RARE, mage.cards.s.SavagebornHydra.class)); + cards.add(new SetCardInfo("Scion of Ugin", 1, Rarity.COMMON, mage.cards.s.ScionOfUgin.class)); + cards.add(new SetCardInfo("Scourge of Valkas", 145, Rarity.RARE, mage.cards.s.ScourgeOfValkas.class)); + cards.add(new SetCardInfo("Search for Tomorrow", 185, Rarity.COMMON, mage.cards.s.SearchForTomorrow.class)); + cards.add(new SetCardInfo("Seeker of the Way", 29, Rarity.COMMON, mage.cards.s.SeekerOfTheWay.class)); cards.add(new SetCardInfo("Selesnya Sanctuary", 247, Rarity.UNCOMMON, mage.cards.s.SelesnyaSanctuary.class)); + cards.add(new SetCardInfo("Serra Angel", 30, Rarity.UNCOMMON, mage.cards.s.SerraAngel.class)); + cards.add(new SetCardInfo("Serra Ascendant", 31, Rarity.RARE, mage.cards.s.SerraAscendant.class)); + cards.add(new SetCardInfo("Serum Powder", 228, Rarity.RARE, mage.cards.s.SerumPowder.class)); + cards.add(new SetCardInfo("Sheoldred, Whispering One", 108, Rarity.MYTHIC, mage.cards.s.SheoldredWhisperingOne.class)); cards.add(new SetCardInfo("Shimmering Grotto", 248, Rarity.COMMON, mage.cards.s.ShimmeringGrotto.class)); + cards.add(new SetCardInfo("Shriekgeist", 72, Rarity.COMMON, mage.cards.s.Shriekgeist.class)); cards.add(new SetCardInfo("Simic Growth Chamber", 249, Rarity.UNCOMMON, mage.cards.s.SimicGrowthChamber.class)); - + cards.add(new SetCardInfo("Simic Sky Swallower", 208, Rarity.RARE, mage.cards.s.SimicSkySwallower.class)); + cards.add(new SetCardInfo("Skywise Teachings", 73, Rarity.UNCOMMON, mage.cards.s.SkywiseTeachings.class)); + cards.add(new SetCardInfo("Sphinx of Uthuun", 74, Rarity.RARE, mage.cards.s.SphinxOfUthuun.class)); + cards.add(new SetCardInfo("Spiritmonger", 209, Rarity.RARE, mage.cards.s.Spiritmonger.class)); + cards.add(new SetCardInfo("Splatter Thug", 146, Rarity.COMMON, mage.cards.s.SplatterThug.class)); + cards.add(new SetCardInfo("Staggershock", 147, Rarity.UNCOMMON, mage.cards.s.Staggershock.class)); + cards.add(new SetCardInfo("Stalwart Aven", 32, Rarity.COMMON, mage.cards.s.StalwartAven.class)); + cards.add(new SetCardInfo("Star Compass", 229, Rarity.COMMON, mage.cards.s.StarCompass.class)); + cards.add(new SetCardInfo("Student of Ojutai", 33, Rarity.COMMON, mage.cards.s.StudentOfOjutai.class)); + cards.add(new SetCardInfo("Sultai Flayer", 186, Rarity.UNCOMMON, mage.cards.s.SultaiFlayer.class)); + cards.add(new SetCardInfo("Supreme Verdict", 210, Rarity.RARE, mage.cards.s.SupremeVerdict.class)); + cards.add(new SetCardInfo("Surreal Memoir", 148, Rarity.UNCOMMON, mage.cards.s.SurrealMemoir.class)); + cards.add(new SetCardInfo("Survival Cache", 34, Rarity.COMMON, mage.cards.s.SurvivalCache.class)); + cards.add(new SetCardInfo("Sustainer of the Realm", 35, Rarity.COMMON, mage.cards.s.SustainerOfTheRealm.class)); + cards.add(new SetCardInfo("Swords to Plowshares", 36, Rarity.UNCOMMON, mage.cards.s.SwordsToPlowshares.class)); + cards.add(new SetCardInfo("Tavern Swindler", 109, Rarity.UNCOMMON, mage.cards.t.TavernSwindler.class)); + cards.add(new SetCardInfo("Teferi, Mage of Zhalfir", 75, Rarity.RARE, mage.cards.t.TeferiMageOfZhalfir.class)); + cards.add(new SetCardInfo("Thought Scour", 76, Rarity.COMMON, mage.cards.t.ThoughtScour.class)); + cards.add(new SetCardInfo("Thoughtseize", 110, Rarity.RARE, mage.cards.t.Thoughtseize.class)); + cards.add(new SetCardInfo("Thran Dynamo", 230, Rarity.UNCOMMON, mage.cards.t.ThranDynamo.class)); + cards.add(new SetCardInfo("Thrill-Kill Assassin", 111, Rarity.COMMON, mage.cards.t.ThrillKillAssassin.class)); + cards.add(new SetCardInfo("Thundermaw Hellkite", 149, Rarity.MYTHIC, mage.cards.t.ThundermawHellkite.class)); + cards.add(new SetCardInfo("Timberland Guide", 187, Rarity.COMMON, mage.cards.t.TimberlandGuide.class)); + cards.add(new SetCardInfo("Topan Freeblade", 37, Rarity.UNCOMMON, mage.cards.t.TopanFreeblade.class)); + cards.add(new SetCardInfo("Tormenting Voice", 150, Rarity.COMMON, mage.cards.t.TormentingVoice.class)); + cards.add(new SetCardInfo("Trepanation Blade", 231, Rarity.UNCOMMON, mage.cards.t.TrepanationBlade.class)); + cards.add(new SetCardInfo("Trumpet Blast", 151, Rarity.COMMON, mage.cards.t.TrumpetBlast.class)); + cards.add(new SetCardInfo("Ulcerate", 112, Rarity.UNCOMMON, mage.cards.u.Ulcerate.class)); + cards.add(new SetCardInfo("Undercity Troll", 188, Rarity.UNCOMMON, mage.cards.u.UndercityTroll.class)); + cards.add(new SetCardInfo("Urabrask the Hidden", 152, Rarity.MYTHIC, mage.cards.u.UrabraskTheHidden.class)); + cards.add(new SetCardInfo("Vent Sentinel", 153, Rarity.COMMON, mage.cards.v.VentSentinel.class)); + cards.add(new SetCardInfo("Virulent Swipe", 113, Rarity.COMMON, mage.cards.v.VirulentSwipe.class)); + cards.add(new SetCardInfo("Vizkopa Guildmage", 211, Rarity.UNCOMMON, mage.cards.v.VizkopaGuildmage.class)); + cards.add(new SetCardInfo("Vorinclex, Voice of Hunger", 189, Rarity.MYTHIC, mage.cards.v.VorinclexVoiceOfHunger.class)); + cards.add(new SetCardInfo("Wall of Roots", 190, Rarity.COMMON, mage.cards.w.WallOfRoots.class)); + cards.add(new SetCardInfo("Wight of Precinct Six", 114, Rarity.COMMON, mage.cards.w.WightOfPrecinctSix.class)); + cards.add(new SetCardInfo("Wildsize", 191, Rarity.COMMON, mage.cards.w.Wildsize.class)); + cards.add(new SetCardInfo("Windfall", 77, Rarity.UNCOMMON, mage.cards.w.Windfall.class)); + cards.add(new SetCardInfo("Wing Shards", 38, Rarity.UNCOMMON, mage.cards.w.WingShards.class)); + cards.add(new SetCardInfo("Wrench Mind", 115, Rarity.COMMON, mage.cards.w.WrenchMind.class)); + cards.add(new SetCardInfo("Yosei, the Morning Star", 39, Rarity.RARE, mage.cards.y.YoseiTheMorningStar.class)); } } From fc2f2d48203e57ba8c6a0e73978e3b03baf4f130 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 12 Sep 2019 10:24:55 -0400 Subject: [PATCH 086/373] Implemented Phell the Pheasant --- .../src/mage/cards/f/FellThePheasant.java | 46 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + Utils/mtg-cards-data.txt | 1 + 3 files changed, 48 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/f/FellThePheasant.java diff --git a/Mage.Sets/src/mage/cards/f/FellThePheasant.java b/Mage.Sets/src/mage/cards/f/FellThePheasant.java new file mode 100644 index 0000000000..14c4c01826 --- /dev/null +++ b/Mage.Sets/src/mage/cards/f/FellThePheasant.java @@ -0,0 +1,46 @@ +package mage.cards.f; + +import mage.abilities.effects.common.CreateTokenEffect; +import mage.abilities.effects.common.DamageTargetEffect; +import mage.abilities.keyword.FlyingAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterCreaturePermanent; +import mage.filter.predicate.mageobject.AbilityPredicate; +import mage.game.permanent.token.FoodToken; +import mage.target.TargetPermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class FellThePheasant extends CardImpl { + + + private static final FilterPermanent filter = new FilterCreaturePermanent("creature with flying."); + + static { + filter.add(new AbilityPredicate(FlyingAbility.class)); + } + + public FellThePheasant(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.INSTANT}, "{1}{G}"); + + // Fell the Pheasant deals 5 damage to target creature with flying. Create a Food token. + this.getSpellAbility().addEffect(new DamageTargetEffect(5)); + this.getSpellAbility().addEffect(new CreateTokenEffect(new FoodToken())); + this.getSpellAbility().addTarget(new TargetPermanent(filter)); + } + + private FellThePheasant(final FellThePheasant card) { + super(card); + } + + @Override + public FellThePheasant copy() { + return new FellThePheasant(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index efde2345e4..710640b618 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -66,6 +66,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Faerie Guidemother", 11, Rarity.COMMON, mage.cards.f.FaerieGuidemother.class)); cards.add(new SetCardInfo("Faerie Vandal", 45, Rarity.UNCOMMON, mage.cards.f.FaerieVandal.class)); cards.add(new SetCardInfo("Feasting Troll King", 152, Rarity.RARE, mage.cards.f.FeastingTrollKing.class)); + cards.add(new SetCardInfo("Fell the Pheasant", 153, Rarity.COMMON, mage.cards.f.FellThePheasant.class)); cards.add(new SetCardInfo("Fireborn Knight", 210, Rarity.UNCOMMON, mage.cards.f.FirebornKnight.class)); cards.add(new SetCardInfo("Flaxen Intruder", 155, Rarity.UNCOMMON, mage.cards.f.FlaxenIntruder.class)); cards.add(new SetCardInfo("Foulmire Knight", 90, Rarity.UNCOMMON, mage.cards.f.FoulmireKnight.class)); diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index d2e655c136..cc4931a096 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -36075,6 +36075,7 @@ Fertile Footsteps|Throne of Eldraine|149|U|{2}{G}|Sorcery - Adventure|*|*|Search Curious Pair|Throne of Eldraine|150|C|{1}{G}|Creature - Human Peasant|1|3|| Treats to Share|Throne of Eldraine|150|C|{G}|Sorcery - Adventure|1|3|Create a Food token.| Feasting Troll King|Throne of Eldraine|152|R|{2}{G}{G}{G}{G}|Creature - Troll Noble|7|6|Vigilance, trample$When Feasting Troll King enters the battlefield, if you cast it from your hand, create three Food tokens.$Sacrifice three Foods: Return Feasting Troll King from your graveyard to the battlefield. Activate this ability only during your turn.| +Fell the Pheasant|Throne of Eldraine|153|C|{1}{G}|Instant|||Fell the Pheasant deals 5 damage to target creature with flying. Create a Food token.| Flaxen Intruder|Throne of Eldraine|155|U|{G}|Creature - Human Berserker|1|2|Whenever Flaxen Intruder deals combat damage to a player, you may sacrifice it. When you do, destroy target artifact or enchantment.| Welcome Home|Throne of Eldraine|155|U|{5}{G}{G}|Sorcery - Adventure|1|2|Create three 2/2 green Bear creature tokens.| Garenbrig Paladin|Throne of Eldraine|157|C|{4}{G}|Creature - Giant Knight|4|4|Adamant — If at least three green mana was spent to cast this spell, Garenbrig Paladin enters the battlefield with a +1/+1 counter on it.$Garenbrig Paladin can't be blocked by creatures with power 2 or less.| From 12828b78d631755b1551450a1a4e2c0ec9590d41 Mon Sep 17 00:00:00 2001 From: Adrian Petrescu Date: Thu, 12 Sep 2019 14:32:59 -0400 Subject: [PATCH 087/373] Check Archfiend of Spite trigger on CREATURE_DAMAGED Currently, it ignored the trigger unless a player was also damaged (by other unblocked attacking creatures, for example), so there are plenty of situations where it will fail to occur. The included test fails against current master, but passes with the patch. Fixes #5971. --- .../src/mage/cards/a/ArchfiendOfSpite.java | 2 +- .../cards/single/ArchfiendOfSpiteTest.java | 32 +++++++++++++++++++ 2 files changed, 33 insertions(+), 1 deletion(-) create mode 100644 Mage.Tests/src/test/java/org/mage/test/cards/single/ArchfiendOfSpiteTest.java diff --git a/Mage.Sets/src/mage/cards/a/ArchfiendOfSpite.java b/Mage.Sets/src/mage/cards/a/ArchfiendOfSpite.java index be75084658..fc186f0ba0 100644 --- a/Mage.Sets/src/mage/cards/a/ArchfiendOfSpite.java +++ b/Mage.Sets/src/mage/cards/a/ArchfiendOfSpite.java @@ -73,7 +73,7 @@ class ArchfiendOfSpiteAbility extends TriggeredAbilityImpl { @Override public boolean checkEventType(GameEvent event, Game game) { - return event.getType() == GameEvent.EventType.DAMAGED_PLAYER; + return event.getType() == GameEvent.EventType.DAMAGED_CREATURE; } @Override diff --git a/Mage.Tests/src/test/java/org/mage/test/cards/single/ArchfiendOfSpiteTest.java b/Mage.Tests/src/test/java/org/mage/test/cards/single/ArchfiendOfSpiteTest.java new file mode 100644 index 0000000000..00622f1471 --- /dev/null +++ b/Mage.Tests/src/test/java/org/mage/test/cards/single/ArchfiendOfSpiteTest.java @@ -0,0 +1,32 @@ +package org.mage.test.cards.single; + +import mage.constants.PhaseStep; +import mage.constants.Zone; +import org.junit.Assert; +import org.junit.Test; +import org.mage.test.serverside.base.CardTestPlayerBase; + +public class ArchfiendOfSpiteTest extends CardTestPlayerBase { + + @Test + public void damageTriggerTest() { + addCard(Zone.BATTLEFIELD, playerA, "Archfiend of Spite"); + addCard(Zone.BATTLEFIELD, playerB, "Mountain", 1); + addCard(Zone.HAND, playerB, "Lightning Bolt", 1); + setStopAt(1, PhaseStep.UNTAP); + execute(); + + assertPermanentCount(playerA, "Archfiend of Spite", 1); + assertLife(playerB, 20); + + castSpell(1, PhaseStep.PRECOMBAT_MAIN, playerB, "Lightning Bolt", "Archfiend of Spite"); + setStopAt(1, PhaseStep.POSTCOMBAT_MAIN); + setStrictChooseMode(true); + execute(); + + assertPermanentCount(playerA, "Archfiend of Spite", 1); + assertPermanentCount(playerB, "Mountain", 1); + assertDamageReceived(playerA, "Archfiend of Spite", 3); + assertLife(playerB, 17); + } +} From d79ee886ee770ea4e914defdd4a1427d3fb9d259 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 12 Sep 2019 16:18:44 -0400 Subject: [PATCH 088/373] updated ELD spoiler --- Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 2 +- Utils/mtg-cards-data.txt | 16 +++++++++++++++- 2 files changed, 16 insertions(+), 2 deletions(-) diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 710640b618..7b5619457c 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -138,7 +138,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Steelbane Hydra", 322, Rarity.RARE, mage.cards.s.SteelbaneHydra.class)); cards.add(new SetCardInfo("Steelclaw Lance", 202, Rarity.UNCOMMON, mage.cards.s.SteelclawLance.class)); cards.add(new SetCardInfo("Syr Carah, the Bold", 145, Rarity.UNCOMMON, mage.cards.s.SyrCarahTheBold.class)); - cards.add(new SetCardInfo("Syr Elenora the Discerning", 67, Rarity.UNCOMMON, mage.cards.s.SyrElenoraTheDiscerning.class)); + cards.add(new SetCardInfo("Syr Elenora, the Discerning", 67, Rarity.UNCOMMON, mage.cards.s.SyrElenoraTheDiscerning.class)); cards.add(new SetCardInfo("Syr Gwyn, Hero of Ashvale", 330, Rarity.MYTHIC, mage.cards.s.SyrGwynHeroOfAshvale.class)); cards.add(new SetCardInfo("Syr Konrad, the Grim", 107, Rarity.UNCOMMON, mage.cards.s.SyrKonradTheGrim.class)); cards.add(new SetCardInfo("Taste of Death", 320, Rarity.RARE, mage.cards.t.TasteOfDeath.class)); diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index cc4931a096..4c0fe3638b 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -35994,14 +35994,19 @@ Swamp|Commander 2019|294|C||Basic Land - Swamp|||({T}: Add {B}.)| Mountain|Commander 2019|297|C||Basic Land - Mountain|||({T}: Add {R}.)| Forest|Commander 2019|300|C||Basic Land - Forest|||({T}: Add {G}.)| All That Glitters|Throne of Eldraine|2|U|{1}{W}|Enchantment - Aura|||Enchant creature$Enchanted creature gets +1/+1 for each artifact and/or enchantment you control.| +Ardenvale Tactician|Throne of Eldraine|5|C|{1}{W}{W}|Creature - Human Knight|2|3|Flying| +Dizzying Swoop|Throne of Eldraine|5|C|{1}{W}|Instant - Adventure|2|3|Tap up to two target creatures.| Beloved Princess|Throne of Eldraine|7|C|{W}|Creature - Human Noble|1|1|Lifelink$Beloved Princess can't be blocked by creatures with power 3 or greater.| Charming Prince|Throne of Eldraine|8|R|{1}{W}|Creature - Human Noble|2|2|When Charming Prince enters the battlefield, choose one —$• Scry 2.$• You gain 3 life.$• Exile another target creature you own. Return it to the battlefield under your control at the beginning of the next end step.| The Circle of Loyalty|Throne of Eldraine|9|M|{4}{W}{W}|Legendary Artifact|||This spell costs {1} less to cast for each Knight you control.$Creatures you control get +1/+1.$Whenever you cast a legendary spell, create a 2/2 white Knight creature token with vigilance.${3}{W}, {T}: Create a 2/2 white Knight creature token with vigilance.| +Deafening Silence|Throne of Eldraine|10|U|{W}|Enchantment|||Each player can't cast more than one noncreature spell each turn.| Faerie Guidemother|Throne of Eldraine|11|C|{W}|Creature - Faerie|1|1|Flying| Gift of the Fae|Throne of Eldraine|11|C|{1}{W}|Sorcery - Adventure|1|1|Target creature gets +2/+1 and gains flying until end of turn.| Chop Down|Throne of Eldraine|14|R|{2}{W}|Instant - Adventure|1|2|Destroy target creature with power 4 or greater.| Giant Killer|Throne of Eldraine|14|R|{W}|Creature - Human Peasant|1|2|{1}{W}, {T}: Tap target creature.| +Glass Casket|Throne of Eldraine|15|U|{1}{W}|Artifact|||When Glass Casket enters the battlefield, exile target creature an opponent controls with converted mana cost 3 or less until Glass Casket leaves the battlefield.| Harmonious Archon|Throne of Eldraine|17|M|{4}{W}{W}|Creature - Archon|4|5|Flying$Non-Archon creatures have base power and toughness 3/3.$When Harmonious Archon enters the battlefield, create two 1/1 white Human creature tokens.| +Knight of the Keep|Throne of Eldraine|19|C|{2}{W}|Creature - Human Knight|3|2|| Righteousness|Throne of Eldraine|27|U|{W}|Instant|||Target blocking creature gets +7/+7 until end of turn.| Shining Armor|Throne of Eldraine|29|C|{1}{W}|Artifact - Equipment|||Flash$When Shining Armor enters the battlefield, attach it to target Knight you control.$Equipped creature gets +0/+2 and has vigilance.$Equip {3}| Silverflame Ritual|Throne of Eldraine|30|C|{3}{W}|Sorcery|||Put a +1/+1 counter on each creature you control.$Adamant — If at least three white mana was spent to cast this spell, creatures you control gain vigilance until end of turn.| @@ -36022,7 +36027,8 @@ Midnight Clock|Throne of Eldraine|54|R|{2}{U}|Artifact|||{T}: Add {U}.${2}{U}: P Mystical Dispute|Throne of Eldraine|58|U|{2}{U}|Instant|||This spell costs {2} less to cast if it targets a blue spell.$Counter target spell unless its controller pays {3}.| Opt|Throne of Eldraine|59|C|{U}|Instant|||Scry 1.$Draw a card.| Run Away Together|Throne of Eldraine|62|C|{1}{U}|Instant|||Choose two target creatures controlled by different players. Return those creatures to their owners' hands.| -Syr Elenora the Discerning|Throne of Eldraine|67|U|{3}{U}{U}|Legendary Creature - Human Knight|*|4|Syr Elenora the Discerning's power is equal to the number of cards in your hand.$When Syr Elenora enters the battlefield, draw a card.$Spells your opponents cast that target Syr Elenora cost {2} more to cast.| +Stolen by the Fae|Throne of Eldraine|66|R|{X}{U}{U}|Sorcery|||Return target creature with converted mana cost X to its owner's hand. You create X 1/1 blue Faerie creature tokens with flying.| +Syr Elenora, the Discerning|Throne of Eldraine|67|U|{3}{U}{U}|Legendary Creature - Human Knight|*|4|Syr Elenora, the Discerning's power is equal to the number of cards in your hand.$When Syr Elenora enters the battlefield, draw a card.$Spells your opponents cast that target Syr Elenora cost {2} more to cast.| Tome Raider|Throne of Eldraine|68|C|{2}{U}|Creature - Faerie|1|1|Flying$When Tome Raider enters the battlefield, draw a card.| Turn into a Pumpkin|Throne of Eldraine|69|U|{3}{U}|Instant|||Return target nonland permanent to its owner's hand. Draw a card.$Adamant — If at least three blue mana was spent to cast this spell, create a Food token.| Wishful Merfolk|Throne of Eldraine|73|C|{1}{U}|Creature - Merfolk|3|2|Defender${1}{U}: Wishful Merfolk loses defender and becomes a Human until end of turn.| @@ -36037,6 +36043,7 @@ Epic Downfall|Throne of Eldraine|85|U|{1}{B}|Sorcery|||Exile target creature wit Eye Collector|Throne of Eldraine|86|C|{B}|Creature - Faerie|1|1|Flying$Whenever Eye Collector deals combat damage to a player, each player puts the top card of their library into their graveyard.| Foulmire Knight|Throne of Eldraine|90|U|{B}|Creature - Zombie Knight|1|1|Deathtouch| Profane Insight|Throne of Eldraine|90|U|{2}{B}|Instant - Adventure|1|1|You draw a card and you lose 1 life.| +Lost Legion|Throne of Eldraine|94|C|{1}{B}{B}|Creature - Spirit Knight|2|3|When Lost Legion enters the battlefield, scry 2.| Murderous Rider|Throne of Eldraine|97|R|{1}{B}{B}|Creature - Zombie Knight|2|3|Lifelink$When Murderous Rider dies, put it on the bottom of its owner's library.| Swift End|Throne of Eldraine|97|R|{1}{B}{B}|Instant - Adventure|2|3|Destroy target creature or planeswalker. You lose 2 life.| Alter Fate|Throne of Eldraine|99|U|{1}{B}|Sorcery - Adventure|2|2|Return target creature card from your graveyard to your hand.| @@ -36061,7 +36068,11 @@ Battle Display|Throne of Eldraine|122|U|{R}|Sorcery - Adventure|2|1|Destroy targ Embereth Shieldbreaker|Throne of Eldraine|122|U|{1}{R}|Creature - Human Knight|2|1|| Fervent Champion|Throne of Eldraine|124|R|{R}|Creature - Human Knight|1|1|First strike, haste$Whenever Fervent Champion attacks, another target attacking Knight you control gets +1/+0 until end of turn.$Equip abilities you activate that target Fervent Champion cost {3} less to activate.| Joust|Throne of Eldraine|129|U|{1}{R}|Sorcery|||Choose target creature you control and target creature you don't control. The creature you control gets +2/+1 until end of turn if it's a Knight. Then those creatures fight each other.| +Haggle|Throne of Eldraine|131|C|{R}|Instant - Adventure|2|3|You may discard a card. If you do, draw a card.| +Merchant of the Vale|Throne of Eldraine|131|C|{2}{R}|Creature - Human Peasant|2|3|{2}{R}, Discard a card: Draw a card.| +Ogre Errant|Throne of Eldraine|132|C|{3}{R}|Creature - Ogre Knight|3|4|Whenever Ogre Errant attacks, another target attacking Knight gains menace until end of turn.| Opportunistic Dragon|Throne of Eldraine|133|R|{2}{R}{R}|Creature - Dragon|4|3|Flying$When Opportunistic Dragon enters the battlefield, choose target Human or artifact an opponent controls. For as long as Opportunistic Dragon remains on the battlefield, gain control of that permanent, it loses all abilities, and it can't attack or block.| +Raging Redcap|Throne of Eldraine|134|C|{2}{R}|Creature - Goblin Knight|1|2|Double strike| Robber of the Rich|Throne of Eldraine|138|M|{1}{R}|Creature - Human Archer Rogue|2|2|Reach, haste$Whenever Robber of the Rich attacks, if defending player has more cards in hand than you, exile the top card of their library. During any turn you attacked with a Rogue, you may cast that card and you may spend mana as though it were mana of any color to cast that spell.| Scorching Dragonfire|Throne of Eldraine|139|C|{1}{R}|Instant|||Scorching Dragonfire deals 3 damage to target creature or planeswalker. If that creature or planeswalker would die this turn, exile it instead.| Searing Barrage|Throne of Eldraine|140|C|{4}{R}|Instant|||Searing Barrage deals 5 damage to target creature.$Adamant — If at least three red mana was spent to cast this spell, Searing Barrage deals 3 damage to that creature's controller.| @@ -36074,6 +36085,7 @@ Beanstalk Giant|Throne of Eldraine|149|U|{6}{G}|Creature - Giant|*|*|Beanstalk G Fertile Footsteps|Throne of Eldraine|149|U|{2}{G}|Sorcery - Adventure|*|*|Search your library for a basic land card, put it onto the battlefield, then shuffle your library.| Curious Pair|Throne of Eldraine|150|C|{1}{G}|Creature - Human Peasant|1|3|| Treats to Share|Throne of Eldraine|150|C|{G}|Sorcery - Adventure|1|3|Create a Food token.| +Edgewall Innkeeper|Throne of Eldraine|151|U|{G}|Creature - Human Peasant|1|1|Whenever you cast a creature spell that has an Adventure, draw a card.| Feasting Troll King|Throne of Eldraine|152|R|{2}{G}{G}{G}{G}|Creature - Troll Noble|7|6|Vigilance, trample$When Feasting Troll King enters the battlefield, if you cast it from your hand, create three Food tokens.$Sacrifice three Foods: Return Feasting Troll King from your graveyard to the battlefield. Activate this ability only during your turn.| Fell the Pheasant|Throne of Eldraine|153|C|{1}{G}|Instant|||Fell the Pheasant deals 5 damage to target creature with flying. Create a Food token.| Flaxen Intruder|Throne of Eldraine|155|U|{G}|Creature - Human Berserker|1|2|Whenever Flaxen Intruder deals combat damage to a player, you may sacrifice it. When you do, destroy target artifact or enchantment.| @@ -36107,6 +36119,7 @@ The Royal Scions|Throne of Eldraine|199|M|{1}{U}{R}|Legendary Planeswalker - Wil Savvy Hunter|Throne of Eldraine|200|U|{1}{B}{G}|Creature - Human Warrior|3|3|Whenever Savvy Hunter attacks or blocks, create a Food token.$Sacrifice two Foods: Draw a card.| Shinechaser|Throne of Eldraine|201|U|{1}{W}{U}|Creature - Faerie|1|1|Flying, vigilance$Shinechaser gets +1/+1 as long as you control an artifact.$Shinechaser gets +1/+1 as long as you control an enchantment.| Steelclaw Lance|Throne of Eldraine|202|U|{B}{R}|Artifact - Equipment|||Equipped creature gets +2/+2.$Equip Knight {1}$Equip {3}| +Wandermare|Throne of Eldraine|204|U|{1}{G}{W}|Creature - Horse|3|3|Whenever you cast a creature spell that has an Adventure, put a +1/+1 counter on Wandermare.| Wintermoor Commander|Throne of Eldraine|205|U|{W}{B}|Creature - Human Knight|2|*|Deathtouch$Wintermoor Commander's toughness is equal to the number of Knights you control.$Whenever Wintermoor Commander attacks, another target Knight you control gains indestructible until end of turn.| Arcanist's Owl|Throne of Eldraine|206|U|{W/U}{W/U}{W/U}{W/U}|Artifact Creature - Bird|3|3|Flying$When Arcanist's Owl enters the battlefield, look at the top four cards of your library. You may reveal an artifact or enchantment card from among them and put it into your hand. Put the rest on the bottom of your library in a random order.| Covetous Urge|Throne of Eldraine|207|U|{U/B}{U/B}{U/B}{U/B}|Sorcery|||Target opponent reveals their hand. You choose a nonland card from that player's graveyard or hand and exile it. You may cast that card for as long as it remains exiled, and you may spend mana as though it were mana of any color to cast that spell.| @@ -36114,6 +36127,7 @@ Elite Headhunter|Throne of Eldraine|209|U|{B/R}{B/R}{B/R}{B/R}|Creature - Human Fireborn Knight|Throne of Eldraine|210|U|{R/W}{R/W}{R/W}{R/W}|Creature - Human Knight|2|3|Double strike${R/W}{R/W}{R/W}{R/W}: Fireborn Knight gets +1/+1 until end of turn.| Bring Back|Throne of Eldraine|212|U|{G/W}{G/W}{G/W}{G/W}|Sorcery - Adventure|2|2|Create two 1/1 white Human creature tokens.| Oakhame Ranger|Throne of Eldraine|212|U|{G/W}{G/W}{G/W}{G/W}|Creature - Elf Knight|2|2|{T}: Creatures you control get +1/+1 until end of turn.| +Thunderous Snapper|Throne of Eldraine|215|U|{G/U}{G/U}{G/U}{G/U}|Creature - Turtle Hydra|4|4|Whenever you cast a spell with converted mana cost 5 or greater, draw a card.| Enchanted Carriage|Throne of Eldraine|218|U|{5}|Artifact - Vehicle|4|4|When Enchanted Carriage enters the battlefield, create two 1/1 white Mouse creature tokens.$Crew 2| Gingerbrute|Throne of Eldraine|219|C|{1}|Artifact Creature - Food Golem|1|1|Haste${1}: Gingerbrute can't be blocked this turn except by creatures with haste.${2}, {T}, Sacrifice Gingerbrute: You gain 3 life.| Golden Egg|Throne of Eldraine|220|C|{2}|Artifact - Food|||When Golden Egg enters the battlefield, draw a card.${1}, {T}, Sacrifice Golden Egg: Add one mana of any color.${2}, {T}, Sacrifice Golden Egg: You gain 3 life.| From e2c8fa5ace4bf88e3b0369cf1493a54078a33c4d Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 12 Sep 2019 16:19:28 -0400 Subject: [PATCH 089/373] Implemented Raging Redcap --- Mage.Sets/src/mage/cards/r/RagingRedcap.java | 37 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 38 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/r/RagingRedcap.java diff --git a/Mage.Sets/src/mage/cards/r/RagingRedcap.java b/Mage.Sets/src/mage/cards/r/RagingRedcap.java new file mode 100644 index 0000000000..4681a9673a --- /dev/null +++ b/Mage.Sets/src/mage/cards/r/RagingRedcap.java @@ -0,0 +1,37 @@ +package mage.cards.r; + +import mage.MageInt; +import mage.abilities.keyword.DoubleStrikeAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class RagingRedcap extends CardImpl { + + public RagingRedcap(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{2}{R}"); + + this.subtype.add(SubType.GOBLIN); + this.subtype.add(SubType.KNIGHT); + this.power = new MageInt(1); + this.toughness = new MageInt(2); + + // Double strike + this.addAbility(DoubleStrikeAbility.getInstance()); + } + + private RagingRedcap(final RagingRedcap card) { + super(card); + } + + @Override + public RagingRedcap copy() { + return new RagingRedcap(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 7b5619457c..8b3e5e5b72 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -111,6 +111,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Outmuscle", 170, Rarity.COMMON, mage.cards.o.Outmuscle.class)); cards.add(new SetCardInfo("Piper of the Swarm", 100, Rarity.RARE, mage.cards.p.PiperOfTheSwarm.class)); cards.add(new SetCardInfo("Questing Beast", 171, Rarity.MYTHIC, mage.cards.q.QuestingBeast.class)); + cards.add(new SetCardInfo("Raging Redcap", 134, Rarity.COMMON, mage.cards.r.RagingRedcap.class)); cards.add(new SetCardInfo("Rankle, Master of Pranks", 101, Rarity.MYTHIC, mage.cards.r.RankleMasterOfPranks.class)); cards.add(new SetCardInfo("Reave Soul", 103, Rarity.COMMON, mage.cards.r.ReaveSoul.class)); cards.add(new SetCardInfo("Return to Nature", 173, Rarity.COMMON, mage.cards.r.ReturnToNature.class)); From 1dd023b78cce997d259a0d0662d4ac79ec9f2cf9 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 12 Sep 2019 16:19:52 -0400 Subject: [PATCH 090/373] Implemented Knight of the Keep --- .../src/mage/cards/k/KnightOfTheKeep.java | 33 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 34 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/k/KnightOfTheKeep.java diff --git a/Mage.Sets/src/mage/cards/k/KnightOfTheKeep.java b/Mage.Sets/src/mage/cards/k/KnightOfTheKeep.java new file mode 100644 index 0000000000..4a44649a46 --- /dev/null +++ b/Mage.Sets/src/mage/cards/k/KnightOfTheKeep.java @@ -0,0 +1,33 @@ +package mage.cards.k; + +import mage.MageInt; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class KnightOfTheKeep extends CardImpl { + + public KnightOfTheKeep(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{2}{W}"); + + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.KNIGHT); + this.power = new MageInt(3); + this.toughness = new MageInt(2); + } + + private KnightOfTheKeep(final KnightOfTheKeep card) { + super(card); + } + + @Override + public KnightOfTheKeep copy() { + return new KnightOfTheKeep(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 8b3e5e5b72..d910e4efce 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -90,6 +90,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Jousting Dummy", 224, Rarity.COMMON, mage.cards.j.JoustingDummy.class)); cards.add(new SetCardInfo("Keeper of Fables", 163, Rarity.UNCOMMON, mage.cards.k.KeeperOfFables.class)); cards.add(new SetCardInfo("Kenrith, the Returned King", 303, Rarity.MYTHIC, mage.cards.k.KenrithTheReturnedKing.class)); + cards.add(new SetCardInfo("Knight of the Keep", 19, Rarity.COMMON, mage.cards.k.KnightOfTheKeep.class)); cards.add(new SetCardInfo("Knights' Charge", 328, Rarity.RARE, mage.cards.k.KnightsCharge.class)); cards.add(new SetCardInfo("Korvold, Fae-Cursed King", 329, Rarity.MYTHIC, mage.cards.k.KorvoldFaeCursedKing.class)); cards.add(new SetCardInfo("Lochmere Serpent", 195, Rarity.RARE, mage.cards.l.LochmereSerpent.class)); From 0b70a0fffdef24717400b782098e62552f120464 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 12 Sep 2019 16:21:55 -0400 Subject: [PATCH 091/373] Implemented Lost Legion --- Mage.Sets/src/mage/cards/l/LostLegion.java | 38 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 39 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/l/LostLegion.java diff --git a/Mage.Sets/src/mage/cards/l/LostLegion.java b/Mage.Sets/src/mage/cards/l/LostLegion.java new file mode 100644 index 0000000000..9c6ec9dacc --- /dev/null +++ b/Mage.Sets/src/mage/cards/l/LostLegion.java @@ -0,0 +1,38 @@ +package mage.cards.l; + +import mage.MageInt; +import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.effects.keyword.ScryEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class LostLegion extends CardImpl { + + public LostLegion(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{1}{B}{B}"); + + this.subtype.add(SubType.SPIRIT); + this.subtype.add(SubType.KNIGHT); + this.power = new MageInt(2); + this.toughness = new MageInt(3); + + // When Lost Legion enters the battlefield, scry 2. + this.addAbility(new EntersBattlefieldTriggeredAbility(new ScryEffect(2))); + } + + private LostLegion(final LostLegion card) { + super(card); + } + + @Override + public LostLegion copy() { + return new LostLegion(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index d910e4efce..ae10c3c070 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -94,6 +94,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Knights' Charge", 328, Rarity.RARE, mage.cards.k.KnightsCharge.class)); cards.add(new SetCardInfo("Korvold, Fae-Cursed King", 329, Rarity.MYTHIC, mage.cards.k.KorvoldFaeCursedKing.class)); cards.add(new SetCardInfo("Lochmere Serpent", 195, Rarity.RARE, mage.cards.l.LochmereSerpent.class)); + cards.add(new SetCardInfo("Lost Legion", 94, Rarity.COMMON, mage.cards.l.LostLegion.class)); cards.add(new SetCardInfo("Lovestruck Beast", 165, Rarity.RARE, mage.cards.l.LovestruckBeast.class)); cards.add(new SetCardInfo("Mace of the Valiant", 314, Rarity.RARE, mage.cards.m.MaceOfTheValiant.class)); cards.add(new SetCardInfo("Maraleaf Pixie", 196, Rarity.UNCOMMON, mage.cards.m.MaraleafPixie.class)); From 23585b25bb3757245877618e5ded896961f1f66a Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 12 Sep 2019 16:25:12 -0400 Subject: [PATCH 092/373] Implemented Ardenvale Tactician --- .../src/mage/cards/a/ArdenvaleTactician.java | 44 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 45 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/a/ArdenvaleTactician.java diff --git a/Mage.Sets/src/mage/cards/a/ArdenvaleTactician.java b/Mage.Sets/src/mage/cards/a/ArdenvaleTactician.java new file mode 100644 index 0000000000..cfafc8aac4 --- /dev/null +++ b/Mage.Sets/src/mage/cards/a/ArdenvaleTactician.java @@ -0,0 +1,44 @@ +package mage.cards.a; + +import mage.MageInt; +import mage.abilities.effects.common.TapTargetEffect; +import mage.abilities.keyword.FlyingAbility; +import mage.cards.AdventureCard; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.target.common.TargetCreaturePermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class ArdenvaleTactician extends AdventureCard { + + public ArdenvaleTactician(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, new CardType[]{CardType.INSTANT}, "{1}{W}{W}", "Dizzying Swoop", "{1}{W}"); + + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.KNIGHT); + this.power = new MageInt(2); + this.toughness = new MageInt(3); + + // Flying + this.addAbility(FlyingAbility.getInstance()); + + // Dizzying Swoop + // Tap up to two target creatures. + this.getAdventureSpellAbility().addEffect(new TapTargetEffect()); + this.getAdventureSpellAbility().addTarget(new TargetCreaturePermanent(0, 2)); + } + + private ArdenvaleTactician(final ArdenvaleTactician card) { + super(card); + } + + @Override + public ArdenvaleTactician copy() { + return new ArdenvaleTactician(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index ae10c3c070..9dc75aa944 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -33,6 +33,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Animating Faerie", 38, Rarity.UNCOMMON, mage.cards.a.AnimatingFaerie.class)); cards.add(new SetCardInfo("Arcane Signet", 331, Rarity.COMMON, mage.cards.a.ArcaneSignet.class)); cards.add(new SetCardInfo("Arcanist's Owl", 206, Rarity.UNCOMMON, mage.cards.a.ArcanistsOwl.class)); + cards.add(new SetCardInfo("Ardenvale Tactician", 5, Rarity.COMMON, mage.cards.a.ArdenvaleTactician.class)); cards.add(new SetCardInfo("Bake into a Pie", 76, Rarity.COMMON, mage.cards.b.BakeIntoAPie.class)); cards.add(new SetCardInfo("Banish into Fable", 325, Rarity.RARE, mage.cards.b.BanishIntoFable.class)); cards.add(new SetCardInfo("Beanstalk Giant", 149, Rarity.UNCOMMON, mage.cards.b.BeanstalkGiant.class)); From 77f1fd0df204930b7a3375842a6399de8611e11a Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 12 Sep 2019 16:30:57 -0400 Subject: [PATCH 093/373] Implemented Thunderous Snapper --- .../src/mage/cards/t/ThunderousSnapper.java | 49 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 50 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/t/ThunderousSnapper.java diff --git a/Mage.Sets/src/mage/cards/t/ThunderousSnapper.java b/Mage.Sets/src/mage/cards/t/ThunderousSnapper.java new file mode 100644 index 0000000000..2a54b4a295 --- /dev/null +++ b/Mage.Sets/src/mage/cards/t/ThunderousSnapper.java @@ -0,0 +1,49 @@ +package mage.cards.t; + +import mage.MageInt; +import mage.abilities.common.SpellCastControllerTriggeredAbility; +import mage.abilities.effects.common.DrawCardSourceControllerEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.ComparisonType; +import mage.constants.SubType; +import mage.filter.FilterSpell; +import mage.filter.predicate.mageobject.ConvertedManaCostPredicate; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class ThunderousSnapper extends CardImpl { + + private static final FilterSpell filter = new FilterSpell("a spell with converted mana cost 5 or greater"); + + static { + filter.add(new ConvertedManaCostPredicate(ComparisonType.MORE_THAN, 4)); + } + + public ThunderousSnapper(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{G/U}{G/U}{G/U}{G/U}"); + + this.subtype.add(SubType.TURTLE); + this.subtype.add(SubType.HYDRA); + this.power = new MageInt(4); + this.toughness = new MageInt(4); + + // Whenever you cast a spell with converted mana cost 5 or greater, draw a card. + this.addAbility(new SpellCastControllerTriggeredAbility( + new DrawCardSourceControllerEffect(1), filter, false + )); + } + + private ThunderousSnapper(final ThunderousSnapper card) { + super(card); + } + + @Override + public ThunderousSnapper copy() { + return new ThunderousSnapper(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 9dc75aa944..9a14e94e4b 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -150,6 +150,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("The Royal Scions", 199, Rarity.MYTHIC, mage.cards.t.TheRoyalScions.class)); cards.add(new SetCardInfo("Thorn Mammoth", 323, Rarity.RARE, mage.cards.t.ThornMammoth.class)); cards.add(new SetCardInfo("Thornwood Falls", 313, Rarity.COMMON, mage.cards.t.ThornwoodFalls.class)); + cards.add(new SetCardInfo("Thunderous Snapper", 215, Rarity.UNCOMMON, mage.cards.t.ThunderousSnapper.class)); cards.add(new SetCardInfo("Tome Raider", 68, Rarity.COMMON, mage.cards.t.TomeRaider.class)); cards.add(new SetCardInfo("Tome of Legends", 332, Rarity.RARE, mage.cards.t.TomeOfLegends.class)); cards.add(new SetCardInfo("Tournament Grounds", 248, Rarity.UNCOMMON, mage.cards.t.TournamentGrounds.class)); From 93c0156c90e920786c56455304fa0edf818ab3aa Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 12 Sep 2019 16:43:13 -0400 Subject: [PATCH 094/373] Implemented Elite Headhunter --- .../src/mage/cards/e/EliteHeadhunter.java | 77 +++++++++++++++++++ .../src/mage/cards/k/KumenasSpeaker.java | 36 +++++---- Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 3 files changed, 101 insertions(+), 13 deletions(-) create mode 100644 Mage.Sets/src/mage/cards/e/EliteHeadhunter.java diff --git a/Mage.Sets/src/mage/cards/e/EliteHeadhunter.java b/Mage.Sets/src/mage/cards/e/EliteHeadhunter.java new file mode 100644 index 0000000000..b5e86c7537 --- /dev/null +++ b/Mage.Sets/src/mage/cards/e/EliteHeadhunter.java @@ -0,0 +1,77 @@ +package mage.cards.e; + +import mage.MageInt; +import mage.MageObject; +import mage.abilities.Ability; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.costs.common.SacrificeTargetCost; +import mage.abilities.costs.mana.ManaCostsImpl; +import mage.abilities.effects.common.DamageTargetEffect; +import mage.abilities.keyword.MenaceAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.filter.common.FilterControlledPermanent; +import mage.filter.predicate.ObjectSourcePlayer; +import mage.filter.predicate.ObjectSourcePlayerPredicate; +import mage.game.Game; +import mage.target.common.TargetControlledPermanent; +import mage.target.common.TargetCreatureOrPlaneswalker; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class EliteHeadhunter extends CardImpl { + + private static final FilterControlledPermanent filter + = new FilterControlledPermanent("another creature or an artifact"); + + static { + filter.add(EliteHeadhunterPredicate.instance); + } + + public EliteHeadhunter(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{B/R}{B/R}{B/R}{B/R}"); + + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.KNIGHT); + this.power = new MageInt(2); + this.toughness = new MageInt(3); + + // Menace + this.addAbility(new MenaceAbility()); + + // {B/R}{B/R}{B/R}, Sacrifice another creature or an artifact: Elite Headhunter deals 2 damage to target creature or planeswalker. + Ability ability = new SimpleActivatedAbility( + new DamageTargetEffect(2), new ManaCostsImpl("{B/R}{B/R}{B/R}") + ); + ability.addCost(new SacrificeTargetCost(new TargetControlledPermanent(filter))); + ability.addTarget(new TargetCreatureOrPlaneswalker()); + this.addAbility(ability); + } + + private EliteHeadhunter(final EliteHeadhunter card) { + super(card); + } + + @Override + public EliteHeadhunter copy() { + return new EliteHeadhunter(this); + } +} + +enum EliteHeadhunterPredicate implements ObjectSourcePlayerPredicate> { + instance; + + @Override + public boolean apply(ObjectSourcePlayer input, Game game) { + MageObject obj = input.getObject(); + if (obj.getId().equals(input.getSourceId())) { + return obj.isArtifact(); + } + return obj.isCreature() || obj.isArtifact(); + } +} diff --git a/Mage.Sets/src/mage/cards/k/KumenasSpeaker.java b/Mage.Sets/src/mage/cards/k/KumenasSpeaker.java index 58cc2dd777..9626941ed4 100644 --- a/Mage.Sets/src/mage/cards/k/KumenasSpeaker.java +++ b/Mage.Sets/src/mage/cards/k/KumenasSpeaker.java @@ -1,22 +1,21 @@ - package mage.cards.k; -import java.util.UUID; import mage.MageInt; +import mage.MageObject; import mage.abilities.common.SimpleStaticAbility; import mage.abilities.effects.common.continuous.BoostSourceWhileControlsEffect; import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.CardType; import mage.constants.SubType; -import mage.constants.Zone; import mage.filter.FilterPermanent; -import mage.filter.predicate.Predicates; -import mage.filter.predicate.mageobject.SubtypePredicate; -import mage.filter.predicate.permanent.AnotherPredicate; +import mage.filter.predicate.ObjectSourcePlayer; +import mage.filter.predicate.ObjectSourcePlayerPredicate; +import mage.game.Game; + +import java.util.UUID; /** - * * @author TheElk801 */ public final class KumenasSpeaker extends CardImpl { @@ -24,10 +23,7 @@ public final class KumenasSpeaker extends CardImpl { private static final FilterPermanent filter = new FilterPermanent("another Merfolk or an Island"); static { - filter.add(AnotherPredicate.instance); - filter.add(Predicates.or( - new SubtypePredicate(SubType.ISLAND), - new SubtypePredicate(SubType.MERFOLK))); + filter.add(KumenasSpeakerPredicate.instance); } public KumenasSpeaker(UUID ownerId, CardSetInfo setInfo) { @@ -39,10 +35,10 @@ public final class KumenasSpeaker extends CardImpl { this.toughness = new MageInt(1); // Kumena's Omenspeaker gets +1/+1 as long as you control another Merfolk or Island. - this.addAbility(new SimpleStaticAbility(Zone.BATTLEFIELD, new BoostSourceWhileControlsEffect(filter, 1, 1))); + this.addAbility(new SimpleStaticAbility(new BoostSourceWhileControlsEffect(filter, 1, 1))); } - public KumenasSpeaker(final KumenasSpeaker card) { + private KumenasSpeaker(final KumenasSpeaker card) { super(card); } @@ -51,3 +47,17 @@ public final class KumenasSpeaker extends CardImpl { return new KumenasSpeaker(this); } } + +enum KumenasSpeakerPredicate implements ObjectSourcePlayerPredicate> { + instance; + + @Override + public boolean apply(ObjectSourcePlayer input, Game game) { + MageObject obj = input.getObject(); + if (obj.getId().equals(input.getSourceId())) { + return obj.hasSubtype(SubType.ISLAND, game); + } + return obj.hasSubtype(SubType.ISLAND, game) + || obj.hasSubtype(SubType.MERFOLK, game); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 9a14e94e4b..795839494c 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -55,6 +55,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Crystal Slipper", 119, Rarity.COMMON, mage.cards.c.CrystalSlipper.class)); cards.add(new SetCardInfo("Curious Pair", 150, Rarity.COMMON, mage.cards.c.CuriousPair.class)); cards.add(new SetCardInfo("Doom Foretold", 187, Rarity.RARE, mage.cards.d.DoomForetold.class)); + cards.add(new SetCardInfo("Elite Headhunter", 209, Rarity.UNCOMMON, mage.cards.e.EliteHeadhunter.class)); cards.add(new SetCardInfo("Embercleave", 120, Rarity.MYTHIC, mage.cards.e.Embercleave.class)); cards.add(new SetCardInfo("Embereth Paladin", 121, Rarity.COMMON, mage.cards.e.EmberethPaladin.class)); cards.add(new SetCardInfo("Embereth Shieldbreaker", 122, Rarity.UNCOMMON, mage.cards.e.EmberethShieldbreaker.class)); From 57ff0a814d3b8bd479c38ef620dd2c35792295be Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 12 Sep 2019 16:59:38 -0400 Subject: [PATCH 095/373] Implemented Stolen by the Fae --- .../src/mage/cards/s/StolenByTheFae.java | 57 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 58 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/s/StolenByTheFae.java diff --git a/Mage.Sets/src/mage/cards/s/StolenByTheFae.java b/Mage.Sets/src/mage/cards/s/StolenByTheFae.java new file mode 100644 index 0000000000..08fd09a589 --- /dev/null +++ b/Mage.Sets/src/mage/cards/s/StolenByTheFae.java @@ -0,0 +1,57 @@ +package mage.cards.s; + +import mage.abilities.Ability; +import mage.abilities.dynamicvalue.common.ManacostVariableValue; +import mage.abilities.effects.common.CreateTokenEffect; +import mage.abilities.effects.common.ReturnToHandTargetEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.ComparisonType; +import mage.filter.common.FilterCreaturePermanent; +import mage.filter.predicate.mageobject.ConvertedManaCostPredicate; +import mage.game.Game; +import mage.game.permanent.token.FaerieToken; +import mage.target.common.TargetCreaturePermanent; +import mage.target.targetadjustment.TargetAdjuster; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class StolenByTheFae extends CardImpl { + + public StolenByTheFae(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.SORCERY}, "{X}{U}{U}"); + + // Return target creature with converted mana cost X to its owner's hand. You create X 1/1 blue Faerie creature tokens with flying. + this.getSpellAbility().addEffect(new ReturnToHandTargetEffect() + .setText("Return target creature with converted mana cost X to its owner's hand.")); + this.getSpellAbility().addEffect(new CreateTokenEffect(new FaerieToken(), ManacostVariableValue.instance) + .setText("You create X 1/1 blue Faerie creature tokens with flying.")); + this.getSpellAbility().setTargetAdjuster(StolenByTheFaeAdjuster.instance); + } + + private StolenByTheFae(final StolenByTheFae card) { + super(card); + } + + @Override + public StolenByTheFae copy() { + return new StolenByTheFae(this); + } +} + +enum StolenByTheFaeAdjuster implements TargetAdjuster { + instance; + + @Override + public void adjustTargets(Ability ability, Game game) { + ability.getTargets().clear(); + int xValue = ability.getManaCostsToPay().getX(); + FilterCreaturePermanent filter = new FilterCreaturePermanent("creature with converted mana cost " + xValue); + filter.add(new ConvertedManaCostPredicate(ComparisonType.EQUAL_TO, xValue)); + ability.addTarget(new TargetCreaturePermanent(filter)); + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 795839494c..6895787be9 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -142,6 +142,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Spinning Wheel", 234, Rarity.UNCOMMON, mage.cards.s.SpinningWheel.class)); cards.add(new SetCardInfo("Steelbane Hydra", 322, Rarity.RARE, mage.cards.s.SteelbaneHydra.class)); cards.add(new SetCardInfo("Steelclaw Lance", 202, Rarity.UNCOMMON, mage.cards.s.SteelclawLance.class)); + cards.add(new SetCardInfo("Stolen by the Fae", 66, Rarity.RARE, mage.cards.s.StolenByTheFae.class)); cards.add(new SetCardInfo("Syr Carah, the Bold", 145, Rarity.UNCOMMON, mage.cards.s.SyrCarahTheBold.class)); cards.add(new SetCardInfo("Syr Elenora, the Discerning", 67, Rarity.UNCOMMON, mage.cards.s.SyrElenoraTheDiscerning.class)); cards.add(new SetCardInfo("Syr Gwyn, Hero of Ashvale", 330, Rarity.MYTHIC, mage.cards.s.SyrGwynHeroOfAshvale.class)); From b026ad4b9b6eee13d797ebc0e84ad61663054670 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 12 Sep 2019 17:05:48 -0400 Subject: [PATCH 096/373] Implemented Merchant of the Vale --- .../src/mage/cards/m/MerchantOfTheVale.java | 52 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 53 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/m/MerchantOfTheVale.java diff --git a/Mage.Sets/src/mage/cards/m/MerchantOfTheVale.java b/Mage.Sets/src/mage/cards/m/MerchantOfTheVale.java new file mode 100644 index 0000000000..f89f695ad7 --- /dev/null +++ b/Mage.Sets/src/mage/cards/m/MerchantOfTheVale.java @@ -0,0 +1,52 @@ +package mage.cards.m; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.costs.common.DiscardCardCost; +import mage.abilities.costs.mana.ManaCostsImpl; +import mage.abilities.effects.common.DoIfCostPaid; +import mage.abilities.effects.common.DrawCardSourceControllerEffect; +import mage.cards.AdventureCard; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class MerchantOfTheVale extends AdventureCard { + + public MerchantOfTheVale(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, new CardType[]{CardType.INSTANT}, "{2}{R}", "Haggle", "{R}"); + + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.PEASANT); + this.power = new MageInt(2); + this.toughness = new MageInt(3); + + // {2}{R}, Discard a card: Draw a card. + Ability ability = new SimpleActivatedAbility( + new DrawCardSourceControllerEffect(1), new ManaCostsImpl("{2}{R}") + ); + ability.addCost(new DiscardCardCost()); + this.addAbility(ability); + + // Haggle + // You may discard a card. If you do, draw a card. + this.getAdventureSpellAbility().addEffect(new DoIfCostPaid( + new DrawCardSourceControllerEffect(1), new DiscardCardCost() + )); + } + + private MerchantOfTheVale(final MerchantOfTheVale card) { + super(card); + } + + @Override + public MerchantOfTheVale copy() { + return new MerchantOfTheVale(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 6895787be9..e48d9a06f8 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -101,6 +101,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Mace of the Valiant", 314, Rarity.RARE, mage.cards.m.MaceOfTheValiant.class)); cards.add(new SetCardInfo("Maraleaf Pixie", 196, Rarity.UNCOMMON, mage.cards.m.MaraleafPixie.class)); cards.add(new SetCardInfo("Maraleaf Rider", 166, Rarity.COMMON, mage.cards.m.MaraleafRider.class)); + cards.add(new SetCardInfo("Merchant of the Vale", 131, Rarity.COMMON, mage.cards.m.MerchantOfTheVale.class)); cards.add(new SetCardInfo("Midnight Clock", 54, Rarity.RARE, mage.cards.m.MidnightClock.class)); cards.add(new SetCardInfo("Murderous Rider", 97, Rarity.RARE, mage.cards.m.MurderousRider.class)); cards.add(new SetCardInfo("Mystical Dispute", 58, Rarity.UNCOMMON, mage.cards.m.MysticalDispute.class)); From 4b8e9d0a0982edd2297815b43e3664648f97ba81 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 12 Sep 2019 17:10:02 -0400 Subject: [PATCH 097/373] Implemented Wandermare --- Mage.Sets/src/mage/cards/w/Wandermare.java | 50 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + .../mageobject/AdventurePredicate.java | 23 +++++++++ 3 files changed, 74 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/w/Wandermare.java create mode 100644 Mage/src/main/java/mage/filter/predicate/mageobject/AdventurePredicate.java diff --git a/Mage.Sets/src/mage/cards/w/Wandermare.java b/Mage.Sets/src/mage/cards/w/Wandermare.java new file mode 100644 index 0000000000..1b6e77b317 --- /dev/null +++ b/Mage.Sets/src/mage/cards/w/Wandermare.java @@ -0,0 +1,50 @@ +package mage.cards.w; + +import mage.MageInt; +import mage.abilities.common.SpellCastControllerTriggeredAbility; +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.counters.CounterType; +import mage.filter.FilterSpell; +import mage.filter.common.FilterCreatureSpell; +import mage.filter.predicate.mageobject.AdventurePredicate; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class Wandermare extends CardImpl { + + private static final FilterSpell filter + = new FilterCreatureSpell("a creature spell that has an Adventure"); + + static { + filter.add(AdventurePredicate.instance); + } + + public Wandermare(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{1}{G}{W}"); + + this.subtype.add(SubType.HORSE); + this.power = new MageInt(3); + this.toughness = new MageInt(3); + + // Whenever you cast a creature spell that has an Adventure, put a +1/+1 counter on Wandermare. + this.addAbility(new SpellCastControllerTriggeredAbility( + new AddCountersSourceEffect(CounterType.P1P1.createInstance()), filter, false + )); + } + + private Wandermare(final Wandermare card) { + super(card); + } + + @Override + public Wandermare copy() { + return new Wandermare(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index e48d9a06f8..e97d420812 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -160,6 +160,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("True Love's Kiss", 34, Rarity.COMMON, mage.cards.t.TrueLovesKiss.class)); cards.add(new SetCardInfo("Turn into a Pumpkin", 69, Rarity.UNCOMMON, mage.cards.t.TurnIntoAPumpkin.class)); cards.add(new SetCardInfo("Venerable Knight", 35, Rarity.UNCOMMON, mage.cards.v.VenerableKnight.class)); + cards.add(new SetCardInfo("Wandermare", 204, Rarity.UNCOMMON, mage.cards.w.Wandermare.class)); cards.add(new SetCardInfo("Weaselback Redcap", 148, Rarity.COMMON, mage.cards.w.WeaselbackRedcap.class)); cards.add(new SetCardInfo("Wicked Guardian", 109, Rarity.COMMON, mage.cards.w.WickedGuardian.class)); cards.add(new SetCardInfo("Wicked Wolf", 181, Rarity.RARE, mage.cards.w.WickedWolf.class)); diff --git a/Mage/src/main/java/mage/filter/predicate/mageobject/AdventurePredicate.java b/Mage/src/main/java/mage/filter/predicate/mageobject/AdventurePredicate.java new file mode 100644 index 0000000000..90927d92ca --- /dev/null +++ b/Mage/src/main/java/mage/filter/predicate/mageobject/AdventurePredicate.java @@ -0,0 +1,23 @@ +package mage.filter.predicate.mageobject; + +import mage.MageObject; +import mage.filter.predicate.Predicate; +import mage.game.Game; + +/** + * @author TheElk801 + * TODO: make this actually work + */ +public enum AdventurePredicate implements Predicate { + instance; + + @Override + public boolean apply(MageObject input, Game game) { + return false; + } + + @Override + public String toString() { + return "Adventure"; + } +} From ca83f1a00ee184626f8091526fde286543bbf04d Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 12 Sep 2019 17:12:13 -0400 Subject: [PATCH 098/373] Implemented Edgewall Innkeeper --- .../src/mage/cards/e/EdgewallInnkeeper.java | 50 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 51 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/e/EdgewallInnkeeper.java diff --git a/Mage.Sets/src/mage/cards/e/EdgewallInnkeeper.java b/Mage.Sets/src/mage/cards/e/EdgewallInnkeeper.java new file mode 100644 index 0000000000..95ef140f1f --- /dev/null +++ b/Mage.Sets/src/mage/cards/e/EdgewallInnkeeper.java @@ -0,0 +1,50 @@ +package mage.cards.e; + +import mage.MageInt; +import mage.abilities.common.SpellCastControllerTriggeredAbility; +import mage.abilities.effects.common.DrawCardSourceControllerEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.filter.FilterSpell; +import mage.filter.common.FilterCreatureSpell; +import mage.filter.predicate.mageobject.AdventurePredicate; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class EdgewallInnkeeper extends CardImpl { + + private static final FilterSpell filter + = new FilterCreatureSpell("a creature spell that has an Adventure"); + + static { + filter.add(AdventurePredicate.instance); + } + + public EdgewallInnkeeper(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{G}"); + + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.PEASANT); + this.power = new MageInt(1); + this.toughness = new MageInt(1); + + // Whenever you cast a creature spell that has an Adventure, draw a card. + this.addAbility(new SpellCastControllerTriggeredAbility( + new DrawCardSourceControllerEffect(1), filter, false + )); + } + + private EdgewallInnkeeper(final EdgewallInnkeeper card) { + super(card); + } + + @Override + public EdgewallInnkeeper copy() { + return new EdgewallInnkeeper(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index e97d420812..80cf873746 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -55,6 +55,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Crystal Slipper", 119, Rarity.COMMON, mage.cards.c.CrystalSlipper.class)); cards.add(new SetCardInfo("Curious Pair", 150, Rarity.COMMON, mage.cards.c.CuriousPair.class)); cards.add(new SetCardInfo("Doom Foretold", 187, Rarity.RARE, mage.cards.d.DoomForetold.class)); + cards.add(new SetCardInfo("Edgewall Innkeeper", 151, Rarity.UNCOMMON, mage.cards.e.EdgewallInnkeeper.class)); cards.add(new SetCardInfo("Elite Headhunter", 209, Rarity.UNCOMMON, mage.cards.e.EliteHeadhunter.class)); cards.add(new SetCardInfo("Embercleave", 120, Rarity.MYTHIC, mage.cards.e.Embercleave.class)); cards.add(new SetCardInfo("Embereth Paladin", 121, Rarity.COMMON, mage.cards.e.EmberethPaladin.class)); From 9ace4df8543207255519fae7c741dc091712b5d4 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 12 Sep 2019 17:17:18 -0400 Subject: [PATCH 099/373] Implemented Glass Casket --- Mage.Sets/src/mage/cards/g/GlassCasket.java | 53 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 54 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/g/GlassCasket.java diff --git a/Mage.Sets/src/mage/cards/g/GlassCasket.java b/Mage.Sets/src/mage/cards/g/GlassCasket.java new file mode 100644 index 0000000000..a2267dcbb0 --- /dev/null +++ b/Mage.Sets/src/mage/cards/g/GlassCasket.java @@ -0,0 +1,53 @@ +package mage.cards.g; + +import mage.abilities.Ability; +import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.common.delayed.OnLeaveReturnExiledToBattlefieldAbility; +import mage.abilities.effects.common.CreateDelayedTriggeredAbilityEffect; +import mage.abilities.effects.common.ExileUntilSourceLeavesEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.ComparisonType; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterOpponentsCreaturePermanent; +import mage.filter.predicate.mageobject.ConvertedManaCostPredicate; +import mage.target.TargetPermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class GlassCasket extends CardImpl { + + private static final FilterPermanent filter + = new FilterOpponentsCreaturePermanent("creature an opponent controls with converted mana cost 3 or less"); + + static { + filter.add(new ConvertedManaCostPredicate(ComparisonType.FEWER_THAN, 4)); + } + + public GlassCasket(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT}, "{1}{W}"); + + // When Glass Casket enters the battlefield, exile target creature an opponent controls with converted mana cost 3 or less until Glass Casket leaves the battlefield. + Ability ability = new EntersBattlefieldTriggeredAbility( + new ExileUntilSourceLeavesEffect("") + .setText("exile target creature an opponent controls with converted mana cost 3 " + + "or less until {this} leaves the battlefield") + ); + ability.addTarget(new TargetPermanent(filter)); + ability.addEffect(new CreateDelayedTriggeredAbilityEffect(new OnLeaveReturnExiledToBattlefieldAbility())); + this.addAbility(ability); + } + + private GlassCasket(final GlassCasket card) { + super(card); + } + + @Override + public GlassCasket copy() { + return new GlassCasket(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 80cf873746..f2c4a481c3 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -80,6 +80,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Giant Killer", 14, Rarity.RARE, mage.cards.g.GiantKiller.class)); cards.add(new SetCardInfo("Gilded Goose", 160, Rarity.RARE, mage.cards.g.GildedGoose.class)); cards.add(new SetCardInfo("Gingerbrute", 219, Rarity.COMMON, mage.cards.g.Gingerbrute.class)); + cards.add(new SetCardInfo("Glass Casket", 15, Rarity.UNCOMMON, mage.cards.g.GlassCasket.class)); cards.add(new SetCardInfo("Gluttonous Troll", 327, Rarity.RARE, mage.cards.g.GluttonousTroll.class)); cards.add(new SetCardInfo("Golden Egg", 220, Rarity.COMMON, mage.cards.g.GoldenEgg.class)); cards.add(new SetCardInfo("Harmonious Archon", 17, Rarity.MYTHIC, mage.cards.h.HarmoniousArchon.class)); From 2a514c73b23b645292625abbb206b7980675cd88 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 12 Sep 2019 17:22:00 -0400 Subject: [PATCH 100/373] Implemented Ogre Errant --- Mage.Sets/src/mage/cards/o/OgreErrant.java | 57 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 58 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/o/OgreErrant.java diff --git a/Mage.Sets/src/mage/cards/o/OgreErrant.java b/Mage.Sets/src/mage/cards/o/OgreErrant.java new file mode 100644 index 0000000000..683342b6b4 --- /dev/null +++ b/Mage.Sets/src/mage/cards/o/OgreErrant.java @@ -0,0 +1,57 @@ +package mage.cards.o; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.AttacksTriggeredAbility; +import mage.abilities.effects.common.continuous.GainAbilityTargetEffect; +import mage.abilities.keyword.MenaceAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; +import mage.filter.FilterPermanent; +import mage.filter.predicate.permanent.AnotherPredicate; +import mage.filter.predicate.permanent.AttackingPredicate; +import mage.target.TargetPermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class OgreErrant extends CardImpl { + + private static final FilterPermanent filter + = new FilterPermanent(SubType.KNIGHT, "another attacking Knight"); + + static { + filter.add(AttackingPredicate.instance); + filter.add(AnotherPredicate.instance); + } + + public OgreErrant(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{3}{R}"); + + this.subtype.add(SubType.OGRE); + this.subtype.add(SubType.KNIGHT); + this.power = new MageInt(3); + this.toughness = new MageInt(4); + + // Whenever Ogre Errant attacks, another target attacking Knight gains menace until end of turn. + Ability ability = new AttacksTriggeredAbility(new GainAbilityTargetEffect( + new MenaceAbility(), Duration.EndOfTurn + ).setText("another target attacking Knight gains menace until end of turn"), false); + ability.addTarget(new TargetPermanent(filter)); + this.addAbility(ability); + } + + private OgreErrant(final OgreErrant card) { + super(card); + } + + @Override + public OgreErrant copy() { + return new OgreErrant(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index f2c4a481c3..0b9e86b177 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -108,6 +108,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Murderous Rider", 97, Rarity.RARE, mage.cards.m.MurderousRider.class)); cards.add(new SetCardInfo("Mystical Dispute", 58, Rarity.UNCOMMON, mage.cards.m.MysticalDispute.class)); cards.add(new SetCardInfo("Oakhame Ranger", 212, Rarity.UNCOMMON, mage.cards.o.OakhameRanger.class)); + cards.add(new SetCardInfo("Ogre Errant", 132, Rarity.COMMON, mage.cards.o.OgreErrant.class)); cards.add(new SetCardInfo("Oko's Accomplices", 310, Rarity.COMMON, mage.cards.o.OkosAccomplices.class)); cards.add(new SetCardInfo("Oko's Hospitality", 312, Rarity.RARE, mage.cards.o.OkosHospitality.class)); cards.add(new SetCardInfo("Oko, Thief of Crowns", 197, Rarity.MYTHIC, mage.cards.o.OkoThiefOfCrowns.class)); From 99c884eca1b78b8ab394381ca05eb5b427e0213b Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 12 Sep 2019 17:35:55 -0400 Subject: [PATCH 101/373] Implemented Trail of Crumbs --- Mage.Sets/src/mage/cards/t/TrailOfCrumbs.java | 86 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 87 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/t/TrailOfCrumbs.java diff --git a/Mage.Sets/src/mage/cards/t/TrailOfCrumbs.java b/Mage.Sets/src/mage/cards/t/TrailOfCrumbs.java new file mode 100644 index 0000000000..707eaa5063 --- /dev/null +++ b/Mage.Sets/src/mage/cards/t/TrailOfCrumbs.java @@ -0,0 +1,86 @@ +package mage.cards.t; + +import mage.abilities.TriggeredAbilityImpl; +import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.costs.mana.GenericManaCost; +import mage.abilities.effects.common.CreateTokenEffect; +import mage.abilities.effects.common.DoIfCostPaid; +import mage.abilities.effects.common.LookLibraryAndPickControllerEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.constants.Zone; +import mage.filter.FilterCard; +import mage.filter.common.FilterPermanentCard; +import mage.game.Game; +import mage.game.events.GameEvent; +import mage.game.permanent.Permanent; +import mage.game.permanent.token.FoodToken; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class TrailOfCrumbs extends CardImpl { + + public TrailOfCrumbs(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ENCHANTMENT}, "{1}{G}"); + + // When Trail of Crumbs enters the battlefield, create a Food token. + this.addAbility(new EntersBattlefieldTriggeredAbility(new CreateTokenEffect(new FoodToken()))); + + // 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()); + } + + private TrailOfCrumbs(final TrailOfCrumbs card) { + super(card); + } + + @Override + public TrailOfCrumbs copy() { + return new TrailOfCrumbs(this); + } +} + +class TrailOfCrumbsTriggeredAbility extends TriggeredAbilityImpl { + + private static final FilterCard filter = new FilterPermanentCard(); + + TrailOfCrumbsTriggeredAbility() { + super(Zone.BATTLEFIELD, new DoIfCostPaid(new LookLibraryAndPickControllerEffect( + 2, 1, filter, true, true, Zone.HAND, true + ), new GenericManaCost(1))); + } + + 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); + } + + @Override + public String getRule() { + return "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."; + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 0b9e86b177..42a5d7802d 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -160,6 +160,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Tome Raider", 68, Rarity.COMMON, mage.cards.t.TomeRaider.class)); cards.add(new SetCardInfo("Tome of Legends", 332, Rarity.RARE, mage.cards.t.TomeOfLegends.class)); cards.add(new SetCardInfo("Tournament Grounds", 248, Rarity.UNCOMMON, mage.cards.t.TournamentGrounds.class)); + cards.add(new SetCardInfo("Trail of Crumbs", 179, Rarity.UNCOMMON, mage.cards.t.TrailOfCrumbs.class)); cards.add(new SetCardInfo("True Love's Kiss", 34, Rarity.COMMON, mage.cards.t.TrueLovesKiss.class)); cards.add(new SetCardInfo("Turn into a Pumpkin", 69, Rarity.UNCOMMON, mage.cards.t.TurnIntoAPumpkin.class)); cards.add(new SetCardInfo("Venerable Knight", 35, Rarity.UNCOMMON, mage.cards.v.VenerableKnight.class)); From e3a4e9a57de75c0e3b832fbf15714ca27e31ef83 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 12 Sep 2019 19:13:11 -0400 Subject: [PATCH 102/373] Implemented Deafening Silence --- .../src/mage/cards/d/DeafeningSilence.java | 120 ++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 121 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/d/DeafeningSilence.java diff --git a/Mage.Sets/src/mage/cards/d/DeafeningSilence.java b/Mage.Sets/src/mage/cards/d/DeafeningSilence.java new file mode 100644 index 0000000000..b6863e1c3e --- /dev/null +++ b/Mage.Sets/src/mage/cards/d/DeafeningSilence.java @@ -0,0 +1,120 @@ +package mage.cards.d; + +import mage.abilities.Ability; +import mage.abilities.Mode; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.effects.ContinuousRuleModifyingEffectImpl; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.Outcome; +import mage.constants.WatcherScope; +import mage.game.Game; +import mage.game.events.GameEvent; +import mage.game.stack.Spell; +import mage.watchers.Watcher; + +import java.util.HashSet; +import java.util.Set; +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class DeafeningSilence extends CardImpl { + + public DeafeningSilence(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ENCHANTMENT}, "{W}"); + + // Each player can't cast more than one noncreature spell each turn. + this.addAbility(new SimpleStaticAbility(new DeafeningSilenceEffect()), new DeafeningSilenceWatcher()); + } + + private DeafeningSilence(final DeafeningSilence card) { + super(card); + } + + @Override + public DeafeningSilence copy() { + return new DeafeningSilence(this); + } +} + +class DeafeningSilenceEffect extends ContinuousRuleModifyingEffectImpl { + + DeafeningSilenceEffect() { + super(Duration.WhileOnBattlefield, Outcome.Detriment); + staticText = "each player can't cast more than one noncreature spell each turn"; + } + + private DeafeningSilenceEffect(final DeafeningSilenceEffect effect) { + super(effect); + } + + @Override + public DeafeningSilenceEffect copy() { + return new DeafeningSilenceEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + return true; + } + + @Override + public boolean checksEventType(GameEvent event, Game game) { + return event.getType() == GameEvent.EventType.CAST_SPELL; + } + + @Override + public boolean applies(GameEvent event, Ability source, Game game) { + Spell spell = game.getSpell(event.getTargetId()); + if (spell == null || spell.isCreature()) { + return false; + } + DeafeningSilenceWatcher watcher = game.getState().getWatcher(DeafeningSilenceWatcher.class); + return watcher != null && watcher.castSpell(event.getPlayerId()); + } + + @Override + public String getText(Mode mode) { + return "Each player can't cast more than one noncreature spell each turn."; + } +} + +class DeafeningSilenceWatcher extends Watcher { + + private final Set castSpell = new HashSet<>(); + + DeafeningSilenceWatcher() { + super(WatcherScope.GAME); + } + + private DeafeningSilenceWatcher(final DeafeningSilenceWatcher watcher) { + super(watcher); + this.castSpell.addAll(watcher.castSpell); + } + + @Override + public void watch(GameEvent event, Game game) { + if (event.getType() != GameEvent.EventType.SPELL_CAST) { + return; + } + Spell spell = game.getSpell(event.getTargetId()); + if (spell == null || spell.isCreature()) { + return; + } + castSpell.add(event.getPlayerId()); + } + + @Override + public void reset() { + super.reset(); + castSpell.clear(); + } + + boolean castSpell(UUID playerId) { + return castSpell.contains(playerId); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 42a5d7802d..107050170d 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -54,6 +54,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Corridor Monitor", 41, Rarity.COMMON, mage.cards.c.CorridorMonitor.class)); cards.add(new SetCardInfo("Crystal Slipper", 119, Rarity.COMMON, mage.cards.c.CrystalSlipper.class)); cards.add(new SetCardInfo("Curious Pair", 150, Rarity.COMMON, mage.cards.c.CuriousPair.class)); + cards.add(new SetCardInfo("Deafening Silence", 10, Rarity.UNCOMMON, mage.cards.d.DeafeningSilence.class)); cards.add(new SetCardInfo("Doom Foretold", 187, Rarity.RARE, mage.cards.d.DoomForetold.class)); cards.add(new SetCardInfo("Edgewall Innkeeper", 151, Rarity.UNCOMMON, mage.cards.e.EdgewallInnkeeper.class)); cards.add(new SetCardInfo("Elite Headhunter", 209, Rarity.UNCOMMON, mage.cards.e.EliteHeadhunter.class)); From 952f79be485f431f90868de36c4f5067442c5d51 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 12 Sep 2019 19:32:14 -0400 Subject: [PATCH 103/373] Implemented Fervent Champion --- .../src/mage/cards/f/FerventChampion.java | 107 ++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 108 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/f/FerventChampion.java diff --git a/Mage.Sets/src/mage/cards/f/FerventChampion.java b/Mage.Sets/src/mage/cards/f/FerventChampion.java new file mode 100644 index 0000000000..e6122045a4 --- /dev/null +++ b/Mage.Sets/src/mage/cards/f/FerventChampion.java @@ -0,0 +1,107 @@ +package mage.cards.f; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.AttacksTriggeredAbility; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.effects.common.continuous.BoostTargetEffect; +import mage.abilities.effects.common.cost.CostModificationEffectImpl; +import mage.abilities.keyword.EquipAbility; +import mage.abilities.keyword.FirstStrikeAbility; +import mage.abilities.keyword.HasteAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.*; +import mage.filter.FilterPermanent; +import mage.filter.predicate.permanent.AnotherPredicate; +import mage.filter.predicate.permanent.AttackingPredicate; +import mage.game.Game; +import mage.target.Target; +import mage.target.TargetPermanent; +import mage.util.CardUtil; + +import java.util.Collection; +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class FerventChampion extends CardImpl { + + private static final FilterPermanent filter + = new FilterPermanent(SubType.KNIGHT, "another target attacking Knight"); + + static { + filter.add(AttackingPredicate.instance); + filter.add(AnotherPredicate.instance); + } + + public FerventChampion(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{R}"); + + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.KNIGHT); + this.power = new MageInt(1); + this.toughness = new MageInt(1); + + // First strike + this.addAbility(FirstStrikeAbility.getInstance()); + + // Haste + this.addAbility(HasteAbility.getInstance()); + + // Whenever Fervent Champion attacks, another target attacking Knight you control gets +1/+0 until end of turn. + Ability ability = new AttacksTriggeredAbility( + new BoostTargetEffect(1, 0, Duration.EndOfTurn), false + ); + ability.addTarget(new TargetPermanent(filter)); + this.addAbility(ability); + + // Equip abilities you activate that target Fervent Champion cost {3} less to activate. + this.addAbility(new SimpleStaticAbility(new FerventChampionEffect())); + } + + private FerventChampion(final FerventChampion card) { + super(card); + } + + @Override + public FerventChampion copy() { + return new FerventChampion(this); + } +} + +class FerventChampionEffect extends CostModificationEffectImpl { + + FerventChampionEffect() { + super(Duration.Custom, Outcome.Benefit, CostModificationType.REDUCE_COST); + staticText = "equip abilities you activate that target {this} cost {3} less to activate"; + } + + private FerventChampionEffect(final FerventChampionEffect effect) { + super(effect); + } + + @Override + public boolean apply(Game game, Ability source, Ability abilityToModify) { + CardUtil.reduceCost(abilityToModify, 3); + return true; + } + + @Override + public boolean applies(Ability abilityToModify, Ability source, Game game) { + return abilityToModify instanceof EquipAbility + && abilityToModify.isControlledBy(source.getControllerId()) + && abilityToModify + .getTargets() + .stream() + .map(Target::getTargets) + .flatMap(Collection::stream) + .anyMatch(source.getSourceId()::equals); + } + + @Override + public FerventChampionEffect copy() { + return new FerventChampionEffect(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 107050170d..92ca262db1 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -71,6 +71,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Faerie Vandal", 45, Rarity.UNCOMMON, mage.cards.f.FaerieVandal.class)); cards.add(new SetCardInfo("Feasting Troll King", 152, Rarity.RARE, mage.cards.f.FeastingTrollKing.class)); cards.add(new SetCardInfo("Fell the Pheasant", 153, Rarity.COMMON, mage.cards.f.FellThePheasant.class)); + cards.add(new SetCardInfo("Fervent Champion", 124, Rarity.RARE, mage.cards.f.FerventChampion.class)); cards.add(new SetCardInfo("Fireborn Knight", 210, Rarity.UNCOMMON, mage.cards.f.FirebornKnight.class)); cards.add(new SetCardInfo("Flaxen Intruder", 155, Rarity.UNCOMMON, mage.cards.f.FlaxenIntruder.class)); cards.add(new SetCardInfo("Foulmire Knight", 90, Rarity.UNCOMMON, mage.cards.f.FoulmireKnight.class)); From 6465bd33b2d3258446fa857531bd3760ebec06a1 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 12 Sep 2019 20:06:45 -0400 Subject: [PATCH 104/373] updated ELD spoiler --- Utils/mtg-cards-data.txt | 2 ++ 1 file changed, 2 insertions(+) diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index 4c0fe3638b..02096e76eb 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -36010,6 +36010,7 @@ Knight of the Keep|Throne of Eldraine|19|C|{2}{W}|Creature - Human Knight|3|2|| Righteousness|Throne of Eldraine|27|U|{W}|Instant|||Target blocking creature gets +7/+7 until end of turn.| Shining Armor|Throne of Eldraine|29|C|{1}{W}|Artifact - Equipment|||Flash$When Shining Armor enters the battlefield, attach it to target Knight you control.$Equipped creature gets +0/+2 and has vigilance.$Equip {3}| Silverflame Ritual|Throne of Eldraine|30|C|{3}{W}|Sorcery|||Put a +1/+1 counter on each creature you control.$Adamant — If at least three white mana was spent to cast this spell, creatures you control gain vigilance until end of turn.| +Trapped in the Tower|Throne of Eldraine|33|C|{1}{W}|Enchantment - Aura|||Enchant creature without flying$Enchanted creature can't attack or block, and its activated abilities can't be activated.| True Love's Kiss|Throne of Eldraine|34|C|{2}{W}{W}|Instant|||Exile target artifact or enchantment.$Draw a card| Venerable Knight|Throne of Eldraine|35|U|{W}|Creature - Human Knight|2|1|When Venerable Knight dies, put a +1/+1 counter on target Knight you control.| Worthy Knight|Throne of Eldraine|36|R|{1}{W}|Creature - Human Knight|2|2|Whenever you cast a Knight spell, create a 1/1 white Human creature token.| @@ -36171,3 +36172,4 @@ Syr Gwyn, Hero of Ashvale|Throne of Eldraine|330|M|{3}{R}{W}{B}|Legendary Creatu Arcane Signet|Throne of Eldraine|331|C|{2}|Artifact|||{T}: Add one mana of any color in your commander's color identity.| Tome of Legends|Throne of Eldraine|332|R|{2}|Artifact|||Tome of Legends enters the battlefield with a page counter on it.$Whenever your commander enters the battlefield or attacks, put a page counter on Tome of Legends.${1}, {T}, Remove a page counter from Tome of Legends: Draw a card.| Command Tower|Throne of Eldraine|333|C||Land|||{T}: Add one mana of any color in your commander's color identity.| +Oathsworn Knight|Throne of Eldraine|354|R|{1}{B}{B}|Creature - Human Knight|0|0|Oathsworn Knight enters the battlefield with four +1/+1 counters on it.$Oathsworn Knight attacks each combat if able.$If damage would be dealt to Oathsworn Knight while it has a +1/+1 counter on it, prevent that damage and remove a +1/+1 counter from it.| From 9f17ecc89a775204271dbebd61bcfc7075603931 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 12 Sep 2019 20:09:23 -0400 Subject: [PATCH 105/373] Implemented Trapped in the Tower --- .../src/mage/cards/t/TrappedInTheTower.java | 56 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 57 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/t/TrappedInTheTower.java diff --git a/Mage.Sets/src/mage/cards/t/TrappedInTheTower.java b/Mage.Sets/src/mage/cards/t/TrappedInTheTower.java new file mode 100644 index 0000000000..9a20346278 --- /dev/null +++ b/Mage.Sets/src/mage/cards/t/TrappedInTheTower.java @@ -0,0 +1,56 @@ +package mage.cards.t; + +import mage.abilities.Ability; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.effects.common.AttachEffect; +import mage.abilities.effects.common.combat.CantBlockAttackActivateAttachedEffect; +import mage.abilities.keyword.EnchantAbility; +import mage.abilities.keyword.FlyingAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Outcome; +import mage.constants.SubType; +import mage.filter.common.FilterCreaturePermanent; +import mage.filter.predicate.Predicates; +import mage.filter.predicate.mageobject.AbilityPredicate; +import mage.target.TargetPermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class TrappedInTheTower extends CardImpl { + + private static final FilterCreaturePermanent filter = new FilterCreaturePermanent("creature without flying"); + + static { + filter.add(Predicates.not(new AbilityPredicate(FlyingAbility.class))); + } + + public TrappedInTheTower(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ENCHANTMENT}, "{1}{W}"); + + this.subtype.add(SubType.AURA); + + // Enchant creature without flying + TargetPermanent auraTarget = new TargetPermanent(filter); + this.getSpellAbility().addTarget(auraTarget); + this.getSpellAbility().addEffect(new AttachEffect(Outcome.BoostCreature)); + Ability ability = new EnchantAbility(auraTarget.getTargetName()); + this.addAbility(ability); + + // Enchanted creature can't attack or block, and its activated abilities can't be activated. + this.addAbility(new SimpleStaticAbility(new CantBlockAttackActivateAttachedEffect())); + } + + private TrappedInTheTower(final TrappedInTheTower card) { + super(card); + } + + @Override + public TrappedInTheTower copy() { + return new TrappedInTheTower(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 92ca262db1..6b2d50b347 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -163,6 +163,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Tome of Legends", 332, Rarity.RARE, mage.cards.t.TomeOfLegends.class)); cards.add(new SetCardInfo("Tournament Grounds", 248, Rarity.UNCOMMON, mage.cards.t.TournamentGrounds.class)); cards.add(new SetCardInfo("Trail of Crumbs", 179, Rarity.UNCOMMON, mage.cards.t.TrailOfCrumbs.class)); + cards.add(new SetCardInfo("Trapped in the Tower", 33, Rarity.COMMON, mage.cards.t.TrappedInTheTower.class)); cards.add(new SetCardInfo("True Love's Kiss", 34, Rarity.COMMON, mage.cards.t.TrueLovesKiss.class)); cards.add(new SetCardInfo("Turn into a Pumpkin", 69, Rarity.UNCOMMON, mage.cards.t.TurnIntoAPumpkin.class)); cards.add(new SetCardInfo("Venerable Knight", 35, Rarity.UNCOMMON, mage.cards.v.VenerableKnight.class)); From f9819493edaa9ecc2433511652b4f02559694893 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 12 Sep 2019 20:33:55 -0400 Subject: [PATCH 106/373] Implemented Once and Future --- Mage.Sets/src/mage/cards/o/OnceAndFuture.java | 101 ++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 102 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/o/OnceAndFuture.java diff --git a/Mage.Sets/src/mage/cards/o/OnceAndFuture.java b/Mage.Sets/src/mage/cards/o/OnceAndFuture.java new file mode 100644 index 0000000000..f1fd695ac4 --- /dev/null +++ b/Mage.Sets/src/mage/cards/o/OnceAndFuture.java @@ -0,0 +1,101 @@ +package mage.cards.o; + +import mage.abilities.Ability; +import mage.abilities.condition.common.AdamantCondition; +import mage.abilities.effects.OneShotEffect; +import mage.abilities.effects.common.ExileSpellEffect; +import mage.cards.*; +import mage.constants.CardType; +import mage.constants.Outcome; +import mage.constants.Zone; +import mage.game.Game; +import mage.players.Player; +import mage.target.Target; +import mage.target.common.TargetCardInYourGraveyard; +import mage.watchers.common.ManaSpentToCastWatcher; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class OnceAndFuture extends CardImpl { + + public OnceAndFuture(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.INSTANT}, "{3}{G}"); + + // Return target card from your graveyard to your hand. Put up to one other target card from your graveyard on top of your library. Exile Once and Future. + // Adamant — If at least three green mana was spent to cast this spell, instead return those cards to your hand and exile Once and Future. + this.getSpellAbility().addEffect(new OnceAndFutureEffect()); + + Target target = new TargetCardInYourGraveyard().withChooseHint("To put in your hand"); + target.setTargetTag(1); + this.getSpellAbility().addTarget(target); + + target = new TargetCardInYourGraveyard(0, 1).withChooseHint("To put on top of your library"); + target.setTargetTag(2); + this.getSpellAbility().addTarget(target); + + this.getSpellAbility().addWatcher(new ManaSpentToCastWatcher()); + } + + private OnceAndFuture(final OnceAndFuture card) { + super(card); + } + + @Override + public OnceAndFuture copy() { + return new OnceAndFuture(this); + } +} + +class OnceAndFutureEffect extends OneShotEffect { + + OnceAndFutureEffect() { + super(Outcome.Benefit); + staticText = "Return target card from your graveyard to your hand. " + + "Put up to one other target card from your graveyard on top of your library. Exile {this}." + + "
Adamant — If at least three green mana was spent to cast this spell, " + + "instead return those cards to your hand and exile {this}."; + } + + private OnceAndFutureEffect(final OnceAndFutureEffect effect) { + super(effect); + } + + @Override + public OnceAndFutureEffect copy() { + return new OnceAndFutureEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + Player player = game.getPlayer(source.getControllerId()); + if (player == null) { + return false; + } + Card card1 = game.getCard(source.getFirstTarget()); + Card card2 = game.getCard(source.getTargets().get(1).getFirstTarget()); + if (card1 == null) { + card1 = card2; + card2 = null; + } + if (card1 == null) { + return false; + } + if (card2 == null) { + player.putInHand(card1, game); + return ExileSpellEffect.getInstance().apply(game, source); + } + if (AdamantCondition.GREEN.apply(game, source)) { + Cards cards = new CardsImpl(); + cards.add(card1); + cards.add(card2); + player.moveCards(cards, Zone.HAND, source, game); + return ExileSpellEffect.getInstance().apply(game, source); + } + player.putInHand(card1, game); + player.putCardsOnTopOfLibrary(new CardsImpl(card2), game, source, false); + return ExileSpellEffect.getInstance().apply(game, source); + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 6b2d50b347..cc27430e97 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -116,6 +116,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Oko, Thief of Crowns", 197, Rarity.MYTHIC, mage.cards.o.OkoThiefOfCrowns.class)); cards.add(new SetCardInfo("Oko, the Trickster", 309, Rarity.MYTHIC, mage.cards.o.OkoTheTrickster.class)); cards.add(new SetCardInfo("Once Upon a Time", 169, Rarity.RARE, mage.cards.o.OnceUponATime.class)); + cards.add(new SetCardInfo("Once and Future", 168, Rarity.UNCOMMON, mage.cards.o.OnceAndFuture.class)); cards.add(new SetCardInfo("Opt", 59, Rarity.COMMON, mage.cards.o.Opt.class)); cards.add(new SetCardInfo("Order of Midnight", 99, Rarity.UNCOMMON, mage.cards.o.OrderOfMidnight.class)); cards.add(new SetCardInfo("Outmuscle", 170, Rarity.COMMON, mage.cards.o.Outmuscle.class)); From 8d461d8676d4d3748f4d3e498e9cf9ebce4968d1 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 13 Sep 2019 08:05:37 -0400 Subject: [PATCH 107/373] fixed Arcanist's Owl not triggering when it enters the battlefield (fixes #5980) --- Mage.Sets/src/mage/cards/a/ArcanistsOwl.java | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/Mage.Sets/src/mage/cards/a/ArcanistsOwl.java b/Mage.Sets/src/mage/cards/a/ArcanistsOwl.java index 47e465d620..eb42874e68 100644 --- a/Mage.Sets/src/mage/cards/a/ArcanistsOwl.java +++ b/Mage.Sets/src/mage/cards/a/ArcanistsOwl.java @@ -1,6 +1,7 @@ package mage.cards.a; import mage.MageInt; +import mage.abilities.common.EntersBattlefieldTriggeredAbility; import mage.abilities.dynamicvalue.common.StaticValue; import mage.abilities.effects.common.LookLibraryAndPickControllerEffect; import mage.abilities.keyword.FlyingAbility; @@ -32,7 +33,7 @@ public final class ArcanistsOwl extends CardImpl { this.addAbility(FlyingAbility.getInstance()); // When Arcanist's Owl enters the battlefield, look at the top four cards of your library. You may reveal an artifact or enchantment card from among them and put it into your hand. Put the rest on the bottom of your library in a random order. - this.getSpellAbility().addEffect( + this.addAbility(new EntersBattlefieldTriggeredAbility( new LookLibraryAndPickControllerEffect( new StaticValue(4), false, new StaticValue(1), filter, Zone.LIBRARY, false, true, false, Zone.HAND, @@ -40,7 +41,7 @@ public final class ArcanistsOwl extends CardImpl { ).setBackInRandomOrder(true).setText("Look at the top four cards of your library. " + "You may reveal an artifact or enchantment from among them and put it into your hand. " + "Put the rest on the bottom of your library in a random order.") - ); + )); } private ArcanistsOwl(final ArcanistsOwl card) { From dd134271f35c9116e848c7ae95ce5ea40245cf5d Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 13 Sep 2019 08:07:56 -0400 Subject: [PATCH 108/373] updated ELD spoiler --- Utils/mtg-cards-data.txt | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index 02096e76eb..4b9c44658f 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -36047,6 +36047,7 @@ Profane Insight|Throne of Eldraine|90|U|{2}{B}|Instant - Adventure|1|1|You draw Lost Legion|Throne of Eldraine|94|C|{1}{B}{B}|Creature - Spirit Knight|2|3|When Lost Legion enters the battlefield, scry 2.| Murderous Rider|Throne of Eldraine|97|R|{1}{B}{B}|Creature - Zombie Knight|2|3|Lifelink$When Murderous Rider dies, put it on the bottom of its owner's library.| Swift End|Throne of Eldraine|97|R|{1}{B}{B}|Instant - Adventure|2|3|Destroy target creature or planeswalker. You lose 2 life.| +Oathsworn Knight|Throne of Eldraine|98|R|{1}{B}{B}|Creature - Human Knight|0|0|Oathsworn Knight enters the battlefield with four +1/+1 counters on it.$Oathsworn Knight attacks each combat if able.$If damage would be dealt to Oathsworn Knight while it has a +1/+1 counter on it, prevent that damage and remove a +1/+1 counter from it.| Alter Fate|Throne of Eldraine|99|U|{1}{B}|Sorcery - Adventure|2|2|Return target creature card from your graveyard to your hand.| Order of Midnight|Throne of Eldraine|99|U|{1}{B}|Creature - Human Knight|2|2|Flying$Order of Midnight can't block.| Piper of the Swarm|Throne of Eldraine|100|R|{1}{B}|Creature - Human Warlock|1|3|Rats you control have menace.${1}{B}, {T}: Create a 1/1 black Rat creature token.${2}{B}{B}, {T}, Sacrifice three Rats: Gain control of target creature.| @@ -36089,12 +36090,14 @@ Treats to Share|Throne of Eldraine|150|C|{G}|Sorcery - Adventure|1|3|Create a Fo Edgewall Innkeeper|Throne of Eldraine|151|U|{G}|Creature - Human Peasant|1|1|Whenever you cast a creature spell that has an Adventure, draw a card.| Feasting Troll King|Throne of Eldraine|152|R|{2}{G}{G}{G}{G}|Creature - Troll Noble|7|6|Vigilance, trample$When Feasting Troll King enters the battlefield, if you cast it from your hand, create three Food tokens.$Sacrifice three Foods: Return Feasting Troll King from your graveyard to the battlefield. Activate this ability only during your turn.| Fell the Pheasant|Throne of Eldraine|153|C|{1}{G}|Instant|||Fell the Pheasant deals 5 damage to target creature with flying. Create a Food token.| +Fierce Witchstalker|Throne of Eldraine|154|C|{2}{G}{G}|Creature - Wolf|4|4|Trample$When Fierce Witchstalker enters the battlefield, create a Food token.| Flaxen Intruder|Throne of Eldraine|155|U|{G}|Creature - Human Berserker|1|2|Whenever Flaxen Intruder deals combat damage to a player, you may sacrifice it. When you do, destroy target artifact or enchantment.| Welcome Home|Throne of Eldraine|155|U|{5}{G}{G}|Sorcery - Adventure|1|2|Create three 2/2 green Bear creature tokens.| Garenbrig Paladin|Throne of Eldraine|157|C|{4}{G}|Creature - Giant Knight|4|4|Adamant — If at least three green mana was spent to cast this spell, Garenbrig Paladin enters the battlefield with a +1/+1 counter on it.$Garenbrig Paladin can't be blocked by creatures with power 2 or less.| Gilded Goose|Throne of Eldraine|160|R|{G}|Creature - Bird|0|2|Flying$When Gilded Goose enters the battlefield, create a Food token.${1}{G}, {T}: Create a Food token.${T}, Sacrifice a Food: Add one mana of any color.| Insatiable Appetite|Throne of Eldraine|162|C|{1}{G}|Instant|||You may sacrifice a Food. If you do, target creature gets +5/+5 until end of turn. Otherwise, that creature gets +3/+3 until end of turn.| Keeper of Fables|Throne of Eldraine|163|U|{3}{G}{G}|Creature - Cat|4|5|Whenever one or more non-Human creatures you control deal combat damage to a player, draw a card.| +Wolf's Quarry|Throne of Eldraine|164|C|{4}{G}{G}|Sorcery|||Create three 1/1 green Boar creature tokens with "When this creature dies, create a Food token."| Heart's Desire|Throne of Eldraine|165|R|{G}|Sorcery - Adventure|5|5|Create a 1/1 white Human creature token.| Lovestruck Beast|Throne of Eldraine|165|R|{2}{G}|Creature - Beast Noble|5|5|Lovestruck Beast can't attack unless you control a 1/1 creature.| Maraleaf Rider|Throne of Eldraine|166|C|{1}{G}|Creature - Elf Knight|3|1|Sacrifice a Food: Target creature blocks Maraleaf Rider this turn if able.| @@ -36110,6 +36113,7 @@ Wicked Wolf|Throne of Eldraine|181|R|{2}{G}{G}|Creature - Wolf|3|3|When Wicked W Wildborn Preserver|Throne of Eldraine|182|R|{1}{G}|Creature - Elf Archer|2|2|Flash$Reach$Whenever another non-Human creature enters the battlefield under your control, you may pay {X}. When you do, put X +1/+1 counters on Wildborn Preserver.| Wildwood Tracker|Throne of Eldraine|183|C|{G}|Creature - Elf Warrior|1|1|Whenever Wildwood Tracker attacks or blocks, if you control another non-Human creature, Wildwood Tracker gets +1/+1 until end of turn.| Doom Foretold|Throne of Eldraine|187|R|{2}{W}{B}|Enchantment|||At the beginning of each player's upkeep, that player sacrifices a nonland, nontoken permanent. If that player can't, they discard a card, they lose 2 life, you draw a card, you gain 2 life, you create a 2/2 white Knight creature token with vigilance, then you sacrifice Doom Foretold.| +Faeburrow Elder|Throne of Eldraine|190|R|{1}{G}{W}|Creature - Treefolk Druid|0|0|Vigilance$Faeburrow Elder gets +1/+1 for each color among permanents you control.${T}: For each color among permanents you control, add one mana of that color.| Garruk, Cursed Huntsman|Throne of Eldraine|191|M|{4}{B}{G}|Legendary Planeswalker - Garruk|5|0: Create two 2/2 black and green Wolf creature tokens with "When this creature dies, put a loyalty counter on each Garruk you control."$−3: Destroy target creature. Draw a card.$−6: You get an emblem with "Creatures you control get +3/+3 and have trample."| Inspiring Veteran|Throne of Eldraine|194|U|{R}{W}|Creature - Human Knight|2|2|Other Knights you control get +1/+1.| Lochmere Serpent|Throne of Eldraine|195|R|{4}{U}{B}|Creature - Serpent|7|7|Flash${U}, Sacrifice an Island: Lochmere Serpent can't be blocked this turn.${B}, Sacrifice a Swamp: You gain 1 life and draw a card.${U}{B}: Exile five target cards from an opponent's graveyard. Return Lochmere Serpent from your graveyard to your hand. Activate this ability only any time you could cast a sorcery.| @@ -36172,4 +36176,3 @@ Syr Gwyn, Hero of Ashvale|Throne of Eldraine|330|M|{3}{R}{W}{B}|Legendary Creatu Arcane Signet|Throne of Eldraine|331|C|{2}|Artifact|||{T}: Add one mana of any color in your commander's color identity.| Tome of Legends|Throne of Eldraine|332|R|{2}|Artifact|||Tome of Legends enters the battlefield with a page counter on it.$Whenever your commander enters the battlefield or attacks, put a page counter on Tome of Legends.${1}, {T}, Remove a page counter from Tome of Legends: Draw a card.| Command Tower|Throne of Eldraine|333|C||Land|||{T}: Add one mana of any color in your commander's color identity.| -Oathsworn Knight|Throne of Eldraine|354|R|{1}{B}{B}|Creature - Human Knight|0|0|Oathsworn Knight enters the battlefield with four +1/+1 counters on it.$Oathsworn Knight attacks each combat if able.$If damage would be dealt to Oathsworn Knight while it has a +1/+1 counter on it, prevent that damage and remove a +1/+1 counter from it.| From a22165f38857aee5b922694f99e0c3703d45b03d Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 13 Sep 2019 08:08:41 -0400 Subject: [PATCH 109/373] Implemented Fierce Witchstalker --- .../src/mage/cards/f/FierceWitchstalker.java | 42 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 43 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/f/FierceWitchstalker.java diff --git a/Mage.Sets/src/mage/cards/f/FierceWitchstalker.java b/Mage.Sets/src/mage/cards/f/FierceWitchstalker.java new file mode 100644 index 0000000000..a4defd85a5 --- /dev/null +++ b/Mage.Sets/src/mage/cards/f/FierceWitchstalker.java @@ -0,0 +1,42 @@ +package mage.cards.f; + +import mage.MageInt; +import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.effects.common.CreateTokenEffect; +import mage.abilities.keyword.TrampleAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.game.permanent.token.FoodToken; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class FierceWitchstalker extends CardImpl { + + public FierceWitchstalker(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{2}{G}{G}"); + + this.subtype.add(SubType.WOLF); + this.power = new MageInt(4); + this.toughness = new MageInt(4); + + // Trample + this.addAbility(TrampleAbility.getInstance()); + + // When Fierce Witchstalker enters the battlefield, create a Food token. + this.addAbility(new EntersBattlefieldTriggeredAbility(new CreateTokenEffect(new FoodToken()))); + } + + private FierceWitchstalker(final FierceWitchstalker card) { + super(card); + } + + @Override + public FierceWitchstalker copy() { + return new FierceWitchstalker(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index cc27430e97..dd8297bb40 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -72,6 +72,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Feasting Troll King", 152, Rarity.RARE, mage.cards.f.FeastingTrollKing.class)); cards.add(new SetCardInfo("Fell the Pheasant", 153, Rarity.COMMON, mage.cards.f.FellThePheasant.class)); cards.add(new SetCardInfo("Fervent Champion", 124, Rarity.RARE, mage.cards.f.FerventChampion.class)); + cards.add(new SetCardInfo("Fierce Witchstalker", 154, Rarity.COMMON, mage.cards.f.FierceWitchstalker.class)); cards.add(new SetCardInfo("Fireborn Knight", 210, Rarity.UNCOMMON, mage.cards.f.FirebornKnight.class)); cards.add(new SetCardInfo("Flaxen Intruder", 155, Rarity.UNCOMMON, mage.cards.f.FlaxenIntruder.class)); cards.add(new SetCardInfo("Foulmire Knight", 90, Rarity.UNCOMMON, mage.cards.f.FoulmireKnight.class)); From 9604aa9bef9964a32ccfe4f7b9a11630d09c4bdd Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 13 Sep 2019 08:12:09 -0400 Subject: [PATCH 110/373] Implemented Wolf's Quarry --- Mage.Sets/src/mage/cards/w/WolfsQuarry.java | 31 ++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + .../permanent/token/WolfsQuarryToken.java | 32 +++++++++++++++++++ 3 files changed, 64 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/w/WolfsQuarry.java create mode 100644 Mage/src/main/java/mage/game/permanent/token/WolfsQuarryToken.java diff --git a/Mage.Sets/src/mage/cards/w/WolfsQuarry.java b/Mage.Sets/src/mage/cards/w/WolfsQuarry.java new file mode 100644 index 0000000000..befa35de34 --- /dev/null +++ b/Mage.Sets/src/mage/cards/w/WolfsQuarry.java @@ -0,0 +1,31 @@ +package mage.cards.w; + +import mage.abilities.effects.common.CreateTokenEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.game.permanent.token.WolfsQuarryToken; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class WolfsQuarry extends CardImpl { + + public WolfsQuarry(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.SORCERY}, "{4}{G}{G}"); + + // Create three 1/1 green Boar creature tokens with "When this creature dies, create a Food token." + this.getSpellAbility().addEffect(new CreateTokenEffect(new WolfsQuarryToken(), 3)); + } + + private WolfsQuarry(final WolfsQuarry card) { + super(card); + } + + @Override + public WolfsQuarry copy() { + return new WolfsQuarry(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index dd8297bb40..a0c72314ae 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -183,6 +183,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Witch's Oven", 237, Rarity.UNCOMMON, mage.cards.w.WitchsOven.class)); cards.add(new SetCardInfo("Witch's Vengeance", 111, Rarity.RARE, mage.cards.w.WitchsVengeance.class)); cards.add(new SetCardInfo("Witching Well", 74, Rarity.COMMON, mage.cards.w.WitchingWell.class)); + cards.add(new SetCardInfo("Wolf's Quarry", 164, Rarity.COMMON, mage.cards.w.WolfsQuarry.class)); cards.add(new SetCardInfo("Workshop Elders", 318, Rarity.RARE, mage.cards.w.WorkshopElders.class)); cards.add(new SetCardInfo("Worthy Knight", 36, Rarity.RARE, mage.cards.w.WorthyKnight.class)); diff --git a/Mage/src/main/java/mage/game/permanent/token/WolfsQuarryToken.java b/Mage/src/main/java/mage/game/permanent/token/WolfsQuarryToken.java new file mode 100644 index 0000000000..60f4b9f96d --- /dev/null +++ b/Mage/src/main/java/mage/game/permanent/token/WolfsQuarryToken.java @@ -0,0 +1,32 @@ +package mage.game.permanent.token; + +import mage.MageInt; +import mage.abilities.common.DiesTriggeredAbility; +import mage.abilities.effects.common.CreateTokenEffect; +import mage.constants.CardType; +import mage.constants.SubType; + +/** + * @author TheElk801 + */ +public final class WolfsQuarryToken extends TokenImpl { + + public WolfsQuarryToken() { + super("Boar", "1/1 green Boar creature token with \"When this creature dies, create a Food token.\""); + cardType.add(CardType.CREATURE); + color.setGreen(true); + subtype.add(SubType.BOAR); + power = new MageInt(1); + toughness = new MageInt(1); + + this.addAbility(new DiesTriggeredAbility(new CreateTokenEffect(new FoodToken()))); + } + + private WolfsQuarryToken(final WolfsQuarryToken token) { + super(token); + } + + public WolfsQuarryToken copy() { + return new WolfsQuarryToken(this); + } +} From cc9721f6b0f8a246386a1d78c19711d1281565ff Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 13 Sep 2019 08:36:35 -0400 Subject: [PATCH 111/373] Implemented Faeburrow Elder --- .../src/mage/cards/f/FaeburrowElder.java | 142 ++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 143 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/f/FaeburrowElder.java diff --git a/Mage.Sets/src/mage/cards/f/FaeburrowElder.java b/Mage.Sets/src/mage/cards/f/FaeburrowElder.java new file mode 100644 index 0000000000..6cfbe65430 --- /dev/null +++ b/Mage.Sets/src/mage/cards/f/FaeburrowElder.java @@ -0,0 +1,142 @@ +package mage.cards.f; + +import mage.MageInt; +import mage.Mana; +import mage.ObjectColor; +import mage.abilities.Ability; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.costs.common.TapSourceCost; +import mage.abilities.dynamicvalue.DynamicValue; +import mage.abilities.effects.Effect; +import mage.abilities.effects.common.ManaEffect; +import mage.abilities.effects.common.continuous.BoostSourceEffect; +import mage.abilities.keyword.VigilanceAbility; +import mage.abilities.mana.SimpleManaAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; +import mage.constants.Zone; +import mage.game.Game; +import mage.game.permanent.Permanent; +import mage.players.Player; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class FaeburrowElder extends CardImpl { + + public FaeburrowElder(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{1}{G}{W}"); + + this.subtype.add(SubType.TREEFOLK); + this.subtype.add(SubType.DRUID); + this.power = new MageInt(0); + this.toughness = new MageInt(0); + + // Vigilance + this.addAbility(VigilanceAbility.getInstance()); + + // Faeburrow Elder gets +1/+1 for each color among permanents you control. + this.addAbility(new SimpleStaticAbility(new BoostSourceEffect( + FaeburrowElderValue.instance, FaeburrowElderValue.instance, Duration.WhileOnBattlefield, false + ))); + + // {T}: For each color among permanents you control, add one mana of that color. + this.addAbility(new SimpleManaAbility(Zone.BATTLEFIELD, new FaeburrowElderManaEffect(), new TapSourceCost())); + } + + private FaeburrowElder(final FaeburrowElder card) { + super(card); + } + + @Override + public FaeburrowElder copy() { + return new FaeburrowElder(this); + } +} + +enum FaeburrowElderValue implements DynamicValue { + instance; + + @Override + public int calculate(Game game, Ability sourceAbility, Effect effect) { + ObjectColor color = new ObjectColor(""); + game.getBattlefield() + .getAllActivePermanents(sourceAbility.getControllerId()) + .stream() + .map(permanent -> permanent.getColor(game)) + .forEach(color::addColor); + return color.getColorCount(); + } + + @Override + public FaeburrowElderValue copy() { + return instance; + } + + @Override + public String toString() { + return "1"; + } + + @Override + public String getMessage() { + return "for each color among permanents you control"; + } +} + +class FaeburrowElderManaEffect extends ManaEffect { + + FaeburrowElderManaEffect() { + super(); + staticText = "For each color among permanents you control, add one mana of that color"; + } + + private FaeburrowElderManaEffect(final FaeburrowElderManaEffect effect) { + super(effect); + } + + @Override + public FaeburrowElderManaEffect copy() { + return new FaeburrowElderManaEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + Player controller = game.getPlayer(source.getControllerId()); + if (controller == null) { + return false; + } + Mana mana = getMana(game, source); + checkToFirePossibleEvents(mana, game, source); + controller.getManaPool().addMana(mana, game, source); + return true; + } + + @Override + public Mana produceMana(boolean netMana, Game game, Ability source) { + Mana mana = new Mana(); + for (Permanent permanent : game.getBattlefield().getAllActivePermanents(source.getControllerId())) { + if (mana.getBlack() == 0 && permanent.getColor(game).isBlack()) { + mana.increaseBlack(); + } + if (mana.getBlue() == 0 && permanent.getColor(game).isBlue()) { + mana.increaseBlue(); + } + if (mana.getRed() == 0 && permanent.getColor(game).isRed()) { + mana.increaseRed(); + } + if (mana.getGreen() == 0 && permanent.getColor(game).isGreen()) { + mana.increaseGreen(); + } + if (mana.getWhite() == 0 && permanent.getColor(game).isWhite()) { + mana.increaseWhite(); + } + } + return mana; + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index a0c72314ae..0b45bfd813 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -66,6 +66,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Enchanted Carriage", 218, Rarity.UNCOMMON, mage.cards.e.EnchantedCarriage.class)); cards.add(new SetCardInfo("Epic Downfall", 85, Rarity.UNCOMMON, mage.cards.e.EpicDownfall.class)); cards.add(new SetCardInfo("Eye Collector", 86, Rarity.COMMON, mage.cards.e.EyeCollector.class)); + cards.add(new SetCardInfo("Faeburrow Elder", 190, Rarity.RARE, mage.cards.f.FaeburrowElder.class)); cards.add(new SetCardInfo("Faerie Formation", 316, Rarity.RARE, mage.cards.f.FaerieFormation.class)); cards.add(new SetCardInfo("Faerie Guidemother", 11, Rarity.COMMON, mage.cards.f.FaerieGuidemother.class)); cards.add(new SetCardInfo("Faerie Vandal", 45, Rarity.UNCOMMON, mage.cards.f.FaerieVandal.class)); From 42e2c3a53c6f8d01078a830b336a980b8ff641b9 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 13 Sep 2019 13:01:11 -0400 Subject: [PATCH 112/373] updated ELD spoiler --- Utils/mtg-cards-data.txt | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index 4b9c44658f..9c56bae362 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -36019,12 +36019,15 @@ Bring to Life|Throne of Eldraine|38|U|{2}{U}|Sorcery - Adventure|2|2|Target nonc Corridor Monitor|Throne of Eldraine|41|C|{1}{U}|Artifact Creature - Construct|1|4|When Corridor Monitor enters the battlefield, untap target artifact or creature you control.| Emry, Lurker of the Loch|Throne of Eldraine|43|R|{2}{U}|Legendary Creature - Merfolk Wizard|1|2|This spell costs {1} less to cast for each artifact you control.$When Emry, Lurker of the Loch enters the battlefield, put the top four cards of your library into your graveyard.${T}: Choose target artifact card in your graveyard. You may cast that card this turn.| Faerie Vandal|Throne of Eldraine|45|U|{1}{U}|Creature - Faerie Rogue|1|2|Flash$Flying$Whenever you draw your second card each turn, put a +1/+1 counter on Faerie Vandal.| +Folio of Fancies|Throne of Eldraine|46|R|{1}{U}|Artifact|||Players have no maximum hand size.${X}{X}, {T}: Each player draws X cards.${2}{U}, {T}: Each opponent puts a number of cards equal to the number of cards in their hand from the top of their library into their graveyard.| Frogify|Throne of Eldraine|47|U|{1}{U}|Enchantment - Aura|||Enchant creature$Enchanted creature loses all abilities and is a blue Frog creature with base power and toughness 1/1.| Gadwick, the Wizened|Throne of Eldraine|48|R|{X}{U}{U}{U}|Legendary Creature - Human Wizard|3|3|When Gadwick, the Wizened enters the battlefield, draw X cards.$Whenever you cast a blue spell, tap target nonland permanent an opponent controls.| Hypnotic Sprite|Throne of Eldraine|49|U|{U}{U}|Creature - Faerie|2|1|Flying| Mesmeric Glare|Throne of Eldraine|49|U|{2}{U}|Instant - Adventure|2|1|Counter target spell with converted mana cost 3 or less.| Into the Story|Throne of Eldraine|50|U|{5}{U}{U}|Instant|||This spell costs {3} less to cast if an opponent has seven or more cards in their graveyard.$Draw four cards.| +The Magic Mirror|Throne of Eldraine|51|M|{6}{U}{U}{U}|Legendary Artifact|||This spell costs {1} less to cast for each instant and sorcery card in your graveyard.$You have no maximum hand size.$At the beginning of your upkeep, put a knowledge counter on The Magic Mirror, then draw a card for each knowledge counter on The Magic Mirror.| Midnight Clock|Throne of Eldraine|54|R|{2}{U}|Artifact|||{T}: Add {U}.${2}{U}: Put an hour counter on Midnight Clock.$At the beginning of each upkeep, put an hour counter on Midnight Clock.$When the twelfth hour counter is put on Midnight Clock, shuffle your hand and graveyard into your library, then draw seven cards. Exile Midnight Clock.| +Mirrormade|Throne of Eldraine|55|R|{1}{U}{U}|Enchantment|||You may have Mirrormade enter the battlefield as a copy of any artifact or enchantment on the battlefield.| Mystical Dispute|Throne of Eldraine|58|U|{2}{U}|Instant|||This spell costs {2} less to cast if it targets a blue spell.$Counter target spell unless its controller pays {3}.| Opt|Throne of Eldraine|59|C|{U}|Instant|||Scry 1.$Draw a card.| Run Away Together|Throne of Eldraine|62|C|{1}{U}|Instant|||Choose two target creatures controlled by different players. Return those creatures to their owners' hands.| @@ -36032,6 +36035,7 @@ Stolen by the Fae|Throne of Eldraine|66|R|{X}{U}{U}|Sorcery|||Return target crea Syr Elenora, the Discerning|Throne of Eldraine|67|U|{3}{U}{U}|Legendary Creature - Human Knight|*|4|Syr Elenora, the Discerning's power is equal to the number of cards in your hand.$When Syr Elenora enters the battlefield, draw a card.$Spells your opponents cast that target Syr Elenora cost {2} more to cast.| Tome Raider|Throne of Eldraine|68|C|{2}{U}|Creature - Faerie|1|1|Flying$When Tome Raider enters the battlefield, draw a card.| Turn into a Pumpkin|Throne of Eldraine|69|U|{3}{U}|Instant|||Return target nonland permanent to its owner's hand. Draw a card.$Adamant — If at least three blue mana was spent to cast this spell, create a Food token.| +Vantress Gargoyle|Throne of Eldraine|71|R|{1}{U}|Artifact Creature - Gargoyle|5|4|Flying$Vantress Gargoyle can't attack unless defending player has seven or more cards in their graveyard.$Vantress Gargoyle can't block unless you have four or more cards in hand.${T}: Each player puts the top card of their library into their graveyard.| Wishful Merfolk|Throne of Eldraine|73|C|{1}{U}|Creature - Merfolk|3|2|Defender${1}{U}: Wishful Merfolk loses defender and becomes a Human until end of turn.| Witching Well|Throne of Eldraine|74|C|{U}|Artifact|||When Witching Well enters the battlefield, scry 2.${3}{U}, Sacrifice Witching Well: Draw two cards.| Ayara, First of Locthwain|Throne of Eldraine|75|R|{B}{B}{B}|Legendary Creature - Elf Noble|2|3|Whenever Ayara, First of Locthwain or another black creature enters the battlefield under your control, each opponent loses 1 life and you gain 1 life.${T}, Sacrifice another black creature: Draw a card.| @@ -36060,6 +36064,8 @@ Wicked Guardian|Throne of Eldraine|109|C|{3}{B}|Creature - Human Noble|4|2|When Wishclaw Talisman|Throne of Eldraine|110|R|{1}{B}|Artifact|||Wishclaw Talisman enters the battlefield with three wish counters on it.${1}, {T}, Remove a wish counter from Wishclaw Talisman: Search your library for a card, put it into your hand, then shuffle your library. An opponent gains control of Wishclaw Talisman. Activate this ability only during your turn.| Witch's Vengeance|Throne of Eldraine|111|R|{1}{B}{B}|Sorcery|||Creatures of the creature type of your choice get -3/-3 until end of turn.| Blow Your House Down|Throne of Eldraine|114|C|{2}{R}|Sorcery|||Up to three target creatures can't block this turn. Destroy any of them that are Walls.| +Bonecrusher Giant|Throne of Eldraine|115|R|{2}{R}|Creature - Giant|4|3|Whenever Bonecrusher Giant becomes the target of a spell, Bonecrusher Giant deals 2 damage to that spell's controller.| +Stomp|Throne of Eldraine|115|R|{1}{R}|Instant - Adventure|4|3|Damage can't be prevented this turn. Stomp deals 2 damage to any target.| Brimstone Trebuchet|Throne of Eldraine|116|C|{2}{R}|Artifact Creature - Wall|1|3|Defender, reach${T}: Brimstone Trebuchet deals 1 damage to each opponent.$Whenever a Knight enters the battlefield under your control, untap Brimstone Trebuchet.| Burning-Yard Trainer|Throne of Eldraine|117|U|{4}{R}|Creature - Human Knight|3|3|Trample, haste$When Burning-Yard Trainer enters the battlefield, another target Knight you control gets +2/+2 and gains trample and haste until end of turn.| Claim the Firstborn|Throne of Eldraine|118|U|{R}|Sorcery|||Gain control of target creature with converted mana cost 3 or less until end of turn. Untap that creature. It gains haste until end of turn.| @@ -36069,6 +36075,7 @@ Embereth Paladin|Throne of Eldraine|121|C|{3}{R}|Creature - Human Knight|4|1|Has Battle Display|Throne of Eldraine|122|U|{R}|Sorcery - Adventure|2|1|Destroy target artifact.| Embereth Shieldbreaker|Throne of Eldraine|122|U|{1}{R}|Creature - Human Knight|2|1|| Fervent Champion|Throne of Eldraine|124|R|{R}|Creature - Human Knight|1|1|First strike, haste$Whenever Fervent Champion attacks, another target attacking Knight you control gets +1/+0 until end of turn.$Equip abilities you activate that target Fervent Champion cost {3} less to activate.| +Irencrag Feat|Throne of Eldraine|127|R|{1}{R}{R}{R}|Sorcery|||Add seven {R}. You can cast only one more spell this turn.| Joust|Throne of Eldraine|129|U|{1}{R}|Sorcery|||Choose target creature you control and target creature you don't control. The creature you control gets +2/+1 until end of turn if it's a Knight. Then those creatures fight each other.| Haggle|Throne of Eldraine|131|C|{R}|Instant - Adventure|2|3|You may discard a card. If you do, draw a card.| Merchant of the Vale|Throne of Eldraine|131|C|{2}{R}|Creature - Human Peasant|2|3|{2}{R}, Discard a card: Draw a card.| @@ -36112,6 +36119,7 @@ Trail of Crumbs|Throne of Eldraine|179|U|{1}{G}|Enchantment|||When Trail of Crum Wicked Wolf|Throne of Eldraine|181|R|{2}{G}{G}|Creature - Wolf|3|3|When Wicked Wolf enters the battlefield, it fights up to one target creature you don't control.$Sacrifice a Food: Put a +1/+1 counter on Wicked Wolf. It gains indestructible until end of turn. Tap it.| Wildborn Preserver|Throne of Eldraine|182|R|{1}{G}|Creature - Elf Archer|2|2|Flash$Reach$Whenever another non-Human creature enters the battlefield under your control, you may pay {X}. When you do, put X +1/+1 counters on Wildborn Preserver.| Wildwood Tracker|Throne of Eldraine|183|C|{G}|Creature - Elf Warrior|1|1|Whenever Wildwood Tracker attacks or blocks, if you control another non-Human creature, Wildwood Tracker gets +1/+1 until end of turn.| +Dance of the Manse|Throne of Eldraine|186|R|{X}{W}{U}|Sorcery|||Return up to X target artifact and/or non-Aura enchantment cards each with converted mana cost X or less from your graveyard to the battlefield. If X is 6 or more, those permanents are 4/4 creatures in addition to their other types.| Doom Foretold|Throne of Eldraine|187|R|{2}{W}{B}|Enchantment|||At the beginning of each player's upkeep, that player sacrifices a nonland, nontoken permanent. If that player can't, they discard a card, they lose 2 life, you draw a card, you gain 2 life, you create a 2/2 white Knight creature token with vigilance, then you sacrifice Doom Foretold.| Faeburrow Elder|Throne of Eldraine|190|R|{1}{G}{W}|Creature - Treefolk Druid|0|0|Vigilance$Faeburrow Elder gets +1/+1 for each color among permanents you control.${T}: For each color among permanents you control, add one mana of that color.| Garruk, Cursed Huntsman|Throne of Eldraine|191|M|{4}{B}{G}|Legendary Planeswalker - Garruk|5|0: Create two 2/2 black and green Wolf creature tokens with "When this creature dies, put a loyalty counter on each Garruk you control."$−3: Destroy target creature. Draw a card.$−6: You get an emblem with "Creatures you control get +3/+3 and have trample."| From 4ab1e4a8eda83d5de7e61ba1d5dae40469237fa1 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 13 Sep 2019 13:02:20 -0400 Subject: [PATCH 113/373] Implemented Mirrormade --- Mage.Sets/src/mage/cards/m/Mirrormade.java | 34 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 35 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/m/Mirrormade.java diff --git a/Mage.Sets/src/mage/cards/m/Mirrormade.java b/Mage.Sets/src/mage/cards/m/Mirrormade.java new file mode 100644 index 0000000000..4a82c19e0d --- /dev/null +++ b/Mage.Sets/src/mage/cards/m/Mirrormade.java @@ -0,0 +1,34 @@ +package mage.cards.m; + +import mage.abilities.common.EntersBattlefieldAbility; +import mage.abilities.effects.common.CopyPermanentEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.filter.StaticFilters; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class Mirrormade extends CardImpl { + + public Mirrormade(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ENCHANTMENT}, "{1}{U}{U}"); + + // You may have Mirrormade enter the battlefield as a copy of any artifact or enchantment on the battlefield. + this.addAbility(new EntersBattlefieldAbility( + new CopyPermanentEffect(StaticFilters.FILTER_PERMANENT_ARTIFACT_OR_ENCHANTMENT), true + )); + } + + private Mirrormade(final Mirrormade card) { + super(card); + } + + @Override + public Mirrormade copy() { + return new Mirrormade(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 0b45bfd813..3bc91be1db 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -109,6 +109,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Maraleaf Rider", 166, Rarity.COMMON, mage.cards.m.MaraleafRider.class)); cards.add(new SetCardInfo("Merchant of the Vale", 131, Rarity.COMMON, mage.cards.m.MerchantOfTheVale.class)); cards.add(new SetCardInfo("Midnight Clock", 54, Rarity.RARE, mage.cards.m.MidnightClock.class)); + cards.add(new SetCardInfo("Mirrormade", 55, Rarity.RARE, mage.cards.m.Mirrormade.class)); cards.add(new SetCardInfo("Murderous Rider", 97, Rarity.RARE, mage.cards.m.MurderousRider.class)); cards.add(new SetCardInfo("Mystical Dispute", 58, Rarity.UNCOMMON, mage.cards.m.MysticalDispute.class)); cards.add(new SetCardInfo("Oakhame Ranger", 212, Rarity.UNCOMMON, mage.cards.o.OakhameRanger.class)); From 8806174caeeb1304b0f2b6c19523cd29ad63b41e Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 13 Sep 2019 13:24:13 -0400 Subject: [PATCH 114/373] Implemented Folio of Fancies --- .../src/mage/cards/f/FolioOfFancies.java | 95 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 96 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/f/FolioOfFancies.java diff --git a/Mage.Sets/src/mage/cards/f/FolioOfFancies.java b/Mage.Sets/src/mage/cards/f/FolioOfFancies.java new file mode 100644 index 0000000000..191fe2c06d --- /dev/null +++ b/Mage.Sets/src/mage/cards/f/FolioOfFancies.java @@ -0,0 +1,95 @@ +package mage.cards.f; + +import mage.abilities.Ability; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.costs.common.TapSourceCost; +import mage.abilities.costs.mana.ManaCostsImpl; +import mage.abilities.dynamicvalue.common.ManacostVariableValue; +import mage.abilities.effects.OneShotEffect; +import mage.abilities.effects.common.DrawCardAllEffect; +import mage.abilities.effects.common.continuous.MaximumHandSizeControllerEffect; +import mage.cards.Card; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.*; +import mage.game.Game; +import mage.players.Player; + +import java.util.Collection; +import java.util.Objects; +import java.util.Set; +import java.util.UUID; +import java.util.stream.Collectors; + +/** + * @author TheElk801 + */ +public final class FolioOfFancies extends CardImpl { + + public FolioOfFancies(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT}, "{1}{U}"); + + // Players have no maximum hand size. + this.addAbility(new SimpleStaticAbility(new MaximumHandSizeControllerEffect( + Integer.MAX_VALUE, Duration.WhileOnBattlefield, + MaximumHandSizeControllerEffect.HandSizeModification.SET, TargetController.ANY + ))); + + // {X}{X}, {T}: Each player draws X cards. + Ability ability = new SimpleActivatedAbility( + new DrawCardAllEffect(ManacostVariableValue.instance), new ManaCostsImpl("{X}{X}") + ); + ability.addCost(new TapSourceCost()); + this.addAbility(ability); + + // {2}{U}, {T}: Each opponent puts a number of cards equal to the number of cards in their hand from the top of their library into their graveyard. + ability = new SimpleActivatedAbility(new FolioOfFanciesEffect(), new ManaCostsImpl("{2}{U}")); + ability.addCost(new TapSourceCost()); + this.addAbility(ability); + } + + private FolioOfFancies(final FolioOfFancies card) { + super(card); + } + + @Override + public FolioOfFancies copy() { + return new FolioOfFancies(this); + } +} + +class FolioOfFanciesEffect extends OneShotEffect { + + FolioOfFanciesEffect() { + super(Outcome.Benefit); + staticText = "Each opponent puts a number of cards equal to the number of cards in their hand " + + "from the top of their library into their graveyard."; + } + + private FolioOfFanciesEffect(final FolioOfFanciesEffect effect) { + super(effect); + } + + @Override + public FolioOfFanciesEffect copy() { + return new FolioOfFanciesEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + Player controller = game.getPlayer(source.getControllerId()); + if (controller == null) { + return false; + } + Set cards = game.getOpponents(source.getControllerId()) + .stream() + .map(game::getPlayer) + .filter(Objects::nonNull) + .filter(player -> !player.getHand().isEmpty()) + .map(player -> player.getLibrary().getTopCards(game, player.getHand().size())) + .flatMap(Collection::stream) + .collect(Collectors.toSet()); + return controller.moveCards(cards, Zone.GRAVEYARD, source, game); + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 3bc91be1db..3cb1376808 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -76,6 +76,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Fierce Witchstalker", 154, Rarity.COMMON, mage.cards.f.FierceWitchstalker.class)); cards.add(new SetCardInfo("Fireborn Knight", 210, Rarity.UNCOMMON, mage.cards.f.FirebornKnight.class)); cards.add(new SetCardInfo("Flaxen Intruder", 155, Rarity.UNCOMMON, mage.cards.f.FlaxenIntruder.class)); + cards.add(new SetCardInfo("Folio of Fancies", 46, Rarity.RARE, mage.cards.f.FolioOfFancies.class)); cards.add(new SetCardInfo("Foulmire Knight", 90, Rarity.UNCOMMON, mage.cards.f.FoulmireKnight.class)); cards.add(new SetCardInfo("Frogify", 47, Rarity.UNCOMMON, mage.cards.f.Frogify.class)); cards.add(new SetCardInfo("Garenbrig Paladin", 157, Rarity.COMMON, mage.cards.g.GarenbrigPaladin.class)); From 909f35fb2f3aa0434f9eb5394eceec4871f93f29 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 13 Sep 2019 17:58:50 -0400 Subject: [PATCH 115/373] Implemented Loch Dragon --- Mage.Sets/src/mage/cards/l/LochDragon.java | 45 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + Utils/mtg-cards-data.txt | 1 + 3 files changed, 47 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/l/LochDragon.java diff --git a/Mage.Sets/src/mage/cards/l/LochDragon.java b/Mage.Sets/src/mage/cards/l/LochDragon.java new file mode 100644 index 0000000000..aedf384cff --- /dev/null +++ b/Mage.Sets/src/mage/cards/l/LochDragon.java @@ -0,0 +1,45 @@ +package mage.cards.l; + +import mage.MageInt; +import mage.abilities.common.EntersBattlefieldOrAttacksSourceTriggeredAbility; +import mage.abilities.costs.common.DiscardCardCost; +import mage.abilities.effects.common.DoIfCostPaid; +import mage.abilities.effects.common.DrawCardSourceControllerEffect; +import mage.abilities.keyword.FlyingAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class LochDragon extends CardImpl { + + public LochDragon(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{U/R}{U/R}{U/R}{U/R}"); + + this.subtype.add(SubType.DRAGON); + this.power = new MageInt(3); + this.toughness = new MageInt(2); + + // Flying + this.addAbility(FlyingAbility.getInstance()); + + // Whenever Loch Dragon enters the battlefield or attacks, you may discard a card. If you do, draw a card. + this.addAbility(new EntersBattlefieldOrAttacksSourceTriggeredAbility( + new DoIfCostPaid(new DrawCardSourceControllerEffect(1), new DiscardCardCost()) + )); + } + + private LochDragon(final LochDragon card) { + super(card); + } + + @Override + public LochDragon copy() { + return new LochDragon(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 3cb1376808..3b9d3d7b33 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -102,6 +102,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Knight of the Keep", 19, Rarity.COMMON, mage.cards.k.KnightOfTheKeep.class)); cards.add(new SetCardInfo("Knights' Charge", 328, Rarity.RARE, mage.cards.k.KnightsCharge.class)); cards.add(new SetCardInfo("Korvold, Fae-Cursed King", 329, Rarity.MYTHIC, mage.cards.k.KorvoldFaeCursedKing.class)); + cards.add(new SetCardInfo("Loch Dragon", 211, Rarity.UNCOMMON, mage.cards.l.LochDragon.class)); cards.add(new SetCardInfo("Lochmere Serpent", 195, Rarity.RARE, mage.cards.l.LochmereSerpent.class)); cards.add(new SetCardInfo("Lost Legion", 94, Rarity.COMMON, mage.cards.l.LostLegion.class)); cards.add(new SetCardInfo("Lovestruck Beast", 165, Rarity.RARE, mage.cards.l.LovestruckBeast.class)); diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index 9c56bae362..82c9c5008e 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -36138,6 +36138,7 @@ Arcanist's Owl|Throne of Eldraine|206|U|{W/U}{W/U}{W/U}{W/U}|Artifact Creature - Covetous Urge|Throne of Eldraine|207|U|{U/B}{U/B}{U/B}{U/B}|Sorcery|||Target opponent reveals their hand. You choose a nonland card from that player's graveyard or hand and exile it. You may cast that card for as long as it remains exiled, and you may spend mana as though it were mana of any color to cast that spell.| Elite Headhunter|Throne of Eldraine|209|U|{B/R}{B/R}{B/R}{B/R}|Creature - Human Knight|2|3|Menace${B/R}{B/R}{B/R}, Sacrifice another creature or an artifact: Elite Headhunter deals 2 damage to target creature or planeswalker.| Fireborn Knight|Throne of Eldraine|210|U|{R/W}{R/W}{R/W}{R/W}|Creature - Human Knight|2|3|Double strike${R/W}{R/W}{R/W}{R/W}: Fireborn Knight gets +1/+1 until end of turn.| +Loch Dragon|Throne of Eldraine|211|U|{U/R}{U/R}{U/R}{U/R}|Creature - Dragon|3|2|Flying$Whenever Loch Dragon enters the battlefield or attacks, you may discard a card. If you do, draw a card.| Bring Back|Throne of Eldraine|212|U|{G/W}{G/W}{G/W}{G/W}|Sorcery - Adventure|2|2|Create two 1/1 white Human creature tokens.| Oakhame Ranger|Throne of Eldraine|212|U|{G/W}{G/W}{G/W}{G/W}|Creature - Elf Knight|2|2|{T}: Creatures you control get +1/+1 until end of turn.| Thunderous Snapper|Throne of Eldraine|215|U|{G/U}{G/U}{G/U}{G/U}|Creature - Turtle Hydra|4|4|Whenever you cast a spell with converted mana cost 5 or greater, draw a card.| From 9af127d880c2f7df1e456d478debb6ef38e7964b Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 13 Sep 2019 18:01:16 -0400 Subject: [PATCH 116/373] updated ELD spoiler --- Mage.Sets/src/mage/cards/o/Outmuscle.java | 4 ++-- Utils/mtg-cards-data.txt | 11 ++++++++++- 2 files changed, 12 insertions(+), 3 deletions(-) diff --git a/Mage.Sets/src/mage/cards/o/Outmuscle.java b/Mage.Sets/src/mage/cards/o/Outmuscle.java index bc799bba81..02fc9bbbbf 100644 --- a/Mage.Sets/src/mage/cards/o/Outmuscle.java +++ b/Mage.Sets/src/mage/cards/o/Outmuscle.java @@ -39,7 +39,7 @@ public final class Outmuscle extends CardImpl { public Outmuscle(UUID ownerId, CardSetInfo setInfo) { super(ownerId, setInfo, new CardType[]{CardType.SORCERY}, "{3}{G}"); - // Put a +1/+1 counter on target creature you control, then it fights another target creature you don't control. + // Put a +1/+1 counter on target creature you control, then it fights target creature you don't control. // Adamant — If at least three green mana was spent to cast this spell, the creature you control gains indestructible until end of turn. this.getSpellAbility().addEffect(new OutmuscleEffect()); this.getSpellAbility().addTarget(new TargetControlledCreaturePermanent()); @@ -62,7 +62,7 @@ class OutmuscleEffect extends OneShotEffect { OutmuscleEffect() { super(Outcome.Benefit); staticText = "Put a +1/+1 counter on target creature you control, " + - "then it fights another target creature you don't control." + + "then it fights target creature you don't control." + "
Adamant — If at least three green mana was spent to cast this spell, " + "the creature you control gains indestructible until end of turn."; } diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index 82c9c5008e..e4d6e9f2ec 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -36028,6 +36028,7 @@ Into the Story|Throne of Eldraine|50|U|{5}{U}{U}|Instant|||This spell costs {3} The Magic Mirror|Throne of Eldraine|51|M|{6}{U}{U}{U}|Legendary Artifact|||This spell costs {1} less to cast for each instant and sorcery card in your graveyard.$You have no maximum hand size.$At the beginning of your upkeep, put a knowledge counter on The Magic Mirror, then draw a card for each knowledge counter on The Magic Mirror.| Midnight Clock|Throne of Eldraine|54|R|{2}{U}|Artifact|||{T}: Add {U}.${2}{U}: Put an hour counter on Midnight Clock.$At the beginning of each upkeep, put an hour counter on Midnight Clock.$When the twelfth hour counter is put on Midnight Clock, shuffle your hand and graveyard into your library, then draw seven cards. Exile Midnight Clock.| Mirrormade|Throne of Eldraine|55|R|{1}{U}{U}|Enchantment|||You may have Mirrormade enter the battlefield as a copy of any artifact or enchantment on the battlefield.| +Mistford River Turtle|Throne of Eldraine|56|C|{3}{U}|Creature - Turtle|1|5|Whenever Mistford River Turtle attacks, another target attacking non-Human creature can't be blocked this turn.| Mystical Dispute|Throne of Eldraine|58|U|{2}{U}|Instant|||This spell costs {2} less to cast if it targets a blue spell.$Counter target spell unless its controller pays {3}.| Opt|Throne of Eldraine|59|C|{U}|Instant|||Scry 1.$Draw a card.| Run Away Together|Throne of Eldraine|62|C|{1}{U}|Instant|||Choose two target creatures controlled by different players. Return those creatures to their owners' hands.| @@ -36057,12 +36058,15 @@ Order of Midnight|Throne of Eldraine|99|U|{1}{B}|Creature - Human Knight|2|2|Fly Piper of the Swarm|Throne of Eldraine|100|R|{1}{B}|Creature - Human Warlock|1|3|Rats you control have menace.${1}{B}, {T}: Create a 1/1 black Rat creature token.${2}{B}{B}, {T}, Sacrifice three Rats: Gain control of target creature.| Rankle, Master of Pranks|Throne of Eldraine|101|M|{2}{B}{B}|Legendary Creature - Faerie Rogue|3|3|Flying, haste$Whenever Rankle, Master of Pranks deals combat damage to a player, choose any number —$• Each player discards a card.$• Each player loses 1 life and draws a card.$• Each player sacrifices a creature.| Reave Soul|Throne of Eldraine|103|C|{1}{B}|Sorcery|||Destroy target creature with power 3 or less.| +Revenge of Ravens|Throne of Eldraine|104|U|{3}{B}|Enchantment|||Whenever a creature attacks you or a planeswalker you control, that creature's controller loses 1 life and you gain 1 life.| Curry Favor|Throne of Eldraine|105|C|{B}|Sorcery - Adventure|2|1|You gain X life and each opponent loses X life, where X is the number of Knights you control.| Smitten Swordmaster|Throne of Eldraine|105|C|{1}{B}|Creature - Human Knight|2|1|Lifelink| +Specter's Shriek|Throne of Eldraine|106|U|{B}|Sorcery|||Target opponent reveals their hand. You may choose a nonland card from it. If you do, that player exiles that card. If a nonblack card is exiled this way, exile a card from your hand.| Syr Konrad, the Grim|Throne of Eldraine|107|U|{3}{B}{B}|Legendary Creature - Human Knight|5|4|Whenever another creature dies, or a creature card is put into a graveyard from anywhere other than the battlefield, or a creature card leaves your graveyard, Syr Konrad, the Grim deals 1 damage to each opponent.${1}{B}: Each player puts the top card of their library into their graveyard.| Wicked Guardian|Throne of Eldraine|109|C|{3}{B}|Creature - Human Noble|4|2|When Wicked Guardian enters the battlefield, you may have it deal 2 damage to another creature you control. If you do, draw a card.| Wishclaw Talisman|Throne of Eldraine|110|R|{1}{B}|Artifact|||Wishclaw Talisman enters the battlefield with three wish counters on it.${1}, {T}, Remove a wish counter from Wishclaw Talisman: Search your library for a card, put it into your hand, then shuffle your library. An opponent gains control of Wishclaw Talisman. Activate this ability only during your turn.| Witch's Vengeance|Throne of Eldraine|111|R|{1}{B}{B}|Sorcery|||Creatures of the creature type of your choice get -3/-3 until end of turn.| +Barge In|Throne of Eldraine|112|C|{R}|Instant|||Target attacking creature gets +2/+2 until end of turn. Each attacking non-Human creature gains trample until end of turn.| Blow Your House Down|Throne of Eldraine|114|C|{2}{R}|Sorcery|||Up to three target creatures can't block this turn. Destroy any of them that are Walls.| Bonecrusher Giant|Throne of Eldraine|115|R|{2}{R}|Creature - Giant|4|3|Whenever Bonecrusher Giant becomes the target of a spell, Bonecrusher Giant deals 2 damage to that spell's controller.| Stomp|Throne of Eldraine|115|R|{1}{R}|Instant - Adventure|4|3|Damage can't be prevented this turn. Stomp deals 2 damage to any target.| @@ -36074,6 +36078,7 @@ Embercleave|Throne of Eldraine|120|M|{4}{R}{R}|Legendary Artifact - Equipment||| Embereth Paladin|Throne of Eldraine|121|C|{3}{R}|Creature - Human Knight|4|1|Haste$Adamant — If at least three red mana was spent to cast this spell, Embereth Paladin enters the battlefield with a +1/+1 counter on it.| Battle Display|Throne of Eldraine|122|U|{R}|Sorcery - Adventure|2|1|Destroy target artifact.| Embereth Shieldbreaker|Throne of Eldraine|122|U|{1}{R}|Creature - Human Knight|2|1|| +Ferocity of the Wilds|Throne of Eldraine|123|U|{2}{R}|Enchantment|||Attacking non-Human creatures you control get +1/+0 and have trample.| Fervent Champion|Throne of Eldraine|124|R|{R}|Creature - Human Knight|1|1|First strike, haste$Whenever Fervent Champion attacks, another target attacking Knight you control gets +1/+0 until end of turn.$Equip abilities you activate that target Fervent Champion cost {3} less to activate.| Irencrag Feat|Throne of Eldraine|127|R|{1}{R}{R}{R}|Sorcery|||Add seven {R}. You can cast only one more spell this turn.| Joust|Throne of Eldraine|129|U|{1}{R}|Sorcery|||Choose target creature you control and target creature you don't control. The creature you control gets +2/+1 until end of turn if it's a Knight. Then those creatures fight each other.| @@ -36082,6 +36087,8 @@ Merchant of the Vale|Throne of Eldraine|131|C|{2}{R}|Creature - Human Peasant|2| Ogre Errant|Throne of Eldraine|132|C|{3}{R}|Creature - Ogre Knight|3|4|Whenever Ogre Errant attacks, another target attacking Knight gains menace until end of turn.| Opportunistic Dragon|Throne of Eldraine|133|R|{2}{R}{R}|Creature - Dragon|4|3|Flying$When Opportunistic Dragon enters the battlefield, choose target Human or artifact an opponent controls. For as long as Opportunistic Dragon remains on the battlefield, gain control of that permanent, it loses all abilities, and it can't attack or block.| Raging Redcap|Throne of Eldraine|134|C|{2}{R}|Creature - Goblin Knight|1|2|Double strike| +Redcap Melee|Throne of Eldraine|135|U|{R}|Instant|||Redcap Melee deals 4 damage to target creature or planeswalker. If a nonred permanent is dealt damage this way, you sacrifice a land.| +Redcap Raiders|Throne of Eldraine|136|C|{2}{R}|Creature - Goblin Warrior|3|2|Whenever Redcap Raiders attacks, you may tap an untapped non-Human creature you control. If you do, Redcap Raiders gets +1/+1 and gains trample until end of turn.| Robber of the Rich|Throne of Eldraine|138|M|{1}{R}|Creature - Human Archer Rogue|2|2|Reach, haste$Whenever Robber of the Rich attacks, if defending player has more cards in hand than you, exile the top card of their library. During any turn you attacked with a Rogue, you may cast that card and you may spend mana as though it were mana of any color to cast that spell.| Scorching Dragonfire|Throne of Eldraine|139|C|{1}{R}|Instant|||Scorching Dragonfire deals 3 damage to target creature or planeswalker. If that creature or planeswalker would die this turn, exile it instead.| Searing Barrage|Throne of Eldraine|140|C|{4}{R}|Instant|||Searing Barrage deals 5 damage to target creature.$Adamant — If at least three red mana was spent to cast this spell, Searing Barrage deals 3 damage to that creature's controller.| @@ -36108,9 +36115,10 @@ Wolf's Quarry|Throne of Eldraine|164|C|{4}{G}{G}|Sorcery|||Create three 1/1 gree Heart's Desire|Throne of Eldraine|165|R|{G}|Sorcery - Adventure|5|5|Create a 1/1 white Human creature token.| Lovestruck Beast|Throne of Eldraine|165|R|{2}{G}|Creature - Beast Noble|5|5|Lovestruck Beast can't attack unless you control a 1/1 creature.| Maraleaf Rider|Throne of Eldraine|166|C|{1}{G}|Creature - Elf Knight|3|1|Sacrifice a Food: Target creature blocks Maraleaf Rider this turn if able.| +Oakhame Adversary|Throne of Eldraine|167|U|{3}{G}|Creature - Elf Warrior|2|3|This spell costs {2} less to cast if your opponent controls a green permanent.$Deathtouch$Whenever Oakhame Adversary deals combat damage to a player, draw a card.| Once and Future|Throne of Eldraine|168|U|{3}{G}|Instant|||Return target card from your graveyard to your hand. Put up to one other target card from your graveyard on top of your library. Exile Once and Future.$Adamant — If at least three green mana was spent to cast this spell, instead return those cards to your hand and exile Once and Future.| Once Upon a Time|Throne of Eldraine|169|R|{1}{G}|Instant|||If this spell is the first spell you've cast this game, you may cast it without paying its mana cost.$Look at the top five cards of your library. You may reveal a creature or land card from among them and put it into your hand. Put the rest on the bottom of your library in a random order.| -Outmuscle|Throne of Eldraine|170|C|{3}{G}|Sorcery|||Put a +1/+1 counter on target creature you control, then it fights another target creature you don't control.$Adamant — If at least three green mana was spent to cast this spell, the creature you control gains indestructible until end of turn.| +Outmuscle|Throne of Eldraine|170|C|{3}{G}|Sorcery|||Put a +1/+1 counter on target creature you control, then it fights target creature you don't control.$Adamant — If at least three green mana was spent to cast this spell, the creature you control gains indestructible until end of turn.| Questing Beast|Throne of Eldraine|171|M|{2}{G}{G}|Legendary Creature - Beast|4|4|Vigilance, deathtouch, haste$Questing Beast can't be blocked by creatures with power 2 or less.$Combat damage that would be dealt by creatures you control can't be prevented.$Whenever Questing Beast deals combat damage to an opponent, it deals that much damage to target planeswalker that player controls.| Return to Nature|Throne of Eldraine|173|C|{1}{G}|Instant|||Choose one —$• Destroy target artifact.$• Destroy target enchantment.$• Exile target card from a graveyard.| Rosethorn Acolyte|Throne of Eldraine|174|C|{2}{G}|Creature - Elf Druid|2|3|{T}: Add one mana of any color.| @@ -36123,6 +36131,7 @@ Dance of the Manse|Throne of Eldraine|186|R|{X}{W}{U}|Sorcery|||Return up to X t Doom Foretold|Throne of Eldraine|187|R|{2}{W}{B}|Enchantment|||At the beginning of each player's upkeep, that player sacrifices a nonland, nontoken permanent. If that player can't, they discard a card, they lose 2 life, you draw a card, you gain 2 life, you create a 2/2 white Knight creature token with vigilance, then you sacrifice Doom Foretold.| Faeburrow Elder|Throne of Eldraine|190|R|{1}{G}{W}|Creature - Treefolk Druid|0|0|Vigilance$Faeburrow Elder gets +1/+1 for each color among permanents you control.${T}: For each color among permanents you control, add one mana of that color.| Garruk, Cursed Huntsman|Throne of Eldraine|191|M|{4}{B}{G}|Legendary Planeswalker - Garruk|5|0: Create two 2/2 black and green Wolf creature tokens with "When this creature dies, put a loyalty counter on each Garruk you control."$−3: Destroy target creature. Draw a card.$−6: You get an emblem with "Creatures you control get +3/+3 and have trample."| +Grumgully, the Generous|Throne of Eldraine|192|U|{1}{R}{G}|Legendary Creature - Goblin Shaman|3|3|Each other non-Human creature you controls enters the battlefield with an additional +1/+1 counter on it.| Inspiring Veteran|Throne of Eldraine|194|U|{R}{W}|Creature - Human Knight|2|2|Other Knights you control get +1/+1.| Lochmere Serpent|Throne of Eldraine|195|R|{4}{U}{B}|Creature - Serpent|7|7|Flash${U}, Sacrifice an Island: Lochmere Serpent can't be blocked this turn.${B}, Sacrifice a Swamp: You gain 1 life and draw a card.${U}{B}: Exile five target cards from an opponent's graveyard. Return Lochmere Serpent from your graveyard to your hand. Activate this ability only any time you could cast a sorcery.| Maraleaf Pixie|Throne of Eldraine|196|U|{G}{U}|Creature - Faerie|2|2|Flying${T}: Add {G} or {U}.| From 946ed82f24b2ea60121667b80786e4e8624b4ede Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 13 Sep 2019 18:15:06 -0400 Subject: [PATCH 117/373] Implemented Redcap Melee --- Mage.Sets/src/mage/cards/r/RedcapMelee.java | 72 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 73 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/r/RedcapMelee.java diff --git a/Mage.Sets/src/mage/cards/r/RedcapMelee.java b/Mage.Sets/src/mage/cards/r/RedcapMelee.java new file mode 100644 index 0000000000..e0673a7be6 --- /dev/null +++ b/Mage.Sets/src/mage/cards/r/RedcapMelee.java @@ -0,0 +1,72 @@ +package mage.cards.r; + +import mage.abilities.Ability; +import mage.abilities.effects.Effect; +import mage.abilities.effects.OneShotEffect; +import mage.abilities.effects.common.SacrificeControllerEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Outcome; +import mage.filter.StaticFilters; +import mage.game.Game; +import mage.game.permanent.Permanent; +import mage.target.common.TargetCreatureOrPlaneswalker; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class RedcapMelee extends CardImpl { + + public RedcapMelee(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.INSTANT}, "{R}"); + + // Redcap Melee deals 4 damage to target creature or planeswalker. If a nonred permanent is dealt damage this way, you sacrifice a land. + this.getSpellAbility().addEffect(new RedcapMeleeEffect()); + this.getSpellAbility().addTarget(new TargetCreatureOrPlaneswalker()); + } + + private RedcapMelee(final RedcapMelee card) { + super(card); + } + + @Override + public RedcapMelee copy() { + return new RedcapMelee(this); + } +} + +class RedcapMeleeEffect extends OneShotEffect { + + private static final Effect effect = new SacrificeControllerEffect(StaticFilters.FILTER_LAND, 1, ""); + + RedcapMeleeEffect() { + super(Outcome.Benefit); + staticText = "{this} deals 4 damage to target creature or planeswalker. " + + "If a nonred permanent is dealt damage this way, you sacrifice a land."; + } + + private RedcapMeleeEffect(final RedcapMeleeEffect effect) { + super(effect); + } + + @Override + public RedcapMeleeEffect copy() { + return new RedcapMeleeEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + Permanent permanent = game.getPermanent(source.getFirstTarget()); + if (permanent == null) { + return false; + } + boolean isRed = permanent.getColor(game).isRed(); + if (permanent.damage(4, source.getSourceId(), game) > 0 && !isRed) { + return effect.apply(game, source); + } + return true; + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 3b9d3d7b33..c448e1eca8 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -130,6 +130,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Raging Redcap", 134, Rarity.COMMON, mage.cards.r.RagingRedcap.class)); cards.add(new SetCardInfo("Rankle, Master of Pranks", 101, Rarity.MYTHIC, mage.cards.r.RankleMasterOfPranks.class)); cards.add(new SetCardInfo("Reave Soul", 103, Rarity.COMMON, mage.cards.r.ReaveSoul.class)); + cards.add(new SetCardInfo("Redcap Melee", 135, Rarity.UNCOMMON, mage.cards.r.RedcapMelee.class)); cards.add(new SetCardInfo("Return to Nature", 173, Rarity.COMMON, mage.cards.r.ReturnToNature.class)); cards.add(new SetCardInfo("Righteousness", 27, Rarity.UNCOMMON, mage.cards.r.Righteousness.class)); cards.add(new SetCardInfo("Robber of the Rich", 138, Rarity.MYTHIC, mage.cards.r.RobberOfTheRich.class)); From 731eb8af39162e2d9a87d9a465a2b745e714101b Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 13 Sep 2019 19:22:15 -0400 Subject: [PATCH 118/373] Implemented Mistford River Turtle --- .../src/mage/cards/m/MistfordRiverTurtle.java | 58 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 59 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/m/MistfordRiverTurtle.java diff --git a/Mage.Sets/src/mage/cards/m/MistfordRiverTurtle.java b/Mage.Sets/src/mage/cards/m/MistfordRiverTurtle.java new file mode 100644 index 0000000000..3bfb928789 --- /dev/null +++ b/Mage.Sets/src/mage/cards/m/MistfordRiverTurtle.java @@ -0,0 +1,58 @@ +package mage.cards.m; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.AttacksTriggeredAbility; +import mage.abilities.effects.common.combat.CantBeBlockedTargetEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterCreaturePermanent; +import mage.filter.predicate.Predicates; +import mage.filter.predicate.mageobject.SubtypePredicate; +import mage.filter.predicate.permanent.AnotherPredicate; +import mage.filter.predicate.permanent.AttackingPredicate; +import mage.target.TargetPermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class MistfordRiverTurtle extends CardImpl { + + private static final FilterPermanent filter + = new FilterCreaturePermanent("another target attacking non-Human creature"); + + static { + filter.add(AnotherPredicate.instance); + filter.add(AttackingPredicate.instance); + filter.add(Predicates.not(new SubtypePredicate(SubType.HUMAN))); + } + + public MistfordRiverTurtle(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{3}{U}"); + + this.subtype.add(SubType.TURTLE); + this.power = new MageInt(1); + this.toughness = new MageInt(5); + + // Whenever Mistford River Turtle attacks, another target attacking non-Human creature can't be blocked this turn. + Ability ability = new AttacksTriggeredAbility(new CantBeBlockedTargetEffect(Duration.EndOfTurn) + .setText("another target attacking non-Human creature can't be blocked this turn"), false); + ability.addTarget(new TargetPermanent(filter)); + this.addAbility(ability); + } + + private MistfordRiverTurtle(final MistfordRiverTurtle card) { + super(card); + } + + @Override + public MistfordRiverTurtle copy() { + return new MistfordRiverTurtle(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index c448e1eca8..d433997f15 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -112,6 +112,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Merchant of the Vale", 131, Rarity.COMMON, mage.cards.m.MerchantOfTheVale.class)); cards.add(new SetCardInfo("Midnight Clock", 54, Rarity.RARE, mage.cards.m.MidnightClock.class)); cards.add(new SetCardInfo("Mirrormade", 55, Rarity.RARE, mage.cards.m.Mirrormade.class)); + cards.add(new SetCardInfo("Mistford River Turtle", 56, Rarity.COMMON, mage.cards.m.MistfordRiverTurtle.class)); cards.add(new SetCardInfo("Murderous Rider", 97, Rarity.RARE, mage.cards.m.MurderousRider.class)); cards.add(new SetCardInfo("Mystical Dispute", 58, Rarity.UNCOMMON, mage.cards.m.MysticalDispute.class)); cards.add(new SetCardInfo("Oakhame Ranger", 212, Rarity.UNCOMMON, mage.cards.o.OakhameRanger.class)); From 6dc25cd9968929ce442acdbf787ff2c465af2260 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 13 Sep 2019 19:40:32 -0400 Subject: [PATCH 119/373] Implemented Redcap Raiders --- Mage.Sets/src/mage/cards/r/RedcapRaiders.java | 62 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 63 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/r/RedcapRaiders.java diff --git a/Mage.Sets/src/mage/cards/r/RedcapRaiders.java b/Mage.Sets/src/mage/cards/r/RedcapRaiders.java new file mode 100644 index 0000000000..876af13159 --- /dev/null +++ b/Mage.Sets/src/mage/cards/r/RedcapRaiders.java @@ -0,0 +1,62 @@ +package mage.cards.r; + +import mage.MageInt; +import mage.abilities.common.AttacksTriggeredAbility; +import mage.abilities.costs.common.TapTargetCost; +import mage.abilities.effects.common.DoIfCostPaid; +import mage.abilities.effects.common.continuous.BoostSourceEffect; +import mage.abilities.effects.common.continuous.GainAbilitySourceEffect; +import mage.abilities.keyword.TrampleAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; +import mage.filter.common.FilterControlledCreaturePermanent; +import mage.filter.common.FilterControlledPermanent; +import mage.filter.predicate.Predicates; +import mage.filter.predicate.mageobject.SubtypePredicate; +import mage.filter.predicate.permanent.TappedPredicate; +import mage.target.common.TargetControlledPermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class RedcapRaiders extends CardImpl { + + private static final FilterControlledPermanent filter + = new FilterControlledCreaturePermanent("an untapped non-Human creature you control"); + + static { + filter.add(Predicates.not(TappedPredicate.instance)); + filter.add(Predicates.not(new SubtypePredicate(SubType.HUMAN))); + } + + public RedcapRaiders(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{2}{R}"); + + this.subtype.add(SubType.GOBLIN); + this.subtype.add(SubType.WARRIOR); + this.power = new MageInt(3); + this.toughness = new MageInt(2); + + // Whenever Redcap Raiders attacks, you may tap an untapped non-Human creature you control. If you do, Redcap Raiders gets +1/+1 and gains trample until end of turn. + this.addAbility(new AttacksTriggeredAbility(new DoIfCostPaid( + new BoostSourceEffect(1, 1, Duration.EndOfTurn).setText("{this} gets +1/+1"), + new TapTargetCost(new TargetControlledPermanent(filter)) + ).addEffect(new GainAbilitySourceEffect( + TrampleAbility.getInstance(), Duration.EndOfTurn + ).setText("and gains trample until end of turn")), false)); + } + + private RedcapRaiders(final RedcapRaiders card) { + super(card); + } + + @Override + public RedcapRaiders copy() { + return new RedcapRaiders(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index d433997f15..db29bcfa7c 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -132,6 +132,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Rankle, Master of Pranks", 101, Rarity.MYTHIC, mage.cards.r.RankleMasterOfPranks.class)); cards.add(new SetCardInfo("Reave Soul", 103, Rarity.COMMON, mage.cards.r.ReaveSoul.class)); cards.add(new SetCardInfo("Redcap Melee", 135, Rarity.UNCOMMON, mage.cards.r.RedcapMelee.class)); + cards.add(new SetCardInfo("Redcap Raiders", 136, Rarity.COMMON, mage.cards.r.RedcapRaiders.class)); cards.add(new SetCardInfo("Return to Nature", 173, Rarity.COMMON, mage.cards.r.ReturnToNature.class)); cards.add(new SetCardInfo("Righteousness", 27, Rarity.UNCOMMON, mage.cards.r.Righteousness.class)); cards.add(new SetCardInfo("Robber of the Rich", 138, Rarity.MYTHIC, mage.cards.r.RobberOfTheRich.class)); From 00c5a2c7b24b4d737de8359f863950dca7f9324b Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 13 Sep 2019 19:49:34 -0400 Subject: [PATCH 120/373] Implemented Ferocity of the Wilds --- .../src/mage/cards/f/FerocityOfTheWilds.java | 57 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 58 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/f/FerocityOfTheWilds.java diff --git a/Mage.Sets/src/mage/cards/f/FerocityOfTheWilds.java b/Mage.Sets/src/mage/cards/f/FerocityOfTheWilds.java new file mode 100644 index 0000000000..43da88093b --- /dev/null +++ b/Mage.Sets/src/mage/cards/f/FerocityOfTheWilds.java @@ -0,0 +1,57 @@ +package mage.cards.f; + +import mage.abilities.Ability; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.effects.common.continuous.BoostControlledEffect; +import mage.abilities.effects.common.continuous.GainAbilityAllEffect; +import mage.abilities.keyword.TrampleAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; +import mage.constants.TargetController; +import mage.filter.common.FilterCreaturePermanent; +import mage.filter.predicate.Predicates; +import mage.filter.predicate.mageobject.SubtypePredicate; +import mage.filter.predicate.permanent.AttackingPredicate; +import mage.filter.predicate.permanent.ControllerPredicate; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class FerocityOfTheWilds extends CardImpl { + + private static final FilterCreaturePermanent filter + = new FilterCreaturePermanent("attacking non-Human creatures"); + + static { + filter.add(AttackingPredicate.instance); + filter.add(new ControllerPredicate(TargetController.YOU)); + filter.add(Predicates.not(new SubtypePredicate(SubType.HUMAN))); + } + + public FerocityOfTheWilds(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ENCHANTMENT}, "{2}{R}"); + + // Attacking non-Human creatures you control get +1/+0 and have trample. + Ability ability = new SimpleStaticAbility( + new BoostControlledEffect(1, 0, Duration.WhileOnBattlefield, filter) + ); + ability.addEffect(new GainAbilityAllEffect( + TrampleAbility.getInstance(), Duration.WhileOnBattlefield, filter, "and have trample" + )); + this.addAbility(ability); + } + + private FerocityOfTheWilds(final FerocityOfTheWilds card) { + super(card); + } + + @Override + public FerocityOfTheWilds copy() { + return new FerocityOfTheWilds(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index db29bcfa7c..7fc6222c3f 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -72,6 +72,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Faerie Vandal", 45, Rarity.UNCOMMON, mage.cards.f.FaerieVandal.class)); cards.add(new SetCardInfo("Feasting Troll King", 152, Rarity.RARE, mage.cards.f.FeastingTrollKing.class)); cards.add(new SetCardInfo("Fell the Pheasant", 153, Rarity.COMMON, mage.cards.f.FellThePheasant.class)); + cards.add(new SetCardInfo("Ferocity of the Wilds", 123, Rarity.UNCOMMON, mage.cards.f.FerocityOfTheWilds.class)); cards.add(new SetCardInfo("Fervent Champion", 124, Rarity.RARE, mage.cards.f.FerventChampion.class)); cards.add(new SetCardInfo("Fierce Witchstalker", 154, Rarity.COMMON, mage.cards.f.FierceWitchstalker.class)); cards.add(new SetCardInfo("Fireborn Knight", 210, Rarity.UNCOMMON, mage.cards.f.FirebornKnight.class)); From 417a582365b8c43daaa2da155ed04c35d3c91113 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 13 Sep 2019 19:53:47 -0400 Subject: [PATCH 121/373] Implemented Barge In --- Mage.Sets/src/mage/cards/b/BargeIn.java | 52 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 53 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/b/BargeIn.java diff --git a/Mage.Sets/src/mage/cards/b/BargeIn.java b/Mage.Sets/src/mage/cards/b/BargeIn.java new file mode 100644 index 0000000000..6f3e297b92 --- /dev/null +++ b/Mage.Sets/src/mage/cards/b/BargeIn.java @@ -0,0 +1,52 @@ +package mage.cards.b; + +import mage.abilities.effects.common.continuous.BoostTargetEffect; +import mage.abilities.effects.common.continuous.GainAbilityAllEffect; +import mage.abilities.keyword.TrampleAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterCreaturePermanent; +import mage.filter.predicate.Predicates; +import mage.filter.predicate.mageobject.SubtypePredicate; +import mage.filter.predicate.permanent.AttackingPredicate; +import mage.target.common.TargetAttackingCreature; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class BargeIn extends CardImpl { + + private static final FilterPermanent filter + = new FilterCreaturePermanent("Each attacking non-Human creature"); + + static { + filter.add(AttackingPredicate.instance); + filter.add(Predicates.not(new SubtypePredicate(SubType.HUMAN))); + } + + public BargeIn(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.INSTANT}, "{R}"); + + // Target attacking creature gets +2/+2 until end of turn. Each attacking non-Human creature gains trample until end of turn. + this.getSpellAbility().addEffect(new BoostTargetEffect(2, 2, Duration.EndOfTurn)); + this.getSpellAbility().addEffect(new GainAbilityAllEffect( + TrampleAbility.getInstance(), Duration.EndOfTurn, filter + )); + this.getSpellAbility().addTarget(new TargetAttackingCreature()); + } + + private BargeIn(final BargeIn card) { + super(card); + } + + @Override + public BargeIn copy() { + return new BargeIn(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 7fc6222c3f..e41df85a7e 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -36,6 +36,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Ardenvale Tactician", 5, Rarity.COMMON, mage.cards.a.ArdenvaleTactician.class)); cards.add(new SetCardInfo("Bake into a Pie", 76, Rarity.COMMON, mage.cards.b.BakeIntoAPie.class)); cards.add(new SetCardInfo("Banish into Fable", 325, Rarity.RARE, mage.cards.b.BanishIntoFable.class)); + cards.add(new SetCardInfo("Barge In", 112, Rarity.COMMON, mage.cards.b.BargeIn.class)); cards.add(new SetCardInfo("Beanstalk Giant", 149, Rarity.UNCOMMON, mage.cards.b.BeanstalkGiant.class)); cards.add(new SetCardInfo("Belle of the Brawl", 78, Rarity.UNCOMMON, mage.cards.b.BelleOfTheBrawl.class)); cards.add(new SetCardInfo("Beloved Princess", 7, Rarity.COMMON, mage.cards.b.BelovedPrincess.class)); From c06a7b35a1260a18dd6e590e90a6490f48bf6f69 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 13 Sep 2019 20:06:49 -0400 Subject: [PATCH 122/373] Implemented Grumgully, the Generous --- .../mage/cards/g/GrumgullyTheGenerous.java | 86 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 87 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/g/GrumgullyTheGenerous.java diff --git a/Mage.Sets/src/mage/cards/g/GrumgullyTheGenerous.java b/Mage.Sets/src/mage/cards/g/GrumgullyTheGenerous.java new file mode 100644 index 0000000000..cd77305d73 --- /dev/null +++ b/Mage.Sets/src/mage/cards/g/GrumgullyTheGenerous.java @@ -0,0 +1,86 @@ +package mage.cards.g; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.effects.ReplacementEffectImpl; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.*; +import mage.counters.CounterType; +import mage.game.Game; +import mage.game.events.EntersTheBattlefieldEvent; +import mage.game.events.GameEvent; +import mage.game.permanent.Permanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class GrumgullyTheGenerous extends CardImpl { + + public GrumgullyTheGenerous(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{1}{R}{G}"); + + this.addSuperType(SuperType.LEGENDARY); + this.subtype.add(SubType.GOBLIN); + this.subtype.add(SubType.SHAMAN); + this.power = new MageInt(3); + this.toughness = new MageInt(3); + + // Each other non-Human creature you controls enters the battlefield with an additional +1/+1 counter on it. + this.addAbility(new SimpleStaticAbility(new GrumgullyTheGenerousReplacementEffect())); + } + + private GrumgullyTheGenerous(final GrumgullyTheGenerous card) { + super(card); + } + + @Override + public GrumgullyTheGenerous copy() { + return new GrumgullyTheGenerous(this); + } +} + +class GrumgullyTheGenerousReplacementEffect extends ReplacementEffectImpl { + + GrumgullyTheGenerousReplacementEffect() { + super(Duration.WhileOnBattlefield, Outcome.BoostCreature); + staticText = "Each other non-Human creature you controls " + + "enters the battlefield with an additional +1/+1 counter on it."; + } + + private GrumgullyTheGenerousReplacementEffect(final GrumgullyTheGenerousReplacementEffect effect) { + super(effect); + } + + @Override + public boolean checksEventType(GameEvent event, Game game) { + return event.getType() == GameEvent.EventType.ENTERS_THE_BATTLEFIELD; + } + + @Override + public boolean applies(GameEvent event, Ability source, Game game) { + Permanent creature = ((EntersTheBattlefieldEvent) event).getTarget(); + return creature != null + && creature.isCreature() + && !source.getSourceId().equals(creature.getId()) + && creature.isControlledBy(source.getControllerId()) + && !creature.hasSubtype(SubType.HUMAN, game); + } + + @Override + public boolean replaceEvent(GameEvent event, Ability source, Game game) { + Permanent creature = ((EntersTheBattlefieldEvent) event).getTarget(); + if (creature != null) { + creature.addCounters(CounterType.P1P1.createInstance(), source, game, event.getAppliedEffects()); + } + return false; + } + + @Override + public GrumgullyTheGenerousReplacementEffect copy() { + return new GrumgullyTheGenerousReplacementEffect(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index e41df85a7e..cf7eddde14 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -90,6 +90,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Glass Casket", 15, Rarity.UNCOMMON, mage.cards.g.GlassCasket.class)); cards.add(new SetCardInfo("Gluttonous Troll", 327, Rarity.RARE, mage.cards.g.GluttonousTroll.class)); cards.add(new SetCardInfo("Golden Egg", 220, Rarity.COMMON, mage.cards.g.GoldenEgg.class)); + cards.add(new SetCardInfo("Grumgully, the Generous", 192, Rarity.UNCOMMON, mage.cards.g.GrumgullyTheGenerous.class)); cards.add(new SetCardInfo("Harmonious Archon", 17, Rarity.MYTHIC, mage.cards.h.HarmoniousArchon.class)); cards.add(new SetCardInfo("Heraldic Banner", 222, Rarity.UNCOMMON, mage.cards.h.HeraldicBanner.class)); cards.add(new SetCardInfo("Hypnotic Sprite", 49, Rarity.UNCOMMON, mage.cards.h.HypnoticSprite.class)); From 537c48b20435d2603a380e642447a38e6d5f6c44 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 13 Sep 2019 20:13:49 -0400 Subject: [PATCH 123/373] Implemented Oakhame Adversary --- .../src/mage/cards/o/OakhameAdversary.java | 69 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 70 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/o/OakhameAdversary.java diff --git a/Mage.Sets/src/mage/cards/o/OakhameAdversary.java b/Mage.Sets/src/mage/cards/o/OakhameAdversary.java new file mode 100644 index 0000000000..e33931ff44 --- /dev/null +++ b/Mage.Sets/src/mage/cards/o/OakhameAdversary.java @@ -0,0 +1,69 @@ +package mage.cards.o; + +import mage.MageInt; +import mage.ObjectColor; +import mage.abilities.common.DealsCombatDamageToAPlayerTriggeredAbility; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.condition.Condition; +import mage.abilities.condition.common.PermanentsOnTheBattlefieldCondition; +import mage.abilities.effects.common.DrawCardSourceControllerEffect; +import mage.abilities.effects.common.cost.SpellCostReductionSourceEffect; +import mage.abilities.keyword.DeathtouchAbility; +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.FilterPermanent; +import mage.filter.predicate.mageobject.ColorPredicate; +import mage.filter.predicate.permanent.ControllerPredicate; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class OakhameAdversary extends CardImpl { + + private static final FilterPermanent filter + = new FilterPermanent("your opponent controls a green permanent"); + + static { + filter.add(new ControllerPredicate(TargetController.OPPONENT)); + filter.add(new ColorPredicate(ObjectColor.GREEN)); + } + + private static final Condition condition = new PermanentsOnTheBattlefieldCondition(filter); + + public OakhameAdversary(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{3}{G}"); + + this.subtype.add(SubType.ELF); + this.subtype.add(SubType.WARRIOR); + this.power = new MageInt(2); + this.toughness = new MageInt(3); + + // This spell costs {2} less to cast if your opponent controls a green permanent. + this.addAbility(new SimpleStaticAbility( + Zone.STACK, new SpellCostReductionSourceEffect(2, condition) + ).setRuleAtTheTop(true)); + + // Deathtouch + this.addAbility(DeathtouchAbility.getInstance()); + + // Whenever Oakhame Adversary deals combat damage to a player, draw a card. + this.addAbility(new DealsCombatDamageToAPlayerTriggeredAbility( + new DrawCardSourceControllerEffect(1), false + )); + } + + private OakhameAdversary(final OakhameAdversary card) { + super(card); + } + + @Override + public OakhameAdversary copy() { + return new OakhameAdversary(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index cf7eddde14..6d4c62e596 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -118,6 +118,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Mistford River Turtle", 56, Rarity.COMMON, mage.cards.m.MistfordRiverTurtle.class)); cards.add(new SetCardInfo("Murderous Rider", 97, Rarity.RARE, mage.cards.m.MurderousRider.class)); cards.add(new SetCardInfo("Mystical Dispute", 58, Rarity.UNCOMMON, mage.cards.m.MysticalDispute.class)); + cards.add(new SetCardInfo("Oakhame Adversary", 167, Rarity.UNCOMMON, mage.cards.o.OakhameAdversary.class)); cards.add(new SetCardInfo("Oakhame Ranger", 212, Rarity.UNCOMMON, mage.cards.o.OakhameRanger.class)); cards.add(new SetCardInfo("Ogre Errant", 132, Rarity.COMMON, mage.cards.o.OgreErrant.class)); cards.add(new SetCardInfo("Oko's Accomplices", 310, Rarity.COMMON, mage.cards.o.OkosAccomplices.class)); From 2c384b0d931ffad59528206760b8c9cc474b7b89 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 13 Sep 2019 23:20:28 -0400 Subject: [PATCH 124/373] Implemented Revenge of Ravens --- .../src/mage/cards/r/RevengeOfRavens.java | 41 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 42 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/r/RevengeOfRavens.java diff --git a/Mage.Sets/src/mage/cards/r/RevengeOfRavens.java b/Mage.Sets/src/mage/cards/r/RevengeOfRavens.java new file mode 100644 index 0000000000..e37f9a5ed6 --- /dev/null +++ b/Mage.Sets/src/mage/cards/r/RevengeOfRavens.java @@ -0,0 +1,41 @@ +package mage.cards.r; + +import mage.abilities.Ability; +import mage.abilities.common.AttacksAllTriggeredAbility; +import mage.abilities.effects.common.GainLifeEffect; +import mage.abilities.effects.common.LoseLifeTargetEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SetTargetPointer; +import mage.filter.StaticFilters; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class RevengeOfRavens extends CardImpl { + + public RevengeOfRavens(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ENCHANTMENT}, "{3}{B}"); + + // Whenever a creature attacks you or a planeswalker you control, that creature's controller loses 1 life and you gain 1 life. + Ability ability = new AttacksAllTriggeredAbility( + new LoseLifeTargetEffect(1).setText("that creature's controller loses 1 life"), + false, StaticFilters.FILTER_PERMANENT_CREATURE, + SetTargetPointer.PLAYER, true, true + ); + ability.addEffect(new GainLifeEffect(1).concatBy("and")); + this.addAbility(ability); + } + + private RevengeOfRavens(final RevengeOfRavens card) { + super(card); + } + + @Override + public RevengeOfRavens copy() { + return new RevengeOfRavens(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 6d4c62e596..ed28ee4a11 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -138,6 +138,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Redcap Melee", 135, Rarity.UNCOMMON, mage.cards.r.RedcapMelee.class)); cards.add(new SetCardInfo("Redcap Raiders", 136, Rarity.COMMON, mage.cards.r.RedcapRaiders.class)); cards.add(new SetCardInfo("Return to Nature", 173, Rarity.COMMON, mage.cards.r.ReturnToNature.class)); + cards.add(new SetCardInfo("Revenge of Ravens", 104, Rarity.UNCOMMON, mage.cards.r.RevengeOfRavens.class)); cards.add(new SetCardInfo("Righteousness", 27, Rarity.UNCOMMON, mage.cards.r.Righteousness.class)); cards.add(new SetCardInfo("Robber of the Rich", 138, Rarity.MYTHIC, mage.cards.r.RobberOfTheRich.class)); cards.add(new SetCardInfo("Rosethorn Acolyte", 174, Rarity.COMMON, mage.cards.r.RosethornAcolyte.class)); From 5579407144d3afb3d0cc56e71d7a80151e3cfd62 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 13 Sep 2019 23:46:50 -0400 Subject: [PATCH 125/373] Implemented Bonecrusher Giant --- .../src/mage/cards/b/BonecrusherGiant.java | 82 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + .../common/BecomesTargetTriggeredAbility.java | 31 ++++++- 3 files changed, 111 insertions(+), 3 deletions(-) create mode 100644 Mage.Sets/src/mage/cards/b/BonecrusherGiant.java diff --git a/Mage.Sets/src/mage/cards/b/BonecrusherGiant.java b/Mage.Sets/src/mage/cards/b/BonecrusherGiant.java new file mode 100644 index 0000000000..5d33e4e228 --- /dev/null +++ b/Mage.Sets/src/mage/cards/b/BonecrusherGiant.java @@ -0,0 +1,82 @@ +package mage.cards.b; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.BecomesTargetTriggeredAbility; +import mage.abilities.effects.ReplacementEffectImpl; +import mage.abilities.effects.common.DamageTargetEffect; +import mage.cards.AdventureCard; +import mage.cards.CardSetInfo; +import mage.constants.*; +import mage.filter.StaticFilters; +import mage.game.Game; +import mage.game.events.GameEvent; +import mage.target.common.TargetAnyTarget; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class BonecrusherGiant extends AdventureCard { + + public BonecrusherGiant(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, new CardType[]{CardType.INSTANT}, "{2}{R}", "Stomp", "{1}{R}"); + + this.subtype.add(SubType.GIANT); + this.power = new MageInt(4); + this.toughness = new MageInt(3); + + // Whenever Bonecrusher Giant becomes the target of a spell, Bonecrusher Giant deals 2 damage to that spell's controller. + this.addAbility(new BecomesTargetTriggeredAbility(new DamageTargetEffect( + 2, true, "that's spell's controller", "{this}" + ), StaticFilters.FILTER_SPELL_A, SetTargetPointer.PLAYER)); + + // Stomp + // Damage can’t be prevented this turn. Stomp deals 2 damage to any target. + this.getAdventureSpellAbility().addEffect(new StompEffect()); + this.getAdventureSpellAbility().addEffect(new DamageTargetEffect(2)); + this.getAdventureSpellAbility().addTarget(new TargetAnyTarget()); + } + + private BonecrusherGiant(final BonecrusherGiant card) { + super(card); + } + + @Override + public BonecrusherGiant copy() { + return new BonecrusherGiant(this); + } +} + +class StompEffect extends ReplacementEffectImpl { + + StompEffect() { + super(Duration.EndOfTurn, Outcome.Benefit); + staticText = "Damage can't be prevented this turn."; + } + + private StompEffect(final StompEffect effect) { + super(effect); + } + + @Override + public StompEffect copy() { + return new StompEffect(this); + } + + @Override + public boolean replaceEvent(GameEvent event, Ability source, Game game) { + return true; + } + + @Override + public boolean checksEventType(GameEvent event, Game game) { + return event.getType() == GameEvent.EventType.PREVENT_DAMAGE; + } + + @Override + public boolean applies(GameEvent event, Ability source, Game game) { + return true; + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index ed28ee4a11..2053f49f9c 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -42,6 +42,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Beloved Princess", 7, Rarity.COMMON, mage.cards.b.BelovedPrincess.class)); cards.add(new SetCardInfo("Blow Your House Down", 114, Rarity.COMMON, mage.cards.b.BlowYourHouseDown.class)); cards.add(new SetCardInfo("Bog Naughty", 80, Rarity.UNCOMMON, mage.cards.b.BogNaughty.class)); + cards.add(new SetCardInfo("Bonecrusher Giant", 115, Rarity.RARE, mage.cards.b.BonecrusherGiant.class)); cards.add(new SetCardInfo("Bramblefort Fink", 311, Rarity.UNCOMMON, mage.cards.b.BramblefortFink.class)); cards.add(new SetCardInfo("Brimstone Trebuchet", 116, Rarity.COMMON, mage.cards.b.BrimstoneTrebuchet.class)); cards.add(new SetCardInfo("Burning-Yard Trainer", 117, Rarity.UNCOMMON, mage.cards.b.BurningYardTrainer.class)); diff --git a/Mage/src/main/java/mage/abilities/common/BecomesTargetTriggeredAbility.java b/Mage/src/main/java/mage/abilities/common/BecomesTargetTriggeredAbility.java index 54263a11bc..1833985830 100644 --- a/Mage/src/main/java/mage/abilities/common/BecomesTargetTriggeredAbility.java +++ b/Mage/src/main/java/mage/abilities/common/BecomesTargetTriggeredAbility.java @@ -1,35 +1,42 @@ - package mage.abilities.common; import mage.abilities.TriggeredAbilityImpl; import mage.abilities.effects.Effect; +import mage.constants.SetTargetPointer; import mage.constants.Zone; import mage.filter.FilterStackObject; import mage.filter.StaticFilters; import mage.game.Game; import mage.game.events.GameEvent; import mage.game.stack.StackObject; +import mage.target.targetpointer.FixedTarget; /** - * * @author North */ public class BecomesTargetTriggeredAbility extends TriggeredAbilityImpl { private final FilterStackObject filter; + private final SetTargetPointer setTargetPointer; public BecomesTargetTriggeredAbility(Effect effect) { this(effect, StaticFilters.FILTER_SPELL_OR_ABILITY); } public BecomesTargetTriggeredAbility(Effect effect, FilterStackObject filter) { + this(effect, filter, SetTargetPointer.NONE); + } + + public BecomesTargetTriggeredAbility(Effect effect, FilterStackObject filter, SetTargetPointer setTargetPointer) { super(Zone.BATTLEFIELD, effect); this.filter = filter.copy(); + this.setTargetPointer = setTargetPointer; } public BecomesTargetTriggeredAbility(final BecomesTargetTriggeredAbility ability) { super(ability); this.filter = ability.filter.copy(); + this.setTargetPointer = ability.setTargetPointer; } @Override @@ -45,7 +52,25 @@ public class BecomesTargetTriggeredAbility extends TriggeredAbilityImpl { @Override public boolean checkTrigger(GameEvent event, Game game) { StackObject sourceObject = game.getStack().getStackObject(event.getSourceId()); - return event.getTargetId().equals(getSourceId()) && filter.match(sourceObject, getSourceId(), getControllerId(), game); + if (!event.getTargetId().equals(getSourceId()) + || !filter.match(sourceObject, getSourceId(), getControllerId(), game)) { + return false; + } + switch (setTargetPointer) { + case PLAYER: + this.getEffects().stream() + .forEach(effect -> effect.setTargetPointer( + new FixedTarget(sourceObject.getControllerId(), game) + )); + break; + case SPELL: + this.getEffects().stream() + .forEach(effect -> effect.setTargetPointer( + new FixedTarget(sourceObject.getId(), game) + )); + break; + } + return true; } @Override From 23c6bf5bd20219f66e94a7600402cbfbf831d7ed Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 14 Sep 2019 10:08:59 -0400 Subject: [PATCH 126/373] Implemented Irencrag Feat --- Mage.Sets/src/mage/cards/i/IrencragFeat.java | 97 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 98 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/i/IrencragFeat.java diff --git a/Mage.Sets/src/mage/cards/i/IrencragFeat.java b/Mage.Sets/src/mage/cards/i/IrencragFeat.java new file mode 100644 index 0000000000..8ff350b5ea --- /dev/null +++ b/Mage.Sets/src/mage/cards/i/IrencragFeat.java @@ -0,0 +1,97 @@ +package mage.cards.i; + +import mage.abilities.Ability; +import mage.abilities.effects.ContinuousRuleModifyingEffectImpl; +import mage.abilities.effects.OneShotEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.Outcome; +import mage.game.Game; +import mage.game.events.GameEvent; +import mage.watchers.common.CastSpellLastTurnWatcher; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class IrencragFeat extends CardImpl { + + public IrencragFeat(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.SORCERY}, "{1}{R}{R}{R}"); + + // Add seven {R}. You can cast only one more spell this turn. + this.getSpellAbility().addEffect(new IrencragFeatEffect()); + } + + private IrencragFeat(final IrencragFeat card) { + super(card); + } + + @Override + public IrencragFeat copy() { + return new IrencragFeat(this); + } +} + +class IrencragFeatEffect extends OneShotEffect { + + IrencragFeatEffect() { + super(Outcome.Benefit); + staticText = "Add seven {R}. You can cast only one more spell this turn."; + } + + private IrencragFeatEffect(final IrencragFeatEffect effect) { + super(effect); + } + + @Override + public IrencragFeatEffect copy() { + return new IrencragFeatEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + CastSpellLastTurnWatcher watcher = game.getState().getWatcher(CastSpellLastTurnWatcher.class); + if (watcher == null) { + return false; + } + int spellsCast = watcher.getAmountOfSpellsPlayerCastOnCurrentTurn(source.getControllerId()); + game.addEffect(new IrencragFeatCantCastEffect(spellsCast), source); + return true; + } +} + +class IrencragFeatCantCastEffect extends ContinuousRuleModifyingEffectImpl { + + private final int spellsCast; + + IrencragFeatCantCastEffect(int spellsCast) { + super(Duration.WhileOnBattlefield, Outcome.Detriment); + this.spellsCast = spellsCast; + } + + private IrencragFeatCantCastEffect(final IrencragFeatCantCastEffect effect) { + super(effect); + this.spellsCast = effect.spellsCast; + } + + @Override + public IrencragFeatCantCastEffect copy() { + return new IrencragFeatCantCastEffect(this); + } + + @Override + public boolean checksEventType(GameEvent event, Game game) { + return event.getType() == GameEvent.EventType.CAST_SPELL; + } + + @Override + public boolean applies(GameEvent event, Ability source, Game game) { + CastSpellLastTurnWatcher watcher = game.getState().getWatcher(CastSpellLastTurnWatcher.class); + return event.getPlayerId().equals(source.getControllerId()) + && watcher.getAmountOfSpellsPlayerCastOnCurrentTurn(event.getPlayerId()) > spellsCast + 1; + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 2053f49f9c..26abff6992 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -99,6 +99,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Insatiable Appetite", 162, Rarity.COMMON, mage.cards.i.InsatiableAppetite.class)); cards.add(new SetCardInfo("Inspiring Veteran", 194, Rarity.UNCOMMON, mage.cards.i.InspiringVeteran.class)); cards.add(new SetCardInfo("Into the Story", 50, Rarity.UNCOMMON, mage.cards.i.IntoTheStory.class)); + cards.add(new SetCardInfo("Irencrag Feat", 127, Rarity.RARE, mage.cards.i.IrencragFeat.class)); cards.add(new SetCardInfo("Joust", 129, Rarity.UNCOMMON, mage.cards.j.Joust.class)); cards.add(new SetCardInfo("Jousting Dummy", 224, Rarity.COMMON, mage.cards.j.JoustingDummy.class)); cards.add(new SetCardInfo("Keeper of Fables", 163, Rarity.UNCOMMON, mage.cards.k.KeeperOfFables.class)); From 82f1c1f000fb6b1fea816e599c07784634978865 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 14 Sep 2019 10:41:02 -0400 Subject: [PATCH 127/373] Implemented Danse Manatee --- .../src/mage/cards/d/DanceOfTheManse.java | 122 ++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 123 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/d/DanceOfTheManse.java diff --git a/Mage.Sets/src/mage/cards/d/DanceOfTheManse.java b/Mage.Sets/src/mage/cards/d/DanceOfTheManse.java new file mode 100644 index 0000000000..b46a38d00c --- /dev/null +++ b/Mage.Sets/src/mage/cards/d/DanceOfTheManse.java @@ -0,0 +1,122 @@ +package mage.cards.d; + +import mage.abilities.Ability; +import mage.abilities.effects.ContinuousEffect; +import mage.abilities.effects.OneShotEffect; +import mage.abilities.effects.common.continuous.AddCardTypeTargetEffect; +import mage.abilities.effects.common.continuous.SetPowerToughnessTargetEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.cards.Cards; +import mage.cards.CardsImpl; +import mage.constants.*; +import mage.filter.FilterCard; +import mage.filter.predicate.Predicates; +import mage.filter.predicate.mageobject.CardTypePredicate; +import mage.filter.predicate.mageobject.ConvertedManaCostPredicate; +import mage.filter.predicate.mageobject.SubtypePredicate; +import mage.game.Game; +import mage.players.Player; +import mage.target.Target; +import mage.target.common.TargetCardInYourGraveyard; +import mage.target.targetadjustment.TargetAdjuster; +import mage.target.targetpointer.FixedTarget; + +import java.util.Collection; +import java.util.Objects; +import java.util.UUID; +import java.util.stream.Collectors; + +/** + * @author TheElk801 + */ +public final class DanceOfTheManse extends CardImpl { + + public DanceOfTheManse(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.SORCERY}, "{X}{W}{U}"); + + // Return up to X target artifact and/or non-Aura enchantment cards each with converted mana cost X or less from your graveyard to the battlefield. If X is 6 or more, those permanents are 4/4 creatures in addition to their other types. + this.getSpellAbility().addEffect(new DanceOfTheManseEffect()); + this.getSpellAbility().setTargetAdjuster(DanceOfTheManseAdjuster.instance); + } + + private DanceOfTheManse(final DanceOfTheManse card) { + super(card); + } + + @Override + public DanceOfTheManse copy() { + return new DanceOfTheManse(this); + } +} + +enum DanceOfTheManseAdjuster implements TargetAdjuster { + instance; + + @Override + public void adjustTargets(Ability ability, Game game) { + int xValue = ability.getManaCostsToPay().getX(); + FilterCard filter = new FilterCard("artifact and/or non-Aura enchantment cards " + + "each with converted mana cost " + xValue + " or less from your graveyard"); + filter.add(Predicates.or( + new CardTypePredicate(CardType.ARTIFACT), + Predicates.and( + new CardTypePredicate(CardType.ENCHANTMENT), + Predicates.not(new SubtypePredicate(SubType.AURA)) + ) + )); + filter.add(new ConvertedManaCostPredicate(ComparisonType.FEWER_THAN, xValue + 1)); + ability.getTargets().clear(); + ability.addTarget(new TargetCardInYourGraveyard(0, xValue, filter)); + } +} + +class DanceOfTheManseEffect extends OneShotEffect { + + DanceOfTheManseEffect() { + super(Outcome.Benefit); + staticText = "Return up to X target artifact and/or non-Aura enchantment cards " + + "each with converted mana cost X or less from your graveyard to the battlefield. " + + "If X is 6 or more, those permanents are 4/4 creatures in addition to their other types."; + } + + private DanceOfTheManseEffect(final DanceOfTheManseEffect effect) { + super(effect); + } + + @Override + public DanceOfTheManseEffect copy() { + return new DanceOfTheManseEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + Player player = game.getPlayer(source.getControllerId()); + if (player == null) { + return false; + } + Cards cards = new CardsImpl(source + .getTargets() + .stream() + .map(Target::getTargets) + .flatMap(Collection::stream) + .map(game::getCard) + .collect(Collectors.toSet())); + player.moveCards(cards, Zone.BATTLEFIELD, source, game); + if (source.getManaCostsToPay().getX() < 6) { + return true; + } + cards.stream() + .map(game::getPermanent) + .filter(Objects::nonNull) + .forEach(permanent -> { + ContinuousEffect effect = new AddCardTypeTargetEffect(Duration.EndOfGame, CardType.CREATURE); + effect.setTargetPointer(new FixedTarget(permanent, game)); + game.addEffect(effect, source); + effect = new SetPowerToughnessTargetEffect(4, 4, Duration.EndOfGame); + effect.setTargetPointer(new FixedTarget(permanent, game)); + game.addEffect(effect, source); + }); + return true; + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 26abff6992..f5c09c4a0c 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -56,6 +56,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Corridor Monitor", 41, Rarity.COMMON, mage.cards.c.CorridorMonitor.class)); cards.add(new SetCardInfo("Crystal Slipper", 119, Rarity.COMMON, mage.cards.c.CrystalSlipper.class)); cards.add(new SetCardInfo("Curious Pair", 150, Rarity.COMMON, mage.cards.c.CuriousPair.class)); + cards.add(new SetCardInfo("Dance of the Manse", 186, Rarity.RARE, mage.cards.d.DanceOfTheManse.class)); cards.add(new SetCardInfo("Deafening Silence", 10, Rarity.UNCOMMON, mage.cards.d.DeafeningSilence.class)); cards.add(new SetCardInfo("Doom Foretold", 187, Rarity.RARE, mage.cards.d.DoomForetold.class)); cards.add(new SetCardInfo("Edgewall Innkeeper", 151, Rarity.UNCOMMON, mage.cards.e.EdgewallInnkeeper.class)); From 0799040a1f1aa06378e885f996c3d725cfafcfaa Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 14 Sep 2019 11:20:27 -0400 Subject: [PATCH 128/373] Implemented Specter's Shriek --- .../src/mage/cards/s/SpectersShriek.java | 94 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 95 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/s/SpectersShriek.java diff --git a/Mage.Sets/src/mage/cards/s/SpectersShriek.java b/Mage.Sets/src/mage/cards/s/SpectersShriek.java new file mode 100644 index 0000000000..0a5a41119e --- /dev/null +++ b/Mage.Sets/src/mage/cards/s/SpectersShriek.java @@ -0,0 +1,94 @@ +package mage.cards.s; + +import mage.abilities.Ability; +import mage.abilities.effects.OneShotEffect; +import mage.cards.Card; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Outcome; +import mage.constants.Zone; +import mage.filter.FilterCard; +import mage.filter.StaticFilters; +import mage.game.Game; +import mage.players.Player; +import mage.target.TargetCard; +import mage.target.common.TargetCardInHand; +import mage.target.common.TargetOpponent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class SpectersShriek extends CardImpl { + + public SpectersShriek(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.SORCERY}, "{B}"); + + // Target opponent reveals their hand. You may choose a nonland card from it. If you do, that player exiles that card. If a nonblack card is exiled this way, exile a card from your hand. + this.getSpellAbility().addEffect(new SpectersShriekEffect()); + this.getSpellAbility().addTarget(new TargetOpponent()); + } + + private SpectersShriek(final SpectersShriek card) { + super(card); + } + + @Override + public SpectersShriek copy() { + return new SpectersShriek(this); + } +} + +class SpectersShriekEffect extends OneShotEffect { + + private static final FilterCard filter = new FilterCard("card in your hand (to exile)"); + + SpectersShriekEffect() { + super(Outcome.Benefit); + staticText = "Target opponent reveals their hand. You may choose a nonland card from it. If you do, " + + "that player exiles that card. If a nonblack card is exiled this way, exile a card from your hand."; + } + + private SpectersShriekEffect(final SpectersShriekEffect effect) { + super(effect); + } + + @Override + public SpectersShriekEffect copy() { + return new SpectersShriekEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + Player controller = game.getPlayer(source.getControllerId()); + Player player = game.getPlayer(source.getFirstTarget()); + if (controller == null || player == null) { + return false; + } + player.revealCards(source, player.getHand(), game); + if (player.getHand().count(StaticFilters.FILTER_CARD_NON_LAND, game) == 0 + || !controller.chooseUse(outcome, "Exile a card from " + player.getName() + "'s hand?", source, game)) { + return true; + } + TargetCard target = new TargetCardInHand(StaticFilters.FILTER_CARD_NON_LAND); + target.setNotTarget(true); + if (!controller.choose(outcome, player.getHand(), target, game)) { + return false; + } + Card card = game.getCard(target.getFirstTarget()); + if (card == null) { + return false; + } + boolean isBlack = card.getColor(game).isBlack(); + player.moveCards(card, Zone.EXILED, source, game); + if (isBlack || controller.getHand().isEmpty()) { + return true; + } + target = new TargetCardInHand(filter); + target.setNotTarget(true); + return controller.choose(outcome, controller.getHand(), target, game) + && controller.moveCards(game.getCard(target.getFirstTarget()), Zone.EXILED, source, game); + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index f5c09c4a0c..6702cd00e5 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -162,6 +162,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Slaying Fire", 143, Rarity.UNCOMMON, mage.cards.s.SlayingFire.class)); cards.add(new SetCardInfo("Smitten Swordmaster", 105, Rarity.COMMON, mage.cards.s.SmittenSwordmaster.class)); cards.add(new SetCardInfo("Sorcerous Spyglass", 233, Rarity.RARE, mage.cards.s.SorcerousSpyglass.class)); + cards.add(new SetCardInfo("Specter's Shriek", 106, Rarity.UNCOMMON, mage.cards.s.SpectersShriek.class)); cards.add(new SetCardInfo("Spinning Wheel", 234, Rarity.UNCOMMON, mage.cards.s.SpinningWheel.class)); cards.add(new SetCardInfo("Steelbane Hydra", 322, Rarity.RARE, mage.cards.s.SteelbaneHydra.class)); cards.add(new SetCardInfo("Steelclaw Lance", 202, Rarity.UNCOMMON, mage.cards.s.SteelclawLance.class)); From 0dabd089847458923d8d41e2ab70c84723f8f738 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 14 Sep 2019 11:40:21 -0400 Subject: [PATCH 129/373] Implemented The Magic Mirror --- Mage.Sets/src/mage/cards/b/BedlamReveler.java | 3 +- .../src/mage/cards/t/TheMagicMirror.java | 62 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + .../main/java/mage/counters/CounterType.java | 1 + .../main/java/mage/filter/StaticFilters.java | 6 ++ 5 files changed, 72 insertions(+), 1 deletion(-) create mode 100644 Mage.Sets/src/mage/cards/t/TheMagicMirror.java diff --git a/Mage.Sets/src/mage/cards/b/BedlamReveler.java b/Mage.Sets/src/mage/cards/b/BedlamReveler.java index 6bd1228508..5eff9cbdb0 100644 --- a/Mage.Sets/src/mage/cards/b/BedlamReveler.java +++ b/Mage.Sets/src/mage/cards/b/BedlamReveler.java @@ -14,6 +14,7 @@ import mage.abilities.keyword.ProwessAbility; import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.*; +import mage.filter.StaticFilters; import mage.filter.common.FilterInstantOrSorceryCard; /** @@ -29,7 +30,7 @@ public final class BedlamReveler extends CardImpl { this.toughness = new MageInt(4); // Bedlam Reveler costs {1} less to cast for each instant or sorcery card in your graveyard. - Ability ability = new SimpleStaticAbility(Zone.ALL, new SourceCostReductionForEachCardInGraveyardEffect(new FilterInstantOrSorceryCard())); + Ability ability = new SimpleStaticAbility(Zone.ALL, new SourceCostReductionForEachCardInGraveyardEffect(StaticFilters.FILTER_CARD_INSTANT_AND_SORCERY)); ability.setRuleAtTheTop(true); this.addAbility(ability); diff --git a/Mage.Sets/src/mage/cards/t/TheMagicMirror.java b/Mage.Sets/src/mage/cards/t/TheMagicMirror.java new file mode 100644 index 0000000000..9090a80225 --- /dev/null +++ b/Mage.Sets/src/mage/cards/t/TheMagicMirror.java @@ -0,0 +1,62 @@ +package mage.cards.t; + +import mage.abilities.Ability; +import mage.abilities.common.BeginningOfUpkeepTriggeredAbility; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.dynamicvalue.DynamicValue; +import mage.abilities.dynamicvalue.common.CountersSourceCount; +import mage.abilities.effects.common.DrawCardSourceControllerEffect; +import mage.abilities.effects.common.continuous.MaximumHandSizeControllerEffect; +import mage.abilities.effects.common.cost.SourceCostReductionForEachCardInGraveyardEffect; +import mage.abilities.effects.common.counter.AddCountersSourceEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.*; +import mage.counters.CounterType; +import mage.filter.StaticFilters; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class TheMagicMirror extends CardImpl { + + private static final DynamicValue xValue = new CountersSourceCount(CounterType.KNOWLEDGE); + + public TheMagicMirror(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT}, "{6}{U}{U}{U}"); + + this.addSuperType(SuperType.LEGENDARY); + + // This spell costs {1} less to cast for each instant and sorcery card in your graveyard. + this.addAbility(new SimpleStaticAbility( + Zone.ALL, new SourceCostReductionForEachCardInGraveyardEffect( + StaticFilters.FILTER_CARD_INSTANT_AND_SORCERY + )).setRuleAtTheTop(true)); + + // You have no maximum hand size. + this.addAbility(new SimpleStaticAbility(new MaximumHandSizeControllerEffect( + Integer.MAX_VALUE, Duration.WhileOnBattlefield, + MaximumHandSizeControllerEffect.HandSizeModification.SET + ))); + + // At the beginning of your upkeep, put a knowledge counter on The Magic Mirror, then draw a card for each knowledge counter on The Magic Mirror. + Ability ability = new BeginningOfUpkeepTriggeredAbility( + new AddCountersSourceEffect(CounterType.KNOWLEDGE.createInstance()) + .setText("put a knowledge counter on {this},"), + TargetController.YOU, false + ); + ability.addEffect(new DrawCardSourceControllerEffect(xValue).concatBy("then")); + this.addAbility(ability); + } + + private TheMagicMirror(final TheMagicMirror card) { + super(card); + } + + @Override + public TheMagicMirror copy() { + return new TheMagicMirror(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 6702cd00e5..a5b0a894e2 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -173,6 +173,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Syr Konrad, the Grim", 107, Rarity.UNCOMMON, mage.cards.s.SyrKonradTheGrim.class)); cards.add(new SetCardInfo("Taste of Death", 320, Rarity.RARE, mage.cards.t.TasteOfDeath.class)); cards.add(new SetCardInfo("The Circle of Loyalty", 9, Rarity.MYTHIC, mage.cards.t.TheCircleOfLoyalty.class)); + cards.add(new SetCardInfo("The Magic Mirror", 51, Rarity.MYTHIC, mage.cards.t.TheMagicMirror.class)); cards.add(new SetCardInfo("The Royal Scions", 199, Rarity.MYTHIC, mage.cards.t.TheRoyalScions.class)); cards.add(new SetCardInfo("Thorn Mammoth", 323, Rarity.RARE, mage.cards.t.ThornMammoth.class)); cards.add(new SetCardInfo("Thornwood Falls", 313, Rarity.COMMON, mage.cards.t.ThornwoodFalls.class)); diff --git a/Mage/src/main/java/mage/counters/CounterType.java b/Mage/src/main/java/mage/counters/CounterType.java index 1478bd84c5..401631f780 100644 --- a/Mage/src/main/java/mage/counters/CounterType.java +++ b/Mage/src/main/java/mage/counters/CounterType.java @@ -67,6 +67,7 @@ public enum CounterType { INTERVENTION("intervention"), ISOLATION("isolation"), JAVELIN("javelin"), + KNOWLEDGE("knowledge"), KI("ki"), LANDMARK("landmark"), LEVEL("level"), diff --git a/Mage/src/main/java/mage/filter/StaticFilters.java b/Mage/src/main/java/mage/filter/StaticFilters.java index 27e4b7db7a..04807cef09 100644 --- a/Mage/src/main/java/mage/filter/StaticFilters.java +++ b/Mage/src/main/java/mage/filter/StaticFilters.java @@ -139,6 +139,12 @@ public final class StaticFilters { FILTER_CARD_INSTANT_OR_SORCERY.setLockedFilter(true); } + public static final FilterInstantOrSorceryCard FILTER_CARD_INSTANT_AND_SORCERY = new FilterInstantOrSorceryCard("instant and sorcery card"); + + static { + FILTER_CARD_INSTANT_AND_SORCERY.setLockedFilter(true); + } + public static final FilterPermanent FILTER_PERMANENT = new FilterPermanent(); static { From 3f270d9c2ec1c20d833a7e79a1fa8d81fb47767d Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 14 Sep 2019 12:21:07 -0400 Subject: [PATCH 130/373] updated ELD spoiler and reprints --- Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 2 +- Utils/mtg-cards-data.txt | 4 +++- 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index a5b0a894e2..c5b8c50819 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -200,7 +200,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Witch's Oven", 237, Rarity.UNCOMMON, mage.cards.w.WitchsOven.class)); cards.add(new SetCardInfo("Witch's Vengeance", 111, Rarity.RARE, mage.cards.w.WitchsVengeance.class)); cards.add(new SetCardInfo("Witching Well", 74, Rarity.COMMON, mage.cards.w.WitchingWell.class)); - cards.add(new SetCardInfo("Wolf's Quarry", 164, Rarity.COMMON, mage.cards.w.WolfsQuarry.class)); + cards.add(new SetCardInfo("Wolf's Quarry", 184, Rarity.COMMON, mage.cards.w.WolfsQuarry.class)); cards.add(new SetCardInfo("Workshop Elders", 318, Rarity.RARE, mage.cards.w.WorkshopElders.class)); cards.add(new SetCardInfo("Worthy Knight", 36, Rarity.RARE, mage.cards.w.WorthyKnight.class)); diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index e4d6e9f2ec..9fd6449d25 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -36095,6 +36095,7 @@ Searing Barrage|Throne of Eldraine|140|C|{4}{R}|Instant|||Searing Barrage deals Seven Dwarves|Throne of Eldraine|141|C|{1}{R}|Creature - Dwarf|2|2|Seven Dwarves gets +1/+1 for each other creature named Seven Dwarves you control.$A deck can have up to seven cards named Seven Dwarves.| Skullknocker Ogre|Throne of Eldraine|142|U|{3}{R}|Creature - Ogre|4|3|Whenever Skullknocker Ogre deals damage to an opponent, that player discards a card at random. If the player does, they draw a card.| Slaying Fire|Throne of Eldraine|143|U|{2}{R}|Instant|||Slaying Fire deals 3 damage to any target.$Adamant — If at least three red mana was spent to cast this spell, it deals 4 damage instead.| +Sundering Stroke|Throne of Eldraine|144|R|{6}{R}|Sorcery|||Sundering Stroke deals 7 damage divided as you choose amone one, two, or three targets. If at least seven red mana was spent to cast this spell, instead Sundering Stroke deals 7 damage to each of those permanents and/or players.| Syr Carah, the Bold|Throne of Eldraine|145|U|{3}{R}{R}|Legendary Creature - Human Knight|3|3|When Syr Carah, the Bold or an instant or sorcery spell you control deals damage to a player, exile the top card of your library. You may play that card this turn.${T}: Syr Carah deals 1 damage to any target.| Weaselback Redcap|Throne of Eldraine|148|C|{R}|Creature - Goblin Knight|1|1|{1}{R}: Weaselback Redcap gets +2/+0 until end of turn.| Beanstalk Giant|Throne of Eldraine|149|U|{6}{G}|Creature - Giant|*|*|Beanstalk Giant's power and toughness are each equal to the number of lands you control.| @@ -36111,7 +36112,6 @@ Garenbrig Paladin|Throne of Eldraine|157|C|{4}{G}|Creature - Giant Knight|4|4|Ad Gilded Goose|Throne of Eldraine|160|R|{G}|Creature - Bird|0|2|Flying$When Gilded Goose enters the battlefield, create a Food token.${1}{G}, {T}: Create a Food token.${T}, Sacrifice a Food: Add one mana of any color.| Insatiable Appetite|Throne of Eldraine|162|C|{1}{G}|Instant|||You may sacrifice a Food. If you do, target creature gets +5/+5 until end of turn. Otherwise, that creature gets +3/+3 until end of turn.| Keeper of Fables|Throne of Eldraine|163|U|{3}{G}{G}|Creature - Cat|4|5|Whenever one or more non-Human creatures you control deal combat damage to a player, draw a card.| -Wolf's Quarry|Throne of Eldraine|164|C|{4}{G}{G}|Sorcery|||Create three 1/1 green Boar creature tokens with "When this creature dies, create a Food token."| Heart's Desire|Throne of Eldraine|165|R|{G}|Sorcery - Adventure|5|5|Create a 1/1 white Human creature token.| Lovestruck Beast|Throne of Eldraine|165|R|{2}{G}|Creature - Beast Noble|5|5|Lovestruck Beast can't attack unless you control a 1/1 creature.| Maraleaf Rider|Throne of Eldraine|166|C|{1}{G}|Creature - Elf Knight|3|1|Sacrifice a Food: Target creature blocks Maraleaf Rider this turn if able.| @@ -36127,6 +36127,7 @@ Trail of Crumbs|Throne of Eldraine|179|U|{1}{G}|Enchantment|||When Trail of Crum Wicked Wolf|Throne of Eldraine|181|R|{2}{G}{G}|Creature - Wolf|3|3|When Wicked Wolf enters the battlefield, it fights up to one target creature you don't control.$Sacrifice a Food: Put a +1/+1 counter on Wicked Wolf. It gains indestructible until end of turn. Tap it.| Wildborn Preserver|Throne of Eldraine|182|R|{1}{G}|Creature - Elf Archer|2|2|Flash$Reach$Whenever another non-Human creature enters the battlefield under your control, you may pay {X}. When you do, put X +1/+1 counters on Wildborn Preserver.| Wildwood Tracker|Throne of Eldraine|183|C|{G}|Creature - Elf Warrior|1|1|Whenever Wildwood Tracker attacks or blocks, if you control another non-Human creature, Wildwood Tracker gets +1/+1 until end of turn.| +Wolf's Quarry|Throne of Eldraine|184|C|{4}{G}{G}|Sorcery|||Create three 1/1 green Boar creature tokens with "When this creature dies, create a Food token."| Dance of the Manse|Throne of Eldraine|186|R|{X}{W}{U}|Sorcery|||Return up to X target artifact and/or non-Aura enchantment cards each with converted mana cost X or less from your graveyard to the battlefield. If X is 6 or more, those permanents are 4/4 creatures in addition to their other types.| Doom Foretold|Throne of Eldraine|187|R|{2}{W}{B}|Enchantment|||At the beginning of each player's upkeep, that player sacrifices a nonland, nontoken permanent. If that player can't, they discard a card, they lose 2 life, you draw a card, you gain 2 life, you create a 2/2 white Knight creature token with vigilance, then you sacrifice Doom Foretold.| Faeburrow Elder|Throne of Eldraine|190|R|{1}{G}{W}|Creature - Treefolk Druid|0|0|Vigilance$Faeburrow Elder gets +1/+1 for each color among permanents you control.${T}: For each color among permanents you control, add one mana of that color.| @@ -36194,3 +36195,4 @@ Syr Gwyn, Hero of Ashvale|Throne of Eldraine|330|M|{3}{R}{W}{B}|Legendary Creatu Arcane Signet|Throne of Eldraine|331|C|{2}|Artifact|||{T}: Add one mana of any color in your commander's color identity.| Tome of Legends|Throne of Eldraine|332|R|{2}|Artifact|||Tome of Legends enters the battlefield with a page counter on it.$Whenever your commander enters the battlefield or attacks, put a page counter on Tome of Legends.${1}, {T}, Remove a page counter from Tome of Legends: Draw a card.| Command Tower|Throne of Eldraine|333|C||Land|||{T}: Add one mana of any color in your commander's color identity.| +Clockwork Servant|Throne of Eldraine|216|U|{3}|Artifact Creature - Gnome|2|3|Adamant - When Clockwork Servant enters the battlefield, if at least three mana of the same color was spent to cast it, draw a card.| \ No newline at end of file From 3867937b3841ad8803fb915c5bcf168e0349c157 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 14 Sep 2019 12:32:05 -0400 Subject: [PATCH 131/373] Implemented Clockwork Servant --- .../src/mage/cards/c/ClockworkServant.java | 59 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + .../condition/common/AdamantCondition.java | 6 +- 3 files changed, 62 insertions(+), 4 deletions(-) create mode 100644 Mage.Sets/src/mage/cards/c/ClockworkServant.java diff --git a/Mage.Sets/src/mage/cards/c/ClockworkServant.java b/Mage.Sets/src/mage/cards/c/ClockworkServant.java new file mode 100644 index 0000000000..7e9d949630 --- /dev/null +++ b/Mage.Sets/src/mage/cards/c/ClockworkServant.java @@ -0,0 +1,59 @@ +package mage.cards.c; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.condition.Condition; +import mage.abilities.condition.common.AdamantCondition; +import mage.abilities.decorator.ConditionalInterveningIfTriggeredAbility; +import mage.abilities.effects.common.DrawCardSourceControllerEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.game.Game; +import mage.watchers.common.ManaSpentToCastWatcher; + +import java.util.Arrays; +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class ClockworkServant extends CardImpl { + + public ClockworkServant(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT, CardType.CREATURE}, "{3}"); + + this.subtype.add(SubType.GNOME); + this.power = new MageInt(2); + this.toughness = new MageInt(3); + + // Adamant - When Clockwork Servant enters the battlefield, if at least three mana of the same color was spent to cast it, draw a card. + this.addAbility(new ConditionalInterveningIfTriggeredAbility( + new EntersBattlefieldTriggeredAbility(new DrawCardSourceControllerEffect(1)), + ClockworkServantCondition.instance, "
Adamant — When {this} enters the battlefield, " + + "if at least three mana of the same color was spent to cast it, draw a card." + ), new ManaSpentToCastWatcher()); + } + + private ClockworkServant(final ClockworkServant card) { + super(card); + } + + @Override + public ClockworkServant copy() { + return new ClockworkServant(this); + } +} + +enum ClockworkServantCondition implements Condition { + instance; + + @Override + public boolean apply(Game game, Ability source) { + return Arrays + .stream(AdamantCondition.values()) + .anyMatch(adamantCondition -> adamantCondition.apply(game, source)); + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index c5b8c50819..1276b76e94 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -52,6 +52,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Chulane, Teller of Tales", 326, Rarity.MYTHIC, mage.cards.c.ChulaneTellerOfTales.class)); cards.add(new SetCardInfo("Clackbridge Troll", 84, Rarity.RARE, mage.cards.c.ClackbridgeTroll.class)); cards.add(new SetCardInfo("Claim the Firstborn", 118, Rarity.UNCOMMON, mage.cards.c.ClaimTheFirstborn.class)); + cards.add(new SetCardInfo("Clockwork Servant", 216, Rarity.UNCOMMON, mage.cards.c.ClockworkServant.class)); cards.add(new SetCardInfo("Command Tower", 333, Rarity.COMMON, mage.cards.c.CommandTower.class)); cards.add(new SetCardInfo("Corridor Monitor", 41, Rarity.COMMON, mage.cards.c.CorridorMonitor.class)); cards.add(new SetCardInfo("Crystal Slipper", 119, Rarity.COMMON, mage.cards.c.CrystalSlipper.class)); diff --git a/Mage/src/main/java/mage/abilities/condition/common/AdamantCondition.java b/Mage/src/main/java/mage/abilities/condition/common/AdamantCondition.java index 63b511921e..ae6fb8f11f 100644 --- a/Mage/src/main/java/mage/abilities/condition/common/AdamantCondition.java +++ b/Mage/src/main/java/mage/abilities/condition/common/AdamantCondition.java @@ -11,8 +11,6 @@ import mage.watchers.common.ManaSpentToCastWatcher; /** * @author TheElk801 */ - - public enum AdamantCondition implements Condition { WHITE(ColoredManaSymbol.W), BLUE(ColoredManaSymbol.U), @@ -20,7 +18,7 @@ public enum AdamantCondition implements Condition { RED(ColoredManaSymbol.R), GREEN(ColoredManaSymbol.G); - protected ColoredManaSymbol coloredManaSymbol; + private final ColoredManaSymbol coloredManaSymbol; private AdamantCondition(ColoredManaSymbol coloredManaSymbol) { this.coloredManaSymbol = coloredManaSymbol; @@ -29,7 +27,7 @@ public enum AdamantCondition implements Condition { @Override public boolean apply(Game game, Ability source) { if (source.getAbilityType() == AbilityType.SPELL) { - return (source.getManaCostsToPay().getPayment().getColor(coloredManaSymbol) > 0); + return source.getManaCostsToPay().getPayment().getColor(coloredManaSymbol) > 2; } ManaSpentToCastWatcher watcher = game.getState().getWatcher(ManaSpentToCastWatcher.class, source.getSourceId()); if (watcher == null) { From 4e974b0d3c9c55504920fd31f28e6e35a45bfac9 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 14 Sep 2019 17:52:45 -0400 Subject: [PATCH 132/373] Implemented Vantress Gargoyle --- .../src/mage/cards/c/ChainedThroatseeker.java | 19 ++-- .../src/mage/cards/v/VantressGargoyle.java | 92 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 3 files changed, 100 insertions(+), 12 deletions(-) create mode 100644 Mage.Sets/src/mage/cards/v/VantressGargoyle.java diff --git a/Mage.Sets/src/mage/cards/c/ChainedThroatseeker.java b/Mage.Sets/src/mage/cards/c/ChainedThroatseeker.java index f9ac5ba327..ded5fb991e 100644 --- a/Mage.Sets/src/mage/cards/c/ChainedThroatseeker.java +++ b/Mage.Sets/src/mage/cards/c/ChainedThroatseeker.java @@ -10,7 +10,6 @@ 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.game.Game; import mage.game.permanent.Permanent; @@ -34,10 +33,10 @@ public final class ChainedThroatseeker extends CardImpl { this.addAbility(InfectAbility.getInstance()); // Chained Throatseeker can't attack unless defending player is poisoned. - this.addAbility(new SimpleStaticAbility(Zone.BATTLEFIELD, new ChainedThroatseekerCantAttackEffect())); + this.addAbility(new SimpleStaticAbility(new ChainedThroatseekerCantAttackEffect())); } - public ChainedThroatseeker(final ChainedThroatseeker card) { + private ChainedThroatseeker(final ChainedThroatseeker card) { super(card); } @@ -49,12 +48,12 @@ public final class ChainedThroatseeker extends CardImpl { class ChainedThroatseekerCantAttackEffect extends RestrictionEffect { - public ChainedThroatseekerCantAttackEffect() { + ChainedThroatseekerCantAttackEffect() { super(Duration.WhileOnBattlefield); staticText = "{this} can't attack unless defending player is poisoned"; } - public ChainedThroatseekerCantAttackEffect(final ChainedThroatseekerCantAttackEffect effect) { + private ChainedThroatseekerCantAttackEffect(final ChainedThroatseekerCantAttackEffect effect) { super(effect); } @@ -65,16 +64,12 @@ class ChainedThroatseekerCantAttackEffect extends RestrictionEffect { @Override public boolean canAttack(Permanent attacker, UUID defenderId, Ability source, Game game, boolean canUseChooseDialogs) { - Player targetPlayer = game.getPlayer(defenderId); - if (targetPlayer != null) { - return targetPlayer.getCounters().containsKey(CounterType.POISON); - } - return false; + Player targetPlayer = game.getPlayerOrPlaneswalkerController(defenderId); + return targetPlayer != null && targetPlayer.getCounters().containsKey(CounterType.POISON); } @Override public ChainedThroatseekerCantAttackEffect copy() { return new ChainedThroatseekerCantAttackEffect(this); } - -} \ No newline at end of file +} diff --git a/Mage.Sets/src/mage/cards/v/VantressGargoyle.java b/Mage.Sets/src/mage/cards/v/VantressGargoyle.java new file mode 100644 index 0000000000..09c5ac5add --- /dev/null +++ b/Mage.Sets/src/mage/cards/v/VantressGargoyle.java @@ -0,0 +1,92 @@ +package mage.cards.v; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.condition.Condition; +import mage.abilities.condition.common.CardsInHandCondition; +import mage.abilities.costs.common.TapSourceCost; +import mage.abilities.decorator.ConditionalContinuousEffect; +import mage.abilities.effects.RestrictionEffect; +import mage.abilities.effects.common.PutTopCardOfLibraryIntoGraveEachPlayerEffect; +import mage.abilities.effects.common.combat.CantBlockSourceEffect; +import mage.abilities.keyword.FlyingAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.*; +import mage.game.Game; +import mage.game.permanent.Permanent; +import mage.players.Player; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class VantressGargoyle extends CardImpl { + + private static final Condition condition = new CardsInHandCondition(ComparisonType.FEWER_THAN, 4); + + public VantressGargoyle(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT, CardType.CREATURE}, "{1}{U}"); + + this.subtype.add(SubType.GARGOYLE); + this.power = new MageInt(5); + this.toughness = new MageInt(4); + + // Flying + this.addAbility(FlyingAbility.getInstance()); + + // Vantress Gargoyle can't attack unless defending player has seven or more cards in their graveyard. + this.addAbility(new SimpleStaticAbility(new VantressGargoyleEffect())); + + // Vantress Gargoyle can't block unless you have four or more cards in hand. + this.addAbility(new SimpleStaticAbility(new ConditionalContinuousEffect( + new CantBlockSourceEffect(Duration.WhileOnBattlefield), condition, + "{this} can't block unless you have four or more cards in hand" + ))); + + // {T}: Each player puts the top card of their library into their graveyard. + this.addAbility(new SimpleActivatedAbility( + new PutTopCardOfLibraryIntoGraveEachPlayerEffect(1, TargetController.ANY), new TapSourceCost() + )); + } + + private VantressGargoyle(final VantressGargoyle card) { + super(card); + } + + @Override + public VantressGargoyle copy() { + return new VantressGargoyle(this); + } +} + +class VantressGargoyleEffect extends RestrictionEffect { + + VantressGargoyleEffect() { + super(Duration.WhileOnBattlefield); + staticText = "{this} can't attack unless defending player has seven or more cards in their graveyard"; + } + + private VantressGargoyleEffect(final VantressGargoyleEffect effect) { + super(effect); + } + + @Override + public boolean applies(Permanent permanent, Ability source, Game game) { + return permanent.getId().equals(source.getSourceId()); + } + + @Override + public boolean canAttack(Permanent attacker, UUID defenderId, Ability source, Game game, boolean canUseChooseDialogs) { + Player player = game.getPlayerOrPlaneswalkerController(defenderId); + return player != null && player.getGraveyard().size() > 6; + } + + @Override + public VantressGargoyleEffect copy() { + return new VantressGargoyleEffect(this); + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 1276b76e94..bb7105c5cc 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -186,6 +186,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Trapped in the Tower", 33, Rarity.COMMON, mage.cards.t.TrappedInTheTower.class)); cards.add(new SetCardInfo("True Love's Kiss", 34, Rarity.COMMON, mage.cards.t.TrueLovesKiss.class)); cards.add(new SetCardInfo("Turn into a Pumpkin", 69, Rarity.UNCOMMON, mage.cards.t.TurnIntoAPumpkin.class)); + cards.add(new SetCardInfo("Vantress Gargoyle", 71, Rarity.RARE, mage.cards.v.VantressGargoyle.class)); cards.add(new SetCardInfo("Venerable Knight", 35, Rarity.UNCOMMON, mage.cards.v.VenerableKnight.class)); cards.add(new SetCardInfo("Wandermare", 204, Rarity.UNCOMMON, mage.cards.w.Wandermare.class)); cards.add(new SetCardInfo("Weaselback Redcap", 148, Rarity.COMMON, mage.cards.w.WeaselbackRedcap.class)); From 3491b36ae8116dc44316ca44ed00381368583969 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 14 Sep 2019 18:30:51 -0400 Subject: [PATCH 133/373] Implemented Oathsworn Knight --- .../src/mage/cards/o/OathswornKnight.java | 50 +++++++++++++++++++ .../src/mage/cards/u/UginsConjurant.java | 2 +- Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + .../PreventDamageAndRemoveCountersEffect.java | 30 ++++++----- 4 files changed, 70 insertions(+), 13 deletions(-) create mode 100644 Mage.Sets/src/mage/cards/o/OathswornKnight.java diff --git a/Mage.Sets/src/mage/cards/o/OathswornKnight.java b/Mage.Sets/src/mage/cards/o/OathswornKnight.java new file mode 100644 index 0000000000..70e3164371 --- /dev/null +++ b/Mage.Sets/src/mage/cards/o/OathswornKnight.java @@ -0,0 +1,50 @@ +package mage.cards.o; + +import mage.MageInt; +import mage.abilities.common.AttacksEachCombatStaticAbility; +import mage.abilities.common.EntersBattlefieldAbility; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.effects.PreventDamageAndRemoveCountersEffect; +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.counters.CounterType; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class OathswornKnight extends CardImpl { + + public OathswornKnight(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{1}{B}{B}"); + + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.KNIGHT); + this.power = new MageInt(0); + this.toughness = new MageInt(0); + + // Oathsworn Knight enters the battlefield with four +1/+1 counters on it. + this.addAbility(new EntersBattlefieldAbility(new AddCountersSourceEffect( + CounterType.P1P1.createInstance(4) + ), "with four +1/+1 counters on it")); + + // Oathsworn Knight attacks each combat if able. + this.addAbility(new AttacksEachCombatStaticAbility()); + + // If damage would be dealt to Oathsworn Knight while it has a +1/+1 counter on it, prevent that damage and remove a +1/+1 counter from it. + this.addAbility(new SimpleStaticAbility(new PreventDamageAndRemoveCountersEffect(false))); + } + + private OathswornKnight(final OathswornKnight card) { + super(card); + } + + @Override + public OathswornKnight copy() { + return new OathswornKnight(this); + } +} diff --git a/Mage.Sets/src/mage/cards/u/UginsConjurant.java b/Mage.Sets/src/mage/cards/u/UginsConjurant.java index a633fbff27..cf2582e131 100644 --- a/Mage.Sets/src/mage/cards/u/UginsConjurant.java +++ b/Mage.Sets/src/mage/cards/u/UginsConjurant.java @@ -31,7 +31,7 @@ public final class UginsConjurant extends CardImpl { // Ugin’s Conjurant enters the battlefield with X +1/+1 counters on it. this.addAbility(new EntersBattlefieldAbility(new EntersBattlefieldWithXCountersEffect(CounterType.P1P1.createInstance()))); // If damage would be dealt to Ugin’s Conjurant while it has a +1/+1 counter on it, prevent that damage and remove that many +1/+1 counters from Ugin’s Conjurant. - this.addAbility(new SimpleStaticAbility(Zone.BATTLEFIELD, new PreventDamageAndRemoveCountersEffect())); + this.addAbility(new SimpleStaticAbility(Zone.BATTLEFIELD, new PreventDamageAndRemoveCountersEffect(true))); } private UginsConjurant(final UginsConjurant card) { diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index bb7105c5cc..222d60f52a 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -124,6 +124,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Mystical Dispute", 58, Rarity.UNCOMMON, mage.cards.m.MysticalDispute.class)); cards.add(new SetCardInfo("Oakhame Adversary", 167, Rarity.UNCOMMON, mage.cards.o.OakhameAdversary.class)); cards.add(new SetCardInfo("Oakhame Ranger", 212, Rarity.UNCOMMON, mage.cards.o.OakhameRanger.class)); + cards.add(new SetCardInfo("Oathsworn Knight", 98, Rarity.RARE, mage.cards.o.OathswornKnight.class)); cards.add(new SetCardInfo("Ogre Errant", 132, Rarity.COMMON, mage.cards.o.OgreErrant.class)); cards.add(new SetCardInfo("Oko's Accomplices", 310, Rarity.COMMON, mage.cards.o.OkosAccomplices.class)); cards.add(new SetCardInfo("Oko's Hospitality", 312, Rarity.RARE, mage.cards.o.OkosHospitality.class)); diff --git a/Mage/src/main/java/mage/abilities/effects/PreventDamageAndRemoveCountersEffect.java b/Mage/src/main/java/mage/abilities/effects/PreventDamageAndRemoveCountersEffect.java index 81c1e19e28..813f1ad790 100644 --- a/Mage/src/main/java/mage/abilities/effects/PreventDamageAndRemoveCountersEffect.java +++ b/Mage/src/main/java/mage/abilities/effects/PreventDamageAndRemoveCountersEffect.java @@ -13,18 +13,21 @@ import mage.game.events.GameEvent; import mage.game.permanent.Permanent; /** - * * @author antoni-g */ public class PreventDamageAndRemoveCountersEffect extends PreventionEffectImpl { + private final boolean thatMany; - public PreventDamageAndRemoveCountersEffect() { + public PreventDamageAndRemoveCountersEffect(boolean thatMany) { super(Duration.WhileOnBattlefield, Integer.MAX_VALUE, false, false); - staticText = "If damage would be dealt to {this}, prevent that damage and remove that many +1/+1 counters from it"; + this.thatMany = thatMany; + staticText = "If damage would be dealt to {this} while it has a +1/+1 counter on it, " + + "prevent that damage and remove " + (thatMany ? "that many +1/+1 counters" : "a +1/+1 counter") + " from it"; } - public PreventDamageAndRemoveCountersEffect(final PreventDamageAndRemoveCountersEffect effect) { + private PreventDamageAndRemoveCountersEffect(final PreventDamageAndRemoveCountersEffect effect) { super(effect); + this.thatMany = effect.thatMany; } @Override @@ -42,19 +45,22 @@ public class PreventDamageAndRemoveCountersEffect extends PreventionEffectImpl { int damage = event.getAmount(); preventDamageAction(event, source, game); Permanent permanent = game.getPermanent(source.getSourceId()); - if (permanent != null) { - permanent.removeCounters(CounterType.P1P1.createInstance(damage), game); //MTG ruling (this) loses counters even if the damage isn't prevented + if (permanent == null) { + return false; } + if (!thatMany) { + damage = 1; + } + permanent.removeCounters(CounterType.P1P1.createInstance(damage), game); //MTG ruling (this) loses counters even if the damage isn't prevented return false; } @Override public boolean applies(GameEvent event, Ability source, Game game) { - if (super.applies(event, source, game)) { - if (event.getTargetId().equals(source.getSourceId())) { - return true; - } - } - return false; + Permanent permanent = game.getPermanent(event.getTargetId()); + return super.applies(event, source, game) + && permanent != null + && event.getTargetId().equals(source.getSourceId()) + && permanent.getCounters(game).containsKey(CounterType.P1P1); } } From a03e5f11fb137f9af38d124c657f6b1c3d17e0dc Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 14 Sep 2019 19:07:41 -0400 Subject: [PATCH 134/373] Implemented Seven Dwarves --- .../src/mage/deck/AusHighlander.java | 9 +-- .../src/mage/deck/Brawl.java | 9 +-- .../src/mage/deck/CanadianHighlander.java | 9 +-- .../src/mage/deck/Commander.java | 9 +-- .../src/mage/deck/FreeformCommander.java | 9 +-- .../src/mage/deck/Oathbreaker.java | 9 +-- .../src/mage/deck/TinyLeaders.java | 9 +-- .../src/mage/deck/Limited.java | 13 +++- Mage.Sets/src/mage/cards/s/SevenDwarves.java | 64 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + .../java/mage/cards/decks/Constructed.java | 31 ++++++--- 11 files changed, 104 insertions(+), 68 deletions(-) create mode 100644 Mage.Sets/src/mage/cards/s/SevenDwarves.java diff --git a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/AusHighlander.java b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/AusHighlander.java index 574bfec565..d59a9fa4ef 100644 --- a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/AusHighlander.java +++ b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/AusHighlander.java @@ -133,14 +133,7 @@ public class AusHighlander extends Constructed { Map counts = new HashMap<>(); countCards(counts, deck.getCards()); countCards(counts, deck.getSideboard()); - for (Map.Entry entry : counts.entrySet()) { - if (entry.getValue() > 1) { - if (!basicLandNames.contains(entry.getKey()) && !anyNumberCardsAllowed.contains(entry.getKey())) { - invalid.put(entry.getKey(), "Too many: " + entry.getValue()); - valid = false; - } - } - } + valid = checkCounts(1, counts) && valid; int totalPoints = 0; for (Map.Entry entry : counts.entrySet()) { diff --git a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Brawl.java b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Brawl.java index 8b1feca862..fdf8ace073 100644 --- a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Brawl.java +++ b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Brawl.java @@ -49,14 +49,7 @@ public class Brawl extends Constructed { Map counts = new HashMap<>(); countCards(counts, deck.getCards()); countCards(counts, deck.getSideboard()); - for (Map.Entry entry : counts.entrySet()) { - if (entry.getValue() > 1) { - if (!basicLandNames.contains(entry.getKey()) && !anyNumberCardsAllowed.contains(entry.getKey())) { - invalid.put(entry.getKey(), "Too many: " + entry.getValue()); - valid = false; - } - } - } + valid = checkCounts(1, counts) && valid; for (String bannedCard : banned) { if (counts.containsKey(bannedCard)) { diff --git a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CanadianHighlander.java b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CanadianHighlander.java index 527cbbead6..7af1dc83a9 100644 --- a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CanadianHighlander.java +++ b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CanadianHighlander.java @@ -88,14 +88,7 @@ public class CanadianHighlander extends Constructed { Map counts = new HashMap<>(); countCards(counts, deck.getCards()); countCards(counts, deck.getSideboard()); - for (Map.Entry entry : counts.entrySet()) { - if (entry.getValue() > 1) { - if (!basicLandNames.contains(entry.getKey()) && !anyNumberCardsAllowed.contains(entry.getKey())) { - invalid.put(entry.getKey(), "Too many: " + entry.getValue()); - valid = false; - } - } - } + valid = checkCounts(1, counts) && valid; int allowedPoints = 10; int totalPoints = 0; diff --git a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Commander.java b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Commander.java index d9fcf98cd2..431aa35cbf 100644 --- a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Commander.java +++ b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Commander.java @@ -99,14 +99,7 @@ public class Commander extends Constructed { Map counts = new HashMap<>(); countCards(counts, deck.getCards()); countCards(counts, deck.getSideboard()); - for (Map.Entry entry : counts.entrySet()) { - if (entry.getValue() > 1) { - if (!basicLandNames.contains(entry.getKey()) && !anyNumberCardsAllowed.contains(entry.getKey())) { - invalid.put(entry.getKey(), "Too many: " + entry.getValue()); - valid = false; - } - } - } + valid = checkCounts(1, counts) && valid; for (String bannedCard : banned) { if (counts.containsKey(bannedCard)) { diff --git a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/FreeformCommander.java b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/FreeformCommander.java index fc6da30d75..8a1a41c631 100644 --- a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/FreeformCommander.java +++ b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/FreeformCommander.java @@ -59,14 +59,7 @@ public class FreeformCommander extends Constructed { countCards(counts, deck.getCards()); countCards(counts, deck.getSideboard()); - for (Map.Entry entry : counts.entrySet()) { - if (entry.getValue() > 1) { - if (!basicLandNames.contains(entry.getKey()) && !anyNumberCardsAllowed.contains(entry.getKey())) { - invalid.put(entry.getKey(), "Too many: " + entry.getValue()); - valid = false; - } - } - } + valid = checkCounts(1, counts) && valid; if (deck.getSideboard().isEmpty() || deck.getSideboard().size() > 2) { invalid.put("Commander", "Sideboard must contain only the commander(s)"); diff --git a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Oathbreaker.java b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Oathbreaker.java index 28231f41e7..5ca36ba216 100644 --- a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Oathbreaker.java +++ b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Oathbreaker.java @@ -99,14 +99,7 @@ public class Oathbreaker extends Vintage { } } - for (Map.Entry entry : counts.entrySet()) { - if (entry.getValue() > 1) { - if (!basicLandNames.contains(entry.getKey()) && !anyNumberCardsAllowed.contains(entry.getKey())) { - invalid.put(entry.getKey(), "Too many: " + entry.getValue()); - valid = false; - } - } - } + valid = checkCounts(1, counts) && valid; Set commanderNames = new HashSet<>(); Set signatureSpells = new HashSet<>(); diff --git a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/TinyLeaders.java b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/TinyLeaders.java index a93db2a326..e136d33205 100644 --- a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/TinyLeaders.java +++ b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/TinyLeaders.java @@ -113,14 +113,7 @@ public class TinyLeaders extends Constructed { counts.put(deck.getName(), 1); // add the commander to the counts, so it can't be in the deck or sideboard again countCards(counts, deck.getCards()); countCards(counts, deck.getSideboard()); - for (Map.Entry entry : counts.entrySet()) { - if (entry.getValue() > 1) { - if (!basicLandNames.contains(entry.getKey()) && !anyNumberCardsAllowed.contains(entry.getKey())) { - invalid.put(entry.getKey(), "Too many: " + entry.getValue()); - valid = false; - } - } - } + valid = checkCounts(1, counts) && valid; for (String bannedCard : banned) { if (counts.containsKey(bannedCard)) { diff --git a/Mage.Server.Plugins/Mage.Deck.Limited/src/mage/deck/Limited.java b/Mage.Server.Plugins/Mage.Deck.Limited/src/mage/deck/Limited.java index 30d32964e0..542f045045 100644 --- a/Mage.Server.Plugins/Mage.Deck.Limited/src/mage/deck/Limited.java +++ b/Mage.Server.Plugins/Mage.Deck.Limited/src/mage/deck/Limited.java @@ -3,6 +3,9 @@ package mage.deck; import mage.cards.decks.Deck; import mage.cards.decks.DeckValidator; +import java.util.HashMap; +import java.util.Map; + /** * @author BetaSteward_at_googlemail.com */ @@ -29,9 +32,15 @@ public class Limited extends DeckValidator { if (deck.getCards().size() < getDeckMinSize()) { invalid.put("Deck", "Must contain at least " + getDeckMinSize() + " cards: has only " + deck.getCards().size() + " cards"); valid = false; - + } + Map counts = new HashMap<>(); + countCards(counts, deck.getCards()); + for (Map.Entry entry : counts.entrySet()) { + if (entry.getValue() > 7 && entry.getKey().equals("Seven Dwarves")) { + invalid.put(entry.getKey(), "Too many: " + entry.getValue()); + valid = false; + } } return valid; } - } diff --git a/Mage.Sets/src/mage/cards/s/SevenDwarves.java b/Mage.Sets/src/mage/cards/s/SevenDwarves.java new file mode 100644 index 0000000000..03a6b1caa1 --- /dev/null +++ b/Mage.Sets/src/mage/cards/s/SevenDwarves.java @@ -0,0 +1,64 @@ +package mage.cards.s; + +import mage.MageInt; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.dynamicvalue.DynamicValue; +import mage.abilities.dynamicvalue.common.PermanentsOnBattlefieldCount; +import mage.abilities.effects.common.InfoEffect; +import mage.abilities.effects.common.continuous.BoostSourceEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; +import mage.constants.Zone; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterControlledCreaturePermanent; +import mage.filter.predicate.mageobject.NamePredicate; +import mage.filter.predicate.permanent.AnotherPredicate; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class SevenDwarves extends CardImpl { + + private static final FilterPermanent filter = new FilterControlledCreaturePermanent(); + + static { + filter.add(AnotherPredicate.instance); + filter.add(new NamePredicate("Seven Dwarves")); + } + + private static final DynamicValue xValue = new PermanentsOnBattlefieldCount(filter); + + public SevenDwarves(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{1}{R}"); + + this.subtype.add(SubType.DWARF); + this.power = new MageInt(2); + this.toughness = new MageInt(2); + + // Seven Dwarves gets +1/+1 for each other creature named Seven Dwarves you control. + this.addAbility(new SimpleStaticAbility( + new BoostSourceEffect(xValue, xValue, Duration.WhileOnBattlefield).setText( + "{this} gets +1/+1 for each other creature named Seven Dwarves you control" + ) + )); + + // A deck can have up to seven cards named Seven Dwarves. + this.addAbility(new SimpleStaticAbility( + Zone.ALL, new InfoEffect("A deck can have up to seven cards named Seven Dwarves.") + )); + } + + private SevenDwarves(final SevenDwarves card) { + super(card); + } + + @Override + public SevenDwarves copy() { + return new SevenDwarves(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 222d60f52a..4c7b18c94e 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -155,6 +155,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Savvy Hunter", 200, Rarity.UNCOMMON, mage.cards.s.SavvyHunter.class)); cards.add(new SetCardInfo("Scorching Dragonfire", 139, Rarity.COMMON, mage.cards.s.ScorchingDragonfire.class)); cards.add(new SetCardInfo("Searing Barrage", 140, Rarity.COMMON, mage.cards.s.SearingBarrage.class)); + cards.add(new SetCardInfo("Seven Dwarves", 141, Rarity.COMMON, mage.cards.s.SevenDwarves.class)); cards.add(new SetCardInfo("Shimmer Dragon", 317, Rarity.RARE, mage.cards.s.ShimmerDragon.class)); cards.add(new SetCardInfo("Shinechaser", 201, Rarity.UNCOMMON, mage.cards.s.Shinechaser.class)); cards.add(new SetCardInfo("Shining Armor", 29, Rarity.COMMON, mage.cards.s.ShiningArmor.class)); diff --git a/Mage/src/main/java/mage/cards/decks/Constructed.java b/Mage/src/main/java/mage/cards/decks/Constructed.java index aaa95e435b..8718c63540 100644 --- a/Mage/src/main/java/mage/cards/decks/Constructed.java +++ b/Mage/src/main/java/mage/cards/decks/Constructed.java @@ -16,8 +16,8 @@ public class Constructed extends DeckValidator { private static final Logger logger = Logger.getLogger(DeckValidator.class); - protected static final List anyNumberCardsAllowed = new ArrayList<>(Arrays.asList( - "Relentless Rats", "Shadowborn Apostle", "Rat Colony", "Persistent Petitioners" + private static final List anyNumberCardsAllowed = new ArrayList<>(Arrays.asList( + "Relentless Rats", "Shadowborn Apostle", "Rat Colony", "Persistent Petitioners", "Seven Dwarves" )); protected static final List basicLandNames = new ArrayList<>(Arrays.asList( "Forest", "Island", "Mountain", "Swamp", "Plains", "Wastes", "Snow-Covered Forest", @@ -67,14 +67,8 @@ public class Constructed extends DeckValidator { Map counts = new HashMap<>(); countCards(counts, deck.getCards()); countCards(counts, deck.getSideboard()); - for (Entry entry : counts.entrySet()) { - if (entry.getValue() > 4) { - if (!basicLandNames.contains(entry.getKey()) && !anyNumberCardsAllowed.contains(entry.getKey())) { - invalid.put(entry.getKey(), "Too many: " + entry.getValue()); - valid = false; - } - } - } + valid = checkCounts(4, counts) && valid; + for (String bannedCard : banned) { if (counts.containsKey(bannedCard)) { invalid.put(bannedCard, "Banned"); @@ -179,4 +173,21 @@ public class Constructed extends DeckValidator { } return legal; } + + protected boolean checkCounts(int maxCopies, Map counts) { + boolean valid = true; + for (Entry entry : counts.entrySet()) { + if (entry.getValue() > maxCopies + && !basicLandNames.contains(entry.getKey()) + && !anyNumberCardsAllowed.contains(entry.getKey())) { + invalid.put(entry.getKey(), "Too many: " + entry.getValue()); + valid = false; + } + if (entry.getValue() > 7 && entry.getKey().equals("Seven Dwarves")) { + invalid.put(entry.getKey(), "Too many: " + entry.getValue()); + valid = false; + } + } + return valid; + } } From 575b0bca3050b77214d870b6eef22d52b5ecad9b Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 14 Sep 2019 19:28:26 -0400 Subject: [PATCH 135/373] updated Adamant implementation --- .../src/mage/cards/c/ClockworkServant.java | 17 +---------------- .../condition/common/AdamantCondition.java | 17 ++++++++++++++++- 2 files changed, 17 insertions(+), 17 deletions(-) diff --git a/Mage.Sets/src/mage/cards/c/ClockworkServant.java b/Mage.Sets/src/mage/cards/c/ClockworkServant.java index 7e9d949630..2604166602 100644 --- a/Mage.Sets/src/mage/cards/c/ClockworkServant.java +++ b/Mage.Sets/src/mage/cards/c/ClockworkServant.java @@ -1,9 +1,7 @@ package mage.cards.c; import mage.MageInt; -import mage.abilities.Ability; import mage.abilities.common.EntersBattlefieldTriggeredAbility; -import mage.abilities.condition.Condition; import mage.abilities.condition.common.AdamantCondition; import mage.abilities.decorator.ConditionalInterveningIfTriggeredAbility; import mage.abilities.effects.common.DrawCardSourceControllerEffect; @@ -11,10 +9,8 @@ import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.CardType; import mage.constants.SubType; -import mage.game.Game; import mage.watchers.common.ManaSpentToCastWatcher; -import java.util.Arrays; import java.util.UUID; /** @@ -32,7 +28,7 @@ public final class ClockworkServant extends CardImpl { // Adamant - When Clockwork Servant enters the battlefield, if at least three mana of the same color was spent to cast it, draw a card. this.addAbility(new ConditionalInterveningIfTriggeredAbility( new EntersBattlefieldTriggeredAbility(new DrawCardSourceControllerEffect(1)), - ClockworkServantCondition.instance, "
Adamant — When {this} enters the battlefield, " + + AdamantCondition.ALL, "
Adamant — When {this} enters the battlefield, " + "if at least three mana of the same color was spent to cast it, draw a card." ), new ManaSpentToCastWatcher()); } @@ -46,14 +42,3 @@ public final class ClockworkServant extends CardImpl { return new ClockworkServant(this); } } - -enum ClockworkServantCondition implements Condition { - instance; - - @Override - public boolean apply(Game game, Ability source) { - return Arrays - .stream(AdamantCondition.values()) - .anyMatch(adamantCondition -> adamantCondition.apply(game, source)); - } -} \ No newline at end of file diff --git a/Mage/src/main/java/mage/abilities/condition/common/AdamantCondition.java b/Mage/src/main/java/mage/abilities/condition/common/AdamantCondition.java index ae6fb8f11f..7e1b5ab383 100644 --- a/Mage/src/main/java/mage/abilities/condition/common/AdamantCondition.java +++ b/Mage/src/main/java/mage/abilities/condition/common/AdamantCondition.java @@ -8,6 +8,8 @@ import mage.constants.ColoredManaSymbol; import mage.game.Game; import mage.watchers.common.ManaSpentToCastWatcher; +import java.util.Arrays; + /** * @author TheElk801 */ @@ -16,7 +18,8 @@ public enum AdamantCondition implements Condition { BLUE(ColoredManaSymbol.U), BLACK(ColoredManaSymbol.B), RED(ColoredManaSymbol.R), - GREEN(ColoredManaSymbol.G); + GREEN(ColoredManaSymbol.G), + ALL(null); private final ColoredManaSymbol coloredManaSymbol; @@ -27,6 +30,12 @@ public enum AdamantCondition implements Condition { @Override public boolean apply(Game game, Ability source) { if (source.getAbilityType() == AbilityType.SPELL) { + if (coloredManaSymbol == null) { + return Arrays + .stream(ColoredManaSymbol.values()) + .map(source.getManaCostsToPay().getPayment()::getColor) + .anyMatch(i -> i > 2); + } return source.getManaCostsToPay().getPayment().getColor(coloredManaSymbol) > 2; } ManaSpentToCastWatcher watcher = game.getState().getWatcher(ManaSpentToCastWatcher.class, source.getSourceId()); @@ -37,6 +46,12 @@ public enum AdamantCondition implements Condition { if (payment == null) { return false; } + if (coloredManaSymbol == null) { + return Arrays + .stream(ColoredManaSymbol.values()) + .map(payment::getColor) + .anyMatch(i -> i > 2); + } return payment.getColor(coloredManaSymbol) > 2; } } From 821d196b369e4b27abaca60ed35769237ea6d6e5 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 14 Sep 2019 19:38:14 -0400 Subject: [PATCH 136/373] Implemented Gadwick, the Wizened --- .../src/mage/cards/g/GadwickTheWizened.java | 69 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 70 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/g/GadwickTheWizened.java diff --git a/Mage.Sets/src/mage/cards/g/GadwickTheWizened.java b/Mage.Sets/src/mage/cards/g/GadwickTheWizened.java new file mode 100644 index 0000000000..c20b0a635a --- /dev/null +++ b/Mage.Sets/src/mage/cards/g/GadwickTheWizened.java @@ -0,0 +1,69 @@ +package mage.cards.g; + +import mage.MageInt; +import mage.ObjectColor; +import mage.abilities.Ability; +import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.common.SpellCastControllerTriggeredAbility; +import mage.abilities.dynamicvalue.common.ManacostVariableValue; +import mage.abilities.effects.common.DrawCardSourceControllerEffect; +import mage.abilities.effects.common.TapTargetEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.constants.SuperType; +import mage.constants.TargetController; +import mage.filter.FilterPermanent; +import mage.filter.FilterSpell; +import mage.filter.common.FilterNonlandPermanent; +import mage.filter.predicate.mageobject.ColorPredicate; +import mage.filter.predicate.permanent.ControllerPredicate; +import mage.target.TargetPermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class GadwickTheWizened extends CardImpl { + + private static final FilterSpell filter + = new FilterSpell("a blue spell"); + private static final FilterPermanent filter2 + = new FilterNonlandPermanent("nonland permanent an opponent controls"); + + static { + filter.add(new ColorPredicate(ObjectColor.BLUE)); + filter2.add(new ControllerPredicate(TargetController.OPPONENT)); + } + + public GadwickTheWizened(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{X}{U}{U}{U}"); + + this.addSuperType(SuperType.LEGENDARY); + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.WIZARD); + this.power = new MageInt(3); + this.toughness = new MageInt(3); + + // When Gadwick, the Wizened enters the battlefield, draw X cards. + this.addAbility(new EntersBattlefieldTriggeredAbility( + new DrawCardSourceControllerEffect(ManacostVariableValue.instance) + )); + + // Whenever you cast a blue spell, tap target nonland permanent an opponent controls. + Ability ability = new SpellCastControllerTriggeredAbility(new TapTargetEffect(), filter, false); + ability.addTarget(new TargetPermanent(filter2)); + this.addAbility(ability); + } + + private GadwickTheWizened(final GadwickTheWizened card) { + super(card); + } + + @Override + public GadwickTheWizened copy() { + return new GadwickTheWizened(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 4c7b18c94e..0c1d8eec2a 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -84,6 +84,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Folio of Fancies", 46, Rarity.RARE, mage.cards.f.FolioOfFancies.class)); cards.add(new SetCardInfo("Foulmire Knight", 90, Rarity.UNCOMMON, mage.cards.f.FoulmireKnight.class)); cards.add(new SetCardInfo("Frogify", 47, Rarity.UNCOMMON, mage.cards.f.Frogify.class)); + cards.add(new SetCardInfo("Gadwick, the Wizened", 48, Rarity.RARE, mage.cards.g.GadwickTheWizened.class)); cards.add(new SetCardInfo("Garenbrig Paladin", 157, Rarity.COMMON, mage.cards.g.GarenbrigPaladin.class)); cards.add(new SetCardInfo("Garrison Griffin", 305, Rarity.COMMON, mage.cards.g.GarrisonGriffin.class)); cards.add(new SetCardInfo("Garruk, Cursed Huntsman", 191, Rarity.MYTHIC, mage.cards.g.GarrukCursedHuntsman.class)); From 39dd0f5df249a3ca45ac391440b11f659ba1bb14 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 14 Sep 2019 19:52:33 -0400 Subject: [PATCH 137/373] Implemented Ayara, First of Locthwain --- .../mage/cards/a/AyaraFirstOfLocthwain.java | 69 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 70 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/a/AyaraFirstOfLocthwain.java diff --git a/Mage.Sets/src/mage/cards/a/AyaraFirstOfLocthwain.java b/Mage.Sets/src/mage/cards/a/AyaraFirstOfLocthwain.java new file mode 100644 index 0000000000..64d5860988 --- /dev/null +++ b/Mage.Sets/src/mage/cards/a/AyaraFirstOfLocthwain.java @@ -0,0 +1,69 @@ +package mage.cards.a; + +import mage.MageInt; +import mage.ObjectColor; +import mage.abilities.Ability; +import mage.abilities.common.EntersBattlefieldControlledTriggeredAbility; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.costs.common.SacrificeTargetCost; +import mage.abilities.costs.common.TapSourceCost; +import mage.abilities.effects.common.DrawCardSourceControllerEffect; +import mage.abilities.effects.common.GainLifeEffect; +import mage.abilities.effects.common.LoseLifeOpponentsEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.constants.SuperType; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterControlledCreaturePermanent; +import mage.filter.common.FilterControlledPermanent; +import mage.filter.predicate.mageobject.ColorPredicate; +import mage.target.common.TargetControlledPermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class AyaraFirstOfLocthwain extends CardImpl { + + private static final FilterPermanent filter + = new FilterPermanent("{this} or another black creature"); + private static final FilterControlledPermanent filter2 + = new FilterControlledCreaturePermanent("another black creature"); + + static { + filter.add(new ColorPredicate(ObjectColor.BLACK)); + filter2.add(new ColorPredicate(ObjectColor.BLACK)); + } + + public AyaraFirstOfLocthwain(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{B}{B}{B}"); + + this.addSuperType(SuperType.LEGENDARY); + this.subtype.add(SubType.ELF); + this.subtype.add(SubType.NOBLE); + this.power = new MageInt(2); + this.toughness = new MageInt(3); + + // Whenever Ayara, First of Locthwain or another black creature enters the battlefield under your control, each opponent loses 1 life and you gain 1 life. + Ability ability = new EntersBattlefieldControlledTriggeredAbility(new LoseLifeOpponentsEffect(1), filter); + ability.addEffect(new GainLifeEffect(1).concatBy("and")); + this.addAbility(ability); + + // {T}, Sacrifice another black creature: Draw a card. + ability = new SimpleActivatedAbility(new DrawCardSourceControllerEffect(1), new TapSourceCost()); + ability.addCost(new SacrificeTargetCost(new TargetControlledPermanent(filter2))); + this.addAbility(ability); + } + + private AyaraFirstOfLocthwain(final AyaraFirstOfLocthwain card) { + super(card); + } + + @Override + public AyaraFirstOfLocthwain copy() { + return new AyaraFirstOfLocthwain(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 0c1d8eec2a..8155cc50dc 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -34,6 +34,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Arcane Signet", 331, Rarity.COMMON, mage.cards.a.ArcaneSignet.class)); cards.add(new SetCardInfo("Arcanist's Owl", 206, Rarity.UNCOMMON, mage.cards.a.ArcanistsOwl.class)); cards.add(new SetCardInfo("Ardenvale Tactician", 5, Rarity.COMMON, mage.cards.a.ArdenvaleTactician.class)); + cards.add(new SetCardInfo("Ayara, First of Locthwain", 75, Rarity.RARE, mage.cards.a.AyaraFirstOfLocthwain.class)); cards.add(new SetCardInfo("Bake into a Pie", 76, Rarity.COMMON, mage.cards.b.BakeIntoAPie.class)); cards.add(new SetCardInfo("Banish into Fable", 325, Rarity.RARE, mage.cards.b.BanishIntoFable.class)); cards.add(new SetCardInfo("Barge In", 112, Rarity.COMMON, mage.cards.b.BargeIn.class)); From 7d05f8a1d883f6b6c7cf7993f08adab12c0775be Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 14 Sep 2019 19:59:07 -0400 Subject: [PATCH 138/373] fixed an error --- Mage.Sets/src/mage/cards/p/ProteanHydra.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Mage.Sets/src/mage/cards/p/ProteanHydra.java b/Mage.Sets/src/mage/cards/p/ProteanHydra.java index ca3820ba66..ad50c03001 100644 --- a/Mage.Sets/src/mage/cards/p/ProteanHydra.java +++ b/Mage.Sets/src/mage/cards/p/ProteanHydra.java @@ -38,7 +38,7 @@ public final class ProteanHydra extends CardImpl { this.addAbility(new EntersBattlefieldAbility(new EntersBattlefieldWithXCountersEffect(CounterType.P1P1.createInstance()))); // If damage would be dealt to Protean Hydra, prevent that damage and remove that many +1/+1 counters from it. - this.addAbility(new SimpleStaticAbility(Zone.BATTLEFIELD, new PreventDamageAndRemoveCountersEffect())); + this.addAbility(new SimpleStaticAbility(Zone.BATTLEFIELD, new PreventDamageAndRemoveCountersEffect(true))); // Whenever a +1/+1 counter is removed from Protean Hydra, put two +1/+1 counters on it at the beginning of the next end step. this.addAbility(new ProteanHydraAbility()); From 6af989d6a04a8db1a1f4f7073fe3b0d0f6cf2321 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sun, 15 Sep 2019 10:22:04 -0400 Subject: [PATCH 139/373] Implemented Henge Walker --- .../src/mage/cards/c/ClockworkServant.java | 2 +- Mage.Sets/src/mage/cards/h/HengeWalker.java | 44 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + .../condition/common/AdamantCondition.java | 2 +- Utils/mtg-cards-data.txt | 5 ++- 5 files changed, 50 insertions(+), 4 deletions(-) create mode 100644 Mage.Sets/src/mage/cards/h/HengeWalker.java diff --git a/Mage.Sets/src/mage/cards/c/ClockworkServant.java b/Mage.Sets/src/mage/cards/c/ClockworkServant.java index 2604166602..0e38967ad9 100644 --- a/Mage.Sets/src/mage/cards/c/ClockworkServant.java +++ b/Mage.Sets/src/mage/cards/c/ClockworkServant.java @@ -28,7 +28,7 @@ public final class ClockworkServant extends CardImpl { // Adamant - When Clockwork Servant enters the battlefield, if at least three mana of the same color was spent to cast it, draw a card. this.addAbility(new ConditionalInterveningIfTriggeredAbility( new EntersBattlefieldTriggeredAbility(new DrawCardSourceControllerEffect(1)), - AdamantCondition.ALL, "
Adamant — When {this} enters the battlefield, " + + AdamantCondition.ANY, "
Adamant — When {this} enters the battlefield, " + "if at least three mana of the same color was spent to cast it, draw a card." ), new ManaSpentToCastWatcher()); } diff --git a/Mage.Sets/src/mage/cards/h/HengeWalker.java b/Mage.Sets/src/mage/cards/h/HengeWalker.java new file mode 100644 index 0000000000..767e62c7b5 --- /dev/null +++ b/Mage.Sets/src/mage/cards/h/HengeWalker.java @@ -0,0 +1,44 @@ +package mage.cards.h; + +import mage.MageInt; +import mage.abilities.common.EntersBattlefieldAbility; +import mage.abilities.condition.common.AdamantCondition; +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.counters.CounterType; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class HengeWalker extends CardImpl { + + public HengeWalker(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT, CardType.CREATURE}, "{3}"); + + this.subtype.add(SubType.GOLEM); + this.power = new MageInt(2); + this.toughness = new MageInt(2); + + // Adamant — If at least three mana of the same color was spent to cast this spell, Henge Walker enters the battlefield with a +1/+1 counter on it. + this.addAbility(new EntersBattlefieldAbility( + new AddCountersSourceEffect(CounterType.P1P1.createInstance()), + AdamantCondition.ANY, "
Adamant — " + + "If at least three mana of the same color was spent to cast this spell, " + + "{this} enters the battlefield with a +1/+1 counter on it.", "" + )); + } + + private HengeWalker(final HengeWalker card) { + super(card); + } + + @Override + public HengeWalker copy() { + return new HengeWalker(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 8155cc50dc..24e0093ad9 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -97,6 +97,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Golden Egg", 220, Rarity.COMMON, mage.cards.g.GoldenEgg.class)); cards.add(new SetCardInfo("Grumgully, the Generous", 192, Rarity.UNCOMMON, mage.cards.g.GrumgullyTheGenerous.class)); cards.add(new SetCardInfo("Harmonious Archon", 17, Rarity.MYTHIC, mage.cards.h.HarmoniousArchon.class)); + cards.add(new SetCardInfo("Henge Walker", 221, Rarity.COMMON, mage.cards.h.HengeWalker.class)); cards.add(new SetCardInfo("Heraldic Banner", 222, Rarity.UNCOMMON, mage.cards.h.HeraldicBanner.class)); cards.add(new SetCardInfo("Hypnotic Sprite", 49, Rarity.UNCOMMON, mage.cards.h.HypnoticSprite.class)); cards.add(new SetCardInfo("Inquisitive Puppet", 223, Rarity.UNCOMMON, mage.cards.i.InquisitivePuppet.class)); diff --git a/Mage/src/main/java/mage/abilities/condition/common/AdamantCondition.java b/Mage/src/main/java/mage/abilities/condition/common/AdamantCondition.java index 7e1b5ab383..4e45cdf04f 100644 --- a/Mage/src/main/java/mage/abilities/condition/common/AdamantCondition.java +++ b/Mage/src/main/java/mage/abilities/condition/common/AdamantCondition.java @@ -19,7 +19,7 @@ public enum AdamantCondition implements Condition { BLACK(ColoredManaSymbol.B), RED(ColoredManaSymbol.R), GREEN(ColoredManaSymbol.G), - ALL(null); + ANY(null); private final ColoredManaSymbol coloredManaSymbol; diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index 9fd6449d25..39e56d7506 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -36095,7 +36095,7 @@ Searing Barrage|Throne of Eldraine|140|C|{4}{R}|Instant|||Searing Barrage deals Seven Dwarves|Throne of Eldraine|141|C|{1}{R}|Creature - Dwarf|2|2|Seven Dwarves gets +1/+1 for each other creature named Seven Dwarves you control.$A deck can have up to seven cards named Seven Dwarves.| Skullknocker Ogre|Throne of Eldraine|142|U|{3}{R}|Creature - Ogre|4|3|Whenever Skullknocker Ogre deals damage to an opponent, that player discards a card at random. If the player does, they draw a card.| Slaying Fire|Throne of Eldraine|143|U|{2}{R}|Instant|||Slaying Fire deals 3 damage to any target.$Adamant — If at least three red mana was spent to cast this spell, it deals 4 damage instead.| -Sundering Stroke|Throne of Eldraine|144|R|{6}{R}|Sorcery|||Sundering Stroke deals 7 damage divided as you choose amone one, two, or three targets. If at least seven red mana was spent to cast this spell, instead Sundering Stroke deals 7 damage to each of those permanents and/or players.| +Sundering Stroke|Throne of Eldraine|144|R|{6}{R}|Sorcery|||Sundering Stroke deals 7 damage divided as you choose among one, two, or three targets. If at least seven red mana was spent to cast this spell, instead Sundering Stroke deals 7 damage to each of those permanents and/or players.| Syr Carah, the Bold|Throne of Eldraine|145|U|{3}{R}{R}|Legendary Creature - Human Knight|3|3|When Syr Carah, the Bold or an instant or sorcery spell you control deals damage to a player, exile the top card of your library. You may play that card this turn.${T}: Syr Carah deals 1 damage to any target.| Weaselback Redcap|Throne of Eldraine|148|C|{R}|Creature - Goblin Knight|1|1|{1}{R}: Weaselback Redcap gets +2/+0 until end of turn.| Beanstalk Giant|Throne of Eldraine|149|U|{6}{G}|Creature - Giant|*|*|Beanstalk Giant's power and toughness are each equal to the number of lands you control.| @@ -36152,9 +36152,11 @@ Loch Dragon|Throne of Eldraine|211|U|{U/R}{U/R}{U/R}{U/R}|Creature - Dragon|3|2| Bring Back|Throne of Eldraine|212|U|{G/W}{G/W}{G/W}{G/W}|Sorcery - Adventure|2|2|Create two 1/1 white Human creature tokens.| Oakhame Ranger|Throne of Eldraine|212|U|{G/W}{G/W}{G/W}{G/W}|Creature - Elf Knight|2|2|{T}: Creatures you control get +1/+1 until end of turn.| Thunderous Snapper|Throne of Eldraine|215|U|{G/U}{G/U}{G/U}{G/U}|Creature - Turtle Hydra|4|4|Whenever you cast a spell with converted mana cost 5 or greater, draw a card.| +Clockwork Servant|Throne of Eldraine|216|U|{3}|Artifact Creature - Gnome|2|3|Adamant — When Clockwork Servant enters the battlefield, if at least three mana of the same color was spent to cast it, draw a card.| Enchanted Carriage|Throne of Eldraine|218|U|{5}|Artifact - Vehicle|4|4|When Enchanted Carriage enters the battlefield, create two 1/1 white Mouse creature tokens.$Crew 2| Gingerbrute|Throne of Eldraine|219|C|{1}|Artifact Creature - Food Golem|1|1|Haste${1}: Gingerbrute can't be blocked this turn except by creatures with haste.${2}, {T}, Sacrifice Gingerbrute: You gain 3 life.| Golden Egg|Throne of Eldraine|220|C|{2}|Artifact - Food|||When Golden Egg enters the battlefield, draw a card.${1}, {T}, Sacrifice Golden Egg: Add one mana of any color.${2}, {T}, Sacrifice Golden Egg: You gain 3 life.| +Henge Walker|Throne of Eldraine|221|C|{3}|Artifact Creature - Golem|2|2|Adamant — If at least three mana of the same color was spent to cast this spell, Henge Walker enters the battlefield with a +1/+1 counter on it.| Heraldic Banner|Throne of Eldraine|222|U|{3}|Artifact|||As Heraldic Banner enters the battlefield, choose a color.$Creatures you control of the chosen color get +1/+0.${T}: Add one mana of the chosen color.| Inquisitive Puppet|Throne of Eldraine|223|U|{1}|Artifact Creature - Construct|0|2|When Inquisitive Puppet enters the battlefield, scry 1.$Exile Inquisitive Puppet: Create a 1/1 white Human creature token.| Jousting Dummy|Throne of Eldraine|224|C|{2}|Artifact Creature - Scarecrow Knight|2|1|{3}: Jousting Dummy gets +1/+0 until end of turn.| @@ -36195,4 +36197,3 @@ Syr Gwyn, Hero of Ashvale|Throne of Eldraine|330|M|{3}{R}{W}{B}|Legendary Creatu Arcane Signet|Throne of Eldraine|331|C|{2}|Artifact|||{T}: Add one mana of any color in your commander's color identity.| Tome of Legends|Throne of Eldraine|332|R|{2}|Artifact|||Tome of Legends enters the battlefield with a page counter on it.$Whenever your commander enters the battlefield or attacks, put a page counter on Tome of Legends.${1}, {T}, Remove a page counter from Tome of Legends: Draw a card.| Command Tower|Throne of Eldraine|333|C||Land|||{T}: Add one mana of any color in your commander's color identity.| -Clockwork Servant|Throne of Eldraine|216|U|{3}|Artifact Creature - Gnome|2|3|Adamant - When Clockwork Servant enters the battlefield, if at least three mana of the same color was spent to cast it, draw a card.| \ No newline at end of file From 29faab73d13d0f0753511b42e2c917106fedccbc Mon Sep 17 00:00:00 2001 From: Matthaios Tsiridis Date: Sun, 15 Sep 2019 17:55:17 +0300 Subject: [PATCH 140/373] FIXED a bug where Worthy Knight was only creating tokens if the spell was a human spell. --- Mage.Sets/src/mage/cards/w/WorthyKnight.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Mage.Sets/src/mage/cards/w/WorthyKnight.java b/Mage.Sets/src/mage/cards/w/WorthyKnight.java index d3521c5897..636dbc351a 100644 --- a/Mage.Sets/src/mage/cards/w/WorthyKnight.java +++ b/Mage.Sets/src/mage/cards/w/WorthyKnight.java @@ -21,7 +21,7 @@ public final class WorthyKnight extends CardImpl { private static final FilterSpell filter = new FilterSpell("a Knight spell"); static { - filter.add(new SubtypePredicate(SubType.HUMAN)); + filter.add(new SubtypePredicate(SubType.KNIGHT)); } public WorthyKnight(UUID ownerId, CardSetInfo setInfo) { From db7f61e6c5bb7bf4d99559bec13bde1925dcc4b6 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sun, 15 Sep 2019 10:56:43 -0400 Subject: [PATCH 141/373] fixed Vantress Gargoyle erroring --- .../src/mage/cards/v/VantressGargoyle.java | 60 +++++++++++++------ 1 file changed, 42 insertions(+), 18 deletions(-) diff --git a/Mage.Sets/src/mage/cards/v/VantressGargoyle.java b/Mage.Sets/src/mage/cards/v/VantressGargoyle.java index 09c5ac5add..0639373464 100644 --- a/Mage.Sets/src/mage/cards/v/VantressGargoyle.java +++ b/Mage.Sets/src/mage/cards/v/VantressGargoyle.java @@ -4,17 +4,16 @@ import mage.MageInt; import mage.abilities.Ability; import mage.abilities.common.SimpleActivatedAbility; import mage.abilities.common.SimpleStaticAbility; -import mage.abilities.condition.Condition; -import mage.abilities.condition.common.CardsInHandCondition; import mage.abilities.costs.common.TapSourceCost; -import mage.abilities.decorator.ConditionalContinuousEffect; import mage.abilities.effects.RestrictionEffect; import mage.abilities.effects.common.PutTopCardOfLibraryIntoGraveEachPlayerEffect; -import mage.abilities.effects.common.combat.CantBlockSourceEffect; import mage.abilities.keyword.FlyingAbility; 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.TargetController; import mage.game.Game; import mage.game.permanent.Permanent; import mage.players.Player; @@ -26,8 +25,6 @@ import java.util.UUID; */ public final class VantressGargoyle extends CardImpl { - private static final Condition condition = new CardsInHandCondition(ComparisonType.FEWER_THAN, 4); - public VantressGargoyle(UUID ownerId, CardSetInfo setInfo) { super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT, CardType.CREATURE}, "{1}{U}"); @@ -39,13 +36,10 @@ public final class VantressGargoyle extends CardImpl { this.addAbility(FlyingAbility.getInstance()); // Vantress Gargoyle can't attack unless defending player has seven or more cards in their graveyard. - this.addAbility(new SimpleStaticAbility(new VantressGargoyleEffect())); + this.addAbility(new SimpleStaticAbility(new VantressGargoyleAttackEffect())); // Vantress Gargoyle can't block unless you have four or more cards in hand. - this.addAbility(new SimpleStaticAbility(new ConditionalContinuousEffect( - new CantBlockSourceEffect(Duration.WhileOnBattlefield), condition, - "{this} can't block unless you have four or more cards in hand" - ))); + this.addAbility(new SimpleStaticAbility(new VantressGargoyleBlockEffect())); // {T}: Each player puts the top card of their library into their graveyard. this.addAbility(new SimpleActivatedAbility( @@ -63,14 +57,14 @@ public final class VantressGargoyle extends CardImpl { } } -class VantressGargoyleEffect extends RestrictionEffect { +class VantressGargoyleAttackEffect extends RestrictionEffect { - VantressGargoyleEffect() { + VantressGargoyleAttackEffect() { super(Duration.WhileOnBattlefield); staticText = "{this} can't attack unless defending player has seven or more cards in their graveyard"; } - private VantressGargoyleEffect(final VantressGargoyleEffect effect) { + private VantressGargoyleAttackEffect(final VantressGargoyleAttackEffect effect) { super(effect); } @@ -86,7 +80,37 @@ class VantressGargoyleEffect extends RestrictionEffect { } @Override - public VantressGargoyleEffect copy() { - return new VantressGargoyleEffect(this); + public VantressGargoyleAttackEffect copy() { + return new VantressGargoyleAttackEffect(this); } -} \ No newline at end of file +} + +class VantressGargoyleBlockEffect extends RestrictionEffect { + + VantressGargoyleBlockEffect() { + super(Duration.WhileOnBattlefield); + staticText = "{this} can't block unless you have four or more cards in hand"; + } + + private VantressGargoyleBlockEffect(final VantressGargoyleBlockEffect effect) { + super(effect); + } + + @Override + public VantressGargoyleBlockEffect copy() { + return new VantressGargoyleBlockEffect(this); + } + + @Override + public boolean canBlock(Permanent attacker, Permanent blocker, Ability source, Game game, boolean canUseChooseDialogs) { + return false; + } + + @Override + public boolean applies(Permanent permanent, Ability source, Game game) { + Player player = game.getPlayer(source.getControllerId()); + return player != null + && player.getHand().size() < 4 + && permanent.getId().equals(source.getSourceId()); + } +} From 5f20674d09f5ee1317b69ef74400e51a2b02ee5b Mon Sep 17 00:00:00 2001 From: Matthaios Tsiridis Date: Sun, 15 Sep 2019 18:36:10 +0300 Subject: [PATCH 142/373] Fixed Inspiring Veteran where there was a bug that he would Give +1/+1 to himself as well. --- .../src/mage/cards/i/InspiringVeteran.java | 18 ++++++++++++++---- 1 file changed, 14 insertions(+), 4 deletions(-) diff --git a/Mage.Sets/src/mage/cards/i/InspiringVeteran.java b/Mage.Sets/src/mage/cards/i/InspiringVeteran.java index caa57a7a20..31c7682ff8 100644 --- a/Mage.Sets/src/mage/cards/i/InspiringVeteran.java +++ b/Mage.Sets/src/mage/cards/i/InspiringVeteran.java @@ -2,13 +2,19 @@ package mage.cards.i; import mage.MageInt; import mage.abilities.common.SimpleStaticAbility; -import mage.abilities.effects.common.continuous.BoostControlledEffect; +import mage.abilities.effects.common.continuous.BoostAllEffect; import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.CardType; import mage.constants.Duration; import mage.constants.SubType; +import mage.constants.TargetController; import mage.filter.common.FilterCreaturePermanent; +import mage.filter.predicate.permanent.ControllerPredicate; +import mage.constants.Zone; +import mage.filter.predicate.mageobject.SubtypePredicate; + + import java.util.UUID; @@ -20,6 +26,12 @@ public final class InspiringVeteran extends CardImpl { private static final FilterCreaturePermanent filter = new FilterCreaturePermanent(SubType.KNIGHT, "Knights"); + static + { + filter.add(new SubtypePredicate(SubType.KNIGHT)); + filter.add(new ControllerPredicate(TargetController.YOU)); + } + public InspiringVeteran(UUID ownerId, CardSetInfo setInfo) { super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{R}{W}"); @@ -29,9 +41,7 @@ public final class InspiringVeteran extends CardImpl { this.toughness = new MageInt(2); // Other Knights you control get +1/+1. - this.addAbility(new SimpleStaticAbility( - new BoostControlledEffect(1, 1, Duration.WhileOnBattlefield, filter) - )); + this.addAbility(new SimpleStaticAbility(Zone.BATTLEFIELD, new BoostAllEffect(1, 1, Duration.WhileOnBattlefield, filter, true))); } private InspiringVeteran(final InspiringVeteran card) { From 48071c5f2e023bd92a6754c94fb29d0b41c8caf6 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sun, 15 Sep 2019 11:59:21 -0400 Subject: [PATCH 143/373] fixed Inspiring Veteran pumping itself (fixes #5982) --- Mage.Sets/src/mage/cards/i/InspiringVeteran.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Mage.Sets/src/mage/cards/i/InspiringVeteran.java b/Mage.Sets/src/mage/cards/i/InspiringVeteran.java index caa57a7a20..e0b441424e 100644 --- a/Mage.Sets/src/mage/cards/i/InspiringVeteran.java +++ b/Mage.Sets/src/mage/cards/i/InspiringVeteran.java @@ -30,7 +30,7 @@ public final class InspiringVeteran extends CardImpl { // Other Knights you control get +1/+1. this.addAbility(new SimpleStaticAbility( - new BoostControlledEffect(1, 1, Duration.WhileOnBattlefield, filter) + new BoostControlledEffect(1, 1, Duration.WhileOnBattlefield, filter, true) )); } From 66d5a950c3beffda4f8870fe0e93faafcb1c4456 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 16 Sep 2019 09:40:11 -0400 Subject: [PATCH 144/373] updated ELD spoiler --- Mage.Sets/src/mage/cards/h/HengeWalker.java | 3 ++- Utils/mtg-cards-data.txt | 5 +++++ 2 files changed, 7 insertions(+), 1 deletion(-) diff --git a/Mage.Sets/src/mage/cards/h/HengeWalker.java b/Mage.Sets/src/mage/cards/h/HengeWalker.java index 767e62c7b5..1550201d9c 100644 --- a/Mage.Sets/src/mage/cards/h/HengeWalker.java +++ b/Mage.Sets/src/mage/cards/h/HengeWalker.java @@ -9,6 +9,7 @@ import mage.cards.CardSetInfo; import mage.constants.CardType; import mage.constants.SubType; import mage.counters.CounterType; +import mage.watchers.common.ManaSpentToCastWatcher; import java.util.UUID; @@ -30,7 +31,7 @@ public final class HengeWalker extends CardImpl { AdamantCondition.ANY, "
Adamant — " + "If at least three mana of the same color was spent to cast this spell, " + "{this} enters the battlefield with a +1/+1 counter on it.", "" - )); + ), new ManaSpentToCastWatcher()); } private HengeWalker(final HengeWalker card) { diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index 39e56d7506..423238ac88 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -35996,6 +35996,7 @@ Forest|Commander 2019|300|C||Basic Land - Forest|||({T}: Add {G}.)| All That Glitters|Throne of Eldraine|2|U|{1}{W}|Enchantment - Aura|||Enchant creature$Enchanted creature gets +1/+1 for each artifact and/or enchantment you control.| Ardenvale Tactician|Throne of Eldraine|5|C|{1}{W}{W}|Creature - Human Knight|2|3|Flying| Dizzying Swoop|Throne of Eldraine|5|C|{1}{W}|Instant - Adventure|2|3|Tap up to two target creatures.| +Bartered Cow|Throne of Eldraine|6|C|{3}{W}|Creature - Ox|3|3|When Bartered Cow dies or when you discard it, create a Food token.| Beloved Princess|Throne of Eldraine|7|C|{W}|Creature - Human Noble|1|1|Lifelink$Beloved Princess can't be blocked by creatures with power 3 or greater.| Charming Prince|Throne of Eldraine|8|R|{1}{W}|Creature - Human Noble|2|2|When Charming Prince enters the battlefield, choose one —$• Scry 2.$• You gain 3 life.$• Exile another target creature you own. Return it to the battlefield under your control at the beginning of the next end step.| The Circle of Loyalty|Throne of Eldraine|9|M|{4}{W}{W}|Legendary Artifact|||This spell costs {1} less to cast for each Knight you control.$Creatures you control get +1/+1.$Whenever you cast a legendary spell, create a 2/2 white Knight creature token with vigilance.${3}{W}, {T}: Create a 2/2 white Knight creature token with vigilance.| @@ -36109,6 +36110,7 @@ Fierce Witchstalker|Throne of Eldraine|154|C|{2}{G}{G}|Creature - Wolf|4|4|Tramp Flaxen Intruder|Throne of Eldraine|155|U|{G}|Creature - Human Berserker|1|2|Whenever Flaxen Intruder deals combat damage to a player, you may sacrifice it. When you do, destroy target artifact or enchantment.| Welcome Home|Throne of Eldraine|155|U|{5}{G}{G}|Sorcery - Adventure|1|2|Create three 2/2 green Bear creature tokens.| Garenbrig Paladin|Throne of Eldraine|157|C|{4}{G}|Creature - Giant Knight|4|4|Adamant — If at least three green mana was spent to cast this spell, Garenbrig Paladin enters the battlefield with a +1/+1 counter on it.$Garenbrig Paladin can't be blocked by creatures with power 2 or less.| +Giant Opportunity|Throne of Eldraine|159|U|{2}{G}|Sorcery|||You may sacrifice two Foods. If you do, create a 7/7 green Giant creature token. Otherwise, create three Food tokens.| Gilded Goose|Throne of Eldraine|160|R|{G}|Creature - Bird|0|2|Flying$When Gilded Goose enters the battlefield, create a Food token.${1}{G}, {T}: Create a Food token.${T}, Sacrifice a Food: Add one mana of any color.| Insatiable Appetite|Throne of Eldraine|162|C|{1}{G}|Instant|||You may sacrifice a Food. If you do, target creature gets +5/+5 until end of turn. Otherwise, that creature gets +3/+3 until end of turn.| Keeper of Fables|Throne of Eldraine|163|U|{3}{G}{G}|Creature - Cat|4|5|Whenever one or more non-Human creatures you control deal combat damage to a player, draw a card.| @@ -36123,6 +36125,7 @@ Questing Beast|Throne of Eldraine|171|M|{2}{G}{G}|Legendary Creature - Beast|4|4 Return to Nature|Throne of Eldraine|173|C|{1}{G}|Instant|||Choose one —$• Destroy target artifact.$• Destroy target enchantment.$• Exile target card from a graveyard.| Rosethorn Acolyte|Throne of Eldraine|174|C|{2}{G}|Creature - Elf Druid|2|3|{T}: Add one mana of any color.| Seasonal Ritual|Throne of Eldraine|174|C|{G}|Sorcery - Adventure|2|3|Add one mana of any color.| +Tall as a Beanstalk|Throne of Eldraine|178|C|{3}{G}|Enchantment - Aura|||Enchant creature$Enchanted creature gets +3/+3, has reach, and is a Giant in addition to its other types.| Trail of Crumbs|Throne of Eldraine|179|U|{1}{G}|Enchantment|||When Trail of Crumbs enters the battlefield, create a Food token.$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.| Wicked Wolf|Throne of Eldraine|181|R|{2}{G}{G}|Creature - Wolf|3|3|When Wicked Wolf enters the battlefield, it fights up to one target creature you don't control.$Sacrifice a Food: Put a +1/+1 counter on Wicked Wolf. It gains indestructible until end of turn. Tap it.| Wildborn Preserver|Throne of Eldraine|182|R|{1}{G}|Creature - Elf Archer|2|2|Flash$Reach$Whenever another non-Human creature enters the battlefield under your control, you may pay {X}. When you do, put X +1/+1 counters on Wildborn Preserver.| @@ -36130,6 +36133,7 @@ Wildwood Tracker|Throne of Eldraine|183|C|{G}|Creature - Elf Warrior|1|1|Wheneve Wolf's Quarry|Throne of Eldraine|184|C|{4}{G}{G}|Sorcery|||Create three 1/1 green Boar creature tokens with "When this creature dies, create a Food token."| Dance of the Manse|Throne of Eldraine|186|R|{X}{W}{U}|Sorcery|||Return up to X target artifact and/or non-Aura enchantment cards each with converted mana cost X or less from your graveyard to the battlefield. If X is 6 or more, those permanents are 4/4 creatures in addition to their other types.| Doom Foretold|Throne of Eldraine|187|R|{2}{W}{B}|Enchantment|||At the beginning of each player's upkeep, that player sacrifices a nonland, nontoken permanent. If that player can't, they discard a card, they lose 2 life, you draw a card, you gain 2 life, you create a 2/2 white Knight creature token with vigilance, then you sacrifice Doom Foretold.| +Drown in the Loch|Throne of Eldraine|188|U|{U}{B}|Instant|||Choose one —$• Counter target spell with converted mana cost less than or equal to the number of cards in its controller's graveyard.$• Destroy target creature with converted mana cost less than or equal to the number of cards in its controller's graveyard.| Faeburrow Elder|Throne of Eldraine|190|R|{1}{G}{W}|Creature - Treefolk Druid|0|0|Vigilance$Faeburrow Elder gets +1/+1 for each color among permanents you control.${T}: For each color among permanents you control, add one mana of that color.| Garruk, Cursed Huntsman|Throne of Eldraine|191|M|{4}{B}{G}|Legendary Planeswalker - Garruk|5|0: Create two 2/2 black and green Wolf creature tokens with "When this creature dies, put a loyalty counter on each Garruk you control."$−3: Destroy target creature. Draw a card.$−6: You get an emblem with "Creatures you control get +3/+3 and have trample."| Grumgully, the Generous|Throne of Eldraine|192|U|{1}{R}{G}|Legendary Creature - Goblin Shaman|3|3|Each other non-Human creature you controls enters the battlefield with an additional +1/+1 counter on it.| @@ -36197,3 +36201,4 @@ Syr Gwyn, Hero of Ashvale|Throne of Eldraine|330|M|{3}{R}{W}{B}|Legendary Creatu Arcane Signet|Throne of Eldraine|331|C|{2}|Artifact|||{T}: Add one mana of any color in your commander's color identity.| Tome of Legends|Throne of Eldraine|332|R|{2}|Artifact|||Tome of Legends enters the battlefield with a page counter on it.$Whenever your commander enters the battlefield or attacks, put a page counter on Tome of Legends.${1}, {T}, Remove a page counter from Tome of Legends: Draw a card.| Command Tower|Throne of Eldraine|333|C||Land|||{T}: Add one mana of any color in your commander's color identity.| +Torbran, Thane of Red Fell|Throne of Eldraine|367|R|{1}{R}{R}{R}|Legendary Creature - Dwarf Noble|2|4|If a red source you control would deal damage to an opponent or a permanent an opponent controls, it deals that much damage plus 2 instead.| From 2cdb2693471c9fea7b7ff76fa1a8d5dabe4093e8 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 16 Sep 2019 09:48:27 -0400 Subject: [PATCH 145/373] Implemented Drown in the Loch --- .../src/mage/cards/d/DrownInTheLoch.java | 70 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 71 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/d/DrownInTheLoch.java diff --git a/Mage.Sets/src/mage/cards/d/DrownInTheLoch.java b/Mage.Sets/src/mage/cards/d/DrownInTheLoch.java new file mode 100644 index 0000000000..0fcbf673e2 --- /dev/null +++ b/Mage.Sets/src/mage/cards/d/DrownInTheLoch.java @@ -0,0 +1,70 @@ +package mage.cards.d; + +import mage.MageObject; +import mage.abilities.Mode; +import mage.abilities.effects.common.CounterTargetEffect; +import mage.abilities.effects.common.DestroyTargetEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.filter.FilterPermanent; +import mage.filter.FilterSpell; +import mage.filter.common.FilterCreaturePermanent; +import mage.filter.predicate.Predicate; +import mage.game.Game; +import mage.players.Player; +import mage.target.TargetPermanent; +import mage.target.TargetSpell; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class DrownInTheLoch extends CardImpl { + + private static final FilterSpell filter + = new FilterSpell("spell with converted mana cost less than or equal to " + + "the number of cards in its controller's graveyard"); + private static final FilterPermanent filter2 + = new FilterCreaturePermanent("creature with converted mana cost less than or equal to " + + "the number of cards in its controller's graveyard"); + + static { + filter.add(DrownInTheLochPredicate.instance); + filter2.add(DrownInTheLochPredicate.instance); + } + + public DrownInTheLoch(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.INSTANT}, "{U}{B}"); + + // Choose one — + // • Counter target spell with converted mana cost less than or equal to the number of cards in its controller's graveyard. + this.getSpellAbility().addEffect(new CounterTargetEffect()); + this.getSpellAbility().addTarget(new TargetSpell(filter)); + + // • Destroy target creature with converted mana cost less than or equal to the number of cards in its controller's graveyard. + Mode mode = new Mode(new DestroyTargetEffect()); + mode.addTarget(new TargetPermanent(filter2)); + this.getSpellAbility().addMode(mode); + } + + private DrownInTheLoch(final DrownInTheLoch card) { + super(card); + } + + @Override + public DrownInTheLoch copy() { + return new DrownInTheLoch(this); + } +} + +enum DrownInTheLochPredicate implements Predicate { + instance; + + @Override + public boolean apply(MageObject input, Game game) { + Player player = game.getPlayer(game.getControllerId(input.getId())); + return player != null && input.getConvertedManaCost() <= player.getGraveyard().size(); + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 24e0093ad9..553c76a8f2 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -61,6 +61,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Dance of the Manse", 186, Rarity.RARE, mage.cards.d.DanceOfTheManse.class)); cards.add(new SetCardInfo("Deafening Silence", 10, Rarity.UNCOMMON, mage.cards.d.DeafeningSilence.class)); cards.add(new SetCardInfo("Doom Foretold", 187, Rarity.RARE, mage.cards.d.DoomForetold.class)); + cards.add(new SetCardInfo("Drown in the Loch", 188, Rarity.UNCOMMON, mage.cards.d.DrownInTheLoch.class)); cards.add(new SetCardInfo("Edgewall Innkeeper", 151, Rarity.UNCOMMON, mage.cards.e.EdgewallInnkeeper.class)); cards.add(new SetCardInfo("Elite Headhunter", 209, Rarity.UNCOMMON, mage.cards.e.EliteHeadhunter.class)); cards.add(new SetCardInfo("Embercleave", 120, Rarity.MYTHIC, mage.cards.e.Embercleave.class)); From 56c68a9d9f8c7b5e07a37b3d7fecca95307a3505 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 16 Sep 2019 09:53:07 -0400 Subject: [PATCH 146/373] Implemented Tall as a Beanstalk --- .../src/mage/cards/t/TallAsABeanstalk.java | 57 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 58 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/t/TallAsABeanstalk.java diff --git a/Mage.Sets/src/mage/cards/t/TallAsABeanstalk.java b/Mage.Sets/src/mage/cards/t/TallAsABeanstalk.java new file mode 100644 index 0000000000..fbb5509206 --- /dev/null +++ b/Mage.Sets/src/mage/cards/t/TallAsABeanstalk.java @@ -0,0 +1,57 @@ +package mage.cards.t; + +import mage.abilities.Ability; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.effects.common.AttachEffect; +import mage.abilities.effects.common.continuous.AddCardSubtypeAttachedEffect; +import mage.abilities.effects.common.continuous.BoostEnchantedEffect; +import mage.abilities.effects.common.continuous.GainAbilityAttachedEffect; +import mage.abilities.keyword.EnchantAbility; +import mage.abilities.keyword.ReachAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.*; +import mage.target.TargetPermanent; +import mage.target.common.TargetCreaturePermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class TallAsABeanstalk extends CardImpl { + + public TallAsABeanstalk(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ENCHANTMENT}, "{3}{G}"); + + this.subtype.add(SubType.AURA); + + // Enchant creature + TargetPermanent auraTarget = new TargetCreaturePermanent(); + this.getSpellAbility().addTarget(auraTarget); + this.getSpellAbility().addEffect(new AttachEffect(Outcome.BoostCreature)); + Ability ability = new EnchantAbility(auraTarget.getTargetName()); + this.addAbility(ability); + + // Enchanted creature gets +3/+3, has reach, and is a Giant in addition to its other types. + ability = new SimpleStaticAbility( + new BoostEnchantedEffect(3, 3).setText("enchanted creature gets +3/+3,") + ); + ability.addEffect(new GainAbilityAttachedEffect( + ReachAbility.getInstance(), AttachmentType.AURA + ).setText("has reach,")); + ability.addEffect(new AddCardSubtypeAttachedEffect( + SubType.GIANT, Duration.WhileOnBattlefield, AttachmentType.AURA + ).setText("and is a Giant in addition to its other types")); + this.addAbility(ability); + } + + private TallAsABeanstalk(final TallAsABeanstalk card) { + super(card); + } + + @Override + public TallAsABeanstalk copy() { + return new TallAsABeanstalk(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 553c76a8f2..1e4e434fcf 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -178,6 +178,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Syr Elenora, the Discerning", 67, Rarity.UNCOMMON, mage.cards.s.SyrElenoraTheDiscerning.class)); cards.add(new SetCardInfo("Syr Gwyn, Hero of Ashvale", 330, Rarity.MYTHIC, mage.cards.s.SyrGwynHeroOfAshvale.class)); cards.add(new SetCardInfo("Syr Konrad, the Grim", 107, Rarity.UNCOMMON, mage.cards.s.SyrKonradTheGrim.class)); + cards.add(new SetCardInfo("Tall as a Beanstalk", 178, Rarity.COMMON, mage.cards.t.TallAsABeanstalk.class)); cards.add(new SetCardInfo("Taste of Death", 320, Rarity.RARE, mage.cards.t.TasteOfDeath.class)); cards.add(new SetCardInfo("The Circle of Loyalty", 9, Rarity.MYTHIC, mage.cards.t.TheCircleOfLoyalty.class)); cards.add(new SetCardInfo("The Magic Mirror", 51, Rarity.MYTHIC, mage.cards.t.TheMagicMirror.class)); From 64dcfb840da291f871a3ff480f98bbae6396c70b Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 16 Sep 2019 10:01:06 -0400 Subject: [PATCH 147/373] Implemented Giant Opportunity --- .../src/mage/cards/g/GiantOpportunity.java | 44 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + .../token/GiantOpportunityToken.java | 28 ++++++++++++ 3 files changed, 73 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/g/GiantOpportunity.java create mode 100644 Mage/src/main/java/mage/game/permanent/token/GiantOpportunityToken.java diff --git a/Mage.Sets/src/mage/cards/g/GiantOpportunity.java b/Mage.Sets/src/mage/cards/g/GiantOpportunity.java new file mode 100644 index 0000000000..0baf6ebb8b --- /dev/null +++ b/Mage.Sets/src/mage/cards/g/GiantOpportunity.java @@ -0,0 +1,44 @@ +package mage.cards.g; + +import mage.abilities.costs.common.SacrificeTargetCost; +import mage.abilities.effects.common.CreateTokenEffect; +import mage.abilities.effects.common.DoIfCostPaid; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.filter.common.FilterControlledPermanent; +import mage.game.permanent.token.FoodToken; +import mage.game.permanent.token.GiantOpportunityToken; +import mage.target.common.TargetControlledPermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class GiantOpportunity extends CardImpl { + + private static final FilterControlledPermanent filter = new FilterControlledPermanent(SubType.FOOD, "Foods"); + + public GiantOpportunity(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.SORCERY}, "{2}{G}"); + + // You may sacrifice two Foods. If you do, create a 7/7 green Giant creature token. Otherwise, create three Food tokens. + this.getSpellAbility().addEffect(new DoIfCostPaid( + new CreateTokenEffect(new GiantOpportunityToken()), + new CreateTokenEffect(new FoodToken(), 3), + new SacrificeTargetCost(new TargetControlledPermanent(2, filter)) + ).setText("You may sacrifice two Foods. If you do, create a 7/7 green Giant creature token. " + + "Otherwise, create three Food tokens.")); + } + + private GiantOpportunity(final GiantOpportunity card) { + super(card); + } + + @Override + public GiantOpportunity copy() { + return new GiantOpportunity(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 1e4e434fcf..dda7fa3739 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -91,6 +91,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Garrison Griffin", 305, Rarity.COMMON, mage.cards.g.GarrisonGriffin.class)); cards.add(new SetCardInfo("Garruk, Cursed Huntsman", 191, Rarity.MYTHIC, mage.cards.g.GarrukCursedHuntsman.class)); cards.add(new SetCardInfo("Giant Killer", 14, Rarity.RARE, mage.cards.g.GiantKiller.class)); + cards.add(new SetCardInfo("Giant Opportunity", 159, Rarity.UNCOMMON, mage.cards.g.GiantOpportunity.class)); cards.add(new SetCardInfo("Gilded Goose", 160, Rarity.RARE, mage.cards.g.GildedGoose.class)); cards.add(new SetCardInfo("Gingerbrute", 219, Rarity.COMMON, mage.cards.g.Gingerbrute.class)); cards.add(new SetCardInfo("Glass Casket", 15, Rarity.UNCOMMON, mage.cards.g.GlassCasket.class)); diff --git a/Mage/src/main/java/mage/game/permanent/token/GiantOpportunityToken.java b/Mage/src/main/java/mage/game/permanent/token/GiantOpportunityToken.java new file mode 100644 index 0000000000..d8bee08b4e --- /dev/null +++ b/Mage/src/main/java/mage/game/permanent/token/GiantOpportunityToken.java @@ -0,0 +1,28 @@ +package mage.game.permanent.token; + +import mage.MageInt; +import mage.constants.CardType; +import mage.constants.SubType; + +/** + * @author TheElk801 + */ +public final class GiantOpportunityToken extends TokenImpl { + + public GiantOpportunityToken() { + super("Giant", "7/7 green Giant creature token"); + cardType.add(CardType.CREATURE); + subtype.add(SubType.GIANT); + color.setGreen(true); + power = new MageInt(7); + toughness = new MageInt(7); + } + + private GiantOpportunityToken(final GiantOpportunityToken token) { + super(token); + } + + public GiantOpportunityToken copy() { + return new GiantOpportunityToken(this); + } +} From 0346e2103f521565333e1d07a16b8d65ed490d7e Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 16 Sep 2019 14:35:13 -0400 Subject: [PATCH 148/373] updated ELD spoiler --- Utils/mtg-cards-data.txt | 14 ++++++++++++++ 1 file changed, 14 insertions(+) diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index 423238ac88..74629abfa0 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -35994,6 +35994,7 @@ Swamp|Commander 2019|294|C||Basic Land - Swamp|||({T}: Add {B}.)| Mountain|Commander 2019|297|C||Basic Land - Mountain|||({T}: Add {R}.)| Forest|Commander 2019|300|C||Basic Land - Forest|||({T}: Add {G}.)| All That Glitters|Throne of Eldraine|2|U|{1}{W}|Enchantment - Aura|||Enchant creature$Enchanted creature gets +1/+1 for each artifact and/or enchantment you control.| +Ardenvale Paladin|Throne of Eldraine|4|C|{3}{W}|Creature - Human Knight|2|5|Adamant — If at least three white ana was spent to cast this spell, Ardenvale Paladin enters the battlefield with a +1/+1 counter on it.| Ardenvale Tactician|Throne of Eldraine|5|C|{1}{W}{W}|Creature - Human Knight|2|3|Flying| Dizzying Swoop|Throne of Eldraine|5|C|{1}{W}|Instant - Adventure|2|3|Tap up to two target creatures.| Bartered Cow|Throne of Eldraine|6|C|{3}{W}|Creature - Ox|3|3|When Bartered Cow dies or when you discard it, create a Food token.| @@ -36008,9 +36009,15 @@ Giant Killer|Throne of Eldraine|14|R|{W}|Creature - Human Peasant|1|2|{1}{W}, {T Glass Casket|Throne of Eldraine|15|U|{1}{W}|Artifact|||When Glass Casket enters the battlefield, exile target creature an opponent controls with converted mana cost 3 or less until Glass Casket leaves the battlefield.| Harmonious Archon|Throne of Eldraine|17|M|{4}{W}{W}|Creature - Archon|4|5|Flying$Non-Archon creatures have base power and toughness 3/3.$When Harmonious Archon enters the battlefield, create two 1/1 white Human creature tokens.| Knight of the Keep|Throne of Eldraine|19|C|{2}{W}|Creature - Human Knight|3|2|| +Linden, the Steadfast Queen|Throne of Eldraine|20|R|{W}{W}{W}|Legendary Creature - Human Noble|3|3|Vigilance$Whenever a white creature you control attacks, you gain 1 life.| +Lonesome Unicorn|Throne of Eldraine|21|C|{4}{W}|Creature - Unicorn|3|3|Vigilance| +Rider in Need|Throne of Eldraine|21|C|{2}{W}|Sorcery - Adventure|3|3|Create a 2/2 white Knight creature token with vigilance.| +Rally for the Throne|Throne of Eldraine|25|U|{2}{W}|Instant|||Create two 1/1 white Human creature tokens.$Adamant — If at least three white mana was spent to cast this spell, you gain 1 life for each creature you control.| Righteousness|Throne of Eldraine|27|U|{W}|Instant|||Target blocking creature gets +7/+7 until end of turn.| Shining Armor|Throne of Eldraine|29|C|{1}{W}|Artifact - Equipment|||Flash$When Shining Armor enters the battlefield, attach it to target Knight you control.$Equipped creature gets +0/+2 and has vigilance.$Equip {3}| Silverflame Ritual|Throne of Eldraine|30|C|{3}{W}|Sorcery|||Put a +1/+1 counter on each creature you control.$Adamant — If at least three white mana was spent to cast this spell, creatures you control gain vigilance until end of turn.| +On Alert|Throne of Eldraine|31|C|{2}{W}|Instant - Adventure|2|1|Target creature gets +2/+2 until end of turn. Untap it.| +Silverflame Squire|Throne of Eldraine|31|C|{1}{W}|Creature - Human Soldier|2|1|| Trapped in the Tower|Throne of Eldraine|33|C|{1}{W}|Enchantment - Aura|||Enchant creature without flying$Enchanted creature can't attack or block, and its activated abilities can't be activated.| True Love's Kiss|Throne of Eldraine|34|C|{2}{W}{W}|Instant|||Exile target artifact or enchantment.$Draw a card| Venerable Knight|Throne of Eldraine|35|U|{W}|Creature - Human Knight|2|1|When Venerable Knight dies, put a +1/+1 counter on target Knight you control.| @@ -36081,6 +36088,7 @@ Battle Display|Throne of Eldraine|122|U|{R}|Sorcery - Adventure|2|1|Destroy targ Embereth Shieldbreaker|Throne of Eldraine|122|U|{1}{R}|Creature - Human Knight|2|1|| Ferocity of the Wilds|Throne of Eldraine|123|U|{2}{R}|Enchantment|||Attacking non-Human creatures you control get +1/+0 and have trample.| Fervent Champion|Throne of Eldraine|124|R|{R}|Creature - Human Knight|1|1|First strike, haste$Whenever Fervent Champion attacks, another target attacking Knight you control gets +1/+0 until end of turn.$Equip abilities you activate that target Fervent Champion cost {3} less to activate.| +Fires of Invention|Throne of Eldraine|125|R|{3}{R}|Enchantment|||You can cast spells only during your turn and you can cast no more than two spells each turn.$You may cast spells with converted mana cost less than or equal to the number of lands you control without paying their mana costs.| Irencrag Feat|Throne of Eldraine|127|R|{1}{R}{R}{R}|Sorcery|||Add seven {R}. You can cast only one more spell this turn.| Joust|Throne of Eldraine|129|U|{1}{R}|Sorcery|||Choose target creature you control and target creature you don't control. The creature you control gets +2/+1 until end of turn if it's a Knight. Then those creatures fight each other.| Haggle|Throne of Eldraine|131|C|{R}|Instant - Adventure|2|3|You may discard a card. If you do, draw a card.| @@ -36110,6 +36118,7 @@ Fierce Witchstalker|Throne of Eldraine|154|C|{2}{G}{G}|Creature - Wolf|4|4|Tramp Flaxen Intruder|Throne of Eldraine|155|U|{G}|Creature - Human Berserker|1|2|Whenever Flaxen Intruder deals combat damage to a player, you may sacrifice it. When you do, destroy target artifact or enchantment.| Welcome Home|Throne of Eldraine|155|U|{5}{G}{G}|Sorcery - Adventure|1|2|Create three 2/2 green Bear creature tokens.| Garenbrig Paladin|Throne of Eldraine|157|C|{4}{G}|Creature - Giant Knight|4|4|Adamant — If at least three green mana was spent to cast this spell, Garenbrig Paladin enters the battlefield with a +1/+1 counter on it.$Garenbrig Paladin can't be blocked by creatures with power 2 or less.| +Garenbrig Squire|Throne of Eldraine|158|C|{1}{G}|Creature - Human Soldier|2|2|Whenever you cast a creature spell that has an Adventure, Garenbrig Squire gets +1/+1 until end of turn.| Giant Opportunity|Throne of Eldraine|159|U|{2}{G}|Sorcery|||You may sacrifice two Foods. If you do, create a 7/7 green Giant creature token. Otherwise, create three Food tokens.| Gilded Goose|Throne of Eldraine|160|R|{G}|Creature - Bird|0|2|Flying$When Gilded Goose enters the battlefield, create a Food token.${1}{G}, {T}: Create a Food token.${T}, Sacrifice a Food: Add one mana of any color.| Insatiable Appetite|Throne of Eldraine|162|C|{1}{G}|Instant|||You may sacrifice a Food. If you do, target creature gets +5/+5 until end of turn. Otherwise, that creature gets +3/+3 until end of turn.| @@ -36127,6 +36136,8 @@ Rosethorn Acolyte|Throne of Eldraine|174|C|{2}{G}|Creature - Elf Druid|2|3|{T}: Seasonal Ritual|Throne of Eldraine|174|C|{G}|Sorcery - Adventure|2|3|Add one mana of any color.| Tall as a Beanstalk|Throne of Eldraine|178|C|{3}{G}|Enchantment - Aura|||Enchant creature$Enchanted creature gets +3/+3, has reach, and is a Giant in addition to its other types.| Trail of Crumbs|Throne of Eldraine|179|U|{1}{G}|Enchantment|||When Trail of Crumbs enters the battlefield, create a Food token.$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.| +Oaken Boon|Throne of Eldraine|180|C|{3}{G}|Sorcery - Adventure|6|5|Put two +1/+1 counters on target creature.| +Tuinvale Treefolk|Throne of Eldraine|180|C|{5}{G}|Creature - Treefolk Druid|6|5|| Wicked Wolf|Throne of Eldraine|181|R|{2}{G}{G}|Creature - Wolf|3|3|When Wicked Wolf enters the battlefield, it fights up to one target creature you don't control.$Sacrifice a Food: Put a +1/+1 counter on Wicked Wolf. It gains indestructible until end of turn. Tap it.| Wildborn Preserver|Throne of Eldraine|182|R|{1}{G}|Creature - Elf Archer|2|2|Flash$Reach$Whenever another non-Human creature enters the battlefield under your control, you may pay {X}. When you do, put X +1/+1 counters on Wildborn Preserver.| Wildwood Tracker|Throne of Eldraine|183|C|{G}|Creature - Elf Warrior|1|1|Whenever Wildwood Tracker attacks or blocks, if you control another non-Human creature, Wildwood Tracker gets +1/+1 until end of turn.| @@ -36165,9 +36176,12 @@ Heraldic Banner|Throne of Eldraine|222|U|{3}|Artifact|||As Heraldic Banner enter Inquisitive Puppet|Throne of Eldraine|223|U|{1}|Artifact Creature - Construct|0|2|When Inquisitive Puppet enters the battlefield, scry 1.$Exile Inquisitive Puppet: Create a 1/1 white Human creature token.| Jousting Dummy|Throne of Eldraine|224|C|{2}|Artifact Creature - Scarecrow Knight|2|1|{3}: Jousting Dummy gets +1/+0 until end of turn.| Roving Keep|Throne of Eldraine|228|C|{7}|Artifact Creature - Wall|5|7|Defender${7}: Roving Keep gets +2/+0 and gains trample until end of turn. It can attack this turn as though it didn't have defender.| +Shambling Suit|Throne of Eldraine|230|U|{3}|Artifact Creature - Construct|*|3|Shambling Suit's power is equal to the number of artifacts and/or enchantments you control.| Sorcerous Spyglass|Throne of Eldraine|233|R|{2}|Artifact|||As Sorcerous Spyglass enters the battlefield, look at an opponent's hand, then choose any card name.$Activated abilities of sources with the chosen name can't be activated unless they're mana abilities.| Spinning Wheel|Throne of Eldraine|234|U|{3}|Artifact|||{T}: Add one mana of any color.${5}, {T}: Tap target creature.| +Stonecoil Serpent|Throne of Eldraine|235|R|{X}|Artifact Creature - Snake|0|0|Reach, trample, protection from multicolored$Stonecoil Serpent enters the battlefield with X +1/+1 counters on it.| Witch's Oven|Throne of Eldraine|237|U|{1}|Artifact|||{T}, Sacrifice a creature: Create a Food token. If the sacrificed creature's toughness was 4 or greater, create two Food tokens instead.| +Idyllic Grange|Throne of Eldraine|246|C||Land - Plains|||({T}: Add {W}.)$Idyllic Grange enters the battlefield tapped unless you control three or more other Plains.$When Idyllic Grange enters the battlefield untapped, put a +1/+1 counter on target creature you control.| Tournament Grounds|Throne of Eldraine|248|U||Land|||{T}: Add {C}.${T}: Add {R}, {W}, or {B}. Spend this mana only to cast a Knight or Equipment spell.| Witch's Cottage|Throne of Eldraine|249|C||Land - Swamp|||({T}: Add {B}.)$Witch's Cottage enters the battlefield tapped unless you control three or more other Swamps.$When Witch's Cottage enters the battlefield untapped, you may put target creature card from your graveyard on top of your library.| Kenrith, the Returned King|Throne of Eldraine|303|M|{4}{W}|Legendary Creature - Human Noble|5|5|{R}: All creatures gain trample and haste until end of turn.${1}{G}: Put a +1/+1 counter on target creature.${2}{W}: Target player gains 5 life.${3}{U}: Target player draws a card.${4}{B}: Put target creature card from a graveyard onto the battlefield under its owner's control.| From 56c2ace9c5b2b53aeb6b87c62ed7a0970154a553 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 16 Sep 2019 14:39:26 -0400 Subject: [PATCH 149/373] Implemented Linden, the Steadfast Queen --- .../mage/cards/l/LindenTheSteadfastQueen.java | 54 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 55 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/l/LindenTheSteadfastQueen.java diff --git a/Mage.Sets/src/mage/cards/l/LindenTheSteadfastQueen.java b/Mage.Sets/src/mage/cards/l/LindenTheSteadfastQueen.java new file mode 100644 index 0000000000..f016f227fa --- /dev/null +++ b/Mage.Sets/src/mage/cards/l/LindenTheSteadfastQueen.java @@ -0,0 +1,54 @@ +package mage.cards.l; + +import mage.MageInt; +import mage.ObjectColor; +import mage.abilities.common.AttacksCreatureYouControlTriggeredAbility; +import mage.abilities.effects.common.GainLifeEffect; +import mage.abilities.keyword.VigilanceAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.constants.SuperType; +import mage.filter.common.FilterControlledCreaturePermanent; +import mage.filter.predicate.mageobject.ColorPredicate; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class LindenTheSteadfastQueen extends CardImpl { + + private static final FilterControlledCreaturePermanent filter + = new FilterControlledCreaturePermanent("white creature you control"); + + static { + filter.add(new ColorPredicate(ObjectColor.WHITE)); + } + + public LindenTheSteadfastQueen(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{W}{W}{W}"); + + this.addSuperType(SuperType.LEGENDARY); + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.NOBLE); + this.power = new MageInt(3); + this.toughness = new MageInt(3); + + // Vigilance + this.addAbility(VigilanceAbility.getInstance()); + + // Whenever a white creature you control attacks, you gain 1 life. + this.addAbility(new AttacksCreatureYouControlTriggeredAbility(new GainLifeEffect(1), false, filter)); + } + + private LindenTheSteadfastQueen(final LindenTheSteadfastQueen card) { + super(card); + } + + @Override + public LindenTheSteadfastQueen copy() { + return new LindenTheSteadfastQueen(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index dda7fa3739..e016e2720c 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -114,6 +114,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Knight of the Keep", 19, Rarity.COMMON, mage.cards.k.KnightOfTheKeep.class)); cards.add(new SetCardInfo("Knights' Charge", 328, Rarity.RARE, mage.cards.k.KnightsCharge.class)); cards.add(new SetCardInfo("Korvold, Fae-Cursed King", 329, Rarity.MYTHIC, mage.cards.k.KorvoldFaeCursedKing.class)); + cards.add(new SetCardInfo("Linden, the Steadfast Queen", 20, Rarity.RARE, mage.cards.l.LindenTheSteadfastQueen.class)); cards.add(new SetCardInfo("Loch Dragon", 211, Rarity.UNCOMMON, mage.cards.l.LochDragon.class)); cards.add(new SetCardInfo("Lochmere Serpent", 195, Rarity.RARE, mage.cards.l.LochmereSerpent.class)); cards.add(new SetCardInfo("Lost Legion", 94, Rarity.COMMON, mage.cards.l.LostLegion.class)); From a6422d70d40f98cd68578899a8e7754b8578c037 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 16 Sep 2019 14:44:16 -0400 Subject: [PATCH 150/373] Implemented Rally for the Throne --- .../src/mage/cards/r/RallyForTheThrone.java | 49 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 50 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/r/RallyForTheThrone.java diff --git a/Mage.Sets/src/mage/cards/r/RallyForTheThrone.java b/Mage.Sets/src/mage/cards/r/RallyForTheThrone.java new file mode 100644 index 0000000000..86e39e86e9 --- /dev/null +++ b/Mage.Sets/src/mage/cards/r/RallyForTheThrone.java @@ -0,0 +1,49 @@ +package mage.cards.r; + +import mage.abilities.condition.common.AdamantCondition; +import mage.abilities.decorator.ConditionalOneShotEffect; +import mage.abilities.dynamicvalue.DynamicValue; +import mage.abilities.dynamicvalue.common.PermanentsOnBattlefieldCount; +import mage.abilities.effects.common.CreateTokenEffect; +import mage.abilities.effects.common.GainLifeEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.filter.StaticFilters; +import mage.game.permanent.token.HumanToken; +import mage.watchers.common.ManaSpentToCastWatcher; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class RallyForTheThrone extends CardImpl { + + private static final DynamicValue xValue + = new PermanentsOnBattlefieldCount(StaticFilters.FILTER_CONTROLLED_CREATURE); + + public RallyForTheThrone(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.INSTANT}, "{2}{W}"); + + // Create two 1/1 white Human creature tokens. + this.getSpellAbility().addEffect(new CreateTokenEffect(new HumanToken(), 2)); + + // Adamant — If at least three white mana was spent to cast this spell, you gain 1 life for each creature you control. + this.getSpellAbility().addEffect(new ConditionalOneShotEffect( + new GainLifeEffect(xValue), AdamantCondition.WHITE, "
Adamant — " + + "If at least three white mana was spent to cast this spell, " + + "you gain 1 life for each creature you control." + )); + this.getSpellAbility().addWatcher(new ManaSpentToCastWatcher()); + } + + private RallyForTheThrone(final RallyForTheThrone card) { + super(card); + } + + @Override + public RallyForTheThrone copy() { + return new RallyForTheThrone(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index e016e2720c..f7c5ef058f 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -144,6 +144,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Piper of the Swarm", 100, Rarity.RARE, mage.cards.p.PiperOfTheSwarm.class)); cards.add(new SetCardInfo("Questing Beast", 171, Rarity.MYTHIC, mage.cards.q.QuestingBeast.class)); cards.add(new SetCardInfo("Raging Redcap", 134, Rarity.COMMON, mage.cards.r.RagingRedcap.class)); + cards.add(new SetCardInfo("Rally for the Throne", 25, Rarity.UNCOMMON, mage.cards.r.RallyForTheThrone.class)); cards.add(new SetCardInfo("Rankle, Master of Pranks", 101, Rarity.MYTHIC, mage.cards.r.RankleMasterOfPranks.class)); cards.add(new SetCardInfo("Reave Soul", 103, Rarity.COMMON, mage.cards.r.ReaveSoul.class)); cards.add(new SetCardInfo("Redcap Melee", 135, Rarity.UNCOMMON, mage.cards.r.RedcapMelee.class)); From 6dbdfa4bbbb2e98a324a9a345a855b98cc05b925 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 16 Sep 2019 14:46:16 -0400 Subject: [PATCH 151/373] Implemented Ardenvale Paladin --- .../src/mage/cards/a/ArdenvalePaladin.java | 46 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 47 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/a/ArdenvalePaladin.java diff --git a/Mage.Sets/src/mage/cards/a/ArdenvalePaladin.java b/Mage.Sets/src/mage/cards/a/ArdenvalePaladin.java new file mode 100644 index 0000000000..4c93d78958 --- /dev/null +++ b/Mage.Sets/src/mage/cards/a/ArdenvalePaladin.java @@ -0,0 +1,46 @@ +package mage.cards.a; + +import mage.MageInt; +import mage.abilities.common.EntersBattlefieldAbility; +import mage.abilities.condition.common.AdamantCondition; +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.counters.CounterType; +import mage.watchers.common.ManaSpentToCastWatcher; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class ArdenvalePaladin extends CardImpl { + + public ArdenvalePaladin(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{3}{W}"); + + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.KNIGHT); + this.power = new MageInt(2); + this.toughness = new MageInt(5); + + // Adamant — If at least three white mana was spent to cast this spell, Ardenvale Paladin enters the battlefield with a +1/+1 counter on it. + this.addAbility(new EntersBattlefieldAbility( + new AddCountersSourceEffect(CounterType.P1P1.createInstance()), + AdamantCondition.WHITE, "
Adamant — " + + "If at least three white mana was spent to cast this spell, " + + "{this} enters the battlefield with a +1/+1 counter on it.", "" + ), new ManaSpentToCastWatcher()); + } + + private ArdenvalePaladin(final ArdenvalePaladin card) { + super(card); + } + + @Override + public ArdenvalePaladin copy() { + return new ArdenvalePaladin(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index f7c5ef058f..0b749d7029 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -33,6 +33,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Animating Faerie", 38, Rarity.UNCOMMON, mage.cards.a.AnimatingFaerie.class)); cards.add(new SetCardInfo("Arcane Signet", 331, Rarity.COMMON, mage.cards.a.ArcaneSignet.class)); cards.add(new SetCardInfo("Arcanist's Owl", 206, Rarity.UNCOMMON, mage.cards.a.ArcanistsOwl.class)); + cards.add(new SetCardInfo("Ardenvale Paladin", 4, Rarity.COMMON, mage.cards.a.ArdenvalePaladin.class)); cards.add(new SetCardInfo("Ardenvale Tactician", 5, Rarity.COMMON, mage.cards.a.ArdenvaleTactician.class)); cards.add(new SetCardInfo("Ayara, First of Locthwain", 75, Rarity.RARE, mage.cards.a.AyaraFirstOfLocthwain.class)); cards.add(new SetCardInfo("Bake into a Pie", 76, Rarity.COMMON, mage.cards.b.BakeIntoAPie.class)); From 44036f59393ca3b78298a72039d7bdf0b2ded26a Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 16 Sep 2019 15:05:56 -0400 Subject: [PATCH 152/373] Implemented Stonecoil Serpent --- .../src/mage/cards/s/StonecoilSerpent.java | 58 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 59 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/s/StonecoilSerpent.java diff --git a/Mage.Sets/src/mage/cards/s/StonecoilSerpent.java b/Mage.Sets/src/mage/cards/s/StonecoilSerpent.java new file mode 100644 index 0000000000..04ee0683b9 --- /dev/null +++ b/Mage.Sets/src/mage/cards/s/StonecoilSerpent.java @@ -0,0 +1,58 @@ +package mage.cards.s; + +import mage.MageInt; +import mage.abilities.common.EntersBattlefieldAbility; +import mage.abilities.effects.common.EntersBattlefieldWithXCountersEffect; +import mage.abilities.keyword.ProtectionAbility; +import mage.abilities.keyword.ReachAbility; +import mage.abilities.keyword.TrampleAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.counters.CounterType; +import mage.filter.FilterObject; +import mage.filter.predicate.mageobject.MulticoloredPredicate; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class StonecoilSerpent extends CardImpl { + + private static final FilterObject filter = new FilterObject("multicolored"); + + static { + filter.add(MulticoloredPredicate.instance); + } + + public StonecoilSerpent(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT, CardType.CREATURE}, "{X}"); + + this.subtype.add(SubType.SNAKE); + this.power = new MageInt(0); + this.toughness = new MageInt(0); + + // Reach + this.addAbility(ReachAbility.getInstance()); + + // Trample + this.addAbility(TrampleAbility.getInstance()); + + // Protection from multicolored + this.addAbility(new ProtectionAbility(filter)); + + // Stonecoil Serpent enters the battlefield with X +1/+1 counters on it. + this.addAbility(new EntersBattlefieldAbility(new EntersBattlefieldWithXCountersEffect(CounterType.P1P1.createInstance()))); + } + + private StonecoilSerpent(final StonecoilSerpent card) { + super(card); + } + + @Override + public StonecoilSerpent copy() { + return new StonecoilSerpent(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 0b749d7029..829b258ac9 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -178,6 +178,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Steelbane Hydra", 322, Rarity.RARE, mage.cards.s.SteelbaneHydra.class)); cards.add(new SetCardInfo("Steelclaw Lance", 202, Rarity.UNCOMMON, mage.cards.s.SteelclawLance.class)); cards.add(new SetCardInfo("Stolen by the Fae", 66, Rarity.RARE, mage.cards.s.StolenByTheFae.class)); + cards.add(new SetCardInfo("Stonecoil Serpent", 235, Rarity.RARE, mage.cards.s.StonecoilSerpent.class)); cards.add(new SetCardInfo("Syr Carah, the Bold", 145, Rarity.UNCOMMON, mage.cards.s.SyrCarahTheBold.class)); cards.add(new SetCardInfo("Syr Elenora, the Discerning", 67, Rarity.UNCOMMON, mage.cards.s.SyrElenoraTheDiscerning.class)); cards.add(new SetCardInfo("Syr Gwyn, Hero of Ashvale", 330, Rarity.MYTHIC, mage.cards.s.SyrGwynHeroOfAshvale.class)); From 0d1e29bcc1b3217ee194924c281494f046153ff8 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 16 Sep 2019 15:28:11 -0400 Subject: [PATCH 153/373] Implemented Shambling Suit --- Mage.Sets/src/mage/cards/s/ShamblingSuit.java | 50 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 51 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/s/ShamblingSuit.java diff --git a/Mage.Sets/src/mage/cards/s/ShamblingSuit.java b/Mage.Sets/src/mage/cards/s/ShamblingSuit.java new file mode 100644 index 0000000000..43efe5a380 --- /dev/null +++ b/Mage.Sets/src/mage/cards/s/ShamblingSuit.java @@ -0,0 +1,50 @@ +package mage.cards.s; + +import mage.MageInt; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.dynamicvalue.DynamicValue; +import mage.abilities.dynamicvalue.common.PermanentsOnBattlefieldCount; +import mage.abilities.effects.common.continuous.SetPowerSourceEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.*; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterArtifactOrEnchantmentPermanent; +import mage.filter.predicate.permanent.ControllerPredicate; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class ShamblingSuit extends CardImpl { + + private static final FilterPermanent filter + = new FilterArtifactOrEnchantmentPermanent("artifacts and/or enchantments you control"); + + static { + filter.add(new ControllerPredicate(TargetController.YOU)); + } + + private static final DynamicValue xValue = new PermanentsOnBattlefieldCount(filter); + + public ShamblingSuit(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT, CardType.CREATURE}, "{3}"); + + this.subtype.add(SubType.CONSTRUCT); + this.power = new MageInt(0); + this.toughness = new MageInt(3); + + // Shambling Suit's power is equal to the number of artifacts and/or enchantments you control. + this.addAbility(new SimpleStaticAbility(Zone.ALL, new SetPowerSourceEffect(xValue, Duration.EndOfGame))); + } + + private ShamblingSuit(final ShamblingSuit card) { + super(card); + } + + @Override + public ShamblingSuit copy() { + return new ShamblingSuit(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 829b258ac9..48206a6aa2 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -164,6 +164,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Scorching Dragonfire", 139, Rarity.COMMON, mage.cards.s.ScorchingDragonfire.class)); cards.add(new SetCardInfo("Searing Barrage", 140, Rarity.COMMON, mage.cards.s.SearingBarrage.class)); cards.add(new SetCardInfo("Seven Dwarves", 141, Rarity.COMMON, mage.cards.s.SevenDwarves.class)); + cards.add(new SetCardInfo("Shambling Suit", 230, Rarity.UNCOMMON, mage.cards.s.ShamblingSuit.class)); cards.add(new SetCardInfo("Shimmer Dragon", 317, Rarity.RARE, mage.cards.s.ShimmerDragon.class)); cards.add(new SetCardInfo("Shinechaser", 201, Rarity.UNCOMMON, mage.cards.s.Shinechaser.class)); cards.add(new SetCardInfo("Shining Armor", 29, Rarity.COMMON, mage.cards.s.ShiningArmor.class)); From 26c21379b7f46d88e667edbe7520d458a46e898e Mon Sep 17 00:00:00 2001 From: Matthaios Tsiridis Date: Mon, 16 Sep 2019 22:35:50 +0300 Subject: [PATCH 154/373] Implement Stonecoil Serpent --- .../src/mage/cards/s/StonecoilSerpent.java | 55 +++++++++++++++++++ 1 file changed, 55 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/s/StonecoilSerpent.java diff --git a/Mage.Sets/src/mage/cards/s/StonecoilSerpent.java b/Mage.Sets/src/mage/cards/s/StonecoilSerpent.java new file mode 100644 index 0000000000..74c9c5047b --- /dev/null +++ b/Mage.Sets/src/mage/cards/s/StonecoilSerpent.java @@ -0,0 +1,55 @@ +package mage.cards.s; + +import mage.MageInt; +import mage.abilities.common.EntersBattlefieldAbility; +import mage.abilities.effects.common.EntersBattlefieldWithXCountersEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.counters.CounterType; +import mage.abilities.keyword.ProtectionAbility; +import mage.filter.predicate.mageobject.MulticoloredPredicate; +import mage.filter.FilterObject; +import mage.abilities.keyword.ReachAbility; +import mage.abilities.keyword.TrampleAbility; + +import java.util.UUID; + +/** + * + * @author Tsirides + */ +public final class StonecoilSerpent extends CardImpl { + + private static final FilterObject filter = new FilterObject("multicolored"); + + static { + filter.add(MulticoloredPredicate.instance); + } + + public StonecoilSerpent(UUID ownerId, CardSetInfo setInfo) { + super(ownerId,setInfo,new CardType[]{CardType.ARTIFACT,CardType.CREATURE},"{X}"); + this.subtype.add(SubType.SNAKE); + this.power = new MageInt(0); + this.toughness = new MageInt(0); + + //Trample, Reach, Protection from Multicolored + this.addAbility(new ProtectionAbility(filter)); + this.addAbility(ReachAbility.getInstance()); + this.addAbility(TrampleAbility.getInstance()); + + + // Endless One enters the battlefield with X +1/+1 counters on it. + this.addAbility(new EntersBattlefieldAbility(new EntersBattlefieldWithXCountersEffect(CounterType.P1P1.createInstance()))); + } + + public StonecoilSerpent(final StonecoilSerpent card) { + super(card); + } + + @Override + public StonecoilSerpent copy() { + return new StonecoilSerpent(this); + } +} From 275d28d22cd4fbbd707cf68039b950dc56eb7136 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 16 Sep 2019 15:40:02 -0400 Subject: [PATCH 155/373] Implemented Idyllic Grange --- Mage.Sets/src/mage/cards/i/IdyllicGrange.java | 69 +++++++++++++++++++ Mage.Sets/src/mage/cards/w/WitchsCottage.java | 51 ++++---------- Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + ...rsBattlefieldUntappedTriggeredAbility.java | 39 +++++++++++ 4 files changed, 124 insertions(+), 36 deletions(-) create mode 100644 Mage.Sets/src/mage/cards/i/IdyllicGrange.java create mode 100644 Mage/src/main/java/mage/abilities/common/EntersBattlefieldUntappedTriggeredAbility.java diff --git a/Mage.Sets/src/mage/cards/i/IdyllicGrange.java b/Mage.Sets/src/mage/cards/i/IdyllicGrange.java new file mode 100644 index 0000000000..50b1d4bfc6 --- /dev/null +++ b/Mage.Sets/src/mage/cards/i/IdyllicGrange.java @@ -0,0 +1,69 @@ +package mage.cards.i; + +import mage.abilities.Ability; +import mage.abilities.common.EntersBattlefieldAbility; +import mage.abilities.common.EntersBattlefieldUntappedTriggeredAbility; +import mage.abilities.condition.Condition; +import mage.abilities.condition.common.PermanentsOnTheBattlefieldCondition; +import mage.abilities.decorator.ConditionalOneShotEffect; +import mage.abilities.effects.common.TapSourceEffect; +import mage.abilities.effects.common.counter.AddCountersTargetEffect; +import mage.abilities.mana.WhiteManaAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.ComparisonType; +import mage.constants.SubType; +import mage.counters.CounterType; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterControlledPermanent; +import mage.filter.predicate.permanent.AnotherPredicate; +import mage.target.common.TargetControlledCreaturePermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class IdyllicGrange extends CardImpl { + + private static final FilterPermanent filter + = new FilterControlledPermanent(SubType.PLAINS); + + static { + filter.add(AnotherPredicate.instance); + } + private static final Condition condition + = new PermanentsOnTheBattlefieldCondition(filter, ComparisonType.FEWER_THAN, 3); + + public IdyllicGrange(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.LAND}, ""); + + this.subtype.add(SubType.PLAINS); + + // ({T}: Add {W}.) + this.addAbility(new WhiteManaAbility()); + + // Idyllic Grange enters the battlefield tapped unless you control three or more other Plains. + this.addAbility(new EntersBattlefieldAbility( + new ConditionalOneShotEffect(new TapSourceEffect(), condition), + "tapped unless you control three or more other Plains" + )); + + // When Idyllic Grange enters the battlefield untapped, put a +1/+1 counter on target creature you control. + Ability ability = new EntersBattlefieldUntappedTriggeredAbility( + new AddCountersTargetEffect(CounterType.P1P1.createInstance()), false + ); + ability.addTarget(new TargetControlledCreaturePermanent()); + this.addAbility(ability); + } + + private IdyllicGrange(final IdyllicGrange card) { + super(card); + } + + @Override + public IdyllicGrange copy() { + return new IdyllicGrange(this); + } +} diff --git a/Mage.Sets/src/mage/cards/w/WitchsCottage.java b/Mage.Sets/src/mage/cards/w/WitchsCottage.java index 9c78e1429c..bf659a2d3b 100644 --- a/Mage.Sets/src/mage/cards/w/WitchsCottage.java +++ b/Mage.Sets/src/mage/cards/w/WitchsCottage.java @@ -1,7 +1,8 @@ package mage.cards.w; +import mage.abilities.Ability; import mage.abilities.common.EntersBattlefieldAbility; -import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.common.EntersBattlefieldUntappedTriggeredAbility; import mage.abilities.condition.Condition; import mage.abilities.condition.common.PermanentsOnTheBattlefieldCondition; import mage.abilities.decorator.ConditionalOneShotEffect; @@ -16,9 +17,7 @@ import mage.constants.SubType; import mage.filter.FilterPermanent; import mage.filter.StaticFilters; import mage.filter.common.FilterControlledPermanent; -import mage.game.Game; -import mage.game.events.GameEvent; -import mage.game.permanent.Permanent; +import mage.filter.predicate.permanent.AnotherPredicate; import mage.target.common.TargetCardInYourGraveyard; import java.util.UUID; @@ -30,6 +29,11 @@ public final class WitchsCottage extends CardImpl { private static final FilterPermanent filter = new FilterControlledPermanent(SubType.SWAMP); + + static { + filter.add(AnotherPredicate.instance); + } + private static final Condition condition = new PermanentsOnTheBattlefieldCondition(filter, ComparisonType.FEWER_THAN, 3); @@ -48,7 +52,13 @@ public final class WitchsCottage extends CardImpl { )); // When Witch's Cottage enters the battlefield untapped, you may put target creature card from your graveyard on top of your library. - this.addAbility(new WitchsCottageTriggeredAbility()); + Ability ability = new EntersBattlefieldUntappedTriggeredAbility( + new PutOnLibraryTargetEffect(true) + .setText("put target creature card from your graveyard on top of your library"), + true + ); + ability.addTarget(new TargetCardInYourGraveyard(StaticFilters.FILTER_CARD_CREATURE_YOUR_GRAVEYARD)); + this.addAbility(ability); } private WitchsCottage(final WitchsCottage card) { @@ -60,34 +70,3 @@ public final class WitchsCottage extends CardImpl { return new WitchsCottage(this); } } - -class WitchsCottageTriggeredAbility extends EntersBattlefieldTriggeredAbility { - - WitchsCottageTriggeredAbility() { - super(new PutOnLibraryTargetEffect(true), true); - this.addTarget(new TargetCardInYourGraveyard(StaticFilters.FILTER_CARD_CREATURE_YOUR_GRAVEYARD)); - } - - private WitchsCottageTriggeredAbility(final WitchsCottageTriggeredAbility ability) { - super(ability); - } - - @Override - public WitchsCottageTriggeredAbility copy() { - return new WitchsCottageTriggeredAbility(this); - } - - @Override - public boolean checkTrigger(GameEvent event, Game game) { - if (!super.checkTrigger(event, game)) { - return false; - } - Permanent permanent = game.getPermanent(event.getTargetId()); - return permanent != null && permanent.isTapped(); - } - - @Override - public String getRule() { - return "When {this} enters the battlefield untapped, you may put target creature card from your graveyard on top of your library."; - } -} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 48206a6aa2..23038c1507 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -103,6 +103,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Henge Walker", 221, Rarity.COMMON, mage.cards.h.HengeWalker.class)); cards.add(new SetCardInfo("Heraldic Banner", 222, Rarity.UNCOMMON, mage.cards.h.HeraldicBanner.class)); cards.add(new SetCardInfo("Hypnotic Sprite", 49, Rarity.UNCOMMON, mage.cards.h.HypnoticSprite.class)); + cards.add(new SetCardInfo("Idyllic Grange", 246, Rarity.COMMON, mage.cards.i.IdyllicGrange.class)); cards.add(new SetCardInfo("Inquisitive Puppet", 223, Rarity.UNCOMMON, mage.cards.i.InquisitivePuppet.class)); cards.add(new SetCardInfo("Insatiable Appetite", 162, Rarity.COMMON, mage.cards.i.InsatiableAppetite.class)); cards.add(new SetCardInfo("Inspiring Veteran", 194, Rarity.UNCOMMON, mage.cards.i.InspiringVeteran.class)); diff --git a/Mage/src/main/java/mage/abilities/common/EntersBattlefieldUntappedTriggeredAbility.java b/Mage/src/main/java/mage/abilities/common/EntersBattlefieldUntappedTriggeredAbility.java new file mode 100644 index 0000000000..687fa4dfa6 --- /dev/null +++ b/Mage/src/main/java/mage/abilities/common/EntersBattlefieldUntappedTriggeredAbility.java @@ -0,0 +1,39 @@ +package mage.abilities.common; + +import mage.abilities.effects.Effect; +import mage.game.Game; +import mage.game.events.GameEvent; +import mage.game.permanent.Permanent; + +/** + * @author TheElk801 + */ +public class EntersBattlefieldUntappedTriggeredAbility extends EntersBattlefieldTriggeredAbility { + + public EntersBattlefieldUntappedTriggeredAbility(Effect effect, boolean optional) { + super(effect, optional); + } + + private EntersBattlefieldUntappedTriggeredAbility(final EntersBattlefieldUntappedTriggeredAbility ability) { + super(ability); + } + + @Override + public EntersBattlefieldUntappedTriggeredAbility copy() { + return new EntersBattlefieldUntappedTriggeredAbility(this); + } + + @Override + public boolean checkTrigger(GameEvent event, Game game) { + if (!super.checkTrigger(event, game)) { + return false; + } + Permanent permanent = game.getPermanent(event.getTargetId()); + return permanent != null && permanent.isTapped(); + } + + @Override + public String getRule() { + return "When {this} enters the battlefield untapped, " + super.getRule(); + } +} \ No newline at end of file From 8ded83d3feca9c800c1a975bc8e1a229012d65e7 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 16 Sep 2019 15:42:13 -0400 Subject: [PATCH 156/373] Implemented Garenbrig Squire --- .../src/mage/cards/g/GarenbrigSquire.java | 51 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 52 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/g/GarenbrigSquire.java diff --git a/Mage.Sets/src/mage/cards/g/GarenbrigSquire.java b/Mage.Sets/src/mage/cards/g/GarenbrigSquire.java new file mode 100644 index 0000000000..29c9d887f3 --- /dev/null +++ b/Mage.Sets/src/mage/cards/g/GarenbrigSquire.java @@ -0,0 +1,51 @@ +package mage.cards.g; + +import mage.MageInt; +import mage.abilities.common.SpellCastControllerTriggeredAbility; +import mage.abilities.effects.common.continuous.BoostSourceEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; +import mage.filter.FilterSpell; +import mage.filter.common.FilterCreatureSpell; +import mage.filter.predicate.mageobject.AdventurePredicate; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class GarenbrigSquire extends CardImpl { + + private static final FilterSpell filter + = new FilterCreatureSpell("a creature spell that has an Adventure"); + + static { + filter.add(AdventurePredicate.instance); + } + + public GarenbrigSquire(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{1}{G}"); + + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.SOLDIER); + this.power = new MageInt(2); + this.toughness = new MageInt(2); + + // Whenever you cast a creature spell that has an Adventure, Garenbrig Squire gets +1/+1 until end of turn. + this.addAbility(new SpellCastControllerTriggeredAbility( + new BoostSourceEffect(1, 1, Duration.EndOfTurn), filter, false + )); + } + + private GarenbrigSquire(final GarenbrigSquire card) { + super(card); + } + + @Override + public GarenbrigSquire copy() { + return new GarenbrigSquire(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 23038c1507..9b57e8523b 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -89,6 +89,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Frogify", 47, Rarity.UNCOMMON, mage.cards.f.Frogify.class)); cards.add(new SetCardInfo("Gadwick, the Wizened", 48, Rarity.RARE, mage.cards.g.GadwickTheWizened.class)); cards.add(new SetCardInfo("Garenbrig Paladin", 157, Rarity.COMMON, mage.cards.g.GarenbrigPaladin.class)); + cards.add(new SetCardInfo("Garenbrig Squire", 158, Rarity.COMMON, mage.cards.g.GarenbrigSquire.class)); cards.add(new SetCardInfo("Garrison Griffin", 305, Rarity.COMMON, mage.cards.g.GarrisonGriffin.class)); cards.add(new SetCardInfo("Garruk, Cursed Huntsman", 191, Rarity.MYTHIC, mage.cards.g.GarrukCursedHuntsman.class)); cards.add(new SetCardInfo("Giant Killer", 14, Rarity.RARE, mage.cards.g.GiantKiller.class)); From a6a21c6858e2098bd01670ef4e65560ccad80f1f Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 16 Sep 2019 15:47:39 -0400 Subject: [PATCH 157/373] remove Stonecoil Serpent --- .../src/mage/cards/s/StonecoilSerpent.java | 58 ------------------- Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 - 2 files changed, 59 deletions(-) delete mode 100644 Mage.Sets/src/mage/cards/s/StonecoilSerpent.java diff --git a/Mage.Sets/src/mage/cards/s/StonecoilSerpent.java b/Mage.Sets/src/mage/cards/s/StonecoilSerpent.java deleted file mode 100644 index 04ee0683b9..0000000000 --- a/Mage.Sets/src/mage/cards/s/StonecoilSerpent.java +++ /dev/null @@ -1,58 +0,0 @@ -package mage.cards.s; - -import mage.MageInt; -import mage.abilities.common.EntersBattlefieldAbility; -import mage.abilities.effects.common.EntersBattlefieldWithXCountersEffect; -import mage.abilities.keyword.ProtectionAbility; -import mage.abilities.keyword.ReachAbility; -import mage.abilities.keyword.TrampleAbility; -import mage.cards.CardImpl; -import mage.cards.CardSetInfo; -import mage.constants.CardType; -import mage.constants.SubType; -import mage.counters.CounterType; -import mage.filter.FilterObject; -import mage.filter.predicate.mageobject.MulticoloredPredicate; - -import java.util.UUID; - -/** - * @author TheElk801 - */ -public final class StonecoilSerpent extends CardImpl { - - private static final FilterObject filter = new FilterObject("multicolored"); - - static { - filter.add(MulticoloredPredicate.instance); - } - - public StonecoilSerpent(UUID ownerId, CardSetInfo setInfo) { - super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT, CardType.CREATURE}, "{X}"); - - this.subtype.add(SubType.SNAKE); - this.power = new MageInt(0); - this.toughness = new MageInt(0); - - // Reach - this.addAbility(ReachAbility.getInstance()); - - // Trample - this.addAbility(TrampleAbility.getInstance()); - - // Protection from multicolored - this.addAbility(new ProtectionAbility(filter)); - - // Stonecoil Serpent enters the battlefield with X +1/+1 counters on it. - this.addAbility(new EntersBattlefieldAbility(new EntersBattlefieldWithXCountersEffect(CounterType.P1P1.createInstance()))); - } - - private StonecoilSerpent(final StonecoilSerpent card) { - super(card); - } - - @Override - public StonecoilSerpent copy() { - return new StonecoilSerpent(this); - } -} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 9b57e8523b..4209664fc5 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -181,7 +181,6 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Steelbane Hydra", 322, Rarity.RARE, mage.cards.s.SteelbaneHydra.class)); cards.add(new SetCardInfo("Steelclaw Lance", 202, Rarity.UNCOMMON, mage.cards.s.SteelclawLance.class)); cards.add(new SetCardInfo("Stolen by the Fae", 66, Rarity.RARE, mage.cards.s.StolenByTheFae.class)); - cards.add(new SetCardInfo("Stonecoil Serpent", 235, Rarity.RARE, mage.cards.s.StonecoilSerpent.class)); cards.add(new SetCardInfo("Syr Carah, the Bold", 145, Rarity.UNCOMMON, mage.cards.s.SyrCarahTheBold.class)); cards.add(new SetCardInfo("Syr Elenora, the Discerning", 67, Rarity.UNCOMMON, mage.cards.s.SyrElenoraTheDiscerning.class)); cards.add(new SetCardInfo("Syr Gwyn, Hero of Ashvale", 330, Rarity.MYTHIC, mage.cards.s.SyrGwynHeroOfAshvale.class)); From ce920fa5421f4e0ca2de8b0a13418b83da99bb80 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 16 Sep 2019 16:13:40 -0400 Subject: [PATCH 158/373] Implemented Fires of Invention --- .../src/mage/cards/f/FiresOfInvention.java | 99 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + ...stFromHandWithoutPayingManaCostEffect.java | 42 ++++++-- .../main/java/mage/filter/StaticFilters.java | 7 ++ 4 files changed, 139 insertions(+), 10 deletions(-) create mode 100644 Mage.Sets/src/mage/cards/f/FiresOfInvention.java diff --git a/Mage.Sets/src/mage/cards/f/FiresOfInvention.java b/Mage.Sets/src/mage/cards/f/FiresOfInvention.java new file mode 100644 index 0000000000..2c23f65279 --- /dev/null +++ b/Mage.Sets/src/mage/cards/f/FiresOfInvention.java @@ -0,0 +1,99 @@ +package mage.cards.f; + +import mage.MageObject; +import mage.abilities.Ability; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.effects.ContinuousRuleModifyingEffectImpl; +import mage.abilities.effects.common.continuous.CastFromHandWithoutPayingManaCostEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.Outcome; +import mage.filter.FilterCard; +import mage.filter.StaticFilters; +import mage.filter.predicate.ObjectSourcePlayer; +import mage.filter.predicate.ObjectSourcePlayerPredicate; +import mage.game.Game; +import mage.game.events.GameEvent; +import mage.watchers.common.CastSpellLastTurnWatcher; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class FiresOfInvention extends CardImpl { + + private static final FilterCard filter + = new FilterCard("spells with converted mana cost less than or equal to the number of lands you control"); + + static { + filter.add(FiresOfInventionPredicate.instance); + } + + public FiresOfInvention(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ENCHANTMENT}, "{3}{R}"); + + // You can cast spells only during your turn and you can cast no more than two spells each turn. + this.addAbility(new SimpleStaticAbility(new FiresOfInventionCastEffect())); + + // You may cast spells with converted mana cost less than or equal to the number of lands you control without paying their mana costs. + this.addAbility(new SimpleStaticAbility(new CastFromHandWithoutPayingManaCostEffect(filter, false))); + } + + private FiresOfInvention(final FiresOfInvention card) { + super(card); + } + + @Override + public FiresOfInvention copy() { + return new FiresOfInvention(this); + } +} + +enum FiresOfInventionPredicate implements ObjectSourcePlayerPredicate> { + instance; + + @Override + public boolean apply(ObjectSourcePlayer input, Game game) { + return input.getObject().getConvertedManaCost() <= + game.getBattlefield().countAll(StaticFilters.FILTER_LAND, game.getControllerId(input.getSourceId()), game); + } +} + +class FiresOfInventionCastEffect extends ContinuousRuleModifyingEffectImpl { + + FiresOfInventionCastEffect() { + super(Duration.WhileOnBattlefield, Outcome.Detriment); + staticText = "you can cast spells only during your turn and you can cast no more than two spells each turn"; + } + + private FiresOfInventionCastEffect(final FiresOfInventionCastEffect effect) { + super(effect); + } + + @Override + public FiresOfInventionCastEffect copy() { + return new FiresOfInventionCastEffect(this); + } + + @Override + public boolean checksEventType(GameEvent event, Game game) { + return event.getType() == GameEvent.EventType.CAST_SPELL; + } + + @Override + public boolean applies(GameEvent event, Ability source, Game game) { + if (!event.getPlayerId().equals(source.getControllerId())) { + return false; + } + CastSpellLastTurnWatcher watcher = game.getState().getWatcher(CastSpellLastTurnWatcher.class); + if (watcher == null) { + return false; + } + return watcher.getAmountOfSpellsPlayerCastOnCurrentTurn(source.getControllerId()) > 2 + || !game.getActivePlayerId().equals(source.getControllerId()); + } + +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 4209664fc5..003a9e6a08 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -83,6 +83,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Fervent Champion", 124, Rarity.RARE, mage.cards.f.FerventChampion.class)); cards.add(new SetCardInfo("Fierce Witchstalker", 154, Rarity.COMMON, mage.cards.f.FierceWitchstalker.class)); cards.add(new SetCardInfo("Fireborn Knight", 210, Rarity.UNCOMMON, mage.cards.f.FirebornKnight.class)); + cards.add(new SetCardInfo("Fires of Invention", 125, Rarity.RARE, mage.cards.f.FiresOfInvention.class)); cards.add(new SetCardInfo("Flaxen Intruder", 155, Rarity.UNCOMMON, mage.cards.f.FlaxenIntruder.class)); cards.add(new SetCardInfo("Folio of Fancies", 46, Rarity.RARE, mage.cards.f.FolioOfFancies.class)); cards.add(new SetCardInfo("Foulmire Knight", 90, Rarity.UNCOMMON, mage.cards.f.FoulmireKnight.class)); diff --git a/Mage/src/main/java/mage/abilities/effects/common/continuous/CastFromHandWithoutPayingManaCostEffect.java b/Mage/src/main/java/mage/abilities/effects/common/continuous/CastFromHandWithoutPayingManaCostEffect.java index dcd3f9695e..a330989828 100644 --- a/Mage/src/main/java/mage/abilities/effects/common/continuous/CastFromHandWithoutPayingManaCostEffect.java +++ b/Mage/src/main/java/mage/abilities/effects/common/continuous/CastFromHandWithoutPayingManaCostEffect.java @@ -10,7 +10,8 @@ import mage.abilities.effects.ContinuousEffectImpl; import mage.cards.Card; import mage.cards.SplitCardHalf; import mage.constants.*; -import mage.filter.common.FilterNonlandCard; +import mage.filter.FilterCard; +import mage.filter.StaticFilters; import mage.game.Game; import mage.game.stack.Spell; import mage.players.Player; @@ -19,13 +20,26 @@ import java.util.UUID; public class CastFromHandWithoutPayingManaCostEffect extends ContinuousEffectImpl { + private final FilterCard filter; + private final boolean fromHand; + public CastFromHandWithoutPayingManaCostEffect() { - super(Duration.WhileOnBattlefield, Outcome.Detriment); - staticText = "You may cast nonland cards from your hand without paying their mana costs"; + this(StaticFilters.FILTER_CARDS_NON_LAND, true); } - public CastFromHandWithoutPayingManaCostEffect(final CastFromHandWithoutPayingManaCostEffect effect) { + public CastFromHandWithoutPayingManaCostEffect(FilterCard filter, boolean fromHand) { + super(Duration.WhileOnBattlefield, Outcome.Detriment); + this.filter = filter; + this.fromHand = fromHand; + staticText = "You may cast " + filter.getMessage() + + (fromHand ? " from your hand" : "") + + " without paying their mana costs"; + } + + private CastFromHandWithoutPayingManaCostEffect(final CastFromHandWithoutPayingManaCostEffect effect) { super(effect); + this.filter = effect.filter; + this.fromHand = effect.fromHand; } @Override @@ -36,12 +50,19 @@ public class CastFromHandWithoutPayingManaCostEffect extends ContinuousEffectImp @Override public boolean apply(Layer layer, SubLayer sublayer, Ability source, Game game) { Player controller = game.getPlayer(source.getControllerId()); - if (controller != null) { - controller.getAlternativeSourceCosts().add(new AlternativeCostSourceAbility( - null, new CompoundCondition(SourceIsSpellCondition.instance, new IsBeingCastFromHandCondition()), null, new FilterNonlandCard(), true)); - return true; + if (controller == null) { + return false; } - return false; + Condition condition; + if (fromHand) { + condition = new CompoundCondition(SourceIsSpellCondition.instance, IsBeingCastFromHandCondition.instance); + } else { + condition = SourceIsSpellCondition.instance; + } + controller.getAlternativeSourceCosts().add(new AlternativeCostSourceAbility( + null, condition, null, filter, true + )); + return true; } @Override @@ -55,7 +76,8 @@ public class CastFromHandWithoutPayingManaCostEffect extends ContinuousEffectImp } } -class IsBeingCastFromHandCondition implements Condition { +enum IsBeingCastFromHandCondition implements Condition { + instance; @Override public boolean apply(Game game, Ability source) { diff --git a/Mage/src/main/java/mage/filter/StaticFilters.java b/Mage/src/main/java/mage/filter/StaticFilters.java index 04807cef09..2888e8840a 100644 --- a/Mage/src/main/java/mage/filter/StaticFilters.java +++ b/Mage/src/main/java/mage/filter/StaticFilters.java @@ -133,6 +133,13 @@ public final class StaticFilters { FILTER_CARD_A_NON_LAND.setLockedFilter(true); } + + public static final FilterNonlandCard FILTER_CARDS_NON_LAND = new FilterNonlandCard("nonland cards"); + + static { + FILTER_CARDS_NON_LAND.setLockedFilter(true); + } + public static final FilterInstantOrSorceryCard FILTER_CARD_INSTANT_OR_SORCERY = new FilterInstantOrSorceryCard(); static { From 1aa7dcedd917cf7dd26d3f8fc1e05df28452a70f Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 16 Sep 2019 16:27:38 -0400 Subject: [PATCH 159/373] Implemented Lonesome Unicorn --- .../src/mage/cards/l/LonesomeUnicorn.java | 42 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 43 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/l/LonesomeUnicorn.java diff --git a/Mage.Sets/src/mage/cards/l/LonesomeUnicorn.java b/Mage.Sets/src/mage/cards/l/LonesomeUnicorn.java new file mode 100644 index 0000000000..ead17bfb3e --- /dev/null +++ b/Mage.Sets/src/mage/cards/l/LonesomeUnicorn.java @@ -0,0 +1,42 @@ +package mage.cards.l; + +import mage.MageInt; +import mage.abilities.effects.common.CreateTokenEffect; +import mage.abilities.keyword.VigilanceAbility; +import mage.cards.AdventureCard; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.game.permanent.token.KnightToken; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class LonesomeUnicorn extends AdventureCard { + + public LonesomeUnicorn(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, new CardType[]{CardType.SORCERY}, "{4}{W}", "Rider in Need", "{2}{W}"); + + this.subtype.add(SubType.UNICORN); + this.power = new MageInt(3); + this.toughness = new MageInt(3); + + // Vigilance + this.addAbility(VigilanceAbility.getInstance()); + + // Rider in Need + // Create a 2/2 white Knight creature token with vigilance. + this.getAdventureSpellAbility().addEffect(new CreateTokenEffect(new KnightToken())); + } + + private LonesomeUnicorn(final LonesomeUnicorn card) { + super(card); + } + + @Override + public LonesomeUnicorn copy() { + return new LonesomeUnicorn(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 003a9e6a08..0afc28b7dc 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -121,6 +121,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Linden, the Steadfast Queen", 20, Rarity.RARE, mage.cards.l.LindenTheSteadfastQueen.class)); cards.add(new SetCardInfo("Loch Dragon", 211, Rarity.UNCOMMON, mage.cards.l.LochDragon.class)); cards.add(new SetCardInfo("Lochmere Serpent", 195, Rarity.RARE, mage.cards.l.LochmereSerpent.class)); + cards.add(new SetCardInfo("Lonesome Unicorn", 21, Rarity.COMMON, mage.cards.l.LonesomeUnicorn.class)); cards.add(new SetCardInfo("Lost Legion", 94, Rarity.COMMON, mage.cards.l.LostLegion.class)); cards.add(new SetCardInfo("Lovestruck Beast", 165, Rarity.RARE, mage.cards.l.LovestruckBeast.class)); cards.add(new SetCardInfo("Mace of the Valiant", 314, Rarity.RARE, mage.cards.m.MaceOfTheValiant.class)); From b0249916349fcb64ce708fea3dee36af23f3392c Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 16 Sep 2019 16:30:54 -0400 Subject: [PATCH 160/373] Implemented Tuinvale Treefolk --- .../src/mage/cards/t/TuinvaleTreefolk.java | 41 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 42 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/t/TuinvaleTreefolk.java diff --git a/Mage.Sets/src/mage/cards/t/TuinvaleTreefolk.java b/Mage.Sets/src/mage/cards/t/TuinvaleTreefolk.java new file mode 100644 index 0000000000..117552adc9 --- /dev/null +++ b/Mage.Sets/src/mage/cards/t/TuinvaleTreefolk.java @@ -0,0 +1,41 @@ +package mage.cards.t; + +import mage.MageInt; +import mage.abilities.effects.common.counter.AddCountersTargetEffect; +import mage.cards.AdventureCard; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.counters.CounterType; +import mage.target.common.TargetCreaturePermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class TuinvaleTreefolk extends AdventureCard { + + public TuinvaleTreefolk(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, new CardType[]{CardType.SORCERY}, "{5}{G}", "Oaken Boon", "{3}{G}"); + + this.subtype.add(SubType.TREEFOLK); + this.subtype.add(SubType.DRUID); + this.power = new MageInt(6); + this.toughness = new MageInt(5); + + // Oaken Boon + // Put two +1/+1 counters on target creature. + this.getAdventureSpellAbility().addEffect(new AddCountersTargetEffect(CounterType.P1P1.createInstance(2))); + this.getAdventureSpellAbility().addTarget(new TargetCreaturePermanent()); + } + + private TuinvaleTreefolk(final TuinvaleTreefolk card) { + super(card); + } + + @Override + public TuinvaleTreefolk copy() { + return new TuinvaleTreefolk(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 0afc28b7dc..04e322ddab 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -201,6 +201,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Trail of Crumbs", 179, Rarity.UNCOMMON, mage.cards.t.TrailOfCrumbs.class)); cards.add(new SetCardInfo("Trapped in the Tower", 33, Rarity.COMMON, mage.cards.t.TrappedInTheTower.class)); cards.add(new SetCardInfo("True Love's Kiss", 34, Rarity.COMMON, mage.cards.t.TrueLovesKiss.class)); + cards.add(new SetCardInfo("Tuinvale Treefolk", 180, Rarity.COMMON, mage.cards.t.TuinvaleTreefolk.class)); cards.add(new SetCardInfo("Turn into a Pumpkin", 69, Rarity.UNCOMMON, mage.cards.t.TurnIntoAPumpkin.class)); cards.add(new SetCardInfo("Vantress Gargoyle", 71, Rarity.RARE, mage.cards.v.VantressGargoyle.class)); cards.add(new SetCardInfo("Venerable Knight", 35, Rarity.UNCOMMON, mage.cards.v.VenerableKnight.class)); From 0507388ef938197eb24fb940e5a2d3b9b4e901d8 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 16 Sep 2019 16:33:58 -0400 Subject: [PATCH 161/373] Implemented SIlverflame Squire --- .../src/mage/cards/s/SilverflameSquire.java | 43 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 44 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/s/SilverflameSquire.java diff --git a/Mage.Sets/src/mage/cards/s/SilverflameSquire.java b/Mage.Sets/src/mage/cards/s/SilverflameSquire.java new file mode 100644 index 0000000000..1e607a73ff --- /dev/null +++ b/Mage.Sets/src/mage/cards/s/SilverflameSquire.java @@ -0,0 +1,43 @@ +package mage.cards.s; + +import mage.MageInt; +import mage.abilities.effects.common.UntapTargetEffect; +import mage.abilities.effects.common.continuous.BoostTargetEffect; +import mage.cards.AdventureCard; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; +import mage.target.common.TargetCreaturePermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class SilverflameSquire extends AdventureCard { + + public SilverflameSquire(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, new CardType[]{CardType.INSTANT}, "{1}{W}", "On Alert", "{2}{W}"); + + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.SOLDIER); + this.power = new MageInt(2); + this.toughness = new MageInt(1); + + // On Alert + // Target creature gets +2/+2 until end of turn. Untap it. + this.getAdventureSpellAbility().addEffect(new BoostTargetEffect(2, 2, Duration.EndOfTurn)); + this.getAdventureSpellAbility().addEffect(new UntapTargetEffect().setText("Untap it")); + this.getAdventureSpellAbility().addTarget(new TargetCreaturePermanent()); + } + + private SilverflameSquire(final SilverflameSquire card) { + super(card); + } + + @Override + public SilverflameSquire copy() { + return new SilverflameSquire(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 04e322ddab..503146dd04 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -173,6 +173,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Shinechaser", 201, Rarity.UNCOMMON, mage.cards.s.Shinechaser.class)); cards.add(new SetCardInfo("Shining Armor", 29, Rarity.COMMON, mage.cards.s.ShiningArmor.class)); cards.add(new SetCardInfo("Silverflame Ritual", 30, Rarity.COMMON, mage.cards.s.SilverflameRitual.class)); + cards.add(new SetCardInfo("Silverflame Squire", 31, Rarity.COMMON, mage.cards.s.SilverflameSquire.class)); cards.add(new SetCardInfo("Silverwing Squadron", 315, Rarity.RARE, mage.cards.s.SilverwingSquadron.class)); cards.add(new SetCardInfo("Skullknocker Ogre", 142, Rarity.UNCOMMON, mage.cards.s.SkullknockerOgre.class)); cards.add(new SetCardInfo("Slaying Fire", 143, Rarity.UNCOMMON, mage.cards.s.SlayingFire.class)); From d746f89cde8d27478b5f3b52f1ceeab8658a3441 Mon Sep 17 00:00:00 2001 From: Matthaios Tsiridis Date: Tue, 17 Sep 2019 00:42:25 +0300 Subject: [PATCH 162/373] Implement Blacklance Paragon --- .../src/mage/cards/b/BlacklanceParagon.java | 61 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 62 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/b/BlacklanceParagon.java diff --git a/Mage.Sets/src/mage/cards/b/BlacklanceParagon.java b/Mage.Sets/src/mage/cards/b/BlacklanceParagon.java new file mode 100644 index 0000000000..8d0385d937 --- /dev/null +++ b/Mage.Sets/src/mage/cards/b/BlacklanceParagon.java @@ -0,0 +1,61 @@ + +package mage.cards.b; + +import java.util.UUID; +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.effects.common.continuous.GainAbilityTargetEffect; +import mage.abilities.effects.Effect; +import mage.abilities.keyword.DeathtouchAbility; +import mage.abilities.keyword.LifelinkAbility; +import mage.abilities.keyword.FlashAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; +import mage.filter.common.FilterCreaturePermanent; +import mage.target.common.TargetCreaturePermanent; + +/** + * + * @author LevelX2 + */ +public final class BlacklanceParagon extends CardImpl { + + private static final FilterCreaturePermanent filter = new FilterCreaturePermanent(SubType.KNIGHT, "knight"); + + public BlacklanceParagon(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{1}{B}"); + + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.KNIGHT); + this.power = new MageInt(3); + this.toughness = new MageInt(1); + + // Flash + this.addAbility(FlashAbility.getInstance()); + + + // When Blacklance Paragon enters the battlefield, target Knight gains deathtouch and lifelink until end of turn. + Effect effect = new GainAbilityTargetEffect(DeathtouchAbility.getInstance(), Duration.EndOfTurn); + effect.setText("target knight gains deathtouch"); + Ability ability = new EntersBattlefieldTriggeredAbility(effect); + effect = new GainAbilityTargetEffect(LifelinkAbility.getInstance(), Duration.EndOfTurn); + effect.setText("and lifelink until end of turn"); + ability.addEffect(effect); + ability.addTarget(new TargetCreaturePermanent(filter)); + this.addAbility(ability); + + } + + public BlacklanceParagon(final BlacklanceParagon card) { + super(card); + } + + @Override + public BlacklanceParagon copy() { + return new BlacklanceParagon(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 66d73aa2dc..3dc44ab7b8 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -42,6 +42,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Beanstalk Giant", 149, Rarity.UNCOMMON, mage.cards.b.BeanstalkGiant.class)); cards.add(new SetCardInfo("Belle of the Brawl", 78, Rarity.UNCOMMON, mage.cards.b.BelleOfTheBrawl.class)); cards.add(new SetCardInfo("Beloved Princess", 7, Rarity.COMMON, mage.cards.b.BelovedPrincess.class)); + cards.add(new SetCardInfo("Blacklance Paragon", 79, Rarity.RARE, mage.cards.b.BlacklanceParagon.class)); cards.add(new SetCardInfo("Blow Your House Down", 114, Rarity.COMMON, mage.cards.b.BlowYourHouseDown.class)); cards.add(new SetCardInfo("Bog Naughty", 80, Rarity.UNCOMMON, mage.cards.b.BogNaughty.class)); cards.add(new SetCardInfo("Bonecrusher Giant", 115, Rarity.RARE, mage.cards.b.BonecrusherGiant.class)); From f248a5ea3ebcc894aeb1af6b9ec0f7b3d490ff24 Mon Sep 17 00:00:00 2001 From: tsirides Date: Tue, 17 Sep 2019 01:21:55 +0300 Subject: [PATCH 163/373] Update BlacklanceParagon.java --- Mage.Sets/src/mage/cards/b/BlacklanceParagon.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Mage.Sets/src/mage/cards/b/BlacklanceParagon.java b/Mage.Sets/src/mage/cards/b/BlacklanceParagon.java index 8d0385d937..2e1555336c 100644 --- a/Mage.Sets/src/mage/cards/b/BlacklanceParagon.java +++ b/Mage.Sets/src/mage/cards/b/BlacklanceParagon.java @@ -20,7 +20,7 @@ import mage.target.common.TargetCreaturePermanent; /** * - * @author LevelX2 + * @author Tsirides */ public final class BlacklanceParagon extends CardImpl { From 7f9d08bdc36e7676d3e67924d56ba0491e494b4b Mon Sep 17 00:00:00 2001 From: tsirides Date: Tue, 17 Sep 2019 01:26:10 +0300 Subject: [PATCH 164/373] Update BlacklanceParagon.java --- Mage.Sets/src/mage/cards/b/BlacklanceParagon.java | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/Mage.Sets/src/mage/cards/b/BlacklanceParagon.java b/Mage.Sets/src/mage/cards/b/BlacklanceParagon.java index 2e1555336c..f7b066a634 100644 --- a/Mage.Sets/src/mage/cards/b/BlacklanceParagon.java +++ b/Mage.Sets/src/mage/cards/b/BlacklanceParagon.java @@ -24,7 +24,7 @@ import mage.target.common.TargetCreaturePermanent; */ public final class BlacklanceParagon extends CardImpl { - private static final FilterCreaturePermanent filter = new FilterCreaturePermanent(SubType.KNIGHT, "knight"); + private static final FilterCreaturePermanent filter = new FilterCreaturePermanent(SubType.KNIGHT, "Knight"); public BlacklanceParagon(UUID ownerId, CardSetInfo setInfo) { super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{1}{B}"); @@ -40,7 +40,7 @@ public final class BlacklanceParagon extends CardImpl { // When Blacklance Paragon enters the battlefield, target Knight gains deathtouch and lifelink until end of turn. Effect effect = new GainAbilityTargetEffect(DeathtouchAbility.getInstance(), Duration.EndOfTurn); - effect.setText("target knight gains deathtouch"); + effect.setText("target Knight gains deathtouch"); Ability ability = new EntersBattlefieldTriggeredAbility(effect); effect = new GainAbilityTargetEffect(LifelinkAbility.getInstance(), Duration.EndOfTurn); effect.setText("and lifelink until end of turn"); From 15b711e9d9f1eeca419911719e9bdaad46ae1307 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 16 Sep 2019 18:27:19 -0400 Subject: [PATCH 165/373] updated ELD spoiler --- Utils/mtg-cards-data.txt | 9 ++++++++- 1 file changed, 8 insertions(+), 1 deletion(-) diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index 74629abfa0..dd3f235d56 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -35994,7 +35994,7 @@ Swamp|Commander 2019|294|C||Basic Land - Swamp|||({T}: Add {B}.)| Mountain|Commander 2019|297|C||Basic Land - Mountain|||({T}: Add {R}.)| Forest|Commander 2019|300|C||Basic Land - Forest|||({T}: Add {G}.)| All That Glitters|Throne of Eldraine|2|U|{1}{W}|Enchantment - Aura|||Enchant creature$Enchanted creature gets +1/+1 for each artifact and/or enchantment you control.| -Ardenvale Paladin|Throne of Eldraine|4|C|{3}{W}|Creature - Human Knight|2|5|Adamant — If at least three white ana was spent to cast this spell, Ardenvale Paladin enters the battlefield with a +1/+1 counter on it.| +Ardenvale Paladin|Throne of Eldraine|4|C|{3}{W}|Creature - Human Knight|2|5|Adamant — If at least three white mana was spent to cast this spell, Ardenvale Paladin enters the battlefield with a +1/+1 counter on it.| Ardenvale Tactician|Throne of Eldraine|5|C|{1}{W}{W}|Creature - Human Knight|2|3|Flying| Dizzying Swoop|Throne of Eldraine|5|C|{1}{W}|Instant - Adventure|2|3|Tap up to two target creatures.| Bartered Cow|Throne of Eldraine|6|C|{3}{W}|Creature - Ox|3|3|When Bartered Cow dies or when you discard it, create a Food token.| @@ -36018,6 +36018,7 @@ Shining Armor|Throne of Eldraine|29|C|{1}{W}|Artifact - Equipment|||Flash$When S Silverflame Ritual|Throne of Eldraine|30|C|{3}{W}|Sorcery|||Put a +1/+1 counter on each creature you control.$Adamant — If at least three white mana was spent to cast this spell, creatures you control gain vigilance until end of turn.| On Alert|Throne of Eldraine|31|C|{2}{W}|Instant - Adventure|2|1|Target creature gets +2/+2 until end of turn. Untap it.| Silverflame Squire|Throne of Eldraine|31|C|{1}{W}|Creature - Human Soldier|2|1|| +Syr Alin, the Lion's Claw|Throne of Eldraine|32|U|{3}{W}{W}|Legendary Creature - Human Knight|4|4|First strike$Whenever Syr Alin, the Lion's Claw attacks, other creatures you control get +1/+1 until end of turn.| Trapped in the Tower|Throne of Eldraine|33|C|{1}{W}|Enchantment - Aura|||Enchant creature without flying$Enchanted creature can't attack or block, and its activated abilities can't be activated.| True Love's Kiss|Throne of Eldraine|34|C|{2}{W}{W}|Instant|||Exile target artifact or enchantment.$Draw a card| Venerable Knight|Throne of Eldraine|35|U|{W}|Creature - Human Knight|2|1|When Venerable Knight dies, put a +1/+1 counter on target Knight you control.| @@ -36039,6 +36040,7 @@ Mirrormade|Throne of Eldraine|55|R|{1}{U}{U}|Enchantment|||You may have Mirrorma Mistford River Turtle|Throne of Eldraine|56|C|{3}{U}|Creature - Turtle|1|5|Whenever Mistford River Turtle attacks, another target attacking non-Human creature can't be blocked this turn.| Mystical Dispute|Throne of Eldraine|58|U|{2}{U}|Instant|||This spell costs {2} less to cast if it targets a blue spell.$Counter target spell unless its controller pays {3}.| Opt|Throne of Eldraine|59|C|{U}|Instant|||Scry 1.$Draw a card.| +Overwhelmed Apprentice|Throne of Eldraine|60|U|{U}|Creature - Human Wizard|1|2|When Overwhelmed Apprentice enters the battlefield, each opponent puts the top two cards of their library into their graveyard. Then you scry 2.| Run Away Together|Throne of Eldraine|62|C|{1}{U}|Instant|||Choose two target creatures controlled by different players. Return those creatures to their owners' hands.| Stolen by the Fae|Throne of Eldraine|66|R|{X}{U}{U}|Sorcery|||Return target creature with converted mana cost X to its owner's hand. You create X 1/1 blue Faerie creature tokens with flying.| Syr Elenora, the Discerning|Throne of Eldraine|67|U|{3}{U}{U}|Legendary Creature - Human Knight|*|4|Syr Elenora, the Discerning's power is equal to the number of cards in your hand.$When Syr Elenora enters the battlefield, draw a card.$Spells your opponents cast that target Syr Elenora cost {2} more to cast.| @@ -36050,11 +36052,15 @@ Witching Well|Throne of Eldraine|74|C|{U}|Artifact|||When Witching Well enters t Ayara, First of Locthwain|Throne of Eldraine|75|R|{B}{B}{B}|Legendary Creature - Elf Noble|2|3|Whenever Ayara, First of Locthwain or another black creature enters the battlefield under your control, each opponent loses 1 life and you gain 1 life.${T}, Sacrifice another black creature: Draw a card.| Bake into a Pie|Throne of Eldraine|76|C|{2}{B}{B}|Instant|||Destroy target creature. Create a Food token.| Belle of the Brawl|Throne of Eldraine|78|U|{2}{B}|Creature - Human Knight|3|2|Menace$Whenever Belle of the Brawl attacks, other Knights you control get +1/+0 until end of turn.| +Blacklace Paragon|Throne of Eldraine|79|R|{1}{B}|Creature - Human Knight|3|1|Flash$When Blacklace Paragon enters the battlefield, target Knight gains deathtouch and lifelink until end of turn.| Bog Naughty|Throne of Eldraine|80|U|{3}{B}{B}|Creature - Faerie|3|3|Flying${2}{B}, Sacrifice a Food: Target creature gets -3/-3 until end of turn.| Cauldron Familiar|Throne of Eldraine|81|U|{B}|Creature - Cat|1|1|When Cauldron Familiar enters the battlefield, each opponent loses 1 life and you gain 1 life.$Sacrifice a Food: Return Cauldron Familiar from your graveyard to the battlefield.| +The Cauldron of Eternity|Throne of Eldraine|82|M|{10}{B}{B}|Legendary Artifact|||This spell costs {2} less for each creature card in your graveyard.$Whenever a creature you control dies, put it on the bottom of its owner's library.${2}{B}, {T}, Pay 2 life: Return target card from your graveyard to the battlefield. Activate this ability only any time you could cast a sorcery.| +Cauldron's Gift|Throne of Eldraine|83|U|{4}{B}|Sorcery|||Adamant — If at least three black mana was spent to cast this spell, put the top four cards of your library into your graveyard.$You may choose a creature card in your graveyard. If you do, return it to the battlefield with an additional +1/+1 counter on it.| Clackbridge Troll|Throne of Eldraine|84|R|{3}{B}{B}|Creature - Troll|8|8|Trample, haste$When Clackbridge Troll enters the battlefield, target opponent creates three 0/1 white Goat creature tokens.$At the beginning of combat on your turn, any opponent may sacrifice a creature. If a player does, tap Clackbridge Troll, you gain 3 life, and you draw a card.| Epic Downfall|Throne of Eldraine|85|U|{1}{B}|Sorcery|||Exile target creature with converted mana cost 3 or greater.| Eye Collector|Throne of Eldraine|86|C|{B}|Creature - Faerie|1|1|Flying$Whenever Eye Collector deals combat damage to a player, each player puts the top card of their library into their graveyard.| +Forever Young|Throne of Eldraine|89|C|{1}{B}|Sorcery|||Put any number of target creature cards from your graveyard on top of your library.$Draw a card.| Foulmire Knight|Throne of Eldraine|90|U|{B}|Creature - Zombie Knight|1|1|Deathtouch| Profane Insight|Throne of Eldraine|90|U|{2}{B}|Instant - Adventure|1|1|You draw a card and you lose 1 life.| Lost Legion|Throne of Eldraine|94|C|{1}{B}{B}|Creature - Spirit Knight|2|3|When Lost Legion enters the battlefield, scry 2.| @@ -36177,6 +36183,7 @@ Inquisitive Puppet|Throne of Eldraine|223|U|{1}|Artifact Creature - Construct|0| Jousting Dummy|Throne of Eldraine|224|C|{2}|Artifact Creature - Scarecrow Knight|2|1|{3}: Jousting Dummy gets +1/+0 until end of turn.| Roving Keep|Throne of Eldraine|228|C|{7}|Artifact Creature - Wall|5|7|Defender${7}: Roving Keep gets +2/+0 and gains trample until end of turn. It can attack this turn as though it didn't have defender.| Shambling Suit|Throne of Eldraine|230|U|{3}|Artifact Creature - Construct|*|3|Shambling Suit's power is equal to the number of artifacts and/or enchantments you control.| +Sorcerer's Broom|Throne of Eldraine|232|U|{2}|Artifact Creature - Spirit|2|1|Whenever you sacrifice another permanent, you may pay {3}. If you do, create a token that's a copy of Sorcerer's Broom.| Sorcerous Spyglass|Throne of Eldraine|233|R|{2}|Artifact|||As Sorcerous Spyglass enters the battlefield, look at an opponent's hand, then choose any card name.$Activated abilities of sources with the chosen name can't be activated unless they're mana abilities.| Spinning Wheel|Throne of Eldraine|234|U|{3}|Artifact|||{T}: Add one mana of any color.${5}, {T}: Tap target creature.| Stonecoil Serpent|Throne of Eldraine|235|R|{X}|Artifact Creature - Snake|0|0|Reach, trample, protection from multicolored$Stonecoil Serpent enters the battlefield with X +1/+1 counters on it.| From 7a43bbd5a9b1fbd12dd94a74358227b86743d9e6 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 16 Sep 2019 19:41:57 -0400 Subject: [PATCH 166/373] updated implementation of Hostage Taker --- Mage.Sets/src/mage/cards/h/HostageTaker.java | 111 ++++++++---------- .../src/mage/cards/r/RobberOfTheRich.java | 6 +- 2 files changed, 53 insertions(+), 64 deletions(-) diff --git a/Mage.Sets/src/mage/cards/h/HostageTaker.java b/Mage.Sets/src/mage/cards/h/HostageTaker.java index fd60803464..816ff40e09 100644 --- a/Mage.Sets/src/mage/cards/h/HostageTaker.java +++ b/Mage.Sets/src/mage/cards/h/HostageTaker.java @@ -1,6 +1,5 @@ package mage.cards.h; -import java.util.UUID; import mage.MageInt; import mage.abilities.Ability; import mage.abilities.common.EntersBattlefieldTriggeredAbility; @@ -12,17 +11,12 @@ import mage.abilities.effects.OneShotEffect; import mage.abilities.effects.common.CreateDelayedTriggeredAbilityEffect; import mage.cards.CardImpl; import mage.cards.CardSetInfo; -import mage.constants.AsThoughEffectType; -import mage.constants.CardType; -import mage.constants.Duration; -import mage.constants.ManaType; -import mage.constants.Outcome; -import mage.constants.SubType; -import mage.constants.Zone; +import mage.constants.*; import mage.filter.FilterPermanent; import mage.filter.predicate.Predicates; import mage.filter.predicate.mageobject.CardTypePredicate; import mage.filter.predicate.permanent.AnotherPredicate; +import mage.game.ExileZone; import mage.game.Game; import mage.game.permanent.Permanent; import mage.players.ManaPoolItem; @@ -31,8 +25,10 @@ import mage.target.TargetPermanent; import mage.target.targetpointer.FixedTarget; import mage.util.CardUtil; +import java.util.Objects; +import java.util.UUID; + /** - * * @author TheElk801 */ public final class HostageTaker extends CardImpl { @@ -43,7 +39,8 @@ public final class HostageTaker extends CardImpl { filter.add(AnotherPredicate.instance); filter.add(Predicates.or( new CardTypePredicate(CardType.ARTIFACT), - new CardTypePredicate(CardType.CREATURE))); + new CardTypePredicate(CardType.CREATURE) + )); } public HostageTaker(UUID ownerId, CardSetInfo setInfo) { @@ -55,13 +52,13 @@ public final class HostageTaker extends CardImpl { this.toughness = new MageInt(3); // When Hostage Taker enters the battlefield, exile another target artifact or creature until Hostage Taker leaves the battlefield. You may cast that card as long as it remains exiled, and you may spend mana as though it were mana of any type to cast that spell. - Ability ability = new EntersBattlefieldTriggeredAbility(new HostageTakerExileEffect(filter.getMessage())); + Ability ability = new EntersBattlefieldTriggeredAbility(new HostageTakerExileEffect()); ability.addTarget(new TargetPermanent(filter)); ability.addEffect(new CreateDelayedTriggeredAbilityEffect(new OnLeaveReturnExiledToBattlefieldAbility())); this.addAbility(ability); } - public HostageTaker(final HostageTaker card) { + private HostageTaker(final HostageTaker card) { super(card); } @@ -73,14 +70,14 @@ public final class HostageTaker extends CardImpl { class HostageTakerExileEffect extends OneShotEffect { - public HostageTakerExileEffect(String targetName) { + HostageTakerExileEffect() { super(Outcome.Benefit); this.staticText = "exile another target artifact or creature until {this} leaves the battlefield. " + "You may cast that card as long as it remains exiled, " + "and you may spend mana as though it were mana of any type to cast that spell"; } - public HostageTakerExileEffect(final HostageTakerExileEffect effect) { + private HostageTakerExileEffect(final HostageTakerExileEffect effect) { super(effect); } @@ -93,35 +90,41 @@ class HostageTakerExileEffect extends OneShotEffect { public boolean apply(Game game, Ability source) { Permanent card = game.getPermanent(getTargetPointer().getFirst(game, source)); Permanent permanent = game.getPermanent(source.getSourceId()); - if (permanent != null && card != null) { - Player controller = game.getPlayer(card.getControllerId()); - if (controller != null) { - // move card to exile - UUID exileId = CardUtil.getCardExileZoneId(game, source); - controller.moveCardToExileWithInfo(card, exileId, permanent.getIdName(), source.getSourceId(), game, Zone.BATTLEFIELD, true); - // allow to cast the card - ContinuousEffect effect = new HostageTakerCastFromExileEffect(); - effect.setTargetPointer(new FixedTarget(card.getId())); - game.addEffect(effect, source); - // and you may spend mana as though it were mana of any color to cast it - effect = new HostageTakerSpendAnyManaEffect(); - effect.setTargetPointer(new FixedTarget(card.getId())); - game.addEffect(effect, source); - } + if (permanent == null || card == null) { + return false; } + Player controller = game.getPlayer(card.getControllerId()); + if (controller == null) { + return false; + } + // move card to exile + UUID exileId = CardUtil.getCardExileZoneId(game, source); + controller.moveCardToExileWithInfo(card, exileId, permanent.getIdName(), source.getSourceId(), game, Zone.BATTLEFIELD, true); + // allow to cast the card + game.addEffect(new HostageTakerCastFromExileEffect(card.getId(), exileId), source); + // and you may spend mana as though it were mana of any color to cast it + ContinuousEffect effect = new HostageTakerSpendAnyManaEffect(); + effect.setTargetPointer(new FixedTarget(card.getId(), game)); + game.addEffect(effect, source); return false; } } class HostageTakerCastFromExileEffect extends AsThoughEffectImpl { - public HostageTakerCastFromExileEffect() { + private UUID cardId; + private UUID exileId; + + HostageTakerCastFromExileEffect(UUID cardId, UUID exileId) { super(AsThoughEffectType.PLAY_FROM_NOT_OWN_HAND_ZONE, Duration.Custom, Outcome.Benefit); - staticText = "You may cast that card for as long as it remains exiled, and you may spend mana as though it were mana of any color to cast that spell"; + this.cardId = cardId; + this.exileId = exileId; } - public HostageTakerCastFromExileEffect(final HostageTakerCastFromExileEffect effect) { + private HostageTakerCastFromExileEffect(final HostageTakerCastFromExileEffect effect) { super(effect); + this.cardId = effect.cardId; + this.exileId = effect.exileId; } @Override @@ -135,29 +138,26 @@ class HostageTakerCastFromExileEffect extends AsThoughEffectImpl { } @Override - public boolean applies(UUID objectId, Ability source, UUID affectedControllerId, Game game) { - if (objectId.equals(getTargetPointer().getFirst(game, source))) { - if (affectedControllerId.equals(source.getControllerId())) { - return true; - } - } else { - if (((FixedTarget) getTargetPointer()).getTarget().equals(objectId)) { - // object has moved zone so effect can be discarted - this.discard(); - } + public boolean applies(UUID sourceId, Ability source, UUID affectedControllerId, Game game) { + if (!sourceId.equals(cardId) || !source.isControlledBy(affectedControllerId)) { + return false; } + ExileZone exileZone = game.getState().getExile().getExileZone(exileId); + if (exileZone != null && exileZone.contains(cardId)) { + return true; + } + discard(); return false; } } class HostageTakerSpendAnyManaEffect extends AsThoughEffectImpl implements AsThoughManaEffect { - public HostageTakerSpendAnyManaEffect() { + HostageTakerSpendAnyManaEffect() { super(AsThoughEffectType.SPEND_OTHER_MANA, Duration.Custom, Outcome.Benefit); - staticText = "you may spend mana as though it were mana of any color to cast it"; } - public HostageTakerSpendAnyManaEffect(final HostageTakerSpendAnyManaEffect effect) { + private HostageTakerSpendAnyManaEffect(final HostageTakerSpendAnyManaEffect effect) { super(effect); } @@ -173,22 +173,11 @@ class HostageTakerSpendAnyManaEffect extends AsThoughEffectImpl implements AsTho @Override public boolean applies(UUID objectId, Ability source, UUID affectedControllerId, Game game) { - objectId = game.getCard(objectId).getMainCard().getId(); // for split cards - if (objectId.equals(((FixedTarget) getTargetPointer()).getTarget()) - && game.getState().getZoneChangeCounter(objectId) <= ((FixedTarget) getTargetPointer()).getZoneChangeCounter() + 1) { - if (affectedControllerId.equals(source.getControllerId())) { - // if the card moved from exile to spell the zone change counter is increased by 1 - if (game.getState().getZoneChangeCounter(objectId) == ((FixedTarget) getTargetPointer()).getZoneChangeCounter() + 1) { - return true; - } - } - } else { - if (((FixedTarget) getTargetPointer()).getTarget().equals(objectId)) { - // object has moved zone so effect can be discarted - this.discard(); - } - } - return false; + FixedTarget fixedTarget = ((FixedTarget) getTargetPointer()); + return source.isControlledBy(affectedControllerId) + && Objects.equals(objectId, fixedTarget.getTarget()) + && fixedTarget.getZoneChangeCounter() + 1 == game.getState().getZoneChangeCounter(objectId) + && game.getState().getZone(objectId) == Zone.STACK; } @Override diff --git a/Mage.Sets/src/mage/cards/r/RobberOfTheRich.java b/Mage.Sets/src/mage/cards/r/RobberOfTheRich.java index 783d97b909..923b51ecb1 100644 --- a/Mage.Sets/src/mage/cards/r/RobberOfTheRich.java +++ b/Mage.Sets/src/mage/cards/r/RobberOfTheRich.java @@ -194,10 +194,10 @@ class RobberOfTheRichSpendAnyManaEffect extends AsThoughEffectImpl implements As @Override public boolean applies(UUID objectId, Ability source, UUID affectedControllerId, Game game) { + FixedTarget fixedTarget = ((FixedTarget) getTargetPointer()); return source.isControlledBy(affectedControllerId) - && Objects.equals(objectId, ((FixedTarget) getTargetPointer()).getTarget()) - && ((FixedTarget) getTargetPointer()).getZoneChangeCounter() + 1 == game.getState().getZoneChangeCounter(objectId) - && (((FixedTarget) getTargetPointer()).getZoneChangeCounter() + 1 == game.getState().getZoneChangeCounter(objectId)) + && Objects.equals(objectId, fixedTarget.getTarget()) + && fixedTarget.getZoneChangeCounter() + 1 == game.getState().getZoneChangeCounter(objectId) && game.getState().getZone(objectId) == Zone.STACK; } From 1f8924c2a2752b0a6fa1cd0a7799ef163940a915 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 16 Sep 2019 19:54:10 -0400 Subject: [PATCH 167/373] Implemented Sorcerer's Broom --- .../src/mage/cards/s/SorcerersBroom.java | 75 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 76 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/s/SorcerersBroom.java diff --git a/Mage.Sets/src/mage/cards/s/SorcerersBroom.java b/Mage.Sets/src/mage/cards/s/SorcerersBroom.java new file mode 100644 index 0000000000..393347aafb --- /dev/null +++ b/Mage.Sets/src/mage/cards/s/SorcerersBroom.java @@ -0,0 +1,75 @@ +package mage.cards.s; + +import mage.MageInt; +import mage.abilities.TriggeredAbilityImpl; +import mage.abilities.costs.mana.GenericManaCost; +import mage.abilities.effects.CreateTokenCopySourceEffect; +import mage.abilities.effects.common.DoIfCostPaid; +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 java.util.UUID; + +/** + * @author TheElk801 + */ +public final class SorcerersBroom extends CardImpl { + + public SorcerersBroom(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT, CardType.CREATURE}, "{2}"); + + this.subtype.add(SubType.SPIRIT); + this.power = new MageInt(2); + 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()); + } + + private SorcerersBroom(final SorcerersBroom card) { + super(card); + } + + @Override + public SorcerersBroom copy() { + 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/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index fa6dcca2c4..3bf52b7555 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -179,6 +179,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Skullknocker Ogre", 142, Rarity.UNCOMMON, mage.cards.s.SkullknockerOgre.class)); cards.add(new SetCardInfo("Slaying Fire", 143, Rarity.UNCOMMON, mage.cards.s.SlayingFire.class)); cards.add(new SetCardInfo("Smitten Swordmaster", 105, Rarity.COMMON, mage.cards.s.SmittenSwordmaster.class)); + cards.add(new SetCardInfo("Sorcerer's Broom", 232, Rarity.UNCOMMON, mage.cards.s.SorcerersBroom.class)); cards.add(new SetCardInfo("Sorcerous Spyglass", 233, Rarity.RARE, mage.cards.s.SorcerousSpyglass.class)); cards.add(new SetCardInfo("Specter's Shriek", 106, Rarity.UNCOMMON, mage.cards.s.SpectersShriek.class)); cards.add(new SetCardInfo("Spinning Wheel", 234, Rarity.UNCOMMON, mage.cards.s.SpinningWheel.class)); From 87e8b67b2e43a62e34481c628aa226db714bb00e Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 16 Sep 2019 20:04:16 -0400 Subject: [PATCH 168/373] Implemented Forever Young --- Mage.Sets/src/mage/cards/f/ForeverYoung.java | 80 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + Utils/mtg-cards-data.txt | 2 +- 3 files changed, 82 insertions(+), 1 deletion(-) create mode 100644 Mage.Sets/src/mage/cards/f/ForeverYoung.java diff --git a/Mage.Sets/src/mage/cards/f/ForeverYoung.java b/Mage.Sets/src/mage/cards/f/ForeverYoung.java new file mode 100644 index 0000000000..abfe7a967f --- /dev/null +++ b/Mage.Sets/src/mage/cards/f/ForeverYoung.java @@ -0,0 +1,80 @@ +package mage.cards.f; + +import mage.abilities.Ability; +import mage.abilities.effects.OneShotEffect; +import mage.abilities.effects.common.DrawCardSourceControllerEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.cards.CardsImpl; +import mage.constants.CardType; +import mage.constants.Outcome; +import mage.filter.StaticFilters; +import mage.game.Game; +import mage.players.Player; +import mage.target.Target; +import mage.target.common.TargetCardInYourGraveyard; + +import java.util.Collection; +import java.util.UUID; +import java.util.stream.Collectors; + +/** + * @author TheElk801 + */ +public final class ForeverYoung extends CardImpl { + + public ForeverYoung(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.SORCERY}, "{1}{B}"); + + // Put any number of target creature cards from your graveyard on top of your library. + this.getSpellAbility().addEffect(new ForeverYoungEffect()); + this.getSpellAbility().addTarget(new TargetCardInYourGraveyard( + 0, Integer.MAX_VALUE, StaticFilters.FILTER_CARD_CREATURES_YOUR_GRAVEYARD + )); + + // Draw a card. + this.getSpellAbility().addEffect(new DrawCardSourceControllerEffect(1)); + } + + private ForeverYoung(final ForeverYoung card) { + super(card); + } + + @Override + public ForeverYoung copy() { + return new ForeverYoung(this); + } +} + +class ForeverYoungEffect extends OneShotEffect { + + ForeverYoungEffect() { + super(Outcome.Benefit); + staticText = "Put any number of target creature cards from your graveyard on top of your library."; + } + + private ForeverYoungEffect(final ForeverYoungEffect effect) { + super(effect); + } + + @Override + public ForeverYoungEffect copy() { + return new ForeverYoungEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + Player player = game.getPlayer(source.getControllerId()); + if (player == null) { + return false; + } + return player.putCardsOnTopOfLibrary(new CardsImpl( + source.getTargets() + .stream() + .map(Target::getTargets) + .flatMap(Collection::stream) + .map(game::getCard) + .collect(Collectors.toSet()) + ), game, source, true); + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 3bf52b7555..ca0c963400 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -87,6 +87,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Fires of Invention", 125, Rarity.RARE, mage.cards.f.FiresOfInvention.class)); cards.add(new SetCardInfo("Flaxen Intruder", 155, Rarity.UNCOMMON, mage.cards.f.FlaxenIntruder.class)); cards.add(new SetCardInfo("Folio of Fancies", 46, Rarity.RARE, mage.cards.f.FolioOfFancies.class)); + cards.add(new SetCardInfo("Forever Young", 89, Rarity.COMMON, mage.cards.f.ForeverYoung.class)); cards.add(new SetCardInfo("Foulmire Knight", 90, Rarity.UNCOMMON, mage.cards.f.FoulmireKnight.class)); cards.add(new SetCardInfo("Frogify", 47, Rarity.UNCOMMON, mage.cards.f.Frogify.class)); cards.add(new SetCardInfo("Gadwick, the Wizened", 48, Rarity.RARE, mage.cards.g.GadwickTheWizened.class)); diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index dd3f235d56..332d5b69f2 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -36052,7 +36052,7 @@ Witching Well|Throne of Eldraine|74|C|{U}|Artifact|||When Witching Well enters t Ayara, First of Locthwain|Throne of Eldraine|75|R|{B}{B}{B}|Legendary Creature - Elf Noble|2|3|Whenever Ayara, First of Locthwain or another black creature enters the battlefield under your control, each opponent loses 1 life and you gain 1 life.${T}, Sacrifice another black creature: Draw a card.| Bake into a Pie|Throne of Eldraine|76|C|{2}{B}{B}|Instant|||Destroy target creature. Create a Food token.| Belle of the Brawl|Throne of Eldraine|78|U|{2}{B}|Creature - Human Knight|3|2|Menace$Whenever Belle of the Brawl attacks, other Knights you control get +1/+0 until end of turn.| -Blacklace Paragon|Throne of Eldraine|79|R|{1}{B}|Creature - Human Knight|3|1|Flash$When Blacklace Paragon enters the battlefield, target Knight gains deathtouch and lifelink until end of turn.| +Blacklance Paragon|Throne of Eldraine|79|R|{1}{B}|Creature - Human Knight|3|1|Flash$When Blacklance Paragon enters the battlefield, target Knight gains deathtouch and lifelink until end of turn.| Bog Naughty|Throne of Eldraine|80|U|{3}{B}{B}|Creature - Faerie|3|3|Flying${2}{B}, Sacrifice a Food: Target creature gets -3/-3 until end of turn.| Cauldron Familiar|Throne of Eldraine|81|U|{B}|Creature - Cat|1|1|When Cauldron Familiar enters the battlefield, each opponent loses 1 life and you gain 1 life.$Sacrifice a Food: Return Cauldron Familiar from your graveyard to the battlefield.| The Cauldron of Eternity|Throne of Eldraine|82|M|{10}{B}{B}|Legendary Artifact|||This spell costs {2} less for each creature card in your graveyard.$Whenever a creature you control dies, put it on the bottom of its owner's library.${2}{B}, {T}, Pay 2 life: Return target card from your graveyard to the battlefield. Activate this ability only any time you could cast a sorcery.| From 112b564bd1f145dbd0acd50891482fa8db965444 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 16 Sep 2019 20:07:40 -0400 Subject: [PATCH 169/373] Implemented Overwhelmed Apprentice --- .../mage/cards/o/OverwhelmedApprentice.java | 45 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 46 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/o/OverwhelmedApprentice.java diff --git a/Mage.Sets/src/mage/cards/o/OverwhelmedApprentice.java b/Mage.Sets/src/mage/cards/o/OverwhelmedApprentice.java new file mode 100644 index 0000000000..c62134e566 --- /dev/null +++ b/Mage.Sets/src/mage/cards/o/OverwhelmedApprentice.java @@ -0,0 +1,45 @@ +package mage.cards.o; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.effects.common.PutTopCardOfLibraryIntoGraveEachPlayerEffect; +import mage.abilities.effects.keyword.ScryEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.constants.TargetController; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class OverwhelmedApprentice extends CardImpl { + + public OverwhelmedApprentice(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{U}"); + + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.WIZARD); + this.power = new MageInt(1); + this.toughness = new MageInt(2); + + // When Overwhelmed Apprentice enters the battlefield, each opponent puts the top two cards of their library into their graveyard. Then you scry 2. + Ability ability = new EntersBattlefieldTriggeredAbility( + new PutTopCardOfLibraryIntoGraveEachPlayerEffect(2, TargetController.OPPONENT) + ); + ability.addEffect(new ScryEffect(2).setText("Then you scry 2.")); + this.addAbility(ability); + } + + private OverwhelmedApprentice(final OverwhelmedApprentice card) { + super(card); + } + + @Override + public OverwhelmedApprentice copy() { + return new OverwhelmedApprentice(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index ca0c963400..b04144b917 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -148,6 +148,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Opt", 59, Rarity.COMMON, mage.cards.o.Opt.class)); cards.add(new SetCardInfo("Order of Midnight", 99, Rarity.UNCOMMON, mage.cards.o.OrderOfMidnight.class)); cards.add(new SetCardInfo("Outmuscle", 170, Rarity.COMMON, mage.cards.o.Outmuscle.class)); + cards.add(new SetCardInfo("Overwhelmed Apprentice", 60, Rarity.UNCOMMON, mage.cards.o.OverwhelmedApprentice.class)); cards.add(new SetCardInfo("Piper of the Swarm", 100, Rarity.RARE, mage.cards.p.PiperOfTheSwarm.class)); cards.add(new SetCardInfo("Questing Beast", 171, Rarity.MYTHIC, mage.cards.q.QuestingBeast.class)); cards.add(new SetCardInfo("Raging Redcap", 134, Rarity.COMMON, mage.cards.r.RagingRedcap.class)); From ca14b2fe507017e93d32e8ce26aa3ede1f1729ef Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 16 Sep 2019 20:12:10 -0400 Subject: [PATCH 170/373] Implemented Syr Alin, the Lion's Claw --- .../src/mage/cards/s/SyrAlinTheLionsClaw.java | 47 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 48 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/s/SyrAlinTheLionsClaw.java diff --git a/Mage.Sets/src/mage/cards/s/SyrAlinTheLionsClaw.java b/Mage.Sets/src/mage/cards/s/SyrAlinTheLionsClaw.java new file mode 100644 index 0000000000..d34ae1e9f4 --- /dev/null +++ b/Mage.Sets/src/mage/cards/s/SyrAlinTheLionsClaw.java @@ -0,0 +1,47 @@ +package mage.cards.s; + +import mage.MageInt; +import mage.abilities.common.AttacksTriggeredAbility; +import mage.abilities.effects.common.continuous.BoostControlledEffect; +import mage.abilities.keyword.FirstStrikeAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; +import mage.constants.SuperType; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class SyrAlinTheLionsClaw extends CardImpl { + + public SyrAlinTheLionsClaw(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{3}{W}{W}"); + + this.addSuperType(SuperType.LEGENDARY); + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.KNIGHT); + this.power = new MageInt(4); + this.toughness = new MageInt(4); + + // First strike + this.addAbility(FirstStrikeAbility.getInstance()); + + // Whenever Syr Alin, the Lion's Claw attacks, other creatures you control get +1/+1 until end of turn. + this.addAbility(new AttacksTriggeredAbility(new BoostControlledEffect( + 1, 1, Duration.EndOfTurn, true + ), false)); + } + + private SyrAlinTheLionsClaw(final SyrAlinTheLionsClaw card) { + super(card); + } + + @Override + public SyrAlinTheLionsClaw copy() { + return new SyrAlinTheLionsClaw(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index b04144b917..b16a6e08fb 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -189,6 +189,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Steelclaw Lance", 202, Rarity.UNCOMMON, mage.cards.s.SteelclawLance.class)); cards.add(new SetCardInfo("Stolen by the Fae", 66, Rarity.RARE, mage.cards.s.StolenByTheFae.class)); cards.add(new SetCardInfo("Stonecoil Serpent", 235, Rarity.RARE, mage.cards.s.StonecoilSerpent.class)); + cards.add(new SetCardInfo("Syr Alin, the Lion's Claw", 32, Rarity.UNCOMMON, mage.cards.s.SyrAlinTheLionsClaw.class)); cards.add(new SetCardInfo("Syr Carah, the Bold", 145, Rarity.UNCOMMON, mage.cards.s.SyrCarahTheBold.class)); cards.add(new SetCardInfo("Syr Elenora, the Discerning", 67, Rarity.UNCOMMON, mage.cards.s.SyrElenoraTheDiscerning.class)); cards.add(new SetCardInfo("Syr Gwyn, Hero of Ashvale", 330, Rarity.MYTHIC, mage.cards.s.SyrGwynHeroOfAshvale.class)); From 0f8794a7004efa1616f829b7e7454210f1daa060 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 16 Sep 2019 20:22:31 -0400 Subject: [PATCH 171/373] Implemented Torbran, Thane of Red Fell --- .../mage/cards/t/TorbranThaneOfRedFell.java | 102 ++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 103 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/t/TorbranThaneOfRedFell.java diff --git a/Mage.Sets/src/mage/cards/t/TorbranThaneOfRedFell.java b/Mage.Sets/src/mage/cards/t/TorbranThaneOfRedFell.java new file mode 100644 index 0000000000..e9d707ce0e --- /dev/null +++ b/Mage.Sets/src/mage/cards/t/TorbranThaneOfRedFell.java @@ -0,0 +1,102 @@ +package mage.cards.t; + +import mage.MageInt; +import mage.MageObject; +import mage.abilities.Ability; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.effects.ReplacementEffectImpl; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.*; +import mage.game.Game; +import mage.game.events.GameEvent; +import mage.game.permanent.Permanent; +import mage.players.Player; +import mage.util.CardUtil; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class TorbranThaneOfRedFell extends CardImpl { + + public TorbranThaneOfRedFell(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{1}{R}{R}{R}"); + + this.addSuperType(SuperType.LEGENDARY); + this.subtype.add(SubType.DWARF); + this.subtype.add(SubType.NOBLE); + this.power = new MageInt(2); + this.toughness = new MageInt(4); + + // If a red source you control would deal damage to an opponent or a permanent an opponent controls, it deals that much damage plus 2 instead. + this.addAbility(new SimpleStaticAbility(new TorbranThaneOfRedFellEffect())); + } + + private TorbranThaneOfRedFell(final TorbranThaneOfRedFell card) { + super(card); + } + + @Override + public TorbranThaneOfRedFell copy() { + return new TorbranThaneOfRedFell(this); + } +} + +class TorbranThaneOfRedFellEffect extends ReplacementEffectImpl { + + TorbranThaneOfRedFellEffect() { + super(Duration.WhileOnBattlefield, Outcome.Damage); + this.staticText = "If a red source you control would deal damage to an opponent " + + "or a permanent an opponent controls, it deals that much damage plus 2 instead."; + } + + private TorbranThaneOfRedFellEffect(final TorbranThaneOfRedFellEffect effect) { + super(effect); + } + + @Override + public boolean replaceEvent(GameEvent event, Ability source, Game game) { + event.setAmount(CardUtil.addWithOverflowCheck(event.getAmount(), 2)); + return false; + } + + @Override + public boolean checksEventType(GameEvent event, Game game) { + switch (event.getType()) { + case DAMAGE_CREATURE: + case DAMAGE_PLANESWALKER: + case DAMAGE_PLAYER: + return true; + default: + return false; + } + } + + @Override + public boolean applies(GameEvent event, Ability source, Game game) { + Player player = game.getPlayer(source.getControllerId()); + if (player == null + || !player.hasOpponent(game.getControllerId(event.getTargetId()), game) + || !source.isControlledBy(game.getControllerId(event.getSourceId()))) { + return false; + } + MageObject sourceObject; + Permanent sourcePermanent = game.getPermanentOrLKIBattlefield(event.getSourceId()); + if (sourcePermanent == null) { + sourceObject = game.getObject(event.getSourceId()); + } else { + sourceObject = sourcePermanent; + } + return sourceObject != null + && sourceObject.getColor(game).isRed() + && !sourceObject.getId().equals(source.getSourceId()); + } + + @Override + public TorbranThaneOfRedFellEffect copy() { + return new TorbranThaneOfRedFellEffect(this); + } + +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index b16a6e08fb..9c779eb7b7 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -204,6 +204,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Thunderous Snapper", 215, Rarity.UNCOMMON, mage.cards.t.ThunderousSnapper.class)); cards.add(new SetCardInfo("Tome Raider", 68, Rarity.COMMON, mage.cards.t.TomeRaider.class)); cards.add(new SetCardInfo("Tome of Legends", 332, Rarity.RARE, mage.cards.t.TomeOfLegends.class)); + cards.add(new SetCardInfo("Torbran, Thane of Red Fell", 367, Rarity.RARE, mage.cards.t.TorbranThaneOfRedFell.class)); cards.add(new SetCardInfo("Tournament Grounds", 248, Rarity.UNCOMMON, mage.cards.t.TournamentGrounds.class)); cards.add(new SetCardInfo("Trail of Crumbs", 179, Rarity.UNCOMMON, mage.cards.t.TrailOfCrumbs.class)); cards.add(new SetCardInfo("Trapped in the Tower", 33, Rarity.COMMON, mage.cards.t.TrappedInTheTower.class)); From 25eec140e6805abf62f76fa2df054ba812c5c51c Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 16 Sep 2019 20:34:59 -0400 Subject: [PATCH 172/373] Implemented Opportunistic Dragon --- .../src/mage/cards/o/OpportunisticDragon.java | 70 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 71 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/o/OpportunisticDragon.java diff --git a/Mage.Sets/src/mage/cards/o/OpportunisticDragon.java b/Mage.Sets/src/mage/cards/o/OpportunisticDragon.java new file mode 100644 index 0000000000..5787c4685e --- /dev/null +++ b/Mage.Sets/src/mage/cards/o/OpportunisticDragon.java @@ -0,0 +1,70 @@ +package mage.cards.o; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.effects.common.combat.CantAttackBlockTargetEffect; +import mage.abilities.effects.common.continuous.GainControlTargetEffect; +import mage.abilities.effects.common.continuous.LoseAllAbilitiesTargetEffect; +import mage.abilities.keyword.FlyingAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; +import mage.constants.TargetController; +import mage.filter.FilterPermanent; +import mage.filter.predicate.Predicates; +import mage.filter.predicate.mageobject.CardTypePredicate; +import mage.filter.predicate.mageobject.SubtypePredicate; +import mage.filter.predicate.permanent.ControllerPredicate; +import mage.target.TargetPermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class OpportunisticDragon extends CardImpl { + + private static final FilterPermanent filter = new FilterPermanent("Human or artifact an opponent controls"); + + static { + filter.add(Predicates.or( + new CardTypePredicate(CardType.ARTIFACT), + new SubtypePredicate(SubType.HUMAN) + )); + filter.add(new ControllerPredicate(TargetController.OPPONENT)); + } + + public OpportunisticDragon(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{2}{R}{R}"); + + this.subtype.add(SubType.DRAGON); + this.power = new MageInt(4); + this.toughness = new MageInt(3); + + // Flying + this.addAbility(FlyingAbility.getInstance()); + + // When Opportunistic Dragon enters the battlefield, choose target Human or artifact an opponent controls. For as long as Opportunistic Dragon remains on the battlefield, gain control of that permanent, it loses all abilities, and it can't attack or block. + Ability ability = new EntersBattlefieldTriggeredAbility(new GainControlTargetEffect(Duration.WhileOnBattlefield) + .setText("choose target Human or artifact an opponent controls. " + + "For as long as {this} remains on the battlefield, gain control of that permanent,")); + ability.addEffect(new LoseAllAbilitiesTargetEffect(Duration.WhileOnBattlefield) + .setText("it loses all abilities,")); + ability.addEffect(new CantAttackBlockTargetEffect(Duration.WhileOnBattlefield) + .setText("and it can't attack or block")); + ability.addTarget(new TargetPermanent(filter)); + this.addAbility(ability); + } + + private OpportunisticDragon(final OpportunisticDragon card) { + super(card); + } + + @Override + public OpportunisticDragon copy() { + return new OpportunisticDragon(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 9c779eb7b7..0580b7580d 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -145,6 +145,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Oko, the Trickster", 309, Rarity.MYTHIC, mage.cards.o.OkoTheTrickster.class)); cards.add(new SetCardInfo("Once Upon a Time", 169, Rarity.RARE, mage.cards.o.OnceUponATime.class)); cards.add(new SetCardInfo("Once and Future", 168, Rarity.UNCOMMON, mage.cards.o.OnceAndFuture.class)); + cards.add(new SetCardInfo("Opportunistic Dragon", 133, Rarity.RARE, mage.cards.o.OpportunisticDragon.class)); cards.add(new SetCardInfo("Opt", 59, Rarity.COMMON, mage.cards.o.Opt.class)); cards.add(new SetCardInfo("Order of Midnight", 99, Rarity.UNCOMMON, mage.cards.o.OrderOfMidnight.class)); cards.add(new SetCardInfo("Outmuscle", 170, Rarity.COMMON, mage.cards.o.Outmuscle.class)); From 5c1a0b2fcd4330a4f4a52314770f9c7a4da05913 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Tue, 17 Sep 2019 08:39:43 -0400 Subject: [PATCH 173/373] Implemented Castle Vantress --- .../src/mage/cards/c/CastleVantress.java | 58 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 5 +- Utils/mtg-cards-data.txt | 1 + 3 files changed, 62 insertions(+), 2 deletions(-) create mode 100644 Mage.Sets/src/mage/cards/c/CastleVantress.java diff --git a/Mage.Sets/src/mage/cards/c/CastleVantress.java b/Mage.Sets/src/mage/cards/c/CastleVantress.java new file mode 100644 index 0000000000..9e73d7a217 --- /dev/null +++ b/Mage.Sets/src/mage/cards/c/CastleVantress.java @@ -0,0 +1,58 @@ +package mage.cards.c; + +import mage.abilities.Ability; +import mage.abilities.common.EntersBattlefieldAbility; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.condition.Condition; +import mage.abilities.condition.common.PermanentsOnTheBattlefieldCondition; +import mage.abilities.costs.common.TapSourceCost; +import mage.abilities.costs.mana.ManaCostsImpl; +import mage.abilities.decorator.ConditionalOneShotEffect; +import mage.abilities.effects.common.TapSourceEffect; +import mage.abilities.effects.keyword.ScryEffect; +import mage.abilities.mana.BlueManaAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.ComparisonType; +import mage.constants.SubType; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterControlledPermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class CastleVantress extends CardImpl { + + private static final FilterPermanent filter = new FilterControlledPermanent(SubType.ISLAND); + private static final Condition condition + = new PermanentsOnTheBattlefieldCondition(filter, ComparisonType.EQUAL_TO, 0); + + public CastleVantress(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.LAND}, ""); + + // Castle Vantress enters the battlefield tapped unless you control an Island. + this.addAbility(new EntersBattlefieldAbility(new ConditionalOneShotEffect( + new TapSourceEffect(), condition + ), "tapped unless you control an Island")); + + // {T}: Add {U}. + this.addAbility(new BlueManaAbility()); + + // {2}{U}{U}, {T}: Scry 2. + Ability ability = new SimpleActivatedAbility(new ScryEffect(2), new ManaCostsImpl("{2}{U}{U}")); + ability.addCost(new TapSourceCost()); + this.addAbility(ability); + } + + private CastleVantress(final CastleVantress card) { + super(card); + } + + @Override + public CastleVantress copy() { + return new CastleVantress(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 0580b7580d..9eab75b869 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -42,13 +42,14 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Beanstalk Giant", 149, Rarity.UNCOMMON, mage.cards.b.BeanstalkGiant.class)); cards.add(new SetCardInfo("Belle of the Brawl", 78, Rarity.UNCOMMON, mage.cards.b.BelleOfTheBrawl.class)); cards.add(new SetCardInfo("Beloved Princess", 7, Rarity.COMMON, mage.cards.b.BelovedPrincess.class)); - cards.add(new SetCardInfo("Blacklance Paragon", 79, Rarity.RARE, mage.cards.b.BlacklanceParagon.class)); + cards.add(new SetCardInfo("Blacklance Paragon", 79, Rarity.RARE, mage.cards.b.BlacklanceParagon.class)); cards.add(new SetCardInfo("Blow Your House Down", 114, Rarity.COMMON, mage.cards.b.BlowYourHouseDown.class)); cards.add(new SetCardInfo("Bog Naughty", 80, Rarity.UNCOMMON, mage.cards.b.BogNaughty.class)); cards.add(new SetCardInfo("Bonecrusher Giant", 115, Rarity.RARE, mage.cards.b.BonecrusherGiant.class)); cards.add(new SetCardInfo("Bramblefort Fink", 311, Rarity.UNCOMMON, mage.cards.b.BramblefortFink.class)); cards.add(new SetCardInfo("Brimstone Trebuchet", 116, Rarity.COMMON, mage.cards.b.BrimstoneTrebuchet.class)); cards.add(new SetCardInfo("Burning-Yard Trainer", 117, Rarity.UNCOMMON, mage.cards.b.BurningYardTrainer.class)); + cards.add(new SetCardInfo("Castle Vantress", 242, Rarity.RARE, mage.cards.c.CastleVantress.class)); cards.add(new SetCardInfo("Cauldron Familiar", 81, Rarity.UNCOMMON, mage.cards.c.CauldronFamiliar.class)); cards.add(new SetCardInfo("Charming Prince", 8, Rarity.RARE, mage.cards.c.CharmingPrince.class)); cards.add(new SetCardInfo("Chittering Witch", 319, Rarity.RARE, mage.cards.c.ChitteringWitch.class)); @@ -189,7 +190,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Steelbane Hydra", 322, Rarity.RARE, mage.cards.s.SteelbaneHydra.class)); cards.add(new SetCardInfo("Steelclaw Lance", 202, Rarity.UNCOMMON, mage.cards.s.SteelclawLance.class)); cards.add(new SetCardInfo("Stolen by the Fae", 66, Rarity.RARE, mage.cards.s.StolenByTheFae.class)); - cards.add(new SetCardInfo("Stonecoil Serpent", 235, Rarity.RARE, mage.cards.s.StonecoilSerpent.class)); + cards.add(new SetCardInfo("Stonecoil Serpent", 235, Rarity.RARE, mage.cards.s.StonecoilSerpent.class)); cards.add(new SetCardInfo("Syr Alin, the Lion's Claw", 32, Rarity.UNCOMMON, mage.cards.s.SyrAlinTheLionsClaw.class)); cards.add(new SetCardInfo("Syr Carah, the Bold", 145, Rarity.UNCOMMON, mage.cards.s.SyrCarahTheBold.class)); cards.add(new SetCardInfo("Syr Elenora, the Discerning", 67, Rarity.UNCOMMON, mage.cards.s.SyrElenoraTheDiscerning.class)); diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index 332d5b69f2..a5492a5d11 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -36188,6 +36188,7 @@ Sorcerous Spyglass|Throne of Eldraine|233|R|{2}|Artifact|||As Sorcerous Spyglass Spinning Wheel|Throne of Eldraine|234|U|{3}|Artifact|||{T}: Add one mana of any color.${5}, {T}: Tap target creature.| Stonecoil Serpent|Throne of Eldraine|235|R|{X}|Artifact Creature - Snake|0|0|Reach, trample, protection from multicolored$Stonecoil Serpent enters the battlefield with X +1/+1 counters on it.| Witch's Oven|Throne of Eldraine|237|U|{1}|Artifact|||{T}, Sacrifice a creature: Create a Food token. If the sacrificed creature's toughness was 4 or greater, create two Food tokens instead.| +Castle Vantress|Throne of Eldraine|242|R||Land|||Castle Vantress enters the battlefield tapped unless you control an Island.${T}: Add {U}.${2}{U}{U}, {T}: Scry 2.| Idyllic Grange|Throne of Eldraine|246|C||Land - Plains|||({T}: Add {W}.)$Idyllic Grange enters the battlefield tapped unless you control three or more other Plains.$When Idyllic Grange enters the battlefield untapped, put a +1/+1 counter on target creature you control.| Tournament Grounds|Throne of Eldraine|248|U||Land|||{T}: Add {C}.${T}: Add {R}, {W}, or {B}. Spend this mana only to cast a Knight or Equipment spell.| Witch's Cottage|Throne of Eldraine|249|C||Land - Swamp|||({T}: Add {B}.)$Witch's Cottage enters the battlefield tapped unless you control three or more other Swamps.$When Witch's Cottage enters the battlefield untapped, you may put target creature card from your graveyard on top of your library.| From bc648993e8f25154c52ab33a96f02e0f797433d5 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Tue, 17 Sep 2019 17:09:13 -0400 Subject: [PATCH 174/373] updated ELD spoiler --- Utils/mtg-cards-data.txt | 12 +++++++++++- 1 file changed, 11 insertions(+), 1 deletion(-) diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index a5492a5d11..5d18eddc36 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -36004,6 +36004,7 @@ The Circle of Loyalty|Throne of Eldraine|9|M|{4}{W}{W}|Legendary Artifact|||This Deafening Silence|Throne of Eldraine|10|U|{W}|Enchantment|||Each player can't cast more than one noncreature spell each turn.| Faerie Guidemother|Throne of Eldraine|11|C|{W}|Creature - Faerie|1|1|Flying| Gift of the Fae|Throne of Eldraine|11|C|{1}{W}|Sorcery - Adventure|1|1|Target creature gets +2/+1 and gains flying until end of turn.| +Fortifying Provisions|Throne of Eldraine|13|C|{2}{W}|Enchantment|||Creatures you control get +0/+1.$When Fortifying Provisions enters the battlefield, create a Food token.| Chop Down|Throne of Eldraine|14|R|{2}{W}|Instant - Adventure|1|2|Destroy target creature with power 4 or greater.| Giant Killer|Throne of Eldraine|14|R|{W}|Creature - Human Peasant|1|2|{1}{W}, {T}: Tap target creature.| Glass Casket|Throne of Eldraine|15|U|{1}{W}|Artifact|||When Glass Casket enters the battlefield, exile target creature an opponent controls with converted mana cost 3 or less until Glass Casket leaves the battlefield.| @@ -36012,7 +36013,10 @@ Knight of the Keep|Throne of Eldraine|19|C|{2}{W}|Creature - Human Knight|3|2|| Linden, the Steadfast Queen|Throne of Eldraine|20|R|{W}{W}{W}|Legendary Creature - Human Noble|3|3|Vigilance$Whenever a white creature you control attacks, you gain 1 life.| Lonesome Unicorn|Throne of Eldraine|21|C|{4}{W}|Creature - Unicorn|3|3|Vigilance| Rider in Need|Throne of Eldraine|21|C|{2}{W}|Sorcery - Adventure|3|3|Create a 2/2 white Knight creature token with vigilance.| +Mysterious Pathlighter|Throne of Eldraine|22|U|{2}{W}|Creature - Faerie|2|2|Flying$Each creature you control that has an Adventure enters the battlefield with an additional +1/+1 counter on it.| Rally for the Throne|Throne of Eldraine|25|U|{2}{W}|Instant|||Create two 1/1 white Human creature tokens.$Adamant — If at least three white mana was spent to cast this spell, you gain 1 life for each creature you control.| +Cast Off|Throne of Eldraine|26|M|{3}{W}{W}|Sorcery - Adventure|7|7|Destroy all non-Giant creatures.| +Realm-Cloaked Giant|Throne of Eldraine|26|M|{5}{W}{W}|Creature - Giant|7|7|Vigilance| Righteousness|Throne of Eldraine|27|U|{W}|Instant|||Target blocking creature gets +7/+7 until end of turn.| Shining Armor|Throne of Eldraine|29|C|{1}{W}|Artifact - Equipment|||Flash$When Shining Armor enters the battlefield, attach it to target Knight you control.$Equipped creature gets +0/+2 and has vigilance.$Equip {3}| Silverflame Ritual|Throne of Eldraine|30|C|{3}{W}|Sorcery|||Put a +1/+1 counter on each creature you control.$Adamant — If at least three white mana was spent to cast this spell, creatures you control gain vigilance until end of turn.| @@ -36055,7 +36059,7 @@ Belle of the Brawl|Throne of Eldraine|78|U|{2}{B}|Creature - Human Knight|3|2|Me Blacklance Paragon|Throne of Eldraine|79|R|{1}{B}|Creature - Human Knight|3|1|Flash$When Blacklance Paragon enters the battlefield, target Knight gains deathtouch and lifelink until end of turn.| Bog Naughty|Throne of Eldraine|80|U|{3}{B}{B}|Creature - Faerie|3|3|Flying${2}{B}, Sacrifice a Food: Target creature gets -3/-3 until end of turn.| Cauldron Familiar|Throne of Eldraine|81|U|{B}|Creature - Cat|1|1|When Cauldron Familiar enters the battlefield, each opponent loses 1 life and you gain 1 life.$Sacrifice a Food: Return Cauldron Familiar from your graveyard to the battlefield.| -The Cauldron of Eternity|Throne of Eldraine|82|M|{10}{B}{B}|Legendary Artifact|||This spell costs {2} less for each creature card in your graveyard.$Whenever a creature you control dies, put it on the bottom of its owner's library.${2}{B}, {T}, Pay 2 life: Return target card from your graveyard to the battlefield. Activate this ability only any time you could cast a sorcery.| +The Cauldron of Eternity|Throne of Eldraine|82|M|{10}{B}{B}|Legendary Artifact|||This spell costs {2} less for each creature card in your graveyard.$Whenever a creature you control dies, put it on the bottom of its owner's library.${2}{B}, {T}, Pay 2 life: Return target creature card from your graveyard to the battlefield. Activate this ability only any time you could cast a sorcery.| Cauldron's Gift|Throne of Eldraine|83|U|{4}{B}|Sorcery|||Adamant — If at least three black mana was spent to cast this spell, put the top four cards of your library into your graveyard.$You may choose a creature card in your graveyard. If you do, return it to the battlefield with an additional +1/+1 counter on it.| Clackbridge Troll|Throne of Eldraine|84|R|{3}{B}{B}|Creature - Troll|8|8|Trample, haste$When Clackbridge Troll enters the battlefield, target opponent creates three 0/1 white Goat creature tokens.$At the beginning of combat on your turn, any opponent may sacrifice a creature. If a player does, tap Clackbridge Troll, you gain 3 life, and you draw a card.| Epic Downfall|Throne of Eldraine|85|U|{1}{B}|Sorcery|||Exile target creature with converted mana cost 3 or greater.| @@ -36063,6 +36067,7 @@ Eye Collector|Throne of Eldraine|86|C|{B}|Creature - Faerie|1|1|Flying$Whenever Forever Young|Throne of Eldraine|89|C|{1}{B}|Sorcery|||Put any number of target creature cards from your graveyard on top of your library.$Draw a card.| Foulmire Knight|Throne of Eldraine|90|U|{B}|Creature - Zombie Knight|1|1|Deathtouch| Profane Insight|Throne of Eldraine|90|U|{2}{B}|Instant - Adventure|1|1|You draw a card and you lose 1 life.| +Giant's Skewer|Throne of Eldraine|91|C|{1}{B}|Artifact - Equipment|||Equipped creature gets +2/+1.$Whenever equipped creature deals combat damage to a creature, create a Food token.$Equip {3}| Lost Legion|Throne of Eldraine|94|C|{1}{B}{B}|Creature - Spirit Knight|2|3|When Lost Legion enters the battlefield, scry 2.| Murderous Rider|Throne of Eldraine|97|R|{1}{B}{B}|Creature - Zombie Knight|2|3|Lifelink$When Murderous Rider dies, put it on the bottom of its owner's library.| Swift End|Throne of Eldraine|97|R|{1}{B}{B}|Instant - Adventure|2|3|Destroy target creature or planeswalker. You lose 2 life.| @@ -36140,6 +36145,7 @@ Questing Beast|Throne of Eldraine|171|M|{2}{G}{G}|Legendary Creature - Beast|4|4 Return to Nature|Throne of Eldraine|173|C|{1}{G}|Instant|||Choose one —$• Destroy target artifact.$• Destroy target enchantment.$• Exile target card from a graveyard.| Rosethorn Acolyte|Throne of Eldraine|174|C|{2}{G}|Creature - Elf Druid|2|3|{T}: Add one mana of any color.| Seasonal Ritual|Throne of Eldraine|174|C|{G}|Sorcery - Adventure|2|3|Add one mana of any color.| +Syr Faren, the Hengehammer|Throne of Eldraine|177|U|{G}{G}|Legendary Creature - Human Knight|2|2|Whenever Syr Faren, the Hengehammer attacks, another target attacking creature gets +X/+X until end of turn, where X is Syr Faren's power.| Tall as a Beanstalk|Throne of Eldraine|178|C|{3}{G}|Enchantment - Aura|||Enchant creature$Enchanted creature gets +3/+3, has reach, and is a Giant in addition to its other types.| Trail of Crumbs|Throne of Eldraine|179|U|{1}{G}|Enchantment|||When Trail of Crumbs enters the battlefield, create a Food token.$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.| Oaken Boon|Throne of Eldraine|180|C|{3}{G}|Sorcery - Adventure|6|5|Put two +1/+1 counters on target creature.| @@ -36151,6 +36157,7 @@ Wolf's Quarry|Throne of Eldraine|184|C|{4}{G}{G}|Sorcery|||Create three 1/1 gree Dance of the Manse|Throne of Eldraine|186|R|{X}{W}{U}|Sorcery|||Return up to X target artifact and/or non-Aura enchantment cards each with converted mana cost X or less from your graveyard to the battlefield. If X is 6 or more, those permanents are 4/4 creatures in addition to their other types.| Doom Foretold|Throne of Eldraine|187|R|{2}{W}{B}|Enchantment|||At the beginning of each player's upkeep, that player sacrifices a nonland, nontoken permanent. If that player can't, they discard a card, they lose 2 life, you draw a card, you gain 2 life, you create a 2/2 white Knight creature token with vigilance, then you sacrifice Doom Foretold.| Drown in the Loch|Throne of Eldraine|188|U|{U}{B}|Instant|||Choose one —$• Counter target spell with converted mana cost less than or equal to the number of cards in its controller's graveyard.$• Destroy target creature with converted mana cost less than or equal to the number of cards in its controller's graveyard.| +Escape to the Wilds|Throne of Eldraine|189|R|{3}{R}{G}|Sorcery|||Exile the top five cards of your library. You may play cards exiled this way until the end of your next turn.$You may play an additional land this turn.| Faeburrow Elder|Throne of Eldraine|190|R|{1}{G}{W}|Creature - Treefolk Druid|0|0|Vigilance$Faeburrow Elder gets +1/+1 for each color among permanents you control.${T}: For each color among permanents you control, add one mana of that color.| Garruk, Cursed Huntsman|Throne of Eldraine|191|M|{4}{B}{G}|Legendary Planeswalker - Garruk|5|0: Create two 2/2 black and green Wolf creature tokens with "When this creature dies, put a loyalty counter on each Garruk you control."$−3: Destroy target creature. Draw a card.$−6: You get an emblem with "Creatures you control get +3/+3 and have trample."| Grumgully, the Generous|Throne of Eldraine|192|U|{1}{R}{G}|Legendary Creature - Goblin Shaman|3|3|Each other non-Human creature you controls enters the battlefield with an additional +1/+1 counter on it.| @@ -36181,6 +36188,7 @@ Henge Walker|Throne of Eldraine|221|C|{3}|Artifact Creature - Golem|2|2|Adamant Heraldic Banner|Throne of Eldraine|222|U|{3}|Artifact|||As Heraldic Banner enters the battlefield, choose a color.$Creatures you control of the chosen color get +1/+0.${T}: Add one mana of the chosen color.| Inquisitive Puppet|Throne of Eldraine|223|U|{1}|Artifact Creature - Construct|0|2|When Inquisitive Puppet enters the battlefield, scry 1.$Exile Inquisitive Puppet: Create a 1/1 white Human creature token.| Jousting Dummy|Throne of Eldraine|224|C|{2}|Artifact Creature - Scarecrow Knight|2|1|{3}: Jousting Dummy gets +1/+0 until end of turn.| +Lucky Clover|Throne of Eldraine|226|U|{2}|Artifact|||Whenever you cast an Adventure instant or sorcery spell, copy it. You may choose new targets for the copy.| Roving Keep|Throne of Eldraine|228|C|{7}|Artifact Creature - Wall|5|7|Defender${7}: Roving Keep gets +2/+0 and gains trample until end of turn. It can attack this turn as though it didn't have defender.| Shambling Suit|Throne of Eldraine|230|U|{3}|Artifact Creature - Construct|*|3|Shambling Suit's power is equal to the number of artifacts and/or enchantments you control.| Sorcerer's Broom|Throne of Eldraine|232|U|{2}|Artifact Creature - Spirit|2|1|Whenever you sacrifice another permanent, you may pay {3}. If you do, create a token that's a copy of Sorcerer's Broom.| @@ -36188,6 +36196,8 @@ Sorcerous Spyglass|Throne of Eldraine|233|R|{2}|Artifact|||As Sorcerous Spyglass Spinning Wheel|Throne of Eldraine|234|U|{3}|Artifact|||{T}: Add one mana of any color.${5}, {T}: Tap target creature.| Stonecoil Serpent|Throne of Eldraine|235|R|{X}|Artifact Creature - Snake|0|0|Reach, trample, protection from multicolored$Stonecoil Serpent enters the battlefield with X +1/+1 counters on it.| Witch's Oven|Throne of Eldraine|237|U|{1}|Artifact|||{T}, Sacrifice a creature: Create a Food token. If the sacrificed creature's toughness was 4 or greater, create two Food tokens instead.| +Castle Embereth|Throne of Eldraine|239|R||Land|||Castle Embereth enters the battlefield tapped unless you control a Mountain.${T}: Add {R}.${1}{R}{R}, {T}: Creatures you control get +1/+0 until end of turn.| +Castle Garenbrig|Throne of Eldraine|240|R||Land|||Castle Garenbrig enters the battlefield tapped unelss you control a Forest.${T}: Add {G}.${2}{G}{G}, {T}: Add six {G}. Spend this mana only to cast creature spells or activate abilities of creatures.| Castle Vantress|Throne of Eldraine|242|R||Land|||Castle Vantress enters the battlefield tapped unless you control an Island.${T}: Add {U}.${2}{U}{U}, {T}: Scry 2.| Idyllic Grange|Throne of Eldraine|246|C||Land - Plains|||({T}: Add {W}.)$Idyllic Grange enters the battlefield tapped unless you control three or more other Plains.$When Idyllic Grange enters the battlefield untapped, put a +1/+1 counter on target creature you control.| Tournament Grounds|Throne of Eldraine|248|U||Land|||{T}: Add {C}.${T}: Add {R}, {W}, or {B}. Spend this mana only to cast a Knight or Equipment spell.| From a8f2ac17fcc79f0cbfc5bcec886419acefce9e03 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Tue, 17 Sep 2019 17:13:02 -0400 Subject: [PATCH 175/373] Implemented Fortifying Provisions --- .../mage/cards/f/FortifyingProvisions.java | 38 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 39 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/f/FortifyingProvisions.java diff --git a/Mage.Sets/src/mage/cards/f/FortifyingProvisions.java b/Mage.Sets/src/mage/cards/f/FortifyingProvisions.java new file mode 100644 index 0000000000..61f6c41034 --- /dev/null +++ b/Mage.Sets/src/mage/cards/f/FortifyingProvisions.java @@ -0,0 +1,38 @@ +package mage.cards.f; + +import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.effects.common.CreateTokenEffect; +import mage.abilities.effects.common.continuous.BoostControlledEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.game.permanent.token.FoodToken; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class FortifyingProvisions extends CardImpl { + + public FortifyingProvisions(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ENCHANTMENT}, "{2}{W}"); + + // Creatures you control get +0/+1. + this.addAbility(new SimpleStaticAbility(new BoostControlledEffect(0, 1, Duration.WhileOnBattlefield))); + + // When Fortifying Provisions enters the battlefield, create a Food token. + this.addAbility(new EntersBattlefieldTriggeredAbility(new CreateTokenEffect(new FoodToken()))); + } + + private FortifyingProvisions(final FortifyingProvisions card) { + super(card); + } + + @Override + public FortifyingProvisions copy() { + return new FortifyingProvisions(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 9eab75b869..60b39a9418 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -89,6 +89,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Flaxen Intruder", 155, Rarity.UNCOMMON, mage.cards.f.FlaxenIntruder.class)); cards.add(new SetCardInfo("Folio of Fancies", 46, Rarity.RARE, mage.cards.f.FolioOfFancies.class)); cards.add(new SetCardInfo("Forever Young", 89, Rarity.COMMON, mage.cards.f.ForeverYoung.class)); + cards.add(new SetCardInfo("Fortifying Provisions", 13, Rarity.COMMON, mage.cards.f.FortifyingProvisions.class)); cards.add(new SetCardInfo("Foulmire Knight", 90, Rarity.UNCOMMON, mage.cards.f.FoulmireKnight.class)); cards.add(new SetCardInfo("Frogify", 47, Rarity.UNCOMMON, mage.cards.f.Frogify.class)); cards.add(new SetCardInfo("Gadwick, the Wizened", 48, Rarity.RARE, mage.cards.g.GadwickTheWizened.class)); From bcc72d4686a2b20c16242c631546708b861661b2 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Tue, 17 Sep 2019 17:16:19 -0400 Subject: [PATCH 176/373] Implemented Castle Embereth --- .../src/mage/cards/c/CastleEmbereth.java | 61 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 62 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/c/CastleEmbereth.java diff --git a/Mage.Sets/src/mage/cards/c/CastleEmbereth.java b/Mage.Sets/src/mage/cards/c/CastleEmbereth.java new file mode 100644 index 0000000000..53ef68f844 --- /dev/null +++ b/Mage.Sets/src/mage/cards/c/CastleEmbereth.java @@ -0,0 +1,61 @@ +package mage.cards.c; + +import mage.abilities.Ability; +import mage.abilities.common.EntersBattlefieldAbility; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.condition.Condition; +import mage.abilities.condition.common.PermanentsOnTheBattlefieldCondition; +import mage.abilities.costs.common.TapSourceCost; +import mage.abilities.costs.mana.ManaCostsImpl; +import mage.abilities.decorator.ConditionalOneShotEffect; +import mage.abilities.effects.common.TapSourceEffect; +import mage.abilities.effects.common.continuous.BoostControlledEffect; +import mage.abilities.mana.RedManaAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.ComparisonType; +import mage.constants.Duration; +import mage.constants.SubType; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterControlledPermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class CastleEmbereth extends CardImpl { + + private static final FilterPermanent filter = new FilterControlledPermanent(SubType.MOUNTAIN); + private static final Condition condition + = new PermanentsOnTheBattlefieldCondition(filter, ComparisonType.EQUAL_TO, 0); + + public CastleEmbereth(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.LAND}, ""); + + // Castle Embereth enters the battlefield tapped unless you control a Mountain. + this.addAbility(new EntersBattlefieldAbility(new ConditionalOneShotEffect( + new TapSourceEffect(), condition + ), "tapped unless you control an Mountain")); + + // {T}: Add {R}. + this.addAbility(new RedManaAbility()); + + // {1}{R}{R}, {T}: Creatures you control get +1/+0 until end of turn. + Ability ability = new SimpleActivatedAbility( + new BoostControlledEffect(1, 0, Duration.EndOfTurn), new ManaCostsImpl("{1}{R}{R}") + ); + ability.addCost(new TapSourceCost()); + this.addAbility(ability); + } + + private CastleEmbereth(final CastleEmbereth card) { + super(card); + } + + @Override + public CastleEmbereth copy() { + return new CastleEmbereth(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 60b39a9418..27262353e6 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -49,6 +49,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Bramblefort Fink", 311, Rarity.UNCOMMON, mage.cards.b.BramblefortFink.class)); cards.add(new SetCardInfo("Brimstone Trebuchet", 116, Rarity.COMMON, mage.cards.b.BrimstoneTrebuchet.class)); cards.add(new SetCardInfo("Burning-Yard Trainer", 117, Rarity.UNCOMMON, mage.cards.b.BurningYardTrainer.class)); + cards.add(new SetCardInfo("Castle Embereth", 239, Rarity.RARE, mage.cards.c.CastleEmbereth.class)); cards.add(new SetCardInfo("Castle Vantress", 242, Rarity.RARE, mage.cards.c.CastleVantress.class)); cards.add(new SetCardInfo("Cauldron Familiar", 81, Rarity.UNCOMMON, mage.cards.c.CauldronFamiliar.class)); cards.add(new SetCardInfo("Charming Prince", 8, Rarity.RARE, mage.cards.c.CharmingPrince.class)); From d557e6a27e70057c5c5727fede253e8af09ec6e1 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Tue, 17 Sep 2019 17:28:01 -0400 Subject: [PATCH 177/373] Implemented Lucky Clover --- Mage.Sets/src/mage/cards/l/LuckyClover.java | 45 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + .../src/main/java/mage/constants/SubType.java | 1 + 3 files changed, 47 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/l/LuckyClover.java diff --git a/Mage.Sets/src/mage/cards/l/LuckyClover.java b/Mage.Sets/src/mage/cards/l/LuckyClover.java new file mode 100644 index 0000000000..08ef868750 --- /dev/null +++ b/Mage.Sets/src/mage/cards/l/LuckyClover.java @@ -0,0 +1,45 @@ +package mage.cards.l; + +import mage.abilities.common.SpellCastControllerTriggeredAbility; +import mage.abilities.effects.common.CopyTargetSpellEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.filter.FilterSpell; +import mage.filter.common.FilterInstantOrSorcerySpell; +import mage.filter.predicate.mageobject.SubtypePredicate; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class LuckyClover extends CardImpl { + + private static final FilterSpell filter + = new FilterInstantOrSorcerySpell("an Adventure instant or sorcery spell"); + + static { + filter.add(new SubtypePredicate(SubType.ADVENTURE)); + } + + public LuckyClover(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT}, "{2}"); + + // Whenever you cast an Adventure instant or sorcery spell, copy it. You may choose new targets for the copy. + this.addAbility(new SpellCastControllerTriggeredAbility( + new CopyTargetSpellEffect(true).withSpellName("it"), + filter, false, true + )); + } + + private LuckyClover(final LuckyClover card) { + super(card); + } + + @Override + public LuckyClover copy() { + return new LuckyClover(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 27262353e6..807401b18a 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -129,6 +129,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Lonesome Unicorn", 21, Rarity.COMMON, mage.cards.l.LonesomeUnicorn.class)); cards.add(new SetCardInfo("Lost Legion", 94, Rarity.COMMON, mage.cards.l.LostLegion.class)); cards.add(new SetCardInfo("Lovestruck Beast", 165, Rarity.RARE, mage.cards.l.LovestruckBeast.class)); + cards.add(new SetCardInfo("Lucky Clover", 226, Rarity.UNCOMMON, mage.cards.l.LuckyClover.class)); cards.add(new SetCardInfo("Mace of the Valiant", 314, Rarity.RARE, mage.cards.m.MaceOfTheValiant.class)); cards.add(new SetCardInfo("Maraleaf Pixie", 196, Rarity.UNCOMMON, mage.cards.m.MaraleafPixie.class)); cards.add(new SetCardInfo("Maraleaf Rider", 166, Rarity.COMMON, mage.cards.m.MaraleafRider.class)); diff --git a/Mage/src/main/java/mage/constants/SubType.java b/Mage/src/main/java/mage/constants/SubType.java index da6b5bc629..e74f2a8552 100644 --- a/Mage/src/main/java/mage/constants/SubType.java +++ b/Mage/src/main/java/mage/constants/SubType.java @@ -10,6 +10,7 @@ import java.util.stream.Collectors; public enum SubType { //205.3k Instants and sorceries share their lists of subtypes; these subtypes are called spell types. + ADVENTURE("Adventure", SubTypeSet.SpellType), ARCANE("Arcane", SubTypeSet.SpellType), TRAP("Trap", SubTypeSet.SpellType), // 205.3i: Lands have their own unique set of subtypes; these subtypes are called land types. From 2bc056278dbecb2879a303e02b147f123a566313 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Tue, 17 Sep 2019 20:41:02 -0400 Subject: [PATCH 178/373] Implemented Escape to the Wilds --- .../src/mage/cards/e/EscapeToTheWilds.java | 119 ++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 120 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/e/EscapeToTheWilds.java diff --git a/Mage.Sets/src/mage/cards/e/EscapeToTheWilds.java b/Mage.Sets/src/mage/cards/e/EscapeToTheWilds.java new file mode 100644 index 0000000000..0c36bdd097 --- /dev/null +++ b/Mage.Sets/src/mage/cards/e/EscapeToTheWilds.java @@ -0,0 +1,119 @@ +package mage.cards.e; + +import mage.abilities.Ability; +import mage.abilities.effects.AsThoughEffectImpl; +import mage.abilities.effects.ContinuousEffect; +import mage.abilities.effects.OneShotEffect; +import mage.abilities.effects.common.continuous.PlayAdditionalLandsControllerEffect; +import mage.cards.*; +import mage.constants.*; +import mage.game.Game; +import mage.players.Player; +import mage.target.targetpointer.FixedTarget; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class EscapeToTheWilds extends CardImpl { + + public EscapeToTheWilds(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.SORCERY}, "{3}{R}{G}"); + + // Exile the top five cards of your library. You may play cards exiled this way until the end of your next turn. + // You may play an additional land this turn. + this.getSpellAbility().addEffect(new EscapeToTheWildsEffect()); + } + + private EscapeToTheWilds(final EscapeToTheWilds card) { + super(card); + } + + @Override + public EscapeToTheWilds copy() { + return new EscapeToTheWilds(this); + } +} + +class EscapeToTheWildsEffect extends OneShotEffect { + + EscapeToTheWildsEffect() { + super(Outcome.PlayForFree); + this.staticText = "Exile the top five cards of your library. " + + "You may play cards exiled this way until the end of your next turn.
" + + "You may play an additional land this turn."; + } + + private EscapeToTheWildsEffect(final EscapeToTheWildsEffect effect) { + super(effect); + } + + @Override + public EscapeToTheWildsEffect copy() { + return new EscapeToTheWildsEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + Player controller = game.getPlayer(source.getControllerId()); + if (controller == null) { + return false; + } + Cards cards = new CardsImpl(controller.getLibrary().getTopCards(game, 5)); + Card sourceCard = game.getCard(source.getSourceId()); + controller.moveCards(cards, Zone.EXILED, source, game); + + cards.getCards(game).stream().forEach(card -> { + ContinuousEffect effect = new EscapeToTheWildsMayPlayEffect(); + effect.setTargetPointer(new FixedTarget(card.getId())); + game.addEffect(effect, source); + }); + game.addEffect(new PlayAdditionalLandsControllerEffect(1, Duration.EndOfTurn), source); + return true; + } +} + +class EscapeToTheWildsMayPlayEffect extends AsThoughEffectImpl { + + private int castOnTurn = 0; + + EscapeToTheWildsMayPlayEffect() { + super(AsThoughEffectType.PLAY_FROM_NOT_OWN_HAND_ZONE, Duration.Custom, Outcome.Benefit); + this.staticText = "Until the end of your next turn, you may play that card."; + } + + private EscapeToTheWildsMayPlayEffect(final EscapeToTheWildsMayPlayEffect effect) { + super(effect); + castOnTurn = effect.castOnTurn; + } + + @Override + public EscapeToTheWildsMayPlayEffect copy() { + return new EscapeToTheWildsMayPlayEffect(this); + } + + @Override + public void init(Ability source, Game game) { + super.init(source, game); + castOnTurn = game.getTurnNum(); + } + + @Override + public boolean isInactive(Ability source, Game game) { + return castOnTurn != game.getTurnNum() + && game.getPhase().getStep().getType() == PhaseStep.END_TURN + && game.isActivePlayer(source.getControllerId()); + } + + @Override + public boolean apply(Game game, Ability source) { + return true; + } + + @Override + public boolean applies(UUID sourceId, Ability source, UUID affectedControllerId, Game game) { + return source.isControlledBy(affectedControllerId) + && getTargetPointer().getTargets(game, source).contains(sourceId); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 807401b18a..debc77c922 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -75,6 +75,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Emry, Lurker of the Loch", 43, Rarity.RARE, mage.cards.e.EmryLurkerOfTheLoch.class)); cards.add(new SetCardInfo("Enchanted Carriage", 218, Rarity.UNCOMMON, mage.cards.e.EnchantedCarriage.class)); cards.add(new SetCardInfo("Epic Downfall", 85, Rarity.UNCOMMON, mage.cards.e.EpicDownfall.class)); + cards.add(new SetCardInfo("Escape to the Wilds", 189, Rarity.RARE, mage.cards.e.EscapeToTheWilds.class)); cards.add(new SetCardInfo("Eye Collector", 86, Rarity.COMMON, mage.cards.e.EyeCollector.class)); cards.add(new SetCardInfo("Faeburrow Elder", 190, Rarity.RARE, mage.cards.f.FaeburrowElder.class)); cards.add(new SetCardInfo("Faerie Formation", 316, Rarity.RARE, mage.cards.f.FaerieFormation.class)); From ddef945ad869c00b04fb658fd527f3a61c2a4c61 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Tue, 17 Sep 2019 20:55:45 -0400 Subject: [PATCH 179/373] Implemented Castle Garenbrig --- .../src/mage/cards/c/CastleGarenbrig.java | 99 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 100 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/c/CastleGarenbrig.java diff --git a/Mage.Sets/src/mage/cards/c/CastleGarenbrig.java b/Mage.Sets/src/mage/cards/c/CastleGarenbrig.java new file mode 100644 index 0000000000..d2144fa3be --- /dev/null +++ b/Mage.Sets/src/mage/cards/c/CastleGarenbrig.java @@ -0,0 +1,99 @@ +package mage.cards.c; + +import mage.ConditionalMana; +import mage.MageObject; +import mage.Mana; +import mage.abilities.Ability; +import mage.abilities.common.EntersBattlefieldAbility; +import mage.abilities.condition.Condition; +import mage.abilities.condition.common.PermanentsOnTheBattlefieldCondition; +import mage.abilities.costs.common.TapSourceCost; +import mage.abilities.costs.mana.ManaCostsImpl; +import mage.abilities.decorator.ConditionalOneShotEffect; +import mage.abilities.effects.common.TapSourceEffect; +import mage.abilities.mana.ConditionalColoredManaAbility; +import mage.abilities.mana.GreenManaAbility; +import mage.abilities.mana.builder.ConditionalManaBuilder; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.ComparisonType; +import mage.constants.SubType; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterControlledPermanent; +import mage.game.Game; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class CastleGarenbrig extends CardImpl { + + private static final FilterPermanent filter = new FilterControlledPermanent(SubType.FOREST); + private static final Condition condition + = new PermanentsOnTheBattlefieldCondition(filter, ComparisonType.EQUAL_TO, 0); + + public CastleGarenbrig(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.LAND}, ""); + + // Castle Garenbrig enters the battlefield tapped unless you control a Forest. + this.addAbility(new EntersBattlefieldAbility(new ConditionalOneShotEffect( + new TapSourceEffect(), condition + ), "tapped unless you control an Forest")); + + // {T}: Add {G}. + this.addAbility(new GreenManaAbility()); + + // {2}{G}{G}, {T}: Add six {G}. Spend this mana only to cast creature spells or activate abilities of creatures. + Ability ability = new ConditionalColoredManaAbility( + new ManaCostsImpl("{2}{G}{G}"), Mana.GreenMana(6), new CastleGarenbrigManaBuilder() + ); + ability.addCost(new TapSourceCost()); + this.addAbility(ability); + } + + private CastleGarenbrig(final CastleGarenbrig card) { + super(card); + } + + @Override + public CastleGarenbrig copy() { + return new CastleGarenbrig(this); + } +} + +class CastleGarenbrigManaBuilder extends ConditionalManaBuilder { + + @Override + public ConditionalMana build(Object... options) { + return new CastleGarenbrigConditionalMana(this.mana); + } + + @Override + public String getRule() { + return "Spend this mana only to cast creature spells or activate abilities of creatures"; + } +} + +class CastleGarenbrigConditionalMana extends ConditionalMana { + + CastleGarenbrigConditionalMana(Mana mana) { + super(mana); + this.staticText = "Spend this mana only to cast creature spells or activate abilities of creatures"; + addCondition(CastleGarenbrigManaCondition.instance); + } +} + +enum CastleGarenbrigManaCondition implements Condition { + instance; + + @Override + public boolean apply(Game game, Ability source) { + MageObject object = game.getObject(source.getSourceId()); + if (object != null && object.isCreature()) { + return true; + } + return false; + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index debc77c922..c45bb365e9 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -50,6 +50,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Brimstone Trebuchet", 116, Rarity.COMMON, mage.cards.b.BrimstoneTrebuchet.class)); cards.add(new SetCardInfo("Burning-Yard Trainer", 117, Rarity.UNCOMMON, mage.cards.b.BurningYardTrainer.class)); cards.add(new SetCardInfo("Castle Embereth", 239, Rarity.RARE, mage.cards.c.CastleEmbereth.class)); + cards.add(new SetCardInfo("Castle Garenbrig", 240, Rarity.RARE, mage.cards.c.CastleGarenbrig.class)); cards.add(new SetCardInfo("Castle Vantress", 242, Rarity.RARE, mage.cards.c.CastleVantress.class)); cards.add(new SetCardInfo("Cauldron Familiar", 81, Rarity.UNCOMMON, mage.cards.c.CauldronFamiliar.class)); cards.add(new SetCardInfo("Charming Prince", 8, Rarity.RARE, mage.cards.c.CharmingPrince.class)); From d4c06bcbe52ef1911c01f157a668a54961dac52c Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Tue, 17 Sep 2019 21:15:13 -0400 Subject: [PATCH 180/373] Implemented Syr Faren, the Hengehammer --- .../mage/cards/s/SyrFarenTheHengehammer.java | 60 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 61 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/s/SyrFarenTheHengehammer.java diff --git a/Mage.Sets/src/mage/cards/s/SyrFarenTheHengehammer.java b/Mage.Sets/src/mage/cards/s/SyrFarenTheHengehammer.java new file mode 100644 index 0000000000..c4e4071fc7 --- /dev/null +++ b/Mage.Sets/src/mage/cards/s/SyrFarenTheHengehammer.java @@ -0,0 +1,60 @@ +package mage.cards.s; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.AttacksTriggeredAbility; +import mage.abilities.dynamicvalue.DynamicValue; +import mage.abilities.dynamicvalue.common.SourcePermanentPowerCount; +import mage.abilities.effects.common.continuous.BoostTargetEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; +import mage.constants.SuperType; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterAttackingCreature; +import mage.filter.predicate.permanent.AnotherPredicate; +import mage.target.TargetPermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class SyrFarenTheHengehammer extends CardImpl { + + private static final DynamicValue xValue = new SourcePermanentPowerCount(); + private static final FilterPermanent filter + = new FilterAttackingCreature("another target attacking creature"); + + static { + filter.add(AnotherPredicate.instance); + } + + public SyrFarenTheHengehammer(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{G}{G}"); + + this.addSuperType(SuperType.LEGENDARY); + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.KNIGHT); + this.power = new MageInt(2); + this.toughness = new MageInt(2); + + // Whenever Syr Faren, the Hengehammer attacks, another target attacking creature gets +X/+X until end of turn, where X is Syr Faren's power. + Ability ability = new AttacksTriggeredAbility( + new BoostTargetEffect(xValue, xValue, Duration.EndOfTurn), false + ); + ability.addTarget(new TargetPermanent(filter)); + this.addAbility(ability); + } + + private SyrFarenTheHengehammer(final SyrFarenTheHengehammer card) { + super(card); + } + + @Override + public SyrFarenTheHengehammer copy() { + return new SyrFarenTheHengehammer(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index c45bb365e9..795cb6b743 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -199,6 +199,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Syr Alin, the Lion's Claw", 32, Rarity.UNCOMMON, mage.cards.s.SyrAlinTheLionsClaw.class)); cards.add(new SetCardInfo("Syr Carah, the Bold", 145, Rarity.UNCOMMON, mage.cards.s.SyrCarahTheBold.class)); cards.add(new SetCardInfo("Syr Elenora, the Discerning", 67, Rarity.UNCOMMON, mage.cards.s.SyrElenoraTheDiscerning.class)); + cards.add(new SetCardInfo("Syr Faren, the Hengehammer", 177, Rarity.UNCOMMON, mage.cards.s.SyrFarenTheHengehammer.class)); cards.add(new SetCardInfo("Syr Gwyn, Hero of Ashvale", 330, Rarity.MYTHIC, mage.cards.s.SyrGwynHeroOfAshvale.class)); cards.add(new SetCardInfo("Syr Konrad, the Grim", 107, Rarity.UNCOMMON, mage.cards.s.SyrKonradTheGrim.class)); cards.add(new SetCardInfo("Tall as a Beanstalk", 178, Rarity.COMMON, mage.cards.t.TallAsABeanstalk.class)); From 3e7c896e77e360d66632f9ede0f7b12c077590b6 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Tue, 17 Sep 2019 21:20:11 -0400 Subject: [PATCH 181/373] Implemented Realm-Cloaked Giant --- .../src/mage/cards/r/RealmCloakedGiant.java | 52 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 53 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/r/RealmCloakedGiant.java diff --git a/Mage.Sets/src/mage/cards/r/RealmCloakedGiant.java b/Mage.Sets/src/mage/cards/r/RealmCloakedGiant.java new file mode 100644 index 0000000000..ea2c8bdd57 --- /dev/null +++ b/Mage.Sets/src/mage/cards/r/RealmCloakedGiant.java @@ -0,0 +1,52 @@ +package mage.cards.r; + +import mage.MageInt; +import mage.abilities.effects.common.DestroyAllEffect; +import mage.abilities.keyword.VigilanceAbility; +import mage.cards.AdventureCard; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.filter.common.FilterCreaturePermanent; +import mage.filter.predicate.Predicates; +import mage.filter.predicate.mageobject.SubtypePredicate; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class RealmCloakedGiant extends AdventureCard { + + private static final FilterCreaturePermanent filter + = new FilterCreaturePermanent("non-Giant creatures"); + + static { + filter.add(Predicates.not(new SubtypePredicate(SubType.GIANT))); + } + + public RealmCloakedGiant(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, new CardType[]{CardType.SORCERY}, "{5}{W}{W}", "{5}{W}{W}", "{3}{W}{W}"); + + this.subtype.add(SubType.GIANT); + this.power = new MageInt(7); + this.toughness = new MageInt(7); + + // Vigilance + this.addAbility(VigilanceAbility.getInstance()); + + // Cast Off + // Destroy all non-Giant creatures. + this.getAdventureSpellAbility().addEffect(new DestroyAllEffect(filter)); + } + + private RealmCloakedGiant(final RealmCloakedGiant card) { + super(card); + } + + @Override + public RealmCloakedGiant copy() { + return new RealmCloakedGiant(this); + } +} +// clock up diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 795cb6b743..0d6c03ec9a 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -161,6 +161,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Raging Redcap", 134, Rarity.COMMON, mage.cards.r.RagingRedcap.class)); cards.add(new SetCardInfo("Rally for the Throne", 25, Rarity.UNCOMMON, mage.cards.r.RallyForTheThrone.class)); cards.add(new SetCardInfo("Rankle, Master of Pranks", 101, Rarity.MYTHIC, mage.cards.r.RankleMasterOfPranks.class)); + cards.add(new SetCardInfo("Realm-Cloaked Giant", 26, Rarity.MYTHIC, mage.cards.r.RealmCloakedGiant.class)); cards.add(new SetCardInfo("Reave Soul", 103, Rarity.COMMON, mage.cards.r.ReaveSoul.class)); cards.add(new SetCardInfo("Redcap Melee", 135, Rarity.UNCOMMON, mage.cards.r.RedcapMelee.class)); cards.add(new SetCardInfo("Redcap Raiders", 136, Rarity.COMMON, mage.cards.r.RedcapRaiders.class)); From 3f125dcca729b63b663c6ad65219b6e9e73e1fee Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 18 Sep 2019 08:05:02 -0400 Subject: [PATCH 182/373] fixed Wishclaw Talisman activation cost (fixes #5991) --- Mage.Sets/src/mage/cards/w/WishclawTalisman.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Mage.Sets/src/mage/cards/w/WishclawTalisman.java b/Mage.Sets/src/mage/cards/w/WishclawTalisman.java index ea39ffbac2..381a63d977 100644 --- a/Mage.Sets/src/mage/cards/w/WishclawTalisman.java +++ b/Mage.Sets/src/mage/cards/w/WishclawTalisman.java @@ -48,7 +48,7 @@ public final class WishclawTalisman extends CardImpl { Zone.BATTLEFIELD, new WishclawTalismanEffect(), new GenericManaCost(1), MyTurnCondition.instance ); ability.addCost(new TapSourceCost()); - ability.addCost(new RemoveCountersSourceCost(CounterType.WISH.createInstance(3))); + ability.addCost(new RemoveCountersSourceCost(CounterType.WISH.createInstance())); this.addAbility(ability); } From c6b95b02d22fc0d4fc243a1b4f20882acad3a193 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 18 Sep 2019 08:07:04 -0400 Subject: [PATCH 183/373] fixed Goryo's Vengeance targeting noncreature legendary cards (fixes #5992) --- .../src/mage/cards/g/GoryosVengeance.java | 55 +++++++++---------- 1 file changed, 27 insertions(+), 28 deletions(-) diff --git a/Mage.Sets/src/mage/cards/g/GoryosVengeance.java b/Mage.Sets/src/mage/cards/g/GoryosVengeance.java index d05257c919..45b8fb8753 100644 --- a/Mage.Sets/src/mage/cards/g/GoryosVengeance.java +++ b/Mage.Sets/src/mage/cards/g/GoryosVengeance.java @@ -1,4 +1,3 @@ - package mage.cards.g; import mage.abilities.Ability; @@ -16,6 +15,7 @@ import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.*; import mage.filter.FilterCard; +import mage.filter.common.FilterCreatureCard; import mage.filter.predicate.mageobject.SupertypePredicate; import mage.game.Game; import mage.game.permanent.Permanent; @@ -26,19 +26,18 @@ import mage.target.targetpointer.FixedTarget; import java.util.UUID; /** - * * @author LevelX2 */ public final class GoryosVengeance extends CardImpl { - private static final FilterCard filter = new FilterCard("legendary creature card"); + private static final FilterCard filter = new FilterCreatureCard("legendary creature card"); static { filter.add(new SupertypePredicate(SuperType.LEGENDARY)); } public GoryosVengeance(UUID ownerId, CardSetInfo setInfo) { - super(ownerId,setInfo,new CardType[]{CardType.INSTANT},"{1}{B}"); + super(ownerId, setInfo, new CardType[]{CardType.INSTANT}, "{1}{B}"); this.subtype.add(SubType.ARCANE); // Return target legendary creature card from your graveyard to the battlefield. That creature gains haste. Exile it at the beginning of the next end step. @@ -49,7 +48,7 @@ public final class GoryosVengeance extends CardImpl { this.addAbility(new SpliceOntoArcaneAbility("{2}{B}")); } - public GoryosVengeance(final GoryosVengeance card) { + private GoryosVengeance(final GoryosVengeance card) { super(card); } @@ -61,12 +60,12 @@ public final class GoryosVengeance extends CardImpl { class GoryosVengeanceEffect extends OneShotEffect { - public GoryosVengeanceEffect() { + GoryosVengeanceEffect() { super(Outcome.PutCardInPlay); this.staticText = "Return target legendary creature card from your graveyard to the battlefield. That creature gains haste. Exile it at the beginning of the next end step"; } - public GoryosVengeanceEffect(final GoryosVengeanceEffect effect) { + private GoryosVengeanceEffect(final GoryosVengeanceEffect effect) { super(effect); } @@ -78,27 +77,27 @@ class GoryosVengeanceEffect extends OneShotEffect { @Override public boolean apply(Game game, Ability source) { Player controller = game.getPlayer(source.getControllerId()); - if (controller != null) { - Card card = game.getCard(targetPointer.getFirst(game, source)); - if (card != null) { - if (controller.moveCards(card, Zone.BATTLEFIELD, source, game)) { - Permanent permanent = game.getPermanent(card.getId()); - if (permanent != null) { - // Haste - ContinuousEffect effect = new GainAbilityTargetEffect(HasteAbility.getInstance(), Duration.Custom); - effect.setTargetPointer(new FixedTarget(permanent, game)); - game.addEffect(effect, source); - // Exile it at end of turn - Effect exileEffect = new ExileTargetEffect("Exile " + permanent.getName() + " at the beginning of the next end step"); - exileEffect.setTargetPointer(new FixedTarget(permanent, game)); - DelayedTriggeredAbility delayedAbility = new AtTheBeginOfNextEndStepDelayedTriggeredAbility(exileEffect); - game.addDelayedTriggeredAbility(delayedAbility, source); - return true; - - } - } - } + if (controller == null) { + return false; } - return false; + Card card = game.getCard(targetPointer.getFirst(game, source)); + if (card == null || !controller.moveCards(card, Zone.BATTLEFIELD, source, game)) { + return false; + } + Permanent permanent = game.getPermanent(card.getId()); + if (permanent == null) { + return false; + } + // Haste + ContinuousEffect effect = new GainAbilityTargetEffect(HasteAbility.getInstance(), Duration.Custom); + effect.setTargetPointer(new FixedTarget(permanent, game)); + game.addEffect(effect, source); + // Exile it at end of turn + Effect exileEffect = new ExileTargetEffect("Exile " + permanent.getName() + " at the beginning of the next end step"); + exileEffect.setTargetPointer(new FixedTarget(permanent, game)); + DelayedTriggeredAbility delayedAbility = new AtTheBeginOfNextEndStepDelayedTriggeredAbility(exileEffect); + game.addDelayedTriggeredAbility(delayedAbility, source); + return true; + } } From ecb139c6d0e5d8ac35157a43eb1e7bfbf94f9b14 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 18 Sep 2019 08:08:20 -0400 Subject: [PATCH 184/373] fixed Feasting Troll King activated ability not working --- Mage.Sets/src/mage/cards/f/FeastingTrollKing.java | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/Mage.Sets/src/mage/cards/f/FeastingTrollKing.java b/Mage.Sets/src/mage/cards/f/FeastingTrollKing.java index 7ceaa6025c..8a8955c7da 100644 --- a/Mage.Sets/src/mage/cards/f/FeastingTrollKing.java +++ b/Mage.Sets/src/mage/cards/f/FeastingTrollKing.java @@ -8,7 +8,7 @@ import mage.abilities.condition.common.MyTurnCondition; import mage.abilities.costs.common.SacrificeTargetCost; import mage.abilities.decorator.ConditionalInterveningIfTriggeredAbility; import mage.abilities.effects.common.CreateTokenEffect; -import mage.abilities.effects.common.ReturnSourceFromGraveyardToHandEffect; +import mage.abilities.effects.common.ReturnSourceFromGraveyardToBattlefieldEffect; import mage.abilities.keyword.TrampleAbility; import mage.abilities.keyword.VigilanceAbility; import mage.cards.CardImpl; @@ -53,8 +53,8 @@ public final class FeastingTrollKing extends CardImpl { // Sacrifice three Foods: Return Feasting Troll King from your graveyard to the battlefield. Activate this ability only during your turn. this.addAbility(new ActivateIfConditionActivatedAbility( - Zone.BATTLEFIELD, - new ReturnSourceFromGraveyardToHandEffect(), + Zone.GRAVEYARD, + new ReturnSourceFromGraveyardToBattlefieldEffect(), new SacrificeTargetCost(new TargetControlledPermanent(3, filter)), MyTurnCondition.instance )); From f0dd7854d1ba4edd5e49fd9bdfd4b2d60775ff89 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 18 Sep 2019 08:11:17 -0400 Subject: [PATCH 185/373] fixed Irencrag Feat not adding mana --- Mage.Sets/src/mage/cards/i/IrencragFeat.java | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/Mage.Sets/src/mage/cards/i/IrencragFeat.java b/Mage.Sets/src/mage/cards/i/IrencragFeat.java index 8ff350b5ea..022811c4af 100644 --- a/Mage.Sets/src/mage/cards/i/IrencragFeat.java +++ b/Mage.Sets/src/mage/cards/i/IrencragFeat.java @@ -1,8 +1,11 @@ package mage.cards.i; +import mage.Mana; import mage.abilities.Ability; import mage.abilities.effects.ContinuousRuleModifyingEffectImpl; +import mage.abilities.effects.Effect; import mage.abilities.effects.OneShotEffect; +import mage.abilities.effects.mana.BasicManaEffect; import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.CardType; @@ -38,6 +41,8 @@ public final class IrencragFeat extends CardImpl { class IrencragFeatEffect extends OneShotEffect { + private static final Effect effect = new BasicManaEffect(Mana.RedMana(7)); + IrencragFeatEffect() { super(Outcome.Benefit); staticText = "Add seven {R}. You can cast only one more spell this turn."; @@ -60,7 +65,7 @@ class IrencragFeatEffect extends OneShotEffect { } int spellsCast = watcher.getAmountOfSpellsPlayerCastOnCurrentTurn(source.getControllerId()); game.addEffect(new IrencragFeatCantCastEffect(spellsCast), source); - return true; + return effect.apply(game, source); } } From f31669f7efcfe50cbd805aa7d8b7653a530ed2e2 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 18 Sep 2019 08:12:59 -0400 Subject: [PATCH 186/373] updated ELD spoiler --- Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 2 +- Utils/mtg-cards-data.txt | 12 +++++++++++- 2 files changed, 12 insertions(+), 2 deletions(-) diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 0d6c03ec9a..6040667815 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -213,7 +213,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Thunderous Snapper", 215, Rarity.UNCOMMON, mage.cards.t.ThunderousSnapper.class)); cards.add(new SetCardInfo("Tome Raider", 68, Rarity.COMMON, mage.cards.t.TomeRaider.class)); cards.add(new SetCardInfo("Tome of Legends", 332, Rarity.RARE, mage.cards.t.TomeOfLegends.class)); - cards.add(new SetCardInfo("Torbran, Thane of Red Fell", 367, Rarity.RARE, mage.cards.t.TorbranThaneOfRedFell.class)); + cards.add(new SetCardInfo("Torbran, Thane of Red Fell", 147, Rarity.RARE, mage.cards.t.TorbranThaneOfRedFell.class)); cards.add(new SetCardInfo("Tournament Grounds", 248, Rarity.UNCOMMON, mage.cards.t.TournamentGrounds.class)); cards.add(new SetCardInfo("Trail of Crumbs", 179, Rarity.UNCOMMON, mage.cards.t.TrailOfCrumbs.class)); cards.add(new SetCardInfo("Trapped in the Tower", 33, Rarity.COMMON, mage.cards.t.TrappedInTheTower.class)); diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index 5d18eddc36..a1ded3089e 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -35993,7 +35993,9 @@ Island|Commander 2019|291|C||Basic Land - Island|||({T}: Add {U}.)| Swamp|Commander 2019|294|C||Basic Land - Swamp|||({T}: Add {B}.)| Mountain|Commander 2019|297|C||Basic Land - Mountain|||({T}: Add {R}.)| Forest|Commander 2019|300|C||Basic Land - Forest|||({T}: Add {G}.)| +Acclaimed Contender|Throne of Eldraine|1|R|{2}{W}|Creature - Human Knight|3|3|When Acclaimed Contender enters the battlefield, if you control another Knight, look at the top five cards of your library. You may reveal a Knight, Aura, Equipment, or legendary artifact card from among them and put it into your hand. Put the rest on the bottom of your library in a random order.| All That Glitters|Throne of Eldraine|2|U|{1}{W}|Enchantment - Aura|||Enchant creature$Enchanted creature gets +1/+1 for each artifact and/or enchantment you control.| +Archon of Absolution|Throne of Eldraine|3|U|{3}{W}|Creature - Archon|3|2|Flying$Protection from white$Creatures can't attack you or a planeswalker you control unless their controller pays {1} for each of those creatures.| Ardenvale Paladin|Throne of Eldraine|4|C|{3}{W}|Creature - Human Knight|2|5|Adamant — If at least three white mana was spent to cast this spell, Ardenvale Paladin enters the battlefield with a +1/+1 counter on it.| Ardenvale Tactician|Throne of Eldraine|5|C|{1}{W}{W}|Creature - Human Knight|2|3|Flying| Dizzying Swoop|Throne of Eldraine|5|C|{1}{W}|Instant - Adventure|2|3|Tap up to two target creatures.| @@ -36018,6 +36020,8 @@ Rally for the Throne|Throne of Eldraine|25|U|{2}{W}|Instant|||Create two 1/1 whi Cast Off|Throne of Eldraine|26|M|{3}{W}{W}|Sorcery - Adventure|7|7|Destroy all non-Giant creatures.| Realm-Cloaked Giant|Throne of Eldraine|26|M|{5}{W}{W}|Creature - Giant|7|7|Vigilance| Righteousness|Throne of Eldraine|27|U|{W}|Instant|||Target blocking creature gets +7/+7 until end of turn.| +Shepherd of the Flock|Throne of Eldraine|28|U|{1}{W}|Creature - Human Peasant|3|1|| +Usher to Safety|Throne of Eldraine|28|U|{W}|Instant - Adventure|3|1|Return target permanent you control to its owner's hand.| Shining Armor|Throne of Eldraine|29|C|{1}{W}|Artifact - Equipment|||Flash$When Shining Armor enters the battlefield, attach it to target Knight you control.$Equipped creature gets +0/+2 and has vigilance.$Equip {3}| Silverflame Ritual|Throne of Eldraine|30|C|{3}{W}|Sorcery|||Put a +1/+1 counter on each creature you control.$Adamant — If at least three white mana was spent to cast this spell, creatures you control gain vigilance until end of turn.| On Alert|Throne of Eldraine|31|C|{2}{W}|Instant - Adventure|2|1|Target creature gets +2/+2 until end of turn. Untap it.| @@ -36031,6 +36035,8 @@ Animating Faerie|Throne of Eldraine|38|U|{2}{U}|Creature - Faerie|2|2|Flying| Bring to Life|Throne of Eldraine|38|U|{2}{U}|Sorcery - Adventure|2|2|Target noncreature artifact you control becomes a 0/0 artifact creature. Put four +1/+1 counters on it.| Corridor Monitor|Throne of Eldraine|41|C|{1}{U}|Artifact Creature - Construct|1|4|When Corridor Monitor enters the battlefield, untap target artifact or creature you control.| Emry, Lurker of the Loch|Throne of Eldraine|43|R|{2}{U}|Legendary Creature - Merfolk Wizard|1|2|This spell costs {1} less to cast for each artifact you control.$When Emry, Lurker of the Loch enters the battlefield, put the top four cards of your library into your graveyard.${T}: Choose target artifact card in your graveyard. You may cast that card this turn.| +Fae of Wishes|Throne of Eldraine|44|R|{1}{U}|Creature - Faerie Wizard|1|4|Flying${1}{U}, Discard two cards: Return Fae of Wishes to its owner's hand.| +Granted|Throne of Eldraine|44|R|{3}{U}|Creature - Faerie Wizard|1|4|You may choose a noncreature card you own from outside the game, reveal it, and put it into your hand.| Faerie Vandal|Throne of Eldraine|45|U|{1}{U}|Creature - Faerie Rogue|1|2|Flash$Flying$Whenever you draw your second card each turn, put a +1/+1 counter on Faerie Vandal.| Folio of Fancies|Throne of Eldraine|46|R|{1}{U}|Artifact|||Players have no maximum hand size.${X}{X}, {T}: Each player draws X cards.${2}{U}, {T}: Each opponent puts a number of cards equal to the number of cards in their hand from the top of their library into their graveyard.| Frogify|Throne of Eldraine|47|U|{1}{U}|Enchantment - Aura|||Enchant creature$Enchanted creature loses all abilities and is a blue Frog creature with base power and toughness 1/1.| @@ -36117,6 +36123,7 @@ Skullknocker Ogre|Throne of Eldraine|142|U|{3}{R}|Creature - Ogre|4|3|Whenever S Slaying Fire|Throne of Eldraine|143|U|{2}{R}|Instant|||Slaying Fire deals 3 damage to any target.$Adamant — If at least three red mana was spent to cast this spell, it deals 4 damage instead.| Sundering Stroke|Throne of Eldraine|144|R|{6}{R}|Sorcery|||Sundering Stroke deals 7 damage divided as you choose among one, two, or three targets. If at least seven red mana was spent to cast this spell, instead Sundering Stroke deals 7 damage to each of those permanents and/or players.| Syr Carah, the Bold|Throne of Eldraine|145|U|{3}{R}{R}|Legendary Creature - Human Knight|3|3|When Syr Carah, the Bold or an instant or sorcery spell you control deals damage to a player, exile the top card of your library. You may play that card this turn.${T}: Syr Carah deals 1 damage to any target.| +Torbran, Thane of Red Fell|Throne of Eldraine|147|R|{1}{R}{R}{R}|Legendary Creature - Dwarf Noble|2|4|If a red source you control would deal damage to an opponent or a permanent an opponent controls, it deals that much damage plus 2 instead.| Weaselback Redcap|Throne of Eldraine|148|C|{R}|Creature - Goblin Knight|1|1|{1}{R}: Weaselback Redcap gets +2/+0 until end of turn.| Beanstalk Giant|Throne of Eldraine|149|U|{6}{G}|Creature - Giant|*|*|Beanstalk Giant's power and toughness are each equal to the number of lands you control.| Fertile Footsteps|Throne of Eldraine|149|U|{2}{G}|Sorcery - Adventure|*|*|Search your library for a basic land card, put it onto the battlefield, then shuffle your library.| @@ -36128,6 +36135,8 @@ Fell the Pheasant|Throne of Eldraine|153|C|{1}{G}|Instant|||Fell the Pheasant de Fierce Witchstalker|Throne of Eldraine|154|C|{2}{G}{G}|Creature - Wolf|4|4|Trample$When Fierce Witchstalker enters the battlefield, create a Food token.| Flaxen Intruder|Throne of Eldraine|155|U|{G}|Creature - Human Berserker|1|2|Whenever Flaxen Intruder deals combat damage to a player, you may sacrifice it. When you do, destroy target artifact or enchantment.| Welcome Home|Throne of Eldraine|155|U|{5}{G}{G}|Sorcery - Adventure|1|2|Create three 2/2 green Bear creature tokens.| +Garenbrig Carver|Throne of Eldraine|156|C|{3}{G}|Creature - Human Warrior|3|2|| +Shield's Might|Throne of Eldraine|156|C|{1}{G}|Instant - Adventure|3|2|Target creature gets +2/+2 until end of turn.| Garenbrig Paladin|Throne of Eldraine|157|C|{4}{G}|Creature - Giant Knight|4|4|Adamant — If at least three green mana was spent to cast this spell, Garenbrig Paladin enters the battlefield with a +1/+1 counter on it.$Garenbrig Paladin can't be blocked by creatures with power 2 or less.| Garenbrig Squire|Throne of Eldraine|158|C|{1}{G}|Creature - Human Soldier|2|2|Whenever you cast a creature spell that has an Adventure, Garenbrig Squire gets +1/+1 until end of turn.| Giant Opportunity|Throne of Eldraine|159|U|{2}{G}|Sorcery|||You may sacrifice two Foods. If you do, create a 7/7 green Giant creature token. Otherwise, create three Food tokens.| @@ -36154,6 +36163,7 @@ Wicked Wolf|Throne of Eldraine|181|R|{2}{G}{G}|Creature - Wolf|3|3|When Wicked W Wildborn Preserver|Throne of Eldraine|182|R|{1}{G}|Creature - Elf Archer|2|2|Flash$Reach$Whenever another non-Human creature enters the battlefield under your control, you may pay {X}. When you do, put X +1/+1 counters on Wildborn Preserver.| Wildwood Tracker|Throne of Eldraine|183|C|{G}|Creature - Elf Warrior|1|1|Whenever Wildwood Tracker attacks or blocks, if you control another non-Human creature, Wildwood Tracker gets +1/+1 until end of turn.| Wolf's Quarry|Throne of Eldraine|184|C|{4}{G}{G}|Sorcery|||Create three 1/1 green Boar creature tokens with "When this creature dies, create a Food token."| +Yorvo, Lord of Garenbrig|Throne of Eldraine|185|R|{G}{G}{G}|Legendary Creature - Giant Noble|0|0|Yorvo, Lord of Garenbrig enters the battlefield with four +1/+1 counters on it.$Whenever another green creature enters the battlefield under your control, put a +1/+1 counter on Yorvo. Then if that creature's power is greater than Yorvo's power, put another +1/+1 counter on Yorvo.| Dance of the Manse|Throne of Eldraine|186|R|{X}{W}{U}|Sorcery|||Return up to X target artifact and/or non-Aura enchantment cards each with converted mana cost X or less from your graveyard to the battlefield. If X is 6 or more, those permanents are 4/4 creatures in addition to their other types.| Doom Foretold|Throne of Eldraine|187|R|{2}{W}{B}|Enchantment|||At the beginning of each player's upkeep, that player sacrifices a nonland, nontoken permanent. If that player can't, they discard a card, they lose 2 life, you draw a card, you gain 2 life, you create a 2/2 white Knight creature token with vigilance, then you sacrifice Doom Foretold.| Drown in the Loch|Throne of Eldraine|188|U|{U}{B}|Instant|||Choose one —$• Counter target spell with converted mana cost less than or equal to the number of cards in its controller's graveyard.$• Destroy target creature with converted mana cost less than or equal to the number of cards in its controller's graveyard.| @@ -36170,6 +36180,7 @@ The Royal Scions|Throne of Eldraine|199|M|{1}{U}{R}|Legendary Planeswalker - Wil Savvy Hunter|Throne of Eldraine|200|U|{1}{B}{G}|Creature - Human Warrior|3|3|Whenever Savvy Hunter attacks or blocks, create a Food token.$Sacrifice two Foods: Draw a card.| Shinechaser|Throne of Eldraine|201|U|{1}{W}{U}|Creature - Faerie|1|1|Flying, vigilance$Shinechaser gets +1/+1 as long as you control an artifact.$Shinechaser gets +1/+1 as long as you control an enchantment.| Steelclaw Lance|Throne of Eldraine|202|U|{B}{R}|Artifact - Equipment|||Equipped creature gets +2/+2.$Equip Knight {1}$Equip {3}| +Stormfist Crusader|Throne of Eldraine|203|R|{B}{R}|Creature - Human Knight|2|2|Menace$At the beginning of your upkeep, each player draws a card and loses 1 life.| Wandermare|Throne of Eldraine|204|U|{1}{G}{W}|Creature - Horse|3|3|Whenever you cast a creature spell that has an Adventure, put a +1/+1 counter on Wandermare.| Wintermoor Commander|Throne of Eldraine|205|U|{W}{B}|Creature - Human Knight|2|*|Deathtouch$Wintermoor Commander's toughness is equal to the number of Knights you control.$Whenever Wintermoor Commander attacks, another target Knight you control gains indestructible until end of turn.| Arcanist's Owl|Throne of Eldraine|206|U|{W/U}{W/U}{W/U}{W/U}|Artifact Creature - Bird|3|3|Flying$When Arcanist's Owl enters the battlefield, look at the top four cards of your library. You may reveal an artifact or enchantment card from among them and put it into your hand. Put the rest on the bottom of your library in a random order.| @@ -36233,4 +36244,3 @@ Syr Gwyn, Hero of Ashvale|Throne of Eldraine|330|M|{3}{R}{W}{B}|Legendary Creatu Arcane Signet|Throne of Eldraine|331|C|{2}|Artifact|||{T}: Add one mana of any color in your commander's color identity.| Tome of Legends|Throne of Eldraine|332|R|{2}|Artifact|||Tome of Legends enters the battlefield with a page counter on it.$Whenever your commander enters the battlefield or attacks, put a page counter on Tome of Legends.${1}, {T}, Remove a page counter from Tome of Legends: Draw a card.| Command Tower|Throne of Eldraine|333|C||Land|||{T}: Add one mana of any color in your commander's color identity.| -Torbran, Thane of Red Fell|Throne of Eldraine|367|R|{1}{R}{R}{R}|Legendary Creature - Dwarf Noble|2|4|If a red source you control would deal damage to an opponent or a permanent an opponent controls, it deals that much damage plus 2 instead.| From eaacc0c824913288aa5d0657a578347f403430fb Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 18 Sep 2019 10:05:49 -0400 Subject: [PATCH 187/373] updated ELD spoiler --- Utils/mtg-cards-data.txt | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index a1ded3089e..6226a6b065 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -36056,7 +36056,9 @@ Stolen by the Fae|Throne of Eldraine|66|R|{X}{U}{U}|Sorcery|||Return target crea Syr Elenora, the Discerning|Throne of Eldraine|67|U|{3}{U}{U}|Legendary Creature - Human Knight|*|4|Syr Elenora, the Discerning's power is equal to the number of cards in your hand.$When Syr Elenora enters the battlefield, draw a card.$Spells your opponents cast that target Syr Elenora cost {2} more to cast.| Tome Raider|Throne of Eldraine|68|C|{2}{U}|Creature - Faerie|1|1|Flying$When Tome Raider enters the battlefield, draw a card.| Turn into a Pumpkin|Throne of Eldraine|69|U|{3}{U}|Instant|||Return target nonland permanent to its owner's hand. Draw a card.$Adamant — If at least three blue mana was spent to cast this spell, create a Food token.| +Unexplained Vision|Throne of Eldraine|70|C|{4}{U}|Sorcery|||Draw three cards.$Adamant — If at least three blue mana was spent to cast this spell, scry 3.| Vantress Gargoyle|Throne of Eldraine|71|R|{1}{U}|Artifact Creature - Gargoyle|5|4|Flying$Vantress Gargoyle can't attack unless defending player has seven or more cards in their graveyard.$Vantress Gargoyle can't block unless you have four or more cards in hand.${T}: Each player puts the top card of their library into their graveyard.| +Vantress Paladin|Throne of Eldraine|72|C|{3}{U}|Creature - Human Knight|2|2|Flying$Adamant — If at least three blue mana was spent to cast this spell, Vantress Paladin enters the battlefield with an additional +1/+1 counter on it.| Wishful Merfolk|Throne of Eldraine|73|C|{1}{U}|Creature - Merfolk|3|2|Defender${1}{U}: Wishful Merfolk loses defender and becomes a Human until end of turn.| Witching Well|Throne of Eldraine|74|C|{U}|Artifact|||When Witching Well enters the battlefield, scry 2.${3}{U}, Sacrifice Witching Well: Draw two cards.| Ayara, First of Locthwain|Throne of Eldraine|75|R|{B}{B}{B}|Legendary Creature - Elf Noble|2|3|Whenever Ayara, First of Locthwain or another black creature enters the battlefield under your control, each opponent loses 1 life and you gain 1 life.${T}, Sacrifice another black creature: Draw a card.| @@ -36208,7 +36210,7 @@ Spinning Wheel|Throne of Eldraine|234|U|{3}|Artifact|||{T}: Add one mana of any Stonecoil Serpent|Throne of Eldraine|235|R|{X}|Artifact Creature - Snake|0|0|Reach, trample, protection from multicolored$Stonecoil Serpent enters the battlefield with X +1/+1 counters on it.| Witch's Oven|Throne of Eldraine|237|U|{1}|Artifact|||{T}, Sacrifice a creature: Create a Food token. If the sacrificed creature's toughness was 4 or greater, create two Food tokens instead.| Castle Embereth|Throne of Eldraine|239|R||Land|||Castle Embereth enters the battlefield tapped unless you control a Mountain.${T}: Add {R}.${1}{R}{R}, {T}: Creatures you control get +1/+0 until end of turn.| -Castle Garenbrig|Throne of Eldraine|240|R||Land|||Castle Garenbrig enters the battlefield tapped unelss you control a Forest.${T}: Add {G}.${2}{G}{G}, {T}: Add six {G}. Spend this mana only to cast creature spells or activate abilities of creatures.| +Castle Garenbrig|Throne of Eldraine|240|R||Land|||Castle Garenbrig enters the battlefield tapped unless you control a Forest.${T}: Add {G}.${2}{G}{G}, {T}: Add six {G}. Spend this mana only to cast creature spells or activate abilities of creatures.| Castle Vantress|Throne of Eldraine|242|R||Land|||Castle Vantress enters the battlefield tapped unless you control an Island.${T}: Add {U}.${2}{U}{U}, {T}: Scry 2.| Idyllic Grange|Throne of Eldraine|246|C||Land - Plains|||({T}: Add {W}.)$Idyllic Grange enters the battlefield tapped unless you control three or more other Plains.$When Idyllic Grange enters the battlefield untapped, put a +1/+1 counter on target creature you control.| Tournament Grounds|Throne of Eldraine|248|U||Land|||{T}: Add {C}.${T}: Add {R}, {W}, or {B}. Spend this mana only to cast a Knight or Equipment spell.| From 0b4dd444a72fb2eea3bf8c98ced3460f8f62b0aa Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 18 Sep 2019 10:07:32 -0400 Subject: [PATCH 188/373] Implemented Vantress Paladin --- .../src/mage/cards/v/VantressPaladin.java | 50 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 51 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/v/VantressPaladin.java diff --git a/Mage.Sets/src/mage/cards/v/VantressPaladin.java b/Mage.Sets/src/mage/cards/v/VantressPaladin.java new file mode 100644 index 0000000000..2c1ef9dfef --- /dev/null +++ b/Mage.Sets/src/mage/cards/v/VantressPaladin.java @@ -0,0 +1,50 @@ +package mage.cards.v; + +import mage.MageInt; +import mage.abilities.common.EntersBattlefieldAbility; +import mage.abilities.condition.common.AdamantCondition; +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.counters.CounterType; +import mage.watchers.common.ManaSpentToCastWatcher; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class VantressPaladin extends CardImpl { + + public VantressPaladin(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{3}{U}"); + + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.KNIGHT); + this.power = new MageInt(2); + this.toughness = new MageInt(2); + + // Flying + this.addAbility(FlyingAbility.getInstance()); + + // Adamant — If at least three blue mana was spent to cast this spell, Vantress Paladin enters the battlefield with an additional +1/+1 counter on it. + this.addAbility(new EntersBattlefieldAbility( + new AddCountersSourceEffect(CounterType.P1P1.createInstance()), + AdamantCondition.BLUE, "
Adamant — " + + "If at least three blue mana was spent to cast this spell, " + + "{this} enters the battlefield with a +1/+1 counter on it.", "" + ), new ManaSpentToCastWatcher()); + } + + private VantressPaladin(final VantressPaladin card) { + super(card); + } + + @Override + public VantressPaladin copy() { + return new VantressPaladin(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 6040667815..5a3613005f 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -221,6 +221,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Tuinvale Treefolk", 180, Rarity.COMMON, mage.cards.t.TuinvaleTreefolk.class)); cards.add(new SetCardInfo("Turn into a Pumpkin", 69, Rarity.UNCOMMON, mage.cards.t.TurnIntoAPumpkin.class)); cards.add(new SetCardInfo("Vantress Gargoyle", 71, Rarity.RARE, mage.cards.v.VantressGargoyle.class)); + cards.add(new SetCardInfo("Vantress Paladin", 72, Rarity.COMMON, mage.cards.v.VantressPaladin.class)); cards.add(new SetCardInfo("Venerable Knight", 35, Rarity.UNCOMMON, mage.cards.v.VenerableKnight.class)); cards.add(new SetCardInfo("Wandermare", 204, Rarity.UNCOMMON, mage.cards.w.Wandermare.class)); cards.add(new SetCardInfo("Weaselback Redcap", 148, Rarity.COMMON, mage.cards.w.WeaselbackRedcap.class)); From 0bb3caa9505adb59ea0fc4e5bcd6ebaef719147d Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 18 Sep 2019 10:09:23 -0400 Subject: [PATCH 189/373] Implemented Unexplained Vision --- .../src/mage/cards/u/UnexplainedVision.java | 39 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 40 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/u/UnexplainedVision.java diff --git a/Mage.Sets/src/mage/cards/u/UnexplainedVision.java b/Mage.Sets/src/mage/cards/u/UnexplainedVision.java new file mode 100644 index 0000000000..bfca6cf922 --- /dev/null +++ b/Mage.Sets/src/mage/cards/u/UnexplainedVision.java @@ -0,0 +1,39 @@ +package mage.cards.u; + +import mage.abilities.condition.common.AdamantCondition; +import mage.abilities.decorator.ConditionalOneShotEffect; +import mage.abilities.effects.common.DrawCardSourceControllerEffect; +import mage.abilities.effects.keyword.ScryEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class UnexplainedVision extends CardImpl { + + public UnexplainedVision(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.SORCERY}, "{4}{U}"); + + // Draw three cards. + this.getSpellAbility().addEffect(new DrawCardSourceControllerEffect(3)); + + // Adamant — If at least three blue mana was spent to cast this spell, scry 3. + this.getSpellAbility().addEffect(new ConditionalOneShotEffect( + new ScryEffect(3), AdamantCondition.BLUE, "
Adamant — " + + "If at least three blue mana was spent to cast this spell, scry 3." + )); + } + + private UnexplainedVision(final UnexplainedVision card) { + super(card); + } + + @Override + public UnexplainedVision copy() { + return new UnexplainedVision(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 5a3613005f..d02f677d3a 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -220,6 +220,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("True Love's Kiss", 34, Rarity.COMMON, mage.cards.t.TrueLovesKiss.class)); cards.add(new SetCardInfo("Tuinvale Treefolk", 180, Rarity.COMMON, mage.cards.t.TuinvaleTreefolk.class)); cards.add(new SetCardInfo("Turn into a Pumpkin", 69, Rarity.UNCOMMON, mage.cards.t.TurnIntoAPumpkin.class)); + cards.add(new SetCardInfo("Unexplained Vision", 70, Rarity.COMMON, mage.cards.u.UnexplainedVision.class)); cards.add(new SetCardInfo("Vantress Gargoyle", 71, Rarity.RARE, mage.cards.v.VantressGargoyle.class)); cards.add(new SetCardInfo("Vantress Paladin", 72, Rarity.COMMON, mage.cards.v.VantressPaladin.class)); cards.add(new SetCardInfo("Venerable Knight", 35, Rarity.UNCOMMON, mage.cards.v.VenerableKnight.class)); From 1c701ecf7c1107907da49a403a883f55795a0faf Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 18 Sep 2019 10:17:21 -0400 Subject: [PATCH 190/373] added missing watcher --- Mage.Sets/src/mage/cards/u/UnexplainedVision.java | 2 ++ 1 file changed, 2 insertions(+) diff --git a/Mage.Sets/src/mage/cards/u/UnexplainedVision.java b/Mage.Sets/src/mage/cards/u/UnexplainedVision.java index bfca6cf922..3fb0d06e51 100644 --- a/Mage.Sets/src/mage/cards/u/UnexplainedVision.java +++ b/Mage.Sets/src/mage/cards/u/UnexplainedVision.java @@ -7,6 +7,7 @@ import mage.abilities.effects.keyword.ScryEffect; import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.CardType; +import mage.watchers.common.ManaSpentToCastWatcher; import java.util.UUID; @@ -26,6 +27,7 @@ public final class UnexplainedVision extends CardImpl { new ScryEffect(3), AdamantCondition.BLUE, "
Adamant — " + "If at least three blue mana was spent to cast this spell, scry 3." )); + this.getSpellAbility().addWatcher(new ManaSpentToCastWatcher()); } private UnexplainedVision(final UnexplainedVision card) { From 0982e36002be8b4fde6011eada5e1b04d3ca5ffd Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 18 Sep 2019 13:08:26 -0400 Subject: [PATCH 191/373] improved implementation of second draw triggers --- Mage.Sets/src/mage/cards/f/FaerieVandal.java | 68 ++---------------- .../mage/cards/j/JaceArcaneStrategist.java | 72 +++---------------- .../DrawSecondCardTriggeredAbility.java | 67 +++++++++++++++++ 3 files changed, 83 insertions(+), 124 deletions(-) create mode 100644 Mage/src/main/java/mage/abilities/common/DrawSecondCardTriggeredAbility.java diff --git a/Mage.Sets/src/mage/cards/f/FaerieVandal.java b/Mage.Sets/src/mage/cards/f/FaerieVandal.java index 7f45e7d8b9..dff975f655 100644 --- a/Mage.Sets/src/mage/cards/f/FaerieVandal.java +++ b/Mage.Sets/src/mage/cards/f/FaerieVandal.java @@ -1,7 +1,7 @@ package mage.cards.f; import mage.MageInt; -import mage.abilities.TriggeredAbilityImpl; +import mage.abilities.common.DrawSecondCardTriggeredAbility; import mage.abilities.effects.common.counter.AddCountersSourceEffect; import mage.abilities.keyword.FlashAbility; import mage.abilities.keyword.FlyingAbility; @@ -9,18 +9,13 @@ import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.CardType; import mage.constants.SubType; -import mage.constants.Zone; import mage.counters.CounterType; -import mage.game.Game; -import mage.game.events.GameEvent; import java.util.UUID; /** * @author jmharmon */ - - public final class FaerieVandal extends CardImpl { public FaerieVandal(UUID ownerId, CardSetInfo setInfo) { @@ -38,10 +33,12 @@ public final class FaerieVandal extends CardImpl { this.addAbility(FlyingAbility.getInstance()); // Whenever you draw your second card each turn, put a +1/+1 counter on Faerie Vandal. - this.addAbility(new FaerieVandalTriggeredAbility()); + this.addAbility(new DrawSecondCardTriggeredAbility( + new AddCountersSourceEffect(CounterType.P1P1.createInstance()), false + )); } - public FaerieVandal(final FaerieVandal card) { + private FaerieVandal(final FaerieVandal card) { super(card); } @@ -50,58 +47,3 @@ public final class FaerieVandal extends CardImpl { return new FaerieVandal(this); } } - -class FaerieVandalTriggeredAbility extends TriggeredAbilityImpl { - - private boolean triggeredOnce = false; - private boolean triggeredTwice = false; - - FaerieVandalTriggeredAbility() { - super(Zone.BATTLEFIELD, new AddCountersSourceEffect(CounterType.P1P1.createInstance()), false); - } - - private FaerieVandalTriggeredAbility(final FaerieVandalTriggeredAbility ability) { - super(ability); - this.triggeredOnce = ability.triggeredOnce; - this.triggeredTwice = ability.triggeredTwice; - } - - @Override - public boolean checkEventType(GameEvent event, Game game) { - return event.getType() == GameEvent.EventType.DREW_CARD - || event.getType() == GameEvent.EventType.END_PHASE_POST; - } - - @Override - public boolean checkTrigger(GameEvent event, Game game) { - if (event.getType() == GameEvent.EventType.END_PHASE_POST) { - triggeredOnce = triggeredTwice = false; - return false; - } - if (event.getType() == GameEvent.EventType.DREW_CARD - && event.getPlayerId().equals(controllerId)) { - if (triggeredOnce) { - if (triggeredTwice) { - return false; - } else { - triggeredTwice = true; - return true; - } - } else { - triggeredOnce = true; - return false; - } - } - return false; - } - - @Override - public String getRule() { - return "Whenever you draw your second card each turn, put a +1/+1 counter on {this}."; - } - - @Override - public FaerieVandalTriggeredAbility copy() { - return new FaerieVandalTriggeredAbility(this); - } -} diff --git a/Mage.Sets/src/mage/cards/j/JaceArcaneStrategist.java b/Mage.Sets/src/mage/cards/j/JaceArcaneStrategist.java index bbaeeef62d..cec4fe502c 100644 --- a/Mage.Sets/src/mage/cards/j/JaceArcaneStrategist.java +++ b/Mage.Sets/src/mage/cards/j/JaceArcaneStrategist.java @@ -1,18 +1,20 @@ package mage.cards.j; +import mage.abilities.Ability; import mage.abilities.LoyaltyAbility; -import mage.abilities.TriggeredAbilityImpl; +import mage.abilities.common.DrawSecondCardTriggeredAbility; import mage.abilities.common.PlaneswalkerEntersWithLoyaltyCountersAbility; import mage.abilities.effects.common.DrawCardSourceControllerEffect; import mage.abilities.effects.common.combat.CantBeBlockedAllEffect; import mage.abilities.effects.common.counter.AddCountersTargetEffect; 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.counters.CounterType; import mage.filter.StaticFilters; -import mage.game.Game; -import mage.game.events.GameEvent; import mage.target.common.TargetControlledCreaturePermanent; import java.util.UUID; @@ -30,7 +32,11 @@ public final class JaceArcaneStrategist extends CardImpl { this.addAbility(new PlaneswalkerEntersWithLoyaltyCountersAbility(4)); // Whenever you draw your second card each turn, put a +1/+1 counter on target creature you control. - this.addAbility(new JaceArcaneStrategistTriggeredAbility()); + Ability ability = new DrawSecondCardTriggeredAbility( + new AddCountersTargetEffect(CounterType.P1P1.createInstance()), false + ); + ability.addTarget(new TargetControlledCreaturePermanent()); + this.addAbility(ability); // +1: Draw a card. this.addAbility(new LoyaltyAbility(new DrawCardSourceControllerEffect(1), 1)); @@ -50,59 +56,3 @@ public final class JaceArcaneStrategist extends CardImpl { return new JaceArcaneStrategist(this); } } - -class JaceArcaneStrategistTriggeredAbility extends TriggeredAbilityImpl { - - private boolean triggeredOnce = false; - private boolean triggeredTwice = false; - - JaceArcaneStrategistTriggeredAbility() { - super(Zone.BATTLEFIELD, new AddCountersTargetEffect(CounterType.P1P1.createInstance()), false); - this.addTarget(new TargetControlledCreaturePermanent()); - } - - private JaceArcaneStrategistTriggeredAbility(final JaceArcaneStrategistTriggeredAbility ability) { - super(ability); - this.triggeredOnce = ability.triggeredOnce; - this.triggeredTwice = ability.triggeredTwice; - } - - @Override - public boolean checkEventType(GameEvent event, Game game) { - return event.getType() == GameEvent.EventType.DREW_CARD - || event.getType() == GameEvent.EventType.END_PHASE_POST; - } - - @Override - public boolean checkTrigger(GameEvent event, Game game) { - if (event.getType() == GameEvent.EventType.END_PHASE_POST) { - triggeredOnce = triggeredTwice = false; - return false; - } - if (event.getType() == GameEvent.EventType.DREW_CARD - && event.getPlayerId().equals(controllerId)) { - if (triggeredOnce) { - if (triggeredTwice) { - return false; - } else { - triggeredTwice = true; - return true; - } - } else { - triggeredOnce = true; - return false; - } - } - return false; - } - - @Override - public String getRule() { - return "Whenever you draw your second card each turn, put a +1/+1 counter on target creature you control."; - } - - @Override - public JaceArcaneStrategistTriggeredAbility copy() { - return new JaceArcaneStrategistTriggeredAbility(this); - } -} diff --git a/Mage/src/main/java/mage/abilities/common/DrawSecondCardTriggeredAbility.java b/Mage/src/main/java/mage/abilities/common/DrawSecondCardTriggeredAbility.java new file mode 100644 index 0000000000..becd3c41d1 --- /dev/null +++ b/Mage/src/main/java/mage/abilities/common/DrawSecondCardTriggeredAbility.java @@ -0,0 +1,67 @@ +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.watchers.common.CardsAmountDrawnThisTurnWatcher; + +/** + * @author TheElk801 + */ +public class DrawSecondCardTriggeredAbility extends TriggeredAbilityImpl { + + private boolean triggeredOnce = false; + + public DrawSecondCardTriggeredAbility(Effect effect, boolean optional) { + super(Zone.ALL, effect, optional); + this.addWatcher(new CardsAmountDrawnThisTurnWatcher()); + } + + private DrawSecondCardTriggeredAbility(final DrawSecondCardTriggeredAbility ability) { + super(ability); + this.triggeredOnce = ability.triggeredOnce; + } + + @Override + public boolean checkEventType(GameEvent event, Game game) { + return event.getType() == GameEvent.EventType.DREW_CARD + || event.getType() == GameEvent.EventType.END_PHASE_POST; + } + + @Override + public boolean checkTrigger(GameEvent event, Game game) { + if (event.getType() == GameEvent.EventType.END_PHASE_POST) { + triggeredOnce = false; + return false; + } + if (event.getType() != GameEvent.EventType.DREW_CARD + || !event.getPlayerId().equals(controllerId) + || game.getPermanent(sourceId) == null) { + return false; + } + if (triggeredOnce) { + return false; + } + CardsAmountDrawnThisTurnWatcher watcher = game.getState().getWatcher(CardsAmountDrawnThisTurnWatcher.class); + if (watcher == null) { + return false; + } + if (watcher.getAmountCardsDrawn(controllerId) > 1) { + triggeredOnce = true; + return true; + } + return false; + } + + @Override + public String getRule() { + return "Whenever you draw your second card each turn, " + super.getRule(); + } + + @Override + public DrawSecondCardTriggeredAbility copy() { + return new DrawSecondCardTriggeredAbility(this); + } +} From 56376117c496fec667059cbeb49588bf19e5ec5d Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 18 Sep 2019 13:09:22 -0400 Subject: [PATCH 192/373] fixed Piper of the Swarm boosting P/T rather than granting menace --- Mage.Sets/src/mage/cards/p/PiperOfTheSwarm.java | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/Mage.Sets/src/mage/cards/p/PiperOfTheSwarm.java b/Mage.Sets/src/mage/cards/p/PiperOfTheSwarm.java index ceac31b061..028bd0c5c1 100644 --- a/Mage.Sets/src/mage/cards/p/PiperOfTheSwarm.java +++ b/Mage.Sets/src/mage/cards/p/PiperOfTheSwarm.java @@ -8,13 +8,15 @@ import mage.abilities.costs.common.SacrificeTargetCost; import mage.abilities.costs.common.TapSourceCost; import mage.abilities.costs.mana.ManaCostsImpl; import mage.abilities.effects.common.CreateTokenEffect; -import mage.abilities.effects.common.continuous.BoostControlledEffect; +import mage.abilities.effects.common.continuous.GainAbilityControlledEffect; import mage.abilities.effects.common.continuous.GainControlTargetEffect; +import mage.abilities.keyword.MenaceAbility; import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.CardType; import mage.constants.Duration; import mage.constants.SubType; +import mage.filter.FilterPermanent; import mage.filter.common.FilterControlledPermanent; import mage.filter.common.FilterCreaturePermanent; import mage.game.permanent.token.RatToken; @@ -28,7 +30,7 @@ import java.util.UUID; */ public final class PiperOfTheSwarm extends CardImpl { - private static final FilterCreaturePermanent filter = new FilterCreaturePermanent(SubType.RAT, "Rats"); + private static final FilterPermanent filter = new FilterCreaturePermanent(SubType.RAT, "Rats"); private static final FilterControlledPermanent filter2 = new FilterControlledPermanent(SubType.RAT, "Rats"); public PiperOfTheSwarm(UUID ownerId, CardSetInfo setInfo) { @@ -41,7 +43,7 @@ public final class PiperOfTheSwarm extends CardImpl { // Rats you control have menace. this.addAbility(new SimpleStaticAbility( - new BoostControlledEffect(1, 1, Duration.WhileOnBattlefield, filter) + new GainAbilityControlledEffect(new MenaceAbility(), Duration.WhileOnBattlefield, filter) )); // {1}{B}, {T}: Create a 1/1 black Rat creature token. From 65975940d682e49cb4da7465563dea76c13ed894 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 18 Sep 2019 13:12:24 -0400 Subject: [PATCH 193/373] updated ELD spoiler --- Utils/mtg-cards-data.txt | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index 6226a6b065..ecffb5d8a2 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -36036,7 +36036,7 @@ Bring to Life|Throne of Eldraine|38|U|{2}{U}|Sorcery - Adventure|2|2|Target nonc Corridor Monitor|Throne of Eldraine|41|C|{1}{U}|Artifact Creature - Construct|1|4|When Corridor Monitor enters the battlefield, untap target artifact or creature you control.| Emry, Lurker of the Loch|Throne of Eldraine|43|R|{2}{U}|Legendary Creature - Merfolk Wizard|1|2|This spell costs {1} less to cast for each artifact you control.$When Emry, Lurker of the Loch enters the battlefield, put the top four cards of your library into your graveyard.${T}: Choose target artifact card in your graveyard. You may cast that card this turn.| Fae of Wishes|Throne of Eldraine|44|R|{1}{U}|Creature - Faerie Wizard|1|4|Flying${1}{U}, Discard two cards: Return Fae of Wishes to its owner's hand.| -Granted|Throne of Eldraine|44|R|{3}{U}|Creature - Faerie Wizard|1|4|You may choose a noncreature card you own from outside the game, reveal it, and put it into your hand.| +Granted|Throne of Eldraine|44|R|{3}{U}|Sorcery - Adventure|1|4|You may choose a noncreature card you own from outside the game, reveal it, and put it into your hand.| Faerie Vandal|Throne of Eldraine|45|U|{1}{U}|Creature - Faerie Rogue|1|2|Flash$Flying$Whenever you draw your second card each turn, put a +1/+1 counter on Faerie Vandal.| Folio of Fancies|Throne of Eldraine|46|R|{1}{U}|Artifact|||Players have no maximum hand size.${X}{X}, {T}: Each player draws X cards.${2}{U}, {T}: Each opponent puts a number of cards equal to the number of cards in their hand from the top of their library into their graveyard.| Frogify|Throne of Eldraine|47|U|{1}{U}|Enchantment - Aura|||Enchant creature$Enchanted creature loses all abilities and is a blue Frog creature with base power and toughness 1/1.| @@ -36090,6 +36090,7 @@ Curry Favor|Throne of Eldraine|105|C|{B}|Sorcery - Adventure|2|1|You gain X life Smitten Swordmaster|Throne of Eldraine|105|C|{1}{B}|Creature - Human Knight|2|1|Lifelink| Specter's Shriek|Throne of Eldraine|106|U|{B}|Sorcery|||Target opponent reveals their hand. You may choose a nonland card from it. If you do, that player exiles that card. If a nonblack card is exiled this way, exile a card from your hand.| Syr Konrad, the Grim|Throne of Eldraine|107|U|{3}{B}{B}|Legendary Creature - Human Knight|5|4|Whenever another creature dies, or a creature card is put into a graveyard from anywhere other than the battlefield, or a creature card leaves your graveyard, Syr Konrad, the Grim deals 1 damage to each opponent.${1}{B}: Each player puts the top card of their library into their graveyard.| +Tempting Witch|Throne of Eldraine|108|C|{2}{B}|Creature - Human Warlock|1|3|When Tempting Witch enters the battlefield, create a Food token.${2}, {T}, Sacrifice a Food: Target player loses 3 life.| Wicked Guardian|Throne of Eldraine|109|C|{3}{B}|Creature - Human Noble|4|2|When Wicked Guardian enters the battlefield, you may have it deal 2 damage to another creature you control. If you do, draw a card.| Wishclaw Talisman|Throne of Eldraine|110|R|{1}{B}|Artifact|||Wishclaw Talisman enters the battlefield with three wish counters on it.${1}, {T}, Remove a wish counter from Wishclaw Talisman: Search your library for a card, put it into your hand, then shuffle your library. An opponent gains control of Wishclaw Talisman. Activate this ability only during your turn.| Witch's Vengeance|Throne of Eldraine|111|R|{1}{B}{B}|Sorcery|||Creatures of the creature type of your choice get -3/-3 until end of turn.| @@ -36143,6 +36144,7 @@ Garenbrig Paladin|Throne of Eldraine|157|C|{4}{G}|Creature - Giant Knight|4|4|Ad Garenbrig Squire|Throne of Eldraine|158|C|{1}{G}|Creature - Human Soldier|2|2|Whenever you cast a creature spell that has an Adventure, Garenbrig Squire gets +1/+1 until end of turn.| Giant Opportunity|Throne of Eldraine|159|U|{2}{G}|Sorcery|||You may sacrifice two Foods. If you do, create a 7/7 green Giant creature token. Otherwise, create three Food tokens.| Gilded Goose|Throne of Eldraine|160|R|{G}|Creature - Bird|0|2|Flying$When Gilded Goose enters the battlefield, create a Food token.${1}{G}, {T}: Create a Food token.${T}, Sacrifice a Food: Add one mana of any color.| +The Great Henge|Throne of Eldraine|161|M|{7}{G}{G}|Legendary Artifact|||This spell costs {X} less to cast, where X is the greatest power among creatures you control.${T}: Add {G}{G}. You gain 2 life.$Whenever a nontoken creature enters the battlefield under your control, put a +1/+1 counter on it and draw a card.| Insatiable Appetite|Throne of Eldraine|162|C|{1}{G}|Instant|||You may sacrifice a Food. If you do, target creature gets +5/+5 until end of turn. Otherwise, that creature gets +3/+3 until end of turn.| Keeper of Fables|Throne of Eldraine|163|U|{3}{G}{G}|Creature - Cat|4|5|Whenever one or more non-Human creatures you control deal combat damage to a player, draw a card.| Heart's Desire|Throne of Eldraine|165|R|{G}|Sorcery - Adventure|5|5|Create a 1/1 white Human creature token.| @@ -36192,6 +36194,7 @@ Fireborn Knight|Throne of Eldraine|210|U|{R/W}{R/W}{R/W}{R/W}|Creature - Human K Loch Dragon|Throne of Eldraine|211|U|{U/R}{U/R}{U/R}{U/R}|Creature - Dragon|3|2|Flying$Whenever Loch Dragon enters the battlefield or attacks, you may discard a card. If you do, draw a card.| Bring Back|Throne of Eldraine|212|U|{G/W}{G/W}{G/W}{G/W}|Sorcery - Adventure|2|2|Create two 1/1 white Human creature tokens.| Oakhame Ranger|Throne of Eldraine|212|U|{G/W}{G/W}{G/W}{G/W}|Creature - Elf Knight|2|2|{T}: Creatures you control get +1/+1 until end of turn.| +Rampart Smasher|Throne of Eldraine|213|U|{R/G}{R/G}{R/G}{R/G}|Creature - Giant|5|5|Rampart Smasher can't be blocked by Knights or Walls.| Thunderous Snapper|Throne of Eldraine|215|U|{G/U}{G/U}{G/U}{G/U}|Creature - Turtle Hydra|4|4|Whenever you cast a spell with converted mana cost 5 or greater, draw a card.| Clockwork Servant|Throne of Eldraine|216|U|{3}|Artifact Creature - Gnome|2|3|Adamant — When Clockwork Servant enters the battlefield, if at least three mana of the same color was spent to cast it, draw a card.| Enchanted Carriage|Throne of Eldraine|218|U|{5}|Artifact - Vehicle|4|4|When Enchanted Carriage enters the battlefield, create two 1/1 white Mouse creature tokens.$Crew 2| @@ -36209,8 +36212,10 @@ Sorcerous Spyglass|Throne of Eldraine|233|R|{2}|Artifact|||As Sorcerous Spyglass Spinning Wheel|Throne of Eldraine|234|U|{3}|Artifact|||{T}: Add one mana of any color.${5}, {T}: Tap target creature.| Stonecoil Serpent|Throne of Eldraine|235|R|{X}|Artifact Creature - Snake|0|0|Reach, trample, protection from multicolored$Stonecoil Serpent enters the battlefield with X +1/+1 counters on it.| Witch's Oven|Throne of Eldraine|237|U|{1}|Artifact|||{T}, Sacrifice a creature: Create a Food token. If the sacrificed creature's toughness was 4 or greater, create two Food tokens instead.| +Castle Ardenvale|Throne of Eldraine|238|R||Land|||Castle Ardenvale enters the battlefield tapped unless you control a Plains.${T}: Add {W}.${2}{W}{W}, {T}: Create a 1/1 white Human creature token.| Castle Embereth|Throne of Eldraine|239|R||Land|||Castle Embereth enters the battlefield tapped unless you control a Mountain.${T}: Add {R}.${1}{R}{R}, {T}: Creatures you control get +1/+0 until end of turn.| Castle Garenbrig|Throne of Eldraine|240|R||Land|||Castle Garenbrig enters the battlefield tapped unless you control a Forest.${T}: Add {G}.${2}{G}{G}, {T}: Add six {G}. Spend this mana only to cast creature spells or activate abilities of creatures.| +Castle Locthwain|Throne of Eldraine|241|R||Land|||Castle Locthwain enters the battlefield tapped unless you control a Swamp.${T}: Add {B}.${1}{B}{B}, {T}: Draw a card, then you lose life equal to the number of cards in your hand.| Castle Vantress|Throne of Eldraine|242|R||Land|||Castle Vantress enters the battlefield tapped unless you control an Island.${T}: Add {U}.${2}{U}{U}, {T}: Scry 2.| Idyllic Grange|Throne of Eldraine|246|C||Land - Plains|||({T}: Add {W}.)$Idyllic Grange enters the battlefield tapped unless you control three or more other Plains.$When Idyllic Grange enters the battlefield untapped, put a +1/+1 counter on target creature you control.| Tournament Grounds|Throne of Eldraine|248|U||Land|||{T}: Add {C}.${T}: Add {R}, {W}, or {B}. Spend this mana only to cast a Knight or Equipment spell.| From 16660d32eb61263f3936a69c880a251e509bc83b Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 18 Sep 2019 13:14:04 -0400 Subject: [PATCH 194/373] Implemented Castle Ardenvale --- .../src/mage/cards/c/CastleArdenvale.java | 61 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 62 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/c/CastleArdenvale.java diff --git a/Mage.Sets/src/mage/cards/c/CastleArdenvale.java b/Mage.Sets/src/mage/cards/c/CastleArdenvale.java new file mode 100644 index 0000000000..94075da1d1 --- /dev/null +++ b/Mage.Sets/src/mage/cards/c/CastleArdenvale.java @@ -0,0 +1,61 @@ +package mage.cards.c; + +import mage.abilities.Ability; +import mage.abilities.common.EntersBattlefieldAbility; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.condition.Condition; +import mage.abilities.condition.common.PermanentsOnTheBattlefieldCondition; +import mage.abilities.costs.common.TapSourceCost; +import mage.abilities.costs.mana.ManaCostsImpl; +import mage.abilities.decorator.ConditionalOneShotEffect; +import mage.abilities.effects.common.CreateTokenEffect; +import mage.abilities.effects.common.TapSourceEffect; +import mage.abilities.mana.WhiteManaAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.ComparisonType; +import mage.constants.SubType; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterControlledPermanent; +import mage.game.permanent.token.HumanToken; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class CastleArdenvale extends CardImpl { + + private static final FilterPermanent filter = new FilterControlledPermanent(SubType.PLAINS); + private static final Condition condition + = new PermanentsOnTheBattlefieldCondition(filter, ComparisonType.EQUAL_TO, 0); + + public CastleArdenvale(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.LAND}, ""); + + // Castle Ardenvale enters the battlefield tapped unless you control a Plains. + this.addAbility(new EntersBattlefieldAbility(new ConditionalOneShotEffect( + new TapSourceEffect(), condition + ), "tapped unless you control an Plains")); + + // {T}: Add {W}. + this.addAbility(new WhiteManaAbility()); + + // {2}{W}{W}, {T}: Create a 1/1 white Human creature token. + Ability ability = new SimpleActivatedAbility( + new CreateTokenEffect(new HumanToken()), new ManaCostsImpl("{2}{W}{W}") + ); + ability.addCost(new TapSourceCost()); + this.addAbility(ability); + } + + private CastleArdenvale(final CastleArdenvale card) { + super(card); + } + + @Override + public CastleArdenvale copy() { + return new CastleArdenvale(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index d02f677d3a..d068d7bc69 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -49,6 +49,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Bramblefort Fink", 311, Rarity.UNCOMMON, mage.cards.b.BramblefortFink.class)); cards.add(new SetCardInfo("Brimstone Trebuchet", 116, Rarity.COMMON, mage.cards.b.BrimstoneTrebuchet.class)); cards.add(new SetCardInfo("Burning-Yard Trainer", 117, Rarity.UNCOMMON, mage.cards.b.BurningYardTrainer.class)); + cards.add(new SetCardInfo("Castle Ardenvale", 238, Rarity.RARE, mage.cards.c.CastleArdenvale.class)); cards.add(new SetCardInfo("Castle Embereth", 239, Rarity.RARE, mage.cards.c.CastleEmbereth.class)); cards.add(new SetCardInfo("Castle Garenbrig", 240, Rarity.RARE, mage.cards.c.CastleGarenbrig.class)); cards.add(new SetCardInfo("Castle Vantress", 242, Rarity.RARE, mage.cards.c.CastleVantress.class)); From 4d0808fbd1440443a8e00ad2120e39529ca3a536 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 18 Sep 2019 13:18:21 -0400 Subject: [PATCH 195/373] Implemented Tempting Witch --- Mage.Sets/src/mage/cards/t/TemptingWitch.java | 59 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 60 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/t/TemptingWitch.java diff --git a/Mage.Sets/src/mage/cards/t/TemptingWitch.java b/Mage.Sets/src/mage/cards/t/TemptingWitch.java new file mode 100644 index 0000000000..2af415f528 --- /dev/null +++ b/Mage.Sets/src/mage/cards/t/TemptingWitch.java @@ -0,0 +1,59 @@ +package mage.cards.t; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.costs.common.SacrificeTargetCost; +import mage.abilities.costs.common.TapSourceCost; +import mage.abilities.costs.mana.GenericManaCost; +import mage.abilities.effects.common.CreateTokenEffect; +import mage.abilities.effects.common.LoseLifeTargetEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.filter.common.FilterControlledPermanent; +import mage.game.permanent.token.FoodToken; +import mage.target.TargetPlayer; +import mage.target.common.TargetControlledPermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class TemptingWitch extends CardImpl { + + private static final FilterControlledPermanent filter = new FilterControlledPermanent(SubType.FOOD, "a Food"); + + public TemptingWitch(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{2}{B}"); + + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.WARLOCK); + this.power = new MageInt(1); + this.toughness = new MageInt(3); + + // When Tempting Witch enters the battlefield, create a Food token. + this.addAbility(new EntersBattlefieldTriggeredAbility(new CreateTokenEffect(new FoodToken()))); + + // {2}, {T}, Sacrifice a Food: Target player loses 3 life. + Ability ability = new SimpleActivatedAbility( + new LoseLifeTargetEffect(3), new GenericManaCost(2) + ); + ability.addCost(new TapSourceCost()); + ability.addCost(new SacrificeTargetCost(new TargetControlledPermanent(filter))); + ability.addTarget(new TargetPlayer()); + this.addAbility(ability); + } + + private TemptingWitch(final TemptingWitch card) { + super(card); + } + + @Override + public TemptingWitch copy() { + return new TemptingWitch(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index d068d7bc69..fbeebc6a4f 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -206,6 +206,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Syr Konrad, the Grim", 107, Rarity.UNCOMMON, mage.cards.s.SyrKonradTheGrim.class)); cards.add(new SetCardInfo("Tall as a Beanstalk", 178, Rarity.COMMON, mage.cards.t.TallAsABeanstalk.class)); cards.add(new SetCardInfo("Taste of Death", 320, Rarity.RARE, mage.cards.t.TasteOfDeath.class)); + cards.add(new SetCardInfo("Tempting Witch", 108, Rarity.COMMON, mage.cards.t.TemptingWitch.class)); cards.add(new SetCardInfo("The Circle of Loyalty", 9, Rarity.MYTHIC, mage.cards.t.TheCircleOfLoyalty.class)); cards.add(new SetCardInfo("The Magic Mirror", 51, Rarity.MYTHIC, mage.cards.t.TheMagicMirror.class)); cards.add(new SetCardInfo("The Royal Scions", 199, Rarity.MYTHIC, mage.cards.t.TheRoyalScions.class)); From 8cdf656a3ce19fb06644cdfd910990a8a3bbe51b Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 18 Sep 2019 13:21:10 -0400 Subject: [PATCH 196/373] Implemented Stormfist Crusader --- .../src/mage/cards/s/StormfistCrusader.java | 50 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 51 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/s/StormfistCrusader.java diff --git a/Mage.Sets/src/mage/cards/s/StormfistCrusader.java b/Mage.Sets/src/mage/cards/s/StormfistCrusader.java new file mode 100644 index 0000000000..ab4d35ed3d --- /dev/null +++ b/Mage.Sets/src/mage/cards/s/StormfistCrusader.java @@ -0,0 +1,50 @@ +package mage.cards.s; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.BeginningOfUpkeepTriggeredAbility; +import mage.abilities.dynamicvalue.common.StaticValue; +import mage.abilities.effects.common.DrawCardAllEffect; +import mage.abilities.effects.common.LoseLifeAllPlayersEffect; +import mage.abilities.keyword.MenaceAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.constants.TargetController; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class StormfistCrusader extends CardImpl { + + public StormfistCrusader(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{B}{R}"); + + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.KNIGHT); + this.power = new MageInt(2); + this.toughness = new MageInt(2); + + // Menace + this.addAbility(new MenaceAbility()); + + // At the beginning of your upkeep, each player draws a card and loses 1 life. + Ability ability = new BeginningOfUpkeepTriggeredAbility( + new DrawCardAllEffect(1), TargetController.YOU, false + ); + ability.addEffect(new LoseLifeAllPlayersEffect(new StaticValue(1), "and loses 1 life")); + this.addAbility(ability); + } + + private StormfistCrusader(final StormfistCrusader card) { + super(card); + } + + @Override + public StormfistCrusader copy() { + return new StormfistCrusader(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index fbeebc6a4f..2ae2e45b17 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -198,6 +198,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Steelclaw Lance", 202, Rarity.UNCOMMON, mage.cards.s.SteelclawLance.class)); cards.add(new SetCardInfo("Stolen by the Fae", 66, Rarity.RARE, mage.cards.s.StolenByTheFae.class)); cards.add(new SetCardInfo("Stonecoil Serpent", 235, Rarity.RARE, mage.cards.s.StonecoilSerpent.class)); + cards.add(new SetCardInfo("Stormfist Crusader", 203, Rarity.RARE, mage.cards.s.StormfistCrusader.class)); cards.add(new SetCardInfo("Syr Alin, the Lion's Claw", 32, Rarity.UNCOMMON, mage.cards.s.SyrAlinTheLionsClaw.class)); cards.add(new SetCardInfo("Syr Carah, the Bold", 145, Rarity.UNCOMMON, mage.cards.s.SyrCarahTheBold.class)); cards.add(new SetCardInfo("Syr Elenora, the Discerning", 67, Rarity.UNCOMMON, mage.cards.s.SyrElenoraTheDiscerning.class)); From cae1678ddcc993785abbee865d897b8989a6bf3e Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 18 Sep 2019 18:55:08 -0400 Subject: [PATCH 197/373] Implemented Brazen Borrower --- .../src/mage/cards/b/BrazenBorrower.java | 63 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + Utils/mtg-cards-data.txt | 2 + 3 files changed, 66 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/b/BrazenBorrower.java diff --git a/Mage.Sets/src/mage/cards/b/BrazenBorrower.java b/Mage.Sets/src/mage/cards/b/BrazenBorrower.java new file mode 100644 index 0000000000..14bc967401 --- /dev/null +++ b/Mage.Sets/src/mage/cards/b/BrazenBorrower.java @@ -0,0 +1,63 @@ +package mage.cards.b; + +import mage.MageInt; +import mage.abilities.common.CanBlockOnlyFlyingAbility; +import mage.abilities.effects.common.ReturnToHandTargetEffect; +import mage.abilities.keyword.FlashAbility; +import mage.abilities.keyword.FlyingAbility; +import mage.cards.AdventureCard; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.constants.TargetController; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterNonlandPermanent; +import mage.filter.predicate.permanent.ControllerPredicate; +import mage.target.TargetPermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class BrazenBorrower extends AdventureCard { + + private static final FilterPermanent filter + = new FilterNonlandPermanent("nonland permanent an opponent controls"); + + static { + filter.add(new ControllerPredicate(TargetController.OPPONENT)); + } + + public BrazenBorrower(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, new CardType[]{CardType.INSTANT}, "{1}{U}{U}", "Petty Theft", "{1}{U}"); + + this.subtype.add(SubType.FAERIE); + this.subtype.add(SubType.ROGUE); + this.power = new MageInt(3); + this.toughness = new MageInt(1); + + // Flash + this.addAbility(FlashAbility.getInstance()); + + // Flying + this.addAbility(FlyingAbility.getInstance()); + + // Bazen Borrower can block only creatures with flying. + this.addAbility(new CanBlockOnlyFlyingAbility()); + + // Petty Theft + // Return target nonland permanent an opponent controls to its owner's hand. + this.getAdventureSpellAbility().addEffect(new ReturnToHandTargetEffect()); + this.getAdventureSpellAbility().addTarget(new TargetPermanent(filter)); + } + + private BrazenBorrower(final BrazenBorrower card) { + super(card); + } + + @Override + public BrazenBorrower copy() { + return new BrazenBorrower(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 2ae2e45b17..0dcfac4cab 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -47,6 +47,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Bog Naughty", 80, Rarity.UNCOMMON, mage.cards.b.BogNaughty.class)); cards.add(new SetCardInfo("Bonecrusher Giant", 115, Rarity.RARE, mage.cards.b.BonecrusherGiant.class)); cards.add(new SetCardInfo("Bramblefort Fink", 311, Rarity.UNCOMMON, mage.cards.b.BramblefortFink.class)); + cards.add(new SetCardInfo("Brazen Borrower", 39, Rarity.MYTHIC, mage.cards.b.BrazenBorrower.class)); cards.add(new SetCardInfo("Brimstone Trebuchet", 116, Rarity.COMMON, mage.cards.b.BrimstoneTrebuchet.class)); cards.add(new SetCardInfo("Burning-Yard Trainer", 117, Rarity.UNCOMMON, mage.cards.b.BurningYardTrainer.class)); cards.add(new SetCardInfo("Castle Ardenvale", 238, Rarity.RARE, mage.cards.c.CastleArdenvale.class)); diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index ecffb5d8a2..c14ef5be9b 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -36033,6 +36033,8 @@ Venerable Knight|Throne of Eldraine|35|U|{W}|Creature - Human Knight|2|1|When Ve Worthy Knight|Throne of Eldraine|36|R|{1}{W}|Creature - Human Knight|2|2|Whenever you cast a Knight spell, create a 1/1 white Human creature token.| Animating Faerie|Throne of Eldraine|38|U|{2}{U}|Creature - Faerie|2|2|Flying| Bring to Life|Throne of Eldraine|38|U|{2}{U}|Sorcery - Adventure|2|2|Target noncreature artifact you control becomes a 0/0 artifact creature. Put four +1/+1 counters on it.| +Brazen Borrower|Throne of Eldraine|39|M|{1}{U}{U}|Creature - Faerie Rogue|3|1|Flash$Flying$Bazen Borrower can block only creatures with flying.| +Petty Theft|Throne of Eldraine|39|M|{1}{U}|Instant - Adventure|3|1|Return target nonland permanent an opponent controls to its owner's hand.| Corridor Monitor|Throne of Eldraine|41|C|{1}{U}|Artifact Creature - Construct|1|4|When Corridor Monitor enters the battlefield, untap target artifact or creature you control.| Emry, Lurker of the Loch|Throne of Eldraine|43|R|{2}{U}|Legendary Creature - Merfolk Wizard|1|2|This spell costs {1} less to cast for each artifact you control.$When Emry, Lurker of the Loch enters the battlefield, put the top four cards of your library into your graveyard.${T}: Choose target artifact card in your graveyard. You may cast that card this turn.| Fae of Wishes|Throne of Eldraine|44|R|{1}{U}|Creature - Faerie Wizard|1|4|Flying${1}{U}, Discard two cards: Return Fae of Wishes to its owner's hand.| From 592638b406da5de8489660b7816dae92b8083473 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 18 Sep 2019 19:02:28 -0400 Subject: [PATCH 198/373] Implemented Fae of Wishes --- Mage.Sets/src/mage/cards/f/FaeOfWishes.java | 56 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 57 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/f/FaeOfWishes.java diff --git a/Mage.Sets/src/mage/cards/f/FaeOfWishes.java b/Mage.Sets/src/mage/cards/f/FaeOfWishes.java new file mode 100644 index 0000000000..d6aa24c094 --- /dev/null +++ b/Mage.Sets/src/mage/cards/f/FaeOfWishes.java @@ -0,0 +1,56 @@ +package mage.cards.f; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.costs.common.DiscardTargetCost; +import mage.abilities.costs.mana.ManaCostsImpl; +import mage.abilities.effects.common.ReturnToHandSourceEffect; +import mage.abilities.effects.common.WishEffect; +import mage.abilities.keyword.FlyingAbility; +import mage.cards.AdventureCard; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.filter.StaticFilters; +import mage.target.common.TargetCardInHand; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class FaeOfWishes extends AdventureCard { + + public FaeOfWishes(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, new CardType[]{CardType.SORCERY}, "{1}{U}", "Granted", "{3}{U}"); + + this.subtype.add(SubType.FAERIE); + this.subtype.add(SubType.WIZARD); + this.power = new MageInt(1); + this.toughness = new MageInt(4); + + // Flying + this.addAbility(FlyingAbility.getInstance()); + + // {1}{U}, Discard two cards: Return Fae of Wishes to its owner's hand. + Ability ability = new SimpleActivatedAbility( + new ReturnToHandSourceEffect(true), new ManaCostsImpl("{1}{U}") + ); + ability.addCost(new DiscardTargetCost(new TargetCardInHand(2, StaticFilters.FILTER_CARD))); + this.addAbility(ability); + + // Granted + // You may choose a noncreature card you own from outside the game, reveal it, and put it into your hand. + this.getAdventureSpellAbility().addEffect(new WishEffect(StaticFilters.FILTER_CARD_A_NON_LAND)); + } + + private FaeOfWishes(final FaeOfWishes card) { + super(card); + } + + @Override + public FaeOfWishes copy() { + return new FaeOfWishes(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 0dcfac4cab..8c7eb6d5c6 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -80,6 +80,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Epic Downfall", 85, Rarity.UNCOMMON, mage.cards.e.EpicDownfall.class)); cards.add(new SetCardInfo("Escape to the Wilds", 189, Rarity.RARE, mage.cards.e.EscapeToTheWilds.class)); cards.add(new SetCardInfo("Eye Collector", 86, Rarity.COMMON, mage.cards.e.EyeCollector.class)); + cards.add(new SetCardInfo("Fae of Wishes", 44, Rarity.RARE, mage.cards.f.FaeOfWishes.class)); cards.add(new SetCardInfo("Faeburrow Elder", 190, Rarity.RARE, mage.cards.f.FaeburrowElder.class)); cards.add(new SetCardInfo("Faerie Formation", 316, Rarity.RARE, mage.cards.f.FaerieFormation.class)); cards.add(new SetCardInfo("Faerie Guidemother", 11, Rarity.COMMON, mage.cards.f.FaerieGuidemother.class)); From e41e278a62077efd2fe29d1cff2fc2c46501c6ed Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 18 Sep 2019 19:10:18 -0400 Subject: [PATCH 199/373] Implemented Garenbrig Carver --- .../src/mage/cards/g/GarenbrigCarver.java | 41 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 42 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/g/GarenbrigCarver.java diff --git a/Mage.Sets/src/mage/cards/g/GarenbrigCarver.java b/Mage.Sets/src/mage/cards/g/GarenbrigCarver.java new file mode 100644 index 0000000000..311deb9a14 --- /dev/null +++ b/Mage.Sets/src/mage/cards/g/GarenbrigCarver.java @@ -0,0 +1,41 @@ +package mage.cards.g; + +import mage.MageInt; +import mage.abilities.effects.common.continuous.BoostTargetEffect; +import mage.cards.AdventureCard; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; +import mage.target.common.TargetCreaturePermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class GarenbrigCarver extends AdventureCard { + + public GarenbrigCarver(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, new CardType[]{CardType.INSTANT}, "{3}{G}", "Shield's Might", "{1}{G}"); + + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.WARRIOR); + this.power = new MageInt(3); + this.toughness = new MageInt(2); + + // Shield's Might + // Target creature gets +2/+2 until end of turn. + this.getAdventureSpellAbility().addEffect(new BoostTargetEffect(2, 2, Duration.EndOfTurn)); + this.getAdventureSpellAbility().addTarget(new TargetCreaturePermanent()); + } + + private GarenbrigCarver(final GarenbrigCarver card) { + super(card); + } + + @Override + public GarenbrigCarver copy() { + return new GarenbrigCarver(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 8c7eb6d5c6..6aaf90e1dc 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -99,6 +99,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Foulmire Knight", 90, Rarity.UNCOMMON, mage.cards.f.FoulmireKnight.class)); cards.add(new SetCardInfo("Frogify", 47, Rarity.UNCOMMON, mage.cards.f.Frogify.class)); cards.add(new SetCardInfo("Gadwick, the Wizened", 48, Rarity.RARE, mage.cards.g.GadwickTheWizened.class)); + cards.add(new SetCardInfo("Garenbrig Carver", 156, Rarity.COMMON, mage.cards.g.GarenbrigCarver.class)); cards.add(new SetCardInfo("Garenbrig Paladin", 157, Rarity.COMMON, mage.cards.g.GarenbrigPaladin.class)); cards.add(new SetCardInfo("Garenbrig Squire", 158, Rarity.COMMON, mage.cards.g.GarenbrigSquire.class)); cards.add(new SetCardInfo("Garrison Griffin", 305, Rarity.COMMON, mage.cards.g.GarrisonGriffin.class)); From 88e033c1e39e9d71eb18e7593b250ef6d7e075cf Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 18 Sep 2019 19:15:57 -0400 Subject: [PATCH 200/373] Implemented Shepherd of the Flock --- .../src/mage/cards/s/ShepherdOfTheFlock.java | 40 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 41 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/s/ShepherdOfTheFlock.java diff --git a/Mage.Sets/src/mage/cards/s/ShepherdOfTheFlock.java b/Mage.Sets/src/mage/cards/s/ShepherdOfTheFlock.java new file mode 100644 index 0000000000..37c657ff45 --- /dev/null +++ b/Mage.Sets/src/mage/cards/s/ShepherdOfTheFlock.java @@ -0,0 +1,40 @@ +package mage.cards.s; + +import mage.MageInt; +import mage.abilities.effects.common.ReturnToHandTargetEffect; +import mage.cards.AdventureCard; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.target.common.TargetControlledPermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class ShepherdOfTheFlock extends AdventureCard { + + public ShepherdOfTheFlock(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, new CardType[]{CardType.INSTANT}, "{1}{W}", "Usher to Safety", "{W}"); + + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.PEASANT); + this.power = new MageInt(3); + this.toughness = new MageInt(1); + + // Usher to Safety + // Return target permanent you control to its owner’s hand. + this.getAdventureSpellAbility().addEffect(new ReturnToHandTargetEffect()); + this.getAdventureSpellAbility().addTarget(new TargetControlledPermanent()); + } + + private ShepherdOfTheFlock(final ShepherdOfTheFlock card) { + super(card); + } + + @Override + public ShepherdOfTheFlock copy() { + return new ShepherdOfTheFlock(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 6aaf90e1dc..1a2b2c9d75 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -184,6 +184,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Searing Barrage", 140, Rarity.COMMON, mage.cards.s.SearingBarrage.class)); cards.add(new SetCardInfo("Seven Dwarves", 141, Rarity.COMMON, mage.cards.s.SevenDwarves.class)); cards.add(new SetCardInfo("Shambling Suit", 230, Rarity.UNCOMMON, mage.cards.s.ShamblingSuit.class)); + cards.add(new SetCardInfo("Shepherd of the Flock", 28, Rarity.UNCOMMON, mage.cards.s.ShepherdOfTheFlock.class)); cards.add(new SetCardInfo("Shimmer Dragon", 317, Rarity.RARE, mage.cards.s.ShimmerDragon.class)); cards.add(new SetCardInfo("Shinechaser", 201, Rarity.UNCOMMON, mage.cards.s.Shinechaser.class)); cards.add(new SetCardInfo("Shining Armor", 29, Rarity.COMMON, mage.cards.s.ShiningArmor.class)); From 374827d7176fb12198ae59b948443f4b67f38629 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 18 Sep 2019 19:21:11 -0400 Subject: [PATCH 201/373] Implemented Castle Locthwain --- .../src/mage/cards/c/CastleArdenvale.java | 2 +- .../src/mage/cards/c/CastleEmbereth.java | 2 +- .../src/mage/cards/c/CastleGarenbrig.java | 2 +- .../src/mage/cards/c/CastleLocthwain.java | 64 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 5 files changed, 68 insertions(+), 3 deletions(-) create mode 100644 Mage.Sets/src/mage/cards/c/CastleLocthwain.java diff --git a/Mage.Sets/src/mage/cards/c/CastleArdenvale.java b/Mage.Sets/src/mage/cards/c/CastleArdenvale.java index 94075da1d1..6e15956b76 100644 --- a/Mage.Sets/src/mage/cards/c/CastleArdenvale.java +++ b/Mage.Sets/src/mage/cards/c/CastleArdenvale.java @@ -37,7 +37,7 @@ public final class CastleArdenvale extends CardImpl { // Castle Ardenvale enters the battlefield tapped unless you control a Plains. this.addAbility(new EntersBattlefieldAbility(new ConditionalOneShotEffect( new TapSourceEffect(), condition - ), "tapped unless you control an Plains")); + ), "tapped unless you control a Plains")); // {T}: Add {W}. this.addAbility(new WhiteManaAbility()); diff --git a/Mage.Sets/src/mage/cards/c/CastleEmbereth.java b/Mage.Sets/src/mage/cards/c/CastleEmbereth.java index 53ef68f844..2b4f10aea8 100644 --- a/Mage.Sets/src/mage/cards/c/CastleEmbereth.java +++ b/Mage.Sets/src/mage/cards/c/CastleEmbereth.java @@ -37,7 +37,7 @@ public final class CastleEmbereth extends CardImpl { // Castle Embereth enters the battlefield tapped unless you control a Mountain. this.addAbility(new EntersBattlefieldAbility(new ConditionalOneShotEffect( new TapSourceEffect(), condition - ), "tapped unless you control an Mountain")); + ), "tapped unless you control a Mountain")); // {T}: Add {R}. this.addAbility(new RedManaAbility()); diff --git a/Mage.Sets/src/mage/cards/c/CastleGarenbrig.java b/Mage.Sets/src/mage/cards/c/CastleGarenbrig.java index d2144fa3be..4e79fc9239 100644 --- a/Mage.Sets/src/mage/cards/c/CastleGarenbrig.java +++ b/Mage.Sets/src/mage/cards/c/CastleGarenbrig.java @@ -40,7 +40,7 @@ public final class CastleGarenbrig extends CardImpl { // Castle Garenbrig enters the battlefield tapped unless you control a Forest. this.addAbility(new EntersBattlefieldAbility(new ConditionalOneShotEffect( new TapSourceEffect(), condition - ), "tapped unless you control an Forest")); + ), "tapped unless you control a Forest")); // {T}: Add {G}. this.addAbility(new GreenManaAbility()); diff --git a/Mage.Sets/src/mage/cards/c/CastleLocthwain.java b/Mage.Sets/src/mage/cards/c/CastleLocthwain.java new file mode 100644 index 0000000000..06aa17106c --- /dev/null +++ b/Mage.Sets/src/mage/cards/c/CastleLocthwain.java @@ -0,0 +1,64 @@ +package mage.cards.c; + +import mage.abilities.Ability; +import mage.abilities.common.EntersBattlefieldAbility; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.condition.Condition; +import mage.abilities.condition.common.PermanentsOnTheBattlefieldCondition; +import mage.abilities.costs.common.TapSourceCost; +import mage.abilities.costs.mana.ManaCostsImpl; +import mage.abilities.decorator.ConditionalOneShotEffect; +import mage.abilities.dynamicvalue.common.CardsInControllerHandCount; +import mage.abilities.effects.common.DrawCardSourceControllerEffect; +import mage.abilities.effects.common.LoseLifeSourceControllerEffect; +import mage.abilities.effects.common.TapSourceEffect; +import mage.abilities.mana.BlackManaAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.ComparisonType; +import mage.constants.SubType; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterControlledPermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class CastleLocthwain extends CardImpl { + + private static final FilterPermanent filter = new FilterControlledPermanent(SubType.SWAMP); + private static final Condition condition + = new PermanentsOnTheBattlefieldCondition(filter, ComparisonType.EQUAL_TO, 0); + + public CastleLocthwain(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.LAND}, ""); + + // Castle Locthwain enters the battlefield tapped unless you control a Swamp. + this.addAbility(new EntersBattlefieldAbility(new ConditionalOneShotEffect( + new TapSourceEffect(), condition + ), "tapped unless you control a Swamp")); + + // {T}: Add {B}. + this.addAbility(new BlackManaAbility()); + + // {1}{B}{B}, {T}: Draw a card, then you lose life equal to the number of cards in your hand. + Ability ability = new SimpleActivatedAbility( + new DrawCardSourceControllerEffect(1).setText("draw a card,"), new ManaCostsImpl("{1}{B}{B}") + ); + ability.addEffect(new LoseLifeSourceControllerEffect(CardsInControllerHandCount.instance) + .setText("then you lose life equal to the number of cards in your hand")); + ability.addCost(new TapSourceCost()); + this.addAbility(ability); + } + + private CastleLocthwain(final CastleLocthwain card) { + super(card); + } + + @Override + public CastleLocthwain copy() { + return new CastleLocthwain(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 1a2b2c9d75..03b0494ef9 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -53,6 +53,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Castle Ardenvale", 238, Rarity.RARE, mage.cards.c.CastleArdenvale.class)); cards.add(new SetCardInfo("Castle Embereth", 239, Rarity.RARE, mage.cards.c.CastleEmbereth.class)); cards.add(new SetCardInfo("Castle Garenbrig", 240, Rarity.RARE, mage.cards.c.CastleGarenbrig.class)); + cards.add(new SetCardInfo("Castle Locthwain", 241, Rarity.RARE, mage.cards.c.CastleLocthwain.class)); cards.add(new SetCardInfo("Castle Vantress", 242, Rarity.RARE, mage.cards.c.CastleVantress.class)); cards.add(new SetCardInfo("Cauldron Familiar", 81, Rarity.UNCOMMON, mage.cards.c.CauldronFamiliar.class)); cards.add(new SetCardInfo("Charming Prince", 8, Rarity.RARE, mage.cards.c.CharmingPrince.class)); From 05f70e532046d88e8e644ad39352be563e5a2524 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 18 Sep 2019 19:35:15 -0400 Subject: [PATCH 202/373] Implemented Yorvo, Lord of Garenbrig --- .../mage/cards/y/YorvoLordOfGarenbrig.java | 101 ++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 102 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/y/YorvoLordOfGarenbrig.java diff --git a/Mage.Sets/src/mage/cards/y/YorvoLordOfGarenbrig.java b/Mage.Sets/src/mage/cards/y/YorvoLordOfGarenbrig.java new file mode 100644 index 0000000000..d9cdc571ff --- /dev/null +++ b/Mage.Sets/src/mage/cards/y/YorvoLordOfGarenbrig.java @@ -0,0 +1,101 @@ +package mage.cards.y; + +import mage.MageInt; +import mage.ObjectColor; +import mage.abilities.Ability; +import mage.abilities.common.EntersBattlefieldAbility; +import mage.abilities.common.EntersBattlefieldControlledTriggeredAbility; +import mage.abilities.effects.OneShotEffect; +import mage.abilities.effects.common.counter.AddCountersSourceEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.*; +import mage.counters.CounterType; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterCreaturePermanent; +import mage.filter.predicate.mageobject.ColorPredicate; +import mage.filter.predicate.permanent.AnotherPredicate; +import mage.game.Game; +import mage.game.permanent.Permanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class YorvoLordOfGarenbrig extends CardImpl { + + private static final FilterPermanent filter = new FilterCreaturePermanent(); + + static { + filter.add(AnotherPredicate.instance); + filter.add(new ColorPredicate(ObjectColor.GREEN)); + } + + public YorvoLordOfGarenbrig(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{G}{G}{G}"); + + this.addSuperType(SuperType.LEGENDARY); + this.subtype.add(SubType.GIANT); + this.subtype.add(SubType.NOBLE); + this.power = new MageInt(0); + this.toughness = new MageInt(0); + + // Yorvo, Lord of Garenbrig enters the battlefield with four +1/+1 counters on it. + this.addAbility(new EntersBattlefieldAbility( + new AddCountersSourceEffect(CounterType.P1P1.createInstance(4)), + "{this} enters the battlefield with four +1/+1 counters on it" + )); + + // Whenever another green creature enters the battlefield under your control, put a +1/+1 counter on Yorvo. Then if that creature's power is greater than Yorvo's power, put another +1/+1 counter on Yorvo. + this.addAbility(new EntersBattlefieldControlledTriggeredAbility( + Zone.BATTLEFIELD, new YorvoLordOfGarenbrigEffect(), filter, false, SetTargetPointer.PERMANENT, + "Whenever another green creature enters the battlefield under your control, " + + "put a +1/+1 counter on {this}. Then if that creature's power is greater than {this}'s power, " + + "put another +1/+1 counter on {this}." + )); + } + + private YorvoLordOfGarenbrig(final YorvoLordOfGarenbrig card) { + super(card); + } + + @Override + public YorvoLordOfGarenbrig copy() { + return new YorvoLordOfGarenbrig(this); + } +} + +class YorvoLordOfGarenbrigEffect extends OneShotEffect { + + YorvoLordOfGarenbrigEffect() { + super(Outcome.Benefit); + } + + private YorvoLordOfGarenbrigEffect(final YorvoLordOfGarenbrigEffect effect) { + super(effect); + } + + @Override + public YorvoLordOfGarenbrigEffect copy() { + return new YorvoLordOfGarenbrigEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + Permanent sourcePerm = game.getPermanent(source.getSourceId()); + if (sourcePerm == null) { + return false; + } + sourcePerm.addCounters(CounterType.P1P1.createInstance(), source, game); + Permanent permanent = game.getPermanentOrLKIBattlefield(targetPointer.getFirst(game, source)); + if (permanent == null) { + return true; + } + game.applyEffects(); + if (permanent.getPower().getValue() > sourcePerm.getPower().getValue()) { + sourcePerm.addCounters(CounterType.P1P1.createInstance(), source, game); + } + return true; + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 03b0494ef9..0db97bfc5b 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -249,6 +249,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Wolf's Quarry", 184, Rarity.COMMON, mage.cards.w.WolfsQuarry.class)); cards.add(new SetCardInfo("Workshop Elders", 318, Rarity.RARE, mage.cards.w.WorkshopElders.class)); cards.add(new SetCardInfo("Worthy Knight", 36, Rarity.RARE, mage.cards.w.WorthyKnight.class)); + cards.add(new SetCardInfo("Yorvo, Lord of Garenbrig", 185, Rarity.RARE, mage.cards.y.YorvoLordOfGarenbrig.class)); // This is here to prevent the incomplete adventure implementation from causing problems and will be removed cards.removeIf(setCardInfo -> AdventureCard.class.isAssignableFrom(setCardInfo.getCardClass())); From e20c5f2da81cd875d7dc9d160b824a6327804bf3 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 18 Sep 2019 19:44:40 -0400 Subject: [PATCH 203/373] Implemented Rampart Smasher --- .../src/mage/cards/r/RampartSmasher.java | 52 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 53 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/r/RampartSmasher.java diff --git a/Mage.Sets/src/mage/cards/r/RampartSmasher.java b/Mage.Sets/src/mage/cards/r/RampartSmasher.java new file mode 100644 index 0000000000..381abf43da --- /dev/null +++ b/Mage.Sets/src/mage/cards/r/RampartSmasher.java @@ -0,0 +1,52 @@ +package mage.cards.r; + +import mage.MageInt; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.effects.common.combat.CantBeBlockedByCreaturesSourceEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; +import mage.filter.common.FilterCreaturePermanent; +import mage.filter.predicate.Predicates; +import mage.filter.predicate.mageobject.SubtypePredicate; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class RampartSmasher extends CardImpl { + + private static final FilterCreaturePermanent filter = new FilterCreaturePermanent("Knights or Walls"); + + static { + filter.add(Predicates.or( + new SubtypePredicate(SubType.KNIGHT), + new SubtypePredicate(SubType.WALL) + )); + } + + public RampartSmasher(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{R/G}{R/G}{R/G}{R/G}"); + + this.subtype.add(SubType.GIANT); + this.power = new MageInt(5); + this.toughness = new MageInt(5); + + // Rampart Smasher can't be blocked by Knights or Walls. + this.addAbility(new SimpleStaticAbility( + new CantBeBlockedByCreaturesSourceEffect(filter, Duration.WhileOnBattlefield) + )); + } + + private RampartSmasher(final RampartSmasher card) { + super(card); + } + + @Override + public RampartSmasher copy() { + return new RampartSmasher(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 0db97bfc5b..f373d99868 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -165,6 +165,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Questing Beast", 171, Rarity.MYTHIC, mage.cards.q.QuestingBeast.class)); cards.add(new SetCardInfo("Raging Redcap", 134, Rarity.COMMON, mage.cards.r.RagingRedcap.class)); cards.add(new SetCardInfo("Rally for the Throne", 25, Rarity.UNCOMMON, mage.cards.r.RallyForTheThrone.class)); + cards.add(new SetCardInfo("Rampart Smasher", 213, Rarity.UNCOMMON, mage.cards.r.RampartSmasher.class)); cards.add(new SetCardInfo("Rankle, Master of Pranks", 101, Rarity.MYTHIC, mage.cards.r.RankleMasterOfPranks.class)); cards.add(new SetCardInfo("Realm-Cloaked Giant", 26, Rarity.MYTHIC, mage.cards.r.RealmCloakedGiant.class)); cards.add(new SetCardInfo("Reave Soul", 103, Rarity.COMMON, mage.cards.r.ReaveSoul.class)); From c3d141d83cb596faed43fe903b2a62cf69cc8a95 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 18 Sep 2019 19:58:19 -0400 Subject: [PATCH 204/373] Implemented The Great Henge --- Mage.Sets/src/mage/cards/t/TheGreatHenge.java | 110 ++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + ...ReductionForEachCardInGraveyardEffect.java | 7 +- 3 files changed, 114 insertions(+), 4 deletions(-) create mode 100644 Mage.Sets/src/mage/cards/t/TheGreatHenge.java diff --git a/Mage.Sets/src/mage/cards/t/TheGreatHenge.java b/Mage.Sets/src/mage/cards/t/TheGreatHenge.java new file mode 100644 index 0000000000..ebe1cbfafe --- /dev/null +++ b/Mage.Sets/src/mage/cards/t/TheGreatHenge.java @@ -0,0 +1,110 @@ +package mage.cards.t; + +import mage.MageInt; +import mage.Mana; +import mage.abilities.Ability; +import mage.abilities.SpellAbility; +import mage.abilities.common.EntersBattlefieldControlledTriggeredAbility; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.costs.common.TapSourceCost; +import mage.abilities.effects.common.DrawCardSourceControllerEffect; +import mage.abilities.effects.common.GainLifeEffect; +import mage.abilities.effects.common.cost.CostModificationEffectImpl; +import mage.abilities.effects.common.counter.AddCountersTargetEffect; +import mage.abilities.mana.SimpleManaAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.*; +import mage.counters.CounterType; +import mage.filter.FilterPermanent; +import mage.filter.StaticFilters; +import mage.filter.common.FilterCreaturePermanent; +import mage.filter.predicate.Predicates; +import mage.filter.predicate.permanent.TokenPredicate; +import mage.game.Game; +import mage.game.permanent.Permanent; +import mage.util.CardUtil; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class TheGreatHenge extends CardImpl { + + private static final FilterPermanent filter = new FilterCreaturePermanent(); + + static { + filter.add(Predicates.not(TokenPredicate.instance)); + } + + public TheGreatHenge(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT}, "{7}{G}{G}"); + + this.addSuperType(SuperType.LEGENDARY); + + // This spell costs {X} less to cast, where X is the greatest power among creatures you control. + this.addAbility(new SimpleStaticAbility(Zone.ALL, new TheGreatHengeCostReductionEffect())); + + // {T}: Add {G}{G}. You gain 2 life. + Ability ability = new SimpleManaAbility(Zone.BATTLEFIELD, Mana.GreenMana(2), new TapSourceCost()); + ability.addEffect(new GainLifeEffect(2).setText("You gain 2 life.")); + this.addAbility(ability); + + // Whenever a nontoken creature enters the battlefield under your control, put a +1/+1 counter on it and draw a card. + ability = new EntersBattlefieldControlledTriggeredAbility( + Zone.BATTLEFIELD, new AddCountersTargetEffect(CounterType.P1P1.createInstance()), + filter, false, SetTargetPointer.PERMANENT, "Whenever a nontoken creature " + + "enters the battlefield under your control, put a +1/+1 counter on it and draw a card." + ); + ability.addEffect(new DrawCardSourceControllerEffect(1)); + this.addAbility(ability); + } + + private TheGreatHenge(final TheGreatHenge card) { + super(card); + } + + @Override + public TheGreatHenge copy() { + return new TheGreatHenge(this); + } +} + +class TheGreatHengeCostReductionEffect extends CostModificationEffectImpl { + + TheGreatHengeCostReductionEffect() { + super(Duration.WhileOnStack, Outcome.Benefit, CostModificationType.REDUCE_COST); + staticText = "This spell costs {X} less to cast, where X is the greatest power among creatures you control"; + } + + private TheGreatHengeCostReductionEffect(final TheGreatHengeCostReductionEffect effect) { + super(effect); + } + + @Override + public boolean apply(Game game, Ability source, Ability abilityToModify) { + int reductionAmount = game.getBattlefield() + .getAllActivePermanents( + StaticFilters.FILTER_PERMANENT_CREATURE, source.getControllerId(), game + ).stream() + .map(Permanent::getPower) + .mapToInt(MageInt::getValue) + .max() + .getAsInt(); + CardUtil.reduceCost(abilityToModify, reductionAmount); + return true; + } + + @Override + public boolean applies(Ability abilityToModify, Ability source, Game game) { + return abilityToModify instanceof SpellAbility + && abilityToModify.getSourceId().equals(source.getSourceId()) + && game.getCard(abilityToModify.getSourceId()) != null; + } + + @Override + public TheGreatHengeCostReductionEffect copy() { + return new TheGreatHengeCostReductionEffect(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index f373d99868..f5b3db91b7 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -215,6 +215,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Taste of Death", 320, Rarity.RARE, mage.cards.t.TasteOfDeath.class)); cards.add(new SetCardInfo("Tempting Witch", 108, Rarity.COMMON, mage.cards.t.TemptingWitch.class)); cards.add(new SetCardInfo("The Circle of Loyalty", 9, Rarity.MYTHIC, mage.cards.t.TheCircleOfLoyalty.class)); + cards.add(new SetCardInfo("The Great Henge", 161, Rarity.MYTHIC, mage.cards.t.TheGreatHenge.class)); cards.add(new SetCardInfo("The Magic Mirror", 51, Rarity.MYTHIC, mage.cards.t.TheMagicMirror.class)); cards.add(new SetCardInfo("The Royal Scions", 199, Rarity.MYTHIC, mage.cards.t.TheRoyalScions.class)); cards.add(new SetCardInfo("Thorn Mammoth", 323, Rarity.RARE, mage.cards.t.ThornMammoth.class)); diff --git a/Mage/src/main/java/mage/abilities/effects/common/cost/SourceCostReductionForEachCardInGraveyardEffect.java b/Mage/src/main/java/mage/abilities/effects/common/cost/SourceCostReductionForEachCardInGraveyardEffect.java index 54257d349e..ab50288e85 100644 --- a/Mage/src/main/java/mage/abilities/effects/common/cost/SourceCostReductionForEachCardInGraveyardEffect.java +++ b/Mage/src/main/java/mage/abilities/effects/common/cost/SourceCostReductionForEachCardInGraveyardEffect.java @@ -1,4 +1,3 @@ - package mage.abilities.effects.common.cost; import mage.abilities.Ability; @@ -7,12 +6,12 @@ import mage.constants.CostModificationType; import mage.constants.Duration; import mage.constants.Outcome; import mage.filter.FilterCard; +import mage.filter.StaticFilters; import mage.game.Game; import mage.players.Player; import mage.util.CardUtil; /** - * * @author Styxo */ public class SourceCostReductionForEachCardInGraveyardEffect extends CostModificationEffectImpl { @@ -20,7 +19,7 @@ public class SourceCostReductionForEachCardInGraveyardEffect extends CostModific private FilterCard filter; public SourceCostReductionForEachCardInGraveyardEffect() { - this(new FilterCard()); + this(StaticFilters.FILTER_CARD); } public SourceCostReductionForEachCardInGraveyardEffect(FilterCard filter) { @@ -29,7 +28,7 @@ public class SourceCostReductionForEachCardInGraveyardEffect extends CostModific staticText = "{this} costs {1} less to cast for each " + filter.getMessage() + " in your graveyard"; } - SourceCostReductionForEachCardInGraveyardEffect(SourceCostReductionForEachCardInGraveyardEffect effect) { + private SourceCostReductionForEachCardInGraveyardEffect(SourceCostReductionForEachCardInGraveyardEffect effect) { super(effect); this.filter = effect.filter.copy(); } From 51cc42ef02d01319e55c46d72789ab5fbb399251 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 18 Sep 2019 21:46:20 -0400 Subject: [PATCH 205/373] Archon of Absolution --- .../src/mage/cards/a/ArchonOfAbsolution.java | 49 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 50 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/a/ArchonOfAbsolution.java diff --git a/Mage.Sets/src/mage/cards/a/ArchonOfAbsolution.java b/Mage.Sets/src/mage/cards/a/ArchonOfAbsolution.java new file mode 100644 index 0000000000..f1aec8f3df --- /dev/null +++ b/Mage.Sets/src/mage/cards/a/ArchonOfAbsolution.java @@ -0,0 +1,49 @@ +package mage.cards.a; + +import mage.MageInt; +import mage.ObjectColor; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.costs.mana.ManaCostsImpl; +import mage.abilities.effects.common.combat.CantAttackYouUnlessPayManaAllEffect; +import mage.abilities.keyword.FlyingAbility; +import mage.abilities.keyword.ProtectionAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class ArchonOfAbsolution extends CardImpl { + + public ArchonOfAbsolution(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{3}{W}"); + + this.subtype.add(SubType.ARCHON); + this.power = new MageInt(3); + this.toughness = new MageInt(2); + + // Flying + this.addAbility(FlyingAbility.getInstance()); + + // Protection from white + this.addAbility(ProtectionAbility.from(ObjectColor.WHITE)); + + // Creatures can't attack you or a planeswalker you control unless their controller pays {1} for each of those creatures. + this.addAbility(new SimpleStaticAbility( + new CantAttackYouUnlessPayManaAllEffect(new ManaCostsImpl("{1}"), true) + )); + } + + private ArchonOfAbsolution(final ArchonOfAbsolution card) { + super(card); + } + + @Override + public ArchonOfAbsolution copy() { + return new ArchonOfAbsolution(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index f5b3db91b7..5c5fd7af27 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -33,6 +33,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Animating Faerie", 38, Rarity.UNCOMMON, mage.cards.a.AnimatingFaerie.class)); cards.add(new SetCardInfo("Arcane Signet", 331, Rarity.COMMON, mage.cards.a.ArcaneSignet.class)); cards.add(new SetCardInfo("Arcanist's Owl", 206, Rarity.UNCOMMON, mage.cards.a.ArcanistsOwl.class)); + cards.add(new SetCardInfo("Archon of Absolution", 3, Rarity.UNCOMMON, mage.cards.a.ArchonOfAbsolution.class)); cards.add(new SetCardInfo("Ardenvale Paladin", 4, Rarity.COMMON, mage.cards.a.ArdenvalePaladin.class)); cards.add(new SetCardInfo("Ardenvale Tactician", 5, Rarity.COMMON, mage.cards.a.ArdenvaleTactician.class)); cards.add(new SetCardInfo("Ayara, First of Locthwain", 75, Rarity.RARE, mage.cards.a.AyaraFirstOfLocthwain.class)); From ca518ed7df667e6633ebfe2f23c904521b7648b9 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 18 Sep 2019 21:57:01 -0400 Subject: [PATCH 206/373] Implemented Acclaimed Contender --- .../src/mage/cards/a/AcclaimedContender.java | 79 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 80 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/a/AcclaimedContender.java diff --git a/Mage.Sets/src/mage/cards/a/AcclaimedContender.java b/Mage.Sets/src/mage/cards/a/AcclaimedContender.java new file mode 100644 index 0000000000..7dfaf13e36 --- /dev/null +++ b/Mage.Sets/src/mage/cards/a/AcclaimedContender.java @@ -0,0 +1,79 @@ +package mage.cards.a; + +import mage.MageInt; +import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.condition.Condition; +import mage.abilities.condition.common.PermanentsOnTheBattlefieldCondition; +import mage.abilities.decorator.ConditionalInterveningIfTriggeredAbility; +import mage.abilities.dynamicvalue.common.StaticValue; +import mage.abilities.effects.common.LookLibraryAndPickControllerEffect; +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.filter.FilterCard; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterControlledPermanent; +import mage.filter.predicate.Predicates; +import mage.filter.predicate.mageobject.CardTypePredicate; +import mage.filter.predicate.mageobject.SubtypePredicate; +import mage.filter.predicate.mageobject.SupertypePredicate; +import mage.filter.predicate.permanent.AnotherPredicate; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class AcclaimedContender extends CardImpl { + + private static final FilterPermanent filter = new FilterControlledPermanent(SubType.KNIGHT); + private static final FilterCard filter2 + = new FilterCard("a Knight, Aura, Equipment, or legendary artifact card"); + + static { + filter.add(AnotherPredicate.instance); + filter2.add(Predicates.or( + new SubtypePredicate(SubType.KNIGHT), + new SubtypePredicate(SubType.AURA), + new SubtypePredicate(SubType.EQUIPMENT), + Predicates.and( + new SupertypePredicate(SuperType.LEGENDARY), + new CardTypePredicate(CardType.ARTIFACT) + ) + )); + } + + private static final Condition condition = new PermanentsOnTheBattlefieldCondition(filter); + + public AcclaimedContender(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{2}{W}"); + + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.KNIGHT); + this.power = new MageInt(3); + this.toughness = new MageInt(3); + + // When Acclaimed Contender enters the battlefield, if you control another Knight, look at the top five cards of your library. You may reveal a Knight, Aura, Equipment, or legendary artifact card from among them and put it into your hand. Put the rest on the bottom of your library in a random order. + this.addAbility(new ConditionalInterveningIfTriggeredAbility( + new EntersBattlefieldTriggeredAbility(new LookLibraryAndPickControllerEffect( + new StaticValue(5), false, new StaticValue(1), filter2, Zone.LIBRARY, false, + true, false, Zone.HAND, true, false, false + ).setBackInRandomOrder(true)), condition, "When {this} enters the battlefield, " + + "if you control another Knight, look at the top five cards of your library. " + + "You may reveal a Knight, Aura, Equipment, or legendary artifact card from among them " + + "and put it into your hand. Put the rest on the bottom of your library in a random order." + )); + } + + private AcclaimedContender(final AcclaimedContender card) { + super(card); + } + + @Override + public AcclaimedContender copy() { + return new AcclaimedContender(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 5c5fd7af27..b1f538f47a 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -28,6 +28,7 @@ public final class ThroneOfEldraine extends ExpansionSet { this.ratioBoosterMythic = 8; this.maxCardNumberInBooster = 269; // unconfirmed for now + cards.add(new SetCardInfo("Acclaimed Contender", 1, Rarity.RARE, mage.cards.a.AcclaimedContender.class)); cards.add(new SetCardInfo("Alela, Artful Provocateur", 324, Rarity.MYTHIC, mage.cards.a.AlelaArtfulProvocateur.class)); cards.add(new SetCardInfo("All That Glitters", 2, Rarity.UNCOMMON, mage.cards.a.AllThatGlitters.class)); cards.add(new SetCardInfo("Animating Faerie", 38, Rarity.UNCOMMON, mage.cards.a.AnimatingFaerie.class)); From c6bacef9acad1ffe5c1bc133219ac7f233649d47 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 18 Sep 2019 22:07:04 -0400 Subject: [PATCH 207/373] Implemented Giant's Skewer --- Mage.Sets/src/mage/cards/g/GiantsSkewer.java | 84 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 85 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/g/GiantsSkewer.java diff --git a/Mage.Sets/src/mage/cards/g/GiantsSkewer.java b/Mage.Sets/src/mage/cards/g/GiantsSkewer.java new file mode 100644 index 0000000000..1baf34e5fa --- /dev/null +++ b/Mage.Sets/src/mage/cards/g/GiantsSkewer.java @@ -0,0 +1,84 @@ +package mage.cards.g; + +import mage.abilities.TriggeredAbilityImpl; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.effects.common.CreateTokenEffect; +import mage.abilities.effects.common.continuous.BoostEquippedEffect; +import mage.abilities.keyword.EquipAbility; +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.DamagedCreatureEvent; +import mage.game.events.GameEvent; +import mage.game.permanent.Permanent; +import mage.game.permanent.token.FoodToken; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class GiantsSkewer extends CardImpl { + + public GiantsSkewer(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT}, "{1}{B}"); + + this.subtype.add(SubType.EQUIPMENT); + + // Equipped creature gets +2/+1. + this.addAbility(new SimpleStaticAbility(new BoostEquippedEffect(2, 1))); + + // Whenever equipped creature deals combat damage to a creature, create a Food token. + this.addAbility(new GiantsSkewerTriggeredAbility()); + + // Equip {3} + this.addAbility(new EquipAbility(3)); + } + + private GiantsSkewer(final GiantsSkewer card) { + super(card); + } + + @Override + public GiantsSkewer copy() { + return new GiantsSkewer(this); + } +} + +class GiantsSkewerTriggeredAbility extends TriggeredAbilityImpl { + + GiantsSkewerTriggeredAbility() { + super(Zone.BATTLEFIELD, new CreateTokenEffect(new FoodToken())); + } + + private GiantsSkewerTriggeredAbility(final GiantsSkewerTriggeredAbility ability) { + super(ability); + } + + @Override + public GiantsSkewerTriggeredAbility copy() { + return new GiantsSkewerTriggeredAbility(this); + } + + @Override + public boolean checkEventType(GameEvent event, Game game) { + return event.getType() == GameEvent.EventType.DAMAGED_CREATURE; + } + + @Override + public boolean checkTrigger(GameEvent event, Game game) { + if (!((DamagedCreatureEvent) event).isCombatDamage()) { + return false; + } + Permanent permanent = game.getPermanent(event.getSourceId()); + return permanent != null && permanent.getAttachments().contains(this.getSourceId()); + } + + @Override + public String getRule() { + return "Whenever equipped creature deals combat damage to a creature, create a Food token."; + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index b1f538f47a..832f0b907f 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -109,6 +109,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Garruk, Cursed Huntsman", 191, Rarity.MYTHIC, mage.cards.g.GarrukCursedHuntsman.class)); cards.add(new SetCardInfo("Giant Killer", 14, Rarity.RARE, mage.cards.g.GiantKiller.class)); cards.add(new SetCardInfo("Giant Opportunity", 159, Rarity.UNCOMMON, mage.cards.g.GiantOpportunity.class)); + cards.add(new SetCardInfo("Giant's Skewer", 91, Rarity.COMMON, mage.cards.g.GiantsSkewer.class)); cards.add(new SetCardInfo("Gilded Goose", 160, Rarity.RARE, mage.cards.g.GildedGoose.class)); cards.add(new SetCardInfo("Gingerbrute", 219, Rarity.COMMON, mage.cards.g.Gingerbrute.class)); cards.add(new SetCardInfo("Glass Casket", 15, Rarity.UNCOMMON, mage.cards.g.GlassCasket.class)); From fbf172e38a1db6566f506773a9a0cad4e1f99118 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 19 Sep 2019 07:22:17 -0400 Subject: [PATCH 208/373] updated ELD spoiler --- Utils/mtg-cards-data.txt | 11 +++++++++++ 1 file changed, 11 insertions(+) diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index c14ef5be9b..a45375ede2 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -36047,6 +36047,7 @@ Hypnotic Sprite|Throne of Eldraine|49|U|{U}{U}|Creature - Faerie|2|1|Flying| Mesmeric Glare|Throne of Eldraine|49|U|{2}{U}|Instant - Adventure|2|1|Counter target spell with converted mana cost 3 or less.| Into the Story|Throne of Eldraine|50|U|{5}{U}{U}|Instant|||This spell costs {3} less to cast if an opponent has seven or more cards in their graveyard.$Draw four cards.| The Magic Mirror|Throne of Eldraine|51|M|{6}{U}{U}{U}|Legendary Artifact|||This spell costs {1} less to cast for each instant and sorcery card in your graveyard.$You have no maximum hand size.$At the beginning of your upkeep, put a knowledge counter on The Magic Mirror, then draw a card for each knowledge counter on The Magic Mirror.| +Mantle of Tides|Throne of Eldraine|52|C|{U}|Artifact - Equipment|||Equipped creature gets +1/+2.$Whenever you draw your second card each turn, attach Mantle of Tides to target creature you control.$Equip {3}| Midnight Clock|Throne of Eldraine|54|R|{2}{U}|Artifact|||{T}: Add {U}.${2}{U}: Put an hour counter on Midnight Clock.$At the beginning of each upkeep, put an hour counter on Midnight Clock.$When the twelfth hour counter is put on Midnight Clock, shuffle your hand and graveyard into your library, then draw seven cards. Exile Midnight Clock.| Mirrormade|Throne of Eldraine|55|R|{1}{U}{U}|Enchantment|||You may have Mirrormade enter the battlefield as a copy of any artifact or enchantment on the battlefield.| Mistford River Turtle|Throne of Eldraine|56|C|{3}{U}|Creature - Turtle|1|5|Whenever Mistford River Turtle attacks, another target attacking non-Human creature can't be blocked this turn.| @@ -36054,6 +36055,8 @@ Mystical Dispute|Throne of Eldraine|58|U|{2}{U}|Instant|||This spell costs {2} l Opt|Throne of Eldraine|59|C|{U}|Instant|||Scry 1.$Draw a card.| Overwhelmed Apprentice|Throne of Eldraine|60|U|{U}|Creature - Human Wizard|1|2|When Overwhelmed Apprentice enters the battlefield, each opponent puts the top two cards of their library into their graveyard. Then you scry 2.| Run Away Together|Throne of Eldraine|62|C|{1}{U}|Instant|||Choose two target creatures controlled by different players. Return those creatures to their owners' hands.| +So Tiny|Throne of Eldraine|64|C|{U}|Enchantment - Aura|||Flash$Enchant creature$Enchanted creature gets -2/-0. It gets -6/-0 instead as long as its controller has seven or more cards in their graveyard.| +Steelgaze Griffin|Throne of Eldraine|65|C|{4}{U}|Creature - Griffin|2|4|Flying$When you draw your second card each turn, Steelgaze Griffin gets +2/+0 until end of turn.| Stolen by the Fae|Throne of Eldraine|66|R|{X}{U}{U}|Sorcery|||Return target creature with converted mana cost X to its owner's hand. You create X 1/1 blue Faerie creature tokens with flying.| Syr Elenora, the Discerning|Throne of Eldraine|67|U|{3}{U}{U}|Legendary Creature - Human Knight|*|4|Syr Elenora, the Discerning's power is equal to the number of cards in your hand.$When Syr Elenora enters the battlefield, draw a card.$Spells your opponents cast that target Syr Elenora cost {2} more to cast.| Tome Raider|Throne of Eldraine|68|C|{2}{U}|Creature - Faerie|1|1|Flying$When Tome Raider enters the battlefield, draw a card.| @@ -36074,10 +36077,12 @@ Cauldron's Gift|Throne of Eldraine|83|U|{4}{B}|Sorcery|||Adamant — If at least Clackbridge Troll|Throne of Eldraine|84|R|{3}{B}{B}|Creature - Troll|8|8|Trample, haste$When Clackbridge Troll enters the battlefield, target opponent creates three 0/1 white Goat creature tokens.$At the beginning of combat on your turn, any opponent may sacrifice a creature. If a player does, tap Clackbridge Troll, you gain 3 life, and you draw a card.| Epic Downfall|Throne of Eldraine|85|U|{1}{B}|Sorcery|||Exile target creature with converted mana cost 3 or greater.| Eye Collector|Throne of Eldraine|86|C|{B}|Creature - Faerie|1|1|Flying$Whenever Eye Collector deals combat damage to a player, each player puts the top card of their library into their graveyard.| +Foreboding Fruit|Throne of Eldraine|88|C|{2}{B}|Sorcery|||Target player draws two card sand loses 2 life.$Adament — If at least three black mana was spent to cast this spell, create a Food token.| Forever Young|Throne of Eldraine|89|C|{1}{B}|Sorcery|||Put any number of target creature cards from your graveyard on top of your library.$Draw a card.| Foulmire Knight|Throne of Eldraine|90|U|{B}|Creature - Zombie Knight|1|1|Deathtouch| Profane Insight|Throne of Eldraine|90|U|{2}{B}|Instant - Adventure|1|1|You draw a card and you lose 1 life.| Giant's Skewer|Throne of Eldraine|91|C|{1}{B}|Artifact - Equipment|||Equipped creature gets +2/+1.$Whenever equipped creature deals combat damage to a creature, create a Food token.$Equip {3}| +Locthwain Paladin|Throne of Eldraine|93|C|{3}{B}|Creature - Human Knight|3|2|Menace$Adament — If at least three black mana was spent to cast this spell, Locthwain Paladin enters the battlefield with a +1/+1 counter on it.| Lost Legion|Throne of Eldraine|94|C|{1}{B}{B}|Creature - Spirit Knight|2|3|When Lost Legion enters the battlefield, scry 2.| Murderous Rider|Throne of Eldraine|97|R|{1}{B}{B}|Creature - Zombie Knight|2|3|Lifelink$When Murderous Rider dies, put it on the bottom of its owner's library.| Swift End|Throne of Eldraine|97|R|{1}{B}{B}|Instant - Adventure|2|3|Destroy target creature or planeswalker. You lose 2 life.| @@ -36097,6 +36102,7 @@ Wicked Guardian|Throne of Eldraine|109|C|{3}{B}|Creature - Human Noble|4|2|When Wishclaw Talisman|Throne of Eldraine|110|R|{1}{B}|Artifact|||Wishclaw Talisman enters the battlefield with three wish counters on it.${1}, {T}, Remove a wish counter from Wishclaw Talisman: Search your library for a card, put it into your hand, then shuffle your library. An opponent gains control of Wishclaw Talisman. Activate this ability only during your turn.| Witch's Vengeance|Throne of Eldraine|111|R|{1}{B}{B}|Sorcery|||Creatures of the creature type of your choice get -3/-3 until end of turn.| Barge In|Throne of Eldraine|112|C|{R}|Instant|||Target attacking creature gets +2/+2 until end of turn. Each attacking non-Human creature gains trample until end of turn.| +Bloodhaze Wolverine|Throne of Eldraine|113|C|{1}{R}|Creature - Wolverine|2|1|Whenever you draw your second card each turn, Bloodhaze Wolverine gets +1/+1 and gains first strike until end of turn.| Blow Your House Down|Throne of Eldraine|114|C|{2}{R}|Sorcery|||Up to three target creatures can't block this turn. Destroy any of them that are Walls.| Bonecrusher Giant|Throne of Eldraine|115|R|{2}{R}|Creature - Giant|4|3|Whenever Bonecrusher Giant becomes the target of a spell, Bonecrusher Giant deals 2 damage to that spell's controller.| Stomp|Throne of Eldraine|115|R|{1}{R}|Instant - Adventure|4|3|Damage can't be prevented this turn. Stomp deals 2 damage to any target.| @@ -36113,6 +36119,7 @@ Fervent Champion|Throne of Eldraine|124|R|{R}|Creature - Human Knight|1|1|First Fires of Invention|Throne of Eldraine|125|R|{3}{R}|Enchantment|||You can cast spells only during your turn and you can cast no more than two spells each turn.$You may cast spells with converted mana cost less than or equal to the number of lands you control without paying their mana costs.| Irencrag Feat|Throne of Eldraine|127|R|{1}{R}{R}{R}|Sorcery|||Add seven {R}. You can cast only one more spell this turn.| Joust|Throne of Eldraine|129|U|{1}{R}|Sorcery|||Choose target creature you control and target creature you don't control. The creature you control gets +2/+1 until end of turn if it's a Knight. Then those creatures fight each other.| +Mad Ratter|Throne of Eldraine|130|U|{3}{R}|Creature - Goblin|1|2|Whenever you draw your second card each turn, create two 1/1 black Rat creature tokens.| Haggle|Throne of Eldraine|131|C|{R}|Instant - Adventure|2|3|You may discard a card. If you do, draw a card.| Merchant of the Vale|Throne of Eldraine|131|C|{2}{R}|Creature - Human Peasant|2|3|{2}{R}, Discard a card: Draw a card.| Ogre Errant|Throne of Eldraine|132|C|{3}{R}|Creature - Ogre Knight|3|4|Whenever Ogre Errant attacks, another target attacking Knight gains menace until end of turn.| @@ -36160,6 +36167,7 @@ Questing Beast|Throne of Eldraine|171|M|{2}{G}{G}|Legendary Creature - Beast|4|4 Return to Nature|Throne of Eldraine|173|C|{1}{G}|Instant|||Choose one —$• Destroy target artifact.$• Destroy target enchantment.$• Exile target card from a graveyard.| Rosethorn Acolyte|Throne of Eldraine|174|C|{2}{G}|Creature - Elf Druid|2|3|{T}: Add one mana of any color.| Seasonal Ritual|Throne of Eldraine|174|C|{G}|Sorcery - Adventure|2|3|Add one mana of any color.| +Rosethorn Halberd|Throne of Eldraine|175|C|{G}|Artifact - Equipment|||When Rosethorn Halberd enters the battlefield, attach to to target non-human creature you control.$Equipped creature gets +2/+1.$Equip {5}| Syr Faren, the Hengehammer|Throne of Eldraine|177|U|{G}{G}|Legendary Creature - Human Knight|2|2|Whenever Syr Faren, the Hengehammer attacks, another target attacking creature gets +X/+X until end of turn, where X is Syr Faren's power.| Tall as a Beanstalk|Throne of Eldraine|178|C|{3}{G}|Enchantment - Aura|||Enchant creature$Enchanted creature gets +3/+3, has reach, and is a Giant in addition to its other types.| Trail of Crumbs|Throne of Eldraine|179|U|{1}{G}|Enchantment|||When Trail of Crumbs enters the battlefield, create a Food token.$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.| @@ -36177,6 +36185,7 @@ Escape to the Wilds|Throne of Eldraine|189|R|{3}{R}{G}|Sorcery|||Exile the top f Faeburrow Elder|Throne of Eldraine|190|R|{1}{G}{W}|Creature - Treefolk Druid|0|0|Vigilance$Faeburrow Elder gets +1/+1 for each color among permanents you control.${T}: For each color among permanents you control, add one mana of that color.| Garruk, Cursed Huntsman|Throne of Eldraine|191|M|{4}{B}{G}|Legendary Planeswalker - Garruk|5|0: Create two 2/2 black and green Wolf creature tokens with "When this creature dies, put a loyalty counter on each Garruk you control."$−3: Destroy target creature. Draw a card.$−6: You get an emblem with "Creatures you control get +3/+3 and have trample."| Grumgully, the Generous|Throne of Eldraine|192|U|{1}{R}{G}|Legendary Creature - Goblin Shaman|3|3|Each other non-Human creature you controls enters the battlefield with an additional +1/+1 counter on it.| +Improbable Alliance|Throne of Eldraine|193|U|{U}{R}|Enchantment|||Whenever you draw your second card each turn, create a 1/1 blue Faerie creature token with flying.${4}{U}{R}: Draw a card, then discard a card.| Inspiring Veteran|Throne of Eldraine|194|U|{R}{W}|Creature - Human Knight|2|2|Other Knights you control get +1/+1.| Lochmere Serpent|Throne of Eldraine|195|R|{4}{U}{B}|Creature - Serpent|7|7|Flash${U}, Sacrifice an Island: Lochmere Serpent can't be blocked this turn.${B}, Sacrifice a Swamp: You gain 1 life and draw a card.${U}{B}: Exile five target cards from an opponent's graveyard. Return Lochmere Serpent from your graveyard to your hand. Activate this ability only any time you could cast a sorcery.| Maraleaf Pixie|Throne of Eldraine|196|U|{G}{U}|Creature - Faerie|2|2|Flying${T}: Add {G} or {U}.| @@ -36191,6 +36200,7 @@ Wandermare|Throne of Eldraine|204|U|{1}{G}{W}|Creature - Horse|3|3|Whenever you Wintermoor Commander|Throne of Eldraine|205|U|{W}{B}|Creature - Human Knight|2|*|Deathtouch$Wintermoor Commander's toughness is equal to the number of Knights you control.$Whenever Wintermoor Commander attacks, another target Knight you control gains indestructible until end of turn.| Arcanist's Owl|Throne of Eldraine|206|U|{W/U}{W/U}{W/U}{W/U}|Artifact Creature - Bird|3|3|Flying$When Arcanist's Owl enters the battlefield, look at the top four cards of your library. You may reveal an artifact or enchantment card from among them and put it into your hand. Put the rest on the bottom of your library in a random order.| Covetous Urge|Throne of Eldraine|207|U|{U/B}{U/B}{U/B}{U/B}|Sorcery|||Target opponent reveals their hand. You choose a nonland card from that player's graveyard or hand and exile it. You may cast that card for as long as it remains exiled, and you may spend mana as though it were mana of any color to cast that spell.| +Deathless Knight|Throne of Eldraine|208|U|{B/G}{B/G}{B/G}{B/G}|Creature - Skeleton Knight|4|2|Haste$Whenever you gain life for the first time each turn, return Deathless Knight from your graveyard to your hand.| Elite Headhunter|Throne of Eldraine|209|U|{B/R}{B/R}{B/R}{B/R}|Creature - Human Knight|2|3|Menace${B/R}{B/R}{B/R}, Sacrifice another creature or an artifact: Elite Headhunter deals 2 damage to target creature or planeswalker.| Fireborn Knight|Throne of Eldraine|210|U|{R/W}{R/W}{R/W}{R/W}|Creature - Human Knight|2|3|Double strike${R/W}{R/W}{R/W}{R/W}: Fireborn Knight gets +1/+1 until end of turn.| Loch Dragon|Throne of Eldraine|211|U|{U/R}{U/R}{U/R}{U/R}|Creature - Dragon|3|2|Flying$Whenever Loch Dragon enters the battlefield or attacks, you may discard a card. If you do, draw a card.| @@ -36219,6 +36229,7 @@ Castle Embereth|Throne of Eldraine|239|R||Land|||Castle Embereth enters the batt Castle Garenbrig|Throne of Eldraine|240|R||Land|||Castle Garenbrig enters the battlefield tapped unless you control a Forest.${T}: Add {G}.${2}{G}{G}, {T}: Add six {G}. Spend this mana only to cast creature spells or activate abilities of creatures.| Castle Locthwain|Throne of Eldraine|241|R||Land|||Castle Locthwain enters the battlefield tapped unless you control a Swamp.${T}: Add {B}.${1}{B}{B}, {T}: Draw a card, then you lose life equal to the number of cards in your hand.| Castle Vantress|Throne of Eldraine|242|R||Land|||Castle Vantress enters the battlefield tapped unless you control an Island.${T}: Add {U}.${2}{U}{U}, {T}: Scry 2.| +Fabled Passage|Throne of Eldraine|244|R||Land|||{T}, Sacrifice Fabled Passage: Search your library for a basic land card, put it onto the battlefield tapped, then shuffle your library. Then if you control four or more lands, untap that land.| Idyllic Grange|Throne of Eldraine|246|C||Land - Plains|||({T}: Add {W}.)$Idyllic Grange enters the battlefield tapped unless you control three or more other Plains.$When Idyllic Grange enters the battlefield untapped, put a +1/+1 counter on target creature you control.| Tournament Grounds|Throne of Eldraine|248|U||Land|||{T}: Add {C}.${T}: Add {R}, {W}, or {B}. Spend this mana only to cast a Knight or Equipment spell.| Witch's Cottage|Throne of Eldraine|249|C||Land - Swamp|||({T}: Add {B}.)$Witch's Cottage enters the battlefield tapped unless you control three or more other Swamps.$When Witch's Cottage enters the battlefield untapped, you may put target creature card from your graveyard on top of your library.| From aa26d33246835e8c98c5934115d2118e623682bb Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 19 Sep 2019 08:09:39 -0400 Subject: [PATCH 209/373] Implemented Mad Ratter --- Mage.Sets/src/mage/cards/m/MadRatter.java | 38 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 39 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/m/MadRatter.java diff --git a/Mage.Sets/src/mage/cards/m/MadRatter.java b/Mage.Sets/src/mage/cards/m/MadRatter.java new file mode 100644 index 0000000000..aa38a13633 --- /dev/null +++ b/Mage.Sets/src/mage/cards/m/MadRatter.java @@ -0,0 +1,38 @@ +package mage.cards.m; + +import mage.MageInt; +import mage.abilities.common.DrawSecondCardTriggeredAbility; +import mage.abilities.effects.common.CreateTokenEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.game.permanent.token.RatToken; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class MadRatter extends CardImpl { + + public MadRatter(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{3}{R}"); + + this.subtype.add(SubType.GOBLIN); + this.power = new MageInt(1); + this.toughness = new MageInt(2); + + // Whenever you draw your second card each turn, create two 1/1 black Rat creature tokens. + this.addAbility(new DrawSecondCardTriggeredAbility(new CreateTokenEffect(new RatToken(), 2), false)); + } + + private MadRatter(final MadRatter card) { + super(card); + } + + @Override + public MadRatter copy() { + return new MadRatter(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 832f0b907f..aa57982bd6 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -141,6 +141,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Lovestruck Beast", 165, Rarity.RARE, mage.cards.l.LovestruckBeast.class)); cards.add(new SetCardInfo("Lucky Clover", 226, Rarity.UNCOMMON, mage.cards.l.LuckyClover.class)); cards.add(new SetCardInfo("Mace of the Valiant", 314, Rarity.RARE, mage.cards.m.MaceOfTheValiant.class)); + cards.add(new SetCardInfo("Mad Ratter", 130, Rarity.UNCOMMON, mage.cards.m.MadRatter.class)); cards.add(new SetCardInfo("Maraleaf Pixie", 196, Rarity.UNCOMMON, mage.cards.m.MaraleafPixie.class)); cards.add(new SetCardInfo("Maraleaf Rider", 166, Rarity.COMMON, mage.cards.m.MaraleafRider.class)); cards.add(new SetCardInfo("Merchant of the Vale", 131, Rarity.COMMON, mage.cards.m.MerchantOfTheVale.class)); From a645932c4f722bb9440ad7ec2a33253846a1e3b3 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 19 Sep 2019 08:12:34 -0400 Subject: [PATCH 210/373] Implemented Steelgaze Griffin --- .../src/mage/cards/s/SteelgazeGriffin.java | 42 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 43 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/s/SteelgazeGriffin.java diff --git a/Mage.Sets/src/mage/cards/s/SteelgazeGriffin.java b/Mage.Sets/src/mage/cards/s/SteelgazeGriffin.java new file mode 100644 index 0000000000..303869131e --- /dev/null +++ b/Mage.Sets/src/mage/cards/s/SteelgazeGriffin.java @@ -0,0 +1,42 @@ +package mage.cards.s; + +import mage.MageInt; +import mage.abilities.common.DrawSecondCardTriggeredAbility; +import mage.abilities.effects.common.continuous.BoostSourceEffect; +import mage.abilities.keyword.FlyingAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class SteelgazeGriffin extends CardImpl { + + public SteelgazeGriffin(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{4}{U}"); + + this.subtype.add(SubType.GRIFFIN); + this.power = new MageInt(2); + this.toughness = new MageInt(4); + + // Flying + this.addAbility(FlyingAbility.getInstance()); + + // When you draw your second card each turn, Steelgaze Griffin gets +2/+0 until end of turn. + this.addAbility(new DrawSecondCardTriggeredAbility(new BoostSourceEffect(2, 0, Duration.EndOfTurn), false)); + } + + private SteelgazeGriffin(final SteelgazeGriffin card) { + super(card); + } + + @Override + public SteelgazeGriffin copy() { + return new SteelgazeGriffin(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index aa57982bd6..c6e5bce55a 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -206,6 +206,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Spinning Wheel", 234, Rarity.UNCOMMON, mage.cards.s.SpinningWheel.class)); cards.add(new SetCardInfo("Steelbane Hydra", 322, Rarity.RARE, mage.cards.s.SteelbaneHydra.class)); cards.add(new SetCardInfo("Steelclaw Lance", 202, Rarity.UNCOMMON, mage.cards.s.SteelclawLance.class)); + cards.add(new SetCardInfo("Steelgaze Griffin", 65, Rarity.COMMON, mage.cards.s.SteelgazeGriffin.class)); cards.add(new SetCardInfo("Stolen by the Fae", 66, Rarity.RARE, mage.cards.s.StolenByTheFae.class)); cards.add(new SetCardInfo("Stonecoil Serpent", 235, Rarity.RARE, mage.cards.s.StonecoilSerpent.class)); cards.add(new SetCardInfo("Stormfist Crusader", 203, Rarity.RARE, mage.cards.s.StormfistCrusader.class)); From 351e8a12b52c5ca4185348a4360e03b40de52d8c Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 19 Sep 2019 08:17:12 -0400 Subject: [PATCH 211/373] Implemented Improbable Alliance --- .../src/mage/cards/i/ImprobableAlliance.java | 40 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 41 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/i/ImprobableAlliance.java diff --git a/Mage.Sets/src/mage/cards/i/ImprobableAlliance.java b/Mage.Sets/src/mage/cards/i/ImprobableAlliance.java new file mode 100644 index 0000000000..85c917a197 --- /dev/null +++ b/Mage.Sets/src/mage/cards/i/ImprobableAlliance.java @@ -0,0 +1,40 @@ +package mage.cards.i; + +import mage.abilities.common.DrawSecondCardTriggeredAbility; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.costs.mana.ManaCostsImpl; +import mage.abilities.effects.common.CreateTokenEffect; +import mage.abilities.effects.common.DrawDiscardControllerEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.game.permanent.token.FaerieToken; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class ImprobableAlliance extends CardImpl { + + public ImprobableAlliance(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ENCHANTMENT}, "{U}{R}"); + + // Whenever you draw your second card each turn, create a 1/1 blue Faerie creature token with flying. + this.addAbility(new DrawSecondCardTriggeredAbility(new CreateTokenEffect(new FaerieToken()), false)); + + // {4}{U}{R}: Draw a card, then discard a card. + this.addAbility(new SimpleActivatedAbility( + new DrawDiscardControllerEffect(1, 1), new ManaCostsImpl("{4}{U}{R}") + )); + } + + private ImprobableAlliance(final ImprobableAlliance card) { + super(card); + } + + @Override + public ImprobableAlliance copy() { + return new ImprobableAlliance(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index c6e5bce55a..415bfa396b 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -121,6 +121,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Heraldic Banner", 222, Rarity.UNCOMMON, mage.cards.h.HeraldicBanner.class)); cards.add(new SetCardInfo("Hypnotic Sprite", 49, Rarity.UNCOMMON, mage.cards.h.HypnoticSprite.class)); cards.add(new SetCardInfo("Idyllic Grange", 246, Rarity.COMMON, mage.cards.i.IdyllicGrange.class)); + cards.add(new SetCardInfo("Improbable Alliance", 193, Rarity.UNCOMMON, mage.cards.i.ImprobableAlliance.class)); cards.add(new SetCardInfo("Inquisitive Puppet", 223, Rarity.UNCOMMON, mage.cards.i.InquisitivePuppet.class)); cards.add(new SetCardInfo("Insatiable Appetite", 162, Rarity.COMMON, mage.cards.i.InsatiableAppetite.class)); cards.add(new SetCardInfo("Inspiring Veteran", 194, Rarity.UNCOMMON, mage.cards.i.InspiringVeteran.class)); From eea574ebaf6f9eceeed676a6cbf88771b3513308 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 19 Sep 2019 08:28:01 -0400 Subject: [PATCH 212/373] Implemented Mantle of Tides --- Mage.Sets/src/mage/cards/m/MantleOfTides.java | 50 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 51 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/m/MantleOfTides.java diff --git a/Mage.Sets/src/mage/cards/m/MantleOfTides.java b/Mage.Sets/src/mage/cards/m/MantleOfTides.java new file mode 100644 index 0000000000..efde9dae20 --- /dev/null +++ b/Mage.Sets/src/mage/cards/m/MantleOfTides.java @@ -0,0 +1,50 @@ +package mage.cards.m; + +import mage.abilities.Ability; +import mage.abilities.common.DrawSecondCardTriggeredAbility; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.effects.common.AttachEffect; +import mage.abilities.effects.common.continuous.BoostEquippedEffect; +import mage.abilities.keyword.EquipAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Outcome; +import mage.constants.SubType; +import mage.target.common.TargetControlledCreaturePermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class MantleOfTides extends CardImpl { + + public MantleOfTides(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT}, "{U}"); + + this.subtype.add(SubType.EQUIPMENT); + + // Equipped creature gets +1/+2. + this.addAbility(new SimpleStaticAbility(new BoostEquippedEffect(1, 2))); + + // Whenever you draw your second card each turn, attach Mantle of Tides to target creature you control. + Ability ability = new DrawSecondCardTriggeredAbility(new AttachEffect( + Outcome.Benefit, "attach {this} to target creature you control" + ), false); + ability.addTarget(new TargetControlledCreaturePermanent()); + this.addAbility(ability); + + // Equip {3} + this.addAbility(new EquipAbility(3)); + } + + private MantleOfTides(final MantleOfTides card) { + super(card); + } + + @Override + public MantleOfTides copy() { + return new MantleOfTides(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 415bfa396b..e77010639e 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -143,6 +143,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Lucky Clover", 226, Rarity.UNCOMMON, mage.cards.l.LuckyClover.class)); cards.add(new SetCardInfo("Mace of the Valiant", 314, Rarity.RARE, mage.cards.m.MaceOfTheValiant.class)); cards.add(new SetCardInfo("Mad Ratter", 130, Rarity.UNCOMMON, mage.cards.m.MadRatter.class)); + cards.add(new SetCardInfo("Mantle of Tides", 52, Rarity.COMMON, mage.cards.m.MantleOfTides.class)); cards.add(new SetCardInfo("Maraleaf Pixie", 196, Rarity.UNCOMMON, mage.cards.m.MaraleafPixie.class)); cards.add(new SetCardInfo("Maraleaf Rider", 166, Rarity.COMMON, mage.cards.m.MaraleafRider.class)); cards.add(new SetCardInfo("Merchant of the Vale", 131, Rarity.COMMON, mage.cards.m.MerchantOfTheVale.class)); From 91355a0cd612ed608f406e5e08708cd13efbfba7 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 19 Sep 2019 08:31:21 -0400 Subject: [PATCH 213/373] Implemented Locthwain Paladin --- .../src/mage/cards/l/LocthwainPaladin.java | 50 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 51 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/l/LocthwainPaladin.java diff --git a/Mage.Sets/src/mage/cards/l/LocthwainPaladin.java b/Mage.Sets/src/mage/cards/l/LocthwainPaladin.java new file mode 100644 index 0000000000..ab4ffa5d21 --- /dev/null +++ b/Mage.Sets/src/mage/cards/l/LocthwainPaladin.java @@ -0,0 +1,50 @@ +package mage.cards.l; + +import mage.MageInt; +import mage.abilities.common.EntersBattlefieldAbility; +import mage.abilities.condition.common.AdamantCondition; +import mage.abilities.effects.common.counter.AddCountersSourceEffect; +import mage.abilities.keyword.MenaceAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.counters.CounterType; +import mage.watchers.common.ManaSpentToCastWatcher; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class LocthwainPaladin extends CardImpl { + + public LocthwainPaladin(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{3}{B}"); + + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.KNIGHT); + this.power = new MageInt(3); + this.toughness = new MageInt(2); + + // Menace + this.addAbility(new MenaceAbility()); + + // Adamant — If at least three black mana was spent to cast this spell, Locthwain Paladin enters the battlefield with a +1/+1 counter on it. + this.addAbility(new EntersBattlefieldAbility( + new AddCountersSourceEffect(CounterType.P1P1.createInstance()), + AdamantCondition.BLACK, "
Adamant — " + + "If at least three black mana was spent to cast this spell, " + + "{this} enters the battlefield with a +1/+1 counter on it.", "" + ), new ManaSpentToCastWatcher()); + } + + private LocthwainPaladin(final LocthwainPaladin card) { + super(card); + } + + @Override + public LocthwainPaladin copy() { + return new LocthwainPaladin(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index e77010639e..2adf0a525b 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -137,6 +137,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Linden, the Steadfast Queen", 20, Rarity.RARE, mage.cards.l.LindenTheSteadfastQueen.class)); cards.add(new SetCardInfo("Loch Dragon", 211, Rarity.UNCOMMON, mage.cards.l.LochDragon.class)); cards.add(new SetCardInfo("Lochmere Serpent", 195, Rarity.RARE, mage.cards.l.LochmereSerpent.class)); + cards.add(new SetCardInfo("Locthwain Paladin", 93, Rarity.COMMON, mage.cards.l.LocthwainPaladin.class)); cards.add(new SetCardInfo("Lonesome Unicorn", 21, Rarity.COMMON, mage.cards.l.LonesomeUnicorn.class)); cards.add(new SetCardInfo("Lost Legion", 94, Rarity.COMMON, mage.cards.l.LostLegion.class)); cards.add(new SetCardInfo("Lovestruck Beast", 165, Rarity.RARE, mage.cards.l.LovestruckBeast.class)); From 9e3ca82279bc86d5efbac54dce75b5649969280c Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 19 Sep 2019 08:36:29 -0400 Subject: [PATCH 214/373] Implemented Bloodhaze Wolverine --- .../src/mage/cards/b/BloodhazeWolverine.java | 47 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 48 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/b/BloodhazeWolverine.java diff --git a/Mage.Sets/src/mage/cards/b/BloodhazeWolverine.java b/Mage.Sets/src/mage/cards/b/BloodhazeWolverine.java new file mode 100644 index 0000000000..38b7b6e513 --- /dev/null +++ b/Mage.Sets/src/mage/cards/b/BloodhazeWolverine.java @@ -0,0 +1,47 @@ +package mage.cards.b; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.DrawSecondCardTriggeredAbility; +import mage.abilities.effects.common.continuous.BoostSourceEffect; +import mage.abilities.effects.common.continuous.GainAbilitySourceEffect; +import mage.abilities.keyword.FirstStrikeAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class BloodhazeWolverine extends CardImpl { + + public BloodhazeWolverine(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{1}{R}"); + + this.subtype.add(SubType.WOLVERINE); + this.power = new MageInt(2); + this.toughness = new MageInt(1); + + // Whenever you draw your second card each turn, Bloodhaze Wolverine gets +1/+1 and gains first strike until end of turn. + Ability ability = new DrawSecondCardTriggeredAbility(new BoostSourceEffect( + 1, 1, Duration.EndOfTurn + ).setText("{this} gets +1/+1"), false); + ability.addEffect(new GainAbilitySourceEffect( + FirstStrikeAbility.getInstance(), Duration.EndOfTurn + ).setText("and gains first strike until end of turn")); + this.addAbility(ability); + } + + private BloodhazeWolverine(final BloodhazeWolverine card) { + super(card); + } + + @Override + public BloodhazeWolverine copy() { + return new BloodhazeWolverine(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 2adf0a525b..2137558b37 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -45,6 +45,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Belle of the Brawl", 78, Rarity.UNCOMMON, mage.cards.b.BelleOfTheBrawl.class)); cards.add(new SetCardInfo("Beloved Princess", 7, Rarity.COMMON, mage.cards.b.BelovedPrincess.class)); cards.add(new SetCardInfo("Blacklance Paragon", 79, Rarity.RARE, mage.cards.b.BlacklanceParagon.class)); + cards.add(new SetCardInfo("Bloodhaze Wolverine", 113, Rarity.COMMON, mage.cards.b.BloodhazeWolverine.class)); cards.add(new SetCardInfo("Blow Your House Down", 114, Rarity.COMMON, mage.cards.b.BlowYourHouseDown.class)); cards.add(new SetCardInfo("Bog Naughty", 80, Rarity.UNCOMMON, mage.cards.b.BogNaughty.class)); cards.add(new SetCardInfo("Bonecrusher Giant", 115, Rarity.RARE, mage.cards.b.BonecrusherGiant.class)); From bab15fec862f31b9d35fbfd5d3eab1152332529d Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 19 Sep 2019 08:46:01 -0400 Subject: [PATCH 215/373] Implemented Foreboding Fruit --- .../src/mage/cards/f/ForebodingFruit.java | 46 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 47 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/f/ForebodingFruit.java diff --git a/Mage.Sets/src/mage/cards/f/ForebodingFruit.java b/Mage.Sets/src/mage/cards/f/ForebodingFruit.java new file mode 100644 index 0000000000..14cf2f4416 --- /dev/null +++ b/Mage.Sets/src/mage/cards/f/ForebodingFruit.java @@ -0,0 +1,46 @@ +package mage.cards.f; + +import mage.abilities.condition.common.AdamantCondition; +import mage.abilities.decorator.ConditionalOneShotEffect; +import mage.abilities.effects.common.CreateTokenEffect; +import mage.abilities.effects.common.DrawCardTargetEffect; +import mage.abilities.effects.common.LoseLifeTargetEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.game.permanent.token.FoodToken; +import mage.target.TargetPlayer; +import mage.watchers.common.ManaSpentToCastWatcher; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class ForebodingFruit extends CardImpl { + + public ForebodingFruit(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.SORCERY}, "{2}{B}"); + + // Target player draws two cards and loses 2 life. + this.getSpellAbility().addEffect(new DrawCardTargetEffect(2)); + this.getSpellAbility().addEffect(new LoseLifeTargetEffect(2).setText("and loses 2 life")); + this.getSpellAbility().addTarget(new TargetPlayer()); + + // Adamant — If at least three black mana was spent to cast this spell, create a Food token. + this.getSpellAbility().addEffect(new ConditionalOneShotEffect( + new CreateTokenEffect(new FoodToken()), AdamantCondition.BLACK, "
Adamant — " + + "If at least three black mana was spent to cast this spell, create a Food token." + )); + this.getSpellAbility().addWatcher(new ManaSpentToCastWatcher()); + } + + private ForebodingFruit(final ForebodingFruit card) { + super(card); + } + + @Override + public ForebodingFruit copy() { + return new ForebodingFruit(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 2137558b37..005efcf594 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -98,6 +98,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Fires of Invention", 125, Rarity.RARE, mage.cards.f.FiresOfInvention.class)); cards.add(new SetCardInfo("Flaxen Intruder", 155, Rarity.UNCOMMON, mage.cards.f.FlaxenIntruder.class)); cards.add(new SetCardInfo("Folio of Fancies", 46, Rarity.RARE, mage.cards.f.FolioOfFancies.class)); + cards.add(new SetCardInfo("Foreboding Fruit", 88, Rarity.COMMON, mage.cards.f.ForebodingFruit.class)); cards.add(new SetCardInfo("Forever Young", 89, Rarity.COMMON, mage.cards.f.ForeverYoung.class)); cards.add(new SetCardInfo("Fortifying Provisions", 13, Rarity.COMMON, mage.cards.f.FortifyingProvisions.class)); cards.add(new SetCardInfo("Foulmire Knight", 90, Rarity.UNCOMMON, mage.cards.f.FoulmireKnight.class)); From 62284d78178f7bb54aee2c9f7141e3d336e8d895 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 19 Sep 2019 08:51:36 -0400 Subject: [PATCH 216/373] Implemented Rosethorn Halberd --- .../src/mage/cards/r/RosethornHalberd.java | 61 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + Utils/mtg-cards-data.txt | 8 +-- 3 files changed, 66 insertions(+), 4 deletions(-) create mode 100644 Mage.Sets/src/mage/cards/r/RosethornHalberd.java diff --git a/Mage.Sets/src/mage/cards/r/RosethornHalberd.java b/Mage.Sets/src/mage/cards/r/RosethornHalberd.java new file mode 100644 index 0000000000..ca2c55f834 --- /dev/null +++ b/Mage.Sets/src/mage/cards/r/RosethornHalberd.java @@ -0,0 +1,61 @@ +package mage.cards.r; + +import mage.abilities.Ability; +import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.effects.common.AttachEffect; +import mage.abilities.effects.common.continuous.BoostEquippedEffect; +import mage.abilities.keyword.EquipAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Outcome; +import mage.constants.SubType; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterControlledCreaturePermanent; +import mage.filter.predicate.Predicates; +import mage.filter.predicate.mageobject.SubtypePredicate; +import mage.target.TargetPermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class RosethornHalberd extends CardImpl { + + private static final FilterPermanent filter + = new FilterControlledCreaturePermanent("non-Human creature you control"); + + static { + filter.add(Predicates.not(new SubtypePredicate(SubType.HUMAN))); + } + + public RosethornHalberd(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT}, "{G}"); + + this.subtype.add(SubType.EQUIPMENT); + + // When Rosethorn Halberd enters the battlefield, attach it to target non-Human creature you control. + Ability ability = new EntersBattlefieldTriggeredAbility( + new AttachEffect(Outcome.Benefit, "attach it to target non-Human creature you control") + ); + ability.addTarget(new TargetPermanent(filter)); + this.addAbility(ability); + + // Equipped creature gets +2/+1. + this.addAbility(new SimpleStaticAbility(new BoostEquippedEffect(2, 1))); + + // Equip {5} + this.addAbility(new EquipAbility(5)); + } + + private RosethornHalberd(final RosethornHalberd card) { + super(card); + } + + @Override + public RosethornHalberd copy() { + return new RosethornHalberd(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 005efcf594..4690f59840 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -185,6 +185,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Righteousness", 27, Rarity.UNCOMMON, mage.cards.r.Righteousness.class)); cards.add(new SetCardInfo("Robber of the Rich", 138, Rarity.MYTHIC, mage.cards.r.RobberOfTheRich.class)); cards.add(new SetCardInfo("Rosethorn Acolyte", 174, Rarity.COMMON, mage.cards.r.RosethornAcolyte.class)); + cards.add(new SetCardInfo("Rosethorn Halberd", 175, Rarity.COMMON, mage.cards.r.RosethornHalberd.class)); cards.add(new SetCardInfo("Roving Keep", 228, Rarity.COMMON, mage.cards.r.RovingKeep.class)); cards.add(new SetCardInfo("Rowan's Battleguard", 306, Rarity.UNCOMMON, mage.cards.r.RowansBattleguard.class)); cards.add(new SetCardInfo("Rowan's Stalwarts", 307, Rarity.RARE, mage.cards.r.RowansStalwarts.class)); diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index a45375ede2..d777d603b7 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -36033,7 +36033,7 @@ Venerable Knight|Throne of Eldraine|35|U|{W}|Creature - Human Knight|2|1|When Ve Worthy Knight|Throne of Eldraine|36|R|{1}{W}|Creature - Human Knight|2|2|Whenever you cast a Knight spell, create a 1/1 white Human creature token.| Animating Faerie|Throne of Eldraine|38|U|{2}{U}|Creature - Faerie|2|2|Flying| Bring to Life|Throne of Eldraine|38|U|{2}{U}|Sorcery - Adventure|2|2|Target noncreature artifact you control becomes a 0/0 artifact creature. Put four +1/+1 counters on it.| -Brazen Borrower|Throne of Eldraine|39|M|{1}{U}{U}|Creature - Faerie Rogue|3|1|Flash$Flying$Bazen Borrower can block only creatures with flying.| +Brazen Borrower|Throne of Eldraine|39|M|{1}{U}{U}|Creature - Faerie Rogue|3|1|Flash$Flying$Brazen Borrower can block only creatures with flying.| Petty Theft|Throne of Eldraine|39|M|{1}{U}|Instant - Adventure|3|1|Return target nonland permanent an opponent controls to its owner's hand.| Corridor Monitor|Throne of Eldraine|41|C|{1}{U}|Artifact Creature - Construct|1|4|When Corridor Monitor enters the battlefield, untap target artifact or creature you control.| Emry, Lurker of the Loch|Throne of Eldraine|43|R|{2}{U}|Legendary Creature - Merfolk Wizard|1|2|This spell costs {1} less to cast for each artifact you control.$When Emry, Lurker of the Loch enters the battlefield, put the top four cards of your library into your graveyard.${T}: Choose target artifact card in your graveyard. You may cast that card this turn.| @@ -36077,12 +36077,12 @@ Cauldron's Gift|Throne of Eldraine|83|U|{4}{B}|Sorcery|||Adamant — If at least Clackbridge Troll|Throne of Eldraine|84|R|{3}{B}{B}|Creature - Troll|8|8|Trample, haste$When Clackbridge Troll enters the battlefield, target opponent creates three 0/1 white Goat creature tokens.$At the beginning of combat on your turn, any opponent may sacrifice a creature. If a player does, tap Clackbridge Troll, you gain 3 life, and you draw a card.| Epic Downfall|Throne of Eldraine|85|U|{1}{B}|Sorcery|||Exile target creature with converted mana cost 3 or greater.| Eye Collector|Throne of Eldraine|86|C|{B}|Creature - Faerie|1|1|Flying$Whenever Eye Collector deals combat damage to a player, each player puts the top card of their library into their graveyard.| -Foreboding Fruit|Throne of Eldraine|88|C|{2}{B}|Sorcery|||Target player draws two card sand loses 2 life.$Adament — If at least three black mana was spent to cast this spell, create a Food token.| +Foreboding Fruit|Throne of Eldraine|88|C|{2}{B}|Sorcery|||Target player draws two cards and loses 2 life.$Adamant — If at least three black mana was spent to cast this spell, create a Food token.| Forever Young|Throne of Eldraine|89|C|{1}{B}|Sorcery|||Put any number of target creature cards from your graveyard on top of your library.$Draw a card.| Foulmire Knight|Throne of Eldraine|90|U|{B}|Creature - Zombie Knight|1|1|Deathtouch| Profane Insight|Throne of Eldraine|90|U|{2}{B}|Instant - Adventure|1|1|You draw a card and you lose 1 life.| Giant's Skewer|Throne of Eldraine|91|C|{1}{B}|Artifact - Equipment|||Equipped creature gets +2/+1.$Whenever equipped creature deals combat damage to a creature, create a Food token.$Equip {3}| -Locthwain Paladin|Throne of Eldraine|93|C|{3}{B}|Creature - Human Knight|3|2|Menace$Adament — If at least three black mana was spent to cast this spell, Locthwain Paladin enters the battlefield with a +1/+1 counter on it.| +Locthwain Paladin|Throne of Eldraine|93|C|{3}{B}|Creature - Human Knight|3|2|Menace$Adamant — If at least three black mana was spent to cast this spell, Locthwain Paladin enters the battlefield with a +1/+1 counter on it.| Lost Legion|Throne of Eldraine|94|C|{1}{B}{B}|Creature - Spirit Knight|2|3|When Lost Legion enters the battlefield, scry 2.| Murderous Rider|Throne of Eldraine|97|R|{1}{B}{B}|Creature - Zombie Knight|2|3|Lifelink$When Murderous Rider dies, put it on the bottom of its owner's library.| Swift End|Throne of Eldraine|97|R|{1}{B}{B}|Instant - Adventure|2|3|Destroy target creature or planeswalker. You lose 2 life.| @@ -36167,7 +36167,7 @@ Questing Beast|Throne of Eldraine|171|M|{2}{G}{G}|Legendary Creature - Beast|4|4 Return to Nature|Throne of Eldraine|173|C|{1}{G}|Instant|||Choose one —$• Destroy target artifact.$• Destroy target enchantment.$• Exile target card from a graveyard.| Rosethorn Acolyte|Throne of Eldraine|174|C|{2}{G}|Creature - Elf Druid|2|3|{T}: Add one mana of any color.| Seasonal Ritual|Throne of Eldraine|174|C|{G}|Sorcery - Adventure|2|3|Add one mana of any color.| -Rosethorn Halberd|Throne of Eldraine|175|C|{G}|Artifact - Equipment|||When Rosethorn Halberd enters the battlefield, attach to to target non-human creature you control.$Equipped creature gets +2/+1.$Equip {5}| +Rosethorn Halberd|Throne of Eldraine|175|C|{G}|Artifact - Equipment|||When Rosethorn Halberd enters the battlefield, attach it to target non-Human creature you control.$Equipped creature gets +2/+1.$Equip {5}| Syr Faren, the Hengehammer|Throne of Eldraine|177|U|{G}{G}|Legendary Creature - Human Knight|2|2|Whenever Syr Faren, the Hengehammer attacks, another target attacking creature gets +X/+X until end of turn, where X is Syr Faren's power.| Tall as a Beanstalk|Throne of Eldraine|178|C|{3}{G}|Enchantment - Aura|||Enchant creature$Enchanted creature gets +3/+3, has reach, and is a Giant in addition to its other types.| Trail of Crumbs|Throne of Eldraine|179|U|{1}{G}|Enchantment|||When Trail of Crumbs enters the battlefield, create a Food token.$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.| From 0ead44c15682edd7eec28e79b50f7b3c6b2625e0 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 19 Sep 2019 17:31:45 -0400 Subject: [PATCH 217/373] updated ELD spoilers --- Utils/mtg-cards-data.txt | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index d777d603b7..8eb503f3fc 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -36010,6 +36010,7 @@ Fortifying Provisions|Throne of Eldraine|13|C|{2}{W}|Enchantment|||Creatures you Chop Down|Throne of Eldraine|14|R|{2}{W}|Instant - Adventure|1|2|Destroy target creature with power 4 or greater.| Giant Killer|Throne of Eldraine|14|R|{W}|Creature - Human Peasant|1|2|{1}{W}, {T}: Tap target creature.| Glass Casket|Throne of Eldraine|15|U|{1}{W}|Artifact|||When Glass Casket enters the battlefield, exile target creature an opponent controls with converted mana cost 3 or less until Glass Casket leaves the battlefield.| +Happily Ever After|Throne of Eldraine|16|R|{2}{W}|Enchantment|||When Happily Ever After enters the battlefield, each player gains 5 life and draws a card.$At the beginning of your upkeep, if there are five colors among permanents you control, there are six or more card types among permanents you control and/or cards in your graveyard, and your life total is greater than or equal to your starting life total, you win the game.| Harmonious Archon|Throne of Eldraine|17|M|{4}{W}{W}|Creature - Archon|4|5|Flying$Non-Archon creatures have base power and toughness 3/3.$When Harmonious Archon enters the battlefield, create two 1/1 white Human creature tokens.| Knight of the Keep|Throne of Eldraine|19|C|{2}{W}|Creature - Human Knight|3|2|| Linden, the Steadfast Queen|Throne of Eldraine|20|R|{W}{W}{W}|Legendary Creature - Human Noble|3|3|Vigilance$Whenever a white creature you control attacks, you gain 1 life.| @@ -36055,6 +36056,7 @@ Mystical Dispute|Throne of Eldraine|58|U|{2}{U}|Instant|||This spell costs {2} l Opt|Throne of Eldraine|59|C|{U}|Instant|||Scry 1.$Draw a card.| Overwhelmed Apprentice|Throne of Eldraine|60|U|{U}|Creature - Human Wizard|1|2|When Overwhelmed Apprentice enters the battlefield, each opponent puts the top two cards of their library into their graveyard. Then you scry 2.| Run Away Together|Throne of Eldraine|62|C|{1}{U}|Instant|||Choose two target creatures controlled by different players. Return those creatures to their owners' hands.| +Sage of the Falls|Throne of Eldraine|63|U|{4}{U}|Creature - Merfolk Wizard|2|5|Whenever Sage of the Falls or another non-Human creature enters the battlefield under you control, you may draw a card. If you do, discard a card.| So Tiny|Throne of Eldraine|64|C|{U}|Enchantment - Aura|||Flash$Enchant creature$Enchanted creature gets -2/-0. It gets -6/-0 instead as long as its controller has seven or more cards in their graveyard.| Steelgaze Griffin|Throne of Eldraine|65|C|{4}{U}|Creature - Griffin|2|4|Flying$When you draw your second card each turn, Steelgaze Griffin gets +2/+0 until end of turn.| Stolen by the Fae|Throne of Eldraine|66|R|{X}{U}{U}|Sorcery|||Return target creature with converted mana cost X to its owner's hand. You create X 1/1 blue Faerie creature tokens with flying.| @@ -36077,6 +36079,7 @@ Cauldron's Gift|Throne of Eldraine|83|U|{4}{B}|Sorcery|||Adamant — If at least Clackbridge Troll|Throne of Eldraine|84|R|{3}{B}{B}|Creature - Troll|8|8|Trample, haste$When Clackbridge Troll enters the battlefield, target opponent creates three 0/1 white Goat creature tokens.$At the beginning of combat on your turn, any opponent may sacrifice a creature. If a player does, tap Clackbridge Troll, you gain 3 life, and you draw a card.| Epic Downfall|Throne of Eldraine|85|U|{1}{B}|Sorcery|||Exile target creature with converted mana cost 3 or greater.| Eye Collector|Throne of Eldraine|86|C|{B}|Creature - Faerie|1|1|Flying$Whenever Eye Collector deals combat damage to a player, each player puts the top card of their library into their graveyard.| +Festive Funeral|Throne of Eldraine|87|C|{4}{B}|Instant|||Target creature gets -X/-X until end of turn, where X is the number of cards in your graveyard.| Foreboding Fruit|Throne of Eldraine|88|C|{2}{B}|Sorcery|||Target player draws two cards and loses 2 life.$Adamant — If at least three black mana was spent to cast this spell, create a Food token.| Forever Young|Throne of Eldraine|89|C|{1}{B}|Sorcery|||Put any number of target creature cards from your graveyard on top of your library.$Draw a card.| Foulmire Knight|Throne of Eldraine|90|U|{B}|Creature - Zombie Knight|1|1|Deathtouch| @@ -36118,6 +36121,7 @@ Ferocity of the Wilds|Throne of Eldraine|123|U|{2}{R}|Enchantment|||Attacking no Fervent Champion|Throne of Eldraine|124|R|{R}|Creature - Human Knight|1|1|First strike, haste$Whenever Fervent Champion attacks, another target attacking Knight you control gets +1/+0 until end of turn.$Equip abilities you activate that target Fervent Champion cost {3} less to activate.| Fires of Invention|Throne of Eldraine|125|R|{3}{R}|Enchantment|||You can cast spells only during your turn and you can cast no more than two spells each turn.$You may cast spells with converted mana cost less than or equal to the number of lands you control without paying their mana costs.| Irencrag Feat|Throne of Eldraine|127|R|{1}{R}{R}{R}|Sorcery|||Add seven {R}. You can cast only one more spell this turn.| +Irencrag Pyromancer|Throne of Eldraine|128|R|{2}{R}|Creature - Human Wizard|0|4|Whenever you draw your second card each turn, Irencrag Pyromancer deals 3 damage to any target.| Joust|Throne of Eldraine|129|U|{1}{R}|Sorcery|||Choose target creature you control and target creature you don't control. The creature you control gets +2/+1 until end of turn if it's a Knight. Then those creatures fight each other.| Mad Ratter|Throne of Eldraine|130|U|{3}{R}|Creature - Goblin|1|2|Whenever you draw your second card each turn, create two 1/1 black Rat creature tokens.| Haggle|Throne of Eldraine|131|C|{R}|Instant - Adventure|2|3|You may discard a card. If you do, draw a card.| @@ -36164,6 +36168,7 @@ Once and Future|Throne of Eldraine|168|U|{3}{G}|Instant|||Return target card fro Once Upon a Time|Throne of Eldraine|169|R|{1}{G}|Instant|||If this spell is the first spell you've cast this game, you may cast it without paying its mana cost.$Look at the top five cards of your library. You may reveal a creature or land card from among them and put it into your hand. Put the rest on the bottom of your library in a random order.| Outmuscle|Throne of Eldraine|170|C|{3}{G}|Sorcery|||Put a +1/+1 counter on target creature you control, then it fights target creature you don't control.$Adamant — If at least three green mana was spent to cast this spell, the creature you control gains indestructible until end of turn.| Questing Beast|Throne of Eldraine|171|M|{2}{G}{G}|Legendary Creature - Beast|4|4|Vigilance, deathtouch, haste$Questing Beast can't be blocked by creatures with power 2 or less.$Combat damage that would be dealt by creatures you control can't be prevented.$Whenever Questing Beast deals combat damage to an opponent, it deals that much damage to target planeswalker that player controls.| +Return of the Wildspeaker|Throne of Eldraine|172|R|{4}{G}|Instant|||Choose one —$• Draw cards equal to the greatest power among non-Human creatures you control.$• Non-Human creatures you control get +3/+3 until end of turn.| Return to Nature|Throne of Eldraine|173|C|{1}{G}|Instant|||Choose one —$• Destroy target artifact.$• Destroy target enchantment.$• Exile target card from a graveyard.| Rosethorn Acolyte|Throne of Eldraine|174|C|{2}{G}|Creature - Elf Druid|2|3|{T}: Add one mana of any color.| Seasonal Ritual|Throne of Eldraine|174|C|{G}|Sorcery - Adventure|2|3|Add one mana of any color.| @@ -36207,6 +36212,7 @@ Loch Dragon|Throne of Eldraine|211|U|{U/R}{U/R}{U/R}{U/R}|Creature - Dragon|3|2| Bring Back|Throne of Eldraine|212|U|{G/W}{G/W}{G/W}{G/W}|Sorcery - Adventure|2|2|Create two 1/1 white Human creature tokens.| Oakhame Ranger|Throne of Eldraine|212|U|{G/W}{G/W}{G/W}{G/W}|Creature - Elf Knight|2|2|{T}: Creatures you control get +1/+1 until end of turn.| Rampart Smasher|Throne of Eldraine|213|U|{R/G}{R/G}{R/G}{R/G}|Creature - Giant|5|5|Rampart Smasher can't be blocked by Knights or Walls.| +Resolute Rider|Throne of Eldraine|214|U|{W/B}{W/B}{W/B}{W/B}|Creature - Human Knight|||{W/B}{W/B}: Resolute Rider gains lifelink until end of turn.${W/B}{W/B}{W/B}: Resolute Rider gains indestructible until end of turn.| Thunderous Snapper|Throne of Eldraine|215|U|{G/U}{G/U}{G/U}{G/U}|Creature - Turtle Hydra|4|4|Whenever you cast a spell with converted mana cost 5 or greater, draw a card.| Clockwork Servant|Throne of Eldraine|216|U|{3}|Artifact Creature - Gnome|2|3|Adamant — When Clockwork Servant enters the battlefield, if at least three mana of the same color was spent to cast it, draw a card.| Enchanted Carriage|Throne of Eldraine|218|U|{5}|Artifact - Vehicle|4|4|When Enchanted Carriage enters the battlefield, create two 1/1 white Mouse creature tokens.$Crew 2| @@ -36231,6 +36237,7 @@ Castle Locthwain|Throne of Eldraine|241|R||Land|||Castle Locthwain enters the ba Castle Vantress|Throne of Eldraine|242|R||Land|||Castle Vantress enters the battlefield tapped unless you control an Island.${T}: Add {U}.${2}{U}{U}, {T}: Scry 2.| Fabled Passage|Throne of Eldraine|244|R||Land|||{T}, Sacrifice Fabled Passage: Search your library for a basic land card, put it onto the battlefield tapped, then shuffle your library. Then if you control four or more lands, untap that land.| Idyllic Grange|Throne of Eldraine|246|C||Land - Plains|||({T}: Add {W}.)$Idyllic Grange enters the battlefield tapped unless you control three or more other Plains.$When Idyllic Grange enters the battlefield untapped, put a +1/+1 counter on target creature you control.| +Mystic Sanctuary|Throne of Eldraine|247|C||Land - Island|||({T}: Add {U}.)$Mystic Sanctuary enters the battlefield tapped unless you control three or more other Islands.$When Mystic Sanctuary enters the battlefield untapped, you may put target instant or sorcery card from your graveyard on top of your library.| Tournament Grounds|Throne of Eldraine|248|U||Land|||{T}: Add {C}.${T}: Add {R}, {W}, or {B}. Spend this mana only to cast a Knight or Equipment spell.| Witch's Cottage|Throne of Eldraine|249|C||Land - Swamp|||({T}: Add {B}.)$Witch's Cottage enters the battlefield tapped unless you control three or more other Swamps.$When Witch's Cottage enters the battlefield untapped, you may put target creature card from your graveyard on top of your library.| Kenrith, the Returned King|Throne of Eldraine|303|M|{4}{W}|Legendary Creature - Human Noble|5|5|{R}: All creatures gain trample and haste until end of turn.${1}{G}: Put a +1/+1 counter on target creature.${2}{W}: Target player gains 5 life.${3}{U}: Target player draws a card.${4}{B}: Put target creature card from a graveyard onto the battlefield under its owner's control.| From dd93f29e46e7b7e86d4d9b974c379ceb8e1321b4 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 19 Sep 2019 17:42:04 -0400 Subject: [PATCH 218/373] Implemented Happily Ever After --- .../src/mage/cards/h/HappilyEverAfter.java | 125 ++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 126 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/h/HappilyEverAfter.java diff --git a/Mage.Sets/src/mage/cards/h/HappilyEverAfter.java b/Mage.Sets/src/mage/cards/h/HappilyEverAfter.java new file mode 100644 index 0000000000..c1f1b476a1 --- /dev/null +++ b/Mage.Sets/src/mage/cards/h/HappilyEverAfter.java @@ -0,0 +1,125 @@ +package mage.cards.h; + +import mage.ObjectColor; +import mage.abilities.Ability; +import mage.abilities.common.BeginningOfUpkeepTriggeredAbility; +import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.condition.Condition; +import mage.abilities.decorator.ConditionalInterveningIfTriggeredAbility; +import mage.abilities.effects.OneShotEffect; +import mage.abilities.effects.common.WinGameSourceControllerEffect; +import mage.cards.Card; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Outcome; +import mage.constants.TargetController; +import mage.game.Game; +import mage.game.permanent.Permanent; +import mage.players.Player; + +import java.util.Collection; +import java.util.EnumSet; +import java.util.Objects; +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class HappilyEverAfter extends CardImpl { + + public HappilyEverAfter(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ENCHANTMENT}, "{2}{W}"); + + // When Happily Ever After enters the battlefield, each player gains 5 life and draws a card. + this.addAbility(new EntersBattlefieldTriggeredAbility(new HappilyEverAfterEffect())); + + // At the beginning of your upkeep, if there are five colors among permanents you control, there are six or more card types among permanents you control and/or cards in your graveyard, and your life total is greater than or equal to your starting life total, you win the game. + this.addAbility(new ConditionalInterveningIfTriggeredAbility( + new BeginningOfUpkeepTriggeredAbility( + new WinGameSourceControllerEffect(), TargetController.YOU, false + ), HappilyEverAfterCondition.instance, "At the beginning of your upkeep, " + + "if there are five colors among permanents you control, there are six or more card types " + + "among permanents you control and/or cards in your graveyard, and your life total is " + + "greater than or equal to your starting life total, you win the game." + )); + } + + private HappilyEverAfter(final HappilyEverAfter card) { + super(card); + } + + @Override + public HappilyEverAfter copy() { + return new HappilyEverAfter(this); + } +} + +class HappilyEverAfterEffect extends OneShotEffect { + + HappilyEverAfterEffect() { + super(Outcome.GainLife); + staticText = "each player gains 5 life and draws a card"; + } + + private HappilyEverAfterEffect(final HappilyEverAfterEffect effect) { + super(effect); + } + + @Override + public HappilyEverAfterEffect copy() { + return new HappilyEverAfterEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + game.getState() + .getPlayersInRange(source.getControllerId(), game) + .stream() + .map(game::getPlayer) + .filter(Objects::nonNull) + .forEachOrdered(player -> { + player.gainLife(5, game, source); + player.drawCards(1, game); + }); + return true; + } +} + +enum HappilyEverAfterCondition implements Condition { + instance; + + @Override + public boolean apply(Game game, Ability source) { + Player player = game.getPlayer(source.getControllerId()); + if (player == null || player.getLife() < game.getLife()) { + return false; + } + ObjectColor color = new ObjectColor(""); + game.getBattlefield() + .getAllActivePermanents(source.getControllerId()) + .stream() + .map(permanent -> permanent.getColor(game)) + .forEach(color::addColor); + if (color.getColorCount() < 5) { + return false; + } + EnumSet cardTypeEnumSet = EnumSet.noneOf(CardType.class); + game.getBattlefield() + .getAllActivePermanents(source.getControllerId()) + .stream() + .map(Permanent::getCardType) + .flatMap(Collection::stream) + .forEach(cardTypeEnumSet::add); + if (cardTypeEnumSet.size() >= 6) { + return true; + } + player.getGraveyard() + .getCards(game) + .stream() + .map(Card::getCardType) + .flatMap(Collection::stream) + .forEach(cardTypeEnumSet::add); + return cardTypeEnumSet.size() >= 6; + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 4690f59840..7aec26915e 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -118,6 +118,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Gluttonous Troll", 327, Rarity.RARE, mage.cards.g.GluttonousTroll.class)); cards.add(new SetCardInfo("Golden Egg", 220, Rarity.COMMON, mage.cards.g.GoldenEgg.class)); cards.add(new SetCardInfo("Grumgully, the Generous", 192, Rarity.UNCOMMON, mage.cards.g.GrumgullyTheGenerous.class)); + cards.add(new SetCardInfo("Happily Ever After", 16, Rarity.RARE, mage.cards.h.HappilyEverAfter.class)); cards.add(new SetCardInfo("Harmonious Archon", 17, Rarity.MYTHIC, mage.cards.h.HarmoniousArchon.class)); cards.add(new SetCardInfo("Henge Walker", 221, Rarity.COMMON, mage.cards.h.HengeWalker.class)); cards.add(new SetCardInfo("Heraldic Banner", 222, Rarity.UNCOMMON, mage.cards.h.HeraldicBanner.class)); From faa51b56e03879312eb8886f5cefcc3becd07f69 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 19 Sep 2019 17:45:40 -0400 Subject: [PATCH 219/373] Implemented Mystic Sanctuary --- .../src/mage/cards/m/MysticSanctuary.java | 75 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 76 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/m/MysticSanctuary.java diff --git a/Mage.Sets/src/mage/cards/m/MysticSanctuary.java b/Mage.Sets/src/mage/cards/m/MysticSanctuary.java new file mode 100644 index 0000000000..b01e015bd5 --- /dev/null +++ b/Mage.Sets/src/mage/cards/m/MysticSanctuary.java @@ -0,0 +1,75 @@ +package mage.cards.m; + +import mage.abilities.Ability; +import mage.abilities.common.EntersBattlefieldAbility; +import mage.abilities.common.EntersBattlefieldUntappedTriggeredAbility; +import mage.abilities.condition.Condition; +import mage.abilities.condition.common.PermanentsOnTheBattlefieldCondition; +import mage.abilities.decorator.ConditionalOneShotEffect; +import mage.abilities.effects.common.PutOnLibraryTargetEffect; +import mage.abilities.effects.common.TapSourceEffect; +import mage.abilities.mana.BlueManaAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.ComparisonType; +import mage.constants.SubType; +import mage.filter.FilterCard; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterControlledPermanent; +import mage.filter.common.FilterInstantOrSorceryCard; +import mage.filter.predicate.permanent.AnotherPredicate; +import mage.target.common.TargetCardInYourGraveyard; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class MysticSanctuary extends CardImpl { + + private static final FilterPermanent filter + = new FilterControlledPermanent(SubType.ISLAND); + private static final FilterCard filter2 + = new FilterInstantOrSorceryCard("instant or sorcery card from your graveyard"); + + static { + filter.add(AnotherPredicate.instance); + } + + private static final Condition condition + = new PermanentsOnTheBattlefieldCondition(filter, ComparisonType.FEWER_THAN, 3); + + public MysticSanctuary(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.LAND}, ""); + + this.subtype.add(SubType.ISLAND); + + // ({T}: Add {U}.) + this.addAbility(new BlueManaAbility()); + + // Mystic Sanctuary enters the battlefield tapped unless you control three or more other Islands. + this.addAbility(new EntersBattlefieldAbility( + new ConditionalOneShotEffect(new TapSourceEffect(), condition), + "tapped unless you control three or more other Islands" + )); + + // When Mystic Sanctuary enters the battlefield untapped, you may put target instant or sorcery card from your graveyard on top of your library. + Ability ability = new EntersBattlefieldUntappedTriggeredAbility( + new PutOnLibraryTargetEffect(true) + .setText("put target instant or sorcery card from your graveyard on top of your library"), + true + ); + ability.addTarget(new TargetCardInYourGraveyard(filter2)); + this.addAbility(ability); + } + + private MysticSanctuary(final MysticSanctuary card) { + super(card); + } + + @Override + public MysticSanctuary copy() { + return new MysticSanctuary(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 7aec26915e..dc75989bb3 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -155,6 +155,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Mirrormade", 55, Rarity.RARE, mage.cards.m.Mirrormade.class)); cards.add(new SetCardInfo("Mistford River Turtle", 56, Rarity.COMMON, mage.cards.m.MistfordRiverTurtle.class)); cards.add(new SetCardInfo("Murderous Rider", 97, Rarity.RARE, mage.cards.m.MurderousRider.class)); + cards.add(new SetCardInfo("Mystic Sanctuary", 247, Rarity.COMMON, mage.cards.m.MysticSanctuary.class)); cards.add(new SetCardInfo("Mystical Dispute", 58, Rarity.UNCOMMON, mage.cards.m.MysticalDispute.class)); cards.add(new SetCardInfo("Oakhame Adversary", 167, Rarity.UNCOMMON, mage.cards.o.OakhameAdversary.class)); cards.add(new SetCardInfo("Oakhame Ranger", 212, Rarity.UNCOMMON, mage.cards.o.OakhameRanger.class)); From ed6fff72cd5add749386fa665c2cfcd1b6cfdb31 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 19 Sep 2019 17:49:18 -0400 Subject: [PATCH 220/373] Implemented Resolute Rider --- Mage.Sets/src/mage/cards/r/ResoluteRider.java | 46 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 47 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/r/ResoluteRider.java diff --git a/Mage.Sets/src/mage/cards/r/ResoluteRider.java b/Mage.Sets/src/mage/cards/r/ResoluteRider.java new file mode 100644 index 0000000000..60f4f1c8ed --- /dev/null +++ b/Mage.Sets/src/mage/cards/r/ResoluteRider.java @@ -0,0 +1,46 @@ +package mage.cards.r; + +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.costs.mana.ManaCostsImpl; +import mage.abilities.effects.common.continuous.GainAbilitySourceEffect; +import mage.abilities.keyword.IndestructibleAbility; +import mage.abilities.keyword.LifelinkAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class ResoluteRider extends CardImpl { + + public ResoluteRider(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{W/B}{W/B}{W/B}{W/B}"); + + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.KNIGHT); + + // {W/B}{W/B}: Resolute Rider gains lifelink until end of turn. + this.addAbility(new SimpleActivatedAbility(new GainAbilitySourceEffect( + LifelinkAbility.getInstance(), Duration.EndOfTurn + ), new ManaCostsImpl("{W/B}{W/B}"))); + + // {W/B}{W/B}{W/B}: Resolute Rider gains indestructible until end of turn. + this.addAbility(new SimpleActivatedAbility(new GainAbilitySourceEffect( + IndestructibleAbility.getInstance(), Duration.EndOfTurn + ), new ManaCostsImpl("{W/B}{W/B}{W/B}"))); + } + + private ResoluteRider(final ResoluteRider card) { + super(card); + } + + @Override + public ResoluteRider copy() { + return new ResoluteRider(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index dc75989bb3..f60280b905 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -182,6 +182,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Reave Soul", 103, Rarity.COMMON, mage.cards.r.ReaveSoul.class)); cards.add(new SetCardInfo("Redcap Melee", 135, Rarity.UNCOMMON, mage.cards.r.RedcapMelee.class)); cards.add(new SetCardInfo("Redcap Raiders", 136, Rarity.COMMON, mage.cards.r.RedcapRaiders.class)); + cards.add(new SetCardInfo("Resolute Rider", 214, Rarity.UNCOMMON, mage.cards.r.ResoluteRider.class)); cards.add(new SetCardInfo("Return to Nature", 173, Rarity.COMMON, mage.cards.r.ReturnToNature.class)); cards.add(new SetCardInfo("Revenge of Ravens", 104, Rarity.UNCOMMON, mage.cards.r.RevengeOfRavens.class)); cards.add(new SetCardInfo("Righteousness", 27, Rarity.UNCOMMON, mage.cards.r.Righteousness.class)); From 1193763c8f8f96f2360a5be4d301c64882d62172 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 19 Sep 2019 19:40:13 -0400 Subject: [PATCH 221/373] Implemented Thrill of Possibility --- .../src/mage/cards/t/ThrillOfPossibility.java | 35 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + Utils/mtg-cards-data.txt | 1 + 3 files changed, 37 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/t/ThrillOfPossibility.java diff --git a/Mage.Sets/src/mage/cards/t/ThrillOfPossibility.java b/Mage.Sets/src/mage/cards/t/ThrillOfPossibility.java new file mode 100644 index 0000000000..6c66625447 --- /dev/null +++ b/Mage.Sets/src/mage/cards/t/ThrillOfPossibility.java @@ -0,0 +1,35 @@ +package mage.cards.t; + +import mage.abilities.costs.common.DiscardTargetCost; +import mage.abilities.effects.common.DrawCardSourceControllerEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.target.common.TargetCardInHand; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class ThrillOfPossibility extends CardImpl { + + public ThrillOfPossibility(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.INSTANT}, "{1}{R}"); + + // As an additional cost to cast this spell, discard a card. + this.getSpellAbility().addCost(new DiscardTargetCost(new TargetCardInHand())); + + // Draw two cards. + this.getSpellAbility().addEffect(new DrawCardSourceControllerEffect(2)); + } + + private ThrillOfPossibility(final ThrillOfPossibility card) { + super(card); + } + + @Override + public ThrillOfPossibility copy() { + return new ThrillOfPossibility(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index f60280b905..ddace38543 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -234,6 +234,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("The Royal Scions", 199, Rarity.MYTHIC, mage.cards.t.TheRoyalScions.class)); cards.add(new SetCardInfo("Thorn Mammoth", 323, Rarity.RARE, mage.cards.t.ThornMammoth.class)); cards.add(new SetCardInfo("Thornwood Falls", 313, Rarity.COMMON, mage.cards.t.ThornwoodFalls.class)); + cards.add(new SetCardInfo("Thrill of Possibility", 146, Rarity.COMMON, mage.cards.t.ThrillOfPossibility.class)); cards.add(new SetCardInfo("Thunderous Snapper", 215, Rarity.UNCOMMON, mage.cards.t.ThunderousSnapper.class)); cards.add(new SetCardInfo("Tome Raider", 68, Rarity.COMMON, mage.cards.t.TomeRaider.class)); cards.add(new SetCardInfo("Tome of Legends", 332, Rarity.RARE, mage.cards.t.TomeOfLegends.class)); diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index 8eb503f3fc..6b54ba777f 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -36139,6 +36139,7 @@ Skullknocker Ogre|Throne of Eldraine|142|U|{3}{R}|Creature - Ogre|4|3|Whenever S Slaying Fire|Throne of Eldraine|143|U|{2}{R}|Instant|||Slaying Fire deals 3 damage to any target.$Adamant — If at least three red mana was spent to cast this spell, it deals 4 damage instead.| Sundering Stroke|Throne of Eldraine|144|R|{6}{R}|Sorcery|||Sundering Stroke deals 7 damage divided as you choose among one, two, or three targets. If at least seven red mana was spent to cast this spell, instead Sundering Stroke deals 7 damage to each of those permanents and/or players.| Syr Carah, the Bold|Throne of Eldraine|145|U|{3}{R}{R}|Legendary Creature - Human Knight|3|3|When Syr Carah, the Bold or an instant or sorcery spell you control deals damage to a player, exile the top card of your library. You may play that card this turn.${T}: Syr Carah deals 1 damage to any target.| +Thrill of Possibility|Throne of Eldraine|146|C|{1}{R}|Instant|||As an additional cost to cast this spell, discard a card.$Draw two cards.| Torbran, Thane of Red Fell|Throne of Eldraine|147|R|{1}{R}{R}{R}|Legendary Creature - Dwarf Noble|2|4|If a red source you control would deal damage to an opponent or a permanent an opponent controls, it deals that much damage plus 2 instead.| Weaselback Redcap|Throne of Eldraine|148|C|{R}|Creature - Goblin Knight|1|1|{1}{R}: Weaselback Redcap gets +2/+0 until end of turn.| Beanstalk Giant|Throne of Eldraine|149|U|{6}{G}|Creature - Giant|*|*|Beanstalk Giant's power and toughness are each equal to the number of lands you control.| From 069751773c92e1fd9f428246c0b88de2c3e05185 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 19 Sep 2019 19:44:27 -0400 Subject: [PATCH 222/373] Implemented Irencrag Pyromancer --- .../src/mage/cards/i/IrencragPyromancer.java | 42 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 43 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/i/IrencragPyromancer.java diff --git a/Mage.Sets/src/mage/cards/i/IrencragPyromancer.java b/Mage.Sets/src/mage/cards/i/IrencragPyromancer.java new file mode 100644 index 0000000000..15265ab317 --- /dev/null +++ b/Mage.Sets/src/mage/cards/i/IrencragPyromancer.java @@ -0,0 +1,42 @@ +package mage.cards.i; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.DrawSecondCardTriggeredAbility; +import mage.abilities.effects.common.DamageTargetEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.target.common.TargetAnyTarget; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class IrencragPyromancer extends CardImpl { + + public IrencragPyromancer(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{2}{R}"); + + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.WIZARD); + this.power = new MageInt(0); + this.toughness = new MageInt(4); + + // Whenever you draw your second card each turn, Irencrag Pyromancer deals 3 damage to any target. + Ability ability = new DrawSecondCardTriggeredAbility(new DamageTargetEffect(3), false); + ability.addTarget(new TargetAnyTarget()); + this.addAbility(ability); + } + + private IrencragPyromancer(final IrencragPyromancer card) { + super(card); + } + + @Override + public IrencragPyromancer copy() { + return new IrencragPyromancer(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index ddace38543..cb1df86b43 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -130,6 +130,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Inspiring Veteran", 194, Rarity.UNCOMMON, mage.cards.i.InspiringVeteran.class)); cards.add(new SetCardInfo("Into the Story", 50, Rarity.UNCOMMON, mage.cards.i.IntoTheStory.class)); cards.add(new SetCardInfo("Irencrag Feat", 127, Rarity.RARE, mage.cards.i.IrencragFeat.class)); + cards.add(new SetCardInfo("Irencrag Pyromancer", 128, Rarity.RARE, mage.cards.i.IrencragPyromancer.class)); cards.add(new SetCardInfo("Joust", 129, Rarity.UNCOMMON, mage.cards.j.Joust.class)); cards.add(new SetCardInfo("Jousting Dummy", 224, Rarity.COMMON, mage.cards.j.JoustingDummy.class)); cards.add(new SetCardInfo("Keeper of Fables", 163, Rarity.UNCOMMON, mage.cards.k.KeeperOfFables.class)); From ee9b76ab359e1bcd35c29af7f268d60eecfad83c Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 19 Sep 2019 19:55:25 -0400 Subject: [PATCH 223/373] Implemented Return of the Wildspeaker --- .../mage/cards/r/ReturnOfTheWildspeaker.java | 84 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 85 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/r/ReturnOfTheWildspeaker.java diff --git a/Mage.Sets/src/mage/cards/r/ReturnOfTheWildspeaker.java b/Mage.Sets/src/mage/cards/r/ReturnOfTheWildspeaker.java new file mode 100644 index 0000000000..93e95bd7eb --- /dev/null +++ b/Mage.Sets/src/mage/cards/r/ReturnOfTheWildspeaker.java @@ -0,0 +1,84 @@ +package mage.cards.r; + +import mage.MageInt; +import mage.MageObject; +import mage.abilities.Ability; +import mage.abilities.Mode; +import mage.abilities.dynamicvalue.DynamicValue; +import mage.abilities.effects.Effect; +import mage.abilities.effects.common.DrawCardSourceControllerEffect; +import mage.abilities.effects.common.continuous.BoostControlledEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; +import mage.filter.common.FilterCreaturePermanent; +import mage.filter.predicate.Predicates; +import mage.filter.predicate.mageobject.SubtypePredicate; +import mage.game.Game; +import mage.game.permanent.Permanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class ReturnOfTheWildspeaker extends CardImpl { + + private static final FilterCreaturePermanent filter = new FilterCreaturePermanent("non-Human creatures"); + + static { + filter.add(Predicates.not(new SubtypePredicate(SubType.HUMAN))); + } + + public ReturnOfTheWildspeaker(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.INSTANT}, "{4}{G}"); + + // Choose one — + // • Draw cards equal to the greatest power among non-Human creatures you control. + this.getSpellAbility().addEffect(new DrawCardSourceControllerEffect(ReturnOfTheWildspeakerValue.instance) + .setText("draw cards equal to the greatest power among non-Human creatures you control")); + + // • Non-Human creatures you control get +3/+3 until end of turn. + this.getSpellAbility().addMode(new Mode( + new BoostControlledEffect(3, 3, Duration.EndOfTurn, filter) + )); + } + + private ReturnOfTheWildspeaker(final ReturnOfTheWildspeaker card) { + super(card); + } + + @Override + public ReturnOfTheWildspeaker copy() { + return new ReturnOfTheWildspeaker(this); + } +} + +enum ReturnOfTheWildspeakerValue implements DynamicValue { + instance; + + @Override + public int calculate(Game game, Ability sourceAbility, Effect effect) { + return game.getBattlefield() + .getAllActivePermanents(sourceAbility.getControllerId()) + .stream() + .filter(Permanent::isCreature) + .filter(permanent -> !permanent.hasSubtype(SubType.HUMAN, game)) + .map(MageObject::getPower) + .mapToInt(MageInt::getValue) + .max() + .getAsInt(); + } + + @Override + public DynamicValue copy() { + return instance; + } + + @Override + public String getMessage() { + return ""; + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index cb1df86b43..e04af00de4 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -184,6 +184,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Redcap Melee", 135, Rarity.UNCOMMON, mage.cards.r.RedcapMelee.class)); cards.add(new SetCardInfo("Redcap Raiders", 136, Rarity.COMMON, mage.cards.r.RedcapRaiders.class)); cards.add(new SetCardInfo("Resolute Rider", 214, Rarity.UNCOMMON, mage.cards.r.ResoluteRider.class)); + cards.add(new SetCardInfo("Return of the Wildspeaker", 172, Rarity.RARE, mage.cards.r.ReturnOfTheWildspeaker.class)); cards.add(new SetCardInfo("Return to Nature", 173, Rarity.COMMON, mage.cards.r.ReturnToNature.class)); cards.add(new SetCardInfo("Revenge of Ravens", 104, Rarity.UNCOMMON, mage.cards.r.RevengeOfRavens.class)); cards.add(new SetCardInfo("Righteousness", 27, Rarity.UNCOMMON, mage.cards.r.Righteousness.class)); From 788a879c7f6ff9f93f32bd0a0dd71ea603883ea0 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 19 Sep 2019 20:04:53 -0400 Subject: [PATCH 224/373] Implemented Festive Funeral --- .../src/mage/cards/f/FestiveFuneral.java | 40 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + .../CardsInControllerGraveyardCount.java | 3 +- 3 files changed, 43 insertions(+), 1 deletion(-) create mode 100644 Mage.Sets/src/mage/cards/f/FestiveFuneral.java diff --git a/Mage.Sets/src/mage/cards/f/FestiveFuneral.java b/Mage.Sets/src/mage/cards/f/FestiveFuneral.java new file mode 100644 index 0000000000..087e7d73d4 --- /dev/null +++ b/Mage.Sets/src/mage/cards/f/FestiveFuneral.java @@ -0,0 +1,40 @@ +package mage.cards.f; + +import mage.abilities.dynamicvalue.DynamicValue; +import mage.abilities.dynamicvalue.common.CardsInControllerGraveyardCount; +import mage.abilities.effects.common.continuous.BoostTargetEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.filter.StaticFilters; +import mage.target.common.TargetCreaturePermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class FestiveFuneral extends CardImpl { + + private static final DynamicValue xValue = new CardsInControllerGraveyardCount(StaticFilters.FILTER_CARD, -1); + + public FestiveFuneral(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.INSTANT}, "{4}{B}"); + + // Target creature gets -X/-X until end of turn, where X is the number of cards in your graveyard. + this.getSpellAbility().addEffect(new BoostTargetEffect( + xValue, xValue, Duration.EndOfTurn, true + ).setText("target creature gets -X/-X until end of turn, where X is the number of cards in your graveyard")); + this.getSpellAbility().addTarget(new TargetCreaturePermanent()); + } + + private FestiveFuneral(final FestiveFuneral card) { + super(card); + } + + @Override + public FestiveFuneral copy() { + return new FestiveFuneral(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index e04af00de4..f24c7e340e 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -93,6 +93,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Fell the Pheasant", 153, Rarity.COMMON, mage.cards.f.FellThePheasant.class)); cards.add(new SetCardInfo("Ferocity of the Wilds", 123, Rarity.UNCOMMON, mage.cards.f.FerocityOfTheWilds.class)); cards.add(new SetCardInfo("Fervent Champion", 124, Rarity.RARE, mage.cards.f.FerventChampion.class)); + cards.add(new SetCardInfo("Festive Funeral", 87, Rarity.COMMON, mage.cards.f.FestiveFuneral.class)); cards.add(new SetCardInfo("Fierce Witchstalker", 154, Rarity.COMMON, mage.cards.f.FierceWitchstalker.class)); cards.add(new SetCardInfo("Fireborn Knight", 210, Rarity.UNCOMMON, mage.cards.f.FirebornKnight.class)); cards.add(new SetCardInfo("Fires of Invention", 125, Rarity.RARE, mage.cards.f.FiresOfInvention.class)); diff --git a/Mage/src/main/java/mage/abilities/dynamicvalue/common/CardsInControllerGraveyardCount.java b/Mage/src/main/java/mage/abilities/dynamicvalue/common/CardsInControllerGraveyardCount.java index c69bea308f..3242e4d845 100644 --- a/Mage/src/main/java/mage/abilities/dynamicvalue/common/CardsInControllerGraveyardCount.java +++ b/Mage/src/main/java/mage/abilities/dynamicvalue/common/CardsInControllerGraveyardCount.java @@ -4,6 +4,7 @@ import mage.abilities.Ability; import mage.abilities.dynamicvalue.DynamicValue; import mage.abilities.effects.Effect; import mage.filter.FilterCard; +import mage.filter.StaticFilters; import mage.game.Game; import mage.players.Player; @@ -17,7 +18,7 @@ public class CardsInControllerGraveyardCount implements DynamicValue { private Integer amount; public CardsInControllerGraveyardCount() { - this(new FilterCard(), 1); + this(StaticFilters.FILTER_CARD, 1); } public CardsInControllerGraveyardCount(FilterCard filter) { From 77db079fd335c353e91e7a69c12c4d394617d0b1 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 19 Sep 2019 20:15:38 -0400 Subject: [PATCH 225/373] Implemented Fabled Passage --- Mage.Sets/src/mage/cards/f/FabledPassage.java | 90 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 91 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/f/FabledPassage.java diff --git a/Mage.Sets/src/mage/cards/f/FabledPassage.java b/Mage.Sets/src/mage/cards/f/FabledPassage.java new file mode 100644 index 0000000000..a1cdd2098b --- /dev/null +++ b/Mage.Sets/src/mage/cards/f/FabledPassage.java @@ -0,0 +1,90 @@ +package mage.cards.f; + +import mage.abilities.Ability; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.costs.common.SacrificeSourceCost; +import mage.abilities.costs.common.TapSourceCost; +import mage.abilities.effects.OneShotEffect; +import mage.cards.Card; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Outcome; +import mage.constants.Zone; +import mage.filter.StaticFilters; +import mage.game.Game; +import mage.game.permanent.Permanent; +import mage.players.Player; +import mage.target.common.TargetCardInLibrary; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class FabledPassage extends CardImpl { + + public FabledPassage(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.LAND}, ""); + + // {T}, Sacrifice Fabled Passage: Search your library for a basic land card, put it onto the battlefield tapped, then shuffle your library. Then if you control four or more lands, untap that land. + Ability ability = new SimpleActivatedAbility(new FabledPassageEffect(), new TapSourceCost()); + ability.addCost(new SacrificeSourceCost()); + this.addAbility(ability); + } + + private FabledPassage(final FabledPassage card) { + super(card); + } + + @Override + public FabledPassage copy() { + return new FabledPassage(this); + } +} + +class FabledPassageEffect extends OneShotEffect { + + FabledPassageEffect() { + super(Outcome.Benefit); + staticText = "Search your library for a basic land card, put it onto the battlefield tapped, " + + "then shuffle your library. Then if you control four or more lands, untap that land."; + } + + private FabledPassageEffect(final FabledPassageEffect effect) { + super(effect); + } + + @Override + public FabledPassageEffect copy() { + return new FabledPassageEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + Player player = game.getPlayer(source.getControllerId()); + if (player == null) { + return false; + } + TargetCardInLibrary target = new TargetCardInLibrary(StaticFilters.FILTER_CARD_BASIC_LAND_A); + if (!player.searchLibrary(target, source, game)) { + return false; + } + player.shuffleLibrary(source, game); + Card card = game.getCard(target.getFirstTarget()); + if (card == null) { + return false; + } + if (!player.moveCards(card, Zone.BATTLEFIELD, source, game)) { + return false; + } + if (game.getBattlefield().countAll(StaticFilters.FILTER_LAND, source.getControllerId(), game) < 4) { + return true; + } + Permanent permanent = game.getPermanent(card.getId()); + if (permanent == null) { + return false; + } + return permanent.untap(game); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index f24c7e340e..53e8e666f5 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -84,6 +84,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Epic Downfall", 85, Rarity.UNCOMMON, mage.cards.e.EpicDownfall.class)); cards.add(new SetCardInfo("Escape to the Wilds", 189, Rarity.RARE, mage.cards.e.EscapeToTheWilds.class)); cards.add(new SetCardInfo("Eye Collector", 86, Rarity.COMMON, mage.cards.e.EyeCollector.class)); + cards.add(new SetCardInfo("Fabled Passage", 244, Rarity.RARE, mage.cards.f.FabledPassage.class)); cards.add(new SetCardInfo("Fae of Wishes", 44, Rarity.RARE, mage.cards.f.FaeOfWishes.class)); cards.add(new SetCardInfo("Faeburrow Elder", 190, Rarity.RARE, mage.cards.f.FaeburrowElder.class)); cards.add(new SetCardInfo("Faerie Formation", 316, Rarity.RARE, mage.cards.f.FaerieFormation.class)); From 6dc6a1c9bc083cfa9b41880afe343cf0f05e7ede Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 19 Sep 2019 20:28:58 -0400 Subject: [PATCH 226/373] Implemented So Tiny --- Mage.Sets/src/mage/cards/s/SoTiny.java | 88 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 89 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/s/SoTiny.java diff --git a/Mage.Sets/src/mage/cards/s/SoTiny.java b/Mage.Sets/src/mage/cards/s/SoTiny.java new file mode 100644 index 0000000000..6b41d69da8 --- /dev/null +++ b/Mage.Sets/src/mage/cards/s/SoTiny.java @@ -0,0 +1,88 @@ +package mage.cards.s; + +import mage.abilities.Ability; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.dynamicvalue.DynamicValue; +import mage.abilities.dynamicvalue.common.StaticValue; +import mage.abilities.effects.Effect; +import mage.abilities.effects.common.AttachEffect; +import mage.abilities.effects.common.continuous.BoostEnchantedEffect; +import mage.abilities.keyword.EnchantAbility; +import mage.abilities.keyword.FlashAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Outcome; +import mage.constants.SubType; +import mage.game.Game; +import mage.game.permanent.Permanent; +import mage.players.Player; +import mage.target.TargetPermanent; +import mage.target.common.TargetCreaturePermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class SoTiny extends CardImpl { + + public SoTiny(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ENCHANTMENT}, "{U}"); + + this.subtype.add(SubType.AURA); + + // Flash + this.addAbility(FlashAbility.getInstance()); + + // Enchant creature + TargetPermanent auraTarget = new TargetCreaturePermanent(); + this.getSpellAbility().addTarget(auraTarget); + this.getSpellAbility().addEffect(new AttachEffect(Outcome.BoostCreature)); + Ability ability = new EnchantAbility(auraTarget.getTargetName()); + this.addAbility(ability); + + // Enchanted creature gets -2/-0. It gets -6/-0 instead as long as its controller has seven or more cards in their graveyard. + this.addAbility(new SimpleStaticAbility( + new BoostEnchantedEffect(SoTinyValue.instance, StaticValue.getZeroValue()) + .setText("enchanted creature gets -2/-0. It gets -6/-0 instead as long as " + + "its controller has seven or more cards in their graveyard") + )); + } + + private SoTiny(final SoTiny card) { + super(card); + } + + @Override + public SoTiny copy() { + return new SoTiny(this); + } +} + +enum SoTinyValue implements DynamicValue { + instance; + + @Override + public int calculate(Game game, Ability sourceAbility, Effect effect) { + Permanent permanent = game.getPermanent(sourceAbility.getSourceId()); + if (permanent == null) { + return -2; + } + Player player = game.getPlayer(game.getControllerId(permanent.getAttachedTo())); + if (player == null || player.getGraveyard().size() < 7) { + return -2; + } + return -6; + } + + @Override + public DynamicValue copy() { + return instance; + } + + @Override + public String getMessage() { + return ""; + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 53e8e666f5..708b0d78aa 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -213,6 +213,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Skullknocker Ogre", 142, Rarity.UNCOMMON, mage.cards.s.SkullknockerOgre.class)); cards.add(new SetCardInfo("Slaying Fire", 143, Rarity.UNCOMMON, mage.cards.s.SlayingFire.class)); cards.add(new SetCardInfo("Smitten Swordmaster", 105, Rarity.COMMON, mage.cards.s.SmittenSwordmaster.class)); + cards.add(new SetCardInfo("So Tiny", 64, Rarity.COMMON, mage.cards.s.SoTiny.class)); cards.add(new SetCardInfo("Sorcerer's Broom", 232, Rarity.UNCOMMON, mage.cards.s.SorcerersBroom.class)); cards.add(new SetCardInfo("Sorcerous Spyglass", 233, Rarity.RARE, mage.cards.s.SorcerousSpyglass.class)); cards.add(new SetCardInfo("Specter's Shriek", 106, Rarity.UNCOMMON, mage.cards.s.SpectersShriek.class)); From 4245c836321980cf21e6d48f8a139c267ee77e76 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 19 Sep 2019 20:43:16 -0400 Subject: [PATCH 227/373] Implemented Mysterious Pathlighter --- .../mage/cards/m/MysteriousPathlighter.java | 95 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 96 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/m/MysteriousPathlighter.java diff --git a/Mage.Sets/src/mage/cards/m/MysteriousPathlighter.java b/Mage.Sets/src/mage/cards/m/MysteriousPathlighter.java new file mode 100644 index 0000000000..49cfff12c0 --- /dev/null +++ b/Mage.Sets/src/mage/cards/m/MysteriousPathlighter.java @@ -0,0 +1,95 @@ +package mage.cards.m; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.effects.ReplacementEffectImpl; +import mage.abilities.keyword.FlyingAbility; +import mage.cards.AdventureCard; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.Outcome; +import mage.constants.SubType; +import mage.counters.CounterType; +import mage.game.Game; +import mage.game.events.EntersTheBattlefieldEvent; +import mage.game.events.GameEvent; +import mage.game.permanent.Permanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class MysteriousPathlighter extends CardImpl { + + public MysteriousPathlighter(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{2}{W}"); + + this.subtype.add(SubType.FAERIE); + this.power = new MageInt(2); + this.toughness = new MageInt(2); + + // Flying + this.addAbility(FlyingAbility.getInstance()); + + // Each creature you control that has an Adventure enters the battlefield with an additional +1/+1 counter on it. + this.addAbility(new SimpleStaticAbility(new MysteriousPathlighterEffect())); + } + + private MysteriousPathlighter(final MysteriousPathlighter card) { + super(card); + } + + @Override + public MysteriousPathlighter copy() { + return new MysteriousPathlighter(this); + } +} + +class MysteriousPathlighterEffect extends ReplacementEffectImpl { + + MysteriousPathlighterEffect() { + super(Duration.WhileOnBattlefield, Outcome.BoostCreature); + this.staticText = "Each creature you control that has an Adventure " + + "enters the battlefield with an additional +1/+1 counter on it"; + } + + private MysteriousPathlighterEffect(MysteriousPathlighterEffect effect) { + super(effect); + } + + @Override + public boolean checksEventType(GameEvent event, Game game) { + return event.getType() == GameEvent.EventType.ENTERS_THE_BATTLEFIELD; + } + + @Override + public boolean applies(GameEvent event, Ability source, Game game) { + Permanent permanent = ((EntersTheBattlefieldEvent) event).getTarget(); + return permanent instanceof AdventureCard + && permanent.isControlledBy(source.getControllerId()) + && permanent.isCreature(); + } + + @Override + public boolean apply(Game game, Ability source) { + return false; + } + + @Override + public boolean replaceEvent(GameEvent event, Ability source, Game game) { + Permanent target = ((EntersTheBattlefieldEvent) event).getTarget(); + if (target != null) { + target.addCounters(CounterType.P1P1.createInstance(), source, game, event.getAppliedEffects()); + } + return false; + } + + @Override + public MysteriousPathlighterEffect copy() { + return new MysteriousPathlighterEffect(this); + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 708b0d78aa..0c05b8d6ce 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -158,6 +158,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Mirrormade", 55, Rarity.RARE, mage.cards.m.Mirrormade.class)); cards.add(new SetCardInfo("Mistford River Turtle", 56, Rarity.COMMON, mage.cards.m.MistfordRiverTurtle.class)); cards.add(new SetCardInfo("Murderous Rider", 97, Rarity.RARE, mage.cards.m.MurderousRider.class)); + cards.add(new SetCardInfo("Mysterious Pathlighter", 22, Rarity.UNCOMMON, mage.cards.m.MysteriousPathlighter.class)); cards.add(new SetCardInfo("Mystic Sanctuary", 247, Rarity.COMMON, mage.cards.m.MysticSanctuary.class)); cards.add(new SetCardInfo("Mystical Dispute", 58, Rarity.UNCOMMON, mage.cards.m.MysticalDispute.class)); cards.add(new SetCardInfo("Oakhame Adversary", 167, Rarity.UNCOMMON, mage.cards.o.OakhameAdversary.class)); From 3b8039b79c3e73552be64c255b1adee08cbf33bc Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 19 Sep 2019 20:46:31 -0400 Subject: [PATCH 228/373] Implemented Sage of the Falls --- .../src/mage/cards/s/SageOfTheFalls.java | 51 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 52 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/s/SageOfTheFalls.java diff --git a/Mage.Sets/src/mage/cards/s/SageOfTheFalls.java b/Mage.Sets/src/mage/cards/s/SageOfTheFalls.java new file mode 100644 index 0000000000..d8acc2ca0a --- /dev/null +++ b/Mage.Sets/src/mage/cards/s/SageOfTheFalls.java @@ -0,0 +1,51 @@ +package mage.cards.s; + +import mage.MageInt; +import mage.abilities.common.EntersBattlefieldControlledTriggeredAbility; +import mage.abilities.effects.common.DrawDiscardControllerEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterCreaturePermanent; +import mage.filter.predicate.Predicates; +import mage.filter.predicate.mageobject.SubtypePredicate; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class SageOfTheFalls extends CardImpl { + + private static final FilterPermanent filter + = new FilterCreaturePermanent("{this} or another non-Human creature"); + + static { + filter.add(Predicates.not(new SubtypePredicate(SubType.HUMAN))); + } + + public SageOfTheFalls(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{4}{U}"); + + this.subtype.add(SubType.MERFOLK); + this.subtype.add(SubType.WIZARD); + this.power = new MageInt(2); + this.toughness = new MageInt(5); + + // Whenever Sage of the Falls or another non-Human creature enters the battlefield under you control, you may draw a card. If you do, discard a card. + this.addAbility(new EntersBattlefieldControlledTriggeredAbility( + new DrawDiscardControllerEffect(1, 1, true), filter + )); + } + + private SageOfTheFalls(final SageOfTheFalls card) { + super(card); + } + + @Override + public SageOfTheFalls copy() { + return new SageOfTheFalls(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 0c05b8d6ce..ff8a6520cc 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -199,6 +199,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Rowan's Stalwarts", 307, Rarity.RARE, mage.cards.r.RowansStalwarts.class)); cards.add(new SetCardInfo("Rowan, Fearless Sparkmage", 304, Rarity.MYTHIC, mage.cards.r.RowanFearlessSparkmage.class)); cards.add(new SetCardInfo("Run Away Together", 62, Rarity.COMMON, mage.cards.r.RunAwayTogether.class)); + cards.add(new SetCardInfo("Sage of the Falls", 63, Rarity.UNCOMMON, mage.cards.s.SageOfTheFalls.class)); cards.add(new SetCardInfo("Savvy Hunter", 200, Rarity.UNCOMMON, mage.cards.s.SavvyHunter.class)); cards.add(new SetCardInfo("Scorching Dragonfire", 139, Rarity.COMMON, mage.cards.s.ScorchingDragonfire.class)); cards.add(new SetCardInfo("Searing Barrage", 140, Rarity.COMMON, mage.cards.s.SearingBarrage.class)); From 538369c248bd3c18af133064ad3be5ad0e5c009d Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 20 Sep 2019 07:38:05 -0400 Subject: [PATCH 229/373] updated ELD spoiler --- Mage.Sets/src/mage/cards/r/ResoluteRider.java | 3 +++ Utils/mtg-cards-data.txt | 4 +++- 2 files changed, 6 insertions(+), 1 deletion(-) diff --git a/Mage.Sets/src/mage/cards/r/ResoluteRider.java b/Mage.Sets/src/mage/cards/r/ResoluteRider.java index 60f4f1c8ed..ed3b33441e 100644 --- a/Mage.Sets/src/mage/cards/r/ResoluteRider.java +++ b/Mage.Sets/src/mage/cards/r/ResoluteRider.java @@ -1,5 +1,6 @@ package mage.cards.r; +import mage.MageInt; import mage.abilities.common.SimpleActivatedAbility; import mage.abilities.costs.mana.ManaCostsImpl; import mage.abilities.effects.common.continuous.GainAbilitySourceEffect; @@ -23,6 +24,8 @@ public final class ResoluteRider extends CardImpl { this.subtype.add(SubType.HUMAN); this.subtype.add(SubType.KNIGHT); + this.power = new MageInt(4); + this.toughness = new MageInt(2); // {W/B}{W/B}: Resolute Rider gains lifelink until end of turn. this.addAbility(new SimpleActivatedAbility(new GainAbilitySourceEffect( diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index 6b54ba777f..9122d45ef1 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -36012,6 +36012,7 @@ Giant Killer|Throne of Eldraine|14|R|{W}|Creature - Human Peasant|1|2|{1}{W}, {T Glass Casket|Throne of Eldraine|15|U|{1}{W}|Artifact|||When Glass Casket enters the battlefield, exile target creature an opponent controls with converted mana cost 3 or less until Glass Casket leaves the battlefield.| Happily Ever After|Throne of Eldraine|16|R|{2}{W}|Enchantment|||When Happily Ever After enters the battlefield, each player gains 5 life and draws a card.$At the beginning of your upkeep, if there are five colors among permanents you control, there are six or more card types among permanents you control and/or cards in your graveyard, and your life total is greater than or equal to your starting life total, you win the game.| Harmonious Archon|Throne of Eldraine|17|M|{4}{W}{W}|Creature - Archon|4|5|Flying$Non-Archon creatures have base power and toughness 3/3.$When Harmonious Archon enters the battlefield, create two 1/1 white Human creature tokens.| +Hushbringer|Throne of Eldraine|18|R|{1}{W}|Creature - Faerie|1|2|Flying, lifelink$Creatures entering the battlefield or dying don't cause abilities to trigger.| Knight of the Keep|Throne of Eldraine|19|C|{2}{W}|Creature - Human Knight|3|2|| Linden, the Steadfast Queen|Throne of Eldraine|20|R|{W}{W}{W}|Legendary Creature - Human Noble|3|3|Vigilance$Whenever a white creature you control attacks, you gain 1 life.| Lonesome Unicorn|Throne of Eldraine|21|C|{4}{W}|Creature - Unicorn|3|3|Vigilance| @@ -36213,7 +36214,7 @@ Loch Dragon|Throne of Eldraine|211|U|{U/R}{U/R}{U/R}{U/R}|Creature - Dragon|3|2| Bring Back|Throne of Eldraine|212|U|{G/W}{G/W}{G/W}{G/W}|Sorcery - Adventure|2|2|Create two 1/1 white Human creature tokens.| Oakhame Ranger|Throne of Eldraine|212|U|{G/W}{G/W}{G/W}{G/W}|Creature - Elf Knight|2|2|{T}: Creatures you control get +1/+1 until end of turn.| Rampart Smasher|Throne of Eldraine|213|U|{R/G}{R/G}{R/G}{R/G}|Creature - Giant|5|5|Rampart Smasher can't be blocked by Knights or Walls.| -Resolute Rider|Throne of Eldraine|214|U|{W/B}{W/B}{W/B}{W/B}|Creature - Human Knight|||{W/B}{W/B}: Resolute Rider gains lifelink until end of turn.${W/B}{W/B}{W/B}: Resolute Rider gains indestructible until end of turn.| +Resolute Rider|Throne of Eldraine|214|U|{W/B}{W/B}{W/B}{W/B}|Creature - Human Knight|4|2|{W/B}{W/B}: Resolute Rider gains lifelink until end of turn.${W/B}{W/B}{W/B}: Resolute Rider gains indestructible until end of turn.| Thunderous Snapper|Throne of Eldraine|215|U|{G/U}{G/U}{G/U}{G/U}|Creature - Turtle Hydra|4|4|Whenever you cast a spell with converted mana cost 5 or greater, draw a card.| Clockwork Servant|Throne of Eldraine|216|U|{3}|Artifact Creature - Gnome|2|3|Adamant — When Clockwork Servant enters the battlefield, if at least three mana of the same color was spent to cast it, draw a card.| Enchanted Carriage|Throne of Eldraine|218|U|{5}|Artifact - Vehicle|4|4|When Enchanted Carriage enters the battlefield, create two 1/1 white Mouse creature tokens.$Crew 2| @@ -36237,6 +36238,7 @@ Castle Garenbrig|Throne of Eldraine|240|R||Land|||Castle Garenbrig enters the ba Castle Locthwain|Throne of Eldraine|241|R||Land|||Castle Locthwain enters the battlefield tapped unless you control a Swamp.${T}: Add {B}.${1}{B}{B}, {T}: Draw a card, then you lose life equal to the number of cards in your hand.| Castle Vantress|Throne of Eldraine|242|R||Land|||Castle Vantress enters the battlefield tapped unless you control an Island.${T}: Add {U}.${2}{U}{U}, {T}: Scry 2.| Fabled Passage|Throne of Eldraine|244|R||Land|||{T}, Sacrifice Fabled Passage: Search your library for a basic land card, put it onto the battlefield tapped, then shuffle your library. Then if you control four or more lands, untap that land.| +Gingerbread Cabin|Throne of Eldraine|245|C||Land - Forest|||({T}: Add {G}.)$Gingerbread Cabin enters the battlefield tapped unless you control three or more other Forests.$When Gingerbread Cabin enters the battlefield untapped, create a Food token.| Idyllic Grange|Throne of Eldraine|246|C||Land - Plains|||({T}: Add {W}.)$Idyllic Grange enters the battlefield tapped unless you control three or more other Plains.$When Idyllic Grange enters the battlefield untapped, put a +1/+1 counter on target creature you control.| Mystic Sanctuary|Throne of Eldraine|247|C||Land - Island|||({T}: Add {U}.)$Mystic Sanctuary enters the battlefield tapped unless you control three or more other Islands.$When Mystic Sanctuary enters the battlefield untapped, you may put target instant or sorcery card from your graveyard on top of your library.| Tournament Grounds|Throne of Eldraine|248|U||Land|||{T}: Add {C}.${T}: Add {R}, {W}, or {B}. Spend this mana only to cast a Knight or Equipment spell.| From b4a615b1883f2b64a1be094d7b88e77aa990ae10 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 20 Sep 2019 07:41:49 -0400 Subject: [PATCH 230/373] Implemented Gingerbread Cabin --- .../src/mage/cards/g/GingerbreadCabin.java | 64 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 65 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/g/GingerbreadCabin.java diff --git a/Mage.Sets/src/mage/cards/g/GingerbreadCabin.java b/Mage.Sets/src/mage/cards/g/GingerbreadCabin.java new file mode 100644 index 0000000000..a6d6295fbb --- /dev/null +++ b/Mage.Sets/src/mage/cards/g/GingerbreadCabin.java @@ -0,0 +1,64 @@ +package mage.cards.g; + +import mage.abilities.common.EntersBattlefieldAbility; +import mage.abilities.common.EntersBattlefieldUntappedTriggeredAbility; +import mage.abilities.condition.Condition; +import mage.abilities.condition.common.PermanentsOnTheBattlefieldCondition; +import mage.abilities.decorator.ConditionalOneShotEffect; +import mage.abilities.effects.common.CreateTokenEffect; +import mage.abilities.effects.common.TapSourceEffect; +import mage.abilities.mana.GreenManaAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.ComparisonType; +import mage.constants.SubType; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterControlledPermanent; +import mage.filter.predicate.permanent.AnotherPredicate; +import mage.game.permanent.token.FoodToken; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class GingerbreadCabin extends CardImpl { + + private static final FilterPermanent filter + = new FilterControlledPermanent(SubType.FOREST); + + static { + filter.add(AnotherPredicate.instance); + } + + private static final Condition condition + = new PermanentsOnTheBattlefieldCondition(filter, ComparisonType.FEWER_THAN, 3); + + public GingerbreadCabin(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.LAND}, ""); + + this.subtype.add(SubType.FOREST); + + // ({T}: Add {G}.) + this.addAbility(new GreenManaAbility()); + + // Gingerbread Cabin enters the battlefield tapped unless you control three or more other Forests. + this.addAbility(new EntersBattlefieldAbility( + new ConditionalOneShotEffect(new TapSourceEffect(), condition), + "tapped unless you control three or more other Forests" + )); + + // When Gingerbread Cabin enters the battlefield untapped, create a Food token. + this.addAbility(new EntersBattlefieldUntappedTriggeredAbility(new CreateTokenEffect(new FoodToken()), false)); + } + + private GingerbreadCabin(final GingerbreadCabin card) { + super(card); + } + + @Override + public GingerbreadCabin copy() { + return new GingerbreadCabin(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index ff8a6520cc..daed3c1057 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -115,6 +115,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Giant Opportunity", 159, Rarity.UNCOMMON, mage.cards.g.GiantOpportunity.class)); cards.add(new SetCardInfo("Giant's Skewer", 91, Rarity.COMMON, mage.cards.g.GiantsSkewer.class)); cards.add(new SetCardInfo("Gilded Goose", 160, Rarity.RARE, mage.cards.g.GildedGoose.class)); + cards.add(new SetCardInfo("Gingerbread Cabin", 245, Rarity.COMMON, mage.cards.g.GingerbreadCabin.class)); cards.add(new SetCardInfo("Gingerbrute", 219, Rarity.COMMON, mage.cards.g.Gingerbrute.class)); cards.add(new SetCardInfo("Glass Casket", 15, Rarity.UNCOMMON, mage.cards.g.GlassCasket.class)); cards.add(new SetCardInfo("Gluttonous Troll", 327, Rarity.RARE, mage.cards.g.GluttonousTroll.class)); From 8429e7b2fa387b88bff4870a7fc7dc4ddbcf4d64 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 20 Sep 2019 08:35:03 -0400 Subject: [PATCH 231/373] Implemented The Cauldron of Eternity --- .../mage/cards/t/TheCauldronOfEternity.java | 104 ++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 105 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/t/TheCauldronOfEternity.java diff --git a/Mage.Sets/src/mage/cards/t/TheCauldronOfEternity.java b/Mage.Sets/src/mage/cards/t/TheCauldronOfEternity.java new file mode 100644 index 0000000000..b2f1196cf8 --- /dev/null +++ b/Mage.Sets/src/mage/cards/t/TheCauldronOfEternity.java @@ -0,0 +1,104 @@ +package mage.cards.t; + +import mage.MageObject; +import mage.abilities.Ability; +import mage.abilities.SpellAbility; +import mage.abilities.common.ActivateAsSorceryActivatedAbility; +import mage.abilities.common.DiesCreatureTriggeredAbility; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.costs.common.PayLifeCost; +import mage.abilities.costs.common.TapSourceCost; +import mage.abilities.costs.mana.ManaCostsImpl; +import mage.abilities.effects.common.PutOnLibraryTargetEffect; +import mage.abilities.effects.common.ReturnFromGraveyardToBattlefieldTargetEffect; +import mage.abilities.effects.common.cost.CostModificationEffectImpl; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.*; +import mage.filter.StaticFilters; +import mage.game.Game; +import mage.players.Player; +import mage.target.common.TargetCardInYourGraveyard; +import mage.util.CardUtil; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class TheCauldronOfEternity extends CardImpl { + + public TheCauldronOfEternity(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT}, "{10}{B}{B}"); + + this.addSuperType(SuperType.LEGENDARY); + + // This spell costs {2} less for each creature card in your graveyard. + this.addAbility(new SimpleStaticAbility(Zone.ALL, new TheCauldronOfEternityCostReductionEffect())); + + // Whenever a creature you control dies, put it on the bottom of its owner's library. + this.addAbility(new DiesCreatureTriggeredAbility( + new PutOnLibraryTargetEffect(false, "put it on the bottom of its owner's library"), + false, StaticFilters.FILTER_CONTROLLED_A_CREATURE, true + )); + + // {2}{B}, {T}, Pay 2 life: Return target creature card from your graveyard to the battlefield. Activate this ability only any time you could cast a sorcery. + Ability ability = new ActivateAsSorceryActivatedAbility( + Zone.BATTLEFIELD, new ReturnFromGraveyardToBattlefieldTargetEffect(), new ManaCostsImpl("{2}{B}") + ); + ability.addCost(new TapSourceCost()); + ability.addCost(new PayLifeCost(2)); + ability.addTarget(new TargetCardInYourGraveyard(StaticFilters.FILTER_CARD_CREATURE_YOUR_GRAVEYARD)); + this.addAbility(ability); + } + + private TheCauldronOfEternity(final TheCauldronOfEternity card) { + super(card); + } + + @Override + public TheCauldronOfEternity copy() { + return new TheCauldronOfEternity(this); + } +} + +class TheCauldronOfEternityCostReductionEffect extends CostModificationEffectImpl { + + TheCauldronOfEternityCostReductionEffect() { + super(Duration.WhileOnStack, Outcome.Benefit, CostModificationType.REDUCE_COST); + staticText = "This spell costs {2} less for each creature card in your graveyard"; + } + + private TheCauldronOfEternityCostReductionEffect(final TheCauldronOfEternityCostReductionEffect effect) { + super(effect); + } + + @Override + public boolean apply(Game game, Ability source, Ability abilityToModify) { + Player player = game.getPlayer(source.getControllerId()); + if (player == null) { + return false; + } + int reductionAmount = player + .getGraveyard() + .getCards(game) + .stream() + .filter(MageObject::isCreature) + .mapToInt(card -> 2) + .sum(); + CardUtil.reduceCost(abilityToModify, reductionAmount); + return true; + } + + @Override + public boolean applies(Ability abilityToModify, Ability source, Game game) { + return abilityToModify instanceof SpellAbility + && abilityToModify.getSourceId().equals(source.getSourceId()) + && game.getCard(abilityToModify.getSourceId()) != null; + } + + @Override + public TheCauldronOfEternityCostReductionEffect copy() { + return new TheCauldronOfEternityCostReductionEffect(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index daed3c1057..3dc68edb28 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -236,6 +236,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Tall as a Beanstalk", 178, Rarity.COMMON, mage.cards.t.TallAsABeanstalk.class)); cards.add(new SetCardInfo("Taste of Death", 320, Rarity.RARE, mage.cards.t.TasteOfDeath.class)); cards.add(new SetCardInfo("Tempting Witch", 108, Rarity.COMMON, mage.cards.t.TemptingWitch.class)); + cards.add(new SetCardInfo("The Cauldron of Eternity", 82, Rarity.MYTHIC, mage.cards.t.TheCauldronOfEternity.class)); cards.add(new SetCardInfo("The Circle of Loyalty", 9, Rarity.MYTHIC, mage.cards.t.TheCircleOfLoyalty.class)); cards.add(new SetCardInfo("The Great Henge", 161, Rarity.MYTHIC, mage.cards.t.TheGreatHenge.class)); cards.add(new SetCardInfo("The Magic Mirror", 51, Rarity.MYTHIC, mage.cards.t.TheMagicMirror.class)); From 73a91115559a4cef254856bb7d2d83491501ed3d Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 20 Sep 2019 08:46:25 -0400 Subject: [PATCH 232/373] Implemented Cauldron's Gift --- Mage.Sets/src/mage/cards/c/CauldronsGift.java | 92 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 93 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/c/CauldronsGift.java diff --git a/Mage.Sets/src/mage/cards/c/CauldronsGift.java b/Mage.Sets/src/mage/cards/c/CauldronsGift.java new file mode 100644 index 0000000000..9ed9e0bd8b --- /dev/null +++ b/Mage.Sets/src/mage/cards/c/CauldronsGift.java @@ -0,0 +1,92 @@ +package mage.cards.c; + +import mage.abilities.Ability; +import mage.abilities.condition.common.AdamantCondition; +import mage.abilities.effects.OneShotEffect; +import mage.cards.Card; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Outcome; +import mage.constants.Zone; +import mage.counters.CounterType; +import mage.filter.StaticFilters; +import mage.game.Game; +import mage.game.permanent.Permanent; +import mage.players.Player; +import mage.target.TargetCard; +import mage.target.common.TargetCardInYourGraveyard; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class CauldronsGift extends CardImpl { + + public CauldronsGift(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.SORCERY}, "{4}{B}"); + + // Adamant — If at least three black mana was spent to cast this spell, put the top four cards of your library into your graveyard. + // You may choose a creature card in your graveyard. If you do, return it to the battlefield with an additional +1/+1 counter on it. + this.getSpellAbility().addEffect(new CauldronsGiftEffect()); + } + + private CauldronsGift(final CauldronsGift card) { + super(card); + } + + @Override + public CauldronsGift copy() { + return new CauldronsGift(this); + } +} + +class CauldronsGiftEffect extends OneShotEffect { + + CauldronsGiftEffect() { + super(Outcome.Benefit); + staticText = "Adamant — If at least three black mana was spent to cast this spell, " + + "put the top four cards of your library into your graveyard." + + "
You may choose a creature card in your graveyard. " + + "If you do, return it to the battlefield with an additional +1/+1 counter on it."; + } + + private CauldronsGiftEffect(final CauldronsGiftEffect effect) { + super(effect); + } + + @Override + public CauldronsGiftEffect copy() { + return new CauldronsGiftEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + Player player = game.getPlayer(source.getControllerId()); + if (player == null) { + return false; + } + if (AdamantCondition.BLACK.apply(game, source)) { + player.moveCards(player.getLibrary().getTopCards(game, 4), Zone.GRAVEYARD, source, game); + } + if (player.getGraveyard().count(StaticFilters.FILTER_CARD_CREATURE, game) == 0 + || !player.chooseUse(outcome, "Choose a creature card in your graveyard to return to the battlefield?", source, game)) { + return true; + } + TargetCard target = new TargetCardInYourGraveyard(StaticFilters.FILTER_CARD_CREATURE_YOUR_GRAVEYARD); + target.setNotTarget(true); + if (!player.choose(outcome, player.getGraveyard(), target, game)) { + return false; + } + Card card = game.getCard(target.getFirstTarget()); + if (card == null || player.moveCards(card, Zone.BATTLEFIELD, source, game)) { + return false; + } + Permanent permanent = game.getPermanent(card.getId()); + if (permanent != null) { + permanent.addCounters(CounterType.P1P1.createInstance(), source, game); + } + return true; + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 3dc68edb28..dccfbf9a51 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -59,6 +59,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Castle Locthwain", 241, Rarity.RARE, mage.cards.c.CastleLocthwain.class)); cards.add(new SetCardInfo("Castle Vantress", 242, Rarity.RARE, mage.cards.c.CastleVantress.class)); cards.add(new SetCardInfo("Cauldron Familiar", 81, Rarity.UNCOMMON, mage.cards.c.CauldronFamiliar.class)); + cards.add(new SetCardInfo("Cauldron's Gift", 83, Rarity.UNCOMMON, mage.cards.c.CauldronsGift.class)); cards.add(new SetCardInfo("Charming Prince", 8, Rarity.RARE, mage.cards.c.CharmingPrince.class)); cards.add(new SetCardInfo("Chittering Witch", 319, Rarity.RARE, mage.cards.c.ChitteringWitch.class)); cards.add(new SetCardInfo("Chulane, Teller of Tales", 326, Rarity.MYTHIC, mage.cards.c.ChulaneTellerOfTales.class)); From 70d5aeaf6d615f0bf2bd071d6a6084e2db56a3ad Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 20 Sep 2019 13:34:04 -0400 Subject: [PATCH 233/373] updated ELD spoiler and reprints --- Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 23 ++++++++++++ Utils/mtg-cards-data.txt | 36 ++++++++++++++++++- 2 files changed, 58 insertions(+), 1 deletion(-) diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index dccfbf9a51..dbab649397 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -100,8 +100,13 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Fireborn Knight", 210, Rarity.UNCOMMON, mage.cards.f.FirebornKnight.class)); cards.add(new SetCardInfo("Fires of Invention", 125, Rarity.RARE, mage.cards.f.FiresOfInvention.class)); cards.add(new SetCardInfo("Flaxen Intruder", 155, Rarity.UNCOMMON, mage.cards.f.FlaxenIntruder.class)); + cards.add(new SetCardInfo("Fling", 126, Rarity.COMMON, mage.cards.f.Fling.class)); cards.add(new SetCardInfo("Folio of Fancies", 46, Rarity.RARE, mage.cards.f.FolioOfFancies.class)); cards.add(new SetCardInfo("Foreboding Fruit", 88, Rarity.COMMON, mage.cards.f.ForebodingFruit.class)); + cards.add(new SetCardInfo("Forest", 266, Rarity.LAND, mage.cards.basiclands.Forest.class, NON_FULL_USE_VARIOUS)); + cards.add(new SetCardInfo("Forest", 267, Rarity.LAND, mage.cards.basiclands.Forest.class, NON_FULL_USE_VARIOUS)); + cards.add(new SetCardInfo("Forest", 268, Rarity.LAND, mage.cards.basiclands.Forest.class, NON_FULL_USE_VARIOUS)); + cards.add(new SetCardInfo("Forest", 269, Rarity.LAND, mage.cards.basiclands.Forest.class, NON_FULL_USE_VARIOUS)); cards.add(new SetCardInfo("Forever Young", 89, Rarity.COMMON, mage.cards.f.ForeverYoung.class)); cards.add(new SetCardInfo("Fortifying Provisions", 13, Rarity.COMMON, mage.cards.f.FortifyingProvisions.class)); cards.add(new SetCardInfo("Foulmire Knight", 90, Rarity.UNCOMMON, mage.cards.f.FoulmireKnight.class)); @@ -135,6 +140,10 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Into the Story", 50, Rarity.UNCOMMON, mage.cards.i.IntoTheStory.class)); cards.add(new SetCardInfo("Irencrag Feat", 127, Rarity.RARE, mage.cards.i.IrencragFeat.class)); cards.add(new SetCardInfo("Irencrag Pyromancer", 128, Rarity.RARE, mage.cards.i.IrencragPyromancer.class)); + cards.add(new SetCardInfo("Island", 254, Rarity.LAND, mage.cards.basiclands.Island.class, NON_FULL_USE_VARIOUS)); + cards.add(new SetCardInfo("Island", 255, Rarity.LAND, mage.cards.basiclands.Island.class, NON_FULL_USE_VARIOUS)); + cards.add(new SetCardInfo("Island", 256, Rarity.LAND, mage.cards.basiclands.Island.class, NON_FULL_USE_VARIOUS)); + cards.add(new SetCardInfo("Island", 257, Rarity.LAND, mage.cards.basiclands.Island.class, NON_FULL_USE_VARIOUS)); cards.add(new SetCardInfo("Joust", 129, Rarity.UNCOMMON, mage.cards.j.Joust.class)); cards.add(new SetCardInfo("Jousting Dummy", 224, Rarity.COMMON, mage.cards.j.JoustingDummy.class)); cards.add(new SetCardInfo("Keeper of Fables", 163, Rarity.UNCOMMON, mage.cards.k.KeeperOfFables.class)); @@ -159,6 +168,10 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Midnight Clock", 54, Rarity.RARE, mage.cards.m.MidnightClock.class)); cards.add(new SetCardInfo("Mirrormade", 55, Rarity.RARE, mage.cards.m.Mirrormade.class)); cards.add(new SetCardInfo("Mistford River Turtle", 56, Rarity.COMMON, mage.cards.m.MistfordRiverTurtle.class)); + cards.add(new SetCardInfo("Mountain", 262, Rarity.LAND, mage.cards.basiclands.Mountain.class, NON_FULL_USE_VARIOUS)); + cards.add(new SetCardInfo("Mountain", 263, Rarity.LAND, mage.cards.basiclands.Mountain.class, NON_FULL_USE_VARIOUS)); + cards.add(new SetCardInfo("Mountain", 264, Rarity.LAND, mage.cards.basiclands.Mountain.class, NON_FULL_USE_VARIOUS)); + cards.add(new SetCardInfo("Mountain", 265, Rarity.LAND, mage.cards.basiclands.Mountain.class, NON_FULL_USE_VARIOUS)); cards.add(new SetCardInfo("Murderous Rider", 97, Rarity.RARE, mage.cards.m.MurderousRider.class)); cards.add(new SetCardInfo("Mysterious Pathlighter", 22, Rarity.UNCOMMON, mage.cards.m.MysteriousPathlighter.class)); cards.add(new SetCardInfo("Mystic Sanctuary", 247, Rarity.COMMON, mage.cards.m.MysticSanctuary.class)); @@ -179,6 +192,10 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Outmuscle", 170, Rarity.COMMON, mage.cards.o.Outmuscle.class)); cards.add(new SetCardInfo("Overwhelmed Apprentice", 60, Rarity.UNCOMMON, mage.cards.o.OverwhelmedApprentice.class)); cards.add(new SetCardInfo("Piper of the Swarm", 100, Rarity.RARE, mage.cards.p.PiperOfTheSwarm.class)); + cards.add(new SetCardInfo("Plains", 250, Rarity.LAND, mage.cards.basiclands.Plains.class, NON_FULL_USE_VARIOUS)); + cards.add(new SetCardInfo("Plains", 251, Rarity.LAND, mage.cards.basiclands.Plains.class, NON_FULL_USE_VARIOUS)); + cards.add(new SetCardInfo("Plains", 252, Rarity.LAND, mage.cards.basiclands.Plains.class, NON_FULL_USE_VARIOUS)); + cards.add(new SetCardInfo("Plains", 253, Rarity.LAND, mage.cards.basiclands.Plains.class, NON_FULL_USE_VARIOUS)); cards.add(new SetCardInfo("Questing Beast", 171, Rarity.MYTHIC, mage.cards.q.QuestingBeast.class)); cards.add(new SetCardInfo("Raging Redcap", 134, Rarity.COMMON, mage.cards.r.RagingRedcap.class)); cards.add(new SetCardInfo("Rally for the Throne", 25, Rarity.UNCOMMON, mage.cards.r.RallyForTheThrone.class)); @@ -222,12 +239,17 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Sorcerous Spyglass", 233, Rarity.RARE, mage.cards.s.SorcerousSpyglass.class)); cards.add(new SetCardInfo("Specter's Shriek", 106, Rarity.UNCOMMON, mage.cards.s.SpectersShriek.class)); cards.add(new SetCardInfo("Spinning Wheel", 234, Rarity.UNCOMMON, mage.cards.s.SpinningWheel.class)); + cards.add(new SetCardInfo("Sporecap Spider", 176, Rarity.COMMON, mage.cards.s.SporecapSpider.class)); cards.add(new SetCardInfo("Steelbane Hydra", 322, Rarity.RARE, mage.cards.s.SteelbaneHydra.class)); cards.add(new SetCardInfo("Steelclaw Lance", 202, Rarity.UNCOMMON, mage.cards.s.SteelclawLance.class)); cards.add(new SetCardInfo("Steelgaze Griffin", 65, Rarity.COMMON, mage.cards.s.SteelgazeGriffin.class)); cards.add(new SetCardInfo("Stolen by the Fae", 66, Rarity.RARE, mage.cards.s.StolenByTheFae.class)); cards.add(new SetCardInfo("Stonecoil Serpent", 235, Rarity.RARE, mage.cards.s.StonecoilSerpent.class)); cards.add(new SetCardInfo("Stormfist Crusader", 203, Rarity.RARE, mage.cards.s.StormfistCrusader.class)); + cards.add(new SetCardInfo("Swamp", 258, Rarity.LAND, mage.cards.basiclands.Swamp.class, NON_FULL_USE_VARIOUS)); + cards.add(new SetCardInfo("Swamp", 259, Rarity.LAND, mage.cards.basiclands.Swamp.class, NON_FULL_USE_VARIOUS)); + cards.add(new SetCardInfo("Swamp", 260, Rarity.LAND, mage.cards.basiclands.Swamp.class, NON_FULL_USE_VARIOUS)); + cards.add(new SetCardInfo("Swamp", 261, Rarity.LAND, mage.cards.basiclands.Swamp.class, NON_FULL_USE_VARIOUS)); cards.add(new SetCardInfo("Syr Alin, the Lion's Claw", 32, Rarity.UNCOMMON, mage.cards.s.SyrAlinTheLionsClaw.class)); cards.add(new SetCardInfo("Syr Carah, the Bold", 145, Rarity.UNCOMMON, mage.cards.s.SyrCarahTheBold.class)); cards.add(new SetCardInfo("Syr Elenora, the Discerning", 67, Rarity.UNCOMMON, mage.cards.s.SyrElenoraTheDiscerning.class)); @@ -277,6 +299,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Workshop Elders", 318, Rarity.RARE, mage.cards.w.WorkshopElders.class)); cards.add(new SetCardInfo("Worthy Knight", 36, Rarity.RARE, mage.cards.w.WorthyKnight.class)); cards.add(new SetCardInfo("Yorvo, Lord of Garenbrig", 185, Rarity.RARE, mage.cards.y.YorvoLordOfGarenbrig.class)); + cards.add(new SetCardInfo("Youthful Knight", 37, Rarity.COMMON, mage.cards.y.YouthfulKnight.class)); // This is here to prevent the incomplete adventure implementation from causing problems and will be removed cards.removeIf(setCardInfo -> AdventureCard.class.isAssignableFrom(setCardInfo.getCardClass())); diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index 9122d45ef1..dbb0159d3c 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -36006,6 +36006,7 @@ The Circle of Loyalty|Throne of Eldraine|9|M|{4}{W}{W}|Legendary Artifact|||This Deafening Silence|Throne of Eldraine|10|U|{W}|Enchantment|||Each player can't cast more than one noncreature spell each turn.| Faerie Guidemother|Throne of Eldraine|11|C|{W}|Creature - Faerie|1|1|Flying| Gift of the Fae|Throne of Eldraine|11|C|{1}{W}|Sorcery - Adventure|1|1|Target creature gets +2/+1 and gains flying until end of turn.| +Flutterfox|Throne of Eldraine|12|C|{1}{W}|Creature - Fox|||As long as you control an artifact or enchantment, Flutterfox has flying.| Fortifying Provisions|Throne of Eldraine|13|C|{2}{W}|Enchantment|||Creatures you control get +0/+1.$When Fortifying Provisions enters the battlefield, create a Food token.| Chop Down|Throne of Eldraine|14|R|{2}{W}|Instant - Adventure|1|2|Destroy target creature with power 4 or greater.| Giant Killer|Throne of Eldraine|14|R|{W}|Creature - Human Peasant|1|2|{1}{W}, {T}: Tap target creature.| @@ -36018,6 +36019,8 @@ Linden, the Steadfast Queen|Throne of Eldraine|20|R|{W}{W}{W}|Legendary Creature Lonesome Unicorn|Throne of Eldraine|21|C|{4}{W}|Creature - Unicorn|3|3|Vigilance| Rider in Need|Throne of Eldraine|21|C|{2}{W}|Sorcery - Adventure|3|3|Create a 2/2 white Knight creature token with vigilance.| Mysterious Pathlighter|Throne of Eldraine|22|U|{2}{W}|Creature - Faerie|2|2|Flying$Each creature you control that has an Adventure enters the battlefield with an additional +1/+1 counter on it.| +Outflank|Throne of Eldraine|23|C|{W}|Instant|||Outflank deals damage to target attacking or blocking creature equal to the number of creatures you control.| +Prized Griffin|Throne of Eldraine|24|C|{4}{W}|Creature - Griffin|||Flying| Rally for the Throne|Throne of Eldraine|25|U|{2}{W}|Instant|||Create two 1/1 white Human creature tokens.$Adamant — If at least three white mana was spent to cast this spell, you gain 1 life for each creature you control.| Cast Off|Throne of Eldraine|26|M|{3}{W}{W}|Sorcery - Adventure|7|7|Destroy all non-Giant creatures.| Realm-Cloaked Giant|Throne of Eldraine|26|M|{5}{W}{W}|Creature - Giant|7|7|Vigilance| @@ -36033,11 +36036,14 @@ Trapped in the Tower|Throne of Eldraine|33|C|{1}{W}|Enchantment - Aura|||Enchant True Love's Kiss|Throne of Eldraine|34|C|{2}{W}{W}|Instant|||Exile target artifact or enchantment.$Draw a card| Venerable Knight|Throne of Eldraine|35|U|{W}|Creature - Human Knight|2|1|When Venerable Knight dies, put a +1/+1 counter on target Knight you control.| Worthy Knight|Throne of Eldraine|36|R|{1}{W}|Creature - Human Knight|2|2|Whenever you cast a Knight spell, create a 1/1 white Human creature token.| +Youthful Knight|Throne of Eldraine|37|C|{1}{W}|Creature - Human Knight|2|1|First strike| Animating Faerie|Throne of Eldraine|38|U|{2}{U}|Creature - Faerie|2|2|Flying| Bring to Life|Throne of Eldraine|38|U|{2}{U}|Sorcery - Adventure|2|2|Target noncreature artifact you control becomes a 0/0 artifact creature. Put four +1/+1 counters on it.| Brazen Borrower|Throne of Eldraine|39|M|{1}{U}{U}|Creature - Faerie Rogue|3|1|Flash$Flying$Brazen Borrower can block only creatures with flying.| Petty Theft|Throne of Eldraine|39|M|{1}{U}|Instant - Adventure|3|1|Return target nonland permanent an opponent controls to its owner's hand.| +Charmed Sleep|Throne of Eldraine|40|C|{1}{U}{U}|Enchantment - Aura|||Enchant creature$When Charmed Sleep enters the battlefield, tap enchanted creature.$Enchanted creature doesn't untap during its controller's untap step.| Corridor Monitor|Throne of Eldraine|41|C|{1}{U}|Artifact Creature - Construct|1|4|When Corridor Monitor enters the battlefield, untap target artifact or creature you control.| +Didn't Say Please|Throne of Eldraine|42|C|{1}{U}{U}|Instant|||Counter target spell. its controller puts the top three cards of their library into their graveyard.| Emry, Lurker of the Loch|Throne of Eldraine|43|R|{2}{U}|Legendary Creature - Merfolk Wizard|1|2|This spell costs {1} less to cast for each artifact you control.$When Emry, Lurker of the Loch enters the battlefield, put the top four cards of your library into your graveyard.${T}: Choose target artifact card in your graveyard. You may cast that card this turn.| Fae of Wishes|Throne of Eldraine|44|R|{1}{U}|Creature - Faerie Wizard|1|4|Flying${1}{U}, Discard two cards: Return Fae of Wishes to its owner's hand.| Granted|Throne of Eldraine|44|R|{3}{U}|Sorcery - Adventure|1|4|You may choose a noncreature card you own from outside the game, reveal it, and put it into your hand.| @@ -36050,12 +36056,17 @@ Mesmeric Glare|Throne of Eldraine|49|U|{2}{U}|Instant - Adventure|2|1|Counter ta Into the Story|Throne of Eldraine|50|U|{5}{U}{U}|Instant|||This spell costs {3} less to cast if an opponent has seven or more cards in their graveyard.$Draw four cards.| The Magic Mirror|Throne of Eldraine|51|M|{6}{U}{U}{U}|Legendary Artifact|||This spell costs {1} less to cast for each instant and sorcery card in your graveyard.$You have no maximum hand size.$At the beginning of your upkeep, put a knowledge counter on The Magic Mirror, then draw a card for each knowledge counter on The Magic Mirror.| Mantle of Tides|Throne of Eldraine|52|C|{U}|Artifact - Equipment|||Equipped creature gets +1/+2.$Whenever you draw your second card each turn, attach Mantle of Tides to target creature you control.$Equip {3}| +Merfolk Secretkeeper|Throne of Eldraine|53|C|{U}|Creature - Merfolk Wizard|0|4|| +Venture Deeper|Throne of Eldraine|53|C|{U}|Sorcery - Adventure|0|4|Target player puts the top four cards of their library into their graveyard.| Midnight Clock|Throne of Eldraine|54|R|{2}{U}|Artifact|||{T}: Add {U}.${2}{U}: Put an hour counter on Midnight Clock.$At the beginning of each upkeep, put an hour counter on Midnight Clock.$When the twelfth hour counter is put on Midnight Clock, shuffle your hand and graveyard into your library, then draw seven cards. Exile Midnight Clock.| Mirrormade|Throne of Eldraine|55|R|{1}{U}{U}|Enchantment|||You may have Mirrormade enter the battlefield as a copy of any artifact or enchantment on the battlefield.| Mistford River Turtle|Throne of Eldraine|56|C|{3}{U}|Creature - Turtle|1|5|Whenever Mistford River Turtle attacks, another target attacking non-Human creature can't be blocked this turn.| +Moonlit Scavengers|Throne of Eldraine|57|C|{5}{U}|Creature - Merfolk Rogue|4|5|When Moonlit Scavengers enters the battlefield, if you control an artifact or enchantment, return target creature an opponent controls to its owner's hand.| Mystical Dispute|Throne of Eldraine|58|U|{2}{U}|Instant|||This spell costs {2} less to cast if it targets a blue spell.$Counter target spell unless its controller pays {3}.| Opt|Throne of Eldraine|59|C|{U}|Instant|||Scry 1.$Draw a card.| Overwhelmed Apprentice|Throne of Eldraine|60|U|{U}|Creature - Human Wizard|1|2|When Overwhelmed Apprentice enters the battlefield, each opponent puts the top two cards of their library into their graveyard. Then you scry 2.| +Queen of Ice|Throne of Eldraine|61|C|{2}{U}|Creature - Human Noble Wizard|2|3|Whenever Queen of Ice deals combat damage to a creature, tap that creature. It doesn't untap during its controller's next untap step.| +Rage of Winter|Throne of Eldraine|61|C|{1}{U}|Sorcery - Adventure|2|3|Tap target creature. It doesn't untap during its controller's next untap step.| Run Away Together|Throne of Eldraine|62|C|{1}{U}|Instant|||Choose two target creatures controlled by different players. Return those creatures to their owners' hands.| Sage of the Falls|Throne of Eldraine|63|U|{4}{U}|Creature - Merfolk Wizard|2|5|Whenever Sage of the Falls or another non-Human creature enters the battlefield under you control, you may draw a card. If you do, discard a card.| So Tiny|Throne of Eldraine|64|C|{U}|Enchantment - Aura|||Flash$Enchant creature$Enchanted creature gets -2/-0. It gets -6/-0 instead as long as its controller has seven or more cards in their graveyard.| @@ -36071,6 +36082,7 @@ Wishful Merfolk|Throne of Eldraine|73|C|{1}{U}|Creature - Merfolk|3|2|Defender${ Witching Well|Throne of Eldraine|74|C|{U}|Artifact|||When Witching Well enters the battlefield, scry 2.${3}{U}, Sacrifice Witching Well: Draw two cards.| Ayara, First of Locthwain|Throne of Eldraine|75|R|{B}{B}{B}|Legendary Creature - Elf Noble|2|3|Whenever Ayara, First of Locthwain or another black creature enters the battlefield under your control, each opponent loses 1 life and you gain 1 life.${T}, Sacrifice another black creature: Draw a card.| Bake into a Pie|Throne of Eldraine|76|C|{2}{B}{B}|Instant|||Destroy target creature. Create a Food token.| +Barrow Witches|Throne of Eldraine|77|C|{4}{B}|Creature - Human Warlock|3|4|When Barrow Witches enters the battlefield, return target Knight card from your graveyard to your hand.| Belle of the Brawl|Throne of Eldraine|78|U|{2}{B}|Creature - Human Knight|3|2|Menace$Whenever Belle of the Brawl attacks, other Knights you control get +1/+0 until end of turn.| Blacklance Paragon|Throne of Eldraine|79|R|{1}{B}|Creature - Human Knight|3|1|Flash$When Blacklance Paragon enters the battlefield, target Knight gains deathtouch and lifelink until end of turn.| Bog Naughty|Throne of Eldraine|80|U|{3}{B}{B}|Creature - Faerie|3|3|Flying${2}{B}, Sacrifice a Food: Target creature gets -3/-3 until end of turn.| @@ -36086,8 +36098,11 @@ Forever Young|Throne of Eldraine|89|C|{1}{B}|Sorcery|||Put any number of target Foulmire Knight|Throne of Eldraine|90|U|{B}|Creature - Zombie Knight|1|1|Deathtouch| Profane Insight|Throne of Eldraine|90|U|{2}{B}|Instant - Adventure|1|1|You draw a card and you lose 1 life.| Giant's Skewer|Throne of Eldraine|91|C|{1}{B}|Artifact - Equipment|||Equipped creature gets +2/+1.$Whenever equipped creature deals combat damage to a creature, create a Food token.$Equip {3}| +Lash of Thorns|Throne of Eldraine|92|C|{B}|Instant|||Target creature gets +2/+1 and gains deathtouch until end of turn.| Locthwain Paladin|Throne of Eldraine|93|C|{3}{B}|Creature - Human Knight|3|2|Menace$Adamant — If at least three black mana was spent to cast this spell, Locthwain Paladin enters the battlefield with a +1/+1 counter on it.| Lost Legion|Throne of Eldraine|94|C|{1}{B}{B}|Creature - Spirit Knight|2|3|When Lost Legion enters the battlefield, scry 2.| +Malevolent Noble|Throne of Eldraine|95|C|{1}{B}|Creature - Human Noble|2|2|{2}, Sacrifice an artifact or another creature: Put a +1/+1 counter on Malevolent Noble.| +Memory Theft|Throne of Eldraine|96|C|{2}{B}|Sorcery|||Target opponent reveals their hand. You choose a nonland card from it. That player discards that card. You may put a card that has an Adventure that player owns from exile into that player's graveyard.| Murderous Rider|Throne of Eldraine|97|R|{1}{B}{B}|Creature - Zombie Knight|2|3|Lifelink$When Murderous Rider dies, put it on the bottom of its owner's library.| Swift End|Throne of Eldraine|97|R|{1}{B}{B}|Instant - Adventure|2|3|Destroy target creature or planeswalker. You lose 2 life.| Oathsworn Knight|Throne of Eldraine|98|R|{1}{B}{B}|Creature - Human Knight|0|0|Oathsworn Knight enters the battlefield with four +1/+1 counters on it.$Oathsworn Knight attacks each combat if able.$If damage would be dealt to Oathsworn Knight while it has a +1/+1 counter on it, prevent that damage and remove a +1/+1 counter from it.| @@ -36095,6 +36110,8 @@ Alter Fate|Throne of Eldraine|99|U|{1}{B}|Sorcery - Adventure|2|2|Return target Order of Midnight|Throne of Eldraine|99|U|{1}{B}|Creature - Human Knight|2|2|Flying$Order of Midnight can't block.| Piper of the Swarm|Throne of Eldraine|100|R|{1}{B}|Creature - Human Warlock|1|3|Rats you control have menace.${1}{B}, {T}: Create a 1/1 black Rat creature token.${2}{B}{B}, {T}, Sacrifice three Rats: Gain control of target creature.| Rankle, Master of Pranks|Throne of Eldraine|101|M|{2}{B}{B}|Legendary Creature - Faerie Rogue|3|3|Flying, haste$Whenever Rankle, Master of Pranks deals combat damage to a player, choose any number —$• Each player discards a card.$• Each player loses 1 life and draws a card.$• Each player sacrifices a creature.| +Harvest Fear|Throne of Eldraine|102|C|{3}{B}|Sorcery - Adventure|4|5|Target opponent discards two cards.| +Reaper of Night|Throne of Eldraine|102|C|{5}{B}{B}|Creature - Specter|4|5|Whenever Reaper of Night attacks, if defending player hass two or fewer cards in hand, it gains flying until end of turn.| Reave Soul|Throne of Eldraine|103|C|{1}{B}|Sorcery|||Destroy target creature with power 3 or less.| Revenge of Ravens|Throne of Eldraine|104|U|{3}{B}|Enchantment|||Whenever a creature attacks you or a planeswalker you control, that creature's controller loses 1 life and you gain 1 life.| Curry Favor|Throne of Eldraine|105|C|{B}|Sorcery - Adventure|2|1|You gain X life and each opponent loses X life, where X is the number of Knights you control.| @@ -36121,6 +36138,7 @@ Embereth Shieldbreaker|Throne of Eldraine|122|U|{1}{R}|Creature - Human Knight|2 Ferocity of the Wilds|Throne of Eldraine|123|U|{2}{R}|Enchantment|||Attacking non-Human creatures you control get +1/+0 and have trample.| Fervent Champion|Throne of Eldraine|124|R|{R}|Creature - Human Knight|1|1|First strike, haste$Whenever Fervent Champion attacks, another target attacking Knight you control gets +1/+0 until end of turn.$Equip abilities you activate that target Fervent Champion cost {3} less to activate.| Fires of Invention|Throne of Eldraine|125|R|{3}{R}|Enchantment|||You can cast spells only during your turn and you can cast no more than two spells each turn.$You may cast spells with converted mana cost less than or equal to the number of lands you control without paying their mana costs.| +Fling|Throne of Eldraine|126|C|{1}{R}|Instant|||As an additional cost to cast this spell, sacrifice a creature.$Fling deals damage equal to the sacrificed creature's power to any target.| Irencrag Feat|Throne of Eldraine|127|R|{1}{R}{R}{R}|Sorcery|||Add seven {R}. You can cast only one more spell this turn.| Irencrag Pyromancer|Throne of Eldraine|128|R|{2}{R}|Creature - Human Wizard|0|4|Whenever you draw your second card each turn, Irencrag Pyromancer deals 3 damage to any target.| Joust|Throne of Eldraine|129|U|{1}{R}|Sorcery|||Choose target creature you control and target creature you don't control. The creature you control gets +2/+1 until end of turn if it's a Knight. Then those creatures fight each other.| @@ -36132,6 +36150,8 @@ Opportunistic Dragon|Throne of Eldraine|133|R|{2}{R}{R}|Creature - Dragon|4|3|Fl Raging Redcap|Throne of Eldraine|134|C|{2}{R}|Creature - Goblin Knight|1|2|Double strike| Redcap Melee|Throne of Eldraine|135|U|{R}|Instant|||Redcap Melee deals 4 damage to target creature or planeswalker. If a nonred permanent is dealt damage this way, you sacrifice a land.| Redcap Raiders|Throne of Eldraine|136|C|{2}{R}|Creature - Goblin Warrior|3|2|Whenever Redcap Raiders attacks, you may tap an untapped non-Human creature you control. If you do, Redcap Raiders gets +1/+1 and gains trample until end of turn.| +Boulder Rush|Throne of Eldraine|137|C|{R}|Instant - Adventure|3|1|Target creature gets +2/+0 until end of turn.| +Rimrock Knight|Throne of Eldraine|137|C|{1}{R}|Creature - Dwarf Knight|3|1|Rimrock Knight can't block| Robber of the Rich|Throne of Eldraine|138|M|{1}{R}|Creature - Human Archer Rogue|2|2|Reach, haste$Whenever Robber of the Rich attacks, if defending player has more cards in hand than you, exile the top card of their library. During any turn you attacked with a Rogue, you may cast that card and you may spend mana as though it were mana of any color to cast that spell.| Scorching Dragonfire|Throne of Eldraine|139|C|{1}{R}|Instant|||Scorching Dragonfire deals 3 damage to target creature or planeswalker. If that creature or planeswalker would die this turn, exile it instead.| Searing Barrage|Throne of Eldraine|140|C|{4}{R}|Instant|||Searing Barrage deals 5 damage to target creature.$Adamant — If at least three red mana was spent to cast this spell, Searing Barrage deals 3 damage to that creature's controller.| @@ -36162,6 +36182,7 @@ Gilded Goose|Throne of Eldraine|160|R|{G}|Creature - Bird|0|2|Flying$When Gilded The Great Henge|Throne of Eldraine|161|M|{7}{G}{G}|Legendary Artifact|||This spell costs {X} less to cast, where X is the greatest power among creatures you control.${T}: Add {G}{G}. You gain 2 life.$Whenever a nontoken creature enters the battlefield under your control, put a +1/+1 counter on it and draw a card.| Insatiable Appetite|Throne of Eldraine|162|C|{1}{G}|Instant|||You may sacrifice a Food. If you do, target creature gets +5/+5 until end of turn. Otherwise, that creature gets +3/+3 until end of turn.| Keeper of Fables|Throne of Eldraine|163|U|{3}{G}{G}|Creature - Cat|4|5|Whenever one or more non-Human creatures you control deal combat damage to a player, draw a card.| +Kenrith's Transformation|Throne of Eldraine|164|U|{1}{G}|Enchantment - Aura|||Enchant creature$When Kenrith's Transformation enters the battlefield, draw a card.$Enchanted creature loses all abilities and is a green Elk creature with base power and toughness 3/3.| Heart's Desire|Throne of Eldraine|165|R|{G}|Sorcery - Adventure|5|5|Create a 1/1 white Human creature token.| Lovestruck Beast|Throne of Eldraine|165|R|{2}{G}|Creature - Beast Noble|5|5|Lovestruck Beast can't attack unless you control a 1/1 creature.| Maraleaf Rider|Throne of Eldraine|166|C|{1}{G}|Creature - Elf Knight|3|1|Sacrifice a Food: Target creature blocks Maraleaf Rider this turn if able.| @@ -36175,6 +36196,7 @@ Return to Nature|Throne of Eldraine|173|C|{1}{G}|Instant|||Choose one —$• De Rosethorn Acolyte|Throne of Eldraine|174|C|{2}{G}|Creature - Elf Druid|2|3|{T}: Add one mana of any color.| Seasonal Ritual|Throne of Eldraine|174|C|{G}|Sorcery - Adventure|2|3|Add one mana of any color.| Rosethorn Halberd|Throne of Eldraine|175|C|{G}|Artifact - Equipment|||When Rosethorn Halberd enters the battlefield, attach it to target non-Human creature you control.$Equipped creature gets +2/+1.$Equip {5}| +Sporecap Spider|Throne of Eldraine|176|C|{2}{G}|Creature - Spider|1|5|Reach| Syr Faren, the Hengehammer|Throne of Eldraine|177|U|{G}{G}|Legendary Creature - Human Knight|2|2|Whenever Syr Faren, the Hengehammer attacks, another target attacking creature gets +X/+X until end of turn, where X is Syr Faren's power.| Tall as a Beanstalk|Throne of Eldraine|178|C|{3}{G}|Enchantment - Aura|||Enchant creature$Enchanted creature gets +3/+3, has reach, and is a Giant in addition to its other types.| Trail of Crumbs|Throne of Eldraine|179|U|{1}{G}|Enchantment|||When Trail of Crumbs enters the battlefield, create a Food token.$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.| @@ -36207,7 +36229,7 @@ Wandermare|Throne of Eldraine|204|U|{1}{G}{W}|Creature - Horse|3|3|Whenever you Wintermoor Commander|Throne of Eldraine|205|U|{W}{B}|Creature - Human Knight|2|*|Deathtouch$Wintermoor Commander's toughness is equal to the number of Knights you control.$Whenever Wintermoor Commander attacks, another target Knight you control gains indestructible until end of turn.| Arcanist's Owl|Throne of Eldraine|206|U|{W/U}{W/U}{W/U}{W/U}|Artifact Creature - Bird|3|3|Flying$When Arcanist's Owl enters the battlefield, look at the top four cards of your library. You may reveal an artifact or enchantment card from among them and put it into your hand. Put the rest on the bottom of your library in a random order.| Covetous Urge|Throne of Eldraine|207|U|{U/B}{U/B}{U/B}{U/B}|Sorcery|||Target opponent reveals their hand. You choose a nonland card from that player's graveyard or hand and exile it. You may cast that card for as long as it remains exiled, and you may spend mana as though it were mana of any color to cast that spell.| -Deathless Knight|Throne of Eldraine|208|U|{B/G}{B/G}{B/G}{B/G}|Creature - Skeleton Knight|4|2|Haste$Whenever you gain life for the first time each turn, return Deathless Knight from your graveyard to your hand.| +Deathless Knight|Throne of Eldraine|208|U|{B/G}{B/G}{B/G}{B/G}|Creature - Skeleton Knight|4|2|Haste$When you gain life for the first time each turn, return Deathless Knight from your graveyard to your hand.| Elite Headhunter|Throne of Eldraine|209|U|{B/R}{B/R}{B/R}{B/R}|Creature - Human Knight|2|3|Menace${B/R}{B/R}{B/R}, Sacrifice another creature or an artifact: Elite Headhunter deals 2 damage to target creature or planeswalker.| Fireborn Knight|Throne of Eldraine|210|U|{R/W}{R/W}{R/W}{R/W}|Creature - Human Knight|2|3|Double strike${R/W}{R/W}{R/W}{R/W}: Fireborn Knight gets +1/+1 until end of turn.| Loch Dragon|Throne of Eldraine|211|U|{U/R}{U/R}{U/R}{U/R}|Creature - Dragon|3|2|Flying$Whenever Loch Dragon enters the battlefield or attacks, you may discard a card. If you do, draw a card.| @@ -36217,6 +36239,7 @@ Rampart Smasher|Throne of Eldraine|213|U|{R/G}{R/G}{R/G}{R/G}|Creature - Giant|5 Resolute Rider|Throne of Eldraine|214|U|{W/B}{W/B}{W/B}{W/B}|Creature - Human Knight|4|2|{W/B}{W/B}: Resolute Rider gains lifelink until end of turn.${W/B}{W/B}{W/B}: Resolute Rider gains indestructible until end of turn.| Thunderous Snapper|Throne of Eldraine|215|U|{G/U}{G/U}{G/U}{G/U}|Creature - Turtle Hydra|4|4|Whenever you cast a spell with converted mana cost 5 or greater, draw a card.| Clockwork Servant|Throne of Eldraine|216|U|{3}|Artifact Creature - Gnome|2|3|Adamant — When Clockwork Servant enters the battlefield, if at least three mana of the same color was spent to cast it, draw a card.| +Crashing Drawbridge|Throne of Eldraine|217|C|{2}|Artifact Creature - Wall|0|4|Defender${T}: Creatures you control gain haste until end of turn.| Enchanted Carriage|Throne of Eldraine|218|U|{5}|Artifact - Vehicle|4|4|When Enchanted Carriage enters the battlefield, create two 1/1 white Mouse creature tokens.$Crew 2| Gingerbrute|Throne of Eldraine|219|C|{1}|Artifact Creature - Food Golem|1|1|Haste${1}: Gingerbrute can't be blocked this turn except by creatures with haste.${2}, {T}, Sacrifice Gingerbrute: You gain 3 life.| Golden Egg|Throne of Eldraine|220|C|{2}|Artifact - Food|||When Golden Egg enters the battlefield, draw a card.${1}, {T}, Sacrifice Golden Egg: Add one mana of any color.${2}, {T}, Sacrifice Golden Egg: You gain 3 life.| @@ -36224,25 +36247,36 @@ Henge Walker|Throne of Eldraine|221|C|{3}|Artifact Creature - Golem|2|2|Adamant Heraldic Banner|Throne of Eldraine|222|U|{3}|Artifact|||As Heraldic Banner enters the battlefield, choose a color.$Creatures you control of the chosen color get +1/+0.${T}: Add one mana of the chosen color.| Inquisitive Puppet|Throne of Eldraine|223|U|{1}|Artifact Creature - Construct|0|2|When Inquisitive Puppet enters the battlefield, scry 1.$Exile Inquisitive Puppet: Create a 1/1 white Human creature token.| Jousting Dummy|Throne of Eldraine|224|C|{2}|Artifact Creature - Scarecrow Knight|2|1|{3}: Jousting Dummy gets +1/+0 until end of turn.| +Locthwain Gargoyle|Throne of Eldraine|225|C|{1}|Artifact Creature - Gargoyle|0|3|{4}: "Locthwain Gargoyle" gets +2/+0 and gains flying until end of turn.| Lucky Clover|Throne of Eldraine|226|U|{2}|Artifact|||Whenever you cast an Adventure instant or sorcery spell, copy it. You may choose new targets for the copy.| +Prophet of the Peak|Throne of Eldraine|227|C|{6}|Artifact Creature - Cat|5|5|When Prophet of the Peak enters the battlefield, scry 2.| Roving Keep|Throne of Eldraine|228|C|{7}|Artifact Creature - Wall|5|7|Defender${7}: Roving Keep gets +2/+0 and gains trample until end of turn. It can attack this turn as though it didn't have defender.| +Scalding Cauldron|Throne of Eldraine|229|C|{1}|Artifact|||{3}, {T}, Sacrifice Scalding Cauldron: It deals 3 damage to target creature.| Shambling Suit|Throne of Eldraine|230|U|{3}|Artifact Creature - Construct|*|3|Shambling Suit's power is equal to the number of artifacts and/or enchantments you control.| +Signpost Scarecrow|Throne of Eldraine|231|C|{4}|Artifact Creature - Scarecrow|2|4|Vigilance${2}: Add one mana of any color.| Sorcerer's Broom|Throne of Eldraine|232|U|{2}|Artifact Creature - Spirit|2|1|Whenever you sacrifice another permanent, you may pay {3}. If you do, create a token that's a copy of Sorcerer's Broom.| Sorcerous Spyglass|Throne of Eldraine|233|R|{2}|Artifact|||As Sorcerous Spyglass enters the battlefield, look at an opponent's hand, then choose any card name.$Activated abilities of sources with the chosen name can't be activated unless they're mana abilities.| Spinning Wheel|Throne of Eldraine|234|U|{3}|Artifact|||{T}: Add one mana of any color.${5}, {T}: Tap target creature.| Stonecoil Serpent|Throne of Eldraine|235|R|{X}|Artifact Creature - Snake|0|0|Reach, trample, protection from multicolored$Stonecoil Serpent enters the battlefield with X +1/+1 counters on it.| +Weapon Rack|Throne of Eldraine|236|C|{4}|Artifact|||Weapon Rack enters the battlefield with three +1/+1 counters on it.${T}: Move a +1/+1 counter from Weapon Rack onto target creature. Activate this ability only any time you could cast a sorcery.| Witch's Oven|Throne of Eldraine|237|U|{1}|Artifact|||{T}, Sacrifice a creature: Create a Food token. If the sacrificed creature's toughness was 4 or greater, create two Food tokens instead.| Castle Ardenvale|Throne of Eldraine|238|R||Land|||Castle Ardenvale enters the battlefield tapped unless you control a Plains.${T}: Add {W}.${2}{W}{W}, {T}: Create a 1/1 white Human creature token.| Castle Embereth|Throne of Eldraine|239|R||Land|||Castle Embereth enters the battlefield tapped unless you control a Mountain.${T}: Add {R}.${1}{R}{R}, {T}: Creatures you control get +1/+0 until end of turn.| Castle Garenbrig|Throne of Eldraine|240|R||Land|||Castle Garenbrig enters the battlefield tapped unless you control a Forest.${T}: Add {G}.${2}{G}{G}, {T}: Add six {G}. Spend this mana only to cast creature spells or activate abilities of creatures.| Castle Locthwain|Throne of Eldraine|241|R||Land|||Castle Locthwain enters the battlefield tapped unless you control a Swamp.${T}: Add {B}.${1}{B}{B}, {T}: Draw a card, then you lose life equal to the number of cards in your hand.| Castle Vantress|Throne of Eldraine|242|R||Land|||Castle Vantress enters the battlefield tapped unless you control an Island.${T}: Add {U}.${2}{U}{U}, {T}: Scry 2.| +Dwarven Mine|Throne of Eldraine|243|C||Land - Mountain|||({T}: Add {R}.)$Dwarven Mine enters the battlefield tapped unless you control three or more other Mountains.$When Dwarven Mine enters the battlefield untapped, create a 1/1 red Dwarf creature token.| Fabled Passage|Throne of Eldraine|244|R||Land|||{T}, Sacrifice Fabled Passage: Search your library for a basic land card, put it onto the battlefield tapped, then shuffle your library. Then if you control four or more lands, untap that land.| Gingerbread Cabin|Throne of Eldraine|245|C||Land - Forest|||({T}: Add {G}.)$Gingerbread Cabin enters the battlefield tapped unless you control three or more other Forests.$When Gingerbread Cabin enters the battlefield untapped, create a Food token.| Idyllic Grange|Throne of Eldraine|246|C||Land - Plains|||({T}: Add {W}.)$Idyllic Grange enters the battlefield tapped unless you control three or more other Plains.$When Idyllic Grange enters the battlefield untapped, put a +1/+1 counter on target creature you control.| Mystic Sanctuary|Throne of Eldraine|247|C||Land - Island|||({T}: Add {U}.)$Mystic Sanctuary enters the battlefield tapped unless you control three or more other Islands.$When Mystic Sanctuary enters the battlefield untapped, you may put target instant or sorcery card from your graveyard on top of your library.| Tournament Grounds|Throne of Eldraine|248|U||Land|||{T}: Add {C}.${T}: Add {R}, {W}, or {B}. Spend this mana only to cast a Knight or Equipment spell.| Witch's Cottage|Throne of Eldraine|249|C||Land - Swamp|||({T}: Add {B}.)$Witch's Cottage enters the battlefield tapped unless you control three or more other Swamps.$When Witch's Cottage enters the battlefield untapped, you may put target creature card from your graveyard on top of your library.| +Plains|Throne of Eldraine|250|C||Basic Land - Plains|||({T}: Add {W}.)| +Island|Throne of Eldraine|254|C||Basic Land - Island|||({T}: Add {U}.)| +Swamp|Throne of Eldraine|258|C||Basic Land - Swamp|||({T}: Add {B}.)| +Mountain|Throne of Eldraine|262|C||Basic Land - Mountain|||({T}: Add {R}.)| +Forest|Throne of Eldraine|266|C||Basic Land - Forest|||({T}: Add {G}.)| Kenrith, the Returned King|Throne of Eldraine|303|M|{4}{W}|Legendary Creature - Human Noble|5|5|{R}: All creatures gain trample and haste until end of turn.${1}{G}: Put a +1/+1 counter on target creature.${2}{W}: Target player gains 5 life.${3}{U}: Target player draws a card.${4}{B}: Put target creature card from a graveyard onto the battlefield under its owner's control.| Rowan, Fearless Sparkmage|Throne of Eldraine|304|M|{3}{R}{R}|Legendary Planeswalker - Rowan|5|+1: Up to one target creature gets +3/+0 and gains first strike until end of turn.$−2: Rowan, Fearless Sparkmage deals 1 damage to each of up to two target creatures. Those creatures can't block this turn.$−9: Gain control of all creatures until end of turn. Untap them. They gain haste until end of turn.| Garrison Griffin|Throne of Eldraine|305|C|{2}{W}|Creature - Griffin|2|2|Flying$Whenever Garrison Griffin attacks, target Knight you control gains flying until end of turn.| From 324aa51cfece1774cff4ce7a0433c4a99f81574d Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 20 Sep 2019 13:39:51 -0400 Subject: [PATCH 234/373] Implemented Charmed Sleep --- Mage.Sets/src/mage/cards/c/CharmedSleep.java | 52 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 53 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/c/CharmedSleep.java diff --git a/Mage.Sets/src/mage/cards/c/CharmedSleep.java b/Mage.Sets/src/mage/cards/c/CharmedSleep.java new file mode 100644 index 0000000000..41daf61253 --- /dev/null +++ b/Mage.Sets/src/mage/cards/c/CharmedSleep.java @@ -0,0 +1,52 @@ +package mage.cards.c; + +import mage.abilities.Ability; +import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.effects.common.AttachEffect; +import mage.abilities.effects.common.DontUntapInControllersUntapStepEnchantedEffect; +import mage.abilities.effects.common.TapEnchantedEffect; +import mage.abilities.keyword.EnchantAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Outcome; +import mage.constants.SubType; +import mage.target.TargetPermanent; +import mage.target.common.TargetCreaturePermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class CharmedSleep extends CardImpl { + + public CharmedSleep(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ENCHANTMENT}, "{1}{U}{U}"); + + this.subtype.add(SubType.AURA); + + // Enchant creature + TargetPermanent auraTarget = new TargetCreaturePermanent(); + this.getSpellAbility().addTarget(auraTarget); + this.getSpellAbility().addEffect(new AttachEffect(Outcome.BoostCreature)); + Ability ability = new EnchantAbility(auraTarget.getTargetName()); + this.addAbility(ability); + + // When Charmed Sleep enters the battlefield, tap enchanted creature. + this.addAbility(new EntersBattlefieldTriggeredAbility(new TapEnchantedEffect())); + + // Enchanted creature doesn't untap during its controller's untap step. + this.addAbility(new SimpleStaticAbility(new DontUntapInControllersUntapStepEnchantedEffect())); + } + + private CharmedSleep(final CharmedSleep card) { + super(card); + } + + @Override + public CharmedSleep copy() { + return new CharmedSleep(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index dbab649397..3475dc2929 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -60,6 +60,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Castle Vantress", 242, Rarity.RARE, mage.cards.c.CastleVantress.class)); cards.add(new SetCardInfo("Cauldron Familiar", 81, Rarity.UNCOMMON, mage.cards.c.CauldronFamiliar.class)); cards.add(new SetCardInfo("Cauldron's Gift", 83, Rarity.UNCOMMON, mage.cards.c.CauldronsGift.class)); + cards.add(new SetCardInfo("Charmed Sleep", 40, Rarity.COMMON, mage.cards.c.CharmedSleep.class)); cards.add(new SetCardInfo("Charming Prince", 8, Rarity.RARE, mage.cards.c.CharmingPrince.class)); cards.add(new SetCardInfo("Chittering Witch", 319, Rarity.RARE, mage.cards.c.ChitteringWitch.class)); cards.add(new SetCardInfo("Chulane, Teller of Tales", 326, Rarity.MYTHIC, mage.cards.c.ChulaneTellerOfTales.class)); From 8fdf7f3b3a9b76b2b42ff778be626ff51c00521f Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 20 Sep 2019 13:42:00 -0400 Subject: [PATCH 235/373] Implemented Crashing Drawbridge --- .../src/mage/cards/c/CrashingDrawbridge.java | 47 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 48 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/c/CrashingDrawbridge.java diff --git a/Mage.Sets/src/mage/cards/c/CrashingDrawbridge.java b/Mage.Sets/src/mage/cards/c/CrashingDrawbridge.java new file mode 100644 index 0000000000..fedc767115 --- /dev/null +++ b/Mage.Sets/src/mage/cards/c/CrashingDrawbridge.java @@ -0,0 +1,47 @@ +package mage.cards.c; + +import mage.MageInt; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.costs.common.TapSourceCost; +import mage.abilities.effects.common.continuous.GainAbilityControlledEffect; +import mage.abilities.keyword.DefenderAbility; +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.filter.StaticFilters; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class CrashingDrawbridge extends CardImpl { + + public CrashingDrawbridge(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT, CardType.CREATURE}, "{2}"); + + this.subtype.add(SubType.WALL); + this.power = new MageInt(0); + this.toughness = new MageInt(4); + + // Defender + this.addAbility(DefenderAbility.getInstance()); + + // {T}: Creatures you control gain haste until end of turn. + this.addAbility(new SimpleActivatedAbility(new GainAbilityControlledEffect( + HasteAbility.getInstance(), Duration.EndOfTurn, StaticFilters.FILTER_PERMANENT_CREATURES + ), new TapSourceCost())); + } + + private CrashingDrawbridge(final CrashingDrawbridge card) { + super(card); + } + + @Override + public CrashingDrawbridge copy() { + return new CrashingDrawbridge(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 3475dc2929..780b80b170 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -69,6 +69,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Clockwork Servant", 216, Rarity.UNCOMMON, mage.cards.c.ClockworkServant.class)); cards.add(new SetCardInfo("Command Tower", 333, Rarity.COMMON, mage.cards.c.CommandTower.class)); cards.add(new SetCardInfo("Corridor Monitor", 41, Rarity.COMMON, mage.cards.c.CorridorMonitor.class)); + cards.add(new SetCardInfo("Crashing Drawbridge", 217, Rarity.COMMON, mage.cards.c.CrashingDrawbridge.class)); cards.add(new SetCardInfo("Crystal Slipper", 119, Rarity.COMMON, mage.cards.c.CrystalSlipper.class)); cards.add(new SetCardInfo("Curious Pair", 150, Rarity.COMMON, mage.cards.c.CuriousPair.class)); cards.add(new SetCardInfo("Dance of the Manse", 186, Rarity.RARE, mage.cards.d.DanceOfTheManse.class)); From ba03bb50a3f45784450e2b96d320c27e98496c6f Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 20 Sep 2019 13:44:57 -0400 Subject: [PATCH 236/373] Implemented Locthwain Gargoyle --- .../src/mage/cards/l/LocthwainGargoyle.java | 48 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 49 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/l/LocthwainGargoyle.java diff --git a/Mage.Sets/src/mage/cards/l/LocthwainGargoyle.java b/Mage.Sets/src/mage/cards/l/LocthwainGargoyle.java new file mode 100644 index 0000000000..3337259447 --- /dev/null +++ b/Mage.Sets/src/mage/cards/l/LocthwainGargoyle.java @@ -0,0 +1,48 @@ +package mage.cards.l; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.costs.mana.GenericManaCost; +import mage.abilities.effects.common.continuous.BoostSourceEffect; +import mage.abilities.effects.common.continuous.GainAbilitySourceEffect; +import mage.abilities.keyword.FlyingAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class LocthwainGargoyle extends CardImpl { + + public LocthwainGargoyle(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT, CardType.CREATURE}, "{1}"); + + this.subtype.add(SubType.GARGOYLE); + this.power = new MageInt(0); + this.toughness = new MageInt(3); + + // {4}: Locthwain Gargoyle gets +2/+0 and gains flying until end of turn. + Ability ability = new SimpleActivatedAbility(new BoostSourceEffect( + 2, 0, Duration.EndOfTurn).setText("{this} gets +2/+0" + ), new GenericManaCost(4)); + ability.addEffect(new GainAbilitySourceEffect( + FlyingAbility.getInstance(), Duration.EndOfTurn + ).setText("and gains flying until end of turn")); + this.addAbility(ability); + } + + private LocthwainGargoyle(final LocthwainGargoyle card) { + super(card); + } + + @Override + public LocthwainGargoyle copy() { + return new LocthwainGargoyle(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 780b80b170..8c5e09bb5d 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -156,6 +156,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Linden, the Steadfast Queen", 20, Rarity.RARE, mage.cards.l.LindenTheSteadfastQueen.class)); cards.add(new SetCardInfo("Loch Dragon", 211, Rarity.UNCOMMON, mage.cards.l.LochDragon.class)); cards.add(new SetCardInfo("Lochmere Serpent", 195, Rarity.RARE, mage.cards.l.LochmereSerpent.class)); + cards.add(new SetCardInfo("Locthwain Gargoyle", 225, Rarity.COMMON, mage.cards.l.LocthwainGargoyle.class)); cards.add(new SetCardInfo("Locthwain Paladin", 93, Rarity.COMMON, mage.cards.l.LocthwainPaladin.class)); cards.add(new SetCardInfo("Lonesome Unicorn", 21, Rarity.COMMON, mage.cards.l.LonesomeUnicorn.class)); cards.add(new SetCardInfo("Lost Legion", 94, Rarity.COMMON, mage.cards.l.LostLegion.class)); From 569eb27a4e6e049ee960e714d403f97cebe8fcde Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 20 Sep 2019 13:45:50 -0400 Subject: [PATCH 237/373] Implemented Prized Griffin --- Mage.Sets/src/mage/cards/p/PrizedGriffin.java | 36 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 37 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/p/PrizedGriffin.java diff --git a/Mage.Sets/src/mage/cards/p/PrizedGriffin.java b/Mage.Sets/src/mage/cards/p/PrizedGriffin.java new file mode 100644 index 0000000000..5487a3b732 --- /dev/null +++ b/Mage.Sets/src/mage/cards/p/PrizedGriffin.java @@ -0,0 +1,36 @@ +package mage.cards.p; + +import mage.MageInt; +import mage.abilities.keyword.FlyingAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class PrizedGriffin extends CardImpl { + + public PrizedGriffin(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{4}{W}"); + + this.subtype.add(SubType.GRIFFIN); + this.power = new MageInt(3); + this.toughness = new MageInt(4); + + // Flying + this.addAbility(FlyingAbility.getInstance()); + } + + private PrizedGriffin(final PrizedGriffin card) { + super(card); + } + + @Override + public PrizedGriffin copy() { + return new PrizedGriffin(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 8c5e09bb5d..ce09234172 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -199,6 +199,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Plains", 251, Rarity.LAND, mage.cards.basiclands.Plains.class, NON_FULL_USE_VARIOUS)); cards.add(new SetCardInfo("Plains", 252, Rarity.LAND, mage.cards.basiclands.Plains.class, NON_FULL_USE_VARIOUS)); cards.add(new SetCardInfo("Plains", 253, Rarity.LAND, mage.cards.basiclands.Plains.class, NON_FULL_USE_VARIOUS)); + cards.add(new SetCardInfo("Prized Griffin", 24, Rarity.COMMON, mage.cards.p.PrizedGriffin.class)); cards.add(new SetCardInfo("Questing Beast", 171, Rarity.MYTHIC, mage.cards.q.QuestingBeast.class)); cards.add(new SetCardInfo("Raging Redcap", 134, Rarity.COMMON, mage.cards.r.RagingRedcap.class)); cards.add(new SetCardInfo("Rally for the Throne", 25, Rarity.UNCOMMON, mage.cards.r.RallyForTheThrone.class)); From 6f2e9c44f5d71f2029b6d8a33adc027389c70486 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 20 Sep 2019 15:25:20 -0400 Subject: [PATCH 238/373] fixed a test failure --- Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index ce09234172..d5c3d15f67 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -20,13 +20,12 @@ public final class ThroneOfEldraine extends ExpansionSet { super("Throne of Eldraine", "ELD", ExpansionSet.buildDate(2019, 10, 4), SetType.EXPANSION); this.blockName = "Throne of Eldraine"; this.hasBoosters = true; - this.hasBasicLands = false;// false until basics officially spoiled this.numBoosterLands = 1; this.numBoosterCommon = 10; this.numBoosterUncommon = 3; this.numBoosterRare = 1; this.ratioBoosterMythic = 8; - this.maxCardNumberInBooster = 269; // unconfirmed for now + this.maxCardNumberInBooster = 269; cards.add(new SetCardInfo("Acclaimed Contender", 1, Rarity.RARE, mage.cards.a.AcclaimedContender.class)); cards.add(new SetCardInfo("Alela, Artful Provocateur", 324, Rarity.MYTHIC, mage.cards.a.AlelaArtfulProvocateur.class)); From af5b85c8cd6a641196725148885da7cad9566ecd Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 20 Sep 2019 18:45:52 -0400 Subject: [PATCH 239/373] updated ELD spoiler --- Utils/mtg-cards-data.txt | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index dbb0159d3c..0d8209f081 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -36006,7 +36006,7 @@ The Circle of Loyalty|Throne of Eldraine|9|M|{4}{W}{W}|Legendary Artifact|||This Deafening Silence|Throne of Eldraine|10|U|{W}|Enchantment|||Each player can't cast more than one noncreature spell each turn.| Faerie Guidemother|Throne of Eldraine|11|C|{W}|Creature - Faerie|1|1|Flying| Gift of the Fae|Throne of Eldraine|11|C|{1}{W}|Sorcery - Adventure|1|1|Target creature gets +2/+1 and gains flying until end of turn.| -Flutterfox|Throne of Eldraine|12|C|{1}{W}|Creature - Fox|||As long as you control an artifact or enchantment, Flutterfox has flying.| +Flutterfox|Throne of Eldraine|12|C|{1}{W}|Creature - Fox|2|2|As long as you control an artifact or enchantment, Flutterfox has flying.| Fortifying Provisions|Throne of Eldraine|13|C|{2}{W}|Enchantment|||Creatures you control get +0/+1.$When Fortifying Provisions enters the battlefield, create a Food token.| Chop Down|Throne of Eldraine|14|R|{2}{W}|Instant - Adventure|1|2|Destroy target creature with power 4 or greater.| Giant Killer|Throne of Eldraine|14|R|{W}|Creature - Human Peasant|1|2|{1}{W}, {T}: Tap target creature.| @@ -36020,7 +36020,7 @@ Lonesome Unicorn|Throne of Eldraine|21|C|{4}{W}|Creature - Unicorn|3|3|Vigilance Rider in Need|Throne of Eldraine|21|C|{2}{W}|Sorcery - Adventure|3|3|Create a 2/2 white Knight creature token with vigilance.| Mysterious Pathlighter|Throne of Eldraine|22|U|{2}{W}|Creature - Faerie|2|2|Flying$Each creature you control that has an Adventure enters the battlefield with an additional +1/+1 counter on it.| Outflank|Throne of Eldraine|23|C|{W}|Instant|||Outflank deals damage to target attacking or blocking creature equal to the number of creatures you control.| -Prized Griffin|Throne of Eldraine|24|C|{4}{W}|Creature - Griffin|||Flying| +Prized Griffin|Throne of Eldraine|24|C|{4}{W}|Creature - Griffin|3|4|Flying| Rally for the Throne|Throne of Eldraine|25|U|{2}{W}|Instant|||Create two 1/1 white Human creature tokens.$Adamant — If at least three white mana was spent to cast this spell, you gain 1 life for each creature you control.| Cast Off|Throne of Eldraine|26|M|{3}{W}{W}|Sorcery - Adventure|7|7|Destroy all non-Giant creatures.| Realm-Cloaked Giant|Throne of Eldraine|26|M|{5}{W}{W}|Creature - Giant|7|7|Vigilance| @@ -36043,7 +36043,7 @@ Brazen Borrower|Throne of Eldraine|39|M|{1}{U}{U}|Creature - Faerie Rogue|3|1|Fl Petty Theft|Throne of Eldraine|39|M|{1}{U}|Instant - Adventure|3|1|Return target nonland permanent an opponent controls to its owner's hand.| Charmed Sleep|Throne of Eldraine|40|C|{1}{U}{U}|Enchantment - Aura|||Enchant creature$When Charmed Sleep enters the battlefield, tap enchanted creature.$Enchanted creature doesn't untap during its controller's untap step.| Corridor Monitor|Throne of Eldraine|41|C|{1}{U}|Artifact Creature - Construct|1|4|When Corridor Monitor enters the battlefield, untap target artifact or creature you control.| -Didn't Say Please|Throne of Eldraine|42|C|{1}{U}{U}|Instant|||Counter target spell. its controller puts the top three cards of their library into their graveyard.| +Didn't Say Please|Throne of Eldraine|42|C|{1}{U}{U}|Instant|||Counter target spell. Its controller puts the top three cards of their library into their graveyard.| Emry, Lurker of the Loch|Throne of Eldraine|43|R|{2}{U}|Legendary Creature - Merfolk Wizard|1|2|This spell costs {1} less to cast for each artifact you control.$When Emry, Lurker of the Loch enters the battlefield, put the top four cards of your library into your graveyard.${T}: Choose target artifact card in your graveyard. You may cast that card this turn.| Fae of Wishes|Throne of Eldraine|44|R|{1}{U}|Creature - Faerie Wizard|1|4|Flying${1}{U}, Discard two cards: Return Fae of Wishes to its owner's hand.| Granted|Throne of Eldraine|44|R|{3}{U}|Sorcery - Adventure|1|4|You may choose a noncreature card you own from outside the game, reveal it, and put it into your hand.| @@ -36111,7 +36111,7 @@ Order of Midnight|Throne of Eldraine|99|U|{1}{B}|Creature - Human Knight|2|2|Fly Piper of the Swarm|Throne of Eldraine|100|R|{1}{B}|Creature - Human Warlock|1|3|Rats you control have menace.${1}{B}, {T}: Create a 1/1 black Rat creature token.${2}{B}{B}, {T}, Sacrifice three Rats: Gain control of target creature.| Rankle, Master of Pranks|Throne of Eldraine|101|M|{2}{B}{B}|Legendary Creature - Faerie Rogue|3|3|Flying, haste$Whenever Rankle, Master of Pranks deals combat damage to a player, choose any number —$• Each player discards a card.$• Each player loses 1 life and draws a card.$• Each player sacrifices a creature.| Harvest Fear|Throne of Eldraine|102|C|{3}{B}|Sorcery - Adventure|4|5|Target opponent discards two cards.| -Reaper of Night|Throne of Eldraine|102|C|{5}{B}{B}|Creature - Specter|4|5|Whenever Reaper of Night attacks, if defending player hass two or fewer cards in hand, it gains flying until end of turn.| +Reaper of Night|Throne of Eldraine|102|C|{5}{B}{B}|Creature - Specter|4|5|Whenever Reaper of Night attacks, if defending player has two or fewer cards in hand, it gains flying until end of turn.| Reave Soul|Throne of Eldraine|103|C|{1}{B}|Sorcery|||Destroy target creature with power 3 or less.| Revenge of Ravens|Throne of Eldraine|104|U|{3}{B}|Enchantment|||Whenever a creature attacks you or a planeswalker you control, that creature's controller loses 1 life and you gain 1 life.| Curry Favor|Throne of Eldraine|105|C|{B}|Sorcery - Adventure|2|1|You gain X life and each opponent loses X life, where X is the number of Knights you control.| @@ -36247,7 +36247,7 @@ Henge Walker|Throne of Eldraine|221|C|{3}|Artifact Creature - Golem|2|2|Adamant Heraldic Banner|Throne of Eldraine|222|U|{3}|Artifact|||As Heraldic Banner enters the battlefield, choose a color.$Creatures you control of the chosen color get +1/+0.${T}: Add one mana of the chosen color.| Inquisitive Puppet|Throne of Eldraine|223|U|{1}|Artifact Creature - Construct|0|2|When Inquisitive Puppet enters the battlefield, scry 1.$Exile Inquisitive Puppet: Create a 1/1 white Human creature token.| Jousting Dummy|Throne of Eldraine|224|C|{2}|Artifact Creature - Scarecrow Knight|2|1|{3}: Jousting Dummy gets +1/+0 until end of turn.| -Locthwain Gargoyle|Throne of Eldraine|225|C|{1}|Artifact Creature - Gargoyle|0|3|{4}: "Locthwain Gargoyle" gets +2/+0 and gains flying until end of turn.| +Locthwain Gargoyle|Throne of Eldraine|225|C|{1}|Artifact Creature - Gargoyle|0|3|{4}: Locthwain Gargoyle gets +2/+0 and gains flying until end of turn.| Lucky Clover|Throne of Eldraine|226|U|{2}|Artifact|||Whenever you cast an Adventure instant or sorcery spell, copy it. You may choose new targets for the copy.| Prophet of the Peak|Throne of Eldraine|227|C|{6}|Artifact Creature - Cat|5|5|When Prophet of the Peak enters the battlefield, scry 2.| Roving Keep|Throne of Eldraine|228|C|{7}|Artifact Creature - Wall|5|7|Defender${7}: Roving Keep gets +2/+0 and gains trample until end of turn. It can attack this turn as though it didn't have defender.| From 9f52aea05ddf98f6a7931cfce3f778a9b6ba4de8 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 20 Sep 2019 18:51:54 -0400 Subject: [PATCH 240/373] Implemented Prophet of the Peak --- .../src/mage/cards/p/ProphetOfThePeak.java | 37 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 38 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/p/ProphetOfThePeak.java diff --git a/Mage.Sets/src/mage/cards/p/ProphetOfThePeak.java b/Mage.Sets/src/mage/cards/p/ProphetOfThePeak.java new file mode 100644 index 0000000000..3f55e1e3f2 --- /dev/null +++ b/Mage.Sets/src/mage/cards/p/ProphetOfThePeak.java @@ -0,0 +1,37 @@ +package mage.cards.p; + +import mage.MageInt; +import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.effects.keyword.ScryEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class ProphetOfThePeak extends CardImpl { + + public ProphetOfThePeak(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT, CardType.CREATURE}, "{6}"); + + this.subtype.add(SubType.CAT); + this.power = new MageInt(5); + this.toughness = new MageInt(5); + + // When Prophet of the Peak enters the battlefield, scry 2. + this.addAbility(new EntersBattlefieldTriggeredAbility(new ScryEffect(2))); + } + + private ProphetOfThePeak(final ProphetOfThePeak card) { + super(card); + } + + @Override + public ProphetOfThePeak copy() { + return new ProphetOfThePeak(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index d5c3d15f67..eb6b8ff8f3 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -199,6 +199,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Plains", 252, Rarity.LAND, mage.cards.basiclands.Plains.class, NON_FULL_USE_VARIOUS)); cards.add(new SetCardInfo("Plains", 253, Rarity.LAND, mage.cards.basiclands.Plains.class, NON_FULL_USE_VARIOUS)); cards.add(new SetCardInfo("Prized Griffin", 24, Rarity.COMMON, mage.cards.p.PrizedGriffin.class)); + cards.add(new SetCardInfo("Prophet of the Peak", 227, Rarity.COMMON, mage.cards.p.ProphetOfThePeak.class)); cards.add(new SetCardInfo("Questing Beast", 171, Rarity.MYTHIC, mage.cards.q.QuestingBeast.class)); cards.add(new SetCardInfo("Raging Redcap", 134, Rarity.COMMON, mage.cards.r.RagingRedcap.class)); cards.add(new SetCardInfo("Rally for the Throne", 25, Rarity.UNCOMMON, mage.cards.r.RallyForTheThrone.class)); From 6578dbc3d89942a2a3d6336570d674e87bf6553d Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 20 Sep 2019 18:55:59 -0400 Subject: [PATCH 241/373] Implemented Signpost Scarecrow --- .../src/mage/cards/s/SignpostScarecrow.java | 41 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 42 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/s/SignpostScarecrow.java diff --git a/Mage.Sets/src/mage/cards/s/SignpostScarecrow.java b/Mage.Sets/src/mage/cards/s/SignpostScarecrow.java new file mode 100644 index 0000000000..a68cf6434c --- /dev/null +++ b/Mage.Sets/src/mage/cards/s/SignpostScarecrow.java @@ -0,0 +1,41 @@ +package mage.cards.s; + +import mage.MageInt; +import mage.abilities.costs.mana.GenericManaCost; +import mage.abilities.keyword.VigilanceAbility; +import mage.abilities.mana.AnyColorManaAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class SignpostScarecrow extends CardImpl { + + public SignpostScarecrow(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT, CardType.CREATURE}, "{4}"); + + this.subtype.add(SubType.SCARECROW); + this.power = new MageInt(2); + this.toughness = new MageInt(4); + + // Vigilance + this.addAbility(VigilanceAbility.getInstance()); + + // {2}: Add one mana of any color. + this.addAbility(new AnyColorManaAbility(new GenericManaCost(2))); + } + + private SignpostScarecrow(final SignpostScarecrow card) { + super(card); + } + + @Override + public SignpostScarecrow copy() { + return new SignpostScarecrow(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index eb6b8ff8f3..89c49183b8 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -232,6 +232,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Shimmer Dragon", 317, Rarity.RARE, mage.cards.s.ShimmerDragon.class)); cards.add(new SetCardInfo("Shinechaser", 201, Rarity.UNCOMMON, mage.cards.s.Shinechaser.class)); cards.add(new SetCardInfo("Shining Armor", 29, Rarity.COMMON, mage.cards.s.ShiningArmor.class)); + cards.add(new SetCardInfo("Signpost Scarecrow", 231, Rarity.COMMON, mage.cards.s.SignpostScarecrow.class)); cards.add(new SetCardInfo("Silverflame Ritual", 30, Rarity.COMMON, mage.cards.s.SilverflameRitual.class)); cards.add(new SetCardInfo("Silverflame Squire", 31, Rarity.COMMON, mage.cards.s.SilverflameSquire.class)); cards.add(new SetCardInfo("Silverwing Squadron", 315, Rarity.RARE, mage.cards.s.SilverwingSquadron.class)); From a31bf66bee09104047f3ae1585d713f93b4feb4f Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 20 Sep 2019 19:06:22 -0400 Subject: [PATCH 242/373] Implemented Moonlit Scavengers --- .../src/mage/cards/m/MoonlitScavengers.java | 61 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 62 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/m/MoonlitScavengers.java diff --git a/Mage.Sets/src/mage/cards/m/MoonlitScavengers.java b/Mage.Sets/src/mage/cards/m/MoonlitScavengers.java new file mode 100644 index 0000000000..e3a3872292 --- /dev/null +++ b/Mage.Sets/src/mage/cards/m/MoonlitScavengers.java @@ -0,0 +1,61 @@ +package mage.cards.m; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.condition.Condition; +import mage.abilities.condition.common.PermanentsOnTheBattlefieldCondition; +import mage.abilities.decorator.ConditionalInterveningIfTriggeredAbility; +import mage.abilities.effects.common.ReturnToHandTargetEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.constants.TargetController; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterArtifactOrEnchantmentPermanent; +import mage.filter.predicate.permanent.ControllerPredicate; +import mage.target.common.TargetOpponentsCreaturePermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class MoonlitScavengers extends CardImpl { + + private static final FilterPermanent filter = new FilterArtifactOrEnchantmentPermanent(); + + static { + filter.add(new ControllerPredicate(TargetController.YOU)); + } + + private static final Condition condition = new PermanentsOnTheBattlefieldCondition(filter); + + public MoonlitScavengers(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{5}{U}"); + + this.subtype.add(SubType.MERFOLK); + this.subtype.add(SubType.ROGUE); + this.power = new MageInt(4); + this.toughness = new MageInt(5); + + // When Moonlit Scavengers enters the battlefield, if you control an artifact or enchantment, return target creature an opponent controls to its owner's hand. + Ability ability = new ConditionalInterveningIfTriggeredAbility( + new EntersBattlefieldTriggeredAbility(new ReturnToHandTargetEffect()), condition, + "When {this} enters the battlefield, if you control an artifact or enchantment, " + + "return target creature an opponent controls to its owner's hand." + ); + ability.addTarget(new TargetOpponentsCreaturePermanent()); + this.addAbility(ability); + } + + private MoonlitScavengers(final MoonlitScavengers card) { + super(card); + } + + @Override + public MoonlitScavengers copy() { + return new MoonlitScavengers(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 89c49183b8..6a72e35ca0 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -170,6 +170,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Midnight Clock", 54, Rarity.RARE, mage.cards.m.MidnightClock.class)); cards.add(new SetCardInfo("Mirrormade", 55, Rarity.RARE, mage.cards.m.Mirrormade.class)); cards.add(new SetCardInfo("Mistford River Turtle", 56, Rarity.COMMON, mage.cards.m.MistfordRiverTurtle.class)); + cards.add(new SetCardInfo("Moonlit Scavengers", 57, Rarity.COMMON, mage.cards.m.MoonlitScavengers.class)); cards.add(new SetCardInfo("Mountain", 262, Rarity.LAND, mage.cards.basiclands.Mountain.class, NON_FULL_USE_VARIOUS)); cards.add(new SetCardInfo("Mountain", 263, Rarity.LAND, mage.cards.basiclands.Mountain.class, NON_FULL_USE_VARIOUS)); cards.add(new SetCardInfo("Mountain", 264, Rarity.LAND, mage.cards.basiclands.Mountain.class, NON_FULL_USE_VARIOUS)); From 16ab270da52ec8a61d1798f7db08f6ffcc95bd15 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 20 Sep 2019 19:13:32 -0400 Subject: [PATCH 243/373] Implemented Flutterfox --- Mage.Sets/src/mage/cards/f/Flutterfox.java | 57 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 58 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/f/Flutterfox.java diff --git a/Mage.Sets/src/mage/cards/f/Flutterfox.java b/Mage.Sets/src/mage/cards/f/Flutterfox.java new file mode 100644 index 0000000000..aaf6b55a8f --- /dev/null +++ b/Mage.Sets/src/mage/cards/f/Flutterfox.java @@ -0,0 +1,57 @@ +package mage.cards.f; + +import mage.MageInt; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.condition.Condition; +import mage.abilities.condition.common.PermanentsOnTheBattlefieldCondition; +import mage.abilities.decorator.ConditionalContinuousEffect; +import mage.abilities.effects.common.continuous.GainAbilitySourceEffect; +import mage.abilities.keyword.FlyingAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; +import mage.constants.TargetController; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterArtifactOrEnchantmentPermanent; +import mage.filter.predicate.permanent.ControllerPredicate; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class Flutterfox extends CardImpl { + + private static final FilterPermanent filter = new FilterArtifactOrEnchantmentPermanent(); + + static { + filter.add(new ControllerPredicate(TargetController.YOU)); + } + + private static final Condition condition = new PermanentsOnTheBattlefieldCondition(filter); + + public Flutterfox(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{1}{W}"); + + this.subtype.add(SubType.FOX); + this.power = new MageInt(2); + this.toughness = new MageInt(2); + + // As long as you control an artifact or enchantment, Flutterfox has flying. + this.addAbility(new SimpleStaticAbility(new ConditionalContinuousEffect( + new GainAbilitySourceEffect(FlyingAbility.getInstance(), Duration.WhileOnBattlefield), + condition, "As long as you control an artifact or enchantment, {this} has flying." + ))); + } + + private Flutterfox(final Flutterfox card) { + super(card); + } + + @Override + public Flutterfox copy() { + return new Flutterfox(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 6a72e35ca0..055316db26 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -102,6 +102,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Fires of Invention", 125, Rarity.RARE, mage.cards.f.FiresOfInvention.class)); cards.add(new SetCardInfo("Flaxen Intruder", 155, Rarity.UNCOMMON, mage.cards.f.FlaxenIntruder.class)); cards.add(new SetCardInfo("Fling", 126, Rarity.COMMON, mage.cards.f.Fling.class)); + cards.add(new SetCardInfo("Flutterfox", 12, Rarity.COMMON, mage.cards.f.Flutterfox.class)); cards.add(new SetCardInfo("Folio of Fancies", 46, Rarity.RARE, mage.cards.f.FolioOfFancies.class)); cards.add(new SetCardInfo("Foreboding Fruit", 88, Rarity.COMMON, mage.cards.f.ForebodingFruit.class)); cards.add(new SetCardInfo("Forest", 266, Rarity.LAND, mage.cards.basiclands.Forest.class, NON_FULL_USE_VARIOUS)); From 6d81d91f52926d0653ec50359509b5f15c7ea1b1 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 20 Sep 2019 19:21:24 -0400 Subject: [PATCH 244/373] Implemented Malevolent Noble --- .../src/mage/cards/m/MalevolentNoble.java | 73 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 74 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/m/MalevolentNoble.java diff --git a/Mage.Sets/src/mage/cards/m/MalevolentNoble.java b/Mage.Sets/src/mage/cards/m/MalevolentNoble.java new file mode 100644 index 0000000000..4c7f6ff3bf --- /dev/null +++ b/Mage.Sets/src/mage/cards/m/MalevolentNoble.java @@ -0,0 +1,73 @@ +package mage.cards.m; + +import mage.MageInt; +import mage.MageObject; +import mage.abilities.Ability; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.costs.common.SacrificeTargetCost; +import mage.abilities.costs.mana.GenericManaCost; +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.counters.CounterType; +import mage.filter.common.FilterControlledPermanent; +import mage.filter.predicate.ObjectSourcePlayer; +import mage.filter.predicate.ObjectSourcePlayerPredicate; +import mage.game.Game; +import mage.target.common.TargetControlledPermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class MalevolentNoble extends CardImpl { + + private static final FilterControlledPermanent filter + = new FilterControlledPermanent("an artifact or another creature"); + + static { + filter.add(MalevolentNoblePredicate.instance); + } + + public MalevolentNoble(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{1}{B}"); + + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.NOBLE); + this.power = new MageInt(2); + this.toughness = new MageInt(2); + + // {2}, Sacrifice an artifact or another creature: Put a +1/+1 counter on Malevolent Noble. + Ability ability = new SimpleActivatedAbility( + new AddCountersSourceEffect(CounterType.P1P1.createInstance()), new GenericManaCost(2) + ); + ability.addCost(new SacrificeTargetCost(new TargetControlledPermanent(filter))); + this.addAbility(ability); + } + + private MalevolentNoble(final MalevolentNoble card) { + super(card); + } + + @Override + public MalevolentNoble copy() { + return new MalevolentNoble(this); + } +} + +enum MalevolentNoblePredicate implements ObjectSourcePlayerPredicate> { + instance; + + @Override + public boolean apply(ObjectSourcePlayer input, Game game) { + MageObject obj = input.getObject(); + if (obj.getId().equals(input.getSourceId())) { + return obj.isArtifact(); + } + return obj.isArtifact() + || obj.isCreature(); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 055316db26..d3ad0ffa23 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -164,6 +164,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Lucky Clover", 226, Rarity.UNCOMMON, mage.cards.l.LuckyClover.class)); cards.add(new SetCardInfo("Mace of the Valiant", 314, Rarity.RARE, mage.cards.m.MaceOfTheValiant.class)); cards.add(new SetCardInfo("Mad Ratter", 130, Rarity.UNCOMMON, mage.cards.m.MadRatter.class)); + cards.add(new SetCardInfo("Malevolent Noble", 95, Rarity.COMMON, mage.cards.m.MalevolentNoble.class)); cards.add(new SetCardInfo("Mantle of Tides", 52, Rarity.COMMON, mage.cards.m.MantleOfTides.class)); cards.add(new SetCardInfo("Maraleaf Pixie", 196, Rarity.UNCOMMON, mage.cards.m.MaraleafPixie.class)); cards.add(new SetCardInfo("Maraleaf Rider", 166, Rarity.COMMON, mage.cards.m.MaraleafRider.class)); From baf9dbabc5a77e2f2c25d38161a1b6e5008f85ee Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 20 Sep 2019 19:24:04 -0400 Subject: [PATCH 245/373] Implemented Lash of Thorns --- Mage.Sets/src/mage/cards/l/LashOfThorns.java | 40 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 41 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/l/LashOfThorns.java diff --git a/Mage.Sets/src/mage/cards/l/LashOfThorns.java b/Mage.Sets/src/mage/cards/l/LashOfThorns.java new file mode 100644 index 0000000000..ecf2961622 --- /dev/null +++ b/Mage.Sets/src/mage/cards/l/LashOfThorns.java @@ -0,0 +1,40 @@ +package mage.cards.l; + +import mage.abilities.effects.common.continuous.BoostTargetEffect; +import mage.abilities.effects.common.continuous.GainAbilityTargetEffect; +import mage.abilities.keyword.DeathtouchAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.target.common.TargetCreaturePermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class LashOfThorns extends CardImpl { + + public LashOfThorns(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.INSTANT}, "{B}"); + + // Target creature gets +2/+1 and gains deathtouch until end of turn. + this.getSpellAbility().addEffect(new BoostTargetEffect( + 2, 1, Duration.EndOfTurn + ).setText("target creature gets +2/+1")); + this.getSpellAbility().addEffect(new GainAbilityTargetEffect( + DeathtouchAbility.getInstance(), Duration.EndOfTurn + ).setText("and gains deathtouch until end of turn")); + this.getSpellAbility().addTarget(new TargetCreaturePermanent()); + } + + private LashOfThorns(final LashOfThorns card) { + super(card); + } + + @Override + public LashOfThorns copy() { + return new LashOfThorns(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index d3ad0ffa23..1f3bf67db9 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -153,6 +153,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Knight of the Keep", 19, Rarity.COMMON, mage.cards.k.KnightOfTheKeep.class)); cards.add(new SetCardInfo("Knights' Charge", 328, Rarity.RARE, mage.cards.k.KnightsCharge.class)); cards.add(new SetCardInfo("Korvold, Fae-Cursed King", 329, Rarity.MYTHIC, mage.cards.k.KorvoldFaeCursedKing.class)); + cards.add(new SetCardInfo("Lash of Thorns", 92, Rarity.COMMON, mage.cards.l.LashOfThorns.class)); cards.add(new SetCardInfo("Linden, the Steadfast Queen", 20, Rarity.RARE, mage.cards.l.LindenTheSteadfastQueen.class)); cards.add(new SetCardInfo("Loch Dragon", 211, Rarity.UNCOMMON, mage.cards.l.LochDragon.class)); cards.add(new SetCardInfo("Lochmere Serpent", 195, Rarity.RARE, mage.cards.l.LochmereSerpent.class)); From 0d4bea3c4dd93b23676b91196a317e576b2f4190 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 20 Sep 2019 19:28:04 -0400 Subject: [PATCH 246/373] Implemented Didn't Say Please --- .../src/mage/cards/d/DidntSayPlease.java | 69 +++++++++++++++++++ .../src/mage/cards/t/ThoughtCollapse.java | 5 +- Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 3 files changed, 74 insertions(+), 1 deletion(-) create mode 100644 Mage.Sets/src/mage/cards/d/DidntSayPlease.java diff --git a/Mage.Sets/src/mage/cards/d/DidntSayPlease.java b/Mage.Sets/src/mage/cards/d/DidntSayPlease.java new file mode 100644 index 0000000000..f4e6a186b5 --- /dev/null +++ b/Mage.Sets/src/mage/cards/d/DidntSayPlease.java @@ -0,0 +1,69 @@ +package mage.cards.d; + +import mage.abilities.Ability; +import mage.abilities.effects.Effect; +import mage.abilities.effects.OneShotEffect; +import mage.abilities.effects.common.CounterTargetEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Outcome; +import mage.constants.Zone; +import mage.game.Game; +import mage.players.Player; +import mage.target.TargetSpell; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class DidntSayPlease extends CardImpl { + + public DidntSayPlease(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.INSTANT}, "{1}{U}{U}"); + + // Counter target spell. Its controller puts the top three cards of their library into their graveyard. + this.getSpellAbility().addEffect(new DidntSayPleaseEffect()); + this.getSpellAbility().addTarget(new TargetSpell()); + } + + private DidntSayPlease(final DidntSayPlease card) { + super(card); + } + + @Override + public DidntSayPlease copy() { + return new DidntSayPlease(this); + } +} + +class DidntSayPleaseEffect extends OneShotEffect { + + private static final Effect effect = new CounterTargetEffect(); + + DidntSayPleaseEffect() { + super(Outcome.Benefit); + staticText = "Counter target spell. Its controller puts " + + "the top three cards of their library into their graveyard."; + } + + private DidntSayPleaseEffect(final DidntSayPleaseEffect effect) { + super(effect); + } + + @Override + public DidntSayPleaseEffect copy() { + return new DidntSayPleaseEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + Player player = game.getPlayer(game.getControllerId(source.getFirstTarget())); + if (player == null) { + return false; + } + player.moveCards(player.getLibrary().getTopCards(game, 3), Zone.GRAVEYARD, source, game); + return effect.apply(game, source); + } +} diff --git a/Mage.Sets/src/mage/cards/t/ThoughtCollapse.java b/Mage.Sets/src/mage/cards/t/ThoughtCollapse.java index e09ad3f024..ed4faf06f7 100644 --- a/Mage.Sets/src/mage/cards/t/ThoughtCollapse.java +++ b/Mage.Sets/src/mage/cards/t/ThoughtCollapse.java @@ -1,6 +1,7 @@ package mage.cards.t; import mage.abilities.Ability; +import mage.abilities.effects.Effect; import mage.abilities.effects.OneShotEffect; import mage.abilities.effects.common.CounterTargetEffect; import mage.cards.CardImpl; @@ -39,6 +40,8 @@ public final class ThoughtCollapse extends CardImpl { class ThoughtCollapseEffect extends OneShotEffect { + private static final Effect effect = new CounterTargetEffect(); + ThoughtCollapseEffect() { super(Outcome.Benefit); staticText = "Counter target spell. Its controller puts " + @@ -61,6 +64,6 @@ class ThoughtCollapseEffect extends OneShotEffect { return false; } player.moveCards(player.getLibrary().getTopCards(game, 3), Zone.GRAVEYARD, source, game); - return new CounterTargetEffect().apply(game, source); + return effect.apply(game, source); } } \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 1f3bf67db9..83b3490467 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -73,6 +73,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Curious Pair", 150, Rarity.COMMON, mage.cards.c.CuriousPair.class)); cards.add(new SetCardInfo("Dance of the Manse", 186, Rarity.RARE, mage.cards.d.DanceOfTheManse.class)); cards.add(new SetCardInfo("Deafening Silence", 10, Rarity.UNCOMMON, mage.cards.d.DeafeningSilence.class)); + cards.add(new SetCardInfo("Didn't Say Please", 42, Rarity.COMMON, mage.cards.d.DidntSayPlease.class)); cards.add(new SetCardInfo("Doom Foretold", 187, Rarity.RARE, mage.cards.d.DoomForetold.class)); cards.add(new SetCardInfo("Drown in the Loch", 188, Rarity.UNCOMMON, mage.cards.d.DrownInTheLoch.class)); cards.add(new SetCardInfo("Edgewall Innkeeper", 151, Rarity.UNCOMMON, mage.cards.e.EdgewallInnkeeper.class)); From 61bf0f758d9585e1ae46799b23e8f7a4203a7bf1 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 20 Sep 2019 19:36:09 -0400 Subject: [PATCH 247/373] Implemented Dwarven Mine --- Mage.Sets/src/mage/cards/d/DwarvenMine.java | 64 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + .../mage/game/permanent/token/DwarfToken.java | 28 ++++++++ 3 files changed, 93 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/d/DwarvenMine.java create mode 100644 Mage/src/main/java/mage/game/permanent/token/DwarfToken.java diff --git a/Mage.Sets/src/mage/cards/d/DwarvenMine.java b/Mage.Sets/src/mage/cards/d/DwarvenMine.java new file mode 100644 index 0000000000..bf26b0e4b4 --- /dev/null +++ b/Mage.Sets/src/mage/cards/d/DwarvenMine.java @@ -0,0 +1,64 @@ +package mage.cards.d; + +import mage.abilities.common.EntersBattlefieldAbility; +import mage.abilities.common.EntersBattlefieldUntappedTriggeredAbility; +import mage.abilities.condition.Condition; +import mage.abilities.condition.common.PermanentsOnTheBattlefieldCondition; +import mage.abilities.decorator.ConditionalOneShotEffect; +import mage.abilities.effects.common.CreateTokenEffect; +import mage.abilities.effects.common.TapSourceEffect; +import mage.abilities.mana.RedManaAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.ComparisonType; +import mage.constants.SubType; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterControlledPermanent; +import mage.filter.predicate.permanent.AnotherPredicate; +import mage.game.permanent.token.DwarfToken; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class DwarvenMine extends CardImpl { + + private static final FilterPermanent filter + = new FilterControlledPermanent(SubType.MOUNTAIN); + + static { + filter.add(AnotherPredicate.instance); + } + + private static final Condition condition + = new PermanentsOnTheBattlefieldCondition(filter, ComparisonType.FEWER_THAN, 3); + + public DwarvenMine(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.LAND}, ""); + + this.subtype.add(SubType.MOUNTAIN); + + // ({T}: Add {R}.) + this.addAbility(new RedManaAbility()); + + // Dwarven Mine enters the battlefield tapped unless you control three or more other Mountains. + this.addAbility(new EntersBattlefieldAbility( + new ConditionalOneShotEffect(new TapSourceEffect(), condition), + "tapped unless you control three or more other Mountains" + )); + + // When Dwarven Mine enters the battlefield untapped, create a 1/1 red Dwarf creature token. + this.addAbility(new EntersBattlefieldUntappedTriggeredAbility(new CreateTokenEffect(new DwarfToken()), false)); + } + + private DwarvenMine(final DwarvenMine card) { + super(card); + } + + @Override + public DwarvenMine copy() { + return new DwarvenMine(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 83b3490467..716e411a2c 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -76,6 +76,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Didn't Say Please", 42, Rarity.COMMON, mage.cards.d.DidntSayPlease.class)); cards.add(new SetCardInfo("Doom Foretold", 187, Rarity.RARE, mage.cards.d.DoomForetold.class)); cards.add(new SetCardInfo("Drown in the Loch", 188, Rarity.UNCOMMON, mage.cards.d.DrownInTheLoch.class)); + cards.add(new SetCardInfo("Dwarven Mine", 243, Rarity.COMMON, mage.cards.d.DwarvenMine.class)); cards.add(new SetCardInfo("Edgewall Innkeeper", 151, Rarity.UNCOMMON, mage.cards.e.EdgewallInnkeeper.class)); cards.add(new SetCardInfo("Elite Headhunter", 209, Rarity.UNCOMMON, mage.cards.e.EliteHeadhunter.class)); cards.add(new SetCardInfo("Embercleave", 120, Rarity.MYTHIC, mage.cards.e.Embercleave.class)); diff --git a/Mage/src/main/java/mage/game/permanent/token/DwarfToken.java b/Mage/src/main/java/mage/game/permanent/token/DwarfToken.java new file mode 100644 index 0000000000..861d0bad56 --- /dev/null +++ b/Mage/src/main/java/mage/game/permanent/token/DwarfToken.java @@ -0,0 +1,28 @@ +package mage.game.permanent.token; + +import mage.MageInt; +import mage.constants.CardType; +import mage.constants.SubType; + +/** + * @author TheElk801 + */ +public final class DwarfToken extends TokenImpl { + + public DwarfToken() { + super("Dwarf", "1/1 red Dwarf creature token"); + cardType.add(CardType.CREATURE); + color.setRed(true); + subtype.add(SubType.DWARF); + power = new MageInt(1); + toughness = new MageInt(1); + } + + private DwarfToken(final DwarfToken token) { + super(token); + } + + public DwarfToken copy() { + return new DwarfToken(this); + } +} From 25fc1827eeb4c080acb500f967332b6621075f4a Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 20 Sep 2019 19:45:10 -0400 Subject: [PATCH 248/373] Implemented Rimrock Knight --- Mage.Sets/src/mage/cards/r/RimrockKnight.java | 45 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 46 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/r/RimrockKnight.java diff --git a/Mage.Sets/src/mage/cards/r/RimrockKnight.java b/Mage.Sets/src/mage/cards/r/RimrockKnight.java new file mode 100644 index 0000000000..929b181a06 --- /dev/null +++ b/Mage.Sets/src/mage/cards/r/RimrockKnight.java @@ -0,0 +1,45 @@ +package mage.cards.r; + +import mage.MageInt; +import mage.abilities.common.CantBlockAbility; +import mage.abilities.effects.common.continuous.BoostTargetEffect; +import mage.cards.AdventureCard; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; +import mage.target.common.TargetCreaturePermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class RimrockKnight extends AdventureCard { + + public RimrockKnight(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, new CardType[]{CardType.INSTANT}, "{1}{R}", "Boulder Rush", "{R}"); + + this.subtype.add(SubType.DWARF); + this.subtype.add(SubType.KNIGHT); + this.power = new MageInt(3); + this.toughness = new MageInt(1); + + // Rimrock Knight can't block + this.addAbility(new CantBlockAbility()); + + // Boulder Rush + // Target creature gets +2/+0 until end of turn. + this.getAdventureSpellAbility().addEffect(new BoostTargetEffect(2, 0, Duration.EndOfTurn)); + this.getAdventureSpellAbility().addTarget(new TargetCreaturePermanent()); + } + + private RimrockKnight(final RimrockKnight card) { + super(card); + } + + @Override + public RimrockKnight copy() { + return new RimrockKnight(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 716e411a2c..54d0f0431f 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -220,6 +220,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Return to Nature", 173, Rarity.COMMON, mage.cards.r.ReturnToNature.class)); cards.add(new SetCardInfo("Revenge of Ravens", 104, Rarity.UNCOMMON, mage.cards.r.RevengeOfRavens.class)); cards.add(new SetCardInfo("Righteousness", 27, Rarity.UNCOMMON, mage.cards.r.Righteousness.class)); + cards.add(new SetCardInfo("Rimrock Knight", 137, Rarity.COMMON, mage.cards.r.RimrockKnight.class)); cards.add(new SetCardInfo("Robber of the Rich", 138, Rarity.MYTHIC, mage.cards.r.RobberOfTheRich.class)); cards.add(new SetCardInfo("Rosethorn Acolyte", 174, Rarity.COMMON, mage.cards.r.RosethornAcolyte.class)); cards.add(new SetCardInfo("Rosethorn Halberd", 175, Rarity.COMMON, mage.cards.r.RosethornHalberd.class)); From 90d0abec4b257e820f512b69454e0e400fde8bc6 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 20 Sep 2019 19:51:27 -0400 Subject: [PATCH 249/373] Implemented Scalding Cauldron --- .../src/mage/cards/s/ScaldingCauldron.java | 42 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 43 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/s/ScaldingCauldron.java diff --git a/Mage.Sets/src/mage/cards/s/ScaldingCauldron.java b/Mage.Sets/src/mage/cards/s/ScaldingCauldron.java new file mode 100644 index 0000000000..39d1685f3c --- /dev/null +++ b/Mage.Sets/src/mage/cards/s/ScaldingCauldron.java @@ -0,0 +1,42 @@ +package mage.cards.s; + +import mage.abilities.Ability; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.costs.common.SacrificeSourceCost; +import mage.abilities.costs.common.TapSourceCost; +import mage.abilities.costs.mana.GenericManaCost; +import mage.abilities.effects.common.DamageTargetEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.target.common.TargetCreaturePermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class ScaldingCauldron extends CardImpl { + + public ScaldingCauldron(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT}, "{1}"); + + // {3}, {T}, Sacrifice Scalding Cauldron: It deals 3 damage to target creature. + Ability ability = new SimpleActivatedAbility( + new DamageTargetEffect(3, "it"), new GenericManaCost(3) + ); + ability.addCost(new TapSourceCost()); + ability.addCost(new SacrificeSourceCost()); + ability.addTarget(new TargetCreaturePermanent()); + this.addAbility(ability); + } + + private ScaldingCauldron(final ScaldingCauldron card) { + super(card); + } + + @Override + public ScaldingCauldron copy() { + return new ScaldingCauldron(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 54d0f0431f..52728d867b 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -231,6 +231,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Run Away Together", 62, Rarity.COMMON, mage.cards.r.RunAwayTogether.class)); cards.add(new SetCardInfo("Sage of the Falls", 63, Rarity.UNCOMMON, mage.cards.s.SageOfTheFalls.class)); cards.add(new SetCardInfo("Savvy Hunter", 200, Rarity.UNCOMMON, mage.cards.s.SavvyHunter.class)); + cards.add(new SetCardInfo("Scalding Cauldron", 229, Rarity.COMMON, mage.cards.s.ScaldingCauldron.class)); cards.add(new SetCardInfo("Scorching Dragonfire", 139, Rarity.COMMON, mage.cards.s.ScorchingDragonfire.class)); cards.add(new SetCardInfo("Searing Barrage", 140, Rarity.COMMON, mage.cards.s.SearingBarrage.class)); cards.add(new SetCardInfo("Seven Dwarves", 141, Rarity.COMMON, mage.cards.s.SevenDwarves.class)); From cac106dacca852a5f95ef7b97bd0ad82525127bc Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 20 Sep 2019 19:57:47 -0400 Subject: [PATCH 250/373] Implemented Merfolk Secretkeeper --- .../src/mage/cards/m/MerfolkSecretkeeper.java | 40 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 41 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/m/MerfolkSecretkeeper.java diff --git a/Mage.Sets/src/mage/cards/m/MerfolkSecretkeeper.java b/Mage.Sets/src/mage/cards/m/MerfolkSecretkeeper.java new file mode 100644 index 0000000000..fcc7b742a1 --- /dev/null +++ b/Mage.Sets/src/mage/cards/m/MerfolkSecretkeeper.java @@ -0,0 +1,40 @@ +package mage.cards.m; + +import mage.MageInt; +import mage.abilities.effects.common.PutLibraryIntoGraveTargetEffect; +import mage.cards.AdventureCard; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.target.TargetPlayer; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class MerfolkSecretkeeper extends AdventureCard { + + public MerfolkSecretkeeper(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, new CardType[]{CardType.SORCERY}, "{U}", "Venture Deeper", "{U}"); + + this.subtype.add(SubType.MERFOLK); + this.subtype.add(SubType.WIZARD); + this.power = new MageInt(0); + this.toughness = new MageInt(4); + + // Venture Deeper + // Target player puts the top four cards of their library into their graveyard. + this.getAdventureSpellAbility().addEffect(new PutLibraryIntoGraveTargetEffect(4)); + this.getAdventureSpellAbility().addTarget(new TargetPlayer()); + } + + private MerfolkSecretkeeper(final MerfolkSecretkeeper card) { + super(card); + } + + @Override + public MerfolkSecretkeeper copy() { + return new MerfolkSecretkeeper(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 52728d867b..d68f45670f 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -172,6 +172,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Maraleaf Pixie", 196, Rarity.UNCOMMON, mage.cards.m.MaraleafPixie.class)); cards.add(new SetCardInfo("Maraleaf Rider", 166, Rarity.COMMON, mage.cards.m.MaraleafRider.class)); cards.add(new SetCardInfo("Merchant of the Vale", 131, Rarity.COMMON, mage.cards.m.MerchantOfTheVale.class)); + cards.add(new SetCardInfo("Merfolk Secretkeeper", 53, Rarity.COMMON, mage.cards.m.MerfolkSecretkeeper.class)); cards.add(new SetCardInfo("Midnight Clock", 54, Rarity.RARE, mage.cards.m.MidnightClock.class)); cards.add(new SetCardInfo("Mirrormade", 55, Rarity.RARE, mage.cards.m.Mirrormade.class)); cards.add(new SetCardInfo("Mistford River Turtle", 56, Rarity.COMMON, mage.cards.m.MistfordRiverTurtle.class)); From fae1802ef6342c42865ca5144f12e0e1b06820bc Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 20 Sep 2019 20:07:55 -0400 Subject: [PATCH 251/373] Implemented Reaper of Night --- Mage.Sets/src/mage/cards/r/ReaperOfNight.java | 66 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 67 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/r/ReaperOfNight.java diff --git a/Mage.Sets/src/mage/cards/r/ReaperOfNight.java b/Mage.Sets/src/mage/cards/r/ReaperOfNight.java new file mode 100644 index 0000000000..6bdd66b0da --- /dev/null +++ b/Mage.Sets/src/mage/cards/r/ReaperOfNight.java @@ -0,0 +1,66 @@ +package mage.cards.r; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.AttacksTriggeredAbility; +import mage.abilities.condition.Condition; +import mage.abilities.decorator.ConditionalInterveningIfTriggeredAbility; +import mage.abilities.effects.common.continuous.GainAbilitySourceEffect; +import mage.abilities.effects.common.discard.DiscardTargetEffect; +import mage.abilities.keyword.FlyingAbility; +import mage.cards.AdventureCard; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; +import mage.game.Game; +import mage.players.Player; +import mage.target.common.TargetOpponent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class ReaperOfNight extends AdventureCard { + + public ReaperOfNight(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, new CardType[]{CardType.SORCERY}, "{5}{B}{B}", "Harvest Fear", "{3}{B}"); + + this.subtype.add(SubType.SPECTER); + this.power = new MageInt(4); + this.toughness = new MageInt(5); + + // Whenever Reaper of Night attacks, if defending player has two or fewer cards in hand, it gains flying until end of turn. + this.addAbility(new ConditionalInterveningIfTriggeredAbility( + new AttacksTriggeredAbility(new GainAbilitySourceEffect( + FlyingAbility.getInstance(), Duration.EndOfTurn + ), false), ReaperOfNightCondition.instance, "Whenever {this} attacks, " + + "if defending player has two or fewer cards in hand, it gains flying until end of turn." + )); + + // Harvest Fear + // Target opponent discards two cards. + this.getAdventureSpellAbility().addEffect(new DiscardTargetEffect(2)); + this.getAdventureSpellAbility().addTarget(new TargetOpponent()); + } + + private ReaperOfNight(final ReaperOfNight card) { + super(card); + } + + @Override + public ReaperOfNight copy() { + return new ReaperOfNight(this); + } +} + +enum ReaperOfNightCondition implements Condition { + instance; + + @Override + public boolean apply(Game game, Ability source) { + Player player = game.getPlayer(game.getCombat().getDefendingPlayerId(source.getSourceId(), game)); + return player != null && player.getHand().size() <= 2; + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index d68f45670f..439527f9a9 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -213,6 +213,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Rampart Smasher", 213, Rarity.UNCOMMON, mage.cards.r.RampartSmasher.class)); cards.add(new SetCardInfo("Rankle, Master of Pranks", 101, Rarity.MYTHIC, mage.cards.r.RankleMasterOfPranks.class)); cards.add(new SetCardInfo("Realm-Cloaked Giant", 26, Rarity.MYTHIC, mage.cards.r.RealmCloakedGiant.class)); + cards.add(new SetCardInfo("Reaper of Night", 102, Rarity.COMMON, mage.cards.r.ReaperOfNight.class)); cards.add(new SetCardInfo("Reave Soul", 103, Rarity.COMMON, mage.cards.r.ReaveSoul.class)); cards.add(new SetCardInfo("Redcap Melee", 135, Rarity.UNCOMMON, mage.cards.r.RedcapMelee.class)); cards.add(new SetCardInfo("Redcap Raiders", 136, Rarity.COMMON, mage.cards.r.RedcapRaiders.class)); From 109291a0249ca8198da4ae9ba29b9bfaaf8eed4c Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 20 Sep 2019 20:16:39 -0400 Subject: [PATCH 252/373] Implemented Barrow Witches --- Mage.Sets/src/mage/cards/b/BarrowWitches.java | 50 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 51 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/b/BarrowWitches.java diff --git a/Mage.Sets/src/mage/cards/b/BarrowWitches.java b/Mage.Sets/src/mage/cards/b/BarrowWitches.java new file mode 100644 index 0000000000..f442b28e5c --- /dev/null +++ b/Mage.Sets/src/mage/cards/b/BarrowWitches.java @@ -0,0 +1,50 @@ +package mage.cards.b; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.effects.common.ReturnFromGraveyardToHandTargetEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.filter.FilterCard; +import mage.filter.predicate.mageobject.SubtypePredicate; +import mage.target.common.TargetCardInYourGraveyard; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class BarrowWitches extends CardImpl { + + private static final FilterCard filter = new FilterCard("Knight card from your graveyard"); + + static { + filter.add(new SubtypePredicate(SubType.KNIGHT)); + } + + public BarrowWitches(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{4}{B}"); + + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.WARLOCK); + this.power = new MageInt(3); + this.toughness = new MageInt(4); + + // When Barrow Witches enters the battlefield, return target Knight card from your graveyard to your hand. + Ability ability = new EntersBattlefieldTriggeredAbility(new ReturnFromGraveyardToHandTargetEffect()); + ability.addTarget(new TargetCardInYourGraveyard(filter)); + this.addAbility(ability); + } + + private BarrowWitches(final BarrowWitches card) { + super(card); + } + + @Override + public BarrowWitches copy() { + return new BarrowWitches(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 439527f9a9..873d8395b0 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -40,6 +40,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Bake into a Pie", 76, Rarity.COMMON, mage.cards.b.BakeIntoAPie.class)); cards.add(new SetCardInfo("Banish into Fable", 325, Rarity.RARE, mage.cards.b.BanishIntoFable.class)); cards.add(new SetCardInfo("Barge In", 112, Rarity.COMMON, mage.cards.b.BargeIn.class)); + cards.add(new SetCardInfo("Barrow Witches", 77, Rarity.COMMON, mage.cards.b.BarrowWitches.class)); cards.add(new SetCardInfo("Beanstalk Giant", 149, Rarity.UNCOMMON, mage.cards.b.BeanstalkGiant.class)); cards.add(new SetCardInfo("Belle of the Brawl", 78, Rarity.UNCOMMON, mage.cards.b.BelleOfTheBrawl.class)); cards.add(new SetCardInfo("Beloved Princess", 7, Rarity.COMMON, mage.cards.b.BelovedPrincess.class)); From 4afc35caf025e4b6546949a3562ce525395a4b8d Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 21 Sep 2019 10:40:57 -0400 Subject: [PATCH 253/373] fixed ETB untapped triggered abilities --- .../common/EntersBattlefieldUntappedTriggeredAbility.java | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/Mage/src/main/java/mage/abilities/common/EntersBattlefieldUntappedTriggeredAbility.java b/Mage/src/main/java/mage/abilities/common/EntersBattlefieldUntappedTriggeredAbility.java index 687fa4dfa6..8aa7c5aa6d 100644 --- a/Mage/src/main/java/mage/abilities/common/EntersBattlefieldUntappedTriggeredAbility.java +++ b/Mage/src/main/java/mage/abilities/common/EntersBattlefieldUntappedTriggeredAbility.java @@ -12,6 +12,7 @@ public class EntersBattlefieldUntappedTriggeredAbility extends EntersBattlefield public EntersBattlefieldUntappedTriggeredAbility(Effect effect, boolean optional) { super(effect, optional); + this.noRule = true; } private EntersBattlefieldUntappedTriggeredAbility(final EntersBattlefieldUntappedTriggeredAbility ability) { @@ -29,7 +30,7 @@ public class EntersBattlefieldUntappedTriggeredAbility extends EntersBattlefield return false; } Permanent permanent = game.getPermanent(event.getTargetId()); - return permanent != null && permanent.isTapped(); + return permanent != null && !permanent.isTapped(); } @Override From 25c40b5857226e8d0beb2260259e73643c4b6805 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 21 Sep 2019 15:20:07 -0400 Subject: [PATCH 254/373] fixed Run Away Together targeting incorrectly --- .../src/mage/cards/r/RunAwayTogether.java | 21 ++++++++++++------- 1 file changed, 14 insertions(+), 7 deletions(-) diff --git a/Mage.Sets/src/mage/cards/r/RunAwayTogether.java b/Mage.Sets/src/mage/cards/r/RunAwayTogether.java index 2b6f0628d4..258ed0d3c7 100644 --- a/Mage.Sets/src/mage/cards/r/RunAwayTogether.java +++ b/Mage.Sets/src/mage/cards/r/RunAwayTogether.java @@ -5,11 +5,12 @@ import mage.abilities.effects.common.ReturnToHandTargetEffect; import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.CardType; -import mage.filter.StaticFilters; +import mage.filter.common.FilterCreaturePermanent; import mage.game.Game; import mage.game.permanent.Permanent; import mage.target.common.TargetCreaturePermanent; +import java.util.Objects; import java.util.UUID; /** @@ -21,7 +22,10 @@ public final class RunAwayTogether extends CardImpl { super(ownerId, setInfo, new CardType[]{CardType.INSTANT}, "{1}{U}"); // Choose two target creatures controlled by different players. Return those creatures to their owners' hands. - this.getSpellAbility().addEffect(new ReturnToHandTargetEffect(true)); + this.getSpellAbility().addEffect(new ReturnToHandTargetEffect(true) + .setText("Choose two target creatures controlled by different players. " + + "Return those creatures to their owners' hands.") + ); this.getSpellAbility().addTarget(new RunAwayTogetherTarget()); } @@ -37,8 +41,11 @@ public final class RunAwayTogether extends CardImpl { class RunAwayTogetherTarget extends TargetCreaturePermanent { + private static final FilterCreaturePermanent filter + = new FilterCreaturePermanent("creatures controlled by different players"); + RunAwayTogetherTarget() { - super(2, 2, StaticFilters.FILTER_PERMANENT_CREATURE, false); + super(2, 2, filter, false); } private RunAwayTogetherTarget(final RunAwayTogetherTarget target) { @@ -59,12 +66,12 @@ class RunAwayTogetherTarget extends TargetCreaturePermanent { if (creature == null) { return false; } - return !this.getTargets() + return this.getTargets() .stream() .map(game::getPermanent) - .anyMatch(permanent -> permanent != null - && !creature.getId().equals(permanent.getId()) - && !creature.isControlledBy(permanent.getControllerId()) + .filter(Objects::nonNull) + .noneMatch(permanent -> creature.getId().equals(permanent.getId()) + || creature.isControlledBy(permanent.getControllerId()) ); } } From 874ff2d2523ef0e58f46e38ea55e9279043a4f02 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 21 Sep 2019 15:33:06 -0400 Subject: [PATCH 255/373] fixed Opportunistic Dragon not working --- .../src/mage/cards/o/OpportunisticDragon.java | 90 +++++++++++++++++-- 1 file changed, 83 insertions(+), 7 deletions(-) diff --git a/Mage.Sets/src/mage/cards/o/OpportunisticDragon.java b/Mage.Sets/src/mage/cards/o/OpportunisticDragon.java index 5787c4685e..d4e9aa9746 100644 --- a/Mage.Sets/src/mage/cards/o/OpportunisticDragon.java +++ b/Mage.Sets/src/mage/cards/o/OpportunisticDragon.java @@ -18,6 +18,7 @@ import mage.filter.predicate.Predicates; import mage.filter.predicate.mageobject.CardTypePredicate; import mage.filter.predicate.mageobject.SubtypePredicate; import mage.filter.predicate.permanent.ControllerPredicate; +import mage.game.Game; import mage.target.TargetPermanent; import java.util.UUID; @@ -48,13 +49,9 @@ public final class OpportunisticDragon extends CardImpl { this.addAbility(FlyingAbility.getInstance()); // When Opportunistic Dragon enters the battlefield, choose target Human or artifact an opponent controls. For as long as Opportunistic Dragon remains on the battlefield, gain control of that permanent, it loses all abilities, and it can't attack or block. - Ability ability = new EntersBattlefieldTriggeredAbility(new GainControlTargetEffect(Duration.WhileOnBattlefield) - .setText("choose target Human or artifact an opponent controls. " + - "For as long as {this} remains on the battlefield, gain control of that permanent,")); - ability.addEffect(new LoseAllAbilitiesTargetEffect(Duration.WhileOnBattlefield) - .setText("it loses all abilities,")); - ability.addEffect(new CantAttackBlockTargetEffect(Duration.WhileOnBattlefield) - .setText("and it can't attack or block")); + Ability ability = new EntersBattlefieldTriggeredAbility(new OpportunisticDragonControlEffect()); + ability.addEffect(new OpportunisticDragonLoseAbilitiesEffect()); + ability.addEffect(new OpportunisticDragonAttackBlockEffect()); ability.addTarget(new TargetPermanent(filter)); this.addAbility(ability); } @@ -68,3 +65,82 @@ public final class OpportunisticDragon extends CardImpl { return new OpportunisticDragon(this); } } + +class OpportunisticDragonControlEffect extends GainControlTargetEffect { + + OpportunisticDragonControlEffect() { + super(Duration.Custom); + staticText = "choose target Human or artifact an opponent controls. " + + "For as long as {this} remains on the battlefield, gain control of that permanent,"; + } + + private OpportunisticDragonControlEffect(final OpportunisticDragonControlEffect effect) { + super(effect); + } + + @Override + public OpportunisticDragonControlEffect copy() { + return new OpportunisticDragonControlEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + if (source.getSourcePermanentIfItStillExists(game) == null) { + discard(); + return false; + } + return super.apply(game, source); + } +} + +class OpportunisticDragonLoseAbilitiesEffect extends LoseAllAbilitiesTargetEffect { + + OpportunisticDragonLoseAbilitiesEffect() { + super(Duration.Custom); + staticText = "it loses all abilities,"; + } + + private OpportunisticDragonLoseAbilitiesEffect(final OpportunisticDragonLoseAbilitiesEffect effect) { + super(effect); + } + + @Override + public OpportunisticDragonLoseAbilitiesEffect copy() { + return new OpportunisticDragonLoseAbilitiesEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + if (source.getSourcePermanentIfItStillExists(game) == null) { + discard(); + return false; + } + return super.apply(game, source); + } +} + +class OpportunisticDragonAttackBlockEffect extends CantAttackBlockTargetEffect { + + OpportunisticDragonAttackBlockEffect() { + super(Duration.Custom); + staticText = "and it can't attack or block"; + } + + private OpportunisticDragonAttackBlockEffect(final OpportunisticDragonAttackBlockEffect effect) { + super(effect); + } + + @Override + public OpportunisticDragonAttackBlockEffect copy() { + return new OpportunisticDragonAttackBlockEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + if (source.getSourcePermanentIfItStillExists(game) == null) { + discard(); + return false; + } + return super.apply(game, source); + } +} From 3b9a9d7645364163507320c4fc135a86c11815bb Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 21 Sep 2019 15:38:27 -0400 Subject: [PATCH 256/373] Implemented Outflank --- Mage.Sets/src/mage/cards/o/Outflank.java | 40 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 41 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/o/Outflank.java diff --git a/Mage.Sets/src/mage/cards/o/Outflank.java b/Mage.Sets/src/mage/cards/o/Outflank.java new file mode 100644 index 0000000000..3818073819 --- /dev/null +++ b/Mage.Sets/src/mage/cards/o/Outflank.java @@ -0,0 +1,40 @@ +package mage.cards.o; + +import mage.abilities.dynamicvalue.DynamicValue; +import mage.abilities.dynamicvalue.common.PermanentsOnBattlefieldCount; +import mage.abilities.effects.common.DamageTargetEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.filter.StaticFilters; +import mage.target.common.TargetAttackingOrBlockingCreature; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class Outflank extends CardImpl { + + private static final DynamicValue xValue + = new PermanentsOnBattlefieldCount(StaticFilters.FILTER_CONTROLLED_CREATURE); + + public Outflank(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.INSTANT}, "{W}"); + + // Outflank deals damage to target attacking or blocking creature equal to the number of creatures you control. + this.getSpellAbility().addEffect(new DamageTargetEffect(xValue) + .setText("{this} deals damage to target attacking or blocking creature " + + "equal to the number of creatures you control")); + this.getSpellAbility().addTarget(new TargetAttackingOrBlockingCreature()); + } + + private Outflank(final Outflank card) { + super(card); + } + + @Override + public Outflank copy() { + return new Outflank(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 873d8395b0..8461fe8500 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -199,6 +199,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Opportunistic Dragon", 133, Rarity.RARE, mage.cards.o.OpportunisticDragon.class)); cards.add(new SetCardInfo("Opt", 59, Rarity.COMMON, mage.cards.o.Opt.class)); cards.add(new SetCardInfo("Order of Midnight", 99, Rarity.UNCOMMON, mage.cards.o.OrderOfMidnight.class)); + cards.add(new SetCardInfo("Outflank", 23, Rarity.COMMON, mage.cards.o.Outflank.class)); cards.add(new SetCardInfo("Outmuscle", 170, Rarity.COMMON, mage.cards.o.Outmuscle.class)); cards.add(new SetCardInfo("Overwhelmed Apprentice", 60, Rarity.UNCOMMON, mage.cards.o.OverwhelmedApprentice.class)); cards.add(new SetCardInfo("Piper of the Swarm", 100, Rarity.RARE, mage.cards.p.PiperOfTheSwarm.class)); From 482f49e229158dde36e79843d5b517bdb47a4d26 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 21 Sep 2019 15:43:11 -0400 Subject: [PATCH 257/373] Implemented Queen of Ice --- Mage.Sets/src/mage/cards/q/QueenOfIce.java | 57 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 58 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/q/QueenOfIce.java diff --git a/Mage.Sets/src/mage/cards/q/QueenOfIce.java b/Mage.Sets/src/mage/cards/q/QueenOfIce.java new file mode 100644 index 0000000000..0bbbf185f4 --- /dev/null +++ b/Mage.Sets/src/mage/cards/q/QueenOfIce.java @@ -0,0 +1,57 @@ +package mage.cards.q; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.DealsDamageToACreatureTriggeredAbility; +import mage.abilities.effects.common.DontUntapInControllersNextUntapStepTargetEffect; +import mage.abilities.effects.common.TapTargetEffect; +import mage.cards.AdventureCard; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.target.common.TargetCreaturePermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class QueenOfIce extends AdventureCard { + + public QueenOfIce(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, new CardType[]{CardType.SORCERY}, "{2}{U}", "Rage of Winter", "{1}{U}"); + + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.NOBLE); + this.subtype.add(SubType.WIZARD); + this.power = new MageInt(2); + this.toughness = new MageInt(3); + + // Whenever Queen of Ice deals combat damage to a creature, tap that creature. It doesn't untap during its controller's next untap step. + Ability ability = new DealsDamageToACreatureTriggeredAbility( + new TapTargetEffect().setText("tap that creature."), + true, false, true + ); + ability.addEffect(new DontUntapInControllersNextUntapStepTargetEffect() + .setText("It doesn't untap during its controller's next untap step") + ); + this.addAbility(ability); + + // Rage of Winter + // Tap target creature. It doesn’t untap during its controller’s next untap step. + this.getAdventureSpellAbility().addEffect(new TapTargetEffect()); + this.getAdventureSpellAbility().addEffect(new DontUntapInControllersNextUntapStepTargetEffect() + .setText("It doesn't untap during its controller's next untap step")); + this.getAdventureSpellAbility().addTarget(new TargetCreaturePermanent()); + } + + private QueenOfIce(final QueenOfIce card) { + super(card); + } + + @Override + public QueenOfIce copy() { + return new QueenOfIce(this); + } +} +// let it go diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 8461fe8500..8052a5d039 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -209,6 +209,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Plains", 253, Rarity.LAND, mage.cards.basiclands.Plains.class, NON_FULL_USE_VARIOUS)); cards.add(new SetCardInfo("Prized Griffin", 24, Rarity.COMMON, mage.cards.p.PrizedGriffin.class)); cards.add(new SetCardInfo("Prophet of the Peak", 227, Rarity.COMMON, mage.cards.p.ProphetOfThePeak.class)); + cards.add(new SetCardInfo("Queen of Ice", 61, Rarity.COMMON, mage.cards.q.QueenOfIce.class)); cards.add(new SetCardInfo("Questing Beast", 171, Rarity.MYTHIC, mage.cards.q.QuestingBeast.class)); cards.add(new SetCardInfo("Raging Redcap", 134, Rarity.COMMON, mage.cards.r.RagingRedcap.class)); cards.add(new SetCardInfo("Rally for the Throne", 25, Rarity.UNCOMMON, mage.cards.r.RallyForTheThrone.class)); From 0077ad5a07567e8cfb10ed7cc8cb781703b48705 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 21 Sep 2019 15:57:08 -0400 Subject: [PATCH 258/373] added ELD collector's edition --- .../ThroneOfEldraineCollectorsEdition.java | 114 +++++++++++++++++ Utils/known-sets.txt | 1 + Utils/mtg-cards-data.txt | 121 ++++++++++++++++++ Utils/mtg-sets-data.txt | 1 + 4 files changed, 237 insertions(+) create mode 100644 Mage.Sets/src/mage/sets/ThroneOfEldraineCollectorsEdition.java diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraineCollectorsEdition.java b/Mage.Sets/src/mage/sets/ThroneOfEldraineCollectorsEdition.java new file mode 100644 index 0000000000..d4d578a987 --- /dev/null +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraineCollectorsEdition.java @@ -0,0 +1,114 @@ +package mage.sets; + +import mage.cards.AdventureCard; +import mage.cards.ExpansionSet; +import mage.constants.Rarity; +import mage.constants.SetType; + +/** + * @author TheElk801 + */ +public final class ThroneOfEldraineCollectorsEdition extends ExpansionSet { + + private static final ThroneOfEldraineCollectorsEdition instance = new ThroneOfEldraineCollectorsEdition(); + + public static ThroneOfEldraineCollectorsEdition getInstance() { + return instance; + } + + private ThroneOfEldraineCollectorsEdition() { + super("Throne of Eldraine Collector's Edition", "CELD", ExpansionSet.buildDate(2019, 10, 4), SetType.PROMOTIONAL); + + cards.add(new SetCardInfo("Acclaimed Contender", 334, Rarity.RARE, mage.cards.a.AcclaimedContender.class)); + cards.add(new SetCardInfo("Animating Faerie", 280, Rarity.UNCOMMON, mage.cards.a.AnimatingFaerie.class)); + cards.add(new SetCardInfo("Ardenvale Tactician", 273, Rarity.COMMON, mage.cards.a.ArdenvaleTactician.class)); + cards.add(new SetCardInfo("Ayara, First of Locthwain", 350, Rarity.RARE, mage.cards.a.AyaraFirstOfLocthwain.class)); + cards.add(new SetCardInfo("Beanstalk Giant", 295, Rarity.UNCOMMON, mage.cards.b.BeanstalkGiant.class)); + cards.add(new SetCardInfo("Blacklance Paragon", 351, Rarity.RARE, mage.cards.b.BlacklanceParagon.class)); + cards.add(new SetCardInfo("Bonecrusher Giant", 291, Rarity.RARE, mage.cards.b.BonecrusherGiant.class)); + cards.add(new SetCardInfo("Brazen Borrower", 281, Rarity.MYTHIC, mage.cards.b.BrazenBorrower.class)); + cards.add(new SetCardInfo("Castle Ardenvale", 386, Rarity.RARE, mage.cards.c.CastleArdenvale.class)); + cards.add(new SetCardInfo("Castle Embereth", 387, Rarity.RARE, mage.cards.c.CastleEmbereth.class)); + cards.add(new SetCardInfo("Castle Garenbrig", 388, Rarity.RARE, mage.cards.c.CastleGarenbrig.class)); + cards.add(new SetCardInfo("Castle Locthwain", 389, Rarity.RARE, mage.cards.c.CastleLocthwain.class)); + cards.add(new SetCardInfo("Castle Vantress", 390, Rarity.RARE, mage.cards.c.CastleVantress.class)); + cards.add(new SetCardInfo("Charming Prince", 335, Rarity.RARE, mage.cards.c.CharmingPrince.class)); + cards.add(new SetCardInfo("Clackbridge Troll", 353, Rarity.RARE, mage.cards.c.ClackbridgeTroll.class)); + cards.add(new SetCardInfo("Curious Pair", 296, Rarity.COMMON, mage.cards.c.CuriousPair.class)); + cards.add(new SetCardInfo("Dance of the Manse", 377, Rarity.RARE, mage.cards.d.DanceOfTheManse.class)); + cards.add(new SetCardInfo("Doom Foretold", 378, Rarity.RARE, mage.cards.d.DoomForetold.class)); + cards.add(new SetCardInfo("Embercleave", 359, Rarity.MYTHIC, mage.cards.e.Embercleave.class)); + cards.add(new SetCardInfo("Embereth Shieldbreaker", 292, Rarity.UNCOMMON, mage.cards.e.EmberethShieldbreaker.class)); + cards.add(new SetCardInfo("Emry, Lurker of the Loch", 342, Rarity.RARE, mage.cards.e.EmryLurkerOfTheLoch.class)); + cards.add(new SetCardInfo("Escape to the Wilds", 379, Rarity.RARE, mage.cards.e.EscapeToTheWilds.class)); + cards.add(new SetCardInfo("Fabled Passage", 391, Rarity.RARE, mage.cards.f.FabledPassage.class)); + cards.add(new SetCardInfo("Fae of Wishes", 282, Rarity.RARE, mage.cards.f.FaeOfWishes.class)); + cards.add(new SetCardInfo("Faeburrow Elder", 380, Rarity.RARE, mage.cards.f.FaeburrowElder.class)); + cards.add(new SetCardInfo("Faerie Guidemother", 274, Rarity.COMMON, mage.cards.f.FaerieGuidemother.class)); + cards.add(new SetCardInfo("Feasting Troll King", 368, Rarity.RARE, mage.cards.f.FeastingTrollKing.class)); + cards.add(new SetCardInfo("Fervent Champion", 360, Rarity.RARE, mage.cards.f.FerventChampion.class)); + cards.add(new SetCardInfo("Fires of Invention", 361, Rarity.RARE, mage.cards.f.FiresOfInvention.class)); + cards.add(new SetCardInfo("Flaxen Intruder", 297, Rarity.UNCOMMON, mage.cards.f.FlaxenIntruder.class)); + cards.add(new SetCardInfo("Folio of Fancies", 343, Rarity.RARE, mage.cards.f.FolioOfFancies.class)); + cards.add(new SetCardInfo("Foulmire Knight", 286, Rarity.UNCOMMON, mage.cards.f.FoulmireKnight.class)); + cards.add(new SetCardInfo("Gadwick, the Wizened", 344, Rarity.RARE, mage.cards.g.GadwickTheWizened.class)); + cards.add(new SetCardInfo("Garenbrig Carver", 298, Rarity.COMMON, mage.cards.g.GarenbrigCarver.class)); + cards.add(new SetCardInfo("Garruk, Cursed Huntsman", 270, Rarity.MYTHIC, mage.cards.g.GarrukCursedHuntsman.class)); + cards.add(new SetCardInfo("Giant Killer", 275, Rarity.RARE, mage.cards.g.GiantKiller.class)); + cards.add(new SetCardInfo("Gilded Goose", 369, Rarity.RARE, mage.cards.g.GildedGoose.class)); + cards.add(new SetCardInfo("Happily Ever After", 337, Rarity.RARE, mage.cards.h.HappilyEverAfter.class)); + cards.add(new SetCardInfo("Harmonious Archon", 338, Rarity.MYTHIC, mage.cards.h.HarmoniousArchon.class)); + cards.add(new SetCardInfo("Hypnotic Sprite", 283, Rarity.UNCOMMON, mage.cards.h.HypnoticSprite.class)); + cards.add(new SetCardInfo("Irencrag Feat", 362, Rarity.RARE, mage.cards.i.IrencragFeat.class)); + cards.add(new SetCardInfo("Irencrag Pyromancer", 363, Rarity.RARE, mage.cards.i.IrencragPyromancer.class)); + cards.add(new SetCardInfo("Linden, the Steadfast Queen", 340, Rarity.RARE, mage.cards.l.LindenTheSteadfastQueen.class)); + cards.add(new SetCardInfo("Lochmere Serpent", 381, Rarity.RARE, mage.cards.l.LochmereSerpent.class)); + cards.add(new SetCardInfo("Lonesome Unicorn", 276, Rarity.COMMON, mage.cards.l.LonesomeUnicorn.class)); + cards.add(new SetCardInfo("Lovestruck Beast", 299, Rarity.RARE, mage.cards.l.LovestruckBeast.class)); + cards.add(new SetCardInfo("Merchant of the Vale", 293, Rarity.COMMON, mage.cards.m.MerchantOfTheVale.class)); + cards.add(new SetCardInfo("Merfolk Secretkeeper", 284, Rarity.COMMON, mage.cards.m.MerfolkSecretkeeper.class)); + cards.add(new SetCardInfo("Midnight Clock", 346, Rarity.RARE, mage.cards.m.MidnightClock.class)); + cards.add(new SetCardInfo("Mirrormade", 347, Rarity.RARE, mage.cards.m.Mirrormade.class)); + cards.add(new SetCardInfo("Murderous Rider", 287, Rarity.RARE, mage.cards.m.MurderousRider.class)); + cards.add(new SetCardInfo("Oakhame Ranger", 302, Rarity.UNCOMMON, mage.cards.o.OakhameRanger.class)); + cards.add(new SetCardInfo("Oathsworn Knight", 354, Rarity.RARE, mage.cards.o.OathswornKnight.class)); + cards.add(new SetCardInfo("Oko, Thief of Crowns", 271, Rarity.MYTHIC, mage.cards.o.OkoThiefOfCrowns.class)); + cards.add(new SetCardInfo("Once Upon a Time", 371, Rarity.RARE, mage.cards.o.OnceUponATime.class)); + cards.add(new SetCardInfo("Opportunistic Dragon", 364, Rarity.RARE, mage.cards.o.OpportunisticDragon.class)); + cards.add(new SetCardInfo("Order of Midnight", 288, Rarity.UNCOMMON, mage.cards.o.OrderOfMidnight.class)); + cards.add(new SetCardInfo("Piper of the Swarm", 355, Rarity.RARE, mage.cards.p.PiperOfTheSwarm.class)); + cards.add(new SetCardInfo("Queen of Ice", 285, Rarity.COMMON, mage.cards.q.QueenOfIce.class)); + cards.add(new SetCardInfo("Questing Beast", 372, Rarity.MYTHIC, mage.cards.q.QuestingBeast.class)); + cards.add(new SetCardInfo("Rankle, Master of Pranks", 356, Rarity.MYTHIC, mage.cards.r.RankleMasterOfPranks.class)); + cards.add(new SetCardInfo("Realm-Cloaked Giant", 277, Rarity.MYTHIC, mage.cards.r.RealmCloakedGiant.class)); + cards.add(new SetCardInfo("Reaper of Night", 289, Rarity.COMMON, mage.cards.r.ReaperOfNight.class)); + cards.add(new SetCardInfo("Return of the Wildspeaker", 373, Rarity.RARE, mage.cards.r.ReturnOfTheWildspeaker.class)); + cards.add(new SetCardInfo("Rimrock Knight", 294, Rarity.COMMON, mage.cards.r.RimrockKnight.class)); + cards.add(new SetCardInfo("Robber of the Rich", 365, Rarity.MYTHIC, mage.cards.r.RobberOfTheRich.class)); + cards.add(new SetCardInfo("Rosethorn Acolyte", 300, Rarity.COMMON, mage.cards.r.RosethornAcolyte.class)); + cards.add(new SetCardInfo("Shepherd of the Flock", 278, Rarity.UNCOMMON, mage.cards.s.ShepherdOfTheFlock.class)); + cards.add(new SetCardInfo("Silverflame Squire", 279, Rarity.COMMON, mage.cards.s.SilverflameSquire.class)); + cards.add(new SetCardInfo("Smitten Swordmaster", 290, Rarity.COMMON, mage.cards.s.SmittenSwordmaster.class)); + cards.add(new SetCardInfo("Sorcerous Spyglass", 384, Rarity.RARE, mage.cards.s.SorcerousSpyglass.class)); + cards.add(new SetCardInfo("Stolen by the Fae", 348, Rarity.RARE, mage.cards.s.StolenByTheFae.class)); + cards.add(new SetCardInfo("Stonecoil Serpent", 385, Rarity.RARE, mage.cards.s.StonecoilSerpent.class)); + cards.add(new SetCardInfo("Stormfist Crusader", 383, Rarity.RARE, mage.cards.s.StormfistCrusader.class)); + cards.add(new SetCardInfo("The Cauldron of Eternity", 352, Rarity.MYTHIC, mage.cards.t.TheCauldronOfEternity.class)); + cards.add(new SetCardInfo("The Circle of Loyalty", 336, Rarity.MYTHIC, mage.cards.t.TheCircleOfLoyalty.class)); + cards.add(new SetCardInfo("The Great Henge", 370, Rarity.MYTHIC, mage.cards.t.TheGreatHenge.class)); + cards.add(new SetCardInfo("The Magic Mirror", 345, Rarity.MYTHIC, mage.cards.t.TheMagicMirror.class)); + cards.add(new SetCardInfo("The Royal Scions", 272, Rarity.MYTHIC, mage.cards.t.TheRoyalScions.class)); + cards.add(new SetCardInfo("Torbran, Thane of Red Fell", 367, Rarity.RARE, mage.cards.t.TorbranThaneOfRedFell.class)); + cards.add(new SetCardInfo("Tuinvale Treefolk", 301, Rarity.COMMON, mage.cards.t.TuinvaleTreefolk.class)); + cards.add(new SetCardInfo("Vantress Gargoyle", 349, Rarity.RARE, mage.cards.v.VantressGargoyle.class)); + cards.add(new SetCardInfo("Wicked Wolf", 374, Rarity.RARE, mage.cards.w.WickedWolf.class)); + cards.add(new SetCardInfo("Wildborn Preserver", 375, Rarity.RARE, mage.cards.w.WildbornPreserver.class)); + cards.add(new SetCardInfo("Wishclaw Talisman", 357, Rarity.RARE, mage.cards.w.WishclawTalisman.class)); + cards.add(new SetCardInfo("Witch's Vengeance", 358, Rarity.RARE, mage.cards.w.WitchsVengeance.class)); + cards.add(new SetCardInfo("Worthy Knight", 341, Rarity.RARE, mage.cards.w.WorthyKnight.class)); + cards.add(new SetCardInfo("Yorvo, Lord of Garenbrig", 376, Rarity.RARE, mage.cards.y.YorvoLordOfGarenbrig.class)); + + // This is here to prevent the incomplete adventure implementation from causing problems and will be removed + cards.removeIf(setCardInfo -> AdventureCard.class.isAssignableFrom(setCardInfo.getCardClass())); + } +} diff --git a/Utils/known-sets.txt b/Utils/known-sets.txt index 7bf3b5eeaf..93b95715ac 100644 --- a/Utils/known-sets.txt +++ b/Utils/known-sets.txt @@ -187,6 +187,7 @@ Tenth Edition|TenthEdition| The Dark|TheDark| Theros|Theros| Throne of Eldraine|ThroneOfEldraine| +Throne of Eldraine Collector's Edition|ThroneOfEldraineCollectorsEdition| Time Spiral|TimeSpiral| Time Spiral "Timeshifted"|TimeSpiralTimeshifted| Torment|Torment| diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index 0d8209f081..fd3529d093 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -36308,3 +36308,124 @@ Syr Gwyn, Hero of Ashvale|Throne of Eldraine|330|M|{3}{R}{W}{B}|Legendary Creatu Arcane Signet|Throne of Eldraine|331|C|{2}|Artifact|||{T}: Add one mana of any color in your commander's color identity.| Tome of Legends|Throne of Eldraine|332|R|{2}|Artifact|||Tome of Legends enters the battlefield with a page counter on it.$Whenever your commander enters the battlefield or attacks, put a page counter on Tome of Legends.${1}, {T}, Remove a page counter from Tome of Legends: Draw a card.| Command Tower|Throne of Eldraine|333|C||Land|||{T}: Add one mana of any color in your commander's color identity.| +Garruk, Cursed Huntsman|Throne of Eldraine Collector's Edition|270|M|{4}{B}{G}|Legendary Planeswalker - Garruk|5|0: Create two 2/2 black and green Wolf creature tokens with "When this creature dies, put a loyalty counter on each Garruk you control."$−3: Destroy target creature. Draw a card.$−6: You get an emblem with "Creatures you control get +3/+3 and have trample."| +Oko, Thief of Crowns|Throne of Eldraine Collector's Edition|271|M|{1}{G}{U}|Legendary Planeswalker - Oko|4|+2: Create a Food token.$+1: Target artifact or creature loses all abilities and becomes a green Elk creature with base power and toughness 3/3.$−5: Exchange control of target artifact or creature you control and target creature an opponent controls with power 3 or less.| +The Royal Scions|Throne of Eldraine Collector's Edition|272|M|{1}{U}{R}|Legendary Planeswalker - Will Rowan|5|+1: Draw a card, then discard a card.$+1: Target creature gets +2/+0 and gains first strike and trample until end of turn.$−8: Draw four cards. When you do, The Royal Scions deals damage to any target equal to the number of cards in your hand.| +Ardenvale Tactician|Throne of Eldraine Collector's Edition|273|C|{1}{W}{W}|Creature - Human Knight|2|3|Flying| +Dizzying Swoop|Throne of Eldraine Collector's Edition|273|C|{1}{W}|Instant - Adventure|2|3|Tap up to two target creatures.| +Faerie Guidemother|Throne of Eldraine Collector's Edition|274|C|{W}|Creature - Faerie|1|1|Flying| +Gift of the Fae|Throne of Eldraine Collector's Edition|274|C|{1}{W}|Sorcery - Adventure|1|1|Target creature gets +2/+1 and gains flying until end of turn.| +Chop Down|Throne of Eldraine Collector's Edition|275|R|{2}{W}|Instant - Adventure|1|2|Destroy target creature with power 4 or greater.| +Giant Killer|Throne of Eldraine Collector's Edition|275|R|{W}|Creature - Human Peasant|1|2|{1}{W}, {T}: Tap target creature.| +Lonesome Unicorn|Throne of Eldraine Collector's Edition|276|C|{4}{W}|Creature - Unicorn|3|3|Vigilance| +Rider in Need|Throne of Eldraine Collector's Edition|276|C|{2}{W}|Sorcery - Adventure|3|3|Create a 2/2 white Knight creature token with vigilance.| +Cast Off|Throne of Eldraine Collector's Edition|277|M|{3}{W}{W}|Sorcery - Adventure|7|7|Destroy all non-Giant creatures.| +Realm-Cloaked Giant|Throne of Eldraine Collector's Edition|277|M|{5}{W}{W}|Creature - Giant|7|7|Vigilance| +Shepherd of the Flock|Throne of Eldraine Collector's Edition|278|U|{1}{W}|Creature - Human Peasant|3|1|| +Usher to Safety|Throne of Eldraine Collector's Edition|278|U|{W}|Instant - Adventure|3|1|Return target permanent you control to its owner's hand.| +On Alert|Throne of Eldraine Collector's Edition|279|C|{2}{W}|Instant - Adventure|2|1|Target creature gets +2/+2 until end of turn. Untap it.| +Silverflame Squire|Throne of Eldraine Collector's Edition|279|C|{1}{W}|Creature - Human Soldier|2|1|| +Animating Faerie|Throne of Eldraine Collector's Edition|280|U|{2}{U}|Creature - Faerie|2|2|Flying| +Bring to Life|Throne of Eldraine Collector's Edition|280|U|{2}{U}|Sorcery - Adventure|2|2|Target noncreature artifact you control becomes a 0/0 artifact creature. Put four +1/+1 counters on it.| +Brazen Borrower|Throne of Eldraine Collector's Edition|281|M|{1}{U}{U}|Creature - Faerie Rogue|3|1|Flash$Flying$Brazen Borrower can block only creatures with flying.| +Petty Theft|Throne of Eldraine Collector's Edition|281|M|{1}{U}|Instant - Adventure|3|1|Return target nonland permanent an opponent controls to its owner's hand.| +Fae of Wishes|Throne of Eldraine Collector's Edition|282|R|{1}{U}|Creature - Faerie Wizard|1|4|Flying${1}{U}, Discard two cards: Return Fae of Wishes to its owner's hand.| +Granted|Throne of Eldraine Collector's Edition|282|R|{3}{U}|Sorcery - Adventure|1|4|You may choose a noncreature card you own from outside the game, reveal it, and put it into your hand.| +Hypnotic Sprite|Throne of Eldraine Collector's Edition|283|U|{U}{U}|Creature - Faerie|2|1|Flying| +Mesmeric Glare|Throne of Eldraine Collector's Edition|283|U|{2}{U}|Instant - Adventure|2|1|Counter target spell with converted mana cost 3 or less.| +Merfolk Secretkeeper|Throne of Eldraine Collector's Edition|284|C|{U}|Creature - Merfolk Wizard|0|4|| +Venture Deeper|Throne of Eldraine Collector's Edition|284|C|{U}|Sorcery - Adventure|0|4|Target player puts the top four cards of their library into their graveyard.| +Queen of Ice|Throne of Eldraine Collector's Edition|285|C|{2}{U}|Creature - Human Noble Wizard|2|3|Whenever Queen of Ice deals combat damage to a creature, tap that creature. It doesn't untap during its controller's next untap step.| +Rage of Winter|Throne of Eldraine Collector's Edition|285|C|{1}{U}|Sorcery - Adventure|2|3|Tap target creature. It doesn't untap during its controller's next untap step.| +Foulmire Knight|Throne of Eldraine Collector's Edition|286|U|{B}|Creature - Zombie Knight|1|1|Deathtouch| +Profane Insight|Throne of Eldraine Collector's Edition|286|U|{2}{B}|Instant - Adventure|1|1|You draw a card and you lose 1 life.| +Murderous Rider|Throne of Eldraine Collector's Edition|287|R|{1}{B}{B}|Creature - Zombie Knight|2|3|Lifelink$When Murderous Rider dies, put it on the bottom of its owner's library.| +Swift End|Throne of Eldraine Collector's Edition|287|R|{1}{B}{B}|Instant - Adventure|2|3|Destroy target creature or planeswalker. You lose 2 life.| +Alter Fate|Throne of Eldraine Collector's Edition|288|U|{1}{B}|Sorcery - Adventure|2|2|Return target creature card from your graveyard to your hand.| +Order of Midnight|Throne of Eldraine Collector's Edition|288|U|{1}{B}|Creature - Human Knight|2|2|Flying$Order of Midnight can't block.| +Harvest Fear|Throne of Eldraine Collector's Edition|289|C|{3}{B}|Sorcery - Adventure|4|5|Target opponent discards two cards.| +Reaper of Night|Throne of Eldraine Collector's Edition|289|C|{5}{B}{B}|Creature - Specter|4|5|Whenever Reaper of Night attacks, if defending player has two or fewer cards in hand, it gains flying until end of turn.| +Curry Favor|Throne of Eldraine Collector's Edition|290|C|{B}|Sorcery - Adventure|2|1|You gain X life and each opponent loses X life, where X is the number of Knights you control.| +Smitten Swordmaster|Throne of Eldraine Collector's Edition|290|C|{1}{B}|Creature - Human Knight|2|1|Lifelink| +Bonecrusher Giant|Throne of Eldraine Collector's Edition|291|R|{2}{R}|Creature - Giant|4|3|Whenever Bonecrusher Giant becomes the target of a spell, Bonecrusher Giant deals 2 damage to that spell's controller.| +Stomp|Throne of Eldraine Collector's Edition|291|R|{1}{R}|Instant - Adventure|4|3|Damage can't be prevented this turn. Stomp deals 2 damage to any target.| +Battle Display|Throne of Eldraine Collector's Edition|292|U|{R}|Sorcery - Adventure|2|1|Destroy target artifact.| +Embereth Shieldbreaker|Throne of Eldraine Collector's Edition|292|U|{1}{R}|Creature - Human Knight|2|1|| +Haggle|Throne of Eldraine Collector's Edition|293|C|{R}|Instant - Adventure|2|3|You may discard a card. If you do, draw a card.| +Merchant of the Vale|Throne of Eldraine Collector's Edition|293|C|{2}{R}|Creature - Human Peasant|2|3|{2}{R}, Discard a card: Draw a card.| +Boulder Rush|Throne of Eldraine Collector's Edition|294|C|{R}|Instant - Adventure|3|1|Target creature gets +2/+0 until end of turn.| +Rimrock Knight|Throne of Eldraine Collector's Edition|294|C|{1}{R}|Creature - Dwarf Knight|3|1|Rimrock Knight can't block| +Beanstalk Giant|Throne of Eldraine Collector's Edition|295|U|{6}{G}|Creature - Giant|*|*|Beanstalk Giant's power and toughness are each equal to the number of lands you control.| +Fertile Footsteps|Throne of Eldraine Collector's Edition|295|U|{2}{G}|Sorcery - Adventure|*|*|Search your library for a basic land card, put it onto the battlefield, then shuffle your library.| +Curious Pair|Throne of Eldraine Collector's Edition|296|C|{1}{G}|Creature - Human Peasant|1|3|| +Treats to Share|Throne of Eldraine Collector's Edition|296|C|{G}|Sorcery - Adventure|1|3|Create a Food token.| +Flaxen Intruder|Throne of Eldraine Collector's Edition|297|U|{G}|Creature - Human Berserker|1|2|Whenever Flaxen Intruder deals combat damage to a player, you may sacrifice it. When you do, destroy target artifact or enchantment.| +Welcome Home|Throne of Eldraine Collector's Edition|297|U|{5}{G}{G}|Sorcery - Adventure|1|2|Create three 2/2 green Bear creature tokens.| +Garenbrig Carver|Throne of Eldraine Collector's Edition|298|C|{3}{G}|Creature - Human Warrior|3|2|| +Shield's Might|Throne of Eldraine Collector's Edition|298|C|{1}{G}|Instant - Adventure|3|2|Target creature gets +2/+2 until end of turn.| +Heart's Desire|Throne of Eldraine Collector's Edition|299|R|{G}|Sorcery - Adventure|5|5|Create a 1/1 white Human creature token.| +Lovestruck Beast|Throne of Eldraine Collector's Edition|299|R|{2}{G}|Creature - Beast Noble|5|5|Lovestruck Beast can't attack unless you control a 1/1 creature.| +Rosethorn Acolyte|Throne of Eldraine Collector's Edition|300|C|{2}{G}|Creature - Elf Druid|2|3|{T}: Add one mana of any color.| +Seasonal Ritual|Throne of Eldraine Collector's Edition|300|C|{G}|Sorcery - Adventure|2|3|Add one mana of any color.| +Oaken Boon|Throne of Eldraine Collector's Edition|301|C|{3}{G}|Sorcery - Adventure|6|5|Put two +1/+1 counters on target creature.| +Tuinvale Treefolk|Throne of Eldraine Collector's Edition|301|C|{5}{G}|Creature - Treefolk Druid|6|5|| +Bring Back|Throne of Eldraine Collector's Edition|302|U|{G/W}{G/W}{G/W}{G/W}|Sorcery - Adventure|2|2|Create two 1/1 white Human creature tokens.| +Oakhame Ranger|Throne of Eldraine Collector's Edition|302|U|{G/W}{G/W}{G/W}{G/W}|Creature - Elf Knight|2|2|{T}: Creatures you control get +1/+1 until end of turn.| +Acclaimed Contender|Throne of Eldraine Collector's Edition|334|R|{2}{W}|Creature - Human Knight|3|3|When Acclaimed Contender enters the battlefield, if you control another Knight, look at the top five cards of your library. You may reveal a Knight, Aura, Equipment, or legendary artifact card from among them and put it into your hand. Put the rest on the bottom of your library in a random order.| +Charming Prince|Throne of Eldraine Collector's Edition|335|R|{1}{W}|Creature - Human Noble|2|2|When Charming Prince enters the battlefield, choose one —$• Scry 2.$• You gain 3 life.$• Exile another target creature you own. Return it to the battlefield under your control at the beginning of the next end step.| +The Circle of Loyalty|Throne of Eldraine Collector's Edition|336|M|{4}{W}{W}|Legendary Artifact|||This spell costs {1} less to cast for each Knight you control.$Creatures you control get +1/+1.$Whenever you cast a legendary spell, create a 2/2 white Knight creature token with vigilance.${3}{W}, {T}: Create a 2/2 white Knight creature token with vigilance.| +Happily Ever After|Throne of Eldraine Collector's Edition|337|R|{2}{W}|Enchantment|||When Happily Ever After enters the battlefield, each player gains 5 life and draws a card.$At the beginning of your upkeep, if there are five colors among permanents you control, there are six or more card types among permanents you control and/or cards in your graveyard, and your life total is greater than or equal to your starting life total, you win the game.| +Harmonious Archon|Throne of Eldraine Collector's Edition|338|M|{4}{W}{W}|Creature - Archon|4|5|Flying$Non-Archon creatures have base power and toughness 3/3.$When Harmonious Archon enters the battlefield, create two 1/1 white Human creature tokens.| +Hushbringer|Throne of Eldraine Collector's Edition|339|R|{1}{W}|Creature - Faerie|1|2|Flying, lifelink$Creatures entering the battlefield or dying don't cause abilities to trigger.| +Linden, the Steadfast Queen|Throne of Eldraine Collector's Edition|340|R|{W}{W}{W}|Legendary Creature - Human Noble|3|3|Vigilance$Whenever a white creature you control attacks, you gain 1 life.| +Worthy Knight|Throne of Eldraine Collector's Edition|341|R|{1}{W}|Creature - Human Knight|2|2|Whenever you cast a Knight spell, create a 1/1 white Human creature token.| +Emry, Lurker of the Loch|Throne of Eldraine Collector's Edition|342|R|{2}{U}|Legendary Creature - Merfolk Wizard|1|2|This spell costs {1} less to cast for each artifact you control.$When Emry, Lurker of the Loch enters the battlefield, put the top four cards of your library into your graveyard.${T}: Choose target artifact card in your graveyard. You may cast that card this turn.| +Folio of Fancies|Throne of Eldraine Collector's Edition|343|R|{1}{U}|Artifact|||Players have no maximum hand size.${X}{X}, {T}: Each player draws X cards.${2}{U}, {T}: Each opponent puts a number of cards equal to the number of cards in their hand from the top of their library into their graveyard.| +Gadwick, the Wizened|Throne of Eldraine Collector's Edition|344|R|{X}{U}{U}{U}|Legendary Creature - Human Wizard|3|3|When Gadwick, the Wizened enters the battlefield, draw X cards.$Whenever you cast a blue spell, tap target nonland permanent an opponent controls.| +The Magic Mirror|Throne of Eldraine Collector's Edition|345|M|{6}{U}{U}{U}|Legendary Artifact|||This spell costs {1} less to cast for each instant and sorcery card in your graveyard.$You have no maximum hand size.$At the beginning of your upkeep, put a knowledge counter on The Magic Mirror, then draw a card for each knowledge counter on The Magic Mirror.| +Midnight Clock|Throne of Eldraine Collector's Edition|346|R|{2}{U}|Artifact|||{T}: Add {U}.${2}{U}: Put an hour counter on Midnight Clock.$At the beginning of each upkeep, put an hour counter on Midnight Clock.$When the twelfth hour counter is put on Midnight Clock, shuffle your hand and graveyard into your library, then draw seven cards. Exile Midnight Clock.| +Mirrormade|Throne of Eldraine Collector's Edition|347|R|{1}{U}{U}|Enchantment|||You may have Mirrormade enter the battlefield as a copy of any artifact or enchantment on the battlefield.| +Stolen by the Fae|Throne of Eldraine Collector's Edition|348|R|{X}{U}{U}|Sorcery|||Return target creature with converted mana cost X to its owner's hand. You create X 1/1 blue Faerie creature tokens with flying.| +Vantress Gargoyle|Throne of Eldraine Collector's Edition|349|R|{1}{U}|Artifact Creature - Gargoyle|5|4|Flying$Vantress Gargoyle can't attack unless defending player has seven or more cards in their graveyard.$Vantress Gargoyle can't block unless you have four or more cards in hand.${T}: Each player puts the top card of their library into their graveyard.| +Ayara, First of Locthwain|Throne of Eldraine Collector's Edition|350|R|{B}{B}{B}|Legendary Creature - Elf Noble|2|3|Whenever Ayara, First of Locthwain or another black creature enters the battlefield under your control, each opponent loses 1 life and you gain 1 life.${T}, Sacrifice another black creature: Draw a card.| +Blacklance Paragon|Throne of Eldraine Collector's Edition|351|R|{1}{B}|Creature - Human Knight|3|1|Flash$When Blacklance Paragon enters the battlefield, target Knight gains deathtouch and lifelink until end of turn.| +The Cauldron of Eternity|Throne of Eldraine Collector's Edition|352|M|{10}{B}{B}|Legendary Artifact|||This spell costs {2} less for each creature card in your graveyard.$Whenever a creature you control dies, put it on the bottom of its owner's library.${2}{B}, {T}, Pay 2 life: Return target creature card from your graveyard to the battlefield. Activate this ability only any time you could cast a sorcery.| +Clackbridge Troll|Throne of Eldraine Collector's Edition|353|R|{3}{B}{B}|Creature - Troll|8|8|Trample, haste$When Clackbridge Troll enters the battlefield, target opponent creates three 0/1 white Goat creature tokens.$At the beginning of combat on your turn, any opponent may sacrifice a creature. If a player does, tap Clackbridge Troll, you gain 3 life, and you draw a card.| +Oathsworn Knight|Throne of Eldraine Collector's Edition|354|R|{1}{B}{B}|Creature - Human Knight|0|0|Oathsworn Knight enters the battlefield with four +1/+1 counters on it.$Oathsworn Knight attacks each combat if able.$If damage would be dealt to Oathsworn Knight while it has a +1/+1 counter on it, prevent that damage and remove a +1/+1 counter from it.| +Piper of the Swarm|Throne of Eldraine Collector's Edition|355|R|{1}{B}|Creature - Human Warlock|1|3|Rats you control have menace.${1}{B}, {T}: Create a 1/1 black Rat creature token.${2}{B}{B}, {T}, Sacrifice three Rats: Gain control of target creature.| +Rankle, Master of Pranks|Throne of Eldraine Collector's Edition|356|M|{2}{B}{B}|Legendary Creature - Faerie Rogue|3|3|Flying, haste$Whenever Rankle, Master of Pranks deals combat damage to a player, choose any number —$• Each player discards a card.$• Each player loses 1 life and draws a card.$• Each player sacrifices a creature.| +Wishclaw Talisman|Throne of Eldraine Collector's Edition|357|R|{1}{B}|Artifact|||Wishclaw Talisman enters the battlefield with three wish counters on it.${1}, {T}, Remove a wish counter from Wishclaw Talisman: Search your library for a card, put it into your hand, then shuffle your library. An opponent gains control of Wishclaw Talisman. Activate this ability only during your turn.| +Witch's Vengeance|Throne of Eldraine Collector's Edition|358|R|{1}{B}{B}|Sorcery|||Creatures of the creature type of your choice get -3/-3 until end of turn.| +Embercleave|Throne of Eldraine Collector's Edition|359|M|{4}{R}{R}|Legendary Artifact - Equipment|||Flash$This spell costs {1} less to cast for each attacking creature you control.$When Embercleave enters the battlefield, attach it to target creature you control.$Equipped creature gets +1/+1 and has double strike and trample.$Equip {3}| +Fervent Champion|Throne of Eldraine Collector's Edition|360|R|{R}|Creature - Human Knight|1|1|First strike, haste$Whenever Fervent Champion attacks, another target attacking Knight you control gets +1/+0 until end of turn.$Equip abilities you activate that target Fervent Champion cost {3} less to activate.| +Fires of Invention|Throne of Eldraine Collector's Edition|361|R|{3}{R}|Enchantment|||You can cast spells only during your turn and you can cast no more than two spells each turn.$You may cast spells with converted mana cost less than or equal to the number of lands you control without paying their mana costs.| +Irencrag Feat|Throne of Eldraine Collector's Edition|362|R|{1}{R}{R}{R}|Sorcery|||Add seven {R}. You can cast only one more spell this turn.| +Irencrag Pyromancer|Throne of Eldraine Collector's Edition|363|R|{2}{R}|Creature - Human Wizard|0|4|Whenever you draw your second card each turn, Irencrag Pyromancer deals 3 damage to any target.| +Opportunistic Dragon|Throne of Eldraine Collector's Edition|364|R|{2}{R}{R}|Creature - Dragon|4|3|Flying$When Opportunistic Dragon enters the battlefield, choose target Human or artifact an opponent controls. For as long as Opportunistic Dragon remains on the battlefield, gain control of that permanent, it loses all abilities, and it can't attack or block.| +Robber of the Rich|Throne of Eldraine Collector's Edition|365|M|{1}{R}|Creature - Human Archer Rogue|2|2|Reach, haste$Whenever Robber of the Rich attacks, if defending player has more cards in hand than you, exile the top card of their library. During any turn you attacked with a Rogue, you may cast that card and you may spend mana as though it were mana of any color to cast that spell.| +Sundering Stroke|Throne of Eldraine Collector's Edition|366|R|{6}{R}|Sorcery|||Sundering Stroke deals 7 damage divided as you choose among one, two, or three targets. If at least seven red mana was spent to cast this spell, instead Sundering Stroke deals 7 damage to each of those permanents and/or players.| +Torbran, Thane of Red Fell|Throne of Eldraine Collector's Edition|367|R|{1}{R}{R}{R}|Legendary Creature - Dwarf Noble|2|4|If a red source you control would deal damage to an opponent or a permanent an opponent controls, it deals that much damage plus 2 instead.| +Feasting Troll King|Throne of Eldraine Collector's Edition|368|R|{2}{G}{G}{G}{G}|Creature - Troll Noble|7|6|Vigilance, trample$When Feasting Troll King enters the battlefield, if you cast it from your hand, create three Food tokens.$Sacrifice three Foods: Return Feasting Troll King from your graveyard to the battlefield. Activate this ability only during your turn.| +Gilded Goose|Throne of Eldraine Collector's Edition|369|R|{G}|Creature - Bird|0|2|Flying$When Gilded Goose enters the battlefield, create a Food token.${1}{G}, {T}: Create a Food token.${T}, Sacrifice a Food: Add one mana of any color.| +The Great Henge|Throne of Eldraine Collector's Edition|370|M|{7}{G}{G}|Legendary Artifact|||This spell costs {X} less to cast, where X is the greatest power among creatures you control.${T}: Add {G}{G}. You gain 2 life.$Whenever a nontoken creature enters the battlefield under your control, put a +1/+1 counter on it and draw a card.| +Once Upon a Time|Throne of Eldraine Collector's Edition|371|R|{1}{G}|Instant|||If this spell is the first spell you've cast this game, you may cast it without paying its mana cost.$Look at the top five cards of your library. You may reveal a creature or land card from among them and put it into your hand. Put the rest on the bottom of your library in a random order.| +Questing Beast|Throne of Eldraine Collector's Edition|372|M|{2}{G}{G}|Legendary Creature - Beast|4|4|Vigilance, deathtouch, haste$Questing Beast can't be blocked by creatures with power 2 or less.$Combat damage that would be dealt by creatures you control can't be prevented.$Whenever Questing Beast deals combat damage to an opponent, it deals that much damage to target planeswalker that player controls.| +Return of the Wildspeaker|Throne of Eldraine Collector's Edition|373|R|{4}{G}|Instant|||Choose one —$• Draw cards equal to the greatest power among non-Human creatures you control.$• Non-Human creatures you control get +3/+3 until end of turn.| +Wicked Wolf|Throne of Eldraine Collector's Edition|374|R|{2}{G}{G}|Creature - Wolf|3|3|When Wicked Wolf enters the battlefield, it fights up to one target creature you don't control.$Sacrifice a Food: Put a +1/+1 counter on Wicked Wolf. It gains indestructible until end of turn. Tap it.| +Wildborn Preserver|Throne of Eldraine Collector's Edition|375|R|{1}{G}|Creature - Elf Archer|2|2|Flash$Reach$Whenever another non-Human creature enters the battlefield under your control, you may pay {X}. When you do, put X +1/+1 counters on Wildborn Preserver.| +Yorvo, Lord of Garenbrig|Throne of Eldraine Collector's Edition|376|R|{G}{G}{G}|Legendary Creature - Giant Noble|0|0|Yorvo, Lord of Garenbrig enters the battlefield with four +1/+1 counters on it.$Whenever another green creature enters the battlefield under your control, put a +1/+1 counter on Yorvo. Then if that creature's power is greater than Yorvo's power, put another +1/+1 counter on Yorvo.| +Dance of the Manse|Throne of Eldraine Collector's Edition|377|R|{X}{W}{U}|Sorcery|||Return up to X target artifact and/or non-Aura enchantment cards each with converted mana cost X or less from your graveyard to the battlefield. If X is 6 or more, those permanents are 4/4 creatures in addition to their other types.| +Doom Foretold|Throne of Eldraine Collector's Edition|378|R|{2}{W}{B}|Enchantment|||At the beginning of each player's upkeep, that player sacrifices a nonland, nontoken permanent. If that player can't, they discard a card, they lose 2 life, you draw a card, you gain 2 life, you create a 2/2 white Knight creature token with vigilance, then you sacrifice Doom Foretold.| +Escape to the Wilds|Throne of Eldraine Collector's Edition|379|R|{3}{R}{G}|Sorcery|||Exile the top five cards of your library. You may play cards exiled this way until the end of your next turn.$You may play an additional land this turn.| +Faeburrow Elder|Throne of Eldraine Collector's Edition|380|R|{1}{G}{W}|Creature - Treefolk Druid|0|0|Vigilance$Faeburrow Elder gets +1/+1 for each color among permanents you control.${T}: For each color among permanents you control, add one mana of that color.| +Lochmere Serpent|Throne of Eldraine Collector's Edition|381|R|{4}{U}{B}|Creature - Serpent|7|7|Flash${U}, Sacrifice an Island: Lochmere Serpent can't be blocked this turn.${B}, Sacrifice a Swamp: You gain 1 life and draw a card.${U}{B}: Exile five target cards from an opponent's graveyard. Return Lochmere Serpent from your graveyard to your hand. Activate this ability only any time you could cast a sorcery.| +Outlaws' Merriment|Throne of Eldraine Collector's Edition|382|M|{1}{R}{W}{W}|Enchantment|||At the beginning of your upkeep, choose one at random. Create a red and white creature token with those characteristics.$• 3/1 Human Warrior with trample and haste.$• 2/1 Human Cleric with lifelink and haste.$• 1/2 Human Rogue with haste and "When this creature enters the battlefield, it deals 1 damage to any target."| +Stormfist Crusader|Throne of Eldraine Collector's Edition|383|R|{B}{R}|Creature - Human Knight|2|2|Menace$At the beginning of your upkeep, each player draws a card and loses 1 life.| +Sorcerous Spyglass|Throne of Eldraine Collector's Edition|384|R|{2}|Artifact|||As Sorcerous Spyglass enters the battlefield, look at an opponent's hand, then choose any card name.$Activated abilities of sources with the chosen name can't be activated unless they're mana abilities.| +Stonecoil Serpent|Throne of Eldraine Collector's Edition|385|R|{X}|Artifact Creature - Snake|0|0|Reach, trample, protection from multicolored$Stonecoil Serpent enters the battlefield with X +1/+1 counters on it.| +Castle Ardenvale|Throne of Eldraine Collector's Edition|386|R||Land|||Castle Ardenvale enters the battlefield tapped unless you control a Plains.${T}: Add {W}.${2}{W}{W}, {T}: Create a 1/1 white Human creature token.| +Castle Embereth|Throne of Eldraine Collector's Edition|387|R||Land|||Castle Embereth enters the battlefield tapped unless you control a Mountain.${T}: Add {R}.${1}{R}{R}, {T}: Creatures you control get +1/+0 until end of turn.| +Castle Garenbrig|Throne of Eldraine Collector's Edition|388|R||Land|||Castle Garenbrig enters the battlefield tapped unless you control a Forest.${T}: Add {G}.${2}{G}{G}, {T}: Add six {G}. Spend this mana only to cast creature spells or activate abilities of creatures.| +Castle Locthwain|Throne of Eldraine Collector's Edition|389|R||Land|||Castle Locthwain enters the battlefield tapped unless you control a Swamp.${T}: Add {B}.${1}{B}{B}, {T}: Draw a card, then you lose life equal to the number of cards in your hand.| +Castle Vantress|Throne of Eldraine Collector's Edition|390|R||Land|||Castle Vantress enters the battlefield tapped unless you control an Island.${T}: Add {U}.${2}{U}{U}, {T}: Scry 2.| +Fabled Passage|Throne of Eldraine Collector's Edition|391|R||Land|||{T}, Sacrifice Fabled Passage: Search your library for a basic land card, put it onto the battlefield tapped, then shuffle your library. Then if you control four or more lands, untap that land.| diff --git a/Utils/mtg-sets-data.txt b/Utils/mtg-sets-data.txt index 37b5025c86..5c02dc8f1b 100644 --- a/Utils/mtg-sets-data.txt +++ b/Utils/mtg-sets-data.txt @@ -185,6 +185,7 @@ Super Series|SUS| Theros|THS| Tempest|TMP| Throne of Eldraine|ELD| +Throne of Eldraine Collector's Edition|CELD| Torment|TOR| Tempest Remastered|TPR| Time Spiral "Timeshifted"|TSB| From d5ab4a60d5daed02fb2bd3e0903e2b2ee1953832 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 21 Sep 2019 16:09:02 -0400 Subject: [PATCH 259/373] Implemented Weapon Rack --- Mage.Sets/src/mage/cards/w/WeaponRack.java | 82 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 83 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/w/WeaponRack.java diff --git a/Mage.Sets/src/mage/cards/w/WeaponRack.java b/Mage.Sets/src/mage/cards/w/WeaponRack.java new file mode 100644 index 0000000000..70066e2551 --- /dev/null +++ b/Mage.Sets/src/mage/cards/w/WeaponRack.java @@ -0,0 +1,82 @@ +package mage.cards.w; + +import mage.abilities.Ability; +import mage.abilities.common.ActivateAsSorceryActivatedAbility; +import mage.abilities.common.EntersBattlefieldAbility; +import mage.abilities.costs.common.TapSourceCost; +import mage.abilities.effects.OneShotEffect; +import mage.abilities.effects.common.counter.AddCountersSourceEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Outcome; +import mage.constants.Zone; +import mage.counters.CounterType; +import mage.game.Game; +import mage.game.permanent.Permanent; +import mage.target.common.TargetCreaturePermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class WeaponRack extends CardImpl { + + public WeaponRack(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT}, "{4}"); + + // Weapon Rack enters the battlefield with three +1/+1 counters on it. + this.addAbility(new EntersBattlefieldAbility( + new AddCountersSourceEffect(CounterType.P1P1.createInstance(3)), + "{this} enters the battlefield with three +1/+1 counters on it" + )); + + // {T}: Move a +1/+1 counter from Weapon Rack onto target creature. Activate this ability only any time you could cast a sorcery. + Ability ability = new ActivateAsSorceryActivatedAbility( + Zone.BATTLEFIELD, new WeaponRackEffect(), new TapSourceCost() + ); + ability.addTarget(new TargetCreaturePermanent()); + this.addAbility(ability); + } + + private WeaponRack(final WeaponRack card) { + super(card); + } + + @Override + public WeaponRack copy() { + return new WeaponRack(this); + } +} + +class WeaponRackEffect extends OneShotEffect { + + WeaponRackEffect() { + super(Outcome.Benefit); + staticText = "move a +1/+1 counter from {this} onto target creature"; + } + + private WeaponRackEffect(final WeaponRackEffect effect) { + super(effect); + } + + @Override + public WeaponRackEffect copy() { + return new WeaponRackEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + Permanent sourcePermanent = game.getPermanent(source.getSourceId()); + if (sourcePermanent == null || !sourcePermanent.getCounters(game).containsKey(CounterType.P1P1)) { + return false; + } + Permanent permanent = game.getPermanent(source.getFirstTarget()); + if (permanent == null || !permanent.addCounters(CounterType.P1P1.createInstance(), source, game)) { + return false; + } + sourcePermanent.removeCounters(CounterType.P1P1.createInstance(), game); + return true; + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 8052a5d039..5b72bbb0d2 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -300,6 +300,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Vantress Paladin", 72, Rarity.COMMON, mage.cards.v.VantressPaladin.class)); cards.add(new SetCardInfo("Venerable Knight", 35, Rarity.UNCOMMON, mage.cards.v.VenerableKnight.class)); cards.add(new SetCardInfo("Wandermare", 204, Rarity.UNCOMMON, mage.cards.w.Wandermare.class)); + cards.add(new SetCardInfo("Weapon Rack", 236, Rarity.COMMON, mage.cards.w.WeaponRack.class)); cards.add(new SetCardInfo("Weaselback Redcap", 148, Rarity.COMMON, mage.cards.w.WeaselbackRedcap.class)); cards.add(new SetCardInfo("Wicked Guardian", 109, Rarity.COMMON, mage.cards.w.WickedGuardian.class)); cards.add(new SetCardInfo("Wicked Wolf", 181, Rarity.RARE, mage.cards.w.WickedWolf.class)); From e9f04114d8c4a8e01f14fa1a548b9727fe910172 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 21 Sep 2019 16:17:01 -0400 Subject: [PATCH 260/373] Implemented Kenrith's Transformation --- .../mage/cards/k/KenrithsTransformation.java | 58 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 59 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/k/KenrithsTransformation.java diff --git a/Mage.Sets/src/mage/cards/k/KenrithsTransformation.java b/Mage.Sets/src/mage/cards/k/KenrithsTransformation.java new file mode 100644 index 0000000000..800bc419d5 --- /dev/null +++ b/Mage.Sets/src/mage/cards/k/KenrithsTransformation.java @@ -0,0 +1,58 @@ +package mage.cards.k; + +import mage.abilities.Ability; +import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.effects.common.AttachEffect; +import mage.abilities.effects.common.DrawCardSourceControllerEffect; +import mage.abilities.effects.common.continuous.BecomesCreatureAttachedEffect; +import mage.abilities.keyword.EnchantAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.Outcome; +import mage.constants.SubType; +import mage.game.permanent.token.custom.CreatureToken; +import mage.target.TargetPermanent; +import mage.target.common.TargetCreaturePermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class KenrithsTransformation extends CardImpl { + + public KenrithsTransformation(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ENCHANTMENT}, "{1}{G}"); + + this.subtype.add(SubType.AURA); + + // Enchant creature + TargetPermanent auraTarget = new TargetCreaturePermanent(); + this.getSpellAbility().addTarget(auraTarget); + this.getSpellAbility().addEffect(new AttachEffect(Outcome.BoostCreature)); + Ability ability = new EnchantAbility(auraTarget.getTargetName()); + this.addAbility(ability); + + // When Kenrith's Transformation enters the battlefield, draw a card. + this.addAbility(new EntersBattlefieldTriggeredAbility(new DrawCardSourceControllerEffect(1))); + + // Enchanted creature loses all abilities and is a green Elk creature with base power and toughness 3/3. + this.addAbility(new SimpleStaticAbility(new BecomesCreatureAttachedEffect( + new CreatureToken(3, 3, "", SubType.ELK).withColor("G"), + "Enchanted creature loses all abilities and is a green Elk creature with base power and toughness 3/3", + Duration.WhileOnBattlefield, BecomesCreatureAttachedEffect.LoseType.ALL + ))); + } + + private KenrithsTransformation(final KenrithsTransformation card) { + super(card); + } + + @Override + public KenrithsTransformation copy() { + return new KenrithsTransformation(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 5b72bbb0d2..2c7579e810 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -152,6 +152,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Joust", 129, Rarity.UNCOMMON, mage.cards.j.Joust.class)); cards.add(new SetCardInfo("Jousting Dummy", 224, Rarity.COMMON, mage.cards.j.JoustingDummy.class)); cards.add(new SetCardInfo("Keeper of Fables", 163, Rarity.UNCOMMON, mage.cards.k.KeeperOfFables.class)); + cards.add(new SetCardInfo("Kenrith's Transformation", 164, Rarity.UNCOMMON, mage.cards.k.KenrithsTransformation.class)); cards.add(new SetCardInfo("Kenrith, the Returned King", 303, Rarity.MYTHIC, mage.cards.k.KenrithTheReturnedKing.class)); cards.add(new SetCardInfo("Knight of the Keep", 19, Rarity.COMMON, mage.cards.k.KnightOfTheKeep.class)); cards.add(new SetCardInfo("Knights' Charge", 328, Rarity.RARE, mage.cards.k.KnightsCharge.class)); From 112cc446667a6e8164ea4c523cfa6535da575802 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 21 Sep 2019 16:30:06 -0400 Subject: [PATCH 261/373] Implemented Bartered Cow --- Mage.Sets/src/mage/cards/b/BarteredCow.java | 66 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 67 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/b/BarteredCow.java diff --git a/Mage.Sets/src/mage/cards/b/BarteredCow.java b/Mage.Sets/src/mage/cards/b/BarteredCow.java new file mode 100644 index 0000000000..07fb03f4e6 --- /dev/null +++ b/Mage.Sets/src/mage/cards/b/BarteredCow.java @@ -0,0 +1,66 @@ +package mage.cards.b; + +import mage.MageInt; +import mage.MageObject; +import mage.abilities.common.DiesTriggeredAbility; +import mage.abilities.effects.Effect; +import mage.abilities.effects.common.CreateTokenEffect; +import mage.abilities.effects.common.DiscardCardControllerTriggeredAbility; +import mage.abilities.meta.OrTriggeredAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.constants.Zone; +import mage.filter.FilterCard; +import mage.filter.predicate.ObjectSourcePlayer; +import mage.filter.predicate.ObjectSourcePlayerPredicate; +import mage.game.Game; +import mage.game.permanent.token.FoodToken; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class BarteredCow extends CardImpl { + + private static final FilterCard filter = new FilterCard(); + + static { + filter.add(BarteredCowPredicate.instance); + } + + public BarteredCow(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{3}{W}"); + + this.subtype.add(SubType.OX); + this.power = new MageInt(3); + this.toughness = new MageInt(3); + + // When Bartered Cow dies or when you discard it, create a Food token. + this.addAbility(new OrTriggeredAbility( + Zone.ALL, new CreateTokenEffect(new FoodToken()), false, + "When {this} dies or when you discard it, ", new DiesTriggeredAbility((Effect) null), + new DiscardCardControllerTriggeredAbility(null, false, filter) + )); + } + + private BarteredCow(final BarteredCow card) { + super(card); + } + + @Override + public BarteredCow copy() { + return new BarteredCow(this); + } +} + +enum BarteredCowPredicate implements ObjectSourcePlayerPredicate> { + instance; + + @Override + public boolean apply(ObjectSourcePlayer input, Game game) { + return input.getObject().getId().equals(input.getSourceId()); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 2c7579e810..5657c97769 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -41,6 +41,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Banish into Fable", 325, Rarity.RARE, mage.cards.b.BanishIntoFable.class)); cards.add(new SetCardInfo("Barge In", 112, Rarity.COMMON, mage.cards.b.BargeIn.class)); cards.add(new SetCardInfo("Barrow Witches", 77, Rarity.COMMON, mage.cards.b.BarrowWitches.class)); + cards.add(new SetCardInfo("Bartered Cow", 6, Rarity.COMMON, mage.cards.b.BarteredCow.class)); cards.add(new SetCardInfo("Beanstalk Giant", 149, Rarity.UNCOMMON, mage.cards.b.BeanstalkGiant.class)); cards.add(new SetCardInfo("Belle of the Brawl", 78, Rarity.UNCOMMON, mage.cards.b.BelleOfTheBrawl.class)); cards.add(new SetCardInfo("Beloved Princess", 7, Rarity.COMMON, mage.cards.b.BelovedPrincess.class)); From fa73f2d1a54551b58b3781fce452f57657968226 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 21 Sep 2019 16:42:03 -0400 Subject: [PATCH 262/373] fixed a verify error --- Mage.Sets/src/mage/sets/ThroneOfEldraineCollectorsEdition.java | 1 + 1 file changed, 1 insertion(+) diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraineCollectorsEdition.java b/Mage.Sets/src/mage/sets/ThroneOfEldraineCollectorsEdition.java index d4d578a987..f9791879c4 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraineCollectorsEdition.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraineCollectorsEdition.java @@ -18,6 +18,7 @@ public final class ThroneOfEldraineCollectorsEdition extends ExpansionSet { private ThroneOfEldraineCollectorsEdition() { super("Throne of Eldraine Collector's Edition", "CELD", ExpansionSet.buildDate(2019, 10, 4), SetType.PROMOTIONAL); + this.hasBasicLands = false; cards.add(new SetCardInfo("Acclaimed Contender", 334, Rarity.RARE, mage.cards.a.AcclaimedContender.class)); cards.add(new SetCardInfo("Animating Faerie", 280, Rarity.UNCOMMON, mage.cards.a.AnimatingFaerie.class)); From 48a678fad9a37e71ec2b68a70cd0cf4479a7da67 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 21 Sep 2019 19:40:19 -0400 Subject: [PATCH 263/373] Implemented Covetous Urge --- Mage.Sets/src/mage/cards/c/CovetousUrge.java | 172 ++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + .../abilities/effects/ContinuousEffect.java | 4 + .../effects/ContinuousEffectImpl.java | 7 + 4 files changed, 184 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/c/CovetousUrge.java diff --git a/Mage.Sets/src/mage/cards/c/CovetousUrge.java b/Mage.Sets/src/mage/cards/c/CovetousUrge.java new file mode 100644 index 0000000000..96ff870840 --- /dev/null +++ b/Mage.Sets/src/mage/cards/c/CovetousUrge.java @@ -0,0 +1,172 @@ +package mage.cards.c; + +import mage.MageObjectReference; +import mage.abilities.Ability; +import mage.abilities.effects.AsThoughEffectImpl; +import mage.abilities.effects.AsThoughManaEffect; +import mage.abilities.effects.OneShotEffect; +import mage.cards.Card; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.*; +import mage.filter.StaticFilters; +import mage.game.Game; +import mage.players.ManaPoolItem; +import mage.players.Player; +import mage.target.TargetCard; +import mage.target.common.TargetCardInGraveyard; +import mage.target.common.TargetCardInHand; +import mage.target.common.TargetOpponent; +import mage.target.targetpointer.FixedTarget; + +import java.util.Objects; +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class CovetousUrge extends CardImpl { + + public CovetousUrge(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.SORCERY}, "{U/B}{U/B}{U/B}{U/B}"); + + // Target opponent reveals their hand. You choose a nonland card from that player's graveyard or hand and exile it. You may cast that card for as long as it remains exiled, and you may spend mana as though it were mana of any color to cast that spell. + this.getSpellAbility().addEffect(new CovetousUrgeEffect()); + this.getSpellAbility().addTarget(new TargetOpponent()); + } + + private CovetousUrge(final CovetousUrge card) { + super(card); + } + + @Override + public CovetousUrge copy() { + return new CovetousUrge(this); + } +} + +class CovetousUrgeEffect extends OneShotEffect { + + CovetousUrgeEffect() { + super(Outcome.Benefit); + staticText = "Target opponent reveals their hand. You choose a nonland card from that player's graveyard " + + "or hand and exile it. You may cast that card for as long as it remains exiled," + + " and you may spend mana as though it were mana of any color to cast that spell."; + } + + private CovetousUrgeEffect(final CovetousUrgeEffect effect) { + super(effect); + } + + @Override + public CovetousUrgeEffect copy() { + return new CovetousUrgeEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + Player controller = game.getPlayer(source.getControllerId()); + Player player = game.getPlayer(source.getFirstTarget()); + if (controller == null || player == null) { + return false; + } + player.revealCards(source, player.getHand(), game); + if (!controller.chooseUse(outcome, "Choose a nonland card to exile?", source, game)) { + return false; + } + TargetCard target; + if (player.getGraveyard().isEmpty() || controller.chooseUse(outcome, + "Exile a nonland card from " + player.getName() + "'s hand or graveyard", + "", "Hand", "Graveyard", source, game)) { + if (player.getHand().isEmpty()) { + return true; + } + target = new TargetCardInHand(StaticFilters.FILTER_CARD_A_NON_LAND); + controller.choose(outcome, player.getHand(), target, game); + } else { + target = new TargetCardInGraveyard(StaticFilters.FILTER_CARD_A_NON_LAND); + controller.choose(outcome, player.getGraveyard(), target, game); + } + Card card = game.getCard(target.getFirstTarget()); + if (card == null || !controller.moveCards(card, Zone.EXILED, source, game)) { + return false; + } + if (card.getSpellAbility() == null) { + return true; + } + game.addEffect(new CovetousUrgeCastFromExileEffect(new MageObjectReference(card, game)), source); + game.addEffect(new CovetousUrgeSpendAnyManaEffect().setTargetPointer(new FixedTarget(card, game)), source); + return true; + } +} + +class CovetousUrgeCastFromExileEffect extends AsThoughEffectImpl { + + private final MageObjectReference mor; + + CovetousUrgeCastFromExileEffect(MageObjectReference mor) { + super(AsThoughEffectType.PLAY_FROM_NOT_OWN_HAND_ZONE, Duration.Custom, Outcome.Benefit); + this.mor = mor; + } + + private CovetousUrgeCastFromExileEffect(final CovetousUrgeCastFromExileEffect effect) { + super(effect); + this.mor = effect.mor; + } + + @Override + public boolean apply(Game game, Ability source) { + return true; + } + + @Override + public CovetousUrgeCastFromExileEffect copy() { + return new CovetousUrgeCastFromExileEffect(this); + } + + @Override + public boolean applies(UUID sourceId, Ability source, UUID affectedControllerId, Game game) { + Card card = mor.getCard(game); + if (card == null || !sourceId.equals(card.getId()) + || !source.isControlledBy(affectedControllerId)) { + return false; + } + discard(); + return false; + } +} + +class CovetousUrgeSpendAnyManaEffect extends AsThoughEffectImpl implements AsThoughManaEffect { + + CovetousUrgeSpendAnyManaEffect() { + super(AsThoughEffectType.SPEND_OTHER_MANA, Duration.Custom, Outcome.Benefit); + } + + private CovetousUrgeSpendAnyManaEffect(final CovetousUrgeSpendAnyManaEffect effect) { + super(effect); + } + + @Override + public boolean apply(Game game, Ability source) { + return true; + } + + @Override + public CovetousUrgeSpendAnyManaEffect copy() { + return new CovetousUrgeSpendAnyManaEffect(this); + } + + @Override + public boolean applies(UUID objectId, Ability source, UUID affectedControllerId, Game game) { + FixedTarget fixedTarget = ((FixedTarget) getTargetPointer()); + return source.isControlledBy(affectedControllerId) + && Objects.equals(objectId, fixedTarget.getTarget()) + && fixedTarget.getZoneChangeCounter() + 1 == game.getState().getZoneChangeCounter(objectId) + && game.getState().getZone(objectId) == Zone.STACK; + } + + @Override + public ManaType getAsThoughManaType(ManaType manaType, ManaPoolItem mana, UUID affectedControllerId, Ability source, Game game) { + return mana.getFirstAvailable(); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 5657c97769..0b20461e44 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -70,6 +70,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Clockwork Servant", 216, Rarity.UNCOMMON, mage.cards.c.ClockworkServant.class)); cards.add(new SetCardInfo("Command Tower", 333, Rarity.COMMON, mage.cards.c.CommandTower.class)); cards.add(new SetCardInfo("Corridor Monitor", 41, Rarity.COMMON, mage.cards.c.CorridorMonitor.class)); + cards.add(new SetCardInfo("Covetous Urge", 207, Rarity.UNCOMMON, mage.cards.c.CovetousUrge.class)); cards.add(new SetCardInfo("Crashing Drawbridge", 217, Rarity.COMMON, mage.cards.c.CrashingDrawbridge.class)); cards.add(new SetCardInfo("Crystal Slipper", 119, Rarity.COMMON, mage.cards.c.CrystalSlipper.class)); cards.add(new SetCardInfo("Curious Pair", 150, Rarity.COMMON, mage.cards.c.CuriousPair.class)); diff --git a/Mage/src/main/java/mage/abilities/effects/ContinuousEffect.java b/Mage/src/main/java/mage/abilities/effects/ContinuousEffect.java index 66f262c750..3666e45af7 100644 --- a/Mage/src/main/java/mage/abilities/effects/ContinuousEffect.java +++ b/Mage/src/main/java/mage/abilities/effects/ContinuousEffect.java @@ -7,6 +7,7 @@ import mage.constants.Duration; import mage.constants.Layer; import mage.constants.SubLayer; import mage.game.Game; +import mage.target.targetpointer.TargetPointer; import java.util.EnumSet; import java.util.List; @@ -77,4 +78,7 @@ public interface ContinuousEffect extends Effect { boolean isTemporary(); void setTemporary(boolean temporary); + + @Override + ContinuousEffect setTargetPointer(TargetPointer targetPointer); } diff --git a/Mage/src/main/java/mage/abilities/effects/ContinuousEffectImpl.java b/Mage/src/main/java/mage/abilities/effects/ContinuousEffectImpl.java index 7cc9ed6c86..e414bfb3c1 100644 --- a/Mage/src/main/java/mage/abilities/effects/ContinuousEffectImpl.java +++ b/Mage/src/main/java/mage/abilities/effects/ContinuousEffectImpl.java @@ -10,6 +10,7 @@ import mage.abilities.dynamicvalue.common.StaticValue; import mage.constants.*; import mage.game.Game; import mage.players.Player; +import mage.target.targetpointer.TargetPointer; import java.util.*; @@ -334,4 +335,10 @@ public abstract class ContinuousEffectImpl extends EffectImpl implements Continu dependendToTypes.add(dependencyType); } + @Override + public ContinuousEffect setTargetPointer(TargetPointer targetPointer) { + super.setTargetPointer(targetPointer); + return this; + } + } From 5a5e51a1511d1f986c881dfb3fe6e29dde5d9faf Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 21 Sep 2019 20:00:46 -0400 Subject: [PATCH 264/373] Implemented Memory Theft --- Mage.Sets/src/mage/cards/m/MemoryTheft.java | 86 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 87 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/m/MemoryTheft.java diff --git a/Mage.Sets/src/mage/cards/m/MemoryTheft.java b/Mage.Sets/src/mage/cards/m/MemoryTheft.java new file mode 100644 index 0000000000..47a31c1099 --- /dev/null +++ b/Mage.Sets/src/mage/cards/m/MemoryTheft.java @@ -0,0 +1,86 @@ +package mage.cards.m; + +import mage.abilities.Ability; +import mage.abilities.effects.OneShotEffect; +import mage.abilities.effects.common.discard.DiscardCardYouChooseTargetEffect; +import mage.cards.Card; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Outcome; +import mage.constants.TargetController; +import mage.constants.Zone; +import mage.filter.FilterCard; +import mage.filter.StaticFilters; +import mage.filter.predicate.mageobject.AdventurePredicate; +import mage.filter.predicate.other.OwnerIdPredicate; +import mage.game.Game; +import mage.players.Player; +import mage.target.TargetCard; +import mage.target.common.TargetCardInExile; +import mage.target.common.TargetOpponent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class MemoryTheft extends CardImpl { + + public MemoryTheft(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.SORCERY}, "{2}{B}"); + + // Target opponent reveals their hand. You choose a nonland card from it. That player discards that card. You may put a card that has an Adventure that player owns from exile into that player's graveyard. + this.getSpellAbility().addEffect( + new DiscardCardYouChooseTargetEffect(StaticFilters.FILTER_CARD_NON_LAND, TargetController.ANY) + ); + this.getSpellAbility().addEffect(new MemoryTheftEffect()); + this.getSpellAbility().addTarget(new TargetOpponent()); + } + + private MemoryTheft(final MemoryTheft card) { + super(card); + } + + @Override + public MemoryTheft copy() { + return new MemoryTheft(this); + } +} + +class MemoryTheftEffect extends OneShotEffect { + + MemoryTheftEffect() { + super(Outcome.Benefit); + staticText = "Target opponent reveals their hand. You choose a nonland card from it. " + + "That player discards that card. You may put a card that has an Adventure " + + "that player owns from exile into that player's graveyard."; + } + + private MemoryTheftEffect(final MemoryTheftEffect effect) { + super(effect); + } + + @Override + public MemoryTheftEffect copy() { + return new MemoryTheftEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + Player controller = game.getPlayer(source.getControllerId()); + Player player = game.getPlayer(source.getFirstTarget()); + if (controller == null || player == null) { + return false; + } + FilterCard filter = new FilterCard("card owned by " + player.getName() + " that has an Adventure"); + filter.add(AdventurePredicate.instance); + filter.add(new OwnerIdPredicate(player.getId())); + TargetCard target = new TargetCardInExile(0, 1, filter, null, true); + if (!controller.choose(outcome, target, source.getSourceId(), game)) { + return false; + } + Card card = game.getCard(target.getFirstTarget()); + return controller.moveCards(card, Zone.GRAVEYARD, source, game); + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 0b20461e44..b5ffa3ba5f 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -175,6 +175,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Mantle of Tides", 52, Rarity.COMMON, mage.cards.m.MantleOfTides.class)); cards.add(new SetCardInfo("Maraleaf Pixie", 196, Rarity.UNCOMMON, mage.cards.m.MaraleafPixie.class)); cards.add(new SetCardInfo("Maraleaf Rider", 166, Rarity.COMMON, mage.cards.m.MaraleafRider.class)); + cards.add(new SetCardInfo("Memory Theft", 96, Rarity.COMMON, mage.cards.m.MemoryTheft.class)); cards.add(new SetCardInfo("Merchant of the Vale", 131, Rarity.COMMON, mage.cards.m.MerchantOfTheVale.class)); cards.add(new SetCardInfo("Merfolk Secretkeeper", 53, Rarity.COMMON, mage.cards.m.MerfolkSecretkeeper.class)); cards.add(new SetCardInfo("Midnight Clock", 54, Rarity.RARE, mage.cards.m.MidnightClock.class)); From 3b6da056ea5d4f155d8599ea3c156be97f249594 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 21 Sep 2019 20:36:24 -0400 Subject: [PATCH 265/373] Implemented Hushbringer --- Mage.Sets/src/mage/cards/h/Hushbringer.java | 119 ++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + .../ThroneOfEldraineCollectorsEdition.java | 1 + 3 files changed, 121 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/h/Hushbringer.java diff --git a/Mage.Sets/src/mage/cards/h/Hushbringer.java b/Mage.Sets/src/mage/cards/h/Hushbringer.java new file mode 100644 index 0000000000..76e83933fb --- /dev/null +++ b/Mage.Sets/src/mage/cards/h/Hushbringer.java @@ -0,0 +1,119 @@ +package mage.cards.h; + +import mage.MageInt; +import mage.MageObject; +import mage.abilities.Ability; +import mage.abilities.TriggeredAbility; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.effects.ContinuousRuleModifyingEffectImpl; +import mage.abilities.keyword.FlyingAbility; +import mage.abilities.keyword.LifelinkAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.*; +import mage.game.Game; +import mage.game.events.EntersTheBattlefieldEvent; +import mage.game.events.GameEvent; +import mage.game.events.ZoneChangeEvent; +import mage.game.permanent.Permanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class Hushbringer extends CardImpl { + + public Hushbringer(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{1}{W}"); + + this.subtype.add(SubType.FAERIE); + this.power = new MageInt(1); + this.toughness = new MageInt(2); + + // Flying + this.addAbility(FlyingAbility.getInstance()); + + // Lifelink + this.addAbility(LifelinkAbility.getInstance()); + + // Creatures entering the battlefield or dying don't cause abilities to trigger. + this.addAbility(new SimpleStaticAbility(new HushbringerEffect())); + } + + private Hushbringer(final Hushbringer card) { + super(card); + } + + @Override + public Hushbringer copy() { + return new Hushbringer(this); + } +} + +class HushbringerEffect extends ContinuousRuleModifyingEffectImpl { + + HushbringerEffect() { + super(Duration.WhileOnBattlefield, Outcome.Detriment, false, false); + staticText = "Creatures entering the battlefield or dying don't cause abilities to trigger"; + } + + private HushbringerEffect(final HushbringerEffect effect) { + super(effect); + } + + @Override + public boolean checksEventType(GameEvent event, Game game) { + return event.getType() == GameEvent.EventType.ENTERS_THE_BATTLEFIELD + || event.getType() == GameEvent.EventType.ZONE_CHANGE; + } + + @Override + public boolean applies(GameEvent event, Ability source, Game game) { + Ability ability = (Ability) getValue("targetAbility"); + if (ability == null || ability.getAbilityType() != AbilityType.TRIGGERED) { + return false; + } + Permanent permanent; + switch (event.getType()) { + case ENTERS_THE_BATTLEFIELD: + permanent = ((EntersTheBattlefieldEvent) event).getTarget(); + break; + case ZONE_CHANGE: + ZoneChangeEvent zEvent = ((ZoneChangeEvent) event); + if (!zEvent.isDiesEvent()) { + return false; + } + permanent = zEvent.getTarget(); + break; + default: + return false; + } + + if (permanent == null || !permanent.isCreature()) { + return false; + } + return (((TriggeredAbility) ability).checkTrigger(event, game)); + } + + @Override + public String getInfoMessage(Ability source, GameEvent event, Game game) { + MageObject enteringObject = game.getObject(event.getSourceId()); + MageObject sourceObject = game.getObject(source.getSourceId()); + Ability ability = (Ability) getValue("targetAbility"); + if (enteringObject == null || sourceObject == null || ability == null) { + return null; + } + MageObject abilitObject = game.getObject(ability.getSourceId()); + if (abilitObject == null) { + return null; + } + return sourceObject.getLogName() + " prevented ability of " + + abilitObject.getLogName() + " from triggering."; + } + + @Override + public HushbringerEffect copy() { + return new HushbringerEffect(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index b5ffa3ba5f..2ab7cc2697 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -138,6 +138,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Harmonious Archon", 17, Rarity.MYTHIC, mage.cards.h.HarmoniousArchon.class)); cards.add(new SetCardInfo("Henge Walker", 221, Rarity.COMMON, mage.cards.h.HengeWalker.class)); cards.add(new SetCardInfo("Heraldic Banner", 222, Rarity.UNCOMMON, mage.cards.h.HeraldicBanner.class)); + cards.add(new SetCardInfo("Hushbringer", 18, Rarity.RARE, mage.cards.h.Hushbringer.class)); cards.add(new SetCardInfo("Hypnotic Sprite", 49, Rarity.UNCOMMON, mage.cards.h.HypnoticSprite.class)); cards.add(new SetCardInfo("Idyllic Grange", 246, Rarity.COMMON, mage.cards.i.IdyllicGrange.class)); cards.add(new SetCardInfo("Improbable Alliance", 193, Rarity.UNCOMMON, mage.cards.i.ImprobableAlliance.class)); diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraineCollectorsEdition.java b/Mage.Sets/src/mage/sets/ThroneOfEldraineCollectorsEdition.java index f9791879c4..55abb35254 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraineCollectorsEdition.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraineCollectorsEdition.java @@ -59,6 +59,7 @@ public final class ThroneOfEldraineCollectorsEdition extends ExpansionSet { cards.add(new SetCardInfo("Gilded Goose", 369, Rarity.RARE, mage.cards.g.GildedGoose.class)); cards.add(new SetCardInfo("Happily Ever After", 337, Rarity.RARE, mage.cards.h.HappilyEverAfter.class)); cards.add(new SetCardInfo("Harmonious Archon", 338, Rarity.MYTHIC, mage.cards.h.HarmoniousArchon.class)); + cards.add(new SetCardInfo("Hushbringer", 339, Rarity.RARE, mage.cards.h.Hushbringer.class)); cards.add(new SetCardInfo("Hypnotic Sprite", 283, Rarity.UNCOMMON, mage.cards.h.HypnoticSprite.class)); cards.add(new SetCardInfo("Irencrag Feat", 362, Rarity.RARE, mage.cards.i.IrencragFeat.class)); cards.add(new SetCardInfo("Irencrag Pyromancer", 363, Rarity.RARE, mage.cards.i.IrencragPyromancer.class)); From c3807f6c381f10b41052f47ae043c05846d940ad Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 21 Sep 2019 20:53:21 -0400 Subject: [PATCH 266/373] Implemented Deathless Knight --- .../src/mage/cards/d/DeathlessKnight.java | 93 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + 2 files changed, 94 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/d/DeathlessKnight.java diff --git a/Mage.Sets/src/mage/cards/d/DeathlessKnight.java b/Mage.Sets/src/mage/cards/d/DeathlessKnight.java new file mode 100644 index 0000000000..8b536dbf10 --- /dev/null +++ b/Mage.Sets/src/mage/cards/d/DeathlessKnight.java @@ -0,0 +1,93 @@ +package mage.cards.d; + +import mage.MageInt; +import mage.abilities.TriggeredAbilityImpl; +import mage.abilities.effects.common.ReturnSourceFromGraveyardToHandEffect; +import mage.abilities.keyword.HasteAbility; +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 java.util.UUID; + +/** + * @author TheElk801 + */ +public final class DeathlessKnight extends CardImpl { + + public DeathlessKnight(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{B/G}{B/G}{B/G}{B/G}"); + + this.subtype.add(SubType.SKELETON); + this.subtype.add(SubType.KNIGHT); + this.power = new MageInt(4); + this.toughness = new MageInt(2); + + // Haste + this.addAbility(HasteAbility.getInstance()); + + // When you gain life for the first time each turn, return Deathless Knight from your graveyard to your hand. + this.addAbility(new DeathlessKnightTriggeredAbility()); + } + + private DeathlessKnight(final DeathlessKnight card) { + super(card); + } + + @Override + public DeathlessKnight copy() { + return new DeathlessKnight(this); + } +} + +class DeathlessKnightTriggeredAbility extends TriggeredAbilityImpl { + + private boolean triggeredOnce = false; + + DeathlessKnightTriggeredAbility() { + super(Zone.ALL, new ReturnSourceFromGraveyardToHandEffect(), false); + } + + private DeathlessKnightTriggeredAbility(final DeathlessKnightTriggeredAbility ability) { + super(ability); + this.triggeredOnce = ability.triggeredOnce; + } + + @Override + public boolean checkEventType(GameEvent event, Game game) { + return event.getType() == GameEvent.EventType.GAINED_LIFE + || event.getType() == GameEvent.EventType.END_PHASE_POST; + } + + @Override + public boolean checkTrigger(GameEvent event, Game game) { + if (event.getType() == GameEvent.EventType.END_PHASE_POST) { + triggeredOnce = false; + return false; + } + if (event.getType() != GameEvent.EventType.GAINED_LIFE + || !event.getPlayerId().equals(controllerId) + || game.getState().getZone(this.getSourceId()) == Zone.GRAVEYARD) { + return false; + } + if (triggeredOnce) { + return false; + } + triggeredOnce = true; + return true; + } + + @Override + public String getRule() { + return "When you gain life for the first time each turn, return {this} from your graveyard to your hand."; + } + + @Override + public DeathlessKnightTriggeredAbility copy() { + return new DeathlessKnightTriggeredAbility(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 2ab7cc2697..b96ca36576 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -76,6 +76,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Curious Pair", 150, Rarity.COMMON, mage.cards.c.CuriousPair.class)); cards.add(new SetCardInfo("Dance of the Manse", 186, Rarity.RARE, mage.cards.d.DanceOfTheManse.class)); cards.add(new SetCardInfo("Deafening Silence", 10, Rarity.UNCOMMON, mage.cards.d.DeafeningSilence.class)); + cards.add(new SetCardInfo("Deathless Knight", 208, Rarity.UNCOMMON, mage.cards.d.DeathlessKnight.class)); cards.add(new SetCardInfo("Didn't Say Please", 42, Rarity.COMMON, mage.cards.d.DidntSayPlease.class)); cards.add(new SetCardInfo("Doom Foretold", 187, Rarity.RARE, mage.cards.d.DoomForetold.class)); cards.add(new SetCardInfo("Drown in the Loch", 188, Rarity.UNCOMMON, mage.cards.d.DrownInTheLoch.class)); From 13ba8b09002ade93dece9dea705c017bd9161994 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 21 Sep 2019 21:29:08 -0400 Subject: [PATCH 267/373] used reset method on triggered abilities --- .../src/mage/cards/d/DeathlessKnight.java | 21 ++++++++----------- .../DrawSecondCardTriggeredAbility.java | 21 ++++++++----------- 2 files changed, 18 insertions(+), 24 deletions(-) diff --git a/Mage.Sets/src/mage/cards/d/DeathlessKnight.java b/Mage.Sets/src/mage/cards/d/DeathlessKnight.java index 8b536dbf10..88500d97e2 100644 --- a/Mage.Sets/src/mage/cards/d/DeathlessKnight.java +++ b/Mage.Sets/src/mage/cards/d/DeathlessKnight.java @@ -59,28 +59,25 @@ class DeathlessKnightTriggeredAbility extends TriggeredAbilityImpl { @Override public boolean checkEventType(GameEvent event, Game game) { - return event.getType() == GameEvent.EventType.GAINED_LIFE - || event.getType() == GameEvent.EventType.END_PHASE_POST; + return event.getType() == GameEvent.EventType.GAINED_LIFE; } @Override public boolean checkTrigger(GameEvent event, Game game) { - if (event.getType() == GameEvent.EventType.END_PHASE_POST) { - triggeredOnce = false; - return false; - } - if (event.getType() != GameEvent.EventType.GAINED_LIFE - || !event.getPlayerId().equals(controllerId) - || game.getState().getZone(this.getSourceId()) == Zone.GRAVEYARD) { - return false; - } - if (triggeredOnce) { + if (!event.getPlayerId().equals(controllerId) + || game.getState().getZone(this.getSourceId()) == Zone.GRAVEYARD + || triggeredOnce) { return false; } triggeredOnce = true; return true; } + @Override + public void reset(Game game) { + triggeredOnce = false; + } + @Override public String getRule() { return "When you gain life for the first time each turn, return {this} from your graveyard to your hand."; diff --git a/Mage/src/main/java/mage/abilities/common/DrawSecondCardTriggeredAbility.java b/Mage/src/main/java/mage/abilities/common/DrawSecondCardTriggeredAbility.java index becd3c41d1..9cec4aaf98 100644 --- a/Mage/src/main/java/mage/abilities/common/DrawSecondCardTriggeredAbility.java +++ b/Mage/src/main/java/mage/abilities/common/DrawSecondCardTriggeredAbility.java @@ -26,22 +26,14 @@ public class DrawSecondCardTriggeredAbility extends TriggeredAbilityImpl { @Override public boolean checkEventType(GameEvent event, Game game) { - return event.getType() == GameEvent.EventType.DREW_CARD - || event.getType() == GameEvent.EventType.END_PHASE_POST; + return event.getType() == GameEvent.EventType.DREW_CARD; } @Override public boolean checkTrigger(GameEvent event, Game game) { - if (event.getType() == GameEvent.EventType.END_PHASE_POST) { - triggeredOnce = false; - return false; - } - if (event.getType() != GameEvent.EventType.DREW_CARD - || !event.getPlayerId().equals(controllerId) - || game.getPermanent(sourceId) == null) { - return false; - } - if (triggeredOnce) { + if (!event.getPlayerId().equals(controllerId) + || game.getPermanent(sourceId) == null + || triggeredOnce) { return false; } CardsAmountDrawnThisTurnWatcher watcher = game.getState().getWatcher(CardsAmountDrawnThisTurnWatcher.class); @@ -55,6 +47,11 @@ public class DrawSecondCardTriggeredAbility extends TriggeredAbilityImpl { return false; } + @Override + public void reset(Game game) { + triggeredOnce = false; + } + @Override public String getRule() { return "Whenever you draw your second card each turn, " + super.getRule(); From 24a7f13c8161bec644eabda86f0edd4f07b7bb86 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 21 Sep 2019 21:36:36 -0400 Subject: [PATCH 268/373] fixed Pattern Matcher counting itself when it searches (fixes #5994) --- Mage.Sets/src/mage/cards/p/PatternMatcher.java | 14 ++++++++------ 1 file changed, 8 insertions(+), 6 deletions(-) diff --git a/Mage.Sets/src/mage/cards/p/PatternMatcher.java b/Mage.Sets/src/mage/cards/p/PatternMatcher.java index 61844ffa6d..c53382c25e 100644 --- a/Mage.Sets/src/mage/cards/p/PatternMatcher.java +++ b/Mage.Sets/src/mage/cards/p/PatternMatcher.java @@ -19,9 +19,9 @@ import mage.game.permanent.Permanent; import mage.players.Player; import mage.target.common.TargetCardInLibrary; -import java.util.ArrayList; import java.util.List; import java.util.UUID; +import java.util.stream.Collectors; /** * @author TheElk801 @@ -72,14 +72,16 @@ class RegularExpression extends OneShotEffect { if (player == null) { return false; } - List predicates = new ArrayList(); - game.getBattlefield() - .getAllActivePermanents( - StaticFilters.FILTER_CONTROLLED_ANOTHER_CREATURE, source.getControllerId(), game + List predicates = game + .getBattlefield() + .getActivePermanents( + StaticFilters.FILTER_CONTROLLED_ANOTHER_CREATURE, + source.getControllerId(), source.getSourceId(), game ).stream() .map(Permanent::getName) .filter(s -> !"".equals(s)) - .forEach(s -> predicates.add(new NamePredicate(s))); + .map(NamePredicate::new) + .collect(Collectors.toList()); FilterCard filter = new FilterCard("a creature card with the same name as another creature you control"); filter.add(Predicates.or(predicates)); From 6911a2540bd399ce244c2fea824ff54e23224288 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sun, 22 Sep 2019 13:09:50 -0400 Subject: [PATCH 269/373] fixed Searing Barrage dealing too much to players --- Mage.Sets/src/mage/cards/s/SearingBarrage.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Mage.Sets/src/mage/cards/s/SearingBarrage.java b/Mage.Sets/src/mage/cards/s/SearingBarrage.java index f6912d1c9d..3032de92a3 100644 --- a/Mage.Sets/src/mage/cards/s/SearingBarrage.java +++ b/Mage.Sets/src/mage/cards/s/SearingBarrage.java @@ -26,7 +26,7 @@ public final class SearingBarrage extends CardImpl { // Adamant — If at least three red mana was spent to cast this spell, Searing Barrage deals 3 damage to that creature's controller. this.getSpellAbility().addEffect(new ConditionalOneShotEffect( - new DamageTargetControllerEffect(5), AdamantCondition.RED, + new DamageTargetControllerEffect(3), AdamantCondition.RED, "
Adamant — If at least three red mana was spent to cast this spell, " + "{this} deals 3 damage to that creature's controller." )); From 674e24f020e069adae69722e16ad10be96f529f4 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sun, 22 Sep 2019 13:11:10 -0400 Subject: [PATCH 270/373] fixed Cauldron's Gift not giving a counter to the creature --- Mage.Sets/src/mage/cards/c/CauldronsGift.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Mage.Sets/src/mage/cards/c/CauldronsGift.java b/Mage.Sets/src/mage/cards/c/CauldronsGift.java index 9ed9e0bd8b..923e9568a8 100644 --- a/Mage.Sets/src/mage/cards/c/CauldronsGift.java +++ b/Mage.Sets/src/mage/cards/c/CauldronsGift.java @@ -80,7 +80,7 @@ class CauldronsGiftEffect extends OneShotEffect { return false; } Card card = game.getCard(target.getFirstTarget()); - if (card == null || player.moveCards(card, Zone.BATTLEFIELD, source, game)) { + if (card == null || !player.moveCards(card, Zone.BATTLEFIELD, source, game)) { return false; } Permanent permanent = game.getPermanent(card.getId()); From 71aab17858f46412ac142fc2b7bf3e85f7c4bc3e Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sun, 22 Sep 2019 16:00:24 -0400 Subject: [PATCH 271/373] fixed Gadwick, the Wizened not drawing cards --- .../src/mage/cards/g/GadwickTheWizened.java | 90 +++++++++++++++++-- 1 file changed, 83 insertions(+), 7 deletions(-) diff --git a/Mage.Sets/src/mage/cards/g/GadwickTheWizened.java b/Mage.Sets/src/mage/cards/g/GadwickTheWizened.java index c20b0a635a..cfdece046c 100644 --- a/Mage.Sets/src/mage/cards/g/GadwickTheWizened.java +++ b/Mage.Sets/src/mage/cards/g/GadwickTheWizened.java @@ -1,26 +1,31 @@ package mage.cards.g; import mage.MageInt; +import mage.MageObjectReference; import mage.ObjectColor; import mage.abilities.Ability; import mage.abilities.common.EntersBattlefieldTriggeredAbility; import mage.abilities.common.SpellCastControllerTriggeredAbility; -import mage.abilities.dynamicvalue.common.ManacostVariableValue; +import mage.abilities.dynamicvalue.DynamicValue; +import mage.abilities.effects.Effect; import mage.abilities.effects.common.DrawCardSourceControllerEffect; import mage.abilities.effects.common.TapTargetEffect; import mage.cards.CardImpl; import mage.cards.CardSetInfo; -import mage.constants.CardType; -import mage.constants.SubType; -import mage.constants.SuperType; -import mage.constants.TargetController; +import mage.constants.*; import mage.filter.FilterPermanent; import mage.filter.FilterSpell; import mage.filter.common.FilterNonlandPermanent; import mage.filter.predicate.mageobject.ColorPredicate; import mage.filter.predicate.permanent.ControllerPredicate; +import mage.game.Game; +import mage.game.events.GameEvent; +import mage.game.stack.Spell; import mage.target.TargetPermanent; +import mage.watchers.Watcher; +import java.util.HashMap; +import java.util.Map; import java.util.UUID; /** @@ -49,8 +54,8 @@ public final class GadwickTheWizened extends CardImpl { // When Gadwick, the Wizened enters the battlefield, draw X cards. this.addAbility(new EntersBattlefieldTriggeredAbility( - new DrawCardSourceControllerEffect(ManacostVariableValue.instance) - )); + new DrawCardSourceControllerEffect(GadwickTheWizenedValue.instance) + ), new GadwickTheWizenedWatcher()); // Whenever you cast a blue spell, tap target nonland permanent an opponent controls. Ability ability = new SpellCastControllerTriggeredAbility(new TapTargetEffect(), filter, false); @@ -67,3 +72,74 @@ public final class GadwickTheWizened extends CardImpl { return new GadwickTheWizened(this); } } + +enum GadwickTheWizenedValue implements DynamicValue { + instance; + + @Override + public int calculate(Game game, Ability sourceAbility, Effect effect) { + GadwickTheWizenedWatcher watcher = game.getState().getWatcher(GadwickTheWizenedWatcher.class); + if (watcher == null) { + return 0; + } + return watcher.getX(new MageObjectReference(sourceAbility.getSourceId(), game)); + } + + @Override + public DynamicValue copy() { + return instance; + } + + @Override + public String toString() { + return "X"; + } + + @Override + public String getMessage() { + return ""; + } +} + +class GadwickTheWizenedWatcher extends Watcher { + + private final Map xMap = new HashMap(); + + GadwickTheWizenedWatcher() { + super(WatcherScope.GAME); + } + + private GadwickTheWizenedWatcher(final GadwickTheWizenedWatcher watcher) { + super(watcher); + this.xMap.putAll(watcher.xMap); + } + + @Override + public void watch(GameEvent event, Game game) { + if (event.getType() != GameEvent.EventType.SPELL_CAST) { + return; + } + Spell spell = game.getSpellOrLKIStack(event.getTargetId()); + if (spell == null) { + return; + } + xMap.put(new MageObjectReference( + spell.getSourceId(), spell.getZoneChangeCounter(game) + 1, game + ), spell.getSpellAbility().getManaCostsToPay().getX()); + } + + @Override + public GadwickTheWizenedWatcher copy() { + return new GadwickTheWizenedWatcher(this); + } + + @Override + public void reset() { + super.reset(); + xMap.clear(); + } + + public int getX(MageObjectReference mageObjectReference) { + return xMap.getOrDefault(mageObjectReference, 0); + } +} From d888d81209fbf9df70e0e3de7c6541d7618bdade Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sun, 22 Sep 2019 19:11:55 -0400 Subject: [PATCH 272/373] fixed Joust causing your creature to fight itself --- Mage.Sets/src/mage/cards/j/Joust.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Mage.Sets/src/mage/cards/j/Joust.java b/Mage.Sets/src/mage/cards/j/Joust.java index 813bb56ac0..c6ccef240f 100644 --- a/Mage.Sets/src/mage/cards/j/Joust.java +++ b/Mage.Sets/src/mage/cards/j/Joust.java @@ -70,7 +70,7 @@ class JoustEffect extends OneShotEffect { @Override public boolean apply(Game game, Ability source) { Permanent creature1 = game.getPermanent(source.getTargets().get(0).getFirstTarget()); - Permanent creature2 = game.getPermanent(source.getTargets().get(0).getFirstTarget()); + Permanent creature2 = game.getPermanent(source.getTargets().get(1).getFirstTarget()); if (creature1 == null) { return false; } From 316f823ebf87c60d48d8eac446de723157054b4e Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sun, 22 Sep 2019 20:54:29 -0400 Subject: [PATCH 273/373] cleaned up the TargetAmount classes in preparation for updating them --- .../target/common/TargetAnyTargetAmount.java | 169 +--------- .../TargetCreatureOrPlaneswalkerAmount.java | 318 ++++++++---------- .../common/TargetCreatureOrPlayerAmount.java | 169 +--------- .../common/TargetPermanentOrPlayerAmount.java | 190 +++++++++++ 4 files changed, 359 insertions(+), 487 deletions(-) create mode 100644 Mage/src/main/java/mage/target/common/TargetPermanentOrPlayerAmount.java diff --git a/Mage/src/main/java/mage/target/common/TargetAnyTargetAmount.java b/Mage/src/main/java/mage/target/common/TargetAnyTargetAmount.java index 37c8d4f8fb..cb3fa0c8d4 100644 --- a/Mage/src/main/java/mage/target/common/TargetAnyTargetAmount.java +++ b/Mage/src/main/java/mage/target/common/TargetAnyTargetAmount.java @@ -1,28 +1,24 @@ package mage.target.common; -import java.util.HashSet; -import java.util.Set; -import java.util.UUID; -import mage.MageObject; -import mage.abilities.Ability; import mage.abilities.dynamicvalue.DynamicValue; import mage.abilities.dynamicvalue.common.StaticValue; +import mage.constants.CardType; import mage.constants.Zone; -import mage.filter.Filter; -import mage.filter.StaticFilters; import mage.filter.common.FilterCreaturePlayerOrPlaneswalker; -import mage.game.Game; -import mage.game.permanent.Permanent; -import mage.players.Player; -import mage.target.TargetAmount; +import mage.filter.common.FilterPermanentOrPlayer; +import mage.filter.predicate.mageobject.CardTypePredicate; /** - * * @author BetaSteward_at_googlemail.com */ -public class TargetAnyTargetAmount extends TargetAmount { +public class TargetAnyTargetAmount extends TargetPermanentOrPlayerAmount { - protected final FilterCreaturePlayerOrPlaneswalker filter; + private static final FilterPermanentOrPlayer defaultFilter + = new FilterCreaturePlayerOrPlaneswalker("targets"); + + static { + defaultFilter.getPermanentFilter().add(new CardTypePredicate(CardType.CREATURE)); + } public TargetAnyTargetAmount(int amount) { // 107.1c If a rule or ability instructs a player to choose “any number,” that player may choose @@ -36,158 +32,17 @@ public class TargetAnyTargetAmount extends TargetAmount { public TargetAnyTargetAmount(DynamicValue amount) { super(amount); this.zone = Zone.ALL; - this.filter = new FilterCreaturePlayerOrPlaneswalker("targets"); + this.filter = defaultFilter; this.targetName = filter.getMessage(); } - public TargetAnyTargetAmount(final TargetAnyTargetAmount target) { + private TargetAnyTargetAmount(final TargetAnyTargetAmount target) { super(target); this.filter = target.filter.copy(); } - @Override - public Filter getFilter() { - return this.filter; - } - - @Override - public boolean canTarget(UUID objectId, Game game) { - Permanent permanent = game.getPermanent(objectId); - if (permanent != null) { - return filter.match(permanent, game); - } - Player player = game.getPlayer(objectId); - return player != null && filter.match(player, game); - } - - @Override - public boolean canTarget(UUID objectId, Ability source, Game game) { - Permanent permanent = game.getPermanent(objectId); - Player player = game.getPlayer(objectId); - - if (source != null) { - MageObject targetSource = source.getSourceObject(game); - if (permanent != null) { - return permanent.canBeTargetedBy(targetSource, source.getControllerId(), game) && filter.match(permanent, source.getSourceId(), source.getControllerId(), game); - } - if (player != null) { - return player.canBeTargetedBy(targetSource, source.getControllerId(), game) && filter.match(player, game); - } - } - - if (permanent != null) { - return filter.match(permanent, game); - } - return player != null && filter.match(player, game); - } - - @Override - public boolean canTarget(UUID playerId, UUID objectId, Ability source, Game game) { - return canTarget(objectId, source, game); - } - - @Override - public boolean canChoose(UUID sourceId, UUID sourceControllerId, Game game) { - int count = 0; - MageObject targetSource = game.getObject(sourceId); - for (UUID playerId : game.getState().getPlayersInRange(sourceControllerId, game)) { - Player player = game.getPlayer(playerId); - if (player != null && player.canBeTargetedBy(targetSource, sourceControllerId, game) && filter.match(player, game)) { - count++; - if (count >= this.minNumberOfTargets) { - return true; - } - } - } - for (Permanent permanent : game.getBattlefield().getActivePermanents(StaticFilters.FILTER_PERMANENT, sourceControllerId, game)) { - if (permanent.canBeTargetedBy(targetSource, sourceControllerId, game) && filter.match(permanent, sourceId, sourceControllerId, game)) { - count++; - if (count >= this.minNumberOfTargets) { - return true; - } - } - } - return false; - } - - @Override - public boolean canChoose(UUID sourceControllerId, Game game) { - int count = 0; - for (UUID playerId : game.getState().getPlayersInRange(sourceControllerId, game)) { - Player player = game.getPlayer(playerId); - if (player != null && filter.match(player, game)) { - count++; - if (count >= this.minNumberOfTargets) { - return true; - } - } - } - for (Permanent permanent : game.getBattlefield().getActivePermanents(StaticFilters.FILTER_PERMANENT, sourceControllerId, game)) { - if (filter.match(permanent, null, sourceControllerId, game)) { - count++; - if (count >= this.minNumberOfTargets) { - return true; - } - } - } - return false; - } - - @Override - public Set possibleTargets(UUID sourceId, UUID sourceControllerId, Game game) { - Set possibleTargets = new HashSet<>(); - MageObject targetSource = game.getObject(sourceId); - for (UUID playerId : game.getState().getPlayersInRange(sourceControllerId, game)) { - Player player = game.getPlayer(playerId); - if (player != null && player.canBeTargetedBy(targetSource, sourceControllerId, game) && filter.match(player, game)) { - possibleTargets.add(playerId); - } - } - for (Permanent permanent : game.getBattlefield().getActivePermanents(StaticFilters.FILTER_PERMANENT, sourceControllerId, game)) { - if (permanent.canBeTargetedBy(targetSource, sourceControllerId, game) && filter.match(permanent, sourceId, sourceControllerId, game)) { - possibleTargets.add(permanent.getId()); - } - } - return possibleTargets; - } - - @Override - public Set possibleTargets(UUID sourceControllerId, Game game) { - Set possibleTargets = new HashSet<>(); - for (UUID playerId : game.getState().getPlayersInRange(sourceControllerId, game)) { - Player player = game.getPlayer(playerId); - if (player != null && filter.match(player, game)) { - possibleTargets.add(playerId); - } - } - for (Permanent permanent : game.getBattlefield().getActivePermanents(StaticFilters.FILTER_PERMANENT, sourceControllerId, game)) { - if (filter.match(permanent, null, sourceControllerId, game)) { - possibleTargets.add(permanent.getId()); - } - } - return possibleTargets; - } - - @Override - public String getTargetedName(Game game) { - StringBuilder sb = new StringBuilder(); - for (UUID targetId : getTargets()) { - Permanent permanent = game.getPermanent(targetId); - if (permanent != null) { - sb.append(permanent.getLogName()).append('(').append(getTargetAmount(targetId)).append(") "); - } else { - Player player = game.getPlayer(targetId); - if (player != null) { - sb.append(player.getLogName()).append('(').append(getTargetAmount(targetId)).append(") "); - } - } - } - return sb.toString(); - } - @Override public TargetAnyTargetAmount copy() { return new TargetAnyTargetAmount(this); } - } diff --git a/Mage/src/main/java/mage/target/common/TargetCreatureOrPlaneswalkerAmount.java b/Mage/src/main/java/mage/target/common/TargetCreatureOrPlaneswalkerAmount.java index b373715695..d005822bc0 100644 --- a/Mage/src/main/java/mage/target/common/TargetCreatureOrPlaneswalkerAmount.java +++ b/Mage/src/main/java/mage/target/common/TargetCreatureOrPlaneswalkerAmount.java @@ -1,179 +1,151 @@ - /* - * Copyright 2010 BetaSteward_at_googlemail.com. All rights reserved. - * - * Redistribution and use in source and binary forms, with or without modification, are - * permitted provided that the following conditions are met: - * - * 1. Redistributions of source code must retain the above copyright notice, this list of - * conditions and the following disclaimer. - * - * 2. Redistributions in binary form must reproduce the above copyright notice, this list - * of conditions and the following disclaimer in the documentation and/or other materials - * provided with the distribution. - * - * THIS SOFTWARE IS PROVIDED BY BetaSteward_at_googlemail.com ``AS IS'' AND ANY EXPRESS OR IMPLIED - * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND - * FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL BetaSteward_at_googlemail.com OR - * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR - * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR - * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON - * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING - * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF - * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. - * - * The views and conclusions contained in the software and documentation are those of the - * authors and should not be interpreted as representing official policies, either expressed - * or implied, of BetaSteward_at_googlemail.com. - */ - package mage.target.common; +package mage.target.common; - import java.util.HashSet; - import java.util.Set; - import java.util.UUID; - import mage.constants.Zone; - import mage.MageObject; - import mage.abilities.Ability; - import mage.abilities.dynamicvalue.DynamicValue; - import mage.abilities.dynamicvalue.common.StaticValue; - import mage.filter.Filter; - import mage.filter.common.FilterCreatureOrPlaneswalkerPermanent; - import mage.game.Game; - import mage.game.permanent.Permanent; - import mage.target.TargetAmount; +import mage.MageObject; +import mage.abilities.Ability; +import mage.abilities.dynamicvalue.DynamicValue; +import mage.abilities.dynamicvalue.common.StaticValue; +import mage.constants.Zone; +import mage.filter.Filter; +import mage.filter.common.FilterCreatureOrPlaneswalkerPermanent; +import mage.game.Game; +import mage.game.permanent.Permanent; +import mage.target.TargetAmount; - /** - * - * @author BetaSteward_at_googlemail.com - */ - public class TargetCreatureOrPlaneswalkerAmount extends TargetAmount { +import java.util.Objects; +import java.util.Set; +import java.util.UUID; +import java.util.stream.Collectors; - protected final FilterCreatureOrPlaneswalkerPermanent filter; +/** + * @author BetaSteward_at_googlemail.com + */ +public class TargetCreatureOrPlaneswalkerAmount extends TargetAmount { - public TargetCreatureOrPlaneswalkerAmount(int amount) { - // 107.1c If a rule or ability instructs a player to choose “any number,” that player may choose - // any positive number or zero, unless something (such as damage or counters) is being divided - // or distributed among “any number” of players and/or objects. In that case, a nonzero number - // of players and/or objects must be chosen if possible. - this(amount, new FilterCreatureOrPlaneswalkerPermanent()); - } - - public TargetCreatureOrPlaneswalkerAmount(DynamicValue amount) { - this(amount, new FilterCreatureOrPlaneswalkerPermanent()); - } - - public TargetCreatureOrPlaneswalkerAmount(int amount, FilterCreatureOrPlaneswalkerPermanent filter) { - this(new StaticValue(amount), filter); - } - - public TargetCreatureOrPlaneswalkerAmount(DynamicValue amount, FilterCreatureOrPlaneswalkerPermanent filter) { - super(amount); - this.zone = Zone.ALL; - this.filter = filter; - this.targetName = filter.getMessage(); - } - - public TargetCreatureOrPlaneswalkerAmount(final TargetCreatureOrPlaneswalkerAmount target) { - super(target); - this.filter = target.filter.copy(); - } - - @Override - public Filter getFilter() { - return this.filter; - } - - @Override - public boolean canTarget(UUID objectId, Game game) { - Permanent permanent = game.getPermanent(objectId); - return permanent != null && filter.match(permanent, game); - } - - @Override - public boolean canTarget(UUID objectId, Ability source, Game game) { - Permanent permanent = game.getPermanent(objectId); - if (permanent != null) { - if (source != null) { - MageObject targetSource = source.getSourceObject(game); - return permanent.canBeTargetedBy(targetSource, source.getControllerId(), game) && filter.match(permanent, source.getSourceId(), source.getControllerId(), game); - } else { - return filter.match(permanent, game); - } - } - return false; - } - - @Override - public boolean canTarget(UUID playerId, UUID objectId, Ability source, Game game) { - return canTarget(objectId, source, game); - } - - @Override - public boolean canChoose(UUID sourceId, UUID sourceControllerId, Game game) { - int count = 0; - MageObject targetSource = game.getObject(sourceId); - for (Permanent permanent : game.getBattlefield().getActivePermanents(new FilterCreatureOrPlaneswalkerPermanent(), sourceControllerId, game)) { - if (permanent.canBeTargetedBy(targetSource, sourceControllerId, game) && filter.match(permanent, sourceId, sourceControllerId, game)) { - count++; - if (count >= this.minNumberOfTargets) { - return true; - } - } - } - return false; - } - - @Override - public boolean canChoose(UUID sourceControllerId, Game game) { - int count = 0; - for (Permanent permanent : game.getBattlefield().getActivePermanents(new FilterCreatureOrPlaneswalkerPermanent(), sourceControllerId, game)) { - if (filter.match(permanent, null, sourceControllerId, game)) { - count++; - if (count >= this.minNumberOfTargets) { - return true; - } - } - } - return false; - } - - @Override - public Set possibleTargets(UUID sourceId, UUID sourceControllerId, Game game) { - Set possibleTargets = new HashSet<>(); - MageObject targetSource = game.getObject(sourceId); - for (Permanent permanent : game.getBattlefield().getActivePermanents(new FilterCreatureOrPlaneswalkerPermanent(), sourceControllerId, game)) { - if (permanent.canBeTargetedBy(targetSource, sourceControllerId, game) && filter.match(permanent, sourceId, sourceControllerId, game)) { - possibleTargets.add(permanent.getId()); - } - } - return possibleTargets; - } - - @Override - public Set possibleTargets(UUID sourceControllerId, Game game) { - Set possibleTargets = new HashSet<>(); - for (Permanent permanent : game.getBattlefield().getActivePermanents(new FilterCreatureOrPlaneswalkerPermanent(), sourceControllerId, game)) { - if (filter.match(permanent, null, sourceControllerId, game)) { - possibleTargets.add(permanent.getId()); - } - } - return possibleTargets; - } - - @Override - public String getTargetedName(Game game) { - StringBuilder sb = new StringBuilder(); - for (UUID targetId : getTargets()) { - Permanent permanent = game.getPermanent(targetId); - if (permanent != null) { - sb.append(permanent.getLogName()).append('(').append(getTargetAmount(targetId)).append(") "); - } - } - return sb.toString(); - } - - @Override - public TargetCreatureOrPlaneswalkerAmount copy() { - return new TargetCreatureOrPlaneswalkerAmount(this); - } + protected final FilterCreatureOrPlaneswalkerPermanent filter; + private static final FilterCreatureOrPlaneswalkerPermanent defaultFilter + = new FilterCreatureOrPlaneswalkerPermanent(); + public TargetCreatureOrPlaneswalkerAmount(int amount) { + // 107.1c If a rule or ability instructs a player to choose “any number,” that player may choose + // any positive number or zero, unless something (such as damage or counters) is being divided + // or distributed among “any number” of players and/or objects. In that case, a nonzero number + // of players and/or objects must be chosen if possible. + this(amount, defaultFilter); } + + public TargetCreatureOrPlaneswalkerAmount(DynamicValue amount) { + this(amount, defaultFilter); + } + + public TargetCreatureOrPlaneswalkerAmount(int amount, FilterCreatureOrPlaneswalkerPermanent filter) { + this(new StaticValue(amount), filter); + } + + public TargetCreatureOrPlaneswalkerAmount(DynamicValue amount, FilterCreatureOrPlaneswalkerPermanent filter) { + super(amount); + this.zone = Zone.ALL; + this.filter = filter; + this.targetName = filter.getMessage(); + } + + private TargetCreatureOrPlaneswalkerAmount(final TargetCreatureOrPlaneswalkerAmount target) { + super(target); + this.filter = target.filter.copy(); + } + + @Override + public Filter getFilter() { + return this.filter; + } + + @Override + public boolean canTarget(UUID objectId, Game game) { + Permanent permanent = game.getPermanent(objectId); + return permanent != null && filter.match(permanent, game); + } + + @Override + public boolean canTarget(UUID objectId, Ability source, Game game) { + Permanent permanent = game.getPermanent(objectId); + if (permanent != null) { + if (source != null) { + MageObject targetSource = source.getSourceObject(game); + return permanent.canBeTargetedBy(targetSource, source.getControllerId(), game) + && filter.match(permanent, source.getSourceId(), source.getControllerId(), game); + } else { + return filter.match(permanent, game); + } + } + return false; + } + + @Override + public boolean canTarget(UUID playerId, UUID objectId, Ability source, Game game) { + return canTarget(objectId, source, game); + } + + @Override + public boolean canChoose(UUID sourceId, UUID sourceControllerId, Game game) { + int count = 0; + for (Permanent permanent : game.getBattlefield().getActivePermanents(filter, sourceControllerId, sourceId, game)) { + count++; + if (count >= this.minNumberOfTargets) { + return true; + } + } + return false; + } + + @Override + public boolean canChoose(UUID sourceControllerId, Game game) { + int count = 0; + for (Permanent permanent : game.getBattlefield().getActivePermanents(filter, sourceControllerId, game)) { + count++; + if (count >= this.minNumberOfTargets) { + return true; + } + } + return false; + } + + @Override + public Set possibleTargets(UUID sourceId, UUID sourceControllerId, Game game) { + MageObject targetSource = game.getObject(sourceId); + return game + .getBattlefield() + .getActivePermanents(filter, sourceId, sourceControllerId, game) + .stream() + .filter(Objects::nonNull) + .filter(permanent -> permanent.canBeTargetedBy(targetSource, sourceControllerId, game)) + .map(Permanent::getId) + .collect(Collectors.toSet()); + } + + @Override + public Set possibleTargets(UUID sourceControllerId, Game game) { + return game + .getBattlefield() + .getActivePermanents(filter, sourceControllerId, game) + .stream() + .map(Permanent::getId) + .collect(Collectors.toSet()); + } + + @Override + public String getTargetedName(Game game) { + StringBuilder sb = new StringBuilder(); + for (UUID targetId : getTargets()) { + Permanent permanent = game.getPermanent(targetId); + if (permanent != null) { + sb.append(permanent.getLogName()).append('(').append(getTargetAmount(targetId)).append(") "); + } + } + return sb.toString(); + } + + @Override + public TargetCreatureOrPlaneswalkerAmount copy() { + return new TargetCreatureOrPlaneswalkerAmount(this); + } + +} diff --git a/Mage/src/main/java/mage/target/common/TargetCreatureOrPlayerAmount.java b/Mage/src/main/java/mage/target/common/TargetCreatureOrPlayerAmount.java index 06e7ebba6e..00fa98bf45 100644 --- a/Mage/src/main/java/mage/target/common/TargetCreatureOrPlayerAmount.java +++ b/Mage/src/main/java/mage/target/common/TargetCreatureOrPlayerAmount.java @@ -1,29 +1,23 @@ - package mage.target.common; -import java.util.HashSet; -import java.util.Set; -import java.util.UUID; -import mage.MageObject; -import mage.abilities.Ability; import mage.abilities.dynamicvalue.DynamicValue; import mage.abilities.dynamicvalue.common.StaticValue; +import mage.constants.CardType; import mage.constants.Zone; -import mage.filter.Filter; -import mage.filter.StaticFilters; -import mage.filter.common.FilterCreatureOrPlayer; -import mage.game.Game; -import mage.game.permanent.Permanent; -import mage.players.Player; -import mage.target.TargetAmount; +import mage.filter.common.FilterPermanentOrPlayer; +import mage.filter.predicate.mageobject.CardTypePredicate; /** - * * @author BetaSteward_at_googlemail.com */ -public class TargetCreatureOrPlayerAmount extends TargetAmount { +public class TargetCreatureOrPlayerAmount extends TargetPermanentOrPlayerAmount { - protected final FilterCreatureOrPlayer filter; + private static final FilterPermanentOrPlayer defaultFilter + = new FilterPermanentOrPlayer("creatures and/or players"); + + static { + defaultFilter.getPermanentFilter().add(new CardTypePredicate(CardType.CREATURE)); + } public TargetCreatureOrPlayerAmount(int amount) { // 107.1c If a rule or ability instructs a player to choose “any number,” that player may choose @@ -37,156 +31,17 @@ public class TargetCreatureOrPlayerAmount extends TargetAmount { public TargetCreatureOrPlayerAmount(DynamicValue amount) { super(amount); this.zone = Zone.ALL; - this.filter = new FilterCreatureOrPlayer("creatures and/or players"); + this.filter = defaultFilter; this.targetName = filter.getMessage(); } - public TargetCreatureOrPlayerAmount(final TargetCreatureOrPlayerAmount target) { + private TargetCreatureOrPlayerAmount(final TargetCreatureOrPlayerAmount target) { super(target); this.filter = target.filter.copy(); } - @Override - public Filter getFilter() { - return this.filter; - } - - @Override - public boolean canTarget(UUID objectId, Game game) { - Permanent permanent = game.getPermanent(objectId); - if (permanent != null) { - return filter.match(permanent, game); - } - Player player = game.getPlayer(objectId); - return player != null && filter.match(player, game); - } - - @Override - public boolean canTarget(UUID objectId, Ability source, Game game) { - Permanent permanent = game.getPermanent(objectId); - Player player = game.getPlayer(objectId); - - if (source != null) { - MageObject targetSource = source.getSourceObject(game); - if (permanent != null) { - return permanent.canBeTargetedBy(targetSource, source.getControllerId(), game) && filter.match(permanent, source.getSourceId(), source.getControllerId(), game); - } - if (player != null) { - return player.canBeTargetedBy(targetSource, source.getControllerId(), game) && filter.match(player, game); - } - } - - if (permanent != null) { - return filter.match(permanent, game); - } - return player != null && filter.match(player, game); - } - - @Override - public boolean canTarget(UUID playerId, UUID objectId, Ability source, Game game) { - return canTarget(objectId, source, game); - } - - @Override - public boolean canChoose(UUID sourceId, UUID sourceControllerId, Game game) { - int count = 0; - MageObject targetSource = game.getObject(sourceId); - for (UUID playerId : game.getState().getPlayersInRange(sourceControllerId, game)) { - Player player = game.getPlayer(playerId); - if (player != null && player.canBeTargetedBy(targetSource, sourceControllerId, game) && filter.match(player, game)) { - count++; - if (count >= this.minNumberOfTargets) { - return true; - } - } - } - for (Permanent permanent : game.getBattlefield().getActivePermanents(StaticFilters.FILTER_PERMANENT_CREATURE, sourceControllerId, game)) { - if (permanent.canBeTargetedBy(targetSource, sourceControllerId, game) && filter.match(permanent, sourceId, sourceControllerId, game)) { - count++; - if (count >= this.minNumberOfTargets) { - return true; - } - } - } - return false; - } - - @Override - public boolean canChoose(UUID sourceControllerId, Game game) { - int count = 0; - for (UUID playerId : game.getState().getPlayersInRange(sourceControllerId, game)) { - Player player = game.getPlayer(playerId); - if (player != null && filter.match(player, game)) { - count++; - if (count >= this.minNumberOfTargets) { - return true; - } - } - } - for (Permanent permanent : game.getBattlefield().getActivePermanents(StaticFilters.FILTER_PERMANENT_CREATURE, sourceControllerId, game)) { - if (filter.match(permanent, null, sourceControllerId, game)) { - count++; - if (count >= this.minNumberOfTargets) { - return true; - } - } - } - return false; - } - - @Override - public Set possibleTargets(UUID sourceId, UUID sourceControllerId, Game game) { - Set possibleTargets = new HashSet<>(); - MageObject targetSource = game.getObject(sourceId); - for (UUID playerId : game.getState().getPlayersInRange(sourceControllerId, game)) { - Player player = game.getPlayer(playerId); - if (player != null && player.canBeTargetedBy(targetSource, sourceControllerId, game) && filter.match(player, game)) { - possibleTargets.add(playerId); - } - } - for (Permanent permanent : game.getBattlefield().getActivePermanents(StaticFilters.FILTER_PERMANENT_CREATURE, sourceControllerId, game)) { - if (permanent.canBeTargetedBy(targetSource, sourceControllerId, game) && filter.match(permanent, sourceId, sourceControllerId, game)) { - possibleTargets.add(permanent.getId()); - } - } - return possibleTargets; - } - - @Override - public Set possibleTargets(UUID sourceControllerId, Game game) { - Set possibleTargets = new HashSet<>(); - for (UUID playerId : game.getState().getPlayersInRange(sourceControllerId, game)) { - Player player = game.getPlayer(playerId); - if (player != null && filter.match(player, game)) { - possibleTargets.add(playerId); - } - } - for (Permanent permanent : game.getBattlefield().getActivePermanents(StaticFilters.FILTER_PERMANENT_CREATURE, sourceControllerId, game)) { - if (filter.match(permanent, null, sourceControllerId, game)) { - possibleTargets.add(permanent.getId()); - } - } - return possibleTargets; - } - - @Override - public String getTargetedName(Game game) { - StringBuilder sb = new StringBuilder(); - for (UUID targetId : getTargets()) { - Permanent permanent = game.getPermanent(targetId); - if (permanent != null) { - sb.append(permanent.getLogName()).append('(').append(getTargetAmount(targetId)).append(") "); - } else { - Player player = game.getPlayer(targetId); - sb.append(player.getLogName()).append('(').append(getTargetAmount(targetId)).append(") "); - } - } - return sb.toString(); - } - @Override public TargetCreatureOrPlayerAmount copy() { return new TargetCreatureOrPlayerAmount(this); } - } diff --git a/Mage/src/main/java/mage/target/common/TargetPermanentOrPlayerAmount.java b/Mage/src/main/java/mage/target/common/TargetPermanentOrPlayerAmount.java new file mode 100644 index 0000000000..623233dd23 --- /dev/null +++ b/Mage/src/main/java/mage/target/common/TargetPermanentOrPlayerAmount.java @@ -0,0 +1,190 @@ +package mage.target.common; + +import mage.MageObject; +import mage.abilities.Ability; +import mage.abilities.dynamicvalue.DynamicValue; +import mage.filter.Filter; +import mage.filter.StaticFilters; +import mage.filter.common.FilterPermanentOrPlayer; +import mage.game.Game; +import mage.game.permanent.Permanent; +import mage.players.Player; +import mage.target.TargetAmount; + +import java.util.HashSet; +import java.util.Objects; +import java.util.Set; +import java.util.UUID; + +/** + * @author TheElk801 + */ +public abstract class TargetPermanentOrPlayerAmount extends TargetAmount { + + protected FilterPermanentOrPlayer filter; + + TargetPermanentOrPlayerAmount(DynamicValue amount) { + super(amount); + } + + TargetPermanentOrPlayerAmount(final TargetPermanentOrPlayerAmount target) { + super(target); + this.filter = target.filter.copy(); + } + + @Override + public Filter getFilter() { + return this.filter; + } + + @Override + public boolean canTarget(UUID objectId, Game game) { + Permanent permanent = game.getPermanent(objectId); + if (permanent != null) { + return filter.match(permanent, game); + } + Player player = game.getPlayer(objectId); + return player != null && filter.match(player, game); + } + + @Override + public boolean canTarget(UUID objectId, Ability source, Game game) { + Permanent permanent = game.getPermanent(objectId); + Player player = game.getPlayer(objectId); + + if (source != null) { + MageObject targetSource = source.getSourceObject(game); + if (permanent != null) { + return permanent.canBeTargetedBy(targetSource, source.getControllerId(), game) + && filter.match(permanent, source.getSourceId(), source.getControllerId(), game); + } + if (player != null) { + return player.canBeTargetedBy(targetSource, source.getControllerId(), game) + && filter.match(player, game); + } + } + + if (permanent != null) { + return filter.match(permanent, game); + } + return player != null && filter.match(player, game); + } + + @Override + public boolean canTarget(UUID playerId, UUID objectId, Ability source, Game game) { + return canTarget(objectId, source, game); + } + + @Override + public boolean canChoose(UUID sourceId, UUID sourceControllerId, Game game) { + int count = 0; + MageObject targetSource = game.getObject(sourceId); + for (UUID playerId : game.getState().getPlayersInRange(sourceControllerId, game)) { + Player player = game.getPlayer(playerId); + if (player == null + || !player.canBeTargetedBy(targetSource, sourceControllerId, game) + || !filter.match(player, game)) { + continue; + } + count++; + if (count >= this.minNumberOfTargets) { + return true; + } + } + for (Permanent permanent : game.getBattlefield().getActivePermanents(filter.getPermanentFilter(), sourceControllerId, game)) { + if (!permanent.canBeTargetedBy(targetSource, sourceControllerId, game)) { + continue; + } + count++; + if (count >= this.minNumberOfTargets) { + return true; + } + } + return false; + } + + @Override + public boolean canChoose(UUID sourceControllerId, Game game) { + int count = 0; + for (UUID playerId : game.getState().getPlayersInRange(sourceControllerId, game)) { + Player player = game.getPlayer(playerId); + if (player == null || !filter.match(player, game)) { + continue; + } + count++; + if (count >= this.minNumberOfTargets) { + return true; + } + } + for (Permanent permanent : game.getBattlefield().getActivePermanents(filter.getPermanentFilter(), sourceControllerId, game)) { + count++; + if (count >= this.minNumberOfTargets) { + return true; + } + } + return false; + } + + @Override + public Set possibleTargets(UUID sourceId, UUID sourceControllerId, Game game) { + Set possibleTargets = new HashSet<>(); + MageObject targetSource = game.getObject(sourceId); + + game.getState() + .getPlayersInRange(sourceControllerId, game) + .stream() + .map(game::getPlayer) + .filter(Objects::nonNull) + .filter(player -> player.canBeTargetedBy(targetSource, sourceControllerId, game) + && filter.match(player, game) + ) + .map(Player::getId) + .forEach(possibleTargets::add); + + game.getBattlefield() + .getActivePermanents(filter.getPermanentFilter(), sourceControllerId, game) + .stream() + .filter(Objects::nonNull) + .filter(permanent -> permanent.canBeTargetedBy(targetSource, sourceControllerId, game)) + .map(Permanent::getId) + .forEach(possibleTargets::add); + + return possibleTargets; + } + + @Override + public Set possibleTargets(UUID sourceControllerId, Game game) { + Set possibleTargets = new HashSet<>(); + game.getState() + .getPlayersInRange(sourceControllerId, game) + .stream() + .map(game::getPlayer) + .filter(Objects::nonNull) + .filter(player -> filter.match(player, game)) + .map(Player::getId) + .forEach(possibleTargets::add); + + game.getBattlefield() + .getActivePermanents(filter.getPermanentFilter(), sourceControllerId, game) + .stream() + .map(Permanent::getId) + .forEach(possibleTargets::add); + + return possibleTargets; + } + + @Override + public String getTargetedName(Game game) { + StringBuilder sb = new StringBuilder(); + for (UUID targetId : getTargets()) { + Permanent permanent = game.getPermanent(targetId); + if (permanent != null) { + sb.append(permanent.getLogName()).append('(').append(getTargetAmount(targetId)).append(") "); + } else { + Player player = game.getPlayer(targetId); + sb.append(player.getLogName()).append('(').append(getTargetAmount(targetId)).append(") "); + } + } + return sb.toString(); + } +} From 520de8a6d58dad6601cc93e52d0cc8a66f7058ac Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sun, 22 Sep 2019 21:13:12 -0400 Subject: [PATCH 274/373] fixed Torbran, Thane of Red Fell not increasing damage to players --- Mage.Sets/src/mage/cards/t/TorbranThaneOfRedFell.java | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-) diff --git a/Mage.Sets/src/mage/cards/t/TorbranThaneOfRedFell.java b/Mage.Sets/src/mage/cards/t/TorbranThaneOfRedFell.java index e9d707ce0e..659c6588b9 100644 --- a/Mage.Sets/src/mage/cards/t/TorbranThaneOfRedFell.java +++ b/Mage.Sets/src/mage/cards/t/TorbranThaneOfRedFell.java @@ -78,7 +78,7 @@ class TorbranThaneOfRedFellEffect extends ReplacementEffectImpl { public boolean applies(GameEvent event, Ability source, Game game) { Player player = game.getPlayer(source.getControllerId()); if (player == null - || !player.hasOpponent(game.getControllerId(event.getTargetId()), game) + || !player.hasOpponent(getControllerOrSelf(event.getTargetId(), game), game) || !source.isControlledBy(game.getControllerId(event.getSourceId()))) { return false; } @@ -90,8 +90,12 @@ class TorbranThaneOfRedFellEffect extends ReplacementEffectImpl { sourceObject = sourcePermanent; } return sourceObject != null - && sourceObject.getColor(game).isRed() - && !sourceObject.getId().equals(source.getSourceId()); + && sourceObject.getColor(game).isRed(); + } + + private static UUID getControllerOrSelf(UUID id, Game game) { + UUID outId = game.getControllerId(id); + return outId == null ? id : outId; } @Override From fc6347b472c3b4c9d987007845579e8bdd9cfb8e Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sun, 22 Sep 2019 21:15:48 -0400 Subject: [PATCH 275/373] fixed Heraldic Banner pumping all creatures of the chosen color --- .../src/mage/cards/h/HeraldicBanner.java | 32 ++++++++++--------- 1 file changed, 17 insertions(+), 15 deletions(-) diff --git a/Mage.Sets/src/mage/cards/h/HeraldicBanner.java b/Mage.Sets/src/mage/cards/h/HeraldicBanner.java index 6e40a48304..4171169e3f 100644 --- a/Mage.Sets/src/mage/cards/h/HeraldicBanner.java +++ b/Mage.Sets/src/mage/cards/h/HeraldicBanner.java @@ -12,7 +12,7 @@ import mage.abilities.mana.SimpleManaAbility; import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.*; -import mage.filter.common.FilterCreaturePermanent; +import mage.filter.StaticFilters; import mage.game.Game; import mage.game.permanent.Permanent; @@ -31,13 +31,13 @@ public final class HeraldicBanner extends CardImpl { this.addAbility(new AsEntersBattlefieldAbility(new ChooseColorEffect(Outcome.Benefit))); // Creatures you control of the chosen color get +1/+0. - this.addAbility(new SimpleStaticAbility(Zone.BATTLEFIELD, new HeraldicBannerEffect())); + this.addAbility(new SimpleStaticAbility(new HeraldicBannerEffect())); // {T}: Add one mana of the chosen color. this.addAbility(new SimpleManaAbility(Zone.BATTLEFIELD, new AddManaChosenColorEffect(), new TapSourceCost())); } - public HeraldicBanner(final HeraldicBanner card) { + private HeraldicBanner(final HeraldicBanner card) { super(card); } @@ -49,14 +49,12 @@ public final class HeraldicBanner extends CardImpl { class HeraldicBannerEffect extends ContinuousEffectImpl { - private static final FilterCreaturePermanent filter = new FilterCreaturePermanent(); - - public HeraldicBannerEffect() { + HeraldicBannerEffect() { super(Duration.WhileOnBattlefield, Layer.PTChangingEffects_7, SubLayer.ModifyPT_7c, Outcome.BoostCreature); staticText = "Creatures you control of the chosen color get +1/+0"; } - public HeraldicBannerEffect(final HeraldicBannerEffect effect) { + private HeraldicBannerEffect(final HeraldicBannerEffect effect) { super(effect); } @@ -68,14 +66,18 @@ class HeraldicBannerEffect extends ContinuousEffectImpl { @Override public boolean apply(Game game, Ability source) { Permanent permanent = game.getPermanent(source.getSourceId()); - if (permanent != null) { - ObjectColor color = (ObjectColor) game.getState().getValue(permanent.getId() + "_color"); - if (color != null) { - for (Permanent perm : game.getBattlefield().getActivePermanents(filter, source.getControllerId(), game)) { - if (perm.getColor(game).contains(color)) { - perm.addPower(1); - } - } + if (permanent == null) { + return false; + } + ObjectColor color = (ObjectColor) game.getState().getValue(permanent.getId() + "_color"); + if (color == null) { + return false; + } + for (Permanent perm : game.getBattlefield().getActivePermanents( + StaticFilters.FILTER_CONTROLLED_CREATURE, source.getControllerId(), source.getSourceId(), game + )) { + if (perm.getColor(game).contains(color)) { + perm.addPower(1); } } return true; From 6bd622072c7e861e8303e549ba4ea5c3beacbf5a Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sun, 22 Sep 2019 21:26:02 -0400 Subject: [PATCH 276/373] fixed Kazuul, Tyrant of the Cliffs not triggering when a planeswalker is attacked --- .../mage/cards/k/KazuulTyrantOfTheCliffs.java | 48 ++++++++----------- 1 file changed, 20 insertions(+), 28 deletions(-) diff --git a/Mage.Sets/src/mage/cards/k/KazuulTyrantOfTheCliffs.java b/Mage.Sets/src/mage/cards/k/KazuulTyrantOfTheCliffs.java index 370f5d4eb7..c5061f7826 100644 --- a/Mage.Sets/src/mage/cards/k/KazuulTyrantOfTheCliffs.java +++ b/Mage.Sets/src/mage/cards/k/KazuulTyrantOfTheCliffs.java @@ -1,8 +1,5 @@ - package mage.cards.k; -import java.util.Objects; -import java.util.UUID; import mage.MageInt; import mage.abilities.Ability; import mage.abilities.TriggeredAbilityImpl; @@ -11,21 +8,17 @@ import mage.abilities.costs.mana.GenericManaCost; import mage.abilities.effects.OneShotEffect; 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.game.Game; import mage.game.events.GameEvent; import mage.game.events.GameEvent.EventType; -import mage.game.permanent.Permanent; import mage.game.permanent.token.OgreToken; import mage.players.Player; import mage.target.targetpointer.FixedTarget; +import java.util.UUID; + /** - * * @author jeffwadsworth */ public final class KazuulTyrantOfTheCliffs extends CardImpl { @@ -55,11 +48,11 @@ public final class KazuulTyrantOfTheCliffs extends CardImpl { class KazuulTyrantOfTheCliffsTriggeredAbility extends TriggeredAbilityImpl { - public KazuulTyrantOfTheCliffsTriggeredAbility() { + KazuulTyrantOfTheCliffsTriggeredAbility() { super(Zone.BATTLEFIELD, new KazuulTyrantOfTheCliffsEffect(new GenericManaCost(3))); } - public KazuulTyrantOfTheCliffsTriggeredAbility(final KazuulTyrantOfTheCliffsTriggeredAbility ability) { + private KazuulTyrantOfTheCliffsTriggeredAbility(final KazuulTyrantOfTheCliffsTriggeredAbility ability) { super(ability); } @@ -75,19 +68,17 @@ class KazuulTyrantOfTheCliffsTriggeredAbility extends TriggeredAbilityImpl { @Override public boolean checkTrigger(GameEvent event, Game game) { - Permanent attacker = game.getPermanent(event.getSourceId()); - Player defender = game.getPlayer(event.getTargetId()); - Player you = game.getPlayer(controllerId); - if (!Objects.equals(attacker.getControllerId(), you.getId()) && Objects.equals(defender, you)) { - this.getEffects().get(0).setTargetPointer(new FixedTarget(attacker.getControllerId())); - return true; + if (!getControllerId().equals(game.getCombat().getDefendingPlayerId(event.getSourceId(), game))) { + return false; } - return false; + this.getEffects().get(0).setTargetPointer(new FixedTarget(game.getControllerId(event.getSourceId()))); + return true; } @Override public String getRule() { - return "Whenever a creature an opponent controls attacks, if you're the defending player, create a 3/3 red Ogre creature token unless that creature's controller pays {3}"; + return "Whenever a creature an opponent controls attacks, if you're the defending player, " + + "create a 3/3 red Ogre creature token unless that creature's controller pays {3}"; } } @@ -96,12 +87,12 @@ class KazuulTyrantOfTheCliffsEffect extends OneShotEffect { protected Cost cost; private static OgreToken token = new OgreToken(); - public KazuulTyrantOfTheCliffsEffect(Cost cost) { + KazuulTyrantOfTheCliffsEffect(Cost cost) { super(Outcome.PutCreatureInPlay); this.cost = cost; } - public KazuulTyrantOfTheCliffsEffect(KazuulTyrantOfTheCliffsEffect effect) { + private KazuulTyrantOfTheCliffsEffect(KazuulTyrantOfTheCliffsEffect effect) { super(effect); this.cost = effect.cost.copy(); } @@ -109,13 +100,14 @@ class KazuulTyrantOfTheCliffsEffect extends OneShotEffect { @Override public boolean apply(Game game, Ability source) { Player payee = game.getPlayer(targetPointer.getFirst(game, source)); - if (payee != null) { - cost.clearPaid(); - if (!cost.pay(source, game, source.getSourceId(), payee.getId(), false, null)) { - return token.putOntoBattlefield(1, game, source.getSourceId(), source.getControllerId()); - } + if (payee == null) { + return false; } - return false; + cost.clearPaid(); + if (cost.pay(source, game, source.getSourceId(), payee.getId(), false, null)) { + return false; + } + return token.putOntoBattlefield(1, game, source.getSourceId(), source.getControllerId()); } @Override From 2daa9b60044326a8e935a36767a3e5be68c9bb3f Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 23 Sep 2019 10:00:23 -0400 Subject: [PATCH 277/373] fixed Fires of Invention allowing more than two spells cast --- Mage.Sets/src/mage/cards/f/FiresOfInvention.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Mage.Sets/src/mage/cards/f/FiresOfInvention.java b/Mage.Sets/src/mage/cards/f/FiresOfInvention.java index 2c23f65279..b87e4c6185 100644 --- a/Mage.Sets/src/mage/cards/f/FiresOfInvention.java +++ b/Mage.Sets/src/mage/cards/f/FiresOfInvention.java @@ -92,7 +92,7 @@ class FiresOfInventionCastEffect extends ContinuousRuleModifyingEffectImpl { if (watcher == null) { return false; } - return watcher.getAmountOfSpellsPlayerCastOnCurrentTurn(source.getControllerId()) > 2 + return watcher.getAmountOfSpellsPlayerCastOnCurrentTurn(source.getControllerId()) > 1 || !game.getActivePlayerId().equals(source.getControllerId()); } From bad26b182a19026a83cf76bb1b1cc6c6be409931 Mon Sep 17 00:00:00 2001 From: Oleg Agafonov Date: Tue, 24 Sep 2019 07:44:14 +0400 Subject: [PATCH 278/373] Added max targets limit support in TargetAmount --- .../target/common/TargetAnyTargetAmount.java | 12 +++++-- .../common/TargetPermanentOrPlayerAmount.java | 34 ++++++++++++++++++- 2 files changed, 43 insertions(+), 3 deletions(-) diff --git a/Mage/src/main/java/mage/target/common/TargetAnyTargetAmount.java b/Mage/src/main/java/mage/target/common/TargetAnyTargetAmount.java index cb3fa0c8d4..544c8a6de3 100644 --- a/Mage/src/main/java/mage/target/common/TargetAnyTargetAmount.java +++ b/Mage/src/main/java/mage/target/common/TargetAnyTargetAmount.java @@ -21,16 +21,24 @@ public class TargetAnyTargetAmount extends TargetPermanentOrPlayerAmount { } public TargetAnyTargetAmount(int amount) { + this(amount, 0); + } + + public TargetAnyTargetAmount(int amount, int maxNumberOfTargets) { // 107.1c If a rule or ability instructs a player to choose “any number,” that player may choose // any positive number or zero, unless something (such as damage or counters) is being divided // or distributed among “any number” of players and/or objects. In that case, a nonzero number // of players and/or objects must be chosen if possible. - this(new StaticValue(amount)); + this(new StaticValue(amount), maxNumberOfTargets); this.minNumberOfTargets = 1; } public TargetAnyTargetAmount(DynamicValue amount) { - super(amount); + this(amount, 0); + } + + public TargetAnyTargetAmount(DynamicValue amount, int maxNumberOfTargets) { + super(amount, maxNumberOfTargets); this.zone = Zone.ALL; this.filter = defaultFilter; this.targetName = filter.getMessage(); diff --git a/Mage/src/main/java/mage/target/common/TargetPermanentOrPlayerAmount.java b/Mage/src/main/java/mage/target/common/TargetPermanentOrPlayerAmount.java index 623233dd23..adc75fae2c 100644 --- a/Mage/src/main/java/mage/target/common/TargetPermanentOrPlayerAmount.java +++ b/Mage/src/main/java/mage/target/common/TargetPermanentOrPlayerAmount.java @@ -4,7 +4,6 @@ import mage.MageObject; import mage.abilities.Ability; import mage.abilities.dynamicvalue.DynamicValue; import mage.filter.Filter; -import mage.filter.StaticFilters; import mage.filter.common.FilterPermanentOrPlayer; import mage.game.Game; import mage.game.permanent.Permanent; @@ -24,7 +23,12 @@ public abstract class TargetPermanentOrPlayerAmount extends TargetAmount { protected FilterPermanentOrPlayer filter; TargetPermanentOrPlayerAmount(DynamicValue amount) { + this(amount, 0); + } + + TargetPermanentOrPlayerAmount(DynamicValue amount, int maxNumberOfTargets) { super(amount); + this.maxNumberOfTargets = maxNumberOfTargets; } TargetPermanentOrPlayerAmount(final TargetPermanentOrPlayerAmount target) { @@ -39,6 +43,12 @@ public abstract class TargetPermanentOrPlayerAmount extends TargetAmount { @Override public boolean canTarget(UUID objectId, Game game) { + + // max targets limit reached (only selected can be choosen again) + if (getMaxNumberOfTargets() > 0 && getTargets().size() >= getMaxNumberOfTargets()) { + return getTargets().contains(objectId); + } + Permanent permanent = game.getPermanent(objectId); if (permanent != null) { return filter.match(permanent, game); @@ -49,6 +59,12 @@ public abstract class TargetPermanentOrPlayerAmount extends TargetAmount { @Override public boolean canTarget(UUID objectId, Ability source, Game game) { + + // max targets limit reached (only selected can be choosen again) + if (getMaxNumberOfTargets() > 0 && getTargets().size() >= getMaxNumberOfTargets()) { + return getTargets().contains(objectId); + } + Permanent permanent = game.getPermanent(objectId); Player player = game.getPlayer(objectId); @@ -77,6 +93,7 @@ public abstract class TargetPermanentOrPlayerAmount extends TargetAmount { @Override public boolean canChoose(UUID sourceId, UUID sourceControllerId, Game game) { + // no max targets limit here int count = 0; MageObject targetSource = game.getObject(sourceId); for (UUID playerId : game.getState().getPlayersInRange(sourceControllerId, game)) { @@ -105,6 +122,7 @@ public abstract class TargetPermanentOrPlayerAmount extends TargetAmount { @Override public boolean canChoose(UUID sourceControllerId, Game game) { + // no max targets limit here int count = 0; for (UUID playerId : game.getState().getPlayersInRange(sourceControllerId, game)) { Player player = game.getPlayer(playerId); @@ -128,6 +146,13 @@ public abstract class TargetPermanentOrPlayerAmount extends TargetAmount { @Override public Set possibleTargets(UUID sourceId, UUID sourceControllerId, Game game) { Set possibleTargets = new HashSet<>(); + + // max targets limit reached (only selected can be choosen again) + if (getMaxNumberOfTargets() > 0 && getTargets().size() >= getMaxNumberOfTargets()) { + possibleTargets.addAll(getTargets()); + return possibleTargets; + } + MageObject targetSource = game.getObject(sourceId); game.getState() @@ -155,6 +180,13 @@ public abstract class TargetPermanentOrPlayerAmount extends TargetAmount { @Override public Set possibleTargets(UUID sourceControllerId, Game game) { Set possibleTargets = new HashSet<>(); + + // max targets limit reached (only selected can be choosen again) + if (getMaxNumberOfTargets() > 0 && getTargets().size() >= getMaxNumberOfTargets()) { + possibleTargets.addAll(getTargets()); + return possibleTargets; + } + game.getState() .getPlayersInRange(sourceControllerId, game) .stream() From eafb4eb65320f276746852629397c7281a1d5608 Mon Sep 17 00:00:00 2001 From: Oleg Agafonov Date: Tue, 24 Sep 2019 07:47:02 +0400 Subject: [PATCH 279/373] * UI: improved choose target amount dialog (added info about selected targets and amount); --- .../src/mage/player/human/HumanPlayer.java | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/Mage.Server.Plugins/Mage.Player.Human/src/mage/player/human/HumanPlayer.java b/Mage.Server.Plugins/Mage.Player.Human/src/mage/player/human/HumanPlayer.java index ff0a8289b5..4858198299 100644 --- a/Mage.Server.Plugins/Mage.Player.Human/src/mage/player/human/HumanPlayer.java +++ b/Mage.Server.Plugins/Mage.Player.Human/src/mage/player/human/HumanPlayer.java @@ -708,7 +708,11 @@ public class HumanPlayer extends PlayerImpl { while (!abort) { prepareForResponse(game); if (!isExecutingMacro()) { - game.fireSelectTargetEvent(playerId, new MessageToClient(target.getMessage() + "\n Amount remaining:" + target.getAmountRemaining(), getRelatedObjectName(source, game)), + String selectedNames = target.getTargetedName(game); + game.fireSelectTargetEvent(playerId, new MessageToClient(target.getMessage() + + "
Amount remaining: " + target.getAmountRemaining() + + (selectedNames.isEmpty() ? "" : ", selected: " + selectedNames), + getRelatedObjectName(source, game)), target.possibleTargets(source == null ? null : source.getSourceId(), playerId, game), target.isRequired(source), getOptions(target, null)); From 6cc2472ed6321e9457d04aee04c73d269b8c91d2 Mon Sep 17 00:00:00 2001 From: Oleg Agafonov Date: Tue, 24 Sep 2019 08:40:58 +0400 Subject: [PATCH 280/373] * UI: improved choose target amount dialog (selected targets can be removed/de-selected); --- .../src/mage/player/human/HumanPlayer.java | 15 +++++++++-- .../main/java/mage/target/TargetAmount.java | 25 ++++++++++++------- 2 files changed, 29 insertions(+), 11 deletions(-) diff --git a/Mage.Server.Plugins/Mage.Player.Human/src/mage/player/human/HumanPlayer.java b/Mage.Server.Plugins/Mage.Player.Human/src/mage/player/human/HumanPlayer.java index 4858198299..d2c615b80b 100644 --- a/Mage.Server.Plugins/Mage.Player.Human/src/mage/player/human/HumanPlayer.java +++ b/Mage.Server.Plugins/Mage.Player.Human/src/mage/player/human/HumanPlayer.java @@ -721,8 +721,19 @@ public class HumanPlayer extends PlayerImpl { if (response.getUUID() != null) { if (target.canTarget(response.getUUID(), source, game)) { UUID targetId = response.getUUID(); - int amountSelected = getAmount(1, target.getAmountRemaining(), "Select amount", game); - target.addTarget(targetId, amountSelected, source, game); + MageObject targetObject = game.getObject(targetId); + + boolean removeMode = target.getTargets().contains(targetId) + && chooseUse(outcome, "What do you want to do with " + (targetObject != null ? targetObject.getLogName() : "target") + "?", "", + "Remove from selected", "Add extra amount", source, game); + + if (removeMode) { + target.remove(targetId); + } else { + int amountSelected = getAmount(1, target.getAmountRemaining(), "Select amount", game); + target.addTarget(targetId, amountSelected, source, game); + } + return true; } } else if (!target.isRequired(source)) { diff --git a/Mage/src/main/java/mage/target/TargetAmount.java b/Mage/src/main/java/mage/target/TargetAmount.java index df3f372fd1..84ced7d035 100644 --- a/Mage/src/main/java/mage/target/TargetAmount.java +++ b/Mage/src/main/java/mage/target/TargetAmount.java @@ -1,5 +1,3 @@ - - package mage.target; import mage.abilities.Ability; @@ -7,11 +5,14 @@ import mage.abilities.dynamicvalue.DynamicValue; import mage.abilities.dynamicvalue.common.StaticValue; import mage.constants.Outcome; import mage.game.Game; -import java.util.*; + +import java.util.ArrayList; +import java.util.List; +import java.util.Set; +import java.util.UUID; import java.util.stream.Collectors; /** - * * @author BetaSteward_at_googlemail.com */ public abstract class TargetAmount extends TargetImpl { @@ -63,8 +64,8 @@ public abstract class TargetAmount extends TargetImpl { public void setAmountDefinition(DynamicValue amount) { this.amount = amount; - } - + } + public void setAmount(Ability source, Game game) { remainingAmount = amount.calculate(game, source, null); amountWasSet = true; @@ -82,6 +83,13 @@ public abstract class TargetAmount extends TargetImpl { } } + @Override + public void remove(UUID id) { + int amount = getTargetAmount(id); + super.remove(id); + this.remainingAmount += amount; + } + @Override public boolean chooseTarget(Outcome outcome, UUID playerId, Ability source, Game game) { if (!amountWasSet) { @@ -111,7 +119,7 @@ public abstract class TargetAmount extends TargetImpl { if (!amountWasSet) { setAmount(source, game); } - for (UUID targetId: targets) { + for (UUID targetId : targets) { for (int n = 1; n <= target.remainingAmount; n++) { TargetAmount t = target.copy(); t.addTarget(targetId, n, source, game, true); @@ -120,8 +128,7 @@ public abstract class TargetAmount extends TargetImpl { Set newTargets = targets.stream().filter(newTarget -> !newTarget.equals(targetId)).collect(Collectors.toSet()); addTargets(t, newTargets, options, source, game); } - } - else { + } else { options.add(t); } } From a2c4dc69d8800bbe2d78d8c291186aa80137d72c Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Tue, 24 Sep 2019 08:23:26 -0400 Subject: [PATCH 281/373] fixed Wicked Guardian drawing two cards instead of one (fixes #5996) --- Mage.Sets/src/mage/cards/w/WickedGuardian.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Mage.Sets/src/mage/cards/w/WickedGuardian.java b/Mage.Sets/src/mage/cards/w/WickedGuardian.java index 3309300daa..23136034fb 100644 --- a/Mage.Sets/src/mage/cards/w/WickedGuardian.java +++ b/Mage.Sets/src/mage/cards/w/WickedGuardian.java @@ -87,6 +87,6 @@ class WickedGuardianEffect extends OneShotEffect { return false; } permanent.damage(2, source.getSourceId(), game); - return player.drawCards(2, game) > 0; + return player.drawCards(1, game) > 0; } } \ No newline at end of file From a4f9c76425f3892046feed6dfd46238549c976fe Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Tue, 24 Sep 2019 08:37:45 -0400 Subject: [PATCH 282/373] Implemented Sundering Stroke --- .../src/mage/cards/s/SunderingStroke.java | 52 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + .../ThroneOfEldraineCollectorsEdition.java | 1 + 3 files changed, 54 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/s/SunderingStroke.java diff --git a/Mage.Sets/src/mage/cards/s/SunderingStroke.java b/Mage.Sets/src/mage/cards/s/SunderingStroke.java new file mode 100644 index 0000000000..59ea9619d7 --- /dev/null +++ b/Mage.Sets/src/mage/cards/s/SunderingStroke.java @@ -0,0 +1,52 @@ +package mage.cards.s; + +import mage.abilities.Ability; +import mage.abilities.condition.Condition; +import mage.abilities.decorator.ConditionalOneShotEffect; +import mage.abilities.effects.common.DamageMultiEffect; +import mage.abilities.effects.common.DamageTargetEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.ColoredManaSymbol; +import mage.game.Game; +import mage.target.common.TargetAnyTargetAmount; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class SunderingStroke extends CardImpl { + + public SunderingStroke(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.SORCERY}, "{6}{R}"); + + // Sundering Stroke deals 7 damage divided as you choose among one, two, or three targets. If at least seven red mana was spent to cast this spell, instead Sundering Stroke deals 7 damage to each of those permanents and/or players. + this.getSpellAbility().addEffect(new ConditionalOneShotEffect( + new DamageTargetEffect(7), new DamageMultiEffect(7), SunderingStrokeCondtition.instance, + "{this} deals 7 damage divided as you choose among one, two, or three targets. " + + "If at least seven red mana was spent to cast this spell, " + + "instead {this} deals 7 damage to each of those permanents and/or players" + )); + this.getSpellAbility().addTarget(new TargetAnyTargetAmount(7, 3)); + } + + private SunderingStroke(final SunderingStroke card) { + super(card); + } + + @Override + public SunderingStroke copy() { + return new SunderingStroke(this); + } +} + +enum SunderingStrokeCondtition implements Condition { + instance; + + @Override + public boolean apply(Game game, Ability source) { + return source.getManaCostsToPay().getPayment().getColor(ColoredManaSymbol.R) >= 6; + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index b96ca36576..778ce2282f 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -270,6 +270,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Stolen by the Fae", 66, Rarity.RARE, mage.cards.s.StolenByTheFae.class)); cards.add(new SetCardInfo("Stonecoil Serpent", 235, Rarity.RARE, mage.cards.s.StonecoilSerpent.class)); cards.add(new SetCardInfo("Stormfist Crusader", 203, Rarity.RARE, mage.cards.s.StormfistCrusader.class)); + cards.add(new SetCardInfo("Sundering Stroke", 144, Rarity.RARE, mage.cards.s.SunderingStroke.class)); cards.add(new SetCardInfo("Swamp", 258, Rarity.LAND, mage.cards.basiclands.Swamp.class, NON_FULL_USE_VARIOUS)); cards.add(new SetCardInfo("Swamp", 259, Rarity.LAND, mage.cards.basiclands.Swamp.class, NON_FULL_USE_VARIOUS)); cards.add(new SetCardInfo("Swamp", 260, Rarity.LAND, mage.cards.basiclands.Swamp.class, NON_FULL_USE_VARIOUS)); diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraineCollectorsEdition.java b/Mage.Sets/src/mage/sets/ThroneOfEldraineCollectorsEdition.java index 55abb35254..3d22d30c87 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraineCollectorsEdition.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraineCollectorsEdition.java @@ -95,6 +95,7 @@ public final class ThroneOfEldraineCollectorsEdition extends ExpansionSet { cards.add(new SetCardInfo("Stolen by the Fae", 348, Rarity.RARE, mage.cards.s.StolenByTheFae.class)); cards.add(new SetCardInfo("Stonecoil Serpent", 385, Rarity.RARE, mage.cards.s.StonecoilSerpent.class)); cards.add(new SetCardInfo("Stormfist Crusader", 383, Rarity.RARE, mage.cards.s.StormfistCrusader.class)); + cards.add(new SetCardInfo("Sundering Stroke", 366, Rarity.RARE, mage.cards.s.SunderingStroke.class)); cards.add(new SetCardInfo("The Cauldron of Eternity", 352, Rarity.MYTHIC, mage.cards.t.TheCauldronOfEternity.class)); cards.add(new SetCardInfo("The Circle of Loyalty", 336, Rarity.MYTHIC, mage.cards.t.TheCircleOfLoyalty.class)); cards.add(new SetCardInfo("The Great Henge", 370, Rarity.MYTHIC, mage.cards.t.TheGreatHenge.class)); From ed8ce472af929c821f75f410a88139a0aae17a1a Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Tue, 24 Sep 2019 09:26:31 -0400 Subject: [PATCH 283/373] fixed Fabled Passage putting lands into play untapped --- Mage.Sets/src/mage/cards/f/FabledPassage.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Mage.Sets/src/mage/cards/f/FabledPassage.java b/Mage.Sets/src/mage/cards/f/FabledPassage.java index a1cdd2098b..7897263e3a 100644 --- a/Mage.Sets/src/mage/cards/f/FabledPassage.java +++ b/Mage.Sets/src/mage/cards/f/FabledPassage.java @@ -75,7 +75,7 @@ class FabledPassageEffect extends OneShotEffect { if (card == null) { return false; } - if (!player.moveCards(card, Zone.BATTLEFIELD, source, game)) { + if (!player.moveCards(card, Zone.BATTLEFIELD, source, game, true, false, false, null)) { return false; } if (game.getBattlefield().countAll(StaticFilters.FILTER_LAND, source.getControllerId(), game) < 4) { From 84206205ad96043ea3c9fd44f8ca30b2480f1d44 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Tue, 24 Sep 2019 19:45:31 -0400 Subject: [PATCH 284/373] updated TargetAmount for permanents --- .../TargetCreatureOrPlaneswalkerAmount.java | 123 +------------- .../common/TargetCreaturePermanentAmount.java | 125 +-------------- .../target/common/TargetPermanentAmount.java | 150 ++++++++++++++++++ 3 files changed, 161 insertions(+), 237 deletions(-) create mode 100644 Mage/src/main/java/mage/target/common/TargetPermanentAmount.java diff --git a/Mage/src/main/java/mage/target/common/TargetCreatureOrPlaneswalkerAmount.java b/Mage/src/main/java/mage/target/common/TargetCreatureOrPlaneswalkerAmount.java index d005822bc0..3485646d4d 100644 --- a/Mage/src/main/java/mage/target/common/TargetCreatureOrPlaneswalkerAmount.java +++ b/Mage/src/main/java/mage/target/common/TargetCreatureOrPlaneswalkerAmount.java @@ -1,151 +1,38 @@ package mage.target.common; -import mage.MageObject; -import mage.abilities.Ability; import mage.abilities.dynamicvalue.DynamicValue; -import mage.abilities.dynamicvalue.common.StaticValue; -import mage.constants.Zone; -import mage.filter.Filter; import mage.filter.common.FilterCreatureOrPlaneswalkerPermanent; -import mage.game.Game; -import mage.game.permanent.Permanent; -import mage.target.TargetAmount; - -import java.util.Objects; -import java.util.Set; -import java.util.UUID; -import java.util.stream.Collectors; /** * @author BetaSteward_at_googlemail.com */ -public class TargetCreatureOrPlaneswalkerAmount extends TargetAmount { +public class TargetCreatureOrPlaneswalkerAmount extends TargetPermanentAmount { - protected final FilterCreatureOrPlaneswalkerPermanent filter; private static final FilterCreatureOrPlaneswalkerPermanent defaultFilter = new FilterCreatureOrPlaneswalkerPermanent(); public TargetCreatureOrPlaneswalkerAmount(int amount) { - // 107.1c If a rule or ability instructs a player to choose “any number,” that player may choose - // any positive number or zero, unless something (such as damage or counters) is being divided - // or distributed among “any number” of players and/or objects. In that case, a nonzero number - // of players and/or objects must be chosen if possible. - this(amount, defaultFilter); + super(amount, defaultFilter); } public TargetCreatureOrPlaneswalkerAmount(DynamicValue amount) { - this(amount, defaultFilter); + super(amount, defaultFilter); } public TargetCreatureOrPlaneswalkerAmount(int amount, FilterCreatureOrPlaneswalkerPermanent filter) { - this(new StaticValue(amount), filter); + super(amount, filter); } public TargetCreatureOrPlaneswalkerAmount(DynamicValue amount, FilterCreatureOrPlaneswalkerPermanent filter) { - super(amount); - this.zone = Zone.ALL; - this.filter = filter; - this.targetName = filter.getMessage(); + super(amount, filter); } private TargetCreatureOrPlaneswalkerAmount(final TargetCreatureOrPlaneswalkerAmount target) { super(target); - this.filter = target.filter.copy(); - } - - @Override - public Filter getFilter() { - return this.filter; - } - - @Override - public boolean canTarget(UUID objectId, Game game) { - Permanent permanent = game.getPermanent(objectId); - return permanent != null && filter.match(permanent, game); - } - - @Override - public boolean canTarget(UUID objectId, Ability source, Game game) { - Permanent permanent = game.getPermanent(objectId); - if (permanent != null) { - if (source != null) { - MageObject targetSource = source.getSourceObject(game); - return permanent.canBeTargetedBy(targetSource, source.getControllerId(), game) - && filter.match(permanent, source.getSourceId(), source.getControllerId(), game); - } else { - return filter.match(permanent, game); - } - } - return false; - } - - @Override - public boolean canTarget(UUID playerId, UUID objectId, Ability source, Game game) { - return canTarget(objectId, source, game); - } - - @Override - public boolean canChoose(UUID sourceId, UUID sourceControllerId, Game game) { - int count = 0; - for (Permanent permanent : game.getBattlefield().getActivePermanents(filter, sourceControllerId, sourceId, game)) { - count++; - if (count >= this.minNumberOfTargets) { - return true; - } - } - return false; - } - - @Override - public boolean canChoose(UUID sourceControllerId, Game game) { - int count = 0; - for (Permanent permanent : game.getBattlefield().getActivePermanents(filter, sourceControllerId, game)) { - count++; - if (count >= this.minNumberOfTargets) { - return true; - } - } - return false; - } - - @Override - public Set possibleTargets(UUID sourceId, UUID sourceControllerId, Game game) { - MageObject targetSource = game.getObject(sourceId); - return game - .getBattlefield() - .getActivePermanents(filter, sourceId, sourceControllerId, game) - .stream() - .filter(Objects::nonNull) - .filter(permanent -> permanent.canBeTargetedBy(targetSource, sourceControllerId, game)) - .map(Permanent::getId) - .collect(Collectors.toSet()); - } - - @Override - public Set possibleTargets(UUID sourceControllerId, Game game) { - return game - .getBattlefield() - .getActivePermanents(filter, sourceControllerId, game) - .stream() - .map(Permanent::getId) - .collect(Collectors.toSet()); - } - - @Override - public String getTargetedName(Game game) { - StringBuilder sb = new StringBuilder(); - for (UUID targetId : getTargets()) { - Permanent permanent = game.getPermanent(targetId); - if (permanent != null) { - sb.append(permanent.getLogName()).append('(').append(getTargetAmount(targetId)).append(") "); - } - } - return sb.toString(); } @Override public TargetCreatureOrPlaneswalkerAmount copy() { return new TargetCreatureOrPlaneswalkerAmount(this); } - } diff --git a/Mage/src/main/java/mage/target/common/TargetCreaturePermanentAmount.java b/Mage/src/main/java/mage/target/common/TargetCreaturePermanentAmount.java index fae796583a..855cb08516 100644 --- a/Mage/src/main/java/mage/target/common/TargetCreaturePermanentAmount.java +++ b/Mage/src/main/java/mage/target/common/TargetCreaturePermanentAmount.java @@ -1,145 +1,32 @@ - package mage.target.common; -import java.util.HashSet; -import java.util.Set; -import java.util.UUID; -import mage.MageObject; -import mage.abilities.Ability; import mage.abilities.dynamicvalue.DynamicValue; -import mage.abilities.dynamicvalue.common.StaticValue; -import mage.constants.Zone; -import mage.filter.Filter; import mage.filter.StaticFilters; import mage.filter.common.FilterCreaturePermanent; -import mage.game.Game; -import mage.game.permanent.Permanent; -import mage.target.TargetAmount; /** - * * @author North */ -public class TargetCreaturePermanentAmount extends TargetAmount { - - protected final FilterCreaturePermanent filter; +public class TargetCreaturePermanentAmount extends TargetPermanentAmount { public TargetCreaturePermanentAmount(int amount) { - this(amount, new FilterCreaturePermanent()); + super(amount, StaticFilters.FILTER_PERMANENT_CREATURE); } public TargetCreaturePermanentAmount(DynamicValue amount) { - this(amount, new FilterCreaturePermanent()); + this(amount, StaticFilters.FILTER_PERMANENT_CREATURE); } public TargetCreaturePermanentAmount(int amount, FilterCreaturePermanent filter) { - this(new StaticValue(amount), filter); + super(amount, filter); } public TargetCreaturePermanentAmount(DynamicValue amount, FilterCreaturePermanent filter) { - super(amount); - this.zone = Zone.ALL; - this.filter = filter; - this.targetName = filter.getMessage(); + super(amount, filter); } - public TargetCreaturePermanentAmount(final TargetCreaturePermanentAmount target) { + private TargetCreaturePermanentAmount(final TargetCreaturePermanentAmount target) { super(target); - this.filter = target.filter.copy(); - } - - @Override - public Filter getFilter() { - return this.filter; - } - - @Override - public boolean canTarget(UUID id, Game game) { - Permanent permanent = game.getPermanent(id); - return permanent != null && filter.match(permanent, game); - } - - @Override - public boolean canTarget(UUID id, Ability source, Game game) { - Permanent permanent = game.getPermanent(id); - if (permanent != null) { - if (source != null) { - MageObject targetSource = game.getObject(source.getSourceId()); - return permanent.canBeTargetedBy(targetSource, source.getControllerId(), game) && filter.match(permanent, source.getSourceId(), source.getControllerId(), game); - } else { - return filter.match(permanent, game); - } - } - return false; - } - - @Override - public boolean canTarget(UUID playerId, UUID id, Ability source, Game game) { - return canTarget(id, source, game); - } - - @Override - public boolean canChoose(UUID sourceId, UUID sourceControllerId, Game game) { - int count = 0; - MageObject targetSource = game.getObject(sourceId); - for (Permanent permanent : game.getBattlefield().getActivePermanents(StaticFilters.FILTER_PERMANENT_CREATURE, sourceControllerId, game)) { - if (permanent.canBeTargetedBy(targetSource, sourceControllerId, game) && filter.match(permanent, sourceId, sourceControllerId, game)) { - count++; - if (count >= this.minNumberOfTargets) { - return true; - } - } - } - return false; - } - - @Override - public boolean canChoose(UUID sourceControllerId, Game game) { - int count = 0; - for (Permanent permanent : game.getBattlefield().getActivePermanents(StaticFilters.FILTER_PERMANENT_CREATURE, sourceControllerId, game)) { - if (filter.match(permanent, null, sourceControllerId, game)) { - count++; - if (count >= this.minNumberOfTargets) { - return true; - } - } - } - return false; - } - - @Override - public Set possibleTargets(UUID sourceId, UUID sourceControllerId, Game game) { - Set possibleTargets = new HashSet<>(); - MageObject targetSource = game.getObject(sourceId); - for (Permanent permanent : game.getBattlefield().getActivePermanents(StaticFilters.FILTER_PERMANENT_CREATURE, sourceControllerId, game)) { - if (permanent.canBeTargetedBy(targetSource, sourceControllerId, game) && filter.match(permanent, sourceId, sourceControllerId, game)) { - possibleTargets.add(permanent.getId()); - } - } - return possibleTargets; - } - - @Override - public Set possibleTargets(UUID sourceControllerId, Game game) { - Set possibleTargets = new HashSet<>(); - for (Permanent permanent : game.getBattlefield().getActivePermanents(StaticFilters.FILTER_PERMANENT_CREATURE, sourceControllerId, game)) { - if (filter.match(permanent, null, sourceControllerId, game)) { - possibleTargets.add(permanent.getId()); - } - } - return possibleTargets; - } - - @Override - public String getTargetedName(Game game) { - StringBuilder sb = new StringBuilder(); - for (UUID targetId : getTargets()) { - Permanent permanent = game.getPermanent(targetId); - if (permanent != null) { - sb.append(permanent.getLogName()).append('(').append(getTargetAmount(targetId)).append(") "); - } - } - return sb.toString(); } @Override diff --git a/Mage/src/main/java/mage/target/common/TargetPermanentAmount.java b/Mage/src/main/java/mage/target/common/TargetPermanentAmount.java new file mode 100644 index 0000000000..b6c9afedc3 --- /dev/null +++ b/Mage/src/main/java/mage/target/common/TargetPermanentAmount.java @@ -0,0 +1,150 @@ +package mage.target.common; + +import mage.MageObject; +import mage.abilities.Ability; +import mage.abilities.dynamicvalue.DynamicValue; +import mage.abilities.dynamicvalue.common.StaticValue; +import mage.constants.Zone; +import mage.filter.Filter; +import mage.filter.FilterPermanent; +import mage.game.Game; +import mage.game.permanent.Permanent; +import mage.target.TargetAmount; + +import java.util.Objects; +import java.util.Set; +import java.util.UUID; +import java.util.stream.Collectors; + +/** + * @author TheElk801 + */ +public abstract class TargetPermanentAmount extends TargetAmount { + + protected final FilterPermanent filter; + + TargetPermanentAmount(int amount, FilterPermanent filter) { + // 107.1c If a rule or ability instructs a player to choose “any number,” that player may choose + // any positive number or zero, unless something (such as damage or counters) is being divided + // or distributed among “any number” of players and/or objects. In that case, a nonzero number + // of players and/or objects must be chosen if possible. + this(new StaticValue(amount), filter); + } + + TargetPermanentAmount(DynamicValue amount, FilterPermanent filter) { + super(amount); + this.zone = Zone.ALL; + this.filter = filter; + this.targetName = filter.getMessage(); + } + + TargetPermanentAmount(final TargetPermanentAmount target) { + super(target); + this.filter = target.filter.copy(); + } + + @Override + public Filter getFilter() { + return this.filter; + } + + @Override + public boolean canTarget(UUID objectId, Game game) { + Permanent permanent = game.getPermanent(objectId); + return permanent != null && filter.match(permanent, game); + } + + @Override + public boolean canTarget(UUID objectId, Ability source, Game game) { + if (getMaxNumberOfTargets() > 0 && getTargets().size() >= getMaxNumberOfTargets()) { + return getTargets().contains(objectId); + } + Permanent permanent = game.getPermanent(objectId); + if (permanent == null) { + return false; + } + if (source == null) { + return filter.match(permanent, game); + } + MageObject targetSource = source.getSourceObject(game); + return permanent.canBeTargetedBy(targetSource, source.getControllerId(), game) + && filter.match(permanent, source.getSourceId(), source.getControllerId(), game); + } + + @Override + public boolean canTarget(UUID playerId, UUID objectId, Ability source, Game game) { + return canTarget(objectId, source, game); + } + + @Override + public boolean canChoose(UUID sourceId, UUID sourceControllerId, Game game) { + int count = 0; + for (Permanent permanent : game.getBattlefield().getActivePermanents(filter, sourceControllerId, sourceId, game)) { + count++; + if (count >= this.minNumberOfTargets) { + return true; + } + } + return false; + } + + @Override + public boolean canChoose(UUID sourceControllerId, Game game) { + int count = 0; + for (Permanent permanent : game.getBattlefield().getActivePermanents(filter, sourceControllerId, game)) { + count++; + if (count >= this.minNumberOfTargets) { + return true; + } + } + return false; + } + + @Override + public Set possibleTargets(UUID sourceId, UUID sourceControllerId, Game game) { + if (getMaxNumberOfTargets() > 0 && getTargets().size() >= getMaxNumberOfTargets()) { + return getTargets() + .stream() + .collect(Collectors.toSet()); + } + MageObject targetSource = game.getObject(sourceId); + return game + .getBattlefield() + .getActivePermanents(filter, sourceControllerId, sourceId, game) + .stream() + .filter(Objects::nonNull) + .filter(permanent -> permanent.canBeTargetedBy(targetSource, sourceControllerId, game)) + .map(Permanent::getId) + .collect(Collectors.toSet()); + } + + @Override + public Set possibleTargets(UUID sourceControllerId, Game game) { + if (getMaxNumberOfTargets() > 0 && getTargets().size() >= getMaxNumberOfTargets()) { + return getTargets() + .stream() + .collect(Collectors.toSet()); + } + return game + .getBattlefield() + .getActivePermanents(filter, sourceControllerId, game) + .stream() + .map(Permanent::getId) + .collect(Collectors.toSet()); + } + + @Override + public String getTargetedName(Game game) { + StringBuilder sb = new StringBuilder(); + for (UUID targetId : getTargets()) { + Permanent permanent = game.getPermanent(targetId); + if (permanent != null) { + sb.append(permanent.getLogName()).append('(').append(getTargetAmount(targetId)).append(") "); + } + } + return sb.toString(); + } + + @Override + public abstract TargetPermanentAmount copy(); +} From 3c2471fe7d19fc80ac80487c269d7e64a076d508 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Tue, 24 Sep 2019 19:50:02 -0400 Subject: [PATCH 285/373] Implemented Forked Lightning --- .../src/mage/cards/f/ForkedLightning.java | 35 +++++++++++++++++++ .../src/mage/sets/MastersEditionIII.java | 1 + Mage.Sets/src/mage/sets/Portal.java | 1 + 3 files changed, 37 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/f/ForkedLightning.java diff --git a/Mage.Sets/src/mage/cards/f/ForkedLightning.java b/Mage.Sets/src/mage/cards/f/ForkedLightning.java new file mode 100644 index 0000000000..0d14651ab6 --- /dev/null +++ b/Mage.Sets/src/mage/cards/f/ForkedLightning.java @@ -0,0 +1,35 @@ +package mage.cards.f; + +import java.util.UUID; + +import mage.abilities.effects.common.DamageMultiEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.target.Target; +import mage.target.common.TargetCreaturePermanentAmount; + +/** + * + * @author TheElk801 + */ +public final class ForkedLightning extends CardImpl { + + public ForkedLightning(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.SORCERY}, "{3}{R}"); + + // Forked Lightning deals 4 damage divided as you choose among one, two, or three target creatures. + this.getSpellAbility().addEffect(new DamageMultiEffect(4) + .setText("{this} deals 4 damage divided as you choose among one, two, or three target creatures")); + Target target=new TargetCreaturePermanentAmount(4);target.setMaxNumberOfTargets(3);this.getSpellAbility().addTarget(target); + } + + private ForkedLightning(final ForkedLightning card) { + super(card); + } + + @Override + public ForkedLightning copy() { + return new ForkedLightning(this); + } +} diff --git a/Mage.Sets/src/mage/sets/MastersEditionIII.java b/Mage.Sets/src/mage/sets/MastersEditionIII.java index 20f24d901e..61c5d64e4f 100644 --- a/Mage.Sets/src/mage/sets/MastersEditionIII.java +++ b/Mage.Sets/src/mage/sets/MastersEditionIII.java @@ -96,6 +96,7 @@ public final class MastersEditionIII extends ExpansionSet { cards.add(new SetCardInfo("Forest", 228, Rarity.LAND, mage.cards.basiclands.Forest.class, NON_FULL_USE_VARIOUS)); cards.add(new SetCardInfo("Forest", 229, Rarity.LAND, mage.cards.basiclands.Forest.class, NON_FULL_USE_VARIOUS)); cards.add(new SetCardInfo("Forest", 230, Rarity.LAND, mage.cards.basiclands.Forest.class, NON_FULL_USE_VARIOUS)); + cards.add(new SetCardInfo("Forked Lightning", 100, Rarity.UNCOMMON, mage.cards.f.ForkedLightning.class)); cards.add(new SetCardInfo("Freyalise's Winds", 119, Rarity.RARE, mage.cards.f.FreyalisesWinds.class)); cards.add(new SetCardInfo("Frost Giant", 101, Rarity.UNCOMMON, mage.cards.f.FrostGiant.class)); cards.add(new SetCardInfo("Gabriel Angelfire", 148, Rarity.RARE, mage.cards.g.GabrielAngelfire.class)); diff --git a/Mage.Sets/src/mage/sets/Portal.java b/Mage.Sets/src/mage/sets/Portal.java index 822317e27b..7dfcb239ca 100644 --- a/Mage.Sets/src/mage/sets/Portal.java +++ b/Mage.Sets/src/mage/sets/Portal.java @@ -106,6 +106,7 @@ public final class Portal extends ExpansionSet { cards.add(new SetCardInfo("Forest", 213, Rarity.LAND, mage.cards.basiclands.Forest.class, NON_FULL_USE_VARIOUS)); cards.add(new SetCardInfo("Forest", 214, Rarity.LAND, mage.cards.basiclands.Forest.class, NON_FULL_USE_VARIOUS)); cards.add(new SetCardInfo("Forest", 215, Rarity.LAND, mage.cards.basiclands.Forest.class, NON_FULL_USE_VARIOUS)); + cards.add(new SetCardInfo("Forked Lightning", 135, Rarity.RARE, mage.cards.f.ForkedLightning.class)); cards.add(new SetCardInfo("Fruition", 166, Rarity.COMMON, mage.cards.f.Fruition.class)); cards.add(new SetCardInfo("Giant Octopus", 56, Rarity.COMMON, mage.cards.g.GiantOctopus.class)); cards.add(new SetCardInfo("Giant Spider", 167, Rarity.COMMON, mage.cards.g.GiantSpider.class)); From 80790b74e7d37ce680de01dd94b290fc93afaa91 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Tue, 24 Sep 2019 20:03:00 -0400 Subject: [PATCH 286/373] fixed a numbering error --- Mage.Sets/src/mage/sets/Portal.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Mage.Sets/src/mage/sets/Portal.java b/Mage.Sets/src/mage/sets/Portal.java index 7dfcb239ca..36eb3c8f52 100644 --- a/Mage.Sets/src/mage/sets/Portal.java +++ b/Mage.Sets/src/mage/sets/Portal.java @@ -106,7 +106,7 @@ public final class Portal extends ExpansionSet { cards.add(new SetCardInfo("Forest", 213, Rarity.LAND, mage.cards.basiclands.Forest.class, NON_FULL_USE_VARIOUS)); cards.add(new SetCardInfo("Forest", 214, Rarity.LAND, mage.cards.basiclands.Forest.class, NON_FULL_USE_VARIOUS)); cards.add(new SetCardInfo("Forest", 215, Rarity.LAND, mage.cards.basiclands.Forest.class, NON_FULL_USE_VARIOUS)); - cards.add(new SetCardInfo("Forked Lightning", 135, Rarity.RARE, mage.cards.f.ForkedLightning.class)); + cards.add(new SetCardInfo("Forked Lightning", 130, Rarity.RARE, mage.cards.f.ForkedLightning.class)); cards.add(new SetCardInfo("Fruition", 166, Rarity.COMMON, mage.cards.f.Fruition.class)); cards.add(new SetCardInfo("Giant Octopus", 56, Rarity.COMMON, mage.cards.g.GiantOctopus.class)); cards.add(new SetCardInfo("Giant Spider", 167, Rarity.COMMON, mage.cards.g.GiantSpider.class)); From a99afc763d8d3ae353d345cec767b2a7b28df720 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Tue, 24 Sep 2019 20:07:12 -0400 Subject: [PATCH 287/373] updated Dread Warlock creature type --- Mage.Sets/src/mage/cards/d/DreadWarlock.java | 1 + Mage.Verify/src/test/java/mage/verify/VerifyCardDataTest.java | 1 + 2 files changed, 2 insertions(+) diff --git a/Mage.Sets/src/mage/cards/d/DreadWarlock.java b/Mage.Sets/src/mage/cards/d/DreadWarlock.java index 7652b982f5..48c352c4f1 100644 --- a/Mage.Sets/src/mage/cards/d/DreadWarlock.java +++ b/Mage.Sets/src/mage/cards/d/DreadWarlock.java @@ -31,6 +31,7 @@ public final class DreadWarlock extends CardImpl { super(ownerId,setInfo,new CardType[]{CardType.CREATURE},"{1}{B}{B}"); this.subtype.add(SubType.HUMAN); this.subtype.add(SubType.WIZARD); + this.subtype.add(SubType.WARLOCK); this.power = new MageInt(2); this.toughness = new MageInt(2); diff --git a/Mage.Verify/src/test/java/mage/verify/VerifyCardDataTest.java b/Mage.Verify/src/test/java/mage/verify/VerifyCardDataTest.java index d6ba12acdf..33d8f28e08 100644 --- a/Mage.Verify/src/test/java/mage/verify/VerifyCardDataTest.java +++ b/Mage.Verify/src/test/java/mage/verify/VerifyCardDataTest.java @@ -93,6 +93,7 @@ public class VerifyCardDataTest { // subtype skipListCreate("SUBTYPE"); skipListAddName("SUBTYPE", "UGL", "Miss Demeanor"); + skipListAddName("SUBTYPE", "M10", "Dread Warlock"); // number skipListCreate("NUMBER"); From b245b493b83a3277807c3dbe5553812539712d20 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Tue, 24 Sep 2019 21:41:02 -0400 Subject: [PATCH 288/373] Implemented Outlaws' Merriment --- .../src/mage/cards/o/OutlawsMerriment.java | 55 +++++++++++++++++++ Mage.Sets/src/mage/sets/ThroneOfEldraine.java | 1 + .../ThroneOfEldraineCollectorsEdition.java | 1 + Mage/src/main/java/mage/abilities/Modes.java | 30 ++++++++-- .../token/OutlawsMerrimentClericToken.java | 35 ++++++++++++ .../token/OutlawsMerrimentRogueToken.java | 40 ++++++++++++++ .../token/OutlawsMerrimentWarriorToken.java | 35 ++++++++++++ 7 files changed, 193 insertions(+), 4 deletions(-) create mode 100644 Mage.Sets/src/mage/cards/o/OutlawsMerriment.java create mode 100644 Mage/src/main/java/mage/game/permanent/token/OutlawsMerrimentClericToken.java create mode 100644 Mage/src/main/java/mage/game/permanent/token/OutlawsMerrimentRogueToken.java create mode 100644 Mage/src/main/java/mage/game/permanent/token/OutlawsMerrimentWarriorToken.java diff --git a/Mage.Sets/src/mage/cards/o/OutlawsMerriment.java b/Mage.Sets/src/mage/cards/o/OutlawsMerriment.java new file mode 100644 index 0000000000..653fa86cf9 --- /dev/null +++ b/Mage.Sets/src/mage/cards/o/OutlawsMerriment.java @@ -0,0 +1,55 @@ +package mage.cards.o; + +import mage.abilities.Ability; +import mage.abilities.Mode; +import mage.abilities.common.BeginningOfUpkeepTriggeredAbility; +import mage.abilities.effects.common.CreateTokenEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.TargetController; +import mage.game.permanent.token.OutlawsMerrimentClericToken; +import mage.game.permanent.token.OutlawsMerrimentRogueToken; +import mage.game.permanent.token.OutlawsMerrimentWarriorToken; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class OutlawsMerriment extends CardImpl { + + public OutlawsMerriment(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ENCHANTMENT}, "{1}{R}{W}{W}"); + + // At the beginning of your upkeep, choose one at random. Create a red and white creature token with those characteristics. + // • 3/1 Human Warrior with trample and haste. + Ability ability = new BeginningOfUpkeepTriggeredAbility( + new CreateTokenEffect(new OutlawsMerrimentWarriorToken()) + .setText("3/1 Human Warrior with trample and haste"), + TargetController.YOU, false + ); + + // • 2/1 Human Cleric with lifelink and haste. + ability.addMode(new Mode(new CreateTokenEffect(new OutlawsMerrimentClericToken()) + .setText("2/1 Human Cleric with lifelink and haste"))); + + // • 1/2 Human Rogue with haste and "When this creature enters the battlefield, it deals 1 damage to any target." + ability.addMode(new Mode(new CreateTokenEffect(new OutlawsMerrimentRogueToken()) + .setText("1/2 Human Rogue with haste and \"When this creature enters the battlefield, it deals 1 damage to any target.\""))); + + ability.getModes().setChooseText("choose one at random. Create a red and white creature token with those characteristics."); + ability.getModes().setRandom(true); + + this.addAbility(ability); + } + + private OutlawsMerriment(final OutlawsMerriment card) { + super(card); + } + + @Override + public OutlawsMerriment copy() { + return new OutlawsMerriment(this); + } +} diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java index 778ce2282f..2a8c83a769 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraine.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraine.java @@ -206,6 +206,7 @@ public final class ThroneOfEldraine extends ExpansionSet { cards.add(new SetCardInfo("Opt", 59, Rarity.COMMON, mage.cards.o.Opt.class)); cards.add(new SetCardInfo("Order of Midnight", 99, Rarity.UNCOMMON, mage.cards.o.OrderOfMidnight.class)); cards.add(new SetCardInfo("Outflank", 23, Rarity.COMMON, mage.cards.o.Outflank.class)); + cards.add(new SetCardInfo("Outlaws' Merriment", 198, Rarity.MYTHIC, mage.cards.o.OutlawsMerriment.class)); cards.add(new SetCardInfo("Outmuscle", 170, Rarity.COMMON, mage.cards.o.Outmuscle.class)); cards.add(new SetCardInfo("Overwhelmed Apprentice", 60, Rarity.UNCOMMON, mage.cards.o.OverwhelmedApprentice.class)); cards.add(new SetCardInfo("Piper of the Swarm", 100, Rarity.RARE, mage.cards.p.PiperOfTheSwarm.class)); diff --git a/Mage.Sets/src/mage/sets/ThroneOfEldraineCollectorsEdition.java b/Mage.Sets/src/mage/sets/ThroneOfEldraineCollectorsEdition.java index 3d22d30c87..9606cef6f0 100644 --- a/Mage.Sets/src/mage/sets/ThroneOfEldraineCollectorsEdition.java +++ b/Mage.Sets/src/mage/sets/ThroneOfEldraineCollectorsEdition.java @@ -78,6 +78,7 @@ public final class ThroneOfEldraineCollectorsEdition extends ExpansionSet { cards.add(new SetCardInfo("Once Upon a Time", 371, Rarity.RARE, mage.cards.o.OnceUponATime.class)); cards.add(new SetCardInfo("Opportunistic Dragon", 364, Rarity.RARE, mage.cards.o.OpportunisticDragon.class)); cards.add(new SetCardInfo("Order of Midnight", 288, Rarity.UNCOMMON, mage.cards.o.OrderOfMidnight.class)); + cards.add(new SetCardInfo("Outlaws' Merriment", 382, Rarity.MYTHIC, mage.cards.o.OutlawsMerriment.class)); cards.add(new SetCardInfo("Piper of the Swarm", 355, Rarity.RARE, mage.cards.p.PiperOfTheSwarm.class)); cards.add(new SetCardInfo("Queen of Ice", 285, Rarity.COMMON, mage.cards.q.QueenOfIce.class)); cards.add(new SetCardInfo("Questing Beast", 372, Rarity.MYTHIC, mage.cards.q.QuestingBeast.class)); diff --git a/Mage/src/main/java/mage/abilities/Modes.java b/Mage/src/main/java/mage/abilities/Modes.java index d74e678baf..68bccffbd6 100644 --- a/Mage/src/main/java/mage/abilities/Modes.java +++ b/Mage/src/main/java/mage/abilities/Modes.java @@ -9,6 +9,7 @@ import mage.filter.FilterPlayer; import mage.game.Game; import mage.players.Player; import mage.target.common.TargetOpponent; +import mage.util.RandomUtil; import java.util.*; @@ -27,6 +28,8 @@ public class Modes extends LinkedHashMap { private final Map duplicateModes = new LinkedHashMap<>(); private OptionalAdditionalModeSourceCosts optionalAdditionalModeSourceCosts = null; // only set if costs have to be paid private Filter maxModesFilter = null; // calculates the max number of available modes + private boolean isRandom = false; + private String chooseText = null; public Modes() { this.currentMode = new Mode(); @@ -56,6 +59,8 @@ public class Modes extends LinkedHashMap { this.optionalAdditionalModeSourceCosts = modes.optionalAdditionalModeSourceCosts; this.maxModesFilter = modes.maxModesFilter; // can't change so no copy needed + this.isRandom = modes.isRandom; + this.chooseText = modes.chooseText; if (modes.getSelectedModes().isEmpty()) { this.currentMode = values().iterator().next(); } else { @@ -163,6 +168,12 @@ public class Modes extends LinkedHashMap { if (this.size() > 1) { this.selectedModes.clear(); this.duplicateModes.clear(); + if (this.isRandom) { + List modes = getAvailableModes(source, game); + int r = RandomUtil.nextInt(modes.size()); + this.addSelectedMode(modes.get(r).getId()); + return true; + } // check if mode modifying abilities exist Card card = game.getCard(source.getSourceId()); if (card != null) { @@ -332,7 +343,9 @@ public class Modes extends LinkedHashMap { return this.getMode().getEffects().getText(this.getMode()); } StringBuilder sb = new StringBuilder(); - if (this.getMaxModesFilter() != null) { + if (this.chooseText != null) { + sb.append(chooseText); + } else if (this.getMaxModesFilter() != null) { sb.append("choose one or more. Each mode must target ").append(getMaxModesFilter().getMessage()); } else if (this.getMinModes() == 0 && this.getMaxModes() == 1) { sb.append("choose up to one"); @@ -357,11 +370,13 @@ public class Modes extends LinkedHashMap { } if (isEachModeMoreThanOnce()) { - sb.append(". You may choose the same mode more than once.
"); - } else { - sb.append(" —
"); + sb.append(". You may choose the same mode more than once."); + } else if (chooseText == null) { + sb.append(" —"); } + sb.append("
"); + for (Mode mode : this.values()) { sb.append("&bull "); sb.append(mode.getEffects().getTextStartingUpperCase(mode)); @@ -401,4 +416,11 @@ public class Modes extends LinkedHashMap { this.optionalAdditionalModeSourceCosts = optionalAdditionalModeSourceCosts; } + public void setRandom(boolean isRandom) { + this.isRandom = isRandom; + } + + public void setChooseText(String chooseText) { + this.chooseText = chooseText; + } } diff --git a/Mage/src/main/java/mage/game/permanent/token/OutlawsMerrimentClericToken.java b/Mage/src/main/java/mage/game/permanent/token/OutlawsMerrimentClericToken.java new file mode 100644 index 0000000000..e6553091f6 --- /dev/null +++ b/Mage/src/main/java/mage/game/permanent/token/OutlawsMerrimentClericToken.java @@ -0,0 +1,35 @@ +package mage.game.permanent.token; + +import mage.MageInt; +import mage.abilities.keyword.HasteAbility; +import mage.abilities.keyword.LifelinkAbility; +import mage.constants.CardType; +import mage.constants.SubType; + +/** + * @author TheElk801 + */ +public final class OutlawsMerrimentClericToken extends TokenImpl { + + public OutlawsMerrimentClericToken() { + super("Human Cleric", "2/1 Human Cleric with lifelink and haste"); + cardType.add(CardType.CREATURE); + subtype.add(SubType.HUMAN); + subtype.add(SubType.CLERIC); + color.setWhite(true); + color.setRed(true); + power = new MageInt(2); + toughness = new MageInt(1); + + this.addAbility(LifelinkAbility.getInstance()); + this.addAbility(HasteAbility.getInstance()); + } + + private OutlawsMerrimentClericToken(final OutlawsMerrimentClericToken token) { + super(token); + } + + public OutlawsMerrimentClericToken copy() { + return new OutlawsMerrimentClericToken(this); + } +} diff --git a/Mage/src/main/java/mage/game/permanent/token/OutlawsMerrimentRogueToken.java b/Mage/src/main/java/mage/game/permanent/token/OutlawsMerrimentRogueToken.java new file mode 100644 index 0000000000..11d4f52d8f --- /dev/null +++ b/Mage/src/main/java/mage/game/permanent/token/OutlawsMerrimentRogueToken.java @@ -0,0 +1,40 @@ +package mage.game.permanent.token; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.effects.common.DamageTargetEffect; +import mage.abilities.keyword.HasteAbility; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.target.common.TargetAnyTarget; + +/** + * @author TheElk801 + */ +public final class OutlawsMerrimentRogueToken extends TokenImpl { + + public OutlawsMerrimentRogueToken() { + super("Human Rogue", "1/2 Human Rogue with haste and \"When this creature enters the battlefield, it deals 1 damage to any target.\""); + cardType.add(CardType.CREATURE); + subtype.add(SubType.HUMAN); + subtype.add(SubType.ROGUE); + color.setWhite(true); + color.setRed(true); + power = new MageInt(1); + toughness = new MageInt(2); + + this.addAbility(HasteAbility.getInstance()); + Ability ability = new EntersBattlefieldTriggeredAbility(new DamageTargetEffect(1, "it")); + ability.addTarget(new TargetAnyTarget()); + this.addAbility(ability); + } + + private OutlawsMerrimentRogueToken(final OutlawsMerrimentRogueToken token) { + super(token); + } + + public OutlawsMerrimentRogueToken copy() { + return new OutlawsMerrimentRogueToken(this); + } +} diff --git a/Mage/src/main/java/mage/game/permanent/token/OutlawsMerrimentWarriorToken.java b/Mage/src/main/java/mage/game/permanent/token/OutlawsMerrimentWarriorToken.java new file mode 100644 index 0000000000..fdf816a51d --- /dev/null +++ b/Mage/src/main/java/mage/game/permanent/token/OutlawsMerrimentWarriorToken.java @@ -0,0 +1,35 @@ +package mage.game.permanent.token; + +import mage.MageInt; +import mage.abilities.keyword.HasteAbility; +import mage.abilities.keyword.TrampleAbility; +import mage.constants.CardType; +import mage.constants.SubType; + +/** + * @author TheElk801 + */ +public final class OutlawsMerrimentWarriorToken extends TokenImpl { + + public OutlawsMerrimentWarriorToken() { + super("Human Warrior", "3/1 Human Warrior with trample and haste"); + cardType.add(CardType.CREATURE); + subtype.add(SubType.HUMAN); + subtype.add(SubType.WARRIOR); + color.setWhite(true); + color.setRed(true); + power = new MageInt(3); + toughness = new MageInt(1); + + this.addAbility(TrampleAbility.getInstance()); + this.addAbility(HasteAbility.getInstance()); + } + + private OutlawsMerrimentWarriorToken(final OutlawsMerrimentWarriorToken token) { + super(token); + } + + public OutlawsMerrimentWarriorToken copy() { + return new OutlawsMerrimentWarriorToken(this); + } +} From 3d5925826cfe92365d6bfc6e5e9a99558531eea6 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Tue, 24 Sep 2019 22:26:28 -0400 Subject: [PATCH 289/373] temporary workaround for Rankle, Master of Pranks (still can't choose zero modes) #5979 --- Mage.Sets/src/mage/cards/r/RankleMasterOfPranks.java | 3 ++- Mage/src/main/java/mage/abilities/Modes.java | 3 +-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/Mage.Sets/src/mage/cards/r/RankleMasterOfPranks.java b/Mage.Sets/src/mage/cards/r/RankleMasterOfPranks.java index 182ff06ed1..9686f52d2c 100644 --- a/Mage.Sets/src/mage/cards/r/RankleMasterOfPranks.java +++ b/Mage.Sets/src/mage/cards/r/RankleMasterOfPranks.java @@ -51,8 +51,9 @@ public final class RankleMasterOfPranks extends CardImpl { // • Each player sacrifices a creature. ability.addMode(new Mode(new SacrificeAllEffect(StaticFilters.FILTER_CONTROLLED_CREATURE_SHORT_TEXT))); - ability.getModes().setMinModes(0); + ability.getModes().setMinModes(1); ability.getModes().setMaxModes(3); + ability.getModes().setChooseText("choose any number —"); this.addAbility(ability); } diff --git a/Mage/src/main/java/mage/abilities/Modes.java b/Mage/src/main/java/mage/abilities/Modes.java index 68bccffbd6..77b8bb3afe 100644 --- a/Mage/src/main/java/mage/abilities/Modes.java +++ b/Mage/src/main/java/mage/abilities/Modes.java @@ -170,8 +170,7 @@ public class Modes extends LinkedHashMap { this.duplicateModes.clear(); if (this.isRandom) { List modes = getAvailableModes(source, game); - int r = RandomUtil.nextInt(modes.size()); - this.addSelectedMode(modes.get(r).getId()); + this.addSelectedMode(modes.get(RandomUtil.nextInt(modes.size())).getId()); return true; } // check if mode modifying abilities exist From 9a993f987175fe0089f144bf0c191b1ac5de0319 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 25 Sep 2019 09:07:02 -0400 Subject: [PATCH 290/373] fixed The Great Henge and Return of the Wildspeaker throwing errors when no creatures are present --- Mage.Sets/src/mage/cards/r/ReturnOfTheWildspeaker.java | 2 +- Mage.Sets/src/mage/cards/t/TheGreatHenge.java | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/Mage.Sets/src/mage/cards/r/ReturnOfTheWildspeaker.java b/Mage.Sets/src/mage/cards/r/ReturnOfTheWildspeaker.java index 93e95bd7eb..ea0ae6927e 100644 --- a/Mage.Sets/src/mage/cards/r/ReturnOfTheWildspeaker.java +++ b/Mage.Sets/src/mage/cards/r/ReturnOfTheWildspeaker.java @@ -69,7 +69,7 @@ enum ReturnOfTheWildspeakerValue implements DynamicValue { .map(MageObject::getPower) .mapToInt(MageInt::getValue) .max() - .getAsInt(); + .orElse(0); } @Override diff --git a/Mage.Sets/src/mage/cards/t/TheGreatHenge.java b/Mage.Sets/src/mage/cards/t/TheGreatHenge.java index ebe1cbfafe..3c81dc3e09 100644 --- a/Mage.Sets/src/mage/cards/t/TheGreatHenge.java +++ b/Mage.Sets/src/mage/cards/t/TheGreatHenge.java @@ -91,8 +91,8 @@ class TheGreatHengeCostReductionEffect extends CostModificationEffectImpl { .map(Permanent::getPower) .mapToInt(MageInt::getValue) .max() - .getAsInt(); - CardUtil.reduceCost(abilityToModify, reductionAmount); + .orElse(0); + CardUtil.reduceCost(abilityToModify, Math.max(0, reductionAmount)); return true; } From c4aebb49db75fa3adf7f15ae4519809c558f553e Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 25 Sep 2019 09:19:14 -0400 Subject: [PATCH 291/373] fixed Syr Konrad, the Grim errors (fixes #5973) --- Mage.Sets/src/mage/cards/s/SyrKonradTheGrim.java | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/Mage.Sets/src/mage/cards/s/SyrKonradTheGrim.java b/Mage.Sets/src/mage/cards/s/SyrKonradTheGrim.java index 6f3cffaebe..aa61685d40 100644 --- a/Mage.Sets/src/mage/cards/s/SyrKonradTheGrim.java +++ b/Mage.Sets/src/mage/cards/s/SyrKonradTheGrim.java @@ -65,12 +65,12 @@ class SyrKonradTheGrimTriggeredAbility extends TriggeredAbilityImpl { } @Override - public boolean checkTrigger(GameEvent event, Game game) { + public boolean checkEventType(GameEvent event, Game game) { return event.getType() == GameEvent.EventType.ZONE_CHANGE; } @Override - public boolean checkEventType(GameEvent event, Game game) { + public boolean checkTrigger(GameEvent event, Game game) { ZoneChangeEvent zEvent = (ZoneChangeEvent) event; if (zEvent.isDiesEvent() && zEvent.getTarget() != null From 56ede98b03deae07175497f9603400f4b6486411 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 25 Sep 2019 10:07:54 -0400 Subject: [PATCH 292/373] fixed Covetous Urge not allowing the exiled card to be cast --- Mage.Sets/src/mage/cards/c/CovetousUrge.java | 7 +++---- 1 file changed, 3 insertions(+), 4 deletions(-) diff --git a/Mage.Sets/src/mage/cards/c/CovetousUrge.java b/Mage.Sets/src/mage/cards/c/CovetousUrge.java index 96ff870840..df7c1e307e 100644 --- a/Mage.Sets/src/mage/cards/c/CovetousUrge.java +++ b/Mage.Sets/src/mage/cards/c/CovetousUrge.java @@ -127,12 +127,11 @@ class CovetousUrgeCastFromExileEffect extends AsThoughEffectImpl { @Override public boolean applies(UUID sourceId, Ability source, UUID affectedControllerId, Game game) { Card card = mor.getCard(game); - if (card == null || !sourceId.equals(card.getId()) - || !source.isControlledBy(affectedControllerId)) { + if (card == null) { + discard(); return false; } - discard(); - return false; + return source.isControlledBy(affectedControllerId); } } From 720180ed933ef161d7a1b74bf8286383c91d6819 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 25 Sep 2019 10:18:14 -0400 Subject: [PATCH 293/373] fixed Memory Theft error --- Mage.Sets/src/mage/cards/m/MemoryTheft.java | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/Mage.Sets/src/mage/cards/m/MemoryTheft.java b/Mage.Sets/src/mage/cards/m/MemoryTheft.java index 47a31c1099..e302ecfeef 100644 --- a/Mage.Sets/src/mage/cards/m/MemoryTheft.java +++ b/Mage.Sets/src/mage/cards/m/MemoryTheft.java @@ -77,7 +77,8 @@ class MemoryTheftEffect extends OneShotEffect { filter.add(AdventurePredicate.instance); filter.add(new OwnerIdPredicate(player.getId())); TargetCard target = new TargetCardInExile(0, 1, filter, null, true); - if (!controller.choose(outcome, target, source.getSourceId(), game)) { + if (!target.canChoose(source.getSourceId(), source.getControllerId(), game) + || !controller.choose(outcome, target, source.getSourceId(), game)) { return false; } Card card = game.getCard(target.getFirstTarget()); From 928058a192749faaf240a0cc718a3de6343fa253 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 25 Sep 2019 12:26:32 -0400 Subject: [PATCH 294/373] fixed Run Away Together not resolving --- Mage.Sets/src/mage/cards/r/RunAwayTogether.java | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/Mage.Sets/src/mage/cards/r/RunAwayTogether.java b/Mage.Sets/src/mage/cards/r/RunAwayTogether.java index 258ed0d3c7..03a7ecd3b3 100644 --- a/Mage.Sets/src/mage/cards/r/RunAwayTogether.java +++ b/Mage.Sets/src/mage/cards/r/RunAwayTogether.java @@ -70,8 +70,8 @@ class RunAwayTogetherTarget extends TargetCreaturePermanent { .stream() .map(game::getPermanent) .filter(Objects::nonNull) - .noneMatch(permanent -> creature.getId().equals(permanent.getId()) - || creature.isControlledBy(permanent.getControllerId()) + .noneMatch(permanent -> !creature.getId().equals(permanent.getId()) + && creature.isControlledBy(permanent.getControllerId()) ); } } From 9170df13449223da5bf89e1bb79e216989863b4e Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 25 Sep 2019 17:32:49 -0400 Subject: [PATCH 295/373] fixed cost modifying effects requiring snow mana unnecessarily (fixes #6000) --- Mage/src/main/java/mage/util/CardUtil.java | 16 +++++++++++++++- 1 file changed, 15 insertions(+), 1 deletion(-) diff --git a/Mage/src/main/java/mage/util/CardUtil.java b/Mage/src/main/java/mage/util/CardUtil.java index 851d83c8de..85770a50a3 100644 --- a/Mage/src/main/java/mage/util/CardUtil.java +++ b/Mage/src/main/java/mage/util/CardUtil.java @@ -9,12 +9,14 @@ import mage.abilities.costs.VariableCost; import mage.abilities.costs.mana.*; import mage.cards.Card; import mage.constants.EmptyNames; +import mage.filter.Filter; import mage.game.Game; import mage.game.permanent.Permanent; import mage.game.permanent.token.Token; import mage.util.functions.CopyTokenFunction; import java.text.SimpleDateFormat; +import java.util.Objects; import java.util.UUID; /** @@ -87,6 +89,10 @@ public final class CardUtil { ManaCosts adjustedCost = new ManaCostsImpl<>(); boolean updated = false; for (ManaCost manaCost : manaCosts) { + if (manaCost instanceof SnowManaCost) { + adjustedCost.add(manaCost); + continue; + } Mana mana = manaCost.getOptions().get(0); int colorless = mana != null ? mana.getGeneric() : 0; if (restToReduce != 0 && colorless > 0) { @@ -107,7 +113,15 @@ public final class CardUtil { if (!updated && reduceCount < 0) { adjustedCost.add(new GenericManaCost(-reduceCount)); } - adjustedCost.setSourceFilter(manaCosts.getSourceFilter()); + Filter filter = manaCosts.stream() + .filter(manaCost -> !(manaCost instanceof SnowManaCost)) + .map(ManaCost::getSourceFilter) + .filter(Objects::nonNull) + .findFirst() + .orElse(null); + if (filter != null) { + adjustedCost.setSourceFilter(filter); + } return adjustedCost; } From 626a8b55b83a17ce99fac968469787b6d05a4c6a Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 26 Sep 2019 10:09:41 -0400 Subject: [PATCH 296/373] fixed triggered abilities which trigger off of "one or more creatures" dealing damage not working with double strike --- .../src/mage/cards/j/JaceCunningCastaway.java | 46 +++++++++---------- .../src/mage/cards/k/KeeperOfFables.java | 4 +- .../src/mage/cards/t/ThopterSpyNetwork.java | 24 +++++----- 3 files changed, 35 insertions(+), 39 deletions(-) diff --git a/Mage.Sets/src/mage/cards/j/JaceCunningCastaway.java b/Mage.Sets/src/mage/cards/j/JaceCunningCastaway.java index f4bd134f43..38841f6747 100644 --- a/Mage.Sets/src/mage/cards/j/JaceCunningCastaway.java +++ b/Mage.Sets/src/mage/cards/j/JaceCunningCastaway.java @@ -1,24 +1,17 @@ package mage.cards.j; -import java.util.ArrayList; -import java.util.List; -import java.util.UUID; import mage.abilities.Ability; import mage.abilities.DelayedTriggeredAbility; import mage.abilities.LoyaltyAbility; import mage.abilities.common.PlaneswalkerEntersWithLoyaltyCountersAbility; import mage.abilities.effects.OneShotEffect; +import mage.abilities.effects.common.CreateTokenCopyTargetEffect; import mage.abilities.effects.common.CreateTokenEffect; import mage.abilities.effects.common.DrawDiscardControllerEffect; -import mage.abilities.effects.common.CreateTokenCopyTargetEffect; 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.SuperType; +import mage.constants.*; import mage.game.Game; import mage.game.events.DamagedPlayerEvent; import mage.game.events.GameEvent; @@ -26,8 +19,11 @@ import mage.game.permanent.Permanent; import mage.game.permanent.token.JaceCunningCastawayIllusionToken; import mage.target.targetpointer.FixedTarget; +import java.util.ArrayList; +import java.util.List; +import java.util.UUID; + /** - * * @author TheElk801 */ public final class JaceCunningCastaway extends CardImpl { @@ -50,7 +46,7 @@ public final class JaceCunningCastaway extends CardImpl { this.addAbility(new LoyaltyAbility(new JaceCunningCastawayCopyEffect(), -5)); } - public JaceCunningCastaway(final JaceCunningCastaway card) { + private JaceCunningCastaway(final JaceCunningCastaway card) { super(card); } @@ -62,12 +58,12 @@ public final class JaceCunningCastaway extends CardImpl { class JaceCunningCastawayEffect1 extends OneShotEffect { - public JaceCunningCastawayEffect1() { + JaceCunningCastawayEffect1() { super(Outcome.DrawCard); this.staticText = "Whenever one or more creatures you control deal combat damage to a player this turn, draw a card, then discard a card"; } - public JaceCunningCastawayEffect1(final JaceCunningCastawayEffect1 effect) { + private JaceCunningCastawayEffect1(final JaceCunningCastawayEffect1 effect) { super(effect); } @@ -86,13 +82,13 @@ class JaceCunningCastawayEffect1 extends OneShotEffect { class JaceCunningCastawayDamageTriggeredAbility extends DelayedTriggeredAbility { - List damagedPlayerIds = new ArrayList<>(); + private final List damagedPlayerIds = new ArrayList<>(); - public JaceCunningCastawayDamageTriggeredAbility() { + JaceCunningCastawayDamageTriggeredAbility() { super(new DrawDiscardControllerEffect(1, 1), Duration.EndOfTurn, false); } - public JaceCunningCastawayDamageTriggeredAbility(final JaceCunningCastawayDamageTriggeredAbility ability) { + private JaceCunningCastawayDamageTriggeredAbility(final JaceCunningCastawayDamageTriggeredAbility ability) { super(ability); } @@ -104,7 +100,7 @@ class JaceCunningCastawayDamageTriggeredAbility extends DelayedTriggeredAbility @Override public boolean checkEventType(GameEvent event, Game game) { return event.getType() == GameEvent.EventType.DAMAGED_PLAYER - || event.getType() == GameEvent.EventType.END_COMBAT_STEP_POST; + || event.getType() == GameEvent.EventType.COMBAT_DAMAGE_STEP_POST; } @Override @@ -119,7 +115,7 @@ class JaceCunningCastawayDamageTriggeredAbility extends DelayedTriggeredAbility } } } - if (event.getType() == GameEvent.EventType.END_COMBAT_STEP_POST) { + if (event.getType() == GameEvent.EventType.COMBAT_DAMAGE_STEP_POST) { damagedPlayerIds.clear(); } return false; @@ -138,7 +134,7 @@ class JaceCunningCastawayCopyEffect extends OneShotEffect { this.staticText = "Create two tokens that are copies of {this}, except they're not legendary"; } - JaceCunningCastawayCopyEffect(final JaceCunningCastawayCopyEffect effect) { + private JaceCunningCastawayCopyEffect(final JaceCunningCastawayCopyEffect effect) { super(effect); } @@ -150,12 +146,12 @@ class JaceCunningCastawayCopyEffect extends OneShotEffect { @Override public boolean apply(Game game, Ability source) { Permanent permanent = game.getPermanentOrLKIBattlefield(source.getSourceId()); - if (permanent != null) { - CreateTokenCopyTargetEffect effect = new CreateTokenCopyTargetEffect(source.getControllerId(), null, false, 2); - effect.setTargetPointer(new FixedTarget(source.getSourceId(), game)); - effect.setIsntLegendary(true); - return effect.apply(game, source); + if (permanent == null) { + return false; } - return false; + CreateTokenCopyTargetEffect effect = new CreateTokenCopyTargetEffect(source.getControllerId(), null, false, 2); + effect.setTargetPointer(new FixedTarget(source.getSourceId(), game)); + effect.setIsntLegendary(true); + return effect.apply(game, source); } } diff --git a/Mage.Sets/src/mage/cards/k/KeeperOfFables.java b/Mage.Sets/src/mage/cards/k/KeeperOfFables.java index ff9db9fd6e..e5e07bdb11 100644 --- a/Mage.Sets/src/mage/cards/k/KeeperOfFables.java +++ b/Mage.Sets/src/mage/cards/k/KeeperOfFables.java @@ -63,7 +63,7 @@ class KeeperOfFablesTriggeredAbility extends TriggeredAbilityImpl { @Override public boolean checkEventType(GameEvent event, Game game) { return event.getType() == GameEvent.EventType.DAMAGED_PLAYER - || event.getType() == GameEvent.EventType.END_COMBAT_STEP_POST; + || event.getType() == GameEvent.EventType.COMBAT_DAMAGE_STEP_POST; } @Override @@ -80,7 +80,7 @@ class KeeperOfFablesTriggeredAbility extends TriggeredAbilityImpl { } } } - if (event.getType() == GameEvent.EventType.END_COMBAT_STEP_POST) { + if (event.getType() == GameEvent.EventType.COMBAT_DAMAGE_STEP_POST) { damagedPlayerIds.clear(); } return false; diff --git a/Mage.Sets/src/mage/cards/t/ThopterSpyNetwork.java b/Mage.Sets/src/mage/cards/t/ThopterSpyNetwork.java index 8514dc9255..bd4b10cef6 100644 --- a/Mage.Sets/src/mage/cards/t/ThopterSpyNetwork.java +++ b/Mage.Sets/src/mage/cards/t/ThopterSpyNetwork.java @@ -1,9 +1,6 @@ package mage.cards.t; -import java.util.ArrayList; -import java.util.List; -import java.util.UUID; import mage.abilities.TriggeredAbilityImpl; import mage.abilities.effects.common.CreateTokenEffect; import mage.abilities.effects.common.DrawCardSourceControllerEffect; @@ -18,8 +15,11 @@ import mage.game.events.GameEvent; import mage.game.permanent.Permanent; import mage.game.permanent.token.ThopterColorlessToken; +import java.util.ArrayList; +import java.util.List; +import java.util.UUID; + /** - * * @author fireshoes */ public final class ThopterSpyNetwork extends CardImpl { @@ -34,7 +34,7 @@ public final class ThopterSpyNetwork extends CardImpl { this.addAbility(new ThopterSpyNetworkDamageTriggeredAbility()); } - public ThopterSpyNetwork(final ThopterSpyNetwork card) { + private ThopterSpyNetwork(final ThopterSpyNetwork card) { super(card); } @@ -46,11 +46,11 @@ public final class ThopterSpyNetwork extends CardImpl { class ThopterSpyNetworkUpkeepTriggeredAbility extends TriggeredAbilityImpl { - public ThopterSpyNetworkUpkeepTriggeredAbility() { + ThopterSpyNetworkUpkeepTriggeredAbility() { super(Zone.BATTLEFIELD, new CreateTokenEffect(new ThopterColorlessToken(), 1), false); } - public ThopterSpyNetworkUpkeepTriggeredAbility(final ThopterSpyNetworkUpkeepTriggeredAbility ability) { + private ThopterSpyNetworkUpkeepTriggeredAbility(final ThopterSpyNetworkUpkeepTriggeredAbility ability) { super(ability); } @@ -82,13 +82,13 @@ class ThopterSpyNetworkUpkeepTriggeredAbility extends TriggeredAbilityImpl { class ThopterSpyNetworkDamageTriggeredAbility extends TriggeredAbilityImpl { - List damagedPlayerIds = new ArrayList<>(); + private final List damagedPlayerIds = new ArrayList<>(); - public ThopterSpyNetworkDamageTriggeredAbility() { + ThopterSpyNetworkDamageTriggeredAbility() { super(Zone.BATTLEFIELD, new DrawCardSourceControllerEffect(1), false); } - public ThopterSpyNetworkDamageTriggeredAbility(final ThopterSpyNetworkDamageTriggeredAbility ability) { + private ThopterSpyNetworkDamageTriggeredAbility(final ThopterSpyNetworkDamageTriggeredAbility ability) { super(ability); } @@ -100,7 +100,7 @@ class ThopterSpyNetworkDamageTriggeredAbility extends TriggeredAbilityImpl { @Override public boolean checkEventType(GameEvent event, Game game) { return event.getType() == GameEvent.EventType.DAMAGED_PLAYER - || event.getType() == GameEvent.EventType.END_COMBAT_STEP_POST; + || event.getType() == GameEvent.EventType.COMBAT_DAMAGE_STEP_POST; } @Override @@ -115,7 +115,7 @@ class ThopterSpyNetworkDamageTriggeredAbility extends TriggeredAbilityImpl { } } } - if (event.getType() == GameEvent.EventType.END_COMBAT_STEP_POST) { + if (event.getType() == GameEvent.EventType.COMBAT_DAMAGE_STEP_POST) { damagedPlayerIds.clear(); } return false; From f719503a890f1c502f8b34a4e98885deb9117418 Mon Sep 17 00:00:00 2001 From: Oleg Agafonov Date: Fri, 27 Sep 2019 21:19:03 +0400 Subject: [PATCH 297/373] Prepare new release --- Mage.Client/pom.xml | 2 +- Mage.Common/pom.xml | 2 +- Mage.Common/src/main/java/mage/utils/MageVersion.java | 2 +- Mage.Plugins/Mage.Counter.Plugin/pom.xml | 2 +- Mage.Plugins/pom.xml | 2 +- Mage.Server.Console/pom.xml | 2 +- Mage.Server.Plugins/Mage.Deck.Constructed/pom.xml | 2 +- Mage.Server.Plugins/Mage.Deck.Limited/pom.xml | 2 +- Mage.Server.Plugins/Mage.Game.BrawlDuel/pom.xml | 2 +- Mage.Server.Plugins/Mage.Game.BrawlFreeForAll/pom.xml | 2 +- Mage.Server.Plugins/Mage.Game.CanadianHighlanderDuel/pom.xml | 2 +- Mage.Server.Plugins/Mage.Game.CommanderDuel/pom.xml | 2 +- Mage.Server.Plugins/Mage.Game.CommanderFreeForAll/pom.xml | 2 +- Mage.Server.Plugins/Mage.Game.FreeForAll/pom.xml | 2 +- Mage.Server.Plugins/Mage.Game.FreeformCommanderDuel/pom.xml | 2 +- .../Mage.Game.FreeformCommanderFreeForAll/pom.xml | 2 +- Mage.Server.Plugins/Mage.Game.MomirDuel/pom.xml | 2 +- Mage.Server.Plugins/Mage.Game.MomirGame/pom.xml | 2 +- Mage.Server.Plugins/Mage.Game.OathbreakerDuel/pom.xml | 4 ++-- Mage.Server.Plugins/Mage.Game.OathbreakerFreeForAll/pom.xml | 2 +- .../Mage.Game.PennyDreadfulCommanderFreeForAll/pom.xml | 2 +- Mage.Server.Plugins/Mage.Game.TinyLeadersDuel/pom.xml | 2 +- Mage.Server.Plugins/Mage.Game.TwoPlayerDuel/pom.xml | 2 +- Mage.Server.Plugins/Mage.Player.AI.DraftBot/pom.xml | 2 +- Mage.Server.Plugins/Mage.Player.AI.MA/pom.xml | 2 +- Mage.Server.Plugins/Mage.Player.AI/pom.xml | 2 +- Mage.Server.Plugins/Mage.Player.AIMCTS/pom.xml | 2 +- Mage.Server.Plugins/Mage.Player.AIMinimax/pom.xml | 2 +- Mage.Server.Plugins/Mage.Player.Human/pom.xml | 2 +- Mage.Server.Plugins/Mage.Tournament.BoosterDraft/pom.xml | 2 +- Mage.Server.Plugins/Mage.Tournament.Constructed/pom.xml | 2 +- Mage.Server.Plugins/Mage.Tournament.Sealed/pom.xml | 2 +- Mage.Server.Plugins/pom.xml | 2 +- Mage.Server/pom.xml | 2 +- Mage.Sets/pom.xml | 2 +- Mage.Tests/pom.xml | 2 +- Mage.Verify/pom.xml | 4 ++-- Mage/pom.xml | 2 +- pom.xml | 4 ++-- 39 files changed, 42 insertions(+), 42 deletions(-) diff --git a/Mage.Client/pom.xml b/Mage.Client/pom.xml index 399d2d8a35..78fb0b9f4c 100644 --- a/Mage.Client/pom.xml +++ b/Mage.Client/pom.xml @@ -6,7 +6,7 @@ org.mage mage-root - 1.4.38 + 1.4.39 mage-client diff --git a/Mage.Common/pom.xml b/Mage.Common/pom.xml index c70174e465..2aa92f8cbe 100644 --- a/Mage.Common/pom.xml +++ b/Mage.Common/pom.xml @@ -7,7 +7,7 @@ org.mage mage-root - 1.4.38 + 1.4.39 mage-common diff --git a/Mage.Common/src/main/java/mage/utils/MageVersion.java b/Mage.Common/src/main/java/mage/utils/MageVersion.java index ae105f28dc..1a2ed5a8a8 100644 --- a/Mage.Common/src/main/java/mage/utils/MageVersion.java +++ b/Mage.Common/src/main/java/mage/utils/MageVersion.java @@ -11,7 +11,7 @@ public class MageVersion implements Serializable, Comparable { public static final int MAGE_VERSION_MAJOR = 1; public static final int MAGE_VERSION_MINOR = 4; - public static final int MAGE_VERSION_PATCH = 38; + public static final int MAGE_VERSION_PATCH = 39; public static final String MAGE_EDITION_INFO = ""; // set "-beta" for 1.4.32-betaV0 public static final String MAGE_VERSION_MINOR_PATCH = "V0"; // default // strict mode diff --git a/Mage.Plugins/Mage.Counter.Plugin/pom.xml b/Mage.Plugins/Mage.Counter.Plugin/pom.xml index 5c784e951a..eb0d6042d5 100644 --- a/Mage.Plugins/Mage.Counter.Plugin/pom.xml +++ b/Mage.Plugins/Mage.Counter.Plugin/pom.xml @@ -7,7 +7,7 @@ org.mage mage-plugins - 1.4.38 + 1.4.39 mage-counter-plugin diff --git a/Mage.Plugins/pom.xml b/Mage.Plugins/pom.xml index 3758ccc807..f670b9ff44 100644 --- a/Mage.Plugins/pom.xml +++ b/Mage.Plugins/pom.xml @@ -7,7 +7,7 @@ org.mage mage-root - 1.4.38 + 1.4.39 mage-plugins diff --git a/Mage.Server.Console/pom.xml b/Mage.Server.Console/pom.xml index cdb5f300a8..95edc3ef3e 100644 --- a/Mage.Server.Console/pom.xml +++ b/Mage.Server.Console/pom.xml @@ -6,7 +6,7 @@ org.mage mage-root - 1.4.38 + 1.4.39 mage.server.console diff --git a/Mage.Server.Plugins/Mage.Deck.Constructed/pom.xml b/Mage.Server.Plugins/Mage.Deck.Constructed/pom.xml index 3ac439742f..76ddbeb0c6 100644 --- a/Mage.Server.Plugins/Mage.Deck.Constructed/pom.xml +++ b/Mage.Server.Plugins/Mage.Deck.Constructed/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.38 + 1.4.39 mage-deck-constructed diff --git a/Mage.Server.Plugins/Mage.Deck.Limited/pom.xml b/Mage.Server.Plugins/Mage.Deck.Limited/pom.xml index 13841539ed..012723d4e4 100644 --- a/Mage.Server.Plugins/Mage.Deck.Limited/pom.xml +++ b/Mage.Server.Plugins/Mage.Deck.Limited/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.38 + 1.4.39 mage-deck-limited diff --git a/Mage.Server.Plugins/Mage.Game.BrawlDuel/pom.xml b/Mage.Server.Plugins/Mage.Game.BrawlDuel/pom.xml index 76b6ad42a3..c439d1bfb7 100644 --- a/Mage.Server.Plugins/Mage.Game.BrawlDuel/pom.xml +++ b/Mage.Server.Plugins/Mage.Game.BrawlDuel/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.38 + 1.4.39 mage-game-brawlduel diff --git a/Mage.Server.Plugins/Mage.Game.BrawlFreeForAll/pom.xml b/Mage.Server.Plugins/Mage.Game.BrawlFreeForAll/pom.xml index 738d8a5ff5..d1890b2c63 100644 --- a/Mage.Server.Plugins/Mage.Game.BrawlFreeForAll/pom.xml +++ b/Mage.Server.Plugins/Mage.Game.BrawlFreeForAll/pom.xml @@ -6,7 +6,7 @@ org.mage mage-server-plugins - 1.4.38 + 1.4.39 mage-game-brawlfreeforall diff --git a/Mage.Server.Plugins/Mage.Game.CanadianHighlanderDuel/pom.xml b/Mage.Server.Plugins/Mage.Game.CanadianHighlanderDuel/pom.xml index a3111d63f6..91de1f20e5 100644 --- a/Mage.Server.Plugins/Mage.Game.CanadianHighlanderDuel/pom.xml +++ b/Mage.Server.Plugins/Mage.Game.CanadianHighlanderDuel/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.38 + 1.4.39 mage-game-canadianhighlanderduel diff --git a/Mage.Server.Plugins/Mage.Game.CommanderDuel/pom.xml b/Mage.Server.Plugins/Mage.Game.CommanderDuel/pom.xml index 51bf17613c..efca633d52 100644 --- a/Mage.Server.Plugins/Mage.Game.CommanderDuel/pom.xml +++ b/Mage.Server.Plugins/Mage.Game.CommanderDuel/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.38 + 1.4.39 mage-game-commanderduel diff --git a/Mage.Server.Plugins/Mage.Game.CommanderFreeForAll/pom.xml b/Mage.Server.Plugins/Mage.Game.CommanderFreeForAll/pom.xml index 3bce053074..c346e6d407 100644 --- a/Mage.Server.Plugins/Mage.Game.CommanderFreeForAll/pom.xml +++ b/Mage.Server.Plugins/Mage.Game.CommanderFreeForAll/pom.xml @@ -6,7 +6,7 @@ org.mage mage-server-plugins - 1.4.38 + 1.4.39 mage-game-commanderfreeforall diff --git a/Mage.Server.Plugins/Mage.Game.FreeForAll/pom.xml b/Mage.Server.Plugins/Mage.Game.FreeForAll/pom.xml index 8627c42417..35beea22a9 100644 --- a/Mage.Server.Plugins/Mage.Game.FreeForAll/pom.xml +++ b/Mage.Server.Plugins/Mage.Game.FreeForAll/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.38 + 1.4.39 mage-game-freeforall diff --git a/Mage.Server.Plugins/Mage.Game.FreeformCommanderDuel/pom.xml b/Mage.Server.Plugins/Mage.Game.FreeformCommanderDuel/pom.xml index c5ba60eb28..aa5f263b55 100644 --- a/Mage.Server.Plugins/Mage.Game.FreeformCommanderDuel/pom.xml +++ b/Mage.Server.Plugins/Mage.Game.FreeformCommanderDuel/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.38 + 1.4.39 mage-game-freeformcommanderduel diff --git a/Mage.Server.Plugins/Mage.Game.FreeformCommanderFreeForAll/pom.xml b/Mage.Server.Plugins/Mage.Game.FreeformCommanderFreeForAll/pom.xml index 0d4a4abedf..ca94da6302 100644 --- a/Mage.Server.Plugins/Mage.Game.FreeformCommanderFreeForAll/pom.xml +++ b/Mage.Server.Plugins/Mage.Game.FreeformCommanderFreeForAll/pom.xml @@ -6,7 +6,7 @@ org.mage mage-server-plugins - 1.4.38 + 1.4.39 mage-game-freeformcommanderfreeforall diff --git a/Mage.Server.Plugins/Mage.Game.MomirDuel/pom.xml b/Mage.Server.Plugins/Mage.Game.MomirDuel/pom.xml index b1587dc6f5..722608ea31 100644 --- a/Mage.Server.Plugins/Mage.Game.MomirDuel/pom.xml +++ b/Mage.Server.Plugins/Mage.Game.MomirDuel/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.38 + 1.4.39 mage-game-momirduel diff --git a/Mage.Server.Plugins/Mage.Game.MomirGame/pom.xml b/Mage.Server.Plugins/Mage.Game.MomirGame/pom.xml index 138e2c121b..be6053a9f6 100644 --- a/Mage.Server.Plugins/Mage.Game.MomirGame/pom.xml +++ b/Mage.Server.Plugins/Mage.Game.MomirGame/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.38 + 1.4.39 mage-game-momirfreeforall diff --git a/Mage.Server.Plugins/Mage.Game.OathbreakerDuel/pom.xml b/Mage.Server.Plugins/Mage.Game.OathbreakerDuel/pom.xml index f58c13f4ff..aecfbc697e 100644 --- a/Mage.Server.Plugins/Mage.Game.OathbreakerDuel/pom.xml +++ b/Mage.Server.Plugins/Mage.Game.OathbreakerDuel/pom.xml @@ -6,7 +6,7 @@ org.mage mage-server-plugins - 1.4.38 + 1.4.39 mage-game-oathbreakerduel @@ -22,7 +22,7 @@ org.mage mage-game-oathbreakerfreeforall - 1.4.38 + 1.4.39 compile diff --git a/Mage.Server.Plugins/Mage.Game.OathbreakerFreeForAll/pom.xml b/Mage.Server.Plugins/Mage.Game.OathbreakerFreeForAll/pom.xml index f3bc0fc572..4df90b35dd 100644 --- a/Mage.Server.Plugins/Mage.Game.OathbreakerFreeForAll/pom.xml +++ b/Mage.Server.Plugins/Mage.Game.OathbreakerFreeForAll/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.38 + 1.4.39 mage-game-oathbreakerfreeforall diff --git a/Mage.Server.Plugins/Mage.Game.PennyDreadfulCommanderFreeForAll/pom.xml b/Mage.Server.Plugins/Mage.Game.PennyDreadfulCommanderFreeForAll/pom.xml index 4d81776e12..2128a509e3 100644 --- a/Mage.Server.Plugins/Mage.Game.PennyDreadfulCommanderFreeForAll/pom.xml +++ b/Mage.Server.Plugins/Mage.Game.PennyDreadfulCommanderFreeForAll/pom.xml @@ -6,7 +6,7 @@ org.mage mage-server-plugins - 1.4.38 + 1.4.39 mage-game-pennydreadfulcommanderfreeforall diff --git a/Mage.Server.Plugins/Mage.Game.TinyLeadersDuel/pom.xml b/Mage.Server.Plugins/Mage.Game.TinyLeadersDuel/pom.xml index befe91a990..890ce33b47 100644 --- a/Mage.Server.Plugins/Mage.Game.TinyLeadersDuel/pom.xml +++ b/Mage.Server.Plugins/Mage.Game.TinyLeadersDuel/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.38 + 1.4.39 mage-game-tinyleadersduel diff --git a/Mage.Server.Plugins/Mage.Game.TwoPlayerDuel/pom.xml b/Mage.Server.Plugins/Mage.Game.TwoPlayerDuel/pom.xml index ceb330bd4e..2d2a71777d 100644 --- a/Mage.Server.Plugins/Mage.Game.TwoPlayerDuel/pom.xml +++ b/Mage.Server.Plugins/Mage.Game.TwoPlayerDuel/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.38 + 1.4.39 mage-game-twoplayerduel diff --git a/Mage.Server.Plugins/Mage.Player.AI.DraftBot/pom.xml b/Mage.Server.Plugins/Mage.Player.AI.DraftBot/pom.xml index ad088fb549..4a3cb786af 100644 --- a/Mage.Server.Plugins/Mage.Player.AI.DraftBot/pom.xml +++ b/Mage.Server.Plugins/Mage.Player.AI.DraftBot/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.38 + 1.4.39 mage-player-ai-draftbot diff --git a/Mage.Server.Plugins/Mage.Player.AI.MA/pom.xml b/Mage.Server.Plugins/Mage.Player.AI.MA/pom.xml index fa4ad1a121..28e3a25276 100644 --- a/Mage.Server.Plugins/Mage.Player.AI.MA/pom.xml +++ b/Mage.Server.Plugins/Mage.Player.AI.MA/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.38 + 1.4.39 mage-player-ai-ma diff --git a/Mage.Server.Plugins/Mage.Player.AI/pom.xml b/Mage.Server.Plugins/Mage.Player.AI/pom.xml index 71d893bcd2..cb99882986 100644 --- a/Mage.Server.Plugins/Mage.Player.AI/pom.xml +++ b/Mage.Server.Plugins/Mage.Player.AI/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.38 + 1.4.39 mage-player-ai diff --git a/Mage.Server.Plugins/Mage.Player.AIMCTS/pom.xml b/Mage.Server.Plugins/Mage.Player.AIMCTS/pom.xml index 0a2eb8b997..b34b687f76 100644 --- a/Mage.Server.Plugins/Mage.Player.AIMCTS/pom.xml +++ b/Mage.Server.Plugins/Mage.Player.AIMCTS/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.38 + 1.4.39 mage-player-ai-mcts diff --git a/Mage.Server.Plugins/Mage.Player.AIMinimax/pom.xml b/Mage.Server.Plugins/Mage.Player.AIMinimax/pom.xml index 87acc59bb0..5373478dc2 100644 --- a/Mage.Server.Plugins/Mage.Player.AIMinimax/pom.xml +++ b/Mage.Server.Plugins/Mage.Player.AIMinimax/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.38 + 1.4.39 mage-player-aiminimax diff --git a/Mage.Server.Plugins/Mage.Player.Human/pom.xml b/Mage.Server.Plugins/Mage.Player.Human/pom.xml index f62a0362c5..e19fa52fda 100644 --- a/Mage.Server.Plugins/Mage.Player.Human/pom.xml +++ b/Mage.Server.Plugins/Mage.Player.Human/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.38 + 1.4.39 mage-player-human diff --git a/Mage.Server.Plugins/Mage.Tournament.BoosterDraft/pom.xml b/Mage.Server.Plugins/Mage.Tournament.BoosterDraft/pom.xml index e10e6f3804..ddc1ef1fea 100644 --- a/Mage.Server.Plugins/Mage.Tournament.BoosterDraft/pom.xml +++ b/Mage.Server.Plugins/Mage.Tournament.BoosterDraft/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.38 + 1.4.39 mage-tournament-boosterdraft diff --git a/Mage.Server.Plugins/Mage.Tournament.Constructed/pom.xml b/Mage.Server.Plugins/Mage.Tournament.Constructed/pom.xml index bc41290a61..df95dc6a2d 100644 --- a/Mage.Server.Plugins/Mage.Tournament.Constructed/pom.xml +++ b/Mage.Server.Plugins/Mage.Tournament.Constructed/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.38 + 1.4.39 mage-tournament-constructed diff --git a/Mage.Server.Plugins/Mage.Tournament.Sealed/pom.xml b/Mage.Server.Plugins/Mage.Tournament.Sealed/pom.xml index 44cb2749a2..39ea1f9fe3 100644 --- a/Mage.Server.Plugins/Mage.Tournament.Sealed/pom.xml +++ b/Mage.Server.Plugins/Mage.Tournament.Sealed/pom.xml @@ -7,7 +7,7 @@ org.mage mage-server-plugins - 1.4.38 + 1.4.39 mage-tournament-sealed diff --git a/Mage.Server.Plugins/pom.xml b/Mage.Server.Plugins/pom.xml index ecc291cabc..e20f356938 100644 --- a/Mage.Server.Plugins/pom.xml +++ b/Mage.Server.Plugins/pom.xml @@ -7,7 +7,7 @@ org.mage mage-root - 1.4.38 + 1.4.39 mage-server-plugins diff --git a/Mage.Server/pom.xml b/Mage.Server/pom.xml index 7400d723f3..49a6a79a2b 100644 --- a/Mage.Server/pom.xml +++ b/Mage.Server/pom.xml @@ -6,7 +6,7 @@ org.mage mage-root - 1.4.38 + 1.4.39 mage-server diff --git a/Mage.Sets/pom.xml b/Mage.Sets/pom.xml index 1274851f79..a91e4de445 100644 --- a/Mage.Sets/pom.xml +++ b/Mage.Sets/pom.xml @@ -7,7 +7,7 @@ org.mage mage-root - 1.4.38 + 1.4.39 mage-sets diff --git a/Mage.Tests/pom.xml b/Mage.Tests/pom.xml index 6939dccfec..e64596f21c 100644 --- a/Mage.Tests/pom.xml +++ b/Mage.Tests/pom.xml @@ -6,7 +6,7 @@ org.mage mage-root - 1.4.38 + 1.4.39 mage-tests diff --git a/Mage.Verify/pom.xml b/Mage.Verify/pom.xml index 59ac81ced7..e19bf29e08 100644 --- a/Mage.Verify/pom.xml +++ b/Mage.Verify/pom.xml @@ -6,7 +6,7 @@ org.mage mage-root - 1.4.38 + 1.4.39 mage-verify @@ -49,7 +49,7 @@ org.mage mage-client - 1.4.38 + 1.4.39 diff --git a/Mage/pom.xml b/Mage/pom.xml index 494a5a3a18..32afbc41b0 100644 --- a/Mage/pom.xml +++ b/Mage/pom.xml @@ -6,7 +6,7 @@ org.mage mage-root - 1.4.38 + 1.4.39 mage diff --git a/pom.xml b/pom.xml index a7b6eb9414..ee8de698c6 100644 --- a/pom.xml +++ b/pom.xml @@ -6,7 +6,7 @@ org.mage mage-root - 1.4.38 + 1.4.39 pom Mage Root Mage Root POM @@ -86,7 +86,7 @@ - 1.4.38 + 1.4.39 UTF-8 yyyy-MM-dd'T'HH:mm:ss'Z' From 3877d2267ae147964b681cfb0e7c564b5dfb6976 Mon Sep 17 00:00:00 2001 From: Oleg Agafonov Date: Fri, 27 Sep 2019 22:11:30 +0400 Subject: [PATCH 298/373] AI: fix wrong cards outcome in choose dialogs; --- Mage.Sets/src/mage/cards/b/BloodForBones.java | 2 +- Mage.Sets/src/mage/cards/c/CavalierOfFlame.java | 2 +- Mage.Sets/src/mage/cards/c/CouncilGuardian.java | 15 +++++++-------- .../src/mage/cards/d/DefensiveManeuvers.java | 7 +++---- Mage.Sets/src/mage/cards/d/DoomForetold.java | 5 +++-- Mage.Sets/src/mage/cards/e/Extinction.java | 7 +++---- .../src/mage/cards/s/SeasonedPyromancer.java | 2 +- Mage.Sets/src/mage/cards/v/ViviensArkbow.java | 2 +- 8 files changed, 20 insertions(+), 22 deletions(-) diff --git a/Mage.Sets/src/mage/cards/b/BloodForBones.java b/Mage.Sets/src/mage/cards/b/BloodForBones.java index e04e4a2717..c0c4ea3716 100644 --- a/Mage.Sets/src/mage/cards/b/BloodForBones.java +++ b/Mage.Sets/src/mage/cards/b/BloodForBones.java @@ -56,7 +56,7 @@ class BloodForBonesEffect extends OneShotEffect { = new FilterCreatureCard("creature card in your graveyard (to put into your hand"); BloodForBonesEffect() { - super(Outcome.Benefit); + super(Outcome.PutCardInPlay); staticText = "Return a creature card from your graveyard to the battlefield, " + "then return another creature card from your graveyard to your hand."; } diff --git a/Mage.Sets/src/mage/cards/c/CavalierOfFlame.java b/Mage.Sets/src/mage/cards/c/CavalierOfFlame.java index d39443a884..6021ff0504 100644 --- a/Mage.Sets/src/mage/cards/c/CavalierOfFlame.java +++ b/Mage.Sets/src/mage/cards/c/CavalierOfFlame.java @@ -103,7 +103,7 @@ class CavalierOfFlameEffect extends OneShotEffect { return false; } TargetCardInHand target = new TargetCardInHand(0, player.getHand().size(), StaticFilters.FILTER_CARD); - if (player.choose(outcome, player.getHand(), target, game)) { + if (player.choose(Outcome.Discard, player.getHand(), target, game)) { int counter = target .getTargets() .stream() diff --git a/Mage.Sets/src/mage/cards/c/CouncilGuardian.java b/Mage.Sets/src/mage/cards/c/CouncilGuardian.java index 0931fdd466..631f174e09 100644 --- a/Mage.Sets/src/mage/cards/c/CouncilGuardian.java +++ b/Mage.Sets/src/mage/cards/c/CouncilGuardian.java @@ -1,9 +1,5 @@ - package mage.cards.c; -import java.util.HashMap; -import java.util.Map; -import java.util.UUID; import mage.MageInt; import mage.ObjectColor; import mage.abilities.Ability; @@ -15,14 +11,17 @@ import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.choices.ChoiceColor; import mage.constants.CardType; -import mage.constants.SubType; import mage.constants.Duration; import mage.constants.Outcome; +import mage.constants.SubType; import mage.game.Game; import mage.players.Player; +import java.util.HashMap; +import java.util.Map; +import java.util.UUID; + /** - * * @author Styxo */ public final class CouncilGuardian extends CardImpl { @@ -53,7 +52,7 @@ public final class CouncilGuardian extends CardImpl { class CouncilsGuardianEffect extends OneShotEffect { public CouncilsGuardianEffect() { - super(Outcome.Exile); + super(Outcome.Benefit); this.staticText = "starting with you, each player votes for blue, black, red, or green. {this} gains protection from each color with the most votes or tied for most votes"; } @@ -78,7 +77,7 @@ class CouncilsGuardianEffect extends OneShotEffect { Player player = game.getPlayer(playerId); if (player != null) { choice.clearChoice(); - if (player.choose(outcome, choice, game)) { + if (player.choose(Outcome.Detriment, choice, game)) { ObjectColor color = choice.getColor(); if (color != null) { if (chosenColors.containsKey(color)) { diff --git a/Mage.Sets/src/mage/cards/d/DefensiveManeuvers.java b/Mage.Sets/src/mage/cards/d/DefensiveManeuvers.java index afdce81b29..755fe98290 100644 --- a/Mage.Sets/src/mage/cards/d/DefensiveManeuvers.java +++ b/Mage.Sets/src/mage/cards/d/DefensiveManeuvers.java @@ -1,7 +1,5 @@ - package mage.cards.d; -import java.util.UUID; import mage.MageObject; import mage.abilities.Ability; import mage.abilities.effects.OneShotEffect; @@ -19,8 +17,9 @@ import mage.filter.predicate.mageobject.SubtypePredicate; import mage.game.Game; import mage.players.Player; +import java.util.UUID; + /** - * * @author TheElk801 */ public final class DefensiveManeuvers extends CardImpl { @@ -45,7 +44,7 @@ public final class DefensiveManeuvers extends CardImpl { class DefensiveManeuversEffect extends OneShotEffect { DefensiveManeuversEffect() { - super(Outcome.Benefit); + super(Outcome.BoostCreature); this.staticText = "Creatures of the creature type of your choice get +0/+4 until end of turn."; } diff --git a/Mage.Sets/src/mage/cards/d/DoomForetold.java b/Mage.Sets/src/mage/cards/d/DoomForetold.java index b472cde979..2a997df0c6 100644 --- a/Mage.Sets/src/mage/cards/d/DoomForetold.java +++ b/Mage.Sets/src/mage/cards/d/DoomForetold.java @@ -87,7 +87,7 @@ class DoomForetoldEffect extends OneShotEffect { if (game.getBattlefield().contains(filter2, 1, game)) { TargetPermanent target = new TargetPermanent(filter2); target.setNotTarget(true); - if (player.choose(outcome, target, source.getSourceId(), game)) { + if (player.choose(Outcome.Sacrifice, target, source.getSourceId(), game)) { Permanent permanent = game.getPermanent(target.getFirstTarget()); if (permanent != null && permanent.sacrifice(source.getSourceId(), game)) { return true; @@ -99,6 +99,7 @@ class DoomForetoldEffect extends OneShotEffect { controller.drawCards(1, game); controller.gainLife(2, game, source); effect1.apply(game, source); - return effect2.apply(game, source); + effect2.apply(game, source); + return true; } } \ No newline at end of file diff --git a/Mage.Sets/src/mage/cards/e/Extinction.java b/Mage.Sets/src/mage/cards/e/Extinction.java index e77c192cb2..27e3bc3be3 100644 --- a/Mage.Sets/src/mage/cards/e/Extinction.java +++ b/Mage.Sets/src/mage/cards/e/Extinction.java @@ -1,7 +1,5 @@ - package mage.cards.e; -import java.util.UUID; import mage.MageObject; import mage.abilities.Ability; import mage.abilities.effects.OneShotEffect; @@ -18,8 +16,9 @@ import mage.game.Game; import mage.game.permanent.Permanent; import mage.players.Player; +import java.util.UUID; + /** - * * @author fireshoes */ public final class Extinction extends CardImpl { @@ -44,7 +43,7 @@ public final class Extinction extends CardImpl { class ExtinctionEffect extends OneShotEffect { public ExtinctionEffect() { - super(Outcome.UnboostCreature); + super(Outcome.DestroyPermanent); staticText = "Destroy all creatures of the creature type of your choice"; } diff --git a/Mage.Sets/src/mage/cards/s/SeasonedPyromancer.java b/Mage.Sets/src/mage/cards/s/SeasonedPyromancer.java index 64859e6951..f30bcf4b83 100644 --- a/Mage.Sets/src/mage/cards/s/SeasonedPyromancer.java +++ b/Mage.Sets/src/mage/cards/s/SeasonedPyromancer.java @@ -86,7 +86,7 @@ class SeasonedPyromancerEffect extends OneShotEffect { int toDiscard = Math.min(player.getHand().size(), 2); if (toDiscard > 0) { TargetCard target = new TargetCardInHand(toDiscard, StaticFilters.FILTER_CARD); - if (player.choose(outcome, player.getHand(), target, game)) { + if (player.choose(Outcome.Discard, player.getHand(), target, game)) { Cards cards = new CardsImpl(target.getTargets()); for (Card card : cards.getCards(game)) { if (player.discard(card, source, game) && !card.isLand()) { diff --git a/Mage.Sets/src/mage/cards/v/ViviensArkbow.java b/Mage.Sets/src/mage/cards/v/ViviensArkbow.java index 0db7847a76..82b5814347 100644 --- a/Mage.Sets/src/mage/cards/v/ViviensArkbow.java +++ b/Mage.Sets/src/mage/cards/v/ViviensArkbow.java @@ -50,7 +50,7 @@ public final class ViviensArkbow extends CardImpl { class ViviensArkbowEffect extends OneShotEffect { ViviensArkbowEffect() { - super(Outcome.Benefit); + super(Outcome.PutCardInPlay); staticText = "Look at the top X cards of your library. " + "You may put a creature card with converted mana cost X or less " + "from among them onto the battlefield. Put the rest on the bottom of your library in a random order."; From a74fb36053fc585cf81a39778c89d59f62fc69c5 Mon Sep 17 00:00:00 2001 From: Oleg Agafonov Date: Fri, 27 Sep 2019 22:32:44 +0400 Subject: [PATCH 299/373] * UI: fixed error in card viewer while viewing pages with tokens; --- .../mage/client/deckeditor/collection/viewer/MageBook.java | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/Mage.Client/src/main/java/mage/client/deckeditor/collection/viewer/MageBook.java b/Mage.Client/src/main/java/mage/client/deckeditor/collection/viewer/MageBook.java index ae4d2db50c..7ef72f3440 100644 --- a/Mage.Client/src/main/java/mage/client/deckeditor/collection/viewer/MageBook.java +++ b/Mage.Client/src/main/java/mage/client/deckeditor/collection/viewer/MageBook.java @@ -695,13 +695,13 @@ public class MageBook extends JComponent { int totalTokensEmblems = totalTokens + getTotalNumEmblems(set); int start = 0; if (!(page * conf.CARDS_PER_PAGE <= totalTokensEmblems && (page + 1) * conf.CARDS_PER_PAGE >= totalTokensEmblems)) { - start = page * conf.CARDS_PER_PAGE - totalTokensEmblems; + start = Math.max(0, page * conf.CARDS_PER_PAGE - totalTokensEmblems); pageRight.setVisible(true); } int end = planes.size(); if ((page + 1) * conf.CARDS_PER_PAGE < totalTokensEmblems + planes.size()) { - end = (page + 1) * conf.CARDS_PER_PAGE - totalTokensEmblems; + end = Math.max(0, (page + 1) * conf.CARDS_PER_PAGE - totalTokensEmblems); pageRight.setVisible(true); } else { pageRight.setVisible(false); From 2227490413d7831ebfd855c3b4332c5b6e70944b Mon Sep 17 00:00:00 2001 From: Oleg Agafonov Date: Fri, 27 Sep 2019 22:49:17 +0400 Subject: [PATCH 300/373] Food token - fixed that it doesn't use multiple images; --- .../mage/game/permanent/token/FoodToken.java | 19 ++++++++++--------- 1 file changed, 10 insertions(+), 9 deletions(-) diff --git a/Mage/src/main/java/mage/game/permanent/token/FoodToken.java b/Mage/src/main/java/mage/game/permanent/token/FoodToken.java index 0107d5e614..9cc5e12305 100644 --- a/Mage/src/main/java/mage/game/permanent/token/FoodToken.java +++ b/Mage/src/main/java/mage/game/permanent/token/FoodToken.java @@ -9,6 +9,7 @@ import mage.abilities.effects.common.GainLifeEffect; import mage.constants.CardType; import mage.constants.SubType; import mage.constants.Zone; +import mage.util.RandomUtil; import java.util.ArrayList; import java.util.Arrays; @@ -27,17 +28,8 @@ public final class FoodToken extends TokenImpl { } public FoodToken() { - this(null, 0); - } - - public FoodToken(String setCode) { - this(setCode, 0); - } - - public FoodToken(String setCode, int tokenType) { super("Food", "Food token"); availableImageSetCodes = tokenImageSets; - setOriginalExpansionSetCode(setCode); cardType.add(CardType.ARTIFACT); subtype.add(SubType.FOOD); @@ -50,6 +42,15 @@ public final class FoodToken extends TokenImpl { this.addAbility(ability); } + @Override + public void setExpansionSetCodeForImage(String code) { + super.setExpansionSetCodeForImage(code); + + if (getOriginalExpansionSetCode() != null && getOriginalExpansionSetCode().equals("ELD")) { + setTokenType(RandomUtil.nextInt(4) + 1); // 1...4 + } + } + public FoodToken(final FoodToken token) { super(token); } From 9d2d318a6cb0642aa9358aa6691178322e0c92d1 Mon Sep 17 00:00:00 2001 From: Oleg Agafonov Date: Fri, 27 Sep 2019 22:50:18 +0400 Subject: [PATCH 301/373] [ELD] added tokens --- .../sources/ScryfallImageSupportTokens.java | 30 +++++++++++++++---- .../src/main/resources/card-pictures-tok.txt | 19 ++++++++++++ .../game/permanent/token/FaerieToken.java | 10 +++---- .../mage/game/permanent/token/GoatToken.java | 14 ++++----- .../mage/game/permanent/token/HumanToken.java | 2 +- .../game/permanent/token/KnightToken.java | 10 +++---- .../mage/game/permanent/token/RatToken.java | 21 ++++++++----- 7 files changed, 73 insertions(+), 33 deletions(-) diff --git a/Mage.Client/src/main/java/org/mage/plugins/card/dl/sources/ScryfallImageSupportTokens.java b/Mage.Client/src/main/java/org/mage/plugins/card/dl/sources/ScryfallImageSupportTokens.java index e9efc72aba..5866c5ddee 100644 --- a/Mage.Client/src/main/java/org/mage/plugins/card/dl/sources/ScryfallImageSupportTokens.java +++ b/Mage.Client/src/main/java/org/mage/plugins/card/dl/sources/ScryfallImageSupportTokens.java @@ -92,8 +92,8 @@ public class ScryfallImageSupportTokens { put("MH1/Squirrel", "https://api.scryfall.com/cards/tmh1/15/en?format=image"); put("MH1/Emblem Wrenn and Six", "https://api.scryfall.com/cards/tmh1/21/en?format=image"); put("MH1/Zombie", "https://api.scryfall.com/cards/tmh1/7/en?format=image"); - - //M19 + + // M19 put("M19/Emblem Ajani, Adversary of Tyrants", "https://api.scryfall.com/cards/tm19/15/en?format=image"); put("M19/Angel", "https://api.scryfall.com/cards/tm19/1/en?format=image"); put("M19/Avatar", "https://api.scryfall.com/cards/tm19/2/en?format=image"); @@ -111,7 +111,7 @@ public class ScryfallImageSupportTokens { put("M19/Thopter", "https://api.scryfall.com/cards/tm19/14/en?format=image"); put("M19/Emblem Vivien Reid", "https://api.scryfall.com/cards/tm19/17/en?format=image"); put("M19/Zombie", "https://api.scryfall.com/cards/tm19/8/en?format=image"); - + // M20 put("M20/Ajani's Pridemate", "https://api.scryfall.com/cards/tm20/1/en?format=image"); put("M20/Emblem Chandra, Awakened Inferno", "https://api.scryfall.com/cards/tm20/11/en?format=image"); @@ -125,8 +125,8 @@ public class ScryfallImageSupportTokens { put("M20/Treasure", "https://api.scryfall.com/cards/tm20/10/en?format=image"); put("M20/Wolf", "https://api.scryfall.com/cards/tm20/8/en?format=image"); put("M20/Zombie", "https://api.scryfall.com/cards/tm20/6/en?format=image"); - - //C18 + + // C18 put("C18/Angel", "https://api.scryfall.com/cards/tc18/3/en?format=image"); put("C18/Cat Warrior", "https://api.scryfall.com/cards/tc18/15/en?format=image"); put("C18/Cat", "https://api.scryfall.com/cards/tc18/5/en?format=image"); @@ -149,6 +149,26 @@ public class ScryfallImageSupportTokens { put("C18/Worm", "https://api.scryfall.com/cards/tc18/18/en?format=image"); put("C18/Zombie", "https://api.scryfall.com/cards/tc18/9/en?format=image"); + // ELD + put("ELD/Bear", "https://api.scryfall.com/cards/teld/8/en?format=image"); + put("ELD/Boar", "https://api.scryfall.com/cards/teld/9/en?format=image"); + put("ELD/Dwarf", "https://api.scryfall.com/cards/teld/7/en?format=image"); + put("ELD/Faerie", "https://api.scryfall.com/cards/teld/5/en?format=image"); + put("ELD/Food/1", "https://api.scryfall.com/cards/teld/15/en?format=image"); + put("ELD/Food/2", "https://api.scryfall.com/cards/teld/16/en?format=image"); + put("ELD/Food/3", "https://api.scryfall.com/cards/teld/17/en?format=image"); + put("ELD/Food/4", "https://api.scryfall.com/cards/teld/18/en?format=image"); + put("ELD/Emblem Garruk, Cursed Huntsman", "https://api.scryfall.com/cards/teld/19/en?format=image"); + put("ELD/Giant", "https://api.scryfall.com/cards/teld/10/en?format=image"); + put("ELD/Goat", "https://api.scryfall.com/cards/teld/1/en?format=image"); + put("ELD/Human Cleric", "https://api.scryfall.com/cards/teld/11/en?format=image"); + put("ELD/Human Rogue", "https://api.scryfall.com/cards/teld/12/en?format=image"); + put("ELD/Human Warrior", "https://api.scryfall.com/cards/teld/13/en?format=image"); + put("ELD/Human", "https://api.scryfall.com/cards/teld/2/en?format=image"); + put("ELD/Knight", "https://api.scryfall.com/cards/teld/3/en?format=image"); + put("ELD/Mouse", "https://api.scryfall.com/cards/teld/4/en?format=image"); + put("ELD/Rat", "https://api.scryfall.com/cards/teld/6/en?format=image"); + put("ELD/Wolf", "https://api.scryfall.com/cards/teld/14/en?format=image"); // generate supported sets supportedSets.clear(); diff --git a/Mage.Client/src/main/resources/card-pictures-tok.txt b/Mage.Client/src/main/resources/card-pictures-tok.txt index 253b394719..7f0eee9c74 100644 --- a/Mage.Client/src/main/resources/card-pictures-tok.txt +++ b/Mage.Client/src/main/resources/card-pictures-tok.txt @@ -95,6 +95,7 @@ |Generate|EMBLEM:M19|Vivien Reid||Emblem Vivien|VivienReidEmblem| |Generate|EMBLEM:M20|Chandra, Awakened Inferno||Emblem Chandra|ChandraAwakenedInfernoEmblem| |Generate|EMBLEM:M20|Mu Yanling, Sky Dancer||Emblem Yanling|MuYanlingSkyDancerEmblem| +|Generate|EMBLEM:ELD|Garruk, Cursed Huntsman||Emblem Garruk|GarrukCursedHuntsmanEmblem| |Generate|PLANE:PCA|Plane - Academy At Tolaria West|||AcademyAtTolariaWestPlane| |Generate|PLANE:PCA|Plane - Agyrem|||AgyremPlane| |Generate|PLANE:PCA|Plane - Akoum|||AkoumPlane| @@ -1285,3 +1286,21 @@ |Generate|TOK:M20|Treasure|||TreasureToken| |Generate|TOK:M20|Wolf|||WolfToken| |Generate|TOK:M20|Zombie|||ZombieToken| +|Generate|TOK:ELD|Bear|||BearToken| +|Generate|TOK:ELD|Boar|||WolfsQuarryToken| +|Generate|TOK:ELD|Dwarf|||DwarfToken| +|Generate|TOK:ELD|Faerie|||FaerieToken| +|Generate|TOK:ELD|Food|1||FoodToken| +|Generate|TOK:ELD|Food|2||FoodToken| +|Generate|TOK:ELD|Food|3||FoodToken| +|Generate|TOK:ELD|Food|4||FoodToken| +|Generate|TOK:ELD|Giant|||GiantOpportunityToken| +|Generate|TOK:ELD|Goat|||GoatToken| +|Generate|TOK:ELD|Human|||HumanToken| +|Generate|TOK:ELD|Human Cleric|||OutlawsMerrimentClericToken| +|Generate|TOK:ELD|Human Rogue|||OutlawsMerrimentRogueToken| +|Generate|TOK:ELD|Human Warrior|||OutlawsMerrimentWarriorToken| +|Generate|TOK:ELD|Knight|||KnightToken| +|Generate|TOK:ELD|Mouse|||MouseToken| +|Generate|TOK:ELD|Rat|||RatToken| +|Generate|TOK:ELD|Wolf|||GarrukCursedHuntsmanToken| \ No newline at end of file diff --git a/Mage/src/main/java/mage/game/permanent/token/FaerieToken.java b/Mage/src/main/java/mage/game/permanent/token/FaerieToken.java index f2ac0a9340..bc53e43870 100644 --- a/Mage/src/main/java/mage/game/permanent/token/FaerieToken.java +++ b/Mage/src/main/java/mage/game/permanent/token/FaerieToken.java @@ -1,19 +1,17 @@ - - package mage.game.permanent.token; -import mage.constants.CardType; -import mage.constants.SubType; + import mage.MageInt; import mage.abilities.keyword.FlyingAbility; +import mage.constants.CardType; +import mage.constants.SubType; /** - * * @author spjspj */ public final class FaerieToken extends TokenImpl { public FaerieToken() { - super("Faerie", "1/1 blue Faerie creature tokens with flying"); + super("Faerie", "1/1 blue Faerie creature token with flying"); cardType.add(CardType.CREATURE); color.setBlue(true); subtype.add(SubType.FAERIE); diff --git a/Mage/src/main/java/mage/game/permanent/token/GoatToken.java b/Mage/src/main/java/mage/game/permanent/token/GoatToken.java index d2d509018c..16c0ca7ba7 100644 --- a/Mage/src/main/java/mage/game/permanent/token/GoatToken.java +++ b/Mage/src/main/java/mage/game/permanent/token/GoatToken.java @@ -1,16 +1,14 @@ - - package mage.game.permanent.token; -import java.util.ArrayList; -import java.util.Arrays; -import java.util.List; import mage.MageInt; import mage.constants.CardType; import mage.constants.SubType; +import java.util.ArrayList; +import java.util.Arrays; +import java.util.List; + /** - * * @author LoneFox */ public final class GoatToken extends TokenImpl { @@ -18,7 +16,7 @@ public final class GoatToken extends TokenImpl { static final private List tokenImageSets = new ArrayList<>(); static { - tokenImageSets.addAll(Arrays.asList("EVE", "M13", "M14", "C14")); + tokenImageSets.addAll(Arrays.asList("EVE", "M13", "M14", "C14", "ELD")); } public GoatToken() { @@ -46,5 +44,5 @@ public final class GoatToken extends TokenImpl { public GoatToken copy() { return new GoatToken(this); - } + } } diff --git a/Mage/src/main/java/mage/game/permanent/token/HumanToken.java b/Mage/src/main/java/mage/game/permanent/token/HumanToken.java index b1509f116b..3b565946ca 100644 --- a/Mage/src/main/java/mage/game/permanent/token/HumanToken.java +++ b/Mage/src/main/java/mage/game/permanent/token/HumanToken.java @@ -18,7 +18,7 @@ public final class HumanToken extends TokenImpl { subtype.add(SubType.HUMAN); power = new MageInt(1); toughness = new MageInt(1); - availableImageSetCodes.addAll(Arrays.asList("DKA", "AVR", "FNMP", "RNA")); + availableImageSetCodes.addAll(Arrays.asList("DKA", "AVR", "FNMP", "RNA", "ELD")); } public HumanToken(final HumanToken token) { diff --git a/Mage/src/main/java/mage/game/permanent/token/KnightToken.java b/Mage/src/main/java/mage/game/permanent/token/KnightToken.java index e69e3735b0..35f63cd23b 100644 --- a/Mage/src/main/java/mage/game/permanent/token/KnightToken.java +++ b/Mage/src/main/java/mage/game/permanent/token/KnightToken.java @@ -1,16 +1,16 @@ package mage.game.permanent.token; -import java.util.ArrayList; -import java.util.Arrays; -import java.util.List; import mage.MageInt; import mage.abilities.keyword.VigilanceAbility; import mage.constants.CardType; import mage.constants.SubType; import mage.util.RandomUtil; +import java.util.ArrayList; +import java.util.Arrays; +import java.util.List; + /** - * * @author LevelX2 */ public final class KnightToken extends TokenImpl { @@ -18,7 +18,7 @@ public final class KnightToken extends TokenImpl { static final private List tokenImageSets = new ArrayList<>(); static { - tokenImageSets.addAll(Arrays.asList("ORI", "RTR", "C15", "CMA", "DOM")); + tokenImageSets.addAll(Arrays.asList("ORI", "RTR", "C15", "CMA", "DOM", "ELD")); } public KnightToken() { diff --git a/Mage/src/main/java/mage/game/permanent/token/RatToken.java b/Mage/src/main/java/mage/game/permanent/token/RatToken.java index 20e05a5937..9cf4c9b9fc 100644 --- a/Mage/src/main/java/mage/game/permanent/token/RatToken.java +++ b/Mage/src/main/java/mage/game/permanent/token/RatToken.java @@ -1,30 +1,35 @@ - - package mage.game.permanent.token; import mage.MageInt; import mage.constants.CardType; import mage.constants.SubType; +import java.util.ArrayList; +import java.util.Arrays; +import java.util.List; + /** - * * @author LevelX2 */ public final class RatToken extends TokenImpl { - public RatToken() { - this("GTC"); + static final private List tokenImageSets = new ArrayList<>(); + + static { + tokenImageSets.addAll(Arrays.asList("GTC", "ELD")); } - - public RatToken(String setCode) { + + public RatToken() { super("Rat", "1/1 black Rat creature token"); - this.setOriginalExpansionSetCode(setCode); cardType.add(CardType.CREATURE); color.setBlack(true); subtype.add(SubType.RAT); power = new MageInt(1); toughness = new MageInt(1); + + availableImageSetCodes = tokenImageSets; } + public RatToken(final RatToken token) { super(token); } From d4baa4ebd22056942b1f7bdc9db5500e074396a1 Mon Sep 17 00:00:00 2001 From: Oleg Agafonov Date: Sat, 28 Sep 2019 00:30:28 +0400 Subject: [PATCH 302/373] * Game: premodern ban list updated (Frantic Search removed, Yawgmoth's Bargain added); --- .../Mage.Deck.Constructed/src/mage/deck/Premodern.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Premodern.java b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Premodern.java index 138a97fe9e..a73be72a95 100644 --- a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Premodern.java +++ b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Premodern.java @@ -54,7 +54,6 @@ public class Premodern extends Constructed { banned.add("Entomb"); banned.add("Flash"); banned.add("Force of Will"); - banned.add("Frantic Search"); banned.add("Goblin Recruiter"); banned.add("Grim Monolith"); banned.add("Jeweled Bird"); @@ -76,5 +75,6 @@ public class Premodern extends Constructed { banned.add("Windfall"); banned.add("Worldgorger Dragon"); banned.add("Yawgmoth's Will"); + banned.add("Yawgmoth's Bargain"); } } From f264205dfe60a274143369781e5952aa614dc6e8 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 27 Sep 2019 13:41:39 -0400 Subject: [PATCH 303/373] updated creatures that gained the Noble subtype --- .../mage/cards/a/AboshanCephalidEmperor.java | 25 +++++++-------- Mage.Sets/src/mage/cards/b/BaronSengir.java | 15 +++++---- .../src/mage/cards/b/BragoKingEternal.java | 7 ++--- .../src/mage/cards/c/CephalidAristocrat.java | 9 +++--- Mage.Sets/src/mage/cards/e/EmpressGalina.java | 17 ++++------ Mage.Sets/src/mage/cards/f/FaerieNoble.java | 11 +++---- .../mage/cards/f/FalkenrathAristocrat.java | 10 +++--- .../src/mage/cards/f/FalkenrathNoble.java | 31 +++++++++---------- .../src/mage/cards/g/GarzaZolPlagueQueen.java | 13 ++++---- .../src/mage/cards/i/ImposingSovereign.java | 29 +++++++---------- .../src/mage/cards/i/IndulgentAristocrat.java | 12 +++---- .../mage/cards/k/KingMacarTheGoldCursed.java | 6 ++-- Mage.Sets/src/mage/cards/k/KingSuleiman.java | 14 ++++----- .../mage/cards/l/LlawanCephalidEmpress.java | 14 ++++----- .../src/mage/cards/m/MerfolkSovereign.java | 10 +++--- Mage.Sets/src/mage/cards/s/SpriteNoble.java | 16 +++++----- .../src/mage/cards/s/StromkirkNoble.java | 8 ++--- .../src/mage/cards/v/VampireAristocrat.java | 12 +++---- Mage.Sets/src/mage/cards/v/VampireNoble.java | 9 +++--- .../src/mage/cards/v/VampireSovereign.java | 8 ++--- 20 files changed, 123 insertions(+), 153 deletions(-) diff --git a/Mage.Sets/src/mage/cards/a/AboshanCephalidEmperor.java b/Mage.Sets/src/mage/cards/a/AboshanCephalidEmperor.java index c7e2fb8075..f24172edee 100644 --- a/Mage.Sets/src/mage/cards/a/AboshanCephalidEmperor.java +++ b/Mage.Sets/src/mage/cards/a/AboshanCephalidEmperor.java @@ -1,7 +1,5 @@ - package mage.cards.a; -import java.util.UUID; import mage.MageInt; import mage.abilities.Ability; import mage.abilities.common.SimpleActivatedAbility; @@ -24,24 +22,25 @@ import mage.filter.predicate.mageobject.SubtypePredicate; import mage.target.TargetPermanent; import mage.target.common.TargetControlledCreaturePermanent; +import java.util.UUID; + /** - * * @author cbt33 */ public final class AboshanCephalidEmperor extends CardImpl { - -static final FilterControlledCreaturePermanent filter1 = new FilterControlledCreaturePermanent("untapped Cephalid you control"); -static final FilterCreaturePermanent filter2 = new FilterCreaturePermanent("creatures without flying"); -static { - filter1.add(new SubtypePredicate(SubType.CEPHALID)); - filter2.add(Predicates.not(new AbilityPredicate(FlyingAbility.class))); -} + static final FilterControlledCreaturePermanent filter1 = new FilterControlledCreaturePermanent("untapped Cephalid you control"); + static final FilterCreaturePermanent filter2 = new FilterCreaturePermanent("creatures without flying"); + + static { + filter1.add(new SubtypePredicate(SubType.CEPHALID)); + filter2.add(Predicates.not(new AbilityPredicate(FlyingAbility.class))); + } public AboshanCephalidEmperor(UUID ownerId, CardSetInfo setInfo) { - super(ownerId,setInfo,new CardType[]{CardType.CREATURE},"{4}{U}{U}"); + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{4}{U}{U}"); addSuperType(SuperType.LEGENDARY); - this.subtype.add(SubType.CEPHALID); + this.subtype.add(SubType.CEPHALID, SubType.NOBLE); this.power = new MageInt(3); this.toughness = new MageInt(3); @@ -50,7 +49,7 @@ static { Ability ability = new SimpleActivatedAbility(Zone.BATTLEFIELD, new TapTargetEffect(), new TapTargetCost(new TargetControlledCreaturePermanent(1, 1, filter1, true))); ability.addTarget(new TargetPermanent()); this.addAbility(ability); - + // {U}{U}{U}: Tap all creatures without flying. this.addAbility(new SimpleActivatedAbility(Zone.BATTLEFIELD, new TapAllEffect(filter2), new ManaCostsImpl("{U}{U}{U}"))); } diff --git a/Mage.Sets/src/mage/cards/b/BaronSengir.java b/Mage.Sets/src/mage/cards/b/BaronSengir.java index 41375fb1ce..f97a75dbd9 100644 --- a/Mage.Sets/src/mage/cards/b/BaronSengir.java +++ b/Mage.Sets/src/mage/cards/b/BaronSengir.java @@ -1,7 +1,5 @@ - package mage.cards.b; -import java.util.UUID; import mage.MageInt; import mage.abilities.Ability; import mage.abilities.common.DealtDamageAndDiedTriggeredAbility; @@ -22,12 +20,13 @@ import mage.filter.predicate.mageobject.SubtypePredicate; import mage.filter.predicate.permanent.AnotherPredicate; import mage.target.common.TargetCreaturePermanent; +import java.util.UUID; + /** - * * @author fireshoes */ public final class BaronSengir extends CardImpl { - + private static final FilterCreaturePermanent filter = new FilterCreaturePermanent("another target Vampire"); static { @@ -36,18 +35,18 @@ public final class BaronSengir extends CardImpl { } public BaronSengir(UUID ownerId, CardSetInfo setInfo) { - super(ownerId,setInfo,new CardType[]{CardType.CREATURE},"{5}{B}{B}{B}"); + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{5}{B}{B}{B}"); addSuperType(SuperType.LEGENDARY); - this.subtype.add(SubType.VAMPIRE); + this.subtype.add(SubType.VAMPIRE, SubType.NOBLE); this.power = new MageInt(5); this.toughness = new MageInt(5); // Flying this.addAbility(FlyingAbility.getInstance()); - + // Whenever a creature dealt damage by Baron Sengir this turn dies, put a +2/+2 counter on Baron Sengir. this.addAbility(new DealtDamageAndDiedTriggeredAbility(new AddCountersSourceEffect(CounterType.P2P2.createInstance()), false)); - + // {tap}: Regenerate another target Vampire. Ability ability = new SimpleActivatedAbility(Zone.BATTLEFIELD, new RegenerateTargetEffect(), new TapSourceCost()); ability.addTarget(new TargetCreaturePermanent(filter)); diff --git a/Mage.Sets/src/mage/cards/b/BragoKingEternal.java b/Mage.Sets/src/mage/cards/b/BragoKingEternal.java index f1445fd1ee..ce1353d4d0 100644 --- a/Mage.Sets/src/mage/cards/b/BragoKingEternal.java +++ b/Mage.Sets/src/mage/cards/b/BragoKingEternal.java @@ -1,7 +1,5 @@ - package mage.cards.b; -import java.util.UUID; import mage.MageInt; import mage.abilities.Ability; import mage.abilities.common.DealsCombatDamageToAPlayerTriggeredAbility; @@ -20,8 +18,9 @@ import mage.filter.predicate.Predicates; import mage.filter.predicate.mageobject.CardTypePredicate; import mage.target.common.TargetControlledPermanent; +import java.util.UUID; + /** - * * @author LevelX2 */ public final class BragoKingEternal extends CardImpl { @@ -29,7 +28,7 @@ public final class BragoKingEternal extends CardImpl { public BragoKingEternal(UUID ownerId, CardSetInfo setInfo) { super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{2}{W}{U}"); addSuperType(SuperType.LEGENDARY); - this.subtype.add(SubType.SPIRIT); + this.subtype.add(SubType.SPIRIT, SubType.NOBLE); this.power = new MageInt(2); this.toughness = new MageInt(4); diff --git a/Mage.Sets/src/mage/cards/c/CephalidAristocrat.java b/Mage.Sets/src/mage/cards/c/CephalidAristocrat.java index 7cdf081dfc..18f3ea581e 100644 --- a/Mage.Sets/src/mage/cards/c/CephalidAristocrat.java +++ b/Mage.Sets/src/mage/cards/c/CephalidAristocrat.java @@ -1,7 +1,5 @@ - package mage.cards.c; -import java.util.UUID; import mage.MageInt; import mage.abilities.common.BecomesTargetTriggeredAbility; import mage.abilities.effects.common.PutTopCardOfLibraryIntoGraveControllerEffect; @@ -10,15 +8,16 @@ import mage.cards.CardSetInfo; import mage.constants.CardType; import mage.constants.SubType; +import java.util.UUID; + /** - * * @author fireshoes */ public final class CephalidAristocrat extends CardImpl { public CephalidAristocrat(UUID ownerId, CardSetInfo setInfo) { - super(ownerId,setInfo,new CardType[]{CardType.CREATURE},"{4}{U}"); - this.subtype.add(SubType.CEPHALID); + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{4}{U}"); + this.subtype.add(SubType.CEPHALID, SubType.NOBLE); this.power = new MageInt(3); this.toughness = new MageInt(3); diff --git a/Mage.Sets/src/mage/cards/e/EmpressGalina.java b/Mage.Sets/src/mage/cards/e/EmpressGalina.java index cf5419eed4..f07c72a432 100644 --- a/Mage.Sets/src/mage/cards/e/EmpressGalina.java +++ b/Mage.Sets/src/mage/cards/e/EmpressGalina.java @@ -1,7 +1,5 @@ - package mage.cards.e; -import java.util.UUID; import mage.MageInt; import mage.abilities.Ability; import mage.abilities.common.SimpleActivatedAbility; @@ -10,21 +8,18 @@ import mage.abilities.costs.mana.ManaCostsImpl; import mage.abilities.effects.common.continuous.GainControlTargetEffect; import mage.cards.CardImpl; import mage.cards.CardSetInfo; -import mage.constants.CardType; -import mage.constants.SubType; -import mage.constants.Duration; -import mage.constants.SuperType; -import mage.constants.Zone; +import mage.constants.*; import mage.filter.FilterPermanent; import mage.filter.predicate.mageobject.SupertypePredicate; import mage.target.TargetPermanent; +import java.util.UUID; + /** - * * @author fireshoes */ public final class EmpressGalina extends CardImpl { - + private static final FilterPermanent filter = new FilterPermanent("legendary permanent"); static { @@ -32,9 +27,9 @@ public final class EmpressGalina extends CardImpl { } public EmpressGalina(UUID ownerId, CardSetInfo setInfo) { - super(ownerId,setInfo,new CardType[]{CardType.CREATURE},"{3}{U}{U}"); + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{3}{U}{U}"); addSuperType(SuperType.LEGENDARY); - this.subtype.add(SubType.MERFOLK); + this.subtype.add(SubType.MERFOLK, SubType.NOBLE); this.power = new MageInt(1); this.toughness = new MageInt(3); diff --git a/Mage.Sets/src/mage/cards/f/FaerieNoble.java b/Mage.Sets/src/mage/cards/f/FaerieNoble.java index 6962d48718..e9d6f52b52 100644 --- a/Mage.Sets/src/mage/cards/f/FaerieNoble.java +++ b/Mage.Sets/src/mage/cards/f/FaerieNoble.java @@ -1,7 +1,5 @@ - package mage.cards.f; -import java.util.UUID; import mage.MageInt; import mage.abilities.Ability; import mage.abilities.common.SimpleActivatedAbility; @@ -19,12 +17,13 @@ import mage.constants.Zone; import mage.filter.common.FilterCreaturePermanent; import mage.filter.predicate.mageobject.SubtypePredicate; +import java.util.UUID; + /** - * * @author ilcartographer */ public final class FaerieNoble extends CardImpl { - + private static final FilterCreaturePermanent filter = new FilterCreaturePermanent("Faerie creatures"); static { @@ -32,8 +31,8 @@ public final class FaerieNoble extends CardImpl { } public FaerieNoble(UUID ownerId, CardSetInfo setInfo) { - super(ownerId,setInfo,new CardType[]{CardType.CREATURE},"{2}{G}"); - this.subtype.add(SubType.FAERIE); + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{2}{G}"); + this.subtype.add(SubType.FAERIE, SubType.NOBLE); this.power = new MageInt(1); this.toughness = new MageInt(2); diff --git a/Mage.Sets/src/mage/cards/f/FalkenrathAristocrat.java b/Mage.Sets/src/mage/cards/f/FalkenrathAristocrat.java index 7dbd0922e2..70ee0b725c 100644 --- a/Mage.Sets/src/mage/cards/f/FalkenrathAristocrat.java +++ b/Mage.Sets/src/mage/cards/f/FalkenrathAristocrat.java @@ -1,7 +1,5 @@ - package mage.cards.f; -import java.util.UUID; import mage.MageInt; import mage.abilities.Ability; import mage.abilities.common.SimpleActivatedAbility; @@ -16,20 +14,22 @@ import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.*; import mage.counters.CounterType; -import static mage.filter.StaticFilters.FILTER_CONTROLLED_CREATURE_SHORT_TEXT; import mage.game.Game; import mage.game.permanent.Permanent; import mage.target.common.TargetControlledCreaturePermanent; +import java.util.UUID; + +import static mage.filter.StaticFilters.FILTER_CONTROLLED_CREATURE_SHORT_TEXT; + /** - * * @author North */ public final class FalkenrathAristocrat extends CardImpl { public FalkenrathAristocrat(UUID ownerId, CardSetInfo setInfo) { super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{2}{B}{R}"); - this.subtype.add(SubType.VAMPIRE); + this.subtype.add(SubType.VAMPIRE, SubType.NOBLE); this.power = new MageInt(4); this.toughness = new MageInt(1); diff --git a/Mage.Sets/src/mage/cards/f/FalkenrathNoble.java b/Mage.Sets/src/mage/cards/f/FalkenrathNoble.java index 3491dc5262..35cc7bbde1 100644 --- a/Mage.Sets/src/mage/cards/f/FalkenrathNoble.java +++ b/Mage.Sets/src/mage/cards/f/FalkenrathNoble.java @@ -1,7 +1,5 @@ - package mage.cards.f; -import java.util.UUID; import mage.MageInt; import mage.abilities.TriggeredAbilityImpl; import mage.abilities.effects.common.GainLifeEffect; @@ -19,15 +17,16 @@ import mage.game.events.ZoneChangeEvent; import mage.game.permanent.Permanent; import mage.target.TargetPlayer; +import java.util.UUID; + /** - * * @author North */ public final class FalkenrathNoble extends CardImpl { public FalkenrathNoble(UUID ownerId, CardSetInfo setInfo) { - super(ownerId,setInfo,new CardType[]{CardType.CREATURE},"{3}{B}"); - this.subtype.add(SubType.VAMPIRE); + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{3}{B}"); + this.subtype.add(SubType.VAMPIRE, SubType.NOBLE); this.power = new MageInt(2); this.toughness = new MageInt(2); @@ -72,19 +71,17 @@ class FalkenrathNobleTriggeredAbility extends TriggeredAbilityImpl { @Override public boolean checkTrigger(GameEvent event, Game game) { ZoneChangeEvent zEvent = (ZoneChangeEvent) event; - if (zEvent.isDiesEvent()) { - Permanent permanent = (Permanent) game.getLastKnownInformation(event.getTargetId(), Zone.BATTLEFIELD); - if (permanent != null) { - if (permanent.getId().equals(this.getSourceId())) { - return true; - } else { - if (permanent.isCreature()) { - return true; - } - } - } + if (!zEvent.isDiesEvent()) { + return false; } - return false; + Permanent permanent = (Permanent) game.getLastKnownInformation(event.getTargetId(), Zone.BATTLEFIELD); + if (permanent == null) { + return false; + } + if (permanent.getId().equals(this.getSourceId())) { + return true; + } + return permanent.isCreature(); } @Override diff --git a/Mage.Sets/src/mage/cards/g/GarzaZolPlagueQueen.java b/Mage.Sets/src/mage/cards/g/GarzaZolPlagueQueen.java index 250468050c..7e6971f640 100644 --- a/Mage.Sets/src/mage/cards/g/GarzaZolPlagueQueen.java +++ b/Mage.Sets/src/mage/cards/g/GarzaZolPlagueQueen.java @@ -1,7 +1,5 @@ - package mage.cards.g; -import java.util.UUID; import mage.MageInt; import mage.abilities.common.DealsCombatDamageToAPlayerTriggeredAbility; import mage.abilities.common.DealtDamageAndDiedTriggeredAbility; @@ -16,25 +14,26 @@ import mage.constants.SubType; import mage.constants.SuperType; import mage.counters.CounterType; +import java.util.UUID; + /** - * * @author fireshoes */ public final class GarzaZolPlagueQueen extends CardImpl { public GarzaZolPlagueQueen(UUID ownerId, CardSetInfo setInfo) { - super(ownerId,setInfo,new CardType[]{CardType.CREATURE},"{4}{U}{B}{R}"); + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{4}{U}{B}{R}"); addSuperType(SuperType.LEGENDARY); - this.subtype.add(SubType.VAMPIRE); + this.subtype.add(SubType.VAMPIRE, SubType.NOBLE); this.power = new MageInt(5); this.toughness = new MageInt(5); // Flying this.addAbility(FlyingAbility.getInstance()); - + // Haste this.addAbility(HasteAbility.getInstance()); - + // Whenever a creature dealt damage by Garza Zol, Plague Queen this turn dies, put a +1/+1 counter on Garza Zol. this.addAbility(new DealtDamageAndDiedTriggeredAbility(new AddCountersSourceEffect(CounterType.P1P1.createInstance()))); diff --git a/Mage.Sets/src/mage/cards/i/ImposingSovereign.java b/Mage.Sets/src/mage/cards/i/ImposingSovereign.java index e46be3e1bc..9a38f66703 100644 --- a/Mage.Sets/src/mage/cards/i/ImposingSovereign.java +++ b/Mage.Sets/src/mage/cards/i/ImposingSovereign.java @@ -1,32 +1,27 @@ - package mage.cards.i; -import java.util.UUID; import mage.MageInt; import mage.abilities.Ability; import mage.abilities.common.SimpleStaticAbility; import mage.abilities.effects.ReplacementEffectImpl; 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.EntersTheBattlefieldEvent; import mage.game.events.GameEvent; import mage.game.permanent.Permanent; +import java.util.UUID; + /** - * * @author jeffwadsworth */ public final class ImposingSovereign extends CardImpl { public ImposingSovereign(UUID ownerId, CardSetInfo setInfo) { - super(ownerId,setInfo,new CardType[]{CardType.CREATURE},"{1}{W}"); - this.subtype.add(SubType.HUMAN); + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{1}{W}"); + this.subtype.add(SubType.HUMAN, SubType.NOBLE); this.power = new MageInt(2); this.toughness = new MageInt(1); @@ -36,7 +31,7 @@ public final class ImposingSovereign extends CardImpl { } - public ImposingSovereign(final ImposingSovereign card) { + private ImposingSovereign(final ImposingSovereign card) { super(card); } @@ -53,7 +48,7 @@ class ImposingSovereignEffect extends ReplacementEffectImpl { staticText = "Creatures your opponents control enter the battlefield tapped"; } - ImposingSovereignEffect(final ImposingSovereignEffect effect) { + private ImposingSovereignEffect(final ImposingSovereignEffect effect) { super(effect); } @@ -73,13 +68,11 @@ class ImposingSovereignEffect extends ReplacementEffectImpl { @Override public boolean applies(GameEvent event, Ability source, Game game) { - if (game.getOpponents(source.getControllerId()).contains(event.getPlayerId())) { - Permanent permanent = ((EntersTheBattlefieldEvent) event).getTarget(); - if (permanent != null && permanent.isCreature()) { - return true; - } + if (!game.getOpponents(source.getControllerId()).contains(event.getPlayerId())) { + return false; } - return false; + Permanent permanent = ((EntersTheBattlefieldEvent) event).getTarget(); + return permanent != null && permanent.isCreature(); } @Override diff --git a/Mage.Sets/src/mage/cards/i/IndulgentAristocrat.java b/Mage.Sets/src/mage/cards/i/IndulgentAristocrat.java index 3379c1dc35..ec6c93cdd6 100644 --- a/Mage.Sets/src/mage/cards/i/IndulgentAristocrat.java +++ b/Mage.Sets/src/mage/cards/i/IndulgentAristocrat.java @@ -1,7 +1,5 @@ - package mage.cards.i; -import java.util.UUID; import mage.MageInt; import mage.abilities.Ability; import mage.abilities.common.SimpleActivatedAbility; @@ -15,13 +13,15 @@ import mage.constants.CardType; import mage.constants.SubType; import mage.constants.Zone; import mage.counters.CounterType; -import static mage.filter.StaticFilters.FILTER_CONTROLLED_CREATURE_SHORT_TEXT; import mage.filter.common.FilterControlledPermanent; import mage.filter.predicate.mageobject.SubtypePredicate; import mage.target.common.TargetControlledCreaturePermanent; +import java.util.UUID; + +import static mage.filter.StaticFilters.FILTER_CONTROLLED_CREATURE_SHORT_TEXT; + /** - * * @author fireshoes */ public final class IndulgentAristocrat extends CardImpl { @@ -34,7 +34,7 @@ public final class IndulgentAristocrat extends CardImpl { public IndulgentAristocrat(UUID ownerId, CardSetInfo setInfo) { super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{B}"); - this.subtype.add(SubType.VAMPIRE); + this.subtype.add(SubType.VAMPIRE, SubType.NOBLE); this.power = new MageInt(1); this.toughness = new MageInt(1); @@ -47,7 +47,7 @@ public final class IndulgentAristocrat extends CardImpl { this.addAbility(ability); } - public IndulgentAristocrat(final IndulgentAristocrat card) { + private IndulgentAristocrat(final IndulgentAristocrat card) { super(card); } diff --git a/Mage.Sets/src/mage/cards/k/KingMacarTheGoldCursed.java b/Mage.Sets/src/mage/cards/k/KingMacarTheGoldCursed.java index f943bf421d..c9ce38abf2 100644 --- a/Mage.Sets/src/mage/cards/k/KingMacarTheGoldCursed.java +++ b/Mage.Sets/src/mage/cards/k/KingMacarTheGoldCursed.java @@ -1,7 +1,6 @@ package mage.cards.k; -import java.util.UUID; import mage.MageInt; import mage.abilities.Ability; import mage.abilities.effects.Effect; @@ -16,8 +15,9 @@ import mage.constants.SuperType; import mage.game.permanent.token.GoldToken; import mage.target.common.TargetCreaturePermanent; +import java.util.UUID; + /** - * * @author LevelX2 */ public final class KingMacarTheGoldCursed extends CardImpl { @@ -25,7 +25,7 @@ public final class KingMacarTheGoldCursed extends CardImpl { public KingMacarTheGoldCursed(UUID ownerId, CardSetInfo setInfo) { super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{2}{B}{B}"); addSuperType(SuperType.LEGENDARY); - this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.HUMAN, SubType.NOBLE); this.power = new MageInt(2); this.toughness = new MageInt(3); diff --git a/Mage.Sets/src/mage/cards/k/KingSuleiman.java b/Mage.Sets/src/mage/cards/k/KingSuleiman.java index 3af926e5db..b3ea6d5648 100644 --- a/Mage.Sets/src/mage/cards/k/KingSuleiman.java +++ b/Mage.Sets/src/mage/cards/k/KingSuleiman.java @@ -1,7 +1,5 @@ - package mage.cards.k; -import java.util.UUID; import mage.MageInt; import mage.abilities.Ability; import mage.abilities.common.SimpleActivatedAbility; @@ -17,8 +15,9 @@ import mage.filter.predicate.Predicates; import mage.filter.predicate.mageobject.SubtypePredicate; import mage.target.TargetPermanent; +import java.util.UUID; + /** - * * @author KholdFuzion */ public final class KingSuleiman extends CardImpl { @@ -26,14 +25,15 @@ public final class KingSuleiman extends CardImpl { private static final FilterPermanent filter = new FilterPermanent("Djinn or Efreet"); static { - filter.add( Predicates.or( + filter.add(Predicates.or( new SubtypePredicate(SubType.DJINN), - new SubtypePredicate(SubType.EFREET))); + new SubtypePredicate(SubType.EFREET) + )); } public KingSuleiman(UUID ownerId, CardSetInfo setInfo) { - super(ownerId,setInfo,new CardType[]{CardType.CREATURE},"{1}{W}"); - this.subtype.add(SubType.HUMAN); + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{1}{W}"); + this.subtype.add(SubType.HUMAN, SubType.NOBLE); this.power = new MageInt(1); this.toughness = new MageInt(1); diff --git a/Mage.Sets/src/mage/cards/l/LlawanCephalidEmpress.java b/Mage.Sets/src/mage/cards/l/LlawanCephalidEmpress.java index ed0cb60905..9821dd9e9c 100644 --- a/Mage.Sets/src/mage/cards/l/LlawanCephalidEmpress.java +++ b/Mage.Sets/src/mage/cards/l/LlawanCephalidEmpress.java @@ -1,7 +1,6 @@ package mage.cards.l; -import java.util.UUID; import mage.MageInt; import mage.MageObject; import mage.ObjectColor; @@ -23,8 +22,9 @@ import mage.game.Game; import mage.game.events.GameEvent; import mage.players.Player; +import java.util.UUID; + /** - * * @author LevelX2 */ public final class LlawanCephalidEmpress extends CardImpl { @@ -38,9 +38,9 @@ public final class LlawanCephalidEmpress extends CardImpl { } public LlawanCephalidEmpress(UUID ownerId, CardSetInfo setInfo) { - super(ownerId,setInfo,new CardType[]{CardType.CREATURE},"{3}{U}"); + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{3}{U}"); addSuperType(SuperType.LEGENDARY); - this.subtype.add(SubType.CEPHALID); + this.subtype.add(SubType.CEPHALID, SubType.NOBLE); this.power = new MageInt(2); this.toughness = new MageInt(3); @@ -90,7 +90,7 @@ class LlawanCephalidRuleModifyingEffect extends ContinuousRuleModifyingEffectImp public boolean apply(Game game, Ability source) { return true; } - + @Override public String getInfoMessage(Ability source, GameEvent event, Game game) { MageObject mageObject = game.getObject(source.getSourceId()); @@ -99,12 +99,12 @@ class LlawanCephalidRuleModifyingEffect extends ContinuousRuleModifyingEffectImp } return null; } - + @Override public boolean checksEventType(GameEvent event, Game game) { return event.getType() == GameEvent.EventType.CAST_SPELL; } - + @Override public boolean applies(GameEvent event, Ability source, Game game) { Player controller = game.getPlayer(source.getControllerId()); diff --git a/Mage.Sets/src/mage/cards/m/MerfolkSovereign.java b/Mage.Sets/src/mage/cards/m/MerfolkSovereign.java index f2637dd00d..c39b6fbaaf 100644 --- a/Mage.Sets/src/mage/cards/m/MerfolkSovereign.java +++ b/Mage.Sets/src/mage/cards/m/MerfolkSovereign.java @@ -1,8 +1,5 @@ - - package mage.cards.m; -import java.util.UUID; import mage.MageInt; import mage.abilities.Ability; import mage.abilities.common.SimpleActivatedAbility; @@ -20,8 +17,9 @@ import mage.filter.common.FilterCreaturePermanent; import mage.filter.predicate.mageobject.SubtypePredicate; import mage.target.common.TargetCreaturePermanent; +import java.util.UUID; + /** - * * @author BetaSteward_at_googlemail.com */ public final class MerfolkSovereign extends CardImpl { @@ -35,8 +33,8 @@ public final class MerfolkSovereign extends CardImpl { } public MerfolkSovereign(UUID ownerId, CardSetInfo setInfo) { - super(ownerId,setInfo,new CardType[]{CardType.CREATURE},"{1}{U}{U}"); - this.subtype.add(SubType.MERFOLK); + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{1}{U}{U}"); + this.subtype.add(SubType.MERFOLK, SubType.NOBLE); this.power = new MageInt(2); this.toughness = new MageInt(2); diff --git a/Mage.Sets/src/mage/cards/s/SpriteNoble.java b/Mage.Sets/src/mage/cards/s/SpriteNoble.java index 44888832a9..e59d4e4554 100644 --- a/Mage.Sets/src/mage/cards/s/SpriteNoble.java +++ b/Mage.Sets/src/mage/cards/s/SpriteNoble.java @@ -1,7 +1,5 @@ - package mage.cards.s; -import java.util.UUID; import mage.MageInt; import mage.abilities.common.SimpleActivatedAbility; import mage.abilities.common.SimpleStaticAbility; @@ -11,16 +9,16 @@ import mage.abilities.keyword.FlyingAbility; import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.CardType; -import mage.constants.SubType; import mage.constants.Duration; +import mage.constants.SubType; import mage.constants.Zone; import mage.filter.common.FilterCreaturePermanent; import mage.filter.predicate.mageobject.AbilityPredicate; -/** - * - * @author LoneFox +import java.util.UUID; +/** + * @author LoneFox */ public final class SpriteNoble extends CardImpl { @@ -31,8 +29,8 @@ public final class SpriteNoble extends CardImpl { } public SpriteNoble(UUID ownerId, CardSetInfo setInfo) { - super(ownerId,setInfo,new CardType[]{CardType.CREATURE},"{1}{U}{U}"); - this.subtype.add(SubType.FAERIE); + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{1}{U}{U}"); + this.subtype.add(SubType.FAERIE, SubType.NOBLE); this.power = new MageInt(2); this.toughness = new MageInt(2); @@ -42,7 +40,7 @@ public final class SpriteNoble extends CardImpl { this.addAbility(new SimpleStaticAbility(Zone.BATTLEFIELD, new BoostControlledEffect(0, 1, Duration.WhileOnBattlefield, filter, true))); // {tap}: Other creatures you control with flying get +1/+0 until end of turn. this.addAbility(new SimpleActivatedAbility(Zone.BATTLEFIELD, new BoostControlledEffect(1, 0, Duration.EndOfTurn, filter, true), - new TapSourceCost())); + new TapSourceCost())); } public SpriteNoble(final SpriteNoble card) { diff --git a/Mage.Sets/src/mage/cards/s/StromkirkNoble.java b/Mage.Sets/src/mage/cards/s/StromkirkNoble.java index 03254100e4..1f75187de2 100644 --- a/Mage.Sets/src/mage/cards/s/StromkirkNoble.java +++ b/Mage.Sets/src/mage/cards/s/StromkirkNoble.java @@ -1,7 +1,5 @@ - package mage.cards.s; -import java.util.UUID; import mage.MageInt; import mage.abilities.common.DealsCombatDamageToAPlayerTriggeredAbility; import mage.abilities.common.SimpleEvasionAbility; @@ -15,8 +13,9 @@ import mage.constants.SubType; import mage.counters.CounterType; import mage.filter.common.FilterCreaturePermanent; +import java.util.UUID; + /** - * * @author Alvin * @author ayratn */ @@ -24,7 +23,7 @@ public final class StromkirkNoble extends CardImpl { public StromkirkNoble(UUID ownerId, CardSetInfo setInfo) { super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{R}"); - this.subtype.add(SubType.VAMPIRE); + this.subtype.add(SubType.VAMPIRE, SubType.NOBLE); this.power = new MageInt(1); this.toughness = new MageInt(1); @@ -34,7 +33,6 @@ public final class StromkirkNoble extends CardImpl { new CantBeBlockedByCreaturesSourceEffect(new FilterCreaturePermanent(SubType.HUMAN, "Humans"), Duration.WhileOnBattlefield))); // Whenever Stromkirk Noble deals combat damage to a player, put a +1/+1 counter on it. this.addAbility(new DealsCombatDamageToAPlayerTriggeredAbility(new AddCountersSourceEffect(CounterType.P1P1.createInstance()), false)); - } public StromkirkNoble(final StromkirkNoble card) { diff --git a/Mage.Sets/src/mage/cards/v/VampireAristocrat.java b/Mage.Sets/src/mage/cards/v/VampireAristocrat.java index 0c20539e79..aeb08d03d0 100644 --- a/Mage.Sets/src/mage/cards/v/VampireAristocrat.java +++ b/Mage.Sets/src/mage/cards/v/VampireAristocrat.java @@ -1,7 +1,5 @@ - package mage.cards.v; -import java.util.UUID; import mage.MageInt; import mage.abilities.Ability; import mage.abilities.common.SimpleActivatedAbility; @@ -11,22 +9,22 @@ import mage.abilities.effects.common.continuous.BoostSourceEffect; import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.CardType; -import mage.constants.SubType; import mage.constants.Duration; +import mage.constants.SubType; import mage.constants.Zone; import mage.filter.common.FilterControlledCreaturePermanent; import mage.target.common.TargetControlledCreaturePermanent; +import java.util.UUID; + /** - * * @author Loki */ public final class VampireAristocrat extends CardImpl { public VampireAristocrat(UUID ownerId, CardSetInfo setInfo) { - super(ownerId,setInfo,new CardType[]{CardType.CREATURE},"{2}{B}"); - this.subtype.add(SubType.VAMPIRE); - this.subtype.add(SubType.ROGUE); + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{2}{B}"); + this.subtype.add(SubType.VAMPIRE, SubType.NOBLE, SubType.ROGUE); this.power = new MageInt(2); this.toughness = new MageInt(2); diff --git a/Mage.Sets/src/mage/cards/v/VampireNoble.java b/Mage.Sets/src/mage/cards/v/VampireNoble.java index 88099f000d..67189ec9c6 100644 --- a/Mage.Sets/src/mage/cards/v/VampireNoble.java +++ b/Mage.Sets/src/mage/cards/v/VampireNoble.java @@ -1,22 +1,21 @@ - package mage.cards.v; -import java.util.UUID; import mage.MageInt; import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.CardType; import mage.constants.SubType; +import java.util.UUID; + /** - * * @author fireshoes */ public final class VampireNoble extends CardImpl { public VampireNoble(UUID ownerId, CardSetInfo setInfo) { - super(ownerId,setInfo,new CardType[]{CardType.CREATURE},"{2}{B}"); - this.subtype.add(SubType.VAMPIRE); + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{2}{B}"); + this.subtype.add(SubType.VAMPIRE, SubType.NOBLE); this.power = new MageInt(3); this.toughness = new MageInt(2); } diff --git a/Mage.Sets/src/mage/cards/v/VampireSovereign.java b/Mage.Sets/src/mage/cards/v/VampireSovereign.java index 1cfbfe42b6..66b5549d08 100644 --- a/Mage.Sets/src/mage/cards/v/VampireSovereign.java +++ b/Mage.Sets/src/mage/cards/v/VampireSovereign.java @@ -1,20 +1,20 @@ package mage.cards.v; -import java.util.UUID; import mage.MageInt; import mage.abilities.Ability; import mage.abilities.common.EntersBattlefieldTriggeredAbility; import mage.abilities.effects.common.GainLifeEffect; import mage.abilities.effects.common.LoseLifeTargetEffect; -import mage.constants.SubType; import mage.abilities.keyword.FlyingAbility; import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.CardType; +import mage.constants.SubType; import mage.target.common.TargetOpponent; +import java.util.UUID; + /** - * * @author TheElk801 */ public final class VampireSovereign extends CardImpl { @@ -22,7 +22,7 @@ public final class VampireSovereign extends CardImpl { public VampireSovereign(UUID ownerId, CardSetInfo setInfo) { super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{3}{B}{B}"); - this.subtype.add(SubType.VAMPIRE); + this.subtype.add(SubType.VAMPIRE, SubType.NOBLE); this.power = new MageInt(3); this.toughness = new MageInt(4); From f6552d248dc55f00810d8e3debf26fc8685ae97a Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 27 Sep 2019 13:43:18 -0400 Subject: [PATCH 304/373] updated Dwarven Song to match oracle text change --- Mage.Sets/src/mage/cards/d/DwarvenSong.java | 13 +++++-------- 1 file changed, 5 insertions(+), 8 deletions(-) diff --git a/Mage.Sets/src/mage/cards/d/DwarvenSong.java b/Mage.Sets/src/mage/cards/d/DwarvenSong.java index 6cae2173d9..ac6962d25f 100644 --- a/Mage.Sets/src/mage/cards/d/DwarvenSong.java +++ b/Mage.Sets/src/mage/cards/d/DwarvenSong.java @@ -1,7 +1,5 @@ - package mage.cards.d; -import java.util.UUID; import mage.ObjectColor; import mage.abilities.effects.Effect; import mage.abilities.effects.common.continuous.BecomesColorTargetEffect; @@ -9,11 +7,11 @@ import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.CardType; import mage.constants.Duration; -import mage.filter.StaticFilters; import mage.target.common.TargetCreaturePermanent; +import java.util.UUID; + /** - * * @author maxlebedev */ public final class DwarvenSong extends CardImpl { @@ -23,13 +21,12 @@ public final class DwarvenSong extends CardImpl { // Any number of target creatures become red until end of turn. Effect effect = new BecomesColorTargetEffect(ObjectColor.RED, Duration.EndOfTurn); - effect.setText("Any number of target creatures become red until end of turn"); + effect.setText("One or more target creatures become red until end of turn"); this.getSpellAbility().addEffect(effect); - this.getSpellAbility().addTarget(new TargetCreaturePermanent(0, Integer.MAX_VALUE, StaticFilters.FILTER_PERMANENT_CREATURE, false)); - + this.getSpellAbility().addTarget(new TargetCreaturePermanent(1, Integer.MAX_VALUE)); } - public DwarvenSong(final DwarvenSong card) { + private DwarvenSong(final DwarvenSong card) { super(card); } From c482fade5320712e8d2abec7e46df5fa701c1cf5 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 27 Sep 2019 14:06:30 -0400 Subject: [PATCH 305/373] updated damage wording --- Mage.Sets/src/mage/cards/a/AkoumHellkite.java | 7 +-- .../src/mage/cards/b/BrimstoneVolley.java | 58 ++++--------------- .../src/mage/cards/c/CacklingFlames.java | 18 ++---- Mage.Sets/src/mage/cards/c/CratersClaws.java | 2 +- Mage.Sets/src/mage/cards/f/FieryImpulse.java | 12 ++-- .../src/mage/cards/f/FirecannonBlast.java | 17 +++--- Mage.Sets/src/mage/cards/g/GalvanicBlast.java | 13 +++-- Mage.Sets/src/mage/cards/t/ThermalBlast.java | 19 +++--- 8 files changed, 50 insertions(+), 96 deletions(-) diff --git a/Mage.Sets/src/mage/cards/a/AkoumHellkite.java b/Mage.Sets/src/mage/cards/a/AkoumHellkite.java index 24a13cc142..9a512bb57c 100644 --- a/Mage.Sets/src/mage/cards/a/AkoumHellkite.java +++ b/Mage.Sets/src/mage/cards/a/AkoumHellkite.java @@ -23,7 +23,6 @@ import mage.target.targetpointer.FixedTarget; import java.util.UUID; /** - * * @author fireshoes */ public final class AkoumHellkite extends CardImpl { @@ -56,9 +55,6 @@ public final class AkoumHellkite extends CardImpl { class AkoumHellkiteTriggeredAbility extends TriggeredAbilityImpl { - private static final String text = "Landfall — Whenever a land enters the battlefield under your control, {this} deals 1 damage to any target. " - + "If that land is a Mountain, Akoum Hellkite deals 2 damage to that permanent or player instead."; - public AkoumHellkiteTriggeredAbility() { super(Zone.BATTLEFIELD, new AkoumHellkiteDamageEffect()); } @@ -98,7 +94,8 @@ class AkoumHellkiteTriggeredAbility extends TriggeredAbilityImpl { @Override public String getRule() { - return text; + return "Landfall — Whenever a land enters the battlefield under your control, " + + "{this} deals 1 damage to any target. If that land is a Mountain, {this} deals 2 damage instead."; } } diff --git a/Mage.Sets/src/mage/cards/b/BrimstoneVolley.java b/Mage.Sets/src/mage/cards/b/BrimstoneVolley.java index d0fca03525..d58a4b1021 100644 --- a/Mage.Sets/src/mage/cards/b/BrimstoneVolley.java +++ b/Mage.Sets/src/mage/cards/b/BrimstoneVolley.java @@ -1,20 +1,17 @@ package mage.cards.b; -import java.util.UUID; -import mage.abilities.Ability; -import mage.abilities.effects.OneShotEffect; +import mage.abilities.condition.common.HellbentCondition; +import mage.abilities.decorator.ConditionalOneShotEffect; +import mage.abilities.effects.common.DamageTargetEffect; import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.CardType; -import mage.constants.Outcome; -import mage.game.Game; -import mage.game.permanent.Permanent; -import mage.players.Player; import mage.target.common.TargetAnyTarget; -import mage.watchers.Watcher; import mage.watchers.common.MorbidWatcher; +import java.util.UUID; + /** * @author nantuko */ @@ -25,8 +22,13 @@ public final class BrimstoneVolley extends CardImpl { // Brimstone Volley deals 3 damage to any target. // Morbid — Brimstone Volley deals 5 damage to that creature or player instead if a creature died this turn. - this.getSpellAbility().addEffect(new BrimstoneVolleyEffect()); + this.getSpellAbility().addEffect(new ConditionalOneShotEffect( + new DamageTargetEffect(3), new DamageTargetEffect(5), HellbentCondition.instance, + "{this} deals 3 damage to any target." + + "
Morbid — {this} deals 5 damage instead if a creature died this turn." + )); this.getSpellAbility().addTarget(new TargetAnyTarget()); + this.getSpellAbility().addWatcher(new MorbidWatcher()); } public BrimstoneVolley(final BrimstoneVolley card) { @@ -38,41 +40,3 @@ public final class BrimstoneVolley extends CardImpl { return new BrimstoneVolley(this); } } - -class BrimstoneVolleyEffect extends OneShotEffect { - - public BrimstoneVolleyEffect() { - super(Outcome.Damage); - staticText = "{this} deals 3 damage to any target.\n Morbid — {this} deals 5 damage to that permanent or player instead if a creature died this turn"; - } - - public BrimstoneVolleyEffect(final BrimstoneVolleyEffect effect) { - super(effect); - } - - @Override - public boolean apply(Game game, Ability source) { - int damage = 3; - MorbidWatcher watcher = game.getState().getWatcher(MorbidWatcher.class); - if (watcher != null && watcher.conditionMet()) { - damage = 5; - } - Permanent permanent = game.getPermanent(targetPointer.getFirst(game, source)); - if (permanent != null) { - permanent.damage(damage, source.getSourceId(), game, false, true); - return true; - } - Player player = game.getPlayer(targetPointer.getFirst(game, source)); - if (player != null) { - player.damage(damage, source.getSourceId(), game, false, true); - return true; - } - return false; - } - - @Override - public BrimstoneVolleyEffect copy() { - return new BrimstoneVolleyEffect(this); - } - -} diff --git a/Mage.Sets/src/mage/cards/c/CacklingFlames.java b/Mage.Sets/src/mage/cards/c/CacklingFlames.java index 5c7ba05fa3..194036356c 100644 --- a/Mage.Sets/src/mage/cards/c/CacklingFlames.java +++ b/Mage.Sets/src/mage/cards/c/CacklingFlames.java @@ -1,8 +1,5 @@ - package mage.cards.c; -import java.util.UUID; -import mage.abilities.condition.InvertCondition; import mage.abilities.condition.common.HellbentCondition; import mage.abilities.decorator.ConditionalOneShotEffect; import mage.abilities.effects.common.DamageTargetEffect; @@ -11,8 +8,9 @@ import mage.cards.CardSetInfo; import mage.constants.CardType; import mage.target.common.TargetAnyTarget; +import java.util.UUID; + /** - * * @author JotaPeRL */ public final class CacklingFlames extends CardImpl { @@ -21,16 +19,12 @@ public final class CacklingFlames extends CardImpl { super(ownerId, setInfo, new CardType[]{CardType.INSTANT}, "{3}{R}"); // Cackling Flames deals 3 damage to any target. - this.getSpellAbility().addEffect(new ConditionalOneShotEffect( - new DamageTargetEffect(3), - new InvertCondition(HellbentCondition.instance), - "{this} deals 3 damage to any target")); // Hellbent - Cackling Flames deals 5 damage to that creature or player instead if you have no cards in hand. this.getSpellAbility().addEffect(new ConditionalOneShotEffect( - new DamageTargetEffect(5), - HellbentCondition.instance, - "

Hellbent — {this} deals 5 damage to that permanent or player instead if you have no cards in hand.")); - + new DamageTargetEffect(3), new DamageTargetEffect(5), HellbentCondition.instance, + "{this} deals 3 damage to any target
Hellbent " + + "— {this} deals 5 damage instead if you have no cards in hand." + )); this.getSpellAbility().addTarget(new TargetAnyTarget()); } diff --git a/Mage.Sets/src/mage/cards/c/CratersClaws.java b/Mage.Sets/src/mage/cards/c/CratersClaws.java index a4b2b4dbfb..a0b6a3d12d 100644 --- a/Mage.Sets/src/mage/cards/c/CratersClaws.java +++ b/Mage.Sets/src/mage/cards/c/CratersClaws.java @@ -28,7 +28,7 @@ public final class CratersClaws extends CardImpl { new DamageTargetEffect(ManacostVariableValue.instance), FerociousCondition.instance, "{this} deals X damage to any target." - + "
Ferocious — {this} deals X plus 2 damage to that permanent or player instead if you control a creature with power 4 or greater")); + + "
Ferocious — {this} deals X plus 2 damage instead if you control a creature with power 4 or greater")); this.getSpellAbility().addTarget(new TargetAnyTarget()); this.getSpellAbility().addHint(FerociousHint.instance); } diff --git a/Mage.Sets/src/mage/cards/f/FieryImpulse.java b/Mage.Sets/src/mage/cards/f/FieryImpulse.java index b8e2e52d5f..8a1738dc11 100644 --- a/Mage.Sets/src/mage/cards/f/FieryImpulse.java +++ b/Mage.Sets/src/mage/cards/f/FieryImpulse.java @@ -1,7 +1,6 @@ package mage.cards.f; -import java.util.UUID; import mage.abilities.condition.common.SpellMasteryCondition; import mage.abilities.decorator.ConditionalOneShotEffect; import mage.abilities.effects.common.DamageTargetEffect; @@ -10,20 +9,21 @@ import mage.cards.CardSetInfo; import mage.constants.CardType; import mage.target.common.TargetCreaturePermanent; +import java.util.UUID; + /** - * * @author fireshoes */ public final class FieryImpulse extends CardImpl { public FieryImpulse(UUID ownerId, CardSetInfo setInfo) { - super(ownerId,setInfo,new CardType[]{CardType.INSTANT},"{R}"); + super(ownerId, setInfo, new CardType[]{CardType.INSTANT}, "{R}"); // Fiery Impulse deals 2 damage to target creature. // Spell mastery — If there are two or more instant and/or sorcery cards in your graveyard, Fiery Impulse deals 3 damage to that creature instead. - this.getSpellAbility().addEffect(new ConditionalOneShotEffect(new DamageTargetEffect(3), - new DamageTargetEffect(2), SpellMasteryCondition.instance, - "{this} deals 2 damage to target creature. Spell mastery — If there are two or more instant and/or sorcery cards in your graveyard, {this} deals 3 damage to that creature instead")); + this.getSpellAbility().addEffect(new ConditionalOneShotEffect( + new DamageTargetEffect(3), new DamageTargetEffect(2), SpellMasteryCondition.instance, + "{this} deals 2 damage to target creature.
Spell mastery — If there are two or more instant and/or sorcery cards in your graveyard, {this} deals 3 damage instead")); this.getSpellAbility().addTarget(new TargetCreaturePermanent()); } diff --git a/Mage.Sets/src/mage/cards/f/FirecannonBlast.java b/Mage.Sets/src/mage/cards/f/FirecannonBlast.java index abebb600f0..5f387877be 100644 --- a/Mage.Sets/src/mage/cards/f/FirecannonBlast.java +++ b/Mage.Sets/src/mage/cards/f/FirecannonBlast.java @@ -1,7 +1,6 @@ package mage.cards.f; -import java.util.UUID; import mage.abilities.condition.InvertCondition; import mage.abilities.condition.common.RaidCondition; import mage.abilities.decorator.ConditionalOneShotEffect; @@ -12,8 +11,9 @@ import mage.constants.CardType; import mage.target.common.TargetCreaturePermanent; import mage.watchers.common.PlayerAttackedWatcher; +import java.util.UUID; + /** - * * @author LevelX2 */ public final class FirecannonBlast extends CardImpl { @@ -22,16 +22,13 @@ public final class FirecannonBlast extends CardImpl { super(ownerId, setInfo, new CardType[]{CardType.SORCERY}, "{1}{R}{R}"); // Firecannon Blast deals 3 damage to target creature. - this.getSpellAbility().addEffect(new ConditionalOneShotEffect( - new DamageTargetEffect(3), - new InvertCondition(RaidCondition.instance), - "{this} deals 3 damage to target creature")); - this.getSpellAbility().addTarget(new TargetCreaturePermanent()); // Raid - Firecannon Blast deals 6 damage to that creature instead if you attacked with a creature this turn. this.getSpellAbility().addEffect(new ConditionalOneShotEffect( - new DamageTargetEffect(6, false), - RaidCondition.instance, - "

Raid — {this} deals 6 damage to that creature instead if you attacked with a creature this turn")); + new DamageTargetEffect(3), + new DamageTargetEffect(6), + new InvertCondition(RaidCondition.instance), + "{this} deals 3 damage to target creature.
Raid — {this} deals 6 damage instead if you attacked with a creature this turn")); + this.getSpellAbility().addTarget(new TargetCreaturePermanent()); this.getSpellAbility().addWatcher(new PlayerAttackedWatcher()); } diff --git a/Mage.Sets/src/mage/cards/g/GalvanicBlast.java b/Mage.Sets/src/mage/cards/g/GalvanicBlast.java index 6c696f13df..5c49d14547 100644 --- a/Mage.Sets/src/mage/cards/g/GalvanicBlast.java +++ b/Mage.Sets/src/mage/cards/g/GalvanicBlast.java @@ -1,7 +1,5 @@ - package mage.cards.g; -import java.util.UUID; import mage.abilities.condition.common.MetalcraftCondition; import mage.abilities.decorator.ConditionalOneShotEffect; import mage.abilities.effects.common.DamageTargetEffect; @@ -10,13 +8,15 @@ import mage.cards.CardSetInfo; import mage.constants.CardType; import mage.target.common.TargetAnyTarget; +import java.util.UUID; + /** - * * @author North */ public final class GalvanicBlast extends CardImpl { - private static final String effectText = "{this} deals 2 damage to anytarget.
Metalcraft — {this} deals 4 damage to that permanent or player instead if you control three or more artifacts"; + private static final String effectText = "{this} deals 2 damage to any target." + + "
Metalcraft — {this} deals 4 damage instead if you control three or more artifacts"; public GalvanicBlast(UUID ownerId, CardSetInfo setInfo) { super(ownerId, setInfo, new CardType[]{CardType.INSTANT}, "{R}"); @@ -24,7 +24,10 @@ public final class GalvanicBlast extends CardImpl { // Galvanic Blast deals 2 damage to any target. // Metalcraft — Galvanic Blast deals 4 damage to that creature or player instead if you control three or more artifacts. - this.getSpellAbility().addEffect(new ConditionalOneShotEffect(new DamageTargetEffect(4), new DamageTargetEffect(2), MetalcraftCondition.instance, effectText)); + this.getSpellAbility().addEffect(new ConditionalOneShotEffect( + new DamageTargetEffect(4), new DamageTargetEffect(2), + MetalcraftCondition.instance, effectText + )); this.getSpellAbility().addTarget(new TargetAnyTarget()); } diff --git a/Mage.Sets/src/mage/cards/t/ThermalBlast.java b/Mage.Sets/src/mage/cards/t/ThermalBlast.java index 3f7b28b7bc..6ecf16804a 100644 --- a/Mage.Sets/src/mage/cards/t/ThermalBlast.java +++ b/Mage.Sets/src/mage/cards/t/ThermalBlast.java @@ -1,34 +1,33 @@ package mage.cards.t; -import java.util.UUID; import mage.abilities.condition.common.CardsInControllerGraveCondition; import mage.abilities.decorator.ConditionalOneShotEffect; -import mage.abilities.effects.Effect; import mage.abilities.effects.common.DamageTargetEffect; import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.CardType; import mage.target.common.TargetCreaturePermanent; +import java.util.UUID; + /** - * * @author cbt33 */ public final class ThermalBlast extends CardImpl { public ThermalBlast(UUID ownerId, CardSetInfo setInfo) { - super(ownerId,setInfo,new CardType[]{CardType.INSTANT},"{4}{R}"); - + super(ownerId, setInfo, new CardType[]{CardType.INSTANT}, "{4}{R}"); // Thermal Blast deals 3 damage to target creature. // Threshold - Thermal Blast deals 5 damage to that creature instead if seven or more cards are in your graveyard. - Effect effect = new ConditionalOneShotEffect(new DamageTargetEffect(5), - new DamageTargetEffect(3), - new CardsInControllerGraveCondition(7), - "{this} deals 3 damage to target creature.

Threshold — {this} deals 5 damage to that creature instead if seven or more cards are in your graveyard."); + this.getSpellAbility().addEffect(new ConditionalOneShotEffect( + new DamageTargetEffect(5), new DamageTargetEffect(3), + new CardsInControllerGraveCondition(7), + "{this} deals 3 damage to target creature.
Threshold — " + + "{this} deals 5 damage instead if seven or more cards are in your graveyard." + )); this.getSpellAbility().addTarget(new TargetCreaturePermanent()); - this.getSpellAbility().addEffect(effect); } public ThermalBlast(final ThermalBlast card) { From 69802c78fd74d30c78221ab95d94808f6634df0a Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 27 Sep 2019 18:21:50 -0400 Subject: [PATCH 306/373] updated mana spent to cast spell text --- Mage.Sets/src/mage/cards/b/BatwingBrume.java | 4 ++-- Mage.Sets/src/mage/cards/b/BorosFuryShield.java | 2 +- Mage.Sets/src/mage/cards/c/CankerousThirst.java | 2 +- Mage.Sets/src/mage/cards/d/DawnglowInfusion.java | 2 +- Mage.Sets/src/mage/cards/d/DryadsCaress.java | 2 +- Mage.Sets/src/mage/cards/f/Firespout.java | 16 ++++++---------- .../src/mage/cards/f/FlashConscription.java | 2 +- Mage.Sets/src/mage/cards/g/GruulScrapper.java | 2 +- Mage.Sets/src/mage/cards/i/InduceParanoia.java | 4 ++-- Mage.Sets/src/mage/cards/i/InvertTheSkies.java | 2 +- Mage.Sets/src/mage/cards/m/Moonhold.java | 2 +- Mage.Sets/src/mage/cards/o/OgreSavant.java | 2 +- Mage.Sets/src/mage/cards/r/RepelIntruders.java | 4 ++-- Mage.Sets/src/mage/cards/r/RibbonsOfNight.java | 2 +- Mage.Sets/src/mage/cards/r/RiversGrasp.java | 4 ++-- Mage.Sets/src/mage/cards/r/RollingSpoil.java | 2 +- Mage.Sets/src/mage/cards/s/SeedSpark.java | 2 +- .../src/mage/cards/s/ShriekingGrotesque.java | 2 +- Mage.Sets/src/mage/cards/s/SteamcoreWeird.java | 2 +- Mage.Sets/src/mage/cards/t/TorrentOfSouls.java | 4 ++-- Mage.Sets/src/mage/cards/u/UnnervingAssault.java | 2 +- Mage.Sets/src/mage/cards/v/VigorMortis.java | 2 +- 22 files changed, 32 insertions(+), 36 deletions(-) diff --git a/Mage.Sets/src/mage/cards/b/BatwingBrume.java b/Mage.Sets/src/mage/cards/b/BatwingBrume.java index bfd0ffc933..5f09e9bd34 100644 --- a/Mage.Sets/src/mage/cards/b/BatwingBrume.java +++ b/Mage.Sets/src/mage/cards/b/BatwingBrume.java @@ -36,11 +36,11 @@ public final class BatwingBrume extends CardImpl { // Prevent all combat damage that would be dealt this turn if {W} was spent to cast Batwing Brume. Each player loses 1 life for each attacking creature he or she controls if {B} was spent to cast Batwing Brume. Effect effect = new ConditionalReplacementEffect(new PreventAllDamageByAllPermanentsEffect(Duration.EndOfTurn, true), new LockedInCondition(new ManaWasSpentCondition(ColoredManaSymbol.W))); - effect.setText("Prevent all combat damage that would be dealt this turn if {W} was spent to cast {this}"); + effect.setText("Prevent all combat damage that would be dealt this turn if {W} was spent to cast this spell"); this.getSpellAbility().addEffect(effect); this.getSpellAbility().addEffect(new ConditionalOneShotEffect( new BatwingBrumeEffect(), - new ManaWasSpentCondition(ColoredManaSymbol.B), "Each player loses 1 life for each attacking creature he or she controls if {B} was spent to cast {this}")); + new ManaWasSpentCondition(ColoredManaSymbol.B), "Each player loses 1 life for each attacking creature he or she controls if {B} was spent to cast this spell")); this.getSpellAbility().addEffect(new InfoEffect("(Do both if {W}{B} was spent.)")); this.getSpellAbility().addWatcher(new ManaSpentToCastWatcher()); diff --git a/Mage.Sets/src/mage/cards/b/BorosFuryShield.java b/Mage.Sets/src/mage/cards/b/BorosFuryShield.java index 509e6fd4e6..4b744fbe53 100644 --- a/Mage.Sets/src/mage/cards/b/BorosFuryShield.java +++ b/Mage.Sets/src/mage/cards/b/BorosFuryShield.java @@ -37,7 +37,7 @@ public final class BorosFuryShield extends CardImpl { // If {R} was spent to cast Boros Fury-Shield, it deals damage to that creature's controller equal to the creature's power. this.getSpellAbility().addEffect(new ConditionalOneShotEffect( new BorosFuryShieldDamageEffect(), - new ManaWasSpentCondition(ColoredManaSymbol.R), "If {R} was spent to cast {this}, it deals damage to that creature's controller equal to the creature's power")); + new ManaWasSpentCondition(ColoredManaSymbol.R), "If {R} was spent to cast this spell, it deals damage to that creature's controller equal to the creature's power")); } public BorosFuryShield(final BorosFuryShield card) { diff --git a/Mage.Sets/src/mage/cards/c/CankerousThirst.java b/Mage.Sets/src/mage/cards/c/CankerousThirst.java index 724a37456d..0531514051 100644 --- a/Mage.Sets/src/mage/cards/c/CankerousThirst.java +++ b/Mage.Sets/src/mage/cards/c/CankerousThirst.java @@ -54,7 +54,7 @@ class CankerousThirstEffect extends OneShotEffect { public CankerousThirstEffect() { super(Outcome.Benefit); - this.staticText = "If {B} was spent to cast {this}, you may have target creature get -3/-3 until end of turn. If {G} was spent to cast {this}, you may have target creature get +3/+3 until end of turn"; + this.staticText = "If {B} was spent to cast {this}, you may have target creature get -3/-3 until end of turn. If {G} was spent to cast this spell, you may have target creature get +3/+3 until end of turn"; } public CankerousThirstEffect(final CankerousThirstEffect effect) { diff --git a/Mage.Sets/src/mage/cards/d/DawnglowInfusion.java b/Mage.Sets/src/mage/cards/d/DawnglowInfusion.java index 7faec30b05..bf930dca29 100644 --- a/Mage.Sets/src/mage/cards/d/DawnglowInfusion.java +++ b/Mage.Sets/src/mage/cards/d/DawnglowInfusion.java @@ -28,7 +28,7 @@ public final class DawnglowInfusion extends CardImpl { DynamicValue xValue = ManacostVariableValue.instance; this.getSpellAbility().addEffect(new ConditionalOneShotEffect( new GainLifeEffect(xValue), - new ManaWasSpentCondition(ColoredManaSymbol.G), "You gain X life if {G} was spent to cast {this}")); + new ManaWasSpentCondition(ColoredManaSymbol.G), "You gain X life if {G} was spent to cast this spell")); this.getSpellAbility().addEffect(new ConditionalOneShotEffect( new GainLifeEffect(xValue), new ManaWasSpentCondition(ColoredManaSymbol.W), " And X life if {W} was spent to cast it")); diff --git a/Mage.Sets/src/mage/cards/d/DryadsCaress.java b/Mage.Sets/src/mage/cards/d/DryadsCaress.java index 6c0fa37837..4450f3abf2 100644 --- a/Mage.Sets/src/mage/cards/d/DryadsCaress.java +++ b/Mage.Sets/src/mage/cards/d/DryadsCaress.java @@ -33,7 +33,7 @@ public final class DryadsCaress extends CardImpl { //If {W} was spent to cast Dryad's Caress, untap all creatures you control. this.getSpellAbility().addEffect(new ConditionalOneShotEffect( new UntapAllControllerEffect(new FilterControlledCreaturePermanent(), rule), - new ManaWasSpentCondition(ColoredManaSymbol.W), "If {W} was spent to cast {this}, untap all creatures you control")); + new ManaWasSpentCondition(ColoredManaSymbol.W), "If {W} was spent to cast this spell, untap all creatures you control")); } public DryadsCaress(final DryadsCaress card) { diff --git a/Mage.Sets/src/mage/cards/f/Firespout.java b/Mage.Sets/src/mage/cards/f/Firespout.java index 42d3b97e50..5a2f51e589 100644 --- a/Mage.Sets/src/mage/cards/f/Firespout.java +++ b/Mage.Sets/src/mage/cards/f/Firespout.java @@ -1,11 +1,9 @@ package mage.cards.f; -import java.util.UUID; import mage.abilities.condition.common.ManaWasSpentCondition; import mage.abilities.decorator.ConditionalOneShotEffect; import mage.abilities.effects.common.DamageAllEffect; -import mage.abilities.effects.common.InfoEffect; import mage.abilities.keyword.FlyingAbility; import mage.cards.CardImpl; import mage.cards.CardSetInfo; @@ -16,35 +14,33 @@ import mage.filter.predicate.Predicates; import mage.filter.predicate.mageobject.AbilityPredicate; import mage.watchers.common.ManaSpentToCastWatcher; +import java.util.UUID; + /** - * * @author LevelX2 */ public final class Firespout extends CardImpl { private static final FilterCreaturePermanent filter1 = new FilterCreaturePermanent("creature without flying"); private static final FilterCreaturePermanent filter2 = new FilterCreaturePermanent("creature with flying"); + static { filter1.add(Predicates.not(new AbilityPredicate(FlyingAbility.class))); filter2.add(new AbilityPredicate(FlyingAbility.class)); } public Firespout(UUID ownerId, CardSetInfo setInfo) { - super(ownerId,setInfo,new CardType[]{CardType.SORCERY},"{2}{R/G}"); + super(ownerId, setInfo, new CardType[]{CardType.SORCERY}, "{2}{R/G}"); // Firespout deals 3 damage to each creature without flying if {R} was spent to cast Firespout and 3 damage to each creature with flying if {G} was spent to cast it. this.getSpellAbility().addEffect(new ConditionalOneShotEffect( new DamageAllEffect(3, filter1), - new ManaWasSpentCondition(ColoredManaSymbol.R), "{this} deals 3 damage to each creature without flying if {R} was spent to cast {this}")); + new ManaWasSpentCondition(ColoredManaSymbol.R), "{this} deals 3 damage to each creature without flying if {R} was spent to cast this spell")); this.getSpellAbility().addEffect(new ConditionalOneShotEffect( new DamageAllEffect(3, filter2), - new ManaWasSpentCondition(ColoredManaSymbol.G), " And 3 damage to each creature with flying if {G} was spent to cast it")); - this.getSpellAbility().addEffect(new InfoEffect("(Do both if {R}{G} was spent.)")); + new ManaWasSpentCondition(ColoredManaSymbol.G), "and 3 damage to each creature with flying if {G} was spent to cast it. (Do both if {R}{G} was spent.)")); this.getSpellAbility().addWatcher(new ManaSpentToCastWatcher()); - - - } public Firespout(final Firespout card) { diff --git a/Mage.Sets/src/mage/cards/f/FlashConscription.java b/Mage.Sets/src/mage/cards/f/FlashConscription.java index 4e2ac4a41a..ec60a4b850 100644 --- a/Mage.Sets/src/mage/cards/f/FlashConscription.java +++ b/Mage.Sets/src/mage/cards/f/FlashConscription.java @@ -38,7 +38,7 @@ public final class FlashConscription extends CardImpl { this.getSpellAbility().addEffect(new ConditionalContinuousEffect( new GainAbilityTargetEffect(new FlashConscriptionTriggeredAbility(), Duration.EndOfTurn), new ManaWasSpentCondition(ColoredManaSymbol.W), - "If {W} was spent to cast {this}, the creature gains " + "If {W} was spent to cast this spell, the creature gains " + "\"Whenever this creature deals combat damage, you gain that much life\" until end of turn" )); diff --git a/Mage.Sets/src/mage/cards/g/GruulScrapper.java b/Mage.Sets/src/mage/cards/g/GruulScrapper.java index e90188edbf..591ab3071e 100644 --- a/Mage.Sets/src/mage/cards/g/GruulScrapper.java +++ b/Mage.Sets/src/mage/cards/g/GruulScrapper.java @@ -31,7 +31,7 @@ public final class GruulScrapper extends CardImpl { this.toughness = new MageInt(2); //When Gruul Scrapper enters the battlefield, if Red was spent to cast Gruul Scrapper, it gains haste until end of turn. - this.addAbility(new EntersBattlefieldTriggeredAbility(new ConditionalContinuousEffect(new GainAbilitySourceEffect(HasteAbility.getInstance(), Duration.EndOfTurn), new ManaWasSpentCondition(ColoredManaSymbol.R), " if {R} was spent to cast {this}, it gains haste until end of turn")), new ManaSpentToCastWatcher()); + this.addAbility(new EntersBattlefieldTriggeredAbility(new ConditionalContinuousEffect(new GainAbilitySourceEffect(HasteAbility.getInstance(), Duration.EndOfTurn), new ManaWasSpentCondition(ColoredManaSymbol.R), " if {R} was spent to cast this spell, it gains haste until end of turn")), new ManaSpentToCastWatcher()); } diff --git a/Mage.Sets/src/mage/cards/i/InduceParanoia.java b/Mage.Sets/src/mage/cards/i/InduceParanoia.java index d4b4a8d37c..d8862fa168 100644 --- a/Mage.Sets/src/mage/cards/i/InduceParanoia.java +++ b/Mage.Sets/src/mage/cards/i/InduceParanoia.java @@ -31,7 +31,7 @@ public final class InduceParanoia extends CardImpl { this.getSpellAbility().addEffect(new ConditionalOneShotEffect( new InduceParanoiaEffect(), new CounterTargetEffect(), - new ManaWasSpentCondition(ColoredManaSymbol.B), "Counter target spell. If {B} was spent to cast {this}, that spell's controller puts the top X cards of their library into their graveyard, where X is the spell's converted mana cost.")); + new ManaWasSpentCondition(ColoredManaSymbol.B), "Counter target spell. If {B} was spent to cast this spell, that spell's controller puts the top X cards of their library into their graveyard, where X is the spell's converted mana cost.")); // Counter target spell. this.getSpellAbility().addTarget(new TargetSpell()); @@ -51,7 +51,7 @@ class InduceParanoiaEffect extends OneShotEffect { InduceParanoiaEffect() { super(Outcome.Detriment); - this.staticText = "Counter target spell. If {B} was spent to cast {this}, that spell's controller puts the top X cards of their library into their graveyard, where X is the spell's converted mana cost."; + this.staticText = "Counter target spell. If {B} was spent to cast this spell, that spell's controller puts the top X cards of their library into their graveyard, where X is the spell's converted mana cost."; } InduceParanoiaEffect(final InduceParanoiaEffect effect) { diff --git a/Mage.Sets/src/mage/cards/i/InvertTheSkies.java b/Mage.Sets/src/mage/cards/i/InvertTheSkies.java index 6d7daa3836..23ef03b4eb 100644 --- a/Mage.Sets/src/mage/cards/i/InvertTheSkies.java +++ b/Mage.Sets/src/mage/cards/i/InvertTheSkies.java @@ -43,7 +43,7 @@ public final class InvertTheSkies extends CardImpl { this.getSpellAbility().addEffect(new ConditionalContinuousEffect( new LoseAbilityAllEffect(FlyingAbility.getInstance(), Duration.EndOfTurn, filter), new LockedInCondition(new ManaWasSpentCondition(ColoredManaSymbol.G)), - "Creatures your opponents control lose flying until end of turn if {G} was spent to cast {this},")); + "Creatures your opponents control lose flying until end of turn if {G} was spent to cast this spell,")); this.getSpellAbility().addEffect(new ConditionalContinuousEffect( new GainAbilityControlledEffect(FlyingAbility.getInstance(), Duration.EndOfTurn), diff --git a/Mage.Sets/src/mage/cards/m/Moonhold.java b/Mage.Sets/src/mage/cards/m/Moonhold.java index 97926e3e4c..df0c7252f2 100644 --- a/Mage.Sets/src/mage/cards/m/Moonhold.java +++ b/Mage.Sets/src/mage/cards/m/Moonhold.java @@ -34,7 +34,7 @@ public final class Moonhold extends CardImpl { // Target player can't play land cards this turn if {R} was spent to cast Moonhold and can't play creature cards this turn if {W} was spent to cast it. ContinuousRuleModifyingEffect effect = new MoonholdEffect(); ContinuousRuleModifyingEffect effect2 = new MoonholdEffect2(); - effect.setText("Target player can't play lands this turn if {R} was spent to cast {this}"); + effect.setText("Target player can't play lands this turn if {R} was spent to cast this spell"); effect2.setText("and can't cast creature spells this turn if {W} was spent to cast it."); this.getSpellAbility().addEffect(new ConditionalContinuousRuleModifyingEffect( effect, diff --git a/Mage.Sets/src/mage/cards/o/OgreSavant.java b/Mage.Sets/src/mage/cards/o/OgreSavant.java index 3b7cafa2ac..e230ccfccc 100644 --- a/Mage.Sets/src/mage/cards/o/OgreSavant.java +++ b/Mage.Sets/src/mage/cards/o/OgreSavant.java @@ -33,7 +33,7 @@ public final class OgreSavant extends CardImpl { TriggeredAbility ability = new EntersBattlefieldTriggeredAbility(new ReturnToHandTargetEffect(),false); ability.addTarget(new TargetCreaturePermanent()); this.addAbility(new ConditionalInterveningIfTriggeredAbility(ability, new ManaWasSpentCondition(ColoredManaSymbol.U), - "if {U} was spent to cast {this}, return target creature to its owner's hand."), + "if {U} was spent to cast this spell, return target creature to its owner's hand."), new ManaSpentToCastWatcher()); } diff --git a/Mage.Sets/src/mage/cards/r/RepelIntruders.java b/Mage.Sets/src/mage/cards/r/RepelIntruders.java index 93f8d7eabe..2e939e6783 100644 --- a/Mage.Sets/src/mage/cards/r/RepelIntruders.java +++ b/Mage.Sets/src/mage/cards/r/RepelIntruders.java @@ -31,10 +31,10 @@ public final class RepelIntruders extends CardImpl { target.setRequired(false); this.getSpellAbility().addEffect(new ConditionalOneShotEffect( new CreateTokenEffect(new KithkinToken(), 2), - new ManaWasSpentCondition(ColoredManaSymbol.W), "Create two 1/1 white Kithkin Soldier creature tokens if {W} was spent to cast {this}")); + new ManaWasSpentCondition(ColoredManaSymbol.W), "Create two 1/1 white Kithkin Soldier creature tokens if {W} was spent to cast this spell")); this.getSpellAbility().addEffect(new ConditionalOneShotEffect( new CounterTargetEffect(), - new ManaWasSpentCondition(ColoredManaSymbol.U), " Counter up to one target creature spell if {U} was spent to cast {this}")); + new ManaWasSpentCondition(ColoredManaSymbol.U), " Counter up to one target creature spell if {U} was spent to cast this spell")); this.getSpellAbility().addTarget(target); this.getSpellAbility().addEffect(new InfoEffect("(Do both if {W}{U} was spent.)")); this.getSpellAbility().addWatcher(new ManaSpentToCastWatcher()); diff --git a/Mage.Sets/src/mage/cards/r/RibbonsOfNight.java b/Mage.Sets/src/mage/cards/r/RibbonsOfNight.java index f503fc24bc..6294cfedec 100644 --- a/Mage.Sets/src/mage/cards/r/RibbonsOfNight.java +++ b/Mage.Sets/src/mage/cards/r/RibbonsOfNight.java @@ -36,7 +36,7 @@ public final class RibbonsOfNight extends CardImpl { //If {U} was spent to cast Ribbons of Night, draw a card. this.getSpellAbility().addEffect(new ConditionalOneShotEffect( new DrawCardSourceControllerEffect(1), - new ManaWasSpentCondition(ColoredManaSymbol.U), "If {U} was spent to cast {this}, draw a card")); + new ManaWasSpentCondition(ColoredManaSymbol.U), "If {U} was spent to cast this spell, draw a card")); } public RibbonsOfNight(final RibbonsOfNight card) { diff --git a/Mage.Sets/src/mage/cards/r/RiversGrasp.java b/Mage.Sets/src/mage/cards/r/RiversGrasp.java index e337929ba6..f050c73502 100644 --- a/Mage.Sets/src/mage/cards/r/RiversGrasp.java +++ b/Mage.Sets/src/mage/cards/r/RiversGrasp.java @@ -38,10 +38,10 @@ public final class RiversGrasp extends CardImpl { Target targetPlayer = new TargetPlayer(); this.getSpellAbility().addEffect(new ConditionalOneShotEffect( new ReturnToHandTargetEffect(), - new ManaWasSpentCondition(ColoredManaSymbol.U), "If {U} was spent to cast {this}, return up to one target creature to its owner's hand")); + new ManaWasSpentCondition(ColoredManaSymbol.U), "If {U} was spent to cast this spell, return up to one target creature to its owner's hand")); this.getSpellAbility().addEffect(new ConditionalOneShotEffect( new RiversGraspEffect(), - new ManaWasSpentCondition(ColoredManaSymbol.B), " If {B} was spent to cast {this}, target player reveals their hand, you choose a nonland card from it, then that player discards that card")); + new ManaWasSpentCondition(ColoredManaSymbol.B), " If {B} was spent to cast this spell, target player reveals their hand, you choose a nonland card from it, then that player discards that card")); this.getSpellAbility().addTarget(targetCreature); this.getSpellAbility().addTarget(targetPlayer); diff --git a/Mage.Sets/src/mage/cards/r/RollingSpoil.java b/Mage.Sets/src/mage/cards/r/RollingSpoil.java index ec99f76457..ef6341122e 100644 --- a/Mage.Sets/src/mage/cards/r/RollingSpoil.java +++ b/Mage.Sets/src/mage/cards/r/RollingSpoil.java @@ -30,7 +30,7 @@ public final class RollingSpoil extends CardImpl { // If {B} was spent to cast Rolling Spoil, all creatures get -1/-1 until end of turn. this.getSpellAbility().addEffect(new ConditionalContinuousEffect( new BoostAllEffect(-1, -1, Duration.EndOfTurn), - new ManaWasSpentCondition(ColoredManaSymbol.B), "If {B} was spent to cast {this}, all creatures get -1/-1 until end of turn")); + new ManaWasSpentCondition(ColoredManaSymbol.B), "If {B} was spent to cast this spell, all creatures get -1/-1 until end of turn")); } public RollingSpoil(final RollingSpoil card) { diff --git a/Mage.Sets/src/mage/cards/s/SeedSpark.java b/Mage.Sets/src/mage/cards/s/SeedSpark.java index 2d1a454dc2..291e2dec9b 100644 --- a/Mage.Sets/src/mage/cards/s/SeedSpark.java +++ b/Mage.Sets/src/mage/cards/s/SeedSpark.java @@ -31,7 +31,7 @@ public final class SeedSpark extends CardImpl { //If {G} was spent to cast Seed Spark, create two 1/1 green Saproling creature tokens. this.getSpellAbility().addEffect(new ConditionalOneShotEffect( new CreateTokenEffect(new SaprolingToken(), 2), - new ManaWasSpentCondition(ColoredManaSymbol.G), "If {G} was spent to cast {this}, create two 1/1 green Saproling creature tokens")); + new ManaWasSpentCondition(ColoredManaSymbol.G), "If {G} was spent to cast this spell, create two 1/1 green Saproling creature tokens")); } public SeedSpark(final SeedSpark card) { diff --git a/Mage.Sets/src/mage/cards/s/ShriekingGrotesque.java b/Mage.Sets/src/mage/cards/s/ShriekingGrotesque.java index 4cc23ef06a..8303dd981d 100644 --- a/Mage.Sets/src/mage/cards/s/ShriekingGrotesque.java +++ b/Mage.Sets/src/mage/cards/s/ShriekingGrotesque.java @@ -36,7 +36,7 @@ public final class ShriekingGrotesque extends CardImpl { TriggeredAbility ability = new EntersBattlefieldTriggeredAbility(new DiscardTargetEffect(1), false); ability.addTarget(new TargetPlayer()); this.addAbility(new ConditionalInterveningIfTriggeredAbility(ability, new ManaWasSpentCondition(ColoredManaSymbol.B), - "if {B} was spent to cast {this}, target player discards a card."), new ManaSpentToCastWatcher()); + "if {B} was spent to cast this spell, target player discards a card."), new ManaSpentToCastWatcher()); } public ShriekingGrotesque(final ShriekingGrotesque card) { diff --git a/Mage.Sets/src/mage/cards/s/SteamcoreWeird.java b/Mage.Sets/src/mage/cards/s/SteamcoreWeird.java index 6cc807ea45..8d3d998008 100644 --- a/Mage.Sets/src/mage/cards/s/SteamcoreWeird.java +++ b/Mage.Sets/src/mage/cards/s/SteamcoreWeird.java @@ -32,7 +32,7 @@ public final class SteamcoreWeird extends CardImpl { TriggeredAbility ability = new EntersBattlefieldTriggeredAbility(new DamageTargetEffect(2, "it")); ability.addTarget(new TargetAnyTarget()); this.addAbility(new ConditionalInterveningIfTriggeredAbility(ability, new ManaWasSpentCondition(ColoredManaSymbol.R), - "if {R} was spent to cast {this}, it deals 2 damage to any target."), + "if {R} was spent to cast this spell, it deals 2 damage to any target."), new ManaSpentToCastWatcher()); } diff --git a/Mage.Sets/src/mage/cards/t/TorrentOfSouls.java b/Mage.Sets/src/mage/cards/t/TorrentOfSouls.java index 7a694c00b7..9b503932b2 100644 --- a/Mage.Sets/src/mage/cards/t/TorrentOfSouls.java +++ b/Mage.Sets/src/mage/cards/t/TorrentOfSouls.java @@ -42,10 +42,10 @@ public final class TorrentOfSouls extends CardImpl { Target targetPlayer = new TargetPlayer(); this.getSpellAbility().addEffect(new ConditionalOneShotEffect( new ReturnToBattlefieldUnderYourControlTargetEffect(), - new ManaWasSpentCondition(ColoredManaSymbol.B), "Return up to one target creature card from your graveyard to the battlefield if {B} was spent to cast {this}")); + new ManaWasSpentCondition(ColoredManaSymbol.B), "Return up to one target creature card from your graveyard to the battlefield if {B} was spent to cast this spell")); this.getSpellAbility().addEffect(new ConditionalOneShotEffect( new TorrentOfSoulsEffect(), - new ManaWasSpentCondition(ColoredManaSymbol.R), " Creatures target player controls get +2/+0 and gain haste until end of turn if {R} was spent to cast {this}")); + new ManaWasSpentCondition(ColoredManaSymbol.R), " Creatures target player controls get +2/+0 and gain haste until end of turn if {R} was spent to cast this spell")); this.getSpellAbility().addTarget(targetCreature); this.getSpellAbility().addTarget(targetPlayer); diff --git a/Mage.Sets/src/mage/cards/u/UnnervingAssault.java b/Mage.Sets/src/mage/cards/u/UnnervingAssault.java index 5b38d3a21f..d3ab5d6af2 100644 --- a/Mage.Sets/src/mage/cards/u/UnnervingAssault.java +++ b/Mage.Sets/src/mage/cards/u/UnnervingAssault.java @@ -37,7 +37,7 @@ public final class UnnervingAssault extends CardImpl { // Creatures your opponents control get -1/-0 until end of turn if {U} was spent to cast Unnerving Assault, and creatures you control get +1/+0 until end of turn if {R} was spent to cast it. this.getSpellAbility().addEffect(new ConditionalContinuousEffect( new BoostAllEffect(-1, 0, Duration.EndOfTurn, filter, false), - new ManaWasSpentCondition(ColoredManaSymbol.U), "Creatures your opponents control get -1/-0 until end of turn if {U} was spent to cast {this},")); + new ManaWasSpentCondition(ColoredManaSymbol.U), "Creatures your opponents control get -1/-0 until end of turn if {U} was spent to cast this spell,")); this.getSpellAbility().addEffect(new ConditionalContinuousEffect( new BoostAllEffect(1, 0, Duration.EndOfTurn, filter2, false), new ManaWasSpentCondition(ColoredManaSymbol.R), " and creatures you control get +1/+0 until end of turn if {R} was spent to cast it")); diff --git a/Mage.Sets/src/mage/cards/v/VigorMortis.java b/Mage.Sets/src/mage/cards/v/VigorMortis.java index f783c1815e..494e7383c9 100644 --- a/Mage.Sets/src/mage/cards/v/VigorMortis.java +++ b/Mage.Sets/src/mage/cards/v/VigorMortis.java @@ -33,7 +33,7 @@ public final class VigorMortis extends CardImpl { // Return target creature card from your graveyard to the battlefield. If {G} was spent to cast Vigor Mortis, that creature enters the battlefield with an additional +1/+1 counter on it. this.getSpellAbility().addEffect(new VigorMortisReplacementEffect()); // has to be added before the moving effect this.getSpellAbility().addEffect(new ReturnFromGraveyardToBattlefieldTargetEffect()); - this.getSpellAbility().addEffect(new InfoEffect("If {G} was spent to cast {this}, that creature enters the battlefield with an additional +1/+1 counter on it")); + this.getSpellAbility().addEffect(new InfoEffect("If {G} was spent to cast this spell, that creature enters the battlefield with an additional +1/+1 counter on it")); this.getSpellAbility().addTarget(new TargetCardInYourGraveyard(new FilterCreatureCard())); } From 12d8e40368f957a4af96522090b94466ffd5a2af Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 27 Sep 2019 19:11:45 -0400 Subject: [PATCH 307/373] added additional subtype verification skips --- .../java/mage/verify/VerifyCardDataTest.java | 21 ++++++++++++++++--- 1 file changed, 18 insertions(+), 3 deletions(-) diff --git a/Mage.Verify/src/test/java/mage/verify/VerifyCardDataTest.java b/Mage.Verify/src/test/java/mage/verify/VerifyCardDataTest.java index 33d8f28e08..e19ba19913 100644 --- a/Mage.Verify/src/test/java/mage/verify/VerifyCardDataTest.java +++ b/Mage.Verify/src/test/java/mage/verify/VerifyCardDataTest.java @@ -48,6 +48,7 @@ public class VerifyCardDataTest { private static final boolean CHECK_SOURCE_TOKENS = false; private static final HashMap> skipCheckLists = new HashMap<>(); + private static final Set subtypesToIgnore = new HashSet<>(); private static void skipListCreate(String listName) { skipCheckLists.put(listName, new LinkedHashSet<>()); @@ -93,7 +94,9 @@ public class VerifyCardDataTest { // subtype skipListCreate("SUBTYPE"); skipListAddName("SUBTYPE", "UGL", "Miss Demeanor"); - skipListAddName("SUBTYPE", "M10", "Dread Warlock"); + + subtypesToIgnore.add("Noble"); + subtypesToIgnore.add("Warlock"); // number skipListCreate("NUMBER"); @@ -669,8 +672,20 @@ public class VerifyCardDataTest { } } - if (!eqSet(card.getSubtype(null).stream().map(SubType::toString).collect(Collectors.toSet()), expected)) { - fail(card, "subtypes", card.getSubtype(null) + " != " + expected); + // Remove subtypes that need to be ignored + Collection actual = card + .getSubtype(null) + .stream() + .map(SubType::toString) + .collect(Collectors.toSet()); + actual.removeIf(subtypesToIgnore::contains); + + if (expected != null) { + expected.removeIf(subtypesToIgnore::contains); + } + + if (!eqSet(actual, expected)) { + fail(card, "subtypes", actual + " != " + expected); } } From 7e4df908c67a7d21b36eb73677be22c88bfe6ef1 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 27 Sep 2019 21:36:41 -0400 Subject: [PATCH 308/373] fixed Training Grounds applying to noncreature permanents --- .../src/mage/cards/b/BiomancersFamiliar.java | 73 +++++++++---------- .../src/mage/cards/t/TrainingGrounds.java | 72 +++++++++--------- 2 files changed, 72 insertions(+), 73 deletions(-) diff --git a/Mage.Sets/src/mage/cards/b/BiomancersFamiliar.java b/Mage.Sets/src/mage/cards/b/BiomancersFamiliar.java index 99f4667c1a..ced7a58d5f 100644 --- a/Mage.Sets/src/mage/cards/b/BiomancersFamiliar.java +++ b/Mage.Sets/src/mage/cards/b/BiomancersFamiliar.java @@ -37,12 +37,10 @@ public final class BiomancersFamiliar extends CardImpl { this.toughness = new MageInt(2); // Activated abilities of creatures you control cost {2} less to activate. This effect can't reduce the amount of mana an ability costs to activate to less than one mana. - this.addAbility(new SimpleStaticAbility(Zone.BATTLEFIELD, new BiomancersFamiliarCostReductionEffect())); + this.addAbility(new SimpleStaticAbility(new BiomancersFamiliarCostReductionEffect())); // {T}: The next time target creature adapts this turn, it adapts as though it had no +1/+1 counters on it. - Ability ability = new SimpleActivatedAbility( - new BiomancersFamiliarReplacementEffect(), new TapSourceCost() - ); + Ability ability = new SimpleActivatedAbility(new BiomancersFamiliarReplacementEffect(), new TapSourceCost()); ability.addTarget(new TargetCreaturePermanent()); this.addAbility(ability); } @@ -74,47 +72,48 @@ class BiomancersFamiliarCostReductionEffect extends CostModificationEffectImpl { @Override public boolean apply(Game game, Ability source, Ability abilityToModify) { Player controller = game.getPlayer(abilityToModify.getControllerId()); - if (controller != null) { - Mana mana = abilityToModify.getManaCostsToPay().getMana(); - int reduceMax = mana.getGeneric(); - if (reduceMax > 0 && mana.count() == mana.getGeneric()) { - reduceMax--; - } - if (reduceMax > 2) { - reduceMax = 2; - } - if (reduceMax > 0) { - ChoiceImpl choice = new ChoiceImpl(true); - Set set = new LinkedHashSet<>(); - - for (int i = 0; i <= reduceMax; i++) { - set.add(String.valueOf(i)); - } - choice.setChoices(set); - choice.setMessage("Reduce ability cost"); - if (!controller.choose(Outcome.Benefit, choice, game)) { - return false; - } - int reduce = Integer.parseInt(choice.getChoice()); - CardUtil.reduceCost(abilityToModify, reduce); - } + if (controller == null) { + return false; + } + Mana mana = abilityToModify.getManaCostsToPay().getMana(); + int reduceMax = mana.getGeneric(); + if (reduceMax > 0 && mana.count() == mana.getGeneric()) { + reduceMax--; + } + if (reduceMax > 2) { + reduceMax = 2; + } + if (reduceMax <= 0) { return true; } + ChoiceImpl choice = new ChoiceImpl(true); + Set set = new LinkedHashSet<>(); + + for (int i = 0; i <= reduceMax; i++) { + set.add(String.valueOf(i)); + } + choice.setChoices(set); + choice.setMessage("Reduce ability cost"); + if (!controller.choose(Outcome.Benefit, choice, game)) { + return false; + } + int reduce = Integer.parseInt(choice.getChoice()); + CardUtil.reduceCost(abilityToModify, reduce); + return true; - return false; } @Override public boolean applies(Ability abilityToModify, Ability source, Game game) { - if (abilityToModify.getAbilityType() == AbilityType.ACTIVATED - || (abilityToModify.getAbilityType() == AbilityType.MANA && abilityToModify instanceof ActivatedAbility)) { - //Activated abilities of creatures you control - Permanent permanent = game.getPermanent(abilityToModify.getSourceId()); - if (permanent != null && permanent.isCreature() && permanent.isControlledBy(source.getControllerId())) { - return true; - } + if (abilityToModify.getAbilityType() != AbilityType.ACTIVATED + && (abilityToModify.getAbilityType() != AbilityType.MANA + || !(abilityToModify instanceof ActivatedAbility))) { + return false; } - return false; + //Activated abilities of creatures you control + Permanent permanent = game.getPermanent(abilityToModify.getSourceId()); + return permanent != null && permanent.isCreature() + && permanent.isControlledBy(source.getControllerId()); } @Override diff --git a/Mage.Sets/src/mage/cards/t/TrainingGrounds.java b/Mage.Sets/src/mage/cards/t/TrainingGrounds.java index 663138e691..354f42c0bd 100644 --- a/Mage.Sets/src/mage/cards/t/TrainingGrounds.java +++ b/Mage.Sets/src/mage/cards/t/TrainingGrounds.java @@ -1,4 +1,3 @@ - package mage.cards.t; import mage.Mana; @@ -28,10 +27,10 @@ public final class TrainingGrounds extends CardImpl { super(ownerId, setInfo, new CardType[]{CardType.ENCHANTMENT}, "{U}"); // Activated abilities of creatures you control cost up to {2} less to activate. This effect can't reduce the amount of mana an ability costs to activate to less than one mana. - this.addAbility(new SimpleStaticAbility(Zone.BATTLEFIELD, new TrainingGroundsEffect())); + this.addAbility(new SimpleStaticAbility(new TrainingGroundsEffect())); } - public TrainingGrounds(final TrainingGrounds card) { + private TrainingGrounds(final TrainingGrounds card) { super(card); } @@ -58,47 +57,48 @@ class TrainingGroundsEffect extends CostModificationEffectImpl { @Override public boolean apply(Game game, Ability source, Ability abilityToModify) { Player controller = game.getPlayer(abilityToModify.getControllerId()); - if (controller != null) { - Mana mana = abilityToModify.getManaCostsToPay().getMana(); - int reduceMax = mana.getGeneric(); - if (reduceMax > 0 && mana.count() == mana.getGeneric()) { - reduceMax--; - } - if (reduceMax > 2) { - reduceMax = 2; - } - if (reduceMax > 0) { - ChoiceImpl choice = new ChoiceImpl(true); - Set set = new LinkedHashSet<>(); - - for (int i = 0; i <= reduceMax; i++) { - set.add(String.valueOf(i)); - } - choice.setChoices(set); - choice.setMessage("Reduce ability cost"); - if (!controller.choose(Outcome.Benefit, choice, game)) { - return false; - } - int reduce = Integer.parseInt(choice.getChoice()); - CardUtil.reduceCost(abilityToModify, reduce); - } + if (controller == null) { + return false; + } + Mana mana = abilityToModify.getManaCostsToPay().getMana(); + int reduceMax = mana.getGeneric(); + if (reduceMax > 0 && mana.count() == mana.getGeneric()) { + reduceMax--; + } + if (reduceMax > 2) { + reduceMax = 2; + } + if (reduceMax <= 0) { return true; } + ChoiceImpl choice = new ChoiceImpl(true); + Set set = new LinkedHashSet<>(); + + for (int i = 0; i <= reduceMax; i++) { + set.add(String.valueOf(i)); + } + choice.setChoices(set); + choice.setMessage("Reduce ability cost"); + if (!controller.choose(Outcome.Benefit, choice, game)) { + return false; + } + int reduce = Integer.parseInt(choice.getChoice()); + CardUtil.reduceCost(abilityToModify, reduce); + return true; - return false; } @Override public boolean applies(Ability abilityToModify, Ability source, Game game) { - if (abilityToModify.getAbilityType() == AbilityType.ACTIVATED - || (abilityToModify.getAbilityType() == AbilityType.MANA && (abilityToModify instanceof ActivatedAbility))) { - //Activated abilities of creatures you control - Permanent permanent = game.getPermanent(abilityToModify.getSourceId()); - if (permanent != null && permanent.isControlledBy(source.getControllerId())) { - return true; - } + if (abilityToModify.getAbilityType() != AbilityType.ACTIVATED + && (abilityToModify.getAbilityType() != AbilityType.MANA + || !(abilityToModify instanceof ActivatedAbility))) { + return false; } - return false; + //Activated abilities of creatures you control + Permanent permanent = game.getPermanent(abilityToModify.getSourceId()); + return permanent != null && permanent.isCreature() + && permanent.isControlledBy(source.getControllerId()); } @Override From 9dcbdc18a97b3aeb74d80d619c570fcb20f9df39 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Fri, 27 Sep 2019 21:39:04 -0400 Subject: [PATCH 309/373] fixed Shriekhorn text --- Mage.Sets/src/mage/cards/s/Shriekhorn.java | 23 ++++++++++++---------- 1 file changed, 13 insertions(+), 10 deletions(-) diff --git a/Mage.Sets/src/mage/cards/s/Shriekhorn.java b/Mage.Sets/src/mage/cards/s/Shriekhorn.java index 62130c56e6..9cab21e01f 100644 --- a/Mage.Sets/src/mage/cards/s/Shriekhorn.java +++ b/Mage.Sets/src/mage/cards/s/Shriekhorn.java @@ -1,8 +1,5 @@ - - package mage.cards.s; -import java.util.UUID; import mage.abilities.Ability; import mage.abilities.common.EntersBattlefieldAbility; import mage.abilities.common.SimpleActivatedAbility; @@ -13,26 +10,32 @@ import mage.abilities.effects.common.counter.AddCountersSourceEffect; import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.CardType; -import mage.constants.Zone; import mage.counters.CounterType; import mage.target.TargetPlayer; +import java.util.UUID; + /** - * * @author Loki */ public final class Shriekhorn extends CardImpl { - public Shriekhorn (UUID ownerId, CardSetInfo setInfo) { - super(ownerId,setInfo,new CardType[]{CardType.ARTIFACT},"{1}"); - this.addAbility(new EntersBattlefieldAbility(new AddCountersSourceEffect(CounterType.CHARGE.createInstance(3)), "Shriekhorn enters the battlefield with three charge counters on it")); - Ability ability = new SimpleActivatedAbility(Zone.BATTLEFIELD, new PutLibraryIntoGraveTargetEffect(2), new TapSourceCost()); + public Shriekhorn(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT}, "{1}"); + + this.addAbility(new EntersBattlefieldAbility( + new AddCountersSourceEffect( + CounterType.CHARGE.createInstance(3) + ), "with three charge counters on it" + )); + + Ability ability = new SimpleActivatedAbility(new PutLibraryIntoGraveTargetEffect(2), new TapSourceCost()); ability.addCost(new RemoveCountersSourceCost(CounterType.CHARGE.createInstance())); ability.addTarget(new TargetPlayer()); this.addAbility(ability); } - public Shriekhorn (final Shriekhorn card) { + public Shriekhorn(final Shriekhorn card) { super(card); } From 476184dd7318d251502adde9413d804a11da6c0b Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 28 Sep 2019 17:57:08 -0400 Subject: [PATCH 310/373] fixed Elfhame Sanctuary not revealing the card it finds --- Mage.Sets/src/mage/cards/e/ElfhameSanctuary.java | 15 ++++++++------- 1 file changed, 8 insertions(+), 7 deletions(-) diff --git a/Mage.Sets/src/mage/cards/e/ElfhameSanctuary.java b/Mage.Sets/src/mage/cards/e/ElfhameSanctuary.java index 15beccd114..7007ce985b 100644 --- a/Mage.Sets/src/mage/cards/e/ElfhameSanctuary.java +++ b/Mage.Sets/src/mage/cards/e/ElfhameSanctuary.java @@ -19,22 +19,23 @@ import mage.target.common.TargetCardInLibrary; import java.util.UUID; /** - * * @author Markedagain */ public final class ElfhameSanctuary extends CardImpl { public ElfhameSanctuary(UUID ownerId, CardSetInfo setInfo) { - super(ownerId,setInfo,new CardType[]{CardType.ENCHANTMENT},"{1}{G}"); + super(ownerId, setInfo, new CardType[]{CardType.ENCHANTMENT}, "{1}{G}"); // At the beginning of your upkeep, you may search your library for a basic land card, reveal that card, and put it into your hand. If you do, you skip your draw step this turn and shuffle your library. - Ability ability = new BeginningOfUpkeepTriggeredAbility(new SearchLibraryPutInHandEffect(new TargetCardInLibrary(StaticFilters.FILTER_CARD_BASIC_LAND)), TargetController.YOU, true); + Ability ability = new BeginningOfUpkeepTriggeredAbility(new SearchLibraryPutInHandEffect( + new TargetCardInLibrary(StaticFilters.FILTER_CARD_BASIC_LAND), true + ), TargetController.YOU, true); ability.addEffect(new SkipDrawStepThisTurn()); - + this.addAbility(ability); } - public ElfhameSanctuary(final ElfhameSanctuary card) { + private ElfhameSanctuary(final ElfhameSanctuary card) { super(card); } @@ -46,12 +47,12 @@ public final class ElfhameSanctuary extends CardImpl { class SkipDrawStepThisTurn extends ReplacementEffectImpl { - public SkipDrawStepThisTurn() { + SkipDrawStepThisTurn() { super(Duration.UntilYourNextTurn, Outcome.Neutral); staticText = "Skip your draw step this turn"; } - public SkipDrawStepThisTurn(final SkipDrawStepThisTurn effect) { + private SkipDrawStepThisTurn(final SkipDrawStepThisTurn effect) { super(effect); } From 459543b126568ad2f2a26dadc958d4642759741e Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 28 Sep 2019 20:47:43 -0400 Subject: [PATCH 311/373] fixed The Cauldron of Eternity text --- Mage.Sets/src/mage/cards/t/TheCauldronOfEternity.java | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/Mage.Sets/src/mage/cards/t/TheCauldronOfEternity.java b/Mage.Sets/src/mage/cards/t/TheCauldronOfEternity.java index b2f1196cf8..e4a8026e2e 100644 --- a/Mage.Sets/src/mage/cards/t/TheCauldronOfEternity.java +++ b/Mage.Sets/src/mage/cards/t/TheCauldronOfEternity.java @@ -33,7 +33,7 @@ public final class TheCauldronOfEternity extends CardImpl { this.addSuperType(SuperType.LEGENDARY); - // This spell costs {2} less for each creature card in your graveyard. + // This spell costs {2} less to cast for each creature card in your graveyard. this.addAbility(new SimpleStaticAbility(Zone.ALL, new TheCauldronOfEternityCostReductionEffect())); // Whenever a creature you control dies, put it on the bottom of its owner's library. @@ -66,7 +66,7 @@ class TheCauldronOfEternityCostReductionEffect extends CostModificationEffectImp TheCauldronOfEternityCostReductionEffect() { super(Duration.WhileOnStack, Outcome.Benefit, CostModificationType.REDUCE_COST); - staticText = "This spell costs {2} less for each creature card in your graveyard"; + staticText = "This spell costs {2} less to cast for each creature card in your graveyard"; } private TheCauldronOfEternityCostReductionEffect(final TheCauldronOfEternityCostReductionEffect effect) { From 4dbc1aac3a2539223c4c3fa0808d7d5c7bde9b44 Mon Sep 17 00:00:00 2001 From: Oleg Agafonov Date: Mon, 30 Sep 2019 23:06:32 +0400 Subject: [PATCH 312/373] * Images: added support to download Throne of Eldraine collector cards; --- .../plugins/card/dl/sources/ScryfallImageSupportCards.java | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/Mage.Client/src/main/java/org/mage/plugins/card/dl/sources/ScryfallImageSupportCards.java b/Mage.Client/src/main/java/org/mage/plugins/card/dl/sources/ScryfallImageSupportCards.java index 213b653630..31e5cd0eb2 100644 --- a/Mage.Client/src/main/java/org/mage/plugins/card/dl/sources/ScryfallImageSupportCards.java +++ b/Mage.Client/src/main/java/org/mage/plugins/card/dl/sources/ScryfallImageSupportCards.java @@ -23,7 +23,9 @@ public class ScryfallImageSupportCards { put("EURO", "pelp"). put("GPX", "pgpx"). put("MED", "me1"). - put("MEDM", "med").build(); + put("MEDM", "med"). + put("CELD", "eld"). // scryfall moved ELD and CELD cards in one set, but card numbers are different + build(); private static final Set supportedSets = new ArraySet() { { @@ -240,6 +242,7 @@ public class ScryfallImageSupportCards { add("M20"); add("C19"); add("ELD"); + add("CELD"); // add("EURO"); add("GPX"); From c0344015bbe349b7f161f730574d1fb0ce577e03 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 30 Sep 2019 17:43:10 -0400 Subject: [PATCH 313/373] removed test skip for Noble and Warlock creature types --- Mage.Verify/src/test/java/mage/verify/VerifyCardDataTest.java | 3 --- 1 file changed, 3 deletions(-) diff --git a/Mage.Verify/src/test/java/mage/verify/VerifyCardDataTest.java b/Mage.Verify/src/test/java/mage/verify/VerifyCardDataTest.java index e19ba19913..d5ec909522 100644 --- a/Mage.Verify/src/test/java/mage/verify/VerifyCardDataTest.java +++ b/Mage.Verify/src/test/java/mage/verify/VerifyCardDataTest.java @@ -95,9 +95,6 @@ public class VerifyCardDataTest { skipListCreate("SUBTYPE"); skipListAddName("SUBTYPE", "UGL", "Miss Demeanor"); - subtypesToIgnore.add("Noble"); - subtypesToIgnore.add("Warlock"); - // number skipListCreate("NUMBER"); From 037998a187438779c441e79d4524f585b039e030 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 30 Sep 2019 17:47:10 -0400 Subject: [PATCH 314/373] fixed Covetous Urge allowing any card to be cast --- Mage.Sets/src/mage/cards/c/CovetousUrge.java | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/Mage.Sets/src/mage/cards/c/CovetousUrge.java b/Mage.Sets/src/mage/cards/c/CovetousUrge.java index df7c1e307e..45b570c261 100644 --- a/Mage.Sets/src/mage/cards/c/CovetousUrge.java +++ b/Mage.Sets/src/mage/cards/c/CovetousUrge.java @@ -126,12 +126,11 @@ class CovetousUrgeCastFromExileEffect extends AsThoughEffectImpl { @Override public boolean applies(UUID sourceId, Ability source, UUID affectedControllerId, Game game) { - Card card = mor.getCard(game); - if (card == null) { + if (mor.getCard(game) == null) { discard(); return false; } - return source.isControlledBy(affectedControllerId); + return mor.refersTo(sourceId, game) && source.isControlledBy(affectedControllerId); } } From 3d224ffb61203d461c3b2a17636d6596a3b45cd8 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 30 Sep 2019 18:45:10 -0400 Subject: [PATCH 315/373] reverted change to triggered abilities (#6001) --- .../src/mage/cards/d/DeathlessKnight.java | 21 +++++++++++-------- .../DrawSecondCardTriggeredAbility.java | 21 +++++++++++-------- 2 files changed, 24 insertions(+), 18 deletions(-) diff --git a/Mage.Sets/src/mage/cards/d/DeathlessKnight.java b/Mage.Sets/src/mage/cards/d/DeathlessKnight.java index 88500d97e2..8b536dbf10 100644 --- a/Mage.Sets/src/mage/cards/d/DeathlessKnight.java +++ b/Mage.Sets/src/mage/cards/d/DeathlessKnight.java @@ -59,25 +59,28 @@ class DeathlessKnightTriggeredAbility extends TriggeredAbilityImpl { @Override public boolean checkEventType(GameEvent event, Game game) { - return event.getType() == GameEvent.EventType.GAINED_LIFE; + return event.getType() == GameEvent.EventType.GAINED_LIFE + || event.getType() == GameEvent.EventType.END_PHASE_POST; } @Override public boolean checkTrigger(GameEvent event, Game game) { - if (!event.getPlayerId().equals(controllerId) - || game.getState().getZone(this.getSourceId()) == Zone.GRAVEYARD - || triggeredOnce) { + if (event.getType() == GameEvent.EventType.END_PHASE_POST) { + triggeredOnce = false; + return false; + } + if (event.getType() != GameEvent.EventType.GAINED_LIFE + || !event.getPlayerId().equals(controllerId) + || game.getState().getZone(this.getSourceId()) == Zone.GRAVEYARD) { + return false; + } + if (triggeredOnce) { return false; } triggeredOnce = true; return true; } - @Override - public void reset(Game game) { - triggeredOnce = false; - } - @Override public String getRule() { return "When you gain life for the first time each turn, return {this} from your graveyard to your hand."; diff --git a/Mage/src/main/java/mage/abilities/common/DrawSecondCardTriggeredAbility.java b/Mage/src/main/java/mage/abilities/common/DrawSecondCardTriggeredAbility.java index 9cec4aaf98..becd3c41d1 100644 --- a/Mage/src/main/java/mage/abilities/common/DrawSecondCardTriggeredAbility.java +++ b/Mage/src/main/java/mage/abilities/common/DrawSecondCardTriggeredAbility.java @@ -26,14 +26,22 @@ public class DrawSecondCardTriggeredAbility extends TriggeredAbilityImpl { @Override public boolean checkEventType(GameEvent event, Game game) { - return event.getType() == GameEvent.EventType.DREW_CARD; + return event.getType() == GameEvent.EventType.DREW_CARD + || event.getType() == GameEvent.EventType.END_PHASE_POST; } @Override public boolean checkTrigger(GameEvent event, Game game) { - if (!event.getPlayerId().equals(controllerId) - || game.getPermanent(sourceId) == null - || triggeredOnce) { + if (event.getType() == GameEvent.EventType.END_PHASE_POST) { + triggeredOnce = false; + return false; + } + if (event.getType() != GameEvent.EventType.DREW_CARD + || !event.getPlayerId().equals(controllerId) + || game.getPermanent(sourceId) == null) { + return false; + } + if (triggeredOnce) { return false; } CardsAmountDrawnThisTurnWatcher watcher = game.getState().getWatcher(CardsAmountDrawnThisTurnWatcher.class); @@ -47,11 +55,6 @@ public class DrawSecondCardTriggeredAbility extends TriggeredAbilityImpl { return false; } - @Override - public void reset(Game game) { - triggeredOnce = false; - } - @Override public String getRule() { return "Whenever you draw your second card each turn, " + super.getRule(); From 353789b277e54e93ade6a7c3a3a61c7482bb4654 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 30 Sep 2019 19:00:54 -0400 Subject: [PATCH 316/373] added a hint to Sundering Stroke --- Mage.Sets/src/mage/cards/s/SunderingStroke.java | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/Mage.Sets/src/mage/cards/s/SunderingStroke.java b/Mage.Sets/src/mage/cards/s/SunderingStroke.java index 59ea9619d7..fb3feb97f9 100644 --- a/Mage.Sets/src/mage/cards/s/SunderingStroke.java +++ b/Mage.Sets/src/mage/cards/s/SunderingStroke.java @@ -5,6 +5,7 @@ import mage.abilities.condition.Condition; import mage.abilities.decorator.ConditionalOneShotEffect; import mage.abilities.effects.common.DamageMultiEffect; import mage.abilities.effects.common.DamageTargetEffect; +import mage.abilities.hint.StaticHint; import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.CardType; @@ -30,6 +31,9 @@ public final class SunderingStroke extends CardImpl { "instead {this} deals 7 damage to each of those permanents and/or players" )); this.getSpellAbility().addTarget(new TargetAnyTargetAmount(7, 3)); + this.getSpellAbility().addHint(new StaticHint( + "(You have to choose how 7 damage is divided even if you spend seven red mana)" + )); } private SunderingStroke(final SunderingStroke card) { From 8d24702c7cc59209f9b8f531513ede0acf8c7617 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 2 Oct 2019 08:04:18 -0400 Subject: [PATCH 317/373] fixed Thrill of Possibility text --- .../src/mage/cards/t/ThrillOfPossibility.java | 5 ++--- Mage.Sets/src/mage/cards/t/TormentingVoice.java | 15 ++++++--------- Mage.Sets/src/mage/cards/w/WildGuess.java | 15 ++++++--------- 3 files changed, 14 insertions(+), 21 deletions(-) diff --git a/Mage.Sets/src/mage/cards/t/ThrillOfPossibility.java b/Mage.Sets/src/mage/cards/t/ThrillOfPossibility.java index 6c66625447..9320896230 100644 --- a/Mage.Sets/src/mage/cards/t/ThrillOfPossibility.java +++ b/Mage.Sets/src/mage/cards/t/ThrillOfPossibility.java @@ -1,11 +1,10 @@ package mage.cards.t; -import mage.abilities.costs.common.DiscardTargetCost; +import mage.abilities.costs.common.DiscardCardCost; import mage.abilities.effects.common.DrawCardSourceControllerEffect; import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.CardType; -import mage.target.common.TargetCardInHand; import java.util.UUID; @@ -18,7 +17,7 @@ public final class ThrillOfPossibility extends CardImpl { super(ownerId, setInfo, new CardType[]{CardType.INSTANT}, "{1}{R}"); // As an additional cost to cast this spell, discard a card. - this.getSpellAbility().addCost(new DiscardTargetCost(new TargetCardInHand())); + this.getSpellAbility().addCost(new DiscardCardCost()); // Draw two cards. this.getSpellAbility().addEffect(new DrawCardSourceControllerEffect(2)); diff --git a/Mage.Sets/src/mage/cards/t/TormentingVoice.java b/Mage.Sets/src/mage/cards/t/TormentingVoice.java index f50ec68562..d5cbbadc40 100644 --- a/Mage.Sets/src/mage/cards/t/TormentingVoice.java +++ b/Mage.Sets/src/mage/cards/t/TormentingVoice.java @@ -1,31 +1,28 @@ - package mage.cards.t; -import java.util.UUID; -import mage.abilities.costs.common.DiscardTargetCost; +import mage.abilities.costs.common.DiscardCardCost; import mage.abilities.effects.common.DrawCardSourceControllerEffect; import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.CardType; -import mage.target.common.TargetCardInHand; + +import java.util.UUID; /** - * * @author LevelX2 */ public final class TormentingVoice extends CardImpl { public TormentingVoice(UUID ownerId, CardSetInfo setInfo) { - super(ownerId,setInfo,new CardType[]{CardType.SORCERY},"{1}{R}"); - + super(ownerId, setInfo, new CardType[]{CardType.SORCERY}, "{1}{R}"); // As an additional cost to cast Tormenting Voice, discard a card. - this.getSpellAbility().addCost(new DiscardTargetCost(new TargetCardInHand())); + this.getSpellAbility().addCost(new DiscardCardCost()); // Draw two cards. this.getSpellAbility().addEffect(new DrawCardSourceControllerEffect(2)); } - public TormentingVoice(final TormentingVoice card) { + private TormentingVoice(final TormentingVoice card) { super(card); } diff --git a/Mage.Sets/src/mage/cards/w/WildGuess.java b/Mage.Sets/src/mage/cards/w/WildGuess.java index bd0a53e392..d70767cd39 100644 --- a/Mage.Sets/src/mage/cards/w/WildGuess.java +++ b/Mage.Sets/src/mage/cards/w/WildGuess.java @@ -1,31 +1,28 @@ - package mage.cards.w; -import java.util.UUID; -import mage.abilities.costs.common.DiscardTargetCost; +import mage.abilities.costs.common.DiscardCardCost; import mage.abilities.effects.common.DrawCardSourceControllerEffect; import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.CardType; -import mage.target.common.TargetCardInHand; + +import java.util.UUID; /** - * * @author North */ public final class WildGuess extends CardImpl { public WildGuess(UUID ownerId, CardSetInfo setInfo) { - super(ownerId,setInfo,new CardType[]{CardType.SORCERY},"{R}{R}"); - + super(ownerId, setInfo, new CardType[]{CardType.SORCERY}, "{R}{R}"); // As an additional cost to cast Wild Guess, discard a card. - this.getSpellAbility().addCost(new DiscardTargetCost(new TargetCardInHand())); + this.getSpellAbility().addCost(new DiscardCardCost()); // Draw two cards. this.getSpellAbility().addEffect(new DrawCardSourceControllerEffect(2)); } - public WildGuess(final WildGuess card) { + private WildGuess(final WildGuess card) { super(card); } From 3987c5059526faccd1a068cda2ffdbcf207b6150 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 2 Oct 2019 08:09:08 -0400 Subject: [PATCH 318/373] fixed Lochmere Serpent not targeting cards in graveyards --- Mage.Sets/src/mage/cards/l/LochmereSerpent.java | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/Mage.Sets/src/mage/cards/l/LochmereSerpent.java b/Mage.Sets/src/mage/cards/l/LochmereSerpent.java index 8e6c99faef..80d89e826f 100644 --- a/Mage.Sets/src/mage/cards/l/LochmereSerpent.java +++ b/Mage.Sets/src/mage/cards/l/LochmereSerpent.java @@ -18,7 +18,9 @@ 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.target.common.TargetCardInOpponentsGraveyard; import mage.target.common.TargetControlledPermanent; import java.util.UUID; @@ -63,6 +65,9 @@ public final class LochmereSerpent extends CardImpl { new ManaCostsImpl("{U}{B}") ); ability.addEffect(new ReturnSourceFromGraveyardToHandEffect()); + ability.addTarget(new TargetCardInOpponentsGraveyard( + 5, 5, StaticFilters.FILTER_CARD, true + )); this.addAbility(ability); } From e4bcd0abddc5b3e9cbdf073ff5b469873b96a7d6 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 3 Oct 2019 07:11:26 -0400 Subject: [PATCH 319/373] fixed Kenrith, the Returned King's last ability (fixes #6007) --- Mage.Sets/src/mage/cards/k/KenrithTheReturnedKing.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Mage.Sets/src/mage/cards/k/KenrithTheReturnedKing.java b/Mage.Sets/src/mage/cards/k/KenrithTheReturnedKing.java index 3c22dcbf21..c1b780cf35 100644 --- a/Mage.Sets/src/mage/cards/k/KenrithTheReturnedKing.java +++ b/Mage.Sets/src/mage/cards/k/KenrithTheReturnedKing.java @@ -68,7 +68,7 @@ public final class KenrithTheReturnedKing extends CardImpl { this.addAbility(ability); // {4}{B}: Put target creature card from a graveyard onto the battlefield under its owner's control. - ability = new SimpleActivatedAbility(new GainLifeTargetEffect(5), new ManaCostsImpl("{4}{B}")); + ability = new SimpleActivatedAbility(new KenrithTheReturnedKingEffect(), new ManaCostsImpl("{4}{B}")); ability.addTarget(new TargetCardInGraveyard(StaticFilters.FILTER_CARD_CREATURE)); this.addAbility(ability); } From ef69aa7326e6ad79a350634ad48be21816cc5007 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 3 Oct 2019 12:35:22 -0400 Subject: [PATCH 320/373] updated some class names to match naming conventions --- ...heFateShifter.java => AminatouTheFateshifter.java} | 10 +++++----- ...{AzoriusAEthermage.java => AzoriusAethermage.java} | 10 +++++----- ...EmpiresVolVii.java => SarpadianEmpiresVolVII.java} | 11 +++++------ Mage.Sets/src/mage/sets/Commander2018Edition.java | 2 +- Mage.Sets/src/mage/sets/Dissension.java | 2 +- Mage.Sets/src/mage/sets/TimeSpiral.java | 5 +++-- 6 files changed, 20 insertions(+), 20 deletions(-) rename Mage.Sets/src/mage/cards/a/{AminatouTheFateShifter.java => AminatouTheFateshifter.java} (96%) rename Mage.Sets/src/mage/cards/a/{AzoriusAEthermage.java => AzoriusAethermage.java} (92%) rename Mage.Sets/src/mage/cards/s/{SarpadianEmpiresVolVii.java => SarpadianEmpiresVolVII.java} (93%) diff --git a/Mage.Sets/src/mage/cards/a/AminatouTheFateShifter.java b/Mage.Sets/src/mage/cards/a/AminatouTheFateshifter.java similarity index 96% rename from Mage.Sets/src/mage/cards/a/AminatouTheFateShifter.java rename to Mage.Sets/src/mage/cards/a/AminatouTheFateshifter.java index bdd8b1e1ed..b9a89f87e3 100644 --- a/Mage.Sets/src/mage/cards/a/AminatouTheFateShifter.java +++ b/Mage.Sets/src/mage/cards/a/AminatouTheFateshifter.java @@ -34,7 +34,7 @@ import java.util.UUID; * * @author Colin Redman */ -public class AminatouTheFateShifter extends CardImpl { +public class AminatouTheFateshifter extends CardImpl { private static final FilterPermanent filter = new FilterPermanent("permanent you own"); @@ -43,7 +43,7 @@ public class AminatouTheFateShifter extends CardImpl { filter.add(AnotherPredicate.instance); } - public AminatouTheFateShifter(UUID ownerId, CardSetInfo setInfo) { + public AminatouTheFateshifter(UUID ownerId, CardSetInfo setInfo) { super(ownerId, setInfo, new CardType[]{CardType.PLANESWALKER}, "{W}{U}{B}"); this.addSuperType(SuperType.LEGENDARY); this.subtype.add(SubType.AMINATOU); @@ -69,13 +69,13 @@ public class AminatouTheFateShifter extends CardImpl { this.addAbility(CanBeYourCommanderAbility.getInstance()); } - public AminatouTheFateShifter(final AminatouTheFateShifter card) { + public AminatouTheFateshifter(final AminatouTheFateshifter card) { super(card); } @Override - public AminatouTheFateShifter copy() { - return new AminatouTheFateShifter(this); + public AminatouTheFateshifter copy() { + return new AminatouTheFateshifter(this); } } diff --git a/Mage.Sets/src/mage/cards/a/AzoriusAEthermage.java b/Mage.Sets/src/mage/cards/a/AzoriusAethermage.java similarity index 92% rename from Mage.Sets/src/mage/cards/a/AzoriusAEthermage.java rename to Mage.Sets/src/mage/cards/a/AzoriusAethermage.java index 851c91793a..16aed74a47 100644 --- a/Mage.Sets/src/mage/cards/a/AzoriusAEthermage.java +++ b/Mage.Sets/src/mage/cards/a/AzoriusAethermage.java @@ -23,11 +23,11 @@ import mage.game.permanent.Permanent; * * @author jeffwadsworth */ -public final class AzoriusAEthermage extends CardImpl { +public final class AzoriusAethermage extends CardImpl { private static final String rule = "Whenever a permanent is returned to your hand, "; - public AzoriusAEthermage(UUID ownerId, CardSetInfo setInfo) { + public AzoriusAethermage(UUID ownerId, CardSetInfo setInfo) { super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{1}{W}{U}"); this.subtype.add(SubType.HUMAN); @@ -40,13 +40,13 @@ public final class AzoriusAEthermage extends CardImpl { this.addAbility(new AzoriusAEthermageAbility(Zone.BATTLEFIELD, Zone.BATTLEFIELD, Zone.HAND, effect, new FilterPermanent(), rule, true)); } - public AzoriusAEthermage(final AzoriusAEthermage card) { + public AzoriusAethermage(final AzoriusAethermage card) { super(card); } @Override - public AzoriusAEthermage copy() { - return new AzoriusAEthermage(this); + public AzoriusAethermage copy() { + return new AzoriusAethermage(this); } } diff --git a/Mage.Sets/src/mage/cards/s/SarpadianEmpiresVolVii.java b/Mage.Sets/src/mage/cards/s/SarpadianEmpiresVolVII.java similarity index 93% rename from Mage.Sets/src/mage/cards/s/SarpadianEmpiresVolVii.java rename to Mage.Sets/src/mage/cards/s/SarpadianEmpiresVolVII.java index a31d1760e2..8f54f958b3 100644 --- a/Mage.Sets/src/mage/cards/s/SarpadianEmpiresVolVii.java +++ b/Mage.Sets/src/mage/cards/s/SarpadianEmpiresVolVII.java @@ -21,7 +21,6 @@ import mage.game.permanent.token.CitizenToken; import mage.game.permanent.token.GoblinToken; import mage.game.permanent.token.SaprolingToken; import mage.game.permanent.token.ThrullToken; -import mage.game.permanent.token.TokenImpl; import mage.game.permanent.token.Token; import mage.players.Player; @@ -29,9 +28,9 @@ import mage.players.Player; * * @author LoneFox */ -public final class SarpadianEmpiresVolVii extends CardImpl { +public final class SarpadianEmpiresVolVII extends CardImpl { - public SarpadianEmpiresVolVii(UUID ownerId, CardSetInfo setInfo) { + public SarpadianEmpiresVolVII(UUID ownerId, CardSetInfo setInfo) { super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT}, "{3}"); // As Sarpadian Empires, Vol. VII enters the battlefield, choose white Citizen, blue Camarid, black Thrull, red Goblin, or green Saproling. @@ -42,13 +41,13 @@ public final class SarpadianEmpiresVolVii extends CardImpl { this.addAbility(ability); } - public SarpadianEmpiresVolVii(final SarpadianEmpiresVolVii card) { + public SarpadianEmpiresVolVII(final SarpadianEmpiresVolVII card) { super(card); } @Override - public SarpadianEmpiresVolVii copy() { - return new SarpadianEmpiresVolVii(this); + public SarpadianEmpiresVolVII copy() { + return new SarpadianEmpiresVolVII(this); } } diff --git a/Mage.Sets/src/mage/sets/Commander2018Edition.java b/Mage.Sets/src/mage/sets/Commander2018Edition.java index ac3896c801..073f6299fa 100644 --- a/Mage.Sets/src/mage/sets/Commander2018Edition.java +++ b/Mage.Sets/src/mage/sets/Commander2018Edition.java @@ -27,7 +27,7 @@ public final class Commander2018Edition extends ExpansionSet { cards.add(new SetCardInfo("Akoum Refuge", 231, Rarity.UNCOMMON, mage.cards.a.AkoumRefuge.class)); cards.add(new SetCardInfo("Akroma's Vengeance", 62, Rarity.RARE, mage.cards.a.AkromasVengeance.class)); cards.add(new SetCardInfo("Aminatou's Augury", 6, Rarity.RARE, mage.cards.a.AminatousAugury.class)); - cards.add(new SetCardInfo("Aminatou, the Fateshifter", 37, Rarity.MYTHIC, mage.cards.a.AminatouTheFateShifter.class)); + cards.add(new SetCardInfo("Aminatou, the Fateshifter", 37, Rarity.MYTHIC, mage.cards.a.AminatouTheFateshifter.class)); cards.add(new SetCardInfo("Ancient Stone Idol", 53, Rarity.RARE, mage.cards.a.AncientStoneIdol.class)); cards.add(new SetCardInfo("Arcane Sanctum", 232, Rarity.UNCOMMON, mage.cards.a.ArcaneSanctum.class)); cards.add(new SetCardInfo("Archetype of Imagination", 81, Rarity.UNCOMMON, mage.cards.a.ArchetypeOfImagination.class)); diff --git a/Mage.Sets/src/mage/sets/Dissension.java b/Mage.Sets/src/mage/sets/Dissension.java index 3aabb0d2ce..0b1ca43840 100644 --- a/Mage.Sets/src/mage/sets/Dissension.java +++ b/Mage.Sets/src/mage/sets/Dissension.java @@ -33,7 +33,7 @@ public final class Dissension extends ExpansionSet { cards.add(new SetCardInfo("Assault Zeppelid", 103, Rarity.COMMON, mage.cards.a.AssaultZeppelid.class)); cards.add(new SetCardInfo("Aurora Eidolon", 1, Rarity.COMMON, mage.cards.a.AuroraEidolon.class)); cards.add(new SetCardInfo("Avatar of Discord", 140, Rarity.RARE, mage.cards.a.AvatarOfDiscord.class)); - cards.add(new SetCardInfo("Azorius Aethermage", 104, Rarity.UNCOMMON, mage.cards.a.AzoriusAEthermage.class)); + cards.add(new SetCardInfo("Azorius Aethermage", 104, Rarity.UNCOMMON, mage.cards.a.AzoriusAethermage.class)); cards.add(new SetCardInfo("Azorius Chancery", 170, Rarity.COMMON, mage.cards.a.AzoriusChancery.class)); cards.add(new SetCardInfo("Azorius First-Wing", 105, Rarity.COMMON, mage.cards.a.AzoriusFirstWing.class)); cards.add(new SetCardInfo("Azorius Guildmage", 141, Rarity.UNCOMMON, mage.cards.a.AzoriusGuildmage.class)); diff --git a/Mage.Sets/src/mage/sets/TimeSpiral.java b/Mage.Sets/src/mage/sets/TimeSpiral.java index a730e26950..1e80b06faa 100644 --- a/Mage.Sets/src/mage/sets/TimeSpiral.java +++ b/Mage.Sets/src/mage/sets/TimeSpiral.java @@ -1,6 +1,5 @@ package mage.sets; -import java.util.List; import mage.cards.Card; import mage.cards.ExpansionSet; import mage.cards.repository.CardCriteria; @@ -8,6 +7,8 @@ import mage.cards.repository.CardRepository; import mage.constants.Rarity; import mage.constants.SetType; +import java.util.List; + public final class TimeSpiral extends ExpansionSet { private static final TimeSpiral instance = new TimeSpiral(); @@ -233,7 +234,7 @@ public final class TimeSpiral extends ExpansionSet { cards.add(new SetCardInfo("Sage of Epityr", 74, Rarity.COMMON, mage.cards.s.SageOfEpityr.class)); cards.add(new SetCardInfo("Saltcrusted Steppe", 277, Rarity.UNCOMMON, mage.cards.s.SaltcrustedSteppe.class)); cards.add(new SetCardInfo("Sangrophage", 127, Rarity.COMMON, mage.cards.s.Sangrophage.class)); - cards.add(new SetCardInfo("Sarpadian Empires, Vol. VII", 263, Rarity.RARE, mage.cards.s.SarpadianEmpiresVolVii.class)); + cards.add(new SetCardInfo("Sarpadian Empires, Vol. VII", 263, Rarity.RARE, mage.cards.s.SarpadianEmpiresVolVII.class)); cards.add(new SetCardInfo("Savage Thallid", 213, Rarity.COMMON, mage.cards.s.SavageThallid.class)); cards.add(new SetCardInfo("Scarwood Treefolk", 214, Rarity.COMMON, mage.cards.s.ScarwoodTreefolk.class)); cards.add(new SetCardInfo("Scion of the Ur-Dragon", 246, Rarity.RARE, mage.cards.s.ScionOfTheUrDragon.class)); From 6c27ccd8a6cf30c5d7e84f2af3bd57c8018340d2 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 3 Oct 2019 12:51:00 -0400 Subject: [PATCH 321/373] Implemented Arctic Foxes --- Mage.Sets/src/mage/cards/a/ArcticFoxes.java | 74 +++++++++++++++++++++ Mage.Sets/src/mage/sets/IceAge.java | 1 + 2 files changed, 75 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/a/ArcticFoxes.java diff --git a/Mage.Sets/src/mage/cards/a/ArcticFoxes.java b/Mage.Sets/src/mage/cards/a/ArcticFoxes.java new file mode 100644 index 0000000000..1c49ae5f02 --- /dev/null +++ b/Mage.Sets/src/mage/cards/a/ArcticFoxes.java @@ -0,0 +1,74 @@ +package mage.cards.a; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.condition.Condition; +import mage.abilities.decorator.ConditionalContinuousEffect; +import mage.abilities.effects.common.combat.CantBeBlockedByCreaturesSourceEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.*; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterCreaturePermanent; +import mage.filter.common.FilterLandPermanent; +import mage.filter.predicate.mageobject.PowerPredicate; +import mage.filter.predicate.mageobject.SupertypePredicate; +import mage.game.Game; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class ArcticFoxes extends CardImpl { + + private static final FilterCreaturePermanent filter = new FilterCreaturePermanent(); + + static { + filter.add(new PowerPredicate(ComparisonType.MORE_THAN, 1)); + } + + public ArcticFoxes(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{1}{W}"); + + this.subtype.add(SubType.FOX); + this.power = new MageInt(1); + this.toughness = new MageInt(1); + + // Creatures with power 2 or greater can't block Arctic Foxes as long as defending player controls a snow land. + this.addAbility(new SimpleStaticAbility(new ConditionalContinuousEffect( + new CantBeBlockedByCreaturesSourceEffect(filter, Duration.WhileOnBattlefield), + ArcticFoxesCondition.instance, "creatures with power 2 or greater can't block {this}" + + " as long as defending player controls a snow land" + ))); + } + + private ArcticFoxes(final ArcticFoxes card) { + super(card); + } + + @Override + public ArcticFoxes copy() { + return new ArcticFoxes(this); + } +} + +enum ArcticFoxesCondition implements Condition { + instance; + + private static final FilterPermanent filter = new FilterLandPermanent(); + + static { + filter.add(new SupertypePredicate(SuperType.SNOW)); + } + + @Override + public boolean apply(Game game, Ability source) { + UUID defenderId = game.getCombat().getDefendingPlayerId(source.getSourceId(), game); + if (defenderId == null) { + return false; + } + return game.getBattlefield().contains(filter, defenderId, 1, game); + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/IceAge.java b/Mage.Sets/src/mage/sets/IceAge.java index 5c0ab4bc85..a31cc9790a 100644 --- a/Mage.Sets/src/mage/sets/IceAge.java +++ b/Mage.Sets/src/mage/sets/IceAge.java @@ -32,6 +32,7 @@ public final class IceAge extends ExpansionSet { cards.add(new SetCardInfo("Aggression", 169, Rarity.UNCOMMON, mage.cards.a.Aggression.class)); cards.add(new SetCardInfo("Altar of Bone", 281, Rarity.RARE, mage.cards.a.AltarOfBone.class)); cards.add(new SetCardInfo("Anarchy", 170, Rarity.UNCOMMON, mage.cards.a.Anarchy.class)); + cards.add(new SetCardInfo("Arctic Foxes", 226, Rarity.COMMON, mage.cards.a.ArcticFoxes.class)); cards.add(new SetCardInfo("Arenson's Aura", 3, Rarity.COMMON, mage.cards.a.ArensonsAura.class)); cards.add(new SetCardInfo("Armor of Faith", 4, Rarity.COMMON, mage.cards.a.ArmorOfFaith.class)); cards.add(new SetCardInfo("Arnjlot's Ascent", 57, Rarity.COMMON, mage.cards.a.ArnjlotsAscent.class)); From 24458d66a5945cde185719aa3e5eeef21496bdb8 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 3 Oct 2019 13:32:41 -0400 Subject: [PATCH 322/373] Implemented Gaea's Balance --- Mage.Sets/src/mage/cards/g/GaeasBalance.java | 104 +++++++++++++++++++ Mage.Sets/src/mage/sets/Apocalypse.java | 1 + Mage.Sets/src/mage/sets/IceAge.java | 2 +- 3 files changed, 106 insertions(+), 1 deletion(-) create mode 100644 Mage.Sets/src/mage/cards/g/GaeasBalance.java diff --git a/Mage.Sets/src/mage/cards/g/GaeasBalance.java b/Mage.Sets/src/mage/cards/g/GaeasBalance.java new file mode 100644 index 0000000000..178cdcee8f --- /dev/null +++ b/Mage.Sets/src/mage/cards/g/GaeasBalance.java @@ -0,0 +1,104 @@ +package mage.cards.g; + +import mage.abilities.Ability; +import mage.abilities.costs.common.SacrificeTargetCost; +import mage.abilities.effects.OneShotEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.cards.Cards; +import mage.cards.CardsImpl; +import mage.constants.CardType; +import mage.constants.Outcome; +import mage.constants.SubType; +import mage.constants.Zone; +import mage.filter.FilterCard; +import mage.filter.StaticFilters; +import mage.filter.common.FilterLandCard; +import mage.filter.predicate.mageobject.SubtypePredicate; +import mage.game.Game; +import mage.players.Player; +import mage.target.common.TargetCardInLibrary; +import mage.target.common.TargetControlledPermanent; + +import java.util.Arrays; +import java.util.List; +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class GaeasBalance extends CardImpl { + + public GaeasBalance(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.SORCERY}, "{3}{G}"); + + // As an additional cost to cast Gaea's Balance, sacrifice five lands. + this.getSpellAbility().addCost(new SacrificeTargetCost( + new TargetControlledPermanent(5, StaticFilters.FILTER_CONTROLLED_LAND_SHORT_TEXT) + )); + + // Search your library for a land card of each basic land type and put them onto the battlefield. Then shuffle your library. + this.getSpellAbility().addEffect(new GaeasBalanceEffect()); + } + + private GaeasBalance(final GaeasBalance card) { + super(card); + } + + @Override + public GaeasBalance copy() { + return new GaeasBalance(this); + } +} + +class GaeasBalanceEffect extends OneShotEffect { + + private static final FilterCard plainsFilter = new FilterLandCard("a Plains land card"); + private static final FilterCard islandFilter = new FilterLandCard("an Island land card"); + private static final FilterCard swampFilter = new FilterLandCard("a Swamp land card"); + private static final FilterCard mountainFilter = new FilterLandCard("a Mountain land card"); + private static final FilterCard forestFilter = new FilterLandCard("a Forest land card"); + + static { + plainsFilter.add(new SubtypePredicate(SubType.PLAINS)); + islandFilter.add(new SubtypePredicate(SubType.ISLAND)); + swampFilter.add(new SubtypePredicate(SubType.SWAMP)); + mountainFilter.add(new SubtypePredicate(SubType.MOUNTAIN)); + forestFilter.add(new SubtypePredicate(SubType.FOREST)); + } + + private static final List filterList = Arrays.asList( + plainsFilter, islandFilter, swampFilter, mountainFilter, forestFilter + ); + + GaeasBalanceEffect() { + super(Outcome.Benefit); + staticText = "Search your library for a land card of each basic land type " + + "and put them onto the battlefield. Then shuffle your library."; + } + + private GaeasBalanceEffect(final GaeasBalanceEffect effect) { + super(effect); + } + + @Override + public GaeasBalanceEffect copy() { + return new GaeasBalanceEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + Player player = game.getPlayer(source.getControllerId()); + if (player == null) { + return false; + } + Cards cards = new CardsImpl(); + filterList.stream().map(TargetCardInLibrary::new).forEachOrdered(target -> { + player.searchLibrary(target, source, game, target.getFilter().getMessage().contains("Forest")); + cards.add(target.getFirstTarget()); + }); + player.moveCards(cards, Zone.BATTLEFIELD, source, game); + player.shuffleLibrary(source, game); + return true; + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/Apocalypse.java b/Mage.Sets/src/mage/sets/Apocalypse.java index e327b2f80c..787c55c20a 100644 --- a/Mage.Sets/src/mage/sets/Apocalypse.java +++ b/Mage.Sets/src/mage/sets/Apocalypse.java @@ -66,6 +66,7 @@ public final class Apocalypse extends ExpansionSet { cards.add(new SetCardInfo("Flowstone Charger", 99, Rarity.UNCOMMON, mage.cards.f.FlowstoneCharger.class)); cards.add(new SetCardInfo("Foul Presence", 39, Rarity.UNCOMMON, mage.cards.f.FoulPresence.class)); cards.add(new SetCardInfo("Fungal Shambler", 100, Rarity.RARE, mage.cards.f.FungalShambler.class)); + cards.add(new SetCardInfo("Gaea's Balance", 77, Rarity.UNCOMMON, mage.cards.g.GaeasBalance.class)); cards.add(new SetCardInfo("Gaea's Skyfolk", 101, Rarity.COMMON, mage.cards.g.GaeasSkyfolk.class)); cards.add(new SetCardInfo("Gerrard Capashen", 11, Rarity.RARE, mage.cards.g.GerrardCapashen.class)); cards.add(new SetCardInfo("Gerrard's Verdict", 102, Rarity.UNCOMMON, mage.cards.g.GerrardsVerdict.class)); diff --git a/Mage.Sets/src/mage/sets/IceAge.java b/Mage.Sets/src/mage/sets/IceAge.java index a31cc9790a..061733516b 100644 --- a/Mage.Sets/src/mage/sets/IceAge.java +++ b/Mage.Sets/src/mage/sets/IceAge.java @@ -32,7 +32,7 @@ public final class IceAge extends ExpansionSet { cards.add(new SetCardInfo("Aggression", 169, Rarity.UNCOMMON, mage.cards.a.Aggression.class)); cards.add(new SetCardInfo("Altar of Bone", 281, Rarity.RARE, mage.cards.a.AltarOfBone.class)); cards.add(new SetCardInfo("Anarchy", 170, Rarity.UNCOMMON, mage.cards.a.Anarchy.class)); - cards.add(new SetCardInfo("Arctic Foxes", 226, Rarity.COMMON, mage.cards.a.ArcticFoxes.class)); + cards.add(new SetCardInfo("Arctic Foxes", 2, Rarity.COMMON, mage.cards.a.ArcticFoxes.class)); cards.add(new SetCardInfo("Arenson's Aura", 3, Rarity.COMMON, mage.cards.a.ArensonsAura.class)); cards.add(new SetCardInfo("Armor of Faith", 4, Rarity.COMMON, mage.cards.a.ArmorOfFaith.class)); cards.add(new SetCardInfo("Arnjlot's Ascent", 57, Rarity.COMMON, mage.cards.a.ArnjlotsAscent.class)); From 67a1f6794afb731bb784a20eb1f34e6d3306e264 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 3 Oct 2019 13:50:20 -0400 Subject: [PATCH 323/373] Implemented Elvish Healer --- Mage.Sets/src/mage/cards/e/ElvishHealer.java | 79 ++++++++++++++++++++ Mage.Sets/src/mage/sets/IceAge.java | 1 + 2 files changed, 80 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/e/ElvishHealer.java diff --git a/Mage.Sets/src/mage/cards/e/ElvishHealer.java b/Mage.Sets/src/mage/cards/e/ElvishHealer.java new file mode 100644 index 0000000000..2719974459 --- /dev/null +++ b/Mage.Sets/src/mage/cards/e/ElvishHealer.java @@ -0,0 +1,79 @@ +package mage.cards.e; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.costs.common.TapSourceCost; +import mage.abilities.effects.OneShotEffect; +import mage.abilities.effects.common.PreventDamageToTargetEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.Outcome; +import mage.constants.SubType; +import mage.game.Game; +import mage.game.permanent.Permanent; +import mage.target.common.TargetAnyTarget; +import mage.target.targetpointer.FixedTarget; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class ElvishHealer extends CardImpl { + + public ElvishHealer(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{2}{W}"); + + this.subtype.add(SubType.ELF); + this.subtype.add(SubType.CLERIC); + this.power = new MageInt(1); + this.toughness = new MageInt(2); + + // {T}: Prevent the next 1 damage that would be dealt to any target this turn. If it’s a green creature, prevent the next 2 damage instead. + Ability ability = new SimpleActivatedAbility(new ElvishHealerEffect(), new TapSourceCost()); + ability.addTarget(new TargetAnyTarget()); + this.addAbility(ability); + } + + private ElvishHealer(final ElvishHealer card) { + super(card); + } + + @Override + public ElvishHealer copy() { + return new ElvishHealer(this); + } +} + +class ElvishHealerEffect extends OneShotEffect { + + ElvishHealerEffect() { + super(Outcome.Benefit); + staticText = "Prevent the next 1 damage that would be dealt to any target this turn. " + + "If it’s a green creature, prevent the next 2 damage instead."; + } + + private ElvishHealerEffect(final ElvishHealerEffect effect) { + super(effect); + } + + @Override + public ElvishHealerEffect copy() { + return new ElvishHealerEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + int toPrevent = 1; + Permanent permanent = game.getPermanent(source.getFirstTarget()); + if (permanent != null && permanent.isCreature() && permanent.getColor(game).isGreen()) { + toPrevent = 2; + } + game.addEffect(new PreventDamageToTargetEffect(Duration.EndOfTurn, toPrevent) + .setTargetPointer(new FixedTarget(source.getFirstTarget(), game)), source); + return true; + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/IceAge.java b/Mage.Sets/src/mage/sets/IceAge.java index 061733516b..c2cbf137b0 100644 --- a/Mage.Sets/src/mage/sets/IceAge.java +++ b/Mage.Sets/src/mage/sets/IceAge.java @@ -100,6 +100,7 @@ public final class IceAge extends ExpansionSet { cards.add(new SetCardInfo("Elder Druid", 232, Rarity.RARE, mage.cards.e.ElderDruid.class)); cards.add(new SetCardInfo("Elemental Augury", 286, Rarity.RARE, mage.cards.e.ElementalAugury.class)); cards.add(new SetCardInfo("Elkin Bottle", 317, Rarity.RARE, mage.cards.e.ElkinBottle.class)); + cards.add(new SetCardInfo("Elvish Healer", 246, Rarity.COMMON, mage.cards.e.ElvishHealer.class)); cards.add(new SetCardInfo("Enduring Renewal", 23, Rarity.RARE, mage.cards.e.EnduringRenewal.class)); cards.add(new SetCardInfo("Energy Storm", 24, Rarity.RARE, mage.cards.e.EnergyStorm.class)); cards.add(new SetCardInfo("Enervate", 67, Rarity.COMMON, mage.cards.e.Enervate.class)); From 29096965a6cc50d7b380d7d0b57d5b736543f7ef Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 3 Oct 2019 14:08:09 -0400 Subject: [PATCH 324/373] Implemented Snowblind --- Mage.Sets/src/mage/cards/s/Snowblind.java | 103 ++++++++++++++++++++++ Mage.Sets/src/mage/sets/IceAge.java | 5 +- 2 files changed, 105 insertions(+), 3 deletions(-) create mode 100644 Mage.Sets/src/mage/cards/s/Snowblind.java diff --git a/Mage.Sets/src/mage/cards/s/Snowblind.java b/Mage.Sets/src/mage/cards/s/Snowblind.java new file mode 100644 index 0000000000..ee0d055176 --- /dev/null +++ b/Mage.Sets/src/mage/cards/s/Snowblind.java @@ -0,0 +1,103 @@ +package mage.cards.s; + +import mage.abilities.Ability; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.dynamicvalue.DynamicValue; +import mage.abilities.effects.Effect; +import mage.abilities.effects.common.AttachEffect; +import mage.abilities.effects.common.continuous.BoostEnchantedEffect; +import mage.abilities.keyword.EnchantAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.*; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterLandPermanent; +import mage.filter.predicate.mageobject.SupertypePredicate; +import mage.game.Game; +import mage.game.permanent.Permanent; +import mage.target.TargetPermanent; +import mage.target.common.TargetCreaturePermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class Snowblind extends CardImpl { + + public Snowblind(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ENCHANTMENT}, "{3}{G}"); + + this.subtype.add(SubType.AURA); + + // Enchant creature + TargetPermanent auraTarget = new TargetCreaturePermanent(); + this.getSpellAbility().addTarget(auraTarget); + this.getSpellAbility().addEffect(new AttachEffect(Outcome.BoostCreature)); + Ability ability = new EnchantAbility(auraTarget.getTargetName()); + this.addAbility(ability); + + // Enchanted creature gets -X/-Y. If that creature is attacking, X is the number of snow lands defending player controls. Otherwise, X is the number of snow lands its controller controls. Y is equal to X or to enchanted creature's toughness minus 1, whichever is smaller. + this.addAbility(new SimpleStaticAbility(new BoostEnchantedEffect( + SnowblindValue.instanceX, SnowblindValue.instanceY, Duration.WhileOnBattlefield + ).setText("Enchanted creature gets -X/-Y. If that creature is attacking, " + + "X is the number of snow lands defending player controls. " + + "Otherwise, X is the number of snow lands its controller controls. " + + "Y is equal to X or to enchanted creature's toughness minus 1, whichever is smaller." + ))); + } + + private Snowblind(final Snowblind card) { + super(card); + } + + @Override + public Snowblind copy() { + return new Snowblind(this); + } +} + +enum SnowblindValue implements DynamicValue { + instanceX, + instanceY; + + private static final FilterPermanent filter = new FilterLandPermanent(); + + static { + filter.add(new SupertypePredicate(SuperType.SNOW)); + } + + @Override + public int calculate(Game game, Ability sourceAbility, Effect effect) { + Permanent sourcePerm = game.getPermanent(sourceAbility.getSourceId()); + if (sourcePerm == null) { + return 0; + } + Permanent permanent = game.getPermanent(sourcePerm.getAttachedTo()); + if (permanent == null) { + return 0; + } + int xValue = 0; + if (permanent.isAttacking()) { + xValue = game.getBattlefield().countAll( + filter, game.getCombat().getDefendingPlayerId(permanent.getId(), game), game + ); + } else { + xValue = game.getBattlefield().countAll(filter, permanent.getControllerId(), game); + } + if (this == instanceX) { + return -xValue; + } + return -Math.min(xValue, permanent.getToughness().getValue() - 1); + } + + @Override + public DynamicValue copy() { + return this; + } + + @Override + public String getMessage() { + return ""; + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/IceAge.java b/Mage.Sets/src/mage/sets/IceAge.java index c2cbf137b0..f142cdf8c6 100644 --- a/Mage.Sets/src/mage/sets/IceAge.java +++ b/Mage.Sets/src/mage/sets/IceAge.java @@ -100,7 +100,7 @@ public final class IceAge extends ExpansionSet { cards.add(new SetCardInfo("Elder Druid", 232, Rarity.RARE, mage.cards.e.ElderDruid.class)); cards.add(new SetCardInfo("Elemental Augury", 286, Rarity.RARE, mage.cards.e.ElementalAugury.class)); cards.add(new SetCardInfo("Elkin Bottle", 317, Rarity.RARE, mage.cards.e.ElkinBottle.class)); - cards.add(new SetCardInfo("Elvish Healer", 246, Rarity.COMMON, mage.cards.e.ElvishHealer.class)); + cards.add(new SetCardInfo("Elvish Healer", 22, Rarity.COMMON, mage.cards.e.ElvishHealer.class)); cards.add(new SetCardInfo("Enduring Renewal", 23, Rarity.RARE, mage.cards.e.EnduringRenewal.class)); cards.add(new SetCardInfo("Energy Storm", 24, Rarity.RARE, mage.cards.e.EnergyStorm.class)); cards.add(new SetCardInfo("Enervate", 67, Rarity.COMMON, mage.cards.e.Enervate.class)); @@ -120,8 +120,6 @@ public final class IceAge extends ExpansionSet { cards.add(new SetCardInfo("Forbidden Lore", 236, Rarity.RARE, mage.cards.f.ForbiddenLore.class)); cards.add(new SetCardInfo("Force Void", 70, Rarity.UNCOMMON, mage.cards.f.ForceVoid.class)); cards.add(new SetCardInfo("Forest", 380, Rarity.LAND, mage.cards.basiclands.Forest.class, NON_FULL_USE_VARIOUS)); - cards.add(new SetCardInfo("Forest", 381, Rarity.LAND, mage.cards.basiclands.Forest.class, NON_FULL_USE_VARIOUS)); - cards.add(new SetCardInfo("Forest", 382, Rarity.LAND, mage.cards.basiclands.Forest.class, NON_FULL_USE_VARIOUS)); cards.add(new SetCardInfo("Forgotten Lore", 237, Rarity.UNCOMMON, mage.cards.f.ForgottenLore.class)); cards.add(new SetCardInfo("Formation", 25, Rarity.RARE, mage.cards.f.Formation.class)); cards.add(new SetCardInfo("Foul Familiar", 126, Rarity.COMMON, mage.cards.f.FoulFamiliar.class)); @@ -311,6 +309,7 @@ public final class IceAge extends ExpansionSet { cards.add(new SetCardInfo("Snow-Covered Mountain", 379, Rarity.LAND, mage.cards.s.SnowCoveredMountain.class)); cards.add(new SetCardInfo("Snow-Covered Plains", 367, Rarity.LAND, mage.cards.s.SnowCoveredPlains.class)); cards.add(new SetCardInfo("Snow-Covered Swamp", 372, Rarity.LAND, mage.cards.s.SnowCoveredSwamp.class)); + cards.add(new SetCardInfo("Snowblind", 264, Rarity.RARE, mage.cards.s.Snowblind.class)); cards.add(new SetCardInfo("Soldevi Golem", 338, Rarity.RARE, mage.cards.s.SoldeviGolem.class)); cards.add(new SetCardInfo("Soldevi Machinist", 102, Rarity.UNCOMMON, mage.cards.s.SoldeviMachinist.class)); cards.add(new SetCardInfo("Soldevi Simulacrum", 339, Rarity.UNCOMMON, mage.cards.s.SoldeviSimulacrum.class)); From bc8cfab6799b2960cbfd554da01df66cdc08e7bd Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 3 Oct 2019 16:04:54 -0400 Subject: [PATCH 325/373] Implemented Grizzled Wolverine --- .../src/mage/cards/g/GrizzledWolverine.java | 65 +++++++++++++++++++ Mage.Sets/src/mage/sets/IceAge.java | 1 + 2 files changed, 66 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/g/GrizzledWolverine.java diff --git a/Mage.Sets/src/mage/cards/g/GrizzledWolverine.java b/Mage.Sets/src/mage/cards/g/GrizzledWolverine.java new file mode 100644 index 0000000000..18712cb7da --- /dev/null +++ b/Mage.Sets/src/mage/cards/g/GrizzledWolverine.java @@ -0,0 +1,65 @@ +package mage.cards.g; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.LimitedTimesPerTurnActivatedAbility; +import mage.abilities.condition.Condition; +import mage.abilities.costs.mana.ManaCostsImpl; +import mage.abilities.effects.common.continuous.BoostSourceEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.*; +import mage.game.Game; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class GrizzledWolverine extends CardImpl { + + public GrizzledWolverine(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{1}{R}{R}"); + + this.subtype.add(SubType.WOLVERINE); + this.power = new MageInt(2); + this.toughness = new MageInt(2); + + // {R}: Grizzled Wolverine gets +2/+0 until end of turn. Activate this ability only during the declare blockers step, only if at least one creature is blocking Grizzled Wolverine, and only once each turn. + this.addAbility(new LimitedTimesPerTurnActivatedAbility( + Zone.BATTLEFIELD, new BoostSourceEffect(2, 0, Duration.EndOfTurn), + new ManaCostsImpl("{R}"), 1, GrizzledWolverineCondition.instance + )); + } + + private GrizzledWolverine(final GrizzledWolverine card) { + super(card); + } + + @Override + public GrizzledWolverine copy() { + return new GrizzledWolverine(this); + } +} + +enum GrizzledWolverineCondition implements Condition { + instance; + + @Override + public boolean apply(Game game, Ability source) { + if (game.getPhase().getStep().getType() != PhaseStep.DECLARE_BLOCKERS) { + return false; + } + return game + .getCombat() + .getGroups() + .stream() + .anyMatch(combatGroup -> combatGroup.getAttackers().contains(source.getSourceId()) + && !combatGroup.getBlockers().isEmpty()); + } + + @Override + public String toString() { + return "during the declare blockers step, only if at least one creature is blocking {this},"; + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/IceAge.java b/Mage.Sets/src/mage/sets/IceAge.java index f142cdf8c6..644cac60c7 100644 --- a/Mage.Sets/src/mage/sets/IceAge.java +++ b/Mage.Sets/src/mage/sets/IceAge.java @@ -150,6 +150,7 @@ public final class IceAge extends ExpansionSet { cards.add(new SetCardInfo("Gorilla Pack", 247, Rarity.COMMON, mage.cards.g.GorillaPack.class)); cards.add(new SetCardInfo("Gravebind", 129, Rarity.RARE, mage.cards.g.Gravebind.class)); cards.add(new SetCardInfo("Green Scarab", 28, Rarity.UNCOMMON, mage.cards.g.GreenScarab.class)); + cards.add(new SetCardInfo("Grizzled Wolverine", 192, Rarity.COMMON, mage.cards.g.GrizzledWolverine.class)); cards.add(new SetCardInfo("Hallowed Ground", 29, Rarity.UNCOMMON, mage.cards.h.HallowedGround.class)); cards.add(new SetCardInfo("Halls of Mist", 354, Rarity.RARE, mage.cards.h.HallsOfMist.class)); cards.add(new SetCardInfo("Heal", 30, Rarity.COMMON, mage.cards.h.Heal.class)); From 2d14a1d12e6d35f36e5402310012f7aa9a0bc5e3 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 3 Oct 2019 16:39:38 -0400 Subject: [PATCH 326/373] Implemented Essence Vortex --- Mage.Sets/src/mage/cards/e/EssenceVortex.java | 69 +++++++++++++++++++ Mage.Sets/src/mage/sets/IceAge.java | 1 + 2 files changed, 70 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/e/EssenceVortex.java diff --git a/Mage.Sets/src/mage/cards/e/EssenceVortex.java b/Mage.Sets/src/mage/cards/e/EssenceVortex.java new file mode 100644 index 0000000000..72256d7394 --- /dev/null +++ b/Mage.Sets/src/mage/cards/e/EssenceVortex.java @@ -0,0 +1,69 @@ +package mage.cards.e; + +import mage.abilities.Ability; +import mage.abilities.costs.Cost; +import mage.abilities.costs.common.PayLifeCost; +import mage.abilities.effects.OneShotEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Outcome; +import mage.game.Game; +import mage.game.permanent.Permanent; +import mage.target.common.TargetCreaturePermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class EssenceVortex extends CardImpl { + + public EssenceVortex(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.INSTANT}, "{1}{U}{B}"); + + // Destroy target creature unless its controller pays life equal to its toughness. A creature destroyed this way can't be regenerated. + this.getSpellAbility().addEffect(new EssenceVortexEffect()); + this.getSpellAbility().addTarget(new TargetCreaturePermanent()); + } + + private EssenceVortex(final EssenceVortex card) { + super(card); + } + + @Override + public EssenceVortex copy() { + return new EssenceVortex(this); + } +} + +class EssenceVortexEffect extends OneShotEffect { + + EssenceVortexEffect() { + super(Outcome.Benefit); + staticText = "Destroy target creature unless its controller pays life equal to its toughness. " + + "A creature destroyed this way can't be regenerated."; + } + + private EssenceVortexEffect(final EssenceVortexEffect effect) { + super(effect); + } + + @Override + public EssenceVortexEffect copy() { + return new EssenceVortexEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + Permanent permanent = game.getPermanent(source.getFirstTarget()); + if (permanent == null) { + return false; + } + Cost cost = new PayLifeCost(permanent.getToughness().getValue()); + if (cost.pay(source, game, source.getSourceId(), permanent.getControllerId(), true)) { + return true; + } + return permanent.destroy(source.getSourceId(), game, true); + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/IceAge.java b/Mage.Sets/src/mage/sets/IceAge.java index 644cac60c7..1e22abab70 100644 --- a/Mage.Sets/src/mage/sets/IceAge.java +++ b/Mage.Sets/src/mage/sets/IceAge.java @@ -108,6 +108,7 @@ public final class IceAge extends ExpansionSet { cards.add(new SetCardInfo("Errantry", 183, Rarity.COMMON, mage.cards.e.Errantry.class)); cards.add(new SetCardInfo("Essence Filter", 233, Rarity.COMMON, mage.cards.e.EssenceFilter.class)); cards.add(new SetCardInfo("Essence Flare", 69, Rarity.COMMON, mage.cards.e.EssenceFlare.class)); + cards.add(new SetCardInfo("Essence Vortex", 287, Rarity.UNCOMMON, mage.cards.e.EssenceVortex.class)); cards.add(new SetCardInfo("Fanatical Fever", 234, Rarity.UNCOMMON, mage.cards.f.FanaticalFever.class)); cards.add(new SetCardInfo("Fear", 124, Rarity.COMMON, mage.cards.f.Fear.class)); cards.add(new SetCardInfo("Fiery Justice", 288, Rarity.RARE, mage.cards.f.FieryJustice.class)); From 55173733e6d01c1f686f28cfc1001b8944fb926b Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 3 Oct 2019 16:58:45 -0400 Subject: [PATCH 327/373] Implemented Spirit Flare --- Mage.Sets/src/mage/cards/s/SpiritFlare.java | 94 +++++++++++++++++++++ Mage.Sets/src/mage/sets/Torment.java | 1 + 2 files changed, 95 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/s/SpiritFlare.java diff --git a/Mage.Sets/src/mage/cards/s/SpiritFlare.java b/Mage.Sets/src/mage/cards/s/SpiritFlare.java new file mode 100644 index 0000000000..c2b78762f6 --- /dev/null +++ b/Mage.Sets/src/mage/cards/s/SpiritFlare.java @@ -0,0 +1,94 @@ +package mage.cards.s; + +import mage.abilities.Ability; +import mage.abilities.costs.common.PayLifeCost; +import mage.abilities.costs.mana.ManaCostsImpl; +import mage.abilities.effects.OneShotEffect; +import mage.abilities.keyword.FlashbackAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Outcome; +import mage.constants.TargetController; +import mage.constants.TimingRule; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterAttackingOrBlockingCreature; +import mage.filter.common.FilterControlledCreaturePermanent; +import mage.filter.predicate.Predicates; +import mage.filter.predicate.permanent.ControllerPredicate; +import mage.filter.predicate.permanent.TappedPredicate; +import mage.game.Game; +import mage.game.permanent.Permanent; +import mage.target.TargetPermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class SpiritFlare extends CardImpl { + + private static final FilterPermanent filter + = new FilterControlledCreaturePermanent("untapped creature you control"); + private static final FilterPermanent filter2 + = new FilterAttackingOrBlockingCreature("attacking or blocking creature an opponent controls"); + + static { + filter.add(Predicates.not(TappedPredicate.instance)); + filter2.add(new ControllerPredicate(TargetController.OPPONENT)); + } + + public SpiritFlare(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.INSTANT}, "{3}{W}"); + + // Tap target untapped creature you control. If you do, it deals damage equal to its power to target attacking or blocking creature an opponent controls. + this.getSpellAbility().addEffect(new SpiritFlareEffect()); + this.getSpellAbility().addTarget(new TargetPermanent(filter)); + this.getSpellAbility().addTarget(new TargetPermanent(filter2)); + + // Flashback-{1}{W}, Pay 3 life. + FlashbackAbility ability = new FlashbackAbility(new ManaCostsImpl("{1}{W}"), TimingRule.INSTANT); + ability.addCost(new PayLifeCost(3)); + this.addAbility(ability); + } + + private SpiritFlare(final SpiritFlare card) { + super(card); + } + + @Override + public SpiritFlare copy() { + return new SpiritFlare(this); + } +} + +class SpiritFlareEffect extends OneShotEffect { + + SpiritFlareEffect() { + super(Outcome.Benefit); + staticText = "tap target untapped creature you control. If you do, " + + "it deals damage equal to its power to target attacking or blocking creature an opponent controls"; + } + + private SpiritFlareEffect(final SpiritFlareEffect effect) { + super(effect); + } + + @Override + public SpiritFlareEffect copy() { + return new SpiritFlareEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + Permanent permanent = game.getPermanent(source.getFirstTarget()); + if (permanent == null || !permanent.tap(game)) { + return false; + } + Permanent permanent1 = game.getPermanent(source.getTargets().get(1).getFirstTarget()); + if (permanent1 == null) { + return false; + } + return permanent1.damage(permanent.getPower().getValue(), permanent.getId(), game) > 0; + } +} diff --git a/Mage.Sets/src/mage/sets/Torment.java b/Mage.Sets/src/mage/sets/Torment.java index 71f87ed2f8..2680b1ba0c 100644 --- a/Mage.Sets/src/mage/sets/Torment.java +++ b/Mage.Sets/src/mage/sets/Torment.java @@ -147,6 +147,7 @@ public final class Torment extends ExpansionSet { cards.add(new SetCardInfo("Slithery Stalker", 84, Rarity.UNCOMMON, mage.cards.s.SlitheryStalker.class)); cards.add(new SetCardInfo("Sonic Seizure", 115, Rarity.COMMON, mage.cards.s.SonicSeizure.class)); cards.add(new SetCardInfo("Soul Scourge", 85, Rarity.COMMON, mage.cards.s.SoulScourge.class)); + cards.add(new SetCardInfo("Spirit Flare", 15, Rarity.COMMON, mage.cards.s.SpiritFlare.class)); cards.add(new SetCardInfo("Stern Judge", 16, Rarity.UNCOMMON, mage.cards.s.SternJudge.class)); cards.add(new SetCardInfo("Strength of Isolation", 17, Rarity.UNCOMMON, mage.cards.s.StrengthOfIsolation.class)); cards.add(new SetCardInfo("Strength of Lunacy", 86, Rarity.UNCOMMON, mage.cards.s.StrengthOfLunacy.class)); From 38c25eedb774c27603d7d3b326a8764febb04b6d Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 3 Oct 2019 18:12:28 -0400 Subject: [PATCH 328/373] Implemented Escaped Shapeshifter --- .../src/mage/cards/e/EscapedShapeshifter.java | 100 ++++++++++++++++++ Mage.Sets/src/mage/sets/Tempest.java | 1 + 2 files changed, 101 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/e/EscapedShapeshifter.java diff --git a/Mage.Sets/src/mage/cards/e/EscapedShapeshifter.java b/Mage.Sets/src/mage/cards/e/EscapedShapeshifter.java new file mode 100644 index 0000000000..93457726f3 --- /dev/null +++ b/Mage.Sets/src/mage/cards/e/EscapedShapeshifter.java @@ -0,0 +1,100 @@ +package mage.cards.e; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.effects.ContinuousEffectImpl; +import mage.abilities.keyword.FirstStrikeAbility; +import mage.abilities.keyword.FlyingAbility; +import mage.abilities.keyword.ProtectionAbility; +import mage.abilities.keyword.TrampleAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.*; +import mage.filter.StaticFilters; +import mage.filter.predicate.mageobject.ColorPredicate; +import mage.game.Game; +import mage.game.permanent.Permanent; + +import java.util.Collection; +import java.util.Objects; +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class EscapedShapeshifter extends CardImpl { + + public EscapedShapeshifter(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{3}{U}{U}"); + + this.subtype.add(SubType.SHAPESHIFTER); + this.power = new MageInt(3); + this.toughness = new MageInt(4); + + // As long as an opponent controls a creature with flying not named Escaped Shapeshifter, Escaped Shapeshifter has flying. The same is true for first strike, trample, and protection from any color. + this.addAbility(new SimpleStaticAbility(new EscapedShapeshifterEffect())); + } + + private EscapedShapeshifter(final EscapedShapeshifter card) { + super(card); + } + + @Override + public EscapedShapeshifter copy() { + return new EscapedShapeshifter(this); + } +} + +class EscapedShapeshifterEffect extends ContinuousEffectImpl { + + EscapedShapeshifterEffect() { + super(Duration.WhileOnBattlefield, Layer.AbilityAddingRemovingEffects_6, SubLayer.NA, Outcome.AddAbility); + this.addDependedToType(DependencyType.AddingAbility); + staticText = "As long as an opponent controls a creature with flying not named Escaped Shapeshifter, " + + "{this} has flying. The same is true for first strike, trample, and protection from any color."; + } + + private EscapedShapeshifterEffect(final EscapedShapeshifterEffect effect) { + super(effect); + } + + @Override + public boolean apply(Game game, Ability source) { + Permanent sourcePermanent = game.getPermanent(source.getSourceId()); + if (sourcePermanent == null) { + return false; + } + + game.getBattlefield() + .getActivePermanents( + StaticFilters.FILTER_OPPONENTS_PERMANENT_CREATURE, + source.getControllerId(), source.getSourceId(), game + ).stream() + .filter(Objects::nonNull) + .filter(permanent -> permanent.getName() != "Escaped Shapeshifter") + .map(Permanent::getAbilities) + .flatMap(Collection::stream).filter(EscapedShapeshifterEffect::checkAbility) + .forEach(ability -> sourcePermanent.addAbility(ability, source.getSourceId(), game)); + return true; + } + + private static boolean checkAbility(Ability ability) { + if (ability instanceof FlyingAbility + || ability instanceof FirstStrikeAbility + || ability instanceof TrampleAbility) { + return true; + } + return ability instanceof ProtectionAbility + && ((ProtectionAbility) ability) + .getFilter() + .getPredicates() + .stream() + .anyMatch(ColorPredicate.class::isInstance); + } + + @Override + public EscapedShapeshifterEffect copy() { + return new EscapedShapeshifterEffect(this); + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/Tempest.java b/Mage.Sets/src/mage/sets/Tempest.java index e1ec411d32..5e2ab52b91 100644 --- a/Mage.Sets/src/mage/sets/Tempest.java +++ b/Mage.Sets/src/mage/sets/Tempest.java @@ -112,6 +112,7 @@ public final class Tempest extends ExpansionSet { cards.add(new SetCardInfo("Energizer", 285, Rarity.RARE, mage.cards.e.Energizer.class)); cards.add(new SetCardInfo("Enfeeblement", 133, Rarity.COMMON, mage.cards.e.Enfeeblement.class)); cards.add(new SetCardInfo("Enraging Licid", 171, Rarity.UNCOMMON, mage.cards.e.EnragingLicid.class)); + cards.add(new SetCardInfo("Escaped Shapeshifter", 62, Rarity.RARE, mage.cards.e.EscapedShapeshifter.class)); cards.add(new SetCardInfo("Essence Bottle", 286, Rarity.UNCOMMON, mage.cards.e.EssenceBottle.class)); cards.add(new SetCardInfo("Evincar's Justice", 134, Rarity.COMMON, mage.cards.e.EvincarsJustice.class)); cards.add(new SetCardInfo("Excavator", 287, Rarity.UNCOMMON, mage.cards.e.Excavator.class)); From bf159edb78da204478cb166a0bba3a0a9b87bc0f Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 3 Oct 2019 18:24:13 -0400 Subject: [PATCH 329/373] Implemented Blind Fury --- Mage.Sets/src/mage/cards/b/BlindFury.java | 83 +++++++++++++++++++++++ Mage.Sets/src/mage/sets/Mirage.java | 1 + 2 files changed, 84 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/b/BlindFury.java diff --git a/Mage.Sets/src/mage/cards/b/BlindFury.java b/Mage.Sets/src/mage/cards/b/BlindFury.java new file mode 100644 index 0000000000..cd7a9bb007 --- /dev/null +++ b/Mage.Sets/src/mage/cards/b/BlindFury.java @@ -0,0 +1,83 @@ +package mage.cards.b; + +import mage.abilities.Ability; +import mage.abilities.effects.ReplacementEffectImpl; +import mage.abilities.effects.common.continuous.LoseAbilityAllEffect; +import mage.abilities.keyword.TrampleAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.Outcome; +import mage.filter.StaticFilters; +import mage.game.Game; +import mage.game.events.DamageCreatureEvent; +import mage.game.events.GameEvent; +import mage.game.permanent.Permanent; +import mage.util.CardUtil; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class BlindFury extends CardImpl { + + public BlindFury(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.INSTANT}, "{2}{R}{R}"); + + // All creatures lose trample until end of turn. If a creature would deal combat damage to a creature this turn, it deals double that damage to that creature instead. + this.getSpellAbility().addEffect(new LoseAbilityAllEffect( + TrampleAbility.getInstance(), Duration.EndOfTurn, + StaticFilters.FILTER_PERMANENT_CREATURES + ).setText("All creatures lose trample until end of turn.")); + this.getSpellAbility().addEffect(new FurnaceOfRathEffect()); + } + + private BlindFury(final BlindFury card) { + super(card); + } + + @Override + public BlindFury copy() { + return new BlindFury(this); + } +} + +class FurnaceOfRathEffect extends ReplacementEffectImpl { + + FurnaceOfRathEffect() { + super(Duration.EndOfTurn, Outcome.Damage); + staticText = "If a creature would deal combat damage to a creature this turn, " + + "it deals double that damage to that creature instead"; + } + + private FurnaceOfRathEffect(final FurnaceOfRathEffect effect) { + super(effect); + } + + @Override + public FurnaceOfRathEffect copy() { + return new FurnaceOfRathEffect(this); + } + + @Override + public boolean checksEventType(GameEvent event, Game game) { + return event.getType() == GameEvent.EventType.DAMAGE_CREATURE; + } + + @Override + public boolean applies(GameEvent event, Ability source, Game game) { + Permanent permanent = game.getPermanent(event.getSourceId()); + return permanent != null + && permanent.isCreature() + && ((DamageCreatureEvent) event).isCombatDamage(); + + } + + @Override + public boolean replaceEvent(GameEvent event, Ability source, Game game) { + event.setAmount(CardUtil.addWithOverflowCheck(event.getAmount(), event.getAmount())); + return false; + } +} diff --git a/Mage.Sets/src/mage/sets/Mirage.java b/Mage.Sets/src/mage/sets/Mirage.java index 5b885dbccd..2ec6544413 100644 --- a/Mage.Sets/src/mage/sets/Mirage.java +++ b/Mage.Sets/src/mage/sets/Mirage.java @@ -49,6 +49,7 @@ public final class Mirage extends ExpansionSet { cards.add(new SetCardInfo("Benthic Djinn", 257, Rarity.RARE, mage.cards.b.BenthicDjinn.class)); cards.add(new SetCardInfo("Binding Agony", 106, Rarity.COMMON, mage.cards.b.BindingAgony.class)); cards.add(new SetCardInfo("Blighted Shaman", 107, Rarity.UNCOMMON, mage.cards.b.BlightedShaman.class)); + cards.add(new SetCardInfo("Blind Fury", 158, Rarity.UNCOMMON, mage.cards.b.BlindFury.class)); cards.add(new SetCardInfo("Blinding Light", 5, Rarity.UNCOMMON, mage.cards.b.BlindingLight.class)); cards.add(new SetCardInfo("Blistering Barrier", 159, Rarity.COMMON, mage.cards.b.BlisteringBarrier.class)); cards.add(new SetCardInfo("Bone Harvest", 108, Rarity.COMMON, mage.cards.b.BoneHarvest.class)); From 69b06087f2433b804644250f9664794d5df3c738 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 3 Oct 2019 19:26:51 -0400 Subject: [PATCH 330/373] fixed a bug with Arctic Foxes --- Mage.Sets/src/mage/cards/a/ArcticFoxes.java | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/Mage.Sets/src/mage/cards/a/ArcticFoxes.java b/Mage.Sets/src/mage/cards/a/ArcticFoxes.java index 1c49ae5f02..a7a503331c 100644 --- a/Mage.Sets/src/mage/cards/a/ArcticFoxes.java +++ b/Mage.Sets/src/mage/cards/a/ArcticFoxes.java @@ -4,7 +4,7 @@ import mage.MageInt; import mage.abilities.Ability; import mage.abilities.common.SimpleStaticAbility; import mage.abilities.condition.Condition; -import mage.abilities.decorator.ConditionalContinuousEffect; +import mage.abilities.decorator.ConditionalRestrictionEffect; import mage.abilities.effects.common.combat.CantBeBlockedByCreaturesSourceEffect; import mage.cards.CardImpl; import mage.cards.CardSetInfo; @@ -37,7 +37,7 @@ public final class ArcticFoxes extends CardImpl { this.toughness = new MageInt(1); // Creatures with power 2 or greater can't block Arctic Foxes as long as defending player controls a snow land. - this.addAbility(new SimpleStaticAbility(new ConditionalContinuousEffect( + this.addAbility(new SimpleStaticAbility(new ConditionalRestrictionEffect( new CantBeBlockedByCreaturesSourceEffect(filter, Duration.WhileOnBattlefield), ArcticFoxesCondition.instance, "creatures with power 2 or greater can't block {this}" + " as long as defending player controls a snow land" From 193182aa3dfaa4000274b04e417fa161da86f7d6 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 3 Oct 2019 19:42:09 -0400 Subject: [PATCH 331/373] Implemented Mtenda Lion --- Mage.Sets/src/mage/cards/m/MtendaLion.java | 78 +++++++++++++++++++ Mage.Sets/src/mage/sets/Mirage.java | 1 + .../PreventCombatDamageBySourceEffect.java | 22 ++---- 3 files changed, 86 insertions(+), 15 deletions(-) create mode 100644 Mage.Sets/src/mage/cards/m/MtendaLion.java diff --git a/Mage.Sets/src/mage/cards/m/MtendaLion.java b/Mage.Sets/src/mage/cards/m/MtendaLion.java new file mode 100644 index 0000000000..cdda060084 --- /dev/null +++ b/Mage.Sets/src/mage/cards/m/MtendaLion.java @@ -0,0 +1,78 @@ +package mage.cards.m; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.AttacksTriggeredAbility; +import mage.abilities.costs.Cost; +import mage.abilities.costs.mana.ManaCostsImpl; +import mage.abilities.effects.OneShotEffect; +import mage.abilities.effects.common.PreventCombatDamageBySourceEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.Outcome; +import mage.constants.SubType; +import mage.game.Game; +import mage.players.Player; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class MtendaLion extends CardImpl { + + public MtendaLion(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{G}"); + + this.subtype.add(SubType.CAT); + this.power = new MageInt(2); + this.toughness = new MageInt(1); + + // Whenever Mtenda Lion attacks, defending player may pay {U}. If that player does, prevent all combat damage that would be dealt by Mtenda Lion this turn. + this.addAbility(new AttacksTriggeredAbility(new MtendaLionEffect(), false)); + } + + private MtendaLion(final MtendaLion card) { + super(card); + } + + @Override + public MtendaLion copy() { + return new MtendaLion(this); + } +} + +class MtendaLionEffect extends OneShotEffect { + + MtendaLionEffect() { + super(Outcome.Benefit); + staticText = "defending player may pay {U}. If that player does, " + + "prevent all combat damage that would be dealt by {this} this turn."; + } + + private MtendaLionEffect(final MtendaLionEffect effect) { + super(effect); + } + + @Override + public MtendaLionEffect copy() { + return new MtendaLionEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + Player player = game.getPlayer(game.getCombat().getDefendingPlayerId(source.getSourceId(), game)); + if (player == null) { + return false; + } + Cost cost = new ManaCostsImpl("{U}"); + if (!player.chooseUse(outcome, "Pay {U} to prevent damage?", source, game) + || !cost.pay(source, game, source.getSourceId(), player.getId(), false)) { + return false; + } + game.addEffect(new PreventCombatDamageBySourceEffect(Duration.EndOfTurn), source); + return true; + } +} diff --git a/Mage.Sets/src/mage/sets/Mirage.java b/Mage.Sets/src/mage/sets/Mirage.java index 2ec6544413..c71f19c42e 100644 --- a/Mage.Sets/src/mage/sets/Mirage.java +++ b/Mage.Sets/src/mage/sets/Mirage.java @@ -208,6 +208,7 @@ public final class Mirage extends ExpansionSet { cards.add(new SetCardInfo("Mountain", 346, Rarity.LAND, mage.cards.basiclands.Mountain.class, NON_FULL_USE_VARIOUS)); cards.add(new SetCardInfo("Mtenda Griffin", 28, Rarity.UNCOMMON, mage.cards.m.MtendaGriffin.class)); cards.add(new SetCardInfo("Mtenda Herder", 29, Rarity.COMMON, mage.cards.m.MtendaHerder.class)); + cards.add(new SetCardInfo("Mtenda Lion", 128, Rarity.COMMON, mage.cards.m.MtendaLion.class)); cards.add(new SetCardInfo("Mystical Tutor", 80, Rarity.UNCOMMON, mage.cards.m.MysticalTutor.class)); cards.add(new SetCardInfo("Natural Balance", 231, Rarity.RARE, mage.cards.n.NaturalBalance.class)); cards.add(new SetCardInfo("Nettletooth Djinn", 232, Rarity.UNCOMMON, mage.cards.n.NettletoothDjinn.class)); diff --git a/Mage/src/main/java/mage/abilities/effects/common/PreventCombatDamageBySourceEffect.java b/Mage/src/main/java/mage/abilities/effects/common/PreventCombatDamageBySourceEffect.java index 5c9c3fbb91..6f7abdc467 100644 --- a/Mage/src/main/java/mage/abilities/effects/common/PreventCombatDamageBySourceEffect.java +++ b/Mage/src/main/java/mage/abilities/effects/common/PreventCombatDamageBySourceEffect.java @@ -1,5 +1,3 @@ - - package mage.abilities.effects.common; import mage.abilities.Ability; @@ -9,33 +7,27 @@ import mage.game.Game; import mage.game.events.GameEvent; /** - * * @author jeffwadsworth */ public class PreventCombatDamageBySourceEffect extends PreventionEffectImpl { public PreventCombatDamageBySourceEffect(Duration duration) { - super(duration, Integer.MAX_VALUE, true); - staticText = "Prevent all combat damage that would be dealt by {this}" + duration.toString(); + super(duration, Integer.MAX_VALUE, true); + staticText = "Prevent all combat damage that would be dealt by {this}" + duration.toString(); } public PreventCombatDamageBySourceEffect(final PreventCombatDamageBySourceEffect effect) { - super(effect); + super(effect); } @Override public PreventCombatDamageBySourceEffect copy() { - return new PreventCombatDamageBySourceEffect(this); + return new PreventCombatDamageBySourceEffect(this); } @Override public boolean applies(GameEvent event, Ability source, Game game) { - if (super.applies(event, source, game)) { - if (event.getSourceId().equals(source.getSourceId())) { - return true; - } - } - return false; + return super.applies(event, source, game) + && event.getSourceId().equals(source.getSourceId()); } - -} \ No newline at end of file +} From be15f60e69c59cb042f5bacf32262b438528ad24 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 3 Oct 2019 20:05:03 -0400 Subject: [PATCH 332/373] Implemented Reign of Terror --- Mage.Sets/src/mage/cards/r/ReignOfTerror.java | 82 +++++++++++++++++++ Mage.Sets/src/mage/sets/Mirage.java | 1 + 2 files changed, 83 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/r/ReignOfTerror.java diff --git a/Mage.Sets/src/mage/cards/r/ReignOfTerror.java b/Mage.Sets/src/mage/cards/r/ReignOfTerror.java new file mode 100644 index 0000000000..c19cb0cd46 --- /dev/null +++ b/Mage.Sets/src/mage/cards/r/ReignOfTerror.java @@ -0,0 +1,82 @@ +package mage.cards.r; + +import mage.ObjectColor; +import mage.abilities.Ability; +import mage.abilities.effects.OneShotEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Outcome; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterCreaturePermanent; +import mage.filter.predicate.mageobject.ColorPredicate; +import mage.game.Game; +import mage.players.Player; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class ReignOfTerror extends CardImpl { + + public ReignOfTerror(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.SORCERY}, "{3}{B}{B}"); + + // Destroy all green creatures or all white creatures. They can't be regenerated. You lose 2 life for each creature that died this way. + this.getSpellAbility().addEffect(new ReignOfTerrorEffect()); + } + + private ReignOfTerror(final ReignOfTerror card) { + super(card); + } + + @Override + public ReignOfTerror copy() { + return new ReignOfTerror(this); + } +} + +class ReignOfTerrorEffect extends OneShotEffect { + + private static final FilterPermanent greenFilter = new FilterCreaturePermanent(); + private static final FilterPermanent whiteFilter = new FilterCreaturePermanent(); + + static { + greenFilter.add(new ColorPredicate(ObjectColor.GREEN)); + whiteFilter.add(new ColorPredicate(ObjectColor.WHITE)); + } + + ReignOfTerrorEffect() { + super(Outcome.Benefit); + staticText = "Destroy all green creatures or all white creatures. They can't be regenerated. " + + "You lose 2 life for each creature that died this way."; + } + + private ReignOfTerrorEffect(final ReignOfTerrorEffect effect) { + super(effect); + } + + @Override + public ReignOfTerrorEffect copy() { + return new ReignOfTerrorEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + Player player = game.getPlayer(source.getControllerId()); + if (player == null) { + return false; + } + FilterPermanent filter = player.chooseUse( + outcome, "Destroy all green creatures or all white creatures?", + "", "Green", "White", source, game + ) ? greenFilter : whiteFilter; + int died = game.getBattlefield() + .getActivePermanents(filter, source.getControllerId(), source.getSourceId(), game) + .stream() + .mapToInt(permanent -> permanent.destroy(source.getSourceId(), game, true) ? 1 : 0) + .sum(); + return player.loseLife(2 * died, game, false) > 0; + } +} diff --git a/Mage.Sets/src/mage/sets/Mirage.java b/Mage.Sets/src/mage/sets/Mirage.java index c71f19c42e..0c7f5f734b 100644 --- a/Mage.Sets/src/mage/sets/Mirage.java +++ b/Mage.Sets/src/mage/sets/Mirage.java @@ -250,6 +250,7 @@ public final class Mirage extends ExpansionSet { cards.add(new SetCardInfo("Reckless Embermage", 189, Rarity.RARE, mage.cards.r.RecklessEmbermage.class)); cards.add(new SetCardInfo("Regeneration", 236, Rarity.COMMON, mage.cards.r.Regeneration.class)); cards.add(new SetCardInfo("Reign of Chaos", 190, Rarity.UNCOMMON, mage.cards.r.ReignOfChaos.class)); + cards.add(new SetCardInfo("Reign of Terror", 35, Rarity.UNCOMMON, mage.cards.r.ReignOfTerror.class)); cards.add(new SetCardInfo("Reparations", 278, Rarity.RARE, mage.cards.r.Reparations.class)); cards.add(new SetCardInfo("Restless Dead", 138, Rarity.COMMON, mage.cards.r.RestlessDead.class)); cards.add(new SetCardInfo("Ritual of Steel", 36, Rarity.COMMON, mage.cards.r.RitualOfSteel.class)); From 90bdfe418398cd94a0da4328dfdaa9931b3fb4e9 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 3 Oct 2019 20:09:13 -0400 Subject: [PATCH 333/373] fixed numbering --- Mage.Sets/src/mage/sets/Mirage.java | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/Mage.Sets/src/mage/sets/Mirage.java b/Mage.Sets/src/mage/sets/Mirage.java index 0c7f5f734b..9f348e37d7 100644 --- a/Mage.Sets/src/mage/sets/Mirage.java +++ b/Mage.Sets/src/mage/sets/Mirage.java @@ -49,7 +49,7 @@ public final class Mirage extends ExpansionSet { cards.add(new SetCardInfo("Benthic Djinn", 257, Rarity.RARE, mage.cards.b.BenthicDjinn.class)); cards.add(new SetCardInfo("Binding Agony", 106, Rarity.COMMON, mage.cards.b.BindingAgony.class)); cards.add(new SetCardInfo("Blighted Shaman", 107, Rarity.UNCOMMON, mage.cards.b.BlightedShaman.class)); - cards.add(new SetCardInfo("Blind Fury", 158, Rarity.UNCOMMON, mage.cards.b.BlindFury.class)); + cards.add(new SetCardInfo("Blind Fury", 158, Rarity.UNCOMMON, mage.cards.b.BlindFury.class)); cards.add(new SetCardInfo("Blinding Light", 5, Rarity.UNCOMMON, mage.cards.b.BlindingLight.class)); cards.add(new SetCardInfo("Blistering Barrier", 159, Rarity.COMMON, mage.cards.b.BlisteringBarrier.class)); cards.add(new SetCardInfo("Bone Harvest", 108, Rarity.COMMON, mage.cards.b.BoneHarvest.class)); @@ -208,7 +208,7 @@ public final class Mirage extends ExpansionSet { cards.add(new SetCardInfo("Mountain", 346, Rarity.LAND, mage.cards.basiclands.Mountain.class, NON_FULL_USE_VARIOUS)); cards.add(new SetCardInfo("Mtenda Griffin", 28, Rarity.UNCOMMON, mage.cards.m.MtendaGriffin.class)); cards.add(new SetCardInfo("Mtenda Herder", 29, Rarity.COMMON, mage.cards.m.MtendaHerder.class)); - cards.add(new SetCardInfo("Mtenda Lion", 128, Rarity.COMMON, mage.cards.m.MtendaLion.class)); + cards.add(new SetCardInfo("Mtenda Lion", 230, Rarity.COMMON, mage.cards.m.MtendaLion.class)); cards.add(new SetCardInfo("Mystical Tutor", 80, Rarity.UNCOMMON, mage.cards.m.MysticalTutor.class)); cards.add(new SetCardInfo("Natural Balance", 231, Rarity.RARE, mage.cards.n.NaturalBalance.class)); cards.add(new SetCardInfo("Nettletooth Djinn", 232, Rarity.UNCOMMON, mage.cards.n.NettletoothDjinn.class)); @@ -250,7 +250,7 @@ public final class Mirage extends ExpansionSet { cards.add(new SetCardInfo("Reckless Embermage", 189, Rarity.RARE, mage.cards.r.RecklessEmbermage.class)); cards.add(new SetCardInfo("Regeneration", 236, Rarity.COMMON, mage.cards.r.Regeneration.class)); cards.add(new SetCardInfo("Reign of Chaos", 190, Rarity.UNCOMMON, mage.cards.r.ReignOfChaos.class)); - cards.add(new SetCardInfo("Reign of Terror", 35, Rarity.UNCOMMON, mage.cards.r.ReignOfTerror.class)); + cards.add(new SetCardInfo("Reign of Terror", 137, Rarity.UNCOMMON, mage.cards.r.ReignOfTerror.class)); cards.add(new SetCardInfo("Reparations", 278, Rarity.RARE, mage.cards.r.Reparations.class)); cards.add(new SetCardInfo("Restless Dead", 138, Rarity.COMMON, mage.cards.r.RestlessDead.class)); cards.add(new SetCardInfo("Ritual of Steel", 36, Rarity.COMMON, mage.cards.r.RitualOfSteel.class)); From 0283a26a3e1fa0747fc26f697b5a9b4adab6b9e0 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 3 Oct 2019 21:12:36 -0400 Subject: [PATCH 334/373] Implemented Stabilizer --- Mage.Sets/src/mage/cards/s/Stabilizer.java | 78 ++++++++++++++++++++++ Mage.Sets/src/mage/sets/Scourge.java | 1 + 2 files changed, 79 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/s/Stabilizer.java diff --git a/Mage.Sets/src/mage/cards/s/Stabilizer.java b/Mage.Sets/src/mage/cards/s/Stabilizer.java new file mode 100644 index 0000000000..bd70c9553e --- /dev/null +++ b/Mage.Sets/src/mage/cards/s/Stabilizer.java @@ -0,0 +1,78 @@ +package mage.cards.s; + +import mage.MageObject; +import mage.abilities.Ability; +import mage.abilities.LoyaltyAbility; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.effects.ContinuousRuleModifyingEffectImpl; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.Outcome; +import mage.game.Game; +import mage.game.events.GameEvent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class Stabilizer extends CardImpl { + + public Stabilizer(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT}, "{2}"); + + // Players can't cycle cards. + this.addAbility(new SimpleStaticAbility(new StabilizerEffect())); + } + + private Stabilizer(final Stabilizer card) { + super(card); + } + + @Override + public Stabilizer copy() { + return new Stabilizer(this); + } +} + +class StabilizerEffect extends ContinuousRuleModifyingEffectImpl { + + StabilizerEffect() { + super(Duration.WhileOnBattlefield, Outcome.Detriment); + staticText = "Players can't cycle cards"; + } + + private StabilizerEffect(final StabilizerEffect effect) { + super(effect); + } + + @Override + public StabilizerEffect copy() { + return new StabilizerEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + return true; + } + + @Override + public String getInfoMessage(Ability source, GameEvent event, Game game) { + MageObject mageObject = game.getObject(source.getSourceId()); + if (mageObject == null) { + return null; + } + return "You can't cycle cards (" + mageObject.getIdName() + ")."; + } + + @Override + public boolean applies(GameEvent event, Ability source, Game game) { + if (event.getType() != GameEvent.EventType.ACTIVATE_ABILITY) { + return false; + } + Ability ability = game.getAbility(event.getTargetId(), event.getSourceId()).orElse(null); + return ability instanceof LoyaltyAbility; + } +} diff --git a/Mage.Sets/src/mage/sets/Scourge.java b/Mage.Sets/src/mage/sets/Scourge.java index 51df2d1077..2ac19bcedc 100644 --- a/Mage.Sets/src/mage/sets/Scourge.java +++ b/Mage.Sets/src/mage/sets/Scourge.java @@ -143,6 +143,7 @@ public final class Scourge extends ExpansionSet { cards.add(new SetCardInfo("Soul Collector", 74, Rarity.RARE, mage.cards.s.SoulCollector.class)); cards.add(new SetCardInfo("Spark Spray", 105, Rarity.COMMON, mage.cards.s.SparkSpray.class)); cards.add(new SetCardInfo("Sprouting Vines", 128, Rarity.COMMON, mage.cards.s.SproutingVines.class)); + cards.add(new SetCardInfo("Stabilizer", 142, Rarity.RARE, mage.cards.s.Stabilizer.class)); cards.add(new SetCardInfo("Stifle", 52, Rarity.RARE, mage.cards.s.Stifle.class)); cards.add(new SetCardInfo("Sulfuric Vortex", 106, Rarity.RARE, mage.cards.s.SulfuricVortex.class)); cards.add(new SetCardInfo("Temple of the False God", 143, Rarity.UNCOMMON, mage.cards.t.TempleOfTheFalseGod.class)); From 517e92ec717dff92c7741a3175b2f60173b84baf Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 3 Oct 2019 21:21:10 -0400 Subject: [PATCH 335/373] Implemented Wall of Resistance --- .../src/mage/cards/w/WallOfResistance.java | 59 +++++++++++++++++++ Mage.Sets/src/mage/sets/Mirage.java | 1 + 2 files changed, 60 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/w/WallOfResistance.java diff --git a/Mage.Sets/src/mage/cards/w/WallOfResistance.java b/Mage.Sets/src/mage/cards/w/WallOfResistance.java new file mode 100644 index 0000000000..06099d7b1d --- /dev/null +++ b/Mage.Sets/src/mage/cards/w/WallOfResistance.java @@ -0,0 +1,59 @@ +package mage.cards.w; + +import mage.MageInt; +import mage.abilities.common.BeginningOfEndStepTriggeredAbility; +import mage.abilities.condition.Condition; +import mage.abilities.condition.common.SourceDealtDamageCondition; +import mage.abilities.decorator.ConditionalInterveningIfTriggeredAbility; +import mage.abilities.effects.common.counter.AddCountersSourceEffect; +import mage.abilities.keyword.DefenderAbility; +import mage.abilities.keyword.FlyingAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.constants.TargetController; +import mage.counters.CounterType; +import mage.watchers.common.DamageDoneWatcher; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class WallOfResistance extends CardImpl { + + private static final Condition condition = new SourceDealtDamageCondition(1); + + public WallOfResistance(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{1}{W}"); + + this.subtype.add(SubType.WALL); + this.power = new MageInt(0); + this.toughness = new MageInt(3); + + // Defender + this.addAbility(DefenderAbility.getInstance()); + + // Flying + this.addAbility(FlyingAbility.getInstance()); + + // At the beginning of each end step, if Wall of Resistance was dealt damage this turn, put a +0/+1 counter on it. + this.addAbility(new ConditionalInterveningIfTriggeredAbility( + new BeginningOfEndStepTriggeredAbility( + new AddCountersSourceEffect(CounterType.P0P1.createInstance()), + TargetController.ANY, false + ), condition, "At the beginning of each end step, " + + "if {this} was dealt damage this turn, put a +0/+1 counter on it." + ), new DamageDoneWatcher()); + } + + private WallOfResistance(final WallOfResistance card) { + super(card); + } + + @Override + public WallOfResistance copy() { + return new WallOfResistance(this); + } +} diff --git a/Mage.Sets/src/mage/sets/Mirage.java b/Mage.Sets/src/mage/sets/Mirage.java index 9f348e37d7..e1190f3f87 100644 --- a/Mage.Sets/src/mage/sets/Mirage.java +++ b/Mage.Sets/src/mage/sets/Mirage.java @@ -328,6 +328,7 @@ public final class Mirage extends ExpansionSet { cards.add(new SetCardInfo("Volcanic Dragon", 201, Rarity.RARE, mage.cards.v.VolcanicDragon.class)); cards.add(new SetCardInfo("Volcanic Geyser", 202, Rarity.UNCOMMON, mage.cards.v.VolcanicGeyser.class)); cards.add(new SetCardInfo("Waiting in the Weeds", 252, Rarity.RARE, mage.cards.w.WaitingInTheWeeds.class)); + cards.add(new SetCardInfo("Wall of Resistance", 46, Rarity.COMMON, mage.cards.w.WallOfResistance.class)); cards.add(new SetCardInfo("Wall of Roots", 253, Rarity.COMMON, mage.cards.w.WallOfRoots.class)); cards.add(new SetCardInfo("Ward of Lights", 47, Rarity.COMMON, mage.cards.w.WardOfLights.class)); cards.add(new SetCardInfo("Warping Wurm", 287, Rarity.RARE, mage.cards.w.WarpingWurm.class)); From 7abbddd0851a2aca856e4a7b3dfaa56d43e211ca Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 5 Oct 2019 13:10:33 -0400 Subject: [PATCH 336/373] Implemented Apathy --- Mage.Sets/src/mage/cards/a/Apathy.java | 93 +++++++++++++++++++++++ Mage.Sets/src/mage/sets/Weatherlight.java | 1 + 2 files changed, 94 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/a/Apathy.java diff --git a/Mage.Sets/src/mage/cards/a/Apathy.java b/Mage.Sets/src/mage/cards/a/Apathy.java new file mode 100644 index 0000000000..5469844970 --- /dev/null +++ b/Mage.Sets/src/mage/cards/a/Apathy.java @@ -0,0 +1,93 @@ +package mage.cards.a; + +import mage.abilities.Ability; +import mage.abilities.common.BeginningOfUpkeepTriggeredAbility; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.effects.OneShotEffect; +import mage.abilities.effects.common.AttachEffect; +import mage.abilities.effects.common.DontUntapInControllersUntapStepEnchantedEffect; +import mage.abilities.keyword.EnchantAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Outcome; +import mage.constants.SubType; +import mage.constants.TargetController; +import mage.game.Game; +import mage.game.permanent.Permanent; +import mage.players.Player; +import mage.target.TargetPermanent; +import mage.target.common.TargetCreaturePermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class Apathy extends CardImpl { + + public Apathy(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ENCHANTMENT}, "{U}"); + + this.subtype.add(SubType.AURA); + + // Enchant creature + TargetPermanent auraTarget = new TargetCreaturePermanent(); + this.getSpellAbility().addTarget(auraTarget); + this.getSpellAbility().addEffect(new AttachEffect(Outcome.BoostCreature)); + Ability ability = new EnchantAbility(auraTarget.getTargetName()); + this.addAbility(ability); + + // Enchanted creature doesn't untap during its controller's untap step. + this.addAbility(new SimpleStaticAbility(new DontUntapInControllersUntapStepEnchantedEffect())); + + // At the beginning of the upkeep of enchanted creature’s controller, that player may discard a card at random. If the player does, untap that creature. + this.addAbility(new BeginningOfUpkeepTriggeredAbility( + new ApathyEffect(), TargetController.CONTROLLER_ATTACHED_TO, false + )); + } + + private Apathy(final Apathy card) { + super(card); + } + + @Override + public Apathy copy() { + return new Apathy(this); + } +} + +class ApathyEffect extends OneShotEffect { + + ApathyEffect() { + super(Outcome.Benefit); + staticText = "that player may discard a card at random. If the player does, untap that creature"; + } + + private ApathyEffect(final ApathyEffect effect) { + super(effect); + } + + @Override + public ApathyEffect copy() { + return new ApathyEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + Player player = game.getPlayer(game.getActivePlayerId()); + if (player == null) { + return false; + } + if (!player.chooseUse(outcome, "Discard a card at random to untap enchanted creature?", source, game) + || player.discardOne(true, source, game) == null) { + return false; + } + Permanent permanent = game.getPermanent(source.getSourceId()); + if (permanent == null) { + return false; + } + permanent = game.getPermanent(permanent.getAttachedTo()); + return permanent != null && permanent.untap(game); + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/Weatherlight.java b/Mage.Sets/src/mage/sets/Weatherlight.java index b8be7cb40e..f93876f43d 100644 --- a/Mage.Sets/src/mage/sets/Weatherlight.java +++ b/Mage.Sets/src/mage/sets/Weatherlight.java @@ -38,6 +38,7 @@ public final class Weatherlight extends ExpansionSet { cards.add(new SetCardInfo("Alms", 3, Rarity.COMMON, mage.cards.a.Alms.class)); cards.add(new SetCardInfo("Ancestral Knowledge", 32, Rarity.RARE, mage.cards.a.AncestralKnowledge.class)); cards.add(new SetCardInfo("Angelic Renewal", 4, Rarity.COMMON, mage.cards.a.AngelicRenewal.class)); + cards.add(new SetCardInfo("Apathy", 33, Rarity.COMMON, mage.cards.a.Apathy.class)); cards.add(new SetCardInfo("Arctic Wolves", 118, Rarity.UNCOMMON, mage.cards.a.ArcticWolves.class)); cards.add(new SetCardInfo("Ardent Militia", 5, Rarity.COMMON, mage.cards.a.ArdentMilitia.class)); cards.add(new SetCardInfo("Argivian Find", 6, Rarity.UNCOMMON, mage.cards.a.ArgivianFind.class)); From e1c2f7954bd24c4882e702e4f290e718eda93d96 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 5 Oct 2019 13:18:43 -0400 Subject: [PATCH 337/373] Implemented Puffer Extract --- Mage.Sets/src/mage/cards/p/PufferExtract.java | 73 +++++++++++++++++++ Mage.Sets/src/mage/sets/MercadianMasques.java | 1 + 2 files changed, 74 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/p/PufferExtract.java diff --git a/Mage.Sets/src/mage/cards/p/PufferExtract.java b/Mage.Sets/src/mage/cards/p/PufferExtract.java new file mode 100644 index 0000000000..8005874a67 --- /dev/null +++ b/Mage.Sets/src/mage/cards/p/PufferExtract.java @@ -0,0 +1,73 @@ +package mage.cards.p; + +import mage.abilities.Ability; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.common.delayed.AtTheBeginOfNextEndStepDelayedTriggeredAbility; +import mage.abilities.costs.common.TapSourceCost; +import mage.abilities.costs.mana.ManaCostsImpl; +import mage.abilities.effects.OneShotEffect; +import mage.abilities.effects.common.DestroyTargetEffect; +import mage.abilities.effects.common.continuous.BoostTargetEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.Outcome; +import mage.game.Game; +import mage.target.common.TargetControlledCreaturePermanent; +import mage.target.targetpointer.FixedTarget; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class PufferExtract extends CardImpl { + + public PufferExtract(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT}, "{5}"); + + // {X}, {T}: Target creature you control gets +X/+X until end of turn. Destroy it at the beginning of the next end step. + Ability ability = new SimpleActivatedAbility(new PufferExtractEffect(), new ManaCostsImpl("{X}")); + ability.addCost(new TapSourceCost()); + ability.addTarget(new TargetControlledCreaturePermanent()); + this.addAbility(ability); + } + + private PufferExtract(final PufferExtract card) { + super(card); + } + + @Override + public PufferExtract copy() { + return new PufferExtract(this); + } +} + +class PufferExtractEffect extends OneShotEffect { + + PufferExtractEffect() { + super(Outcome.Benefit); + staticText = "Target creature you control gets +X/+X until end of turn. " + + "Destroy it at the beginning of the next end step."; + } + + private PufferExtractEffect(final PufferExtractEffect effect) { + super(effect); + } + + @Override + public PufferExtractEffect copy() { + return new PufferExtractEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + int xValue = source.getManaCostsToPay().getX(); + game.addEffect(new BoostTargetEffect(xValue, xValue, Duration.EndOfTurn), source); + game.addDelayedTriggeredAbility(new AtTheBeginOfNextEndStepDelayedTriggeredAbility( + new DestroyTargetEffect().setTargetPointer(new FixedTarget(source.getFirstTarget(), game)) + ), source); + return true; + } +} \ No newline at end of file diff --git a/Mage.Sets/src/mage/sets/MercadianMasques.java b/Mage.Sets/src/mage/sets/MercadianMasques.java index d1ed0a59ca..f715c64f41 100644 --- a/Mage.Sets/src/mage/sets/MercadianMasques.java +++ b/Mage.Sets/src/mage/sets/MercadianMasques.java @@ -235,6 +235,7 @@ public final class MercadianMasques extends ExpansionSet { cards.add(new SetCardInfo("Plains", 334, Rarity.LAND, mage.cards.basiclands.Plains.class, NON_FULL_USE_VARIOUS)); cards.add(new SetCardInfo("Power Matrix", 309, Rarity.RARE, mage.cards.p.PowerMatrix.class)); cards.add(new SetCardInfo("Primeval Shambler", 152, Rarity.UNCOMMON, mage.cards.p.PrimevalShambler.class)); + cards.add(new SetCardInfo("Puffer Extract", 310, Rarity.UNCOMMON, mage.cards.p.PufferExtract.class)); cards.add(new SetCardInfo("Pulverize", 207, Rarity.RARE, mage.cards.p.Pulverize.class)); cards.add(new SetCardInfo("Putrefaction", 153, Rarity.UNCOMMON, mage.cards.p.Putrefaction.class)); cards.add(new SetCardInfo("Puppet's Verdict", 208, Rarity.RARE, mage.cards.p.PuppetsVerdict.class)); From 65efdc36f5b850bfc64b9c47f8619be4757f489d Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sun, 6 Oct 2019 18:28:52 -0400 Subject: [PATCH 338/373] fixed Embercleave text (fixes #6008) --- Mage.Sets/src/mage/cards/e/Embercleave.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Mage.Sets/src/mage/cards/e/Embercleave.java b/Mage.Sets/src/mage/cards/e/Embercleave.java index a5a6c6936b..32480537b1 100644 --- a/Mage.Sets/src/mage/cards/e/Embercleave.java +++ b/Mage.Sets/src/mage/cards/e/Embercleave.java @@ -52,7 +52,7 @@ public final class Embercleave extends CardImpl { ability = new SimpleStaticAbility(new BoostEquippedEffect(1, 1)); ability.addEffect(new GainAbilityAttachedEffect( DoubleStrikeAbility.getInstance(), AttachmentType.EQUIPMENT - ).setText("and has first strike")); + ).setText("and has double strike strike")); ability.addEffect(new GainAbilityAttachedEffect( TrampleAbility.getInstance(), AttachmentType.EQUIPMENT ).setText("and trample")); From 45b3d391d733a56617a4f4ce5dd738c1235908cc Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sun, 6 Oct 2019 18:31:12 -0400 Subject: [PATCH 339/373] fixed Syr Faren, the Hengehammer's ability --- Mage.Sets/src/mage/cards/s/SyrFarenTheHengehammer.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Mage.Sets/src/mage/cards/s/SyrFarenTheHengehammer.java b/Mage.Sets/src/mage/cards/s/SyrFarenTheHengehammer.java index c4e4071fc7..85b8461de3 100644 --- a/Mage.Sets/src/mage/cards/s/SyrFarenTheHengehammer.java +++ b/Mage.Sets/src/mage/cards/s/SyrFarenTheHengehammer.java @@ -43,7 +43,7 @@ public final class SyrFarenTheHengehammer extends CardImpl { // Whenever Syr Faren, the Hengehammer attacks, another target attacking creature gets +X/+X until end of turn, where X is Syr Faren's power. Ability ability = new AttacksTriggeredAbility( - new BoostTargetEffect(xValue, xValue, Duration.EndOfTurn), false + new BoostTargetEffect(xValue, xValue, Duration.EndOfTurn, true), false ); ability.addTarget(new TargetPermanent(filter)); this.addAbility(ability); From f7b2ddda5680a550aba6d3b1a210459ee63f7055 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sun, 6 Oct 2019 18:40:41 -0400 Subject: [PATCH 340/373] Implemented Crimson Roc --- Mage.Sets/src/mage/cards/c/CrimsonRoc.java | 87 ++++++++++++++++++++++ Mage.Sets/src/mage/sets/Mirage.java | 1 + 2 files changed, 88 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/c/CrimsonRoc.java diff --git a/Mage.Sets/src/mage/cards/c/CrimsonRoc.java b/Mage.Sets/src/mage/cards/c/CrimsonRoc.java new file mode 100644 index 0000000000..6b7d68697c --- /dev/null +++ b/Mage.Sets/src/mage/cards/c/CrimsonRoc.java @@ -0,0 +1,87 @@ +package mage.cards.c; + +import mage.MageInt; +import mage.abilities.TriggeredAbilityImpl; +import mage.abilities.effects.common.continuous.BoostSourceEffect; +import mage.abilities.effects.common.continuous.GainAbilitySourceEffect; +import mage.abilities.keyword.FirstStrikeAbility; +import mage.abilities.keyword.FlyingAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; +import mage.constants.Zone; +import mage.game.Game; +import mage.game.events.GameEvent; +import mage.game.permanent.Permanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class CrimsonRoc extends CardImpl { + + public CrimsonRoc(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{4}{R}"); + + this.subtype.add(SubType.BIRD); + this.power = new MageInt(2); + this.toughness = new MageInt(2); + + // Flying + this.addAbility(FlyingAbility.getInstance()); + + // Whenever Crimson Roc blocks a creature without flying, Crimson Roc gets +1/+0 and gains first strike until end of turn. + this.addAbility(new CrimsonRocTriggeredAbility()); + } + + private CrimsonRoc(final CrimsonRoc card) { + super(card); + } + + @Override + public CrimsonRoc copy() { + return new CrimsonRoc(this); + } +} + +class CrimsonRocTriggeredAbility extends TriggeredAbilityImpl { + + CrimsonRocTriggeredAbility() { + super(Zone.BATTLEFIELD, new BoostSourceEffect(1, 0, Duration.EndOfTurn), false); + this.addEffect(new GainAbilitySourceEffect(FirstStrikeAbility.getInstance(), Duration.EndOfTurn)); + } + + private CrimsonRocTriggeredAbility(final CrimsonRocTriggeredAbility ability) { + super(ability); + } + + @Override + public boolean checkEventType(GameEvent event, Game game) { + return event.getType() == GameEvent.EventType.BLOCKER_DECLARED; + } + + @Override + public boolean checkTrigger(GameEvent event, Game game) { + if (!event.getSourceId().equals(this.getSourceId())) { + return false; + } + Permanent permanent = game.getPermanent(event.getTargetId()); + return permanent != null + && permanent.isCreature() + && !permanent.getAbilities(game).contains(FlyingAbility.getInstance()); + } + + @Override + public String getRule() { + return "Whenever {this} blocks a creature without flying, " + + "{this} gets +1/+0 and gains first strike until end of turn."; + } + + @Override + public CrimsonRocTriggeredAbility copy() { + return new CrimsonRocTriggeredAbility(this); + } +} diff --git a/Mage.Sets/src/mage/sets/Mirage.java b/Mage.Sets/src/mage/sets/Mirage.java index e1190f3f87..9fa3fd6af0 100644 --- a/Mage.Sets/src/mage/sets/Mirage.java +++ b/Mage.Sets/src/mage/sets/Mirage.java @@ -79,6 +79,7 @@ public final class Mirage extends ExpansionSet { cards.add(new SetCardInfo("Coral Fighters", 59, Rarity.UNCOMMON, mage.cards.c.CoralFighters.class)); cards.add(new SetCardInfo("Crash of Rhinos", 210, Rarity.COMMON, mage.cards.c.CrashOfRhinos.class)); cards.add(new SetCardInfo("Crimson Hellkite", 167, Rarity.RARE, mage.cards.c.CrimsonHellkite.class)); + cards.add(new SetCardInfo("Crimson Roc", 168, Rarity.UNCOMMON, mage.cards.c.CrimsonRoc.class)); cards.add(new SetCardInfo("Crypt Cobra", 114, Rarity.UNCOMMON, mage.cards.c.CryptCobra.class)); cards.add(new SetCardInfo("Crystal Golem", 298, Rarity.UNCOMMON, mage.cards.c.CrystalGolem.class)); cards.add(new SetCardInfo("Crystal Vein", 325, Rarity.UNCOMMON, mage.cards.c.CrystalVein.class)); From 1bf32d2f3299692f249481ded45c269a9a1ca7c7 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sun, 6 Oct 2019 19:14:06 -0400 Subject: [PATCH 341/373] Implemented Infernal Harvest --- .../src/mage/cards/i/InfernalHarvest.java | 127 ++++++++++++++++++ Mage.Sets/src/mage/sets/Visions.java | 1 + 2 files changed, 128 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/i/InfernalHarvest.java diff --git a/Mage.Sets/src/mage/cards/i/InfernalHarvest.java b/Mage.Sets/src/mage/cards/i/InfernalHarvest.java new file mode 100644 index 0000000000..74f128ab3e --- /dev/null +++ b/Mage.Sets/src/mage/cards/i/InfernalHarvest.java @@ -0,0 +1,127 @@ +package mage.cards.i; + +import mage.abilities.Ability; +import mage.abilities.costs.Cost; +import mage.abilities.costs.CostImpl; +import mage.abilities.costs.VariableCostImpl; +import mage.abilities.dynamicvalue.common.GetXValue; +import mage.abilities.effects.common.DamageMultiEffect; +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.filter.common.FilterControlledPermanent; +import mage.game.Game; +import mage.players.Player; +import mage.target.Target; +import mage.target.common.TargetControlledPermanent; +import mage.target.common.TargetCreaturePermanentAmount; + +import java.util.Collection; +import java.util.Objects; +import java.util.UUID; +import java.util.stream.Collectors; + +/** + * @author TheElk801 + */ +public final class InfernalHarvest extends CardImpl { + + public InfernalHarvest(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.SORCERY}, "{1}{B}"); + + // As an additional cost to cast Infernal Harvest, return X Swamps you control to their owner's hand. + this.getSpellAbility().addCost(new InfernalHarvestVariableCost()); + + // Infernal Harvest deals X damage divided as you choose among any number of target creatures. + this.getSpellAbility().addEffect(new DamageMultiEffect(GetXValue.instance)); + this.getSpellAbility().addTarget(new TargetCreaturePermanentAmount(GetXValue.instance)); + } + + private InfernalHarvest(final InfernalHarvest card) { + super(card); + } + + @Override + public InfernalHarvest copy() { + return new InfernalHarvest(this); + } +} + +class InfernalHarvestVariableCost extends VariableCostImpl { + + private static final FilterControlledPermanent filter = new FilterControlledPermanent(SubType.SWAMP); + + InfernalHarvestVariableCost() { + super("Swamps to return"); + this.text = "return " + xText + " Swamps you control to their owner's hand"; + } + + private InfernalHarvestVariableCost(final InfernalHarvestVariableCost cost) { + super(cost); + } + + @Override + public InfernalHarvestVariableCost copy() { + return new InfernalHarvestVariableCost(this); + } + + @Override + public int getMaxValue(Ability source, Game game) { + return game.getBattlefield().countAll(filter, source.getControllerId(), game); + } + + @Override + public Cost getFixedCostsFromAnnouncedValue(int xValue) { + return new InfernalHarvestCost(xValue); + } + + private static final class InfernalHarvestCost extends CostImpl { + + private final int xValue; + + private InfernalHarvestCost(int xValue) { + super(); + this.xValue = xValue; + this.text = "return " + xValue + " Swamps you control to their owner's hand"; + this.addTarget(new TargetControlledPermanent(xValue, xValue, filter, true)); + } + + private InfernalHarvestCost(final InfernalHarvestCost cost) { + super(cost); + this.xValue = cost.xValue; + } + + @Override + public boolean canPay(Ability ability, UUID sourceId, UUID controllerId, Game game) { + return game.getBattlefield().countAll(filter, controllerId, game) >= xValue; + } + + @Override + public boolean pay(Ability ability, Game game, UUID sourceId, UUID controllerId, boolean noMana, Cost costToPay) { + if (!this.canPay(ability, sourceId, controllerId, game)) { + return false; + } + Player player = game.getPlayer(controllerId); + if (player == null || !targets.choose(Outcome.ReturnToHand, controllerId, sourceId, game)) { + return false; + } + return paid = player.moveCards( + targets.stream() + .map(Target::getTargets) + .flatMap(Collection::stream) + .map(game::getCard) + .filter(Objects::nonNull) + .collect(Collectors.toSet()), + Zone.HAND, ability, game + ); + } + + @Override + public Cost copy() { + return new InfernalHarvestCost(this); + } + } +} diff --git a/Mage.Sets/src/mage/sets/Visions.java b/Mage.Sets/src/mage/sets/Visions.java index 63ca9aeb98..31852388b5 100644 --- a/Mage.Sets/src/mage/sets/Visions.java +++ b/Mage.Sets/src/mage/sets/Visions.java @@ -86,6 +86,7 @@ public final class Visions extends ExpansionSet { cards.add(new SetCardInfo("Hulking Cyclops", 84, Rarity.UNCOMMON, mage.cards.h.HulkingCyclops.class)); cards.add(new SetCardInfo("Impulse", 34, Rarity.COMMON, mage.cards.i.Impulse.class)); cards.add(new SetCardInfo("Infantry Veteran", 9, Rarity.COMMON, mage.cards.i.InfantryVeteran.class)); + cards.add(new SetCardInfo("Infernal Harvest", 62, Rarity.COMMON, mage.cards.i.InfernalHarvest.class)); cards.add(new SetCardInfo("Inspiration", 35, Rarity.COMMON, mage.cards.i.Inspiration.class)); cards.add(new SetCardInfo("Iron-Heart Chimera", 146, Rarity.UNCOMMON, mage.cards.i.IronHeartChimera.class)); cards.add(new SetCardInfo("Jamuraan Lion", 10, Rarity.COMMON, mage.cards.j.JamuraanLion.class)); From fc3910477c73fe8da24476bef35618a691621cbf Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sun, 6 Oct 2019 20:06:28 -0400 Subject: [PATCH 342/373] fixed Embercleave text for real this time (#6008) --- Mage.Sets/src/mage/cards/e/Embercleave.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Mage.Sets/src/mage/cards/e/Embercleave.java b/Mage.Sets/src/mage/cards/e/Embercleave.java index 32480537b1..574be8331d 100644 --- a/Mage.Sets/src/mage/cards/e/Embercleave.java +++ b/Mage.Sets/src/mage/cards/e/Embercleave.java @@ -52,7 +52,7 @@ public final class Embercleave extends CardImpl { ability = new SimpleStaticAbility(new BoostEquippedEffect(1, 1)); ability.addEffect(new GainAbilityAttachedEffect( DoubleStrikeAbility.getInstance(), AttachmentType.EQUIPMENT - ).setText("and has double strike strike")); + ).setText("and has double strike")); ability.addEffect(new GainAbilityAttachedEffect( TrampleAbility.getInstance(), AttachmentType.EQUIPMENT ).setText("and trample")); From 5c820859378e865211d9c2470da68628e68d40ad Mon Sep 17 00:00:00 2001 From: Adrian Petrescu Date: Tue, 8 Oct 2019 13:35:32 -0400 Subject: [PATCH 343/373] Fix poor naming of Embercleave's cost-reduction effect --- Mage.Sets/src/mage/cards/e/Embercleave.java | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/Mage.Sets/src/mage/cards/e/Embercleave.java b/Mage.Sets/src/mage/cards/e/Embercleave.java index 574be8331d..2c0d2baa7d 100644 --- a/Mage.Sets/src/mage/cards/e/Embercleave.java +++ b/Mage.Sets/src/mage/cards/e/Embercleave.java @@ -39,7 +39,7 @@ public final class Embercleave extends CardImpl { this.addAbility(FlashAbility.getInstance()); // This spell costs {1} less to cast for each attacking creature you control. - this.addAbility(new SimpleStaticAbility(Zone.ALL, new AncientStoneIdolCostReductionEffect())); + this.addAbility(new SimpleStaticAbility(Zone.ALL, new EmbercleaveCostReductionEffect())); // When Embercleave enters the battlefield, attach it to target creature you control. Ability ability = new EntersBattlefieldTriggeredAbility(new AttachEffect( @@ -72,7 +72,7 @@ public final class Embercleave extends CardImpl { } } -class AncientStoneIdolCostReductionEffect extends CostModificationEffectImpl { +class EmbercleaveCostReductionEffect extends CostModificationEffectImpl { private static final FilterPermanent filter = new FilterControlledCreaturePermanent(); @@ -80,12 +80,12 @@ class AncientStoneIdolCostReductionEffect extends CostModificationEffectImpl { filter.add(AttackingPredicate.instance); } - AncientStoneIdolCostReductionEffect() { + EmbercleaveCostReductionEffect() { super(Duration.WhileOnStack, Outcome.Benefit, CostModificationType.REDUCE_COST); staticText = "This spell costs {1} less to cast for each attacking creature you control"; } - private AncientStoneIdolCostReductionEffect(AncientStoneIdolCostReductionEffect effect) { + private EmbercleaveCostReductionEffect(EmbercleaveCostReductionEffect effect) { super(effect); } @@ -105,7 +105,7 @@ class AncientStoneIdolCostReductionEffect extends CostModificationEffectImpl { } @Override - public AncientStoneIdolCostReductionEffect copy() { - return new AncientStoneIdolCostReductionEffect(this); + public EmbercleaveCostReductionEffect copy() { + return new EmbercleaveCostReductionEffect(this); } } From 6289e9a1f5bd75a4b092079dba717c7b199ec9fc Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Tue, 8 Oct 2019 22:48:09 -0400 Subject: [PATCH 344/373] updated Freeform Commander Duel life total to 40 (fixes #6010) --- .../src/mage/game/FreeformCommanderDuelMatch.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Mage.Server.Plugins/Mage.Game.FreeformCommanderDuel/src/mage/game/FreeformCommanderDuelMatch.java b/Mage.Server.Plugins/Mage.Game.FreeformCommanderDuel/src/mage/game/FreeformCommanderDuelMatch.java index 57422d41be..f1d1ea7427 100644 --- a/Mage.Server.Plugins/Mage.Game.FreeformCommanderDuel/src/mage/game/FreeformCommanderDuelMatch.java +++ b/Mage.Server.Plugins/Mage.Game.FreeformCommanderDuel/src/mage/game/FreeformCommanderDuelMatch.java @@ -15,7 +15,7 @@ public class FreeformCommanderDuelMatch extends MatchImpl { @Override public void startGame() throws GameException { - int startLife = 20; + int startLife = 40; Mulligan mulligan = options.getMulliganType().getMulligan(options.getFreeMulligans()); FreeformCommanderDuel game = new FreeformCommanderDuel(options.getAttackOption(), options.getRange(), mulligan, startLife); From b324886c09eb066e5c794195a2fb0422163424be Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 10 Oct 2019 17:01:21 -0400 Subject: [PATCH 345/373] fixed Deafening Silence --- Mage.Sets/src/mage/cards/d/DeafeningSilence.java | 11 +++-------- 1 file changed, 3 insertions(+), 8 deletions(-) diff --git a/Mage.Sets/src/mage/cards/d/DeafeningSilence.java b/Mage.Sets/src/mage/cards/d/DeafeningSilence.java index b6863e1c3e..5663fd2f53 100644 --- a/Mage.Sets/src/mage/cards/d/DeafeningSilence.java +++ b/Mage.Sets/src/mage/cards/d/DeafeningSilence.java @@ -1,9 +1,9 @@ package mage.cards.d; import mage.abilities.Ability; -import mage.abilities.Mode; import mage.abilities.common.SimpleStaticAbility; import mage.abilities.effects.ContinuousRuleModifyingEffectImpl; +import mage.cards.Card; import mage.cards.CardImpl; import mage.cards.CardSetInfo; import mage.constants.CardType; @@ -69,18 +69,13 @@ class DeafeningSilenceEffect extends ContinuousRuleModifyingEffectImpl { @Override public boolean applies(GameEvent event, Ability source, Game game) { - Spell spell = game.getSpell(event.getTargetId()); - if (spell == null || spell.isCreature()) { + Card card = game.getCard(event.getTargetId()); + if (card == null || card.isCreature()) { return false; } DeafeningSilenceWatcher watcher = game.getState().getWatcher(DeafeningSilenceWatcher.class); return watcher != null && watcher.castSpell(event.getPlayerId()); } - - @Override - public String getText(Mode mode) { - return "Each player can't cast more than one noncreature spell each turn."; - } } class DeafeningSilenceWatcher extends Watcher { From e9bbefb814d29f2c70390b9c2e68260332708c14 Mon Sep 17 00:00:00 2001 From: Adrian Petrescu Date: Fri, 11 Oct 2019 09:48:26 -0400 Subject: [PATCH 346/373] Adding incorrectly-failing test for SyrKonradTheGrim His ability should only trigger on creatures leaving the controller's graveyard, not any graveyard. --- .../cards/single/SyrKonradTheGrimTest.java | 31 +++++++++++++++++++ 1 file changed, 31 insertions(+) create mode 100644 Mage.Tests/src/test/java/org/mage/test/cards/single/SyrKonradTheGrimTest.java diff --git a/Mage.Tests/src/test/java/org/mage/test/cards/single/SyrKonradTheGrimTest.java b/Mage.Tests/src/test/java/org/mage/test/cards/single/SyrKonradTheGrimTest.java new file mode 100644 index 0000000000..511ed3a938 --- /dev/null +++ b/Mage.Tests/src/test/java/org/mage/test/cards/single/SyrKonradTheGrimTest.java @@ -0,0 +1,31 @@ +package org.mage.test.cards.single; + +import mage.constants.PhaseStep; +import mage.constants.Zone; +import org.junit.Test; +import org.mage.test.serverside.base.CardTestPlayerBase; + +public class SyrKonradTheGrimTest extends CardTestPlayerBase { + + @Test + public void ownGraveyardTriggerTest() { + addCard(Zone.HAND, playerA, "Rest in Peace"); + addCard(Zone.BATTLEFIELD, playerA, "Plains", 2); + addCard(Zone.BATTLEFIELD, playerA, "Syr Konrad, the Grim"); + addCard(Zone.GRAVEYARD, playerA, "Grizzly Bears", 2); + addCard(Zone.GRAVEYARD, playerB, "Grizzly Bears"); + setStopAt(1, PhaseStep.UNTAP); + execute(); + + assertLife(playerB, 20); + + castSpell(1, PhaseStep.PRECOMBAT_MAIN, playerA, "Rest in Peace"); + setStopAt(1, PhaseStep.POSTCOMBAT_MAIN); + execute(); + + assertGraveyardCount(playerA, 0); + assertGraveyardCount(playerB, 0); + assertLife(playerA, 20); + assertLife(playerB, 18); + } +} From 69cff6c920544316fe265c8c43ee9a6f075b0e23 Mon Sep 17 00:00:00 2001 From: Adrian Petrescu Date: Fri, 11 Oct 2019 09:59:06 -0400 Subject: [PATCH 347/373] Fix buggy login in SyrKonradTheGrimTriggeredAbility.checkTrigger() Basically needed to check that creatures leaving the graveyard belong to the controlling player. --- Mage.Sets/src/mage/cards/s/SyrKonradTheGrim.java | 8 ++++++-- .../org/mage/test/cards/single/SyrKonradTheGrimTest.java | 4 +++- 2 files changed, 9 insertions(+), 3 deletions(-) diff --git a/Mage.Sets/src/mage/cards/s/SyrKonradTheGrim.java b/Mage.Sets/src/mage/cards/s/SyrKonradTheGrim.java index aa61685d40..967fc74452 100644 --- a/Mage.Sets/src/mage/cards/s/SyrKonradTheGrim.java +++ b/Mage.Sets/src/mage/cards/s/SyrKonradTheGrim.java @@ -72,6 +72,7 @@ class SyrKonradTheGrimTriggeredAbility extends TriggeredAbilityImpl { @Override public boolean checkTrigger(GameEvent event, Game game) { ZoneChangeEvent zEvent = (ZoneChangeEvent) event; + // Whenever another creature dies if (zEvent.isDiesEvent() && zEvent.getTarget() != null && !zEvent.getTargetId().equals(this.getSourceId()) @@ -79,6 +80,7 @@ class SyrKonradTheGrimTriggeredAbility extends TriggeredAbilityImpl { return true; } Card card = game.getCard(zEvent.getTargetId()); + // Or a creature card is put into a graveyard from anywhere other than the battlefield if (card == null || !card.isCreature()) { return false; } @@ -86,7 +88,9 @@ class SyrKonradTheGrimTriggeredAbility extends TriggeredAbilityImpl { && zEvent.getFromZone() != Zone.BATTLEFIELD) { return true; } - return zEvent.getFromZone() == Zone.GRAVEYARD; + // Or a creature card leaves your graveyard + return zEvent.getFromZone() == Zone.GRAVEYARD + && zEvent.getPlayerId() == this.getControllerId(); } @Override @@ -95,4 +99,4 @@ class SyrKonradTheGrimTriggeredAbility extends TriggeredAbilityImpl { "from anywhere other than the battlefield, or a creature card leaves your graveyard, " + "{this} deals 1 damage to each opponent."; } -} \ No newline at end of file +} diff --git a/Mage.Tests/src/test/java/org/mage/test/cards/single/SyrKonradTheGrimTest.java b/Mage.Tests/src/test/java/org/mage/test/cards/single/SyrKonradTheGrimTest.java index 511ed3a938..f24543cf40 100644 --- a/Mage.Tests/src/test/java/org/mage/test/cards/single/SyrKonradTheGrimTest.java +++ b/Mage.Tests/src/test/java/org/mage/test/cards/single/SyrKonradTheGrimTest.java @@ -8,11 +8,13 @@ import org.mage.test.serverside.base.CardTestPlayerBase; public class SyrKonradTheGrimTest extends CardTestPlayerBase { @Test - public void ownGraveyardTriggerTest() { + public void leavesOwnGraveyardTriggerTest() { addCard(Zone.HAND, playerA, "Rest in Peace"); addCard(Zone.BATTLEFIELD, playerA, "Plains", 2); addCard(Zone.BATTLEFIELD, playerA, "Syr Konrad, the Grim"); + // These leaving the graveyard *should* cause loss of life addCard(Zone.GRAVEYARD, playerA, "Grizzly Bears", 2); + // These ones *shouldn't* addCard(Zone.GRAVEYARD, playerB, "Grizzly Bears"); setStopAt(1, PhaseStep.UNTAP); execute(); From 00fd8d18dae845e80e6bb0ab73004d0757a282e3 Mon Sep 17 00:00:00 2001 From: Adrian Petrescu Date: Fri, 11 Oct 2019 09:59:54 -0400 Subject: [PATCH 348/373] Remove unneeded import in an unrelated test, just for kicks --- .../java/org/mage/test/cards/single/ArchfiendOfSpiteTest.java | 1 - 1 file changed, 1 deletion(-) diff --git a/Mage.Tests/src/test/java/org/mage/test/cards/single/ArchfiendOfSpiteTest.java b/Mage.Tests/src/test/java/org/mage/test/cards/single/ArchfiendOfSpiteTest.java index 00622f1471..4037097d6b 100644 --- a/Mage.Tests/src/test/java/org/mage/test/cards/single/ArchfiendOfSpiteTest.java +++ b/Mage.Tests/src/test/java/org/mage/test/cards/single/ArchfiendOfSpiteTest.java @@ -2,7 +2,6 @@ package org.mage.test.cards.single; import mage.constants.PhaseStep; import mage.constants.Zone; -import org.junit.Assert; import org.junit.Test; import org.mage.test.serverside.base.CardTestPlayerBase; From 5f1fa5608ec0d552cce6abc998611850a5a9c065 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 12 Oct 2019 10:37:22 -0400 Subject: [PATCH 349/373] added Game Night 2019 --- Mage.Sets/src/mage/sets/GameNight2019.java | 21 +++++++++++++++++++++ Utils/known-sets.txt | 2 ++ Utils/mtg-cards-data.txt | 5 +++++ Utils/mtg-sets-data.txt | 2 ++ 4 files changed, 30 insertions(+) create mode 100644 Mage.Sets/src/mage/sets/GameNight2019.java diff --git a/Mage.Sets/src/mage/sets/GameNight2019.java b/Mage.Sets/src/mage/sets/GameNight2019.java new file mode 100644 index 0000000000..34cd51a3ce --- /dev/null +++ b/Mage.Sets/src/mage/sets/GameNight2019.java @@ -0,0 +1,21 @@ +package mage.sets; + +import mage.cards.ExpansionSet; +import mage.constants.SetType; + +/** + * @author TheElk801 + */ +public final class GameNight2019 extends ExpansionSet { + + private static final GameNight2019 instance = new GameNight2019(); + + public static GameNight2019 getInstance() { + return instance; + } + + private GameNight2019() { + super("Game Night 2019", "GN2", ExpansionSet.buildDate(2019, 11, 15), SetType.SUPPLEMENTAL); + this.hasBasicLands = false; // TODO: change when spoiled + } +} diff --git a/Utils/known-sets.txt b/Utils/known-sets.txt index 93b95715ac..638e5cb57a 100644 --- a/Utils/known-sets.txt +++ b/Utils/known-sets.txt @@ -90,6 +90,8 @@ From the Vault: Transform|FromTheVaultTransform| From the Vault: Twenty|FromTheVaultTwenty| Future Sight|FutureSight| Game Day|GameDay| +Game Night|GameNight| +Game Night 2019|GameNight2019| Gatecrash|Gatecrash| Global Series: Jiang Yanggu & Mu Yanling|GlobalSeriesJiangYangguAndMuYanling| Grand Prix|GrandPrixPromos| diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index fd3529d093..c5a6c0505d 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -36429,3 +36429,8 @@ Castle Garenbrig|Throne of Eldraine Collector's Edition|388|R||Land|||Castle Gar Castle Locthwain|Throne of Eldraine Collector's Edition|389|R||Land|||Castle Locthwain enters the battlefield tapped unless you control a Swamp.${T}: Add {B}.${1}{B}{B}, {T}: Draw a card, then you lose life equal to the number of cards in your hand.| Castle Vantress|Throne of Eldraine Collector's Edition|390|R||Land|||Castle Vantress enters the battlefield tapped unless you control an Island.${T}: Add {U}.${2}{U}{U}, {T}: Scry 2.| Fabled Passage|Throne of Eldraine Collector's Edition|391|R||Land|||{T}, Sacrifice Fabled Passage: Search your library for a basic land card, put it onto the battlefield tapped, then shuffle your library. Then if you control four or more lands, untap that land.| +Highcliff Felidar|Game Night 2019|1|M|{5}{W}{W}|Creature - Cat Beast|5|5|Vigilance$When Highcliff Felidar enters the battlefield, for each opponent, choose a creature with the greatest power among creatures that player controls. Destroy those creatures.| +Sphinx of Enlightenment|Game Night 2019|2|M|{4}{U}{U}|Creature - Sphinx|5|5|Flying$When Sphinx of Enlightenment enters the battlefield, target opponent draws a card and you draw three cards.| +Calculating Lich|Game Night 2019|3|M|{4}{B}{B}|Creature - Zombie Wizard|5|5|Menance$Whenever a creature attacks one of your opponents, that player loses 1 life.| +Fiendish Duo|Game Night 2019|4|M|{4}{R}{R}|Creature - Devil|5|5|First strike$If a source would deal damage to an opponent, it deals double that damage that player instead.| +Earthshaker Giant|Game Night 2019|5|M|{4}{G}{G}|Creature - Giant Druid|6|6|Trample$When Earthshaker Giant enters the battlefield, other creatures you control get +3/+3 and gain trample until end of turn.| diff --git a/Utils/mtg-sets-data.txt b/Utils/mtg-sets-data.txt index 5c02dc8f1b..4b50c8d8d6 100644 --- a/Utils/mtg-sets-data.txt +++ b/Utils/mtg-sets-data.txt @@ -139,6 +139,8 @@ Masters Edition III|ME3| Masters Edition IV|ME4| Masters Edition|MED| Game Day|MGDC| +Game Night|GNT| +Game Night 2019|GN2| Mirage|MIR| Launch Party|MLP| Modern Horizons|MH1| From 811ab5d69ab8bfc52d238800ec72c2cf4c83da37 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 12 Oct 2019 10:40:52 -0400 Subject: [PATCH 350/373] Implemented Sphinx of Enlightenment --- .../mage/cards/s/SphinxOfEnlightenment.java | 47 +++++++++++++++++++ Mage.Sets/src/mage/sets/GameNight2019.java | 3 ++ 2 files changed, 50 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/s/SphinxOfEnlightenment.java diff --git a/Mage.Sets/src/mage/cards/s/SphinxOfEnlightenment.java b/Mage.Sets/src/mage/cards/s/SphinxOfEnlightenment.java new file mode 100644 index 0000000000..9ba513d98c --- /dev/null +++ b/Mage.Sets/src/mage/cards/s/SphinxOfEnlightenment.java @@ -0,0 +1,47 @@ +package mage.cards.s; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.effects.common.DrawCardSourceControllerEffect; +import mage.abilities.effects.common.DrawCardTargetEffect; +import mage.abilities.keyword.FlyingAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.target.common.TargetOpponent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class SphinxOfEnlightenment extends CardImpl { + + public SphinxOfEnlightenment(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{4}{U}{U}"); + + this.subtype.add(SubType.SPHINX); + this.power = new MageInt(5); + this.toughness = new MageInt(5); + + // Flying + this.addAbility(FlyingAbility.getInstance()); + + // When Sphinx of Enlightenment enters the battlefield, target opponent draws a card and you draw three cards. + Ability ability = new EntersBattlefieldTriggeredAbility(new DrawCardTargetEffect(1)); + ability.addEffect(new DrawCardSourceControllerEffect(3).concatBy("and you")); + ability.addTarget(new TargetOpponent()); + this.addAbility(ability); + } + + private SphinxOfEnlightenment(final SphinxOfEnlightenment card) { + super(card); + } + + @Override + public SphinxOfEnlightenment copy() { + return new SphinxOfEnlightenment(this); + } +} diff --git a/Mage.Sets/src/mage/sets/GameNight2019.java b/Mage.Sets/src/mage/sets/GameNight2019.java index 34cd51a3ce..31e79d6c3d 100644 --- a/Mage.Sets/src/mage/sets/GameNight2019.java +++ b/Mage.Sets/src/mage/sets/GameNight2019.java @@ -1,6 +1,7 @@ package mage.sets; import mage.cards.ExpansionSet; +import mage.constants.Rarity; import mage.constants.SetType; /** @@ -17,5 +18,7 @@ public final class GameNight2019 extends ExpansionSet { private GameNight2019() { super("Game Night 2019", "GN2", ExpansionSet.buildDate(2019, 11, 15), SetType.SUPPLEMENTAL); this.hasBasicLands = false; // TODO: change when spoiled + + cards.add(new SetCardInfo("Sphinx of Enlightenment", 2, Rarity.MYTHIC, mage.cards.s.SphinxOfEnlightenment.class)); } } From 1693762fa874024157483127c83a845e856d63e9 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 12 Oct 2019 11:19:31 -0400 Subject: [PATCH 351/373] Implemented Highcliff Felidar --- .../src/mage/cards/h/HighcliffFelidar.java | 162 ++++++++++++++++++ Mage.Sets/src/mage/sets/GameNight2019.java | 1 + 2 files changed, 163 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/h/HighcliffFelidar.java diff --git a/Mage.Sets/src/mage/cards/h/HighcliffFelidar.java b/Mage.Sets/src/mage/cards/h/HighcliffFelidar.java new file mode 100644 index 0000000000..38a85db364 --- /dev/null +++ b/Mage.Sets/src/mage/cards/h/HighcliffFelidar.java @@ -0,0 +1,162 @@ +package mage.cards.h; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.effects.OneShotEffect; +import mage.abilities.keyword.VigilanceAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.ComparisonType; +import mage.constants.Outcome; +import mage.constants.SubType; +import mage.filter.FilterPermanent; +import mage.filter.StaticFilters; +import mage.filter.common.FilterCreaturePermanent; +import mage.filter.predicate.mageobject.PowerPredicate; +import mage.filter.predicate.permanent.ControllerIdPredicate; +import mage.game.Game; +import mage.game.permanent.Permanent; +import mage.players.Player; +import mage.target.TargetPermanent; + +import java.util.HashSet; +import java.util.Objects; +import java.util.Set; +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class HighcliffFelidar extends CardImpl { + + public HighcliffFelidar(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{5}{W}{W}"); + + this.subtype.add(SubType.CAT); + this.subtype.add(SubType.BEAST); + this.power = new MageInt(5); + this.toughness = new MageInt(5); + + // Vigilance + this.addAbility(VigilanceAbility.getInstance()); + + // When Highcliff Felidar enters the battlefield, for each opponent, choose a creature with the greatest power among creatures that player controls. Destroy those creatures. + this.addAbility(new EntersBattlefieldTriggeredAbility(new HighcliffFelidarEffect())); + } + + private HighcliffFelidar(final HighcliffFelidar card) { + super(card); + } + + @Override + public HighcliffFelidar copy() { + return new HighcliffFelidar(this); + } +} + +class HighcliffFelidarEffect extends OneShotEffect { + + HighcliffFelidarEffect() { + super(Outcome.Benefit); + staticText = "for each opponent, choose a creature with the greatest power " + + "among creatures that player controls. Destroy those creatures."; + } + + private HighcliffFelidarEffect(final HighcliffFelidarEffect effect) { + super(effect); + } + + @Override + public HighcliffFelidarEffect copy() { + return new HighcliffFelidarEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + Player player = game.getPlayer(source.getControllerId()); + if (player == null) { + return false; + } + Set toDestroy = new HashSet(); + game.getOpponents(source.getControllerId()) + .stream() + .map(game::getPlayer) + .filter(Objects::nonNull) + .forEachOrdered(opponent -> { + int maxPower = game + .getBattlefield() + .getAllActivePermanents(StaticFilters.FILTER_PERMANENT_CREATURE, opponent.getId(), game) + .stream() + .map(Permanent::getPower) + .mapToInt(MageInt::getValue) + .max() + .orElse(Integer.MIN_VALUE); + if (maxPower == Integer.MIN_VALUE) { + return; + } + FilterPermanent filter = new FilterCreaturePermanent( + "creature with the greatest power controlled by " + opponent.getName() + ); + filter.add(new ControllerIdPredicate(opponent.getId())); + filter.add(new PowerPredicate(ComparisonType.EQUAL_TO, maxPower)); + TargetPermanent target = new TargetPermanent(filter); + target.setNotTarget(true); + if (player.choose(outcome, target, source.getSourceId(), game)) { + toDestroy.add(target.getFirstTarget()); + } + }); + toDestroy.stream() + .map(game::getPermanent) + .filter(Objects::nonNull) + .forEachOrdered(permanent -> permanent.destroy(source.getSourceId(), game, false)); + return true; + } +} + +// I realized after writing all this that the ability doesn't target but I like this code too much to erase it + +//enum HighcliffFelidarAdjuster implements TargetAdjuster { +// instance; +// +// private static class HighcliffFelidarPredicate implements Predicate { +// private final UUID controllerId; +// +// private HighcliffFelidarPredicate(UUID controllerId) { +// this.controllerId = controllerId; +// } +// +// @Override +// public boolean apply(Permanent input, Game game) { +// if (input == null || !input.isControlledBy(controllerId) || !input.isCreature()) { +// return false; +// } +// int maxPower = game.getBattlefield() +// .getAllActivePermanents(StaticFilters.FILTER_PERMANENT_CREATURE, controllerId, game) +// .stream() +// .map(Permanent::getPower) +// .mapToInt(MageInt::getValue) +// .max() +// .orElse(Integer.MIN_VALUE); +// return input.getPower().getValue() >= maxPower; +// } +// +// private static TargetPermanent getTarget(Player player) { +// FilterPermanent filter = new FilterPermanent("creature with the greatest power controlled by " + player.getName()); +// filter.add(new HighcliffFelidarPredicate(player.getId())); +// return new TargetPermanent(filter); +// } +// } +// +// @Override +// public void adjustTargets(Ability ability, Game game) { +// ability.getTargets().clear(); +// game.getOpponents(ability.getControllerId()) +// .stream() +// .map(game::getPlayer) +// .filter(Objects::nonNull) +// .map(HighcliffFelidarPredicate::getTarget) +// .forEachOrdered(ability::addTarget); +// } +//} diff --git a/Mage.Sets/src/mage/sets/GameNight2019.java b/Mage.Sets/src/mage/sets/GameNight2019.java index 31e79d6c3d..17cf2199b4 100644 --- a/Mage.Sets/src/mage/sets/GameNight2019.java +++ b/Mage.Sets/src/mage/sets/GameNight2019.java @@ -19,6 +19,7 @@ public final class GameNight2019 extends ExpansionSet { super("Game Night 2019", "GN2", ExpansionSet.buildDate(2019, 11, 15), SetType.SUPPLEMENTAL); this.hasBasicLands = false; // TODO: change when spoiled + cards.add(new SetCardInfo("Highcliff Felidar", 1, Rarity.MYTHIC, mage.cards.h.HighcliffFelidar.class)); cards.add(new SetCardInfo("Sphinx of Enlightenment", 2, Rarity.MYTHIC, mage.cards.s.SphinxOfEnlightenment.class)); } } From 24efd96edba4655304e02800da35d861a384ed73 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 12 Oct 2019 11:22:34 -0400 Subject: [PATCH 352/373] Implemented Earthshaker Giant --- .../src/mage/cards/e/EarthshakerGiant.java | 53 +++++++++++++++++++ Mage.Sets/src/mage/sets/GameNight2019.java | 1 + 2 files changed, 54 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/e/EarthshakerGiant.java diff --git a/Mage.Sets/src/mage/cards/e/EarthshakerGiant.java b/Mage.Sets/src/mage/cards/e/EarthshakerGiant.java new file mode 100644 index 0000000000..8c6c2c7521 --- /dev/null +++ b/Mage.Sets/src/mage/cards/e/EarthshakerGiant.java @@ -0,0 +1,53 @@ +package mage.cards.e; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.effects.common.continuous.BoostControlledEffect; +import mage.abilities.effects.common.continuous.GainAbilityControlledEffect; +import mage.abilities.keyword.TrampleAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.SubType; +import mage.filter.StaticFilters; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class EarthshakerGiant extends CardImpl { + + public EarthshakerGiant(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{4}{G}{G}"); + + this.subtype.add(SubType.GIANT); + this.subtype.add(SubType.DRUID); + this.power = new MageInt(6); + this.toughness = new MageInt(6); + + // Trample + this.addAbility(TrampleAbility.getInstance()); + + // When Earthshaker Giant enters the battlefield, other creatures you control get +3/+3 and gain trample until end of turn. + Ability ability = new EntersBattlefieldTriggeredAbility(new BoostControlledEffect( + 3, 3, Duration.EndOfTurn, true + ).setText("other creatures you control get +3/+3")); + ability.addEffect(new GainAbilityControlledEffect( + TrampleAbility.getInstance(), Duration.EndOfTurn, + StaticFilters.FILTER_PERMANENT_CREATURE, true + ).setText("and gain trample until end of turn")); + this.addAbility(ability); + } + + private EarthshakerGiant(final EarthshakerGiant card) { + super(card); + } + + @Override + public EarthshakerGiant copy() { + return new EarthshakerGiant(this); + } +} diff --git a/Mage.Sets/src/mage/sets/GameNight2019.java b/Mage.Sets/src/mage/sets/GameNight2019.java index 17cf2199b4..d38fb6b4d3 100644 --- a/Mage.Sets/src/mage/sets/GameNight2019.java +++ b/Mage.Sets/src/mage/sets/GameNight2019.java @@ -19,6 +19,7 @@ public final class GameNight2019 extends ExpansionSet { super("Game Night 2019", "GN2", ExpansionSet.buildDate(2019, 11, 15), SetType.SUPPLEMENTAL); this.hasBasicLands = false; // TODO: change when spoiled + cards.add(new SetCardInfo("Earthshaker Giant", 5, Rarity.MYTHIC, mage.cards.e.EarthshakerGiant.class)); cards.add(new SetCardInfo("Highcliff Felidar", 1, Rarity.MYTHIC, mage.cards.h.HighcliffFelidar.class)); cards.add(new SetCardInfo("Sphinx of Enlightenment", 2, Rarity.MYTHIC, mage.cards.s.SphinxOfEnlightenment.class)); } From 2fb9153608dc1de9d10f98cd9d208a58870a9fca Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 12 Oct 2019 11:25:01 -0400 Subject: [PATCH 353/373] updated server pom.xml to fix security vulnerability --- Mage.Server/pom.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Mage.Server/pom.xml b/Mage.Server/pom.xml index 49a6a79a2b..3c4b3ea16f 100644 --- a/Mage.Server/pom.xml +++ b/Mage.Server/pom.xml @@ -91,7 +91,7 @@ org.apache.commons commons-compress - 1.18 + [1.19,) From 6f600c0a50040fec583d4088eb8996ef77ad6512 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 12 Oct 2019 11:31:58 -0400 Subject: [PATCH 354/373] Implemented Fiendish Duo --- Mage.Sets/src/mage/cards/f/FiendishDuo.java | 88 +++++++++++++++++++++ Mage.Sets/src/mage/sets/GameNight2019.java | 1 + 2 files changed, 89 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/f/FiendishDuo.java diff --git a/Mage.Sets/src/mage/cards/f/FiendishDuo.java b/Mage.Sets/src/mage/cards/f/FiendishDuo.java new file mode 100644 index 0000000000..41b7da9023 --- /dev/null +++ b/Mage.Sets/src/mage/cards/f/FiendishDuo.java @@ -0,0 +1,88 @@ +package mage.cards.f; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.SimpleStaticAbility; +import mage.abilities.effects.ReplacementEffectImpl; +import mage.abilities.keyword.FirstStrikeAbility; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.Duration; +import mage.constants.Outcome; +import mage.constants.SubType; +import mage.game.Game; +import mage.game.events.GameEvent; +import mage.players.Player; +import mage.util.CardUtil; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class FiendishDuo extends CardImpl { + + public FiendishDuo(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{4}{R}{R}"); + + this.subtype.add(SubType.DEVIL); + this.power = new MageInt(5); + this.toughness = new MageInt(5); + + // First strike + this.addAbility(FirstStrikeAbility.getInstance()); + + // If a source would deal damage to an opponent, it deals double that damage that player instead. + this.addAbility(new SimpleStaticAbility(new FiendishDuoEffect())); + } + + private FiendishDuo(final FiendishDuo card) { + super(card); + } + + @Override + public FiendishDuo copy() { + return new FiendishDuo(this); + } +} + +class FiendishDuoEffect extends ReplacementEffectImpl { + + FiendishDuoEffect() { + super(Duration.WhileOnBattlefield, Outcome.Damage); + staticText = "If a source would deal damage to an opponent, " + + "it deals double that damage to that player instead"; + } + + private FiendishDuoEffect(final FiendishDuoEffect effect) { + super(effect); + } + + @Override + public FiendishDuoEffect copy() { + return new FiendishDuoEffect(this); + } + + @Override + public boolean checksEventType(GameEvent event, Game game) { + return event.getType() == GameEvent.EventType.DAMAGE_PLAYER; + } + + @Override + public boolean applies(GameEvent event, Ability source, Game game) { + Player player = game.getPlayer(source.getControllerId()); + return player != null && player.hasOpponent(event.getTargetId(), game); + } + + @Override + public boolean apply(Game game, Ability source) { + return true; + } + + @Override + public boolean replaceEvent(GameEvent event, Ability source, Game game) { + event.setAmount(CardUtil.addWithOverflowCheck(event.getAmount(), event.getAmount())); + return false; + } +} diff --git a/Mage.Sets/src/mage/sets/GameNight2019.java b/Mage.Sets/src/mage/sets/GameNight2019.java index d38fb6b4d3..c9b0e4ef04 100644 --- a/Mage.Sets/src/mage/sets/GameNight2019.java +++ b/Mage.Sets/src/mage/sets/GameNight2019.java @@ -20,6 +20,7 @@ public final class GameNight2019 extends ExpansionSet { this.hasBasicLands = false; // TODO: change when spoiled cards.add(new SetCardInfo("Earthshaker Giant", 5, Rarity.MYTHIC, mage.cards.e.EarthshakerGiant.class)); + cards.add(new SetCardInfo("Fiendish Duo", 4, Rarity.MYTHIC, mage.cards.f.FiendishDuo.class)); cards.add(new SetCardInfo("Highcliff Felidar", 1, Rarity.MYTHIC, mage.cards.h.HighcliffFelidar.class)); cards.add(new SetCardInfo("Sphinx of Enlightenment", 2, Rarity.MYTHIC, mage.cards.s.SphinxOfEnlightenment.class)); } From 35ebebd0f472b0d184b2505f6142f1480c231ddc Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 12 Oct 2019 11:43:35 -0400 Subject: [PATCH 355/373] Implemented Calculating Lich --- .../src/mage/cards/c/CalculatingLich.java | 85 +++++++++++++++++++ Mage.Sets/src/mage/cards/f/FiendishDuo.java | 2 +- Mage.Sets/src/mage/sets/GameNight2019.java | 1 + Utils/mtg-cards-data.txt | 2 +- 4 files changed, 88 insertions(+), 2 deletions(-) create mode 100644 Mage.Sets/src/mage/cards/c/CalculatingLich.java diff --git a/Mage.Sets/src/mage/cards/c/CalculatingLich.java b/Mage.Sets/src/mage/cards/c/CalculatingLich.java new file mode 100644 index 0000000000..d003b57b95 --- /dev/null +++ b/Mage.Sets/src/mage/cards/c/CalculatingLich.java @@ -0,0 +1,85 @@ +package mage.cards.c; + +import mage.MageInt; +import mage.abilities.TriggeredAbilityImpl; +import mage.abilities.effects.common.LoseLifeTargetEffect; +import mage.abilities.keyword.MenaceAbility; +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.players.Player; +import mage.target.targetpointer.FixedTarget; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class CalculatingLich extends CardImpl { + + public CalculatingLich(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{4}{B}{B}"); + + this.subtype.add(SubType.ZOMBIE); + this.subtype.add(SubType.WIZARD); + this.power = new MageInt(5); + this.toughness = new MageInt(5); + + // Menace + this.addAbility(new MenaceAbility()); + + // Whenever a creature attacks one of your opponents, that player loses 1 life. + this.addAbility(new CalculatingLichTriggeredAbility()); + } + + private CalculatingLich(final CalculatingLich card) { + super(card); + } + + @Override + public CalculatingLich copy() { + return new CalculatingLich(this); + } +} + +class CalculatingLichTriggeredAbility extends TriggeredAbilityImpl { + + CalculatingLichTriggeredAbility() { + super(Zone.BATTLEFIELD, null, false); + } + + private CalculatingLichTriggeredAbility(final CalculatingLichTriggeredAbility ability) { + super(ability); + } + + @Override + public boolean checkEventType(GameEvent event, Game game) { + return event.getType() == GameEvent.EventType.DECLARED_ATTACKERS; + } + + @Override + public boolean checkTrigger(GameEvent event, Game game) { + Player player = game.getPlayer(getControllerId()); + UUID defenderId = game.getCombat().getDefenderId(event.getSourceId()); + if (player == null || !player.hasOpponent(defenderId, game)) { + return false; + } + getEffects().clear(); + addEffect(new LoseLifeTargetEffect(1).setTargetPointer(new FixedTarget(defenderId, game))); + return true; + } + + @Override + public String getRule() { + return "Whenever a creature attacks one of your opponents, that player loses 1 life."; + } + + @Override + public CalculatingLichTriggeredAbility copy() { + return new CalculatingLichTriggeredAbility(this); + } +} diff --git a/Mage.Sets/src/mage/cards/f/FiendishDuo.java b/Mage.Sets/src/mage/cards/f/FiendishDuo.java index 41b7da9023..e8ae73d92e 100644 --- a/Mage.Sets/src/mage/cards/f/FiendishDuo.java +++ b/Mage.Sets/src/mage/cards/f/FiendishDuo.java @@ -33,7 +33,7 @@ public final class FiendishDuo extends CardImpl { // First strike this.addAbility(FirstStrikeAbility.getInstance()); - // If a source would deal damage to an opponent, it deals double that damage that player instead. + // If a source would deal damage to an opponent, it deals double that damage to that player instead. this.addAbility(new SimpleStaticAbility(new FiendishDuoEffect())); } diff --git a/Mage.Sets/src/mage/sets/GameNight2019.java b/Mage.Sets/src/mage/sets/GameNight2019.java index c9b0e4ef04..ece39af080 100644 --- a/Mage.Sets/src/mage/sets/GameNight2019.java +++ b/Mage.Sets/src/mage/sets/GameNight2019.java @@ -19,6 +19,7 @@ public final class GameNight2019 extends ExpansionSet { super("Game Night 2019", "GN2", ExpansionSet.buildDate(2019, 11, 15), SetType.SUPPLEMENTAL); this.hasBasicLands = false; // TODO: change when spoiled + cards.add(new SetCardInfo("Calculating Lich", 3, Rarity.MYTHIC, mage.cards.c.CalculatingLich.class)); cards.add(new SetCardInfo("Earthshaker Giant", 5, Rarity.MYTHIC, mage.cards.e.EarthshakerGiant.class)); cards.add(new SetCardInfo("Fiendish Duo", 4, Rarity.MYTHIC, mage.cards.f.FiendishDuo.class)); cards.add(new SetCardInfo("Highcliff Felidar", 1, Rarity.MYTHIC, mage.cards.h.HighcliffFelidar.class)); diff --git a/Utils/mtg-cards-data.txt b/Utils/mtg-cards-data.txt index c5a6c0505d..e96203d62f 100644 --- a/Utils/mtg-cards-data.txt +++ b/Utils/mtg-cards-data.txt @@ -36431,6 +36431,6 @@ Castle Vantress|Throne of Eldraine Collector's Edition|390|R||Land|||Castle Vant Fabled Passage|Throne of Eldraine Collector's Edition|391|R||Land|||{T}, Sacrifice Fabled Passage: Search your library for a basic land card, put it onto the battlefield tapped, then shuffle your library. Then if you control four or more lands, untap that land.| Highcliff Felidar|Game Night 2019|1|M|{5}{W}{W}|Creature - Cat Beast|5|5|Vigilance$When Highcliff Felidar enters the battlefield, for each opponent, choose a creature with the greatest power among creatures that player controls. Destroy those creatures.| Sphinx of Enlightenment|Game Night 2019|2|M|{4}{U}{U}|Creature - Sphinx|5|5|Flying$When Sphinx of Enlightenment enters the battlefield, target opponent draws a card and you draw three cards.| -Calculating Lich|Game Night 2019|3|M|{4}{B}{B}|Creature - Zombie Wizard|5|5|Menance$Whenever a creature attacks one of your opponents, that player loses 1 life.| +Calculating Lich|Game Night 2019|3|M|{4}{B}{B}|Creature - Zombie Wizard|5|5|Menace$Whenever a creature attacks one of your opponents, that player loses 1 life.| Fiendish Duo|Game Night 2019|4|M|{4}{R}{R}|Creature - Devil|5|5|First strike$If a source would deal damage to an opponent, it deals double that damage that player instead.| Earthshaker Giant|Game Night 2019|5|M|{4}{G}{G}|Creature - Giant Druid|6|6|Trample$When Earthshaker Giant enters the battlefield, other creatures you control get +3/+3 and gain trample until end of turn.| From 3f7fdb30749b6857b8e59d55a34591b9ce4e865d Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 12 Oct 2019 12:01:46 -0400 Subject: [PATCH 356/373] updated Oathbreaker banlist --- .../Mage.Deck.Constructed/src/mage/deck/Oathbreaker.java | 1 - 1 file changed, 1 deletion(-) diff --git a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Oathbreaker.java b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Oathbreaker.java index 5ca36ba216..b299afbaf6 100644 --- a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Oathbreaker.java +++ b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Oathbreaker.java @@ -52,7 +52,6 @@ public class Oathbreaker extends Vintage { banned.add("Painter's Servant"); banned.add("Panoptic Mirror"); banned.add("Primal Surge"); - banned.add("Recurring Nightmare"); banned.add("Saheeli, the Gifted"); banned.add("Sol Ring"); banned.add("Sundering Titan"); From 16199d12dde7bef2254cab25982260e71448ebd8 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 12 Oct 2019 12:03:41 -0400 Subject: [PATCH 357/373] updated Canadian Highlander points list --- .../src/mage/deck/CanadianHighlander.java | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CanadianHighlander.java b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CanadianHighlander.java index 7af1dc83a9..89f03d1acb 100644 --- a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CanadianHighlander.java +++ b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CanadianHighlander.java @@ -20,7 +20,8 @@ public class CanadianHighlander extends Constructed { pointMap.put("Balance", 1); pointMap.put("Birthing Pod", 2); pointMap.put("Black Lotus", 7); - pointMap.put("Demonic Tutor", 3); + pointMap.put("Crop Rotation", 1); + pointMap.put("Demonic Tutor", 4); pointMap.put("Dig Through Time", 1); pointMap.put("Enlightened Tutor", 1); pointMap.put("Flash", 6); @@ -28,7 +29,7 @@ public class CanadianHighlander extends Constructed { pointMap.put("Imperial Seal", 1); pointMap.put("Intuition", 1); pointMap.put("Library of Alexandria", 1); - pointMap.put("Mana Crypt", 3); + pointMap.put("Mana Crypt", 4); pointMap.put("Mana Drain", 1); pointMap.put("Mana Vault", 1); pointMap.put("Merchant Scroll", 1); @@ -41,7 +42,7 @@ public class CanadianHighlander extends Constructed { pointMap.put("Mystical Tutor", 2); pointMap.put("Natural Order", 4); pointMap.put("Protean Hulk", 3); - pointMap.put("Sol Ring", 3); + pointMap.put("Sol Ring", 4); pointMap.put("Spellseeker", 1); pointMap.put("Stoneforge Mystic", 1); pointMap.put("Strip Mine", 2); From d23d78c7f4763d92479c48559b99b39f0f72e68d Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 12 Oct 2019 12:09:08 -0400 Subject: [PATCH 358/373] updated Australian Highlander points list --- .../src/mage/deck/AusHighlander.java | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) diff --git a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/AusHighlander.java b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/AusHighlander.java index d59a9fa4ef..a66fdab991 100644 --- a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/AusHighlander.java +++ b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/AusHighlander.java @@ -29,7 +29,6 @@ public class AusHighlander extends Constructed { pointMap.put("Sol Ring", 3); pointMap.put("Time Walk", 3); pointMap.put("Vampiric Tutor", 3); - pointMap.put("Yawgmoth's Will", 3); pointMap.put("Channel", 2); pointMap.put("Dig Through Time", 2); pointMap.put("Library of Alexandria", 2); @@ -37,13 +36,16 @@ public class AusHighlander extends Constructed { pointMap.put("Mind Twist", 2); pointMap.put("Mystical Tutor", 2); pointMap.put("Protean Hulk", 2); + pointMap.put("Strip Mine", 2); pointMap.put("Tinker", 2); pointMap.put("Tolarian Academy", 2); pointMap.put("Treasure Cruise", 2); + pointMap.put("True-Name Nemesis", 2); pointMap.put("Balance", 1); pointMap.put("Birthing Pod", 1); pointMap.put("Crop Rotation", 1); pointMap.put("Dark Petition", 1); + pointMap.put("Doomsday", 1); pointMap.put("Enlightened Tutor", 1); pointMap.put("Fastbond", 1); pointMap.put("Flash", 1); @@ -57,25 +59,25 @@ public class AusHighlander extends Constructed { pointMap.put("Lim-Dul's Vault", 1); pointMap.put("Mana Drain", 1); pointMap.put("Mana Vault", 1); - pointMap.put("Memory Jar", 1); pointMap.put("Merchant Scroll", 1); pointMap.put("Mishra's Workshop", 1); pointMap.put("Natural Order", 1); pointMap.put("Oath of Druids", 1); pointMap.put("Personal Tutor", 1); + pointMap.put("Scheming Symmetry", 1); pointMap.put("Sensei's Divining Top", 1); pointMap.put("Skullclamp", 1); pointMap.put("Snapcaster Mage", 1); pointMap.put("Stoneforge Mystic", 1); - pointMap.put("Strip Mine", 1); pointMap.put("Survival of the Fittest", 1); pointMap.put("Tainted Pact", 1); + pointMap.put("Tendrils of Agony", 1); pointMap.put("Time Spiral", 1); pointMap.put("Timetwister", 1); - pointMap.put("True-Name Nemesis", 1); pointMap.put("Umezawa's Jitte", 1); pointMap.put("Wasteland", 1); pointMap.put("Yawgmoth's Bargain", 1); + pointMap.put("Yawgmoth's Will", 1); } public AusHighlander() { From 121a93b9b4e3296e265be400738e5c07e4887b74 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sat, 12 Oct 2019 17:08:26 -0400 Subject: [PATCH 359/373] fixed Ayara, First of Locthwain triggering off of noncreature permanents (fixes #6013) --- Mage.Sets/src/mage/cards/a/AyaraFirstOfLocthwain.java | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/Mage.Sets/src/mage/cards/a/AyaraFirstOfLocthwain.java b/Mage.Sets/src/mage/cards/a/AyaraFirstOfLocthwain.java index 64d5860988..15d2e1a9f4 100644 --- a/Mage.Sets/src/mage/cards/a/AyaraFirstOfLocthwain.java +++ b/Mage.Sets/src/mage/cards/a/AyaraFirstOfLocthwain.java @@ -18,6 +18,7 @@ import mage.constants.SuperType; import mage.filter.FilterPermanent; import mage.filter.common.FilterControlledCreaturePermanent; import mage.filter.common.FilterControlledPermanent; +import mage.filter.common.FilterCreaturePermanent; import mage.filter.predicate.mageobject.ColorPredicate; import mage.target.common.TargetControlledPermanent; @@ -29,7 +30,7 @@ import java.util.UUID; public final class AyaraFirstOfLocthwain extends CardImpl { private static final FilterPermanent filter - = new FilterPermanent("{this} or another black creature"); + = new FilterCreaturePermanent("{this} or another black creature"); private static final FilterControlledPermanent filter2 = new FilterControlledCreaturePermanent("another black creature"); From 041fb31205122cfabcf579b90277e908caf4fc1d Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Sun, 13 Oct 2019 13:20:21 -0400 Subject: [PATCH 360/373] Implemented Silent Assassin --- .../src/mage/cards/s/SilentAssassin.java | 54 +++++++++++++++++++ Mage.Sets/src/mage/sets/MercadianMasques.java | 1 + 2 files changed, 55 insertions(+) create mode 100644 Mage.Sets/src/mage/cards/s/SilentAssassin.java diff --git a/Mage.Sets/src/mage/cards/s/SilentAssassin.java b/Mage.Sets/src/mage/cards/s/SilentAssassin.java new file mode 100644 index 0000000000..d433cbf48b --- /dev/null +++ b/Mage.Sets/src/mage/cards/s/SilentAssassin.java @@ -0,0 +1,54 @@ +package mage.cards.s; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.SimpleActivatedAbility; +import mage.abilities.common.delayed.AtTheEndOfCombatDelayedTriggeredAbility; +import mage.abilities.costs.mana.ManaCostsImpl; +import mage.abilities.effects.common.CreateDelayedTriggeredAbilityEffect; +import mage.abilities.effects.common.DestroyTargetEffect; +import mage.cards.CardImpl; +import mage.cards.CardSetInfo; +import mage.constants.CardType; +import mage.constants.SubType; +import mage.filter.FilterPermanent; +import mage.filter.common.FilterBlockingCreature; +import mage.target.TargetPermanent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class SilentAssassin extends CardImpl { + + private static final FilterPermanent filter = new FilterBlockingCreature(); + + public SilentAssassin(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{B}{B}"); + + this.subtype.add(SubType.HUMAN); + this.subtype.add(SubType.MERCENARY); + this.subtype.add(SubType.ASSASSIN); + this.power = new MageInt(2); + this.toughness = new MageInt(1); + + // {3}{B}: Destroy target blocking creature at end of combat. + Ability ability = new SimpleActivatedAbility(new CreateDelayedTriggeredAbilityEffect( + new AtTheEndOfCombatDelayedTriggeredAbility( + new DestroyTargetEffect().setText("destroy target blocking creature") + ), true + ), new ManaCostsImpl("{3}{B}")); + ability.addTarget(new TargetPermanent(filter)); + this.addAbility(ability); + } + + private SilentAssassin(final SilentAssassin card) { + super(card); + } + + @Override + public SilentAssassin copy() { + return new SilentAssassin(this); + } +} diff --git a/Mage.Sets/src/mage/sets/MercadianMasques.java b/Mage.Sets/src/mage/sets/MercadianMasques.java index f715c64f41..259ea4bb02 100644 --- a/Mage.Sets/src/mage/sets/MercadianMasques.java +++ b/Mage.Sets/src/mage/sets/MercadianMasques.java @@ -287,6 +287,7 @@ public final class MercadianMasques extends ExpansionSet { cards.add(new SetCardInfo("Sever Soul", 159, Rarity.COMMON, mage.cards.s.SeverSoul.class)); cards.add(new SetCardInfo("Shock Troops", 212, Rarity.COMMON, mage.cards.s.ShockTroops.class)); cards.add(new SetCardInfo("Shoving Match", 103, Rarity.UNCOMMON, mage.cards.s.ShovingMatch.class)); + cards.add(new SetCardInfo("Silent Assassin", 160, Rarity.RARE, mage.cards.s.SilentAssassin.class)); cards.add(new SetCardInfo("Silverglade Elemental", 269, Rarity.COMMON, mage.cards.s.SilvergladeElemental.class)); cards.add(new SetCardInfo("Silverglade Pathfinder", 270, Rarity.UNCOMMON, mage.cards.s.SilvergladePathfinder.class)); cards.add(new SetCardInfo("Sizzle", 213, Rarity.COMMON, mage.cards.s.Sizzle.class)); From 35a4f1a2fda881b0d03375cb8d2aa9f3e19bebfa Mon Sep 17 00:00:00 2001 From: acosta Date: Wed, 16 Oct 2019 10:44:59 +0200 Subject: [PATCH 361/373] Add Centurion banlist --- .../mage/client/dialog/NewTableDialog.java | 2 + .../java/mage/client/table/TablesPanel.java | 2 +- .../src/mage/deck/CenturionCommander.java | 86 +++++++++++++++++++ .../src/mage/game/CommanderDuelMatch.java | 2 +- Mage.Server/config/config.xml | 1 + Mage.Server/release/config/config.xml | 1 + 6 files changed, 92 insertions(+), 2 deletions(-) create mode 100644 Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander.java diff --git a/Mage.Client/src/main/java/mage/client/dialog/NewTableDialog.java b/Mage.Client/src/main/java/mage/client/dialog/NewTableDialog.java index 503f59e6b6..a99ef8bec2 100644 --- a/Mage.Client/src/main/java/mage/client/dialog/NewTableDialog.java +++ b/Mage.Client/src/main/java/mage/client/dialog/NewTableDialog.java @@ -637,6 +637,7 @@ public class NewTableDialog extends MageDialog { case "Variant Magic - Commander": case "Variant Magic - Duel Commander": case "Variant Magic - MTGO 1v1 Commander": + case "Variant Magic - Centurion Commander": case "Variant Magic - Penny Dreadful Commander": if (!options.getGameType().startsWith("Commander")) { JOptionPane.showMessageDialog(MageFrame.getDesktop(), "Deck type Commander needs also a Commander game type", "Error", JOptionPane.ERROR_MESSAGE); @@ -683,6 +684,7 @@ public class NewTableDialog extends MageDialog { if (!options.getDeckType().equals("Variant Magic - Commander") && !options.getDeckType().equals("Variant Magic - Duel Commander") && !options.getDeckType().equals("Variant Magic - MTGO 1v1 Commander") + && !options.getDeckType().equals("Variant Magic - Centurion Commander") && !options.getDeckType().equals("Variant Magic - Freeform Commander") && !options.getDeckType().equals("Variant Magic - Penny Dreadful Commander")) { JOptionPane.showMessageDialog(MageFrame.getDesktop(), "Deck type Commander needs also a Commander game type", "Error", JOptionPane.ERROR_MESSAGE); diff --git a/Mage.Client/src/main/java/mage/client/table/TablesPanel.java b/Mage.Client/src/main/java/mage/client/table/TablesPanel.java index 5d01790591..a6e001d385 100644 --- a/Mage.Client/src/main/java/mage/client/table/TablesPanel.java +++ b/Mage.Client/src/main/java/mage/client/table/TablesPanel.java @@ -812,7 +812,7 @@ public class TablesPanel extends javax.swing.JPanel { formatFilterList.add(RowFilter.regexFilter("^Constructed - Premodern", TablesTableModel.COLUMN_DECK_TYPE)); } if (btnFormatCommander.isSelected()) { - formatFilterList.add(RowFilter.regexFilter("^Commander|^Duel Commander|^Penny Dreadful Commander|^Freeform Commander|^MTGO 1v1 Commander|^Duel Brawl|^Brawl", TablesTableModel.COLUMN_DECK_TYPE)); + formatFilterList.add(RowFilter.regexFilter("^Commander|^Duel Commander|^Centurion Commander|^Penny Dreadful Commander|^Freeform Commander|^MTGO 1v1 Commander|^Duel Brawl|^Brawl", TablesTableModel.COLUMN_DECK_TYPE)); } if (btnFormatTinyLeader.isSelected()) { formatFilterList.add(RowFilter.regexFilter("^Tiny", TablesTableModel.COLUMN_DECK_TYPE)); diff --git a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander.java b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander.java new file mode 100644 index 0000000000..2e8352cc44 --- /dev/null +++ b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander.java @@ -0,0 +1,86 @@ + +package mage.deck; + +/** + * + * @author andreacosta + */ +public class CenturionCommander extends Commander { + + public CenturionCommander() { + super("Centurion Commander"); + banned.add("Ancestral Recall"); + banned.add("Ancient Tomb"); + banned.add("Back to Basic"); + banned.add("Balance"); + banned.add("Bazaar of Baghdad"); + banned.add("Black Lotus"); + banned.add("Cataclysm"); + banned.add("Channel"); + banned.add("Chaos Orb"); + banned.add("Chrome Mox"); + banned.add("Demonic Tutor"); + banned.add("Dig Through Time"); + banned.add("Emrakul, the Aeons Torn"); + banned.add("Emrakul, the Promised End"); + banned.add("Entomb"); + banned.add("Erayo, Soratami Ascendant"); + banned.add("Falling Star"); + banned.add("Fastbond"); + banned.add("Food Chain"); + banned.add("Gaea’s Cradle"); + banned.add("Gifts Ungiven"); + banned.add("Grim Monolith"); + banned.add("Grindstone"); + banned.add("Hermit Druid"); + banned.add("High Tide"); + banned.add("Humility"); + banned.add("Imperial Seal"); + banned.add("Karakas"); + banned.add("Library of Alexandria"); + banned.add("Mana Crypt"); + banned.add("Mana Drain"); + banned.add("Mana Vault"); + banned.add("Mishra’s Workshop"); + banned.add("Mind Twist"); + banned.add("Mox Diamond"); + banned.add("Mox Emerald"); + banned.add("Mox Jet"); + banned.add("Mox Pearl"); + banned.add("Mox Ruby"); + banned.add("Mox Sapphire"); + banned.add("Mystical Tutor"); + banned.add("Natural Order"); + banned.add("Necropotence"); + banned.add("Oath of Druids"); + banned.add("Protean Hulk"); + banned.add("Sensei’s Diving Top"); + banned.add("Serra Ascendant"); + banned.add("Sharazad"); + banned.add("Survival of the Fittest"); + banned.add("Sol Ring"); + banned.add("Strip Mine"); + banned.add("The Tabernacle at Pendrell Vale"); + banned.add("Time Vault"); + banned.add("Time Walk"); + banned.add("Tinker"); + banned.add("Tolarian Academy"); + banned.add("Treasure Cruise"); + banned.add("Vampiric Tutor"); + banned.add("Vanishing"); + banned.add("Winter Orb"); + banned.add("Yawgmoth’s Bargain"); + + bannedCommander.add("Baral, Chief of Compliance"); + bannedCommander.add("Derevi, Empyrial Tactician"); + bannedCommander.add("Edgar Markov"); + bannedCommander.add("Kess, Dissident Mage"); + bannedCommander.add("Rofellos, Llanowar Emissary"); + + bannedCommander.add("Rowan Kenrith"); + bannedCommander.add("Tymna the Weaver"); + bannedCommander.add("Will Kenrith"); + bannedCommander.add("Vial Smasher The Fierce"); + } + +} diff --git a/Mage.Server.Plugins/Mage.Game.CommanderDuel/src/mage/game/CommanderDuelMatch.java b/Mage.Server.Plugins/Mage.Game.CommanderDuel/src/mage/game/CommanderDuelMatch.java index f03473c6e2..a6008061ec 100644 --- a/Mage.Server.Plugins/Mage.Game.CommanderDuel/src/mage/game/CommanderDuelMatch.java +++ b/Mage.Server.Plugins/Mage.Game.CommanderDuel/src/mage/game/CommanderDuelMatch.java @@ -22,7 +22,7 @@ public class CommanderDuelMatch extends MatchImpl { startLife = 20; // Starting with the Commander 2016 update (on November 11th, 2016), Duel Commander will be played with 20 life points instead of 30. checkCommanderDamage = false; // since nov 16 duel commander uses no longer commander damage rule } - if (options.getDeckType().equals("Variant Magic - MTGO 1v1 Commander")) { + if (options.getDeckType().equals("Variant Magic - MTGO 1v1 Commander") || options.getDeckType().equals("Variant Magic - Centurion Commander")) { startLife = 30; } Mulligan mulligan = options.getMulliganType().getMulligan(options.getFreeMulligans()); diff --git a/Mage.Server/config/config.xml b/Mage.Server/config/config.xml index 625a01d39d..098bbe7c3d 100644 --- a/Mage.Server/config/config.xml +++ b/Mage.Server/config/config.xml @@ -169,6 +169,7 @@ + diff --git a/Mage.Server/release/config/config.xml b/Mage.Server/release/config/config.xml index 2584861224..111ef0e394 100644 --- a/Mage.Server/release/config/config.xml +++ b/Mage.Server/release/config/config.xml @@ -163,6 +163,7 @@ + From c49e856e564ae2a91c5e0248a3b74de2c0839aeb Mon Sep 17 00:00:00 2001 From: acosta Date: Wed, 16 Oct 2019 11:33:22 +0200 Subject: [PATCH 362/373] Remove banned partners --- .../src/mage/deck/CenturionCommander.java | 5 ----- 1 file changed, 5 deletions(-) diff --git a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander.java b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander.java index 2e8352cc44..d98617ad46 100644 --- a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander.java +++ b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander.java @@ -76,11 +76,6 @@ public class CenturionCommander extends Commander { bannedCommander.add("Edgar Markov"); bannedCommander.add("Kess, Dissident Mage"); bannedCommander.add("Rofellos, Llanowar Emissary"); - - bannedCommander.add("Rowan Kenrith"); - bannedCommander.add("Tymna the Weaver"); - bannedCommander.add("Will Kenrith"); - bannedCommander.add("Vial Smasher The Fierce"); } } From 4a7bf89d8f9999af4270f1738d34f208c39833c0 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 16 Oct 2019 12:38:30 -0400 Subject: [PATCH 363/373] added support for banned partners in commander variants --- .../src/mage/deck/Commander.java | 30 +++++++++++-------- 1 file changed, 18 insertions(+), 12 deletions(-) diff --git a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Commander.java b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Commander.java index 431aa35cbf..8930973535 100644 --- a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Commander.java +++ b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Commander.java @@ -21,7 +21,8 @@ import java.util.*; */ public class Commander extends Constructed { - protected List bannedCommander = new ArrayList<>(); + protected final List bannedCommander = new ArrayList<>(); + protected final List bannedPartner = new ArrayList<>(); protected boolean partnerAllowed = true; public Commander() { @@ -129,18 +130,23 @@ public class Commander extends Constructed { invalid.put("Commander", "Commander invalid (" + commander.getName() + ')'); valid = false; } - if (deck.getSideboard().size() == 2 && !commander.getAbilities().contains(PartnerAbility.getInstance())) { - boolean partnersWith = false; - for (Ability ability : commander.getAbilities()) { - if (ability instanceof PartnerWithAbility - && commanderNames.contains(((PartnerWithAbility) ability).getPartnerName())) { - partnersWith = true; - break; + if (deck.getSideboard().size() == 2) { + if (commander.getAbilities().contains(PartnerAbility.getInstance())) { + if (bannedPartner.contains(commander.getName())) { + invalid.put("Commander", "Partner banned (" + commander.getName() + ')'); + valid = false; + } + } else { + boolean partnersWith = commander.getAbilities() + .stream() + .filter(PartnerWithAbility.class::isInstance) + .map(PartnerWithAbility.class::cast) + .map(PartnerWithAbility::getPartnerName) + .anyMatch(commanderNames::contains); + if (!partnersWith) { + invalid.put("Commander", "Commander without Partner (" + commander.getName() + ')'); + valid = false; } - } - if (!partnersWith) { - invalid.put("Commander", "Commander without Partner (" + commander.getName() + ')'); - valid = false; } } ManaUtil.collectColorIdentity(colorIdentity, commander.getColorIdentity()); From bafac3ca7dbe753414a69832b7a951a895e39888 Mon Sep 17 00:00:00 2001 From: acosta Date: Wed, 16 Oct 2019 20:57:40 +0200 Subject: [PATCH 364/373] Add banned partners --- .../CenturionCommander_20191016205159.java | 81 +++++++++++++++++ .../CenturionCommander_20191016205524.java | 83 +++++++++++++++++ .../CenturionCommander_20191016205526.java | 83 +++++++++++++++++ .../CenturionCommander_20191016205550.java | 87 ++++++++++++++++++ .../CenturionCommander_20191016205555.java | 87 ++++++++++++++++++ .../CenturionCommander_20191016205556.java | 87 ++++++++++++++++++ .../CenturionCommander_20191016205600.java | 87 ++++++++++++++++++ .../CenturionCommander_20191016205601.java | 87 ++++++++++++++++++ .../CenturionCommander_20191016205603.java | 90 +++++++++++++++++++ .../CenturionCommander_20191016205606.java | 90 +++++++++++++++++++ .../CenturionCommander_20191016205607.java | 90 +++++++++++++++++++ .../CenturionCommander_20191016205608.java | 90 +++++++++++++++++++ .../CenturionCommander_20191016205611.java | 90 +++++++++++++++++++ .../CenturionCommander_20191016205616.java | 90 +++++++++++++++++++ .../CenturionCommander_20191016205618.java | 90 +++++++++++++++++++ .../CenturionCommander_20191016205619.java | 90 +++++++++++++++++++ .../CenturionCommander_20191016205622.java | 90 +++++++++++++++++++ .../CenturionCommander_20191016205627.java | 86 ++++++++++++++++++ .../CenturionCommander_20191016205628.java | 86 ++++++++++++++++++ .../src/mage/deck/CenturionCommander.java | 5 ++ 20 files changed, 1669 insertions(+) create mode 100644 .history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205159.java create mode 100644 .history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205524.java create mode 100644 .history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205526.java create mode 100644 .history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205550.java create mode 100644 .history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205555.java create mode 100644 .history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205556.java create mode 100644 .history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205600.java create mode 100644 .history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205601.java create mode 100644 .history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205603.java create mode 100644 .history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205606.java create mode 100644 .history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205607.java create mode 100644 .history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205608.java create mode 100644 .history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205611.java create mode 100644 .history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205616.java create mode 100644 .history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205618.java create mode 100644 .history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205619.java create mode 100644 .history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205622.java create mode 100644 .history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205627.java create mode 100644 .history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205628.java diff --git a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205159.java b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205159.java new file mode 100644 index 0000000000..d98617ad46 --- /dev/null +++ b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205159.java @@ -0,0 +1,81 @@ + +package mage.deck; + +/** + * + * @author andreacosta + */ +public class CenturionCommander extends Commander { + + public CenturionCommander() { + super("Centurion Commander"); + banned.add("Ancestral Recall"); + banned.add("Ancient Tomb"); + banned.add("Back to Basic"); + banned.add("Balance"); + banned.add("Bazaar of Baghdad"); + banned.add("Black Lotus"); + banned.add("Cataclysm"); + banned.add("Channel"); + banned.add("Chaos Orb"); + banned.add("Chrome Mox"); + banned.add("Demonic Tutor"); + banned.add("Dig Through Time"); + banned.add("Emrakul, the Aeons Torn"); + banned.add("Emrakul, the Promised End"); + banned.add("Entomb"); + banned.add("Erayo, Soratami Ascendant"); + banned.add("Falling Star"); + banned.add("Fastbond"); + banned.add("Food Chain"); + banned.add("Gaea’s Cradle"); + banned.add("Gifts Ungiven"); + banned.add("Grim Monolith"); + banned.add("Grindstone"); + banned.add("Hermit Druid"); + banned.add("High Tide"); + banned.add("Humility"); + banned.add("Imperial Seal"); + banned.add("Karakas"); + banned.add("Library of Alexandria"); + banned.add("Mana Crypt"); + banned.add("Mana Drain"); + banned.add("Mana Vault"); + banned.add("Mishra’s Workshop"); + banned.add("Mind Twist"); + banned.add("Mox Diamond"); + banned.add("Mox Emerald"); + banned.add("Mox Jet"); + banned.add("Mox Pearl"); + banned.add("Mox Ruby"); + banned.add("Mox Sapphire"); + banned.add("Mystical Tutor"); + banned.add("Natural Order"); + banned.add("Necropotence"); + banned.add("Oath of Druids"); + banned.add("Protean Hulk"); + banned.add("Sensei’s Diving Top"); + banned.add("Serra Ascendant"); + banned.add("Sharazad"); + banned.add("Survival of the Fittest"); + banned.add("Sol Ring"); + banned.add("Strip Mine"); + banned.add("The Tabernacle at Pendrell Vale"); + banned.add("Time Vault"); + banned.add("Time Walk"); + banned.add("Tinker"); + banned.add("Tolarian Academy"); + banned.add("Treasure Cruise"); + banned.add("Vampiric Tutor"); + banned.add("Vanishing"); + banned.add("Winter Orb"); + banned.add("Yawgmoth’s Bargain"); + + bannedCommander.add("Baral, Chief of Compliance"); + bannedCommander.add("Derevi, Empyrial Tactician"); + bannedCommander.add("Edgar Markov"); + bannedCommander.add("Kess, Dissident Mage"); + bannedCommander.add("Rofellos, Llanowar Emissary"); + } + +} diff --git a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205524.java b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205524.java new file mode 100644 index 0000000000..c4ecd5d406 --- /dev/null +++ b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205524.java @@ -0,0 +1,83 @@ + +package mage.deck; + +/** + * + * @author andreacosta + */ +public class CenturionCommander extends Commander { + + public CenturionCommander() { + super("Centurion Commander"); + banned.add("Ancestral Recall"); + banned.add("Ancient Tomb"); + banned.add("Back to Basic"); + banned.add("Balance"); + banned.add("Bazaar of Baghdad"); + banned.add("Black Lotus"); + banned.add("Cataclysm"); + banned.add("Channel"); + banned.add("Chaos Orb"); + banned.add("Chrome Mox"); + banned.add("Demonic Tutor"); + banned.add("Dig Through Time"); + banned.add("Emrakul, the Aeons Torn"); + banned.add("Emrakul, the Promised End"); + banned.add("Entomb"); + banned.add("Erayo, Soratami Ascendant"); + banned.add("Falling Star"); + banned.add("Fastbond"); + banned.add("Food Chain"); + banned.add("Gaea’s Cradle"); + banned.add("Gifts Ungiven"); + banned.add("Grim Monolith"); + banned.add("Grindstone"); + banned.add("Hermit Druid"); + banned.add("High Tide"); + banned.add("Humility"); + banned.add("Imperial Seal"); + banned.add("Karakas"); + banned.add("Library of Alexandria"); + banned.add("Mana Crypt"); + banned.add("Mana Drain"); + banned.add("Mana Vault"); + banned.add("Mishra’s Workshop"); + banned.add("Mind Twist"); + banned.add("Mox Diamond"); + banned.add("Mox Emerald"); + banned.add("Mox Jet"); + banned.add("Mox Pearl"); + banned.add("Mox Ruby"); + banned.add("Mox Sapphire"); + banned.add("Mystical Tutor"); + banned.add("Natural Order"); + banned.add("Necropotence"); + banned.add("Oath of Druids"); + banned.add("Protean Hulk"); + banned.add("Sensei’s Diving Top"); + banned.add("Serra Ascendant"); + banned.add("Sharazad"); + banned.add("Survival of the Fittest"); + banned.add("Sol Ring"); + banned.add("Strip Mine"); + banned.add("The Tabernacle at Pendrell Vale"); + banned.add("Time Vault"); + banned.add("Time Walk"); + banned.add("Tinker"); + banned.add("Tolarian Academy"); + banned.add("Treasure Cruise"); + banned.add("Vampiric Tutor"); + banned.add("Vanishing"); + banned.add("Winter Orb"); + banned.add("Yawgmoth’s Bargain"); + + bannedCommander.add("Baral, Chief of Compliance"); + bannedCommander.add("Derevi, Empyrial Tactician"); + bannedCommander.add("Edgar Markov"); + bannedCommander.add("Kess, Dissident Mage"); + bannedCommander.add("Rofellos, Llanowar Emissary"); + + bannedPartner.add() + } + +} diff --git a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205526.java b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205526.java new file mode 100644 index 0000000000..913a930a2d --- /dev/null +++ b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205526.java @@ -0,0 +1,83 @@ + +package mage.deck; + +/** + * + * @author andreacosta + */ +public class CenturionCommander extends Commander { + + public CenturionCommander() { + super("Centurion Commander"); + banned.add("Ancestral Recall"); + banned.add("Ancient Tomb"); + banned.add("Back to Basic"); + banned.add("Balance"); + banned.add("Bazaar of Baghdad"); + banned.add("Black Lotus"); + banned.add("Cataclysm"); + banned.add("Channel"); + banned.add("Chaos Orb"); + banned.add("Chrome Mox"); + banned.add("Demonic Tutor"); + banned.add("Dig Through Time"); + banned.add("Emrakul, the Aeons Torn"); + banned.add("Emrakul, the Promised End"); + banned.add("Entomb"); + banned.add("Erayo, Soratami Ascendant"); + banned.add("Falling Star"); + banned.add("Fastbond"); + banned.add("Food Chain"); + banned.add("Gaea’s Cradle"); + banned.add("Gifts Ungiven"); + banned.add("Grim Monolith"); + banned.add("Grindstone"); + banned.add("Hermit Druid"); + banned.add("High Tide"); + banned.add("Humility"); + banned.add("Imperial Seal"); + banned.add("Karakas"); + banned.add("Library of Alexandria"); + banned.add("Mana Crypt"); + banned.add("Mana Drain"); + banned.add("Mana Vault"); + banned.add("Mishra’s Workshop"); + banned.add("Mind Twist"); + banned.add("Mox Diamond"); + banned.add("Mox Emerald"); + banned.add("Mox Jet"); + banned.add("Mox Pearl"); + banned.add("Mox Ruby"); + banned.add("Mox Sapphire"); + banned.add("Mystical Tutor"); + banned.add("Natural Order"); + banned.add("Necropotence"); + banned.add("Oath of Druids"); + banned.add("Protean Hulk"); + banned.add("Sensei’s Diving Top"); + banned.add("Serra Ascendant"); + banned.add("Sharazad"); + banned.add("Survival of the Fittest"); + banned.add("Sol Ring"); + banned.add("Strip Mine"); + banned.add("The Tabernacle at Pendrell Vale"); + banned.add("Time Vault"); + banned.add("Time Walk"); + banned.add("Tinker"); + banned.add("Tolarian Academy"); + banned.add("Treasure Cruise"); + banned.add("Vampiric Tutor"); + banned.add("Vanishing"); + banned.add("Winter Orb"); + banned.add("Yawgmoth’s Bargain"); + + bannedCommander.add("Baral, Chief of Compliance"); + bannedCommander.add("Derevi, Empyrial Tactician"); + bannedCommander.add("Edgar Markov"); + bannedCommander.add("Kess, Dissident Mage"); + bannedCommander.add("Rofellos, Llanowar Emissary"); + + bannedPartner.add(); + } + +} diff --git a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205550.java b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205550.java new file mode 100644 index 0000000000..d1da8c98bd --- /dev/null +++ b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205550.java @@ -0,0 +1,87 @@ + +package mage.deck; + +/** + * + * @author andreacosta + */ +public class CenturionCommander extends Commander { + + public CenturionCommander() { + super("Centurion Commander"); + banned.add("Ancestral Recall"); + banned.add("Ancient Tomb"); + banned.add("Back to Basic"); + banned.add("Balance"); + banned.add("Bazaar of Baghdad"); + banned.add("Black Lotus"); + banned.add("Cataclysm"); + banned.add("Channel"); + banned.add("Chaos Orb"); + banned.add("Chrome Mox"); + banned.add("Demonic Tutor"); + banned.add("Dig Through Time"); + banned.add("Emrakul, the Aeons Torn"); + banned.add("Emrakul, the Promised End"); + banned.add("Entomb"); + banned.add("Erayo, Soratami Ascendant"); + banned.add("Falling Star"); + banned.add("Fastbond"); + banned.add("Food Chain"); + banned.add("Gaea’s Cradle"); + banned.add("Gifts Ungiven"); + banned.add("Grim Monolith"); + banned.add("Grindstone"); + banned.add("Hermit Druid"); + banned.add("High Tide"); + banned.add("Humility"); + banned.add("Imperial Seal"); + banned.add("Karakas"); + banned.add("Library of Alexandria"); + banned.add("Mana Crypt"); + banned.add("Mana Drain"); + banned.add("Mana Vault"); + banned.add("Mishra’s Workshop"); + banned.add("Mind Twist"); + banned.add("Mox Diamond"); + banned.add("Mox Emerald"); + banned.add("Mox Jet"); + banned.add("Mox Pearl"); + banned.add("Mox Ruby"); + banned.add("Mox Sapphire"); + banned.add("Mystical Tutor"); + banned.add("Natural Order"); + banned.add("Necropotence"); + banned.add("Oath of Druids"); + banned.add("Protean Hulk"); + banned.add("Sensei’s Diving Top"); + banned.add("Serra Ascendant"); + banned.add("Sharazad"); + banned.add("Survival of the Fittest"); + banned.add("Sol Ring"); + banned.add("Strip Mine"); + banned.add("The Tabernacle at Pendrell Vale"); + banned.add("Time Vault"); + banned.add("Time Walk"); + banned.add("Tinker"); + banned.add("Tolarian Academy"); + banned.add("Treasure Cruise"); + banned.add("Vampiric Tutor"); + banned.add("Vanishing"); + banned.add("Winter Orb"); + banned.add("Yawgmoth’s Bargain"); + + bannedCommander.add("Baral, Chief of Compliance"); + bannedCommander.add("Derevi, Empyrial Tactician"); + bannedCommander.add("Edgar Markov"); + bannedCommander.add("Kess, Dissident Mage"); + bannedCommander.add("Rofellos, Llanowar Emissary"); + + bannedPartner.add(); + Rowan Kenrith +Tymna the Weaver +Will Kenrith +Vial Smasher The Fierce + } + +} diff --git a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205555.java b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205555.java new file mode 100644 index 0000000000..25f5ce669b --- /dev/null +++ b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205555.java @@ -0,0 +1,87 @@ + +package mage.deck; + +/** + * + * @author andreacosta + */ +public class CenturionCommander extends Commander { + + public CenturionCommander() { + super("Centurion Commander"); + banned.add("Ancestral Recall"); + banned.add("Ancient Tomb"); + banned.add("Back to Basic"); + banned.add("Balance"); + banned.add("Bazaar of Baghdad"); + banned.add("Black Lotus"); + banned.add("Cataclysm"); + banned.add("Channel"); + banned.add("Chaos Orb"); + banned.add("Chrome Mox"); + banned.add("Demonic Tutor"); + banned.add("Dig Through Time"); + banned.add("Emrakul, the Aeons Torn"); + banned.add("Emrakul, the Promised End"); + banned.add("Entomb"); + banned.add("Erayo, Soratami Ascendant"); + banned.add("Falling Star"); + banned.add("Fastbond"); + banned.add("Food Chain"); + banned.add("Gaea’s Cradle"); + banned.add("Gifts Ungiven"); + banned.add("Grim Monolith"); + banned.add("Grindstone"); + banned.add("Hermit Druid"); + banned.add("High Tide"); + banned.add("Humility"); + banned.add("Imperial Seal"); + banned.add("Karakas"); + banned.add("Library of Alexandria"); + banned.add("Mana Crypt"); + banned.add("Mana Drain"); + banned.add("Mana Vault"); + banned.add("Mishra’s Workshop"); + banned.add("Mind Twist"); + banned.add("Mox Diamond"); + banned.add("Mox Emerald"); + banned.add("Mox Jet"); + banned.add("Mox Pearl"); + banned.add("Mox Ruby"); + banned.add("Mox Sapphire"); + banned.add("Mystical Tutor"); + banned.add("Natural Order"); + banned.add("Necropotence"); + banned.add("Oath of Druids"); + banned.add("Protean Hulk"); + banned.add("Sensei’s Diving Top"); + banned.add("Serra Ascendant"); + banned.add("Sharazad"); + banned.add("Survival of the Fittest"); + banned.add("Sol Ring"); + banned.add("Strip Mine"); + banned.add("The Tabernacle at Pendrell Vale"); + banned.add("Time Vault"); + banned.add("Time Walk"); + banned.add("Tinker"); + banned.add("Tolarian Academy"); + banned.add("Treasure Cruise"); + banned.add("Vampiric Tutor"); + banned.add("Vanishing"); + banned.add("Winter Orb"); + banned.add("Yawgmoth’s Bargain"); + + bannedCommander.add("Baral, Chief of Compliance"); + bannedCommander.add("Derevi, Empyrial Tactician"); + bannedCommander.add("Edgar Markov"); + bannedCommander.add("Kess, Dissident Mage"); + bannedCommander.add("Rofellos, Llanowar Emissary"); + + bannedPartner.add(); + "Rowan Kenrith +Tymna the Weaver +Will Kenrith +Vial Smasher The Fierce + } + +} diff --git a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205556.java b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205556.java new file mode 100644 index 0000000000..cd63c763d8 --- /dev/null +++ b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205556.java @@ -0,0 +1,87 @@ + +package mage.deck; + +/** + * + * @author andreacosta + */ +public class CenturionCommander extends Commander { + + public CenturionCommander() { + super("Centurion Commander"); + banned.add("Ancestral Recall"); + banned.add("Ancient Tomb"); + banned.add("Back to Basic"); + banned.add("Balance"); + banned.add("Bazaar of Baghdad"); + banned.add("Black Lotus"); + banned.add("Cataclysm"); + banned.add("Channel"); + banned.add("Chaos Orb"); + banned.add("Chrome Mox"); + banned.add("Demonic Tutor"); + banned.add("Dig Through Time"); + banned.add("Emrakul, the Aeons Torn"); + banned.add("Emrakul, the Promised End"); + banned.add("Entomb"); + banned.add("Erayo, Soratami Ascendant"); + banned.add("Falling Star"); + banned.add("Fastbond"); + banned.add("Food Chain"); + banned.add("Gaea’s Cradle"); + banned.add("Gifts Ungiven"); + banned.add("Grim Monolith"); + banned.add("Grindstone"); + banned.add("Hermit Druid"); + banned.add("High Tide"); + banned.add("Humility"); + banned.add("Imperial Seal"); + banned.add("Karakas"); + banned.add("Library of Alexandria"); + banned.add("Mana Crypt"); + banned.add("Mana Drain"); + banned.add("Mana Vault"); + banned.add("Mishra’s Workshop"); + banned.add("Mind Twist"); + banned.add("Mox Diamond"); + banned.add("Mox Emerald"); + banned.add("Mox Jet"); + banned.add("Mox Pearl"); + banned.add("Mox Ruby"); + banned.add("Mox Sapphire"); + banned.add("Mystical Tutor"); + banned.add("Natural Order"); + banned.add("Necropotence"); + banned.add("Oath of Druids"); + banned.add("Protean Hulk"); + banned.add("Sensei’s Diving Top"); + banned.add("Serra Ascendant"); + banned.add("Sharazad"); + banned.add("Survival of the Fittest"); + banned.add("Sol Ring"); + banned.add("Strip Mine"); + banned.add("The Tabernacle at Pendrell Vale"); + banned.add("Time Vault"); + banned.add("Time Walk"); + banned.add("Tinker"); + banned.add("Tolarian Academy"); + banned.add("Treasure Cruise"); + banned.add("Vampiric Tutor"); + banned.add("Vanishing"); + banned.add("Winter Orb"); + banned.add("Yawgmoth’s Bargain"); + + bannedCommander.add("Baral, Chief of Compliance"); + bannedCommander.add("Derevi, Empyrial Tactician"); + bannedCommander.add("Edgar Markov"); + bannedCommander.add("Kess, Dissident Mage"); + bannedCommander.add("Rofellos, Llanowar Emissary"); + + bannedPartner.add(); + "Rowan Kenrith" +Tymna the Weaver +Will Kenrith +Vial Smasher The Fierce + } + +} diff --git a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205600.java b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205600.java new file mode 100644 index 0000000000..833a168d78 --- /dev/null +++ b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205600.java @@ -0,0 +1,87 @@ + +package mage.deck; + +/** + * + * @author andreacosta + */ +public class CenturionCommander extends Commander { + + public CenturionCommander() { + super("Centurion Commander"); + banned.add("Ancestral Recall"); + banned.add("Ancient Tomb"); + banned.add("Back to Basic"); + banned.add("Balance"); + banned.add("Bazaar of Baghdad"); + banned.add("Black Lotus"); + banned.add("Cataclysm"); + banned.add("Channel"); + banned.add("Chaos Orb"); + banned.add("Chrome Mox"); + banned.add("Demonic Tutor"); + banned.add("Dig Through Time"); + banned.add("Emrakul, the Aeons Torn"); + banned.add("Emrakul, the Promised End"); + banned.add("Entomb"); + banned.add("Erayo, Soratami Ascendant"); + banned.add("Falling Star"); + banned.add("Fastbond"); + banned.add("Food Chain"); + banned.add("Gaea’s Cradle"); + banned.add("Gifts Ungiven"); + banned.add("Grim Monolith"); + banned.add("Grindstone"); + banned.add("Hermit Druid"); + banned.add("High Tide"); + banned.add("Humility"); + banned.add("Imperial Seal"); + banned.add("Karakas"); + banned.add("Library of Alexandria"); + banned.add("Mana Crypt"); + banned.add("Mana Drain"); + banned.add("Mana Vault"); + banned.add("Mishra’s Workshop"); + banned.add("Mind Twist"); + banned.add("Mox Diamond"); + banned.add("Mox Emerald"); + banned.add("Mox Jet"); + banned.add("Mox Pearl"); + banned.add("Mox Ruby"); + banned.add("Mox Sapphire"); + banned.add("Mystical Tutor"); + banned.add("Natural Order"); + banned.add("Necropotence"); + banned.add("Oath of Druids"); + banned.add("Protean Hulk"); + banned.add("Sensei’s Diving Top"); + banned.add("Serra Ascendant"); + banned.add("Sharazad"); + banned.add("Survival of the Fittest"); + banned.add("Sol Ring"); + banned.add("Strip Mine"); + banned.add("The Tabernacle at Pendrell Vale"); + banned.add("Time Vault"); + banned.add("Time Walk"); + banned.add("Tinker"); + banned.add("Tolarian Academy"); + banned.add("Treasure Cruise"); + banned.add("Vampiric Tutor"); + banned.add("Vanishing"); + banned.add("Winter Orb"); + banned.add("Yawgmoth’s Bargain"); + + bannedCommander.add("Baral, Chief of Compliance"); + bannedCommander.add("Derevi, Empyrial Tactician"); + bannedCommander.add("Edgar Markov"); + bannedCommander.add("Kess, Dissident Mage"); + bannedCommander.add("Rofellos, Llanowar Emissary"); + + bannedPartner.add(); + +Tymna the Weaver +Will Kenrith +Vial Smasher The Fierce + } + +} diff --git a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205601.java b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205601.java new file mode 100644 index 0000000000..a70dec1b50 --- /dev/null +++ b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205601.java @@ -0,0 +1,87 @@ + +package mage.deck; + +/** + * + * @author andreacosta + */ +public class CenturionCommander extends Commander { + + public CenturionCommander() { + super("Centurion Commander"); + banned.add("Ancestral Recall"); + banned.add("Ancient Tomb"); + banned.add("Back to Basic"); + banned.add("Balance"); + banned.add("Bazaar of Baghdad"); + banned.add("Black Lotus"); + banned.add("Cataclysm"); + banned.add("Channel"); + banned.add("Chaos Orb"); + banned.add("Chrome Mox"); + banned.add("Demonic Tutor"); + banned.add("Dig Through Time"); + banned.add("Emrakul, the Aeons Torn"); + banned.add("Emrakul, the Promised End"); + banned.add("Entomb"); + banned.add("Erayo, Soratami Ascendant"); + banned.add("Falling Star"); + banned.add("Fastbond"); + banned.add("Food Chain"); + banned.add("Gaea’s Cradle"); + banned.add("Gifts Ungiven"); + banned.add("Grim Monolith"); + banned.add("Grindstone"); + banned.add("Hermit Druid"); + banned.add("High Tide"); + banned.add("Humility"); + banned.add("Imperial Seal"); + banned.add("Karakas"); + banned.add("Library of Alexandria"); + banned.add("Mana Crypt"); + banned.add("Mana Drain"); + banned.add("Mana Vault"); + banned.add("Mishra’s Workshop"); + banned.add("Mind Twist"); + banned.add("Mox Diamond"); + banned.add("Mox Emerald"); + banned.add("Mox Jet"); + banned.add("Mox Pearl"); + banned.add("Mox Ruby"); + banned.add("Mox Sapphire"); + banned.add("Mystical Tutor"); + banned.add("Natural Order"); + banned.add("Necropotence"); + banned.add("Oath of Druids"); + banned.add("Protean Hulk"); + banned.add("Sensei’s Diving Top"); + banned.add("Serra Ascendant"); + banned.add("Sharazad"); + banned.add("Survival of the Fittest"); + banned.add("Sol Ring"); + banned.add("Strip Mine"); + banned.add("The Tabernacle at Pendrell Vale"); + banned.add("Time Vault"); + banned.add("Time Walk"); + banned.add("Tinker"); + banned.add("Tolarian Academy"); + banned.add("Treasure Cruise"); + banned.add("Vampiric Tutor"); + banned.add("Vanishing"); + banned.add("Winter Orb"); + banned.add("Yawgmoth’s Bargain"); + + bannedCommander.add("Baral, Chief of Compliance"); + bannedCommander.add("Derevi, Empyrial Tactician"); + bannedCommander.add("Edgar Markov"); + bannedCommander.add("Kess, Dissident Mage"); + bannedCommander.add("Rofellos, Llanowar Emissary"); + + bannedPartner.add("Rowan Kenrith"); + +Tymna the Weaver +Will Kenrith +Vial Smasher The Fierce + } + +} diff --git a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205603.java b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205603.java new file mode 100644 index 0000000000..09928b5d8a --- /dev/null +++ b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205603.java @@ -0,0 +1,90 @@ + +package mage.deck; + +/** + * + * @author andreacosta + */ +public class CenturionCommander extends Commander { + + public CenturionCommander() { + super("Centurion Commander"); + banned.add("Ancestral Recall"); + banned.add("Ancient Tomb"); + banned.add("Back to Basic"); + banned.add("Balance"); + banned.add("Bazaar of Baghdad"); + banned.add("Black Lotus"); + banned.add("Cataclysm"); + banned.add("Channel"); + banned.add("Chaos Orb"); + banned.add("Chrome Mox"); + banned.add("Demonic Tutor"); + banned.add("Dig Through Time"); + banned.add("Emrakul, the Aeons Torn"); + banned.add("Emrakul, the Promised End"); + banned.add("Entomb"); + banned.add("Erayo, Soratami Ascendant"); + banned.add("Falling Star"); + banned.add("Fastbond"); + banned.add("Food Chain"); + banned.add("Gaea’s Cradle"); + banned.add("Gifts Ungiven"); + banned.add("Grim Monolith"); + banned.add("Grindstone"); + banned.add("Hermit Druid"); + banned.add("High Tide"); + banned.add("Humility"); + banned.add("Imperial Seal"); + banned.add("Karakas"); + banned.add("Library of Alexandria"); + banned.add("Mana Crypt"); + banned.add("Mana Drain"); + banned.add("Mana Vault"); + banned.add("Mishra’s Workshop"); + banned.add("Mind Twist"); + banned.add("Mox Diamond"); + banned.add("Mox Emerald"); + banned.add("Mox Jet"); + banned.add("Mox Pearl"); + banned.add("Mox Ruby"); + banned.add("Mox Sapphire"); + banned.add("Mystical Tutor"); + banned.add("Natural Order"); + banned.add("Necropotence"); + banned.add("Oath of Druids"); + banned.add("Protean Hulk"); + banned.add("Sensei’s Diving Top"); + banned.add("Serra Ascendant"); + banned.add("Sharazad"); + banned.add("Survival of the Fittest"); + banned.add("Sol Ring"); + banned.add("Strip Mine"); + banned.add("The Tabernacle at Pendrell Vale"); + banned.add("Time Vault"); + banned.add("Time Walk"); + banned.add("Tinker"); + banned.add("Tolarian Academy"); + banned.add("Treasure Cruise"); + banned.add("Vampiric Tutor"); + banned.add("Vanishing"); + banned.add("Winter Orb"); + banned.add("Yawgmoth’s Bargain"); + + bannedCommander.add("Baral, Chief of Compliance"); + bannedCommander.add("Derevi, Empyrial Tactician"); + bannedCommander.add("Edgar Markov"); + bannedCommander.add("Kess, Dissident Mage"); + bannedCommander.add("Rofellos, Llanowar Emissary"); + + bannedPartner.add("Rowan Kenrith"); + bannedPartner.add("Rowan Kenrith"); + bannedPartner.add("Rowan Kenrith"); + bannedPartner.add("Rowan Kenrith"); + +Tymna the Weaver +Will Kenrith +Vial Smasher The Fierce + } + +} diff --git a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205606.java b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205606.java new file mode 100644 index 0000000000..d7f0615159 --- /dev/null +++ b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205606.java @@ -0,0 +1,90 @@ + +package mage.deck; + +/** + * + * @author andreacosta + */ +public class CenturionCommander extends Commander { + + public CenturionCommander() { + super("Centurion Commander"); + banned.add("Ancestral Recall"); + banned.add("Ancient Tomb"); + banned.add("Back to Basic"); + banned.add("Balance"); + banned.add("Bazaar of Baghdad"); + banned.add("Black Lotus"); + banned.add("Cataclysm"); + banned.add("Channel"); + banned.add("Chaos Orb"); + banned.add("Chrome Mox"); + banned.add("Demonic Tutor"); + banned.add("Dig Through Time"); + banned.add("Emrakul, the Aeons Torn"); + banned.add("Emrakul, the Promised End"); + banned.add("Entomb"); + banned.add("Erayo, Soratami Ascendant"); + banned.add("Falling Star"); + banned.add("Fastbond"); + banned.add("Food Chain"); + banned.add("Gaea’s Cradle"); + banned.add("Gifts Ungiven"); + banned.add("Grim Monolith"); + banned.add("Grindstone"); + banned.add("Hermit Druid"); + banned.add("High Tide"); + banned.add("Humility"); + banned.add("Imperial Seal"); + banned.add("Karakas"); + banned.add("Library of Alexandria"); + banned.add("Mana Crypt"); + banned.add("Mana Drain"); + banned.add("Mana Vault"); + banned.add("Mishra’s Workshop"); + banned.add("Mind Twist"); + banned.add("Mox Diamond"); + banned.add("Mox Emerald"); + banned.add("Mox Jet"); + banned.add("Mox Pearl"); + banned.add("Mox Ruby"); + banned.add("Mox Sapphire"); + banned.add("Mystical Tutor"); + banned.add("Natural Order"); + banned.add("Necropotence"); + banned.add("Oath of Druids"); + banned.add("Protean Hulk"); + banned.add("Sensei’s Diving Top"); + banned.add("Serra Ascendant"); + banned.add("Sharazad"); + banned.add("Survival of the Fittest"); + banned.add("Sol Ring"); + banned.add("Strip Mine"); + banned.add("The Tabernacle at Pendrell Vale"); + banned.add("Time Vault"); + banned.add("Time Walk"); + banned.add("Tinker"); + banned.add("Tolarian Academy"); + banned.add("Treasure Cruise"); + banned.add("Vampiric Tutor"); + banned.add("Vanishing"); + banned.add("Winter Orb"); + banned.add("Yawgmoth’s Bargain"); + + bannedCommander.add("Baral, Chief of Compliance"); + bannedCommander.add("Derevi, Empyrial Tactician"); + bannedCommander.add("Edgar Markov"); + bannedCommander.add("Kess, Dissident Mage"); + bannedCommander.add("Rofellos, Llanowar Emissary"); + + bannedPartner.add("Rowan Kenrith"); + bannedPartner.add("Rowan Kenrith"); + bannedPartner.add("Rowan Kenrith"); + bannedPartner.add(""); + +Tymna the Weaver +Will Kenrith +Vial Smasher The Fierce + } + +} diff --git a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205607.java b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205607.java new file mode 100644 index 0000000000..96c3a7806f --- /dev/null +++ b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205607.java @@ -0,0 +1,90 @@ + +package mage.deck; + +/** + * + * @author andreacosta + */ +public class CenturionCommander extends Commander { + + public CenturionCommander() { + super("Centurion Commander"); + banned.add("Ancestral Recall"); + banned.add("Ancient Tomb"); + banned.add("Back to Basic"); + banned.add("Balance"); + banned.add("Bazaar of Baghdad"); + banned.add("Black Lotus"); + banned.add("Cataclysm"); + banned.add("Channel"); + banned.add("Chaos Orb"); + banned.add("Chrome Mox"); + banned.add("Demonic Tutor"); + banned.add("Dig Through Time"); + banned.add("Emrakul, the Aeons Torn"); + banned.add("Emrakul, the Promised End"); + banned.add("Entomb"); + banned.add("Erayo, Soratami Ascendant"); + banned.add("Falling Star"); + banned.add("Fastbond"); + banned.add("Food Chain"); + banned.add("Gaea’s Cradle"); + banned.add("Gifts Ungiven"); + banned.add("Grim Monolith"); + banned.add("Grindstone"); + banned.add("Hermit Druid"); + banned.add("High Tide"); + banned.add("Humility"); + banned.add("Imperial Seal"); + banned.add("Karakas"); + banned.add("Library of Alexandria"); + banned.add("Mana Crypt"); + banned.add("Mana Drain"); + banned.add("Mana Vault"); + banned.add("Mishra’s Workshop"); + banned.add("Mind Twist"); + banned.add("Mox Diamond"); + banned.add("Mox Emerald"); + banned.add("Mox Jet"); + banned.add("Mox Pearl"); + banned.add("Mox Ruby"); + banned.add("Mox Sapphire"); + banned.add("Mystical Tutor"); + banned.add("Natural Order"); + banned.add("Necropotence"); + banned.add("Oath of Druids"); + banned.add("Protean Hulk"); + banned.add("Sensei’s Diving Top"); + banned.add("Serra Ascendant"); + banned.add("Sharazad"); + banned.add("Survival of the Fittest"); + banned.add("Sol Ring"); + banned.add("Strip Mine"); + banned.add("The Tabernacle at Pendrell Vale"); + banned.add("Time Vault"); + banned.add("Time Walk"); + banned.add("Tinker"); + banned.add("Tolarian Academy"); + banned.add("Treasure Cruise"); + banned.add("Vampiric Tutor"); + banned.add("Vanishing"); + banned.add("Winter Orb"); + banned.add("Yawgmoth’s Bargain"); + + bannedCommander.add("Baral, Chief of Compliance"); + bannedCommander.add("Derevi, Empyrial Tactician"); + bannedCommander.add("Edgar Markov"); + bannedCommander.add("Kess, Dissident Mage"); + bannedCommander.add("Rofellos, Llanowar Emissary"); + + bannedPartner.add("Rowan Kenrith"); + bannedPartner.add("Rowan Kenrith"); + bannedPartner.add(""); + bannedPartner.add(""); + +Tymna the Weaver +Will Kenrith +Vial Smasher The Fierce + } + +} diff --git a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205608.java b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205608.java new file mode 100644 index 0000000000..75b6ca9e22 --- /dev/null +++ b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205608.java @@ -0,0 +1,90 @@ + +package mage.deck; + +/** + * + * @author andreacosta + */ +public class CenturionCommander extends Commander { + + public CenturionCommander() { + super("Centurion Commander"); + banned.add("Ancestral Recall"); + banned.add("Ancient Tomb"); + banned.add("Back to Basic"); + banned.add("Balance"); + banned.add("Bazaar of Baghdad"); + banned.add("Black Lotus"); + banned.add("Cataclysm"); + banned.add("Channel"); + banned.add("Chaos Orb"); + banned.add("Chrome Mox"); + banned.add("Demonic Tutor"); + banned.add("Dig Through Time"); + banned.add("Emrakul, the Aeons Torn"); + banned.add("Emrakul, the Promised End"); + banned.add("Entomb"); + banned.add("Erayo, Soratami Ascendant"); + banned.add("Falling Star"); + banned.add("Fastbond"); + banned.add("Food Chain"); + banned.add("Gaea’s Cradle"); + banned.add("Gifts Ungiven"); + banned.add("Grim Monolith"); + banned.add("Grindstone"); + banned.add("Hermit Druid"); + banned.add("High Tide"); + banned.add("Humility"); + banned.add("Imperial Seal"); + banned.add("Karakas"); + banned.add("Library of Alexandria"); + banned.add("Mana Crypt"); + banned.add("Mana Drain"); + banned.add("Mana Vault"); + banned.add("Mishra’s Workshop"); + banned.add("Mind Twist"); + banned.add("Mox Diamond"); + banned.add("Mox Emerald"); + banned.add("Mox Jet"); + banned.add("Mox Pearl"); + banned.add("Mox Ruby"); + banned.add("Mox Sapphire"); + banned.add("Mystical Tutor"); + banned.add("Natural Order"); + banned.add("Necropotence"); + banned.add("Oath of Druids"); + banned.add("Protean Hulk"); + banned.add("Sensei’s Diving Top"); + banned.add("Serra Ascendant"); + banned.add("Sharazad"); + banned.add("Survival of the Fittest"); + banned.add("Sol Ring"); + banned.add("Strip Mine"); + banned.add("The Tabernacle at Pendrell Vale"); + banned.add("Time Vault"); + banned.add("Time Walk"); + banned.add("Tinker"); + banned.add("Tolarian Academy"); + banned.add("Treasure Cruise"); + banned.add("Vampiric Tutor"); + banned.add("Vanishing"); + banned.add("Winter Orb"); + banned.add("Yawgmoth’s Bargain"); + + bannedCommander.add("Baral, Chief of Compliance"); + bannedCommander.add("Derevi, Empyrial Tactician"); + bannedCommander.add("Edgar Markov"); + bannedCommander.add("Kess, Dissident Mage"); + bannedCommander.add("Rofellos, Llanowar Emissary"); + + bannedPartner.add("Rowan Kenrith"); + bannedPartner.add(""); + bannedPartner.add(""); + bannedPartner.add(""); + +Tymna the Weaver +Will Kenrith +Vial Smasher The Fierce + } + +} diff --git a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205611.java b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205611.java new file mode 100644 index 0000000000..d3f636ed16 --- /dev/null +++ b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205611.java @@ -0,0 +1,90 @@ + +package mage.deck; + +/** + * + * @author andreacosta + */ +public class CenturionCommander extends Commander { + + public CenturionCommander() { + super("Centurion Commander"); + banned.add("Ancestral Recall"); + banned.add("Ancient Tomb"); + banned.add("Back to Basic"); + banned.add("Balance"); + banned.add("Bazaar of Baghdad"); + banned.add("Black Lotus"); + banned.add("Cataclysm"); + banned.add("Channel"); + banned.add("Chaos Orb"); + banned.add("Chrome Mox"); + banned.add("Demonic Tutor"); + banned.add("Dig Through Time"); + banned.add("Emrakul, the Aeons Torn"); + banned.add("Emrakul, the Promised End"); + banned.add("Entomb"); + banned.add("Erayo, Soratami Ascendant"); + banned.add("Falling Star"); + banned.add("Fastbond"); + banned.add("Food Chain"); + banned.add("Gaea’s Cradle"); + banned.add("Gifts Ungiven"); + banned.add("Grim Monolith"); + banned.add("Grindstone"); + banned.add("Hermit Druid"); + banned.add("High Tide"); + banned.add("Humility"); + banned.add("Imperial Seal"); + banned.add("Karakas"); + banned.add("Library of Alexandria"); + banned.add("Mana Crypt"); + banned.add("Mana Drain"); + banned.add("Mana Vault"); + banned.add("Mishra’s Workshop"); + banned.add("Mind Twist"); + banned.add("Mox Diamond"); + banned.add("Mox Emerald"); + banned.add("Mox Jet"); + banned.add("Mox Pearl"); + banned.add("Mox Ruby"); + banned.add("Mox Sapphire"); + banned.add("Mystical Tutor"); + banned.add("Natural Order"); + banned.add("Necropotence"); + banned.add("Oath of Druids"); + banned.add("Protean Hulk"); + banned.add("Sensei’s Diving Top"); + banned.add("Serra Ascendant"); + banned.add("Sharazad"); + banned.add("Survival of the Fittest"); + banned.add("Sol Ring"); + banned.add("Strip Mine"); + banned.add("The Tabernacle at Pendrell Vale"); + banned.add("Time Vault"); + banned.add("Time Walk"); + banned.add("Tinker"); + banned.add("Tolarian Academy"); + banned.add("Treasure Cruise"); + banned.add("Vampiric Tutor"); + banned.add("Vanishing"); + banned.add("Winter Orb"); + banned.add("Yawgmoth’s Bargain"); + + bannedCommander.add("Baral, Chief of Compliance"); + bannedCommander.add("Derevi, Empyrial Tactician"); + bannedCommander.add("Edgar Markov"); + bannedCommander.add("Kess, Dissident Mage"); + bannedCommander.add("Rofellos, Llanowar Emissary"); + + bannedPartner.add("Rowan Kenrith"); + bannedPartner.add(""); + bannedPartner.add(""); + bannedPartner.add(""); + + +Will Kenrith +Vial Smasher The Fierce + } + +} diff --git a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205616.java b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205616.java new file mode 100644 index 0000000000..017d21d275 --- /dev/null +++ b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205616.java @@ -0,0 +1,90 @@ + +package mage.deck; + +/** + * + * @author andreacosta + */ +public class CenturionCommander extends Commander { + + public CenturionCommander() { + super("Centurion Commander"); + banned.add("Ancestral Recall"); + banned.add("Ancient Tomb"); + banned.add("Back to Basic"); + banned.add("Balance"); + banned.add("Bazaar of Baghdad"); + banned.add("Black Lotus"); + banned.add("Cataclysm"); + banned.add("Channel"); + banned.add("Chaos Orb"); + banned.add("Chrome Mox"); + banned.add("Demonic Tutor"); + banned.add("Dig Through Time"); + banned.add("Emrakul, the Aeons Torn"); + banned.add("Emrakul, the Promised End"); + banned.add("Entomb"); + banned.add("Erayo, Soratami Ascendant"); + banned.add("Falling Star"); + banned.add("Fastbond"); + banned.add("Food Chain"); + banned.add("Gaea’s Cradle"); + banned.add("Gifts Ungiven"); + banned.add("Grim Monolith"); + banned.add("Grindstone"); + banned.add("Hermit Druid"); + banned.add("High Tide"); + banned.add("Humility"); + banned.add("Imperial Seal"); + banned.add("Karakas"); + banned.add("Library of Alexandria"); + banned.add("Mana Crypt"); + banned.add("Mana Drain"); + banned.add("Mana Vault"); + banned.add("Mishra’s Workshop"); + banned.add("Mind Twist"); + banned.add("Mox Diamond"); + banned.add("Mox Emerald"); + banned.add("Mox Jet"); + banned.add("Mox Pearl"); + banned.add("Mox Ruby"); + banned.add("Mox Sapphire"); + banned.add("Mystical Tutor"); + banned.add("Natural Order"); + banned.add("Necropotence"); + banned.add("Oath of Druids"); + banned.add("Protean Hulk"); + banned.add("Sensei’s Diving Top"); + banned.add("Serra Ascendant"); + banned.add("Sharazad"); + banned.add("Survival of the Fittest"); + banned.add("Sol Ring"); + banned.add("Strip Mine"); + banned.add("The Tabernacle at Pendrell Vale"); + banned.add("Time Vault"); + banned.add("Time Walk"); + banned.add("Tinker"); + banned.add("Tolarian Academy"); + banned.add("Treasure Cruise"); + banned.add("Vampiric Tutor"); + banned.add("Vanishing"); + banned.add("Winter Orb"); + banned.add("Yawgmoth’s Bargain"); + + bannedCommander.add("Baral, Chief of Compliance"); + bannedCommander.add("Derevi, Empyrial Tactician"); + bannedCommander.add("Edgar Markov"); + bannedCommander.add("Kess, Dissident Mage"); + bannedCommander.add("Rofellos, Llanowar Emissary"); + + bannedPartner.add("Rowan Kenrith"); + bannedPartner.add("Tymna the Weaver"); + bannedPartner.add(""); + bannedPartner.add(""); + + +Will Kenrith +Vial Smasher The Fierce + } + +} diff --git a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205618.java b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205618.java new file mode 100644 index 0000000000..84d97c4482 --- /dev/null +++ b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205618.java @@ -0,0 +1,90 @@ + +package mage.deck; + +/** + * + * @author andreacosta + */ +public class CenturionCommander extends Commander { + + public CenturionCommander() { + super("Centurion Commander"); + banned.add("Ancestral Recall"); + banned.add("Ancient Tomb"); + banned.add("Back to Basic"); + banned.add("Balance"); + banned.add("Bazaar of Baghdad"); + banned.add("Black Lotus"); + banned.add("Cataclysm"); + banned.add("Channel"); + banned.add("Chaos Orb"); + banned.add("Chrome Mox"); + banned.add("Demonic Tutor"); + banned.add("Dig Through Time"); + banned.add("Emrakul, the Aeons Torn"); + banned.add("Emrakul, the Promised End"); + banned.add("Entomb"); + banned.add("Erayo, Soratami Ascendant"); + banned.add("Falling Star"); + banned.add("Fastbond"); + banned.add("Food Chain"); + banned.add("Gaea’s Cradle"); + banned.add("Gifts Ungiven"); + banned.add("Grim Monolith"); + banned.add("Grindstone"); + banned.add("Hermit Druid"); + banned.add("High Tide"); + banned.add("Humility"); + banned.add("Imperial Seal"); + banned.add("Karakas"); + banned.add("Library of Alexandria"); + banned.add("Mana Crypt"); + banned.add("Mana Drain"); + banned.add("Mana Vault"); + banned.add("Mishra’s Workshop"); + banned.add("Mind Twist"); + banned.add("Mox Diamond"); + banned.add("Mox Emerald"); + banned.add("Mox Jet"); + banned.add("Mox Pearl"); + banned.add("Mox Ruby"); + banned.add("Mox Sapphire"); + banned.add("Mystical Tutor"); + banned.add("Natural Order"); + banned.add("Necropotence"); + banned.add("Oath of Druids"); + banned.add("Protean Hulk"); + banned.add("Sensei’s Diving Top"); + banned.add("Serra Ascendant"); + banned.add("Sharazad"); + banned.add("Survival of the Fittest"); + banned.add("Sol Ring"); + banned.add("Strip Mine"); + banned.add("The Tabernacle at Pendrell Vale"); + banned.add("Time Vault"); + banned.add("Time Walk"); + banned.add("Tinker"); + banned.add("Tolarian Academy"); + banned.add("Treasure Cruise"); + banned.add("Vampiric Tutor"); + banned.add("Vanishing"); + banned.add("Winter Orb"); + banned.add("Yawgmoth’s Bargain"); + + bannedCommander.add("Baral, Chief of Compliance"); + bannedCommander.add("Derevi, Empyrial Tactician"); + bannedCommander.add("Edgar Markov"); + bannedCommander.add("Kess, Dissident Mage"); + bannedCommander.add("Rofellos, Llanowar Emissary"); + + bannedPartner.add("Rowan Kenrith"); + bannedPartner.add("Tymna the Weaver"); + bannedPartner.add(""); + bannedPartner.add(""); + + +Will Kenrith +Vial Smasher The Fierce + } + +} diff --git a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205619.java b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205619.java new file mode 100644 index 0000000000..fd1f426efb --- /dev/null +++ b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205619.java @@ -0,0 +1,90 @@ + +package mage.deck; + +/** + * + * @author andreacosta + */ +public class CenturionCommander extends Commander { + + public CenturionCommander() { + super("Centurion Commander"); + banned.add("Ancestral Recall"); + banned.add("Ancient Tomb"); + banned.add("Back to Basic"); + banned.add("Balance"); + banned.add("Bazaar of Baghdad"); + banned.add("Black Lotus"); + banned.add("Cataclysm"); + banned.add("Channel"); + banned.add("Chaos Orb"); + banned.add("Chrome Mox"); + banned.add("Demonic Tutor"); + banned.add("Dig Through Time"); + banned.add("Emrakul, the Aeons Torn"); + banned.add("Emrakul, the Promised End"); + banned.add("Entomb"); + banned.add("Erayo, Soratami Ascendant"); + banned.add("Falling Star"); + banned.add("Fastbond"); + banned.add("Food Chain"); + banned.add("Gaea’s Cradle"); + banned.add("Gifts Ungiven"); + banned.add("Grim Monolith"); + banned.add("Grindstone"); + banned.add("Hermit Druid"); + banned.add("High Tide"); + banned.add("Humility"); + banned.add("Imperial Seal"); + banned.add("Karakas"); + banned.add("Library of Alexandria"); + banned.add("Mana Crypt"); + banned.add("Mana Drain"); + banned.add("Mana Vault"); + banned.add("Mishra’s Workshop"); + banned.add("Mind Twist"); + banned.add("Mox Diamond"); + banned.add("Mox Emerald"); + banned.add("Mox Jet"); + banned.add("Mox Pearl"); + banned.add("Mox Ruby"); + banned.add("Mox Sapphire"); + banned.add("Mystical Tutor"); + banned.add("Natural Order"); + banned.add("Necropotence"); + banned.add("Oath of Druids"); + banned.add("Protean Hulk"); + banned.add("Sensei’s Diving Top"); + banned.add("Serra Ascendant"); + banned.add("Sharazad"); + banned.add("Survival of the Fittest"); + banned.add("Sol Ring"); + banned.add("Strip Mine"); + banned.add("The Tabernacle at Pendrell Vale"); + banned.add("Time Vault"); + banned.add("Time Walk"); + banned.add("Tinker"); + banned.add("Tolarian Academy"); + banned.add("Treasure Cruise"); + banned.add("Vampiric Tutor"); + banned.add("Vanishing"); + banned.add("Winter Orb"); + banned.add("Yawgmoth’s Bargain"); + + bannedCommander.add("Baral, Chief of Compliance"); + bannedCommander.add("Derevi, Empyrial Tactician"); + bannedCommander.add("Edgar Markov"); + bannedCommander.add("Kess, Dissident Mage"); + bannedCommander.add("Rofellos, Llanowar Emissary"); + + bannedPartner.add("Rowan Kenrith"); + bannedPartner.add("Tymna the Weaver"); + bannedPartner.add(""); + bannedPartner.add(""); + + + +Vial Smasher The Fierce + } + +} diff --git a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205622.java b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205622.java new file mode 100644 index 0000000000..0f17649219 --- /dev/null +++ b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205622.java @@ -0,0 +1,90 @@ + +package mage.deck; + +/** + * + * @author andreacosta + */ +public class CenturionCommander extends Commander { + + public CenturionCommander() { + super("Centurion Commander"); + banned.add("Ancestral Recall"); + banned.add("Ancient Tomb"); + banned.add("Back to Basic"); + banned.add("Balance"); + banned.add("Bazaar of Baghdad"); + banned.add("Black Lotus"); + banned.add("Cataclysm"); + banned.add("Channel"); + banned.add("Chaos Orb"); + banned.add("Chrome Mox"); + banned.add("Demonic Tutor"); + banned.add("Dig Through Time"); + banned.add("Emrakul, the Aeons Torn"); + banned.add("Emrakul, the Promised End"); + banned.add("Entomb"); + banned.add("Erayo, Soratami Ascendant"); + banned.add("Falling Star"); + banned.add("Fastbond"); + banned.add("Food Chain"); + banned.add("Gaea’s Cradle"); + banned.add("Gifts Ungiven"); + banned.add("Grim Monolith"); + banned.add("Grindstone"); + banned.add("Hermit Druid"); + banned.add("High Tide"); + banned.add("Humility"); + banned.add("Imperial Seal"); + banned.add("Karakas"); + banned.add("Library of Alexandria"); + banned.add("Mana Crypt"); + banned.add("Mana Drain"); + banned.add("Mana Vault"); + banned.add("Mishra’s Workshop"); + banned.add("Mind Twist"); + banned.add("Mox Diamond"); + banned.add("Mox Emerald"); + banned.add("Mox Jet"); + banned.add("Mox Pearl"); + banned.add("Mox Ruby"); + banned.add("Mox Sapphire"); + banned.add("Mystical Tutor"); + banned.add("Natural Order"); + banned.add("Necropotence"); + banned.add("Oath of Druids"); + banned.add("Protean Hulk"); + banned.add("Sensei’s Diving Top"); + banned.add("Serra Ascendant"); + banned.add("Sharazad"); + banned.add("Survival of the Fittest"); + banned.add("Sol Ring"); + banned.add("Strip Mine"); + banned.add("The Tabernacle at Pendrell Vale"); + banned.add("Time Vault"); + banned.add("Time Walk"); + banned.add("Tinker"); + banned.add("Tolarian Academy"); + banned.add("Treasure Cruise"); + banned.add("Vampiric Tutor"); + banned.add("Vanishing"); + banned.add("Winter Orb"); + banned.add("Yawgmoth’s Bargain"); + + bannedCommander.add("Baral, Chief of Compliance"); + bannedCommander.add("Derevi, Empyrial Tactician"); + bannedCommander.add("Edgar Markov"); + bannedCommander.add("Kess, Dissident Mage"); + bannedCommander.add("Rofellos, Llanowar Emissary"); + + bannedPartner.add("Rowan Kenrith"); + bannedPartner.add("Tymna the Weaver"); + bannedPartner.add("Will Kenrith"); + bannedPartner.add(""); + + + +Vial Smasher The Fierce + } + +} diff --git a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205627.java b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205627.java new file mode 100644 index 0000000000..8fea4fc748 --- /dev/null +++ b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205627.java @@ -0,0 +1,86 @@ + +package mage.deck; + +/** + * + * @author andreacosta + */ +public class CenturionCommander extends Commander { + + public CenturionCommander() { + super("Centurion Commander"); + banned.add("Ancestral Recall"); + banned.add("Ancient Tomb"); + banned.add("Back to Basic"); + banned.add("Balance"); + banned.add("Bazaar of Baghdad"); + banned.add("Black Lotus"); + banned.add("Cataclysm"); + banned.add("Channel"); + banned.add("Chaos Orb"); + banned.add("Chrome Mox"); + banned.add("Demonic Tutor"); + banned.add("Dig Through Time"); + banned.add("Emrakul, the Aeons Torn"); + banned.add("Emrakul, the Promised End"); + banned.add("Entomb"); + banned.add("Erayo, Soratami Ascendant"); + banned.add("Falling Star"); + banned.add("Fastbond"); + banned.add("Food Chain"); + banned.add("Gaea’s Cradle"); + banned.add("Gifts Ungiven"); + banned.add("Grim Monolith"); + banned.add("Grindstone"); + banned.add("Hermit Druid"); + banned.add("High Tide"); + banned.add("Humility"); + banned.add("Imperial Seal"); + banned.add("Karakas"); + banned.add("Library of Alexandria"); + banned.add("Mana Crypt"); + banned.add("Mana Drain"); + banned.add("Mana Vault"); + banned.add("Mishra’s Workshop"); + banned.add("Mind Twist"); + banned.add("Mox Diamond"); + banned.add("Mox Emerald"); + banned.add("Mox Jet"); + banned.add("Mox Pearl"); + banned.add("Mox Ruby"); + banned.add("Mox Sapphire"); + banned.add("Mystical Tutor"); + banned.add("Natural Order"); + banned.add("Necropotence"); + banned.add("Oath of Druids"); + banned.add("Protean Hulk"); + banned.add("Sensei’s Diving Top"); + banned.add("Serra Ascendant"); + banned.add("Sharazad"); + banned.add("Survival of the Fittest"); + banned.add("Sol Ring"); + banned.add("Strip Mine"); + banned.add("The Tabernacle at Pendrell Vale"); + banned.add("Time Vault"); + banned.add("Time Walk"); + banned.add("Tinker"); + banned.add("Tolarian Academy"); + banned.add("Treasure Cruise"); + banned.add("Vampiric Tutor"); + banned.add("Vanishing"); + banned.add("Winter Orb"); + banned.add("Yawgmoth’s Bargain"); + + bannedCommander.add("Baral, Chief of Compliance"); + bannedCommander.add("Derevi, Empyrial Tactician"); + bannedCommander.add("Edgar Markov"); + bannedCommander.add("Kess, Dissident Mage"); + bannedCommander.add("Rofellos, Llanowar Emissary"); + + bannedPartner.add("Rowan Kenrith"); + bannedPartner.add("Tymna the Weaver"); + bannedPartner.add("Will Kenrith"); + bannedPartner.add(""); + } + +} diff --git a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205628.java b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205628.java new file mode 100644 index 0000000000..e66990b5af --- /dev/null +++ b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205628.java @@ -0,0 +1,86 @@ + +package mage.deck; + +/** + * + * @author andreacosta + */ +public class CenturionCommander extends Commander { + + public CenturionCommander() { + super("Centurion Commander"); + banned.add("Ancestral Recall"); + banned.add("Ancient Tomb"); + banned.add("Back to Basic"); + banned.add("Balance"); + banned.add("Bazaar of Baghdad"); + banned.add("Black Lotus"); + banned.add("Cataclysm"); + banned.add("Channel"); + banned.add("Chaos Orb"); + banned.add("Chrome Mox"); + banned.add("Demonic Tutor"); + banned.add("Dig Through Time"); + banned.add("Emrakul, the Aeons Torn"); + banned.add("Emrakul, the Promised End"); + banned.add("Entomb"); + banned.add("Erayo, Soratami Ascendant"); + banned.add("Falling Star"); + banned.add("Fastbond"); + banned.add("Food Chain"); + banned.add("Gaea’s Cradle"); + banned.add("Gifts Ungiven"); + banned.add("Grim Monolith"); + banned.add("Grindstone"); + banned.add("Hermit Druid"); + banned.add("High Tide"); + banned.add("Humility"); + banned.add("Imperial Seal"); + banned.add("Karakas"); + banned.add("Library of Alexandria"); + banned.add("Mana Crypt"); + banned.add("Mana Drain"); + banned.add("Mana Vault"); + banned.add("Mishra’s Workshop"); + banned.add("Mind Twist"); + banned.add("Mox Diamond"); + banned.add("Mox Emerald"); + banned.add("Mox Jet"); + banned.add("Mox Pearl"); + banned.add("Mox Ruby"); + banned.add("Mox Sapphire"); + banned.add("Mystical Tutor"); + banned.add("Natural Order"); + banned.add("Necropotence"); + banned.add("Oath of Druids"); + banned.add("Protean Hulk"); + banned.add("Sensei’s Diving Top"); + banned.add("Serra Ascendant"); + banned.add("Sharazad"); + banned.add("Survival of the Fittest"); + banned.add("Sol Ring"); + banned.add("Strip Mine"); + banned.add("The Tabernacle at Pendrell Vale"); + banned.add("Time Vault"); + banned.add("Time Walk"); + banned.add("Tinker"); + banned.add("Tolarian Academy"); + banned.add("Treasure Cruise"); + banned.add("Vampiric Tutor"); + banned.add("Vanishing"); + banned.add("Winter Orb"); + banned.add("Yawgmoth’s Bargain"); + + bannedCommander.add("Baral, Chief of Compliance"); + bannedCommander.add("Derevi, Empyrial Tactician"); + bannedCommander.add("Edgar Markov"); + bannedCommander.add("Kess, Dissident Mage"); + bannedCommander.add("Rofellos, Llanowar Emissary"); + + bannedPartner.add("Rowan Kenrith"); + bannedPartner.add("Tymna the Weaver"); + bannedPartner.add("Will Kenrith"); + bannedPartner.add("Vial Smasher The Fierce"); + } + +} diff --git a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander.java b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander.java index d98617ad46..e66990b5af 100644 --- a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander.java +++ b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander.java @@ -76,6 +76,11 @@ public class CenturionCommander extends Commander { bannedCommander.add("Edgar Markov"); bannedCommander.add("Kess, Dissident Mage"); bannedCommander.add("Rofellos, Llanowar Emissary"); + + bannedPartner.add("Rowan Kenrith"); + bannedPartner.add("Tymna the Weaver"); + bannedPartner.add("Will Kenrith"); + bannedPartner.add("Vial Smasher The Fierce"); } } From 4fa860b0bf69e90f56ecb8aca29e02ad9c630070 Mon Sep 17 00:00:00 2001 From: acosta Date: Wed, 16 Oct 2019 21:23:28 +0200 Subject: [PATCH 365/373] Add banned partners --- .../CenturionCommander_20191016205159.java | 81 ----------------- .../CenturionCommander_20191016205524.java | 83 ----------------- .../CenturionCommander_20191016205526.java | 83 ----------------- .../CenturionCommander_20191016205550.java | 87 ------------------ .../CenturionCommander_20191016205555.java | 87 ------------------ .../CenturionCommander_20191016205556.java | 87 ------------------ .../CenturionCommander_20191016205600.java | 87 ------------------ .../CenturionCommander_20191016205601.java | 87 ------------------ .../CenturionCommander_20191016205603.java | 90 ------------------- .../CenturionCommander_20191016205606.java | 90 ------------------- .../CenturionCommander_20191016205607.java | 90 ------------------- .../CenturionCommander_20191016205608.java | 90 ------------------- .../CenturionCommander_20191016205611.java | 90 ------------------- .../CenturionCommander_20191016205616.java | 90 ------------------- .../CenturionCommander_20191016205618.java | 90 ------------------- .../CenturionCommander_20191016205619.java | 90 ------------------- .../CenturionCommander_20191016205622.java | 90 ------------------- .../CenturionCommander_20191016205627.java | 86 ------------------ .../CenturionCommander_20191016205628.java | 86 ------------------ 19 files changed, 1664 deletions(-) delete mode 100644 .history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205159.java delete mode 100644 .history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205524.java delete mode 100644 .history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205526.java delete mode 100644 .history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205550.java delete mode 100644 .history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205555.java delete mode 100644 .history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205556.java delete mode 100644 .history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205600.java delete mode 100644 .history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205601.java delete mode 100644 .history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205603.java delete mode 100644 .history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205606.java delete mode 100644 .history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205607.java delete mode 100644 .history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205608.java delete mode 100644 .history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205611.java delete mode 100644 .history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205616.java delete mode 100644 .history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205618.java delete mode 100644 .history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205619.java delete mode 100644 .history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205622.java delete mode 100644 .history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205627.java delete mode 100644 .history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205628.java diff --git a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205159.java b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205159.java deleted file mode 100644 index d98617ad46..0000000000 --- a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205159.java +++ /dev/null @@ -1,81 +0,0 @@ - -package mage.deck; - -/** - * - * @author andreacosta - */ -public class CenturionCommander extends Commander { - - public CenturionCommander() { - super("Centurion Commander"); - banned.add("Ancestral Recall"); - banned.add("Ancient Tomb"); - banned.add("Back to Basic"); - banned.add("Balance"); - banned.add("Bazaar of Baghdad"); - banned.add("Black Lotus"); - banned.add("Cataclysm"); - banned.add("Channel"); - banned.add("Chaos Orb"); - banned.add("Chrome Mox"); - banned.add("Demonic Tutor"); - banned.add("Dig Through Time"); - banned.add("Emrakul, the Aeons Torn"); - banned.add("Emrakul, the Promised End"); - banned.add("Entomb"); - banned.add("Erayo, Soratami Ascendant"); - banned.add("Falling Star"); - banned.add("Fastbond"); - banned.add("Food Chain"); - banned.add("Gaea’s Cradle"); - banned.add("Gifts Ungiven"); - banned.add("Grim Monolith"); - banned.add("Grindstone"); - banned.add("Hermit Druid"); - banned.add("High Tide"); - banned.add("Humility"); - banned.add("Imperial Seal"); - banned.add("Karakas"); - banned.add("Library of Alexandria"); - banned.add("Mana Crypt"); - banned.add("Mana Drain"); - banned.add("Mana Vault"); - banned.add("Mishra’s Workshop"); - banned.add("Mind Twist"); - banned.add("Mox Diamond"); - banned.add("Mox Emerald"); - banned.add("Mox Jet"); - banned.add("Mox Pearl"); - banned.add("Mox Ruby"); - banned.add("Mox Sapphire"); - banned.add("Mystical Tutor"); - banned.add("Natural Order"); - banned.add("Necropotence"); - banned.add("Oath of Druids"); - banned.add("Protean Hulk"); - banned.add("Sensei’s Diving Top"); - banned.add("Serra Ascendant"); - banned.add("Sharazad"); - banned.add("Survival of the Fittest"); - banned.add("Sol Ring"); - banned.add("Strip Mine"); - banned.add("The Tabernacle at Pendrell Vale"); - banned.add("Time Vault"); - banned.add("Time Walk"); - banned.add("Tinker"); - banned.add("Tolarian Academy"); - banned.add("Treasure Cruise"); - banned.add("Vampiric Tutor"); - banned.add("Vanishing"); - banned.add("Winter Orb"); - banned.add("Yawgmoth’s Bargain"); - - bannedCommander.add("Baral, Chief of Compliance"); - bannedCommander.add("Derevi, Empyrial Tactician"); - bannedCommander.add("Edgar Markov"); - bannedCommander.add("Kess, Dissident Mage"); - bannedCommander.add("Rofellos, Llanowar Emissary"); - } - -} diff --git a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205524.java b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205524.java deleted file mode 100644 index c4ecd5d406..0000000000 --- a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205524.java +++ /dev/null @@ -1,83 +0,0 @@ - -package mage.deck; - -/** - * - * @author andreacosta - */ -public class CenturionCommander extends Commander { - - public CenturionCommander() { - super("Centurion Commander"); - banned.add("Ancestral Recall"); - banned.add("Ancient Tomb"); - banned.add("Back to Basic"); - banned.add("Balance"); - banned.add("Bazaar of Baghdad"); - banned.add("Black Lotus"); - banned.add("Cataclysm"); - banned.add("Channel"); - banned.add("Chaos Orb"); - banned.add("Chrome Mox"); - banned.add("Demonic Tutor"); - banned.add("Dig Through Time"); - banned.add("Emrakul, the Aeons Torn"); - banned.add("Emrakul, the Promised End"); - banned.add("Entomb"); - banned.add("Erayo, Soratami Ascendant"); - banned.add("Falling Star"); - banned.add("Fastbond"); - banned.add("Food Chain"); - banned.add("Gaea’s Cradle"); - banned.add("Gifts Ungiven"); - banned.add("Grim Monolith"); - banned.add("Grindstone"); - banned.add("Hermit Druid"); - banned.add("High Tide"); - banned.add("Humility"); - banned.add("Imperial Seal"); - banned.add("Karakas"); - banned.add("Library of Alexandria"); - banned.add("Mana Crypt"); - banned.add("Mana Drain"); - banned.add("Mana Vault"); - banned.add("Mishra’s Workshop"); - banned.add("Mind Twist"); - banned.add("Mox Diamond"); - banned.add("Mox Emerald"); - banned.add("Mox Jet"); - banned.add("Mox Pearl"); - banned.add("Mox Ruby"); - banned.add("Mox Sapphire"); - banned.add("Mystical Tutor"); - banned.add("Natural Order"); - banned.add("Necropotence"); - banned.add("Oath of Druids"); - banned.add("Protean Hulk"); - banned.add("Sensei’s Diving Top"); - banned.add("Serra Ascendant"); - banned.add("Sharazad"); - banned.add("Survival of the Fittest"); - banned.add("Sol Ring"); - banned.add("Strip Mine"); - banned.add("The Tabernacle at Pendrell Vale"); - banned.add("Time Vault"); - banned.add("Time Walk"); - banned.add("Tinker"); - banned.add("Tolarian Academy"); - banned.add("Treasure Cruise"); - banned.add("Vampiric Tutor"); - banned.add("Vanishing"); - banned.add("Winter Orb"); - banned.add("Yawgmoth’s Bargain"); - - bannedCommander.add("Baral, Chief of Compliance"); - bannedCommander.add("Derevi, Empyrial Tactician"); - bannedCommander.add("Edgar Markov"); - bannedCommander.add("Kess, Dissident Mage"); - bannedCommander.add("Rofellos, Llanowar Emissary"); - - bannedPartner.add() - } - -} diff --git a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205526.java b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205526.java deleted file mode 100644 index 913a930a2d..0000000000 --- a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205526.java +++ /dev/null @@ -1,83 +0,0 @@ - -package mage.deck; - -/** - * - * @author andreacosta - */ -public class CenturionCommander extends Commander { - - public CenturionCommander() { - super("Centurion Commander"); - banned.add("Ancestral Recall"); - banned.add("Ancient Tomb"); - banned.add("Back to Basic"); - banned.add("Balance"); - banned.add("Bazaar of Baghdad"); - banned.add("Black Lotus"); - banned.add("Cataclysm"); - banned.add("Channel"); - banned.add("Chaos Orb"); - banned.add("Chrome Mox"); - banned.add("Demonic Tutor"); - banned.add("Dig Through Time"); - banned.add("Emrakul, the Aeons Torn"); - banned.add("Emrakul, the Promised End"); - banned.add("Entomb"); - banned.add("Erayo, Soratami Ascendant"); - banned.add("Falling Star"); - banned.add("Fastbond"); - banned.add("Food Chain"); - banned.add("Gaea’s Cradle"); - banned.add("Gifts Ungiven"); - banned.add("Grim Monolith"); - banned.add("Grindstone"); - banned.add("Hermit Druid"); - banned.add("High Tide"); - banned.add("Humility"); - banned.add("Imperial Seal"); - banned.add("Karakas"); - banned.add("Library of Alexandria"); - banned.add("Mana Crypt"); - banned.add("Mana Drain"); - banned.add("Mana Vault"); - banned.add("Mishra’s Workshop"); - banned.add("Mind Twist"); - banned.add("Mox Diamond"); - banned.add("Mox Emerald"); - banned.add("Mox Jet"); - banned.add("Mox Pearl"); - banned.add("Mox Ruby"); - banned.add("Mox Sapphire"); - banned.add("Mystical Tutor"); - banned.add("Natural Order"); - banned.add("Necropotence"); - banned.add("Oath of Druids"); - banned.add("Protean Hulk"); - banned.add("Sensei’s Diving Top"); - banned.add("Serra Ascendant"); - banned.add("Sharazad"); - banned.add("Survival of the Fittest"); - banned.add("Sol Ring"); - banned.add("Strip Mine"); - banned.add("The Tabernacle at Pendrell Vale"); - banned.add("Time Vault"); - banned.add("Time Walk"); - banned.add("Tinker"); - banned.add("Tolarian Academy"); - banned.add("Treasure Cruise"); - banned.add("Vampiric Tutor"); - banned.add("Vanishing"); - banned.add("Winter Orb"); - banned.add("Yawgmoth’s Bargain"); - - bannedCommander.add("Baral, Chief of Compliance"); - bannedCommander.add("Derevi, Empyrial Tactician"); - bannedCommander.add("Edgar Markov"); - bannedCommander.add("Kess, Dissident Mage"); - bannedCommander.add("Rofellos, Llanowar Emissary"); - - bannedPartner.add(); - } - -} diff --git a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205550.java b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205550.java deleted file mode 100644 index d1da8c98bd..0000000000 --- a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205550.java +++ /dev/null @@ -1,87 +0,0 @@ - -package mage.deck; - -/** - * - * @author andreacosta - */ -public class CenturionCommander extends Commander { - - public CenturionCommander() { - super("Centurion Commander"); - banned.add("Ancestral Recall"); - banned.add("Ancient Tomb"); - banned.add("Back to Basic"); - banned.add("Balance"); - banned.add("Bazaar of Baghdad"); - banned.add("Black Lotus"); - banned.add("Cataclysm"); - banned.add("Channel"); - banned.add("Chaos Orb"); - banned.add("Chrome Mox"); - banned.add("Demonic Tutor"); - banned.add("Dig Through Time"); - banned.add("Emrakul, the Aeons Torn"); - banned.add("Emrakul, the Promised End"); - banned.add("Entomb"); - banned.add("Erayo, Soratami Ascendant"); - banned.add("Falling Star"); - banned.add("Fastbond"); - banned.add("Food Chain"); - banned.add("Gaea’s Cradle"); - banned.add("Gifts Ungiven"); - banned.add("Grim Monolith"); - banned.add("Grindstone"); - banned.add("Hermit Druid"); - banned.add("High Tide"); - banned.add("Humility"); - banned.add("Imperial Seal"); - banned.add("Karakas"); - banned.add("Library of Alexandria"); - banned.add("Mana Crypt"); - banned.add("Mana Drain"); - banned.add("Mana Vault"); - banned.add("Mishra’s Workshop"); - banned.add("Mind Twist"); - banned.add("Mox Diamond"); - banned.add("Mox Emerald"); - banned.add("Mox Jet"); - banned.add("Mox Pearl"); - banned.add("Mox Ruby"); - banned.add("Mox Sapphire"); - banned.add("Mystical Tutor"); - banned.add("Natural Order"); - banned.add("Necropotence"); - banned.add("Oath of Druids"); - banned.add("Protean Hulk"); - banned.add("Sensei’s Diving Top"); - banned.add("Serra Ascendant"); - banned.add("Sharazad"); - banned.add("Survival of the Fittest"); - banned.add("Sol Ring"); - banned.add("Strip Mine"); - banned.add("The Tabernacle at Pendrell Vale"); - banned.add("Time Vault"); - banned.add("Time Walk"); - banned.add("Tinker"); - banned.add("Tolarian Academy"); - banned.add("Treasure Cruise"); - banned.add("Vampiric Tutor"); - banned.add("Vanishing"); - banned.add("Winter Orb"); - banned.add("Yawgmoth’s Bargain"); - - bannedCommander.add("Baral, Chief of Compliance"); - bannedCommander.add("Derevi, Empyrial Tactician"); - bannedCommander.add("Edgar Markov"); - bannedCommander.add("Kess, Dissident Mage"); - bannedCommander.add("Rofellos, Llanowar Emissary"); - - bannedPartner.add(); - Rowan Kenrith -Tymna the Weaver -Will Kenrith -Vial Smasher The Fierce - } - -} diff --git a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205555.java b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205555.java deleted file mode 100644 index 25f5ce669b..0000000000 --- a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205555.java +++ /dev/null @@ -1,87 +0,0 @@ - -package mage.deck; - -/** - * - * @author andreacosta - */ -public class CenturionCommander extends Commander { - - public CenturionCommander() { - super("Centurion Commander"); - banned.add("Ancestral Recall"); - banned.add("Ancient Tomb"); - banned.add("Back to Basic"); - banned.add("Balance"); - banned.add("Bazaar of Baghdad"); - banned.add("Black Lotus"); - banned.add("Cataclysm"); - banned.add("Channel"); - banned.add("Chaos Orb"); - banned.add("Chrome Mox"); - banned.add("Demonic Tutor"); - banned.add("Dig Through Time"); - banned.add("Emrakul, the Aeons Torn"); - banned.add("Emrakul, the Promised End"); - banned.add("Entomb"); - banned.add("Erayo, Soratami Ascendant"); - banned.add("Falling Star"); - banned.add("Fastbond"); - banned.add("Food Chain"); - banned.add("Gaea’s Cradle"); - banned.add("Gifts Ungiven"); - banned.add("Grim Monolith"); - banned.add("Grindstone"); - banned.add("Hermit Druid"); - banned.add("High Tide"); - banned.add("Humility"); - banned.add("Imperial Seal"); - banned.add("Karakas"); - banned.add("Library of Alexandria"); - banned.add("Mana Crypt"); - banned.add("Mana Drain"); - banned.add("Mana Vault"); - banned.add("Mishra’s Workshop"); - banned.add("Mind Twist"); - banned.add("Mox Diamond"); - banned.add("Mox Emerald"); - banned.add("Mox Jet"); - banned.add("Mox Pearl"); - banned.add("Mox Ruby"); - banned.add("Mox Sapphire"); - banned.add("Mystical Tutor"); - banned.add("Natural Order"); - banned.add("Necropotence"); - banned.add("Oath of Druids"); - banned.add("Protean Hulk"); - banned.add("Sensei’s Diving Top"); - banned.add("Serra Ascendant"); - banned.add("Sharazad"); - banned.add("Survival of the Fittest"); - banned.add("Sol Ring"); - banned.add("Strip Mine"); - banned.add("The Tabernacle at Pendrell Vale"); - banned.add("Time Vault"); - banned.add("Time Walk"); - banned.add("Tinker"); - banned.add("Tolarian Academy"); - banned.add("Treasure Cruise"); - banned.add("Vampiric Tutor"); - banned.add("Vanishing"); - banned.add("Winter Orb"); - banned.add("Yawgmoth’s Bargain"); - - bannedCommander.add("Baral, Chief of Compliance"); - bannedCommander.add("Derevi, Empyrial Tactician"); - bannedCommander.add("Edgar Markov"); - bannedCommander.add("Kess, Dissident Mage"); - bannedCommander.add("Rofellos, Llanowar Emissary"); - - bannedPartner.add(); - "Rowan Kenrith -Tymna the Weaver -Will Kenrith -Vial Smasher The Fierce - } - -} diff --git a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205556.java b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205556.java deleted file mode 100644 index cd63c763d8..0000000000 --- a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205556.java +++ /dev/null @@ -1,87 +0,0 @@ - -package mage.deck; - -/** - * - * @author andreacosta - */ -public class CenturionCommander extends Commander { - - public CenturionCommander() { - super("Centurion Commander"); - banned.add("Ancestral Recall"); - banned.add("Ancient Tomb"); - banned.add("Back to Basic"); - banned.add("Balance"); - banned.add("Bazaar of Baghdad"); - banned.add("Black Lotus"); - banned.add("Cataclysm"); - banned.add("Channel"); - banned.add("Chaos Orb"); - banned.add("Chrome Mox"); - banned.add("Demonic Tutor"); - banned.add("Dig Through Time"); - banned.add("Emrakul, the Aeons Torn"); - banned.add("Emrakul, the Promised End"); - banned.add("Entomb"); - banned.add("Erayo, Soratami Ascendant"); - banned.add("Falling Star"); - banned.add("Fastbond"); - banned.add("Food Chain"); - banned.add("Gaea’s Cradle"); - banned.add("Gifts Ungiven"); - banned.add("Grim Monolith"); - banned.add("Grindstone"); - banned.add("Hermit Druid"); - banned.add("High Tide"); - banned.add("Humility"); - banned.add("Imperial Seal"); - banned.add("Karakas"); - banned.add("Library of Alexandria"); - banned.add("Mana Crypt"); - banned.add("Mana Drain"); - banned.add("Mana Vault"); - banned.add("Mishra’s Workshop"); - banned.add("Mind Twist"); - banned.add("Mox Diamond"); - banned.add("Mox Emerald"); - banned.add("Mox Jet"); - banned.add("Mox Pearl"); - banned.add("Mox Ruby"); - banned.add("Mox Sapphire"); - banned.add("Mystical Tutor"); - banned.add("Natural Order"); - banned.add("Necropotence"); - banned.add("Oath of Druids"); - banned.add("Protean Hulk"); - banned.add("Sensei’s Diving Top"); - banned.add("Serra Ascendant"); - banned.add("Sharazad"); - banned.add("Survival of the Fittest"); - banned.add("Sol Ring"); - banned.add("Strip Mine"); - banned.add("The Tabernacle at Pendrell Vale"); - banned.add("Time Vault"); - banned.add("Time Walk"); - banned.add("Tinker"); - banned.add("Tolarian Academy"); - banned.add("Treasure Cruise"); - banned.add("Vampiric Tutor"); - banned.add("Vanishing"); - banned.add("Winter Orb"); - banned.add("Yawgmoth’s Bargain"); - - bannedCommander.add("Baral, Chief of Compliance"); - bannedCommander.add("Derevi, Empyrial Tactician"); - bannedCommander.add("Edgar Markov"); - bannedCommander.add("Kess, Dissident Mage"); - bannedCommander.add("Rofellos, Llanowar Emissary"); - - bannedPartner.add(); - "Rowan Kenrith" -Tymna the Weaver -Will Kenrith -Vial Smasher The Fierce - } - -} diff --git a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205600.java b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205600.java deleted file mode 100644 index 833a168d78..0000000000 --- a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205600.java +++ /dev/null @@ -1,87 +0,0 @@ - -package mage.deck; - -/** - * - * @author andreacosta - */ -public class CenturionCommander extends Commander { - - public CenturionCommander() { - super("Centurion Commander"); - banned.add("Ancestral Recall"); - banned.add("Ancient Tomb"); - banned.add("Back to Basic"); - banned.add("Balance"); - banned.add("Bazaar of Baghdad"); - banned.add("Black Lotus"); - banned.add("Cataclysm"); - banned.add("Channel"); - banned.add("Chaos Orb"); - banned.add("Chrome Mox"); - banned.add("Demonic Tutor"); - banned.add("Dig Through Time"); - banned.add("Emrakul, the Aeons Torn"); - banned.add("Emrakul, the Promised End"); - banned.add("Entomb"); - banned.add("Erayo, Soratami Ascendant"); - banned.add("Falling Star"); - banned.add("Fastbond"); - banned.add("Food Chain"); - banned.add("Gaea’s Cradle"); - banned.add("Gifts Ungiven"); - banned.add("Grim Monolith"); - banned.add("Grindstone"); - banned.add("Hermit Druid"); - banned.add("High Tide"); - banned.add("Humility"); - banned.add("Imperial Seal"); - banned.add("Karakas"); - banned.add("Library of Alexandria"); - banned.add("Mana Crypt"); - banned.add("Mana Drain"); - banned.add("Mana Vault"); - banned.add("Mishra’s Workshop"); - banned.add("Mind Twist"); - banned.add("Mox Diamond"); - banned.add("Mox Emerald"); - banned.add("Mox Jet"); - banned.add("Mox Pearl"); - banned.add("Mox Ruby"); - banned.add("Mox Sapphire"); - banned.add("Mystical Tutor"); - banned.add("Natural Order"); - banned.add("Necropotence"); - banned.add("Oath of Druids"); - banned.add("Protean Hulk"); - banned.add("Sensei’s Diving Top"); - banned.add("Serra Ascendant"); - banned.add("Sharazad"); - banned.add("Survival of the Fittest"); - banned.add("Sol Ring"); - banned.add("Strip Mine"); - banned.add("The Tabernacle at Pendrell Vale"); - banned.add("Time Vault"); - banned.add("Time Walk"); - banned.add("Tinker"); - banned.add("Tolarian Academy"); - banned.add("Treasure Cruise"); - banned.add("Vampiric Tutor"); - banned.add("Vanishing"); - banned.add("Winter Orb"); - banned.add("Yawgmoth’s Bargain"); - - bannedCommander.add("Baral, Chief of Compliance"); - bannedCommander.add("Derevi, Empyrial Tactician"); - bannedCommander.add("Edgar Markov"); - bannedCommander.add("Kess, Dissident Mage"); - bannedCommander.add("Rofellos, Llanowar Emissary"); - - bannedPartner.add(); - -Tymna the Weaver -Will Kenrith -Vial Smasher The Fierce - } - -} diff --git a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205601.java b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205601.java deleted file mode 100644 index a70dec1b50..0000000000 --- a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205601.java +++ /dev/null @@ -1,87 +0,0 @@ - -package mage.deck; - -/** - * - * @author andreacosta - */ -public class CenturionCommander extends Commander { - - public CenturionCommander() { - super("Centurion Commander"); - banned.add("Ancestral Recall"); - banned.add("Ancient Tomb"); - banned.add("Back to Basic"); - banned.add("Balance"); - banned.add("Bazaar of Baghdad"); - banned.add("Black Lotus"); - banned.add("Cataclysm"); - banned.add("Channel"); - banned.add("Chaos Orb"); - banned.add("Chrome Mox"); - banned.add("Demonic Tutor"); - banned.add("Dig Through Time"); - banned.add("Emrakul, the Aeons Torn"); - banned.add("Emrakul, the Promised End"); - banned.add("Entomb"); - banned.add("Erayo, Soratami Ascendant"); - banned.add("Falling Star"); - banned.add("Fastbond"); - banned.add("Food Chain"); - banned.add("Gaea’s Cradle"); - banned.add("Gifts Ungiven"); - banned.add("Grim Monolith"); - banned.add("Grindstone"); - banned.add("Hermit Druid"); - banned.add("High Tide"); - banned.add("Humility"); - banned.add("Imperial Seal"); - banned.add("Karakas"); - banned.add("Library of Alexandria"); - banned.add("Mana Crypt"); - banned.add("Mana Drain"); - banned.add("Mana Vault"); - banned.add("Mishra’s Workshop"); - banned.add("Mind Twist"); - banned.add("Mox Diamond"); - banned.add("Mox Emerald"); - banned.add("Mox Jet"); - banned.add("Mox Pearl"); - banned.add("Mox Ruby"); - banned.add("Mox Sapphire"); - banned.add("Mystical Tutor"); - banned.add("Natural Order"); - banned.add("Necropotence"); - banned.add("Oath of Druids"); - banned.add("Protean Hulk"); - banned.add("Sensei’s Diving Top"); - banned.add("Serra Ascendant"); - banned.add("Sharazad"); - banned.add("Survival of the Fittest"); - banned.add("Sol Ring"); - banned.add("Strip Mine"); - banned.add("The Tabernacle at Pendrell Vale"); - banned.add("Time Vault"); - banned.add("Time Walk"); - banned.add("Tinker"); - banned.add("Tolarian Academy"); - banned.add("Treasure Cruise"); - banned.add("Vampiric Tutor"); - banned.add("Vanishing"); - banned.add("Winter Orb"); - banned.add("Yawgmoth’s Bargain"); - - bannedCommander.add("Baral, Chief of Compliance"); - bannedCommander.add("Derevi, Empyrial Tactician"); - bannedCommander.add("Edgar Markov"); - bannedCommander.add("Kess, Dissident Mage"); - bannedCommander.add("Rofellos, Llanowar Emissary"); - - bannedPartner.add("Rowan Kenrith"); - -Tymna the Weaver -Will Kenrith -Vial Smasher The Fierce - } - -} diff --git a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205603.java b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205603.java deleted file mode 100644 index 09928b5d8a..0000000000 --- a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205603.java +++ /dev/null @@ -1,90 +0,0 @@ - -package mage.deck; - -/** - * - * @author andreacosta - */ -public class CenturionCommander extends Commander { - - public CenturionCommander() { - super("Centurion Commander"); - banned.add("Ancestral Recall"); - banned.add("Ancient Tomb"); - banned.add("Back to Basic"); - banned.add("Balance"); - banned.add("Bazaar of Baghdad"); - banned.add("Black Lotus"); - banned.add("Cataclysm"); - banned.add("Channel"); - banned.add("Chaos Orb"); - banned.add("Chrome Mox"); - banned.add("Demonic Tutor"); - banned.add("Dig Through Time"); - banned.add("Emrakul, the Aeons Torn"); - banned.add("Emrakul, the Promised End"); - banned.add("Entomb"); - banned.add("Erayo, Soratami Ascendant"); - banned.add("Falling Star"); - banned.add("Fastbond"); - banned.add("Food Chain"); - banned.add("Gaea’s Cradle"); - banned.add("Gifts Ungiven"); - banned.add("Grim Monolith"); - banned.add("Grindstone"); - banned.add("Hermit Druid"); - banned.add("High Tide"); - banned.add("Humility"); - banned.add("Imperial Seal"); - banned.add("Karakas"); - banned.add("Library of Alexandria"); - banned.add("Mana Crypt"); - banned.add("Mana Drain"); - banned.add("Mana Vault"); - banned.add("Mishra’s Workshop"); - banned.add("Mind Twist"); - banned.add("Mox Diamond"); - banned.add("Mox Emerald"); - banned.add("Mox Jet"); - banned.add("Mox Pearl"); - banned.add("Mox Ruby"); - banned.add("Mox Sapphire"); - banned.add("Mystical Tutor"); - banned.add("Natural Order"); - banned.add("Necropotence"); - banned.add("Oath of Druids"); - banned.add("Protean Hulk"); - banned.add("Sensei’s Diving Top"); - banned.add("Serra Ascendant"); - banned.add("Sharazad"); - banned.add("Survival of the Fittest"); - banned.add("Sol Ring"); - banned.add("Strip Mine"); - banned.add("The Tabernacle at Pendrell Vale"); - banned.add("Time Vault"); - banned.add("Time Walk"); - banned.add("Tinker"); - banned.add("Tolarian Academy"); - banned.add("Treasure Cruise"); - banned.add("Vampiric Tutor"); - banned.add("Vanishing"); - banned.add("Winter Orb"); - banned.add("Yawgmoth’s Bargain"); - - bannedCommander.add("Baral, Chief of Compliance"); - bannedCommander.add("Derevi, Empyrial Tactician"); - bannedCommander.add("Edgar Markov"); - bannedCommander.add("Kess, Dissident Mage"); - bannedCommander.add("Rofellos, Llanowar Emissary"); - - bannedPartner.add("Rowan Kenrith"); - bannedPartner.add("Rowan Kenrith"); - bannedPartner.add("Rowan Kenrith"); - bannedPartner.add("Rowan Kenrith"); - -Tymna the Weaver -Will Kenrith -Vial Smasher The Fierce - } - -} diff --git a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205606.java b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205606.java deleted file mode 100644 index d7f0615159..0000000000 --- a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205606.java +++ /dev/null @@ -1,90 +0,0 @@ - -package mage.deck; - -/** - * - * @author andreacosta - */ -public class CenturionCommander extends Commander { - - public CenturionCommander() { - super("Centurion Commander"); - banned.add("Ancestral Recall"); - banned.add("Ancient Tomb"); - banned.add("Back to Basic"); - banned.add("Balance"); - banned.add("Bazaar of Baghdad"); - banned.add("Black Lotus"); - banned.add("Cataclysm"); - banned.add("Channel"); - banned.add("Chaos Orb"); - banned.add("Chrome Mox"); - banned.add("Demonic Tutor"); - banned.add("Dig Through Time"); - banned.add("Emrakul, the Aeons Torn"); - banned.add("Emrakul, the Promised End"); - banned.add("Entomb"); - banned.add("Erayo, Soratami Ascendant"); - banned.add("Falling Star"); - banned.add("Fastbond"); - banned.add("Food Chain"); - banned.add("Gaea’s Cradle"); - banned.add("Gifts Ungiven"); - banned.add("Grim Monolith"); - banned.add("Grindstone"); - banned.add("Hermit Druid"); - banned.add("High Tide"); - banned.add("Humility"); - banned.add("Imperial Seal"); - banned.add("Karakas"); - banned.add("Library of Alexandria"); - banned.add("Mana Crypt"); - banned.add("Mana Drain"); - banned.add("Mana Vault"); - banned.add("Mishra’s Workshop"); - banned.add("Mind Twist"); - banned.add("Mox Diamond"); - banned.add("Mox Emerald"); - banned.add("Mox Jet"); - banned.add("Mox Pearl"); - banned.add("Mox Ruby"); - banned.add("Mox Sapphire"); - banned.add("Mystical Tutor"); - banned.add("Natural Order"); - banned.add("Necropotence"); - banned.add("Oath of Druids"); - banned.add("Protean Hulk"); - banned.add("Sensei’s Diving Top"); - banned.add("Serra Ascendant"); - banned.add("Sharazad"); - banned.add("Survival of the Fittest"); - banned.add("Sol Ring"); - banned.add("Strip Mine"); - banned.add("The Tabernacle at Pendrell Vale"); - banned.add("Time Vault"); - banned.add("Time Walk"); - banned.add("Tinker"); - banned.add("Tolarian Academy"); - banned.add("Treasure Cruise"); - banned.add("Vampiric Tutor"); - banned.add("Vanishing"); - banned.add("Winter Orb"); - banned.add("Yawgmoth’s Bargain"); - - bannedCommander.add("Baral, Chief of Compliance"); - bannedCommander.add("Derevi, Empyrial Tactician"); - bannedCommander.add("Edgar Markov"); - bannedCommander.add("Kess, Dissident Mage"); - bannedCommander.add("Rofellos, Llanowar Emissary"); - - bannedPartner.add("Rowan Kenrith"); - bannedPartner.add("Rowan Kenrith"); - bannedPartner.add("Rowan Kenrith"); - bannedPartner.add(""); - -Tymna the Weaver -Will Kenrith -Vial Smasher The Fierce - } - -} diff --git a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205607.java b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205607.java deleted file mode 100644 index 96c3a7806f..0000000000 --- a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205607.java +++ /dev/null @@ -1,90 +0,0 @@ - -package mage.deck; - -/** - * - * @author andreacosta - */ -public class CenturionCommander extends Commander { - - public CenturionCommander() { - super("Centurion Commander"); - banned.add("Ancestral Recall"); - banned.add("Ancient Tomb"); - banned.add("Back to Basic"); - banned.add("Balance"); - banned.add("Bazaar of Baghdad"); - banned.add("Black Lotus"); - banned.add("Cataclysm"); - banned.add("Channel"); - banned.add("Chaos Orb"); - banned.add("Chrome Mox"); - banned.add("Demonic Tutor"); - banned.add("Dig Through Time"); - banned.add("Emrakul, the Aeons Torn"); - banned.add("Emrakul, the Promised End"); - banned.add("Entomb"); - banned.add("Erayo, Soratami Ascendant"); - banned.add("Falling Star"); - banned.add("Fastbond"); - banned.add("Food Chain"); - banned.add("Gaea’s Cradle"); - banned.add("Gifts Ungiven"); - banned.add("Grim Monolith"); - banned.add("Grindstone"); - banned.add("Hermit Druid"); - banned.add("High Tide"); - banned.add("Humility"); - banned.add("Imperial Seal"); - banned.add("Karakas"); - banned.add("Library of Alexandria"); - banned.add("Mana Crypt"); - banned.add("Mana Drain"); - banned.add("Mana Vault"); - banned.add("Mishra’s Workshop"); - banned.add("Mind Twist"); - banned.add("Mox Diamond"); - banned.add("Mox Emerald"); - banned.add("Mox Jet"); - banned.add("Mox Pearl"); - banned.add("Mox Ruby"); - banned.add("Mox Sapphire"); - banned.add("Mystical Tutor"); - banned.add("Natural Order"); - banned.add("Necropotence"); - banned.add("Oath of Druids"); - banned.add("Protean Hulk"); - banned.add("Sensei’s Diving Top"); - banned.add("Serra Ascendant"); - banned.add("Sharazad"); - banned.add("Survival of the Fittest"); - banned.add("Sol Ring"); - banned.add("Strip Mine"); - banned.add("The Tabernacle at Pendrell Vale"); - banned.add("Time Vault"); - banned.add("Time Walk"); - banned.add("Tinker"); - banned.add("Tolarian Academy"); - banned.add("Treasure Cruise"); - banned.add("Vampiric Tutor"); - banned.add("Vanishing"); - banned.add("Winter Orb"); - banned.add("Yawgmoth’s Bargain"); - - bannedCommander.add("Baral, Chief of Compliance"); - bannedCommander.add("Derevi, Empyrial Tactician"); - bannedCommander.add("Edgar Markov"); - bannedCommander.add("Kess, Dissident Mage"); - bannedCommander.add("Rofellos, Llanowar Emissary"); - - bannedPartner.add("Rowan Kenrith"); - bannedPartner.add("Rowan Kenrith"); - bannedPartner.add(""); - bannedPartner.add(""); - -Tymna the Weaver -Will Kenrith -Vial Smasher The Fierce - } - -} diff --git a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205608.java b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205608.java deleted file mode 100644 index 75b6ca9e22..0000000000 --- a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205608.java +++ /dev/null @@ -1,90 +0,0 @@ - -package mage.deck; - -/** - * - * @author andreacosta - */ -public class CenturionCommander extends Commander { - - public CenturionCommander() { - super("Centurion Commander"); - banned.add("Ancestral Recall"); - banned.add("Ancient Tomb"); - banned.add("Back to Basic"); - banned.add("Balance"); - banned.add("Bazaar of Baghdad"); - banned.add("Black Lotus"); - banned.add("Cataclysm"); - banned.add("Channel"); - banned.add("Chaos Orb"); - banned.add("Chrome Mox"); - banned.add("Demonic Tutor"); - banned.add("Dig Through Time"); - banned.add("Emrakul, the Aeons Torn"); - banned.add("Emrakul, the Promised End"); - banned.add("Entomb"); - banned.add("Erayo, Soratami Ascendant"); - banned.add("Falling Star"); - banned.add("Fastbond"); - banned.add("Food Chain"); - banned.add("Gaea’s Cradle"); - banned.add("Gifts Ungiven"); - banned.add("Grim Monolith"); - banned.add("Grindstone"); - banned.add("Hermit Druid"); - banned.add("High Tide"); - banned.add("Humility"); - banned.add("Imperial Seal"); - banned.add("Karakas"); - banned.add("Library of Alexandria"); - banned.add("Mana Crypt"); - banned.add("Mana Drain"); - banned.add("Mana Vault"); - banned.add("Mishra’s Workshop"); - banned.add("Mind Twist"); - banned.add("Mox Diamond"); - banned.add("Mox Emerald"); - banned.add("Mox Jet"); - banned.add("Mox Pearl"); - banned.add("Mox Ruby"); - banned.add("Mox Sapphire"); - banned.add("Mystical Tutor"); - banned.add("Natural Order"); - banned.add("Necropotence"); - banned.add("Oath of Druids"); - banned.add("Protean Hulk"); - banned.add("Sensei’s Diving Top"); - banned.add("Serra Ascendant"); - banned.add("Sharazad"); - banned.add("Survival of the Fittest"); - banned.add("Sol Ring"); - banned.add("Strip Mine"); - banned.add("The Tabernacle at Pendrell Vale"); - banned.add("Time Vault"); - banned.add("Time Walk"); - banned.add("Tinker"); - banned.add("Tolarian Academy"); - banned.add("Treasure Cruise"); - banned.add("Vampiric Tutor"); - banned.add("Vanishing"); - banned.add("Winter Orb"); - banned.add("Yawgmoth’s Bargain"); - - bannedCommander.add("Baral, Chief of Compliance"); - bannedCommander.add("Derevi, Empyrial Tactician"); - bannedCommander.add("Edgar Markov"); - bannedCommander.add("Kess, Dissident Mage"); - bannedCommander.add("Rofellos, Llanowar Emissary"); - - bannedPartner.add("Rowan Kenrith"); - bannedPartner.add(""); - bannedPartner.add(""); - bannedPartner.add(""); - -Tymna the Weaver -Will Kenrith -Vial Smasher The Fierce - } - -} diff --git a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205611.java b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205611.java deleted file mode 100644 index d3f636ed16..0000000000 --- a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205611.java +++ /dev/null @@ -1,90 +0,0 @@ - -package mage.deck; - -/** - * - * @author andreacosta - */ -public class CenturionCommander extends Commander { - - public CenturionCommander() { - super("Centurion Commander"); - banned.add("Ancestral Recall"); - banned.add("Ancient Tomb"); - banned.add("Back to Basic"); - banned.add("Balance"); - banned.add("Bazaar of Baghdad"); - banned.add("Black Lotus"); - banned.add("Cataclysm"); - banned.add("Channel"); - banned.add("Chaos Orb"); - banned.add("Chrome Mox"); - banned.add("Demonic Tutor"); - banned.add("Dig Through Time"); - banned.add("Emrakul, the Aeons Torn"); - banned.add("Emrakul, the Promised End"); - banned.add("Entomb"); - banned.add("Erayo, Soratami Ascendant"); - banned.add("Falling Star"); - banned.add("Fastbond"); - banned.add("Food Chain"); - banned.add("Gaea’s Cradle"); - banned.add("Gifts Ungiven"); - banned.add("Grim Monolith"); - banned.add("Grindstone"); - banned.add("Hermit Druid"); - banned.add("High Tide"); - banned.add("Humility"); - banned.add("Imperial Seal"); - banned.add("Karakas"); - banned.add("Library of Alexandria"); - banned.add("Mana Crypt"); - banned.add("Mana Drain"); - banned.add("Mana Vault"); - banned.add("Mishra’s Workshop"); - banned.add("Mind Twist"); - banned.add("Mox Diamond"); - banned.add("Mox Emerald"); - banned.add("Mox Jet"); - banned.add("Mox Pearl"); - banned.add("Mox Ruby"); - banned.add("Mox Sapphire"); - banned.add("Mystical Tutor"); - banned.add("Natural Order"); - banned.add("Necropotence"); - banned.add("Oath of Druids"); - banned.add("Protean Hulk"); - banned.add("Sensei’s Diving Top"); - banned.add("Serra Ascendant"); - banned.add("Sharazad"); - banned.add("Survival of the Fittest"); - banned.add("Sol Ring"); - banned.add("Strip Mine"); - banned.add("The Tabernacle at Pendrell Vale"); - banned.add("Time Vault"); - banned.add("Time Walk"); - banned.add("Tinker"); - banned.add("Tolarian Academy"); - banned.add("Treasure Cruise"); - banned.add("Vampiric Tutor"); - banned.add("Vanishing"); - banned.add("Winter Orb"); - banned.add("Yawgmoth’s Bargain"); - - bannedCommander.add("Baral, Chief of Compliance"); - bannedCommander.add("Derevi, Empyrial Tactician"); - bannedCommander.add("Edgar Markov"); - bannedCommander.add("Kess, Dissident Mage"); - bannedCommander.add("Rofellos, Llanowar Emissary"); - - bannedPartner.add("Rowan Kenrith"); - bannedPartner.add(""); - bannedPartner.add(""); - bannedPartner.add(""); - - -Will Kenrith -Vial Smasher The Fierce - } - -} diff --git a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205616.java b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205616.java deleted file mode 100644 index 017d21d275..0000000000 --- a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205616.java +++ /dev/null @@ -1,90 +0,0 @@ - -package mage.deck; - -/** - * - * @author andreacosta - */ -public class CenturionCommander extends Commander { - - public CenturionCommander() { - super("Centurion Commander"); - banned.add("Ancestral Recall"); - banned.add("Ancient Tomb"); - banned.add("Back to Basic"); - banned.add("Balance"); - banned.add("Bazaar of Baghdad"); - banned.add("Black Lotus"); - banned.add("Cataclysm"); - banned.add("Channel"); - banned.add("Chaos Orb"); - banned.add("Chrome Mox"); - banned.add("Demonic Tutor"); - banned.add("Dig Through Time"); - banned.add("Emrakul, the Aeons Torn"); - banned.add("Emrakul, the Promised End"); - banned.add("Entomb"); - banned.add("Erayo, Soratami Ascendant"); - banned.add("Falling Star"); - banned.add("Fastbond"); - banned.add("Food Chain"); - banned.add("Gaea’s Cradle"); - banned.add("Gifts Ungiven"); - banned.add("Grim Monolith"); - banned.add("Grindstone"); - banned.add("Hermit Druid"); - banned.add("High Tide"); - banned.add("Humility"); - banned.add("Imperial Seal"); - banned.add("Karakas"); - banned.add("Library of Alexandria"); - banned.add("Mana Crypt"); - banned.add("Mana Drain"); - banned.add("Mana Vault"); - banned.add("Mishra’s Workshop"); - banned.add("Mind Twist"); - banned.add("Mox Diamond"); - banned.add("Mox Emerald"); - banned.add("Mox Jet"); - banned.add("Mox Pearl"); - banned.add("Mox Ruby"); - banned.add("Mox Sapphire"); - banned.add("Mystical Tutor"); - banned.add("Natural Order"); - banned.add("Necropotence"); - banned.add("Oath of Druids"); - banned.add("Protean Hulk"); - banned.add("Sensei’s Diving Top"); - banned.add("Serra Ascendant"); - banned.add("Sharazad"); - banned.add("Survival of the Fittest"); - banned.add("Sol Ring"); - banned.add("Strip Mine"); - banned.add("The Tabernacle at Pendrell Vale"); - banned.add("Time Vault"); - banned.add("Time Walk"); - banned.add("Tinker"); - banned.add("Tolarian Academy"); - banned.add("Treasure Cruise"); - banned.add("Vampiric Tutor"); - banned.add("Vanishing"); - banned.add("Winter Orb"); - banned.add("Yawgmoth’s Bargain"); - - bannedCommander.add("Baral, Chief of Compliance"); - bannedCommander.add("Derevi, Empyrial Tactician"); - bannedCommander.add("Edgar Markov"); - bannedCommander.add("Kess, Dissident Mage"); - bannedCommander.add("Rofellos, Llanowar Emissary"); - - bannedPartner.add("Rowan Kenrith"); - bannedPartner.add("Tymna the Weaver"); - bannedPartner.add(""); - bannedPartner.add(""); - - -Will Kenrith -Vial Smasher The Fierce - } - -} diff --git a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205618.java b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205618.java deleted file mode 100644 index 84d97c4482..0000000000 --- a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205618.java +++ /dev/null @@ -1,90 +0,0 @@ - -package mage.deck; - -/** - * - * @author andreacosta - */ -public class CenturionCommander extends Commander { - - public CenturionCommander() { - super("Centurion Commander"); - banned.add("Ancestral Recall"); - banned.add("Ancient Tomb"); - banned.add("Back to Basic"); - banned.add("Balance"); - banned.add("Bazaar of Baghdad"); - banned.add("Black Lotus"); - banned.add("Cataclysm"); - banned.add("Channel"); - banned.add("Chaos Orb"); - banned.add("Chrome Mox"); - banned.add("Demonic Tutor"); - banned.add("Dig Through Time"); - banned.add("Emrakul, the Aeons Torn"); - banned.add("Emrakul, the Promised End"); - banned.add("Entomb"); - banned.add("Erayo, Soratami Ascendant"); - banned.add("Falling Star"); - banned.add("Fastbond"); - banned.add("Food Chain"); - banned.add("Gaea’s Cradle"); - banned.add("Gifts Ungiven"); - banned.add("Grim Monolith"); - banned.add("Grindstone"); - banned.add("Hermit Druid"); - banned.add("High Tide"); - banned.add("Humility"); - banned.add("Imperial Seal"); - banned.add("Karakas"); - banned.add("Library of Alexandria"); - banned.add("Mana Crypt"); - banned.add("Mana Drain"); - banned.add("Mana Vault"); - banned.add("Mishra’s Workshop"); - banned.add("Mind Twist"); - banned.add("Mox Diamond"); - banned.add("Mox Emerald"); - banned.add("Mox Jet"); - banned.add("Mox Pearl"); - banned.add("Mox Ruby"); - banned.add("Mox Sapphire"); - banned.add("Mystical Tutor"); - banned.add("Natural Order"); - banned.add("Necropotence"); - banned.add("Oath of Druids"); - banned.add("Protean Hulk"); - banned.add("Sensei’s Diving Top"); - banned.add("Serra Ascendant"); - banned.add("Sharazad"); - banned.add("Survival of the Fittest"); - banned.add("Sol Ring"); - banned.add("Strip Mine"); - banned.add("The Tabernacle at Pendrell Vale"); - banned.add("Time Vault"); - banned.add("Time Walk"); - banned.add("Tinker"); - banned.add("Tolarian Academy"); - banned.add("Treasure Cruise"); - banned.add("Vampiric Tutor"); - banned.add("Vanishing"); - banned.add("Winter Orb"); - banned.add("Yawgmoth’s Bargain"); - - bannedCommander.add("Baral, Chief of Compliance"); - bannedCommander.add("Derevi, Empyrial Tactician"); - bannedCommander.add("Edgar Markov"); - bannedCommander.add("Kess, Dissident Mage"); - bannedCommander.add("Rofellos, Llanowar Emissary"); - - bannedPartner.add("Rowan Kenrith"); - bannedPartner.add("Tymna the Weaver"); - bannedPartner.add(""); - bannedPartner.add(""); - - -Will Kenrith -Vial Smasher The Fierce - } - -} diff --git a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205619.java b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205619.java deleted file mode 100644 index fd1f426efb..0000000000 --- a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205619.java +++ /dev/null @@ -1,90 +0,0 @@ - -package mage.deck; - -/** - * - * @author andreacosta - */ -public class CenturionCommander extends Commander { - - public CenturionCommander() { - super("Centurion Commander"); - banned.add("Ancestral Recall"); - banned.add("Ancient Tomb"); - banned.add("Back to Basic"); - banned.add("Balance"); - banned.add("Bazaar of Baghdad"); - banned.add("Black Lotus"); - banned.add("Cataclysm"); - banned.add("Channel"); - banned.add("Chaos Orb"); - banned.add("Chrome Mox"); - banned.add("Demonic Tutor"); - banned.add("Dig Through Time"); - banned.add("Emrakul, the Aeons Torn"); - banned.add("Emrakul, the Promised End"); - banned.add("Entomb"); - banned.add("Erayo, Soratami Ascendant"); - banned.add("Falling Star"); - banned.add("Fastbond"); - banned.add("Food Chain"); - banned.add("Gaea’s Cradle"); - banned.add("Gifts Ungiven"); - banned.add("Grim Monolith"); - banned.add("Grindstone"); - banned.add("Hermit Druid"); - banned.add("High Tide"); - banned.add("Humility"); - banned.add("Imperial Seal"); - banned.add("Karakas"); - banned.add("Library of Alexandria"); - banned.add("Mana Crypt"); - banned.add("Mana Drain"); - banned.add("Mana Vault"); - banned.add("Mishra’s Workshop"); - banned.add("Mind Twist"); - banned.add("Mox Diamond"); - banned.add("Mox Emerald"); - banned.add("Mox Jet"); - banned.add("Mox Pearl"); - banned.add("Mox Ruby"); - banned.add("Mox Sapphire"); - banned.add("Mystical Tutor"); - banned.add("Natural Order"); - banned.add("Necropotence"); - banned.add("Oath of Druids"); - banned.add("Protean Hulk"); - banned.add("Sensei’s Diving Top"); - banned.add("Serra Ascendant"); - banned.add("Sharazad"); - banned.add("Survival of the Fittest"); - banned.add("Sol Ring"); - banned.add("Strip Mine"); - banned.add("The Tabernacle at Pendrell Vale"); - banned.add("Time Vault"); - banned.add("Time Walk"); - banned.add("Tinker"); - banned.add("Tolarian Academy"); - banned.add("Treasure Cruise"); - banned.add("Vampiric Tutor"); - banned.add("Vanishing"); - banned.add("Winter Orb"); - banned.add("Yawgmoth’s Bargain"); - - bannedCommander.add("Baral, Chief of Compliance"); - bannedCommander.add("Derevi, Empyrial Tactician"); - bannedCommander.add("Edgar Markov"); - bannedCommander.add("Kess, Dissident Mage"); - bannedCommander.add("Rofellos, Llanowar Emissary"); - - bannedPartner.add("Rowan Kenrith"); - bannedPartner.add("Tymna the Weaver"); - bannedPartner.add(""); - bannedPartner.add(""); - - - -Vial Smasher The Fierce - } - -} diff --git a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205622.java b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205622.java deleted file mode 100644 index 0f17649219..0000000000 --- a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205622.java +++ /dev/null @@ -1,90 +0,0 @@ - -package mage.deck; - -/** - * - * @author andreacosta - */ -public class CenturionCommander extends Commander { - - public CenturionCommander() { - super("Centurion Commander"); - banned.add("Ancestral Recall"); - banned.add("Ancient Tomb"); - banned.add("Back to Basic"); - banned.add("Balance"); - banned.add("Bazaar of Baghdad"); - banned.add("Black Lotus"); - banned.add("Cataclysm"); - banned.add("Channel"); - banned.add("Chaos Orb"); - banned.add("Chrome Mox"); - banned.add("Demonic Tutor"); - banned.add("Dig Through Time"); - banned.add("Emrakul, the Aeons Torn"); - banned.add("Emrakul, the Promised End"); - banned.add("Entomb"); - banned.add("Erayo, Soratami Ascendant"); - banned.add("Falling Star"); - banned.add("Fastbond"); - banned.add("Food Chain"); - banned.add("Gaea’s Cradle"); - banned.add("Gifts Ungiven"); - banned.add("Grim Monolith"); - banned.add("Grindstone"); - banned.add("Hermit Druid"); - banned.add("High Tide"); - banned.add("Humility"); - banned.add("Imperial Seal"); - banned.add("Karakas"); - banned.add("Library of Alexandria"); - banned.add("Mana Crypt"); - banned.add("Mana Drain"); - banned.add("Mana Vault"); - banned.add("Mishra’s Workshop"); - banned.add("Mind Twist"); - banned.add("Mox Diamond"); - banned.add("Mox Emerald"); - banned.add("Mox Jet"); - banned.add("Mox Pearl"); - banned.add("Mox Ruby"); - banned.add("Mox Sapphire"); - banned.add("Mystical Tutor"); - banned.add("Natural Order"); - banned.add("Necropotence"); - banned.add("Oath of Druids"); - banned.add("Protean Hulk"); - banned.add("Sensei’s Diving Top"); - banned.add("Serra Ascendant"); - banned.add("Sharazad"); - banned.add("Survival of the Fittest"); - banned.add("Sol Ring"); - banned.add("Strip Mine"); - banned.add("The Tabernacle at Pendrell Vale"); - banned.add("Time Vault"); - banned.add("Time Walk"); - banned.add("Tinker"); - banned.add("Tolarian Academy"); - banned.add("Treasure Cruise"); - banned.add("Vampiric Tutor"); - banned.add("Vanishing"); - banned.add("Winter Orb"); - banned.add("Yawgmoth’s Bargain"); - - bannedCommander.add("Baral, Chief of Compliance"); - bannedCommander.add("Derevi, Empyrial Tactician"); - bannedCommander.add("Edgar Markov"); - bannedCommander.add("Kess, Dissident Mage"); - bannedCommander.add("Rofellos, Llanowar Emissary"); - - bannedPartner.add("Rowan Kenrith"); - bannedPartner.add("Tymna the Weaver"); - bannedPartner.add("Will Kenrith"); - bannedPartner.add(""); - - - -Vial Smasher The Fierce - } - -} diff --git a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205627.java b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205627.java deleted file mode 100644 index 8fea4fc748..0000000000 --- a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205627.java +++ /dev/null @@ -1,86 +0,0 @@ - -package mage.deck; - -/** - * - * @author andreacosta - */ -public class CenturionCommander extends Commander { - - public CenturionCommander() { - super("Centurion Commander"); - banned.add("Ancestral Recall"); - banned.add("Ancient Tomb"); - banned.add("Back to Basic"); - banned.add("Balance"); - banned.add("Bazaar of Baghdad"); - banned.add("Black Lotus"); - banned.add("Cataclysm"); - banned.add("Channel"); - banned.add("Chaos Orb"); - banned.add("Chrome Mox"); - banned.add("Demonic Tutor"); - banned.add("Dig Through Time"); - banned.add("Emrakul, the Aeons Torn"); - banned.add("Emrakul, the Promised End"); - banned.add("Entomb"); - banned.add("Erayo, Soratami Ascendant"); - banned.add("Falling Star"); - banned.add("Fastbond"); - banned.add("Food Chain"); - banned.add("Gaea’s Cradle"); - banned.add("Gifts Ungiven"); - banned.add("Grim Monolith"); - banned.add("Grindstone"); - banned.add("Hermit Druid"); - banned.add("High Tide"); - banned.add("Humility"); - banned.add("Imperial Seal"); - banned.add("Karakas"); - banned.add("Library of Alexandria"); - banned.add("Mana Crypt"); - banned.add("Mana Drain"); - banned.add("Mana Vault"); - banned.add("Mishra’s Workshop"); - banned.add("Mind Twist"); - banned.add("Mox Diamond"); - banned.add("Mox Emerald"); - banned.add("Mox Jet"); - banned.add("Mox Pearl"); - banned.add("Mox Ruby"); - banned.add("Mox Sapphire"); - banned.add("Mystical Tutor"); - banned.add("Natural Order"); - banned.add("Necropotence"); - banned.add("Oath of Druids"); - banned.add("Protean Hulk"); - banned.add("Sensei’s Diving Top"); - banned.add("Serra Ascendant"); - banned.add("Sharazad"); - banned.add("Survival of the Fittest"); - banned.add("Sol Ring"); - banned.add("Strip Mine"); - banned.add("The Tabernacle at Pendrell Vale"); - banned.add("Time Vault"); - banned.add("Time Walk"); - banned.add("Tinker"); - banned.add("Tolarian Academy"); - banned.add("Treasure Cruise"); - banned.add("Vampiric Tutor"); - banned.add("Vanishing"); - banned.add("Winter Orb"); - banned.add("Yawgmoth’s Bargain"); - - bannedCommander.add("Baral, Chief of Compliance"); - bannedCommander.add("Derevi, Empyrial Tactician"); - bannedCommander.add("Edgar Markov"); - bannedCommander.add("Kess, Dissident Mage"); - bannedCommander.add("Rofellos, Llanowar Emissary"); - - bannedPartner.add("Rowan Kenrith"); - bannedPartner.add("Tymna the Weaver"); - bannedPartner.add("Will Kenrith"); - bannedPartner.add(""); - } - -} diff --git a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205628.java b/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205628.java deleted file mode 100644 index e66990b5af..0000000000 --- a/.history/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/CenturionCommander_20191016205628.java +++ /dev/null @@ -1,86 +0,0 @@ - -package mage.deck; - -/** - * - * @author andreacosta - */ -public class CenturionCommander extends Commander { - - public CenturionCommander() { - super("Centurion Commander"); - banned.add("Ancestral Recall"); - banned.add("Ancient Tomb"); - banned.add("Back to Basic"); - banned.add("Balance"); - banned.add("Bazaar of Baghdad"); - banned.add("Black Lotus"); - banned.add("Cataclysm"); - banned.add("Channel"); - banned.add("Chaos Orb"); - banned.add("Chrome Mox"); - banned.add("Demonic Tutor"); - banned.add("Dig Through Time"); - banned.add("Emrakul, the Aeons Torn"); - banned.add("Emrakul, the Promised End"); - banned.add("Entomb"); - banned.add("Erayo, Soratami Ascendant"); - banned.add("Falling Star"); - banned.add("Fastbond"); - banned.add("Food Chain"); - banned.add("Gaea’s Cradle"); - banned.add("Gifts Ungiven"); - banned.add("Grim Monolith"); - banned.add("Grindstone"); - banned.add("Hermit Druid"); - banned.add("High Tide"); - banned.add("Humility"); - banned.add("Imperial Seal"); - banned.add("Karakas"); - banned.add("Library of Alexandria"); - banned.add("Mana Crypt"); - banned.add("Mana Drain"); - banned.add("Mana Vault"); - banned.add("Mishra’s Workshop"); - banned.add("Mind Twist"); - banned.add("Mox Diamond"); - banned.add("Mox Emerald"); - banned.add("Mox Jet"); - banned.add("Mox Pearl"); - banned.add("Mox Ruby"); - banned.add("Mox Sapphire"); - banned.add("Mystical Tutor"); - banned.add("Natural Order"); - banned.add("Necropotence"); - banned.add("Oath of Druids"); - banned.add("Protean Hulk"); - banned.add("Sensei’s Diving Top"); - banned.add("Serra Ascendant"); - banned.add("Sharazad"); - banned.add("Survival of the Fittest"); - banned.add("Sol Ring"); - banned.add("Strip Mine"); - banned.add("The Tabernacle at Pendrell Vale"); - banned.add("Time Vault"); - banned.add("Time Walk"); - banned.add("Tinker"); - banned.add("Tolarian Academy"); - banned.add("Treasure Cruise"); - banned.add("Vampiric Tutor"); - banned.add("Vanishing"); - banned.add("Winter Orb"); - banned.add("Yawgmoth’s Bargain"); - - bannedCommander.add("Baral, Chief of Compliance"); - bannedCommander.add("Derevi, Empyrial Tactician"); - bannedCommander.add("Edgar Markov"); - bannedCommander.add("Kess, Dissident Mage"); - bannedCommander.add("Rofellos, Llanowar Emissary"); - - bannedPartner.add("Rowan Kenrith"); - bannedPartner.add("Tymna the Weaver"); - bannedPartner.add("Will Kenrith"); - bannedPartner.add("Vial Smasher The Fierce"); - } - -} From 862faada772ab0167e924359ac4e6004d1b0332b Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 16 Oct 2019 15:26:18 -0400 Subject: [PATCH 366/373] Update .gitignore --- .gitignore | 3 +++ 1 file changed, 3 insertions(+) diff --git a/.gitignore b/.gitignore index ae4cade4b6..34ddf1abfb 100644 --- a/.gitignore +++ b/.gitignore @@ -152,3 +152,6 @@ mage-bundle # build-tools config and log files when building client/server with Atom .build-tools.cson build-output.log + +# Visual Studio Code +.history From dd85324bc9505551b84def97fd0a9f09feb93962 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 21 Oct 2019 15:35:52 -0400 Subject: [PATCH 367/373] updated Pauper ban list --- .../Mage.Deck.Constructed/src/mage/deck/Pauper.java | 1 + 1 file changed, 1 insertion(+) diff --git a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Pauper.java b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Pauper.java index beee09be79..f22eba8467 100644 --- a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Pauper.java +++ b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Pauper.java @@ -21,6 +21,7 @@ public class Pauper extends Constructed { rarities.add(Rarity.COMMON); rarities.add(Rarity.LAND); + banned.add("Arcum's Astrolabe"); banned.add("Cloud of Faeries"); banned.add("Cloudpost"); banned.add("Cranial Plating"); From e0eb61053ef78af21fc3661b4039b364764be1bf Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 21 Oct 2019 15:36:04 -0400 Subject: [PATCH 368/373] updated Standard ban list --- .../Mage.Deck.Constructed/src/mage/deck/Standard.java | 2 ++ 1 file changed, 2 insertions(+) diff --git a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Standard.java b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Standard.java index 6abe881da1..07dc1bdb59 100644 --- a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Standard.java +++ b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Standard.java @@ -16,6 +16,8 @@ public class Standard extends Constructed { super("Constructed - Standard"); setCodes.addAll(makeLegalSets()); + + banned.add("Field of the Dead"); // since 2019-10-21 } private static boolean isFallSet(ExpansionSet set) { From b49bf569cef8629310a12eb49a059c2b4650db36 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Mon, 21 Oct 2019 21:46:37 -0400 Subject: [PATCH 369/373] added Pioneer format --- .../java/mage/client/table/TablesPanel.java | 4 +++ .../client/util/sets/ConstructedFormats.java | 9 ++++++ .../src/mage/deck/Pioneer.java | 31 +++++++++++++++++++ Mage.Server/config/config.xml | 1 + Mage.Server/release/config/config.xml | 1 + 5 files changed, 46 insertions(+) create mode 100644 Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Pioneer.java diff --git a/Mage.Client/src/main/java/mage/client/table/TablesPanel.java b/Mage.Client/src/main/java/mage/client/table/TablesPanel.java index a6e001d385..2d4ac36918 100644 --- a/Mage.Client/src/main/java/mage/client/table/TablesPanel.java +++ b/Mage.Client/src/main/java/mage/client/table/TablesPanel.java @@ -802,6 +802,9 @@ public class TablesPanel extends javax.swing.JPanel { if (btnFormatModern.isSelected()) { formatFilterList.add(RowFilter.regexFilter("^Constructed - Modern", TablesTableModel.COLUMN_DECK_TYPE)); } + if (btnFormatPioneer.isSelected()) { + formatFilterList.add(RowFilter.regexFilter("^Constructed - Pioneer", TablesTableModel.COLUMN_DECK_TYPE)); + } if (btnFormatLegacy.isSelected()) { formatFilterList.add(RowFilter.regexFilter("^Constructed - Legacy", TablesTableModel.COLUMN_DECK_TYPE)); } @@ -1670,6 +1673,7 @@ public class TablesPanel extends javax.swing.JPanel { private javax.swing.JToggleButton btnFormatLegacy; private javax.swing.JToggleButton btnFormatLimited; private javax.swing.JToggleButton btnFormatModern; + private javax.swing.JToggleButton btnFormatPioneer; private javax.swing.JToggleButton btnFormatOathbreaker; private javax.swing.JToggleButton btnFormatOther; private javax.swing.JToggleButton btnFormatPremodern; diff --git a/Mage.Client/src/main/java/mage/client/util/sets/ConstructedFormats.java b/Mage.Client/src/main/java/mage/client/util/sets/ConstructedFormats.java index 37d050fc46..854f6d5195 100644 --- a/Mage.Client/src/main/java/mage/client/util/sets/ConstructedFormats.java +++ b/Mage.Client/src/main/java/mage/client/util/sets/ConstructedFormats.java @@ -20,6 +20,7 @@ public final class ConstructedFormats { public static final String STANDARD = "- Standard"; public static final String EXTENDED = "- Extended"; public static final String FRONTIER = "- Frontier"; + public static final String PIONEER = "- Pioneer"; public static final String MODERN = "- Modern"; public static final String VINTAGE_LEGACY = "- Vintage / Legacy"; public static final String JOKE = "- Joke Sets"; @@ -29,6 +30,7 @@ public final class ConstructedFormats { // Attention -Month is 0 Based so Feb = 1 for example. // private static final Date extendedDate = new GregorianCalendar(2009, 7, 20).getTime(); private static final Date frontierDate = new GregorianCalendar(2014, 6, 17).getTime(); + private static final Date pioneerDate = new GregorianCalendar(2012, 10, 5).getTime(); private static final Date modernDate = new GregorianCalendar(2003, 6, 20).getTime(); // for all sets just return empty list @@ -82,6 +84,7 @@ public final class ConstructedFormats { underlyingSetCodesPerFormat.put(STANDARD, new ArrayList<>()); underlyingSetCodesPerFormat.put(EXTENDED, new ArrayList<>()); underlyingSetCodesPerFormat.put(FRONTIER, new ArrayList<>()); + underlyingSetCodesPerFormat.put(PIONEER, new ArrayList<>()); underlyingSetCodesPerFormat.put(MODERN, new ArrayList<>()); underlyingSetCodesPerFormat.put(VINTAGE_LEGACY, new ArrayList<>()); underlyingSetCodesPerFormat.put(JOKE, new ArrayList<>()); @@ -134,6 +137,11 @@ public final class ConstructedFormats { underlyingSetCodesPerFormat.get(FRONTIER).add(set.getCode()); } + // frontier + if (set.getType().isStandardLegal() && set.getReleaseDate().after(pioneerDate)) { + underlyingSetCodesPerFormat.get(PIONEER).add(set.getCode()); + } + // modern if (set.getType().isModernLegal() && set.getReleaseDate().after(modernDate)) { underlyingSetCodesPerFormat.get(MODERN).add(set.getCode()); @@ -251,6 +259,7 @@ public final class ConstructedFormats { formats.add(0, JOKE); formats.add(0, VINTAGE_LEGACY); formats.add(0, MODERN); + formats.add(0, PIONEER); formats.add(0, FRONTIER); formats.add(0, EXTENDED); formats.add(0, STANDARD); diff --git a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Pioneer.java b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Pioneer.java new file mode 100644 index 0000000000..95a1e50fc0 --- /dev/null +++ b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Pioneer.java @@ -0,0 +1,31 @@ +package mage.deck; + +import mage.cards.ExpansionSet; +import mage.cards.Sets; +import mage.cards.decks.Constructed; + +import java.util.Date; +import java.util.GregorianCalendar; + +/** + * @author TheElk801 + */ +public class Pioneer extends Constructed { + + public Pioneer() { + super("Constructed - Pioneer"); + + Date cutoff = new GregorianCalendar(2012, 10, 5).getTime(); // M15 release date + for (ExpansionSet set : Sets.getInstance().values()) { + if (set.getSetType().isStandardLegal() && (set.getReleaseDate().after(cutoff) || set.getReleaseDate().equals(cutoff))) { + setCodes.add(set.getCode()); + } + } + + banned.add("Bloodstained Mire"); + banned.add("Flooded Strand"); + banned.add("Polluted Delta"); + banned.add("Windswept Heath"); + banned.add("Wooded Foothills"); + } +} diff --git a/Mage.Server/config/config.xml b/Mage.Server/config/config.xml index 098bbe7c3d..8f182580c1 100644 --- a/Mage.Server/config/config.xml +++ b/Mage.Server/config/config.xml @@ -149,6 +149,7 @@ + diff --git a/Mage.Server/release/config/config.xml b/Mage.Server/release/config/config.xml index 111ef0e394..75c5d943a0 100644 --- a/Mage.Server/release/config/config.xml +++ b/Mage.Server/release/config/config.xml @@ -143,6 +143,7 @@ + From 2281a4df7c85ba73ad93da30daa20d75e3c6cfbc Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Wed, 23 Oct 2019 20:46:01 -0400 Subject: [PATCH 370/373] fixed Obzedat, Ghost Council interacting incorrectly with other exile effects --- .../src/mage/cards/o/ObzedatGhostCouncil.java | 82 ++++++++++--------- 1 file changed, 42 insertions(+), 40 deletions(-) diff --git a/Mage.Sets/src/mage/cards/o/ObzedatGhostCouncil.java b/Mage.Sets/src/mage/cards/o/ObzedatGhostCouncil.java index b0ea8280e2..c936c96074 100644 --- a/Mage.Sets/src/mage/cards/o/ObzedatGhostCouncil.java +++ b/Mage.Sets/src/mage/cards/o/ObzedatGhostCouncil.java @@ -1,14 +1,12 @@ package mage.cards.o; -import java.util.UUID; import mage.MageInt; +import mage.MageObjectReference; import mage.abilities.Ability; import mage.abilities.DelayedTriggeredAbility; import mage.abilities.common.BeginningOfYourEndStepTriggeredAbility; import mage.abilities.common.EntersBattlefieldTriggeredAbility; -import mage.abilities.effects.Effect; import mage.abilities.effects.OneShotEffect; -import mage.abilities.effects.common.CreateDelayedTriggeredAbilityEffect; import mage.abilities.effects.common.GainLifeEffect; import mage.abilities.effects.common.LoseLifeTargetEffect; import mage.abilities.effects.common.continuous.GainAbilitySourceEffect; @@ -24,8 +22,9 @@ import mage.game.permanent.Permanent; import mage.players.Player; import mage.target.common.TargetOpponent; +import java.util.UUID; + /** - * * @author Plopman */ public final class ObzedatGhostCouncil extends CardImpl { @@ -41,16 +40,15 @@ public final class ObzedatGhostCouncil extends CardImpl { //When Obzedat, Ghost Council enters the battlefield, target opponent loses 2 life and you gain 2 life. Ability ability = new EntersBattlefieldTriggeredAbility(new LoseLifeTargetEffect(2)); - ability.addEffect(new GainLifeEffect(2).setText("and you gain 2 life")); + ability.addEffect(new GainLifeEffect(2).concatBy("and")); ability.addTarget(new TargetOpponent()); this.addAbility(ability); //At the beginning of your end step you may exile Obzedat. If you do, return it to the battlefield under its owner's control at the beginning of your next upkeep. It gains haste. Ability ability2 = new BeginningOfYourEndStepTriggeredAbility(new ObzedatGhostCouncilExileSourceEffect(), true); - ability2.addEffect(new CreateDelayedTriggeredAbilityEffect(new BeginningOfYourUpkeepdelayTriggeredAbility())); this.addAbility(ability2); } - public ObzedatGhostCouncil(final ObzedatGhostCouncil card) { + private ObzedatGhostCouncil(final ObzedatGhostCouncil card) { super(card); } @@ -62,12 +60,13 @@ public final class ObzedatGhostCouncil extends CardImpl { class ObzedatGhostCouncilExileSourceEffect extends OneShotEffect { - public ObzedatGhostCouncilExileSourceEffect() { + ObzedatGhostCouncilExileSourceEffect() { super(Outcome.Exile); - staticText = "exile {this}"; + staticText = "exile {this}. If you do, return it to the battlefield under its owner's control " + + "at the beginning of your next upkeep. It gains haste."; } - public ObzedatGhostCouncilExileSourceEffect(final ObzedatGhostCouncilExileSourceEffect effect) { + private ObzedatGhostCouncilExileSourceEffect(final ObzedatGhostCouncilExileSourceEffect effect) { super(effect); } @@ -78,27 +77,25 @@ class ObzedatGhostCouncilExileSourceEffect extends OneShotEffect { @Override public boolean apply(Game game, Ability source) { + Player player = game.getPlayer(source.getControllerId()); Permanent permanent = game.getPermanent(source.getSourceId()); - if (permanent != null) { - return permanent.moveToExile(source.getSourceId(), permanent.getName(), source.getSourceId(), game); + if (permanent == null || player == null + || !player.moveCards(permanent, Zone.EXILED, source, game)) { + return false; } - return false; + game.addDelayedTriggeredAbility(new ObzedatGhostCouncilDelayedTriggeredAbility(new MageObjectReference(permanent, game)), source); + return true; } } -class BeginningOfYourUpkeepdelayTriggeredAbility extends DelayedTriggeredAbility { +class ObzedatGhostCouncilDelayedTriggeredAbility extends DelayedTriggeredAbility { - public BeginningOfYourUpkeepdelayTriggeredAbility() { - this(new ObzedatGhostCouncilReturnEffect(), TargetController.YOU); - this.addEffect(new GainAbilitySourceEffect(HasteAbility.getInstance(), Duration.Custom)); + ObzedatGhostCouncilDelayedTriggeredAbility(MageObjectReference mor) { + super(new ObzedatGhostCouncilReturnEffect(mor)); } - public BeginningOfYourUpkeepdelayTriggeredAbility(Effect effect, TargetController targetController) { - super(effect); - } - - public BeginningOfYourUpkeepdelayTriggeredAbility(BeginningOfYourUpkeepdelayTriggeredAbility ability) { + private ObzedatGhostCouncilDelayedTriggeredAbility(ObzedatGhostCouncilDelayedTriggeredAbility ability) { super(ability); } @@ -113,24 +110,28 @@ class BeginningOfYourUpkeepdelayTriggeredAbility extends DelayedTriggeredAbility } @Override - public BeginningOfYourUpkeepdelayTriggeredAbility copy() { - return new BeginningOfYourUpkeepdelayTriggeredAbility(this); + public ObzedatGhostCouncilDelayedTriggeredAbility copy() { + return new ObzedatGhostCouncilDelayedTriggeredAbility(this); } @Override public String getRule() { - return "If you do, return it to the battlefield under its owner's control at the beginning of your next upkeep. It gains haste"; + return "Return {this} to the battlefield under its owner's control at the beginning of your next upkeep. It gains haste"; } } class ObzedatGhostCouncilReturnEffect extends OneShotEffect { - public ObzedatGhostCouncilReturnEffect() { + private final MageObjectReference mor; + + ObzedatGhostCouncilReturnEffect(MageObjectReference mor) { super(Outcome.Benefit); + this.mor = mor; } - public ObzedatGhostCouncilReturnEffect(final ObzedatGhostCouncilReturnEffect effect) { + private ObzedatGhostCouncilReturnEffect(final ObzedatGhostCouncilReturnEffect effect) { super(effect); + this.mor = effect.mor; } @Override @@ -140,19 +141,20 @@ class ObzedatGhostCouncilReturnEffect extends OneShotEffect { @Override public boolean apply(Game game, Ability source) { - Card card = game.getCard(source.getSourceId()); - if (card != null) { - Zone zone = game.getState().getZone(source.getSourceId()); - // return it from every public zone - http://www.mtgsalvation.com/forums/magic-fundamentals/magic-rulings/magic-rulings-archives/513186-obzedat-gc-as-edh-commander - if (zone != Zone.BATTLEFIELD && zone != Zone.LIBRARY && zone != Zone.HAND) { - Player owner = game.getPlayer(card.getOwnerId()); - if (owner != null) { - owner.moveCards(card, Zone.BATTLEFIELD, source, game); - } - } - return true; + Card card = mor.getCard(game); + if (card == null) { + return false; } - return false; + Zone zone = game.getState().getZone(source.getSourceId()); + // return it from every public zone - http://www.mtgsalvation.com/forums/magic-fundamentals/magic-rulings/magic-rulings-archives/513186-obzedat-gc-as-edh-commander + if (zone == Zone.BATTLEFIELD || zone == Zone.LIBRARY || zone == Zone.HAND) { + return false; + } + Player owner = game.getPlayer(card.getOwnerId()); + if (owner == null || !owner.moveCards(card, Zone.BATTLEFIELD, source, game)) { + return false; + } + game.addEffect(new GainAbilitySourceEffect(HasteAbility.getInstance(), Duration.WhileOnBattlefield), source); + return true; } - } From cf39bce677a49e3fcc70d6ab4ed7e1d6d871c955 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Thu, 24 Oct 2019 17:41:23 -0400 Subject: [PATCH 371/373] updated Brawl banned list --- .../Mage.Deck.Constructed/src/mage/deck/Brawl.java | 2 -- .../Mage.Deck.Constructed/src/mage/deck/Standard.java | 2 +- 2 files changed, 1 insertion(+), 3 deletions(-) diff --git a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Brawl.java b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Brawl.java index fdf8ace073..2a3c502b68 100644 --- a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Brawl.java +++ b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Brawl.java @@ -22,8 +22,6 @@ public class Brawl extends Constructed { // Copy of standard sets setCodes.addAll(Standard.makeLegalSets()); - banned.add("Baral, Chief of Compliance"); - banned.add("Smuggler's Copter"); banned.add("Sorcerous Spyglass"); } diff --git a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Standard.java b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Standard.java index 07dc1bdb59..3c95dc7616 100644 --- a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Standard.java +++ b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Standard.java @@ -27,7 +27,7 @@ public class Standard extends Constructed { return set.getSetType() == SetType.EXPANSION && (cal.get(Calendar.MONTH) > 7); } - public static List makeLegalSets() { + static List makeLegalSets() { List codes = new ArrayList<>(); GregorianCalendar current = new GregorianCalendar(); List sets = new ArrayList(Sets.getInstance().values()); From 4ab598a7c906f32a1f6416b2d3f9af4935e9a802 Mon Sep 17 00:00:00 2001 From: Oleg Agafonov Date: Tue, 5 Nov 2019 22:29:22 +0400 Subject: [PATCH 372/373] Fixed missing code in Pioneer format --- .../java/mage/client/table/TablesPanel.form | 14 ++++++++++++++ .../java/mage/client/table/TablesPanel.java | 17 ++++++++++++++++- 2 files changed, 30 insertions(+), 1 deletion(-) diff --git a/Mage.Client/src/main/java/mage/client/table/TablesPanel.form b/Mage.Client/src/main/java/mage/client/table/TablesPanel.form index 41e7b06a4c..14518523fd 100644 --- a/Mage.Client/src/main/java/mage/client/table/TablesPanel.form +++ b/Mage.Client/src/main/java/mage/client/table/TablesPanel.form @@ -366,6 +366,20 @@ + + + + + + + + + + + + + + diff --git a/Mage.Client/src/main/java/mage/client/table/TablesPanel.java b/Mage.Client/src/main/java/mage/client/table/TablesPanel.java index 2d4ac36918..62326c77a8 100644 --- a/Mage.Client/src/main/java/mage/client/table/TablesPanel.java +++ b/Mage.Client/src/main/java/mage/client/table/TablesPanel.java @@ -333,7 +333,7 @@ public class TablesPanel extends javax.swing.JPanel { filterButtons = new JToggleButton[]{btnStateWaiting, btnStateActive, btnStateFinished, btnTypeMatch, btnTypeTourneyConstructed, btnTypeTourneyLimited, btnFormatBlock, btnFormatStandard, btnFormatModern, btnFormatLegacy, btnFormatVintage, btnFormatPremodern, btnFormatCommander, btnFormatTinyLeader, btnFormatLimited, btnFormatOther, - btnSkillBeginner, btnSkillCasual, btnSkillSerious, btnRated, btnUnrated, btnOpen, btnPassword, btnFormatOathbreaker}; + btnSkillBeginner, btnSkillCasual, btnSkillSerious, btnRated, btnUnrated, btnOpen, btnPassword, btnFormatOathbreaker, btnFormatPioneer}; JComponent[] components = new JComponent[]{chatPanelMain, jSplitPane1, jScrollPaneTablesActive, jScrollPaneTablesFinished, jPanelTop, jPanelTables}; for (JComponent component : components) { @@ -968,6 +968,7 @@ public class TablesPanel extends javax.swing.JPanel { btnFormatBlock = new javax.swing.JToggleButton(); btnFormatStandard = new javax.swing.JToggleButton(); btnFormatModern = new javax.swing.JToggleButton(); + btnFormatPioneer = new javax.swing.JToggleButton(); btnFormatLegacy = new javax.swing.JToggleButton(); btnFormatVintage = new javax.swing.JToggleButton(); btnFormatPremodern = new javax.swing.JToggleButton(); @@ -1259,6 +1260,20 @@ public class TablesPanel extends javax.swing.JPanel { }); filterBar2.add(btnFormatModern); + btnFormatPioneer.setSelected(true); + btnFormatPioneer.setText("Pioneer"); + btnFormatPioneer.setToolTipText("Pioneer format."); + btnFormatPioneer.setFocusPainted(false); + btnFormatPioneer.setFocusable(false); + btnFormatPioneer.setRequestFocusEnabled(false); + btnFormatPioneer.setVerifyInputWhenFocusTarget(false); + btnFormatPioneer.addActionListener(new java.awt.event.ActionListener() { + public void actionPerformed(java.awt.event.ActionEvent evt) { + btnFilterActionPerformed(evt); + } + }); + filterBar2.add(btnFormatPioneer); + btnFormatLegacy.setSelected(true); btnFormatLegacy.setText("Legacy"); btnFormatLegacy.setToolTipText("Legacy format."); From b4325b1daa0aa6d68add7f2b214064129715540e Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Tue, 5 Nov 2019 20:11:04 -0500 Subject: [PATCH 373/373] updated Pioneer ban list --- .../Mage.Deck.Constructed/src/mage/deck/Pioneer.java | 3 +++ 1 file changed, 3 insertions(+) diff --git a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Pioneer.java b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Pioneer.java index 95a1e50fc0..fe7f1ebd42 100644 --- a/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Pioneer.java +++ b/Mage.Server.Plugins/Mage.Deck.Constructed/src/mage/deck/Pioneer.java @@ -27,5 +27,8 @@ public class Pioneer extends Constructed { banned.add("Polluted Delta"); banned.add("Windswept Heath"); banned.add("Wooded Foothills"); + banned.add("Felidar Guardian"); + banned.add("Leyline of Abundance"); + banned.add("Oath of Nissa"); } }