随风而动,随遇而安......
Java实现扫雷小游戏三
05/26
本文最后更新于
2022年08月13日,已超过
849天没有更新。如果文章内容或图片资源失效,请留言反馈,我会及时处理,谢谢!
接下来是完成菜单栏的功能
游戏菜单
添加菜单监听器(com.panel/BombJMenuBar.java)
在init()方法中插入
// 开局事件处理
menuItemStart.addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent e) {
mainframe.reStartGame();
}
});
// 添加事件监听器
MenuListener listener = new MenuListener(mainframe);
menuItemStart.addActionListener(listener);
menuItemLow.addActionListener(listener);
menuItemMid.addActionListener(listener);
menuItemHigh.addActionListener(listener);
menuItemOrder.addActionListener(listener);
menuHeroLow.addActionListener(new ActionListener(){
public void actionPerformed(ActionEvent e) {
new Hero(mainframe);
}});
menuHeroMid.addActionListener(new ActionListener(){
public void actionPerformed(ActionEvent e) {
new Hero1(mainframe);
}});
menuHeroHigh.addActionListener(new ActionListener(){
public void actionPerformed(ActionEvent e) {
new Hero2(mainframe);
}});
menuItemAbout.addActionListener(listener);
// 后门外挂方便测试
menuItemHole.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
}
});
menuItemExit.addActionListener(new ActionListener() { //加一个系统退出的处理监听
public void actionPerformed(ActionEvent e) {
System.exit(0);
}
});
编写等级菜单监听类(com.listener/MenuListener)
// 等级菜单监听器
public class MenuListener implements ActionListener {
JMenuItem jMenuItem;
JTextField jTextField=new JTextField();
MainFrame mainframe;
public MenuListener(MainFrame mainframe){
this.mainframe = mainframe;
}
public void actionPerformed(ActionEvent e) {
if(e.getActionCommand().equals("开局(N)")){
this.mainframe.reStartGame();
}
if(e.getActionCommand().equals("初级(B)")){
Tools.rows = 9;
Tools.cols = 9;
Tools.allcount = 10;
Tools.currentLevel = Tools.LOWER_LEVEL;
this.mainframe.reStartGame();
}
if(e.getActionCommand().equals("中级(I)")){
Tools.rows = 16;
Tools.cols = 16;
Tools.allcount = 40;
Tools.currentLevel = Tools.MIDDLE_LEVEL;
this.mainframe.reStartGame();
}
if(e.getActionCommand().equals("高级(E)")){
Tools.rows = 16;
Tools.cols = 30;
Tools.allcount = 99;
Tools.currentLevel = Tools.HEIGHT_LEVEL;
this.mainframe.reStartGame();
}
if(e.getActionCommand().equals("自定义(C)")){
new UserDefined(mainframe);
}
if(e.getActionCommand().equals("关于扫雷(A)")){
new About(mainframe);
}
}
}
注意:在雷区BombJPanel.java中之前是把行和列写成固定的,实现初级、中级、高级时要进行下述修改:
// MineLabel[][] labels = new MineLabel[9][9];
MineLabel[][] labels = new MineLabel[Tools.rows][Tools.cols];
运行效果:
自定义菜单项(com.dialog/UserDefined.java)
需求分析:出现弹窗界面,数据校验不能超过三位,只能为数字。
通过继承JDialog实现用户自定义对话框
public class UserDefined extends JDialog {
// 自定义
private static final long serialVersionUID = 1L;
private JLabel jLabelHigh = new JLabel("高度: ");
private JLabel jLabelWide = new JLabel("宽度: ");
private JLabel jLabelBomb = new JLabel("雷数: ");
private JLabel jLabelMessage = new JLabel(" ");
private JTextField jTextFieldHigh;
private JTextField jTextFieldWide;
private JTextField jTextFieldBomb;
private JPanel panel;
private JButton buttonSure;
private JButton buttonCancer;
MainFrame mainFrame;
public UserDefined(final MainFrame mainFrame) {
super(mainFrame);
this.mainFrame = mainFrame;
this.setIconImage(Tools.getImageIcon().getImage());
jLabelMessage.setFont(new Font("楷书", Font.PLAIN, 12));
jLabelMessage.setForeground(Color.red);
this.setTitle("自定义雷区");
this.add(getPanel());
this.add(jLabelMessage, BorderLayout.NORTH);
this.setSize(new Dimension(200, 150));
this.setDefaultCloseOperation(JDialog.DISPOSE_ON_CLOSE);
this.setLocationRelativeTo(null);
this.setResizable(false);
this.addWindowListener(new WindowAdapter() {
@Override
public void windowDeactivated(WindowEvent e) {
mainFrame.reStartGame();
}
});
this.setModal(true);
this.setVisible(true);
}
public JPanel getPanel() {
JPanel jPanel = new JPanel();
Border border1 = BorderFactory.createEmptyBorder(5, 20, 5, 5);
panel = new JPanel();
panel.setLayout(new GridLayout(1, 2));
Box boxHigh = Box.createHorizontalBox();
jTextFieldHigh = new JTextField(Tools.rows + "");
jTextFieldHigh.setPreferredSize(new Dimension(30, 20));
jTextFieldHigh.addKeyListener(new KeyListener() {
@Override
public void keyReleased(KeyEvent e) {
String text = jTextFieldHigh.getText();
Pattern pattern = Pattern.compile("^[0-9]{1,3}$");
Matcher matcher = pattern.matcher(text);
if (!matcher.matches()) {
jLabelMessage.setText("请输入数字,不能超过三位");
if (text.length() > 3) {
jTextFieldHigh.setText(text.substring(0, 3));
}
}
}
@Override
public void keyTyped(KeyEvent e) {
char ch = e.getKeyChar();
if ((ch < '0') || (ch > '9')) {
jLabelMessage.setText("请输入数字,不能超过三位");
e.setKeyChar((char) 8);
} else {
jLabelMessage.setText(" ");
}
}
@Override
public void keyPressed(KeyEvent e) {
}
});
boxHigh.add(jLabelHigh);
boxHigh.add(jTextFieldHigh);
Box boxWide = Box.createHorizontalBox();
jTextFieldWide = new JTextField(Tools.cols + "");
jTextFieldWide.setPreferredSize(new Dimension(30, 20));
jTextFieldWide.addKeyListener(new KeyListener() {
@Override
public void keyReleased(KeyEvent e) {
String text = jTextFieldWide.getText();
Pattern pattern = Pattern.compile("^[0-9]{1,3}$");
Matcher matcher = pattern.matcher(text);
if (!matcher.matches()) {
jLabelMessage.setText("请输入数字,不能超过三位");
if (text.length() > 3) {
jTextFieldWide.setText(text.substring(0, 3));
}
}
}
@Override
public void keyTyped(KeyEvent e) {
char ch = e.getKeyChar();
if ((ch < '0') || (ch > '9')) {
jLabelMessage.setText("请输入数字,不能超过三位");
e.setKeyChar((char) 8);
} else {
jLabelMessage.setText(" ");
}
}
@Override
public void keyPressed(KeyEvent e) {
}
});
boxWide.add(jLabelWide);
boxWide.add(jTextFieldWide);
Box boxBomb = Box.createHorizontalBox();
jTextFieldBomb = new JTextField(Tools.bombCount + "");
jTextFieldBomb.setPreferredSize(new Dimension(30, 20));
jTextFieldBomb.addKeyListener(new KeyListener() {
@Override
public void keyReleased(KeyEvent e) {
String text = jTextFieldBomb.getText();
Pattern pattern = Pattern.compile("^[0-9]{1,3}$");
Matcher matcher = pattern.matcher(text);
if (!matcher.matches()) {
jLabelMessage.setText("请输入数字,不能超过三位");
if (text.length() > 3) {
jTextFieldBomb.setText(text.substring(0, 3));
}
}
}
@Override
public void keyTyped(KeyEvent e) {
char ch = e.getKeyChar();
if ((ch < '0') || (ch > '9')) {
jLabelMessage.setText("请输入数字,不能超过三位");
e.setKeyChar((char) 8);
} else {
jLabelMessage.setText(" ");
}
}
@Override
public void keyPressed(KeyEvent e) {
}
});
boxBomb.add(jLabelBomb);
boxBomb.add(jTextFieldBomb);
Box boxS = new Box(BoxLayout.Y_AXIS);
boxS.add(boxHigh);
boxS.add(Box.createVerticalStrut(8));
boxS.add(boxWide);
boxS.add(Box.createVerticalStrut(8));
boxS.add(boxBomb);
boxS.add(Box.createVerticalStrut(8));
boxS.setBorder(border1);
Box boxT = new Box(BoxLayout.Y_AXIS);
buttonSure = new JButton("确定");
UserDefinedListener definedListener = new UserDefinedListener(this, mainFrame);
buttonSure.setPreferredSize(new Dimension(70, 30));
buttonSure.setMargin(new Insets(0, 2, 0, 2));
buttonSure.addActionListener(definedListener);
buttonCancer = new JButton("取消");
buttonCancer.setMargin(new Insets(0, 2, 0, 2));
buttonCancer.setSize(new Dimension(70, 30));
buttonCancer.addActionListener(definedListener);
boxT.add(buttonSure);
boxT.add(Box.createVerticalStrut(25));
boxT.add(buttonCancer);
boxT.setBorder(border1);
panel.add(boxS);
panel.add(boxT);
Border border = BorderFactory.createEmptyBorder(3, 15, 5, 15);
jPanel.setBorder(border);
jPanel.add(panel);
return jPanel;
}
}
自定义窗口监听器(com.listener/UserDefinedListener.java)
public class UserDefinedListener implements ActionListener {
UserDefined userDefined;
MainFrame mainFrame;
public UserDefinedListener(UserDefined userDefined, MainFrame mainFrame) {
this.mainFrame = mainFrame;
this.userDefined = userDefined;
}
@Override
public void actionPerformed(ActionEvent e) {
if (e.getSource() == userDefined.getButtonCancer()) {
userDefined.dispose();
mainFrame.reStartGame();
} else if (e.getSource() == userDefined.getButtonSure()) {
String highT = userDefined.getjTextFieldHigh().getText();
Pattern pattern = Pattern.compile("^[0-9]{1,3}$");
Matcher matcher = pattern.matcher(highT);
int row = 0;
if (!matcher.matches()) {
userDefined.getjLabelMessage()
.setText("输入的行数范围应在9-30之间");
return;
} else {
row = Integer.parseInt(highT);
if (row < 9 || row > 30) {
userDefined.getjLabelMessage().setText(
"输入的行数范围应在9-30之间");
return;
}
}
String colT = userDefined.getjTextFieldWide().getText();
int col = 0;
try {
col = Integer.parseInt(colT);
if (col < 9 || col > 30) {
userDefined.getjLabelMessage().setText(
"输入的列数范围应在9-30之间");
return;
}
} catch (Exception e2) {
userDefined.getjLabelMessage().setText(
"列数应该为数字且范围应在9-30之间");
return;
}
String mineT = userDefined.getjTextFieldBomb().getText();
int mine = 0;
try {
mine = Integer.parseInt(mineT);
if (mine < 10) {
mine = 10;
} else {
mine = Math.min(mine, Tools.rows * Tools.cols * 4 / 5);
}
} catch (Exception e3) {
userDefined.getjLabelMessage().setText("雷数应该为数字");
return;
}
userDefined.dispose();
Tools.rows = row;
Tools.cols = col;
Tools.allcount = mine;
mainFrame.reStartGame();
}
}
}
运行效果:
英雄榜
弹出胜利窗口(com.dialog/Win.java)
public class Win extends JDialog {
MainFrame mainframe;
private JTextField text;
TreeSet<Own> LOWER = new TreeSet<Own>();
TreeSet<Own> MIDDLE = new TreeSet<Own>();
TreeSet<Own> HEIGHT = new TreeSet<Own>();
public Win(MainFrame mainframe){
this.mainframe = mainframe;
this.setIconImage(Tools.getImageIcon().getImage());
this.setTitle("扫雷成功");
this.setLocationRelativeTo(null);
this.setSize(200, 150);
this.init();
this.setVisible(true);
}
private void init() {
// 存放记入
JPanel panel = new JPanel();
panel.setLayout(new GridLayout(4,1));
JLabel label = new JLabel("好厉害!请留下你的大名");
panel.add(label);
text = new JTextField();
panel.add(text);
// times = mainframe.getTimer().getTimes();
JLabel labTime = new JLabel("你所使用的时间:"+Tools.timecount);
panel.add(labTime);
JButton butys = new JButton("保存");
butys.addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent e) {
if(Tools.currentLevel.equals("初级")){
if(Tools.time1>=Tools.timecount && Tools.time2>=Tools.timecount && Tools.time3>=Tools.timecount){
Tools.time3 = Tools.time2;
Tools.name3 = Tools.name2;
Tools.time2 = Tools.time1;
Tools.name2 = Tools.name1;
Tools.time1 = Tools.timecount;
Tools.name1=text.getText();
}else if(Tools.time2>=Tools.timecount && Tools.time3>=Tools.timecount && Tools.time1<=Tools.timecount){
Tools.time3 = Tools.time2;
Tools.name3 = Tools.name2;
Tools.time2 = Tools.timecount;
Tools.name2=text.getText();
}else if(Tools.time3>=Tools.timecount && Tools.time1<=Tools.timecount && Tools.time2<=Tools.timecount){
Tools.time3 = Tools.timecount;
Tools.name3=text.getText();
}
}
if(Tools.currentLevel.equals("中级")){
if(Tools.time01>=Tools.timecount && Tools.time02>=Tools.timecount && Tools.time03>=Tools.timecount){
Tools.time03 = Tools.time02;
Tools.name03 = Tools.name02;
Tools.time02 = Tools.time01;
Tools.name02 = Tools.name01;
Tools.time01 = Tools.timecount;
Tools.name01=text.getText();
}else if(Tools.time02>=Tools.timecount && Tools.time03>=Tools.timecount && Tools.time01<=Tools.timecount){
Tools.time03 = Tools.time02;
Tools.name03 = Tools.name02;
Tools.time02 = Tools.timecount;
Tools.name02=text.getText();
}else if(Tools.time03>=Tools.timecount && Tools.time01<=Tools.timecount && Tools.time02<=Tools.timecount){
Tools.time03 = Tools.timecount;
Tools.name03=text.getText();
}
}
if(Tools.currentLevel.equals("高级")){
if(Tools.time001>=Tools.timecount && Tools.time002>=Tools.timecount && Tools.time003>=Tools.timecount){
Tools.time003 = Tools.time002;
Tools.name003 = Tools.name002;
Tools.time002 = Tools.time001;
Tools.name002 = Tools.name001;
Tools.time001 = Tools.timecount;
Tools.name001=text.getText();
}else if(Tools.time002>=Tools.timecount && Tools.time003>=Tools.timecount && Tools.time001<=Tools.timecount){
Tools.time003 = Tools.time002;
Tools.name003 = Tools.name002;
Tools.time002 = Tools.timecount;
Tools.name002=text.getText();
}else if(Tools.time003>=Tools.timecount && Tools.time001<=Tools.timecount && Tools.time002<=Tools.timecount){
Tools.time003 = Tools.timecount;
Tools.name003=text.getText();
}
}
Win.this.dispose();
}
});
panel.add(butys);
this.add(panel);
}
public JTextField getText() {
return text;
}
运行效果:
英雄榜类(com.dialog/Hero.java)
英雄榜分为初级、中级、高级英雄榜;每个英雄榜类逻辑是一样的,通过胜利窗口的事件监听器判断是哪个等级的英雄榜数据,然后写入临时变量中保存。以此类推编写中级、高级英雄榜Hero1,Hero2,当然也可以只写一个类,不过需要多加一些判断条件。
public class Hero extends JDialog{
private JLabel jlabel1;
private JLabel jlabel2;
private JLabel jlabel3;
private JLabel jlabel4;
private JLabel jlabel5;
private JLabel jlabel6;
private JLabel time1;
private JLabel time2;
private JLabel time3;
private JLabel name1;
private JLabel name2;
private JLabel name3;
private JButton jbutton1;
private JButton jbutton2;
private MainFrame mainframe;
private JPanel jpanel;
public Hero(MainFrame mainframe) {
this.mainframe=mainframe;
this.setIconImage(Tools.getImageIcon().getImage());
this.setTitle("初级英雄榜");
this.setVisible(true);
this.setSize(220,220);
this.setResizable(false);
this.setLocationRelativeTo(mainframe);
this.setDefaultCloseOperation(JDialog.DISPOSE_ON_CLOSE);
init();
}
public JLabel getJLabel1() {
return jlabel1;
}
public void setJLabel1(JLabel jlabel1) {
this.jlabel1 = jlabel1;
}
public JLabel getJLabel2() {
return jlabel2;
}
public void setJLabel2(JLabel jlabel2) {
this.jlabel2 = jlabel2;
}
public JLabel getJLabel3() {
return jlabel3;
}
public void setJLabel3(JLabel jlabel3) {
this.jlabel3 = jlabel3;
}
public JLabel getJLabel4() {
return jlabel4;
}
public void setJLabel4(JLabel jlabel4) {
this.jlabel4 = jlabel4;
}
public JLabel getJLabel5() {
return jlabel5;
}
public void setJLabel5(JLabel jlabel5) {
this.jlabel5 = jlabel5;
}
public JLabel getJLabel6() {
return jlabel6;
}
public void setJLabel6(JLabel jlabel6) {
this.jlabel6 = jlabel6;
}
public JLabel getTime1() {
return time1;
}
public void setTime1(JLabel time1) {
this.time1 = time1;
}
public JLabel getTime2() {
return time2;
}
public void setTime2(JLabel time2) {
this.time2 = time2;
}
public JLabel getTime3() {
return time3;
}
public void setTime3(JLabel time3) {
this.time3 = time3;
}
public JLabel getName1() {
return name1;
}
public void setName1(JLabel name1) {
this.name1 = name1;
}
public JLabel getName2() {
return name2;
}
public void setName2(JLabel name2) {
this.name2 = name2;
}
public JLabel getName3() {
return name3;
}
public void setName3(JLabel name3) {
this.name3 = name3;
}
public void init(){
HeroListener heroListener = new HeroListener();
jlabel1 = new JLabel(" 名次");
jlabel2 = new JLabel(" 成绩");
jlabel3 = new JLabel(" 玩家");
jlabel4 = new JLabel(" 第一名:");
jlabel5 = new JLabel(" 第二名:");
jlabel6 = new JLabel(" 第三名:");
time1 = new JLabel(""+Tools.time1);
time2 = new JLabel(""+Tools.time2);
time3 = new JLabel(""+Tools.time3);
name1 = new JLabel(" "+Tools.name1);
name2 = new JLabel(" "+Tools.name2);
name3 = new JLabel(" "+Tools.name3);
jbutton1=new JButton("确定");
jbutton1.addActionListener(heroListener);
jbutton2=new JButton("重新设置");
jbutton2.addActionListener(heroListener);
jpanel=new JPanel();
Box box1 = Box.createVerticalBox();
box1.add(jlabel1);
box1.add(Box.createVerticalStrut(10));
box1.add(jlabel4);
box1.add(Box.createVerticalStrut(10));
box1.add(jlabel5);
box1.add(Box.createVerticalStrut(10));
box1.add(jlabel6);
Box box2 = Box.createVerticalBox();
box2.add(jlabel2);
box2.add(Box.createVerticalStrut(10));
box2.add(time1);
box2.add(Box.createVerticalStrut(10));
box2.add(time2);
box2.add(Box.createVerticalStrut(10));
box2.add(time3);
Box box3 = Box.createVerticalBox();
box3.add(jlabel3);
box3.add(Box.createVerticalStrut(10));
box3.add(name1);
box3.add(Box.createVerticalStrut(10));
box3.add(name2);
box3.add(Box.createVerticalStrut(10));
box3.add(name3);
Box box4 = Box.createHorizontalBox();
box4.add(jbutton1);
box4.add(Box.createHorizontalStrut(20));
box4.add(jbutton2);
Box box5 = Box.createHorizontalBox();
box5.add(box1);
box5.add(box2);
box5.add(box3);
Box box6 = Box.createVerticalBox();
box6.add(Box.createVerticalStrut(20));
box6.add(box5);
box6.add(Box.createVerticalStrut(20));
box6.add(box4);
jpanel.add(box6);
this.add(jpanel);
}
class HeroListener implements ActionListener{
public void actionPerformed(ActionEvent e){
String command = e.getActionCommand();
if(command.equals("确定")){
dispose();
}
else {
Tools.time1 = 999;
Tools.time2 = 999;
Tools.time3 = 999;
Tools.name1 = " 匿名";
Tools.name2 = " 匿名";
Tools.name3 = " 匿名";
time1.setText(""+Tools.time1);
name1.setText(Tools.name1);
time2.setText(""+Tools.time2);
name2.setText(Tools.name2);
time3.setText(""+Tools.time3);
name3.setText(Tools.name3);
//dispose();
}
}
}
}
运行效果:
帮助菜单
关于扫雷(com.dialog/About.java)
可以根据自己的需求添加想要的窗口内容。
public class About extends JDialog {
MainFrame mainframe;
public About(MainFrame mainframe){
this.setIconImage(Tools.getImageIcon().getImage());
this.mainframe = mainframe;
this.setTitle("关于扫雷");
this.setLocationRelativeTo(null);
this.setResizable(false);
this.setSize(200, 130);
this.init();
this.setVisible(true);
}
private void init() {
Box box = Box.createVerticalBox();
JPanel jpanel = new JPanel();
JLabel jlabel = new JLabel("扫雷 ©2022");
JLabel jlabel1 = new JLabel("作者:XG.孤梦");
JLabel jlabel2 = new JLabel("我的博客:https://www.xggm.top");
box.add(jlabel);
box.add(Box.createVerticalStrut(10));
box.add(jlabel1);
box.add(Box.createVerticalStrut(10));
box.add(jlabel2);
jpanel.add(box);
this.add(jpanel);
}
}
运行效果:
外挂后门(com.listener/MenuListener.java)
可以在布雷完成之后就编写这个方法,目的为了方便测试,节省时间,点击外挂,就会将是雷的小方格图片替换成其他图片,比如弄成中间有个小黑点的小方格
// 后门外挂方便测试
menuItemHole.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
if (Tools.isStart) {
Tools.isHole = true;
// 判断每一个雷块是否是雷
for (MineLabel[] mineLabel : BombJMenuBar.this.mainframe
.getBombJPanel().getLabels()) {
for (MineLabel m : mineLabel) {
if (m.isMineTag()) {
m.setIcon(Tools.hole);
}
}
}
}
}
});
运行效果:
最后一个Java实现扫雷项目就这样完成了。