java - 井字游戏 'X' 直到第二个 'O' 被点击后才出现

标签 java arrays tic-tac-toe

你好,我一直在用 Java 开发一个井字游戏应用程序并且我已经运行了,但我的问题是当我与 X 对战时,在我点击放置第一个 O 的位置​​后 X 不可见。 X在那里,但在我点击第二个点作为我的第二个 O 之前它是不可见的。我不明白为什么。我将在下面提供代码。

public class TicTacToeApp{
public static void main(String[] args){
    TicTacToeView view = new TicTacToeView();
    TicTacToeModel model = new TicTacToeModel();
    TicTacToeViewController controller = new TicTacToeViewController(view,model);
    view.setVisible(true);
}
}

public class TicTacToeModel {

double xpos,ypos,xr,yr;
char[][] position = {{' ',' ',' '},
                     {' ',' ',' '},
                     {' ',' ',' '}};

/**
 * Turns row, col into the center of the cells of any screen of resolution h       by w.
 * This is ideal for the view.
 */
public void computePos(int row, int col, int h, int w){
    xpos=(col+0.5)*w/3.0;
    ypos=(row+0.5)*h/3.0;
    xr=w/8.0;
    yr=h/8.0;
}

/**
 * returns true if the cell at xpos ypos is blank
* Validates that xpos and ypos are within range.
 */
public boolean isEmpty(int xpos, int ypos){
    if(position[xpos][ypos]==' ')
  {
  return true;
  }
  return false;
}

/*
 * Places an O at position xpos and ypos. No additional validation.
 */
public void placeO(int xpos, int ypos) {
    position[xpos][ypos]='O';
}

/**
 * Really dumb strategy for the computer to play tic-tac-toe.
* Places an X in the next available space from left to right and
* top to bottom.
 */
public int putX(){
    for(int i=0; i<3;i++)
        for(int j = 0;j<3;j++) {
            if(position[i][j]==' ') {
                position[i][j]='X';
                return 0;
            }
        }
    return -1; //some error occurred. This is odd. No cells were free.
}


    public void printBoard(){
    for(int i=0;i<3;i++)
        System.out.println(position[i][0]+"|"+position[i][1]+"|"+position[i]   [2]);
    }
  }

  import java.awt.*;
  import javax.swing.*;
  import java.awt.event.*;
  import java.awt.geom.*;
  import javax.swing.*;
  import javax.swing.event.*;
  import java.util.ArrayList;

public class TicTacToeView extends JFrame{

private JButton oButton, xButton;
public JPanel board;
public ArrayList<Shape> shapes;

public TicTacToeView(){
    shapes = new ArrayList<Shape>();
    JPanel topPanel=new JPanel();
    topPanel.setLayout(new FlowLayout());
    add(topPanel, BorderLayout.NORTH);
    add(board=new Board(), BorderLayout.CENTER);
    setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
    setSize(500, 500);
}


private class Board extends JPanel {
    public void paintComponent(Graphics g) {
        super.paintComponent(g);
        int w=getWidth();
        int h=getHeight();
        Graphics2D g2d = (Graphics2D) g;

        // Draw the grid
        g2d.setPaint(Color.WHITE);
        g2d.fill(new Rectangle2D.Double(0, 0, w, h));
        g2d.setPaint(Color.BLACK);
        g2d.setStroke(new BasicStroke(4));
        g2d.draw(new Line2D.Double(0, h/3, w, h/3));
        g2d.draw(new Line2D.Double(0, h*2/3, w, h*2/3));
        g2d.draw(new Line2D.Double(w/3, 0, w/3, h));
        g2d.draw(new Line2D.Double(w*2/3, 0, w*2/3, h));
        //draw circles and xs by visiting elements in the array List.
        for(Shape shape : shapes){
            g2d.setPaint(Color.BLUE);
            g2d.draw(shape);
        }
    }
  }

 /*
 * Adds the mouse listener passed to Board.
 */
    public void addMouseListener(MouseListener ml){
    board.addMouseListener(ml);
}


  public static void main(String[] args) {
    TicTacToeView ttv = new TicTacToeView();
    ttv.setVisible(true);

   }
 }



import java.awt.event.*;
import java.awt.geom.*;
import java.awt.Graphics2D;
import java.awt.Color;
import javax.swing.JOptionPane;

/*
* This is the controller for the tic-tac-toe.
* Notice that it implements a MouseListener that 
* can be attached to a graphical component and therefore
* complies with the interface MouseListener.
*/
public class TicTacToeViewController implements MouseListener{

TicTacToeView view;
TicTacToeModel model;
Color oColor=Color.BLUE, xColor=Color.RED;

