summaryrefslogtreecommitdiff
path: root/pieces.c
diff options
context:
space:
mode:
authorFrederick Yin <fkfd@fkfd.me>2022-05-31 19:00:42 +0800
committerFrederick Yin <fkfd@fkfd.me>2022-05-31 19:00:42 +0800
commit5b9a799146f25dd23d108b01abed72dc50556076 (patch)
treef352f1fcbce4febd6f814639613b96bfdf7b8d72 /pieces.c
Initial commit: placing pieces
Diffstat (limited to 'pieces.c')
-rw-r--r--pieces.c75
1 files changed, 75 insertions, 0 deletions
diff --git a/pieces.c b/pieces.c
new file mode 100644
index 0000000..95c9923
--- /dev/null
+++ b/pieces.c
@@ -0,0 +1,75 @@
+#include <stdlib.h>
+#include <stdio.h>
+#include <string.h>
+#include "pieces.h"
+
+const int N_SHAPES = 17;
+const struct piece SHAPES[] = {
+ {1, 1, "+"},
+ {1, 2, "++"},
+ {1, 3, "+++"},
+ {1, 4, "++++"},
+ {1, 5, "+++++"},
+ {2, 2, "+ +"}, // 2x2 diagonal
+ {2, 2, "++++"}, // 2x2 square
+ {2, 3, "++++ "}, // L shape
+ {2, 3, "++ ++"}, // Z shape
+ {2, 3, "+++ + "}, // T shape
+ {2, 3, "++++++"}, // 2x3 rectangle
+ {2, 4, "+++++ "}, // long L shape
+ {2, 4, "++++++++"}, // 2x4 rectangle
+ {3, 3, "++++ + "}, // large L shape
+ {3, 3, "+++ + + "}, // large T shape
+ {3, 3, "+ + +"}, // 3x3 diagonal
+ {3, 3, "+++++++++"}, // 3x3 square
+};
+
+void transpose(struct piece* pc) {
+ // transpose blocks
+ char* old = malloc(strlen(pc->blocks) + 1);
+ strcpy(old, pc->blocks); // before transposition
+ for (int r = 0; r < pc->h; r++) {
+ for (int c = 0; c < pc->w; c++) {
+ pc->blocks[c * (pc->h) + r] = old[r * (pc->w) + c];
+ }
+ }
+ free(old);
+ // swap dimensions
+ int h = pc->h;
+ pc->h = pc->w;
+ pc->w = h;
+}
+
+void rotate(struct piece* pc) {
+ // rotate `pc` ccw by 90 degrees
+ // transpose blocks
+ char* old = malloc(strlen(pc->blocks) + 1);
+ strcpy(old, pc->blocks); // before transposition
+ for (int r = 0; r < pc->h; r++) {
+ for (int c = 0; c < pc->w; c++) {
+ pc->blocks[(pc->w - c - 1) * (pc->h) + r] = old[r * (pc->w) + c];
+ }
+ }
+ free(old);
+ // swap dimensions
+ int h = pc->h;
+ pc->h = pc->w;
+ pc->w = h;
+}
+
+struct piece* randpiece() {
+ // select a random shape from `SHAPES`, make a copy where memory for `.blocks` is manually managed,
+ // then do random transformations to the copy
+ struct piece shape = SHAPES[rand() % N_SHAPES];
+ char* blocks = malloc(strlen(shape.blocks) + 1);
+ strcpy(blocks, shape.blocks);
+ struct piece* pc = malloc(sizeof(struct piece));
+ pc->h = shape.h;
+ pc->w = shape.w;
+ pc->blocks = blocks;
+ if (rand() % 2) transpose(pc);
+ for (int i = rand() % 4; i > 0; i--) // 0 to 3 times
+ rotate(pc);
+ return pc;
+}
+