井字游戏 java mouseListener

Tic tac toe java mouseListener

所以我一直在使用 MVC 开发 Tic Tac Toe 应用程序。我在视图页面中实现鼠标侦听器时遇到困难。我需要板的每个面板都可以点击。有人可以帮助我吗?

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;

            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);
            }
        }
    }
    public void addMouseListener(MouseListener ml){

    }
}

如果每个单元格都是它自己的 Shape(如 Rectangle)会更容易,但是,对于您当前的代码,您可以使用类似...

addMouseListener(new MouseAdapter() {
    @Override
    public void mouseClicked(MouseEvent e) {
        int w = getWidth();
        int h = getHeight();
        selectedCell = null;
        for (int col = 0; col < 3 && selectedCell == null; col++) {
            for (int row = 0; row < 3; row++) {
                int x = (w / 3) * col;
                int y = (h / 3) * row;
                Rectangle cell = new Rectangle(x, y, w / 3, h / 3);
                if (cell.contains(e.getPoint())) {
                    System.out.println("In");
                    selectedCell = cell;
                    repaint();
                    break;
                }
            }
        }
    }
});

现在,所有这一切都是循环遍历每一列和每一行,创建一个 Rectangle 并检查它是否包含 MouseEvent 点。如果它找到匹配项,它会将单元格的矩形分配给一个实例字段,我用它在您的绘画方法中突出显示。

这就是为什么将每个单元格作为 Rectangle 存储在 List

中会更容易

作为一个可运行的例子...

import java.awt.BasicStroke;
import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Dimension;
import java.awt.EventQueue;
import java.awt.FlowLayout;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.Rectangle;
import java.awt.Shape;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.awt.geom.Line2D;
import java.awt.geom.Rectangle2D;
import java.util.ArrayList;
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.UIManager;
import javax.swing.UnsupportedLookAndFeelException;

public class TicTacToeView extends JFrame {

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

    public static void main(String[] args) {
        EventQueue.invokeLater(new Runnable() {
            @Override
            public void run() {
                try {
                    UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
                } catch (ClassNotFoundException | InstantiationException | IllegalAccessException | UnsupportedLookAndFeelException ex) {
                    ex.printStackTrace();
                }

                JFrame frame = new TicTacToeView();
                frame.pack();
                frame.setLocationRelativeTo(null);
                frame.setVisible(true);
            }
        });
    }

    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);
    }

    private class Board extends JPanel {

        private Rectangle selectedCell = null;

        public Board() {
    addMouseListener(new MouseAdapter() {
        @Override
        public void mouseClicked(MouseEvent e) {
            int w = getWidth();
            int h = getHeight();
            selectedCell = null;
            for (int col = 0; col < 3 && selectedCell == null; col++) {
                for (int row = 0; row < 3; row++) {
                    int x = (w / 3) * col;
                    int y = (h / 3) * row;
                    Rectangle cell = new Rectangle(x, y, w / 3, h / 3);
                    if (cell.contains(e.getPoint())) {
                        System.out.println("In");
                        selectedCell = cell;
                        repaint();
                        break;
                    }
                }
            }
        }
    });
        }

        @Override
        public Dimension getPreferredSize() {
            return new Dimension(200, 200);
        }

        @Override
        public void paintComponent(Graphics g) {
            super.paintComponent(g);
            int w = getWidth();
            int h = getHeight();
            Graphics2D g2d = (Graphics2D) g;

            g2d.setPaint(Color.WHITE);
            g2d.fill(new Rectangle2D.Double(0, 0, w, h));

            if (selectedCell != null) {
                g2d.setColor(Color.BLUE);
                g2d.fill(selectedCell);
            }

            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);
            }
        }
    }

}

所以实际上我让它变得比实际更难。基本上,您只需将 MouseListener 从控制器(实现 MouseListener)传递到视图并将其添加到 JPanel,在本例中为 "board"。 所以在视图页面中,看起来像这样。

public void addMouseListener(MouseListener ml){

  this.board.addMouseListener(ml);

}

然后您将要为每个鼠标事件执行的操作放入控制器中。 希望有人觉得这有帮助。