|
From: Erik V. <ev...@us...> - 2011-12-06 21:01:50
|
data/1835/CompanyManager.xml | 6
rails/game/OperatingRound.java | 154 ++++++++++++---------
rails/game/specific/_1835/OperatingRound_1835.java | 42 +----
3 files changed, 102 insertions(+), 100 deletions(-)
New commits:
commit 8912fbffa6d8f12e9067da0d497eebc949e17f1c
Merge: 96ae931 31d0618
Author: Erik Vos <eri...@xs...>
Date: Tue Dec 6 21:58:11 2011 +0100
Merge branch 'master' of ssh://rails.git.sourceforge.net/gitroot/rails/rails
Conflicts:
rails/game/OperatingRound.java
commit 96ae93123cd0273ad7681345928a7aac2889b8e0
Author: Erik Vos <eri...@xs...>
Date: Fri Dec 2 23:14:24 2011 +0100
1825 minors have 10%, not 20% shares
diff --git a/data/1825/CompanyManager.xml b/data/1825/CompanyManager.xml
index 2ae65c9..7be3e79 100644
--- a/data/1825/CompanyManager.xml
+++ b/data/1825/CompanyManager.xml
@@ -23,14 +23,14 @@
<CompanyType name="Minor" class="rails.game.specific._1825.PublicCompany_1825">
<Float percentage="40"/>
<StockPrice par="no"/>
- <ShareUnit percentage="20"/>
+ <ShareUnit percentage="10"/>
<BaseTokens>
<!-- HomeBase lay options: "whenStarted", "whenFloated", "firstOR" (default) -->
<HomeBase lay="firstOR"/>
<LayCost method="sequence" cost="0"/>
</BaseTokens>
- <Certificate type="President" shares="2"/>
- <Certificate shares="1" number="3"/>
+ <Certificate type="President" shares="4"/>
+ <Certificate shares="2" number="3"/>
<Trains limit="4,3"/>
<!--TileLays>
<Number colour="yellow" number="2" phase="1,2,3,4"></Number></TileLays-->
commit 5c7069a25a41a974fb25001ed3145cce979f0832
Author: Erik Vos <eri...@xs...>
Date: Tue Dec 6 21:20:37 2011 +0100
Further changes to fix special tile lays.
Special tile lay prevalidation has been factored out into a separate method
to allow OperatingRound subclasses to add game-specific checks.
diff --git a/data/1830/CompanyManager.xml b/data/1830/CompanyManager.xml
index 3623f7f..5c2fe0e 100644
--- a/data/1830/CompanyManager.xml
+++ b/data/1830/CompanyManager.xml
@@ -40,7 +40,7 @@
<Blocking hex="B20"/>
<SpecialProperties>
<SpecialProperty condition="ifOwnedByCompany" when="tileLayingStep" class="rails.game.special.SpecialTileLay">
- <SpecialTileLay location="B20" extra="yes" free="yes"/>
+ <SpecialTileLay colour="yellow" location="B20" extra="yes" free="yes"/>
</SpecialProperty>
</SpecialProperties>
</Company>
diff --git a/data/1835/CompanyManager.xml b/data/1835/CompanyManager.xml
index 7127047..58db0e2 100644
--- a/data/1835/CompanyManager.xml
+++ b/data/1835/CompanyManager.xml
@@ -46,10 +46,10 @@
<Company name="OBB" longname="Ostbayerische Bahn" type="Private" basePrice="120" revenue="10">
<SpecialProperties>
<SpecialProperty condition="ifOwnedByPlayer" when="tileLayingStep" class="rails.game.special.SpecialTileLay">
- <SpecialTileLay location="M15" extra="yes" free="yes" />
+ <SpecialTileLay location="M15" colour="yellow" extra="yes" free="yes" />
</SpecialProperty>
<SpecialProperty condition="ifOwnedByPlayer" when="tileLayingStep" class="rails.game.special.SpecialTileLay">
- <SpecialTileLay location="M17" extra="yes" free="yes" />
+ <SpecialTileLay location="M17" colour="yellow" extra="yes" free="yes" />
</SpecialProperty>
</SpecialProperties>
<ClosingConditions>
@@ -61,7 +61,7 @@
<Company name="PfB" longname="Pfalzbahnen" type="Private" basePrice="150" revenue="15">
<SpecialProperties>
<SpecialProperty condition="ifOwnedByPlayer" when="tileLayingStep" class="rails.game.special.SpecialTileLay">
- <SpecialTileLay location="L6" extra="yes" free="yes" />
+ <SpecialTileLay location="L6" colour="green" extra="yes" free="yes" />
</SpecialProperty>
<SpecialProperty condition="ifOwnedByPlayer" when="orTurn" class="rails.game.special.SpecialTokenLay">
<SpecialTokenLay location="L6" extra="yes" free="yes"/>
diff --git a/rails/game/OperatingRound.java b/rails/game/OperatingRound.java
index f754fa8..d799ad9 100644
--- a/rails/game/OperatingRound.java
+++ b/rails/game/OperatingRound.java
@@ -1688,56 +1688,10 @@ public class OperatingRound extends Round implements Observer {
if (operatingCompany.get().canUseSpecialProperties()) {
- // What colours can be laid in the current phase?
- List<String> phaseColours = getCurrentPhase().getTileColours();
-
for (SpecialTileLay stl : getSpecialProperties(SpecialTileLay.class)) {
- if (stl.isExtra()
- // If the special tile lay is not extra, it is only allowed if
- // normal tile lays are also (still) allowed
- || checkNormalTileLay(stl.getTile(), false)) {
- LayTile lt = new LayTile(stl);
- TileI tile = stl.getTile();
-
- // Which tile colour(s) are specified explicitly...
- String[] stlc = stl.getTileColours();
- if ((stlc == null || stlc.length == 0) && tile != null) {
- // ... or implicitly
- stlc = new String[] {tile.getColourName()};
- }
-
- // Which of the specified tile colours can really be laid now?
- List<String> layableColours;
- if (stlc == null) {
- layableColours = phaseColours;
- } else {
- layableColours = new ArrayList<String>();
- for (String colour : stlc) {
- if (phaseColours.contains(colour)) layableColours.add(colour);
- }
- }
- // If any locations are specified, check if tile or colour(s) can be laid there.
- Map<String, Integer> tc = new HashMap<String, Integer>();
- List<MapHex> hexes = stl.getLocations();
- for (String colour : layableColours) {
- if (hexes != null) {
- for (MapHex hex : hexes) {
- // At least one hex does not have that colour yet
- if (hex.getCurrentTile().getColourNumber() + 1
- == Tile.getColourNumberForName(colour)) {
- tc.put(colour, 1);
- continue;
- }
- }
- } else {
- tc.put(colour, 1);
- }
- }
-
- if (!tc.isEmpty()) lt.setTileColours(tc);
- if (!tc.isEmpty() || hexes == null) currentSpecialTileLays.add(lt);
- }
+ LayTile layTile = new LayTile(stl);
+ if (validateSpecialTileLay (layTile)) currentSpecialTileLays.add(layTile);
}
}
@@ -1755,6 +1709,94 @@ public class OperatingRound extends Round implements Observer {
return currentSpecialTileLays;
}
+ /** Prevalidate a special tile lay.
+ * <p>During prevalidation, the action may be updated (i.e. restricted).
+ * TODO <p>Note: The name of this method may suggest that it can also be used for postvalidation
+ * (i.e. to validate the action after the player has selected it). This is not yet the case,
+ * but it is conceivable that this method can be extended to cover postvalidation as well.
+ * Postvalidation is really a different process, which in this context has not yet been considered in detail.
+ * @param layTile A LayTile object embedding a SpecialTileLay property.
+ * Any other LayTile objects are rejected. The object may be changed by this method.
+ * @return TRUE if allowed.
+ */
+ protected boolean validateSpecialTileLay (LayTile layTile) {
+
+ if (layTile == null) return false;
+
+ SpecialProperty sp = layTile.getSpecialProperty();
+ if (sp == null || !(sp instanceof SpecialTileLay)) return false;
+
+ SpecialTileLay stl = (SpecialTileLay) sp;
+
+ if (!stl.isExtra()
+ // If the special tile lay is not extra, it is only allowed if
+ // normal tile lays are also (still) allowed
+ && !checkNormalTileLay(stl.getTile(), false)) return false;
+
+ TileI tile = stl.getTile();
+
+ // What colours can be laid in the current phase?
+ List<String> phaseColours = getCurrentPhase().getTileColours();
+
+ // Which tile colour(s) are specified explicitly...
+ String[] stlc = stl.getTileColours();
+ if ((stlc == null || stlc.length == 0) && tile != null) {
+ // ... or implicitly
+ stlc = new String[] {tile.getColourName()};
+ }
+
+ // Which of the specified tile colours can really be laid now?
+ List<String> layableColours;
+ if (stlc == null) {
+ layableColours = phaseColours;
+ } else {
+ layableColours = new ArrayList<String>();
+ for (String colour : stlc) {
+ if (phaseColours.contains(colour)) layableColours.add(colour);
+ }
+ if (layableColours.isEmpty()) return false;
+ }
+
+ // If any locations are specified, check if tile or colour(s) can be laid there.
+ Map<String, Integer> tc = new HashMap<String, Integer>();
+ List<MapHex> hexes = stl.getLocations();
+ List<MapHex> remainingHexes = null;
+ List<String> remainingColours = null;
+ int cash = operatingCompany.get().getCash();
+
+ if (hexes != null) {
+ remainingHexes = new ArrayList<MapHex> ();
+ remainingColours = new ArrayList<String>();
+ }
+ for (String colour : layableColours) {
+ if (hexes != null) {
+ for (MapHex hex : hexes) {
+ // Check if the company can pay any costs
+ if (cash < hex.getTileCost()) continue;
+
+ // At least one hex does not have that colour yet
+ if (hex.getCurrentTile().getColourNumber() + 1
+ == Tile.getColourNumberForName(colour)) {
+ tc.put(colour, 1);
+ remainingColours.add(colour);
+ remainingHexes.add(hex);
+ continue;
+ }
+ }
+ } else {
+ tc.put(colour, 1);
+ }
+ }
+ if (!tc.isEmpty()) layTile.setTileColours(tc);
+
+ if (hexes != null) {
+ if (remainingHexes.isEmpty()) return false;
+ layTile.setLocations(remainingHexes);
+ }
+
+ return true;
+ }
+
protected boolean areTileLaysPossible() {
return !tileLaysPerColour.isEmpty()
|| !getSpecialTileLays(false).isEmpty();
diff --git a/rails/game/action/LayTile.java b/rails/game/action/LayTile.java
index a5d0ad2..074e0ea 100644
--- a/rails/game/action/LayTile.java
+++ b/rails/game/action/LayTile.java
@@ -181,6 +181,11 @@ public class LayTile extends PossibleORAction {
return locations;
}
+ public void setLocations(List<MapHex> locations) {
+ this.locations = locations;
+ if (locations != null) buildLocationNameString();
+ }
+
public int getType() {
return type;
}
diff --git a/rails/game/special/SpecialTileLay.java b/rails/game/special/SpecialTileLay.java
index b7fd63a..3e1dea6 100644
--- a/rails/game/special/SpecialTileLay.java
+++ b/rails/game/special/SpecialTileLay.java
@@ -8,7 +8,7 @@ import rails.common.LocalText;
import rails.common.parser.ConfigurationException;
import rails.common.parser.Tag;
import rails.game.*;
-import rails.util.*;
+import rails.util.Util;
public class SpecialTileLay extends SpecialProperty {
@@ -25,9 +25,9 @@ public class SpecialTileLay extends SpecialProperty {
* Default is same colours as is allowed in a a normal tile lay.
* Don't use if specific tiles are specified! */
protected String[] tileColours = null;
-
+
@Override
- public void configureFromXML(Tag tag) throws ConfigurationException {
+ public void configureFromXML(Tag tag) throws ConfigurationException {
super.configureFromXML(tag);
Tag tileLayTag = tag.getChild("SpecialTileLay");
@@ -41,43 +41,43 @@ public class SpecialTileLay extends SpecialProperty {
tileNumber = tileLayTag.getAttributeAsInteger("tile", 0);
- String coloursString = tag.getAttributeAsString("colour");
+ String coloursString = tileLayTag.getAttributeAsString("colour");
if (Util.hasValue(coloursString)) {
tileColours = coloursString.split(",");
}
-
+
name = tileLayTag.getAttributeAsString("name");
extra = tileLayTag.getAttributeAsBoolean("extra", extra);
free = tileLayTag.getAttributeAsBoolean("free", free);
connected = tileLayTag.getAttributeAsBoolean("connected", connected); /* sfy 1889 extension */
closingValue =
- tileLayTag.getAttributeAsInteger("closingValue", closingValue);
+ tileLayTag.getAttributeAsInteger("closingValue", closingValue);
if (tileNumber > 0) {
- description = LocalText.getText("LayNamedTileInfo",
- tileNumber,
- name != null ? name : "",
- locationCodes,
- (extra ? LocalText.getText("extra"):LocalText.getText("notExtra")),
- (free ? LocalText.getText("noCost") : LocalText.getText("normalCost")),
- (connected ? LocalText.getText("connected") : LocalText.getText("unconnected"))
- /* sfy 1889 extension */
- );
+ description = LocalText.getText("LayNamedTileInfo",
+ tileNumber,
+ name != null ? name : "",
+ locationCodes,
+ (extra ? LocalText.getText("extra"):LocalText.getText("notExtra")),
+ (free ? LocalText.getText("noCost") : LocalText.getText("normalCost")),
+ (connected ? LocalText.getText("connected") : LocalText.getText("unconnected"))
+ /* sfy 1889 extension */
+ );
} else {
- description = LocalText.getText("LayTileInfo",
- locationCodes,
- (extra ? LocalText.getText("extra"):LocalText.getText("notExtra")),
- (free ? LocalText.getText("noCost") : LocalText.getText("normalCost")),
+ description = LocalText.getText("LayTileInfo",
+ locationCodes,
+ (extra ? LocalText.getText("extra"):LocalText.getText("notExtra")),
+ (free ? LocalText.getText("noCost") : LocalText.getText("normalCost")),
(connected ? LocalText.getText("connected") : LocalText.getText("unconnected"))
/* sfy 1889 extension */
- );
+ );
}
}
@Override
- public void finishConfiguration (GameManagerI gameManager)
+ public void finishConfiguration (GameManagerI gameManager)
throws ConfigurationException {
TileManager tmgr = gameManager.getTileManager();
@@ -93,7 +93,7 @@ public class SpecialTileLay extends SpecialProperty {
hex = mmgr.getHex(hexName);
if (hex == null)
throw new ConfigurationException("Location " + hexName
- + " does not exist");
+ + " does not exist");
locations.add(hex);
}
@@ -140,18 +140,20 @@ public class SpecialTileLay extends SpecialProperty {
}
@Override
- public String toString() {
- return "SpecialTileLay comp=" + originalCompany.getName() + " hex="
- + locationCodes + " extra=" + extra + " cost=" + free + " connected=" + connected;
+ public String toString() {
+ return "SpecialTileLay comp=" + originalCompany.getName()
+ + " hex=" + locationCodes
+ + " colour="+tileColours
+ + " extra=" + extra + " cost=" + free + " connected=" + connected;
}
@Override
- public String toMenu() {
- return description;
+ public String toMenu() {
+ return description;
}
@Override
- public String getInfo() {
- return description;
+ public String getInfo() {
+ return description;
}
}
diff --git a/rails/game/specific/_1835/OperatingRound_1835.java b/rails/game/specific/_1835/OperatingRound_1835.java
index 6f4d312..4513f32 100644
--- a/rails/game/specific/_1835/OperatingRound_1835.java
+++ b/rails/game/specific/_1835/OperatingRound_1835.java
@@ -10,7 +10,8 @@ import rails.game.action.DiscardTrain;
import rails.game.action.LayTile;
import rails.game.move.CashMove;
import rails.game.move.MapChange;
-import rails.game.special.*;
+import rails.game.special.ExchangeForShare;
+import rails.game.special.SpecialPropertyI;
import rails.game.state.BooleanState;
public class OperatingRound_1835 extends OperatingRound {
@@ -183,42 +184,17 @@ public class OperatingRound_1835 extends OperatingRound {
}
@Override
- protected List<LayTile> getSpecialTileLays(boolean display) {
+ protected boolean validateSpecialTileLay (LayTile layTile) {
- /* Special-property tile lays */
- List<LayTile> currentSpecialTileLays = new ArrayList<LayTile>();
+ if (!super.validateSpecialTileLay(layTile)) return false;
- if (operatingCompany.get().canUseSpecialProperties()) {
+ // Exclude the second OBB free tile if the first was laid in this round
+ if (layTile.getSpecialProperty().getLocationNameString().matches("M1(7|9)")
+ && hasLaidExtraOBBTile.booleanValue()) return false;
- for (SpecialTileLay stl : getSpecialProperties(SpecialTileLay.class)) {
- if (stl.isExtra()
- // If the special tile lay is not extra, it is only allowed if
- // normal tile lays are also (still) allowed
- || stl.getTile() != null
- && getCurrentPhase().isTileColourAllowed(stl.getTile().getColourName())) {
-
- // Exclude the second OBB free tile if the first was laid in this round
- if (stl.getLocationNameString().matches("M1(7|9)")
- && hasLaidExtraOBBTile.booleanValue()) continue;
-
- currentSpecialTileLays.add(new LayTile(stl));
- }
- }
- }
-
- if (display) {
- int size = currentSpecialTileLays.size();
- if (size == 0) {
- log.debug("No special tile lays");
- } else {
- for (LayTile tileLay : currentSpecialTileLays) {
- log.debug("Special tile lay: " + tileLay.toString());
- }
- }
- }
-
- return currentSpecialTileLays;
+ return true;
}
+
@Override
public boolean layTile(LayTile action) {
|