/* * bullets.c * * Handle bullets (shots and clusterbombs) in flight */ #include #include #include #include #include #include "graphics.h" #include "grv.h" struct bullet { int x, y; /* Current location */ int dx, dy; /* Direction of movement */ int color; /* Color */ }; #define MAX_BULLETS 57 /* 8 clusterbombs*7 shards + 1 player shot */ /* Two lists; flip between loops */ static struct bullet bullet_lists[2][MAX_BULLETS]; static struct bullet *bullets = bullet_lists[0]; static int bullet_list = 0; static int nbullets = 0; /* * Add a bullet to the list */ void add_bullet(int x, int y, int dx, int dy, int color) { int n; if ( nbullets >= MAX_BULLETS ) return; n = nbullets++; bullets[n].x = x; bullets[n].y = y; bullets[n].dx = dx; bullets[n].dy = dy; bullets[n].color = color; } /* * Run bullet action */ void run_bullets(void) { struct bullet *b, *bb, *eb; int x, y, s, f; int live; int hpp; while ( nbullets ) { bb = bullets; eb = &bullets[nbullets]; /* Flip lists and initialize to zero */ bullet_list ^= 1; bullets = bullet_lists[bullet_list]; nbullets = 0; for ( b = bb ; b < eb ; b++ ) { live = 1; x = (b->x += b->dx); y = (b->y += b->dy); if ( x < 2 || x > 23 || y < 1 || y > 40 ) { live = 0; b->color = 0; /* Don't draw */ } else { s = screen(x, y); f = bg(x, y); if ( strchr("\xfe\xb0\xb1\xe5\xec\x04?" DOORS, s) ) { live = 0; b->color = 0; } else { color(b->color, f); lprint(x,y,"\xf9"); switch ( s ) { case SYM_CHERRY: take_cherry(); live = 0; break; case SYM_DIAMOND: take_diamond(); live = 0; break; case SYM_GHOST: kill_ghost(x,y); live = 0; break; case 'H': hpp = 0; goto hyper; case 'Y': hpp = 1; goto hyper; case 'P': hpp = 2; goto hyper; case 'E': hpp = 3; goto hyper; case 'R': hpp = 4; goto hyper; hyper: gp.Hyp++; color(15,gp.c); lprintf(25, 31+hpp*2, "%c", s); live = 0; break; case SYM_CLUSTER: { int di, dj; for ( di = -1 ; di <= 1 ; di++ ) for ( dj = -1 ; dj <= 1 ; dj++ ) if ( (di||dj) && (di!=-b->dx || dj!=-b->dy) ) add_bullet(x,y,di,dj,12); live = 0; } break; default: break; } } } if ( live ) add_bullet(x,y,b->dx,b->dy,b->color); } update_score(); mymssleep(10); /* Allow the user to notice :) */ /* Erase bullets */ for ( b = bb ; b < eb ; b++ ) { if ( b->color ) { color(0,bg(b->x,b->y)); lprint(b->x,b->y," "); } } } }