import javafx.application.Application; import javafx.geometry.*; import javafx.scene.Scene; import javafx.scene.image.*; import javafx.scene.control.*; import javafx.scene.layout.*; import javafx.stage.Stage; import java.util.Random; public class GameUI extends Application{ Scene game, winningScene; BorderPane gameBorderPane, winningBorderPane; private Board board = new Board(); private Label playerLabel = new Label("Player X's turn"); private Label winnerLabel = new Label("Won"); private Label scoreLabelX = new Label("Player X: 0"); private Label scoreLabelO= new Label("Player O: 0"); private Button[] buttons = new Button[9]; /** * Random for Images */ Random rnd = new Random(); /** * Provides styles allignment and the scenes for labels, buttons and boxes. * * @param stage starts the scene and is the main stage for the application */ @Override public void start(Stage stage){ playerLabel.setStyle("-fx-font-size: 30px; -fx-font-family: 'Impact'; -fx-text-fill: blue;"); winnerLabel.setStyle("-fx-font-size: 150px; -fx-font-family: 'Impact'; -fx-text-fill: blue;"); scoreLabelX.setStyle("-fx-font-size: 30px; -fx-font-family: 'Impact'; -fx-text-fill: black;"); scoreLabelO.setStyle("-fx-font-size: 30px; -fx-font-family: 'Impact'; -fx-text-fill: black;"); gameBorderPane = new BorderPane(); winningBorderPane = new BorderPane(); GridPane gridPane = new GridPane(); for(int i = 0; i < 9; i++){ int index = i; buttons[i] = new Button(); buttons[i].setPrefSize(150, 150); buttons[i].setOnAction(e -> handleTurn(index, stage)); String imageSymbols = getClass().getResource("/textures/empty.png").toExternalForm(); Image image = new Image("" + imageSymbols); ImageView imageView = new ImageView(image); imageView.setFitWidth(135); imageView.setFitHeight(135); imageView.setPreserveRatio(true); buttons[index].setGraphic(imageView); gridPane.add(buttons[i], i % 3, i / 3); } gameBorderPane.setCenter(gridPane); //HBox for the labels HBox box = new HBox(20); box.setAlignment(Pos.CENTER); playerLabel.setAlignment(Pos.TOP_CENTER); playerLabel.setPadding(new Insets(10, 0, 15, 15)); box.getChildren().add(playerLabel); //space between the labels Region spacer = new Region(); HBox.setHgrow(spacer, Priority.ALWAYS); box.getChildren().add(spacer); //score labels design scoreLabelX.setAlignment(Pos.TOP_CENTER); scoreLabelO.setAlignment(Pos.TOP_CENTER); VBox scoreBox = new VBox(15); scoreBox.setPadding(new Insets(15, 25, 5, 5)); scoreBox.setAlignment(Pos.TOP_RIGHT); scoreBox.getChildren().addAll(scoreLabelX, scoreLabelO); box.getChildren().add(scoreBox); gameBorderPane.setTop(box); //board allignment gridPane.setPadding(new Insets(10)); gridPane.setHgap(30); gridPane.setVgap(30); gridPane.setAlignment(Pos.CENTER); //reset button Button reset = new Button("Reset"); reset.setStyle("-fx-font-size: 30px; -fx-font-family: 'Impact'; -fx-text-fill: black;"); reset.setOnAction(e -> { board = new Board(board.getPlayers(), board.getFirstPlayer()); for(int i = 0; i < 9; i++){ int index = i; String imageSymbols = getClass().getResource("/textures/empty.png").toExternalForm(); Image image = new Image("" + imageSymbols); ImageView imageView = new ImageView(image); imageView.setFitWidth(135); imageView.setFitHeight(135); imageView.setPreserveRatio(true); buttons[index].setGraphic(imageView); } updatePlayerTurn(board.getCurrentPlayer()); stage.setScene(game); }); //winning/tie screen winnerLabel.setAlignment(Pos.CENTER); VBox finalBox = new VBox(35); finalBox.setAlignment(Pos.CENTER); finalBox.getChildren().addAll(winnerLabel, reset); winningBorderPane.setCenter(finalBox); winningScene = new Scene(winningBorderPane, 1500,850); //main Scene game = new Scene(gameBorderPane, 1500, 850); stage.setScene(game); stage.setTitle("Tick-Tack-Trauma"); stage.show(); } /** * method for the game updating its state including changing turn of the player and check for win or tie. Images are set as symbols. * * @param index of the selectet tile * @param stage current scene */ private void handleTurn(int index, Stage stage){ if (board.hasTileOwner(index)) { return; } int currentPlayer = board.getCurrentPlayer(); board.setTileOwner(index, currentPlayer); //replace symbols with images int i = rnd.nextInt(10); String imageSymbols = currentPlayer == 0 ? getClass().getResource("/textures/1_" + i + ".png").toExternalForm() : getClass().getResource("/textures/0_" + i + ".png").toExternalForm(); Image image = new Image(""+ imageSymbols); ImageView imageView = new ImageView(image); //size of the image imageView.setFitWidth(135); imageView.setFitHeight(135); imageView.setPreserveRatio(true); buttons[index].setGraphic(imageView); switch (board.turnEnd()) { case 0: updatePlayerTurn(board.getCurrentPlayer()); break; case 1: //changes label state for the winning player and updates its score winnerLabel.setText("Player " + (currentPlayer == 0 ? "X" : "O") + " wins!"); updatePlayerScore(); stage.setScene(winningScene); break; case 2: //changes label state to draw winnerLabel.setText("It's a draw!"); stage.setScene(winningScene); break; default: //should never be reached System.out.println("How did we get here?"); break; } } /** * updates the label of the current player * * @param currentPlayer player whose turn it is */ private void updatePlayerTurn(int currentPlayer) { String playerSymbol = (currentPlayer == 0) ? "X" : "O"; playerLabel.setText("Player " + playerSymbol + "'s turn"); } /** * updates the score of a player who won * */ private void updatePlayerScore(){ scoreLabelX.setText("Player X: " + board.getPlayer(0).getPlayerScore()); scoreLabelO.setText("Player O: " + board.getPlayer(1).getPlayerScore()); } /** * starts the javafx application * * @param args */ public void call(String[] args){ launch(args); } }