diff options
| -rw-r--r-- | .clang-format | 9 | ||||
| -rw-r--r-- | mazerator.c | 192 | ||||
| -rw-r--r-- | stack.c | 41 | ||||
| -rw-r--r-- | stack.h | 19 | 
4 files changed, 156 insertions, 105 deletions
| diff --git a/.clang-format b/.clang-format new file mode 100644 index 0000000..1681843 --- /dev/null +++ b/.clang-format @@ -0,0 +1,9 @@ +BasedOnStyle: LLVM +UseTab: Always +IndentWidth: 4 +TabWidth: 4 +BreakBeforeBraces: Allman +AllowShortIfStatementsOnASingleLine: false +IndentCaseLabels: false +ColumnLimit: 0 +AccessModifierOffset: -4
\ No newline at end of file diff --git a/mazerator.c b/mazerator.c index 9b2e434..f15c4ae 100644 --- a/mazerator.c +++ b/mazerator.c @@ -1,67 +1,26 @@ +#include "stack.h" +#include <ctype.h> +#include <getopt.h>  #include <stdio.h>  #include <stdlib.h> -#include <getopt.h> -#include <unistd.h> -#include <ctype.h>  #include <string.h> +#include <unistd.h>  // Error handling -void err(int id){ -	switch(id){ -	case 0: printf("Error: Stack overflow\nBe kind and report this problem."); break; -	case 1: printf("Error: Stack underflow\nBe kind and report this problem."); break; +void err(int id) +{ +	switch (id) +	{ +	case 0: +		printf("Error: Stack overflow\nBe kind and report this problem."); +		break; +	case 1: +		printf("Error: Stack underflow\nBe kind and report this problem."); +		break;  	}  	exit(1);  } -// The fundementals for the maze-generation algoritm -// A stack data-structure -struct stack -{ -	int max_size; -	int top;         -	int *items; -}; - -// Create a new stack -struct stack* new_stack(int capacity) -{ -	struct stack *pt = (struct stack*)malloc(sizeof(struct stack)); -	pt->max_size = capacity; -	pt->top = -1; -	pt->items = (int*)malloc(sizeof(int) * capacity); -	return pt; -} - -// Add a new item to a stack -void stack_push(struct stack *pt, int x) -{ -	// Avoid a overflow by checking if the stack is full -	if (pt->top == pt->max_size - 1) -		err(0); -	// Add an element and increase the top index -	pt->items[++pt->top] = x; -} - -// Get the topmost item of a stack -int stack_peek(struct stack *pt) -{ -	// Check if the stack is empty -	if (pt->top == -1) -		err(1); -	return pt->items[pt->top]; -} - -// Remove the topmost item of a stack -int stack_pop(struct stack *pt) -{ -	// Check for a stack underflow -	if (pt->top == -1) -		err(0); -	// Decrease the stack size by 1 and (optionally) return the popped element -	return pt->items[pt->top--]; -} -  // Get a position in the maze from coordinates y and x  //  // This is achieved by concatenating the binary values of the two variables. @@ -71,10 +30,7 @@ int stack_pop(struct stack *pt)  // X: 15   00001111  // Will become:  // 0000100000001111 -int get_maze_pos(int posY, int posX) -{ -	return ((posY) << 8) | posX; -} +int get_maze_pos(int posY, int posX) { return ((posY) << 8) | posX; }  // Get y and x coordinates from a position in the maze  // @@ -91,46 +47,51 @@ int get_maze_coords(int pos, int *y, int *x)  // Find out if a string is a number by running it through  // isdigit() char-by-char -int is_number(char * str) +int is_number(char *str)  {  	size_t len = strlen(str); -	for(int c = 0; c < len; c++){ -		if(!isdigit(str[c])) +	for (int c = 0; c < len; c++) +	{ +		if (!isdigit(str[c]))  			return 0;  	}  	return 1;  } -// Where the magic happends  int main(int argc, char *argv[])  {  	int maze_width = 40;  	int maze_heigth = 20;  	char *wall = "█"; -	int seed; +	int seed = 0;  	static struct option options[] = {  		/*   NAME	ARGUMENT		FLAG	SHORTNAME */ -		{"width",	required_argument,	NULL,	'w'}, -		{"heigth",	required_argument,	NULL,	'h'}, -		{"wall",	required_argument,	NULL,	'W'}, -		{"seed",	required_argument,	NULL,	's'}, -		{"help",	no_argument,		NULL,	0}, -		{NULL,		0,			NULL,	0} -	}; -	 +		{"width", required_argument, NULL, 'w'}, +		{"heigth", required_argument, NULL, 'h'}, +		{"wall", required_argument, NULL, 'W'}, +		{"seed", required_argument, NULL, 's'}, +		{"help", no_argument, NULL, 0}, +		{NULL, 0, NULL, 0}}; +  	int c; -	while((c = getopt_long(argc, argv, "w:h:W:s:", options, NULL)) != -1) { -		switch(c){ +	while ((c = getopt_long(argc, argv, "w:h:W:s:", options, NULL)) != -1) +	{ +		switch (c) +		{  		case 'w':  		case 'h':  			// Set heigth or width -			if(is_number(optarg) && atoi(optarg) >= 1 && atoi(optarg) <= 255) -				switch(c){ -				case 'h': maze_heigth = atoi(optarg); -				case 'w': maze_width = atoi(optarg); +			if (is_number(optarg) && atoi(optarg) >= 1 && atoi(optarg) <= 255) +				switch (c) +				{ +				case 'h': +					maze_heigth = atoi(optarg); +				case 'w': +					maze_width = atoi(optarg);  				} -			else{ +			else +			{  				printf("Invalid option argument for -%c!\n", c);  				exit(1);  			} @@ -141,17 +102,20 @@ int main(int argc, char *argv[])  			break;  		case 's':  			// Set the seed -			if(is_number(optarg)){ +			if (is_number(optarg)) +			{  				seed = atoi(optarg);  				break;  			} -			else{ +			else +			{  				printf("Invalid option argument for -s/--seed!\n");  				exit(1);  			}  		case 0:  			// Help -			printf("Usage: mazerator [--help] [-W wall] [-s seed] [-w width] [-h heigth]\n\n\ +			printf( +				"Usage: mazerator [--help] [-W wall] [-s seed] [-w width] [-h heigth]\n\n\  OPTIONS\n\      --width        -w     The width of the maze. (1-255). Default: 40\n\      --heigth       -h     The heigth of the maze. (1-255). Default: 20\n\ @@ -165,75 +129,92 @@ OPTIONS\n\  			exit(1);  		}  	} -	 +  	int maze[maze_heigth][maze_width];  	char *maze_visual[maze_heigth * 2 + 1][maze_width * 2 + 1];  	struct stack *path = new_stack(maze_width * maze_heigth);  	// Prepares seed value for randr()  	// Get's a seed from /dev/urandom if not already set -	if(seed == 0){ +	if (seed == 0) +	{ +		printf("What");  		FILE *f = fopen("/dev/urandom", "r");  		fread(&seed, sizeof(seed), 1, f);  		fclose(f);  	}  	srand(seed); -	 +  	// Prepares the maze grids -	// Fills the maze with zeroes indicating that none of the grid squares have been visited +	// Fills the maze with zeroes indicating that none of the grid squares have +	// been visited  	//  	// Fills the visual maze with walls -	for(int y = 0; y < sizeof(maze) / sizeof(maze[0]); y++){ -		for(int x = 0; x < sizeof(maze[0]) / sizeof(maze[0][0]); x++){ +	for (int y = 0; y < sizeof(maze) / sizeof(maze[0]); y++) +	{ +		for (int x = 0; x < sizeof(maze[0]) / sizeof(maze[0][0]); x++) +		{  			maze[y][x] = 0;  		}  	} -	for(int y = 0; y < sizeof(maze_visual) / sizeof(maze_visual[0]); y++){ -		for(int x = 0; x < sizeof(maze_visual[0]) / sizeof(maze_visual[0][0]); x++){ +	for (int y = 0; y < sizeof(maze_visual) / sizeof(maze_visual[0]); y++) +	{ +		for (int x = 0; x < sizeof(maze_visual[0]) / sizeof(maze_visual[0][0]); +			 x++) +		{  			maze_visual[y][x] = wall;  		}  	} -	 +  	// Set the start value (0, 0) and begin the algoritm loop  	stack_push(path, 0);  	int cnt = 0; -	while(1){ +	while (1) +	{  		int pos = stack_peek(path);  		int posY, posX;  		get_maze_coords(pos, &posY, &posX); -		 -		// Set the currently visited grid square to 1 indicating that it has been visited -		// and excavate the visual maze + +		// Set the currently visited grid square to 1 indicating that it has been +		// visited and excavate the visual maze  		maze[posY][posX] = 1;  		maze_visual[posY * 2 + 1][posX * 2 + 1] = " ";  		// Find out available next positions to go to  		int neighbours[3];  		int i = 0; -		if(posY != 0 && maze[posY - 1][posX] == 0){ +		if (posY != 0 && maze[posY - 1][posX] == 0) +		{  			neighbours[i] = get_maze_pos(posY - 1, posX);  			i++; -			  		} -		if(posY != maze_heigth - 1 && maze[posY + 1][posX] == 0){ +		if (posY != maze_heigth - 1 && maze[posY + 1][posX] == 0) +		{  			neighbours[i] = get_maze_pos(posY + 1, posX);  			i++;  		} -		if(posX != 0 && maze[posY][posX - 1] == 0){ +		if (posX != 0 && maze[posY][posX - 1] == 0) +		{  			neighbours[i] = get_maze_pos(posY, posX - 1);  			i++;  		} -		if(posX != maze_width - 1 && maze[posY][posX + 1] == 0){ +		if (posX != maze_width - 1 && maze[posY][posX + 1] == 0) +		{  			neighbours[i] = get_maze_pos(posY, posX + 1);  			i++;  		} -		switch(i){ +		switch (i) +		{  		case 0:  			// No available next positions -			if(cnt == (maze_heigth * maze_width) - 1){ -				for(int y = 0; y < sizeof(maze_visual) / sizeof(maze_visual[0]); y++){ -					for(int x = 0; x < sizeof(maze_visual[0]) / sizeof(maze_visual[0][0]); x++){ +			if (cnt == (maze_heigth * maze_width) - 1) +			{ +				for (int y = 0; y < sizeof(maze_visual) / sizeof(maze_visual[0]); y++) +				{ +					for (int x = 0; +						 x < sizeof(maze_visual[0]) / sizeof(maze_visual[0][0]); x++) +					{  						printf("%s", maze_visual[y][x]);  					}  					printf("\n"); @@ -249,7 +230,8 @@ OPTIONS\n\  			int next = neighbours[rand() % i];  			int next_y, next_x;  			get_maze_coords(next, &next_y, &next_x); -			maze_visual[posY * 2 - (posY - next_y) + 1][posX * 2 - (posX - next_x) + 1] = " "; +			maze_visual[posY * 2 - (posY - next_y) + 1] +					   [posX * 2 - (posX - next_x) + 1] = " ";  			stack_push(path, next);  		}  	} @@ -0,0 +1,41 @@ +#include "stack.h" +#include <stdlib.h> + +// Create a new stack +struct stack *new_stack(int capacity) +{ +	struct stack *pt = (struct stack *)malloc(sizeof(struct stack)); +	pt->max_size = capacity; +	pt->top = -1; +	pt->items = (int *)malloc(sizeof(int) * capacity); +	return pt; +} + +// Add a new item to a stack +void stack_push(struct stack *pt, int x) +{ +	// Avoid a overflow by checking if the stack is full +	if (pt->top == pt->max_size - 1) +		err(0); +	// Add an element and increase the top index +	pt->items[++pt->top] = x; +} + +// Get the topmost item of a stack +int stack_peek(struct stack *pt) +{ +	// Check if the stack is empty +	if (pt->top == -1) +		err(1); +	return pt->items[pt->top]; +} + +// Remove the topmost item of a stack +int stack_pop(struct stack *pt) +{ +	// Check for a stack underflow +	if (pt->top == -1) +		err(0); +	// Decrease the stack size by 1 and (optionally) return the popped element +	return pt->items[pt->top--]; +}
\ No newline at end of file @@ -0,0 +1,19 @@ +#ifndef STACK_H +#define STACK_H + +struct stack +{ +	int max_size; +	int top; +	int *items; +}; + +struct stack *new_stack(int capacity); + +void stack_push(struct stack *pt, int x); + +int stack_peek(struct stack *pt); + +int stack_pop(struct stack *pt); + +#endif
\ No newline at end of file | 
