Add files via upload

This commit is contained in:
fassband
2021-11-19 08:32:32 +01:00
committed by GitHub Enterprise
parent e9a9181cd0
commit f2fe06f720
19 changed files with 8166 additions and 0 deletions
+254
View File
@@ -0,0 +1,254 @@
package ch.zhaw.catan;
import java.awt.Point;
import java.util.Collections;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.function.Function;
import java.util.stream.Collectors;
/**
* This class specifies the most important and basic parameters of the game
* Catan.
* <p>
* The class provides definitions such as for the type and number of resource
* cards or the number of available road elements per player. Furthermore, it
* provides a dice number to field and a field to land type mapping for the
* standard setup detailed <a href=
* "https://www.catan.de/files/downloads/4002051693602_catan_-_das_spiel_0.pdf">here</a>
* </p>
* @author tebe
*
*/
public class Config {
// Minimum number of players
// Note: The max. number is equal to the number of factions (see Faction enum)
public static final int MIN_NUMBER_OF_PLAYERS = 2;
// Initial thief position (on the desert field)
public static final Point INITIAL_THIEF_POSITION = new Point(7, 11);
// Available factions
public enum Faction {
RED("rr"), BLUE("bb"), GREEN("gg"), YELLOW("yy");
private String name;
private Faction(String name) {
this.name = name;
}
@Override
public String toString() {
return name;
}
}
// RESOURCE CARD DECK
public static final Map<Resource, Integer> INITIAL_RESOURCE_CARDS_BANK = Map.of(Resource.LUMBER, 19,
Resource.BRICK, 19, Resource.WOOL, 19, Resource.GRAIN, 19, Resource.ORE, 19);
// SPECIFICATION OF AVAILABLE RESOURCE TYPES
/**
* This {@link Enum} specifies the available resource types in the game.
*
* @author tebe
*/
public enum Resource {
GRAIN("GR"), WOOL("WL"), LUMBER("LU"), ORE("OR"), BRICK("BR");
private String name;
private Resource(String name) {
this.name = name;
}
@Override
public String toString() {
return name;
}
}
// SPECIFICATION OF AVAILABLE LAND TYPES
/**
* This {@link Enum} specifies the available lands in the game. Some land types
* produce resources (e.g., {@link Land#FOREST}, others do not (e.g.,
* {@link Land#WATER}.
*
* @author tebe
*/
public enum Land {
FOREST(Resource.LUMBER), PASTURE(Resource.WOOL), FIELDS(Resource.GRAIN),
MOUNTAIN(Resource.ORE), HILLS(Resource.BRICK), WATER("~~"), DESERT("--");
private Resource resource = null;
private String name;
private Land(Resource resource) {
this(resource.toString());
this.resource = resource;
}
private Land(String name) {
this.name = name;
}
@Override
public String toString() {
return this.name;
}
/**
* Returns the {@link Resource} that this land provides or null,
* if it does not provide any.
*
* @return the {@link Resource} or null
*/
public Resource getResource() {
return resource;
}
}
// STRUCTURES (with costs)
private static final int NUMBER_OF_ROADS_PER_PLAYER = 15;
private static final int NUMBER_OF_SETTLEMENTS_PER_PLAYER = 5;
private static final int NUMBER_OF_CITIES_PER_PLAYER = 4;
public static final int MAX_CARDS_IN_HAND_NO_DROP = 7;
/**
* This enum models the different structures that can be built.
* <p>
* The enum provides information about the cost of a structure and how many of
* these structures are available per player.
* </p>
*/
public enum Structure {
SETTLEMENT(List.of(Resource.LUMBER, Resource.BRICK, Resource.WOOL, Resource.GRAIN),
NUMBER_OF_SETTLEMENTS_PER_PLAYER),
CITY(List.of(Resource.ORE, Resource.ORE, Resource.ORE, Resource.GRAIN, Resource.GRAIN),
NUMBER_OF_CITIES_PER_PLAYER),
ROAD(List.of(Resource.LUMBER, Resource.BRICK), NUMBER_OF_ROADS_PER_PLAYER);
private List<Resource> costs;
private int stockPerPlayer;
private Structure(List<Resource> costs, int stockPerPlayer) {
this.costs = costs;
this.stockPerPlayer = stockPerPlayer;
}
/**
* Returns the build costs of this structure.
* <p>
* Each list entry represents a resource card. The value of an entry (e.g., {@link Resource#LUMBER})
* identifies the resource type of the card.
* </p>
* @return the build costs
*/
public List<Resource> getCosts() {
return costs;
}
/**
* Returns the build costs of this structure.
*
* @return the build costs in terms of the number of resource cards per resource type
*/
public Map<Resource, Long> getCostsAsMap() {
return costs.stream()
.collect(Collectors.groupingBy(Function.identity(), Collectors.counting()));
}
/**
* Returns the number of pieces that are available of a certain structure (per
* player). For example, there are {@link Config#NUMBER_OF_ROADS_PER_PLAYER}
* pieces of the structure {@link Structure#ROAD} per player.
*
*
* @return the stock per player
*/
public int getStockPerPlayer() {
return stockPerPlayer;
}
}
// STANDARD FIXED DICE NUMBER TO FIELD SETUP
/**
* Returns a mapping of the dice values per field.
*
* @return the dice values per field
*/
public static final Map<Point, Integer> getStandardDiceNumberPlacement() {
Map<Point, Integer> assignment = new HashMap<>();
assignment.put(new Point(4, 8), 2);
assignment.put(new Point(7, 5), 3);
assignment.put(new Point(8, 14), 3);
assignment.put(new Point(6, 8), 4);
assignment.put(new Point(7, 17), 4);
assignment.put(new Point(3, 11), 5);
assignment.put(new Point(8, 8), 5);
assignment.put(new Point(5, 5), 6);
assignment.put(new Point(9, 11), 6);
assignment.put(new Point(7, 11), 7);
assignment.put(new Point(9, 5), 8);
assignment.put(new Point(5, 17), 8);
assignment.put(new Point(5, 11), 9);
assignment.put(new Point(11, 11), 9);
assignment.put(new Point(4, 14), 10);
assignment.put(new Point(10, 8), 10);
assignment.put(new Point(6, 14), 11);
assignment.put(new Point(9, 17), 11);
assignment.put(new Point(10, 14), 12);
return Collections.unmodifiableMap(assignment);
}
// STANDARD FIXED LAND SETUP
/**
* Returns the field (coordinate) to {@link Land} mapping for the <a href=
* "https://www.catan.de/files/downloads/4002051693602_catan_-_das_spiel_0.pdf">standard
* setup</a> of the game Catan..
*
* @return the field to {@link Land} mapping for the standard setup
*/
public static final Map<Point, Land> getStandardLandPlacement() {
Map<Point, Land> assignment = new HashMap<>();
Point[] water = { new Point(4, 2), new Point(6, 2), new Point(8, 2), new Point(10, 2),
new Point(3, 5), new Point(11, 5), new Point(2, 8), new Point(12, 8), new Point(1, 11),
new Point(13, 11), new Point(2, 14), new Point(12, 14), new Point(3, 17), new Point(11, 17),
new Point(4, 20), new Point(6, 20), new Point(8, 20), new Point(10, 20) };
for (Point p : water) {
assignment.put(p, Land.WATER);
}
assignment.put(new Point(5, 5), Land.FOREST);
assignment.put(new Point(7, 5), Land.PASTURE);
assignment.put(new Point(9, 5), Land.PASTURE);
assignment.put(new Point(4, 8), Land.FIELDS);
assignment.put(new Point(6, 8), Land.MOUNTAIN);
assignment.put(new Point(8, 8), Land.FIELDS);
assignment.put(new Point(10, 8), Land.FOREST);
assignment.put(new Point(3, 11), Land.FOREST);
assignment.put(new Point(5, 11), Land.HILLS);
assignment.put(new Point(7, 11), Land.DESERT);
assignment.put(new Point(9, 11), Land.MOUNTAIN);
assignment.put(new Point(11, 11), Land.FIELDS);
assignment.put(new Point(4, 14), Land.FIELDS);
assignment.put(new Point(6, 14), Land.MOUNTAIN);
assignment.put(new Point(8, 14), Land.FOREST);
assignment.put(new Point(10, 14), Land.PASTURE);
assignment.put(new Point(5, 17), Land.PASTURE);
assignment.put(new Point(7, 17), Land.HILLS);
assignment.put(new Point(9, 17), Land.HILLS);
return Collections.unmodifiableMap(assignment);
}
}
+59
View File
@@ -0,0 +1,59 @@
package ch.zhaw.catan;
import ch.zhaw.catan.Config.Land;
import ch.zhaw.hexboard.Label;
import java.awt.Point;
import java.util.HashMap;
import java.util.Map;
import org.beryx.textio.TextIO;
import org.beryx.textio.TextIoFactory;
import org.beryx.textio.TextTerminal;
public class Dummy {
public enum Actions {
SHOW, QUIT
}
private void run() {
TextIO textIO = TextIoFactory.getTextIO();
TextTerminal<?> textTerminal = textIO.getTextTerminal();
SiedlerBoard board = new SiedlerBoard();
board.addField(new Point(2, 2), Land.FOREST);
board.setCorner(new Point(3, 3), "RR");
board.setEdge(new Point(2, 0), new Point(3, 1), "r");
board.addFieldAnnotation(new Point(2, 2), new Point(3, 1), "AA");
Map<Point, Label> lowerFieldLabel = new HashMap<>();
lowerFieldLabel.put(new Point(2, 2), new Label('0', '9'));
SiedlerBoardTextView view = new SiedlerBoardTextView(board);
for (Map.Entry<Point, Label> e : lowerFieldLabel.entrySet()) {
view.setLowerFieldLabel(e.getKey(), e.getValue());
}
boolean running = true;
while (running) {
switch (getEnumValue(textIO, Actions.class)) {
case SHOW:
textTerminal.println(view.toString());
break;
case QUIT:
running = false;
break;
default:
throw new IllegalStateException("Internal error found - Command not implemented.");
}
}
textIO.dispose();
}
public static <T extends Enum<T>> T getEnumValue(TextIO textIO, Class<T> commands) {
return textIO.newEnumInputReader(commands).read("What would you like to do?");
}
public static void main(String[] args) {
new Dummy().run();
}
}
+37
View File
@@ -0,0 +1,37 @@
package ch.zhaw.catan;
import ch.zhaw.catan.Config.Land;
import ch.zhaw.hexboard.HexBoard;
import java.awt.*;
import java.util.Collections;
import java.util.List;
public class SiedlerBoard extends HexBoard<Land, String, String, String> {
//TODO: Add fields, constructors and methods as you see fit. Do NOT change the signature
// of the methods below.
/**
* Returns the fields associated with the specified dice value.
*
* @param dice the dice value
* @return the fields associated with the dice value
*/
public List<Point> getFieldsForDiceValue(int dice) {
//TODO: Implement.
return Collections.emptyList();
}
/**
* Returns the {@link Land}s adjacent to the specified corner.
*
* @param corner the corner
* @return the list with the adjacent {@link Land}s
*/
public List<Land> getLandsForCorner(Point corner) {
//TODO: Implement.
return Collections.emptyList();
}
}
@@ -0,0 +1,12 @@
package ch.zhaw.catan;
import ch.zhaw.catan.Config.Land;
import ch.zhaw.hexboard.HexBoardTextView;
public class SiedlerBoardTextView extends HexBoardTextView<Land, String, String, String> {
public SiedlerBoardTextView(SiedlerBoard board) {
super(board);
}
}
+255
View File
@@ -0,0 +1,255 @@
package ch.zhaw.catan;
import ch.zhaw.catan.Config.Faction;
import ch.zhaw.catan.Config.Resource;
import java.awt.Point;
import java.util.Collections;
import java.util.List;
import java.util.Map;
/**
* This class performs all actions related to modifying the game state.
*
* TODO: (your documentation)
*
* @author TODO
*
*/
public class SiedlerGame {
static final int FOUR_TO_ONE_TRADE_OFFER = 4;
static final int FOUR_TO_ONE_TRADE_WANT = 1;
/**
* Constructs a SiedlerGame game state object.
*
* @param winPoints the number of points required to win the game
* @param numberOfPlayers the number of players
*
* @throws IllegalArgumentException if winPoints is lower than
* three or players is not between two and four
*/
public SiedlerGame(int winPoints, int numberOfPlayers) {
// TODO: Implement
}
/**
* Switches to the next player in the defined sequence of players.
*/
public void switchToNextPlayer() {
// TODO: Implement
}
/**
* Switches to the previous player in the defined sequence of players.
*/
public void switchToPreviousPlayer() {
// TODO: Implement
}
/**
* Returns the {@link Faction}s of the active players.
*
* <p>The order of the player's factions in the list must
* correspond to the oder in which they play.
* Hence, the player that sets the first settlement must be
* at position 0 in the list etc.
*
* <strong>Important note:</strong> The list must contain the
* factions of active players only.</p>
*
* @return the list with player's factions
*/
public List<Faction> getPlayerFactions() {
// TODO: Implement
return Collections.emptyList();
}
/**
* Returns the game board.
*
* @return the game board
*/
public SiedlerBoard getBoard() {
// TODO: Implement
return null;
}
/**
* Returns the {@link Faction} of the current player.
*
* @return the faction of the current player
*/
public Faction getCurrentPlayerFaction() {
// TODO: Implement
return null;
}
/**
* Returns how many resource cards of the specified type
* the current player owns.
*
* @param resource the resource type
* @return the number of resource cards of this type
*/
public int getCurrentPlayerResourceStock(Resource resource) {
// TODO: Implement
return 0;
}
/**
* Places a settlement in the founder's phase (phase II) of the game.
*
* <p>The placement does not cost any resource cards. If payout is
* set to true, for each adjacent resource-producing field, a resource card of the
* type of the resource produced by the field is taken from the bank (if available) and added to
* the players' stock of resource cards.</p>
*
* @param position the position of the settlement
* @param payout if true, the player gets one resource card per adjacent resource-producing field
* @return true, if the placement was successful
*/
public boolean placeInitialSettlement(Point position, boolean payout) {
// TODO: Implement
return false;
}
/**
* Places a road in the founder's phase (phase II) of the game.
* The placement does not cost any resource cards.
*
* @param roadStart position of the start of the road
* @param roadEnd position of the end of the road
* @return true, if the placement was successful
*/
public boolean placeInitialRoad(Point roadStart, Point roadEnd) {
// TODO: Implement
return false;
}
/**
* This method takes care of actions depending on the dice throw result.
*
* A key action is the payout of the resource cards to the players
* according to the payout rules of the game. This includes the
* "negative payout" in case a 7 is thrown and a player has more than
* {@link Config#MAX_CARDS_IN_HAND_NO_DROP} resource cards.
*
* If a player does not get resource cards, the list for this players'
* {@link Faction} is <b>an empty list (not null)</b>!.
*
* <p>
* The payout rules of the game take into account factors such as, the number
* of resource cards currently available in the bank, settlement types
* (settlement or city), and the number of players that should get resource
* cards of a certain type (relevant if there are not enough left in the bank).
* </p>
*
* @param dicethrow the resource cards that have been distributed to the players
* @return the resource cards added to the stock of the different players
*/
public Map<Faction, List<Resource>> throwDice(int dicethrow) {
// TODO: Implement
return null;
}
/**
* Builds a settlement at the specified position on the board.
*
* <p>The settlement can be built if:
* <ul>
* <li> the player possesses the required resource cards</li>
* <li> a settlement to place on the board</li>
* <li> the specified position meets the build rules for settlements</li>
* </ul>
*
* @param position the position of the settlement
* @return true, if the placement was successful
*/
public boolean buildSettlement(Point position) {
// TODO: Implement
return false;
}
/**
* Builds a city at the specified position on the board.
*
* <p>The city can be built if:
* <ul>
* <li> the player possesses the required resource cards</li>
* <li> a city to place on the board</li>
* <li> the specified position meets the build rules for cities</li>
* </ul>
*
* @param position the position of the city
* @return true, if the placement was successful
*/
public boolean buildCity(Point position) {
// TODO: OPTIONAL task - Implement
return false;
}
/**
* Builds a road at the specified position on the board.
*
* <p>The road can be built if:
* <ul>
* <li> the player possesses the required resource cards</li>
* <li> a road to place on the board</li>
* <li> the specified position meets the build rules for roads</li>
* </ul>
*
* @param roadStart the position of the start of the road
* @param roadEnd the position of the end of the road
* @return true, if the placement was successful
*/
public boolean buildRoad(Point roadStart, Point roadEnd) {
// TODO: Implement
return false;
}
/**
* Trades in {@link #FOUR_TO_ONE_TRADE_OFFER} resource cards of the
* offered type for {@link #FOUR_TO_ONE_TRADE_WANT} resource cards of the wanted type.
*
* The trade only works when bank and player possess the resource cards
* for the trade before the trade is executed.
*
* @param offer offered type
* @param want wanted type
* @return true, if the trade was successful
*/
public boolean tradeWithBankFourToOne(Resource offer, Resource want) {
// TODO: Implement
return false;
}
/**
* Returns the winner of the game, if any.
*
* @return the winner of the game or null, if there is no winner (yet)
*/
public Faction getWinner() {
// TODO: Implement
return null;
}
/**
* Places the thief on the specified field and steals a random resource card (if
* the player has such cards) from a random player with a settlement at that
* field (if there is a settlement) and adds it to the resource cards of the
* current player.
*
* @param field the field on which to place the thief
* @return false, if the specified field is not a field or the thief cannot be
* placed there (e.g., on water)
*/
public boolean placeThiefAndStealCard(Point field) {
//TODO: Implement (or longest road functionality)
return false;
}
}