【问题标题】:Java Minesweeper GUIJava 扫雷 GUI
【发布时间】:2014-03-28 13:05:15
【问题描述】:

我必须制作一个扫雷 GUI,但我不知道如何让每个按钮都有自己的 mouseAdapter。当我单击一个按钮时,它会更改屏幕上的每个按钮,而不仅仅是我单击的那个。我可以指点一下如何做到这一点吗?

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

public class MinePanel extends JPanel 
{
    private final int ROWS = 10;
    private final int COLUMNS = 10;
    private int numOfMines;
    private double probability;
    private JLabel statusBar;
    private int minesLeft;
    private JButton Minefield[][];
    private boolean hasMine = false;
    private int curRow = 0;
    private int curCol = 0;
    private JButton cell;

    public MinePanel() 
    {
        setLayout(new GridLayout(10, 10));
        Minefield = new JButton[ROWS][COLUMNS];
        //menuStuff();
        buildButtonField();
    }

    //I will eventually want to create a menu, but it's extra credit so I'm going to
    //wait until I have a working program.
    public JMenuBar menuStuff()
    {
        JMenuBar menuBar = new JMenuBar();
        //add(menuBar);
        JMenu file = new JMenu("File");
        menuBar.add(file);
        JMenu edit = new JMenu("Edit");
        menuBar.add(edit);
        return menuBar;
    }

    //Adds one to the total number of mines.
    public void addMine()
    {
        numOfMines++;
    }

    //Removes one from the total number of mines.
    public void removeMine()
    {
        numOfMines--;
    }

    //Assigns a JButton the value of true or false, which represents whether or not it
    //it is a mine. Is this the correct way to do this?
    public boolean setMines(JButton button)
    {
        probability  = Math.random()*100;
        if(probability >= 80)
        {
            hasMine = true;
            addMine();
        }
        else
        {
            hasMine = false;
        }
        return hasMine;
    }

    //This is supposed to change the JButton that is clicked on to either a T
    //or an F, eventually this will reveal what the value of the button is
    //or place a flag down. I'm guessing I shouldn't have used a for loop, but I don't 
    //know how else to do it.
    private class MouseHandler extends MouseAdapter
    {
        public void mouseClicked(MouseEvent e)
        {
            for(int r=0; r<ROWS; r++)
            {
                for(int c=0; c<COLUMNS; c++)
                {
                    if(e.getButton() == 1)
                    {
                        Minefield[r][c].setText("T");
                    }
                    else if(e.getButton() == 3)
                    {
                        Minefield[r][c].setText("F");
                    }
                }
            }
        }
    }

    //This builds the "Minefield" with a ROWS*COLUMNS amount of buttons.
    //It works fine but I'm open to suggestions on a better way to do this.
    public void buildButtonField()
    {
        for(int r = 0; r < ROWS; r++)
        {
            curRow++;
            for(int c = 0; c < COLUMNS; c++)
            {
                Minefield[r][c] = new JButton((r+1) + ", " + (c+1));

                setMines(Minefield[r][c]);

                Minefield[r][c].addMouseListener(new MouseHandler());

                add(Minefield[r][c]);
                curCol++;
            }
        }
    }
}

提前感谢你们提供的任何帮助!我要去上课了,所以我可能需要一点时间来回复。

【问题讨论】:

    标签: java swing user-interface


    【解决方案1】:

    当鼠标事件发生时,您将遍历网格中的每个单元格。首先,去掉 MouseHandler 中的循环:

    private class MouseHandler extends MouseAdapter
    {
        public void mouseClicked(MouseEvent e)
        {
            if(e.getButton() == 1)
            {
                Minefield[r][c].setText("T");
            }
            else if(e.getButton() == 3)
            {
                Minefield[r][c].setText("F");
            }
        }
    }
    

    然后,您可以将两个参数添加到 MouseHandler 构造函数中的行和列,以便每个鼠标处理程序都知道它负责哪个单元格。

    public class MouseHandler extends MouseAdapter
    {
        public int r, c; // instance variables
        public MouseHandler(int r, int c)
        {
            this.r = r;
            this.c = c;
        }
    
        ... // above code here
    }
    

    创建对象可能如下所示:Minefield[r][c].addMouseListener(new MouseHandler(r,c));

    您也可以在引发事件时找到鼠标坐标以手动确定单击了哪个单元格,但这很麻烦。

    【讨论】:

    • +1,虽然我建议使用rowcolumn 而不是rc。单字母变量名永远不会结束。
    • 当一个方法接受两个名为rc 的参数时,很明显,至少在我的编码方法中,它们代表行和列。与xy 相同。它还可以节省我的打字时间,并且在我犯错并且必须删除/重新输入内容时非常方便。不同的人有不同的笔画。
    • 只要您亲自维护代码,它可能会起作用(也许)。但是,当您与团队一起开发时,个人约定并不适用。 After all...
    猜你喜欢
    • 1970-01-01
    • 2015-05-15
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-06-10
    • 2014-08-27
    • 1970-01-01
    • 2023-03-31
    相关资源
    最近更新 更多