Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
36 changes: 18 additions & 18 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,18 +1,18 @@
# Tic Tac Toe Game

A fully interactive Tic Tac Toe game built using JavaFX. The game supports two players, maintains a leaderboard, and tracks average time per move.

## Features
- Interactive GUI for Tic Tac Toe gameplay.
- Player leaderboard with win/loss statistics and average time per move.
- Dynamic game timer for each player's turn.
- Persistent player data storage and retrieval.

## Prerequisites
- **Java Development Kit (JDK):** Version 17 or higher
- **JavaFX:** Ensure that JavaFX is correctly configured in your IntelliJ IDEA project.

## Setup Instructions
1. Clone the repository to your local machine.
```bash
git clone <repository-url>
# Tic Tac Toe Game
A fully interactive Tic Tac Toe game built using JavaFX. The game supports two players, maintains a leaderboard, and tracks average time per move.
## Features
- Interactive GUI for Tic Tac Toe gameplay.
- Player leaderboard with win/loss statistics and average time per move.
- Dynamic game timer for each player's turn.
- Persistent player data storage and retrieval.
## Prerequisites
- **Java Development Kit (JDK):** Version 17 or higher
- **JavaFX:** Ensure that JavaFX is correctly configured in your IntelliJ IDEA project.
## Setup Instructions
1. Clone the repository to your local machine.
```bash
git clone <repository-url>
Binary file modified players.dat
Binary file not shown.
162 changes: 75 additions & 87 deletions pom.xml
Original file line number Diff line number Diff line change
@@ -1,88 +1,76 @@
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>

<groupId>co.ppg2</groupId>
<artifactId>TicTacToe</artifactId>
<version>1.0.0</version>

<properties>
<maven.compiler.source>21</maven.compiler.source>
<maven.compiler.target>21</maven.compiler.target>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<junit.version>5.11.2</junit.version>
<javafx.version>22</javafx.version>
</properties>
<dependencies>
<dependency>
<groupId>org.openjfx</groupId>
<artifactId>javafx-fxml</artifactId>
<version>${javafx.version}</version>
</dependency>
<dependency>
<groupId>org.openjfx</groupId>
<artifactId>javafx-web</artifactId>
<version>${javafx.version}</version>
</dependency>

<dependency>
<groupId>org.junit.jupiter</groupId>
<artifactId>junit-jupiter-api</artifactId>
<version>${junit.version}</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.junit.jupiter</groupId>
<artifactId>junit-jupiter-engine</artifactId>
<version>${junit.version}</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.testfx</groupId>
<artifactId>testfx-core</artifactId>
<version>4.0.18</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.testfx</groupId>
<artifactId>testfx-junit5</artifactId>
<version>4.0.18</version>
<scope>test</scope>
</dependency>
</dependencies>

<build>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<version>3.13.0</version>
<configuration>
<source>21</source>
<target>21</target>
</configuration>
</plugin>
<plugin>
<groupId>org.openjfx</groupId>
<artifactId>javafx-maven-plugin</artifactId>
<version>0.0.8</version>
<executions>
<execution>
<!-- Default configuration for running with: mvn clean javafx:run -->
<id>default-cli</id>
<configuration>
<launcher>app</launcher>
<jlinkZipName>app</jlinkZipName>
<jlinkImageName>app</jlinkImageName>
<noManPages>true</noManPages>
<stripDebug>true</stripDebug>
<noHeaderFiles>true</noHeaderFiles>
</configuration>
</execution>
</executions>
</plugin>
</plugins>
</build>
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>

<groupId>co.ppg2</groupId>
<artifactId>TicTacToe</artifactId>
<version>1.0.0</version>

<properties>
<maven.compiler.source>21</maven.compiler.source>
<maven.compiler.target>21</maven.compiler.target>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<junit.version>5.11.2</junit.version>
<javafx.version>22</javafx.version>
</properties>
<dependencies>
<dependency>
<groupId>org.openjfx</groupId>
<artifactId>javafx-fxml</artifactId>
<version>${javafx.version}</version>
</dependency>
<dependency>
<groupId>org.openjfx</groupId>
<artifactId>javafx-web</artifactId>
<version>${javafx.version}</version>
</dependency>

<dependency>
<groupId>org.junit.jupiter</groupId>
<artifactId>junit-jupiter-api</artifactId>
<version>${junit.version}</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.junit.jupiter</groupId>
<artifactId>junit-jupiter-engine</artifactId>
<version>${junit.version}</version>
<scope>test</scope>
</dependency>
</dependencies>

