You can subscribe to this list here.
2008 |
Jan
|
Feb
|
Mar
|
Apr
|
May
|
Jun
|
Jul
|
Aug
|
Sep
|
Oct
(3) |
Nov
(46) |
Dec
(57) |
---|---|---|---|---|---|---|---|---|---|---|---|---|
2009 |
Jan
(51) |
Feb
(10) |
Mar
|
Apr
|
May
(14) |
Jun
|
Jul
(13) |
Aug
(30) |
Sep
(83) |
Oct
(56) |
Nov
(148) |
Dec
(107) |
2010 |
Jan
(260) |
Feb
(164) |
Mar
(183) |
Apr
(99) |
May
(160) |
Jun
(40) |
Jul
(33) |
Aug
(48) |
Sep
(22) |
Oct
(24) |
Nov
(1) |
Dec
(12) |
2011 |
Jan
(6) |
Feb
(15) |
Mar
(13) |
Apr
(37) |
May
(27) |
Jun
(29) |
Jul
(33) |
Aug
(20) |
Sep
(17) |
Oct
(20) |
Nov
(33) |
Dec
(17) |
2012 |
Jan
(39) |
Feb
(38) |
Mar
(20) |
Apr
(21) |
May
(17) |
Jun
(22) |
Jul
(16) |
Aug
(3) |
Sep
(9) |
Oct
(10) |
Nov
|
Dec
|
From: Brett L. <wak...@us...> - 2011-09-21 13:10:41
|
rails/game/StartRound_1830.java | 4 ++++ 1 file changed, 4 insertions(+) New commits: commit 4a170a460e1adc1cc8c3882e6541d7b18a12f2ef Author: Bill Rosgen <ro...@gm...> Date: Wed Sep 21 16:25:08 2011 +0800 bug fix: 1830-stye initial auction should advance player after price is reduced on first item diff --git a/rails/game/StartRound_1830.java b/rails/game/StartRound_1830.java index eef05f1..517a470 100644 --- a/rails/game/StartRound_1830.java +++ b/rails/game/StartRound_1830.java @@ -354,6 +354,10 @@ public class StartRound_1830 extends StartRound { startPacket.getFirstItem(), 0, 0); gameManager.setPriorityPlayer(); // startPacket.getFirstItem().getName()); + } else { + //BR: If the first item's price is reduced, but not to 0, + // we still need to advance to the next player + setNextPlayer(); } } else { numPasses.set(0); |
From: Stefan F. <ste...@us...> - 2011-09-20 10:11:24
|
rails/algorithms/NetworkVertex.java | 5 +++-- rails/game/Stop.java | 4 ++-- 2 files changed, 5 insertions(+), 4 deletions(-) New commits: commit 6f0ec2417866c9861df2845add71c584b952d421 Author: Stefan Frey <ste...@we...> Date: Tue Sep 20 12:13:06 2011 +0200 Fixed missing check for no-tokens stop in runthrough allowed method diff --git a/rails/algorithms/NetworkVertex.java b/rails/algorithms/NetworkVertex.java index cbe5394..91356af 100644 --- a/rails/algorithms/NetworkVertex.java +++ b/rails/algorithms/NetworkVertex.java @@ -227,8 +227,9 @@ public final class NetworkVertex implements Comparable<NetworkVertex> { // check if it has to be removed because it is run-to only // if company == null, then no vertex gets removed - if (company != null && !city.isRunToAllowedFor(company)) { - return false; + if (company != null && !city.isRunToAllowedFor(company)) { + log.info("Vertex is removed"); + return false; } // check if it is a major or minor diff --git a/rails/game/Stop.java b/rails/game/Stop.java index 7bf116a..d1e918c 100644 --- a/rails/game/Stop.java +++ b/rails/game/Stop.java @@ -344,8 +344,8 @@ public class Stop implements TokenHolder { public boolean isRunThroughAllowedFor (PublicCompanyI company) { switch (runThroughAllowed) { - case YES: - return hasTokenOf (company) || hasTokenSlotsLeft(); + case YES: // either it has no tokens at all, or it has a company tokens or empty token slots + return !hasTokens() || hasTokenOf (company) || hasTokenSlotsLeft() ; case NO: return false; case TOKENONLY: |
From: Brett L. <wak...@us...> - 2011-09-19 21:47:52
|
data/1830/TileSet.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) New commits: commit bd0f038dd8fc9efa6cbbb9960a87fb3cbc10c4d1 Author: Adam Badura <ab...@o2...> Date: Mon Sep 19 22:08:55 2011 +0200 Another fix for 1830 Wabash diff --git a/data/1830/TileSet.xml b/data/1830/TileSet.xml index 33d35b7..a50a2b0 100644 --- a/data/1830/TileSet.xml +++ b/data/1830/TileSet.xml @@ -174,7 +174,7 @@ </Tile> </IfOption> <Tile id="54" quantity="1"> - <IfOption name="Variant" value="Basegame,Pere Marquette,Reading,Simple"> + <IfOption name="Variant" value="Basegame,Pere Marquette,Reading,Simple,Wabash"> <Upgrade id="62" /> </IfOption> <IfOption name="Variant" value="Coalfields,Coalfields&Reading"> |
From: Erik V. <ev...@us...> - 2011-09-18 22:01:55
|
data/1830/TileSet.xml | 7 ++----- 1 file changed, 2 insertions(+), 5 deletions(-) New commits: commit 5f9c074c8b44070dc47282b509b5046fd96d5a9b Author: Erik Vos <eri...@xs...> Date: Sun Sep 18 23:58:27 2011 +0200 Fixed some missing tiles in 1830 Wabash diff --git a/data/1830/TileSet.xml b/data/1830/TileSet.xml index be759b6..33d35b7 100644 --- a/data/1830/TileSet.xml +++ b/data/1830/TileSet.xml @@ -210,7 +210,7 @@ <Tile id="1061" extId="61" quantity="1" /> <Tile id="2061" extId="BA" quantity="1" /> </IfOption> - <IfOption name="Variant" value="Basegame,Pere Marquette,Reading"> + <IfOption name="Variant" value="Basegame,Pere Marquette,Reading,Wabash"> <Tile id="62" quantity="1" /> </IfOption> <IfOption name="Variant" value="Simple"> @@ -221,10 +221,7 @@ <IfOption name="Variant" value="Coalfields,Coalfields&Reading"> <Tile id="1062" extId="62" quantity="1" /> </IfOption> - <Tile id="63"> - <IfOption name="Variant" value="Basegame,Pere Marquette,Reading,Simple"> - <Attributes quantity="3"/> - </IfOption> + <Tile id="63" quantity="3"> <IfOption name="Variant" value="Coalfields,Coalfields&Reading"> <Attributes quantity="4"/> </IfOption> |
From: Erik V. <ev...@us...> - 2011-09-18 15:13:59
|
data/18TN/CompanyManager.xml | 8 ++------ data/18TN/Game.xml | 4 ++-- 2 files changed, 4 insertions(+), 8 deletions(-) New commits: commit 25203f7d21bd3d23d9633dce14e6cbb3c65945f0 Author: Erik Vos <eri...@xs...> Date: Sun Sep 18 17:12:06 2011 +0200 Fixed 18TN configuration errors: - Purchase max. one train until phase 4 - No hex blocking by privates - Two yellow tiles allowed from the start diff --git a/data/18TN/CompanyManager.xml b/data/18TN/CompanyManager.xml index 282fe15..b08c3fb 100644 --- a/data/18TN/CompanyManager.xml +++ b/data/18TN/CompanyManager.xml @@ -20,14 +20,13 @@ <Certificate shares="1" number="8"/> <Trains limit="4,3,2"/> <CanUseSpecialProperties/> - <TileLays> - <Number colour="yellow" phase="3,3½,4,5,6,6½,8" number="2"/> + <TileLays> + <Number colour="yellow" phase="2,3,3½,4,5,6,6½,8" number="2"/> </TileLays> </CompanyType> <Company name="TCC" type="Private" basePrice="20" revenue="5" longname="Tennessee Copper Company"> - <Blocking hex="H17"/> <SpecialProperties> <SpecialProperty condition="ifOwnedByCompany" when="tileLayingStep" class="rails.game.special.SpecialTileLay"> <SpecialTileLay location="H17" extra="yes" free="yes"/> @@ -36,7 +35,6 @@ </Company> <Company name="ET&WNC" type="Private" basePrice="40" revenue="10" longname="East Tennessee and Western North Carolina"> - <Blocking hex="F19"/> <SpecialProperties> <SpecialProperty condition="ifOwnedByCompany" when="tileLayingStep" class="rails.game.special.SpecialTileLay"> <SpecialTileLay location="F19" extra="yes" free="yes"/> @@ -45,7 +43,6 @@ </Company> <Company name="M&C" type="Private" basePrice="70" revenue="15" longname="Memphis and Charleston Railroad"> - <Blocking hex="H3"/> <SpecialProperties> <SpecialProperty condition="ifOwnedByCompany" when="tileLayingStep" class="rails.game.special.SpecialTileLay"> <SpecialTileLay location="H5" extra="yes" free="yes"/> @@ -54,7 +51,6 @@ </Company> <Company name="O&W" type="Private" basePrice="100" revenue="20" longname="Oneida and Western Railroad"> - <Blocking hex="E16"/> <SpecialProperties> <SpecialProperty condition="ifOwnedByCompany" when="tileLayingStep" class="rails.game.special.SpecialTileLay"> <SpecialTileLay location="E16" extra="yes" free="yes"/> diff --git a/data/18TN/Game.xml b/data/18TN/Game.xml index 837b8e9..0a19ccc 100644 --- a/data/18TN/Game.xml +++ b/data/18TN/Game.xml @@ -93,7 +93,7 @@ <Tiles colour="yellow"/> <Privates sellingAllowed="no"/> <OperatingRounds number="1"/> - <Trains tradingAllowed="yes"/> + <Trains onePerTurn="yes" tradingAllowed="yes"/> </Phase> <Phase name="3"> <Tiles colour="yellow,green"/> @@ -104,7 +104,7 @@ <Action name="CivilWar"/><!-- No value needed --> </Phase> <Phase name="4"> - <Trains rusted="2" limitStep="2"/> + <Trains rusted="2" limitStep="2" onePerTurn="no"/> </Phase> <Phase name="5"> <Tiles colour="yellow,green,brown"/> |
From: Stefan F. <ste...@us...> - 2011-09-08 12:43:23
|
build.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) New commits: commit f34f8b0f901130853fe2d24072048d85a63940c5 Author: Stefan Frey <ste...@we...> Date: Thu Sep 8 14:45:34 2011 +0200 Updated for the new Junit 4.8.2 library diff --git a/build.xml b/build.xml index 03699f2..00fcd78 100644 --- a/build.xml +++ b/build.xml @@ -24,7 +24,7 @@ <pathelement location="lib/batik-1.7/lib/batik-ext.jar"/> <pathelement location="lib/jgraph5/jgraph.jar"/> <pathelement location="lib/jgrapht-0.7.3/jgrapht-jdk1.5.jar"/> - <pathelement location="lib/junit_3.8.2/junit.jar"/> + <pathelement location="lib/junit-4.8.2/junit.jar"/> </path> <target depends="clean" name="init"> <mkdir dir="classes"/> |
From: Stefan F. <ste...@us...> - 2011-09-05 05:52:58
|
data/GamesList.xml | 33 +++++++++++++++++++-------------- 1 file changed, 19 insertions(+), 14 deletions(-) New commits: commit fe1526fecf551fee2bf6a48dc94fab961eae7ce9 Author: Stefan Frey <ste...@we...> Date: Mon Sep 5 07:53:17 2011 +0200 Changed 18TN to fully playable and added copyright information diff --git a/data/GamesList.xml b/data/GamesList.xml index bd703b5..63b992c 100644 --- a/data/GamesList.xml +++ b/data/GamesList.xml @@ -140,7 +140,7 @@ Not yet implemented: </Game> <Game name="18GA"> - <Note>Fully Playable</Note> + <Note>Fully playable</Note> <Description>18GA - The Railroads Come to Georgia Copyright 2000, 2007, Mark Derrick and John David Galt</Description> <Option name="Variant" values="Basegame,Cotton Port" default="Basegame" /> @@ -174,7 +174,24 @@ Should work, but has not been extensively tested. Limitations as with 1830. <Option name="SeparateSalesAtSamePrice" type="toggle" default="yes"/> <Players minimum="3" maximum="6"/> </Game> - + + <Game name="18TN"> + <Note>Fully playable</Note> + <Description>18TN - The Railroads Come to Tennessee + Copyright 1996, 2006, Mark Derrick + Published by Deep Thought Games, LLC + + </Description> + <Option name="RouteAwareness" values="Highlight,Deactivate" default="Highlight" /> + <Option name="RevenueCalculation" values="Suggest,Deactivate" default="Suggest" /> + <Option name="NoMapMode" type="toggle" default="no" /> + <Option name="UnlimitedTiles" type="toggle" default="no"/> + <Option name="UnlimitedTopTrains" parm="8" type="toggle" default="no"/> + <Option name="LeaveAuctionOnPass" type="toggle" default="no"/> + <Option name="TwoPlayersCertLimit70Percent" type="toggle" default="no"/> + <Players minimum="2" maximum="5"/> + </Game> + <Game name="1835"> <Note>Almost playable</Note> <Description>1835 (Germany) @@ -290,18 +307,6 @@ Known Issues: <Players minimum="2" maximum="5" /> </Game> - <Game name="18TN"> - <Note>Prototype</Note> - <Description>18TN - The Railroads Come to Tennessee</Description> - <Option name="RouteAwareness" values="Highlight,Deactivate" default="Highlight" /> - <Option name="RevenueCalculation" values="Suggest,Deactivate" default="Suggest" /> - <Option name="NoMapMode" type="toggle" default="no" /> - <Option name="UnlimitedTiles" type="toggle" default="no"/> - <Option name="UnlimitedTopTrains" parm="8" type="toggle" default="no"/> - <Option name="LeaveAuctionOnPass" type="toggle" default="no"/> - <Option name="TwoPlayersCertLimit70Percent" type="toggle" default="no"/> - <Players minimum="2" maximum="5"/> - </Game> <Game name="1880"> <Note>Prototype</Note> <Description>1880 - China |
From: Stefan F. <ste...@us...> - 2011-08-25 19:55:41
|
rails/common/parser/GameOption.java | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) New commits: commit 8f7435c4885f0976d4cad7504a5915848a4cf56a Author: Stefan Frey <ste...@we...> Date: Thu Aug 25 21:58:00 2011 +0200 Removed Bill Rosgen fix for GameOption. Was unnecessary due to fix of Adam Badura. diff --git a/rails/common/parser/GameOption.java b/rails/common/parser/GameOption.java index aa893df..395203c 100644 --- a/rails/common/parser/GameOption.java +++ b/rails/common/parser/GameOption.java @@ -60,10 +60,7 @@ public class GameOption { } public String getName() { - if (parametrisedName != null) - return parametrisedName; - - return name; + return parametrisedName; } public String getLocalisedName() { |
From: Stefan F. <ste...@us...> - 2011-08-25 05:52:58
|
LocalisedText.properties | 1 + rails/common/parser/GameOption.java | 3 ++- tiles/Create_TileDictionary_pdf.sh | 4 ++-- 3 files changed, 5 insertions(+), 3 deletions(-) New commits: commit 6e25c4b3ca3ecb705741cf7877181b3830e9fc11 Author: Stefan Frey <ste...@we...> Date: Thu Aug 25 07:50:35 2011 +0200 Patch from "Adam Badura" <ab...@o2...>: (1) There is a localized string missing for 1830 option. (2) There was bug in game options parsing from XML. Non-parametrized names did not initialized the name that they then returned resulting in options being overwritten in maps as they have had all ânullâ name. diff --git a/LocalisedText.properties b/LocalisedText.properties index b0750ce..a0dad56 100644 --- a/LocalisedText.properties +++ b/LocalisedText.properties @@ -61,6 +61,7 @@ BuysRight={0} buys the ''{1}'' right for {2} BuysTrain={0} buys a {1}-train from {2} for {3}. BuysTrainUsingSP={0} buys a {1}-train from {2} for {3} using {4}. BYFloatsAt=Bayern floats at +C&ACertificate(ReadingOnly)=C&A Certificate (Reading variant only) CASH=Cash CANCEL=Cancel CanOperate={0} can operate this round diff --git a/rails/common/parser/GameOption.java b/rails/common/parser/GameOption.java index 009f9e0..aa893df 100644 --- a/rails/common/parser/GameOption.java +++ b/rails/common/parser/GameOption.java @@ -32,7 +32,8 @@ public class GameOption { private static final Pattern pattern = Pattern.compile("\\{(.*)\\}"); public GameOption(String name) { - this.name = name; + this.name = name; + parametrisedName = constructParametrisedName (name, null); } public GameOption(String name, String[] parameters) { commit d389ae0a8372a86e59a697e9dcb6089397a09f1d Author: Stefan Frey <ste...@we...> Date: Wed Aug 24 07:15:47 2011 +0200 Updated paths for tools inside shell script diff --git a/tiles/Create_TileDictionary_pdf.sh b/tiles/Create_TileDictionary_pdf.sh index de3c719..0c521fa 100755 --- a/tiles/Create_TileDictionary_pdf.sh +++ b/tiles/Create_TileDictionary_pdf.sh @@ -1,13 +1,13 @@ # !/bin/bash # author Stefan Frey -# requires installed tools: java, batik library, mmv and imagemagick (montage command) +# requires installed tools: mmv and imagemagick (montage command) # use whereis to retrieve path information # creates temporary directory mkdir svg_catalog_tmp # convert svg to png -java -jar /usr/share/batik/batik-rasterizer.jar -d svg_catalog_tmp/ -w 400 -h 400 -dpi 400 -m image/png svg/ +java -jar ../lib/batik-1.7/batik-rasterizer.jar -d svg_catalog_tmp/ -w 400 -h 400 -dpi 400 -m image/png svg/ # rename to have all filenames in -xxxxx.png notation /usr/bin/mmv 'svg_catalog_tmp/tile0.png' 'svg_catalog_tmp/m00000.png' |
From: Brett L. <wak...@us...> - 2011-08-22 04:35:58
|
Tag 'v1.4.3' created by Brett Lentz <bl...@cl...> at 2011-08-22 04:35 +0000 Rails v1.4.3 Changes since v1.4.2-95: --- 0 files changed --- |
From: Erik V. <ev...@us...> - 2011-08-17 09:17:40
|
data/1830/TileSet.xml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) New commits: commit 182ef16766661a56bea34448c59c32411c862eaf Merge: 346577b 1c25df5 Author: Erik Vos <eri...@xs...> Date: Wed Aug 17 11:17:31 2011 +0200 Merge branch 'master' of ssh://ev...@ra.../gitroot/rails/rails commit 346577b82749da26a1fa6a89bb63181aeb0119cf Author: Erik Vos <eri...@xs...> Date: Wed Aug 17 11:14:43 2011 +0200 Fix by Bill Rosgen: Tile #15 upgrade in Reading variant diff --git a/data/1830/TileSet.xml b/data/1830/TileSet.xml index 9485b32..be759b6 100644 --- a/data/1830/TileSet.xml +++ b/data/1830/TileSet.xml @@ -120,7 +120,7 @@ <IfOption name="Variant" value="Wabash"> <Upgrade id="63,448"/> </IfOption> - <IfOption name="Variant" value="Basegame,Pere Marquette,Coalfields,Coalfields&Reading,Simple"> + <IfOption name="Variant" value="Basegame,Pere Marquette,Coalfields,Coalfields&Reading,Reading,Simple"> <Upgrade id="63" /> </IfOption> </Tile> |
From: Stefan F. <ste...@us...> - 2011-08-17 05:27:37
|
rails/algorithms/NetworkVertex.java | 28 +++++++--------------------- 1 file changed, 7 insertions(+), 21 deletions(-) New commits: commit 1c25df567ee6d094b10b6026cbb924931733f622 Author: Stefan Frey <ste...@we...> Date: Wed Aug 17 06:47:24 2011 +0200 NetworkVertex uses new functions in Stop class diff --git a/rails/algorithms/NetworkVertex.java b/rails/algorithms/NetworkVertex.java index 05ae58c..cbe5394 100644 --- a/rails/algorithms/NetworkVertex.java +++ b/rails/algorithms/NetworkVertex.java @@ -226,33 +226,23 @@ public final class NetworkVertex implements Comparable<NetworkVertex> { log.info("Init of vertex " + this); // check if it has to be removed because it is run-to only - if (company != null) { // if company == null, then no vertex gets removed - if (hex.isRunToAllowed() == Stop.RunTo.NO || hex.isRunToAllowed() == Stop.RunTo.TOKENONLY && !city.hasTokenOf(company)) - { + // if company == null, then no vertex gets removed + if (company != null && !city.isRunToAllowedFor(company)) { return false; - } } // check if it is a major or minor - if (station.getType().equals(Station.CITY) || station.getType().equals(Station.OFF_MAP_AREA)) { + if (city.getScoreType() == Stop.Score.MAJOR) { setStationType(StationType.MAJOR); - } else if (station.getType().equals(Station.TOWN) || station.getType().equals(Station.PORT) - || station.getType().equals(Station.HALT)) { + } else if (city.getScoreType() == Stop.Score.MINOR) { setStationType(StationType.MINOR); } // check if it is a sink if (company == null) { // if company == null, then all sinks are deactivated sink = false; - } else if (station.getType().equals(Station.OFF_MAP_AREA) || ( - // or station is city - station.getType().equals(Station.CITY) - // and is either fully tokened and has token slots or only tokens allow run through - && ( city.getSlots() != 0 && !city.hasTokenSlotsLeft() || hex.isRunThroughAllowed() == Stop.RunThrough.TOKENONLY) - // and city does not have a token - && !city.hasTokenOf(company)) - ) { - sink = true; + } else { + sink = !city.isRunThroughAllowedFor(company); } // define locationName @@ -278,11 +268,7 @@ public final class NetworkVertex implements Comparable<NetworkVertex> { if (virtual || type == VertexType.SIDE) return; // define value - if (hex.hasValuesPerPhase()) { - value = hex.getCurrentValueForPhase(phase); - } else { - value = station.getValue(); - } + value = city.getValueForPhase(phase); } |
From: Erik V. <ev...@us...> - 2011-08-15 20:07:35
|
data/1830/CompanyManager.xml | 2 +- rails/common/parser/GameOption.java | 5 ++++- 2 files changed, 5 insertions(+), 2 deletions(-) New commits: commit be6c0003bb345032e3e046b312834bb90e54160e Author: Erik Vos <eri...@xs...> Date: Mon Aug 15 22:06:43 2011 +0200 Fixes by Bill Rosgen: 1830 Reading C&O home, and GameOption names. diff --git a/data/1830/CompanyManager.xml b/data/1830/CompanyManager.xml index 769e079..3623f7f 100644 --- a/data/1830/CompanyManager.xml +++ b/data/1830/CompanyManager.xml @@ -90,7 +90,7 @@ </Company> <Company name="C&O" type="Public" tokens="3" fgColour="000000" bgColour="A0E0FF" longname="Chesapeake & Ohio"> - <IfOption name="Variant" value="Basegame,Pere Marquette,Simple,Wabash"> + <IfOption name="Variant" value="Basegame,Pere Marquette,Reading,Simple,Wabash"> <Home hex="F6"/> </IfOption> <IfOption name="Variant" value="Coalfields,Coalfields&Reading"> diff --git a/rails/common/parser/GameOption.java b/rails/common/parser/GameOption.java index 3889dd7..009f9e0 100644 --- a/rails/common/parser/GameOption.java +++ b/rails/common/parser/GameOption.java @@ -59,7 +59,10 @@ public class GameOption { } public String getName() { - return parametrisedName; + if (parametrisedName != null) + return parametrisedName; + + return name; } public String getLocalisedName() { |
From: Erik V. <ev...@us...> - 2011-08-14 21:23:07
|
rails/ui/swing/GameStatus.java | 207 +++++++++++++++++++---------------------- 1 file changed, 97 insertions(+), 110 deletions(-) New commits: commit 0a746d147813b99417ec229d39d4b32e359732f0 Author: Erik Vos <eri...@xs...> Date: Sun Aug 14 23:21:14 2011 +0200 Fixed player highlighting in GameStatus window after a change in player order. diff --git a/rails/ui/swing/GameStatus.java b/rails/ui/swing/GameStatus.java index 41389af..71a1ce4 100644 --- a/rails/ui/swing/GameStatus.java +++ b/rails/ui/swing/GameStatus.java @@ -113,11 +113,11 @@ public class GameStatus extends GridPanel implements ActionListener { protected ClickField dummyButton; // To be selected if none else is. protected Map<PublicCompanyI, Integer> companyIndex = - new HashMap<PublicCompanyI, Integer>(); + new HashMap<PublicCompanyI, Integer>(); protected Map<Player, Integer> playerIndex = new HashMap<Player, Integer>(); protected static Logger log = - Logger.getLogger(GameStatus.class.getPackage().getName()); + Logger.getLogger(GameStatus.class.getPackage().getName()); public GameStatus() { super(); @@ -271,8 +271,8 @@ public class GameStatus extends GridPanel implements ActionListener { if (compCanHoldOwnShares) { addField(treasurySharesCaption = - new Caption(LocalText.getText("TREASURY_SHARES")), - certInTreasuryXOffset, 0, 1, 2, WIDE_RIGHT + WIDE_BOTTOM, true); + new Caption(LocalText.getText("TREASURY_SHARES")), + certInTreasuryXOffset, 0, 1, 2, WIDE_RIGHT + WIDE_BOTTOM, true); } if (this.hasParPrices) { @@ -289,7 +289,7 @@ public class GameStatus extends GridPanel implements ActionListener { } addField(new Caption(LocalText.getText("COMPANY_DETAILS")), compCashXOffset, 0, 4 + (compCanBuyPrivates ? 1 : 0) - + (hasCompanyLoans ? 1 : 0), 1, 0, true); + + (hasCompanyLoans ? 1 : 0), 1, 0, true); addField(new Caption(LocalText.getText("CASH")), compCashXOffset, 1, 1, 1, WIDE_BOTTOM, true); addField(new Caption(LocalText.getText("REVENUE")), compRevenueXOffset, @@ -318,7 +318,7 @@ public class GameStatus extends GridPanel implements ActionListener { c = companies[i]; companyIndex.put(c, new Integer(i)); rowVisibilityObservers[i] - = new RowVisibility (this, certPerPlayerYOffset + i, c.getInGameModel(), false); + = new RowVisibility (this, certPerPlayerYOffset + i, c.getInGameModel(), false); boolean visible = rowVisibilityObservers[i].lastValue(); f = new Caption(c.getName()); @@ -328,29 +328,29 @@ public class GameStatus extends GridPanel implements ActionListener { for (int j = 0; j < np; j++) { f = - certPerPlayer[i][j] = - new Field( - players[j].getPortfolio().getShareModel( - c)); + certPerPlayer[i][j] = + new Field( + players[j].getPortfolio().getShareModel( + c)); addField(f, certPerPlayerXOffset + j, certPerPlayerYOffset + i, 1, 1, 0, visible); f = - certPerPlayerButton[i][j] = - new ClickField("", SELL_CMD, - LocalText.getText("ClickForSell"), - this, buySellGroup); + certPerPlayerButton[i][j] = + new ClickField("", SELL_CMD, + LocalText.getText("ClickForSell"), + this, buySellGroup); addField(f, certPerPlayerXOffset + j, certPerPlayerYOffset + i, 1, 1, 0, false); } f = certInIPO[i] = new Field(ipo.getShareModel(c)); addField(f, certInIPOXOffset, certInIPOYOffset + i, 1, 1, WIDE_LEFT, visible); f = - certInIPOButton[i] = - new ClickField( - certInIPO[i].getText(), - BUY_FROM_IPO_CMD, - LocalText.getText("ClickToSelectForBuying"), - this, buySellGroup); + certInIPOButton[i] = + new ClickField( + certInIPO[i].getText(), + BUY_FROM_IPO_CMD, + LocalText.getText("ClickToSelectForBuying"), + this, buySellGroup); addField(f, certInIPOXOffset, certInIPOYOffset + i, 1, 1, WIDE_LEFT, false); certInIPO[i].setPreferredSize(certInIPOButton[i].getPreferredSize()); @@ -358,29 +358,29 @@ public class GameStatus extends GridPanel implements ActionListener { addField(f, certInPoolXOffset, certInPoolYOffset + i, 1, 1, WIDE_RIGHT, visible); f = - certInPoolButton[i] = - new ClickField( - certInPool[i].getText(), - BUY_FROM_POOL_CMD, - LocalText.getText("ClickToSelectForBuying"), - this, buySellGroup); + certInPoolButton[i] = + new ClickField( + certInPool[i].getText(), + BUY_FROM_POOL_CMD, + LocalText.getText("ClickToSelectForBuying"), + this, buySellGroup); addField(f, certInPoolXOffset, certInPoolYOffset + i, 1, 1, WIDE_RIGHT, false); certInPool[i].setPreferredSize(certInIPOButton[i].getPreferredSize());/* sic */ if (compCanHoldOwnShares) { f = - certInTreasury[i] = - new Field(c.getPortfolio().getShareModel(c)); + certInTreasury[i] = + new Field(c.getPortfolio().getShareModel(c)); addField(f, certInTreasuryXOffset, certInTreasuryYOffset + i, 1, 1, WIDE_RIGHT, visible); f = - certInTreasuryButton[i] = - new ClickField( - certInTreasury[i].getText(), - BUY_FROM_POOL_CMD, - LocalText.getText("ClickForSell"), - this, buySellGroup); + certInTreasuryButton[i] = + new ClickField( + certInTreasury[i].getText(), + BUY_FROM_POOL_CMD, + LocalText.getText("ClickForSell"), + this, buySellGroup); addField(f, certInTreasuryXOffset, certInTreasuryYOffset + i, 1, 1, WIDE_RIGHT, false); certInTreasury[i].setPreferredSize(certInTreasuryButton[i].getPreferredSize());/* sic */ @@ -399,13 +399,13 @@ public class GameStatus extends GridPanel implements ActionListener { addField(f, compCashXOffset, compCashYOffset + i, 1, 1, 0, visible); f = compCashButton[i] = - new ClickField( - compCash[i].getText(), - CASH_CORRECT_CMD, - LocalText.getText("CorrectCashToolTip"), - this, buySellGroup); + new ClickField( + compCash[i].getText(), + CASH_CORRECT_CMD, + LocalText.getText("CorrectCashToolTip"), + this, buySellGroup); addField(f, compCashXOffset, compCashYOffset + i, 1, 1, - WIDE_RIGHT, false); + WIDE_RIGHT, false); f = compRevenue[i] = new Field(c.getLastRevenueModel()); addField(f, compRevenueXOffset, compRevenueYOffset + i, 1, 1, 0, visible); @@ -418,9 +418,9 @@ public class GameStatus extends GridPanel implements ActionListener { if (this.compCanBuyPrivates) { f = - compPrivates[i] = - new Field( - c.getPortfolio().getPrivatesOwnedModel()); + compPrivates[i] = + new Field( + c.getPortfolio().getPrivatesOwnedModel()); addField(f, compPrivatesXOffset, compPrivatesYOffset + i, 1, 1, 0, visible); } @@ -432,7 +432,7 @@ public class GameStatus extends GridPanel implements ActionListener { } addField (f, compLoansXOffset, compLoansYOffset+i, 1, 1, 0, visible); } - + if (hasRights) { f = rights[i] = new Field (c.getRightsModel()); addField (f, rightsXOffset, rightsYOffset + i, 1, 1, 0, visible); @@ -455,11 +455,11 @@ public class GameStatus extends GridPanel implements ActionListener { WIDE_TOP, true); f = playerCashButton[i] = - new ClickField( - playerCash[i].getText(), - CASH_CORRECT_CMD, - LocalText.getText("CorrectCashToolTip"), - this, buySellGroup); + new ClickField( + playerCash[i].getText(), + CASH_CORRECT_CMD, + LocalText.getText("CorrectCashToolTip"), + this, buySellGroup); addField(f, playerCashXOffset + i, playerCashYOffset, 1, 1, WIDE_TOP, false); } @@ -468,9 +468,9 @@ public class GameStatus extends GridPanel implements ActionListener { WIDE_RIGHT, false); for (int i = 0; i < np; i++) { f = - playerPrivates[i] = - new Field( - players[i].getPortfolio().getPrivatesOwnedModel()); + playerPrivates[i] = + new Field( + players[i].getPortfolio().getPrivatesOwnedModel()); addField(f, playerPrivatesXOffset + i, playerPrivatesYOffset, 1, 1, 0, true); } @@ -493,8 +493,8 @@ public class GameStatus extends GridPanel implements ActionListener { WIDE_RIGHT + WIDE_TOP, true); for (int i = 0; i < np; i++) { f = - playerCertCount[i] = - new Field(players[i].getCertCountModel(), true); + playerCertCount[i] = + new Field(players[i].getCertCountModel(), true); addField(f, playerCertCountXOffset + i, playerCertCountYOffset, 1, 1, WIDE_TOP, true); } @@ -529,7 +529,7 @@ public class GameStatus extends GridPanel implements ActionListener { // Trains addField(new Caption(LocalText.getText("TRAINS")), poolTrainsXOffset - 1, poolTrainsYOffset - 1, 1, 2, WIDE_TOP - + WIDE_LEFT, true); + + WIDE_LEFT, true); addField(new Caption(LocalText.getText("USED")), poolTrainsXOffset, poolTrainsYOffset - 1, 1, 1, WIDE_TOP, true); poolTrains = new Field(pool.getTrainsModel()); @@ -586,12 +586,12 @@ public class GameStatus extends GridPanel implements ActionListener { for (int i = 1; i <= sale.getMaximumNumber(); i++) { options.add(LocalText.getText("SellShares", - i, + i, sale.getShare(), i * sale.getShare(), sale.getCompanyName(), Bank.format(i * sale.getShareUnits() - * sale.getPrice()) )); + * sale.getPrice()) )); sellActions.add(sale); sellAmounts.add(i); } @@ -600,17 +600,17 @@ public class GameStatus extends GridPanel implements ActionListener { if (options.size() > 1) { String message = LocalText.getText("PleaseSelect"); String sp = - (String) JOptionPane.showInputDialog(this, message, - message, JOptionPane.QUESTION_MESSAGE, - null, options.toArray(new String[0]), - options.get(0)); + (String) JOptionPane.showInputDialog(this, message, + message, JOptionPane.QUESTION_MESSAGE, + null, options.toArray(new String[0]), + options.get(0)); index = options.indexOf(sp); } else if (options.size() == 1) { String message = LocalText.getText("PleaseConfirm"); int result = - JOptionPane.showConfirmDialog(this, options.get(0), - message, JOptionPane.OK_CANCEL_OPTION, - JOptionPane.QUESTION_MESSAGE); + JOptionPane.showConfirmDialog(this, options.get(0), + message, JOptionPane.OK_CANCEL_OPTION, + JOptionPane.QUESTION_MESSAGE); index = (result == JOptionPane.OK_OPTION ? 0 : -1); } if (index < 0) { @@ -624,7 +624,7 @@ public class GameStatus extends GridPanel implements ActionListener { List<String> options = new ArrayList<String>(); List<BuyCertificate> buyActions = - new ArrayList<BuyCertificate>(); + new ArrayList<BuyCertificate>(); List<Integer> buyAmounts = new ArrayList<Integer>(); BuyCertificate buy; PublicCertificateI cert; @@ -650,7 +650,7 @@ public class GameStatus extends GridPanel implements ActionListener { int[] startPrices; if (((StartCompany) buy).mustSelectAPrice()) { startPrices = - ((StartCompany) buy).getStartPrices(); + ((StartCompany) buy).getStartPrices(); Arrays.sort(startPrices); if (startPrices.length > 1) { for (int i = 0; i < startPrices.length; i++) { @@ -695,7 +695,7 @@ public class GameStatus extends GridPanel implements ActionListener { companyName, buy.getFromPortfolio().getName(), Bank.format(i * sharesPerCert - * buy.getPrice()) )); + * buy.getPrice()) )); buyActions.add(buy); buyAmounts.add(i); } @@ -704,34 +704,34 @@ public class GameStatus extends GridPanel implements ActionListener { int index = 0; if (options.size() > 1) { if (startCompany) { - RadioButtonDialog dialog = new RadioButtonDialog ( + RadioButtonDialog dialog = new RadioButtonDialog ( gameUIManager, parent, LocalText.getText("PleaseSelect"), LocalText.getText("WHICH_START_PRICE", playerName, companyName), - options.toArray(new String[0]), -1); + options.toArray(new String[0]), -1); gameUIManager.setCurrentDialog(dialog, actions.get(0)); return; } else { String sp = - (String) JOptionPane.showInputDialog(this, - LocalText.getText(startCompany - ? "WHICH_PRICE" - : "HOW_MANY_SHARES"), - LocalText.getText("PleaseSelect"), - JOptionPane.QUESTION_MESSAGE, null, - options.toArray(new String[0]), - options.get(0)); + (String) JOptionPane.showInputDialog(this, + LocalText.getText(startCompany + ? "WHICH_PRICE" + : "HOW_MANY_SHARES"), + LocalText.getText("PleaseSelect"), + JOptionPane.QUESTION_MESSAGE, null, + options.toArray(new String[0]), + options.get(0)); index = options.indexOf(sp); } } else if (options.size() == 1) { int result = - JOptionPane.showConfirmDialog(this, options.get(0), - LocalText.getText("PleaseConfirm"), - JOptionPane.OK_CANCEL_OPTION, - JOptionPane.QUESTION_MESSAGE); + JOptionPane.showConfirmDialog(this, options.get(0), + LocalText.getText("PleaseConfirm"), + JOptionPane.OK_CANCEL_OPTION, + JOptionPane.QUESTION_MESSAGE); index = (result == JOptionPane.OK_OPTION ? 0 : -1); } if (index < 0) { @@ -763,7 +763,7 @@ public class GameStatus extends GridPanel implements ActionListener { } else { chosenAction = - processGameSpecificActions(actor, actions.get(0)); + processGameSpecificActions(actor, actions.get(0)); } } else { @@ -789,22 +789,12 @@ public class GameStatus extends GridPanel implements ActionListener { ActionEvent actor, PossibleAction chosenAction) { return chosenAction; } - + public void initTurn(int actorIndex, boolean myTurn) { int i, j; dummyButton.setSelected(true); - // Reset previous highlights - if ((j = this.actorIndex) >= 0) { - upperPlayerCaption[j].setHighlight(false); - lowerPlayerCaption[j].setHighlight(false); - for (i = 0; i < nc; i++) { - setPlayerCertButton(i, j, false); - } - } else if (j == -1 && compCanHoldOwnShares) { - treasurySharesCaption.setHighlight(false); - } for (i = 0; i < nc; i++) { setIPOCertButton(i, false); setPoolCertButton(i, false); @@ -814,24 +804,21 @@ public class GameStatus extends GridPanel implements ActionListener { this.actorIndex = actorIndex; + highlightCurrentPlayer(playerIndex.get(gameUIManager.getCurrentPlayer())); + if (treasurySharesCaption != null) treasurySharesCaption.setHighlight(actorIndex == -1); + // Set new highlights if ((j = this.actorIndex) >= -1) { - if (j >= 0) { - upperPlayerCaption[j].setHighlight(true); - lowerPlayerCaption[j].setHighlight(true); - } else if (j == -1 && treasurySharesCaption != null) { - treasurySharesCaption.setHighlight(true); - } - + if (myTurn) { PublicCompanyI company; Portfolio holder; int index; CashHolder owner; - + List<BuyCertificate> buyableCerts = - possibleActions.getType(BuyCertificate.class); + possibleActions.getType(BuyCertificate.class); if (buyableCerts != null) { for (BuyCertificate bCert : buyableCerts) { company = bCert.getCompany(); @@ -849,9 +836,9 @@ public class GameStatus extends GridPanel implements ActionListener { } } } - + List<SellShares> sellableShares = - possibleActions.getType(SellShares.class); + possibleActions.getType(SellShares.class); if (sellableShares != null) { for (SellShares share : sellableShares) { company = share.getCompany(); @@ -863,11 +850,11 @@ public class GameStatus extends GridPanel implements ActionListener { } } } - + initGameSpecificActions(); - + List<NullAction> nullActions = - possibleActions.getType(NullAction.class); + possibleActions.getType(NullAction.class); if (nullActions != null) { for (NullAction na : nullActions) { (parent).setPassButton(na); @@ -924,10 +911,10 @@ public class GameStatus extends GridPanel implements ActionListener { for (int j = 0; j < np; j++) { upperPlayerCaption[j].setText(players[j].getName() - + (j == index ? " PD" : "")); + + (j == index ? " PD" : "")); } } - + public void highlightCurrentPlayer (int index) { for (int j = 0; j < np; j++) { upperPlayerCaption[j].setHighlight(j == index); @@ -1045,7 +1032,7 @@ public class GameStatus extends GridPanel implements ActionListener { compCashButton[i].setText(compCash[i].getText()); } else { compCashButton[i].clearPossibleActions(); -} + } compCash[i].setVisible(visible && !clickable); compCashButton[i].setVisible(visible && clickable); if (action != null) |
From: Erik V. <ev...@us...> - 2011-08-14 14:28:34
|
data/1830/Map.xml | 17 data/1830/TileSet.xml | 3 data/1856/Map.xml | 4 data/18EU/Map.xml | 16 rails/algorithms/NetworkGraphBuilder.java | 8 rails/algorithms/NetworkVertex.java | 161 +++--- rails/game/BaseToken.java | 2 rails/game/City.java | 201 -------- rails/game/Game.java | 40 - rails/game/MapHex.java | 320 +++++++----- rails/game/MapManager.java | 103 ++++ rails/game/PublicCompany.java | 12 rails/game/Round.java | 4 rails/game/Station.java | 14 rails/game/Stop.java | 346 ++++++++++++++ rails/game/Tile.java | 153 +++++- rails/game/TileI.java | 21 rails/game/TileManager.java | 2 rails/game/correct/MapCorrectionManager.java | 4 rails/game/move/TileMove.java | 8 rails/game/specific/_1835/PrussianFormationRound.java | 2 rails/game/specific/_1856/CGRFormationRound.java | 14 rails/game/specific/_18EU/StartCompany_18EU.java | 20 rails/game/specific/_18EU/StockRound_18EU.java | 8 rails/ui/swing/GameUIManager.java | 4 rails/ui/swing/ORUIManager.java | 12 rails/ui/swing/gamespecific/_18EU/GameUIManager_18EU.java | 4 rails/ui/swing/hexmap/GUIHex.java | 36 - 28 files changed, 980 insertions(+), 559 deletions(-) New commits: commit 2582e0ece356f1a6ed534d29c9b9fdbf5ea5fc84 Author: Erik Vos <eri...@xs...> Date: Sun Aug 14 16:26:41 2011 +0200 Stop properties wrap-up diff --git a/data/1830/Map.xml b/data/1830/Map.xml index d43649c..9a286e8 100644 --- a/data/1830/Map.xml +++ b/data/1830/Map.xml @@ -1,9 +1,10 @@ <Map tileOrientation="EW" letterOrientation="vertical" even="B"> <Defaults> - <Access type="offMap" runTo="yes" runThrough="no" loop="no"/> - <Access type="major" runTo="yes" runThrough="yes" loop="yes"/> + <Access type="offMap" runTo="yes" runThrough="no" loop="no" score="major"/> + <Access type="city" runTo="yes" runThrough="yes" loop="yes" score="major"/> + <Access type="town" runTo="yes" runThrough="yes" loop="yes" score="minor"/> </Defaults> - <!-- The above defaults are redundant, these settings are the defaults anyway --> + <!-- The above defaults are redundant, these settings are the system defaults anyway --> <Hex name="A9" tile="-901" orientation="0" value="30,50" city="Canadian West"/> <Hex name="A11" tile="-902" orientation="1" value="30,50" city="Canadian West"/> <Hex name="A17" tile="-7" orientation="1" city="Montreal"/> diff --git a/rails/algorithms/NetworkVertex.java b/rails/algorithms/NetworkVertex.java index b4c9056..952c971 100644 --- a/rails/algorithms/NetworkVertex.java +++ b/rails/algorithms/NetworkVertex.java @@ -53,7 +53,7 @@ public final class NetworkVertex implements Comparable<NetworkVertex> { this.hex = hex; this.station = station; this.side = -1; - this.city = hex.getRelatedCity(station); + this.city = hex.getRelatedStop(station); if (city != null) { log.info("Found city " + city); } else { diff --git a/rails/game/City.java b/rails/game/City.java deleted file mode 100644 index 75d5ba9..0000000 --- a/rails/game/City.java +++ /dev/null @@ -1,201 +0,0 @@ -/* $Header: /Users/blentz/rails_rcs/cvs/18xx/rails/game/City.java,v 1.12 2010/04/18 15:08:57 evos Exp $ */ -package rails.game; - -import java.util.ArrayList; -import java.util.List; - -import org.apache.log4j.Logger; - -import rails.game.move.Moveable; -import rails.game.state.GenericState; -import rails.util.Util; - -/** - * A City object represents any junction on the map that is relevant for - * establishing train run length and revenue calculation. A City object is bound - * to (1) a MapHex, (2) to a Station object on the current Tile laid on that - * MapHex, and (3) any tokens laid on that tile and station. <p> Each City has a - * unique ID, that is derived from the MapHex name and the City number. The - * initial City numbers are derived from the Station numbers of the preprinted - * tile of that hex. <p> Please note, that during upgrades the Station numbers - * related to a city on a multiple-city hex may change: city 1 on one tile may - * be numbered 2 on its upgrade, depending on the rotation of the upgrading - * tile. However, the City numbers will not change, unless cities are merged - * during upgrades; but even then it is attempted to retain the old city numbers - * as much as possible. - * - * @author Erik Vos - */ -public class City implements TokenHolder { - private int number; - private String uniqueId; - //private Station relatedStation; - private GenericState<Station> relatedStation; - private int slots; - private ArrayList<TokenI> tokens; - private MapHex mapHex; - private String trackEdges; - - protected static Logger log = - Logger.getLogger(City.class.getPackage().getName()); - - public City(MapHex mapHex, int number, Station station) { - this.mapHex = mapHex; - this.number = number; - - uniqueId = mapHex.getName() + "_" + number; - relatedStation = new GenericState<Station>("City_"+uniqueId+"_station", station); - setRelatedStation(station); - - - tokens = new ArrayList<TokenI>(4); - } - - public String getName() { - return mapHex.getName() + "/" + number; - - } - - /** - * @return Returns the holder. - */ - public MapHex getHolder() { - return mapHex; - } - - public int getNumber() { - return number; - } - - public Station getRelatedStation() { - return relatedStation.get(); - } - - public void setRelatedStation(Station relatedStation) { - this.relatedStation.set(relatedStation); - slots = relatedStation.getBaseSlots(); - trackEdges = - mapHex.getConnectionString(mapHex.getCurrentTile(), - mapHex.getCurrentTileRotation(), - relatedStation.getNumber()); - } - - public void setSlots(int slots) { - this.slots = slots; - } - - /** - * @return Returns the id. - */ - public String getUniqueId() { - return uniqueId; - } - - public boolean addToken(TokenI token, int position) { - - if (tokens.contains(token)) return false; - - boolean result = Util.addToList(tokens, token, position); - if (result) token.setHolder(this); - return result; - } - - public boolean addObject(Moveable object, int[] position) { - if (object instanceof TokenI) { - return addToken((TokenI) object, position == null ? -1 : position[0]); - } else { - return false; - } - } - - public boolean removeObject(Moveable object) { - if (object instanceof TokenI) { - return removeToken((TokenI) object); - } else { - return false; - } - } - - public List<TokenI> getTokens() { - return tokens; - } - - public boolean hasTokens() { - return tokens.size() > 0; - } - - public int getSlots() { - return slots; - } - - public boolean hasTokenSlotsLeft() { - return tokens.size() < slots; - } - - public int getTokenSlotsLeft () { - return slots - tokens.size(); - } - - public boolean removeToken(TokenI token) { - - boolean result = tokens.remove(token); - return result; - } - - /** - * @param company - * @return true if this City already contains an instance of the specified - * company's token. Do this by calling the hasTokenOf with Company Name. - * Using a tokens.contains(company) fails since the tokens are a ArrayList - * of TokenI not a ArrayList of PublicCompanyI. - */ - public boolean hasTokenOf(PublicCompanyI company) { - return hasTokenOf (company.getName()); - } - - public boolean hasTokenOf (String companyName) { - for (TokenI token : tokens) { - if (token instanceof BaseToken - && ((BaseToken)token).getCompany().getName().equals(companyName)) { - return true; - } - } - return false; - } - - public int[] getListIndex (Moveable object) { - if (object instanceof BaseToken) { - return new int[] {tokens.indexOf(object)}; - } else { - return Moveable.AT_END; - } - } - - public void setTokens(ArrayList<TokenI> tokens) { - this.tokens = tokens; - } - - public String getTrackEdges() { - return trackEdges; - } - - public void setTrackEdges(String trackEdges) { - this.trackEdges = trackEdges; - } - - @Override - public String toString() { - StringBuffer b = new StringBuffer(); - b.append("Hex ").append(mapHex.getName()); - String cityName = mapHex.getCityName(); - b.append(" ("); - if (Util.hasValue(cityName)) { - b.append(cityName); - } - if (mapHex.getCities().size() > 1) { - b.append(" ").append(trackEdges); - } - b.append(")"); - return b.toString(); - } -} diff --git a/rails/game/MapHex.java b/rails/game/MapHex.java index f962f46..4093b0e 100644 --- a/rails/game/MapHex.java +++ b/rails/game/MapHex.java @@ -13,6 +13,7 @@ import rails.common.parser.*; import rails.game.Stop.Loop; import rails.game.Stop.RunThrough; import rails.game.Stop.RunTo; +import rails.game.Stop.Score; import rails.game.Stop.Type; import rails.game.action.LayTile; import rails.game.model.ModelObject; @@ -149,10 +150,14 @@ StationHolder, TokenHolder { /** Type of any stops on the hex. * Normally the type will be derived from the tile properties. - * Hex-specific types are known to be required in 18VA (mine and offmap). */ protected Type stopType = null; + /** + * Score type: do stops on this hex count as major or minor stops with respect to n+m trains? + */ + protected Score scoreType = null; + protected MapManager mapManager = null; protected static Logger log = @@ -302,7 +307,17 @@ StationHolder, TokenHolder { stopType = Type.valueOf(typeString.toUpperCase()); } catch (IllegalArgumentException e) { throw new ConfigurationException ("Illegal value for MapHex " - +name+" type property: "+typeString, e); + +name+" stop type property: "+typeString, e); + } + } + + String scoreTypeString = accessTag.getAttributeAsString("score"); + if (Util.hasValue(scoreTypeString)) { + try { + scoreType = Score.valueOf(scoreTypeString.toUpperCase()); + } catch (IllegalArgumentException e) { + throw new ConfigurationException ("Illegal value for MapHex " + +name+" score type property: "+scoreTypeString, e); } } } @@ -1037,38 +1052,38 @@ StationHolder, TokenHolder { return 0; } - public List<Stop> getCities() { + public List<Stop> getStops() { return stops; } - public Stop getCity(int cityNumber) { - return mStops.get(cityNumber); + public Stop getStop(int stopNumber) { + return mStops.get(stopNumber); } - public Stop getRelatedCity(Station station) { - Stop foundCity = null; - for (Stop city:mStops.values()) { - if (station == city.getRelatedStation()) { - foundCity = city; + public Stop getRelatedStop(Station station) { + Stop foundStop = null; + for (Stop stop:mStops.values()) { + if (station == stop.getRelatedStation()) { + foundStop = stop; } } - return foundCity; + return foundStop; } - public void addHome(PublicCompanyI company, int cityNumber) throws ConfigurationException { + public void addHome(PublicCompanyI company, int stopNumber) throws ConfigurationException { if (homes == null) homes = new HashMap<PublicCompanyI, Stop>(); if (stops.isEmpty()) { log.error("No cities for home station on hex " + name); } else { // not yet decided - if (cityNumber == 0) { + if (stopNumber == 0) { homes.put(company, null); log.debug("Added home of " + company + " in hex " + this.toString() + " city not yet decided"); - } else if (cityNumber > stops.size()) { - throw new ConfigurationException ("Invalid city number "+cityNumber+" for hex "+name + } else if (stopNumber > stops.size()) { + throw new ConfigurationException ("Invalid city number "+stopNumber+" for hex "+name +" which has "+stops.size()+" cities"); } else { - Stop homeCity = stops.get(Math.max(cityNumber - 1, 0)); + Stop homeCity = stops.get(Math.max(stopNumber - 1, 0)); homes.put(company, homeCity); log.debug("Added home of " + company + " set to " + homeCity + " id= " +homeCity.getUniqueId()); } @@ -1178,7 +1193,7 @@ StationHolder, TokenHolder { // Return MapHex attribute if defined return isBlockedForTokenLays.booleanValue(); } else if (homes != null && !homes.isEmpty()) { - Stop cityToLay = this.getCity(cityNumber); + Stop cityToLay = this.getStop(cityNumber); if (cityToLay == null) { // city does not exist, this does not block itself return false; } @@ -1360,4 +1375,7 @@ StationHolder, TokenHolder { return stopType; } + public Score getScoreType() { + return scoreType; + } } \ No newline at end of file diff --git a/rails/game/MapManager.java b/rails/game/MapManager.java index 9ac030d..f5220f9 100644 --- a/rails/game/MapManager.java +++ b/rails/game/MapManager.java @@ -9,6 +9,7 @@ import rails.common.parser.*; import rails.game.Stop.Loop; import rails.game.Stop.RunThrough; import rails.game.Stop.RunTo; +import rails.game.Stop.Score; import rails.game.Stop.Type; import rails.util.Util; @@ -57,6 +58,7 @@ public class MapManager implements ConfigurableComponentI { protected Map<Type,RunTo> runToDefaults = new HashMap<Type, RunTo>(); protected Map<Type,RunThrough> runThroughDefaults = new HashMap<Type, RunThrough>(); protected Map<Type,Loop> loopDefaults = new HashMap<Type, Loop>(); + protected Map<Type,Score> scoreTypeDefaults = new HashMap<Type, Score>(); protected static Logger log = Logger.getLogger(MapManager.class.getPackage().getName()); @@ -165,6 +167,7 @@ public class MapManager implements ConfigurableComponentI { RunTo runTo; RunThrough runThrough; Loop loop; + Score score; String s; Tag defaultsTag = tag.getChild("Defaults"); if (defaultsTag != null) { @@ -214,6 +217,17 @@ public class MapManager implements ConfigurableComponentI { } loopDefaults.put(type, loop); } + // Score type (not allowed for a null stop type) + s = accessTag.getAttributeAsString("scoreType", null); + if (type != null && Util.hasValue(s)) { + try { + score = Score.valueOf(s.toUpperCase()); + } catch (IllegalArgumentException e) { + throw new ConfigurationException ("Illegal value for " + +type+" default score type property: "+s, e); + } + scoreTypeDefaults.put(type, score); + } } } } @@ -275,11 +289,6 @@ public class MapManager implements ConfigurableComponentI { hex.addDestination(company); } } - - // Define default Stop property defaults - if (!runToDefaults.containsKey(null)) runToDefaults.put(null, RunTo.YES); - if (!runThroughDefaults.containsKey(null)) runThroughDefaults.put(null, RunThrough.YES); - if (!loopDefaults.containsKey(null)) loopDefaults.put(null, Loop.YES); } /** @@ -379,7 +388,7 @@ public class MapManager implements ConfigurableComponentI { public List<Stop> getCurrentStations() { List<Stop> stations = new ArrayList<Stop>(); for (MapHex hex : mHexes.values()) { - stations.addAll(hex.getCities()); + stations.addAll(hex.getStops()); } return stations; } @@ -509,4 +518,8 @@ public class MapManager implements ConfigurableComponentI { return loopDefaults.containsKey(type) ? loopDefaults.get(type) : null; } + public Score getScoreTypeDefault(Type type) { + return scoreTypeDefaults.containsKey(type) ? scoreTypeDefaults.get(type) : null; + } + } diff --git a/rails/game/PublicCompany.java b/rails/game/PublicCompany.java index 3f95068..8888f6f 100644 --- a/rails/game/PublicCompany.java +++ b/rails/game/PublicCompany.java @@ -1828,14 +1828,14 @@ public class PublicCompany extends Company implements PublicCompanyI { } else { // Cover the case that there already is another token. // Allowing this is optional for 1856 Hamilton (THB home) - List<Stop> cities = homeHex.getCities(); - List<Stop> openCities = new ArrayList<Stop>(); - for (Stop city : cities) { - if (city.hasTokenSlotsLeft()) openCities.add (city); + List<Stop> stops = homeHex.getStops(); + List<Stop> openStops = new ArrayList<Stop>(); + for (Stop stop : stops) { + if (stop.hasTokenSlotsLeft()) openStops.add (stop); } - if (openCities.size() == 1) { + if (openStops.size() == 1) { // Just one spot: lay the home base there. - homeCityNumber = openCities.get(0).getNumber(); + homeCityNumber = openStops.get(0).getNumber(); } else { // ?? // TODO Will player be asked?? diff --git a/rails/game/Round.java b/rails/game/Round.java index 14cdbc4..b162080 100644 --- a/rails/game/Round.java +++ b/rails/game/Round.java @@ -220,7 +220,7 @@ public abstract class Round implements RoundI { cityNumber = 1; } hex = mapManager.getHex(hexName); - city = hex.getCity(cityNumber); + city = hex.getStop(cityNumber); if (token.isSelected()) { diff --git a/rails/game/Stop.java b/rails/game/Stop.java index 6a2068f..edffce5 100644 --- a/rails/game/Stop.java +++ b/rails/game/Stop.java @@ -41,6 +41,7 @@ public class Stop implements TokenHolder { private RunTo runToAllowed = null; private RunThrough runThroughAllowed = null; private Loop loopAllowed = null; + private Score scoreType = null; protected static Logger log = Logger.getLogger(Stop.class.getPackage().getName()); @@ -63,15 +64,37 @@ public class Stop implements TokenHolder { } public enum Type { + + CITY (RunTo.YES, RunThrough.YES, Loop.YES, Score.MAJOR), + TOWN (RunTo.YES, RunThrough.YES, Loop.YES, Score.MINOR), + OFFMAP (RunTo.YES, RunThrough.NO, Loop.NO, Score.MAJOR); + + private RunTo defaultRunToAllowed; + private RunThrough defaultRunThroughAllowed; + private Loop defaultLoopAllowed; + private Score defaultScoreType; + + Type (RunTo runTo, + RunThrough runThrough, + Loop loop, + Score scoreType) { + + this.defaultRunToAllowed = runTo; + this.defaultRunThroughAllowed = runThrough; + this.defaultLoopAllowed = loop; + this.defaultScoreType = scoreType; + } + + public RunTo getDefaultRunTo() { return defaultRunToAllowed; } + public RunThrough getDefaultRunThrough() { return defaultRunThroughAllowed; } + public Loop getDefaultLoop() { return defaultLoopAllowed; } + public Score getDefaultScoreType() { return defaultScoreType; } + + } + + public enum Score { MAJOR, - MINOR, - OFFMAP, - MEDIUM, - HALT, - PASS, - PORT, - MINE, - NULL + MINOR } public Stop(MapHex mapHex, int number, Station station) { @@ -94,23 +117,23 @@ public class Stop implements TokenHolder { MapManager mapManager = mapHex.getMapManager(); TileManager tileManager = tile.getTileManager(); - // Type + // Stop type type = mapHex.getStopType(); if (type == null) type = tile.getStopType(); if (type == null) { String stationType = relatedStation.get().getType(); if (stationType.equals(Station.CITY)) { - type = Type.MAJOR; + type = Type.CITY; } else if (stationType.equals(Station.TOWN)) { - type = Type.MINOR; + type = Type.TOWN; } else if (stationType.equals(Station.OFF_MAP_AREA)) { type = Type.OFFMAP; } else if (stationType.equals(Station.PASS)) { - type = Type.PASS; + type = Type.CITY; } else { // The above four types seem to be all that can be assigned in ConvertTileXML. // If all else fails, assume City. - type = Type.MAJOR; + type = Type.CITY; } } @@ -121,7 +144,7 @@ public class Stop implements TokenHolder { if (runToAllowed == null) runToAllowed = tileManager.getRunToDefault(type); if (runToAllowed == null) runToAllowed = mapManager.getRunToDefault(null); if (runToAllowed == null) runToAllowed = tileManager.getRunToDefault(null); - if (runToAllowed == null) runToAllowed = RunTo.YES; + if (runToAllowed == null) runToAllowed = type.getDefaultRunTo(); // RunThrough runThroughAllowed = mapHex.isRunThroughAllowed(); @@ -130,7 +153,7 @@ public class Stop implements TokenHolder { if (runThroughAllowed == null) runThroughAllowed = tileManager.getRunThroughDefault(type); if (runThroughAllowed == null) runThroughAllowed = mapManager.getRunThroughDefault(null); if (runThroughAllowed == null) runThroughAllowed = tileManager.getRunThroughDefault(null); - if (runThroughAllowed == null) runThroughAllowed = type == Type.OFFMAP ? RunThrough.NO : RunThrough.YES; + if (runThroughAllowed == null) runThroughAllowed = type.getDefaultRunThrough(); // Loop loopAllowed = mapHex.isLoopAllowed(); @@ -139,11 +162,18 @@ public class Stop implements TokenHolder { if (loopAllowed == null) loopAllowed = tileManager.getLoopDefault(type); if (loopAllowed == null) loopAllowed = mapManager.getLoopDefault(null); if (loopAllowed == null) loopAllowed = tileManager.getLoopDefault(null); - if (loopAllowed == null) loopAllowed = type == Type.OFFMAP ? Loop.NO : Loop.YES; + if (loopAllowed == null) loopAllowed = type.getDefaultLoop(); + + // Score type + scoreType = mapHex.getScoreType(); + if (scoreType == null) scoreType = tile.getScoreType(); + if (scoreType == null) scoreType = mapManager.getScoreTypeDefault(type); + if (scoreType == null) scoreType = tileManager.getScoreTypeDefault(type); + if (scoreType == null) scoreType = type.getDefaultScoreType(); log.debug("+++ Hex="+mapHex.getName()+" tile="+tile.getId()+" city="+number - +": type="+type+" runTo="+runToAllowed+" runThrough="+runThroughAllowed - +" loop="+loopAllowed); + +": stopType="+type+" runTo="+runToAllowed+" runThrough="+runThroughAllowed + +" loop="+loopAllowed+" scoreType="+scoreType); } public String getName() { @@ -282,6 +312,10 @@ public class Stop implements TokenHolder { return type; } + public Score getScoreType () { + return scoreType; + } + public RunTo isRunToAllowed() { return runToAllowed; } @@ -303,7 +337,7 @@ public class Stop implements TokenHolder { if (Util.hasValue(cityName)) { b.append(cityName); } - if (mapHex.getCities().size() > 1) { + if (mapHex.getStops().size() > 1) { b.append(" ").append(trackEdges); } b.append(")"); diff --git a/rails/game/Tile.java b/rails/game/Tile.java index bf25b17..10fe33c 100644 --- a/rails/game/Tile.java +++ b/rails/game/Tile.java @@ -12,6 +12,7 @@ import rails.common.parser.Tag; import rails.game.Stop.Loop; import rails.game.Stop.RunThrough; import rails.game.Stop.RunTo; +import rails.game.Stop.Score; import rails.game.Stop.Type; import rails.game.model.ModelObject; import rails.util.Util; @@ -64,6 +65,7 @@ public class Tile extends ModelObject implements TileI, StationHolder, Comparabl protected RunTo runToAllowed = null; protected RunThrough runThroughAllowed = null; protected Loop loopAllowed = null; + protected Score scoreType = null; protected TileManager tileManager; @@ -357,7 +359,17 @@ public class Tile extends ModelObject implements TileI, StationHolder, Comparabl stopType = Type.valueOf(typeString.toUpperCase()); } catch (IllegalArgumentException e) { throw new ConfigurationException ("Illegal value for Tile " - +name+" type property: "+typeString, e); + +name+" stop type property: "+typeString, e); + } + } + + String scoreTypeString = accessTag.getAttributeAsString("score"); + if (Util.hasValue(scoreTypeString)) { + try { + scoreType = Score.valueOf(scoreTypeString.toUpperCase()); + } catch (IllegalArgumentException e) { + throw new ConfigurationException ("Illegal value for Tile " + +name+" sscore type property: "+scoreTypeString, e); } } } @@ -620,6 +632,10 @@ public class Tile extends ModelObject implements TileI, StationHolder, Comparabl return loopAllowed; } + public Score getScoreType() { + return scoreType; + } + public TileManager getTileManager () { return tileManager; } diff --git a/rails/game/TileI.java b/rails/game/TileI.java index 320f9cd..16e8afe 100644 --- a/rails/game/TileI.java +++ b/rails/game/TileI.java @@ -10,6 +10,7 @@ import rails.common.parser.Tag; import rails.game.Stop.Loop; import rails.game.Stop.RunThrough; import rails.game.Stop.RunTo; +import rails.game.Stop.Score; import rails.game.Stop.Type; public interface TileI { @@ -82,6 +83,7 @@ public interface TileI { public RunTo isRunToAllowed(); public RunThrough isRunThroughAllowed(); public Loop isLoopAllowed(); + public Score getScoreType(); public TileManager getTileManager(); diff --git a/rails/game/TileManager.java b/rails/game/TileManager.java index ed262a6..0878175 100644 --- a/rails/game/TileManager.java +++ b/rails/game/TileManager.java @@ -1 +1 @@ -/* $Header: /Users/blentz/rails_rcs/cvs/18xx/rails/game/TileManager.java,v 1.17 2010/05/29 09:38:58 stefanfrey Exp $ */ package rails.game; import java.util.*; import org.apache.log4j.Logger; import rails.common.LocalText; import rails.common.parser.*; import rails.game.Stop.Loop; import rails.game.Stop.RunThrough; import rails.game.Stop.RunTo; import rails.game.Stop.Type; import rails.util.Util; public class TileManager implements ConfigurableComponentI { protected Map<Integer, TileI> tileMap = new HashMap<Integer, TileI>(); protected List<Integer> tileIds = new ArrayList<Integer>(); // private static List<String> directories = new ArrayList<String>(); private List<String> directories = new ArrayList<String>(); // Stop property defaults per stop type protected Map<Type,RunTo> runToDefaults = new HashMap<Type, RunTo>(); protected Map<Type,RunThrough> runThroughDefaults = new HashMap<Type, RunThrough>(); protected Map<Type,Loop> loopDefaults = new HashMap<Type, Loop>(); protected static Logger log = Logger.getLogger(TileManager.class.getPackage().getName()); /** * No-args constructor. */ public TileManager() { } /** * @see rails.common.parser.ConfigurableComponentI#configureFromXML(org.w3c.dom.Element) */ public void configureFromXML(Tag tileSetTop) throws ConfigurationException { /* * Note: prefix se is used for elements from TileSet.xml, prefix te for * elements from Tiles.xml. */ String tileDefFileName = tileSetTop.getAttributeAsString("tiles"); if (tileDefFileName == null) throw new ConfigurationException(LocalText.getText("NoTilesXML")); directories.add("data/" + GameManager.getInstance().getGameName()); Tag tileDefTop = Tag.findTopTagInFile(tileDefFileName, directories, "Tiles"); if (tileDefTop == null) throw new ConfigurationException(LocalText.getText("NoTilesTag")); List<Tag> tileSetList = |
From: Erik V. <ev...@us...> - 2011-08-11 22:16:26
|
rails/game/OperatingRound.java | 4163 ++++++++++++++++++++--------------------- 1 file changed, 2110 insertions(+), 2053 deletions(-) New commits: commit 8d9ca907cc522935c710a8349d13a9f97a50eebf Author: Erik Vos <eri...@xs...> Date: Fri Aug 12 00:14:14 2011 +0200 Reorganized OperatingRound No code changes, but methods have been sorted into functional groups, each preceded by a header. Hopefully this class will now be easier to grasp. diff --git a/rails/game/OperatingRound.java b/rails/game/OperatingRound.java index 957203e..ec8de9c 100644 --- a/rails/game/OperatingRound.java +++ b/rails/game/OperatingRound.java @@ -3,9 +3,7 @@ package rails.game; import java.util.*; -import rails.common.DisplayBuffer; -import rails.common.GuiDef; -import rails.common.LocalText; +import rails.common.*; import rails.common.parser.GameOption; import rails.game.action.*; import rails.game.correct.ClosePrivate; @@ -82,9 +80,12 @@ public class OperatingRound extends Round implements Observer { protected TrainManager trainManager = gameManager.getTrainManager(); + /*======================================= + * 1. OR START and END + *=======================================*/ + /** * Constructor with no parameters, call the super Class (Round's) Constructor with no parameters - * */ public OperatingRound(GameManagerI gameManager) { super (gameManager); @@ -158,7 +159,56 @@ public class OperatingRound extends Round implements Observer { } - /*----- METHODS THAT PROCESS PLAYER ACTIONS -----*/ + @Override + public void resume() { + + if (savedAction instanceof BuyTrain) { + buyTrain ((BuyTrain)savedAction); + } else if (savedAction instanceof SetDividend) { + executeSetRevenueAndDividend ((SetDividend) savedAction); + } else if (savedAction instanceof RepayLoans) { + executeRepayLoans ((RepayLoans) savedAction); + } else if (savedAction == null) { + //nextStep(); + } + savedAction = null; + wasInterrupted.set(true); + + guiHints.setVisibilityHint(GuiDef.Panel.STOCK_MARKET, false); + guiHints.setVisibilityHint(GuiDef.Panel.STATUS, true); + guiHints.setActivePanel(GuiDef.Panel.MAP); + } + + protected void finishOR() { + + // Check if any privates must be closed + // (now only applies to 1856 W&SR) - no, that is at end of TURN + //for (PrivateCompanyI priv : gameManager.getAllPrivateCompanies()) { + // priv.checkClosingIfExercised(true); + //} + + ReportBuffer.add(" "); + ReportBuffer.add(LocalText.getText("EndOfOperatingRound", thisOrNumber)); + + // Update the worth increase per player + int orWorthIncrease; + for (Player player : gameManager.getPlayers()) { + player.setLastORWorthIncrease(); + orWorthIncrease = player.getLastORWorthIncrease().intValue(); + ReportBuffer.add(LocalText.getText("ORWorthIncrease", + player.getName(), + thisOrNumber, + Bank.format(orWorthIncrease))); + } + + // OR done. Inform GameManager. + finishRound(); + } + + /*======================================= + * 2. CENTRAL PROCESSING FUNCTIONS + * 2.1. PROCESS USER ACTION + *=======================================*/ @Override public boolean process(PossibleAction action) { @@ -236,10 +286,10 @@ public class OperatingRound extends Round implements Observer { } else if (selectedAction instanceof ClosePrivate) { result = executeClosePrivate((ClosePrivate)selectedAction); - + } else if (selectedAction instanceof UseSpecialProperty && ((UseSpecialProperty)selectedAction).getSpecialProperty() instanceof SpecialRight) { - + result = buyRight ((UseSpecialProperty)selectedAction); } else if (selectedAction instanceof NullAction) { @@ -275,1073 +325,1284 @@ public class OperatingRound extends Round implements Observer { return false; } - public boolean layTile(LayTile action) { + /*======================================= + * 2.2. PREPARE NEXT ACTION + *=======================================*/ - String errMsg = null; - int cost = 0; - SpecialTileLay stl = null; - boolean extra = false; + /** + * To be called after each change, to re-establish the currently allowed + * actions. (new method, intended to absorb code from several other + * methods). + * + */ + @Override + public boolean setPossibleActions() { - PublicCompanyI company = action.getCompany(); - String companyName = company.getName(); - TileI tile = action.getLaidTile(); - MapHex hex = action.getChosenHex(); - int orientation = action.getOrientation(); + /* Create a new list of possible actions for the UI */ + possibleActions.clear(); + selectedAction = null; - // Dummy loop to enable a quick jump out. - while (true) { - // Checks - // Must be correct company. - if (!companyName.equals(operatingCompany.get().getName())) { - errMsg = - LocalText.getText("WrongCompany", - companyName, - operatingCompany.get().getName() ); - break; - } - // Must be correct step - if (getStep() != GameDef.OrStep.LAY_TRACK) { - errMsg = LocalText.getText("WrongActionNoTileLay"); - break; + boolean forced = false; + doneAllowed = false; // set default (fix of bug 2954654) + + if (getStep() == GameDef.OrStep.INITIAL) { + initTurn(); + if (noMapMode) { + nextStep (GameDef.OrStep.LAY_TOKEN); + } else { + initNormalTileLays(); // new: only called once per turn ? + setStep (GameDef.OrStep.LAY_TRACK); } + } - if (tile == null) break; + GameDef.OrStep step = getStep(); + if (step == GameDef.OrStep.LAY_TRACK) { - if (!getCurrentPhase().isTileColourAllowed(tile.getColourName())) { - errMsg = - LocalText.getText("TileNotYetAvailable", - tile.getExternalId()); - break; - } - if (tile.countFreeTiles() == 0) { - errMsg = - LocalText.getText("TileNotAvailable", - tile.getExternalId()); - break; + if (!operatingCompany.get().hasLaidHomeBaseTokens()) { + // This can occur if the home hex has two cities and track, + // such as the green OO tile #59 + possibleActions.add(new LayBaseToken (operatingCompany.get().getHomeHexes())); + forced = true; + } else { + possibleActions.addAll(getNormalTileLays(true)); + possibleActions.addAll(getSpecialTileLays(true)); + possibleActions.add(new NullAction(NullAction.SKIP)); } - /* - * Check if the current tile is allowed via the LayTile allowance. - * (currently the set if tiles is always null, which means that this - * check is redundant. This may change in the future. - */ - if (action != null) { - List<TileI> tiles = action.getTiles(); - if (tiles != null && !tiles.isEmpty() && !tiles.contains(tile)) { - errMsg = - LocalText.getText( - "TileMayNotBeLaidInHex", - tile.getExternalId(), - hex.getName() ); - break; - } - stl = action.getSpecialProperty(); - if (stl != null) extra = stl.isExtra(); - } + } else if (step == GameDef.OrStep.LAY_TOKEN) { + setNormalTokenLays(); + setSpecialTokenLays(); + log.debug("Normal token lays: " + currentNormalTokenLays.size()); + log.debug("Special token lays: " + currentSpecialTokenLays.size()); - /* - * If this counts as a normal tile lay, check if the allowed number - * of normal tile lays is not exceeded. - */ - if (!extra && !validateNormalTileLay(tile)) { - errMsg = - LocalText.getText("NumberOfNormalTileLaysExceeded", - tile.getColourName()); - break; - } + possibleActions.addAll(currentNormalTokenLays); + possibleActions.addAll(currentSpecialTokenLays); + possibleActions.add(new NullAction(NullAction.SKIP)); + } else if (step == GameDef.OrStep.CALC_REVENUE) { + prepareRevenueAndDividendAction(); + if (noMapMode) + prepareNoMapActions(); + } else if (step == GameDef.OrStep.BUY_TRAIN) { + setBuyableTrains(); + // TODO Need route checking here. + // TEMPORARILY allow not buying a train if none owned + //if (!operatingCompany.getObject().mustOwnATrain() + // || operatingCompany.getObject().getPortfolio().getNumberOfTrains() > 0) { + doneAllowed = true; + //} + if (noMapMode && (operatingCompany.get().getLastRevenue() == 0)) + prepareNoMapActions(); - // Sort out cost - if (stl != null && stl.isFree()) { - cost = 0; - } else { - cost = hex.getTileCost(); - } + } else if (step == GameDef.OrStep.DISCARD_TRAINS) { - // Amount must be non-negative multiple of 10 - if (cost < 0) { - errMsg = - LocalText.getText("NegativeAmountNotAllowed", - Bank.format(cost)); - break; - } - if (cost % 10 != 0) { - errMsg = - LocalText.getText("AmountMustBeMultipleOf10", - Bank.format(cost)); - break; - } - // Does the company have the money? - if (cost > operatingCompany.get().getCash()) { - errMsg = - LocalText.getText("NotEnoughMoney", - companyName, - Bank.format(operatingCompany.get().getCash()), - Bank.format(cost) ); - break; - } - break; - } - if (errMsg != null) { - DisplayBuffer.add(LocalText.getText("CannotLayTileOn", - companyName, - tile.getExternalId(), - hex.getName(), - Bank.format(cost), - errMsg )); - return false; + forced = true; + setTrainsToDiscard(); } - /* End of validation, start of execution */ - moveStack.start(true); + // The following additional "common" actions are only available if the + // primary action is not forced. + if (!forced) { - if (tile != null) { - if (cost > 0) - new CashMove(operatingCompany.get(), bank, cost); - operatingCompany.get().layTile(hex, tile, orientation, cost); + setBonusTokenLays(); - if (cost == 0) { - ReportBuffer.add(LocalText.getText("LaysTileAt", - companyName, - tile.getExternalId(), - hex.getName(), - hex.getOrientationName(orientation))); - } else { - ReportBuffer.add(LocalText.getText("LaysTileAtFor", - companyName, - tile.getExternalId(), - hex.getName(), - hex.getOrientationName(orientation), - Bank.format(cost) )); - } - hex.upgrade(action); + setDestinationActions(); - // Was a special property used? - if (stl != null) { - stl.setExercised(); - //currentSpecialTileLays.remove(action); - log.debug("This was a special tile lay, " - + (extra ? "" : " not") + " extra"); + setGameSpecificPossibleActions(); + // Private Company manually closure + for (PrivateCompanyI priv: companyManager.getAllPrivateCompanies()) { + if (!priv.isClosed() && priv.closesManually()) + possibleActions.add(new ClosePrivate(priv)); } - if (!extra) { - log.debug("This was a normal tile lay"); - registerNormalTileLay(tile); - } - } - if (tile == null || !areTileLaysPossible()) { - nextStep(); - } - - return true; - } + // Can private companies be bought? + if (isPrivateSellingAllowed()) { - protected boolean validateNormalTileLay(TileI tile) { - return checkNormalTileLay(tile, false); - } + // Create a list of players with the current one in front + int currentPlayerIndex = operatingCompany.get().getPresident().getIndex(); + Player player; + int minPrice, maxPrice; + List<Player> players = getPlayers(); + int numberOfPlayers = getNumberOfPlayers(); + for (int i = currentPlayerIndex; i < currentPlayerIndex + + numberOfPlayers; i++) { + player = players.get(i % numberOfPlayers); + if (!maySellPrivate(player)) continue; + for (PrivateCompanyI privComp : player.getPortfolio().getPrivateCompanies()) { - protected void registerNormalTileLay(TileI tile) { - checkNormalTileLay(tile, true); - } + // check to see if the private can be sold to a company + if (!privComp.tradeableToCompany()) { + continue; + } - protected boolean checkNormalTileLay(TileI tile, boolean update) { + minPrice = getPrivateMinimumPrice (privComp); - // Unspecified tile (e.g. 1889 D private, which is free on mountains) - if (tile == null) { - return !tileLaysPerColour.isEmpty(); - } - - String colour = tile.getColourName(); - Integer oldAllowedNumberObject = tileLaysPerColour.get(colour); + maxPrice = getPrivateMaximumPrice (privComp); - if (oldAllowedNumberObject == null) return false; + possibleActions.add(new BuyPrivate(privComp, minPrice, + maxPrice)); + } + } + } - int oldAllowedNumber = oldAllowedNumberObject.intValue(); - if (oldAllowedNumber <= 0) return false; + if (operatingCompany.get().canUseSpecialProperties()) { - if (update) updateAllowedTileColours(colour, oldAllowedNumber); - return true; - } + // Are there any "common" special properties, + // i.e. properties that are available to everyone? + List<SpecialPropertyI> commonSP = gameManager.getCommonSpecialProperties(); + if (commonSP != null) { + SellBonusToken sbt; + loop: for (SpecialPropertyI sp : commonSP) { + if (sp instanceof SellBonusToken) { + sbt = (SellBonusToken) sp; + // Can't buy if already owned + if (operatingCompany.get().getBonuses() != null) { + for (Bonus bonus : operatingCompany.get().getBonuses()) { + if (bonus.getName().equals(sp.getName())) continue loop; + } + } + possibleActions.add (new BuyBonusToken (sbt)); + } + } + } - /* - * We will assume that in all cases the following assertions hold: 1. If - * the allowed number for the colour of the just laid tile reaches zero, - * all normal tile lays have been consumed. 2. If any colour is laid, no - * different colours may be laid. THIS MAY NOT BE TRUE FOR ALL GAMES! - */ + // Are there other step-independent special properties owned by the company? + List<SpecialPropertyI> orsps = operatingCompany.get().getPortfolio().getAllSpecialProperties(); + List<SpecialPropertyI> compsps = operatingCompany.get().getSpecialProperties(); + if (compsps != null) orsps.addAll(compsps); - protected void updateAllowedTileColours (String colour, int oldAllowedNumber) { - - if (oldAllowedNumber <= 1) { - tileLaysPerColour.clear(); - log.debug("No more normal tile lays allowed"); - //currentNormalTileLays.clear();// Shouldn't be needed anymore ?? - } else { - List<String> coloursToRemove = new ArrayList<String>(); - for (String key:tileLaysPerColour.viewKeySet()) { - if (colour.equals(key)) { - tileLaysPerColour.put(key, oldAllowedNumber-1); - } else { - coloursToRemove.add(key); + if (orsps != null) { + for (SpecialPropertyI sp : orsps) { + if (!sp.isExercised() && sp.isUsableIfOwnedByCompany() + && sp.isUsableDuringOR(step)) { + if (sp instanceof SpecialTokenLay) { + if (getStep() != GameDef.OrStep.LAY_TOKEN) { + possibleActions.add(new LayBaseToken((SpecialTokenLay)sp)); + } + } else { + possibleActions.add(new UseSpecialProperty(sp)); + } + } + } + } + // Are there other step-independent special properties owned by the president? + orsps = getCurrentPlayer().getPortfolio().getAllSpecialProperties(); + if (orsps != null) { + for (SpecialPropertyI sp : orsps) { + if (!sp.isExercised() && sp.isUsableIfOwnedByPlayer() + && sp.isUsableDuringOR(step)) { + if (sp instanceof SpecialTokenLay) { + if (getStep() != GameDef.OrStep.LAY_TOKEN) { + possibleActions.add(new LayBaseToken((SpecialTokenLay)sp)); + } + } else { + possibleActions.add(new UseSpecialProperty(sp)); + } + } + } } } - // Two-step removal to prevent ConcurrentModificatioonException. - for (String key : coloursToRemove) { - tileLaysPerColour.remove(key); - } - log.debug((oldAllowedNumber - 1) + " additional " + colour - + " tile lays allowed; no other colours"); } - } - public boolean layBaseToken(LayBaseToken action) { + if (doneAllowed) { + possibleActions.add(new NullAction(NullAction.DONE)); + } - String errMsg = null; - int cost = 0; - SpecialTokenLay stl = null; - boolean extra = false; + for (PossibleAction pa : possibleActions.getList()) { + try { + log.debug(operatingCompany.get().getName() + " may: " + pa.toString()); + } catch (Exception e) { + log.error("Error in toString() of " + pa.getClass(), e); + } + } - MapHex hex = action.getChosenHex(); - int station = action.getChosenStation(); - String companyName = operatingCompany.get().getName(); + return true; + } - // TEMPORARY FIX to enable fixing invalidated saved files - //if ("N11".equals(hex.getName()) && station == 2) { - // station = 1; - // action.setChosenStation(1); - //} + /** Stub, can be overridden by subclasses */ + protected void setGameSpecificPossibleActions() { - // Dummy loop to enable a quick jump out. - while (true) { + } - // Checks - // Must be correct step (exception: home base lay & some special token lay) - if (getStep() != GameDef.OrStep.LAY_TOKEN - && action.getType() != LayBaseToken.HOME_CITY - && action.getType() != LayBaseToken.SPECIAL_PROPERTY) { - errMsg = LocalText.getText("WrongActionNoTokenLay"); - break; - } + /*======================================= + * 2.3. TURN CONTROL + *=======================================*/ - if (operatingCompany.get().getNumberOfFreeBaseTokens() == 0) { - errMsg = LocalText.getText("HasNoTokensLeft", companyName); - break; - } + protected void initTurn() { + log.debug("Starting turn of "+operatingCompany.get().getName()); + ReportBuffer.add(" "); + ReportBuffer.add(LocalText.getText("CompanyOperates", + operatingCompany.get().getName(), + operatingCompany.get().getPresident().getName())); + setCurrentPlayer(operatingCompany.get().getPresident()); - if (!isTokenLayAllowed (operatingCompany.get(), hex, station)) { - errMsg = LocalText.getText("BaseTokenSlotIsReserved"); - break; + if (noMapMode && !operatingCompany.get().hasLaidHomeBaseTokens()){ + // Lay base token in noMapMode + BaseToken token = operatingCompany.get().getFreeToken(); + if (token == null) { + log.error("Company " + operatingCompany.get().getName() + " has no free token to lay base token"); + } else { + log.debug("Company " + operatingCompany.get().getName() + " lays base token in nomap mode"); + token.moveTo(bank.getUnavailable()); } + } + operatingCompany.get().initTurn(); + trainsBoughtThisTurn.clear(); + } - if (!hex.hasTokenSlotsLeft(station)) { - errMsg = LocalText.getText("CityHasNoEmptySlots"); - break; - } + protected void finishTurn() { - /* - * TODO: the below condition holds for 1830. in some games, separate - * cities on one tile may hold tokens of the same company; this case - * is not yet covered. - */ - if (hex.hasTokenOfCompany(operatingCompany.get())) { - errMsg = - LocalText.getText("TileAlreadyHasToken", - hex.getName(), - companyName ); - break; - } + if (!operatingCompany.get().isClosed()) { + operatingCompany.get().setOperated(); + companiesOperatedThisRound.add(operatingCompany.get()); - if (action != null) { - List<MapHex> locations = action.getLocations(); - if (locations != null && locations.size() > 0 - && !locations.contains(hex) && !locations.contains(null)) { - errMsg = - LocalText.getText("TokenLayingHexMismatch", - hex.getName(), - action.getLocationNameString() ); - break; - } - stl = action.getSpecialProperty(); - if (stl != null) extra = stl.isExtra(); + // Check if any privates must be closed (now only applies to 1856 W&SR) + // Copy list first to avoid concurrent modifications + for (PrivateCompanyI priv : + new ArrayList<PrivateCompanyI> (operatingCompany.get().getPortfolio().getPrivateCompanies())) { + priv.checkClosingIfExercised(true); } + } - cost = operatingCompany.get().getBaseTokenLayCost(hex); - if (stl != null && stl.isFree()) cost = 0; + if (!finishTurnSpecials()) return; - // Does the company have the money? - if (cost > operatingCompany.get().getCash()) { - errMsg = LocalText.getText("NotEnoughMoney", - companyName, - Bank.format(operatingCompany.get().getCash()), - Bank.format(cost)); - break; - } - break; - } - if (errMsg != null) { - DisplayBuffer.add(LocalText.getText("CannotLayBaseTokenOn", - companyName, - hex.getName(), - Bank.format(cost), - errMsg )); - return false; + if (setNextOperatingCompany(false)) { + setStep(GameDef.OrStep.INITIAL); + } else { + finishOR(); } + } - /* End of validation, start of execution */ - moveStack.start(true); + /** Stub, may be overridden in subclasses + * Return value: + * TRUE = normal turn end; + * FALSE = return immediately from finishTurn(). + */ + protected boolean finishTurnSpecials () { + return true; + } - if (hex.layBaseToken(operatingCompany.get(), station)) { - /* TODO: the false return value must be impossible. */ + protected boolean setNextOperatingCompany(boolean initial) { - operatingCompany.get().layBaseToken(hex, cost); - - // If this is a home base token lay, stop here - if (action.getType() == LayBaseToken.HOME_CITY) { - return true; - } - - if (cost > 0) { - new CashMove(operatingCompany.get(), bank, cost); - ReportBuffer.add(LocalText.getText("LAYS_TOKEN_ON", - companyName, - hex.getName(), - Bank.format(cost) )); + while (true) { + if (initial || operatingCompany.get() == null || operatingCompany == null) { + setOperatingCompany(operatingCompanies.get(0)); + initial = false; } else { - ReportBuffer.add(LocalText.getText("LAYS_FREE_TOKEN_ON", - companyName, - hex.getName() )); - } + int index = operatingCompanies.indexOf(operatingCompany.get()); + if (++index >= operatingCompanies.size()) { + return false; + } - // Was a special property used? - if (stl != null) { - stl.setExercised(); - currentSpecialTokenLays.remove(action); - log.debug("This was a special token lay, " - + (extra ? "" : " not") + " extra"); + // Check if the operating order has changed + List<PublicCompanyI> newOperatingCompanies + = setOperatingCompanies (operatingCompanies.viewList(), operatingCompany.get()); + PublicCompanyI company; + for (int i=0; i<newOperatingCompanies.size(); i++) { + company = newOperatingCompanies.get(i); + if (company != operatingCompanies.get(i)) { + log.debug("Company "+company.getName() + +" replaces "+operatingCompanies.get(i).getName() + +" in operating sequence"); + operatingCompanies.move(company, i); + } + } + setOperatingCompany(operatingCompanies.get(index)); } - // Jump out if we aren't in the token laying step - if (getStep() != GameDef.OrStep.LAY_TOKEN) return true; - - if (!extra) { - currentNormalTokenLays.clear(); - log.debug("This was a normal token lay"); - } + if (operatingCompany.get().isClosed()) continue; - if (currentNormalTokenLays.isEmpty()) { - log.debug("No more normal token lays are allowed"); - } else if (operatingCompany.get().getNumberOfFreeBaseTokens() == 0) { - log.debug("Normal token lay allowed by no more tokens"); - currentNormalTokenLays.clear(); - } else { - log.debug("A normal token lay is still allowed"); - } - setSpecialTokenLays(); - log.debug("There are now " + currentSpecialTokenLays.size() - + " special token lay objects"); - if (currentNormalTokenLays.isEmpty() - && currentSpecialTokenLays.isEmpty()) { - nextStep(); - } + return true; + } + } + protected void setOperatingCompany (PublicCompanyI company) { + if (operatingCompany == null) { + operatingCompany = + new GenericState<PublicCompanyI>("OperatingCompany", company); + } else { + operatingCompany.set(company); } + } - return true; + /** + * Get the public company that has the turn to operate. + * + * @return The currently operating company object. + */ + public PublicCompanyI getOperatingCompany() { + return operatingCompany.get(); } - public boolean layBonusToken(LayBonusToken action) { + public List<PublicCompanyI> getOperatingCompanies() { + return operatingCompanies.viewList(); + } - String errMsg = null; - int cost = 0; - SpecialTokenLay stl = null; - boolean extra = false; + public int getOperatingCompanyIndex() { + int index = operatingCompanies.indexOf(getOperatingCompany()); + return index; + } - MapHex hex = action.getChosenHex(); - BonusToken token = action.getToken(); - // Dummy loop to enable a quick jump out. - while (true) { + /*======================================= + * 2.4. STEP CONTROL + *=======================================*/ - // Checks - MapHex location = action.getChosenHex(); - if (location != hex) { - errMsg = - LocalText.getText("TokenLayingHexMismatch", - hex.getName(), - location.getName() ); - break; - } - stl = action.getSpecialProperty(); - if (stl != null) extra = stl.isExtra(); + /** + * Get the current operating round step (i.e. the next action). + * + * @return The number that defines the next action. + */ + public GameDef.OrStep getStep() { + return (GameDef.OrStep) stepObject.get(); + } - cost = 0; // Let's assume for now that bonus tokens are always - // free - if (stl != null && stl.isFree()) cost = 0; + /** + * Bypass normal order of operations and explicitly set round step. This + * should only be done for specific rails.game exceptions, such as forced + * train purchases. + * + * @param step + */ + protected void setStep(GameDef.OrStep step) { - // Does the company have the money? - if (cost > operatingCompany.get().getCash()) { - errMsg = - LocalText.getText("NotEnoughMoney", - operatingCompany.get().getName()); - break; - } - break; - } - if (errMsg != null) { - DisplayBuffer.add(LocalText.getText("CannotLayBonusTokenOn", - token.getName(), - hex.getName(), - Bank.format(cost), - errMsg )); - return false; - } + stepObject.set(step); - /* End of validation, start of execution */ - moveStack.start(true); + } - if (hex.layBonusToken(token, gameManager.getPhaseManager())) { - /* TODO: the false return value must be impossible. */ + /** + * Internal method: change the OR state to the next step. If the currently + * Operating Company is done, notify this. + * + * @param company The current company. + */ + protected void nextStep() { + nextStep(getStep()); + } - operatingCompany.get().addBonus(new Bonus(operatingCompany.get(), - token.getName(), - token.getValue(), Collections.singletonList(hex))); - token.setUser(operatingCompany.get()); + /** Take the next step after a given one (see nextStep()) */ + protected void nextStep(GameDef.OrStep step) { - ReportBuffer.add(LocalText.getText("LaysBonusTokenOn", - operatingCompany.get().getName(), - token.getName(), - Bank.format(token.getValue()), - hex.getName() )); + PublicCompanyI company = operatingCompany.get(); - // Was a special property used? - if (stl != null) { - stl.setExercised(); - currentSpecialTokenLays.remove(action); - log.debug("This was a special token lay, " - + (extra ? "" : " not") + " extra"); + // Cycle through the steps until we reach one where a user action is + // expected. + int stepIndex; + for (stepIndex = 0; stepIndex < steps.length; stepIndex++) { + if (steps[stepIndex] == step) break; + } + while (++stepIndex < steps.length) { + step = steps[stepIndex]; + log.debug("Step " + step); + if (step == GameDef.OrStep.LAY_TOKEN + && company.getNumberOfFreeBaseTokens() == 0) { + continue; } - } + if (step == GameDef.OrStep.CALC_REVENUE) { - return true; - } + if (!company.canRunTrains()) { + // No trains, then the revenue is zero. + executeSetRevenueAndDividend ( + new SetDividend (0, false, new int[] {SetDividend.NO_TRAIN})); + // TODO: This probably does not handle share selling correctly + continue; + } + } - public boolean buyBonusToken(BuyBonusToken action) { + if (step == GameDef.OrStep.PAYOUT) { + // This step is now obsolete + continue; + } - String errMsg = null; - int cost; - SellBonusToken sbt = null; - CashHolder seller = null; + if (step == GameDef.OrStep.TRADE_SHARES) { - // Dummy loop to enable a quick jump out. - while (true) { + // Is company allowed to trade trasury shares? + if (!company.mayTradeShares() + || !company.hasOperated()) { + continue; + } - // Checks - sbt = action.getSpecialProperty(); - cost = sbt.getPrice(); - seller = sbt.getSeller(); + /* Check if any trading is possible. + * If not, skip this step. + * (but register a Done action for BACKWARDS COMPATIBILITY only) + */ + // Preload some expensive results + int ownShare = company.getPortfolio().getShare(company); + int poolShare = pool.getShare(company); // Expensive, do it once + // Can it buy? + boolean canBuy = + ownShare < getGameParameterAsInt (GameDef.Parm.TREASURY_SHARE_LIMIT) + && company.getCash() >= company.getCurrentSpace().getPrice() + && poolShare > 0; + // Can it sell? + boolean canSell = + company.getPortfolio().getShare(company) > 0 + && poolShare < getGameParameterAsInt (GameDef.Parm.POOL_SHARE_LIMIT); + // Above we ignore the possible existence of double shares (as in 1835). + + if (!canBuy && !canSell) { + // XXX For BACKWARDS COMPATIBILITY only, + // register a Done skip action during reloading. + if (gameManager.isReloading()) { + gameManager.setSkipDone(GameDef.OrStep.TRADE_SHARES); + log.debug("If the next saved action is 'Done', skip it"); + } + log.info("Skipping Treasury share trading step"); + continue; + } + + gameManager.startTreasuryShareTradingRound(); - // Does the company have the money? - if (cost > operatingCompany.get().getCash()) { - errMsg = - LocalText.getText("NotEnoughMoney", - operatingCompany.get().getName(), - Bank.format(operatingCompany.get().getCash()), - Bank.format(cost)); - break; } + + if (!gameSpecificNextStep (step)) continue; + + // No reason found to skip this step break; } - if (errMsg != null) { - DisplayBuffer.add(LocalText.getText("CannotBuyBonusToken", - operatingCompany.get().getName(), - sbt.getName(), - seller.getName(), - Bank.format(cost), - errMsg )); - return false; + + if (step == GameDef.OrStep.FINAL) { + finishTurn(); + } else { + setStep(step); } - /* End of validation, start of execution */ - moveStack.start(true); + } - new CashMove (operatingCompany.get(), seller, cost); - operatingCompany.get().addBonus(new Bonus(operatingCompany.get(), - sbt.getName(), - sbt.getValue(), - sbt.getLocations())); + /** Stub, can be overridden in subclasses to check for extra steps */ + protected boolean gameSpecificNextStep (GameDef.OrStep step) { + return true; + } - ReportBuffer.add(LocalText.getText("BuysBonusTokenFrom", - operatingCompany.get().getName(), - sbt.getName(), - Bank.format(sbt.getValue()), - seller.getName(), - Bank.format(sbt.getPrice()))); + /** + * This method is only called at the start of each step (unlike + * updateStatus(), which is called after each user action) + */ + protected void prepareStep() { + GameDef.OrStep step = stepObject.value(); - sbt.setExercised(); + if (step == GameDef.OrStep.LAY_TRACK) { + // getNormalTileLays(); + } else if (step == GameDef.OrStep.LAY_TOKEN) { - return true; - } + } else { + currentSpecialProperties = null; + } + } + /*======================================= + * 3. COMMON ACTIONS (not bound to steps) + * 3.1. NOOPS + *=======================================*/ - public boolean setRevenueAndDividend(SetDividend action) { + public void skip() { + log.debug("Skip step " + stepObject.value()); + moveStack.start(true); + nextStep(); + } - String errMsg = validateSetRevenueAndDividend (action); + /** + * The current Company is done operating. + * + * @param company Name of the company that finished operating. + * @return False if an error is found. + */ + public boolean done() { - if (errMsg != null) { - DisplayBuffer.add(LocalText.getText( - "CannotProcessRevenue", - Bank.format (action.getActualRevenue()), - action.getCompanyName(), - errMsg - )); + if (operatingCompany.get().getPortfolio().getNumberOfTrains() == 0 + && operatingCompany.get().mustOwnATrain()) { + // FIXME: Need to check for valid route before throwing an + // error. + /* Check TEMPORARILY disabled + errMsg = + LocalText.getText("CompanyMustOwnATrain", + operatingCompany.getObject().getName()); + setStep(STEP_BUY_TRAIN); + DisplayBuffer.add(errMsg); return false; + */ } - moveStack.start(true); + moveStack.start(false); - ReportBuffer.add(LocalText.getText("CompanyRevenue", - action.getCompanyName(), - Bank.format(action.getActualRevenue()))); + nextStep(); - int remainingAmount = checkForDeductions (action); - if (remainingAmount < 0) { - // A share selling round will be run to raise cash to pay debts - return true; + if (getStep() == GameDef.OrStep.FINAL) { + finishTurn(); } - executeSetRevenueAndDividend (action); - return true; - } - protected String validateSetRevenueAndDividend (SetDividend action) { + /*======================================= + * 3.2. DISCARDING TRAINS + *=======================================*/ + + public boolean discardTrain(DiscardTrain action) { + + TrainI train = action.getDiscardedTrain(); + PublicCompanyI company = action.getCompany(); + String companyName = company.getName(); String errMsg = null; - PublicCompanyI company; - String companyName; - int amount = 0; - int revenueAllocation = -1; // Dummy loop to enable a quick jump out. while (true) { - // Checks - // Must be correct company. - company = action.getCompany(); - companyName = company.getName(); - if (company != operatingCompany.get()) { - errMsg = - LocalText.getText("WrongCompany", - companyName, - operatingCompany.get().getName() ); - break; - } // Must be correct step - if (getStep() != GameDef.OrStep.CALC_REVENUE) { - errMsg = LocalText.getText("WrongActionNoRevenue"); + if (getStep() != GameDef.OrStep.BUY_TRAIN + && getStep() != GameDef.OrStep.DISCARD_TRAINS) { + errMsg = LocalText.getText("WrongActionNoDiscardTrain"); break; } - // Amount must be non-negative multiple of 10 - amount = action.getActualRevenue(); - if (amount < 0) { - errMsg = - LocalText.getText("NegativeAmountNotAllowed", - String.valueOf(amount)); - break; - } - if (amount % 10 != 0) { - errMsg = - LocalText.getText("AmountMustBeMultipleOf10", - String.valueOf(amount)); + if (train == null && action.isForced()) { + errMsg = LocalText.getText("NoTrainSpecified"); break; } - // Check chosen revenue distribution - if (amount > 0) { - // Check the allocation type index (see SetDividend for values) - revenueAllocation = action.getRevenueAllocation(); - if (revenueAllocation < 0 - || revenueAllocation >= SetDividend.NUM_OPTIONS) { - errMsg = - LocalText.getText("InvalidAllocationTypeIndex", - String.valueOf(revenueAllocation)); - break; - } - - // Validate the chosen allocation type - int[] allowedAllocations = - ((SetDividend) selectedAction).getAllowedAllocations(); - boolean valid = false; - for (int aa : allowedAllocations) { - if (revenueAllocation == aa) { - valid = true; - break; - } - } - if (!valid) { - errMsg = - LocalText.getText(SetDividend.getAllocationNameKey(revenueAllocation)); - break; - } - } else { - // If there is no revenue, use withhold. - action.setRevenueAllocation(SetDividend.WITHHOLD); - } + // Does the company own such a train? - if (amount == 0 && operatingCompany.get().getNumberOfTrains() == 0) { - DisplayBuffer.add(LocalText.getText("RevenueWithNoTrains", - operatingCompany.get().getName(), - Bank.format(0) )); + if (!company.getPortfolio().getTrainList().contains(train)) { + errMsg = + LocalText.getText("CompanyDoesNotOwnTrain", + company.getName(), + train.getName() ); + break; } break; } + if (errMsg != null) { + DisplayBuffer.add(LocalText.getText("CannotDiscardTrain", + companyName, + (train != null ?train.getName() : "?"), + errMsg )); + return false; + } - return errMsg; - } + /* End of validation, start of execution */ + moveStack.start(true); + // + if (action.isForced()) moveStack.linkToPreviousMoveSet(); - protected void executeSetRevenueAndDividend (SetDividend action) { + // Reset type of dual trains + if (train.getCertType().getPotentialTrainTypes().size() > 1) { + train.setType(null); + } - int amount = action.getActualRevenue(); - int revenueAllocation = action.getRevenueAllocation(); + train.moveTo(train.isObsolete() ? scrapHeap : pool); + ReportBuffer.add(LocalText.getText("CompanyDiscardsTrain", + companyName, + train.getName() )); - operatingCompany.get().setLastRevenue(amount); - operatingCompany.get().setLastRevenueAllocation(revenueAllocation); + // Check if any more companies must discard trains, + // otherwise continue train buying + if (!checkForExcessTrains()) { + // Trains may have been discarded by other players + setCurrentPlayer (operatingCompany.get().getPresident()); + stepObject.set(GameDef.OrStep.BUY_TRAIN); + } - // Pay any debts from treasury, revenue and/or president's cash - // The remaining dividend may be less that the original income - amount = executeDeductions (action); + //setPossibleActions(); - if (amount == 0) { + return true; + } - ReportBuffer.add(LocalText.getText("CompanyDoesNotPayDividend", - operatingCompany.get().getName())); - withhold(amount); + protected void setTrainsToDiscard() { - } else if (revenueAllocation == SetDividend.PAYOUT) { + // Scan the players in SR sequence, starting with the current player + Player player; + List<PublicCompanyI> list; + int currentPlayerIndex = getCurrentPlayerIndex(); + for (int i = currentPlayerIndex; i < currentPlayerIndex + + getNumberOfPlayers(); i++) { + player = gameManager.getPlayerByIndex(i); + if (excessTrainCompanies.containsKey(player)) { + setCurrentPlayer(player); + list = excessTrainCompanies.get(player); + for (PublicCompanyI comp : list) { + possibleActions.add(new DiscardTrain(comp, + comp.getPortfolio().getUniqueTrains(), true)); + // We handle one company at at time. + // We come back here until all excess trains have been + // discarded. + return; + } + } + } + } + /*======================================= + * 3.3. PRIVATES (BUYING, SELLING, CLOSING) + *=======================================*/ - ReportBuffer.add(LocalText.getText("CompanyPaysOutFull", - operatingCompany.get().getName(), Bank.format(amount) )); + public boolean buyPrivate(BuyPrivate action) { - payout(amount); + String errMsg = null; + PublicCompanyI publicCompany = action.getCompany(); + String publicCompanyName = publicCompany.getName(); + PrivateCompanyI privateCompany = action.getPrivateCompany(); + String privateCompanyName = privateCompany.getName(); + int price = action.getPrice(); + CashHolder owner = null; + Player player = null; + int upperPrice; + int lowerPrice; - } else if (revenueAllocation == SetDividend.SPLIT) { + // Dummy loop to enable a quick jump out. + while (true) { - ReportBuffer.add(LocalText.getText("CompanySplits", - operatingCompany.get().getName(), Bank.format(amount) )); + // Checks + // Does private exist? + if ((privateCompany = + companyManager.getPrivateCompany( + privateCompanyName)) == null) { + errMsg = + LocalText.getText("PrivateDoesNotExist", + privateCompanyName); + break; + } + // Is private still open? + if (privateCompany.isClosed()) { + errMsg = + LocalText.getText("PrivateIsAlreadyClosed", + privateCompanyName); + break; + } + // Is private owned by a player? + owner = privateCompany.getPortfolio().getOwner(); + if (!(owner instanceof Player)) { + errMsg = + LocalText.getText("PrivateIsNotOwnedByAPlayer", + privateCompanyName); + break; + } + player = (Player) owner; + upperPrice = privateCompany.getUpperPrice(); + lowerPrice = privateCompany.getLowerPrice(); - splitRevenue(amount); + // Is private buying allowed? + if (!isPrivateSellingAllowed()) { + errMsg = LocalText.getText("PrivateBuyingIsNotAllowed"); + break; + } - } else if (revenueAllocation == SetDividend.WITHHOLD) { + // Price must be in the allowed range + if (lowerPrice != PrivateCompanyI.NO_PRICE_LIMIT && price < lowerPrice) { + errMsg = + LocalText.getText("PriceBelowLowerLimit", + Bank.format(price), + Bank.format(lowerPrice), + privateCompanyName ); + break; + } + if (upperPrice != PrivateCompanyI.NO_PRICE_LIMIT && price > upperPrice) { + errMsg = + LocalText.getText("PriceAboveUpperLimit", + Bank.format(price), + Bank.format(lowerPrice), + privateCompanyName ); + break; + } + // Does the company have the money? + if (price > operatingCompany.get().getCash()) { + errMsg = + LocalText.getText("NotEnoughMoney", + publicCompanyName, + Bank.format(operatingCompany.get().getCash()), + Bank.format(price) ); + break; + } + break; + } + if (errMsg != null) { + if (owner != null) { + DisplayBuffer.add(LocalText.getText("CannotBuyPrivateFromFor", + publicCompanyName, + privateCompanyName, + owner.getName(), + Bank.format(price), + errMsg )); + } else { + DisplayBuffer.add(LocalText.getText("CannotBuyPrivateFor", + publicCompanyName, + privateCompanyName, + Bank.format(price), + errMsg )); + } + return false; + } - ReportBuffer.add(LocalText.getText("CompanyWithholds", - operatingCompany.get().getName(), - Bank.format(amount) )); + moveStack.start(true); - withhold(amount); + operatingCompany.get().buyPrivate(privateCompany, player.getPortfolio(), + price); + + return true; + + } + + protected boolean isPrivateSellingAllowed() { + return getCurrentPhase().isPrivateSellingAllowed(); + } + protected int getPrivateMinimumPrice (PrivateCompanyI privComp) { + int minPrice = privComp.getLowerPrice(); + if (minPrice == PrivateCompanyI.NO_PRICE_LIMIT) { + minPrice = 0; } + return minPrice; + } - // Rust any obsolete trains - operatingCompany.get().getPortfolio().rustObsoleteTrains(); + protected int getPrivateMaximumPrice (PrivateCompanyI privComp) { + int maxPrice = privComp.getUpperPrice(); + if (maxPrice == PrivateCompanyI.NO_PRICE_LIMIT) { + maxPrice = operatingCompany.get().getCash(); + } + return maxPrice; + } - // We have done the payout step, so continue from there - nextStep(GameDef.OrStep.PAYOUT); + protected boolean maySellPrivate (Player player) { + return true; } - /** - * Distribute the dividend amongst the shareholders. - * - * @param amount - */ - public void payout(int amount) { + protected boolean executeClosePrivate(ClosePrivate action) { - if (amount == 0) return; + PrivateCompanyI priv = action.getPrivateCompany(); - int part; - int shares; + log.debug("Executed close private action for private " + priv.getName()); - Map<CashHolder, Integer> sharesPerRecipient = countSharesPerRecipient(); + String errMsg = null; - // Calculate, round up, report and add the cash + if (priv.isClosed()) + errMsg = LocalText.getText("PrivateAlreadyClosed", priv.getName()); - // Define a precise sequence for the reporting - Set<CashHolder> recipientSet = sharesPerRecipient.keySet(); - for (CashHolder recipient : SequenceUtil.sortCashHolders(recipientSet)) { - if (recipient instanceof Bank) continue; - shares = (sharesPerRecipient.get(recipient)); - if (shares == 0) continue; - part = (int) Math.ceil(amount * shares * operatingCompany.get().getShareUnit() / 100.0); - ReportBuffer.add(LocalText.getText("Payout", - recipient.getName(), - Bank.format(part), - shares, - operatingCompany.get().getShareUnit())); - pay (bank, recipient, part); + if (errMsg != null) { + DisplayBuffer.add(errMsg); + return false; } - // Move the token - operatingCompany.get().payout(amount); + moveStack.start(true); - } + priv.setClosed(); - protected Map<CashHolder, Integer> countSharesPerRecipient () { + return true; + } - Map<CashHolder, Integer> sharesPerRecipient = new HashMap<CashHolder, Integer>(); + /*======================================= + * 3.4. DESTINATIONS + *=======================================*/ - // Changed to accomodate the CGR 5% share roundup rule. - // For now it is assumed, that actual payouts are always rounded up - // (the withheld half of split revenues is not handled here, see splitRevenue()). + /** Stub for applying any follow-up actions when + * a company reaches it destinations. + * Default version: no actions. + * @param company + */ + protected void reachDestination (PublicCompanyI company) { - // First count the shares per recipient - for (PublicCertificateI cert : operatingCompany.get().getCertificates()) { - CashHolder recipient = getBeneficiary(cert); - if (!sharesPerRecipient.containsKey(recipient)) { - sharesPerRecipient.put(recipient, cert.getShares()); - } else { - sharesPerRecipient.put(recipient, - sharesPerRecipient.get(recipient) + cert.getShares()); - } - } - return sharesPerRecipient; } - /** Who gets the per-share revenue? */ - protected CashHolder getBeneficiary(PublicCertificateI cert) { + public boolean reachDestinations (ReachDestinations action) { - Portfolio holder = cert.getPortfolio(); - CashHolder beneficiary = holder.getOwner(); - // Special cases apply if the holder is the IPO or the Pool - if (operatingCompany.get().paysOutToTreasury(cert)) { - beneficiary = operatingCompany.get(); + List<PublicCompanyI> destinedCompanies + = action.getReachedCompanies(); + if (destinedCompanies != null) { + for (PublicCompanyI company : destinedCompanies) { + if (company.hasDestination() + && !company.hasReachedDestination()) { + if (!moveStack.isOpen()) moveStack.start(true); + company.setReachedDestination(true); + ReportBuffer.add(LocalText.getText("DestinationReached", + company.getName(), + company.getDestinationHex().getName() + )); + // Process any consequences of reaching a destination + // (default none) + reachDestination (company); + } + } } - return beneficiary; + return true; } /** - * Withhold a given amount of revenue (and store it). - * - * @param The revenue amount. + * This is currently a stub, as it is unclear if there is a common + * rule for setting destination reaching options. + * See OperatingRound_1856 for a first implementation + * of such rules. */ - public void withhold(int amount) { + protected void setDestinationActions () { - PublicCompanyI company = operatingCompany.get(); + } - // Payout revenue to company - pay (bank, company, amount); + /*======================================= + * ... [truncated message content] |
From: Stefan F. <ste...@us...> - 2011-08-11 16:06:04
|
data/profiles/test.profile | 2 test/data/real/1830_A.report | 2770 ++++++++++++------------- test/data/real/1856_A.report | 2782 +++++++++++++------------- test/data/real/1889_A.report | 838 +++---- test/data/real/1889_B.report | 1760 ++++++++-------- test/data/real/1889_C.report | 1946 +++++++++--------- test/data/real/18AL_A.report | 1346 ++++++------ test/data/real/18EU_A.report | 2512 +++++++++++------------ test/data/test/1830_5forDtrainExchange.report | 616 ++--- test/data/test/1835_PR_3rdTrain.report | 1408 ++++++------- test/data/test/1851_Late.report | 772 +++---- test/data/test/1856_2nd6T+PrezCash2.report | 1386 ++++++------ test/data/test/18EU_After2nd8Train.report | 1374 ++++++------ 13 files changed, 9756 insertions(+), 9756 deletions(-) New commits: commit 19de64c86ec5397d86972bad5b06f454c1ca8aa0 Author: Stefan Frey <ste...@we...> Date: Thu Aug 11 18:08:07 2011 +0200 Updated test.profile such that reports contain no currency identifier Updated reports accordingly diff --git a/data/profiles/test.profile b/data/profiles/test.profile index 06be5fc..2b39565 100644 --- a/data/profiles/test.profile +++ b/data/profiles/test.profile @@ -26,7 +26,7 @@ locale=te_ST # An overriding format can be specified here, but then applies to all games. # The @ character must be present and is replaced by the amount. # Example: �@ to specify a pound sign prefix: �100. -#money_format=$@ +money_format=@ ### Save file directory # If the below entry exists, is not empty, and specifies an existing diff --git a/test/data/real/1830_A.report b/test/data/real/1830_A.report index 0302cf7..9e6782f 100644 --- a/test/data/real/1830_A.report +++ b/test/data/real/1830_A.report @@ -4,31 +4,31 @@ PlayerIs,2,Si PlayerIs,3,Ed PlayerIs,4,Phil PlayerIs,5,Chris -PlayerCash,$480 -BankHas,$17600 +PlayerCash,480 +BankHas,17600 StartOfPhase,2 -BankSizeIs,$17600 +BankSizeIs,17600 StartOfInitialRound HasPriority,Marcus -BID_ITEM_LOG,Marcus,$115,M&H,$365 -BID_ITEM_LOG,Si,$165,C&A,$315 -BID_ITEM_LOG,Ed,$170,C&A,$310 -BID_ITEM_LOG,Phil,$75,D&H,$405 -BID_ITEM_LOG,Chris,$45,C&StL,$435 -BuysItemFor,Marcus,SVNRR,$20 -BuysItemFor,Chris,C&StL,$45 -BuysItemFor,Phil,D&H,$75 -BuysItemFor,Marcus,M&H,$115 +BID_ITEM_LOG,Marcus,115,M&H,365 +BID_ITEM_LOG,Si,165,C&A,315 +BID_ITEM_LOG,Ed,170,C&A,310 +BID_ITEM_LOG,Phil,75,D&H,405 +BID_ITEM_LOG,Chris,45,C&StL,435 +BuysItemFor,Marcus,SVNRR,20 +BuysItemFor,Chris,C&StL,45 +BuysItemFor,Phil,D&H,75 +BuysItemFor,Marcus,M&H,115 TO_AUCTION,C&A -BID_ITEM_LOG,Si,$175,C&A,$305 -BID_ITEM_LOG,Ed,$180,C&A,$300 -BID_ITEM_LOG,Si,$185,C&A,$295 -BID_ITEM_LOG,Ed,$190,C&A,$290 -BID_ITEM_LOG,Si,$195,C&A,$285 -BID_ITEM_LOG,Ed,$200,C&A,$280 -BID_ITEM_LOG,Si,$210,C&A,$270 +BID_ITEM_LOG,Si,175,C&A,305 +BID_ITEM_LOG,Ed,180,C&A,300 +BID_ITEM_LOG,Si,185,C&A,295 +BID_ITEM_LOG,Ed,190,C&A,290 +BID_ITEM_LOG,Si,195,C&A,285 +BID_ITEM_LOG,Ed,200,C&A,280 +BID_ITEM_LOG,Si,210,C&A,270 PASSES,Ed -BuysItemFor,Si,C&A,$210 +BuysItemFor,Si,C&A,210 ALSO_GETS,Si,CERT_NAME,RDG,10 PASSES,Si PASSES,Ed @@ -36,60 +36,60 @@ PASSES,Phil PASSES,Chris PASSES,Marcus ALL_PASSED -Has,Marcus,$345 -Has,Si,$270 -Has,Ed,$480 -Has,Phil,$405 -Has,Chris,$435 +Has,Marcus,345 +Has,Si,270 +Has,Ed,480 +Has,Phil,405 +Has,Chris,435 START_OR,0.0 -ReceivesFor,Marcus,$5,SVNRR -ReceivesFor,Chris,$10,C&StL -ReceivesFor,Phil,$15,D&H -ReceivesFor,Marcus,$20,M&H -ReceivesFor,Si,$25,C&A +ReceivesFor,Marcus,5,SVNRR +ReceivesFor,Chris,10,C&StL +ReceivesFor,Phil,15,D&H +ReceivesFor,Marcus,20,M&H +ReceivesFor,Si,25,C&A ShortORExecuted -Has,Marcus,$370 -Has,Si,$295 -Has,Ed,$480 -Has,Phil,$420 -Has,Chris,$445 +Has,Marcus,370 +Has,Si,295 +Has,Ed,480 +Has,Phil,420 +Has,Chris,445 StartOfInitialRound HasPriority,Si PASSES,Si -BuysItemFor,Ed,B&O,$220 +BuysItemFor,Ed,B&O,220 ALSO_GETS,Ed,PRES_CERT_NAME,B&O,20 -Has,Marcus,$370 -Has,Si,$295 -Has,Ed,$260 -Has,Phil,$420 -Has,Chris,$445 +Has,Marcus,370 +Has,Si,295 +Has,Ed,260 +Has,Phil,420 +Has,Chris,445 StartStockRound,1 HasPriority,Phil -START_COMPANY_LOG,Phil,NYC,$67,$134,2,20,BANK -START_COMPANY_LOG,Chris,N&W,$71,$142,2,20,BANK -START_COMPANY_LOG,Marcus,NYNH,$71,$142,2,20,BANK -BUY_SHARE_LOG,Si,10,NYC,IPO,$67 -BUY_SHARE_LOG,Ed,10,NYNH,IPO,$71 -BUY_SHARE_LOG,Phil,10,NYC,IPO,$67 -BUY_SHARE_LOG,Chris,10,N&W,IPO,$71 -BUY_SHARE_LOG,Marcus,10,NYNH,IPO,$71 -BUY_SHARE_LOG,Si,10,NYC,IPO,$67 -BUY_SHARE_LOG,Ed,10,NYNH,IPO,$71 -BUY_SHARE_LOG,Phil,10,NYC,IPO,$67 -FloatsWithCash,NYC,$670 -BUY_SHARE_LOG,Chris,10,N&W,IPO,$71 -BUY_SHARE_LOG,Marcus,10,NYNH,IPO,$71 -FloatsWithCash,NYNH,$710 -BUY_SHARE_LOG,Si,10,NYC,IPO,$67 +START_COMPANY_LOG,Phil,NYC,67,134,2,20,BANK +START_COMPANY_LOG,Chris,N&W,71,142,2,20,BANK +START_COMPANY_LOG,Marcus,NYNH,71,142,2,20,BANK +BUY_SHARE_LOG,Si,10,NYC,IPO,67 +BUY_SHARE_LOG,Ed,10,NYNH,IPO,71 +BUY_SHARE_LOG,Phil,10,NYC,IPO,67 +BUY_SHARE_LOG,Chris,10,N&W,IPO,71 +BUY_SHARE_LOG,Marcus,10,NYNH,IPO,71 +BUY_SHARE_LOG,Si,10,NYC,IPO,67 +BUY_SHARE_LOG,Ed,10,NYNH,IPO,71 +BUY_SHARE_LOG,Phil,10,NYC,IPO,67 +FloatsWithCash,NYC,670 +BUY_SHARE_LOG,Chris,10,N&W,IPO,71 +BUY_SHARE_LOG,Marcus,10,NYNH,IPO,71 +FloatsWithCash,NYNH,710 +BUY_SHARE_LOG,Si,10,NYC,IPO,67 Autopasses,Ed -BUY_SHARE_LOG,Phil,10,NYC,IPO,$67 -BUY_SHARE_LOG,Chris,10,N&W,IPO,$71 -BUY_SHARE_LOG,Marcus,10,NYNH,IPO,$71 -BUY_SHARE_LOG,Si,10,NYC,IPO,$67 -BUY_SHARE_LOG,Ed,10,NYC,IPO,$67 +BUY_SHARE_LOG,Phil,10,NYC,IPO,67 +BUY_SHARE_LOG,Chris,10,N&W,IPO,71 +BUY_SHARE_LOG,Marcus,10,NYNH,IPO,71 +BUY_SHARE_LOG,Si,10,NYC,IPO,67 +BUY_SHARE_LOG,Ed,10,NYC,IPO,67 Autopasses,Phil -BUY_SHARE_LOG,Chris,10,N&W,IPO,$71 -FloatsWithCash,N&W,$710 +BUY_SHARE_LOG,Chris,10,N&W,IPO,71 +FloatsWithCash,N&W,710 PASSES,Marcus PASSES,Si PASSES,Ed @@ -97,67 +97,67 @@ Autopasses,Phil PASSES,Chris END_SR,1 -PRICE_MOVES_LOG,NYC,$67,G6,$71,G5 -SoldOut,NYC,$67,G6,$71,G5 -Has,N&W,$710 -Has,NYC,$670 -Has,NYNH,$710 -Has,Marcus,$15 -Has,Si,$27 -Has,Ed,$51 -Has,Phil,$85 -Has,Chris,$19 +PRICE_MOVES_LOG,NYC,67,G6,71,G5 +SoldOut,NYC,67,G6,71,G5 +Has,N&W,710 +Has,NYC,670 +Has,NYNH,710 +Has,Marcus,15 +Has,Si,27 +Has,Ed,51 +Has,Phil,85 +Has,Chris,19 START_OR,1.1 -ReceivesFor,Marcus,$5,SVNRR -ReceivesFor,Chris,$10,C&StL -ReceivesFor,Phil,$15,D&H -ReceivesFor,Marcus,$20,M&H -ReceivesFor,Si,$25,C&A -ReceivesFor,Ed,$30,B&O +ReceivesFor,Marcus,5,SVNRR +ReceivesFor,Chris,10,C&StL +ReceivesFor,Phil,15,D&H +ReceivesFor,Marcus,20,M&H +ReceivesFor,Si,25,C&A +ReceivesFor,Ed,30,B&O CompanyOperates,N&W,Chris LaysTileAt,N&W,9,L14,W CompanyDoesNotPayDividend,N&W -PRICE_MOVES_LOG,N&W,$71,G5,$67,F5 -BuysTrain,N&W,2,IPO,$80 +PRICE_MOVES_LOG,N&W,71,G5,67,F5 +BuysTrain,N&W,2,IPO,80 FirstTrainBought,2 CompanyOperates,NYNH,Marcus LaysTileAt,NYNH,57,F20,SW CompanyDoesNotPayDividend,NYNH -PRICE_MOVES_LOG,NYNH,$71,G5,$67,F5 -BuysTrain,NYNH,2,IPO,$80 +PRICE_MOVES_LOG,NYNH,71,G5,67,F5 +BuysTrain,NYNH,2,IPO,80 CompanyOperates,NYC,Phil LaysTileAt,NYC,57,E19,NE CompanyDoesNotPayDividend,NYC -PRICE_MOVES_LOG,NYC,$71,G5,$67,F5 -BuysTrain,NYC,2,IPO,$80 -BuysTrain,NYC,2,IPO,$80 -BuysTrain,NYC,2,IPO,$80 -BuysTrain,NYC,2,IPO,$80 +PRICE_MOVES_LOG,NYC,71,G5,67,F5 +BuysTrain,NYC,2,IPO,80 +BuysTrain,NYC,2,IPO,80 +BuysTrain,NYC,2,IPO,80 +BuysTrain,NYC,2,IPO,80 All 2-trains are sold out, 3-trains now available EndOfOperatingRound,1.1 -ORWorthIncrease,Marcus,1.1,$5 -ORWorthIncrease,Si,1.1,$9 -ORWorthIncrease,Ed,1.1,$18 -ORWorthIncrease,Phil,1.1,-$5 -ORWorthIncrease,Chris,1.1,-$14 -Has,N&W,$630 -Has,NYC,$350 -Has,NYNH,$630 -Has,Marcus,$40 -Has,Si,$52 -Has,Ed,$81 -Has,Phil,$100 -Has,Chris,$29 +ORWorthIncrease,Marcus,1.1,5 +ORWorthIncrease,Si,1.1,9 +ORWorthIncrease,Ed,1.1,18 +ORWorthIncrease,Phil,1.1,-5 +ORWorthIncrease,Chris,1.1,-14 +Has,N&W,630 +Has,NYC,350 +Has,NYNH,630 +Has,Marcus,40 +Has,Si,52 +Has,Ed,81 +Has,Phil,100 +Has,Chris,29 StartStockRound,2 HasPriority,Marcus PASSES,Marcus PASSES,Si -BUY_SHARE_LOG,Ed,10,NYNH,IPO,$71 -BUY_SHARE_LOG,Phil,10,N&W,IPO,$71 +BUY_SHARE_LOG,Ed,10,NYNH,IPO,71 +BUY_SHARE_LOG,Phil,10,N&W,IPO,71 PASSES,Chris PASSES,Marcus PASSES,Si @@ -165,71 +165,71 @@ PASSES,Ed PASSES,Phil END_SR,2 -PRICE_MOVES_LOG,NYC,$67,F5,$71,F4 -SoldOut,NYC,$67,F5,$71,F4 -Has,N&W,$630 -Has,NYC,$350 -Has,NYNH,$630 -Has,Marcus,$40 -Has,Si,$52 -Has,Ed,$10 -Has,Phil,$29 -Has,Chris,$29 +PRICE_MOVES_LOG,NYC,67,F5,71,F4 +SoldOut,NYC,67,F5,71,F4 +Has,N&W,630 +Has,NYC,350 +Has,NYNH,630 +Has,Marcus,40 +Has,Si,52 +Has,Ed,10 +Has,Phil,29 +Has,Chris,29 START_OR,2.1 -ReceivesFor,Marcus,$5,SVNRR -ReceivesFor,Chris,$10,C&StL -ReceivesFor,Phil,$15,D&H -ReceivesFor,Marcus,$20,M&H -ReceivesFor,Si,$25,C&A -ReceivesFor,Ed,$30,B&O +ReceivesFor,Marcus,5,SVNRR +ReceivesFor,Chris,10,C&StL +ReceivesFor,Phil,15,D&H +ReceivesFor,Marcus,20,M&H +ReceivesFor,Si,25,C&A +ReceivesFor,Ed,30,B&O CompanyOperates,NYC,Phil LaysTileAt,NYC,8,F18,W -CompanyRevenue,NYC,$0 +CompanyRevenue,NYC,0 CompanyDoesNotPayDividend,NYC -PRICE_MOVES_LOG,NYC,$71,F4,$66,E4 +PRICE_MOVES_LOG,NYC,71,F4,66,E4 CompanyOperates,N&W,Chris LaysTileAt,N&W,9,L12,W CorrectionModeActivate,Chris,CORRECT_CASH -CorrectCashSubstractMoney,N&W,$140 +CorrectCashSubstractMoney,N&W,140 CorrectionModeDeactivate,Chris,CORRECT_CASH -CompanyRevenue,N&W,$70 -CompanyPaysOutFull,N&W,$70 -Payout,Phil,$7,1,10 -Payout,Chris,$42,6,10 -PRICE_MOVES_LOG,N&W,$67,F5,$71,G5 +CompanyRevenue,N&W,70 +CompanyPaysOutFull,N&W,70 +Payout,Phil,7,1,10 +Payout,Chris,42,6,10 +PRICE_MOVES_LOG,N&W,67,F5,71,G5 CompanyOperates,NYNH,Marcus -LaysTileAtFor,NYNH,9,E21,SW,$120 -CompanyRevenue,NYNH,$60 -CompanyPaysOutFull,NYNH,$60 -Payout,Ed,$18,3,10 -Payout,Marcus,$30,5,10 -PRICE_MOVES_LOG,NYNH,$67,F5,$71,G5 -BuysTrain,NYNH,3,IPO,$180 +LaysTileAtFor,NYNH,9,E21,SW,120 +CompanyRevenue,NYNH,60 +CompanyPaysOutFull,NYNH,60 +Payout,Ed,18,3,10 +Payout,Marcus,30,5,10 +PRICE_MOVES_LOG,NYNH,67,F5,71,G5 +BuysTrain,NYNH,3,IPO,180 FirstTrainBought,3 StartOfPhase,3 EndOfOperatingRound,2.1 -ORWorthIncrease,Marcus,2.1,$75 -ORWorthIncrease,Si,2.1,$5 -ORWorthIncrease,Ed,2.1,$55 -ORWorthIncrease,Phil,2.1,$1 -ORWorthIncrease,Chris,2.1,$76 -Has,N&W,$490 -Has,NYC,$350 -Has,NYNH,$330 -Has,Marcus,$95 -Has,Si,$77 -Has,Ed,$58 -Has,Phil,$51 -Has,Chris,$81 +ORWorthIncrease,Marcus,2.1,75 +ORWorthIncrease,Si,2.1,5 +ORWorthIncrease,Ed,2.1,55 +ORWorthIncrease,Phil,2.1,1 +ORWorthIncrease,Chris,2.1,76 +Has,N&W,490 +Has,NYC,350 +Has,NYNH,330 +Has,Marcus,95 +Has,Si,77 +Has,Ed,58 +Has,Phil,51 +Has,Chris,81 StartStockRound,3 HasPriority,Chris -BUY_SHARE_LOG,Chris,10,NYNH,IPO,$71 -BUY_SHARE_LOG,Marcus,10,NYNH,IPO,$71 -BUY_SHARE_LOG,Si,10,N&W,IPO,$71 +BUY_SHARE_LOG,Chris,10,NYNH,IPO,71 +BUY_SHARE_LOG,Marcus,10,NYNH,IPO,71 +BUY_SHARE_LOG,Si,10,N&W,IPO,71 PASSES,Ed PASSES,Phil PASSES,Chris @@ -237,155 +237,155 @@ PASSES,Marcus PASSES,Si END_SR,3 -PRICE_MOVES_LOG,NYNH,$71,G5,$76,G4 -SoldOut,NYNH,$71,G5,$76,G4 -PRICE_MOVES_LOG,NYC,$66,E4,$70,E3 -SoldOut,NYC,$66,E4,$70,E3 -Has,N&W,$490 -Has,NYC,$350 -Has,NYNH,$330 -Has,Marcus,$24 -Has,Si,$6 -Has,Ed,$58 -Has,Phil,$51 -Has,Chris,$10 +PRICE_MOVES_LOG,NYNH,71,G5,76,G4 +SoldOut,NYNH,71,G5,76,G4 +PRICE_MOVES_LOG,NYC,66,E4,70,E3 +SoldOut,NYC,66,E4,70,E3 +Has,N&W,490 +Has,NYC,350 +Has,NYNH,330 +Has,Marcus,24 +Has,Si,6 +Has,Ed,58 +Has,Phil,51 +Has,Chris,10 START_OR,3.1 -ReceivesFor,Marcus,$5,SVNRR -ReceivesFor,Chris,$10,C&StL -ReceivesFor,Phil,$15,D&H -ReceivesFor,Marcus,$20,M&H -ReceivesFor,Si,$25,C&A -ReceivesFor,Ed,$30,B&O +ReceivesFor,Marcus,5,SVNRR +ReceivesFor,Chris,10,C&StL +ReceivesFor,Phil,15,D&H +ReceivesFor,Marcus,20,M&H +ReceivesFor,Si,25,C&A +ReceivesFor,Ed,30,B&O CompanyOperates,NYNH,Marcus -LaysTileAtFor,NYNH,54,G19,SW,$80 -CompanyRevenue,NYNH,$80 -CompanyPaysOutFull,NYNH,$80 -Payout,Ed,$24,3,10 -Payout,Marcus,$48,6,10 -Payout,Chris,$8,1,10 -PRICE_MOVES_LOG,NYNH,$76,G4,$82,H4 +LaysTileAtFor,NYNH,54,G19,SW,80 +CompanyRevenue,NYNH,80 +CompanyPaysOutFull,NYNH,80 +Payout,Ed,24,3,10 +Payout,Marcus,48,6,10 +Payout,Chris,8,1,10 +PRICE_MOVES_LOG,NYNH,76,G4,82,H4 CompanyOperates,N&W,Chris -LaysTileAtFor,N&W,9,K15,NW,$40 -CompanyRevenue,N&W,$70 -CompanyPaysOutFull,N&W,$70 -Payout,Chris,$42,6,10 -Payout,Phil,$7,1,10 -Payout,Si,$7,1,10 -PRICE_MOVES_LOG,N&W,$71,G5,$76,H5 -BuysTrain,N&W,3,IPO,$180 +LaysTileAtFor,N&W,9,K15,NW,40 +CompanyRevenue,N&W,70 +CompanyPaysOutFull,N&W,70 +Payout,Chris,42,6,10 +Payout,Phil,7,1,10 +Payout,Si,7,1,10 +PRICE_MOVES_LOG,N&W,71,G5,76,H5 +BuysTrain,N&W,3,IPO,180 CompanyOperates,NYC,Phil -BuysPrivateFromFor,NYC,D&H,Phil,$140 -LaysTileAtFor,NYC,57,F16,W,$120 +BuysPrivateFromFor,NYC,D&H,Phil,140 +LaysTileAtFor,NYC,57,F16,W,120 LAYS_FREE_TOKEN_ON,NYC,F16 -CompanyRevenue,NYC,$40 -CompanyPaysOutFull,NYC,$40 -Payout,Ed,$4,1,10 -Payout,Phil,$20,5,10 -Payout,Si,$16,4,10 -PRICE_MOVES_LOG,NYC,$70,E3,$76,F3 +CompanyRevenue,NYC,40 +CompanyPaysOutFull,NYC,40 +Payout,Ed,4,1,10 +Payout,Phil,20,5,10 +Payout,Si,16,4,10 +PRICE_MOVES_LOG,NYC,70,E3,76,F3 EndOfOperatingRound,3.1 -ORWorthIncrease,Marcus,3.1,$109 -ORWorthIncrease,Si,3.1,$77 -ORWorthIncrease,Ed,3.1,$82 -ORWorthIncrease,Phil,3.1,$147 -ORWorthIncrease,Chris,3.1,$96 -Has,N&W,$270 -Has,NYC,$90 -Has,NYNH,$250 -Has,Marcus,$97 -Has,Si,$54 -Has,Ed,$116 -Has,Phil,$233 -Has,Chris,$70 +ORWorthIncrease,Marcus,3.1,109 +ORWorthIncrease,Si,3.1,77 +ORWorthIncrease,Ed,3.1,82 +ORWorthIncrease,Phil,3.1,147 +ORWorthIncrease,Chris,3.1,96 +Has,N&W,270 +Has,NYC,90 +Has,NYNH,250 +Has,Marcus,97 +Has,Si,54 +Has,Ed,116 +Has,Phil,233 +Has,Chris,70 START_OR,3.2 -ReceivesFor,Marcus,$5,SVNRR -ReceivesFor,Chris,$10,C&StL -ReceivesFor,NYC,$15,D&H -ReceivesFor,Marcus,$20,M&H -ReceivesFor,Si,$25,C&A -ReceivesFor,Ed,$30,B&O +ReceivesFor,Marcus,5,SVNRR +ReceivesFor,Chris,10,C&StL +ReceivesFor,NYC,15,D&H +ReceivesFor,Marcus,20,M&H +ReceivesFor,Si,25,C&A +ReceivesFor,Ed,30,B&O CompanyOperates,NYNH,Marcus LaysTileAt,NYNH,25,F18,W -CompanyRevenue,NYNH,$160 -CompanyPaysOutFull,NYNH,$160 -Payout,Ed,$48,3,10 -Payout,Marcus,$96,6,10 -Payout,Chris,$16,1,10 -PRICE_MOVES_LOG,NYNH,$82,H4,$90,I4 +CompanyRevenue,NYNH,160 +CompanyPaysOutFull,NYNH,160 +Payout,Ed,48,3,10 +Payout,Marcus,96,6,10 +Payout,Chris,16,1,10 +PRICE_MOVES_LOG,NYNH,82,H4,90,I4 CompanyOperates,N&W,Chris -LaysTileAtFor,N&W,57,J14,NW,$80 -CompanyRevenue,N&W,$120 -CompanyPaysOutFull,N&W,$120 -Payout,Phil,$12,1,10 -Payout,Chris,$72,6,10 -Payout,Si,$12,1,10 -PRICE_MOVES_LOG,N&W,$76,H5,$82,I5 -BuysPrivateFromFor,N&W,C&StL,Chris,$20 +LaysTileAtFor,N&W,57,J14,NW,80 +CompanyRevenue,N&W,120 +CompanyPaysOutFull,N&W,120 +Payout,Phil,12,1,10 +Payout,Chris,72,6,10 +Payout,Si,12,1,10 +PRICE_MOVES_LOG,N&W,76,H5,82,I5 +BuysPrivateFromFor,N&W,C&StL,Chris,20 CompanyOperates,NYC,Phil LaysTileAt,NYC,14,F16,W -CompanyRevenue,NYC,$90 -CompanyPaysOutFull,NYC,$90 -Payout,Ed,$9,1,10 -Payout,Phil,$45,5,10 -Payout,Si,$36,4,10 -PRICE_MOVES_LOG,NYC,$76,F3,$82,G3 +CompanyRevenue,NYC,90 +CompanyPaysOutFull,NYC,90 +Payout,Ed,9,1,10 +Payout,Phil,45,5,10 +Payout,Si,36,4,10 +PRICE_MOVES_LOG,NYC,76,F3,82,G3 EndOfOperatingRound,3.2 -ORWorthIncrease,Marcus,3.2,$169 -ORWorthIncrease,Si,3.2,$103 -ORWorthIncrease,Ed,3.2,$117 -ORWorthIncrease,Phil,3.2,$93 -ORWorthIncrease,Chris,3.2,$122 -Has,N&W,$170 -Has,NYC,$105 -Has,NYNH,$250 -Has,Marcus,$218 -Has,Si,$127 -Has,Ed,$203 -Has,Phil,$290 -Has,Chris,$188 +ORWorthIncrease,Marcus,3.2,169 +ORWorthIncrease,Si,3.2,103 +ORWorthIncrease,Ed,3.2,117 +ORWorthIncrease,Phil,3.2,93 +ORWorthIncrease,Chris,3.2,122 +Has,N&W,170 +Has,NYC,105 +Has,NYNH,250 +Has,Marcus,218 +Has,Si,127 +Has,Ed,203 +Has,Phil,290 +Has,Chris,188 StartStockRound,4 HasPriority,Ed -SELL_SHARE_LOG,Ed,10,NYC,$82 -PRICE_MOVES_LOG,NYC,$82,G3,$76,G4 -SELL_SHARES_LOG,Ed,3,10,30,NYNH,$270 -PRICE_MOVES_LOG,NYNH,$90,I4,$70,I7 -START_COMPANY_LOG,Ed,RDG,$100,$300,3,30,BANK -SELL_SHARES_LOG,Phil,4,10,40,NYC,$304 -PRICE_MOVES_LOG,NYC,$76,G4,$67,G8 +SELL_SHARE_LOG,Ed,10,NYC,82 +PRICE_MOVES_LOG,NYC,82,G3,76,G4 +SELL_SHARES_LOG,Ed,3,10,30,NYNH,270 +PRICE_MOVES_LOG,NYNH,90,I4,70,I7 +START_COMPANY_LOG,Ed,RDG,100,300,3,30,BANK +SELL_SHARES_LOG,Phil,4,10,40,NYC,304 +PRICE_MOVES_LOG,NYC,76,G4,67,G8 IS_NOW_PRES_OF,Si,NYC -START_COMPANY_LOG,Phil,C&O,$90,$180,2,20,BANK -BUY_SHARE_LOG,Chris,10,NYNH,Pool,$70 -START_COMPANY_LOG,Marcus,Erie,$90,$180,2,20,BANK +START_COMPANY_LOG,Phil,C&O,90,180,2,20,BANK +BUY_SHARE_LOG,Chris,10,NYNH,Pool,70 +START_COMPANY_LOG,Marcus,Erie,90,180,2,20,BANK SwapsPrivateForCertificate,Marcus,M&H,10,NYC PrivateCloses,M&H -BUY_SHARE_LOG,Si,10,N&W,IPO,$71 -BUY_SHARE_LOG,Ed,10,RDG,IPO,$100 -BUY_SHARE_LOG,Phil,10,C&O,IPO,$90 -BUY_SHARE_LOG,Chris,10,NYNH,Pool,$70 +BUY_SHARE_LOG,Si,10,N&W,IPO,71 +BUY_SHARE_LOG,Ed,10,RDG,IPO,100 +BUY_SHARE_LOG,Phil,10,C&O,IPO,90 +BUY_SHARE_LOG,Chris,10,NYNH,Pool,70 Autopasses,Marcus PASSES,Si -BUY_SHARE_LOG,Ed,10,RDG,IPO,$100 -FloatsWithCash,RDG,$1000 -BUY_SHARE_LOG,Phil,10,C&O,IPO,$90 +BUY_SHARE_LOG,Ed,10,RDG,IPO,100 +FloatsWithCash,RDG,1000 +BUY_SHARE_LOG,Phil,10,C&O,IPO,90 Autopasses,Chris Autopasses,Marcus PASSES,Si PASSES,Ed -BUY_SHARE_LOG,Phil,10,C&O,IPO,$90 +BUY_SHARE_LOG,Phil,10,C&O,IPO,90 Autopasses,Chris Autopasses,Marcus PASSES,Si PASSES,Ed -BUY_SHARE_LOG,Phil,10,C&O,IPO,$90 -FloatsWithCash,C&O,$900 +BUY_SHARE_LOG,Phil,10,C&O,IPO,90 +FloatsWithCash,C&O,900 Autopasses,Chris Autopasses,Marcus PASSES,Si @@ -393,197 +393,197 @@ PASSES,Ed PASSES,Phil END_SR,4 -Has,C&O,$900 -Has,N&W,$170 -Has,NYC,$105 -Has,NYNH,$250 -Has,RDG,$1000 -Has,Marcus,$38 -Has,Si,$56 -Has,Ed,$55 -Has,Phil,$54 -Has,Chris,$48 +Has,C&O,900 +Has,N&W,170 +Has,NYC,105 +Has,NYNH,250 +Has,RDG,1000 +Has,Marcus,38 +Has,Si,56 +Has,Ed,55 +Has,Phil,54 +Has,Chris,48 START_OR,4.1 -ReceivesFor,Marcus,$5,SVNRR -ReceivesFor,N&W,$10,C&StL -ReceivesFor,NYC,$15,D&H -ReceivesFor,Si,$25,C&A -ReceivesFor,Ed,$30,B&O +ReceivesFor,Marcus,5,SVNRR +ReceivesFor,N&W,10,C&StL +ReceivesFor,NYC,15,D&H +ReceivesFor,Si,25,C&A +ReceivesFor,Ed,30,B&O CompanyOperates,RDG,Ed LaysTileAt,RDG,57,H16,W CompanyDoesNotPayDividend,RDG -PRICE_MOVES_LOG,RDG,$100,G1,$90,F1 -BuysTrain,RDG,3,IPO,$180 +PRICE_MOVES_LOG,RDG,100,G1,90,F1 +BuysTrain,RDG,3,IPO,180 CompanyOperates,C&O,Phil LaysTileAt,C&O,57,K13,SW CompanyDoesNotPayDividend,C&O -PRICE_MOVES_LOG,C&O,$90,G2,$82,F2 -BuysTrain,C&O,3,IPO,$180 -BuysTrain,C&O,3,IPO,$180 +PRICE_MOVES_LOG,C&O,90,G2,82,F2 +BuysTrain,C&O,3,IPO,180 +BuysTrain,C&O,3,IPO,180 All 3-trains are sold out, 4-trains now available -BuysTrain,C&O,4,IPO,$300 +BuysTrain,C&O,4,IPO,300 FirstTrainBought,4 StartOfPhase,4 CompanyDiscardsTrain,NYC,2 CompanyOperates,N&W,Chris LaysTileAt,N&W,8,M11,NW -CompanyRevenue,N&W,$150 -CompanyWithholds,N&W,$150 -PRICE_MOVES_LOG,N&W,$82,I5,$76,H5 +CompanyRevenue,N&W,150 +CompanyWithholds,N&W,150 +PRICE_MOVES_LOG,N&W,82,I5,76,H5 TrainsObsoleteRusted,2,N&W -BuysTrain,N&W,4,IPO,$300 +BuysTrain,N&W,4,IPO,300 CompanyOperates,NYNH,Marcus LaysTileAt,NYNH,14,F20,SW -CompanyRevenue,NYNH,$180 -CompanyWithholds,NYNH,$180 -PRICE_MOVES_LOG,NYNH,$70,I7,$69,H7 +CompanyRevenue,NYNH,180 +CompanyWithholds,NYNH,180 +PRICE_MOVES_LOG,NYNH,70,I7,69,H7 TrainsObsoleteRusted,2,NYNH -BuysTrain,NYNH,4,IPO,$300 +BuysTrain,NYNH,4,IPO,300 CompanyOperates,NYC,Si LaysTileAt,NYC,1,G17,W -CompanyRevenue,NYC,$130 -CompanyPaysOutFull,NYC,$130 -Payout,Si,$52,4,10 -Payout,Marcus,$13,1,10 -Payout,Phil,$13,1,10 -Payout,NYC,$52,4,10 -PRICE_MOVES_LOG,NYC,$67,G8,$68,H8 +CompanyRevenue,NYC,130 +CompanyPaysOutFull,NYC,130 +Payout,Si,52,4,10 +Payout,Marcus,13,1,10 +Payout,Phil,13,1,10 +Payout,NYC,52,4,10 +PRICE_MOVES_LOG,NYC,67,G8,68,H8 TrainsObsoleteRusted,2,NYC TrainsObsoleteRusted,2,NYC TrainsObsoleteRusted,2,NYC -PresidentAddsCash,NYC,Si,$128 -BuysTrain,NYC,4,IPO,$300 +PresidentAddsCash,NYC,Si,128 +BuysTrain,NYC,4,IPO,300 EndOfOperatingRound,4.1 -ORWorthIncrease,Marcus,4.1,$13 -ORWorthIncrease,Si,4.1,-$69 -ORWorthIncrease,Ed,4.1,-$20 -ORWorthIncrease,Phil,4.1,-$40 -ORWorthIncrease,Chris,4.1,-$39 -Has,C&O,$240 -Has,N&W,$30 -Has,NYC,$0 -Has,NYNH,$130 -Has,RDG,$820 -Has,Marcus,$56 -Has,Si,$5 -Has,Ed,$85 -Has,Phil,$67 -Has,Chris,$48 +ORWorthIncrease,Marcus,4.1,13 +ORWorthIncrease,Si,4.1,-69 +ORWorthIncrease,Ed,4.1,-20 +ORWorthIncrease,Phil,4.1,-40 +ORWorthIncrease,Chris,4.1,-39 +Has,C&O,240 +Has,N&W,30 +Has,NYC,0 +Has,NYNH,130 +Has,RDG,820 +Has,Marcus,56 +Has,Si,5 +Has,Ed,85 +Has,Phil,67 +Has,Chris,48 START_OR,4.2 -ReceivesFor,Marcus,$5,SVNRR -ReceivesFor,N&W,$10,C&StL -ReceivesFor,NYC,$15,D&H -ReceivesFor,Si,$25,C&A -ReceivesFor,Ed,$30,B&O +ReceivesFor,Marcus,5,SVNRR +ReceivesFor,N&W,10,C&StL +ReceivesFor,NYC,15,D&H +ReceivesFor,Si,25,C&A +ReceivesFor,Ed,30,B&O CompanyOperates,RDG,Ed LaysTileAt,RDG,14,H16,SW -CompanyRevenue,RDG,$50 -CompanyPaysOutFull,RDG,$50 -Payout,Ed,$25,5,10 -Payout,Si,$5,1,10 -PRICE_MOVES_LOG,RDG,$90,F1,$100,G1 +CompanyRevenue,RDG,50 +CompanyPaysOutFull,RDG,50 +Payout,Ed,25,5,10 +Payout,Si,5,1,10 +PRICE_MOVES_LOG,RDG,90,F1,100,G1 CompanyOperates,C&O,Phil LaysTileAt,C&O,24,L12,W CorrectionModeActivate,Phil,CORRECT_CASH -CorrectCashSubstractMoney,C&O,$140 +CorrectCashSubstractMoney,C&O,140 CorrectionModeDeactivate,Phil,CORRECT_CASH -CompanyRevenue,C&O,$90 -CompanyPaysOutFull,C&O,$90 -Payout,Phil,$54,6,10 -PRICE_MOVES_LOG,C&O,$82,F2,$90,G2 +CompanyRevenue,C&O,90 +CompanyPaysOutFull,C&O,90 +Payout,Phil,54,6,10 +PRICE_MOVES_LOG,C&O,82,F2,90,G2 CompanyOperates,N&W,Chris LaysTileAt,N&W,14,J14,NW -LAYS_TOKEN_ON,N&W,J14,$40 -CompanyRevenue,N&W,$210 -CompanyPaysOutFull,N&W,$210 -Payout,Phil,$21,1,10 -Payout,Si,$42,2,10 -Payout,Chris,$126,6,10 -PRICE_MOVES_LOG,N&W,$76,H5,$82,I5 +LAYS_TOKEN_ON,N&W,J14,40 +CompanyRevenue,N&W,210 +CompanyPaysOutFull,N&W,210 +Payout,Phil,21,1,10 +Payout,Si,42,2,10 +Payout,Chris,126,6,10 +PRICE_MOVES_LOG,N&W,76,H5,82,I5 CompanyOperates,NYNH,Marcus -LaysTileAtFor,NYNH,57,F22,W,$80 -LAYS_TOKEN_ON,NYNH,F16,$40 -CompanyRevenue,NYNH,$270 -CompanyPaysOutFull,NYNH,$270 -Payout,Chris,$81,3,10 -Payout,Marcus,$162,6,10 -Payout,NYNH,$27,1,10 -PRICE_MOVES_LOG,NYNH,$69,H7,$70,I7 +LaysTileAtFor,NYNH,57,F22,W,80 +LAYS_TOKEN_ON,NYNH,F16,40 +CompanyRevenue,NYNH,270 +CompanyPaysOutFull,NYNH,270 +Payout,Chris,81,3,10 +Payout,Marcus,162,6,10 +Payout,NYNH,27,1,10 +PRICE_MOVES_LOG,NYNH,69,H7,70,I7 CompanyOperates,NYC,Si LaysTileAt,NYC,15,E19,NE -CompanyRevenue,NYC,$160 -CompanyPaysOutFull,NYC,$160 -Payout,Marcus,$16,1,10 -Payout,Phil,$16,1,10 -Payout,Si,$64,4,10 -Payout,NYC,$64,4,10 -PRICE_MOVES_LOG,NYC,$68,H8,$69,H7 +CompanyRevenue,NYC,160 +CompanyPaysOutFull,NYC,160 +Payout,Marcus,16,1,10 +Payout,Phil,16,1,10 +Payout,Si,64,4,10 +Payout,NYC,64,4,10 +PRICE_MOVES_LOG,NYC,68,H8,69,H7 EndOfOperatingRound,4.2 -ORWorthIncrease,Marcus,4.2,$190 -ORWorthIncrease,Si,4.2,$162 -ORWorthIncrease,Ed,4.2,$105 -ORWorthIncrease,Phil,4.2,$146 -ORWorthIncrease,Chris,4.2,$246 -Has,C&O,$100 -Has,N&W,$0 -Has,NYC,$79 -Has,NYNH,$37 -Has,RDG,$820 -Has,Marcus,$239 -Has,Si,$141 -Has,Ed,$140 -Has,Phil,$158 -Has,Chris,$255 +ORWorthIncrease,Marcus,4.2,190 +ORWorthIncrease,Si,4.2,162 +ORWorthIncrease,Ed,4.2,105 +ORWorthIncrease,Phil,4.2,146 +ORWorthIncrease,Chris,4.2,246 +Has,C&O,100 +Has,N&W,0 +Has,NYC,79 +Has,NYNH,37 +Has,RDG,820 +Has,Marcus,239 +Has,Si,141 +Has,Ed,140 +Has,Phil,158 +Has,Chris,255 StartStockRound,5 HasPriority,Chris -SELL_SHARES_LOG,Chris,3,10,30,NYNH,$210 -START_COMPANY_LOG,Chris,PRR,$76,$152,2,20,BANK -BUY_SHARE_LOG,Marcus,10,N&W,IPO,$71 -SELL_SHARES_LOG,Si,2,10,20,N&W,$164 -PRICE_MOVES_LOG,N&W,$82,I5,$70,I7 -SELL_SHARE_LOG,Si,10,RDG,$100 -PRICE_MOVES_LOG,RDG,$100,G1,$90,G2 -BUY_SHARE_LOG,Si,10,Erie,IPO,$90 -BUY_SHARE_LOG,Ed,10,RDG,Pool,$90 -BUY_SHARE_LOG,Phil,10,NYNH,Pool,$70 -BUY_SHARE_LOG,Chris,10,PRR,IPO,$76 -BUY_SHARE_LOG,Marcus,10,Erie,IPO,$90 -BUY_SHARE_LOG,Si,10,Erie,IPO,$90 +SELL_SHARES_LOG,Chris,3,10,30,NYNH,210 +START_COMPANY_LOG,Chris,PRR,76,152,2,20,BANK +BUY_SHARE_LOG,Marcus,10,N&W,IPO,71 +SELL_SHARES_LOG,Si,2,10,20,N&W,164 +PRICE_MOVES_LOG,N&W,82,I5,70,I7 +SELL_SHARE_LOG,Si,10,RDG,100 +PRICE_MOVES_LOG,RDG,100,G1,90,G2 +BUY_SHARE_LOG,Si,10,Erie,IPO,90 +BUY_SHARE_LOG,Ed,10,RDG,Pool,90 +BUY_SHARE_LOG,Phil,10,NYNH,Pool,70 +BUY_SHARE_LOG,Chris,10,PRR,IPO,76 +BUY_SHARE_LOG,Marcus,10,Erie,IPO,90 +BUY_SHARE_LOG,Si,10,Erie,IPO,90 Autopasses,Ed -BUY_SHARE_LOG,Phil,10,NYNH,Pool,$70 -BUY_SHARE_LOG,Chris,10,PRR,IPO,$76 -SELL_SHARE_LOG,Marcus,10,NYC,$69 -PRICE_MOVES_LOG,NYC,$69,H7,$68,H8 -BUY_SHARE_LOG,Marcus,10,Erie,IPO,$90 -FloatsWithCash,Erie,$900 -BUY_SHARE_LOG,Si,10,Erie,IPO,$90 +BUY_SHARE_LOG,Phil,10,NYNH,Pool,70 +BUY_SHARE_LOG,Chris,10,PRR,IPO,76 +SELL_SHARE_LOG,Marcus,10,NYC,69 +PRICE_MOVES_LOG,NYC,69,H7,68,H8 +BUY_SHARE_LOG,Marcus,10,Erie,IPO,90 +FloatsWithCash,Erie,900 +BUY_SHARE_LOG,Si,10,Erie,IPO,90 Autopasses,Ed PASSES,Phil -BUY_SHARE_LOG,Chris,10,PRR,IPO,$76 -SELL_SHARE_LOG,Marcus,10,N&W,$70 -BUY_SHARE_LOG,Marcus,10,Erie,IPO,$90 -BUY_SHARE_LOG,Si,10,Erie,IPO,$90 +BUY_SHARE_LOG,Chris,10,PRR,IPO,76 +SELL_SHARE_LOG,Marcus,10,N&W,70 +BUY_SHARE_LOG,Marcus,10,Erie,IPO,90 +BUY_SHARE_LOG,Si,10,Erie,IPO,90 Autopasses,Ed PASSES,Phil -BUY_SHARE_LOG,Chris,10,PRR,IPO,$76 -FloatsWithCash,PRR,$760 +BUY_SHARE_LOG,Chris,10,PRR,IPO,76 +FloatsWithCash,PRR,760 PASSES,Marcus PASSES,Si Autopasses,Ed -SELL_SHARE_LOG,Phil,10,NYNH,$70 -BUY_SHARE_LOG,Phil,10,PRR,IPO,$76 +SELL_SHARE_LOG,Phil,10,NYNH,70 +BUY_SHARE_LOG,Phil,10,PRR,IPO,76 PASSES,Chris PASSES,Marcus PASSES,Si @@ -591,69 +591,69 @@ Autopasses,Ed PASSES,Phil END_SR,5 -Has,C&O,$100 -Has,Erie,$900 -Has,N&W,$0 -Has,NYC,$79 -Has,NYNH,$37 -Has,PRR,$760 -Has,RDG,$820 -Has,Marcus,$37 -Has,Si,$45 -Has,Ed,$50 -Has,Phil,$12 -Has,Chris,$9 +Has,C&O,100 +Has,Erie,900 +Has,N&W,0 +Has,NYC,79 +Has,NYNH,37 +Has,PRR,760 +Has,RDG,820 +Has,Marcus,37 +Has,Si,45 +Has,Ed,50 +Has,Phil,12 +Has,Chris,9 START_OR,5.1 -ReceivesFor,Marcus,$5,SVNRR -ReceivesFor,N&W,$10,C&StL -ReceivesFor,NYC,$15,D&H -ReceivesFor,Si,$25,C&A -ReceivesFor,Ed,$30,B&O +ReceivesFor,Marcus,5,SVNRR +ReceivesFor,N&W,10,C&StL +ReceivesFor,NYC,15,D&H +ReceivesFor,Si,25,C&A +ReceivesFor,Ed,30,B&O CompanyOperates,Erie,Marcus LaysTileAt,Erie,59,E11,SW CompanyDoesNotPayDividend,Erie -PRICE_MOVES_LOG,Erie,$90,G2,$82,F2 -BuysTrain,Erie,4,IPO,$300 -BuysPrivateFromFor,Erie,SVNRR,Marcus,$40 +PRICE_MOVES_LOG,Erie,90,G2,82,F2 +BuysTrain,Erie,4,IPO,300 +BuysPrivateFromFor,Erie,SVNRR,Marcus,40 CompanyOperates,C&O,Phil LaysTileAt,C&O,15,K13,SW -LAYS_TOKEN_ON,C&O,J14,$40 -CompanyRevenue,C&O,$250 -CompanyPaysOutFull,C&O,$250 -Payout,Phil,$150,6,10 -PRICE_MOVES_LOG,C&O,$90,G2,$100,H2 +LAYS_TOKEN_ON,C&O,J14,40 +CompanyRevenue,C&O,250 +CompanyPaysOutFull,C&O,250 +Payout,Phil,150,6,10 +PRICE_MOVES_LOG,C&O,90,G2,100,H2 CompanyOperates,RDG,Ed LaysTileAt,RDG,57,H10,W -CompanyRevenue,RDG,$60 -CompanyPaysOutFull,RDG,$60 -Payout,Ed,$36,6,10 -PRICE_MOVES_LOG,RDG,$90,G2,$100,H2 +CompanyRevenue,RDG,60 +CompanyPaysOutFull,RDG,60 +Payout,Ed,36,6,10 +PRICE_MOVES_LOG,RDG,90,G2,100,H2 CompanyOperates,PRR,Chris LaysTileAt,PRR,15,H10,E CompanyDoesNotPayDividend,PRR -PRICE_MOVES_LOG,PRR,$76,G4,$71,F4 -BuysTrain,PRR,4,IPO,$300 +PRICE_MOVES_LOG,PRR,76,G4,71,F4 +BuysTrain,PRR,4,IPO,300 All 4-trains are sold out, 5-trains now available -BuysTrain,PRR,3,N&W,$400 +BuysTrain,PRR,3,N&W,400 CompanyOperates,NYNH,Marcus LaysTileAt,NYNH,27,E21,SW -CompanyRevenue,NYNH,$280 -CompanyPaysOutFull,NYNH,$280 -Payout,Phil,$28,1,10 -Payout,Marcus,$168,6,10 -Payout,NYNH,$84,3,10 -PRICE_MOVES_LOG,NYNH,$70,I7,$75,I6 +CompanyRevenue,NYNH,280 +CompanyPaysOutFull,NYNH,280 +Payout,Phil,28,1,10 +Payout,Marcus,168,6,10 +Payout,NYNH,84,3,10 +PRICE_MOVES_LOG,NYNH,70,I7,75,I6 CompanyOperates,N&W,Chris -CompanyRevenue,N&W,$130 -CompanyWithholds,N&W,$130 -PRICE_MOVES_LOG,N&W,$70,I7,$69,H7 -BuysTrain,N&W,5,IPO,$450 +CompanyRevenue,N&W,130 +CompanyWithholds,N&W,130 +PRICE_MOVES_LOG,N&W,70,I7,69,H7 +BuysTrain,N&W,5,IPO,450 FirstTrainBought,5 StartOfPhase,5 PrivateCloses,SVNRR @@ -665,189 +665,189 @@ CompanyDiscardsTrain,C&O,3 CompanyOperates,NYC,Si LaysTileAt,NYC,62,G19,NE -CompanyRevenue,NYC,$170 -CompanyPaysOutFull,NYC,$170 -Payout,Phil,$17,1,10 -Payout,Si,$68,4,10 -Payout,NYC,$85,5,10 -PRICE_MOVES_LOG,NYC,$68,H8,$69,H7 +CompanyRevenue,NYC,170 +CompanyPaysOutFull,NYC,170 +Payout,Phil,17,1,10 +Payout,Si,68,4,10 +Payout,NYC,85,5,10 +PRICE_MOVES_LOG,NYC,68,H8,69,H7 EndOfOperatingRound,5.1 -ORWorthIncrease,Marcus,5.1,$183 -ORWorthIncrease,Si,5.1,-$95 -ORWorthIncrease,Ed,5.1,-$94 -ORWorthIncrease,Phil,5.1,$255 -ORWorthIncrease,Chris,5.1,-$36 -Has,C&O,$60 -Has,Erie,$560 -Has,N&W,$90 -Has,NYC,$179 -Has,NYNH,$121 -Has,PRR,$60 -Has,RDG,$820 -Has,Marcus,$250 -Has,Si,$138 -Has,Ed,$116 -Has,Phil,$207 -Has,Chris,$9 +ORWorthIncrease,Marcus,5.1,183 +ORWorthIncrease,Si,5.1,-95 +ORWorthIncrease,Ed,5.1,-94 +ORWorthIncrease,Phil,5.1,255 +ORWorthIncrease,Chris,5.1,-36 +Has,C&O,60 +Has,Erie,560 +Has,N&W,90 +Has,NYC,179 +Has,NYNH,121 +Has,PRR,60 +Has,RDG,820 +Has,Marcus,250 +Has,Si,138 +Has,Ed,116 +Has,Phil,207 +Has,Chris,9 START_OR,5.2 CompanyOperates,C&O,Phil LaysTileAt,C&O,53,I15,SW -CompanyRevenue,C&O,$290 -CompanyPaysOutFull,C&O,$290 -Payout,Phil,$174,6,10 -PRICE_MOVES_LOG,C&O,$100,H2,$112,I2 +CompanyRevenue,C&O,290 +CompanyPaysOutFull,C&O,290 +Payout,Phil,174,6,10 +PRICE_MOVES_LOG,C&O,100,H2,112,I2 CompanyOperates,RDG,Ed LaysTileAt,RDG,BA,I15,NE -LAYS_TOKEN_ON,RDG,I15,$40 -CompanyRevenue,RDG,$120 -CompanyPaysOutFull,RDG,$120 -Payout,Ed,$72,6,10 -PRICE_MOVES_LOG,RDG,$100,H2,$112,I2 -BuysTrain,RDG,5,IPO,$450 +LAYS_TOKEN_ON,RDG,I15,40 +CompanyRevenue,RDG,120 +CompanyPaysOutFull,RDG,120 +Payout,Ed,72,6,10 +PRICE_MOVES_LOG,RDG,100,H2,112,I2 +BuysTrain,RDG,5,IPO,450 CompanyOperates,Erie,Marcus LaysTileAt,Erie,4,F10,SW -CompanyRevenue,Erie,$50 -CompanyPaysOutFull,Erie,$50 -Payout,Marcus,$25,5,10 -Payout,Si,$20,4,10 -PRICE_MOVES_LOG,Erie,$82,F2,$90,G2 +CompanyRevenue,Erie,50 +CompanyPaysOutFull,Erie,50 +Payout,Marcus,25,5,10 +Payout,Si,20,4,10 +PRICE_MOVES_LOG,Erie,82,F2,90,G2 CompanyOperates,NYNH,Marcus LaysTileAt,NYNH,59,H18,NE -CompanyRevenue,NYNH,$300 -CompanyWithholds,NYNH,$300 -PRICE_MOVES_LOG,NYNH,$75,I6,$71,H6 +CompanyRevenue,NYNH,300 +CompanyWithholds,NYNH,300 +PRICE_MOVES_LOG,NYNH,75,I6,71,H6 CompanyOperates,PRR,Chris LaysTileAt,PRR,G17,G17,W -LAYS_TOKEN_ON,PRR,G19,$40 -CompanyRevenue,PRR,$340 -CompanyPaysOutFull,PRR,$340 -Payout,Phil,$34,1,10 -Payout,Chris,$204,6,10 -PRICE_MOVES_LOG,PRR,$71,F4,$76,G4 +LAYS_TOKEN_ON,PRR,G19,40 +CompanyRevenue,PRR,340 +CompanyPaysOutFull,PRR,340 +Payout,Phil,34,1,10 +Payout,Chris,204,6,10 +PRICE_MOVES_LOG,PRR,71,F4,76,G4 CompanyOperates,N&W,Chris LaysTileAt,N&W,63,H16,SW -CompanyRevenue,N&W,$410 -CompanyPaysOutFull,N&W,$410 -Payout,Phil,$41,1,10 -Payout,Chris,$246,6,10 -Payout,N&W,$123,3,10 -PRICE_MOVES_LOG,N&W,$69,H7,$70,I7 +CompanyRevenue,N&W,410 +CompanyPaysOutFull,N&W,410 +Payout,Phil,41,1,10 +Payout,Chris,246,6,10 +Payout,N&W,123,3,10 +PRICE_MOVES_LOG,N&W,69,H7,70,I7 CompanyOperates,NYC,Si LaysTileAt,NYC,64,H18,SE -LAYS_TOKEN_ON,NYC,G19,$100 -CompanyRevenue,NYC,$200 -CompanyPaysOutFull,NYC,$200 -Payout,Phil,$20,1,10 -Payout,Si,$80,4,10 -Payout,NYC,$100,5,10 -PRICE_MOVES_LOG,NYC,$69,H7,$70,I7 +LAYS_TOKEN_ON,NYC,G19,100 +CompanyRevenue,NYC,200 +CompanyPaysOutFull,NYC,200 +Payout,Phil,20,1,10 +Payout,Si,80,4,10 +Payout,NYC,100,5,10 +PRICE_MOVES_LOG,NYC,69,H7,70,I7 EndOfOperatingRound,5.2 -ORWorthIncrease,Marcus,5.2,$41 -ORWorthIncrease,Si,5.2,$136 -ORWorthIncrease,Ed,5.2,$144 -ORWorthIncrease,Phil,5.2,$344 -ORWorthIncrease,Chris,5.2,$486 -Has,C&O,$60 -Has,Erie,$560 -Has,N&W,$213 -Has,NYC,$179 -Has,NYNH,$421 -Has,PRR,$20 -Has,RDG,$330 -Has,Marcus,$275 -Has,Si,$238 -Has,Ed,$188 -Has,Phil,$476 -Has,Chris,$459 +ORWorthIncrease,Marcus,5.2,41 +ORWorthIncrease,Si,5.2,136 +ORWorthIncrease,Ed,5.2,144 +ORWorthIncrease,Phil,5.2,344 +ORWorthIncrease,Chris,5.2,486 +Has,C&O,60 +Has,Erie,560 +Has,N&W,213 +Has,NYC,179 +Has,NYNH,421 +Has,PRR,20 +Has,RDG,330 +Has,Marcus,275 +Has,Si,238 +Has,Ed,188 +Has,Phil,476 +Has,Chris,459 StartStockRound,6 HasPriority,Chris -START_COMPANY_LOG,Chris,B&M,$76,$152,2,20,BANK -BUY_SHARE_LOG,Marcus,10,N&W,Pool,$70 -SELL_SHARES_LOG,Si,4,10,40,Erie,$360 -PRICE_MOVES_LOG,Erie,$90,G2,$67,G6 -START_COMPANY_LOG,Si,CPR,$82,$164,2,20,BANK -BUY_SHARE_LOG,Ed,10,C&O,IPO,$90 -BUY_SHARE_LOG,Phil,10,B&O,IPO,$100 -BUY_SHARE_LOG,Chris,10,B&M,IPO,$76 -BUY_SHARE_LOG,Marcus,10,N&W,Pool,$70 -BUY_SHARE_LOG,Si,10,CPR,IPO,$82 -BUY_SHARE_LOG,Ed,10,C&O,IPO,$90 -SELL_SHARES_LOG,Phil,5,10,50,C&O,$560 -PRICE_MOVES_LOG,C&O,$112,I2,$70,I7 +START_COMPANY_LOG,Chris,B&M,76,152,2,20,BANK +BUY_SHARE_LOG,Marcus,10,N&W,Pool,70 +SELL_SHARES_LOG,Si,4,10,40,Erie,360 +PRICE_MOVES_LOG,Erie,90,G2,67,G6 +START_COMPANY_LOG,Si,CPR,82,164,2,20,BANK +BUY_SHARE_LOG,Ed,10,C&O,IPO,90 +BUY_SHARE_LOG,Phil,10,B&O,IPO,100 +BUY_SHARE_LOG,Chris,10,B&M,IPO,76 +BUY_SHARE_LOG,Marcus,10,N&W,Pool,70 +BUY_SHARE_LOG,Si,10,CPR,IPO,82 +BUY_SHARE_LOG,Ed,10,C&O,IPO,90 +SELL_SHARES_LOG,Phil,5,10,50,C&O,560 +PRICE_MOVES_LOG,C&O,112,I2,70,I7 IS_NOW_PRES_OF,Ed,C&O -BUY_SHARE_LOG,Phil,10,B&O,IPO,$100 -BUY_SHARE_LOG,Chris,10,B&M,IPO,$76 -BUY_SHARE_LOG,Marcus,10,N&W,Pool,$70 -BUY_SHARE_LOG,Si,10,CPR,IPO,$82 +BUY_SHARE_LOG,Phil,10,B&O,IPO,100 +BUY_SHARE_LOG,Chris,10,B&M,IPO,76 +BUY_SHARE_LOG,Marcus,10,N&W,Pool,70 +BUY_SHARE_LOG,Si,10,CPR,IPO,82 PASSES,Ed -BUY_SHARE_LOG,Phil,10,B&O,IPO,$100 +BUY_SHARE_LOG,Phil,10,B&O,IPO,100 IS_NOW_PRES_OF,Phil,B&O -BUY_SHARE_LOG,Chris,10,B&M,IPO,$76 +BUY_SHARE_LOG,Chris,10,B&M,IPO,76 PASSES,Marcus -BUY_SHARE_LOG,Si,10,CPR,IPO,$82 +BUY_SHARE_LOG,Si,10,CPR,IPO,82 PASSES,Ed -BUY_SHARE_LOG,Phil,10,B&O,IPO,$100 -FloatsWithCash,B&O,$1000 -BUY_SHARE_LOG,Chris,10,B&M,IPO,$76 -FloatsWithCash,B&M,$760 +BUY_SHARE_LOG,Phil,10,B&O,IPO,100 +FloatsWithCash,B&O,1000 +BUY_SHARE_LOG,Chris,10,B&M,IPO,76 +FloatsWithCash,B&M,760 PASSES,Marcus -BUY_SHARE_LOG,Si,10,CPR,IPO,$82 -FloatsWithCash,CPR,$820 +BUY_SHARE_LOG,Si,10,CPR,IPO,82 +FloatsWithCash,CPR,820 PASSES,Ed -BUY_SHARE_LOG,Phil,10,B&O,IPO,$100 +BUY_SHARE_LOG,Phil,10,B&O,IPO,100 Autopasses,Chris Autopasses,Marcus -BUY_SHARE_LOG,Si,10,B&M,IPO,$76 +BUY_SHARE_LOG,Si,10,B&M,IPO,76 Autopasses,Ed -BUY_SHARE_LOG,Phil,10,B&O,IPO,$100 +BUY_SHARE_LOG,Phil,10,B&O,IPO,100 Autopasses,Chris Autopasses,Marcus -SELL_SHARE_LOG,Si,10,B&M,$76 -PRICE_MOVES_LOG,B&M,$76,G4,$71,G5 -BUY_SHARE_LOG,Si,10,B&O,IPO,$100 +SELL_SHARE_LOG,Si,10,B&M,76 +PRICE_MOVES_LOG,B&M,76,G4,71,G5 +BUY_SHARE_LOG,Si,10,B&O,IPO,100 Autopasses,Ed -BUY_SHARE_LOG,Phil,10,RDG,IPO,$100 +BUY_SHARE_LOG,Phil,10,RDG,IPO,100 Autopasses,Chris Autopasses,Marcus -SELL_SHARE_LOG,Si,10,B&O,$100 -PRICE_MOVES_LOG,B&O,$100,G1,$90,G2 -BUY_SHARE_LOG,Si,10,RDG,IPO,$100 +SELL_SHARE_LOG,Si,10,B&O,100 +PRICE_MOVES_LOG,B&O,100,G1,90,G2 +BUY_SHARE_LOG,Si,10,RDG,IPO,100 Autopasses,Ed -BUY_SHARE_LOG,Phil,10,B&M,Pool,$71 +BUY_SHARE_LOG,Phil,10,B&M,Pool,71 Autopasses,Chris Autopasses,Marcus -SELL_SHARE_LOG,Si,10,RDG,$112 -PRICE_MOVES_LOG,RDG,$112,I2,$100,I3 -BUY_SHARE_LOG,Si,10,C&O,Pool,$70 +SELL_SHARE_LOG,Si,10,RDG,112 +PRICE_MOVES_LOG,RDG,112,I2,100,I3 +BUY_SHARE_LOG,Si,10,C&O,Pool,70 Autopasses,Ed -BUY_SHARE_LOG,Phil,10,Erie,Pool,$67 +BUY_SHARE_LOG,Phil,10,Erie,Pool,67 Autopasses,Chris Autopasses,Marcus -SELL_SHARE_LOG,Si,10,C&O,$70 -BUY_SHARE_LOG,Si,10,NYNH,Pool,$71 +SELL_SHARE_LOG,Si,10,C&O,70 +BUY_SHARE_LOG,Si,10,NYNH,Pool,71 Autopasses,Ed -BUY_SHARE_LOG,Phil,10,Erie,Pool,$67 +BUY_SHARE_LOG,Phil,10,Erie,Pool,67 Autopasses,Chris Autopasses,Marcus -SELL_SHARE_LOG,Si,10,NYNH,$71 -PRICE_MOVES_LOG,NYNH,$71,H6,$69,H7 -BUY_SHARE_LOG,Si,10,PRR,IPO,$76 +SELL_SHARE_LOG,Si,10,NYNH,71 +PRICE_MOVES_LOG,NYNH,71,H6,69,H7 +BUY_SHARE_LOG,Si,10,PRR,IPO,76 Autopasses,Ed -BUY_SHARE_LOG,Phil,10,B&M,IPO,$76 +BUY_SHARE_LOG,Phil,10,B&M,IPO,76 Autopasses,Chris Autopasses,Marcus -SELL_SHARE_LOG,Si,10,PRR,$76 -PRICE_MOVES_LOG,PRR,$76,G4,$71,G5 -BUY_SHARE_LOG,Si,10,NYC,Pool,$70 +SELL_SHARE_LOG,Si,10,PRR,76 +PRICE_MOVES_LOG,PRR,76,G4,71,G5 +BUY_SHARE_LOG,Si,10,NYC,Pool,70 Autopasses,Ed PASSES,Phil Autopasses,Chris @@ -855,381 +855,381 @@ Autopasses,Marcus PASSES,Si END_SR,6 -PRICE_MOVES_LOG,N&W,$70,I7,$75,I6 -SoldOut,N&W,$70,I7,$75,I6 -Has,B&M,$760 -Has,B&O,$1000 -Has,C&O,$60 -Has,CPR,$820 -Has,Erie,$560 -Has,N&W,$213 -Has,NYC,$179 -Has,NYNH,$421 -Has,PRR,$20 -Has,RDG,$330 -Has,Marcus,$65 -Has,Si,$48 -Has,Ed,$8 -Has,Phil,$55 -Has,Chris,$3 +PRICE_MOVES_LOG,N&W,70,I7,75,I6 +SoldOut,N&W,70,I7,75,I6 +Has,B&M,760 +Has,B&O,1000 +Has,C&O,60 +Has,CPR,820 +Has,Erie,560 +Has,N&W,213 +Has,NYC,179 +Has,NYNH,421 +Has,PRR,20 +Has,RDG,330 +Has,Marcus,65 +Has,Si,48 +Has,Ed,8 +Has,Phil,55 +Has,Chris,3 START_OR,6.1 CompanyOperates,RDG,Ed LaysTileAt,RDG,63,H10,SW -CompanyRevenue,RDG,$380 -CompanyPaysOutFull,RDG,$380 -Payout,Phil,$38,1,10 -Payout,Ed,$228,6,10 -Payout,RDG,$38,1,10 -PRICE_MOVES_LOG,RDG,$100,I3,$111,J3 +CompanyRevenue,RDG,380 +CompanyPaysOutFull,RDG,380 +Payout,Phil,38,1,10 +Payout,Ed,228,6,10 +Payout,RDG,38,1,10 +PRICE_MOVES_LOG,RDG,100,I3,111,J3 CompanyOperates,B&O,Phil LaysTileAt,B&O,40,F18,W -LAYS_TOKEN_ON,B&O,G19,$40 +LAYS_TOKEN_ON,B&O,G19,40 CompanyDoesNotPayDividend,B&O -PRICE_MOVES_LOG,B&O,$90,G2,$82,F2 -BuysTrain,B&O,5,IPO,$450 +PRICE_MOVES_LOG,B&O,90,G2,82,F2 +BuysTrain,B&O,5,IPO,450 All 5-trains are sold out, 6-trains now available CompanyOperates,CPR,Si CompanyDoesNotPayDividend,CPR -PRICE_MOVES_LOG,CPR,$82,G3,$76,F3 -BuysTrain,CPR,6,IPO,$630 +PRICE_MOVES_LOG,CPR,82,G3,76,F3 +BuysTrain,CPR,6,IPO,630 FirstTrainBought,6 StartOfPhase,6 CompanyOperates,N&W,Chris LaysTileAt,N&W,7,G9,SE -LAYS_TOKEN_ON,N&W,I15,$100 -CompanyRevenue,N&W,$450 -CompanyWithholds,N&W,$450 -PRICE_MOVES_LOG,N&W,$75,I6,$71,H6 +LAYS_TOKEN_ON,N&W,I15,100 +CompanyRevenue,N&W,450 +CompanyWithholds,N&W,450 +PRICE_MOVES_LOG,N&W,75,I6,71,H6 CompanyOperates,B&M,Chris LaysTileAt,B&M,15,F22,W -LAYS_TOKEN_ON,B&M,E19,$40 +LAYS_TOKEN_ON,B&M,E19,40 CompanyDoesNotPayDividend,B&M -PRICE_MOVES_LOG,B&M,$71,G5,$67,F5 -BuysTrain,B&M,6,IPO,$630 -BuysTrain,B&M,5,N&W,$90 +PRICE_MOVES_LOG,B&M,71,G5,67,F5 +BuysTrain,B&M,6,IPO,630 +BuysTrain,B&M,5,N&W,90 CompanyOperates,PRR,Chris LaysTileAt,PRR,18,G9,E -CompanyRevenue,PRR,$360 -CompanyPaysOutFull,PRR,$360 -Payout,Phil,$36,1,10 -Payout,Chris,$216,6,10 -Payout,PRR,$36,1,10 -PRICE_MOVES_LOG,PRR,$71,G5,$76,H5 +CompanyRevenue,PRR,360 +CompanyPaysOutFull,PRR,360 +Payout,Phil,36,1,10 +Payout,Chris,216,6,10 +Payout,PRR,36,1,10 +PRICE_MOVES_LOG,PRR,71,G5,76,H5 TrainsObsoleteRusted,3,PRR -BuysTrain,PRR,5,B&M,$6 +BuysTrain,PRR,5,B&M,6 CompanyOperates,NYC,Si LaysTileAt,NYC,53,E23,W -CompanyRevenue,NYC,$200 -CompanyWithholds,NYC,$200 -PRICE_MOVES_LOG,NYC,$70,I7,$69,H7 -BuysTrain,NYC,6,CPR,$1 +CompanyRevenue,NYC,200 +CompanyWithholds,NYC,200 +PRICE_MOVES_LOG,NYC,70,I7,69,H7 +BuysTrain,NYC,6,CPR,1 CompanyOperates,C&O,Ed LaysTileAt,C&O,8,I13,NE -CompanyRevenue,C&O,$320 -CompanyWithholds,C&O,$320 -PRICE_MOVES_LOG,C&O,$70,I7,$69,H7 +CompanyRevenue,C&O,320 +CompanyWithholds,C&O,320 +PRICE_MOVES_LOG,C&O,70,I7,69,H7 TrainsObsoleteRusted,3,C&O CompanyOperates,NYNH,Marcus LaysTileAt,NYNH,63,F16,SW -CompanyRevenue,NYNH,$370 -CompanyPaysOutFull,NYNH,$370 -Payout,Phil,$37,1,10 -Payout,Marcus,$222,6,10 -Payout,NYNH,$111,3,10 -PRICE_MOVES_LOG,NYNH,$69,H7,$70,I7 +CompanyRevenue,NYNH,370 +CompanyPaysOutFull,NYNH,370 +Payout,Phil,37,1,10 +Payout,Marcus,222,6,10 +Payout,NYNH,111,3,10 +PRICE_MOVES_LOG,NYNH,69,H7,70,I7 TrainsObsoleteRusted,3,NYNH -BuysTrain,NYNH,4,Erie,$230 +BuysTrain,NYNH,4,Erie,230 CompanyOperates,Erie,Marcus LaysTileAt,Erie,65,E11,SE CompanyDoesNotPayDividend,Erie -PRICE_MOVES_LOG,Erie,$67,G6,$65,F6 -BuysTrain,Erie,7,IPO,$710 +PRICE_MOVES_LOG,Erie,67,G6,65,F6 +BuysTrain,Erie,7,IPO,710 FirstTrainBought,7 EndOfOperatingRound,6.1 -ORWorthIncrease,Marcus,6.1,$206 -ORWorthIncrease,Si,6.1,-$41 -ORWorthIncrease,Ed,6.1,$276 -ORWorthIncrease,Phil,6.1,$62 -ORWorthIncrease,Chris,6.1,$198 -Has,B&M,$6 -Has,B&O,$510 -Has,C&O,$380 -Has,CPR,$191 -Has,Erie,$80 -Has,N&W,$653 -Has,NYC,$378 -Has,NYNH,$302 -Has,PRR,$50 -Has,RDG,$368 -Has,Marcus,$287 -Has,Si,$48 -Has,Ed,$236 -Has,Phil,$166 -Has,Chris,$219 +ORWorthIncrease,Marcus,6.1,206 +ORWorthIncrease,Si,6.1,-41 +ORWorthIncrease,Ed,6.1,276 +ORWorthIncrease,Phil,6.1,62 +ORWorthIncrease,Chris,6.1,198 +Has,B&M,6 +Has,B&O,510 +Has,C&O,380 +Has,CPR,191 +Has,Erie,80 +Has,N&W,653 +Has,NYC,378 +Has,NYNH,302 +Has,PRR,50 +Has,RDG,368 +Has,Marcus,287 +Has,Si,48 +Has,Ed,236 +Has,Phil,166 +Has,Chris,219 START_OR,6.2 CompanyOperates,RDG,Ed LaysTileAt,RDG,9,I9,SW -CompanyRevenue,RDG,$380 -CompanyPaysOutFull,RDG,$380 -Payout,Phil,$38,1,10 -Payout,Ed,$228,6,10 -Payout,RDG,$38,1,10 -PRICE_MOVES_LOG,RDG,$111,J3,$125,K3 +CompanyRevenue,RDG,380 +CompanyPaysOutFull,RDG,380 +Payout,Phil,38,1,10 +Payout,Ed,228,6,10 +Payout,RDG,38,1,10 +PRICE_MOVES_LOG,RDG,111,J3,125,K3 TrainsObsoleteRusted,3,RDG CompanyOperates,B&O,Phil LaysTileAt,B&O,61,E23,NE -CompanyRevenue,B&O,$250 -CompanyWithholds,B&O,$250 -PRICE_MOVES_LOG,B&O,$82,F2,$76,E2 -ExchangesTrain,B&O,5,D,IPO,$750 +CompanyRevenue,B&O,250 +CompanyWithholds,B&O,250 +PRICE_MOVES_LOG,B&O,82,F2,76,E2 +ExchangesTrain,B&O,5,D,IPO,750 FirstTrainBought,D StartOfPhase,D CompanyOperates,PRR,Chris LaysTileAt,PRR,9,H8,W -CompanyRevenue,PRR,$450 -CompanyWithholds,PRR,$450 -PRICE_MOVES_LOG,PRR,$76,H5,$71,G5 +CompanyRevenue,PRR,450 +CompanyWithholds,PRR,450 +PRICE_MOVES_LOG,PRR,76,H5,71,G5 TrainsObsoleteRusted,4,PRR -BuysTrain,PRR,5,Pool,$450 +BuysTrain,PRR,5,Pool,450 CompanyOperates,CPR,Si CompanyDoesNotPayDividend,CPR -PRICE_MOVES_LOG,CPR,$76,F3,$70,E3 +PRICE_MOVES_LOG,CPR,76,F3,70,E3 CompanyOperates,N&W,Chris LaysTileAt,N&W,8,H6,NW -CompanyRevenue,N&W,$200 -CompanyPaysOutFull,N&W,$200 -Payout,Chris,$120,6,10 -Payout,Phil,$20,1,10 -Payout,Marcus,$60,3,10 -PRICE_MOVES_LOG,N&W,$71,H6,$75,I6 +CompanyRevenue,N&W,200 +CompanyPaysOutFull,N&W,200 +Payout,Chris,120,6,10 +Payout,Phil,20,1,10 +Payout,Marcus,60,3,10 +PRICE_MOVES_LOG,N&W,71,H6,75,I6 TrainsObsoleteRusted,4,N&W -BuysTrain,N&W,6,IPO,$630 +BuysTrain,N&W,6,IPO,630 CompanyOperates,NYNH,Marcus LaysTileAt,NYNH,9,F14,W -CompanyRevenue,NYNH,$400 -CompanyWithholds,NYNH,$400 -PRICE_MOVES_LOG,NYNH,$70,I7,$69,H7 +CompanyRevenue,NYNH,400 +CompanyWithholds,NYNH,400 +PRICE_MOVES_LOG,NYNH,70,I7,69,H7 TrainsObsoleteRusted,4,NYNH TrainsObsoleteRusted,4,NYNH -BuysTrain,NYNH,6,IPO,$630 +BuysTrain,NYNH,6,IPO,630 CompanyOperates,NYC,Si LaysTileAt,NYC,9,C23,NW -CompanyRevenue,NYC,$490 -CompanyWithholds,NYC,$490 -PRICE_MOVES_LOG,NYC,$69,H7,$67,G7 +CompanyRevenue,NYC,490 +CompanyWithholds,NYC,490 +PRICE_MOVES_LOG,NYC,69,H7,67,G7 TrainsObsoleteRusted,4,NYC CompanyOperates,C&O,Ed LaysTileAt,C&O,63,K13,SW -CompanyRevenue,C&O,$190 -CompanyWithholds,C&O,$190 -PRICE_MOVES_LOG,C&O,$69,H7,$67,G7 +CompanyRevenue,C&O,190 +CompanyWithholds,C&O,190 +PRICE_MOVES_LOG,C&O,69,H7,67,G7 TrainsObsoleteRusted,4,C&O -BuysTrain,C&O,5,RDG,$494 +BuysTrain,C&O,5,RDG,494 CompanyOperates,B&M,Chris LaysTileAt,B&M,44,E21,SW -CompanyRevenue,B&M,$270 -CompanyPaysOutFull,B&M,$270 -Payout,Chris,$162,6,10 -Payout,Phil,$54,2,10 -PRICE_MOVES_LOG,B&M,$67,F5,$71,G5 +CompanyRevenue,B&M,270 +CompanyPaysOutFull,B&M,270 +Payout,Chris,162,6,10 +Payout,Phil,54,2,10 +PRICE_MOVES_LOG,B&M,67,F5,71,G5 CompanyOperates,Erie,Marcus -LaysTileAtFor,Erie,59,D10,W,$80 -CompanyRevenue,Erie,$100 -CompanyPaysOutFull,Erie,$100 -Payout,Phil,$20,2,10 -Payout,Marcus,$50,5,10 -Payout,Erie,$20,2,10 -PRICE_MOVES_LOG,Erie,$65,F6,$67,G6 +LaysTileAtFor,Erie,59,D10,W,80 +CompanyRevenue,Erie,100 +CompanyPaysOutFull,Erie,100 +Payout,Phil,20,2,10 +Payout,Marcus,50,5,10 +Payout,Erie,20,2,10 +PRICE_MOVES_LOG,Erie,65,F6,67,G6 EndOfOperatingRound,6.2 -ORWorthIncrease,Marcus,6.2,$126 -ORWorthIncrease,Si,6.2,-$46 -ORWorthIncrease,Ed,6.2,$296 -ORWorthIncrease,Phil,6.2,$116 -ORWorthIncrease,Chris,6.2,$300 -Has,B&M,$6 -Has,B&O,$10 -Has,C&O,$76 -Has,CPR,$191 -Has,Erie,$20 -Has,N&W,$23 -Has,NYC,$868 -Has,NYNH,$72 -Has,PRR,$50 -Has,RDG,$900 -Has,Marcus,$397 -Has,Si,$48 -Has,Ed,$464 -Has,Phil,$298 -Has,Chris,$501 +ORWorthIncrease,Marcus,6.2,126 +ORWorthIncrease,Si,6.2,-46 +ORWorthIncrease,Ed,6.2,296 +ORWorthIncrease,Phil,6.2,116 +ORWorthIncrease,Chris,6.2,300 +Has,B&M,6 +Has,B&O,10 +Has,C&O,76 +Has,CPR,191 +Has,Erie,20 +Has,N&W,23 +Has,NYC,868 +Has,NYNH,72 +Has,PRR,50 +Has,RDG,900 +Has,Marcus,397 +Has,Si,48 +Has,Ed,464 +Has,Phil,298 +Has,Chris,501 START_OR,6.3 CompanyOperates,RDG,Ed LaysTileAt,RDG,9,G11,SW CompanyDoesNotPayDividend,RDG -PRICE_MOVES_LOG,RDG,$125,K3,$111,J3 -BuysTrain,RDG,D,IPO,$900 +PRICE_MOVES_LOG,RDG,125,K3,111,J3 +BuysTrain,RDG,D,IPO,900 CompanyOperates,B&O,Phil LaysTileAt,B&O,8,G5,NE -CompanyRevenue,B&O,$480 -CompanyPaysOutFull,B&O,$480 -Payout,Phil,$288,6,10 -Payout,Ed,$96,2,10 -Payout,B&O,$48,1,10 -PRICE_MOVES_LOG,B&O,$76,E2,$82,F2 +CompanyRevenue,B&O,480 +CompanyPaysOutFull,B&O,480 +Payout,Phil,288,6,10 +Payout,Ed,96,2,10 +Payout,B&O,48,1,10 +PRICE_MOVES_LOG,B&O,76,E2,82,F2 CompanyOperates,N&W,Chris LaysTileAt,N&W,25,G5,SE -CompanyRevenue,N&W,$290 -CompanyPaysOutFull,N&W,$290 -Payout,Phil,$29,1,10 -Payout,Chris,$174,6,10 -Payout,Marcus,$87,3,10 -PRICE_MOVES_LOG,N&W,$75,I6,$80,J6 +CompanyRevenue,N&W,290 +CompanyPaysOutFull,N&W,290 +Payout,Phil,29,1,10 +Payout,Chris,174,6,10 +Payout,Marcus,87,3,10 +PRICE_MOVES_LOG,N&W,75,I6,80,J6 CompanyOperates,PRR,Chris LaysTileAt,PRR,8,G3,NW -CompanyRevenue,PRR,$490 -CompanyPaysOutFull,PRR,$490 -Payout,Chris,$294,6,10 -Payout,Phil,$49,1,10 -Payout,PRR,$49,1,10 -PRICE_MOVES_LOG,PRR,$71,G5,$76,H5 +CompanyRevenue,PRR,490 +CompanyPaysOutFull,PRR,490 +Payout,Chris,294,6,10 +Payout,Phil,49,1,10 +Payout,PRR,49,1,10 +PRICE_MOVES_LOG,PRR,71,G5,76,H5 CompanyOperates,B&M,Chris LaysTileAt,B&M,7,B22,E -CompanyRevenue,B&M,$270 -CompanyPaysOutFull,B&M,$270 -Payout,Chris,$162,6,10 -Payout,Phil,$54,2,10 -PRICE_MOVES_LOG,B&M,$71,G5,$76,H5 +CompanyRevenue,B&M,270 +CompanyPaysOutFull,B&M,270 +Payout,Chris,162,6,10 +Payout,Phil,54,2,10 +PRICE_MOVES_LOG,B&M,71,G5,76,H5 CompanyOperates,CPR,Si LaysTileAt,CPR,58,B20,NW CompanyDoesNotPayDividend,CPR -PRICE_MOVES_LOG,CPR,$70,E3,$65,D3 -BuysTrain,CPR,6,NYC,$70 +PRICE_MOVES_LOG,CPR,70,E3,65,D3 +BuysTrain,CPR,6,NYC,70 CompanyOperates,NYNH,Marcus LaysTileAt,NYNH,8,F12,E -CompanyRevenue,NYNH,$310 -CompanyPaysOutFull,NYNH,$310 -Payout,Phil,$31,1,10 -Payout,Marcus,$186,6,10 -Payout,NYNH,$93,3,10 -PRICE_MOVES_LOG,NYNH,$69,H7,$70,I7 +CompanyRevenue,NYNH,310 +CompanyPaysOutFull,NYNH,310 +Payout,Phil,31,1,10 +Payout,Marcus,186,6,10 +Payout,NYNH,93,3,10 +PRICE_MOVES_LOG,NYNH,69,H7,70,I7 CompanyOperates,Erie,Marcus LaysTileAt,Erie,66,D10,E -CompanyRevenue,Erie,$110 -CompanyPaysOutFull,Erie,$110 -Payout,Phil,$22,2,10 -Payout,Marcus,$55,5,10 -Payout,Erie,$22,2,10 -PRICE_MOVES_LOG,Erie,$67,G6,$71,H6 +CompanyRevenue,Erie,110 +CompanyPaysOutFull,Erie,110 +Payout,Phil,22,2,10 +Payout,Marcus,55,5,10 +Payout,Erie,22,2,10 +PRICE_MOVES_LOG,Erie,67,G6,71,H6 CompanyOperates,NYC,Si LaysTileAt,NYC,27,B22,E CompanyDoesNotPayDividend,NYC -PRICE_MOVES_LOG,NYC,$67,G7,$63,F7 -BuysTrain,NYC,D,IPO,$900 +PRICE_MOVES_LOG,NYC,67,G7,63,F7 +BuysTrain,NYC,D,IPO,900 CompanyOperates,C&O,Ed LaysTileAt,C&O,16,I13,NW -CompanyRevenue,C&O,$230 -CompanyPaysOutFull,C&O,$230 -Payout,Phil,$23,1,10 -Payout,Ed,$46,2,10 -Payout,C&O,$115,5,10 -PRICE_MOVES_LOG,C&O,$67,G7,$69,H7 +CompanyRevenue,C&O,230 +CompanyPaysOutFull,C&O,230 +Payout,Phil,23,1,10 +Payout,Ed,46,2,10 +Payout,C&O,115,5,10 +PRICE_MOVES_LOG,C&O,67,G7,69,H7 EndOfOperatingRound,6.3 -ORWorthIncrease,Marcus,6.3,$369 -ORWorthIncrease,Si,6.3,-$50 -ORWorthIncrease,Ed,6.3,$74 -ORWorthIncrease,Phil,6.3,$545 -ORWorthIncrease,Chris,6.3,$720 -Has,B&M,$6 -Has,B&O,$58 -Has,C&O,$191 -Has,CPR,$121 -Has,Erie,$42 -Has,N&W,$23 -Has,NYC,$38 -Has,NYNH,$165 -Has,PRR,$99 -Has,RDG,$0 -Has,Marcus,$725 -Has,Si,$48 -Has,Ed,$606 -Has,Phil,$794 -Has,Chris,$1131 +ORWorthIncrease,Marcus,6.3,369 +ORWorthIncrease,Si,6.3,-50 +ORWorthIncrease,Ed,6.3,74 +ORWorthIncrease,Phil,6.3,545 +ORWorthIncrease,Chris,6.3,720 +Has,B&M,6 +Has,B&O,58 +Has,C&O,191 +Has,CPR,121 +Has,Erie,42 +Has,N&W,23 +Has,NYC,38 +Has,NYNH,165 +Has,PRR,99 +Has,RDG,0 +Has,Marcus,725 +Has,Si,48 +Has,Ed,606 +Has,Phil,794 +Has,Chris,1131 StartStockRound,7 HasPriority,Ed -BUY_SHARE_LOG,Ed,10,C&O,Pool,$69 -SELL_SHARES_LOG,Phil,2,10,20,Erie,$142 -PRICE_MOVES_LOG,Erie,$71,H6,$68,H8 -BUY_SHARE_LOG,Phil,10,NYC,Pool,$63 -SELL_SHARE_LOG,Chris,10,N&W,$80 -BUY_SHARE_LOG,Chris,10,B&O,Pool,$82 -BUY_SHARE_LOG,Marcus,10,N&W,Pool,$80 -SELL_SHARE_LOG,Si,10,CPR,$65 -PRICE_MOVES_LOG,CPR,$65,D3,$60,D4 -BUY_SHARE_LOG,Si,10,NYC,Pool,$63 -BUY_SHARE_LOG,Ed,10,C&O,Pool,$69 -BUY_SHARE_LOG,Phil,10,CPR,Pool,$60 -SELL_SHARE_LOG,Chris,10,B&O,$82 -PRICE_MOVES_LOG,B&O,$82,F2,$76,F3 -BUY_SHARE_LOG,Chris,10,NYC,Pool,$63 -BUY_SHARE_LOG,Marcus,10,NYC,Pool,$63 +BUY_SHARE_LOG,Ed,10,C&O,Pool,69 +SELL_SHARES_LOG,Phil,2,10,20,Erie,142 +PRICE_MOVES_LOG,Erie,71,H6,68,H8 +BUY_SHARE_LOG,Phil,10,NYC,Pool,63 +SELL_SHARE_LOG,Chris,10,N&W,80 +BUY_SHARE_LOG,Chris,10,B&O,Pool,82 +BUY_SHARE_LOG,Marcus,10,N&W,Pool,80 +SELL_SHARE_LOG,Si,10,CPR,65 +PRICE_MOVES_LOG,CPR,65,D3,60,D4 +BUY_SHARE_LOG,Si,10,NYC,Pool,63 +BUY_SHARE_LOG,Ed,10,C&O,Pool,69 +BUY_SHARE_LOG,Phil,10,CPR,Pool,60 +SELL_SHARE_LOG,Chris,10,B&O,82 +PRICE_MOVES_LOG,B&O,82,F2,76,F3 +BUY_SHARE_LOG,Chris,10,NYC,Pool,63 +BUY_SHARE_LOG,Marcus,10,NYC,Pool,63 Autopasses,Si -BUY_SHARE_LOG,Ed,10,C&O,Pool,$69 -BUY_SHARE_LOG,Phil,10,RDG,IPO,$100 -BUY_SHARE_LOG,Chris,10,CPR,IPO,$82 -BUY_SHARE_LOG,Marcus,10,CPR,IPO,$82 +BUY_SHARE_LOG,Ed,10,C&O,Pool,69 +BUY_SHARE_LOG,Phil,10,RDG,IPO,100 +BUY_SHARE_LOG,Chris,10,CPR,IPO,82 +BUY_SHARE_LOG,Marcus,10,CPR,IPO,82 Autopasses,Si -BUY_SHARE_LOG,Ed,10,C&O,Pool,$69 -SELL_SHARES_LOG,Phil,2,10,20,B&M,$152 -PRICE_MOVES_LOG,B&M,$76,H5,$69,H7 -BUY_SHARE_LOG,Phil,10,RDG,IPO,$100 -BUY_SHARE_LOG,Chris,10,CPR,IPO,$82 -BUY_SHARE_LOG,Marcus,10,CPR,IPO,$82 +BUY_SHARE_LOG,Ed,10,C&O,Pool,69 +SELL_SHARES_LOG,Phil,2,10,20,B&M,152 +PRICE_MOVES_LOG,B&M,76,H5,69,H7 +BUY_SHARE_LOG,Phil,10,RDG,IPO,100 +BUY_SHARE_LOG,Chris,10,CPR,IPO,82 +BUY_SHARE_LOG,Marcus,10,CPR,IPO,82 Autopasses,Si -BUY_SHARE_LOG,Ed,10,PRR,Pool,$76 -BUY_SHARE_LOG,Phil,10,RDG,Pool,$111 +BUY_SHARE_LOG,Ed,10,PRR,Pool,76 +BUY_SHARE_LOG,Phil,10,RDG,Pool,111 PASSES,Chris -BUY_SHARE_LOG,Marcus,10,B&O,Pool,$76 +BUY_SHARE_LOG,Marcus,10,B&O,Pool,76 Autopasses,Si -BUY_SHARE_LOG,Ed,10,PRR,IPO,$76 -SELL_SHARE_LOG,Phil,10,C&O,$69 -PRICE_MOVES_LOG,C&O,$69,H7,$68,H8 -BUY_SHARE_LOG,Phil,10,PRR,IPO,$76 +BUY_SHARE_LOG,Ed,10,PRR,IPO,76 +SELL_SHARE_LOG,Phil,10,C&O,69 +PRICE_MOVES_LOG,C&O,69,H7,68,H8 +BUY_SHARE_LOG,Phil,10,PRR,IPO,76 Autopasses,Chris PASSES,Marcus Autopasses,Si -BUY_SHARE_LOG,Ed,10,B&O,IPO,$100 +BUY_SHARE_LOG,Ed,10,B&O,IPO,100 Autopasses,Phil Autopasses,Chris PASSES,Marcus @@ -1237,434 +1237,434 @@ Autopasses,Si PASSES,Ed END_SR,7 -PRICE_MOVES_LOG,RDG,$111,J3,$126,J2 -SoldOut,RDG,$111,J3,$126,J2 -PRICE_MOVES_LOG,N&W,$80,J6,$90,J5 -SoldOut,N&W,$80,J6,$90,J5 -PRICE_MOVES_LOG,PRR,$76,H5,$82,H4 -SoldOut,PRR,$76,H5,$82,H4 -PRICE_MOVES_LOG,B&O,$76,F3,$82,F2 -SoldOut,B&O,$76,F3,$82,F2 -PRICE_MOVES_LOG,NYC,$63,F7,$65,F6 -SoldOut,NYC,$63,F7,$65,F6 -PRICE_MOVES_LOG,CPR,$60,D4,$65,D3 -SoldOut,CPR,$60,D4,$65,D3 -Has,B&M,$6 -Has,B&O,$58 -Has,C&O,$191 -Has,CPR,$121 -Has,Erie,$42 -Has,N&W,$23 -Has,NYC,$38 -Has,NYNH,$165 -Has,PRR,$99 -Has,RDG,$0 -Has,Marcus,$342 -Has,Si,$50 -Has,Ed,$78 -Has,Phil,$647 -Has,Chris,$984 +PRICE_MOVES_LOG,RDG,111,J3,126,J2 +SoldOut,RDG,111,J3,126,J2 +PRICE_MOVES_LOG,N&W,80,J6,90,J5 +SoldOut,N&W,80,J6,90,J5 +PRICE_MOVES_LOG,PRR,76,H5,82,H4 +SoldOut,PRR,76,H5,82,H4 +PRICE_MOVES_LOG,B&O,76,F3,82,F2 +SoldOut,B&O,76,F3,82,F2 +PRICE_MOVES_LOG,NYC,63,F7,65,F6 +SoldOut,NYC,63,F7,65,F6 +PRICE_MOVES_LOG,CPR,60,D4,65,D3 +SoldOut,CPR,60,D4,65,D3 +Has,B&M,6 +Has,B&O,58 +Has,C&O,191 +Has,CPR,121 +Has,Erie,42 +Has,N&W,23 +Has,NYC,38 +Has,NYNH,165 +Has,PRR,99 +Has,RDG,0 +Has,Marcus,342 +Has,Si,50 +Has,Ed,78 +Has,Phil,647 +Has,Chris,984 START_OR,7.1 CompanyOperates,RDG,Ed LaysTileAt,RDG,56,G7,NE -CompanyRevenue,RDG,$340 -CompanyPaysOutFull,RDG,$340 -Payout,Phil,$136,4,10 -Payout,Ed,$204,6,10 -PRICE_MOVES_LOG,RDG,$126,J2,$142,K2 +CompanyRevenue,RDG,340 +CompanyPaysOutFull,RDG,340 +Payout,Phil,136,4,10 +Payout,Ed,204,6,10 +PRICE_MOVES_LOG,RDG,126,J2,142,K2 CompanyOperates,N&W,Chris LaysTileAt,N&W,45,G5,W -CompanyRevenue,N&W,$290 -CompanyPaysOutFull,N&W,$290 -Payout,Chris,$145,5,10 -Payout,Phil,$29,1,10 -Payout,Marcus,$116,4,10 -PRICE_MOVES_LOG,N&W,$90,J5,$100,K5 +CompanyRevenue,N&W,290 +CompanyPaysOutFull,N&W,290 +Payout,Chris,145,5,10 +Payout,Phil,29,1,10 +Payout,Marcus,116,4,10 +PRICE_MOVES_LOG,N&W,90,J5,100,K5 CompanyOperates,PRR,Chris LaysTileAt,PRR,25,F12,E -CompanyRevenue,PRR,$490 -CompanyPaysOutFull,PRR,$490 -Payout,Chris,$294,6,10 -Payout,Phil,$98,2,10 -Payout,Ed,$98,2,10 -PRICE_MOVES_LOG,PRR,$82,H4,$90,I4 +CompanyRevenue,PRR,490 +CompanyPaysOutFull,PRR,490 +Payout,Chris,294,6,10 +Payout,Phil,98,2,10 +Payout,Ed,98,2,10 +PRICE_MOVES_LOG,PRR,82,H4,90,I4 CompanyOperates,B&O,Phil LaysTileAt,B&O,8,E3,SW -CompanyRevenue,B&O,$540 -CompanyPaysOutFull,B&O,$540 -Payout,Phil,$324,6,10 -Payout,Ed,$162,3,10 -Payout,Marcus,$54,1,10 -PRICE_MOVES_LOG,B&O,$82,F2,$90,G2 +CompanyRevenue,B&O,540 +CompanyPaysOutFull,B&O,540 +Payout,Phil,324,6,10 +Payout,Ed,162,3,10 +Payout,Marcus,54,1,10 +PRICE_MOVES_LOG,B&O,82,F2,90,G2 CompanyOperates,NYNH,Marcus LaysTileAt,NYNH,8,E13,W -CompanyRevenue,NYNH,$310 -CompanyPaysOutFull,NYNH,$310 -Payout,Phil,$31,1,10 -Payout,Marcus,$186,6,10 -Payout,NYNH,$93,3,10 -PRICE_MOVES_LOG,NYNH,$70,I7,$75,I6 +CompanyRevenue,NYNH,310 +CompanyPaysOutFull,NYNH,310 +Payout,Phil,31,1,10 +Payout,Marcus,186,6,10 +Payout,NYNH,93,3,10 +PRICE_MOVES_LOG,NYNH,70,I7,75,I6 CompanyOperates,B&M,Chris LaysTileAt,B&M,41,B22,E -CompanyRevenue,B&M,$270 -CompanyPaysOutFull,B&M,$270 -Payout,Chris,$162,6,10 -Payout,B&M,$54,2,10 -PRICE_MOVES_LOG,B&M,$69,H7,$70,I7 +CompanyRevenue,B&M,270 +CompanyPaysOutFull,B&M,270 +Payout,Chris,162,6,10 +Payout,B&M,54,2,10 +PRICE_MOVES_LOG,B&M,69,H7,70,I7 CompanyOperates,Erie,Marcus LaysTileAt,Erie,7,D8,E -LAYS_TOKEN_ON,Erie,D10,$40 -CompanyRevenue,Erie,$160 -CompanyPaysOutFull,Erie,$160 -Payout,Marcus,$80,5,10 -Payout,Erie,$64,4,10 -PRICE_MOVES_LOG,Erie,$68,H8,$69,H7 +LAYS_TOKEN_ON,Erie,D10,40 +CompanyRevenue,Erie,160 +CompanyPaysOutFull,Erie,160 +Payout,Marcus,80,5,10 +Payout,Erie,64,4,10 +PRICE_MOVES_LOG,Erie,68,H8,69,H7 CompanyOperates,C&O,Ed LaysTileAt,C&O,43,I13,NW -CompanyRevenue,C&O,$230 -CompanyPaysOutFull,C&O,$230 -Payout,Ed,$138,6,10 -Payout,C&O,$46,2,10 -PRICE_MOVES_LOG,C&O,$68,H8,$69,H7 +CompanyRevenue,C&O,230 +CompanyPaysOutFull,C&O,230 +Payout,Ed,138,6,10 +Payout,C&O,46,2,10 +PRICE_MOVES_LOG,C&O,68,H8,69,H7 CompanyOperates,NYC,Si LaysTileAt,NYC,23,G11,SW -CompanyRevenue,NYC,$590 -CompanyPaysOutFull,NYC,$590 -Payout,Chris,$59,1,10 -Payout,Phil,$118,2,10 -Payout,Marcus,$59,1,10 -Payout,Si,$354,6,10 -PRICE_MOVES_LOG,NYC,$65,F6,$67,G6 +CompanyRevenue,NYC,590 +CompanyPaysOutFull,NYC,590 +Payout,Chris,59,1,10 +Payout,Phil,118,2,10 +Payout,Marcus,59,1,10 +Payout,Si,354,6,10 +PRICE_MOVES_LOG,NYC,65,F6,67,G6 CompanyOperates,CPR,Si -LaysTileAtFor,CPR,7,B18,NW,$80 -CompanyRevenue,CPR,$250 -CompanyPaysOutFull,CPR,$250 -Payout,Chris,$50,2,10 -Payout,Phil,$25,1,10 -Payout,Marcus,$50,2,10 -Payout,Si,$125,5,10 -PRICE_MOVES_LOG,CPR,$65,D3,$70,E3 +LaysTileAtFor,CPR,7,B18,NW,80 +CompanyRevenue,CPR,250 +CompanyPaysOutFull,CPR,250 +Payout,Chris,50,2,10 +Payout,Phil,25,1,10 +Payout,Marcus,50,2,10 +Payout,Si,125,5,10 +PRICE_MOVES_LOG,CPR,65,D3,70,E3 EndOfOperatingRound,7.1 -ORWorthIncrease,Marcus,7.1,$640 -ORWorthIncrease,Si,7.1,$516 -ORWorthIncrease,Ed,7.1,$744 -ORWorthIncrease,Phil,7.1,$913 -ORWorthIncrease,Chris,7.1,$826 -Has,B&M,$60 -Has,B&O,$58 -Has,C&O,$237 -Has,CPR,$41 -Has,Erie,$66 -Has,N&W,$23 -Has,NYC,$38 -Has,NYNH,$258 -Has,PRR,$99 -Has,RDG,$0 -Has,Marcus,$887 -Has,Si,$529 -Has,Ed,$680 -Has,Phil,$1408 -Has,Chris,$1694 +ORWorthIncrease,Marcus,7.1,640 +ORWorthIncrease,Si,7.1,516 +ORWorthIncrease,Ed,7.1,744 +ORWorthIncrease,Phil,7.1,913 +ORWorthIncrease,Chris,7.1,826 +Has,B&M,60 +Has,B&O,58 +Has,C&O,237 +Has,CPR,41 +Has,Erie,66 +Has,N&W,23 +Has,NYC,38 +Has,NYNH,258 +Has,PRR,99 +Has,RDG,0 +Has,Marcus,887 +Has,Si,529 +Has,Ed,680 +Has,Phil,1408 +Has,Chris,1694 START_OR,7.2 CompanyOperates,RDG,Ed LaysTileAt,RDG,24,F14,W -CompanyRevenue,RDG,$380 -CompanyPaysOutFull,RDG,$380 -Payout,Phil,$152,4,10 -Payout,Ed,$228,6,10 -PRICE_MOVES_LOG,RDG,$142,K2,$160,L2 +CompanyRevenue,RDG,380 +CompanyPaysOutFull,RDG,380 +Payout,Phil,152,4,10 +Payout,Ed,228,6,10 +PRICE_MOVES_LOG,RDG,142,K2,160,L2 CompanyOperates,N&W,Chris LaysTileAt,N&W,24,E3,SW -CompanyRevenue,N&W,$290 -CompanyPaysOutFull,N&W,$290 -Payout,Chris,$145,5,10 -Payout,Phil,$29,1,10 -Payout,Marcus,$116,4,10 -PRICE_MOVES_LOG,N&W,$100,K5,$110,K4 +CompanyRevenue,N&W,290 +CompanyPaysOutFull,N&W,290 +Payout,Chris,145,5,10 +Payout,Phil,29,1,10 +Payout,Marcus,116,4,10 +PRICE_MOVES_LOG,N&W,100,K5,110,K4 CompanyOperates,PRR,Chris LaysTileAt,PRR,4,D4,W -CompanyRevenue,PRR,$490 -CompanyPaysOutFull,PRR,$490 -Payout,Chris,$294,6,10 -Payout,Phil,$98,2,10 -Payout,Ed,$98,2,10 -PRICE_MOVES_LOG,PRR,$90,I4,$100,J4 +CompanyRevenue,PRR,490 +CompanyPaysOutFull,PRR,490 +Payout,Chris,294,6,10 +Payout,Phil,98,2,10 +Payout,Ed,98,2,10 +PRICE_MOVES_LOG,PRR,90,I4,100,J4 CompanyOperates,B&O,Phil LaysTileAt,B&O,8,J8,W -CompanyRevenue,B&O,$570 -CompanyPaysOutFull,B&O,$570 -Payout,Phil,$342,6,10 -Payout,Ed,$171,3,10 -Payout,Marcus,$57,1,10 -PRICE_MOVES_LOG,B&O,$90,G2,$100,H2 +CompanyRevenue,B&O,570 +CompanyPaysOutFull,B&O,570 +Payout,Phil,342,6,10 +Payout,Ed,171,3,10 +Payout,Marcus,57,1,10 +PRICE_MOVES_LOG,B&O,90,G2,100,H2 CompanyOperates,NYNH,Marcus LaysTileAt,NYNH,9,D12,W -CompanyRevenue,NYNH,$310 -CompanyPaysOutFull,NYNH,$310 -Payout,Phil,$31,1,10 -Payout,Marcus,$186,6,10 -Payout,NYNH,$93,3,10 -PRICE_MOVES_LOG,NYNH,$75,I6,$80,J6 +CompanyRevenue,NYNH,310 +CompanyPaysOutFull,NYNH,310 +Payout,Phil,31,1,10 +Payout,Marcus,186,6,10 +Payout,NYNH,93,3,10 +PRICE_MOVES_LOG,NYNH,75,I6,80,J6 CompanyOperates,B&M,Chris -CompanyRevenue,B&M,$270 -CompanyPaysOutFull,B&M,$270 -Payout,Chris,$162,6,10 -Payout,B&M,$54,2,10 -PRICE_MOVES_LOG,B&M,$70,I7,$75,I6 +CompanyRevenue,B&M,270 +CompanyPaysOutFull,B&M,270 +Payout,Chris,162,6,10 +Payout,B&M,54,2,10 +PRICE_MOVES_LOG,B&M,70,I7,75,I6 CompanyOperates,CPR,Si LaysTileAt,CPR,57,B16,SW -CompanyRevenue,CPR,$250 -CompanyPaysOutFull,CPR,$250 -Payout,Chris,$50,2,10 -Payout,Phil,$25,1,10 -Payout,Marcus,$50,2,10 -Payout,Si,$125,5,10 -PRICE_MOVES_LOG,CPR,$70,E3,$76,F3 +CompanyRevenue,CPR,250 +CompanyPaysOutFull,CPR,250 +Payout,Chris,50,2,10 +Payout,Phil,25,1,10 +Payout,Marcus,50,2,10 +Payout,Si,125,5,10 +PRICE_MOVES_LOG,CPR,70,E3,76,F3 CompanyOperates,Erie,Marcus LaysTileAt,Erie,45,F12,SW -CompanyRevenue,Erie,$270 -CompanyPaysOutFull,Erie,$270 -Payout,Marcus,$135,5,10 -Payout,Erie,$108,4,10 -PRICE_MOVES_LOG,Erie,$69,H7,$70,I7 +CompanyRevenue,Erie,270 +CompanyPaysOutFull,Erie,270 +Payout,Marcus,135,5,10 +Payout,Erie,108,4,10 +PRICE_MOVES_LOG,Erie,69,H7,70,I7 CompanyOperates,C&O,Ed LaysTileAt,C&O,9,E15,SW -CompanyRevenue,C&O,$230 -CompanyPaysOutFull,C&O,$230 -Payout,Ed,$138,6,10 -Payout,C&O,$46,2,10 -PRICE_MOVES_LOG,C&O,$69,H7,$70,I7 +CompanyRevenue,C&O,230 +CompanyPaysOutFull,C&O,230 +Payout,Ed,138,6,10 +Payout,C&O,46,2,10 +PRICE_MOVES_LOG,C&O,69,H7,70,I7 CompanyOperates,NYC,Si LaysTileAt,NYC,43,G9,E -CompanyRevenue,NYC,$600 -CompanyPaysOutFull,NYC,$600 -Payout,Chris,$60,1,10 -Payout,Phil,$120,2,10 -Payout,Marcus,$60,1,10 -Payout,Si,$360,6,10 -PRICE_MOVES_LOG,NYC,$67,G6,$71,H6 +CompanyRevenue,NYC,600 +CompanyPaysOutFull,NYC,600 +Payout,Chris,60,1,10 +Payout,Phil,120,2,10 +Payout,Marcus,60,1,10 +Payout,Si,360,6,10 +PRICE_MOVES_LOG,NYC,67,G6,71,H6 EndOfOperatingRound,7.2 -ORWorthIncrease,Marcus,7.2,$705 -ORWorthIncrease,Si,7.2,$539 -ORWorthIncrease,Ed,7.2,$799 -ORWorthIncrease,Phil,7.2,$978 -ORWorthIncrease,Chris,7.2,$867 -Has,B&M,$114 -Has,B&O,$58 -Has,C&O,$283 -Has,CPR,$41 -Has,Erie,$174 -Has,N&W,$23 -Has,NYC,$38 -Has,NYNH,$351 -Has,PRR,$99 -Has,RDG,$0 -Has,Marcus,$1491 -Has,Si,$1014 -Has,Ed,$1315 -Has,Phil,$2205 -Has,Chris,$2405 +ORWorthIncrease,Marcus,7.2,705 +ORWorthIncrease,Si,7.2,539 +ORWorthIncrease,Ed,7.2,799 +ORWorthIncrease,Phil,7.2,978 +ORWorthIncrease,Chris,7.2,867 +Has,B&M,114 +Has,B&O,58 +Has,C&O,283 +Has,CPR,41 +Has,Erie,174 +Has,N&W,23 +Has,NYC,38 +Has,NYNH,351 +Has,PRR,99 +Has,RDG,0 +Has,Marcus,1491 +Has,Si,1014 +Has,Ed,1315 +Has,Phil,2205 +Has,Chris,... [truncated message content] |
From: Stefan F. <ste...@us...> - 2011-08-11 10:00:38
|
rails/game/specific/_18TN/PublicCompany_18TN.java | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) New commits: commit 65f7ed334d271a38a138aeaa2e25ca5c36b9d759 Author: Stefan Frey <ste...@we...> Date: Thu Aug 11 12:02:39 2011 +0200 Fixed bug in 18TN modifier diff --git a/rails/game/specific/_18TN/PublicCompany_18TN.java b/rails/game/specific/_18TN/PublicCompany_18TN.java index b6fe19d..8b3869e 100644 --- a/rails/game/specific/_18TN/PublicCompany_18TN.java +++ b/rails/game/specific/_18TN/PublicCompany_18TN.java @@ -54,6 +54,9 @@ public class PublicCompany_18TN extends PublicCompany implements RevenueStaticMo */ public boolean modifyCalculator(RevenueAdapter revenueAdapter) { + // check first if it is the company for the revenue calculation + if (revenueAdapter.getCompany() != this) return false; + // check if it is civil war, otherwise no effect if (!isCivilWar()) return false; @@ -72,8 +75,5 @@ public class PublicCompany_18TN extends PublicCompany implements RevenueStaticMo public String prettyPrint(RevenueAdapter revenueAdapter) { return LocalText.getText("CivilWarActive"); } - - - } |
From: Stefan F. <ste...@us...> - 2011-08-11 09:56:22
|
LocalisedText.properties | 1 data/18TN/Game.xml | 3 rails/algorithms/NetworkGraphBuilder.java | 2 rails/algorithms/NetworkTrain.java | 43 +++++ rails/algorithms/RevenueAdapter.java | 62 +++----- rails/algorithms/RevenueManager.java | 114 +++++++++++++-- rails/algorithms/RevenueStaticModifier.java | 13 + rails/game/Bonus.java | 13 + rails/game/special/SpecialRight.java | 17 +- rails/game/specific/_1825/ScoreTileOnlyOnceModifier.java | 12 + rails/game/specific/_1851/OffBoardRevenueModifier.java | 9 + rails/game/specific/_1856/PublicCompany_CGR.java | 11 + rails/game/specific/_18AL/NamedTrainRevenueModifier.java | 19 +- rails/game/specific/_18EU/OffBoardRevenueModifier.java | 12 + rails/game/specific/_18Kaas/RuhrRevenueModifier.java | 11 + rails/game/specific/_18TN/PublicCompany_18TN.java | 38 ++++- 16 files changed, 309 insertions(+), 71 deletions(-) New commits: commit 4ba69a2f5672264290b00102a18afa06fe53187f Author: Stefan Frey <ste...@we...> Date: Thu Aug 11 11:57:16 2011 +0200 Refactoring of the revenue modifiers: Moving a lot of functionality from revenue adapter to the revenue manager. Allow static modifier to display pretty print as well. diff --git a/LocalisedText.properties b/LocalisedText.properties index f5b4b38..b0750ce 100644 --- a/LocalisedText.properties +++ b/LocalisedText.properties @@ -129,6 +129,7 @@ CantSell={0} cannot sell {1} share(s) of {2}: {3} CantStart={0} cannot start company {1} for {2}: {3} CertificateLimit=The certificate limit is now {0} ({1} players, {2} companies) CityHasNoEmptySlots=City has not empty slots +CivilWarActive=Civil War is active. ClassCannotBeInstantiated=Class {0} cannot be instantiated ClickForSell=Click to select for selling ClickToSelectForBuying=Click to select for buying diff --git a/rails/algorithms/NetworkGraphBuilder.java b/rails/algorithms/NetworkGraphBuilder.java index ec34efb..1488cc9 100644 --- a/rails/algorithms/NetworkGraphBuilder.java +++ b/rails/algorithms/NetworkGraphBuilder.java @@ -153,7 +153,7 @@ public final class NetworkGraphBuilder implements Iterable<NetworkVertex> { // add graph modifiers if (revenueManager != null) { - revenueManager.callGraphModifiers(this); + revenueManager.initGraphModifiers(this); } } diff --git a/rails/algorithms/RevenueAdapter.java b/rails/algorithms/RevenueAdapter.java index 080b585..9df031a 100644 --- a/rails/algorithms/RevenueAdapter.java +++ b/rails/algorithms/RevenueAdapter.java @@ -60,6 +60,7 @@ public final class RevenueAdapter implements Runnable { // basic links, to be defined at creation private final GameManagerI gameManager; + private final RevenueManager revenueManager; private final NetworkGraphBuilder graphBuilder; private final NetworkCompanyGraph companyGraph; private final PublicCompanyI company; @@ -81,7 +82,8 @@ public final class RevenueAdapter implements Runnable { private List<NetworkVertex> rcVertices; private List<NetworkEdge> rcEdges; private List<RevenueTrainRun> optimalRun; - private List<RevenueDynamicModifier> dynamicModifiers; + private boolean hasDynamicModifiers; + private boolean hasDynamicCalculator; // revenue listener to communicate results private RevenueListener revenueListener; @@ -89,6 +91,7 @@ public final class RevenueAdapter implements Runnable { public RevenueAdapter(GameManagerI gameManager, NetworkGraphBuilder graphBuilder, NetworkCompanyGraph companyGraph, PublicCompanyI company, PhaseI phase){ this.gameManager = gameManager; + this.revenueManager = gameManager.getRevenueManager(); this.graphBuilder = graphBuilder; this.companyGraph = companyGraph; this.company = company; @@ -231,8 +234,8 @@ public final class RevenueAdapter implements Runnable { } // add all static modifiers - if (gameManager.getRevenueManager() != null) { - gameManager.getRevenueManager().callStaticModifiers(this); + if (revenueManager != null) { + revenueManager.initStaticModifiers(this); } } @@ -302,11 +305,10 @@ public final class RevenueAdapter implements Runnable { this.useMultiGraph = useMultiGraph; - // add all dynamic modifiers - if (gameManager.getRevenueManager() != null) { - dynamicModifiers = gameManager.getRevenueManager().callDynamicModifiers(this); - } else { - dynamicModifiers = new ArrayList<RevenueDynamicModifier>(); + // check for dynamic modifiers (including an own calculator + if (revenueManager != null) { + hasDynamicModifiers = revenueManager.initDynamicModifiers(this); + hasDynamicCalculator = revenueManager.hasDynamicCalculator(); } // define optimized graph @@ -524,7 +526,7 @@ public final class RevenueAdapter implements Runnable { // activate dynamic modifiers - rc.setDynamicModifiers(!dynamicModifiers.isEmpty()); + rc.setDynamicModifiers(hasDynamicModifiers); } public int getVertexValue(NetworkVertex vertex, NetworkTrain train, PhaseI phase) { @@ -583,19 +585,10 @@ public final class RevenueAdapter implements Runnable { } public int calculateRevenue() { - // allow dynamic modifiers to have their own revenue calculation method - boolean isModified = false; - int value = 0; - for (RevenueDynamicModifier modifier:dynamicModifiers) { - if (modifier.providesOwnCalculateRevenue()) { - isModified = true; - value += modifier.calculateRevenue(this); - } - } - // if no modifier was used, standard method is to evaluate all trains - if (isModified) { - return value; - } else { + // allows (one) dynamic modifiers to have their own revenue calculation method + if (hasDynamicCalculator) { + return revenueManager.revenueFromDynamicCalculator(this); + } else { // otherwise standard calculation return calculateRevenue(0, trains.size() - 1); } } @@ -615,9 +608,8 @@ public final class RevenueAdapter implements Runnable { public List<RevenueTrainRun> getOptimalRun() { if (optimalRun == null) { optimalRun = convertRcRun(rc.getOptimalRun()); - // allow dynamic modifiers to change the optimal run - for (RevenueDynamicModifier modifier:dynamicModifiers) { - modifier.adjustOptimalRun(optimalRun); + if (hasDynamicModifiers) { + revenueManager.adjustOptimalRun(optimalRun); } } return optimalRun; @@ -632,9 +624,8 @@ public final class RevenueAdapter implements Runnable { */ int dynamicEvaluation() { int value = 0; - List<RevenueTrainRun> run = this.getCurrentRun(); - for (RevenueDynamicModifier modifier:dynamicModifiers) { - value += modifier.evaluationValue(run, false); + if (hasDynamicModifiers) { + value = revenueManager.evaluationValue(this.getCurrentRun(), false); } return value; } @@ -644,8 +635,8 @@ public final class RevenueAdapter implements Runnable { */ int dynamicPrediction() { int value = 0; - for (RevenueDynamicModifier modifier:dynamicModifiers) { - value += modifier.predictionValue(); + if (hasDynamicModifiers) { + value = revenueManager.predictionValue(); } return value; } @@ -687,16 +678,13 @@ public final class RevenueAdapter implements Runnable { } } if (includeDetails) { - for (RevenueDynamicModifier modifier:dynamicModifiers) { - String modifierText = modifier.prettyPrint(this); - if (modifierText != null) { - runPrettyPrint.append(modifierText); - } + if (revenueManager != null) { + runPrettyPrint.append(revenueManager.prettyPrint(this)); } } else { int dynamicBonuses = 0; - for (RevenueDynamicModifier modifier:dynamicModifiers) { - dynamicBonuses += modifier.evaluationValue(this.getOptimalRun(), true); + if (hasDynamicModifiers) { + dynamicBonuses = revenueManager.evaluationValue(this.getOptimalRun(), true); } if (dynamicBonuses != 0) { runPrettyPrint.append("; " + diff --git a/rails/algorithms/RevenueManager.java b/rails/algorithms/RevenueManager.java index 5f4210d..d8b11e2 100644 --- a/rails/algorithms/RevenueManager.java +++ b/rails/algorithms/RevenueManager.java @@ -29,17 +29,24 @@ public final class RevenueManager implements ConfigurableComponentI { protected static Logger log = Logger.getLogger(RevenueManager.class.getPackage().getName()); + private final HashSet<ConfigurableComponentI> configurableModifiers; private final ArrayListState<NetworkGraphModifier> graphModifiers; private final ArrayListState<RevenueStaticModifier> staticModifiers; private final ArrayListState<RevenueDynamicModifier> dynamicModifiers; - private final HashSet<ConfigurableComponentI> configurableModifiers; + + private final ArrayList<RevenueStaticModifier> activeStaticModifiers; + private final ArrayList<RevenueDynamicModifier> activeDynamicModifiers; + private RevenueDynamicModifier activeCalculator; public RevenueManager() { graphModifiers = new ArrayListState<NetworkGraphModifier>("NetworkGraphModifiers"); staticModifiers = new ArrayListState<RevenueStaticModifier>("RevenueStaticModifiers"); dynamicModifiers = new ArrayListState<RevenueDynamicModifier>("RevenueDynamicModifiers"); configurableModifiers = new HashSet<ConfigurableComponentI>(); + + activeStaticModifiers = new ArrayList<RevenueStaticModifier>(); + activeDynamicModifiers = new ArrayList<RevenueDynamicModifier>(); } public void configureFromXML(Tag tag) throws ConfigurationException { @@ -144,25 +151,116 @@ public final class RevenueManager implements ConfigurableComponentI { return result; } - void callGraphModifiers(NetworkGraphBuilder graphBuilder) { + void initGraphModifiers(NetworkGraphBuilder graphBuilder) { for (NetworkGraphModifier modifier:graphModifiers.viewList()) { modifier.modifyGraph(graphBuilder); } } - void callStaticModifiers(RevenueAdapter revenueAdapter) { + void initStaticModifiers(RevenueAdapter revenueAdapter) { + activeStaticModifiers.clear(); for (RevenueStaticModifier modifier:staticModifiers.viewList()) { - modifier.modifyCalculator(revenueAdapter); + if (modifier.modifyCalculator(revenueAdapter)) { + activeStaticModifiers.add(modifier); + } } } - List<RevenueDynamicModifier> callDynamicModifiers(RevenueAdapter revenueAdapter) { - List<RevenueDynamicModifier> activeModifiers = new ArrayList<RevenueDynamicModifier>(); + /** + * @param revenueAdapter + * @return true if there are active dynamic modifiers + */ + boolean initDynamicModifiers(RevenueAdapter revenueAdapter) { + activeDynamicModifiers.clear(); for (RevenueDynamicModifier modifier:dynamicModifiers.viewList()) { if (modifier.prepareModifier(revenueAdapter)) - activeModifiers.add(modifier); + activeDynamicModifiers.add(modifier); + } + return !activeDynamicModifiers.isEmpty(); + } + + /** + * @return true if one of the dynamic modifiers is an calculator of its own + */ + boolean hasDynamicCalculator() { + for (RevenueDynamicModifier modifier:activeDynamicModifiers) { + if (modifier.providesOwnCalculateRevenue()) { + activeCalculator = modifier; + return true; + } } - return activeModifiers; + return false; + } + + /** + * @param revenueAdapter + * @return revenue from active calculator + */ + int revenueFromDynamicCalculator(RevenueAdapter revenueAdapter) { + return activeCalculator.calculateRevenue(revenueAdapter); + } + /** + * Allows dynamic modifiers to adjust the optimal run + * @param optimalRun + */ + void adjustOptimalRun(List<RevenueTrainRun> optimalRun) { + // allow dynamic modifiers to change the optimal run + for (RevenueDynamicModifier modifier:activeDynamicModifiers) { + modifier.adjustOptimalRun(optimalRun); + } + } + + /** + * @param run the current run + * @param optimal flag if this is the found optimal run + * @return total value of dynamic modifiers + */ + int evaluationValue(List<RevenueTrainRun> run, boolean optimal) { + // allow dynamic modifiers to change the optimal run + int value = 0; + for (RevenueDynamicModifier modifier:activeDynamicModifiers) { + value += modifier.evaluationValue(run, optimal); + } + return value; + } + + /** + * @return total prediction value of dynamic modifiers + */ + int predictionValue() { + int value = 0; + for (RevenueDynamicModifier modifier:activeDynamicModifiers) { + value += modifier.predictionValue(); + } + return value; + } + + /** + * + * @param revenueAdapter + * @return pretty print output from all modifiers (both static and dynamic) + */ + String prettyPrint(RevenueAdapter revenueAdapter) { + StringBuffer prettyPrint = new StringBuffer(); + + for (RevenueStaticModifier modifier:activeStaticModifiers) { + String modifierText = modifier.prettyPrint(revenueAdapter); + if (modifierText != null) { + prettyPrint.append(modifierText + "\n"); + } + } + + for (RevenueDynamicModifier modifier:activeDynamicModifiers) { + String modifierText = modifier.prettyPrint(revenueAdapter); + if (modifierText != null) { + prettyPrint.append(modifierText + "\n"); + } + } + + return prettyPrint.toString(); + } + + } diff --git a/rails/algorithms/RevenueStaticModifier.java b/rails/algorithms/RevenueStaticModifier.java index 501aa21..27e68cd 100644 --- a/rails/algorithms/RevenueStaticModifier.java +++ b/rails/algorithms/RevenueStaticModifier.java @@ -13,6 +13,17 @@ package rails.algorithms; public interface RevenueStaticModifier{ - public void modifyCalculator(RevenueAdapter revenueAdapter); + /** method called after the setup of the revenueAdapter, but before the actual calculation + * Allows to call methods of the revenue adapter to change the content + * @param revenueAdapter + * @return if true a pretty print text is required + */ + public boolean modifyCalculator(RevenueAdapter revenueAdapter); + + /** + * Allows to append additional text + * Only called if modifyCalculator returned true + * @return String output for display in Rails */ + public String prettyPrint(RevenueAdapter revenueAdapter); } diff --git a/rails/game/Bonus.java b/rails/game/Bonus.java index 9cde020..1256b65 100644 --- a/rails/game/Bonus.java +++ b/rails/game/Bonus.java @@ -104,17 +104,26 @@ public class Bonus implements Closeable, RevenueStaticModifier { /** * Add bonus value to revenue calculator */ - public void modifyCalculator(RevenueAdapter revenueAdapter) { + public boolean modifyCalculator(RevenueAdapter revenueAdapter) { // 1. check operating company - if (owner != revenueAdapter.getCompany()) return; + if (owner != revenueAdapter.getCompany()) return false; // 2. find vertices to hex + boolean found = false; Set<NetworkVertex> bonusVertices = NetworkVertex.getVerticesByHexes(revenueAdapter.getVertices(), locations); for (NetworkVertex bonusVertex:bonusVertices) { if (!bonusVertex.isStation()) continue; RevenueBonus bonus = new RevenueBonus(value, name); bonus.addVertex(bonusVertex); revenueAdapter.addRevenueBonus(bonus); + found = true; } + return found; } + + public String prettyPrint(RevenueAdapter revenueAdapter) { + if (name == null) return null; + return "Bonus active = " + name; + } + } diff --git a/rails/game/special/SpecialRight.java b/rails/game/special/SpecialRight.java index 65f0611..0b9647b 100644 --- a/rails/game/special/SpecialRight.java +++ b/rails/game/special/SpecialRight.java @@ -122,15 +122,22 @@ public class SpecialRight extends SpecialProperty implements RevenueStaticModifi /** * modify revenue calculation of the - * TODO: rights is missing a location field, currently hardcoded for 1830 coalfields + * TODO: if owner would be known or only one rights object pretty print would be possible */ - public void modifyCalculator(RevenueAdapter revenueAdapter) { + public boolean modifyCalculator(RevenueAdapter revenueAdapter) { // 1. check operating company if it has the right then it is excluded from the removal - if (revenueAdapter.getCompany().hasRight(rightName)) return; + if (revenueAdapter.getCompany().hasRight(rightName)) return false; // 2. find vertices to hex and remove those - MapHex hex = GameManager.getInstance().getMapManager().getHex("L10"); - Set<NetworkVertex> verticesToRemove = NetworkVertex.getVerticesByHex(revenueAdapter.getVertices(), hex); + Set<NetworkVertex> verticesToRemove = NetworkVertex.getVerticesByHexes(revenueAdapter.getVertices(), locations); revenueAdapter.getGraph().removeAllVertices(verticesToRemove); + + // nothing to print, as the owner is unknown + return false; + } + + public String prettyPrint(RevenueAdapter revenueAdapter) { + // nothing to print + return null; } } diff --git a/rails/game/specific/_1825/ScoreTileOnlyOnceModifier.java b/rails/game/specific/_1825/ScoreTileOnlyOnceModifier.java index baa2eb7..66c4285 100644 --- a/rails/game/specific/_1825/ScoreTileOnlyOnceModifier.java +++ b/rails/game/specific/_1825/ScoreTileOnlyOnceModifier.java @@ -15,7 +15,8 @@ import rails.game.MapHex; public class ScoreTileOnlyOnceModifier implements RevenueStaticModifier { - public void modifyCalculator(RevenueAdapter revenueAdapter) { + public boolean modifyCalculator(RevenueAdapter revenueAdapter) { + // 1. define for each hex a list of stations HashMap<MapHex, List<NetworkVertex>> hexStations = new HashMap<MapHex, List<NetworkVertex>>(); for (NetworkVertex v:revenueAdapter.getVertices()) { @@ -27,13 +28,20 @@ public class ScoreTileOnlyOnceModifier implements RevenueStaticModifier { hexStations.get(v.getHex()).add(v); } } + // 2. convert those with more than one station to a vertex visit set for (MapHex hex:hexStations.keySet()) { if (hexStations.get(hex).size() >= 2) { revenueAdapter.addVertexVisitSet(revenueAdapter.new VertexVisit(hexStations.get(hex))); } } - + // nothing to print + return false; } + public String prettyPrint(RevenueAdapter revenueAdapter) { + // nothing to print + return null; + } + } diff --git a/rails/game/specific/_1851/OffBoardRevenueModifier.java b/rails/game/specific/_1851/OffBoardRevenueModifier.java index 4fc7e0a..6956f3c 100644 --- a/rails/game/specific/_1851/OffBoardRevenueModifier.java +++ b/rails/game/specific/_1851/OffBoardRevenueModifier.java @@ -13,7 +13,7 @@ public class OffBoardRevenueModifier implements RevenueStaticModifier { private static final int BONUS_VALUE = 10; - public void modifyCalculator(RevenueAdapter revenueAdapter) { + public boolean modifyCalculator(RevenueAdapter revenueAdapter) { // 1. get all off-board type stations and all other stations Set<NetworkVertex> offBoard = new HashSet<NetworkVertex>(); Set<NetworkVertex> otherStations = new HashSet<NetworkVertex>(); @@ -43,5 +43,12 @@ public class OffBoardRevenueModifier implements RevenueStaticModifier { } } } + // no additional text required + return false; + } + + public String prettyPrint(RevenueAdapter revenueAdapter) { + // nothing to print + return null; } } diff --git a/rails/game/specific/_1856/PublicCompany_CGR.java b/rails/game/specific/_1856/PublicCompany_CGR.java index e39a88a..113edd2 100644 --- a/rails/game/specific/_1856/PublicCompany_CGR.java +++ b/rails/game/specific/_1856/PublicCompany_CGR.java @@ -162,13 +162,20 @@ public class PublicCompany_CGR extends PublicCompany implements RevenueStaticMod return (hasTemporaryPresident() ? "T" : ""); } - public void modifyCalculator(RevenueAdapter revenueAdapter) { + public boolean modifyCalculator(RevenueAdapter revenueAdapter) { // check if the running company is the cgr - if (revenueAdapter.getCompany() != this) return; + if (revenueAdapter.getCompany() != this) return false; // add the diesel train if (runsWithBorrowedTrain()) { revenueAdapter.addTrainByString("D"); + return true; } + return false; + } + + public String prettyPrint(RevenueAdapter revenueAdapter) { + + return null; } } diff --git a/rails/game/specific/_18AL/NamedTrainRevenueModifier.java b/rails/game/specific/_18AL/NamedTrainRevenueModifier.java index 4777915..43893b9 100644 --- a/rails/game/specific/_18AL/NamedTrainRevenueModifier.java +++ b/rails/game/specific/_18AL/NamedTrainRevenueModifier.java @@ -57,9 +57,9 @@ public class NamedTrainRevenueModifier implements RevenueStaticModifier, Revenue } - public void modifyCalculator(RevenueAdapter revenueAdapter) { + public boolean modifyCalculator(RevenueAdapter revenueAdapter) { // static modifier - if (dynamic) return; + if (dynamic) return false; // 1. check all Trains for name Tokens for (NetworkTrain networkTrain:revenueAdapter.getTrains()) { @@ -73,6 +73,8 @@ public class NamedTrainRevenueModifier implements RevenueStaticModifier, Revenue bonus.addTrain(train); revenueAdapter.addRevenueBonus(bonus); } + // no additional text required + return false; } public boolean prepareModifier(RevenueAdapter revenueAdapter) { @@ -129,19 +131,24 @@ public class NamedTrainRevenueModifier implements RevenueStaticModifier, Revenue } public String prettyPrint(RevenueAdapter revenueAdapter) { + List<RevenueTrainRun> runs = revenueAdapter.getOptimalRun(); StringBuffer prettyPrint = new StringBuffer(); + + boolean first = true; for (RevenueBonus bonus:bonuses) { for (RevenueTrainRun run:runs) { if (run.getUniqueVertices().containsAll(bonus.getVertices())) { - prettyPrint.append(bonus.getName() + " = " + bonus.getValue() + "\n"); + if (!first) { + prettyPrint.append("\n"); // add line break, except for the first + } else { + first = false; + } + prettyPrint.append(bonus.getName() + " = " + bonus.getValue()); continue; // each bonus can only be scored once } } } return prettyPrint.toString(); } - - - } diff --git a/rails/game/specific/_18EU/OffBoardRevenueModifier.java b/rails/game/specific/_18EU/OffBoardRevenueModifier.java index 656f917..ce0d0ae 100644 --- a/rails/game/specific/_18EU/OffBoardRevenueModifier.java +++ b/rails/game/specific/_18EU/OffBoardRevenueModifier.java @@ -20,7 +20,7 @@ public class OffBoardRevenueModifier implements RevenueStaticModifier { Logger.getLogger(OffBoardRevenueModifier.class.getPackage().getName()); - public void modifyCalculator(RevenueAdapter revenueAdapter) { + public boolean modifyCalculator(RevenueAdapter revenueAdapter) { // 1. define value PhaseI phase = revenueAdapter.getPhase(); @@ -32,7 +32,7 @@ public class OffBoardRevenueModifier implements RevenueStaticModifier { } else if (phase.isTileColourAllowed(Tile.GREEN_COLOUR_NAME)) { bonusValue = 10; } else { - return; + return false; } log.info("OffBoardRevenueModifier: bonusValue = " + bonusValue); @@ -79,5 +79,13 @@ public class OffBoardRevenueModifier implements RevenueStaticModifier { } } } + // no additional text required + return false; + } + + + public String prettyPrint(RevenueAdapter revenueAdapter) { + // nothing to do + return null; } } diff --git a/rails/game/specific/_18Kaas/RuhrRevenueModifier.java b/rails/game/specific/_18Kaas/RuhrRevenueModifier.java index 99555e2..840fab5 100644 --- a/rails/game/specific/_18Kaas/RuhrRevenueModifier.java +++ b/rails/game/specific/_18Kaas/RuhrRevenueModifier.java @@ -32,7 +32,7 @@ public class RuhrRevenueModifier implements RevenueStaticModifier, ConfigurableC } // creates revenueBonuses that double the value of each station/value vertex - public void modifyCalculator(RevenueAdapter revenueAdapter) { + public boolean modifyCalculator(RevenueAdapter revenueAdapter) { Set<NetworkVertex> ruhrGebied = new HashSet<NetworkVertex>(); for (NetworkVertex vertex:revenueAdapter.getVertices()) { @@ -41,6 +41,7 @@ public class RuhrRevenueModifier implements RevenueStaticModifier, ConfigurableC ruhrGebied.add(vertex); } } + // 2. add revenue bonuses for stations for (NetworkVertex vertex:revenueAdapter.getVertices()) { if (!ruhrGebied.contains(vertex) && vertex.isStation() && (vertex.isMajor() || !doublesOnlyMajors)) { @@ -52,5 +53,13 @@ public class RuhrRevenueModifier implements RevenueStaticModifier, ConfigurableC } } } + + // nothing to print + return false; + } + + public String prettyPrint(RevenueAdapter revenueAdapter) { + // nothing to print + return null; } } diff --git a/rails/game/specific/_18TN/PublicCompany_18TN.java b/rails/game/specific/_18TN/PublicCompany_18TN.java index 53c550f..b6fe19d 100644 --- a/rails/game/specific/_18TN/PublicCompany_18TN.java +++ b/rails/game/specific/_18TN/PublicCompany_18TN.java @@ -6,6 +6,7 @@ import java.util.List; import rails.algorithms.NetworkTrain; import rails.algorithms.RevenueAdapter; import rails.algorithms.RevenueStaticModifier; +import rails.common.LocalText; import rails.common.parser.ConfigurationException; import rails.game.GameManagerI; import rails.game.PublicCompany; @@ -16,7 +17,6 @@ public class PublicCompany_18TN extends PublicCompany implements RevenueStaticMo private BooleanState civilWar; - public ModelObject getCivilWar() { return civilWar; } @@ -52,20 +52,28 @@ public class PublicCompany_18TN extends PublicCompany implements RevenueStaticMo /** * Modify the revenue calculation for the civil war by removing the shortest train */ - public void modifyCalculator(RevenueAdapter revenueAdapter) { + public boolean modifyCalculator(RevenueAdapter revenueAdapter) { // check if it is civil war, otherwise no effect - if (!isCivilWar()) return; + if (!isCivilWar()) return false; List<NetworkTrain> trains = revenueAdapter.getTrains(); - if (trains.size() == 0) return; // no train, no effect + if (trains.size() == 0) return false; // no train, no effect // sort trains in ascending order (by domination which is equal to length for TN) Collections.sort(trains); // and remove the first train (shortest) trains.remove(0); + + return true; + } + + public String prettyPrint(RevenueAdapter revenueAdapter) { + return LocalText.getText("CivilWarActive"); } + + } commit 92911e549ee5d25bf7d3fb7808cc7d344e8bdd35 Author: Stefan Frey <ste...@we...> Date: Wed Aug 10 12:38:59 2011 +0200 Added train domination comparator to NetworkTrains Civil war effects on Revenue Calculation diff --git a/data/18TN/Game.xml b/data/18TN/Game.xml index 8e971cd..837b8e9 100644 --- a/data/18TN/Game.xml +++ b/data/18TN/Game.xml @@ -121,5 +121,8 @@ </Phase> <Phase name="8"> </Phase> + </Component> + <Component name="RevenueManager" class="rails.algorithms.RevenueManager"> + <!-- Required for TN civil war '--> </Component> </ComponentManager> \ No newline at end of file diff --git a/rails/algorithms/NetworkTrain.java b/rails/algorithms/NetworkTrain.java index 2232c36..b532bda 100644 --- a/rails/algorithms/NetworkTrain.java +++ b/rails/algorithms/NetworkTrain.java @@ -1,11 +1,12 @@ package rails.algorithms; + import org.apache.log4j.Logger; import rails.game.TrainI; import rails.game.TrainType; -public final class NetworkTrain { +public final class NetworkTrain implements Comparable<NetworkTrain>{ protected static Logger log = Logger.getLogger(NetworkTrain.class.getPackage().getName()); @@ -164,4 +165,44 @@ public final class NetworkTrain { return trainName; } + + /** + * Comperator on trains as defined by train domination + * + * A train dominates: + * it has to be longer in either majors and minors + * and at least equally long in both + * + * Furthermore the dominating train has at least the same multiples as the shorter + */ + + public int compareTo(NetworkTrain other) { + + // Check if A is the longer train first + boolean longerA = this.majors > other.majors && this.minors >= other.minors || this.majors == other.majors && this.minors > other.minors; + + if (longerA) { + // then check the multiples + if (this.multiplyMajors >= other.multiplyMajors && this.multiplyMinors >= other.multiplyMinors) { + return 1; + } else { + return 0; + } + } else { + // otherwise B might B longer + boolean longerB = this.majors < other.majors && this.minors <= other.minors || this.majors == other.majors && this.minors < other.minors; + if (longerB) { + // then check the multiples + if (this.multiplyMajors <= other.multiplyMajors && this.multiplyMinors <= other.multiplyMinors) { + return -1; + } else { + return 0; + } + } else { + // none is longer + return 0; + } + } + } + } diff --git a/rails/game/specific/_18TN/PublicCompany_18TN.java b/rails/game/specific/_18TN/PublicCompany_18TN.java index 738200c..53c550f 100644 --- a/rails/game/specific/_18TN/PublicCompany_18TN.java +++ b/rails/game/specific/_18TN/PublicCompany_18TN.java @@ -1,12 +1,18 @@ package rails.game.specific._18TN; +import java.util.Collections; +import java.util.List; + +import rails.algorithms.NetworkTrain; +import rails.algorithms.RevenueAdapter; +import rails.algorithms.RevenueStaticModifier; import rails.common.parser.ConfigurationException; import rails.game.GameManagerI; import rails.game.PublicCompany; import rails.game.model.ModelObject; import rails.game.state.BooleanState; -public class PublicCompany_18TN extends PublicCompany { +public class PublicCompany_18TN extends PublicCompany implements RevenueStaticModifier { private BooleanState civilWar; @@ -22,6 +28,8 @@ public class PublicCompany_18TN extends PublicCompany { super.finishConfiguration(gameManager); civilWar = new BooleanState (name+"_CivilWar", false); + + gameManager.getRevenueManager().addStaticModifier(this); } public boolean isCivilWar() { @@ -41,5 +49,23 @@ public class PublicCompany_18TN extends PublicCompany { stockMarket.withhold(this); } + /** + * Modify the revenue calculation for the civil war by removing the shortest train + */ + public void modifyCalculator(RevenueAdapter revenueAdapter) { + + // check if it is civil war, otherwise no effect + if (!isCivilWar()) return; + + List<NetworkTrain> trains = revenueAdapter.getTrains(); + if (trains.size() == 0) return; // no train, no effect + + // sort trains in ascending order (by domination which is equal to length for TN) + Collections.sort(trains); + + // and remove the first train (shortest) + trains.remove(0); + } + } |
From: Erik V. <ev...@us...> - 2011-08-09 20:54:08
|
data/18TN/CompanyManager.xml | 2 data/18TN/Game.xml | 1 rails/game/GameManager.java | 188 ++++++++++----------- rails/game/GameManagerI.java | 3 rails/game/OperatingRound.java | 8 rails/game/Phase.java | 94 ++++++---- rails/game/PublicCompany.java | 6 rails/game/PublicCompanyI.java | 3 rails/game/Round.java | 67 ++++--- rails/game/RoundI.java | 2 rails/game/specific/_18TN/OperatingRound_18TN.java | 69 +++++-- rails/game/specific/_18TN/PublicCompany_18TN.java | 45 +++++ 12 files changed, 298 insertions(+), 190 deletions(-) New commits: commit cee06b8d1fde54e05bc1f981894d841c1398e926 Author: Erik Vos <eri...@xs...> Date: Tue Aug 9 22:22:09 2011 +0200 Phase management step 4 and application to 18TN Civil War <Phase> can now have an <Action> child with (required) name and (optional) value attributes. Each action caused gameManager.processPhaseAction (name, value) to be called when that phase is activated. GameManager in turn calls processPhaseAction(name, value) in the current round. This new feature is used to implement 18TN Civil War (except the revenue calculation). Updated OperatingRound_18TN and created new PublicCompany_18TN. Added stub hasRoute() to PublicCompany (currently always returns true). diff --git a/data/18TN/CompanyManager.xml b/data/18TN/CompanyManager.xml index 8268cc4..282fe15 100644 --- a/data/18TN/CompanyManager.xml +++ b/data/18TN/CompanyManager.xml @@ -7,7 +7,7 @@ <Tradeable toCompany="yes" lowerPriceFactor="0.5" upperPriceFactor="2.0"/> <Tradeable toPlayer="yes"/> </CompanyType> - <CompanyType name="Public" class="rails.game.PublicCompany"> + <CompanyType name="Public" class="rails.game.specific._18TN.PublicCompany_18TN"> <CanBuyPrivates/> <PoolPaysOut/> <Float percentage="60"/> diff --git a/data/18TN/Game.xml b/data/18TN/Game.xml index 1cddd70..8e971cd 100644 --- a/data/18TN/Game.xml +++ b/data/18TN/Game.xml @@ -101,6 +101,7 @@ <OperatingRounds number="2"/> </Phase> <Phase name="3½"> + <Action name="CivilWar"/><!-- No value needed --> </Phase> <Phase name="4"> <Trains rusted="2" limitStep="2"/> diff --git a/rails/game/GameManager.java b/rails/game/GameManager.java index 4973f4b..eac056d 100644 --- a/rails/game/GameManager.java +++ b/rails/game/GameManager.java @@ -3,30 +3,22 @@ package rails.game; import java.io.*; import java.lang.reflect.Constructor; -import java.text.SimpleDateFormat; import java.util.*; import org.apache.log4j.Logger; import org.apache.log4j.NDC; import rails.algorithms.RevenueManager; -import rails.common.DisplayBuffer; -import rails.common.GuiDef; -import rails.common.GuiHints; -import rails.common.LocalText; -import rails.common.parser.Config; -import rails.common.parser.ConfigurableComponentI; -import rails.common.parser.ConfigurationException; -import rails.common.parser.GameOption; -import rails.common.parser.Tag; +import rails.common.*; +import rails.common.parser.*; import rails.game.action.*; import rails.game.correct.*; import rails.game.move.*; import rails.game.special.SpecialPropertyI; import rails.game.special.SpecialTokenLay; -import rails.game.specific._1856.CGRFormationRound; import rails.game.state.*; -import rails.util.*; +import rails.util.GameFileIO; +import rails.util.Util; /** * This class manages the playing rounds by supervising all implementations of @@ -46,7 +38,7 @@ public class GameManager implements ConfigurableComponentI, GameManagerI { protected Class<? extends OperatingRound> operatingRoundClass = OperatingRound.class; protected Class<? extends ShareSellingRound> shareSellingRoundClass - = ShareSellingRound.class; + = ShareSellingRound.class; // Variable UI Class names protected String gameUIManagerClassName = GuiDef.getDefaultClassName(GuiDef.ClassName.GAME_UI_MANAGER); @@ -68,7 +60,7 @@ public class GameManager implements ConfigurableComponentI, GameManagerI { // map of correctionManagers protected Map<CorrectionType, CorrectionManagerI> correctionManagers = new HashMap<CorrectionType, CorrectionManagerI>(); - + protected String gameName; protected Map<String, String> gameOptions; @@ -87,7 +79,7 @@ public class GameManager implements ConfigurableComponentI, GameManagerI { new HashMap<String, Portfolio> (); protected IntegerState playerCertificateLimit - = new IntegerState ("PlayerCertificateLimit", 0); + = new IntegerState ("PlayerCertificateLimit", 0); protected int currentNumberOfOperatingRounds = 1; protected boolean skipFirstStockRound = false; protected boolean showCompositeORNumber = true; @@ -103,7 +95,7 @@ public class GameManager implements ConfigurableComponentI, GameManagerI { protected boolean reloading = false; protected EnumMap<GameDef.Parm, Object> gameParameters - = new EnumMap<GameDef.Parm, Object>(GameDef.Parm.class); + = new EnumMap<GameDef.Parm, Object>(GameDef.Parm.class); /** * Current round should not be set here but from within the Round classes. @@ -228,7 +220,7 @@ public class GameManager implements ConfigurableComponentI, GameManagerI { // TODO: Move that to a better place protected Map<String, Object> objectStorage = new HashMap<String, Object>(); protected Map<String, Integer> storageIds = new HashMap<String, Integer>(); - + protected static Logger log = Logger.getLogger(GameManager.class.getPackage().getName()); @@ -276,11 +268,11 @@ public class GameManager implements ConfigurableComponentI, GameManagerI { optionParameters = null; optionNameParameters = optionTag.getAttributeAsString("parm"); - if (optionNameParameters != null) { - optionParameters = optionNameParameters.split(","); - } + if (optionNameParameters != null) { + optionParameters = optionNameParameters.split(","); + } optionName = GameOption.constructParametrisedName ( - optionName, optionParameters); + optionName, optionParameters); if (gameOptions.containsKey(optionName)) continue; @@ -365,20 +357,20 @@ public class GameManager implements ConfigurableComponentI, GameManagerI { Tag orderTag = orTag.getChild("OperatingOrder"); if (orderTag != null) { - dynamicOperatingOrder = orderTag.getAttributeAsBoolean("dynamic", - dynamicOperatingOrder); + dynamicOperatingOrder = orderTag.getAttributeAsBoolean("dynamic", + dynamicOperatingOrder); } - + Tag emergencyTag = orTag.getChild("EmergencyTrainBuying"); if (emergencyTag != null) { setGameParameter (GameDef.Parm.EMERGENCY_MUST_BUY_CHEAPEST_TRAIN, - emergencyTag.getAttributeAsBoolean("mustBuyCheapestTrain", + emergencyTag.getAttributeAsBoolean("mustBuyCheapestTrain", GameDef.Parm.EMERGENCY_MUST_BUY_CHEAPEST_TRAIN.defaultValueAsBoolean())); setGameParameter (GameDef.Parm.EMERGENCY_MAY_ALWAYS_BUY_NEW_TRAIN, - emergencyTag.getAttributeAsBoolean("mayAlwaysBuyNewTrain", + emergencyTag.getAttributeAsBoolean("mayAlwaysBuyNewTrain", GameDef.Parm.EMERGENCY_MAY_ALWAYS_BUY_NEW_TRAIN.defaultValueAsBoolean())); setGameParameter (GameDef.Parm.EMERGENCY_MAY_BUY_FROM_COMPANY, - emergencyTag.getAttributeAsBoolean("mayBuyFromCompany", + emergencyTag.getAttributeAsBoolean("mayBuyFromCompany", GameDef.Parm.EMERGENCY_MAY_BUY_FROM_COMPANY.defaultValueAsBoolean())); } } @@ -396,7 +388,7 @@ public class GameManager implements ConfigurableComponentI, GameManagerI { + ssrClassName, e); } } - + /* Max. % of shares of one company that a player may hold */ Tag shareLimitTag = gameParmTag.getChild("PlayerShareLimit"); if (shareLimitTag != null) { @@ -765,7 +757,7 @@ public class GameManager implements ConfigurableComponentI, GameManagerI { return String.valueOf(absoluteORNumber.intValue()); } } - + public int getAbsoluteORNumber () { return absoluteORNumber.intValue(); } @@ -802,8 +794,8 @@ public class GameManager implements ConfigurableComponentI, GameManagerI { // check if other companies can be dumped createRound (shareSellingRoundClass, interruptedRound) - .start(player, cashToRaise, cashNeedingCompany, - !problemDumpOtherCompanies || forcedSellingCompanyDump); + .start(player, cashToRaise, cashNeedingCompany, + !problemDumpOtherCompanies || forcedSellingCompanyDump); // the last parameter indicates if the dump of other companies is allowed, either this is explicit or // the action does not require that check } @@ -1009,8 +1001,8 @@ public class GameManager implements ConfigurableComponentI, GameManagerI { //&& currentRound.get().getClass() != CGRFormationRound.class && possibleActions.contains(RepayLoans.class) && (!possibleActions.contains(action.getClass()) - || (action.getClass() == NullAction.class - && ((NullAction)action).getMode() != NullAction.DONE))) { + || (action.getClass() == NullAction.class + && ((NullAction)action).getMode() != NullAction.DONE))) { // Insert "Done" log.debug("Action DONE inserted"); getCurrentRound().process(new NullAction (NullAction.DONE)); @@ -1025,13 +1017,13 @@ public class GameManager implements ConfigurableComponentI, GameManagerI { // FOR BACKWARDS COMPATIBILITY boolean doProcess = true; if (skipNextDone) { - if (action instanceof NullAction - && ((NullAction)action).getMode() == NullAction.DONE) { - if (currentRound.get() instanceof OperatingRound - && ((OperatingRound)currentRound.get()).getStep() == skippedStep) { - doProcess = false; - } - } + if (action instanceof NullAction + && ((NullAction)action).getMode() == NullAction.DONE) { + if (currentRound.get() instanceof OperatingRound + && ((OperatingRound)currentRound.get()).getStep() == skippedStep) { + doProcess = false; + } + } } skipNextDone = false; skippedStep = null; @@ -1141,17 +1133,17 @@ public class GameManager implements ConfigurableComponentI, GameManagerI { return gameSaver.saveGame(file, displayErrorMessage, errorMessageKey); } /** - * tries to reload the current game + * tries to reload the current game * executes the additional action(s) - */ + */ protected boolean reload(GameAction reloadAction) { log.info("Reloading started"); - + /* Use gameLoader to load the game data */ GameFileIO gameLoader = new GameFileIO(); String filepath = reloadAction.getFilepath(); gameLoader.loadGameData(filepath); - + /* followed by actions and comments */ try{ gameLoader.loadActionsAndComments(); @@ -1161,19 +1153,19 @@ public class GameManager implements ConfigurableComponentI, GameManagerI { } log.debug("Starting to compare loaded actions"); - + /* gameLoader actions get compared to the executed actions of the current game */ List<PossibleAction> savedActions = gameLoader.getActions(); - + setReloading(true); - + // Check size if (savedActions.size() < executedActions.size()) { DisplayBuffer.add(LocalText.getText("LoadFailed", - "loaded file has less actions than current game")); + "loaded file has less actions than current game")); return true; } - + // Check action identity int index = 0; PossibleAction executedAction; @@ -1201,14 +1193,14 @@ public class GameManager implements ConfigurableComponentI, GameManagerI { } } index++; - } + } } catch (Exception e) { log.error("Reload failed", e); DisplayBuffer.add(LocalText.getText("LoadFailed", e.getMessage())); return true; } - - + + setReloading(false); finishLoading(); @@ -1320,7 +1312,7 @@ public class GameManager implements ConfigurableComponentI, GameManagerI { msgContinue = LocalText.getText("gameOverPlaySetOfORs"); else msgContinue = LocalText.getText("gameOverPlayOnlyOR"); - String msg = LocalText.getText("MaxedSharePriceDisplayText", + String msg = LocalText.getText("MaxedSharePriceDisplayText", company.getName(), Bank.format(space.getPrice()), msgContinue); @@ -1349,10 +1341,10 @@ public class GameManager implements ConfigurableComponentI, GameManagerI { public boolean isDynamicOperatingOrder() { - return dynamicOperatingOrder; - } + return dynamicOperatingOrder; + } - /* (non-Javadoc) + /* (non-Javadoc) * @see rails.game.GameManagerI#isGameOver() */ public boolean isGameOver() { @@ -1666,7 +1658,7 @@ public class GameManager implements ConfigurableComponentI, GameManagerI { return false; } } - + public void setGuiParameter (GuiDef.Parm key, boolean value) { guiParameters.put (key, value); } @@ -1848,43 +1840,43 @@ public class GameManager implements ConfigurableComponentI, GameManagerI { return new ArrayList<PublicCompanyI>(operatingCompanies.values()); } - public boolean isReloading() { - return reloading; - } - - public void setReloading(boolean reloading) { - this.reloading = reloading; - } - - public void setSkipDone (GameDef.OrStep step) { - skipNextDone = true; - skippedStep = step; - } - - /** - * - *@param ascending Boolean to determine if the playerlist will be sorted in ascending or descending order based on their cash - *@return Returns the player at index position 0 that is either the player with the most or least cash depending on sort order. - */ - public Player reorderPlayersByCash (boolean ascending) { - - final boolean _ascending = ascending; - Collections.sort (players, new Comparator<Player>() { - public int compare (Player p1, Player p2) { - return _ascending ? p1.getCash() - p2.getCash() : p2.getCash() - p1.getCash(); - } - }); - - Player player; - for (int i=0; i<players.size(); i++) { - player = players.get(i); - player.setIndex (i); - playerNames.set (i, player.getName()); - log.debug("New player "+i+" is "+player.getName() +" (cash="+Bank.format(player.getCash())+")"); - } - - return players.get(0); - } + public boolean isReloading() { + return reloading; + } + + public void setReloading(boolean reloading) { + this.reloading = reloading; + } + + public void setSkipDone (GameDef.OrStep step) { + skipNextDone = true; + skippedStep = step; + } + + /** + * + *@param ascending Boolean to determine if the playerlist will be sorted in ascending or descending order based on their cash + *@return Returns the player at index position 0 that is either the player with the most or least cash depending on sort order. + */ + public Player reorderPlayersByCash (boolean ascending) { + + final boolean _ascending = ascending; + Collections.sort (players, new Comparator<Player>() { + public int compare (Player p1, Player p2) { + return _ascending ? p1.getCash() - p2.getCash() : p2.getCash() - p1.getCash(); + } + }); + + Player player; + for (int i=0; i<players.size(); i++) { + player = players.get(i); + player.setIndex (i); + playerNames.set (i, player.getName()); + log.debug("New player "+i+" is "+player.getName() +" (cash="+Bank.format(player.getCash())+")"); + } + + return players.get(0); + } public void resetStorage() { objectStorage = new HashMap<String, Object>(); @@ -1898,10 +1890,14 @@ public class GameManager implements ConfigurableComponentI, GameManagerI { storageIds.put(typeName, id + 1); // store next id return id; } - + public Object retrieveObject(String typeName, int id) { return objectStorage.get(typeName + id); } - + + /** Process an action triggered by a phase change. */ + public void processPhaseAction (String name, String value) { + getCurrentRound().processPhaseAction(name, value); + } } diff --git a/rails/game/GameManagerI.java b/rails/game/GameManagerI.java index e9d5936..01253a0 100644 --- a/rails/game/GameManagerI.java +++ b/rails/game/GameManagerI.java @@ -241,7 +241,8 @@ public interface GameManagerI extends MoveableHolder, ConfigurableComponentI { */ public Object retrieveObject(String typeName, int id); - + /** Process an action triggered by a phase change. */ + public void processPhaseAction (String name, String value); } \ No newline at end of file diff --git a/rails/game/OperatingRound.java b/rails/game/OperatingRound.java index 59c1058..957203e 100644 --- a/rails/game/OperatingRound.java +++ b/rails/game/OperatingRound.java @@ -914,14 +914,6 @@ public class OperatingRound extends Round implements Observer { operatingCompany.get().setLastRevenue(amount); operatingCompany.get().setLastRevenueAllocation(revenueAllocation); - /* Seems people don't like this popup... - if (amount == 0 && operatingCompany.get().getNumberOfTrains() == 0) { - DisplayBuffer.add(LocalText.getText("RevenueWithNoTrains", - operatingCompany.get().getName(), - Bank.format(0) )); - } - */ - // Pay any debts from treasury, revenue and/or president's cash // The remaining dividend may be less that the original income amount = executeDeductions (action); diff --git a/rails/game/Phase.java b/rails/game/Phase.java index 448bb51..e509507 100644 --- a/rails/game/Phase.java +++ b/rails/game/Phase.java @@ -8,13 +8,14 @@ import org.apache.log4j.Logger; import rails.common.LocalText; import rails.common.parser.ConfigurationException; import rails.common.parser.Tag; +import rails.util.Util; public class Phase implements PhaseI { protected int index; protected String name; - + protected String realName; protected String colourList = ""; @@ -28,11 +29,11 @@ public class Phase implements PhaseI { protected int numberOfOperatingRounds = 1; protected int offBoardRevenueStep = 1; - + /** New style train limit configuration. */ protected int trainLimitStep = 1; - + protected int privatesRevenueStep = 1; // sfy 1889 protected boolean trainTradingAllowed = false; @@ -51,27 +52,34 @@ public class Phase implements PhaseI { /** Items to close if a phase gets activated */ protected List<Closeable> closedObjects = null; - + /** Train types to rust or obsolete if a phase gets activated */ protected List<TrainCertificateType> rustedTrains; String rustedTrainNames; - + /** Train types to release (make available for buying) if a phase gets activated */ protected List<TrainCertificateType> releasedTrains; String releasedTrainNames; - - private TrainManager trainManager; + + /** Actions for this phase. + * When this phase is activated, the GameManager method phaseAction() will be called, + * which in turn will call the current Round, which is responsible to handle the action. + * <p> + * Set actions have a name and may have a value. */ + protected Map<String, String> actions; + + private GameManagerI gameManager; private Portfolio lastTrainBuyer; protected String extraInfo = ""; - + /** A HashMap to contain phase-dependent parameters * by name and value. */ protected Map<String, String> parameters = null; protected static Logger log = - Logger.getLogger(Phase.class.getPackage().getName()); + Logger.getLogger(Phase.class.getPackage().getName()); public Phase(int index, String name, Phase previousPhase) { this.index = index; @@ -98,7 +106,7 @@ public class Phase implements PhaseI { } } } - + // Real name (as in the printed game) realName = tag.getAttributeAsString("realName", null); @@ -120,8 +128,8 @@ public class Phase implements PhaseI { Tag privatesTag = tag.getChild("Privates"); if (privatesTag != null) { privateSellingAllowed = - privatesTag.getAttributeAsBoolean("sellingAllowed", - privateSellingAllowed); + privatesTag.getAttributeAsBoolean("sellingAllowed", + privateSellingAllowed); privatesClose = privatesTag.getAttributeAsBoolean("close", false); privatesRevenueStep = privatesTag.getAttributeAsInteger("revenueStep", privatesRevenueStep); // sfy 1889 } @@ -130,32 +138,32 @@ public class Phase implements PhaseI { Tag orTag = tag.getChild("OperatingRounds"); if (orTag != null) { numberOfOperatingRounds = - orTag.getAttributeAsInteger("number", - numberOfOperatingRounds); + orTag.getAttributeAsInteger("number", + numberOfOperatingRounds); } // Off-board revenue steps (starts at 1) Tag offBoardTag = tag.getChild("OffBoardRevenue"); if (offBoardTag != null) { offBoardRevenueStep = - offBoardTag.getAttributeAsInteger("step", - offBoardRevenueStep); + offBoardTag.getAttributeAsInteger("step", + offBoardRevenueStep); } - + Tag trainsTag = tag.getChild("Trains"); if (trainsTag != null) { trainLimitStep = trainsTag.getAttributeAsInteger("limitStep", trainLimitStep); rustedTrainNames = trainsTag.getAttributeAsString("rusted", null); releasedTrainNames = trainsTag.getAttributeAsString("released", null); trainTradingAllowed = - trainsTag.getAttributeAsBoolean("tradingAllowed", - trainTradingAllowed); + trainsTag.getAttributeAsBoolean("tradingAllowed", + trainTradingAllowed); oneTrainPerTurn = - trainsTag.getAttributeAsBoolean("onePerTurn", - oneTrainPerTurn); + trainsTag.getAttributeAsBoolean("onePerTurn", + oneTrainPerTurn); oneTrainPerTypePerTurn = - trainsTag.getAttributeAsBoolean("onePerTypePerTurn", - oneTrainPerTypePerTurn); + trainsTag.getAttributeAsBoolean("onePerTypePerTurn", + oneTrainPerTypePerTurn); } Tag loansTag = tag.getChild("Loans"); @@ -173,6 +181,17 @@ public class Phase implements PhaseI { } } + Tag setTag = tag.getChild("Action"); + if (setTag != null) { + if (actions == null) actions = new HashMap<String, String>(); + String key = setTag.getAttributeAsString("name"); + if (!Util.hasValue(key)) { + throw new ConfigurationException ("Phase "+name+": <Set> without action name"); + } + String value = setTag.getAttributeAsString("value", null); + actions.put (key, value); + } + // Extra info text(usually related to extra-share special properties) Tag infoTag = tag.getChild("Info"); if (infoTag != null) { @@ -185,16 +204,17 @@ public class Phase implements PhaseI { public void finishConfiguration (GameManagerI gameManager) throws ConfigurationException { - - trainManager = gameManager.getTrainManager(); + + this.gameManager = gameManager; + TrainManager trainManager = gameManager.getTrainManager(); TrainCertificateType type; - + if (rustedTrainNames != null) { rustedTrains = new ArrayList<TrainCertificateType>(2); for (String typeName : rustedTrainNames.split(",")) { type = trainManager.getCertTypeByName(typeName); if (type == null) { - throw new ConfigurationException (" Unknown rusted train type '"+typeName+"' for phase '"+name+"'"); + throw new ConfigurationException (" Unknown rusted train type '"+typeName+"' for phase '"+name+"'"); } rustedTrains.add(type); type.setPermanent(false); @@ -206,7 +226,7 @@ public class Phase implements PhaseI { for (String typeName : releasedTrainNames.split(",")) { type = trainManager.getCertTypeByName(typeName); if (type == null) { - throw new ConfigurationException (" Unknown released train type '"+typeName+"' for phase '"+name+"'"); + throw new ConfigurationException (" Unknown released train type '"+typeName+"' for phase '"+name+"'"); } releasedTrains.add(type); } @@ -222,20 +242,28 @@ public class Phase implements PhaseI { object.close(); } } - + + TrainManager trainManager = gameManager.getTrainManager(); + if (rustedTrains != null && !rustedTrains.isEmpty()) { for (TrainCertificateType type : rustedTrains) { - trainManager.rustTrainType(type, lastTrainBuyer); + trainManager.rustTrainType(type, lastTrainBuyer); } } - + if (releasedTrains != null && !releasedTrains.isEmpty()) { for (TrainCertificateType type : releasedTrains) { trainManager.makeTrainAvailable(type); } } + + if (actions != null && !actions.isEmpty()) { + for (String actionName : actions.keySet()) { + gameManager.processPhaseAction (actionName, actions.get(actionName)); + } + } } - + public void setLastTrainBuyer(Portfolio lastTrainBuyer) { this.lastTrainBuyer = lastTrainBuyer; } @@ -259,7 +287,7 @@ public class Phase implements PhaseI { public int getTrainLimitStep() { return trainLimitStep; } - + public int getTrainLimitIndex() { return trainLimitStep - 1; } diff --git a/rails/game/PublicCompany.java b/rails/game/PublicCompany.java index 2a9cad6..7c1a3ca 100644 --- a/rails/game/PublicCompany.java +++ b/rails/game/PublicCompany.java @@ -2068,4 +2068,10 @@ public class PublicCompany extends Company implements PublicCompanyI { return ""; } + /** Does the company has a route? + * Currently this is a stub that always returns true. + */ + public boolean hasRoute() { + return true; + } } diff --git a/rails/game/PublicCompanyI.java b/rails/game/PublicCompanyI.java index 63ad78b..71fbd1f 100644 --- a/rails/game/PublicCompanyI.java +++ b/rails/game/PublicCompanyI.java @@ -352,4 +352,7 @@ public interface PublicCompanyI extends CompanyI, CashHolder, TokenHolder { public ModelObject getInGameModel (); public ModelObject getIsClosedModel (); + /** Does the company has a route? */ + public boolean hasRoute(); + } diff --git a/rails/game/Round.java b/rails/game/Round.java index 2358579..9789cef 100644 --- a/rails/game/Round.java +++ b/rails/game/Round.java @@ -9,9 +9,7 @@ import java.util.*; import org.apache.log4j.Logger; -import rails.common.DisplayBuffer; -import rails.common.GuiHints; -import rails.common.LocalText; +import rails.common.*; import rails.game.action.*; import rails.game.move.*; import rails.game.special.SpecialPropertyI; @@ -26,7 +24,7 @@ public abstract class Round implements RoundI { protected GuiHints guiHints = null; protected static Logger log = - Logger.getLogger(Round.class.getPackage().getName()); + Logger.getLogger(Round.class.getPackage().getName()); protected GameManagerI gameManager = null; protected CompanyManagerI companyManager = null; @@ -144,7 +142,7 @@ public abstract class Round implements RoundI { public String getGameOption (String name) { return gameManager.getGameOption(name); } - /* + /* * (non-Javadoc) * * @see rails.game.RoundI#getHelp() @@ -268,13 +266,13 @@ public abstract class Round implements RoundI { PublicCompanyI lastOperatingCompany) { Map<Integer, PublicCompanyI> operatingCompanies = - new TreeMap<Integer, PublicCompanyI>(); + new TreeMap<Integer, PublicCompanyI>(); List<PublicCompanyI> newOperatingCompanies; StockSpaceI space; int key; int minorNo = 0; boolean reorder = gameManager.isDynamicOperatingOrder() - && oldOperatingCompanies != null && lastOperatingCompany != null; + && oldOperatingCompanies != null && lastOperatingCompany != null; int lastOperatingCompanyIndex; if (reorder) { @@ -297,9 +295,9 @@ public abstract class Round implements RoundI { // is ascending. space = company.getCurrentSpace(); key = 1000000 * (999 - space.getPrice()) - + 10000 * (99 - space.getColumn()) - + 100 * (space.getRow()+1) - + space.getStackPosition(company); + + 10000 * (99 - space.getColumn()) + + 100 * (space.getRow()+1) + + space.getStackPosition(company); } else { key = 50 + ++minorNo; } @@ -333,21 +331,21 @@ public abstract class Round implements RoundI { /** Determine sold percentage for floating purposes */ protected int getSoldPercentage (PublicCompanyI company) { - int soldPercentage = 0; - for (PublicCertificateI cert : company.getCertificates()) { - if (certCountsAsSold(cert)) { - soldPercentage += cert.getShare(); - } - } - return soldPercentage; + int soldPercentage = 0; + for (PublicCertificateI cert : company.getCertificates()) { + if (certCountsAsSold(cert)) { + soldPercentage += cert.getShare(); + } + } + return soldPercentage; } /** Can be subclassed for games with special rules */ protected boolean certCountsAsSold (PublicCertificateI cert) { - Portfolio holder = cert.getPortfolio(); - CashHolder owner = holder.getOwner(); - return owner instanceof Player - || holder == pool; + Portfolio holder = cert.getPortfolio(); + CashHolder owner = holder.getOwner(); + return owner instanceof Player + || holder == pool; } /** @@ -391,15 +389,15 @@ public abstract class Round implements RoundI { if (cash > 0) { new CashMove(bank, company, cash); ReportBuffer.add(LocalText.getText("FloatsWithCash", - company.getName(), - Bank.format(cash) )); + company.getName(), + Bank.format(cash) )); } else { ReportBuffer.add(LocalText.getText("Floats", company.getName())); } if (capitalisationMode == PublicCompanyI.CAPITALISE_INCREMENTAL - && company.canHoldOwnShares()) { + && company.canHoldOwnShares()) { List<Certificate> moving = new ArrayList<Certificate>(); for (Certificate ipoCert : ipo.getCertificatesPerCompany( company.getName())) { @@ -413,7 +411,7 @@ public abstract class Round implements RoundI { protected void finishRound() { // Report financials - ReportBuffer.add(""); + ReportBuffer.add(""); for (PublicCompanyI c : companyManager.getAllPublicCompanies()) { if (c.hasFloated() && !c.isClosed()) { ReportBuffer.add(LocalText.getText("Has", c.getName(), @@ -452,13 +450,13 @@ public abstract class Round implements RoundI { // Note: all transferred shares must come from the same old shareholder. protected void transferCertificates(List<? extends Certificate> certs, - Portfolio newHolder) { + Portfolio newHolder) { - for (Certificate cert : certs) { - if (cert != null) { - cert.moveTo(newHolder); - } - } + for (Certificate cert : certs) { + if (cert != null) { + cert.moveTo(newHolder); + } + } } protected void pay (CashHolder from, CashHolder to, int amount) { @@ -540,5 +538,12 @@ public abstract class Round implements RoundI { return autopasses; } + /** A stub for processing actions triggered by a phase change. + * Must be overridden by subclasses that need to process such actions. + * @param name (required) The name of the action to be executed + * @param value (optional) The value of the action to be executed, if applicable + */ + public void processPhaseAction (String name, String value) { + } } diff --git a/rails/game/RoundI.java b/rails/game/RoundI.java index 95fa769..0fdfb07 100644 --- a/rails/game/RoundI.java +++ b/rails/game/RoundI.java @@ -30,5 +30,5 @@ public interface RoundI { public String getRoundName(); - + public void processPhaseAction (String name, String value); } diff --git a/rails/game/specific/_18TN/OperatingRound_18TN.java b/rails/game/specific/_18TN/OperatingRound_18TN.java index f0c682e..f5a3b55 100644 --- a/rails/game/specific/_18TN/OperatingRound_18TN.java +++ b/rails/game/specific/_18TN/OperatingRound_18TN.java @@ -1,26 +1,29 @@ package rails.game.specific._18TN; -import java.util.*; +import java.util.List; import rails.game.*; import rails.game.action.BuyPrivate; +import rails.game.action.SetDividend; import rails.game.state.ArrayListState; public class OperatingRound_18TN extends OperatingRound { - + private ArrayListState<Player> playersSoldInOR1; - + public OperatingRound_18TN (GameManagerI gameManager) { super (gameManager); } + @Override protected boolean isPrivateSellingAllowed() { - return super.isPrivateSellingAllowed() - // 18TN special - || gameManager.getAbsoluteORNumber() == 1 - && !ownsPrivate(operatingCompany.get()); + return super.isPrivateSellingAllowed() + // 18TN special + || gameManager.getAbsoluteORNumber() == 1 + && !ownsPrivate(operatingCompany.get()); } - + + @Override protected int getPrivateMinimumPrice (PrivateCompanyI privComp) { if (gameManager.getAbsoluteORNumber() == 1 && !getCurrentPhase().isPrivateSellingAllowed()) { @@ -30,7 +33,8 @@ public class OperatingRound_18TN extends OperatingRound { return super.getPrivateMinimumPrice(privComp); } } - + + @Override protected int getPrivateMaximumPrice (PrivateCompanyI privComp) { if (gameManager.getAbsoluteORNumber() == 1 && !getCurrentPhase().isPrivateSellingAllowed()) { @@ -40,38 +44,65 @@ public class OperatingRound_18TN extends OperatingRound { return super.getPrivateMaximumPrice(privComp); } } - + private boolean ownsPrivate (PublicCompanyI company) { List<PrivateCompanyI> privates = company.getPortfolio().getPrivateCompanies(); return privates != null && !privates.isEmpty(); } - + + @Override protected boolean maySellPrivate (Player player) { - return gameManager.getAbsoluteORNumber() != 1 - || !hasPlayerSoldInOR1(player); + return gameManager.getAbsoluteORNumber() != 1 + || !hasPlayerSoldInOR1(player); } - + private boolean hasPlayerSoldInOR1 (Player player) { return playersSoldInOR1 != null && playersSoldInOR1.contains(player); } + @Override public boolean buyPrivate(BuyPrivate action) { - + Player sellingPlayer = null; - + if (gameManager.getAbsoluteORNumber() == 1) { sellingPlayer = (Player)((Portfolio)action.getPrivateCompany().getHolder()).getOwner(); } - + boolean result = super.buyPrivate(action); - + if (result && gameManager.getAbsoluteORNumber() == 1) { if (playersSoldInOR1 == null) playersSoldInOR1 = new ArrayListState<Player>("PlayersSoldPrivateInOR1"); if (!playersSoldInOR1.contains(sellingPlayer)) { playersSoldInOR1.add(sellingPlayer); } } - + return result; } + + @Override + public void processPhaseAction (String name, String value) { + if (name.equalsIgnoreCase("CivilWar")) { + for (PublicCompanyI company : getOperatingCompanies()) { + if (company.hasFloated() && company.getPortfolio().getNumberOfTrains() > 0 + && company.hasRoute()) { + ((PublicCompany_18TN)company).setCivilWar(true); + } + } + } + } + + + @Override + protected void executeSetRevenueAndDividend (SetDividend action) { + + // Save operating company (it may change) + PublicCompany_18TN company = (PublicCompany_18TN) operatingCompany.get(); + + super.executeSetRevenueAndDividend(action); + + // Reset Civil War condition + if (company.isCivilWar()) company.setCivilWar(false); + } } diff --git a/rails/game/specific/_18TN/PublicCompany_18TN.java b/rails/game/specific/_18TN/PublicCompany_18TN.java new file mode 100644 index 0000000..738200c --- /dev/null +++ b/rails/game/specific/_18TN/PublicCompany_18TN.java @@ -0,0 +1,45 @@ +package rails.game.specific._18TN; + +import rails.common.parser.ConfigurationException; +import rails.game.GameManagerI; +import rails.game.PublicCompany; +import rails.game.model.ModelObject; +import rails.game.state.BooleanState; + +public class PublicCompany_18TN extends PublicCompany { + + private BooleanState civilWar; + + + public ModelObject getCivilWar() { + return civilWar; + } + + @Override + public void finishConfiguration(GameManagerI gameManager) + throws ConfigurationException { + + super.finishConfiguration(gameManager); + + civilWar = new BooleanState (name+"_CivilWar", false); + } + + public boolean isCivilWar() { + return civilWar.booleanValue(); + } + + public void setCivilWar(boolean value) { + civilWar.set(value); + } + + /** Don't move the space if the company has one train in the civil war + * (the revenue amount must then be zero) + */ + @Override + public void withhold(int amount) { + if (isCivilWar() && portfolio.getNumberOfTrains() == 1) return; + stockMarket.withhold(this); + } + + +} |
From: Stefan F. <ste...@us...> - 2011-08-08 17:52:04
|
.classpath | 32 ++++++++++++++++---------------- dev/null |binary lib/junit-4.8.2/junit.jar |binary 3 files changed, 16 insertions(+), 16 deletions(-) New commits: commit 8a7aeeddea0396d6bfacb2a77399ad7b93b4a8b5 Author: Stefan Frey <ste...@we...> Date: Mon Aug 8 17:03:20 2011 +0200 Updated junit.jar to 4.8.2 diff --git a/.classpath b/.classpath index ff7466a..25b28ed 100644 --- a/.classpath +++ b/.classpath @@ -1,16 +1,16 @@ -<?xml version="1.0" encoding="UTF-8"?> -<classpath> - <classpathentry excluding="lib/batik-1.7/|lib/jgraph5/|lib/jgrapht-0.7.3/|lib/junit_3.8.2/|lib/log4j-1.2/|lib/batik-1.7/lib/|lib/jgraph5/|lib/jgrapht-0.7.3/|lib/junit_3.8.2/|lib/log4j-1.2/|lib/batik-1.7/|lib/batik-1.7/lib/" kind="src" path=""/> - <classpathentry exported="true" kind="con" path="org.eclipse.jdt.launching.JRE_CONTAINER"/> - <classpathentry exported="true" kind="lib" path="lib/log4j-1.2/log4j-1.2.14.jar"/> - <classpathentry exported="true" kind="lib" path="lib/jgrapht-0.7.3/jgrapht-jdk1.5.jar"/> - <classpathentry exported="true" kind="lib" path="lib/junit_3.8.2/junit.jar"/> - <classpathentry exported="true" kind="lib" path="lib/jgraph5/jgraph.jar"/> - <classpathentry exported="true" kind="lib" path="lib/batik-1.7/batik.jar"/> - <classpathentry exported="true" kind="lib" path="lib/batik-1.7/lib/batik-bridge.jar"/> - <classpathentry exported="true" kind="lib" path="lib/batik-1.7/lib/batik-dom.jar"/> - <classpathentry exported="true" kind="lib" path="lib/batik-1.7/lib/batik-ext.jar"/> - <classpathentry exported="true" kind="lib" path="lib/batik-1.7/lib/batik-gvt.jar"/> - <classpathentry exported="true" kind="lib" path="lib/batik-1.7/lib/batik-util.jar"/> - <classpathentry kind="output" path="classes"/> -</classpath> +<?xml version="1.0" encoding="UTF-8"?> +<classpath> + <classpathentry excluding="lib/batik-1.7/|lib/batik-1.7/|lib/batik-1.7/lib/|lib/batik-1.7/lib/|lib/jgraph5/|lib/jgraph5/|lib/jgrapht-0.7.3/|lib/jgrapht-0.7.3/|lib/junit-4.8.2|lib/log4j-1.2/|lib/log4j-1.2/" kind="src" path=""/> + <classpathentry exported="true" kind="con" path="org.eclipse.jdt.launching.JRE_CONTAINER"/> + <classpathentry exported="true" kind="lib" path="lib/log4j-1.2/log4j-1.2.14.jar"/> + <classpathentry exported="true" kind="lib" path="lib/jgrapht-0.7.3/jgrapht-jdk1.5.jar"/> + <classpathentry exported="true" kind="lib" path="lib/jgraph5/jgraph.jar"/> + <classpathentry exported="true" kind="lib" path="lib/batik-1.7/batik.jar"/> + <classpathentry exported="true" kind="lib" path="lib/batik-1.7/lib/batik-bridge.jar"/> + <classpathentry exported="true" kind="lib" path="lib/batik-1.7/lib/batik-dom.jar"/> + <classpathentry exported="true" kind="lib" path="lib/batik-1.7/lib/batik-ext.jar"/> + <classpathentry exported="true" kind="lib" path="lib/batik-1.7/lib/batik-gvt.jar"/> + <classpathentry exported="true" kind="lib" path="lib/batik-1.7/lib/batik-util.jar"/> + <classpathentry kind="lib" path="lib/junit-4.8.2/junit.jar"/> + <classpathentry kind="output" path="classes"/> +</classpath> diff --git a/lib/junit-4.8.2/junit.jar b/lib/junit-4.8.2/junit.jar new file mode 100644 index 0000000..5b4bb84 Binary files /dev/null and b/lib/junit-4.8.2/junit.jar differ diff --git a/lib/junit_3.8.2/junit.jar b/lib/junit_3.8.2/junit.jar deleted file mode 100644 index 4f2fef2..0000000 Binary files a/lib/junit_3.8.2/junit.jar and /dev/null differ |
From: Stefan F. <ste...@us...> - 2011-08-06 05:51:48
|
data/profiles/test.profile | 1 + rails/test/GameTest.java | 23 ----------------------- test/TestGame.java | 17 +++++++++++++++-- test/TestGameBuilder.java | 37 +++++++++++++++++++++++-------------- 4 files changed, 39 insertions(+), 39 deletions(-) New commits: commit a3aed45bb43b36c663be37682bb9c234a8a16a83 Author: Stefan Frey <ste...@we...> Date: Fri Aug 5 17:00:08 2011 +0200 TestGame creates a failed report diff --git a/data/profiles/test.profile b/data/profiles/test.profile index 10dd67c..06be5fc 100644 --- a/data/profiles/test.profile +++ b/data/profiles/test.profile @@ -63,6 +63,7 @@ save.filename.extension=rails # The date/time pattern must be as defined in the Java SimpleDateFormat class. #report.filename.date_time_pattern=yyyyMMdd report.filename.extension=report +failed.filename.extension=failed ### Windows ## Report window visibility diff --git a/test/TestGame.java b/test/TestGame.java index 0769927..3556073 100644 --- a/test/TestGame.java +++ b/test/TestGame.java @@ -23,6 +23,8 @@ public class TestGame extends TestCase { private List<String> testReport = null; private List<String> expectedReport = null; + private boolean passed = false; + protected static Logger log = Logger.getLogger(TestGame.class.getPackage().getName()); @@ -66,6 +68,7 @@ public class TestGame extends TestCase { expectedReport.get(line), testReport.get(line)); line = line + 1; } + passed = true; } protected void setUp() throws Exception { @@ -105,11 +108,21 @@ public class TestGame extends TestCase { } protected void tearDown() throws Exception { + // test has failed, so save the test Report + String reportFilename = gamePath + File.separator + gameName + "." + Config.get("failed.filename.extension"); + if (!passed) { + TestGameBuilder.saveGameReport(testReport, reportFilename, true); + } else { // otherwise check if the test Report exists and delete it + File f = new File(reportFilename); + if (f.exists()) { + if (f.delete()) { + System.out.println("Deleted failed report at " + reportFilename); + } + } + } super.tearDown(); testReport.clear(); expectedReport.clear(); - - } } diff --git a/test/TestGameBuilder.java b/test/TestGameBuilder.java index bdbc978..7702ffb 100644 --- a/test/TestGameBuilder.java +++ b/test/TestGameBuilder.java @@ -30,6 +30,28 @@ public final class TestGameBuilder extends TestCase { // true = optimal for ant html reports, false = optimal for test runner private static boolean extendedTestNames = true; + static void saveGameReport(List<String> report, String reportFilename, boolean failed) { + PrintWriter reportFile = null; + try{ + reportFile = new PrintWriter(reportFilename); + } catch (IOException e) + { + System.err.print("Error: cannot open file " + reportFilename + " for report writing"); + } + if (reportFile != null) { + for (String msg:report){ + reportFile.println(msg); + } + reportFile.close(); + if (failed) { + System.out.println("Created failed report at " + reportFilename); + } else { + System.out.println("Created base line report file at " + reportFilename); + } + } + } + + private static void prepareGameReport(File gameFile, String reportFilename) { Game game = null; @@ -39,21 +61,8 @@ public final class TestGameBuilder extends TestCase { if (game != null) { List<String> report = ReportBuffer.getAsList(); + saveGameReport(report, reportFilename, false); NDC.clear(); // remove reference to GameManager - PrintWriter reportFile = null; - try{ - reportFile = new PrintWriter(reportFilename); - } catch (IOException e) - { - System.err.print("Cannot open file " + reportFilename + " to save game report"); - } - if (reportFile != null) { - for (String msg:report){ - reportFile.println(msg); - } - reportFile.close(); - System.out.println("Created reportfile at " + reportFilename); - } } } commit 42d85295292965303c14926c41d83cdb375c1c83 Author: Stefan Frey <ste...@we...> Date: Fri Aug 5 16:19:45 2011 +0200 Removed GameTest diff --git a/rails/test/GameTest.java b/rails/test/GameTest.java deleted file mode 100644 index 4bab9a6..0000000 --- a/rails/test/GameTest.java +++ /dev/null @@ -1,23 +0,0 @@ -package rails.test; - -import rails.common.parser.Config; -import rails.ui.swing.GameSetupWindow; - -public class GameTest { - - public static void main(String[] args) { - - // intialize configuration - Config.setConfigSelection(); - - int nargs = 0; - if (args != null && args.length > 0) { - for (String arg : args) { - System.out.println ("Arg "+(++nargs)+": "+arg); - } - } - - /* Start the rails.game selector, which will do all the rest. */ - new GameSetupWindow(); - } -} |
From: Stefan F. <ste...@us...> - 2011-08-04 05:43:02
|
dev/null |binary test/TestGame.java | 5 test/TestGameBuilder.java | 3 test/data/real/1856_A.report | 1 test/data/real/1889_A.report | 1 test/data/real/1889_B.rails |binary test/data/real/1889_B.report | 1262 +++++++++++++++++++++++++++++ test/data/real/1889_C.report | 1 test/data/real/18AL_A.report | 1 test/data/real/18EU_A.report | 1 test/data/test/1835_PR_3rdTrain.report | 1 test/data/test/1851_Late.report | 1 test/data/test/1856_2nd6T+PrezCash2.report | 1 test/data/test/18EU_After2nd8Train.report | 1 14 files changed, 1278 insertions(+), 1 deletion(-) New commits: commit 7e4acf029e0f45362bc79c5d9cb80cfd793e9725 Author: Stefan Frey <ste...@we...> Date: Thu Aug 4 07:44:12 2011 +0200 Fixed problem with GameIs report line, missing NDC.clear() diff --git a/test/TestGame.java b/test/TestGame.java index 4109ac7..0769927 100644 --- a/test/TestGame.java +++ b/test/TestGame.java @@ -7,6 +7,7 @@ import java.util.List; import java.util.Scanner; import org.apache.log4j.Logger; +import org.apache.log4j.NDC; import rails.common.parser.Config; import rails.game.Game; @@ -94,8 +95,10 @@ public class TestGame extends TestCase { if (gameFile.exists()) { log.debug("Found gamefile at " + gameFilename); Game testGame = Game.load(gameFilename); - if (testGame != null) + if (testGame != null) { testReport = ReportBuffer.getAsList(); + NDC.clear(); // remove reference to GameManager + } } else { log.error("Did not find gamefile at " + gameFilename); } diff --git a/test/TestGameBuilder.java b/test/TestGameBuilder.java index af3f83a..bdbc978 100644 --- a/test/TestGameBuilder.java +++ b/test/TestGameBuilder.java @@ -11,6 +11,8 @@ import javax.swing.JFileChooser; import javax.swing.JPanel; import javax.swing.filechooser.FileFilter; +import org.apache.log4j.NDC; + import junit.framework.Test; import junit.framework.TestCase; import junit.framework.TestSuite; @@ -37,6 +39,7 @@ public final class TestGameBuilder extends TestCase { if (game != null) { List<String> report = ReportBuffer.getAsList(); + NDC.clear(); // remove reference to GameManager PrintWriter reportFile = null; try{ reportFile = new PrintWriter(reportFilename); diff --git a/test/data/real/1856_A.report b/test/data/real/1856_A.report index dce4fb6..fbd5951 100644 --- a/test/data/real/1856_A.report +++ b/test/data/real/1856_A.report @@ -1,3 +1,4 @@ +GameIs,1856 PlayerIs,1,Adam PlayerIs,2,Aliza PlayerIs,3,Ed diff --git a/test/data/real/1889_A.report b/test/data/real/1889_A.report index 4edc005..b697222 100644 --- a/test/data/real/1889_A.report +++ b/test/data/real/1889_A.report @@ -1,3 +1,4 @@ +GameIs,1889 PlayerIs,1,Phil PlayerIs,2,Simon PlayerIs,3,Chris diff --git a/test/data/real/1889_B.rails b/test/data/real/1889_B.rails new file mode 100644 index 0000000..c118a18 Binary files /dev/null and b/test/data/real/1889_B.rails differ diff --git a/test/data/real/1889_B.rails.corrupt b/test/data/real/1889_B.rails.corrupt deleted file mode 100644 index c118a18..0000000 Binary files a/test/data/real/1889_B.rails.corrupt and /dev/null differ diff --git a/test/data/real/1889_B.report b/test/data/real/1889_B.report new file mode 100644 index 0000000..b281a75 --- /dev/null +++ b/test/data/real/1889_B.report @@ -0,0 +1,1262 @@ +GameIs,1889 +PlayerIs,1,klaus +PlayerIs,2,Josha +PlayerIs,3,bernd +PlayerIs,4,stefan +PlayerCash,¥420 +BankHas,¥5320 +StartOfPhase,2 +BankSizeIs,¥5320 +StartOfInitialRound +HasPriority,klaus +BID_ITEM_LOG,klaus,¥65,E,¥355 +BID_ITEM_LOG,Josha,¥55,D,¥365 +BID_ITEM_LOG,bernd,¥35,B,¥385 +BID_ITEM_LOG,stefan,¥40,B,¥380 +BuysItemFor,klaus,A,¥20 +TO_AUCTION,B +PASSES,bernd +BuysItemFor,stefan,B,¥40 +BuysItemFor,Josha,C,¥40 +BuysItemFor,Josha,D,¥55 +BuysItemFor,klaus,E,¥65 +BuysItemFor,bernd,F,¥80 +BuysItemFor,stefan,G,¥150 +Has,klaus,¥335 +Has,Josha,¥325 +Has,bernd,¥340 +Has,stefan,¥230 +StartStockRound,1 +HasPriority,klaus +START_COMPANY_LOG,klaus,IR,¥80,¥160,2,20,BANK +PASSES,Josha +START_COMPANY_LOG,bernd,UR,¥65,¥130,2,20,BANK +BUY_SHARE_LOG,stefan,10,IR,IPO,¥80 +BUY_SHARE_LOG,klaus,10,IR,IPO,¥80 +START_COMPANY_LOG,Josha,TR,¥80,¥160,2,20,BANK +BUY_SHARE_LOG,bernd,10,UR,IPO,¥65 +BUY_SHARE_LOG,stefan,10,UR,IPO,¥65 +BUY_SHARE_LOG,klaus,10,IR,IPO,¥80 +FloatsWithCash,IR,¥800 +BUY_SHARE_LOG,Josha,10,TR,IPO,¥80 +BUY_SHARE_LOG,bernd,10,UR,IPO,¥65 +FloatsWithCash,UR,¥650 +BUY_SHARE_LOG,stefan,10,IR,IPO,¥80 +PASSES,klaus +BUY_SHARE_LOG,Josha,10,IR,IPO,¥80 +BUY_SHARE_LOG,bernd,10,UR,IPO,¥65 +PASSES,stefan +PASSES,klaus +PASSES,Josha +PASSES,bernd + +END_SR,1 +Has,IR,¥800 +Has,UR,¥650 +Has,klaus,¥15 +Has,Josha,¥5 +Has,bernd,¥15 +Has,stefan,¥5 +START_OR,1.1 +ReceivesFor,klaus,¥5,A +ReceivesFor,stefan,¥5,B +ReceivesFor,Josha,¥10,C +ReceivesFor,Josha,¥15,D +ReceivesFor,klaus,¥15,E +ReceivesFor,bernd,¥20,F +ReceivesFor,stefan,¥30,G + +CompanyOperates,IR,klaus +LaysTileAt,IR,5,E2,S +CompanyDoesNotPayDividend,IR +PRICE_MOVES_LOG,IR,¥80,D3,¥75,C3 +BuysTrain,IR,2,IPO,¥80 +FirstTrainBought,2 +BuysTrain,IR,2,IPO,¥80 +BuysTrain,IR,2,IPO,¥80 + +CompanyOperates,UR,bernd +LaysTileAt,UR,9,B5,S +LAYS_TOKEN_ON,UR,C4,¥40 +CompanyDoesNotPayDividend,UR +PRICE_MOVES_LOG,UR,¥65,D6,¥60,C6 +BuysTrain,UR,2,IPO,¥80 +BuysTrain,UR,2,IPO,¥80 + +EndOfOperatingRound,1.1 +ORWorthIncrease,klaus,1.1,¥0 +ORWorthIncrease,Josha,1.1,¥20 +ORWorthIncrease,bernd,1.1,-¥5 +ORWorthIncrease,stefan,1.1,¥20 +Has,IR,¥560 +Has,UR,¥450 +Has,klaus,¥35 +Has,Josha,¥30 +Has,bernd,¥35 +Has,stefan,¥40 +StartStockRound,2 +HasPriority,stefan +PASSES,stefan +PASSES,klaus +PASSES,Josha +PASSES,bernd + +END_SR,2 +Has,IR,¥560 +Has,UR,¥450 +Has,klaus,¥35 +Has,Josha,¥30 +Has,bernd,¥35 +Has,stefan,¥40 +START_OR,2.1 +ReceivesFor,klaus,¥5,A +ReceivesFor,stefan,¥5,B +ReceivesFor,Josha,¥10,C +ReceivesFor,Josha,¥15,D +ReceivesFor,klaus,¥15,E +ReceivesFor,bernd,¥20,F +ReceivesFor,stefan,¥30,G + +CompanyOperates,IR,klaus +LaysTileAt,IR,5,F3,NE +LAYS_TOKEN_ON,IR,F3,¥40 +CompanyRevenue,IR,¥140 +CompanyPaysOutFull,IR,¥140 +Payout,stefan,¥28,2,10 +Payout,Josha,¥14,1,10 +Payout,klaus,¥56,4,10 +PRICE_MOVES_LOG,IR,¥75,C3,¥80,D3 + +CompanyOperates,UR,bernd +LaysTileAt,UR,9,C8,NW +CompanyRevenue,UR,¥100 +CompanyPaysOutFull,UR,¥100 +Payout,stefan,¥10,1,10 +Payout,bernd,¥50,5,10 +PRICE_MOVES_LOG,UR,¥60,C6,¥65,D6 + +EndOfOperatingRound,2.1 +ORWorthIncrease,klaus,2.1,¥96 +ORWorthIncrease,Josha,2.1,¥44 +ORWorthIncrease,bernd,2.1,¥95 +ORWorthIncrease,stefan,2.1,¥88 +Has,IR,¥520 +Has,UR,¥450 +Has,klaus,¥111 +Has,Josha,¥69 +Has,bernd,¥105 +Has,stefan,¥113 +StartStockRound,3 +HasPriority,stefan +SELL_SHARES_LOG,stefan,2,10,20,IR,¥160 +PRICE_MOVES_LOG,IR,¥80,D3,¥70,D5 +SELL_SHARE_LOG,stefan,10,UR,¥65 +PRICE_MOVES_LOG,UR,¥65,D6,¥60,D7 +START_COMPANY_LOG,stefan,KO,¥65,¥130,2,20,BANK +BUY_SHARE_LOG,klaus,10,IR,Pool,¥70 +BUY_SHARE_LOG,Josha,10,UR,Pool,¥60 +BUY_SHARE_LOG,bernd,10,IR,Pool,¥70 +BUY_SHARE_LOG,stefan,10,KO,IPO,¥65 +SwapsPrivateForCertificate,klaus,E,10,IR +PrivateCloses,E +PASSES,Josha +PASSES,bernd +BUY_SHARE_LOG,stefan,10,KO,IPO,¥65 +PASSES,klaus +PASSES,Josha +PASSES,bernd +BUY_SHARE_LOG,stefan,10,KO,IPO,¥65 +FloatsWithCash,KO,¥650 +PASSES,klaus +PASSES,Josha +PASSES,bernd +PASSES,stefan + +END_SR,3 +Has,IR,¥520 +Has,KO,¥650 +Has,UR,¥450 +Has,klaus,¥41 +Has,Josha,¥9 +Has,bernd,¥35 +Has,stefan,¥13 +START_OR,3.1 +ReceivesFor,klaus,¥5,A +ReceivesFor,stefan,¥5,B +ReceivesFor,Josha,¥10,C +ReceivesFor,Josha,¥15,D +ReceivesFor,bernd,¥20,F +ReceivesFor,stefan,¥30,G + +CompanyOperates,IR,klaus +CompanyRevenue,IR,¥140 +CompanyPaysOutFull,IR,¥140 +Payout,bernd,¥14,1,10 +Payout,Josha,¥14,1,10 +Payout,klaus,¥84,6,10 +PRICE_MOVES_LOG,IR,¥70,D5,¥75,E5 + +CompanyOperates,KO,stefan +LaysTileAt,KO,58,J5,NW +CompanyDoesNotPayDividend,KO +PRICE_MOVES_LOG,KO,¥65,D6,¥60,C6 +BuysTrain,KO,2,IPO,¥80 +All 2-trains are sold out, 3-trains now available +BuysTrain,KO,3,IPO,¥180 +FirstTrainBought,3 +StartOfPhase,3 +BuysPrivateFromFor,KO,B,stefan,¥60 + +CompanyOperates,UR,bernd +LaysTileAt,UR,8,D9,NW +CompanyRevenue,UR,¥100 +CompanyPaysOutFull,UR,¥100 +Payout,bernd,¥50,5,10 +Payout,Josha,¥10,1,10 +PRICE_MOVES_LOG,UR,¥60,D7,¥65,E7 +BuysTrain,UR,3,IPO,¥180 +BuysPrivateFromFor,UR,F,bernd,¥160 + +EndOfOperatingRound,3.1 +ORWorthIncrease,klaus,3.1,¥119 +ORWorthIncrease,Josha,3.1,¥59 +ORWorthIncrease,bernd,3.1,¥194 +ORWorthIncrease,stefan,3.1,¥40 +Has,IR,¥520 +Has,KO,¥330 +Has,UR,¥110 +Has,klaus,¥130 +Has,Josha,¥58 +Has,bernd,¥279 +Has,stefan,¥108 +StartStockRound,4 +HasPriority,klaus +BUY_SHARE_LOG,klaus,10,TR,IPO,¥80 +SELL_SHARE_LOG,Josha,10,UR,¥65 +PRICE_MOVES_LOG,UR,¥65,E7,¥60,E8 +BUY_SHARE_LOG,Josha,10,TR,IPO,¥80 +FloatsWithCash,TR,¥800 +SELL_SHARE_LOG,bernd,10,IR,¥75 +PRICE_MOVES_LOG,IR,¥75,E5,¥70,E6 +START_COMPANY_LOG,bernd,KU,¥70,¥140,2,20,BANK +BUY_SHARE_LOG,stefan,10,UR,Pool,¥60 +PASSES,klaus +PASSES,Josha +BUY_SHARE_LOG,bernd,10,KU,IPO,¥70 +SELL_SHARES_LOG,stefan,2,10,20,KO,¥120 +PRICE_MOVES_LOG,KO,¥60,C6,¥50,C8 +BUY_SHARE_LOG,stefan,10,IR,Pool,¥70 +BUY_SHARE_LOG,klaus,10,KO,Pool,¥50 +PASSES,Josha +BUY_SHARE_LOG,bernd,10,KU,IPO,¥70 +BUY_SHARE_LOG,stefan,10,IR,IPO,¥80 +PASSES,klaus +PASSES,Josha +BUY_SHARE_LOG,bernd,10,KU,IPO,¥70 +FloatsWithCash,KU,¥700 +PASSES,stefan +PASSES,klaus +SELL_SHARE_LOG,Josha,10,TR,¥80 +PRICE_MOVES_LOG,TR,¥80,D3,¥75,D4 +BUY_SHARE_LOG,Josha,10,IR,IPO,¥80 +PASSES,bernd +PASSES,stefan +PASSES,klaus +PASSES,Josha + +END_SR,4 +PRICE_MOVES_LOG,IR,¥70,E6,¥75,E5 +SoldOut,IR,¥70,E6,¥75,E5 +Has,IR,¥520 +Has,KO,¥330 +Has,TR,¥800 +Has,KU,¥700 +Has,UR,¥110 +Has,klaus,¥0 +Has,Josha,¥43 +Has,bernd,¥4 +Has,stefan,¥18 +START_OR,4.1 +ReceivesFor,klaus,¥5,A +ReceivesFor,KO,¥5,B +ReceivesFor,Josha,¥10,C +ReceivesFor,Josha,¥15,D +ReceivesFor,UR,¥20,F +ReceivesFor,stefan,¥30,G + +CompanyOperates,IR,klaus +LaysTileAt,IR,14,F3,NW +CompanyRevenue,IR,¥160 +CompanyPaysOutFull,IR,¥160 +Payout,klaus,¥96,6,10 +Payout,stefan,¥32,2,10 +Payout,Josha,¥32,2,10 +PRICE_MOVES_LOG,IR,¥75,E5,¥80,F5 +BuysTrain,IR,3,IPO,¥180 + +CompanyOperates,TR,Josha +BuysPrivateFromFor,TR,D,Josha,¥100 +CorrectionModeActivate,Josha,CORRECT_MAP +CorrectMapLaysTileAt,9,F7,S +CorrectionModeDeactivate,Josha,CORRECT_MAP +CompanyDoesNotPayDividend,TR +PRICE_MOVES_LOG,TR,¥75,D4,¥70,C4 +BuysTrain,TR,3,IPO,¥180 +BuysTrain,TR,3,IPO,¥180 +All 3-trains are sold out, 4-trains now available +BuysTrain,TR,4,IPO,¥300 +FirstTrainBought,4 +StartOfPhase,4 + +CompanyOperates,KU,bernd +LaysTileAt,KU,5,C10,SE +CompanyDoesNotPayDividend,KU +PRICE_MOVES_LOG,KU,¥70,D5,¥65,C5 +BuysTrain,KU,4,IPO,¥300 + +CompanyOperates,UR,bernd +LaysTileAt,UR,23,C8,SE +CompanyRevenue,UR,¥80 +CompanyPaysOutFull,UR,¥80 +Payout,bernd,¥40,5,10 +Payout,stefan,¥8,1,10 +PRICE_MOVES_LOG,UR,¥60,E8,¥65,E7 + +CompanyOperates,KO,stefan +LaysTileAt,KO,9,J3,NW +CompanyRevenue,KO,¥40 +CompanyPaysOutFull,KO,¥40 +Payout,klaus,¥4,1,10 +Payout,stefan,¥12,3,10 +Payout,KO,¥4,1,10 +PRICE_MOVES_LOG,KO,¥50,C8,¥55,D8 + +EndOfOperatingRound,4.1 +ORWorthIncrease,klaus,4.1,¥135 +ORWorthIncrease,Josha,4.1,¥102 +ORWorthIncrease,bernd,4.1,¥40 +ORWorthIncrease,stefan,4.1,¥112 +Has,IR,¥340 +Has,KO,¥339 +Has,TR,¥40 +Has,KU,¥400 +Has,UR,¥130 +Has,klaus,¥105 +Has,Josha,¥200 +Has,bernd,¥44 +Has,stefan,¥100 +START_OR,4.2 +ReceivesFor,klaus,¥5,A +ReceivesFor,KO,¥5,B +ReceivesFor,Josha,¥10,C +ReceivesFor,TR,¥15,D +ReceivesFor,UR,¥20,F +ReceivesFor,stefan,¥30,G + +CompanyOperates,IR,klaus +LaysTileAt,IR,205,E2,SE +CompanyRevenue,IR,¥90 +CompanyPaysOutFull,IR,¥90 +Payout,klaus,¥54,6,10 +Payout,stefan,¥18,2,10 +Payout,Josha,¥18,2,10 +PRICE_MOVES_LOG,IR,¥80,F5,¥90,G5 +BuysTrain,IR,4,IPO,¥300 + +CompanyOperates,TR,Josha +CorrectionModeActivate,Josha,CORRECT_MAP +CorrectMapLaysTileAt,9,F5,S +CorrectionModeDeactivate,Josha,CORRECT_MAP +LAYS_TOKEN_ON,TR,F3,¥40 +CompanyRevenue,TR,¥180 +CompanyPaysOutFull,TR,¥180 +Payout,klaus,¥18,1,10 +Payout,Josha,¥54,3,10 +Payout,TR,¥18,1,10 +PRICE_MOVES_LOG,TR,¥70,C4,¥75,D4 + +CompanyOperates,UR,bernd +LaysTileAt,UR,8,E8,SE +CompanyRevenue,UR,¥100 +CompanyPaysOutFull,UR,¥100 +Payout,stefan,¥10,1,10 +Payout,bernd,¥50,5,10 +PRICE_MOVES_LOG,UR,¥65,E7,¥70,F7 + +CompanyOperates,KU,bernd +LaysTileAt,KU,23,D9,SW +CompanyRevenue,KU,¥120 +CompanyPaysOutFull,KU,¥120 +Payout,bernd,¥60,5,10 +PRICE_MOVES_LOG,KU,¥65,C5,¥70,D5 +BuysTrain,KU,4,IPO,¥300 +All 4-trains are sold out, 5-trains now available + +CompanyOperates,KO,stefan +LaysTileAt,KO,5,I2,S +CompanyRevenue,KO,¥70 +CompanyPaysOutFull,KO,¥70 +Payout,klaus,¥7,1,10 +Payout,stefan,¥21,3,10 +Payout,KO,¥7,1,10 +PRICE_MOVES_LOG,KO,¥55,D8,¥60,E8 + +EndOfOperatingRound,4.2 +ORWorthIncrease,klaus,4.2,¥154 +ORWorthIncrease,Josha,4.2,¥117 +ORWorthIncrease,bernd,4.2,¥160 +ORWorthIncrease,stefan,4.2,¥119 +Has,IR,¥40 +Has,KO,¥351 +Has,TR,¥33 +Has,KU,¥100 +Has,UR,¥150 +Has,klaus,¥189 +Has,Josha,¥282 +Has,bernd,¥154 +Has,stefan,¥179 +StartStockRound,5 +HasPriority,bernd +BUY_SHARE_LOG,bernd,10,TR,Pool,¥75 +SELL_SHARE_LOG,stefan,10,UR,¥70 +SELL_SHARES_LOG,stefan,2,10,20,IR,¥180 +PRICE_MOVES_LOG,IR,¥90,G5,¥80,G6 +SELL_SHARE_LOG,stefan,10,KO,¥60 +START_COMPANY_LOG,stefan,SR,¥90,¥180,2,20,BANK +BUY_SHARE_LOG,klaus,10,SR,IPO,¥90 +SELL_SHARES_LOG,Josha,2,10,20,IR,¥160 +START_COMPANY_LOG,Josha,AR,¥80,¥160,2,20,BANK +BUY_SHARE_LOG,bernd,10,UR,IPO,¥65 +BUY_SHARE_LOG,stefan,10,SR,IPO,¥90 +BUY_SHARE_LOG,klaus,10,SR,IPO,¥90 +FloatsWithCash,SR,¥900 +BUY_SHARE_LOG,Josha,10,AR,IPO,¥80 +SELL_SHARE_LOG,bernd,10,UR,¥70 +BUY_SHARE_LOG,bernd,10,KU,IPO,¥70 +BUY_SHARE_LOG,stefan,10,SR,IPO,¥90 +SELL_SHARES_LOG,klaus,2,10,20,SR,¥180 +PRICE_MOVES_LOG,SR,¥90,D2,¥75,D4 +BUY_SHARE_LOG,klaus,10,TR,IPO,¥80 +BUY_SHARE_LOG,Josha,10,TR,IPO,¥80 +PASSES,bernd +BUY_SHARE_LOG,stefan,10,AR,IPO,¥80 +BUY_SHARE_LOG,klaus,10,AR,IPO,¥80 +FloatsWithCash,AR,¥800 +BUY_SHARE_LOG,Josha,10,TR,IPO,¥80 +PASSES,bernd +SELL_SHARE_LOG,stefan,10,AR,¥80 +PRICE_MOVES_LOG,AR,¥80,D3,¥75,D4 +BUY_SHARE_LOG,stefan,10,SR,Pool,¥75 +SELL_SHARE_LOG,klaus,10,AR,¥75 +PRICE_MOVES_LOG,AR,¥75,D4,¥70,D5 +BUY_SHARE_LOG,klaus,10,TR,IPO,¥80 +PASSES,Josha +PASSES,bernd +PASSES,stefan +PASSES,klaus + +END_SR,5 +Has,AR,¥800 +Has,IR,¥40 +Has,SR,¥900 +Has,KO,¥351 +Has,TR,¥33 +Has,KU,¥100 +Has,UR,¥150 +Has,klaus,¥24 +Has,Josha,¥42 +Has,bernd,¥14 +Has,stefan,¥54 +START_OR,5.1 +ReceivesFor,klaus,¥5,A +ReceivesFor,KO,¥5,B +ReceivesFor,Josha,¥10,C +ReceivesFor,TR,¥15,D +ReceivesFor,UR,¥20,F +ReceivesFor,stefan,¥30,G + +CompanyOperates,IR,klaus +LaysTileAt,IR,57,G4,NW +CompanyRevenue,IR,¥220 +CompanyPaysOutFull,IR,¥220 +Payout,klaus,¥132,6,10 +Payout,IR,¥88,4,10 +PRICE_MOVES_LOG,IR,¥80,G6,¥90,G5 + +CompanyOperates,TR,Josha +CorrectionModeActivate,Josha,CORRECT_MAP +CorrectMapLaysTileAt,9,G8,SW +CorrectionModeDeactivate,Josha,CORRECT_MAP +CompanyRevenue,TR,¥280 +CompanyWithholds,TR,¥280 +PRICE_MOVES_LOG,TR,¥75,D4,¥70,C4 +BuysPrivateFromFor,TR,C,Josha,¥80 +LaysTileAt,TR,15,C4,SE + +CompanyOperates,SR,stefan +LaysTileAt,SR,15,I2,NE +CompanyDoesNotPayDividend,SR +PRICE_MOVES_LOG,SR,¥75,D4,¥70,C4 +BuysTrain,SR,5,IPO,¥450 +FirstTrainBought,5 +StartOfPhase,5 +PrivateCloses,A +PrivateCloses,B +PrivateCloses,C +PrivateCloses,D +PrivateCloses,F +CompanyDiscardsTrain,TR,3 +BuysTrain,SR,5,IPO,¥450 + +CompanyOperates,UR,bernd +LaysTileAt,UR,15,C10,SW +CompanyRevenue,UR,¥100 +CompanyPaysOutFull,UR,¥100 +Payout,bernd,¥50,5,10 +Payout,UR,¥20,2,10 +PRICE_MOVES_LOG,UR,¥70,F7,¥75,F6 +BuysTrain,UR,4,KU,¥185 + +CompanyOperates,KU,bernd +LaysTileAt,KU,448,C10,NE +CompanyRevenue,KU,¥140 +CompanyPaysOutFull,KU,¥140 +Payout,bernd,¥84,6,10 +PRICE_MOVES_LOG,KU,¥70,D5,¥75,E5 + +CompanyOperates,AR,Josha +LaysTileAt,AR,6,K8,SE +CompanyDoesNotPayDividend,AR +PRICE_MOVES_LOG,AR,¥70,D5,¥65,C5 +BuysTrain,AR,5,IPO,¥450 +All 5-trains are sold out, 6-trains now available + +CompanyOperates,KO,stefan +LaysTileAt,KO,440,K4,S +CompanyRevenue,KO,¥110 +CompanyPaysOutFull,KO,¥110 +Payout,klaus,¥11,1,10 +Payout,stefan,¥22,2,10 +Payout,KO,¥22,2,10 +PRICE_MOVES_LOG,KO,¥60,E8,¥65,E7 +BuysTrain,KO,5,SR,¥378 + +EndOfOperatingRound,5.1 +ORWorthIncrease,klaus,5.1,¥178 +ORWorthIncrease,Josha,5.1,¥10 +ORWorthIncrease,bernd,5.1,¥184 +ORWorthIncrease,stefan,5.1,¥37 +Has,AR,¥350 +Has,IR,¥128 +Has,SR,¥378 +Has,KO,¥0 +Has,TR,¥248 +Has,KU,¥285 +Has,UR,¥5 +Has,klaus,¥172 +Has,Josha,¥132 +Has,bernd,¥148 +Has,stefan,¥106 +START_OR,5.2 +ReceivesFor,stefan,¥50,G + +CompanyOperates,IR,klaus +LaysTileAt,IR,611,F3,S +CompanyRevenue,IR,¥300 +CompanyPaysOutFull,IR,¥300 +Payout,klaus,¥180,6,10 +Payout,IR,¥120,4,10 +PRICE_MOVES_LOG,IR,¥90,G5,¥100,H5 + +CompanyOperates,UR,bernd +LaysTileAt,UR,611,C4,SE +CompanyRevenue,UR,¥250 +CompanyPaysOutFull,UR,¥250 +Payout,bernd,¥125,5,10 +Payout,UR,¥50,2,10 +PRICE_MOVES_LOG,UR,¥75,F6,¥80,G6 + +CompanyOperates,KU,bernd +LaysTileAt,KU,41,C8,SE +CompanyRevenue,KU,¥150 +CompanyPaysOutFull,KU,¥150 +Payout,bernd,¥90,6,10 +PRICE_MOVES_LOG,KU,¥75,E5,¥80,F5 + +CompanyOperates,TR,Josha +LaysTileAt,TR,6,H7,NW +CompanyRevenue,TR,¥280 +CompanyPaysOutFull,TR,¥280 +Payout,bernd,¥28,1,10 +Payout,klaus,¥84,3,10 +Payout,Josha,¥140,5,10 +PRICE_MOVES_LOG,TR,¥70,C4,¥75,D4 + +CompanyOperates,SR,stefan +LaysTileAtFor,SR,438,I4,NE,¥80 +CompanyRevenue,SR,¥160 +CompanyPaysOutFull,SR,¥160 +Payout,stefan,¥80,5,10 +Payout,SR,¥16,1,10 +PRICE_MOVES_LOG,SR,¥70,C4,¥75,D4 + +CompanyOperates,KO,stefan +LaysTileAt,KO,466,K4,S +CompanyRevenue,KO,¥270 +CompanyPaysOutFull,KO,¥270 +Payout,klaus,¥27,1,10 +Payout,stefan,¥54,2,10 +Payout,KO,¥54,2,10 +PRICE_MOVES_LOG,KO,¥65,E7,¥70,F7 + +CompanyOperates,AR,Josha +LaysTileAt,AR,8,I8,NW +LAYS_TOKEN_ON,AR,F9,¥40 +CompanyRevenue,AR,¥170 +CompanyPaysOutFull,AR,¥170 +Payout,Josha,¥51,3,10 +Payout,AR,¥34,2,10 +PRICE_MOVES_LOG,AR,¥65,C5,¥70,D5 +BuysTrain,AR,3,TR,¥263 + +EndOfOperatingRound,5.2 +ORWorthIncrease,klaus,5.2,¥371 +ORWorthIncrease,Josha,5.2,¥231 +ORWorthIncrease,bernd,5.2,¥303 +ORWorthIncrease,stefan,5.2,¥219 +Has,AR,¥81 +Has,IR,¥248 +Has,SR,¥314 +Has,KO,¥54 +Has,TR,¥511 +Has,KU,¥285 +Has,UR,¥55 +Has,klaus,¥463 +Has,Josha,¥323 +Has,bernd,¥391 +Has,stefan,¥290 +StartStockRound,6 +HasPriority,Josha +BUY_SHARE_LOG,Josha,10,KO,IPO,¥65 +BUY_SHARE_LOG,bernd,10,KO,IPO,¥65 +BUY_SHARE_LOG,stefan,10,KO,IPO,¥65 +BUY_SHARE_LOG,klaus,10,TR,IPO,¥80 +BUY_SHARE_LOG,Josha,10,IR,Pool,¥100 +BUY_SHARE_LOG,bernd,10,KO,IPO,¥65 +BUY_SHARE_LOG,stefan,10,KO,IPO,¥65 +BUY_SHARE_LOG,klaus,10,SR,Pool,¥75 +BUY_SHARE_LOG,Josha,10,IR,Pool,¥100 +BUY_SHARE_LOG,bernd,10,IR,Pool,¥100 +BUY_SHARE_LOG,stefan,10,KO,Pool,¥70 +BUY_SHARE_LOG,klaus,10,KO,Pool,¥70 +SELL_SHARE_LOG,Josha,10,KO,¥70 +BUY_SHARE_LOG,Josha,10,IR,Pool,¥100 +BUY_SHARE_LOG,bernd,10,UR,IPO,¥65 +BUY_SHARE_LOG,stefan,10,KO,Pool,¥70 +BUY_SHARE_LOG,klaus,10,SR,IPO,¥90 +PASSES,Josha +SELL_SHARE_LOG,bernd,10,UR,¥80 +BUY_SHARE_LOG,bernd,10,AR,Pool,¥70 +PASSES,stefan +BUY_SHARE_LOG,klaus,10,KU,IPO,¥70 +PASSES,Josha +SELL_SHARE_LOG,bernd,10,KO,¥70 +BUY_SHARE_LOG,bernd,10,SR,IPO,¥90 +PASSES,stefan +SELL_SHARE_LOG,klaus,10,KU,¥80 +PRICE_MOVES_LOG,KU,¥80,F5,¥75,F6 +PASSES,Josha +PASSES,bernd +PASSES,stefan +BUY_SHARE_LOG,klaus,10,KO,Pool,¥70 +PASSES,Josha +PASSES,bernd +PASSES,stefan +PASSES,klaus + +END_SR,6 +PRICE_MOVES_LOG,IR,¥100,H5,¥110,H4 +SoldOut,IR,¥100,H5,¥110,H4 +PRICE_MOVES_LOG,TR,¥75,D4,¥80,D3 +SoldOut,TR,¥75,D4,¥80,D3 +PRICE_MOVES_LOG,KO,¥70,F7,¥75,F6 +SoldOut,KO,¥70,F7,¥75,F6 +Has,AR,¥81 +Has,IR,¥248 +Has,SR,¥314 +Has,KO,¥54 +Has,TR,¥511 +Has,KU,¥285 +Has,UR,¥55 +Has,klaus,¥88 +Has,Josha,¥28 +Has,bernd,¥86 +Has,stefan,¥20 +START_OR,6.1 +ReceivesFor,stefan,¥50,G + +CompanyOperates,IR,klaus +LaysTileAt,IR,15,G4,SE +CompanyRevenue,IR,¥290 +CompanyWithholds,IR,¥290 +PRICE_MOVES_LOG,IR,¥110,H4,¥100,G4 + +CompanyOperates,UR,bernd +LaysTileAt,UR,23,E8,NE +CompanyRevenue,UR,¥210 +CompanyPaysOutFull,UR,¥210 +Payout,bernd,¥105,5,10 +Payout,UR,¥63,3,10 +PRICE_MOVES_LOG,UR,¥80,G6,¥90,G5 + +CompanyOperates,TR,Josha +LaysTileAt,TR,24,F7,N +CompanyRevenue,TR,¥170 +CompanyPaysOutFull,TR,¥170 +Payout,bernd,¥17,1,10 +Payout,klaus,¥68,4,10 +Payout,Josha,¥85,5,10 +PRICE_MOVES_LOG,TR,¥80,D3,¥90,E3 + +CompanyOperates,KU,bernd +LaysTileAt,KU,46,F7,N +CompanyRevenue,KU,¥140 +CompanyPaysOutFull,KU,¥140 +Payout,bernd,¥84,6,10 +Payout,KU,¥14,1,10 +PRICE_MOVES_LOG,KU,¥75,F6,¥80,G6 + +CompanyOperates,KO,stefan +LaysTileAt,KO,448,I2,SW +CompanyRevenue,KO,¥290 +CompanyPaysOutFull,KO,¥290 +Payout,bernd,¥29,1,10 +Payout,klaus,¥87,3,10 +Payout,stefan,¥174,6,10 +PRICE_MOVES_LOG,KO,¥75,F6,¥80,G6 + +CompanyOperates,SR,stefan +LaysTileAtFor,SR,439,I4,S,¥80 +CompanyRevenue,SR,¥210 +CompanyPaysOutFull,SR,¥210 +Payout,bernd,¥21,1,10 +Payout,klaus,¥42,2,10 +Payout,stefan,¥105,5,10 +PRICE_MOVES_LOG,SR,¥75,D4,¥80,E4 + +CompanyOperates,AR,Josha +LaysTileAt,AR,14,H7,SW +CompanyRevenue,AR,¥270 +CompanyWithholds,AR,¥270 +PRICE_MOVES_LOG,AR,¥70,D5,¥65,C5 + +EndOfOperatingRound,6.1 +ORWorthIncrease,klaus,6.1,¥202 +ORWorthIncrease,Josha,6.1,¥90 +ORWorthIncrease,bernd,6.1,¥341 +ORWorthIncrease,stefan,6.1,¥384 +Has,AR,¥351 +Has,IR,¥538 +Has,SR,¥234 +Has,KO,¥54 +Has,TR,¥511 +Has,KU,¥299 +Has,UR,¥118 +Has,klaus,¥285 +Has,Josha,¥113 +Has,bernd,¥342 +Has,stefan,¥349 +START_OR,6.2 +ReceivesFor,stefan,¥50,G + +CompanyOperates,IR,klaus +LaysTileAtFor,IR,8,H5,NW,¥80 +CompanyRevenue,IR,¥320 +CompanyWithholds,IR,¥320 +PRICE_MOVES_LOG,IR,¥100,G4,¥90,F4 + +CompanyOperates,UR,bernd +LaysTileAt,UR,9,D3,SW +CompanyRevenue,UR,¥240 +CompanyPaysOutFull,UR,¥240 +Payout,bernd,¥120,5,10 +Payout,UR,¥72,3,10 +PRICE_MOVES_LOG,UR,¥90,G5,¥100,H5 + +CompanyOperates,TR,Josha +LaysTileAt,TR,448,E2,SW +LAYS_TOKEN_ON,TR,E2,¥40 +CompanyRevenue,TR,¥190 +CompanyPaysOutFull,TR,¥190 +Payout,bernd,¥19,1,10 +Payout,klaus,¥76,4,10 +Payout,Josha,¥95,5,10 +PRICE_MOVES_LOG,TR,¥90,E3,¥100,F3 + +CompanyOperates,KU,bernd +LaysTileAt,KU,47,E8,SW +CompanyRevenue,KU,¥140 +CompanyPaysOutFull,KU,¥140 +Payout,bernd,¥84,6,10 +Payout,KU,¥14,1,10 +PRICE_MOVES_LOG,KU,¥80,G6,¥90,G5 + +CompanyOperates,KO,stefan +LaysTileAt,KO,23,F5,N +CompanyRevenue,KO,¥360 +CompanyPaysOutFull,KO,¥360 +Payout,bernd,¥36,1,10 +Payout,klaus,¥108,3,10 +Payout,stefan,¥216,6,10 +PRICE_MOVES_LOG,KO,¥80,G6,¥90,G5 + +CompanyOperates,SR,stefan +LaysTileAt,SR,448,G4,NW +LAYS_TOKEN_ON,SR,G4,¥40 +CompanyRevenue,SR,¥240 +CompanyPaysOutFull,SR,¥240 +Payout,bernd,¥24,1,10 +Payout,klaus,¥48,2,10 +Payout,stefan,¥120,5,10 +PRICE_MOVES_LOG,SR,¥80,E4,¥90,F4 + +CompanyOperates,AR,Josha +LaysTileAt,AR,45,F5,S +CompanyRevenue,AR,¥340 +CompanyWithholds,AR,¥340 +PRICE_MOVES_LOG,AR,¥65,C5,¥60,B5 + +EndOfOperatingRound,6.2 +ORWorthIncrease,klaus,6.2,¥262 +ORWorthIncrease,Josha,6.2,¥100 +ORWorthIncrease,bernd,6.2,¥408 +ORWorthIncrease,stefan,6.2,¥496 +Has,AR,¥691 +Has,IR,¥778 +Has,SR,¥194 +Has,KO,¥54 +Has,TR,¥471 +Has,KU,¥313 +Has,UR,¥190 +Has,klaus,¥517 +Has,Josha,¥208 +Has,bernd,¥625 +Has,stefan,¥735 +START_OR,6.3 +ReceivesFor,stefan,¥50,G + +CompanyOperates,UR,bernd +LaysTileAt,UR,23,G8,SW +LAYS_TOKEN_ON,UR,H7,¥40 +CompanyRevenue,UR,¥280 +CompanyPaysOutFull,UR,¥280 +Payout,bernd,¥140,5,10 +Payout,UR,¥84,3,10 +PRICE_MOVES_LOG,UR,¥100,H5,¥110,H4 + +CompanyOperates,TR,Josha +LaysTileAt,TR,24,H5,NW +CompanyRevenue,TR,¥200 +CompanyPaysOutFull,TR,¥200 +Payout,bernd,¥20,1,10 +Payout,klaus,¥80,4,10 +Payout,Josha,¥100,5,10 +PRICE_MOVES_LOG,TR,¥100,F3,¥110,G3 +BuysTrain,TR,5,AR,¥470 + +CompanyOperates,KU,bernd +LaysTileAt,KU,58,B11,NW +CompanyRevenue,KU,¥140 +CompanyPaysOutFull,KU,¥140 +Payout,bernd,¥84,6,10 +Payout,KU,¥14,1,10 +PRICE_MOVES_LOG,KU,¥90,G5,¥100,H5 + +CompanyOperates,KO,stefan +LAYS_TOKEN_ON,KO,G4,¥40 +CompanyRevenue,KO,¥370 +CompanyPaysOutFull,KO,¥370 +Payout,bernd,¥37,1,10 +Payout,klaus,¥111,3,10 +Payout,stefan,¥222,6,10 +PRICE_MOVES_LOG,KO,¥90,G5,¥100,H5 + +CompanyOperates,IR,klaus +CompanyRevenue,IR,¥310 +CompanyPaysOutFull,IR,¥310 +Payout,bernd,¥31,1,10 +Payout,klaus,¥186,6,10 +Payout,Josha,¥93,3,10 +PRICE_MOVES_LOG,IR,¥90,F4,¥100,G4 + +CompanyOperates,SR,stefan +LaysTileAtFor,SR,465,F9,NE,¥80 +CompanyRevenue,SR,¥260 +CompanyPaysOutFull,SR,¥260 +Payout,bernd,¥26,1,10 +Payout,klaus,¥52,2,10 +Payout,stefan,¥130,5,10 +PRICE_MOVES_LOG,SR,¥90,F4,¥100,G4 +BuysTrain,SR,5,KO,¥1 + +CompanyOperates,AR,Josha +LaysTileAt,AR,15,K8,SW +CompanyRevenue,AR,¥140 +CompanyWithholds,AR,¥140 +PRICE_MOVES_LOG,AR,¥60,B5,¥55,A5 +BuysTrain,AR,6,IPO,¥630 +FirstTrainBought,6 +StartOfPhase,6 +BuysTrain,AR,5,TR,¥670 + +EndOfOperatingRound,6.3 +ORWorthIncrease,klaus,6.3,¥579 +ORWorthIncrease,Josha,6.3,¥258 +ORWorthIncrease,bernd,6.3,¥483 +ORWorthIncrease,stefan,6.3,¥512 +Has,AR,¥1 +Has,IR,¥778 +Has,SR,¥113 +Has,KO,¥15 +Has,TR,¥671 +Has,KU,¥327 +Has,UR,¥234 +Has,klaus,¥946 +Has,Josha,¥401 +Has,bernd,¥963 +Has,stefan,¥1137 +StartStockRound,7 +HasPriority,Josha +BUY_SHARE_LOG,Josha,10,SR,IPO,¥90 +SELL_SHARE_LOG,bernd,10,KU,¥100 +BUY_SHARE_LOG,bernd,10,SR,IPO,¥90 +SELL_SHARES_LOG,stefan,5,10,50,KO,¥500 +IS_NOW_PRES_OF,klaus,KO +BUY_SHARE_LOG,stefan,10,AR,Pool,¥55 +BUY_SHARE_LOG,klaus,10,KO,Pool,¥100 +BUY_SHARE_LOG,Josha,10,UR,IPO,¥65 +SELL_SHARE_LOG,bernd,10,KU,¥100 +BUY_SHARE_LOG,bernd,10,UR,IPO,¥65 +BUY_SHARE_LOG,stefan,10,AR,IPO,¥80 +PASSES,klaus +BUY_SHARE_LOG,Josha,10,AR,IPO,¥80 +SELL_SHARES_LOG,bernd,2,10,20,UR,¥220 +PRICE_MOVES_LOG,UR,¥110,H4,¥100,H5 +BUY_SHARE_LOG,bernd,10,AR,IPO,¥80 +BUY_SHARE_LOG,stefan,10,AR,IPO,¥80 +PASSES,klaus +BUY_SHARE_LOG,Josha,10,AR,IPO,¥80 +PASSES,bernd +BUY_SHARE_LOG,stefan,10,KU,IPO,¥70 +SELL_SHARES_LOG,klaus,2,10,20,SR,¥200 +PRICE_MOVES_LOG,SR,¥100,G4,¥80,G6 +BUY_SHARE_LOG,klaus,10,KO,Pool,¥100 +SELL_SHARES_LOG,Josha,2,10,20,IR,¥200 +PRICE_MOVES_LOG,IR,¥100,G4,¥80,G6 +BUY_SHARE_LOG,Josha,10,SR,Pool,¥80 +BUY_SHARE_LOG,bernd,10,SR,Pool,¥80 +BUY_SHARE_LOG,stefan,10,IR,Pool,¥80 +BUY_SHARE_LOG,klaus,10,KO,Pool,¥100 +BUY_SHARE_LOG,Josha,10,KU,IPO,¥70 +PASSES,bernd +BUY_SHARE_LOG,stefan,10,KU,IPO,¥70 +SELL_SHARE_LOG,stefan,10,KU,¥100 +PASSES,klaus +BUY_SHARE_LOG,Josha,10,KO,Pool,¥100 +PASSES,bernd +BUY_SHARE_LOG,stefan,10,UR,Pool,¥100 +PASSES,klaus +PASSES,Josha +PASSES,bernd +BUY_SHARE_LOG,stefan,10,IR,Pool,¥80 +PASSES,klaus +PASSES,Josha +PASSES,bernd +BUY_SHARE_LOG,stefan,10,UR,Pool,¥100 +PASSES,klaus +PASSES,Josha +PASSES,bernd +PASSES,stefan + +END_SR,7 +PRICE_MOVES_LOG,TR,¥110,G3,¥125,G2 +SoldOut,TR,¥110,G3,¥125,G2 +PRICE_MOVES_LOG,SR,¥80,G6,¥90,G5 +SoldOut,SR,¥80,G6,¥90,G5 +PRICE_MOVES_LOG,IR,¥80,G6,¥90,G5 +SoldOut,IR,¥80,G6,¥90,G5 +PRICE_MOVES_LOG,AR,¥55,A5,¥60,A4 +SoldOut,AR,¥55,A5,¥60,A4 +Has,AR,¥1 +Has,IR,¥778 +Has,SR,¥113 +Has,KO,¥15 +Has,TR,¥671 +Has,KU,¥327 +Has,UR,¥234 +Has,klaus,¥846 +Has,Josha,¥36 +Has,bernd,¥1068 +Has,stefan,¥1022 +START_OR,7.1 +ReceivesFor,stefan,¥50,G + +CompanyOperates,TR,Josha +LaysTileAt,TR,24,I8,NW +CompanyRevenue,TR,¥200 +CompanyWithholds,TR,¥200 +PRICE_MOVES_LOG,TR,¥125,G2,¥110,F2 +ExchangesTrain,TR,4,D,IPO,¥800 +FirstTrainBought,D +StartOfPhase,D + +CompanyOperates,KU,bernd +CompanyDoesNotPayDividend,KU +PRICE_MOVES_LOG,KU,¥100,H5,¥90,G5 +PresidentAddsCash,KU,bernd,¥303 +BuysTrain,KU,6,IPO,¥630 + +CompanyOperates,KO,klaus +CompanyDoesNotPayDividend,KO +PRICE_MOVES_LOG,KO,¥100,H5,¥90,G5 +PlayerMustSellShares,klaus,¥239 +SELL_SHARES_LOG,klaus,3,10,30,TR,¥330 +PRICE_MOVES_LOG,TR,¥110,F2,¥80,F5 +PresidentAddsCash,KO,klaus,¥1085 +BuysTrain,KO,D,IPO,¥1100 + +CompanyOperates,UR,bernd +CompanyDoesNotPayDividend,UR +PRICE_MOVES_LOG,UR,¥100,H5,¥90,G5 +PlayerMustSellShares,bernd,¥101 +SELL_SHARES_LOG,bernd,1,10,10,AR,¥60 +PRICE_MOVES_LOG,AR,¥60,A4,¥55,A5 +SELL_SHARES_LOG,bernd,1,10,10,SR,¥90 +PRICE_MOVES_LOG,SR,¥90,G5,¥80,G6 +PresidentAddsCash,UR,bernd,¥866 +BuysTrain,UR,D,IPO,¥1100 + +CompanyOperates,IR,klaus +CompanyDoesNotPayDividend,IR +PRICE_MOVES_LOG,IR,¥90,G5,¥80,F5 +PlayerMustSellShares,klaus,¥231 +SELL_SHARES_LOG,klaus,1,10,10,TR,¥80 +PRICE_MOVES_LOG,TR,¥80,F5,¥75,F6 +SELL_SHARES_LOG,klaus,2,10,20,KO,¥180 +PRICE_MOVES_LOG,KO,¥90,G5,¥80,G6 +PresidentAddsCash,IR,klaus,¥322 +BuysTrain,IR,D,IPO,¥1100 + +CompanyOperates,SR,stefan +LaysTileAt,SR,42,I8,NW +CompanyRevenue,SR,¥450 +CompanyPaysOutFull,SR,¥450 +Payout,stefan,¥225,5,10 +Payout,bernd,¥90,2,10 +Payout,Josha,¥90,2,10 +Payout,SR,¥45,1,10 +PRICE_MOVES_LOG,SR,¥80,G6,¥90,G5 + +CompanyOperates,AR,Josha +LaysTileAt,AR,58,J9,NW +CompanyRevenue,AR,¥440 +CompanyPaysOutFull,AR,¥440 +Payout,stefan,¥132,3,10 +Payout,bernd,¥44,1,10 +Payout,Josha,¥220,5,10 +Payout,AR,¥44,1,10 +PRICE_MOVES_LOG,AR,¥55,A5,¥60,B5 + +EndOfOperatingRound,7.1 +ORWorthIncrease,klaus,7.1,-¥1657 +ORWorthIncrease,Josha,7.1,¥10 +ORWorthIncrease,bernd,7.1,-¥1195 +ORWorthIncrease,stefan,7.1,¥337 +Has,AR,¥45 +Has,IR,¥0 +Has,SR,¥158 +Has,KO,¥0 +Has,TR,¥71 +Has,KU,¥0 +Has,UR,¥0 +Has,klaus,¥29 +Has,Josha,¥346 +Has,bernd,¥183 +Has,stefan,¥1429 +START_OR,7.2 +ReceivesFor,stefan,¥50,G + +CompanyOperates,KU,bernd +CompanyRevenue,KU,¥240 +CompanyPaysOutFull,KU,¥240 +Payout,stefan,¥24,1,10 +Payout,Josha,¥24,1,10 +Payout,bernd,¥96,4,10 +Payout,KU,¥96,4,10 +PRICE_MOVES_LOG,KU,¥90,G5,¥100,H5 + +CompanyOperates,UR,bernd +CompanyRevenue,UR,¥390 +CompanyPaysOutFull,UR,¥390 +Payout,stefan,¥78,2,10 +Payout,Josha,¥39,1,10 +Payout,bernd,¥156,4,10 +Payout,UR,¥117,3,10 +PRICE_MOVES_LOG,UR,¥90,G5,¥100,H5 + +CompanyOperates,SR,stefan +LaysTileAt,SR,26,B5,N +CompanyRevenue,SR,¥450 +CompanyPaysOutFull,SR,¥450 +Payout,stefan,¥225,5,10 +Payout,bernd,¥90,2,10 +Payout,Josha,¥90,2,10 +Payout,SR,¥45,1,10 +PRICE_MOVES_LOG,SR,¥90,G5,¥100,H5 + +CompanyOperates,KO,klaus +CompanyRevenue,KO,¥530 +CompanyPaysOutFull,KO,¥530 +Payout,stefan,¥53,1,10 +Payout,bernd,¥53,1,10 +Payout,Josha,¥53,1,10 +Payout,klaus,¥212,4,10 +Payout,KO,¥159,3,10 +PRICE_MOVES_LOG,KO,¥80,G6,¥90,G5 + +CompanyOperates,IR,klaus +CompanyRevenue,IR,¥530 +CompanyPaysOutFull,IR,¥530 +Payout,stefan,¥106,2,10 +Payout,bernd,¥53,1,10 +Payout,Josha,¥53,1,10 +Payout,klaus,¥318,6,10 +PRICE_MOVES_LOG,IR,¥80,F5,¥90,G5 + +CompanyOperates,TR,Josha +CompanyRevenue,TR,¥530 +CompanyPaysOutFull,TR,¥530 +Payout,bernd,¥53,1,10 +Payout,Josha,¥265,5,10 +Payout,TR,¥212,4,10 +PRICE_MOVES_LOG,TR,¥75,F6,¥80,G6 + +CompanyOperates,AR,Josha +CompanyRevenue,AR,¥440 +CompanyPaysOutFull,AR,¥440 +Payout,stefan,¥132,3,10 +Payout,Josha,¥220,5,10 +Payout,bernd,¥44,1,10 +Payout,AR,¥44,1,10 +PRICE_MOVES_LOG,AR,¥60,B5,¥65,C5 + +EndOfOperatingRound,7.2 +ORWorthIncrease,klaus,7.2,¥630 +ORWorthIncrease,Josha,7.2,¥854 +ORWorthIncrease,bernd,7.2,¥675 +ORWorthIncrease,stefan,7.2,¥793 +Has,AR,¥89 +Has,IR,¥0 +Has,SR,¥203 +Has,KO,¥159 +Has,TR,¥283 +Has,KU,¥96 +Has,UR,¥117 +Has,klaus,¥559 +Has,Josha,¥1090 +Has,bernd,¥728 +Has,stefan,¥2097 +START_OR,7.3 +ReceivesFor,stefan,¥50,G + +CompanyOperates,KU,bernd +LaysTileAtFor,KU,9,K6,S,¥80 +CompanyRevenue,KU,¥260 +CompanyPaysOutFull,KU,¥260 +Payout,stefan,¥26,1,10 +Payout,Josha,¥26,1,10 +Payout,bernd,¥104,4,10 +Payout,KU,¥104,4,10 +PRICE_MOVES_LOG,KU,¥100,H5,¥110,H4 + +CompanyOperates,UR,bernd +CompanyRevenue,UR,¥560 +CompanyPaysOutFull,UR,¥560 +Payout,stefan,¥112,2,10 +Payout,Josha,¥56,1,10 +Payout,bernd,¥224,4,10 +Payout,UR,¥168,3,10 +PRICE_MOVES_LOG,UR,¥100,H5,¥110,H4 + +CompanyOperates,SR,stefan +CompanyRevenue,SR,¥470 +CompanyPaysOutFull,SR,¥470 +Payout,stefan,¥235,5,10 +Payout,Josha,¥94,2,10 +Payout,bernd,¥94,2,10 +Payout,SR,¥47,1,10 +PRICE_MOVES_LOG,SR,¥100,H5,¥110,H4 + +CompanyOperates,KO,klaus +LaysTileAtFor,KO,492,I4,S,¥80 +CompanyRevenue,KO,¥580 +CompanyPaysOutFull,KO,¥580 +Payout,stefan,¥58,1,10 +Payout,Josha,¥58,1,10 +Payout,bernd,¥58,1,10 +Payout,klaus,¥232,4,10 +BankIsBrokenReportText +Payout,KO,¥174,3,10 +PRICE_MOVES_LOG,KO,¥90,G5,¥100,H5 + +CompanyOperates,IR,klaus +CompanyRevenue,IR,¥720 +CompanyPaysOutFull,IR,¥720 +Payout,stefan,¥144,2,10 +Payout,Josha,¥72,1,10 +Payout,bernd,¥72,1,10 +Payout,klaus,¥432,6,10 +PRICE_MOVES_LOG,IR,¥90,G5,¥100,H5 + +CompanyOperates,TR,Josha +LaysTileAtFor,TR,8,A8,NE,¥80 +CompanyRevenue,TR,¥720 +CompanyPaysOutFull,TR,¥720 +Payout,Josha,¥360,5,10 +Payout,bernd,¥72,1,10 +Payout,TR,¥288,4,10 +PRICE_MOVES_LOG,TR,¥80,G6,¥90,G5 + +CompanyOperates,AR,Josha +LaysTileAt,AR,6,A10,S +CompanyRevenue,AR,¥500 +CompanyPaysOutFull,AR,¥500 +Payout,stefan,¥150,3,10 +Payout,Josha,¥250,5,10 +Payout,bernd,¥50,1,10 +Payout,AR,¥50,1,10 +PRICE_MOVES_LOG,AR,¥65,C5,¥70,D5 + +EndOfOperatingRound,7.3 +ORWorthIncrease,klaus,7.3,¥764 +ORWorthIncrease,Josha,7.3,¥1051 +ORWorthIncrease,bernd,7.3,¥809 +ORWorthIncrease,stefan,7.3,¥900 +Has,AR,¥139 +Has,IR,¥0 +Has,SR,¥250 +Has,KO,¥253 +Has,TR,¥491 +Has,KU,¥120 +Has,UR,¥285 +Has,klaus,¥1223 +Has,Josha,¥2006 +Has,bernd,¥1402 +Has,stefan,¥2872 +GameOver +EoGWinnerstefan! +EoGFinalRanking : +1. ¥4412 stefan +2. ¥3446 Josha +3. ¥2862 bernd +4. ¥2223 klaus diff --git a/test/data/real/1889_C.report b/test/data/real/1889_C.report index 60ac6da..e947ecd 100644 --- a/test/data/real/1889_C.report +++ b/test/data/real/1889_C.report @@ -1,3 +1,4 @@ +GameIs,1889 PlayerIs,1,Klaus PlayerIs,2,Henning PlayerIs,3,Stefan diff --git a/test/data/real/18AL_A.report b/test/data/real/18AL_A.report index 25eeac4..d613d80 100644 --- a/test/data/real/18AL_A.report +++ b/test/data/real/18AL_A.report @@ -1,3 +1,4 @@ +GameIs,18AL PlayerIs,1,Jim PlayerIs,2,Steve PlayerIs,3,Peter diff --git a/test/data/real/18EU_A.report b/test/data/real/18EU_A.report index bf80b12..80caf8f 100644 --- a/test/data/real/18EU_A.report +++ b/test/data/real/18EU_A.report @@ -1,3 +1,4 @@ +GameIs,18EU PlayerIs,1,Chris PlayerIs,2,Joakim PlayerIs,3,Joshua diff --git a/test/data/test/1835_PR_3rdTrain.report b/test/data/test/1835_PR_3rdTrain.report index 58ede86..ebd8e66 100644 --- a/test/data/test/1835_PR_3rdTrain.report +++ b/test/data/test/1835_PR_3rdTrain.report @@ -1,3 +1,4 @@ +GameIs,1835 PlayerIs,1,Alice PlayerIs,2,Bob PlayerIs,3,Charlie diff --git a/test/data/test/1851_Late.report b/test/data/test/1851_Late.report index 1aece90..38fc142 100644 --- a/test/data/test/1851_Late.report +++ b/test/data/test/1851_Late.report @@ -1,3 +1,4 @@ +GameIs,1851 PlayerIs,1,Alice PlayerIs,2,Bob PlayerIs,3,Charlie diff --git a/test/data/test/1856_2nd6T+PrezCash2.report b/test/data/test/1856_2nd6T+PrezCash2.report index d4f8fd4..2b3b52b 100644 --- a/test/data/test/1856_2nd6T+PrezCash2.report +++ b/test/data/test/1856_2nd6T+PrezCash2.report @@ -1,3 +1,4 @@ +GameIs,1856 PlayerIs,1,Alice PlayerIs,2,Bob PlayerIs,3,Charlie diff --git a/test/data/test/18EU_After2nd8Train.report b/test/data/test/18EU_After2nd8Train.report index c100dc8..3ab8275 100644 --- a/test/data/test/18EU_After2nd8Train.report +++ b/test/data/test/18EU_After2nd8Train.report @@ -1,3 +1,4 @@ +GameIs,18EU PlayerIs,1,Alice PlayerIs,2,Bob PlayerIs,3,Charlie |
From: Erik V. <ev...@us...> - 2011-08-03 21:12:01
|
rails/game/MapManager.java | 88 +++---- rails/game/correct/MapCorrectionManager.java | 71 ++---- rails/game/state/HashMapState.java | 39 +-- rails/ui/swing/UpgradesPanel.java | 32 +- rails/util/ListAndFixSavedFiles.java | 299 -------------------------- rails/util/Util.java | 34 ++- tools/ListAndFixSavedFiles.java | 301 +++++++++++++++++++++++++++ tools/Util.java | 37 --- tools/XmlUtils.java | 2 9 files changed, 431 insertions(+), 472 deletions(-) New commits: commit 66795c3b6fc0a5c416cad30dd7af0ac7316a67b1 Author: Erik Vos <eri...@xs...> Date: Wed Aug 3 23:10:21 2011 +0200 Minor tools/util refactoring. Moved ListAndFixSavedFiles to tools. Merged tools.Util into rails.util.Util. diff --git a/rails/game/MapManager.java b/rails/game/MapManager.java index f40e509..8ec32be 100644 --- a/rails/game/MapManager.java +++ b/rails/game/MapManager.java @@ -5,11 +5,7 @@ import java.util.*; import org.apache.log4j.Logger; -import rails.common.parser.Config; -import rails.common.parser.ConfigurableComponentI; -import rails.common.parser.ConfigurationException; -import rails.common.parser.Tag; -import tools.Util; +import rails.common.parser.*; /** * MapManager configures the map layout from XML @@ -23,7 +19,7 @@ public class MapManager implements ConfigurableComponentI { protected TileOrientation tileOrientation; protected boolean lettersGoHorizontal; protected boolean letterAHasEvenNumbers; - + // Optional map image (SVG file) protected String mapImageFilename = null; protected String mapImageFilepath = null; @@ -43,13 +39,13 @@ public class MapManager implements ConfigurableComponentI { // information to define neighbours protected static final int[] xDeltaNS = new int[] { 0, -1, -1, 0, +1, +1 }; protected static final int[] yXEvenDeltaNS = - new int[] { +1, 0, -1, -1, -1, 0 }; + new int[] { +1, 0, -1, -1, -1, 0 }; protected static final int[] yXOddDeltaNS = - new int[] { +1, +1, 0, -1, 0, +1 }; + new int[] { +1, +1, 0, -1, 0, +1 }; protected static final int[] xYEvenDeltaEW = - new int[] { -1, -1, -1, 0, +1, 0 }; + new int[] { -1, -1, -1, 0, +1, 0 }; protected static final int[] xYOddDeltaEW = - new int[] { 0, -1, 0, +1, +1, +1 }; + new int[] { 0, -1, 0, +1, +1, +1 }; protected static final int[] yDeltaEW = new int[] { +1, 0, -1, -1, 0, +1 }; protected static Logger log = @@ -91,7 +87,7 @@ public class MapManager implements ConfigurableComponentI { lettersGoHorizontal = false; } else { throw new ConfigurationException("Invalid letter orientation: " - + attr); + + attr); } attr = tag.getAttributeAsString("even"); @@ -130,7 +126,7 @@ public class MapManager implements ConfigurableComponentI { } } log.debug("Possible tileCosts on map are "+possibleTileCosts); - + int xOffset = 0; int yOffset = 0; if (minX < 0) { @@ -161,16 +157,16 @@ public class MapManager implements ConfigurableComponentI { int i, j, k; MapHex nb; - mapImageUsed = Util.hasValue(mapImageFilename) - && "yes".equalsIgnoreCase(Config.get("map.image.display")); + mapImageUsed = rails.util.Util.hasValue(mapImageFilename) + && "yes".equalsIgnoreCase(Config.get("map.image.display")); if (mapImageUsed) { String rootDirectory = Config.get("map.root_directory"); - if (!Util.hasValue(rootDirectory)) { + if (!rails.util.Util.hasValue(rootDirectory)) { rootDirectory = "data"; } mapImageFilepath = rootDirectory + "/" + mapImageFilename; } - + for (String hexName : mHexes.keySet()) { hex = mHexes.get(hexName); hex.finishConfiguration(gameManager); @@ -227,22 +223,22 @@ public class MapManager implements ConfigurableComponentI { public boolean lettersGoHorizontal() { return lettersGoHorizontal; } - + public int getAdjacentX (int x, int y, int orientation) { - - if (tileOrientation == TileOrientation.EW) { + + if (tileOrientation == TileOrientation.EW) { return x + (y % 2 == 0 ? xYEvenDeltaEW[orientation] : xYOddDeltaEW[orientation]); - } else { + } else { return x + xDeltaNS[orientation]; - } + } } - + public int getAdjacentY (int x, int y, int orientation) { - + if (tileOrientation == TileOrientation.EW) { return y + yDeltaEW[orientation]; } else { - return y + ((x % 2 == 0) == letterAHasEvenNumbers ? + return y + ((x % 2 == 0) == letterAHasEvenNumbers ? yXEvenDeltaNS[orientation] : yXOddDeltaNS[orientation]); } } @@ -260,7 +256,7 @@ public class MapManager implements ConfigurableComponentI { public MapHex[][] getHexes() { return hexes; } - + public List<MapHex> getHexesAsList() { return new ArrayList<MapHex>(mHexes.values()); } @@ -348,31 +344,31 @@ public class MapManager implements ConfigurableComponentI { */ public int getHexDistance (MapHex hex1, MapHex hex2) { - if (distances == null) distances = new HashMap<MapHex, Map<MapHex, Integer>> (); - if (distances.get(hex1) == null) { - distances.put(hex1, new HashMap<MapHex, Integer>()); - calculateHexDistances(hex1, hex1, 0); - } - return distances.get(hex1).get(hex2); + if (distances == null) distances = new HashMap<MapHex, Map<MapHex, Integer>> (); + if (distances.get(hex1) == null) { + distances.put(hex1, new HashMap<MapHex, Integer>()); + calculateHexDistances(hex1, hex1, 0); + } + return distances.get(hex1).get(hex2); } private void calculateHexDistances (MapHex hex1, MapHex hex2, int depth) { - if (distances.get(hex1).get(hex2) == null) { - distances.get(hex1).put(hex2, depth); - } else { - if (distances.get(hex1).get(hex2) <= depth) return; - distances.get(hex1).put(hex2, depth); - } - - for (MapHex hex3 : hex2.getNeighbors()) { - if (hex3 == null) continue; - if (distances.get(hex1).get(hex3) == null) { - calculateHexDistances (hex1, hex3, depth+1); - } else if (distances.get(hex1).get(hex3) > depth+1) { - calculateHexDistances (hex1, hex3, depth+1); - } - } + if (distances.get(hex1).get(hex2) == null) { + distances.get(hex1).put(hex2, depth); + } else { + if (distances.get(hex1).get(hex2) <= depth) return; + distances.get(hex1).put(hex2, depth); + } + + for (MapHex hex3 : hex2.getNeighbors()) { + if (hex3 == null) continue; + if (distances.get(hex1).get(hex3) == null) { + calculateHexDistances (hex1, hex3, depth+1); + } else if (distances.get(hex1).get(hex3) > depth+1) { + calculateHexDistances (hex1, hex3, depth+1); + } + } } /** Cache to hold all unique distance values of tokenable cities from a given hex */ diff --git a/rails/game/correct/MapCorrectionManager.java b/rails/game/correct/MapCorrectionManager.java index 43716f2..39a210b 100644 --- a/rails/game/correct/MapCorrectionManager.java +++ b/rails/game/correct/MapCorrectionManager.java @@ -1,53 +1,42 @@ package rails.game.correct; -import java.util.ArrayList; -import java.util.HashMap; -import java.util.List; +import java.util.*; import rails.common.DisplayBuffer; import rails.common.LocalText; -import rails.game.BaseToken; -import rails.game.City; -import rails.game.GameManager; -import rails.game.MapHex; -import rails.game.ReportBuffer; -import rails.game.Station; -import rails.game.TileI; -import rails.game.TileManager; -import rails.game.TokenI; -import tools.Util; +import rails.game.*; public class MapCorrectionManager extends CorrectionManager { - + public static enum ActionStep { SELECT_HEX,SELECT_TILE,SELECT_ORIENTATION,CONFIRM,RELAY_BASETOKENS,FINISHED,CANCELLED; } - + private MapCorrectionAction activeTileAction = null; - + protected MapCorrectionManager(GameManager gm) { super(gm, CorrectionType.CORRECT_MAP); } - + @Override public List<CorrectionAction> createCorrections() { List<CorrectionAction> actions = super.createCorrections(); - + if (isActive()) { if (activeTileAction == null) activeTileAction = new MapCorrectionAction(); actions.add(activeTileAction); } - + return actions; } - + @Override public boolean executeCorrection(CorrectionAction action){ if (action instanceof MapCorrectionAction) return execute((MapCorrectionAction) action); else // any other action, could be a correctionMode action - return super.executeCorrection(action); + return super.executeCorrection(action); } private boolean execute(MapCorrectionAction action){ @@ -60,18 +49,18 @@ public class MapCorrectionManager extends CorrectionManager { activeTileAction = null; return true; } - + MapHex hex = action.getLocation(); - + TileI chosenTile = action.getChosenTile(); TileManager tmgr = gameManager.getTileManager(); TileI preprintedTile = tmgr.getTile(hex.getPreprintedTileId()); - // check conditions + // check conditions String errMsg = null; while (true) { // check if chosenTile is still available (not for preprinted) - if (chosenTile != null && Util.hasValue(chosenTile.getExternalId()) + if (chosenTile != null && rails.util.Util.hasValue(chosenTile.getExternalId()) && chosenTile != hex.getCurrentTile() && chosenTile.countFreeTiles() == 0) { errMsg = @@ -100,7 +89,7 @@ public class MapCorrectionManager extends CorrectionManager { } // check if chosenTile requires relays // this is not implemented yet, thus error message - if (chosenTile.getNumStations() >= 2 + if (chosenTile.getNumStations() >= 2 && hex.getCurrentTile().getColourNumber() >= chosenTile.getColourNumber() // B. or the current tile requires relays || hex.getCurrentTile().relayBaseTokensOnUpgrade()) { @@ -131,7 +120,7 @@ public class MapCorrectionManager extends CorrectionManager { // preparation for the next step switch (nextStep) { - case SELECT_TILE: + case SELECT_TILE: // create list of possible up and downgrades List<TileI> possibleTiles = tmgr.getAllUpgrades(preprintedTile, hex); if (preprintedTile == hex.getCurrentTile()) @@ -153,10 +142,10 @@ public class MapCorrectionManager extends CorrectionManager { } case RELAY_BASETOKENS: // check if relays are necessary: - // A. downgrades or equalgrades to a tile with two stations or more - if (chosenTile.getNumStations() >= 2 + // A. downgrades or equalgrades to a tile with two stations or more + if (chosenTile.getNumStations() >= 2 && hex.getCurrentTile().getColourNumber() >= chosenTile.getColourNumber() - // B. or the current tile requires relays + // B. or the current tile requires relays || hex.getCurrentTile().relayBaseTokensOnUpgrade()) { // define tokens for relays List<BaseToken> tokens = new ArrayList<BaseToken>(); @@ -178,27 +167,27 @@ public class MapCorrectionManager extends CorrectionManager { } case FINISHED: gameManager.getMoveStack().start(false); - + // lays tile int orientation = action.getOrientation(); hex.upgrade(chosenTile, orientation, new HashMap<String,Integer>()); - + String msg = LocalText.getText("CorrectMapLaysTileAt", chosenTile.getExternalId(), hex.getName(), hex.getOrientationName(orientation)); ReportBuffer.add(msg); gameManager.addToNextPlayerMessages(msg, true); // relays tokens -// if (action.getTokensToRelay() != null) { -// for (BaseToken token:action.getTokensToRelay()) { -// int i = action.getTokensToRelay().indexOf(token); -// -// } -// } - + // if (action.getTokensToRelay() != null) { + // for (BaseToken token:action.getTokensToRelay()) { + // int i = action.getTokensToRelay().indexOf(token); + // + // } + // } + activeTileAction = null; break; - + case CANCELLED: // should be captured above activeTileAction = null; @@ -207,7 +196,7 @@ public class MapCorrectionManager extends CorrectionManager { if (action.getStep() != ActionStep.FINISHED) { action.moveToNextStep(); } - + return true; } } diff --git a/rails/game/state/HashMapState.java b/rails/game/state/HashMapState.java index 225346d..5e1fe9e 100644 --- a/rails/game/state/HashMapState.java +++ b/rails/game/state/HashMapState.java @@ -1,17 +1,10 @@ package rails.game.state; -import java.util.ArrayList; -import java.util.Collection; -import java.util.Collections; -import java.util.HashMap; -import java.util.List; -import java.util.Map; -import java.util.Set; +import java.util.*; import rails.game.model.ModelObject; import rails.game.move.MapChange; import rails.game.move.RemoveFromMap; -import tools.Util; /** * State class that wraps a HashMap @@ -29,7 +22,7 @@ public class HashMapState<K,V> extends ModelObject { private final HashMap<K,V> map = new HashMap<K,V>(); private String mapName; - + /** * constructor for an empty map */ @@ -42,29 +35,29 @@ public class HashMapState<K,V> extends ModelObject { public HashMapState(String listName, Map<K,V> map) { this(listName); } - + public void put(K key, V value) { new MapChange<K,V>(map, key, value, this); } - + public void putAll(Map<K,V> map) { for (K key:map.keySet()) { new MapChange<K,V>(map, key, map.get(key), this); } } - + public V get(K key) { return map.get(key); } - + public void remove(K key) { - new RemoveFromMap<K,V>(map, key, this); + new RemoveFromMap<K,V>(map, key, this); } - + public boolean hasKey(K key) { return map.containsKey(key); } - + public void clear() { // Two-step process to avoid concurrent modification exception List<K> keys = new ArrayList<K>(); @@ -98,8 +91,8 @@ public class HashMapState<K,V> extends ModelObject { } update(); } - - /** + + /** * @return unmodifiable view of map */ public Map<K,V> viewMap() { @@ -111,26 +104,26 @@ public class HashMapState<K,V> extends ModelObject { public Set<K> viewKeySet() { return Collections.unmodifiableSet(map.keySet()); } - + public Collection<V> viewValues() { return Collections.unmodifiableCollection(map.values()); } - + public boolean isEmpty() { return map.isEmpty(); } - + @Override public String getText() { if (map == null) return ""; - + StringBuilder buf = new StringBuilder("<html>"); for (K name : map.keySet()) { if (buf.length() > 6) buf.append("<br>"); buf.append(name.toString()); Object value = map.get(name); - if (value != null && Util.hasValue(value.toString())) buf.append("=").append(value.toString()); + if (value != null && rails.util.Util.hasValue(value.toString())) buf.append("=").append(value.toString()); } if (buf.length() > 6) { buf.append("</html>"); diff --git a/rails/ui/swing/UpgradesPanel.java b/rails/ui/swing/UpgradesPanel.java index 15b258c..0d9f925 100644 --- a/rails/ui/swing/UpgradesPanel.java +++ b/rails/ui/swing/UpgradesPanel.java @@ -4,9 +4,8 @@ package rails.ui.swing; import java.awt.*; import java.awt.event.*; import java.awt.image.BufferedImage; -import java.util.ArrayList; +import java.util.*; import java.util.List; -import java.util.Set; import javax.swing.*; import javax.swing.border.Border; @@ -21,7 +20,6 @@ import rails.game.correct.MapCorrectionAction; import rails.ui.swing.elements.ActionLabel; import rails.ui.swing.hexmap.GUIHex; import rails.ui.swing.hexmap.HexMap; -import tools.Util; public class UpgradesPanel extends Box implements MouseListener, ActionListener { private static final long serialVersionUID = 1L; @@ -45,12 +43,12 @@ public class UpgradesPanel extends Box implements MouseListener, ActionListener private boolean tokenMode = false; private boolean correctionTokenMode = false; private JButton cancelButton = - new JButton(LocalText.getText(INIT_CANCEL_TEXT)); + new JButton(LocalText.getText(INIT_CANCEL_TEXT)); private JButton doneButton = new JButton(LocalText.getText(INIT_DONE_TEXT)); private HexMap hexMap; protected static Logger log = - Logger.getLogger(UpgradesPanel.class.getPackage().getName()); + Logger.getLogger(UpgradesPanel.class.getPackage().getName()); public UpgradesPanel(ORUIManager orUIManager) { super(BoxLayout.Y_AXIS); @@ -94,12 +92,12 @@ public class UpgradesPanel extends Box implements MouseListener, ActionListener for (LayTile layTile : hexMap.getTileAllowancesForHex(hex)) { tiles = layTile.getTiles(); - if (tiles == null) { + if (tiles == null) { for (TileI tile : uiHex.getCurrentTile().getValidUpgrades(hex, orUIManager.gameUIManager.getCurrentPhase())) { // Skip if not allowed in LayTile //if (!layTile.isTileColourAllowed(tile.getColourName())) continue; - + if (!orUIManager.tileUpgrades.contains(tile)) orUIManager.tileUpgrades.add(tile); } @@ -123,7 +121,7 @@ public class UpgradesPanel extends Box implements MouseListener, ActionListener panelLayout.setRows(defaultNbPanelElements); if (tokenMode && possibleTokenLays != null - && possibleTokenLays.size() > 0) { + && possibleTokenLays.size() > 0) { Color fgColour = null; Color bgColour = null; @@ -145,7 +143,7 @@ public class UpgradesPanel extends Box implements MouseListener, ActionListener fgColour = Color.BLACK; bgColour = Color.WHITE; BonusToken token = - (BonusToken) action.getSpecialProperty().getToken(); + (BonusToken) action.getSpecialProperty().getToken(); description = token.getName(); text = "+" + token.getValue(); } @@ -245,7 +243,7 @@ public class UpgradesPanel extends Box implements MouseListener, ActionListener upgradePanel.add(doneButton); upgradePanel.add(cancelButton); -// repaint(); + // repaint(); revalidate(); } @@ -298,7 +296,7 @@ public class UpgradesPanel extends Box implements MouseListener, ActionListener upgradePanel.add(doneButton); upgradePanel.add(cancelButton); -// repaint(); + // repaint(); revalidate(); } @@ -312,7 +310,7 @@ public class UpgradesPanel extends Box implements MouseListener, ActionListener public void setSelectedTokenIndex(int index) { log.debug("Selected token index from " + selectedTokenIndex + " to " - + index); + + index); selectedTokenIndex = index; } @@ -474,7 +472,7 @@ public class UpgradesPanel extends Box implements MouseListener, ActionListener super(tokenIcon); this.token = token; } - + } /** JLabel extension to allow attaching the internal hex ID */ @@ -501,7 +499,7 @@ public class UpgradesPanel extends Box implements MouseListener, ActionListener void setTextFromTile(TileI tile) { StringBuffer text = new StringBuffer(); - if (Util.hasValue(tile.getExternalId())) { + if (rails.util.Util.hasValue(tile.getExternalId())) { text.append("<HTML><BODY>" + tile.getExternalId()); if (tile.countFreeTiles() != -1) { text.append("<BR> (" + tile.countFreeTiles() + ")"); @@ -515,7 +513,7 @@ public class UpgradesPanel extends Box implements MouseListener, ActionListener TileI currentTile = orUIManager.getGameUIManager().getGameManager().getTileManager().getTile(internalId); StringBuffer tt = new StringBuffer("<html>"); tt.append("<b>Tile</b>: ").append(currentTile.getName()); // or - // getId() + // getId() if (currentTile.hasStations()) { // for (Station st : currentTile.getStations()) int cityNumber = 0; @@ -524,11 +522,11 @@ public class UpgradesPanel extends Box implements MouseListener, ActionListener cityNumber++; // = city.getNumber(); tt.append("<br> ").append(st.getType()).append(" ").append( cityNumber) // .append("/").append(st.getNumber()) - .append(": value "); + .append(": value "); tt.append(st.getValue()); if (st.getBaseSlots() > 0) { tt.append(", ").append(st.getBaseSlots()).append( - " slots"); + " slots"); } } } diff --git a/rails/util/ListAndFixSavedFiles.java b/rails/util/ListAndFixSavedFiles.java deleted file mode 100644 index 11a6938..0000000 --- a/rails/util/ListAndFixSavedFiles.java +++ /dev/null @@ -1,299 +0,0 @@ -package rails.util; - -import java.awt.*; -import java.awt.event.*; -import java.io.*; -import java.util.*; -import java.util.List; - -import javax.swing.*; - -import org.apache.log4j.Logger; - -import rails.common.DisplayBuffer; -import rails.common.LocalText; -import rails.common.parser.Config; -import rails.common.parser.ConfigurationException; -import rails.game.*; -import rails.game.action.PossibleAction; -import rails.ui.swing.elements.ActionMenuItem; - -public class ListAndFixSavedFiles extends JFrame -implements ActionListener, KeyListener { - - private static final long serialVersionUID = 1L; - private JTextArea reportText; - private JScrollPane messageScroller; - private JScrollBar vbar; - private JPanel messagePanel; - private ListAndFixSavedFiles messageWindow; - private JMenuBar menuBar; - private JMenu fileMenu, editMenu; - private JMenuItem saveItem, loadItem; - private JMenuItem trimItem, deleteItem; - - private StringBuffer headerText = new StringBuffer(); - - private GameFileIO fileIO; - - private int vbarPos; - - private static String saveDirectory; - private String filepath; - - protected static Logger log; - - /** - * @param args - */ - public static void main(String[] args) { - - // intialize configuration - Config.setConfigSelection(); - - // delayed setting of logger - log = Logger.getLogger(ListAndFixSavedFiles.class.getPackage().getName()); - - saveDirectory = Config.get("save.directory"); - System.out.println("Save directory = " + saveDirectory); - - new ListAndFixSavedFiles (); - - } - - public ListAndFixSavedFiles () { - - super(); - - messageWindow = this; - - reportText = new JTextArea(); - reportText.setEditable(false); - reportText.setLineWrap(false); - reportText.setBackground(Color.WHITE); - reportText.setOpaque(true); - reportText.setBorder(BorderFactory.createEmptyBorder(5, 5, 5, 5)); - - messagePanel = new JPanel(new GridBagLayout()); - messageScroller = - new JScrollPane(reportText, - ScrollPaneConstants.VERTICAL_SCROLLBAR_ALWAYS, - ScrollPaneConstants.HORIZONTAL_SCROLLBAR_AS_NEEDED); - vbar = messageScroller.getVerticalScrollBar(); - GridBagConstraints gbc = new GridBagConstraints(); - gbc.gridx = gbc.gridy = 0; - gbc.weightx = gbc.weighty = 1.0; - gbc.fill = GridBagConstraints.BOTH; - messagePanel.add(messageScroller, gbc); - - menuBar = new JMenuBar(); - fileMenu = new JMenu(LocalText.getText("FILE")); - fileMenu.setMnemonic(KeyEvent.VK_F); - editMenu = new JMenu(LocalText.getText("EDIT")); - editMenu.setMnemonic(KeyEvent.VK_E); - - loadItem = new ActionMenuItem(LocalText.getText("LOAD")); - loadItem.setActionCommand("LOAD"); - loadItem.setMnemonic(KeyEvent.VK_L); - loadItem.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_L, - ActionEvent.ALT_MASK)); - loadItem.addActionListener(this); - loadItem.setEnabled(true); - fileMenu.add(loadItem); - - saveItem = new ActionMenuItem(LocalText.getText("SAVE")); - saveItem.setActionCommand("SAVE"); - saveItem.setMnemonic(KeyEvent.VK_S); - saveItem.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_S, - ActionEvent.ALT_MASK)); - saveItem.addActionListener(this); - saveItem.setEnabled(true); - fileMenu.add(saveItem); - - trimItem = new ActionMenuItem("Trim"); - trimItem.setActionCommand("TRIM"); - trimItem.setMnemonic(KeyEvent.VK_T); - trimItem.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_T, - ActionEvent.ALT_MASK)); - trimItem.addActionListener(this); - trimItem.setEnabled(true); - editMenu.add(trimItem); - - deleteItem = new ActionMenuItem("Delete"); - deleteItem.setActionCommand("DELETE"); - deleteItem.setMnemonic(KeyEvent.VK_D); - deleteItem.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_D, - ActionEvent.ALT_MASK)); - deleteItem.addActionListener(this); - deleteItem.setEnabled(true); - editMenu.add(deleteItem); - - menuBar.add(fileMenu); - menuBar.add(editMenu); - - setJMenuBar(menuBar); - - setContentPane(messagePanel); - - setSize(400, 400); - setLocation(600, 400); - setTitle("List and fix saved files"); - - addKeyListener(this); - - - setVisible(true); - - saveDirectory = Config.get("save.directory"); - - load(); - - } - - private void load() { - - JFileChooser jfc = new JFileChooser(); - jfc.setCurrentDirectory(new File(saveDirectory)); - - if (jfc.showOpenDialog(getContentPane()) == JFileChooser.APPROVE_OPTION) { - - File selectedFile = jfc.getSelectedFile(); - filepath = selectedFile.getPath(); - saveDirectory = selectedFile.getParent(); - - // clear header text - headerText = new StringBuffer(); - - // use GameLoader object to load game - fileIO = new GameFileIO(); - - fileIO.loadGameData(filepath); - add(fileIO.getGameDataAsText()); - try{ - fileIO.initGame(); - fileIO.loadActionsAndComments(); - setReportText(true); - - } catch (ConfigurationException e) { - log.fatal("Load failed", e); - DisplayBuffer.add(LocalText.getText("LoadFailed", e.getMessage())); - } - } - - } - - public void add (String text) { - if (text.length() > 0) { - headerText.append(text); - headerText.append("\n"); - } - } - - private void setReportText(boolean initial) { - if (initial) - vbarPos = -1; - else - vbarPos = this.vbar.getValue(); - - reportText.setText(headerText.toString()); - // append actionText - int i=0; - for (PossibleAction action : fileIO.getActions()) { - reportText.append("Action "+i+" "+action.getPlayerName()+": "+action.toString()); - reportText.append("\n"); - // check for comments for this action - String comment = fileIO.getComments().get(i); - if (comment!= null) { - reportText.append("Comment to action " + i + ": " + comment + "\n"); - } - i++; - } - scrollDown(vbarPos); - } - - - public void scrollDown (int pos) { - SwingUtilities.invokeLater(new Runnable() { - public void run() { - if (vbarPos == -1) - messageWindow.vbar.setValue(messageWindow.vbar.getMaximum()); - else - messageWindow.vbar.setValue(vbarPos); - } - }); - } - - - - public void actionPerformed(ActionEvent actor) { - String command = actor.getActionCommand(); - if ("TRIM".equalsIgnoreCase(command)) { - String result = JOptionPane.showInputDialog("Enter last action number to be retained"); - if (Util.hasValue(result)) { - try { - int index = Integer.parseInt(result); - // delete actions - int size = fileIO.getActions().size(); - fileIO.getActions().subList(index + 1, size).clear(); - // delete comments - for (int id = 0; id < size; id++) { - if (id > index) { - fileIO.getComments().remove(id); - } - } - setReportText(false); - } catch (NumberFormatException e) { - - } - } - } else if ("DELETE".equalsIgnoreCase(command)) { - String result = JOptionPane.showInputDialog("Enter action number to be deleted"); - if (Util.hasValue(result)) { - try { - int index = Integer.parseInt(result); - fileIO.getActions().remove(index); - // delete and renumber in user Comments - SortedMap<Integer, String> newComments = new TreeMap<Integer, String>(); - for (Integer id:fileIO.getComments().keySet()) { - if (id < index) { - newComments.put(id, fileIO.getComments().get(id)); - } else if (id > index) { - newComments.put(id-1, fileIO.getComments().get(id)); - } - } - fileIO.setComments(newComments); - setReportText(false); - } catch (NumberFormatException e) { - log.error("Number format exception for '"+result+"'", e); - } - } - } else if ("SAVE".equalsIgnoreCase(command)) { - save(); - } else if ("LOAD".equalsIgnoreCase(command)) { - load(); - } - } - - private void save() { - JFileChooser jfc = new JFileChooser(); - if (Util.hasValue(saveDirectory)) { - jfc.setCurrentDirectory(new File(saveDirectory)); - } - if (Util.hasValue(filepath)) { - jfc.setSelectedFile(new File(filepath)); - } - if (jfc.showSaveDialog(this) == JFileChooser.APPROVE_OPTION) { - File selectedFile = jfc.getSelectedFile(); - fileIO.saveGame(selectedFile, true, "SaveFailed"); - } - - } - - public void keyPressed(KeyEvent e) { - } - - public void keyReleased(KeyEvent e) {} - - public void keyTyped(KeyEvent e) {} - -} diff --git a/rails/util/Util.java b/rails/util/Util.java index 2e20814..e558719 100644 --- a/rails/util/Util.java +++ b/rails/util/Util.java @@ -2,6 +2,7 @@ package rails.util; import java.awt.Color; +import java.io.*; import java.util.ArrayList; import java.util.List; @@ -79,7 +80,7 @@ public final class Util { } } - + /** * Convert java string to html string * Transformations: @@ -88,9 +89,9 @@ public final class Util { public static String convertToHtml(String javaString) { return javaString.replace("\n", "<br>"); } - - - + + + /** * Safely move a list of objects from one holder to another, avoiding * ConcurrentModificationExceptions. @@ -148,7 +149,7 @@ public final class Util { } return Boolean.parseBoolean(s); } - + /** * Parse a colour definition string. * Currently supported formats: @@ -183,9 +184,9 @@ public final class Util { return c; } - - - + + + /** * Is a colour dark? (to check if FG colour needs be reversed) */ @@ -207,4 +208,21 @@ public final class Util { public static String lowerCaseFirst (String text) { return text.substring(0, 1).toLowerCase() + text.substring(1); } + + /** + * Open an input stream from a file, which may exist as a physical file or + * in a JAR file. The name must be valid for both options. + * + * @author Erik Vos + */ + public static InputStream getStreamForFile(String fileName) + throws IOException { + + File file = new File(fileName); + if (file.exists()) { + return new FileInputStream(file); + } else { + return null; + } + } } diff --git a/tools/ListAndFixSavedFiles.java b/tools/ListAndFixSavedFiles.java new file mode 100644 index 0000000..6a66c25 --- /dev/null +++ b/tools/ListAndFixSavedFiles.java @@ -0,0 +1,301 @@ +package tools; + +import java.awt.*; +import java.awt.event.*; +import java.io.*; +import java.util.*; +import java.util.List; + +import javax.swing.*; + +import org.apache.log4j.Logger; + +import rails.common.DisplayBuffer; +import rails.common.LocalText; +import rails.common.parser.Config; +import rails.common.parser.ConfigurationException; +import rails.game.*; +import rails.game.action.PossibleAction; +import rails.ui.swing.elements.ActionMenuItem; +import rails.util.GameFileIO; +import rails.util.Util; + +public class ListAndFixSavedFiles extends JFrame +implements ActionListener, KeyListener { + + private static final long serialVersionUID = 1L; + private JTextArea reportText; + private JScrollPane messageScroller; + private JScrollBar vbar; + private JPanel messagePanel; + private ListAndFixSavedFiles messageWindow; + private JMenuBar menuBar; + private JMenu fileMenu, editMenu; + private JMenuItem saveItem, loadItem; + private JMenuItem trimItem, deleteItem; + + private StringBuffer headerText = new StringBuffer(); + + private GameFileIO fileIO; + + private int vbarPos; + + private static String saveDirectory; + private String filepath; + + protected static Logger log; + + /** + * @param args + */ + public static void main(String[] args) { + + // intialize configuration + Config.setConfigSelection(); + + // delayed setting of logger + log = Logger.getLogger(ListAndFixSavedFiles.class.getPackage().getName()); + + saveDirectory = Config.get("save.directory"); + System.out.println("Save directory = " + saveDirectory); + + new ListAndFixSavedFiles (); + + } + + public ListAndFixSavedFiles () { + + super(); + + messageWindow = this; + + reportText = new JTextArea(); + reportText.setEditable(false); + reportText.setLineWrap(false); + reportText.setBackground(Color.WHITE); + reportText.setOpaque(true); + reportText.setBorder(BorderFactory.createEmptyBorder(5, 5, 5, 5)); + + messagePanel = new JPanel(new GridBagLayout()); + messageScroller = + new JScrollPane(reportText, + ScrollPaneConstants.VERTICAL_SCROLLBAR_ALWAYS, + ScrollPaneConstants.HORIZONTAL_SCROLLBAR_AS_NEEDED); + vbar = messageScroller.getVerticalScrollBar(); + GridBagConstraints gbc = new GridBagConstraints(); + gbc.gridx = gbc.gridy = 0; + gbc.weightx = gbc.weighty = 1.0; + gbc.fill = GridBagConstraints.BOTH; + messagePanel.add(messageScroller, gbc); + + menuBar = new JMenuBar(); + fileMenu = new JMenu(LocalText.getText("FILE")); + fileMenu.setMnemonic(KeyEvent.VK_F); + editMenu = new JMenu(LocalText.getText("EDIT")); + editMenu.setMnemonic(KeyEvent.VK_E); + + loadItem = new ActionMenuItem(LocalText.getText("LOAD")); + loadItem.setActionCommand("LOAD"); + loadItem.setMnemonic(KeyEvent.VK_L); + loadItem.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_L, + ActionEvent.ALT_MASK)); + loadItem.addActionListener(this); + loadItem.setEnabled(true); + fileMenu.add(loadItem); + + saveItem = new ActionMenuItem(LocalText.getText("SAVE")); + saveItem.setActionCommand("SAVE"); + saveItem.setMnemonic(KeyEvent.VK_S); + saveItem.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_S, + ActionEvent.ALT_MASK)); + saveItem.addActionListener(this); + saveItem.setEnabled(true); + fileMenu.add(saveItem); + + trimItem = new ActionMenuItem("Trim"); + trimItem.setActionCommand("TRIM"); + trimItem.setMnemonic(KeyEvent.VK_T); + trimItem.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_T, + ActionEvent.ALT_MASK)); + trimItem.addActionListener(this); + trimItem.setEnabled(true); + editMenu.add(trimItem); + + deleteItem = new ActionMenuItem("Delete"); + deleteItem.setActionCommand("DELETE"); + deleteItem.setMnemonic(KeyEvent.VK_D); + deleteItem.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_D, + ActionEvent.ALT_MASK)); + deleteItem.addActionListener(this); + deleteItem.setEnabled(true); + editMenu.add(deleteItem); + + menuBar.add(fileMenu); + menuBar.add(editMenu); + + setJMenuBar(menuBar); + + setContentPane(messagePanel); + + setSize(400, 400); + setLocation(600, 400); + setTitle("List and fix saved files"); + + addKeyListener(this); + + + setVisible(true); + + saveDirectory = Config.get("save.directory"); + + load(); + + } + + private void load() { + + JFileChooser jfc = new JFileChooser(); + jfc.setCurrentDirectory(new File(saveDirectory)); + + if (jfc.showOpenDialog(getContentPane()) == JFileChooser.APPROVE_OPTION) { + + File selectedFile = jfc.getSelectedFile(); + filepath = selectedFile.getPath(); + saveDirectory = selectedFile.getParent(); + + // clear header text + headerText = new StringBuffer(); + + // use GameLoader object to load game + fileIO = new GameFileIO(); + + fileIO.loadGameData(filepath); + add(fileIO.getGameDataAsText()); + try{ + fileIO.initGame(); + fileIO.loadActionsAndComments(); + setReportText(true); + + } catch (ConfigurationException e) { + log.fatal("Load failed", e); + DisplayBuffer.add(LocalText.getText("LoadFailed", e.getMessage())); + } + } + + } + + public void add (String text) { + if (text.length() > 0) { + headerText.append(text); + headerText.append("\n"); + } + } + + private void setReportText(boolean initial) { + if (initial) + vbarPos = -1; + else + vbarPos = this.vbar.getValue(); + + reportText.setText(headerText.toString()); + // append actionText + int i=0; + for (PossibleAction action : fileIO.getActions()) { + reportText.append("Action "+i+" "+action.getPlayerName()+": "+action.toString()); + reportText.append("\n"); + // check for comments for this action + String comment = fileIO.getComments().get(i); + if (comment!= null) { + reportText.append("Comment to action " + i + ": " + comment + "\n"); + } + i++; + } + scrollDown(vbarPos); + } + + + public void scrollDown (int pos) { + SwingUtilities.invokeLater(new Runnable() { + public void run() { + if (vbarPos == -1) + messageWindow.vbar.setValue(messageWindow.vbar.getMaximum()); + else + messageWindow.vbar.setValue(vbarPos); + } + }); + } + + + + public void actionPerformed(ActionEvent actor) { + String command = actor.getActionCommand(); + if ("TRIM".equalsIgnoreCase(command)) { + String result = JOptionPane.showInputDialog("Enter last action number to be retained"); + if (Util.hasValue(result)) { + try { + int index = Integer.parseInt(result); + // delete actions + int size = fileIO.getActions().size(); + fileIO.getActions().subList(index + 1, size).clear(); + // delete comments + for (int id = 0; id < size; id++) { + if (id > index) { + fileIO.getComments().remove(id); + } + } + setReportText(false); + } catch (NumberFormatException e) { + + } + } + } else if ("DELETE".equalsIgnoreCase(command)) { + String result = JOptionPane.showInputDialog("Enter action number to be deleted"); + if (Util.hasValue(result)) { + try { + int index = Integer.parseInt(result); + fileIO.getActions().remove(index); + // delete and renumber in user Comments + SortedMap<Integer, String> newComments = new TreeMap<Integer, String>(); + for (Integer id:fileIO.getComments().keySet()) { + if (id < index) { + newComments.put(id, fileIO.getComments().get(id)); + } else if (id > index) { + newComments.put(id-1, fileIO.getComments().get(id)); + } + } + fileIO.setComments(newComments); + setReportText(false); + } catch (NumberFormatException e) { + log.error("Number format exception for '"+result+"'", e); + } + } + } else if ("SAVE".equalsIgnoreCase(command)) { + save(); + } else if ("LOAD".equalsIgnoreCase(command)) { + load(); + } + } + + private void save() { + JFileChooser jfc = new JFileChooser(); + if (Util.hasValue(saveDirectory)) { + jfc.setCurrentDirectory(new File(saveDirectory)); + } + if (Util.hasValue(filepath)) { + jfc.setSelectedFile(new File(filepath)); + } + if (jfc.showSaveDialog(this) == JFileChooser.APPROVE_OPTION) { + File selectedFile = jfc.getSelectedFile(); + fileIO.saveGame(selectedFile, true, "SaveFailed"); + } + + } + + public void keyPressed(KeyEvent e) { + } + + public void keyReleased(KeyEvent e) {} + + public void keyTyped(KeyEvent e) {} + +} diff --git a/tools/Util.java b/tools/Util.java deleted file mode 100644 index 0233f6b..0000000 --- a/tools/Util.java +++ /dev/null @@ -1,37 +0,0 @@ -/* $Header: /Users/blentz/rails_rcs/cvs/18xx/tools/Util.java,v 1.1 2010/02/03 20:16:38 evos Exp $*/ -package tools; - -import java.io.File; -import java.io.FileInputStream; -import java.io.IOException; -import java.io.InputStream; - -public final class Util { - /** - * No-args private constructor, to prevent (meaningless) construction of one - * of these. - */ - private Util() {} - - public static boolean hasValue(String s) { - return s != null && !s.equals(""); - } - - /** - * Open an input stream from a file, which may exist as a physical file or - * in a JAR file. The name must be valid for both options. - * - * @author Erik Vos - */ - public static InputStream getStreamForFile(String fileName) - throws IOException { - - File file = new File(fileName); - if (file.exists()) { - return new FileInputStream(file); - } else { - return null; - } - } - -} diff --git a/tools/XmlUtils.java b/tools/XmlUtils.java index 244dea5..7f419cc 100644 --- a/tools/XmlUtils.java +++ b/tools/XmlUtils.java @@ -186,7 +186,7 @@ public final class XmlUtils { DocumentBuilder db = dbf.newDocumentBuilder(); // Step 3: parse the input file to get a Document object - doc = db.parse(Util.getStreamForFile(fileName)); + doc = db.parse(rails.util.Util.getStreamForFile(fileName)); } catch (ParserConfigurationException e) { throw new ConfigurationException("Could not read/parse " + fileName |
From: Stefan F. <ste...@us...> - 2011-08-03 09:23:05
|
test/TestGame.java | 21 test/data/real/1830_A.report | 2036 +++++++++++++++++++++++++ test/data/real/1856_A.report | 2018 +++++++++++++++++++++++++ test/data/real/1889_A.report | 640 +++++++ test/data/real/1889_C.report | 1414 +++++++++++++++++ test/data/real/18AL_A.report | 960 +++++++++++ test/data/real/18EU_A.report | 2097 ++++++++++++++++++++++++++ test/data/test/1830_5forDtrainExchange.rails |binary test/data/test/1830_5forDtrainExchange.report | 471 +++++ test/data/test/1835_PR_3rdTrain.rails |binary test/data/test/1835_PR_3rdTrain.report | 1102 +++++++++++++ test/data/test/1851_Late.rails |binary test/data/test/1851_Late.report | 602 +++++++ test/data/test/1856_2nd6T+PrezCash2.rails |binary test/data/test/1856_2nd6T+PrezCash2.report | 1028 ++++++++++++ test/data/test/18EU_After2nd8Train.rails |binary test/data/test/18EU_After2nd8Train.report | 1193 ++++++++++++++ 17 files changed, 13574 insertions(+), 8 deletions(-) New commits: commit 8c693cae4dcfedb4f7f2af224659ff8c4a32cfca Merge: f2d4511 f34e7b0 Author: Stefan Frey <ste...@we...> Date: Wed Aug 3 11:18:22 2011 +0200 Merge branch 'master' of git://rails.git.sourceforge.net/gitroot/rails/rails commit f2d4511d0b95a445d00efe26c3522bbb7dfd7fc6 Author: Stefan Frey <ste...@we...> Date: Wed Aug 3 07:47:49 2011 +0200 Added some more logging code to test game Added Erik test games Remark: Currently the second 1830 test games fails automatically. diff --git a/test/TestGame.java b/test/TestGame.java index 04d06e2..4109ac7 100644 --- a/test/TestGame.java +++ b/test/TestGame.java @@ -45,18 +45,23 @@ public class TestGame extends TestCase { int line = 0; while (true) { // test for size of reports - if (line >= expectedReport.size()) - if (line >= testReport.size()) - break; // test succesfull - else + if (line >= expectedReport.size()) { + if (line >= testReport.size()) { + break; // test successful + } else { fail("Test report exceeeds expected report." + " Last line (" + line + "): " + testReport.get(line-1)); - else - if (line >= testReport.size()) + } + } else { + if (line >= testReport.size()) { fail("Expected report exceeds test report." + " Last line (" + line + "): " + expectedReport.get(line-1)); - - assertEquals("Reports differ in line " + line+1, + } + } + log.debug("Comparing line " + (line+1)); + log.debug("Expected = " + expectedReport.get(line)); + log.debug("Actual = " + testReport.get(line)); + assertEquals("Reports differ in line " + (line+1), expectedReport.get(line), testReport.get(line)); line = line + 1; } diff --git a/test/data/real/1830_A.report b/test/data/real/1830_A.report new file mode 100644 index 0000000..0302cf7 --- /dev/null +++ b/test/data/real/1830_A.report @@ -0,0 +1,2036 @@ +GameIs,1830 +PlayerIs,1,Marcus +PlayerIs,2,Si +PlayerIs,3,Ed +PlayerIs,4,Phil +PlayerIs,5,Chris +PlayerCash,$480 +BankHas,$17600 +StartOfPhase,2 +BankSizeIs,$17600 +StartOfInitialRound +HasPriority,Marcus +BID_ITEM_LOG,Marcus,$115,M&H,$365 +BID_ITEM_LOG,Si,$165,C&A,$315 +BID_ITEM_LOG,Ed,$170,C&A,$310 +BID_ITEM_LOG,Phil,$75,D&H,$405 +BID_ITEM_LOG,Chris,$45,C&StL,$435 +BuysItemFor,Marcus,SVNRR,$20 +BuysItemFor,Chris,C&StL,$45 +BuysItemFor,Phil,D&H,$75 +BuysItemFor,Marcus,M&H,$115 +TO_AUCTION,C&A +BID_ITEM_LOG,Si,$175,C&A,$305 +BID_ITEM_LOG,Ed,$180,C&A,$300 +BID_ITEM_LOG,Si,$185,C&A,$295 +BID_ITEM_LOG,Ed,$190,C&A,$290 +BID_ITEM_LOG,Si,$195,C&A,$285 +BID_ITEM_LOG,Ed,$200,C&A,$280 +BID_ITEM_LOG,Si,$210,C&A,$270 +PASSES,Ed +BuysItemFor,Si,C&A,$210 +ALSO_GETS,Si,CERT_NAME,RDG,10 +PASSES,Si +PASSES,Ed +PASSES,Phil +PASSES,Chris +PASSES,Marcus +ALL_PASSED +Has,Marcus,$345 +Has,Si,$270 +Has,Ed,$480 +Has,Phil,$405 +Has,Chris,$435 +START_OR,0.0 +ReceivesFor,Marcus,$5,SVNRR +ReceivesFor,Chris,$10,C&StL +ReceivesFor,Phil,$15,D&H +ReceivesFor,Marcus,$20,M&H +ReceivesFor,Si,$25,C&A +ShortORExecuted +Has,Marcus,$370 +Has,Si,$295 +Has,Ed,$480 +Has,Phil,$420 +Has,Chris,$445 +StartOfInitialRound +HasPriority,Si +PASSES,Si +BuysItemFor,Ed,B&O,$220 +ALSO_GETS,Ed,PRES_CERT_NAME,B&O,20 +Has,Marcus,$370 +Has,Si,$295 +Has,Ed,$260 +Has,Phil,$420 +Has,Chris,$445 +StartStockRound,1 +HasPriority,Phil +START_COMPANY_LOG,Phil,NYC,$67,$134,2,20,BANK +START_COMPANY_LOG,Chris,N&W,$71,$142,2,20,BANK +START_COMPANY_LOG,Marcus,NYNH,$71,$142,2,20,BANK +BUY_SHARE_LOG,Si,10,NYC,IPO,$67 +BUY_SHARE_LOG,Ed,10,NYNH,IPO,$71 +BUY_SHARE_LOG,Phil,10,NYC,IPO,$67 +BUY_SHARE_LOG,Chris,10,N&W,IPO,$71 +BUY_SHARE_LOG,Marcus,10,NYNH,IPO,$71 +BUY_SHARE_LOG,Si,10,NYC,IPO,$67 +BUY_SHARE_LOG,Ed,10,NYNH,IPO,$71 +BUY_SHARE_LOG,Phil,10,NYC,IPO,$67 +FloatsWithCash,NYC,$670 +BUY_SHARE_LOG,Chris,10,N&W,IPO,$71 +BUY_SHARE_LOG,Marcus,10,NYNH,IPO,$71 +FloatsWithCash,NYNH,$710 +BUY_SHARE_LOG,Si,10,NYC,IPO,$67 +Autopasses,Ed +BUY_SHARE_LOG,Phil,10,NYC,IPO,$67 +BUY_SHARE_LOG,Chris,10,N&W,IPO,$71 +BUY_SHARE_LOG,Marcus,10,NYNH,IPO,$71 +BUY_SHARE_LOG,Si,10,NYC,IPO,$67 +BUY_SHARE_LOG,Ed,10,NYC,IPO,$67 +Autopasses,Phil +BUY_SHARE_LOG,Chris,10,N&W,IPO,$71 +FloatsWithCash,N&W,$710 +PASSES,Marcus +PASSES,Si +PASSES,Ed +Autopasses,Phil +PASSES,Chris + +END_SR,1 +PRICE_MOVES_LOG,NYC,$67,G6,$71,G5 +SoldOut,NYC,$67,G6,$71,G5 +Has,N&W,$710 +Has,NYC,$670 +Has,NYNH,$710 +Has,Marcus,$15 +Has,Si,$27 +Has,Ed,$51 +Has,Phil,$85 +Has,Chris,$19 +START_OR,1.1 +ReceivesFor,Marcus,$5,SVNRR +ReceivesFor,Chris,$10,C&StL +ReceivesFor,Phil,$15,D&H +ReceivesFor,Marcus,$20,M&H +ReceivesFor,Si,$25,C&A +ReceivesFor,Ed,$30,B&O + +CompanyOperates,N&W,Chris +LaysTileAt,N&W,9,L14,W +CompanyDoesNotPayDividend,N&W +PRICE_MOVES_LOG,N&W,$71,G5,$67,F5 +BuysTrain,N&W,2,IPO,$80 +FirstTrainBought,2 + +CompanyOperates,NYNH,Marcus +LaysTileAt,NYNH,57,F20,SW +CompanyDoesNotPayDividend,NYNH +PRICE_MOVES_LOG,NYNH,$71,G5,$67,F5 +BuysTrain,NYNH,2,IPO,$80 + +CompanyOperates,NYC,Phil +LaysTileAt,NYC,57,E19,NE +CompanyDoesNotPayDividend,NYC +PRICE_MOVES_LOG,NYC,$71,G5,$67,F5 +BuysTrain,NYC,2,IPO,$80 +BuysTrain,NYC,2,IPO,$80 +BuysTrain,NYC,2,IPO,$80 +BuysTrain,NYC,2,IPO,$80 +All 2-trains are sold out, 3-trains now available + +EndOfOperatingRound,1.1 +ORWorthIncrease,Marcus,1.1,$5 +ORWorthIncrease,Si,1.1,$9 +ORWorthIncrease,Ed,1.1,$18 +ORWorthIncrease,Phil,1.1,-$5 +ORWorthIncrease,Chris,1.1,-$14 +Has,N&W,$630 +Has,NYC,$350 +Has,NYNH,$630 +Has,Marcus,$40 +Has,Si,$52 +Has,Ed,$81 +Has,Phil,$100 +Has,Chris,$29 +StartStockRound,2 +HasPriority,Marcus +PASSES,Marcus +PASSES,Si +BUY_SHARE_LOG,Ed,10,NYNH,IPO,$71 +BUY_SHARE_LOG,Phil,10,N&W,IPO,$71 +PASSES,Chris +PASSES,Marcus +PASSES,Si +PASSES,Ed +PASSES,Phil + +END_SR,2 +PRICE_MOVES_LOG,NYC,$67,F5,$71,F4 +SoldOut,NYC,$67,F5,$71,F4 +Has,N&W,$630 +Has,NYC,$350 +Has,NYNH,$630 +Has,Marcus,$40 +Has,Si,$52 +Has,Ed,$10 +Has,Phil,$29 +Has,Chris,$29 +START_OR,2.1 +ReceivesFor,Marcus,$5,SVNRR +ReceivesFor,Chris,$10,C&StL +ReceivesFor,Phil,$15,D&H +ReceivesFor,Marcus,$20,M&H +ReceivesFor,Si,$25,C&A +ReceivesFor,Ed,$30,B&O + +CompanyOperates,NYC,Phil +LaysTileAt,NYC,8,F18,W +CompanyRevenue,NYC,$0 +CompanyDoesNotPayDividend,NYC +PRICE_MOVES_LOG,NYC,$71,F4,$66,E4 + +CompanyOperates,N&W,Chris +LaysTileAt,N&W,9,L12,W +CorrectionModeActivate,Chris,CORRECT_CASH +CorrectCashSubstractMoney,N&W,$140 +CorrectionModeDeactivate,Chris,CORRECT_CASH +CompanyRevenue,N&W,$70 +CompanyPaysOutFull,N&W,$70 +Payout,Phil,$7,1,10 +Payout,Chris,$42,6,10 +PRICE_MOVES_LOG,N&W,$67,F5,$71,G5 + +CompanyOperates,NYNH,Marcus +LaysTileAtFor,NYNH,9,E21,SW,$120 +CompanyRevenue,NYNH,$60 +CompanyPaysOutFull,NYNH,$60 +Payout,Ed,$18,3,10 +Payout,Marcus,$30,5,10 +PRICE_MOVES_LOG,NYNH,$67,F5,$71,G5 +BuysTrain,NYNH,3,IPO,$180 +FirstTrainBought,3 +StartOfPhase,3 + +EndOfOperatingRound,2.1 +ORWorthIncrease,Marcus,2.1,$75 +ORWorthIncrease,Si,2.1,$5 +ORWorthIncrease,Ed,2.1,$55 +ORWorthIncrease,Phil,2.1,$1 +ORWorthIncrease,Chris,2.1,$76 +Has,N&W,$490 +Has,NYC,$350 +Has,NYNH,$330 +Has,Marcus,$95 +Has,Si,$77 +Has,Ed,$58 +Has,Phil,$51 +Has,Chris,$81 +StartStockRound,3 +HasPriority,Chris +BUY_SHARE_LOG,Chris,10,NYNH,IPO,$71 +BUY_SHARE_LOG,Marcus,10,NYNH,IPO,$71 +BUY_SHARE_LOG,Si,10,N&W,IPO,$71 +PASSES,Ed +PASSES,Phil +PASSES,Chris +PASSES,Marcus +PASSES,Si + +END_SR,3 +PRICE_MOVES_LOG,NYNH,$71,G5,$76,G4 +SoldOut,NYNH,$71,G5,$76,G4 +PRICE_MOVES_LOG,NYC,$66,E4,$70,E3 +SoldOut,NYC,$66,E4,$70,E3 +Has,N&W,$490 +Has,NYC,$350 +Has,NYNH,$330 +Has,Marcus,$24 +Has,Si,$6 +Has,Ed,$58 +Has,Phil,$51 +Has,Chris,$10 +START_OR,3.1 +ReceivesFor,Marcus,$5,SVNRR +ReceivesFor,Chris,$10,C&StL +ReceivesFor,Phil,$15,D&H +ReceivesFor,Marcus,$20,M&H +ReceivesFor,Si,$25,C&A +ReceivesFor,Ed,$30,B&O + +CompanyOperates,NYNH,Marcus +LaysTileAtFor,NYNH,54,G19,SW,$80 +CompanyRevenue,NYNH,$80 +CompanyPaysOutFull,NYNH,$80 +Payout,Ed,$24,3,10 +Payout,Marcus,$48,6,10 +Payout,Chris,$8,1,10 +PRICE_MOVES_LOG,NYNH,$76,G4,$82,H4 + +CompanyOperates,N&W,Chris +LaysTileAtFor,N&W,9,K15,NW,$40 +CompanyRevenue,N&W,$70 +CompanyPaysOutFull,N&W,$70 +Payout,Chris,$42,6,10 +Payout,Phil,$7,1,10 +Payout,Si,$7,1,10 +PRICE_MOVES_LOG,N&W,$71,G5,$76,H5 +BuysTrain,N&W,3,IPO,$180 + +CompanyOperates,NYC,Phil +BuysPrivateFromFor,NYC,D&H,Phil,$140 +LaysTileAtFor,NYC,57,F16,W,$120 +LAYS_FREE_TOKEN_ON,NYC,F16 +CompanyRevenue,NYC,$40 +CompanyPaysOutFull,NYC,$40 +Payout,Ed,$4,1,10 +Payout,Phil,$20,5,10 +Payout,Si,$16,4,10 +PRICE_MOVES_LOG,NYC,$70,E3,$76,F3 + +EndOfOperatingRound,3.1 +ORWorthIncrease,Marcus,3.1,$109 +ORWorthIncrease,Si,3.1,$77 +ORWorthIncrease,Ed,3.1,$82 +ORWorthIncrease,Phil,3.1,$147 +ORWorthIncrease,Chris,3.1,$96 +Has,N&W,$270 +Has,NYC,$90 +Has,NYNH,$250 +Has,Marcus,$97 +Has,Si,$54 +Has,Ed,$116 +Has,Phil,$233 +Has,Chris,$70 +START_OR,3.2 +ReceivesFor,Marcus,$5,SVNRR +ReceivesFor,Chris,$10,C&StL +ReceivesFor,NYC,$15,D&H +ReceivesFor,Marcus,$20,M&H +ReceivesFor,Si,$25,C&A +ReceivesFor,Ed,$30,B&O + +CompanyOperates,NYNH,Marcus +LaysTileAt,NYNH,25,F18,W +CompanyRevenue,NYNH,$160 +CompanyPaysOutFull,NYNH,$160 +Payout,Ed,$48,3,10 +Payout,Marcus,$96,6,10 +Payout,Chris,$16,1,10 +PRICE_MOVES_LOG,NYNH,$82,H4,$90,I4 + +CompanyOperates,N&W,Chris +LaysTileAtFor,N&W,57,J14,NW,$80 +CompanyRevenue,N&W,$120 +CompanyPaysOutFull,N&W,$120 +Payout,Phil,$12,1,10 +Payout,Chris,$72,6,10 +Payout,Si,$12,1,10 +PRICE_MOVES_LOG,N&W,$76,H5,$82,I5 +BuysPrivateFromFor,N&W,C&StL,Chris,$20 + +CompanyOperates,NYC,Phil +LaysTileAt,NYC,14,F16,W +CompanyRevenue,NYC,$90 +CompanyPaysOutFull,NYC,$90 +Payout,Ed,$9,1,10 +Payout,Phil,$45,5,10 +Payout,Si,$36,4,10 +PRICE_MOVES_LOG,NYC,$76,F3,$82,G3 + +EndOfOperatingRound,3.2 +ORWorthIncrease,Marcus,3.2,$169 +ORWorthIncrease,Si,3.2,$103 +ORWorthIncrease,Ed,3.2,$117 +ORWorthIncrease,Phil,3.2,$93 +ORWorthIncrease,Chris,3.2,$122 +Has,N&W,$170 +Has,NYC,$105 +Has,NYNH,$250 +Has,Marcus,$218 +Has,Si,$127 +Has,Ed,$203 +Has,Phil,$290 +Has,Chris,$188 +StartStockRound,4 +HasPriority,Ed +SELL_SHARE_LOG,Ed,10,NYC,$82 +PRICE_MOVES_LOG,NYC,$82,G3,$76,G4 +SELL_SHARES_LOG,Ed,3,10,30,NYNH,$270 +PRICE_MOVES_LOG,NYNH,$90,I4,$70,I7 +START_COMPANY_LOG,Ed,RDG,$100,$300,3,30,BANK +SELL_SHARES_LOG,Phil,4,10,40,NYC,$304 +PRICE_MOVES_LOG,NYC,$76,G4,$67,G8 +IS_NOW_PRES_OF,Si,NYC +START_COMPANY_LOG,Phil,C&O,$90,$180,2,20,BANK +BUY_SHARE_LOG,Chris,10,NYNH,Pool,$70 +START_COMPANY_LOG,Marcus,Erie,$90,$180,2,20,BANK +SwapsPrivateForCertificate,Marcus,M&H,10,NYC +PrivateCloses,M&H +BUY_SHARE_LOG,Si,10,N&W,IPO,$71 +BUY_SHARE_LOG,Ed,10,RDG,IPO,$100 +BUY_SHARE_LOG,Phil,10,C&O,IPO,$90 +BUY_SHARE_LOG,Chris,10,NYNH,Pool,$70 +Autopasses,Marcus +PASSES,Si +BUY_SHARE_LOG,Ed,10,RDG,IPO,$100 +FloatsWithCash,RDG,$1000 +BUY_SHARE_LOG,Phil,10,C&O,IPO,$90 +Autopasses,Chris +Autopasses,Marcus +PASSES,Si +PASSES,Ed +BUY_SHARE_LOG,Phil,10,C&O,IPO,$90 +Autopasses,Chris +Autopasses,Marcus +PASSES,Si +PASSES,Ed +BUY_SHARE_LOG,Phil,10,C&O,IPO,$90 +FloatsWithCash,C&O,$900 +Autopasses,Chris +Autopasses,Marcus +PASSES,Si +PASSES,Ed +PASSES,Phil + +END_SR,4 +Has,C&O,$900 +Has,N&W,$170 +Has,NYC,$105 +Has,NYNH,$250 +Has,RDG,$1000 +Has,Marcus,$38 +Has,Si,$56 +Has,Ed,$55 +Has,Phil,$54 +Has,Chris,$48 +START_OR,4.1 +ReceivesFor,Marcus,$5,SVNRR +ReceivesFor,N&W,$10,C&StL +ReceivesFor,NYC,$15,D&H +ReceivesFor,Si,$25,C&A +ReceivesFor,Ed,$30,B&O + +CompanyOperates,RDG,Ed +LaysTileAt,RDG,57,H16,W +CompanyDoesNotPayDividend,RDG +PRICE_MOVES_LOG,RDG,$100,G1,$90,F1 +BuysTrain,RDG,3,IPO,$180 + +CompanyOperates,C&O,Phil +LaysTileAt,C&O,57,K13,SW +CompanyDoesNotPayDividend,C&O +PRICE_MOVES_LOG,C&O,$90,G2,$82,F2 +BuysTrain,C&O,3,IPO,$180 +BuysTrain,C&O,3,IPO,$180 +All 3-trains are sold out, 4-trains now available +BuysTrain,C&O,4,IPO,$300 +FirstTrainBought,4 +StartOfPhase,4 +CompanyDiscardsTrain,NYC,2 + +CompanyOperates,N&W,Chris +LaysTileAt,N&W,8,M11,NW +CompanyRevenue,N&W,$150 +CompanyWithholds,N&W,$150 +PRICE_MOVES_LOG,N&W,$82,I5,$76,H5 +TrainsObsoleteRusted,2,N&W +BuysTrain,N&W,4,IPO,$300 + +CompanyOperates,NYNH,Marcus +LaysTileAt,NYNH,14,F20,SW +CompanyRevenue,NYNH,$180 +CompanyWithholds,NYNH,$180 +PRICE_MOVES_LOG,NYNH,$70,I7,$69,H7 +TrainsObsoleteRusted,2,NYNH +BuysTrain,NYNH,4,IPO,$300 + +CompanyOperates,NYC,Si +LaysTileAt,NYC,1,G17,W +CompanyRevenue,NYC,$130 +CompanyPaysOutFull,NYC,$130 +Payout,Si,$52,4,10 +Payout,Marcus,$13,1,10 +Payout,Phil,$13,1,10 +Payout,NYC,$52,4,10 +PRICE_MOVES_LOG,NYC,$67,G8,$68,H8 +TrainsObsoleteRusted,2,NYC +TrainsObsoleteRusted,2,NYC +TrainsObsoleteRusted,2,NYC +PresidentAddsCash,NYC,Si,$128 +BuysTrain,NYC,4,IPO,$300 + +EndOfOperatingRound,4.1 +ORWorthIncrease,Marcus,4.1,$13 +ORWorthIncrease,Si,4.1,-$69 +ORWorthIncrease,Ed,4.1,-$20 +ORWorthIncrease,Phil,4.1,-$40 +ORWorthIncrease,Chris,4.1,-$39 +Has,C&O,$240 +Has,N&W,$30 +Has,NYC,$0 +Has,NYNH,$130 +Has,RDG,$820 +Has,Marcus,$56 +Has,Si,$5 +Has,Ed,$85 +Has,Phil,$67 +Has,Chris,$48 +START_OR,4.2 +ReceivesFor,Marcus,$5,SVNRR +ReceivesFor,N&W,$10,C&StL +ReceivesFor,NYC,$15,D&H +ReceivesFor,Si,$25,C&A +ReceivesFor,Ed,$30,B&O + +CompanyOperates,RDG,Ed +LaysTileAt,RDG,14,H16,SW +CompanyRevenue,RDG,$50 +CompanyPaysOutFull,RDG,$50 +Payout,Ed,$25,5,10 +Payout,Si,$5,1,10 +PRICE_MOVES_LOG,RDG,$90,F1,$100,G1 + +CompanyOperates,C&O,Phil +LaysTileAt,C&O,24,L12,W +CorrectionModeActivate,Phil,CORRECT_CASH +CorrectCashSubstractMoney,C&O,$140 +CorrectionModeDeactivate,Phil,CORRECT_CASH +CompanyRevenue,C&O,$90 +CompanyPaysOutFull,C&O,$90 +Payout,Phil,$54,6,10 +PRICE_MOVES_LOG,C&O,$82,F2,$90,G2 + +CompanyOperates,N&W,Chris +LaysTileAt,N&W,14,J14,NW +LAYS_TOKEN_ON,N&W,J14,$40 +CompanyRevenue,N&W,$210 +CompanyPaysOutFull,N&W,$210 +Payout,Phil,$21,1,10 +Payout,Si,$42,2,10 +Payout,Chris,$126,6,10 +PRICE_MOVES_LOG,N&W,$76,H5,$82,I5 + +CompanyOperates,NYNH,Marcus +LaysTileAtFor,NYNH,57,F22,W,$80 +LAYS_TOKEN_ON,NYNH,F16,$40 +CompanyRevenue,NYNH,$270 +CompanyPaysOutFull,NYNH,$270 +Payout,Chris,$81,3,10 +Payout,Marcus,$162,6,10 +Payout,NYNH,$27,1,10 +PRICE_MOVES_LOG,NYNH,$69,H7,$70,I7 + +CompanyOperates,NYC,Si +LaysTileAt,NYC,15,E19,NE +CompanyRevenue,NYC,$160 +CompanyPaysOutFull,NYC,$160 +Payout,Marcus,$16,1,10 +Payout,Phil,$16,1,10 +Payout,Si,$64,4,10 +Payout,NYC,$64,4,10 +PRICE_MOVES_LOG,NYC,$68,H8,$69,H7 + +EndOfOperatingRound,4.2 +ORWorthIncrease,Marcus,4.2,$190 +ORWorthIncrease,Si,4.2,$162 +ORWorthIncrease,Ed,4.2,$105 +ORWorthIncrease,Phil,4.2,$146 +ORWorthIncrease,Chris,4.2,$246 +Has,C&O,$100 +Has,N&W,$0 +Has,NYC,$79 +Has,NYNH,$37 +Has,RDG,$820 +Has,Marcus,$239 +Has,Si,$141 +Has,Ed,$140 +Has,Phil,$158 +Has,Chris,$255 +StartStockRound,5 +HasPriority,Chris +SELL_SHARES_LOG,Chris,3,10,30,NYNH,$210 +START_COMPANY_LOG,Chris,PRR,$76,$152,2,20,BANK +BUY_SHARE_LOG,Marcus,10,N&W,IPO,$71 +SELL_SHARES_LOG,Si,2,10,20,N&W,$164 +PRICE_MOVES_LOG,N&W,$82,I5,$70,I7 +SELL_SHARE_LOG,Si,10,RDG,$100 +PRICE_MOVES_LOG,RDG,$100,G1,$90,G2 +BUY_SHARE_LOG,Si,10,Erie,IPO,$90 +BUY_SHARE_LOG,Ed,10,RDG,Pool,$90 +BUY_SHARE_LOG,Phil,10,NYNH,Pool,$70 +BUY_SHARE_LOG,Chris,10,PRR,IPO,$76 +BUY_SHARE_LOG,Marcus,10,Erie,IPO,$90 +BUY_SHARE_LOG,Si,10,Erie,IPO,$90 +Autopasses,Ed +BUY_SHARE_LOG,Phil,10,NYNH,Pool,$70 +BUY_SHARE_LOG,Chris,10,PRR,IPO,$76 +SELL_SHARE_LOG,Marcus,10,NYC,$69 +PRICE_MOVES_LOG,NYC,$69,H7,$68,H8 +BUY_SHARE_LOG,Marcus,10,Erie,IPO,$90 +FloatsWithCash,Erie,$900 +BUY_SHARE_LOG,Si,10,Erie,IPO,$90 +Autopasses,Ed +PASSES,Phil +BUY_SHARE_LOG,Chris,10,PRR,IPO,$76 +SELL_SHARE_LOG,Marcus,10,N&W,$70 +BUY_SHARE_LOG,Marcus,10,Erie,IPO,$90 +BUY_SHARE_LOG,Si,10,Erie,IPO,$90 +Autopasses,Ed +PASSES,Phil +BUY_SHARE_LOG,Chris,10,PRR,IPO,$76 +FloatsWithCash,PRR,$760 +PASSES,Marcus +PASSES,Si +Autopasses,Ed +SELL_SHARE_LOG,Phil,10,NYNH,$70 +BUY_SHARE_LOG,Phil,10,PRR,IPO,$76 +PASSES,Chris +PASSES,Marcus +PASSES,Si +Autopasses,Ed +PASSES,Phil + +END_SR,5 +Has,C&O,$100 +Has,Erie,$900 +Has,N&W,$0 +Has,NYC,$79 +Has,NYNH,$37 +Has,PRR,$760 +Has,RDG,$820 +Has,Marcus,$37 +Has,Si,$45 +Has,Ed,$50 +Has,Phil,$12 +Has,Chris,$9 +START_OR,5.1 +ReceivesFor,Marcus,$5,SVNRR +ReceivesFor,N&W,$10,C&StL +ReceivesFor,NYC,$15,D&H +ReceivesFor,Si,$25,C&A +ReceivesFor,Ed,$30,B&O + +CompanyOperates,Erie,Marcus +LaysTileAt,Erie,59,E11,SW +CompanyDoesNotPayDividend,Erie +PRICE_MOVES_LOG,Erie,$90,G2,$82,F2 +BuysTrain,Erie,4,IPO,$300 +BuysPrivateFromFor,Erie,SVNRR,Marcus,$40 + +CompanyOperates,C&O,Phil +LaysTileAt,C&O,15,K13,SW +LAYS_TOKEN_ON,C&O,J14,$40 +CompanyRevenue,C&O,$250 +CompanyPaysOutFull,C&O,$250 +Payout,Phil,$150,6,10 +PRICE_MOVES_LOG,C&O,$90,G2,$100,H2 + +CompanyOperates,RDG,Ed +LaysTileAt,RDG,57,H10,W +CompanyRevenue,RDG,$60 +CompanyPaysOutFull,RDG,$60 +Payout,Ed,$36,6,10 +PRICE_MOVES_LOG,RDG,$90,G2,$100,H2 + +CompanyOperates,PRR,Chris +LaysTileAt,PRR,15,H10,E +CompanyDoesNotPayDividend,PRR +PRICE_MOVES_LOG,PRR,$76,G4,$71,F4 +BuysTrain,PRR,4,IPO,$300 +All 4-trains are sold out, 5-trains now available +BuysTrain,PRR,3,N&W,$400 + +CompanyOperates,NYNH,Marcus +LaysTileAt,NYNH,27,E21,SW +CompanyRevenue,NYNH,$280 +CompanyPaysOutFull,NYNH,$280 +Payout,Phil,$28,1,10 +Payout,Marcus,$168,6,10 +Payout,NYNH,$84,3,10 +PRICE_MOVES_LOG,NYNH,$70,I7,$75,I6 + +CompanyOperates,N&W,Chris +CompanyRevenue,N&W,$130 +CompanyWithholds,N&W,$130 +PRICE_MOVES_LOG,N&W,$70,I7,$69,H7 +BuysTrain,N&W,5,IPO,$450 +FirstTrainBought,5 +StartOfPhase,5 +PrivateCloses,SVNRR +PrivateCloses,C&StL +PrivateCloses,D&H +PrivateCloses,C&A +PrivateCloses,B&O +CompanyDiscardsTrain,C&O,3 + +CompanyOperates,NYC,Si +LaysTileAt,NYC,62,G19,NE +CompanyRevenue,NYC,$170 +CompanyPaysOutFull,NYC,$170 +Payout,Phil,$17,1,10 +Payout,Si,$68,4,10 +Payout,NYC,$85,5,10 +PRICE_MOVES_LOG,NYC,$68,H8,$69,H7 + +EndOfOperatingRound,5.1 +ORWorthIncrease,Marcus,5.1,$183 +ORWorthIncrease,Si,5.1,-$95 +ORWorthIncrease,Ed,5.1,-$94 +ORWorthIncrease,Phil,5.1,$255 +ORWorthIncrease,Chris,5.1,-$36 +Has,C&O,$60 +Has,Erie,$560 +Has,N&W,$90 +Has,NYC,$179 +Has,NYNH,$121 +Has,PRR,$60 +Has,RDG,$820 +Has,Marcus,$250 +Has,Si,$138 +Has,Ed,$116 +Has,Phil,$207 +Has,Chris,$9 +START_OR,5.2 + +CompanyOperates,C&O,Phil +LaysTileAt,C&O,53,I15,SW +CompanyRevenue,C&O,$290 +CompanyPaysOutFull,C&O,$290 +Payout,Phil,$174,6,10 +PRICE_MOVES_LOG,C&O,$100,H2,$112,I2 + +CompanyOperates,RDG,Ed +LaysTileAt,RDG,BA,I15,NE +LAYS_TOKEN_ON,RDG,I15,$40 +CompanyRevenue,RDG,$120 +CompanyPaysOutFull,RDG,$120 +Payout,Ed,$72,6,10 +PRICE_MOVES_LOG,RDG,$100,H2,$112,I2 +BuysTrain,RDG,5,IPO,$450 + +CompanyOperates,Erie,Marcus +LaysTileAt,Erie,4,F10,SW +CompanyRevenue,Erie,$50 +CompanyPaysOutFull,Erie,$50 +Payout,Marcus,$25,5,10 +Payout,Si,$20,4,10 +PRICE_MOVES_LOG,Erie,$82,F2,$90,G2 + +CompanyOperates,NYNH,Marcus +LaysTileAt,NYNH,59,H18,NE +CompanyRevenue,NYNH,$300 +CompanyWithholds,NYNH,$300 +PRICE_MOVES_LOG,NYNH,$75,I6,$71,H6 + +CompanyOperates,PRR,Chris +LaysTileAt,PRR,G17,G17,W +LAYS_TOKEN_ON,PRR,G19,$40 +CompanyRevenue,PRR,$340 +CompanyPaysOutFull,PRR,$340 +Payout,Phil,$34,1,10 +Payout,Chris,$204,6,10 +PRICE_MOVES_LOG,PRR,$71,F4,$76,G4 + +CompanyOperates,N&W,Chris +LaysTileAt,N&W,63,H16,SW +CompanyRevenue,N&W,$410 +CompanyPaysOutFull,N&W,$410 +Payout,Phil,$41,1,10 +Payout,Chris,$246,6,10 +Payout,N&W,$123,3,10 +PRICE_MOVES_LOG,N&W,$69,H7,$70,I7 + +CompanyOperates,NYC,Si +LaysTileAt,NYC,64,H18,SE +LAYS_TOKEN_ON,NYC,G19,$100 +CompanyRevenue,NYC,$200 +CompanyPaysOutFull,NYC,$200 +Payout,Phil,$20,1,10 +Payout,Si,$80,4,10 +Payout,NYC,$100,5,10 +PRICE_MOVES_LOG,NYC,$69,H7,$70,I7 + +EndOfOperatingRound,5.2 +ORWorthIncrease,Marcus,5.2,$41 +ORWorthIncrease,Si,5.2,$136 +ORWorthIncrease,Ed,5.2,$144 +ORWorthIncrease,Phil,5.2,$344 +ORWorthIncrease,Chris,5.2,$486 +Has,C&O,$60 +Has,Erie,$560 +Has,N&W,$213 +Has,NYC,$179 +Has,NYNH,$421 +Has,PRR,$20 +Has,RDG,$330 +Has,Marcus,$275 +Has,Si,$238 +Has,Ed,$188 +Has,Phil,$476 +Has,Chris,$459 +StartStockRound,6 +HasPriority,Chris +START_COMPANY_LOG,Chris,B&M,$76,$152,2,20,BANK +BUY_SHARE_LOG,Marcus,10,N&W,Pool,$70 +SELL_SHARES_LOG,Si,4,10,40,Erie,$360 +PRICE_MOVES_LOG,Erie,$90,G2,$67,G6 +START_COMPANY_LOG,Si,CPR,$82,$164,2,20,BANK +BUY_SHARE_LOG,Ed,10,C&O,IPO,$90 +BUY_SHARE_LOG,Phil,10,B&O,IPO,$100 +BUY_SHARE_LOG,Chris,10,B&M,IPO,$76 +BUY_SHARE_LOG,Marcus,10,N&W,Pool,$70 +BUY_SHARE_LOG,Si,10,CPR,IPO,$82 +BUY_SHARE_LOG,Ed,10,C&O,IPO,$90 +SELL_SHARES_LOG,Phil,5,10,50,C&O,$560 +PRICE_MOVES_LOG,C&O,$112,I2,$70,I7 +IS_NOW_PRES_OF,Ed,C&O +BUY_SHARE_LOG,Phil,10,B&O,IPO,$100 +BUY_SHARE_LOG,Chris,10,B&M,IPO,$76 +BUY_SHARE_LOG,Marcus,10,N&W,Pool,$70 +BUY_SHARE_LOG,Si,10,CPR,IPO,$82 +PASSES,Ed +BUY_SHARE_LOG,Phil,10,B&O,IPO,$100 +IS_NOW_PRES_OF,Phil,B&O +BUY_SHARE_LOG,Chris,10,B&M,IPO,$76 +PASSES,Marcus +BUY_SHARE_LOG,Si,10,CPR,IPO,$82 +PASSES,Ed +BUY_SHARE_LOG,Phil,10,B&O,IPO,$100 +FloatsWithCash,B&O,$1000 +BUY_SHARE_LOG,Chris,10,B&M,IPO,$76 +FloatsWithCash,B&M,$760 +PASSES,Marcus +BUY_SHARE_LOG,Si,10,CPR,IPO,$82 +FloatsWithCash,CPR,$820 +PASSES,Ed +BUY_SHARE_LOG,Phil,10,B&O,IPO,$100 +Autopasses,Chris +Autopasses,Marcus +BUY_SHARE_LOG,Si,10,B&M,IPO,$76 +Autopasses,Ed +BUY_SHARE_LOG,Phil,10,B&O,IPO,$100 +Autopasses,Chris +Autopasses,Marcus +SELL_SHARE_LOG,Si,10,B&M,$76 +PRICE_MOVES_LOG,B&M,$76,G4,$71,G5 +BUY_SHARE_LOG,Si,10,B&O,IPO,$100 +Autopasses,Ed +BUY_SHARE_LOG,Phil,10,RDG,IPO,$100 +Autopasses,Chris +Autopasses,Marcus +SELL_SHARE_LOG,Si,10,B&O,$100 +PRICE_MOVES_LOG,B&O,$100,G1,$90,G2 +BUY_SHARE_LOG,Si,10,RDG,IPO,$100 +Autopasses,Ed +BUY_SHARE_LOG,Phil,10,B&M,Pool,$71 +Autopasses,Chris +Autopasses,Marcus +SELL_SHARE_LOG,Si,10,RDG,$112 +PRICE_MOVES_LOG,RDG,$112,I2,$100,I3 +BUY_SHARE_LOG,Si,10,C&O,Pool,$70 +Autopasses,Ed +BUY_SHARE_LOG,Phil,10,Erie,Pool,$67 +Autopasses,Chris +Autopasses,Marcus +SELL_SHARE_LOG,Si,10,C&O,$70 +BUY_SHARE_LOG,Si,10,NYNH,Pool,$71 +Autopasses,Ed +BUY_SHARE_LOG,Phil,10,Erie,Pool,$67 +Autopasses,Chris +Autopasses,Marcus +SELL_SHARE_LOG,Si,10,NYNH,$71 +PRICE_MOVES_LOG,NYNH,$71,H6,$69,H7 +BUY_SHARE_LOG,Si,10,PRR,IPO,$76 +Autopasses,Ed +BUY_SHARE_LOG,Phil,10,B&M,IPO,$76 +Autopasses,Chris +Autopasses,Marcus +SELL_SHARE_LOG,Si,10,PRR,$76 +PRICE_MOVES_LOG,PRR,$76,G4,$71,G5 +BUY_SHARE_LOG,Si,10,NYC,Pool,$70 +Autopasses,Ed +PASSES,Phil +Autopasses,Chris +Autopasses,Marcus +PASSES,Si + +END_SR,6 +PRICE_MOVES_LOG,N&W,$70,I7,$75,I6 +SoldOut,N&W,$70,I7,$75,I6 +Has,B&M,$760 +Has,B&O,$1000 +Has,C&O,$60 +Has,CPR,$820 +Has,Erie,$560 +Has,N&W,$213 +Has,NYC,$179 +Has,NYNH,$421 +Has,PRR,$20 +Has,RDG,$330 +Has,Marcus,$65 +Has,Si,$48 +Has,Ed,$8 +Has,Phil,$55 +Has,Chris,$3 +START_OR,6.1 + +CompanyOperates,RDG,Ed +LaysTileAt,RDG,63,H10,SW +CompanyRevenue,RDG,$380 +CompanyPaysOutFull,RDG,$380 +Payout,Phil,$38,1,10 +Payout,Ed,$228,6,10 +Payout,RDG,$38,1,10 +PRICE_MOVES_LOG,RDG,$100,I3,$111,J3 + +CompanyOperates,B&O,Phil +LaysTileAt,B&O,40,F18,W +LAYS_TOKEN_ON,B&O,G19,$40 +CompanyDoesNotPayDividend,B&O +PRICE_MOVES_LOG,B&O,$90,G2,$82,F2 +BuysTrain,B&O,5,IPO,$450 +All 5-trains are sold out, 6-trains now available + +CompanyOperates,CPR,Si +CompanyDoesNotPayDividend,CPR +PRICE_MOVES_LOG,CPR,$82,G3,$76,F3 +BuysTrain,CPR,6,IPO,$630 +FirstTrainBought,6 +StartOfPhase,6 + +CompanyOperates,N&W,Chris +LaysTileAt,N&W,7,G9,SE +LAYS_TOKEN_ON,N&W,I15,$100 +CompanyRevenue,N&W,$450 +CompanyWithholds,N&W,$450 +PRICE_MOVES_LOG,N&W,$75,I6,$71,H6 + +CompanyOperates,B&M,Chris +LaysTileAt,B&M,15,F22,W +LAYS_TOKEN_ON,B&M,E19,$40 +CompanyDoesNotPayDividend,B&M +PRICE_MOVES_LOG,B&M,$71,G5,$67,F5 +BuysTrain,B&M,6,IPO,$630 +BuysTrain,B&M,5,N&W,$90 + +CompanyOperates,PRR,Chris +LaysTileAt,PRR,18,G9,E +CompanyRevenue,PRR,$360 +CompanyPaysOutFull,PRR,$360 +Payout,Phil,$36,1,10 +Payout,Chris,$216,6,10 +Payout,PRR,$36,1,10 +PRICE_MOVES_LOG,PRR,$71,G5,$76,H5 +TrainsObsoleteRusted,3,PRR +BuysTrain,PRR,5,B&M,$6 + +CompanyOperates,NYC,Si +LaysTileAt,NYC,53,E23,W +CompanyRevenue,NYC,$200 +CompanyWithholds,NYC,$200 +PRICE_MOVES_LOG,NYC,$70,I7,$69,H7 +BuysTrain,NYC,6,CPR,$1 + +CompanyOperates,C&O,Ed +LaysTileAt,C&O,8,I13,NE +CompanyRevenue,C&O,$320 +CompanyWithholds,C&O,$320 +PRICE_MOVES_LOG,C&O,$70,I7,$69,H7 +TrainsObsoleteRusted,3,C&O + +CompanyOperates,NYNH,Marcus +LaysTileAt,NYNH,63,F16,SW +CompanyRevenue,NYNH,$370 +CompanyPaysOutFull,NYNH,$370 +Payout,Phil,$37,1,10 +Payout,Marcus,$222,6,10 +Payout,NYNH,$111,3,10 +PRICE_MOVES_LOG,NYNH,$69,H7,$70,I7 +TrainsObsoleteRusted,3,NYNH +BuysTrain,NYNH,4,Erie,$230 + +CompanyOperates,Erie,Marcus +LaysTileAt,Erie,65,E11,SE +CompanyDoesNotPayDividend,Erie +PRICE_MOVES_LOG,Erie,$67,G6,$65,F6 +BuysTrain,Erie,7,IPO,$710 +FirstTrainBought,7 + +EndOfOperatingRound,6.1 +ORWorthIncrease,Marcus,6.1,$206 +ORWorthIncrease,Si,6.1,-$41 +ORWorthIncrease,Ed,6.1,$276 +ORWorthIncrease,Phil,6.1,$62 +ORWorthIncrease,Chris,6.1,$198 +Has,B&M,$6 +Has,B&O,$510 +Has,C&O,$380 +Has,CPR,$191 +Has,Erie,$80 +Has,N&W,$653 +Has,NYC,$378 +Has,NYNH,$302 +Has,PRR,$50 +Has,RDG,$368 +Has,Marcus,$287 +Has,Si,$48 +Has,Ed,$236 +Has,Phil,$166 +Has,Chris,$219 +START_OR,6.2 + +CompanyOperates,RDG,Ed +LaysTileAt,RDG,9,I9,SW +CompanyRevenue,RDG,$380 +CompanyPaysOutFull,RDG,$380 +Payout,Phil,$38,1,10 +Payout,Ed,$228,6,10 +Payout,RDG,$38,1,10 +PRICE_MOVES_LOG,RDG,$111,J3,$125,K3 +TrainsObsoleteRusted,3,RDG + +CompanyOperates,B&O,Phil +LaysTileAt,B&O,61,E23,NE +CompanyRevenue,B&O,$250 +CompanyWithholds,B&O,$250 +PRICE_MOVES_LOG,B&O,$82,F2,$76,E2 +ExchangesTrain,B&O,5,D,IPO,$750 +FirstTrainBought,D +StartOfPhase,D + +CompanyOperates,PRR,Chris +LaysTileAt,PRR,9,H8,W +CompanyRevenue,PRR,$450 +CompanyWithholds,PRR,$450 +PRICE_MOVES_LOG,PRR,$76,H5,$71,G5 +TrainsObsoleteRusted,4,PRR +BuysTrain,PRR,5,Pool,$450 + +CompanyOperates,CPR,Si +CompanyDoesNotPayDividend,CPR +PRICE_MOVES_LOG,CPR,$76,F3,$70,E3 + +CompanyOperates,N&W,Chris +LaysTileAt,N&W,8,H6,NW +CompanyRevenue,N&W,$200 +CompanyPaysOutFull,N&W,$200 +Payout,Chris,$120,6,10 +Payout,Phil,$20,1,10 +Payout,Marcus,$60,3,10 +PRICE_MOVES_LOG,N&W,$71,H6,$75,I6 +TrainsObsoleteRusted,4,N&W +BuysTrain,N&W,6,IPO,$630 + +CompanyOperates,NYNH,Marcus +LaysTileAt,NYNH,9,F14,W +CompanyRevenue,NYNH,$400 +CompanyWithholds,NYNH,$400 +PRICE_MOVES_LOG,NYNH,$70,I7,$69,H7 +TrainsObsoleteRusted,4,NYNH +TrainsObsoleteRusted,4,NYNH +BuysTrain,NYNH,6,IPO,$630 + +CompanyOperates,NYC,Si +LaysTileAt,NYC,9,C23,NW +CompanyRevenue,NYC,$490 +CompanyWithholds,NYC,$490 +PRICE_MOVES_LOG,NYC,$69,H7,$67,G7 +TrainsObsoleteRusted,4,NYC + +CompanyOperates,C&O,Ed +LaysTileAt,C&O,63,K13,SW +CompanyRevenue,C&O,$190 +CompanyWithholds,C&O,$190 +PRICE_MOVES_LOG,C&O,$69,H7,$67,G7 +TrainsObsoleteRusted,4,C&O +BuysTrain,C&O,5,RDG,$494 + +CompanyOperates,B&M,Chris +LaysTileAt,B&M,44,E21,SW +CompanyRevenue,B&M,$270 +CompanyPaysOutFull,B&M,$270 +Payout,Chris,$162,6,10 +Payout,Phil,$54,2,10 +PRICE_MOVES_LOG,B&M,$67,F5,$71,G5 + +CompanyOperates,Erie,Marcus +LaysTileAtFor,Erie,59,D10,W,$80 +CompanyRevenue,Erie,$100 +CompanyPaysOutFull,Erie,$100 +Payout,Phil,$20,2,10 +Payout,Marcus,$50,5,10 +Payout,Erie,$20,2,10 +PRICE_MOVES_LOG,Erie,$65,F6,$67,G6 + +EndOfOperatingRound,6.2 +ORWorthIncrease,Marcus,6.2,$126 +ORWorthIncrease,Si,6.2,-$46 +ORWorthIncrease,Ed,6.2,$296 +ORWorthIncrease,Phil,6.2,$116 +ORWorthIncrease,Chris,6.2,$300 +Has,B&M,$6 +Has,B&O,$10 +Has,C&O,$76 +Has,CPR,$191 +Has,Erie,$20 +Has,N&W,$23 +Has,NYC,$868 +Has,NYNH,$72 +Has,PRR,$50 +Has,RDG,$900 +Has,Marcus,$397 +Has,Si,$48 +Has,Ed,$464 +Has,Phil,$298 +Has,Chris,$501 +START_OR,6.3 + +CompanyOperates,RDG,Ed +LaysTileAt,RDG,9,G11,SW +CompanyDoesNotPayDividend,RDG +PRICE_MOVES_LOG,RDG,$125,K3,$111,J3 +BuysTrain,RDG,D,IPO,$900 + +CompanyOperates,B&O,Phil +LaysTileAt,B&O,8,G5,NE +CompanyRevenue,B&O,$480 +CompanyPaysOutFull,B&O,$480 +Payout,Phil,$288,6,10 +Payout,Ed,$96,2,10 +Payout,B&O,$48,1,10 +PRICE_MOVES_LOG,B&O,$76,E2,$82,F2 + +CompanyOperates,N&W,Chris +LaysTileAt,N&W,25,G5,SE +CompanyRevenue,N&W,$290 +CompanyPaysOutFull,N&W,$290 +Payout,Phil,$29,1,10 +Payout,Chris,$174,6,10 +Payout,Marcus,$87,3,10 +PRICE_MOVES_LOG,N&W,$75,I6,$80,J6 + +CompanyOperates,PRR,Chris +LaysTileAt,PRR,8,G3,NW +CompanyRevenue,PRR,$490 +CompanyPaysOutFull,PRR,$490 +Payout,Chris,$294,6,10 +Payout,Phil,$49,1,10 +Payout,PRR,$49,1,10 +PRICE_MOVES_LOG,PRR,$71,G5,$76,H5 + +CompanyOperates,B&M,Chris +LaysTileAt,B&M,7,B22,E +CompanyRevenue,B&M,$270 +CompanyPaysOutFull,B&M,$270 +Payout,Chris,$162,6,10 +Payout,Phil,$54,2,10 +PRICE_MOVES_LOG,B&M,$71,G5,$76,H5 + +CompanyOperates,CPR,Si +LaysTileAt,CPR,58,B20,NW +CompanyDoesNotPayDividend,CPR +PRICE_MOVES_LOG,CPR,$70,E3,$65,D3 +BuysTrain,CPR,6,NYC,$70 + +CompanyOperates,NYNH,Marcus +LaysTileAt,NYNH,8,F12,E +CompanyRevenue,NYNH,$310 +CompanyPaysOutFull,NYNH,$310 +Payout,Phil,$31,1,10 +Payout,Marcus,$186,6,10 +Payout,NYNH,$93,3,10 +PRICE_MOVES_LOG,NYNH,$69,H7,$70,I7 + +CompanyOperates,Erie,Marcus +LaysTileAt,Erie,66,D10,E +CompanyRevenue,Erie,$110 +CompanyPaysOutFull,Erie,$110 +Payout,Phil,$22,2,10 +Payout,Marcus,$55,5,10 +Payout,Erie,$22,2,10 +PRICE_MOVES_LOG,Erie,$67,G6,$71,H6 + +CompanyOperates,NYC,Si +LaysTileAt,NYC,27,B22,E +CompanyDoesNotPayDividend,NYC +PRICE_MOVES_LOG,NYC,$67,G7,$63,F7 +BuysTrain,NYC,D,IPO,$900 + +CompanyOperates,C&O,Ed +LaysTileAt,C&O,16,I13,NW +CompanyRevenue,C&O,$230 +CompanyPaysOutFull,C&O,$230 +Payout,Phil,$23,1,10 +Payout,Ed,$46,2,10 +Payout,C&O,$115,5,10 +PRICE_MOVES_LOG,C&O,$67,G7,$69,H7 + +EndOfOperatingRound,6.3 +ORWorthIncrease,Marcus,6.3,$369 +ORWorthIncrease,Si,6.3,-$50 +ORWorthIncrease,Ed,6.3,$74 +ORWorthIncrease,Phil,6.3,$545 +ORWorthIncrease,Chris,6.3,$720 +Has,B&M,$6 +Has,B&O,$58 +Has,C&O,$191 +Has,CPR,$121 +Has,Erie,$42 +Has,N&W,$23 +Has,NYC,$38 +Has,NYNH,$165 +Has,PRR,$99 +Has,RDG,$0 +Has,Marcus,$725 +Has,Si,$48 +Has,Ed,$606 +Has,Phil,$794 +Has,Chris,$1131 +StartStockRound,7 +HasPriority,Ed +BUY_SHARE_LOG,Ed,10,C&O,Pool,$69 +SELL_SHARES_LOG,Phil,2,10,20,Erie,$142 +PRICE_MOVES_LOG,Erie,$71,H6,$68,H8 +BUY_SHARE_LOG,Phil,10,NYC,Pool,$63 +SELL_SHARE_LOG,Chris,10,N&W,$80 +BUY_SHARE_LOG,Chris,10,B&O,Pool,$82 +BUY_SHARE_LOG,Marcus,10,N&W,Pool,$80 +SELL_SHARE_LOG,Si,10,CPR,$65 +PRICE_MOVES_LOG,CPR,$65,D3,$60,D4 +BUY_SHARE_LOG,Si,10,NYC,Pool,$63 +BUY_SHARE_LOG,Ed,10,C&O,Pool,$69 +BUY_SHARE_LOG,Phil,10,CPR,Pool,$60 +SELL_SHARE_LOG,Chris,10,B&O,$82 +PRICE_MOVES_LOG,B&O,$82,F2,$76,F3 +BUY_SHARE_LOG,Chris,10,NYC,Pool,$63 +BUY_SHARE_LOG,Marcus,10,NYC,Pool,$63 +Autopasses,Si +BUY_SHARE_LOG,Ed,10,C&O,Pool,$69 +BUY_SHARE_LOG,Phil,10,RDG,IPO,$100 +BUY_SHARE_LOG,Chris,10,CPR,IPO,$82 +BUY_SHARE_LOG,Marcus,10,CPR,IPO,$82 +Autopasses,Si +BUY_SHARE_LOG,Ed,10,C&O,Pool,$69 +SELL_SHARES_LOG,Phil,2,10,20,B&M,$152 +PRICE_MOVES_LOG,B&M,$76,H5,$69,H7 +BUY_SHARE_LOG,Phil,10,RDG,IPO,$100 +BUY_SHARE_LOG,Chris,10,CPR,IPO,$82 +BUY_SHARE_LOG,Marcus,10,CPR,IPO,$82 +Autopasses,Si +BUY_SHARE_LOG,Ed,10,PRR,Pool,$76 +BUY_SHARE_LOG,Phil,10,RDG,Pool,$111 +PASSES,Chris +BUY_SHARE_LOG,Marcus,10,B&O,Pool,$76 +Autopasses,Si +BUY_SHARE_LOG,Ed,10,PRR,IPO,$76 +SELL_SHARE_LOG,Phil,10,C&O,$69 +PRICE_MOVES_LOG,C&O,$69,H7,$68,H8 +BUY_SHARE_LOG,Phil,10,PRR,IPO,$76 +Autopasses,Chris +PASSES,Marcus +Autopasses,Si +BUY_SHARE_LOG,Ed,10,B&O,IPO,$100 +Autopasses,Phil +Autopasses,Chris +PASSES,Marcus +Autopasses,Si +PASSES,Ed + +END_SR,7 +PRICE_MOVES_LOG,RDG,$111,J3,$126,J2 +SoldOut,RDG,$111,J3,$126,J2 +PRICE_MOVES_LOG,N&W,$80,J6,$90,J5 +SoldOut,N&W,$80,J6,$90,J5 +PRICE_MOVES_LOG,PRR,$76,H5,$82,H4 +SoldOut,PRR,$76,H5,$82,H4 +PRICE_MOVES_LOG,B&O,$76,F3,$82,F2 +SoldOut,B&O,$76,F3,$82,F2 +PRICE_MOVES_LOG,NYC,$63,F7,$65,F6 +SoldOut,NYC,$63,F7,$65,F6 +PRICE_MOVES_LOG,CPR,$60,D4,$65,D3 +SoldOut,CPR,$60,D4,$65,D3 +Has,B&M,$6 +Has,B&O,$58 +Has,C&O,$191 +Has,CPR,$121 +Has,Erie,$42 +Has,N&W,$23 +Has,NYC,$38 +Has,NYNH,$165 +Has,PRR,$99 +Has,RDG,$0 +Has,Marcus,$342 +Has,Si,$50 +Has,Ed,$78 +Has,Phil,$647 +Has,Chris,$984 +START_OR,7.1 + +CompanyOperates,RDG,Ed +LaysTileAt,RDG,56,G7,NE +CompanyRevenue,RDG,$340 +CompanyPaysOutFull,RDG,$340 +Payout,Phil,$136,4,10 +Payout,Ed,$204,6,10 +PRICE_MOVES_LOG,RDG,$126,J2,$142,K2 + +CompanyOperates,N&W,Chris +LaysTileAt,N&W,45,G5,W +CompanyRevenue,N&W,$290 +CompanyPaysOutFull,N&W,$290 +Payout,Chris,$145,5,10 +Payout,Phil,$29,1,10 +Payout,Marcus,$116,4,10 +PRICE_MOVES_LOG,N&W,$90,J5,$100,K5 + +CompanyOperates,PRR,Chris +LaysTileAt,PRR,25,F12,E +CompanyRevenue,PRR,$490 +CompanyPaysOutFull,PRR,$490 +Payout,Chris,$294,6,10 +Payout,Phil,$98,2,10 +Payout,Ed,$98,2,10 +PRICE_MOVES_LOG,PRR,$82,H4,$90,I4 + +CompanyOperates,B&O,Phil +LaysTileAt,B&O,8,E3,SW +CompanyRevenue,B&O,$540 +CompanyPaysOutFull,B&O,$540 +Payout,Phil,$324,6,10 +Payout,Ed,$162,3,10 +Payout,Marcus,$54,1,10 +PRICE_MOVES_LOG,B&O,$82,F2,$90,G2 + +CompanyOperates,NYNH,Marcus +LaysTileAt,NYNH,8,E13,W +CompanyRevenue,NYNH,$310 +CompanyPaysOutFull,NYNH,$310 +Payout,Phil,$31,1,10 +Payout,Marcus,$186,6,10 +Payout,NYNH,$93,3,10 +PRICE_MOVES_LOG,NYNH,$70,I7,$75,I6 + +CompanyOperates,B&M,Chris +LaysTileAt,B&M,41,B22,E +CompanyRevenue,B&M,$270 +CompanyPaysOutFull,B&M,$270 +Payout,Chris,$162,6,10 +Payout,B&M,$54,2,10 +PRICE_MOVES_LOG,B&M,$69,H7,$70,I7 + +CompanyOperates,Erie,Marcus +LaysTileAt,Erie,7,D8,E +LAYS_TOKEN_ON,Erie,D10,$40 +CompanyRevenue,Erie,$160 +CompanyPaysOutFull,Erie,$160 +Payout,Marcus,$80,5,10 +Payout,Erie,$64,4,10 +PRICE_MOVES_LOG,Erie,$68,H8,$69,H7 + +CompanyOperates,C&O,Ed +LaysTileAt,C&O,43,I13,NW +CompanyRevenue,C&O,$230 +CompanyPaysOutFull,C&O,$230 +Payout,Ed,$138,6,10 +Payout,C&O,$46,2,10 +PRICE_MOVES_LOG,C&O,$68,H8,$69,H7 + +CompanyOperates,NYC,Si +LaysTileAt,NYC,23,G11,SW +CompanyRevenue,NYC,$590 +CompanyPaysOutFull,NYC,$590 +Payout,Chris,$59,1,10 +Payout,Phil,$118,2,10 +Payout,Marcus,$59,1,10 +Payout,Si,$354,6,10 +PRICE_MOVES_LOG,NYC,$65,F6,$67,G6 + +CompanyOperates,CPR,Si +LaysTileAtFor,CPR,7,B18,NW,$80 +CompanyRevenue,CPR,$250 +CompanyPaysOutFull,CPR,$250 +Payout,Chris,$50,2,10 +Payout,Phil,$25,1,10 +Payout,Marcus,$50,2,10 +Payout,Si,$125,5,10 +PRICE_MOVES_LOG,CPR,$65,D3,$70,E3 + +EndOfOperatingRound,7.1 +ORWorthIncrease,Marcus,7.1,$640 +ORWorthIncrease,Si,7.1,$516 +ORWorthIncrease,Ed,7.1,$744 +ORWorthIncrease,Phil,7.1,$913 +ORWorthIncrease,Chris,7.1,$826 +Has,B&M,$60 +Has,B&O,$58 +Has,C&O,$237 +Has,CPR,$41 +Has,Erie,$66 +Has,N&W,$23 +Has,NYC,$38 +Has,NYNH,$258 +Has,PRR,$99 +Has,RDG,$0 +Has,Marcus,$887 +Has,Si,$529 +Has,Ed,$680 +Has,Phil,$1408 +Has,Chris,$1694 +START_OR,7.2 + +CompanyOperates,RDG,Ed +LaysTileAt,RDG,24,F14,W +CompanyRevenue,RDG,$380 +CompanyPaysOutFull,RDG,$380 +Payout,Phil,$152,4,10 +Payout,Ed,$228,6,10 +PRICE_MOVES_LOG,RDG,$142,K2,$160,L2 + +CompanyOperates,N&W,Chris +LaysTileAt,N&W,24,E3,SW +CompanyRevenue,N&W,$290 +CompanyPaysOutFull,N&W,$290 +Payout,Chris,$145,5,10 +Payout,Phil,$29,1,10 +Payout,Marcus,$116,4,10 +PRICE_MOVES_LOG,N&W,$100,K5,$110,K4 + +CompanyOperates,PRR,Chris +LaysTileAt,PRR,4,D4,W +CompanyRevenue,PRR,$490 +CompanyPaysOutFull,PRR,$490 +Payout,Chris,$294,6,10 +Payout,Phil,$98,2,10 +Payout,Ed,$98,2,10 +PRICE_MOVES_LOG,PRR,$90,I4,$100,J4 + +CompanyOperates,B&O,Phil +LaysTileAt,B&O,8,J8,W +CompanyRevenue,B&O,$570 +CompanyPaysOutFull,B&O,$570 +Payout,Phil,$342,6,10 +Payout,Ed,$171,3,10 +Payout,Marcus,$57,1,10 +PRICE_MOVES_LOG,B&O,$90,G2,$100,H2 + +CompanyOperates,NYNH,Marcus +LaysTileAt,NYNH,9,D12,W +CompanyRevenue,NYNH,$310 +CompanyPaysOutFull,NYNH,$310 +Payout,Phil,$31,1,10 +Payout,Marcus,$186,6,10 +Payout,NYNH,$93,3,10 +PRICE_MOVES_LOG,NYNH,$75,I6,$80,J6 + +CompanyOperates,B&M,Chris +CompanyRevenue,B&M,$270 +CompanyPaysOutFull,B&M,$270 +Payout,Chris,$162,6,10 +Payout,B&M,$54,2,10 +PRICE_MOVES_LOG,B&M,$70,I7,$75,I6 + +CompanyOperates,CPR,Si +LaysTileAt,CPR,57,B16,SW +CompanyRevenue,CPR,$250 +CompanyPaysOutFull,CPR,$250 +Payout,Chris,$50,2,10 +Payout,Phil,$25,1,10 +Payout,Marcus,$50,2,10 +Payout,Si,$125,5,10 +PRICE_MOVES_LOG,CPR,$70,E3,$76,F3 + +CompanyOperates,Erie,Marcus +LaysTileAt,Erie,45,F12,SW +CompanyRevenue,Erie,$270 +CompanyPaysOutFull,Erie,$270 +Payout,Marcus,$135,5,10 +Payout,Erie,$108,4,10 +PRICE_MOVES_LOG,Erie,$69,H7,$70,I7 + +CompanyOperates,C&O,Ed +LaysTileAt,C&O,9,E15,SW +CompanyRevenue,C&O,$230 +CompanyPaysOutFull,C&O,$230 +Payout,Ed,$138,6,10 +Payout,C&O,$46,2,10 +PRICE_MOVES_LOG,C&O,$69,H7,$70,I7 + +CompanyOperates,NYC,Si +LaysTileAt,NYC,43,G9,E +CompanyRevenue,NYC,$600 +CompanyPaysOutFull,NYC,$600 +Payout,Chris,$60,1,10 +Payout,Phil,$120,2,10 +Payout,Marcus,$60,1,10 +Payout,Si,$360,6,10 +PRICE_MOVES_LOG,NYC,$67,G6,$71,H6 + +EndOfOperatingRound,7.2 +ORWorthIncrease,Marcus,7.2,$705 +ORWorthIncrease,Si,7.2,$539 +ORWorthIncrease,Ed,7.2,$799 +ORWorthIncrease,Phil,7.2,$978 +ORWorthIncrease,Chris,7.2,$867 +Has,B&M,$114 +Has,B&O,$58 +Has,C&O,$283 +Has,CPR,$41 +Has,Erie,$174 +Has,N&W,$23 +Has,NYC,$38 +Has,NYNH,$351 +Has,PRR,$99 +Has,RDG,$0 +Has,Marcus,$1491 +Has,Si,$1014 +Has,Ed,$1315 +Has,Phil,$2205 +Has,Chris,$2405 +START_OR,7.3 + +CompanyOperates,RDG,Ed +LaysTileAt,RDG,7,D16,SW +CompanyRevenue,RDG,$410 +CompanyPaysOutFull,RDG,$410 +Payout,Phil,$164,4,10 +Payout,Ed,$246,6,10 +PRICE_MOVES_LOG,RDG,$160,L2,$180,M2 + +CompanyOperates,N&W,Chris +LaysTileAt,N&W,23,J8,SW +CompanyRevenue,N&W,$290 +CompanyPaysOutFull,N&W,$290 +Payout,Phil,$29,1,10 +Payout,Chris,$145,5,10 +Payout,Marcus,$116,4,10 +PRICE_MOVES_LOG,N&W,$110,K4,$120,L4 + +CompanyOperates,PRR,Chris +LaysTileAt,PRR,8,K7,NE +CompanyRevenue,PRR,$490 +CompanyPaysOutFull,PRR,$490 +Payout,Chris,$294,6,10 +Payout,Phil,$98,2,10 +Payout,Ed,$98,2,10 +PRICE_MOVES_LOG,PRR,$100,J4,$110,K4 + +CompanyOperates,B&O,Phil +LaysTileAt,B&O,16,E13,SW +CompanyRevenue,B&O,$580 +CompanyPaysOutFull,B&O,$580 +Payout,Phil,$348,6,10 +Payout,Ed,$174,3,10 +Payout,Marcus,$58,1,10 +PRICE_MOVES_LOG,B&O,$100,H2,$112,I2 + +CompanyOperates,NYNH,Marcus +LaysTileAt,NYNH,23,D12,E +CompanyRevenue,NYNH,$310 +CompanyPaysOutFull,NYNH,$310 +Payout,Phil,$31,1,10 +Payout,Marcus,$186,6,10 +Payout,NYNH,$93,3,10 +PRICE_MOVES_LOG,NYNH,$80,J6,$90,J5 + +CompanyOperates,CPR,Si +LaysTileAt,CPR,9,C13,W +CompanyRevenue,CPR,$250 +CompanyPaysOutFull,CPR,$250 +Payout,Phil,$25,1,10 +Payout,Chris,$50,2,10 +Payout,Marcus,$50,2,10 +Payout,Si,$125,5,10 +PRICE_MOVES_LOG,CPR,$76,F3,$82,G3 + +CompanyOperates,B&M,Chris +CompanyRevenue,B&M,$270 +CompanyPaysOutFull,B&M,$270 +Payout,Chris,$162,6,10 +Payout,B&M,$54,2,10 +PRICE_MOVES_LOG,B&M,$75,I6,$80,J6 + +CompanyOperates,NYC,Si +LaysTileAt,NYC,8,D20,SW +CompanyRevenue,NYC,$600 +CompanyPaysOutFull,NYC,$600 +Payout,Chris,$60,1,10 +Payout,Phil,$120,2,10 +Payout,Marcus,$60,1,10 +Payout,Si,$360,6,10 +PRICE_MOVES_LOG,NYC,$71,H6,$75,I6 + +CompanyOperates,Erie,Marcus +LAYS_TOKEN_ON,Erie,H16,$100 +CompanyRevenue,Erie,$330 +CompanyPaysOutFull,Erie,$330 +Payout,Marcus,$165,5,10 +Payout,Erie,$132,4,10 +PRICE_MOVES_LOG,Erie,$70,I7,$75,I6 + +CompanyOperates,C&O,Ed +CompanyRevenue,C&O,$230 +CompanyPaysOutFull,C&O,$230 +Payout,Ed,$138,6,10 +Payout,C&O,$46,2,10 +PRICE_MOVES_LOG,C&O,$70,I7,$75,I6 + +EndOfOperatingRound,7.3 +ORWorthIncrease,Marcus,7.3,$788 +ORWorthIncrease,Si,7.3,$539 +ORWorthIncrease,Ed,7.3,$862 +ORWorthIncrease,Phil,7.3,$1021 +ORWorthIncrease,Chris,7.3,$867 +Has,B&M,$168 +Has,B&O,$58 +Has,C&O,$329 +Has,CPR,$41 +Has,Erie,$206 +Has,N&W,$23 +Has,NYC,$38 +Has,NYNH,$444 +Has,PRR,$99 +Has,RDG,$0 +Has,Marcus,$2126 +Has,Si,$1499 +Has,Ed,$1971 +Has,Phil,$3020 +Has,Chris,$3116 +StartStockRound,8 +HasPriority,Phil +SELL_SHARE_LOG,Phil,10,CPR,$82 +PRICE_MOVES_LOG,CPR,$82,G3,$76,G4 +SELL_SHARES_LOG,Chris,2,10,20,CPR,$152 +PRICE_MOVES_LOG,CPR,$76,G4,$67,G6 +SELL_SHARE_LOG,Chris,10,B&M,$80 +BUY_SHARE_LOG,Chris,10,Erie,Pool,$75 +SELL_SHARES_LOG,Marcus,3,10,30,N&W,$360 +BUY_SHARE_LOG,Marcus,10,Erie,Pool,$75 +BUY_SHARE_LOG,Si,10,Erie,Pool,$75 +BUY_SHARE_LOG,Ed,10,Erie,Pool,$75 +Autopasses,Phil +SELL_SHARE_LOG,Chris,10,B&M,$80 +BUY_SHARE_LOG,Chris,10,NYNH,Pool,$90 +PASSES,Marcus +BUY_SHARE_LOG,Si,10,NYNH,Pool,$90 +Autopasses,Ed +Autopasses,Phil +SELL_SHARE_LOG,Chris,10,B&M,$80 +BUY_SHARE_LOG,Chris,10,NYNH,Pool,$90 +PASSES,Marcus +BUY_SHARE_LOG,Si,10,B&M,IPO,$76 +Autopasses,Ed +Autopasses,Phil +Autopasses,Chris +Autopasses,Marcus +BUY_SHARE_LOG,Si,10,N&W,Pool,$120 +Autopasses,Ed +Autopasses,Phil +Autopasses,Chris +Autopasses,Marcus +BUY_SHARE_LOG,Si,10,N&W,Pool,$120 +Autopasses,Ed +Autopasses,Phil +Autopasses,Chris +Autopasses,Marcus +BUY_SHARE_LOG,Si,10,N&W,Pool,$120 +SELL_SHARES_LOG,Si,2,10,20,CPR,$134 +PRICE_MOVES_LOG,CPR,$67,G6,$67,G8 +Autopasses,Ed +Autopasses,Phil +Autopasses,Chris +Autopasses,Marcus +BUY_SHARE_LOG,Si,10,B&M,IPO,$76 +Autopasses,Ed +Autopasses,Phil +Autopasses,Chris +Autopasses,Marcus +SELL_SHARE_LOG,Si,10,NYNH,$90 +PRICE_MOVES_LOG,NYNH,$90,J5,$80,J6 +SELL_SHARE_LOG,Si,10,Erie,$75 +PRICE_MOVES_LOG,Erie,$75,I6,$70,I7 +BUY_SHARE_LOG,Si,10,B&M,Pool,$80 +Autopasses,Ed +Autopasses,Phil +Autopasses,Chris +Autopasses,Marcus +BUY_SHARE_LOG,Si,10,B&M,Pool,$80 +IS_NOW_PRES_OF,Si,B&M +Autopasses,Ed +Autopasses,Phil +SELL_SHARE_LOG,Chris,10,B&M,$80 +Autopasses,Marcus +BUY_SHARE_LOG,Si,10,B&M,Pool,$80 +Autopasses,Ed +Autopasses,Phil +Autopasses,Chris +Autopasses,Marcus +BUY_SHARE_LOG,Si,10,B&M,Pool,$80 +Autopasses,Ed +Autopasses,Phil +Autopasses,Chris +Autopasses,Marcus +PASSES,Si + +END_SR,8 +PRICE_MOVES_LOG,RDG,$180,M2,$200,M1 +SoldOut,RDG,$180,M2,$200,M1 +PRICE_MOVES_LOG,N&W,$120,L4,$140,L3 +SoldOut,N&W,$120,L4,$140,L3 +PRICE_MOVES_LOG,B&O,$112,I2,$126,I1 +SoldOut,B&O,$112,I2,$126,I1 +PRICE_MOVES_LOG,PRR,$110,K4,$125,K3 +SoldOut,PRR,$110,K4,$125,K3 +PRICE_MOVES_LOG,NYC,$75,I6,$82,I5 +SoldOut,NYC,$75,I6,$82,I5 +Has,B&M,$168 +Has,B&O,$58 +Has,C&O,$329 +Has,CPR,$41 +Has,Erie,$206 +Has,N&W,$23 +Has,NYC,$38 +Has,NYNH,$444 +Has,PRR,$99 +Has,RDG,$0 +Has,Marcus,$2411 +Has,Si,$801 +Has,Ed,$1896 +Has,Phil,$3102 +Has,Chris,$3333 +START_OR,8.1 + +CompanyOperates,RDG,Ed +LaysTileAt,RDG,8,J6,E +CompanyRevenue,RDG,$460 +CompanyPaysOutFull,RDG,$460 +Payout,Phil,$184,4,10 +Payout,Ed,$276,6,10 +PRICE_MOVES_LOG,RDG,$200,M1,$225,N1 + +CompanyOperates,N&W,Chris +CompanyRevenue,N&W,$310 +CompanyPaysOutFull,N&W,$310 +Payout,Phil,$31,1,10 +Payout,Chris,$155,5,10 +Payout,Marcus,$31,1,10 +Payout,Si,$93,3,10 +PRICE_MOVES_LOG,N&W,$140,L3,$155,M3 + +CompanyOperates,B&O,Phil +CompanyRevenue,B&O,$630 +CompanyPaysOutFull,B&O,$630 +Payout,Phil,$378,6,10 +Payout,Ed,$189,3,10 +Payout,Marcus,$63,1,10 +PRICE_MOVES_LOG,B&O,$126,I1,$142,J1 + +CompanyOperates,PRR,Chris +CompanyRevenue,PRR,$490 +CompanyPaysOutFull,PRR,$490 +Payout,Phil,$98,2,10 +Payout,Chris,$294,6,10 +Payout,Ed,$98,2,10 +PRICE_MOVES_LOG,PRR,$125,K3,$140,L3 + +CompanyOperates,NYC,Si +LaysTileAt,NYC,41,D12,E +CompanyRevenue,NYC,$660 +CompanyPaysOutFull,NYC,$660 +Payout,Phil,$132,2,10 +Payout,Chris,$66,1,10 +Payout,Marcus,$66,1,10 +Payout,Si,$396,6,10 +PRICE_MOVES_LOG,NYC,$82,I5,$90,J5 + +CompanyOperates,B&M,Si +LaysTileAt,B&M,23,C23,NW +CompanyRevenue,B&M,$270 +CompanyPaysOutFull,B&M,$270 +Payout,Chris,$54,2,10 +Payout,Si,$162,6,10 +Payout,B&M,$54,2,10 +PRICE_MOVES_LOG,B&M,$80,J6,$90,J5 + +CompanyOperates,NYNH,Marcus +LaysTileAt,NYNH,26,E15,NE +CompanyRevenue,NYNH,$310 +CompanyPaysOutFull,NYNH,$310 +Payout,Phil,$31,1,10 +Payout,Chris,$62,2,10 +Payout,Marcus,$186,6,10 +Payout,NYNH,$31,1,10 +PRICE_MOVES_LOG,NYNH,$80,J6,$90,J5 + +CompanyOperates,C&O,Ed +LaysTileAt,C&O,9,K5,SW +CompanyRevenue,C&O,$230 +CompanyPaysOutFull,C&O,$230 +Payout,Ed,$138,6,10 +Payout,C&O,$46,2,10 +PRICE_MOVES_LOG,C&O,$75,I6,$80,J6 + +CompanyOperates,Erie,Marcus +LaysTileAt,Erie,42,E15,NE +CompanyRevenue,Erie,$330 +CompanyPaysOutFull,Erie,$330 +Payout,Chris,$33,1,10 +Payout,Ed,$33,1,10 +Payout,Marcus,$198,6,10 +Payout,Erie,$33,1,10 +PRICE_MOVES_LOG,Erie,$70,I7,$75,I6 + +CompanyOperates,CPR,Si +LaysTileAt,CPR,27,B18,NW +CompanyRevenue,CPR,$250 +CompanyPaysOutFull,CPR,$250 +Payout,Marcus,$50,2,10 +Payout,Si,$75,3,10 +Payout,CPR,$125,5,10 +PRICE_MOVES_LOG,CPR,$67,G8,$68,H8 + +EndOfOperatingRound,8.1 +ORWorthIncrease,Marcus,8.1,$725 +ORWorthIncrease,Si,8.1,$882 +ORWorthIncrease,Ed,8.1,$997 +ORWorthIncrease,Phil,8.1,$1121 +ORWorthIncrease,Chris,8.1,$882 +Has,B&M,$222 +Has,B&O,$58 +Has,C&O,$375 +Has,CPR,$166 +Has,Erie,$239 +Has,N&W,$23 +Has,NYC,$38 +Has,NYNH,$475 +Has,PRR,$99 +Has,RDG,$0 +Has,Marcus,$3005 +Has,Si,$1527 +Has,Ed,$2630 +Has,Phil,$3956 +Has,Chris,$3997 +START_OR,8.2 + +CompanyOperates,RDG,Ed +LaysTileAt,RDG,8,L4,W +CompanyRevenue,RDG,$460 +CompanyPaysOutFull,RDG,$460 +Payout,Phil,$184,4,10 +Payout,Ed,$276,6,10 +PRICE_MOVES_LOG,RDG,$225,N1,$250,O1 + +CompanyOperates,N&W,Chris +CompanyRevenue,N&W,$310 +CompanyPaysOutFull,N&W,$310 +Payout,Phil,$31,1,10 +Payout,Chris,$155,5,10 +Payout,Marcus,$31,1,10 +Payout,Si,$93,3,10 +PRICE_MOVES_LOG,N&W,$155,M3,$170,N3 + +CompanyOperates,B&O,Phil +LaysTileAt,B&O,57,K3,SW +CompanyRevenue,B&O,$630 +CompanyPaysOutFull,B&O,$630 +Payout,Phil,$378,6,10 +Payout,Ed,$189,3,10 +Payout,Marcus,$63,1,10 +PRICE_MOVES_LOG,B&O,$142,J1,$160,K1 + +CompanyOperates,PRR,Chris +CompanyRevenue,PRR,$500 +CompanyPaysOutFull,PRR,$500 +Payout,Phil,$100,2,10 +Payout,Chris,$300,6,10 +Payout,Ed,$100,2,10 +PRICE_MOVES_LOG,PRR,$140,L3,$155,M3 + +CompanyOperates,NYC,Si +LaysTileAt,NYC,70,E13,SW +CompanyRevenue,NYC,$660 +CompanyPaysOutFull,NYC,$660 +Payout,Phil,$132,2,10 +Payout,Chris,$66,1,10 +Payout,Marcus,$66,1,10 +Payout,Si,$396,6,10 +PRICE_MOVES_LOG,NYC,$90,J5,$100,K5 + +CompanyOperates,B&M,Si +LaysTileAtFor,B&M,9,C19,NW,$80 +CompanyRevenue,B&M,$270 +CompanyPaysOutFull,B&M,$270 +Payout,Chris,$54,2,10 +Payout,Si,$162,6,10 +Payout,B&M,$54,2,10 +PRICE_MOVES_LOG,B&M,$90,J5,$100,K5 + +CompanyOperates,NYNH,Marcus +LaysTileAtFor,NYNH,8,G15,NE,$120 +CompanyRevenue,NYNH,$320 +CompanyPaysOutFull,NYNH,$320 +Payout,Phil,$32,1,10 +Payout,Chris,$64,2,10 +Payout,Marcus,$192,6,10 +Payout,NYNH,$32,1,10 +PRICE_MOVES_LOG,NYNH,$90,J5,$100,K5 + +CompanyOperates,C&O,Ed +CompanyRevenue,C&O,$230 +CompanyPaysOutFull,C&O,$230 +Payout,Ed,$138,6,10 +Payout,C&O,$46,2,10 +PRICE_MOVES_LOG,C&O,$80,J6,$90,J5 + +CompanyOperates,Erie,Marcus +CompanyRevenue,Erie,$330 +CompanyPaysOutFull,Erie,$330 +Payout,Chris,$33,1,10 +Payout,Ed,$33,1,10 +BankIsBrokenReportText +Payout,Marcus,$198,6,10 +Payout,Erie,$33,1,10 +PRICE_MOVES_LOG,Erie,$75,I6,$80,J6 + +CompanyOperates,CPR,Si +LaysTileAt,CPR,14,B16,SW +CompanyRevenue,CPR,$250 +CompanyPaysOutFull,CPR,$250 +Payout,Marcus,$50,2,10 +Payout,Si,$75,3,10 +Payout,CPR,$125,5,10 +PRICE_MOVES_LOG,CPR,$68,H8,$69,H7 + +EndOfOperatingRound,8.2 +ORWorthIncrease,Marcus,8.2,$735 +ORWorthIncrease,Si,8.2,$894 +ORWorthIncrease,Ed,8.2,$1035 +ORWorthIncrease,Phil,8.2,$1140 +ORWorthIncrease,Chris,8.2,$892 +Has,B&M,$196 +Has,B&O,$58 +Has,C&O,$421 +Has,CPR,$291 +Has,Erie,$272 +Has,N&W,$23 +Has,NYC,$38 +Has,NYNH,$387 +Has,PRR,$99 +Has,RDG,$0 +Has,Marcus,$3605 +Has,Si,$2253 +Has,Ed,$3366 +Has,Phil,$4813 +Has,Chris,$4669 +START_OR,8.3 + +CompanyOperates,RDG,Ed +CompanyRevenue,RDG,$460 +CompanyPaysOutFull,RDG,$460 +Payout,Phil,$184,4,10 +Payout,Ed,$276,6,10 +PRICE_MOVES_LOG,RDG,$250,O1,$275,P1 + +CompanyOperates,N&W,Chris +CompanyRevenue,N&W,$290 +CompanyPaysOutFull,N&W,$290 +Payout,Phil,$29,1,10 +Payout,Chris,$145,5,10 +Payout,Marcus,$29,1,10 +Payout,Si,$87,3,10 +PRICE_MOVES_LOG,N&W,$170,N3,$185,O3 + +CompanyOperates,B&O,Phil +CompanyRevenue,B&O,$630 +CompanyPaysOutFull,B&O,$630 +Payout,Phil,$378,6,10 +Payout,Ed,$189,3,10 +Payout,Marcus,$63,1,10 +PRICE_MOVES_LOG,B&O,$160,K1,$180,L1 + +CompanyOperates,PRR,Chris +CompanyRevenue,PRR,$490 +CompanyPaysOutFull,PRR,$490 +Payout,Phil,$98,2,10 +Payout,Chris,$294,6,10 +Payout,Ed,$98,2,10 +PRICE_MOVES_LOG,PRR,$155,M3,$170,N3 + +CompanyOperates,NYC,Si +CompanyRevenue,NYC,$660 +CompanyPaysOutFull,NYC,$660 +Payout,Phil,$132,2,10 +Payout,Chris,$66,1,10 +Payout,Marcus,$66,1,10 +Payout,Si,$396,6,10 +PRICE_MOVES_LOG,NYC,$100,K5,$110,K4 + +CompanyOperates,B&M,Si +CompanyRevenue,B&M,$270 +CompanyPaysOutFull,B&M,$270 +Payout,Chris,$54,2,10 +Payout,Si,$162,6,10 +Payout,B&M,$54,2,10 +PRICE_MOVES_LOG,B&M,$100,K5,$110,K4 + +CompanyOperates,NYNH,Marcus +CompanyRevenue,NYNH,$320 +CompanyPaysOutFull,NYNH,$320 +Payout,Phil,$32,1,10 +Payout,Chris,$64,2,10 +Payout,Marcus,$192,6,10 +Payout,NYNH,$32,1,10 +PRICE_MOVES_LOG,NYNH,$100,K5,$110,K4 + +CompanyOperates,C&O,Ed +CompanyRevenue,C&O,$230 +CompanyPaysOutFull,C&O,$230 +Payout,Ed,$138,6,10 +Payout,C&O,$46,2,10 +PRICE_MOVES_LOG,C&O,$90,J5,$100,K5 + +CompanyOperates,Erie,Marcus +CompanyRevenue,Erie,$330 +CompanyPaysOutFull,Erie,$330 +Payout,Chris,$33,1,10 +Payout,Ed,$33,1,10 +Payout,Marcus,$198,6,10 +Payout,Erie,$33,1,10 +PRICE_MOVES_LOG,Erie,$80,J6,$90,J5 + +CompanyOperates,CPR,Si +CompanyRevenue,CPR,$250 +CompanyPaysOutFull,CPR,$250 +Payout,Marcus,$50,2,10 +Payout,Si,$75,3,10 +Payout,CPR,$125,5,10 +PRICE_MOVES_LOG,CPR,$69,H7,$70,I7 + +EndOfOperatingRound,8.3 +ORWorthIncrease,Marcus,8.3,$765 +ORWorthIncrease,Si,8.3,$888 +ORWorthIncrease,Ed,8.3,$1044 +ORWorthIncrease,Phil,8.3,$1148 +ORWorthIncrease,Chris,8.3,$881 +Has,B&M,$250 +Has,B&O,$58 +Has,C&O,$467 +Has,CPR,$416 +Has,Erie,$305 +Has,N&W,$23 +Has,NYC,$38 +Has,NYNH,$419 +Has,PRR,$99 +Has,RDG,$0 +Has,Marcus,$4203 +Has,Si,$2973 +Has,Ed,$4100 +Has,Phil,$5666 +Has,Chris,$5325 +GameOver +EoGWinnerPhil! +EoGFinalRanking : +1. $8701 Phil +2. $7910 Chris +3. $7320 Ed +4. $6018 Marcus +5. $5058 Si diff --git a/test/data/real/1856_A.report b/test/data/real/1856_A.report new file mode 100644 index 0000000..dce4fb6 --- /dev/null +++ b/test/data/real/1856_A.report @@ -0,0 +1,2018 @@ +PlayerIs,1,Adam +PlayerIs,2,Aliza +PlayerIs,3,Ed +PlayerIs,4,Stefan +PlayerIs,5,Joakim +PlayerCash,$300 +BankHas,$10500 +StartOfPhase,2 +BankSizeIs,$10500 +StartOfInitialRound +HasPriority,Adam +BID_ITEM_LOG,Adam,$75,Ship,$225 +BID_ITEM_LOG,Aliza,$105,Tunn,$195 +BID_ITEM_LOG,Ed,$105,Brdg,$195 +BID_ITEM_LOG,Stefan,$45,W&SR,$255 +BID_ITEM_LOG,Joakim,$110,Tunn,$190 +BID_ITEM_LOG,Adam,$55,TCC,$170 +BuysItemFor,Aliza,Flos,$20 +BuysItemFor,Stefan,W&SR,$45 +BuysItemFor,Adam,TCC,$55 +BuysItemFor,Adam,Ship,$75 +BuysItemFor,Ed,Brdg,$105 +TO_AUCTION,Tunn +PASSES,Aliza +BuysItemFor,Joakim,Tunn,$110 +Has,Adam,$170 +Has,Aliza,$280 +Has,Ed,$195 +Has,Stefan,$255 +Has,Joakim,$190 +StartStockRound,1 +HasPriority,Ed +START_COMPANY_LOG,Ed,WR,$65,$130,2,20,WR +Floats,WR +START_COMPANY_LOG,Stefan,LPS,$75,$150,2,20,LPS +Floats,LPS +START_COMPANY_LOG,Joakim,GW,$80,$160,2,20,GW +Floats,GW +PASSES,Adam +START_COMPANY_LOG,Aliza,GT,$65,$130,2,20,GT +Floats,GT +BUY_SHARE_LOG,Ed,10,WR,IPO,$65 +PriceIsPaidTo,$65,WR +BUY_SHARE_LOG,Stefan,10,LPS,IPO,$75 +PriceIsPaidTo,$75,LPS +PASSES,Joakim +BUY_SHARE_LOG,Adam,10,WR,IPO,$65 +PriceIsPaidTo,$65,WR +BUY_SHARE_LOG,Aliza,10,GT,IPO,$65 +PriceIsPaidTo,$65,GT +PASSES,Ed +PASSES,Stefan +PASSES,Joakim +BUY_SHARE_LOG,Adam,10,WR,IPO,$65 +PriceIsPaidTo,$65,WR +BUY_SHARE_LOG,Aliza,10,GT,IPO,$65 +PriceIsPaidTo,$65,GT +PASSES,Ed +PASSES,Stefan +PASSES,Joakim +PASSES,Adam +PASSES,Aliza + +END_SR,1 +Has,GT,$260 +Has,LPS,$225 +Has,WR,$325 +Has,GW,$160 +Has,Adam,$40 +Has,Aliza,$20 +Has,Ed,$0 +Has,Stefan,$30 +Has,Joakim,$30 +START_OR,1.1 +ReceivesFor,Aliza,$5,Flos +ReceivesFor,Stefan,$10,W&SR +ReceivesFor,Adam,$10,TCC +ReceivesFor,Adam,$15,Ship +ReceivesFor,Ed,$20,Brdg +ReceivesFor,Joakim,$20,Tunn + +CompanyOperates,GW,Joakim +LaysTileAt,GW,5,F17,NE +CompanyDoesNotPayDividend,GW +PRICE_MOVES_LOG,GW,$80,E3,$75,D3 +BuysTrain,GW,2,IPO,$100 +FirstTrainBought,2 +CompanyTakesLoan,GW,$100,$90 + +CompanyOperates,LPS,Stefan +LaysTileAt,LPS,5,C14,N +CompanyDoesNotPayDividend,LPS +PRICE_MOVES_LOG,LPS,$75,E4,$70,D4 +BuysTrain,LPS,2,IPO,$100 +BuysTrain,LPS,2,IPO,$100 + +CompanyOperates,WR,Ed +LaysTileAt,WR,6,O16,NW +CompanyDoesNotPayDividend,WR +PRICE_MOVES_LOG,WR,$65,E6,$60,D6 +BuysTrain,WR,2,IPO,$100 +CompanyTakesLoan,WR,$100,$90 +BuysTrain,WR,2,IPO,$100 + +CompanyOperates,GT,Aliza +CompanyTakesLoan,GT,$100,$100 +LaysTileAt,GT,6,P9,NW +InterestPaidFromTreasury,GT,$10 +CompanyDoesNotPayDividend,GT +PRICE_MOVES_LOG,GT,$65,E6,$60,D6 +BuysTrain,GT,2,IPO,$100 +All 2-trains are sold out, 3-trains now available +BuysTrain,GT,3,IPO,$225 +FirstTrainBought,3 +StartOfPhase,3 + +EndOfOperatingRound,1.1 +ORWorthIncrease,Adam,1.1,-$5 +ORWorthIncrease,Aliza,1.1,-$55 +ORWorthIncrease,Ed,1.1,-$25 +ORWorthIncrease,Stefan,1.1,-$5 +ORWorthIncrease,Joakim,1.1,-$10 +Has,GT,$25 +Has,LPS,$25 +Has,WR,$215 +Has,GW,$150 +Has,Adam,$65 +Has,Aliza,$25 +Has,Ed,$20 +Has,Stefan,$40 +Has,Joakim,$50 +StartStockRound,2 +HasPriority,Ed +Autopasses,Ed +PASSES,Stefan +PASSES,Joakim +BUY_SHARE_LOG,Adam,10,GT,IPO,$65 +PriceIsPaidTo,$65,GT +PASSES,Aliza +Autopasses,Ed +PASSES,Stefan +PASSES,Joakim +Autopasses,Adam + +END_SR,2 +Has,GT,$90 +Has,LPS,$25 +Has,WR,$215 +Has,GW,$150 +Has,Adam,$0 +Has,Aliza,$25 +Has,Ed,$20 +Has,Stefan,$40 +Has,Joakim,$50 +START_OR,2.1 +ReceivesFor,Aliza,$5,Flos +ReceivesFor,Stefan,$10,W&SR +ReceivesFor,Adam,$10,TCC +ReceivesFor,Adam,$15,Ship +ReceivesFor,Ed,$20,Brdg +ReceivesFor,Joakim,$20,Tunn + +CompanyOperates,GW,Joakim +LaysTileAt,GW,8,E16,SE +CompanyRevenue,GW,$50 +CompanyMustPayLoanInterest,GW,$10 +InterestPaidFromTreasury,GW,$10 +CompanyPaysOutFull,GW,$50 +Payout,Joakim,$10,2,10 +PRICE_MOVES_LOG,GW,$75,D3,$80,E3 + +CompanyOperates,LPS,Stefan +LaysTileAt,LPS,7,B15,N +CompanyRevenue,LPS,$100 +CompanyPaysOutFull,LPS,$100 +Payout,Stefan,$30,3,10 +PRICE_MOVES_LOG,LPS,$70,D4,$75,E4 + +CompanyOperates,WR,Ed +BuysPrivateFromFor,WR,Brdg,Ed,$200 +AcquiresBonus,WR,Bridge,$10,P17,P19 +LaysTileAt,WR,59,N17,S +CompanyRevenue,WR,$120 +CompanyMustPayLoanInterest,WR,$10 +InterestPaidFromTreasury,WR,$10 +CompanyPaysOutFull,WR,$120 +Payout,Ed,$36,3,10 +Payout,Adam,$24,2,10 +PRICE_MOVES_LOG,WR,$60,D6,$65,E6 +CompanyTakesLoan,WR,$100,$90 + +CompanyOperates,GT,Aliza +LaysTileAt,GT,9,O10,SW +CompanyRevenue,GT,$90 +CompanyMustPayLoanInterest,GT,$10 +InterestPaidFromTreasury,GT,$10 +CompanyPaysOutFull,GT,$90 +Payout,Adam,$9,1,10 +Payout,Aliza,$36,4,10 +PRICE_MOVES_LOG,GT,$60,D6,$65,E6 +CompanyTakesLoan,GT,$100,$90 + +EndOfOperatingRound,2.1 +ORWorthIncrease,Adam,2.1,$43 +ORWorthIncrease,Aliza,2.1,$21 +ORWorthIncrease,Ed,2.1,$141 +ORWorthIncrease,Stefan,2.1,$55 +ORWorthIncrease,Joakim,2.1,$40 +Has,GT,$170 +Has,LPS,$25 +Has,WR,$95 +Has,GW,$140 +Has,Adam,$58 +Has,Aliza,$66 +Has,Ed,$276 +Has,Stefan,$80 +Has,Joakim,$80 +START_OR,2.2 +ReceivesFor,Aliza,$5,Flos +ReceivesFor,Stefan,$10,W&SR +ReceivesFor,Adam,$10,TCC +ReceivesFor,Adam,$15,Ship +ReceivesFor,WR,$20,Brdg +ReceivesFor,Joakim,$20,Tunn + +CompanyOperates,GW,Joakim +LaysTileAt,GW,121,F15,SW +CompanyTakesLoan,GW,$100,$100 +BuysPrivateFromFor,GW,Tunn,Joakim,$200 +AcquiresBonus,GW,Tunnel,$10,B13 +CompanyRevenue,GW,$70 +CompanyMustPayLoanInterest,GW,$20 +InterestPaidFromTreasury,GW,$20 +CompanyPaysOutFull,GW,$70 +Payout,Joakim,$14,2,10 +PRICE_MOVES_LOG,GW,$80,E3,$90,F3 + +CompanyOperates,LPS,Stefan +LaysTileAt,LPS,14,C14,SW +CompanyTakesLoan,LPS,$100,$100 +BuysPrivateFromFor,LPS,W&SR,Stefan,$80 +CompanyRevenue,LPS,$120 +CompanyMustPayLoanInterest,LPS,$10 +InterestPaidFromTreasury,LPS,$10 +CompanyPaysOutFull,LPS,$120 +Payout,Stefan,$36,3,10 +PRICE_MOVES_LOG,LPS,$75,E4,$80,F4 + +CompanyOperates,WR,Ed +LaysTileAt,WR,15,O16,SE +CompanyRevenue,WR,$140 +CompanyMustPayLoanInterest,WR,$20 +InterestPaidFromTreasury,WR,$20 +CompanyPaysOutFull,WR,$140 +Payout,Ed,$42,3,10 +Payout,Adam,$28,2,10 +PRICE_MOVES_LOG,WR,$65,E6,$70,F6 +CompanyTakesLoan,WR,$100,$90 + +CompanyOperates,GT,Aliza +LaysTileAt,GT,120,N11,NE +CompanyRevenue,GT,$120 +CompanyMustPayLoanInterest,GT,$20 +InterestPaidFromTreasury,GT,$20 +CompanyPaysOutFull,GT,$120 +Payout,Adam,$12,1,10 +Payout,Aliza,$48,4,10 +PRICE_MOVES_LOG,GT,$65,E6,$70,F6 +CompanyTakesLoan,GT,$100,$90 +BuysPrivateFromFor,GT,Flos,Aliza,$40 + +EndOfOperatingRound,2.2 +ORWorthIncrease,Adam,2.2,$50 +ORWorthIncrease,Aliza,2.2,$53 +ORWorthIncrease,Ed,2.2,$27 +ORWorthIncrease,Stefan,2.2,$71 +ORWorthIncrease,Joakim,2.2,$134 +Has,GT,$200 +Has,LPS,$35 +Has,WR,$185 +Has,GW,$20 +Has,Adam,$123 +Has,Aliza,$159 +Has,Ed,$318 +Has,Stefan,$206 +Has,Joakim,$314 +StartStockRound,3 +HasPriority,Aliza +BUY_SHARE_LOG,Aliza,10,GW,IPO,$80 +PriceIsPaidTo,$80,GW +START_COMPANY_LOG,Ed,CPR,$75,$150,2,20,CPR +BUY_SHARE_LOG,Stefan,10,LPS,IPO,$75 +PriceIsPaidTo,$75,LPS +BUY_SHARE_LOG,Joakim,10,GW,IPO,$80 +PriceIsPaidTo,$80,GW +BUY_SHARE_LOG,Adam,10,GT,IPO,$65 +HoldMoneyInEscrow,$65,$65,GT +SELL_SHARE_LOG,Aliza,10,GW,$90 +PRICE_MOVES_LOG,GW,$90,F3,$80,F4 +BUY_SHARE_LOG,Aliza,10,GT,IPO,$65 +HoldMoneyInEscrow,$65,$130,GT +BUY_SHARE_LOG,Ed,10,CPR,IPO,$75 +PriceIsPaidTo,$75,CPR +Floats,CPR +BUY_SHARE_LOG,Stefan,10,LPS,IPO,$75 +PriceIsPaidTo,$75,LPS +BUY_SHARE_LOG,Joakim,10,GW,IPO,$80 +PriceIsPaidTo,$80,GW +Autopasses,Adam +BUY_SHARE_LOG,Aliza,10,GT,IPO,$65 +HoldMoneyInEscrow,$65,$195,GT +BUY_SHARE_LOG,Ed,10,CPR,IPO,$75 +PriceIsPaidTo,$75,CPR +PASSES,Stefan +BUY_SHARE_LOG,Joakim,10,WR,IPO,$65 +HoldMoneyInEscrow,$65,$65,WR +Autopasses,Adam +PASSES,Aliza +Autopasses,Ed +PASSES,Stefan +BUY_SHARE_LOG,Joakim,10,GT,IPO,$65 +HoldMoneyInEscrow,$65,$260,GT +Autopasses,Adam +PASSES,Aliza +Autopasses,Ed +Autopasses,Stefan +SELL_SHARE_LOG,Joakim,10,GT,$70 +PRICE_MOVES_LOG,GT,$70,F6,$65,F7 +SELL_SHARE_LOG,Joakim,10,WR,$70 +PRICE_MOVES_LOG,WR,$70,F6,$65,F7 +START_COMPANY_LOG,Joakim,CA,$80,$160,2,20,CA +Autopasses,Adam +PASSES,Aliza +Autopasses,Ed +Autopasses,Stefan +SELL_SHARE_LOG,Joakim,10,GW,$80 +PRICE_MOVES_LOG,GW,$80,F4,$75,F5 +BUY_SHARE_LOG,Joakim,10,CA,IPO,$80 +PriceIsPaidTo,$80,CA +Floats,CA +Autopasses,Adam +PASSES,Aliza +Autopasses,Ed +Autopasses,Stefan +PASSES,Joakim + +END_SR,3 +Has,GT,$200 +Has,LPS,$185 +Has,WR,$185 +Has,CPR,$300 +Has,CA,$240 +Has,GW,$260 +Has,Adam,$58 +Has,Aliza,$39 +Has,Ed,$18 +Has,Stefan,$56 +Has,Joakim,$4 +START_OR,3.1 +ReceivesFor,GT,$5,Flos +ReceivesFor,LPS,$10,W&SR +ReceivesFor,Adam,$10,TCC +ReceivesFor,Adam,$15,Ship +ReceivesFor,WR,$20,Brdg +ReceivesFor,GW,$20,Tunn + +CompanyOperates,LPS,Stefan +BuysBonusTokenFrom,LPS,Tunnel,$10,GW,$50 +LaysTileAt,LPS,8,D15,NW +CompanyRevenue,LPS,$140 +CompanyMustPayLoanInterest,LPS,$10 +InterestPaidFromTreasury,LPS,$10 +CompanyPaysOutFull,LPS,$140 +Payout,Stefan,$70,5,10 +PRICE_MOVES_LOG,LPS,$80,F4,$90,G4 +CompanyTakesLoan,LPS,$100,$90 +BuysTrain,LPS,3,IPO,$225 + +CompanyOperates,CA,Joakim +LaysTileAt,CA,57,D17,SW +CompanyTakesLoan,CA,$100,$100 +BuysBonusTokenFrom,CA,Tunnel,$10,GW,$50 +LAYS_TOKEN_ON,CA,F15,$40 +InterestPaidFromTreasury,CA,$10 +CompanyDoesNotPayDividend,CA +PRICE_MOVES_LOG,CA,$80,E3,$75,D3 +BuysTrain,CA,3,IPO,$225 + +CompanyOperates,GW,Joakim +LaysTileAt,GW,8,E14,SE +CompanyTakesLoan,GW,$100,$100 +CompanyRevenue,GW,$80 +CompanyMustPayLoanInterest,GW,$30 +InterestPaidFromTreasury,GW,$30 +CompanyPaysOutFull,GW,$80 +Payout,Joakim,$24,3,10 +Payout,GW,$16,2,10 +PRICE_MOVES_LOG,GW,$75,F5,$80,G5 +BuysTrain,GW,3,IPO,$225 +BuysTrain,GW,3,IPO,$225 +All 3-trains are sold out, 4-trains now available + +CompanyOperates,CPR,Ed +LaysTileAtFor,CPR,57,N3,SW,$40 +CompanyDoesNotPayDividend,CPR +PRICE_MOVES_LOG,CPR,$75,E4,$70,D4 +CompanyTakesLoan,CPR,$100,$90 +BuysTrain,CPR,4,IPO,$350 +FirstTrainBought,4 +StartOfPhase,4 + +CompanyOperates,GT,Aliza +LaysTileAt,GT,58,N9,S +CompanyRevenue,GT,$100 +CompanyMustPayLoanInterest,GT,$30 +InterestPaidFromTreasury,GT,$30 +CompanyWithholds,GT,$100 +PRICE_MOVES_LOG,GT,$65,F7,$60,E7 +CompanyTakesLoan,GT,$100,$90 +BuysTrain,GT,4,IPO,$350 + +CompanyOperates,WR,Ed +LaysTileAt,WR,5,O18,SE +CompanyTakesLoan,WR,$100,$100 +InterestPaidFromTreasury,WR,$40 +CompanyDoesNotPayDividend,WR +PRICE_MOVES_LOG,WR,$65,F7,$60,E7 +PlayerMustSellShares,Ed,$67 +SELL_SHARES_LOG,Ed,1,10,10,CPR,$70 +PRICE_MOVES_LOG,CPR,$70,D4,$65,D5 +PresidentAddsCash,WR,Ed,$85 +BuysTrain,WR,4,IPO,$350 + +EndOfOperatingRound,3.1 +ORWorthIncrease,Adam,3.1,-$35 +ORWorthIncrease,Aliza,3.1,-$90 +ORWorthIncrease,Ed,3.1,-$195 +ORWorthIncrease,Stefan,3.1,$70 +ORWorthIncrease,Joakim,3.1,-$36 +Has,GT,$15 +Has,LPS,$0 +Has,WR,$0 +Has,CPR,$0 +Has,CA,$15 +Has,GW,$16 +Has,Adam,$83 +Has,Aliza,$39 +Has,Ed,$3 +Has,Stefan,$126... [truncated message content] |