-
Notifications
You must be signed in to change notification settings - Fork 0
/
Grid.pde
134 lines (116 loc) · 3.92 KB
/
Grid.pde
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
class Grid {
int rows, cols;
color[][] colors;
ArrayList<Integer> clearedRows = new ArrayList<Integer>();
Grid(int rows, int cols) {
this.rows = rows;
this.cols = cols;
colors = new color[cols][rows];
for (int i = 0; i < cols; ++i)
for (int j = 0; j < rows; ++j)
colors[i][j] = 0;
}
Grid(Grid other) {
this.rows = other.rows;
this.cols = other.cols;
colors = new color[cols][rows];
for (int i = 0; i < cols; ++i)
for (int j = 0; j < rows; ++j)
colors[i][j] = other.colors[i][j];
}
void clear() {
for (int i = 0; i < cols; ++i)
for (int j = 0; j < rows; ++j)
colors[i][j] = 0;
}
void eraseCleared() {
for (int row : clearedRows) {
for (int j = row - 1; j >= 0; --j) {
for (int i = 0; i < cols; ++i)
colors[i][j + 1] = colors[i][j];
}
for (int i = 0; i < cols; ++i)
colors[i][0] = 0;
}
}
public boolean placeShape(Shape s, int x, int y) {
for (int i = 0; i < s.matrix.length; ++i) {
for (int j = 0; j < s.matrix.length; ++j) {
if (s.matrix[i][j]) {
int col = i + x;
int row = j + y;
if (row < 0)
continue;
else if (row < rows && (col >= 0 && col < cols))
colors[i + x][j + y] = s.c;
else
return false;
}
}
}
return true;
}
boolean isOccupied(int x, int y) {
if (y < 0 && x < cols && x >= 0) // allow movement/flipping to spaces above the board
return false;
return (x >= cols || x < 0 || y >= rows || colors[x][y] != 0);
}
// Performs a collision test from a shape against the blocks
// already in the grid. Returns true if there is no collision,
// false if there is.
public boolean isLegal(Shape shape, int col, int row) {
for (int i = 0; i < shape.matrix.length; ++i)
for (int j = 0; j < shape.matrix.length; ++j)
if (shape.matrix[i][j] && isOccupied(col + i, row + j))
return false;
return true;
}
public void updatedClearedRows() {
clearedRows.clear();
for (int j = 0; j < rows; ++j) {
boolean cleared = true;
for (int i = 0; i < cols; ++i)
if (colors[i][j] == 0) {
cleared = false;
break;
}
if (cleared) clearedRows.add(j);
}
}
// Higher values represent a more challenging grid to clear
public int scoreGrid() {
int numberHoles = 0; // A hole is an empty cell that has a filled cell immediately above it (a hole with a height of 2 is worth the same as a hole with a height of 1)
int highestFilleCell = 0;
int numberFilledCells = 0;
int weighedFilledCells = 0; // The number of filled cells each multiplied by their height
int biggestSlope = 0; // The highest difference in height between a column and it's neighbors
int roughness = 0; // Roughness is the sum of the slopes of all columns
int[] columnHeights = new int[cols];
for (int row = 0; row < rows; ++row) {
int height = rows - row;
for (int col = 0; col < cols; ++col) {
if (colors[col][row] == 0) {
// Cell is empty, check above if it's filled -> hole
if (row > 0 && colors[col][row-1] != 0) {
++numberHoles;
}
} else {
// Cell is filled, update the score
if (height > columnHeights[col]) columnHeights[col] = height;
++numberFilledCells;
weighedFilledCells += height;
}
}
}
for (int col = 0; col < cols; ++col) {
int height = columnHeights[col];
if (height > highestFilleCell) highestFilleCell = height;
if (col < (cols - 1)) {
int slope = abs(height - columnHeights[col + 1]);
if (slope > biggestSlope) biggestSlope = slope;
roughness += slope;
}
}
return 20 * numberHoles + highestFilleCell + numberFilledCells + weighedFilledCells + biggestSlope + roughness;
}
}