Answered step by step
Verified Expert Solution
Link Copied!

Question

1 Approved Answer

I need to write a java program that plays a 'game of Threes': The game consists of a grid of moveable tiles. Each tile contains

I need to write a java program that plays a 'game of Threes':

The game consists of a grid of moveable tiles. Each tile contains a number 1, 2, 3, or a value that results from starting with a 3 and doubling a bunch of times. We will think of the grid as a 2D array of integer values, where the value 0 means there is no tile in that cell. There are only four possible operations: to "shift" the grid up, down, left, or right. What this means is that the tiles are shifted in the indicated direction, and certain combinations of tiles may be merged if "pushed" together against one of the boundaries. The exact rules for merging are discussed in a later section. The screenshot on the right shows the result of shifting in the "up" direction. The two 12's are "pushed" against the top and merge to make 24. In addition, the 1 and 2 in the second column are merged to make a 3. All other tiles that can move (the two 2's in this case) are shifted up as well. Whenever the grid is shifted in some direction, a new tile appears on the opposite side. The game ends when the grid can't be shifted in any direction because there are no empty cells and no merges are possible. The object of the game is to get the highest possible score. The score is the sum, for all tiles on the grid, of a predetermined number associated with each individual tile value.

Methods to be used in GameUtil:

int mergeValues(int a, int b) Determines whether the two tile values can be merged and returns the merged value, returning zero if no merge is possible. The basic rules are that 1 can be merged with 2, and values larger than 2 can be merged if they are equal. In either case the merged value is the sum. This method is already implemented.

int getScoreForValue(int value) Returns the score for a tile with the given value.

int calculateTotalScore(int[][] grid) Returns the total score for the given grid. This method is already implemented.

int[][] initializeNewGrid(int size, Random rand) Initializes a new grid, using the given Random object to position two initial tiles. This method is already implemented.

int[][] copyGrid(int[] grid) Makes a copy of the given 2D array. This method is already implemented.

int generateRandomTileValue(Random rand) Returns a randomly generated tile value according to a predefined set of probabilities, using the given Random object.

TilePosition generateRandomTilePosition(int[] grid, Random rand, Direction lastMove) Returns a randomly selected tile position on the side of the grid that is opposite the direction of the most recent shift.

ArrayList shiftArray(int[] arr) Shifts the array elements to the left according to the rules of the game, possibly merging two of the cells.

See below for details.

The shiftArray() method The basic rules for shifting are as follows. Remember that we interpret an array cell containing zero to be "empty". If there is an adjacent pair that can be merged, and has no empty cell to its left, then the leftmost such pair is merged (the merged value goes into the left one of the two cells) and all elements to the right are shifted one cell to the left. Otherwise, if there is an empty cell in the array, then all elements to the right of the leftmost empty cell are shifted one cell to the left. Otherwise, the method does nothing.

The method mergeValues() (see overview above) determines which pairs of values can be merged, and if so what the resulting value is. Note that at most one pair in in the array is merged.

Here are some examples:

For arr = [3, 1, 2, 1], after shiftArray(arr), the array is [3, 3, 1, 0] For arr = [1, 2, 1, 2], after shiftArray(arr), the array is [3, 1, 2, 0] For arr = [6, 3, 3, 3, 3], after shiftArray(arr), the array is [6, 6, 3, 3, 0] For arr = [3, 6, 6, 0], after shiftArray(arr), the array is [3, 12, 0, 0] For arr = [3, 0, 1, 2], after shiftArray(arr), the array is [3, 1, 2, 0] The return value of shiftArray() is a list of Move objects. A Move object is a simple data container that encapsulates the information about a move of one cell or a merge of a pair of cells. The Move objects do not directly affect the game state, but can be used by a client (such as a GUI) to animate the motion of tiles. The Move class is in the api package; see the source code to see what it does.

Methods to be used in Game.Java:

Game(int givenSize, GameUtil givenConfig, java.util.Random givenRandom).Constructs a game with a grid of the given size, using the given instance of Random for the random number generator.

