- *
- * Will eventually be marked deprecated.
- *
- * @return a {@link forge.game.player.Player} object.
- * @since 1.0.15
- */
- @Deprecated
- public static Player getHumanPlayer() {
- if (Singletons.getModel() == null)
- return null;
-
- return Aggregates.firstFieldEquals(Singletons.getModel().getGameState().getPlayers(), Player.Accessors.FN_GET_TYPE, PlayerType.HUMAN);
- }
-
- /**
- *
- * getComputerPlayer.
- *
- *
- * Will eventually be marked deprecated.
- *
- * @return a {@link forge.game.player.Player} object.
- * @since 1.0.15
- */
- @Deprecated
- public static Player getComputerPlayer() {
- List players = Singletons.getModel().getGameState().getPlayers();
- return Aggregates.firstFieldEquals(players, Player.Accessors.FN_GET_TYPE, PlayerType.COMPUTER);
- }
-
/**
*
* getGauntletData.
diff --git a/src/main/java/forge/AllZoneUtil.java b/src/main/java/forge/AllZoneUtil.java
index 11894862138..d1b5e56785d 100644
--- a/src/main/java/forge/AllZoneUtil.java
+++ b/src/main/java/forge/AllZoneUtil.java
@@ -21,6 +21,7 @@ import java.util.ArrayList;
import java.util.List;
import com.google.common.base.Predicate;
+import com.google.common.collect.Iterables;
import forge.CardPredicates.Presets;
import forge.game.player.Player;
@@ -47,33 +48,24 @@ public abstract class AllZoneUtil {
* @return a List with all cards currently in a graveyard
*/
public static List getCardsIn(final ZoneType zone) {
- final List cards = new ArrayList();
- getCardsIn(zone, cards);
- return cards;
- }
-
- private static void getCardsIn(final ZoneType zone, final List cards) {
if (zone == ZoneType.Stack) {
- cards.addAll(AllZone.getStackZone().getCards());
+ return AllZone.getStackZone().getCards();
} else {
+ List cards = null;
for (final Player p : Singletons.getModel().getGameState().getPlayers()) {
- cards.addAll(p.getZone(zone).getCards());
+ if ( cards == null )
+ cards = p.getZone(zone).getCards();
+ else
+ cards.addAll(p.getZone(zone).getCards());
}
+ return cards;
}
}
public static List getCardsIn(final Iterable zones) {
final List cards = new ArrayList();
for (final ZoneType z : zones) {
- getCardsIn(z, cards);
- }
- return cards;
- }
-
- public static List getCardsIn(final ZoneType[] zones) {
- final List cards = new ArrayList();
- for (final ZoneType z : zones) {
- getCardsIn(z, cards);
+ cards.addAll(getCardsIn(z));
}
return cards;
}
@@ -182,10 +174,9 @@ public abstract class AllZoneUtil {
* @return true is the card is in play, false otherwise
*/
public static boolean isCardInPlay(final String cardName) {
- for (Card card : AllZoneUtil.getCardsIn(ZoneType.Battlefield)) {
- if (card.getName().equals(cardName)) {
+ for (final Player p : Singletons.getModel().getGameState().getPlayers()) {
+ if (isCardInPlay(cardName, p))
return true;
- }
}
return false;
}
@@ -200,12 +191,7 @@ public abstract class AllZoneUtil {
* @return true if that player has that card in play, false otherwise
*/
public static boolean isCardInPlay(final String cardName, final Player player) {
- for (Card card : player.getCardsIn(ZoneType.Battlefield)) {
- if (card.getName().equals(cardName)) {
- return true;
- }
- }
- return false;
+ return Iterables.any(player.getZone(ZoneType.Battlefield), CardPredicates.nameEquals(cardName));
}
// ////////////// getting all cards of a given color
diff --git a/src/main/java/forge/GameAction.java b/src/main/java/forge/GameAction.java
index ab7b9a9f931..99008d8acbc 100644
--- a/src/main/java/forge/GameAction.java
+++ b/src/main/java/forge/GameAction.java
@@ -26,6 +26,7 @@ import java.util.List;
import javax.swing.JFrame;
import com.google.common.base.Predicate;
+import com.google.common.collect.Iterables;
import forge.card.abilityfactory.AbilityFactory;
import forge.card.abilityfactory.AbilityFactoryAttach;
@@ -51,8 +52,8 @@ import forge.card.trigger.TriggerType;
import forge.control.input.InputPayManaCost;
import forge.control.input.InputPayManaCostUtil;
import forge.game.GameEndReason;
-import forge.game.GameSummary;
-import forge.game.phase.PhaseHandler;
+import forge.game.GameLossReason;
+import forge.game.GameState;
import forge.game.player.ComputerUtil;
import forge.game.player.Player;
import forge.game.zone.PlayerZone;
@@ -896,54 +897,43 @@ public class GameAction {
*
* @return a boolean.
*/
- public final boolean checkEndGameState() {
+ public final boolean checkEndGameState(final GameState game) {
// if game is already over return true
- if (Singletons.getModel().getGameState().isGameOver()) {
+ if (game.isGameOver()) {
return true;
}
- // Win / Lose
- final GameSummary game = Singletons.getModel().getGameSummary();
- boolean humanWins = false;
- boolean computerWins = false;
- final Player computer = AllZone.getComputerPlayer();
- final Player human = AllZone.getHumanPlayer();
- // Winning Conditions can be worth more than losing conditions
- if (human.hasWon() || computer.hasLost()) {
- humanWins = true;
-
- if (human.getAltWin()) {
- game.end(GameEndReason.WinsGameSpellEffect, human.getName(), human.getWinConditionSource());
- } else {
- game.end(GameEndReason.AllOpponentsLost, human.getName(), null);
- }
+ GameEndReason reason = null;
+ // award loses as SBE
+ for (Player p : game.getPlayers() ) {
+ p.checkLoseCondition(); // this will set appropriate outcomes
}
-
- if (computer.hasWon() || human.hasLost()) {
- if (humanWins) {
- // both players won/lost at the same time.
- game.end(GameEndReason.Draw, null, null);
- } else {
- computerWins = true;
-
- if (computer.getAltWin()) {
- game.end(GameEndReason.WinsGameSpellEffect, computer.getName(), computer.getWinConditionSource());
- } else {
- game.end(GameEndReason.AllOpponentsLost, computer.getName(), null);
+
+ // Has anyone won by spelleffect?
+ for (Player p : game.getPlayers() ) {
+ if( p.hasWon() ) { // then the rest have lost!
+ reason = GameEndReason.WinsGameSpellEffect;
+ for (Player pl : game.getPlayers() ) {
+ if( !pl.equals(p) )
+ if ( !pl.loseConditionMet(GameLossReason.OpponentWon, p.getOutcome().altWinSourceName) )
+ reason = null; // they cannot lose!
}
-
+ break;
}
}
-
- final boolean isGameDone = humanWins || computerWins;
- if (isGameDone) {
- Singletons.getModel().getGameState().setGameOver(true);
- game.getPlayerRating(computer.getName()).setLossReason(computer.getLossState(), computer.getLossConditionSource());
- game.getPlayerRating(human.getName()).setLossReason(human.getLossState(), human.getLossConditionSource());
- Singletons.getModel().getMatchState().addGamePlayed(game);
+
+ // still unclear why this has not caught me conceding
+ if ( reason == null && Iterables.size(Iterables.filter(game.getPlayers(), Player.Predicates.NOT_LOST)) == 1 )
+ {
+ reason = GameEndReason.AllOpponentsLost;
+ }
+
+ if (reason != null) {
+ game.setGameOver();
+ Singletons.getModel().getMatch().addGamePlayed(reason, game);
}
- return isGameDone;
+ return reason != null;
}
/** */
@@ -1015,7 +1005,7 @@ public class GameAction {
return;
}
- if (this.checkEndGameState()) {
+ if (this.checkEndGameState(Singletons.getModel().getGameState())) {
// Clear Simultaneous triggers at the end of the game
new ViewWinLose();
Singletons.getModel().getGameState().getStack().clearSimultaneousStack();
@@ -1031,9 +1021,6 @@ public class GameAction {
boolean checkAgain = false;
- AllZone.getHumanPlayer().setMaxHandSize(7);
- AllZone.getComputerPlayer().setMaxHandSize(7);
-
this.checkStaticAbilities();
final HashMap runParams = new HashMap();
@@ -1693,7 +1680,7 @@ public class GameAction {
originalCard.setXManaCostPaid(0);
}
- if (PhaseHandler.getGameBegins() != 1 || sa.isTrigger()) {
+ if (Singletons.getModel().getGameState() != null || sa.isTrigger()) {
return manaCost;
}
diff --git a/src/main/java/forge/card/cardfactory/CardFactory.java b/src/main/java/forge/card/cardfactory/CardFactory.java
index 86e946ddb89..d1ceae20863 100644
--- a/src/main/java/forge/card/cardfactory/CardFactory.java
+++ b/src/main/java/forge/card/cardfactory/CardFactory.java
@@ -29,7 +29,6 @@ import forge.CardUtil;
import forge.Singletons;
import forge.card.CardRules;
import forge.card.cost.Cost;
-import forge.card.mana.ManaCost;
import forge.card.spellability.Spell;
import forge.card.spellability.SpellAbility;
import forge.card.spellability.SpellPermanent;
diff --git a/src/main/java/forge/card/mana/ManaPool.java b/src/main/java/forge/card/mana/ManaPool.java
index eabf5788d1c..b12e03c4cfe 100644
--- a/src/main/java/forge/card/mana/ManaPool.java
+++ b/src/main/java/forge/card/mana/ManaPool.java
@@ -64,7 +64,6 @@ public class ManaPool {
*/
public ManaPool(final Player player) {
owner = player;
- owner.updateObservers();
clearPool();
ManaPool.MAP.put(Constant.Color.WHITE, 0);
ManaPool.MAP.put(Constant.Color.BLUE, 1);
diff --git a/src/main/java/forge/control/FControl.java b/src/main/java/forge/control/FControl.java
index 38350768f71..aa76bdce84c 100644
--- a/src/main/java/forge/control/FControl.java
+++ b/src/main/java/forge/control/FControl.java
@@ -35,6 +35,7 @@ import forge.AllZone;
import forge.Singletons;
import forge.control.KeyboardShortcuts.Shortcut;
import forge.game.player.Player;
+import forge.game.player.PlayerType;
import forge.gui.deckeditor.CDeckEditorUI;
import forge.gui.deckeditor.VDeckEditorUI;
import forge.gui.framework.SOverflowUtil;
@@ -49,6 +50,7 @@ import forge.properties.ForgeProps;
import forge.properties.NewConstants;
import forge.quest.data.QuestPreferences.QPref;
import forge.quest.io.QuestDataIO;
+import forge.util.Aggregates;
import forge.view.FView;
/**
@@ -273,6 +275,20 @@ public enum FControl {
/** @return {@link forge.game.player.Player} */
public Player getPlayer() {
- return AllZone.getHumanPlayer();
+ if (Singletons.getModel() == null)
+ return null;
+
+ return Aggregates.firstFieldEquals(Singletons.getModel().getGameState().getPlayers(), Player.Accessors.FN_GET_TYPE, PlayerType.HUMAN);
+ }
+
+ /**
+ * TODO: Write javadoc for this method.
+ * @return
+ */
+ private Lobby lobby = null;
+ public Lobby getLobby() {
+ if( lobby == null )
+ lobby = new Lobby();
+ return lobby;
}
}
diff --git a/src/main/java/forge/control/Lobby.java b/src/main/java/forge/control/Lobby.java
new file mode 100644
index 00000000000..62047d4f9c3
--- /dev/null
+++ b/src/main/java/forge/control/Lobby.java
@@ -0,0 +1,102 @@
+package forge.control;
+
+import java.util.Random;
+
+import forge.game.player.LobbyPlayer;
+import forge.game.player.PlayerType;
+import forge.util.MyRandom;
+
+/**
+ * TODO: Write javadoc for this type.
+ *
+ */
+public class Lobby {
+
+
+ private final String[] opponentNames = new String[] {
+ "Abigail", "Ada", "Adeline", "Adriana", "Agatha", "Agnes", "Aileen", "Alba", "Alcyon",
+ "Alethea", "Alice", "Alicia", "Alison", "Amanda", "Amelia", "Amy", "Andrea", "Angelina",
+ "Anita", "Ann", "Annabel", "Anne", "Audrey", "Barbara", "Belinda", "Bernice", "Bertha",
+ "Bonnie", "Brenda", "Bridget", "Bunny", "Carmen", "Carol", "Catherine", "Cheryl",
+ "Christine", "Cinderalla", "Claire", "Clarice", "Claudia", "Constance", "Cora",
+ "Corinne", "Cnythia", "Daisy", "Daphne", "Dawn", "Deborah", "Diana", "Dolly", "Dora",
+ "Doreen", "Doris", "Dorothy", "Eileen", "Elaine", "Elizabeth", "Emily", "Emma", "Ethel",
+ "Evelyn", "Fiona", "Florence", "Frances", "Geraldine", "Gertrude", "Gladys", "Gloria",
+ "Grace", "Greta", "Harriet", "Hazel", "Helen", "Hilda", "Ida", "Ingrid", "Irene",
+ "Isabel", "Jacinta", "Jackie", "Jane", "Janet", "Janice", "Jennifer", "Jessie", "Joan",
+ "Jocelyn", "Josephine", "Joyce", "Judith", "Julia", "Juliana", "Karina", "Kathleen",
+ "Laura", "Lilian", "Lily", "Linda", "Lisa", "Lilita", "Lora", "Lorna", "Lucy", "Lydia",
+ "Mabel", "Madeline", "Maggie", "Maria", "Mariam", "Marilyn", "Mary", "Matilda", "Mavis",
+ "Melanie", "Melinda", "Melody", "Michelle", "Mildred", "Molly", "Mona", "Monica",
+ "Nancy", "Nora", "Norma", "Olga", "Pamela", "Patricia", "Paula", "Pauline", "Pearl",
+ "Peggy", "Penny", "Phoebe", "Phyllis", "Polly", "Priscilla", "Rachel", "Rebecca",
+ "Rita", "Rosa", "Rosalind", "Rose", "Rosemary", "Rowena", "Ruby", "Sally", "Samantha",
+ "Sarah", "Selina", "Sharon", "Sheila", "Shirley", "Sonya", "Stella", "Sue", "Susan",
+ "Sylvia", "Tina", "Tracy", "Ursula", "Valentine", "Valerie", "Vanessa", "Veronica",
+ "Victoria", "Violet", "Vivian", "Wendy", "Winnie", "Yvonne", "Aaron", "Abraham", "Adam",
+ "Adrain", "Alain", "Alan", "Alban", "Albert", "Alec", "Alexander", "Alfonso", "Alfred",
+ "Allan", "Allen", "Alonso", "Aloysius", "Alphonso", "Alvin", "Andrew", "Andy", "Amadeus",
+ "Amselm", "Anthony", "Arnold", "Augusta", "Austin", "Barnaby", "Benedict", "Benjamin",
+ "Bertie", "Bertram", "Bill", "Bob", "Boris", "Brady", "Brian", "Bruce", "Burt", "Byron",
+ "Calvin", "Carl", "Carter", "Casey", "Cecil", "Charles", "Christian", "Christopher",
+ "Clarence", "Clement", "Colin", "Conan", "Dalton", "Damian", "Daniel", "David", "Denis",
+ "Derek", "Desmond", "Dick", "Dominic", "Donald", "Douglas", "Duncan", "Edmund",
+ "Edward", "Ellen", "Elton", "Elvis", "Eric", "Eugene", "Felix", "Francis", "Frank",
+ "Frederick", "Gary", "Geoffrey", "George", "Gerald", "Gerry", "Gordon", "Hamish",
+ "Hardy", "Harold", "Harry", "Henry", "Herbert", "Ignatius", "Jack", "James", "Jeffrey",
+ "Jim", "Joe", "John", "Joseph", "Karl", "Keith", "Kenneth", "Kevin", "Larry", "Lawrence",
+ "Leonard", "Lionel", "Louis", "Lucas", "Malcolm", "Mark", "Martin", "Mathew", "Maurice",
+ "Max", "Melvin", "Michael", "Milton", "Morgan", "Morris", "Murphy", "Neville",
+ "Nicholas", "Noel", "Norman", "Oliver", "Oscar", "Patrick", "Paul", "Perkin", "Peter",
+ "Philip", "Ralph", "Randy", "Raymond", "Richard", "Ricky", "Robert", "Robin", "Rodney",
+ "Roger", "Roland", "Ronald", "Roy", "Sam", "Sebastian", "Simon", "Stanley", "Stephen",
+ "Stuart", "Terence", "Thomas", "Tim", "Tom", "Tony", "Victor", "Vincent", "Wallace",
+ "Walter", "Wilfred", "William", "Winston"
+ };
+
+ /**
+ * TODO: Write javadoc for this method.
+ * @param human
+ * @return
+ */
+ public LobbyPlayer findLocalPlayer(PlayerType type, String name) {
+
+
+ return new LobbyPlayer(type, name);
+ }
+
+ /**
+ * TODO: Write javadoc for this method.
+ * @param human
+ * @return
+ */
+ public LobbyPlayer findLocalPlayer(PlayerType type) {
+ if ( type == PlayerType.HUMAN )
+ return new LobbyPlayer(type, "Human"); // need to get name!
+
+
+ return findLocalPlayer(type, getRandomName());
+ }
+
+ /**
+ * TODO: Write javadoc for this method.
+ * @param nextInt
+ * @return
+ */
+ private String getRandomName() {
+ Random my = MyRandom.getRandom();
+ return opponentNames[my.nextInt(opponentNames.length)];
+
+ }
+
+ /**
+ * TODO: Write javadoc for this method.
+ * @return
+ */
+ public LobbyPlayer getQuestPlayer() {
+ return new LobbyPlayer(PlayerType.HUMAN, "Human"); // need to get name!
+ }
+
+
+
+}
diff --git a/src/main/java/forge/control/input/InputControl.java b/src/main/java/forge/control/input/InputControl.java
index 11dfc092d4e..b2c3130ccfb 100644
--- a/src/main/java/forge/control/input/InputControl.java
+++ b/src/main/java/forge/control/input/InputControl.java
@@ -21,6 +21,7 @@ import java.util.LinkedList;
import java.util.Stack;
import forge.AllZone;
+import forge.Singletons;
import forge.game.phase.PhaseHandler;
import forge.game.phase.PhaseType;
import forge.game.player.ComputerAIInput;
@@ -198,7 +199,7 @@ public class InputControl extends MyObservable implements java.io.Serializable {
return this.input;
}
- if ((PhaseHandler.getGameBegins() != 0) && handler.doPhaseEffects()) {
+ if (Singletons.getModel().getGameState() != null && handler.doPhaseEffects()) {
// Handle begin phase stuff, then start back from the top
handler.handleBeginPhase();
return this.updateInput();
@@ -215,7 +216,7 @@ public class InputControl extends MyObservable implements java.io.Serializable {
this.model.getGameState().getStack().freezeStack();
if (playerTurn.isHuman() && !handler.getAutoPass()) {
- AllZone.getCombat().initiatePossibleDefenders(AllZone.getComputerPlayer());
+ AllZone.getCombat().initiatePossibleDefenders(playerTurn.getOpponent());
return new InputAttack();
}
} else if (phase == PhaseType.COMBAT_DECLARE_BLOCKERS) {
diff --git a/src/main/java/forge/control/input/InputMulligan.java b/src/main/java/forge/control/input/InputMulligan.java
index a93500275e7..10f38d83230 100644
--- a/src/main/java/forge/control/input/InputMulligan.java
+++ b/src/main/java/forge/control/input/InputMulligan.java
@@ -30,8 +30,6 @@ import forge.GameActionUtil;
import forge.Singletons;
import forge.card.abilityfactory.AbilityFactory;
import forge.card.spellability.SpellAbility;
-import forge.game.GamePlayerRating;
-import forge.game.phase.PhaseHandler;
import forge.game.phase.PhaseUtil;
import forge.game.player.ComputerUtil;
import forge.game.player.Player;
@@ -41,8 +39,6 @@ import forge.gui.framework.SDisplayUtil;
import forge.gui.match.CMatchUI;
import forge.gui.match.VMatchUI;
import forge.gui.match.views.VMessage;
-import forge.quest.QuestController;
-import forge.quest.bazaar.QuestItemType;
import forge.view.ButtonUtil;
/**
*
@@ -56,7 +52,6 @@ public class InputMulligan extends Input {
/** Constant serialVersionUID=-8112954303001155622L. */
private static final long serialVersionUID = -8112954303001155622L;
- private static final int MAGIC_NUMBER_OF_SHUFFLES = 100;
private static final int AI_MULLIGAN_THRESHOLD = 5;
/** {@inheritDoc} */
@@ -67,7 +62,7 @@ public class InputMulligan extends Input {
VMatchUI.SINGLETON_INSTANCE.getBtnCancel().setText("Yes");
final String str =
- (Singletons.getModel().getGameState().getPhaseHandler().getPlayerTurn().equals(AllZone.getHumanPlayer())
+ (Singletons.getModel().getGameState().getPhaseHandler().getPlayerTurn().equals(Singletons.getControl().getPlayer())
? "You're going first. " : "The computer is going first. ");
CMatchUI.SINGLETON_INSTANCE.showMessage(str + "Do you want to Mulligan?");
}
@@ -78,82 +73,48 @@ public class InputMulligan extends Input {
this.end();
}
- /**
- *
- * TODO Write javadoc for this method.
- *
- * @param player
- * a Player object
- * @param playerRating
- * a GamePlayerRating object
- * @return an int
- */
- public final int doMulligan(final Player player, final GamePlayerRating playerRating) {
- final List hand = player.getCardsIn(ZoneType.Hand);
- for (final Card c : hand) {
- Singletons.getModel().getGameAction().moveToLibrary(c);
- }
- for (int i = 0; i < InputMulligan.MAGIC_NUMBER_OF_SHUFFLES; i++) {
- player.shuffle();
- }
- final int newHand = hand.size() - 1;
- for (int i = 0; i < newHand; i++) {
- player.drawCard();
- }
- AllZone.getGameLog().add("Mulligan", player + " has mulliganed down to " + newHand + " cards.", 0);
- playerRating.notifyHasMulliganed();
- playerRating.notifyOpeningHandSize(newHand);
- return newHand;
- }
+
/** {@inheritDoc} */
@Override
public final void selectButtonCancel() {
- final Player humanPlayer = AllZone.getHumanPlayer();
- final GamePlayerRating humanRating = Singletons.getModel().getGameSummary().getPlayerRating(humanPlayer.getName());
+ final Player humanPlayer = Singletons.getControl().getPlayer();
+
- final int newHand = this.doMulligan(humanPlayer, humanRating);
-
- final QuestController quest = Singletons.getModel().getQuest();
- if (quest.isLoaded() && quest.getAssets().hasItem(QuestItemType.SLEIGHT) && (humanRating.getMulliganCount() == 1)) {
- AllZone.getHumanPlayer().drawCard();
- humanRating.notifyOpeningHandSize(newHand + 1);
- }
+ final int newHand = humanPlayer.doMulligan();
if (newHand == 0) {
this.end();
}
} // selectButtonOK()
- /**
- *
- * end.
- *
- */
final void end() {
// Computer mulligan
- final GameAction ga = Singletons.getModel().getGameAction();
- final Player aiPlayer = AllZone.getComputerPlayer();
- final GamePlayerRating aiRating = Singletons.getModel().getGameSummary().getPlayerRating(aiPlayer.getName());
- boolean aiTakesMulligan = true;
- // Computer mulligans if there are no cards with converted mana cost of
- // 0 in its hand
- while (aiTakesMulligan) {
-
- final List handList = aiPlayer.getCardsIn(ZoneType.Hand);
- final boolean hasLittleCmc0Cards = CardLists.getValidCards(handList, "Card.cmcEQ0", aiPlayer, null).size() < 2;
- aiTakesMulligan = (handList.size() > InputMulligan.AI_MULLIGAN_THRESHOLD) && hasLittleCmc0Cards;
-
- if (aiTakesMulligan) {
- this.doMulligan(aiPlayer, aiRating);
+ for (Player ai : Singletons.getModel().getGameState().getPlayers()) {
+ if ( ai.isHuman() ) continue;
+
+ boolean aiTakesMulligan = true;
+
+ // Computer mulligans if there are no cards with converted mana cost of
+ // 0 in its hand
+ while (aiTakesMulligan) {
+
+ final List handList = ai.getCardsIn(ZoneType.Hand);
+ final boolean hasLittleCmc0Cards = CardLists.getValidCards(handList, "Card.cmcEQ0", ai, null).size() < 2;
+ aiTakesMulligan = (handList.size() > InputMulligan.AI_MULLIGAN_THRESHOLD) && hasLittleCmc0Cards;
+
+ if (aiTakesMulligan) {
+ ai.doMulligan();
+ }
}
}
// Human Leylines & Chancellors
ButtonUtil.reset();
final AbilityFactory af = new AbilityFactory();
-
+
+ final GameAction ga = Singletons.getModel().getGameAction();
for (Player p : Singletons.getModel().getGameState().getPlayers()) {
final List openingHand = p.getCardsIn(ZoneType.Hand);
@@ -210,7 +171,7 @@ public class InputMulligan extends Input {
//ga.checkStateEffects();
ga.checkStateEffects();
- PhaseHandler.setGameBegins(1);
+
AllZone.getGameLog().add("Turn",
"Turn " + Singletons.getModel().getGameState().getPhaseHandler().getTurn()
+ " (" + Singletons.getModel().getGameState().getPhaseHandler().getPlayerTurn() + ")",
diff --git a/src/main/java/forge/control/input/InputPassPriority.java b/src/main/java/forge/control/input/InputPassPriority.java
index 1a77be36114..a024aad2937 100644
--- a/src/main/java/forge/control/input/InputPassPriority.java
+++ b/src/main/java/forge/control/input/InputPassPriority.java
@@ -86,7 +86,7 @@ public class InputPassPriority extends Input implements java.io.Serializable {
@Override
public final void selectCard(final Card card, final PlayerZone zone) {
if (Singletons.getModel().getGameAction().playCard(card)) {
- Singletons.getModel().getGameState().getPhaseHandler().setPriority(AllZone.getHumanPlayer());
+ Singletons.getModel().getGameState().getPhaseHandler().setPriority(Singletons.getControl().getPlayer());
}
else {
SDisplayUtil.remind(VMessage.SINGLETON_INSTANCE);
diff --git a/src/main/java/forge/control/input/InputPayManaCost.java b/src/main/java/forge/control/input/InputPayManaCost.java
index 74dbbdcc7c3..6970a12cc10 100644
--- a/src/main/java/forge/control/input/InputPayManaCost.java
+++ b/src/main/java/forge/control/input/InputPayManaCost.java
@@ -23,7 +23,6 @@ import forge.Singletons;
import forge.card.mana.ManaCost;
import forge.card.spellability.SpellAbility;
import forge.card.trigger.TriggerType;
-import forge.game.phase.PhaseHandler;
import forge.game.player.Player;
import forge.game.zone.PlayerZone;
import forge.game.zone.ZoneType;
@@ -76,7 +75,7 @@ public class InputPayManaCost extends InputMana {
this.spell = sa;
- if (PhaseHandler.getGameBegins() == 1) {
+ if (Singletons.getModel().getGameState() != null) {
if (sa.getSourceCard().isCopiedSpell() && sa.isSpell()) {
if (this.spell.getAfterPayMana() != null) {
this.stopSetNext(this.spell.getAfterPayMana());
@@ -121,7 +120,7 @@ public class InputPayManaCost extends InputMana {
this.spell = sa;
- if (PhaseHandler.getGameBegins() == 1) {
+ if (Singletons.getModel().getGameState() != null ) {
if (sa.getSourceCard().isCopiedSpell() && sa.isSpell()) {
if (this.spell.getAfterPayMana() != null) {
this.stopSetNext(this.spell.getAfterPayMana());
@@ -266,8 +265,9 @@ public class InputPayManaCost extends InputMana {
}
this.resetManaCost();
- AllZone.getHumanPlayer().getManaPool().refundManaPaid(this.spell, true);
- AllZone.getHumanPlayer().getZone(ZoneType.Battlefield).updateObservers(); // DO
+ Player human = Singletons.getControl().getPlayer();
+ human.getManaPool().refundManaPaid(this.spell, true);
+ human.getZone(ZoneType.Battlefield).updateObservers(); // DO
this.stop();
}
diff --git a/src/main/java/forge/control/input/InputPayManaCostAbility.java b/src/main/java/forge/control/input/InputPayManaCostAbility.java
index 346458d9607..a2cb17d2dd8 100644
--- a/src/main/java/forge/control/input/InputPayManaCostAbility.java
+++ b/src/main/java/forge/control/input/InputPayManaCostAbility.java
@@ -17,7 +17,6 @@
*/
package forge.control.input;
-import forge.AllZone;
import forge.Card;
import forge.Command;
import forge.Singletons;
@@ -202,7 +201,7 @@ public class InputPayManaCostAbility extends InputMana {
public final void selectButtonCancel() {
this.unpaidCommand.execute();
this.resetManaCost();
- AllZone.getHumanPlayer().getManaPool().refundManaPaid(this.fakeAbility, true);
+ Singletons.getControl().getPlayer().getManaPool().refundManaPaid(this.fakeAbility, true);
this.stop();
}
diff --git a/src/main/java/forge/control/input/InputPayManaCostUtil.java b/src/main/java/forge/control/input/InputPayManaCostUtil.java
index 51137649c4e..676a429d04c 100644
--- a/src/main/java/forge/control/input/InputPayManaCostUtil.java
+++ b/src/main/java/forge/control/input/InputPayManaCostUtil.java
@@ -37,7 +37,6 @@ import forge.card.mana.ManaPool;
import forge.card.spellability.AbilityMana;
import forge.card.spellability.SpellAbility;
import forge.card.trigger.TriggerType;
-import forge.game.phase.PhaseHandler;
import forge.game.player.Player;
import forge.game.zone.PlayerZone;
import forge.game.zone.ZoneType;
@@ -418,7 +417,7 @@ public class InputPayManaCostUtil {
public void selectButtonCancel() {
this.stop();
payment.cancelCost();
- AllZone.getHumanPlayer().getZone(ZoneType.Battlefield).updateObservers();
+ Singletons.getControl().getPlayer().getZone(ZoneType.Battlefield).updateObservers();
}
@Override
@@ -470,7 +469,7 @@ public class InputPayManaCostUtil {
final int manaToAdd) {
final ManaCost manaCost;
- if (PhaseHandler.getGameBegins() == 1) {
+ if (Singletons.getModel().getGameState() != null ) {
final String mana = costMana.getManaToPay();
manaCost = new ManaCost(mana);
manaCost.increaseColorlessMana(manaToAdd);
@@ -574,7 +573,7 @@ public class InputPayManaCostUtil {
this.stop();
this.resetManaCost();
payment.cancelCost();
- AllZone.getHumanPlayer().getZone(ZoneType.Battlefield).updateObservers();
+ Singletons.getControl().getPlayer().getZone(ZoneType.Battlefield).updateObservers();
}
@Override
diff --git a/src/main/java/forge/control/input/InputPayReturnCost.java b/src/main/java/forge/control/input/InputPayReturnCost.java
index 749855c6e3f..215733e685d 100644
--- a/src/main/java/forge/control/input/InputPayReturnCost.java
+++ b/src/main/java/forge/control/input/InputPayReturnCost.java
@@ -19,7 +19,6 @@ package forge.control.input;
import java.util.List;
-import forge.AllZone;
import forge.Card;
import forge.CardLists;
@@ -77,7 +76,7 @@ public class InputPayReturnCost extends Input {
this.ability = sa;
this.returnCost = cost;
- this.choiceList = CardLists.getValidCards(AllZone.getHumanPlayer().getCardsIn(ZoneType.Battlefield), cost.getType().split(";"), AllZone.getHumanPlayer(), source);
+ this.choiceList = CardLists.getValidCards(Singletons.getControl().getPlayer().getCardsIn(ZoneType.Battlefield), cost.getType().split(";"), Singletons.getControl().getPlayer(), source);
String amountString = cost.getAmount();
this.numRequired = amountString.matches("[0-9][0-9]?") ? Integer.parseInt(amountString)
: CardFactoryUtil.xCount(source, source.getSVar(amountString));
diff --git a/src/main/java/forge/control/input/InputPaySacCost.java b/src/main/java/forge/control/input/InputPaySacCost.java
index 3f3c00d157e..06a9661d6e7 100644
--- a/src/main/java/forge/control/input/InputPaySacCost.java
+++ b/src/main/java/forge/control/input/InputPaySacCost.java
@@ -19,7 +19,6 @@ package forge.control.input;
import java.util.List;
-import forge.AllZone;
import forge.Card;
import forge.CardLists;
@@ -28,6 +27,7 @@ import forge.Singletons;
import forge.card.cardfactory.CardFactoryUtil;
import forge.card.cost.CostSacrifice;
import forge.card.spellability.SpellAbility;
+import forge.game.player.Player;
import forge.game.zone.PlayerZone;
import forge.game.zone.ZoneType;
import forge.gui.match.CMatchUI;
@@ -77,7 +77,8 @@ public class InputPaySacCost extends Input {
this.ability = sa;
this.sacCost = cost;
- this.choiceList = CardLists.getValidCards(AllZone.getHumanPlayer().getCardsIn(ZoneType.Battlefield), cost.getType().split(";"), AllZone.getHumanPlayer(), source);
+ Player human = Singletons.getControl().getPlayer();
+ this.choiceList = CardLists.getValidCards(human.getCardsIn(ZoneType.Battlefield), cost.getType().split(";"), human, source);
String amountString = cost.getAmount();
this.numRequired = amountString.matches("[0-9][0-9]?") ? Integer.parseInt(amountString)
: CardFactoryUtil.xCount(source, source.getSVar(amountString));
diff --git a/src/main/java/forge/game/GameLossReason.java b/src/main/java/forge/game/GameLossReason.java
index d2f675f0fcd..43a123b1b03 100644
--- a/src/main/java/forge/game/GameLossReason.java
+++ b/src/main/java/forge/game/GameLossReason.java
@@ -21,10 +21,6 @@ package forge.game;
* The Enum GameLossReason.
*/
public enum GameLossReason {
-
- /** The Did not lose yet. */
- DidNotLoseYet, // a winner must have this status by the end of the game
-
/** The Conceded. */
Conceded, // rule 104.3a
/** The Life reached zero. */
@@ -36,7 +32,9 @@ public enum GameLossReason {
// 104.3e and others
/** The Spell effect. */
- SpellEffect
+ SpellEffect,
+
+ OpponentWon
/*
* DoorToNothingness, // Door To Nothingness's ability activated
diff --git a/src/main/java/forge/game/GameNew.java b/src/main/java/forge/game/GameNew.java
index c3b6f3c806d..22a06232758 100644
--- a/src/main/java/forge/game/GameNew.java
+++ b/src/main/java/forge/game/GameNew.java
@@ -19,21 +19,12 @@ import forge.Card;
import forge.CardLists;
import forge.CardPredicates;
import forge.CardUtil;
-import forge.Constant.Preferences;
import forge.Singletons;
-import forge.control.FControl;
-import forge.control.input.InputMulligan;
+import forge.deck.Deck;
import forge.game.player.Player;
import forge.game.zone.PlayerZone;
import forge.game.zone.ZoneType;
-import forge.gui.framework.EDocID;
-import forge.gui.framework.SDisplayUtil;
-import forge.gui.match.CMatchUI;
-import forge.gui.match.VMatchUI;
-import forge.gui.match.controllers.CMessage;
-import forge.gui.match.nonsingleton.VField;
import forge.gui.match.views.VAntes;
-import forge.gui.toolbox.FLabel;
import forge.item.CardPrinted;
import forge.properties.ForgePreferences.FPref;
import forge.util.Aggregates;
@@ -44,6 +35,63 @@ import forge.util.MyRandom;
* All of these methods can and should be static.
*/
public class GameNew {
+ private static void prepareSingleLibrary(final Player player, final Deck deck, final Map> removedAnteCards, final List rAICards) {
+ final Random generator = MyRandom.getRandom();
+ boolean useAnte = Singletons.getModel().getPreferences().getPrefBoolean(FPref.UI_ANTE);
+ final boolean canRandomFoil = Singletons.getModel().getPreferences().getPrefBoolean(FPref.UI_RANDOM_FOIL)
+ && Singletons.getModel().getMatch().getGameType() == GameType.Constructed;
+
+
+ PlayerZone library = player.getZone(ZoneType.Library);
+ for (final Entry stackOfCards : deck.getMain()) {
+ final CardPrinted cardPrinted = stackOfCards.getKey();
+ for (int i = 0; i < stackOfCards.getValue(); i++) {
+
+ final Card card = cardPrinted.toForgeCard(player);
+
+ // apply random pictures for cards
+ if ( player.isComputer() ) {
+ final int cntVariants = cardPrinted.getCard().getEditionInfo(cardPrinted.getEdition()).getCopiesCount();
+ if (cntVariants > 1) {
+ card.setRandomPicture(generator.nextInt(cntVariants - 1) + 1);
+ card.setImageFilename(CardUtil.buildFilename(card));
+ }
+ }
+
+ // Assign random foiling on approximately 1:20 cards
+ if (cardPrinted.isFoil() || (canRandomFoil && MyRandom.percentTrue(5))) {
+ final int iFoil = MyRandom.getRandom().nextInt(9) + 1;
+ card.setFoil(iFoil);
+ }
+
+ if (!useAnte && card.hasKeyword("Remove CARDNAME from your deck before playing if you're not playing for ante.")) {
+ if(!removedAnteCards.containsKey(player))
+ removedAnteCards.put(player, new ArrayList());
+ removedAnteCards.get(player).add(card.getName());
+ } else {
+ library.add(card);
+ }
+
+ // mark card as difficult for AI to play
+ if ( player.isComputer() && card.getSVar("RemAIDeck").equals("True") && !rAICards.contains(card.getName())) {
+ rAICards.add(card.getName());
+ // get card picture so that it is in the image cache
+ // ImageCache.getImage(card);
+ }
+ }
+ }
+
+ // Shuffling
+ // Ai may cheat
+ if ( player.isComputer() && Singletons.getModel().getPreferences().getPrefBoolean(FPref.UI_SMOOTH_LAND) ) {
+ // do this instead of shuffling Computer's deck
+ final Iterable c1 = GameNew.smoothComputerManaCurve(player.getCardsIn(ZoneType.Library));
+ player.getZone(ZoneType.Library).setCards(c1);
+ } else
+ player.shuffle();
+ }
+
+
/**
* Constructor for new game allowing card lists to be put into play
* immediately, and life totals to be adjusted, for computer and human.
@@ -51,30 +99,27 @@ public class GameNew {
* TODO: Accept something like match state as parameter. Match should be aware of players,
* their decks and other special starting conditions.
*/
- public static void newGame(final PlayerStartsGame... players) {
- Singletons.getControl().changeState(FControl.MATCH_SCREEN);
- SDisplayUtil.showTab(EDocID.REPORT_LOG.getDoc());
-
- // Update observers
- AllZone.getStack().updateObservers();
- AllZone.getInputControl().updateObservers();
- AllZone.getGameLog().updateObservers();
-
- newGameCleanup();
- newMatchCleanup();
+ public static void newGame(final Map playersConditions) {
+ AllZone.getInputControl().clearInput();
+ AllZone.getColorChanger().reset();
- Singletons.getModel().getPreferences().actuateMatchPreferences();
Card.resetUniqueNumber();
-
- for( PlayerStartsGame p : players ) {
- final Player player = p.getPlayer();
- player.setStartingLife(p.initialLives);
+ // need this code here, otherwise observables fail
+ forge.card.trigger.Trigger.resetIDs();
+ AllZone.getTriggerHandler().clearTriggerSettings();
+ AllZone.getTriggerHandler().clearDelayedTrigger();
+
+ // friendliness
+ final Map> removedAnteCards = new HashMap>();
+ final List rAICards = new ArrayList();
+
+ for( Entry p : playersConditions.entrySet() ) {
+ final Player player = p.getKey();
+ player.setStartingLife(p.getValue().getStartingLife());
// what if I call it for AI player?
- player.updateObservers();
- player.setDeck(p.getDeck());
PlayerZone bf = player.getZone(ZoneType.Battlefield);
- if (p.cardsOnBattlefield != null) {
- for (final Card c : p.cardsOnBattlefield) {
+ if (p.getValue().getCardsOnTable() != null) {
+ for (final Card c : p.getValue().getCardsOnTable()) {
c.addController(player);
c.setOwner(player);
bf.add(c, false);
@@ -83,77 +128,14 @@ public class GameNew {
c.refreshUniqueNumber();
}
}
+
+ prepareSingleLibrary(player, p.getValue().getDeck(), removedAnteCards, rAICards);
+ player.updateObservers();
bf.updateObservers();
- p.getPlayer().getZone(ZoneType.Hand).updateObservers();
- }
- GameNew.actuateGame(players);
- }
-
- /**
- * This must be separated from the newGame method since life totals and
- * player details could be adjusted before the game is started.
- *
- * That process (also cleanup and observer updates) should be done in
- * newGame, then when all is ready, call this function.
- */
- private static void actuateGame(final PlayerStartsGame... players) {
- forge.card.trigger.Trigger.resetIDs();
- AllZone.getTriggerHandler().clearTriggerSettings();
- AllZone.getTriggerHandler().clearDelayedTrigger();
- CMessage.SINGLETON_INSTANCE.updateGameInfo();
-
- // friendliness
- final boolean canRandomFoil = Singletons.getModel().getPreferences().getPrefBoolean(FPref.UI_RANDOM_FOIL)
- && Singletons.getModel().getMatchState().getGameType().equals(GameType.Constructed);
- final Random generator = MyRandom.getRandom();
-
-
- boolean useAnte = Singletons.getModel().getPreferences().getPrefBoolean(FPref.UI_ANTE);
- final Map> removedAnteCards = new HashMap>();
- final List rAICards = new ArrayList();
-
- // Create Card libraries out of decks (CardPrinted)
- for( PlayerStartsGame p : players )
- {
- PlayerZone library = p.getPlayer().getZone(ZoneType.Library);
- for (final Entry stackOfCards : p.getDeck().getMain()) {
- final CardPrinted cardPrinted = stackOfCards.getKey();
- for (int i = 0; i < stackOfCards.getValue(); i++) {
-
- final Card card = cardPrinted.toForgeCard(p.getPlayer());
-
- // apply random pictures for cards
- if ( p.getPlayer().isComputer() ) {
- final int cntVariants = cardPrinted.getCard().getEditionInfo(cardPrinted.getEdition()).getCopiesCount();
- if (cntVariants > 1) {
- card.setRandomPicture(generator.nextInt(cntVariants - 1) + 1);
- card.setImageFilename(CardUtil.buildFilename(card));
- }
- }
-
- // Assign random foiling on approximately 1:20 cards
- if (cardPrinted.isFoil() || (canRandomFoil && MyRandom.percentTrue(5))) {
- final int iFoil = MyRandom.getRandom().nextInt(9) + 1;
- card.setFoil(iFoil);
- }
-
- if (!useAnte && card.hasKeyword("Remove CARDNAME from your deck before playing if you're not playing for ante.")) {
- if(!removedAnteCards.containsKey(p.getPlayer()))
- removedAnteCards.put(p.getPlayer(), new ArrayList());
- removedAnteCards.get(p.getPlayer()).add(card.getName());
- } else {
- library.add(card);
- }
-
- // mark card as difficult for AI to play
- if ( p.getPlayer().isComputer() && card.getSVar("RemAIDeck").equals("True") && !rAICards.contains(card.getName())) {
- rAICards.add(card.getName());
- // get card picture so that it is in the image cache
- // ImageCache.getImage(card);
- }
- }
- }
+ player.getZone(ZoneType.Hand).updateObservers();
}
+
+
if (rAICards.size() > 0) {
String message = buildFourColumnList("AI deck contains the following cards that it can't play or may be buggy:", rAICards);
@@ -167,34 +149,18 @@ public class GameNew {
}
JOptionPane.showMessageDialog(null, ante.toString(), "", JOptionPane.INFORMATION_MESSAGE);
}
-
- // It is supposed that some code to-be-written adds all players passed to this method into game here.
- // So, the upcoming code already refers to AllZone.getPlayersInGame()
+ GameNew.actuateGame();
+ }
- // Shuffling
- final boolean smoothLand = Singletons.getModel().getPreferences().getPrefBoolean(FPref.UI_SMOOTH_LAND);
- for( Player player : Singletons.getModel().getGameState().getPlayers() )
- {
- if ( player.isHuman() ) {
- for (int i = 0; i < 100; i++) {
- player.shuffle();
- }
- }
-
- // Ai may cheat
- if ( player.isComputer() ) {
- if (smoothLand) {
- // do this instead of shuffling Computer's deck
- final Iterable c1 = GameNew.smoothComputerManaCurve(player.getCardsIn(ZoneType.Library));
- player.getZone(ZoneType.Library).setCards(c1);
- } else {
- player.shuffle();
- }
- }
-
- }
-
+ /**
+ * This must be separated from the newGame method since life totals and
+ * player details could be adjusted before the game is started.
+ *
+ * That process (also cleanup and observer updates) should be done in
+ * newGame, then when all is ready, call this function.
+ */
+ private static void actuateGame() {
// Deciding which cards go to ante
if (Singletons.getModel().getPreferences().getPrefBoolean(FPref.UI_ANTE)) {
@@ -217,15 +183,14 @@ public class GameNew {
// Only cut/coin toss if it's the first game of the match
- if (Singletons.getModel().getMatchState().getGamesPlayedCount() == 0) {
+ if (Singletons.getModel().getMatch().getPlayedGames().isEmpty()) {
GameNew.seeWhoPlaysFirstDice();
-
- } else if (Singletons.getModel().getMatchState().hasWonLastGame(AllZone.getHumanPlayer().getName())) {
- // if player won last, AI starts
- GameNew.computerPlayOrDraw("Computer lost the last game.");
} else {
- GameNew.humanPlayOrDraw("Human lost the last game.");
+ Player human = Singletons.getControl().getPlayer();
+ Player goesFirst = Singletons.getModel().getMatch().getLastGameOutcome().isWinner(human.getLobbyPlayer()) ? human.getOpponent() : human;
+ setPlayersFirstTurn(goesFirst);
}
+
// Draw 7 cards
@@ -235,9 +200,6 @@ public class GameNew {
p.drawCard();
}
}
-
- CMatchUI.SINGLETON_INSTANCE.setCard(AllZone.getHumanPlayer().getCardsIn(ZoneType.Hand).get(0));
- AllZone.getInputControl().setInput(new InputMulligan());
} // newGame()
private static String buildFourColumnList(String firstLine, List cAnteRemoved ) {
@@ -254,52 +216,6 @@ public class GameNew {
return sb.toString();
}
- private static void newGameCleanup() {
- final GameState gs = Singletons.getModel().getGameState();
-
- gs.setGameSummary(new GameSummary(Iterables.transform(gs.getPlayers(), Player.Accessors.FN_GET_NAME)));
-
- gs.getPhaseHandler().reset();
- gs.getStack().reset();
- gs.getCombat().reset();
- gs.getEndOfTurn().reset();
- gs.getEndOfCombat().reset();
- gs.getUntap().reset();
- gs.getUpkeep().reset();
- gs.getGameLog().reset();
- gs.setGameOver(false);
-
- for (final Player p : gs.getPlayers()) {
- p.reset();
- for (final ZoneType z : Player.ALL_ZONES) {
- p.getZone(z).reset();
- }
- }
-
- gs.getStaticEffects().reset();
-
- AllZone.getInputControl().clearInput();
- AllZone.getColorChanger().reset();
- }
-
- private static void newMatchCleanup() {
- if (Singletons.getModel().getMatchState().getGamesPlayedCount() != 0) { return; }
-
- // TODO restore this functionality!!!
- //VMatchUI.SINGLETON_INSTANCE.getViewDevMode().getDocument().setVisible(Preferences.DEV_MODE);
-
- final List allFields = VMatchUI.SINGLETON_INSTANCE.getFieldViews();
-
- for (final VField field : allFields) {
- ((FLabel) field.getLblHand()).setHoverable(Preferences.DEV_MODE);
- ((FLabel) field.getLblLibrary()).setHoverable(Preferences.DEV_MODE);
- }
-
- VAntes.SINGLETON_INSTANCE.clearAnteCards();
- AllZone.getInputControl().resetInput();
- Singletons.getModel().getMatchState().reset();
- }
-
// this is where the computer cheats
// changes AllZone.getComputerPlayer().getZone(Zone.Library)
@@ -371,48 +287,34 @@ public class GameNew {
computerDie = MyRandom.getRandom().nextInt(20);
}
- if (playerDie > computerDie) {
- humanPlayOrDraw(dieRollMessage(playerDie, computerDie));
- }
- else {
- computerPlayOrDraw(dieRollMessage(playerDie, computerDie));
+ List allPlayers = Singletons.getModel().getGameState().getPlayers();
+ setPlayersFirstTurn(allPlayers.get(MyRandom.getRandom().nextInt(allPlayers.size())));
+ }
+
+ private static void setPlayersFirstTurn(Player goesFirst)
+ {
+ String message = goesFirst + " has won the coin toss.";
+ if ( goesFirst.isHuman() ) {
+ if( !humanPlayOrDraw(message) );
+
+ } else {
+ computerPlayOrDraw(message);
}
+ Singletons.getModel().getGameState().getPhaseHandler().setPlayerTurn(goesFirst);
} // seeWhoPlaysFirstDice()
-
- private static void computerStartsGame() {
- final Player computer = AllZone.getComputerPlayer();
- Singletons.getModel().getGameState().getPhaseHandler().setPlayerTurn(computer);
- // AllZone.getGameInfo().setPlayerWhoGotFirstTurn(computer.getName());
- }
-
- private static String dieRollMessage(int playerDie, int computerDie) {
- StringBuilder sb = new StringBuilder();
- sb.append("Human has rolled a: ");
- sb.append(playerDie);
- sb.append(". ");
- sb.append("Computer has rolled a: ");
- sb.append(computerDie);
- sb.append(".");
- return sb.toString();
- }
-
- private static void humanPlayOrDraw(String message) {
+ private static boolean humanPlayOrDraw(String message) {
final Object[] possibleValues = { "Play", "Draw" };
final Object playDraw = JOptionPane.showOptionDialog(null, message + "\n\nWould you like to play or draw?",
"Play or Draw?", JOptionPane.DEFAULT_OPTION, JOptionPane.INFORMATION_MESSAGE, null,
possibleValues, possibleValues[0]);
- if (playDraw.equals(1)) {
- computerStartsGame();
- }
+ return !playDraw.equals(1);
}
private static void computerPlayOrDraw(String message) {
JOptionPane.showMessageDialog(null, message + "\nComputer Going First",
"Play or Draw?", JOptionPane.INFORMATION_MESSAGE);
-
- computerStartsGame();
}
}
\ No newline at end of file
diff --git a/src/main/java/forge/game/GameSummary.java b/src/main/java/forge/game/GameOutcome.java
similarity index 57%
rename from src/main/java/forge/game/GameSummary.java
rename to src/main/java/forge/game/GameOutcome.java
index 5250352557b..0d5ae7d90d9 100644
--- a/src/main/java/forge/game/GameSummary.java
+++ b/src/main/java/forge/game/GameOutcome.java
@@ -1,171 +1,174 @@
-/*
- * 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 .
- */
-package forge.game;
-
-import java.util.Arrays;
-import java.util.HashMap;
-import java.util.Map;
-
-/**
- *
- * GameInfo class.
- *
- *
- * @author Forge
- * @version $Id$
- */
-
-// This class might be divided in two parts: the very summary (immutable with
-// only getters) and
-// GameObserver class - who should be notified of any considerable ingame event
-public final class GameSummary {
-
- /** The player winner. */
- private String playerWinner = "Nobody";
-
- /** The player got first turn. */
- // private String playerGotFirstTurn = "Nobody";
-
- /** The last turn number. */
- private int lastTurnNumber = 0;
-
- /** The win condition. */
- private GameEndReason winCondition;
-
- /** The spell effect win. */
- private String spellEffectWin;
-
- /** The player rating. */
- private final Map playerRating = new HashMap();
-
- /**
- * Instantiates a new game summary.
- *
- * @param names
- * the names
- */
- public GameSummary(final String... names) {
- this(Arrays.asList(names));
- }
-
- public GameSummary(final Iterable list) {
- for (final String n : list) {
- this.playerRating.put(n, new GamePlayerRating());
- }
- }
-
- /**
- * End.
- *
- * @param condition
- * the condition
- * @param winner
- * the winner
- * @param spellEffect
- * the spell effect
- */
- public void end(final GameEndReason condition, final String winner, final String spellEffect) {
- this.winCondition = condition;
- this.playerWinner = winner;
- this.spellEffectWin = spellEffect;
- }
-
- /**
- * Checks if is draw.
- *
- * @return true, if is draw
- */
- public boolean isDraw() {
- return null == this.playerWinner;
- }
-
- /**
- * Checks if is winner.
- *
- * @param name
- * the name
- * @return true, if is winner
- */
- public boolean isWinner(final String name) {
- return (name != null) && name.equals(this.playerWinner);
- }
-
- /**
- * Gets the winner.
- *
- * @return the winner
- */
- public String getWinner() {
- return this.playerWinner;
- }
-
- /**
- * Gets the win condition.
- *
- * @return the win condition
- */
- public GameEndReason getWinCondition() {
- return this.winCondition;
- }
-
- /**
- * Gets the player rating.
- *
- * @param name
- * the name
- * @return the player rating
- */
- public GamePlayerRating getPlayerRating(final String name) {
- return this.playerRating.get(name);
- }
-
- /**
- * Gets the turn game ended.
- *
- * @return the turn game ended
- */
- public int getLastTurnNumber() {
- return this.lastTurnNumber;
- }
-
- /**
- * Sets the player who got first turn.
- *
- */
- /*
- * public void setPlayerWhoGotFirstTurn(final String playerName) {
- * this.playerGotFirstTurn = playerName; }
- */
-
- /**
- * Notify next turn.
- */
- public void notifyNextTurn() {
- this.lastTurnNumber++;
- }
-
- /**
- * Gets the win spell effect.
- *
- * @return the win spell effect
- */
- public String getWinSpellEffect() {
- return this.spellEffectWin;
- }
-
-}
+/*
+ * 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 .
+ */
+package forge.game;
+
+import java.util.Arrays;
+import java.util.HashMap;
+import java.util.Iterator;
+import java.util.Map;
+import java.util.Map.Entry;
+
+import forge.game.player.LobbyPlayer;
+import forge.game.player.Player;
+import forge.game.player.PlayerStatistics;
+
+/**
+ *
+ * GameInfo class.
+ *
+ *
+ * @author Forge
+ * @version $Id: GameOutcome.java 17559 2012-10-18 07:59:42Z Max mtg $
+ */
+
+// This class might be divided in two parts: the very summary (immutable with
+// only getters) and
+// GameObserver class - who should be notified of any considerable ingame event
+public final class GameOutcome implements Iterable> {
+
+
+ /** The player got first turn. */
+ // private String playerGotFirstTurn = "Nobody";
+
+ /** The last turn number. */
+ private int lastTurnNumber = 0;
+
+ /** The player rating. */
+ private final Map playerRating = new HashMap(4);
+
+ private GameEndReason winCondition;
+
+ /**
+ * Instantiates a new game summary.
+ *
+ * @param names
+ * the names
+ */
+ public GameOutcome(GameEndReason reason, final Player... names) {
+ this(reason, Arrays.asList(names));
+ }
+
+ public GameOutcome(GameEndReason reason, final Iterable list) {
+ winCondition = reason;
+ for (final Player n : list) {
+ this.playerRating.put(n.getLobbyPlayer(), n.getStats());
+ }
+ }
+
+
+ /**
+ * Checks if is draw.
+ *
+ * @return true, if is draw
+ */
+ public boolean isDraw() {
+ for( PlayerStatistics pv : playerRating.values())
+ {
+ if ( pv.getOutcome().hasWon() )
+ return false;
+ }
+ return true;
+ }
+
+ /**
+ * Checks if is winner.
+ *
+ * @param name
+ * the name
+ * @return true, if is winner
+ */
+ public boolean isWinner(final LobbyPlayer who) {
+ PlayerStatistics stats = playerRating.get(who);
+ return stats.getOutcome().hasWon();
+ }
+
+ /**
+ * Gets the winner.
+ *
+ * @return the winner
+ */
+ public LobbyPlayer getWinner() {
+ for( Entry ps : playerRating.entrySet())
+ {
+ if ( ps.getValue().getOutcome().hasWon() )
+ return ps.getKey();
+ }
+ return null;
+ }
+
+ /**
+ * Gets the win condition.
+ *
+ * @return the win condition
+ */
+ public GameEndReason getWinCondition() {
+ return this.winCondition;
+ }
+
+ /**
+ * Gets the player rating.
+ *
+ * @param name
+ * the name
+ * @return the player rating
+ */
+ public PlayerStatistics getStatistics(final LobbyPlayer name) {
+ return this.playerRating.get(name);
+ }
+
+ /**
+ * Gets the turn game ended.
+ *
+ * @return the turn game ended
+ */
+ public int getLastTurnNumber() {
+ return this.lastTurnNumber;
+ }
+
+ /**
+ * Sets the player who got first turn.
+ *
+ */
+ /*
+ * public void setPlayerWhoGotFirstTurn(final String playerName) {
+ * this.playerGotFirstTurn = playerName; }
+ */
+
+ /**
+ * Gets the win spell effect.
+ *
+ * @return the win spell effect
+ */
+ public String getWinSpellEffect() {
+ for( PlayerStatistics pv : playerRating.values())
+ {
+ if ( pv.getOutcome().hasWon() )
+ return pv.getOutcome().altWinSourceName;
+ }
+ return null;
+ }
+
+ /* (non-Javadoc)
+ * @see java.lang.Iterable#iterator()
+ */
+ @Override
+ public Iterator> iterator() {
+ return playerRating.entrySet().iterator();
+ }
+
+}
diff --git a/src/main/java/forge/game/GameState.java b/src/main/java/forge/game/GameState.java
index c018a9da8f9..97e99458630 100644
--- a/src/main/java/forge/game/GameState.java
+++ b/src/main/java/forge/game/GameState.java
@@ -32,8 +32,7 @@ import forge.game.phase.EndOfTurn;
import forge.game.phase.PhaseHandler;
import forge.game.phase.Untap;
import forge.game.phase.Upkeep;
-import forge.game.player.AIPlayer;
-import forge.game.player.HumanPlayer;
+import forge.game.player.LobbyPlayer;
import forge.game.player.Player;
import forge.game.zone.PlayerZone;
import forge.game.zone.MagicStack;
@@ -51,14 +50,13 @@ public class GameState {
/** The Constant AI_PLAYER_NAME. */
public static final String AI_PLAYER_NAME = "Computer";
- private final List players = new ArrayList();
private final List roPlayers;
private final Cleanup cleanup = new Cleanup();
private final EndOfTurn endOfTurn = new EndOfTurn();
private final EndOfCombat endOfCombat = new EndOfCombat();
private final Untap untap = new Untap();
private final Upkeep upkeep = new Upkeep();
- private final PhaseHandler phaseHandler = new PhaseHandler();
+ private PhaseHandler phaseHandler = new PhaseHandler();
private final MagicStack stack = new MagicStack();
private final StaticEffects staticEffects = new StaticEffects();
private final TriggerHandler triggerHandler = new TriggerHandler();
@@ -70,15 +68,17 @@ public class GameState {
private final PlayerZone stackZone = new PlayerZone(ZoneType.Stack, null);
private long timestamp = 0;
- private GameSummary gameSummary;
-
+ private int nTurn = 0;
+
/**
* Constructor.
+ * @param players2
*/
- public GameState() { /* no more zones to map here */
- players.add(new HumanPlayer(GameState.HUMAN_PLAYER_NAME));
- players.add(new AIPlayer(GameState.AI_PLAYER_NAME));
-
+ public GameState(Iterable players2) { /* no more zones to map here */
+ List players = new ArrayList();
+ for(LobbyPlayer p : players2) {
+ players.add(p.getIngamePlayer());
+ }
roPlayers = Collections.unmodifiableList(players);
}
@@ -238,23 +238,6 @@ public class GameState {
this.timestamp = timestamp0;
}
- /**
- * Gets the game info.
- *
- * @return the game info
- */
- public final GameSummary getGameSummary() {
- return this.gameSummary;
- }
-
- /**
- * Sets the game info.
- *
- * @param summary0 {@link forge.game.GameSummary}
- */
- public final void setGameSummary(final GameSummary summary0) {
- this.gameSummary = summary0;
- }
/**
* @return the replacementHandler
@@ -273,8 +256,25 @@ public class GameState {
/**
* @param go the gameOver to set
*/
- public void setGameOver(boolean go) {
- this.gameOver = go;
+ public void setGameOver() {
+ this.gameOver = true;
+ for(Player p : roPlayers) {
+ p.onGameOver();
+ }
}
+ /**
+ * TODO: Write javadoc for this method.
+ * @return
+ */
+ public int getTurnNumber() {
+ return nTurn;
+ }
+
+ /**
+ * TODO: Write javadoc for this method.
+ */
+ public void notifyNextTurn() {
+ nTurn++;
+ }
}
diff --git a/src/main/java/forge/game/MatchController.java b/src/main/java/forge/game/MatchController.java
new file mode 100644
index 00000000000..eb85a86ddb2
--- /dev/null
+++ b/src/main/java/forge/game/MatchController.java
@@ -0,0 +1,259 @@
+package forge.game;
+
+import java.util.ArrayList;
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+import forge.AllZone;
+import forge.Singletons;
+import forge.Constant.Preferences;
+import forge.control.FControl;
+import forge.control.input.InputMulligan;
+import forge.deck.Deck;
+import forge.error.ErrorViewer;
+import forge.game.player.ComputerAIGeneral;
+import forge.game.player.ComputerAIInput;
+import forge.game.player.LobbyPlayer;
+import forge.game.player.Player;
+import forge.game.player.PlayerType;
+import forge.game.zone.ZoneType;
+import forge.gui.framework.EDocID;
+import forge.gui.framework.SDisplayUtil;
+import forge.gui.match.CMatchUI;
+import forge.gui.match.VMatchUI;
+import forge.gui.match.controllers.CLog;
+import forge.gui.match.controllers.CMessage;
+import forge.gui.match.controllers.CStack;
+import forge.gui.match.nonsingleton.VField;
+import forge.gui.match.views.VAntes;
+import forge.gui.toolbox.FLabel;
+import forge.util.Aggregates;
+
+/**
+ * TODO: Write javadoc for this type.
+ *
+ */
+
+public class MatchController {
+
+ private final Map players = new HashMap();
+ private GameType gameType = GameType.Constructed;
+
+ private int gamesPerMatch = 3;
+ private int gamesToWinMatch = 2;
+
+ private GameState currentGame = null;
+
+ private final List gamesPlayed = new ArrayList();
+ private final List gamesPlayedRo;
+
+ public MatchController() {
+ gamesPlayedRo = Collections.unmodifiableList(gamesPlayed);
+ }
+
+ /**
+ * Gets the games played.
+ *
+ * @return the games played
+ */
+ public final List getPlayedGames() {
+ return this.gamesPlayedRo;
+ }
+
+ /** @return int */
+ public int getGamesPerMatch() {
+ return gamesPerMatch;
+ }
+
+ /** @return int */
+ public int getGamesToWinMatch() {
+ return gamesToWinMatch;
+ }
+
+ /**
+ * TODO: Write javadoc for this method.
+ * @param reason
+ *
+ * @param game
+ */
+ public void addGamePlayed(GameEndReason reason, GameState game) {
+ if ( !game.isGameOver() )
+ throw new RuntimeException("Game is not over yet.");
+
+ GameOutcome result = new GameOutcome(reason, game.getPlayers());
+ gamesPlayed.add(result);
+ }
+
+ /**
+ * TODO: Write javadoc for this method.
+ */
+ public void startRound() {
+
+ // Will this lose all the ordering?
+ currentGame = Singletons.getModel().newGame(players.keySet());
+
+ Map startConditions = new HashMap();
+ for (Player p : currentGame.getPlayers())
+ startConditions.put(p, players.get(p.getLobbyPlayer()));
+
+ try {
+ CMatchUI.SINGLETON_INSTANCE.initMatch(currentGame.getPlayers(), Singletons.getControl().getPlayer());
+ Singletons.getModel().getPreferences().actuateMatchPreferences();
+ Singletons.getControl().changeState(FControl.MATCH_SCREEN);
+ SDisplayUtil.showTab(EDocID.REPORT_LOG.getDoc());
+
+ // set all observers
+ CMessage.SINGLETON_INSTANCE.subscribe(currentGame);
+ CLog.SINGLETON_INSTANCE.subscribe(currentGame);
+ CStack.SINGLETON_INSTANCE.subscribe(currentGame);
+
+
+ GameNew.newGame(startConditions);
+
+ Player computerPlayer = Aggregates.firstFieldEquals(currentGame.getPlayers(), Player.Accessors.FN_GET_TYPE, PlayerType.COMPUTER);
+ AllZone.getInputControl().setComputer(new ComputerAIInput(new ComputerAIGeneral(computerPlayer)));
+
+
+ if (this.getPlayedGames().isEmpty()) {
+ // TODO restore this functionality!!!
+ //VMatchUI.SINGLETON_INSTANCE.getViewDevMode().getDocument().setVisible(Preferences.DEV_MODE);
+
+ for (final VField field : VMatchUI.SINGLETON_INSTANCE.getFieldViews()) {
+ ((FLabel) field.getLblHand()).setHoverable(Preferences.DEV_MODE);
+ ((FLabel) field.getLblLibrary()).setHoverable(Preferences.DEV_MODE);
+ }
+
+ VAntes.SINGLETON_INSTANCE.clearAnteCards();
+ AllZone.getInputControl().resetInput();
+ }
+
+ // per player observers were set in CMatchUI.SINGLETON_INSTANCE.initMatch
+
+ CMessage.SINGLETON_INSTANCE.updateGameInfo(this);
+ // Update observers
+ AllZone.getStack().updateObservers();
+ AllZone.getInputControl().updateObservers();
+ AllZone.getGameLog().updateObservers();
+
+
+ for( Player p : currentGame.getPlayers() ) {
+ p.updateObservers();
+ p.getZone(ZoneType.Hand).updateObservers();
+ }
+
+ CMatchUI.SINGLETON_INSTANCE.setCard(Singletons.getControl().getPlayer().getCardsIn(ZoneType.Hand).get(0));
+ AllZone.getInputControl().setInput(new InputMulligan());
+
+ } catch (Exception e) {
+ ErrorViewer.showError(e);
+ }
+ // bf.updateObservers();
+ // player.updateObservers();
+ // player.getZone(ZoneType.Hand).updateObservers();
+
+ }
+
+ /**
+ * TODO: Write javadoc for this method.
+ */
+ public void initMatch(GameType type, Map map) {
+ gamesPlayed.clear();
+ players.clear();
+ players.putAll(map);
+ gameType = type;
+ }
+
+ /**
+ * TODO: Write javadoc for this method.
+ */
+ public void replayRound() {
+ gamesPlayed.remove(gamesPlayed.size() - 1);
+ }
+
+ /**
+ * TODO: Write javadoc for this method.
+ *
+ * @return
+ */
+ public GameType getGameType() {
+ return gameType;
+ }
+
+ /**
+ * TODO: Write javadoc for this method.
+ *
+ * @return
+ */
+ public GameOutcome getLastGameOutcome() {
+ return gamesPlayed.isEmpty() ? null : gamesPlayed.get(gamesPlayed.size() - 1);
+ }
+
+ public GameState getCurrentGame() {
+ return currentGame;
+ }
+
+ /**
+ * TODO: Write javadoc for this method.
+ *
+ * @return
+ */
+ public boolean isMatchOver() {
+ int[] victories = new int[players.size()];
+ for (GameOutcome go : gamesPlayed) {
+ LobbyPlayer winner = go.getWinner();
+ int i = 0;
+ for (LobbyPlayer p : players.keySet()) {
+ if (p.equals(winner)) {
+ victories[i]++;
+ break; // can't have 2 winners per game
+ }
+ i++;
+ }
+ }
+
+ for (int score : victories) {
+ if (score >= gamesToWinMatch)
+ return true;
+ }
+ return gamesPlayed.size() >= gamesPerMatch;
+ }
+
+ /**
+ * TODO: Write javadoc for this method.
+ *
+ * @param questPlayer
+ * @return
+ */
+ public int getGamesWonBy(LobbyPlayer questPlayer) {
+ int sum = 0;
+ for (GameOutcome go : gamesPlayed) {
+ if (go.getWinner().equals(questPlayer)) {
+ sum++;
+ }
+ }
+ return sum;
+ }
+
+ /**
+ * TODO: Write javadoc for this method.
+ *
+ * @param questPlayer
+ * @return
+ */
+ public boolean isWonBy(LobbyPlayer questPlayer) {
+ return getGamesWonBy(questPlayer) >= gamesToWinMatch;
+ }
+
+ /**
+ * TODO: Write javadoc for this method.
+ *
+ * @param lobbyPlayer
+ * @return
+ */
+ public Deck getPlayersDeck(LobbyPlayer lobbyPlayer) {
+ PlayerStartConditions cond = players.get(lobbyPlayer);
+ return cond == null ? null : cond.getDeck();
+ }
+}
diff --git a/src/main/java/forge/game/MatchStartHelper.java b/src/main/java/forge/game/MatchStartHelper.java
new file mode 100644
index 00000000000..f9012900514
--- /dev/null
+++ b/src/main/java/forge/game/MatchStartHelper.java
@@ -0,0 +1,30 @@
+package forge.game;
+
+import java.util.HashMap;
+import java.util.Map;
+
+import forge.deck.Deck;
+import forge.game.player.LobbyPlayer;
+
+/**
+ * TODO: Write javadoc for this type.
+ *
+ */
+public class MatchStartHelper {
+ private final Map players = new HashMap();
+
+ public void addPlayer(LobbyPlayer player, PlayerStartConditions c) {
+ players.put(player,c);
+ }
+
+ public void addPlayer(LobbyPlayer player, Deck deck) {
+ players.put(player, new PlayerStartConditions(deck));
+ }
+
+ public Map getPlayerMap()
+ {
+ return players;
+ }
+
+
+}
diff --git a/src/main/java/forge/game/PlayerStartConditions.java b/src/main/java/forge/game/PlayerStartConditions.java
new file mode 100644
index 00000000000..01172c1ddf0
--- /dev/null
+++ b/src/main/java/forge/game/PlayerStartConditions.java
@@ -0,0 +1,36 @@
+package forge.game;
+
+import java.util.List;
+
+import forge.Card;
+import forge.deck.Deck;
+
+
+public class PlayerStartConditions {
+ private final Deck deck;
+ private int startingLife = 20;
+ private List cardsOnTable = null;
+
+ public PlayerStartConditions( Deck deck0 ) {
+ deck = deck0;
+ }
+
+ public final Deck getDeck() {
+ return deck;
+ }
+ public final int getStartingLife() {
+ return startingLife;
+ }
+ public final List getCardsOnTable() {
+ return cardsOnTable;
+ }
+
+ public final void setStartingLife(int startingLife) {
+ this.startingLife = startingLife;
+ }
+ public final void setCardsOnTable(List cardsOnTable) {
+ this.cardsOnTable = cardsOnTable;
+ }
+
+
+}
diff --git a/src/main/java/forge/game/PlayerStartsGame.java b/src/main/java/forge/game/PlayerStartsGame.java
deleted file mode 100644
index bcba0376979..00000000000
--- a/src/main/java/forge/game/PlayerStartsGame.java
+++ /dev/null
@@ -1,35 +0,0 @@
-package forge.game;
-
-import java.util.List;
-
-import forge.Card;
-import forge.deck.Deck;
-import forge.game.player.Player;
-
-/**
- * TODO: Write javadoc for this type.
- * @param
- *
- */
-public class PlayerStartsGame {
-
- private final Player player;
- private final Deck deck;
- public int initialLives = 20;
- public List cardsOnBattlefield = null;
-
- public PlayerStartsGame(Player who, Deck cards) {
- player = who;
- deck = cards;
- }
-
- public Player getPlayer() {
- return player;
- }
-
- public Deck getDeck() {
- return deck;
- }
-
-
-}
diff --git a/src/main/java/forge/game/limited/GauntletMini.java b/src/main/java/forge/game/limited/GauntletMini.java
index 5870c23af95..3f6053d23b0 100644
--- a/src/main/java/forge/game/limited/GauntletMini.java
+++ b/src/main/java/forge/game/limited/GauntletMini.java
@@ -19,16 +19,17 @@ package forge.game.limited;
import javax.swing.SwingUtilities;
import javax.swing.SwingWorker;
+
import java.util.List;
-import forge.AllZone;
import forge.Singletons;
+import forge.control.Lobby;
import forge.deck.Deck;
-import forge.game.GameNew;
import forge.game.GameType;
-import forge.game.PlayerStartsGame;
+import forge.game.MatchController;
+import forge.game.MatchStartHelper;
+import forge.game.player.PlayerType;
import forge.gui.SOverlayUtils;
-import forge.gui.match.CMatchUI;
/**
*
@@ -158,10 +159,15 @@ public class GauntletMini {
@Override
public Object doInBackground() {
- CMatchUI.SINGLETON_INSTANCE.initMatch(null);
- Singletons.getModel().getMatchState().setGameType(gauntletType);
- GameNew.newGame( new PlayerStartsGame(AllZone.getHumanPlayer(), humanDeck),
- new PlayerStartsGame(AllZone.getComputerPlayer(), aiDecks.get(currentRound)));
+
+ MatchStartHelper starter = new MatchStartHelper();
+ Lobby lobby = Singletons.getControl().getLobby();
+ starter.addPlayer(lobby.findLocalPlayer(PlayerType.HUMAN), humanDeck);
+ starter.addPlayer(lobby.findLocalPlayer(PlayerType.COMPUTER), aiDecks.get(currentRound));
+
+ MatchController mc = Singletons.getModel().getMatch();
+ mc.initMatch(gauntletType, starter.getPlayerMap());
+ mc.startRound();
return null;
}
diff --git a/src/main/java/forge/game/phase/CombatUtil.java b/src/main/java/forge/game/phase/CombatUtil.java
index 1e0faa6cfae..870fb27f7cb 100644
--- a/src/main/java/forge/game/phase/CombatUtil.java
+++ b/src/main/java/forge/game/phase/CombatUtil.java
@@ -382,7 +382,7 @@ public class CombatUtil {
*/
public static boolean finishedMandatoryBlocks(final Combat combat) {
- final List blockers = AllZoneUtil.getCreaturesInPlay(AllZone.getHumanPlayer());
+ final List blockers = AllZoneUtil.getCreaturesInPlay(Singletons.getControl().getPlayer());
final List attackers = combat.getAttackerList();
// if a creature does not block but should, return false
diff --git a/src/main/java/forge/game/phase/PhaseHandler.java b/src/main/java/forge/game/phase/PhaseHandler.java
index e3695264fb4..359af529f88 100644
--- a/src/main/java/forge/game/phase/PhaseHandler.java
+++ b/src/main/java/forge/game/phase/PhaseHandler.java
@@ -19,7 +19,6 @@ package forge.game.phase;
import java.util.HashMap;
import java.util.List;
-import java.util.Observer;
import java.util.Stack;
import com.esotericsoftware.minlog.Log;
@@ -53,27 +52,39 @@ public class PhaseHandler extends MyObservable implements java.io.Serializable {
/** Constant serialVersionUID=5207222278370963197L. */
private static final long serialVersionUID = 5207222278370963197L;
- private int phaseIndex;
- private int turn;
-
- // Please use getX, setX, and incrementX methods instead of directly
- // accessing the following:
- /** Constant GameBegins=0. */
- private static int gameBegins = 0;
+ private int phaseIndex = 0;
+ private int turn = 1;
private final Stack extraTurns = new Stack();
- private int extraCombats;
+ private int extraCombats = 0;
- private int nCombatsThisTurn;
- private boolean bPreventCombatDamageThisTurn;
+ private int nCombatsThisTurn = 0;
+ private boolean bPreventCombatDamageThisTurn = false;
- private Player playerTurn = AllZone.getHumanPlayer();
+ private Player playerTurn = null;
- private Player skipToTurn = AllZone.getHumanPlayer();
+ private Player skipToTurn = null;
private PhaseType skipToPhase = PhaseType.CLEANUP;
private boolean autoPass = false;
+ // priority player
+
+ private Player pPlayerPriority = null;
+ private Player pFirstPriority = null;
+ private boolean bPhaseEffects = true;
+ private boolean bSkipPhase = true;
+ private boolean bCombat = false;
+ private boolean bRepeat = false;
+
+ /** The need to next phase. */
+ private boolean needToNextPhase = false;
+
+ // This should only be true four times! that is for the initial nextPhases
+ // in MyObservable
+ /** The need to next phase init. */
+ private int needToNextPhaseInit = 0;
+
/**
*
* isPlayerTurn.
@@ -112,8 +123,6 @@ public class PhaseHandler extends MyObservable implements java.io.Serializable {
// priority player
- private Player pPlayerPriority = AllZone.getHumanPlayer();
-
/**
*
* getPriorityPlayer.
@@ -137,8 +146,6 @@ public class PhaseHandler extends MyObservable implements java.io.Serializable {
this.pPlayerPriority = p;
}
- private Player pFirstPriority = AllZone.getHumanPlayer();
-
/**
*
* handleBeginPhase.
@@ -902,15 +869,6 @@ public class PhaseHandler extends MyObservable implements java.io.Serializable {
}
}
- /** {@inheritDoc} */
- @Override
- public final void addObserver(final Observer o) {
- super.addObserver(o);
- }
-
- /** The need to next phase. */
- private boolean needToNextPhase = false;
-
/**
*
* Setter for the field needToNextPhase.
@@ -934,11 +892,6 @@ public class PhaseHandler extends MyObservable implements java.io.Serializable {
return this.needToNextPhase;
}
- // This should only be true four times! that is for the initial nextPhases
- // in MyObservable
- /** The need to next phase init. */
- private int needToNextPhaseInit = 0;
-
/**
*
- *
- * @return a int.
- */
- public static int getGameBegins() {
- return PhaseHandler.gameBegins;
- }
-
// this is a hack for the setup game state mode, do not use outside of
// devSetupGameState code
// as it avoids calling any of the phase effects that may be necessary in a
diff --git a/src/main/java/forge/game/phase/PhaseUtil.java b/src/main/java/forge/game/phase/PhaseUtil.java
index eff33e64888..f0f368567a1 100644
--- a/src/main/java/forge/game/phase/PhaseUtil.java
+++ b/src/main/java/forge/game/phase/PhaseUtil.java
@@ -87,8 +87,8 @@ public class PhaseUtil {
final PhaseHandler ph = Singletons.getModel().getGameState().getPhaseHandler();
final Player turn = ph.getPlayerTurn();
- Singletons.getModel().getGameSummary().notifyNextTurn();
- CMessage.SINGLETON_INSTANCE.updateGameInfo();
+ Singletons.getModel().getGameState().notifyNextTurn();
+ CMessage.SINGLETON_INSTANCE.updateGameInfo(Singletons.getModel().getMatch());
AllZone.getCombat().reset();
AllZone.getCombat().setAttackingPlayer(turn);
diff --git a/src/main/java/forge/game/player/AIPlayer.java b/src/main/java/forge/game/player/AIPlayer.java
index e7aa5591797..c6386904f2a 100644
--- a/src/main/java/forge/game/player/AIPlayer.java
+++ b/src/main/java/forge/game/player/AIPlayer.java
@@ -50,24 +50,8 @@ public class AIPlayer extends Player {
* @param myName
* a {@link java.lang.String} object.
*/
- public AIPlayer(final String myName) {
- this(myName, 20, 0);
- }
-
- /**
- *
- * Constructor for AIPlayer.
- *
- *
- * @param myName
- * a {@link java.lang.String} object.
- * @param myLife
- * a int.
- * @param myPoisonCounters
- * a int.
- */
- public AIPlayer(final String myName, final int myLife, final int myPoisonCounters) {
- super(myName, myLife, myPoisonCounters);
+ public AIPlayer(final LobbyPlayer player) {
+ super(player);
}
diff --git a/src/main/java/forge/game/player/HumanPlayer.java b/src/main/java/forge/game/player/HumanPlayer.java
index f549ccfebd6..94e594e914a 100644
--- a/src/main/java/forge/game/player/HumanPlayer.java
+++ b/src/main/java/forge/game/player/HumanPlayer.java
@@ -29,6 +29,8 @@ import forge.control.input.Input;
import forge.game.zone.ZoneType;
import forge.gui.GuiChoose;
import forge.gui.match.CMatchUI;
+import forge.quest.QuestController;
+import forge.quest.bazaar.QuestItemType;
/**
*
@@ -48,24 +50,8 @@ public class HumanPlayer extends Player {
* @param myName
* a {@link java.lang.String} object.
*/
- public HumanPlayer(final String myName) {
- this(myName, 20, 0);
- }
-
- /**
- *
- * Constructor for HumanPlayer.
- *
- *
- * @param myName
- * a {@link java.lang.String} object.
- * @param myLife
- * a int.
- * @param myPoisonCounters
- * a int.
- */
- public HumanPlayer(final String myName, final int myLife, final int myPoisonCounters) {
- super(myName, myLife, myPoisonCounters);
+ public HumanPlayer(final LobbyPlayer player) {
+ super(player);
}
// //////////////
@@ -222,4 +208,15 @@ public class HumanPlayer extends Player {
return PlayerType.HUMAN;
}
+ @Override
+ public final int doMulligan() {
+ int newHand = super.doMulligan();
+ final QuestController quest = Singletons.getModel().getQuest();
+ if (quest.isLoaded() && quest.getAssets().hasItem(QuestItemType.SLEIGHT) && (getStats().getMulliganCount() == 1)) {
+ drawCard();
+ newHand++;
+ getStats().notifyOpeningHandSize(newHand);
+ }
+ return newHand;
+ }
} // end HumanPlayer class
diff --git a/src/main/java/forge/game/player/LobbyPlayer.java b/src/main/java/forge/game/player/LobbyPlayer.java
new file mode 100644
index 00000000000..76997664192
--- /dev/null
+++ b/src/main/java/forge/game/player/LobbyPlayer.java
@@ -0,0 +1,75 @@
+package forge.game.player;
+
+/**
+ * This means a player's part unchanged for all games.
+ *
+ * May store player's assets here.
+ *
+ */
+public class LobbyPlayer {
+
+ final protected PlayerType type;
+ final protected String name;
+ protected String picture;
+
+ public LobbyPlayer(PlayerType type, String name)
+ {
+ this.type = type;
+ this.name = name;
+ }
+
+ public final String getPicture() {
+ return picture;
+ }
+
+ public final void setPicture(String picture) {
+ this.picture = picture;
+ }
+
+ /**
+ * TODO: Write javadoc for this method.
+ * @return
+ */
+ public Player getIngamePlayer() {
+ if ( type == PlayerType.HUMAN )
+ return new HumanPlayer(this);
+ else
+ return new AIPlayer(this);
+ }
+
+ /**
+ * TODO: Write javadoc for this method.
+ * @return
+ */
+ public String getName() {
+ return name;
+ }
+
+ @Override
+ public int hashCode() {
+ final int prime = 31;
+ int result = 1;
+ result = prime * result + ((name == null) ? 0 : name.hashCode());
+ result = prime * result + ((type == null) ? 0 : type.hashCode());
+ return result;
+ }
+
+ @Override
+ public boolean equals(Object obj) {
+ if (this == obj)
+ return true;
+ if (obj == null)
+ return false;
+ if (getClass() != obj.getClass())
+ return false;
+ LobbyPlayer other = (LobbyPlayer) obj;
+ if (name == null) {
+ if (other.name != null)
+ return false;
+ } else if (!name.equals(other.name))
+ return false;
+ if (type != other.type)
+ return false;
+ return true;
+ }
+}
diff --git a/src/main/java/forge/game/player/Player.java b/src/main/java/forge/game/player/Player.java
index d0b7c3eab85..b9b615b3176 100644
--- a/src/main/java/forge/game/player/Player.java
+++ b/src/main/java/forge/game/player/Player.java
@@ -51,7 +51,6 @@ import forge.card.replacement.ReplacementResult;
import forge.card.spellability.SpellAbility;
import forge.card.staticability.StaticAbility;
import forge.card.trigger.TriggerType;
-import forge.deck.Deck;
import forge.game.GameLossReason;
import forge.game.phase.PhaseHandler;
import forge.game.zone.PlayerZone;
@@ -69,15 +68,15 @@ import forge.util.MyRandom;
* @author Forge
* @version $Id$
*/
-public abstract class Player extends GameEntity implements Comparable {
+public abstract class Player extends GameEntity implements Comparable {
/** The poison counters. */
- private int poisonCounters;
+ private int poisonCounters = 0;
/** The life. */
- private int life;
+ private int life = 20;
/** The life this player started the game with. */
- private int startingLife;
+ private int startingLife = 20;
/** The assigned damage. */
private final Map assignedDamage = new HashMap();
@@ -88,24 +87,6 @@ public abstract class Player extends GameEntity implements Comparable {
/** The num power surge lands. */
private int numPowerSurgeLands;
- /** The alt win. */
- private boolean altWin = false;
-
- /** The alt win source name. */
- private String altWinSourceName;
-
- /** The alt lose. */
- // private boolean altLose = false;
-
- /** The loss state. */
- private GameLossReason lossState = GameLossReason.DidNotLoseYet;
-
- /** The lose condition spell. */
- private String loseConditionSpell;
-
- /** The n turns. */
- private int nTurns = 0;
-
/** The skip next untap. */
private boolean skipNextUntap = false;
@@ -122,7 +103,7 @@ public abstract class Player extends GameEntity implements Comparable {
private int maxHandSize = 7;
/** The last drawn card. */
- private Card lastDrawnCard;
+ private Card lastDrawnCard = null;
/** The num drawn this turn. */
private int numDrawnThisTurn = 0;
@@ -134,7 +115,7 @@ public abstract class Player extends GameEntity implements Comparable {
private ArrayList keywords = new ArrayList();
/** The mana pool. */
- private ManaPool manaPool = null;
+ private ManaPool manaPool = new ManaPool(this);
/** The must attack entity. */
private Object mustAttackEntity = null;
@@ -148,24 +129,19 @@ public abstract class Player extends GameEntity implements Comparable {
/** The zones. */
private final Map zones = new EnumMap(ZoneType.class);
+ private PlayerStatistics stats = new PlayerStatistics();
+
/** The Constant ALL_ZONES. */
public static final List ALL_ZONES = Collections.unmodifiableList(Arrays.asList(ZoneType.Battlefield,
- ZoneType.Library, ZoneType.Graveyard, ZoneType.Hand, ZoneType.Exile, ZoneType.Command, ZoneType.Ante, ZoneType.Stack));
+ ZoneType.Library, ZoneType.Graveyard, ZoneType.Hand, ZoneType.Exile, ZoneType.Command, ZoneType.Ante));
- // Moved deck here from Constants.Runtime
- private Deck deck;
- /**
- *
- * Constructor for Player.
- *
- *
- * @param myName
- * a {@link java.lang.String} object.
- */
- public Player(final String myName) {
- this(myName, 20, 0);
+
+ private LobbyPlayer lobbyPlayer;
+
+ public final PlayerOutcome getOutcome() {
+ return stats.getOutcome();
}
/**
@@ -180,48 +156,19 @@ public abstract class Player extends GameEntity implements Comparable {
* @param myPoisonCounters
* a int.
*/
- public Player(final String myName, final int myLife, final int myPoisonCounters) {
+ public Player(LobbyPlayer lobbyPlayer0) {
+ lobbyPlayer = lobbyPlayer0;
for (final ZoneType z : Player.ALL_ZONES) {
- final PlayerZone toPut = z == ZoneType.Battlefield ? new PlayerZoneBattlefield(z, this)
+ final PlayerZone toPut = z == ZoneType.Battlefield
+ ? new PlayerZoneBattlefield(z, this)
: new PlayerZone(z, this);
this.zones.put(z, toPut);
}
-
- this.reset();
-
- this.setName(myName);
- this.life = myLife;
- this.poisonCounters = myPoisonCounters;
+ this.setName(lobbyPlayer.getName());
}
- /**
- *
- * reset.
- *
- */
- public final void reset() {
- this.life = 20;
- this.lifeLostThisTurn = 0;
- this.poisonCounters = 0;
- this.assignedDamage.clear();
- this.setPreventNextDamage(0);
- this.lastDrawnCard = null;
- this.numDrawnThisTurn = 0;
- this.slowtripList = new ArrayList();
- this.nTurns = 0;
- this.altWin = false;
- this.altWinSourceName = null;
- // altLose = false;
- this.lossState = GameLossReason.DidNotLoseYet;
- this.loseConditionSpell = null;
- this.maxLandsToPlay = 1;
- this.numLandsPlayed = 0;
- this.prowl = new ArrayList();
-
- this.keywords.clear();
- this.manaPool = new ManaPool(this);
-
- this.updateObservers();
+ public final PlayerStatistics getStats() {
+ return stats;
}
/**
@@ -1266,6 +1213,32 @@ public abstract class Player extends GameEntity implements Comparable {
}
return drawn;
}
+
+ /**
+ *
+ * TODO Write javadoc for this method.
+ *
+ * @param player
+ * a Player object
+ * @param playerRating
+ * a GamePlayerRating object
+ * @return an int
+ */
+ public int doMulligan() {
+ final List hand = getCardsIn(ZoneType.Hand);
+ for (final Card c : hand) {
+ Singletons.getModel().getGameAction().moveToLibrary(c);
+ }
+ shuffle();
+ final int newHand = hand.size() - 1;
+ for (int i = 0; i < newHand; i++) {
+ drawCard();
+ }
+ AllZone.getGameLog().add("Mulligan", this + " has mulliganed down to " + newHand + " cards.", 0);
+ stats.notifyHasMulliganed();
+ stats.notifyOpeningHandSize(newHand);
+ return newHand;
+ }
/**
*
@@ -1307,7 +1280,7 @@ public abstract class Player extends GameEntity implements Comparable {
}
}
- if (PhaseHandler.getGameBegins() == 1) {
+ if (Singletons.getModel().getGameState() != null) {
this.setLastDrawnCard(c);
c.setDrawnThisTurn(true);
this.numDrawnThisTurn++;
@@ -1441,7 +1414,9 @@ public abstract class Player extends GameEntity implements Comparable {
* @return the all cards
*/
public final List getAllCards() {
- return this.getCardsIn(Player.ALL_ZONES);
+ List allExcStack = this.getCardsIn(Player.ALL_ZONES);
+ allExcStack.addAll(getCardsIn(ZoneType.Stack));
+ return allExcStack;
}
/**
@@ -2035,7 +2010,7 @@ public abstract class Player extends GameEntity implements Comparable {
* @return a int.
*/
public final int getTurn() {
- return this.nTurns;
+ return this.stats.getTurnsPlayed();
}
/**
@@ -2044,7 +2019,7 @@ public abstract class Player extends GameEntity implements Comparable {
*
*/
public final void incrementTurn() {
- this.nTurns++;
+ this.stats.nextTurn();
}
/**
@@ -2116,48 +2091,6 @@ public abstract class Player extends GameEntity implements Comparable {
// Game win/loss
- /**
- *
- * Getter for the field altWin.
- *
- *
- * @return a boolean.
- */
- public final boolean getAltWin() {
- return this.altWin;
- }
-
- /**
- *
- * Getter for the field winCondition.
- *
- *
- * @return a {@link java.lang.String} object.
- */
- public final String getWinConditionSource() {
- return this.altWinSourceName;
- }
-
- /**
- *
- * Getter for the field loseCondition.
- *
- *
- * @return a {@link java.lang.String} object.
- */
- public final GameLossReason getLossState() {
- return this.lossState;
- }
-
- /**
- * Gets the loss condition source.
- *
- * @return the loss condition source
- */
- public final String getLossConditionSource() {
- return this.loseConditionSpell;
- }
-
/**
*
* altWinConditionMet.
@@ -2171,8 +2104,8 @@ public abstract class Player extends GameEntity implements Comparable {
System.out.println("Tried to win, but currently can't.");
return;
}
- this.altWin = true;
- this.altWinSourceName = sourceName;
+ this.setOutcome(PlayerOutcome.altWin(sourceName));
+
}
/**
@@ -2187,22 +2120,23 @@ public abstract class Player extends GameEntity implements Comparable {
* @return a boolean.
*/
public final boolean loseConditionMet(final GameLossReason state, final String spellName) {
- if (this.cantLose()) {
- System.out.println("Tried to lose, but currently can't.");
- return false;
+ if ( state != GameLossReason.OpponentWon ) {
+ if (this.cantLose()) {
+ System.out.println("Tried to lose, but currently can't.");
+ return false;
+ }
+
+ // Replacement effects
+ final HashMap runParams = new HashMap();
+ runParams.put("Affected", this);
+ runParams.put("Event", "GameLoss");
+
+ if (AllZone.getReplacementHandler().run(runParams) != ReplacementResult.NotReplaced) {
+ return false;
+ }
}
- // Replacement effects
- final HashMap runParams = new HashMap();
- runParams.put("Affected", this);
- runParams.put("Event", "GameLoss");
-
- if (AllZone.getReplacementHandler().run(runParams) != ReplacementResult.NotReplaced) {
- return false;
- }
-
- this.lossState = state;
- this.loseConditionSpell = spellName;
+ setOutcome(PlayerOutcome.loss(state, spellName));
return true;
}
@@ -2210,8 +2144,7 @@ public abstract class Player extends GameEntity implements Comparable {
* Concede.
*/
public final void concede() { // No cantLose checks - just lose
- this.lossState = GameLossReason.Conceded;
- this.loseConditionSpell = null;
+ setOutcome(PlayerOutcome.concede());
}
/**
@@ -2222,7 +2155,7 @@ public abstract class Player extends GameEntity implements Comparable {
* @return a boolean.
*/
public final boolean cantLose() {
- if (this.lossState == GameLossReason.Conceded) {
+ if (this.getOutcome() != null && this.getOutcome().lossState == GameLossReason.Conceded) {
return false;
}
@@ -2258,11 +2191,10 @@ public abstract class Player extends GameEntity implements Comparable {
*
* @return a boolean.
*/
- public final boolean hasLost() {
-
- if (this.lossState != GameLossReason.DidNotLoseYet) {
- return this.loseConditionMet(this.lossState, null);
- }
+ public final boolean checkLoseCondition() {
+
+ if ( this.getOutcome() != null )
+ return this.getOutcome().lossState != null;
if (this.poisonCounters >= 10) {
return this.loseConditionMet(GameLossReason.Poisoned, null);
@@ -2287,8 +2219,10 @@ public abstract class Player extends GameEntity implements Comparable {
if (this.cantWin()) {
return false;
}
+ // in multiplayer game one player's win is replaced by all other's lose (rule 103.4h)
+ // so if someone cannot lose, the game appears to continue
- return this.altWin;
+ return this.getOutcome() != null && this.getOutcome().lossState == null;
}
/**
@@ -2714,16 +2648,15 @@ public abstract class Player extends GameEntity implements Comparable {
return (41 * (41 + this.getName().hashCode()));
}
- public Deck getDeck() {
- return deck;
- }
-
- public void setDeck(Deck deck) {
- this.deck = deck;
- }
-
public static class Predicates {
+ public static final Predicate NOT_LOST = new Predicate() {
+ @Override
+ public boolean apply(Player p) {
+ return p.getOutcome() == null || p.getOutcome().hasWon();
+ }
+ };
+
public static Predicate isType(final PlayerType type) {
return new Predicate() {
@Override
@@ -2735,6 +2668,13 @@ public abstract class Player extends GameEntity implements Comparable {
}
public static class Accessors {
+ public static Function FN_GET_LOBBY_PLAYER = new Function(){
+ @Override
+ public LobbyPlayer apply(Player input) {
+ return input.getLobbyPlayer();
+ }
+ };
+
public static Function FN_GET_LIFE = new Function(){
@Override
public Integer apply(Player input) {
@@ -2765,4 +2705,24 @@ public abstract class Player extends GameEntity implements Comparable {
};
}
}
+
+ /**
+ * TODO: Write javadoc for this method.
+ * @return
+ */
+ public LobbyPlayer getLobbyPlayer() {
+ return lobbyPlayer;
+ }
+
+ private void setOutcome(PlayerOutcome outcome) {
+ stats.setOutcome(outcome);
+ }
+
+ /**
+ * TODO: Write javadoc for this method.
+ */
+ public void onGameOver() {
+ if ( null == stats.getOutcome() ) // not lost?
+ setOutcome(PlayerOutcome.win()); // then won!
+ }
}
diff --git a/src/main/java/forge/game/player/PlayerOutcome.java b/src/main/java/forge/game/player/PlayerOutcome.java
new file mode 100644
index 00000000000..8de14a65bb8
--- /dev/null
+++ b/src/main/java/forge/game/player/PlayerOutcome.java
@@ -0,0 +1,57 @@
+package forge.game.player;
+
+import forge.game.GameLossReason;
+
+/**
+ * TODO: Write javadoc for this type.
+ */
+public class PlayerOutcome {
+ /** The alt win source name. */
+ public final String altWinSourceName;
+ /** The loss state. */
+ public final GameLossReason lossState;
+ /** The lose condition spell. */
+ public final String loseConditionSpell;
+
+ private PlayerOutcome(String altWinSourceName, GameLossReason lossState, String loseConditionSpell) {
+ this.altWinSourceName= altWinSourceName;
+ this.loseConditionSpell = loseConditionSpell;
+ this.lossState = lossState;
+ }
+
+ /**
+ * TODO: Write javadoc for this method.
+ * @param sourceName
+ * @return
+ */
+ public static PlayerOutcome win() {
+ return new PlayerOutcome(null, null, null);
+ }
+
+ public static PlayerOutcome altWin(String sourceName) {
+ return new PlayerOutcome(sourceName, null, null);
+ }
+
+ /**
+ * TODO: Write javadoc for this method.
+ * @param state
+ * @param spellName
+ * @return
+ */
+ public static PlayerOutcome loss(GameLossReason state, String spellName) {
+ return new PlayerOutcome(null, state, spellName);
+ }
+
+ /**
+ * TODO: Write javadoc for this method.
+ * @return
+ */
+ public static PlayerOutcome concede() {
+ return new PlayerOutcome(null, GameLossReason.Conceded, null);
+ }
+
+ public boolean hasWon() {
+ return lossState == null;
+ }
+
+}
\ No newline at end of file
diff --git a/src/main/java/forge/game/GamePlayerRating.java b/src/main/java/forge/game/player/PlayerStatistics.java
similarity index 62%
rename from src/main/java/forge/game/GamePlayerRating.java
rename to src/main/java/forge/game/player/PlayerStatistics.java
index aeab8a05a1a..d36ba41a219 100644
--- a/src/main/java/forge/game/GamePlayerRating.java
+++ b/src/main/java/forge/game/player/PlayerStatistics.java
@@ -15,14 +15,14 @@
* You should have received a copy of the GNU General Public License
* along with this program. If not, see .
*/
-package forge.game;
+package forge.game.player;
/**
* The Class GamePlayerRating.
*
* @author Max
*/
-public class GamePlayerRating {
+public class PlayerStatistics {
/** The opening hand size. */
private int openingHandSize = 7;
@@ -30,42 +30,10 @@ public class GamePlayerRating {
/** The times mulliganed. */
private int timesMulliganed = 0;
- /** The loss reason. */
- private GameLossReason lossReason = GameLossReason.DidNotLoseYet;
+ private int turnsPlayed = 0;
- /** The loss spell name. */
- private String lossSpellName;
-
- /**
- * Gets the loss reason.
- *
- * @return the loss reason
- */
- public final GameLossReason getLossReason() {
- return this.lossReason;
- }
-
- /**
- * Sets the loss reason.
- *
- * @param loseCondition
- * the lose condition
- * @param spellName
- * the spell name
- */
- public void setLossReason(final GameLossReason loseCondition, final String spellName) {
- this.lossReason = loseCondition;
- this.lossSpellName = spellName;
- }
-
- /**
- * Gets the loss spell name.
- *
- * @return the loss spell name
- */
- public String getLossSpellName() {
- return this.lossSpellName;
- }
+
+ private PlayerOutcome outcome;
/**
* Gets the opening hand size.
@@ -102,4 +70,20 @@ public class GamePlayerRating {
this.openingHandSize = newHand;
}
+ public int getTurnsPlayed() {
+ return turnsPlayed;
+ }
+
+ public void nextTurn() {
+ this.turnsPlayed++;
+ }
+
+ public PlayerOutcome getOutcome() {
+ return outcome;
+ }
+
+ public void setOutcome(PlayerOutcome gameOutcome) {
+ this.outcome = gameOutcome;
+ }
+
}
diff --git a/src/main/java/forge/game/zone/PlayerZone.java b/src/main/java/forge/game/zone/PlayerZone.java
index 4229a4cbb78..063ddc770cb 100644
--- a/src/main/java/forge/game/zone/PlayerZone.java
+++ b/src/main/java/forge/game/zone/PlayerZone.java
@@ -46,7 +46,7 @@ public class PlayerZone extends MyObservable implements IPlayerZone, Observer, j
private static final long serialVersionUID = -5687652485777639176L;
/** The cards. */
- protected final List cardList;
+ protected final List cardList = new ArrayList();
protected final Collection roCardList;
private final ZoneType zoneName;
private final Player player;
@@ -70,7 +70,6 @@ public class PlayerZone extends MyObservable implements IPlayerZone, Observer, j
public PlayerZone(final ZoneType zone, final Player inPlayer) {
this.zoneName = zone;
this.player = inPlayer;
- this.cardList = new ArrayList();
this.roCardList = Collections.unmodifiableCollection(cardList);
}
diff --git a/src/main/java/forge/game/zone/ZoneType.java b/src/main/java/forge/game/zone/ZoneType.java
index 65b8bd1465f..8f944203af7 100644
--- a/src/main/java/forge/game/zone/ZoneType.java
+++ b/src/main/java/forge/game/zone/ZoneType.java
@@ -1,6 +1,7 @@
package forge.game.zone;
import java.util.ArrayList;
+import java.util.Arrays;
import java.util.List;
/**
@@ -33,7 +34,7 @@ public enum ZoneType {
/** Ante. */
Ante(false);
- public static final ZoneType[] STATIC_ABILITIES_SOURCE_ZONES = new ZoneType[]{Battlefield, Graveyard, Exile/*, Hand*/};
+ public static final List STATIC_ABILITIES_SOURCE_ZONES = Arrays.asList(new ZoneType[]{Battlefield, Graveyard, Exile/*, Hand*/});
private final boolean holdsHiddenInfo;
private ZoneType(boolean holdsHidden) {
diff --git a/src/main/java/forge/gui/GuiInput.java b/src/main/java/forge/gui/GuiInput.java
index 178da6f6b7c..3a629c936eb 100644
--- a/src/main/java/forge/gui/GuiInput.java
+++ b/src/main/java/forge/gui/GuiInput.java
@@ -22,8 +22,8 @@ import java.util.Observer;
import forge.AllZone;
import forge.Card;
-import forge.Singletons;
import forge.control.input.Input;
+import forge.game.GameState;
import forge.game.player.Player;
import forge.game.zone.PlayerZone;
import forge.util.MyObservable;
@@ -41,16 +41,6 @@ public class GuiInput extends MyObservable implements Observer {
/** The input. */
private Input input;
- /**
- *