mazegame/main.c
2022-05-29 10:17:23 +02:00

317 lines
10 KiB
C

#include <stdio.h>
#include <stdlib.h>
#include <time.h>
#include <stdint.h>
#include <ncurses.h>
#include <unistd.h>
#include <math.h>
uint16_t Hole_Div = 40;
uint16_t SCR_X;
uint16_t SCR_Y;
#define FPS (60)
char blank_char = 32;
char wall_char = 35;
char goal_char = 71;
char player_char = 80;
char bullet_char = 120;
char inchar = ' ';
uint16_t blank_color = 0;
uint16_t wall_color = 1;
uint16_t goal_color = 2;
uint16_t player_color = 3;
uint16_t border_color = 4;
uint16_t bullet1_color = 5;
uint16_t bullet2_color = 5;
char letter = ' ';
struct Object {
uint16_t x;
uint16_t y;
char letter;
uint16_t color;
uint8_t dir;
};
struct Bullet {
uint16_t x;
uint16_t y;
uint8_t dir;
uint8_t color;
};
uint16_t bulletptr = 0;
uint16_t player_x = 0;
uint16_t player_y = 0;
uint16_t goal_x = 0;
uint16_t goal_y = 0;
uint16_t rng_tmp = 0;
uint16_t orient = 0;
uint16_t inputs_tmp = 0;
struct Object *rendered;
struct Bullet *bullets;
char *playfield;
int randomInt(int lower, int upper) {
return rand() % (upper - lower + 1) + lower;
}
void generate_maze(){
//fill playfield with blank
for (uint16_t y = 0; y < SCR_Y; y++) {
for (uint16_t x = 0; x < SCR_X; x++) {
//playfield[y][x] = blank_char;
//do it in one dimension
playfield[y*SCR_X + x] = blank_char;
}
}
//fill every other row with walls
for (uint16_t y = 0; y < SCR_Y; y += 2) {
for (uint16_t x = 0; x < SCR_X; x++) {
//playfield[y][x] = wall_char;
//do it in one dimension
playfield[y*SCR_X + x] = wall_char;
}
}
//punch holes in the walls
for (uint16_t y = 0; y < SCR_Y; y++) {
//punch holes in the walls depending on the SCR_X
for (uint16_t ix = 0; ix < ((SCR_X-(SCR_X%Hole_Div))/Hole_Div); ix += 1) {
rng_tmp = randomInt(1, SCR_X);
//playfield[y][rng_tmp] = blank_char;
//do it in one dimension
playfield[y*SCR_X + rng_tmp] = blank_char;
}
if (orient == 0) {
if(y == 0){
//playfield[y][rng_tmp] = goal_char;
//do it in one dimension
playfield[y*SCR_X + rng_tmp] = goal_char;
goal_x = rng_tmp;
goal_y = y;
}
if (y == SCR_Y -1){
//playfield[y][rng_tmp] = player_char;
//do it in one dimension
playfield[y*SCR_X + rng_tmp] = player_char;
player_x = rng_tmp;
player_y = y;
}
} else {
if(y == SCR_Y -1){
//playfield[y][rng_tmp] = goal_char;
//do it in one dimension
playfield[y*SCR_X + rng_tmp] = goal_char;
goal_x = rng_tmp;
goal_y = y;
}
if (y == 0){
//playfield[y][rng_tmp] = player_char;
//do it in one dimension
playfield[y*SCR_X + rng_tmp] = player_char;
player_x = rng_tmp;
player_y = y;
}
}
}
}
void render_maze(){
//fill rendered with blank
for (uint16_t y = 0; y < SCR_Y; y++) {
for (uint16_t x = 0; x < SCR_X; x++) {
//rendered[y][x] = blank_char;
//do it in one dimension
rendered[y*SCR_X + x].letter = blank_char;
rendered[y*SCR_X + x].color = blank_color;
rendered[y*SCR_X + x].x = x;
rendered[y*SCR_X + x].y = y;
}
}
for (uint16_t y = 0; y < SCR_Y; y++) {
for (uint16_t x = 0; x < SCR_X; x++) {
//letter = playfield[y - 1][x- 1];
//do it in one dimension
letter = playfield[(y)*SCR_X + (x)];
//rendered[x][y].letter = letter;
//do it in one dimension
rendered[(y)*SCR_X + (x)].letter = letter;
//rendered[x][y].x = x;
//do it in one dimension
rendered[(y)*SCR_X + (x)].x = x;
//rendered[x][y].y = y;
//do it in one dimension
rendered[(y)*SCR_X + (x)].y = y;
if (letter == goal_char){
//rendered[x][y].color = goal_color;
//do it in one dimension
rendered[(y)*SCR_X + (x)].color = goal_color;
}
else if (letter == player_char){
//rendered[x][y].color = player_color;
//do it in one dimension
rendered[(y)*SCR_X + (x)].color = player_color;
}
else if (letter == blank_char){
//rendered[x][y].color = blank_color;
//do it in one dimension
rendered[(y)*SCR_X + (x)].color = blank_color;
}
else if (letter == wall_char){
//rendered[x][y].color = wall_color;
//do it in one dimension
rendered[(y)*SCR_X + (x)].color = wall_color;
}
}
}
}
void draw_maze(){
//FILE *fp;
//fp = fopen("logx", "w");
for (uint16_t y = 0; y < SCR_Y; y++) {
for (uint16_t x = 0; x < SCR_X; x++) {
//attron(COLOR_PAIR(rendered[x][y].color));
//do it in one dimension
attron(COLOR_PAIR(rendered[(y)*SCR_X + (x)].color));
//mvaddch(y, x, rendered[x][y].letter);
//do it in one dimension
mvaddch(y, x, rendered[(y)*SCR_X + (x)].letter);
//fprintf(fp, "%c, x:%d y:%d\n", rendered[(y)*SCR_X + (x)].letter, rendered[(y)*SCR_X + (x)].x, rendered[(y)*SCR_X + (x)].y);
//attroff(COLOR_PAIR(rendered[x][y].color));
//do it in one dimension
attroff(COLOR_PAIR(rendered[(y)*SCR_X + (x)].color));
}
}
//fclose(fp);
refresh();
}
void init(){
initscr();
//get screen size
getmaxyx(stdscr, SCR_Y, SCR_X);
playfield = malloc(sizeof(char) * SCR_Y * SCR_X);
rendered = malloc(sizeof(struct Object) * (SCR_X) * (SCR_Y));
bullets = malloc(sizeof(struct Bullet) * (SCR_X) * (SCR_Y));
noecho();
nodelay(stdscr, TRUE);
start_color();
init_pair(blank_color, COLOR_WHITE, COLOR_WHITE);
init_pair(wall_color, COLOR_BLACK, COLOR_RED);
init_pair(goal_color, COLOR_BLACK, COLOR_GREEN);
init_pair(player_color, COLOR_BLACK, COLOR_YELLOW);
init_pair(border_color, COLOR_WHITE, COLOR_BLUE);
init_pair(bullet1_color, COLOR_BLACK, COLOR_YELLOW);
init_pair(bullet2_color, COLOR_BLACK, COLOR_GREEN);
attron(COLOR_PAIR(blank_color));
clear();
srand(time(NULL));
}
int keyinput(){
inchar = getch();
if (inchar == 'q'){
return 1;
}
if (inchar == 'w'){
//if (playfield[player_y - 1][player_x] == blank_char){
if (player_y > 0&&playfield[(player_y-1)*SCR_X + player_x] == blank_char){
//playfield[player_y][player_x] = blank_char;
//do it in one dimension
playfield[(player_y)*SCR_X + player_x] = blank_char;
player_y--;
//playfield[player_y][player_x] = player_char;
//do it in one dimension
playfield[(player_y)*SCR_X + player_x] = player_char;
//}else if (playfield[player_y - 1][player_x] == goal_char){
}else if (playfield[(player_y-1)*SCR_X + player_x] == goal_char){
return 2;
}
}
if (inchar == 'a'){
//if (playfield[player_y][player_x - 1] == blank_char){
if (player_x > 0 &&playfield[(player_y)*SCR_X + (player_x-1)] == blank_char){
//playfield[player_y][player_x] = blank_char;
//do it in one dimension
playfield[(player_y)*SCR_X + player_x] = blank_char;
player_x--;
//playfield[player_y][player_x] = player_char;
//do it in one dimension
playfield[(player_y)*SCR_X + player_x] = player_char;
}
//else if (playfield[player_y][player_x - 1] == goal_char){
else if (playfield[(player_y)*SCR_X + (player_x-1)] == goal_char){
return 2;
}
}
if (inchar == 's'){
//if (playfield[player_y + 1][player_x] == blank_char){
if (player_x < SCR_X - 1 &&playfield[(player_y+1)*SCR_X + player_x] == blank_char){
// playfield[player_y][player_x] = blank_char;
playfield[(player_y)*SCR_X + player_x] = blank_char;
player_y++;
// playfield[player_y][player_x] = player_char;
playfield[(player_y)*SCR_X + player_x] = player_char;
// }else if (playfield[player_y + 1][player_x] == goal_char){
}else if (playfield[(player_y+1)*SCR_X + player_x] == goal_char){
return 2;
}
}
if (inchar == 'd'){
// if (playfield[player_y][player_x + 1] == blank_char){
if (player_x < SCR_X - 1 &&playfield[(player_y)*SCR_X + (player_x+1)] == blank_char){
//playfield[player_y][player_x] = blank_char;
playfield[(player_y)*SCR_X + player_x] = blank_char;
player_x++;
//playfield[player_y][player_x] = player_char;
playfield[(player_y)*SCR_X + player_x] = player_char;
}
//else if (playfield[player_y][player_x + 1] == goal_char){
else if (playfield[(player_y)*SCR_X + (player_x+1)] == goal_char){
return 2;
}
}
}
int main(int argc, char *argv[]){
init();
//parse the command line arguments for width and height
if (argc == 3){
SCR_X = atoi(argv[1]);
SCR_Y = atoi(argv[2]);
}
if (argc == 2){
Hole_Div = atoi(argv[1]);
}
if (argc == 4){
SCR_X = atoi(argv[1]);
SCR_Y = atoi(argv[2]);
Hole_Div = atoi(argv[3]);
}
generate_maze();
render_maze();
draw_maze();
while (1)
{
inputs_tmp = keyinput();
if (inputs_tmp == 1){
break;
}
if (inputs_tmp == 2){
if (orient == 0){
orient = 1;
} else {
orient = 0;
}
generate_maze();
}
render_maze();
draw_maze();
usleep(round(1000000/FPS));
}
endwin();
free(playfield);
free(rendered);
return 0;
}