feat: TicTacToe interaction

This commit is contained in:
2024-12-30 21:22:13 +01:00
parent 171f760d4e
commit 910808eb6e
7 changed files with 371 additions and 2 deletions

View File

@ -3,5 +3,6 @@ package cz.jzitnik.api.types;
public enum Interaction {
Farmer,
Cashier,
Librarian
Librarian,
Innkeeper
}

View File

@ -45,6 +45,10 @@ public class Interactions {
Wordle wordle = new Wordle(character, apiService, playerKey);
wordle.play();
}
case Innkeeper -> {
TicTacToe ticTacToe = new TicTacToe(character, apiService, playerKey);
ticTacToe.play();
}
}
}
}

View File

@ -0,0 +1,125 @@
package cz.jzitnik.game.interactions;
import com.fasterxml.jackson.databind.ObjectMapper;
import cz.jzitnik.api.ApiService;
import cz.jzitnik.api.requests.InteractionRequest;
import cz.jzitnik.api.responses.InteractionResponse;
import cz.jzitnik.api.types.Character;
import cz.jzitnik.utils.Cli;
import lombok.AllArgsConstructor;
import lombok.Getter;
import java.io.Console;
import java.io.IOException;
@AllArgsConstructor
public class TicTacToe {
private Character character;
private ApiService apiService;
private String playerKey;
@Getter
private static class TicTacToeResponse {
public enum Type {
GAME_CREATED,
GAME_WON,
GAME_TIED,
GAME_CONTINUE,
}
private Type type;
private String[] board;
private boolean playerTurn;
}
public void play() throws IOException {
var response = apiService.isInteracting(playerKey, character.getId()).execute();
var interacting = response.body().getData().get();
if (!interacting) {
init();
} else {
// Get data where we have left off
var body = apiService.interact(playerKey, new InteractionRequest("get_data", character.getId())).execute().body();
var data = body.getData().get();
gameContinue(data);
}
}
private void init() throws IOException {
var body = apiService.interact(playerKey, new InteractionRequest("", character.getId())).execute().body();
var data = body.getData().get();
gameContinue(data);
}
private void gameContinue(InteractionResponse data) throws IOException {
ObjectMapper objectMapper = new ObjectMapper();
var ticTacToeData = objectMapper.readValue(data.getResponseText(), TicTacToeResponse.class);
switch (ticTacToeData.getType()) {
case GAME_WON -> {
System.out.println(formatBoard(ticTacToeData.getBoard()));
Cli.type(character, "Vyhrál jsi!");
Cli.gotItems(data.getItems());
}
case GAME_TIED -> Cli.type(character, "Prohrál jsi! Hra skončila remízou.");
case GAME_CONTINUE, GAME_CREATED -> {
System.out.println("Aktuální stav pole:");
System.out.println(formatBoard(ticTacToeData.getBoard()));
if (ticTacToeData.isPlayerTurn()) {
var move = askForMove(ticTacToeData.getBoard());
var response = apiService.interact(playerKey, new InteractionRequest(String.valueOf(move), character.getId())).execute();
var body = response.body().getData().get();
gameContinue(body);
} else {
System.out.println("Čekání na tah počítače...");
// Wait for computer to play its move
var response = apiService.interact(playerKey, new InteractionRequest("get_data", character.getId())).execute();
var body = response.body().getData().get();
gameContinue(body);
}
}
}
}
private String formatBoard(String[] board) {
StringBuilder boardRepresentation = new StringBuilder();
for (int i = 0; i < 9; i++) {
boardRepresentation.append(board[i]);
if ((i + 1) % 3 == 0) {
boardRepresentation.append("\n");
} else {
boardRepresentation.append(" ");
}
}
return boardRepresentation.toString();
}
private int askForMove(String[] board) {
Console console = System.console();
String data = console.readLine("Zadejte číslo pole (1-9): ");
try {
int move = Integer.parseInt(data);
if (move < 1 || move > 9) {
Cli.error("Neplatný vstup! Číslo musí být mezi 1 a 9.");
return askForMove(board);
}
if (!board[move].equals("_")) {
Cli.error("Toto pole již bylo obsazeno!");
return askForMove(board);
}
return move - 1;
} catch (NumberFormatException e) {
Cli.error("Neplatný vstup! Zadejte číslo.");
return askForMove(board);
}
}
}