diff --git a/.idea/artifacts/Client_jar.xml b/.idea/artifacts/Client_jar.xml
index defd9ad..114e9cc 100644
--- a/.idea/artifacts/Client_jar.xml
+++ b/.idea/artifacts/Client_jar.xml
@@ -1,14 +1,17 @@
-
+
$PROJECT_DIR$/out/artifacts/Client_jar
-
-
-
-
-
-
-
-
+
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/Client/src/Launcher.java b/Client/src/Launcher.java
deleted file mode 100644
index b2ca47e..0000000
--- a/Client/src/Launcher.java
+++ /dev/null
@@ -1,7 +0,0 @@
-import game.TicTacToe_Client;
-
-public class Launcher {
- public static void main(String[] args) {
- TicTacToe_Client.main(args);
- }
-}
\ No newline at end of file
diff --git a/Client/src/META-INF/MANIFEST.MF b/Client/src/META-INF/MANIFEST.MF
index b851779..eee92a3 100644
--- a/Client/src/META-INF/MANIFEST.MF
+++ b/Client/src/META-INF/MANIFEST.MF
@@ -1,3 +1,3 @@
Manifest-Version: 1.0
-Main-Class: game.TicTacToe_Client
+Main-Class: TicTacToe_Client
diff --git a/Client/src/TicTacToe_Client.java b/Client/src/TicTacToe_Client.java
new file mode 100644
index 0000000..4de2390
--- /dev/null
+++ b/Client/src/TicTacToe_Client.java
@@ -0,0 +1,131 @@
+import javafx.application.Platform;
+import networking.Client;
+import render.Engine;
+
+import java.util.Arrays;
+import java.util.LinkedList;
+
+public class TicTacToe_Client {
+
+ private Engine renderEngine;
+ private Client client;
+ private boolean isSingleServer;
+
+ public TicTacToe_Client(){
+ renderEngine = Engine.waitForEngine();
+ }
+
+ private void ticTacToe_gameloop(){
+ //Setup
+ client = new Client("server", 2589, "second");
+ client.handshake();
+ isSingleServer = client.getServerType();
+ if (isSingleServer){
+ this.setWindowTitle(client.isPlayerOne());
+ client.sendToServer("ready");
+ while (client.isConnected()) {
+ String message = client.getResponse();
+ //Check if message is gamestate
+ if (message.charAt(0) == 'x' || message.charAt(0) == '-' || message.charAt(0) == 'o') {
+ this.drawBoard(message);
+ this.gameFlow("userInput");
+ }
+ //Handle everything else
+ else {
+ this.gameFlow(message);
+ }
+ }
+ } else {
+ this.setWindowTitle(client.isPlayerOne());
+ }
+ }
+
+ private void gameFlow(String input){
+ switch (input) {
+ case "userInput":
+ while(!renderEngine.isMouseClicked()){
+ try {
+ Thread.sleep(100);
+ } catch (InterruptedException e) {
+ e.printStackTrace();
+ }
+ }
+ renderEngine.setMouseClicked(false);
+ this.userInput();
+ break;
+ }
+ }
+
+
+
+
+ private void userInput(){
+ //Send command
+ client.sendToServer("clientMove");
+ //Send position
+ client.sendToServer(String.format("%f|%f", renderEngine.getCoordinates().getX(), renderEngine.getCoordinates().getY()));
+ //Get gameState
+ String gameState = client.getResponse();
+ if (gameState.length() == 9) {
+ this.drawBoard(gameState);
+ //Send command
+ if (!client.getGameEnded()) {
+ client.sendToServer("computerMove");
+ this.drawBoard(client.getResponse());
+ } else {
+ LinkedList winCoordinates = new LinkedList<>();
+ //Get winning fields
+ String response = client.getResponse();
+ for (String s : Arrays.copyOfRange(response.split(";"), 0, 4)) {
+ winCoordinates.add(Integer.valueOf(s) * 300);
+ }
+ //this.drawWinningLine(winCoordinates);
+ client.exitProcess();
+ System.exit(0);
+ }
+ } else {
+ int column = (int) renderEngine.getCoordinates().getX() / 300;
+ int row = (int) renderEngine.getCoordinates().getY() / 300;
+ System.err.printf("You are not allowed to place at %d|%d%n", column, row);
+ }
+ }
+
+ private void drawBoard(String gameState) {
+ Platform.runLater(new Runnable() {
+ @Override
+ public void run() {
+ renderEngine.drawBoard(gameState);
+ }
+ });
+ }
+
+ private void setWindowTitle(boolean isClientOne){
+ if (isClientOne){
+ Platform.runLater(new Runnable() {
+ @Override
+ public void run() {
+ renderEngine.updateTitle("Client One");
+ }
+ });
+ } else {
+ Platform.runLater(new Runnable() {
+ @Override
+ public void run() {
+ renderEngine.updateTitle("Client Two");
+ }
+ });
+ }
+ }
+
+ public static void main(String[] args) {
+ new Thread(){
+ @Override
+ public void run(){
+ javafx.application.Application.launch(Engine.class);
+ }
+ }.start();
+ TicTacToe_Client test = new TicTacToe_Client();
+ test.ticTacToe_gameloop();
+ }
+
+}
diff --git a/Client/src/game/TicTacToe_Client.java b/Client/src/game/TicTacToe_Client.java
deleted file mode 100644
index d88b917..0000000
--- a/Client/src/game/TicTacToe_Client.java
+++ /dev/null
@@ -1,135 +0,0 @@
-package game;
-
-import javafx.application.Application;
-import javafx.event.EventHandler;
-import javafx.geometry.Pos;
-import javafx.scene.Scene;
-import javafx.scene.input.MouseEvent;
-import javafx.scene.layout.GridPane;
-import javafx.scene.paint.Color;
-import javafx.scene.shape.Line;
-import javafx.scene.text.Font;
-import javafx.scene.text.FontWeight;
-import javafx.scene.text.Text;
-import javafx.stage.Stage;
-import networking.Client;
-
-import java.util.Arrays;
-import java.util.LinkedList;
-
-public class TicTacToe_Client extends Application {
-
- GridPane grid;
- Client client;
- Scene scene;
-
- private void initializeGrid() {
- grid = new GridPane();
- grid.setMinSize(900, 900);
- grid.setAlignment(Pos.CENTER);
- grid.setHgap(150);
- grid.setVgap(75);
- }
-
- private void drawCross(int column, int row) {
- Text cross = new Text("X");
- cross.setFont(Font.font("Tahoma", FontWeight.NORMAL, 200));
- grid.add(cross, column, row);
- }
-
- private void drawCircle(int column, int row) {
- Text circle = new Text("O");
- circle.setFont(Font.font("Tahoma", FontWeight.NORMAL, 200));
- grid.add(circle, column, row);
- }
-
- private void drawEmptyField(int column, int row) {
- Text emptyField = new Text(" ");
- emptyField.setFont(Font.font("Tahoma", FontWeight.NORMAL, 220));
- grid.add(emptyField, column, row);
- }
-
- private void drawBoard(String gameState) {
- if (gameState.length() != 9) {
- System.err.println("Wrong length of gameState string");
- return;
- }
- for (int i = 0; i < gameState.length(); i++) {
- int column = i / 3;
- int row = i % 3;
- if (gameState.charAt(i) == 'x') {
- this.drawCross(column, row);
- } else if (gameState.charAt(i) == 'o') {
- this.drawCircle(column, row);
- } else {
- this.drawEmptyField(column, row);
- }
-
- }
- }
-
- private Scene setScene() {
- scene = new Scene(grid, 900, 900);
- scene.getStylesheets().add
- (TicTacToe_Client.class.getResource("TicTacToe_Client.css").toExternalForm());
- scene.setOnMousePressed(new EventHandler() {
- @Override
- public void handle(MouseEvent event) {
- onMouseClick(event);
- }
- });
- return scene;
- }
-
- private void onMouseClick(MouseEvent event) {
- client.sendToServer("update");
- client.sendToServer(String.format("%f|%f", event.getX(), event.getY()));
- String gameState = client.getResponse();
- System.out.println(gameState);
- if (gameState.length() == 9) {
- drawBoard(gameState);
- if (!client.getGameEnded()) {
- gameState = client.getResponse();
- drawBoard(gameState);
- } else {
- LinkedList winCoordinates = new LinkedList<>();
- String response = client.getResponse();
- for (String s : Arrays.copyOfRange(response.split(";"), 0, 4)) {
- winCoordinates.add(Integer.valueOf(s) * 300);
- }
- this.drawWinningLine(winCoordinates);
- client.exitProcess();
- }
- } else {
- int column = (int) event.getX() / 300;
- int row = (int) event.getY() / 300;
- System.err.printf("You are not allowed to place at %d|%d%n", column, row);
- }
- }
-
- private void drawWinningLine(LinkedList winCoordinates) {
- Line winningLine = new Line(winCoordinates.get(0), winCoordinates.get(1), winCoordinates.get(2), winCoordinates.get(3));
- winningLine.setFill(Color.RED);
- grid.add(winningLine, winCoordinates.get(0) / 300, winCoordinates.get(1) / 300, 3, 3);
- }
-
- @Override
- public void start(Stage primaryStage) {
- client = new Client("server", 2589, "Cato");
- client.handshake();
-
- primaryStage.setTitle("TicTacToe");
- primaryStage.setResizable(false);
-
- this.initializeGrid();
- primaryStage.setScene(this.setScene());
- primaryStage.show();
-
- this.drawBoard(client.getGameState());
- }
-
- public static void main(String[] args) {
- launch(args);
- }
-
-}
diff --git a/Client/src/networking/Client.java b/Client/src/networking/Client.java
index a2bc568..7d95fec 100644
--- a/Client/src/networking/Client.java
+++ b/Client/src/networking/Client.java
@@ -10,6 +10,7 @@ import java.net.Socket;
import java.util.Scanner;
public class Client {
+ private Socket serverSocket;
private DataOutputStream out;
private DataInputStream in;
private static Scanner scanner;
@@ -21,7 +22,8 @@ public class Client {
public Client(String ip, int port, String name) {
try {
scanner = new Scanner(System.in);
- Socket serverSocket = new Socket(ip, port);
+ serverSocket = new Socket(ip, port);
+ serverName = serverSocket.getRemoteSocketAddress().toString();
out = new DataOutputStream(serverSocket.getOutputStream());
in = new DataInputStream(serverSocket.getInputStream());
clientLogger = new ClientLogger();
@@ -41,7 +43,6 @@ public class Client {
if (success) {
out.writeUTF(name);
out.flush();
- serverName = in.readUTF();
clientLogger.printLog("You successfully connected to me", serverName, success, LogType.Log);
} else {
clientLogger.printLog("Connection failed try again", success, LogType.Log);
@@ -63,10 +64,20 @@ public class Client {
}
}
+ public void sendConfirmation(){
+ try {
+ out.writeInt(200);
+ out.flush();
+ clientLogger.printLog("Sent verification code", serverName, true, LogType.Log);
+ } catch (IOException e) {
+ e.printStackTrace();
+ }
+ }
+
public String getResponse() {
try {
String message = in.readUTF();
- clientLogger.printLog(String.format("Message recieved: %s", message), serverName, success, LogType.Log);
+ clientLogger.printLog(String.format("Message recieved: %s", message), serverName, true, LogType.Log);
return message;
} catch (IOException e) {
e.printStackTrace();
@@ -74,17 +85,29 @@ public class Client {
return "";
}
- public boolean getBooleanResponse(String value){
+ public boolean getBooleanResponse(String message) {
try {
- boolean booleanResponse = in.readBoolean();
- clientLogger.printLog(String.format(value + ": %b", booleanResponse), serverName, booleanResponse, LogType.Log);
- return booleanResponse;
+ boolean state = in.readBoolean();
+ clientLogger.printLog(String.format("%s: %b", message, state), serverName, true, LogType.Log);
+ return state;
} catch (IOException e) {
e.printStackTrace();
}
return false;
}
+ public boolean isPlayerOne(){
+ this.sendToServer("isClientOne");
+ boolean isClientOne = this.getBooleanResponse("isClientOne");
+ return isClientOne;
+ }
+
+ public boolean getServerType(){
+ this.sendToServer("serverType");
+ boolean serverType = this.getBooleanResponse("isSingleServer");
+ return serverType;
+ }
+
public String getGameState() {
this.sendToServer("gameState");
String gameState = this.getResponse();
@@ -93,10 +116,20 @@ public class Client {
public boolean getGameEnded() {
this.sendToServer("gameEnded");
- boolean gameEnded = this.getBooleanResponse("Game ended");
+ boolean gameEnded = false;
+ try {
+ gameEnded = in.readBoolean();
+ clientLogger.printLog(String.format("Game ended: %b", gameEnded), serverName, gameEnded, LogType.Log);
+ } catch (IOException e) {
+ e.printStackTrace();
+ }
return gameEnded;
}
+ public void waitForInput() {
+
+ }
+
public void exitProcess(){
try {
out.writeUTF("exit()");
@@ -108,12 +141,13 @@ public class Client {
}
}
- public boolean hasSucceeded() {
- return success;
- }
-
public String getName() {
return name;
}
+ public boolean isConnected(){
+ return serverSocket.isConnected();
+ }
+
+
}
\ No newline at end of file
diff --git a/Client/src/render/Engine.java b/Client/src/render/Engine.java
new file mode 100644
index 0000000..9b811b1
--- /dev/null
+++ b/Client/src/render/Engine.java
@@ -0,0 +1,141 @@
+package render;
+
+import javafx.application.Application;
+import javafx.event.EventHandler;
+import javafx.geometry.Pos;
+import javafx.scene.Scene;
+import javafx.scene.input.MouseEvent;
+import javafx.scene.layout.GridPane;
+import javafx.scene.text.Font;
+import javafx.scene.text.FontWeight;
+import javafx.scene.text.Text;
+import javafx.stage.Stage;
+
+import java.awt.*;
+import java.util.concurrent.CountDownLatch;
+
+public class Engine extends Application {
+
+ private GridPane grid;
+ private Scene scene;
+ private static final CountDownLatch latch = new CountDownLatch(1);
+ private static Engine engine = null;
+ private boolean mouseClicked = false;
+ private Point coordinates = new Point();
+ private Stage primaryStage;
+ private MouseEvent mouseEvent;
+
+ public Engine() {
+ setEngine(this);
+ }
+
+ private void initializeGrid() {
+ grid = new GridPane();
+ grid.setPrefSize(900, 900);
+ grid.setAlignment(Pos.CENTER);
+ grid.setHgap(150);
+ grid.setVgap(75);
+ }
+
+ private Scene setScene() {
+ scene = new Scene(grid, 900, 900);
+ scene.getStylesheets().add("res/TicTacToe_Client.css");
+ scene.setOnMousePressed(new EventHandler() {
+ @Override
+ public void handle(MouseEvent event) {
+ onMouseClick(event);
+ }
+ });
+ return scene;
+ }
+
+ public static Engine waitForEngine() {
+ try {
+ latch.await();
+ } catch (InterruptedException e) {
+ e.printStackTrace();
+ }
+ return engine;
+ }
+
+ public static void setEngine(Engine new_engine) {
+ engine = new_engine;
+ latch.countDown();
+ }
+
+ public void updateTitle(String title){
+ System.out.println("title: " + title);
+ primaryStage.setTitle(title);
+ }
+
+ public void drawCross(int column, int row) {
+ Text cross = new Text("X");
+ cross.setFont(Font.font("Tahoma", FontWeight.NORMAL, 200));
+ grid.add(cross, column, row);
+ }
+
+ public void drawCircle(int column, int row) {
+ Text circle = new Text("O");
+ circle.setFont(Font.font("Tahoma", FontWeight.NORMAL, 200));
+ grid.add(circle, column, row);
+ }
+
+ public void drawEmptyField(int column, int row) {
+ Text emptyField = new Text(" ");
+ emptyField.setFont(Font.font("Tahoma", FontWeight.NORMAL, 220));
+ grid.add(emptyField, column, row);
+ }
+
+ public void drawBoard(String gameState) {
+ if (gameState.length() != 9) {
+ System.err.println("Wrong length of gameState string");
+ return;
+ }
+ for (int i = 0; i < gameState.length(); i++) {
+ int column = i / 3;
+ int row = i % 3;
+ if (gameState.charAt(i) == 'x') {
+ this.drawCross(column, row);
+ } else if (gameState.charAt(i) == 'o') {
+ this.drawCircle(column, row);
+ } else {
+ this.drawEmptyField(column, row);
+ }
+
+ }
+ }
+
+ private void onMouseClick(MouseEvent event) {
+ mouseClicked = true;
+ coordinates.setLocation(event.getX(), event.getY());
+ System.out.println(coordinates.getX() + ":" + coordinates.getY());
+ }
+
+ public boolean isMouseClicked() {
+ return mouseClicked;
+ }
+
+ public void setMouseClicked(boolean mouseClicked) {
+ this.mouseClicked = mouseClicked;
+ }
+
+ public Point getCoordinates() {
+ return coordinates;
+ }
+
+ @Override
+ public void start(Stage primaryStage) throws Exception {
+ //initialize window
+ this.primaryStage = primaryStage;
+ primaryStage.setTitle("Test");
+ primaryStage.setResizable(true);
+ this.initializeGrid();
+ primaryStage.setScene(this.setScene());
+ primaryStage.sizeToScene();
+ primaryStage.show();
+ }
+
+ public static void main(String[] args) {
+ launch(args);
+ }
+}
diff --git a/Client/src/game/TicTacToe_Client.css b/Client/src/res/TicTacToe_Client.css
similarity index 100%
rename from Client/src/game/TicTacToe_Client.css
rename to Client/src/res/TicTacToe_Client.css
diff --git a/Client/src/game/TicTacToe_Grid.png b/Client/src/res/TicTacToe_Grid.png
similarity index 100%
rename from Client/src/game/TicTacToe_Grid.png
rename to Client/src/res/TicTacToe_Grid.png
diff --git a/Server/src/networking/MultiPlayerServer.java b/Server/src/networking/MultiPlayerServer.java
index 7cab212..9a1be17 100644
--- a/Server/src/networking/MultiPlayerServer.java
+++ b/Server/src/networking/MultiPlayerServer.java
@@ -1,6 +1,6 @@
package networking;
-import game.TicTacToe_Server;
+import res.TicTacToe_Server;
import logging.LogType;
import logging.ServerLogger;
@@ -11,6 +11,8 @@ import java.io.IOException;
import java.net.ServerSocket;
import java.net.Socket;
import java.util.HashMap;
+import java.util.Map;
+import java.util.Objects;
import java.util.Scanner;
public class MultiPlayerServer {
@@ -35,6 +37,7 @@ public class MultiPlayerServer {
scanner = new Scanner(System.in);
serverLogger = new ServerLogger();
requiredConnections = 2;
+ serverLogger.printLog(ticTacToe_server.getGameState(), this.getClass().getName(), LogType.Log);
serverLogger.printLog("Server started successfully", LogType.Log);
} catch (IOException e) {
@@ -66,8 +69,6 @@ public class MultiPlayerServer {
outstreams.get(client).writeInt(200);
outstreams.get(client).flush();
clientNames.put(client, instreams.get(client).readUTF());
- outstreams.get(client).writeUTF(serverSocket.getInetAddress().getHostAddress() + ":" + serverSocket.getLocalPort());
- outstreams.get(client).flush();
serverLogger.printLog(String.format("%s got connected", clientNames.get(client)), LogType.Log);
} else {
outstreams.get(client).writeInt(403);
@@ -81,15 +82,15 @@ public class MultiPlayerServer {
}
public void ticTacToe_gameloop() {
- while(clients.size() == 2) {
+ while (clients.size() == 2) {
for (Socket client : clients.values()) {
try {
- String message = instreams.get(client).readUTF();
- serverLogger.printLog(message, clientNames.get(client), LogType.Message);
- outstreams.get(client).writeInt(200);
- outstreams.get(client).flush();
- serverLogger.printLog("Sent verification code", clientNames.get(client), LogType.Log);
- this.gameFlow(message, client);
+ String message = instreams.get(client).readUTF();
+ serverLogger.printLog(message, clientNames.get(client), LogType.Message);
+ outstreams.get(client).writeInt(200);
+ outstreams.get(client).flush();
+ serverLogger.printLog("Sent verification code", clientNames.get(client), LogType.Log);
+ this.gameFlow(message, client);
} catch (IOException e) {
e.printStackTrace();
try {
@@ -102,64 +103,110 @@ public class MultiPlayerServer {
}
}
- public void gameFlow(String input, Socket client) {
- switch (input) {
- case "gameState":
- try {
- outstreams.get(client).writeUTF(ticTacToe_server.getGameState());
- outstreams.get(client).flush();
- serverLogger.printLog("Sent gameState", clientNames.get(client), LogType.Log);
- break;
- } catch (IOException e) {
- e.printStackTrace();
- }
+ public void sendGameState(){
+ try {
+ int index = 0;
+ for (DataOutputStream outstream: outstreams.values()) {
+ outstream.writeUTF(ticTacToe_server.getGameState());
+ outstream.flush();
+ serverLogger.printLog("Sent gameState", clientNames.get(index), LogType.Log);
+ index++;
+ }
- case "update":
+ } catch (IOException e) {
+ e.printStackTrace();
+ }
+ }
+
+ public void gameFlow(String input, Socket client){
+ switch (input){
+ case "ready":
+ gameFlow("gameState", client);
+ break;
+
+ case "gameState":
+ sendGameState();
+ break;
+
+ case "clientMove":
try {
+ //Get position (X|Y)
String position = instreams.get(client).readUTF();
serverLogger.printLog(position, clientNames.get(client), LogType.Message);
+ //Send confirmation (2ßß)
outstreams.get(client).writeInt(200);
outstreams.get(client).flush();
serverLogger.printLog("Sent verification code", clientNames.get(client), LogType.Log);
- boolean isAllowed = ticTacToe_server.makeClientMove(position);
- if (isAllowed) {
- String gameState = ticTacToe_server.getGameState();
- outstreams.get(client).writeUTF(gameState);
- outstreams.get(client).flush();
- serverLogger.printLog(String.format("Sent gameState: %s", gameState), clientNames.get(client), LogType.Log);
- break;
+ boolean moveAllowed = ticTacToe_server.makeClientMove(position);
+ if (moveAllowed) {
+ sendGameState();
} else {
- outstreams.get(client).writeUTF(" ");
+ //send " "
+ outstreams.get(client).writeUTF("userInput");
outstreams.get(client).flush();
+ serverLogger.printLog("Requested userInput", LogType.Log);
serverLogger.printLog(String.format("Move is not allowed!"), clientNames.get(client), LogType.Error);
- break;
}
} catch (IOException e) {
e.printStackTrace();
}
+ break;
+
+ case "computerMove":
+ ticTacToe_server.makeComputerMove();
+ sendGameState();
+ try {
+ outstreams.get(client).writeUTF("userInput");
+ outstreams.get(client).flush();
+ serverLogger.printLog("Requested userInput", LogType.Log);
+ } catch (IOException e) {
+ e.printStackTrace();
+ }
+ break;
+
+ case "serverType":
+ try {
+ outstreams.get(client).writeBoolean(true);
+ outstreams.get(client).flush();
+ serverLogger.printLog("Sent serverType", clientNames.get(client), LogType.Log);
+ } catch (IOException e) {
+ e.printStackTrace();
+ }
+ break;
+
+ case "isClientOne":
+ for (Map.Entry entry : clients.entrySet()) {
+ if (Objects.equals(client, entry.getValue())) {
+ try {
+ outstreams.get(client).writeBoolean(entry.getKey() == 0);
+ outstreams.get(client).flush();
+ serverLogger.printLog("Sent isPlayerOne", clientNames.get(client), LogType.Log);
+ } catch (IOException e) {
+ e.printStackTrace();
+ }
+ } else {
+ serverLogger.printLog("Current client not in clients!", LogType.Error);
+ }
+ }
+ break;
case "gameEnded":
try {
boolean gameEnded = ticTacToe_server.gameEnded();
outstreams.get(client).writeBoolean(gameEnded);
if (gameEnded) {
+ //send coordinates
String coordinates = "";
- for (Point point : ticTacToe_server.getWinCoordinates()) {
+ for (Point point: ticTacToe_server.getWinCoordinates()) {
coordinates += point.x + ";" + point.y + ";";
}
+ //send winning fields
outstreams.get(client).writeUTF(coordinates);
- break;
- } else {
- ticTacToe_server.makeServerMove();
- String gameState = ticTacToe_server.getGameState();
- outstreams.get(client).writeUTF(gameState);
- outstreams.get(client).flush();
- serverLogger.printLog(String.format("Sent gameState: %s", gameState), clientNames.get(client), LogType.Log);
- break;
}
} catch (IOException e) {
e.printStackTrace();
}
+ break;
case "exit()":
try {
@@ -168,11 +215,11 @@ public class MultiPlayerServer {
outstreams.get(client).close();
instreams.get(client).close();
client.close();
- serverLogger.printLog(String.format("%s closed the connection", clientNames.get(client)), LogType.Log);
- break;
+ serverLogger.printLog(String.format("%s closed the connection",clientNames.get(client)), LogType.Log);
} catch (IOException e) {
e.printStackTrace();
}
+ break;
}
}
diff --git a/Server/src/networking/SinglePlayerServer.java b/Server/src/networking/SinglePlayerServer.java
index 3c12f99..087c429 100644
--- a/Server/src/networking/SinglePlayerServer.java
+++ b/Server/src/networking/SinglePlayerServer.java
@@ -1,6 +1,6 @@
package networking;
-import game.TicTacToe_Server;
+import res.TicTacToe_Server;
import logging.LogType;
import logging.ServerLogger;
@@ -11,6 +11,8 @@ import java.io.IOException;
import java.net.ServerSocket;
import java.net.Socket;
import java.util.HashMap;
+import java.util.Map;
+import java.util.Objects;
import java.util.Scanner;
public class SinglePlayerServer {
@@ -66,8 +68,6 @@ public class SinglePlayerServer {
outstreams.get(client).writeInt(200);
outstreams.get(client).flush();
clientNames.put(client, instreams.get(client).readUTF());
- outstreams.get(client).writeUTF(serverSocket.getInetAddress().getHostAddress()+":"+serverSocket.getLocalPort());
- outstreams.get(client).flush();
serverLogger.printLog(String.format("%s got connected", clientNames.get(client)), LogType.Log);
} else {
outstreams.get(client).writeInt(403);
@@ -84,6 +84,7 @@ public class SinglePlayerServer {
for (Socket client: clients.values()) {
try {
while (!client.isClosed()) {
+ //Get instruction
String message = instreams.get(client).readUTF();
serverLogger.printLog(message, clientNames.get(client), LogType.Message);
outstreams.get(client).writeInt(200);
@@ -102,64 +103,105 @@ public class SinglePlayerServer {
}
}
+ public void sendGameState(Socket client){
+ try {
+ outstreams.get(client).writeUTF(ticTacToe_server.getGameState());
+ outstreams.get(client).flush();
+ serverLogger.printLog("Sent gameState", clientNames.get(client), LogType.Log);
+ } catch (IOException e) {
+ e.printStackTrace();
+ }
+ }
+
public void gameFlow(String input, Socket client){
switch (input){
- case "gameState":
- try {
- outstreams.get(client).writeUTF(ticTacToe_server.getGameState());
- outstreams.get(client).flush();
- serverLogger.printLog("Sent gameState", clientNames.get(client), LogType.Log);
- break;
- } catch (IOException e) {
- e.printStackTrace();
- }
+ case "ready":
+ gameFlow("gameState", client);
+ break;
- case "update":
+ case "gameState":
+ sendGameState(client);
+ break;
+
+ case "clientMove":
try {
+ //Get position (X|Y)
String position = instreams.get(client).readUTF();
serverLogger.printLog(position, clientNames.get(client), LogType.Message);
+ //Send confirmation (2ßß)
outstreams.get(client).writeInt(200);
outstreams.get(client).flush();
serverLogger.printLog("Sent verification code", clientNames.get(client), LogType.Log);
boolean moveAllowed = ticTacToe_server.makeClientMove(position);
if (moveAllowed) {
- String gameState = ticTacToe_server.getGameState();
- outstreams.get(client).writeUTF(gameState);
- outstreams.get(client).flush();
- serverLogger.printLog(String.format("Sent gameState: %s", gameState), clientNames.get(client), LogType.Log);
- break;
+ sendGameState(client);
} else {
- outstreams.get(client).writeUTF(" ");
+ //send " "
+ outstreams.get(client).writeUTF("userInput");
outstreams.get(client).flush();
+ serverLogger.printLog("Requested userInput", LogType.Log);
serverLogger.printLog(String.format("Move is not allowed!"), clientNames.get(client), LogType.Error);
- break;
}
} catch (IOException e) {
e.printStackTrace();
}
+ break;
+
+ case "computerMove":
+ ticTacToe_server.makeComputerMove();
+ sendGameState(client);
+ try {
+ outstreams.get(client).writeUTF("userInput");
+ outstreams.get(client).flush();
+ serverLogger.printLog("Requested userInput", LogType.Log);
+ } catch (IOException e) {
+ e.printStackTrace();
+ }
+ break;
+
+ case "serverType":
+ try {
+ outstreams.get(client).writeBoolean(true);
+ outstreams.get(client).flush();
+ serverLogger.printLog("Sent serverType", clientNames.get(client), LogType.Log);
+ } catch (IOException e) {
+ e.printStackTrace();
+ }
+ break;
+
+ case "isClientOne":
+ for (Map.Entry entry : clients.entrySet()) {
+ if (Objects.equals(client, entry.getValue())) {
+ try {
+ outstreams.get(client).writeBoolean(entry.getKey() == 0);
+ outstreams.get(client).flush();
+ serverLogger.printLog("Sent isPlayerOne", clientNames.get(client), LogType.Log);
+ } catch (IOException e) {
+ e.printStackTrace();
+ }
+ } else {
+ serverLogger.printLog("Current client not in clients!", LogType.Error);
+ }
+ }
+ break;
case "gameEnded":
try {
boolean gameEnded = ticTacToe_server.gameEnded();
outstreams.get(client).writeBoolean(gameEnded);
if (gameEnded) {
+ //send coordinates
String coordinates = "";
for (Point point: ticTacToe_server.getWinCoordinates()) {
coordinates += point.x + ";" + point.y + ";";
}
+ //send winning fields
outstreams.get(client).writeUTF(coordinates);
- break;
- } else {
- ticTacToe_server.makeServerMove();
- String gameState = ticTacToe_server.getGameState();
- outstreams.get(client).writeUTF(gameState);
- outstreams.get(client).flush();
- serverLogger.printLog(String.format("Sent gameState: %s", gameState), clientNames.get(client), LogType.Log);
- break;
}
} catch (IOException e) {
e.printStackTrace();
}
+ break;
case "exit()":
try {
@@ -169,10 +211,10 @@ public class SinglePlayerServer {
instreams.get(client).close();
client.close();
serverLogger.printLog(String.format("%s closed the connection",clientNames.get(client)), LogType.Log);
- break;
} catch (IOException e) {
e.printStackTrace();
}
+ break;
}
}
diff --git a/Server/src/game/TicTacToe_Server.java b/Server/src/res/TicTacToe_Server.java
similarity index 98%
rename from Server/src/game/TicTacToe_Server.java
rename to Server/src/res/TicTacToe_Server.java
index ab30ef6..dfaf859 100644
--- a/Server/src/game/TicTacToe_Server.java
+++ b/Server/src/res/TicTacToe_Server.java
@@ -1,4 +1,4 @@
-package game;
+package res;
import java.awt.*;
import java.nio.charset.StandardCharsets;
@@ -47,7 +47,7 @@ public class TicTacToe_Server {
}
}
- public void makeServerMove(){
+ public void makeComputerMove(){
LinkedList emptySpaces = getEmptySpaces();
if (emptySpaces.size() > 0) {
Random random = new Random();
diff --git a/out/production/Client/META-INF/MANIFEST.MF b/out/production/Client/META-INF/MANIFEST.MF
index b851779..eee92a3 100644
--- a/out/production/Client/META-INF/MANIFEST.MF
+++ b/out/production/Client/META-INF/MANIFEST.MF
@@ -1,3 +1,3 @@
Manifest-Version: 1.0
-Main-Class: game.TicTacToe_Client
+Main-Class: TicTacToe_Client
diff --git a/out/production/Client/game/TicTacToe_Client.css b/out/production/Client/res/TicTacToe_Client.css
similarity index 100%
rename from out/production/Client/game/TicTacToe_Client.css
rename to out/production/Client/res/TicTacToe_Client.css
diff --git a/out/production/Client/game/TicTacToe_Grid.png b/out/production/Client/res/TicTacToe_Grid.png
similarity index 100%
rename from out/production/Client/game/TicTacToe_Grid.png
rename to out/production/Client/res/TicTacToe_Grid.png