diff --git a/.gitattributes b/.gitattributes index c8e13264c18..2e133f62ea0 100644 --- a/.gitattributes +++ b/.gitattributes @@ -1077,6 +1077,7 @@ res/cardsfolder/b/burrowing.txt svneol=native#text/plain res/cardsfolder/b/burst_lightning.txt svneol=native#text/plain res/cardsfolder/b/burst_of_energy.txt svneol=native#text/plain res/cardsfolder/b/burst_of_speed.txt svneol=native#text/plain +res/cardsfolder/b/bushi_tenderfoot_kenzo_the_hardhearted.txt -text res/cardsfolder/b/butcher_of_malakir.txt svneol=native#text/plain res/cardsfolder/b/butchers_cleaver.txt -text res/cardsfolder/c/cabal_archon.txt svneol=native#text/plain @@ -1408,6 +1409,7 @@ res/cardsfolder/c/clockwork_gnomes.txt svneol=native#text/plain res/cardsfolder/c/clockwork_steed.txt -text res/cardsfolder/c/clockwork_swarm.txt -text res/cardsfolder/c/clockwork_vorrac.txt svneol=native#text/plain +res/cardsfolder/c/cloistered_youth_unholy_fiend.txt -text res/cardsfolder/c/clone.txt svneol=native#text/plain res/cardsfolder/c/close_quarters.txt svneol=native#text/plain res/cardsfolder/c/clot_sliver.txt svneol=native#text/plain @@ -1823,6 +1825,7 @@ res/cardsfolder/d/day_of_destiny.txt svneol=native#text/plain res/cardsfolder/d/day_of_judgment.txt svneol=native#text/plain res/cardsfolder/d/day_of_the_dragons.txt svneol=native#text/plain res/cardsfolder/d/daybreak_coronet.txt -text +res/cardsfolder/d/daybreak_ranger_nightfall_predator.txt -text res/cardsfolder/d/daze.txt svneol=native#text/plain res/cardsfolder/d/dead_iron_sledge.txt svneol=native#text/plain res/cardsfolder/d/dead_weight.txt -text @@ -3043,6 +3046,7 @@ res/cardsfolder/g/gangrenous_zombies.txt svneol=native#text/plain res/cardsfolder/g/gargoyle_castle.txt svneol=native#text/plain res/cardsfolder/g/gargoyle_sentinel.txt svneol=native#text/plain res/cardsfolder/g/garruk_primal_hunter.txt svneol=native#text/plain +res/cardsfolder/g/garruk_relentless_garruk_the_veil_cursed.txt -text res/cardsfolder/g/garruk_wildspeaker.txt svneol=native#text/plain res/cardsfolder/g/garruks_companion.txt svneol=native#text/plain res/cardsfolder/g/garruks_horde.txt -text @@ -3054,6 +3058,7 @@ res/cardsfolder/g/gate_to_phyrexia.txt svneol=native#text/plain res/cardsfolder/g/gatekeeper_of_malakir.txt svneol=native#text/plain res/cardsfolder/g/gathan_raiders.txt svneol=native#text/plain res/cardsfolder/g/gatherer_of_graces.txt svneol=native#text/plain +res/cardsfolder/g/gatstaf_shepherd_gatstaf_howler.txt -text res/cardsfolder/g/gauntlet_of_might.txt svneol=native#text/plain res/cardsfolder/g/gavony_township.txt -text res/cardsfolder/g/gaze_of_adamaro.txt svneol=native#text/plain @@ -5186,6 +5191,7 @@ res/cardsfolder/m/moonglove_extract.txt svneol=native#text/plain res/cardsfolder/m/moonglove_winnower.txt svneol=native#text/plain res/cardsfolder/m/moonlit_strider.txt svneol=native#text/plain res/cardsfolder/m/moonlit_wake.txt svneol=native#text/plain +res/cardsfolder/m/moonmist.txt -text res/cardsfolder/m/moonring_island.txt -text res/cardsfolder/m/moonwing_moth.txt svneol=native#text/plain res/cardsfolder/m/moor_fiend.txt svneol=native#text/plain @@ -6891,6 +6897,7 @@ res/cardsfolder/s/screaming_fury.txt svneol=native#text/plain res/cardsfolder/s/screaming_seahawk.txt svneol=native#text/plain res/cardsfolder/s/screams_from_within.txt -text res/cardsfolder/s/screams_of_the_damned.txt svneol=native#text/plain +res/cardsfolder/s/screeching_bat_stalking_vampire.txt -text res/cardsfolder/s/screeching_buzzard.txt svneol=native#text/plain res/cardsfolder/s/screeching_drake.txt svneol=native#text/plain res/cardsfolder/s/screeching_harpy.txt svneol=native#text/plain @@ -8282,6 +8289,7 @@ res/cardsfolder/t/thoughtseize.txt svneol=native#text/plain res/cardsfolder/t/thoughtweft_gambit.txt svneol=native#text/plain res/cardsfolder/t/thousand_legged_kami.txt svneol=native#text/plain res/cardsfolder/t/thraben_purebloods.txt -text +res/cardsfolder/t/thraben_sentry_thraben_militia.txt -text res/cardsfolder/t/thran_dynamo.txt svneol=native#text/plain res/cardsfolder/t/thran_forge.txt svneol=native#text/plain res/cardsfolder/t/thran_foundry.txt svneol=native#text/plain @@ -10225,6 +10233,7 @@ src/main/java/forge/ZCTrigger.java svneol=native#text/plain src/main/java/forge/card/BoosterGenerator.java svneol=native#text/plain src/main/java/forge/card/BoosterUtils.java svneol=native#text/plain src/main/java/forge/card/CardBlock.java -text +src/main/java/forge/card/CardCharacteristics.java -text src/main/java/forge/card/CardColor.java -text src/main/java/forge/card/CardCoreType.java -text src/main/java/forge/card/CardInSet.java -text @@ -10232,6 +10241,7 @@ src/main/java/forge/card/CardManaCost.java -text src/main/java/forge/card/CardManaCostShard.java -text src/main/java/forge/card/CardRarity.java -text src/main/java/forge/card/CardRatings.java -text +src/main/java/forge/card/CardRuleCharacteristics.java -text src/main/java/forge/card/CardRules.java -text src/main/java/forge/card/CardRulesReader.java svneol=native#text/plain src/main/java/forge/card/CardSet.java -text @@ -10242,6 +10252,7 @@ src/main/java/forge/card/abilityFactory/AbilityFactory.java svneol=native#text/p src/main/java/forge/card/abilityFactory/AbilityFactory_AlterLife.java svneol=native#text/plain src/main/java/forge/card/abilityFactory/AbilityFactory_Animate.java svneol=native#text/plain src/main/java/forge/card/abilityFactory/AbilityFactory_Attach.java svneol=native#text/plain +src/main/java/forge/card/abilityFactory/AbilityFactory_ChangeState.java -text src/main/java/forge/card/abilityFactory/AbilityFactory_ChangeZone.java svneol=native#text/plain src/main/java/forge/card/abilityFactory/AbilityFactory_Charm.java -text src/main/java/forge/card/abilityFactory/AbilityFactory_Choose.java svneol=native#text/plain @@ -10455,6 +10466,7 @@ src/main/java/forge/gui/skin/FSkin.java -text src/main/java/forge/item/BoosterPack.java -text src/main/java/forge/item/CardDb.java -text src/main/java/forge/item/CardPrinted.java -text +src/main/java/forge/item/CardPrintedCharacteristics.java -text src/main/java/forge/item/InventoryItem.java -text src/main/java/forge/item/InventoryItemFromSet.java -text src/main/java/forge/item/ItemPool.java -text diff --git a/res/blockdata/boosters.txt b/res/blockdata/boosters.txt index 119a2099925..0b815348ddd 100644 --- a/res/blockdata/boosters.txt +++ b/res/blockdata/boosters.txt @@ -71,4 +71,4 @@ Set:VIS|Commons:11|Uncommons:3|Rares:1 Set:WTH|Commons:11|Uncommons:3|Rares:1 Set:WWK|Commons:10|Uncommons:3|Rares:1 Set:ZEN|Commons:10|Uncommons:3|Rares:1 -Set:ISD|Commons:10|Uncommons:3|Rares:1 \ No newline at end of file +Set:ISD|Commons:9|Uncommons:3|DoubleFaced:1|Rares:1 \ No newline at end of file diff --git a/res/cardsfolder/b/bushi_tenderfoot_kenzo_the_hardhearted.txt b/res/cardsfolder/b/bushi_tenderfoot_kenzo_the_hardhearted.txt new file mode 100644 index 00000000000..dc8c07f55a3 --- /dev/null +++ b/res/cardsfolder/b/bushi_tenderfoot_kenzo_the_hardhearted.txt @@ -0,0 +1,27 @@ +Name:Bushi Tenderfoot +ManaCost:W +Types:Creature Human Soldier +Text:no text +PT:1/1 +T:Mode$ ChangesZone | Origin$ Battlefield | Destination$ Graveyard | ValidCard$ Creature.DamagedBy | TriggerZones$ Battlefield | Execute$ TrigFlip | TriggerDescription$ When a creature dealt damage by CARDNAME this turn dies, flip CARDNAME. +SVar:TrigFlip:AB$ChangeState | Cost$ 0 | Defined$ Self +SVar:Rarity:Uncommon +AlternateMode:Flip +SetInfo:CHK|Uncommon|http://magiccards.info/scans/en/chk/2.jpg +Oracle:When a creature dealt damage by Bushi Tenderfoot this turn is put into a graveyard, flip Bushi Tenderfoot. + +ALTERNATE + +Name:Kenzo the Hardhearted +ManaCost:W +Colors:white +Types:Legendary Creature Human Samurai +Text:no text +PT:3/4 +K:Double Strike +K:Bushido 2 +SVar:Rarity:Uncommon +SetInfo:CHK|Uncommon|http://magiccards.info/scans/en/chk/307.jpg +Oracle:Double strike; bushido 2 (When this blocks or becomes blocked, it gets +2/+2 until end of turn.) + +End \ No newline at end of file diff --git a/res/cardsfolder/c/cloistered_youth_unholy_fiend.txt b/res/cardsfolder/c/cloistered_youth_unholy_fiend.txt new file mode 100644 index 00000000000..e07defddbf5 --- /dev/null +++ b/res/cardsfolder/c/cloistered_youth_unholy_fiend.txt @@ -0,0 +1,27 @@ +Name:Cloistered Youth +ManaCost:1 W +Types:Creature Human +Text:no text +PT:1/1 +T:Mode$ Phase | Phase$ Upkeep | ValidPlayer$ You | TriggerZones$ Battlefield | Execute$ TrigTransform | OptionalDecider$ You | TriggerDescription$ At the beginning of your upkeep, you may transform CARDNAME. +SVar:TrigTransform:AB$ChangeState | Cost$ 0 | Defined$ Self +SVar:Rarity:Uncommon +AlternateMode:DoubleFaced +SetInfo:ISD|Uncommon|http://magiccards.info/scans/en/isd/8a.jpg +Oracle:At the beginning of your upkeep, you may transform Cloistered Youth.\n----\nUnholy Fiend\n(Black)\nCreature - Horror\n3/3\nAt the beginning of your end step, you lose 1 life. + +ALTERNATE + +Name:Unholy Fiend +ManaCost:no cost +Colors:black +Types:Creature Horror +Text:no text +PT:3/3 +T:Mode$ Phase | Phase$ End of Turn | ValidPlayer$ You | TriggerZones$ Battlefield | Execute$ TrigLoseLife | TriggerDescription$ At the beginning of your end step, you lose 1 life. +SVar:TrigLoseLife:AB$LoseLife | Cost$ 0 | Defined$ You | LifeAmount$ 1 +SVar:Rarity:Uncommon +SetInfo:ISD|Uncommon|http://magiccards.info/scans/en/isd/8b.jpg +Oracle:Creature - Horror\n3/3\nAt the beginning of your end step, you lose 1 life. + +End \ No newline at end of file diff --git a/res/cardsfolder/d/daybreak_ranger_nightfall_predator.txt b/res/cardsfolder/d/daybreak_ranger_nightfall_predator.txt new file mode 100644 index 00000000000..f3543e13507 --- /dev/null +++ b/res/cardsfolder/d/daybreak_ranger_nightfall_predator.txt @@ -0,0 +1,31 @@ +Name:Daybreak Ranger +ManaCost:2 G +Types:Creature Human Archer Werewolf +Text:no text +PT:2/2 +A:AB$DealDamage | Cost$ T | ValidTgts$ Creature.withFlying | TgtPrompt$ Select target creature with flying. | NumDmg$ 2 | SpellDescription$ CARDNAME deals 2 damage to target creature with flying. +T:Mode$Phase | Phase$ Upkeep | WerewolfTransformCondition$ True | TriggerZones$ Battlefield | Execute$ TrigTransform | TriggerDescription$ At the beginning of each upkeep, if no spells were cast last turn, transform CARDNAME. +SVar:TrigTransform:AB$ChangeState | Cost$ 0 | Defined$ Self +SVar:Rarity:Rare +AlternateMode:DoubleFaced +SetInfo:ISD|Rare|http://magiccards.info/scans/en/isd/176a.jpg +Oracle:{T}: Daybreak Ranger deals 2 damage to target creature with flying.\nAt the beginning of each upkeep, if no spells were cast last turn, transform Daybreak Ranger. + +ALTERNATE + +Name:Nightfall Predator +ManaCost:no cost +Colors:green +Types:Creature Werewolf +Text:no text +PT:4/4 +A:AB$ DealDamage | Cost$ R T | ValidTgts$ Creature | TgtPrompt$ Select target creature | NumDmg$ X | SubAbility$ SVar=DamageThis | SpellDescription$ CARDNAME fights target creature. (Each deals damage equal to its power to the other.) +SVar:DamageThis:DB$DealDamage | Defined$ Self | DamageSource$ Targeted | NumDmg$ Y +SVar:X:Count$CardPower +SVar:Y:Targeted$CardPower +T:Mode$Phase | Phase$ Upkeep | WerewolfTransformCondition$ True | TriggerZones$ Battlefield | Execute$ TrigTransform | TriggerDescription$ At the beginning of each upkeep, if no spells were cast last turn, transform CARDNAME. +SVar:TrigTransform:AB$ChangeState | Cost$ 0 | Defined$ Self +SVar:Rarity:Rare +SetInfo:ISD|Rare|http://magiccards.info/scans/en/isd/176b.jpg +Oracle:{R}, {T}: Nightfall Predator fights target creature. (Each deals damage equal to its power to the other.)\nAt the beginning of each upkeep, if a player cast two or more spells last turn, transform Nightfall Predator. +End \ No newline at end of file diff --git a/res/cardsfolder/g/garruk_relentless_garruk_the_veil_cursed.txt b/res/cardsfolder/g/garruk_relentless_garruk_the_veil_cursed.txt new file mode 100644 index 00000000000..e4250cb9ac4 --- /dev/null +++ b/res/cardsfolder/g/garruk_relentless_garruk_the_veil_cursed.txt @@ -0,0 +1,33 @@ +Name:Garruk Relentless +ManaCost:3 G +Types:Planeswalker Garruk +Text:no text +Loyalty:3 +T:Mode$ Always | IsPresent$ Card.Self+counters_LE2_LOYALTY | Execute$ TrigTransform | TriggerDescription$ When CARDNAME has two or fewer loyalty counters on him, transform him. +A:AB$ DealDamage | Cost$ 0 | ValidTgts$ Creature | TgtPrompt$ Select target creature | NumDmg$ 3 | SubAbility$ SVar=DamageThis | Planeswalker$ True | SpellDescription$ CARDNAME deals damage equal to its power to target creature. That creature deals damage equal to its power to CARDNAME. +A:AB$ Token | Cost$ SubCounter<1/LOYALTY> | TokenAmount$ 1 | TokenName$ Wolf | TokenColors$ Green | TokenTypes$ Creature,Wolf | TokenOwner$ You | TokenPower$ 2 | TokenToughness$ 2 | Planeswalker$ True | SpellDescription$ Put a 2/2 green Wolf creature token onto the battlefield. +SVar:DamageThis:DB$DealDamage | Defined$ Self | DamageSource$ Targeted | NumDmg$ Y +SVar:X:Targeted$CardPower +SVar:TrigTransform:AB$ChangeState | Cost$ 0 | Defined$ Self +AlternateMode:DoubleFaced +SVar:Rarity:Mythic +SetInfo:ISD|Mythic|http://magiccards.info/scans/en/isd/181a.jpg +Oracle:When Garruk Relentless has two or fewer loyalty counters on him, transform him.\n[0] Garruk Relentless deals 3 damage to target creature. That creature deals damage equal to its power to him.\n[0] Put a 2/2 green Wolf creature token onto the battlefield. + +ALTERNATE + +Name:Garruk, the Veil-Cursed +ManaCost:no cost +Colors:green,black +Types:Planeswalker Garruk +Text:no text +Loyalty:3 +A:AB$ Token | Cost$ AddCounter<1/LOYALTY> | TokenAmount$ 1 | TokenName$ Wolf | TokenColors$ Black | TokenTypes$ Creature,Wolf | TokenOwner$ You | TokenPower$ 1 | TokenTougness$ 1 | TokenKeywords$ Deathtouch | Planeswalker$ True | SpellDescription$ Put a 1/1 black Wolf creature token with deathtouch onto the battlefield. +A:AB$ Sacrifice | Cost$ SubCounter<1/LOYALTY> | ValidTgts$ Creature.YouCtrl | TgtPrompt$ Select target creature | RememberSacrificed$ True | SubAbility$ DBSearch | Planeswalker$ True | SpellDescription$ Sacrifice a creature.If you do, search your library for a creature card, reveal it, put it into your hand, then shuffle your library. +A:AB$ PumpAll | Cost$ SubCounter<3/LOYALTY> | ValidCards$ Creature.YouCtrl | KW$ Trample | NumAtt$ X | NumDef$ X | Planeswalker$ True | Ultimate$ True | SpellDescription$ Creatures you control gain trample and get +X/+X until end of turn, where X is the number of creature cards in your graveyard. +SVar:X:Count$InYourYard.Creature +SVar:DBSearch:DB$ ChangeZone | Origin$ Library | Destination$ Hand | ChangeType$ Creature | ChangeNum$ 1 +SVar:Rarity:Mythic +SetInfo:ISD|Mythic|http://magiccards.info/scans/en/isd/181b.jpg +Oracle:[+1] Put a 1/1 black Wolf creature token with deathtouch onto the battlefield.\n[-1] Sacrifice a creature. If you do, search your library for a creature card, reveal it, put it into your hand, then shuffle your library.\n[-3] Creatures you control gain trample and get +X/+X until end of turn, where X is the number of creature cards in your graveyard. +End \ No newline at end of file diff --git a/res/cardsfolder/g/gatstaf_shepherd_gatstaf_howler.txt b/res/cardsfolder/g/gatstaf_shepherd_gatstaf_howler.txt new file mode 100644 index 00000000000..5c6fd523670 --- /dev/null +++ b/res/cardsfolder/g/gatstaf_shepherd_gatstaf_howler.txt @@ -0,0 +1,27 @@ +Name:Gatstaf Shepherd +ManaCost:1 G +Types:Creature Human Werewolf +Text:no text +PT:2/2 +T:Mode$Phase | Phase$ Upkeep | WerewolfTransformCondition$ True | TriggerZones$ Battlefield | Execute$ TrigTransform | TriggerDescription$ At the beginning of each upkeep, if no spells were cast last turn, transform CARDNAME. +SVar:TrigTransform:AB$ChangeState | Cost$ 0 | Defined$ Self +SVar:Rarity:Uncommon +AlternateMode:DoubleFaced +SetInfo:ISD|Uncommon|http://magiccards.info/scans/en/isd/182a.jpg +Oracle:At the beginning of each upkeep, if no spells were cast last turn, transform Gatstaf Shepherd. + +ALTERNATE + +Name:Gatstaf Howler +ManaCost:no cost +Colors:green +Types:Creature Werewolf +Text:no text +PT:3/3 +K:Intimidate +T:Mode$Phase | Phase$ Upkeep | WerewolfUntransformCondition$ True | TriggerZones$ Battlefield | Execute$ TrigTransform | TriggerDescription$ At the beginning of each upkeep, if a player cast two or more spells last turn, transform CARDNAME. +SVar:TrigTransform:AB$ChangeState | Cost$ 0 | Defined$ Self +SVar:Rarity:Uncommon +SetInfo:ISD|Uncommon|http://magiccards.info/scans/en/isd/182b.jpg +Oracle:Intimidate (This creature can't be blocked except by artifact creatures and/or creatures that share a color with it.)\nAt the beginning of each upkeep, if a player cast two or more spells last turn, transform Gatstaf Howler. +End \ No newline at end of file diff --git a/res/cardsfolder/m/moonmist.txt b/res/cardsfolder/m/moonmist.txt new file mode 100644 index 00000000000..20b1d24f178 --- /dev/null +++ b/res/cardsfolder/m/moonmist.txt @@ -0,0 +1,11 @@ +Name:Moonmist +ManaCost:1 G +Types:Instant +Text:no text +A:SP$ChangeStateAll | Cost$ 1 G | ValidCards$ Creature.Human+DoubleFaced | SubAbility$ DBCurseNonWolves | SpellDescription$ Transform all Humans. Prevent all combat damage that would be dealt this turn by creatures other than Werewolves and Wolves. (Only double-faced cards can be transformed.) +SVar:DBCurseNonWolves:DB$Effect | Name$ Moonmist Effect. | StaticAbilities$ Curse +SVar:Curse:Mode$ PreventDamage | Source$ Creature.nonWerewolf+nonWolf | CombatDamage$ True | Description$ Prevent all combat damage that would be dealt this turn by creatures other than Werewolves and Wolves. +SVar:Rarity:Common +SetInfo:ISD|Common|http://magiccards.info/scans/en/isd/195.jpg +Oracle:Transform all Humans. Prevent all combat damage that would be dealt this turn by creatures other than Werewolves and Wolves. (Only double-faced cards can be transformed.) +End \ No newline at end of file diff --git a/res/cardsfolder/s/screeching_bat_stalking_vampire.txt b/res/cardsfolder/s/screeching_bat_stalking_vampire.txt new file mode 100644 index 00000000000..d7e916b8822 --- /dev/null +++ b/res/cardsfolder/s/screeching_bat_stalking_vampire.txt @@ -0,0 +1,27 @@ +Name:Screeching Bat +ManaCost:2 B +Types:Creature Bat +Text:no text +PT:2/2 +K:Flying +T:Mode$ Phase | Phase$ Upkeep | ValidPlayer$ You | TriggerZones$ Battlefield | Execute$ TrigTransform | OptionalDecider$ You | TriggerDescription$ At the beginning of your upkeep, you may pay 2 B B. If you do, transform CARDNAME. +SVar:TrigTransform:AB$ChangeState | Cost$ 2 B B | Defined$ Self +SVar:Rarity:Uncommon +AlternateMode:DoubleFaced +Oracle:Flying\nAt the beginning of your upkeep, you may pay {2}{B}{B}. If you do, transform Screeching Bat.\n----\nStalking Vampire\n(Black)\nCreature - Vampire\n5/5\nAt the beginning of your upkeep, you may pay {2}{B}{B}. If you do, transform Stalking Vampire. +SetInfo:ISD|Uncommon|http://magiccards.info/scans/en/isd/114a.jpg + +ALTERNATE + +Name:Stalking Vampire +ManaCost:no cost +Colors:black +Types:Creature Vampire +Text:no text +PT:5/5 +T:Mode$ Phase | Phase$ Upkeep | ValidPlayer$ You | TriggerZones$ Battlefield | Execute$ TrigTransform | OptionalDecider$ You | TriggerDescription$ At the beginning of your upkeep, you may pay 2 B B. If you do, transform CARDNAME. +SVar:TrigTransform:AB$ChangeState | Cost$ 2 B B | Defined$ Self +SVar:Rarity:Uncommon +Oracle:Creature - Vampire\n5/5\nAt the beginning of your upkeep, you may pay {2}{B}{B}. If you do, transform Stalking Vampire. +SetInfo:ISD|Uncommon|http://magiccards.info/scans/en/isd/114b.jpg +End \ No newline at end of file diff --git a/res/cardsfolder/t/thraben_sentry_thraben_militia.txt b/res/cardsfolder/t/thraben_sentry_thraben_militia.txt new file mode 100644 index 00000000000..f096934ff88 --- /dev/null +++ b/res/cardsfolder/t/thraben_sentry_thraben_militia.txt @@ -0,0 +1,26 @@ +Name:Thraben Sentry +ManaCost:3 W +Types:Creature Human Soldier +Text:no text +PT:2/2 +K:Vigilance +T:Mode$ChangesZone | Origin$ Battlefield | Destination$ Graveyard | ValidCard$ Creature.Other+YouCtrl | Execute$ TrigTransform | OptionalDecider$ You | TriggerDescription$ Whenever another creature you control dies, you may transform CARDNAME. +SVar:TrigTransform:AB$ChangeState | Cost$ 0 | Defined$ Self +SVar:Rarity:Common +AlternateMode:DoubleFaced +SetInfo:ISD|Common|http://magiccards.info/scans/en/isd/38a.jpg +Oracle:Vigilance\nWhenever another creature you control dies, you may transform Thraben Sentry. + +ALTERNATE + +Name:Thraben Militia +ManaCost:no cost +Colors:white +Types:Creature Human Soldier +Text:no text +PT:5/4 +K:Trample +SVar:Rarity:Common +SetInfo:ISD|Common|http://magiccards.info/scans/en/isd/38b.jpg +Oracle:Trample +End \ No newline at end of file diff --git a/src/main/java/forge/Card.java b/src/main/java/forge/Card.java index e8569f88ff3..945cb6ad742 100644 --- a/src/main/java/forge/Card.java +++ b/src/main/java/forge/Card.java @@ -14,6 +14,7 @@ import java.util.TreeMap; import com.esotericsoftware.minlog.Log; import forge.Constant.Zone; +import forge.card.CardCharacteristics; import forge.card.cardFactory.CardFactoryUtil; import forge.card.cost.Cost; import forge.card.mana.ManaCost; @@ -39,12 +40,90 @@ public class Card extends GameEntity implements Comparable { private int uniqueNumber = nextUniqueNumber++; private long value; + + private CardCharacteristics[] characteristics = new CardCharacteristics[] { new CardCharacteristics(), null }; + private int currentCharacteristic = 0; + private boolean isDoubleFaced = false; + private boolean isFlip = false; + + private CardCharacteristics getCharacteristics() { + return characteristics[currentCharacteristic]; + } + + public void addAlternateState() { + characteristics[1] = new CardCharacteristics(); + } + + public void clearAlternateState() { + if(currentCharacteristic == 1) { + changeState(); + } + characteristics[1] = null; + } + + public void clearOtherState() { + characteristics[1-currentCharacteristic] = null; + } + + @Override + public String getName() { + return getCharacteristics().getName(); + } + + @Override + public void setName(String name0) { + getCharacteristics().setName(name0); + } + + public boolean isInAlternateState() { + return currentCharacteristic == 1; + } + + public boolean hasAlternateState() { + return characteristics[1] != null; + } + + public boolean changeState() { + if(characteristics[1-currentCharacteristic] != null) { + currentCharacteristic = 1 - currentCharacteristic; + + return true; + } + + return false; + } + /** + * @return the isDoubleFaced + */ + public boolean isDoubleFaced() { + return isDoubleFaced; + } + + /** + * @param isDoubleFaced0 the isDoubleFaced to set + */ + public void setDoubleFaced(boolean isDoubleFaced0) { + this.isDoubleFaced = isDoubleFaced0; // TODO: Add 0 to parameter's name. + } + + /** + * @return the isFlip + */ + public boolean isFlip() { + return isFlip; + } + + /** + * @param isFlip0 the isFlip to set + */ + public void setFlip(boolean isFlip0) { + this.isFlip = isFlip0; // TODO: Add 0 to parameter's name. + } + + private Map counters = new TreeMap(); private Map triggeringObjects = new TreeMap(); - private ArrayList triggers = new ArrayList(); - private ArrayList intrinsicAbility = new ArrayList(); private ArrayList staticAbilityStrings = new ArrayList(); - private ArrayList intrinsicKeyword = new ArrayList(); private ArrayList extrinsicKeyword = new ArrayList(); //Hidden keywords won't be displayed on the card private ArrayList hiddenExtrinsicKeyword = new ArrayList(); @@ -59,17 +138,13 @@ public class Card extends GameEntity implements Comparable { //if this card is an Aura, what Entity is it enchanting? private GameEntity enchanting = null; - private ArrayList type = new ArrayList(); private ArrayList prevType = new ArrayList(); private ArrayList choicesMade = new ArrayList(); private ArrayList targetsForChoices = new ArrayList(); - private ArrayList spellAbility = new ArrayList(); - private ArrayList manaAbility = new ArrayList(); - private ArrayList cardColor = new ArrayList(); + //changes by AF animate and continuous static effects private ArrayList changedCardTypes = new ArrayList(); private ArrayList changedCardKeywords = new ArrayList(); - private ArrayList staticAbilities = new ArrayList(); private ArrayList rememberedObjects = new ArrayList(); private ArrayList imprintedCards = new ArrayList(); @@ -123,8 +198,6 @@ public class Card extends GameEntity implements Comparable { private long timestamp = -1; // permanents on the battlefield - private int baseAttack = 0; - private int baseDefense = 0; private ArrayList newPT = new ArrayList(); // stack of set power/toughness private int baseLoyalty = 0; private String baseAttackString = null; @@ -160,7 +233,6 @@ public class Card extends GameEntity implements Comparable { private String imageName = ""; //private String rarity = ""; private String text = ""; - private String manaCost = ""; private String echoCost = ""; private String madnessCost = ""; private String chosenType = ""; @@ -185,8 +257,6 @@ public class Card extends GameEntity implements Comparable { private ArrayList untapCommandList = new ArrayList(); private ArrayList changeControllerCommandList = new ArrayList(); - private Map counters = new TreeMap(); - private Map sVars = new TreeMap(); private static String[] storableSVars = {"ChosenX"}; private ArrayList hauntedBy = new ArrayList(); @@ -332,14 +402,14 @@ public class Card extends GameEntity implements Comparable { public final Trigger addTrigger(final Trigger t) { Trigger newtrig = t.getCopy(); newtrig.setHostCard(this); - triggers.add(newtrig); + getCharacteristics().getTriggers().add(newtrig); return newtrig; } public final void moveTrigger(final Trigger t) { t.setHostCard(this); - if(!triggers.contains(t)) - triggers.add(t); + if(!getCharacteristics().getTriggers().contains(t)) + getCharacteristics().getTriggers().add(t); } /** @@ -348,7 +418,7 @@ public class Card extends GameEntity implements Comparable { * @param t a {@link forge.card.trigger.Trigger} object. */ public final void removeTrigger(final Trigger t) { - triggers.remove(t); + getCharacteristics().getTriggers().remove(t); } /** @@ -357,7 +427,7 @@ public class Card extends GameEntity implements Comparable { * @return a {@link java.util.ArrayList} object. */ public final ArrayList getTriggers() { - return triggers; + return getCharacteristics().getTriggers(); } /** @@ -367,7 +437,7 @@ public class Card extends GameEntity implements Comparable { * @return a {@link forge.card.trigger.Trigger} object. */ public final Trigger getNamedTrigger(final String name) { - for (Trigger t : triggers) { + for (Trigger t : getCharacteristics().getTriggers()) { if (t.getName() != null && t.getName().equals(name)) { return t; } @@ -382,18 +452,21 @@ public class Card extends GameEntity implements Comparable { * @param trigs a {@link java.util.ArrayList} object. */ public final void setTriggers(final ArrayList trigs) { + ArrayList copyList = new ArrayList(); for (Trigger t : trigs) { Trigger newtrig = t.getCopy(); newtrig.setHostCard(this); - triggers.add(newtrig); + copyList.add(newtrig); } + + getCharacteristics().setTriggers(copyList); } /** *

