508 lines
16 KiB
Java
508 lines
16 KiB
Java
package fassade;
|
|
|
|
import domain.Game;
|
|
import domain.Player;
|
|
import domain.Sheet;
|
|
import domain.StarwarsSheet;
|
|
import domain.sheets.Category;
|
|
|
|
import java.io.*;
|
|
import java.time.LocalDateTime;
|
|
import java.time.format.DateTimeFormatter;
|
|
import java.util.*;
|
|
|
|
public class KniffelSystem {
|
|
String lederboardLocation = "scores.csv";
|
|
ArrayList<String> playerColors;
|
|
ArrayList<Category> allValidCombinations = new ArrayList<>();
|
|
Game game;
|
|
public KniffelSystem(){
|
|
game = new Game();
|
|
playerColors = new ArrayList<>(Arrays.asList(
|
|
"\u001B[31m", // Quelle 2 Anfang
|
|
"\u001B[32m", //
|
|
"\u001B[34m", //
|
|
"\u001B[33m", //
|
|
"\u001B[36m")); // Quelle 2 Ende
|
|
}
|
|
|
|
|
|
public String setGamemode(String gamemode){
|
|
return game.setGamemode(gamemode);
|
|
}
|
|
|
|
private String getGamemode(){
|
|
return game.getGamemode();
|
|
}
|
|
|
|
|
|
public String addPlayer(int playerNumber, String name) {
|
|
String playerColor = colorPicker(playerNumber);
|
|
Player playerToAdd = new Player(playerNumber, name, playerColor, 0, getGamemode());
|
|
game.addPlayer(playerToAdd);
|
|
|
|
return changeStringFormat(name, playerColor);
|
|
}
|
|
|
|
|
|
public String changeStringFormat(String string, String formatation){
|
|
String ANSI_RESET = "\u001B[0m";
|
|
|
|
return String.format(formatation + string + ANSI_RESET);
|
|
}
|
|
|
|
|
|
private String colorPicker(int playerNumber){
|
|
if (playerNumber == 1){
|
|
return "\u001B[35m"; // Quelle 2
|
|
}
|
|
|
|
Random rand = new Random(); // Quelle 1 Anfang
|
|
int randomIndex = rand.nextInt(playerColors.size()); //
|
|
return playerColors.remove(randomIndex); // Quelle 1 Ende
|
|
}
|
|
|
|
|
|
public Player getCurrentPlayer(){
|
|
return game.getCurrentPlayer();
|
|
}
|
|
|
|
|
|
public void nextPlayer(){
|
|
game.nextTurn();
|
|
}
|
|
|
|
|
|
public void creteDevPlayers(int amountPlayer){
|
|
String[] names = {"Vic", "Nastja", "Lilli", "Emelie", "Esra", "Oli"};
|
|
for (int i = 0; i < amountPlayer; i++){
|
|
addPlayer(i+1, names[i]);
|
|
}
|
|
}
|
|
|
|
|
|
public ArrayList<Integer> rollDices(ArrayList<Integer> rolls, String keptDice){
|
|
//? DEV TEST
|
|
if (keptDice.startsWith("dev")){
|
|
return createDevRoll(keptDice);
|
|
}
|
|
|
|
ArrayList<Integer> oldRolls = extractKeptDice(rolls, keptDice);
|
|
|
|
int amountNewRolls = oldRolls.size();
|
|
ArrayList<Integer> newRolls = rollMultipleDice(5 - amountNewRolls);
|
|
|
|
oldRolls.addAll(newRolls);
|
|
|
|
return oldRolls;
|
|
}
|
|
|
|
|
|
private ArrayList<Integer> extractKeptDice(ArrayList<Integer> previousRolls, String keptDice){
|
|
ArrayList<Integer> keptRolls = new ArrayList<Integer>();
|
|
|
|
if (keptDice.isEmpty()){
|
|
return keptRolls;
|
|
}
|
|
|
|
//? Remove whitespaces
|
|
keptDice = keptDice.replaceAll("\\s+","");
|
|
|
|
if (keptDice.length() == 1){
|
|
int singleIndex = Integer.parseInt(keptDice);
|
|
keptRolls.add(previousRolls.get(singleIndex - 1));
|
|
return keptRolls;
|
|
}
|
|
|
|
keptDice = keptDice.substring(1, keptDice.length()-1);
|
|
|
|
String[] keptDiceIndicesStrings = keptDice.split(",");
|
|
|
|
for (String keptDiceIndicesString : keptDiceIndicesStrings) {
|
|
int index = Integer.parseInt(keptDiceIndicesString);
|
|
keptRolls.add(previousRolls.get(index - 1));
|
|
}
|
|
|
|
return keptRolls;
|
|
}
|
|
|
|
|
|
private ArrayList<Integer> rollMultipleDice(int amountRolls){
|
|
ArrayList<Integer> rolls = new ArrayList<>();
|
|
if (amountRolls == 0){
|
|
return rolls;
|
|
}
|
|
|
|
for (int i = 0; i < amountRolls; i++){
|
|
rolls.add(game.rollDice());
|
|
}
|
|
return rolls;
|
|
}
|
|
|
|
|
|
public String evaluateRoll(ArrayList<Integer> rolls){
|
|
HashMap<String, Category> possibleCombinations = createCategoryHashMap();
|
|
ArrayList<Category> validUpperCombinations = new ArrayList<>();
|
|
allValidCombinations = new ArrayList<>();
|
|
//TODO Add starwars logic
|
|
|
|
|
|
for (int dice : rolls){
|
|
switch (dice){
|
|
case 1:
|
|
possibleCombinations.get("Aces").addAmount();
|
|
break;
|
|
case 2:
|
|
possibleCombinations.get("Twos").addAmount();
|
|
break;
|
|
case 3:
|
|
possibleCombinations.get("Threes").addAmount();
|
|
break;
|
|
case 4:
|
|
possibleCombinations.get("Fours").addAmount();
|
|
break;
|
|
case 5:
|
|
possibleCombinations.get("Fives").addAmount();
|
|
break;
|
|
case 6:
|
|
possibleCombinations.get("Sixes").addAmount();
|
|
break;
|
|
}
|
|
if (getGamemode().equals("default")){
|
|
continue;
|
|
}
|
|
switch (dice){
|
|
case 7:
|
|
possibleCombinations.get("Sevens").addAmount();
|
|
break;
|
|
case 8:
|
|
possibleCombinations.get("Eights").addAmount();
|
|
break;
|
|
}
|
|
}
|
|
|
|
StringBuilder sb = new StringBuilder();
|
|
sb.append(String.format("%s \n", changeStringFormat("Possible combinations:", "\u001B[32m")));
|
|
sb.append(String.format("%s \n", changeStringFormat("Upper half:", "\u001b[4m")));
|
|
|
|
|
|
for (String key : possibleCombinations.keySet()) {
|
|
Category keyObj = possibleCombinations.get(key);
|
|
|
|
if (keyObj.getAmount() != 0){
|
|
validUpperCombinations.add(keyObj);
|
|
addCombinationToStringbuilder(sb, keyObj, allValidCombinations);
|
|
}
|
|
}
|
|
|
|
//? ------------------------------ LOWER HALF-------------------------------------------------
|
|
sb.append("\n");
|
|
sb.append(String.format("%s \n", changeStringFormat("Lower half:", "\u001b[4m")));
|
|
|
|
int index = 0;
|
|
Category keyObj;
|
|
for(Category category : validUpperCombinations){
|
|
|
|
//? Three of a kind
|
|
if (category.getAmount() >= 3){
|
|
keyObj = possibleCombinations.get("ThreeOfKind");
|
|
|
|
keyObj.calcValueFromRoll(rolls);
|
|
addCombinationToStringbuilder(sb, keyObj, allValidCombinations);
|
|
}
|
|
|
|
//? Four of a kind
|
|
if (category.getAmount() >= 4){
|
|
keyObj = possibleCombinations.get("FourOfKind");
|
|
|
|
keyObj.calcValueFromRoll(rolls);
|
|
addCombinationToStringbuilder(sb, keyObj, allValidCombinations);
|
|
}
|
|
|
|
//? Full House
|
|
if (category.getAmount() == 3){
|
|
for(Category innerCategory : validUpperCombinations){
|
|
if ((innerCategory.getAmount() == 2) && !(innerCategory.toString().equals(category.toString()))){
|
|
keyObj = possibleCombinations.get("FullHouse");
|
|
|
|
keyObj.independentValue();
|
|
addCombinationToStringbuilder(sb, keyObj, allValidCombinations);
|
|
}
|
|
}
|
|
}
|
|
|
|
ArrayList<Integer> sortedRolls = new ArrayList<>(rolls);
|
|
Collections.sort(sortedRolls);
|
|
|
|
|
|
//? Small Straight
|
|
if (index == 0) {
|
|
checkForSmallStraight(sortedRolls, possibleCombinations, sb);
|
|
}
|
|
|
|
//? Large Straight
|
|
if (index == 0){
|
|
checkForLargeStraight(sortedRolls, index, possibleCombinations, sb);
|
|
}
|
|
|
|
//? Yahtzee
|
|
if (category.getAmount() == 5){
|
|
keyObj = possibleCombinations.get("Yahtzee");
|
|
|
|
keyObj.independentValue();
|
|
addCombinationToStringbuilder(sb, keyObj, allValidCombinations);
|
|
}
|
|
|
|
index ++;
|
|
}
|
|
|
|
//? StarWars
|
|
if (getGamemode().equals("starwars")){
|
|
|
|
//? StarWarsDay
|
|
if ((rolls.contains(4)) && rolls.contains(5)){
|
|
keyObj = possibleCombinations.get("StarWarsDay");
|
|
|
|
keyObj.calcValueFromRoll(rolls);
|
|
addCombinationToStringbuilder(sb, keyObj, allValidCombinations);
|
|
}
|
|
|
|
//? R2D2
|
|
ArrayList<Integer> r2d2Array = new ArrayList<>(Arrays.asList(1, 8, 2, 4, 2));
|
|
if(rolls.equals(r2d2Array)){
|
|
keyObj = possibleCombinations.get("R2D2");
|
|
|
|
keyObj.independentValue();
|
|
addCombinationToStringbuilder(sb, keyObj, allValidCombinations);
|
|
}
|
|
}
|
|
|
|
|
|
//? Chance
|
|
keyObj = possibleCombinations.get("Chance");
|
|
|
|
keyObj.calcValueFromRoll(rolls);
|
|
addCombinationToStringbuilder(sb, keyObj, allValidCombinations);
|
|
|
|
return sb.toString();
|
|
}
|
|
|
|
|
|
private void checkForLargeStraight(ArrayList<Integer> sortedRolls, int index, HashMap<String, Category> possibleCombinations, StringBuilder sb) {
|
|
Category keyObj;
|
|
int amountRolls = sortedRolls.size();
|
|
|
|
if ((sortedRolls.get(index) + 1) == sortedRolls.get(index + 1)){
|
|
boolean isNotLargeStraight = false;
|
|
|
|
for (int i = 1; i < (amountRolls - 1); i++){
|
|
|
|
if ((sortedRolls.get(i) + 1) != sortedRolls.get(i + 1)){
|
|
isNotLargeStraight = true;
|
|
break;
|
|
}
|
|
}
|
|
if (!(isNotLargeStraight)){
|
|
keyObj = possibleCombinations.get("LargeStraight");
|
|
|
|
keyObj.independentValue();
|
|
addCombinationToStringbuilder(sb, keyObj, allValidCombinations);
|
|
}
|
|
}
|
|
}
|
|
|
|
private void checkForSmallStraight(ArrayList<Integer> sortedRolls, HashMap<String, Category> possibleCombinations, StringBuilder sb) {
|
|
Category keyObj;
|
|
|
|
boolean isSmallStraight = false;
|
|
for (int i = 0; i < sortedRolls.size() - 3; i++) { // Quelle 3 Anfang
|
|
if (sortedRolls.get(i) + 1 == sortedRolls.get(i + 1) //
|
|
&& sortedRolls.get(i) + 2 == sortedRolls.get(i + 2) //
|
|
&& sortedRolls.get(i) + 3 == sortedRolls.get(i + 3)) //
|
|
{ // Quelle 3 Ende
|
|
isSmallStraight = true;
|
|
break;
|
|
}
|
|
}
|
|
|
|
if (isSmallStraight) {
|
|
keyObj = possibleCombinations.get("SmallStraight");
|
|
|
|
keyObj.independentValue();
|
|
addCombinationToStringbuilder(sb, keyObj, allValidCombinations);
|
|
}
|
|
}
|
|
|
|
|
|
private void addCombinationToStringbuilder(StringBuilder sb, Category keyObj, ArrayList<Category> allValidCombinations){
|
|
int keyValue = keyObj.getValue();
|
|
String keyValueString = changeStringFormat(Integer.toString(keyValue), "\u001b[1m");
|
|
|
|
allValidCombinations.add(keyObj);
|
|
|
|
int keyAmount = keyObj.getAmount();
|
|
if (keyAmount == 0) {
|
|
sb.append(String.format("%s: Value: %s \n", keyObj, keyValueString));
|
|
return;
|
|
}
|
|
|
|
sb.append(String.format("%s: %d, Value: %s \n",keyObj, keyAmount, keyValueString));
|
|
}
|
|
|
|
|
|
private HashMap<String, Category> createCategoryHashMap(){
|
|
String gamemode = getGamemode();
|
|
Sheet sheet;
|
|
if (gamemode.equals("default")){
|
|
sheet = new Sheet();
|
|
} else {
|
|
sheet = new StarwarsSheet();
|
|
}
|
|
|
|
|
|
return sheet.getAllCategories();
|
|
}
|
|
|
|
|
|
public void writeToSheet(String sheetInput){
|
|
HashMap<String, Category> possibleCombinations = createCategoryHashMap();
|
|
|
|
Sheet currentPlayerSheet = getCurrentPlayer().getSheet();
|
|
|
|
Category categoryToWrite = possibleCombinations.get(sheetInput);
|
|
|
|
|
|
boolean contains = false;
|
|
|
|
for (Category validCombination : allValidCombinations){
|
|
if(validCombination.toString().equals(categoryToWrite.toString())){
|
|
categoryToWrite = validCombination;
|
|
contains = true;
|
|
break;
|
|
}
|
|
}
|
|
|
|
if (contains){
|
|
currentPlayerSheet.writeCategory(categoryToWrite, false);
|
|
}else {
|
|
currentPlayerSheet.writeCategory(categoryToWrite, true);
|
|
}
|
|
}
|
|
|
|
|
|
public ArrayList<String> getUnusedRows(){
|
|
Sheet currentPlayerSheet = getCurrentPlayer().getSheet();
|
|
return currentPlayerSheet.getUnusedRows();
|
|
}
|
|
|
|
|
|
public boolean checkGameEnd(){
|
|
return getCurrentPlayer().getSheet().checkGameEnd();
|
|
}
|
|
|
|
|
|
public String afterGame() throws IOException {
|
|
StringBuilder sb = new StringBuilder();
|
|
|
|
for (Player player : game.getPlayers()){
|
|
int score = player.getSheet().calcSheet();
|
|
player.setScore(score);
|
|
sb.append(String.format("%s scored %d points!", player.toString(), score));
|
|
writeToFile(createLeaderboardString(player));
|
|
}
|
|
|
|
return sb.toString();
|
|
}
|
|
|
|
|
|
private String createLeaderboardString(Player player){
|
|
DateTimeFormatter dtf = DateTimeFormatter.ofPattern("dd.MM.yyy");
|
|
LocalDateTime now = LocalDateTime.now();
|
|
|
|
String date = dtf.format(now);
|
|
int score = player.getScore();
|
|
String name = player.getName();
|
|
|
|
return String.format("%s,%d,%s",name, score, date);
|
|
}
|
|
|
|
|
|
public ArrayList<String> readFromFile() throws FileNotFoundException {
|
|
ArrayList<String> leaderboardRows = new ArrayList<>();
|
|
Scanner fsc = null;
|
|
try {
|
|
fsc = new Scanner(new File(lederboardLocation));
|
|
} catch (FileNotFoundException e) {
|
|
System.out.println("There is an error opening the leaderboard.");
|
|
System.out.println("Returning to main menu \n");
|
|
return leaderboardRows;
|
|
}
|
|
|
|
while (fsc.hasNextLine()){
|
|
leaderboardRows.add(fsc.nextLine());
|
|
}
|
|
return leaderboardRows;
|
|
}
|
|
|
|
|
|
public void writeToFile(String stringToEnter) throws IOException {
|
|
|
|
if (stringToEnter.isEmpty()){
|
|
BufferedWriter writer = new BufferedWriter(new FileWriter(lederboardLocation));
|
|
writer.write("");
|
|
return;
|
|
}
|
|
System.out.printf("Not empty |%s| \n", stringToEnter); //! TEST
|
|
|
|
ArrayList<String> currentRows = readFromFile();
|
|
|
|
currentRows.add(stringToEnter);
|
|
|
|
StringBuilder sb = new StringBuilder();
|
|
for(String leaderboardRow : currentRows) {
|
|
System.out.println(leaderboardRow);
|
|
String[] row = leaderboardRow.split(",");
|
|
System.out.printf("len row: %d \n", row.length);
|
|
sb.append(String.format("%s - %s - %s \n", row[1], row[0], row[2]));
|
|
}
|
|
|
|
BufferedWriter writer = new BufferedWriter(new FileWriter(lederboardLocation));
|
|
writer.write(sb.toString());
|
|
}
|
|
|
|
|
|
public void clearLeaderboard() throws IOException {
|
|
writeToFile("");
|
|
}
|
|
|
|
|
|
|
|
private ArrayList<Integer> createDevRoll(String keptDice){
|
|
// Format: dev(1,2,3,4,5)
|
|
// values aren't indices, they are the dice value
|
|
ArrayList<Integer> devRoll = new ArrayList<>();
|
|
|
|
keptDice = keptDice.replaceAll("\\s+","");
|
|
keptDice = keptDice.substring(4, keptDice.length()-1);
|
|
|
|
String[] rollStrings = keptDice.split(",");
|
|
for (String rollString : rollStrings){
|
|
devRoll.add(Integer.parseInt(rollString));
|
|
}
|
|
return devRoll;
|
|
}
|
|
|
|
|
|
//! TEST
|
|
public String[] getAllPlayerStrings(){
|
|
ArrayList<Player> players = game.getPlayers();
|
|
String[] returnStrings = new String[players.size()];
|
|
|
|
for (int i = 0; i < players.size(); i++){
|
|
returnStrings[i] = players.get(i).toString();
|
|
}
|
|
|
|
return returnStrings;
|
|
}
|
|
}
|