This commit is contained in:
Goudt 2017-01-30 20:31:23 +01:00
commit bfbffb4582
13 changed files with 196 additions and 30 deletions

View file

@ -599,7 +599,7 @@ public class TablesPanel extends javax.swing.JPanel {
formatFilterList.add(RowFilter.regexFilter("^Limited", TableTableModel.COLUMN_DECK_TYPE));
}
if (btnFormatOther.isSelected()) {
formatFilterList.add(RowFilter.regexFilter("^Momir Basic|^Constructed - Pauper|^Constructed - Frontier|^Constructed - Extended|^Constructed - Eternal|^Constructed - Historical|^Constructed - Super|^Constructed - Freeform|^Australian Highlander", TableTableModel.COLUMN_DECK_TYPE));
formatFilterList.add(RowFilter.regexFilter("^Momir Basic|^Constructed - Pauper|^Constructed - Frontier|^Constructed - Extended|^Constructed - Eternal|^Constructed - Historical|^Constructed - Super|^Constructed - Freeform|^Australian Highlander|^Canadian Highlander", TableTableModel.COLUMN_DECK_TYPE));
}
List<RowFilter<Object, Object>> skillFilterList = new ArrayList<>();

View file

@ -0,0 +1,158 @@
/*
* Copyright 2011 BetaSteward_at_googlemail.com. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without modification, are
* permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice, this list of
* conditions and the following disclaimer.
*
* 2. Redistributions in binary form must reproduce the above copyright notice, this list
* of conditions and the following disclaimer in the documentation and/or other materials
* provided with the distribution.
*
* THIS SOFTWARE IS PROVIDED BY BetaSteward_at_googlemail.com ``AS IS'' AND ANY EXPRESS OR IMPLIED
* WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
* FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL BetaSteward_at_googlemail.com OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
* SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
* ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
* ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*
* The views and conclusions contained in the software and documentation are those of the
* authors and should not be interpreted as representing official policies, either expressed
* or implied, of BetaSteward_at_googlemail.com.
*/
package mage.deck;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import mage.cards.ExpansionSet;
import mage.cards.Sets;
import mage.cards.decks.Constructed;
import mage.cards.decks.Deck;
import mage.constants.SetType;
/**
*
* @author spjspj
*/
public class CanadianHighlander extends Constructed {
public CanadianHighlander() {
this("Canadian Highlander");
for (ExpansionSet set : Sets.getInstance().values()) {
if (set.getSetType() != SetType.CUSTOM_SET) {
setCodes.add(set.getCode());
}
}
}
public CanadianHighlander(String name) {
super(name);
}
@Override
public boolean validate(Deck deck) {
boolean valid = true;
if (deck.getCards().size() < 100) {
invalid.put("Deck", "Must contain 100 or more singleton cards: has " + (deck.getCards().size()) + " cards");
valid = false;
}
if (deck.getSideboard().size() > 0) {
invalid.put("Deck", "Sideboard can't contain any cards: has " + (deck.getSideboard().size()) + " cards");
valid = false;
}
List<String> basicLandNames = new ArrayList<>(Arrays.asList("Forest", "Island", "Mountain", "Swamp", "Plains", "Wastes",
"Snow-Covered Forest", "Snow-Covered Island", "Snow-Covered Mountain", "Snow-Covered Swamp", "Snow-Covered Plains"));
Map<String, Integer> counts = new HashMap<>();
countCards(counts, deck.getCards());
countCards(counts, deck.getSideboard());
for (Map.Entry<String, Integer> entry : counts.entrySet()) {
if (entry.getValue() > 1) {
if (!basicLandNames.contains(entry.getKey()) && !entry.getKey().equals("Relentless Rats") && !entry.getKey().equals("Shadowborn Apostle")) {
invalid.put(entry.getKey(), "Too many: " + entry.getValue());
valid = false;
}
}
}
int allowedPoints = 10 * (int) Math.floor(deck.getCards().size()/100.0);
int totalPoints = 0;
for (Map.Entry<String, Integer> entry : counts.entrySet()) {
String cn = entry.getKey();
if(cn.equals("Balance")
|| cn.equals("Dig Through Time")
|| cn.equals("Fastbond")
|| cn.equals("Gifts Ungiven")
|| cn.equals("Intuition")
|| cn.equals("Library of Alexandria")
|| cn.equals("Lim-Dul's Vault")
|| cn.equals("Mana Vault")
|| cn.equals("Mind Twist")
|| cn.equals("Oath of Druids")
|| cn.equals("Personal Tutor")
|| cn.equals("Stoneforge Mystic")
|| cn.equals("Tainted Pact")
|| cn.equals("Tolarian Academy")
|| cn.equals("Transmute Artifact")
|| cn.equals("Treasure Cruise")
|| cn.equals("True-Name Nemesis")) {
totalPoints += 1;
}
if(cn.equals("Doomsday")
|| cn.equals("Enlightened Tutor")
|| cn.equals("Imperial Seal")
|| cn.equals("Mana Crypt")
|| cn.equals("Mystical Tutor")
|| cn.equals("Strip Mine")
|| cn.equals("Summoner's Pact")
|| cn.equals("Survival of the Fittest")
|| cn.equals("Umezawa's Jitte")) {
totalPoints += 2;
}
if(cn.equals("Birthing Pod")
|| cn.equals("Mox Emerald")
|| cn.equals("Mox Jet")
|| cn.equals("Mox Pearl")
|| cn.equals("Mox Ruby")
|| cn.equals("Mox Sapphire")
|| cn.equals("Protean Hulk")
|| cn.equals("Vampiric Tutor")) {
totalPoints += 3;
}
if(cn.equals("Demonic Tutor")
|| cn.equals("Hermit Druid")
|| cn.equals("Sol Ring")) {
totalPoints += 4;
}
if(cn.equals("Ancestral Recall")
|| cn.equals("Natural Order")
|| cn.equals("Time Walk")
|| cn.equals("Tinker")) {
totalPoints += 5;
}
if(cn.equals("Flash")) {
totalPoints += 6;
}
if(cn.equals("Black Lotus")
|| cn.equals("Time Vault")) {
totalPoints += 7;
}
}
if(totalPoints > allowedPoints) {
invalid.put("Total points too high", "Your calculated point total was " + totalPoints);
valid = false;
}
return valid;
}
}

