diff --git a/Meilenstein II/Protocol.txt b/Meilenstein II/Protocol.txt index d53d36c..283c592 100644 --- a/Meilenstein II/Protocol.txt +++ b/Meilenstein II/Protocol.txt @@ -7,7 +7,7 @@ Implemented: * PINGB Pingback from client to server. * NAMEC$name Change name to whatever is specified * STGAM start the Game - * CVOTE$position Client has voted for position + * CVOTE$position$vote Client at position has voted for position Future / planned: * CRTGM Create a new game @@ -24,8 +24,8 @@ Server Commands: Implemented: * SPING Ping from server to client * PINGB Pingback from client to server. - * GVOTR Ghosts: Please vote now - * HVOTR Humans: Please vote now + * GVOTR$position$msg Ghosts: Please vote now + * HVOTR$position$msg Humans: Please vote now Future / planned: * MSGRS "Message received": Paramaters: a string detailing to the client that and what the server received as command. diff --git a/src/main/java/ch/unibas/dmi/dbis/cs108/gamelogic/Game.java b/src/main/java/ch/unibas/dmi/dbis/cs108/gamelogic/Game.java index 5339c9e..1d45b50 100644 --- a/src/main/java/ch/unibas/dmi/dbis/cs108/gamelogic/Game.java +++ b/src/main/java/ch/unibas/dmi/dbis/cs108/gamelogic/Game.java @@ -89,11 +89,11 @@ public class Game implements Runnable { while (i < order.length) { int index = order[i]; if (passengerTrain[index].getIsGhost()) { //if they are a ghost - GhostNPC ghostNPC = new GhostNPC(passengerTrain[index].getPosition(), "NPC" + passengerTrain[index].getPosition(),passengerTrain[index].getIsOG() ,this); + GhostNPC ghostNPC = new GhostNPC(passengerTrain[index].getPosition(), "NPC" + passengerTrain[index].getPosition(),passengerTrain[index].getIsOG()); gameState.getPassengerTrain()[index] = ghostNPC; } else { //ToDo: give NPC nice usernames - HumanNPC humanNPC = new HumanNPC(passengerTrain[index].getPosition(), "NPC" + passengerTrain[index].getPosition(),this); + HumanNPC humanNPC = new HumanNPC(passengerTrain[index].getPosition(), "NPC" + passengerTrain[index].getPosition()); gameState.getPassengerTrain()[index] = humanNPC; } i++; diff --git a/src/main/java/ch/unibas/dmi/dbis/cs108/gamelogic/GhostifyHandler.java b/src/main/java/ch/unibas/dmi/dbis/cs108/gamelogic/GhostifyHandler.java index ff2a088..b2fb8c0 100644 --- a/src/main/java/ch/unibas/dmi/dbis/cs108/gamelogic/GhostifyHandler.java +++ b/src/main/java/ch/unibas/dmi/dbis/cs108/gamelogic/GhostifyHandler.java @@ -2,6 +2,7 @@ package ch.unibas.dmi.dbis.cs108.gamelogic; import ch.unibas.dmi.dbis.cs108.BudaLogConfig; import ch.unibas.dmi.dbis.cs108.gamelogic.klassenstruktur.Ghost; +import ch.unibas.dmi.dbis.cs108.gamelogic.klassenstruktur.GhostNPC; import ch.unibas.dmi.dbis.cs108.gamelogic.klassenstruktur.GhostPlayer; import ch.unibas.dmi.dbis.cs108.gamelogic.klassenstruktur.Passenger; import org.apache.logging.log4j.LogManager; @@ -19,11 +20,23 @@ public class GhostifyHandler { public Ghost ghost(Passenger p, Game game) { //TODO: Adjust for not only players but also npcs LOGGER.debug("Passenger Position " + p.getPosition()); - p.setGhost(); Ghost g; - g = new Ghost(); - g.setGhost(); - g.setPosition(p.getPosition()); + if (p.getIsPlayer()) { + p.setGhost(); + GhostPlayer ghostPlayer; + ghostPlayer = new GhostPlayer(p.getPosition(), p.getName(), p.getClientHandler(),p.getIsOG()); + ghostPlayer.setGhost(); + ghostPlayer.setPosition(p.getPosition()); + g = ghostPlayer; + } else { + p.setGhost(); + GhostNPC ghostNPC; + ghostNPC = new GhostNPC(p.getPosition(), p.getName(),p.getIsOG()); + ghostNPC.setGhost(); + ghostNPC.setPosition(p.getPosition()); + g = ghostNPC; + + } game.gameState.addNewPassenger(g, g.getPosition()); LOGGER.info("Passenger at position " + p.getPosition() + "has been ghostified"); return g; diff --git a/src/main/java/ch/unibas/dmi/dbis/cs108/gamelogic/ServerGameInfoHandler.java b/src/main/java/ch/unibas/dmi/dbis/cs108/gamelogic/ServerGameInfoHandler.java index 68576d9..2fd184d 100644 --- a/src/main/java/ch/unibas/dmi/dbis/cs108/gamelogic/ServerGameInfoHandler.java +++ b/src/main/java/ch/unibas/dmi/dbis/cs108/gamelogic/ServerGameInfoHandler.java @@ -25,16 +25,16 @@ public class ServerGameInfoHandler { * @param msg the message to be formatted * @return a message in a protocol format */ - public static String format(String msg, Game game) { + public static String format(String msg, Passenger p, Game game) { switch (msg) { case "Vote on who to ghostify!": - msg = Protocol.serverRequestsGhostVote + "$" + game.gameState.toString(); + msg = Protocol.serverRequestsGhostVote + "$" + p.getPosition() +"$" + game.gameState.toString(); break; case "Vote for a ghost to kick off!": - msg = Protocol.serverRequestsHumanVote + "$" + game.gameState.humanToString(); + msg = Protocol.serverRequestsHumanVote + "$" + p.getPosition() +"$"+ game.gameState.humanToString(); break; default: - msg = Protocol.printToClientConsole + "$" + msg; + msg = Protocol.printToClientConsole + "$" + p.getPosition() +"$"+ msg; } LOGGER.info(msg); return msg; diff --git a/src/main/java/ch/unibas/dmi/dbis/cs108/gamelogic/VoteHandler.java b/src/main/java/ch/unibas/dmi/dbis/cs108/gamelogic/VoteHandler.java index 41362bc..ab81971 100644 --- a/src/main/java/ch/unibas/dmi/dbis/cs108/gamelogic/VoteHandler.java +++ b/src/main/java/ch/unibas/dmi/dbis/cs108/gamelogic/VoteHandler.java @@ -33,6 +33,7 @@ public class VoteHandler { */ public void ghostVote(Passenger[] passengers, Game game) { LOGGER.debug("ghostVote has been called"); + LOGGER.info(game.getGameState().toString()); // array to collect votes for all players during voting, i.e. votes for player 1 (passengers[0]) // are saved in @@ -101,6 +102,7 @@ public class VoteHandler { passengers[ghostPosition].send( "You are now a ghost!", game); // TODO: ServerGameInfoHandler might deal with this one + LOGGER.info(game.getGameState().toString()); // set hasVoted to false for all passengers for future votings for (Passenger passenger : passengers) { passenger.setHasVoted(false); @@ -117,7 +119,7 @@ public class VoteHandler { * @param passengers: train passengers */ public String humanVote(Passenger[] passengers, Game game) { - + LOGGER.info(game.getGameState().toString()); // array to collect votes for all players during voting, i.e. votes for player 1 are saved in // votesForPlayers[0] @@ -134,20 +136,19 @@ public class VoteHandler { } try { // waits 20 seconds before votes get collected - Thread.sleep(30*1000); + Thread.sleep(20*1000); } catch (InterruptedException e) { LOGGER.warn("Thread " + Thread.currentThread() + " was interrupted"); } for (Passenger passenger : passengers) { + passenger.getVoteFromClientHandler(); // collecting the votes - distribute them among the vote counters for all players // TODO: Perhaps the vote results should be handled by ClientGameInfoHandler if (passenger.getHasVoted()) { for (int i = 0; i < votesForPlayers.length; i++) { - LOGGER.info("Passenger: " + passenger.getPosition() + " voted for: " + passenger.getVote() ); if (passenger.getVote() == i) { votesForPlayers[i]++; - } } } @@ -202,6 +203,7 @@ public class VoteHandler { } } } + LOGGER.info(game.getGameState().toString()); // set hasVoted to false for all passengers for future voting for (Passenger passenger : passengers) { passenger.setHasVoted(false); diff --git a/src/main/java/ch/unibas/dmi/dbis/cs108/gamelogic/klassenstruktur/GhostNPC.java b/src/main/java/ch/unibas/dmi/dbis/cs108/gamelogic/klassenstruktur/GhostNPC.java index 78e2cd8..80ee9d4 100644 --- a/src/main/java/ch/unibas/dmi/dbis/cs108/gamelogic/klassenstruktur/GhostNPC.java +++ b/src/main/java/ch/unibas/dmi/dbis/cs108/gamelogic/klassenstruktur/GhostNPC.java @@ -19,7 +19,7 @@ public class GhostNPC extends Ghost { * @param name player name. if null, then a default name is used. * @param isOG true if the ghost is the original ghost. */ - public GhostNPC(int position, String name, boolean isOG, Game game) { + public GhostNPC(int position, String name, boolean isOG) { this.isOG = isOG; this.position = position; this.clientHandler = null; diff --git a/src/main/java/ch/unibas/dmi/dbis/cs108/gamelogic/klassenstruktur/GhostPlayer.java b/src/main/java/ch/unibas/dmi/dbis/cs108/gamelogic/klassenstruktur/GhostPlayer.java index c89bce0..c964b67 100644 --- a/src/main/java/ch/unibas/dmi/dbis/cs108/gamelogic/klassenstruktur/GhostPlayer.java +++ b/src/main/java/ch/unibas/dmi/dbis/cs108/gamelogic/klassenstruktur/GhostPlayer.java @@ -35,7 +35,7 @@ public class GhostPlayer extends Ghost { @Override public void send(String msg, Game game) { - String formattedMsg = ServerGameInfoHandler.format(msg, game); + String formattedMsg = ServerGameInfoHandler.format(msg, this, game); clientHandler.sendMsgToClient(formattedMsg); } @@ -45,10 +45,11 @@ public class GhostPlayer extends Ghost { */ @Override public void getVoteFromClientHandler() { - vote = clientHandler.getVote(); - hasVoted = clientHandler.getHasVoted(); - clientHandler.setVote(Integer.MAX_VALUE); - clientHandler.setHasVoted(false); + vote = clientHandler.getVote()[position]; + hasVoted = clientHandler.getHasVoted()[position]; + clientHandler.setVote(position,Integer.MAX_VALUE); + clientHandler.setHasVoted(position,false); + LOGGER.info("Ghost at Pos: " + position + " has voted for: " + vote); /* * if vote wasn't valid, make sure, the passenger field hasVoted == false, probably redundant but better be safe than sorry */ diff --git a/src/main/java/ch/unibas/dmi/dbis/cs108/gamelogic/klassenstruktur/HumanNPC.java b/src/main/java/ch/unibas/dmi/dbis/cs108/gamelogic/klassenstruktur/HumanNPC.java index 4c24749..fd32f17 100644 --- a/src/main/java/ch/unibas/dmi/dbis/cs108/gamelogic/klassenstruktur/HumanNPC.java +++ b/src/main/java/ch/unibas/dmi/dbis/cs108/gamelogic/klassenstruktur/HumanNPC.java @@ -16,7 +16,7 @@ public class HumanNPC extends Human { * @param position position on the train * @param name player name. if null, then a default name is used. */ - public HumanNPC(int position, String name, Game game) { + public HumanNPC(int position, String name) { this.position = position; this.clientHandler = null; isGhost = false; @@ -38,8 +38,11 @@ public class HumanNPC extends Human { * Currently returns a random integer for voting * @return integer between 0 and 5 */ - public int vote(){ - return (int) (Math.random()*6); + public void vote(){ + int randomNr = (int) (Math.random()*6); + vote = randomNr; + hasVoted = true; + LOGGER.info("HumanNPC at Position: " + this.getPosition() + " has voted for: " + vote); } public void noise() { diff --git a/src/main/java/ch/unibas/dmi/dbis/cs108/gamelogic/klassenstruktur/HumanPlayer.java b/src/main/java/ch/unibas/dmi/dbis/cs108/gamelogic/klassenstruktur/HumanPlayer.java index 07469ac..bdb05c5 100644 --- a/src/main/java/ch/unibas/dmi/dbis/cs108/gamelogic/klassenstruktur/HumanPlayer.java +++ b/src/main/java/ch/unibas/dmi/dbis/cs108/gamelogic/klassenstruktur/HumanPlayer.java @@ -32,7 +32,7 @@ public class HumanPlayer extends Human { @Override public void send(String msg, Game game) { - String formattedMsg = ServerGameInfoHandler.format(msg, game); + String formattedMsg = ServerGameInfoHandler.format(msg,this, game); clientHandler.sendMsgToClient(formattedMsg); } @@ -42,10 +42,12 @@ public class HumanPlayer extends Human { */ @Override public void getVoteFromClientHandler() { - vote = clientHandler.getVote(); - hasVoted = clientHandler.getHasVoted(); - clientHandler.setVote(Integer.MAX_VALUE); - clientHandler.setHasVoted(false); + LOGGER.info("method was called by: " + position); + vote = clientHandler.getVote()[position]; + LOGGER.info("Human at Pos: " + position + " has voted for: " + vote); + hasVoted = clientHandler.getHasVoted()[position]; + clientHandler.setVote(position,Integer.MAX_VALUE); + clientHandler.setHasVoted(position,false); /* * if vote wasn't valid, make sure, the passenger field hasVoted == false, probably redundant but better be safe than sorry */ diff --git a/src/main/java/ch/unibas/dmi/dbis/cs108/gamelogic/klassenstruktur/Passenger.java b/src/main/java/ch/unibas/dmi/dbis/cs108/gamelogic/klassenstruktur/Passenger.java index 333ce24..7151294 100644 --- a/src/main/java/ch/unibas/dmi/dbis/cs108/gamelogic/klassenstruktur/Passenger.java +++ b/src/main/java/ch/unibas/dmi/dbis/cs108/gamelogic/klassenstruktur/Passenger.java @@ -28,7 +28,7 @@ public class Passenger { **/ public void send(String msg, Game game) { if (isPlayer) { - String formattedMsg = ServerGameInfoHandler.format(msg,game); + String formattedMsg = ServerGameInfoHandler.format(msg,this,game); clientHandler.sendMsgToClient(formattedMsg); } LOGGER.warn("This object should not just be a passenger. Position:" + position); @@ -113,6 +113,7 @@ public class Passenger { * When called by NPC nothing should happen, because clientHandler = null */ public void getVoteFromClientHandler() { + LOGGER.debug("a NPC called this method hopefully: " + position); } } diff --git a/src/main/java/ch/unibas/dmi/dbis/cs108/multiplayer/client/Client.java b/src/main/java/ch/unibas/dmi/dbis/cs108/multiplayer/client/Client.java index 9771c76..f63b2aa 100644 --- a/src/main/java/ch/unibas/dmi/dbis/cs108/multiplayer/client/Client.java +++ b/src/main/java/ch/unibas/dmi/dbis/cs108/multiplayer/client/Client.java @@ -5,6 +5,7 @@ import ch.unibas.dmi.dbis.cs108.multiplayer.helpers.ClientPinger; import ch.unibas.dmi.dbis.cs108.multiplayer.helpers.Protocol; +import ch.unibas.dmi.dbis.cs108.multiplayer.server.JServerProtocolParser; import java.net.Socket; import java.io.*; import java.net.UnknownHostException; @@ -77,6 +78,9 @@ public class Client { */ public void voteGetter(String msg) { + int msgIndex = msg.indexOf('$'); + String position = msg.substring(0, msgIndex);; + msg = msg.substring(msgIndex + 1); Scanner userInput = new Scanner(System.in); //TODO(Seraina): implement System.out.println(msg); @@ -91,10 +95,9 @@ public class Client { LOGGER.warn(e.getMessage()); System.out.println("Invalid vote"); input = String.valueOf(Integer.MAX_VALUE); - } finally { - sendMsgToServer(Protocol.votedFor + "$" + input); } - + sendMsgToServer(Protocol.votedFor + "$" + position + "$" + input); + LOGGER.info("msg to server is: " + Protocol.votedFor + "$" + position + "$" + input); } diff --git a/src/main/java/ch/unibas/dmi/dbis/cs108/multiplayer/client/JClientProtocolParser.java b/src/main/java/ch/unibas/dmi/dbis/cs108/multiplayer/client/JClientProtocolParser.java index bb3a7ab..a3e1462 100644 --- a/src/main/java/ch/unibas/dmi/dbis/cs108/multiplayer/client/JClientProtocolParser.java +++ b/src/main/java/ch/unibas/dmi/dbis/cs108/multiplayer/client/JClientProtocolParser.java @@ -44,10 +44,12 @@ public class JClientProtocolParser { break; case Protocol.serverRequestsGhostVote: System.out.println("Ghost received Vote request"); + c.voteGetter(msg.substring(6)); //TODO(Seraina): How can be enforced, that clients won't vote otherwise? Trigger a methode here that listens to input break; case Protocol.serverRequestsHumanVote: - System.out.println("Human received Vote request"); + LOGGER.info("Human received Vote request"); + c.voteGetter(msg.substring(6)); //TODO(Seraina): How can be enforced, that clients won't vote otherwise? Trigger a methode here that listens to input break; default: diff --git a/src/main/java/ch/unibas/dmi/dbis/cs108/multiplayer/helpers/ServerPinger.java b/src/main/java/ch/unibas/dmi/dbis/cs108/multiplayer/helpers/ServerPinger.java index dfc34e5..6400ad4 100644 --- a/src/main/java/ch/unibas/dmi/dbis/cs108/multiplayer/helpers/ServerPinger.java +++ b/src/main/java/ch/unibas/dmi/dbis/cs108/multiplayer/helpers/ServerPinger.java @@ -56,9 +56,8 @@ public class ServerPinger implements Runnable { System.out.println( "Lost connection to user " + c.getClientUserName() + ". Waiting to reconnect..."); } else { - c.disconnectClient(); - LOGGER.debug( - "gotPingBack has not been set to true and isConnected has been set to false before"); + //c.disconnectClient(); + //LOGGER.debug("gotPingBack has not been set to true and isConnected has been set to false before"); } } } diff --git a/src/main/java/ch/unibas/dmi/dbis/cs108/multiplayer/server/ClientHandler.java b/src/main/java/ch/unibas/dmi/dbis/cs108/multiplayer/server/ClientHandler.java index 1a70a38..2ed5c99 100644 --- a/src/main/java/ch/unibas/dmi/dbis/cs108/multiplayer/server/ClientHandler.java +++ b/src/main/java/ch/unibas/dmi/dbis/cs108/multiplayer/server/ClientHandler.java @@ -6,6 +6,7 @@ import ch.unibas.dmi.dbis.cs108.multiplayer.helpers.ServerPinger; import java.io.*; import java.net.InetAddress; import java.net.Socket; +import java.util.Arrays; import java.util.HashSet; import java.util.Scanner; import org.apache.logging.log4j.LogManager; @@ -35,8 +36,8 @@ public class ClientHandler implements Runnable { public static HashSet disconnectedClients = new HashSet<>(); //todo: implement re-connection public static HashSet lobby = new HashSet<>(); public static HashSet ghostClients = new HashSet<>(); - private int vote; //saves vote of clientHandler for later transmission to passenger, by default MAX_VALUE - private boolean hasVoted; //saves hasVoted status of clientHandler for later transmission to passenger, by default false + private int[] vote; //saves vote of clientHandler for later transmission to passenger, by default MAX_VALUE, index corresponds to Passenger position + private boolean[] hasVoted; //saves hasVoted status of clientHandler for later transmission to passenger, by default false, index corresponds to Passenger position /** * Implements the login logic in client-server architecture. @@ -51,8 +52,10 @@ public class ClientHandler implements Runnable { this.in = new BufferedReader(new InputStreamReader((socket.getInputStream()))); this.loggedIn = false; this.clientUserName = nameDuplicateChecker.checkName("U.N. Owen"); - this.vote = Integer.MAX_VALUE; - this.hasVoted = false; + int[] h = new int[1000]; + Arrays.fill(h,Integer.MAX_VALUE); + this.vote = h; + this.hasVoted = new boolean[1000]; connectedClients.add(this); serverPinger = new ServerPinger(socket, this); Thread sP = new Thread(serverPinger); @@ -91,11 +94,11 @@ public class ClientHandler implements Runnable { return loggedIn; } - public int getVote() { + public int[] getVote() { return vote; } - public boolean getHasVoted() { + public boolean[] getHasVoted() { return hasVoted; } @@ -108,12 +111,12 @@ public class ClientHandler implements Runnable { this.loggedIn = loggedIn; } - public void setVote(int vote) { - this.vote = vote; + public void setVote(int position, int vote) { + this.vote[position] = vote; } - public void setHasVoted(boolean hasVoted) { - this.hasVoted = hasVoted; + public void setHasVoted(int position, boolean hasVoted) { + this.hasVoted[position] = hasVoted; } @Override diff --git a/src/main/java/ch/unibas/dmi/dbis/cs108/multiplayer/server/JServerProtocolParser.java b/src/main/java/ch/unibas/dmi/dbis/cs108/multiplayer/server/JServerProtocolParser.java index eddceed..a7a8c70 100644 --- a/src/main/java/ch/unibas/dmi/dbis/cs108/multiplayer/server/JServerProtocolParser.java +++ b/src/main/java/ch/unibas/dmi/dbis/cs108/multiplayer/server/JServerProtocolParser.java @@ -32,6 +32,9 @@ public class JServerProtocolParser { String header = ""; //"header" is the first 5 characters, i.e. the protocol part try { header = msg.substring(0, 5); + if(!header.equals(Protocol.pingBack) &&!header.equals(Protocol.pingFromClient)) { //for debuging without constant pings + LOGGER.debug("got message: " + msg + "."); + } } catch (IndexOutOfBoundsException e) { System.out.println("Received unknown command"); } @@ -70,16 +73,21 @@ public class JServerProtocolParser { LOGGER.debug(Protocol.listLobbies + " command received from: " + h.getClientUserName()); break; case Protocol.votedFor: + msg = msg.substring(6); + int msgIndex = msg.indexOf('$'); int vote = Integer.MAX_VALUE; + int position = 0; + LOGGER.debug("Message is " + msg.substring(6)); try { - vote = Integer.parseInt(msg.substring(6)); + position = Integer.parseInt(msg.substring(0,msgIndex)); + vote = Integer.parseInt(msg.substring(msgIndex + 1)); } catch (Exception e) { LOGGER.warn("Invalid vote " + e.getMessage()); - } finally { - if(vote != Integer.MAX_VALUE) { //gets MAX_VALUE when the vote wasn't valid - h.setVote(vote); - h.setHasVoted(true); - } + } + if(vote != Integer.MAX_VALUE) { //gets MAX_VALUE when the vote wasn't valid + h.setVote(position,vote); + LOGGER.debug("Player vote: " + vote); + h.setHasVoted(position,true); } break; case Protocol.startANewGame: