diff --git a/pom.xml b/pom.xml index 01b4791..07e8170 100644 --- a/pom.xml +++ b/pom.xml @@ -4,7 +4,7 @@ xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"> 4.0.0 - com.tman + com.koet MauMau 1.0-SNAPSHOT @@ -16,9 +16,18 @@ + + + + maven-surefire-plugin + 2.22.1 + + + + - 17 - 17 + 16 + 16 UTF-8 diff --git a/src/main/java/mau/mau/Game.java b/src/main/java/mau/mau/Game.java index ee6a47f..18e106f 100644 --- a/src/main/java/mau/mau/Game.java +++ b/src/main/java/mau/mau/Game.java @@ -5,17 +5,15 @@ import mau.mau.players.Human; import mau.mau.players.Player; import java.util.ArrayList; -import java.util.Collections; import java.util.List; public class Game { private Card currentCard; - private Deck deck = new Deck(); + private final Deck deck = new Deck(); private Dealer dealer; - private Human human; - private Referee referee = new Referee(); - private List turnOrder = new ArrayList<>(); - private Boolean skipNextPlayer = false; + private final List players = new ArrayList<>(); + private int playerTurn = 0; + private Boolean reverse = false; public Game() { setupGame(); @@ -24,40 +22,39 @@ public class Game { private void setupGame() { dealer = new Dealer(deck); - human = new Human(dealer); - turnOrder.add(human); - turnOrder.add(new Bot(dealer)); - dealer.dealCards(turnOrder); + Human human = new Human("Peppie's Maueria", dealer); + players.add(human); + players.add(new Bot("Jordan", dealer)); + players.add(new Bot("MaarKoet", dealer)); + dealer.dealCards(players); currentCard = dealer.getInitialCard(); } private void playGame() { - while (turnOrder.size() > 1) { - for (Player player : turnOrder) { - if (skipNextPlayer) { - skipNextPlayer = false; - continue; + while (players.size() > 1) { + Player player = players.get(playerTurn); + + System.out.println("Current card: " + currentCard); + Card playedCard = player.getPlay(currentCard); + if(player.getHandSize() > 0) { + if(playedCard != null){ + playCard(playedCard); } - System.out.println("Current card is " + currentCard); - Card card = player.getPlay(currentCard); - if (card != null) { - playCard(card); - } - if (player.getHandSize() == 0) { - if (Referee.isValidEndCard(currentCard)) { - System.out.println(player.getClass().getSimpleName() + " won!"); - turnOrder.remove(player); - break; - } else { - System.out.println("You can't end with this card!"); - player.addCardToHand(card); + System.out.println(deck.getDeck().size() + " cards left in deck"); + } else { + if(Referee.isValidEndCard(playedCard)) { + playCard(playedCard); + System.out.println(player.getName() + " won!"); + } else { + System.out.println("You can't end the game with that card!"); + for (int i = 0; i < 5; i++) { + player.addCardToHand(dealer.drawCard()); } - turnOrder.remove(player); - break; } + break; } - System.out.println(deck.getDeck().size() + " cards left in deck"); - turnOrder.removeIf(Player::handIsEmpty); + players.removeIf(Player::handIsEmpty); + handleTurn(playedCard); } System.out.println("Game has ended"); } @@ -68,38 +65,74 @@ public class Game { } public void handleTurn(Card card) { + if(card == null){ + incrementPlayerTurn(1); + return; + } TYPENUM cardType = card.getType(); VALUENUM cardValue = card.getValue(); if (cardType == TYPENUM.JOKER) { - // Draw 5 cards - // Choose color + + incrementPlayerTurn(1); + Player player = players.get(playerTurn); + Referee.setAllowedCards(player.getTypeChoice()); + + for (int i = 0; i < 5; i++) { + player.addCardToHand(dealer.drawCard()); + } + incrementPlayerTurn(1); return; } switch (cardValue) { - case TWO: - handleTwo(); + case TWO -> { + incrementPlayerTurn(1); + Player player = players.get(playerTurn); + for (int i = 0; i < 2; i++) { + player.addCardToHand(dealer.drawCard()); + } + incrementPlayerTurn(1); return; - case SEVEN: - case KING: - // Keep turn + } + case SEVEN -> { + System.out.println("Sticky seven go again"); return; - case EIGHT: - // Skip next player + } + case KING -> { + System.out.println("Kinky king go again"); return; - case JACK: - // Draw 5 cards - // Change card type - return; - case ACE: - Collections.reverse(turnOrder); + } + case EIGHT -> { + System.out.println("Eighty wait"); + incrementPlayerTurn(2); return; + } + case JACK -> { + Player player = players.get(playerTurn); + Referee.setAllowedCards(player.getTypeChoice()); + } + case ACE -> { + reverse = !reverse; + if (players.size() == 2) { + return; + } + } } + incrementPlayerTurn(1); } - private void handleTwo(){ - Player player = turnOrder.get(1); - player.addCardToHand(dealer.drawCard()); - player.addCardToHand(dealer.drawCard()); - skipNextPlayer = true; + private void incrementPlayerTurn(int increment) { + for (int i = 0; i < increment; i++) { + if (reverse) { + playerTurn--; + } else { + playerTurn++; + } + if (playerTurn < 0) { + playerTurn = players.size() - 1; + } + if (playerTurn >= players.size()) { + playerTurn = 0; + } + } } } diff --git a/src/main/java/mau/mau/Referee.java b/src/main/java/mau/mau/Referee.java index 190381c..43c5808 100644 --- a/src/main/java/mau/mau/Referee.java +++ b/src/main/java/mau/mau/Referee.java @@ -1,8 +1,13 @@ package mau.mau; +import java.util.ArrayList; + public class Referee { + public static ArrayList allowedTypes = new ArrayList<>(); + public static boolean isValidMove(Card currentCard, Card playedCard) { + TYPENUM currentCardType = currentCard.getType(); VALUENUM currentCardValue = currentCard.getValue(); TYPENUM playedCardType = playedCard.getType(); @@ -29,4 +34,9 @@ public class Referee { public static boolean isValidEndCard(Card card) { return !isMauCard(card); } + + public static void setAllowedCards(TYPENUM type) { + allowedTypes.add(type); + allowedTypes.add(TYPENUM.JOKER); + } } \ No newline at end of file diff --git a/src/main/java/mau/mau/TYPENUM.java b/src/main/java/mau/mau/TYPENUM.java index 67a8e72..09f4111 100644 --- a/src/main/java/mau/mau/TYPENUM.java +++ b/src/main/java/mau/mau/TYPENUM.java @@ -1,5 +1,5 @@ package mau.mau; public enum TYPENUM { - SPADES, HEARTS, DIAMOND, CLUBS, JOKER; + SPADES, HEARTS, DIAMONDS, CLUBS, JOKER; } diff --git a/src/main/java/mau/mau/VALUENUM.java b/src/main/java/mau/mau/VALUENUM.java index 2356b33..1b5f072 100644 --- a/src/main/java/mau/mau/VALUENUM.java +++ b/src/main/java/mau/mau/VALUENUM.java @@ -7,7 +7,7 @@ public enum VALUENUM { EIGHT (8), NINE (9), TEN (10), JACK (11), QUEEN (12), KING (13), - ACE (13); + ACE (14); private final int VALUE; diff --git a/src/main/java/mau/mau/players/Bot.java b/src/main/java/mau/mau/players/Bot.java index 8c79c6d..56ab5b8 100644 --- a/src/main/java/mau/mau/players/Bot.java +++ b/src/main/java/mau/mau/players/Bot.java @@ -2,40 +2,85 @@ package mau.mau.players; import mau.mau.*; +import java.util.HashMap; import java.util.List; import java.util.Scanner; public class Bot extends Player { - public Bot(Dealer dealer) { - super(dealer); + public Bot(String name, Dealer dealer) { + super(name, dealer); } @Override public Card getPlay(Card currentCard) { - new Scanner(System.in).nextLine(); - List hand = super.getHand(); + List hand = getHand(); if (hand.size() == 1 && Referee.isValidEndCard(hand.get(0))) { - return hand.get(0); + Card card = hand.get(0); + System.out.println(getName() + " played " + card); + hand.remove(0); + System.out.println(getName() + " now has " + hand.size() + " cards"); + new Scanner(System.in).nextLine(); + return card; } else if (hand.size() == 1) { hand.add(drawCard()); - System.out.println("Bot drew a card"); - System.out.println("Bot now has " + hand.size() + " cards"); + System.out.println(getName() + " drew a card"); + System.out.println(getName() + " now has " + hand.size() + " cards"); + new Scanner(System.in).nextLine(); return null; } - for(Card card : hand) { - if(Referee.isValidMove(card, currentCard)) { - System.out.println("Bot played " + card); - hand.remove(card); - System.out.println("Bot now has " + hand.size() + " cards"); - return card; + for (Card card : hand) { + if(Referee.allowedTypes.isEmpty()) { + if (Referee.isValidMove(card, currentCard)) { + System.out.println(getName() + " played " + card); + hand.remove(card); + System.out.println(getName() + " now has " + hand.size() + " cards"); + new Scanner(System.in).nextLine(); + return card; + } + } else { + if (Referee.allowedTypes.contains(card.getType())) { + Referee.allowedTypes.clear(); + System.out.println(getName() + " played " + card); + hand.remove(card); + System.out.println(getName() + " now has " + hand.size() + " cards"); + new Scanner(System.in).nextLine(); + return card; + } } } hand.add(drawCard()); - System.out.println("Bot drew a card"); - System.out.println("Bot now has " + hand.size() + " cards"); + System.out.println(getName() + " drew a card"); + System.out.println(getName() + " now has " + hand.size() + " cards"); + new Scanner(System.in).nextLine(); return null; } + + @Override + public TYPENUM getTypeChoice() { + HashMap typeCount = new HashMap<>(); + for (Card card : getHand()) { + TYPENUM type = card.getType(); + if (typeCount.containsKey(type)) { + typeCount.put(type, typeCount.get(type) + 1); + } else { + typeCount.put(type, 1); + } + } + TYPENUM typeChoice = null; + int maxCount = 0; + for (TYPENUM type : typeCount.keySet()) { + if (typeCount.get(type) > maxCount) { + typeChoice = type; + maxCount = typeCount.get(type); + } + } + if (typeChoice == null || typeChoice == TYPENUM.JOKER) { + typeChoice = TYPENUM.values()[(int) (Math.random() * 4)]; + } + System.out.println(getName() + " chose " + typeChoice); + return typeChoice; + } } \ No newline at end of file diff --git a/src/main/java/mau/mau/players/Human.java b/src/main/java/mau/mau/players/Human.java index aca8ffd..6ce3e53 100644 --- a/src/main/java/mau/mau/players/Human.java +++ b/src/main/java/mau/mau/players/Human.java @@ -1,17 +1,14 @@ package mau.mau.players; -import mau.mau.Card; -import mau.mau.Dealer; -import mau.mau.Referee; -import mau.mau.Utils; +import mau.mau.*; import java.util.List; import java.util.Scanner; public class Human extends Player { - public Human(Dealer dealer) { - super(dealer); + public Human(String name, Dealer dealer) { + super(name, dealer); } @Override @@ -20,14 +17,14 @@ public class Human extends Player { Scanner scanner = new Scanner(System.in); - List hand = super.getHand(); - while (true){ + List hand = getHand(); + while (true) { String input = scanner.nextLine(); - if(input.equals("quit")){ + if (input.equals("quit")) { System.out.println("You quit the game!"); System.exit(69); } - if (input.equals("draw")) { + if (input.equals("draw") || input.equals("d")) { Card card = drawCard(); System.out.println("You drew a " + card); hand.add(card); @@ -35,14 +32,20 @@ public class Human extends Player { } if (Utils.isNumeric(input)) { int cardIndex = Integer.parseInt(input); - if (cardIndex < 0 || cardIndex > hand.size()){ + if (cardIndex < 0 || cardIndex > hand.size()) { System.out.println("Invalid card"); continue; } Card card = hand.get(cardIndex); - if (!Referee.isValidMove(card, currentCard)) { - System.out.println("Invalid move"); - continue; + if (Referee.allowedTypes.isEmpty()) { + if (!Referee.isValidMove(card, currentCard)) { + System.out.println("Invalid move"); + continue; + } + } else { + if (Referee.allowedTypes.contains(card.getType())) { + Referee.allowedTypes.clear(); + } } hand.remove(cardIndex); return card; @@ -51,8 +54,34 @@ public class Human extends Player { } } - private void printHand(){ - List hand = super.getHand(); + @Override + public TYPENUM getTypeChoice() { + System.out.println("Choose a new type:"); + System.out.println("(1) Spades"); + System.out.println("(2) Hearts"); + System.out.println("(3) Diamonds"); + System.out.println("(4) Clubs"); + + Scanner scanner = new Scanner(System.in); + while (true) { + int input = scanner.nextInt(); + switch (input) { + case 1: + return TYPENUM.SPADES; + case 2: + return TYPENUM.HEARTS; + case 3: + return TYPENUM.DIAMONDS; + case 4: + return TYPENUM.CLUBS; + default: + System.out.println("Invalid input"); + } + } + } + + private void printHand() { + List hand = getHand(); for (int i = 0; i < hand.size(); i++) { Card card = hand.get(i); System.out.println("(" + i + ") " + card); diff --git a/src/main/java/mau/mau/players/Player.java b/src/main/java/mau/mau/players/Player.java index 32459cb..74aa743 100644 --- a/src/main/java/mau/mau/players/Player.java +++ b/src/main/java/mau/mau/players/Player.java @@ -2,15 +2,18 @@ package mau.mau.players; import mau.mau.Card; import mau.mau.Dealer; +import mau.mau.TYPENUM; import java.util.List; public abstract class Player { + private String name; private List hand; private Dealer dealer; - public Player(Dealer dealer) { + public Player(String name, Dealer dealer) { + this.name = name; this.dealer = dealer; } @@ -22,11 +25,11 @@ public abstract class Player { return this.hand = hand; } - public Boolean handIsEmpty(){ + public Boolean handIsEmpty() { return hand.isEmpty(); } - public void addCardToHand(Card card){ + public void addCardToHand(Card card) { hand.add(card); } @@ -34,15 +37,21 @@ public abstract class Player { return dealer.drawCard(); } - public Card playCard(int cardIndex){ + public Card playCard(int cardIndex) { Card playCard = hand.get(cardIndex); hand.remove(cardIndex); return playCard; } - public int getHandSize(){ + public int getHandSize() { return hand.size(); } public abstract Card getPlay(Card currentCard); + + public abstract TYPENUM getTypeChoice(); + + public String getName() { + return name; + } } diff --git a/src/main/resources/TODO.md b/src/main/resources/TODO.md new file mode 100644 index 0000000..f621e7d --- /dev/null +++ b/src/main/resources/TODO.md @@ -0,0 +1,22 @@ +# TODO +1. Refactoring +2. Huisregels toevoegen + * Kwartet = win + * 69 mag tegelijk opgelegd worden + * ~~Als er 2 spelers zijn, mag je 2x na een Ace~~ +3. Spelers kunnen een naam kiezen +4. ~~Als je laatste kaart een pestkaart is moet je 5 kaarten pakken als je hem probeert op te leggen~~ +5. 100% test coverage +6. Redesign terminal interface + +## Known Bugs +1. Teveel kaarten in deck na het opnieuw schudden + +### In een land hier ver, ver vandaan +1. UI + * Kattenkaarten (Mau Mau) + * Jokers = Koet + * Verslepen van kaarten voor de volgorde +2. Multiplayer +3. Game settings +4. Betere bot \ No newline at end of file diff --git a/src/main/java/diagrams/ClassDiagram.puml b/src/main/resources/diagrams/ClassDiagram.puml similarity index 100% rename from src/main/java/diagrams/ClassDiagram.puml rename to src/main/resources/diagrams/ClassDiagram.puml diff --git a/src/main/java/diagrams/SSD.puml b/src/main/resources/diagrams/SSD.puml similarity index 100% rename from src/main/java/diagrams/SSD.puml rename to src/main/resources/diagrams/SSD.puml diff --git a/src/main/java/diagrams/SequenceDiagram.puml b/src/main/resources/diagrams/SequenceDiagram.puml similarity index 100% rename from src/main/java/diagrams/SequenceDiagram.puml rename to src/main/resources/diagrams/SequenceDiagram.puml diff --git a/src/test/java/mau/mau/DealerTest.java b/src/test/java/mau/mau/DealerTest.java index b1f30d8..49b8d37 100644 --- a/src/test/java/mau/mau/DealerTest.java +++ b/src/test/java/mau/mau/DealerTest.java @@ -5,17 +5,4 @@ import org.junit.jupiter.api.Test; import static org.junit.jupiter.api.Assertions.assertTrue; public class DealerTest { - - @Test - public void isDealerAGoodShufflerTest() { - //Assign - Deck deck = new Deck(); - Dealer sut = new Dealer(deck); - - //Act -// sut.shuffleDeck(); - - //Assert - assertTrue(false); - } } diff --git a/src/test/java/mau/mau/RefereeTest.java b/src/test/java/mau/mau/RefereeTest.java index bf57f03..872f072 100644 --- a/src/test/java/mau/mau/RefereeTest.java +++ b/src/test/java/mau/mau/RefereeTest.java @@ -24,7 +24,7 @@ public class RefereeTest { public void isSameCardValueValidMoveTest(){ //Assign Card testCardOne = new Card(TYPENUM.HEARTS, VALUENUM.ACE); - Card testCardTwo = new Card(TYPENUM.DIAMOND, VALUENUM.ACE); + Card testCardTwo = new Card(TYPENUM.DIAMONDS, VALUENUM.ACE); //Act boolean result = Referee.isValidMove(testCardOne, testCardTwo);