-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge develop branch into Master branch - Release v1.1.0 (#5)
- Loading branch information
Showing
116 changed files
with
57,713 additions
and
406 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -51,7 +51,6 @@ obj/ | |
*.lo | ||
|
||
# Shared objects (inc. Windows DLLs) | ||
*.dll | ||
*.so | ||
*.so.* | ||
*.dylib | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,71 @@ | ||
|
||
#ifndef GAME_MACROS_H_INCLUDED | ||
#define GAME_MACROS_H_INCLUDED | ||
|
||
/** | ||
* @def DASHBOARD_ROWS | ||
* @brief Defines the number of rows in a grid. | ||
* | ||
* This macro is used to define the number of rows in a grid. | ||
* It is typically used in conjunction with the `DASHBOARD_COLS` macro to define | ||
* the size of a grid. | ||
* | ||
* @warning The value of `DASHBOARD_ROWS` must be a positive integer. | ||
*/ | ||
#define DASHBOARD_ROWS 56 | ||
|
||
/** | ||
* @def DASHBOARD_COLS | ||
* @brief Defines the number of columns in a grid. | ||
* | ||
* This macro is used to define the number of columns in a grid. | ||
* It is typically used in conjunction with the `DASHBOARD_ROWS` macro to define | ||
* the size of a grid. | ||
* | ||
* @warning The value of `DASHBOARD_COLS` must be a positive integer. | ||
*/ | ||
#define DASHBOARD_COLS 110 | ||
|
||
/** | ||
* @def ALIVE_CELL | ||
* @brief Represents a live cell. | ||
* | ||
* @warning The value of `ALIVE_CELL` must be a single character. | ||
*/ | ||
#define ALIVE_CELL 'o' | ||
|
||
/** | ||
* @def ALIVE_CELL_NG | ||
* @brief Represents a cell that is going to be alive in the next generation. | ||
* | ||
* @warning The value of `ALIVE_CELL_NG` must be a single character and must not be equal to | ||
* `ALIVE_CELL`, `DEAD_CELL`, or `DEAD_CELL_NG` macros. | ||
*/ | ||
#define ALIVE_CELL_NG '1' | ||
|
||
/** | ||
* @def DEAD_CELL | ||
* @brief Represents a dead cell. | ||
* | ||
* @warning The value of `DEAD_CELL` must be a single character. | ||
*/ | ||
#define DEAD_CELL ' ' | ||
|
||
/** | ||
* @def DEAD_CELL_NG | ||
* @brief Represents a cell that is going to be dead in the next generation. | ||
* | ||
* @warning The value of `DEAD_CELL_NG` must be a single character and must not be equal to | ||
* `ALIVE_CELL`, `ALIVE_CELL_NG`, or `DEAD_CELL` macros. | ||
*/ | ||
#define DEAD_CELL_NG '0' | ||
|
||
/** | ||
* @def NEIGHBORHOOD_RADIUS | ||
* @brief Defines the radius of the neighborhood. | ||
* | ||
* @warning The value of `NEIGHBORHOOD_RADIUS` must be greater or equal to 1. | ||
*/ | ||
#define NEIGHBORHOOD_RADIUS 1 | ||
|
||
#endif // GAME_MACROS_H_INCLUDED |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,10 @@ | ||
|
||
#ifndef GAME_MAIN_H_INCLUDED | ||
#define GAME_MAIN_H_INCLUDED | ||
|
||
// Root | ||
#include "./macros.h" | ||
#include "./methods.h" | ||
#include "./structs.h" | ||
|
||
#endif // GAME_MAIN_H_INCLUDED |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,233 @@ | ||
|
||
#include "./methods.h" | ||
|
||
#include <limits.h> | ||
#include <stdio.h> | ||
|
||
#include "../patterns/main.h" | ||
#include "./macros.h" | ||
#include "./structs.h" | ||
|
||
int countAliveNeighbors(TGame* pGame, int cellRow, int cellCol, int radius) { | ||
int i; | ||
int j; | ||
|
||
int startRow = cellRow - radius; | ||
int startCol = cellCol - radius; | ||
|
||
int endRow = cellRow + radius + 1; | ||
int endCol = cellCol + radius + 1; | ||
|
||
int aliveNeighbors = 0; | ||
|
||
for (i = startRow; i < endRow; i++) { | ||
if (i > pGame->rows - 1) break; | ||
if (i < 0) continue; | ||
|
||
for (j = startCol; j < endCol; j++) { | ||
if (j > pGame->cols - 1) break; | ||
if (j < 0) continue; | ||
|
||
if (i == cellRow && j == cellCol) continue; | ||
|
||
if (pGame->dashboard[i][j] == ALIVE_CELL || pGame->dashboard[i][j] == DEAD_CELL_NG) | ||
aliveNeighbors++; | ||
} | ||
} | ||
|
||
return aliveNeighbors; | ||
} | ||
|
||
void drawPattern(TGame* pGame, char* pattern) { | ||
TPattern SPattern; | ||
|
||
char arr[PATTERN_ROWS][PATTERN_COLS]; | ||
|
||
SPattern.arr = arr; | ||
|
||
fillDashboard(pGame, DEAD_CELL); | ||
|
||
if (strcmpi(pattern, "glider") == 0) { | ||
newGliderPattern(&SPattern); | ||
pGame->cellsAlive = 5; | ||
} else if (strcmpi(pattern, "glider cannon") == 0) { | ||
newGliderCannonPattern(&SPattern); | ||
pGame->cellsAlive = 36; | ||
} else if (strcmpi(pattern, "press") == 0) { | ||
newPressPattern(&SPattern); | ||
pGame->cellsAlive = 48; | ||
} else if (strcmpi(pattern, "toad") == 0) { | ||
newToadPattern(&SPattern); | ||
pGame->cellsAlive = 6; | ||
} else { | ||
return; | ||
} | ||
|
||
pGame->cellsDead = (pGame->cols * pGame->rows) - pGame->cellsAlive; | ||
pGame->generation = 0; | ||
|
||
drawPatternInDashboard(pGame, &SPattern); | ||
} | ||
|
||
void drawPatternInDashboard(TGame* pGame, TPattern* pPattern) { | ||
int i; | ||
int j; | ||
|
||
int pI = 0; | ||
int pJ = 0; | ||
|
||
int startRow = pGame->center[0] - pPattern->center[0]; | ||
int startCol = pGame->center[1] - pPattern->center[1]; | ||
|
||
for (i = startRow; pI < pPattern->rows; i++) { | ||
if (i < 0) continue; | ||
if (i > pGame->rows - 1) break; | ||
|
||
for (j = startCol; pJ < pPattern->cols; j++) { | ||
if (j < 0) continue; | ||
if (j > pGame->cols - 1) break; | ||
|
||
pGame->dashboard[i][j] = pPattern->arr[pI][pJ]; | ||
pJ++; | ||
}; | ||
|
||
pJ = 0; | ||
pI++; | ||
} | ||
} | ||
|
||
void fillDashboard(TGame* pGame, char with) { | ||
int i; | ||
int j; | ||
|
||
for (i = 0; i < pGame->rows; i++) { | ||
for (j = 0; j < pGame->cols; j++) { | ||
pGame->dashboard[i][j] = with; | ||
} | ||
} | ||
} | ||
|
||
void generateNextGeneration(TGame* pGame) { | ||
int i; | ||
int j; | ||
|
||
int aliveNeighbors; | ||
|
||
for (i = 0; i < pGame->rows; i++) { | ||
for (j = 0; j < pGame->cols; j++) { | ||
aliveNeighbors = countAliveNeighbors(pGame, i, j, NEIGHBORHOOD_RADIUS); | ||
|
||
if (pGame->dashboard[i][j] == DEAD_CELL) { | ||
if (aliveNeighbors == 3) { | ||
pGame->cellsDead--; | ||
pGame->cellsAlive++; | ||
pGame->dashboard[i][j] = ALIVE_CELL_NG; | ||
}; | ||
|
||
continue; | ||
} | ||
|
||
if (aliveNeighbors < 2 || aliveNeighbors > 3) { | ||
pGame->cellsAlive--; | ||
pGame->cellsDead++; | ||
pGame->dashboard[i][j] = DEAD_CELL_NG; | ||
}; | ||
} | ||
} | ||
|
||
for (i = 0; i < pGame->rows; i++) { | ||
for (j = 0; j < pGame->cols; j++) { | ||
if (pGame->dashboard[i][j] == DEAD_CELL_NG) { | ||
pGame->dashboard[i][j] = DEAD_CELL; | ||
continue; | ||
} | ||
|
||
if (pGame->dashboard[i][j] == ALIVE_CELL_NG) pGame->dashboard[i][j] = ALIVE_CELL; | ||
} | ||
} | ||
} | ||
|
||
void printDashboardByConsole(TGame* pGame) { | ||
int i; | ||
int j; | ||
|
||
for (i = 0; i < pGame->rows; i++) { | ||
printf("\n"); | ||
|
||
for (j = 0; j < pGame->cols; j++) { | ||
printf("%c", pGame->dashboard[i][j]); | ||
} | ||
} | ||
} | ||
|
||
void printGameByConsole(TGame* pGame) { | ||
int i; | ||
int j; | ||
|
||
// Print header | ||
for (i = 0; i < pGame->cols + 2; i++) printf("-"); | ||
|
||
printf("\n| Cells alive: %*d |", pGame->cols - 17 + 2, pGame->cellsAlive); | ||
printf("\n| Cells dead: %*d |", pGame->cols - 16 + 2, pGame->cellsDead); | ||
printf("\n| Generation: %*d |", pGame->cols - 16 + 2, pGame->generation); | ||
|
||
if (pGame->maximumGeneration == INT_MAX) { | ||
printf("\n| Maximum generation: %*s |", pGame->cols - 25 + 3, "infinity"); | ||
} else { | ||
printf("\n| Maximum generation: %*d |", pGame->cols - 25 + 3, pGame->maximumGeneration); | ||
} | ||
|
||
printf("\n| Delay between generations: %*d ms |\n", pGame->cols - 35 + 3, | ||
pGame->delayBetweenGenerations); | ||
|
||
// Print dashboard | ||
for (i = 0; i < pGame->cols + 2; i++) printf("-"); | ||
|
||
for (i = 0; i < pGame->rows; i++) { | ||
printf("\n|"); | ||
|
||
for (j = 0; j < pGame->cols; j++) { | ||
printf("%c", pGame->dashboard[i][j]); | ||
} | ||
|
||
printf("|"); | ||
} | ||
|
||
printf("\n"); | ||
for (i = 0; i < pGame->cols + 2; i++) printf("-"); | ||
} | ||
|
||
void setDashboardCenter(TGame* pGame) { | ||
int row = pGame->rows / 2; | ||
int col = pGame->cols / 2; | ||
|
||
pGame->center[0] = row; | ||
pGame->center[1] = col; | ||
} | ||
|
||
void startGameByConsole(TGame* pGame, int maxGeneration, int delayBetweenGenerations) { | ||
int generation = 0; | ||
int isToInfinity = maxGeneration == INT_MAX; | ||
|
||
pGame->generation = 0; | ||
pGame->maximumGeneration = maxGeneration; | ||
pGame->delayBetweenGenerations = delayBetweenGenerations; | ||
|
||
system("cls"); | ||
printGameByConsole(pGame); | ||
if (generation == maxGeneration) return; | ||
sleep(delayBetweenGenerations); | ||
|
||
while (isToInfinity || generation < maxGeneration) { | ||
generateNextGeneration(pGame); | ||
|
||
if (generation != INT_MAX) { | ||
generation++; | ||
pGame->generation = generation; | ||
}; | ||
|
||
system("cls"); | ||
printGameByConsole(pGame); | ||
if (generation != maxGeneration) sleep(delayBetweenGenerations); | ||
} | ||
} |
Oops, something went wrong.