From 4f312d72b15a48ab42eea1c6d35392eeca7c182e Mon Sep 17 00:00:00 2001
From: "dario.genga" <dario.genga@etu.hesge.ch>
Date: Tue, 21 Dec 2021 14:07:24 +0100
Subject: [PATCH] Add manual play and fix display errors

The display generated a SIGABRT error after multiple print, because the
display string wasn't cleared.

The manual play doesn't use the program arguments yet.
---
 main.c      | 19 +++++++++++++++++++
 puissance.c | 42 +++++++++++++++++++++++++++++++++++++-----
 puissance.h |  6 ++++--
 3 files changed, 60 insertions(+), 7 deletions(-)

diff --git a/main.c b/main.c
index ae79ccc..85f11ce 100644
--- a/main.c
+++ b/main.c
@@ -12,6 +12,25 @@ int main() {
 
     game_init(&game, RAND_AI, DEFAULT_ROW, DEFAULT_COL);
     print_game(game);
+    print_game(game);
+    manual_play(&game, 0);
+    print_game(game);
+    manual_play(&game, 4);
+    print_game(game);
+    manual_play(&game, 0);
+    print_game(game);
+    manual_play(&game, -1);
+    print_game(game);
+    manual_play(&game, 9);
+    print_game(game);
+    manual_play(&game, 0);
+    manual_play(&game, 0);
+    manual_play(&game, 0);
+    manual_play(&game, 0);
+    print_game(game);
+    manual_play(&game, 0);
+    manual_play(&game, 1);
+    print_game(game);
 
     game_destroy(&game);
     
diff --git a/puissance.c b/puissance.c
index fd0eb3e..18f0285 100644
--- a/puissance.c
+++ b/puissance.c
@@ -21,14 +21,14 @@ void game_init(puissance *p, GameMode mode, int row, int col) {
     // Set a default value for the data
     for (int r = 0; r < row; r++) {
         for (int c = 0; c < col; c++) {
-            p->data[r][c] = -1;
+            p->data[r][c] = EMPTY_CELL_VALUE;
         }
     }
 }
 
 void print_top(char *display, int col) {
     // Print top
-    strcat(display, "ā”Œ");
+    strcat(display, "\nā”Œ");
     for (int i = 1; i <= col * 2 - 1; i++) {
         if (i % 2 == 1) {
             strcat(display, "─");
@@ -58,6 +58,7 @@ void print_bot(char *display, int col) {
         strcat(display, " ");
         strcat(display, i_has_string);
     }
+    strcat(display, "\n");
 }
 
 void print_row_separator(char *display, int col) {
@@ -107,17 +108,48 @@ void print_game(puissance p) {
 
     // Print the bottom then display the game
     print_bot(display, p.col);
-    printf("%s\n", display);
+    printf("%s", display);
+    // Clear the string to avoid SIGABRT
+    display[0] = '\0';
 }
 
 void verify_game(puissance p) {
 
 }
 
+int get_available_row_index(puissance *p, int selected_col_index) {
+    // Verify the index selected
+    if (selected_col_index >= p->col || selected_col_index < 0) {
+        return EMPTY_CELL_VALUE;
+    }
+
+    for (int i = p->row - 1; i >= 0; i--) {
+        if (p->data[i][selected_col_index] == EMPTY_CELL_VALUE) {
+            return i;
+        }
+    }
+    return EMPTY_CELL_VALUE;
+}
+
 bool manual_play(puissance *p, int selected_col_index) {
-    bool valid_action = true;
+    // Get the available row index and verify that the column is not full.
+    int row_index = get_available_row_index(p, selected_col_index);
+    if (row_index == EMPTY_CELL_VALUE) {
+        return false;
+    }
 
-    return valid_action;
+    // Play
+    p->data[row_index][selected_col_index] = p->current_player;
+
+    // Switch the current player
+    if (p->current_player == PLAYER_ONE) {
+        p->current_player = PLAYER_TWO;
+    } else {
+        p->current_player = PLAYER_ONE;
+    }
+
+    // Valid the action
+    return true;
 }
 
 bool random_play(puissance *p) {
diff --git a/puissance.h b/puissance.h
index af9ea04..4a56ade 100644
--- a/puissance.h
+++ b/puissance.h
@@ -13,8 +13,9 @@
 #define COL_MIN 4
 #define DEFAULT_ROW 6
 #define DEFAULT_COL 7
-#define PLAYER_ONE_STRING "O"
-#define PLAYER_TWO_STRING "X"
+#define PLAYER_ONE_STRING "X"
+#define PLAYER_TWO_STRING "O"
+#define EMPTY_CELL_VALUE -1
 
 typedef enum {
     RAND_AI,
@@ -45,6 +46,7 @@ typedef struct _puissance {
 void game_init(puissance *p, GameMode mode, int row, int col);
 void print_game(puissance p);
 void verify_game(puissance p);
+int get_available_row_index(puissance *p, int selected_col_index);
 bool manual_play(puissance *p, int selected_col_index);
 bool random_play(puissance *p);
 bool smart_play(puissance *p);
-- 
GitLab