View file

@ -133,6 +133,7 @@
<deckType name="Constructed - Super Type 2" jar="mage-deck-constructed.jar" className="mage.deck.SuperType2"/>
<deckType name="Constructed - Freeform" jar="mage-deck-constructed.jar" className="mage.deck.Freeform"/>
<deckType name="Constructed - Australian Highlander" jar="mage-deck-constructed.jar" className="mage.deck.AusHighlander"/>
<deckType name="Constructed - Canadian Highlander" jar="mage-deck-constructed.jar" className="mage.deck.CanadianHighlander"/>
<deckType name="Variant Magic - Commander" jar="mage-deck-constructed.jar" className="mage.deck.Commander"/>
<deckType name="Variant Magic - Duel Commander" jar="mage-deck-constructed.jar" className="mage.deck.DuelCommander"/>
<deckType name="Variant Magic - Tiny Leaders" jar="mage-deck-constructed.jar" className="mage.deck.TinyLeaders"/>

View file

@ -130,6 +130,7 @@
<deckType name="Constructed - Super Type 2" jar="mage-deck-constructed-${project.version}.jar" className="mage.deck.SuperType2"/>
<deckType name="Constructed - Freeform" jar="mage-deck-constructed-${project.version}.jar" className="mage.deck.Freeform"/>
<deckType name="Constructed - Australian Highlander" jar="mage-deck-constructed-${project.version}.jar" className="mage.deck.AusHighlander"/>
<deckType name="Constructed - Canadian Highlander" jar="mage-deck-constructed-${project.version}.jar" className="mage.deck.CanadianHighlander"/>
<deckType name="Variant Magic - Commander" jar="mage-deck-constructed-${project.version}.jar" className="mage.deck.Commander"/>
<deckType name="Variant Magic - Duel Commander" jar="mage-deck-constructed-${project.version}.jar" className="mage.deck.DuelCommander"/>
<deckType name="Variant Magic - Tiny Leaders" jar="mage-deck-constructed-${project.version}.jar" className="mage.deck.TinyLeaders"/>

View file

