summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--inc/tetromino.h92
-rw-r--r--src/main.c203
2 files changed, 238 insertions, 57 deletions
diff --git a/inc/tetromino.h b/inc/tetromino.h
index 45c335b..30d55a3 100644
--- a/inc/tetromino.h
+++ b/inc/tetromino.h
@@ -29,8 +29,8 @@ struct Tetromino tetrominos[7] = {
.directions = {
[NORTH] = {
{0, 0, 0, 0},
- {1, 1, 1, 1},
{0, 0, 0, 0},
+ {1, 1, 1, 1},
{0, 0, 0, 0}
},
@@ -42,8 +42,8 @@ struct Tetromino tetrominos[7] = {
},
[SOUTH] = {
{0, 0, 0, 0},
- {0, 0, 0, 0},
{1, 1, 1, 1},
+ {0, 0, 0, 0},
{0, 0, 0, 0}
},
[WEST] = {
@@ -59,24 +59,24 @@ struct Tetromino tetrominos[7] = {
.color = BLUE,
.directions = {
[NORTH] = {
- {1, 0, 0},
+ {0, 0, 0},
{1, 1, 1},
- {0, 0, 0}
+ {1, 0, 0}
},
[EAST] = {
- {0, 1, 1},
{0, 1, 0},
- {0, 1, 0}
+ {0, 1, 0},
+ {0, 1, 1}
},
[SOUTH] = {
- {0, 0, 0},
+ {0, 0, 1},
{1, 1, 1},
- {0, 0, 1}
+ {0, 0, 0}
},
[WEST] = {
+ {1, 1, 0},
{0, 1, 0},
- {0, 1, 0},
- {1, 1, 0}
+ {0, 1, 0}
}
}
},
@@ -85,24 +85,24 @@ struct Tetromino tetrominos[7] = {
.color = ORANGE,
.directions = {
[NORTH] = {
- {0, 0, 1},
+ {0, 0, 0},
{1, 1, 1},
- {0, 0, 0}
+ {0, 0, 1}
},
[EAST] = {
+ {0, 1, 1},
{0, 1, 0},
- {0, 1, 0},
- {0, 1, 1}
+ {0, 1, 0}
},
[SOUTH] = {
- {0, 0, 0},
+ {1, 0, 0},
{1, 1, 1},
- {1, 0, 0}
+ {0, 0, 0}
},
[WEST] = {
- {1, 1, 0},
{0, 1, 0},
- {0, 1, 0}
+ {0, 1, 0},
+ {1, 1, 0}
}
}
},
@@ -111,24 +111,24 @@ struct Tetromino tetrominos[7] = {
.color = YELLOW,
.directions = {
[NORTH] = {
+ {0, 0, 0},
{0, 1, 1},
- {0, 1, 1},
- {0, 0, 0}
+ {0, 1, 1}
},
[EAST] = {
+ {0, 0, 0},
{0, 1, 1},
- {0, 1, 1},
- {0, 0, 0}
+ {0, 1, 1}
},
[SOUTH] = {
+ {0, 0, 0},
{0, 1, 1},
- {0, 1, 1},
- {0, 0, 0}
+ {0, 1, 1}
},
[WEST] = {
+ {0, 0, 0},
{0, 1, 1},
- {0, 1, 1},
- {0, 0, 0}
+ {0, 1, 1}
}
}
},
@@ -137,24 +137,24 @@ struct Tetromino tetrominos[7] = {
.color = GREEN,
.directions = {
[NORTH] = {
- {0, 1, 1},
+ {0, 0, 0},
{1, 1, 0},
- {0, 0, 0}
+ {0, 1, 1}
},
[EAST] = {
- {0, 1, 0},
+ {0, 0, 1},
{0, 1, 1},
- {0, 0, 1}
+ {0, 1, 0}
},
[SOUTH] = {
- {0, 0, 0},
+ {1, 1, 0},
{0, 1, 1},
- {1, 1, 0}
+ {0, 0, 0}
},
[WEST] = {
- {1, 0, 0},
+ {0, 1, 0},
{1, 1, 0},
- {0, 1, 0}
+ {1, 0, 0}
}
}
},
@@ -163,9 +163,9 @@ struct Tetromino tetrominos[7] = {
.color = PURPLE,
.directions = {
[NORTH] = {
- {0, 1, 0},
+ {0, 0, 0},
{1, 1, 1},
- {0, 0, 0}
+ {0, 1, 0}
},
[EAST] = {
{0, 1, 0},
@@ -173,9 +173,9 @@ struct Tetromino tetrominos[7] = {
{0, 1, 0}
},
[SOUTH] = {
- {0, 0, 0},
+ {0, 1, 0},
{1, 1, 1},
- {0, 1, 0}
+ {0, 0, 0}
},
[WEST] = {
{0, 1, 0},
@@ -189,24 +189,24 @@ struct Tetromino tetrominos[7] = {
.color = RED,
.directions = {
[NORTH] = {
- {1, 1, 0},
+ {0, 0, 0},
{0, 1, 1},
- {0, 0, 0}
+ {1, 1, 0}
},
[EAST] = {
- {0, 0, 1},
+ {0, 1, 0},
{0, 1, 1},
- {0, 1, 0}
+ {0, 0, 1}
},
[SOUTH] = {
- {0, 0, 0},
+ {0, 1, 1},
{1, 1, 0},
- {0, 1, 1}
+ {0, 0, 0}
},
[WEST] = {
- {0, 1, 0},
+ {1, 0, 0},
{1, 1, 0},
- {1, 0, 0}
+ {0, 1, 0}
}
}
}
diff --git a/src/main.c b/src/main.c
index 0b65f7d..35cb460 100644
--- a/src/main.c
+++ b/src/main.c
@@ -11,7 +11,7 @@
#define BLOCK_SIZE 25
-#define FALL_TICK 0.5
+#define FALL_TICK 0.2
enum Phases {
GENERATION,
@@ -35,9 +35,9 @@ struct {
} current_piece;
struct Color matrix[MATRIX_WIDTH][MATRIX_HEIGHT];
-int piece_queue[2][TETROMINO_COUNT] = {
- {0, 1, 2, 3, 4, 5, 6},
- {0, 1, 2, 3, 4, 5, 6}
+int piece_queue[TETROMINO_COUNT*2] = {
+ 0, 1, 2, 3, 4, 5, 6,
+ 0, 1, 2, 3, 4, 5, 6
};
int current_bag = 0;
int current_piece_index = 0;
@@ -80,7 +80,7 @@ void render_matrix(void)
if (tetrominos[current_piece.type].directions[current_piece.rotation][j][i] == 1) {
draw_block(
(matrix_origin_x + ((current_piece.pos_x + i - 1) * BLOCK_SIZE)) + 1
- ,(matrix_origin_y + ((current_piece.pos_y - j + 1) * BLOCK_SIZE)) + 1
+ ,(matrix_origin_y + ((current_piece.pos_y + j - 1) * BLOCK_SIZE)) + 1
,BLOCK_SIZE - 2
,BLOCK_SIZE - 2
,tetrominos[current_piece.type].color
@@ -100,27 +100,195 @@ void shuffle_bag(int *bag)
}
}
+int is_overlap(int x, int y)
+{
+ for (int i = 0; i < tetrominos[current_piece.type].size; i++) {
+ for (int j = 0; j < tetrominos[current_piece.type].size; j++) {
+ if (tetrominos[current_piece.type].directions[current_piece.rotation][j][i] == 1) {
+ if (current_piece.pos_x + i - 1 + x >= MATRIX_WIDTH
+ || current_piece.pos_x + i - 1 + x < 0
+ || current_piece.pos_y + j - 1 + y < 0
+ || (!ColorIsEqual(BLACK, matrix[current_piece.pos_x + i - 1 + x][current_piece.pos_y + j - 1 + y])
+ && !ColorIsEqual(WHITE, matrix[current_piece.pos_x + i - 1 + x][current_piece.pos_y + j - 1 + y]))) {
+ return 1;
+ }
+ }
+ }
+ }
+ return 0;
+}
+
void generation_phase(void)
{
// bag generation
- if (current_piece_index > TETROMINO_COUNT) {
+ if (current_piece_index == 14) {
+ shuffle_bag(&(piece_queue[7]));
current_piece_index = 0;
- shuffle_bag(piece_queue[current_bag]);
- current_bag = !current_bag;
+ }
+ if (current_piece_index == 7) {
+ shuffle_bag(piece_queue);
}
// set current piece
- current_piece.type = piece_queue[current_bag][current_piece_index++];
+ current_piece.type = piece_queue[current_piece_index++];
current_piece.rotation = NORTH;
current_piece.pos_x = 4;
current_piece.pos_y = 20;
+ if (is_overlap(0,0)) {
+ CloseWindow();
+ }
+}
+
+void handle_rotate(void)
+{
+ static int rotated_cw = 0;
+ static int rotated_ccw = 0;
+ if (game_phase == FALL || game_phase == LOCK) {
+ if (IsKeyDown(KEY_L) && !rotated_cw) {
+ current_piece.rotation++;
+ current_piece.rotation = current_piece.rotation % 4;
+ if (is_overlap(0, 0)) {
+ current_piece.rotation--;
+ if (current_piece.rotation < 0) current_piece.rotation = 3;
+ }
+ rotated_cw = 1;
+ }
+ if (IsKeyUp(KEY_L)) {
+ rotated_cw = 0;
+ }
+ if (IsKeyDown(KEY_J) && !rotated_ccw) {
+ current_piece.rotation--;
+ if (current_piece.rotation < 0) current_piece.rotation = 3;
+ if (is_overlap(0, 0)) {
+ current_piece.rotation++;
+ current_piece.rotation = current_piece.rotation % 4;
+ }
+ rotated_ccw = 1;
+ }
+ if (IsKeyUp(KEY_J)) {
+ rotated_ccw = 0;
+ }
+ }
+}
+
+void move_right(void)
+{
+ if (is_overlap(1, 0)) {
+ return;
+ }
+ current_piece.pos_x++;
+}
+
+void move_left(void)
+{
+ if (is_overlap(-1, 0)) {
+ return;
+ }
+ current_piece.pos_x--;
+}
+
+void handle_lr(void)
+{
+ static int moved_right = 0;
+ static int moved_left = 0;
+ if (game_phase == FALL || game_phase == LOCK) {
+ if (IsKeyDown(KEY_D) && !moved_right) {
+ move_right();
+ moved_right = 1;
+ }
+ if (IsKeyUp(KEY_D)) {
+ moved_right = 0;
+ }
+ if (IsKeyDown(KEY_A) && !moved_left) {
+ move_left();
+ moved_left = 1;
+ }
+ if (IsKeyUp(KEY_A)) {
+ moved_left = 0;
+ }
+ }
+}
+
+void move_piece_to_matrix(void)
+{
+ for (int i = 0; i < tetrominos[current_piece.type].size; i++) {
+ for (int j = 0; j < tetrominos[current_piece.type].size; j++) {
+ if (tetrominos[current_piece.type].directions[current_piece.rotation][j][i] == 1) {
+ matrix[current_piece.pos_x + i - 1][current_piece.pos_y + j - 1] = tetrominos[current_piece.type].color;
+ }
+ }
+ }
+}
+
+void handle_fall(void)
+{
+ static double phase_time = 0.0;
+ if (game_phase == FALL) {
+ phase_time += GetFrameTime();
+ if ((!IsKeyDown(KEY_S) && phase_time < FALL_TICK) || phase_time < FALL_TICK * 0.5) {
+ return;
+ } else {
+ phase_time = 0.0;
+ }
+ }
+
+ if (is_overlap(0, -1)) {
+ move_piece_to_matrix();
+ generation_phase();
+ return;
+ }
+
+ current_piece.pos_y--;
+}
+
+void handle_hard_drop(void)
+{
+ static int dropped = 0;
+ if (game_phase == FALL) {
+ if (IsKeyDown(KEY_W) && !dropped) {
+ dropped = 1;
+ while(!is_overlap(0, -1)) {
+ current_piece.pos_y--;
+ }
+ }
+ if (IsKeyUp(KEY_W)) {
+ dropped = 0;
+ }
+ }
+}
+
+void clear_line(int line) {
+ for (int y = line; y < MATRIX_HEIGHT - 1; y++) {
+ for (int x = 0; x < MATRIX_WIDTH; x++) {
+ matrix[x][y] = matrix[x][y+1];
+ if (ColorIsEqual(matrix[x][y], WHITE) && y < 20) {
+ matrix[x][y] = BLACK;
+ }
+ }
+ }
+}
+
+void handle_line_clears(void)
+{
+ for (int y = 0; y < MATRIX_HEIGHT; y++) {
+ int line_full = 1;
+ for (int x = 0; x < MATRIX_WIDTH; x++) {
+ if (ColorIsEqual(matrix[x][y], BLACK) || ColorIsEqual(matrix[x][y], WHITE)) {
+ line_full = 0;
+ }
+ }
+ if (line_full) {
+ clear_line(y);
+ }
+ }
}
int main(void)
{
- //srand(time(NULL));
+ srand(time(NULL));
InitWindow(SCREEN_WIDTH, SCREEN_HEIGHT, "~turnipGod's Tetris");
+
// set all blocks to white
for (int y = 0; y < 40; y++) {
for (int x = 0; x < 10; x++) {
@@ -128,9 +296,22 @@ int main(void)
}
}
- shuffle_bag(piece_queue[0]);
+ for (int y = 0; y < 20; y++) {
+ for (int x = 0; x < 10; x++) {
+ matrix[x][y] = BLACK;
+ }
+ }
+
+ game_phase = FALL;
+ shuffle_bag(piece_queue);
+ shuffle_bag(&(piece_queue[7]));
generation_phase();
while (!WindowShouldClose()) {
+ handle_lr();
+ handle_rotate();
+ handle_hard_drop();
+ handle_fall();
+ handle_line_clears();
BeginDrawing();
ClearBackground(WHITE);
render_matrix();