    public TicTacToeViewController(TicTacToeView view, TicTacToeModel model) { 
    this.view = view;
    this.model = model;
  // do this
  view.addMouseListener(this);
}

/** Ask the model what's the next move.
 */
    public void play(int ypos, int xpos) {
        if (model.isEmpty(xpos,ypos)) {// changed x and y because it lands   in    the wrong position.
        // TO DO: Put the O in xpos ypos using the model.
     model.placeO(xpos,ypos);
     // TO DO: Put the X using the model.
     drawBoard();
     view.repaint();
     model.putX();


    }
    // TO DO: add the conditions inside the () of the if's that determine  the   winner.
        if( didWin('X') ) 
        JOptionPane.showMessageDialog(null,"X Wins","Winner",    JOptionPane.INFORMATION_MESSAGE);
    else if ( didWin('O')  )
        JOptionPane.showMessageDialog(null,"O    Wins","Winner",JOptionPane.INFORMATION_MESSAGE);
}


/** Control the drawing of O and X.
 * This looks at the model to see where there are Xs and Os and draws two     diagonal
 * lines or a circle (an Ellipse, actually) in the positions given.
 */
public void drawBoard() {
    Graphics2D g2d = (Graphics2D)view.board.getGraphics();

    for (int i=0; i<3; i++) 
        for(int j=0; j<3;j++) {
               model.computePos(i,j,view.board.getHeight(),view.board.getWidth());
            double xpos = model.xpos;
            double xr = model.xr;
            double ypos = model.ypos;
            double yr = model.yr;
            // TODO: Complete the expressions within the if statements as    follows:
            // if the array that represents the board has a O in position i, j... else,
            // if it has an X...
            if ( model.position[i][j]=='O' ) {
                // Adds a circle (which is an Ellipse of sorts) to the list of elements to draw
           view.shapes.add(new Ellipse2D.Double(xpos-xr, ypos-yr, xr*2, yr*2));
            }
            if  (model.position[i][j]=='X' ) {
          // Adds two lines crossed (the X) to the list of shapes to draw.
              view.shapes.add(new Line2D.Double(xpos-xr, ypos-yr, xpos+xr,   ypos+yr));
              view.shapes.add(new Line2D.Double(xpos-xr, ypos+yr, xpos+xr, ypos-yr));
            }
            System.out.println("Coords: xpos:"+xpos+", ypos:"+ypos+", xr"+xr+", yr"+yr);
    }
}

/** MouseListener event
 * Converts the coordinates of the mouse into the corresponding row and   column of the cell
 */
  public void mouseClicked(MouseEvent e) {
  int xpos=e.getX()*3/view.getWidth();
  int ypos=e.getY()*3/view.getHeight();
  //System.out.println("Play "+xpos+","+ypos);
  play(xpos,ypos);
}

/**
 * Check wheather player has won. Checks happen against the model.
 */
  public boolean didWin(char player) {
    // TO DO
  int count = 0;
  int count2 = 0;

  for(int i = 0; i < 3; i++)
  {

     for(int j = 0; j<3; j++)
     {

        if(model.position[i][j]== player)
        {
        count++;
        if(count == 3 )
        return true;
        }
    }
  count = 0;
   }
  for(int n = 0; n < 3; n++)
     {
        for(int n2=0; n2 <3; n2++)
           {
              if(model.position[n][n2]==player)
                 {
                 count2++;
                 if(count2 == 3)// if doesnt work change back to 2
                 return true;
                 }
           } count2=0;
 }
     if(model.position[0][0]==player && model.position[1][1]==player &&   model.position[2][2]==player)
    return true;

    if(model.position[0][2]==player && model.position[1][1]==player && model.position[2][0]==player)
    return true;






  return false;
  }




    /** Ignore other mouse events*/
    public void mousePressed(MouseEvent e) {}
    public void mouseReleased(MouseEvent e) {}
    public void mouseEntered(MouseEvent e) {}
    public void mouseExited(MouseEvent e) {}
}

最佳答案

在 TicTacToe Controller 类中的 play 方法中,您应该在 model.putX() 方法之后调用 drawBoard() 和 view.repaint()

model.putX();
drawBoard();
view.repaint();

完整方法

 public void play(int ypos, int xpos) {
        if (model.isEmpty(xpos,ypos)) {// changed x and y because it lands   in    the wrong position.
        // TO DO: Put the O in xpos ypos using the model.
     model.placeO(xpos,ypos);
     // TO DO: Put the X using the model.
     drawBoard();
     view.repaint();
     model.putX();
     drawBoard();
     view.repaint();



    }
    // TO DO: add the conditions inside the () of the if's that determine  the   winner.
        if( didWin('X') ) 
        JOptionPane.showMessageDialog(null,"X Wins","Winner",    JOptionPane.INFORMATION_MESSAGE);
    else if ( didWin('O')  )
        JOptionPane.showMessageDialog(null,"O    Wins","Winner",JOptionPane.INFORMATION_MESSAGE);
}

关于java - 井字游戏 'X' 直到第二个 'O' 被点击后才出现,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/34831377/

相关文章:

python - 如何使用Python根据ascii顺序移动字符

ruby - Minimax 算法 Ruby Tic Tac Toe

java - java - 如何在Java中的一段时间后停止执行?

java - Camel 响应从 bean 返回到 ActiveMQ 队列

java - 从排序到原始数组的索引映射

c - 短数组的最佳排序函数

java - Java 中的两人井字游戏 - 如何防止非整数输入

c++ - 井字游戏帮助

java - 如何找出运行时间?

java - 将 SQL(不是 JPQL)映射到一组简单的 Java 对象?