diff options
author | eug-vs <eugene@eug-vs.xyz> | 2022-03-31 22:36:17 +0300 |
---|---|---|
committer | eug-vs <eugene@eug-vs.xyz> | 2022-03-31 22:36:17 +0300 |
commit | 33d4ede846df55578bcdbe9ce5907e0b6d6e304b (patch) | |
tree | f4849c0a09867211cdc60c663d59182e492f7660 | |
parent | c5418464d57de2b71a91ddfbb4c42df25a743da9 (diff) | |
download | carcassonne-engine-c-33d4ede846df55578bcdbe9ce5907e0b6d6e304b.tar.gz |
refactor: merge structures into board
-rw-r--r-- | src/board.c | 82 | ||||
-rw-r--r-- | src/board.h | 32 | ||||
-rw-r--r-- | src/main.c | 43 |
3 files changed, 82 insertions, 75 deletions
diff --git a/src/board.c b/src/board.c index d885a8c..fdafd2d 100644 --- a/src/board.c +++ b/src/board.c @@ -1,34 +1,36 @@ #include <stdio.h> #include "board.h" -void print_board(char* board) { - for (int row = 0; row < BOARD_ROW_BYTES; row++) { - for (int i = 0; i < BOARD_ROW_BYTES; i++) { - int index = BOARD_ROW_BYTES * row + i; - if (board[index] == EMPTY && is_center_index(index)) printf("*"); - else printf("%c", board[index]); +void print_board(BoardUnit* board) { + for (int row = 0; row < BOARD_ROW_UNITS; row++) { + for (int i = 0; i < BOARD_ROW_UNITS; i++) { + int index = BOARD_ROW_UNITS * row + i; + if (board[index].feature == EMPTY && is_center_index(index)) printf("*"); + else printf("%c", board[index].feature); } printf("\n"); } } -void initialize_board(char* board) { - for (int i = 0; i < BOARD_BYTES; i++) { - board[i] = EMPTY; +void initialize_board(BoardUnit* board) { + for (int i = 0; i < BOARD_UNITS; i++) { + board[i].feature = EMPTY; + board[i].meeple = 0; + board[i].structure_group = 0; } } int is_center_index(int index) { - return ((index / BOARD_ROW_BYTES) % 2 == 1) && ((index % BOARD_ROW_BYTES) % 2 == 1); + return ((index / BOARD_ROW_UNITS) % 2 == 1) && ((index % BOARD_ROW_UNITS) % 2 == 1); } -int is_allowed_placement(Tile tile, int index, char* board) { - if (board[index] != EMPTY) return 0; +int is_allowed_placement(Tile tile, int index, BoardUnit* board) { + if (board[index].feature != EMPTY) return 0; int neighbor_count = 0; for (int i = 0; i < 4; i++) { - char neighbor = board[index + neighbor_increments[i]]; + char neighbor = board[index + neighbor_increments[i]].feature; if (neighbor != EMPTY) { if (neighbor != tile.edges[i]) return 0; neighbor_count++; @@ -38,7 +40,7 @@ int is_allowed_placement(Tile tile, int index, char* board) { return neighbor_count > 0; } -int place_tile(Tile tile, int index, char* board, int force) { +int place_tile(Tile tile, int index, BoardUnit* board, int force) { if (!is_center_index(index)) { printf("Not a valid tile index: %i\n", index); return 0; @@ -49,30 +51,32 @@ int place_tile(Tile tile, int index, char* board, int force) { return 0; } - board[index] = tile.center; + board[index].feature = tile.center; for (int i = 0; i < 4; i++) { - board[index + neighbor_increments[i]] = tile.edges[i]; + board[index + neighbor_increments[i]].feature = tile.edges[i]; } return 1; } -void traverse_structure(char id, int index, char* board, char* structures) { - structures[index] = id; +void traverse_structure(int group, int index, BoardUnit* board) { + board[index].structure_group = group; for (int i = 0; i < 4; i++) { - int new_byte = index + neighbor_increments[i]; - if (board[new_byte] == board[index] && structures[new_byte] == EMPTY) { - traverse_structure(id, new_byte, board, structures); + int new_unit = index + neighbor_increments[i]; + if (board[new_unit].feature == board[index].feature && board[new_unit].structure_group == 0) { + traverse_structure(group, new_unit, board); } } } -void create_structure_mask(char* board, char* structures) { - char structure_id = '1'; - for (int i = 0; i < BOARD_BYTES; i++) { - if (structures[i] == EMPTY && board[i] != EMPTY && board[i] != 'F') { - traverse_structure(structure_id, i, board, structures); - structure_id += 1; +void refresh_structure_groups(BoardUnit* board) { + for (int i = 0; i < BOARD_UNITS; i++) board[i].structure_group = 0; + + int structure_group = 1; + for (int i = 0; i < BOARD_UNITS; i++) { + if (board[i].structure_group == 0 && board[i].feature != EMPTY && board[i].feature != 'F') { + traverse_structure(structure_group, i, board); + structure_group += 1; } } } @@ -83,19 +87,19 @@ int translate_coordinate(int center_index) { (2 * (center_index % BOARD_WIDTH) + 1); } -int evaluate_structure(int index, char* board, char* structures) { +int evaluate_structure(int index, BoardUnit* board) { int value = 0; - char structure = board[index]; - char structure_id = structures[index]; - printf("Evaluating group %c (%c)\n", structure_id, structure); + char feature = board[index].feature; + int structure_group = board[index].structure_group; + printf("Evaluating group %i (%c)\n", structure_group, feature); for (int i = 0; i < BOARD_WIDTH; i++) { for (int j = 0; j < BOARD_WIDTH; j++) { int index = translate_coordinate(i * BOARD_WIDTH + j); - if (board[index] != EMPTY) { // Empty tiles doesn't count + if (board[index].feature != EMPTY) { // Empty tiles doesn't count for (int k = 0; k < 4; k++) { - if (structures[index + neighbor_increments[k]] == structure_id) { + if (board[index + neighbor_increments[k]].structure_group == structure_group) { printf("Found at tile %i\n", i * BOARD_WIDTH + j); value++; break; @@ -108,15 +112,3 @@ int evaluate_structure(int index, char* board, char* structures) { printf("Value: %i\n", value); return value; } - -void write_board(char* board, char* filename) { - FILE* file = fopen(filename, "w"); - fprintf(file, "%s\n", board); - fclose(file); -} - -void read_board(char* board, char* filename) { - FILE* file = fopen(filename, "r"); - fgets(board, BOARD_BYTES, file); - fclose(file); -} diff --git a/src/board.h b/src/board.h index 117d5b2..dc1995a 100644 --- a/src/board.h +++ b/src/board.h @@ -1,14 +1,14 @@ #define BOARD_WIDTH 7 -#define BOARD_ROW_BYTES ((BOARD_WIDTH * 2) + 1) -#define BOARD_BYTES BOARD_ROW_BYTES * BOARD_ROW_BYTES +#define BOARD_ROW_UNITS ((BOARD_WIDTH * 2) + 1) +#define BOARD_UNITS BOARD_ROW_UNITS * BOARD_ROW_UNITS char EMPTY = ' '; int neighbor_increments[] = { - - BOARD_ROW_BYTES, + - BOARD_ROW_UNITS, 1, - BOARD_ROW_BYTES, + BOARD_ROW_UNITS, - 1 }; @@ -20,19 +20,25 @@ typedef struct { int shield; } Tile; +typedef struct { + char feature; + int meeple; + int structure_group; +} BoardUnit; + /* board */ -void initialize_board(char* board); -void print_board(char* board); -void write_board(char* board, char* filename); -void read_board(char* board, char* filename); +void initialize_board(BoardUnit* board); +void print_board(BoardUnit* board); +void write_board(BoardUnit* board, char* filename); +void read_board(BoardUnit* board, char* filename); /* moves */ -int is_allowed_placement(Tile tile, int index, char* board); +int is_allowed_placement(Tile tile, int index, BoardUnit* board); int translate_coordinate(int index); int is_center_index(int index); -int place_tile(Tile tile, int index, char* board, int force); +int place_tile(Tile tile, int index, BoardUnit* board, int force); /* structures */ -void traverse_structure(char id, int index, char* board, char* structures); -void create_structure_mask(char* board, char* structures); -int evaluate_structure(int index, char* board, char* structures); +void traverse_structure(int group, int index, BoardUnit* board); +void refresh_structure_groups(BoardUnit* board); +int evaluate_structure(int index, BoardUnit* board); @@ -3,13 +3,24 @@ #include <curses.h> #include "board.h" -void draw_board(char* board, WINDOW* win) { +void draw_board(BoardUnit* board, WINDOW* win) { wmove(win, 0, 0); - for (int row = 0; row < BOARD_ROW_BYTES; row++) { - for (int i = 0; i < BOARD_ROW_BYTES; i++) { - int index = BOARD_ROW_BYTES * row + i; - if (board[index] == EMPTY && is_center_index(index)) waddch(win, '*'); - else waddch(win, board[index]); + for (int row = 0; row < BOARD_ROW_UNITS; row++) { + for (int i = 0; i < BOARD_ROW_UNITS; i++) { + int index = BOARD_ROW_UNITS * row + i; + if (board[index].feature == EMPTY && is_center_index(index)) waddch(win, '*'); + else waddch(win, board[index].feature); + } + } +} + +void draw_structures(BoardUnit* board, WINDOW* win) { + wmove(win, 0, 0); + for (int row = 0; row < BOARD_ROW_UNITS; row++) { + for (int i = 0; i < BOARD_ROW_UNITS; i++) { + int index = BOARD_ROW_UNITS * row + i; + if (board[index].feature == EMPTY && is_center_index(index)) waddch(win, '*'); + else waddch(win, board[index].structure_group == 0 ? ' ' : '0' + board[index].structure_group); } } } @@ -20,32 +31,31 @@ int main() { cbreak(); /* create board window */ - WINDOW* board_box = newwin(BOARD_ROW_BYTES + 2, BOARD_ROW_BYTES + 2, 0, 0); - WINDOW* board_win = derwin(board_box, BOARD_ROW_BYTES, BOARD_ROW_BYTES, 1, 1); + WINDOW* board_box = newwin(BOARD_ROW_UNITS + 2, BOARD_ROW_UNITS + 2, 0, 0); + WINDOW* board_win = derwin(board_box, BOARD_ROW_UNITS, BOARD_ROW_UNITS, 1, 1); box(board_box, 0, 0); wrefresh(board_box); /* create structures window */ - WINDOW* structures_box = newwin(BOARD_ROW_BYTES + 2, BOARD_ROW_BYTES + 2, 0, BOARD_ROW_BYTES + 3); - WINDOW* structures_win = derwin(structures_box, BOARD_ROW_BYTES, BOARD_ROW_BYTES, 1, 1); + WINDOW* structures_box = newwin(BOARD_ROW_UNITS + 2, BOARD_ROW_UNITS + 2, 0, BOARD_ROW_UNITS + 3); + WINDOW* structures_win = derwin(structures_box, BOARD_ROW_UNITS, BOARD_ROW_UNITS, 1, 1); box(structures_box, 0, 0); wrefresh(structures_box); /* create input window */ - WINDOW* input_box = newwin(3, 22, BOARD_ROW_BYTES + 3, 0); + WINDOW* input_box = newwin(3, 22, BOARD_ROW_UNITS + 3, 0); WINDOW* input_win = derwin(input_box, 1, 20, 1, 1); box(input_box, 0, 0); wrefresh(input_box); /* create messages window */ - WINDOW* messages_box = newwin(40, 60, BOARD_ROW_BYTES + 6, 0); + WINDOW* messages_box = newwin(40, 60, BOARD_ROW_UNITS + 6, 0); WINDOW* messages_win = derwin(messages_box, 40 - 2, 60 - 2, 1, 1); box(messages_box, 0, 0); wrefresh(messages_box); - char board[BOARD_BYTES]; - char structures[BOARD_BYTES]; + BoardUnit board[BOARD_UNITS]; initialize_board(board); Tile tile = { "FRCR", 'R', 0 }; @@ -56,13 +66,12 @@ int main() { while (1) { /* prepare */ - initialize_board(structures); - create_structure_mask(board, structures); + refresh_structure_groups(board); wclear(input_win); /* draw onto the screen */ draw_board(board, board_win); - draw_board(structures, structures_win); + draw_structures(board, structures_win); wrefresh(board_win); wrefresh(structures_win); |