Project

General

Profile

Statistics
| Revision:

root / proj / src / proj.c @ 310

History | View | Annotate | Download (25.4 KB)

1 144 up20180655
#include <lcom/lcf.h>
2
#include <lcom/proj.h>
3
#include <lcom/liblm.h>
4 185 up20180655
#include <math.h>
5 144 up20180655
6 149 up20180655
#include "proj_macros.h"
7 179 up20180642
#include "proj_func.h"
8 147 up20180655
9 149 up20180655
#include "kbc.h"
10
#include "timer.h"
11
#include "keyboard.h"
12 150 up20180655
#include "mouse.h"
13 189 up20180655
#include "graph.h"
14 291 up20180642
#include "menu.h"
15 234 up20180655
#include "rtc.h"
16 287 up20180642
#include "hltp.h"
17 153 up20180655
#include "interrupts_func.h"
18 270 up20180655
#include "makecode_map.h"
19 149 up20180655
20 179 up20180642
#include "graph.h"
21
#include "rectangle.h"
22 182 up20180642
#include "font.h"
23 192 up20180642
#include "ent.h"
24 168 up20180642
25 192 up20180642
#include "crosshair.h"
26
#include "shooter.h"
27 303 up20180642
#include "zombie.h"
28 192 up20180642
#include "pistol.h"
29
#include "nothing.h"
30 237 up20180642
#include "bullet.h"
31 216 up20180642
#include "map1.h"
32 183 up20180642
33 294 up20180642
#include "errors.h"
34
35 226 up20180642
#include "list.h"
36
37 144 up20180655
int main(int argc, char* argv[]) {
38
39
    lcf_set_language("EN-US");
40
41 310 up20180642
    //lcf_trace_calls("/home/lcom/labs/proj/trace.txt");
42 144 up20180655
43 310 up20180642
    //lcf_log_output("/home/lcom/labs/proj/output.txt");
44 144 up20180655
45
    if (lcf_start(argc, argv)) return 1;
46
47
    lcf_cleanup();
48
49
    return 0;
50
}
51 147 up20180655
52 294 up20180642
font_t               *consolas      = NULL;
53
basic_sprite_t       *bsp_crosshair = NULL;
54
basic_sprite_t       *bsp_shooter   = NULL;
55 301 up20180642
basic_sprite_t       *bsp_zombie    = NULL;
56 294 up20180642
basic_sprite_t       *bsp_pistol    = NULL;
57
basic_sprite_t       *bsp_nothing   = NULL;
58
basic_sprite_t       *bsp_bullet    = NULL;
59
map_t                *map1          = NULL;
60
sprite_t             *sp_crosshair  = NULL;
61
62 300 up20180642
static int (singleplayer)(void);
63 308 up20180655
//static int (multiplayer)(void);
64 300 up20180642
static int (chat)(void);
65 149 up20180655
int(proj_main_loop)(int argc, char *argv[]) {
66 170 up20180642
67
    int r;
68
69 294 up20180642
    consolas = font_ctor("/home/lcom/labs/proj/media/font/Consolas/xpm2");
70 261 up20180642
    if(consolas == NULL){ printf("Failed to load consolas\n"); return 1; }
71 192 up20180642
72 261 up20180642
    /// subscribe interrupts
73
    if (subscribe_all()) { return 1; }
74 170 up20180642
75 297 up20180642
    /// initialize graphics
76
    if(graph_init(GRAPH_MODE)){
77
        printf("%s: failed to initalize graphics.\n", __func__);
78
        if (cleanup()) printf("%s: failed to cleanup.\n", __func__);
79
        return 1;
80
    }
81 152 up20180642
82 261 up20180642
    /// Load stuff
83
    {
84 297 up20180642
        graph_clear_screen();
85
        text_t *txt = text_ctor(consolas, "Loading...");
86 309 up20180642
        text_set_pos(txt, graph_get_XRes()/2, graph_get_YRes()/2);
87
        text_set_valign(txt, text_valign_center);
88
        text_set_halign(txt, text_halign_center);
89
        text_set_color(txt, TEXT_COLOR);
90 297 up20180642
        text_draw(txt);
91
        text_dtor(txt);
92
        graph_draw();
93 183 up20180642
94 261 up20180642
        bsp_crosshair = get_crosshair(); if(bsp_crosshair == NULL) printf("Failed to get crosshair\n");
95
        bsp_shooter   = get_shooter  (); if(bsp_shooter   == NULL) printf("Failed to get shooter\n");
96 303 up20180642
        bsp_zombie    = get_zombie   (); if(bsp_zombie    == NULL) printf("Failed to get zombie\n");
97 261 up20180642
        bsp_pistol    = get_pistol   (); if(bsp_pistol    == NULL) printf("Failed to get pistol\n");
98
        bsp_nothing   = get_nothing  (); if(bsp_nothing   == NULL) printf("Failed to get nothing\n");
99
        bsp_bullet    = get_bullet   (); if(bsp_bullet    == NULL) printf("Failed to get bullet\n");
100
        map1          = get_map1     (); if(map1          == NULL) printf("Failed to get map1\n");
101 226 up20180642
102 261 up20180642
        sp_crosshair = sprite_ctor(bsp_crosshair); if(sp_crosshair == NULL) printf("Failed to get crosshair sprite\n");
103
    }
104 226 up20180642
105 297 up20180642
    menu_t *main_menu = menu_ctor(consolas);
106 299 up20180642
    menu_add_item(main_menu, "Single player");
107
    menu_add_item(main_menu, "Multiplayer");
108 297 up20180642
    menu_add_item(main_menu, "Chat");
109
    menu_add_item(main_menu, "Exit");
110 234 up20180655
111 297 up20180642
    //uint32_t refresh_count_value = sys_hz() / REFRESH_RATE;
112
    uint8_t last_lb = 0;
113
    struct packet pp;
114
    keys_t *keys = get_key_presses();
115
116 261 up20180642
    /// loop stuff
117 297 up20180642
    int click = 0;
118 307 up20180642
    uint32_t int_vector = 0;
119 295 up20180642
    int good = true;
120
    while (good) {
121 261 up20180642
        /* Get a request message. */
122 307 up20180642
        if((r = get_interrupts_vector(&int_vector))) return r;
123
        for (uint32_t i = 0, n = 1; i < 32; i++, n <<= 1) {
124
            if (int_vector & n) {
125
                interrupt_handler(i);
126
                switch (i) {
127
                    case TIMER0_IRQ:
128 192 up20180642
129 307 up20180642
                    graph_clear_screen();
130
                    switch(menu_update_state(main_menu, click)){
131
                        case -1: break;
132
                        case  0: singleplayer(); break; //campaign(); break;
133
                        case  1: break;
134
                        case  2: chat(); break;
135
                        case  3: good = false; break;
136
                    }
137
                    menu_draw(main_menu);
138 192 up20180642
139 307 up20180642
                    click = 0;
140 202 up20180655
141 307 up20180642
                    sprite_set_pos(sp_crosshair, *get_mouse_X(), *get_mouse_Y());
142
                    sprite_draw(sp_crosshair);
143
                    graph_draw();
144 231 up20180655
145 307 up20180642
                    break;
146
                    case KBC_IRQ:
147
                    if ((scancode[0]) == ESC_BREAK_CODE) good = false;
148
                    case MOUSE_IRQ:
149
                    if (counter_mouse_ih >= 3) {
150
                        mouse_parse_packet(packet_mouse_ih, &pp);
151
                        update_mouse(&pp);
152
                        if (!click) click = last_lb ^ keys->lb_pressed && keys->lb_pressed;
153
                        last_lb = keys->lb_pressed;
154
                        counter_mouse_ih = 0;
155 261 up20180642
                    }
156 307 up20180642
                    break;
157
                    case COM1_IRQ: nctp_ih(); break;
158 305 up20180642
                }
159 147 up20180655
            }
160
        }
161 261 up20180642
    }
162 149 up20180655
163 261 up20180642
    basic_sprite_dtor      (bsp_crosshair); bsp_crosshair = NULL;
164
    basic_sprite_dtor      (bsp_shooter  ); bsp_shooter   = NULL;
165 307 up20180642
    basic_sprite_dtor      (bsp_zombie   ); bsp_zombie    = NULL;
166 261 up20180642
    sprite_dtor            (sp_crosshair ); sp_crosshair  = NULL;
167
    basic_sprite_dtor      (bsp_pistol   ); bsp_pistol    = NULL;
168
    basic_sprite_dtor      (bsp_nothing  ); bsp_nothing   = NULL;
169
    map_dtor               (map1         ); map1          = NULL;
170
    font_dtor              (consolas     ); consolas      = NULL;
171 243 up20180642
172 261 up20180642
    // Unsubscribe interrupts
173
    if (unsubscribe_all()) {
174
        if (cleanup())
175 305 up20180642
        printf("%s: failed to cleanup.\n", __func__);
176 261 up20180642
        return 1;
177
    }
178 188 up20180642
179 261 up20180642
    if (cleanup()) {
180
        printf("%s: failed to cleanup.\n", __func__);
181
        return 1;
182
    }
183 155 up20180655
184 149 up20180655
    return 0;
185 147 up20180655
}
186 294 up20180642
187 308 up20180655
typedef struct __attribute__((packed)) {
188
    // player 1
189
    double player1_x;
190
    double player1_y;
191
    double player1_health;
192
    double player1_current_health;
193
194
    // player 2
195
    double player2_x;
196
    double player2_y;
197
    double player2_health;
198
    double player2_current_health;
199
200
    // bullets
201
    size_t no_bullets;
202
    double *bullets_x;
203
    double *bullets_y;
204
    double *bullets_vx;
205
    double *bullets_vy;
206
    bool   *bullet_shooter; // 0 for player 1, otherwise 1 for player 2
207
} host_info;
208
209
typedef struct __attribute__((packed)) {
210
    keys_t client_keys_pressed;
211
    int32_t client_mouse_x;
212
    int32_t client_mouse_y;
213
    size_t bullets_shot;
214
    double *bullets_x;
215
    double *bullets_y;
216
} client_info;
217
/*
218
static void host_to_client_process(const uint8_t *p, const size_t sz) {
219

220
}
221

222
static void client_to_host_process(const uint8_t *p, const size_t sz) {
223
}
224

225
static int (multiplayer)(void) {
226

227
    //int r;
228

229
    ent_set_scale(DEFAULT_SCALE);
230
    //text_timer_t *in_game_timer = timer_ctor(consolas);
231

232
    list_t *shooter_list = list_ctor();
233

234
    gunner_t *shooter1 = gunner_ctor(bsp_shooter, bsp_pistol, gunner_player, 1); if(shooter1 == NULL) printf("Failed to get shooter1\n");
235
    gunner_set_spawn(shooter1, 75, 75);
236

237
    gunner_t *shooter2 = gunner_ctor(bsp_shooter, bsp_pistol, gunner_player, 1); if(shooter2 == NULL) printf("Failed to get shooter2\n");
238
    gunner_set_spawn(shooter2, 975, 75);
239

240
    list_insert(shooter_list, list_end(shooter_list), shooter1);
241
    list_insert(shooter_list, list_end(shooter_list), shooter2);
242

243
    do {
244
        get_random_spawn(map1, shooter1, shooter_list);
245
        get_random_spawn(map1, shooter2, shooter_list);
246
    } while (distance_gunners(shooter1, shooter2) < 700);
247

248
    list_t *bullet_list  = list_ctor();
249

250
    ent_set_origin(gunner_get_x(shooter1)-ent_get_XLength()/2.0,
251
    gunner_get_y(shooter1)-ent_get_YLength()/2.0);
252

253
    //uint32_t refresh_count_value = sys_hz() / REFRESH_RATE;
254
    uint8_t last_lb = 0;
255
    struct packet pp;
256
    keys_t *keys = get_key_presses();
257

258
    /// loop stuff
259
    uint32_t int_vector = 0;
260
    int good = true;
261

262
    // incomplete
263

264
    return 0;
265
}*/
266
267 300 up20180642
static int (campaign)(void);
268 301 up20180642
static int (zombies)(void);
269 300 up20180642
static int (singleplayer)(void) {
270
271 295 up20180642
    int r;
272
273 300 up20180642
    menu_t *main_menu = menu_ctor(consolas);
274
    menu_add_item(main_menu, "Campaign");
275
    menu_add_item(main_menu, "Zombies");
276
    menu_add_item(main_menu, "Back");
277
278
    //uint32_t refresh_count_value = sys_hz() / REFRESH_RATE;
279
    uint8_t last_lb = 0;
280
    struct packet pp;
281
    keys_t *keys = get_key_presses();
282
283
    /// loop stuff
284
    int click = 0;
285 304 up20180642
    uint32_t int_vector = 0;
286 300 up20180642
    int good = true;
287
    while (good) {
288
        /* Get a request message. */
289 304 up20180642
        if((r = get_interrupts_vector(&int_vector))) return r;
290
        for (uint32_t i = 0, n = 1; i < 32; i++, n <<= 1) {
291
            if (int_vector & n) {
292
                interrupt_handler(i);
293
                switch (i) {
294 305 up20180642
                    case TIMER0_IRQ:
295 300 up20180642
296 304 up20180642
                    graph_clear_screen();
297
                    switch(menu_update_state(main_menu, click)){
298
                        case -1: break;
299
                        case  0: campaign(); break;
300
                        case  1: zombies(); break;
301
                        case  2: good = false; break;
302
                    }
303
                    menu_draw(main_menu);
304 300 up20180642
305 304 up20180642
                    click = 0;
306 300 up20180642
307 304 up20180642
                    sprite_set_pos(sp_crosshair, *get_mouse_X(), *get_mouse_Y());
308
                    sprite_draw(sp_crosshair);
309
                    graph_draw();
310 300 up20180642
311 304 up20180642
                    break;
312 305 up20180642
                    case KBC_IRQ:
313 304 up20180642
                    if ((scancode[0]) == ESC_BREAK_CODE) good = false;
314 305 up20180642
                    case MOUSE_IRQ:
315 304 up20180642
                    if (counter_mouse_ih >= 3) {
316
                        mouse_parse_packet(packet_mouse_ih, &pp);
317
                        update_mouse(&pp);
318
                        if (!click) click = last_lb ^ keys->lb_pressed && keys->lb_pressed;
319
                        last_lb = keys->lb_pressed;
320
                        counter_mouse_ih = 0;
321 300 up20180642
                    }
322
                    break;
323 305 up20180642
                    case COM1_IRQ: nctp_ih(); break;
324 304 up20180642
                }
325 300 up20180642
            }
326
        }
327
    }
328
329
    return 0;
330
}
331
332
static int (campaign)(void){
333
334
    int r;
335
336 295 up20180642
    ent_set_scale(DEFAULT_SCALE);
337
    text_timer_t *in_game_timer = timer_ctor(consolas);
338
339
    list_t *shooter_list = list_ctor();
340
341 302 up20180642
    gunner_t *shooter1 = gunner_ctor(bsp_shooter, bsp_pistol, gunner_player, 1); if(shooter1 == NULL) printf("Failed to get shooter1\n");
342 295 up20180642
    gunner_set_spawn(shooter1, 75, 75);
343
    gunner_set_pos(shooter1, 75, 75);
344
345 302 up20180642
    gunner_t *shooter2 = gunner_ctor(bsp_shooter, bsp_nothing, gunner_player, 2);
346 295 up20180642
    gunner_set_spawn(shooter2, 975, 75);
347
    gunner_set_pos(shooter2, 775, 75);
348
349
    list_insert(shooter_list, list_end(shooter_list), shooter1);
350
    list_insert(shooter_list, list_end(shooter_list), shooter2);
351
352
    list_t *bullet_list  = list_ctor();
353
354
    ent_set_origin(gunner_get_x(shooter1)-ent_get_XLength()/2.0,
355 305 up20180642
    gunner_get_y(shooter1)-ent_get_YLength()/2.0);
356 295 up20180642
357 305 up20180642
    //uint32_t refresh_count_value = sys_hz() / REFRESH_RATE;
358
    uint8_t last_lb = 0;
359
    struct packet pp;
360
    keys_t *keys = get_key_presses();
361 295 up20180642
362
    /// loop stuff
363 304 up20180642
    uint32_t int_vector = 0;
364 296 up20180642
    int good = true;
365
    while (good) {
366 304 up20180642
        /* Get a request message. */
367
        if((r = get_interrupts_vector(&int_vector))) return r;
368
        for (uint32_t i = 0, n = 1; i < 32; i++, n <<= 1) {
369 309 up20180642
            if(!good) break;
370 305 up20180642
            if (int_vector & n) {
371
                interrupt_handler(i);
372
                switch (i) {
373
                    case TIMER0_IRQ:
374 295 up20180642
375 305 up20180642
                    if (no_interrupts % 60 == 0) timer_update(in_game_timer);
376
                    update_movement(map1, shooter1, keys, shooter_list);
377 295 up20180642
378 305 up20180642
                    update_game_state(map1, shooter_list, bullet_list);
379 295 up20180642
380 305 up20180642
                    //update_scale();
381
                    double angle = get_mouse_angle(shooter1);
382
                    gunner_set_angle(shooter1, angle - M_PI_2);
383 295 up20180642
384 305 up20180642
                    ent_set_origin(gunner_get_x(shooter1)-ent_get_XLength()/2.0,
385
                    gunner_get_y(shooter1)-ent_get_YLength()/2.0);
386 295 up20180642
387 305 up20180642
                    graph_clear_screen();
388
                    map_draw   (map1);
389
                    bullet_draw_list(bullet_list);
390
                    gunner_draw_list(shooter_list);
391 295 up20180642
392 305 up20180642
                    text_draw(in_game_timer->text);
393 295 up20180642
394 305 up20180642
                    sprite_set_pos(sp_crosshair, *get_mouse_X(), *get_mouse_Y());
395
                    sprite_draw(sp_crosshair);
396
                    graph_draw();
397 295 up20180642
398 305 up20180642
                    break;
399
                    case KBC_IRQ:
400
                    if ((scancode[0]) == ESC_BREAK_CODE) {
401
                        good = false;
402
                    }
403
                    break;
404
                    case MOUSE_IRQ:
405
                    if (counter_mouse_ih >= 3) {
406
                        mouse_parse_packet(packet_mouse_ih, &pp);
407
                        update_mouse(&pp);
408
                        if (last_lb ^ keys->lb_pressed && keys->lb_pressed)
409
                        shoot_bullet(shooter1, bullet_list, bsp_bullet);
410
                        last_lb = keys->lb_pressed;
411
                        counter_mouse_ih = 0;
412 304 up20180642
413 305 up20180642
                    }
414
                    break;
415
                    case COM1_IRQ: nctp_ih(); break;
416
                }
417
            }
418 304 up20180642
        }
419 295 up20180642
    }
420
421
    while(list_size(shooter_list) > 0){
422
        gunner_t *p = list_erase(shooter_list, list_begin(shooter_list));
423
        gunner_dtor(p);
424
    }
425 296 up20180642
    if(list_dtor(shooter_list)) printf("COULD NOT DESTRUCT SHOOTER LIST\n");
426 295 up20180642
427 301 up20180642
    while(list_size(bullet_list) > 0){
428
        bullet_t *p = (bullet_t*)list_erase(bullet_list, list_begin(bullet_list));
429
        bullet_dtor(p);
430
    }
431
    if(list_dtor(bullet_list)) printf("COULD NOT DESTRUCT BULLET LIST\n");
432
433
    timer_dtor(in_game_timer); in_game_timer = NULL;
434
435
    return SUCCESS;
436
}
437
438
#define ZOMBIES_NUM             5
439
#define ZOMBIE_HEALTH_FACTOR    1.1
440
static int (zombies)(void){
441
442
    int r;
443
444
    ent_set_scale(DEFAULT_SCALE);
445
    text_timer_t *in_game_timer = timer_ctor(consolas);
446
447
    list_t *shooter_list = list_ctor();
448
449 302 up20180642
    gunner_t *shooter1 = gunner_ctor(bsp_shooter, bsp_pistol, gunner_player, 1); if(shooter1 == NULL) printf("Failed to get shooter1\n");
450 305 up20180642
    gunner_set_spawn(shooter1, 980, 790);
451
    gunner_set_pos(shooter1, 980, 790);
452 301 up20180642
453
    list_insert(shooter_list, list_end(shooter_list), shooter1);
454
455
    list_t *bullet_list  = list_ctor();
456
457
    ent_set_origin(gunner_get_x(shooter1)-ent_get_XLength()/2.0,
458 305 up20180642
    gunner_get_y(shooter1)-ent_get_YLength()/2.0);
459 301 up20180642
460 305 up20180642
    //uint32_t refresh_count_value = sys_hz() / REFRESH_RATE;
461
    uint8_t last_lb = 0;
462
    struct packet pp;
463
    keys_t *keys = get_key_presses();
464 301 up20180642
465
    /// loop stuff
466 304 up20180642
    uint32_t int_vector = 0;
467 301 up20180642
    int good = true;
468 302 up20180642
    int dead = false;
469 301 up20180642
470
    int health = 50;
471
472 309 up20180642
    /** #DEV */ /* {
473
        gunner_t *zombie = gunner_ctor(bsp_zombie, bsp_nothing, gunner_melee | gunner_follow, 3);
474
        gunner_set_health(zombie, health);
475
        gunner_set_curr_health(zombie, health);
476
        health *= ZOMBIE_HEALTH_FACTOR;
477
        gunner_set_pos(zombie, 1100, 75);
478
        list_push_back(shooter_list, zombie);
479
    }*/ //\#DEV
480
481
    map_make_dijkstra(map1, gunner_get_x(shooter1), gunner_get_y(shooter1));
482
483 302 up20180642
    while (good && !dead) {
484 304 up20180642
        /* Get a request message. */
485
        if((r = get_interrupts_vector(&int_vector))) return r;
486
        for (uint32_t i = 0, n = 1; i < 32; i++, n <<= 1) {
487 309 up20180642
            if(!good || dead) break;
488 304 up20180642
            if (int_vector & n) {
489 305 up20180642
                interrupt_handler(i);
490
                switch (i) {
491
                    case TIMER0_IRQ:
492
                    if (no_interrupts % 60 == 0) timer_update(in_game_timer);
493 309 up20180642
                    if (no_interrupts %  6 == 0){
494
                        map_make_dijkstra(map1, gunner_get_x(shooter1), gunner_get_y(shooter1));
495
                    }
496 301 up20180642
497 305 up20180642
                    update_movement(map1, shooter1, keys, shooter_list);
498 301 up20180642
499 305 up20180642
                    update_game_state(map1, shooter_list, bullet_list);
500 302 up20180642
501 305 up20180642
                    if(list_find(shooter_list, shooter1) == list_end(shooter_list)){
502
                        good = false;
503
                        dead = true;
504
                        break;
505
                    }
506 301 up20180642
507 305 up20180642
                    double angle = get_mouse_angle(shooter1);
508
                    gunner_set_angle(shooter1, angle - M_PI_2);
509 301 up20180642
510 305 up20180642
                    ent_set_origin(gunner_get_x(shooter1)-ent_get_XLength()/2.0,
511
                                   gunner_get_y(shooter1)-ent_get_YLength()/2.0);
512 301 up20180642
513 309 up20180642
                    while(list_size(shooter_list) < ZOMBIES_NUM+1){
514 305 up20180642
                        gunner_t *zombie = gunner_ctor(bsp_zombie, bsp_nothing, gunner_melee | gunner_follow, 3);
515
                        gunner_set_health(zombie, health);
516
                        gunner_set_curr_health(zombie, health);
517
                        health *= ZOMBIE_HEALTH_FACTOR;
518 307 up20180642
                        get_random_spawn(map1, zombie, shooter_list);
519 305 up20180642
                        list_push_back(shooter_list, zombie);
520
                    }
521 301 up20180642
522 305 up20180642
                    graph_clear_screen();
523
                    map_draw   (map1);
524
                    bullet_draw_list(bullet_list);
525
                    gunner_draw_list(shooter_list);
526 301 up20180642
527 305 up20180642
                    text_draw(in_game_timer->text);
528 301 up20180642
529 305 up20180642
                    sprite_set_pos(sp_crosshair, *get_mouse_X(), *get_mouse_Y());
530
                    sprite_draw(sp_crosshair);
531
                    graph_draw();
532 304 up20180642
533 305 up20180642
                    break;
534
                    case KBC_IRQ:
535
                    if ((scancode[0]) == ESC_BREAK_CODE) {
536
                        good = false;
537
                    }
538
                    break;
539
                    case MOUSE_IRQ:
540
                    if (counter_mouse_ih >= 3) {
541
                        mouse_parse_packet(packet_mouse_ih, &pp);
542
                        update_mouse(&pp);
543
                        if (last_lb ^ keys->lb_pressed && keys->lb_pressed)
544
                        shoot_bullet(shooter1, bullet_list, bsp_bullet);
545
                        last_lb = keys->lb_pressed;
546
                        counter_mouse_ih = 0;
547
548
                    }
549
                    break;
550
                    case COM1_IRQ: nctp_ih(); break;
551
                }
552
            }
553
        }
554 301 up20180642
    }
555
556
    while(list_size(shooter_list) > 0){
557
        gunner_t *p = list_erase(shooter_list, list_begin(shooter_list));
558
        gunner_dtor(p);
559
    }
560
    if(list_dtor(shooter_list)) printf("COULD NOT DESTRUCT SHOOTER LIST\n");
561
562 295 up20180642
    while(list_size(bullet_list) > 0){
563
        bullet_t *p = (bullet_t*)list_erase(bullet_list, list_begin(bullet_list));
564
        bullet_dtor(p);
565
    }
566
    if(list_dtor(bullet_list)) printf("COULD NOT DESTRUCT BULLET LIST\n");
567
568 302 up20180642
    if(dead){
569
        printf("YOU DIED\n");
570
    }
571
572 295 up20180642
    timer_dtor(in_game_timer); in_game_timer = NULL;
573
574 294 up20180642
    return SUCCESS;
575
}
576 296 up20180642
577 298 up20180642
#define CHAT_MAX_SIZE   75
578
#define CHAT_MAX_NUM    19
579 297 up20180642
text_t      *t_text[CHAT_MAX_NUM] = {NULL};
580
rectangle_t *r_text               =  NULL;
581
static void chat_process(const uint8_t *p, const size_t sz){
582
    char buffer2[CHAT_MAX_NUM+3];
583
    void *dest = NULL;
584
    hltp_type tp = hltp_interpret(p, sz, &dest);
585
    switch(tp){
586
        case hltp_type_string:
587 305 up20180642
        strcpy(buffer2, dest);
588
        strncat(buffer2, " <", 2);
589
        for(size_t i = CHAT_MAX_NUM-1; i; --i)
590
        text_set_text(t_text[i], text_get_string(t_text[i-1]));
591
        text_set_text(t_text[0], buffer2);
592
        for(size_t i = 0; i < CHAT_MAX_NUM; ++i){
593
            if(text_get_string(t_text[i])[0] == '>'){
594
                text_set_pos(t_text[i], rectangle_get_x(r_text)+50, text_get_y(t_text[i]));
595
                text_set_halign(t_text[i], text_halign_left);
596
            }else{
597
                text_set_pos(t_text[i], rectangle_get_x(r_text)+rectangle_get_w(r_text)-50, text_get_y(t_text[i]));
598
                text_set_halign(t_text[i], text_halign_right);
599 297 up20180642
            }
600 305 up20180642
        }
601
        break;
602 297 up20180642
        default: break;
603
    }
604
}
605 300 up20180642
static int (chat)(void){
606 297 up20180642
    int r;
607
608 298 up20180642
    nctp_dump();
609 297 up20180642
    nctp_set_processor(chat_process);
610
611
    struct packet pp;
612
613 298 up20180642
    char buffer[CHAT_MAX_SIZE] = "";
614 297 up20180642
    rectangle_t *r_buffer = NULL; {
615 298 up20180642
        r_buffer = rectangle_ctor(0,0,900,70);
616 297 up20180642
        rectangle_set_pos(r_buffer, graph_get_XRes()/2  -rectangle_get_w(r_buffer)/2,
617 305 up20180642
        graph_get_YRes()*0.87-rectangle_get_h(r_buffer)/2);
618 297 up20180642
        rectangle_set_fill_color   (r_buffer, GRAPH_BLACK);
619
        rectangle_set_outline_width(r_buffer, 2);
620
        rectangle_set_outline_color(r_buffer, GRAPH_WHITE);
621
        rectangle_set_fill_trans(r_buffer, GRAPH_TRANSPARENT);
622
    }
623
    text_t      *t_buffer = NULL; {
624
        t_buffer = text_ctor(consolas, "");
625
        text_set_pos(t_buffer, rectangle_get_x(r_buffer)+50,
626 305 up20180642
        rectangle_get_y(r_buffer)+rectangle_get_h(r_buffer)/2);
627 297 up20180642
        text_set_halign(t_buffer, text_halign_left);
628
        text_set_valign(t_buffer, text_valign_center);
629
        text_set_color (t_buffer, TEXT_COLOR);
630
    }
631 298 up20180642
    text_t      *t_size   = NULL; {
632
        t_size = text_ctor(consolas, "");
633
        text_set_pos(t_size, rectangle_get_x(r_buffer)+rectangle_get_w(r_buffer)-5,
634 305 up20180642
        rectangle_get_y(r_buffer)+rectangle_get_h(r_buffer)-5);
635 298 up20180642
        text_set_halign(t_size, text_halign_right);
636
        text_set_valign(t_size, text_valign_bottom);
637
        text_set_color (t_size, TEXT_COLOR);
638
        text_set_size  (t_size, 18);
639
        char buffer2[20];
640
        sprintf(buffer2, "%d/%d", strlen(buffer), CHAT_MAX_SIZE);
641
        text_set_text(t_size, buffer2);
642
    }
643 297 up20180642
644
    /** r_text */ {
645 305 up20180642
    r_text = rectangle_ctor(0,0,900,550);
646
    rectangle_set_pos(r_text, graph_get_XRes()/2  -rectangle_get_w(r_buffer)/2,
647
    graph_get_YRes()*0.09);
648
    rectangle_set_fill_color   (r_text, GRAPH_BLACK);
649
    rectangle_set_outline_width(r_text, 2);
650
    rectangle_set_outline_color(r_text, GRAPH_WHITE);
651
    rectangle_set_fill_trans(r_text, GRAPH_TRANSPARENT);
652
}
653
/** t_text */ {
654
for(size_t i = 0; i < CHAT_MAX_NUM; ++i){
655
    t_text[i] = text_ctor(consolas, " ");
656
    text_set_pos(t_text[i], rectangle_get_x(r_text)+50,
657
    rectangle_get_y(r_text)+rectangle_get_h(r_text)-30-25*i);
658
    text_set_halign(t_text[i], text_halign_left);
659
    text_set_valign(t_text[i], text_valign_bottom);
660
    text_set_color (t_text[i], TEXT_COLOR);
661
}
662
}
663 297 up20180642
664 305 up20180642
/// loop stuff
665
uint32_t int_vector = 0;
666
int good = true;
667
while (good) {
668
    /* Get a request message. */
669
    if((r = get_interrupts_vector(&int_vector))) return r;
670
    for (uint32_t i = 0, n = 1; i < 32; i++, n <<= 1) {
671
        if (int_vector & n) {
672
            interrupt_handler(i);
673
            switch (i) {
674 304 up20180642
                case TIMER0_IRQ:
675 305 up20180642
                graph_clear_screen();
676
                sprite_set_pos(sp_crosshair, *get_mouse_X(), *get_mouse_Y());
677 297 up20180642
678 305 up20180642
                rectangle_draw(r_buffer);
679
                text_draw(t_buffer);
680
                text_draw(t_size);
681 297 up20180642
682 305 up20180642
                rectangle_draw(r_text);
683
                for(size_t i = 0; i < CHAT_MAX_NUM; ++i) text_draw(t_text[i]);
684 297 up20180642
685 305 up20180642
                sprite_draw(sp_crosshair);
686
                graph_draw();
687
                break;
688 304 up20180642
                case KBC_IRQ:
689 305 up20180642
                if      (scancode[0] == ESC_BREAK_CODE) good = false;
690
                else if (scancode[0] == ENTER_MAKE_CODE) {
691
                    hltp_send_string(buffer);
692
                    char buffer2[CHAT_MAX_SIZE+3] = "> ";
693
                    strncat(buffer2, buffer, strlen(buffer));
694
                    for(size_t i = CHAT_MAX_NUM-1; i; --i)
695
                    text_set_text(t_text[i], text_get_string(t_text[i-1]));
696
                    text_set_text(t_text[0], buffer2);
697
                    for(size_t i = 0; i < CHAT_MAX_NUM; ++i){
698
                        if(text_get_string(t_text[i])[0] == '>'){
699
                            text_set_pos(t_text[i], rectangle_get_x(r_text)+50, text_get_y(t_text[i]));
700
                            text_set_halign(t_text[i], text_halign_left);
701
                        }else{
702
                            text_set_pos(t_text[i], rectangle_get_x(r_text)+rectangle_get_w(r_text)-50, text_get_y(t_text[i]));
703
                            text_set_halign(t_text[i], text_halign_right);
704 297 up20180642
                        }
705
                    }
706 305 up20180642
                    buffer[0] = '\0';
707
                } else if(scancode[0] == BACKSPACE_MAKE_CODE){
708
                    buffer[strlen(buffer)-1] = '\0';
709
                } else {
710
                    char c = map_makecode(scancode[0]);
711
                    if (c == ERROR_CODE) break;
712
                    if(strlen(buffer) < CHAT_MAX_SIZE) strncat(buffer, &c, 1);
713
                    else                               printf("Char limit exceeded\n");
714
                }
715
                text_set_text(t_buffer, buffer);
716
                char buffer2[20];
717
                sprintf(buffer2, "%d/%d", strlen(buffer), CHAT_MAX_SIZE);
718
                text_set_text(t_size, buffer2);
719 304 up20180642
                case MOUSE_IRQ:
720 305 up20180642
                if (counter_mouse_ih >= 3) {
721
                    mouse_parse_packet(packet_mouse_ih, &pp);
722
                    update_mouse(&pp);
723
                    counter_mouse_ih = 0;
724
                }
725
                break;
726 304 up20180642
                case COM1_IRQ: nctp_ih(); break;
727 297 up20180642
            }
728
        }
729
    }
730 305 up20180642
}
731 297 up20180642
732 305 up20180642
rectangle_dtor(r_buffer);
733
text_dtor     (t_buffer);
734 297 up20180642
735 305 up20180642
rectangle_dtor(r_text);
736
for(size_t i = 0; i < CHAT_MAX_NUM; ++i) text_dtor(t_text[i]);
737 297 up20180642
738 305 up20180642
nctp_set_processor(NULL);
739 298 up20180642
740 305 up20180642
return SUCCESS;
741 296 up20180642
}