m_brain.c 20 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896
  1. // Copyright (c) ZeniMax Media Inc.
  2. // Licensed under the GNU General Public License 2.0.
  3. /*
  4. ==============================================================================
  5. brain
  6. ==============================================================================
  7. */
  8. #include "g_local.h"
  9. #include "m_brain.h"
  10. static int sound_chest_open;
  11. static int sound_tentacles_extend;
  12. static int sound_tentacles_retract;
  13. static int sound_death;
  14. static int sound_idle1;
  15. static int sound_idle2;
  16. static int sound_idle3;
  17. static int sound_pain1;
  18. static int sound_pain2;
  19. static int sound_sight;
  20. static int sound_search;
  21. static int sound_melee1;
  22. static int sound_melee2;
  23. static int sound_melee3;
  24. void brain_sight (edict_t *self, edict_t *other)
  25. {
  26. gi.sound (self, CHAN_VOICE, sound_sight, 1, ATTN_NORM, 0);
  27. }
  28. void brain_search (edict_t *self)
  29. {
  30. gi.sound (self, CHAN_VOICE, sound_search, 1, ATTN_NORM, 0);
  31. }
  32. void brain_run (edict_t *self);
  33. void brain_dead (edict_t *self);
  34. //
  35. // STAND
  36. //
  37. mframe_t brain_frames_stand [] =
  38. {
  39. ai_stand, 0, NULL,
  40. ai_stand, 0, NULL,
  41. ai_stand, 0, NULL,
  42. ai_stand, 0, NULL,
  43. ai_stand, 0, NULL,
  44. ai_stand, 0, NULL,
  45. ai_stand, 0, NULL,
  46. ai_stand, 0, NULL,
  47. ai_stand, 0, NULL,
  48. ai_stand, 0, NULL,
  49. ai_stand, 0, NULL,
  50. ai_stand, 0, NULL,
  51. ai_stand, 0, NULL,
  52. ai_stand, 0, NULL,
  53. ai_stand, 0, NULL,
  54. ai_stand, 0, NULL,
  55. ai_stand, 0, NULL,
  56. ai_stand, 0, NULL,
  57. ai_stand, 0, NULL,
  58. ai_stand, 0, NULL,
  59. ai_stand, 0, NULL,
  60. ai_stand, 0, NULL,
  61. ai_stand, 0, NULL,
  62. ai_stand, 0, NULL,
  63. ai_stand, 0, NULL,
  64. ai_stand, 0, NULL,
  65. ai_stand, 0, NULL,
  66. ai_stand, 0, NULL,
  67. ai_stand, 0, NULL,
  68. ai_stand, 0, NULL
  69. };
  70. mmove_t brain_move_stand = {FRAME_stand01, FRAME_stand30, brain_frames_stand, NULL};
  71. void brain_stand (edict_t *self)
  72. {
  73. self->monsterinfo.currentmove = &brain_move_stand;
  74. }
  75. //
  76. // IDLE
  77. //
  78. mframe_t brain_frames_idle [] =
  79. {
  80. ai_stand, 0, NULL,
  81. ai_stand, 0, NULL,
  82. ai_stand, 0, NULL,
  83. ai_stand, 0, NULL,
  84. ai_stand, 0, NULL,
  85. ai_stand, 0, NULL,
  86. ai_stand, 0, NULL,
  87. ai_stand, 0, NULL,
  88. ai_stand, 0, NULL,
  89. ai_stand, 0, NULL,
  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. };
  111. mmove_t brain_move_idle = {FRAME_stand31, FRAME_stand60, brain_frames_idle, brain_stand};
  112. void brain_idle (edict_t *self)
  113. {
  114. gi.sound (self, CHAN_AUTO, sound_idle3, 1, ATTN_IDLE, 0);
  115. self->monsterinfo.currentmove = &brain_move_idle;
  116. }
  117. //
  118. // WALK
  119. //
  120. mframe_t brain_frames_walk1 [] =
  121. {
  122. ai_walk, 7, NULL,
  123. ai_walk, 2, NULL,
  124. ai_walk, 3, NULL,
  125. ai_walk, 3, NULL,
  126. ai_walk, 1, NULL,
  127. ai_walk, 0, NULL,
  128. ai_walk, 0, NULL,
  129. ai_walk, 9, NULL,
  130. ai_walk, -4, NULL,
  131. ai_walk, -1, NULL,
  132. ai_walk, 2, NULL
  133. };
  134. mmove_t brain_move_walk1 = {FRAME_walk101, FRAME_walk111, brain_frames_walk1, NULL};
  135. // walk2 is FUBAR, do not use
  136. #if 0
  137. void brain_walk2_cycle (edict_t *self)
  138. {
  139. if (random() > 0.1)
  140. self->monsterinfo.nextframe = FRAME_walk220;
  141. }
  142. mframe_t brain_frames_walk2 [] =
  143. {
  144. ai_walk, 3, NULL,
  145. ai_walk, -2, NULL,
  146. ai_walk, -4, NULL,
  147. ai_walk, -3, NULL,
  148. ai_walk, 0, NULL,
  149. ai_walk, 1, NULL,
  150. ai_walk, 12, NULL,
  151. ai_walk, 0, NULL,
  152. ai_walk, -3, NULL,
  153. ai_walk, 0, NULL,
  154. ai_walk, -2, NULL,
  155. ai_walk, 0, NULL,
  156. ai_walk, 0, NULL,
  157. ai_walk, 1, NULL,
  158. ai_walk, 0, NULL,
  159. ai_walk, 0, NULL,
  160. ai_walk, 0, NULL,
  161. ai_walk, 0, NULL,
  162. ai_walk, 0, NULL,
  163. ai_walk, 10, NULL, // Cycle Start
  164. ai_walk, -1, NULL,
  165. ai_walk, 7, NULL,
  166. ai_walk, 0, NULL,
  167. ai_walk, 3, NULL,
  168. ai_walk, -3, NULL,
  169. ai_walk, 2, NULL,
  170. ai_walk, 4, NULL,
  171. ai_walk, -3, NULL,
  172. ai_walk, 2, NULL,
  173. ai_walk, 0, NULL,
  174. ai_walk, 4, brain_walk2_cycle,
  175. ai_walk, -1, NULL,
  176. ai_walk, -1, NULL,
  177. ai_walk, -8, NULL,
  178. ai_walk, 0, NULL,
  179. ai_walk, 1, NULL,
  180. ai_walk, 5, NULL,
  181. ai_walk, 2, NULL,
  182. ai_walk, -1, NULL,
  183. ai_walk, -5, NULL
  184. };
  185. mmove_t brain_move_walk2 = {FRAME_walk201, FRAME_walk240, brain_frames_walk2, NULL};
  186. #endif
  187. void brain_walk (edict_t *self)
  188. {
  189. // if (random() <= 0.5)
  190. self->monsterinfo.currentmove = &brain_move_walk1;
  191. // else
  192. // self->monsterinfo.currentmove = &brain_move_walk2;
  193. }
  194. mframe_t brain_frames_defense [] =
  195. {
  196. ai_move, 0, NULL,
  197. ai_move, 0, NULL,
  198. ai_move, 0, NULL,
  199. ai_move, 0, NULL,
  200. ai_move, 0, NULL,
  201. ai_move, 0, NULL,
  202. ai_move, 0, NULL,
  203. ai_move, 0, NULL,
  204. ai_move, 0, NULL
  205. };
  206. mmove_t brain_move_defense = {FRAME_defens01, FRAME_defens08, brain_frames_defense, NULL};
  207. mframe_t brain_frames_pain3 [] =
  208. {
  209. ai_move, -2, NULL,
  210. ai_move, 2, NULL,
  211. ai_move, 1, NULL,
  212. ai_move, 3, NULL,
  213. ai_move, 0, NULL,
  214. ai_move, -4, NULL
  215. };
  216. mmove_t brain_move_pain3 = {FRAME_pain301, FRAME_pain306, brain_frames_pain3, brain_run};
  217. mframe_t brain_frames_pain2 [] =
  218. {
  219. ai_move, -2, NULL,
  220. ai_move, 0, NULL,
  221. ai_move, 0, NULL,
  222. ai_move, 0, NULL,
  223. ai_move, 0, NULL,
  224. ai_move, 3, NULL,
  225. ai_move, 1, NULL,
  226. ai_move, -2, NULL
  227. };
  228. mmove_t brain_move_pain2 = {FRAME_pain201, FRAME_pain208, brain_frames_pain2, brain_run};
  229. mframe_t brain_frames_pain1 [] =
  230. {
  231. ai_move, -6, NULL,
  232. ai_move, -2, NULL,
  233. ai_move, -6, 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,
  239. ai_move, 0, NULL,
  240. ai_move, 0, NULL,
  241. ai_move, 0, NULL,
  242. ai_move, 0, NULL,
  243. ai_move, 0, NULL,
  244. ai_move, 2, NULL,
  245. ai_move, 0, NULL,
  246. ai_move, 2, NULL,
  247. ai_move, 1, NULL,
  248. ai_move, 7, NULL,
  249. ai_move, 0, NULL,
  250. ai_move, 3, NULL,
  251. ai_move, -1, NULL
  252. };
  253. mmove_t brain_move_pain1 = {FRAME_pain101, FRAME_pain121, brain_frames_pain1, brain_run};
  254. //
  255. // DUCK
  256. //
  257. void brain_duck_down (edict_t *self)
  258. {
  259. if (self->monsterinfo.aiflags & AI_DUCKED)
  260. return;
  261. self->monsterinfo.aiflags |= AI_DUCKED;
  262. self->maxs[2] -= 32;
  263. self->takedamage = DAMAGE_YES;
  264. gi.linkentity (self);
  265. }
  266. void brain_duck_hold (edict_t *self)
  267. {
  268. if (level.time >= self->monsterinfo.pausetime)
  269. self->monsterinfo.aiflags &= ~AI_HOLD_FRAME;
  270. else
  271. self->monsterinfo.aiflags |= AI_HOLD_FRAME;
  272. }
  273. void brain_duck_up (edict_t *self)
  274. {
  275. self->monsterinfo.aiflags &= ~AI_DUCKED;
  276. self->maxs[2] += 32;
  277. self->takedamage = DAMAGE_AIM;
  278. gi.linkentity (self);
  279. }
  280. mframe_t brain_frames_duck [] =
  281. {
  282. ai_move, 0, NULL,
  283. ai_move, -2, brain_duck_down,
  284. ai_move, 17, brain_duck_hold,
  285. ai_move, -3, NULL,
  286. ai_move, -1, brain_duck_up,
  287. ai_move, -5, NULL,
  288. ai_move, -6, NULL,
  289. ai_move, -6, NULL
  290. };
  291. mmove_t brain_move_duck = {FRAME_duck01, FRAME_duck08, brain_frames_duck, brain_run};
  292. void brain_dodge (edict_t *self, edict_t *attacker, float eta)
  293. {
  294. if (random() > 0.25)
  295. return;
  296. if (!self->enemy)
  297. self->enemy = attacker;
  298. self->monsterinfo.pausetime = level.time + eta + 0.5;
  299. self->monsterinfo.currentmove = &brain_move_duck;
  300. }
  301. mframe_t brain_frames_death2 [] =
  302. {
  303. ai_move, 0, NULL,
  304. ai_move, 0, NULL,
  305. ai_move, 0, NULL,
  306. ai_move, 9, NULL,
  307. ai_move, 0, NULL
  308. };
  309. mmove_t brain_move_death2 = {FRAME_death201, FRAME_death205, brain_frames_death2, brain_dead};
  310. mframe_t brain_frames_death1 [] =
  311. {
  312. ai_move, 0, NULL,
  313. ai_move, 0, NULL,
  314. ai_move, -2, NULL,
  315. ai_move, 9, NULL,
  316. ai_move, 0, NULL,
  317. ai_move, 0, NULL,
  318. ai_move, 0, NULL,
  319. ai_move, 0, NULL,
  320. ai_move, 0, NULL,
  321. ai_move, 0, NULL,
  322. ai_move, 0, NULL,
  323. ai_move, 0, NULL,
  324. ai_move, 0, NULL,
  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. };
  331. mmove_t brain_move_death1 = {FRAME_death101, FRAME_death118, brain_frames_death1, brain_dead};
  332. //
  333. // MELEE
  334. //
  335. void brain_swing_right (edict_t *self)
  336. {
  337. gi.sound (self, CHAN_BODY, sound_melee1, 1, ATTN_NORM, 0);
  338. }
  339. void brain_hit_right (edict_t *self)
  340. {
  341. vec3_t aim;
  342. VectorSet (aim, MELEE_DISTANCE, self->maxs[0], 8);
  343. if (fire_hit (self, aim, (15 + (rand() %5)), 40))
  344. gi.sound (self, CHAN_WEAPON, sound_melee3, 1, ATTN_NORM, 0);
  345. }
  346. void brain_swing_left (edict_t *self)
  347. {
  348. gi.sound (self, CHAN_BODY, sound_melee2, 1, ATTN_NORM, 0);
  349. }
  350. void brain_hit_left (edict_t *self)
  351. {
  352. vec3_t aim;
  353. VectorSet (aim, MELEE_DISTANCE, self->mins[0], 8);
  354. if (fire_hit (self, aim, (15 + (rand() %5)), 40))
  355. gi.sound (self, CHAN_WEAPON, sound_melee3, 1, ATTN_NORM, 0);
  356. }
  357. mframe_t brain_frames_attack1 [] =
  358. {
  359. ai_charge, 8, NULL,
  360. ai_charge, 3, NULL,
  361. ai_charge, 5, NULL,
  362. ai_charge, 0, NULL,
  363. ai_charge, -3, brain_swing_right,
  364. ai_charge, 0, NULL,
  365. ai_charge, -5, NULL,
  366. ai_charge, -7, brain_hit_right,
  367. ai_charge, 0, NULL,
  368. ai_charge, 6, brain_swing_left,
  369. ai_charge, 1, NULL,
  370. ai_charge, 2, brain_hit_left,
  371. ai_charge, -3, NULL,
  372. ai_charge, 6, NULL,
  373. ai_charge, -1, NULL,
  374. ai_charge, -3, NULL,
  375. ai_charge, 2, NULL,
  376. ai_charge, -11,NULL
  377. };
  378. mmove_t brain_move_attack1 = {FRAME_attak101, FRAME_attak118, brain_frames_attack1, brain_run};
  379. void brain_chest_open (edict_t *self)
  380. {
  381. self->spawnflags &= ~65536;
  382. self->monsterinfo.power_armor_type = POWER_ARMOR_NONE;
  383. gi.sound (self, CHAN_BODY, sound_chest_open, 1, ATTN_NORM, 0);
  384. }
  385. void brain_tentacle_attack (edict_t *self)
  386. {
  387. vec3_t aim;
  388. VectorSet (aim, MELEE_DISTANCE, 0, 8);
  389. if (fire_hit (self, aim, (10 + (rand() %5)), -600) && skill->value > 0)
  390. self->spawnflags |= 65536;
  391. gi.sound (self, CHAN_WEAPON, sound_tentacles_retract, 1, ATTN_NORM, 0);
  392. }
  393. void brain_chest_closed (edict_t *self)
  394. {
  395. self->monsterinfo.power_armor_type = POWER_ARMOR_SCREEN;
  396. if (self->spawnflags & 65536)
  397. {
  398. self->spawnflags &= ~65536;
  399. self->monsterinfo.currentmove = &brain_move_attack1;
  400. }
  401. }
  402. mframe_t brain_frames_attack2 [] =
  403. {
  404. ai_charge, 5, NULL,
  405. ai_charge, -4, NULL,
  406. ai_charge, -4, NULL,
  407. ai_charge, -3, NULL,
  408. ai_charge, 0, brain_chest_open,
  409. ai_charge, 0, NULL,
  410. ai_charge, 13, brain_tentacle_attack,
  411. ai_charge, 0, NULL,
  412. ai_charge, 2, NULL,
  413. ai_charge, 0, NULL,
  414. ai_charge, -9, brain_chest_closed,
  415. ai_charge, 0, NULL,
  416. ai_charge, 4, NULL,
  417. ai_charge, 3, NULL,
  418. ai_charge, 2, NULL,
  419. ai_charge, -3, NULL,
  420. ai_charge, -6, NULL
  421. };
  422. mmove_t brain_move_attack2 = {FRAME_attak201, FRAME_attak217, brain_frames_attack2, brain_run};
  423. void brain_melee(edict_t *self)
  424. {
  425. if (random() <= 0.5)
  426. self->monsterinfo.currentmove = &brain_move_attack1;
  427. else
  428. self->monsterinfo.currentmove = &brain_move_attack2;
  429. }
  430. static qboolean brain_tounge_attack_ok (vec3_t start, vec3_t end)
  431. {
  432. vec3_t dir, angles;
  433. // check for max distance
  434. VectorSubtract (start, end, dir);
  435. if (VectorLength(dir) > 512)
  436. return false;
  437. // check for min/max pitch
  438. vectoangles (dir, angles);
  439. if (angles[0] < -180)
  440. angles[0] += 360;
  441. if (fabs(angles[0]) > 30)
  442. return false;
  443. return true;
  444. }
  445. void brain_tounge_attack (edict_t *self)
  446. {
  447. vec3_t offset, start, f, r, end, dir;
  448. trace_t tr;
  449. int damage;
  450. AngleVectors (self->s.angles, f, r, NULL);
  451. // VectorSet (offset, 24, 0, 6);
  452. VectorSet (offset, 24, 0, 16);
  453. G_ProjectSource (self->s.origin, offset, f, r, start);
  454. VectorCopy (self->enemy->s.origin, end);
  455. if (!brain_tounge_attack_ok(start, end))
  456. {
  457. end[2] = self->enemy->s.origin[2] + self->enemy->maxs[2] - 8;
  458. if (!brain_tounge_attack_ok(start, end))
  459. {
  460. end[2] = self->enemy->s.origin[2] + self->enemy->mins[2] + 8;
  461. if (!brain_tounge_attack_ok(start, end))
  462. return;
  463. }
  464. }
  465. VectorCopy (self->enemy->s.origin, end);
  466. tr = gi.trace (start, NULL, NULL, end, self, MASK_SHOT);
  467. if (tr.ent != self->enemy)
  468. return;
  469. damage = 5;
  470. gi.sound (self, CHAN_WEAPON, sound_tentacles_retract, 1, ATTN_NORM, 0);
  471. gi.WriteByte (svc_temp_entity);
  472. gi.WriteByte (TE_PARASITE_ATTACK);
  473. gi.WriteShort (self - g_edicts);
  474. gi.WritePosition (start);
  475. gi.WritePosition (end);
  476. gi.multicast (self->s.origin, MULTICAST_PVS);
  477. VectorSubtract (start, end, dir);
  478. T_Damage (self->enemy, self, self, dir, self->enemy->s.origin, vec3_origin, damage, 0, DAMAGE_NO_KNOCKBACK, MOD_BRAINTENTACLE);
  479. // pull the enemy in
  480. {
  481. vec3_t forward;
  482. self->s.origin[2] += 1;
  483. AngleVectors (self->s.angles, forward, NULL, NULL);
  484. VectorScale (forward, -1200, self->enemy->velocity);
  485. }
  486. }
  487. // Brian right eye center
  488. struct r_eyeball
  489. {
  490. float x;
  491. float y;
  492. float z;
  493. } brain_reye [11] = {
  494. { 0.746700, 0.238370, 34.167690 },
  495. { -1.076390, 0.238370, 33.386372 },
  496. { -1.335500, 5.334300, 32.177170 },
  497. { -0.175360, 8.846370, 30.635479 },
  498. { -2.757590, 7.804610, 30.150860 },
  499. { -5.575090, 5.152840, 30.056160 },
  500. { -7.017550, 3.262470, 30.552521 },
  501. { -7.915740, 0.638800, 33.176189 },
  502. { -3.915390, 8.285730, 33.976349 },
  503. { -0.913540, 10.933030, 34.141811 },
  504. { -0.369900, 8.923900, 34.189079 }
  505. };
  506. // Brain left eye center
  507. struct l_eyeball
  508. {
  509. float x;
  510. float y;
  511. float z;
  512. } brain_leye [11] = {
  513. { -3.364710, 0.327750, 33.938381 },
  514. { -5.140450, 0.493480, 32.659851 },
  515. { -5.341980, 5.646980, 31.277901 },
  516. { -4.134480, 9.277440, 29.925621 },
  517. { -6.598340, 6.815090, 29.322620 },
  518. { -8.610840, 2.529650, 29.251591 },
  519. { -9.231360, 0.093280, 29.747959 },
  520. { -11.004110, 1.936930, 32.395260 },
  521. { -7.878310, 7.648190, 33.148151 },
  522. { -4.947370, 11.430050, 33.313610 },
  523. { -4.332820, 9.444570, 33.526340 }
  524. };
  525. // note to self
  526. // need to get an x,y,z offset for
  527. // each frame of the run cycle
  528. void brain_laserbeam (edict_t *self)
  529. {
  530. vec3_t forward, right, up;
  531. vec3_t tempang, start;
  532. vec3_t dir, angles, end;
  533. edict_t *ent;
  534. // RAFAEL
  535. // cant call sound this frequent
  536. if (random() > 0.8)
  537. gi.sound(self, CHAN_AUTO, gi.soundindex("misc/lasfly.wav"), 1, ATTN_STATIC, 0);
  538. // check for max distance
  539. VectorCopy (self->s.origin, start);
  540. VectorCopy (self->enemy->s.origin, end);
  541. VectorSubtract (end, start, dir);
  542. vectoangles (dir, angles);
  543. // dis is my right eye
  544. ent = G_Spawn ();
  545. VectorCopy (self->s.origin, ent->s.origin);
  546. VectorCopy (angles, tempang);
  547. AngleVectors (tempang, forward, right, up);
  548. VectorCopy (tempang, ent->s.angles);
  549. VectorCopy (ent->s.origin, start);
  550. VectorMA (start, brain_reye[self->s.frame - FRAME_walk101].x, right, start);
  551. VectorMA (start, brain_reye[self->s.frame - FRAME_walk101].y, forward, start);
  552. VectorMA (start, brain_reye[self->s.frame - FRAME_walk101].z, up, start);
  553. VectorCopy (start, ent->s.origin);
  554. ent->enemy = self->enemy;
  555. ent->owner = self;
  556. ent->dmg = 1;
  557. monster_dabeam (ent);
  558. // dis is me left eye
  559. ent = G_Spawn ();
  560. VectorCopy (self->s.origin, ent->s.origin);
  561. VectorCopy (angles, tempang);
  562. AngleVectors (tempang, forward, right, up);
  563. VectorCopy (tempang, ent->s.angles);
  564. VectorCopy (ent->s.origin, start);
  565. VectorMA (start, brain_leye[self->s.frame - FRAME_walk101].x, right, start);
  566. VectorMA (start, brain_leye[self->s.frame - FRAME_walk101].y, forward, start);
  567. VectorMA (start, brain_leye[self->s.frame - FRAME_walk101].z, up, start);
  568. VectorCopy (start, ent->s.origin);
  569. ent->enemy = self->enemy;
  570. ent->owner = self;
  571. ent->dmg = 1;
  572. monster_dabeam (ent);
  573. }
  574. void brain_laserbeam_reattack (edict_t *self)
  575. {
  576. if (random() < 0.5)
  577. if (visible (self, self->enemy))
  578. if (self->enemy->health > 0)
  579. self->s.frame = FRAME_walk101;
  580. }
  581. mframe_t brain_frames_attack3 [] =
  582. {
  583. ai_charge, 5, NULL,
  584. ai_charge, -4, NULL,
  585. ai_charge, -4, NULL,
  586. ai_charge, -3, NULL,
  587. ai_charge, 0, brain_chest_open,
  588. ai_charge, 0, brain_tounge_attack,
  589. ai_charge, 13, NULL,
  590. ai_charge, 0, brain_tentacle_attack,
  591. ai_charge, 2, NULL,
  592. ai_charge, 0, brain_tounge_attack,
  593. ai_charge, -9, brain_chest_closed,
  594. ai_charge, 0, NULL,
  595. ai_charge, 4, NULL,
  596. ai_charge, 3, NULL,
  597. ai_charge, 2, NULL,
  598. ai_charge, -3, NULL,
  599. ai_charge, -6, NULL
  600. };
  601. mmove_t brain_move_attack3 = {FRAME_attak201, FRAME_attak217, brain_frames_attack3, brain_run};
  602. mframe_t brain_frames_attack4 [] =
  603. {
  604. ai_charge, 9, brain_laserbeam,
  605. ai_charge, 2, brain_laserbeam,
  606. ai_charge, 3, brain_laserbeam,
  607. ai_charge, 3, brain_laserbeam,
  608. ai_charge, 1, brain_laserbeam,
  609. ai_charge, 0, brain_laserbeam,
  610. ai_charge, 0, brain_laserbeam,
  611. ai_charge, 10, brain_laserbeam,
  612. ai_charge, -4, brain_laserbeam,
  613. ai_charge, -1, brain_laserbeam,
  614. ai_charge, 2, brain_laserbeam_reattack
  615. };
  616. mmove_t brain_move_attack4 = {FRAME_walk101, FRAME_walk111, brain_frames_attack4, brain_run};
  617. // RAFAEL
  618. void brain_attack (edict_t *self)
  619. {
  620. int r;
  621. if (random() < 0.8)
  622. {
  623. r = range (self, self->enemy);
  624. if (r == RANGE_NEAR)
  625. {
  626. if (random() < 0.5)
  627. self->monsterinfo.currentmove = &brain_move_attack3;
  628. else
  629. self->monsterinfo.currentmove = &brain_move_attack4;
  630. }
  631. else if (r > RANGE_NEAR)
  632. self->monsterinfo.currentmove = &brain_move_attack4;
  633. }
  634. }
  635. //
  636. // RUN
  637. //
  638. mframe_t brain_frames_run [] =
  639. {
  640. ai_run, 9, NULL,
  641. ai_run, 2, NULL,
  642. ai_run, 3, NULL,
  643. ai_run, 3, NULL,
  644. ai_run, 1, NULL,
  645. ai_run, 0, NULL,
  646. ai_run, 0, NULL,
  647. ai_run, 10, NULL,
  648. ai_run, -4, NULL,
  649. ai_run, -1, NULL,
  650. ai_run, 2, NULL
  651. };
  652. mmove_t brain_move_run = {FRAME_walk101, FRAME_walk111, brain_frames_run, NULL};
  653. void brain_run (edict_t *self)
  654. {
  655. self->monsterinfo.power_armor_type = POWER_ARMOR_SCREEN;
  656. if (self->monsterinfo.aiflags & AI_STAND_GROUND)
  657. self->monsterinfo.currentmove = &brain_move_stand;
  658. else
  659. self->monsterinfo.currentmove = &brain_move_run;
  660. }
  661. void brain_pain (edict_t *self, edict_t *other, float kick, int damage)
  662. {
  663. float r;
  664. if (self->health < (self->max_health / 2))
  665. self->s.skinnum = 1;
  666. if (level.time < self->pain_debounce_time)
  667. return;
  668. self->pain_debounce_time = level.time + 3;
  669. r = random();
  670. if (r < 0.33)
  671. {
  672. gi.sound (self, CHAN_VOICE, sound_pain1, 1, ATTN_NORM, 0);
  673. self->monsterinfo.currentmove = &brain_move_pain1;
  674. }
  675. else if (r < 0.66)
  676. {
  677. gi.sound (self, CHAN_VOICE, sound_pain2, 1, ATTN_NORM, 0);
  678. self->monsterinfo.currentmove = &brain_move_pain2;
  679. }
  680. else
  681. {
  682. gi.sound (self, CHAN_VOICE, sound_pain1, 1, ATTN_NORM, 0);
  683. self->monsterinfo.currentmove = &brain_move_pain3;
  684. }
  685. }
  686. void brain_dead (edict_t *self)
  687. {
  688. VectorSet (self->mins, -16, -16, -24);
  689. VectorSet (self->maxs, 16, 16, -8);
  690. self->movetype = MOVETYPE_TOSS;
  691. self->svflags |= SVF_DEADMONSTER;
  692. self->nextthink = 0;
  693. gi.linkentity (self);
  694. }
  695. void brain_die (edict_t *self, edict_t *inflictor, edict_t *attacker, int damage, vec3_t point)
  696. {
  697. int n;
  698. self->s.effects = 0;
  699. self->monsterinfo.power_armor_type = POWER_ARMOR_NONE;
  700. // check for gib
  701. if (self->health <= self->gib_health)
  702. {
  703. gi.sound (self, CHAN_VOICE, gi.soundindex ("misc/udeath.wav"), 1, ATTN_NORM, 0);
  704. for (n= 0; n < 2; n++)
  705. ThrowGib (self, "models/objects/gibs/bone/tris.md2", damage, GIB_ORGANIC);
  706. for (n= 0; n < 4; n++)
  707. ThrowGib (self, "models/objects/gibs/sm_meat/tris.md2", damage, GIB_ORGANIC);
  708. ThrowHead (self, "models/objects/gibs/head2/tris.md2", damage, GIB_ORGANIC);
  709. self->deadflag = DEAD_DEAD;
  710. return;
  711. }
  712. if (self->deadflag == DEAD_DEAD)
  713. return;
  714. // regular death
  715. gi.sound (self, CHAN_VOICE, sound_death, 1, ATTN_NORM, 0);
  716. self->deadflag = DEAD_DEAD;
  717. self->takedamage = DAMAGE_YES;
  718. if (random() <= 0.5)
  719. self->monsterinfo.currentmove = &brain_move_death1;
  720. else
  721. self->monsterinfo.currentmove = &brain_move_death2;
  722. }
  723. /*QUAKED monster_brain (1 .5 0) (-16 -16 -24) (16 16 32) Ambush Trigger_Spawn Sight
  724. */
  725. void SP_monster_brain (edict_t *self)
  726. {
  727. if (deathmatch->value)
  728. {
  729. G_FreeEdict (self);
  730. return;
  731. }
  732. sound_chest_open = gi.soundindex ("brain/brnatck1.wav");
  733. sound_tentacles_extend = gi.soundindex ("brain/brnatck2.wav");
  734. sound_tentacles_retract = gi.soundindex ("brain/brnatck3.wav");
  735. sound_death = gi.soundindex ("brain/brndeth1.wav");
  736. sound_idle1 = gi.soundindex ("brain/brnidle1.wav");
  737. sound_idle2 = gi.soundindex ("brain/brnidle2.wav");
  738. sound_idle3 = gi.soundindex ("brain/brnlens1.wav");
  739. sound_pain1 = gi.soundindex ("brain/brnpain1.wav");
  740. sound_pain2 = gi.soundindex ("brain/brnpain2.wav");
  741. sound_sight = gi.soundindex ("brain/brnsght1.wav");
  742. sound_search = gi.soundindex ("brain/brnsrch1.wav");
  743. sound_melee1 = gi.soundindex ("brain/melee1.wav");
  744. sound_melee2 = gi.soundindex ("brain/melee2.wav");
  745. sound_melee3 = gi.soundindex ("brain/melee3.wav");
  746. self->movetype = MOVETYPE_STEP;
  747. self->solid = SOLID_BBOX;
  748. self->s.modelindex = gi.modelindex ("models/monsters/brain/tris.md2");
  749. VectorSet (self->mins, -16, -16, -24);
  750. VectorSet (self->maxs, 16, 16, 32);
  751. self->health = 300;
  752. self->gib_health = -150;
  753. self->mass = 400;
  754. self->pain = brain_pain;
  755. self->die = brain_die;
  756. self->monsterinfo.stand = brain_stand;
  757. self->monsterinfo.walk = brain_walk;
  758. self->monsterinfo.run = brain_run;
  759. self->monsterinfo.dodge = brain_dodge;
  760. self->monsterinfo.attack = brain_attack;
  761. self->monsterinfo.melee = brain_melee;
  762. self->monsterinfo.sight = brain_sight;
  763. self->monsterinfo.search = brain_search;
  764. self->monsterinfo.idle = brain_idle;
  765. self->monsterinfo.power_armor_type = POWER_ARMOR_SCREEN;
  766. self->monsterinfo.power_armor_power = 100;
  767. gi.linkentity (self);
  768. self->monsterinfo.currentmove = &brain_move_stand;
  769. self->monsterinfo.scale = MODEL_SCALE;
  770. walkmonster_start (self);
  771. }