Added freddie and vulture monsters to missionpack DLL.

Added functions ThrowGibFrame() and ThrowDebrisFrame() to g_misc.c in missionpack DLL.
Added GIB_FEATHER gib type and MOVETYPE_FEATHER phys type to missionpack DLL.
Added precache functions for monster weapons in g_weapon_q1.c in missionpack DLL.
Moved function AimGrenade() from grenade.c to g_weapon.c in missionpack DLL.
This commit is contained in:
Knightmare66 2020-12-03 17:00:15 -05:00
parent c7334dfab0
commit e8769195cd
43 changed files with 2605 additions and 421 deletions

View file

@ -2146,16 +2146,16 @@ qboolean ai_chicken (edict_t *self, edict_t *badguy)
return true;
}
VectorCopy(self->mins,mins);
VectorCopy (self->mins, mins);
mins[2] += 18;
if (mins[2] > 0) mins[2] = 0;
VectorCopy(self->maxs,maxs);
VectorCopy(self->maxs, maxs);
// Find a vector that will hide the actor from his enemy
VectorCopy(badguy->s.origin,atk);
VectorCopy (badguy->s.origin, atk);
atk[2] += badguy->viewheight;
VectorClear(best_dir);
AngleVectors(self->s.angles,forward,NULL,NULL);
AngleVectors (self->s.angles, forward, NULL, NULL);
dir[2] = 0;
for (travel=512; travel>63 && best_dist == 0; travel /= 2)
{

View file

@ -534,6 +534,22 @@ extern float target_angle ( edict_t * self ) ;
extern void widow_sight ( edict_t * self , edict_t * other ) ;
extern void widow_search ( edict_t * self ) ;
extern void showme ( edict_t * self ) ;
extern void SP_monster_vulture ( edict_t * self ) ;
extern void vulture_die ( edict_t * self , edict_t * inflictor , edict_t * attacker , int damage , vec3_t point ) ;
extern void vulture_dead ( edict_t * self ) ;
extern void vulture_pain ( edict_t * self , edict_t * other , float kick , int damage ) ;
extern void vulture_melee ( edict_t * self ) ;
extern void vulture_peck ( edict_t * self ) ;
extern void vulture_run ( edict_t * self ) ;
extern void vulture_landed ( edict_t * self ) ;
extern void vulture_airborne ( edict_t * self ) ;
extern void vulture_walk ( edict_t * self ) ;
extern void vulture_perch ( edict_t * self ) ;
extern void vulture_flap ( edict_t * self ) ;
extern void vulture_idle ( edict_t * self ) ;
extern void vulture_soar_idle ( edict_t * self ) ;
extern void vulture_perch_idle ( edict_t * self ) ;
extern void vulture_sight ( edict_t * self , edict_t * other ) ;
extern void SP_monster_turret ( edict_t * self ) ;
extern qboolean turret_checkattack ( edict_t * self ) ;
extern void turret_activate ( edict_t * self , edict_t * other , edict_t * activator ) ;
@ -864,6 +880,32 @@ extern void q1grunt_run ( edict_t * self ) ;
extern void q1grunt_walk ( edict_t * self ) ;
extern void q1grunt_stand ( edict_t * self ) ;
extern void q1grunt_idle ( edict_t * self ) ;
extern void SP_monster_q1_freddie ( edict_t * self ) ;
extern void freddie_die ( edict_t * self , edict_t * inflictor , edict_t * attacker , int damage , vec3_t point ) ;
extern void freddie_nogib ( edict_t * self ) ;
extern void freddie_dead ( edict_t * self ) ;
extern void freddie_melee ( edict_t * self ) ;
extern void freddie_melee_repeat ( edict_t * self ) ;
extern void freddie_blade_left ( edict_t * self ) ;
extern void freddie_blade_right ( edict_t * self ) ;
extern void freddie_blade ( edict_t * self , float side ) ;
extern void freddie_saw_sound ( edict_t * self ) ;
extern void freddie_attack ( edict_t * self ) ;
extern void freddie_attack_spindown ( edict_t * self ) ;
extern void freddie_do_sfire ( edict_t * self ) ;
extern void freddie_stand_fire ( edict_t * self ) ;
extern void freddie_fireweapon ( edict_t * self , vec3_t offset ) ;
extern void freddie_attack_prefire ( edict_t * self ) ;
extern void freddie_attack_spinupsound ( edict_t * self ) ;
extern void freddie_pain ( edict_t * self , edict_t * other , float kick , int damage ) ;
extern void freddie_run_frame ( edict_t * self ) ;
extern void freddie_rfire ( edict_t * self ) ;
extern void freddie_run ( edict_t * self ) ;
extern void freddie_walk ( edict_t * self ) ;
extern void freddie_stand ( edict_t * self ) ;
extern void freddie_sound_footstep ( edict_t * self ) ;
extern void freddie_sight ( edict_t * self , edict_t * other ) ;
extern void freddie_idle_sound ( edict_t * self ) ;
extern void SP_monster_q1_fiend ( edict_t * self ) ;
extern void fiend_die ( edict_t * self , edict_t * inflictor , edict_t * attacker , int damage , vec3_t point ) ;
extern void fiend_nogib ( edict_t * self ) ;
@ -1532,29 +1574,38 @@ extern void actor_walk_back ( edict_t * self ) ;
extern void actor_walk ( edict_t * self ) ;
extern void actor_stand ( edict_t * self ) ;
extern void InitLithiumVars ( void ) ;
extern void q1_gib_precache ( void ) ;
extern void q1_fire_gib ( edict_t * self , vec3_t start , vec3_t aimdir , int damage , int speed ) ;
extern void q1_zombiegib_touch ( edict_t * ent , edict_t * other , cplane_t * plane , csurface_t * surf ) ;
extern void q1_acidspit_precache ( void ) ;
extern void q1_fire_acidspit ( edict_t * self , vec3_t start , vec3_t dir , int damage , int speed ) ;
extern void q1_acidbolt_touch ( edict_t * ent , edict_t * other , cplane_t * plane , csurface_t * surf ) ;
extern void q1_fire_lavaball_precache ( void ) ;
extern void q1_fire_lavaball ( edict_t * self , vec3_t start , vec3_t dir , int damage , int speed , float damage_radius , int radius_damage ) ;
extern void q1_lavaball_touch ( edict_t * ent , edict_t * other , cplane_t * plane , csurface_t * surf ) ;
extern void q1_firepod_precache ( void ) ;
extern void q1_fire_firepod ( edict_t * self , vec3_t dir ) ;
extern void q1_firepod_home ( edict_t * self ) ;
extern void q1_firepod_touch ( edict_t * self , edict_t * other , cplane_t * plane , csurface_t * surf ) ;
extern void q1_fire_lightning ( edict_t * self , vec3_t start , vec3_t dir , int damage ) ;
extern void q1_rocket_precahce ( void ) ;
extern void q1_fire_rocket ( edict_t * self , vec3_t start , vec3_t dir , int damage , int speed , float damage_radius , int radius_damage ) ;
extern void q1rocket_trail ( edict_t * self , vec3_t start , vec3_t dir ) ;
extern void q1rocketTrail_touch ( edict_t * ent , edict_t * other , cplane_t * plane , csurface_t * surf ) ;
extern void q1_rocket_touch ( edict_t * ent , edict_t * other , cplane_t * plane , csurface_t * surf ) ;
extern void q1_grenade_precache ( void ) ;
extern void q1_fire_grenade ( edict_t * self , vec3_t start , vec3_t aimdir , int damage , int speed , float timer , float damage_radius ) ;
extern void q1_grenade_touch ( edict_t * ent , edict_t * other , cplane_t * plane , csurface_t * surf ) ;
extern void q1_grenade_explode ( edict_t * ent ) ;
extern void q1_explode ( edict_t * self ) ;
extern void q1_flame_precache ( void ) ;
extern void q1_fire_flame ( edict_t * self , vec3_t start , vec3_t dir , float leftrightoff ) ;
extern void q1_flame_touch ( edict_t * self , edict_t * other , cplane_t * plane , csurface_t * surf ) ;
extern void q1_flame_splash ( int type , int count , int color , vec3_t start , vec3_t movdir , vec3_t origin ) ;
extern void q1_laser_precache ( void ) ;
extern void q1_fire_laser ( edict_t * self , vec3_t start , vec3_t dir , int damage , int speed ) ;
extern void q1_laser_touch ( edict_t * self , edict_t * other , cplane_t * plane , csurface_t * surf ) ;
extern void q1_nail_precache ( void ) ;
extern void q1_fire_nail ( edict_t * self , vec3_t start , vec3_t dir , int damage , int speed , qboolean sng ) ;
extern void q1_nail_touch ( edict_t * self , edict_t * other , cplane_t * plane , csurface_t * surf ) ;
extern void SP_goop ( edict_t * goop ) ;
@ -1613,6 +1664,7 @@ extern void fire_missile ( edict_t * self , vec3_t start , vec3_t dir , int dama
extern void missile_die ( edict_t * self , edict_t * inflictor , edict_t * attacker , int damage , vec3_t point ) ;
extern void missile_explode ( edict_t * ent ) ;
extern void missile_touch ( edict_t * ent , edict_t * other , cplane_t * plane , csurface_t * surf ) ;
extern qboolean AimGrenade ( edict_t * self , vec3_t start , vec3_t target , vec_t speed , vec3_t aim ) ;
extern void SP_handgrenade ( edict_t * grenade ) ;
extern void handgrenade_delayed_start ( edict_t * grenade ) ;
extern void SP_grenade ( edict_t * grenade ) ;
@ -1807,7 +1859,7 @@ extern void thing_grenade_boom ( edict_t * self ) ;
extern void thing_think_pause ( edict_t * self ) ;
extern void thing_think ( edict_t * self ) ;
extern void thing_restore_leader ( edict_t * self ) ;
extern edict_t * SpawnThing ( ) ;
extern edict_t * SpawnThing ( void ) ;
extern void SP_target_earthquake ( edict_t * self ) ;
extern void target_earthquake_use ( edict_t * self , edict_t * other , edict_t * activator ) ;
extern void target_earthquake_think ( edict_t * self ) ;
@ -2421,6 +2473,7 @@ extern void BecomeExplosion1 ( edict_t * self ) ;
extern void SP_debris ( edict_t * debris ) ;
extern void debris_delayed_start ( edict_t * debris ) ;
extern void ThrowDebris ( edict_t * self , char * modelname , float speed , vec3_t origin , int skin , int effects ) ;
extern void ThrowDebrisFrame ( edict_t * self , char * modelname , float speed , vec3_t origin , int frame , int skin , int effects ) ;
extern void debris_die ( edict_t * self , edict_t * inflictor , edict_t * attacker , int damage , vec3_t point ) ;
extern void ThrowClientHead ( edict_t * self , int damage ) ;
extern void SP_gibhead ( edict_t * gib ) ;
@ -2428,6 +2481,7 @@ extern void ThrowHead ( edict_t * self , char * gibname , int damage , int type
extern void SP_gib ( edict_t * gib ) ;
extern void gib_delayed_start ( edict_t * gib ) ;
extern void ThrowGib ( edict_t * self , char * gibname , int damage , int type ) ;
extern void ThrowGibFrame ( edict_t * self , char * gibname , int frame , int damage , int type ) ;
extern void gib_die ( edict_t * self , edict_t * inflictor , edict_t * attacker , int damage , vec3_t point ) ;
extern void gib_touch ( edict_t * self , edict_t * other , cplane_t * plane , csurface_t * surf ) ;
extern void gib_think ( edict_t * self ) ;
@ -2827,7 +2881,6 @@ extern void ai_walk ( edict_t * self , float dist ) ;
extern void ai_stand ( edict_t * self , float dist ) ;
extern void ai_move ( edict_t * self , float dist ) ;
extern void AI_SetSightClient ( void ) ;
extern qboolean AimGrenade ( edict_t * self , vec3_t start , vec3_t target , vec_t speed , vec3_t aim ) ;
extern void SP_dm_tag_token ( edict_t * self ) ;
extern void Tag_PostInitSetup ( void ) ;
extern void Tag_GameInit ( void ) ;

View file

@ -534,6 +534,22 @@
{"widow_sight", (byte *)widow_sight},
{"widow_search", (byte *)widow_search},
{"showme", (byte *)showme},
{"SP_monster_vulture", (byte *)SP_monster_vulture},
{"vulture_die", (byte *)vulture_die},
{"vulture_dead", (byte *)vulture_dead},
{"vulture_pain", (byte *)vulture_pain},
{"vulture_melee", (byte *)vulture_melee},
{"vulture_peck", (byte *)vulture_peck},
{"vulture_run", (byte *)vulture_run},
{"vulture_landed", (byte *)vulture_landed},
{"vulture_airborne", (byte *)vulture_airborne},
{"vulture_walk", (byte *)vulture_walk},
{"vulture_perch", (byte *)vulture_perch},
{"vulture_flap", (byte *)vulture_flap},
{"vulture_idle", (byte *)vulture_idle},
{"vulture_soar_idle", (byte *)vulture_soar_idle},
{"vulture_perch_idle", (byte *)vulture_perch_idle},
{"vulture_sight", (byte *)vulture_sight},
{"SP_monster_turret", (byte *)SP_monster_turret},
{"turret_checkattack", (byte *)turret_checkattack},
{"turret_activate", (byte *)turret_activate},
@ -864,6 +880,32 @@
{"q1grunt_walk", (byte *)q1grunt_walk},
{"q1grunt_stand", (byte *)q1grunt_stand},
{"q1grunt_idle", (byte *)q1grunt_idle},
{"SP_monster_q1_freddie", (byte *)SP_monster_q1_freddie},
{"freddie_die", (byte *)freddie_die},
{"freddie_nogib", (byte *)freddie_nogib},
{"freddie_dead", (byte *)freddie_dead},
{"freddie_melee", (byte *)freddie_melee},
{"freddie_melee_repeat", (byte *)freddie_melee_repeat},
{"freddie_blade_left", (byte *)freddie_blade_left},
{"freddie_blade_right", (byte *)freddie_blade_right},
{"freddie_blade", (byte *)freddie_blade},
{"freddie_saw_sound", (byte *)freddie_saw_sound},
{"freddie_attack", (byte *)freddie_attack},
{"freddie_attack_spindown", (byte *)freddie_attack_spindown},
{"freddie_do_sfire", (byte *)freddie_do_sfire},
{"freddie_stand_fire", (byte *)freddie_stand_fire},
{"freddie_fireweapon", (byte *)freddie_fireweapon},
{"freddie_attack_prefire", (byte *)freddie_attack_prefire},
{"freddie_attack_spinupsound", (byte *)freddie_attack_spinupsound},
{"freddie_pain", (byte *)freddie_pain},
{"freddie_run_frame", (byte *)freddie_run_frame},
{"freddie_rfire", (byte *)freddie_rfire},
{"freddie_run", (byte *)freddie_run},
{"freddie_walk", (byte *)freddie_walk},
{"freddie_stand", (byte *)freddie_stand},
{"freddie_sound_footstep", (byte *)freddie_sound_footstep},
{"freddie_sight", (byte *)freddie_sight},
{"freddie_idle_sound", (byte *)freddie_idle_sound},
{"SP_monster_q1_fiend", (byte *)SP_monster_q1_fiend},
{"fiend_die", (byte *)fiend_die},
{"fiend_nogib", (byte *)fiend_nogib},
@ -1532,29 +1574,38 @@
{"actor_walk", (byte *)actor_walk},
{"actor_stand", (byte *)actor_stand},
{"InitLithiumVars", (byte *)InitLithiumVars},
{"q1_gib_precache", (byte *)q1_gib_precache},
{"q1_fire_gib", (byte *)q1_fire_gib},
{"q1_zombiegib_touch", (byte *)q1_zombiegib_touch},
{"q1_acidspit_precache", (byte *)q1_acidspit_precache},
{"q1_fire_acidspit", (byte *)q1_fire_acidspit},
{"q1_acidbolt_touch", (byte *)q1_acidbolt_touch},
{"q1_fire_lavaball_precache", (byte *)q1_fire_lavaball_precache},
{"q1_fire_lavaball", (byte *)q1_fire_lavaball},
{"q1_lavaball_touch", (byte *)q1_lavaball_touch},
{"q1_firepod_precache", (byte *)q1_firepod_precache},
{"q1_fire_firepod", (byte *)q1_fire_firepod},
{"q1_firepod_home", (byte *)q1_firepod_home},
{"q1_firepod_touch", (byte *)q1_firepod_touch},
{"q1_fire_lightning", (byte *)q1_fire_lightning},
{"q1_rocket_precahce", (byte *)q1_rocket_precahce},
{"q1_fire_rocket", (byte *)q1_fire_rocket},
{"q1rocket_trail", (byte *)q1rocket_trail},
{"q1rocketTrail_touch", (byte *)q1rocketTrail_touch},
{"q1_rocket_touch", (byte *)q1_rocket_touch},
{"q1_grenade_precache", (byte *)q1_grenade_precache},
{"q1_fire_grenade", (byte *)q1_fire_grenade},
{"q1_grenade_touch", (byte *)q1_grenade_touch},
{"q1_grenade_explode", (byte *)q1_grenade_explode},
{"q1_explode", (byte *)q1_explode},
{"q1_flame_precache", (byte *)q1_flame_precache},
{"q1_fire_flame", (byte *)q1_fire_flame},
{"q1_flame_touch", (byte *)q1_flame_touch},
{"q1_flame_splash", (byte *)q1_flame_splash},
{"q1_laser_precache", (byte *)q1_laser_precache},
{"q1_fire_laser", (byte *)q1_fire_laser},
{"q1_laser_touch", (byte *)q1_laser_touch},
{"q1_nail_precache", (byte *)q1_nail_precache},
{"q1_fire_nail", (byte *)q1_fire_nail},
{"q1_nail_touch", (byte *)q1_nail_touch},
{"SP_goop", (byte *)SP_goop},
@ -1613,6 +1664,7 @@
{"missile_die", (byte *)missile_die},
{"missile_explode", (byte *)missile_explode},
{"missile_touch", (byte *)missile_touch},
{"AimGrenade", (byte *)AimGrenade},
{"SP_handgrenade", (byte *)SP_handgrenade},
{"handgrenade_delayed_start", (byte *)handgrenade_delayed_start},
{"SP_grenade", (byte *)SP_grenade},
@ -2421,6 +2473,7 @@
{"SP_debris", (byte *)SP_debris},
{"debris_delayed_start", (byte *)debris_delayed_start},
{"ThrowDebris", (byte *)ThrowDebris},
{"ThrowDebrisFrame", (byte *)ThrowDebrisFrame},
{"debris_die", (byte *)debris_die},
{"ThrowClientHead", (byte *)ThrowClientHead},
{"SP_gibhead", (byte *)SP_gibhead},
@ -2428,6 +2481,7 @@
{"SP_gib", (byte *)SP_gib},
{"gib_delayed_start", (byte *)gib_delayed_start},
{"ThrowGib", (byte *)ThrowGib},
{"ThrowGibFrame", (byte *)ThrowGibFrame},
{"gib_die", (byte *)gib_die},
{"gib_touch", (byte *)gib_touch},
{"gib_think", (byte *)gib_think},
@ -2827,7 +2881,6 @@
{"ai_stand", (byte *)ai_stand},
{"ai_move", (byte *)ai_move},
{"AI_SetSightClient", (byte *)AI_SetSightClient},
{"AimGrenade", (byte *)AimGrenade},
{"SP_dm_tag_token", (byte *)SP_dm_tag_token},
{"Tag_PostInitSetup", (byte *)Tag_PostInitSetup},
{"Tag_GameInit", (byte *)Tag_GameInit},

View file

@ -212,6 +212,7 @@ typedef enum
//gib types
#define GIB_ORGANIC 0
#define GIB_METALLIC 1
#define GIB_FEATHER 2 // Knightmare- added for vulture
// monster ai flags
#define AI_STAND_GROUND 0x00000001
@ -346,6 +347,7 @@ MOVETYPE_PENDULUM, // same as MOVETYPE_PUSH, but used only for pendulums to gra
MOVETYPE_CONVEYOR, // conveyor
MOVETYPE_SHOCKBOUNCE, // Knightmare- added for shockwave
MOVETYPE_FEATHER, // Knightmare- added for vulture, specifies slow falling
// Zaero
MOVETYPE_FREEZE, // player freeze, used for Zaero Camera
MOVETYPE_FALLFLOAT, // falls down slopes and floats in water
@ -1409,7 +1411,9 @@ void gib_fade (edict_t *self);
void ThrowHead (edict_t *self, char *gibname, int damage, int type);
void ThrowClientHead (edict_t *self, int damage);
void ThrowGib (edict_t *self, char *gibname, int damage, int type);
void ThrowGibFrame (edict_t *self, char *gibname, int frame, int damage, int type);
void ThrowDebris (edict_t *self, char *modelname, float speed, vec3_t origin, int skin, int effects);
void ThrowDebrisFrame (edict_t *self, char *modelname, float speed, vec3_t origin, int frame, int skin, int effects);
void BecomeExplosion1(edict_t *self);
void BecomeExplosion2(edict_t *self);
void BecomeExplosion3(edict_t *self);
@ -1498,17 +1502,25 @@ void Grenade_Evade (edict_t *monster);
// g_weapon_q1.c
//
void q1_fire_nail (edict_t *self, vec3_t start, vec3_t dir, int damage, int speed, qboolean sng);
void q1_nail_precache (void);
void q1_fire_laser (edict_t *self, vec3_t start, vec3_t dir, int damage, int speed);
void q1_laser_precache (void);
void q1_fire_flame (edict_t *self, vec3_t start, vec3_t dir, float leftrightoff);
void q1_flame_precache (void);
void q1_explode (edict_t *self);
void q1_fire_grenade (edict_t *self, vec3_t start, vec3_t aimdir, int damage, int speed, float timer, float damage_radius);
void q1_grenade_precache (void);
void q1_fire_rocket (edict_t *self, vec3_t start, vec3_t dir, int damage, int speed, float damage_radius, int radius_damage);
void q1_rocket_precahce (void);
void q1_fire_lightning (edict_t *self, vec3_t start, vec3_t dir, int damage);
void q1_fire_firepod (edict_t *self, vec3_t dir);
void q1_firepod_precache (void);
void q1_fire_lavaball (edict_t *self, vec3_t start, vec3_t dir, int damage, int speed, float damage_radius, int radius_damage);
void q1_fire_lavaball_precache (void);
void q1_fire_acidspit (edict_t *self, vec3_t start, vec3_t dir, int damage, int speed);
void q1_acidspit_precache (void);
void q1_fire_gib (edict_t *self, vec3_t start, vec3_t aimdir, int damage, int speed);
void q1_gib_precache (void);
//
// m_actor.c
@ -2237,17 +2249,17 @@ new structure for the backup client data while its in the camera.
typedef struct
{
vec3_t oldorigin; //clients world origin
vec3_t moveorigin; //for client prediction, don't think this is needed as its only an sp modification
vec3_t viewangles; //which way the client is facing
vec3_t oldorigin; // clients world origin
vec3_t moveorigin; // for client prediction, don't think this is needed as its only an sp modification
vec3_t viewangles; // which way the client is facing
int pm_type; //player movetype I believe. (noclip, fly, etc)
int gunindex; //gun model
int pm_type; // player movetype I believe. (noclip, fly, etc)
int gunindex; // gun model
vec3_t blend; //screen blend value (for bleeding, etc)
int rdflags; //render flags for the clent
vec3_t blend; // screen blend value (for bleeding, etc)
int rdflags; // render flags for the clent
//how long left before something happens/runs out
// how long left before something happens/runs out
int quad_framenum;
int invincible_framenum;
int breather_framenum;
@ -2255,15 +2267,15 @@ typedef struct
int grenade_blew_up;
int grenade_time;
int viewheight; //viewheight from the origin
int viewheight; // viewheight from the origin
//various model files the player can be displayed as.
// various model files the player can be displayed as.
int modelindex;
int modelindex2;
int modelindex3;
unsigned int effects; //what effect are we (needs to be unsigned because theres a few
unsigned int effects; // what effect are we (needs to be unsigned because theres a few
int sound;
solid_t solid; //current solid state, 90% certain its SOLID_PLAYER ;)
solid_t solid; // current solid state, 90% certain its SOLID_PLAYER ;)
} backup_t;

View file

@ -298,7 +298,7 @@ void modelspawn_think (edict_t *self)
void model_spawn_use (edict_t *self, edict_t *other, edict_t *activator)
{
if (self->delay) //we started off
if (self->delay) // we started off
{
self->svflags &= ~SVF_NOCLIENT;
self->delay = 0;
@ -312,7 +312,7 @@ void model_spawn_use (edict_t *self, edict_t *other, edict_t *activator)
self->s.attenuation = self->attenuation;
#endif
}
else //we started active
else // we started active
{
self->svflags |= SVF_NOCLIENT;
self->delay = 1;

View file

@ -200,7 +200,7 @@ void gib_die (edict_t *self, edict_t *inflictor, edict_t *attacker, int damage,
G_FreeEdict (self);
}
void ThrowGib (edict_t *self, char *gibname, int damage, int type)
void ThrowGibFrame (edict_t *self, char *gibname, int frame, int damage, int type)
{
edict_t *gib;
vec3_t vd;
@ -248,8 +248,9 @@ void ThrowGib (edict_t *self, char *gibname, int damage, int type)
gib->s.origin[1] = origin[1] + crandom() * size[1];
gib->s.origin[2] = origin[2] + crandom() * size[2];
//gi.setmodel (gib, gibname);
// gi.setmodel (gib, gibname);
gib->s.modelindex = gi.modelindex (gibname);
gib->s.frame = frame; // Knightmare added
gib->clipmask = MASK_SHOT;
VectorSet (gib->mins, -4, -4, -4);
VectorSet (gib->maxs, 4, 4, 4);
@ -288,14 +289,20 @@ void ThrowGib (edict_t *self, char *gibname, int damage, int type)
gib->movetype = MOVETYPE_BOUNCE; // was MOVETYPE_TOSS
gib->touch = gib_touch;
if (self->blood_type == 1)
vscale = 3.0;
vscale = 3.0f;
else
vscale = 1.0;
vscale = 1.0f;
}
else if (type == GIB_FEATHER) // Knightmare- added for vulture
{
gib->movetype = MOVETYPE_FEATHER;
gib->touch = gib_touch;
vscale = 2.0f;
}
else
{
gib->movetype = MOVETYPE_BOUNCE;
vscale = 1.0;
vscale = 1.0f;
}
VelocityForDamage (damage, vd);
@ -316,6 +323,11 @@ void ThrowGib (edict_t *self, char *gibname, int damage, int type)
gi.linkentity (gib);
}
void ThrowGib (edict_t *self, char *gibname, int damage, int type)
{
ThrowGibFrame (self, gibname, 0, damage, type);
}
// NOTE: SP_gib is ONLY intended to be used for gibs that change maps
// via trigger_transition. It should NOT be used for map entities.
@ -434,7 +446,7 @@ void ThrowHead (edict_t *self, char *gibname, int damage, int type)
if (type == GIB_ORGANIC)
{
self->movetype = MOVETYPE_BOUNCE; //was MOVETYPE_TOSS
self->movetype = MOVETYPE_BOUNCE; // was MOVETYPE_TOSS
self->touch = gib_touch;
if (self->blood_type == 1)
vscale = 3.0;
@ -555,7 +567,7 @@ void debris_die (edict_t *self, edict_t *inflictor, edict_t *attacker, int damag
G_FreeEdict (self);
}
void ThrowDebris (edict_t *self, char *modelname, float speed, vec3_t origin, int skin, int effects)
void ThrowDebrisFrame (edict_t *self, char *modelname, float speed, vec3_t origin, int frame, int skin, int effects)
{
edict_t *chunk;
vec3_t v;
@ -599,7 +611,8 @@ void ThrowDebris (edict_t *self, char *modelname, float speed, vec3_t origin, in
chunk->avelocity[2] = random()*600;
chunk->think = gib_fade; // Knightmare- gib fade, was G_FreeEdict
chunk->nextthink = level.time + 8 + random()*10;
chunk->s.frame = 0;
// chunk->s.frame = 0;
chunk->s.frame = frame; // Knightmare added
chunk->flags = 0;
chunk->classname = "debris";
chunk->svflags |= SVF_GIB; // Knightmare- gib flag
@ -615,6 +628,11 @@ void ThrowDebris (edict_t *self, char *modelname, float speed, vec3_t origin, in
gi.linkentity (chunk);
}
void ThrowDebris (edict_t *self, char *modelname, float speed, vec3_t origin, int skin, int effects)
{
ThrowDebrisFrame (self, modelname, speed, origin, 0, skin, effects);
}
// NOTE: SP_debris is ONLY intended to be used for debris chunks that change maps
// via trigger_transition. It should NOT be used for map entities.
@ -4975,7 +4993,7 @@ void spawn_precipitation(edict_t *self, vec3_t org, vec3_t dir, float speed)
drop->s.modelindex = gi.modelindex ("models/objects/drop/tris.md2");
drop->classname = "rain drop";
}
if (self->gravity > 0. || self->attenuation > 0 )
if (self->gravity > 0.0f || self->attenuation > 0 )
drop->movetype = MOVETYPE_DEBRIS;
else
drop->movetype = MOVETYPE_RAIN;
@ -4983,19 +5001,19 @@ void spawn_precipitation(edict_t *self, vec3_t org, vec3_t dir, float speed)
drop->touch = drop_touch;
if (self->style == STYLE_WEATHER_USER)
drop->clipmask = MASK_MONSTERSOLID;
else if ((self->fadeout > 0) && (self->gravity == 0.))
else if ((self->fadeout > 0) && (self->gravity == 0.0f))
drop->clipmask = MASK_SOLID | CONTENTS_WATER;
else
drop->clipmask = MASK_MONSTERSOLID | CONTENTS_WATER;
drop->solid = SOLID_BBOX;
drop->svflags = SVF_DEADMONSTER;
VectorSet(drop->mins,-1,-1,-1);
VectorSet(drop->mins, -1, -1, -1);
VectorSet(drop->maxs, 1, 1, 1);
if (self->spawnflags & SF_WEATHER_GRAVITY_BOUNCE)
drop->gravity = self->gravity;
else
drop->gravity = 0.;
drop->gravity = 0.0f;
drop->attenuation = self->attenuation;
drop->mass = self->mass;
drop->spawnflags = self->spawnflags;
@ -5182,12 +5200,12 @@ void SP_target_precipitation (edict_t *ent)
if (st.gravity)
ent->gravity = atof(st.gravity);
else
ent->gravity = 0.;
ent->gravity = 0.0f;
}
else
{
ent->gravity = 0.;
ent->attenuation = 0.;
ent->gravity = 0.0f;
ent->attenuation = 0.0f;
}
// If not rain or "user", turn off splash. Yeah I know goofy mapper
@ -5397,7 +5415,7 @@ void SP_target_fountain (edict_t *ent)
if (st.gravity)
ent->gravity = atof(st.gravity);
else
ent->gravity = 0.;
ent->gravity = 0.0f;
ent->use = target_fountain_use;

View file

@ -216,7 +216,7 @@ void SP_misc_q1_globe(edict_t *self)
void q1_small_flame_think (edict_t *self)
{
if(self->s.frame >= 5)
if (self->s.frame >= 5)
self->s.frame = 0;
else
self->s.frame++;
@ -285,7 +285,7 @@ void SP_misc_q1_large_flame (edict_t *ent)
void q1_torch_think (edict_t *self)
{
if(self->s.frame >= 5)
if (self->s.frame >= 5)
self->s.frame = 0;
else
self->s.frame++;
@ -354,7 +354,7 @@ void SP_target_q1_trap (edict_t *self)
if (self->spawnflags & 2)
{
self->noise_index = gi.soundindex ("q1enforcer/enfire.wav");
gi.soundindex("q1enforcer/enfstop.wav");
q1_laser_precache ();
if (!self->speed)
self->speed = 600;
}
@ -365,11 +365,12 @@ void SP_target_q1_trap (edict_t *self)
self->noise_index = gi.soundindex ("q1weapons/spike.wav");
gi.soundindex("q1weapons/s_end.wav");
#endif
q1_nail_precache ();
if (!self->speed)
self->speed = 500;
}
if (self->spawnflags & 1 || self->spawnflags & 2) {
if ( (self->spawnflags & 1) || (self->spawnflags & 2) ) {
if (!self->dmg)
self->dmg = 15;
}

View file

@ -92,6 +92,17 @@ extern mmove_t widow_move_attack_blaster ;
extern mmove_t widow_move_attack_post_blaster_l ;
extern mmove_t widow_move_attack_post_blaster_r ;
extern mmove_t widow_move_attack_post_blaster ;
extern mmove_t vulture_move_soardeath ;
extern mmove_t vulture_move_death ;
extern mmove_t vulture_move_soarpain ;
extern mmove_t vulture_move_pain ;
extern mmove_t vulture_move_melee ;
extern mmove_t vulture_move_land ;
extern mmove_t vulture_move_takeoff ;
extern mmove_t vulture_move_fly ;
extern mmove_t vulture_move_soar ;
extern mmove_t vulture_move_walk ;
extern mmove_t vulture_move_perch ;
extern mmove_t turret_move_run ;
extern mmove_t turret_move_seek ;
extern mmove_t turret_move_ready_gun ;
@ -283,6 +294,19 @@ extern mmove_t q1grunt_move_pain1 ;
extern mmove_t q1grunt_move_run ;
extern mmove_t q1grunt_move_walk ;
extern mmove_t q1grunt_move_stand ;
extern mmove_t freddie_move_death ;
extern mmove_t freddie_move_fswinge ;
extern mmove_t freddie_move_bswing ;
extern mmove_t freddie_move_fswing ;
extern mmove_t freddie_move_sfire_stop ;
extern mmove_t freddie_move_sfire ;
extern mmove_t freddie_move_sfire_start ;
extern mmove_t freddie_move_pain2 ;
extern mmove_t freddie_move_pain1 ;
extern mmove_t freddie_move_rfire ;
extern mmove_t freddie_move_run ;
extern mmove_t freddie_move_walk ;
extern mmove_t freddie_move_stand ;
extern mmove_t fiend_move_death ;
extern mmove_t fiend_move_pain ;
extern mmove_t fiend_move_jump ;

View file

@ -92,6 +92,17 @@
{"widow_move_attack_post_blaster_l", &widow_move_attack_post_blaster_l},
{"widow_move_attack_post_blaster_r", &widow_move_attack_post_blaster_r},
{"widow_move_attack_post_blaster", &widow_move_attack_post_blaster},
{"vulture_move_soardeath", &vulture_move_soardeath},
{"vulture_move_death", &vulture_move_death},
{"vulture_move_soarpain", &vulture_move_soarpain},
{"vulture_move_pain", &vulture_move_pain},
{"vulture_move_melee", &vulture_move_melee},
{"vulture_move_land", &vulture_move_land},
{"vulture_move_takeoff", &vulture_move_takeoff},
{"vulture_move_fly", &vulture_move_fly},
{"vulture_move_soar", &vulture_move_soar},
{"vulture_move_walk", &vulture_move_walk},
{"vulture_move_perch", &vulture_move_perch},
{"turret_move_run", &turret_move_run},
{"turret_move_seek", &turret_move_seek},
{"turret_move_ready_gun", &turret_move_ready_gun},
@ -283,6 +294,19 @@
{"q1grunt_move_run", &q1grunt_move_run},
{"q1grunt_move_walk", &q1grunt_move_walk},
{"q1grunt_move_stand", &q1grunt_move_stand},
{"freddie_move_death", &freddie_move_death},
{"freddie_move_fswinge", &freddie_move_fswinge},
{"freddie_move_bswing", &freddie_move_bswing},
{"freddie_move_fswing", &freddie_move_fswing},
{"freddie_move_sfire_stop", &freddie_move_sfire_stop},
{"freddie_move_sfire", &freddie_move_sfire},
{"freddie_move_sfire_start", &freddie_move_sfire_start},
{"freddie_move_pain2", &freddie_move_pain2},
{"freddie_move_pain1", &freddie_move_pain1},
{"freddie_move_rfire", &freddie_move_rfire},
{"freddie_move_run", &freddie_move_run},
{"freddie_move_walk", &freddie_move_walk},
{"freddie_move_stand", &freddie_move_stand},
{"fiend_move_death", &fiend_move_death},
{"fiend_move_pain", &fiend_move_pain},
{"fiend_move_jump", &fiend_move_jump},

View file

@ -319,7 +319,7 @@ void dabeam_hit (edict_t *self)
VectorCopy (self->s.origin, start);
VectorMA (start, 2048, self->movedir, end);
while(1)
while (1)
{ //Knightmare- double trace here, needed to make sure clipping works- must be compiler weirdness
tr = gi.trace (start, NULL, NULL, end, ignore, (CONTENTS_SOLID|CONTENTS_MONSTER|CONTENTS_DEADMONSTER));
tr = gi.trace (start, NULL, NULL, end, ignore, (CONTENTS_SOLID|CONTENTS_MONSTER|CONTENTS_DEADMONSTER));
@ -1323,7 +1323,7 @@ void monster_start_go (edict_t *self)
// Lazarus: move_origin for func_monitor
if (!VectorLength(self->move_origin))
VectorSet(self->move_origin,0,0,self->viewheight);
VectorSet(self->move_origin, 0, 0, self->viewheight);
// check for target to combat_point and change to combattarget
if (self->target)
@ -1426,6 +1426,9 @@ void walkmonster_start_go (edict_t *self)
// PMM - stalkers are too short for this
if (!(strcmp(self->classname, "monster_stalker")))
self->viewheight = 15;
// Knightmare- vultures also too short
else if (!(strcmp(self->classname, "monster_vulture")))
self->viewheight = 8;
else
self->viewheight = 25;
@ -1449,7 +1452,11 @@ void flymonster_start_go (edict_t *self)
if (!self->yaw_speed)
self->yaw_speed = 10;
self->viewheight = 25;
// Knightmare- vultures too short for this
if (!(strcmp(self->classname, "monster_vulture")))
self->viewheight = 8;
else
self->viewheight = 25;
monster_start_go (self);
@ -1636,6 +1643,7 @@ int PatchMonsterModel (char *modelname)
qboolean is_hover = false;
qboolean is_medic = false;
qboolean is_turret = false;
qboolean is_vulture = false;
qboolean is_zboss_mech = false;
qboolean is_zboss_pilot = false;
@ -1660,71 +1668,76 @@ int PatchMonsterModel (char *modelname)
numskins = 8;
// special cases
if (!strcmp(modelname,"models/monsters/tank/tris.md2"))
if (!strcmp(modelname, "models/monsters/tank/tris.md2"))
{
is_tank = true;
numskins = 16;
}
else if (!strcmp(modelname,"models/monsters/soldier/tris.md2"))
else if (!strcmp(modelname, "models/monsters/soldier/tris.md2"))
{
is_soldier = true;
numskins = 32; // was 24
}
// Knightmare added
#ifdef CITADELMOD_FEATURES
else if (!strcmp(modelname,"models/monsters/brain/tris.md2"))
else if (!strcmp(modelname, "models/monsters/brain/tris.md2"))
{
is_brain = true;
numskins = 16;
}
#endif
else if (!strcmp(modelname,"models/monsters/gekk/tris.md2"))
else if (!strcmp(modelname, "models/monsters/gekk/tris.md2"))
{
is_gekk = true;
numskins = 12;
}
else if (!strcmp(modelname,"models/monsters/fixbot/tris.md2"))
else if (!strcmp(modelname, "models/monsters/fixbot/tris.md2"))
{
is_fixbot = true;
numskins = 4;
}
else if (!strcmp(modelname,"models/monsters/bitch/tris.md2")
|| !strcmp(modelname,"models/monsters/bitch2/tris.md2"))
else if (!strcmp(modelname, "models/monsters/bitch/tris.md2")
|| !strcmp(modelname, "models/monsters/bitch2/tris.md2"))
{
is_chick = true;
numskins = 16;
}
else if (!strcmp(modelname,"models/monsters/soldierh/tris.md2"))
else if (!strcmp(modelname, "models/monsters/soldierh/tris.md2"))
{
is_soldierh = true;
numskins = 24;
}
else if (!strcmp(modelname,"models/monsters/carrier/tris.md2"))
else if (!strcmp(modelname, "models/monsters/carrier/tris.md2"))
{
is_carrier = true;
numskins = 8;
}
else if (!strcmp(modelname,"models/monsters/hover/tris.md2"))
else if (!strcmp(modelname, "models/monsters/hover/tris.md2"))
{
is_hover = true;
numskins = 16;
}
else if (!strcmp(modelname,"models/monsters/medic/tris.md2"))
else if (!strcmp(modelname, "models/monsters/medic/tris.md2"))
{
is_medic = true;
numskins = 16;
}
else if (!strcmp(modelname,"models/monsters/turret/tris.md2"))
else if (!strcmp(modelname, "models/monsters/turret/tris.md2"))
{
is_turret = true;
numskins = 12;
}
else if (!strcmp(modelname,"models/monsters/bossz/mech/tris.md2"))
else if (!strcmp(modelname, "models/monsters/vulture/tris.md2"))
{
is_vulture = true;
numskins = 4;
}
else if (!strcmp(modelname, "models/monsters/bossz/mech/tris.md2"))
{
is_zboss_mech = true;
numskins = 12;
}
else if (!strcmp(modelname,"models/monsters/bossz/pilot/tris.md2"))
else if (!strcmp(modelname, "models/monsters/bossz/pilot/tris.md2"))
{
is_zboss_pilot = true;
numskins = 12;
@ -2119,6 +2132,20 @@ int PatchMonsterModel (char *modelname)
Com_strcat (skins[j], sizeof(skins[j]), "custom3_3.pcx"); break;
}
}
else if (is_vulture)
{
switch (j)
{
case 0:
Com_strcat (skins[j], sizeof(skins[j]), "vulture.pcx"); break;
case 1:
Com_strcat (skins[j], sizeof(skins[j]), "custom1.pcx"); break;
case 2:
Com_strcat (skins[j], sizeof(skins[j]), "custom2.pcx"); break;
case 3:
Com_strcat (skins[j], sizeof(skins[j]), "custom3.pcx"); break;
}
}
else if (is_zboss_mech || is_zboss_pilot)
{
switch (j)

View file

@ -718,10 +718,24 @@ void SV_AddGravity (edict_t *ent)
ent->velocity);
}
else if (level.time > ent->gravity_debounce_time)
ent->velocity[2] -= ent->gravity * sv_gravity->value * FRAMETIME;
{
// Knightmare- MOVETYPE_FEATHER specifies slow falling
if ( (ent->movetype == MOVETYPE_FEATHER) && (ent->velocity[2] < 0.0f) ) {
ent->velocity[2] -= ent->gravity * sv_gravity->value * FRAMETIME * 0.001f;
}
else
ent->velocity[2] -= ent->gravity * sv_gravity->value * FRAMETIME;
}
#else
if (level.time > ent->gravity_debounce_time)
ent->velocity[2] -= ent->gravity * sv_gravity->value * FRAMETIME;
{
// Knightmare- MOVETYPE_FEATHER specifies slow falling
if ( (ent->movetype == MOVETYPE_FEATHER) && (ent->velocity[2] < 0.0f) ) {
ent->velocity[2] -= ent->gravity * sv_gravity->value * FRAMETIME * 0.001f;
}
else
ent->velocity[2] -= ent->gravity * sv_gravity->value * FRAMETIME;
}
#endif
}
@ -744,6 +758,7 @@ called for MOVETYPE_TOSS
MOVETYPE_FLY
MOVETYPE_FLYMISSILE
MOVETYPE_RAIN
MOVETYPE_FEATHER
=================================================
*/
trace_t SV_PushEntity (edict_t *ent, vec3_t push)
@ -2798,7 +2813,7 @@ void SV_Physics_FallFloat (edict_t *ent)
SV_CheckVelocity (ent);
wasonground = (ent->groundentity == NULL);
if (ent->velocity[2] < sv_gravity->value*-0.1)
if (ent->velocity[2] < (sv_gravity->value * -0.1f))
hitsound = true;
if (!ent->waterlevel)
@ -2835,8 +2850,7 @@ void SV_Physics_FallFloat (edict_t *ent)
ent->groundentity = NULL;
}
}
else
//if (ent->waterlevel)
else // if (ent->waterlevel)
{
// where's the midpoint? above or below the water?
const double WATER_MASS = 500.0;
@ -3001,6 +3015,7 @@ void G_RunEntity (edict_t *ent)
// RAFAEL
case MOVETYPE_WALLBOUNCE:
case MOVETYPE_RAIN:
case MOVETYPE_FEATHER: // Knightmare added
SV_Physics_Toss (ent);
break;
case MOVETYPE_NEWTOSS:

View file

@ -198,6 +198,8 @@ void SP_misc_seat(edict_t *self);
// Knightmare- the dog from Coconut Monkey 3
void SP_monster_dog (edict_t *self);
// Knightmare- the vulture from Coconut Monkey 2
void SP_monster_vulture (edict_t *self);
void SP_rotating_light (edict_t *self);
void SP_object_repair (edict_t *self);
@ -332,6 +334,7 @@ void SP_monster_q1_shalrath (edict_t *self);
void SP_monster_q1_shambler (edict_t *self);
void SP_monster_q1_tarbaby (edict_t *self);
void SP_monster_q1_zombie (edict_t *self);
void SP_monster_q1_freddie (edict_t *self);
void SP_misc_q1_zombie_crucified (edict_t *self);
void SP_misc_q1_air_bubbles (edict_t *self);
@ -585,6 +588,8 @@ spawn_t spawns[] = {
// Knightmare- the dog from Coconut Monkey 3
{"monster_dog", SP_monster_dog},
// Knightmare- the vulture from Coconut Monkey 2
{"monster_vulture", SP_monster_vulture},
{"misc_nuke", SP_misc_nuke},
@ -706,6 +711,7 @@ spawn_t spawns[] = {
{"q1_monster_shalrath", SP_monster_q1_shalrath},
{"q1_monster_tarbaby", SP_monster_q1_tarbaby},
{"q1_monster_zombie", SP_monster_q1_zombie},
{"q1_monster_freddie", SP_monster_q1_freddie},
// Q2Infighter spawn names
// {"monster_q1_chthon", SP_monster_q1_chthon},
@ -722,6 +728,7 @@ spawn_t spawns[] = {
{"monster_q1_shalrath", SP_monster_q1_shalrath},
{"monster_q1_tarbaby", SP_monster_q1_tarbaby},
{"monster_q1_zombie", SP_monster_q1_zombie},
{"monster_q1_freddie", SP_monster_q1_freddie},
// misc Q1 entities
{"misc_q1_zombie_crucified", SP_misc_q1_zombie_crucified},

View file

@ -3,7 +3,7 @@
qboolean has_valid_enemy (edict_t *self);
void HuntTarget (edict_t *self);
edict_t *SpawnThing()
edict_t *SpawnThing (void)
{
edict_t *thing;
thing = G_Spawn();
@ -16,14 +16,14 @@ void thing_restore_leader (edict_t *self)
{
edict_t *monster;
monster = self->target_ent;
if(!monster || !monster->inuse)
if (!monster || !monster->inuse)
{
G_FreeEdict(self);
return;
}
if(monster->monsterinfo.old_leader && monster->monsterinfo.old_leader->inuse)
if (monster->monsterinfo.old_leader && monster->monsterinfo.old_leader->inuse)
{
if(VectorCompare(monster->monsterinfo.old_leader->s.origin,self->move_origin))
if (VectorCompare(monster->monsterinfo.old_leader->s.origin,self->move_origin))
{
self->nextthink = level.time + 0.5;
return;
@ -48,18 +48,18 @@ void thing_think (edict_t *self)
edict_t *monster;
monster = self->target_ent;
if(level.time <= self->touch_debounce_time)
if (level.time <= self->touch_debounce_time)
{
if(monster && monster->inuse)
if (monster && monster->inuse)
{
if(monster->movetarget == self)
if (monster->movetarget == self)
{
if(monster->health > 0)
if (monster->health > 0)
{
VectorSubtract(monster->s.origin,self->s.origin,vec);
vec[2] = 0;
dist = VectorLength(vec);
if(dist >= monster->size[0])
if (dist >= monster->size[0])
{
self->nextthink = level.time + FRAMETIME;
return;
@ -68,19 +68,19 @@ void thing_think (edict_t *self)
}
}
}
if(!monster || !monster->inuse || (monster->health <= 0))
if (!monster || !monster->inuse || (monster->health <= 0))
{
G_FreeEdict(self);
return;
}
if(monster->goalentity == self)
if (monster->goalentity == self)
monster->goalentity = NULL;
if(monster->movetarget == self)
if (monster->movetarget == self)
monster->movetarget = NULL;
if(monster->monsterinfo.aiflags & AI_FOLLOW_LEADER)
if (monster->monsterinfo.aiflags & AI_FOLLOW_LEADER)
{
monster->monsterinfo.leader = NULL;
if(monster->monsterinfo.old_leader && monster->monsterinfo.old_leader->inuse)
if (monster->monsterinfo.old_leader && monster->monsterinfo.old_leader->inuse)
{
monster->monsterinfo.pausetime = level.time + 2;
monster->monsterinfo.stand(monster);
@ -95,7 +95,7 @@ void thing_think (edict_t *self)
monster->monsterinfo.aiflags &= ~AI_FOLLOW_LEADER;
}
}
if(monster->monsterinfo.aiflags & AI_CHICKEN)
if (monster->monsterinfo.aiflags & AI_CHICKEN)
{
monster->monsterinfo.stand(monster);
monster->monsterinfo.aiflags |= AI_STAND_GROUND;
@ -124,26 +124,26 @@ void thing_think (edict_t *self)
monster->monsterinfo.stand (monster); // crashes here
}
void thing_think_pause(edict_t *self)
void thing_think_pause (edict_t *self)
{
edict_t *monster;
if(level.time > self->touch_debounce_time)
if (level.time > self->touch_debounce_time)
{
thing_think(self);
return;
}
monster = self->target_ent;
if(!monster || !monster->inuse)
if (!monster || !monster->inuse)
{
G_FreeEdict(self);
return;
}
if(has_valid_enemy(monster))
if (has_valid_enemy(monster))
{
vec3_t dir;
vec3_t angles;
if(visible(monster->enemy,monster))
if (visible(monster->enemy,monster))
{
self->touch_debounce_time = 0;
thing_think(self);
@ -164,25 +164,25 @@ void thing_grenade_boom (edict_t *self)
monster = self->target_ent;
G_FreeEdict(self);
if(!monster || !monster->inuse || (monster->health <= 0))
if (!monster || !monster->inuse || (monster->health <= 0))
return;
monster->monsterinfo.aiflags &= ~(AI_CHASE_THING | AI_EVADE_GRENADE | AI_STAND_GROUND);
monster->monsterinfo.pausetime = 0;
if(monster->enemy)
if (monster->enemy)
monster->monsterinfo.run(monster);
}
void thing_touch (edict_t *self, edict_t *other, cplane_t *plane, csurface_t *surf)
{
if(self->target_ent != other)
if (self->target_ent != other)
return;
if(other->health <= 0)
if (other->health <= 0)
{
G_FreeEdict(self);
return;
}
self->touch = NULL;
if( self->target_ent->monsterinfo.aiflags & AI_SEEK_COVER )
if ( self->target_ent->monsterinfo.aiflags & AI_SEEK_COVER )
{
edict_t *monster;
// For monster/actor seeking cover after firing,
@ -195,29 +195,29 @@ void thing_touch (edict_t *self, edict_t *other, cplane_t *plane, csurface_t *su
self->think(self);
return;
}
if( self->target_ent->monsterinfo.aiflags & AI_EVADE_GRENADE )
if ( self->target_ent->monsterinfo.aiflags & AI_EVADE_GRENADE )
{
edict_t *grenade = other->next_grenade;
if(other->goalentity == self)
if (other->goalentity == self)
other->goalentity = NULL;
if(other->movetarget == self)
if (other->movetarget == self)
other->movetarget = NULL;
other->vehicle = NULL;
if(grenade)
if (grenade)
{
// make sure this is still a grenade
if(grenade->inuse)
if (grenade->inuse)
{
if(Q_stricmp(grenade->classname,"grenade") && Q_stricmp(grenade->classname,"hgrenade"))
if (Q_stricmp(grenade->classname,"grenade") && Q_stricmp(grenade->classname,"hgrenade"))
other->next_grenade = grenade = NULL;
}
else
other->next_grenade = grenade = NULL;
}
if(grenade)
if (grenade)
{
if(self->touch_debounce_time > level.time)
if (self->touch_debounce_time > level.time)
{
other->monsterinfo.pausetime = self->touch_debounce_time + 0.1;
other->monsterinfo.aiflags |= AI_STAND_GROUND;
@ -240,7 +240,7 @@ void thing_touch (edict_t *self, edict_t *other, cplane_t *plane, csurface_t *su
other->enemy = NULL;
other->monsterinfo.stand (other);
}
if(other->monsterinfo.pausetime > 0)
if (other->monsterinfo.pausetime > 0)
{
self->think = thing_grenade_boom;
self->nextthink = other->monsterinfo.pausetime;
@ -281,7 +281,7 @@ void SP_thing (edict_t *self)
self->svflags |= SVF_MONSTER;
self->health = 1000;
self->takedamage = DAMAGE_NO;
if(developer->value) {
if (developer->value) {
gi.setmodel (self, "models/items/c_head/tris.md2");
self->s.effects |= EF_BLASTER;
}

View file

@ -1601,6 +1601,7 @@ qboolean UseSpecialGoodGuyFlag (edict_t *monster)
if ( !strcmp(monster->classname, "monster_gekk")
|| !strcmp(monster->classname, "monster_stalker")
|| !strcmp(monster->classname, "monster_vulture")
|| !strcmp(monster->classname, "monster_handler") )
return true;
@ -1625,6 +1626,7 @@ qboolean UseRegularGoodGuyFlag (edict_t *monster)
if ( strcmp(monster->classname, "monster_gekk")
&& strcmp(monster->classname, "monster_stalker")
&& strcmp(monster->classname, "monster_vulture")
&& strcmp(monster->classname, "monster_turret")
&& strcmp(monster->classname, "monster_fixbot")
&& strcmp(monster->classname, "monster_handler")

View file

@ -903,6 +903,175 @@ void SP_handgrenade (edict_t *grenade)
}
//==========================================================================================
//
// AimGrenade finds the correct aim vector to get a grenade from start to target at initial
// velocity = speed. Returns false if grenade can't make it to target.
//
//==========================================================================================
qboolean AimGrenade (edict_t *self, vec3_t start, vec3_t target, vec_t speed, vec3_t aim)
{
vec3_t angles, forward, right, up;
vec3_t from_origin, from_muzzle;
vec3_t aim_point;
vec_t xo, yo;
vec_t x;
float cosa, t, vx, y;
float drop;
float last_error, v_error;
int i;
vec3_t last_aim;
VectorCopy(target,aim_point);
VectorSubtract(aim_point,self->s.origin,from_origin);
VectorSubtract(aim_point, start, from_muzzle);
if(self->svflags & SVF_MONSTER)
{
VectorCopy(from_muzzle,aim);
VectorNormalize(aim);
yo = from_muzzle[2];
xo = sqrt(from_muzzle[0]*from_muzzle[0] + from_muzzle[1]*from_muzzle[1]);
}
else
{
VectorCopy(from_origin,aim);
VectorNormalize(aim);
yo = from_origin[2];
xo = sqrt(from_origin[0]*from_origin[0] + from_origin[1]*from_origin[1]);
}
// If resulting aim vector is looking straight up or straight down, we're
// done. Actually now that I write this down and think about it... should
// probably check straight up to make sure grenade will actually reach the
// target.
if( (aim[2] == 1.0) || (aim[2] == -1.0))
return true;
// horizontal distance to target from muzzle
x = sqrt( from_muzzle[0]*from_muzzle[0] + from_muzzle[1]*from_muzzle[1]);
cosa = sqrt(aim[0]*aim[0] + aim[1]*aim[1]);
// constant horizontal velocity (since grenades don't have drag)
vx = speed * cosa;
// time to reach target x
t = x/vx;
// if flight time is less than one frame, no way grenade will drop much,
// shoot the sucker now.
if(t < FRAMETIME)
return true;
// in that time, grenade will drop this much:
drop = 0.5*sv_gravity->value*t*t;
y = speed*aim[2]*t - drop;
v_error = target[2] - start[2] - y;
// if we're fairly close and we'll hit target at current angle,
// no need for all this, just shoot it
if( (x < 128) && (fabs(v_error) < 16) )
return true;
last_error = 100000.;
VectorCopy(aim,last_aim);
// Unfortunately there is no closed-form solution for this problem,
// so we creep up on an answer and balk if it takes more than
// 10 iterations to converge to the tolerance we'll accept.
for(i=0; i<10 && fabs(v_error) > 4 && fabs(v_error) < fabs(last_error); i++)
{
last_error = v_error;
aim[2] = cosa * (yo + drop)/xo;
VectorNormalize(aim);
if(!(self->svflags & SVF_MONSTER))
{
vectoangles(aim,angles);
AngleVectors(angles, forward, right, up);
G_ProjectSource2(self->s.origin,self->move_origin,forward,right,up,start);
VectorSubtract(aim_point,start,from_muzzle);
x = sqrt(from_muzzle[0]*from_muzzle[0] + from_muzzle[1]*from_muzzle[1]);
}
cosa = sqrt(aim[0]*aim[0] + aim[1]*aim[1]);
vx = speed * cosa;
t = x/vx;
drop = 0.5*sv_gravity->value*t*t;
y = speed*aim[2]*t - drop;
v_error = target[2] - start[2] - y;
if(fabs(v_error) < fabs(last_error))
VectorCopy(aim,last_aim);
}
if(i >= 10 || v_error > 64)
return false;
if(fabs(v_error) > fabs(last_error))
{
VectorCopy(last_aim,aim);
if(!(self->svflags & SVF_MONSTER))
{
vectoangles(aim,angles);
AngleVectors(angles, forward, right, up);
G_ProjectSource2(self->s.origin,self->move_origin,forward,right,up,start);
VectorSubtract(aim_point,start,from_muzzle);
}
}
// Sanity check... if launcher is at the same elevation or a bit above the
// target entity, check to make sure he won't bounce grenades off the
// top of a doorway or other obstruction. If he WOULD do that, then figure out
// the max elevation angle that will get the grenade through the door, and
// hope we get a good bounce.
if( (start[2] - target[2] < 160) &&
(start[2] - target[2] > -16) )
{
trace_t tr;
vec3_t dist;
tr = gi.trace(start,vec3_origin,vec3_origin,aim_point,self,MASK_SOLID);
if( (tr.fraction < 1.0) && (!self->enemy || (tr.ent != self->enemy) )) {
// OK... the aim vector hit a solid, but would the grenade actually hit?
int contents;
cosa = sqrt(aim[0]*aim[0] + aim[1]*aim[1]);
vx = speed * cosa;
VectorSubtract(tr.endpos,start,dist);
dist[2] = 0;
x = VectorLength(dist);
t = x/vx;
drop = 0.5*sv_gravity->value*t*(t+FRAMETIME);
tr.endpos[2] -= drop;
// move just a bit in the aim direction
tr.endpos[0] += aim[0];
tr.endpos[1] += aim[1];
contents = gi.pointcontents(tr.endpos);
while((contents & MASK_SOLID) && (aim_point[2] > target[2])) {
aim_point[2] -= 8.0;
VectorSubtract(aim_point,self->s.origin,from_origin);
VectorCopy(from_origin,aim);
VectorNormalize(aim);
if(!(self->svflags & SVF_MONSTER))
{
vectoangles(aim,angles);
AngleVectors(angles, forward, right, up);
G_ProjectSource2(self->s.origin,self->move_origin,forward,right,up,start);
VectorSubtract(aim_point,start,from_muzzle);
}
tr = gi.trace(start,vec3_origin,vec3_origin,aim_point,self,MASK_SOLID);
if(tr.fraction < 1.0) {
cosa = sqrt(aim[0]*aim[0] + aim[1]*aim[1]);
vx = speed * cosa;
VectorSubtract(tr.endpos,start,dist);
dist[2] = 0;
x = VectorLength(dist);
t = x/vx;
drop = 0.5*sv_gravity->value*t*(t+FRAMETIME);
tr.endpos[2] -= drop;
tr.endpos[0] += aim[0];
tr.endpos[1] += aim[1];
contents = gi.pointcontents(tr.endpos);
}
}
}
}
return true;
}
/*
=================
fire_missile

View file

@ -48,10 +48,10 @@ void q1_nail_touch (edict_t *self, edict_t *other, cplane_t *plane, csurface_t *
gi.WriteDir (plane->normal);
gi.multicast (self->s.origin, MULTICAST_PVS);
//not if online, too laggy
if(!deathmatch->value)
// not if online, too laggy
if (!deathmatch->value)
{
float sound= random();
float sound = random();
if (sound < 0.3)
{
if (sound < 0.1)
@ -116,6 +116,16 @@ void q1_fire_nail (edict_t *self, vec3_t start, vec3_t dir, int damage, int spee
}
void q1_nail_precache (void)
{
gi.modelindex ("models/objects/q1nail/tris.md2");
gi.soundindex ("q1weapons/tink1.wav");
gi.soundindex ("q1weapons/ric1.wav");
gi.soundindex ("q1weapons/ric2.wav");
gi.soundindex ("q1weapons/ric3.wav");
}
/*
=================
q1_fire_laser
@ -213,6 +223,12 @@ void q1_fire_laser (edict_t *self, vec3_t start, vec3_t dir, int damage, int spe
}
}
void q1_laser_precache (void)
{
gi.modelindex ("models/monsters/q1enforcer/laser/tris.md2");
gi.soundindex ("q1enforcer/enfstop.wav");
}
/*
=================
@ -272,6 +288,7 @@ void q1_flame_touch (edict_t *self, edict_t *other, cplane_t *plane, csurface_t
G_FreeEdict (self);
}
void q1_fire_flame (edict_t *self, vec3_t start, vec3_t dir, float leftrightoff)
{
edict_t *bolt;
@ -324,6 +341,13 @@ void q1_fire_flame (edict_t *self, vec3_t start, vec3_t dir, float leftrightoff)
}
void q1_flame_precache (void)
{
gi.modelindex ("models/monsters/q1hknight/k_spike/tris.md2");
gi.soundindex("q1hknight/hit.wav");
}
/*
=================
q1_fire_grenade
@ -449,6 +473,14 @@ void q1_fire_grenade (edict_t *self, vec3_t start, vec3_t aimdir, int damage, in
gi.linkentity (grenade);
}
void q1_grenade_precache (void)
{
gi.modelindex ("models/objects/grenade/tris.md2");
gi.modelindex ("sprites/s_explod.sp2");
gi.soundindex ("q1weapons/bounce.wav");
gi.soundindex ("q1weapons/r_exp3.wav");
}
/*
=================
@ -481,7 +513,7 @@ void q1_rocket_touch (edict_t *ent, edict_t *other, cplane_t *plane, csurface_t
T_Damage (other, ent, ent->owner, ent->velocity, ent->s.origin, plane->normal, ent->dmg, 0, 0, MOD_Q1_RL);
}
T_RadiusDamage(ent, ent->owner, ent->radius_dmg, other, ent->dmg_radius, MOD_Q1_RL_SPLASH);
gi.sound (ent,CHAN_AUTO , gi.soundindex ("q1weapons/r_exp3.wav"), 1.0, ATTN_NORM, 0);
gi.sound (ent, CHAN_AUTO, gi.soundindex ("q1weapons/r_exp3.wav"), 1.0, ATTN_NORM, 0);
gi.WriteByte (svc_temp_entity);
gi.WriteByte (TE_ROCKET_EXPLOSION);
@ -579,6 +611,15 @@ void q1_fire_rocket (edict_t *self, vec3_t start, vec3_t dir, int damage, int sp
}
void q1_rocket_precahce (void)
{
gi.modelindex ("models/objects/rocket/tris.md2");
gi.modelindex ("sprites/s_explod.sp2");
gi.soundindex ("weapons/rockfly.wav");
gi.soundindex ("q1weapons/r_exp3.wav");
}
/*
=================
q1_fire_lightning
@ -599,7 +640,7 @@ void q1_fire_lightning (edict_t *self, vec3_t start, vec3_t dir, int damage)
tr = gi.trace (self->s.origin, NULL, NULL, start, self, MASK_SHOT);
if (tr.fraction < 1.0)
{
if(tr.ent && (tr.ent !=self) && (tr.ent->takedamage))
if (tr.ent && (tr.ent !=self) && (tr.ent->takedamage))
T_Damage (tr.ent, self, self, dir, tr.endpos, tr.plane.normal, damage, 0, DAMAGE_ENERGY, MOD_Q1_LG);
return;
}
@ -656,7 +697,7 @@ void q1_firepod_touch (edict_t *self, edict_t *other, cplane_t *plane, csurface_
T_Damage (other, self, self->owner, vec3_origin, other->s.origin, vec3_origin, 200, 0, 0, 0);
T_RadiusDamage (self, self->owner, 40, NULL, 40, MOD_Q1_FIREPOD);
gi.sound (self,CHAN_AUTO , gi.soundindex ("q1weapons/r_exp3.wav"), 1.0, ATTN_NORM, 0);
gi.sound (self, CHAN_AUTO, gi.soundindex ("q1weapons/r_exp3.wav"), 1.0, ATTN_NORM, 0);
VectorMA (self->s.origin, -0.02, self->velocity, origin);
@ -673,7 +714,7 @@ void q1_firepod_touch (edict_t *self, edict_t *other, cplane_t *plane, csurface_
VectorCopy (origin, self->s.origin);
VectorCopy (origin, self->s.old_origin);
VectorClear (self->velocity);
self->s.modelindex = gi.modelindex ("sprites/s_explod.sp2");
self->s.modelindex = gi.modelindex ("sprites/s_explod.sp2");
self->s.frame = 0;
self->s.sound = 0;
self->s.effects &= ~EF_ANIM_ALLFAST;
@ -770,7 +811,16 @@ void q1_fire_firepod (edict_t *self, vec3_t dir)
VectorMA (pod->s.origin, -10, dir, pod->s.origin);
pod->touch (pod, tr.ent, NULL, NULL);
}
}
}
void q1_firepod_precache (void)
{
gi.modelindex ("models/monsters/q1shalrath/v_spike/tris.md2");
gi.modelindex ("sprites/s_explod.sp2");
gi.soundindex ("q1weapons/r_exp3.wav");
}
/*
=================
@ -861,6 +911,15 @@ void q1_fire_lavaball (edict_t *self, vec3_t start, vec3_t dir, int damage, int
gi.linkentity (lavaball);
}
void q1_fire_lavaball_precache (void)
{
gi.modelindex ("models/monsters/q1chthon/lavaball/tris.md2");
gi.modelindex ("sprites/s_explod.sp2");
gi.soundindex ("q1weapons/r_exp3.wav");
}
/*
=================
q1_acidbolt_touch
@ -943,6 +1002,14 @@ void q1_fire_acidspit (edict_t *self, vec3_t start, vec3_t dir, int damage, int
gi.linkentity (acidbolt);
}
void q1_acidspit_precache (void)
{
gi.modelindex ("models/monsters/q1scrag/w_spike/tris.md2");
gi.soundindex ("q1scrag/hit.wav");
}
/*
=================
q1_fire_gib
@ -1022,3 +1089,11 @@ void q1_fire_gib (edict_t *self, vec3_t start, vec3_t aimdir, int damage, int sp
gi.linkentity (gib);
}
void q1_gib_precache (void)
{
gi.modelindex ("models/monsters/q1zombie/gib/tris.md2");
gi.soundindex ("q1zombie/z_hit.wav");
gi.soundindex ("q1zombie/z_miss.wav");
}

View file

@ -1,169 +0,0 @@
#include "g_local.h"
//==========================================================================================
//
// AimGrenade finds the correct aim vector to get a grenade from start to target at initial
// velocity = speed. Returns false if grenade can't make it to target.
//
//==========================================================================================
qboolean AimGrenade (edict_t *self, vec3_t start, vec3_t target, vec_t speed, vec3_t aim)
{
vec3_t angles, forward, right, up;
vec3_t from_origin, from_muzzle;
vec3_t aim_point;
vec_t xo, yo;
vec_t x;
float cosa, t, vx, y;
float drop;
float last_error, v_error;
int i;
vec3_t last_aim;
VectorCopy(target,aim_point);
VectorSubtract(aim_point,self->s.origin,from_origin);
VectorSubtract(aim_point, start, from_muzzle);
if(self->svflags & SVF_MONSTER)
{
VectorCopy(from_muzzle,aim);
VectorNormalize(aim);
yo = from_muzzle[2];
xo = sqrt(from_muzzle[0]*from_muzzle[0] + from_muzzle[1]*from_muzzle[1]);
}
else
{
VectorCopy(from_origin,aim);
VectorNormalize(aim);
yo = from_origin[2];
xo = sqrt(from_origin[0]*from_origin[0] + from_origin[1]*from_origin[1]);
}
// If resulting aim vector is looking straight up or straight down, we're
// done. Actually now that I write this down and think about it... should
// probably check straight up to make sure grenade will actually reach the
// target.
if( (aim[2] == 1.0) || (aim[2] == -1.0))
return true;
// horizontal distance to target from muzzle
x = sqrt( from_muzzle[0]*from_muzzle[0] + from_muzzle[1]*from_muzzle[1]);
cosa = sqrt(aim[0]*aim[0] + aim[1]*aim[1]);
// constant horizontal velocity (since grenades don't have drag)
vx = speed * cosa;
// time to reach target x
t = x/vx;
// if flight time is less than one frame, no way grenade will drop much,
// shoot the sucker now.
if(t < FRAMETIME)
return true;
// in that time, grenade will drop this much:
drop = 0.5*sv_gravity->value*t*t;
y = speed*aim[2]*t - drop;
v_error = target[2] - start[2] - y;
// if we're fairly close and we'll hit target at current angle,
// no need for all this, just shoot it
if( (x < 128) && (fabs(v_error) < 16) )
return true;
last_error = 100000.;
VectorCopy(aim,last_aim);
// Unfortunately there is no closed-form solution for this problem,
// so we creep up on an answer and balk if it takes more than
// 10 iterations to converge to the tolerance we'll accept.
for(i=0; i<10 && fabs(v_error) > 4 && fabs(v_error) < fabs(last_error); i++)
{
last_error = v_error;
aim[2] = cosa * (yo + drop)/xo;
VectorNormalize(aim);
if(!(self->svflags & SVF_MONSTER))
{
vectoangles(aim,angles);
AngleVectors(angles, forward, right, up);
G_ProjectSource2(self->s.origin,self->move_origin,forward,right,up,start);
VectorSubtract(aim_point,start,from_muzzle);
x = sqrt(from_muzzle[0]*from_muzzle[0] + from_muzzle[1]*from_muzzle[1]);
}
cosa = sqrt(aim[0]*aim[0] + aim[1]*aim[1]);
vx = speed * cosa;
t = x/vx;
drop = 0.5*sv_gravity->value*t*t;
y = speed*aim[2]*t - drop;
v_error = target[2] - start[2] - y;
if(fabs(v_error) < fabs(last_error))
VectorCopy(aim,last_aim);
}
if(i >= 10 || v_error > 64)
return false;
if(fabs(v_error) > fabs(last_error))
{
VectorCopy(last_aim,aim);
if(!(self->svflags & SVF_MONSTER))
{
vectoangles(aim,angles);
AngleVectors(angles, forward, right, up);
G_ProjectSource2(self->s.origin,self->move_origin,forward,right,up,start);
VectorSubtract(aim_point,start,from_muzzle);
}
}
// Sanity check... if launcher is at the same elevation or a bit above the
// target entity, check to make sure he won't bounce grenades off the
// top of a doorway or other obstruction. If he WOULD do that, then figure out
// the max elevation angle that will get the grenade through the door, and
// hope we get a good bounce.
if( (start[2] - target[2] < 160) &&
(start[2] - target[2] > -16) )
{
trace_t tr;
vec3_t dist;
tr = gi.trace(start,vec3_origin,vec3_origin,aim_point,self,MASK_SOLID);
if( (tr.fraction < 1.0) && (!self->enemy || (tr.ent != self->enemy) )) {
// OK... the aim vector hit a solid, but would the grenade actually hit?
int contents;
cosa = sqrt(aim[0]*aim[0] + aim[1]*aim[1]);
vx = speed * cosa;
VectorSubtract(tr.endpos,start,dist);
dist[2] = 0;
x = VectorLength(dist);
t = x/vx;
drop = 0.5*sv_gravity->value*t*(t+FRAMETIME);
tr.endpos[2] -= drop;
// move just a bit in the aim direction
tr.endpos[0] += aim[0];
tr.endpos[1] += aim[1];
contents = gi.pointcontents(tr.endpos);
while((contents & MASK_SOLID) && (aim_point[2] > target[2])) {
aim_point[2] -= 8.0;
VectorSubtract(aim_point,self->s.origin,from_origin);
VectorCopy(from_origin,aim);
VectorNormalize(aim);
if(!(self->svflags & SVF_MONSTER))
{
vectoangles(aim,angles);
AngleVectors(angles, forward, right, up);
G_ProjectSource2(self->s.origin,self->move_origin,forward,right,up,start);
VectorSubtract(aim_point,start,from_muzzle);
}
tr = gi.trace(start,vec3_origin,vec3_origin,aim_point,self,MASK_SOLID);
if(tr.fraction < 1.0) {
cosa = sqrt(aim[0]*aim[0] + aim[1]*aim[1]);
vx = speed * cosa;
VectorSubtract(tr.endpos,start,dist);
dist[2] = 0;
x = VectorLength(dist);
t = x/vx;
drop = 0.5*sv_gravity->value*t*(t+FRAMETIME);
tr.endpos[2] -= drop;
tr.endpos[0] += aim[0];
tr.endpos[1] += aim[1];
contents = gi.pointcontents(tr.endpos);
}
}
}
}
return true;
}

View file

@ -419,5 +419,6 @@ ENTITY_MISC_Q1_TORCH,
ENTITY_TARGET_Q1_TRAPSHOOTER,
ENTITY_MISC_Q1_EXPLOBOX,
ENTITY_Q1_FIREBALL,
ENTITY_MISC_Q1_FIREBALL_SPAWNER
ENTITY_MISC_Q1_FIREBALL_SPAWNER,
ENTITY_MONSTER_Q1_FREDDIE
} entity_id;

View file

@ -256,7 +256,7 @@ void flipper_dead (edict_t *self)
M_FlyCheck (self);
// Lazarus monster fade
if(world->effects & FX_WORLDSPAWN_CORPSEFADE)
if (world->effects & FX_WORLDSPAWN_CORPSEFADE)
{
self->think=FadeDieSink;
self->nextthink=level.time+corpse_fadetime->value;
@ -398,11 +398,11 @@ void SP_monster_flipper (edict_t *self)
VectorSet (self->mins, -16, -16, -8);
VectorSet (self->maxs, 16, 16, 24);
if(!self->health)
if (!self->health)
self->health = 50;
if(!self->gib_health)
if (!self->gib_health)
self->gib_health = -40; //was -30
if(!self->mass)
if (!self->mass)
self->mass = 100;
self->pain = flipper_pain;

View file

@ -348,12 +348,12 @@ mmove_t flyer_move_stop = {FRAME_stop01, FRAME_stop07, flyer_frames_stop, NULL};
void flyer_stop (edict_t *self)
{
self->monsterinfo.currentmove = &flyer_move_stop;
self->monsterinfo.currentmove = &flyer_move_stop;
}
void flyer_start (edict_t *self)
{
self->monsterinfo.currentmove = &flyer_move_start;
self->monsterinfo.currentmove = &flyer_move_start;
}
@ -846,7 +846,7 @@ void SP_monster_flyer (edict_t *self)
self->monsterinfo.blocked = flyer_blocked;
if (!self->blood_type)
self->blood_type = 3; //sparks and blood
self->blood_type = 3; // sparks and blood
// Lazarus
if (self->powerarmor)

View file

@ -140,7 +140,7 @@ mframe_t gladiator_frames_attack_melee [] =
};
mmove_t gladiator_move_attack_melee = {FRAME_melee1, FRAME_melee17, gladiator_frames_attack_melee, gladiator_run};
void gladiator_melee(edict_t *self)
void gladiator_melee (edict_t *self)
{
self->monsterinfo.currentmove = &gladiator_move_attack_melee;
}

View file

@ -28,7 +28,7 @@ static int sound_sight;
void gunner_idlesound (edict_t *self)
{
if(!(self->spawnflags & SF_MONSTER_AMBUSH))
if (!(self->spawnflags & SF_MONSTER_AMBUSH))
gi.sound (self, CHAN_VOICE, sound_idle, 1, ATTN_IDLE, 0);
}
@ -321,7 +321,7 @@ void gunner_dead (edict_t *self)
M_FlyCheck (self);
// Lazarus monster fade
if(world->effects & FX_WORLDSPAWN_CORPSEFADE)
if (world->effects & FX_WORLDSPAWN_CORPSEFADE)
{
self->think=FadeDieSink;
self->nextthink=level.time+corpse_fadetime->value;
@ -354,9 +354,9 @@ void gunner_die (edict_t *self, edict_t *inflictor, edict_t *attacker, int damag
if (self->health <= self->gib_health && !(self->spawnflags & SF_MONSTER_NOGIB))
{
gi.sound (self, CHAN_VOICE, gi.soundindex ("misc/udeath.wav"), 1, ATTN_NORM, 0);
for (n= 0; n < 2; n++)
for (n = 0; n < 2; n++)
ThrowGib (self, "models/objects/gibs/bone/tris.md2", damage, GIB_ORGANIC);
for (n= 0; n < 4; n++)
for (n = 0; n < 4; n++)
ThrowGib (self, "models/objects/gibs/sm_meat/tris.md2", damage, GIB_ORGANIC);
ThrowGib (self, "models/objects/gibs/chest/tris.md2", damage, GIB_ORGANIC);
ThrowHead (self, "models/objects/gibs/head2/tris.md2", damage, GIB_ORGANIC);
@ -384,12 +384,12 @@ qboolean gunner_grenade_check(edict_t *self)
vec3_t vhorz;
float horz,vertmax;
if(!self->enemy)
if (!self->enemy)
return false;
// if the player is above my head, use machinegun.
// if(self->absmax[2] <= self->enemy->absmin[2])
// if (self->absmax[2] <= self->enemy->absmin[2])
// return false;
// Lazarus: We can do better than that... see below
@ -411,7 +411,7 @@ qboolean gunner_grenade_check(edict_t *self)
horz = VectorLength(vhorz);
vertmax = (GRENADE_VELOCITY_SQUARED)/(2*sv_gravity->value) -
0.5*sv_gravity->value*horz*horz/GRENADE_VELOCITY_SQUARED;
if(dir[2] > vertmax)
if (dir[2] > vertmax)
return false;
// Lazarus: Make sure there's a more-or-less clear flight path to target
@ -420,13 +420,13 @@ qboolean gunner_grenade_check(edict_t *self)
VectorCopy(self->enemy->s.origin,target);
target[2] = self->enemy->absmax[2];
tr = gi.trace(start, vec3_origin, vec3_origin, target, self, MASK_SHOT);
if(tr.ent == self->enemy || tr.fraction == 1)
if (tr.ent == self->enemy || tr.fraction == 1)
return true;
// Repeat for feet... in case we're looking down at a target standing under,
// for example, a short doorway
target[2] = self->enemy->absmin[2];
tr = gi.trace(start, vec3_origin, vec3_origin, target, self, MASK_SHOT);
if(tr.ent == self->enemy || tr.fraction == 1)
if (tr.ent == self->enemy || tr.fraction == 1)
return true;
return false;
@ -484,7 +484,7 @@ void GunnerFire (edict_t *self)
vec3_t aim;
int flash_number;
if(!self->enemy || !self->enemy->inuse) //PGM
if (!self->enemy || !self->enemy->inuse) //PGM
return; //PGM
flash_number = MZ2_GUNNER_MACHINEGUN_1 + (self->s.frame - FRAME_attak216);
@ -498,7 +498,7 @@ void GunnerFire (edict_t *self)
target[2] += self->enemy->viewheight;
// Lazarus fog reduction of accuracy
if(self->monsterinfo.visibility < FOG_CANSEEGOOD)
if (self->monsterinfo.visibility < FOG_CANSEEGOOD)
{
target[0] += crandom() * 640 * (FOG_CANSEEGOOD - self->monsterinfo.visibility);
target[1] += crandom() * 640 * (FOG_CANSEEGOOD - self->monsterinfo.visibility);
@ -523,7 +523,7 @@ void GunnerGrenade (edict_t *self)
vec3_t target;
qboolean blindfire;
if(!self->enemy || !self->enemy->inuse) //PGM
if (!self->enemy || !self->enemy->inuse) //PGM
return; //PGM
// pmm
@ -572,7 +572,7 @@ void GunnerGrenade (edict_t *self)
G_ProjectSource (self->s.origin, monster_flash_offset[flash_number], forward, right, start);
//PGM
if(self->enemy)
if (self->enemy)
{
float dist;
@ -582,10 +582,10 @@ void GunnerGrenade (edict_t *self)
// aim at enemy's feet if he's at same elevation or lower. otherwise aim at origin
VectorCopy(self->enemy->s.origin,target);
if(self->enemy->absmin[2] <= self->absmax[2]) target[2] = self->enemy->absmin[2];
if (self->enemy->absmin[2] <= self->absmax[2]) target[2] = self->enemy->absmin[2];
// Lazarus fog reduction of accuracy
if(self->monsterinfo.visibility < FOG_CANSEEGOOD)
if (self->monsterinfo.visibility < FOG_CANSEEGOOD)
{
target[0] += crandom() * 640 * (FOG_CANSEEGOOD - self->monsterinfo.visibility);
target[1] += crandom() * 640 * (FOG_CANSEEGOOD - self->monsterinfo.visibility);
@ -593,7 +593,7 @@ void GunnerGrenade (edict_t *self)
}
// lead target... 20, 35, 50, 65 chance of leading
if( random() < (0.2 + skill->value * 0.15) )
if ( random() < (0.2 + skill->value * 0.15) )
{
float dist;
float time;
@ -605,14 +605,14 @@ void GunnerGrenade (edict_t *self)
}
// aim up if they're on the same level as me and far away.
if((dist > 512) && (aim[2] < 64) && (aim[2] > -64))
if ((dist > 512) && (aim[2] < 64) && (aim[2] > -64))
aim[2] += (dist - 512);
/* VectorNormalize (aim);
pitch = aim[2];
if(pitch > 0.4)
if (pitch > 0.4)
pitch = 0.4;
else if(pitch < -0.5)
else if (pitch < -0.5)
pitch = -0.5;*/
}
//PGM
@ -621,7 +621,7 @@ void GunnerGrenade (edict_t *self)
// Lazarus - take into account (sort of) feature of adding shooter's velocity to
// grenade velocity
monster_speed = VectorLength(self->velocity);
if(monster_speed > 0)
if (monster_speed > 0)
{
vec3_t v1;
vec_t delta;
@ -930,11 +930,11 @@ void gunner_jump2_now (edict_t *self)
void gunner_jump_wait_land (edict_t *self)
{
if(self->groundentity == NULL)
if (self->groundentity == NULL)
{
self->monsterinfo.nextframe = self->s.frame;
if(monster_jump_finished (self))
if (monster_jump_finished (self))
self->monsterinfo.nextframe = self->s.frame + 1;
}
else
@ -973,12 +973,12 @@ mmove_t gunner_move_jump2 = { FRAME_jump01, FRAME_jump10, gunner_frames_jump2, g
void gunner_jump (edict_t *self)
{
if(!self->enemy)
if (!self->enemy)
return;
monster_done_dodge (self);
if(self->enemy->s.origin[2] > self->s.origin[2])
if (self->enemy->s.origin[2] > self->s.origin[2])
self->monsterinfo.currentmove = &gunner_move_jump2;
else
self->monsterinfo.currentmove = &gunner_move_jump;
@ -988,13 +988,13 @@ void gunner_jump (edict_t *self)
//PGM
qboolean gunner_blocked (edict_t *self, float dist)
{
if(blocked_checkshot (self, 0.25 + (0.05 * skill->value) ))
if (blocked_checkshot (self, 0.25 + (0.05 * skill->value) ))
return true;
if(blocked_checkplat (self, dist))
if (blocked_checkplat (self, dist))
return true;
if(blocked_checkjump (self, dist, 192, 40))
if (blocked_checkjump (self, dist, 192, 40))
{
gunner_jump(self);
return true;

View file

@ -157,7 +157,7 @@ mmove_t mutant_move_idle = {FRAME_stand152, FRAME_stand164, mutant_frames_idle,
void mutant_idle (edict_t *self)
{
self->monsterinfo.currentmove = &mutant_move_idle;
if(!(self->spawnflags & SF_MONSTER_AMBUSH))
if (!(self->spawnflags & SF_MONSTER_AMBUSH))
gi.sound (self, CHAN_VOICE, sound_idle, 1, ATTN_IDLE, 0);
}
@ -528,7 +528,7 @@ void mutant_dead (edict_t *self)
M_FlyCheck (self);
// Lazarus monster fade
if(world->effects & FX_WORLDSPAWN_CORPSEFADE)
if (world->effects & FX_WORLDSPAWN_CORPSEFADE)
{
self->think=FadeDieSink;
self->nextthink=level.time+corpse_fadetime->value;
@ -619,7 +619,7 @@ void mutant_jump_up (edict_t *self)
void mutant_jump_wait_land (edict_t *self)
{
if(self->groundentity == NULL)
if (self->groundentity == NULL)
self->monsterinfo.nextframe = self->s.frame;
else
self->monsterinfo.nextframe = self->s.frame + 1;
@ -647,10 +647,10 @@ mmove_t mutant_move_jump_down = { FRAME_jump01, FRAME_jump05, mutant_frames_jump
void mutant_jump_updown (edict_t *self)
{
if(!self->enemy)
if (!self->enemy)
return;
if(self->enemy->s.origin[2] > self->s.origin[2])
if (self->enemy->s.origin[2] > self->s.origin[2])
self->monsterinfo.currentmove = &mutant_move_jump_up;
else
self->monsterinfo.currentmove = &mutant_move_jump_down;
@ -663,13 +663,13 @@ Blocked
*/
qboolean mutant_blocked (edict_t *self, float dist)
{
if(blocked_checkjump (self, dist, 256, 68))
if (blocked_checkjump (self, dist, 256, 68))
{
mutant_jump_updown (self);
return true;
}
if(blocked_checkplat (self, dist))
if (blocked_checkplat (self, dist))
return true;
return false; //Knightmare- this is to prevent warnings
@ -719,11 +719,11 @@ void SP_monster_mutant (edict_t *self)
VectorSet (self->mins, -32, -32, -24);
VectorSet (self->maxs, 32, 32, 48);
if(!self->health)
if (!self->health)
self->health = 300;
if(!self->gib_health)
if (!self->gib_health)
self->gib_health = -120;
if(!self->mass)
if (!self->mass)
self->mass = 300;
self->pain = mutant_pain;
@ -741,11 +741,11 @@ void SP_monster_mutant (edict_t *self)
self->monsterinfo.checkattack = mutant_checkattack;
self->monsterinfo.blocked = mutant_blocked; // PGM
if(!self->monsterinfo.flies)
if (!self->monsterinfo.flies)
self->monsterinfo.flies = 0.80;
// Lazarus
if(self->powerarmor)
if (self->powerarmor)
{
if (self->powerarmortype == 1)
self->monsterinfo.power_armor_type = POWER_ARMOR_SCREEN;

View file

@ -12,6 +12,7 @@ QUAKE DOG
static int sound_pain;
static int sound_death;
static int sound_gib;
static int sound_attack;
static int sound_sight;
static int sound_idle;
@ -397,7 +398,7 @@ void q1dog_die (edict_t *self, edict_t *inflictor, edict_t *attacker, int damage
if (self->health <= self->gib_health && !(self->spawnflags & SF_MONSTER_NOGIB))
{
gi.sound (self, CHAN_VOICE|CHAN_RELIABLE, gi.soundindex ("q1player/udeath.wav"), 1, ATTN_NORM, 0);
gi.sound (self, CHAN_VOICE|CHAN_RELIABLE, sound_gib, 1, ATTN_NORM, 0);
ThrowGib (self, "models/objects/q1gibs/q1gib1/tris.md2", damage, GIB_ORGANIC);
for (n= 0; n < 2; n++)
@ -438,10 +439,16 @@ void SP_monster_q1_dog (edict_t *self)
}
sound_pain = gi.soundindex ("q1dog/dpain1.wav");
sound_death = gi.soundindex ("q1dog/ddeath.wav");
sound_gib = gi.soundindex ("q1player/udeath.wav");
sound_attack = gi.soundindex ("q1dog/dattack1.wav");
sound_sight = gi.soundindex ("q1dog/dsight.wav");
sound_idle = gi.soundindex ("q1dog/idle.wav");
// precache gibs
gi.modelindex ("models/monsters/q1dog/head/tris.md2");
gi.modelindex ("models/objects/q1gibs/q1gib1/tris.md2");
gi.modelindex ("models/objects/q1gibs/q1gib3/tris.md2");
self->movetype = MOVETYPE_STEP;
self->solid = SOLID_BBOX;

View file

@ -12,6 +12,7 @@ QUAKE ENFORCER
static int sound_pain1;
static int sound_pain2;
static int sound_death;
static int sound_gib;
static int sound_idle;
static int sound_sight1;
static int sound_sight2;
@ -253,7 +254,7 @@ void q1enforcer_die (edict_t *self, edict_t *inflictor, edict_t *attacker, int d
// check for gib
if (self->health <= self->gib_health && !(self->spawnflags & SF_MONSTER_NOGIB))
{
gi.sound (self, CHAN_VOICE|CHAN_RELIABLE, gi.soundindex ("q1player/udeath.wav"), 1, ATTN_NORM, 0);
gi.sound (self, CHAN_VOICE|CHAN_RELIABLE, sound_gib, 1, ATTN_NORM, 0);
for (n= 0; n < 2; n++)
ThrowGib (self, "models/objects/q1gibs/q1gib1/tris.md2", damage, GIB_ORGANIC);
@ -347,6 +348,7 @@ void SP_monster_q1_enforcer (edict_t *self)
sound_pain1 = gi.soundindex ("q1enforcer/pain1.wav");
sound_pain2 = gi.soundindex ("q1enforcer/pain2.wav");
sound_death = gi.soundindex ("q1enforcer/death1.wav");
sound_gib = gi.soundindex ("q1player/udeath.wav");
sound_idle = gi.soundindex ("q1enforcer/idle1.wav");
sound_sight1 = gi.soundindex ("q1enforcer/sight1.wav");
sound_sight2 = gi.soundindex ("q1enforcer/sight2.wav");
@ -357,6 +359,12 @@ void SP_monster_q1_enforcer (edict_t *self)
// precache backpack
gi.modelindex ("models/items/q1backpack/tris.md2");
// gi.soundindex ("q1weapons/lock4.wav");
// precache gibs
gi.modelindex ("models/monsters/q1enforcer/head/tris.md2");
gi.modelindex ("models/objects/q1gibs/q1gib1/tris.md2");
gi.modelindex ("models/objects/q1gibs/q1gib3/tris.md2");
// precache laser
q1_laser_precache ();
self->movetype = MOVETYPE_STEP;
self->solid = SOLID_BBOX;

View file

@ -13,6 +13,7 @@ QUAKE FIEND
static int sound_hit;
static int sound_jump;
static int sound_death;
static int sound_gib;
static int sound_idle;
static int sound_pain;
static int sound_sight;
@ -413,7 +414,7 @@ void fiend_die (edict_t *self, edict_t *inflictor, edict_t *attacker, int damage
if (self->health <= self->gib_health && !(self->spawnflags & SF_MONSTER_NOGIB))
{
gi.sound (self, CHAN_VOICE|CHAN_RELIABLE, gi.soundindex ("q1player/udeath.wav"), 1, ATTN_NORM, 0);
gi.sound (self, CHAN_VOICE|CHAN_RELIABLE, sound_gib, 1, ATTN_NORM, 0);
for (n= 0; n < 2; n++)
ThrowGib (self, "models/objects/q1gibs/q1gib1/tris.md2", damage, GIB_ORGANIC);
@ -452,13 +453,19 @@ void SP_monster_q1_fiend (edict_t *self)
return;
}
sound_hit = gi.soundindex ("q1fiend/dhit2.wav");
sound_jump = gi.soundindex ("q1fiend/djump.wav");
sound_death = gi.soundindex ("q1fiend/ddeath.wav");
sound_idle = gi.soundindex ("q1fiend/idle1.wav");
sound_pain = gi.soundindex ("q1fiend/dpain1.wav");
sound_sight = gi.soundindex ("q1fiend/sight2.wav");
sound_land = gi.soundindex ("q1fiend/dland2.wav");
sound_hit = gi.soundindex ("q1fiend/dhit2.wav");
sound_jump = gi.soundindex ("q1fiend/djump.wav");
sound_death = gi.soundindex ("q1fiend/ddeath.wav");
sound_gib = gi.soundindex ("q1player/udeath.wav");
sound_idle = gi.soundindex ("q1fiend/idle1.wav");
sound_pain = gi.soundindex ("q1fiend/dpain1.wav");
sound_sight = gi.soundindex ("q1fiend/sight2.wav");
sound_land = gi.soundindex ("q1fiend/dland2.wav");
// precache gibs
gi.modelindex ("models/monsters/q1fiend/head/tris.md2");
gi.modelindex ("models/objects/q1gibs/q1gib1/tris.md2");
gi.modelindex ("models/objects/q1gibs/q1gib3/tris.md2");
self->movetype = MOVETYPE_STEP;
self->solid = SOLID_BBOX;

890
missionpack/m_q1freddie.c Normal file
View file

@ -0,0 +1,890 @@
/*==============================================================================
Quake AD FREDDIE (Edie from Quoth - Kell/Necros/Preach)
Reimplemented by Knightmare and MikeM
==============================================================================
*/
#include "g_local.h"
#include "m_q1freddie.h"
static int sound_pain1;
static int sound_pain2;
static int sound_death;
static int sound_death2;
static int sound_idle;
static int sound_sight;
static int sound_saw;
static int sound_melee;
static int sound_atk_spinup;
static int sound_atk_nail;
static int sound_atk_laser;
static int sound_step1;
static int sound_step2;
static int sound_step3;
#define SF_FREDDIE_LASER 32
#define FREDDIE_MELEE_DISTANCE 64
void freddie_fireweapon (edict_t *self, vec3_t offset);
void freddie_attack(edict_t *self);
void freddie_check_refire (edict_t *self);
void freddie_idle_sound (edict_t *self)
{
if (random() < 0.2)
gi.sound (self, CHAN_VOICE, sound_idle, 1, ATTN_IDLE, 0);
}
void freddie_sight (edict_t *self, edict_t *other)
{
gi.sound (self, CHAN_VOICE, sound_sight, 1, ATTN_NORM, 0);
freddie_attack (self);
}
void freddie_sound_footstep (edict_t *self)
{
static int stepNum = 0;
switch (stepNum)
{
case 0:
default:
gi.sound (self, CHAN_BODY, sound_step1, 1, ATTN_NORM, 0);
break;
case 1:
gi.sound (self, CHAN_BODY, sound_step2, 1, ATTN_NORM, 0);
break;
case 2:
gi.sound (self, CHAN_BODY, sound_step1, 1, ATTN_NORM, 0);
break;
case 3:
gi.sound (self, CHAN_BODY, sound_step2, 1, ATTN_NORM, 0);
break;
case 4:
gi.sound (self, CHAN_BODY, sound_step3, 1, ATTN_NORM, 0);
break;
}
stepNum++;
if (stepNum > 4)
stepNum = 0;
}
//
// stand
//
void freddie_stand (edict_t *self);
mframe_t freddie_frames_stand [] =
{
ai_stand, 0, freddie_idle_sound,
ai_stand, 0, NULL,
ai_stand, 0, NULL,
ai_stand, 0, NULL,
ai_stand, 0, NULL,
ai_stand, 0, NULL,
ai_stand, 0, NULL,
ai_stand, 0, NULL,
};
mmove_t freddie_move_stand = {FRAME_stand1, FRAME_stand8, freddie_frames_stand, freddie_stand};
void freddie_stand (edict_t *self)
{
self->monsterinfo.currentmove = &freddie_move_stand;
}
//
// walk
//
void freddie_walk (edict_t *self);
mframe_t freddie_frames_walk [] =
{
ai_walk, 20, freddie_idle_sound,
ai_walk, 16, freddie_sound_footstep,
ai_walk, 1, NULL,
ai_walk, 2, NULL,
ai_walk, 4, NULL,
ai_walk, 8, NULL,
ai_walk, 4, NULL,
ai_walk, 16, NULL,
ai_walk, 20, NULL,
ai_walk, 16, freddie_sound_footstep,
ai_walk, 1, NULL,
ai_walk, 2, NULL,
ai_walk, 4, NULL,
ai_walk, 8, NULL,
ai_walk, 4, NULL,
ai_walk, 16, NULL,
};
mmove_t freddie_move_walk = {FRAME_run1, FRAME_run6, freddie_frames_walk, NULL};
void freddie_walk (edict_t *self)
{
self->monsterinfo.currentmove = &freddie_move_walk;
}
//
// run
//
void freddie_run (edict_t *self);
void freddie_run_frame (edict_t *self);
mframe_t freddie_frames_run [] =
{
ai_run, 24, freddie_run_frame, // freddie_idle_sound,
ai_run, 19, freddie_run_frame, // freddie_sound_footstep,
ai_run, 1, freddie_run_frame,
ai_run, 2, freddie_run_frame,
ai_run, 5, freddie_run_frame,
ai_run, 10, freddie_run_frame,
ai_run, 5, freddie_run_frame,
ai_run, 5, freddie_run_frame,
ai_run, 24, freddie_run_frame,
ai_run, 19, freddie_run_frame,
ai_run, 1, freddie_run_frame, // freddie_sound_footstep,
ai_run, 2, freddie_run_frame,
ai_run, 5, freddie_run_frame,
ai_run, 10, freddie_run_frame,
ai_run, 5, freddie_run_frame,
ai_run, 5, freddie_run_frame,
};
mmove_t freddie_move_run = {FRAME_run1, FRAME_run16, freddie_frames_run, NULL};
void freddie_run (edict_t *self)
{
if (self->monsterinfo.aiflags & AI_STAND_GROUND)
self->monsterinfo.currentmove = &freddie_move_stand;
else
self->monsterinfo.currentmove = &freddie_move_run;
}
//
// run + firing
//
mframe_t freddie_frames_rfire [] =
{
ai_run, 24, freddie_run_frame, // freddie_idle_sound,
ai_run, 19, freddie_run_frame, // freddie_sound_footstep,
ai_run, 1, freddie_run_frame,
ai_run, 2, freddie_run_frame,
ai_run, 5, freddie_run_frame,
ai_run, 10, freddie_run_frame,
ai_run, 5, freddie_run_frame,
ai_run, 5, freddie_run_frame,
ai_run, 24, freddie_run_frame,
ai_run, 19, freddie_run_frame,
ai_run, 1, freddie_run_frame, // freddie_sound_footstep,
ai_run, 2, freddie_run_frame,
ai_run, 5, freddie_run_frame,
ai_run, 10, freddie_run_frame,
ai_run, 5, freddie_run_frame,
ai_run, 5, freddie_run_frame,
};
mmove_t freddie_move_rfire = {FRAME_rfire1, FRAME_rfire16, freddie_frames_rfire, NULL};
void freddie_rfire (edict_t *self)
{
if (self->monsterinfo.aiflags & AI_STAND_GROUND)
self->monsterinfo.currentmove = &freddie_move_stand;
else
self->monsterinfo.currentmove = &freddie_move_rfire;
}
void freddie_run_frame (edict_t *self)
{
int startFrame = 0;
if ( !self || (self->health <= 0) )
return;
// If enemy is dead or missing no firing
// if ( !self->enemy || (self->enemy->health <= 0) )
// self->
if (self->monsterinfo.currentmove == &freddie_move_run)
startFrame = FRAME_run1;
else if (self->monsterinfo.currentmove == &freddie_move_rfire)
startFrame = FRAME_rfire1;
switch (self->s.frame - startFrame)
{
case 0:
VectorSet (self->muzzle, 50, -20, 32); freddie_idle_sound (self);
break;
case 1:
VectorSet (self->muzzle, 43, -18, 33); freddie_sound_footstep (self);
break;
case 2:
VectorSet (self->muzzle, 53, -20, 27);
break;
case 3:
VectorSet (self->muzzle, 47, -19, 31);
break;
case 4:
VectorSet (self->muzzle, 54, -17, 29);
break;
case 5:
VectorSet (self->muzzle, 47, -17, 35);
break;
case 6:
VectorSet (self->muzzle, 53, -15, 32);
break;
case 7:
VectorSet (self->muzzle, 47, -15, 36);
break;
case 8:
VectorSet (self->muzzle, 50, -13, 32);
break;
case 9:
VectorSet (self->muzzle, 46, -15, 33);
break;
case 10:
VectorSet (self->muzzle, 51, -14, 33); freddie_sound_footstep (self);
break;
case 11:
VectorSet (self->muzzle, 47, -14, 32);
break;
case 12:
VectorSet (self->muzzle, 52, -14, 33);
break;
case 13:
VectorSet (self->muzzle, 47, -14, 36);
break;
case 14:
VectorSet (self->muzzle, 49, -14, 35);
break;
case 15:
VectorSet (self->muzzle, 45, -15, 34);
break;
default:
VectorSet (self->muzzle, 0, 0, 0);
break;
}
// Run + Fire time?
/* if (self->fog_model > 0)
{
self->fog_index++;
if (self->fog_index > 2)
self->fog_model = 0;
else
freddie_fireweapon (self, self->muzzle);
}*/
}
//
// pain
//
void freddie_pain (edict_t *self, edict_t *other, float kick, int damage);
mframe_t freddie_frames_pain1 [] =
{
ai_move, 0, NULL,
ai_move, 10, NULL,
ai_move, 9, NULL,
ai_move, 4, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL
};
mmove_t freddie_move_pain1 = {FRAME_pain1, FRAME_pain12, freddie_frames_pain1, freddie_run};
mframe_t freddie_frames_pain2 [] =
{
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL
};
mmove_t freddie_move_pain2 = {FRAME_painb1, FRAME_painb5, freddie_frames_pain2, freddie_run};
void freddie_pain (edict_t *self, edict_t *other, float kick, int damage)
{
float r;
if (level.time < self->pain_debounce_time)
return;
r = random();
if (r < 0.5f)
gi.sound (self, CHAN_VOICE, sound_pain1, 1, ATTN_NORM, 0);
else
gi.sound (self, CHAN_VOICE, sound_pain2, 1, ATTN_NORM, 0);
self->pain_debounce_time = level.time + 3 + random() * 2;
if (skill->value == 3) {
self->pain_debounce_time = level.time + 3 + random() * 2;
return; // no pain anims in nightmare
}
if (damage <= 50) {
self->monsterinfo.currentmove = &freddie_move_pain2;
self->pain_debounce_time = level.time + 2 + random() * 2;
}
else {
self->monsterinfo.currentmove = &freddie_move_pain1;
self->pain_debounce_time = level.time + 3 + random() * 2;
}
}
//
// fire (standing)
//
void freddie_attack (edict_t *self);
void freddie_do_sfire (edict_t *self);
void freddie_attack_spindown (edict_t *self);
void freddie_attack_spinupsound (edict_t *self)
{
gi.sound (self, CHAN_BODY, sound_atk_spinup, 1.0, ATTN_NORM, 0);
}
void freddie_attack_prefire (edict_t *self)
{
self->fog_index = 0;
self->fogclip = 4 + (int)skill->value * 2;
}
void freddie_fireweapon (edict_t *self, vec3_t offset)
{
vec3_t start, forward, right, dir, vec; // attack_track
float speed, scale;
if ( !self || (self->health <= 0) )
return;
if ( !self->enemy || (self->enemy->health < 1) ) // If no enemy or enemy dead then stop attack
return;
// Nail and laser use the same firing speed
speed = 500 + (int)skill->value * 150;
// Rotate offset vector
AngleVectors (self->s.angles, forward, right, NULL);
G_ProjectSource (self->s.origin, offset, forward, right, start);
/* if ( (self->fog_model != 0) && ((int)skill->value > 1) ) // The mini burst mode (run+fire) can do tracking
{
if (self->fog_index == 1)
Freddie_Tracking (self->enemy->s.origin, offset, self->enemy, speed, attack_track);
else
Freddie_Tracking (attack_track, offset, self->enemy, speed, attack_track);
VectorSubtract (attack_track, start, dir);
VectorNormalize (dir);
}
else*/ // Standard mode spray bullets at player
{
scale = crandom() * (20 + (random() * 50));
VectorScale (right, scale, vec);
VectorAdd (self->enemy->s.origin, vec, dir);
VectorSubtract (dir, start, dir);
VectorNormalize (dir);
}
if (self->spawnflags & SF_FREDDIE_LASER) {
gi.sound (self, CHAN_WEAPON|CHAN_RELIABLE, sound_atk_laser, 1.0, ATTN_NORM, 0);
q1_fire_laser (self, start, dir, 15, speed);
}
else {
gi.sound (self, CHAN_WEAPON|CHAN_RELIABLE, sound_atk_nail, 1.0, ATTN_NORM, 0);
q1_fire_nail (self, start, dir, 9, speed, true);
}
}
void freddie_stand_fire (edict_t *self)
{
vec3_t offset;
qboolean quitNext = false;
// Easy = 7 shots, Normal = 11 shots, Hard/NM = 15 shots
switch (self->s.frame)
{
case FRAME_sfire9:
VectorSet (offset, 45, -10, 20);
break;
case FRAME_sfire10:
VectorSet (offset, 45, -10, 20);
break;
case FRAME_sfire11:
VectorSet (offset, 45, -10, 22);
break;
case FRAME_sfire12:
VectorSet (offset, 45, -10, 22);
break;
case FRAME_sfire13:
VectorSet (offset, 45, -12, 23);
break;
case FRAME_sfire14:
VectorSet (offset, 42, -12, 25);
break;
case FRAME_sfire15:
VectorSet (offset, 42, -14, 23);
if ((int)skill->value == 0)
quitNext = true;
break;
case FRAME_sfire16:
VectorSet (offset, 38, -14, 27);
break;
case FRAME_sfire17:
VectorSet (offset, 38, -17, 26);
break;
case FRAME_sfire18:
VectorSet (offset, 36, -17, 28);
break;
case FRAME_sfire19:
VectorSet (offset, 36, -17, 26);
if ((int)skill->value == 1)
quitNext = true;
break;
case FRAME_sfire20:
VectorSet (offset, 30, -17, 28);
break;
case FRAME_sfire21:
VectorSet (offset, 30, -18, 25);
break;
case FRAME_sfire22:
VectorSet (offset, 25, -18, 27);
break;
case FRAME_sfire23:
VectorSet (offset, 25, -18, 27);
break;
default:
VectorSet (offset, 0, 0, 0);
break;
}
if ( !self->enemy || (self->enemy->health < 1) ) // If no enemy or enemy dead then stop attack
self->fog_index = self->fogclip + 1;
else if ( visible(self, self->enemy) ) // Check if enemy is visible to weapon
self->fog_index++;
else // Reset counter and keep firing
self->fog_index = 0;
if (self->fog_index > self->fogclip)
freddie_attack_spindown (self);
else
freddie_fireweapon (self, offset);
if (quitNext) // this is our last firing frame based on skill level
self->fog_index = self->fogclip + 1;
}
mframe_t freddie_frames_sfire_start [] =
{
ai_charge, 0, freddie_attack_spinupsound,
ai_charge, 0, NULL,
ai_charge, 0, NULL,
ai_charge, 0, NULL,
ai_charge, 0, freddie_sound_footstep,
ai_charge, 0, NULL,
ai_charge, 0, NULL,
ai_charge, 0, freddie_attack_prefire
};
mmove_t freddie_move_sfire_start = {FRAME_sfire1, FRAME_sfire8, freddie_frames_sfire_start, freddie_do_sfire};
mframe_t freddie_frames_sfire [] =
{
ai_charge, 0, freddie_stand_fire,
ai_charge, 0, freddie_stand_fire,
ai_charge, 0, freddie_stand_fire,
ai_charge, 0, freddie_stand_fire,
ai_charge, 0, freddie_stand_fire,
ai_charge, 0, freddie_stand_fire,
ai_charge, 0, freddie_stand_fire,
ai_charge, 0, freddie_stand_fire,
ai_charge, 0, freddie_stand_fire,
ai_charge, 0, freddie_stand_fire,
ai_charge, 0, freddie_stand_fire,
ai_charge, 0, freddie_stand_fire,
ai_charge, 0, freddie_stand_fire,
ai_charge, 0, freddie_stand_fire,
ai_charge, 0, freddie_stand_fire
};
mmove_t freddie_move_sfire = {FRAME_sfire9, FRAME_sfire23, freddie_frames_sfire, freddie_attack_spindown};
mframe_t freddie_frames_sfire_stop [] =
{
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL
};
mmove_t freddie_move_sfire_stop = {FRAME_sfire24, FRAME_sfire27, freddie_frames_sfire_stop, freddie_run};
void freddie_do_sfire (edict_t *self)
{
self->monsterinfo.currentmove = &freddie_move_sfire;
}
void freddie_attack_spindown (edict_t *self)
{
self->monsterinfo.currentmove = &freddie_move_sfire_stop;
}
void freddie_attack (edict_t *self)
{
self->monsterinfo.currentmove = &freddie_move_sfire_start;
}
//
// melee
//
void freddie_melee (edict_t *self);
void freddie_melee_repeat (edict_t *self);
void freddie_saw_sound (edict_t *self)
{
gi.sound (self, CHAN_VOICE, sound_saw, 1, ATTN_NORM, 0);
}
void freddie_blade (edict_t *self, float side)
{
float damage;
vec3_t aim;
if (!self->enemy)
return;
if (self->enemy->health <= 0)
return;
// 1-45 (3x15) damage
damage = (random() + random() + random()) * 15;
damage = max (1, damage);
VectorSet (aim, FREDDIE_MELEE_DISTANCE, self->mins[0], 8);
if ( fire_hit (self, aim, damage, 100) )
gi.sound (self, CHAN_VOICE, sound_melee, 1, ATTN_NORM, 0);
}
void freddie_blade_right (edict_t *self)
{
freddie_blade (self, -200);
}
void freddie_blade_left (edict_t *self)
{
freddie_blade (self, 200);
}
mframe_t freddie_frames_fswing [] =
{
ai_charge, 8, freddie_saw_sound,
ai_charge, 16, freddie_sound_footstep,
ai_charge, 10, NULL,
ai_charge, 4, freddie_sound_footstep,
ai_charge, 2, NULL,
ai_charge, 1, NULL,
ai_charge, 1, NULL,
ai_charge, 2, freddie_blade_right,
ai_charge, 2, NULL,
ai_charge, 2, NULL,
ai_charge, 0, NULL,
};
mmove_t freddie_move_fswing = {FRAME_fswing1, FRAME_fswing11, freddie_frames_fswing, freddie_melee_repeat};
mframe_t freddie_frames_bswing [] =
{
ai_charge, 20, freddie_saw_sound,
ai_charge, 12, NULL,
ai_charge, 4, NULL,
ai_charge, 2, freddie_sound_footstep,
ai_charge, 6, freddie_blade_left,
ai_charge, 4, NULL,
ai_charge, 4, NULL,
ai_charge, 8, NULL,
ai_charge, 8, freddie_sound_footstep,
ai_charge, 8, NULL,
ai_charge, 8, NULL,
ai_charge, 12, NULL,
ai_charge, 10, NULL,
ai_charge, 10, NULL,
};
mmove_t freddie_move_bswing = {FRAME_bswing1, FRAME_bswing14, freddie_frames_bswing, freddie_run};
mframe_t freddie_frames_fswinge [] =
{
ai_charge, 0, NULL,
ai_charge, 0, NULL,
ai_charge, 0, NULL,
ai_charge, 0, NULL,
ai_charge, 0, NULL,
ai_charge, 0, NULL,
ai_charge, 0, NULL,
ai_charge, 0, NULL,
ai_charge, 0, NULL,
ai_charge, 0, freddie_sound_footstep,
};
mmove_t freddie_move_fswinge = {FRAME_fswinge1, FRAME_fswinge10, freddie_frames_fswinge, freddie_run};
void freddie_melee_repeat (edict_t *self)
{
int r;
if (!self->enemy)
return;
if (self->enemy->health <= 0)
return;
// Check if within range to do a second (backward) swing attack
r = range(self, self->enemy);
if (r == RANGE_MELEE)
{
self->monsterinfo.currentmove = &freddie_move_bswing;
}
else
self->monsterinfo.currentmove = &freddie_move_fswinge;
}
void freddie_melee (edict_t *self)
{
int r;
if (!self->enemy)
return;
if (self->enemy->health <= 0)
return;
r = range(self, self->enemy);
if (r == RANGE_MELEE)
{
self->monsterinfo.currentmove = &freddie_move_fswing;
}
else if (visible(self, self->enemy) && infront(self,self->enemy)
&& (r < RANGE_FAR) && !(self->monsterinfo.aiflags & AI_SOUND_TARGET))
{
self->monsterinfo.currentmove = &freddie_move_sfire_start;
}
else
self->monsterinfo.currentmove = &freddie_move_run;
}
//
// death
//
void freddie_dead (edict_t *self)
{
VectorSet (self->mins, -16, -16, -24);
VectorSet (self->maxs, 16, 16, -8);
self->movetype = MOVETYPE_TOSS;
self->svflags |= SVF_DEADMONSTER;
self->nextthink = 0;
gi.linkentity (self);
}
void freddie_nogib (edict_t *self)
{
self->gib_health = -10000;
}
mframe_t freddie_frames_death [] =
{
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, freddie_nogib,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL
};
mmove_t freddie_move_death = {FRAME_death1, FRAME_death35, freddie_frames_death, freddie_dead};
void freddie_die (edict_t *self, edict_t *inflictor, edict_t *attacker, int damage, vec3_t point)
{
int n, type, bloodTypeBak;
// check for gib
if ( (self->health <= self->gib_health) && !(self->spawnflags & SF_MONSTER_NOGIB) )
{
gi.sound (self, CHAN_VOICE|CHAN_RELIABLE, sound_death2, 1, ATTN_NORM, 0);
// T_RadiusDamage (self, self, 40, NULL, 40, MOD_EXPLOSIVE); // this would cause a crash because inflictor entity is freed
gi.WriteByte (svc_temp_entity);
if (self->waterlevel)
type = TE_ROCKET_EXPLOSION_WATER;
else
type = TE_EXPLOSION1_BIG;
gi.WriteByte (type);
gi.WritePosition (self->s.origin);
gi.multicast (self->s.origin, MULTICAST_PVS);
for (n = 0; n < 6; n++)
ThrowGib (self, "models/objects/q1gibs/q1gib1/tris.md2", damage, GIB_ORGANIC);
for (n = 0; n < 6; n++)
ThrowGib (self, "models/objects/q1gibs/q1gib3/tris.md2", damage, GIB_ORGANIC);
// change blood type to mechanical to throw mech gibs
bloodTypeBak = self->blood_type;
self->blood_type = 2;
for (n = 0; n < 3; n++)
ThrowGibFrame (self, "models/monsters/q1freddie/gib_junk/tris.md2", (int)(random()*3), damage, GIB_METALLIC);
for (n = 0; n < 4; n++)
ThrowGib (self, "models/monsters/q1freddie/gib_metal1/tris.md2", damage, GIB_METALLIC);
for (n = 0; n < 4; n++)
ThrowGib (self, "models/monsters/q1freddie/gib_metal3/tris.md2", damage, GIB_METALLIC);
self->blood_type = bloodTypeBak;
ThrowHead (self, "models/monsters/q1ogre/head/tris.md2", damage, GIB_ORGANIC);
self->deadflag = DEAD_DEAD;
return;
}
if (self->deadflag == DEAD_DEAD)
return;
// regular death
gi.sound (self, CHAN_VOICE, sound_death, 1, ATTN_NORM, 0);
self->deadflag = DEAD_DEAD;
self->takedamage = DAMAGE_YES;
self->monsterinfo.currentmove = &freddie_move_death;
}
/*QUAKED monster_q1_freddie (1 0 0) (-32 -32 -24) (32 32 64) Ambush Trigger_Spawn Sight
model="models/monsters/q1freddie/tris.md2"
*/
void SP_monster_q1_freddie (edict_t *self)
{
if (deathmatch->value)
{
G_FreeEdict (self);
return;
}
sound_pain1 = gi.soundindex ("q1freddie/pain.wav");
sound_pain2 = gi.soundindex ("q1freddie/painshrt.wav");
sound_death = gi.soundindex ("q1freddie/death.wav");
sound_death2 = gi.soundindex ("q1freddie/explode_major.wav");
sound_idle = gi.soundindex ("q1freddie/idle1.wav");
sound_sight = gi.soundindex ("q1freddie/sight.wav");
sound_saw = gi.soundindex ("q1freddie/sawstart.wav");
sound_melee = gi.soundindex ("q1freddie/mangle.wav");
sound_atk_spinup = gi.soundindex ("q1freddie/stfire.wav");
sound_atk_nail = gi.soundindex ("q1weapons/rocket1i.wav");
sound_atk_laser = gi.soundindex ("q1enforcer/enfire.wav");
sound_step1 = gi.soundindex ("q1freddie/step.wav");
sound_step2 = gi.soundindex ("q1freddie/step2.wav");
sound_step3 = gi.soundindex ("q1freddie/step3.wav");
// precache gibs
gi.modelindex ("models/monsters/q1ogre/head/tris.md2");
gi.modelindex ("models/objects/q1gibs/q1gib1/tris.md2");
gi.modelindex ("models/objects/q1gibs/q1gib3/tris.md2");
gi.modelindex ("models/monsters/q1freddie/gib_junk/tris.md2");
gi.modelindex ("models/monsters/q1freddie/gib_metal1/tris.md2");
gi.modelindex ("models/monsters/q1freddie/gib_metal3/tris.md2");
// precache nail/laser
if (self->spawnflags & SF_FREDDIE_LASER)
q1_laser_precache ();
else
q1_nail_precache ();
self->movetype = MOVETYPE_STEP;
self->solid = SOLID_BBOX;
// Lazarus: special purpose skins
if ( self->style )
{
PatchMonsterModel("models/monsters/q1freddie/tris.md2");
self->s.skinnum = self->style * 2;
}
self->s.modelindex = gi.modelindex ("models/monsters/q1freddie/tris.md2");
VectorSet (self->mins, -24, -24, -24);
VectorSet (self->maxs, 24, 24, 64);
if (!self->health)
self->health = 500;
if (!self->gib_health)
self->gib_health = -80;
if (!self->mass)
self->mass = 500;
self->pain = freddie_pain;
self->die = freddie_die;
self->flags |= FL_Q1_MONSTER;
self->monsterinfo.stand = freddie_stand;
self->monsterinfo.walk = freddie_walk;
self->monsterinfo.run = freddie_run;
self->monsterinfo.walk = freddie_walk;
self->monsterinfo.dodge = NULL;
self->monsterinfo.attack = freddie_attack;
self->monsterinfo.melee = freddie_melee;
self->monsterinfo.sight = freddie_sight;
self->monsterinfo.search = freddie_stand;
VectorSet (self->muzzle, 0.0f, 0.0f, 0.0f); // attack_offset from original Quake C
self->fog_model = 0; // attack_timer from original Quake C
if (!self->monsterinfo.flies)
self->monsterinfo.flies = 0.25;
// Lazarus
if (self->powerarmor)
{
if (self->powerarmortype == 1)
self->monsterinfo.power_armor_type = POWER_ARMOR_SCREEN;
else
self->monsterinfo.power_armor_type = POWER_ARMOR_SHIELD;
self->monsterinfo.power_armor_power = self->powerarmor;
}
self->common_name = "Freddie";
self->class_id = ENTITY_MONSTER_Q1_FREDDIE;
gi.linkentity (self);
self->monsterinfo.currentmove = &freddie_move_stand;
self->monsterinfo.scale = MODEL_SCALE;
walkmonster_start (self);
}

161
missionpack/m_q1freddie.h Normal file
View file

@ -0,0 +1,161 @@
// FREDDIE
#define FRAME_run1 0
#define FRAME_run2 1
#define FRAME_run3 2
#define FRAME_run4 3
#define FRAME_run5 4
#define FRAME_run6 5
#define FRAME_run7 6
#define FRAME_run8 7
#define FRAME_run9 8
#define FRAME_run10 9
#define FRAME_run11 10
#define FRAME_run12 11
#define FRAME_run13 12
#define FRAME_run14 13
#define FRAME_run15 14
#define FRAME_run16 15
#define FRAME_rfire1 16
#define FRAME_rfire2 17
#define FRAME_rfire3 18
#define FRAME_rfire4 19
#define FRAME_rfire5 20
#define FRAME_rfire6 21
#define FRAME_rfire7 22
#define FRAME_rfire8 23
#define FRAME_rfire9 24
#define FRAME_rfire10 25
#define FRAME_rfire11 26
#define FRAME_rfire12 27
#define FRAME_rfire13 28
#define FRAME_rfire14 29
#define FRAME_rfire15 30
#define FRAME_rfire16 31
#define FRAME_sfire1 32
#define FRAME_sfire2 33
#define FRAME_sfire3 34
#define FRAME_sfire4 35
#define FRAME_sfire5 36
#define FRAME_sfire6 37
#define FRAME_sfire7 38
#define FRAME_sfire8 39
#define FRAME_sfire9 40
#define FRAME_sfire10 41
#define FRAME_sfire11 42
#define FRAME_sfire12 43
#define FRAME_sfire13 44
#define FRAME_sfire14 45
#define FRAME_sfire15 46
#define FRAME_sfire16 47
#define FRAME_sfire17 48
#define FRAME_sfire18 49
#define FRAME_sfire19 50
#define FRAME_sfire20 51
#define FRAME_sfire21 52
#define FRAME_sfire22 53
#define FRAME_sfire23 54
#define FRAME_sfire24 55
#define FRAME_sfire25 56
#define FRAME_sfire26 57
#define FRAME_sfire27 58
#define FRAME_sfire28 59
#define FRAME_pain1 60
#define FRAME_pain2 61
#define FRAME_pain3 62
#define FRAME_pain4 63
#define FRAME_pain5 64
#define FRAME_pain6 65
#define FRAME_pain7 66
#define FRAME_pain8 67
#define FRAME_pain9 68
#define FRAME_pain10 69
#define FRAME_pain11 70
#define FRAME_pain12 71
#define FRAME_painb1 72
#define FRAME_painb2 73
#define FRAME_painb3 74
#define FRAME_painb4 75
#define FRAME_painb5 76
#define FRAME_fswing1 77
#define FRAME_fswing2 78
#define FRAME_fswing3 79
#define FRAME_fswing4 80
#define FRAME_fswing5 81
#define FRAME_fswing6 82
#define FRAME_fswing7 83
#define FRAME_fswing8 84
#define FRAME_fswing9 85
#define FRAME_fswing10 86
#define FRAME_fswing11 87
#define FRAME_fswinge1 88
#define FRAME_fswinge2 89
#define FRAME_fswinge3 90
#define FRAME_fswinge4 91
#define FRAME_fswinge5 92
#define FRAME_fswinge6 93
#define FRAME_fswinge7 94
#define FRAME_fswinge8 95
#define FRAME_fswinge9 96
#define FRAME_fswinge10 97
#define FRAME_bswing1 98
#define FRAME_bswing2 99
#define FRAME_bswing3 100
#define FRAME_bswing4 101
#define FRAME_bswing5 102
#define FRAME_bswing6 103
#define FRAME_bswing7 104
#define FRAME_bswing8 105
#define FRAME_bswing9 106
#define FRAME_bswing10 107
#define FRAME_bswing11 108
#define FRAME_bswing12 109
#define FRAME_bswing13 110
#define FRAME_bswing14 111
#define FRAME_death1 112
#define FRAME_death2 113
#define FRAME_death3 114
#define FRAME_death4 115
#define FRAME_death5 116
#define FRAME_death6 117
#define FRAME_death7 118
#define FRAME_death8 119
#define FRAME_death9 120
#define FRAME_death10 121
#define FRAME_death11 122
#define FRAME_death12 123
#define FRAME_death13 124
#define FRAME_death14 125
#define FRAME_death15 126
#define FRAME_death16 127
#define FRAME_death17 128
#define FRAME_death18 129
#define FRAME_death19 130
#define FRAME_death20 131
#define FRAME_death21 132
#define FRAME_death22 133
#define FRAME_death23 134
#define FRAME_death24 135
#define FRAME_death25 136
#define FRAME_death26 137
#define FRAME_death27 138
#define FRAME_death28 139
#define FRAME_death29 140
#define FRAME_death30 141
#define FRAME_death31 142
#define FRAME_death32 143
#define FRAME_death33 144
#define FRAME_death34 145
#define FRAME_death35 146
#define FRAME_base1 147
#define FRAME_base2 148
#define FRAME_stand1 149
#define FRAME_stand2 150
#define FRAME_stand3 151
#define FRAME_stand4 152
#define FRAME_stand5 153
#define FRAME_stand6 153
#define FRAME_stand7 155
#define FRAME_stand8 156
#define MODEL_SCALE 1.000000

View file

@ -14,6 +14,7 @@ static int sound_sight;
static int sound_pain1;
static int sound_pain2;
static int sound_death;
static int sound_gib;
static int sound_attack;
@ -361,7 +362,7 @@ void q1grunt_die (edict_t *self, edict_t *inflictor, edict_t *attacker, int dama
// check for gib
if (self->health <= self->gib_health && !(self->spawnflags & SF_MONSTER_NOGIB))
{
gi.sound (self, CHAN_VOICE|CHAN_RELIABLE, gi.soundindex ("q1player/udeath.wav"), 1, ATTN_NORM, 0);
gi.sound (self, CHAN_VOICE|CHAN_RELIABLE, sound_gib, 1, ATTN_NORM, 0);
// if dead body, don't drop pack when gibbed
// if (self->deadflag != DEAD_DEAD)
@ -411,11 +412,16 @@ void SP_monster_q1_grunt (edict_t *self)
sound_pain1 = gi.soundindex ("q1grunt/pain1.wav");
sound_pain2 = gi.soundindex ("q1grunt/pain2.wav");
sound_death = gi.soundindex ("q1grunt/death1.wav");
sound_gib = gi.soundindex ("q1player/udeath.wav");
sound_attack = gi.soundindex ("q1grunt/sattck1.wav");
// precache backpack
gi.modelindex ("models/items/q1backpack/tris.md2");
// gi.soundindex ("q1weapons/lock4.wav");
// precache gibs
gi.modelindex ("models/monsters/q1grunt/head/tris.md2");
gi.modelindex ("models/objects/q1gibs/q1gib1/tris.md2");
gi.modelindex ("models/objects/q1gibs/q1gib2/tris.md2");
self->movetype = MOVETYPE_STEP;
self->solid = SOLID_BBOX;

View file

@ -12,7 +12,9 @@ QUAKE HELL KNIGHT
static int sound_sword1;
static int sound_sword2;
static int sound_flame;
static int sound_death;
static int sound_gib;
static int sound_idle;
static int sound_pain;
static int sound_sight;
@ -363,7 +365,7 @@ void hknight_die (edict_t *self, edict_t *inflictor, edict_t *attacker, int dama
if (self->health <= self->gib_health && !(self->spawnflags & SF_MONSTER_NOGIB))
{
gi.sound (self, CHAN_VOICE|CHAN_RELIABLE, gi.soundindex ("q1player/udeath.wav"), 1, ATTN_NORM, 0);
gi.sound (self, CHAN_VOICE|CHAN_RELIABLE, sound_gib, 1, ATTN_NORM, 0);
for (n= 0; n < 2; n++)
ThrowGib (self, "models/objects/q1gibs/q1gib3/tris.md2", damage, GIB_ORGANIC);
@ -450,7 +452,7 @@ void hknight_fire_flame (edict_t *self)
//vec = VectorNormalizeFastf(
gi.sound (self, CHAN_WEAPON, gi.soundindex ("q1hknight/attack1.wav"), 1, ATTN_NORM, 0);
gi.sound (self, CHAN_WEAPON, sound_flame, 1, ATTN_NORM, 0);
q1_fire_flame (self, start, v_forward, 0);
}
@ -492,12 +494,21 @@ void SP_monster_q1_hknight (edict_t *self)
return;
}
sound_death = gi.soundindex ("q1hknight/death1.wav");
sound_pain = gi.soundindex ("q1hknight/pain1.wav");
sound_idle = gi.soundindex ("q1hknight/idle.wav");
sound_sight = gi.soundindex ("q1hknight/sight1.wav");
sound_sword1 = gi.soundindex ("q1hknight/slash1.wav");
sound_sword2 = gi.soundindex ("q1hknight/slash1.wav");
sound_death = gi.soundindex ("q1hknight/death1.wav");
sound_gib = gi.soundindex ("q1player/udeath.wav");
sound_pain = gi.soundindex ("q1hknight/pain1.wav");
sound_idle = gi.soundindex ("q1hknight/idle.wav");
sound_sight = gi.soundindex ("q1hknight/sight1.wav");
sound_sword1 = gi.soundindex ("q1hknight/slash1.wav");
sound_sword2 = gi.soundindex ("q1hknight/slash1.wav");
sound_flame = gi.soundindex ("q1hknight/attack1.wav");
// precache gibs
gi.modelindex ("models/monsters/q1hknight/head/tris.md2");
gi.modelindex ("models/objects/q1gibs/q1gib1/tris.md2");
gi.modelindex ("models/objects/q1gibs/q1gib3/tris.md2");
// precache flame
q1_flame_precache ();
self->movetype = MOVETYPE_STEP;
self->solid = SOLID_BBOX;

View file

@ -13,6 +13,7 @@ QUAKE KNIGHT
static int sound_sword1;
static int sound_sword2;
static int sound_death;
static int sound_gib;
static int sound_pain;
static int sound_idle;
static int sound_sight;
@ -368,7 +369,7 @@ void knight_die (edict_t *self, edict_t *inflictor, edict_t *attacker, int damag
if (self->health <= self->gib_health && !(self->spawnflags & SF_MONSTER_NOGIB))
{
gi.sound (self, CHAN_VOICE|CHAN_RELIABLE, gi.soundindex ("q1player/udeath.wav"), 1, ATTN_NORM, 0);
gi.sound (self, CHAN_VOICE|CHAN_RELIABLE, sound_gib, 1, ATTN_NORM, 0);
for (n= 0; n < 2; n++)
ThrowGib (self, "models/objects/q1gibs/q1gib3/tris.md2", damage, GIB_ORGANIC);
@ -408,12 +409,18 @@ void SP_monster_q1_knight (edict_t *self)
return;
}
sound_sword1 = gi.soundindex ("q1knight/sword1.wav");
sound_sword2 = gi.soundindex ("q1knight/sword2.wav");
sound_death = gi.soundindex ("q1knight/kdeath.wav");
sound_pain = gi.soundindex ("q1knight/khurt.wav");
sound_idle = gi.soundindex ("q1knight/idle.wav");
sound_sight = gi.soundindex ("q1knight/ksight.wav");
sound_sword1 = gi.soundindex ("q1knight/sword1.wav");
sound_sword2 = gi.soundindex ("q1knight/sword2.wav");
sound_death = gi.soundindex ("q1knight/kdeath.wav");
sound_gib = gi.soundindex ("q1player/udeath.wav");
sound_pain = gi.soundindex ("q1knight/khurt.wav");
sound_idle = gi.soundindex ("q1knight/idle.wav");
sound_sight = gi.soundindex ("q1knight/ksight.wav");
// precache gibs
gi.modelindex ("models/monsters/q1knight/head/tris.md2");
gi.modelindex ("models/objects/q1gibs/q1gib1/tris.md2");
gi.modelindex ("models/objects/q1gibs/q1gib3/tris.md2");
self->movetype = MOVETYPE_STEP;
self->solid = SOLID_BBOX;

View file

@ -11,15 +11,17 @@ QUAKE OGRE
static int sound_pain;
static int sound_death;
static int sound_gib;
static int sound_idle;
static int sound_idle2;
static int sound_wake;
static int sound_shoot;
static int sound_saw;
static int sound_drag;
void ogre_check_refire (edict_t *self);
void ogre_attack(edict_t *self);
void ogre_attack (edict_t *self);
void ogre_idle_sound1 (edict_t *self)
{
@ -36,12 +38,12 @@ void ogre_idle_sound2 (edict_t *self)
void ogre_sight (edict_t *self, edict_t *other)
{
gi.sound (self, CHAN_VOICE, sound_wake, 1, ATTN_NORM, 0);
ogre_attack(self);
ogre_attack (self);
}
void ogre_drag_sound (edict_t *self)
{
//if(anglemod(self->s.angles[YAW]) != self->ideal_yaw)
//if (anglemod(self->s.angles[YAW]) != self->ideal_yaw)
if (random() < 0.2)
gi.sound (self, CHAN_VOICE, sound_drag, 1, ATTN_IDLE, 0);
}
@ -100,15 +102,14 @@ void ogre_walk (edict_t *self)
mframe_t ogre_frames_run [] =
{
ai_run, 9, NULL,
ai_run, 12,NULL,
ai_run, 12, NULL,
ai_run, 8, NULL,
ai_run, 22,NULL,
ai_run, 16,NULL,
ai_run, 22, NULL,
ai_run, 16, NULL,
ai_run, 4, NULL,
ai_run, 13,ogre_attack,
ai_run, 24,NULL
ai_run, 13, ogre_attack,
ai_run, 24, NULL
};
mmove_t ogre_move_run = {FRAME_run1, FRAME_run8, ogre_frames_run, NULL};
@ -199,11 +200,10 @@ void ogre_pain (edict_t *self, edict_t *other, float kick, int damage)
{
float r;
if (level.time < self->pain_debounce_time)
return;
r=random();
r = random();
if (self->health > 0)
gi.sound (self, CHAN_VOICE, sound_pain, 1, ATTN_NORM, 0);
@ -313,17 +313,17 @@ void ogre_die (edict_t *self, edict_t *inflictor, edict_t *attacker, int damage,
int n;
// check for gib
if (self->health <= self->gib_health && !(self->spawnflags & SF_MONSTER_NOGIB))
if ( (self->health <= self->gib_health) && !(self->spawnflags & SF_MONSTER_NOGIB) )
{
gi.sound (self, CHAN_VOICE|CHAN_RELIABLE, gi.soundindex ("q1player/udeath.wav"), 1, ATTN_NORM, 0);
gi.sound (self, CHAN_VOICE|CHAN_RELIABLE, sound_gib, 1, ATTN_NORM, 0);
// if dead body, don't drop pack when gibbed
// if (self->deadflag != DEAD_DEAD)
// ogre_droprockets(self);
for (n= 0; n < 2; n++)
for (n = 0; n < 2; n++)
ThrowGib (self, "models/objects/q1gibs/q1gib1/tris.md2", damage, GIB_ORGANIC);
for (n= 0; n < 4; n++)
for (n = 0; n < 4; n++)
ThrowGib (self, "models/objects/q1gibs/q1gib3/tris.md2", damage, GIB_ORGANIC);
ThrowHead (self, "models/monsters/q1ogre/head/tris.md2", damage, GIB_ORGANIC);
self->deadflag = DEAD_DEAD;
@ -338,14 +338,14 @@ void ogre_die (edict_t *self, edict_t *inflictor, edict_t *attacker, int damage,
self->deadflag = DEAD_DEAD;
self->takedamage = DAMAGE_YES;
if(random() < 0.5)
if (random() < 0.5)
self->monsterinfo.currentmove = &ogre_move_death1;
else
self->monsterinfo.currentmove = &ogre_move_death2;
}
void ogre_grenade_fire(edict_t *self)
void ogre_grenade_fire (edict_t *self)
{
vec3_t start;
@ -359,10 +359,10 @@ void ogre_grenade_fire(edict_t *self)
// project enemy back a bit and target there
VectorCopy (self->enemy->s.origin, target);
//if(range(self,self->enemy) > RANGE_MID)
//if (range(self,self->enemy) > RANGE_MID)
VectorMA (target, -0.1, self->enemy->velocity, target);
if(range(self,self->enemy) > RANGE_MID)
if (range(self,self->enemy) > RANGE_MID)
target[2] += self->enemy->viewheight;
else
target[2] += self->enemy->viewheight*0.8;
@ -375,7 +375,7 @@ void ogre_grenade_fire(edict_t *self)
gi.WriteByte (MZ_MACHINEGUN | 128);
gi.multicast (self->s.origin, MULTICAST_PVS);
gi.sound (self, CHAN_WEAPON|CHAN_RELIABLE, gi.soundindex("q1weapons/grenade.wav"), 1.0, ATTN_NORM, 0);
gi.sound (self, CHAN_WEAPON|CHAN_RELIABLE, sound_shoot, 1.0, ATTN_NORM, 0);
q1_fire_grenade (self, start,aim,40 , 600, 2.5, 80);
}
@ -414,9 +414,9 @@ void ogre_check_refire (edict_t *self)
if (!self->enemy || !self->enemy->inuse || self->enemy->health <= 0)
return;
if (skill->value == 3|| (range(self, self->enemy) == RANGE_MELEE))
if ( (skill->value == 3) || (range(self, self->enemy) == RANGE_MELEE))
{
if(random() > 0.5)
if (random() > 0.5)
self->monsterinfo.nextframe = FRAME_swing1;
else
self->monsterinfo.nextframe = FRAME_smash1;
@ -426,7 +426,7 @@ void ogre_check_refire (edict_t *self)
}
/*static*/ void ogre_sawswingsound(edict_t *self)
/*static*/ void ogre_sawswingsound (edict_t *self)
{
gi.sound (self, CHAN_WEAPON, sound_saw, 1, ATTN_NORM, 0);
}
@ -478,25 +478,25 @@ mframe_t ogre_frames_attack_grenade [] =
ai_charge, 0, NULL,
ai_charge, 0, ogre_grenade_fire,
ai_charge, 0, NULL,
ai_charge, 0, NULL //ogre_attack
ai_charge, 0, NULL // ogre_attack
};
mmove_t ogre_move_attack_grenade = {FRAME_shoot1, FRAME_shoot6, ogre_frames_attack_grenade, ogre_run};
void ogre_attack(edict_t *self)
void ogre_attack (edict_t *self)
{
int r;
if(!self->enemy)
if (!self->enemy)
return;
r = range(self,self->enemy);
r = range(self, self->enemy);
if (r == RANGE_MELEE)
{
self->monsterinfo.currentmove = &ogre_move_swing_attack;
}
else if(visible(self,self->enemy) && infront(self,self->enemy)
else if (visible(self,self->enemy) && infront(self,self->enemy)
&& (r < RANGE_FAR) && !(self->monsterinfo.aiflags & AI_SOUND_TARGET))
{
self->monsterinfo.currentmove = &ogre_move_attack_grenade;
@ -510,7 +510,7 @@ void ogre_attack(edict_t *self)
// SPAWN
//
/*QUAKED monster_q1_ogre (1 .5 0) (-20 -20 -24) (20 20 32) Ambush Trigger_Spawn Sight
/*QUAKED monster_q1_ogre (1 .5 0) (-20 -20 -24) (20 20 32) Ambush Trigger_Spawn Sight GoodGuy NoGib
model="models/monsters/q1ogre/tris.md2"
*/
void SP_monster_q1_ogre (edict_t *self)
@ -523,15 +523,23 @@ void SP_monster_q1_ogre (edict_t *self)
sound_pain = gi.soundindex ("q1ogre/ogpain1.wav");
sound_death = gi.soundindex ("q1ogre/ogdth.wav");
sound_gib = gi.soundindex ("q1player/udeath.wav");
sound_idle = gi.soundindex ("q1ogre/ogidle.wav");
sound_idle2 = gi.soundindex ("q1ogre/ogidle2.wav");
sound_wake = gi.soundindex ("q1ogre/ogwake.wav");
sound_shoot = gi.soundindex ("q1weapons/grenade.wav");
sound_saw = gi.soundindex ("q1ogre/ogsawatk.wav");
sound_drag = gi.soundindex ("q1ogre/ogdrag.wav");
// precache backpack
gi.modelindex ("models/items/q1backpack/tris.md2");
// gi.soundindex ("q1weapons/lock4.wav");
// precache gibs
gi.modelindex ("models/monsters/q1ogre/head/tris.md2");
gi.modelindex ("models/objects/q1gibs/q1gib1/tris.md2");
gi.modelindex ("models/objects/q1gibs/q1gib3/tris.md2");
// precache grenade
q1_grenade_precache ();
self->movetype = MOVETYPE_STEP;
self->solid = SOLID_BBOX;

View file

@ -18,6 +18,7 @@ static int sound_idle1;
static int sound_idle2;
static int sound_attack;
static int sound_die;
static int sound_gib;
static int sound_pain;
static int sound_hit;
@ -197,9 +198,9 @@ void scrag_die (edict_t *self, edict_t *inflictor, edict_t *attacker, int damage
if (self->health <= self->gib_health && !(self->spawnflags & SF_MONSTER_NOGIB))
{
gi.sound (self, CHAN_VOICE|CHAN_RELIABLE, gi.soundindex ("q1player/udeath.wav"), 1, ATTN_NORM, 0);
gi.sound (self, CHAN_VOICE|CHAN_RELIABLE, sound_gib, 1, ATTN_NORM, 0);
for (n= 0; n < 3; n++)
for (n = 0; n < 3; n++)
ThrowGib (self, "models/objects/q1gibs/q1gib2/tris.md2", damage, GIB_ORGANIC);
ThrowHead (self, "models/monsters/q1scrag/head/tris.md2", damage, GIB_ORGANIC);
self->deadflag = DEAD_DEAD;
@ -337,14 +338,21 @@ void SP_monster_q1_scrag (edict_t *self)
return;
}
sound_sight = gi.soundindex ("q1scrag/wsight.wav");
sound_idle1 = gi.soundindex ("q1scrag/widle1.wav");
sound_idle2 = gi.soundindex ("q1scrag/widle2.wav");
sound_attack = gi.soundindex ("q1scrag/wattack.wav");
sound_die = gi.soundindex ("q1scrag/wdeath.wav");
sound_pain = gi.soundindex ("q1scrag/wpain.wav");
sound_hit = gi.soundindex ("q1scrag/hit.wav");
sound_sight = gi.soundindex ("q1scrag/wsight.wav");
sound_idle1 = gi.soundindex ("q1scrag/widle1.wav");
sound_idle2 = gi.soundindex ("q1scrag/widle2.wav");
sound_attack = gi.soundindex ("q1scrag/wattack.wav");
sound_die = gi.soundindex ("q1scrag/wdeath.wav");
sound_gib = gi.soundindex ("q1player/udeath.wav");
sound_pain = gi.soundindex ("q1scrag/wpain.wav");
sound_hit = gi.soundindex ("q1scrag/hit.wav");
// precache gibs
gi.modelindex ("models/monsters/q1scrag/head/tris.md2");
gi.modelindex ("models/objects/q1gibs/q1gib2/tris.md2");
// precache acidspit
q1_acidspit_precache ();
self->movetype = MOVETYPE_STEP;
self->solid = SOLID_BBOX;

View file

@ -10,9 +10,11 @@ QUAKE SHALRATH
#include "m_q1shalrath.h"
static int sound_death;
static int sound_gib;
static int sound_sight;
static int sound_pain1;
static int sound_attack;
static int sound_attack2;
static int sound_idle;
@ -161,7 +163,7 @@ void q1shalrath_fire (edict_t *self)
VectorSubtract (end, start, aim);
VectorNormalize (aim);
gi.sound (self, CHAN_WEAPON|CHAN_RELIABLE, gi.soundindex("shalrath/attack2.wav"), 1, ATTN_NORM, 0);
gi.sound (self, CHAN_WEAPON|CHAN_RELIABLE, sound_attack2, 1, ATTN_NORM, 0);
q1_fire_firepod (self, aim);
}
@ -238,14 +240,17 @@ mmove_t q1shalrath_move_death = {FRAME_death1, FRAME_death7, q1shalrath_frames_d
void q1shalrath_die (edict_t *self, edict_t *inflictor, edict_t *attacker, int damage, vec3_t point)
{
int n;
// check for gib
if (self->health <= self->gib_health && !(self->spawnflags & SF_MONSTER_NOGIB))
{
gi.sound (self, CHAN_VOICE|CHAN_RELIABLE, gi.soundindex ("q1player/udeath.wav"), 1, ATTN_NORM, 0);
gi.sound (self, CHAN_VOICE|CHAN_RELIABLE, sound_gib, 1, ATTN_NORM, 0);
for (n = 0; n < 2; n++)
ThrowGib (self, "models/objects/q1gibs/q1gib1/tris.md2", damage, GIB_ORGANIC);
ThrowGib (self, "models/objects/q1gibs/q1gib2/tris.md2", damage, GIB_ORGANIC);
for (n = 0; n < 2; n++)
ThrowGib (self, "models/objects/q1gibs/q1gib3/tris.md2", damage, GIB_ORGANIC);
ThrowHead (self, "models/monsters/q1shalrath/head/tris.md2", damage, GIB_ORGANIC);
self->deadflag = DEAD_DEAD;
return;
@ -280,10 +285,20 @@ void SP_monster_q1_shalrath (edict_t *self)
sound_sight = gi.soundindex ("q1shalrath/sight.wav");
sound_pain1 = gi.soundindex ("q1shalrath/pain.wav");
sound_gib = gi.soundindex ("q1player/udeath.wav");
sound_death = gi.soundindex ("q1shalrath/death.wav");
sound_attack = gi.soundindex ("q1shalrath/attack.wav");
sound_attack2 = gi.soundindex ("shalrath/attack2.wav");
sound_idle = gi.soundindex ("q1shalrath/idle.wav");
// precache gibs
gi.modelindex ("models/monsters/q1shalrath/head/tris.md2");
gi.modelindex ("models/objects/q1gibs/q1gib1/tris.md2");
gi.modelindex ("models/objects/q1gibs/q1gib2/tris.md2");
gi.modelindex ("models/objects/q1gibs/q1gib3/tris.md2");
// precache firepod
q1_firepod_precache ();
self->movetype = MOVETYPE_STEP;
self->solid = SOLID_BBOX;

View file

@ -17,6 +17,7 @@ static int sound_attack;
static int sound_boom; // ?
static int sound_pain;
static int sound_death;
static int sound_gib;
static int sound_idle;
static int sound_sight;
@ -202,13 +203,16 @@ mmove_t shambler_move_death = {FRAME_death1, FRAME_death11, shambler_frames_deat
void shambler_die (edict_t *self, edict_t *inflictor, edict_t *attacker, int damage, vec3_t point)
{
int n;
// check for gib
if (self->health <= self->gib_health && !(self->spawnflags & SF_MONSTER_NOGIB))
{
gi.sound (self, CHAN_VOICE|CHAN_RELIABLE, gi.soundindex ("q1player/udeath.wav"), 1, ATTN_NORM, 0);
ThrowGib (self, "models/objects/q1gibs/q1gib1/tris.md2", damage, GIB_ORGANIC);
ThrowGib (self, "models/objects/q1gibs/q1gib3/tris.md2", damage, GIB_ORGANIC);
gi.sound (self, CHAN_VOICE|CHAN_RELIABLE, sound_gib, 1, ATTN_NORM, 0);
for (n = 0; n < 2; n++)
ThrowGib (self, "models/objects/q1gibs/q1gib1/tris.md2", damage, GIB_ORGANIC);
for (n = 0; n < 4; n++)
ThrowGib (self, "models/objects/q1gibs/q1gib3/tris.md2", damage, GIB_ORGANIC);
ThrowGib (self, "models/objects/q1gibs/q1gib2/tris.md2", damage, GIB_ORGANIC);
ThrowHead (self, "models/monsters/q1shambler/head/tris.md2", damage, GIB_ORGANIC);
self->deadflag = DEAD_DEAD;
@ -517,15 +521,22 @@ void SP_monster_q1_shambler (edict_t *self)
return;
}
sound_melee1 = gi.soundindex ("q1shambler/melee1.wav");
sound_melee2 = gi.soundindex ("q1shambler/melee1.wav");
sound_melee3 = gi.soundindex ("q1shambler/smack.wav");
sound_attack = gi.soundindex ("q1shambler/sattck1.wav");
sound_boom = gi.soundindex ("q1shambler/sboom.wav");
sound_pain = gi.soundindex ("q1shambler/shurt2.wav");
sound_death = gi.soundindex ("q1shambler/sdeath.wav");
sound_idle = gi.soundindex ("q1shambler/sidle.wav");
sound_sight = gi.soundindex ("q1shambler/ssight.wav");
sound_melee1 = gi.soundindex ("q1shambler/melee1.wav");
sound_melee2 = gi.soundindex ("q1shambler/melee1.wav");
sound_melee3 = gi.soundindex ("q1shambler/smack.wav");
sound_attack = gi.soundindex ("q1shambler/sattck1.wav");
sound_boom = gi.soundindex ("q1shambler/sboom.wav");
sound_pain = gi.soundindex ("q1shambler/shurt2.wav");
sound_death = gi.soundindex ("q1shambler/sdeath.wav");
sound_gib = gi.soundindex ("q1player/udeath.wav");
sound_idle = gi.soundindex ("q1shambler/sidle.wav");
sound_sight = gi.soundindex ("q1shambler/ssight.wav");
// precache gibs
gi.modelindex ("models/monsters/q1shambler/head/tris.md2");
gi.modelindex ("models/objects/q1gibs/q1gib1/tris.md2");
gi.modelindex ("models/objects/q1gibs/q1gib2/tris.md2");
gi.modelindex ("models/objects/q1gibs/q1gib3/tris.md2");
self->movetype = MOVETYPE_STEP;
self->solid = SOLID_BBOX;

View file

@ -607,11 +607,14 @@ void q1zombie_sight(edict_t *self, edict_t *other)
void q1zombie_die (edict_t *self, edict_t *inflictor, edict_t *attacker, int damage, vec3_t point)
{
// gi.sound (self, CHAN_VOICE, sound_gib, 1, ATTN_NORM, 0);
gi.sound (self, CHAN_VOICE, gi.soundindex ("q1zombie/z_gib.wav"), 1, ATTN_NORM, 0);
ThrowGib (self, "models/objects/q1gibs/q1gib1/tris.md2", damage, GIB_ORGANIC);
int n;
gi.sound (self, CHAN_VOICE, sound_gib, 1, ATTN_NORM, 0);
for (n = 0; n < 2; n++)
ThrowGib (self, "models/objects/q1gibs/q1gib1/tris.md2", damage, GIB_ORGANIC);
ThrowGib (self, "models/objects/q1gibs/q1gib2/tris.md2", damage, GIB_ORGANIC);
ThrowGib (self, "models/objects/q1gibs/q1gib3/tris.md2", damage, GIB_ORGANIC);
for (n = 0; n < 2; n++)
ThrowGib (self, "models/objects/q1gibs/q1gib3/tris.md2", damage, GIB_ORGANIC);
ThrowHead (self, "models/monsters/q1zombie/head/tris.md2", damage*2, GIB_ORGANIC);
self->deadflag = DEAD_DEAD;
self->takedamage = DAMAGE_NO;
@ -653,6 +656,14 @@ void SP_monster_q1_zombie (edict_t *self)
sound_gib = gi.soundindex ("q1zombie/z_gib.wav");
sound_shot = gi.soundindex ("q1zombie/z_shot1.wav");
// precache gibs
gi.modelindex ("models/monsters/q1zombie/head/tris.md2");
gi.modelindex ("models/objects/q1gibs/q1gib1/tris.md2");
gi.modelindex ("models/objects/q1gibs/q1gib2/tris.md2");
gi.modelindex ("models/objects/q1gibs/q1gib3/tris.md2");
// precache projectile gib
q1_gib_precache ();
self->movetype = MOVETYPE_STEP;
self->solid = SOLID_BBOX;

View file

@ -654,7 +654,7 @@ void BossExplode (edict_t *self)
case 9:
self->s.sound = 0;
//Knightmare- big explosion
// Knightmare- big explosion
gi.WriteByte (svc_temp_entity);
gi.WriteByte (TE_EXPLOSION1_BIG);
gi.WritePosition (org);

View file

@ -145,7 +145,7 @@ mmove_t tank_move_stop_walk = {FRAME_walk21, FRAME_walk25, tank_frames_stop_walk
void tank_walk (edict_t *self)
{
self->monsterinfo.currentmove = &tank_move_walk;
self->monsterinfo.currentmove = &tank_move_walk;
}

702
missionpack/m_vulture.c Normal file
View file

@ -0,0 +1,702 @@
/*
==============================================================================
flyer
==============================================================================
*/
#include "g_local.h"
#include "m_vulture.h"
#define SF_VULTURE_IN_AIR 8
qboolean visible (edict_t *self, edict_t *other);
static int nextmove; // Used for start/stop frames
//static int sound_sight;
static int sound_perch_idle1;
static int sound_perch_idle2;
static int sound_perch_idle3;
static int sound_soar_idle1;
static int sound_soar_idle2;
static int sound_soar_idle3;
static int sound_flap1;
static int sound_flap2;
static int sound_flap3;
static int sound_peck1;
static int sound_peck2;
static int sound_peck3;
static int sound_pain1;
static int sound_pain2;
static int sound_death;
void vulture_run (edict_t *self);
void vulture_sight (edict_t *self, edict_t *other)
{
// gi.sound (self, CHAN_VOICE, sound_sight, 1, ATTN_NORM, 0);
}
void vulture_perch_idle (edict_t *self)
{
float r;
if (random() < 0.3f)
{
r = random();
if (r < 0.33f)
gi.sound (self, CHAN_VOICE, sound_perch_idle1, 1, ATTN_IDLE, 0);
else if (r < 0.67f)
gi.sound (self, CHAN_VOICE, sound_perch_idle2, 1, ATTN_IDLE, 0);
else
gi.sound (self, CHAN_VOICE, sound_perch_idle3, 1, ATTN_IDLE, 0);
}
}
void vulture_soar_idle (edict_t *self)
{
float r;
if (random() < 0.3f)
{
r = random();
if (r < 0.33f)
gi.sound (self, CHAN_VOICE, sound_soar_idle1, 1, ATTN_IDLE, 0);
else if (r < 0.67f)
gi.sound (self, CHAN_VOICE, sound_soar_idle2, 1, ATTN_IDLE, 0);
else
gi.sound (self, CHAN_VOICE, sound_soar_idle3, 1, ATTN_IDLE, 0);
}
}
void vulture_idle (edict_t *self)
{
if (self->flags & FL_FLY)
vulture_soar_idle (self);
else
vulture_perch_idle (self);
}
void vulture_flap (edict_t *self)
{
float r;
if (random() < 0.67f)
{
r = random();
if (r < 0.33f)
gi.sound (self, CHAN_VOICE, sound_flap1, 1, ATTN_IDLE, 0);
else if (r < 0.67f)
gi.sound (self, CHAN_VOICE, sound_flap2, 1, ATTN_IDLE, 0);
else
gi.sound (self, CHAN_VOICE, sound_flap3, 1, ATTN_IDLE, 0);
}
}
//
// perch
//
mframe_t vulture_frames_perch [] =
{
ai_stand, 0, NULL,
ai_stand, 0, NULL,
ai_stand, 0, NULL,
ai_stand, 0, NULL,
ai_stand, 0, NULL,
ai_stand, 0, NULL,
ai_stand, 0, NULL,
ai_stand, 0, NULL,
ai_stand, 0, NULL,
ai_stand, 0, NULL,
ai_stand, 0, NULL,
ai_stand, 0, NULL,
ai_stand, 0, NULL,
ai_stand, 0, NULL,
ai_stand, 0, NULL,
ai_stand, 0, NULL,
ai_stand, 0, NULL,
ai_stand, 0, NULL,
ai_stand, 0, NULL,
ai_stand, 0, NULL,
ai_stand, 0, NULL,
ai_stand, 0, NULL,
ai_stand, 0, NULL,
ai_stand, 0, NULL,
ai_stand, 0, NULL,
ai_stand, 0, NULL,
ai_stand, 0, NULL,
ai_stand, 0, NULL,
ai_stand, 0, NULL,
ai_stand, 0, NULL
};
mmove_t vulture_move_perch = {FRAME_perch1, FRAME_perch30, vulture_frames_perch, NULL};
void vulture_perch (edict_t *self)
{
self->monsterinfo.currentmove = &vulture_move_perch;
}
//
// walk
//
mframe_t vulture_frames_walk [] =
{
ai_walk, 1, NULL,
ai_walk, 1, NULL,
ai_walk, 1, NULL,
ai_walk, 1, NULL,
ai_walk, 1, NULL,
ai_walk, 1, NULL,
ai_walk, 1, NULL,
ai_walk, 1, NULL,
ai_walk, 1, NULL,
ai_walk, 1, NULL
};
mmove_t vulture_move_walk = {FRAME_walk1, FRAME_walk10, vulture_frames_walk, NULL};
//
// soar
//
mframe_t vulture_frames_soar [] =
{
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL,
ai_walk, 5, NULL
};
mmove_t vulture_move_soar = {FRAME_soar1, FRAME_soar42, vulture_frames_soar, NULL};
/*
void vulture_soar (edict_t *self)
{
self->monsterinfo.currentmove = &vulture_move_soar;
}
*/
#if 0
//
// bank right
//
mframe_t vulture_frames_bankright [] =
{
ai_move, 10, NULL,
ai_move, 10, NULL,
ai_move, 10, NULL,
ai_move, 10, NULL,
ai_move, 10, NULL,
ai_move, 10, NULL,
ai_move, 10, NULL,
ai_move, 10, NULL,
ai_move, 10, NULL,
ai_move, 10, NULL
};
//mmove_t vulture_move_bankright = {FRAME_bankR1, FRAME_bankR10, vulture_frames_bankright, NULL};
void vulture_bankright (edict_t *self)
{
self->monsterinfo.currentmove = &vulture_move_bankright;
}
//
// bank left
//
mframe_t vulture_frames_bankleft [] =
{
ai_move, 10, NULL,
ai_move, 10, NULL,
ai_move, 10, NULL,
ai_move, 10, NULL,
ai_move, 10, NULL,
ai_move, 10, NULL,
ai_move, 10, NULL,
ai_move, 10, NULL,
ai_move, 10, NULL,
ai_move, 10, NULL
};
//mmove_t vulture_move_bankleft = {FRAME_bankL1, FRAME_bankL10, vulture_frames_bankleft, NULL};
void vulture_bankleft (edict_t *self)
{
self->monsterinfo.currentmove = &vulture_move_bankleft;
}
#endif
void vulture_walk (edict_t *self)
{
if (self->flags & FL_FLY) {
self->monsterinfo.currentmove = &vulture_move_soar;
}
else {
self->monsterinfo.currentmove = &vulture_move_walk;
}
}
//
// fly
//
mframe_t vulture_frames_fly [] =
{
ai_run, 15, NULL,
ai_run, 15, vulture_flap,
ai_run, 15, NULL,
ai_run, 15, NULL,
ai_run, 15, NULL
};
mmove_t vulture_move_fly = {FRAME_fly1, FRAME_fly5, vulture_frames_fly, NULL};
/*
void vulture_fly (edict_t *self)
{
self->monsterinfo.currentmove = &vulture_move_fly;
}
*/
//
// takeoff
//
void vulture_airborne (edict_t *self)
{
self->flags |= FL_FLY;
// if (self->flags & FL_FLY)
// gi.dprintf ("successfully converted monster_vulture to flying\n");
}
mframe_t vulture_frames_takeoff [] =
{
ai_move, 5, NULL,
ai_move, 5, NULL,
ai_move, 5, NULL,
ai_move, 5, NULL,
ai_move, 5, NULL,
ai_move, 5, vulture_airborne
};
mmove_t vulture_move_takeoff = {FRAME_takeoff1, FRAME_takeoff6, vulture_frames_takeoff, vulture_run};
/*
void vulture_takeoff (edict_t *self)
{
self->monsterinfo.currentmove = &vulture_move_takeoff;
}
*/
//
// land
//
void vulture_landed (edict_t *self)
{
self->flags &= ~FL_FLY;
// if ( !(self->flags & FL_FLY) )
// gi.dprintf ("successfully converted monster_vulture to ground\n");
}
mframe_t vulture_frames_land [] =
{
ai_move, 5, NULL,
ai_move, 5, NULL,
ai_move, 5, NULL,
ai_move, 5, NULL,
ai_move, 5, NULL,
ai_move, 5, NULL,
ai_move, 5, NULL,
ai_move, 5, NULL,
ai_move, 5, NULL,
ai_move, 5, NULL,
ai_move, 5, NULL,
ai_move, 5, NULL,
ai_move, 5, vulture_landed
};
mmove_t vulture_move_land = {FRAME_land1, FRAME_land13, vulture_frames_land, vulture_walk};
/*
void vulture_land (edict_t *self)
{
self->monsterinfo.currentmove = &vulture_move_land;
}
*/
void vulture_run (edict_t *self)
{
if (self->monsterinfo.aiflags & AI_STAND_GROUND)
{
if (self->flags & FL_FLY) {
self->monsterinfo.currentmove = &vulture_move_soar;
}
else {
self->monsterinfo.currentmove = &vulture_move_perch;
}
}
else
{
if (self->flags & FL_FLY) {
self->monsterinfo.currentmove = &vulture_move_fly;
}
else {
// takeoff if we're on ground
self->monsterinfo.currentmove = &vulture_move_takeoff;
}
}
}
//
// melee
//
void vulture_peck (edict_t *self)
{
vec3_t aim;
float r;
VectorSet (aim, MELEE_DISTANCE, self->mins[0], 0);
if ( fire_hit (self, aim, (int)(10 + (random() * 5)), 0) )
{
r = random();
if (r < 0.33f)
gi.sound (self, CHAN_WEAPON, sound_peck1, 1, ATTN_NORM, 0);
else if (r < 0.67f)
gi.sound (self, CHAN_WEAPON, sound_peck2, 1, ATTN_NORM, 0);
else
gi.sound (self, CHAN_WEAPON, sound_peck3, 1, ATTN_NORM, 0);
}
}
mframe_t vulture_frames_melee [] =
{
ai_charge, 0, NULL,
ai_charge, 0, vulture_peck,
ai_charge, 0, NULL,
ai_charge, 0, NULL
};
mmove_t vulture_move_melee = {FRAME_melee1, FRAME_melee4, vulture_frames_melee, vulture_run};
void vulture_melee (edict_t *self)
{
if (level.time < self->touch_debounce_time)
return;
self->touch_debounce_time = level.time + 0.5f;
self->monsterinfo.currentmove = &vulture_move_melee;
}
/*
void vulture_attack (edict_t *self)
{
int r;
if (!self->enemy)
return;
r = range(self, self->enemy);
if (r == RANGE_MELEE)
{
self->monsterinfo.currentmove = &vulture_move_melee;
}
}
*/
//
// pain
//
mframe_t vulture_frames_pain [] =
{
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL
};
mmove_t vulture_move_pain = {FRAME_pain1, FRAME_pain4, vulture_frames_pain, vulture_run};
//
// soar pain
//
mframe_t vulture_frames_soarpain [] =
{
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL
};
mmove_t vulture_move_soarpain = {FRAME_soarpain1, FRAME_soarpain4, vulture_frames_soarpain, vulture_run};
void vulture_pain (edict_t *self, edict_t *other, float kick, int damage)
{
if (level.time < self->pain_debounce_time)
return;
self->pain_debounce_time = level.time + 3;
if (rand() & 1)
gi.sound (self, CHAN_VOICE, sound_pain1, 1, ATTN_NORM, 0);
else
gi.sound (self, CHAN_VOICE, sound_pain2, 1, ATTN_NORM, 0);
if (skill->value == 3)
return; // no pain anims in nightmare
if (self->flags & FL_FLY)
self->monsterinfo.currentmove = &vulture_move_soarpain;
else
self->monsterinfo.currentmove = &vulture_move_pain;
}
//
// death
//
void vulture_dead (edict_t *self)
{
VectorSet (self->mins, -8, -8, -8);
VectorSet (self->maxs, 8, 8, 8);
self->movetype = MOVETYPE_TOSS;
self->svflags |= SVF_DEADMONSTER;
self->nextthink = 0;
gi.linkentity (self);
M_FlyCheck (self);
// Lazarus monster fade
if (world->effects & FX_WORLDSPAWN_CORPSEFADE)
{
self->think = FadeDieSink;
self->nextthink = level.time + corpse_fadetime->value;
}
}
mframe_t vulture_frames_death [] =
{
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL
};
mmove_t vulture_move_death = {FRAME_die1, FRAME_die4, vulture_frames_death, vulture_dead};
//
// soar death
//
mframe_t vulture_frames_soardeath [] =
{
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL,
ai_move, 0, NULL
};
mmove_t vulture_move_soardeath = {FRAME_soardie1, FRAME_soardie30, vulture_frames_soardeath, vulture_dead};
void vulture_die (edict_t *self, edict_t *inflictor, edict_t *attacker, int damage, vec3_t point)
{
int n;
// check for gib
if ( (self->health <= self->gib_health) && !(self->spawnflags & 32) )
{
gi.sound (self, CHAN_VOICE|CHAN_RELIABLE, gi.soundindex ("misc/udeath.wav"), 1, ATTN_NORM, 0);
for (n = 0; n < 4; n++)
ThrowGib (self, "models/monsters/vulture/feather1.md2", damage, GIB_FEATHER);
for (n = 0; n < 4; n++)
ThrowGib (self, "models/monsters/vulture/feather2.md2", damage, GIB_FEATHER);
ThrowGib (self, "models/objects/gibs/bone/tris.md2", damage, GIB_ORGANIC);
ThrowHead (self, "models/objects/gibs/bone2/tris.md2", damage, GIB_ORGANIC);
self->deadflag = DEAD_DEAD;
return;
}
if (self->deadflag == DEAD_DEAD)
return;
// regular death
gi.sound (self, CHAN_VOICE, sound_death, 1, ATTN_NORM, 0);
self->deadflag = DEAD_DEAD;
self->takedamage = DAMAGE_YES;
if (self->flags & FL_FLY)
self->monsterinfo.currentmove = &vulture_move_soardeath;
else
self->monsterinfo.currentmove = &vulture_move_death;;
}
/*QUAKED monster_vulture (1 .5 0) (-8 -8 -8) (8 8 8) Ambush Trigger_Spawn Sight InAir GoodGuy NoGib
*/
void SP_monster_vulture (edict_t *self)
{
if (deathmatch->value)
{
G_FreeEdict (self);
return;
}
// sound_sight = gi.soundindex ("vulture/sight1.wav");
sound_perch_idle1 = gi.soundindex ("vulture/perch_idle1.wav");
sound_perch_idle2 = gi.soundindex ("vulture/perch_idle2.wav");
sound_perch_idle3 = gi.soundindex ("vulture/perch_idle3.wav");
sound_soar_idle1 = gi.soundindex ("vulture/soar_idle1.wav");
sound_soar_idle2 = gi.soundindex ("vulture/soar_idle2.wav");
sound_soar_idle3 = gi.soundindex ("vulture/soar_idle3.wav");
sound_flap1 = gi.soundindex ("vulture/flap1.wav");
sound_flap2 = gi.soundindex ("vulture/flap2.wav");
sound_flap3 = gi.soundindex ("vulture/flap3.wav");
sound_peck1 = gi.soundindex ("vulture/peck1.wav");
sound_peck2 = gi.soundindex ("vulture/peck2.wav");
sound_peck3 = gi.soundindex ("vulture/peck3.wav");
sound_pain1 = gi.soundindex ("vulture/pain1.wav");
sound_pain2 = gi.soundindex ("vulture/pain2.wav");
sound_death = gi.soundindex ("vulture/death1.wav");
// precache feather gibs
gi.modelindex ("models/monsters/vulture/feather1.md2");
gi.modelindex ("models/monsters/vulture/feather2.md2");
// Lazarus: special purpose skins
if ( self->style )
{
PatchMonsterModel("models/monsters/vulture/tris.md2");
self->s.skinnum = self->style;
}
self->s.modelindex = gi.modelindex ("models/monsters/vulture/tris.md2");
VectorSet (self->mins, -8, -8, -8);
VectorSet (self->maxs, 8, 8, 10);
self->movetype = MOVETYPE_STEP;
self->solid = SOLID_BBOX;
// if spawned as landed, bump origin so we don't start in a brush
/* if ( !(self->spawnflags & SF_VULTURE_IN_AIR) ) {
self->s.origin[2] += 8;
} */
if (!self->health)
self->health = 50;
if (!self->gib_health)
self->gib_health = -20;
if (!self->mass)
self->mass = 50;
self->pain = vulture_pain;
self->die = vulture_die;
self->monsterinfo.stand = vulture_perch;
self->monsterinfo.walk = vulture_walk;
self->monsterinfo.run = vulture_run;
self->monsterinfo.dodge = NULL;
self->monsterinfo.attack = NULL;
self->monsterinfo.melee = vulture_melee;
self->monsterinfo.sight = vulture_sight;
self->monsterinfo.idle = vulture_idle;
self->monsterinfo.search = NULL;
self->monsterinfo.blocked = NULL;
if (!self->monsterinfo.flies)
self->monsterinfo.flies = 0.05;
// Lazarus
if (self->powerarmor)
{
if (self->powerarmortype == 1)
self->monsterinfo.power_armor_type = POWER_ARMOR_SCREEN;
else
self->monsterinfo.power_armor_type = POWER_ARMOR_SHIELD;
self->monsterinfo.power_armor_power = self->powerarmor;
}
self->common_name = "Vulture";
self->class_id = ENTITY_MONSTER_VULTURE;
self->spawnflags |= SF_MONSTER_KNOWS_MIRRORS;
gi.linkentity (self);
// self->monsterinfo.currentmove = &vulture_move_perch;
self->monsterinfo.scale = MODEL_SCALE;
if (self->spawnflags & SF_VULTURE_IN_AIR) {
self->monsterinfo.currentmove = &vulture_move_soar;
flymonster_start (self);
}
else {
self->monsterinfo.currentmove = &vulture_move_perch;
walkmonster_start (self);
}
}

View file

@ -281,10 +281,6 @@ SOURCE=.\g_weapon_q1.c
# End Source File
# Begin Source File
SOURCE=.\grenade.c
# End Source File
# Begin Source File
SOURCE=.\km_cvar.c
# End Source File
# Begin Source File
@ -477,6 +473,10 @@ SOURCE=.\m_turret.c
# End Source File
# Begin Source File
SOURCE=.\m_vulture.c
# End Source File
# Begin Source File
SOURCE=.\m_widow.c
# End Source File
# Begin Source File
@ -757,6 +757,10 @@ SOURCE=.\m_turret.h
# End Source File
# Begin Source File
SOURCE=.\m_vulture.h
# End Source File
# Begin Source File
SOURCE=.\m_zombie.h
# End Source File
# Begin Source File

View file

@ -4,6 +4,7 @@
Version="9.00"
Name="missionpack"
ProjectGUID="{B2C5294F-5F08-4598-B02C-272370AE8F38}"
RootNamespace="missionpack"
TargetFrameworkVersion="0"
>
<Platforms>
@ -602,10 +603,6 @@
RelativePath=".\g_weapon_q1.c"
>
</File>
<File
RelativePath="grenade.c"
>
</File>
<File
RelativePath="km_cvar.c"
>
@ -738,6 +735,10 @@
RelativePath=".\m_q1fiend.c"
>
</File>
<File
RelativePath=".\m_q1freddie.c"
>
</File>
<File
RelativePath=".\m_q1grunt.c"
>
@ -798,6 +799,10 @@
RelativePath="m_turret.c"
>
</File>
<File
RelativePath=".\m_vulture.c"
>
</File>
<File
RelativePath="m_widow.c"
>
@ -1015,6 +1020,10 @@
RelativePath=".\m_q1fiend.h"
>
</File>
<File
RelativePath=".\m_q1freddie.h"
>
</File>
<File
RelativePath=".\m_q1grunt.h"
>
@ -1080,7 +1089,7 @@
>
</File>
<File
RelativePath="m_zombie.h"
RelativePath=".\m_vulture.h"
>
</File>
<File

View file

@ -1044,6 +1044,9 @@ void ClientObituary (edict_t *self, edict_t *inflictor, edict_t *attacker)
// Rottweiler
else if (!strcmp(attacker->classname, "monster_dog"))
message = "was mauled by a";
// Vulture
else if (!strcmp(attacker->classname, "monster_vulture"))
message = "was pecked to death by a";
// Quake 1 Monsters
// Fiend
else if ( !Q_stricmp(attacker->classname, "q1_monster_fiend") || !Q_stricmp(attacker->classname, "monster_q1_demon") )
@ -1086,6 +1089,10 @@ void ClientObituary (edict_t *self, edict_t *inflictor, edict_t *attacker)
// Spawn
else if ( !Q_stricmp(attacker->classname, "q1_monster_tarbaby") || !Q_stricmp(attacker->classname, "monster_q1_tarbaby") )
message = "was slimed by a";
// Freddie
else if ( !Q_stricmp(attacker->classname, "q1_monster_freddie") || !Q_stricmp(attacker->classname, "monster_q1_freddie") )
message = "was exterminated by";
}
if (message)
{

View file

@ -3636,7 +3636,7 @@ void weapon_plasma_rifle_fire (edict_t *ent, qboolean altfire)
}
// if outa ammo, don't fire
if (ent->client->pers.inventory[ent->client->ammo_index] < 1)
if (ent->client->pers.inventory[ent->client->ammo_index] < PLASMA_CELLS_PER_SHOT) // was < 1
{
ent->client->ps.gunframe++;