1115e92d82563ac0e795ba8d1d633c81d48f2004
[Project_algorithmic_C.git] / lib / othello.c
1 /*
2 * =====================================================================================
3 *
4 * Filename: othello.c
5 *
6 * Description: Handle the othello board content
7 *
8 * Version: 1.0
9 * Created: 25/04/2017 15:16:08
10 * Revision: none
11 * Compiler: gcc
12 *
13 * Author: Jerome Benoit (fraggle), jerome.benoit@piment-noir.org
14 * Organization: Piment Noir
15 *
16 * =====================================================================================
17 */
18
19 #include <stdlib.h>
20 #include <stdbool.h>
21
22 #include "othello.h"
23
24 unsigned int current_player(unsigned int round_count) {
25
26 if (round_count % 2 != 0) {
27 return player_two;
28 } else {
29 return player_one;
30 }
31 }
32
33 /* for consitency with ncurses, the board coordinates are in the following order:
34 * O--x-->
35 * |
36 * y
37 * |
38 * v
39 * The origin O has (1, 1) coordinates */
40
41 unsigned int get_box_value(int y, int x, unsigned int pawn_array[board_size][board_size]) {
42
43 return pawn_array[y-1][x-1];
44 }
45
46 bool is_box_type(int y, int x, unsigned int pawn_array[board_size][board_size], unsigned int type) {
47
48 if (type > 2) {
49 return NULL;
50 }
51 if (get_box_value(y, x, pawn_array) == type) {
52 return true;
53 } else {
54 return false;
55 }
56 }
57
58 /* helper function to set a value != empty at the (y, x) coordinates in the pawns array */
59 int** set_pawn(int y, int x, unsigned int type, unsigned int pawn_array[board_size][board_size]) {
60
61 if (is_box_type(y, x, pawn_array, empty)) {
62 pawn_array[y-1][x-1] = type;
63 return (int**)pawn_array;
64 } else {
65 return NULL;
66 }
67 }
68
69 static int** zero_pawns(unsigned int pawn_array[board_size][board_size]) {
70
71 for (unsigned int i = 1; i <= board_size; i++) {
72 for (unsigned int j = 1; j <= board_size; j++) {
73 pawn_array = set_pawn(i, j, empty, pawn_array);
74 }
75 }
76 return (int**)pawn_array;
77 }
78
79 /* set the pawns in the start position */
80 int** init_pawns(unsigned int pawn_array[board_size][board_size]) {
81
82 pawn_array = zero_pawns(pawn_array);
83 pawn_array = set_pawn(5, 4, black, pawn_array);
84 pawn_array = set_pawn(4, 5, black, pawn_array);
85 pawn_array = set_pawn(4, 4, white, pawn_array);
86 pawn_array = set_pawn(5, 5, white, pawn_array);
87 return (int**)pawn_array;
88 }
89
90 unsigned int count_pawn_type(unsigned int pawn_array[board_size][board_size], unsigned int type) {
91 unsigned int count = 0;
92
93 if (type > 2) {
94 return -1;
95 }
96 for (unsigned int i = 1; i <= board_size; i++) {
97 for (unsigned int j = 1; j <= board_size; j++) {
98 if (is_box_type(i, j, pawn_array, type)) {
99 count++;
100 }
101 }
102 }
103 return count;
104 }
105
106 bool is_valid_input(int y, int x, unsigned int pawn_array[board_size][board_size]) {
107
108 /* FIXME: separate the tests to permit to print explicit error messages */
109 if ((y > 0 && y < board_size + 1) && \
110 (x > 0 && x < board_size + 1) && \
111 is_box_type(y, x, pawn_array, empty)) {
112 return true;
113 } else {
114 return false;
115 }
116 }
117
118 bool is_board_full(unsigned int pawn_array[board_size][board_size]) {
119
120 /* an alternate method is to test the round count vs. 60 */
121 for (unsigned int i = 1; i <= board_size; i++) {
122 for (unsigned int j = 1; j <= board_size; j++) {
123 if (is_box_type(i, j, pawn_array , empty)) {
124 return false;
125 }
126 }
127 }
128 return true;
129 }
130
131 unsigned int eval_winner(unsigned int nb_white, unsigned int nb_black) {
132
133 if (nb_white > nb_black) {
134 return player_two;
135 } else if (nb_white < nb_black) {
136 return player_one;
137 } else {
138 return 0;
139 }
140 }
141
142 void direction_to_coordinates(unsigned int direction, int* start_y, int* start_x) {
143
144 if (direction == north) {
145 *start_y = *start_y - 1;
146 } else if (direction == north_east) {
147 *start_y = *start_y - 1;
148 *start_x = *start_x + 1;
149 } else if (direction == east) {
150 *start_x = *start_x + 1;
151 } else if (direction == south_east) {
152 *start_y = *start_y + 1;
153 *start_x = *start_x + 1;
154 } else if (direction == south) {
155 *start_y = *start_y + 1;
156 } else if (direction == south_west) {
157 *start_y = *start_y + 1;
158 *start_x = *start_x - 1;
159 } else if (direction == west) {
160 *start_x = *start_x - 1;
161 } else if (direction == north_west) {
162 *start_y = *start_y - 1;
163 *start_x = *start_x - 1;
164 }
165 }
166
167 bool explore(int y, int x, int direction) {
168
169 }