-// size
const vector SPIDER_MIN = '-18 -18 -25';
const vector SPIDER_MAX = '18 18 30';
-// model
string SPIDER_MODEL = "models/monsters/spider.dpm";
#ifdef SVQC
-// cvars
float autocvar_g_monster_spider;
float autocvar_g_monster_spider_stopspeed;
float autocvar_g_monster_spider_attack_leap_delay;
float autocvar_g_monster_spider_speed_run;
float autocvar_g_monster_spider_attack_type;
-// animations
const float spider_anim_idle = 0;
const float spider_anim_walk = 1;
const float spider_anim_attack = 2;
const float SPIDER_TYPE_ICE = 0;
const float SPIDER_TYPE_FIRE = 1;
-void spider_attack_standing()
-{
- monster_melee(self.enemy, autocvar_g_monster_spider_attack_stand_damage, 0.3, DEATH_MONSTER_SPIDER, TRUE);
+void spider_think()
+{
+ self.think = spider_think;
+ self.nextthink = time + self.ticrate;
- monsters_setframe((random() > 0.5) ? spider_anim_attack : spider_anim_attack2);
-
- self.attack_finished_single = time + autocvar_g_monster_spider_attack_stand_delay;
+ monster_move(autocvar_g_monster_spider_speed_run, autocvar_g_monster_spider_speed_walk, autocvar_g_monster_spider_stopspeed, spider_anim_walk, spider_anim_walk, spider_anim_idle);
}
-void spider_web_explode ()
+void spider_web_explode()
{
- float damg = 0, edamg = 0, rad = 1;
- switch(self.realowner.spider_type)
+ entity e;
+ if(self)
{
- case SPIDER_TYPE_ICE:
- break; // no change
- case SPIDER_TYPE_FIRE:
- damg = 15;
- rad = 25;
- edamg = 6;
- break;
+ float damg = 0, edamg = 0, rad = 1;
+ switch(self.realowner.spider_type)
+ {
+ case SPIDER_TYPE_ICE:
+ rad = 25;
+ pointparticles(particleeffectnum("electro_impact"), self.origin, '0 0 0', 1);
+ break;
+ case SPIDER_TYPE_FIRE:
+ pointparticles(particleeffectnum("fireball_explode"), self.origin, '0 0 0', 1);
+ damg = 15;
+ rad = 25;
+ edamg = 6;
+ break;
+ }
+
+ RadiusDamage(self, self.realowner, damg, edamg, 0, world, rad, DEATH_MONSTER_SPIDER_FIRE, world); // ice deals no damage anyway
+
+ for(e = findradius(self.origin, rad); e; e = e.chain) if(e.takedamage && e.deadflag == DEAD_NO)
+ {
+ switch(self.realowner.spider_type)
+ {
+ case SPIDER_TYPE_ICE:
+ Freeze(e, 0.3, 2, FALSE);
+ break;
+ case SPIDER_TYPE_FIRE:
+ Fire_AddDamage(e, self.realowner, 5 * monster_skill, autocvar_g_monster_spider_attack_fire_time, DEATH_MONSTER_SPIDER_FIRE);
+ break;
+ }
+ }
+
+ remove(self);
}
-
- RadiusDamage (self, self.realowner, damg, edamg, rad, world, 0, self.projectiledeathtype, other);
-
- remove (self);
}
-void spider_web_touch ()
+void spider_web_touch()
{
PROJECTILE_TOUCH;
- if(other.takedamage == DAMAGE_AIM)
- if(other.health > 0)
- switch(self.realowner.spider_type)
- {
- case SPIDER_TYPE_ICE:
- Freeze(other, 0.3, 2, revive_progress);
- break;
- case SPIDER_TYPE_FIRE:
- Fire_AddDamage(other, self.realowner, 5 * monster_skill, autocvar_g_monster_spider_attack_fire_time, DEATH_MONSTER_SPIDER_FIRE);
- break;
- }
-
spider_web_explode();
}
void spider_shootweb(float ptype)
{
- float p = 0, dt = 0;
+ float p = 0;
string snd = "";
switch(ptype)
{
case SPIDER_TYPE_ICE:
p = PROJECTILE_ELECTRO;
- dt = WEP_ELECTRO;
snd = "weapons/electro_fire2.wav";
break;
case SPIDER_TYPE_FIRE:
- p = ((self.scale >= 2) ? PROJECTILE_FIREBALL : PROJECTILE_FIREMINE);
- dt = WEP_FIREBALL;
+ p = PROJECTILE_FIREMINE;
snd = "weapons/fireball_fire.wav";
break;
}
- vector fmins = ((self.scale >= 2) ? '-16 -16 -16' : '-4 -4 -4'), fmaxs = ((self.scale >= 2) ? '16 16 16' : '4 4 4');
-
- entity proj = world;
-
- makevectors(self.angles);
+ vector fmins = '-4 -4 -4', fmaxs = '4 4 4';
W_SetupShot_ProjectileSize(self, fmins, fmaxs, FALSE, 2, snd, CH_WEAPON_A, 0);
w_shotdir = v_forward; // no TrueAim for grenades please
- proj = spawn ();
+ entity proj = spawn ();
proj.classname = "plasma";
proj.owner = proj.realowner = self;
proj.use = spider_web_touch;
proj.bot_dodgerating = 0;
proj.nextthink = time + 5;
PROJECTILE_MAKETRIGGER(proj);
- proj.projectiledeathtype = dt | HITTYPE_SECONDARY;
+ proj.projectiledeathtype = DEATH_MONSTER_SPIDER_FIRE;
setorigin(proj, w_shotorg);
//proj.glow_size = 50;
proj.bouncestop = 0.05;
proj.missile_flags = MIF_SPLASH | MIF_ARC;
- CSQCProjectile(proj, TRUE, p, FALSE); // no culling, it has sound
-}
-
-void spider_attack_leap()
-{
- vector angles_face = vectoangles(self.enemy.origin - self.origin);
-
- // face the enemy
- monsters_setframe(spider_anim_attack2);
- self.angles_y = angles_face_y ;
- self.attack_finished_single = time + autocvar_g_monster_spider_attack_leap_delay;
-
- makevectors(self.angles);
-
- spider_shootweb(self.spider_type);
-}
-
-float spider_attack_ranged()
-{
- if(self.enemy.frozen)
- return FALSE;
-
- spider_attack_leap();
- return TRUE;
+ CSQCProjectile(proj, TRUE, p, TRUE);
}
-void spider_think()
+float spider_attack(float attack_type)
{
- self.think = spider_think;
- self.nextthink = time + self.ticrate;
+ switch(attack_type)
+ {
+ case MONSTER_ATTACK_MELEE:
+ {
+ monster_melee(self.enemy, autocvar_g_monster_spider_attack_stand_damage, 0.3, DEATH_MONSTER_SPIDER, TRUE);
+ monsters_setframe((random() > 0.5) ? spider_anim_attack : spider_anim_attack2);
+ self.attack_finished_single = time + autocvar_g_monster_spider_attack_stand_delay;
+
+ return TRUE;
+ }
+ case MONSTER_ATTACK_RANGED:
+ {
+ if(self.enemy.frozen)
+ return FALSE;
+
+ monsters_setframe(spider_anim_attack2);
+ self.attack_finished_single = time + autocvar_g_monster_spider_attack_leap_delay;
+ monster_makevectors(self.enemy);
+ spider_shootweb(self.spider_type);
+
+ return TRUE;
+ }
+ }
- monster_move(autocvar_g_monster_spider_speed_run, autocvar_g_monster_spider_speed_walk, autocvar_g_monster_spider_stopspeed, spider_anim_walk, spider_anim_walk, spider_anim_idle);
+ return FALSE;
}
-void spider_die ()
+void spider_die()
{
Monster_CheckDropCvars ("spider");
void spider_spawn()
{
if not(self.health)
- self.health = autocvar_g_monster_spider_health * self.scale;
+ self.health = autocvar_g_monster_spider_health;
self.classname = "monster_spider";
self.nextthink = time + random() * 0.5 + 0.1;
- self.checkattack = GenericCheckAttack;
- self.attack_melee = spider_attack_standing;
- self.attack_ranged = spider_attack_ranged;
+ self.monster_attackfunc = spider_attack;
self.think = spider_think;
monsters_setframe(spider_anim_idle);