每次运行我的代码时,GUI都是空白的终极tic tac toe游戏

时间:2016-11-23 13:51:30

标签: user-interface javafx

我一直在努力完成这个终极Tic Tac toe游戏,但我在哪里出错了我不知所措。我的问题是,当我编译并运行代码时,我得到的是一个空白的GUI returncode。除此之外,代码正在后台工作。它只是没有显示构成游戏的垂直和水平线条以及碎片。我很欣赏任何帮助,或者只是指出我正确的方向,谢谢。

我希望重新审视我的代码会看到我所缺少的内容。这是我的XOBoard代码

package javafxapplicationprototype;

//an implementation of the XO board and the game logic
//imports necessary for this class
import javafx.scene.layout.Pane;
import javafx.scene.shape.Circle;
import javafx.scene.paint.Color;
import javafx.scene.shape.Line;
import javafx.scene.shape.Rectangle;
import javafx.scene.transform.Translate;
//class definition for drawing a game board
class XOBoard extends Pane 
{
//constructor for the class
public XOBoard(XOUltimateBoard ultimate1) 
{

    this.ultimate1 = ultimate1;
        // Initialise the boards
        board = new int[3][3];
        // renders is an array that holds the 'render pieces'
        renders = new XOPiece[3][3];
        // initialise the rectangle
         back = new Rectangle();
        // add the rectangle
        getChildren().addAll(back);

    //init the board
    board = new int[3][3];
    renders = new XOPiece[3][3];
    for(int i = 0; i < 3; i++)
        for(int j = 0; j < 3; j++){
            board[i][j] = EMPTY;
            renders[i][j] = null;
        }


    back = new Rectangle();
    back.setFill(Color.BLACK);
    h1 = new Line(); h2 = new Line();
    v1 = new Line(); v2 = new Line();
    h1.setStroke(Color.WHITE); h2.setStroke(Color.WHITE);
    v1.setStroke(Color.WHITE); v2.setStroke(Color.WHITE);

    //horazontal lines 
    h1.setStartX(0); h1.setStartY(0); h1.setEndY(0);
    h2.setStartX(0); h2.setStartY(0); h2.setEndY(0);

    //vertical lines
    v1.setStartX(0); v1.setStartY(0); v1.setEndX(0);
    v2.setStartX(0); v2.setStartY(0); v2.setEndX(0);

    //translation of one cell height and two cell heights
    ch_one = new Translate(0,0);
    ch_two = new Translate(0,0);
    h1.getTransforms().add(ch_one);
    h2.getTransforms().add(ch_two);

    //translation of one cell height and two cell heights
    cw_one = new Translate(0,0);
    cw_two = new Translate(0,0);
    v1.getTransforms().add(cw_one);
    v2.getTransforms().add(cw_two);       

    //add rectangle and lines to this group 
    getChildren().addAll(back,h1,h2,v1,v2);
}


// we have to override resizing behaviour to make our view appear properly
@Override
public void resize(double width, double height) 
{
    //call the superclass method first
    super.resize(width, height);

    // figure out the width and height of a cell
    cell_width = width / 3.0;
    cell_height = height / 3.0;

    //resize the rectangle to take the full size of the widget
    back.setWidth(width); back.setHeight(height);

    //set a new y on the horizontal lines and translate them in to place 
    ch_one.setY(cell_height); ch_two.setY(2 * cell_height);
    h1.setEndX(width); h2.setEndX(width);

    //set a new x on the vertical lines and translate them into place
    cw_one.setX(cell_width); cw_two.setX(2 * cell_width);
    v1.setEndX(height); v2.setEndX(height);

    // we need to reset the sizes and positions of all XOPieces that were placed
    for(int i = 0; i < 3; i++) 
    {
        for(int j = 0; j < 3; j++) 
        {
            if(board[i][j] != 0) 
            {
                renders[i][j].relocate(i * cell_width, j * cell_height);
                renders[i][j].resize(cell_width, cell_height);
            }


        }
    }

}



//public method for resetting the game
public void resetGame() 
{
    for(int i = 0; i < 3; i++) 
    {
        for(int j = 0; j < 3; j++) 
        {
            board[i][j] = 0;
            getChildren().remove(renders[i][j]);
            renders[i][j]= null;
        }
    }
}

//public method that tries to place a piece
public void placePiece(final double x, final double y)
{   
    // translate the x, y coordinates into cell indexes
    int indexx = (int) (x / cell_width);
    int indexy = (int) (y / cell_height);

    // if the position is empty then place a piece and swap the players
    if(board[indexx][indexy] == XPIECE) //toke this out  == EMPTY && current_player 
    {       
        // board is the array that holds all the pieces
        board[indexx][indexy] = XPIECE;
        // Create a new XPIECE
        renders[indexx][indexy] = new XOPiece(XPIECE);
        renders[indexx][indexy].resize(cell_width, cell_height);
        renders[indexx][indexy].relocate(indexx * cell_width,indexy * cell_height);
        // Place an X on the board at position x,y
        getChildren().add(renders[indexx][indexy]);
        this.ultimate1.setCurrent_player(OPIECE);


    }   
else if(board[indexx][indexy]== OPIECE) //toke this out  == EMPTY &&        current_player 
    {
        // board is the array that holds all the pieces
        board[indexx][indexy] = OPIECE;
        // Create a new XPIECE
        renders[indexx][indexy] = new XOPiece(OPIECE);
        renders[indexx][indexy].resize(cell_width, cell_height);
        renders[indexx][indexy].relocate(indexx * cell_width,indexy * cell_height);
        // Place an X on the board at position x,y
        getChildren().add(renders[indexx][indexy]);
        this.ultimate1.setCurrent_player(XPIECE);
    }

}

//private fields of the class
private int[][] board; // array that holds all pieces
private XOPiece[][] renders; // array that holds all the render pieces
private Rectangle back; // background of the board
private final Line h1, h2, v1, v2; // horizontal and vertical grid lines
private double cell_width, cell_height; // width and height of a cell
//translation of {one, two} cell {width, height}
private final Translate ch_one, ch_two, cw_one, cw_two;
// constants for the class
    private final XOUltimateBoard ultimate1;
private final int EMPTY = 0;
private final int XPIECE = 1;
private final int OPIECE = 2;
}

