mirror of
https://github.com/magefree/mage.git
synced 2026-01-10 21:02:08 -08:00
move zoneChangeCounter to GameState - Card is now immutable
This commit is contained in:
parent
45aa5f675c
commit
6405c8d2f0
101 changed files with 899 additions and 257 deletions
|
|
@ -0,0 +1,173 @@
|
|||
/*
|
||||
* Copyright 2010 BetaSteward_at_googlemail.com. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without modification, are
|
||||
* permitted provided that the following conditions are met:
|
||||
*
|
||||
* 1. Redistributions of source code must retain the above copyright notice, this list of
|
||||
* conditions and the following disclaimer.
|
||||
*
|
||||
* 2. Redistributions in binary form must reproduce the above copyright notice, this list
|
||||
* of conditions and the following disclaimer in the documentation and/or other materials
|
||||
* provided with the distribution.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY BetaSteward_at_googlemail.com ``AS IS'' AND ANY EXPRESS OR IMPLIED
|
||||
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
|
||||
* FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL BetaSteward_at_googlemail.com OR
|
||||
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
|
||||
* SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
||||
* ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
|
||||
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
|
||||
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*
|
||||
* The views and conclusions contained in the software and documentation are those of the
|
||||
* authors and should not be interpreted as representing official policies, either expressed
|
||||
* or implied, of BetaSteward_at_googlemail.com.
|
||||
*/
|
||||
|
||||
package org.mage.test.cards.abilities.keywords;
|
||||
|
||||
import mage.constants.PhaseStep;
|
||||
import mage.constants.Zone;
|
||||
import mage.counters.CounterType;
|
||||
import org.junit.Test;
|
||||
import org.mage.test.serverside.base.CardTestPlayerBase;
|
||||
|
||||
/**
|
||||
*
|
||||
* @author BetaSteward
|
||||
*/
|
||||
public class KickerTest extends CardTestPlayerBase {
|
||||
|
||||
/**
|
||||
* 702.32. Kicker
|
||||
* 702.32a Kicker is a static ability that functions while the spell with kicker is on the stack. “Kicker
|
||||
* [cost]” means “You may pay an additional [cost] as you cast this spell.” Paying a spell’s kicker
|
||||
* cost(s) follows the rules for paying additional costs in rules 601.2b and 601.2e–g.
|
||||
* 702.32b The phrase “Kicker [cost 1] and/or [cost 2]” means the same thing as “Kicker [cost 1],
|
||||
* kicker [cost 2].”
|
||||
* 702.32c Multikicker is a variant of the kicker ability. “Multikicker [cost]” means “You may pay an
|
||||
* additional [cost] any number of times as you cast this spell.” A multikicker cost is a kicker cost.
|
||||
* 702.32d If a spell’s controller declares the intention to pay any of that spell’s kicker costs, that spell
|
||||
* has been “kicked.” If a spell has two kicker costs or has multikicker, it may be kicked multiple
|
||||
* times. See rule 601.2b.
|
||||
* 702.32e Objects with kicker or multikicker have additional abilities that specify what happens if
|
||||
* they are kicked. These abilities are linked to the kicker or multikicker abilities printed on that
|
||||
* object: they can refer only to those specific kicker or multikicker abilities. See rule 607, “Linked
|
||||
* Abilities.”
|
||||
* 702.32f Objects with more than one kicker cost have abilities that each correspond to a specific
|
||||
* kicker cost. They contain the phrases “if it was kicked with its [A] kicker” and “if it was kicked
|
||||
* with its [B] kicker,” where A and B are the first and second kicker costs listed on the card,
|
||||
* respectively. Each of those abilities is linked to the appropriate kicker ability.
|
||||
* 702.32g If part of a spell’s ability has its effect only if that spell was kicked, and that part of the
|
||||
* ability includes any targets, the spell’s controller chooses those targets only if that spell was
|
||||
* kicked. Otherwise, the spell is cast as if it did not have those targets. See rule 601.2c.
|
||||
*
|
||||
*/
|
||||
|
||||
/**
|
||||
* AEther Figment
|
||||
* Creature — Illusion 1/1, 1U (2)
|
||||
* Kicker {3} (You may pay an additional {3} as you cast this spell.)
|
||||
* AEther Figment can't be blocked.
|
||||
* If AEther Figment was kicked, it enters the battlefield with two +1/+1 counters on it.
|
||||
*
|
||||
*/
|
||||
@Test
|
||||
public void testUseKicker() {
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Island", 5);
|
||||
addCard(Zone.HAND, playerA, "AEther Figment");
|
||||
|
||||
castSpell(1, PhaseStep.PRECOMBAT_MAIN, playerA, "AEther Figment");
|
||||
setChoice(playerA, "Yes");
|
||||
|
||||
setStopAt(1, PhaseStep.BEGIN_COMBAT);
|
||||
execute();
|
||||
|
||||
assertPermanentCount(playerA, "AEther Figment", 1);
|
||||
assertCounterCount("AEther Figment", CounterType.P1P1, 2);
|
||||
assertPowerToughness(playerA, "AEther Figment", 3, 3);
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testDontUseKicker() {
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Island", 5);
|
||||
addCard(Zone.HAND, playerA, "AEther Figment");
|
||||
|
||||
castSpell(1, PhaseStep.PRECOMBAT_MAIN, playerA, "AEther Figment");
|
||||
setChoice(playerA, "No");
|
||||
|
||||
setStopAt(1, PhaseStep.BEGIN_COMBAT);
|
||||
execute();
|
||||
|
||||
assertPermanentCount(playerA, "AEther Figment", 1);
|
||||
assertCounterCount("AEther Figment", CounterType.P1P1, 0);
|
||||
assertPowerToughness(playerA, "AEther Figment", 1, 1);
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Apex Hawks
|
||||
* Creature — Bird 2/2, 2W (3)
|
||||
* Multikicker {1}{W} (You may pay an additional {1}{W} any number of times as you cast this spell.)
|
||||
* Flying
|
||||
* Apex Hawks enters the battlefield with a +1/+1 counter on it for each time it was kicked.
|
||||
*
|
||||
*/
|
||||
@Test
|
||||
public void testUseMultikickerOnce() {
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Plains", 5);
|
||||
addCard(Zone.HAND, playerA, "Apex Hawks");
|
||||
|
||||
castSpell(1, PhaseStep.PRECOMBAT_MAIN, playerA, "Apex Hawks");
|
||||
setChoice(playerA, "Yes");
|
||||
setChoice(playerA, "No");
|
||||
|
||||
setStopAt(1, PhaseStep.BEGIN_COMBAT);
|
||||
execute();
|
||||
|
||||
assertPermanentCount(playerA, "Apex Hawks", 1);
|
||||
assertCounterCount("Apex Hawks", CounterType.P1P1, 1);
|
||||
assertPowerToughness(playerA, "Apex Hawks", 3, 3);
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testUseMultikickerTwice() {
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Plains", 7);
|
||||
addCard(Zone.HAND, playerA, "Apex Hawks");
|
||||
|
||||
castSpell(1, PhaseStep.PRECOMBAT_MAIN, playerA, "Apex Hawks");
|
||||
setChoice(playerA, "Yes");
|
||||
setChoice(playerA, "Yes");
|
||||
setChoice(playerA, "No");
|
||||
|
||||
setStopAt(1, PhaseStep.BEGIN_COMBAT);
|
||||
execute();
|
||||
|
||||
assertPermanentCount(playerA, "Apex Hawks", 1);
|
||||
assertCounterCount("Apex Hawks", CounterType.P1P1, 2);
|
||||
assertPowerToughness(playerA, "Apex Hawks", 4, 4);
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testDontUseMultikicker() {
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Plains", 7);
|
||||
addCard(Zone.HAND, playerA, "Apex Hawks");
|
||||
|
||||
castSpell(1, PhaseStep.PRECOMBAT_MAIN, playerA, "Apex Hawks");
|
||||
setChoice(playerA, "No");
|
||||
|
||||
setStopAt(1, PhaseStep.BEGIN_COMBAT);
|
||||
execute();
|
||||
|
||||
assertPermanentCount(playerA, "Apex Hawks", 1);
|
||||
assertCounterCount("Apex Hawks", CounterType.P1P1, 0);
|
||||
assertPowerToughness(playerA, "Apex Hawks", 2, 2);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
|
@ -0,0 +1,140 @@
|
|||
/*
|
||||
* Copyright 2010 BetaSteward_at_googlemail.com. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without modification, are
|
||||
* permitted provided that the following conditions are met:
|
||||
*
|
||||
* 1. Redistributions of source code must retain the above copyright notice, this list of
|
||||
* conditions and the following disclaimer.
|
||||
*
|
||||
* 2. Redistributions in binary form must reproduce the above copyright notice, this list
|
||||
* of conditions and the following disclaimer in the documentation and/or other materials
|
||||
* provided with the distribution.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY BetaSteward_at_googlemail.com ``AS IS'' AND ANY EXPRESS OR IMPLIED
|
||||
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
|
||||
* FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL BetaSteward_at_googlemail.com OR
|
||||
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
|
||||
* SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
||||
* ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
|
||||
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
|
||||
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*
|
||||
* The views and conclusions contained in the software and documentation are those of the
|
||||
* authors and should not be interpreted as representing official policies, either expressed
|
||||
* or implied, of BetaSteward_at_googlemail.com.
|
||||
*/
|
||||
|
||||
package org.mage.test.cards.abilities.keywords;
|
||||
|
||||
import mage.constants.PhaseStep;
|
||||
import mage.constants.Zone;
|
||||
import mage.counters.CounterType;
|
||||
import org.junit.Test;
|
||||
import org.mage.test.serverside.base.CardTestPlayerBase;
|
||||
|
||||
/**
|
||||
*
|
||||
* @author BetaSteward
|
||||
*/
|
||||
public class StormTest extends CardTestPlayerBase {
|
||||
|
||||
/**
|
||||
* 702.39. Storm
|
||||
* 702.39a Storm is a triggered ability that functions on the stack. “Storm” means “When you cast this
|
||||
* spell, put a copy of it onto the stack for each other spell that was cast before it this turn. If the
|
||||
* spell has any targets, you may choose new targets for any of the copies.”
|
||||
* 702.39b If a spell has multiple instances of storm, each triggers separately.
|
||||
*
|
||||
*/
|
||||
|
||||
/**
|
||||
* Grapeshot
|
||||
* Sorcery, 1R (2)
|
||||
* Grapeshot deals 1 damage to target creature or player.
|
||||
* Storm (When you cast this spell, copy it for each spell cast before it
|
||||
* this turn. You may choose new targets for the copies.)
|
||||
*
|
||||
*/
|
||||
|
||||
@Test
|
||||
public void testStorm1x() {
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Mountain", 3);
|
||||
addCard(Zone.HAND, playerA, "Grapeshot");
|
||||
addCard(Zone.HAND, playerA, "Lightning Bolt");
|
||||
|
||||
castSpell(1, PhaseStep.PRECOMBAT_MAIN, playerA, "Lightning Bolt", playerB);
|
||||
castSpell(1, PhaseStep.POSTCOMBAT_MAIN, playerA, "Grapeshot", playerB);
|
||||
|
||||
setStopAt(1, PhaseStep.END_TURN);
|
||||
execute();
|
||||
|
||||
assertLife(playerB, 15);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testStorm2x() {
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Mountain", 4);
|
||||
addCard(Zone.HAND, playerA, "Grapeshot");
|
||||
addCard(Zone.HAND, playerA, "Lightning Bolt", 2);
|
||||
|
||||
castSpell(1, PhaseStep.PRECOMBAT_MAIN, playerA, "Lightning Bolt", playerB);
|
||||
castSpell(1, PhaseStep.PRECOMBAT_MAIN, playerA, "Lightning Bolt", playerB);
|
||||
castSpell(1, PhaseStep.POSTCOMBAT_MAIN, playerA, "Grapeshot", playerB);
|
||||
|
||||
setStopAt(1, PhaseStep.END_TURN);
|
||||
execute();
|
||||
|
||||
assertLife(playerB, 11);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testStorm3x() {
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Mountain", 5);
|
||||
addCard(Zone.HAND, playerA, "Grapeshot");
|
||||
addCard(Zone.HAND, playerA, "Lightning Bolt", 3);
|
||||
|
||||
castSpell(1, PhaseStep.PRECOMBAT_MAIN, playerA, "Lightning Bolt", playerB);
|
||||
castSpell(1, PhaseStep.PRECOMBAT_MAIN, playerA, "Lightning Bolt", playerB);
|
||||
castSpell(1, PhaseStep.PRECOMBAT_MAIN, playerA, "Lightning Bolt", playerB);
|
||||
castSpell(1, PhaseStep.POSTCOMBAT_MAIN, playerA, "Grapeshot", playerB);
|
||||
|
||||
setStopAt(1, PhaseStep.END_TURN);
|
||||
execute();
|
||||
|
||||
assertLife(playerB, 7);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testStorm4x() {
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Mountain", 6);
|
||||
addCard(Zone.HAND, playerA, "Grapeshot");
|
||||
addCard(Zone.HAND, playerA, "Lightning Bolt", 4);
|
||||
|
||||
castSpell(1, PhaseStep.PRECOMBAT_MAIN, playerA, "Lightning Bolt", playerB);
|
||||
castSpell(1, PhaseStep.PRECOMBAT_MAIN, playerA, "Lightning Bolt", playerB);
|
||||
castSpell(1, PhaseStep.PRECOMBAT_MAIN, playerA, "Lightning Bolt", playerB);
|
||||
castSpell(1, PhaseStep.PRECOMBAT_MAIN, playerA, "Lightning Bolt", playerB);
|
||||
castSpell(1, PhaseStep.POSTCOMBAT_MAIN, playerA, "Grapeshot", playerB);
|
||||
|
||||
setStopAt(1, PhaseStep.END_TURN);
|
||||
execute();
|
||||
|
||||
assertLife(playerB, 3);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testNoStorm() {
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Mountain", 2);
|
||||
addCard(Zone.HAND, playerA, "Grapeshot");
|
||||
|
||||
castSpell(1, PhaseStep.POSTCOMBAT_MAIN, playerA, "Grapeshot", playerB);
|
||||
|
||||
setStopAt(1, PhaseStep.END_TURN);
|
||||
execute();
|
||||
|
||||
assertLife(playerB, 19);
|
||||
}
|
||||
|
||||
}
|
||||
|
|
@ -0,0 +1,131 @@
|
|||
/*
|
||||
* Copyright 2010 BetaSteward_at_googlemail.com. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without modification, are
|
||||
* permitted provided that the following conditions are met:
|
||||
*
|
||||
* 1. Redistributions of source code must retain the above copyright notice, this list of
|
||||
* conditions and the following disclaimer.
|
||||
*
|
||||
* 2. Redistributions in binary form must reproduce the above copyright notice, this list
|
||||
* of conditions and the following disclaimer in the documentation and/or other materials
|
||||
* provided with the distribution.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY BetaSteward_at_googlemail.com ``AS IS'' AND ANY EXPRESS OR IMPLIED
|
||||
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
|
||||
* FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL BetaSteward_at_googlemail.com OR
|
||||
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
|
||||
* SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
||||
* ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
|
||||
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
|
||||
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*
|
||||
* The views and conclusions contained in the software and documentation are those of the
|
||||
* authors and should not be interpreted as representing official policies, either expressed
|
||||
* or implied, of BetaSteward_at_googlemail.com.
|
||||
*/
|
||||
|
||||
package org.mage.test.cards.continuous;
|
||||
|
||||
import mage.constants.CardType;
|
||||
import mage.constants.PhaseStep;
|
||||
import mage.constants.Zone;
|
||||
import org.junit.Test;
|
||||
import org.mage.test.serverside.base.CardTestPlayerBase;
|
||||
|
||||
/**
|
||||
*
|
||||
* @author BetaSteward
|
||||
*/
|
||||
public class MarchOfTheMachinesTest extends CardTestPlayerBase {
|
||||
|
||||
/**
|
||||
* March of the Machines
|
||||
* Enchantment, 3U (4)
|
||||
* Each noncreature artifact is an artifact creature with power and toughness
|
||||
* each equal to its converted mana cost. (Equipment that's a creature can't
|
||||
* equip a creature.)
|
||||
*
|
||||
*/
|
||||
|
||||
/**
|
||||
* Abzan Banner
|
||||
* Artifact, 3 (3)
|
||||
* {T}: Add {W}, {B}, or {G} to your mana pool.
|
||||
* {W}{B}{G}, {T}, Sacrifice Abzan Banner: Draw a card.
|
||||
*/
|
||||
|
||||
@Test
|
||||
public void testNonCreatureArtifactsBecomeCreatures() {
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Island", 4);
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Abzan Banner");
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Alloy Myr");
|
||||
addCard(Zone.HAND, playerA, "March of the Machines");
|
||||
|
||||
castSpell(1, PhaseStep.PRECOMBAT_MAIN, playerA, "March of the Machines");
|
||||
|
||||
setStopAt(1, PhaseStep.BEGIN_COMBAT);
|
||||
execute();
|
||||
|
||||
assertPowerToughness(playerA, "Alloy Myr", 2, 2);
|
||||
assertPermanentCount(playerA, "Abzan Banner", 1);
|
||||
assertPowerToughness(playerA, "Abzan Banner", 3, 3);
|
||||
assertType("Abzan Banner", CardType.CREATURE, true);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testArtifactsRevertBack() {
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Island", 4);
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Abzan Banner");
|
||||
addCard(Zone.HAND, playerA, "March of the Machines");
|
||||
|
||||
addCard(Zone.HAND, playerB, "Disenchant");
|
||||
addCard(Zone.BATTLEFIELD, playerB, "Plains", 2);
|
||||
|
||||
castSpell(1, PhaseStep.PRECOMBAT_MAIN, playerA, "March of the Machines");
|
||||
castSpell(2, PhaseStep.PRECOMBAT_MAIN, playerB, "Disenchant", "March of the Machines");
|
||||
|
||||
setStopAt(2, PhaseStep.BEGIN_COMBAT);
|
||||
execute();
|
||||
|
||||
assertPermanentCount(playerA, "Abzan Banner", 1);
|
||||
assertType("Abzan Banner", CardType.CREATURE, false);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testEquipmentDetaches() {
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Island", 6);
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Avacyn's Collar");
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Ornithopter");
|
||||
addCard(Zone.HAND, playerA, "March of the Machines");
|
||||
|
||||
activateAbility(1, PhaseStep.PRECOMBAT_MAIN, playerA, "Equip", "Ornithopter");
|
||||
castSpell(1, PhaseStep.POSTCOMBAT_MAIN, playerA, "March of the Machines");
|
||||
|
||||
setStopAt(1, PhaseStep.END_TURN);
|
||||
execute();
|
||||
|
||||
assertPermanentCount(playerA, "Ornithopter", 1);
|
||||
assertPowerToughness(playerA, "Ornithopter", 0, 2);
|
||||
assertPermanentCount(playerA, "Avacyn's Collar", 1);
|
||||
assertPowerToughness(playerA, "Avacyn's Collar", 1, 1);
|
||||
assertType("Avacyn's Collar", CardType.CREATURE, true);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testZeroCostIsDestroyed() {
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Island", 4);
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Accorder's Shield");
|
||||
addCard(Zone.HAND, playerA, "March of the Machines");
|
||||
|
||||
castSpell(1, PhaseStep.PRECOMBAT_MAIN, playerA, "March of the Machines");
|
||||
|
||||
setStopAt(1, PhaseStep.BEGIN_COMBAT);
|
||||
execute();
|
||||
|
||||
assertPermanentCount(playerA, "Accorder's Shield", 0);
|
||||
assertGraveyardCount(playerA, "Accorder's Shield", 1);
|
||||
}
|
||||
|
||||
}
|
||||
|
|
@ -0,0 +1,122 @@
|
|||
/*
|
||||
* Copyright 2010 BetaSteward_at_googlemail.com. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without modification, are
|
||||
* permitted provided that the following conditions are met:
|
||||
*
|
||||
* 1. Redistributions of source code must retain the above copyright notice, this list of
|
||||
* conditions and the following disclaimer.
|
||||
*
|
||||
* 2. Redistributions in binary form must reproduce the above copyright notice, this list
|
||||
* of conditions and the following disclaimer in the documentation and/or other materials
|
||||
* provided with the distribution.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY BetaSteward_at_googlemail.com ``AS IS'' AND ANY EXPRESS OR IMPLIED
|
||||
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
|
||||
* FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL BetaSteward_at_googlemail.com OR
|
||||
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
|
||||
* SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
||||
* ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
|
||||
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
|
||||
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
*
|
||||
* The views and conclusions contained in the software and documentation are those of the
|
||||
* authors and should not be interpreted as representing official policies, either expressed
|
||||
* or implied, of BetaSteward_at_googlemail.com.
|
||||
*/
|
||||
|
||||
package org.mage.test.cards.dynamicvalue;
|
||||
|
||||
import mage.constants.PhaseStep;
|
||||
import mage.constants.Zone;
|
||||
import org.junit.Test;
|
||||
import org.mage.test.serverside.base.CardTestPlayerBase;
|
||||
|
||||
/**
|
||||
*
|
||||
* @author BetaSteward
|
||||
*/
|
||||
public class SweepTest extends CardTestPlayerBase {
|
||||
|
||||
|
||||
/**
|
||||
* Plow Through Reito
|
||||
* 1W
|
||||
* Instant -- Arcane
|
||||
* Sweep -- Return any number of Plains you control to their owner's hand.
|
||||
* Target creature gets +1/+1 until end of turn for each Plains returned this way.
|
||||
*
|
||||
*/
|
||||
@Test
|
||||
public void testSweep1x() {
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Plains", 5);
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Raging Goblin");
|
||||
addCard(Zone.HAND, playerA, "Plow Through Reito");
|
||||
|
||||
castSpell(1, PhaseStep.PRECOMBAT_MAIN, playerA, "Plow Through Reito");
|
||||
addTarget(playerA, "Plains");
|
||||
|
||||
setStopAt(1, PhaseStep.BEGIN_COMBAT);
|
||||
execute();
|
||||
|
||||
assertPermanentCount(playerA, "Raging Goblin", 1);
|
||||
assertPermanentCount(playerA, "Plains", 4);
|
||||
assertPowerToughness(playerA, "Raging Goblin", 2, 2);
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testSweep2x() {
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Plains", 5);
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Raging Goblin");
|
||||
addCard(Zone.HAND, playerA, "Plow Through Reito");
|
||||
|
||||
castSpell(1, PhaseStep.PRECOMBAT_MAIN, playerA, "Plow Through Reito");
|
||||
addTarget(playerA, "Plains^Plains");
|
||||
|
||||
setStopAt(1, PhaseStep.BEGIN_COMBAT);
|
||||
execute();
|
||||
|
||||
assertPermanentCount(playerA, "Raging Goblin", 1);
|
||||
assertPermanentCount(playerA, "Plains", 3);
|
||||
assertPowerToughness(playerA, "Raging Goblin", 3, 3);
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testSweep3x() {
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Plains", 5);
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Raging Goblin");
|
||||
addCard(Zone.HAND, playerA, "Plow Through Reito");
|
||||
|
||||
castSpell(1, PhaseStep.PRECOMBAT_MAIN, playerA, "Plow Through Reito");
|
||||
addTarget(playerA, "Plains^Plains^Plains");
|
||||
|
||||
setStopAt(1, PhaseStep.BEGIN_COMBAT);
|
||||
execute();
|
||||
|
||||
assertPermanentCount(playerA, "Raging Goblin", 1);
|
||||
assertPermanentCount(playerA, "Plains", 2);
|
||||
assertPowerToughness(playerA, "Raging Goblin", 4, 4);
|
||||
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testSweep0x() {
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Plains", 5);
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Raging Goblin");
|
||||
addCard(Zone.HAND, playerA, "Plow Through Reito");
|
||||
|
||||
castSpell(1, PhaseStep.PRECOMBAT_MAIN, playerA, "Plow Through Reito");
|
||||
|
||||
setStopAt(1, PhaseStep.BEGIN_COMBAT);
|
||||
execute();
|
||||
|
||||
assertPermanentCount(playerA, "Raging Goblin", 1);
|
||||
assertPermanentCount(playerA, "Plains", 5);
|
||||
assertPowerToughness(playerA, "Raging Goblin", 1, 1);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
|
@ -11,6 +11,28 @@ import org.mage.test.serverside.base.CardTestPlayerBase;
|
|||
*/
|
||||
public class HuntmasterOfTheFellsTest extends CardTestPlayerBase {
|
||||
|
||||
/**
|
||||
* Huntmaster of the Fells
|
||||
* Creature — Human Werewolf 2/2, 2RG (4)
|
||||
* Whenever this creature enters the battlefield or transforms into Huntmaster
|
||||
* of the Fells, put a 2/2 green Wolf creature token onto the battlefield and
|
||||
* you gain 2 life.
|
||||
* At the beginning of each upkeep, if no spells were cast last turn, transform
|
||||
* Huntmaster of the Fells.
|
||||
*
|
||||
*/
|
||||
|
||||
/**
|
||||
* Ravager of the Fells
|
||||
* Creature — Werewolf 4/4
|
||||
* Trample
|
||||
* Whenever this creature transforms into Ravager of the Fells, it deals 2
|
||||
* damage to target opponent and 2 damage to up to one target creature that
|
||||
* player controls.
|
||||
* At the beginning of each upkeep, if a player cast two or more spells last
|
||||
* turn, transform Ravager of the Fells.
|
||||
*/
|
||||
|
||||
@Test
|
||||
public void testCard() {
|
||||
addCard(Zone.BATTLEFIELD, playerA, "Forest", 3);
|
||||
|
|
|
|||
|
|
@ -31,6 +31,7 @@ import java.io.FilenameFilter;
|
|||
import java.util.*;
|
||||
import java.util.regex.Matcher;
|
||||
import java.util.regex.Pattern;
|
||||
import static org.mage.test.serverside.base.MageTestPlayerBase.currentGame;
|
||||
|
||||
/**
|
||||
* Base class for all tests.
|
||||
|
|
@ -259,7 +260,7 @@ public abstract class MageTestBase {
|
|||
Card card = cardInfo != null ? cardInfo.getCard() : null;
|
||||
if (card != null) {
|
||||
if (gameZone.equals(Zone.BATTLEFIELD)) {
|
||||
PermanentCard p = new PermanentCard(card, null);
|
||||
PermanentCard p = new PermanentCard(card, null, currentGame);
|
||||
p.setTapped(tapped);
|
||||
perms.add(p);
|
||||
} else {
|
||||
|
|
|
|||
|
|
@ -239,7 +239,7 @@ public abstract class MageTestPlayerBase {
|
|||
Card card = cardInfo != null ? cardInfo.getCard() : null;
|
||||
if (card != null) {
|
||||
if (gameZone.equals(Zone.BATTLEFIELD)) {
|
||||
PermanentCard p = new PermanentCard(card, null);
|
||||
PermanentCard p = new PermanentCard(card, null, currentGame);
|
||||
p.setTapped(tapped);
|
||||
perms.add(p);
|
||||
} else {
|
||||
|
|
|
|||
|
|
@ -124,7 +124,7 @@ public abstract class CardTestAPIImpl extends MageTestBase implements CardTestAP
|
|||
if (card == null) {
|
||||
throw new IllegalArgumentException("[TEST] Couldn't find a card: " + cardName);
|
||||
}
|
||||
PermanentCard p = new PermanentCard(card, null);
|
||||
PermanentCard p = new PermanentCard(card, null, currentGame);
|
||||
p.setTapped(tapped);
|
||||
if (player.equals(playerA)) {
|
||||
battlefieldCardsA.add(p);
|
||||
|
|
|
|||
|
|
@ -37,6 +37,7 @@ import java.util.UUID;
|
|||
public abstract class CardTestPlayerAPIImpl extends MageTestPlayerBase implements CardTestAPI {
|
||||
|
||||
static {
|
||||
// CardScanner.scanned = true;
|
||||
CardScanner.scan();
|
||||
}
|
||||
|
||||
|
|
@ -168,7 +169,7 @@ public abstract class CardTestPlayerAPIImpl extends MageTestPlayerBase implement
|
|||
if (card == null) {
|
||||
throw new IllegalArgumentException("[TEST] Couldn't find a card: " + cardName);
|
||||
}
|
||||
PermanentCard p = new PermanentCard(card, null);
|
||||
PermanentCard p = new PermanentCard(card, null, currentGame);
|
||||
p.setTapped(tapped);
|
||||
getBattlefieldCards(player).add(p);
|
||||
}
|
||||
|
|
@ -511,6 +512,28 @@ public abstract class CardTestPlayerAPIImpl extends MageTestPlayerBase implement
|
|||
*
|
||||
* @param cardName Name of the permanent that should be checked.
|
||||
* @param type A type to test for
|
||||
* @param flag true if creature should have type, false if it should not
|
||||
*/
|
||||
public void assertType(String cardName, CardType type, boolean flag) throws AssertionError {
|
||||
Permanent found = null;
|
||||
for (Permanent permanent : currentGame.getBattlefield().getAllActivePermanents()) {
|
||||
if (permanent.getName().equals(cardName)) {
|
||||
found = permanent;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
Assert.assertNotNull("There is no such permanent on the battlefield, cardName=" + cardName, found);
|
||||
|
||||
Assert.assertTrue("(Battlefield) card type not found (" + cardName + ":" + type + ")", (found.getCardType().contains(type) == flag));
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Assert whether a permanent is a specified type
|
||||
*
|
||||
* @param cardName Name of the permanent that should be checked.
|
||||
* @param type A type to test for
|
||||
* @param subType a subtype to test for
|
||||
*/
|
||||
public void assertType(String cardName, CardType type, String subType) throws AssertionError {
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue