- Added the player keyword "At the beginning of the end step, you lose the game.".

- Added Final Fortune, Last Chance and Warrior's Oath.
This commit is contained in:
Sloth
2012-04-30 15:37:33 +00:00
parent 3823552b14
commit 559b62d10a
8 changed files with 182 additions and 16 deletions

4
.gitattributes vendored
View File

@@ -3095,6 +3095,7 @@ res/cardsfolder/f/filigree_sages.txt svneol=native#text/plain
res/cardsfolder/f/fill_with_fright.txt svneol=native#text/plain res/cardsfolder/f/fill_with_fright.txt svneol=native#text/plain
res/cardsfolder/f/filth.txt svneol=native#text/plain res/cardsfolder/f/filth.txt svneol=native#text/plain
res/cardsfolder/f/filthy_cur.txt svneol=native#text/plain res/cardsfolder/f/filthy_cur.txt svneol=native#text/plain
res/cardsfolder/f/final_fortune.txt -text
res/cardsfolder/f/final_judgment.txt svneol=native#text/plain res/cardsfolder/f/final_judgment.txt svneol=native#text/plain
res/cardsfolder/f/final_revels.txt svneol=native#text/plain res/cardsfolder/f/final_revels.txt svneol=native#text/plain
res/cardsfolder/f/final_sting_faerie.txt svneol=native#text/plain res/cardsfolder/f/final_sting_faerie.txt svneol=native#text/plain
@@ -5096,6 +5097,7 @@ res/cardsfolder/l/lashknife_barrier.txt svneol=native#text/plain
res/cardsfolder/l/lashwrithe.txt svneol=native#text/plain res/cardsfolder/l/lashwrithe.txt svneol=native#text/plain
res/cardsfolder/l/last_breath.txt svneol=native#text/plain res/cardsfolder/l/last_breath.txt svneol=native#text/plain
res/cardsfolder/l/last_caress.txt svneol=native#text/plain res/cardsfolder/l/last_caress.txt svneol=native#text/plain
res/cardsfolder/l/last_chance.txt -text
res/cardsfolder/l/last_gasp.txt svneol=native#text/plain res/cardsfolder/l/last_gasp.txt svneol=native#text/plain
res/cardsfolder/l/last_kiss.txt svneol=native#text/plain res/cardsfolder/l/last_kiss.txt svneol=native#text/plain
res/cardsfolder/l/last_laugh.txt svneol=native#text/plain res/cardsfolder/l/last_laugh.txt svneol=native#text/plain
@@ -10376,6 +10378,7 @@ res/cardsfolder/w/warren_scourge_elf.txt svneol=native#text/plain
res/cardsfolder/w/warrior_angel.txt svneol=native#text/plain res/cardsfolder/w/warrior_angel.txt svneol=native#text/plain
res/cardsfolder/w/warriors_charge.txt svneol=native#text/plain res/cardsfolder/w/warriors_charge.txt svneol=native#text/plain
res/cardsfolder/w/warriors_honor.txt svneol=native#text/plain res/cardsfolder/w/warriors_honor.txt svneol=native#text/plain
res/cardsfolder/w/warriors_oath.txt -text
res/cardsfolder/w/warriors_stand.txt -text res/cardsfolder/w/warriors_stand.txt -text
res/cardsfolder/w/warstorm_surge.txt svneol=native#text/plain res/cardsfolder/w/warstorm_surge.txt svneol=native#text/plain
res/cardsfolder/w/warthog.txt svneol=native#text/plain res/cardsfolder/w/warthog.txt svneol=native#text/plain
@@ -11845,6 +11848,7 @@ src/main/java/forge/game/phase/Combat.java svneol=native#text/plain
src/main/java/forge/game/phase/CombatUtil.java svneol=native#text/plain src/main/java/forge/game/phase/CombatUtil.java svneol=native#text/plain
src/main/java/forge/game/phase/EndOfCombat.java svneol=native#text/plain src/main/java/forge/game/phase/EndOfCombat.java svneol=native#text/plain
src/main/java/forge/game/phase/EndOfTurn.java svneol=native#text/plain src/main/java/forge/game/phase/EndOfTurn.java svneol=native#text/plain
src/main/java/forge/game/phase/ExtraTurn.java -text
src/main/java/forge/game/phase/Phase.java svneol=native#text/plain src/main/java/forge/game/phase/Phase.java svneol=native#text/plain
src/main/java/forge/game/phase/PhaseHandler.java -text src/main/java/forge/game/phase/PhaseHandler.java -text
src/main/java/forge/game/phase/PhaseType.java -text src/main/java/forge/game/phase/PhaseType.java -text