copyRowOrColumn(int rowOrColumn, Direction dir) Copy a row or column from the grid into a new one-dimensional array.

getCell(int row, int col) Returns the value in the cell at the given row and column

getNextTileValue() Returns the value that will appear on the next tile generated in a call to newTile.

getScore() Returns the current score.

getSize() Returns the size of this game's grid.

newTile() Generates a new tile and places its value in the grid, provided that there was a previous call to shiftGrid without a corresponding call to undo or newTile.

setCell(int row, int col, int value) Sets the value of the cell at the given row and column.

shiftGrid(Direction dir) Plays one step of the game by shifting the grid in the given direction.

undo() Revernts the shift performed in a previous call to shiftGrid(), provided that neither newTile() nor undo() has been called.

updateRowOrColumn(int[] arr, int rowOrColumn, Direction dir) Updates the grid by copying the given one-dimensional array into a row or column of the grid.

Methods implemented for Game.Java:

/** * Constructs a game with a grid of the given size, using a default * random number generator. The initial grid is produced by the * initializeNewGrid method of the given * GameUtil object. * @param givenSize * size of the grid for this game * @param givenConfig * given instance of GameUtil */ public Game(int givenSize, GameUtil givenConfig) { // just call the other constructor this(givenSize, givenConfig, new Random()); }?

Methods implemented for GameUtil.Java;

/** * Returns the result of merging the two given tile values, or zero * if they can't be merged. The rules are: a 1 can be merged with a 2, * and two values greater than 2 can be merged if they match. The * result of a merge is always the sum of the tile values. * @param a * given tile value * @param b * given tile value * @return * result of merging the two values, or zero if no merge is possible */ public int mergeValues(int a, int b) { if (a > 0 && b > 0 && (a + b == 3) || (a >= 3 && b == a)) { return a + b; } else { return 0; } }?

/** * Returns a new size x size array with two nonzero cells. * The nonzero cells consist of a 1 and a 2, placed randomly * in the grid using the given Random instance. * @param size * width and height of the new array * @param rand * random number generator to use for positioning the nonzero cells * @return * new size x size array */ public int[][] initializeNewGrid(int size, Random rand) { int[][] grid = new int[size][size]; int numCells = size * size; // To select two distinct cells, think of the numCells cells as ordered // left to right within rows, with the rows ordered top to bottom. // First select two distinct integers between 0 and numCells int first = rand.nextInt(numCells); int second = rand.nextInt(numCells - 1); if (second >= first) { second += 1; } // Then, divide by size to get the row, mod by size to get column, // put a 1 in the first and a 2 in the other grid[first / size][first % size] = 1; grid[second / size][second % size] = 2; return grid; }?

/** * Returns the total score for the given grid. The grid * is not modified. * @param grid * given grid * @return * sum of scores for the values in the grid */ public int calculateTotalScore(int[][] grid) { int total = 0; for (int row = 0; row < grid.length; ++row) { for (int col = 0; col < grid[0].length; ++col) { total += getScoreForValue(grid[row][col]); } } return total; } /** * Makes a copy of the given 2D array. The array * must be nonempty and rectangular. * @param grid * given 2D array to copy * @return * copy of the given array */ public int[][] copyGrid(int[][] grid) { int[][] ret = new int[grid.length][grid[0].length]; for (int row = 0; row < grid.length; ++row) { for (int col = 0; col < grid[0].length; ++col) { ret[row][col] = grid[row][col]; } } return ret; }

This is similar to the game 2048 app, but not quite.

Step by Step Solution

There are 3 Steps involved in it

Step: 1

blur-text-image

Get Instant Access with AI-Powered Solutions

See step-by-step solutions with expert insights and AI powered tools for academic success

Step: 2

blur-text-image

Step: 3

blur-text-image

Ace Your Homework with AI

Get the answers you need in no time with our AI-driven, step-by-step assistance

Get Started

Students also viewed these Databases questions