mirror of
https://github.com/magefree/mage.git
synced 2025-12-20 02:30:08 -08:00
Merge branch 'master' into refactor/multiple-names
This commit is contained in:
commit
6208adde58
102 changed files with 2106 additions and 758 deletions
|
|
@ -4,8 +4,12 @@ import mage.MageObject;
|
|||
import mage.cards.Card;
|
||||
import mage.cards.decks.Deck;
|
||||
import mage.client.util.GUISizeHelper;
|
||||
import org.apache.log4j.Logger;
|
||||
|
||||
import java.awt.*;
|
||||
import java.io.BufferedReader;
|
||||
import java.io.InputStream;
|
||||
import java.io.InputStreamReader;
|
||||
import java.util.List;
|
||||
import java.util.*;
|
||||
import java.util.stream.Stream;
|
||||
|
|
@ -16,21 +20,31 @@ import java.util.stream.Stream;
|
|||
* <p>
|
||||
* Support:
|
||||
* - [x] game changers
|
||||
* - [ ] infinite combos
|
||||
* - [x] infinite combos
|
||||
* - [x] mass land destruction
|
||||
* - [x] extra turns
|
||||
* - [x] tutors
|
||||
* Features:
|
||||
* - [x] find possible bracket level of the deck
|
||||
* - [x] find affected cards by checking group
|
||||
* - [ ] TODO: data download and generate
|
||||
* - [ ] TODO: tests
|
||||
* - [ ] TODO: table - players brackets level disclose settings
|
||||
*
|
||||
* @author JayDi85
|
||||
*/
|
||||
public class BracketLegalityLabel extends LegalityLabel {
|
||||
|
||||
private static final Logger logger = Logger.getLogger(BracketLegalityLabel.class);
|
||||
|
||||
private static final String GROUP_GAME_CHANGES = "Game Changers";
|
||||
private static final String GROUP_INFINITE_COMBOS = "Infinite Combos (unsupported)";
|
||||
private static final String GROUP_INFINITE_COMBOS = "Infinite Combos";
|
||||
private static final String GROUP_MASS_LAND_DESTRUCTION = "Mass Land Destruction";
|
||||
private static final String GROUP_EXTRA_TURN = "Extra Turns";
|
||||
private static final String GROUP_TUTORS = "Tutors";
|
||||
|
||||
private static final String RESOURCE_INFINITE_COMBOS = "brackets/infinite-combos.txt";
|
||||
|
||||
private final BracketLevel level;
|
||||
|
||||
private final List<String> foundGameChangers = new ArrayList<>();
|
||||
|
|
@ -41,6 +55,7 @@ public class BracketLegalityLabel extends LegalityLabel {
|
|||
|
||||
private final List<String> badCards = new ArrayList<>();
|
||||
private final List<String> fullGameChanges = new ArrayList<>();
|
||||
private final Set<String> fullInfiniteCombos = new HashSet<>(); // card1@card2, sorted by names, name must be xmage compatible
|
||||
|
||||
public enum BracketLevel {
|
||||
BRACKET_1("Bracket 1"),
|
||||
|
|
@ -243,8 +258,64 @@ public class BracketLegalityLabel extends LegalityLabel {
|
|||
}
|
||||
|
||||
private void collectInfiniteCombos(Deck deck) {
|
||||
// TODO: implement
|
||||
this.foundInfiniteCombos.clear();
|
||||
|
||||
if (this.fullInfiniteCombos.isEmpty()) {
|
||||
InputStream in = BracketLegalityLabel.class.getClassLoader().getResourceAsStream(RESOURCE_INFINITE_COMBOS);
|
||||
if (in == null) {
|
||||
throw new RuntimeException("Commander brackets: can't load infinite combos list");
|
||||
}
|
||||
try (InputStreamReader input = new InputStreamReader(in);
|
||||
BufferedReader reader = new BufferedReader(input)) {
|
||||
String line = reader.readLine();
|
||||
while (line != null) {
|
||||
try {
|
||||
line = line.trim();
|
||||
if (line.startsWith("#")) {
|
||||
continue;
|
||||
}
|
||||
List<String> cards = Arrays.asList(line.split("@"));
|
||||
if (cards.size() != 2) {
|
||||
logger.warn("wrong line format in commander brackets file: " + line);
|
||||
continue;
|
||||
}
|
||||
|
||||
Collections.sort(cards);
|
||||
this.fullInfiniteCombos.add(String.join("@", cards));
|
||||
} finally {
|
||||
line = reader.readLine();
|
||||
}
|
||||
}
|
||||
} catch (Exception e) {
|
||||
throw new RuntimeException("Tokens brackets: can't load infinite combos list - " + e);
|
||||
}
|
||||
}
|
||||
|
||||
// search and check all x2 combinations
|
||||
List<Card> deckCards = new ArrayList<>();
|
||||
Set<Card> foundCards = new HashSet<>();
|
||||
deckCards.addAll(deck.getCards());
|
||||
deckCards.addAll(deck.getSideboard());
|
||||
for (Card card1 : deckCards) {
|
||||
for (Card card2 : deckCards) {
|
||||
if (card1 == card2) {
|
||||
continue;
|
||||
}
|
||||
List<String> names = Arrays.asList(card1.getName(), card2.getName());
|
||||
Collections.sort(names);
|
||||
String deckCombo = String.join("@", names);
|
||||
if (this.fullInfiniteCombos.contains(deckCombo)) {
|
||||
foundCards.add(card1);
|
||||
foundCards.add(card2);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
foundCards.stream()
|
||||
.map(MageObject::getName)
|
||||
.sorted()
|
||||
.forEach(this.foundInfiniteCombos::add);
|
||||
}
|
||||
|
||||
private void collectMassLandDestruction(Deck deck) {
|
||||
|
|
|
|||
|
|
@ -12,7 +12,7 @@ import mage.constants.CardType;
|
|||
import mage.constants.SubType;
|
||||
import mage.filter.common.FilterArtifactOrEnchantmentPermanent;
|
||||
import mage.target.TargetPermanent;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -42,7 +42,7 @@ public final class Aberrant extends CardImpl {
|
|||
Ability ability = new DealsCombatDamageToAPlayerTriggeredAbility(new DestroyTargetEffect(), false, true);
|
||||
ability.withFlavorWord("Heavy Power Hammer");
|
||||
ability.addTarget(new TargetPermanent(filter));
|
||||
ability.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster());
|
||||
ability.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster());
|
||||
this.addAbility(ability);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -1,36 +1,35 @@
|
|||
|
||||
package mage.cards.a;
|
||||
|
||||
import java.util.UUID;
|
||||
import mage.MageInt;
|
||||
import mage.abilities.triggers.BeginningOfUpkeepTriggeredAbility;
|
||||
import mage.abilities.condition.common.ControlsCreatureGreatestToughnessCondition;
|
||||
import mage.abilities.decorator.ConditionalInterveningIfTriggeredAbility;
|
||||
import mage.abilities.decorator.ConditionalOneShotEffect;
|
||||
import mage.abilities.effects.common.DrawCardSourceControllerEffect;
|
||||
import mage.abilities.triggers.BeginningOfUpkeepTriggeredAbility;
|
||||
import mage.cards.CardImpl;
|
||||
import mage.cards.CardSetInfo;
|
||||
import mage.constants.CardType;
|
||||
import mage.constants.SubType;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
/**
|
||||
*
|
||||
* @author LevelX2
|
||||
*/
|
||||
public final class AbzanBeastmaster extends CardImpl {
|
||||
|
||||
public AbzanBeastmaster(UUID ownerId, CardSetInfo setInfo) {
|
||||
super(ownerId,setInfo,new CardType[]{CardType.CREATURE},"{2}{G}");
|
||||
super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{2}{G}");
|
||||
this.subtype.add(SubType.DOG);
|
||||
this.subtype.add(SubType.SHAMAN);
|
||||
this.power = new MageInt(2);
|
||||
this.toughness = new MageInt(1);
|
||||
|
||||
// At the beginning of your upkeep, draw a card if you control the creature with the greatest toughness or tied for the greatest toughness.
|
||||
this.addAbility(new ConditionalInterveningIfTriggeredAbility(
|
||||
new BeginningOfUpkeepTriggeredAbility(new DrawCardSourceControllerEffect(1)),
|
||||
ControlsCreatureGreatestToughnessCondition.instance,
|
||||
"At the beginning of your upkeep, draw a card if you control the creature with the greatest toughness or tied for the greatest toughness."
|
||||
));
|
||||
this.addAbility(new BeginningOfUpkeepTriggeredAbility(new ConditionalOneShotEffect(
|
||||
new DrawCardSourceControllerEffect(1), ControlsCreatureGreatestToughnessCondition.instance,
|
||||
"draw a card if you control the creature with the greatest toughness or tied for the greatest toughness"
|
||||
)));
|
||||
}
|
||||
|
||||
private AbzanBeastmaster(final AbzanBeastmaster card) {
|
||||
|
|
|
|||
|
|
@ -4,7 +4,6 @@ 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.effects.common.LookLibraryAndPickControllerEffect;
|
||||
import mage.cards.CardImpl;
|
||||
import mage.cards.CardSetInfo;
|
||||
|
|
@ -25,7 +24,7 @@ import java.util.UUID;
|
|||
*/
|
||||
public final class AcclaimedContender extends CardImpl {
|
||||
|
||||
private static final FilterPermanent filter = new FilterControlledPermanent(SubType.KNIGHT);
|
||||
private static final FilterPermanent filter = new FilterControlledPermanent(SubType.KNIGHT, "you control another Knight");
|
||||
private static final FilterCard filter2
|
||||
= new FilterCard("a Knight, Aura, Equipment, or legendary artifact card");
|
||||
|
||||
|
|
@ -53,14 +52,9 @@ public final class AcclaimedContender extends CardImpl {
|
|||
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(
|
||||
5, 1, filter2, PutCards.HAND, PutCards.BOTTOM_RANDOM
|
||||
)), condition, "When {this} enters, " +
|
||||
"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 EntersBattlefieldTriggeredAbility(new LookLibraryAndPickControllerEffect(
|
||||
5, 1, filter2, PutCards.HAND, PutCards.BOTTOM_RANDOM
|
||||
)).withInterveningIf(condition));
|
||||
}
|
||||
|
||||
private AcclaimedContender(final AcclaimedContender card) {
|
||||
|
|
|
|||
|
|
@ -6,7 +6,6 @@ import mage.abilities.common.AttacksTriggeredAbility;
|
|||
import mage.abilities.common.EntersBattlefieldTriggeredAbility;
|
||||
import mage.abilities.condition.Condition;
|
||||
import mage.abilities.condition.common.CompletedDungeonCondition;
|
||||
import mage.abilities.decorator.ConditionalInterveningIfTriggeredAbility;
|
||||
import mage.abilities.effects.OneShotEffect;
|
||||
import mage.abilities.effects.common.ReturnToHandSourceEffect;
|
||||
import mage.abilities.effects.keyword.VentureIntoTheDungeonEffect;
|
||||
|
|
@ -22,8 +21,6 @@ import mage.game.Game;
|
|||
import mage.game.permanent.Permanent;
|
||||
import mage.game.permanent.token.ZombieToken;
|
||||
import mage.players.Player;
|
||||
import mage.target.TargetPermanent;
|
||||
import mage.target.common.TargetControlledCreaturePermanent;
|
||||
import mage.target.common.TargetSacrifice;
|
||||
import mage.watchers.common.CompletedDungeonWatcher;
|
||||
|
||||
|
|
@ -44,13 +41,9 @@ public final class AcererakTheArchlich extends CardImpl {
|
|||
this.toughness = new MageInt(5);
|
||||
|
||||
// When Acererak the Archlich enters the battlefield, if you have not completed Tomb of Annihilation, return Acererak the Archlich to its owner's hand and venture into the dungeon.
|
||||
Ability ability = new ConditionalInterveningIfTriggeredAbility(
|
||||
new EntersBattlefieldTriggeredAbility(new ReturnToHandSourceEffect(true)),
|
||||
AcererakTheArchlichCondition.instance, "When {this} enters, " +
|
||||
"if you haven't completed Tomb of Annihilation, return {this} " +
|
||||
"to its owner's hand and venture into the dungeon."
|
||||
);
|
||||
ability.addEffect(new VentureIntoTheDungeonEffect());
|
||||
Ability ability = new EntersBattlefieldTriggeredAbility(new ReturnToHandSourceEffect(true))
|
||||
.withInterveningIf(AcererakTheArchlichCondition.instance);
|
||||
ability.addEffect(new VentureIntoTheDungeonEffect().concatBy("and"));
|
||||
ability.addHint(CurrentDungeonHint.instance);
|
||||
ability.addHint(CompletedDungeonCondition.getHint());
|
||||
this.addAbility(ability, new CompletedDungeonWatcher());
|
||||
|
|
@ -78,6 +71,11 @@ enum AcererakTheArchlichCondition implements Condition {
|
|||
source.getControllerId(), game
|
||||
).contains("Tomb of Annihilation");
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "you haven't completed Tomb of Annihilation";
|
||||
}
|
||||
}
|
||||
|
||||
class AcererakTheArchlichEffect extends OneShotEffect {
|
||||
|
|
|
|||
|
|
@ -1,45 +1,41 @@
|
|||
package mage.cards.a;
|
||||
|
||||
import mage.MageInt;
|
||||
import mage.abilities.triggers.BeginningOfCombatTriggeredAbility;
|
||||
import mage.abilities.condition.Condition;
|
||||
import mage.abilities.condition.common.PermanentsOnTheBattlefieldCondition;
|
||||
import mage.abilities.decorator.ConditionalInterveningIfTriggeredAbility;
|
||||
import mage.abilities.effects.common.counter.AddCountersSourceEffect;
|
||||
import mage.abilities.hint.ConditionHint;
|
||||
import mage.abilities.hint.Hint;
|
||||
import mage.abilities.triggers.BeginningOfCombatTriggeredAbility;
|
||||
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.common.FilterControlledPlaneswalkerPermanent;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
/**
|
||||
*
|
||||
* @author htrajan
|
||||
*/
|
||||
public final class AdherentOfHope extends CardImpl {
|
||||
|
||||
private static final FilterControlledPermanent filter = new FilterControlledPermanent();
|
||||
|
||||
static {
|
||||
filter.add(CardType.PLANESWALKER.getPredicate());
|
||||
filter.add(SubType.BASRI.getPredicate());
|
||||
}
|
||||
private static final Condition condition = new PermanentsOnTheBattlefieldCondition(
|
||||
new FilterControlledPlaneswalkerPermanent(SubType.BASRI, "you control a Basri planeswalker")
|
||||
);
|
||||
private static final Hint hint = new ConditionHint(condition);
|
||||
|
||||
public AdherentOfHope(UUID ownerId, CardSetInfo setInfo) {
|
||||
super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{1}{W}");
|
||||
|
||||
|
||||
this.subtype.add(SubType.HUMAN);
|
||||
this.subtype.add(SubType.SOLDIER);
|
||||
this.power = new MageInt(2);
|
||||
this.toughness = new MageInt(1);
|
||||
|
||||
// At the beginning of combat on your turn, if you control a Basri planeswalker, put a +1/+1 counter on Adherent of Hope.
|
||||
this.addAbility(new ConditionalInterveningIfTriggeredAbility(
|
||||
new BeginningOfCombatTriggeredAbility(new AddCountersSourceEffect(CounterType.P1P1.createInstance())),
|
||||
new PermanentsOnTheBattlefieldCondition(filter),
|
||||
"At the beginning of combat on your turn, if you control a Basri planeswalker, put a +1/+1 counter on {this}."));
|
||||
this.addAbility(new BeginningOfCombatTriggeredAbility(new AddCountersSourceEffect(CounterType.P1P1.createInstance())).withInterveningIf(condition).addHint(hint));
|
||||
}
|
||||
|
||||
private AdherentOfHope(final AdherentOfHope card) {
|
||||
|
|
|
|||
|
|
@ -1,40 +1,38 @@
|
|||
package mage.cards.a;
|
||||
|
||||
import java.util.*;
|
||||
|
||||
import mage.MageInt;
|
||||
import mage.MageObjectReference;
|
||||
import mage.abilities.Ability;
|
||||
import mage.abilities.common.AttacksTriggeredAbility;
|
||||
import mage.abilities.condition.Condition;
|
||||
import mage.abilities.decorator.ConditionalInterveningIfTriggeredAbility;
|
||||
import mage.abilities.effects.ContinuousEffectImpl;
|
||||
import mage.abilities.effects.common.DrawCardSourceControllerEffect;
|
||||
import mage.abilities.effects.common.continuous.AddCardSubTypeSourceEffect;
|
||||
import mage.abilities.hint.ConditionHint;
|
||||
import mage.abilities.hint.Hint;
|
||||
import mage.constants.*;
|
||||
import mage.abilities.keyword.IslandwalkAbility;
|
||||
import mage.abilities.keyword.CrewAbility;
|
||||
import mage.abilities.keyword.IslandwalkAbility;
|
||||
import mage.cards.CardImpl;
|
||||
import mage.cards.CardSetInfo;
|
||||
import mage.constants.*;
|
||||
import mage.filter.common.FilterCreaturePermanent;
|
||||
import mage.game.Game;
|
||||
import mage.game.events.GameEvent;
|
||||
import mage.game.permanent.Permanent;
|
||||
import mage.watchers.Watcher;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
import java.util.UUID;
|
||||
|
||||
/**
|
||||
*
|
||||
* @author Grath
|
||||
*/
|
||||
public final class Adrestia extends CardImpl {
|
||||
|
||||
private static final Condition condition = AdrestiaCondition.instance;
|
||||
|
||||
public Adrestia(UUID ownerId, CardSetInfo setInfo) {
|
||||
super(ownerId, setInfo, new CardType[]{CardType.ARTIFACT}, "{3}");
|
||||
|
||||
|
||||
this.supertype.add(SuperType.LEGENDARY);
|
||||
this.subtype.add(SubType.VEHICLE);
|
||||
this.power = new MageInt(4);
|
||||
|
|
@ -44,16 +42,14 @@ public final class Adrestia extends CardImpl {
|
|||
this.addAbility(new IslandwalkAbility());
|
||||
|
||||
// Whenever Adrestia attacks, if an Assassin crewed it this turn, draw a card. Adrestia becomes an Assassin in addition to its other types until end of turn.
|
||||
Ability ability = new ConditionalInterveningIfTriggeredAbility(
|
||||
new AttacksTriggeredAbility(new DrawCardSourceControllerEffect(1), false),
|
||||
condition, "Whenever {this} attacks, if an Assassin crewed it this turn, draw a card. {this} becomes an Assassin in addition to its other types until end of turn.");
|
||||
Ability ability = new AttacksTriggeredAbility(new DrawCardSourceControllerEffect(1), false)
|
||||
.withInterveningIf(AdrestiaCondition.instance);
|
||||
ability.addEffect(new AddCardSubTypeSourceEffect(Duration.EndOfTurn, true, SubType.ASSASSIN));
|
||||
ability.addHint(AdrestiaCondition.getHint());
|
||||
this.addAbility(ability, new AdrestiaWatcher());
|
||||
|
||||
// Crew 1
|
||||
this.addAbility(new CrewAbility(1));
|
||||
|
||||
}
|
||||
|
||||
private Adrestia(final Adrestia card) {
|
||||
|
|
@ -68,13 +64,18 @@ public final class Adrestia extends CardImpl {
|
|||
|
||||
enum AdrestiaCondition implements Condition {
|
||||
instance;
|
||||
private static final Hint hint = new ConditionHint(instance, "an Assassin crewed it this turn");
|
||||
private static final Hint hint = new ConditionHint(instance);
|
||||
|
||||
@Override
|
||||
public boolean apply(Game game, Ability source) {
|
||||
return AdrestiaWatcher.checkIfAssassinCrewed(source.getSourcePermanentOrLKI(game), game);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "an Assassin crewed it this turn";
|
||||
}
|
||||
|
||||
public static Hint getHint() {
|
||||
return hint;
|
||||
}
|
||||
|
|
@ -97,8 +98,7 @@ class AdrestiaWatcher extends Watcher {
|
|||
if (crewer != null) {
|
||||
if (!crewMap.containsKey(vehicle)) {
|
||||
crewMap.put(vehicle, filter.match(crewer, game));
|
||||
}
|
||||
else {
|
||||
} else {
|
||||
crewMap.put(vehicle, crewMap.get(vehicle) || filter.match(crewer, game));
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -4,7 +4,6 @@ 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.search.SearchLibraryPutInPlayEffect;
|
||||
import mage.abilities.hint.Hint;
|
||||
import mage.abilities.hint.common.LandsYouControlHint;
|
||||
|
|
@ -46,13 +45,10 @@ public final class AerialSurveyor extends CardImpl {
|
|||
this.addAbility(FlyingAbility.getInstance());
|
||||
|
||||
// Whenever Aerial Surveyor attacks, if defending player controls more lands than you, search your library for a basic Plains card, put it onto the battlefield tapped, then shuffle.
|
||||
this.addAbility(new ConditionalInterveningIfTriggeredAbility(
|
||||
new AttacksTriggeredAbility(
|
||||
new SearchLibraryPutInPlayEffect(new TargetCardInLibrary(filter), true)
|
||||
), AerialSurveyorCondition.instance, "Whenever {this} attacks, if defending player " +
|
||||
"controls more lands than you, search your library for a basic Plains card, " +
|
||||
"put it onto the battlefield tapped, then shuffle."
|
||||
).addHint(LandsYouControlHint.instance).addHint(AerialSurveyorHint.instance));
|
||||
this.addAbility(new AttacksTriggeredAbility(new SearchLibraryPutInPlayEffect(new TargetCardInLibrary(filter), true))
|
||||
.withInterveningIf(AerialSurveyorCondition.instance)
|
||||
.addHint(LandsYouControlHint.instance)
|
||||
.addHint(AerialSurveyorHint.instance));
|
||||
|
||||
// Crew 2
|
||||
this.addAbility(new CrewAbility(2));
|
||||
|
|
@ -85,6 +81,11 @@ enum AerialSurveyorCondition implements Condition {
|
|||
source.getControllerId(), source, game
|
||||
);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "";
|
||||
}
|
||||
}
|
||||
|
||||
enum AerialSurveyorHint implements Hint {
|
||||
|
|
|
|||
|
|
@ -14,7 +14,7 @@ import mage.constants.*;
|
|||
import mage.filter.common.FilterCreaturePermanent;
|
||||
import mage.game.permanent.token.FaerieRogueToken;
|
||||
import mage.target.TargetPermanent;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -48,7 +48,7 @@ public final class AlelaCunningConqueror extends CardImpl {
|
|||
Effect effect = new GoadTargetEffect().setText("goad target creature that player controls");
|
||||
Ability ability = new OneOrMoreCombatDamagePlayerTriggeredAbility(Zone.BATTLEFIELD, effect, faerieFilter, SetTargetPointer.PLAYER, false);
|
||||
ability.addTarget(new TargetPermanent(filter));
|
||||
ability.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster());
|
||||
ability.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster());
|
||||
|
||||
this.addAbility(ability);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -12,7 +12,7 @@ import mage.constants.CardType;
|
|||
import mage.constants.Duration;
|
||||
import mage.filter.common.FilterCreaturePermanent;
|
||||
import mage.target.TargetPermanent;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -30,7 +30,7 @@ public final class ArmWithAether extends CardImpl {
|
|||
// Until end of turn, creatures you control gain "Whenever this creature deals damage to an opponent, you may return target creature that player controls to its owner's hand."
|
||||
Ability ability = new DealsCombatDamageToAPlayerTriggeredAbility(new ReturnToHandTargetEffect(), false, true);
|
||||
ability.addTarget(new TargetPermanent(filter));
|
||||
ability.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster());
|
||||
ability.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster());
|
||||
|
||||
Effect effect = new GainAbilityControlledEffect(ability, Duration.EndOfTurn, new FilterCreaturePermanent());
|
||||
effect.setText("Until end of turn, creatures you control gain \"Whenever this creature deals damage to an opponent, you may return target creature that player controls to its owner's hand.\"");
|
||||
|
|
|
|||
|
|
@ -11,7 +11,7 @@ import mage.constants.CardType;
|
|||
import mage.constants.SubType;
|
||||
import mage.constants.SuperType;
|
||||
import mage.target.common.TargetCreaturePermanent;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -32,7 +32,7 @@ public final class AshlingTheExtinguisher extends CardImpl {
|
|||
Effect effect = new SacrificeTargetEffect().setText("choose target creature that player controls. The player sacrifices that creature");
|
||||
Ability ability = new DealsCombatDamageToAPlayerTriggeredAbility(effect, false, true);
|
||||
ability.addTarget(new TargetCreaturePermanent());
|
||||
ability.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster());
|
||||
ability.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster());
|
||||
this.addAbility(ability);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -20,6 +20,7 @@ import mage.game.Game;
|
|||
import mage.game.permanent.Permanent;
|
||||
import mage.players.Player;
|
||||
import mage.target.TargetPermanent;
|
||||
import mage.util.CardUtil;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -67,14 +68,11 @@ enum BladeOfSharedSoulsPredicate implements ObjectSourcePlayerPredicate<Permanen
|
|||
|
||||
@Override
|
||||
public boolean apply(ObjectSourcePlayer<Permanent> input, Game game) {
|
||||
return input.getSource()
|
||||
.getEffects()
|
||||
.stream()
|
||||
.map(effect -> effect.getValue("attachedPermanent"))
|
||||
.filter(Permanent.class::isInstance)
|
||||
.map(Permanent.class::cast)
|
||||
.noneMatch(permanent -> input.getObject().getId().equals(permanent.getId())
|
||||
&& input.getObject().getZoneChangeCounter(game) == permanent.getZoneChangeCounter(game));
|
||||
return !CardUtil
|
||||
.getEffectValueFromAbility(input.getSource(), "attachedPermanent", Permanent.class)
|
||||
.filter(permanent -> input.getObject().getId().equals(permanent.getId())
|
||||
&& input.getObject().getZoneChangeCounter(game) == permanent.getZoneChangeCounter(game))
|
||||
.isPresent();
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -141,4 +139,4 @@ class BladeOfSharedSoulsCopyEffect extends CopyEffect {
|
|||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -14,7 +14,7 @@ import mage.constants.CardType;
|
|||
import mage.constants.SubType;
|
||||
import mage.filter.common.FilterCreaturePermanent;
|
||||
import mage.target.TargetPermanent;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -39,7 +39,7 @@ public final class BlindZealot extends CardImpl {
|
|||
OneShotEffect effect = new DoIfCostPaid(new DestroyTargetEffect(), new SacrificeSourceCost());
|
||||
Ability ability = new DealsCombatDamageToAPlayerTriggeredAbility(effect, false, true);
|
||||
ability.addTarget(new TargetPermanent(filter));
|
||||
ability.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster());
|
||||
ability.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster());
|
||||
this.addAbility(ability);
|
||||
}
|
||||
|
||||
|
|
|
|||
142
Mage.Sets/src/mage/cards/b/BorosStrikeCaptain.java
Normal file
142
Mage.Sets/src/mage/cards/b/BorosStrikeCaptain.java
Normal file
|
|
@ -0,0 +1,142 @@
|
|||
package mage.cards.b;
|
||||
|
||||
import mage.MageInt;
|
||||
import mage.MageObjectReference;
|
||||
import mage.abilities.Ability;
|
||||
import mage.abilities.condition.Condition;
|
||||
import mage.abilities.effects.OneShotEffect;
|
||||
import mage.abilities.hint.ConditionHint;
|
||||
import mage.abilities.hint.Hint;
|
||||
import mage.abilities.keyword.BattalionAbility;
|
||||
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.players.Player;
|
||||
import mage.util.CardUtil;
|
||||
import mage.watchers.Watcher;
|
||||
|
||||
import java.util.*;
|
||||
|
||||
/**
|
||||
* @author TheElk801
|
||||
*/
|
||||
public final class BorosStrikeCaptain extends CardImpl {
|
||||
|
||||
public BorosStrikeCaptain(UUID ownerId, CardSetInfo setInfo) {
|
||||
super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{1}{R/W}{R/W}");
|
||||
|
||||
this.subtype.add(SubType.MINOTAUR);
|
||||
this.subtype.add(SubType.SOLDIER);
|
||||
this.power = new MageInt(3);
|
||||
this.toughness = new MageInt(3);
|
||||
|
||||
// Battalion -- Whenever Boros Strike-Captain and at least two other creatures attack, exile the top card of your library. During any turn you attacked with three or more creatures, you may play that card.
|
||||
this.addAbility(new BattalionAbility(new BorosStrikeCaptainEffect())
|
||||
.addHint(BorosStrikeCaptainCondition.getHint()), new BorosStrikeCaptainWatcher());
|
||||
}
|
||||
|
||||
private BorosStrikeCaptain(final BorosStrikeCaptain card) {
|
||||
super(card);
|
||||
}
|
||||
|
||||
@Override
|
||||
public BorosStrikeCaptain copy() {
|
||||
return new BorosStrikeCaptain(this);
|
||||
}
|
||||
}
|
||||
|
||||
class BorosStrikeCaptainEffect extends OneShotEffect {
|
||||
|
||||
BorosStrikeCaptainEffect() {
|
||||
super(Outcome.Benefit);
|
||||
staticText = "exile the top card of your library. During any turn you attacked " +
|
||||
"with three or more creatures, you may play that card";
|
||||
}
|
||||
|
||||
private BorosStrikeCaptainEffect(final BorosStrikeCaptainEffect effect) {
|
||||
super(effect);
|
||||
}
|
||||
|
||||
@Override
|
||||
public BorosStrikeCaptainEffect copy() {
|
||||
return new BorosStrikeCaptainEffect(this);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean apply(Game game, Ability source) {
|
||||
Player player = game.getPlayer(source.getControllerId());
|
||||
if (player == null) {
|
||||
return false;
|
||||
}
|
||||
Card card = player.getLibrary().getFromTop(game);
|
||||
if (card == null) {
|
||||
return false;
|
||||
}
|
||||
player.moveCards(card, Zone.EXILED, source, game);
|
||||
CardUtil.makeCardPlayable(
|
||||
game, source, card, false, Duration.Custom, false,
|
||||
player.getId(), BorosStrikeCaptainCondition.instance
|
||||
);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
enum BorosStrikeCaptainCondition implements Condition {
|
||||
instance;
|
||||
private static final Hint hint = new ConditionHint(instance);
|
||||
|
||||
public static Hint getHint() {
|
||||
return hint;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean apply(Game game, Ability source) {
|
||||
return BorosStrikeCaptainWatcher.checkPlayer(game, source);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "you attacked with three or more creatures this turn";
|
||||
}
|
||||
}
|
||||
|
||||
class BorosStrikeCaptainWatcher extends Watcher {
|
||||
|
||||
private final Map<UUID, Set<MageObjectReference>> map = new HashMap<>();
|
||||
|
||||
BorosStrikeCaptainWatcher() {
|
||||
super(WatcherScope.GAME);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void watch(GameEvent event, Game game) {
|
||||
if (event.getType() != GameEvent.EventType.ATTACKER_DECLARED) {
|
||||
return;
|
||||
}
|
||||
Optional.ofNullable(event)
|
||||
.map(GameEvent::getTargetId)
|
||||
.map(game::getPermanent)
|
||||
.ifPresent(permanent -> map
|
||||
.computeIfAbsent(permanent.getControllerId(), x -> new HashSet<>())
|
||||
.add(new MageObjectReference(permanent, game)));
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
public void reset() {
|
||||
super.reset();
|
||||
map.clear();
|
||||
}
|
||||
|
||||
static boolean checkPlayer(Game game, Ability source) {
|
||||
return game
|
||||
.getState()
|
||||
.getWatcher(BorosStrikeCaptainWatcher.class)
|
||||
.map
|
||||
.getOrDefault(source.getControllerId(), Collections.emptySet())
|
||||
.size() >= 3;
|
||||
}
|
||||
}
|
||||
|
|
@ -14,7 +14,6 @@ import mage.cards.CardSetInfo;
|
|||
import mage.constants.*;
|
||||
import mage.filter.FilterPermanent;
|
||||
import mage.filter.StaticFilters;
|
||||
import mage.filter.common.FilterControlledCreaturePermanent;
|
||||
import mage.filter.common.FilterCreaturePermanent;
|
||||
import mage.filter.predicate.ObjectSourcePlayer;
|
||||
import mage.filter.predicate.ObjectSourcePlayerPredicate;
|
||||
|
|
@ -23,10 +22,10 @@ import mage.game.events.GameEvent;
|
|||
import mage.game.permanent.Permanent;
|
||||
import mage.game.permanent.token.TreasureToken;
|
||||
import mage.target.TargetPermanent;
|
||||
import mage.util.CardUtil;
|
||||
import mage.watchers.Watcher;
|
||||
|
||||
import java.util.HashSet;
|
||||
import java.util.Objects;
|
||||
import java.util.Set;
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -75,19 +74,11 @@ enum BoxingRingPredicate implements ObjectSourcePlayerPredicate<Permanent> {
|
|||
|
||||
@Override
|
||||
public boolean apply(ObjectSourcePlayer<Permanent> input, Game game) {
|
||||
return input
|
||||
.getObject()
|
||||
.getManaValue()
|
||||
== input
|
||||
.getSource()
|
||||
.getEffects()
|
||||
.stream()
|
||||
.map(effect -> effect.getValue("permanentEnteringBattlefield"))
|
||||
.map(Permanent.class::cast)
|
||||
.filter(Objects::nonNull)
|
||||
return CardUtil
|
||||
.getEffectValueFromAbility(input.getSource(), "permanentEnteringBattlefield", Permanent.class)
|
||||
.map(MageObject::getManaValue)
|
||||
.findFirst()
|
||||
.orElse(-1);
|
||||
.filter(x -> x == input.getObject().getManaValue())
|
||||
.isPresent();
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -12,7 +12,7 @@ import mage.constants.CardType;
|
|||
import mage.constants.SubType;
|
||||
import mage.filter.common.FilterArtifactPermanent;
|
||||
import mage.target.TargetPermanent;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -37,7 +37,7 @@ public final class CausticWasps extends CardImpl {
|
|||
// Whenever Caustic Wasps deals combat damage to a player, you may destroy target artifact that player controls.
|
||||
Ability ability = new DealsCombatDamageToAPlayerTriggeredAbility(new DestroyTargetEffect(), true, true);
|
||||
ability.addTarget(new TargetPermanent(filter));
|
||||
ability.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster());
|
||||
ability.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster());
|
||||
this.addAbility(ability);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -15,30 +15,38 @@ import mage.abilities.mana.builder.ConditionalManaBuilder;
|
|||
import mage.abilities.mana.conditional.CreatureCastManaCondition;
|
||||
import mage.cards.CardImpl;
|
||||
import mage.cards.CardSetInfo;
|
||||
import mage.constants.*;
|
||||
import mage.constants.CardType;
|
||||
import mage.constants.Duration;
|
||||
import mage.constants.SubType;
|
||||
import mage.constants.SuperType;
|
||||
import mage.filter.Filter;
|
||||
import mage.filter.FilterPermanent;
|
||||
import mage.filter.StaticFilters;
|
||||
import mage.filter.common.FilterControlledCreaturePermanent;
|
||||
import mage.filter.predicate.mageobject.ManaValuePredicate;
|
||||
import mage.filter.predicate.ObjectSourcePlayer;
|
||||
import mage.filter.predicate.ObjectSourcePlayerPredicate;
|
||||
import mage.game.Game;
|
||||
import mage.game.events.GameEvent;
|
||||
import mage.game.permanent.Permanent;
|
||||
import mage.target.TargetPermanent;
|
||||
import mage.util.CardUtil;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
/**
|
||||
*
|
||||
* @author earchip94
|
||||
*/
|
||||
public final class ClementTheWorrywort extends CardImpl {
|
||||
|
||||
private static final FilterPermanent filter = new FilterControlledCreaturePermanent("creature you control with lesser mana value");
|
||||
private static final FilterPermanent frogFilter = new FilterPermanent(SubType.FROG, "Frogs");
|
||||
|
||||
static {
|
||||
filter.add(ClementTheWorrywortPredicate.instance);
|
||||
}
|
||||
|
||||
public ClementTheWorrywort(UUID ownerId, CardSetInfo setInfo) {
|
||||
super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{1}{G}{U}");
|
||||
|
||||
|
||||
this.supertype.add(SuperType.LEGENDARY);
|
||||
this.subtype.add(SubType.FROG);
|
||||
this.subtype.add(SubType.DRUID);
|
||||
|
|
@ -49,12 +57,16 @@ public final class ClementTheWorrywort extends CardImpl {
|
|||
this.addAbility(VigilanceAbility.getInstance());
|
||||
|
||||
// Whenever Clement, the Worrywort or another creature you control enters, return up to one target creature you control with lesser mana value to its owner's hand.
|
||||
this.addAbility(new ClementTheWorrywortTriggeredAbility());
|
||||
Ability ability = new EntersBattlefieldThisOrAnotherTriggeredAbility(
|
||||
new ReturnToHandTargetEffect(), StaticFilters.FILTER_CONTROLLED_CREATURE, false, false
|
||||
);
|
||||
ability.addTarget(new TargetPermanent(0, 1, filter));
|
||||
this.addAbility(ability);
|
||||
|
||||
// Frogs you control have "{T}: Add {G} or {U}. Spend this mana only to cast a creature spell."
|
||||
Ability gMana = new ConditionalColoredManaAbility(new TapSourceCost(), Mana.GreenMana(1), new ClementTheWorrywortManaBuilder());
|
||||
Ability bMana = new ConditionalColoredManaAbility(new TapSourceCost(), Mana.BlueMana(1), new ClementTheWorrywortManaBuilder());
|
||||
Ability ability = new SimpleStaticAbility(
|
||||
ability = new SimpleStaticAbility(
|
||||
new GainAbilityControlledEffect(gMana, Duration.WhileOnBattlefield, frogFilter, false)
|
||||
.setText("Frogs you control have \"{T}: Add {G} or {U}.")
|
||||
);
|
||||
|
|
@ -75,40 +87,17 @@ public final class ClementTheWorrywort extends CardImpl {
|
|||
}
|
||||
}
|
||||
|
||||
class ClementTheWorrywortTriggeredAbility extends EntersBattlefieldThisOrAnotherTriggeredAbility {
|
||||
|
||||
ClementTheWorrywortTriggeredAbility() {
|
||||
super(new ReturnToHandTargetEffect().setText("return up to one target creature you control with lesser mana value to its owner's hand"),
|
||||
StaticFilters.FILTER_PERMANENT_CREATURE, false, true);
|
||||
}
|
||||
|
||||
ClementTheWorrywortTriggeredAbility(final ClementTheWorrywortTriggeredAbility ability) {
|
||||
super(ability);
|
||||
}
|
||||
enum ClementTheWorrywortPredicate implements ObjectSourcePlayerPredicate<Permanent> {
|
||||
instance;
|
||||
|
||||
@Override
|
||||
public ClementTheWorrywortTriggeredAbility copy() {
|
||||
return new ClementTheWorrywortTriggeredAbility(this);
|
||||
public boolean apply(ObjectSourcePlayer<Permanent> input, Game game) {
|
||||
return CardUtil.getEffectValueFromAbility(
|
||||
input.getSource(), "permanentEnteringBattlefield", Permanent.class
|
||||
)
|
||||
.filter(permanent -> input.getObject().getManaValue() < permanent.getManaValue())
|
||||
.isPresent();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean checkTrigger(GameEvent event, Game game) {
|
||||
if (super.checkTrigger(event, game)) {
|
||||
this.getTargets().clear();
|
||||
Permanent permanent = game.getPermanent(event.getTargetId());
|
||||
if (permanent == null) {
|
||||
return false;
|
||||
}
|
||||
int mv = permanent.getManaValue();
|
||||
FilterControlledCreaturePermanent filter =
|
||||
new FilterControlledCreaturePermanent("creature you control with mana value " + (mv - 1) + " or less");
|
||||
filter.add(new ManaValuePredicate(ComparisonType.FEWER_THAN, mv));
|
||||
this.addTarget(new TargetPermanent(0,1, filter));
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
class ClementTheWorrywortConditionalMana extends ConditionalMana {
|
||||
|
|
|
|||
|
|
@ -55,20 +55,21 @@ class ComboAttackEffect extends OneShotEffect {
|
|||
|
||||
@Override
|
||||
public boolean apply(Game game, Ability source) {
|
||||
if (source.getTargets().size() < 2 || source.getTargets().get(0).getTargets().size() < 2) {
|
||||
if (source.getTargets().size() < 2) {
|
||||
return false;
|
||||
}
|
||||
Permanent permanent1 = game.getPermanent(source.getTargets().get(0).getTargets().get(0));
|
||||
Permanent permanent2 = game.getPermanent(source.getTargets().get(0).getTargets().get(1));
|
||||
Permanent permanent3 = game.getPermanent(source.getTargets().get(1).getFirstTarget());
|
||||
if (permanent3 == null) {
|
||||
return false;
|
||||
}
|
||||
if (permanent1 != null) {
|
||||
permanent3.damage(permanent1.getPower().getValue(), permanent1.getId(), source, game, false, true);
|
||||
}
|
||||
if (permanent2 != null) {
|
||||
permanent3.damage(permanent2.getPower().getValue(), permanent2.getId(), source, game, false, true);
|
||||
// You can’t cast Combo Attack without targeting two creatures your team controls.
|
||||
// If one of those creatures is an illegal target as Combo Attack resolves,
|
||||
// the other will still deal damage equal to its power. (2018-06-08)
|
||||
for (UUID id : source.getTargets().get(0).getTargets()) {
|
||||
Permanent permanent = game.getPermanent(id);
|
||||
if (permanent != null) {
|
||||
permanent3.damage(permanent.getPower().getValue(), permanent.getId(), source, game);
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
|
|
|||
120
Mage.Sets/src/mage/cards/c/CommanderLiaraPortyr.java
Normal file
120
Mage.Sets/src/mage/cards/c/CommanderLiaraPortyr.java
Normal file
|
|
@ -0,0 +1,120 @@
|
|||
package mage.cards.c;
|
||||
|
||||
import mage.MageInt;
|
||||
import mage.abilities.Ability;
|
||||
import mage.abilities.common.AttacksWithCreaturesTriggeredAbility;
|
||||
import mage.abilities.effects.OneShotEffect;
|
||||
import mage.abilities.effects.common.cost.CostModificationEffectImpl;
|
||||
import mage.cards.*;
|
||||
import mage.constants.*;
|
||||
import mage.game.Game;
|
||||
import mage.game.stack.Spell;
|
||||
import mage.players.Player;
|
||||
import mage.util.CardUtil;
|
||||
|
||||
import java.util.Optional;
|
||||
import java.util.UUID;
|
||||
|
||||
/**
|
||||
* @author TheElk801
|
||||
*/
|
||||
public final class CommanderLiaraPortyr extends CardImpl {
|
||||
|
||||
public CommanderLiaraPortyr(UUID ownerId, CardSetInfo setInfo) {
|
||||
super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{3}{R}{W}");
|
||||
|
||||
this.supertype.add(SuperType.LEGENDARY);
|
||||
this.subtype.add(SubType.HUMAN);
|
||||
this.subtype.add(SubType.SOLDIER);
|
||||
this.power = new MageInt(5);
|
||||
this.toughness = new MageInt(3);
|
||||
|
||||
// Whenever you attack, spells you cast from exile this turn cost {X} less to cast, where X is the number of players being attacked. Exile the top X cards of your library. Until end of turn, you may cast spells from among those exiled cards.
|
||||
Ability ability = new AttacksWithCreaturesTriggeredAbility(new CommanderLiaraPortyrCostEffect(), 1);
|
||||
ability.addEffect(new CommanderLiaraPortyrExileEffect());
|
||||
this.addAbility(ability);
|
||||
}
|
||||
|
||||
private CommanderLiaraPortyr(final CommanderLiaraPortyr card) {
|
||||
super(card);
|
||||
}
|
||||
|
||||
@Override
|
||||
public CommanderLiaraPortyr copy() {
|
||||
return new CommanderLiaraPortyr(this);
|
||||
}
|
||||
}
|
||||
|
||||
class CommanderLiaraPortyrCostEffect extends CostModificationEffectImpl {
|
||||
|
||||
CommanderLiaraPortyrCostEffect() {
|
||||
super(Duration.EndOfTurn, Outcome.Benefit, CostModificationType.REDUCE_COST);
|
||||
staticText = "spells you cast from exile this turn cost {X} less to cast, " +
|
||||
"where X is the number of players being attacked";
|
||||
}
|
||||
|
||||
private CommanderLiaraPortyrCostEffect(final CommanderLiaraPortyrCostEffect effect) {
|
||||
super(effect);
|
||||
}
|
||||
|
||||
@Override
|
||||
public CommanderLiaraPortyrCostEffect copy() {
|
||||
return new CommanderLiaraPortyrCostEffect(this);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean apply(Game game, Ability source, Ability abilityToModify) {
|
||||
Optional.ofNullable((Integer) getValue(AttacksWithCreaturesTriggeredAbility.VALUEKEY_NUMBER_DEFENDING_PLAYERS))
|
||||
.ifPresent(i -> CardUtil.reduceCost(abilityToModify, 1));
|
||||
return true;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean applies(Ability abilityToModify, Ability source, Game game) {
|
||||
return Optional
|
||||
.ofNullable(abilityToModify)
|
||||
.map(Ability::getSourceId)
|
||||
.map(game::getSpell)
|
||||
.map(Spell::getFromZone)
|
||||
.filter(Zone.EXILED::match)
|
||||
.isPresent();
|
||||
}
|
||||
}
|
||||
|
||||
class CommanderLiaraPortyrExileEffect extends OneShotEffect {
|
||||
|
||||
CommanderLiaraPortyrExileEffect() {
|
||||
super(Outcome.Benefit);
|
||||
staticText = "Exile the top X cards of your library. Until end of turn, " +
|
||||
"you may cast spells from among those exiled cards";
|
||||
}
|
||||
|
||||
private CommanderLiaraPortyrExileEffect(final CommanderLiaraPortyrExileEffect effect) {
|
||||
super(effect);
|
||||
}
|
||||
|
||||
@Override
|
||||
public CommanderLiaraPortyrExileEffect copy() {
|
||||
return new CommanderLiaraPortyrExileEffect(this);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean apply(Game game, Ability source) {
|
||||
Player player = game.getPlayer(source.getControllerId());
|
||||
int count = Optional.ofNullable((Integer) getValue(
|
||||
AttacksWithCreaturesTriggeredAbility.VALUEKEY_NUMBER_DEFENDING_PLAYERS
|
||||
)).orElse(0);
|
||||
if (player == null || count < 1) {
|
||||
return true;
|
||||
}
|
||||
Cards cards = new CardsImpl(player.getLibrary().getTopCards(game, count));
|
||||
if (cards.isEmpty()) {
|
||||
return false;
|
||||
}
|
||||
player.moveCards(cards, Zone.EXILED, source, game);
|
||||
for (Card card : cards.getCards(game)) {
|
||||
CardUtil.makeCardPlayable(game, source, card, true, Duration.EndOfTurn, false);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
|
@ -12,7 +12,7 @@ import mage.constants.CardType;
|
|||
import mage.constants.Duration;
|
||||
import mage.target.common.TargetControlledCreaturePermanent;
|
||||
import mage.target.common.TargetCreaturePermanent;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -29,7 +29,7 @@ public final class CommandoRaid extends CardImpl {
|
|||
effect.setText("have it deal damage equal to its power to target creature that player controls.");
|
||||
Ability ability = new DealsCombatDamageToAPlayerTriggeredAbility(effect, true, true);
|
||||
ability.addTarget(new TargetCreaturePermanent());
|
||||
ability.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster());
|
||||
ability.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster());
|
||||
|
||||
this.getSpellAbility().addEffect(new GainAbilityTargetEffect(
|
||||
ability, Duration.EndOfTurn,
|
||||
|
|
|
|||
92
Mage.Sets/src/mage/cards/c/CovetousElegy.java
Normal file
92
Mage.Sets/src/mage/cards/c/CovetousElegy.java
Normal file
|
|
@ -0,0 +1,92 @@
|
|||
package mage.cards.c;
|
||||
|
||||
import mage.abilities.Ability;
|
||||
import mage.abilities.dynamicvalue.DynamicValue;
|
||||
import mage.abilities.dynamicvalue.common.PermanentsOnBattlefieldCount;
|
||||
import mage.abilities.effects.OneShotEffect;
|
||||
import mage.abilities.effects.common.CreateTokenEffect;
|
||||
import mage.abilities.hint.Hint;
|
||||
import mage.abilities.hint.ValueHint;
|
||||
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.TreasureToken;
|
||||
import mage.players.Player;
|
||||
import mage.target.TargetPermanent;
|
||||
import mage.target.common.TargetControlledCreaturePermanent;
|
||||
|
||||
import java.util.HashSet;
|
||||
import java.util.Set;
|
||||
import java.util.UUID;
|
||||
|
||||
/**
|
||||
* @author TheElk801
|
||||
*/
|
||||
public final class CovetousElegy extends CardImpl {
|
||||
|
||||
private static final DynamicValue xValue = new PermanentsOnBattlefieldCount(StaticFilters.FILTER_OPPONENTS_PERMANENT_CREATURE);
|
||||
private static final Hint hint = new ValueHint("Creatures your opponents control", xValue);
|
||||
|
||||
public CovetousElegy(UUID ownerId, CardSetInfo setInfo) {
|
||||
super(ownerId, setInfo, new CardType[]{CardType.SORCERY}, "{4}{W}{B}");
|
||||
|
||||
// Each player chooses up to two creatures they control, then sacrifices the rest. Then you create a tapped Treasure token for each creature your opponents control.
|
||||
this.getSpellAbility().addEffect(new CovetousElegyEffect());
|
||||
this.getSpellAbility().addEffect(new CreateTokenEffect(new TreasureToken(), xValue).concatBy("Then"));
|
||||
this.getSpellAbility().addHint(hint);
|
||||
}
|
||||
|
||||
private CovetousElegy(final CovetousElegy card) {
|
||||
super(card);
|
||||
}
|
||||
|
||||
@Override
|
||||
public CovetousElegy copy() {
|
||||
return new CovetousElegy(this);
|
||||
}
|
||||
}
|
||||
|
||||
class CovetousElegyEffect extends OneShotEffect {
|
||||
|
||||
CovetousElegyEffect() {
|
||||
super(Outcome.Benefit);
|
||||
staticText = "each player chooses up to two creatures they control, then sacrifices the rest";
|
||||
}
|
||||
|
||||
private CovetousElegyEffect(final CovetousElegyEffect effect) {
|
||||
super(effect);
|
||||
}
|
||||
|
||||
@Override
|
||||
public CovetousElegyEffect copy() {
|
||||
return new CovetousElegyEffect(this);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean apply(Game game, Ability source) {
|
||||
Set<UUID> creatures = new HashSet<>();
|
||||
for (UUID playerId : game.getState().getPlayersInRange(source.getControllerId(), game)) {
|
||||
Player player = game.getPlayer(playerId);
|
||||
if (player == null) {
|
||||
continue;
|
||||
}
|
||||
TargetPermanent target = new TargetControlledCreaturePermanent(0, 2);
|
||||
target.withNotTarget(true);
|
||||
target.withChooseHint("the rest will be sacrificed");
|
||||
player.choose(outcome, target, source, game);
|
||||
creatures.addAll(target.getTargets());
|
||||
}
|
||||
for (Permanent permanent : game.getBattlefield().getActivePermanents(
|
||||
StaticFilters.FILTER_PERMANENT_CREATURE, source.getControllerId(), source, game
|
||||
)) {
|
||||
if (!creatures.contains(permanent.getId())) {
|
||||
permanent.sacrifice(source, game);
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
|
@ -13,7 +13,7 @@ import mage.constants.CardType;
|
|||
import mage.constants.SubType;
|
||||
import mage.filter.common.FilterEnchantmentPermanent;
|
||||
import mage.target.TargetPermanent;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -36,7 +36,7 @@ public final class DawningPurist extends CardImpl {
|
|||
// Whenever Dawning Purist deals combat damage to a player, you may destroy target enchantment that player controls.
|
||||
Ability ability = new DealsCombatDamageToAPlayerTriggeredAbility(new DestroyTargetEffect(), true, true);
|
||||
ability.addTarget(new TargetPermanent(filter));
|
||||
ability.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster());
|
||||
ability.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster());
|
||||
this.addAbility(ability);
|
||||
|
||||
// Morph {1}{W}
|
||||
|
|
|
|||
|
|
@ -20,7 +20,7 @@ import mage.filter.common.FilterCreaturePermanent;
|
|||
import mage.filter.common.FilterInstantOrSorceryCard;
|
||||
import mage.filter.predicate.Predicates;
|
||||
import mage.target.common.TargetCardInGraveyard;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -54,7 +54,7 @@ public final class DeluxeDragster extends CardImpl {
|
|||
+ ThatSpellGraveyardExileReplacementEffect.RULE_A);
|
||||
Ability ability = new DealsCombatDamageToAPlayerTriggeredAbility(effect, false, true);
|
||||
ability.addTarget(new TargetCardInGraveyard(filterCard));
|
||||
ability.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster(true));
|
||||
ability.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster(true));
|
||||
this.addAbility(ability);
|
||||
|
||||
// Crew 2
|
||||
|
|
|
|||
|
|
@ -162,12 +162,10 @@ class DranaAndLinvalaManaEffect extends AsThoughEffectImpl implements AsThoughMa
|
|||
return CardUtil
|
||||
.getMainCardId(game, objectId)
|
||||
.equals(source.getSourceId())
|
||||
&& affectedAbility
|
||||
.getEffects()
|
||||
.stream()
|
||||
.map(effect -> effect.getValue("dranaLinvalaFlag"))
|
||||
.filter(Boolean.class::isInstance)
|
||||
.anyMatch(Boolean.class::cast)
|
||||
&& CardUtil
|
||||
.getEffectValueFromAbility(
|
||||
affectedAbility, "dranaLinvalaFlag", Boolean.class
|
||||
).orElse(false)
|
||||
&& source.isControlledBy(playerId);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -15,7 +15,7 @@ import mage.constants.CardType;
|
|||
import mage.filter.common.FilterArtifactPermanent;
|
||||
import mage.target.TargetPermanent;
|
||||
import mage.target.common.TargetAttackingCreature;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -41,7 +41,7 @@ public final class DreadmawsIre extends CardImpl {
|
|||
effect.setText("have it deal damage equal to its power to target creature that player controls.");
|
||||
Ability ability = new DealsCombatDamageToAPlayerTriggeredAbility(new DestroyTargetEffect(), false, true);
|
||||
ability.addTarget(new TargetPermanent(filter));
|
||||
ability.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster());
|
||||
ability.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster());
|
||||
|
||||
this.getSpellAbility().addEffect(new GainAbilityTargetEffect(ability)
|
||||
.setText("and \"Whenever this creature deals combat damage to a player, destroy target artifact that player controls.\""));
|
||||
|
|
|
|||
|
|
@ -1,6 +1,7 @@
|
|||
package mage.cards.d;
|
||||
|
||||
import mage.MageInt;
|
||||
import mage.MageObject;
|
||||
import mage.abilities.Ability;
|
||||
import mage.abilities.common.DiesCreatureTriggeredAbility;
|
||||
import mage.abilities.common.EntersBattlefieldTriggeredAbility;
|
||||
|
|
@ -19,6 +20,7 @@ import mage.counters.CounterType;
|
|||
import mage.game.Game;
|
||||
import mage.game.permanent.Permanent;
|
||||
import mage.game.permanent.token.GuenhwyvarToken;
|
||||
import mage.util.CardUtil;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -66,15 +68,13 @@ enum DrizztDoUrdenCondition implements Condition {
|
|||
@Override
|
||||
public boolean apply(Game game, Ability source) {
|
||||
Permanent sourcePermanent = source.getSourcePermanentOrLKI(game);
|
||||
Permanent creatureDied = (Permanent) source
|
||||
.getEffects()
|
||||
.stream()
|
||||
.map(effect -> effect.getValue("creatureDied"))
|
||||
.findFirst()
|
||||
.orElse(null);
|
||||
return sourcePermanent != null
|
||||
&& creatureDied != null
|
||||
&& creatureDied.getPower().getValue() > sourcePermanent.getPower().getValue();
|
||||
&& CardUtil
|
||||
.getEffectValueFromAbility(source, "creatureDied", Permanent.class)
|
||||
.map(MageObject::getPower)
|
||||
.map(MageInt::getValue)
|
||||
.filter(x -> sourcePermanent.getPower().getValue() < x)
|
||||
.isPresent();
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -75,15 +75,11 @@ enum EshkiTemursRoarCondition implements Condition {
|
|||
|
||||
@Override
|
||||
public boolean apply(Game game, Ability source) {
|
||||
return CardUtil.castStream(
|
||||
source.getEffects()
|
||||
.stream()
|
||||
.map(effect -> effect.getValue("spellCast")),
|
||||
Spell.class
|
||||
)
|
||||
.findFirst()
|
||||
return CardUtil
|
||||
.getEffectValueFromAbility(source, "spellCast", Spell.class)
|
||||
.map(Spell::getPower)
|
||||
.map(MageInt::getValue)
|
||||
.orElse(0) >= amount;
|
||||
.filter(x -> x >= amount)
|
||||
.isPresent();
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -18,7 +18,7 @@ import mage.game.Game;
|
|||
import mage.game.permanent.Permanent;
|
||||
import mage.players.Player;
|
||||
import mage.target.TargetPermanent;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -44,7 +44,7 @@ public final class EtrataTheSilencer extends CardImpl {
|
|||
// Whenever Etrata deals combat damage to a player, exile target creature that player controls and put a hit counter on that card. That player loses the game if they own three or more exiled card with hit counters on them. Etrata's owner shuffles Etrata into their library.
|
||||
Ability ability = new DealsCombatDamageToAPlayerTriggeredAbility(new EtrataTheSilencerEffect(), false, true);
|
||||
ability.addTarget(new TargetPermanent(filter));
|
||||
ability.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster());
|
||||
ability.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster());
|
||||
|
||||
this.addAbility(ability);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -16,8 +16,8 @@ import mage.constants.Duration;
|
|||
import mage.constants.SubType;
|
||||
import mage.constants.SuperType;
|
||||
import mage.game.Game;
|
||||
import mage.util.CardUtil;
|
||||
|
||||
import java.util.Objects;
|
||||
import java.util.UUID;
|
||||
|
||||
/**
|
||||
|
|
@ -65,12 +65,9 @@ enum FaridehDevilsChosenCondition implements Condition {
|
|||
|
||||
@Override
|
||||
public boolean apply(Game game, Ability source) {
|
||||
return source
|
||||
.getEffects()
|
||||
.stream()
|
||||
.map(effect -> effect.getValue("maxDieRoll"))
|
||||
.filter(Objects::nonNull)
|
||||
.mapToInt(Integer.class::cast)
|
||||
.anyMatch(x -> x >= 10);
|
||||
return CardUtil
|
||||
.getEffectValueFromAbility(source, "maxDieRoll", Integer.class)
|
||||
.filter(x -> x >= 10)
|
||||
.isPresent();
|
||||
}
|
||||
}
|
||||
|
|
|
|||
82
Mage.Sets/src/mage/cards/f/FuriousSpinesplitter.java
Normal file
82
Mage.Sets/src/mage/cards/f/FuriousSpinesplitter.java
Normal file
|
|
@ -0,0 +1,82 @@
|
|||
package mage.cards.f;
|
||||
|
||||
import mage.MageInt;
|
||||
import mage.abilities.Ability;
|
||||
import mage.abilities.dynamicvalue.DynamicValue;
|
||||
import mage.abilities.effects.Effect;
|
||||
import mage.abilities.effects.common.counter.AddCountersSourceEffect;
|
||||
import mage.abilities.keyword.TrampleAbility;
|
||||
import mage.abilities.triggers.BeginningOfEndStepTriggeredAbility;
|
||||
import mage.cards.CardImpl;
|
||||
import mage.cards.CardSetInfo;
|
||||
import mage.constants.CardType;
|
||||
import mage.constants.SubType;
|
||||
import mage.counters.CounterType;
|
||||
import mage.game.Game;
|
||||
import mage.watchers.common.AmountOfDamageAPlayerReceivedThisTurnWatcher;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
/**
|
||||
* @author TheElk801
|
||||
*/
|
||||
public final class FuriousSpinesplitter extends CardImpl {
|
||||
|
||||
public FuriousSpinesplitter(UUID ownerId, CardSetInfo setInfo) {
|
||||
super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{2}{R/G}{R/G}");
|
||||
|
||||
this.subtype.add(SubType.OGRE);
|
||||
this.subtype.add(SubType.WARRIOR);
|
||||
this.power = new MageInt(3);
|
||||
this.toughness = new MageInt(3);
|
||||
|
||||
// Trample
|
||||
this.addAbility(TrampleAbility.getInstance());
|
||||
|
||||
// At the beginning of your end step, put a +1/+1 counter on Furious Spinesplitter for each opponent that was dealt damage this turn.
|
||||
this.addAbility(new BeginningOfEndStepTriggeredAbility(new AddCountersSourceEffect(
|
||||
CounterType.P1P1.createInstance(), FuriousSpinesplitterValue.instance
|
||||
)), new AmountOfDamageAPlayerReceivedThisTurnWatcher());
|
||||
}
|
||||
|
||||
private FuriousSpinesplitter(final FuriousSpinesplitter card) {
|
||||
super(card);
|
||||
}
|
||||
|
||||
@Override
|
||||
public FuriousSpinesplitter copy() {
|
||||
return new FuriousSpinesplitter(this);
|
||||
}
|
||||
}
|
||||
|
||||
enum FuriousSpinesplitterValue implements DynamicValue {
|
||||
instance;
|
||||
|
||||
@Override
|
||||
public int calculate(Game game, Ability sourceAbility, Effect effect) {
|
||||
return game
|
||||
.getOpponents(sourceAbility.getControllerId())
|
||||
.stream()
|
||||
.map(game
|
||||
.getState()
|
||||
.getWatcher(AmountOfDamageAPlayerReceivedThisTurnWatcher.class)
|
||||
::getAmountOfDamageReceivedThisTurn)
|
||||
.mapToInt(x -> Math.min(x, 1))
|
||||
.sum();
|
||||
}
|
||||
|
||||
@Override
|
||||
public FuriousSpinesplitterValue copy() {
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getMessage() {
|
||||
return "opponent that was dealt damage this turn";
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "1";
|
||||
}
|
||||
}
|
||||
|
|
@ -16,7 +16,7 @@ import mage.constants.Outcome;
|
|||
import mage.constants.SubType;
|
||||
import mage.filter.FilterPermanent;
|
||||
import mage.target.TargetPermanent;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -38,7 +38,7 @@ public final class HammerOfRuin extends CardImpl {
|
|||
// Whenever equipped creature deals combat damage to a player, you may destroy target Equipment that player controls.
|
||||
Ability ability = new DealsDamageToAPlayerAttachedTriggeredAbility(new DestroyTargetEffect(), "equipped creature", true, true);
|
||||
ability.addTarget(new TargetPermanent(filter));
|
||||
ability.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster());
|
||||
ability.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster());
|
||||
this.addAbility(ability);
|
||||
|
||||
// Equip {2}
|
||||
|
|
|
|||
|
|
@ -70,19 +70,10 @@ enum HammerheadTyrantPredicate implements ObjectSourcePlayerPredicate<Permanent>
|
|||
|
||||
@Override
|
||||
public boolean apply(ObjectSourcePlayer<Permanent> input, Game game) {
|
||||
return input
|
||||
.getObject()
|
||||
.getManaValue()
|
||||
<= CardUtil
|
||||
.castStream(
|
||||
input.getSource()
|
||||
.getEffects()
|
||||
.stream()
|
||||
.map(effect -> effect.getValue("spellCast")),
|
||||
Spell.class
|
||||
)
|
||||
.findFirst()
|
||||
return CardUtil
|
||||
.getEffectValueFromAbility(input.getSource(), "spellCast", Spell.class)
|
||||
.map(Spell::getManaValue)
|
||||
.orElse(-1);
|
||||
.filter(x -> x >= input.getObject().getManaValue())
|
||||
.isPresent();
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -13,10 +13,9 @@ import mage.cards.CardSetInfo;
|
|||
import mage.constants.CardType;
|
||||
import mage.constants.SubType;
|
||||
import mage.constants.SuperType;
|
||||
import mage.constants.Zone;
|
||||
import mage.filter.common.FilterCreatureCard;
|
||||
import mage.target.common.TargetCardInGraveyard;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -43,7 +42,7 @@ public final class InkEyesServantOfOni extends CardImpl {
|
|||
// Whenever Ink-Eyes, Servant of Oni deals combat damage to a player, you may put target creature card from that player's graveyard onto the battlefield under your control.
|
||||
Ability ability = new DealsCombatDamageToAPlayerTriggeredAbility(new ReturnFromGraveyardToBattlefieldTargetEffect(), true, true);
|
||||
ability.addTarget(new TargetCardInGraveyard(filter));
|
||||
ability.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster(true));
|
||||
ability.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster(true));
|
||||
this.addAbility(ability);
|
||||
|
||||
// {1}{B}: Regenerate Ink-Eyes.
|
||||
|
|
|
|||
|
|
@ -2,6 +2,7 @@ package mage.cards.j;
|
|||
|
||||
import mage.MageInt;
|
||||
import mage.Mana;
|
||||
import mage.ObjectColor;
|
||||
import mage.abilities.Ability;
|
||||
import mage.abilities.common.SpellCastControllerTriggeredAbility;
|
||||
import mage.abilities.condition.Condition;
|
||||
|
|
@ -23,7 +24,6 @@ import mage.game.permanent.token.AngelVigilanceToken;
|
|||
import mage.game.stack.Spell;
|
||||
import mage.util.CardUtil;
|
||||
|
||||
import java.util.Objects;
|
||||
import java.util.UUID;
|
||||
|
||||
/**
|
||||
|
|
@ -72,15 +72,12 @@ enum JensonCarthalionDruidExileCondition implements Condition {
|
|||
|
||||
@Override
|
||||
public boolean apply(Game game, Ability source) {
|
||||
return CardUtil.castStream(
|
||||
source.getEffects()
|
||||
.stream()
|
||||
.map(effect -> effect.getValue("spellCast")),
|
||||
Spell.class
|
||||
).findAny()
|
||||
.filter(Objects::nonNull)
|
||||
.map(spell -> spell.getColor(game).getColorCount())
|
||||
.orElse(0) >= 5;
|
||||
return CardUtil
|
||||
.getEffectValueFromAbility(source, "spellCast", Spell.class)
|
||||
.map(spell -> spell.getColor(game))
|
||||
.map(ObjectColor::getColorCount)
|
||||
.filter(x -> x >= 5)
|
||||
.isPresent();
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
|||
|
|
@ -1,10 +1,8 @@
|
|||
package mage.cards.k;
|
||||
|
||||
import mage.MageInt;
|
||||
import mage.MageObjectReference;
|
||||
import mage.abilities.Ability;
|
||||
import mage.abilities.common.SimpleStaticAbility;
|
||||
import mage.abilities.condition.Condition;
|
||||
import mage.abilities.condition.common.SourceHasntDealtDamageThisGameCondition;
|
||||
import mage.abilities.decorator.ConditionalContinuousEffect;
|
||||
import mage.abilities.effects.common.continuous.GainAbilitySourceEffect;
|
||||
import mage.abilities.keyword.FlyingAbility;
|
||||
|
|
@ -15,14 +13,8 @@ import mage.cards.CardImpl;
|
|||
import mage.cards.CardSetInfo;
|
||||
import mage.constants.CardType;
|
||||
import mage.constants.SubType;
|
||||
import mage.constants.WatcherScope;
|
||||
import mage.game.Game;
|
||||
import mage.game.events.GameEvent;
|
||||
import mage.game.permanent.Permanent;
|
||||
import mage.watchers.Watcher;
|
||||
import mage.watchers.common.DealtDamageThisGameWatcher;
|
||||
|
||||
import java.util.HashSet;
|
||||
import java.util.Set;
|
||||
import java.util.UUID;
|
||||
|
||||
/**
|
||||
|
|
@ -49,8 +41,9 @@ public final class KarakykGuardian extends CardImpl {
|
|||
// This creature has hexproof if it hasn't dealt damage yet.
|
||||
this.addAbility(new SimpleStaticAbility(new ConditionalContinuousEffect(
|
||||
new GainAbilitySourceEffect(HexproofAbility.getInstance()),
|
||||
KarakykGuardianCondition.instance, "{this} has hexproof if it hasn't dealt damage yet"
|
||||
)), new KarakykGuardianWatcher());
|
||||
SourceHasntDealtDamageThisGameCondition.instance,
|
||||
"{this} has hexproof if it hasn't dealt damage yet"
|
||||
)).addHint(SourceHasntDealtDamageThisGameCondition.getHint()), new DealtDamageThisGameWatcher());
|
||||
}
|
||||
|
||||
private KarakykGuardian(final KarakykGuardian card) {
|
||||
|
|
@ -62,49 +55,3 @@ public final class KarakykGuardian extends CardImpl {
|
|||
return new KarakykGuardian(this);
|
||||
}
|
||||
}
|
||||
|
||||
enum KarakykGuardianCondition implements Condition {
|
||||
|
||||
instance;
|
||||
|
||||
@Override
|
||||
public boolean apply(Game game, Ability source) {
|
||||
Permanent permanent = game.getPermanent(source.getSourceId());
|
||||
KarakykGuardianWatcher watcher = game.getState().getWatcher(KarakykGuardianWatcher.class);
|
||||
return permanent != null && !watcher.getDamagers().contains(new MageObjectReference(permanent, game));
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "{this} hasn't dealt damage yet";
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
class KarakykGuardianWatcher extends Watcher {
|
||||
|
||||
private final Set<MageObjectReference> damagers = new HashSet<>();
|
||||
|
||||
public KarakykGuardianWatcher() {
|
||||
super(WatcherScope.GAME);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void watch(GameEvent event, Game game) {
|
||||
switch (event.getType()) {
|
||||
case DAMAGED_PERMANENT:
|
||||
case DAMAGED_PLAYER:
|
||||
break;
|
||||
default:
|
||||
return;
|
||||
}
|
||||
Permanent permanent = game.getPermanent(event.getSourceId());
|
||||
if (permanent != null) {
|
||||
damagers.add(new MageObjectReference(permanent, game));
|
||||
}
|
||||
}
|
||||
|
||||
public Set<MageObjectReference> getDamagers() {
|
||||
return damagers;
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -15,7 +15,7 @@ import mage.constants.SubType;
|
|||
import mage.filter.common.FilterArtifactPermanent;
|
||||
import mage.target.TargetPermanent;
|
||||
import mage.target.common.TargetCreaturePermanent;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -45,7 +45,7 @@ public final class LatullasOrders extends CardImpl {
|
|||
new DestroyTargetEffect(), "enchanted creature", true, true
|
||||
).setTriggerPhrase("Whenever enchanted creature deals combat damage to defending player, ");
|
||||
ability.addTarget(new TargetPermanent(filter));
|
||||
ability.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster());
|
||||
ability.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster());
|
||||
this.addAbility(ability);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -15,7 +15,7 @@ import mage.filter.FilterPermanent;
|
|||
import mage.filter.predicate.Predicates;
|
||||
import mage.filter.predicate.mageobject.ColorPredicate;
|
||||
import mage.target.TargetPermanent;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -46,7 +46,7 @@ public final class LightwielderPaladin extends CardImpl {
|
|||
// Whenever Lightwielder Paladin deals combat damage to a player, you may exile target black or red permanent that player controls.
|
||||
Ability ability = new DealsCombatDamageToAPlayerTriggeredAbility(new ExileTargetEffect(), true, true);
|
||||
ability.addTarget(new TargetPermanent(filter));
|
||||
ability.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster());
|
||||
ability.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster());
|
||||
this.addAbility(ability);
|
||||
}
|
||||
|
||||
|
|
|
|||
108
Mage.Sets/src/mage/cards/m/MemoryVampire.java
Normal file
108
Mage.Sets/src/mage/cards/m/MemoryVampire.java
Normal file
|
|
@ -0,0 +1,108 @@
|
|||
package mage.cards.m;
|
||||
|
||||
import mage.MageInt;
|
||||
import mage.abilities.Ability;
|
||||
import mage.abilities.common.DealsCombatDamageToAPlayerTriggeredAbility;
|
||||
import mage.abilities.common.delayed.ReflexiveTriggeredAbility;
|
||||
import mage.abilities.costs.Cost;
|
||||
import mage.abilities.costs.common.CollectEvidenceCost;
|
||||
import mage.abilities.dynamicvalue.common.SavedDamageValue;
|
||||
import mage.abilities.effects.OneShotEffect;
|
||||
import mage.abilities.effects.common.MayCastTargetCardEffect;
|
||||
import mage.abilities.effects.common.MillCardsTargetEffect;
|
||||
import mage.abilities.keyword.FlyingAbility;
|
||||
import mage.cards.CardImpl;
|
||||
import mage.cards.CardSetInfo;
|
||||
import mage.constants.CardType;
|
||||
import mage.constants.CastManaAdjustment;
|
||||
import mage.constants.Outcome;
|
||||
import mage.constants.SubType;
|
||||
import mage.filter.FilterCard;
|
||||
import mage.filter.common.FilterNonlandCard;
|
||||
import mage.filter.predicate.card.OwnerIdPredicate;
|
||||
import mage.game.Game;
|
||||
import mage.players.Player;
|
||||
import mage.target.TargetPlayer;
|
||||
import mage.target.common.TargetCardInGraveyard;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
/**
|
||||
* @author TheElk801
|
||||
*/
|
||||
public final class MemoryVampire extends CardImpl {
|
||||
|
||||
public MemoryVampire(UUID ownerId, CardSetInfo setInfo) {
|
||||
super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{4}{U}{B}");
|
||||
|
||||
this.subtype.add(SubType.VAMPIRE);
|
||||
this.subtype.add(SubType.DETECTIVE);
|
||||
this.power = new MageInt(4);
|
||||
this.toughness = new MageInt(4);
|
||||
|
||||
// Flying
|
||||
this.addAbility(FlyingAbility.getInstance());
|
||||
|
||||
// Whenever Memory Vampire deals combat damage to a player, any number of target players each mill that many cards. Then you may collect evidence 9. When you do, you may cast target nonland card from defending player's graveyard without paying its mana cost.
|
||||
Ability ability = new DealsCombatDamageToAPlayerTriggeredAbility(
|
||||
new MillCardsTargetEffect(SavedDamageValue.MANY)
|
||||
.setText("any number of target players each mill that many cards")
|
||||
);
|
||||
ability.addEffect(new MemoryVampireEffect());
|
||||
ability.addTarget(new TargetPlayer(0, Integer.MAX_VALUE, false));
|
||||
this.addAbility(ability);
|
||||
}
|
||||
|
||||
private MemoryVampire(final MemoryVampire card) {
|
||||
super(card);
|
||||
}
|
||||
|
||||
@Override
|
||||
public MemoryVampire copy() {
|
||||
return new MemoryVampire(this);
|
||||
}
|
||||
}
|
||||
|
||||
class MemoryVampireEffect extends OneShotEffect {
|
||||
|
||||
MemoryVampireEffect() {
|
||||
super(Outcome.Benefit);
|
||||
staticText = "Then you may collect evidence 9. When you do, you may cast target " +
|
||||
"nonland card from defending player's graveyard without paying its mana cost";
|
||||
}
|
||||
|
||||
private MemoryVampireEffect(final MemoryVampireEffect effect) {
|
||||
super(effect);
|
||||
}
|
||||
|
||||
@Override
|
||||
public MemoryVampireEffect copy() {
|
||||
return new MemoryVampireEffect(this);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean apply(Game game, Ability source) {
|
||||
Player player = game.getPlayer(source.getControllerId());
|
||||
if (player == null) {
|
||||
return false;
|
||||
}
|
||||
Cost cost = new CollectEvidenceCost(9);
|
||||
if (!cost.canPay(source, source, source.getControllerId(), game)
|
||||
|| !player.chooseUse(outcome, "Collect evidence 9?", source, game)
|
||||
|| !cost.pay(source, game, source, source.getControllerId(), true)) {
|
||||
return false;
|
||||
}
|
||||
UUID defenderId = (UUID) getValue("damagedPlayer");
|
||||
if (defenderId == null) {
|
||||
return true;
|
||||
}
|
||||
ReflexiveTriggeredAbility ability = new ReflexiveTriggeredAbility(
|
||||
new MayCastTargetCardEffect(CastManaAdjustment.WITHOUT_PAYING_MANA_COST), false
|
||||
);
|
||||
FilterCard filter = new FilterNonlandCard("nonland card from defending player's graveyard");
|
||||
filter.add(new OwnerIdPredicate(defenderId));
|
||||
ability.addTarget(new TargetCardInGraveyard(filter));
|
||||
game.fireReflexiveTriggeredAbility(ability, source);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
|
@ -12,7 +12,7 @@ import mage.constants.CardType;
|
|||
import mage.constants.SubType;
|
||||
import mage.filter.common.FilterCreaturePermanent;
|
||||
import mage.target.common.TargetCreaturePermanent;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -38,7 +38,7 @@ public final class MistbladeShinobi extends CardImpl {
|
|||
// Whenever Mistblade Shinobi deals combat damage to a player, you may return target creature that player controls to its owner's hand.
|
||||
Ability ability = new DealsCombatDamageToAPlayerTriggeredAbility(new ReturnToHandTargetEffect(), true, true);
|
||||
ability.addTarget(new TargetCreaturePermanent(filter));
|
||||
ability.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster());
|
||||
ability.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster());
|
||||
this.addAbility(ability);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -15,9 +15,8 @@ import mage.cards.CardSetInfo;
|
|||
import mage.constants.CardType;
|
||||
import mage.constants.Duration;
|
||||
import mage.constants.SubType;
|
||||
import mage.constants.Zone;
|
||||
import mage.target.common.TargetCreaturePermanent;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -45,7 +44,7 @@ public final class MordantDragon extends CardImpl {
|
|||
effect.setText("have it deal that much damage to target creature that player controls.");
|
||||
Ability ability = new DealsCombatDamageToAPlayerTriggeredAbility(effect, true, true);
|
||||
ability.addTarget(new TargetCreaturePermanent());
|
||||
ability.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster());
|
||||
ability.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster());
|
||||
this.addAbility(ability);
|
||||
}
|
||||
|
||||
|
|
|
|||
104
Mage.Sets/src/mage/cards/o/OrdruunMentor.java
Normal file
104
Mage.Sets/src/mage/cards/o/OrdruunMentor.java
Normal file
|
|
@ -0,0 +1,104 @@
|
|||
package mage.cards.o;
|
||||
|
||||
import mage.MageInt;
|
||||
import mage.abilities.TriggeredAbilityImpl;
|
||||
import mage.abilities.effects.common.continuous.GainAbilityTargetEffect;
|
||||
import mage.abilities.keyword.FirstStrikeAbility;
|
||||
import mage.abilities.keyword.MentorAbility;
|
||||
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.common.FilterCreaturePermanent;
|
||||
import mage.filter.predicate.ObjectSourcePlayer;
|
||||
import mage.filter.predicate.ObjectSourcePlayerPredicate;
|
||||
import mage.game.Game;
|
||||
import mage.game.events.GameEvent;
|
||||
import mage.game.permanent.Permanent;
|
||||
import mage.target.TargetPermanent;
|
||||
import mage.util.CardUtil;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
/**
|
||||
* @author TheElk801
|
||||
*/
|
||||
public final class OrdruunMentor extends CardImpl {
|
||||
|
||||
public OrdruunMentor(UUID ownerId, CardSetInfo setInfo) {
|
||||
super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{2}{R/W}");
|
||||
|
||||
this.subtype.add(SubType.MINOTAUR);
|
||||
this.subtype.add(SubType.SOLDIER);
|
||||
this.power = new MageInt(3);
|
||||
this.toughness = new MageInt(2);
|
||||
|
||||
// Mentor
|
||||
this.addAbility(new MentorAbility());
|
||||
|
||||
// Whenever you attack a player, target creature that's attacking that player gains first strike until end of turn.
|
||||
this.addAbility(new OrdruunMentorTriggeredAbility());
|
||||
}
|
||||
|
||||
private OrdruunMentor(final OrdruunMentor card) {
|
||||
super(card);
|
||||
}
|
||||
|
||||
@Override
|
||||
public OrdruunMentor copy() {
|
||||
return new OrdruunMentor(this);
|
||||
}
|
||||
}
|
||||
|
||||
class OrdruunMentorTriggeredAbility extends TriggeredAbilityImpl {
|
||||
|
||||
private enum OrdruunMentorPredicate implements ObjectSourcePlayerPredicate<Permanent> {
|
||||
instance;
|
||||
|
||||
@Override
|
||||
public boolean apply(ObjectSourcePlayer<Permanent> input, Game game) {
|
||||
return CardUtil.getEffectValueFromAbility(
|
||||
input.getSource(), "playerAttacked", UUID.class
|
||||
)
|
||||
.filter(uuid -> uuid.equals(game.getCombat().getDefenderId(input.getObject().getId())))
|
||||
.isPresent();
|
||||
}
|
||||
}
|
||||
|
||||
private static final FilterPermanent filter = new FilterCreaturePermanent("creature that's attacking that player");
|
||||
|
||||
static {
|
||||
filter.add(OrdruunMentorPredicate.instance);
|
||||
}
|
||||
|
||||
OrdruunMentorTriggeredAbility() {
|
||||
super(Zone.BATTLEFIELD, new GainAbilityTargetEffect(FirstStrikeAbility.getInstance()).setText(""));
|
||||
this.setTriggerPhrase("Whenever you attack a player, ");
|
||||
this.addTarget(new TargetPermanent(filter));
|
||||
}
|
||||
|
||||
private OrdruunMentorTriggeredAbility(final OrdruunMentorTriggeredAbility ability) {
|
||||
super(ability);
|
||||
}
|
||||
|
||||
@Override
|
||||
public OrdruunMentorTriggeredAbility copy() {
|
||||
return new OrdruunMentorTriggeredAbility(this);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean checkEventType(GameEvent event, Game game) {
|
||||
return event.getType() == GameEvent.EventType.DEFENDER_ATTACKED;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean checkTrigger(GameEvent event, Game game) {
|
||||
if (!isControlledBy(event.getPlayerId()) || game.getPlayer(event.getTargetId()) == null) {
|
||||
return false;
|
||||
}
|
||||
this.getEffects().setValue("playerAttacked", event.getTargetId());
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
|
@ -1,13 +1,8 @@
|
|||
package mage.cards.p;
|
||||
|
||||
import java.util.HashSet;
|
||||
import java.util.Set;
|
||||
import java.util.UUID;
|
||||
import mage.MageInt;
|
||||
import mage.MageObjectReference;
|
||||
import mage.abilities.Ability;
|
||||
import mage.abilities.common.SimpleStaticAbility;
|
||||
import mage.abilities.condition.Condition;
|
||||
import mage.abilities.condition.common.SourceHasntDealtDamageThisGameCondition;
|
||||
import mage.abilities.decorator.ConditionalContinuousEffect;
|
||||
import mage.abilities.effects.common.continuous.GainAbilitySourceEffect;
|
||||
import mage.abilities.keyword.FlyingAbility;
|
||||
|
|
@ -19,15 +14,11 @@ import mage.cards.CardSetInfo;
|
|||
import mage.constants.CardType;
|
||||
import mage.constants.SubType;
|
||||
import mage.constants.SuperType;
|
||||
import mage.constants.WatcherScope;
|
||||
import mage.constants.Zone;
|
||||
import mage.game.Game;
|
||||
import mage.game.events.GameEvent;
|
||||
import mage.game.permanent.Permanent;
|
||||
import mage.watchers.Watcher;
|
||||
import mage.watchers.common.DealtDamageThisGameWatcher;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
/**
|
||||
*
|
||||
* @author TheElk801
|
||||
*/
|
||||
public final class PalladiaMorsTheRuiner extends CardImpl {
|
||||
|
|
@ -51,13 +42,11 @@ public final class PalladiaMorsTheRuiner extends CardImpl {
|
|||
this.addAbility(TrampleAbility.getInstance());
|
||||
|
||||
// Palladia-Mors, the Ruiner has hexproof if it hasn't dealt damage yet.
|
||||
this.addAbility(new SimpleStaticAbility(
|
||||
new ConditionalContinuousEffect(
|
||||
new GainAbilitySourceEffect(HexproofAbility.getInstance()),
|
||||
PalladiaMorsTheRuinerCondition.instance,
|
||||
"{this} has hexproof if it hasn't dealt damage yet"
|
||||
)
|
||||
), new PalladiaMorsTheRuinerWatcher());
|
||||
this.addAbility(new SimpleStaticAbility(new ConditionalContinuousEffect(
|
||||
new GainAbilitySourceEffect(HexproofAbility.getInstance()),
|
||||
SourceHasntDealtDamageThisGameCondition.instance,
|
||||
"{this} has hexproof if it hasn't dealt damage yet"
|
||||
)).addHint(SourceHasntDealtDamageThisGameCondition.getHint()), new DealtDamageThisGameWatcher());
|
||||
}
|
||||
|
||||
private PalladiaMorsTheRuiner(final PalladiaMorsTheRuiner card) {
|
||||
|
|
@ -69,49 +58,3 @@ public final class PalladiaMorsTheRuiner extends CardImpl {
|
|||
return new PalladiaMorsTheRuiner(this);
|
||||
}
|
||||
}
|
||||
|
||||
enum PalladiaMorsTheRuinerCondition implements Condition {
|
||||
|
||||
instance;
|
||||
|
||||
@Override
|
||||
public boolean apply(Game game, Ability source) {
|
||||
Permanent permanent = game.getPermanent(source.getSourceId());
|
||||
PalladiaMorsTheRuinerWatcher watcher = game.getState().getWatcher(PalladiaMorsTheRuinerWatcher.class);
|
||||
return permanent != null && !watcher.getDamagers().contains(new MageObjectReference(permanent, game));
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "{this} hasn't dealt damage yet";
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
class PalladiaMorsTheRuinerWatcher extends Watcher {
|
||||
|
||||
private final Set<MageObjectReference> damagers = new HashSet<>();
|
||||
|
||||
public PalladiaMorsTheRuinerWatcher() {
|
||||
super(WatcherScope.GAME);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void watch(GameEvent event, Game game) {
|
||||
switch (event.getType()) {
|
||||
case DAMAGED_PERMANENT:
|
||||
case DAMAGED_PLAYER:
|
||||
break;
|
||||
default:
|
||||
return;
|
||||
}
|
||||
Permanent permanent = game.getPermanent(event.getSourceId());
|
||||
if (permanent != null) {
|
||||
damagers.add(new MageObjectReference(permanent, game));
|
||||
}
|
||||
}
|
||||
|
||||
public Set<MageObjectReference> getDamagers() {
|
||||
return damagers;
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -22,7 +22,7 @@ import mage.filter.common.FilterControlledPermanent;
|
|||
import mage.game.Game;
|
||||
import mage.players.Player;
|
||||
import mage.target.TargetPermanent;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
/**
|
||||
*
|
||||
|
|
@ -49,7 +49,7 @@ public final class ParapetThrasher extends CardImpl {
|
|||
filter, true, true, SetTargetPointer.PLAYER, false)
|
||||
.setTriggerPhrase("Whenever one or more Dragons you control deal combat damage to an opponent, ");
|
||||
ability.addTarget(new TargetPermanent(artifactFilter));
|
||||
ability.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster());
|
||||
ability.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster());
|
||||
ability.setModeTag("destroy artifact");
|
||||
ability.getModes().setLimitUsageByOnce(true);
|
||||
|
||||
|
|
|
|||
|
|
@ -1,6 +1,7 @@
|
|||
package mage.cards.p;
|
||||
|
||||
import mage.MageInt;
|
||||
import mage.MageObject;
|
||||
import mage.abilities.Ability;
|
||||
import mage.abilities.common.AttacksTriggeredAbility;
|
||||
import mage.abilities.common.delayed.AtTheBeginOfNextEndStepDelayedTriggeredAbility;
|
||||
|
|
@ -49,10 +50,7 @@ public final class PheliaExuberantShepherd extends CardImpl {
|
|||
this.addAbility(FlashAbility.getInstance());
|
||||
|
||||
// Whenever Phelia, Exuberant Shepherd attacks, exile up to one other target nonland permanent. At the beginning of the next end step, return that card to the battlefield under its owner's control. If it entered under your control, put a +1/+1 counter on Phelia.
|
||||
Ability ability = new AttacksTriggeredAbility(new ExileTargetEffect().setToSourceExileZone(true));
|
||||
ability.addEffect(new CreateDelayedTriggeredAbilityEffect(
|
||||
new AtTheBeginOfNextEndStepDelayedTriggeredAbility(new PheliaExuberantShepherdEffect()), false
|
||||
));
|
||||
Ability ability = new AttacksTriggeredAbility(new PheliaExuberantShepherdExileEffect());
|
||||
ability.addTarget(new TargetPermanent(0, 1, filter));
|
||||
this.addAbility(ability);
|
||||
}
|
||||
|
|
@ -67,16 +65,55 @@ public final class PheliaExuberantShepherd extends CardImpl {
|
|||
}
|
||||
}
|
||||
|
||||
class PheliaExuberantShepherdExileEffect extends ExileTargetEffect {
|
||||
|
||||
PheliaExuberantShepherdExileEffect() {
|
||||
super();
|
||||
outcome = Outcome.Neutral; // quite contextual outcome.
|
||||
staticText = "exile up to one other target nonland permanent. At the beginning of the next end step, "
|
||||
+ "return that card to the battlefield under its owner's control. If it entered under your control, "
|
||||
+ "put a +1/+1 counter on {this}.";
|
||||
}
|
||||
|
||||
private PheliaExuberantShepherdExileEffect(final PheliaExuberantShepherdExileEffect effect) {
|
||||
super(effect);
|
||||
}
|
||||
|
||||
@Override
|
||||
public PheliaExuberantShepherdExileEffect copy() {
|
||||
return new PheliaExuberantShepherdExileEffect(this);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean apply(Game game, Ability source) {
|
||||
MageObject sourceObject = source.getSourceObject(game);
|
||||
this.exileId = UUID.randomUUID();
|
||||
this.exileZone = sourceObject == null ? null : sourceObject.getIdName();
|
||||
// attempting to exile to the fresh exileId
|
||||
boolean didSomething = super.apply(game, source);
|
||||
// delayed trigger is created even if exiling failed.
|
||||
didSomething |= new CreateDelayedTriggeredAbilityEffect(
|
||||
new AtTheBeginOfNextEndStepDelayedTriggeredAbility(
|
||||
new PheliaExuberantShepherdEffect(this.exileId)), false
|
||||
).apply(game, source);
|
||||
return didSomething;
|
||||
}
|
||||
}
|
||||
|
||||
class PheliaExuberantShepherdEffect extends OneShotEffect {
|
||||
|
||||
PheliaExuberantShepherdEffect() {
|
||||
private final UUID zoneId; // the exile zone's id for cards to return.
|
||||
|
||||
PheliaExuberantShepherdEffect(UUID zoneId) {
|
||||
super(Outcome.Benefit);
|
||||
staticText = "return that card to the battlefield under its owner's control. "
|
||||
+ "If it entered under your control, put a +1/+1 counter on {this}";
|
||||
this.zoneId = zoneId;
|
||||
}
|
||||
|
||||
private PheliaExuberantShepherdEffect(final PheliaExuberantShepherdEffect effect) {
|
||||
super(effect);
|
||||
this.zoneId = effect.zoneId;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
@ -90,7 +127,6 @@ class PheliaExuberantShepherdEffect extends OneShotEffect {
|
|||
if (player == null) {
|
||||
return false;
|
||||
}
|
||||
UUID zoneId = CardUtil.getExileZoneId(game, source.getSourceId(), source.getSourceObjectZoneChangeCounter());
|
||||
ExileZone exileZone = game.getExile().getExileZone(zoneId);
|
||||
if (exileZone == null || exileZone.isEmpty()) {
|
||||
return false;
|
||||
|
|
|
|||
|
|
@ -17,7 +17,7 @@ import mage.filter.FilterCard;
|
|||
import mage.filter.common.FilterEnchantmentCard;
|
||||
import mage.filter.common.FilterEnchantmentPermanent;
|
||||
import mage.target.TargetPermanent;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -52,7 +52,7 @@ public final class PolisCrusher extends CardImpl {
|
|||
// Whenever Polis Crusher deals combat damage to a player, if Polis Crusher is monstrous, destroy target enchantment that player controls.
|
||||
TriggeredAbility ability = new DealsCombatDamageToAPlayerTriggeredAbility(new DestroyTargetEffect(), false, true);
|
||||
ability.addTarget(new TargetPermanent(filterPermanent));
|
||||
ability.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster());
|
||||
ability.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster());
|
||||
|
||||
this.addAbility(new ConditionalInterveningIfTriggeredAbility(ability, MonstrousCondition.instance,
|
||||
"Whenever {this} deals combat damage to a player, if {this} is monstrous, destroy target enchantment that player controls."));
|
||||
|
|
|
|||
|
|
@ -21,7 +21,7 @@ import mage.game.events.GameEvent;
|
|||
import mage.game.events.PreventDamageEvent;
|
||||
import mage.game.permanent.Permanent;
|
||||
import mage.target.TargetPermanent;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -57,7 +57,7 @@ public final class QuestingBeast extends CardImpl {
|
|||
// Whenever Questing Beast deals combat damage to an opponent, it deals that much damage to target planeswalker that player controls.
|
||||
Ability ability = new DealsDamageToOpponentTriggeredAbility(new DamageTargetEffect(SavedDamageValue.MUCH), false, true, true);
|
||||
ability.addTarget(new TargetPermanent(filter));
|
||||
ability.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster());
|
||||
ability.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster());
|
||||
this.addAbility(ability);
|
||||
}
|
||||
|
||||
|
|
|
|||
152
Mage.Sets/src/mage/cards/r/Ratonhnhaketon.java
Normal file
152
Mage.Sets/src/mage/cards/r/Ratonhnhaketon.java
Normal file
|
|
@ -0,0 +1,152 @@
|
|||
package mage.cards.r;
|
||||
|
||||
import mage.MageInt;
|
||||
import mage.abilities.Ability;
|
||||
import mage.abilities.common.DealsCombatDamageToAPlayerTriggeredAbility;
|
||||
import mage.abilities.common.SimpleStaticAbility;
|
||||
import mage.abilities.common.delayed.ReflexiveTriggeredAbility;
|
||||
import mage.abilities.condition.common.SourceHasntDealtDamageThisGameCondition;
|
||||
import mage.abilities.decorator.ConditionalContinuousEffect;
|
||||
import mage.abilities.decorator.ConditionalRestrictionEffect;
|
||||
import mage.abilities.effects.OneShotEffect;
|
||||
import mage.abilities.effects.common.combat.CantBeBlockedSourceEffect;
|
||||
import mage.abilities.effects.common.continuous.GainAbilitySourceEffect;
|
||||
import mage.abilities.keyword.HexproofAbility;
|
||||
import mage.cards.Card;
|
||||
import mage.cards.CardImpl;
|
||||
import mage.cards.CardSetInfo;
|
||||
import mage.constants.*;
|
||||
import mage.filter.FilterCard;
|
||||
import mage.game.Game;
|
||||
import mage.game.permanent.Permanent;
|
||||
import mage.game.permanent.token.AssassinMenaceToken;
|
||||
import mage.game.permanent.token.Token;
|
||||
import mage.players.Player;
|
||||
import mage.target.common.TargetCardInYourGraveyard;
|
||||
import mage.util.CardUtil;
|
||||
import mage.watchers.common.DealtDamageThisGameWatcher;
|
||||
|
||||
import java.util.Optional;
|
||||
import java.util.UUID;
|
||||
|
||||
/**
|
||||
* @author TheElk801
|
||||
*/
|
||||
public final class Ratonhnhaketon extends CardImpl {
|
||||
|
||||
public Ratonhnhaketon(UUID ownerId, CardSetInfo setInfo) {
|
||||
super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{W}{U}{B}");
|
||||
|
||||
this.supertype.add(SuperType.LEGENDARY);
|
||||
this.subtype.add(SubType.HUMAN);
|
||||
this.subtype.add(SubType.ASSASSIN);
|
||||
this.power = new MageInt(3);
|
||||
this.toughness = new MageInt(3);
|
||||
|
||||
// As long as Ratonhnhaketon hasn't dealt damage yet, it has hexproof and can't be blocked.
|
||||
Ability ability = new SimpleStaticAbility(new ConditionalContinuousEffect(
|
||||
new GainAbilitySourceEffect(HexproofAbility.getInstance()),
|
||||
SourceHasntDealtDamageThisGameCondition.instance,
|
||||
"as long as {this} hasn't dealt damage yet, it has hexproof"
|
||||
));
|
||||
ability.addEffect(new ConditionalRestrictionEffect(
|
||||
new CantBeBlockedSourceEffect(),
|
||||
SourceHasntDealtDamageThisGameCondition.instance,
|
||||
"and can't be blocked"
|
||||
));
|
||||
this.addAbility(ability.addHint(SourceHasntDealtDamageThisGameCondition.getHint()), new DealtDamageThisGameWatcher());
|
||||
|
||||
// Whenever Ratonhnhaketon deals combat damage to a player, create a 1/1 black Assassin creature token with menace. When you do, return target Equipment card from your graveyard to the battlefield, then attach it to that token.
|
||||
this.addAbility(new DealsCombatDamageToAPlayerTriggeredAbility(new RatonhnhaketonTokenEffect()));
|
||||
}
|
||||
|
||||
private Ratonhnhaketon(final Ratonhnhaketon card) {
|
||||
super(card);
|
||||
}
|
||||
|
||||
@Override
|
||||
public Ratonhnhaketon copy() {
|
||||
return new Ratonhnhaketon(this);
|
||||
}
|
||||
}
|
||||
|
||||
class RatonhnhaketonTokenEffect extends OneShotEffect {
|
||||
|
||||
private static final FilterCard filter = new FilterCard("Equipment card from your graveyard");
|
||||
|
||||
static {
|
||||
filter.add(SubType.EQUIPMENT.getPredicate());
|
||||
}
|
||||
|
||||
RatonhnhaketonTokenEffect() {
|
||||
super(Outcome.Benefit);
|
||||
staticText = "create a 1/1 black Assassin creature token with menace. When you do, return " +
|
||||
"target Equipment card from your graveyard to the battlefield, then attach it to that token";
|
||||
}
|
||||
|
||||
private RatonhnhaketonTokenEffect(final RatonhnhaketonTokenEffect effect) {
|
||||
super(effect);
|
||||
}
|
||||
|
||||
@Override
|
||||
public RatonhnhaketonTokenEffect copy() {
|
||||
return new RatonhnhaketonTokenEffect(this);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean apply(Game game, Ability source) {
|
||||
Token token = new AssassinMenaceToken();
|
||||
token.putOntoBattlefield(1, game, source);
|
||||
for (UUID tokenId : token.getLastAddedTokenIds()) {
|
||||
Permanent permanent = game.getPermanent(tokenId);
|
||||
if (permanent == null) {
|
||||
continue;
|
||||
}
|
||||
ReflexiveTriggeredAbility ability = new ReflexiveTriggeredAbility(
|
||||
new RatonhnhaketonReturnEffect(tokenId), false
|
||||
);
|
||||
ability.addTarget(new TargetCardInYourGraveyard(filter));
|
||||
game.fireReflexiveTriggeredAbility(ability, source);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
class RatonhnhaketonReturnEffect extends OneShotEffect {
|
||||
|
||||
private final UUID tokenId;
|
||||
|
||||
RatonhnhaketonReturnEffect(UUID tokenId) {
|
||||
super(Outcome.Benefit);
|
||||
staticText = "return target Equipment card from your graveyard to the battlefield, then attach it to that token";
|
||||
this.tokenId = tokenId;
|
||||
}
|
||||
|
||||
private RatonhnhaketonReturnEffect(final RatonhnhaketonReturnEffect effect) {
|
||||
super(effect);
|
||||
this.tokenId = effect.tokenId;
|
||||
}
|
||||
|
||||
@Override
|
||||
public RatonhnhaketonReturnEffect copy() {
|
||||
return new RatonhnhaketonReturnEffect(this);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean apply(Game game, Ability source) {
|
||||
Player player = game.getPlayer(source.getControllerId());
|
||||
Card card = game.getCard(getTargetPointer().getFirst(game, source));
|
||||
if (player == null) {
|
||||
return false;
|
||||
}
|
||||
player.moveCards(card, Zone.BATTLEFIELD, source, game);
|
||||
Permanent permanent = CardUtil.getPermanentFromCardPutToBattlefield(card, game);
|
||||
if (permanent == null) {
|
||||
return false;
|
||||
}
|
||||
Optional.ofNullable(tokenId)
|
||||
.map(game::getPermanent)
|
||||
.ifPresent(p -> p.addAttachment(permanent.getId(), source, game));
|
||||
return true;
|
||||
}
|
||||
}
|
||||
95
Mage.Sets/src/mage/cards/r/ReluctantRoleModel.java
Normal file
95
Mage.Sets/src/mage/cards/r/ReluctantRoleModel.java
Normal file
|
|
@ -0,0 +1,95 @@
|
|||
package mage.cards.r;
|
||||
|
||||
import mage.MageInt;
|
||||
import mage.abilities.Ability;
|
||||
import mage.abilities.abilityword.SurvivalAbility;
|
||||
import mage.abilities.common.DiesThisOrAnotherTriggeredAbility;
|
||||
import mage.abilities.effects.OneShotEffect;
|
||||
import mage.abilities.effects.common.counter.AddCounterChoiceSourceEffect;
|
||||
import mage.cards.CardImpl;
|
||||
import mage.cards.CardSetInfo;
|
||||
import mage.constants.CardType;
|
||||
import mage.constants.Outcome;
|
||||
import mage.constants.SubType;
|
||||
import mage.counters.Counter;
|
||||
import mage.counters.CounterType;
|
||||
import mage.filter.FilterPermanent;
|
||||
import mage.filter.common.FilterControlledCreaturePermanent;
|
||||
import mage.filter.predicate.permanent.CounterAnyPredicate;
|
||||
import mage.game.Game;
|
||||
import mage.game.permanent.Permanent;
|
||||
import mage.target.common.TargetCreaturePermanent;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
/**
|
||||
* @author TheElk801
|
||||
*/
|
||||
public final class ReluctantRoleModel extends CardImpl {
|
||||
|
||||
private static final FilterPermanent filter = new FilterControlledCreaturePermanent();
|
||||
|
||||
static {
|
||||
filter.add(CounterAnyPredicate.instance);
|
||||
}
|
||||
|
||||
public ReluctantRoleModel(UUID ownerId, CardSetInfo setInfo) {
|
||||
super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{1}{W}");
|
||||
|
||||
this.subtype.add(SubType.HUMAN);
|
||||
this.subtype.add(SubType.SURVIVOR);
|
||||
this.power = new MageInt(2);
|
||||
this.toughness = new MageInt(2);
|
||||
|
||||
// Survival -- At the beginning of your second main phase, if this creature is tapped, put a flying, lifelink, or +1/+1 counter on it.
|
||||
this.addAbility(new SurvivalAbility(new AddCounterChoiceSourceEffect(
|
||||
CounterType.FLYING, CounterType.LIFELINK, CounterType.P1P1
|
||||
).setText("put a flying, lifelink, or +1/+1 counter on it")));
|
||||
|
||||
// Whenever this creature or another creature you control dies, if it had counters on it, put those counters on up to one target creature.
|
||||
Ability ability = new DiesThisOrAnotherTriggeredAbility(
|
||||
new ReluctantRoleModelEffect(), false, filter
|
||||
).setApplyFilterOnSource(true);
|
||||
ability.addTarget(new TargetCreaturePermanent(0, 1));
|
||||
this.addAbility(ability);
|
||||
}
|
||||
|
||||
private ReluctantRoleModel(final ReluctantRoleModel card) {
|
||||
super(card);
|
||||
}
|
||||
|
||||
@Override
|
||||
public ReluctantRoleModel copy() {
|
||||
return new ReluctantRoleModel(this);
|
||||
}
|
||||
}
|
||||
|
||||
class ReluctantRoleModelEffect extends OneShotEffect {
|
||||
|
||||
ReluctantRoleModelEffect() {
|
||||
super(Outcome.Benefit);
|
||||
staticText = "if it had counters on it, put those counters on up to one target creature";
|
||||
}
|
||||
|
||||
private ReluctantRoleModelEffect(final ReluctantRoleModelEffect effect) {
|
||||
super(effect);
|
||||
}
|
||||
|
||||
@Override
|
||||
public ReluctantRoleModelEffect copy() {
|
||||
return new ReluctantRoleModelEffect(this);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean apply(Game game, Ability source) {
|
||||
Permanent permanent = (Permanent) getValue("creatureDied");
|
||||
Permanent creature = game.getPermanent(getTargetPointer().getFirst(game, source));
|
||||
if (permanent == null || creature == null) {
|
||||
return false;
|
||||
}
|
||||
for (Counter counter : permanent.getCounters(game).values()) {
|
||||
creature.addCounters(counter.copy(), source, game);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
}
|
||||
74
Mage.Sets/src/mage/cards/r/ResonanceTechnician.java
Normal file
74
Mage.Sets/src/mage/cards/r/ResonanceTechnician.java
Normal file
|
|
@ -0,0 +1,74 @@
|
|||
package mage.cards.r;
|
||||
|
||||
import mage.MageInt;
|
||||
import mage.abilities.Ability;
|
||||
import mage.abilities.common.EntersBattlefieldTriggeredAbility;
|
||||
import mage.abilities.common.SimpleActivatedAbility;
|
||||
import mage.abilities.costs.common.DiscardCardCost;
|
||||
import mage.abilities.costs.common.TapSourceCost;
|
||||
import mage.abilities.costs.common.TapVariableTargetCost;
|
||||
import mage.abilities.dynamicvalue.common.GetXValue;
|
||||
import mage.abilities.effects.common.CopyTargetStackObjectEffect;
|
||||
import mage.abilities.effects.common.DoIfCostPaid;
|
||||
import mage.abilities.effects.keyword.InvestigateEffect;
|
||||
import mage.abilities.keyword.FlyingAbility;
|
||||
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.common.FilterControlledArtifactPermanent;
|
||||
import mage.filter.common.FilterControlledPermanent;
|
||||
import mage.filter.common.FilterInstantOrSorcerySpell;
|
||||
import mage.filter.predicate.permanent.TappedPredicate;
|
||||
import mage.target.TargetSpell;
|
||||
import mage.target.targetadjustment.ManaValueTargetAdjuster;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
/**
|
||||
* @author TheElk801
|
||||
*/
|
||||
public final class ResonanceTechnician extends CardImpl {
|
||||
|
||||
private static final FilterControlledPermanent filter = new FilterControlledArtifactPermanent("untapped artifacts you control");
|
||||
private static final FilterSpell filter2 = new FilterInstantOrSorcerySpell("instant or sorcery spell you control with mana value X");
|
||||
|
||||
static {
|
||||
filter.add(TappedPredicate.UNTAPPED);
|
||||
}
|
||||
|
||||
public ResonanceTechnician(UUID ownerId, CardSetInfo setInfo) {
|
||||
super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{3}{U/R}{U/R}");
|
||||
|
||||
this.subtype.add(SubType.WEIRD);
|
||||
this.subtype.add(SubType.DETECTIVE);
|
||||
this.power = new MageInt(4);
|
||||
this.toughness = new MageInt(4);
|
||||
|
||||
// Flying
|
||||
this.addAbility(FlyingAbility.getInstance());
|
||||
|
||||
// When Resonance Technician enters the battlefield, you may discard a card. If you do, investigate twice.
|
||||
this.addAbility(new EntersBattlefieldTriggeredAbility(
|
||||
new DoIfCostPaid(new InvestigateEffect(2), new DiscardCardCost())
|
||||
));
|
||||
|
||||
// {T}, Tap X untapped artifacts you control: Copy target instant or sorcery spell you control with mana value X. You may choose new targets for the copy.
|
||||
Ability ability = new SimpleActivatedAbility(new CopyTargetStackObjectEffect(), new TapSourceCost());
|
||||
ability.addCost(new TapVariableTargetCost(filter));
|
||||
ability.addTarget(new TargetSpell(filter2));
|
||||
ability.setTargetAdjuster(new ManaValueTargetAdjuster(GetXValue.instance, ComparisonType.EQUAL_TO));
|
||||
this.addAbility(ability);
|
||||
}
|
||||
|
||||
private ResonanceTechnician(final ResonanceTechnician card) {
|
||||
super(card);
|
||||
}
|
||||
|
||||
@Override
|
||||
public ResonanceTechnician copy() {
|
||||
return new ResonanceTechnician(this);
|
||||
}
|
||||
}
|
||||
|
|
@ -16,7 +16,7 @@ import mage.constants.Duration;
|
|||
import mage.constants.SubType;
|
||||
import mage.filter.common.FilterCreaturePermanent;
|
||||
import mage.target.TargetPermanent;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -39,7 +39,7 @@ public final class RiptideEntrancer extends CardImpl {
|
|||
Effect effect = new DoIfCostPaid(new GainControlTargetEffect(Duration.WhileOnBattlefield), new SacrificeSourceCost());
|
||||
Ability ability = new DealsCombatDamageToAPlayerTriggeredAbility(effect, false, true);
|
||||
ability.addTarget(new TargetPermanent(filter));
|
||||
ability.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster());
|
||||
ability.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster());
|
||||
this.addAbility(ability);
|
||||
|
||||
// Morph {U}{U}
|
||||
|
|
|
|||
|
|
@ -16,8 +16,8 @@ import mage.filter.predicate.ObjectSourcePlayerPredicate;
|
|||
import mage.game.Game;
|
||||
import mage.game.permanent.Permanent;
|
||||
import mage.target.common.TargetCardInYourGraveyard;
|
||||
import mage.util.CardUtil;
|
||||
|
||||
import java.util.Objects;
|
||||
import java.util.UUID;
|
||||
|
||||
/**
|
||||
|
|
@ -59,18 +59,10 @@ enum RiveteersAscendancyPredicate implements ObjectSourcePlayerPredicate<Card> {
|
|||
|
||||
@Override
|
||||
public boolean apply(ObjectSourcePlayer<Card> input, Game game) {
|
||||
return input
|
||||
.getObject()
|
||||
.getManaValue()
|
||||
< input
|
||||
.getSource()
|
||||
.getEffects()
|
||||
.stream()
|
||||
.map(effect -> effect.getValue("sacrificedPermanent"))
|
||||
.filter(Objects::nonNull)
|
||||
.map(Permanent.class::cast)
|
||||
.mapToInt(MageObject::getManaValue)
|
||||
.max()
|
||||
.orElse(0);
|
||||
return CardUtil
|
||||
.getEffectValueFromAbility(input.getSource(), "sacrificedPermanent", Permanent.class)
|
||||
.map(MageObject::getManaValue)
|
||||
.filter(x -> input.getObject().getManaValue() < x)
|
||||
.isPresent();
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -11,7 +11,7 @@ import mage.constants.CardType;
|
|||
import mage.constants.SubType;
|
||||
import mage.filter.common.FilterArtifactPermanent;
|
||||
import mage.target.TargetPermanent;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -33,7 +33,7 @@ public final class RustmouthOgre extends CardImpl {
|
|||
// Whenever Rustmouth Ogre deals combat damage to a player, you may destroy target artifact that player controls.
|
||||
Ability ability = new DealsCombatDamageToAPlayerTriggeredAbility(new DestroyTargetEffect(), true, true);
|
||||
ability.addTarget(new TargetPermanent(filter));
|
||||
ability.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster());
|
||||
ability.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster());
|
||||
this.addAbility(ability);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -11,7 +11,7 @@ import mage.constants.CardType;
|
|||
import mage.constants.SubType;
|
||||
import mage.filter.common.FilterArtifactPermanent;
|
||||
import mage.target.TargetPermanent;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -38,7 +38,7 @@ public final class SchemaThief extends CardImpl {
|
|||
// Whenever Schema Thief deals combat damage to a player, create a token that's a copy of target artifact that player controls.
|
||||
Ability ability = new DealsCombatDamageToAPlayerTriggeredAbility(new CreateTokenCopyTargetEffect(), false, true);
|
||||
ability.addTarget(new TargetPermanent(filter));
|
||||
ability.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster());
|
||||
ability.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster());
|
||||
this.addAbility(ability);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -19,7 +19,6 @@ import mage.target.TargetPermanent;
|
|||
import mage.target.common.TargetNonlandPermanent;
|
||||
import mage.util.CardUtil;
|
||||
|
||||
import java.util.Objects;
|
||||
import java.util.Optional;
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -215,12 +214,9 @@ class SchemingFenceManaEffect extends AsThoughEffectImpl implements AsThoughMana
|
|||
@Override
|
||||
public boolean applies(UUID objectId, Ability affectedAbility, Ability source, Game game, UUID playerId) {
|
||||
return source.isControlledBy(playerId)
|
||||
&& affectedAbility
|
||||
.getEffects()
|
||||
.stream()
|
||||
.map(effect -> effect.getValue("schemingFence"))
|
||||
.filter(Objects::nonNull)
|
||||
.anyMatch(source.getSourceId()::equals);
|
||||
&& CardUtil.getEffectValueFromAbility(affectedAbility, "schemingFence", UUID.class)
|
||||
.filter(source.getSourceId()::equals)
|
||||
.isPresent();
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
|||
|
|
@ -11,7 +11,7 @@ import mage.constants.CardType;
|
|||
import mage.constants.SubType;
|
||||
import mage.filter.common.FilterArtifactOrEnchantmentPermanent;
|
||||
import mage.target.TargetPermanent;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -36,7 +36,7 @@ public final class ScionOfCalamity extends CardImpl {
|
|||
// Whenever Scion of Calamity deals combat damage to a player, destroy target artifact or enchantment that player controls.
|
||||
Ability ability = new DealsCombatDamageToAPlayerTriggeredAbility(new DestroyTargetEffect(), false, true);
|
||||
ability.addTarget(new TargetPermanent(filter));
|
||||
ability.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster());
|
||||
ability.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster());
|
||||
this.addAbility(ability);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -14,7 +14,7 @@ import mage.constants.SubType;
|
|||
import mage.filter.FilterCard;
|
||||
import mage.filter.common.FilterCreatureCard;
|
||||
import mage.target.common.TargetCardInGraveyard;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -39,7 +39,7 @@ public final class ScionOfDarkness extends CardImpl {
|
|||
// Whenever Scion of Darkness deals combat damage to a player, you may put target creature card from that player's graveyard onto the battlefield under your control.
|
||||
Ability ability = new DealsCombatDamageToAPlayerTriggeredAbility(new ReturnFromGraveyardToBattlefieldTargetEffect(), true, true);
|
||||
ability.addTarget(new TargetCardInGraveyard(filter));
|
||||
ability.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster(true));
|
||||
ability.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster(true));
|
||||
this.addAbility(ability);
|
||||
|
||||
// Cycling {3}
|
||||
|
|
|
|||
|
|
@ -14,6 +14,7 @@ import mage.counters.CounterType;
|
|||
import mage.filter.StaticFilters;
|
||||
import mage.game.Game;
|
||||
import mage.game.permanent.Permanent;
|
||||
import mage.util.CardUtil;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -68,17 +69,13 @@ class SharpEyedRookieTriggeredAbility extends EntersBattlefieldAllTriggeredAbili
|
|||
@Override
|
||||
public boolean checkInterveningIfClause(Game game) {
|
||||
Permanent sourcePermanent = getSourcePermanentOrLKI(game);
|
||||
Permanent permanentEntering = (Permanent) this
|
||||
.getEffects()
|
||||
.stream()
|
||||
.map(effect -> effect.getValue("permanentEnteringBattlefield"))
|
||||
.findFirst()
|
||||
.orElse(null);
|
||||
return sourcePermanent != null
|
||||
&& permanentEntering != null
|
||||
&& sourcePermanent.isCreature(game)
|
||||
&& permanentEntering.isCreature(game)
|
||||
&& (permanentEntering.getPower().getValue() > sourcePermanent.getPower().getValue()
|
||||
|| permanentEntering.getToughness().getValue() > sourcePermanent.getToughness().getValue());
|
||||
&& CardUtil
|
||||
.getEffectValueFromAbility(this, "permanentEnteringBattlefield", Permanent.class)
|
||||
.filter(permanent -> permanent.isCreature(game))
|
||||
.filter(permanent -> sourcePermanent.getPower().getValue() < permanent.getPower().getValue()
|
||||
|| sourcePermanent.getToughness().getValue() < permanent.getToughness().getValue())
|
||||
.isPresent();
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -14,7 +14,7 @@ import mage.constants.SubType;
|
|||
import mage.filter.common.FilterCreaturePermanent;
|
||||
import mage.target.TargetPermanent;
|
||||
import mage.target.common.TargetCreaturePermanent;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -40,7 +40,7 @@ public final class SigilOfSleep extends CardImpl {
|
|||
Effect effect = new ReturnToHandTargetEffect();
|
||||
ability = new DealsDamageToAPlayerAttachedTriggeredAbility(effect, "enchanted", false, true, false);
|
||||
ability.addTarget(new TargetCreaturePermanent(filter));
|
||||
ability.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster());
|
||||
ability.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster());
|
||||
this.addAbility(ability);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -13,7 +13,7 @@ import mage.constants.CardType;
|
|||
import mage.constants.SubType;
|
||||
import mage.filter.common.FilterCreaturePermanent;
|
||||
import mage.target.TargetPermanent;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -35,7 +35,7 @@ public final class SkirkCommando extends CardImpl {
|
|||
//Whenever Skirk Commando deals combat damage to a player, you may have it deal 2 damage to target creature that player controls.
|
||||
Ability ability = new DealsCombatDamageToAPlayerTriggeredAbility(new DamageTargetEffect(2), true, true);
|
||||
ability.addTarget(new TargetPermanent(filter));
|
||||
ability.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster());
|
||||
ability.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster());
|
||||
this.addAbility(ability);
|
||||
|
||||
//Morph {2}{R} (You may cast this card face down as a 2/2 creature for 3. Turn it face up any time for its morph cost.)
|
||||
|
|
|
|||
|
|
@ -16,7 +16,7 @@ import mage.filter.FilterCard;
|
|||
import mage.filter.common.FilterControlledCreaturePermanent;
|
||||
import mage.filter.predicate.permanent.UnblockedPredicate;
|
||||
import mage.target.common.TargetCardInGraveyard;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -47,7 +47,7 @@ public final class Skullsnatcher extends CardImpl {
|
|||
Effect effect = new ExileTargetEffect(null, "", Zone.GRAVEYARD);
|
||||
Ability ability = new DealsCombatDamageToAPlayerTriggeredAbility(effect, false, true);
|
||||
ability.addTarget(new TargetCardInGraveyard(0, 2, filterGraveyardCard));
|
||||
ability.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster(true));
|
||||
ability.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster(true));
|
||||
this.addAbility(ability);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -13,7 +13,7 @@ import mage.constants.CardType;
|
|||
import mage.constants.SubType;
|
||||
import mage.filter.common.FilterCreaturePermanent;
|
||||
import mage.target.TargetPermanent;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -35,7 +35,7 @@ public final class SnappingThragg extends CardImpl {
|
|||
// Whenever Snapping Thragg deals combat damage to a player, you may have it deal 3 damage to target creature that player controls.
|
||||
Ability ability = new DealsCombatDamageToAPlayerTriggeredAbility(new DamageTargetEffect(3), true, true);
|
||||
ability.addTarget(new TargetPermanent(filter));
|
||||
ability.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster());
|
||||
ability.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster());
|
||||
this.addAbility(ability);
|
||||
|
||||
// Morph {4}{R}{R}
|
||||
|
|
|
|||
|
|
@ -11,7 +11,7 @@ import mage.constants.CardType;
|
|||
import mage.constants.SubType;
|
||||
import mage.filter.common.FilterCreaturePermanent;
|
||||
import mage.target.TargetPermanent;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -36,7 +36,7 @@ public final class SparkMage extends CardImpl {
|
|||
new DamageTargetEffect(1), true, true
|
||||
).withRuleTextReplacement(false);
|
||||
ability.addTarget(new TargetPermanent(filter));
|
||||
ability.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster());
|
||||
ability.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster());
|
||||
this.addAbility(ability);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -12,7 +12,7 @@ import mage.constants.CardType;
|
|||
import mage.constants.SubType;
|
||||
import mage.filter.common.FilterArtifactOrEnchantmentPermanent;
|
||||
import mage.target.TargetPermanent;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -38,7 +38,7 @@ public final class SunderShaman extends CardImpl {
|
|||
// Whenever Sunder Shaman deals combat damage to a player, destroy target artifact or enchantment that player controls.
|
||||
Ability ability = new DealsCombatDamageToAPlayerTriggeredAbility(new DestroyTargetEffect(), false, true);
|
||||
ability.addTarget(new TargetPermanent(filter));
|
||||
ability.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster());
|
||||
ability.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster());
|
||||
this.addAbility(ability);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -15,7 +15,7 @@ import mage.filter.common.FilterCreaturePermanent;
|
|||
import mage.filter.predicate.Predicates;
|
||||
import mage.filter.predicate.mageobject.ColorPredicate;
|
||||
import mage.target.TargetPermanent;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -45,7 +45,7 @@ public final class ThroatSlitter extends CardImpl {
|
|||
// Whenever Throat Slitter deals combat damage to a player, destroy target nonblack creature that player controls.
|
||||
Ability ability = new DealsCombatDamageToAPlayerTriggeredAbility(new DestroyTargetEffect(), false, true);
|
||||
ability.addTarget(new TargetPermanent(filter));
|
||||
ability.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster());
|
||||
ability.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster());
|
||||
this.addAbility(ability);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -15,7 +15,7 @@ import mage.filter.FilterCard;
|
|||
import mage.filter.predicate.Predicates;
|
||||
import mage.filter.predicate.card.FaceDownPredicate;
|
||||
import mage.target.common.TargetCardInExile;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -49,7 +49,7 @@ public final class TimeReaper extends CardImpl {
|
|||
Ability ability = new DealsCombatDamageToAPlayerTriggeredAbility(new PutOnLibraryTargetEffect(false), false, true);
|
||||
ability.addEffect(new GainLifeEffect(3).concatBy("If you do,")); //I don't think the move can fail? If there's no target then the trigger won't happen
|
||||
ability.addTarget(new TargetCardInExile(filter));
|
||||
ability.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster(true));
|
||||
ability.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster(true));
|
||||
ability.withFlavorWord("Consume Anomaly");
|
||||
this.addAbility(ability);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -16,7 +16,7 @@ import mage.filter.FilterCard;
|
|||
import mage.filter.common.FilterPermanentCard;
|
||||
import mage.filter.predicate.Predicates;
|
||||
import mage.target.common.TargetCardInGraveyard;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -48,7 +48,7 @@ public final class TinybonesThePickpocket extends CardImpl {
|
|||
OneShotEffect effect = new MayCastTargetCardEffect(CastManaAdjustment.AS_THOUGH_ANY_MANA_TYPE, false);
|
||||
Ability ability = new DealsCombatDamageToAPlayerTriggeredAbility(effect, false, true);
|
||||
ability.addTarget(new TargetCardInGraveyard(filter));
|
||||
ability.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster(true));
|
||||
ability.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster(true));
|
||||
this.addAbility(ability);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -12,7 +12,7 @@ import mage.constants.CardType;
|
|||
import mage.constants.SubType;
|
||||
import mage.filter.common.FilterArtifactOrEnchantmentPermanent;
|
||||
import mage.target.TargetPermanent;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -36,7 +36,7 @@ public final class TrygonPredator extends CardImpl {
|
|||
// Whenever Trygon Predator deals combat damage to a player, you may destroy target artifact or enchantment that player controls.
|
||||
Ability ability = new DealsCombatDamageToAPlayerTriggeredAbility(new DestroyTargetEffect(), true, true);
|
||||
ability.addTarget(new TargetPermanent(filter));
|
||||
ability.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster());
|
||||
ability.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster());
|
||||
this.addAbility(ability);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -17,8 +17,8 @@ import mage.constants.Duration;
|
|||
import mage.constants.SubType;
|
||||
import mage.game.Game;
|
||||
import mage.game.permanent.token.custom.CreatureToken;
|
||||
import mage.util.CardUtil;
|
||||
|
||||
import java.util.Objects;
|
||||
import java.util.UUID;
|
||||
|
||||
/**
|
||||
|
|
@ -65,11 +65,8 @@ enum WeatherseedTotemCondition implements Condition {
|
|||
|
||||
@Override
|
||||
public boolean apply(Game game, Ability source) {
|
||||
return source
|
||||
.getEffects()
|
||||
.stream()
|
||||
.map(effect -> effect.getValue("permanentWasCreature"))
|
||||
.filter(Objects::nonNull)
|
||||
.anyMatch(Boolean.class::cast);
|
||||
return CardUtil
|
||||
.getEffectValueFromAbility(source, "permanentWasCreature", Boolean.class)
|
||||
.orElse(false);
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -17,7 +17,7 @@ import mage.constants.SuperType;
|
|||
import mage.filter.FilterCard;
|
||||
import mage.filter.common.FilterInstantOrSorceryCard;
|
||||
import mage.target.common.TargetCardInGraveyard;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -50,7 +50,7 @@ public final class WrexialTheRisenDeep extends CardImpl {
|
|||
+ ThatSpellGraveyardExileReplacementEffect.RULE_A);
|
||||
Ability ability = new DealsCombatDamageToAPlayerTriggeredAbility(effect, false, true);
|
||||
ability.addTarget(new TargetCardInGraveyard(filter));
|
||||
ability.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster(true));
|
||||
ability.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster(true));
|
||||
this.addAbility(ability);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -22,7 +22,7 @@ import mage.game.permanent.Permanent;
|
|||
import mage.players.Player;
|
||||
import mage.target.common.TargetCardInGraveyard;
|
||||
import mage.target.common.TargetControlledPermanent;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -61,7 +61,7 @@ public final class ZarethSanTheTrickster extends CardImpl {
|
|||
// Whenever Zareth San deals combat damage to a player, you may put target permanent card from that player's graveyard onto the battlefield under your control.
|
||||
Ability ability2 = new DealsCombatDamageToAPlayerTriggeredAbility(new ReturnFromGraveyardToBattlefieldTargetEffect(), true, true);
|
||||
ability2.addTarget(new TargetCardInGraveyard(filterCardGraveyard));
|
||||
ability2.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster(true));
|
||||
ability2.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster(true));
|
||||
this.addAbility(ability2);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -12,7 +12,7 @@ import mage.constants.SubType;
|
|||
import mage.constants.Zone;
|
||||
import mage.filter.FilterCard;
|
||||
import mage.target.common.TargetCardInGraveyard;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
import java.util.UUID;
|
||||
|
||||
|
|
@ -34,7 +34,7 @@ public final class ZombieCannibal extends CardImpl {
|
|||
Effect effect = new ExileTargetEffect(null, "", Zone.GRAVEYARD);
|
||||
Ability ability = new DealsCombatDamageToAPlayerTriggeredAbility(effect, true, true);
|
||||
ability.addTarget(new TargetCardInGraveyard(filterGraveyardCard));
|
||||
ability.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster(true));
|
||||
ability.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster(true));
|
||||
this.addAbility(ability);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -237,9 +237,9 @@ public final class AssassinsCreed extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Poison-Blade Mentor", 288, Rarity.UNCOMMON, mage.cards.p.PoisonBladeMentor.class));
|
||||
cards.add(new SetCardInfo("Propaganda", 195, Rarity.UNCOMMON, mage.cards.p.Propaganda.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Propaganda", 85, Rarity.UNCOMMON, mage.cards.p.Propaganda.class, NON_FULL_USE_VARIOUS));
|
||||
//cards.add(new SetCardInfo("Ratonhnhake:ton", 150, Rarity.RARE, mage.cards.r.Ratonhnhaketon.class, NON_FULL_USE_VARIOUS));
|
||||
//cards.add(new SetCardInfo("Ratonhnhake:ton", 244, Rarity.RARE, mage.cards.r.Ratonhnhaketon.class, NON_FULL_USE_VARIOUS));
|
||||
//cards.add(new SetCardInfo("Ratonhnhake:ton", 62, Rarity.RARE, mage.cards.r.Ratonhnhakton.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Ratonhnhaketon", 150, Rarity.RARE, mage.cards.r.Ratonhnhaketon.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Ratonhnhaketon", 244, Rarity.RARE, mage.cards.r.Ratonhnhaketon.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Ratonhnhaketon", 62, Rarity.RARE, mage.cards.r.Ratonhnhaketon.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Raven Clan War-Axe", 297, Rarity.RARE, mage.cards.r.RavenClanWarAxe.class));
|
||||
cards.add(new SetCardInfo("Reconnaissance", 179, Rarity.UNCOMMON, mage.cards.r.Reconnaissance.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Reconnaissance", 82, Rarity.UNCOMMON, mage.cards.r.Reconnaissance.class, NON_FULL_USE_VARIOUS));
|
||||
|
|
|
|||
|
|
@ -206,9 +206,9 @@ public final class CommanderLegendsBattleForBaldursGate extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Cloudkill", 121, Rarity.UNCOMMON, mage.cards.c.Cloudkill.class));
|
||||
cards.add(new SetCardInfo("Colossal Badger", 223, Rarity.COMMON, mage.cards.c.ColossalBadger.class));
|
||||
cards.add(new SetCardInfo("Command Tower", 351, Rarity.COMMON, mage.cards.c.CommandTower.class));
|
||||
//cards.add(new SetCardInfo("Commander Liara Portyr", 270, Rarity.UNCOMMON, mage.cards.c.CommanderLiaraPortyr.class, NON_FULL_USE_VARIOUS));
|
||||
//cards.add(new SetCardInfo("Commander Liara Portyr", 418, Rarity.UNCOMMON, mage.cards.c.CommanderLiaraPortyr.class, NON_FULL_USE_VARIOUS));
|
||||
//cards.add(new SetCardInfo("Commander Liara Portyr", 529, Rarity.UNCOMMON, mage.cards.c.CommanderLiaraPortyr.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Commander Liara Portyr", 270, Rarity.UNCOMMON, mage.cards.c.CommanderLiaraPortyr.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Commander Liara Portyr", 418, Rarity.UNCOMMON, mage.cards.c.CommanderLiaraPortyr.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Commander Liara Portyr", 529, Rarity.UNCOMMON, mage.cards.c.CommanderLiaraPortyr.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Compulsive Research", 715, Rarity.COMMON, mage.cards.c.CompulsiveResearch.class));
|
||||
cards.add(new SetCardInfo("Cone of Cold", 61, Rarity.UNCOMMON, mage.cards.c.ConeOfCold.class));
|
||||
cards.add(new SetCardInfo("Consuming Aberration", 840, Rarity.RARE, mage.cards.c.ConsumingAberration.class));
|
||||
|
|
@ -571,8 +571,8 @@ public final class CommanderLegendsBattleForBaldursGate extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Mindblade Render", 762, Rarity.RARE, mage.cards.m.MindbladeRender.class));
|
||||
cards.add(new SetCardInfo("Mindcrank", 866, Rarity.UNCOMMON, mage.cards.m.Mindcrank.class));
|
||||
cards.add(new SetCardInfo("Minimus Containment", 34, Rarity.COMMON, mage.cards.m.MinimusContainment.class));
|
||||
//cards.add(new SetCardInfo("Minsc & Boo, Timeless Heroes", 285, Rarity.MYTHIC, mage.cards.m.MinscAndBooTimelessHeroes.class, NON_FULL_USE_VARIOUS));
|
||||
//cards.add(new SetCardInfo("Minsc & Boo, Timeless Heroes", 363, Rarity.MYTHIC, mage.cards.m.MinscAndBooTimelessHeroes.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Minsc & Boo, Timeless Heroes", 285, Rarity.MYTHIC, mage.cards.m.MinscBooTimelessHeroes.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Minsc & Boo, Timeless Heroes", 363, Rarity.MYTHIC, mage.cards.m.MinscBooTimelessHeroes.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Minthara, Merciless Soul", 286, Rarity.UNCOMMON, mage.cards.m.MintharaMercilessSoul.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Minthara, Merciless Soul", 432, Rarity.UNCOMMON, mage.cards.m.MintharaMercilessSoul.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Minthara, Merciless Soul", 543, Rarity.UNCOMMON, mage.cards.m.MintharaMercilessSoul.class, NON_FULL_USE_VARIOUS));
|
||||
|
|
|
|||
|
|
@ -278,6 +278,9 @@ public final class DuskmournHouseOfHorror extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Razorkin Needlehead", 153, Rarity.RARE, mage.cards.r.RazorkinNeedlehead.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Razorkin Needlehead", 347, Rarity.RARE, mage.cards.r.RazorkinNeedlehead.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Razortrap Gorge", 267, Rarity.COMMON, mage.cards.r.RazortrapGorge.class));
|
||||
cards.add(new SetCardInfo("Reluctant Role Model", 26, Rarity.RARE, mage.cards.r.ReluctantRoleModel.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Reluctant Role Model", 289, Rarity.RARE, mage.cards.r.ReluctantRoleModel.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Reluctant Role Model", 303, Rarity.RARE, mage.cards.r.ReluctantRoleModel.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Resurrected Cultist", 115, Rarity.COMMON, mage.cards.r.ResurrectedCultist.class));
|
||||
cards.add(new SetCardInfo("Rip, Spawn Hunter", 228, Rarity.RARE, mage.cards.r.RipSpawnHunter.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Rip, Spawn Hunter", 362, Rarity.RARE, mage.cards.r.RipSpawnHunter.class, NON_FULL_USE_VARIOUS));
|
||||
|
|
@ -366,7 +369,9 @@ public final class DuskmournHouseOfHorror extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Valgavoth's Lair", 327, Rarity.RARE, mage.cards.v.ValgavothsLair.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Valgavoth's Onslaught", 204, Rarity.RARE, mage.cards.v.ValgavothsOnslaught.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Valgavoth's Onslaught", 324, Rarity.RARE, mage.cards.v.ValgavothsOnslaught.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Valgavoth, Terror Eater", 120, Rarity.MYTHIC, mage.cards.v.ValgavothTerrorEater.class));
|
||||
cards.add(new SetCardInfo("Valgavoth, Terror Eater", 120, Rarity.MYTHIC, mage.cards.v.ValgavothTerrorEater.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Valgavoth, Terror Eater", 352, Rarity.MYTHIC, mage.cards.v.ValgavothTerrorEater.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Valgavoth, Terror Eater", 407, Rarity.MYTHIC, mage.cards.v.ValgavothTerrorEater.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Vanish from Sight", 82, Rarity.COMMON, mage.cards.v.VanishFromSight.class));
|
||||
cards.add(new SetCardInfo("Vengeful Possession", 162, Rarity.UNCOMMON, mage.cards.v.VengefulPossession.class));
|
||||
cards.add(new SetCardInfo("Veteran Survivor", 40, Rarity.UNCOMMON, mage.cards.v.VeteranSurvivor.class));
|
||||
|
|
|
|||
|
|
@ -26,6 +26,8 @@ public class EternalWeekend extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Gush", "2022a", Rarity.RARE, mage.cards.g.Gush.class, RETRO_ART));
|
||||
cards.add(new SetCardInfo("Mental Misstep", "2023a", Rarity.RARE, mage.cards.m.MentalMisstep.class, RETRO_ART));
|
||||
cards.add(new SetCardInfo("Ponder", "2022b", Rarity.RARE, mage.cards.p.Ponder.class, RETRO_ART));
|
||||
cards.add(new SetCardInfo("Tendrils of Agony", "2025a", Rarity.RARE, mage.cards.t.TendrilsOfAgony.class, RETRO_ART));
|
||||
cards.add(new SetCardInfo("Tinker", "2024a", Rarity.MYTHIC, mage.cards.t.Tinker.class, RETRO_ART));
|
||||
cards.add(new SetCardInfo("Trinisphere", "2025b", Rarity.MYTHIC, mage.cards.t.Trinisphere.class, RETRO_ART));
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -43,7 +43,7 @@ public final class RavnicaClueEdition extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Boros Garrison", 231, Rarity.COMMON, mage.cards.b.BorosGarrison.class));
|
||||
cards.add(new SetCardInfo("Boros Guildgate", 232, Rarity.COMMON, mage.cards.b.BorosGuildgate.class));
|
||||
cards.add(new SetCardInfo("Boros Signet", 220, Rarity.COMMON, mage.cards.b.BorosSignet.class));
|
||||
//cards.add(new SetCardInfo("Boros Strike-Captain", 25, Rarity.RARE, mage.cards.b.BorosStrikeCaptain.class));
|
||||
cards.add(new SetCardInfo("Boros Strike-Captain", 25, Rarity.RARE, mage.cards.b.BorosStrikeCaptain.class));
|
||||
cards.add(new SetCardInfo("Breeding Pool", 275, Rarity.RARE, mage.cards.b.BreedingPool.class));
|
||||
cards.add(new SetCardInfo("Candlestick", 8, Rarity.UNCOMMON, mage.cards.c.Candlestick.class));
|
||||
cards.add(new SetCardInfo("Carnage Interpreter", 26, Rarity.RARE, mage.cards.c.CarnageInterpreter.class));
|
||||
|
|
@ -64,7 +64,7 @@ public final class RavnicaClueEdition extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Corpse Churn", 107, Rarity.COMMON, mage.cards.c.CorpseChurn.class));
|
||||
cards.add(new SetCardInfo("Cosmotronic Wave", 129, Rarity.COMMON, mage.cards.c.CosmotronicWave.class));
|
||||
cards.add(new SetCardInfo("Council's Judgment", 57, Rarity.RARE, mage.cards.c.CouncilsJudgment.class));
|
||||
//cards.add(new SetCardInfo("Covetous Elegy", 29, Rarity.RARE, mage.cards.c.CovetousElegy.class));
|
||||
cards.add(new SetCardInfo("Covetous Elegy", 29, Rarity.RARE, mage.cards.c.CovetousElegy.class));
|
||||
cards.add(new SetCardInfo("Curse of Chains", 183, Rarity.COMMON, mage.cards.c.CurseOfChains.class));
|
||||
cards.add(new SetCardInfo("Dagger Caster", 130, Rarity.UNCOMMON, mage.cards.d.DaggerCaster.class));
|
||||
cards.add(new SetCardInfo("Daggerclaw Imp", 108, Rarity.UNCOMMON, mage.cards.d.DaggerclawImp.class));
|
||||
|
|
@ -107,7 +107,7 @@ public final class RavnicaClueEdition extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Fresh-Faced Recruit", 192, Rarity.COMMON, mage.cards.f.FreshFacedRecruit.class));
|
||||
cards.add(new SetCardInfo("Frostburn Weird", 193, Rarity.COMMON, mage.cards.f.FrostburnWeird.class));
|
||||
cards.add(new SetCardInfo("Fungal Rebirth", 163, Rarity.UNCOMMON, mage.cards.f.FungalRebirth.class));
|
||||
//cards.add(new SetCardInfo("Furious Spinesplitter", 33, Rarity.UNCOMMON, mage.cards.f.FuriousSpinesplitter.class));
|
||||
cards.add(new SetCardInfo("Furious Spinesplitter", 33, Rarity.UNCOMMON, mage.cards.f.FuriousSpinesplitter.class));
|
||||
cards.add(new SetCardInfo("Giant Adephage", 164, Rarity.MYTHIC, mage.cards.g.GiantAdephage.class));
|
||||
cards.add(new SetCardInfo("Gift of Strength", 165, Rarity.COMMON, mage.cards.g.GiftOfStrength.class));
|
||||
cards.add(new SetCardInfo("Glorifier of Dusk", 62, Rarity.UNCOMMON, mage.cards.g.GlorifierOfDusk.class));
|
||||
|
|
@ -168,14 +168,14 @@ public final class RavnicaClueEdition extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Master Biomancer", 200, Rarity.MYTHIC, mage.cards.m.MasterBiomancer.class));
|
||||
cards.add(new SetCardInfo("Mastermind Plum", 3, Rarity.RARE, mage.cards.m.MastermindPlum.class));
|
||||
cards.add(new SetCardInfo("Mausoleum Turnkey", 116, Rarity.UNCOMMON, mage.cards.m.MausoleumTurnkey.class));
|
||||
//cards.add(new SetCardInfo("Memory Vampire", 38, Rarity.RARE, mage.cards.m.MemoryVampire.class));
|
||||
cards.add(new SetCardInfo("Memory Vampire", 38, Rarity.RARE, mage.cards.m.MemoryVampire.class));
|
||||
cards.add(new SetCardInfo("Mighty Leap", 66, Rarity.COMMON, mage.cards.m.MightyLeap.class));
|
||||
cards.add(new SetCardInfo("Mountain", 266, Rarity.LAND, mage.cards.basiclands.Mountain.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Mountain", 267, Rarity.LAND, mage.cards.basiclands.Mountain.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Mountain", 268, Rarity.LAND, mage.cards.basiclands.Mountain.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Mountain", 269, Rarity.LAND, mage.cards.basiclands.Mountain.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Nissa's Judgment", 170, Rarity.UNCOMMON, mage.cards.n.NissasJudgment.class));
|
||||
//cards.add(new SetCardInfo("Ordruun Mentor", 39, Rarity.UNCOMMON, mage.cards.o.OrdruunMentor.class));
|
||||
cards.add(new SetCardInfo("Ordruun Mentor", 39, Rarity.UNCOMMON, mage.cards.o.OrdruunMentor.class));
|
||||
cards.add(new SetCardInfo("Ornery Goblin", 143, Rarity.COMMON, mage.cards.o.OrneryGoblin.class));
|
||||
cards.add(new SetCardInfo("Orzhov Basilica", 241, Rarity.COMMON, mage.cards.o.OrzhovBasilica.class));
|
||||
cards.add(new SetCardInfo("Orzhov Guildgate", 242, Rarity.COMMON, mage.cards.o.OrzhovGuildgate.class));
|
||||
|
|
@ -210,7 +210,7 @@ public final class RavnicaClueEdition extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Reduce to Ashes", 145, Rarity.COMMON, mage.cards.r.ReduceToAshes.class));
|
||||
cards.add(new SetCardInfo("Repeal", 94, Rarity.COMMON, mage.cards.r.Repeal.class));
|
||||
cards.add(new SetCardInfo("Rescuer Sphinx", 95, Rarity.UNCOMMON, mage.cards.r.RescuerSphinx.class));
|
||||
//cards.add(new SetCardInfo("Resonance Technician", 41, Rarity.RARE, mage.cards.r.ResonanceTechnician.class));
|
||||
cards.add(new SetCardInfo("Resonance Technician", 41, Rarity.RARE, mage.cards.r.ResonanceTechnician.class));
|
||||
cards.add(new SetCardInfo("Ribbons of Night", 120, Rarity.UNCOMMON, mage.cards.r.RibbonsOfNight.class));
|
||||
cards.add(new SetCardInfo("Ripscale Predator", 146, Rarity.COMMON, mage.cards.r.RipscalePredator.class));
|
||||
cards.add(new SetCardInfo("Roaming Ghostlight", 96, Rarity.COMMON, mage.cards.r.RoamingGhostlight.class));
|
||||
|
|
|
|||
|
|
@ -38,7 +38,7 @@ public class SecretLairDrop extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Reaper King", 9, Rarity.MYTHIC, mage.cards.r.ReaperKing.class));
|
||||
cards.add(new SetCardInfo("Sliver Overlord", 10, Rarity.MYTHIC, mage.cards.s.SliverOverlord.class));
|
||||
cards.add(new SetCardInfo("The Ur-Dragon", 11, Rarity.MYTHIC, mage.cards.t.TheUrDragon.class));
|
||||
cards.add(new SetCardInfo("Bitterblossom", 12, Rarity.MYTHIC, mage.cards.b.Bitterblossom.class));
|
||||
cards.add(new SetCardInfo("Bitterblossom", 12, Rarity.MYTHIC, mage.cards.b.Bitterblossom.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Goblin Bushwhacker", 17, Rarity.RARE, mage.cards.g.GoblinBushwhacker.class));
|
||||
cards.add(new SetCardInfo("Goblin Sharpshooter", 18, Rarity.RARE, mage.cards.g.GoblinSharpshooter.class));
|
||||
cards.add(new SetCardInfo("Goblin King", 19, Rarity.RARE, mage.cards.g.GoblinKing.class, NON_FULL_USE_VARIOUS));
|
||||
|
|
@ -101,7 +101,7 @@ public class SecretLairDrop extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Mogis, God of Slaughter", 78, Rarity.MYTHIC, mage.cards.m.MogisGodOfSlaughter.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Keranos, God of Storms", 79, Rarity.MYTHIC, mage.cards.k.KeranosGodOfStorms.class));
|
||||
cards.add(new SetCardInfo("Nylea, God of the Hunt", 80, Rarity.MYTHIC, mage.cards.n.NyleaGodOfTheHunt.class));
|
||||
cards.add(new SetCardInfo("Xenagos, God of Revels", 81, Rarity.MYTHIC, mage.cards.x.XenagosGodOfRevels.class));
|
||||
cards.add(new SetCardInfo("Xenagos, God of Revels", 81, Rarity.MYTHIC, mage.cards.x.XenagosGodOfRevels.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Pharika, God of Affliction", 82, Rarity.MYTHIC, mage.cards.p.PharikaGodOfAffliction.class));
|
||||
cards.add(new SetCardInfo("Lightning Bolt", 83, Rarity.RARE, mage.cards.l.LightningBolt.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Lightning Bolt", 84, Rarity.RARE, mage.cards.l.LightningBolt.class, NON_FULL_USE_VARIOUS));
|
||||
|
|
@ -170,9 +170,9 @@ public class SecretLairDrop extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Malik, Grim Manipulator", 147, Rarity.MYTHIC, mage.cards.m.MalikGrimManipulator.class));
|
||||
cards.add(new SetCardInfo("Admonition Angel", 154, Rarity.MYTHIC, mage.cards.a.AdmonitionAngel.class));
|
||||
cards.add(new SetCardInfo("Roil Elemental", 155, Rarity.RARE, mage.cards.r.RoilElemental.class));
|
||||
cards.add(new SetCardInfo("Zulaport Cutthroat", 156, Rarity.RARE, mage.cards.z.ZulaportCutthroat.class));
|
||||
cards.add(new SetCardInfo("Zulaport Cutthroat", 156, Rarity.RARE, mage.cards.z.ZulaportCutthroat.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Warren Instigator", 157, Rarity.MYTHIC, mage.cards.w.WarrenInstigator.class));
|
||||
cards.add(new SetCardInfo("Avenger of Zendikar", 158, Rarity.MYTHIC, mage.cards.a.AvengerOfZendikar.class));
|
||||
cards.add(new SetCardInfo("Avenger of Zendikar", 158, Rarity.MYTHIC, mage.cards.a.AvengerOfZendikar.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Demonlord Belzenlok", 159, Rarity.MYTHIC, mage.cards.d.DemonlordBelzenlok.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Demonlord Belzenlok", "159*", Rarity.MYTHIC, mage.cards.d.DemonlordBelzenlok.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Griselbrand", 160, Rarity.MYTHIC, mage.cards.g.Griselbrand.class, NON_FULL_USE_VARIOUS));
|
||||
|
|
@ -198,7 +198,7 @@ public class SecretLairDrop extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Decree of Pain", 187, Rarity.RARE, mage.cards.d.DecreeOfPain.class));
|
||||
cards.add(new SetCardInfo("Gamble", 188, Rarity.RARE, mage.cards.g.Gamble.class));
|
||||
cards.add(new SetCardInfo("Nature's Lore", 189, Rarity.RARE, mage.cards.n.NaturesLore.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Soul-Scar Mage", 190, Rarity.RARE, mage.cards.s.SoulScarMage.class));
|
||||
cards.add(new SetCardInfo("Soul-Scar Mage", 190, Rarity.RARE, mage.cards.s.SoulScarMage.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Dryad of the Ilysian Grove", 191, Rarity.RARE, mage.cards.d.DryadOfTheIlysianGrove.class));
|
||||
cards.add(new SetCardInfo("Sakura-Tribe Elder", 192, Rarity.RARE, mage.cards.s.SakuraTribeElder.class));
|
||||
cards.add(new SetCardInfo("Spell Queller", 193, Rarity.RARE, mage.cards.s.SpellQueller.class));
|
||||
|
|
@ -212,7 +212,7 @@ public class SecretLairDrop extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Chromatic Lantern", 202, Rarity.RARE, mage.cards.c.ChromaticLantern.class));
|
||||
cards.add(new SetCardInfo("Commander's Sphere", 203, Rarity.RARE, mage.cards.c.CommandersSphere.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Darksteel Ingot", 204, Rarity.RARE, mage.cards.d.DarksteelIngot.class));
|
||||
cards.add(new SetCardInfo("Gilded Lotus", 205, Rarity.RARE, mage.cards.g.GildedLotus.class));
|
||||
cards.add(new SetCardInfo("Gilded Lotus", 205, Rarity.RARE, mage.cards.g.GildedLotus.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Exquisite Blood", 206, Rarity.RARE, mage.cards.e.ExquisiteBlood.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Night's Whisper", 207, Rarity.RARE, mage.cards.n.NightsWhisper.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Phyrexian Tower", 208, Rarity.RARE, mage.cards.p.PhyrexianTower.class));
|
||||
|
|
@ -223,7 +223,7 @@ public class SecretLairDrop extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Vorinclex, Voice of Hunger", 213, Rarity.MYTHIC, mage.cards.v.VorinclexVoiceOfHunger.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Heliod, Sun-Crowned", 214, Rarity.MYTHIC, mage.cards.h.HeliodSunCrowned.class));
|
||||
cards.add(new SetCardInfo("Goblin Rabblemaster", 215, Rarity.RARE, mage.cards.g.GoblinRabblemaster.class));
|
||||
cards.add(new SetCardInfo("Monastery Swiftspear", 216, Rarity.RARE, mage.cards.m.MonasterySwiftspear.class));
|
||||
cards.add(new SetCardInfo("Monastery Swiftspear", 216, Rarity.RARE, mage.cards.m.MonasterySwiftspear.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Boros Charm", 217, Rarity.RARE, mage.cards.b.BorosCharm.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Gisela, Blade of Goldnight", 218, Rarity.MYTHIC, mage.cards.g.GiselaBladeOfGoldnight.class));
|
||||
cards.add(new SetCardInfo("Frost Titan", 220, Rarity.MYTHIC, mage.cards.f.FrostTitan.class));
|
||||
|
|
@ -366,7 +366,7 @@ public class SecretLairDrop extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Cut // Ribbons", 367, Rarity.RARE, mage.cards.c.CutRibbons.class));
|
||||
cards.add(new SetCardInfo("Teferi's Puzzle Box", 368, Rarity.RARE, mage.cards.t.TeferisPuzzleBox.class));
|
||||
cards.add(new SetCardInfo("Generous Gift", 369, Rarity.RARE, mage.cards.g.GenerousGift.class));
|
||||
cards.add(new SetCardInfo("Chain Lightning", 370, Rarity.RARE, mage.cards.c.ChainLightning.class));
|
||||
cards.add(new SetCardInfo("Chain Lightning", 370, Rarity.RARE, mage.cards.c.ChainLightning.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Kodama's Reach", 371, Rarity.RARE, mage.cards.k.KodamasReach.class));
|
||||
cards.add(new SetCardInfo("Heirloom Blade", 372, Rarity.RARE, mage.cards.h.HeirloomBlade.class));
|
||||
cards.add(new SetCardInfo("Mulldrifter", 373, Rarity.RARE, mage.cards.m.Mulldrifter.class, NON_FULL_USE_VARIOUS));
|
||||
|
|
@ -472,7 +472,7 @@ public class SecretLairDrop extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Depala, Pilot Exemplar", 464, Rarity.RARE, mage.cards.d.DepalaPilotExemplar.class));
|
||||
cards.add(new SetCardInfo("Nomad Outpost", 465, Rarity.RARE, mage.cards.n.NomadOutpost.class));
|
||||
cards.add(new SetCardInfo("Island", 466, Rarity.LAND, mage.cards.basiclands.Island.class, FULL_ART_BFZ_VARIOUS));
|
||||
cards.add(new SetCardInfo("Concordant Crossroads", 467, Rarity.RARE, mage.cards.c.ConcordantCrossroads.class));
|
||||
cards.add(new SetCardInfo("Concordant Crossroads", 467, Rarity.RARE, mage.cards.c.ConcordantCrossroads.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Ghost Quarter", 468, Rarity.RARE, mage.cards.g.GhostQuarter.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Ash Barrens", 469, Rarity.RARE, mage.cards.a.AshBarrens.class));
|
||||
cards.add(new SetCardInfo("Command Beacon", 470, Rarity.RARE, mage.cards.c.CommandBeacon.class, NON_FULL_USE_VARIOUS));
|
||||
|
|
@ -495,7 +495,7 @@ public class SecretLairDrop extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Mountain", 487, Rarity.LAND, mage.cards.basiclands.Mountain.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Forest", 488, Rarity.LAND, mage.cards.basiclands.Forest.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Akroma, Angel of Wrath", 489, Rarity.MYTHIC, mage.cards.a.AkromaAngelOfWrath.class));
|
||||
cards.add(new SetCardInfo("Mikaeus, the Unhallowed", 490, Rarity.MYTHIC, mage.cards.m.MikaeusTheUnhallowed.class));
|
||||
cards.add(new SetCardInfo("Mikaeus, the Unhallowed", 490, Rarity.MYTHIC, mage.cards.m.MikaeusTheUnhallowed.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Glissa Sunseeker", 491, Rarity.RARE, mage.cards.g.GlissaSunseeker.class));
|
||||
cards.add(new SetCardInfo("Olivia, Mobilized for War", 492, Rarity.MYTHIC, mage.cards.o.OliviaMobilizedForWar.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Kozilek, the Great Distortion", 493, Rarity.MYTHIC, mage.cards.k.KozilekTheGreatDistortion.class));
|
||||
|
|
@ -631,11 +631,11 @@ public class SecretLairDrop extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Basal Sliver", 629, Rarity.RARE, mage.cards.b.BasalSliver.class));
|
||||
cards.add(new SetCardInfo("Dregscape Sliver", 631, Rarity.RARE, mage.cards.d.DregscapeSliver.class));
|
||||
cards.add(new SetCardInfo("Leeching Sliver", 632, Rarity.RARE, mage.cards.l.LeechingSliver.class));
|
||||
cards.add(new SetCardInfo("Plague Sliver", 633, Rarity.RARE, mage.cards.p.PlagueSliver.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Plague Sliver", "633Ph", Rarity.RARE, mage.cards.p.PlagueSliver.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Plague Sliver", 633, Rarity.RARE, mage.cards.p.PlagueSliver.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Syphon Sliver", 634, Rarity.RARE, mage.cards.s.SyphonSliver.class));
|
||||
cards.add(new SetCardInfo("Toxin Sliver", 635, Rarity.RARE, mage.cards.t.ToxinSliver.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Toxin Sliver", "635Ph", Rarity.RARE, mage.cards.t.ToxinSliver.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Toxin Sliver", 635, Rarity.RARE, mage.cards.t.ToxinSliver.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Belligerent Sliver", 636, Rarity.RARE, mage.cards.b.BelligerentSliver.class));
|
||||
cards.add(new SetCardInfo("Blur Sliver", 637, Rarity.RARE, mage.cards.b.BlurSliver.class));
|
||||
cards.add(new SetCardInfo("Fury Sliver", 638, Rarity.RARE, mage.cards.f.FurySliver.class));
|
||||
|
|
@ -657,8 +657,8 @@ public class SecretLairDrop extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Quick Sliver", 655, Rarity.RARE, mage.cards.q.QuickSliver.class));
|
||||
cards.add(new SetCardInfo("Root Sliver", 656, Rarity.RARE, mage.cards.r.RootSliver.class));
|
||||
cards.add(new SetCardInfo("Tempered Sliver", 657, Rarity.RARE, mage.cards.t.TemperedSliver.class));
|
||||
cards.add(new SetCardInfo("Virulent Sliver", 659, Rarity.RARE, mage.cards.v.VirulentSliver.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Virulent Sliver", "659Ph", Rarity.RARE, mage.cards.v.VirulentSliver.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Virulent Sliver", 659, Rarity.RARE, mage.cards.v.VirulentSliver.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Cloudshredder Sliver", 660, Rarity.RARE, mage.cards.c.CloudshredderSliver.class));
|
||||
cards.add(new SetCardInfo("Crystalline Sliver", 661, Rarity.RARE, mage.cards.c.CrystallineSliver.class));
|
||||
cards.add(new SetCardInfo("Frenetic Sliver", 662, Rarity.RARE, mage.cards.f.FreneticSliver.class));
|
||||
|
|
@ -680,8 +680,8 @@ public class SecretLairDrop extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Torbran, Thane of Red Fell", 678, Rarity.RARE, mage.cards.t.TorbranThaneOfRedFell.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Ghost Quarter", 679, Rarity.RARE, mage.cards.g.GhostQuarter.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Shadowborn Apostle", 680, Rarity.RARE, mage.cards.s.ShadowbornApostle.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Shadowborn Apostle", 681, Rarity.RARE, mage.cards.s.ShadowbornApostle.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Shadowborn Apostle", "681Ph", Rarity.RARE, mage.cards.s.ShadowbornApostle.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Shadowborn Apostle", 681, Rarity.RARE, mage.cards.s.ShadowbornApostle.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Shadowborn Apostle", 682, Rarity.RARE, mage.cards.s.ShadowbornApostle.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Shadowborn Apostle", 683, Rarity.RARE, mage.cards.s.ShadowbornApostle.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Shadowborn Apostle", 684, Rarity.RARE, mage.cards.s.ShadowbornApostle.class, NON_FULL_USE_VARIOUS));
|
||||
|
|
@ -734,7 +734,7 @@ public class SecretLairDrop extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Seraph Sanctuary", 733, Rarity.RARE, mage.cards.s.SeraphSanctuary.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Grima Wormtongue", 734, Rarity.RARE, mage.cards.g.GrimaWormtongue.class));
|
||||
cards.add(new SetCardInfo("Gaea's Blessing", 735, Rarity.RARE, mage.cards.g.GaeasBlessing.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Colossus Hammer", 736, Rarity.RARE, mage.cards.c.ColossusHammer.class));
|
||||
cards.add(new SetCardInfo("Colossus Hammer", 736, Rarity.RARE, mage.cards.c.ColossusHammer.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Mountain Goat", 737, Rarity.RARE, mage.cards.m.MountainGoat.class));
|
||||
cards.add(new SetCardInfo("Woodland Cemetery", 738, Rarity.RARE, mage.cards.w.WoodlandCemetery.class));
|
||||
cards.add(new SetCardInfo("Isolated Chapel", 739, Rarity.RARE, mage.cards.i.IsolatedChapel.class));
|
||||
|
|
@ -811,17 +811,19 @@ public class SecretLairDrop extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Seven Dwarves", 813, Rarity.RARE, mage.cards.s.SevenDwarves.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Seven Dwarves", 814, Rarity.RARE, mage.cards.s.SevenDwarves.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Seven Dwarves", 815, Rarity.RARE, mage.cards.s.SevenDwarves.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Seven Dwarves", 816, Rarity.RARE, mage.cards.s.SevenDwarves.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Arcane Signet", 820, Rarity.RARE, mage.cards.a.ArcaneSignet.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Arcane Signet", "820*", Rarity.RARE, mage.cards.a.ArcaneSignet.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Echo of Eons", 821, Rarity.RARE, mage.cards.e.EchoOfEons.class, RETRO_ART));
|
||||
cards.add(new SetCardInfo("Hive Mind", 822, Rarity.RARE, mage.cards.h.HiveMind.class, RETRO_ART));
|
||||
cards.add(new SetCardInfo("Chaos Warp", 823, Rarity.RARE, mage.cards.c.ChaosWarp.class, RETRO_ART_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Evolving Wilds", 824, Rarity.RARE, mage.cards.e.EvolvingWilds.class, RETRO_ART_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Goblin Bombardment", 825, Rarity.RARE, mage.cards.g.GoblinBombardment.class));
|
||||
cards.add(new SetCardInfo("Goblin Bombardment", 825, Rarity.RARE, mage.cards.g.GoblinBombardment.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Kezzerdrix", 826, Rarity.RARE, mage.cards.k.Kezzerdrix.class));
|
||||
cards.add(new SetCardInfo("Norin the Wary", 827, Rarity.RARE, mage.cards.n.NorinTheWary.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Norin the Wary", "827b", Rarity.RARE, mage.cards.n.NorinTheWary.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Keen Duelist", 828, Rarity.RARE, mage.cards.k.KeenDuelist.class));
|
||||
cards.add(new SetCardInfo("Fatestitcher", 835, Rarity.RARE, mage.cards.f.Fatestitcher.class, RETRO_ART));
|
||||
cards.add(new SetCardInfo("Champion of the Perished", 837, Rarity.RARE, mage.cards.c.ChampionOfThePerished.class, RETRO_ART));
|
||||
cards.add(new SetCardInfo("Corpse Connoisseur", 838, Rarity.RARE, mage.cards.c.CorpseConnoisseur.class, RETRO_ART));
|
||||
cards.add(new SetCardInfo("Cryptbreaker", 839, Rarity.RARE, mage.cards.c.Cryptbreaker.class, RETRO_ART));
|
||||
|
|
@ -831,13 +833,16 @@ public class SecretLairDrop extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Haakon, Stromgald Scourge", 843, Rarity.RARE, mage.cards.h.HaakonStromgaldScourge.class, RETRO_ART));
|
||||
cards.add(new SetCardInfo("Headless Rider", 844, Rarity.RARE, mage.cards.h.HeadlessRider.class, RETRO_ART));
|
||||
cards.add(new SetCardInfo("Liliana's Standard Bearer", 845, Rarity.RARE, mage.cards.l.LilianasStandardBearer.class, RETRO_ART));
|
||||
cards.add(new SetCardInfo("Mikaeus, the Unhallowed", 846, Rarity.MYTHIC, mage.cards.m.MikaeusTheUnhallowed.class, RETRO_ART_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Pontiff of Blight", 848, Rarity.RARE, mage.cards.p.PontiffOfBlight.class, RETRO_ART));
|
||||
cards.add(new SetCardInfo("Ravenous Rotbelly", 849, Rarity.RARE, mage.cards.r.RavenousRotbelly.class, RETRO_ART));
|
||||
cards.add(new SetCardInfo("Relentless Dead", 850, Rarity.MYTHIC, mage.cards.r.RelentlessDead.class, RETRO_ART));
|
||||
cards.add(new SetCardInfo("Rotting Regisaur", 852, Rarity.RARE, mage.cards.r.RottingRegisaur.class, RETRO_ART));
|
||||
cards.add(new SetCardInfo("Tomb Tyrant", 854, Rarity.RARE, mage.cards.t.TombTyrant.class, RETRO_ART));
|
||||
cards.add(new SetCardInfo("Tormod, the Desecrator", 855, Rarity.RARE, mage.cards.t.TormodTheDesecrator.class, RETRO_ART));
|
||||
cards.add(new SetCardInfo("Vindictive Lich", 856, Rarity.RARE, mage.cards.v.VindictiveLich.class, RETRO_ART_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Diregraf Captain", 858, Rarity.RARE, mage.cards.d.DiregrafCaptain.class, RETRO_ART));
|
||||
cards.add(new SetCardInfo("Havengul Lich", 859, Rarity.MYTHIC, mage.cards.h.HavengulLich.class, RETRO_ART));
|
||||
cards.add(new SetCardInfo("Nekusar, the Mindrazer", 860, Rarity.MYTHIC, mage.cards.n.NekusarTheMindrazer.class, RETRO_ART_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Varina, Lich Queen", 861, Rarity.MYTHIC, mage.cards.v.VarinaLichQueen.class, RETRO_ART_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Wilhelt, the Rotcleaver", 862, Rarity.MYTHIC, mage.cards.w.WilheltTheRotcleaver.class, RETRO_ART));
|
||||
|
|
@ -859,11 +864,13 @@ public class SecretLairDrop extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Minsc & Boo, Timeless Heroes", 879, Rarity.MYTHIC, mage.cards.m.MinscBooTimelessHeroes.class));
|
||||
cards.add(new SetCardInfo("Stuffy Doll", 880, Rarity.RARE, mage.cards.s.StuffyDoll.class));
|
||||
cards.add(new SetCardInfo("Silence", 881, Rarity.RARE, mage.cards.s.Silence.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Winds of Abandon", 882, Rarity.RARE, mage.cards.w.WindsOfAbandon.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Culling the Weak", 883, Rarity.RARE, mage.cards.c.CullingTheWeak.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Fatal Push", 884, Rarity.RARE, mage.cards.f.FatalPush.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Young Wolf", 885, Rarity.RARE, mage.cards.y.YoungWolf.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Solve the Equation", 886, Rarity.RARE, mage.cards.s.SolveTheEquation.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Enduring Ideal", 887, Rarity.RARE, mage.cards.e.EnduringIdeal.class));
|
||||
cards.add(new SetCardInfo("Changeling Outcast", 894, Rarity.RARE, mage.cards.c.ChangelingOutcast.class));
|
||||
cards.add(new SetCardInfo("Helpful Hunter", 895, Rarity.RARE, mage.cards.h.HelpfulHunter.class));
|
||||
cards.add(new SetCardInfo("Spirited Companion", 896, Rarity.RARE, mage.cards.s.SpiritedCompanion.class));
|
||||
cards.add(new SetCardInfo("The Scarab God", 900, Rarity.MYTHIC, mage.cards.t.TheScarabGod.class));
|
||||
|
|
@ -874,6 +881,7 @@ public class SecretLairDrop extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Ignoble Hierarch", 906, Rarity.RARE, mage.cards.i.IgnobleHierarch.class));
|
||||
cards.add(new SetCardInfo("Seedborn Muse", 907, Rarity.RARE, mage.cards.s.SeedbornMuse.class));
|
||||
cards.add(new SetCardInfo("Arcane Signet", 908, Rarity.RARE, mage.cards.a.ArcaneSignet.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Gilded Lotus", 909, Rarity.RARE, mage.cards.g.GildedLotus.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Sol Ring", 910, Rarity.RARE, mage.cards.s.SolRing.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Elspeth, Knight-Errant", 1001, Rarity.MYTHIC, mage.cards.e.ElspethKnightErrant.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Patron Wizard", 1002, Rarity.RARE, mage.cards.p.PatronWizard.class));
|
||||
|
|
@ -896,10 +904,10 @@ public class SecretLairDrop extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Idyllic Tutor", 1020, Rarity.RARE, mage.cards.i.IdyllicTutor.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Swords to Plowshares", 1021, Rarity.RARE, mage.cards.s.SwordsToPlowshares.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Solve the Equation", 1022, Rarity.RARE, mage.cards.s.SolveTheEquation.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Praetor's Grasp", 1023, Rarity.RARE, mage.cards.p.PraetorsGrasp.class));
|
||||
cards.add(new SetCardInfo("Praetor's Grasp", 1023, Rarity.RARE, mage.cards.p.PraetorsGrasp.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Veil of Summer", 1024, Rarity.RARE, mage.cards.v.VeilOfSummer.class));
|
||||
cards.add(new SetCardInfo("Merciless Executioner", 1025, Rarity.RARE, mage.cards.m.MercilessExecutioner.class));
|
||||
cards.add(new SetCardInfo("Aggravated Assault", 1026, Rarity.RARE, mage.cards.a.AggravatedAssault.class));
|
||||
cards.add(new SetCardInfo("Aggravated Assault", 1026, Rarity.RARE, mage.cards.a.AggravatedAssault.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Krenko, Tin Street Kingpin", 1027, Rarity.RARE, mage.cards.k.KrenkoTinStreetKingpin.class));
|
||||
cards.add(new SetCardInfo("Zurgo Helmsmasher", 1028, Rarity.MYTHIC, mage.cards.z.ZurgoHelmsmasher.class));
|
||||
cards.add(new SetCardInfo("Skysovereign, Consul Flagship", 1029, Rarity.MYTHIC, mage.cards.s.SkysovereignConsulFlagship.class));
|
||||
|
|
@ -972,7 +980,7 @@ public class SecretLairDrop extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Deepglow Skate", 1093, Rarity.RARE, mage.cards.d.DeepglowSkate.class));
|
||||
cards.add(new SetCardInfo("Tireless Tracker", 1094, Rarity.RARE, mage.cards.t.TirelessTracker.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Contagion Engine", 1095, Rarity.RARE, mage.cards.c.ContagionEngine.class));
|
||||
cards.add(new SetCardInfo("Sword of Truth and Justice", 1096, Rarity.MYTHIC, mage.cards.s.SwordOfTruthAndJustice.class));
|
||||
cards.add(new SetCardInfo("Sword of Truth and Justice", 1096, Rarity.MYTHIC, mage.cards.s.SwordOfTruthAndJustice.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Laboratory Maniac", 1097, Rarity.RARE, mage.cards.l.LaboratoryManiac.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Stitcher's Supplier", 1098, Rarity.RARE, mage.cards.s.StitchersSupplier.class));
|
||||
cards.add(new SetCardInfo("Beast Whisperer", 1099, Rarity.RARE, mage.cards.b.BeastWhisperer.class));
|
||||
|
|
@ -1168,7 +1176,7 @@ public class SecretLairDrop extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Grand Abolisher", 1285, Rarity.RARE, mage.cards.g.GrandAbolisher.class));
|
||||
cards.add(new SetCardInfo("Selfless Savior", 1286, Rarity.RARE, mage.cards.s.SelflessSavior.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Akroma, Angel of Fury", 1287, Rarity.MYTHIC, mage.cards.a.AkromaAngelOfFury.class));
|
||||
cards.add(new SetCardInfo("Umezawa's Jitte", 1288, Rarity.RARE, mage.cards.u.UmezawasJitte.class));
|
||||
cards.add(new SetCardInfo("Umezawa's Jitte", 1288, Rarity.RARE, mage.cards.u.UmezawasJitte.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Linvala, Keeper of Silence", 1289, Rarity.MYTHIC, mage.cards.l.LinvalaKeeperOfSilence.class));
|
||||
cards.add(new SetCardInfo("Sunblast Angel", 1290, Rarity.RARE, mage.cards.s.SunblastAngel.class));
|
||||
cards.add(new SetCardInfo("Emeria, the Sky Ruin", 1291, Rarity.RARE, mage.cards.e.EmeriaTheSkyRuin.class));
|
||||
|
|
@ -1346,7 +1354,7 @@ public class SecretLairDrop extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Fynn, the Fangbearer", 1449, Rarity.RARE, mage.cards.f.FynnTheFangbearer.class));
|
||||
cards.add(new SetCardInfo("Brion Stoutarm", 1450, Rarity.RARE, mage.cards.b.BrionStoutarm.class));
|
||||
cards.add(new SetCardInfo("Samut, Voice of Dissent", 1451, Rarity.MYTHIC, mage.cards.s.SamutVoiceOfDissent.class));
|
||||
cards.add(new SetCardInfo("Marchesa, the Black Rose", 1452, Rarity.RARE, mage.cards.m.MarchesaTheBlackRose.class));
|
||||
cards.add(new SetCardInfo("Marchesa, the Black Rose", 1452, Rarity.RARE, mage.cards.m.MarchesaTheBlackRose.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Ajani Goldmane", 1453, Rarity.MYTHIC, mage.cards.a.AjaniGoldmane.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Ajani Goldmane", "1453b", Rarity.MYTHIC, mage.cards.a.AjaniGoldmane.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Jace Beleren", 1454, Rarity.MYTHIC, mage.cards.j.JaceBeleren.class, NON_FULL_USE_VARIOUS));
|
||||
|
|
@ -1527,7 +1535,7 @@ public class SecretLairDrop extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Anowon, the Ruin Thief", "1568*", Rarity.MYTHIC, mage.cards.a.AnowonTheRuinThief.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Grenzo, Dungeon Warden", 1569, Rarity.RARE, mage.cards.g.GrenzoDungeonWarden.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Grenzo, Dungeon Warden", "1569*", Rarity.RARE, mage.cards.g.GrenzoDungeonWarden.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Blade of Selves", 1570, Rarity.RARE, mage.cards.b.BladeOfSelves.class));
|
||||
cards.add(new SetCardInfo("Blade of Selves", 1570, Rarity.RARE, mage.cards.b.BladeOfSelves.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Conqueror's Flail", 1571, Rarity.RARE, mage.cards.c.ConquerorsFlail.class));
|
||||
cards.add(new SetCardInfo("Darksteel Plate", 1572, Rarity.RARE, mage.cards.d.DarksteelPlate.class));
|
||||
cards.add(new SetCardInfo("Deathrender", 1573, Rarity.RARE, mage.cards.d.Deathrender.class));
|
||||
|
|
@ -1700,7 +1708,7 @@ public class SecretLairDrop extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Shivan Dragon", 1709, Rarity.RARE, mage.cards.s.ShivanDragon.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Elves of Deep Shadow", 1710, Rarity.RARE, mage.cards.e.ElvesOfDeepShadow.class));
|
||||
cards.add(new SetCardInfo("Good-Fortune Unicorn", 1711, Rarity.RARE, mage.cards.g.GoodFortuneUnicorn.class));
|
||||
cards.add(new SetCardInfo("Coat of Arms", 1712, Rarity.RARE, mage.cards.c.CoatOfArms.class));
|
||||
cards.add(new SetCardInfo("Coat of Arms", 1712, Rarity.RARE, mage.cards.c.CoatOfArms.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Dictate of Erebos", 1713, Rarity.RARE, mage.cards.d.DictateOfErebos.class));
|
||||
cards.add(new SetCardInfo("Fecundity", 1714, Rarity.RARE, mage.cards.f.Fecundity.class));
|
||||
cards.add(new SetCardInfo("Mayhem Devil", 1715, Rarity.RARE, mage.cards.m.MayhemDevil.class));
|
||||
|
|
@ -1737,7 +1745,7 @@ public class SecretLairDrop extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Black Panther, Wakandan King", 1747, Rarity.MYTHIC, mage.cards.b.BlackPantherWakandanKing.class));
|
||||
cards.add(new SetCardInfo("Secure the Wastes", 1748, Rarity.RARE, mage.cards.s.SecureTheWastes.class));
|
||||
cards.add(new SetCardInfo("Primal Vigor", 1749, Rarity.RARE, mage.cards.p.PrimalVigor.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Heroic Intervention", 1750, Rarity.RARE, mage.cards.h.HeroicIntervention.class));
|
||||
cards.add(new SetCardInfo("Heroic Intervention", 1750, Rarity.RARE, mage.cards.h.HeroicIntervention.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Karn's Bastion", 1751, Rarity.RARE, mage.cards.k.KarnsBastion.class));
|
||||
cards.add(new SetCardInfo("Deadly Rollick", 1754, Rarity.RARE, mage.cards.d.DeadlyRollick.class));
|
||||
cards.add(new SetCardInfo("Saw in Half", 1755, Rarity.RARE, mage.cards.s.SawInHalf.class));
|
||||
|
|
@ -1799,7 +1807,7 @@ public class SecretLairDrop extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Twinflame", 1810, Rarity.RARE, mage.cards.t.Twinflame.class));
|
||||
cards.add(new SetCardInfo("Genesis Chamber", 1811, Rarity.RARE, mage.cards.g.GenesisChamber.class));
|
||||
cards.add(new SetCardInfo("Silence", 1816, Rarity.RARE, mage.cards.s.Silence.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Winds of Abandon", 1817, Rarity.RARE, mage.cards.w.WindsOfAbandon.class));
|
||||
cards.add(new SetCardInfo("Winds of Abandon", 1817, Rarity.RARE, mage.cards.w.WindsOfAbandon.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Culling the Weak", 1818, Rarity.RARE, mage.cards.c.CullingTheWeak.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Fatal Push", 1819, Rarity.RARE, mage.cards.f.FatalPush.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Young Wolf", 1820, Rarity.RARE, mage.cards.y.YoungWolf.class, NON_FULL_USE_VARIOUS));
|
||||
|
|
@ -1834,6 +1842,21 @@ public class SecretLairDrop extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Crib Swap", 1850, Rarity.UNCOMMON, mage.cards.c.CribSwap.class));
|
||||
cards.add(new SetCardInfo("Homeward Path", 1851, Rarity.RARE, mage.cards.h.HomewardPath.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Go-Shintai of Life's Origin", 1853, Rarity.MYTHIC, mage.cards.g.GoShintaiOfLifesOrigin.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Day of Judgment", 1858, Rarity.RARE, mage.cards.d.DayOfJudgment.class));
|
||||
cards.add(new SetCardInfo("Temporal Extortion", 1859, Rarity.RARE, mage.cards.t.TemporalExtortion.class));
|
||||
cards.add(new SetCardInfo("Toxic Deluge", 1860, Rarity.RARE, mage.cards.t.ToxicDeluge.class));
|
||||
cards.add(new SetCardInfo("Praetor's Grasp", 1861, Rarity.RARE, mage.cards.p.PraetorsGrasp.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Star of Extinction", 1862, Rarity.RARE, mage.cards.s.StarOfExtinction.class));
|
||||
cards.add(new SetCardInfo("Staff of the Storyteller", 1863, Rarity.RARE, mage.cards.s.StaffOfTheStoryteller.class));
|
||||
cards.add(new SetCardInfo("Blade of Selves", 1864, Rarity.RARE, mage.cards.b.BladeOfSelves.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Umezawa's Jitte", 1865, Rarity.RARE, mage.cards.u.UmezawasJitte.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Colossus Hammer", 1866, Rarity.RARE, mage.cards.c.ColossusHammer.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Sword of Truth and Justice", 1867, Rarity.MYTHIC, mage.cards.s.SwordOfTruthAndJustice.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Prismatic Ending", 1868, Rarity.RARE, mage.cards.p.PrismaticEnding.class));
|
||||
cards.add(new SetCardInfo("Cyclonic Rift", 1869, Rarity.RARE, mage.cards.c.CyclonicRift.class));
|
||||
cards.add(new SetCardInfo("Damn", 1870, Rarity.RARE, mage.cards.d.Damn.class));
|
||||
cards.add(new SetCardInfo("Lightning Bolt", 1871, Rarity.RARE, mage.cards.l.LightningBolt.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Heroic Intervention", 1872, Rarity.RARE, mage.cards.h.HeroicIntervention.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Aesi, Tyrant of Gyre Strait", 1873, Rarity.MYTHIC, mage.cards.a.AesiTyrantOfGyreStrait.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Aesi, Tyrant of Gyre Strait", "1873b", Rarity.MYTHIC, mage.cards.a.AesiTyrantOfGyreStrait.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Anje Falkenrath", 1874, Rarity.MYTHIC, mage.cards.a.AnjeFalkenrath.class, NON_FULL_USE_VARIOUS));
|
||||
|
|
@ -1851,7 +1874,25 @@ public class SecretLairDrop extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Benevolent Hydra", 1889, Rarity.RARE, mage.cards.b.BenevolentHydra.class));
|
||||
cards.add(new SetCardInfo("Forgotten Ancient", 1890, Rarity.RARE, mage.cards.f.ForgottenAncient.class));
|
||||
cards.add(new SetCardInfo("Animar, Soul of Elements", 1891, Rarity.MYTHIC, mage.cards.a.AnimarSoulOfElements.class));
|
||||
cards.add(new SetCardInfo("Secret Rendezvous", 1892, Rarity.RARE, mage.cards.s.SecretRendezvous.class));
|
||||
cards.add(new SetCardInfo("Serenity", 1893, Rarity.RARE, mage.cards.s.Serenity.class));
|
||||
cards.add(new SetCardInfo("Esika's Chariot", 1894, Rarity.RARE, mage.cards.e.EsikasChariot.class));
|
||||
cards.add(new SetCardInfo("Realms Uncharted", 1895, Rarity.RARE, mage.cards.r.RealmsUncharted.class));
|
||||
cards.add(new SetCardInfo("Morophon, the Boundless", 1896, Rarity.MYTHIC, mage.cards.m.MorophonTheBoundless.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Raise the Palisade", 1897, Rarity.RARE, mage.cards.r.RaiseThePalisade.class));
|
||||
cards.add(new SetCardInfo("Bitterblossom", 1898, Rarity.MYTHIC, mage.cards.b.Bitterblossom.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Taurean Mauler", 1899, Rarity.RARE, mage.cards.t.TaureanMauler.class));
|
||||
cards.add(new SetCardInfo("Avenger of Zendikar", 1900, Rarity.MYTHIC, mage.cards.a.AvengerOfZendikar.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Kindred Summons", 1901, Rarity.RARE, mage.cards.k.KindredSummons.class));
|
||||
cards.add(new SetCardInfo("Tendershoot Dryad", 1902, Rarity.RARE, mage.cards.t.TendershootDryad.class));
|
||||
cards.add(new SetCardInfo("Coat of Arms", 1903, Rarity.RARE, mage.cards.c.CoatOfArms.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Maskwood Nexus", 1904, Rarity.RARE, mage.cards.m.MaskwoodNexus.class));
|
||||
cards.add(new SetCardInfo("Sol Ring", 1905, Rarity.RARE, mage.cards.s.SolRing.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Shapeshifter", 1906, Rarity.RARE, mage.cards.s.Shapeshifter.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Shapeshifter", 1907, Rarity.RARE, mage.cards.s.Shapeshifter.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Shapeshifter", 1908, Rarity.RARE, mage.cards.s.Shapeshifter.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Shapeshifter", 1909, Rarity.RARE, mage.cards.s.Shapeshifter.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Rin and Seri, Inseparable", 1910, Rarity.MYTHIC, mage.cards.r.RinAndSeriInseparable.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Karmic Guide", 1911, Rarity.RARE, mage.cards.k.KarmicGuide.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Ninja of the Deep Hours", 1912, Rarity.RARE, mage.cards.n.NinjaOfTheDeepHours.class));
|
||||
cards.add(new SetCardInfo("Captain Sisay", 1913, Rarity.MYTHIC, mage.cards.c.CaptainSisay.class, NON_FULL_USE_VARIOUS));
|
||||
|
|
@ -1884,11 +1925,16 @@ public class SecretLairDrop extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Swamp", 1941, Rarity.LAND, mage.cards.basiclands.Swamp.class, FULL_ART_BFZ_VARIOUS));
|
||||
cards.add(new SetCardInfo("Mountain", 1942, Rarity.LAND, mage.cards.basiclands.Mountain.class, FULL_ART_BFZ_VARIOUS));
|
||||
cards.add(new SetCardInfo("Forest", 1943, Rarity.LAND, mage.cards.basiclands.Forest.class, FULL_ART_BFZ_VARIOUS));
|
||||
cards.add(new SetCardInfo("Morophon, the Boundless", 1944, Rarity.MYTHIC, mage.cards.m.MorophonTheBoundless.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Big Score", 1955, Rarity.RARE, mage.cards.b.BigScore.class));
|
||||
cards.add(new SetCardInfo("Final Fortune", 1956, Rarity.RARE, mage.cards.f.FinalFortune.class));
|
||||
cards.add(new SetCardInfo("Heat Shimmer", 1957, Rarity.RARE, mage.cards.h.HeatShimmer.class));
|
||||
cards.add(new SetCardInfo("Roiling Vortex", 1958, Rarity.RARE, mage.cards.r.RoilingVortex.class));
|
||||
cards.add(new SetCardInfo("Wheel of Misfortune", 1959, Rarity.RARE, mage.cards.w.WheelOfMisfortune.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Marwyn, the Nurturer", 1960, Rarity.RARE, mage.cards.m.MarwynTheNurturer.class));
|
||||
cards.add(new SetCardInfo("Liesa, Shroud of Dusk", 1961, Rarity.RARE, mage.cards.l.LiesaShroudOfDusk.class));
|
||||
cards.add(new SetCardInfo("Oloro, Ageless Ascetic", 1962, Rarity.MYTHIC, mage.cards.o.OloroAgelessAscetic.class));
|
||||
cards.add(new SetCardInfo("Sythis, Harvest's Hand", 1963, Rarity.RARE, mage.cards.s.SythisHarvestsHand.class));
|
||||
cards.add(new SetCardInfo("Parhelion II", 1964, Rarity.RARE, mage.cards.p.ParhelionII.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Parhelion II", "1964b", Rarity.RARE, mage.cards.p.ParhelionII.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Mechtitan Core", 1965, Rarity.RARE, mage.cards.m.MechtitanCore.class, NON_FULL_USE_VARIOUS));
|
||||
|
|
@ -1911,15 +1957,75 @@ public class SecretLairDrop extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Dragonlord Ojutai", "1973b", Rarity.MYTHIC, mage.cards.d.DragonlordOjutai.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Dragonlord Silumgar", 1974, Rarity.MYTHIC, mage.cards.d.DragonlordSilumgar.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Dragonlord Silumgar", "1974b", Rarity.MYTHIC, mage.cards.d.DragonlordSilumgar.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Deadly Dispute", 1980, Rarity.RARE, mage.cards.d.DeadlyDispute.class));
|
||||
cards.add(new SetCardInfo("Murderous Rider", 1981, Rarity.RARE, mage.cards.m.MurderousRider.class));
|
||||
cards.add(new SetCardInfo("Zulaport Cutthroat", 1982, Rarity.RARE, mage.cards.z.ZulaportCutthroat.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Aggravated Assault", 1983, Rarity.RARE, mage.cards.a.AggravatedAssault.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Desperate Ritual", 1984, Rarity.RARE, mage.cards.d.DesperateRitual.class));
|
||||
cards.add(new SetCardInfo("Agent of Treachery", 2005, Rarity.RARE, mage.cards.a.AgentOfTreachery.class));
|
||||
cards.add(new SetCardInfo("Priest of Forgotten Gods", 2006, Rarity.RARE, mage.cards.p.PriestOfForgottenGods.class));
|
||||
cards.add(new SetCardInfo("Treasonous Ogre", 2007, Rarity.RARE, mage.cards.t.TreasonousOgre.class));
|
||||
cards.add(new SetCardInfo("Uncivil Unrest", 2008, Rarity.RARE, mage.cards.u.UncivilUnrest.class));
|
||||
cards.add(new SetCardInfo("Marchesa, the Black Rose", 2009, Rarity.RARE, mage.cards.m.MarchesaTheBlackRose.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Ashaya, Soul of the Wild", 2014, Rarity.MYTHIC, mage.cards.a.AshayaSoulOfTheWild.class));
|
||||
cards.add(new SetCardInfo("Elvish Reclaimer", 2015, Rarity.RARE, mage.cards.e.ElvishReclaimer.class));
|
||||
cards.add(new SetCardInfo("Harrow", 2016, Rarity.RARE, mage.cards.h.Harrow.class));
|
||||
cards.add(new SetCardInfo("World Shaper", 2017, Rarity.RARE, mage.cards.w.WorldShaper.class));
|
||||
cards.add(new SetCardInfo("Horn of Greed", 2018, Rarity.RARE, mage.cards.h.HornOfGreed.class));
|
||||
cards.add(new SetCardInfo("Goblin Bombardment", 2024, Rarity.RARE, mage.cards.g.GoblinBombardment.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Orcish Lumberjack", 2025, Rarity.RARE, mage.cards.o.OrcishLumberjack.class));
|
||||
cards.add(new SetCardInfo("Constant Mists", 2026, Rarity.RARE, mage.cards.c.ConstantMists.class));
|
||||
cards.add(new SetCardInfo("Song of the Dryads", 2027, Rarity.RARE, mage.cards.s.SongOfTheDryads.class));
|
||||
cards.add(new SetCardInfo("Consecrated Sphinx", 2028, Rarity.RARE, mage.cards.c.ConsecratedSphinx.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Resculpt", 2029, Rarity.RARE, mage.cards.r.Resculpt.class));
|
||||
cards.add(new SetCardInfo("Mirage Mirror", 2030, Rarity.RARE, mage.cards.m.MirageMirror.class));
|
||||
cards.add(new SetCardInfo("Scion of Draco", 2031, Rarity.MYTHIC, mage.cards.s.ScionOfDraco.class));
|
||||
cards.add(new SetCardInfo("Lava Dart", 2037, Rarity.RARE, mage.cards.l.LavaDart.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Monastery Swiftspear", 2038, Rarity.RARE, mage.cards.m.MonasterySwiftspear.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Soul-Scar Mage", 2039, Rarity.RARE, mage.cards.s.SoulScarMage.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Underworld Breach", 2040, Rarity.RARE, mage.cards.u.UnderworldBreach.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Mishra's Bauble", 2041, Rarity.RARE, mage.cards.m.MishrasBauble.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Lava Dart", 2042, Rarity.RARE, mage.cards.l.LavaDart.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Monastery Swiftspear", 2043, Rarity.RARE, mage.cards.m.MonasterySwiftspear.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Soul-Scar Mage", 2044, Rarity.RARE, mage.cards.s.SoulScarMage.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Underworld Breach", 2045, Rarity.RARE, mage.cards.u.UnderworldBreach.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Mishra's Bauble", 2046, Rarity.RARE, mage.cards.m.MishrasBauble.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Chain Lightning", 2047, Rarity.RARE, mage.cards.c.ChainLightning.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Dragon's Rage Channeler", 2048, Rarity.RARE, mage.cards.d.DragonsRageChanneler.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Lava Spike", 2049, Rarity.RARE, mage.cards.l.LavaSpike.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Rift Bolt", 2050, Rarity.RARE, mage.cards.r.RiftBolt.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Skewer the Critics", 2051, Rarity.RARE, mage.cards.s.SkewerTheCritics.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Chain Lightning", 2052, Rarity.RARE, mage.cards.c.ChainLightning.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Dragon's Rage Channeler", 2053, Rarity.RARE, mage.cards.d.DragonsRageChanneler.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Lava Spike", 2054, Rarity.RARE, mage.cards.l.LavaSpike.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Rift Bolt", 2055, Rarity.RARE, mage.cards.r.RiftBolt.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Skewer the Critics", 2056, Rarity.RARE, mage.cards.s.SkewerTheCritics.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Tireless Provisioner", 2057, Rarity.RARE, mage.cards.t.TirelessProvisioner.class));
|
||||
cards.add(new SetCardInfo("Sylvan Library", 2058, Rarity.RARE, mage.cards.s.SylvanLibrary.class));
|
||||
cards.add(new SetCardInfo("Ancient Greenwarden", 2059, Rarity.MYTHIC, mage.cards.a.AncientGreenwarden.class));
|
||||
cards.add(new SetCardInfo("Expressive Iteration", 2060, Rarity.RARE, mage.cards.e.ExpressiveIteration.class));
|
||||
cards.add(new SetCardInfo("Xenagos, God of Revels", 2061, Rarity.MYTHIC, mage.cards.x.XenagosGodOfRevels.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Lightning Greaves", 2062, Rarity.RARE, mage.cards.l.LightningGreaves.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Sol Ring", 2063, Rarity.RARE, mage.cards.s.SolRing.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Cultural Exchange", 2071, Rarity.RARE, mage.cards.c.CulturalExchange.class));
|
||||
cards.add(new SetCardInfo("Folio of Fancies", 2072, Rarity.RARE, mage.cards.f.FolioOfFancies.class));
|
||||
cards.add(new SetCardInfo("Concordant Crossroads", 2073, Rarity.RARE, mage.cards.c.ConcordantCrossroads.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Rites of Flourishing", 2074, Rarity.RARE, mage.cards.r.RitesOfFlourishing.class));
|
||||
cards.add(new SetCardInfo("Font of Mythos", 2075, Rarity.RARE, mage.cards.f.FontOfMythos.class));
|
||||
cards.add(new SetCardInfo("Plains", 2076, Rarity.LAND, mage.cards.basiclands.Plains.class, FULL_ART_BFZ_VARIOUS));
|
||||
cards.add(new SetCardInfo("Island", 2077, Rarity.LAND, mage.cards.basiclands.Island.class, FULL_ART_BFZ_VARIOUS));
|
||||
cards.add(new SetCardInfo("Swamp", 2078, Rarity.LAND, mage.cards.basiclands.Swamp.class, FULL_ART_BFZ_VARIOUS));
|
||||
cards.add(new SetCardInfo("Mountain", 2079, Rarity.LAND, mage.cards.basiclands.Mountain.class, FULL_ART_BFZ_VARIOUS));
|
||||
cards.add(new SetCardInfo("Forest", 2080, Rarity.LAND, mage.cards.basiclands.Forest.class, FULL_ART_BFZ_VARIOUS));
|
||||
cards.add(new SetCardInfo("Feed the Swarm", 7001, Rarity.RARE, mage.cards.f.FeedTheSwarm.class));
|
||||
cards.add(new SetCardInfo("Forge Anew", 7002, Rarity.RARE, mage.cards.f.ForgeAnew.class));
|
||||
cards.add(new SetCardInfo("Silence", 7003, Rarity.RARE, mage.cards.s.Silence.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Smothering Tithe", 7009, Rarity.RARE, mage.cards.s.SmotheringTithe.class));
|
||||
cards.add(new SetCardInfo("Counterspell", 7010, Rarity.RARE, mage.cards.c.Counterspell.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Dismember", 7011, Rarity.RARE, mage.cards.d.Dismember.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Command Tower", 7012, Rarity.RARE, mage.cards.c.CommandTower.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Minds Aglow", 7028, Rarity.RARE, mage.cards.m.MindsAglow.class));
|
||||
cards.add(new SetCardInfo("Command Tower", 7029, Rarity.RARE, mage.cards.c.CommandTower.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Jace, the Mind Sculptor", 8001, Rarity.MYTHIC, mage.cards.j.JaceTheMindSculptor.class));
|
||||
cards.add(new SetCardInfo("Doom Blade", 9990, Rarity.RARE, mage.cards.d.DoomBlade.class));
|
||||
cards.add(new SetCardInfo("Massacre", 9991, Rarity.RARE, mage.cards.m.Massacre.class));
|
||||
|
|
|
|||
|
|
@ -25,6 +25,7 @@ public class SecretLairShowdown extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Dark Ritual", 16, Rarity.RARE, mage.cards.d.DarkRitual.class));
|
||||
cards.add(new SetCardInfo("Death's Shadow", 8, Rarity.RARE, mage.cards.d.DeathsShadow.class));
|
||||
cards.add(new SetCardInfo("Dragonlord Silumgar", 9, Rarity.MYTHIC, mage.cards.d.DragonlordSilumgar.class));
|
||||
cards.add(new SetCardInfo("Echo of Death's Wail", 356, Rarity.RARE, mage.cards.e.EchoOfDeathsWail.class));
|
||||
cards.add(new SetCardInfo("Eldritch Evolution", 5, Rarity.RARE, mage.cards.e.EldritchEvolution.class));
|
||||
cards.add(new SetCardInfo("Explore", 12, Rarity.RARE, mage.cards.e.Explore.class));
|
||||
cards.add(new SetCardInfo("Expressive Iteration", 13, Rarity.RARE, mage.cards.e.ExpressiveIteration.class));
|
||||
|
|
@ -35,10 +36,12 @@ public class SecretLairShowdown extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Goblin Guide", 23, Rarity.RARE, mage.cards.g.GoblinGuide.class));
|
||||
cards.add(new SetCardInfo("Island", 32, Rarity.LAND, mage.cards.basiclands.Island.class, FULL_ART_BFZ_VARIOUS));
|
||||
cards.add(new SetCardInfo("Karn Liberated", 36, Rarity.MYTHIC, mage.cards.k.KarnLiberated.class));
|
||||
cards.add(new SetCardInfo("Laughing Jasper Flint", 44, Rarity.RARE, mage.cards.l.LaughingJasperFlint.class));
|
||||
cards.add(new SetCardInfo("Lightning Bolt", 21, Rarity.RARE, mage.cards.l.LightningBolt.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Lightning Bolt", 37, Rarity.RARE, mage.cards.l.LightningBolt.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Living End", 30, Rarity.MYTHIC, mage.cards.l.LivingEnd.class));
|
||||
cards.add(new SetCardInfo("Mayhem Devil", 28, Rarity.RARE, mage.cards.m.MayhemDevil.class));
|
||||
cards.add(new SetCardInfo("Mountain", 34, Rarity.LAND, mage.cards.basiclands.Mountain.class, FULL_ART_BFZ_VARIOUS));
|
||||
cards.add(new SetCardInfo("Murktide Regent", 17, Rarity.MYTHIC, mage.cards.m.MurktideRegent.class));
|
||||
cards.add(new SetCardInfo("Nexus of Fate", 27, Rarity.RARE, mage.cards.n.NexusOfFate.class));
|
||||
cards.add(new SetCardInfo("Plains", 31, Rarity.LAND, mage.cards.basiclands.Plains.class, FULL_ART_BFZ_VARIOUS));
|
||||
|
|
@ -49,14 +52,15 @@ public class SecretLairShowdown extends ExpansionSet {
|
|||
cards.add(new SetCardInfo("Relentless Rats", 10, Rarity.RARE, mage.cards.r.RelentlessRats.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Relentless Rats", 11, Rarity.RARE, mage.cards.r.RelentlessRats.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Seasoned Pyromancer", 24, Rarity.MYTHIC, mage.cards.s.SeasonedPyromancer.class));
|
||||
cards.add(new SetCardInfo("Shoot the Sheriff", 43, Rarity.RARE, mage.cards.s.ShootTheSheriff.class));
|
||||
cards.add(new SetCardInfo("Sleight of Hand", 25, Rarity.RARE, mage.cards.s.SleightOfHand.class));
|
||||
cards.add(new SetCardInfo("Spell Pierce", 18, Rarity.RARE, mage.cards.s.SpellPierce.class));
|
||||
cards.add(new SetCardInfo("Springleaf Drum", 22, Rarity.RARE, mage.cards.s.SpringleafDrum.class));
|
||||
cards.add(new SetCardInfo("Sudden Edict", 39, Rarity.RARE, mage.cards.s.SuddenEdict.class));
|
||||
cards.add(new SetCardInfo("Supreme Verdict", 26, Rarity.RARE, mage.cards.s.SupremeVerdict.class));
|
||||
cards.add(new SetCardInfo("Swamp", 33, Rarity.LAND, mage.cards.basiclands.Swamp.class, FULL_ART_BFZ_VARIOUS));
|
||||
cards.add(new SetCardInfo("Swords to Plowshares", 20, Rarity.RARE, mage.cards.s.SwordsToPlowshares.class));
|
||||
cards.add(new SetCardInfo("Tribute to Horobi", 356, Rarity.RARE, mage.cards.t.TributeToHorobi.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Echo of Death's Wail", 356, Rarity.RARE, mage.cards.e.EchoOfDeathsWail.class, NON_FULL_USE_VARIOUS));
|
||||
cards.add(new SetCardInfo("Tribute to Horobi", 356, Rarity.RARE, mage.cards.t.TributeToHorobi.class));
|
||||
cards.add(new SetCardInfo("Ugin, the Spirit Dragon", 6, Rarity.MYTHIC, mage.cards.u.UginTheSpiritDragon.class));
|
||||
cards.add(new SetCardInfo("Unholy Heat", 4, Rarity.RARE, mage.cards.u.UnholyHeat.class));
|
||||
cards.add(new SetCardInfo("Valakut, the Molten Pinnacle", 14, Rarity.RARE, mage.cards.v.ValakutTheMoltenPinnacle.class));
|
||||
|
|
|
|||
|
|
@ -42,7 +42,7 @@ public class EvokeTest extends CardTestPlayerBase {
|
|||
|
||||
castSpell(1, PhaseStep.PRECOMBAT_MAIN, playerA, "Shriekmaw");
|
||||
setChoice(playerA, "Cast with Evoke alternative cost: {1}{B} (source: Shriekmaw");
|
||||
setChoice(playerA, "When this permanent enters the battlefield, if its evoke cost was paid, its controller sacrifices it."); // stack triggers
|
||||
setChoice(playerA, "When this permanent enters, if its evoke cost was paid, its controller sacrifices it."); // stack triggers
|
||||
addTarget(playerA, "Silvercoat Lion"); // choice for Shriekmaw Destroy trigger
|
||||
|
||||
castSpell(1, PhaseStep.POSTCOMBAT_MAIN, playerA, "Exhume");
|
||||
|
|
|
|||
|
|
@ -0,0 +1,86 @@
|
|||
package org.mage.test.cards.single.bbd;
|
||||
|
||||
import mage.constants.PhaseStep;
|
||||
import mage.constants.Zone;
|
||||
import org.junit.Test;
|
||||
import org.mage.test.serverside.base.CardTestPlayerBase;
|
||||
|
||||
/**
|
||||
* @author xenohedron
|
||||
*/
|
||||
public class ComboAttackTest extends CardTestPlayerBase {
|
||||
|
||||
/**
|
||||
* {@link mage.cards.c.ComboAttack Combo Attack} {2}{G}
|
||||
* Sorcery
|
||||
* Two target creatures your team controls each deal damage equal to their power to target creature
|
||||
*/
|
||||
private static final String combo = "Combo Attack";
|
||||
|
||||
@Test
|
||||
public void test_Normal() {
|
||||
addCard(Zone.HAND, playerA, combo, 1);
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Memnite", 1);
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Runeclaw Bear", 1);
|
||||
addCard(Zone.BATTLEFIELD, playerB, "Fortress Crab", 1);
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Forest", 3);
|
||||
|
||||
castSpell(1, PhaseStep.PRECOMBAT_MAIN, playerA, combo, "Memnite^Runeclaw Bear^Fortress Crab");
|
||||
|
||||
setStrictChooseMode(true);
|
||||
setStopAt(1, PhaseStep.POSTCOMBAT_MAIN);
|
||||
execute();
|
||||
|
||||
assertGraveyardCount(playerA, combo, 1);
|
||||
assertDamageReceived(playerB, "Fortress Crab", 3);
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void test_IllegalFirst() {
|
||||
addCard(Zone.HAND, playerA, combo, 1);
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Memnite", 1);
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Runeclaw Bear", 1);
|
||||
addCard(Zone.BATTLEFIELD, playerB, "Fortress Crab", 1);
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Forest", 3);
|
||||
addCard(Zone.HAND, playerB, "Unsummon");
|
||||
addCard(Zone.BATTLEFIELD, playerB, "Island");
|
||||
|
||||
castSpell(1, PhaseStep.PRECOMBAT_MAIN, playerA, combo, "Memnite^Runeclaw Bear^Fortress Crab");
|
||||
castSpell(1, PhaseStep.PRECOMBAT_MAIN, playerB, "Unsummon", "Memnite", combo);
|
||||
|
||||
setStrictChooseMode(true);
|
||||
setStopAt(1, PhaseStep.POSTCOMBAT_MAIN);
|
||||
execute();
|
||||
|
||||
assertGraveyardCount(playerA, combo, 1);
|
||||
assertGraveyardCount(playerB, "Unsummon", 1);
|
||||
assertHandCount(playerA, "Memnite", 1);
|
||||
assertDamageReceived(playerB, "Fortress Crab", 2);
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void test_IllegalSecond() {
|
||||
addCard(Zone.HAND, playerA, combo, 1);
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Memnite", 1);
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Runeclaw Bear", 1);
|
||||
addCard(Zone.BATTLEFIELD, playerB, "Fortress Crab", 1);
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Forest", 3);
|
||||
addCard(Zone.HAND, playerB, "Unsummon");
|
||||
addCard(Zone.BATTLEFIELD, playerB, "Island");
|
||||
|
||||
castSpell(1, PhaseStep.PRECOMBAT_MAIN, playerA, combo, "Memnite^Runeclaw Bear^Fortress Crab");
|
||||
castSpell(1, PhaseStep.PRECOMBAT_MAIN, playerB, "Unsummon", "Runeclaw Bear", combo);
|
||||
|
||||
setStrictChooseMode(true);
|
||||
setStopAt(1, PhaseStep.POSTCOMBAT_MAIN);
|
||||
execute();
|
||||
|
||||
assertGraveyardCount(playerA, combo, 1);
|
||||
assertGraveyardCount(playerB, "Unsummon", 1);
|
||||
assertHandCount(playerA, "Runeclaw Bear", 1);
|
||||
assertDamageReceived(playerB, "Fortress Crab", 1);
|
||||
|
||||
}
|
||||
}
|
||||
|
|
@ -4,14 +4,9 @@ import mage.abilities.keyword.HasteAbility;
|
|||
import mage.constants.PhaseStep;
|
||||
import mage.constants.Zone;
|
||||
import mage.counters.CounterType;
|
||||
import mage.game.permanent.Permanent;
|
||||
import org.junit.Assert;
|
||||
import org.junit.Test;
|
||||
import org.mage.test.serverside.base.CardTestPlayerBase;
|
||||
|
||||
import static junit.framework.TestCase.assertEquals;
|
||||
import static org.junit.Assert.fail;
|
||||
|
||||
/**
|
||||
* @author Susucr
|
||||
*/
|
||||
|
|
@ -131,7 +126,7 @@ public class RapidAugmenterTest extends CardTestPlayerBase {
|
|||
|
||||
castSpell(1, PhaseStep.PRECOMBAT_MAIN, playerA, "Ephemerate", true);
|
||||
addTarget(playerA, "Memnite");
|
||||
setChoice(playerA, "Whenever another creature you control you control enters"); // order triggers (doesnt matter the order but a choice must be made)
|
||||
setChoice(playerA, "Whenever another creature you control enters"); // order triggers (doesnt matter the order but a choice must be made)
|
||||
|
||||
attack(1, playerA, rapidAugmenter, playerB);
|
||||
// Rapid Augmenter can't be blocked, Alpine Watchdog wont take damage
|
||||
|
|
|
|||
|
|
@ -51,7 +51,7 @@ public class MulldrifterTest extends CardTestPlayerBase {
|
|||
castSpell(1, PhaseStep.PRECOMBAT_MAIN, playerA, "Mulldrifter");
|
||||
setChoice(playerA, "Cast with Evoke alternative cost: {2}{U} (source: Mulldrifter");
|
||||
setStopAt(1, PhaseStep.BEGIN_COMBAT);
|
||||
setChoice(playerA, "When this permanent enters the battlefield, if its evoke cost was paid, its controller sacrifices it"); // stack triggers
|
||||
setChoice(playerA, "When this permanent enters, if its evoke cost was paid, its controller sacrifices it"); // stack triggers
|
||||
|
||||
execute();
|
||||
|
||||
|
|
@ -67,7 +67,7 @@ public class MulldrifterTest extends CardTestPlayerBase {
|
|||
public void testMulldrifterFlickered() {
|
||||
setStrictChooseMode(true);
|
||||
|
||||
// {4}{U} When Mulldrifter enters the battlefield, draw two cards. Evoke {2}{U}
|
||||
// {4}{U} When Mulldrifter enters, draw two cards. Evoke {2}{U}
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Mulldrifter"); // 2/2
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Merfolk Looter"); // 1/1
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Island", 5);
|
||||
|
|
@ -86,4 +86,4 @@ public class MulldrifterTest extends CardTestPlayerBase {
|
|||
assertGraveyardCount(playerA, "Ghostly Flicker", 1);
|
||||
assertHandCount(playerA, 2); // should have drawn 2 cards
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -149,4 +149,35 @@ public class PheliaExuberantShepherdTest extends CardTestPlayerBase {
|
|||
assertPermanentCount(playerA, "Memnite", 1);
|
||||
}
|
||||
|
||||
// bug: return trigger should not return cards exiled the turn before and not
|
||||
// returned due to a Stifle effect
|
||||
@Test
|
||||
public void test_Stifle() {
|
||||
setStrictChooseMode(true);
|
||||
|
||||
addCard(Zone.BATTLEFIELD, playerA, phelia, 1);
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Memnite", 1);
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Ornithopter", 1);
|
||||
addCard(Zone.HAND, playerB, "Stifle", 1);
|
||||
addCard(Zone.BATTLEFIELD, playerB, "Island", 1);
|
||||
|
||||
attack(1, playerA, phelia, playerB);
|
||||
addTarget(playerA, "Memnite");
|
||||
|
||||
castSpell(1, PhaseStep.END_TURN, playerB, "Stifle", "stack ability (At the beginning");
|
||||
|
||||
checkExileCount("Memnite still exiled", 2, PhaseStep.POSTCOMBAT_MAIN, playerA, "Memnite", 1);
|
||||
|
||||
attack(3, playerA, phelia, playerB);
|
||||
addTarget(playerA, "Ornithopter");
|
||||
|
||||
// end of turn trigger: Ornithopter returns.
|
||||
|
||||
setStopAt(4, PhaseStep.UPKEEP);
|
||||
execute();
|
||||
|
||||
assertPowerToughness(playerA, phelia, 2 + 1, 2 + 1);
|
||||
assertExileCount(playerA, "Memnite", 1);
|
||||
assertPermanentCount(playerA, "Ornithopter", 1);
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,5 +1,6 @@
|
|||
package mage.abilities.common;
|
||||
|
||||
import mage.MageItem;
|
||||
import mage.abilities.TriggeredAbilityImpl;
|
||||
import mage.abilities.effects.Effect;
|
||||
import mage.constants.Zone;
|
||||
|
|
@ -23,6 +24,7 @@ public class AttacksWithCreaturesTriggeredAbility extends TriggeredAbilityImpl {
|
|||
|
||||
// retrieve the number of attackers in triggered effects with getValue
|
||||
public static final String VALUEKEY_NUMBER_ATTACKERS = "number_attackers";
|
||||
public static final String VALUEKEY_NUMBER_DEFENDING_PLAYERS = "number_defending_players";
|
||||
|
||||
private final FilterPermanent filter;
|
||||
private final int minAttackers;
|
||||
|
|
@ -91,6 +93,17 @@ public class AttacksWithCreaturesTriggeredAbility extends TriggeredAbilityImpl {
|
|||
return false;
|
||||
}
|
||||
getEffects().setValue(VALUEKEY_NUMBER_ATTACKERS, attackers.size());
|
||||
getEffects().setValue(
|
||||
VALUEKEY_NUMBER_DEFENDING_PLAYERS,
|
||||
attackers.stream()
|
||||
.map(MageItem::getId)
|
||||
.map(game.getCombat()::getDefenderId)
|
||||
.distinct()
|
||||
.map(game::getPlayer)
|
||||
.filter(Objects::nonNull)
|
||||
.mapToInt(x -> 1)
|
||||
.sum()
|
||||
);
|
||||
if (setTargetPointer) {
|
||||
getEffects().setTargetPointer(new FixedTargets(new ArrayList<>(attackers), game));
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,5 +1,3 @@
|
|||
|
||||
|
||||
package mage.abilities.condition.common;
|
||||
|
||||
import mage.abilities.Ability;
|
||||
|
|
@ -9,17 +7,21 @@ import mage.game.Game;
|
|||
import mage.util.CardUtil;
|
||||
|
||||
/**
|
||||
* Checks if a the spell was cast with the alternate evoke costs
|
||||
* Checks if a the spell was cast with the alternate evoke costs
|
||||
*
|
||||
* @author LevelX2
|
||||
*/
|
||||
|
||||
public enum EvokedCondition implements Condition {
|
||||
|
||||
instance;
|
||||
|
||||
@Override
|
||||
public boolean apply(Game game, Ability source) {
|
||||
return CardUtil.checkSourceCostsTagExists(game, source, EvokeAbility.getActivationKey());
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "its evoke cost was paid";
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -0,0 +1,34 @@
|
|||
package mage.abilities.condition.common;
|
||||
|
||||
import mage.abilities.Ability;
|
||||
import mage.abilities.condition.Condition;
|
||||
import mage.abilities.hint.ConditionHint;
|
||||
import mage.abilities.hint.Hint;
|
||||
import mage.game.Game;
|
||||
import mage.watchers.common.DealtDamageThisGameWatcher;
|
||||
|
||||
/**
|
||||
* requires DealtDamageThisGameWatcher
|
||||
*
|
||||
* @author TheElk801
|
||||
*/
|
||||
public enum SourceHasntDealtDamageThisGameCondition implements Condition {
|
||||
instance;
|
||||
private static final Hint hint = new ConditionHint(
|
||||
instance, "This creature hasn't dealt damage yet this game"
|
||||
);
|
||||
|
||||
public static Hint getHint() {
|
||||
return hint;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean apply(Game game, Ability source) {
|
||||
return DealtDamageThisGameWatcher.checkCreature(game, source);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "{this} hasn't dealt damage yet";
|
||||
}
|
||||
}
|
||||
|
|
@ -12,9 +12,6 @@ import mage.game.permanent.Permanent;
|
|||
import mage.game.stack.Spell;
|
||||
import mage.game.stack.StackObject;
|
||||
import mage.players.Player;
|
||||
import mage.target.Target;
|
||||
import mage.target.targetpointer.FirstTargetPointer;
|
||||
import mage.target.targetpointer.SecondTargetPointer;
|
||||
import mage.util.CardUtil;
|
||||
|
||||
import java.util.LinkedHashSet;
|
||||
|
|
@ -27,8 +24,8 @@ import java.util.UUID;
|
|||
public class ExileTargetEffect extends OneShotEffect {
|
||||
|
||||
private final Zone onlyFromZone;
|
||||
private String exileZone = null;
|
||||
private UUID exileId = null;
|
||||
protected String exileZone = null;
|
||||
protected UUID exileId = null;
|
||||
private boolean toSourceExileZone = false; // exile the targets to a source object specific exile zone (takes care of zone change counter)
|
||||
private boolean withName = true; // for face down - allows to hide card name in game logs before real face down apply
|
||||
|
||||
|
|
|
|||
|
|
@ -21,7 +21,6 @@ import mage.players.Player;
|
|||
import mage.target.common.TargetControlledPermanent;
|
||||
import mage.util.CardUtil;
|
||||
|
||||
import java.util.Objects;
|
||||
import java.util.UUID;
|
||||
|
||||
/*
|
||||
|
|
@ -188,13 +187,9 @@ class ConspireTriggeredAbility extends CastSourceTriggeredAbility {
|
|||
return false;
|
||||
}
|
||||
Spell spell = game.getStack().getSpell(event.getSourceId());
|
||||
return spell != null
|
||||
&& spell
|
||||
.getSpellAbility()
|
||||
.getAllEffects()
|
||||
.stream()
|
||||
.map(effect -> effect.getValue("ConspireActivation" + conspireId + addedById))
|
||||
.anyMatch(Objects::nonNull);
|
||||
return spell != null && CardUtil.getEffectValueFromAbility(
|
||||
spell.getSpellAbility(), "ConspireActivation" + conspireId + addedById, Boolean.class
|
||||
).orElse(false);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
|||
|
|
@ -1,12 +1,10 @@
|
|||
package mage.abilities.keyword;
|
||||
|
||||
import mage.abilities.Ability;
|
||||
import mage.abilities.common.EntersBattlefieldTriggeredAbility;
|
||||
import mage.abilities.condition.common.EvokedCondition;
|
||||
import mage.abilities.costs.AlternativeSourceCostsImpl;
|
||||
import mage.abilities.costs.Cost;
|
||||
import mage.abilities.costs.mana.ManaCostsImpl;
|
||||
import mage.abilities.decorator.ConditionalInterveningIfTriggeredAbility;
|
||||
import mage.abilities.effects.common.SacrificeSourceEffect;
|
||||
|
||||
/**
|
||||
|
|
@ -24,11 +22,9 @@ public class EvokeAbility extends AlternativeSourceCostsImpl {
|
|||
|
||||
public EvokeAbility(Cost cost) {
|
||||
super(EVOKE_KEYWORD, REMINDER_TEXT, cost);
|
||||
Ability ability = new ConditionalInterveningIfTriggeredAbility(
|
||||
new EntersBattlefieldTriggeredAbility(new SacrificeSourceEffect(true)),
|
||||
EvokedCondition.instance, "When this permanent enters the battlefield, if its evoke cost was paid, its controller sacrifices it.");
|
||||
ability.setRuleVisible(false);
|
||||
addSubAbility(ability);
|
||||
this.addSubAbility(new EntersBattlefieldTriggeredAbility(
|
||||
new SacrificeSourceEffect(true).setText("its controller sacrifices it")
|
||||
).setTriggerPhrase("When this permanent enters, ").withInterveningIf(EvokedCondition.instance).setRuleVisible(false));
|
||||
}
|
||||
|
||||
private EvokeAbility(final EvokeAbility ability) {
|
||||
|
|
@ -40,7 +36,7 @@ public class EvokeAbility extends AlternativeSourceCostsImpl {
|
|||
return new EvokeAbility(this);
|
||||
}
|
||||
|
||||
public static String getActivationKey(){
|
||||
public static String getActivationKey() {
|
||||
return getActivationKey(EVOKE_KEYWORD);
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -10,6 +10,7 @@ import mage.filter.StaticFilters;
|
|||
import mage.game.Game;
|
||||
import mage.game.events.GameEvent;
|
||||
import mage.game.permanent.Permanent;
|
||||
import mage.util.CardUtil;
|
||||
|
||||
/**
|
||||
* FAQ 2013/01/11
|
||||
|
|
@ -75,18 +76,14 @@ public class EvolveAbility extends EntersBattlefieldAllTriggeredAbility {
|
|||
@Override
|
||||
public boolean checkInterveningIfClause(Game game) {
|
||||
Permanent sourcePermanent = getSourcePermanentOrLKI(game);
|
||||
Permanent permanentEntering = (Permanent) this
|
||||
.getEffects()
|
||||
.stream()
|
||||
.map(effect -> effect.getValue("permanentEnteringBattlefield"))
|
||||
.findFirst()
|
||||
.orElse(null);
|
||||
return sourcePermanent != null
|
||||
&& permanentEntering != null
|
||||
&& sourcePermanent.isCreature(game)
|
||||
&& permanentEntering.isCreature(game)
|
||||
&& (permanentEntering.getPower().getValue() > sourcePermanent.getPower().getValue()
|
||||
|| permanentEntering.getToughness().getValue() > sourcePermanent.getToughness().getValue());
|
||||
&& CardUtil
|
||||
.getEffectValueFromAbility(this, "permanentEnteringBattlefield", Permanent.class)
|
||||
.filter(permanent -> permanent.isCreature(game))
|
||||
.filter(permanent -> sourcePermanent.getPower().getValue() < permanent.getPower().getValue()
|
||||
|| sourcePermanent.getToughness().getValue() < permanent.getToughness().getValue())
|
||||
.isPresent();
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
|||
|
|
@ -6,7 +6,6 @@ import mage.abilities.StaticAbility;
|
|||
import mage.abilities.common.EntersBattlefieldTriggeredAbility;
|
||||
import mage.abilities.condition.common.GiftWasPromisedCondition;
|
||||
import mage.abilities.costs.*;
|
||||
import mage.abilities.decorator.ConditionalInterveningIfTriggeredAbility;
|
||||
import mage.abilities.effects.OneShotEffect;
|
||||
import mage.cards.Card;
|
||||
import mage.constants.GiftType;
|
||||
|
|
@ -53,11 +52,10 @@ public class GiftAbility extends StaticAbility implements OptionalAdditionalSour
|
|||
this.rule = additionalCost.getName() + ' ' + additionalCost.getReminderText();
|
||||
this.setRuleAtTheTop(true);
|
||||
if (card.isPermanent()) {
|
||||
this.addSubAbility(new ConditionalInterveningIfTriggeredAbility(
|
||||
new EntersBattlefieldTriggeredAbility(new PromiseGiftEffect(giftType)),
|
||||
GiftWasPromisedCondition.TRUE, "When this permanent enters, " +
|
||||
"if the gift was promised, they " + giftType.getDescription() + '.'
|
||||
).setRuleVisible(false));
|
||||
this.addSubAbility(new EntersBattlefieldTriggeredAbility(new PromiseGiftEffect(giftType))
|
||||
.setTriggerPhrase("When this permanent enters, ")
|
||||
.withInterveningIf(GiftWasPromisedCondition.TRUE)
|
||||
.setRuleVisible(false));
|
||||
} else {
|
||||
card.getSpellAbility().addEffect(new PromiseGiftEffect(giftType));
|
||||
}
|
||||
|
|
@ -154,6 +152,7 @@ class PromiseGiftEffect extends OneShotEffect {
|
|||
PromiseGiftEffect(GiftType giftType) {
|
||||
super(Outcome.Benefit);
|
||||
this.giftType = giftType;
|
||||
staticText = "they " + giftType.getDescription();
|
||||
}
|
||||
|
||||
private PromiseGiftEffect(final PromiseGiftEffect effect) {
|
||||
|
|
|
|||
|
|
@ -7,7 +7,6 @@ import mage.abilities.common.EntersBattlefieldTriggeredAbility;
|
|||
import mage.abilities.condition.Condition;
|
||||
import mage.abilities.costs.*;
|
||||
import mage.abilities.costs.mana.ManaCostsImpl;
|
||||
import mage.abilities.decorator.ConditionalInterveningIfTriggeredAbility;
|
||||
import mage.abilities.effects.OneShotEffect;
|
||||
import mage.abilities.effects.common.CreateTokenCopyTargetEffect;
|
||||
import mage.constants.Outcome;
|
||||
|
|
@ -43,10 +42,8 @@ public class OffspringAbility extends StaticAbility implements OptionalAdditiona
|
|||
this.additionalCost.setRepeatable(false);
|
||||
this.rule = additionalCost.getName() + ' ' + additionalCost.getReminderText();
|
||||
this.setRuleAtTheTop(true);
|
||||
this.addSubAbility(new ConditionalInterveningIfTriggeredAbility(
|
||||
new EntersBattlefieldTriggeredAbility(new OffspringEffect()), OffspringCondition.instance,
|
||||
"When this creature enters, if its offspring cost was paid, create a 1/1 token copy of it."
|
||||
).setRuleVisible(false));
|
||||
this.addSubAbility(new EntersBattlefieldTriggeredAbility(new OffspringEffect())
|
||||
.withInterveningIf(OffspringCondition.instance).setRuleVisible(false));
|
||||
}
|
||||
|
||||
private OffspringAbility(final OffspringAbility ability) {
|
||||
|
|
@ -96,6 +93,7 @@ class OffspringEffect extends OneShotEffect {
|
|||
|
||||
OffspringEffect() {
|
||||
super(Outcome.Benefit);
|
||||
staticText = "create a 1/1 token copy of it";
|
||||
}
|
||||
|
||||
private OffspringEffect(final OffspringEffect effect) {
|
||||
|
|
@ -127,6 +125,6 @@ enum OffspringCondition implements Condition {
|
|||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "Offspring cost was paid";
|
||||
return "its offspring cost was paid";
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -4,7 +4,6 @@ import mage.abilities.Ability;
|
|||
import mage.abilities.common.EntersBattlefieldAbility;
|
||||
import mage.abilities.common.EntersBattlefieldTriggeredAbility;
|
||||
import mage.abilities.condition.Condition;
|
||||
import mage.abilities.decorator.ConditionalInterveningIfTriggeredAbility;
|
||||
import mage.abilities.dynamicvalue.common.GetXValue;
|
||||
import mage.abilities.effects.common.DrawCardSourceControllerEffect;
|
||||
import mage.abilities.effects.common.EntersBattlefieldWithXCountersEffect;
|
||||
|
|
@ -18,13 +17,8 @@ public class RavenousAbility extends EntersBattlefieldAbility {
|
|||
|
||||
public RavenousAbility() {
|
||||
super(new EntersBattlefieldWithXCountersEffect(CounterType.P1P1.createInstance()));
|
||||
Ability ability = new ConditionalInterveningIfTriggeredAbility(
|
||||
new EntersBattlefieldTriggeredAbility(new DrawCardSourceControllerEffect(1)),
|
||||
RavenousAbilityCondition.instance, "When this creature enters, " +
|
||||
"if X is 5 or more, draw a card"
|
||||
);
|
||||
ability.setRuleVisible(false);
|
||||
this.addSubAbility(ability);
|
||||
this.addSubAbility(new EntersBattlefieldTriggeredAbility(new DrawCardSourceControllerEffect(1))
|
||||
.withInterveningIf(RavenousAbilityCondition.instance).setRuleVisible(false));
|
||||
}
|
||||
|
||||
private RavenousAbility(final RavenousAbility ability) {
|
||||
|
|
@ -50,4 +44,9 @@ enum RavenousAbilityCondition implements Condition {
|
|||
public boolean apply(Game game, Ability source) {
|
||||
return GetXValue.instance.calculate(game, source, null) >= 5;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "X is 5 or more";
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -3,7 +3,6 @@ package mage.game.command.emblems;
|
|||
import mage.abilities.Ability;
|
||||
import mage.abilities.common.OneOrMoreCombatDamagePlayerTriggeredAbility;
|
||||
import mage.abilities.condition.Condition;
|
||||
import mage.abilities.decorator.ConditionalInterveningIfTriggeredAbility;
|
||||
import mage.abilities.effects.Effect;
|
||||
import mage.abilities.effects.OneShotEffect;
|
||||
import mage.constants.Outcome;
|
||||
|
|
@ -25,13 +24,9 @@ public final class LolthSpiderQueenEmblem extends Emblem {
|
|||
// −8: You get an emblem with "Whenever an opponent is dealt combat damage by one or more creatures you control, if that player lost less than 8 life this turn, they lose life equal to the difference."
|
||||
public LolthSpiderQueenEmblem() {
|
||||
super("Emblem Lolth");
|
||||
this.getAbilities().add(new ConditionalInterveningIfTriggeredAbility(
|
||||
new OneOrMoreCombatDamagePlayerTriggeredAbility(
|
||||
Zone.COMMAND, new LolthSpiderQueenEmblemEffect(), StaticFilters.FILTER_PERMANENT_CREATURES, SetTargetPointer.PLAYER, false
|
||||
), LolthSpiderQueenEmblemCondition.instance, "Whenever an opponent " +
|
||||
"is dealt combat damage by one or more creatures you control, " +
|
||||
"if that player lost less than 8 life this turn, they lose life equal to the difference."
|
||||
));
|
||||
this.getAbilities().add(new OneOrMoreCombatDamagePlayerTriggeredAbility(
|
||||
Zone.COMMAND, new LolthSpiderQueenEmblemEffect(), StaticFilters.FILTER_PERMANENT_CREATURES, SetTargetPointer.PLAYER, false
|
||||
).withInterveningIf(LolthSpiderQueenEmblemCondition.instance).setTriggerPhrase("Whenever an opponent is dealt combat damage by one or more creatures you control, "));
|
||||
}
|
||||
|
||||
private LolthSpiderQueenEmblem(final LolthSpiderQueenEmblem card) {
|
||||
|
|
@ -61,12 +56,18 @@ enum LolthSpiderQueenEmblemCondition implements Condition {
|
|||
PlayerLostLifeWatcher watcher = game.getState().getWatcher(PlayerLostLifeWatcher.class);
|
||||
return player != null && watcher != null && watcher.getLifeLost(player.getId()) < 8;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "that player lost less than 8 life this turn";
|
||||
}
|
||||
}
|
||||
|
||||
class LolthSpiderQueenEmblemEffect extends OneShotEffect {
|
||||
|
||||
LolthSpiderQueenEmblemEffect() {
|
||||
super(Outcome.Benefit);
|
||||
staticText = "they lose life equal to the difference";
|
||||
}
|
||||
|
||||
private LolthSpiderQueenEmblemEffect(final LolthSpiderQueenEmblemEffect effect) {
|
||||
|
|
|
|||
|
|
@ -1,10 +1,9 @@
|
|||
package mage.game.command.emblems;
|
||||
|
||||
import mage.abilities.Ability;
|
||||
import mage.abilities.triggers.BeginningOfFirstMainTriggeredAbility;
|
||||
import mage.abilities.condition.Condition;
|
||||
import mage.abilities.decorator.ConditionalInterveningIfTriggeredAbility;
|
||||
import mage.abilities.effects.OneShotEffect;
|
||||
import mage.abilities.triggers.BeginningOfFirstMainTriggeredAbility;
|
||||
import mage.cards.Cards;
|
||||
import mage.cards.FrameStyle;
|
||||
import mage.cards.repository.TokenInfo;
|
||||
|
|
@ -31,12 +30,9 @@ public class RadiationEmblem extends Emblem {
|
|||
super("Radiation");
|
||||
this.frameStyle = FrameStyle.M15_NORMAL;
|
||||
|
||||
this.getAbilities().add(new ConditionalInterveningIfTriggeredAbility(
|
||||
new BeginningOfFirstMainTriggeredAbility(Zone.ALL, TargetController.YOU, new RadiationEffect(), false),
|
||||
RadiationCondition.instance,
|
||||
"At the beginning of your precombat main phase, if you have any rad counters, "
|
||||
+ "mill that many cards. For each nonland card milled this way, you lose 1 life and a rad counter."
|
||||
));
|
||||
this.getAbilities().add(new BeginningOfFirstMainTriggeredAbility(
|
||||
Zone.ALL, TargetController.YOU, new RadiationEffect(), false
|
||||
).withInterveningIf(RadiationCondition.instance).setTriggerPhrase("At the beginning of each player's precombat main phase, "));
|
||||
|
||||
TokenInfo foundInfo = TokenRepository.instance.findPreferredTokenInfoForXmage(TokenRepository.XMAGE_IMAGE_NAME_RADIATION, null);
|
||||
if (foundInfo != null) {
|
||||
|
|
@ -69,6 +65,11 @@ enum RadiationCondition implements Condition {
|
|||
Player player = game.getPlayer(source.getControllerId());
|
||||
return player != null && player.getCountersCount(CounterType.RAD) > 0;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return "that player has one or more rad counters";
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
|||
|
|
@ -1,12 +1,11 @@
|
|||
package mage.game.permanent.token;
|
||||
|
||||
import mage.MageInt;
|
||||
import mage.abilities.triggers.BeginningOfCombatTriggeredAbility;
|
||||
import mage.abilities.condition.common.WasCardExiledThisTurnCondition;
|
||||
import mage.abilities.decorator.ConditionalInterveningIfTriggeredAbility;
|
||||
import mage.abilities.effects.common.counter.AddCountersSourceEffect;
|
||||
import mage.abilities.hint.ConditionHint;
|
||||
import mage.abilities.hint.Hint;
|
||||
import mage.abilities.triggers.BeginningOfCombatTriggeredAbility;
|
||||
import mage.constants.CardType;
|
||||
import mage.constants.SubType;
|
||||
import mage.counters.CounterType;
|
||||
|
|
@ -22,21 +21,16 @@ public final class AshiokWickedManipulatorNightmareToken extends TokenImpl {
|
|||
* /!\ You need to add CardsExiledThisTurnWatcher to any card using this token
|
||||
*/
|
||||
public AshiokWickedManipulatorNightmareToken() {
|
||||
super("Nightmare Token", "1/1 black Nightmare creature tokens with \"At the beginning of combat on your turn, if a card was put into exile this turn, put a +1/+1 counter on this creature.\"");
|
||||
super("Nightmare Token", "1/1 black Nightmare creature token with \"At the beginning of combat on your turn, if a card was put into exile this turn, put a +1/+1 counter on this token.\"");
|
||||
cardType.add(CardType.CREATURE);
|
||||
color.setBlack(true);
|
||||
subtype.add(SubType.NIGHTMARE);
|
||||
power = new MageInt(1);
|
||||
toughness = new MageInt(1);
|
||||
|
||||
this.addAbility(new ConditionalInterveningIfTriggeredAbility(
|
||||
new BeginningOfCombatTriggeredAbility(
|
||||
new AddCountersSourceEffect(CounterType.P1P1.createInstance())
|
||||
),
|
||||
WasCardExiledThisTurnCondition.instance,
|
||||
"At the beginning of combat on your turn, if a card was put into exile "
|
||||
+ "this turn, put a +1/+1 counter on this creature."
|
||||
).addHint(hint));
|
||||
this.addAbility(new BeginningOfCombatTriggeredAbility(
|
||||
new AddCountersSourceEffect(CounterType.P1P1.createInstance())
|
||||
).withInterveningIf(WasCardExiledThisTurnCondition.instance).addHint(hint));
|
||||
}
|
||||
|
||||
private AshiokWickedManipulatorNightmareToken(final AshiokWickedManipulatorNightmareToken token) {
|
||||
|
|
|
|||
|
|
@ -11,7 +11,7 @@ import mage.constants.Duration;
|
|||
import mage.constants.SubType;
|
||||
import mage.filter.common.FilterArtifactPermanent;
|
||||
import mage.target.TargetPermanent;
|
||||
import mage.target.targetadjustment.DamagedPlayerControlsTargetAdjuster;
|
||||
import mage.target.targetadjustment.ThatPlayerControlsTargetAdjuster;
|
||||
|
||||
public class DragonMenaceAndStealArtifactToken extends TokenImpl {
|
||||
|
||||
|
|
@ -31,7 +31,7 @@ public class DragonMenaceAndStealArtifactToken extends TokenImpl {
|
|||
|
||||
Ability ability = new DealsCombatDamageToAPlayerTriggeredAbility(new GainControlTargetEffect(Duration.EndOfGame), false, true);
|
||||
ability.addTarget(new TargetPermanent(filter));
|
||||
ability.setTargetAdjuster(new DamagedPlayerControlsTargetAdjuster());
|
||||
ability.setTargetAdjuster(new ThatPlayerControlsTargetAdjuster());
|
||||
addAbility(ability);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -5,7 +5,6 @@ import mage.abilities.common.AttacksTriggeredAbility;
|
|||
import mage.abilities.common.SimpleStaticAbility;
|
||||
import mage.abilities.condition.Condition;
|
||||
import mage.abilities.condition.common.SourceMatchesFilterCondition;
|
||||
import mage.abilities.decorator.ConditionalInterveningIfTriggeredAbility;
|
||||
import mage.abilities.effects.common.AttachEffect;
|
||||
import mage.abilities.effects.common.continuous.GainAbilityAttachedEffect;
|
||||
import mage.abilities.effects.common.counter.AddCountersSourceEffect;
|
||||
|
|
@ -23,7 +22,7 @@ import mage.target.common.TargetCreaturePermanent;
|
|||
*/
|
||||
public final class YoungHeroRoleToken extends TokenImpl {
|
||||
|
||||
private static final FilterPermanent filter = new FilterCreaturePermanent();
|
||||
private static final FilterPermanent filter = new FilterCreaturePermanent("its toughness is 3 or less");
|
||||
|
||||
static {
|
||||
filter.add(new ToughnessPredicate(ComparisonType.FEWER_THAN, 4));
|
||||
|
|
@ -45,10 +44,10 @@ public final class YoungHeroRoleToken extends TokenImpl {
|
|||
|
||||
// Enchanted creature has "Whenever this creature attacks, if its toughness is 3 or less, put a +1/+1 counter on it."
|
||||
this.addAbility(new SimpleStaticAbility(new GainAbilityAttachedEffect(
|
||||
new ConditionalInterveningIfTriggeredAbility(
|
||||
new AttacksTriggeredAbility(new AddCountersSourceEffect(CounterType.P1P1.createInstance())),
|
||||
condition, "Whenever this creature attacks, if its toughness is 3 or less, put a +1/+1 counter on it."
|
||||
), AttachmentType.AURA
|
||||
new AttacksTriggeredAbility(
|
||||
new AddCountersSourceEffect(CounterType.P1P1.createInstance())
|
||||
.setText("put a +1/+1 counter on it")
|
||||
).withInterveningIf(condition), AttachmentType.AURA
|
||||
)));
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -1,7 +1,6 @@
|
|||
package mage.target.targetadjustment;
|
||||
|
||||
import mage.abilities.Ability;
|
||||
import mage.abilities.common.OneOrMoreDamagePlayerTriggeredAbility;
|
||||
import mage.filter.Filter;
|
||||
import mage.filter.predicate.card.OwnerIdPredicate;
|
||||
import mage.filter.predicate.permanent.ControllerIdPredicate;
|
||||
|
|
@ -17,20 +16,20 @@ import java.util.UUID;
|
|||
/**
|
||||
* @author notgreat
|
||||
*/
|
||||
public class DamagedPlayerControlsTargetAdjuster extends GenericTargetAdjuster {
|
||||
public class ThatPlayerControlsTargetAdjuster extends GenericTargetAdjuster {
|
||||
private final boolean owner;
|
||||
|
||||
/**
|
||||
* Use with {@link mage.abilities.common.DealsCombatDamageToAPlayerTriggeredAbility} with setTargetPointer enabled,
|
||||
* or {@link OneOrMoreDamagePlayerTriggeredAbility} with "SetTargetPointer.PLAYER" or similar.
|
||||
* Adjusts the target to only target something the damaged player controls (or owns with alternative constructor)
|
||||
* And then removes the effects' target pointer that the triggered ability set
|
||||
* or {@link mage.abilities.common.OneOrMoreDamagePlayerTriggeredAbility} with "SetTargetPointer.PLAYER" or similar.
|
||||
* Adjusts the target to only target something the damaged/attacked/etc. player controls (or owns with alternative constructor)
|
||||
* And then removes the effects' target pointer that the triggered ability set, replacing it with the standard {@link FirstTargetPointer}
|
||||
*/
|
||||
public DamagedPlayerControlsTargetAdjuster() {
|
||||
public ThatPlayerControlsTargetAdjuster() {
|
||||
this(false);
|
||||
}
|
||||
|
||||
public DamagedPlayerControlsTargetAdjuster(boolean owner) {
|
||||
public ThatPlayerControlsTargetAdjuster(boolean owner) {
|
||||
this.owner = owner;
|
||||
}
|
||||
|
||||
|
|
@ -0,0 +1,52 @@
|
|||
package mage.watchers.common;
|
||||
|
||||
import mage.MageObjectReference;
|
||||
import mage.abilities.Ability;
|
||||
import mage.constants.WatcherScope;
|
||||
import mage.game.Game;
|
||||
import mage.game.events.GameEvent;
|
||||
import mage.game.permanent.Permanent;
|
||||
import mage.watchers.Watcher;
|
||||
|
||||
import java.util.HashSet;
|
||||
import java.util.Set;
|
||||
|
||||
/**
|
||||
* @author TheElk801
|
||||
*/
|
||||
public class DealtDamageThisGameWatcher extends Watcher {
|
||||
|
||||
private final Set<MageObjectReference> damagers = new HashSet<>();
|
||||
|
||||
public DealtDamageThisGameWatcher() {
|
||||
super(WatcherScope.GAME);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void watch(GameEvent event, Game game) {
|
||||
switch (event.getType()) {
|
||||
case BEGINNING_PHASE_PRE:
|
||||
// keep the stored values from getting too big, especially since it doesn't reset between games
|
||||
damagers.removeIf(mor -> !mor.zoneCounterIsCurrent(game));
|
||||
return;
|
||||
case DAMAGED_PERMANENT:
|
||||
case DAMAGED_PLAYER:
|
||||
break;
|
||||
default:
|
||||
return;
|
||||
}
|
||||
Permanent permanent = game.getPermanent(event.getSourceId());
|
||||
if (permanent != null) {
|
||||
damagers.add(new MageObjectReference(permanent, game));
|
||||
}
|
||||
}
|
||||
|
||||
public static boolean checkCreature(Game game, Ability source) {
|
||||
return game
|
||||
.getState()
|
||||
.getWatcher(DealtDamageThisGameWatcher.class)
|
||||
.damagers
|
||||
.stream()
|
||||
.noneMatch(mor -> mor.refersTo(source.getSourcePermanentOrLKI(game), game));
|
||||
}
|
||||
}
|
||||
Some files were not shown because too many files have changed in this diff Show more
Loading…
Add table
Add a link
Reference in a new issue