View File

@@ -0,0 +1,13 @@
Name:Final Fortune
ManaCost:R R
Types:Instant
Text:no text
A:SP$ AddTurn | Cost$ R R | NumTurns$ 1 | loseAtEndStep$ True | SpellDescription$ Take an extra turn after this one. At the beginning of that turn's end step, you lose the game.
SVar:RemAIDeck:True
SVar:Rarity:Rare
SVar:Picture:http://www.wizards.com/global/images/magic/general/final_fortune.jpg
SetInfo:6ED|Rare|http://magiccards.info/scans/en/6e/175.jpg
SetInfo:MIR|Rare|http://magiccards.info/scans/en/mr/173.jpg
SetInfo:7ED|Rare|http://magiccards.info/scans/en/7e/182.jpg
Oracle:Take an extra turn after this one. At the beginning of that turn's end step, you lose the game.
End

View File

@@ -0,0 +1,12 @@
Name:Last Chance
ManaCost:R R
Types:Sorcery
Text:no text
A:SP$ AddTurn | Cost$ R R | NumTurns$ 1 | loseAtEndStep$ True | SpellDescription$ Take an extra turn after this one. At the beginning of that turn's end step, you lose the game.
SVar:RemAIDeck:True
SVar:Rarity:Rare
SVar:Picture:http://www.wizards.com/global/images/magic/general/last_chance.jpg
SetInfo:S99|Rare|http://magiccards.info/scans/en/st/110.jpg
SetInfo:POR|Rare|http://magiccards.info/scans/en/po/141.jpg
Oracle:Take an extra turn after this one. At the beginning of that turn's end step, you lose the game.
End

View File

@@ -0,0 +1,11 @@
Name:Warrior's Oath
ManaCost:R R
Types:Sorcery
Text:no text
A:SP$ AddTurn | Cost$ R R | NumTurns$ 1 | loseAtEndStep$ True | SpellDescription$ Take an extra turn after this one. At the beginning of that turn's end step, you lose the game.
SVar:RemAIDeck:True
SVar:Rarity:Rare
SVar:Picture:http://www.wizards.com/global/images/magic/general/warriors_oath.jpg
SetInfo:PTK|Rare|http://magiccards.info/scans/en/p3k/124.jpg
Oracle:Take an extra turn after this one. At the beginning of that turn's end step, you lose the game.
End

View File

@@ -28,6 +28,7 @@ import forge.card.spellability.AbilitySub;
import forge.card.spellability.Spell; import forge.card.spellability.Spell;
import forge.card.spellability.SpellAbility; import forge.card.spellability.SpellAbility;
import forge.card.spellability.Target; import forge.card.spellability.Target;
import forge.game.phase.ExtraTurn;
import forge.game.phase.PhaseType; import forge.game.phase.PhaseType;
import forge.game.player.ComputerUtil; import forge.game.player.ComputerUtil;
import forge.game.player.Player; import forge.game.player.Player;
@@ -319,7 +320,10 @@ public class AbilityFactoryTurns {
for (final Player p : tgtPlayers) { for (final Player p : tgtPlayers) {
if ((tgt == null) || p.canBeTargetedBy(sa)) { if ((tgt == null) || p.canBeTargetedBy(sa)) {
for (int i = 0; i < numTurns; i++) { for (int i = 0; i < numTurns; i++) {
Singletons.getModel().getGameState().getPhaseHandler().addExtraTurn(p); ExtraTurn extra = Singletons.getModel().getGameState().getPhaseHandler().addExtraTurn(p);
if (params.containsKey("loseAtEndStep")) {
extra.setLoseAtEndStep(true);
}
} }
} }
} }

View File

@@ -27,6 +27,7 @@ import forge.Counters;
import forge.Singletons; import forge.Singletons;
import forge.card.spellability.Ability; import forge.card.spellability.Ability;
import forge.card.spellability.SpellAbility; import forge.card.spellability.SpellAbility;
import forge.game.GameLossReason;
import forge.game.player.Player; import forge.game.player.Player;
import forge.game.zone.ZoneType; import forge.game.zone.ZoneType;
import forge.gui.GuiUtils; import forge.gui.GuiUtils;
@@ -53,7 +54,6 @@ public class EndOfTurn extends Phase implements java.io.Serializable {
// TODO - should this freeze the Stack? // TODO - should this freeze the Stack?
// Pyrohemia and Pestilence
final CardList all = AllZoneUtil.getCardsIn(ZoneType.Battlefield); final CardList all = AllZoneUtil.getCardsIn(ZoneType.Battlefield);
EndOfTurn.endOfTurnWallOfReverence(); EndOfTurn.endOfTurnWallOfReverence();
@@ -209,6 +209,21 @@ public class EndOfTurn extends Phase implements java.io.Serializable {
} }
} }
Player activePlayer = Singletons.getModel().getGameState().getPhaseHandler().getPlayerTurn();
if (activePlayer.hasKeyword("At the beginning of the end step, you lose the game.")) {
final Card source = new Card();
final SpellAbility change = new Ability(source, "0") {
@Override
public void resolve() {
this.getActivatingPlayer().loseConditionMet(GameLossReason.SpellEffect, "");
}
};
change.setStackDescription("At the beginning of the end step, you lose the game.");
change.setDescription("At the beginning of the end step, you lose the game.");
change.setActivatingPlayer(activePlayer);
AllZone.getStack().addSimultaneousStackEntry(change);
}
this.execute(this.getAt()); this.execute(this.getAt());

