Java implementa un simple tic-tac-toe (juego OX) V2.0

Introduccion

Descripción del puesto
Aún después del último juego de OX, esta vez la solicitud del maestro es extraña y extraña para decir la verdad, pero después de leerla varias veces, tenemos que entender algunos puntos clave, "esquina superior izquierda", "dibujar" . Parece que acabo de aprender a pintar, así que, en todos los casos, uso paint () para escribirlo. Nota: ¡paint () se ejecuta automáticamente! ! ! En otras palabras, no necesita llamarlo, ¡se dibujará automáticamente en la capa de la clase en la que se encuentre cuando ejecute el programa! !

Ideas principales

  1. Coloque el botón en la esquina superior izquierda de cada cuadrado. Cancele los nueve botones originales para llenar un tablero de ajedrez (JPanel), en lugar de llenar 9 paneles de ajedrez (ChessPanel extiende JPanel) en el tablero de ajedrez de acuerdo con el diseño de la tabla, luego llene los botones originales en el panel de ajedrez de diseño vacío (nulo) (1. Si el diseño no está vacío, no se puede establecer el tamaño del botón. 2. El diseño vacío por defecto coloca el componente en la esquina superior izquierda). Configure el borde del panel de ajedrez para que sea visible, reflejando el "cuadrado pequeño". (Principalmente modificado en initChessboard ())
  2. Responda a eventos y haga dibujos. En primer lugar, debemos tener claro que nuestro objetivo es realizar una operación de círculo o tenedor en el panel de ajedrez después de hacer clic en el botón, pero la pintura se ejecuta automáticamente y no tenemos forma de controlarlo directamente. Por lo tanto, solo podemos configurar cada panel de ajedrez configurándolo La visibilidad del círculo interno o la bifurcación, y luego volver a dibujar (más repintar ()) a través de la respuesta del evento (modificar actionPerformed ()) para lograr el efecto (ver paint () para más detalles). ¿Cómo hacer un dibujo? El tema requiere dibujar círculos y tenedores, por lo que drawLine () se usa para dibujar dos líneas verticales, y drawOval es suficiente para dibujar un círculo. Si desea un punto de vista hermoso, primero ajuste el grosor del pincel para dibujar el color. También puede considerar poner la imagen directamente. Estos dos métodos se reflejan en mi código. Finalmente, enfatice que las coordenadas son coordenadas relativas, es decir, si su pintura está en el panel de ajedrez [3], entonces las coordenadas se refieren a la posición relativa de la esquina superior izquierda del componente dibujado a la esquina superior izquierda del panel de ajedrez [3]. Vea esta publicación de blog para más detalles .

Efecto

Inserte la descripción de la imagen aquí
PD: Originalmente quería cambiar el botón para mantener el número sin cambios, pero fue demasiado problema cambiarlo, así que no lo hice.

Código

import javax.swing.*;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;

public class TestOXGame {
    public static void main(String[] args) {
        MyOXGame myoxgame=new MyOXGame();
    }
}

class MyOXGame extends JFrame implements ActionListener {
    //主体部分,绘制GUI,编辑有关响应

    JButton[] button;//对象数组,表示棋盘上的九个格子
    ChessPanel[] chessPanel;//小方格,放棋子的panel
    JButton restart;//重置键
    JLabel judgement;//裁判,用来显示游戏的结果
    JPanel chessboard,basicPanel;//棋盘,棋盘下部区域
    int player=0;//显示当前玩家编号
    boolean gameOverFlag=false;//记录游戏是否结束,如果结束值为true,停止对事件的响应

    MyOXGame(){//生成函数,生成游戏
        setTitle("MY OXGAME");
        setBounds(400,400,340,360);//窗体基本设置

        button=new JButton[10];
        chessPanel=new ChessPanel[10];
        restart=new JButton("Restart");
        chessboard=new JPanel();
        basicPanel=new JPanel();
        judgement=new JLabel("");
        chessboard.setLayout(new GridLayout(3,3));
        basicPanel.setLayout(new FlowLayout());//组件初始化设置

        add(chessboard,BorderLayout.CENTER);
        add(basicPanel,BorderLayout.SOUTH);
        basicPanel.add(restart);
        basicPanel.add(judgement);//布局设置

        initChessboard();//初始化棋盘,使九个按钮按顺序加上1-9的标签,
        addChessToChessboard(chessboard);//将九个按钮添加至chessboard
        restart.addActionListener(this);//添加监听器

        buttonListener();//为按钮添加监听器

        setVisible(true);//设置可视化
        setDefaultCloseOperation(JFrame.DISPOSE_ON_CLOSE);//使关闭键有用
    }

    private void addChessToChessboard(JPanel chessboard){
        //添加按钮至小方格
        for(int i=1;i<=9;i++) {
            chessboard.add(chessPanel[i]);
        }
    }

    private void initChessboard(){
        //使棋子按钮初始化为1-9
        for(int i=1;i<=9;i++){
            button[i]=new JButton(  ""+i);
            button[i].setSize(45,45);
            chessPanel[i]=new ChessPanel();
            chessPanel[i].setLayout(null);
            chessPanel[i].setBorder(BorderFactory.createLineBorder(Color.black, 1));
            chessPanel[i].add(button[i]);
        }
    }