它从我的XOUltimateBoard类女巫的召唤应该是3场* 3场比赛的终极棋盘游戏

    package javafxapplicationprototype;

//an implementation of the XO board and the game logic
//imports necessary for this class
import javafx.scene.layout.Pane;
import javafx.scene.shape.Circle;
import javafx.scene.paint.Color;
import javafx.scene.shape.Line;
import javafx.scene.shape.Rectangle;
import javafx.scene.transform.Translate;




//class definition for drawing a game board
class XOUltimateBoard extends Pane 
{
    //constructor for the class
    public XOUltimateBoard() 
    {

    // renders is an array that holds the 'render pieces'
    renders = new XOBoard[3][3];

    // Initialise the boards
    board = new int[3][3];
    for (int i = 0; i < 3; i++) 
    {
        for (int j = 0; j < 3; j++)
        {
        board[i][j] = EMPTY;
        renders[i][j] = new XOBoard(this);
        getChildren().add(renders[i][j]);
        }

    }       
    // Current Player is Always X to begin with
    current_player = OPIECE;

}


// override resizing behaviour to make our view appear properly
@Override
public void resize(double width, double height) 
{
    //call the superclass method first
    super.resize(width, height);

    // figure out the width and height of a cell
    cell_width = width / 3.0;
    cell_height = height / 3.0;

    // reset the sizes and positions of all XOPieces that were placed
    for(int i = 0; i < 3; i++) 
    {
        for(int j = 0; j < 3; j++) 
        {
            if(board[i][j] != 0) 
            {
                renders[i][j].relocate(i * cell_width, j * cell_height);
                renders[i][j].resize(cell_width, cell_height);
            }

        }
    }

}



//public method for resetting the game
public void resetGame() 
{
    for(int i = 0; i < 3; i++) 
    {
        for(int j = 0; j < 3; j++) 
        {
            board[i][j] = 0;
            getChildren().remove(renders[i][j]);
        }
    }
}

// Return the current player
public int getCurrent_player(){
    return current_player;
}

// Set the current player
public void setCurrent_player(int current_player){
    this.current_player = current_player;
}

//public method that tries to place a piece
public void placePiece(final double x, final double y)
{   
    //x and y store the coordinates of where the user clicked on the board
    System.out.println(x);
    System.out.println(y);

    // all cells have a constant height and width
    System.out.println(cell_width);
    System.out.println(cell_height);

    // translate the x, y coordinates into cell indexes
    int indexx = (int) (x / cell_width);
    int indexy = (int) (y / cell_height);

    System.out.println("indexx y and indexx x :");
    System.out.println(indexx);
    System.out.println(indexy);


    // if the position is empty then place a piece and swap the players
    if(board[indexx][indexy] == EMPTY && current_player == XPIECE) 
    {
        System.out.println("Value of board[indexx][indexy] IS..."+XPIECE);

        // board is the array that holds all the pieces
        board[indexx][indexy] = XPIECE;


        System.out.println("board[indexx][indexy]....");
        System.out.println(board[indexx][indexy]);
        // Create a new XPIECE
        //renders[indexx][indexy] = new XOPiece(XPIECE);
        // Place an X on the board at position x,y
        getChildren().add(renders[indexx][indexy]);
        current_player = OPIECE;
    }

    else if(board[indexx][indexy] == EMPTY && current_player == OPIECE) 
    {
        board[indexx][indexy] = OPIECE;
        System.out.println("Value of OPIECE IS...");
        System.out.println(OPIECE);
        //renders[indexx][indexy] = new XOPiece(OPIECE);
        getChildren().add(renders[indexx][indexy]);
        current_player = XPIECE;
    }



}

//private fields of the class
private final int[][] board; // array that holds all pieces
private final XOBoard[][] renders; // array that holds all the render pieces
private double cell_width, cell_height; // width and height of a cell
// translation of {one, two} cell {width, height}
private int current_player; // who is the current player
// constants for the class
private final int EMPTY = 0;
private final int XPIECE = 1;
private final int OPIECE = 2;

}  