View File

@@ -0,0 +1,86 @@
/*
* Forge: Play Magic: the Gathering.
* Copyright (C) 2011 Forge Team
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
package forge.game.phase;
import forge.game.player.Player;
/**
* <p>
* ExtraTurn class.
* Stores informations about extra turns
* </p>
*
* @author Forge
* @version $Id: ExtraTurn 12482 2011-12-06 11:14:11Z Sloth $
*/
public class ExtraTurn {
private Player player = null;
private boolean loseAtEndStep = false;
private boolean skipUntap = false;
/**
* TODO: Write javadoc for Constructor.
* @param player
*/
public ExtraTurn(Player player) {
this.player = player;
}
/**
* @return the player
*/
public Player getPlayer() {
return player;
}
/**
* @param player the player to set
*/
public void setPlayer(Player player) {
this.player = player;
}
/**
* @return the loseAtEndStep
*/
public boolean isLoseAtEndStep() {
return loseAtEndStep;
}
/**
* @param loseAtEndStep the loseAtEndStep to set
*/
public void setLoseAtEndStep(boolean loseAtEndStep) {
this.loseAtEndStep = loseAtEndStep;
}
/**
* @return the skipUntap
*/
public boolean isSkipUntap() {
return skipUntap;
}
/**
* @param skipUntap the skipUntap to set
*/
public void setSkipUntap(boolean skipUntap) {
this.skipUntap = skipUntap;
}
} //end class Untap

View File