clearTriggersNew.

*/ public final void clearTriggersNew() { - triggers.clear(); + getCharacteristics().getTriggers().clear(); } /** @@ -587,7 +660,7 @@ public class Card extends GameEntity implements Comparable { * @return a boolean. */ public final boolean canAnyPlayerActivate() { - for (SpellAbility s : spellAbility) { + for (SpellAbility s : getCharacteristics().getSpellAbility()) { if (s.getRestrictions().getAnyPlayer()) { return true; } @@ -1132,8 +1205,8 @@ public class Card extends GameEntity implements Comparable { * @return a {@link java.lang.String} object. */ public final String getSVar(final String var) { - if (sVars.containsKey(var)) { - return sVars.get(var); + if (getCharacteristics().getsVars().containsKey(var)) { + return getCharacteristics().getsVars().get(var); } else { return ""; } @@ -1146,11 +1219,11 @@ public class Card extends GameEntity implements Comparable { * @param str a {@link java.lang.String} object. */ public final void setSVar(final String var, final String str) { - if (sVars.containsKey(var)) { - sVars.remove(var); + if (getCharacteristics().getsVars().containsKey(var)) { + getCharacteristics().getsVars().remove(var); } - sVars.put(var, str); + getCharacteristics().getsVars().put(var, str); } /** @@ -1159,7 +1232,7 @@ public class Card extends GameEntity implements Comparable { * @return a Map object. */ public final Map getSVars() { - return sVars; + return getCharacteristics().getsVars(); } /** @@ -1168,7 +1241,7 @@ public class Card extends GameEntity implements Comparable { * @param newSVars a Map object. */ public final void setSVars(final Map newSVars) { - sVars = newSVars; + getCharacteristics().setsVars(newSVars); } /** @@ -1238,7 +1311,7 @@ public class Card extends GameEntity implements Comparable { * @param s a {@link java.lang.String} object. */ public final void setManaCost(final String s) { - manaCost = s; + getCharacteristics().setManaCost(s); } /** @@ -1247,7 +1320,7 @@ public class Card extends GameEntity implements Comparable { * @return a {@link java.lang.String} object. */ public final String getManaCost() { - return manaCost; + return getCharacteristics().getManaCost(); } /** @@ -1259,7 +1332,7 @@ public class Card extends GameEntity implements Comparable { if (s.equals("")) { s = "0"; } - cardColor.add(new Card_Color(new ManaCost(s), this, false, true)); + getCharacteristics().getCardColor().add(new Card_Color(new ManaCost(s), this, false, true)); } /** @@ -1275,7 +1348,7 @@ public class Card extends GameEntity implements Comparable { if (bIncrease) { Card_Color.increaseTimestamp(); } - cardColor.add(new Card_Color(new ManaCost(s), c, addToColors, false)); + getCharacteristics().getCardColor().add(new Card_Color(new ManaCost(s), c, addToColors, false)); return Card_Color.getTimestamp(); } @@ -1289,14 +1362,14 @@ public class Card extends GameEntity implements Comparable { */ public final void removeColor(final String s, final Card c, final boolean addTo, final long timestampIn) { Card_Color removeCol = null; - for (Card_Color cc : cardColor) { + for (Card_Color cc : getCharacteristics().getCardColor()) { if (cc.equals(s, c, addTo, timestampIn)) { removeCol = cc; } } if (removeCol != null) { - cardColor.remove(removeCol); + getCharacteristics().getCardColor().remove(removeCol); } } @@ -1322,7 +1395,7 @@ public class Card extends GameEntity implements Comparable { * @param colors a {@link java.util.ArrayList} object. */ public final void setColor(final ArrayList colors) { - cardColor = colors; + getCharacteristics().setCardColor(colors); } /** @@ -1331,7 +1404,7 @@ public class Card extends GameEntity implements Comparable { * @return a {@link java.util.ArrayList} object. */ public final ArrayList getColor() { - return cardColor; + return getCharacteristics().getCardColor(); } /** @@ -1342,15 +1415,15 @@ public class Card extends GameEntity implements Comparable { */ final Card_Color determineColor(final ArrayList globalChanges) { Card_Color colors = new Card_Color(this); - int i = cardColor.size() - 1; + int i = getCharacteristics().getCardColor().size() - 1; int j = -1; if (globalChanges != null) { j = globalChanges.size() - 1; } // if both have changes, see which one is most recent while (i >= 0 && j >= 0) { Card_Color cc = null; - if (cardColor.get(i).getStamp() > globalChanges.get(j).getStamp()) { + if (getCharacteristics().getCardColor().get(i).getStamp() > globalChanges.get(j).getStamp()) { // Card has a more recent color stamp - cc = cardColor.get(i); + cc = getCharacteristics().getCardColor().get(i); i--; } else { // Global effect has a more recent color stamp @@ -1366,7 +1439,7 @@ public class Card extends GameEntity implements Comparable { } } while (i >= 0) { - Card_Color cc = cardColor.get(i); + Card_Color cc = getCharacteristics().getCardColor().get(i); i--; for (String s : cc.toStringArray()) { colors.addToCardColor(s); @@ -1395,7 +1468,7 @@ public class Card extends GameEntity implements Comparable { * @return a int. */ public final int getCMC() { - return CardUtil.getConvertedManaCost(manaCost); + return CardUtil.getConvertedManaCost(getCharacteristics().getManaCost()); } /** @@ -1787,14 +1860,14 @@ public class Card extends GameEntity implements Comparable { ArrayList kw = getKeyword(); // Triggered abilities - for (Trigger trig : triggers) { + for (Trigger trig : getCharacteristics().getTriggers()) { if (!trig.isSecondary()) { sb.append(trig.toString() + "\r\n"); } } // static abilities - for (StaticAbility stAb : staticAbilities) { + for (StaticAbility stAb : getCharacteristics().getStaticAbilities()) { String stAbD = stAb.toString(); if (!stAbD.equals("")) { sb.append(stAbD + "\r\n"); @@ -1897,14 +1970,14 @@ public class Card extends GameEntity implements Comparable { */ // Triggered abilities - for (Trigger trig : triggers) { + for (Trigger trig : getCharacteristics().getTriggers()) { if (!trig.isSecondary()) { sb.append(trig.toString() + "\r\n"); } } // static abilities - for (StaticAbility stAb : staticAbilities) { + for (StaticAbility stAb : getCharacteristics().getStaticAbilities()) { sb.append(stAb.toString() + "\r\n"); } @@ -2014,7 +2087,7 @@ public class Card extends GameEntity implements Comparable { * @return a {@link java.util.ArrayList} object. */ public final ArrayList getManaAbility() { - return new ArrayList(manaAbility); + return new ArrayList(getCharacteristics().getManaAbility()); } // Returns basic mana abilities plus "reflected mana" abilities @@ -2062,9 +2135,9 @@ public class Card extends GameEntity implements Comparable { *

clearFirstSpellAbility.

*/ public final void clearFirstSpell() { - for(int i = 0; i < spellAbility.size(); i++) { - if (spellAbility.get(i).isSpell()) { - spellAbility.remove(i); + for(int i = 0; i < getCharacteristics().getSpellAbility().size(); i++) { + if (getCharacteristics().getSpellAbility().get(i).isSpell()) { + getCharacteristics().getSpellAbility().remove(i); return; } } @@ -2074,12 +2147,12 @@ public class Card extends GameEntity implements Comparable { *

clearAllButFirstSpellAbility.

*/ public final void clearAllButFirstSpellAbility() { - if (!spellAbility.isEmpty()) { - SpellAbility first = spellAbility.get(0); - spellAbility.clear(); - spellAbility.add(first); + if (!getCharacteristics().getSpellAbility().isEmpty()) { + SpellAbility first = getCharacteristics().getSpellAbility().get(0); + getCharacteristics().getSpellAbility().clear(); + getCharacteristics().getSpellAbility().add(first); } - manaAbility.clear(); + getCharacteristics().getManaAbility().clear(); } /** @@ -2089,12 +2162,12 @@ public class Card extends GameEntity implements Comparable { */ public final ArrayList getAllButFirstSpellAbility() { ArrayList sas = new ArrayList(); - sas.addAll(spellAbility); + sas.addAll(getCharacteristics().getSpellAbility()); if (!sas.isEmpty()) { - SpellAbility first = spellAbility.get(0); + SpellAbility first = getCharacteristics().getSpellAbility().get(0); sas.remove(first); } - sas.addAll(manaAbility); + sas.addAll(getCharacteristics().getManaAbility()); return sas; } @@ -2103,8 +2176,8 @@ public class Card extends GameEntity implements Comparable { *

clearSpellAbility.

*/ public final void clearSpellAbility() { - spellAbility.clear(); - manaAbility.clear(); + getCharacteristics().getSpellAbility().clear(); + getCharacteristics().getManaAbility().clear(); } /** @@ -2113,7 +2186,7 @@ public class Card extends GameEntity implements Comparable { * @return a {@link forge.card.spellability.Spell_Permanent} object. */ public final Spell_Permanent getSpellPermanent() { - for (SpellAbility sa : spellAbility) { + for (SpellAbility sa : getCharacteristics().getSpellAbility()) { if (sa instanceof Spell_Permanent) { return (Spell_Permanent) sa; } @@ -2125,14 +2198,14 @@ public class Card extends GameEntity implements Comparable { *

clearSpellKeepManaAbility.

*/ public final void clearSpellKeepManaAbility() { - spellAbility.clear(); + getCharacteristics().getSpellAbility().clear(); } /** *

clearManaAbility.

*/ public final void clearManaAbility() { - manaAbility.clear(); + getCharacteristics().getManaAbility().clear(); } @@ -2144,9 +2217,9 @@ public class Card extends GameEntity implements Comparable { public final void addFirstSpellAbility(final SpellAbility a) { a.setSourceCard(this); if (a instanceof Ability_Mana) { - manaAbility.add(0, (Ability_Mana) a); + getCharacteristics().getManaAbility().add(0, (Ability_Mana) a); } else { - spellAbility.add(0, a); + getCharacteristics().getSpellAbility().add(0, a); } } @@ -2158,9 +2231,9 @@ public class Card extends GameEntity implements Comparable { public final void addSpellAbility(final SpellAbility a) { a.setSourceCard(this); if (a instanceof Ability_Mana) { - manaAbility.add((Ability_Mana) a); + getCharacteristics().getManaAbility().add((Ability_Mana) a); } else { - spellAbility.add(a); + getCharacteristics().getSpellAbility().add(a); } } @@ -2172,10 +2245,10 @@ public class Card extends GameEntity implements Comparable { public final void removeSpellAbility(final SpellAbility a) { if (a instanceof Ability_Mana) { //if (a.isExtrinsic()) //never remove intrinsic mana abilities, is this the way to go?? - manaAbility.remove(a); + getCharacteristics().getManaAbility().remove(a); } else { - spellAbility.remove(a); + getCharacteristics().getSpellAbility().remove(a); } } @@ -2187,7 +2260,7 @@ public class Card extends GameEntity implements Comparable { //temp ArrayList, otherwise ConcurrentModificationExceptions occur: ArrayList saList = new ArrayList(); - for (SpellAbility var : manaAbility) { + for (SpellAbility var : getCharacteristics().getManaAbility()) { if (var.isExtrinsic()) { saList.add(var); } @@ -2204,7 +2277,7 @@ public class Card extends GameEntity implements Comparable { */ public ArrayList getIntrinsicManaAbilitiesDescriptions() { ArrayList list = new ArrayList(); - for (SpellAbility var : manaAbility) { + for (SpellAbility var : getCharacteristics().getManaAbility()) { if (var.isIntrinsic()) list.add(var.toString()); } return list; @@ -2216,7 +2289,7 @@ public class Card extends GameEntity implements Comparable { * @return an array of {@link forge.card.spellability.SpellAbility} objects. */ public SpellAbility[] getSpellAbility() { - ArrayList res = new ArrayList(spellAbility); + ArrayList res = new ArrayList(getCharacteristics().getSpellAbility()); res.addAll(getManaAbility()); SpellAbility[] s = new SpellAbility[res.size()]; res.toArray(s); @@ -2229,10 +2302,21 @@ public class Card extends GameEntity implements Comparable { * @return a {@link java.util.ArrayList} object. */ public ArrayList getSpellAbilities() { - ArrayList res = new ArrayList(spellAbility); + ArrayList res = new ArrayList(getCharacteristics().getSpellAbility()); res.addAll(getManaAbility()); return res; } + + public ArrayList getAllSpellAbilities() { + ArrayList res = new ArrayList(getSpellAbilities()); + if(hasAlternateState()) { + changeState(); + res.addAll(getSpellAbilities()); + changeState(); + } + + return res; + } /** *

getSpells.

@@ -2240,7 +2324,7 @@ public class Card extends GameEntity implements Comparable { * @return a {@link java.util.ArrayList} object. */ public ArrayList getSpells() { - ArrayList s = new ArrayList(spellAbility); + ArrayList s = new ArrayList(getCharacteristics().getSpellAbility()); ArrayList res = new ArrayList(); for (SpellAbility sa : s) { @@ -2255,7 +2339,7 @@ public class Card extends GameEntity implements Comparable { * @return a {@link java.util.ArrayList} object. */ public ArrayList getBasicSpells() { - ArrayList s = new ArrayList(spellAbility); + ArrayList s = new ArrayList(getCharacteristics().getSpellAbility()); ArrayList res = new ArrayList(); for (SpellAbility sa : s) { @@ -2270,7 +2354,7 @@ public class Card extends GameEntity implements Comparable { * @return a {@link java.util.ArrayList} object. */ public ArrayList getAdditionalCostSpells() { - ArrayList s = new ArrayList(spellAbility); + ArrayList s = new ArrayList(getCharacteristics().getSpellAbility()); ArrayList res = new ArrayList(); for (SpellAbility sa : s) { @@ -3238,7 +3322,7 @@ public class Card extends GameEntity implements Comparable { * @param a a {@link java.util.ArrayList} object. */ public final void setType(final ArrayList a) { - type = new ArrayList(a); + getCharacteristics().setType(new ArrayList(a)); } /** @@ -3247,7 +3331,7 @@ public class Card extends GameEntity implements Comparable { * @param a a {@link java.lang.String} object. */ public final void addType(final String a) { - type.add(a); + getCharacteristics().getType().add(a); } /** @@ -3256,7 +3340,7 @@ public class Card extends GameEntity implements Comparable { * @param a a {@link java.lang.String} object. */ public final void removeType(final String a) { - type.remove(a); + getCharacteristics().getType().remove(a); } /** @@ -3269,7 +3353,7 @@ public class Card extends GameEntity implements Comparable { // see if type changes are in effect if (!changedCardTypes.isEmpty()) { - ArrayList newType = new ArrayList(type); + ArrayList newType = new ArrayList(getCharacteristics().getType()); ArrayList types = changedCardTypes; Collections.sort(types); // sorts types by timeStamp @@ -3308,7 +3392,7 @@ public class Card extends GameEntity implements Comparable { } //nothing changed - return new ArrayList(type); + return new ArrayList(getCharacteristics().getType()); } public void setChangedCardTypes(ArrayList types) { @@ -3357,8 +3441,8 @@ public class Card extends GameEntity implements Comparable { */ public final ArrayList clearAllTypes() { ArrayList originalTypes = new ArrayList(); - originalTypes.addAll(type); - type.clear(); + originalTypes.addAll(getCharacteristics().getType()); + getCharacteristics().getType().clear(); return originalTypes; } @@ -3425,7 +3509,7 @@ public class Card extends GameEntity implements Comparable { * @return a int. */ public final int getBaseAttack() { - return baseAttack; + return getCharacteristics().getBaseAttack(); } /** @@ -3434,7 +3518,7 @@ public class Card extends GameEntity implements Comparable { * @return a int. */ public final int getBaseDefense() { - return baseDefense; + return getCharacteristics().getBaseDefense(); } //values that are printed on card @@ -3444,7 +3528,7 @@ public class Card extends GameEntity implements Comparable { * @param n a int. */ public final void setBaseAttack(final int n) { - baseAttack = n; + getCharacteristics().setBaseAttack(n); } /** @@ -3453,7 +3537,7 @@ public class Card extends GameEntity implements Comparable { * @param n a int. */ public final void setBaseDefense(final int n) { - baseDefense = n; + getCharacteristics().setBaseDefense(n); } //values that are printed on card @@ -4012,7 +4096,7 @@ public class Card extends GameEntity implements Comparable { * @return a {@link java.util.ArrayList} object. */ public final ArrayList getIntrinsicAbilities() { - return intrinsicAbility; + return getCharacteristics().getIntrinsicAbility(); } /** @@ -4021,14 +4105,14 @@ public class Card extends GameEntity implements Comparable { * @return a {@link java.util.ArrayList} object. */ public final ArrayList getIntrinsicKeyword() { - return new ArrayList(intrinsicKeyword); + return new ArrayList(getCharacteristics().getIntrinsicKeyword()); } /** *

clearIntrinsicKeyword.

*/ public final void clearIntrinsicKeyword() { - intrinsicKeyword.clear(); + getCharacteristics().getIntrinsicKeyword().clear(); } /** @@ -4037,14 +4121,14 @@ public class Card extends GameEntity implements Comparable { * @param a a {@link java.util.ArrayList} object. */ public final void setIntrinsicKeyword(final ArrayList a) { - intrinsicKeyword = new ArrayList(a); + getCharacteristics().setIntrinsicKeyword(new ArrayList(a)); } /** *

clearAllKeywords.

*/ public final void clearAllKeywords() { - intrinsicKeyword.clear(); + getCharacteristics().getIntrinsicKeyword().clear(); extrinsicKeyword.clear(); hiddenExtrinsicKeyword.clear(); //Hidden keywords won't be displayed on the card } @@ -4055,7 +4139,7 @@ public class Card extends GameEntity implements Comparable { * @param a a {@link java.util.ArrayList} object. */ public final void setIntrinsicAbilities(final ArrayList a) { - intrinsicAbility = new ArrayList(a); + getCharacteristics().setIntrinsicAbility(new ArrayList(a)); } /** @@ -4065,7 +4149,7 @@ public class Card extends GameEntity implements Comparable { */ public final void addIntrinsicKeyword(final String s) { if (s.trim().length() != 0) { - intrinsicKeyword.add(s); + getCharacteristics().getIntrinsicKeyword().add(s); //intrinsicKeyword.add((getName().trim().length()== 0 ? s :s.replaceAll(getName(), "CARDNAME"))); } } @@ -4077,7 +4161,7 @@ public class Card extends GameEntity implements Comparable { */ public void addIntrinsicAbility(String s) { if (s.trim().length() != 0) - intrinsicAbility.add(s); + getCharacteristics().getIntrinsicAbility().add(s); } /** @@ -4087,7 +4171,7 @@ public class Card extends GameEntity implements Comparable { */ public final void addNonStackingIntrinsicKeyword(String s) { if (!getIntrinsicKeyword().contains(s) && s.trim().length() != 0) { - intrinsicKeyword.add((getName().trim().length() == 0 ? s : s.replaceAll(getName(), "CARDNAME"))); + getCharacteristics().getIntrinsicKeyword().add((getName().trim().length() == 0 ? s : s.replaceAll(getName(), "CARDNAME"))); } } @@ -4097,7 +4181,7 @@ public class Card extends GameEntity implements Comparable { * @param s a {@link java.lang.String} object. */ public final void removeIntrinsicKeyword(String s) { - intrinsicKeyword.remove(s); + getCharacteristics().getIntrinsicKeyword().remove(s); } /** @@ -4106,7 +4190,7 @@ public class Card extends GameEntity implements Comparable { * @return a int. */ public final int getIntrinsicKeywordSize() { - return intrinsicKeyword.size(); + return getCharacteristics().getIntrinsicKeyword().size(); } /** @@ -4284,18 +4368,18 @@ public class Card extends GameEntity implements Comparable { } public void setStaticAbilities(ArrayList a) { - staticAbilities = new ArrayList(a); + getCharacteristics().setStaticAbilities(new ArrayList(a)); } public ArrayList getStaticAbilities() { - return new ArrayList(staticAbilities); + return new ArrayList(getCharacteristics().getStaticAbilities()); } public void addStaticAbility(String s) { if (s.trim().length() != 0) { StaticAbility stAb = new StaticAbility(s,this); - staticAbilities.add(stAb); + getCharacteristics().getStaticAbilities().add(stAb); } } @@ -4534,7 +4618,7 @@ public class Card extends GameEntity implements Comparable { Card c = (Card) o; int a = getUniqueNumber(); int b = c.getUniqueNumber(); - return (a == b); + return (a == b); } return false; } @@ -4766,7 +4850,7 @@ public class Card extends GameEntity implements Comparable { * @return a boolean. */ public boolean isReflectedLand() { - for(Ability_Mana am : manaAbility) + for(Ability_Mana am : getCharacteristics().getManaAbility()) if (am.isReflectedMana()) return true; @@ -5011,6 +5095,10 @@ public class Card extends GameEntity implements Comparable { //Should this match All chosen colors, or any? Default to first chosen for now until it matters. if (source.getChosenColor().size() == 0) return false; if (!CardUtil.getColors(this).contains(source.getChosenColor().get(0))) return false; + } else if (Property.equals("DoubleFaced")) { + if (!isDoubleFaced) return false; + } else if (Property.equals("Flip")) { + if (!isFlip) return false; } else if (Property.startsWith("YouCtrl")) { if (!getController().isPlayer(sourceController)) return false; } else if (Property.startsWith("YouDontCtrl")) { @@ -5253,7 +5341,7 @@ public class Card extends GameEntity implements Comparable { { if (isType(Property.substring(3))) return false; } else if (Property.equals("CostsPhyrexianMana")) { - if (!manaCost.contains("P")) return false; + if (!getCharacteristics().getManaCost().contains("P")) return false; } else if (Property.equals("IsRemembered")) { if(!source.getRemembered().contains(this)) return false; } else { @@ -6026,7 +6114,7 @@ public class Card extends GameEntity implements Comparable { } - private ArrayList Sets = new ArrayList(); + private String curSetCode = ""; /** @@ -6035,7 +6123,7 @@ public class Card extends GameEntity implements Comparable { * @param sInfo a {@link forge.SetInfo} object. */ public final void addSet(final SetInfo sInfo) { - Sets.add(sInfo); + getCharacteristics().getSets().add(sInfo); } /** @@ -6044,7 +6132,7 @@ public class Card extends GameEntity implements Comparable { * @return a {@link java.util.ArrayList} object. */ public final ArrayList getSets() { - return Sets; + return getCharacteristics().getSets(); } /** @@ -6053,7 +6141,7 @@ public class Card extends GameEntity implements Comparable { * @param siList a {@link java.util.ArrayList} object. */ public final void setSets(final ArrayList siList) { - Sets = siList; + getCharacteristics().setSets(siList); } /** @@ -6078,12 +6166,12 @@ public class Card extends GameEntity implements Comparable { *

setRandomSetCode.

*/ public final void setRandomSetCode() { - if (Sets.size() < 1) { + if (getCharacteristics().getSets().size() < 1) { return; } Random r = MyRandom.random; - SetInfo si = Sets.get(r.nextInt(Sets.size())); + SetInfo si = getCharacteristics().getSets().get(r.nextInt(getCharacteristics().getSets().size())); curSetCode = si.Code; } @@ -6113,9 +6201,9 @@ public class Card extends GameEntity implements Comparable { * @return a {@link java.lang.String} object. */ public final String getCurSetRarity() { - for (int i = 0; i < Sets.size(); i++) { - if (Sets.get(i).Code.equals(curSetCode)) { - return Sets.get(i).Rarity; + for (int i = 0; i < getCharacteristics().getSets().size(); i++) { + if (getCharacteristics().getSets().get(i).Code.equals(curSetCode)) { + return getCharacteristics().getSets().get(i).Rarity; } } @@ -6128,9 +6216,9 @@ public class Card extends GameEntity implements Comparable { * @return a {@link java.lang.String} object. */ public final String getCurSetURL() { - for (int i = 0; i < Sets.size(); i++) { - if (Sets.get(i).Code.equals(curSetCode)) { - return Sets.get(i).URL; + for (int i = 0; i < getCharacteristics().getSets().size(); i++) { + if (getCharacteristics().getSets().get(i).Code.equals(curSetCode)) { + return getCharacteristics().getSets().get(i).URL; } } @@ -6146,15 +6234,13 @@ public class Card extends GameEntity implements Comparable { return CardDb.instance().getCard(this.getName()).getSet(); } - private String ImageFilename = ""; - /** *

setImageFilename.

* * @param iFN a {@link java.lang.String} object. */ public void setImageFilename(final String iFN) { - ImageFilename = iFN; + getCharacteristics().setImageFilename(iFN); } /** @@ -6163,7 +6249,7 @@ public class Card extends GameEntity implements Comparable { * @return a {@link java.lang.String} object. */ public final String getImageFilename() { - return ImageFilename; + return getCharacteristics().getImageFilename(); } /** @@ -6208,8 +6294,8 @@ public class Card extends GameEntity implements Comparable { * @return an int */ public final int getFoil() { - if (sVars.containsKey("Foil")) { - return Integer.parseInt(sVars.get("Foil")); + if (getCharacteristics().getsVars().containsKey("Foil")) { + return Integer.parseInt(getCharacteristics().getsVars().get("Foil")); } return 0; } @@ -6220,7 +6306,7 @@ public class Card extends GameEntity implements Comparable { * @param f an int */ public final void setFoil(final int f) { - sVars.put("Foil", Integer.toString(f)); + getCharacteristics().getsVars().put("Foil", Integer.toString(f)); } public final void addHauntedBy(final Card c) { @@ -6254,5 +6340,18 @@ public class Card extends GameEntity implements Comparable { return sum; } + + /** + * @return the cardColorsOverridden + */ + public boolean isCardColorsOverridden() { + return getCharacteristics().isCardColorsOverridden(); + } + /** + * @param cardColorsOverridden0 the cardColorsOverridden to set + */ + public void setCardColorsOverridden(boolean cardColorsOverridden0) { + getCharacteristics().setCardColorsOverridden(cardColorsOverridden0); + } } //end Card class diff --git a/src/main/java/forge/CardReader.java b/src/main/java/forge/CardReader.java index 238e13e5a14..48ea974b9c5 100644 --- a/src/main/java/forge/CardReader.java +++ b/src/main/java/forge/CardReader.java @@ -27,6 +27,7 @@ import net.slightlymagic.braids.util.progress_monitor.StderrProgressMonitor; import com.google.code.jyield.Generator; import com.google.code.jyield.YieldUtils; +import forge.card.CardColor; import forge.card.CardRules; import forge.card.CardRulesReader; import forge.card.trigger.TriggerHandler; @@ -321,7 +322,9 @@ public class CardReader String line = readLine(reader); while (!"End".equals(line)) { rulesReader.parseLine(line); - if (line.charAt(0) == '#') { // NOPMD by Braids on 8/18/11 10:59 PM + if(line.isEmpty()) { + //Ignore empty lines. + } else if (line.charAt(0) == '#') { // NOPMD by Braids on 8/18/11 10:59 PM //no need to do anything, this indicates a comment line } else if (line.startsWith("Name:")) { final String value = line.substring(5); @@ -389,6 +392,27 @@ public class CardReader } else if (line.startsWith("SetInfo:")) { final String value = line.substring("SetInfo:".length()); card.addSet(new SetInfo(value)); // NOPMD by Braids on 8/18/11 11:08 PM + } else if (line.equals("ALTERNATE")) { + card.addAlternateState(); + card.changeState(); + } else if (line.startsWith("AlternateMode:")) { + final String value = line.substring("AlternateMode:".length()); + if(value.equalsIgnoreCase("Flip")) { + card.setFlip(true); + } else { + card.setDoubleFaced(true); + } + } else if (line.startsWith("Colors:")) { + final String value = line.substring("Colors:".length()); + ArrayList newCols = new ArrayList(); + for(String col : value.split(",")) { + Card_Color newCol = new Card_Color(card); + newCol.addToCardColor(col); + newCols.add(newCol); + } + + card.setColor(newCols); + card.setCardColorsOverridden(true); } line = readLine(reader); @@ -403,8 +427,14 @@ public class CardReader } catch (IOException ignored) { // NOPMD by Braids on 8/18/11 11:08 PM } } + + if(card.isInAlternateState()) { + card.changeState(); + } - listRulesToFill.add(rulesReader.getCard()); + CardRules[] crdRules = rulesReader.getCard(); + listRulesToFill.add(crdRules[0]); + if(crdRules[1] != null) { listRulesToFill.add(crdRules[1]); } mapToFill.put(card.getName(), card); return card; } diff --git a/src/main/java/forge/CombatUtil.java b/src/main/java/forge/CombatUtil.java index daddc4f0303..415eec200d9 100644 --- a/src/main/java/forge/CombatUtil.java +++ b/src/main/java/forge/CombatUtil.java @@ -1039,8 +1039,9 @@ public class CombatUtil { power += defender.getKeywordMagnitude("Bushido"); - ArrayList registeredTriggers = AllZone.getTriggerHandler().getRegisteredTriggers(); - for (Trigger trigger : registeredTriggers) { + ArrayList theTriggers = new ArrayList(defender.getTriggers()); + theTriggers.addAll(attacker.getTriggers()); + for (Trigger trigger : theTriggers) { HashMap trigParams = trigger.getMapParams(); Card source = trigger.getHostCard(); @@ -1092,8 +1093,9 @@ public class CombatUtil { toughness += defender.getKeywordMagnitude("Bushido"); - ArrayList registeredTriggers = AllZone.getTriggerHandler().getRegisteredTriggers(); - for (Trigger trigger : registeredTriggers) { + ArrayList theTriggers = new ArrayList(defender.getTriggers()); + theTriggers.addAll(attacker.getTriggers()); + for (Trigger trigger : theTriggers) { HashMap trigParams = trigger.getMapParams(); Card source = trigger.getHostCard(); @@ -1141,18 +1143,21 @@ public class CombatUtil { int power = 0; power += attacker.getKeywordMagnitude("Bushido"); - + + + ArrayList theTriggers = new ArrayList(attacker.getTriggers()); //if the defender has first strike and wither the attacker will deal less damage than expected if (null != defender) { if ((defender.hasKeyword("First Strike") || defender.hasKeyword("Double Strike")) && (defender.hasKeyword("Wither") || defender.hasKeyword("Infect")) && !(attacker.hasKeyword("First Strike") || attacker.hasKeyword("Double Strike") - || attacker.hasKeyword("CARDNAME can't have counters placed on it."))) + || attacker.hasKeyword("CARDNAME can't have counters placed on it."))) { power -= defender.getNetCombatDamage(); + } + theTriggers.addAll(defender.getTriggers()); } - - ArrayList registeredTriggers = AllZone.getTriggerHandler().getRegisteredTriggers(); - for (Trigger trigger : registeredTriggers) { + + for (Trigger trigger : theTriggers) { HashMap trigParams = trigger.getMapParams(); Card source = trigger.getHostCard(); @@ -1206,12 +1211,14 @@ public class CombatUtil { public static int predictToughnessBonusOfAttacker(Card attacker, Card defender, Combat combat) { int toughness = 0; + ArrayList theTriggers = new ArrayList(attacker.getTriggers()); if (defender != null) { toughness += attacker.getKeywordMagnitude("Bushido"); + theTriggers.addAll(defender.getTriggers()); } - - ArrayList registeredTriggers = AllZone.getTriggerHandler().getRegisteredTriggers(); - for (Trigger trigger : registeredTriggers) { + + + for (Trigger trigger : theTriggers) { HashMap trigParams = trigger.getMapParams(); Card source = trigger.getHostCard(); diff --git a/src/main/java/forge/ComputerUtil_Attack2.java b/src/main/java/forge/ComputerUtil_Attack2.java index 52a43a4c339..0da0e98272d 100644 --- a/src/main/java/forge/ComputerUtil_Attack2.java +++ b/src/main/java/forge/ComputerUtil_Attack2.java @@ -74,10 +74,10 @@ public class ComputerUtil_Attack2 { //Cards with triggers should come first (for Battle Cry) for (Card attacker : in) { - ArrayList registeredTriggers = AllZone.getTriggerHandler().getRegisteredTriggers(); + ArrayList registeredTriggers = attacker.getTriggers(); for (Trigger trigger : registeredTriggers) { HashMap trigParams = trigger.getMapParams(); - if (trigParams.get("Mode").equals("Attacks") && trigger.getHostCard().equals(attacker)) { + if (trigParams.get("Mode").equals("Attacks")) { list.add(attacker); } } @@ -113,12 +113,14 @@ public class ComputerUtil_Attack2 { if (CombatUtil.poisonIfUnblocked(attacker, AllZone.getHumanPlayer(), combat) > 0) { return true; } + + CardList controlledByCompy = AllZone.getComputerPlayer().getAllCards(); - ArrayList registeredTriggers = AllZone.getTriggerHandler().getRegisteredTriggers(); - for (Trigger trigger : registeredTriggers) { - if (CombatUtil.combatTriggerWillTrigger(attacker, null, trigger, combat) - && trigger.getHostCard().getController().isComputer()) { - return true; + for(Card c : controlledByCompy) { + for (Trigger trigger : c.getTriggers()) { + if (CombatUtil.combatTriggerWillTrigger(attacker, null, trigger, combat)) { + return true; + } } } diff --git a/src/main/java/forge/GameAction.java b/src/main/java/forge/GameAction.java index a3edcba07b2..8473c49b842 100644 --- a/src/main/java/forge/GameAction.java +++ b/src/main/java/forge/GameAction.java @@ -66,6 +66,13 @@ public class GameAction { for (SpellAbility sa : card.getSpellAbility()) { sa.getRestrictions().resetTurnActivations(); } + if(card.hasAlternateState()) { + card.changeState(); + for (SpellAbility sa : card.getSpellAbility()) { + sa.getRestrictions().resetTurnActivations(); + } + card.changeState(); + } } } @@ -100,6 +107,9 @@ public class GameAction { lastKnownInfo = c; copied = c; } else { + if(c.isInAlternateState()) { + c.changeState(); + } copied = AllZone.getCardFactory().copyCard(c); lastKnownInfo = CardUtil.getLKICopy(c); @@ -1137,18 +1147,12 @@ public class GameAction { AllZone.getHumanPlayer().setLife(humanLife, null); for (Card c : human) { - for (Trigger trig : c.getTriggers()) { - AllZone.getTriggerHandler().registerTrigger(trig); - } AllZone.getHumanPlayer().getZone(Zone.Battlefield).add(c); c.setSickness(true); } for (Card c : computer) { - for (Trigger trig : c.getTriggers()) { - AllZone.getTriggerHandler().registerTrigger(trig); - } AllZone.getComputerPlayer().getZone(Zone.Battlefield).add(c); c.setSickness(true); @@ -1185,6 +1189,9 @@ public class GameAction { CardPrinted cardPrinted = stackOfCards.getKey(); for (int i = 0; i < stackOfCards.getValue(); i++) { + if(cardPrinted.isAlternate()) { + continue; + } Card card = c.getCard(cardPrinted.getName(), AllZone.getHumanPlayer()); card.setCurSetCode(cardPrinted.getSet()); @@ -1200,9 +1207,11 @@ public class GameAction { } AllZone.getHumanPlayer().getZone(Zone.Library).add(card); - - for (Trigger trig : card.getTriggers()) { - AllZone.getTriggerHandler().registerTrigger(trig); + + if(card.hasAlternateState()) { + card.changeState(); + card.setImageFilename(CardUtil.buildFilename(card)); + card.changeState(); } } } @@ -1228,10 +1237,6 @@ public class GameAction { AllZone.getComputerPlayer().getZone(Zone.Library).add(card); - for (Trigger trig : card.getTriggers()) { - AllZone.getTriggerHandler().registerTrigger(trig); - } - if (card.getSVar("RemAIDeck").equals("True")) { RAICards.add(card.getName()); //get card picture so that it is in the image cache diff --git a/src/main/java/forge/GuiDisplayUtil.java b/src/main/java/forge/GuiDisplayUtil.java index a74e6746ace..3d32caf0666 100644 --- a/src/main/java/forge/GuiDisplayUtil.java +++ b/src/main/java/forge/GuiDisplayUtil.java @@ -1438,9 +1438,6 @@ public final class GuiDisplayUtil implements NewConstants { } c.setImageFilename(CardUtil.buildFilename(c)); - for (Trigger trig : c.getTriggers()) { - AllZone.getTriggerHandler().registerTrigger(trig); - } cl.add(c); } return cl; diff --git a/src/main/java/forge/Player.java b/src/main/java/forge/Player.java index db7b380070c..d20cb2360d5 100644 --- a/src/main/java/forge/Player.java +++ b/src/main/java/forge/Player.java @@ -871,6 +871,18 @@ public abstract class Player extends GameEntity { return new CardList(cards); } + private static ArrayList allZones = new ArrayList(); + + static { + for(Zone z : Constant.Zone.values()) { + allZones.add(z); + } + } + + public CardList getAllCards() { + return getCardsIn(allZones); + } + public CardList getCardsIncludePhasingIn(final Constant.Zone zone) { Card[] cards = zone == Zone.Stack ? AllZone.getStackZone().getCards() : getZone(zone).getCards(false); return new CardList(cards); @@ -896,7 +908,11 @@ public abstract class Player extends GameEntity { */ public CardList getCardsIn(final List zones) { CardList result = new CardList(); - for (Constant.Zone z : zones) { result.addAll(getZone(z).getCards()); } + for (Constant.Zone z : zones) { + if(getZone(z) != null) { + result.addAll(getZone(z).getCards()); + } + } return result; } diff --git a/src/main/java/forge/SetUtils.java b/src/main/java/forge/SetUtils.java index a6fe10511a4..9247e5e60a5 100644 --- a/src/main/java/forge/SetUtils.java +++ b/src/main/java/forge/SetUtils.java @@ -78,7 +78,7 @@ public final class SetUtils { String[] sParts = s.trim().split("\\|"); String code = null; - int nC = 0, nU = 0, nR = 0, nS = 0; + int nC = 0, nU = 0, nR = 0, nS = 0, nDF = 0; for (String sPart : sParts) { String[] kv = sPart.split(":", 2); String key = kv[0].toLowerCase(); @@ -88,8 +88,9 @@ public final class SetUtils { if (key.equalsIgnoreCase("Uncommons")) { nU = Integer.parseInt(kv[1]); } if (key.equalsIgnoreCase("Rares")) { nR = Integer.parseInt(kv[1]); } if (key.equalsIgnoreCase("Special")) { nS = Integer.parseInt(kv[1]); } + if (key.equalsIgnoreCase("DoubleFaced")) { nDF = Integer.parseInt(kv[1]); } } - result.put(code, new CardSet.BoosterData(nC, nU, nR, nS)); + result.put(code, new CardSet.BoosterData(nC, nU, nR, nS, nDF)); } return result; } diff --git a/src/main/java/forge/card/BoosterGenerator.java b/src/main/java/forge/card/BoosterGenerator.java index f13e2192c05..63766ca95af 100644 --- a/src/main/java/forge/card/BoosterGenerator.java +++ b/src/main/java/forge/card/BoosterGenerator.java @@ -42,6 +42,7 @@ public class BoosterGenerator { private final List rares = new ArrayList(); private final List mythics = new ArrayList(); private final List specials = new ArrayList(); + private final List doubleFaced = new ArrayList(); //private List commonCreatures; //private List commonNonCreatures; @@ -53,6 +54,7 @@ public class BoosterGenerator { private int numCommons = 10; private int numUncommons = 3; private int numRareSlots = 1; + private int numDoubleFaced = 0; private int numSpecials = 0; /** @@ -84,8 +86,9 @@ public class BoosterGenerator { numUncommons = bs.getUncommon(); numRareSlots = bs.getRare(); numSpecials = bs.getSpecial(); + numDoubleFaced = bs.getDoubleFaced(); - Predicate filter = CardPrinted.Predicates.printedInSets(cardSet.getCode()); + Predicate filter = Predicate.and(CardPrinted.Predicates.printedInSets(cardSet.getCode()), CardPrinted.Predicates.Presets.nonAlternate); List cardsInThisSet = filter.select(CardDb.instance().getAllCards()); for (CardPrinted c : cardsInThisSet) { @@ -149,13 +152,13 @@ public class BoosterGenerator { public final List getBoosterPack() { - return getBoosterPack(numCommons, numUncommons, numRareSlots, 0, 0, numSpecials, 0, 0); + return getBoosterPack(numCommons, numUncommons, numRareSlots, 0, 0, numSpecials, numDoubleFaced, 0, 0); } /** * So many parameters are needed for custom limited cardpools, */ public final List getBoosterPack(final int nCom, final int nUnc, final int nRareSlots, - final int nRares, final int nMythics, final int nSpecs, final int nAnyCard, final int nLands) { + final int nRares, final int nMythics, final int nSpecs, final int nDoubls, final int nAnyCard, final int nLands) { List temp = new ArrayList(); @@ -179,6 +182,9 @@ public class BoosterGenerator { temp.addAll(pickRandomCards(rares, nRares)); temp.addAll(pickRandomCards(mythics, nMythics)); } + if (nDoubls > 0) { + temp.addAll(pickRandomCards(doubleFaced,nDoubls)); + } temp.addAll(pickRandomCards(specials, nSpecs)); @@ -190,12 +196,16 @@ public class BoosterGenerator { } private void addToRarity(final CardPrinted c) { - switch(c.getRarity()) { - case Common: commons.add(c); break; - case Uncommon: uncommons.add(c); break; - case Rare: rares.add(c); break; - case MythicRare: mythics.add(c); break; - case Special: specials.add(c); break; + if(c.isDoubleFaced() && numDoubleFaced > 0) { + doubleFaced.add(c); + } else { + switch(c.getRarity()) { + case Common: commons.add(c); break; + case Uncommon: uncommons.add(c); break; + case Rare: rares.add(c); break; + case MythicRare: mythics.add(c); break; + case Special: specials.add(c); break; + } } if (c.getCard().getType().isBasicLand()) { diff --git a/src/main/java/forge/card/CardCharacteristics.java b/src/main/java/forge/card/CardCharacteristics.java new file mode 100644 index 00000000000..15129e3eca0 --- /dev/null +++ b/src/main/java/forge/card/CardCharacteristics.java @@ -0,0 +1,229 @@ +package forge.card; + +import java.util.ArrayList; +import java.util.HashMap; +import java.util.Map; +import java.util.TreeMap; + +import forge.Card_Color; +import forge.Counters; +import forge.SetInfo; +import forge.card.spellability.Ability_Mana; +import forge.card.spellability.SpellAbility; +import forge.card.staticAbility.StaticAbility; +import forge.card.trigger.Trigger; + +/** + * TODO: Write javadoc for this type. + * + */ +public class CardCharacteristics { + private String name = ""; + private ArrayList type = new ArrayList(); + private String manaCost = ""; + private ArrayList cardColor = new ArrayList(); + private boolean cardColorsOverridden = false; + private int baseAttack = 0; + private int baseDefense = 0; + private ArrayList intrinsicKeyword = new ArrayList(); + private ArrayList spellAbility = new ArrayList(); + private ArrayList intrinsicAbility = new ArrayList(); + private ArrayList manaAbility = new ArrayList(); + private ArrayList triggers = new ArrayList(); + private ArrayList staticAbilities = new ArrayList(); + private String ImageFilename = ""; + private Map sVars = new TreeMap(); + private ArrayList Sets = new ArrayList(); + /** + * @return the name + */ + public String getName() { + return name; + } + /** + * @param name0 the name to set + */ + public void setName(String name0) { + this.name = name0; // TODO: Add 0 to parameter's name. + } + /** + * @return the type + */ + public ArrayList getType() { + return type; + } + /** + * @param type0 the type to set + */ + public void setType(ArrayList type0) { + this.type = type0; // TODO: Add 0 to parameter's name. + } + /** + * @return the manaCost + */ + public String getManaCost() { + return manaCost; + } + /** + * @param manaCost0 the manaCost to set + */ + public void setManaCost(String manaCost0) { + this.manaCost = manaCost0; // TODO: Add 0 to parameter's name. + } + /** + * @return the cardColor + */ + public ArrayList getCardColor() { + return cardColor; + } + /** + * @param cardColor0 the cardColor to set + */ + public void setCardColor(ArrayList cardColor0) { + this.cardColor = new ArrayList(cardColor0); // TODO: Add 0 to parameter's name. + } + /** + * @return the cardColorsOverridden + */ + public boolean isCardColorsOverridden() { + return cardColorsOverridden; + } + /** + * @param cardColorsOverridden0 the cardColorsOverridden to set + */ + public void setCardColorsOverridden(boolean cardColorsOverridden0) { + this.cardColorsOverridden = cardColorsOverridden0; // TODO: Add 0 to parameter's name. + } + /** + * @return the baseAttack + */ + public int getBaseAttack() { + return baseAttack; + } + /** + * @param baseAttack0 the baseAttack to set + */ + public void setBaseAttack(int baseAttack0) { + this.baseAttack = baseAttack0; // TODO: Add 0 to parameter's name. + } + /** + * @return the baseDefense + */ + public int getBaseDefense() { + return baseDefense; + } + /** + * @param baseDefense0 the baseDefense to set + */ + public void setBaseDefense(int baseDefense0) { + this.baseDefense = baseDefense0; // TODO: Add 0 to parameter's name. + } + /** + * @return the intrinsicKeyword + */ + public ArrayList getIntrinsicKeyword() { + return intrinsicKeyword; + } + /** + * @param intrinsicKeyword0 the intrinsicKeyword to set + */ + public void setIntrinsicKeyword(ArrayList intrinsicKeyword0) { + this.intrinsicKeyword = intrinsicKeyword0; // TODO: Add 0 to parameter's name. + } + /** + * @return the spellAbility + */ + public ArrayList getSpellAbility() { + return spellAbility; + } + /** + * @param spellAbility0 the spellAbility to set + */ + public void setSpellAbility(ArrayList spellAbility0) { + this.spellAbility = spellAbility0; // TODO: Add 0 to parameter's name. + } + /** + * @return the intrinsicAbility + */ + public ArrayList getIntrinsicAbility() { + return intrinsicAbility; + } + /** + * @param intrinsicAbility0 the intrinsicAbility to set + */ + public void setIntrinsicAbility(ArrayList intrinsicAbility0) { + this.intrinsicAbility = intrinsicAbility0; // TODO: Add 0 to parameter's name. + } + /** + * @return the manaAbility + */ + public ArrayList getManaAbility() { + return manaAbility; + } + /** + * @param manaAbility0 the manaAbility to set + */ + public void setManaAbility(ArrayList manaAbility0) { + this.manaAbility = manaAbility0; // TODO: Add 0 to parameter's name. + } + /** + * @return the triggers + */ + public ArrayList getTriggers() { + return triggers; + } + /** + * @param triggers0 the triggers to set + */ + public void setTriggers(ArrayList triggers0) { + this.triggers = triggers0; // TODO: Add 0 to parameter's name. + } + /** + * @return the staticAbilities + */ + public ArrayList getStaticAbilities() { + return staticAbilities; + } + /** + * @param staticAbilities0 the staticAbilities to set + */ + public void setStaticAbilities(ArrayList staticAbilities0) { + this.staticAbilities = new ArrayList(staticAbilities0); // TODO: Add 0 to parameter's name. + } + /** + * @return the imageFilename + */ + public String getImageFilename() { + return ImageFilename; + } + /** + * @param imageFilename0 the imageFilename to set + */ + public void setImageFilename(String imageFilename0) { + ImageFilename = imageFilename0; // TODO: Add 0 to parameter's name. + } + /** + * @return the sVars + */ + public Map getsVars() { + return sVars; + } + /** + * @param sVars0 the sVars to set + */ + public void setsVars(Map sVars0) { + this.sVars = new HashMap(sVars0); // TODO: Add 0 to parameter's name. + } + /** + * @return the sets + */ + public ArrayList getSets() { + return Sets; + } + /** + * @param sets0 the sets to set + */ + public void setSets(ArrayList sets0) { + Sets = new ArrayList(sets0); // TODO: Add 0 to parameter's name. + } +} diff --git a/src/main/java/forge/card/CardRuleCharacteristics.java b/src/main/java/forge/card/CardRuleCharacteristics.java new file mode 100644 index 00000000000..ea2527ef2cf --- /dev/null +++ b/src/main/java/forge/card/CardRuleCharacteristics.java @@ -0,0 +1,104 @@ +package forge.card; + +import java.util.Map; +import java.util.TreeMap; + +/** + * TODO: Write javadoc for this type. + * + */ +public class CardRuleCharacteristics { + private String cardName = null; + private CardType cardType = null; + private CardManaCost manaCost = CardManaCost.empty; + private CardColor color = null; + private String ptLine = null; + private String[] cardRules = null; + private Map setsData = new TreeMap(); + + /** + * @return the cardName + */ + public String getCardName() { + return cardName; + } + /** + * @param cardName0 the cardName to set + */ + public void setCardName(String cardName0) { + this.cardName = cardName0; // TODO: Add 0 to parameter's name. + } + /** + * @return the cardType + */ + public CardType getCardType() { + return cardType; + } + /** + * @param cardType0 the cardType to set + */ + public void setCardType(CardType cardType0) { + this.cardType = cardType0; // TODO: Add 0 to parameter's name. + } + /** + * @return the manaCost + */ + public CardManaCost getManaCost() { + return manaCost; + } + /** + * @param manaCost0 the manaCost to set + */ + public void setManaCost(CardManaCost manaCost0) { + this.manaCost = manaCost0; // TODO: Add 0 to parameter's name. + this.color = new CardColor(this.manaCost); + } + /** + * @return the color + */ + public CardColor getColor() { + return color; + } + /** + * @param color0 the color to set + */ + public void setColor(CardColor color0) { + this.color = color0; // TODO: Add 0 to parameter's name. + } + /** + * @return the ptLine + */ + public String getPtLine() { + return ptLine; + } + /** + * @param ptLine0 the ptLine to set + */ + public void setPtLine(String ptLine0) { + this.ptLine = ptLine0; // TODO: Add 0 to parameter's name. + } + /** + * @return the cardRules + */ + public String[] getCardRules() { + return cardRules; + } + /** + * @param cardRules0 the cardRules to set + */ + public void setCardRules(String[] cardRules0) { + this.cardRules = cardRules0; // TODO: Add 0 to parameter's name. + } + /** + * @return the setsData + */ + public Map getSetsData() { + return setsData; + } + /** + * @param setsData0 the setsData to set + */ + public void setSetsData(Map setsData0) { + this.setsData = setsData0; // TODO: Add 0 to parameter's name. + } +} diff --git a/src/main/java/forge/card/CardRules.java b/src/main/java/forge/card/CardRules.java index 8cfda40688a..c2cfcf78988 100644 --- a/src/main/java/forge/card/CardRules.java +++ b/src/main/java/forge/card/CardRules.java @@ -20,11 +20,8 @@ import org.apache.commons.lang3.StringUtils; * @version $Id: CardOracle.java 9708 2011-08-09 19:34:12Z jendave $ */ public final class CardRules { - private final String name; - private final CardType type; - private final CardManaCost cost; - private CardColor color = null; // color is subject to change yet (parse %cardname% is %color% rule) - private final String[] rules; + + private final CardRuleCharacteristics characteristics; private int iPower = -1; private int iToughness = -1; @@ -39,12 +36,12 @@ public final class CardRules { private boolean isRemovedFromRandomDecks = false; // Ctor and builders are needed here - public String getName() { return name; } - public CardType getType() { return type; } - public CardManaCost getManaCost() { return cost; } - public CardColor getColor() { return color; } - public String[] getRules() { return rules; } - public Set> getSetsPrinted() { return setsPrinted.entrySet(); } + public String getName() { return characteristics.getCardName(); } + public CardType getType() { return characteristics.getCardType(); } + public CardManaCost getManaCost() { return characteristics.getManaCost(); } + public CardColor getColor() { return characteristics.getColor(); } + public String[] getRules() { return characteristics.getCardRules(); } + public Set> getSetsPrinted() { return characteristics.getSetsData().entrySet(); } public String getPower() { return power; } public int getIntPower() { return iPower; } @@ -59,43 +56,51 @@ public final class CardRules { if (getType().isPlaneswalker()) { return loyalty; } return ""; } + + private final boolean isAlt; + public boolean isAltState() { + return isAlt; + } + + private final boolean isDFC; + public boolean isDoubleFaced() { + return isDFC; + } - public CardRules(final String cardName, final CardType cardType, final CardManaCost manacost, - final String ptLine, final String[] oracleRules, final Map setsData, + public CardRules(final CardRuleCharacteristics chars, + final boolean isDoubleFacedCard, final boolean isAlt0, final boolean removedFromRandomDecks, final boolean removedFromAIDecks) { - this.name = cardName; - this.type = cardType; - this.cost = manacost; - this.rules = oracleRules; - this.color = new CardColor(cost); + characteristics = chars; + isAlt = isAlt0; + isDFC = isDoubleFacedCard; this.isRemovedFromAIDecks = removedFromAIDecks; this.isRemovedFromRandomDecks = removedFromRandomDecks; //System.out.println(cardName); - if (cardType.isCreature()) { - int slashPos = ptLine == null ? -1 : ptLine.indexOf('/'); + if (getType().isCreature()) { + int slashPos = characteristics.getPtLine() == null ? -1 : characteristics.getPtLine().indexOf('/'); if (slashPos == -1) { - throw new RuntimeException(String.format("Creature '%s' has bad p/t stats", cardName)); + throw new RuntimeException(String.format("Creature '%s' has bad p/t stats", getName())); } - this.power = ptLine.substring(0, slashPos); - this.toughness = ptLine.substring(slashPos + 1, ptLine.length()); + this.power = characteristics.getPtLine().substring(0, slashPos); + this.toughness = characteristics.getPtLine().substring(slashPos + 1, characteristics.getPtLine().length()); this.iPower = StringUtils.isNumeric(power) ? Integer.parseInt(power) : 0; this.iToughness = StringUtils.isNumeric(toughness) ? Integer.parseInt(toughness) : 0; - } else if (cardType.isPlaneswalker()) { - this.loyalty = ptLine; + } else if (getType().isPlaneswalker()) { + this.loyalty = characteristics.getPtLine(); } - if (setsData.isEmpty()) { - setsData.put("???", new CardInSet(CardRarity.Unknown, 1)); + if (characteristics.getSetsData().isEmpty()) { + characteristics.getSetsData().put("???", new CardInSet(CardRarity.Unknown, 1)); } - setsPrinted = setsData; + setsPrinted = characteristics.getSetsData(); } public boolean rulesContain(final String text) { - if (rules == null) { return false; } - for (String r : rules) { if (StringUtils.containsIgnoreCase(r, text)) { return true; } } + if (characteristics.getCardRules() == null) { return false; } + for (String r : characteristics.getCardRules()) { if (StringUtils.containsIgnoreCase(r, text)) { return true; } } return false; } public String getLatestSetPrinted() { @@ -109,7 +114,7 @@ public final class CardRules { public CardInSet getSetInfo(final String setCode) { CardInSet result = setsPrinted.get(setCode); if (result != null) { return result; } - throw new RuntimeException(String.format("Card '%s' was never printed in set '%s'", name, setCode)); + throw new RuntimeException(String.format("Card '%s' was never printed in set '%s'", getName(), setCode)); } public CardRarity getRarityFromLatestSet() { diff --git a/src/main/java/forge/card/CardRulesReader.java b/src/main/java/forge/card/CardRulesReader.java index c076ce0457c..55da2ef01e5 100644 --- a/src/main/java/forge/card/CardRulesReader.java +++ b/src/main/java/forge/card/CardRulesReader.java @@ -17,53 +17,55 @@ import forge.card.CardManaCost.ManaParser; */ public class CardRulesReader { - private String cardName = null; - private CardType cardType = null; - private CardManaCost manaCost = CardManaCost.empty; - private String ptLine = null; - private String[] cardRules = null; - private Map setsData = new TreeMap(); + private CardRuleCharacteristics[] characteristics = new CardRuleCharacteristics[] { new CardRuleCharacteristics() , null }; + private int curCharacteristics = 0; + + private boolean isFlipCard = false; + private boolean isDoubleFacedCard = false; + private boolean removedFromAIDecks = false; private boolean removedFromRandomDecks = false; // Reset all fields to parse next card (to avoid allocating new CardRulesReader N times) public final void reset() { - cardName = null; - cardType = null; - manaCost = CardManaCost.empty; - ptLine = null; - cardRules = null; - setsData = new TreeMap(); + characteristics = new CardRuleCharacteristics[] { new CardRuleCharacteristics() , null }; + curCharacteristics = 0; removedFromAIDecks = false; removedFromRandomDecks = false; + isDoubleFacedCard = false; + isFlipCard = false; } - public final CardRules getCard() { - return new CardRules(cardName, cardType, manaCost, ptLine, cardRules, setsData, removedFromRandomDecks, removedFromAIDecks); - } - + public final CardRules[] getCard() { + CardRules[] ret = new CardRules[] { new CardRules(characteristics[0], isDoubleFacedCard, false, removedFromRandomDecks, removedFromAIDecks), null }; + if(characteristics[1] != null) { + ret [1] = new CardRules(characteristics[1], isDoubleFacedCard, true, removedFromRandomDecks,removedFromAIDecks); + } + + return ret; + } public final void parseLine(final String line) { if (line.startsWith("Name:")) { - cardName = getValueAfterKey(line, "Name:"); - if (cardName == null || cardName.isEmpty()) { + characteristics[curCharacteristics].setCardName(getValueAfterKey(line, "Name:")); + if (characteristics[curCharacteristics].getCardName() == null || characteristics[curCharacteristics].getCardName().isEmpty()) { throw new RuntimeException("Card name is empty"); } } else if (line.startsWith("ManaCost:")) { String sCost = getValueAfterKey(line, "ManaCost:"); - manaCost = "no cost".equals(sCost) ? CardManaCost.empty : new CardManaCost(new ParserCardnameTxtManaCost(sCost)); + characteristics[curCharacteristics].setManaCost("no cost".equals(sCost) ? CardManaCost.empty : new CardManaCost(new ParserCardnameTxtManaCost(sCost))); } else if (line.startsWith("Types:")) { - cardType = CardType.parse(getValueAfterKey(line, "Types:")); + characteristics[curCharacteristics].setCardType(CardType.parse(getValueAfterKey(line, "Types:"))); } else if (line.startsWith("Oracle:")) { - cardRules = getValueAfterKey(line, "Oracle:").split("\\n"); + characteristics[curCharacteristics].setCardRules(getValueAfterKey(line, "Oracle:").split("\\n")); } else if (line.startsWith("PT:")) { - ptLine = getValueAfterKey(line, "PT:"); + characteristics[curCharacteristics].setPtLine(getValueAfterKey(line, "PT:")); } else if (line.startsWith("Loyalty:")) { - ptLine = getValueAfterKey(line, "Loyalty:"); + characteristics[curCharacteristics].setPtLine(getValueAfterKey(line, "Loyalty:")); } else if (line.startsWith("SVar:RemAIDeck:")) { removedFromAIDecks = "True".equalsIgnoreCase(getValueAfterKey(line, "SVar:RemAIDeck:")); @@ -72,8 +74,16 @@ public class CardRulesReader { removedFromRandomDecks = "True".equalsIgnoreCase(getValueAfterKey(line, "SVar:RemRandomDeck:")); } else if (line.startsWith("SetInfo:")) { - parseSetInfoLine(line, setsData); + parseSetInfoLine(line, characteristics[curCharacteristics].getSetsData()); + + } else if (line.startsWith("AlternateMode:")) { + isDoubleFacedCard = "DoubleFaced".equalsIgnoreCase(getValueAfterKey(line,"AlternateMode:")); + isFlipCard = "Flip".equalsIgnoreCase(getValueAfterKey(line,"AlternateMode:")); + } else if (line.equals("ALTERNATE")) { + characteristics[1] = new CardRuleCharacteristics(); + curCharacteristics = 1; } + } /** diff --git a/src/main/java/forge/card/CardSet.java b/src/main/java/forge/card/CardSet.java index 4d83706a380..2a1f8690605 100644 --- a/src/main/java/forge/card/CardSet.java +++ b/src/main/java/forge/card/CardSet.java @@ -75,21 +75,23 @@ public final class CardSet implements Comparable { // immutable private final int nUncommon; private final int nRare; private final int nSpecial; + private final int nDoubleFaced; private final int nLand; private final int foilRate; private final static int CARDS_PER_BOOSTER = 15; //private final String landCode; - public BoosterData(final int nC, final int nU, final int nR, final int nS) { + public BoosterData(final int nC, final int nU, final int nR, final int nS,final int nDF) { // if this booster has more that 10 cards, there must be a land in 15th slot unless it's already taken - this(nC, nU, nR, nS, nC + nR + nU + nS > 10 ? CARDS_PER_BOOSTER - nC - nR - nU - nS : 0, 68); + this(nC, nU, nR, nS, nDF, nC + nR + nU + nS + nDF > 10 ? CARDS_PER_BOOSTER - nC - nR - nU - nS - nDF : 0, 68); } - public BoosterData(final int nC, final int nU, final int nR, final int nS, final int nL, final int oneFoilPer) { + public BoosterData(final int nC, final int nU, final int nR, final int nS, final int nDF, final int nL, final int oneFoilPer) { nCommon = nC; nUncommon = nU; nRare = nR; nSpecial = nS; + nDoubleFaced = nDF; nLand = nL > 0 ? nL : 0; foilRate = oneFoilPer; } @@ -98,6 +100,7 @@ public final class CardSet implements Comparable { // immutable public int getUncommon() { return nUncommon; } public int getRare() { return nRare; } public int getSpecial() { return nSpecial; } + public int getDoubleFaced() { return nDoubleFaced; } public int getLand() { return nLand; } public int getFoilChance() { return foilRate; } } diff --git a/src/main/java/forge/card/MtgDataParser.java b/src/main/java/forge/card/MtgDataParser.java index fd440e0b03d..5a6591a6d20 100644 --- a/src/main/java/forge/card/MtgDataParser.java +++ b/src/main/java/forge/card/MtgDataParser.java @@ -79,47 +79,74 @@ public final class MtgDataParser implements Iterator { @Override public boolean hasNext() { return weHaveNext; } + private final CardRuleCharacteristics[] chars = new CardRuleCharacteristics[2]; + @Override public CardRules next() { + if(chars[1] != null) { + CardRules ret = new CardRules(chars[1], false, true, false, false); + return ret; + } + chars[0] = new CardRuleCharacteristics(); + Map sets = new HashMap(); + + String nextline = readSingleCard(chars[0]); + if(nextline != null) { + if(nextline.equals("----")) + { + chars[1] = new CardRuleCharacteristics(); + nextline = readSingleCard(chars[1]); + } + if(!nextline.isEmpty()) { + String setsLine = nextline; + boolean isBasicLand = chars[0].getCardType().isLand() && chars[0].getCardType().isBasic(); + chars[0].setSetsData(getValidEditions(setsLine, isBasicLand)); + if(chars[1] != null) { + chars[1].setSetsData(getValidEditions(setsLine, isBasicLand)); + } + } + } + + + // feel free to return null after this line + if (sets.isEmpty()) { return null; } // that was a bad card - it won't be added by invoker + if (chars[0] == null) { return null; } + + return new CardRules(chars[0], false, false, false, false); + } + + private String readSingleCard(CardRuleCharacteristics ret) { + if (!it.hasNext()) { weHaveNext = false; return null; } - String name = it.next(); + ret.setCardName(it.next()); if (!it.hasNext()) { weHaveNext = false; return null; } String manaCost = it.next(); - CardManaCost cost = CardManaCost.empty; + ret.setManaCost(CardManaCost.empty); CardType type = null; if (manaCost.startsWith("{")) { - cost = new CardManaCost(new ManaParserMtgData(manaCost)); + ret.setManaCost(new CardManaCost(new ManaParserMtgData(manaCost))); if (!it.hasNext()) { weHaveNext = false; return null; } type = CardType.parse(it.next()); } else { // Land? type = CardType.parse(manaCost); manaCost = null; } - String ptOrLoyalty = null; + ret.setPtLine(null); if (type.isCreature() || type.isPlaneswalker()) { if (!it.hasNext()) { weHaveNext = false; return null; } - ptOrLoyalty = it.next(); + ret.setPtLine(it.next()); } - - List strs = new ArrayList(); - if (!it.hasNext()) { weHaveNext = false; return null; } - String nextLine = it.next(); - while (StringUtils.isNotBlank(nextLine) && it.hasNext()) { - strs.add(nextLine); - nextLine = it.next(); + + String nextline = it.next(); + ArrayList rules = new ArrayList(); + while(nextline!= null && !nextline.isEmpty() && !nextline.equals("----") && !java.util.regex.Pattern.matches("([A-Z0-9][A-Z0-9][A-Z0-9] [CURM], )*[A-Z0-9][A-Z0-9][A-Z0-9] [CURM]", nextline)) { + rules.add(nextline); } - // feel free to return null after this line - - String setsLine = strs.remove(strs.size() - 1); - boolean isBasicLand = type.isLand() && type.isBasic(); - Map sets = getValidEditions(setsLine, isBasicLand); - - if (sets.isEmpty()) { return null; } // that was a bad card - it won't be added by invoker - - return new CardRules(name, type, cost, ptOrLoyalty, - strs.toArray(ArrayUtils.EMPTY_STRING_ARRAY), sets, false, false); + ret.setCardRules((String[])rules.toArray()); + + return nextline; } private Map getValidEditions(final String sets, final boolean isBasicLand) { diff --git a/src/main/java/forge/card/abilityFactory/AbilityFactory.java b/src/main/java/forge/card/abilityFactory/AbilityFactory.java index a313923cbbc..9bcb7e56ca7 100644 --- a/src/main/java/forge/card/abilityFactory/AbilityFactory.java +++ b/src/main/java/forge/card/abilityFactory/AbilityFactory.java @@ -1079,6 +1079,26 @@ public class AbilityFactory { SA.addCharmChoice(charmAF.getAbility(ab, hostC)); } } + + else if (API.equals("ChangeState")) { + if (isAb) { + SA = AbilityFactory_ChangeState.getChangeStateAbility(this); + } else if (isSp) { + SA = AbilityFactory_ChangeState.getChangeStateSpell(this); + } else if (isDb) { + SA = AbilityFactory_ChangeState.getChangeStateDrawback(this); + } + } + + else if (API.equals("ChangeStateAll")) { + if (isAb) { + SA = AbilityFactory_ChangeState.getChangeStateAllAbility(this); + } else if (isSp) { + SA = AbilityFactory_ChangeState.getChangeStateAllSpell(this); + } else if (isDb) { + SA = AbilityFactory_ChangeState.getChangeStateAllDrawback(this); + } + } if (SA == null) { diff --git a/src/main/java/forge/card/abilityFactory/AbilityFactory_Animate.java b/src/main/java/forge/card/abilityFactory/AbilityFactory_Animate.java index 7f201ef38fb..600ee0a56cb 100644 --- a/src/main/java/forge/card/abilityFactory/AbilityFactory_Animate.java +++ b/src/main/java/forge/card/abilityFactory/AbilityFactory_Animate.java @@ -553,7 +553,6 @@ public final class AbilityFactory_Animate { String actualTrigger = host.getSVar(s); Trigger parsedTrigger = TriggerHandler.parseTrigger(actualTrigger, c, false); addedTriggers.add(c.addTrigger(parsedTrigger)); - AllZone.getTriggerHandler().registerTrigger(parsedTrigger); } } @@ -744,7 +743,6 @@ public final class AbilityFactory_Animate { } for (Trigger t : addedTriggers) { - AllZone.getTriggerHandler().removeRegisteredTrigger(t); c.removeTrigger(t); } @@ -1094,7 +1092,6 @@ public final class AbilityFactory_Animate { String actualTrigger = host.getSVar(s); Trigger parsedTrigger = TriggerHandler.parseTrigger(actualTrigger, c, false); addedTriggers.add(c.addTrigger(parsedTrigger)); - AllZone.getTriggerHandler().registerTrigger(parsedTrigger); } } diff --git a/src/main/java/forge/card/abilityFactory/AbilityFactory_ChangeState.java b/src/main/java/forge/card/abilityFactory/AbilityFactory_ChangeState.java new file mode 100644 index 00000000000..bbdf98ee743 --- /dev/null +++ b/src/main/java/forge/card/abilityFactory/AbilityFactory_ChangeState.java @@ -0,0 +1,318 @@ +package forge.card.abilityFactory; + +import java.util.ArrayList; +import java.util.HashMap; +import java.util.Iterator; +import java.util.Map; + +import forge.AllZone; +import forge.AllZoneUtil; +import forge.Card; +import forge.CardList; +import forge.Player; +import forge.Constant.Zone; +import forge.card.cardFactory.CardFactoryUtil; +import forge.card.spellability.Ability_Activated; +import forge.card.spellability.Ability_Sub; +import forge.card.spellability.Spell; +import forge.card.spellability.SpellAbility; +import forge.card.spellability.Target; + +/** + * AbilityFactory for abilities that cause cards to change states. + * + */ +public class AbilityFactory_ChangeState { + + public static SpellAbility getChangeStateAbility(final AbilityFactory AF) { + SpellAbility ret = new Ability_Activated(AF.getHostCard() ,AF.getAbCost(), AF.getAbTgt()) { + private static final long serialVersionUID = -1083427558368639457L; + + @Override + public String getStackDescription() { + return changeStateStackDescription(AF,this); + } + + @Override + public void resolve() { + changeStateResolve(AF,this); + } + }; + + return ret; + } + + public static SpellAbility getChangeStateSpell(final AbilityFactory AF) { + SpellAbility ret = new Spell(AF.getHostCard()) { + private static final long serialVersionUID = -7506856902233086859L; + + @Override + public String getStackDescription() { + return changeStateStackDescription(AF,this); + } + + @Override + public void resolve() { + changeStateResolve(AF,this); + } + }; + + return ret; + } + + public static SpellAbility getChangeStateDrawback(final AbilityFactory AF) { + Ability_Sub ret = new Ability_Sub(AF.getHostCard(), AF.getAbTgt()) { + + private static final long serialVersionUID = -3793247725721587468L; + + @Override + public String getStackDescription() { + return changeStateStackDescription(AF,this); + } + + @Override + public boolean chkAI_Drawback() { + + //Gross generalization, but this always considers alternate states more powerful + if (AF.getHostCard().isInAlternateState()) { + return false; + } + + return true; + } + + @Override + public boolean doTrigger(boolean mandatory) { + if(!mandatory && AF.getHostCard().isInAlternateState()) { + return false; + } + + return true; + } + + @Override + public void resolve() { + changeStateResolve(AF,this); + } + + }; + + return ret; + } + + private static String changeStateStackDescription(AbilityFactory AF, SpellAbility sa) { + Map params = AF.getMapParams(); + + StringBuilder sb = new StringBuilder(); + Card host = AF.getHostCard(); + + String conditionDesc = params.get("ConditionDescription"); + if (conditionDesc != null) + sb.append(conditionDesc).append(" "); + + ArrayList tgtCards; + + Target tgt = AF.getAbTgt(); + if (tgt != null) + tgtCards = tgt.getTargetCards(); + else { + tgtCards = AbilityFactory.getDefinedCards(sa.getSourceCard(), params.get("Defined"), sa); + } + + if (sa instanceof Ability_Sub) + sb.append(" "); + else + sb.append(host).append(" - "); + + if(params.containsKey("Flip")) { + sb.append("Flip"); + } + else { + sb.append("Transform "); + } + + + Iterator it = tgtCards.iterator(); + while (it.hasNext()) { + Card tgtC = it.next(); + if (tgtC.isFaceDown()) sb.append("Morph ").append("(").append(tgtC.getUniqueNumber()).append(")"); + else sb.append(tgtC); + + if (it.hasNext()) sb.append(", "); + } + sb.append("."); + + Ability_Sub abSub = sa.getSubAbility(); + if (abSub != null) { + sb.append(abSub.getStackDescription()); + } + + return sb.toString(); + } + + private static void changeStateResolve(AbilityFactory AF, SpellAbility sa) { + + ArrayList tgtCards; + + if (AF.getAbTgt() != null) { + tgtCards = AF.getAbTgt().getTargetCards(); + } + else { + tgtCards = AbilityFactory.getDefinedCards(AF.getHostCard(), AF.getMapParams().get("Defined"), sa); + } + + for (Card tgt : tgtCards) { + if(AF.getAbTgt() != null) { + if(!CardFactoryUtil.canTarget(AF.getHostCard(), tgt)) { + continue; + } + } + tgt.changeState(); + } + + } + + //////////////////////////////////////////////// + // changeStateAll // + //////////////////////////////////////////////// + + public static SpellAbility getChangeStateAllAbility(final AbilityFactory AF) { + SpellAbility ret = new Ability_Activated(AF.getHostCard(),AF.getAbCost(),AF.getAbTgt()) { + + private static final long serialVersionUID = 7841029107610111992L; + + @Override + public String getStackDescription() { + return changeStateAllStackDescription(AF,this); + } + + @Override + public void resolve() { + changeStateAllResolve(AF,this); + } + + }; + + return ret; + } + + public static SpellAbility getChangeStateAllSpell(final AbilityFactory AF) { + SpellAbility ret = new Spell(AF.getHostCard()) { + + private static final long serialVersionUID = 4217632586060204603L; + + @Override + public String getStackDescription() { + return changeStateAllStackDescription(AF,this); + } + + @Override + public void resolve() { + changeStateAllResolve(AF,this); + } + }; + + return ret; + } + + public static SpellAbility getChangeStateAllDrawback(final AbilityFactory AF) { + Ability_Sub ret = new Ability_Sub(AF.getHostCard(), AF.getAbTgt()) { + + private static final long serialVersionUID = 4047514893482113436L; + + @Override + public String getStackDescription() { + return changeStateAllStackDescription(AF,this); + } + + @Override + public boolean chkAI_Drawback() { + + //Gross generalization, but this always considers alternate states more powerful + if (AF.getHostCard().isInAlternateState()) { + return false; + } + + return true; + } + + @Override + public boolean doTrigger(boolean mandatory) { + return true; + } + + @Override + public void resolve() { + changeStateAllResolve(AF,this); + } + + }; + + return ret; + } + + private static void changeStateAllResolve(AbilityFactory AF,SpellAbility sa) { + HashMap params = AF.getMapParams(); + + Card card = sa.getSourceCard(); + + Target tgt = AF.getAbTgt(); + Player targetPlayer = null; + if (tgt != null) + targetPlayer = tgt.getTargetPlayers().get(0); + + String Valid = ""; + + if (params.containsKey("ValidCards")) + Valid = params.get("ValidCards"); + + // Ugh. If calculateAmount needs to be called with DestroyAll it _needs_ to use the X variable + // We really need a better solution to this + if (Valid.contains("X")) + Valid = Valid.replace("X", Integer.toString(AbilityFactory.calculateAmount(card, "X", sa))); + + CardList list = AllZoneUtil.getCardsIn(Zone.Battlefield); + + if (targetPlayer != null) { + list = list.getController(targetPlayer); + } + + list = AbilityFactory.filterListByType(list, Valid, sa); + + boolean remChanged = params.containsKey("RememberChanged"); + if (remChanged) + card.clearRemembered(); + + for (int i = 0; i < list.size(); i++) + if (list.get(i).changeState()) + card.addRemembered(list.get(i)); + } + + private static String changeStateAllStackDescription(final AbilityFactory AF, final SpellAbility sa) { + + Card host = AF.getHostCard(); + Map params = AF.getMapParams(); + StringBuilder sb = new StringBuilder(); + + if (sa instanceof Ability_Sub) + sb.append(" "); + else + sb.append(host).append(" - "); + + if(params.containsKey("Flip")) { + sb.append("Flip"); + } + else { + sb.append("Transform "); + } + + sb.append(" permanents."); + + Ability_Sub abSub = sa.getSubAbility(); + if (abSub != null) { + sb.append(abSub.getStackDescription()); + } + + return sb.toString(); + } +} diff --git a/src/main/java/forge/card/abilityFactory/AbilityFactory_Copy.java b/src/main/java/forge/card/abilityFactory/AbilityFactory_Copy.java index f1a1fc22e66..ca3a0c9458e 100644 --- a/src/main/java/forge/card/abilityFactory/AbilityFactory_Copy.java +++ b/src/main/java/forge/card/abilityFactory/AbilityFactory_Copy.java @@ -310,6 +310,12 @@ public final class AbilityFactory_Copy { for (Card c : tgtCards) { if (tgt == null || CardFactoryUtil.canTarget(hostCard, c)) { + boolean wasInAlt = false; + if(c.isInAlternateState()) { + wasInAlt = true; + c.changeState(); + } + //start copied Kiki code int multiplier = AllZoneUtil.getTokenDoublersMagnitude(hostCard.getController()); multiplier *= numCopies; @@ -351,14 +357,26 @@ public final class AbilityFactory_Copy { copy.addIntrinsicKeyword(kw); } - //Slight hack in case we copy a creature with triggers. - for (Trigger t : copy.getTriggers()) { - AllZone.getTriggerHandler().registerTrigger(t); - } - copy.setCurSetCode(c.getCurSetCode()); - copy.setImageFilename(c.getImageFilename()); + if(c.isDoubleFaced()) { //Cloned DFC's can't transform + if(wasInAlt) + { + copy.changeState(); + } + copy.clearOtherState(); + } + if(c.isFlip()) { //Cloned Flips CAN flip. + copy.changeState(); + c.changeState(); + copy.setImageFilename(c.getImageFilename()); + if(!c.isInAlternateState()) { + copy.changeState(); + } + + c.changeState(); + } + if (c.isFaceDown()) { copy.setIsFaceDown(true); copy.setManaCost(""); @@ -398,8 +416,6 @@ public final class AbilityFactory_Copy { AllZone.getGameAction().exile(target[index]); } - //Slight hack in case we copy a creature with triggers - AllZone.getTriggerHandler().removeAllFromCard(target[index]); } } }; diff --git a/src/main/java/forge/card/abilityFactory/AbilityFactory_Effect.java b/src/main/java/forge/card/abilityFactory/AbilityFactory_Effect.java index e877d700f11..1da3fc8838a 100644 --- a/src/main/java/forge/card/abilityFactory/AbilityFactory_Effect.java +++ b/src/main/java/forge/card/abilityFactory/AbilityFactory_Effect.java @@ -270,20 +270,8 @@ public class AbilityFactory_Effect { for (String s : effectTriggers) { String actualTrigger = af.getHostCard().getSVar(s); - //Needs to do some voodoo when the effect disappears to remove the triggers at the same time. - Command LPCommand = new Command() { - - private static final long serialVersionUID = -9007707442828928732L; - - public void execute() { - AllZone.getTriggerHandler().removeAllFromCard(e); - } - - }; - eff.addLeavesPlayCommand(LPCommand); Trigger parsedTrigger = TriggerHandler.parseTrigger(actualTrigger, eff,true); eff.addTrigger(parsedTrigger); - AllZone.getTriggerHandler().registerTrigger(parsedTrigger); } } diff --git a/src/main/java/forge/card/abilityFactory/AbilityFactory_Token.java b/src/main/java/forge/card/abilityFactory/AbilityFactory_Token.java index 7777faaff85..766f742bff0 100644 --- a/src/main/java/forge/card/abilityFactory/AbilityFactory_Token.java +++ b/src/main/java/forge/card/abilityFactory/AbilityFactory_Token.java @@ -438,22 +438,11 @@ public class AbilityFactory_Token extends AbilityFactory { String actualTrigger = AF.getHostCard().getSVar(s); for (final Card c : tokens) { - //Needs to do some voodoo when the token disappears to remove the triggers at the same time. - Command LPCommand = new Command() { - private static final long serialVersionUID = -9007707442828928732L; - - public void execute() { - AllZone.getTriggerHandler().removeAllFromCard(c); - } - - }; - c.addLeavesPlayCommand(LPCommand); Trigger parsedTrigger = TriggerHandler.parseTrigger(actualTrigger, c, true); String ability = AF.getHostCard().getSVar(parsedTrigger.getMapParams().get("Execute")); parsedTrigger.setOverridingAbility(new AbilityFactory().getAbility(ability, c)); c.addTrigger(parsedTrigger); - AllZone.getTriggerHandler().registerTrigger(parsedTrigger); } } } diff --git a/src/main/java/forge/card/cardFactory/AbstractCardFactory.java b/src/main/java/forge/card/cardFactory/AbstractCardFactory.java index 9a2e75cf06a..45593aa4aed 100644 --- a/src/main/java/forge/card/cardFactory/AbstractCardFactory.java +++ b/src/main/java/forge/card/cardFactory/AbstractCardFactory.java @@ -27,6 +27,7 @@ import forge.FileUtil; import forge.GameActionUtil; import forge.Player; import forge.PlayerZone; +import forge.card.CardCharacteristics; import forge.card.abilityFactory.AbilityFactory; import forge.card.cost.Cost; import forge.card.spellability.*; @@ -164,21 +165,24 @@ public abstract class AbstractCardFactory implements NewConstants, CardFactoryIn */ @Override public final Card copyCard(final Card in) { - Card out = getCard(in.getName(), in.getOwner()); out.setUniqueNumber(in.getUniqueNumber()); - out.setSVars(in.getSVars()); - out.setSets(in.getSets()); - out.setCurSetCode(in.getCurSetCode()); - out.setImageFilename(in.getImageFilename()); + CardFactoryUtil.copyCharacteristics(in, out); + if(in.hasAlternateState()) { + in.changeState(); + out.changeState(); + CardFactoryUtil.copyCharacteristics(in, out); + in.changeState(); + out.changeState(); + } + // I'm not sure if we really should be copying enchant/equip stuff over. out.setEquipping(in.getEquipping()); out.setEquippedBy(in.getEquippedBy()); out.setEnchantedBy(in.getEnchantedBy()); out.setEnchanting(in.getEnchanting()); out.setClones(in.getClones()); - out.setCounters(in.getCounters()); for(Object o:in.getRemembered()) { out.addRemembered(o); } @@ -207,9 +211,6 @@ public abstract class AbstractCardFactory implements NewConstants, CardFactoryIn tokens = tokens.filter(CardListFilter.token); all.addAll(tokens); out.setCopiedSpell(true); - for (Trigger t : out.getTriggers()) { - AllZone.getTriggerHandler().registerTrigger(t); - } copiedList.add(out); return out; @@ -407,35 +408,9 @@ public abstract class AbstractCardFactory implements NewConstants, CardFactoryIn return result; } - - /** - *

getCard2.

- * - * @param cardName a {@link java.lang.String} object. - * @param owner a {@link forge.Player} object. - * @return a {@link forge.Card} object. - * @throws RuntimeException if cardName isn't in the Card map - */ - protected Card getCard2(final String cardName, final Player owner) { - //o should be Card object - Object o = map.get(cardName); - if (o == null) { - throw new RuntimeException("CardFactory : getCard() invalid card name - " + cardName); - } - - final Card card = CardFactoryUtil.copyStats(o); - card.setOwner(owner); - card.addColor(card.getManaCost()); - //may have to change the spell - - //this is so permanents like creatures and artifacts have a "default" spell - if (card.isPermanent() && !card.isLand() && !card.isAura()) { - card.addSpellAbility(new Spell_Permanent(card)); - } - - CardFactoryUtil.parseKeywords(card, cardName); - - //************************************************** + + protected void addAbilityFactoryAbilities(Card card) { + //************************************************** // AbilityFactory cards ArrayList ia = card.getIntrinsicAbilities(); if (ia.size() > 0) { @@ -464,6 +439,44 @@ public abstract class AbstractCardFactory implements NewConstants, CardFactoryIn } } + } + + /** + *

getCard2.

+ * + * @param cardName a {@link java.lang.String} object. + * @param owner a {@link forge.Player} object. + * @return a {@link forge.Card} object. + * @throws RuntimeException if cardName isn't in the Card map + */ + protected Card getCard2(final String cardName, final Player owner) { + //o should be Card object + Object o = map.get(cardName); + if (o == null) { + throw new RuntimeException("CardFactory : getCard() invalid card name - " + cardName); + } + + final Card card = CardFactoryUtil.copyStats(o); + card.setOwner(owner); + if(!card.isCardColorsOverridden()) { + card.addColor(card.getManaCost()); + } + //may have to change the spell + + //this is so permanents like creatures and artifacts have a "default" spell + if (card.isPermanent() && !card.isLand() && !card.isAura()) { + card.addSpellAbility(new Spell_Permanent(card)); + } + + CardFactoryUtil.parseKeywords(card, cardName); + + addAbilityFactoryAbilities(card); + if(card.hasAlternateState()) { + card.changeState(); + addAbilityFactoryAbilities(card); + card.changeState(); + } + //register static abilities ArrayList stAbs = card.getStaticAbilityStrings(); @@ -1614,8 +1627,6 @@ public abstract class AbstractCardFactory implements NewConstants, CardFactoryIn private static final long serialVersionUID = 6212378498863558380L; public void execute() { - //Slight hack if the cloner copies a card with triggers - AllZone.getTriggerHandler().removeAllFromCard(cloned[0]); Card orig = cfact.getCard(card.getName(), card.getController()); PlayerZone dest = AllZone.getZoneOf(card.getCurrentlyCloningCard()); @@ -1659,11 +1670,6 @@ public abstract class AbstractCardFactory implements NewConstants, CardFactoryIn cloned[0].addSpellAbility(sa); } - //Slight hack in case the cloner copies a card with triggers - for (Trigger t : cloned[0].getTriggers()) { - AllZone.getTriggerHandler().registerTrigger(t); - } - AllZone.getGameAction().moveToPlay(cloned[0]); card.setCurrentlyCloningCard(cloned[0]); } diff --git a/src/main/java/forge/card/cardFactory/CardFactoryUtil.java b/src/main/java/forge/card/cardFactory/CardFactoryUtil.java index b5cbad403b6..fb7d92ff510 100644 --- a/src/main/java/forge/card/cardFactory/CardFactoryUtil.java +++ b/src/main/java/forge/card/cardFactory/CardFactoryUtil.java @@ -4291,29 +4291,45 @@ public class CardFactoryUtil { public static Card copyStats(final Object o) { Card sim = (Card) o; Card c = new Card(); + + copyCharacteristics(sim,c); + if(sim.hasAlternateState()) { + c.addAlternateState(); + c.changeState(); + sim.changeState(); + copyCharacteristics(sim,c); + c.changeState(); + sim.changeState(); + } - c.setBaseAttack(sim.getBaseAttack()); - c.setBaseDefense(sim.getBaseDefense()); - c.setBaseLoyalty(sim.getBaseLoyalty()); - c.setBaseAttackString(sim.getBaseAttackString()); - c.setBaseDefenseString(sim.getBaseDefenseString()); - c.setIntrinsicKeyword(sim.getKeyword()); - c.setName(sim.getName()); - c.setImageName(sim.getImageName()); - c.setType(sim.getType()); - c.setText(sim.getSpellText()); - c.setManaCost(sim.getManaCost()); - c.setColor(sim.getColor()); - c.setSVars(sim.getSVars()); - c.setSets(sim.getSets()); - c.setIntrinsicAbilities(sim.getIntrinsicAbilities()); + c.setFlip(sim.isFlip()); + c.setDoubleFaced(sim.isDoubleFaced()); c.setCurSetCode(sim.getCurSetCode()); - c.setImageFilename(sim.getImageFilename()); - c.setTriggers(sim.getTriggers()); - c.setStaticAbilityStrings(sim.getStaticAbilityStrings()); - + return c; } // copyStats() + + public static void copyCharacteristics(Card From, Card To) { + To.setBaseAttack(From.getBaseAttack()); + To.setBaseDefense(From.getBaseDefense()); + To.setBaseLoyalty(From.getBaseLoyalty()); + To.setBaseAttackString(From.getBaseAttackString()); + To.setBaseDefenseString(From.getBaseDefenseString()); + To.setIntrinsicKeyword(From.getKeyword()); + To.setName(From.getName()); + To.setType(From.getType()); + To.setText(From.getSpellText()); + To.setManaCost(From.getManaCost()); + To.setColor(From.getColor()); + To.setSVars(From.getSVars()); + To.setSets(From.getSets()); + To.setIntrinsicAbilities(From.getIntrinsicAbilities()); + + To.setImageFilename(From.getImageFilename()); + To.setTriggers(From.getTriggers()); + To.setStaticAbilityStrings(From.getStaticAbilityStrings()); + + } /** *

@@ -4918,7 +4934,6 @@ public class CardFactoryUtil { copyTrigger.setOverridingAbility(origSA); eff.addTrigger(copyTrigger); - AllZone.getTriggerHandler().registerTrigger(copyTrigger); AllZone.getTriggerHandler().suppressMode("ChangesZone"); AllZone.getGameAction().moveToPlay(eff); diff --git a/src/main/java/forge/card/cardFactory/CardFactory_Creatures.java b/src/main/java/forge/card/cardFactory/CardFactory_Creatures.java index 9d3dc990a14..e25247ec0d5 100644 --- a/src/main/java/forge/card/cardFactory/CardFactory_Creatures.java +++ b/src/main/java/forge/card/cardFactory/CardFactory_Creatures.java @@ -2031,8 +2031,6 @@ public class CardFactory_Creatures { private static final long serialVersionUID = 8590474793502538215L; public void execute() { - //Slight hack if the cloner copies a card with triggers - AllZone.getTriggerHandler().removeAllFromCard(cloned[0]); Card orig = cfact.getCard(card.getName(), card.getController()); PlayerZone dest = AllZone.getZoneOf(card.getCurrentlyCloningCard()); @@ -2055,13 +2053,21 @@ public class CardFactory_Creatures { } if (copyTarget[0] != null) { + boolean wasInAlt = copyTarget[0].isInAlternateState(); /* * This cannot just be copyStats with an addSpellAbility loop from copyTarget[0]. * Unless we get a copySpellAbility. Adding the SpellAbility from the * source card causes many weird and Bad Things to happen. */ - try { + try { + if(wasInAlt) { + copyTarget[0].changeState(); + } cloned[0] = cfact.getCard(copyTarget[0].getName(), card.getController()); + if(wasInAlt) { + cloned[0].setImageFilename(copyTarget[0].getImageFilename()); + copyTarget[0].changeState(); + } } catch(RuntimeException re) { //the copyTarget was not found in CardFactory @@ -2075,7 +2081,25 @@ public class CardFactory_Creatures { cloned[0].addLeavesPlayCommand(leaves); cloned[0].setCloneLeavesPlayCommand(leaves); cloned[0].setCurSetCode(copyTarget[0].getCurSetCode()); - cloned[0].setImageFilename(copyTarget[0].getImageFilename()); + + if(copyTarget[0].isDoubleFaced()) { //Cloned DFC's can't transform + if(wasInAlt) + { + cloned[0].changeState(); + } + cloned[0].clearOtherState(); + } + if(copyTarget[0].isFlip()) { //Cloned Flips CAN flip. + cloned[0].changeState(); + copyTarget[0].changeState(); + cloned[0].setImageFilename(copyTarget[0].getImageFilename()); + if(!copyTarget[0].isInAlternateState()) { + cloned[0].changeState(); + } + + copyTarget[0].changeState(); + } + if (cardName.equals("Vesuvan Doppelganger")) { cloned[0].addExtrinsicKeyword("At the beginning of your upkeep, you may have this creature become a copy of target creature except it doesn't copy that creature's color. If you do, this creature gains this ability."); cloned[0].addColor("U", cloned[0], false, true); @@ -2106,12 +2130,6 @@ public class CardFactory_Creatures { cloned[0].setSVar(svarName.toString(), "AB$Sacrifice | Cost$ 0 | Defined$ Self"); } - - //Slight hack in case the cloner copies a card with triggers - for (Trigger t : cloned[0].getTriggers()) { - AllZone.getTriggerHandler().registerTrigger(t); - } - AllZone.getGameAction().moveToPlayFromHand(cloned[0]); card.setCurrentlyCloningCard(cloned[0]); } diff --git a/src/main/java/forge/card/spellability/SpellAbility_Restriction.java b/src/main/java/forge/card/spellability/SpellAbility_Restriction.java index 6111f48fd26..5b60b2a9908 100644 --- a/src/main/java/forge/card/spellability/SpellAbility_Restriction.java +++ b/src/main/java/forge/card/spellability/SpellAbility_Restriction.java @@ -283,7 +283,7 @@ public class SpellAbility_Restriction extends SpellAbility_Variables { return false; } - for (SpellAbility pwAbs : c.getSpellAbility()) { + for (SpellAbility pwAbs : c.getAllSpellAbilities()) { // check all abilities on card that have their planeswalker restriction set to confirm they haven't been activated SpellAbility_Restriction restrict = pwAbs.getRestrictions(); if (restrict.getPlaneswalker() && restrict.getNumberTurnActivations() > 0) { diff --git a/src/main/java/forge/card/staticAbility/StaticAbility_Continuous.java b/src/main/java/forge/card/staticAbility/StaticAbility_Continuous.java index 2df1f1ab3d7..0bcdb191af8 100644 --- a/src/main/java/forge/card/staticAbility/StaticAbility_Continuous.java +++ b/src/main/java/forge/card/staticAbility/StaticAbility_Continuous.java @@ -267,7 +267,6 @@ public class StaticAbility_Continuous { Trigger actualTrigger = TriggerHandler.parseTrigger(trigger, affectedCard, false); actualTrigger.setTemporary(true); affectedCard.addTrigger(actualTrigger); - AllZone.getTriggerHandler().registerTrigger(actualTrigger); } } diff --git a/src/main/java/forge/card/trigger/Trigger.java b/src/main/java/forge/card/trigger/Trigger.java index 6f52286a779..ed86f10aaaa 100644 --- a/src/main/java/forge/card/trigger/Trigger.java +++ b/src/main/java/forge/card/trigger/Trigger.java @@ -4,6 +4,7 @@ import forge.Card; import forge.AllZone; import forge.AllZoneUtil; import forge.CardList; +import forge.CardUtil; import forge.Constant.Zone; import forge.Player; import forge.card.abilityFactory.AbilityFactory; @@ -443,6 +444,20 @@ public abstract class Trigger { return false; } } + + if(mapParams.containsKey("WerewolfTransformCondition")) { + if(CardUtil.getLastTurnCast("Card", hostCard).size() > 0) { + return false; + } + } + + if(mapParams.containsKey("WerewolfUntransformCondition")) { + CardList you = CardUtil.getLastTurnCast("Card.YouCtrl", hostCard); + CardList opp = CardUtil.getLastTurnCast("Card.YouDontCtrl", hostCard); + if(!(you.size() > 1 || opp.size() > 1)) { + return false; + } + } return true; } diff --git a/src/main/java/forge/card/trigger/TriggerHandler.java b/src/main/java/forge/card/trigger/TriggerHandler.java index 839fa595fe9..6d6a22759c9 100644 --- a/src/main/java/forge/card/trigger/TriggerHandler.java +++ b/src/main/java/forge/card/trigger/TriggerHandler.java @@ -4,6 +4,7 @@ import forge.Card; import forge.AllZone; import forge.AllZoneUtil; import forge.Constant.Zone; +import forge.Constant; import forge.Player; import forge.CardList; import forge.Command; @@ -33,12 +34,40 @@ import java.util.Map; */ public class TriggerHandler { - private ArrayList registeredModes = new ArrayList(); - private ArrayList registeredTriggers = new ArrayList(); private ArrayList suppressedModes = new ArrayList(); private ArrayList delayedTriggers = new ArrayList(); + public void cleanUpTemporaryTriggers() { + CardList absolutelyAllCards = new CardList(); + absolutelyAllCards.addAll(AllZone.getHumanPlayer().getAllCards()); + absolutelyAllCards.addAll(AllZone.getComputerPlayer().getAllCards()); + + for(Card c : absolutelyAllCards) { + for(int i=0;i< c.getTriggers().size();i++) { + if(c.getTriggers().get(i).isTemporary()) { + c.getTriggers().remove(i); + i--; + } + } + } + for(Card c : absolutelyAllCards) { + for(int i=0;i< c.getTriggers().size();i++) { + c.getTriggers().get(i).setTemporarilySuppressed(false); + } + } + + } + + /** + *

registerDelayedTrigger.

+ * + * @param trig a {@link forge.card.trigger.Trigger} object. + */ + public final void registerDelayedTrigger(final Trigger trig) { + delayedTriggers.add(trig); + } + /** *

suppressMode.

* @@ -203,95 +232,6 @@ public class TriggerHandler { return mapParams; } - /** - *

registerDelayedTrigger.

- * - * @param trig a {@link forge.card.trigger.Trigger} object. - */ - public final void registerDelayedTrigger(final Trigger trig) { - delayedTriggers.add(trig); - - String mode = trig.getMapParams().get("Mode"); - if (!registeredModes.contains(mode)) { - registeredModes.add(mode); - } - } - - /** - *

registerTrigger.

- * - * @param trig a {@link forge.card.trigger.Trigger} object. - */ - public final void registerTrigger(final Trigger trig) { - registeredTriggers.add(trig); - - String mode = trig.getMapParams().get("Mode"); - if (!registeredModes.contains(mode)) { - registeredModes.add(mode); - } - } - - /** - *

clearRegistered.

- */ - public final void clearRegistered() { - delayedTriggers.clear(); - registeredTriggers.clear(); - registeredModes.clear(); - } - - /** - *

removeRegisteredTrigger.

- * - * @param trig a {@link forge.card.trigger.Trigger} object. - */ - public final void removeRegisteredTrigger(final Trigger trig) { - for (int i = 0; i < registeredTriggers.size(); i++) { - if (registeredTriggers.get(i).equals(trig)) { - registeredTriggers.remove(i); - } - } - } - - /** - *

removeTemporaryTriggers.

- * - */ - public final void cleanUpTemporaryTriggers() { - for (int i = 0; i < registeredTriggers.size(); i++) { - if (registeredTriggers.get(i).isTemporary()) { - registeredTriggers.get(i).hostCard.removeTrigger(registeredTriggers.get(i)); - registeredTriggers.remove(i); - i--; - } - } - for (int i = 0; i < registeredTriggers.size(); i++) { - registeredTriggers.get(i).setTemporarilySuppressed(false); - } - } - - /** - *

Getter for the field registeredTriggers.

- * - * @return a {@link java.util.ArrayList} object. - */ - public final ArrayList getRegisteredTriggers() { - return registeredTriggers; - } - - /** - *

removeAllFromCard.

- * - * @param crd a {@link forge.Card} object. - */ - public final void removeAllFromCard(final Card crd) { - for (int i = 0; i < registeredTriggers.size(); i++) { - if (registeredTriggers.get(i).getHostCard().equals(crd)) { - registeredTriggers.remove(i); - i--; - } - } - } /** *

runTrigger.

@@ -300,20 +240,21 @@ public class TriggerHandler { * @param runParams a {@link java.util.Map} object. */ public final void runTrigger(final String mode, final Map runParams) { - if (suppressedModes.contains(mode) || !registeredModes.contains(mode)) { + if (suppressedModes.contains(mode)) { return; } - + Player playerAP = AllZone.getPhase().getPlayerTurn(); //This is done to allow the list of triggers to be modified while triggers are running. - ArrayList registeredTriggersWorkingCopy = new ArrayList(registeredTriggers); ArrayList delayedTriggersWorkingCopy = new ArrayList(delayedTriggers); - + CardList allCards; + //AP - for (int i = 0; i < registeredTriggersWorkingCopy.size(); i++) { - if (registeredTriggersWorkingCopy.get(i).getHostCard().getController().equals(playerAP)) { - runSingleTrigger(registeredTriggersWorkingCopy.get(i), mode, runParams); + allCards = playerAP.getAllCards(); + for(Card c : allCards) { + for(Trigger t : c.getTriggers()) { + runSingleTrigger(t, mode, runParams); } } for (int i = 0; i < delayedTriggersWorkingCopy.size(); i++) { @@ -328,9 +269,10 @@ public class TriggerHandler { } //NAP - for (int i = 0; i < registeredTriggersWorkingCopy.size(); i++) { - if (registeredTriggersWorkingCopy.get(i).getHostCard().getController().equals(playerAP.getOpponent())) { - runSingleTrigger(registeredTriggersWorkingCopy.get(i), mode, runParams); + allCards = playerAP.getOpponent().getAllCards(); + for(Card c : allCards) { + for(Trigger t : c.getTriggers()) { + runSingleTrigger(t, mode, runParams); } } for (int i = 0; i < delayedTriggersWorkingCopy.size(); i++) { diff --git a/src/main/java/forge/game/limited/BoosterDraft_1.java b/src/main/java/forge/game/limited/BoosterDraft_1.java index 7fa7ff572bf..84330f91ef5 100644 --- a/src/main/java/forge/game/limited/BoosterDraft_1.java +++ b/src/main/java/forge/game/limited/BoosterDraft_1.java @@ -144,9 +144,9 @@ public final class BoosterDraft_1 implements BoosterDraft { Lambda1, BoosterGenerator> fnPick = new Lambda1, BoosterGenerator>() { @Override public List apply(BoosterGenerator pack) { if ( draft.IgnoreRarity ) { - return pack.getBoosterPack(0, 0, 0, 0, 0, 0, draft.NumCards, 0); + return pack.getBoosterPack(0, 0, 0, 0, 0, 0, 0, draft.NumCards, 0); } - return pack.getBoosterPack(draft.NumCommons, draft.NumUncommons, 0, draft.NumRares, draft.NumMythics, draft.NumSpecials, 0, 0); + return pack.getBoosterPack(draft.NumCommons, draft.NumUncommons, 0, draft.NumRares, draft.NumMythics, draft.NumSpecials, 0, 0, 0); } }; diff --git a/src/main/java/forge/game/limited/CustomLimited.java b/src/main/java/forge/game/limited/CustomLimited.java index 7982ef71fee..7269d3791a9 100644 --- a/src/main/java/forge/game/limited/CustomLimited.java +++ b/src/main/java/forge/game/limited/CustomLimited.java @@ -21,6 +21,7 @@ class CustomLimited { public int NumRares = 1; public int NumUncommons = 3; public int NumCommons = 11; + public int NumDoubleFaced = 0; public int NumPacks = 3; public String LandSetCode = AllZone.getCardFactory().getCard("Plains", AllZone.getHumanPlayer()).getMostRecentSet(); @@ -42,6 +43,7 @@ class CustomLimited { if (key.equalsIgnoreCase("LandSetCode")) { cd.LandSetCode = value; } if (key.equalsIgnoreCase("NumCards")) { cd.NumCards = Integer.parseInt(value); } + if (key.equalsIgnoreCase("NumDoubleFaced")) { cd.NumDoubleFaced = Integer.parseInt(value); } if (key.equalsIgnoreCase("NumSpecials")) { cd.NumSpecials = Integer.parseInt(value); } if (key.equalsIgnoreCase("NumMythics")) { cd.NumMythics = Integer.parseInt(value); } if (key.equalsIgnoreCase("NumRares")) { cd.NumRares = Integer.parseInt(value); } diff --git a/src/main/java/forge/game/limited/SealedDeck.java b/src/main/java/forge/game/limited/SealedDeck.java index 8d12a4cc35d..e0bd7371b91 100644 --- a/src/main/java/forge/game/limited/SealedDeck.java +++ b/src/main/java/forge/game/limited/SealedDeck.java @@ -133,9 +133,9 @@ public class SealedDeck { Lambda1, BoosterGenerator> fnPick = new Lambda1, BoosterGenerator>() { @Override public List apply(BoosterGenerator pack) { if ( draft.IgnoreRarity ) { - return pack.getBoosterPack(0, 0, 0, 0, 0, 0, draft.NumCards, 0); + return pack.getBoosterPack(0, 0, 0, 0, 0, 0, 0, draft.NumCards, 0); } - return pack.getBoosterPack(draft.NumCommons, draft.NumUncommons, 0, draft.NumRares, draft.NumMythics, draft.NumSpecials, 0, 0); + return pack.getBoosterPack(draft.NumCommons, draft.NumUncommons, 0, draft.NumRares, draft.NumMythics, draft.NumSpecials, draft.NumDoubleFaced, 0, 0); } }; diff --git a/src/main/java/forge/gui/deckeditor/CardPanelHeavy.java b/src/main/java/forge/gui/deckeditor/CardPanelHeavy.java index 4afda0d5143..6eba002147e 100644 --- a/src/main/java/forge/gui/deckeditor/CardPanelHeavy.java +++ b/src/main/java/forge/gui/deckeditor/CardPanelHeavy.java @@ -15,6 +15,7 @@ import arcane.ui.CardPanel; import arcane.ui.ViewPanel; import forge.Card; +import forge.CardUtil; import forge.GuiDisplayUtil; import forge.ImagePreviewPanel; import forge.Singletons; @@ -33,8 +34,9 @@ public class CardPanelHeavy extends CardPanelBase { private static final long serialVersionUID = -7134546689397508597L; + private JButton changeStateButton = new JButton(); private JButton changePictureButton = new JButton(); - private JButton removePictureButton = new JButton(); + private JButton removePictureButton = new JButton(); // Controls to show card details protected CardDetailPanel detail = new CardDetailPanel(null); @@ -47,6 +49,15 @@ public class CardPanelHeavy extends CardPanelBase { protected static File previousDirectory = null; public CardPanelHeavy() { + changeStateButton.setVisible(false); + changeStateButton.addActionListener(new java.awt.event.ActionListener() { + public void actionPerformed(ActionEvent e) { + changeStateButton_actionPerformed(e); + } + }); + if (!Singletons.getModel().getPreferences().lafFonts) + changeStateButton.setFont(new java.awt.Font("Dialog", 0, 10)); + changePictureButton.setText("Change picture..."); changePictureButton.addActionListener(new java.awt.event.ActionListener() { public void actionPerformed(ActionEvent e) { @@ -69,7 +80,8 @@ public class CardPanelHeavy extends CardPanelBase { this.setLayout(new MigLayout("fill, ins 0")); this.add(detail, "w 239, h 323, grow, flowy, wrap"); - this.add(changePictureButton, "align 50% 0%, split 2, flowx"); + this.add(changeStateButton, "align 50% 0%, split 3, flowx"); + this.add(changePictureButton, "align 50% 0%"); this.add(removePictureButton, "align 50% 0%, wrap"); this.add(pictureViewPanel, "wmin 239, hmin 323, grow"); } @@ -80,7 +92,39 @@ public class CardPanelHeavy extends CardPanelBase { setCard(card2); } public void setCard(Card c) { + if(picture.getCard() != null) { + if(picture.getCard().isInAlternateState()) { + picture.getCard().changeState(); + } + } picture.setCard(c); + + + if(c.hasAlternateState()) { + changeStateButton.setVisible(true); + if(c.isFlip()) { + changeStateButton.setText("Flip"); + } + else { + changeStateButton.setText("Transform"); + } + } + } + + /** + *

+ * changeStateButton_actionPerformed. + *

+ * + * @param e + * a {@link java.awt.event.ActionEvent} object. + */ + void changeStateButton_actionPerformed(ActionEvent e) { + Card cur = picture.getCard(); + cur.changeState(); + + picture.setCard(cur); + detail.setCard(cur); } /** diff --git a/src/main/java/forge/gui/deckeditor/CardPanelLite.java b/src/main/java/forge/gui/deckeditor/CardPanelLite.java index cef8e870fae..aed71b97f16 100644 --- a/src/main/java/forge/gui/deckeditor/CardPanelLite.java +++ b/src/main/java/forge/gui/deckeditor/CardPanelLite.java @@ -1,8 +1,14 @@ package forge.gui.deckeditor; +import java.awt.event.ActionEvent; +import java.awt.event.ActionListener; + +import javax.swing.JButton; + import net.miginfocom.swing.MigLayout; import forge.Card; +import forge.Singletons; import forge.gui.game.CardDetailPanel; import forge.gui.game.CardPicturePanel; import forge.item.CardPrinted; @@ -19,14 +25,25 @@ public class CardPanelLite extends CardPanelBase { // Controls to show card details protected CardDetailPanel detail = new CardDetailPanel(null); private CardPicturePanel picture = new CardPicturePanel(null); + private JButton bChangeState = new JButton(); /** * * Constructor. */ public CardPanelLite() { + bChangeState.setVisible(false); + bChangeState.addActionListener(new ActionListener() { + public void actionPerformed(ActionEvent e) { + bChangeState_actionPerformed(e); + } + }); + if (!Singletons.getModel().getPreferences().lafFonts) + bChangeState.setFont(new java.awt.Font("Dialog", 0, 10)); + this.setLayout(new MigLayout("fill, ins 0")); - this.add(detail, "w 239, h 323, grow, flowy, wrap"); + this.add(detail, "w 239, h 303, grow, flowy, wrap"); + this.add(bChangeState, "align 50% 0%, wrap"); this.add(picture, "wmin 239, hmin 323, grow"); } @@ -41,8 +58,35 @@ public class CardPanelLite extends CardPanelBase { picture.setCard(card); boolean isCard = card != null && card instanceof CardPrinted; detail.setVisible(isCard); - if (isCard) { - detail.setCard(((CardPrinted) card).toForgeCard()); + if (isCard) { + Card toSet = ((CardPrinted) card).toForgeCard(); + + detail.setCard(toSet); + if(toSet.hasAlternateState()) { + bChangeState.setVisible(true); + if(toSet.isFlip()) { + bChangeState.setText("Flip"); + } + else { + bChangeState.setText("Transform"); + } + } + } + } + + public void setCard(Card c) { + picture.setCard(c); + if(c != null) { + detail.setCard(c); + if(c.hasAlternateState()) { + bChangeState.setVisible(true); + if(c.isFlip()) { + bChangeState.setText("Flip"); + } + else { + bChangeState.setText("Transform"); + } + } } } @@ -55,5 +99,14 @@ public class CardPanelLite extends CardPanelBase { public final Card getCard() { return detail.getCard(); } + + private void bChangeState_actionPerformed(ActionEvent e) { + Card cur = detail.getCard(); + if(cur != null) { + cur.changeState(); + + setCard(cur); + } + } } diff --git a/src/main/java/forge/gui/deckeditor/DeckEditorCommon.java b/src/main/java/forge/gui/deckeditor/DeckEditorCommon.java index d8b81e4b088..613fdf651cb 100644 --- a/src/main/java/forge/gui/deckeditor/DeckEditorCommon.java +++ b/src/main/java/forge/gui/deckeditor/DeckEditorCommon.java @@ -223,7 +223,7 @@ public final class DeckEditorCommon extends DeckEditorBase { @Override protected Predicate buildFilter() { - Predicate cardFilter = Predicate.and(filterBoxes.buildFilter(), filterNameTypeSet.buildFilter()); + Predicate cardFilter = Predicate.and(Predicate.and(filterBoxes.buildFilter(), filterNameTypeSet.buildFilter()),CardPrinted.Predicates.Presets.nonAlternate); return Predicate.instanceOf(cardFilter, CardPrinted.class); } diff --git a/src/main/java/forge/item/CardDb.java b/src/main/java/forge/item/CardDb.java index 488d2e440de..e629182ebc2 100644 --- a/src/main/java/forge/item/CardDb.java +++ b/src/main/java/forge/item/CardDb.java @@ -81,25 +81,32 @@ public final class CardDb { // 2. Save refs into two lists: one flat and other keyed with sets & name CardPrinted lastAdded = null; for (Entry s : card.getSetsPrinted()) { - String set = s.getKey(); - - // get this set storage, if not found, create it! - Map setMap = allCardsBySet.get(set); - if (null == setMap) { - setMap = new Hashtable(); - allCardsBySet.put(set, setMap); - } - - int count = s.getValue().getCopiesCount(); - CardPrinted[] cardCopies = new CardPrinted[count]; - setMap.put(cardName, cardCopies); - for (int i = 0; i < count; i++) { - lastAdded = CardPrinted.build(card, set, s.getValue().getRarity(), i); - allCardsFlat.add(lastAdded); - cardCopies[i] = lastAdded; - } + lastAdded = addToLists(card, cardName,s); } - uniqueCards.put(cardName, lastAdded); + uniqueCards.put(cardName, lastAdded); + } + + public CardPrinted addToLists(final CardRules card, final String cardName, final Entry s) { + CardPrinted lastAdded = null; + String set = s.getKey(); + + // get this set storage, if not found, create it! + Map setMap = allCardsBySet.get(set); + if (null == setMap) { + setMap = new Hashtable(); + allCardsBySet.put(set, setMap); + } + + int count = s.getValue().getCopiesCount(); + CardPrinted[] cardCopies = new CardPrinted[count]; + setMap.put(cardName, cardCopies); + for (int i = 0; i < count; i++) { + lastAdded = CardPrinted.build(card, set, s.getValue().getRarity(), i, card.isAltState(),card.isDoubleFaced()); + allCardsFlat.add(lastAdded); + cardCopies[i] = lastAdded; + } + + return lastAdded; } public boolean isCardSupported(final String cardName) { diff --git a/src/main/java/forge/item/CardPrinted.java b/src/main/java/forge/item/CardPrinted.java index 1c97f01ef43..aafe7ff58f8 100644 --- a/src/main/java/forge/item/CardPrinted.java +++ b/src/main/java/forge/item/CardPrinted.java @@ -29,6 +29,8 @@ public final class CardPrinted implements Comparable, InventoryItem private final String cardSet; private final int artIndex; private final boolean foiled; + private final boolean isAlternate; + private final boolean isDoubleFaced; // Calculated fields are below: private final transient CardRarity rarity; // rarity is given in ctor when set is assigned @@ -59,7 +61,7 @@ public final class CardPrinted implements Comparable, InventoryItem // Constructor is private. All non-foiled instances are stored in CardDb private CardPrinted(final CardRules c, final String set, final CardRarity rare, - final int index, final boolean foil) + final int index, final boolean foil, final boolean isAlt, final boolean isDF) { card = c; name = c.getName(); @@ -67,17 +69,19 @@ public final class CardPrinted implements Comparable, InventoryItem artIndex = index; foiled = foil; rarity = rare; + isAlternate = isAlt; + isDoubleFaced = isDF; nameLcase = name.toLowerCase(); } /* package visibility */ - static CardPrinted build(final CardRules c, final String set, final CardRarity rare, final int index) { - return new CardPrinted(c, set, rare, index, false); + static CardPrinted build(final CardRules c, final String set, final CardRarity rare, final int index, final boolean isAlt, final boolean isDF) { + return new CardPrinted(c, set, rare, index, false, isAlt, isDF); } /* foiled don't need to stay in CardDb's structures, so u'r free to create */ public static CardPrinted makeFoiled(final CardPrinted c) { - return new CardPrinted(c.card, c.cardSet, c.rarity, c.artIndex, true); + return new CardPrinted(c.card, c.cardSet, c.rarity, c.artIndex, true, c.isAlternate, c.isDoubleFaced); } // Want this class to be a key for HashTable @@ -115,6 +119,11 @@ public final class CardPrinted implements Comparable, InventoryItem c.setCurSetCode(getSet()); c.setRandomPicture(artIndex+1); c.setImageFilename(getImageFilename()); + if(c.hasAlternateState()) { + c.changeState(); + c.setImageFilename(CardUtil.buildFilename(c)); + c.changeState(); + } } // else throw "Unsupported card"; return c; @@ -127,6 +136,14 @@ public final class CardPrinted implements Comparable, InventoryItem // TODO: compare sets properly return cardSet.compareTo(o.cardSet); } + + public boolean isAlternate() { + return isAlternate; + } + + public boolean isDoubleFaced() { + return isDoubleFaced; + } /** * Number of filters based on CardPrinted values. @@ -158,6 +175,13 @@ public final class CardPrinted implements Comparable, InventoryItem public static Predicate namesExcept(final List what) { return new PredicateNamesExcept(what); } + + private static class PredicateNotAlternate extends Predicate { + @Override + public boolean isTrue(final CardPrinted card) { + return !card.isAlternate; + } + } private static class PredicateRarity extends Predicate { private final CardRarity operand; @@ -233,6 +257,8 @@ public final class CardPrinted implements Comparable, InventoryItem public static final Predicate exceptLands = rarity(false, CardRarity.BasicLand); public static final Predicate isTrue = Predicate.getTrue(CardPrinted.class); + + public static final Predicate nonAlternate = new PredicateNotAlternate(); } } } diff --git a/src/main/java/forge/item/CardPrintedCharacteristics.java b/src/main/java/forge/item/CardPrintedCharacteristics.java new file mode 100644 index 00000000000..3850edb777c --- /dev/null +++ b/src/main/java/forge/item/CardPrintedCharacteristics.java @@ -0,0 +1,34 @@ +package forge.item; + +/** + * TODO: Write javadoc for this type. + * + */ +public class CardPrintedCharacteristics { + private String name; + private String cardSet; + /** + * @return the name + */ + public String getName() { + return name; + } + /** + * @param name0 the name to set + */ + public void setName(String name0) { + this.name = name0; // TODO: Add 0 to parameter's name. + } + /** + * @return the cardSet + */ + public String getCardSet() { + return cardSet; + } + /** + * @param cardSet0 the cardSet to set + */ + public void setCardSet(String cardSet0) { + this.cardSet = cardSet0; // TODO: Add 0 to parameter's name. + } +} diff --git a/src/main/java/forge/model/FGameState.java b/src/main/java/forge/model/FGameState.java index ff17acb5c9c..4e20e46c4ff 100644 --- a/src/main/java/forge/model/FGameState.java +++ b/src/main/java/forge/model/FGameState.java @@ -296,7 +296,6 @@ public class FGameState { } getStaticEffects().reset(); - getTriggerHandler().clearRegistered(); } } diff --git a/src/main/java/forge/quest/data/QuestUtilCards.java b/src/main/java/forge/quest/data/QuestUtilCards.java index 3057bc14222..a56a2581462 100644 --- a/src/main/java/forge/quest/data/QuestUtilCards.java +++ b/src/main/java/forge/quest/data/QuestUtilCards.java @@ -167,7 +167,7 @@ public final class QuestUtilCards { q.shopList.clear(); for (int i = 0; i < totalPacks; i++) { - q.shopList.addAllCards(pack.getBoosterPack(7, 3, 1, 0, 0, 0, 0, 0)); + q.shopList.addAllCards(pack.getBoosterPack(7, 3, 1, 0, 0, 0, 0, 0, 0)); // add some boosters int rollD100 = MyRandom.random.nextInt(100);