1 /*
2  * Copyright (C) 1997-2001 Id Software, Inc.
3  *
4  * This program is free software; you can redistribute it and/or modify it under
5  * the terms of the GNU General Public License as published by the Free
6  * Software Foundation; either version 2 of the License, or (at your option)
7  * any later version.
8  *
9  * This program is distributed in the hope that it will be useful, but WITHOUT
10  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11  * FITNESS FOR A PARTICULAR PURPOSE.
12  *
13  * See the GNU General Public License for more details.
14  *
15  * You should have received a copy of the GNU General Public License along with
16  * this program; if not, write to the Free Software Foundation, Inc., 59
17  * Temple Place - Suite 330, Boston, MA  02111-1307, USA.
18  *
19  */
20 
21 /*
22  *
23  * ============================================================================
24  * ==
25  *
26  * insane
27  *
28  * ======
29  * =======================================================================
30  */
31 
32 #include "g_local.h"
33 #include "m_insane.h"
34 
35 
36 static int	sound_fist;
37 static int	sound_shake;
38 static int	sound_moan;
39 static int	sound_scream[8];
40 
41 void
insane_fist(edict_t * self)42 insane_fist(edict_t * self)
43 {
44 	gi.sound(self, CHAN_VOICE, sound_fist, 1, ATTN_IDLE, 0);
45 }
46 
47 void
insane_shake(edict_t * self)48 insane_shake(edict_t * self)
49 {
50 	gi.sound(self, CHAN_VOICE, sound_shake, 1, ATTN_IDLE, 0);
51 }
52 
53 void
insane_moan(edict_t * self)54 insane_moan(edict_t * self)
55 {
56 	gi.sound(self, CHAN_VOICE, sound_moan, 1, ATTN_IDLE, 0);
57 }
58 
59 void
insane_scream(edict_t * self)60 insane_scream(edict_t * self)
61 {
62 	gi.sound(self, CHAN_VOICE, sound_scream[rand() % 8], 1, ATTN_IDLE, 0);
63 }
64 
65 
66 void		insane_stand(edict_t * self);
67 void		insane_dead(edict_t * self);
68 void		insane_cross(edict_t * self);
69 void		insane_walk(edict_t * self);
70 void		insane_run(edict_t * self);
71 void		insane_checkdown(edict_t * self);
72 void		insane_checkup(edict_t * self);
73 void		insane_onground(edict_t * self);
74 
75 
76 mframe_t	insane_frames_stand_normal[] =
77 {
78 	{ai_stand, 0, NULL},
79 	{ai_stand, 0, NULL},
80 	{ai_stand, 0, NULL},
81 	{ai_stand, 0, NULL},
82 	{ai_stand, 0, NULL},
83 	{ai_stand, 0, insane_checkdown}
84 };
85 mmove_t		insane_move_stand_normal = {FRAME_stand60, FRAME_stand65, insane_frames_stand_normal, insane_stand};
86 
87 mframe_t	insane_frames_stand_insane[] =
88 {
89 	{ai_stand, 0, insane_shake},
90 	{ai_stand, 0, NULL},
91 	{ai_stand, 0, NULL},
92 	{ai_stand, 0, NULL},
93 	{ai_stand, 0, NULL},
94 	{ai_stand, 0, NULL},
95 	{ai_stand, 0, NULL},
96 	{ai_stand, 0, NULL},
97 	{ai_stand, 0, NULL},
98 	{ai_stand, 0, NULL},
99 	{ai_stand, 0, NULL},
100 	{ai_stand, 0, NULL},
101 	{ai_stand, 0, NULL},
102 	{ai_stand, 0, NULL},
103 	{ai_stand, 0, NULL},
104 	{ai_stand, 0, NULL},
105 	{ai_stand, 0, NULL},
106 	{ai_stand, 0, NULL},
107 	{ai_stand, 0, NULL},
108 	{ai_stand, 0, NULL},
109 	{ai_stand, 0, NULL},
110 	{ai_stand, 0, NULL},
111 	{ai_stand, 0, NULL},
112 	{ai_stand, 0, NULL},
113 	{ai_stand, 0, NULL},
114 	{ai_stand, 0, NULL},
115 	{ai_stand, 0, NULL},
116 	{ai_stand, 0, NULL},
117 	{ai_stand, 0, NULL},
118 	{ai_stand, 0, insane_checkdown}
119 };
120 mmove_t		insane_move_stand_insane = {FRAME_stand65, FRAME_stand94, insane_frames_stand_insane, insane_stand};
121 
122 mframe_t	insane_frames_uptodown[] =
123 {
124 	{ai_move, 0, NULL},
125 	{ai_move, 0, NULL},
126 	{ai_move, 0, NULL},
127 	{ai_move, 0, NULL},
128 	{ai_move, 0, NULL},
129 	{ai_move, 0, NULL},
130 	{ai_move, 0, NULL},
131 	{ai_move, 0, insane_moan},
132 	{ai_move, 0, NULL},
133 	{ai_move, 0, NULL},
134 
135 	{ai_move, 0, NULL},
136 	{ai_move, 0, NULL},
137 	{ai_move, 0, NULL},
138 	{ai_move, 0, NULL},
139 	{ai_move, 0, NULL},
140 	{ai_move, 0, NULL},
141 	{ai_move, 0, NULL},
142 	{ai_move, 0, NULL},
143 	{ai_move, 0, NULL},
144 	{ai_move, 0, NULL},
145 
146 	{ai_move, 2.7, NULL},
147 	{ai_move, 4.1, NULL},
148 	{ai_move, 6, NULL},
149 	{ai_move, 7.6, NULL},
150 	{ai_move, 3.6, NULL},
151 	{ai_move, 0, NULL},
152 	{ai_move, 0, NULL},
153 	{ai_move, 0, insane_fist},
154 	{ai_move, 0, NULL},
155 	{ai_move, 0, NULL},
156 
157 	{ai_move, 0, NULL},
158 	{ai_move, 0, NULL},
159 	{ai_move, 0, NULL},
160 	{ai_move, 0, insane_fist},
161 	{ai_move, 0, NULL},
162 	{ai_move, 0, NULL},
163 	{ai_move, 0, NULL},
164 	{ai_move, 0, NULL},
165 	{ai_move, 0, NULL},
166 	{ai_move, 0, NULL}
167 };
168 mmove_t		insane_move_uptodown = {FRAME_stand1, FRAME_stand40, insane_frames_uptodown, insane_onground};
169 
170 
171 mframe_t	insane_frames_downtoup[] =
172 {
173 	{ai_move, -0.7, NULL},	/* 41 */
174 	{ai_move, -1.2, NULL},	/* 42 */
175 	{ai_move, -1.5, NULL},	/* 43 */
176 	{ai_move, -4.5, NULL},	/* 44 */
177 	{ai_move, -3.5, NULL},	/* 45 */
178 	{ai_move, -0.2, NULL},	/* 46 */
179 	{ai_move, 0, NULL},	/* 47 */
180 	{ai_move, -1.3, NULL},	/* 48 */
181 	{ai_move, -3, NULL},	/* 49 */
182 	{ai_move, -2, NULL},	/* 50 */
183 	{ai_move, 0, NULL},	/* 51 */
184 	{ai_move, 0, NULL},	/* 52 */
185 	{ai_move, 0, NULL},	/* 53 */
186 	{ai_move, -3.3, NULL},	/* 54 */
187 	{ai_move, -1.6, NULL},	/* 55 */
188 	{ai_move, -0.3, NULL},	/* 56 */
189 	{ai_move, 0, NULL},	/* 57 */
190 	{ai_move, 0, NULL},	/* 58 */
191 	{ai_move, 0, NULL}	/* 59 */
192 };
193 mmove_t		insane_move_downtoup = {FRAME_stand41, FRAME_stand59, insane_frames_downtoup, insane_stand};
194 
195 mframe_t	insane_frames_jumpdown[] =
196 {
197 	{ai_move, 0.2, NULL},
198 	{ai_move, 11.5, NULL},
199 	{ai_move, 5.1, NULL},
200 	{ai_move, 7.1, NULL},
201 	{ai_move, 0, NULL}
202 };
203 mmove_t		insane_move_jumpdown = {FRAME_stand96, FRAME_stand100, insane_frames_jumpdown, insane_onground};
204 
205 
206 mframe_t	insane_frames_down[] =
207 {
208 	{ai_move, 0, NULL},	/* 100 */
209 	{ai_move, 0, NULL},
210 	{ai_move, 0, NULL},
211 	{ai_move, 0, NULL},
212 	{ai_move, 0, NULL},
213 	{ai_move, 0, NULL},
214 	{ai_move, 0, NULL},
215 	{ai_move, 0, NULL},
216 	{ai_move, 0, NULL},
217 	{ai_move, 0, NULL},
218 	{ai_move, 0, NULL},	/* 110 */
219 	{ai_move, -1.7, NULL},
220 	{ai_move, -1.6, NULL},
221 	{ai_move, 0, NULL},
222 	{ai_move, 0, NULL},
223 	{ai_move, 0, NULL},
224 	{ai_move, 0, insane_fist},
225 	{ai_move, 0, NULL},
226 	{ai_move, 0, NULL},
227 	{ai_move, 0, NULL},
228 	{ai_move, 0, NULL},	/* 120 */
229 	{ai_move, 0, NULL},
230 	{ai_move, 0, NULL},
231 	{ai_move, 0, NULL},
232 	{ai_move, 0, NULL},
233 	{ai_move, 0, NULL},
234 	{ai_move, 0, NULL},
235 	{ai_move, 0, NULL},
236 	{ai_move, 0, NULL},
237 	{ai_move, 0, NULL},
238 	{ai_move, 0, NULL},	/* 130 */
239 	{ai_move, 0, NULL},
240 	{ai_move, 0, NULL},
241 	{ai_move, 0, insane_moan},
242 	{ai_move, 0, NULL},
243 	{ai_move, 0, NULL},
244 	{ai_move, 0, NULL},
245 	{ai_move, 0, NULL},
246 	{ai_move, 0, NULL},
247 	{ai_move, 0, NULL},
248 	{ai_move, 0, NULL},	/* 140 */
249 	{ai_move, 0, NULL},
250 	{ai_move, 0, NULL},
251 	{ai_move, 0, NULL},
252 	{ai_move, 0, NULL},
253 	{ai_move, 0, NULL},
254 	{ai_move, 0, NULL},
255 	{ai_move, 0, NULL},
256 	{ai_move, 0, NULL},
257 	{ai_move, 0, NULL},
258 	{ai_move, 0, NULL},	/* 150 */
259 	{ai_move, 0.5, NULL},
260 	{ai_move, 0, NULL},
261 	{ai_move, -0.2, insane_scream},
262 	{ai_move, 0, NULL},
263 	{ai_move, 0.2, NULL},
264 	{ai_move, 0.4, NULL},
265 	{ai_move, 0.6, NULL},
266 	{ai_move, 0.8, NULL},
267 	{ai_move, 0.7, NULL},
268 	{ai_move, 0, insane_checkup}	/* 160 */
269 };
270 mmove_t		insane_move_down = {FRAME_stand100, FRAME_stand160, insane_frames_down, insane_onground};
271 
272 mframe_t	insane_frames_walk_normal[] =
273 {
274 	{ai_walk, 0, insane_scream},
275 	{ai_walk, 2.5, NULL},
276 	{ai_walk, 3.5, NULL},
277 	{ai_walk, 1.7, NULL},
278 	{ai_walk, 2.3, NULL},
279 	{ai_walk, 2.4, NULL},
280 	{ai_walk, 2.2, NULL},
281 	{ai_walk, 4.2, NULL},
282 	{ai_walk, 5.6, NULL},
283 	{ai_walk, 3.3, NULL},
284 	{ai_walk, 2.4, NULL},
285 	{ai_walk, 0.9, NULL},
286 	{ai_walk, 0, NULL}
287 };
288 mmove_t		insane_move_walk_normal = {FRAME_walk27, FRAME_walk39, insane_frames_walk_normal, insane_walk};
289 mmove_t		insane_move_run_normal = {FRAME_walk27, FRAME_walk39, insane_frames_walk_normal, insane_run};
290 
291 mframe_t	insane_frames_walk_insane[] =
292 {
293 	{ai_walk, 0, insane_scream},	/* walk 1 */
294 	{ai_walk, 3.4, NULL},	/* walk 2 */
295 	{ai_walk, 3.6, NULL},	/* 3 */
296 	{ai_walk, 2.9, NULL},	/* 4 */
297 	{ai_walk, 2.2, NULL},	/* 5 */
298 	{ai_walk, 2.6, NULL},	/* 6 */
299 	{ai_walk, 0, NULL},	/* 7 */
300 	{ai_walk, 0.7, NULL},	/* 8 */
301 	{ai_walk, 4.8, NULL},	/* 9 */
302 	{ai_walk, 5.3, NULL},	/* 10 */
303 	{ai_walk, 1.1, NULL},	/* 11 */
304 	{ai_walk, 2, NULL},	/* 12 */
305 	{ai_walk, 0.5, NULL},	/* 13 */
306 	{ai_walk, 0, NULL},	/* 14 */
307 	{ai_walk, 0, NULL},	/* 15 */
308 	{ai_walk, 4.9, NULL},	/* 16 */
309 	{ai_walk, 6.7, NULL},	/* 17 */
310 	{ai_walk, 3.8, NULL},	/* 18 */
311 	{ai_walk, 2, NULL},	/* 19 */
312 	{ai_walk, 0.2, NULL},	/* 20 */
313 	{ai_walk, 0, NULL},	/* 21 */
314 	{ai_walk, 3.4, NULL},	/* 22 */
315 	{ai_walk, 6.4, NULL},	/* 23 */
316 	{ai_walk, 5, NULL},	/* 24 */
317 	{ai_walk, 1.8, NULL},	/* 25 */
318 	{ai_walk, 0, NULL}	/* 26 */
319 };
320 mmove_t		insane_move_walk_insane = {FRAME_walk1, FRAME_walk26, insane_frames_walk_insane, insane_walk};
321 mmove_t		insane_move_run_insane = {FRAME_walk1, FRAME_walk26, insane_frames_walk_insane, insane_run};
322 
323 mframe_t	insane_frames_stand_pain[] =
324 {
325 	{ai_move, 0, NULL},
326 	{ai_move, 0, NULL},
327 	{ai_move, 0, NULL},
328 	{ai_move, 0, NULL},
329 	{ai_move, 0, NULL},
330 	{ai_move, 0, NULL},
331 	{ai_move, 0, NULL},
332 	{ai_move, 0, NULL},
333 	{ai_move, 0, NULL},
334 	{ai_move, 0, NULL},
335 	{ai_move, 0, NULL}
336 };
337 mmove_t		insane_move_stand_pain = {FRAME_st_pain2, FRAME_st_pain12, insane_frames_stand_pain, insane_run};
338 
339 mframe_t	insane_frames_stand_death[] =
340 {
341 	{ai_move, 0, NULL},
342 	{ai_move, 0, NULL},
343 	{ai_move, 0, NULL},
344 	{ai_move, 0, NULL},
345 	{ai_move, 0, NULL},
346 	{ai_move, 0, NULL},
347 	{ai_move, 0, NULL},
348 	{ai_move, 0, NULL},
349 	{ai_move, 0, NULL},
350 	{ai_move, 0, NULL},
351 	{ai_move, 0, NULL},
352 	{ai_move, 0, NULL},
353 	{ai_move, 0, NULL},
354 	{ai_move, 0, NULL},
355 	{ai_move, 0, NULL},
356 	{ai_move, 0, NULL},
357 	{ai_move, 0, NULL}
358 };
359 mmove_t		insane_move_stand_death = {FRAME_st_death2, FRAME_st_death18, insane_frames_stand_death, insane_dead};
360 
361 mframe_t	insane_frames_crawl[] =
362 {
363 	{ai_walk, 0, insane_scream},
364 	{ai_walk, 1.5, NULL},
365 	{ai_walk, 2.1, NULL},
366 	{ai_walk, 3.6, NULL},
367 	{ai_walk, 2, NULL},
368 	{ai_walk, 0.9, NULL},
369 	{ai_walk, 3, NULL},
370 	{ai_walk, 3.4, NULL},
371 	{ai_walk, 2.4, NULL}
372 };
373 mmove_t		insane_move_crawl = {FRAME_crawl1, FRAME_crawl9, insane_frames_crawl, NULL};
374 mmove_t		insane_move_runcrawl = {FRAME_crawl1, FRAME_crawl9, insane_frames_crawl, NULL};
375 
376 mframe_t	insane_frames_crawl_pain[] =
377 {
378 	{ai_move, 0, NULL},
379 	{ai_move, 0, NULL},
380 	{ai_move, 0, NULL},
381 	{ai_move, 0, NULL},
382 	{ai_move, 0, NULL},
383 	{ai_move, 0, NULL},
384 	{ai_move, 0, NULL},
385 	{ai_move, 0, NULL},
386 	{ai_move, 0, NULL}
387 };
388 mmove_t		insane_move_crawl_pain = {FRAME_cr_pain2, FRAME_cr_pain10, insane_frames_crawl_pain, insane_run};
389 
390 mframe_t	insane_frames_crawl_death[] =
391 {
392 	{ai_move, 0, NULL},
393 	{ai_move, 0, NULL},
394 	{ai_move, 0, NULL},
395 	{ai_move, 0, NULL},
396 	{ai_move, 0, NULL},
397 	{ai_move, 0, NULL},
398 	{ai_move, 0, NULL}
399 };
400 mmove_t		insane_move_crawl_death = {FRAME_cr_death10, FRAME_cr_death16, insane_frames_crawl_death, insane_dead};
401 
402 mframe_t	insane_frames_cross[] =
403 {
404 	{ai_move, 0, insane_moan},
405 	{ai_move, 0, NULL},
406 	{ai_move, 0, NULL},
407 	{ai_move, 0, NULL},
408 	{ai_move, 0, NULL},
409 	{ai_move, 0, NULL},
410 	{ai_move, 0, NULL},
411 	{ai_move, 0, NULL},
412 	{ai_move, 0, NULL},
413 	{ai_move, 0, NULL},
414 	{ai_move, 0, NULL},
415 	{ai_move, 0, NULL},
416 	{ai_move, 0, NULL},
417 	{ai_move, 0, NULL},
418 	{ai_move, 0, NULL}
419 };
420 mmove_t		insane_move_cross = {FRAME_cross1, FRAME_cross15, insane_frames_cross, insane_cross};
421 
422 mframe_t	insane_frames_struggle_cross[] =
423 {
424 	{ai_move, 0, insane_scream},
425 	{ai_move, 0, NULL},
426 	{ai_move, 0, NULL},
427 	{ai_move, 0, NULL},
428 	{ai_move, 0, NULL},
429 	{ai_move, 0, NULL},
430 	{ai_move, 0, NULL},
431 	{ai_move, 0, NULL},
432 	{ai_move, 0, NULL},
433 	{ai_move, 0, NULL},
434 	{ai_move, 0, NULL},
435 	{ai_move, 0, NULL},
436 	{ai_move, 0, NULL},
437 	{ai_move, 0, NULL},
438 	{ai_move, 0, NULL}
439 };
440 mmove_t		insane_move_struggle_cross = {FRAME_cross16, FRAME_cross30, insane_frames_struggle_cross, insane_cross};
441 
442 void
insane_cross(edict_t * self)443 insane_cross(edict_t * self)
444 {
445 	if (random() < 0.8)
446 		self->monsterinfo.currentmove = &insane_move_cross;
447 	else
448 		self->monsterinfo.currentmove = &insane_move_struggle_cross;
449 }
450 
451 void
insane_walk(edict_t * self)452 insane_walk(edict_t * self)
453 {
454 	if (self->spawnflags & 16)	/* Hold Ground? */
455 		if (self->s.frame == FRAME_cr_pain10) {
456 			self->monsterinfo.currentmove = &insane_move_down;
457 			return;
458 		}
459 	if (self->spawnflags & 4)
460 		self->monsterinfo.currentmove = &insane_move_crawl;
461 	else if (random() <= 0.5)
462 		self->monsterinfo.currentmove = &insane_move_walk_normal;
463 	else
464 		self->monsterinfo.currentmove = &insane_move_walk_insane;
465 }
466 
467 void
insane_run(edict_t * self)468 insane_run(edict_t * self)
469 {
470 	if (self->spawnflags & 16)	/* Hold Ground? */
471 		if (self->s.frame == FRAME_cr_pain10) {
472 			self->monsterinfo.currentmove = &insane_move_down;
473 			return;
474 		}
475 	if (self->spawnflags & 4)	/* Crawling? */
476 		self->monsterinfo.currentmove = &insane_move_runcrawl;
477 	else if (random() <= 0.5)	/* Else, mix it up */
478 		self->monsterinfo.currentmove = &insane_move_run_normal;
479 	else
480 		self->monsterinfo.currentmove = &insane_move_run_insane;
481 }
482 
483 
484 void
insane_pain(edict_t * self,edict_t * other,float kick,int damage)485 insane_pain(edict_t * self, edict_t * other, float kick, int damage)
486 {
487 	int		l         , r;
488 
489 	/* if (self->health < (self->max_health / 2)) */
490 	/* self->s.skinnum = 1; */
491 
492 	if (level.time < self->pain_debounce_time)
493 		return;
494 
495 	self->pain_debounce_time = level.time + 3;
496 
497 	r = 1 + (rand() & 1);
498 	if (self->health < 25)
499 		l = 25;
500 	else if (self->health < 50)
501 		l = 50;
502 	else if (self->health < 75)
503 		l = 75;
504 	else
505 		l = 100;
506 	gi.sound(self, CHAN_VOICE, gi.soundindex(va("player/male/pain%i_%i.wav", l, r)), 1, ATTN_IDLE, 0);
507 
508 	if (skill->value == 3)
509 		return;		/* no pain anims in nightmare */
510 
511 	/* Don't go into pain frames if crucified. */
512 	if (self->spawnflags & 8) {
513 		self->monsterinfo.currentmove = &insane_move_struggle_cross;
514 		return;
515 	}
516 	if (((self->s.frame >= FRAME_crawl1) && (self->s.frame <= FRAME_crawl9)) || ((self->s.frame >= FRAME_stand99) && (self->s.frame <= FRAME_stand160))) {
517 		self->monsterinfo.currentmove = &insane_move_crawl_pain;
518 	} else
519 		self->monsterinfo.currentmove = &insane_move_stand_pain;
520 
521 }
522 
523 void
insane_onground(edict_t * self)524 insane_onground(edict_t * self)
525 {
526 	self->monsterinfo.currentmove = &insane_move_down;
527 }
528 
529 void
insane_checkdown(edict_t * self)530 insane_checkdown(edict_t * self)
531 {
532 
533 	/*
534 	 * if ( (self->s.frame == FRAME_stand94) || (self->s.frame ==
535 	 * FRAME_stand65) )
536 	 */
537 	if (self->spawnflags & 32)	/* Always stand */
538 		return;
539 	if (random() < 0.3) {
540 		if (random() < 0.5)
541 			self->monsterinfo.currentmove = &insane_move_uptodown;
542 		else
543 			self->monsterinfo.currentmove = &insane_move_jumpdown;
544 	}
545 }
546 
547 void
insane_checkup(edict_t * self)548 insane_checkup(edict_t * self)
549 {
550 	/* If Hold_Ground and Crawl are set */
551 	if ((self->spawnflags & 4) && (self->spawnflags & 16))
552 		return;
553 	if (random() < 0.5)
554 		self->monsterinfo.currentmove = &insane_move_downtoup;
555 
556 }
557 
558 void
insane_stand(edict_t * self)559 insane_stand(edict_t * self)
560 {
561 	if (self->spawnflags & 8) {	/* If crucified */
562 		self->monsterinfo.currentmove = &insane_move_cross;
563 		self->monsterinfo.aiflags |= AI_STAND_GROUND;
564 	}
565 	/* If Hold_Ground and Crawl are set */
566 	else if ((self->spawnflags & 4) && (self->spawnflags & 16))
567 		self->monsterinfo.currentmove = &insane_move_down;
568 	else if (random() < 0.5)
569 		self->monsterinfo.currentmove = &insane_move_stand_normal;
570 	else
571 		self->monsterinfo.currentmove = &insane_move_stand_insane;
572 }
573 
574 void
insane_dead(edict_t * self)575 insane_dead(edict_t * self)
576 {
577 	if (self->spawnflags & 8) {
578 		self->flags |= FL_FLY;
579 	} else {
580 		VectorSet(self->mins, -16, -16, -24);
581 		VectorSet(self->maxs, 16, 16, -8);
582 		self->movetype = MOVETYPE_TOSS;
583 	}
584 	self->svflags |= SVF_DEADMONSTER;
585 	self->nextthink = 0;
586 	gi.linkentity(self);
587 }
588 
589 
590 void
insane_die(edict_t * self,edict_t * inflictor,edict_t * attacker,int damage,vec3_t point)591 insane_die(edict_t * self, edict_t * inflictor, edict_t * attacker, int damage, vec3_t point)
592 {
593 	int		n;
594 
595 	if (self->health <= self->gib_health) {
596 		gi.sound(self, CHAN_VOICE, gi.soundindex("misc/udeath.wav"), 1, ATTN_IDLE, 0);
597 		for (n = 0; n < 2; n++)
598 			ThrowGib(self, "models/objects/gibs/bone/tris.md2", damage, GIB_ORGANIC);
599 		for (n = 0; n < 4; n++)
600 			ThrowGib(self, "models/objects/gibs/sm_meat/tris.md2", damage, GIB_ORGANIC);
601 		ThrowHead(self, "models/objects/gibs/head2/tris.md2", damage, GIB_ORGANIC);
602 		self->deadflag = DEAD_DEAD;
603 		return;
604 	}
605 	if (self->deadflag == DEAD_DEAD)
606 		return;
607 
608 	gi.sound(self, CHAN_VOICE, gi.soundindex(va("player/male/death%i.wav", (rand() % 4) + 1)), 1, ATTN_IDLE, 0);
609 
610 	self->deadflag = DEAD_DEAD;
611 	self->takedamage = DAMAGE_YES;
612 
613 	if (self->spawnflags & 8) {
614 		insane_dead(self);
615 	} else {
616 		if (((self->s.frame >= FRAME_crawl1) && (self->s.frame <= FRAME_crawl9)) || ((self->s.frame >= FRAME_stand99) && (self->s.frame <= FRAME_stand160)))
617 			self->monsterinfo.currentmove = &insane_move_crawl_death;
618 		else
619 			self->monsterinfo.currentmove = &insane_move_stand_death;
620 	}
621 }
622 
623 
624 /*
625  * QUAKED misc_insane (1 .5 0) (-16 -16 -24) (16 16 32) Ambush Trigger_Spawn
626  * CRAWL CRUCIFIED STAND_GROUND ALWAYS_STAND
627  */
628 void
SP_misc_insane(edict_t * self)629 SP_misc_insane(edict_t * self)
630 {
631 	/* static int skin = 0;	//@@ */
632 
633 	if (deathmatch->value) {
634 		G_FreeEdict(self);
635 		return;
636 	}
637 	sound_fist = gi.soundindex("insane/insane11.wav");
638 	sound_shake = gi.soundindex("insane/insane5.wav");
639 	sound_moan = gi.soundindex("insane/insane7.wav");
640 	sound_scream[0] = gi.soundindex("insane/insane1.wav");
641 	sound_scream[1] = gi.soundindex("insane/insane2.wav");
642 	sound_scream[2] = gi.soundindex("insane/insane3.wav");
643 	sound_scream[3] = gi.soundindex("insane/insane4.wav");
644 	sound_scream[4] = gi.soundindex("insane/insane6.wav");
645 	sound_scream[5] = gi.soundindex("insane/insane8.wav");
646 	sound_scream[6] = gi.soundindex("insane/insane9.wav");
647 	sound_scream[7] = gi.soundindex("insane/insane10.wav");
648 
649 	self->movetype = MOVETYPE_STEP;
650 	self->solid = SOLID_BBOX;
651 	self->s.modelindex = gi.modelindex("models/monsters/insane/tris.md2");
652 
653 	VectorSet(self->mins, -16, -16, -24);
654 	VectorSet(self->maxs, 16, 16, 32);
655 
656 	self->health = 100;
657 	self->gib_health = -50;
658 	self->mass = 300;
659 
660 	self->pain = insane_pain;
661 	self->die = insane_die;
662 
663 	self->monsterinfo.stand = insane_stand;
664 	self->monsterinfo.walk = insane_walk;
665 	self->monsterinfo.run = insane_run;
666 	self->monsterinfo.dodge = NULL;
667 	self->monsterinfo.attack = NULL;
668 	self->monsterinfo.melee = NULL;
669 	self->monsterinfo.sight = NULL;
670 	self->monsterinfo.aiflags |= AI_GOOD_GUY;
671 
672 	/* @@ */
673 	/* self->s.skinnum = skin; */
674 	/* skin++; */
675 	/* if (skin > 12) */
676 	/* skin = 0; */
677 
678 	gi.linkentity(self);
679 
680 	if (self->spawnflags & 16)	/* Stand Ground */
681 		self->monsterinfo.aiflags |= AI_STAND_GROUND;
682 
683 	self->monsterinfo.currentmove = &insane_move_stand_normal;
684 
685 	self->monsterinfo.scale = MODEL_SCALE;
686 
687 	if (self->spawnflags & 8) {	/* Crucified ? */
688 		VectorSet(self->mins, -16, 0, 0);
689 		VectorSet(self->maxs, 16, 8, 32);
690 		self->flags |= FL_NO_KNOCKBACK;
691 		flymonster_start(self);
692 	} else {
693 		walkmonster_start(self);
694 		self->s.skinnum = rand() % 3;
695 	}
696 }
697