1 个答案:

答案 0 :(得分:0)

我不知道为什么您发布的代码无法正常运行。但是,您在此处使用的方法 - 继承Pane并自行管理布局 - 可能不是这种布局的好方法。问题(子类化库类通用的问题)是你没有足够的信息知道如何执行布局 - 例如何时调用resize(..),例如,与layoutChildren()等有关。很可能你只是造成了一些阻止渲染进展的无限循环。

相反,请考虑使您的类使用合成而不是继承,并使用现有布局。 GridPane具有您需要的所有功能。您可以使用CSS样式来提供颜色之间的颜色和间隙等。

以下是我如何处理布局和样式:

XOPiece.java:

import javafx.scene.Parent;
import javafx.scene.layout.StackPane;

public class XOPiece {

    private final StackPane view ;

    public XOPiece() {
        view = new StackPane();
        view.getStyleClass().add("xo-piece");
    }

    // functionality to maintain state of piece (empty, O, or X) and
    // add content to view as state changes, etc.

    public Parent getView() {
        return view ;
    }
}

XOBoard.java:

import javafx.css.PseudoClass;
import javafx.scene.Parent;
import javafx.scene.layout.ColumnConstraints;
import javafx.scene.layout.GridPane;
import javafx.scene.layout.RowConstraints;

public class XOBoard {
    private final GridPane view ;