@ -41,6 +41,7 @@ import mage.cards.CardImpl;
import mage.cards.CardSetInfo;
import mage.constants.CardType;
import mage.constants.TargetController;
import mage.filter.StaticFilters;
/**
*
@ -60,7 +61,8 @@ public class FlameheartWerewolf extends CardImpl {
this.transformable = true;
// Whenever Flameheart Werewolf blocks or becomes blocked by a creature, Flameheart Werewolf deals 2 damage to that creature.
this.addAbility(new BlocksOrBecomesBlockedTriggeredAbility(new DamageTargetEffect(2, true, "that creature"), false));
this.addAbility(new BlocksOrBecomesBlockedTriggeredAbility(new DamageTargetEffect(2, true, "that creature"),
StaticFilters.FILTER_PERMANENT_CREATURE, false, null, true));
// At the beginning of each upkeep, if a player cast two or more spells last turn, transform Flameheart Werewolf.
TriggeredAbility ability = new BeginningOfUpkeepTriggeredAbility(new TransformSourceEffect(false), TargetController.ANY, false);

View file

@ -28,7 +28,7 @@ public class Hivestone extends CardImpl {
// Creatures you control are Slivers in addition to their other creature types.
ArrayList<String> subTypes = new ArrayList<>();
subTypes.add("Slivers");
subTypes.add("Sliver");
Effect effect = new BecomesSubtypeAllEffect(Duration.WhileOnBattlefield, subTypes, filter, false);
effect.setText("Creatures you control are Slivers in addition to their other creature types");
this.addAbility(new SimpleStaticAbility(Zone.BATTLEFIELD, effect));

View file

@ -37,11 +37,12 @@ import mage.abilities.decorator.ConditionalTriggeredAbility;
import mage.abilities.effects.common.DamageTargetEffect;
import mage.abilities.effects.common.TransformSourceEffect;
import mage.abilities.keyword.TransformAbility;
import mage.cards.f.FlameheartWerewolf;
import mage.cards.CardImpl;
import mage.cards.CardSetInfo;
import mage.cards.f.FlameheartWerewolf;
import mage.constants.CardType;
import mage.constants.TargetController;
import mage.filter.StaticFilters;
/**
*
@ -61,7 +62,8 @@ public class KessigForgemaster extends CardImpl {
this.secondSideCardClazz = FlameheartWerewolf.class;
// Whenever Kessig Forgemaster blocks or becomes blocked by a creature, Kessig Forgemaster deals 1 damage to that creature.
this.addAbility(new BlocksOrBecomesBlockedTriggeredAbility(new DamageTargetEffect(1, true, "that creature"), false));
this.addAbility(new BlocksOrBecomesBlockedTriggeredAbility(new DamageTargetEffect(1, true, "that creature"),
StaticFilters.FILTER_PERMANENT_CREATURE, false, null, true));
// At the beginning of each upkeep, if no spells were cast last turn, transform Kessig Forgemaster.
this.addAbility(new TransformAbility());

View file

@ -28,13 +28,12 @@
package mage.cards.m;
import java.util.UUID;
import mage.constants.CardType;
import mage.MageInt;
import mage.abilities.common.SimpleStaticAbility;
import mage.abilities.effects.common.continuous.BoostAllEffect;
import mage.cards.CardImpl;
import mage.cards.CardSetInfo;
import mage.constants.CardType;
import mage.constants.Duration;
import mage.constants.Zone;
import mage.filter.common.FilterCreaturePermanent;
@ -52,11 +51,13 @@ public class MuscleSliver extends CardImpl {
}
public MuscleSliver(UUID ownerId, CardSetInfo setInfo) {
super(ownerId,setInfo,new CardType[]{CardType.CREATURE},"{1}{G}");
super(ownerId, setInfo, new CardType[]{CardType.CREATURE}, "{1}{G}");
this.subtype.add("Sliver");
this.power = new MageInt(1);
this.toughness = new MageInt(1);
// All Sliver creatures get +1/+1.
this.addAbility(new SimpleStaticAbility(Zone.BATTLEFIELD, new BoostAllEffect(1, 1, Duration.WhileOnBattlefield, filter, false)));
}

View file

@ -24,8 +24,7 @@
* 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.oneshot.damage;
import mage.constants.PhaseStep;
@ -48,11 +47,9 @@ public class FlameheartWerewolfTest extends CardTestPlayerBase {
// Flameheart Werewolf is a 3/2 with:
// Whenever Flameheart Werewolf blocks or becomes blocked by a creature, Flameheart Werewolf deals 2 damage to that creature.
// Kalitas, Traitor of Ghet is a 3/4 with:
// Lifelink
// If a nontoken creature an opponent controls would die, instead exile that card and put a 2/2 black Zombie creature token onto the battlefield
addCard(Zone.BATTLEFIELD, playerA, "Flameheart Werewolf");
addCard(Zone.BATTLEFIELD, playerB, "Kalitas, Traitor of Ghet");
@ -92,8 +89,8 @@ public class FlameheartWerewolfTest extends CardTestPlayerBase {
// both 2/2s should die before they had a chance to deal damage
// to Flameheart Werewolf
assertGraveyardCount(playerA, "Kessig Forgemaster", 0);
assertPermanentCount(playerA, "Flameheart Werewolf", 1);
assertGraveyardCount(playerA, "Flameheart Werewolf", 0);
assertPermanentCount(playerB, "Falkenrath Reaver", 0);
assertGraveyardCount(playerB, "Falkenrath Reaver", 1);
assertPermanentCount(playerB, "Wind Drake", 0);

View file

@ -16,26 +16,32 @@ public class HivestoneTest extends CardTestPlayerBase {
*/
@Test
public void abilityCheckTest() {
addCard(Zone.BATTLEFIELD, playerA, "Grizzly Bears", 1);
addCard(Zone.BATTLEFIELD, playerA, "Hivestone", 1);
addCard(Zone.BATTLEFIELD, playerA, "Forest", 4);
addCard(Zone.HAND, playerA, "Grizzly Bears", 1); // Creature {1}{G}
// Creatures you control are Slivers in addition to their other creature types.
addCard(Zone.HAND, playerA, "Hivestone", 1); // Artifact {2}
// All Sliver creatures get +1/+1.
addCard(Zone.BATTLEFIELD, playerA, "Muscle Sliver", 1);
addCard(Zone.BATTLEFIELD, playerB, "Runeclaw Bear", 1); // Creature 2/2
addCard(Zone.BATTLEFIELD, playerB, "Runeclaw Bear", 1);
castSpell(1, PhaseStep.PRECOMBAT_MAIN, playerA, "Grizzly Bears");
castSpell(1, PhaseStep.PRECOMBAT_MAIN, playerA, "Hivestone");
setStopAt(1, PhaseStep.PRECOMBAT_MAIN);
setStopAt(1, PhaseStep.BEGIN_COMBAT);
execute();
assertPermanentCount(playerA, "Hivestone", 1);
assertPermanentCount(playerA, "Grizzly Bears", 1);
assertPowerToughness(playerA, "Grizzly Bears", 3, 3, Filter.ComparisonScope.Any);
assertPowerToughness(playerB, "Runeclaw Bear", 2, 2, Filter.ComparisonScope.Any);
}
/**
* Turns only your creatures on the battlefield, not in other zones, into Slivers. It wont allow you to have
* Root Sliver on the battlefield and make your Grizzly Bears uncounterable, for example.
* Turns only your creatures on the battlefield, not in other zones, into
* Slivers. It wont allow you to have Root Sliver on the battlefield and
* make your Grizzly Bears uncounterable, for example.
*/
@Test
public void rootSliverTest() {
@ -45,7 +51,6 @@ public class HivestoneTest extends CardTestPlayerBase {
addCard(Zone.BATTLEFIELD, playerA, "Root Sliver", 1);
addCard(Zone.BATTLEFIELD, playerA, "Forest", 2);
addCard(Zone.BATTLEFIELD, playerB, "Island", 2);
addCard(Zone.HAND, playerB, "Counterspell");

View file

@ -27,11 +27,11 @@
*/
package mage.abilities.common;
import mage.constants.Zone;
import mage.abilities.TriggeredAbilityImpl;
import mage.abilities.effects.Effect;
import mage.constants.Zone;
import mage.filter.FilterPermanent;
import mage.filter.common.FilterCreaturePermanent;
import mage.filter.StaticFilters;
import mage.game.Game;
import mage.game.events.GameEvent;
import mage.game.permanent.Permanent;
@ -48,7 +48,7 @@ public class BlocksOrBecomesBlockedTriggeredAbility extends TriggeredAbilityImpl
protected boolean setTargetPointer;
public BlocksOrBecomesBlockedTriggeredAbility(Effect effect, boolean optional) {
this(effect, new FilterCreaturePermanent(), optional, null, true);
this(effect, StaticFilters.FILTER_PERMANENT_CREATURE, optional, null, false);
}
public BlocksOrBecomesBlockedTriggeredAbility(Effect effect, FilterPermanent filter, boolean optional) {

View file

@ -70,7 +70,7 @@ public class BecomesSubtypeAllEffect extends ContinuousEffectImpl {
@Override
public boolean apply(Layer layer, SubLayer sublayer, Ability source,
Game game) {
for (Permanent permanent : game.getBattlefield().getAllActivePermanents(filter, game)) {
for (Permanent permanent : game.getBattlefield().getActivePermanents(filter, source.getControllerId(), source.getSourceId(), game)) {
if (permanent != null) {
switch (layer) {
case TypeChangingEffects_4:
@ -86,10 +86,8 @@ public class BecomesSubtypeAllEffect extends ContinuousEffectImpl {
}
break;
}
} else {
if (duration.equals(Duration.Custom)) {
discard();
}
} else if (duration.equals(Duration.Custom)) {
discard();
}
}
return true;

View file

@ -32,6 +32,7 @@ public class StaticFilters {
public static final FilterNonlandCard FILTER_CARD_NON_LAND = new FilterNonlandCard();
public static final FilterCard FILTER_CARD_ARTIFACT_OR_CREATURE = new FilterCard("artifact or creature card");
public static final FilterCreaturePermanent FILTER_PERMANENT_CREATURE = new FilterCreaturePermanent();
public static final FilterCreaturePermanent FILTER_PERMANENT_CREATURE_GOBLINS = new FilterCreaturePermanent("Goblin", "Goblin creatures");
public static final FilterCreaturePermanent FILTER_PERMANENT_CREATURE_SLIVERS = new FilterCreaturePermanent("Sliver", "Sliver creatures");