From 4d81b7618089085013fce9134f7a773abcc080f4 Mon Sep 17 00:00:00 2001 From: Evan Kranzler Date: Tue, 11 Oct 2022 20:56:31 -0400 Subject: [PATCH] [40K] Implemented Shard of the Nightbringer --- .../mage/cards/s/ShardOfTheNightbringer.java | 87 +++++++++++++++++++ Mage.Sets/src/mage/sets/Warhammer40000.java | 1 + .../java/mage/verify/VerifyCardDataTest.java | 19 ++-- .../src/main/java/mage/constants/SubType.java | 1 + 4 files changed, 98 insertions(+), 10 deletions(-) create mode 100644 Mage.Sets/src/mage/cards/s/ShardOfTheNightbringer.java diff --git a/Mage.Sets/src/mage/cards/s/ShardOfTheNightbringer.java b/Mage.Sets/src/mage/cards/s/ShardOfTheNightbringer.java new file mode 100644 index 0000000000..8ec93348cd --- /dev/null +++ b/Mage.Sets/src/mage/cards/s/ShardOfTheNightbringer.java @@ -0,0 +1,87 @@ +package mage.cards.s; + +import mage.MageInt; +import mage.abilities.Ability; +import mage.abilities.common.EntersBattlefieldTriggeredAbility; +import mage.abilities.condition.common.CastFromEverywhereSourceCondition; +import mage.abilities.decorator.ConditionalInterveningIfTriggeredAbility; +import mage.abilities.effects.OneShotEffect; +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.game.Game; +import mage.players.Player; +import mage.target.common.TargetOpponent; + +import java.util.UUID; + +/** + * @author TheElk801 + */ +public final class ShardOfTheNightbringer extends CardImpl { + + public ShardOfTheNightbringer(UUID ownerId, CardSetInfo setInfo) { + super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{5}{B}{B}{B}"); + + this.subtype.add(SubType.CTAN); + this.power = new MageInt(8); + this.toughness = new MageInt(8); + + // Flying + this.addAbility(FlyingAbility.getInstance()); + + // Drain Life -- When Shard of the Nightbringer enters the battlefield, if you cast it, target opponent loses half their life, rounded up. You gain life equal to the life lost this way. + Ability ability = new ConditionalInterveningIfTriggeredAbility( + new EntersBattlefieldTriggeredAbility(new ShardOfTheNightbringerEffect()), + CastFromEverywhereSourceCondition.instance, "When {this} enters the battlefield, " + + "if you cast it, target opponent loses half their life, rounded up. " + + "You gain life equal to the life lost this way." + ); + ability.addTarget(new TargetOpponent()); + this.addAbility(ability.withFlavorWord("Drain Life")); + } + + private ShardOfTheNightbringer(final ShardOfTheNightbringer card) { + super(card); + } + + @Override + public ShardOfTheNightbringer copy() { + return new ShardOfTheNightbringer(this); + } +} + +class ShardOfTheNightbringerEffect extends OneShotEffect { + + ShardOfTheNightbringerEffect() { + super(Outcome.Benefit); + } + + private ShardOfTheNightbringerEffect(final ShardOfTheNightbringerEffect effect) { + super(effect); + } + + @Override + public ShardOfTheNightbringerEffect copy() { + return new ShardOfTheNightbringerEffect(this); + } + + @Override + public boolean apply(Game game, Ability source) { + Player opponent = game.getPlayer(getTargetPointer().getFirst(game, source)); + if (opponent == null) { + return false; + } + int lifeLost = opponent.loseLife( + opponent.getLife() / 2 + opponent.getLife() % 2, game, source, false + ); + if (lifeLost < 1) { + return false; + } + Player controller = game.getPlayer(source.getControllerId()); + return controller == null || controller.gainLife(lifeLost, game, source) > 0; + } +} diff --git a/Mage.Sets/src/mage/sets/Warhammer40000.java b/Mage.Sets/src/mage/sets/Warhammer40000.java index 2655364883..559d4c7d19 100644 --- a/Mage.Sets/src/mage/sets/Warhammer40000.java +++ b/Mage.Sets/src/mage/sets/Warhammer40000.java @@ -200,6 +200,7 @@ public final class Warhammer40000 extends ExpansionSet { cards.add(new SetCardInfo("Scoured Barrens", 293, Rarity.COMMON, mage.cards.s.ScouredBarrens.class)); cards.add(new SetCardInfo("Screamer-Killer", 84, Rarity.RARE, mage.cards.s.ScreamerKiller.class)); cards.add(new SetCardInfo("Sculpting Steel", 247, Rarity.RARE, mage.cards.s.SculptingSteel.class)); + cards.add(new SetCardInfo("Shard of the Nightbringer", 55, Rarity.RARE, mage.cards.s.ShardOfTheNightbringer.class)); cards.add(new SetCardInfo("Sicarian Infiltrator", 25, Rarity.UNCOMMON, mage.cards.s.SicarianInfiltrator.class)); cards.add(new SetCardInfo("Sister Hospitaller", 141, Rarity.RARE, mage.cards.s.SisterHospitaller.class)); cards.add(new SetCardInfo("Sister Repentia", 142, Rarity.RARE, mage.cards.s.SisterRepentia.class)); diff --git a/Mage.Verify/src/test/java/mage/verify/VerifyCardDataTest.java b/Mage.Verify/src/test/java/mage/verify/VerifyCardDataTest.java index 68d5787336..3ec9bda980 100644 --- a/Mage.Verify/src/test/java/mage/verify/VerifyCardDataTest.java +++ b/Mage.Verify/src/test/java/mage/verify/VerifyCardDataTest.java @@ -1321,15 +1321,16 @@ public class VerifyCardDataTest { return; } - Collection expected = ref.subtypes; + List expected = new ArrayList<>(ref.subtypes); // fix names (e.g. Urza’s to Urza's) - if (expected != null && expected.contains("Urza’s")) { - expected = new ArrayList<>(expected); - for (ListIterator it = ((List) expected).listIterator(); it.hasNext(); ) { - if (it.next().equals("Urza’s")) { + for (ListIterator it = expected.listIterator(); it.hasNext(); ) { + switch (it.next()) { + case "Urza’s": it.set("Urza's"); - } + break; + case "C’tan": + it.set("C'tan"); } } @@ -1339,11 +1340,9 @@ public class VerifyCardDataTest { .stream() .map(SubType::toString) .collect(Collectors.toSet()); - actual.removeIf(subtypesToIgnore::contains); - if (expected != null) { - expected.removeIf(subtypesToIgnore::contains); - } + actual.removeIf(subtypesToIgnore::contains); + expected.removeIf(subtypesToIgnore::contains); for (SubType subType : card.getSubtype()) { if (!subType.isCustomSet() && !subType.canGain(card)) { diff --git a/Mage/src/main/java/mage/constants/SubType.java b/Mage/src/main/java/mage/constants/SubType.java index 0f6f93b69e..8f715a4f9a 100644 --- a/Mage/src/main/java/mage/constants/SubType.java +++ b/Mage/src/main/java/mage/constants/SubType.java @@ -116,6 +116,7 @@ public enum SubType { CRAB("Crab", SubTypeSet.CreatureType), CROCODILE("Crocodile", SubTypeSet.CreatureType), CROLUTE("Crolute", SubTypeSet.CreatureType, true), // Star Wars + CTAN("C'tan", SubTypeSet.CreatureType), CUSTODES("Custodes", SubTypeSet.CreatureType), CYBORG("Cyborg", SubTypeSet.CreatureType, true), // Star Wars CYCLOPS("Cyclops", SubTypeSet.CreatureType),