    public XOBoard() {
        view = new GridPane();

        for (int i = 0 ; i < 3; i++) {
            ColumnConstraints cc = new ColumnConstraints();
            cc.setPercentWidth(100.0/3);
            view.getColumnConstraints().add(cc);
        }

        for (int i = 0 ; i < 3; i++) {
            RowConstraints rc = new RowConstraints();
            rc.setPercentHeight(100.0/3);
            view.getRowConstraints().add(rc);
        }

        for (int x = 0 ; x < 3; x++) {
            for (int y = 0 ; y < 3; y++) {
                XOPiece piece = new XOPiece();
                view.add(piece.getView(), x, y);
                GridPane.setFillHeight(piece.getView(), true);
                GridPane.setFillWidth(piece.getView(), true);
                piece.getView().pseudoClassStateChanged(PseudoClass.getPseudoClass("top"), y==0);
                piece.getView().pseudoClassStateChanged(PseudoClass.getPseudoClass("bottom"), y==2);
                piece.getView().pseudoClassStateChanged(PseudoClass.getPseudoClass("left"), x==0);
                piece.getView().pseudoClassStateChanged(PseudoClass.getPseudoClass("right"), x==2);             
            }
        }

        view.getStyleClass().add("xo-board");
    }

    public Parent getView() {
        return view ;
    }
}

XOUltimateBoard.java

import javafx.scene.Parent;
import javafx.scene.layout.ColumnConstraints;
import javafx.scene.layout.GridPane;
import javafx.scene.layout.RowConstraints;

public class XOUltimateBoard {

    private final GridPane view ;

    private static final int ROWS = 3 ;
    private static final int COLUMNS = 3 ;

    private final XOBoard[][] boards ;

    public XOUltimateBoard() {
        view = new GridPane();

        for (int i = 0 ; i < COLUMNS; i++) {
            ColumnConstraints cc = new ColumnConstraints();
            cc.setPercentWidth(100.0/COLUMNS);
            view.getColumnConstraints().add(cc);
        }

        for (int i = 0 ; i < ROWS; i++) {
            RowConstraints rc = new RowConstraints();
            rc.setPercentHeight(100.0/ROWS);
            view.getRowConstraints().add(rc);
        }

        boards = new XOBoard[COLUMNS][ROWS];

        for (int x = 0; x < COLUMNS; x++) {
            for (int y = 0 ; y < ROWS ; y++) {
                boards[x][y] = new XOBoard();
                view.add(boards[x][y].getView(), x, y);
                GridPane.setFillWidth(boards[x][y].getView(), true);
                GridPane.setFillHeight(boards[x][y].getView(), true);
            }
        }


        view.getStyleClass().add("ultimate-board");
    }

    public Parent getView() {
        return view ;
    }
}

Main.java:

import javafx.application.Application;
import javafx.scene.Scene;
import javafx.stage.Stage;

public class Main extends Application {

    @Override
    public void start(Stage primaryStage) {
        Scene scene = new Scene(new XOUltimateBoard().getView());
        scene.getStylesheets().add("ultimate-board.css");
        primaryStage.setScene(scene);
        primaryStage.show();
    }

    public static void main(String[] args) {
        launch(args);
    }
}

最终-board.css

.ultimate-board {
    -fx-hgap: 10 ;
    -fx-vgap: 10 ;
    -fx-min-width: 400 ;
    -fx-min-height: 400 ;
}
.xo-board {
    -fx-background-color: black ;
}
.xo-board-line {
    -fx-stroke: white ;
}
.xo-piece {
    -fx-background-color: white, black ;
    -fx-background-insets: 0, 1 ;
}
.xo-piece:top {
    -fx-background-insets: 0, 0 1 1 1 ;
}
.xo-piece:bottom {
    -fx-background-insets: 0, 1 1 0 1 ;
}
.xo-piece:left {
    -fx-background-insets: 0, 1 1 1 0 ;
}
.xo-piece:right {
    -fx-background-insets: 0, 1 0 1 1 ;
}
.xo-piece:top:left {
    -fx-background-insets: 0, 0 1 1 0 ;
}
.xo-piece:top:right {
    -fx-background-insets: 0, 0 0 1 1 ;
}
.xo-piece:bottom:left {
    -fx-background-insets: 0, 1 1 0 0 ;
}
.xo-piece:bottom:right {
    -fx-background-insets: 0, 1 0 0 1 ;
}

enter image description here