nmtrang / minesweeper

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

Minesweeper Simulator

Minesweeper is a single-player puzzle video game. The objective of the game is to clear a rectangular board containing hidden "mines" or bombs without detonating any of them, with help from clues about the number of neighboring mines in each field. The game originates from the 1960s, and it has been written for many computing platforms in use today. It has many variations and offshoots.

Special thanks to these contributors

Trang Nguyen Tung Phan Tra Le Phuc Tran

Tools used

Language: Java 15

Code editor: IntelliJ IDEA

How to play?

The game can be run in 3 ways

  1. Clone the project and open it in your code editor in order to run the Minesweeper file which is the main file
  2. Double-click Minesweeper.jar file (make sure your Java is of version 15)
  3. Navigate to the folder contains Minesweeper.jar file and run this command line
java -jar Minesweeper.jar

Classes design

So, how did we design and organize classes? Depending on every objects in the game, we extracted the most essential elements in the game and packaged them into these classes:

Game.java

This is the entry point and UI design of the game It is built with the layout of the Java Swing It handles basic user input, specifically, clicking It contains some action events involved in the game (mostly click events)

Note: Given that the grid consists of individual cells, all of which can be thought of as objects, with each cell sharing certain basic properties/functionalities so it will make sense to do some type of class inheritance in the program.

Cell.java (parent class)

This is where we store properties of the most basic cell like whether it’s covered, flagged or what type of that cell: is it BOMB cell? Is it BOMB NEIGHBOR cell? Or is it EMPTY cell?

BombCell (extends Cell)

NeighborOfBombCell (extends Cell)

EmptyCell (extends Cell)

How is this EmptyCell initiated? It has 2 ways of creation:

  • Whenever the game starts to begin, we have all the empty cells, of course

  • When the player starts to play the game, some cells will be covered by some sort of numbers or flagged, some other cells will be left as remaining empty cells.

Board.java

  • Combines every different small classes into one big view and is used as a main controller.

  • Handles user actions (either left or right click) and performs or displays desired moves/information accordingly using paint and event listeners

  • Stores all images of these different types of cells in a map and displays images according to cells clicked

  • Contains recursive function to clear a bomb-free region of empty cells and is called when user clicks on an empty cell

  • Stores user moves whenever user clicks the board, and handles the “undo” functionality whenever the user desires to remove a move

CellType.java and ImageName.java (enums)

Enums used to represent the different types of cells and images in a cleaner, more readable way

  • CellType has Bomb, BombNeighbor, Empty
  • ImageName has Empty, Covered, Marked, Wrongmarked, Bomb

Input.java and CustomMap.java

Has two variable: size of map and number of mines

  • If the user choose 8x8 map: return a map with width and height is equal 8 and the number of mines is 10

  • If the user choose 16x16 map: return a map with width and height is equal 16 and the number of mines is 10

  • If the user choose Custom (new feature):

    • Open the JFrame CustomMap: let the user input the value of size and input the number of mines (0 is invalid)
    • Cannot set the size lower than 6
    • Cannot input Invalid value

Algorithms brief walk-through

2D Array

Since minesweeper takes place on a 16x16 grid (default), we use a 2D array of "Cell" objects, which we think of as a grid, to store the state of each cell in that grid, in relation to which cells are bombing included when empty or adjacent cells (ie "number" cells). Cell was a parent class we created that stores the properties of each cell and handles basic cell behavior based on its type. It is used every time a new game is started in which the 2-D matrix is randomly filled with bomb cells, number cells (cells that are neighbors to the bomb cells that tell how many bombs are nearby) or empty cells . Processing different user actions for a particular cell by using a double for loop representing the rows and columns of the 2D array, or calling individual elements of the 2D array to initialize cell objects. Our use of a 2D matrix was extremely helpful in organizing my entire game board structure and finding user actions indicating the desired locations to handle the logic of the game.

Collection

Players can "undo" their moves when they hit the "undo" button, unless hitting a bomb, which then the game ends. We fully take advantage of the LIFO property of Stack so it would be best for us to implement that principle to store the players’ move in order to undo the most recent step by popping it out of the Stack. In other words, removing the player’s move from Stack and returning the state of the cell depending on the player’s last click. The other function of Stack - push() is also used to add steps to the Stack whenever the player left-click a number of empty cells, and right-click to flag/unflag a cell, which shows the player’s most recent move. The player can undo any number of moves for any type of move, which includes clicking on flagged cells, empty cells, and neighbor cells, but for bomb cells, the undo() function is disabled (because that is plainly cheating, of course!) by “clearing” the Stack.

Recursion

We utilize recursion to reveal and clear a mine-free region of cells. In other words, when a player clicks on a cell that has no bombs with adjacent cells also bomb-free so all adjacent cells are automatically cleared and the region with bomb-free cells is revealed up until the cell that is connected to a bomb.

Enjoy!!!

About


Languages

Language:Java 100.0%