<build>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<version>3.13.0</version>
<configuration>
<source>21</source>
<target>21</target>
</configuration>
</plugin>
<plugin>
<groupId>org.openjfx</groupId>
<artifactId>javafx-maven-plugin</artifactId>
<version>0.0.8</version>
<executions>
<execution>
<!-- Default configuration for running with: mvn clean javafx:run -->
<id>default-cli</id>
<configuration>
<launcher>app</launcher>
<jlinkZipName>app</jlinkZipName>
<jlinkImageName>app</jlinkImageName>
<noManPages>true</noManPages>
<stripDebug>true</stripDebug>
<noHeaderFiles>true</noHeaderFiles>
</configuration>
</execution>
</executions>
</plugin>
</plugins>
</build>
</project>
171 changes: 86 additions & 85 deletions src/main/java/co/ppg2/Main.java
Original file line number Diff line number Diff line change
@@ -1,85 +1,86 @@
package co.ppg2;

import co.ppg2.controllers.GameController;
import co.ppg2.controllers.PlayerDataController;
import co.ppg2.model.Player;
import co.ppg2.services.GameTimer;
import co.ppg2.views.GameView;
import co.ppg2.views.PlayerPopup;
import javafx.application.Application;
import javafx.stage.Stage;
import java.util.ArrayList;

/**
* Adapted from <a href="https://liveexample.pearsoncmg.com/html/TicTacToe.html">...</a>
* Main class for launching the Tic Tac Toe game application.
* This class is responsible for setting up the game, including the players and game timer.
* It also initializes the main game view and controls the flow of the game.
*/
public class Main extends Application {
private static ArrayList<Player> players;
public static GameController gameController;
public static GameView gameView;
public static GameTimer gameTimer; // Shared GameTimer instance

/**
* The entry point for the application. Loads saved players and launches the game.
*
* @param args the command-line arguments (unused).
*/
public static void main(String[] args) {
players = PlayerDataController.loadPlayers(); // Load players on start
launch(args);
}

/**
* Starts the application by displaying the player setup and initializing the game.
* Prompts for the usernames of Player X and Player O, sets up the game,
* and starts the game timer for Player X.
*
* @param primaryStage the main stage for the application.
*/
@Override
public void start(Stage primaryStage) {
// Prompt for Player X's username and Player O's username
Player playerX = PlayerPopup.showPopup("Player X");
Player playerO = PlayerPopup.showPopup("Player O");

// Find or add Player X and Player O in the players list
playerX = findOrAddPlayer(playerX.getUsername());
playerO = findOrAddPlayer(playerO.getUsername());

// Initialize shared GameTimer
gameTimer = new GameTimer();

// Initialize GameController and GameView
gameController = new GameController(playerX, playerO);
gameController.setGameTimer(gameTimer); // Pass GameTimer to GameController
gameView = new GameView(gameController, primaryStage);
gameController.setGameView(gameView);

// Launch the game view
gameView.launchGame();

// Start the timer for Player X
gameTimer.startTimer(playerX.getUsername());
}

/**
* Finds an existing player by username or creates a new player if not found.
*
* @param username the username of the player to find or add.
* @return the found or newly created Player.
*/
private Player findOrAddPlayer(String username) {
for (Player player : players) {
if (player.getUsername().equals(username)) {
return player;
}
}
Player newPlayer = new Player(username);
players.add(newPlayer);
PlayerDataController.savePlayers(players);
return newPlayer;
}
}
package co.ppg2;

import co.ppg2.controllers.GameController;
import co.ppg2.controllers.PlayerDataController;
import co.ppg2.model.Player;
import co.ppg2.services.GameTimer;
import co.ppg2.views.GameView;
import co.ppg2.views.PlayerPopup;
import javafx.application.Application;
import javafx.stage.Stage;
import java.util.ArrayList;

public class Main extends Application {
/**
* Add javadoc would be helpful
*/
private static ArrayList<Player> players;
public static GameController gameController;
public static GameView gameView;
public static GameTimer gameTimer; // Shared GameTimer instance

public static void main(String[] args) {
players = PlayerDataController.loadPlayers(); // Load players on start
launch(args);
}
//can put in playerdatacontroller class instead of having it within the start method which is more efficient

@Override
public void start(Stage primaryStage) {
// Prompt for Player X's username and Player O's username
Player playerX = PlayerPopup.showPopup("Player X");
Player playerO = PlayerPopup.showPopup("Player O");




// Find or add Player X and Player O in the players list
playerX = findOrAddPlayer(playerX.getUsername());
playerO = findOrAddPlayer(playerO.getUsername());




// Initialize shared GameTimer
gameTimer = new GameTimer();




// Initialize GameController and GameView
gameController = new GameController(playerX, playerO);
gameController.setGameTimer(gameTimer); // Pass GameTimer to GameController
gameView = new GameView(gameController, primaryStage);
gameController.setGameView(gameView);




// Launch the game view
gameView.launchGame();




// Start the timer for Player X
gameTimer.startTimer(playerX.getUsername());
}




private Player findOrAddPlayer(String username) {
for (Player player : players) {
if (player.getUsername().equals(username)) {
return player;
}
}
Player newPlayer = new Player(username);
players.add(newPlayer);
PlayerDataController.savePlayers(players);
return newPlayer;
}
}



Loading