    private void buttonListener(){
        //为棋子按钮添加监听器
        for(int i=1;i<=9;i++)
        {
            button[i].addActionListener(this);
        }
    }

    private void restartTheGame(){
        //重置游戏
        chessboard.removeAll();//必须于repaint和updateUI一起用不然要不啥都没有,要不没有改动
        //必须注意removll会清空布局
        chessboard.setLayout(new GridLayout(3,3));
        initChessboard();
        addChessToChessboard(chessboard);
        buttonListener();
        chessboard.updateUI();
        chessboard.repaint();

        judgement.setText("");
        gameOverFlag=false;
    }
    private boolean checkDogfall(char[] chess){
        //检查是否被填满,填满即为平局
        for(int i=1;i<chess.length;i++){
            if (chess[i]>='1'&&chess[i]<='9')
                return false;
        }
        return true;
    }

    private int checkWinner(int playerNow) {
        //检查当前游戏状态,-2表示没有决出胜负,-1表示平局。0表示O玩家胜利,1表示X玩家胜利
        char[] chess=new char[10];
        for(int i=1;i<=9;i++){
            chess[i]=button[i].getLabel().charAt(0);
        }
        if(     (chess[1]==chess[2]&&chess[2]==chess[3])||
                (chess[4]==chess[5]&&chess[5]==chess[6])||
                (chess[7]==chess[8]&&chess[8]==chess[9])||
                (chess[1]==chess[5]&&chess[5]==chess[9])||
                (chess[7]==chess[5]&&chess[5]==chess[3])||
                (chess[1]==chess[4]&&chess[4]==chess[7])||
                (chess[2]==chess[5]&&chess[5]==chess[8])||
                (chess[3]==chess[6]&&chess[6]==chess[9])){
            //判断当前玩家是否为赢家
            return playerNow;
        }
        else if(checkDogfall(chess))
            return -1;
        return -2;
    }

    public class ChessPanel extends JPanel{

        int paintCode=-1;//状态码,用来设置可见性及类型,-1表示不可见,0表示圈圈,1表示叉叉
        public void paint(Graphics g) {
            super.paint(g);
            if(paintCode==0){
                Graphics2D g_2D=(Graphics2D)g;
                g_2D.setStroke(new BasicStroke(6.0f));
                g.drawOval(43,43,23,23);//用笔画
                //Image oo = new ImageIcon("src/oo.png").getImage();
                //g.drawImage(oo,40,40,40,40,this);//用图画

            }
            else if(paintCode==1){
                Image xx = new ImageIcon("src/xx.png").getImage();
                g.drawImage(xx,43,43,25,25,this);//用图画
                //g.drawLine(50,50,60,60);
                //g.drawLine(50,60,60,50);//用笔画
            }
        }
    }


    @Override
    public void actionPerformed(ActionEvent actionEvent) {
        //对监听的事件进行响应
        int statueCode;
        int id;
        JButton buttonSource=(JButton)actionEvent.getSource();
        if(buttonSource==restart){
            //判断是否使restart键,如果是,重置游戏
            restartTheGame();
        }
        if (gameOverFlag==true) return;
        String buttonMark=buttonSource.getLabel();
        id=(int)(buttonMark.charAt(0)-'0');
        if(buttonMark.matches("[0-9]")){
            if(player==0){
                //绘制o
                buttonSource.setLabel("O");
                chessPanel[id].paintCode=0;//更改状态码
                repaint();//使所有chessPanel重绘
            }
            else{
                //绘制x
                buttonSource.setLabel("X");
                chessPanel[id].paintCode=1;
                repaint();
            }
            statueCode=checkWinner(player);
            if(statueCode==0){
                judgement.setText("Player O wins the game! ");
                gameOverFlag=true;
            }
            else if(statueCode==1){
                judgement.setText("Player X wins the game!");
                gameOverFlag=true;
            }
            else if(statueCode==-1){
                judgement.setText("The game a draw!");
            }
            player=(player+1)%2;//更换玩家
        }
    }

}

Postdata

En el espíritu de Internet, intercambiaré experiencias con usted. Espero que todos sigan escribiendo las suyas. No copie directamente la tarea para afectarme y afectarle a usted (¿cómo puede cambiar el nombre de la variable?), Las otras dos tareas esta vez son ambas Si es realmente bueno, ¡no hables de eso! Esta pregunta ha pasado mucho tiempo. La revisé durante mucho tiempo antes de darme cuenta de que no puedo hacer clic para dibujar una directamente. Encontré el origen de las coordenadas dibujadas durante mucho tiempo. Ahorre mucho tiempo Apoyame si te gusta? Si tiene alguna pregunta, por favor comente ~

SA
Publicado 2 artículos originales · elogiado 7 · visitas 373

Supongo que te gusta

Origin blog.csdn.net/weixin_44321098/article/details/105571615
Recomendado
Clasificación