diff --git a/du7/snake/main.c b/du7/main.c similarity index 100% rename from du7/snake/main.c rename to du7/main.c diff --git a/du7/snake/Makefile b/du7/snake/Makefile deleted file mode 100644 index d71d436..0000000 --- a/du7/snake/Makefile +++ /dev/null @@ -1,14 +0,0 @@ -CFLAGS=-std=c99 -Wall -g - -all: game - -%.o: %.c - gcc $(CFLAGS) -c $< -o $@ - -clean: - rm *.o - rm game - -game: main.o world.o snake.o - gcc -rdynamic -g main.o world.o snake.o -lcurses -lm -o game - diff --git a/du7/snake/README.md b/du7/snake/README.md deleted file mode 100644 index 79a2d67..0000000 --- a/du7/snake/README.md +++ /dev/null @@ -1,16 +0,0 @@ -# Snake Master - -Implement Snake game. - -Make the game to pass the automatic tests and make the game to be nice. - -## Files - -Please do not change file names. - -- `snake.h`: you implementation should follow this header. -- `snake.c`: implemement the game according to the documentation in header file in this file to pass automatic tests. -- `Makefile`: rules to build the game. -- `main.c`: trivial main function that runs the game, modify this file to change the appereance of the game and the initial state. -- `world.c`: world game loop and ASCII graphics library (do not change). -- `world.h`: world library interface (do not change). diff --git a/du7/snake/snake.h b/du7/snake/snake.h deleted file mode 100644 index 4d1ff74..0000000 --- a/du7/snake/snake.h +++ /dev/null @@ -1,114 +0,0 @@ -#ifndef snake_h_INCLUDED -#define snake_h_INCLUDED - -// Number of food items on the plane -#define FOOD_COUNT 5 - -/** - * One part of the snake; - * - * The snake is a linked list; - */ - -struct snake { - // x position of the snake part - int x; - // y position of the snake part - int y; - // Pointer to the next snake part. - // The last part of the snake has NULL pointer to the next part. - struct snake* next; -}; - -// End game reason constants, return value of step_state -enum endgame { - // Continue the game - END_CONTINUE = 0, - // Snake hit a wall - END_WALL, - // Snake hit itself - END_SNAKE, - // No food left - END_FOOD, - // Other reason to end - END_USER -}; - -/** - * State of the game. - * - * The state consists of the snake, its speed and food on the plane. - * - * The snake is a linked list of snake parts. - * - * Speed vector is a vector added to the last head position to create a new head. - * - * Food are points on the plane. Food with negative coordinates meads food is already eaten. - */ - -struct state { - // Snake as a linked list - struct snake* snake; - // X of the food positions - int foodx[FOOD_COUNT]; - // Y of the food positions - int foody[FOOD_COUNT]; - int sx; - int sy; - int width; - int height; -}; - -/** - * Add a new snake part with given position. The new snake part becomes the new head. - * - * @param head of the snake. - * @param x coordinate of the new head; - * @param y coordinate of the new head. - * @return new head of the snake. - */ -struct snake* add_snake(struct snake* snake,int x,int y); - -/** - * Remove the last snake part. - * The last snake part should always have NULL next pointer. - * - * @param head of the snake. - * @return new head of the snake. - */ -struct snake* remove_snake(struct snake* snake); - -/** - * Finds out if given coordinates are part of the snake. - * @param snake - * @param x coordinate to search in snake - * @param y coordinate to search in snake - * @return True, if there is a snake part with coordinates x,y. False otherwise - * - */ -int is_snake(struct snake* snake,int x, int y); -/** - * Remove and free each snake part; - * @param head of the snake. - */ -void free_snake(struct snake* sn); -/** - * Change game state. - * - * The function shoud calculate new posision of the snake head - * from the current position and speed vector. - * Then it should modify snake parst or food coordinates according to the rules: - * - * - If the new position is on the snake, end the game, return END_SNAKE. - * - If the new position is on the food, mark food as eaten - * (set its coordinates to -1) and add new snake part on the position of the food. If there is no food left, return END_FOOD. else return END_CONTINUE. - * - If the new position is on the plane, add new snake part on the new position and remove the last part of the snake, return END_CONTINUE. - * - * @param current state of the game - * @return reason to end the game according to enum endgame. - */ -int step_state(struct state* state); - - -#endif // snake_h_INCLUDED - diff --git a/du7/snake/world.c b/du7/snake/world.c deleted file mode 100644 index a45c109..0000000 --- a/du7/snake/world.c +++ /dev/null @@ -1,198 +0,0 @@ -#include "world.h" -#include -#include -#include -#include -#include - -int TIMEOUT; - -void abort_game(const char* message){ - endwin(); - puts(message); - exit(1); -} - -void check_bounds(const char* source,int x, int y){ - char msg[200]; - if (x < 0 || x >= COLS){ - sprintf(msg,"%s:: width %d is out of bounds (0,%d)",source,x,COLS); - abort_game(msg); - } - if (y < 0 || y >= LINES){ - sprintf(msg,"%s:: height %d is out of bounds (0,%d)",source,y,LINES); - abort_game(msg); - } -} - -void clear_screen(){ - // Clear screen - mvaddch(0,0,' '); - int screenchars = LINES*COLS; - for (int j = 1; j < screenchars;j++ ){ - addch(' '); - } -} - -void game_speed(int value){ - if (value < 0){ - abort_game("world_seed:: cannot be negative\n"); - } - TIMEOUT =value; -} - -void set_message(const char* message,int x,int y) { - int l = strlen(message); - for (int i = 0; i < l; i++){ - check_bounds("set_message",x+i,y); - set_cell(message[i],x+i,y); - } -} - -void assert_message(int event,const char* message){ - if (event == 0){ - abort_game(message); - } -} - - -void set_cell(int character,int x,int y) { - check_bounds("set_cell",x,y); - set_color_cell(character,x,y,COLOR_WHITE,COLOR_BLACK); -} - -void set_color_cell(int character,int x,int y,short front_color,short back_color){ - check_bounds("set_color_cell",x,y); - if (has_colors()){ - int pair = COLOR_COUNT * front_color + back_color; - attron(COLOR_PAIR(pair)); - mvaddch(y,x,character); - attroff(COLOR_PAIR(pair)); - } - else{ - mvaddch(y,x,character); - } -} - -int start_world(void* (*init_game)(),int (*world_event)(struct event* event,void* game),void (*destroy_game)(void*)){ - srand(time(NULL)); - int r = 1; - // Speed global variable - TIMEOUT = 100; - if (initscr() == NULL){ - // TODO Which Error? - puts("Curses Error."); - return -1; - } - noecho(); // Nevypisuj vstup na obrazovku - cbreak(); // Zabudni starý vstup - nodelay(stdscr,TRUE); // Nečakaj na stlačenie - keypad(stdscr,TRUE); // Aktivuje šípky - curs_set(FALSE); // Neviditeľný kurzor - /* Get all the mouse events */ - mousemask(ALL_MOUSE_EVENTS, NULL); - MEVENT mouse_event; - if (has_colors()){ // Zistenie či terminál podporuje farby - start_color(); - for (int i = 0; i < COLOR_COUNT;i++){ - for (int j = 0; j < COLOR_COUNT;j++){ - init_pair(i * COLOR_COUNT + j, i,j); - } - } - } - else { - puts("No colors!\n"); - } - void* game = NULL; - if (init_game != NULL){ - game = init_game(); - assert_message(game != NULL,"init_game:: should return non null pointer"); - } - timeout(TIMEOUT); - // Initial step - struct event event; - memset(&event,0,sizeof(struct event)); - event.height = LINES; - event.width = COLS; - event.type = EVENT_START; - clock_t start_time = clock(); - clock_t last_timeout = start_time; - clock_t next_timeout = last_timeout + TIMEOUT; - event.time_ms = start_time; - // Start event - r = world_event(&event,game); - refresh(); - while (!r) { - memset(&event,0,sizeof(struct event)); - event.height = LINES; - event.width = COLS; - event.key = getch(); - // No key was pressed - if (event.key == ERR){ - event.type = EVENT_TIMEOUT; - last_timeout = clock(); - next_timeout = last_timeout + TIMEOUT; - } - // Mouse event - else if (event.key == KEY_MOUSE ){ - event.type = EVENT_MOUSE; - if(getmouse(&mouse_event) == OK){ - event.mouse_x = mouse_event.x; - event.mouse_y = mouse_event.y; - if(mouse_event.bstate & BUTTON1_PRESSED){ - event.mouse_left = 1; - } - if(mouse_event.bstate & BUTTON2_PRESSED){ - event.mouse_middle = 1; - } - if(mouse_event.bstate & BUTTON3_PRESSED){ - event.mouse_right = 1; - } - } - } - else if (event.key == KEY_RESIZE) { - event.type = EVENT_RESIZE; - } - else{ - event.type = EVENT_KEY; - if (event.key == 27){ - int k = getch(); - if (k == -1){ - // Esc Was pressed - event.type = EVENT_ESC; - } - else { - // Alt was pressed - event.key = k; - event.alt_key = 1; - } - } - } - // Draw new world - event.time_ms = clock(); - r = world_event(&event,game); - refresh(); - event.time_ms = clock(); - // set new timeout - int nt = next_timeout - event.time_ms; - //printf("%d\n",nt); - if (nt > 0){ - timeout(nt); - } - else { - timeout(TIMEOUT); - next_timeout = event.time_ms + TIMEOUT; - } - } - memset(&event,0,sizeof(struct event)); - event.height = LINES; - event.width = COLS; - event.type = EVENT_END; - event.time_ms = clock(); - world_event(&event,game); - if (destroy_game != NULL){ - destroy_game(game); - } - endwin(); - return r; -}; diff --git a/du7/snake/world.h b/du7/snake/world.h deleted file mode 100644 index e7a3fdb..0000000 --- a/du7/snake/world.h +++ /dev/null @@ -1,122 +0,0 @@ -#ifndef _WORLD_H_ -#define _WORLD_H_ - -#include - -/** - * World represented as a rectangular matrix of colorful characters. - * - * Point [0,0] is displayed the upper left corner of the screen. - * - */ - -enum event_type { - EVENT_START, - EVENT_TIMEOUT, - EVENT_KEY, - EVENT_MOUSE, - EVENT_RESIZE, - EVENT_ESC, - EVENT_END, -}; - -struct event { - /** - * Last width of the screen. - */ - int width; - /** - * Last height of the screen. - */ - int height; - /** - * Last pressed key or Curses event. - * - * Special event values: - * ERR if timeout, - * KEY_RESIZE if screen resize - * KEY_EVENT, other event, - * KEY_MOUSE, mouse clicked - * - * Key values: - * - * ' ' Space - * KEY_DOWN Arrow down - * KEY_UP Arrow up - * KEY_LEFT Arrow left - * KEY_RIGHT Arrow right - * KEY_A1 Upper left of keypad - * KEY_A3 Upper right of keypad - * KEY_B2 Center of keypad - * KEY_C1 Lower left of keypad - * KEY_C3 Lower right of keypad - * - * KEY_ENTER - * KEY_BACKSPACE - */ - int key; - int alt_key; - enum event_type type; - int mouse_x; - int mouse_y; - int mouse_left; - int mouse_right; - int mouse_middle; - long int time_ms; -}; - -/** - * Sets cell to a state. - * @param event - * @param x coordinate of cell - * @param y coordinate of cell - * @param new state of the cell - */ -void set_cell(int character,int x,int y); - -/** - * COLOR_BLACK 0 - * COLOR_RED 1 - * COLOR_GREEN 2 - * COLOR_YELLOW 3 - * COLOR_BLUE 4 - * COLOR_MAGENTA 5 - * COLOR_CYAN 6 - * COLOR_WHITE 7 - */ - -#define COLOR_COUNT 8 - -void set_color_cell(int character,int x,int y,short front_color,short back_color); - - -/** - * - * @param event - * @param number of commandline arguments - * @param init_world - * @param destroy_world - * - * void init_world(struct event* w); - * Initializes user state. - * Free user state. - * @param event - */ - -int start_world(void* (*init_game)(),int (*world_event)(struct event* event,void* game),void (*destroy_game)(void* game)); -/** - * Set timeout interval in miliseconds - */ -void game_speed(int value); - -/* - * Prints a message in screen on a position x,y - */ - -void set_message(const char* message,int x,int y); -/* - * Clears screen - */ -void clear_screen(); - -#endif