扫雷案例练习
1.启动类
public class StartApp {
public static void main(String[] args) {
new UI();
}
}
2.界面类
import java.awt.Color;
import java.awt.Font;
import java.awt.GridLayout;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;
import javax.swing.ImageIcon;
import javax.swing.Icon;
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JList;
import javax.swing.JOptionPane;
import javax.swing.JPanel;
import javax.swing.JTextArea;
public class UI {
private int[][] corrdinatesUI ;
public static JPanel pane;
public static JButton[][] listBtn ;
private JFrame mainWindow ;
public static int numMine;
private int numRow;
private Color bgColor = new Color(238,233,233);
private Color color;
private JList<String> selList;
private JFrame selFrame;
private JTextArea txt;
public static JLabel dateMine;
public static int loseNum = -1;
Icon ic = new ImageIcon("旗子 (1).png");
public UI() {
selRowMine();
}
public void setUI(int numRow,int numMine) {
this.numRow = numRow;
UI.numMine = numMine;
setWindow();
UI.listBtn = new JButton[numRow][numRow];
setPanel();
setMine(numRow,numMine);
corrdinatesUI = Service.corrdinates;
setButton();
new WinGameThread().start();
setOtherPane();
mainWindow.setVisible(true);
}
public void selRowMine() {
selFrame = new JFrame();
selFrame.setTitle("选择游戏模式!");
selFrame.setAlwaysOnTop(true);
JPanel selPane = new JPanel();
selPane.setBackground(new Color(253,206,218));
selFrame.setBounds(350, 350, 400, 300);
selList = new JList<>(new String[] {"初级游戏模式-10*10","高级游戏模式-15*15"});
selList.setFont(new Font("宋体",0,30));
txt = new JTextArea();
txt.setBounds(178, 90, 150, 30);
txt.setFont(new Font("宋体",0,25));
JLabel txtMine = new JLabel();
txtMine.setText("雷的个数");
txtMine.setFont(new Font("宋体",0,25));
txtMine.setBounds(55, 90, 100, 30);
JButton selBtn = new JButton("确定");
selBtn.setBounds(100, 150, 180, 80);
selBtn.setBackground(new Color(173,196,251));
selBtn.addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent e) {
int num = selList.getSelectedIndex();
if(num == 0) {
int mine = 20;
try {
mine = Integer.parseInt(txt.getText());
} catch (NumberFormatException e1) {
}
setUI(10,mine);
selFrame.dispose();
}else if(num == 1) {
int mine = 40;
try {
mine = Integer.parseInt(txt.getText());
} catch (NumberFormatException e1) {
}
setUI(15,mine);
selFrame.dispose();
}
}
});
selPane.add(selList);
selFrame.add(txtMine);
selFrame.add(txt);
selFrame.add(selBtn);
selFrame.add(selPane);
selFrame.setVisible(true);
}
public void setMine(int row,int mine) {
Service s = new Service();
s.setMine(mine,row);
}
public void setWindow() {
mainWindow = new JFrame();
mainWindow.setBounds(100, 100, numRow*50 + 19, numRow*50 + 100);
mainWindow.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
mainWindow.setTitle("这是一个扫雷游戏");
mainWindow.setLayout(null);
}
public void setOtherPane() {
dateMine = new JLabel();
dateMine.setBounds(0, numRow*50 - 30, numRow*50, 100);
dateMine.setFont(new Font("宋体",0,30));
dateMine.setVisible(true);
mainWindow.add(dateMine);
new DateMineThread().start();
}
public void setPanel() {
pane = new JPanel();
pane.setLayout(new GridLayout(numRow,numRow));
pane.setBounds(0, 0, numRow*50, numRow*50);
mainWindow.add(pane);
}
public void setButton() {
color = new Color(135,206,250);
for (int i = 0; i < corrdinatesUI.length; i++) {
for (int j = 0; j < corrdinatesUI.length; j++) {
JButton btn = new JButton();
String msg = String.valueOf(corrdinatesUI[i][j]);
btn.setText(msg);
btn.setForeground(color);
btn.setName(i + "," + j);
btn.setBackground(color);
btn.addMouseListener(new MouseListener() {
@Override
public void mouseReleased(MouseEvent e) {
}
@Override
public void mousePressed(MouseEvent e) {
}
@Override
public void mouseExited(MouseEvent e) {
}
@Override
public void mouseEntered(MouseEvent e) {
}
@Override
public void mouseClicked(MouseEvent e) {
if(e.getButton() == MouseEvent.BUTTON1) {
if(btn.getText().equals("-1")) {
new Thread(new Runnable() {
@Override
public void run() {
btnMine();
loseNum = 1;
Integer choice = JOptionPane.showConfirmDialog(pane, "游戏结束!");
if(choice == 0) {
mainWindow.dispose();
new UI();
}else {
}
}
}).start();
}
else if(btn.getText().equals("0")){
btnZero(btn,-1,-1);
}
else {
btnNotMine(btn);
}
}
else if(e.getButton() == MouseEvent.BUTTON3) {
if(btn.isSelected() == false) {
if(btn.getIcon() == null) {
numMine--;
btn.setIcon(ic);
}else {
numMine++;
btn.setIcon(null);
}
}
}
}
});
listBtn[i][j] = btn;
pane.add(btn);
}
}
}
public void btnMine() {
for (int i = 0; i < listBtn.length; i++) {
for (int j = 0; j < listBtn.length; j++) {
if(listBtn[i][j].getText().equals("-1")) {
listBtn[i][j].setBackground(Color.RED);
listBtn[i][j].setSelected(true);
listBtn[i][j].setEnabled(false);
try {
Thread.sleep(100);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}
}
public void btnNotMine(JButton btn) {
btn.setBackground(bgColor);
btn.setSelected(true);
if(btn.getText().equals("0")) {
btn.setForeground(bgColor);
}
}
public void btnZero(JButton btn,int x,int y) {
btnNotMine(btn);
if(btn.getText().equals("-1")) {
return;
}
if(!(btn.getText().equals("0"))) {
return;
}
if(x==-1 && y==-1) {
String num = btn.getName();
String[] str = num.split(",");
x = Integer.parseInt(str[0]);
y = Integer.parseInt(str[1]);
}
for (int i = x - 1; i <= x + 1; i++) {
for (int j = y - 1; j <= y + 1; j++) {
if(i == x && j == y) {
continue;
}
try {
if(listBtn[i][j].getText().equals("0") && listBtn[i][j].isSelected() == false) {
btnNotMine(listBtn[i][j]);
btnZero(listBtn[i][j],i,j);
}
else if(listBtn[i][j].getText().equals("-1") && listBtn[i][j].isSelected() == false){
continue;
}
else if(listBtn[i][j].isSelected() == false){
btnNotMine(listBtn[i][j]);
}
} catch (Exception e) {
}
}
}
}
}
3.逻辑类
public class Service {
public static int[][] corrdinates ;
public void setMine(int numMine,int num) {
setArray(num);
int x;
int y;
for(int i = 0 ;i < numMine;i++) {
x = (int)(Math.random() * num);
y = (int)(Math.random() * num);
if(corrdinates[x][y] != -1) {
corrdinates[x][y] = -1;
}else {
i--;
continue;
}
aroundMine(x,y);
}
}
private void aroundMine(int x, int y) {
for (int i = x - 1; i <= x + 1; i++) {
for (int j = y - 1; j <= y + 1; j++) {
if(x == 0 && y == 0) {
continue;
}
try {
if(corrdinates[i][j] != -1) {
corrdinates[i][j]++;
}
} catch (Exception e) {
}
}
}
}
public void setArray(int num) {
corrdinates = new int[num][num];
}
}
4.判断胜利线程类
import javax.swing.JButton;
import javax.swing.JOptionPane;
public class WinGameThread extends Thread{
private JButton[][] listBtn;
private int numMine;
public static int winNum = -1;
@Override
public void run() {
this.numMine = UI.numMine;
while(true) {
this.listBtn = UI.listBtn;
int index = 0;
try {
for (JButton[] jButtons : this.listBtn) {
for (JButton jButton : jButtons) {
if(jButton.isSelected() == false) {
index++;
}
}
}
} catch (Exception e1) {
}
if(index == this.numMine) {
JOptionPane.showMessageDialog(UI.pane, "获得胜利!");
winNum = 1;
break;
}
try {
Thread.sleep(500);
} catch (InterruptedException e) {
e.printStackTrace();
}
}
}
}
5.底部时间和雷数线程类
import javax.swing.JLabel;
public class DateMineThread extends Thread{
private JLabel dateMine;
private int numMine;
public static int gameTime;
@Override
public void run() {
this.dateMine = UI.dateMine;
int index = 0;
while(true) {
this.numMine = UI.numMine;
String str = "已用时间:" + index + " 剩余雷的个数为:" + this.numMine;
dateMine.setText(str);
try {
Thread.sleep(1000);
} catch (InterruptedException e) {
e.printStackTrace();
}
index++;
if(WinGameThread.winNum == 1) {
gameTime = index;
break;
}
if(UI.loseNum == 1) {
gameTime = index;
break;
}
}
}
}