😵
package com.codegym.games.minesweeper;
import com.codegym.engine.cell.*;
public class MinesweeperGame extends Game{
private static final int SIDE=9; // 地图大小
private GameObject[][] gameField = new GameObject[SIDE][SIDE]; // 地图
private int countMinesOnField;// 场上的地雷总数
private int countClosedTiles = SIDE*SIDE; // 未打开的格子总数
private static final String MINE = "\uD83D\uDCA3"; // 地雷
private static final String FLAG = "\uD83D\uDEA9"; // 旗子
private int countFlags;
private int [][] dim = {{-1, 0}, {0, -1}, {0, 1}, {1, 0}, {-1, -1}, {-1, 1}, {1, -1}, {1, 1}};
private boolean isGameStopped;
@Override // 点击鼠标左键
public void onMouseLeftClick(int x, int y){
// 调用 openTile()函数 显示数字或地雷
openTile(x, y);
}
private void openTile(int x, int y){
if(isGameStopped==true || gameField[y][x].isFlag==true || gameField[y][x].isOpen==true){
return;
}
gameField[y][x].isOpen = true;
--countClosedTiles;
setCellColor(x, y, Color.GREEN);
// 判断是否是雷
if(gameField[y][x].isMine==true){
setCellValueEx(x, y, Color.RED, MINE);
gameOver();
return;
}
else {
// 周围没有地雷
if(gameField[y][x].countMineNeighbors==0){
setCellValue(x, y, "");
for(int i=0; i<8; i++){
int x1 = x + dim[i][0];
int y1 = y + dim[i][1];
if(x1>=0&&x1<SIDE&&y1>=0&&y1<SIDE){
if(gameField[y1][x1].isOpen==false){
openTile(x1, y1);
}
}
}
}
else {
setCellNumber(x, y, gameField[y][x].countMineNeighbors);
}
}
if(countClosedTiles == countMinesOnField && gameField[y][x].isMine==false){
win();
}
}
@Override // 鼠标右击
public void onMouseRightClick(int x, int y){
markTile(x, y);
}
private void markTile(int x, int y){
if(isGameStopped==true){
return;
}
// 当前格子 没有显示 / 场上旗子用完 并且该格子不是旗子
if(gameField[y][x].isOpen==true || countFlags==0 && gameField[y][x].isFlag==false){
// 啥也不干
}
else {
if(!gameField[y][x].isFlag){
gameField[y][x].isFlag = true;
countFlags--;
setCellValue(x, y, FLAG);
setCellColor(x, y, Color.YELLOW);
}
else {
gameField[y][x].isFlag = false;
countFlags++;
setCellValue(x, y, "");
setCellColor(x, y, Color.ORANGE);
}
}
}
private void gameOver(){
isGameStopped = true;
showMessageDialog(Color.RED, "GameOver", Color.YELLOW, 80);
}
private void win(){
isGameStopped = true;
showMessageDialog(Color.YELLOW, "You Wins!", Color.RED, 80);
}
// 创造cell 坐标 颜色 计算总的地雷数 重点 i, j 的点对应坐标是 j,i
private void createGame(){
isGameStopped = false;
int mineNum = 0;
for(int i=0; i<SIDE; i++){
mineNum = getRandomNumber(10);
for(int j=0; j<SIDE; j++){
boolean boom = false;
if(mineNum == j){
boom = true;
countMinesOnField++;
}
gameField[i][j] = new GameObject(j, i, boom);
setCellColor(j, i, Color.ORANGE);
}
}
countMineNeighbors();
countFlags = countMinesOnField;
}
// 计算每个cell 周围的地雷数目
private void countMineNeighbors(){
for(int i=0; i<SIDE; i++){
for(int j=0; j<SIDE; j++){
if(gameField[i][j].isMine == false){
gameField[i][j].countMineNeighbors = getNeighbors(gameField[i][j]);
}
}
}
}
// 获取每个非地雷点周围的地雷数
private int getNeighbors(GameObject gameObject){
int x = gameObject.y;
int y = gameObject.x;
int sum = 0;
for(int i=0; i<dim.length; i++){
int x1 = x + dim[i][0];
int y1 = y + dim[i][1];
if(x1>=0&&x1<SIDE&&y1>=0&&y1<SIDE){
if(gameField[x1][y1].isMine==true){
sum++;
}
}
}
return sum;
}
// 初始化
public void initialize(){
setScreenSize(SIDE, SIDE);
createGame();
}
}