fix remapping behavior. Remapping is only necessary if we are rendering on the workbe...
[AROS-Contrib.git] / Games / XInvaders3D / aliens.c
blob4e298c3e93d4b38b31e8e288587d846ea1e39c43
1 /*------------------------------------------------------------------
2 aliens.c:
4 XINVADERS 3D - 3d Shoot'em up
5 Copyright (C) 2000 Don Llopis
7 This program is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 2 of the License, or
10 (at your option) any later version.
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
17 You should have received a copy of the GNU General Public License
18 along with this program; if not, write to the Free Software
19 Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
21 ------------------------------------------------------------------*/
22 #include "game.h"
25 #define ALIEN_RADIUS 20.0f
26 #define ALIEN_RADIUS_SQUARED 400.0f
27 #define BOMB_RADIUS 20.0f
28 #define BOMB_RADIUS_SQUARED 400.0f
30 #define UFO_RADIUS 20.0f
31 #define UFO_RADIUS_SQUARED 400.0f
32 #define UFO_MIN_X_POS -600.0f
33 #define UFO_MAX_X_POS 600.0f
34 #define UFO_Z_POS -950.0f
36 #define FORMATRIX4ION_X_INC 75.0f
37 #define FORMATRIX4ION_Y_INC 100.0f
38 #define FORMATRIX4ION_MAX_X_POS 550.0f
39 #define FORMATRIX4ION_MIN_X_POS -550.0f
40 #define FORMATRIX4ION_MAX_Y_POS 450.0f
41 #define FORMATRIX4ION_MIN_Y_POS 50.0f
42 #define FORMATRIX4ION_MAX_Z_POS -850.0f
43 #define FORMATRIX4ION_MIN_Z_POS 50.0f
45 enum alien_enum
47 MAX_FORMATRIX4IONS = 5,
48 MAX_ALIENS = 40,
49 ALIENS_PER_FORMATRIX4ION = 8,
50 MAX_BOMBS = 12,
52 LEFT = 0,
53 RIGHT = 1,
54 FORWARD = 2,
55 DIRECTION_TOGGLE = 1,
56 ANIMATRIX4ION_TOGGLE = 1,
58 MAX_COLUMNS = 8,
59 START_LEAD_COLUMN = 7,
60 FORMATRIX4ION_STEP = 3, /* dist_between_aliens / thurust */
61 FORWARD_START = 21, /* formation x FORMATRIX4ION_STEP */
62 FORWARD_MAX = 45, /* must calc by hand */
63 FORWARD_MIN = 0,
65 DROP_BOMB_TIME = 500, /* 0.5 sec */
66 DROP_BOMB_CHANCE_1 = 50,
67 DROP_BOMB_CHANCE_2 = 40,
69 UFO_ZONE = 9,
70 UFO_LIGHTS_CYCLE = 250,
71 SPAWN_UFO_TIME = 5000,
72 SPAWN_UFO_CHANCE_1 = 10,
73 SPAWN_UFO_CHANCE_2 = 5
76 OBJECT aliens [MAX_ALIENS];
77 OBJECT bombs [MAX_BOMBS];
78 OBJECT alien_ufo, *ufo;
79 OBJECT the_formation;
81 OBJLIST flist[MAX_FORMATRIX4IONS], *af_list;
82 OBJLIST abomblist, *abombs;
84 /* formation speed in msec */
85 static int fspeed[9] = { 1000, 750, 500,
86 400, 400, 300,
87 200, 150, 100 };
89 static VECTOR4 fstart_pos =
91 FORMATRIX4ION_MIN_X_POS,
92 FORMATRIX4ION_MIN_Y_POS,
93 FORMATRIX4ION_MAX_Z_POS,
94 1.0f
96 static VECTOR4 fstart_dir = { 0.0f, 0.0f, 1.0f, 1.0f };
98 static VECTOR4 fthrust[3] = { { -25.0f, 0.0f, 0.0f, 1.0f },
99 { 25.0f, 0.0f, 0.0f, 1.0f },
100 { 0.0f, 0.0f, 100.0f, 1.0f } };
102 static VECTOR4 abomb_thrust = { 0.0f, 0.0f, 25.0f, 1.0f };
103 static VECTOR4 ufo_thrust = { 5.0f, 0.0f, 0.0f, 1.0f };
105 static VECTOR4 avert1[48] = {
106 { -20.0f, 20.0f, 0.0f, 1.0f }, /* A0: body*/
107 { 20.0f, 20.0f, 0.0f, 1.0f },
108 { 20.0f, 0.0f, 0.0f, 1.0f },
109 { -20.0f, 0.0f, 0.0f, 1.0f },
110 { 0.0f, 0.0f, 0.0f, 1.0f }, /* A0: legs*/
111 { -20.0f, -10.0f, 0.0f, 1.0f },
112 { -15.0f, -15.0f, 0.0f, 1.0f },
113 { -20.0f, -25.0f, 0.0f, 1.0f },
114 { 20.0f, -10.0f, 0.0f, 1.0f },
115 { 15.0f, -15.0f, 0.0f, 1.0f },
116 { 20.0f, -25.0f, 0.0f, 1.0f },
117 { 0.0f, 10.0f, 0.0f, 1.0f }, /* A0: eyes*/
118 { -15.0, 18.0f, 0.0f, 1.0f },
119 { -15.0, 2.0f, 0.0f, 1.0f },
120 { 15.0, 18.0f, 0.0f, 1.0f },
121 { 15.0, 2.0f, 0.0f, 1.0f },
123 { -15.0f, 20.0f, 0.0f, 1.0f }, /* A1: body*/
124 { 15.0f, 20.0f, 0.0f, 1.0f },
125 { 5.0f, 0.0f, 0.0f, 1.0f },
126 { -5.0f, 0.0f, 0.0f, 1.0f },
127 { 0.0f, 0.0f, 0.0f, 1.0f }, /* A1: legs*/
128 { -20.0f, -10.0f, 0.0f, 1.0f },
129 { -15.0f, -15.0f, 0.0f, 1.0f },
130 { -20.0f, -25.0f, 0.0f, 1.0f },
131 { 20.0f, -10.0f, 0.0f, 1.0f },
132 { 15.0f, -15.0f, 0.0f, 1.0f },
133 { 20.0f, -25.0f, 0.0f, 1.0f },
134 { 0.0f, 0.0f, 0.0f, 1.0f }, /* A1: eyes*/
135 { -20.0, 15.0f, 0.0f, 1.0f },
136 { -15.0, 0.0f, 0.0f, 1.0f },
137 { 20.0, 15.0f, 0.0f, 1.0f },
138 { 15.0, 0.0f, 0.0f, 1.0f },
140 { -5.0f, 20.0f, 0.0f, 1.0f }, /* A2: body*/
141 { 5.0f, 20.0f, 0.0f, 1.0f },
142 { 20.0f, 0.0f, 0.0f, 1.0f },
143 { -20.0f, 0.0f, 0.0f, 1.0f },
144 { 0.0f, 0.0f, 0.0f, 1.0f }, /* A2: legs*/
145 { -20.0f, -10.0f, 0.0f, 1.0f },
146 { -15.0f, -15.0f, 0.0f, 1.0f },
147 { -20.0f, -25.0f, 0.0f, 1.0f },
148 { 20.0f, -10.0f, 0.0f, 1.0f },
149 { 15.0f, -15.0f, 0.0f, 1.0f },
150 { 20.0f, -25.0f, 0.0f, 1.0f },
151 { 0.0f, 20.0f, 0.0f, 1.0f }, /* A2: eyes*/
152 { -20.0, 25.0f, 0.0f, 1.0f },
153 { -15.0, 15.0f, 0.0f, 1.0f },
154 { 20.0, 25.0f, 0.0f, 1.0f },
155 { 15.0, 15.0f, 0.0f, 1.0f }
158 static VECTOR4 avert2[48] = {
159 { -20.0f, 20.0f, 0.0f, 1.0f }, /*A0: body*/
160 { 20.0f, 20.0f, 0.0f, 1.0f },
161 { 20.0f, 0.0f, 0.0f, 1.0f },
162 { -20.0f, 0.0f, 0.0f, 1.0f },
163 { 0.0f, 0.0f, 0.0f, 1.0f }, /*A0: legs*/
164 { -10.0f, -5.0f, 0.0f, 1.0f },
165 { -5.0f, -10.0f, 0.0f, 1.0f },
166 { -10.0f, -25.0f, 0.0f, 1.0f },
167 { 10.0f, -5.0f, 0.0f, 1.0f },
168 { 5.0f, -10.0f, 0.0f, 1.0f },
169 { 10.0f, -25.0f, 0.0f, 1.0f },
170 { 0.0f, 15.0f, 0.0f, 1.0f }, /* A0: eyes*/
171 { -10.0, 25.0f, 0.0f, 1.0f },
172 { -15.0, 7.0f, 0.0f, 1.0f },
173 { 10.0, 25.0f, 0.0f, 1.0f },
174 { 15.0, 7.0f, 0.0f, 1.0f },
176 { -15.0f, 20.0f, 0.0f, 1.0f }, /* A1: body*/
177 { 15.0f, 20.0f, 0.0f, 1.0f },
178 { 5.0f, 0.0f, 0.0f, 1.0f },
179 { -5.0f, 0.0f, 0.0f, 1.0f },
180 { 0.0f, 0.0f, 0.0f, 1.0f }, /*A1: legs*/
181 { -10.0f, -5.0f, 0.0f, 1.0f },
182 { -5.0f, -10.0f, 0.0f, 1.0f },
183 { -10.0f, -30.0f, 0.0f, 1.0f },
184 { 10.0f, -5.0f, 0.0f, 1.0f },
185 { 5.0f, -10.0f, 0.0f, 1.0f },
186 { 10.0f, -30.0f, 0.0f, 1.0f },
187 { 0.0f, 10.0f, 0.0f, 1.0f }, /* A1: eyes*/
188 { -20.0, 15.0f, 0.0f, 1.0f },
189 { -15.0, 0.0f, 0.0f, 1.0f },
190 { 20.0, 15.0f, 0.0f, 1.0f },
191 { 15.0, 0.0f, 0.0f, 1.0f },
193 { -5.0f, 20.0f, 0.0f, 1.0f }, /* A2: body*/
194 { 5.0f, 20.0f, 0.0f, 1.0f },
195 { 20.0f, 0.0f, 0.0f, 1.0f },
196 { -20.0f, 0.0f, 0.0f, 1.0f },
197 { 0.0f, 0.0f, 0.0f, 1.0f }, /*A2: legs*/
198 { -10.0f, -5.0f, 0.0f, 1.0f },
199 { -5.0f, -10.0f, 0.0f, 1.0f },
200 { -10.0f, -30.0f, 0.0f, 1.0f },
201 { 10.0f, -5.0f, 0.0f, 1.0f },
202 { 5.0f, -10.0f, 0.0f, 1.0f },
203 { 10.0f, -30.0f, 0.0f, 1.0f },
204 { 0.0f, 5.0f, 0.0f, 1.0f }, /* A2: eyes*/
205 { -20.0, 20.0f, 0.0f, 1.0f },
206 { -15.0, 0.0f, 0.0f, 1.0f },
207 { 20.0, 20.0f, 0.0f, 1.0f },
208 { 15.0, 0.0f, 0.0f, 1.0f }
211 static VECTOR4 abomb_vert[3] = {
212 { -10.0f, 0.0f, -10.0f, 1.0f },
213 { 0.0f, 0.0f, 10.0f, 1.0f },
214 { 10.0f, 0.0f, -10.0f, 1.0f }
217 static VECTOR4 abomb_vert2[3] = {
218 { 0.0f, 10.0f, 0.0f, 1.0f },
219 { 0.0f, 0.0f, 10.0f, 1.0f },
220 { 0.0f, -10.0f, 0.0f, 1.0f }
223 static VECTOR4 uvert1[17] = {
224 { -20.0f, 0.0f, 0.0f, 1.0f }, /* UFO body */
225 { -10.0f, 10.0f, 0.0f, 1.0f },
226 { 10.0f, 10.0f, 0.0f, 1.0f },
227 { 20.0f, 0.0f, 0.0f, 1.0f },
228 { -20.0f, -20.0f, 0.0f, 1.0f }, /* left leg */
229 { -10.0f, 0.0f, 0.0f, 1.0f },
230 { -5.0f, 0.0f, 0.0f, 1.0f },
231 { 20.0f, -20.0f, 0.0f, 1.0f }, /* right leg */
232 { 10.0f, 0.0f, 0.0f, 1.0f },
233 { 5.0f, 0.0f, 0.0f, 1.0f },
234 { -10.0f, 10.0f, 0.0f, 1.0f }, /* top */
235 { 0.0f, 20.0f, 0.0f, 1.0f },
236 { 10.0f, 10.0f, 1.0f, 1.0f },
237 { -15.0f, 5.0f, 0.0f, 1.0f }, /* windows */
238 { -5.0f, 5.0f, 0.0f, 1.0f },
239 { 5.0f, 5.0f, 0.0f, 1.0f },
240 { 15.0f, 5.0f, 0.0f, 1.0f }
243 struct invaders
245 int move; /* FORMATRIX4ION move sideways timer */
246 int forward; /* FORMATRIX4ION move forward counter */
247 int forward_max; /* FORMATRIX4ION move forward max */
248 int leadcol; /* FORMATRIX4ION lead column */
249 int anim; /* FORMATRIX4ION animation counter */
250 int fdir; /* FORMATRIX4ION movement direction */
251 int scur; /* FORMATRIX4ION speed variable */
252 int drop_bomb; /* drop bomb timer */
254 int column[MAX_COLUMNS]; /* FORMATRIX4ION column count */
256 int spawn_ufo; /* spawn ufo timer */
257 int ucolor; /* ufo lights cycle timer */
258 } invaders;
260 static void Add_bomb ( OBJECT * );
262 /*================================================================*/
264 void Aliens_init ( void )
266 int i, j;
267 VECTOR4 tmp_pos;
268 OBJECT *alien;
269 OBJLIST *f_ptr;
271 /* initialize formations */
274 * the formation is a dummy-object used for
275 * object-sorting purposes
277 Object_init ( &the_formation );
278 Object_set_drawfn ( &the_formation, Aliens_draw );
279 Vector_copy ( fstart_pos, the_formation.pos );
280 the_formation.zone = ZONE_8;
281 gv->formation_zone = ZONE_8;
282 gv->alien_count = MAX_ALIENS;
284 invaders.move = 0;
285 invaders.forward = FORWARD_START;
286 invaders.forward_max = FORWARD_MAX;
287 invaders.leadcol = START_LEAD_COLUMN;
288 invaders.fdir = RIGHT;
289 invaders.anim = 0;
290 invaders.scur = 0;
291 invaders.drop_bomb = 0;
293 /* place aliens into their appropriate formations */
294 /* 8 aliens per formation -- total of 5 formations */
295 af_list = &flist[0];
296 f_ptr = &flist[0];
297 alien = &aliens[0];
298 Vector_init ( tmp_pos );
300 for ( i=0; i<MAX_COLUMNS; i++ )
301 invaders.column[i] = 0;
303 for ( i=0; i<MAX_FORMATRIX4IONS; i++ )
305 Objlist_clear ( f_ptr );
307 Vector_copy ( fstart_pos, tmp_pos );
308 tmp_pos[YPOS] += (FORMATRIX4ION_Y_INC * i);
310 for ( j=0; j<ALIENS_PER_FORMATRIX4ION; j++ )
312 Object_init ( alien );
313 Object_set_pos ( alien, tmp_pos );
314 Object_set_dir ( alien, fstart_dir );
316 alien->zone = gv->formation_zone;
317 alien->zheight = i;
318 alien->vpos = j;
319 alien->radius = ALIEN_RADIUS;
320 alien->radius_squared = ALIEN_RADIUS_SQUARED;
322 Objlist_add ( f_ptr, alien );
324 tmp_pos[XPOS] += FORMATRIX4ION_X_INC;
325 invaders.column[j] +=1;
326 alien++;
329 f_ptr++;
332 /* initialize alien bombs */
333 for ( i=0; i<MAX_BOMBS; i++ )
335 Object_init ( &bombs[i] );
336 Object_set_drawfn ( &bombs[i], Alien_missile_draw );
338 bombs[i].radius = BOMB_RADIUS;
339 bombs[i].radius_squared = BOMB_RADIUS_SQUARED;
341 abombs = &abomblist;
342 Objlist_clear ( abombs );
344 /* initialize the UFO */
345 invaders.spawn_ufo = 0;
346 gv->ufo_zone = ZONE_9;
347 ufo = &alien_ufo;
348 Object_init ( ufo );
349 Object_set_drawfn ( ufo, Ufo_draw );
350 ufo->radius = UFO_RADIUS;
351 ufo->radius_squared = UFO_RADIUS_SQUARED;
352 ufo->delay = 0;
353 invaders.ucolor = 0;
356 /*================================================================*/
358 void Aliens_update ( OBJECT *obj )
360 int i, j, tmp;
362 if ( gv->alien_count == 0 ) return;
364 i = obj->vpos;
365 invaders.column[i] -= 1;
367 /* select new lead-column if current lead-column is empty */
368 if ( (invaders.leadcol == i) && (invaders.column[i] == 0) )
370 j = invaders.leadcol;
371 if ( invaders.fdir == LEFT )
373 while ( j < MAX_COLUMNS )
375 if ( invaders.column[j] > 0 )
376 break;
377 j++;
379 tmp = (j-invaders.leadcol) * 3;
381 else
383 while ( j > -1 )
385 if ( invaders.column[j] > 0 )
386 break;
387 j--;
389 tmp = (invaders.leadcol-j) * 3;
392 invaders.forward -= tmp;
393 invaders.leadcol = j;
396 /* update alien movement speed */
397 if ( ( gv->alien_count % 5 ) == 0 )
398 invaders.scur++;
401 void Aliens_move ( void )
403 int i, j, fdir_save, chance;
404 OBJECT *alien, *abomb, *tmp;
406 /* move alien bombs */
407 invaders.drop_bomb += gv->msec;
408 abomb = abombs->head;
409 while ( abomb )
411 Vector_copy ( abomb->pos, abomb->old_pos );
412 abomb->pos[ZPOS] += abomb_thrust[ZPOS] * gv->fadjust;
414 if ( abomb->pos[ZPOS] > 0.0 )
416 abomb->active = FALSE;
417 tmp = abomb->next;
418 Objlist_del ( abombs, abomb );
419 abomb = tmp;
421 else
423 Object_update_zone ( abomb );
424 abomb = abomb->next;
428 /* update alien formation */
429 if ( (gv->alien_count > 0) && player->active )
431 invaders.move += gv->msec;
432 if ( invaders.move > fspeed[invaders.scur] )
434 invaders.move -= fspeed[invaders.scur];
435 invaders.forward++;
436 invaders.anim ^= ANIMATRIX4ION_TOGGLE;
437 fdir_save = invaders.fdir;
439 /* is it time to move the formation forward?? */
440 if ( invaders.forward == invaders.forward_max )
442 invaders.forward = 0;
443 gv->formation_zone--;
444 the_formation.zone--;
445 Vector_addd ( the_formation.pos, fthrust[FORWARD] );
447 /* choose new lead column */
448 if ( invaders.fdir == LEFT )
450 i = MAX_COLUMNS - 1;
451 while ( i > -1 )
453 if ( invaders.column[i] > 0 )
454 break;
455 i--;
457 invaders.forward = ( ( i - invaders.leadcol ) * FORMATRIX4ION_STEP );
458 fdir_save = RIGHT;
460 else
462 i = 0;
463 while ( i < MAX_COLUMNS )
465 if ( invaders.column[i] > 0 )
466 break;
467 i++;
469 invaders.forward = ( ( invaders.leadcol - i ) * FORMATRIX4ION_STEP );
470 fdir_save = LEFT;
472 invaders.leadcol = i;
473 invaders.fdir = FORWARD;
476 for ( i=0; i<MAX_FORMATRIX4IONS; i++ )
478 alien = (af_list+i)->head;
479 while ( alien )
481 Vector_addd ( alien->pos, fthrust[invaders.fdir] );
482 Object_update_zone ( alien );
483 alien = alien->next;
487 invaders.fdir = fdir_save;
491 /* move ufo */
492 if ( ufo->active )
494 /* adjust velocity according to frame time */
495 /* set new position */
496 ufo->pos[XPOS] += ufo_thrust[XPOS] * gv->fadjust;
497 ufo->pos[YPOS] += ufo_thrust[YPOS] * gv->fadjust;
498 ufo->pos[ZPOS] += ufo_thrust[ZPOS] * gv->fadjust;
499 Object_update_zone ( ufo );
500 if ( ufo->pos[XPOS] > UFO_MAX_X_POS )
502 Jumpgate_open ( ufo->pos, RIGHT );
503 ufo->active = FALSE;
506 else
508 invaders.spawn_ufo += gv->msec;
509 if ( invaders.spawn_ufo > SPAWN_UFO_TIME )
511 invaders.spawn_ufo -= SPAWN_UFO_TIME;
512 Ufo_spawn ();
516 /* drop a bomb or two */
517 if ( invaders.drop_bomb > DROP_BOMB_TIME )
519 invaders.drop_bomb -= DROP_BOMB_TIME;
520 chance = rand() % DROP_BOMB_CHANCE_1;
521 if ( chance < DROP_BOMB_CHANCE_2 )
523 /* pick formation infront of player */
524 i = pm->zheight;
525 if ( (i > -1) && (i<ZONE_HEIGHT_MAX) )
527 alien = (af_list+i)->head;
528 if ( alien )
530 /* pick an alien who will drop a bomb */
531 j = (rand() % (af_list+i)->obj_count );
532 while ( j )
534 alien = alien->next;
535 j--;
538 /* find an inactive bomb and use it */
539 Add_bomb ( alien );
543 /* pick a random formation */
544 i = rand () % MAX_FORMATRIX4IONS;
545 alien = (af_list+i)->head;
546 if ( alien )
548 /* pick an alien who will drop a bomb */
549 j = (rand() % (af_list+i)->obj_count );
550 while ( j )
552 alien = alien->next;
553 j--;
556 /* find an inactive bomb and use it */
557 Add_bomb ( alien );
564 /*================================================================*/
566 void Add_bomb ( OBJECT *alien )
568 int i;
569 OBJECT *abomb;
571 for ( i=0; i<MAX_BOMBS; i++ )
573 abomb = &bombs[i];
574 if ( abomb->active == FALSE )
576 abomb->active = TRUE;
577 Vector_copy ( alien->pos, abomb->pos );
578 Vector_copy ( alien->pos, abomb->old_pos );
579 Objlist_add ( abombs, abomb );
580 break;
585 /*================================================================*/
587 void Aliens_draw ( OBJECT *obj, MATRIX4 r )
589 OBJECT *alien;
590 VECTOR4 tmp[16];
591 MATRIX4 tmp_mat;
592 int i, p[32], fmodel;
594 for ( i=0; i<MAX_FORMATRIX4IONS; i++ )
597 if ( i == MAX_FORMATRIX4IONS-1 )
598 fmodel = 2;
599 else if ( i > 1 )
600 fmodel = 1;
601 else
602 fmodel = 0;
604 alien = (af_list+i)->head;
605 while ( alien )
607 Matrix_vec_mult ( r, alien->pos, tmp[0] );
608 Camera_project_points ( tmp, p, 1 );
609 Matrix_copy ( r, tmp_mat );
610 Matrix_set_trans ( tmp_mat, tmp[0] );
612 if ( invaders.anim )
613 Matrix_vec_multn ( tmp_mat, &avert2[fmodel*16], tmp, 16 );
614 else
615 Matrix_vec_multn ( tmp_mat, &avert1[fmodel*16], tmp, 16 );
617 Camera_project_points ( tmp, p, 16 );
619 /* body */
620 Draw_line ( p[0], p[1], p[2], p[3], GREEN );
621 Draw_line ( p[2], p[3], p[4], p[5], GREEN );
622 Draw_line ( p[4], p[5], p[6], p[7], GREEN );
623 Draw_line ( p[6], p[7], p[0], p[1], GREEN );
625 /* left leg */
626 Draw_line ( p[8], p[9], p[10], p[11], GREEN );
627 Draw_line ( p[10], p[11], p[12], p[13], GREEN );
628 Draw_line ( p[12], p[13], p[8], p[9], GREEN );
629 Draw_line ( p[10], p[11], p[14], p[15], GREEN );
630 Draw_line ( p[14], p[15], p[12], p[13], GREEN );
632 /* right leg */
633 Draw_line ( p[8], p[9], p[16], p[17], GREEN );
634 Draw_line ( p[16], p[17], p[18], p[19], GREEN );
635 Draw_line ( p[18], p[19], p[8], p[9], GREEN );
636 Draw_line ( p[16], p[17], p[20], p[21], GREEN );
637 Draw_line ( p[20], p[21], p[18], p[19], GREEN );
639 /* left eye */
640 Draw_line ( p[22], p[23], p[24], p[25], RED );
641 Draw_line ( p[24], p[25], p[26], p[27], RED );
642 Draw_line ( p[26], p[27], p[22], p[23], RED );
644 /* right eye */
645 Draw_line ( p[22], p[23], p[28], p[29], RED );
646 Draw_line ( p[28], p[29], p[30], p[31], RED );
647 Draw_line ( p[30], p[31], p[22], p[23], RED );
649 alien = alien->next;
655 void Alien_missile_draw ( OBJECT *obj, MATRIX4 r )
657 MATRIX4 tmp_mat;
658 VECTOR4 tmp[3];
659 int p[6];
661 Matrix_vec_mult ( r, obj->pos, tmp[0] );
662 Matrix_copy ( r, tmp_mat );
663 Matrix_set_trans ( tmp_mat, tmp[0] );
665 Matrix_vec_multn ( tmp_mat, abomb_vert, tmp, 3 );
666 Camera_project_points ( tmp, p, 3 );
667 Draw_line ( p[0], p[1], p[2], p[3], YELLOW );
668 Draw_line ( p[2], p[3], p[4], p[5], YELLOW );
669 Draw_line ( p[4], p[5], p[0], p[1], YELLOW );
671 Matrix_vec_multn ( tmp_mat, abomb_vert2, tmp, 3 );
672 Camera_project_points ( tmp, p, 3 );
673 Draw_line ( p[0], p[1], p[2], p[3], YELLOW );
674 Draw_line ( p[2], p[3], p[4], p[5], YELLOW );
675 Draw_line ( p[4], p[5], p[0], p[1], YELLOW );
678 /*================================================================*/
680 void Ufo_spawn ( void )
682 int height;
683 float y, z;
685 ufo->active = TRUE;
686 height = rand() % MAX_FORMATRIX4IONS;
687 y = ( (float)(height) * 100.0f ) + 50.0f;
688 z = UFO_Z_POS;
689 ufo->zone = UFO_ZONE;
690 ufo->zheight = height;
692 Vector_set ( ufo->pos, UFO_MIN_X_POS, y, z );
693 Jumpgate_open ( ufo->pos, LEFT );
696 void Ufo_draw ( OBJECT *obj, MATRIX4 r )
698 MATRIX4 tmp_mat;
699 VECTOR4 tmp[17];
700 int p[34];
701 unsigned int color;
703 ufo->delay += gv->msec;
704 if ( ufo->delay > UFO_LIGHTS_CYCLE )
706 ufo->delay -= UFO_LIGHTS_CYCLE;
707 invaders.ucolor++;
708 if ( invaders.ucolor == 4 )
709 invaders.ucolor = 0;
712 color = RED - ( invaders.ucolor * 15 );
714 Matrix_vec_mult ( r, obj->pos, tmp[0] );
715 Matrix_copy ( r, tmp_mat );
716 Matrix_set_trans ( tmp_mat, tmp[0] );
718 Matrix_vec_multn ( tmp_mat, uvert1, tmp, 17 );
719 Camera_project_points ( tmp, p, 17 );
721 Draw_line ( p[0], p[1], p[2], p[3], GREEN );
722 Draw_line ( p[2], p[3], p[4], p[5], GREEN );
723 Draw_line ( p[4], p[5], p[6], p[7], GREEN );
724 Draw_line ( p[6], p[7], p[0], p[1], GREEN );
726 Draw_line ( p[8], p[9], p[10], p[11], GREEN );
727 Draw_line ( p[8], p[9], p[12], p[13], GREEN );
729 Draw_line ( p[14], p[15], p[16], p[17], GREEN );
730 Draw_line ( p[14], p[15], p[18], p[19], GREEN );
732 Draw_line ( p[20], p[21], p[22], p[23], GREEN );
733 Draw_line ( p[22], p[23], p[24], p[25], GREEN );
735 Draw_point ( p[26], p[27], color );
736 Draw_point ( p[28], p[29], color );
737 Draw_point ( p[30], p[31], color );
738 Draw_point ( p[32], p[33], color );
741 /*================================================================*/