#include #include #include #include #include #include #define DELAY 30000 #define ENEMY_N 5 #define BULLET_N 3 #define MIN_WIDTH 52 #define MIN_HEIGHT 30 struct speed { int slowness; int count; }; struct game_obj { char symbol; int x, y; int active; struct speed y_speed; }; /************** FUNZIONI GUI ***************/ void print_menu(WINDOW* win) { mvwprintw(win, 1, 1, "BENVENUTO IN SPACE SHOOTER!\n"); mvwprintw(win, 2, 1, "Premi un tasto qualsiasi per giocare..."); refresh(); getch(); return; } int main() { /************ VARIABILI **************/ WINDOW *game_window; int height, width, win_startx, win_starty; char *pause_msg = "PAUSA: premi q per uscire dal gioco..."; int pause = 0; int max_height; int max_width; int auto_shoot = 0; // Giocatore struct game_obj player = {}; int input; // Proiettile struct game_obj bullet[BULLET_N] = {}; int bullet_attivi = 0; int next_bullet = 0; // Nemici struct game_obj enemy[ENEMY_N] = {}; /**************** INIZIALIZZAZIONE ***************/ initscr(); cbreak(); noecho(); keypad(stdscr, TRUE); curs_set(0); srand(time(NULL)); // "menu" print_menu(stdscr); mvprintw(3, 1, "p per pausa, q per uscire"); refresh(); // Dimensioni finestra di gioco max_height = LINES - 10; max_width = COLS - 10; // Schermo troppo piccolo ? if(max_width < MIN_WIDTH || max_height < MIN_HEIGHT) { delwin(game_window); curs_set(1); endwin(); printf("Gioco terminato.\n"); printf("Schermo troppo piccolo \n"); return 0; } // calcolo delle misure della finestra height = max_height; width = MIN_WIDTH < max_width ? MIN_WIDTH - (MIN_WIDTH%4) : (max_width) - ((max_width)%4); win_startx = (COLS - width)/2; win_starty = (LINES - height)/2; // Crea la finestra di gioco game_window = newwin(height, width, win_starty, win_startx); nodelay(game_window, TRUE); // input non bloccante keypad(game_window, TRUE); box(game_window, 0, 0); wrefresh(game_window); // setup giocatore player.symbol = 'A'; player.x = width / 2; player.y = height - 2; player.active = 1; // setup proiettili for(int i = 0; i < BULLET_N; i++) { bullet[i].symbol = '*'; bullet[i].active = 0; } // setup dei nemici for(int i = 0; i < ENEMY_N; i++) { enemy[i].symbol = 'Q'; enemy[i].active = 0; enemy[i].y_speed.slowness = 7; enemy[i].y_speed.count = 0; } //********************* GAME LOOP ***********************/ while (player.active) { // TODO if pausa all'inizio e continue input = wgetch(game_window); // Gestione input if (input == KEY_RIGHT && !pause && player.x < width - 2) { player.x += 2; } else if (input == KEY_LEFT && !pause && player.x > 2) { player.x -= 2; } else if (!auto_shoot && input == ' ' && bullet_attivi < BULLET_N && !pause) { bullet[next_bullet].x = player.x; bullet[next_bullet].y = player.y - 1; bullet[next_bullet].active = 1; } else if (input == 'p') { pause = !pause; } else if (input == 'q') { player.active = 0; } else if (input == 'g') { auto_shoot= !auto_shoot; } if (auto_shoot && bullet_attivi < BULLET_N && !pause) { bullet[next_bullet].x = player.x; bullet[next_bullet].y = player.y - 1; bullet[next_bullet].active = 1; } // Aggiorna proiettile for(int i = 0; i< BULLET_N; i++) { if (bullet[i].active && !pause) { bullet[i].y--; } if (bullet[i].y < 1) { bullet[i].active = 0; } } // Collisioni 1 for(int j = 0; j < BULLET_N; j++) { if(bullet[j].active && !pause) { for(int i = 0; i < ENEMY_N; i++) { if(bullet[j].x == enemy[i].x && bullet[j].y == enemy[i].y) { enemy[i].active = 0; bullet[j].active = 0; // TODO aggiorna punteggio } } } } // Spawna nemici for(int i = 0; !pause && i < ENEMY_N; i++) { if(!enemy[i].active && !pause) { enemy[i].y = 2; enemy[i].x = (rand()%((width-4)/2))*2 + 2; enemy[i].active = 1; break; } } // Aggiorna posizione nemici for(int i = 0; !pause && i < ENEMY_N; i++) { if(enemy[i].active && !pause) { enemy[i].y_speed.count++; if(enemy[i].y_speed.count > enemy[i].y_speed.slowness) { enemy[i].y++; enemy[i].y_speed.count = 0; } if(enemy[i].y > height - 2) { enemy[i].active = 0; // TODO aggiorna punteggio } } } // Collisioni 2 for(int j = 0; j < BULLET_N; j++) { if(bullet[j].active && !pause) { for(int i = 0; i < ENEMY_N; i++) { if(bullet[j].x == enemy[i].x && bullet[j].y == enemy[i].y) { enemy[i].active = 0; bullet[j].active = 0; // TODO aggiorna punteggio } } } } // Conteggio proiettili bullet_attivi = 0; next_bullet = -1; for (int i = 0; i < BULLET_N; i++) { if (bullet[i].active) { bullet_attivi++; } else if (i < next_bullet || next_bullet == -1) { next_bullet = i; } } // Disegna scena werase(game_window); box(game_window, 0, 0); if (pause) { wattron(game_window, A_REVERSE); mvwprintw(game_window, height/2, (width - strlen(pause_msg)) / 2, "%s", pause_msg); wattroff(game_window, A_REVERSE); } else { // Giocatore mvwprintw(game_window, player.y, player.x, "%c", player.symbol); // Proiettile for(int i = 0; i < BULLET_N; i++) { if (bullet[i].active) mvwprintw(game_window, bullet[i].y, bullet[i].x, "%c", bullet[i].symbol); } // Nemici for(int i = 0; i < ENEMY_N; i++) { if (enemy[i].active) mvwprintw(game_window, enemy[i].y, enemy[i].x, "%c", enemy[i].symbol); } } wrefresh(game_window); usleep(DELAY); } /***************** CHIUSURA *****************/ delwin(game_window); curs_set(1); endwin(); printf("Gioco terminato.\n"); return 0; }