@@ -32,12 +32,8 @@ import forge.GameActionUtil;
import forge.MyObservable; import forge.MyObservable;
import forge.Singletons; import forge.Singletons;
import forge.card.trigger.TriggerType; import forge.card.trigger.TriggerType;
import forge.control.input.Input;
import forge.control.input.InputControl;
import forge.game.player.Player; import forge.game.player.Player;
import forge.game.zone.ZoneType; import forge.game.zone.ZoneType;
import forge.gui.framework.EDocID;
import forge.gui.framework.SDisplayUtil;
import forge.properties.ForgePreferences.FPref; import forge.properties.ForgePreferences.FPref;
/** /**
@@ -61,7 +57,7 @@ public class PhaseHandler extends MyObservable implements java.io.Serializable {
/** Constant <code>GameBegins=0</code>. */ /** Constant <code>GameBegins=0</code>. */
private static int gameBegins = 0; private static int gameBegins = 0;
private final Stack<Player> extraTurns = new Stack<Player>(); private final Stack<ExtraTurn> extraTurns = new Stack<ExtraTurn>();
private int extraCombats; private int extraCombats;
@@ -608,7 +604,6 @@ public class PhaseHandler extends MyObservable implements java.io.Serializable {
* @return a {@link forge.game.player.Player} object. * @return a {@link forge.game.player.Player} object.
*/ */
private Player handleNextTurn() { private Player handleNextTurn() {
final Player nextTurn = this.extraTurns.isEmpty() ? this.getPlayerTurn().getOpponent() : this.extraTurns.pop();
AllZone.getStack().setCardsCastLastTurn(); AllZone.getStack().setCardsCastLastTurn();
AllZone.getStack().clearCardsCastThisTurn(); AllZone.getStack().clearCardsCastThisTurn();
@@ -618,7 +613,33 @@ public class PhaseHandler extends MyObservable implements java.io.Serializable {
AllZone.getComputerPlayer().setLifeLostThisTurn(0); AllZone.getComputerPlayer().setLifeLostThisTurn(0);
AllZone.getHumanPlayer().setLifeLostThisTurn(0); AllZone.getHumanPlayer().setLifeLostThisTurn(0);
return this.skipTurnTimeVault(nextTurn); return getNextActivePlayer();
}
/**
* <p>
* getNextActivePlayer.
* </p>
*
* @return a {@link forge.game.player.Player} object.
*/
private Player getNextActivePlayer() {
Player nextTurn = this.getPlayerTurn().getOpponent();
if (!this.extraTurns.isEmpty()) {
ExtraTurn extraTurn = this.extraTurns.pop();
nextTurn = extraTurn.getPlayer();
if (skipTurnTimeVault(nextTurn)) {
return getNextActivePlayer();
}
if (extraTurn.isLoseAtEndStep()) {
nextTurn.addKeyword("At the beginning of the end step, you lose the game.");
}
return nextTurn;
}
if (skipTurnTimeVault(nextTurn)) {
return getNextActivePlayer();
}
return nextTurn;
} }
/** /**
@@ -630,7 +651,7 @@ public class PhaseHandler extends MyObservable implements java.io.Serializable {
* a {@link forge.game.player.Player} object. * a {@link forge.game.player.Player} object.
* @return a {@link forge.game.player.Player} object. * @return a {@link forge.game.player.Player} object.
*/ */
private Player skipTurnTimeVault(Player turn) { private boolean skipTurnTimeVault(Player turn) {
// time vault: // time vault:
CardList vaults = turn.getCardsIn(ZoneType.Battlefield, "Time Vault"); CardList vaults = turn.getCardsIn(ZoneType.Battlefield, "Time Vault");
vaults = vaults.filter(new CardListFilter() { vaults = vaults.filter(new CardListFilter() {
@@ -646,13 +667,13 @@ public class PhaseHandler extends MyObservable implements java.io.Serializable {
if (turn.isHuman()) { if (turn.isHuman()) {
if (GameActionUtil.showYesNoDialog(crd, "Untap " + crd + "?")) { if (GameActionUtil.showYesNoDialog(crd, "Untap " + crd + "?")) {
crd.untap(); crd.untap();
turn = this.extraTurns.isEmpty() ? turn.getOpponent() : this.extraTurns.pop(); return true;
} }
} else { } else {
// TODO Should AI skip his turn for time vault? // TODO Should AI skip his turn for time vault?
} }
} }
return turn; return false;
} }
/** /**
@@ -717,7 +738,7 @@ public class PhaseHandler extends MyObservable implements java.io.Serializable {
return this.getPlayerTurn().getOpponent(); return this.getPlayerTurn().getOpponent();
} }
return this.extraTurns.peek(); return this.extraTurns.peek().getPlayer();
} }
/** /**
@@ -742,14 +763,14 @@ public class PhaseHandler extends MyObservable implements java.io.Serializable {
* @param player * @param player
* a {@link forge.game.player.Player} object. * a {@link forge.game.player.Player} object.
*/ */
public final void addExtraTurn(final Player player) { public final ExtraTurn addExtraTurn(final Player player) {
// use a stack to handle extra turns, make sure the bottom of the stack // use a stack to handle extra turns, make sure the bottom of the stack
// restores original turn order // restores original turn order
if (this.extraTurns.isEmpty()) { if (this.extraTurns.isEmpty()) {
this.extraTurns.push(this.getPlayerTurn().getOpponent()); this.extraTurns.push(new ExtraTurn(this.getPlayerTurn().getOpponent()));
} }
this.extraTurns.push(player); return this.extraTurns.push(new ExtraTurn(player));
} }
/** /**