Не знаю, что не так. Когда матрица более менее наполнена вместо слияния клеток получаю пустую или 2....
package com.javarush.games.game2048;
import com.javarush.engine.cell.Color;
import com.javarush.engine.cell.Game;
import com.javarush.engine.cell.Key;
public class Game2048 extends Game{
private static final int SIDE = 4;
private int[][] gameField = new int[SIDE][SIDE];
private boolean isGameStopped = false;
private int score;
@Override
public void initialize() {
super.initialize();
setScreenSize(SIDE, SIDE);
createGame();
drawScene();
}
private void createGame() {
for (int x = 0; x < SIDE; x++) {
for (int y = 0; y < SIDE; y++) {
gameField[x][y] = 0;
}
}
score = 0;
setScore(score);
createNewNumber();
createNewNumber();
}
private void createNewNumber() {
if (getMaxTileValue() == 2048) {
win();
}
int x = getRandomNumber(SIDE);
int y = getRandomNumber(SIDE);
int rand = getRandomNumber(10);
if (rand < 9) {
gameField[x][y] = 2;
} else {
gameField[x][y] = 4;
}
}
private int getEmptyTilesCount() {
int empty = 0;
for (int x = 0; x < SIDE; x++) {
for (int y = 0; y < SIDE; y++) {
if (gameField[x][y] == 0) {
empty++;
}
}
}
return empty;
}
private boolean canMerge() {
for (int i = 0; i < SIDE; i++) {
for (int j = 0; j < SIDE - 1; j++) {
if (gameField[i][j] == gameField[i][j + 1]) {
return true;
}
}
}
for (int j = 0; j < SIDE; j++) {
for (int i = 0; i < SIDE - 1; i++) {
if (gameField[i][j] == gameField[i + 1][j]) {
return true;
}
}
}
return false;
}
private boolean canUserMove() {
if (getEmptyTilesCount() > 0 || canMerge()) {
return true;
}
return false;
}
private void drawScene() {
for (int x = 0; x < SIDE; x++) {
for (int y = 0; y < SIDE; y++) {
setCellColoredNumber(y, x, gameField[x][y]);
}
}
}
private void win() {
isGameStopped = true;
showMessageDialog(Color.GREEN, "WIN!", Color.BLACK, 10);
}
private boolean mergeRow(int[] row) {
boolean changes = false;
for (int i = 0; i < row.length - 1; i++) {
if (row[i] != 0 && (row[i] == row[i + 1])) {
score = score + row[i] + row[i + 1];
setScore(score);
row[i] = row[i] + row[i + 1];
row[i + 1] = 0;
changes = true;
}
}
return changes;
}
private boolean compressRow(int[] row) {
boolean changes = false;
for (int i = 0; i < row.length; i++) {
if (row[i] == 0 && i < row.length - 1 && row[i + 1] != 0) {
int temp = row[i];
row[i] = row[i + 1];
row[i + 1] = temp;
i = -1;
changes = true;
}
}
return changes;
}
private void gameOver() {
isGameStopped = true;
showMessageDialog(Color.RED, "GAME OVER!", Color.BLACK, 10);
}
private void setCellColoredNumber(int x, int y, int value) {
String label = String.valueOf(value);
if (value == 0) label = "";
setCellValueEx(x, y, getColorByValue(value), label);
}
private Color getColorByValue(int value) {
switch (value){
case 0:
return Color.LIGHTGREY;
case 2:
return Color.LIGHTYELLOW;
case 4:
return Color.LIGHTGREEN;
case 8:
return Color.LIGHTSALMON;
case 16:
return Color.ORANGE;
case 32:
return Color.LIGHTPINK;
case 64:
return Color.RED;
case 128:
return Color.YELLOW;
case 256:
return Color.YELLOWGREEN;
case 512:
return Color.LIGHTBLUE;
case 1024:
return Color.BLUE;
case 2048:
return Color.BLUEVIOLET;
default:
return Color.LIGHTGREY;
}
}
@Override
public void onKeyPress(Key key) {
if (isGameStopped) {
if (key == Key.SPACE) {
isGameStopped = false;
createGame();
drawScene();
}
} else {
if (!canUserMove()) {
gameOver();
} else {
if (key == Key.LEFT) {
moveLeft();
drawScene();
} else if (key == Key.RIGHT) {
moveRight();
drawScene();
} else if (key == Key.UP) {
moveUp();
drawScene();
} else if (key == Key.DOWN) {
moveDown();
drawScene();
}
}
}
}
private void rotateClockwise() {
int n = SIDE;
int[][] newField = new int[n][n];
for (int i = 0; i < n/2; i++) {
for (int j = i; j < n-i-1; j++) {
int tmp = gameField[i][j];
newField[i][j]=gameField[n-j-1][i];
newField[n-j-1][i]=gameField[n-i-1][n-j-1];
newField[n-i-1][n-j-1]=gameField[j][n-i-1];
newField[j][n-i-1]=tmp;
}
}
gameField = newField;
}
private int getMaxTileValue() {
int max = 0;
for (int x = 0; x < SIDE; x++) {
for (int y = 0; y < SIDE; y++) {
if (gameField[x][y] > max) {
max = gameField[x][y];
}
}
}
return max;
}
private void moveUp() {
rotateClockwise();
rotateClockwise();
rotateClockwise();
moveLeft();
rotateClockwise();
}
private void moveDown() {
rotateClockwise();
moveLeft();
rotateClockwise();
rotateClockwise();
rotateClockwise();
}
private void moveLeft() {
boolean isChanged = false;
for (int i = 0; i < SIDE; i++) {
if (compressRow(gameField[i])) {
isChanged = true;
}
if (mergeRow(gameField[i])) {
isChanged = true;
compressRow(gameField[i]);
}
}
if (isChanged) createNewNumber();
}
private void moveRight() {
rotateClockwise();
rotateClockwise();
moveLeft();
rotateClockwise();
rotateClockwise();
}
}