source: ttyvaders/trunk/src/collide.c @ 50

Last change on this file since 50 was 50, checked in by Sam Hocevar, 17 years ago
  • the beam now digs the tunnel.
  • the starfield is now an array of stars.
  • fixed wall rendering (offset issues and disappearing left wall).
  • 32 seekers on fragbomb explosion, not 16.
File size: 7.8 KB
Line 
1/*
2 *   ttyvaders     Textmode shoot'em up
3 *   Copyright (c) 2002 Sam Hocevar <sam@zoy.org>
4 *                 All Rights Reserved
5 *
6 *   $Id: collide.c,v 1.8 2002/12/23 09:28:37 sam Exp $
7 *
8 *   This program is free software; you can redistribute it and/or modify
9 *   it under the terms of the GNU General Public License as published by
10 *   the Free Software Foundation; either version 2 of the License, or
11 *   (at your option) any later version.
12 *
13 *   This program is distributed in the hope that it will be useful,
14 *   but WITHOUT ANY WARRANTY; without even the implied warranty of
15 *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16 *   GNU General Public License for more details.
17 *
18 *   You should have received a copy of the GNU General Public License
19 *   along with this program; if not, write to the Free Software
20 *   Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
21 */
22
23#include <stdlib.h>
24
25#include "common.h"
26
27void collide_weapons_tunnel( game *g, weapons *wp, tunnel *t, explosions *ex )
28{
29    int i, j, x, y;
30
31    for( i = 0; i < WEAPONS; i++ )
32    {
33        x = wp->x[i] >> 4;
34        y = wp->y[i] >> 4;
35
36        switch( wp->type[i] )
37        {
38        case WEAPON_LIGHTNING:
39        case WEAPON_NONE:
40            break;
41        case WEAPON_SEEKER:
42        case WEAPON_BOMB:
43        case WEAPON_FRAGBOMB:
44            if( x <= t->left[y]
45                 || x >= t->right[y] )
46            {
47                int damage = wp->type[i] == WEAPON_SEEKER ? 1 : 2;
48
49                add_explosion( g, ex, x, y, 0, 1, wp->type[i] == WEAPON_SEEKER ? EXPLOSION_SMALL : EXPLOSION_MEDIUM );
50
51                if( x <= t->left[y] )
52                {
53                    t->right[y-2] -= damage - 1;
54                    t->left[y-1] -= damage;
55                    t->left[y] -= damage + 1;
56                    t->left[y+1] -= damage;
57                    t->right[y+2] -= damage - 1;
58                }
59                else
60                {
61                    t->right[y-2] += damage - 1;
62                    t->right[y-1] += damage;
63                    t->right[y] += damage + 1;
64                    t->right[y+1] += damage;
65                    t->right[y+2] += damage - 1;
66                }
67
68                if( wp->type[i] == WEAPON_FRAGBOMB )
69                {
70                    wp->n[i] = -1;
71                }
72                else
73                {
74                    wp->type[i] = WEAPON_NONE;
75                }
76            }
77            break;
78        case WEAPON_LASER:
79            for( j = GET_MIN( 0, wp->vy[i] >> 4 ) ;
80                 j < GET_MAX( 0, wp->vy[i] >> 4 ) ;
81                 j++ )
82            {
83                if( x <= t->left[y+j] || x >= t->right[y+j] )
84                {
85                    add_explosion( g, ex, x, y+j, 0, 1, EXPLOSION_SMALL );
86                    wp->type[i] = WEAPON_NONE;
87
88                    if( x <= t->left[y+j] )
89                    {
90                        t->left[y+j-1]--;
91                        t->left[y+j] -= 2;
92                        t->left[y+j+1]--;
93                    }
94                    else
95                    {
96                        t->right[y+j-1]++;
97                        t->right[y+j] += 2;
98                        t->right[y+j+1]++;
99                    }
100                    break;
101                }
102            }
103            break;
104        case WEAPON_BEAM:
105            if( wp->n[i] > 19 )
106            {
107                break;
108            }
109
110            j = (29 - wp->n[i]) * (29 - wp->n[i]) / 8;
111            j = GET_MIN( y, j );
112
113            for( ; j > 0 ; j-- )
114            {
115                if( x - 2 <= t->left[y-j] )
116                {
117                    add_explosion( g, ex, GET_MIN(t->left[y-j], x+3), y-j, 0, 1, EXPLOSION_SMALL );
118                    t->left[y-j] -= GET_RAND(0,3);
119                }
120                else if( x + 3 >= t->right[y-j] )
121                {
122                    add_explosion( g, ex, GET_MAX(t->right[y-j], x-2), y-j, 0, 1, EXPLOSION_SMALL );
123                    t->right[y-j] += GET_RAND(0,3);
124                }
125            }
126            break;
127
128        case WEAPON_NUKE:
129            /* The nuke does not break the tunnel */
130            break;
131        }
132    }
133}
134
135void collide_weapons_aliens( game *g, weapons *wp, aliens *al, explosions *ex )
136{
137    int i, j, k, x, y;
138
139    for( i = 0; i < WEAPONS; i++ )
140    {
141        int ok = 0;
142        int r;
143
144        x = wp->x[i] >> 4;
145        y = wp->y[i] >> 4;
146
147        switch( wp->type[i] )
148        {
149        case WEAPON_LIGHTNING:
150        case WEAPON_NONE:
151            break;
152        case WEAPON_NUKE:
153            /* Big nuke */
154            r = (29 - wp->n[i]) * (29 - wp->n[i]) / 8;
155
156            for( j = 0; j < ALIENS; j++ )
157            {
158                if( al->type[j] == ALIEN_NONE || al->life[j] < 0 )
159                {
160                    continue;
161                }
162
163                if( wp->n[i] == 0 /* Nuke destroys _everything_ */ ||
164                    (al->x[j] - x) * (al->x[j] - x)
165                      + 4 * (al->y[j] - y) * (al->y[j] - y)
166                    <= r * r )
167                {
168                    /* Kill alien, not nuke */
169                    al->life[j] -= 10;
170                }
171            }
172            break;
173
174        case WEAPON_BEAM:
175            if( wp->n[i] > 19 )
176            {
177                break;
178            }
179
180            r = (29 - wp->n[i]) * (29 - wp->n[i]) / 8;
181
182            for( j = 0; j < ALIENS; j++ )
183            {
184                if( al->type[j] == ALIEN_NONE || al->life[j] < 0 )
185                {
186                    continue;
187                }
188
189                if( x >= al->x[j] && x <= al->x[j] + 4
190                     && y >= al->y[j] + 2 && y-5-r <= al->y[j] )
191                {
192                    al->life[j] -= 4;
193                }
194            }
195            break;
196
197        case WEAPON_LASER:
198            for( j = 0; j < ALIENS; j++ )
199            {
200                if( al->type[j] == ALIEN_NONE || al->life[j] < 0 )
201                {
202                    continue;
203                }
204
205                for( k = GET_MIN( 0, wp->vy[i] >> 4 ) ;
206                     k < GET_MAX( 0, wp->vy[i] >> 4 ) ;
207                     k++ )
208                {
209                    if( x >= al->x[j] && x <= al->x[j] + 4
210                         && y+k >= al->y[j] && y+k <= al->y[j] + 2 )
211                    {
212                        al->life[j]--;
213                        ok = 1;
214                        break;
215                    }
216                }
217            }
218
219            if( ok )
220            {
221                add_explosion( g, ex, x, y+1, 0, 0, EXPLOSION_SMALL );
222                wp->type[i] = WEAPON_NONE;
223            }
224            break;
225
226        case WEAPON_SEEKER:
227        case WEAPON_BOMB:
228        case WEAPON_FRAGBOMB:
229            for( j = 0; j < ALIENS; j++ )
230            {
231                if( al->type[j] == ALIEN_NONE || al->life[j] < 0 )
232                {
233                    continue;
234                }
235
236                if( x >= al->x[j] && x <= al->x[j] + 4
237                     && y >= al->y[j] && y <= al->y[j] + 2 )
238                {
239                    al->life[j] -= wp->type[i] == WEAPON_SEEKER ? 1 : 5;
240                    ok = 1;
241                }
242            }
243
244            if( ok )
245            {
246                add_explosion( g, ex, x, y+1, 0, 0, wp->type[i] == WEAPON_SEEKER ? EXPLOSION_SMALL : EXPLOSION_MEDIUM );
247
248                if( wp->type[i] == WEAPON_FRAGBOMB )
249                {
250                    wp->n[i] = -1;
251                }
252                else
253                {
254                    wp->type[i] = WEAPON_NONE;
255                }
256            }
257            break;
258        }
259    }
260}
261
262void collide_player_tunnel( game *g, player *p, tunnel *t, explosions *ex )
263{
264    if( p->x <= t->left[p->y] )
265    {
266        p->x += 2;
267        add_explosion( g, ex, p->x+1, p->y-2, 0, 0, EXPLOSION_SMALL );
268    }
269    else if( p->x + 5 >= t->right[p->y] )
270    {
271        p->x -= 2;
272        add_explosion( g, ex, p->x+4, p->y-2, 0, 0, EXPLOSION_SMALL );
273    }
274}
275
Note: See TracBrowser for help on using the repository browser.