From 5e06151e84e741c3e5367d2aa87e34f7ad59a25b Mon Sep 17 00:00:00 2001 From: Andrew Haynes Date: Thu, 26 Feb 2026 15:46:54 -0500 Subject: [PATCH] i forgot about goto until gemini reshowed me --- CMakeLists.txt | 3 - src/main.c | 155 ++++++++++++++++++++++--------------------------- 2 files changed, 69 insertions(+), 89 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 7e87daf..a2a1751 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -1,5 +1,4 @@ cmake_minimum_required(VERSION 3.16) -set(CMAKE_EXPORT_COMPILE_COMMANDS ON) set(CMAKE_C_STANDARD 23) set(CMAKE_C_STANDARD_REQUIRED ON) set(CMAKE_EXPORT_COMPILE_COMMANDS ON) @@ -10,5 +9,3 @@ set(SOURCES ) add_executable(tic_tac_toe ${SOURCES}) - -target_include_directories(tic_tac_toe PRIVATE include) diff --git a/src/main.c b/src/main.c index d0ce1d5..70853ac 100644 --- a/src/main.c +++ b/src/main.c @@ -1,118 +1,101 @@ -#include #include #include #include #include const char p1 = 'x', p2 = 'o'; -char temp = p1; -char status[32]; -char buf[9]; +char temp = 'x'; +char buf[9] = { " " }; +static const unsigned char wins[8][3] = { { 0, 1, 2 }, { 3, 4, 5 }, { 6, 7, 8 }, + { 0, 3, 6 }, { 1, 4, 7 }, { 2, 5, 8 }, + { 0, 4, 8 }, { 2, 4, 6 } }; -bool +int check_line(const char id) { - const int wins[8][3] = { { 0, 1, 2 }, { 3, 4, 5 }, { 6, 7, 8 }, - { 0, 3, 6 }, { 1, 4, 7 }, { 2, 5, 8 }, - { 0, 4, 8 }, { 2, 4, 6 } }; for (int i = 0; i < sizeof(wins) / sizeof(wins[0]); i++) { if ((buf[wins[i][0]] == id && buf[wins[i][1]] == id && buf[wins[i][2]] == id)) { - return true; + return 1; } } - return false; + return 0; } void -set_raw_mode(bool enable) +draw_board() { - static struct termios oldt, newt; - if (enable) + char divider[] = " - + - + -\n"; + write(1, "\033[H\033[J", sizeof("\033[H\033[J") - 1); + for (int i = 0; i < 9; i += 3) { - tcgetattr(STDIN_FILENO, &oldt); - newt = oldt; - newt.c_lflag &= ~(ICANON | ECHO); - tcsetattr(STDIN_FILENO, TCSANOW, &newt); + char row[] = " 0 | 0 | 0\n"; + row[1] = buf[i]; + row[5] = buf[i + 1]; + row[9] = buf[i + 2]; + write(1, row, sizeof(row) - 1); + if (i < 6) write(1, divider, sizeof(divider) - 1); } - else - { - tcsetattr(STDIN_FILENO, TCSANOW, &oldt); - } -} - -bool -update_status() -{ - auto p1_check = check_line(p1); - auto p2_check = check_line(p2); - if (p1_check || p2_check) - { - (p1_check ? (void)strncpy(status, "Game Over! Player 1 wins!\n", - sizeof(status)) - : (void)strncpy(status, "Game Over! Player 2 wins!\n", - sizeof(status))); - return true; - } - int count = 0; - for (int i = 0; i < sizeof(buf) / sizeof(buf[0]); i++) - { - if (buf[i] != ' ') count++; - } - if (count == sizeof(buf) / sizeof(buf[0])) - { - (void)strncpy(status, "Game Over! It's a tie!\n", - sizeof(status)); - return true; - } - snprintf(status, sizeof(status), "Current Player: %c\n", temp); - - return false; -} - -bool -process_input() -{ - char ch; - while (read(STDIN_FILENO, &ch, 1)) - { - if (ch == 'q') return false; - if (ch < '1' || ch > '9') continue; - int index = ch - '1'; - if (buf[index] != ' ') continue; - buf[index] = temp; - temp = (temp == p1) ? p2 : p1; - return true; - } - return true; + write(1, "Current Player: ", 16); + write(1, &temp, 1); + write(1, "\n", 1); } int main() { - bool game_over; - for (int i = 0; i < sizeof(buf) / sizeof(buf[0]); i++) buf[i] = ' '; - - set_raw_mode(true); - printf("\033[?25l"); - do + static struct termios oldt, newt; + tcgetattr(STDIN_FILENO, &oldt); + newt = oldt; + newt.c_lflag &= ~(ICANON | ECHO); + tcsetattr(STDIN_FILENO, TCSANOW, &newt); + write(1, "\033[?25l", sizeof("\033[?25l") - 1); + while (1) { - game_over = update_status(); - printf("\033[H\033[J"); - printf(" %c | %c | %c\n", buf[0], buf[1], buf[2]); - printf(" - + - + -\n"); - printf(" %c | %c | %c\n", buf[3], buf[4], buf[5]); - printf(" - + - + -\n"); - printf(" %c | %c | %c\n", buf[6], buf[7], buf[8]); - printf("%s", status); - fflush(stdout); - } while (!game_over && process_input()); - printf("Press any key to quit.\n"); + if (check_line(p1)) + { + break; + } + if (check_line(p2)) + { + write(1, "P2 wins!\n", sizeof("P2 wins!\n") - 1); + break; + } + int filled = 0; + while (filled < 9) + { + draw_board(); + char ch; + read(0, &ch, 1); + if (ch == 'q') break; + int idx = ch - '1'; + if (ch >= '1' && ch <= '9' && buf[idx] == ' ') + { + buf[idx] = temp; + if (check_line(temp)) + { + draw_board(); + write(1, &temp, 1); + write(1, " wins!\n", + sizeof(" wins!\n") - 1); + goto end; + } + temp = (temp == p1) ? p2 : p1; + filled++; + } + } + write(1, "It's a tie!\n", sizeof("It's a tie!\n") - 1); + break; + } +end: + write(1, "Press any key to quit.\n", + sizeof("Press any key to quit.\n") - 1); char dummy; read(STDIN_FILENO, &dummy, 1); - printf("\033[?25h"); - set_raw_mode(false); + write(1, "\033[?25h", 5); + tcsetattr(STDIN_FILENO, TCSANOW, &oldt); + return 0; }