|
From: <ste...@us...> - 2011-07-06 05:39:23
|
Revision: 1605
http://rails.svn.sourceforge.net/rails/?rev=1605&view=rev
Author: stefanfrey
Date: 2011-07-06 05:39:16 +0000 (Wed, 06 Jul 2011)
Log Message:
-----------
Refactored save and load code into GameFileIO and GameData classes
Modified Paths:
--------------
trunk/18xx/rails/game/Game.java
trunk/18xx/rails/game/GameManager.java
trunk/18xx/rails/util/ListAndFixSavedFiles.java
Added Paths:
-----------
trunk/18xx/rails/util/GameData.java
trunk/18xx/rails/util/GameFileIO.java
Removed Paths:
-------------
trunk/18xx/rails/util/GameLoader.java
Modified: trunk/18xx/rails/game/Game.java
===================================================================
--- trunk/18xx/rails/game/Game.java 2011-07-05 17:03:23 UTC (rev 1604)
+++ trunk/18xx/rails/game/Game.java 2011-07-06 05:39:16 UTC (rev 1605)
@@ -13,7 +13,7 @@
import rails.common.parser.GameFileParser;
import rails.common.parser.GameOption;
import rails.game.action.PossibleAction;
-import rails.util.GameLoader;
+import rails.util.GameFileIO;
public class Game {
public static final String version = "1.4.1+";
@@ -124,7 +124,7 @@
public static Game load(String filepath) {
// use GameLoader object to load game
- GameLoader gameLoader = new GameLoader();
+ GameFileIO gameLoader = new GameFileIO();
gameLoader.loadGameData(filepath);
try{
gameLoader.initGame();
Modified: trunk/18xx/rails/game/GameManager.java
===================================================================
--- trunk/18xx/rails/game/GameManager.java 2011-07-05 17:03:23 UTC (rev 1604)
+++ trunk/18xx/rails/game/GameManager.java 2011-07-06 05:39:16 UTC (rev 1605)
@@ -1115,31 +1115,11 @@
}
protected boolean save(File file, boolean displayErrorMessage, String errorMessageKey) {
- boolean result = false;
-
- try {
- ObjectOutputStream oos =
- new ObjectOutputStream(new FileOutputStream(file));
- oos.writeObject(Game.version+" "+BuildInfo.buildDate);
- oos.writeObject(new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(new Date()));
- oos.writeObject(saveFileVersionID);
- oos.writeObject(gameName);
- oos.writeObject(gameOptions);
- oos.writeObject(playerNames);
- for (PossibleAction action : executedActions) {
- oos.writeObject(action);
- }
- oos.writeObject(ReportBuffer.getCommentItems());
- oos.close();
-
- result = true;
- } catch (IOException e) {
- log.error(errorMessageKey, e);
- if (displayErrorMessage) {
- DisplayBuffer.add(LocalText.getText("SaveFailed", e.getMessage()));
- }
- }
- return result;
+ GameFileIO gameSaver = new GameFileIO();
+ gameSaver.initSave(saveFileVersionID, gameName, gameOptions, playerNames);
+ gameSaver.setActions(executedActions);
+ gameSaver.setComments(ReportBuffer.getCommentItems());
+ return gameSaver.saveGame(file, displayErrorMessage, errorMessageKey);
}
/**
* tries to reload the current game
@@ -1149,7 +1129,7 @@
log.info("Reloading started");
/* Use gameLoader to load the game data */
- GameLoader gameLoader = new GameLoader();
+ GameFileIO gameLoader = new GameFileIO();
String filepath = reloadAction.getFilepath();
gameLoader.loadGameData(filepath);
Added: trunk/18xx/rails/util/GameData.java
===================================================================
--- trunk/18xx/rails/util/GameData.java (rev 0)
+++ trunk/18xx/rails/util/GameData.java 2011-07-06 05:39:16 UTC (rev 1605)
@@ -0,0 +1,57 @@
+package rails.util;
+
+import java.util.List;
+import java.util.Map;
+import java.util.SortedMap;
+
+import rails.game.action.PossibleAction;
+
+/**
+ * Combines all fields required for game IO
+ * Defines the complete game
+ *
+ * @author freystef
+ * */
+
+
+class GameData {
+ class MetaData {
+ String version;
+ String date;
+ Long fileVersionID;
+ String gameName;
+ };
+
+ MetaData meta = new MetaData();
+ Map<String, String> gameOptions;
+ List<String> playerNames;
+ List<PossibleAction> actions;
+ SortedMap<Integer, String> userComments;
+
+ String metaDataAsText() {
+ StringBuilder s = new StringBuilder();
+ s.append("Rails saveVersion = " + meta.version + "\n");
+ s.append("File was saved at " + meta.date + "\n");
+ s.append("Saved versionID=" + meta.fileVersionID + "\n");
+ s.append("Save game=" + meta.gameName + "\n");
+ return s.toString();
+ }
+
+ String gameOptionsAsText() {
+ StringBuilder s = new StringBuilder();
+ for (String key : gameOptions.keySet()) {
+ s.append("Option "+key+"="+gameOptions.get(key)+ "\n");
+ }
+ return s.toString();
+ }
+ String playerNamesAsText() {
+ StringBuilder s = new StringBuilder();
+ int i=1;
+ for (String player : playerNames) {
+ s.append("Player "+(i++)+": "+player + "\n");
+ }
+ return s.toString();
+ }
+
+
+}
Property changes on: trunk/18xx/rails/util/GameData.java
___________________________________________________________________
Added: svn:mime-type
+ text/plain
Copied: trunk/18xx/rails/util/GameFileIO.java (from rev 1604, trunk/18xx/rails/util/GameLoader.java)
===================================================================
--- trunk/18xx/rails/util/GameFileIO.java (rev 0)
+++ trunk/18xx/rails/util/GameFileIO.java 2011-07-06 05:39:16 UTC (rev 1605)
@@ -0,0 +1,296 @@
+package rails.util;
+
+import java.io.EOFException;
+import java.io.File;
+import java.io.FileInputStream;
+import java.io.FileOutputStream;
+import java.io.IOException;
+import java.io.ObjectInputStream;
+import java.io.ObjectOutputStream;
+import java.text.SimpleDateFormat;
+import java.util.ArrayList;
+import java.util.Date;
+import java.util.List;
+import java.util.Map;
+import java.util.SortedMap;
+import java.util.TreeMap;
+
+import org.apache.log4j.Logger;
+
+import rails.common.DisplayBuffer;
+import rails.common.LocalText;
+import rails.common.parser.ConfigurationException;
+import rails.game.Game;
+import rails.game.GameManager;
+import rails.game.GameManagerI;
+import rails.game.ReportBuffer;
+import rails.game.action.PossibleAction;
+
+/**
+ * Functions to load and save games from/to file
+ *
+ * @author freystef
+ *
+ */
+public class GameFileIO {
+
+ protected static Logger log =
+ Logger.getLogger(Game.class.getPackage().getName());
+
+ private GameData gameData = new GameData();
+
+ // fields for data load
+ private ObjectInputStream ois = null;
+ private Game loadedGame = null;
+ private boolean dataLoadDone = false;
+ private boolean initialized = false;
+
+ // fields for data save
+ private boolean initSave = false;
+
+ public String getGameDataAsText() {
+ return gameData.metaDataAsText() + gameData.gameOptionsAsText() + gameData.playerNamesAsText();
+ }
+
+ public Game getGame() {
+ return loadedGame;
+ }
+
+ public List<PossibleAction> getActions() {
+ return gameData.actions;
+ }
+
+ public void setActions(List<PossibleAction> actions) {
+ gameData.actions = actions;
+ }
+
+ public SortedMap<Integer, String> getComments() {
+ return gameData.userComments;
+ }
+
+ public void setComments(SortedMap<Integer, String> comments) {
+ gameData.userComments = comments;
+ }
+
+ @SuppressWarnings("unchecked")
+ public void loadGameData(String filepath) {
+
+ dataLoadDone = true;
+
+ log.info("Loading game from file " + filepath);
+ String filename = filepath.replaceAll(".*[/\\\\]", "");
+
+ try {
+ ois = new ObjectInputStream(new FileInputStream(
+ new File(filepath)));
+
+ Object object = ois.readObject();
+ if (object instanceof String) {
+ // New in 1.0.7: Rails version & save date/time.
+ gameData.meta.version = (String)object;
+ object = ois.readObject();
+ } else {
+ // Allow for older saved file versions.
+ gameData.meta.version = "pre-1.0.7";
+ }
+
+ log.info("Reading Rails " + gameData.meta.version +" saved file "+filename);
+
+ if (object instanceof String) {
+ gameData.meta.date = (String)object;
+ log.info("File was saved at "+ gameData.meta.date);
+ object = ois.readObject();
+ }
+
+ // read versionID for serialization compatibility
+ gameData.meta.fileVersionID = (Long) object;
+ log.debug("Saved versionID="+gameData.meta.fileVersionID+" (object="+object+")");
+ long GMsaveFileVersionID = GameManager.saveFileVersionID;
+
+ if (gameData.meta.fileVersionID != GMsaveFileVersionID) {
+ throw new Exception("Save version " + gameData.meta.fileVersionID
+ + " is incompatible with current version "
+ + GMsaveFileVersionID);
+ }
+
+ // read name of saved game
+ gameData.meta.gameName = (String) ois.readObject();
+ log.debug("Saved game="+ gameData.meta.gameName);
+
+ // read selected game options and player names
+ gameData.gameOptions = (Map<String, String>) ois.readObject();
+ log.debug("Selected game options = " + gameData.gameOptions);
+ gameData.playerNames = (List<String>) ois.readObject();
+ log.debug("Player names = " + gameData.playerNames);
+
+ } catch (Exception e) {
+ dataLoadDone = false;
+ log.fatal("Load failed", e);
+ DisplayBuffer.add(LocalText.getText("LoadFailed", e.getMessage()));
+ }
+ }
+
+ public Game initGame() throws ConfigurationException {
+
+ // check if initial load was done
+ if (!dataLoadDone) {
+ throw new ConfigurationException("No game was loaded");
+ }
+
+ // initialize loadedGame
+ loadedGame = new Game(gameData.meta.gameName, gameData.playerNames, gameData.gameOptions);
+
+ if (!loadedGame.setup()) {
+ loadedGame = null;
+ throw new ConfigurationException("Error in setting up " + gameData.meta.gameName);
+ }
+
+ String startError = loadedGame.start();
+ if (startError != null) {
+ DisplayBuffer.add(startError);
+ }
+
+ return loadedGame;
+ }
+
+
+ @SuppressWarnings("unchecked")
+ public boolean loadActionsAndComments() throws ConfigurationException {
+ if (!dataLoadDone) {
+ throw new ConfigurationException("No game was loaded");
+ }
+ // Read game actions into gameData.listOfActions
+ try {
+ // read next object in stream
+ Object actionObject = null;
+ while (true) { // Single-pass loop.
+ try {
+ actionObject = ois.readObject();
+ } catch (EOFException e) {
+ // Allow saved file at start of game (with no actions).
+ break;
+
+ }
+ if (actionObject instanceof List) {
+ // Until Rails 1.3: one List of PossibleAction
+ gameData.actions = (List<PossibleAction>) actionObject;
+ } else if (actionObject instanceof PossibleAction) {
+ gameData.actions = new ArrayList<PossibleAction>();
+ // Since Rails 1.3.1: separate PossibleActionsObjects
+ while (actionObject instanceof PossibleAction) {
+ gameData.actions.add((PossibleAction)actionObject);
+ try {
+ actionObject = ois.readObject();
+ } catch (EOFException e) {
+ break;
+ }
+ }
+ }
+ break;
+ }
+ /**
+ todo: the code below is far from perfect, but robust
+ */
+
+ // init user comments to have a defined object in any case
+ gameData.userComments = new TreeMap<Integer,String>();
+
+ // at the end of file user comments are added as SortedMap
+ if (actionObject instanceof SortedMap) {
+ gameData.userComments = (SortedMap<Integer, String>) actionObject;
+ log.debug("file load: found user comments");
+ } else {
+ try {
+ Object object = ois.readObject();
+ if (object instanceof SortedMap) {
+ gameData.userComments = (SortedMap<Integer, String>) actionObject;
+ log.debug("file load: found user comments");
+ }
+ } catch (IOException e) {
+ // continue without comments, if any IOException occurs
+ // sometimes not only the EOF Exception is raised
+ // but also the java.io.StreamCorruptedException: invalid type code
+ }
+ }
+ ois.close();
+ ois = null;
+ initialized = true;
+ } catch (Exception e) {
+ log.fatal("Load failed", e);
+ DisplayBuffer.add(LocalText.getText("LoadFailed", e.getMessage()));
+ initialized = false;
+ }
+ return initialized;
+ }
+
+ public void replayGame() throws Exception {
+ if (!initialized) {
+ throw new ConfigurationException("No game was loaded/initialized");
+ }
+
+ GameManagerI gameManager = loadedGame.getGameManager();
+ log.debug("Starting to execute loaded actions");
+ gameManager.setReloading(true);
+
+ for (PossibleAction action : gameData.actions) {
+ if (!gameManager.processOnReload(action)) {
+ log.error ("Load interrupted");
+ DisplayBuffer.add(LocalText.getText("LoadInterrupted"));
+ break;
+ }
+ }
+
+ gameManager.setReloading(false);
+ ReportBuffer.setCommentItems(gameData.userComments);
+
+ // callback to GameManager
+ gameManager.finishLoading();
+ }
+
+ /**
+ * sets the meta data required for a game save
+ */
+ public void initSave(Long saveFileVersionID, String gameName, Map<String, String> gameOptions, List<String> playerNames) {
+ gameData.meta.version = Game.version+" "+BuildInfo.buildDate;
+ gameData.meta.date = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(new Date());
+ gameData.meta.fileVersionID = saveFileVersionID;
+ gameData.meta.gameName = gameName;
+ gameData.gameOptions = gameOptions;
+ gameData.playerNames = playerNames;
+ initSave = true;
+ }
+
+ /**
+ * Stores the game to a file
+ * requires initSave and setting actions and comments
+ */
+ public boolean saveGame(File file, boolean displayErrorMessage, String errorMessageKey) {
+ if (!initSave || gameData.actions == null) return false;
+ boolean result = false;
+
+ try {
+ ObjectOutputStream oos =
+ new ObjectOutputStream(new FileOutputStream(file));
+ oos.writeObject(gameData.meta.version);
+ oos.writeObject(gameData.meta.date);
+ oos.writeObject(gameData.meta.fileVersionID);
+ oos.writeObject(gameData.meta.gameName);
+ oos.writeObject(gameData.gameOptions);
+ oos.writeObject(gameData.playerNames);
+ for (PossibleAction action : gameData.actions) {
+ oos.writeObject(action);
+ }
+ oos.writeObject(gameData.userComments);
+ oos.close();
+
+ result = true;
+ } catch (IOException e) {
+ log.error(errorMessageKey, e);
+ if (displayErrorMessage) {
+ DisplayBuffer.add(LocalText.getText("SaveFailed", e.getMessage()));
+ }
+ }
+ return result;
+ }
+
+}
Property changes on: trunk/18xx/rails/util/GameFileIO.java
___________________________________________________________________
Added: svn:mime-type
+ text/plain
Deleted: trunk/18xx/rails/util/GameLoader.java
===================================================================
--- trunk/18xx/rails/util/GameLoader.java 2011-07-05 17:03:23 UTC (rev 1604)
+++ trunk/18xx/rails/util/GameLoader.java 2011-07-06 05:39:16 UTC (rev 1605)
@@ -1,252 +0,0 @@
-package rails.util;
-
-import java.io.EOFException;
-import java.io.File;
-import java.io.FileInputStream;
-import java.io.IOException;
-import java.io.ObjectInputStream;
-import java.util.ArrayList;
-import java.util.List;
-import java.util.Map;
-import java.util.SortedMap;
-import java.util.TreeMap;
-
-import org.apache.log4j.Logger;
-
-import rails.common.DisplayBuffer;
-import rails.common.LocalText;
-import rails.common.parser.ConfigurationException;
-import rails.game.Game;
-import rails.game.GameManager;
-import rails.game.GameManagerI;
-import rails.game.ReportBuffer;
-import rails.game.action.PossibleAction;
-
-/**
- * @author freystef
- *
- */
-public class GameLoader {
-
- protected static Logger log =
- Logger.getLogger(Game.class.getPackage().getName());
-
- private boolean dataLoadDone;
- private boolean initialized;
-
- private ObjectInputStream ois;
-
- private String saveVersion;
- private String saveDate;
- private Long saveFileVersionID;
- private String saveGameName;
- private Map<String, String> selectedGameOptions;
- private List<String> playerNames;
- private List<PossibleAction> listOfActions;
- private SortedMap<Integer, String> userComments;
-
- private Game loadedGame;
-
- public String getGameData() {
- StringBuilder s = new StringBuilder();
- s.append("Rails saveVersion = " + saveVersion + "\n");
- s.append("File was saved at " + saveDate + "\n");
- s.append("Saved versionID=" + saveFileVersionID + "\n");
- s.append("Save game=" + saveGameName + "\n");
- for (String key : selectedGameOptions.keySet()) {
- s.append("Option "+key+"="+selectedGameOptions.get(key)+ "\n");
- }
- int i=1;
- for (String player : playerNames) {
- s.append("Player "+(i++)+": "+player + "\n");
- }
- return s.toString();
- }
-
- public Game getGame() {
- return loadedGame;
- }
-
- public List<PossibleAction> getActions() {
- return listOfActions;
- }
-
- public SortedMap<Integer, String> getComments() {
- return userComments;
- }
-
- @SuppressWarnings("unchecked")
- public void loadGameData(String filepath) {
-
- dataLoadDone = true;
- log.info("Loading game from file " + filepath);
- String filename = filepath.replaceAll(".*[/\\\\]", "");
-
- try {
- ois = new ObjectInputStream(new FileInputStream(
- new File(filepath)));
-
- Object object = ois.readObject();
- if (object instanceof String) {
- // New in 1.0.7: Rails version & save date/time.
- saveVersion = (String)object;
- object = ois.readObject();
- } else {
- // Allow for older saved file versions.
- saveVersion = "pre-1.0.7";
- }
-
- log.info("Reading Rails " + saveVersion +" saved file "+filename);
-
- if (object instanceof String) {
- saveDate = (String)object;
- log.info("File was saved at "+ saveDate);
- object = ois.readObject();
- }
-
- // read versionID for serialization compatibility
- saveFileVersionID = (Long) object;
- log.debug("Saved versionID="+saveFileVersionID+" (object="+object+")");
- long GMsaveFileVersionID = GameManager.saveFileVersionID;
-
- if (saveFileVersionID != GMsaveFileVersionID) {
- throw new Exception("Save version " + saveFileVersionID
- + " is incompatible with current version "
- + GMsaveFileVersionID);
- }
-
- // read name of saved game
- saveGameName = (String) ois.readObject();
- log.debug("Saved game="+ saveGameName);
-
- // read selected game options and player names
- selectedGameOptions = (Map<String, String>) ois.readObject();
- log.debug("Selected game options = " + selectedGameOptions);
- playerNames = (List<String>) ois.readObject();
- log.debug("Player names = " + playerNames);
-
- } catch (Exception e) {
- log.fatal("Load failed", e);
- DisplayBuffer.add(LocalText.getText("LoadFailed", e.getMessage()));
- }
-
-
- }
-
- public Game initGame() throws ConfigurationException {
-
- // check if initial load was done
- if (!dataLoadDone) {
- throw new ConfigurationException("No game was loaded");
- }
-
- // initialize loadedGame
- loadedGame = new Game(saveGameName, playerNames, selectedGameOptions);
-
- if (!loadedGame.setup()) {
- loadedGame = null;
- throw new ConfigurationException("Error in setting up " + saveGameName);
- }
-
- String startError = loadedGame.start();
- if (startError != null) {
- DisplayBuffer.add(startError);
- }
-
- return loadedGame;
- }
-
-
- @SuppressWarnings("unchecked")
- public boolean loadActionsAndComments() throws ConfigurationException {
- if (!dataLoadDone) {
- throw new ConfigurationException("No game was loaded");
- }
- // Read game actions into listOfActions
- try {
- // read next object in stream
- Object actionObject = null;
- while (true) { // Single-pass loop.
- try {
- actionObject = ois.readObject();
- } catch (EOFException e) {
- // Allow saved file at start of game (with no actions).
- break;
-
- }
- if (actionObject instanceof List) {
- // Until Rails 1.3: one List of PossibleAction
- listOfActions = (List<PossibleAction>) actionObject;
- } else if (actionObject instanceof PossibleAction) {
- listOfActions = new ArrayList<PossibleAction>();
- // Since Rails 1.3.1: separate PossibleActionsObjects
- while (actionObject instanceof PossibleAction) {
- listOfActions.add((PossibleAction)actionObject);
- try {
- actionObject = ois.readObject();
- } catch (EOFException e) {
- break;
- }
- }
- }
- break;
- }
- /**
- todo: the code below is far from perfect, but robust
- */
-
- // init user comments to have a defined object in any case
- userComments = new TreeMap<Integer,String>();
-
- // at the end of file user comments are added as SortedMap
- if (actionObject instanceof SortedMap) {
- userComments = (SortedMap<Integer, String>) actionObject;
- log.debug("file load: found user comments");
- } else {
- try {
- Object object = ois.readObject();
- if (object instanceof SortedMap) {
- userComments = (SortedMap<Integer, String>) actionObject;
- log.debug("file load: found user comments");
- }
- } catch (IOException e) {
- // continue without comments, if any IOException occurs
- // sometimes not only the EOF Exception is raised
- // but also the java.io.StreamCorruptedException: invalid type code
- }
- }
- ois.close();
- ois = null;
- initialized = true;
- } catch (Exception e) {
- log.fatal("Load failed", e);
- DisplayBuffer.add(LocalText.getText("LoadFailed", e.getMessage()));
- initialized = false;
- }
- return initialized;
- }
-
- public void replayGame() throws Exception {
- if (!initialized) {
- throw new ConfigurationException("No game was loaded/initialized");
- }
-
- GameManagerI gameManager = loadedGame.getGameManager();
- log.debug("Starting to execute loaded actions");
- gameManager.setReloading(true);
-
- for (PossibleAction action : listOfActions) {
- if (!gameManager.processOnReload(action)) {
- log.error ("Load interrupted");
- DisplayBuffer.add(LocalText.getText("LoadInterrupted"));
- break;
- }
- }
-
- gameManager.setReloading(false);
- ReportBuffer.setCommentItems(userComments);
-
- // callback to GameManager
- gameManager.finishLoading();
- }
-}
Modified: trunk/18xx/rails/util/ListAndFixSavedFiles.java
===================================================================
--- trunk/18xx/rails/util/ListAndFixSavedFiles.java 2011-07-05 17:03:23 UTC (rev 1604)
+++ trunk/18xx/rails/util/ListAndFixSavedFiles.java 2011-07-06 05:39:16 UTC (rev 1605)
@@ -165,10 +165,10 @@
saveDirectory = selectedFile.getParent();
// use GameLoader object to load game
- GameLoader gameLoader = new GameLoader();
+ GameFileIO gameLoader = new GameFileIO();
gameLoader.loadGameData(filepath);
- add(gameLoader.getGameData());
+ add(gameLoader.getGameDataAsText());
try{
gameLoader.initGame();
gameLoader.loadActionsAndComments();
This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site.
|