mirror of
https://github.com/nzp-team/fteqw.git
synced 2024-11-25 21:31:37 +00:00
monsters added but not "finished", i'm neglecting some bugs.. will fix later
git-svn-id: https://svn.code.sf.net/p/fteqw/code/trunk@1144 fc73d0e0-1445-4013-8a0c-d673dee63da5
This commit is contained in:
parent
c428a29469
commit
c69d233c71
31 changed files with 6497 additions and 211 deletions
750
quakec/basemod/ai.qc
Normal file
750
quakec/basemod/ai.qc
Normal file
|
@ -0,0 +1,750 @@
|
||||||
|
void() t_movetarget;
|
||||||
|
/*
|
||||||
|
|
||||||
|
.enemy
|
||||||
|
Will be world if not currently angry at anyone.
|
||||||
|
|
||||||
|
.movetarget
|
||||||
|
The next path spot to walk toward. If .enemy, ignore .movetarget.
|
||||||
|
When an enemy is killed, the monster will try to return to it's path.
|
||||||
|
|
||||||
|
.huntt_ime
|
||||||
|
Set to time + something when the player is in sight, but movement straight for
|
||||||
|
him is blocked. This causes the monster to use wall following code for
|
||||||
|
movement direction instead of sighting on the player.
|
||||||
|
|
||||||
|
.ideal_yaw
|
||||||
|
A yaw angle of the intended direction, which will be turned towards at up
|
||||||
|
to 45 deg / state. If the enemy is in view and hunt_time is not active,
|
||||||
|
this will be the exact line towards the enemy.
|
||||||
|
|
||||||
|
.pausetime
|
||||||
|
A monster will leave it's stand state and head towards it's .movetarget when
|
||||||
|
time > .pausetime.
|
||||||
|
|
||||||
|
walkmove(angle, speed) primitive is all or nothing
|
||||||
|
*/
|
||||||
|
|
||||||
|
//
|
||||||
|
// when a monster becomes angry at a player, that monster will be used
|
||||||
|
// as the sight target the next frame so that monsters near that one
|
||||||
|
// will wake up even if they wouldn't have noticed the player
|
||||||
|
//
|
||||||
|
entity sight_entity;
|
||||||
|
float sight_entity_time;
|
||||||
|
|
||||||
|
float(float v) anglemod =
|
||||||
|
{
|
||||||
|
while (v >= 360)
|
||||||
|
v = v - 360;
|
||||||
|
while (v < 0)
|
||||||
|
v = v + 360;
|
||||||
|
return v;
|
||||||
|
};
|
||||||
|
|
||||||
|
/*
|
||||||
|
==============================================================================
|
||||||
|
|
||||||
|
MOVETARGET CODE
|
||||||
|
|
||||||
|
The angle of the movetarget effects standing and bowing direction, but has no effect on movement, which allways heads to the next target.
|
||||||
|
|
||||||
|
targetname
|
||||||
|
must be present. The name of this movetarget.
|
||||||
|
|
||||||
|
target
|
||||||
|
the next spot to move to. If not present, stop here for good.
|
||||||
|
|
||||||
|
pausetime
|
||||||
|
The number of seconds to spend standing or bowing for path_stand or path_bow
|
||||||
|
|
||||||
|
==============================================================================
|
||||||
|
*/
|
||||||
|
|
||||||
|
|
||||||
|
void() movetarget_f =
|
||||||
|
{
|
||||||
|
if (!self.targetname)
|
||||||
|
objerror ("monster_movetarget: no targetname");
|
||||||
|
|
||||||
|
self.solid = SOLID_TRIGGER;
|
||||||
|
self.touch = t_movetarget;
|
||||||
|
setsize (self, '-8 -8 -8', '8 8 8');
|
||||||
|
|
||||||
|
};
|
||||||
|
|
||||||
|
/*QUAKED path_corner (0.5 0.3 0) (-8 -8 -8) (8 8 8)
|
||||||
|
Monsters will continue walking towards the next target corner.
|
||||||
|
*/
|
||||||
|
void() path_corner =
|
||||||
|
{
|
||||||
|
movetarget_f ();
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
/*
|
||||||
|
=============
|
||||||
|
t_movetarget
|
||||||
|
|
||||||
|
Something has bumped into a movetarget. If it is a monster
|
||||||
|
moving towards it, change the next destination and continue.
|
||||||
|
==============
|
||||||
|
*/
|
||||||
|
void() t_movetarget =
|
||||||
|
{
|
||||||
|
local entity temp;
|
||||||
|
|
||||||
|
if (other.movetarget != self)
|
||||||
|
return;
|
||||||
|
|
||||||
|
if (other.enemy)
|
||||||
|
return; // fighting, not following a path
|
||||||
|
|
||||||
|
temp = self;
|
||||||
|
self = other;
|
||||||
|
other = temp;
|
||||||
|
|
||||||
|
if (self.classname == "monster_ogre")
|
||||||
|
sound (self, CHAN_VOICE, "ogre/ogdrag.wav", 1, ATTN_IDLE);// play chainsaw drag sound
|
||||||
|
|
||||||
|
//dprint ("t_movetarget\n");
|
||||||
|
self.goalentity = self.movetarget = find (world, targetname, other.target);
|
||||||
|
self.ideal_yaw = vectoyaw(self.goalentity.origin - self.origin);
|
||||||
|
if (!self.movetarget)
|
||||||
|
{
|
||||||
|
self.pausetime = time + 999999;
|
||||||
|
self.th_stand ();
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
|
||||||
|
/*
|
||||||
|
=============
|
||||||
|
range
|
||||||
|
|
||||||
|
returns the range catagorization of an entity reletive to self
|
||||||
|
0 melee range, will become hostile even if back is turned
|
||||||
|
1 visibility and infront, or visibility and show hostile
|
||||||
|
2 infront and show hostile
|
||||||
|
3 only triggered by damage
|
||||||
|
=============
|
||||||
|
*/
|
||||||
|
float(entity targ) range =
|
||||||
|
{
|
||||||
|
local vector spot1, spot2;
|
||||||
|
local float r;
|
||||||
|
|
||||||
|
spot1 = self.origin + self.view_ofs;
|
||||||
|
spot2 = targ.origin + targ.view_ofs;
|
||||||
|
|
||||||
|
r = vlen (spot1 - spot2);
|
||||||
|
if (r < 120)
|
||||||
|
return RANGE_MELEE;
|
||||||
|
if (r < 500)
|
||||||
|
return RANGE_NEAR;
|
||||||
|
if (r < 1000)
|
||||||
|
return RANGE_MID;
|
||||||
|
return RANGE_FAR;
|
||||||
|
};
|
||||||
|
|
||||||
|
/*
|
||||||
|
=============
|
||||||
|
visible
|
||||||
|
|
||||||
|
returns 1 if the entity is visible to self, even if not infront ()
|
||||||
|
=============
|
||||||
|
*/
|
||||||
|
float (entity targ) visible =
|
||||||
|
{
|
||||||
|
local vector spot1, spot2;
|
||||||
|
|
||||||
|
spot1 = self.origin + self.view_ofs;
|
||||||
|
spot2 = targ.origin + targ.view_ofs;
|
||||||
|
traceline (spot1, spot2, TRUE, self); // see through other monsters
|
||||||
|
|
||||||
|
if (trace_inopen && trace_inwater)
|
||||||
|
return FALSE; // sight line crossed contents
|
||||||
|
|
||||||
|
if (trace_fraction == 1)
|
||||||
|
return TRUE;
|
||||||
|
return FALSE;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
/*
|
||||||
|
=============
|
||||||
|
infront
|
||||||
|
|
||||||
|
returns 1 if the entity is in front (in sight) of self
|
||||||
|
=============
|
||||||
|
*/
|
||||||
|
float(entity targ) infront =
|
||||||
|
{
|
||||||
|
local vector vec;
|
||||||
|
local float dot;
|
||||||
|
|
||||||
|
makevectors (self.angles);
|
||||||
|
vec = normalize (targ.origin - self.origin);
|
||||||
|
dot = vec * v_forward;
|
||||||
|
|
||||||
|
if ( dot > 0.3)
|
||||||
|
{
|
||||||
|
return TRUE;
|
||||||
|
}
|
||||||
|
return FALSE;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
|
||||||
|
/*
|
||||||
|
===========
|
||||||
|
ChangeYaw
|
||||||
|
|
||||||
|
Turns towards self.ideal_yaw at self.yaw_speed
|
||||||
|
Sets the global variable current_yaw
|
||||||
|
Called every 0.1 sec by monsters
|
||||||
|
============
|
||||||
|
*/
|
||||||
|
/*
|
||||||
|
void() ChangeYaw =
|
||||||
|
{
|
||||||
|
local float ideal, move, current_yaw;
|
||||||
|
|
||||||
|
//current_yaw = self.ideal_yaw;
|
||||||
|
// mod down the current angle
|
||||||
|
current_yaw = anglemod( self.angles_y );
|
||||||
|
ideal = self.ideal_yaw;
|
||||||
|
|
||||||
|
if (current_yaw == ideal)
|
||||||
|
return;
|
||||||
|
|
||||||
|
move = ideal - current_yaw;
|
||||||
|
if (ideal > current_yaw)
|
||||||
|
{
|
||||||
|
if (move > 180)
|
||||||
|
move = move - 360;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if (move < -180)
|
||||||
|
move = move + 360;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (move > 0)
|
||||||
|
{
|
||||||
|
if (move > self.yaw_speed)
|
||||||
|
move = self.yaw_speed;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if (move < 0-self.yaw_speed )
|
||||||
|
move = 0-self.yaw_speed;
|
||||||
|
}
|
||||||
|
|
||||||
|
current_yaw = anglemod (current_yaw + move);
|
||||||
|
|
||||||
|
self.angles_y = current_yaw;
|
||||||
|
};
|
||||||
|
*/
|
||||||
|
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
|
||||||
|
void() HuntTarget =
|
||||||
|
{
|
||||||
|
self.goalentity = self.enemy;
|
||||||
|
self.think = self.th_run;
|
||||||
|
self.ideal_yaw = vectoyaw(self.enemy.origin - self.origin);
|
||||||
|
self.nextthink = time + 0.1;
|
||||||
|
SUB_AttackFinished (1); // wait a while before first attack
|
||||||
|
};
|
||||||
|
|
||||||
|
void() SightSound =
|
||||||
|
{
|
||||||
|
local float rsnd;
|
||||||
|
local string s;
|
||||||
|
|
||||||
|
switch (self.classname)
|
||||||
|
{
|
||||||
|
case "monster_ogre":
|
||||||
|
s = "ogre/ogwake.wav";
|
||||||
|
break;
|
||||||
|
case "monster_knight":
|
||||||
|
s = "knight/ksight.wav";
|
||||||
|
break;
|
||||||
|
case "monster_shambler":
|
||||||
|
s = "shambler/ssight.wav";
|
||||||
|
break;
|
||||||
|
case "monster_demon1":
|
||||||
|
s = "demon/sight2.wav";
|
||||||
|
break;
|
||||||
|
case "monster_wizard":
|
||||||
|
s = "wizard/wsight.wav";
|
||||||
|
break;
|
||||||
|
case "monster_zombie":
|
||||||
|
s = "zombie/z_idle.wav";
|
||||||
|
break;
|
||||||
|
case "monster_dog":
|
||||||
|
s = "dog/dsight.wav";
|
||||||
|
break;
|
||||||
|
case "monster_hell_knight":
|
||||||
|
s = "hknight/sight1.wav";
|
||||||
|
break;
|
||||||
|
case "monster_tarbaby":
|
||||||
|
s = "blob/sight1.wav";
|
||||||
|
break;
|
||||||
|
case "monster_enforcer":
|
||||||
|
rsnd = random();
|
||||||
|
if (rsnd < 0.25)
|
||||||
|
s = "enforcer/sight1.wav";
|
||||||
|
else if (rsnd < 0.5)
|
||||||
|
s = "enforcer/sight2.wav";
|
||||||
|
else if (rsnd < 0.75)
|
||||||
|
s = "enforcer/sight3.wav";
|
||||||
|
else
|
||||||
|
s = "enforcer/sight4.wav";
|
||||||
|
break;
|
||||||
|
case "monster_shalrath":
|
||||||
|
s = "shalrath/sight.wav";
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
s = "soldier/sight1.wav";
|
||||||
|
}
|
||||||
|
|
||||||
|
sound (self, CHAN_VOICE, s, 1, ATTN_NORM);
|
||||||
|
};
|
||||||
|
|
||||||
|
void() FoundTarget =
|
||||||
|
{
|
||||||
|
if (self.enemy.classname == "player")
|
||||||
|
{ // let other monsters see this monster for a while
|
||||||
|
sight_entity = self;
|
||||||
|
sight_entity_time = time;
|
||||||
|
}
|
||||||
|
|
||||||
|
self.show_hostile = time + 1; // wake up other monsters
|
||||||
|
|
||||||
|
SightSound ();
|
||||||
|
HuntTarget ();
|
||||||
|
};
|
||||||
|
|
||||||
|
/*
|
||||||
|
===========
|
||||||
|
FindTarget
|
||||||
|
|
||||||
|
Self is currently not attacking anything, so try to find a target
|
||||||
|
|
||||||
|
Returns TRUE if an enemy was sighted
|
||||||
|
|
||||||
|
When a player fires a missile, the point of impact becomes a fakeplayer so
|
||||||
|
that monsters that see the impact will respond as if they had seen the
|
||||||
|
player.
|
||||||
|
|
||||||
|
To avoid spending too much time, only a single client (or fakeclient) is
|
||||||
|
checked each frame. This means multi player games will have slightly
|
||||||
|
slower noticing monsters.
|
||||||
|
============
|
||||||
|
*/
|
||||||
|
float() FindTarget =
|
||||||
|
{
|
||||||
|
local entity client;
|
||||||
|
local float r;
|
||||||
|
|
||||||
|
// if the first spawnflag bit is set, the monster will only wake up on
|
||||||
|
// really seeing the player, not another monster getting angry
|
||||||
|
|
||||||
|
// spawnflags & 3 is a big hack, because zombie crucified used the first
|
||||||
|
// spawn flag prior to the ambush flag, and I forgot about it, so the second
|
||||||
|
// spawn flag works as well
|
||||||
|
if (sight_entity_time >= time - 0.1 && !(self.spawnflags & 3) )
|
||||||
|
{
|
||||||
|
client = sight_entity;
|
||||||
|
if (client.enemy == self.enemy)
|
||||||
|
return TRUE;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
client = checkclient ();
|
||||||
|
if (!client)
|
||||||
|
return FALSE; // current check entity isn't in PVS
|
||||||
|
}
|
||||||
|
|
||||||
|
if (client == self.enemy)
|
||||||
|
return FALSE;
|
||||||
|
|
||||||
|
if (client.flags & FL_NOTARGET)
|
||||||
|
return FALSE;
|
||||||
|
if (client.items & IT_INVISIBILITY)
|
||||||
|
return FALSE;
|
||||||
|
|
||||||
|
r = range (client);
|
||||||
|
if (r == RANGE_FAR)
|
||||||
|
return FALSE;
|
||||||
|
|
||||||
|
if (!visible (client))
|
||||||
|
return FALSE;
|
||||||
|
|
||||||
|
if (r == RANGE_NEAR)
|
||||||
|
{
|
||||||
|
if (client.show_hostile < time && !infront (client))
|
||||||
|
return FALSE;
|
||||||
|
}
|
||||||
|
else if (r == RANGE_MID)
|
||||||
|
{
|
||||||
|
if ( /* client.show_hostile < time || */ !infront (client))
|
||||||
|
return FALSE;
|
||||||
|
}
|
||||||
|
|
||||||
|
//
|
||||||
|
// got one
|
||||||
|
//
|
||||||
|
self.enemy = client;
|
||||||
|
if (self.enemy.classname != "player")
|
||||||
|
{
|
||||||
|
self.enemy = self.enemy.enemy;
|
||||||
|
if (self.enemy.classname != "player")
|
||||||
|
{
|
||||||
|
self.enemy = world;
|
||||||
|
return FALSE;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
FoundTarget ();
|
||||||
|
|
||||||
|
return TRUE;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
void(float dist) ai_forward =
|
||||||
|
{
|
||||||
|
walkmove (self.angles_y, dist);
|
||||||
|
};
|
||||||
|
|
||||||
|
void(float dist) ai_back =
|
||||||
|
{
|
||||||
|
walkmove ( (self.angles_y+180), dist);
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
/*
|
||||||
|
=============
|
||||||
|
ai_pain
|
||||||
|
|
||||||
|
stagger back a bit
|
||||||
|
=============
|
||||||
|
*/
|
||||||
|
void(float dist) ai_pain =
|
||||||
|
{
|
||||||
|
ai_back (dist);
|
||||||
|
/*
|
||||||
|
local float away;
|
||||||
|
|
||||||
|
away = anglemod (vectoyaw (self.origin - self.enemy.origin)
|
||||||
|
+ 180*(random()- 0.5) );
|
||||||
|
|
||||||
|
walkmove (away, dist);
|
||||||
|
*/
|
||||||
|
};
|
||||||
|
|
||||||
|
/*
|
||||||
|
=============
|
||||||
|
ai_painforward
|
||||||
|
|
||||||
|
stagger back a bit
|
||||||
|
=============
|
||||||
|
*/
|
||||||
|
void(float dist) ai_painforward =
|
||||||
|
{
|
||||||
|
walkmove (self.ideal_yaw, dist);
|
||||||
|
};
|
||||||
|
|
||||||
|
/*
|
||||||
|
=============
|
||||||
|
ai_walk
|
||||||
|
|
||||||
|
The monster is walking it's beat
|
||||||
|
=============
|
||||||
|
*/
|
||||||
|
void(float dist) ai_walk =
|
||||||
|
{
|
||||||
|
// movedist = dist;
|
||||||
|
|
||||||
|
/*
|
||||||
|
There are no dragons!
|
||||||
|
if (self.classname == "monster_dragon")
|
||||||
|
{
|
||||||
|
movetogoal (dist);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
*/
|
||||||
|
|
||||||
|
// check for noticing a player
|
||||||
|
if (FindTarget ())
|
||||||
|
return;
|
||||||
|
|
||||||
|
movetogoal (dist);
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
/*
|
||||||
|
=============
|
||||||
|
ai_stand
|
||||||
|
|
||||||
|
The monster is staying in one place for a while, with slight angle turns
|
||||||
|
=============
|
||||||
|
*/
|
||||||
|
void() ai_stand =
|
||||||
|
{
|
||||||
|
if (FindTarget ())
|
||||||
|
return;
|
||||||
|
|
||||||
|
if (time > self.pausetime)
|
||||||
|
{
|
||||||
|
self.th_walk ();
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// change angle slightly
|
||||||
|
|
||||||
|
};
|
||||||
|
|
||||||
|
/*
|
||||||
|
=============
|
||||||
|
ai_turn
|
||||||
|
|
||||||
|
don't move, but turn towards ideal_yaw
|
||||||
|
=============
|
||||||
|
*/
|
||||||
|
void() ai_turn =
|
||||||
|
{
|
||||||
|
if (FindTarget ())
|
||||||
|
return;
|
||||||
|
|
||||||
|
ChangeYaw ();
|
||||||
|
};
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
/*
|
||||||
|
=============
|
||||||
|
ChooseTurn
|
||||||
|
=============
|
||||||
|
*/
|
||||||
|
/*
|
||||||
|
void(vector dest3) ChooseTurn =
|
||||||
|
{
|
||||||
|
local vector dir, newdir;
|
||||||
|
|
||||||
|
dir = self.origin - dest3;
|
||||||
|
|
||||||
|
newdir_x = trace_plane_normal_y;
|
||||||
|
newdir_y = 0 - trace_plane_normal_x;
|
||||||
|
newdir_z = 0;
|
||||||
|
|
||||||
|
if (dir * newdir > 0)
|
||||||
|
{
|
||||||
|
dir_x = 0 - trace_plane_normal_y;
|
||||||
|
dir_y = trace_plane_normal_x;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
dir_x = trace_plane_normal_y;
|
||||||
|
dir_y = 0 - trace_plane_normal_x;
|
||||||
|
}
|
||||||
|
|
||||||
|
dir_z = 0;
|
||||||
|
self.ideal_yaw = vectoyaw(dir);
|
||||||
|
};
|
||||||
|
*/
|
||||||
|
|
||||||
|
/*
|
||||||
|
============
|
||||||
|
FacingIdeal
|
||||||
|
|
||||||
|
============
|
||||||
|
*/
|
||||||
|
float() FacingIdeal =
|
||||||
|
{
|
||||||
|
local float delta;
|
||||||
|
|
||||||
|
delta = anglemod(self.angles_y - self.ideal_yaw);
|
||||||
|
if (delta > 45 && delta < 315)
|
||||||
|
return FALSE;
|
||||||
|
return TRUE;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
float(float enemy_range) DogCheckAttack;
|
||||||
|
float(float enemy_range) WizardCheckAttack;
|
||||||
|
float(float enemy_range) DemonCheckAttack;
|
||||||
|
|
||||||
|
float(float enemy_range) CheckAnyAttack =
|
||||||
|
{
|
||||||
|
|
||||||
|
switch (self.classname)
|
||||||
|
{
|
||||||
|
case "monster_army":
|
||||||
|
return SoldierCheckAttack (enemy_range);
|
||||||
|
case "monster_ogre":
|
||||||
|
return OgreCheckAttack (enemy_range);
|
||||||
|
case "monster_shambler":
|
||||||
|
return ShamCheckAttack (enemy_range);
|
||||||
|
case "monster_demon1":
|
||||||
|
return DemonCheckAttack (enemy_range);
|
||||||
|
case "monster_dog":
|
||||||
|
return DogCheckAttack (enemy_range);
|
||||||
|
case "monster_wizard":
|
||||||
|
return WizardCheckAttack (enemy_range);
|
||||||
|
}
|
||||||
|
|
||||||
|
return CheckAttack (enemy_range);
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
/*
|
||||||
|
=============
|
||||||
|
ai_run_melee
|
||||||
|
|
||||||
|
Turn and close until within an angle to launch a melee attack
|
||||||
|
=============
|
||||||
|
*/
|
||||||
|
void(float enemy_yaw) ai_run_melee =
|
||||||
|
{
|
||||||
|
self.ideal_yaw = enemy_yaw;
|
||||||
|
ChangeYaw ();
|
||||||
|
|
||||||
|
if (FacingIdeal())
|
||||||
|
{
|
||||||
|
self.th_melee ();
|
||||||
|
self.attack_state = AS_STRAIGHT;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
/*
|
||||||
|
=============
|
||||||
|
ai_run_missile
|
||||||
|
|
||||||
|
Turn in place until within an angle to launch a missile attack
|
||||||
|
=============
|
||||||
|
*/
|
||||||
|
void(float enemy_yaw) ai_run_missile =
|
||||||
|
{
|
||||||
|
self.ideal_yaw = enemy_yaw;
|
||||||
|
ChangeYaw ();
|
||||||
|
if (FacingIdeal())
|
||||||
|
{
|
||||||
|
self.th_missile ();
|
||||||
|
self.attack_state = AS_STRAIGHT;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
/*
|
||||||
|
=============
|
||||||
|
ai_run_slide
|
||||||
|
|
||||||
|
Strafe sideways, but stay at aproximately the same range
|
||||||
|
=============
|
||||||
|
*/
|
||||||
|
void(float enemy_yaw, float movedist) ai_run_slide =
|
||||||
|
{
|
||||||
|
local float ofs;
|
||||||
|
|
||||||
|
self.ideal_yaw = enemy_yaw;
|
||||||
|
ChangeYaw ();
|
||||||
|
if (self.lefty)
|
||||||
|
ofs = 90;
|
||||||
|
else
|
||||||
|
ofs = -90;
|
||||||
|
|
||||||
|
if (walkmove (self.ideal_yaw + ofs, movedist))
|
||||||
|
return;
|
||||||
|
|
||||||
|
self.lefty = 1 - self.lefty;
|
||||||
|
|
||||||
|
walkmove (self.ideal_yaw - ofs, movedist);
|
||||||
|
};
|
||||||
|
|
||||||
|
/*
|
||||||
|
=============
|
||||||
|
ai_run
|
||||||
|
|
||||||
|
The monster has an enemy it is trying to kill
|
||||||
|
=============
|
||||||
|
*/
|
||||||
|
void(float dist) ai_run =
|
||||||
|
{
|
||||||
|
local float enemy_vis, enemy_yaw;
|
||||||
|
|
||||||
|
// see if the enemy is dead
|
||||||
|
if (self.enemy.health <= 0)
|
||||||
|
{
|
||||||
|
self.enemy = world;
|
||||||
|
// FIXME: look all around for other targets
|
||||||
|
if (self.oldenemy.health > 0)
|
||||||
|
{
|
||||||
|
self.enemy = self.oldenemy;
|
||||||
|
HuntTarget ();
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if (self.movetarget)
|
||||||
|
self.th_walk ();
|
||||||
|
else
|
||||||
|
self.th_stand ();
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
self.show_hostile = time + 1; // wake up other monsters
|
||||||
|
|
||||||
|
// check knowledge of enemy
|
||||||
|
enemy_vis = visible(self.enemy);
|
||||||
|
if (enemy_vis)
|
||||||
|
self.search_time = time + 5;
|
||||||
|
|
||||||
|
// look for other coop players
|
||||||
|
if (coop && self.search_time < time)
|
||||||
|
{
|
||||||
|
if (FindTarget ())
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
enemy_yaw = vectoyaw(self.enemy.origin - self.origin);
|
||||||
|
|
||||||
|
if (self.attack_state == AS_MISSILE)
|
||||||
|
{
|
||||||
|
ai_run_missile (enemy_yaw);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (self.attack_state == AS_MELEE)
|
||||||
|
{
|
||||||
|
ai_run_melee (enemy_yaw);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!enemy_vis)
|
||||||
|
return;
|
||||||
|
|
||||||
|
if (CheckAnyAttack (range(self.enemy)))
|
||||||
|
return; // beginning an attack
|
||||||
|
|
||||||
|
if (self.attack_state == AS_SLIDING)
|
||||||
|
{
|
||||||
|
ai_run_slide (enemy_yaw, dist);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// head straight in
|
||||||
|
movetogoal (dist); // done in C code...
|
||||||
|
};
|
||||||
|
|
|
@ -19,16 +19,18 @@ Usage of ammo_shells, etc as display
|
||||||
|
|
||||||
In progress -
|
In progress -
|
||||||
Item fixing for SP
|
Item fixing for SP
|
||||||
|
Add monsters back
|
||||||
|
|
||||||
Todo -
|
Todo -
|
||||||
Fix ammo_shells, etc for monsters/backpacks
|
Fix ammo_shells, etc for monsters/backpacks
|
||||||
Samelevel 4 (exit acts as a spawnpoint teleporter)
|
Samelevel 4 (exit acts as a spawnpoint teleporter)
|
||||||
Effects/decal system
|
Effects/decal system
|
||||||
Fix weird deathmatch modes, cvar checking
|
Fix weird deathmatch modes, cvar checking
|
||||||
Add monsters back
|
|
||||||
Rogue/hipnotic weapons/monsters/hud stuffs
|
Rogue/hipnotic weapons/monsters/hud stuffs
|
||||||
Q2/Q3 ents
|
Q2/Q3 ents
|
||||||
H2/HL ents
|
H2/HL ents
|
||||||
|
Coop friendly finale
|
||||||
|
Add in shambler resistance in a better way
|
||||||
|
|
||||||
Stray Ideas -
|
Stray Ideas -
|
||||||
Advanced heal decay (only decay health that the megahealth added?)
|
Advanced heal decay (only decay health that the megahealth added?)
|
||||||
|
|
373
quakec/basemod/boss.qc
Normal file
373
quakec/basemod/boss.qc
Normal file
|
@ -0,0 +1,373 @@
|
||||||
|
/*
|
||||||
|
==============================================================================
|
||||||
|
|
||||||
|
BOSS-ONE
|
||||||
|
|
||||||
|
==============================================================================
|
||||||
|
*/
|
||||||
|
$cd id1/models/boss1
|
||||||
|
$origin 0 0 -15
|
||||||
|
$base base
|
||||||
|
$skin skin
|
||||||
|
$scale 5
|
||||||
|
|
||||||
|
$frame rise1 rise2 rise3 rise4 rise5 rise6 rise7 rise8 rise9 rise10
|
||||||
|
$frame rise11 rise12 rise13 rise14 rise15 rise16 rise17
|
||||||
|
|
||||||
|
$frame walk1 walk2 walk3 walk4 walk5 walk6 walk7 walk8
|
||||||
|
$frame walk9 walk10 walk11 walk12 walk13 walk14 walk15
|
||||||
|
$frame walk16 walk17 walk18 walk19 walk20 walk21 walk22
|
||||||
|
$frame walk23 walk24 walk25 walk26 walk27 walk28 walk29 walk30 walk31
|
||||||
|
|
||||||
|
$frame death1 death2 death3 death4 death5 death6 death7 death8 death9
|
||||||
|
|
||||||
|
$frame attack1 attack2 attack3 attack4 attack5 attack6 attack7 attack8
|
||||||
|
$frame attack9 attack10 attack11 attack12 attack13 attack14 attack15
|
||||||
|
$frame attack16 attack17 attack18 attack19 attack20 attack21 attack22
|
||||||
|
$frame attack23
|
||||||
|
|
||||||
|
$frame shocka1 shocka2 shocka3 shocka4 shocka5 shocka6 shocka7 shocka8
|
||||||
|
$frame shocka9 shocka10
|
||||||
|
|
||||||
|
$frame shockb1 shockb2 shockb3 shockb4 shockb5 shockb6
|
||||||
|
|
||||||
|
$frame shockc1 shockc2 shockc3 shockc4 shockc5 shockc6 shockc7 shockc8
|
||||||
|
$frame shockc9 shockc10
|
||||||
|
|
||||||
|
|
||||||
|
void(vector p) boss_missile;
|
||||||
|
|
||||||
|
void() boss_face =
|
||||||
|
{
|
||||||
|
|
||||||
|
// go for another player if multi player
|
||||||
|
if (self.enemy.health <= 0 || random() < 0.02)
|
||||||
|
{
|
||||||
|
self.enemy = find(self.enemy, classname, "player");
|
||||||
|
if (!self.enemy)
|
||||||
|
self.enemy = find(self.enemy, classname, "player");
|
||||||
|
}
|
||||||
|
ai_face();
|
||||||
|
};
|
||||||
|
|
||||||
|
void() boss_rise1 =[ $rise1, boss_rise2 ] {
|
||||||
|
sound (self, CHAN_WEAPON, "boss1/out1.wav", 1, ATTN_NORM);
|
||||||
|
};
|
||||||
|
void() boss_rise2 =[ $rise2, boss_rise3 ] {
|
||||||
|
sound (self, CHAN_VOICE, "boss1/sight1.wav", 1, ATTN_NORM);
|
||||||
|
};
|
||||||
|
void() boss_rise3 =[ $rise3, boss_rise4 ] {};
|
||||||
|
void() boss_rise4 =[ $rise4, boss_rise5 ] {};
|
||||||
|
void() boss_rise5 =[ $rise5, boss_rise6 ] {};
|
||||||
|
void() boss_rise6 =[ $rise6, boss_rise7 ] {};
|
||||||
|
void() boss_rise7 =[ $rise7, boss_rise8 ] {};
|
||||||
|
void() boss_rise8 =[ $rise8, boss_rise9 ] {};
|
||||||
|
void() boss_rise9 =[ $rise9, boss_rise10 ] {};
|
||||||
|
void() boss_rise10 =[ $rise10, boss_rise11 ] {};
|
||||||
|
void() boss_rise11 =[ $rise11, boss_rise12 ] {};
|
||||||
|
void() boss_rise12 =[ $rise12, boss_rise13 ] {};
|
||||||
|
void() boss_rise13 =[ $rise13, boss_rise14 ] {};
|
||||||
|
void() boss_rise14 =[ $rise14, boss_rise15 ] {};
|
||||||
|
void() boss_rise15 =[ $rise15, boss_rise16 ] {};
|
||||||
|
void() boss_rise16 =[ $rise16, boss_rise17 ] {};
|
||||||
|
void() boss_rise17 =[ $rise17, boss_missile1 ] {};
|
||||||
|
|
||||||
|
void() boss_idle1 =[ $walk1, boss_idle2 ]
|
||||||
|
{
|
||||||
|
// look for other players
|
||||||
|
};
|
||||||
|
void() boss_idle2 =[ $walk2, boss_idle3 ] {boss_face();};
|
||||||
|
void() boss_idle3 =[ $walk3, boss_idle4 ] {boss_face();};
|
||||||
|
void() boss_idle4 =[ $walk4, boss_idle5 ] {boss_face();};
|
||||||
|
void() boss_idle5 =[ $walk5, boss_idle6 ] {boss_face();};
|
||||||
|
void() boss_idle6 =[ $walk6, boss_idle7 ] {boss_face();};
|
||||||
|
void() boss_idle7 =[ $walk7, boss_idle8 ] {boss_face();};
|
||||||
|
void() boss_idle8 =[ $walk8, boss_idle9 ] {boss_face();};
|
||||||
|
void() boss_idle9 =[ $walk9, boss_idle10 ] {boss_face();};
|
||||||
|
void() boss_idle10 =[ $walk10, boss_idle11 ] {boss_face();};
|
||||||
|
void() boss_idle11 =[ $walk11, boss_idle12 ] {boss_face();};
|
||||||
|
void() boss_idle12 =[ $walk12, boss_idle13 ] {boss_face();};
|
||||||
|
void() boss_idle13 =[ $walk13, boss_idle14 ] {boss_face();};
|
||||||
|
void() boss_idle14 =[ $walk14, boss_idle15 ] {boss_face();};
|
||||||
|
void() boss_idle15 =[ $walk15, boss_idle16 ] {boss_face();};
|
||||||
|
void() boss_idle16 =[ $walk16, boss_idle17 ] {boss_face();};
|
||||||
|
void() boss_idle17 =[ $walk17, boss_idle18 ] {boss_face();};
|
||||||
|
void() boss_idle18 =[ $walk18, boss_idle19 ] {boss_face();};
|
||||||
|
void() boss_idle19 =[ $walk19, boss_idle20 ] {boss_face();};
|
||||||
|
void() boss_idle20 =[ $walk20, boss_idle21 ] {boss_face();};
|
||||||
|
void() boss_idle21 =[ $walk21, boss_idle22 ] {boss_face();};
|
||||||
|
void() boss_idle22 =[ $walk22, boss_idle23 ] {boss_face();};
|
||||||
|
void() boss_idle23 =[ $walk23, boss_idle24 ] {boss_face();};
|
||||||
|
void() boss_idle24 =[ $walk24, boss_idle25 ] {boss_face();};
|
||||||
|
void() boss_idle25 =[ $walk25, boss_idle26 ] {boss_face();};
|
||||||
|
void() boss_idle26 =[ $walk26, boss_idle27 ] {boss_face();};
|
||||||
|
void() boss_idle27 =[ $walk27, boss_idle28 ] {boss_face();};
|
||||||
|
void() boss_idle28 =[ $walk28, boss_idle29 ] {boss_face();};
|
||||||
|
void() boss_idle29 =[ $walk29, boss_idle30 ] {boss_face();};
|
||||||
|
void() boss_idle30 =[ $walk30, boss_idle31 ] {boss_face();};
|
||||||
|
void() boss_idle31 =[ $walk31, boss_idle1 ] {boss_face();};
|
||||||
|
|
||||||
|
void() boss_missile1 =[ $attack1, boss_missile2 ] {boss_face();};
|
||||||
|
void() boss_missile2 =[ $attack2, boss_missile3 ] {boss_face();};
|
||||||
|
void() boss_missile3 =[ $attack3, boss_missile4 ] {boss_face();};
|
||||||
|
void() boss_missile4 =[ $attack4, boss_missile5 ] {boss_face();};
|
||||||
|
void() boss_missile5 =[ $attack5, boss_missile6 ] {boss_face();};
|
||||||
|
void() boss_missile6 =[ $attack6, boss_missile7 ] {boss_face();};
|
||||||
|
void() boss_missile7 =[ $attack7, boss_missile8 ] {boss_face();};
|
||||||
|
void() boss_missile8 =[ $attack8, boss_missile9 ] {boss_face();};
|
||||||
|
void() boss_missile9 =[ $attack9, boss_missile10 ] {boss_missile('100 100 200');};
|
||||||
|
void() boss_missile10 =[ $attack10, boss_missile11 ] {boss_face();};
|
||||||
|
void() boss_missile11 =[ $attack11, boss_missile12 ] {boss_face();};
|
||||||
|
void() boss_missile12 =[ $attack12, boss_missile13 ] {boss_face();};
|
||||||
|
void() boss_missile13 =[ $attack13, boss_missile14 ] {boss_face();};
|
||||||
|
void() boss_missile14 =[ $attack14, boss_missile15 ] {boss_face();};
|
||||||
|
void() boss_missile15 =[ $attack15, boss_missile16 ] {boss_face();};
|
||||||
|
void() boss_missile16 =[ $attack16, boss_missile17 ] {boss_face();};
|
||||||
|
void() boss_missile17 =[ $attack17, boss_missile18 ] {boss_face();};
|
||||||
|
void() boss_missile18 =[ $attack18, boss_missile19 ] {boss_face();};
|
||||||
|
void() boss_missile19 =[ $attack19, boss_missile20 ] {boss_face();};
|
||||||
|
void() boss_missile20 =[ $attack20, boss_missile21 ] {boss_missile('100 -100 200');};
|
||||||
|
void() boss_missile21 =[ $attack21, boss_missile22 ] {boss_face();};
|
||||||
|
void() boss_missile22 =[ $attack22, boss_missile23 ] {boss_face();};
|
||||||
|
void() boss_missile23 =[ $attack23, boss_missile1 ] {boss_face();};
|
||||||
|
|
||||||
|
void() boss_shocka1 =[ $shocka1, boss_shocka2 ] {};
|
||||||
|
void() boss_shocka2 =[ $shocka2, boss_shocka3 ] {};
|
||||||
|
void() boss_shocka3 =[ $shocka3, boss_shocka4 ] {};
|
||||||
|
void() boss_shocka4 =[ $shocka4, boss_shocka5 ] {};
|
||||||
|
void() boss_shocka5 =[ $shocka5, boss_shocka6 ] {};
|
||||||
|
void() boss_shocka6 =[ $shocka6, boss_shocka7 ] {};
|
||||||
|
void() boss_shocka7 =[ $shocka7, boss_shocka8 ] {};
|
||||||
|
void() boss_shocka8 =[ $shocka8, boss_shocka9 ] {};
|
||||||
|
void() boss_shocka9 =[ $shocka9, boss_shocka10 ] {};
|
||||||
|
void() boss_shocka10 =[ $shocka10, boss_missile1 ] {};
|
||||||
|
|
||||||
|
void() boss_shockb1 =[ $shockb1, boss_shockb2 ] {};
|
||||||
|
void() boss_shockb2 =[ $shockb2, boss_shockb3 ] {};
|
||||||
|
void() boss_shockb3 =[ $shockb3, boss_shockb4 ] {};
|
||||||
|
void() boss_shockb4 =[ $shockb4, boss_shockb5 ] {};
|
||||||
|
void() boss_shockb5 =[ $shockb5, boss_shockb6 ] {};
|
||||||
|
void() boss_shockb6 =[ $shockb6, boss_shockb7 ] {};
|
||||||
|
void() boss_shockb7 =[ $shockb1, boss_shockb8 ] {};
|
||||||
|
void() boss_shockb8 =[ $shockb2, boss_shockb9 ] {};
|
||||||
|
void() boss_shockb9 =[ $shockb3, boss_shockb10 ] {};
|
||||||
|
void() boss_shockb10 =[ $shockb4, boss_missile1 ] {};
|
||||||
|
|
||||||
|
void() boss_shockc1 =[ $shockc1, boss_shockc2 ] {};
|
||||||
|
void() boss_shockc2 =[ $shockc2, boss_shockc3 ] {};
|
||||||
|
void() boss_shockc3 =[ $shockc3, boss_shockc4 ] {};
|
||||||
|
void() boss_shockc4 =[ $shockc4, boss_shockc5 ] {};
|
||||||
|
void() boss_shockc5 =[ $shockc5, boss_shockc6 ] {};
|
||||||
|
void() boss_shockc6 =[ $shockc6, boss_shockc7 ] {};
|
||||||
|
void() boss_shockc7 =[ $shockc7, boss_shockc8 ] {};
|
||||||
|
void() boss_shockc8 =[ $shockc8, boss_shockc9 ] {};
|
||||||
|
void() boss_shockc9 =[ $shockc9, boss_shockc10 ] {};
|
||||||
|
void() boss_shockc10 =[ $shockc10, boss_death1 ] {};
|
||||||
|
|
||||||
|
void() boss_death1 = [$death1, boss_death2] {
|
||||||
|
sound (self, CHAN_VOICE, "boss1/death.wav", 1, ATTN_NORM);
|
||||||
|
};
|
||||||
|
void() boss_death2 = [$death2, boss_death3] {};
|
||||||
|
void() boss_death3 = [$death3, boss_death4] {};
|
||||||
|
void() boss_death4 = [$death4, boss_death5] {};
|
||||||
|
void() boss_death5 = [$death5, boss_death6] {};
|
||||||
|
void() boss_death6 = [$death6, boss_death7] {};
|
||||||
|
void() boss_death7 = [$death7, boss_death8] {};
|
||||||
|
void() boss_death8 = [$death8, boss_death9] {};
|
||||||
|
void() boss_death9 = [$death9, boss_death10]
|
||||||
|
{
|
||||||
|
sound (self, CHAN_BODY, "boss1/out1.wav", 1, ATTN_NORM);
|
||||||
|
TE_lavasplash(self.origin);
|
||||||
|
};
|
||||||
|
|
||||||
|
void() boss_death10 = [$death9, boss_death10]
|
||||||
|
{
|
||||||
|
killed_monsters = killed_monsters + 1;
|
||||||
|
WriteByte (MSG_ALL, SVC_KILLEDMONSTER); // FIXME: reliable broadcast
|
||||||
|
SUB_UseTargets ();
|
||||||
|
remove (self);
|
||||||
|
};
|
||||||
|
|
||||||
|
void(vector p) boss_missile =
|
||||||
|
{
|
||||||
|
local vector offang;
|
||||||
|
local vector org, vec, d;
|
||||||
|
local float t;
|
||||||
|
|
||||||
|
offang = vectoangles (self.enemy.origin - self.origin);
|
||||||
|
makevectors (offang);
|
||||||
|
|
||||||
|
org = self.origin + p_x*v_forward + p_y*v_right + p_z*'0 0 1';
|
||||||
|
|
||||||
|
// lead the player on hard mode
|
||||||
|
if (skill > 1)
|
||||||
|
{
|
||||||
|
t = vlen(self.enemy.origin - org) / 300;
|
||||||
|
vec = self.enemy.velocity;
|
||||||
|
vec_z = 0;
|
||||||
|
d = self.enemy.origin + t * vec;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
d = self.enemy.origin;
|
||||||
|
}
|
||||||
|
|
||||||
|
vec = normalize(d - org) * 300;
|
||||||
|
|
||||||
|
PRJ_FireProjectile(self, "progs/lavaball.mdl", org, vec, PE_EXPLOSION, 100+random()*20, MOD_CHTHON, 5);
|
||||||
|
PRJ_SetRadiusDamage(120, 160, MOD_CHTHON);
|
||||||
|
newmis.avelocity = '200 100 300';
|
||||||
|
|
||||||
|
sound (self, CHAN_WEAPON, "boss1/throw.wav", 1, ATTN_NORM);
|
||||||
|
|
||||||
|
// check for dead enemy
|
||||||
|
if (self.enemy.health <= 0)
|
||||||
|
boss_idle1 ();
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
void() boss_awake =
|
||||||
|
{
|
||||||
|
self.solid = SOLID_SLIDEBOX;
|
||||||
|
self.movetype = MOVETYPE_STEP;
|
||||||
|
self.takedamage = DAMAGE_NO;
|
||||||
|
|
||||||
|
setmodel (self, "progs/boss.mdl");
|
||||||
|
setsize (self, '-128 -128 -24', '128 128 256');
|
||||||
|
|
||||||
|
if (skill == 0)
|
||||||
|
self.health = 1;
|
||||||
|
else
|
||||||
|
self.health = 3;
|
||||||
|
|
||||||
|
self.enemy = activator;
|
||||||
|
|
||||||
|
TE_lavasplash(self.origin);
|
||||||
|
|
||||||
|
self.yaw_speed = 20;
|
||||||
|
boss_rise1 ();
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
/*QUAKED monster_boss (1 0 0) (-128 -128 -24) (128 128 256)
|
||||||
|
*/
|
||||||
|
void() monster_boss =
|
||||||
|
{
|
||||||
|
if (deathmatch)
|
||||||
|
{
|
||||||
|
remove(self);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
precache_model ("progs/boss.mdl");
|
||||||
|
precache_model ("progs/lavaball.mdl");
|
||||||
|
|
||||||
|
precache_sound ("weapons/rocket1i.wav");
|
||||||
|
precache_sound ("boss1/out1.wav");
|
||||||
|
precache_sound ("boss1/sight1.wav");
|
||||||
|
precache_sound ("misc/power.wav");
|
||||||
|
precache_sound ("boss1/throw.wav");
|
||||||
|
precache_sound ("boss1/pain.wav");
|
||||||
|
precache_sound ("boss1/death.wav");
|
||||||
|
|
||||||
|
total_monsters = total_monsters + 1;
|
||||||
|
|
||||||
|
self.use = boss_awake;
|
||||||
|
};
|
||||||
|
|
||||||
|
//===========================================================================
|
||||||
|
|
||||||
|
entity le1, le2;
|
||||||
|
float lightning_end;
|
||||||
|
|
||||||
|
void() lightning_fire =
|
||||||
|
{
|
||||||
|
local vector p1, p2;
|
||||||
|
|
||||||
|
if (time >= lightning_end)
|
||||||
|
{ // done here, put the terminals back up
|
||||||
|
self = le1;
|
||||||
|
door_go_down ();
|
||||||
|
self = le2;
|
||||||
|
door_go_down ();
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
p1 = (le1.mins + le1.maxs) * 0.5;
|
||||||
|
p1_z = le1.absmin_z - 16;
|
||||||
|
|
||||||
|
p2 = (le2.mins + le2.maxs) * 0.5;
|
||||||
|
p2_z = le2.absmin_z - 16;
|
||||||
|
|
||||||
|
// compensate for length of bolt
|
||||||
|
p2 = p2 - normalize(p2-p1)*100;
|
||||||
|
|
||||||
|
self.nextthink = time + 0.1;
|
||||||
|
self.think = lightning_fire;
|
||||||
|
|
||||||
|
TE_lightning3(world, p1, p2);
|
||||||
|
};
|
||||||
|
|
||||||
|
void() lightning_use =
|
||||||
|
{
|
||||||
|
if (lightning_end >= time + 1)
|
||||||
|
return;
|
||||||
|
|
||||||
|
le1 = find( world, target, "lightning");
|
||||||
|
le2 = find( le1, target, "lightning");
|
||||||
|
if (!le1 || !le2)
|
||||||
|
{
|
||||||
|
dprint ("missing lightning targets\n");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (
|
||||||
|
(le1.state != STATE_TOP && le1.state != STATE_BOTTOM)
|
||||||
|
|| (le2.state != STATE_TOP && le2.state != STATE_BOTTOM)
|
||||||
|
|| (le1.state != le2.state) )
|
||||||
|
{
|
||||||
|
// dprint ("not aligned\n");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// don't let the electrodes go back up until the bolt is done
|
||||||
|
le1.nextthink = -1;
|
||||||
|
le2.nextthink = -1;
|
||||||
|
lightning_end = time + 1;
|
||||||
|
|
||||||
|
sound (self, CHAN_VOICE, "misc/power.wav", 1, ATTN_NORM);
|
||||||
|
lightning_fire ();
|
||||||
|
|
||||||
|
// advance the boss pain if down
|
||||||
|
self = find (world, classname, "monster_boss");
|
||||||
|
if (!self)
|
||||||
|
return;
|
||||||
|
self.enemy = activator;
|
||||||
|
if (le1.state == STATE_TOP && self.health > 0)
|
||||||
|
{
|
||||||
|
sound (self, CHAN_VOICE, "boss1/pain.wav", 1, ATTN_NORM);
|
||||||
|
self.health = self.health - 1;
|
||||||
|
if (self.health >= 2)
|
||||||
|
boss_shocka1();
|
||||||
|
else if (self.health == 1)
|
||||||
|
boss_shockb1();
|
||||||
|
else if (self.health == 0)
|
||||||
|
boss_shockc1();
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
/*QUAKED event_lightning (0 1 1) (-16 -16 -16) (16 16 16)
|
||||||
|
Just for boss level.
|
||||||
|
*/
|
||||||
|
void() event_lightning =
|
||||||
|
{
|
||||||
|
if (deathmatch)
|
||||||
|
{
|
||||||
|
remove(self);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
self.use = lightning_use;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
|
@ -76,7 +76,7 @@ void() SetNewParms =
|
||||||
|
|
||||||
void() DecodeLevelParms =
|
void() DecodeLevelParms =
|
||||||
{
|
{
|
||||||
if (serverflags)
|
if (!deathmatch)
|
||||||
{
|
{
|
||||||
if (world.model == "maps/start.bsp")
|
if (world.model == "maps/start.bsp")
|
||||||
SetNewParms (); // take away all stuff on starting new episode
|
SetNewParms (); // take away all stuff on starting new episode
|
||||||
|
@ -317,11 +317,14 @@ void() changelevel_touch =
|
||||||
// if "noexit" is set, blow up the player trying to leave
|
// if "noexit" is set, blow up the player trying to leave
|
||||||
//ZOID, 12-13-96, noexit isn't supported in QW. Overload samelevel
|
//ZOID, 12-13-96, noexit isn't supported in QW. Overload samelevel
|
||||||
// if ((cvar("noexit") == 1) || ((cvar("noexit") == 2) && (mapname != "start")))
|
// if ((cvar("noexit") == 1) || ((cvar("noexit") == 2) && (mapname != "start")))
|
||||||
|
if (deathmatch)
|
||||||
|
{
|
||||||
if ((cvar("samelevel") == 2) || ((cvar("samelevel") == 3) && (mapname != "start")))
|
if ((cvar("samelevel") == 2) || ((cvar("samelevel") == 3) && (mapname != "start")))
|
||||||
{
|
{
|
||||||
T_Damage (other, self, self, 50000, MOD_EXIT);
|
T_Damage (other, self, self, 50000, MOD_EXIT);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
bprint2 (PRINT_HIGH, other.netname, " exited the level\n");
|
bprint2 (PRINT_HIGH, other.netname, " exited the level\n");
|
||||||
|
|
||||||
|
@ -904,6 +907,26 @@ void() WaterMove =
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if ( !(self.flags & FL_INWATER) )
|
||||||
|
{
|
||||||
|
// player enter water sound
|
||||||
|
switch (self.watertype)
|
||||||
|
{
|
||||||
|
case CONTENT_LAVA:
|
||||||
|
sound (self, CHAN_BODY, "player/inlava.wav", 1, ATTN_NORM);
|
||||||
|
break;
|
||||||
|
case CONTENT_WATER:
|
||||||
|
sound (self, CHAN_BODY, "player/inh2o.wav", 1, ATTN_NORM);
|
||||||
|
break;
|
||||||
|
case CONTENT_SLIME:
|
||||||
|
sound (self, CHAN_BODY, "player/slimbrn2.wav", 1, ATTN_NORM);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
self.flags = self.flags + FL_INWATER;
|
||||||
|
self.dmgtime = 0;
|
||||||
|
}
|
||||||
|
|
||||||
if (self.watertype == CONTENT_LAVA)
|
if (self.watertype == CONTENT_LAVA)
|
||||||
{ // do damage
|
{ // do damage
|
||||||
if (self.dmgtime < time)
|
if (self.dmgtime < time)
|
||||||
|
@ -925,21 +948,6 @@ void() WaterMove =
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if ( !(self.flags & FL_INWATER) )
|
|
||||||
{
|
|
||||||
|
|
||||||
// player enter water sound
|
|
||||||
|
|
||||||
if (self.watertype == CONTENT_LAVA)
|
|
||||||
sound (self, CHAN_BODY, "player/inlava.wav", 1, ATTN_NORM);
|
|
||||||
if (self.watertype == CONTENT_WATER)
|
|
||||||
sound (self, CHAN_BODY, "player/inh2o.wav", 1, ATTN_NORM);
|
|
||||||
if (self.watertype == CONTENT_SLIME)
|
|
||||||
sound (self, CHAN_BODY, "player/slimbrn2.wav", 1, ATTN_NORM);
|
|
||||||
|
|
||||||
self.flags = self.flags + FL_INWATER;
|
|
||||||
self.dmgtime = 0;
|
|
||||||
}
|
|
||||||
};
|
};
|
||||||
|
|
||||||
void() CheckWaterJump =
|
void() CheckWaterJump =
|
||||||
|
@ -1276,7 +1284,7 @@ float(entity targ, entity attacker) OnSameTeam;
|
||||||
|
|
||||||
void(entity targ, entity attacker, INTEGER mod) ClientObituary =
|
void(entity targ, entity attacker, INTEGER mod) ClientObituary =
|
||||||
{
|
{
|
||||||
if (attacker.classname == "player")
|
if (attacker.flags & FL_CLIENT)
|
||||||
{
|
{
|
||||||
if (attacker == targ)
|
if (attacker == targ)
|
||||||
{
|
{
|
||||||
|
@ -1294,29 +1302,20 @@ void(entity targ, entity attacker, INTEGER mod) ClientObituary =
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
KillMessage(targ.netname, attacker.netname, mod);
|
if (targ.flags & FL_CLIENT)
|
||||||
if (targ.classname == "player")
|
|
||||||
{
|
{
|
||||||
|
KillMessage(targ.netname, attacker.netname, mod);
|
||||||
attacker.frags = attacker.frags + 1;
|
attacker.frags = attacker.frags + 1;
|
||||||
logfrag(attacker, targ);
|
logfrag(attacker, targ);
|
||||||
}
|
}
|
||||||
return;
|
return;
|
||||||
} // else if attacker != player
|
} // else if attacker != player
|
||||||
|
|
||||||
if (attacker.netname == "")
|
if (targ.flags & FL_CLIENT)
|
||||||
{
|
{
|
||||||
WorldKillMessage(targ.netname, mod);
|
WorldKillMessage(targ.netname, mod);
|
||||||
if (targ.classname == "player")
|
|
||||||
{
|
|
||||||
targ.frags = targ.frags - 1;
|
targ.frags = targ.frags - 1;
|
||||||
logfrag(targ, targ);
|
logfrag(targ, targ);
|
||||||
}
|
}
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
// monster kill, but still consider it a suicide for score purposes
|
|
||||||
KillMessage(targ.netname, attacker.netname, mod);
|
|
||||||
targ.frags = targ.frags - 1;
|
|
||||||
logfrag(targ, targ);
|
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
|
@ -3,9 +3,10 @@ void() info_player_start;
|
||||||
void(entity targ, entity attacker, INTEGER mod) ClientObituary;
|
void(entity targ, entity attacker, INTEGER mod) ClientObituary;
|
||||||
void(entity inflictor, entity attacker, float damage, float radius, entity ignore, INTEGER mod) T_RadiusDamage;
|
void(entity inflictor, entity attacker, float damage, float radius, entity ignore, INTEGER mod) T_RadiusDamage;
|
||||||
|
|
||||||
/*SERVER
|
#ifdef MONSTERS
|
||||||
void() monster_death_use;
|
void() monster_death_use;
|
||||||
*/
|
void() FoundTarget;
|
||||||
|
#endif
|
||||||
|
|
||||||
//============================================================================
|
//============================================================================
|
||||||
|
|
||||||
|
@ -75,11 +76,14 @@ void(entity targ, entity attacker, INTEGER mod) Killed =
|
||||||
}
|
}
|
||||||
|
|
||||||
// bump the monster counter
|
// bump the monster counter
|
||||||
|
#ifdef MONSTERS
|
||||||
if (self.flags & FL_MONSTER)
|
if (self.flags & FL_MONSTER)
|
||||||
{
|
{
|
||||||
killed_monsters = killed_monsters + 1;
|
killed_monsters = killed_monsters + 1;
|
||||||
WriteByte (MSG_ALL, SVC_KILLEDMONSTER);
|
WriteByte (MSG_ALL, SVC_KILLEDMONSTER);
|
||||||
|
monster_death_use();
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
ClientObituary(self, attacker, mod);
|
ClientObituary(self, attacker, mod);
|
||||||
|
|
||||||
|
@ -87,9 +91,6 @@ void(entity targ, entity attacker, INTEGER mod) Killed =
|
||||||
self.touch = SUB_Null;
|
self.touch = SUB_Null;
|
||||||
self.effects = 0;
|
self.effects = 0;
|
||||||
|
|
||||||
/*SERVER
|
|
||||||
monster_death_use();
|
|
||||||
*/
|
|
||||||
self.th_die ();
|
self.th_die ();
|
||||||
|
|
||||||
self = oself;
|
self = oself;
|
||||||
|
@ -258,7 +259,7 @@ void(entity targ, entity inflictor, entity attacker, float damage, INTEGER mod)
|
||||||
oldself = self;
|
oldself = self;
|
||||||
self = targ;
|
self = targ;
|
||||||
|
|
||||||
/*SERVER
|
#ifdef MONSTERS
|
||||||
if ( (self.flags & FL_MONSTER) && attacker != world)
|
if ( (self.flags & FL_MONSTER) && attacker != world)
|
||||||
{
|
{
|
||||||
// get mad unless of the same class (except for soldiers)
|
// get mad unless of the same class (except for soldiers)
|
||||||
|
@ -274,7 +275,8 @@ void(entity targ, entity inflictor, entity attacker, float damage, INTEGER mod)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
*/
|
#endif
|
||||||
|
|
||||||
if (self.th_pain)
|
if (self.th_pain)
|
||||||
{
|
{
|
||||||
self.th_pain (attacker, take);
|
self.th_pain (attacker, take);
|
||||||
|
|
|
@ -282,13 +282,6 @@ void end_sys_fields; // flag for structure dumping
|
||||||
#define SOLID_SLIDEBOX 3 // touch on edge, but not an onground
|
#define SOLID_SLIDEBOX 3 // touch on edge, but not an onground
|
||||||
#define SOLID_BSP 4 // bsp clip, touch on edge, block
|
#define SOLID_BSP 4 // bsp clip, touch on edge, block
|
||||||
|
|
||||||
// range values
|
|
||||||
/*
|
|
||||||
float RANGE_MELEE = 0;
|
|
||||||
float RANGE_NEAR = 1;
|
|
||||||
float RANGE_MID = 2;
|
|
||||||
float RANGE_FAR = 3;
|
|
||||||
*/
|
|
||||||
|
|
||||||
// deadflag values
|
// deadflag values
|
||||||
#define DEAD_NO 0
|
#define DEAD_NO 0
|
||||||
|
@ -462,6 +455,8 @@ float skill;
|
||||||
entity lastspawn;
|
entity lastspawn;
|
||||||
float spotspawn;
|
float spotspawn;
|
||||||
|
|
||||||
|
entity shub; // boss entity
|
||||||
|
|
||||||
//================================================
|
//================================================
|
||||||
|
|
||||||
#define WT_MEDIEVAL 0
|
#define WT_MEDIEVAL 0
|
||||||
|
@ -497,7 +492,7 @@ float spotspawn;
|
||||||
//
|
//
|
||||||
// misc
|
// misc
|
||||||
//
|
//
|
||||||
.float cnt; // misc flag used by trains/dropped pent and quad
|
.float cnt; // misc flag used by trains/dropped pent and quad/monsters
|
||||||
|
|
||||||
// intermission
|
// intermission
|
||||||
float intermission_running;
|
float intermission_running;
|
||||||
|
@ -511,6 +506,15 @@ entity newmis;
|
||||||
.float alpha; // DP_ENT_ALPHA
|
.float alpha; // DP_ENT_ALPHA
|
||||||
|
|
||||||
// enums
|
// enums
|
||||||
|
// ai ranges
|
||||||
|
enum
|
||||||
|
{
|
||||||
|
RANGE_MELEE,
|
||||||
|
RANGE_NEAR,
|
||||||
|
RANGE_MID,
|
||||||
|
RANGE_FAR
|
||||||
|
};
|
||||||
|
|
||||||
// monster attack states
|
// monster attack states
|
||||||
enum
|
enum
|
||||||
{
|
{
|
||||||
|
@ -600,7 +604,7 @@ enum {
|
||||||
float swim_flag; // swim sound playback
|
float swim_flag; // swim sound playback
|
||||||
float air_finished; // when time > air_finished, start drowning
|
float air_finished; // when time > air_finished, start drowning
|
||||||
float waterdmg; // damage water will deal when drowning
|
float waterdmg; // damage water will deal when drowning
|
||||||
float walkframe; // used with walking animation
|
INTEGER walkframe; // used with walking animation
|
||||||
float jump_flag; // last z velocity used for falling damage
|
float jump_flag; // last z velocity used for falling damage
|
||||||
INTEGER ammo_type; // ammo type in use
|
INTEGER ammo_type; // ammo type in use
|
||||||
};
|
};
|
||||||
|
@ -614,10 +618,6 @@ enum {
|
||||||
string mdl; // model used with SUB_regen
|
string mdl; // model used with SUB_regen
|
||||||
float ammo_count; // ammo amount
|
float ammo_count; // ammo amount
|
||||||
};
|
};
|
||||||
struct { // fields used with monsters
|
|
||||||
float pausetime; // time to pause for monsters
|
|
||||||
entity movetarget; // target entity to move to
|
|
||||||
};
|
|
||||||
struct { // fields used with generic projectiles
|
struct { // fields used with generic projectiles
|
||||||
float damage_direct; // damage done with a direct hit
|
float damage_direct; // damage done with a direct hit
|
||||||
float damage_exp; // damage done from radius damage
|
float damage_exp; // damage done from radius damage
|
||||||
|
@ -644,6 +644,12 @@ enum {
|
||||||
void() th_missile; // ranged animation
|
void() th_missile; // ranged animation
|
||||||
void() th_melee; // melee animation
|
void() th_melee; // melee animation
|
||||||
entity oldenemy; // old enemy
|
entity oldenemy; // old enemy
|
||||||
|
entity movetarget; // target entity to move to
|
||||||
|
float pausetime; // time to pause for monsters
|
||||||
|
float hknightattack; // hell knight attack pattern
|
||||||
|
float lefty; // ai slide move
|
||||||
|
float wizardidle; // wizard idle sound timer
|
||||||
|
float inpain; // zombie in pain
|
||||||
};
|
};
|
||||||
// fields used with ambient sounds?
|
// fields used with ambient sounds?
|
||||||
/*
|
/*
|
||||||
|
@ -781,7 +787,6 @@ void() SUB_Remove;
|
||||||
//
|
//
|
||||||
void(entity targ, entity inflictor, entity attacker, float damage, INTEGER mod) T_Damage;
|
void(entity targ, entity inflictor, entity attacker, float damage, INTEGER mod) T_Damage;
|
||||||
|
|
||||||
|
|
||||||
float (entity e, float healamount, float ignore) T_Heal; // health function
|
float (entity e, float healamount, float ignore) T_Heal; // health function
|
||||||
|
|
||||||
float(entity targ, entity inflictor) CanDamage;
|
float(entity targ, entity inflictor) CanDamage;
|
||||||
|
|
356
quakec/basemod/demon.qc
Normal file
356
quakec/basemod/demon.qc
Normal file
|
@ -0,0 +1,356 @@
|
||||||
|
/*
|
||||||
|
==============================================================================
|
||||||
|
|
||||||
|
DEMON
|
||||||
|
|
||||||
|
==============================================================================
|
||||||
|
*/
|
||||||
|
|
||||||
|
$cd id1/models/demon3
|
||||||
|
$scale 0.8
|
||||||
|
$origin 0 0 24
|
||||||
|
$base base
|
||||||
|
$skin base
|
||||||
|
|
||||||
|
$frame stand1 stand2 stand3 stand4 stand5 stand6 stand7 stand8 stand9
|
||||||
|
$frame stand10 stand11 stand12 stand13
|
||||||
|
|
||||||
|
$frame walk1 walk2 walk3 walk4 walk5 walk6 walk7 walk8
|
||||||
|
|
||||||
|
$frame run1 run2 run3 run4 run5 run6
|
||||||
|
|
||||||
|
$frame leap1 leap2 leap3 leap4 leap5 leap6 leap7 leap8 leap9 leap10
|
||||||
|
$frame leap11 leap12
|
||||||
|
|
||||||
|
$frame pain1 pain2 pain3 pain4 pain5 pain6
|
||||||
|
|
||||||
|
$frame death1 death2 death3 death4 death5 death6 death7 death8 death9
|
||||||
|
|
||||||
|
$frame attacka1 attacka2 attacka3 attacka4 attacka5 attacka6 attacka7 attacka8
|
||||||
|
$frame attacka9 attacka10 attacka11 attacka12 attacka13 attacka14 attacka15
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
|
||||||
|
void() Demon_JumpTouch;
|
||||||
|
void(float side) Demon_Melee;
|
||||||
|
|
||||||
|
void() demon1_stand1 =[ $stand1, demon1_stand2 ] {ai_stand();};
|
||||||
|
void() demon1_stand2 =[ $stand2, demon1_stand3 ] {ai_stand();};
|
||||||
|
void() demon1_stand3 =[ $stand3, demon1_stand4 ] {ai_stand();};
|
||||||
|
void() demon1_stand4 =[ $stand4, demon1_stand5 ] {ai_stand();};
|
||||||
|
void() demon1_stand5 =[ $stand5, demon1_stand6 ] {ai_stand();};
|
||||||
|
void() demon1_stand6 =[ $stand6, demon1_stand7 ] {ai_stand();};
|
||||||
|
void() demon1_stand7 =[ $stand7, demon1_stand8 ] {ai_stand();};
|
||||||
|
void() demon1_stand8 =[ $stand8, demon1_stand9 ] {ai_stand();};
|
||||||
|
void() demon1_stand9 =[ $stand9, demon1_stand10 ] {ai_stand();};
|
||||||
|
void() demon1_stand10 =[ $stand10, demon1_stand11 ] {ai_stand();};
|
||||||
|
void() demon1_stand11 =[ $stand11, demon1_stand12 ] {ai_stand();};
|
||||||
|
void() demon1_stand12 =[ $stand12, demon1_stand13 ] {ai_stand();};
|
||||||
|
void() demon1_stand13 =[ $stand13, demon1_stand1 ] {ai_stand();};
|
||||||
|
|
||||||
|
void() demon1_walk1 =[ $walk1, demon1_walk2 ] {
|
||||||
|
if (random() < 0.2)
|
||||||
|
sound (self, CHAN_VOICE, "demon/idle1.wav", 1, ATTN_IDLE);
|
||||||
|
ai_walk(8);
|
||||||
|
};
|
||||||
|
void() demon1_walk2 =[ $walk2, demon1_walk3 ] {ai_walk(6);};
|
||||||
|
void() demon1_walk3 =[ $walk3, demon1_walk4 ] {ai_walk(6);};
|
||||||
|
void() demon1_walk4 =[ $walk4, demon1_walk5 ] {ai_walk(7);};
|
||||||
|
void() demon1_walk5 =[ $walk5, demon1_walk6 ] {ai_walk(4);};
|
||||||
|
void() demon1_walk6 =[ $walk6, demon1_walk7 ] {ai_walk(6);};
|
||||||
|
void() demon1_walk7 =[ $walk7, demon1_walk8 ] {ai_walk(10);};
|
||||||
|
void() demon1_walk8 =[ $walk8, demon1_walk1 ] {ai_walk(10);};
|
||||||
|
|
||||||
|
void() demon1_run1 =[ $run1, demon1_run2 ] {
|
||||||
|
if (random() < 0.2)
|
||||||
|
sound (self, CHAN_VOICE, "demon/idle1.wav", 1, ATTN_IDLE);
|
||||||
|
ai_run(20);};
|
||||||
|
void() demon1_run2 =[ $run2, demon1_run3 ] {ai_run(15);};
|
||||||
|
void() demon1_run3 =[ $run3, demon1_run4 ] {ai_run(36);};
|
||||||
|
void() demon1_run4 =[ $run4, demon1_run5 ] {ai_run(20);};
|
||||||
|
void() demon1_run5 =[ $run5, demon1_run6 ] {ai_run(15);};
|
||||||
|
void() demon1_run6 =[ $run6, demon1_run1 ] {ai_run(36);};
|
||||||
|
|
||||||
|
void() demon1_jump1 =[ $leap1, demon1_jump2 ] {ai_face();};
|
||||||
|
void() demon1_jump2 =[ $leap2, demon1_jump3 ] {ai_face();};
|
||||||
|
void() demon1_jump3 =[ $leap3, demon1_jump4 ] {ai_face();};
|
||||||
|
void() demon1_jump4 =[ $leap4, demon1_jump5 ]
|
||||||
|
{
|
||||||
|
ai_face();
|
||||||
|
|
||||||
|
self.touch = Demon_JumpTouch;
|
||||||
|
makevectors (self.angles);
|
||||||
|
self.origin_z = self.origin_z + 1;
|
||||||
|
self.velocity = v_forward * 600 + '0 0 250';
|
||||||
|
if (self.flags & FL_ONGROUND)
|
||||||
|
self.flags = self.flags - FL_ONGROUND;
|
||||||
|
};
|
||||||
|
void() demon1_jump5 =[ $leap5, demon1_jump6 ] {};
|
||||||
|
void() demon1_jump6 =[ $leap6, demon1_jump7 ] {};
|
||||||
|
void() demon1_jump7 =[ $leap7, demon1_jump8 ] {};
|
||||||
|
void() demon1_jump8 =[ $leap8, demon1_jump9 ] {};
|
||||||
|
void() demon1_jump9 =[ $leap9, demon1_jump10 ] {};
|
||||||
|
void() demon1_jump10 =[ $leap10, demon1_jump1 ] {
|
||||||
|
self.nextthink = time + 3;
|
||||||
|
// if three seconds pass, assume demon is stuck and jump again
|
||||||
|
};
|
||||||
|
|
||||||
|
void() demon1_jump11 =[ $leap11, demon1_jump12 ] {};
|
||||||
|
void() demon1_jump12 =[ $leap12, demon1_run1 ] {};
|
||||||
|
|
||||||
|
|
||||||
|
void() demon1_atta1 =[ $attacka1, demon1_atta2 ] {ai_charge(4);};
|
||||||
|
void() demon1_atta2 =[ $attacka2, demon1_atta3 ] {ai_charge(0);};
|
||||||
|
void() demon1_atta3 =[ $attacka3, demon1_atta4 ] {ai_charge(0);};
|
||||||
|
void() demon1_atta4 =[ $attacka4, demon1_atta5 ] {ai_charge(1);};
|
||||||
|
void() demon1_atta5 =[ $attacka5, demon1_atta6 ] {ai_charge(2); Demon_Melee(200);};
|
||||||
|
void() demon1_atta6 =[ $attacka6, demon1_atta7 ] {ai_charge(1);};
|
||||||
|
void() demon1_atta7 =[ $attacka7, demon1_atta8 ] {ai_charge(6);};
|
||||||
|
void() demon1_atta8 =[ $attacka8, demon1_atta9 ] {ai_charge(8);};
|
||||||
|
void() demon1_atta9 =[ $attacka9, demon1_atta10] {ai_charge(4);};
|
||||||
|
void() demon1_atta10 =[ $attacka10, demon1_atta11] {ai_charge(2);};
|
||||||
|
void() demon1_atta11 =[ $attacka11, demon1_atta12] {Demon_Melee(-200);};
|
||||||
|
void() demon1_atta12 =[ $attacka12, demon1_atta13] {ai_charge(5);};
|
||||||
|
void() demon1_atta13 =[ $attacka13, demon1_atta14] {ai_charge(8);};
|
||||||
|
void() demon1_atta14 =[ $attacka14, demon1_atta15] {ai_charge(4);};
|
||||||
|
void() demon1_atta15 =[ $attacka15, demon1_run1] {ai_charge(4);};
|
||||||
|
|
||||||
|
void() demon1_pain1 =[ $pain1, demon1_pain2 ] {};
|
||||||
|
void() demon1_pain2 =[ $pain2, demon1_pain3 ] {};
|
||||||
|
void() demon1_pain3 =[ $pain3, demon1_pain4 ] {};
|
||||||
|
void() demon1_pain4 =[ $pain4, demon1_pain5 ] {};
|
||||||
|
void() demon1_pain5 =[ $pain5, demon1_pain6 ] {};
|
||||||
|
void() demon1_pain6 =[ $pain6, demon1_run1 ] {};
|
||||||
|
|
||||||
|
void(entity attacker, float damage) demon1_pain =
|
||||||
|
{
|
||||||
|
if (self.touch == Demon_JumpTouch)
|
||||||
|
return;
|
||||||
|
|
||||||
|
if (self.pain_finished > time)
|
||||||
|
return;
|
||||||
|
|
||||||
|
self.pain_finished = time + 1;
|
||||||
|
sound (self, CHAN_VOICE, "demon/dpain1.wav", 1, ATTN_NORM);
|
||||||
|
|
||||||
|
if (random()*200 > damage)
|
||||||
|
return; // didn't flinch
|
||||||
|
|
||||||
|
demon1_pain1 ();
|
||||||
|
};
|
||||||
|
|
||||||
|
void() demon1_die1 =[ $death1, demon1_die2 ] {
|
||||||
|
sound (self, CHAN_VOICE, "demon/ddeath.wav", 1, ATTN_NORM);};
|
||||||
|
void() demon1_die2 =[ $death2, demon1_die3 ] {};
|
||||||
|
void() demon1_die3 =[ $death3, demon1_die4 ] {};
|
||||||
|
void() demon1_die4 =[ $death4, demon1_die5 ] {};
|
||||||
|
void() demon1_die5 =[ $death5, demon1_die6 ] {};
|
||||||
|
void() demon1_die6 =[ $death6, demon1_die7 ]
|
||||||
|
{self.solid = SOLID_NOT;};
|
||||||
|
void() demon1_die7 =[ $death7, demon1_die8 ] {};
|
||||||
|
void() demon1_die8 =[ $death8, demon1_die9 ] {};
|
||||||
|
void() demon1_die9 =[ $death9, demon1_die9 ] {};
|
||||||
|
|
||||||
|
void() demon_die =
|
||||||
|
{
|
||||||
|
// check for gib
|
||||||
|
if (self.health < -80)
|
||||||
|
{
|
||||||
|
sound (self, CHAN_VOICE, "player/udeath.wav", 1, ATTN_NORM);
|
||||||
|
ThrowHead ("progs/h_demon.mdl", self.health);
|
||||||
|
ThrowGib ("progs/gib1.mdl", self.health);
|
||||||
|
ThrowGib ("progs/gib1.mdl", self.health);
|
||||||
|
ThrowGib ("progs/gib1.mdl", self.health);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// regular death
|
||||||
|
demon1_die1 ();
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
void() Demon_MeleeAttack =
|
||||||
|
{
|
||||||
|
demon1_atta1 ();
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
/*QUAKED monster_demon1 (1 0 0) (-32 -32 -24) (32 32 64) Ambush
|
||||||
|
|
||||||
|
*/
|
||||||
|
void() monster_demon1 =
|
||||||
|
{
|
||||||
|
if (deathmatch)
|
||||||
|
{
|
||||||
|
remove(self);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
precache_model ("progs/demon.mdl");
|
||||||
|
precache_model ("progs/h_demon.mdl");
|
||||||
|
|
||||||
|
precache_sound ("demon/ddeath.wav");
|
||||||
|
precache_sound ("demon/dhit2.wav");
|
||||||
|
precache_sound ("demon/djump.wav");
|
||||||
|
precache_sound ("demon/dpain1.wav");
|
||||||
|
precache_sound ("demon/idle1.wav");
|
||||||
|
precache_sound ("demon/sight2.wav");
|
||||||
|
|
||||||
|
self.solid = SOLID_SLIDEBOX;
|
||||||
|
self.movetype = MOVETYPE_STEP;
|
||||||
|
|
||||||
|
setmodel (self, "progs/demon.mdl");
|
||||||
|
|
||||||
|
setsize (self, VEC_HULL2_MIN, VEC_HULL2_MAX);
|
||||||
|
self.health = 300;
|
||||||
|
|
||||||
|
self.th_stand = demon1_stand1;
|
||||||
|
self.th_walk = demon1_walk1;
|
||||||
|
self.th_run = demon1_run1;
|
||||||
|
self.th_die = demon_die;
|
||||||
|
self.th_melee = Demon_MeleeAttack; // one of two attacks
|
||||||
|
self.th_missile = demon1_jump1; // jump attack
|
||||||
|
self.th_pain = demon1_pain;
|
||||||
|
|
||||||
|
walkmonster_start();
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
/*
|
||||||
|
==============================================================================
|
||||||
|
|
||||||
|
DEMON
|
||||||
|
|
||||||
|
==============================================================================
|
||||||
|
*/
|
||||||
|
|
||||||
|
/*
|
||||||
|
==============
|
||||||
|
CheckDemonMelee
|
||||||
|
|
||||||
|
Returns TRUE if a melee attack would hit right now
|
||||||
|
==============
|
||||||
|
*/
|
||||||
|
float(float enemy_range) CheckDemonMelee =
|
||||||
|
{
|
||||||
|
if (enemy_range == RANGE_MELEE)
|
||||||
|
{ // FIXME: check canreach
|
||||||
|
self.attack_state = AS_MELEE;
|
||||||
|
return TRUE;
|
||||||
|
}
|
||||||
|
return FALSE;
|
||||||
|
};
|
||||||
|
|
||||||
|
/*
|
||||||
|
==============
|
||||||
|
CheckDemonJump
|
||||||
|
|
||||||
|
==============
|
||||||
|
*/
|
||||||
|
float() CheckDemonJump =
|
||||||
|
{
|
||||||
|
local vector dist;
|
||||||
|
local float d;
|
||||||
|
|
||||||
|
if (self.origin_z + self.mins_z > self.enemy.origin_z + self.enemy.mins_z
|
||||||
|
+ 0.75 * self.enemy.size_z)
|
||||||
|
return FALSE;
|
||||||
|
|
||||||
|
if (self.origin_z + self.maxs_z < self.enemy.origin_z + self.enemy.mins_z
|
||||||
|
+ 0.25 * self.enemy.size_z)
|
||||||
|
return FALSE;
|
||||||
|
|
||||||
|
dist = self.enemy.origin - self.origin;
|
||||||
|
dist_z = 0;
|
||||||
|
|
||||||
|
d = vlen(dist);
|
||||||
|
|
||||||
|
if (d < 100)
|
||||||
|
return FALSE;
|
||||||
|
|
||||||
|
if (d > 200)
|
||||||
|
{
|
||||||
|
if (random() < 0.9)
|
||||||
|
return FALSE;
|
||||||
|
}
|
||||||
|
|
||||||
|
return TRUE;
|
||||||
|
};
|
||||||
|
|
||||||
|
float(float enemy_range) DemonCheckAttack =
|
||||||
|
{
|
||||||
|
// if close enough for slashing, go for it
|
||||||
|
if (CheckDemonMelee (enemy_range))
|
||||||
|
{
|
||||||
|
self.attack_state = AS_MELEE;
|
||||||
|
return TRUE;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (CheckDemonJump ())
|
||||||
|
{
|
||||||
|
self.attack_state = AS_MISSILE;
|
||||||
|
sound (self, CHAN_VOICE, "demon/djump.wav", 1, ATTN_NORM);
|
||||||
|
return TRUE;
|
||||||
|
}
|
||||||
|
|
||||||
|
return FALSE;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
//===========================================================================
|
||||||
|
|
||||||
|
void(float side) Demon_Melee =
|
||||||
|
{
|
||||||
|
local float ldmg;
|
||||||
|
local vector delta;
|
||||||
|
|
||||||
|
ai_face ();
|
||||||
|
walkmove (self.ideal_yaw, 12); // allow a little closing
|
||||||
|
|
||||||
|
delta = self.enemy.origin - self.origin;
|
||||||
|
|
||||||
|
if (vlen(delta) > 100)
|
||||||
|
return;
|
||||||
|
if (!CanDamage (self.enemy, self))
|
||||||
|
return;
|
||||||
|
|
||||||
|
sound (self, CHAN_WEAPON, "demon/dhit2.wav", 1, ATTN_NORM);
|
||||||
|
ldmg = 10 + 5*random();
|
||||||
|
T_Damage (self.enemy, self, self, ldmg, MOD_DEMON);
|
||||||
|
|
||||||
|
makevectors (self.angles);
|
||||||
|
SpawnMeatSpray (self.origin + v_forward*16, side * v_right);
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
void() Demon_JumpTouch =
|
||||||
|
{
|
||||||
|
local float ldmg;
|
||||||
|
|
||||||
|
if (self.health <= 0)
|
||||||
|
return;
|
||||||
|
|
||||||
|
if (other.takedamage)
|
||||||
|
{
|
||||||
|
if ( vlen(self.velocity) > 400 )
|
||||||
|
{
|
||||||
|
ldmg = 40 + 10*random();
|
||||||
|
T_Damage (other, self, self, ldmg, MOD_DEMON);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!checkbottom(self))
|
||||||
|
{
|
||||||
|
if (self.flags & FL_ONGROUND)
|
||||||
|
{ // jump randomly to not get hung up
|
||||||
|
self.touch = SUB_Null;
|
||||||
|
self.think = demon1_jump1;
|
||||||
|
self.nextthink = time + 0.1;
|
||||||
|
}
|
||||||
|
return; // not on ground yet
|
||||||
|
}
|
||||||
|
|
||||||
|
self.touch = SUB_Null;
|
||||||
|
self.think = demon1_jump11;
|
||||||
|
self.nextthink = time + 0.1;
|
||||||
|
};
|
||||||
|
|
356
quakec/basemod/dog.qc
Normal file
356
quakec/basemod/dog.qc
Normal file
|
@ -0,0 +1,356 @@
|
||||||
|
/*
|
||||||
|
==============================================================================
|
||||||
|
|
||||||
|
DOG
|
||||||
|
|
||||||
|
==============================================================================
|
||||||
|
*/
|
||||||
|
$cd id1/models/dog
|
||||||
|
$origin 0 0 24
|
||||||
|
$base base
|
||||||
|
$skin skin
|
||||||
|
|
||||||
|
$frame attack1 attack2 attack3 attack4 attack5 attack6 attack7 attack8
|
||||||
|
|
||||||
|
$frame death1 death2 death3 death4 death5 death6 death7 death8 death9
|
||||||
|
|
||||||
|
$frame deathb1 deathb2 deathb3 deathb4 deathb5 deathb6 deathb7 deathb8
|
||||||
|
$frame deathb9
|
||||||
|
|
||||||
|
$frame pain1 pain2 pain3 pain4 pain5 pain6
|
||||||
|
|
||||||
|
$frame painb1 painb2 painb3 painb4 painb5 painb6 painb7 painb8 painb9 painb10
|
||||||
|
$frame painb11 painb12 painb13 painb14 painb15 painb16
|
||||||
|
|
||||||
|
$frame run1 run2 run3 run4 run5 run6 run7 run8 run9 run10 run11 run12
|
||||||
|
|
||||||
|
$frame leap1 leap2 leap3 leap4 leap5 leap6 leap7 leap8 leap9
|
||||||
|
|
||||||
|
$frame stand1 stand2 stand3 stand4 stand5 stand6 stand7 stand8 stand9
|
||||||
|
|
||||||
|
$frame walk1 walk2 walk3 walk4 walk5 walk6 walk7 walk8
|
||||||
|
|
||||||
|
|
||||||
|
void() dog_leap1;
|
||||||
|
void() dog_run1;
|
||||||
|
|
||||||
|
/*
|
||||||
|
================
|
||||||
|
dog_bite
|
||||||
|
|
||||||
|
================
|
||||||
|
*/
|
||||||
|
void() dog_bite =
|
||||||
|
{
|
||||||
|
local vector delta;
|
||||||
|
local float ldmg;
|
||||||
|
|
||||||
|
if (!self.enemy)
|
||||||
|
return;
|
||||||
|
|
||||||
|
ai_charge(10);
|
||||||
|
|
||||||
|
if (!CanDamage (self.enemy, self))
|
||||||
|
return;
|
||||||
|
|
||||||
|
delta = self.enemy.origin - self.origin;
|
||||||
|
|
||||||
|
if (vlen(delta) > 100)
|
||||||
|
return;
|
||||||
|
|
||||||
|
ldmg = (random() + random() + random()) * 8;
|
||||||
|
T_Damage (self.enemy, self, self, ldmg, MOD_DOG);
|
||||||
|
};
|
||||||
|
|
||||||
|
void() Dog_JumpTouch =
|
||||||
|
{
|
||||||
|
local float ldmg;
|
||||||
|
|
||||||
|
if (self.health <= 0)
|
||||||
|
return;
|
||||||
|
|
||||||
|
if (other.takedamage)
|
||||||
|
{
|
||||||
|
if ( vlen(self.velocity) > 300 )
|
||||||
|
{
|
||||||
|
ldmg = 10 + 10*random();
|
||||||
|
T_Damage (other, self, self, ldmg, MOD_DOG);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!checkbottom(self))
|
||||||
|
{
|
||||||
|
if (self.flags & FL_ONGROUND)
|
||||||
|
{
|
||||||
|
// jump randomly to not get hung up
|
||||||
|
self.touch = SUB_Null;
|
||||||
|
self.think = dog_leap1;
|
||||||
|
self.nextthink = time + 0.1;
|
||||||
|
}
|
||||||
|
return; // not on ground yet
|
||||||
|
}
|
||||||
|
|
||||||
|
self.touch = SUB_Null;
|
||||||
|
self.think = dog_run1;
|
||||||
|
self.nextthink = time + 0.1;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
void() dog_stand1 =[ $stand1, dog_stand2 ] {ai_stand();};
|
||||||
|
void() dog_stand2 =[ $stand2, dog_stand3 ] {ai_stand();};
|
||||||
|
void() dog_stand3 =[ $stand3, dog_stand4 ] {ai_stand();};
|
||||||
|
void() dog_stand4 =[ $stand4, dog_stand5 ] {ai_stand();};
|
||||||
|
void() dog_stand5 =[ $stand5, dog_stand6 ] {ai_stand();};
|
||||||
|
void() dog_stand6 =[ $stand6, dog_stand7 ] {ai_stand();};
|
||||||
|
void() dog_stand7 =[ $stand7, dog_stand8 ] {ai_stand();};
|
||||||
|
void() dog_stand8 =[ $stand8, dog_stand9 ] {ai_stand();};
|
||||||
|
void() dog_stand9 =[ $stand9, dog_stand1 ] {ai_stand();};
|
||||||
|
|
||||||
|
void() dog_walk1 =[ $walk1 , dog_walk2 ] {
|
||||||
|
if (random() < 0.2)
|
||||||
|
sound (self, CHAN_VOICE, "dog/idle.wav", 1, ATTN_IDLE);
|
||||||
|
ai_walk(8);};
|
||||||
|
void() dog_walk2 =[ $walk2 , dog_walk3 ] {ai_walk(8);};
|
||||||
|
void() dog_walk3 =[ $walk3 , dog_walk4 ] {ai_walk(8);};
|
||||||
|
void() dog_walk4 =[ $walk4 , dog_walk5 ] {ai_walk(8);};
|
||||||
|
void() dog_walk5 =[ $walk5 , dog_walk6 ] {ai_walk(8);};
|
||||||
|
void() dog_walk6 =[ $walk6 , dog_walk7 ] {ai_walk(8);};
|
||||||
|
void() dog_walk7 =[ $walk7 , dog_walk8 ] {ai_walk(8);};
|
||||||
|
void() dog_walk8 =[ $walk8 , dog_walk1 ] {ai_walk(8);};
|
||||||
|
|
||||||
|
void() dog_run1 =[ $run1 , dog_run2 ] {
|
||||||
|
if (random() < 0.2)
|
||||||
|
sound (self, CHAN_VOICE, "dog/idle.wav", 1, ATTN_IDLE);
|
||||||
|
ai_run(16);};
|
||||||
|
void() dog_run2 =[ $run2 , dog_run3 ] {ai_run(32);};
|
||||||
|
void() dog_run3 =[ $run3 , dog_run4 ] {ai_run(32);};
|
||||||
|
void() dog_run4 =[ $run4 , dog_run5 ] {ai_run(20);};
|
||||||
|
void() dog_run5 =[ $run5 , dog_run6 ] {ai_run(64);};
|
||||||
|
void() dog_run6 =[ $run6 , dog_run7 ] {ai_run(32);};
|
||||||
|
void() dog_run7 =[ $run7 , dog_run8 ] {ai_run(16);};
|
||||||
|
void() dog_run8 =[ $run8 , dog_run9 ] {ai_run(32);};
|
||||||
|
void() dog_run9 =[ $run9 , dog_run10 ] {ai_run(32);};
|
||||||
|
void() dog_run10 =[ $run10 , dog_run11 ] {ai_run(20);};
|
||||||
|
void() dog_run11 =[ $run11 , dog_run12 ] {ai_run(64);};
|
||||||
|
void() dog_run12 =[ $run12 , dog_run1 ] {ai_run(32);};
|
||||||
|
|
||||||
|
void() dog_atta1 =[ $attack1, dog_atta2 ] {ai_charge(10);};
|
||||||
|
void() dog_atta2 =[ $attack2, dog_atta3 ] {ai_charge(10);};
|
||||||
|
void() dog_atta3 =[ $attack3, dog_atta4 ] {ai_charge(10);};
|
||||||
|
void() dog_atta4 =[ $attack4, dog_atta5 ] {
|
||||||
|
sound (self, CHAN_VOICE, "dog/dattack1.wav", 1, ATTN_NORM);
|
||||||
|
dog_bite();};
|
||||||
|
void() dog_atta5 =[ $attack5, dog_atta6 ] {ai_charge(10);};
|
||||||
|
void() dog_atta6 =[ $attack6, dog_atta7 ] {ai_charge(10);};
|
||||||
|
void() dog_atta7 =[ $attack7, dog_atta8 ] {ai_charge(10);};
|
||||||
|
void() dog_atta8 =[ $attack8, dog_run1 ] {ai_charge(10);};
|
||||||
|
|
||||||
|
void() dog_leap1 =[ $leap1, dog_leap2 ] {ai_face();};
|
||||||
|
void() dog_leap2 =[ $leap2, dog_leap3 ]
|
||||||
|
{
|
||||||
|
ai_face();
|
||||||
|
|
||||||
|
self.touch = Dog_JumpTouch;
|
||||||
|
makevectors (self.angles);
|
||||||
|
self.origin_z = self.origin_z + 1;
|
||||||
|
self.velocity = v_forward * 300 + '0 0 200';
|
||||||
|
if (self.flags & FL_ONGROUND)
|
||||||
|
self.flags = self.flags - FL_ONGROUND;
|
||||||
|
};
|
||||||
|
|
||||||
|
void() dog_leap3 =[ $leap3, dog_leap4 ] {};
|
||||||
|
void() dog_leap4 =[ $leap4, dog_leap5 ] {};
|
||||||
|
void() dog_leap5 =[ $leap5, dog_leap6 ] {};
|
||||||
|
void() dog_leap6 =[ $leap6, dog_leap7 ] {};
|
||||||
|
void() dog_leap7 =[ $leap7, dog_leap8 ] {};
|
||||||
|
void() dog_leap8 =[ $leap8, dog_leap9 ] {};
|
||||||
|
void() dog_leap9 =[ $leap9, dog_leap9 ] {};
|
||||||
|
|
||||||
|
void() dog_pain1 =[ $pain1 , dog_pain2 ] {};
|
||||||
|
void() dog_pain2 =[ $pain2 , dog_pain3 ] {};
|
||||||
|
void() dog_pain3 =[ $pain3 , dog_pain4 ] {};
|
||||||
|
void() dog_pain4 =[ $pain4 , dog_pain5 ] {};
|
||||||
|
void() dog_pain5 =[ $pain5 , dog_pain6 ] {};
|
||||||
|
void() dog_pain6 =[ $pain6 , dog_run1 ] {};
|
||||||
|
|
||||||
|
void() dog_painb1 =[ $painb1 , dog_painb2 ] {};
|
||||||
|
void() dog_painb2 =[ $painb2 , dog_painb3 ] {};
|
||||||
|
void() dog_painb3 =[ $painb3 , dog_painb4 ] {ai_pain(4);};
|
||||||
|
void() dog_painb4 =[ $painb4 , dog_painb5 ] {ai_pain(12);};
|
||||||
|
void() dog_painb5 =[ $painb5 , dog_painb6 ] {ai_pain(12);};
|
||||||
|
void() dog_painb6 =[ $painb6 , dog_painb7 ] {ai_pain(2);};
|
||||||
|
void() dog_painb7 =[ $painb7 , dog_painb8 ] {};
|
||||||
|
void() dog_painb8 =[ $painb8 , dog_painb9 ] {ai_pain(4);};
|
||||||
|
void() dog_painb9 =[ $painb9 , dog_painb10 ] {};
|
||||||
|
void() dog_painb10 =[ $painb10 , dog_painb11 ] {ai_pain(10);};
|
||||||
|
void() dog_painb11 =[ $painb11 , dog_painb12 ] {};
|
||||||
|
void() dog_painb12 =[ $painb12 , dog_painb13 ] {};
|
||||||
|
void() dog_painb13 =[ $painb13 , dog_painb14 ] {};
|
||||||
|
void() dog_painb14 =[ $painb14 , dog_painb15 ] {};
|
||||||
|
void() dog_painb15 =[ $painb15 , dog_painb16 ] {};
|
||||||
|
void() dog_painb16 =[ $painb16 , dog_run1 ] {};
|
||||||
|
|
||||||
|
void() dog_pain =
|
||||||
|
{
|
||||||
|
sound (self, CHAN_VOICE, "dog/dpain1.wav", 1, ATTN_NORM);
|
||||||
|
|
||||||
|
if (random() > 0.5)
|
||||||
|
dog_pain1 ();
|
||||||
|
else
|
||||||
|
dog_painb1 ();
|
||||||
|
};
|
||||||
|
|
||||||
|
void() dog_die1 =[ $death1, dog_die2 ] {};
|
||||||
|
void() dog_die2 =[ $death2, dog_die3 ] {};
|
||||||
|
void() dog_die3 =[ $death3, dog_die4 ] {};
|
||||||
|
void() dog_die4 =[ $death4, dog_die5 ] {};
|
||||||
|
void() dog_die5 =[ $death5, dog_die6 ] {};
|
||||||
|
void() dog_die6 =[ $death6, dog_die7 ] {};
|
||||||
|
void() dog_die7 =[ $death7, dog_die8 ] {};
|
||||||
|
void() dog_die8 =[ $death8, dog_die9 ] {};
|
||||||
|
void() dog_die9 =[ $death9, dog_die9 ] {};
|
||||||
|
|
||||||
|
void() dog_dieb1 =[ $deathb1, dog_dieb2 ] {};
|
||||||
|
void() dog_dieb2 =[ $deathb2, dog_dieb3 ] {};
|
||||||
|
void() dog_dieb3 =[ $deathb3, dog_dieb4 ] {};
|
||||||
|
void() dog_dieb4 =[ $deathb4, dog_dieb5 ] {};
|
||||||
|
void() dog_dieb5 =[ $deathb5, dog_dieb6 ] {};
|
||||||
|
void() dog_dieb6 =[ $deathb6, dog_dieb7 ] {};
|
||||||
|
void() dog_dieb7 =[ $deathb7, dog_dieb8 ] {};
|
||||||
|
void() dog_dieb8 =[ $deathb8, dog_dieb9 ] {};
|
||||||
|
void() dog_dieb9 =[ $deathb9, dog_dieb9 ] {};
|
||||||
|
|
||||||
|
|
||||||
|
void() dog_die =
|
||||||
|
{
|
||||||
|
// check for gib
|
||||||
|
if (self.health < -35)
|
||||||
|
{
|
||||||
|
sound (self, CHAN_VOICE, "player/udeath.wav", 1, ATTN_NORM);
|
||||||
|
ThrowGib ("progs/gib3.mdl", self.health);
|
||||||
|
ThrowGib ("progs/gib3.mdl", self.health);
|
||||||
|
ThrowGib ("progs/gib3.mdl", self.health);
|
||||||
|
ThrowHead ("progs/h_dog.mdl", self.health);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// regular death
|
||||||
|
sound (self, CHAN_VOICE, "dog/ddeath.wav", 1, ATTN_NORM);
|
||||||
|
self.solid = SOLID_NOT;
|
||||||
|
|
||||||
|
if (random() > 0.5)
|
||||||
|
dog_die1 ();
|
||||||
|
else
|
||||||
|
dog_dieb1 ();
|
||||||
|
};
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
|
||||||
|
/*
|
||||||
|
==============
|
||||||
|
CheckDogMelee
|
||||||
|
|
||||||
|
Returns TRUE if a melee attack would hit right now
|
||||||
|
==============
|
||||||
|
*/
|
||||||
|
float(float enemy_range) CheckDogMelee =
|
||||||
|
{
|
||||||
|
if (enemy_range == RANGE_MELEE)
|
||||||
|
{ // FIXME: check canreach
|
||||||
|
self.attack_state = AS_MELEE;
|
||||||
|
return TRUE;
|
||||||
|
}
|
||||||
|
return FALSE;
|
||||||
|
};
|
||||||
|
|
||||||
|
/*
|
||||||
|
==============
|
||||||
|
CheckDogJump
|
||||||
|
|
||||||
|
==============
|
||||||
|
*/
|
||||||
|
float() CheckDogJump =
|
||||||
|
{
|
||||||
|
local vector dist;
|
||||||
|
local float d;
|
||||||
|
|
||||||
|
if (self.origin_z + self.mins_z > self.enemy.origin_z + self.enemy.mins_z
|
||||||
|
+ 0.75 * self.enemy.size_z)
|
||||||
|
return FALSE;
|
||||||
|
|
||||||
|
if (self.origin_z + self.maxs_z < self.enemy.origin_z + self.enemy.mins_z
|
||||||
|
+ 0.25 * self.enemy.size_z)
|
||||||
|
return FALSE;
|
||||||
|
|
||||||
|
dist = self.enemy.origin - self.origin;
|
||||||
|
dist_z = 0;
|
||||||
|
|
||||||
|
d = vlen(dist);
|
||||||
|
|
||||||
|
if (d < 80)
|
||||||
|
return FALSE;
|
||||||
|
|
||||||
|
if (d > 150)
|
||||||
|
return FALSE;
|
||||||
|
|
||||||
|
return TRUE;
|
||||||
|
};
|
||||||
|
|
||||||
|
float(float enemy_range) DogCheckAttack =
|
||||||
|
{
|
||||||
|
// if close enough for slashing, go for it
|
||||||
|
if (CheckDogMelee (enemy_range))
|
||||||
|
{
|
||||||
|
self.attack_state = AS_MELEE;
|
||||||
|
return TRUE;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (CheckDogJump ())
|
||||||
|
{
|
||||||
|
self.attack_state = AS_MISSILE;
|
||||||
|
return TRUE;
|
||||||
|
}
|
||||||
|
|
||||||
|
return FALSE;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
//===========================================================================
|
||||||
|
|
||||||
|
/*QUAKED monster_dog (1 0 0) (-32 -32 -24) (32 32 40) Ambush
|
||||||
|
|
||||||
|
*/
|
||||||
|
void() monster_dog =
|
||||||
|
{
|
||||||
|
if (deathmatch)
|
||||||
|
{
|
||||||
|
remove(self);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
precache_model ("progs/h_dog.mdl");
|
||||||
|
precache_model ("progs/dog.mdl");
|
||||||
|
|
||||||
|
precache_sound ("dog/dattack1.wav");
|
||||||
|
precache_sound ("dog/ddeath.wav");
|
||||||
|
precache_sound ("dog/dpain1.wav");
|
||||||
|
precache_sound ("dog/dsight.wav");
|
||||||
|
precache_sound ("dog/idle.wav");
|
||||||
|
|
||||||
|
self.solid = SOLID_SLIDEBOX;
|
||||||
|
self.movetype = MOVETYPE_STEP;
|
||||||
|
|
||||||
|
setmodel (self, "progs/dog.mdl");
|
||||||
|
|
||||||
|
setsize (self, '-32 -32 -24', '32 32 40');
|
||||||
|
self.health = 25;
|
||||||
|
|
||||||
|
self.th_stand = dog_stand1;
|
||||||
|
self.th_walk = dog_walk1;
|
||||||
|
self.th_run = dog_run1;
|
||||||
|
self.th_pain = dog_pain;
|
||||||
|
self.th_die = dog_die;
|
||||||
|
self.th_melee = dog_atta1;
|
||||||
|
self.th_missile = dog_leap1;
|
||||||
|
|
||||||
|
walkmonster_start();
|
||||||
|
};
|
|
@ -9,6 +9,71 @@ var float ef_pent = EF_DIMLIGHT; // used for pent effect on player
|
||||||
var float ef_blue = 0; // used for glow on quad
|
var float ef_blue = 0; // used for glow on quad
|
||||||
var float ef_quad = EF_DIMLIGHT; // used for quad effect on player
|
var float ef_quad = EF_DIMLIGHT; // used for quad effect on player
|
||||||
|
|
||||||
|
// base te write functions
|
||||||
|
void WriteVector (float msg, vector org) =
|
||||||
|
{
|
||||||
|
WriteCoord (msg, org_x);
|
||||||
|
WriteCoord (msg, org_y);
|
||||||
|
WriteCoord (msg, org_z);
|
||||||
|
};
|
||||||
|
|
||||||
|
#ifdef NETQUAKE
|
||||||
|
void(vector org, float effect) _EFF_PointEffect =
|
||||||
|
{
|
||||||
|
WriteByte (MSG_BROADCAST, SVC_TEMPENTITY);
|
||||||
|
WriteByte (MSG_BROADCAST, effect);
|
||||||
|
WriteVector (MSG_BROADCAST, org);
|
||||||
|
};
|
||||||
|
|
||||||
|
void(entity ent, vector org, vector org2, float effect) _EFF_BeamEffect =
|
||||||
|
{
|
||||||
|
WriteByte (MSG_BROADCAST, SVC_TEMPENTITY);
|
||||||
|
WriteByte (MSG_BROADCAST, effect);
|
||||||
|
WriteEntity (MSG_BROADCAST, ent);
|
||||||
|
WriteVector (MSG_BROADCAST, org);
|
||||||
|
WriteVector (MSG_BROADCAST, org2);
|
||||||
|
};
|
||||||
|
|
||||||
|
void(vector org, float damage, float effect) _EFF_CountEffect =
|
||||||
|
{
|
||||||
|
WriteByte (MSG_BROADCAST, SVC_TEMPENTITY);
|
||||||
|
WriteByte (MSG_BROADCAST, effect);
|
||||||
|
WriteByte (MSG_BROADCAST, damage);
|
||||||
|
WriteVector (MSG_BROADCAST, org);
|
||||||
|
};
|
||||||
|
|
||||||
|
#define EFF_PointEffect(a,b,c) _EFF_PointEffect(a,b)
|
||||||
|
#define EFF_BeamEffect(a,b,c,d,e) _EFF_BeamEffect(a,b,c,d)
|
||||||
|
#define EFF_CountEffect(a,b,c,d) _EFF_CountEffect(a,b,c)
|
||||||
|
#else
|
||||||
|
void(vector org, float effect, float mcast) EFF_PointEffect =
|
||||||
|
{
|
||||||
|
WriteByte (MSG_MULTICAST, SVC_TEMPENTITY);
|
||||||
|
WriteByte (MSG_MULTICAST, effect);
|
||||||
|
WriteVector (MSG_MULTICAST, org);
|
||||||
|
multicast (org, mcast);
|
||||||
|
};
|
||||||
|
|
||||||
|
void(entity ent, vector org, vector org2, float effect, float mcast) EFF_BeamEffect =
|
||||||
|
{
|
||||||
|
WriteByte (MSG_MULTICAST, SVC_TEMPENTITY);
|
||||||
|
WriteByte (MSG_MULTICAST, effect);
|
||||||
|
WriteEntity (MSG_MULTICAST, ent);
|
||||||
|
WriteVector (MSG_MULTICAST, org);
|
||||||
|
WriteVector (MSG_MULTICAST, org2);
|
||||||
|
multicast (org, mcast);
|
||||||
|
};
|
||||||
|
|
||||||
|
void(vector org, float damage, float effect, float mcast) EFF_CountEffect =
|
||||||
|
{
|
||||||
|
WriteByte (MSG_MULTICAST, SVC_TEMPENTITY);
|
||||||
|
WriteByte (MSG_MULTICAST, effect);
|
||||||
|
WriteByte (MSG_MULTICAST, damage);
|
||||||
|
WriteVector (MSG_MULTICAST, org);
|
||||||
|
multicast (org, mcast);
|
||||||
|
};
|
||||||
|
#endif
|
||||||
|
|
||||||
/*
|
/*
|
||||||
================
|
================
|
||||||
SpawnBlood
|
SpawnBlood
|
||||||
|
@ -24,17 +89,11 @@ void(vector org, float damage) _SpawnBlood =
|
||||||
#ifdef NETQUAKE
|
#ifdef NETQUAKE
|
||||||
particle (org, '0 0 0', 73, damage*2);
|
particle (org, '0 0 0', 73, damage*2);
|
||||||
#else
|
#else
|
||||||
WriteByte (MSG_MULTICAST, SVC_TEMPENTITY);
|
EFF_CountEffect(org, damage, TE_BLOOD, MULTICAST_PVS);
|
||||||
WriteByte (MSG_MULTICAST, TE_BLOOD);
|
|
||||||
WriteByte (MSG_MULTICAST, damage);
|
|
||||||
WriteCoord (MSG_MULTICAST, org_x);
|
|
||||||
WriteCoord (MSG_MULTICAST, org_y);
|
|
||||||
WriteCoord (MSG_MULTICAST, org_z);
|
|
||||||
multicast (org, MULTICAST_PVS);
|
|
||||||
#endif
|
#endif
|
||||||
};
|
};
|
||||||
|
|
||||||
#ifdef NETQUAKE
|
// #if defined(NETQUAKE) || defined(MONSTERS)
|
||||||
void() s_explode6 = [5, SUB_Remove] {};
|
void() s_explode6 = [5, SUB_Remove] {};
|
||||||
void() s_explode5 = [4, s_explode6] {};
|
void() s_explode5 = [4, s_explode6] {};
|
||||||
void() s_explode4 = [3, s_explode5] {};
|
void() s_explode4 = [3, s_explode5] {};
|
||||||
|
@ -60,160 +119,73 @@ void(vector org) CreateExplosion =
|
||||||
|
|
||||||
self = s; // restore old self
|
self = s; // restore old self
|
||||||
};
|
};
|
||||||
#endif
|
// #endif
|
||||||
|
|
||||||
void(vector org) _TE_explosion =
|
void(vector org) _TE_explosion =
|
||||||
{
|
{
|
||||||
|
EFF_PointEffect(org, TE_EXPLOSION, MULTICAST_PHS);
|
||||||
#ifdef NETQUAKE
|
#ifdef NETQUAKE
|
||||||
WriteByte (MSG_BROADCAST, SVC_TEMPENTITY);
|
|
||||||
WriteByte (MSG_BROADCAST, TE_EXPLOSION);
|
|
||||||
WriteCoord (MSG_BROADCAST, org_x);
|
|
||||||
WriteCoord (MSG_BROADCAST, org_y);
|
|
||||||
WriteCoord (MSG_BROADCAST, org_z);
|
|
||||||
CreateExplosion(org);
|
CreateExplosion(org);
|
||||||
#else
|
|
||||||
WriteByte (MSG_MULTICAST, SVC_TEMPENTITY);
|
|
||||||
WriteByte (MSG_MULTICAST, TE_EXPLOSION);
|
|
||||||
WriteCoord (MSG_MULTICAST, org_x);
|
|
||||||
WriteCoord (MSG_MULTICAST, org_y);
|
|
||||||
WriteCoord (MSG_MULTICAST, org_z);
|
|
||||||
multicast (org, MULTICAST_PHS);
|
|
||||||
#endif
|
#endif
|
||||||
};
|
};
|
||||||
|
|
||||||
void(vector org) _TE_gunshot =
|
void(vector org) _TE_gunshot =
|
||||||
{
|
{
|
||||||
#ifdef NETQUAKE
|
#ifdef NETQUAKE
|
||||||
WriteByte (MSG_BROADCAST, SVC_TEMPENTITY);
|
EFF_PointEffect(org, TE_GUNSHOT, MULTICAST_PVS);
|
||||||
WriteByte (MSG_BROADCAST, TE_GUNSHOT);
|
|
||||||
WriteCoord (MSG_BROADCAST, org_x);
|
|
||||||
WriteCoord (MSG_BROADCAST, org_y);
|
|
||||||
WriteCoord (MSG_BROADCAST, org_z);
|
|
||||||
#else
|
#else
|
||||||
WriteByte (MSG_MULTICAST, SVC_TEMPENTITY);
|
EFF_CountEffect(org, 3, TE_GUNSHOT, MULTICAST_PVS);
|
||||||
WriteByte (MSG_MULTICAST, TE_GUNSHOT);
|
|
||||||
WriteByte (MSG_MULTICAST, 3);
|
|
||||||
WriteCoord (MSG_MULTICAST, org_x);
|
|
||||||
WriteCoord (MSG_MULTICAST, org_y);
|
|
||||||
WriteCoord (MSG_MULTICAST, org_z);
|
|
||||||
multicast (org, MULTICAST_PVS);
|
|
||||||
#endif
|
#endif
|
||||||
};
|
};
|
||||||
|
|
||||||
void(vector org) _TE_spike =
|
void(vector org) _TE_spike =
|
||||||
{
|
{
|
||||||
#ifdef NETQUAKE
|
EFF_PointEffect(org, TE_SPIKE, MULTICAST_PHS);
|
||||||
WriteByte (MSG_BROADCAST, SVC_TEMPENTITY);
|
|
||||||
WriteByte (MSG_BROADCAST, TE_SPIKE);
|
|
||||||
WriteCoord (MSG_BROADCAST, org_x);
|
|
||||||
WriteCoord (MSG_BROADCAST, org_y);
|
|
||||||
WriteCoord (MSG_BROADCAST, org_z);
|
|
||||||
#else
|
|
||||||
WriteByte (MSG_MULTICAST, SVC_TEMPENTITY);
|
|
||||||
WriteByte (MSG_MULTICAST, TE_SPIKE);
|
|
||||||
WriteCoord (MSG_MULTICAST, org_x);
|
|
||||||
WriteCoord (MSG_MULTICAST, org_y);
|
|
||||||
WriteCoord (MSG_MULTICAST, org_z);
|
|
||||||
multicast (org, MULTICAST_PHS);
|
|
||||||
#endif
|
|
||||||
};
|
};
|
||||||
|
|
||||||
void(vector org) _TE_knightspike =
|
void(vector org) _TE_knightspike =
|
||||||
{
|
{
|
||||||
#ifdef NETQUAKE
|
EFF_PointEffect(org, TE_KNIGHTSPIKE, MULTICAST_PHS);
|
||||||
WriteByte (MSG_BROADCAST, SVC_TEMPENTITY);
|
|
||||||
WriteByte (MSG_BROADCAST, TE_KNIGHTSPIKE);
|
|
||||||
WriteCoord (MSG_BROADCAST, org_x);
|
|
||||||
WriteCoord (MSG_BROADCAST, org_y);
|
|
||||||
WriteCoord (MSG_BROADCAST, org_z);
|
|
||||||
#else
|
|
||||||
WriteByte (MSG_MULTICAST, SVC_TEMPENTITY);
|
|
||||||
WriteByte (MSG_MULTICAST, TE_KNIGHTSPIKE);
|
|
||||||
WriteCoord (MSG_MULTICAST, org_x);
|
|
||||||
WriteCoord (MSG_MULTICAST, org_y);
|
|
||||||
WriteCoord (MSG_MULTICAST, org_z);
|
|
||||||
multicast (org, MULTICAST_PHS);
|
|
||||||
#endif
|
|
||||||
};
|
};
|
||||||
|
|
||||||
void(vector org) _TE_wizspike =
|
void(vector org) _TE_wizspike =
|
||||||
{
|
{
|
||||||
#ifdef NETQUAKE
|
EFF_PointEffect(org, TE_WIZSPIKE, MULTICAST_PHS);
|
||||||
WriteByte (MSG_BROADCAST, SVC_TEMPENTITY);
|
|
||||||
WriteByte (MSG_BROADCAST, TE_WIZSPIKE);
|
|
||||||
WriteCoord (MSG_BROADCAST, org_x);
|
|
||||||
WriteCoord (MSG_BROADCAST, org_y);
|
|
||||||
WriteCoord (MSG_BROADCAST, org_z);
|
|
||||||
#else
|
|
||||||
WriteByte (MSG_MULTICAST, SVC_TEMPENTITY);
|
|
||||||
WriteByte (MSG_MULTICAST, TE_WIZSPIKE);
|
|
||||||
WriteCoord (MSG_MULTICAST, org_x);
|
|
||||||
WriteCoord (MSG_MULTICAST, org_y);
|
|
||||||
WriteCoord (MSG_MULTICAST, org_z);
|
|
||||||
multicast (org, MULTICAST_PHS);
|
|
||||||
#endif
|
|
||||||
};
|
};
|
||||||
|
|
||||||
void(vector org) _TE_superspike =
|
void(vector org) _TE_superspike =
|
||||||
{
|
{
|
||||||
#ifdef NETQUAKE
|
EFF_PointEffect(org, TE_SUPERSPIKE, MULTICAST_PHS);
|
||||||
WriteByte (MSG_BROADCAST, SVC_TEMPENTITY);
|
|
||||||
WriteByte (MSG_BROADCAST, TE_SUPERSPIKE);
|
|
||||||
WriteCoord (MSG_BROADCAST, org_x);
|
|
||||||
WriteCoord (MSG_BROADCAST, org_y);
|
|
||||||
WriteCoord (MSG_BROADCAST, org_z);
|
|
||||||
#else
|
|
||||||
WriteByte (MSG_MULTICAST, SVC_TEMPENTITY);
|
|
||||||
WriteByte (MSG_MULTICAST, TE_SUPERSPIKE);
|
|
||||||
WriteCoord (MSG_MULTICAST, org_x);
|
|
||||||
WriteCoord (MSG_MULTICAST, org_y);
|
|
||||||
WriteCoord (MSG_MULTICAST, org_z);
|
|
||||||
multicast (org, MULTICAST_PHS);
|
|
||||||
#endif
|
|
||||||
};
|
};
|
||||||
|
|
||||||
void(vector org) _TE_teleport =
|
void(vector org) _TE_teleport =
|
||||||
{
|
{
|
||||||
#ifdef NETQUAKE
|
EFF_PointEffect(org, TE_TELEPORT, MULTICAST_PHS);
|
||||||
WriteByte (MSG_BROADCAST, SVC_TEMPENTITY);
|
};
|
||||||
WriteByte (MSG_BROADCAST, TE_TELEPORT);
|
|
||||||
WriteCoord (MSG_BROADCAST, org_x);
|
void(vector org) _TE_lavasplash =
|
||||||
WriteCoord (MSG_BROADCAST, org_y);
|
{
|
||||||
WriteCoord (MSG_BROADCAST, org_z);
|
EFF_PointEffect(org, TE_LAVASPLASH, MULTICAST_PVS);
|
||||||
#else
|
};
|
||||||
WriteByte (MSG_MULTICAST, SVC_TEMPENTITY);
|
|
||||||
WriteByte (MSG_MULTICAST, TE_TELEPORT);
|
void(vector org) _TE_tarexplosion =
|
||||||
WriteCoord (MSG_MULTICAST, org_x);
|
{
|
||||||
WriteCoord (MSG_MULTICAST, org_y);
|
EFF_PointEffect(org, TE_TAREXPLOSION, MULTICAST_PHS);
|
||||||
WriteCoord (MSG_MULTICAST, org_z);
|
};
|
||||||
multicast (org, MULTICAST_PHS);
|
|
||||||
#endif
|
void(entity ent, vector start, vector end) _TE_lightning1 =
|
||||||
|
{
|
||||||
|
EFF_BeamEffect (ent, start, end, TE_LIGHTNING1, MULTICAST_PHS);
|
||||||
};
|
};
|
||||||
|
|
||||||
void(entity ent, vector start, vector end) _TE_lightning2 =
|
void(entity ent, vector start, vector end) _TE_lightning2 =
|
||||||
{
|
{
|
||||||
#ifdef NETQUAKE
|
EFF_BeamEffect (ent, start, end, TE_LIGHTNING2, MULTICAST_PHS);
|
||||||
WriteByte (MSG_BROADCAST, SVC_TEMPENTITY);
|
};
|
||||||
WriteByte (MSG_BROADCAST, TE_LIGHTNING2);
|
|
||||||
WriteEntity (MSG_BROADCAST, ent);
|
void(entity ent, vector start, vector end) _TE_lightning3 =
|
||||||
WriteCoord (MSG_BROADCAST, start_x);
|
{
|
||||||
WriteCoord (MSG_BROADCAST, start_y);
|
EFF_BeamEffect (ent, start, end, TE_LIGHTNING3, MULTICAST_PHS);
|
||||||
WriteCoord (MSG_BROADCAST, start_z);
|
|
||||||
WriteCoord (MSG_BROADCAST, end_x);
|
|
||||||
WriteCoord (MSG_BROADCAST, end_y);
|
|
||||||
WriteCoord (MSG_BROADCAST, end_z);
|
|
||||||
#else
|
|
||||||
WriteByte (MSG_MULTICAST, SVC_TEMPENTITY);
|
|
||||||
WriteByte (MSG_MULTICAST, TE_LIGHTNING2);
|
|
||||||
WriteEntity (MSG_MULTICAST, ent);
|
|
||||||
WriteCoord (MSG_MULTICAST, start_x);
|
|
||||||
WriteCoord (MSG_MULTICAST, start_y);
|
|
||||||
WriteCoord (MSG_MULTICAST, start_z);
|
|
||||||
WriteCoord (MSG_MULTICAST, end_x);
|
|
||||||
WriteCoord (MSG_MULTICAST, end_y);
|
|
||||||
WriteCoord (MSG_MULTICAST, end_z);
|
|
||||||
multicast (start, MULTICAST_PHS);
|
|
||||||
#endif
|
|
||||||
};
|
};
|
||||||
|
|
||||||
void(vector org) TE_lightningblood =
|
void(vector org) TE_lightningblood =
|
||||||
|
@ -221,12 +193,7 @@ void(vector org) TE_lightningblood =
|
||||||
#ifdef NETQUAKE
|
#ifdef NETQUAKE
|
||||||
particle(org, '0 0 100', 225, 120);
|
particle(org, '0 0 100', 225, 120);
|
||||||
#else
|
#else
|
||||||
WriteByte (MSG_MULTICAST, SVC_TEMPENTITY);
|
EFF_PointEffect(org, TE_LIGHTNINGBLOOD, MULTICAST_PVS);
|
||||||
WriteByte (MSG_MULTICAST, TE_LIGHTNINGBLOOD);
|
|
||||||
WriteCoord (MSG_MULTICAST, org_x);
|
|
||||||
WriteCoord (MSG_MULTICAST, org_y);
|
|
||||||
WriteCoord (MSG_MULTICAST, org_z);
|
|
||||||
multicast (org, MULTICAST_PVS);
|
|
||||||
#endif
|
#endif
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -239,7 +206,11 @@ var void(vector org) TE_knightspike = _TE_knightspike;
|
||||||
var void(vector org) TE_wizspike = _TE_wizspike;
|
var void(vector org) TE_wizspike = _TE_wizspike;
|
||||||
var void(vector org) TE_superspike = _TE_superspike;
|
var void(vector org) TE_superspike = _TE_superspike;
|
||||||
var void(vector org) TE_teleport = _TE_teleport;
|
var void(vector org) TE_teleport = _TE_teleport;
|
||||||
|
var void(vector org) TE_lavasplash = _TE_lavasplash;
|
||||||
|
var void(vector org) TE_tarexplosion = _TE_tarexplosion;
|
||||||
|
var void(entity ent, vector start, vector end) TE_lightning1 = _TE_lightning1;
|
||||||
var void(entity ent, vector start, vector end) TE_lightning2 = _TE_lightning2;
|
var void(entity ent, vector start, vector end) TE_lightning2 = _TE_lightning2;
|
||||||
|
var void(entity ent, vector start, vector end) TE_lightning3 = _TE_lightning3;
|
||||||
|
|
||||||
// set effects function, takes function pointers and assigns them based on detected builtins
|
// set effects function, takes function pointers and assigns them based on detected builtins
|
||||||
void() EFF_SetEffects =
|
void() EFF_SetEffects =
|
||||||
|
@ -266,7 +237,11 @@ void() EFF_SetEffects =
|
||||||
TE_wizspike = _te_wizspike;
|
TE_wizspike = _te_wizspike;
|
||||||
TE_superspike = _te_superspike;
|
TE_superspike = _te_superspike;
|
||||||
TE_teleport = _te_teleport;
|
TE_teleport = _te_teleport;
|
||||||
|
TE_lavasplash = _te_lavasplash;
|
||||||
|
TE_tarexplosion = _te_tarexplosion;
|
||||||
|
TE_lightning1 = _te_lightning1;
|
||||||
TE_lightning2 = _te_lightning2;
|
TE_lightning2 = _te_lightning2;
|
||||||
|
TE_lightning3 = _te_lightning3;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (eng_support & ENG_TEBLOOD)
|
if (eng_support & ENG_TEBLOOD)
|
||||||
|
|
282
quakec/basemod/enforcer.qc
Normal file
282
quakec/basemod/enforcer.qc
Normal file
|
@ -0,0 +1,282 @@
|
||||||
|
/*
|
||||||
|
==============================================================================
|
||||||
|
|
||||||
|
SOLDIER / PLAYER
|
||||||
|
|
||||||
|
==============================================================================
|
||||||
|
*/
|
||||||
|
|
||||||
|
$cd id1/models/enforcer
|
||||||
|
$origin 0 -6 24
|
||||||
|
$base base
|
||||||
|
$skin skin
|
||||||
|
|
||||||
|
$frame stand1 stand2 stand3 stand4 stand5 stand6 stand7
|
||||||
|
|
||||||
|
$frame walk1 walk2 walk3 walk4 walk5 walk6 walk7 walk8 walk9 walk10
|
||||||
|
$frame walk11 walk12 walk13 walk14 walk15 walk16
|
||||||
|
|
||||||
|
$frame run1 run2 run3 run4 run5 run6 run7 run8
|
||||||
|
|
||||||
|
$frame attack1 attack2 attack3 attack4 attack5 attack6
|
||||||
|
$frame attack7 attack8 attack9 attack10
|
||||||
|
|
||||||
|
$frame death1 death2 death3 death4 death5 death6 death7 death8
|
||||||
|
$frame death9 death10 death11 death12 death13 death14
|
||||||
|
|
||||||
|
$frame fdeath1 fdeath2 fdeath3 fdeath4 fdeath5 fdeath6 fdeath7 fdeath8
|
||||||
|
$frame fdeath9 fdeath10 fdeath11
|
||||||
|
|
||||||
|
$frame paina1 paina2 paina3 paina4
|
||||||
|
|
||||||
|
$frame painb1 painb2 painb3 painb4 painb5
|
||||||
|
|
||||||
|
$frame painc1 painc2 painc3 painc4 painc5 painc6 painc7 painc8
|
||||||
|
|
||||||
|
$frame paind1 paind2 paind3 paind4 paind5 paind6 paind7 paind8
|
||||||
|
$frame paind9 paind10 paind11 paind12 paind13 paind14 paind15 paind16
|
||||||
|
$frame paind17 paind18 paind19
|
||||||
|
|
||||||
|
void() enforcer_fire =
|
||||||
|
{
|
||||||
|
local vector org, vec;
|
||||||
|
|
||||||
|
muzzleflash();
|
||||||
|
makevectors (self.angles);
|
||||||
|
|
||||||
|
org = self.origin + v_forward * 30 + v_right * 8.5 + '0 0 16';
|
||||||
|
vec = normalize(self.enemy.origin - self.origin) * 600;
|
||||||
|
|
||||||
|
sound (self, CHAN_VOICE, "enforcer/enfire.wav", 1, ATTN_NORM);
|
||||||
|
PRJ_FireProjectile(self, "progs/laser.mdl", org, vec, PE_LASER, 15, MOD_ENFORCER, 5);
|
||||||
|
newmis.effects |= EF_DIMLIGHT;
|
||||||
|
newmis.alpha = 0.5;
|
||||||
|
};
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
|
||||||
|
void() enf_stand1 =[ $stand1, enf_stand2 ] {ai_stand();};
|
||||||
|
void() enf_stand2 =[ $stand2, enf_stand3 ] {ai_stand();};
|
||||||
|
void() enf_stand3 =[ $stand3, enf_stand4 ] {ai_stand();};
|
||||||
|
void() enf_stand4 =[ $stand4, enf_stand5 ] {ai_stand();};
|
||||||
|
void() enf_stand5 =[ $stand5, enf_stand6 ] {ai_stand();};
|
||||||
|
void() enf_stand6 =[ $stand6, enf_stand7 ] {ai_stand();};
|
||||||
|
void() enf_stand7 =[ $stand7, enf_stand1 ] {ai_stand();};
|
||||||
|
|
||||||
|
void() enf_walk1 =[ $walk1 , enf_walk2 ] {
|
||||||
|
if (random() < 0.2)
|
||||||
|
sound (self, CHAN_VOICE, "enforcer/idle1.wav", 1, ATTN_IDLE);
|
||||||
|
ai_walk(2);};
|
||||||
|
void() enf_walk2 =[ $walk2 , enf_walk3 ] {ai_walk(4);};
|
||||||
|
void() enf_walk3 =[ $walk3 , enf_walk4 ] {ai_walk(4);};
|
||||||
|
void() enf_walk4 =[ $walk4 , enf_walk5 ] {ai_walk(3);};
|
||||||
|
void() enf_walk5 =[ $walk5 , enf_walk6 ] {ai_walk(1);};
|
||||||
|
void() enf_walk6 =[ $walk6 , enf_walk7 ] {ai_walk(2);};
|
||||||
|
void() enf_walk7 =[ $walk7 , enf_walk8 ] {ai_walk(2);};
|
||||||
|
void() enf_walk8 =[ $walk8 , enf_walk9 ] {ai_walk(1);};
|
||||||
|
void() enf_walk9 =[ $walk9 , enf_walk10 ] {ai_walk(2);};
|
||||||
|
void() enf_walk10 =[ $walk10, enf_walk11 ] {ai_walk(4);};
|
||||||
|
void() enf_walk11 =[ $walk11, enf_walk12 ] {ai_walk(4);};
|
||||||
|
void() enf_walk12 =[ $walk12, enf_walk13 ] {ai_walk(1);};
|
||||||
|
void() enf_walk13 =[ $walk13, enf_walk14 ] {ai_walk(2);};
|
||||||
|
void() enf_walk14 =[ $walk14, enf_walk15 ] {ai_walk(3);};
|
||||||
|
void() enf_walk15 =[ $walk15, enf_walk16 ] {ai_walk(4);};
|
||||||
|
void() enf_walk16 =[ $walk16, enf_walk1 ] {ai_walk(2);};
|
||||||
|
|
||||||
|
void() enf_run1 =[ $run1 , enf_run2 ] {
|
||||||
|
if (random() < 0.2)
|
||||||
|
sound (self, CHAN_VOICE, "enforcer/idle1.wav", 1, ATTN_IDLE);
|
||||||
|
ai_run(18);};
|
||||||
|
void() enf_run2 =[ $run2 , enf_run3 ] {ai_run(14);};
|
||||||
|
void() enf_run3 =[ $run3 , enf_run4 ] {ai_run(7);};
|
||||||
|
void() enf_run4 =[ $run4 , enf_run5 ] {ai_run(12);};
|
||||||
|
void() enf_run5 =[ $run5 , enf_run6 ] {ai_run(14);};
|
||||||
|
void() enf_run6 =[ $run6 , enf_run7 ] {ai_run(14);};
|
||||||
|
void() enf_run7 =[ $run7 , enf_run8 ] {ai_run(7);};
|
||||||
|
void() enf_run8 =[ $run8 , enf_run1 ] {ai_run(11);};
|
||||||
|
|
||||||
|
void() enf_atk1 =[ $attack1, enf_atk2 ] {ai_face();};
|
||||||
|
void() enf_atk2 =[ $attack2, enf_atk3 ] {ai_face();};
|
||||||
|
void() enf_atk3 =[ $attack3, enf_atk4 ] {ai_face();};
|
||||||
|
void() enf_atk4 =[ $attack4, enf_atk5 ] {ai_face();};
|
||||||
|
void() enf_atk5 =[ $attack5, enf_atk6 ] {ai_face();};
|
||||||
|
void() enf_atk6 =[ $attack6, enf_atk7 ] {enforcer_fire();};
|
||||||
|
void() enf_atk7 =[ $attack7, enf_atk8 ] {ai_face();};
|
||||||
|
void() enf_atk8 =[ $attack8, enf_atk9 ] {ai_face();};
|
||||||
|
void() enf_atk9 =[ $attack5, enf_atk10 ] {ai_face();};
|
||||||
|
void() enf_atk10 =[ $attack6, enf_atk11 ] {enforcer_fire();};
|
||||||
|
void() enf_atk11 =[ $attack7, enf_atk12 ] {ai_face();};
|
||||||
|
void() enf_atk12 =[ $attack8, enf_atk13 ] {ai_face();};
|
||||||
|
void() enf_atk13 =[ $attack9, enf_atk14 ] {ai_face();};
|
||||||
|
void() enf_atk14 =[ $attack10, enf_run1 ] {ai_face();
|
||||||
|
SUB_CheckRefire (enf_atk1);
|
||||||
|
};
|
||||||
|
|
||||||
|
void() enf_paina1 =[ $paina1, enf_paina2 ] {};
|
||||||
|
void() enf_paina2 =[ $paina2, enf_paina3 ] {};
|
||||||
|
void() enf_paina3 =[ $paina3, enf_paina4 ] {};
|
||||||
|
void() enf_paina4 =[ $paina4, enf_run1 ] {};
|
||||||
|
|
||||||
|
void() enf_painb1 =[ $painb1, enf_painb2 ] {};
|
||||||
|
void() enf_painb2 =[ $painb2, enf_painb3 ] {};
|
||||||
|
void() enf_painb3 =[ $painb3, enf_painb4 ] {};
|
||||||
|
void() enf_painb4 =[ $painb4, enf_painb5 ] {};
|
||||||
|
void() enf_painb5 =[ $painb5, enf_run1 ] {};
|
||||||
|
|
||||||
|
void() enf_painc1 =[ $painc1, enf_painc2 ] {};
|
||||||
|
void() enf_painc2 =[ $painc2, enf_painc3 ] {};
|
||||||
|
void() enf_painc3 =[ $painc3, enf_painc4 ] {};
|
||||||
|
void() enf_painc4 =[ $painc4, enf_painc5 ] {};
|
||||||
|
void() enf_painc5 =[ $painc5, enf_painc6 ] {};
|
||||||
|
void() enf_painc6 =[ $painc6, enf_painc7 ] {};
|
||||||
|
void() enf_painc7 =[ $painc7, enf_painc8 ] {};
|
||||||
|
void() enf_painc8 =[ $painc8, enf_run1 ] {};
|
||||||
|
|
||||||
|
void() enf_paind1 =[ $paind1, enf_paind2 ] {};
|
||||||
|
void() enf_paind2 =[ $paind2, enf_paind3 ] {};
|
||||||
|
void() enf_paind3 =[ $paind3, enf_paind4 ] {};
|
||||||
|
void() enf_paind4 =[ $paind4, enf_paind5 ] {ai_painforward(2);};
|
||||||
|
void() enf_paind5 =[ $paind5, enf_paind6 ] {ai_painforward(1);};
|
||||||
|
void() enf_paind6 =[ $paind6, enf_paind7 ] {};
|
||||||
|
void() enf_paind7 =[ $paind7, enf_paind8 ] {};
|
||||||
|
void() enf_paind8 =[ $paind8, enf_paind9 ] {};
|
||||||
|
void() enf_paind9 =[ $paind9, enf_paind10 ] {};
|
||||||
|
void() enf_paind10 =[ $paind10, enf_paind11 ] {};
|
||||||
|
void() enf_paind11 =[ $paind11, enf_paind12 ] {ai_painforward(1);};
|
||||||
|
void() enf_paind12 =[ $paind12, enf_paind13 ] {ai_painforward(1);};
|
||||||
|
void() enf_paind13 =[ $paind13, enf_paind14 ] {ai_painforward(1);};
|
||||||
|
void() enf_paind14 =[ $paind14, enf_paind15 ] {};
|
||||||
|
void() enf_paind15 =[ $paind15, enf_paind16 ] {};
|
||||||
|
void() enf_paind16 =[ $paind16, enf_paind17 ] {ai_pain(1);};
|
||||||
|
void() enf_paind17 =[ $paind17, enf_paind18 ] {ai_pain(1);};
|
||||||
|
void() enf_paind18 =[ $paind18, enf_paind19 ] {};
|
||||||
|
void() enf_paind19 =[ $paind19, enf_run1 ] {};
|
||||||
|
|
||||||
|
void(entity attacker, float damage) enf_pain =
|
||||||
|
{
|
||||||
|
local float r;
|
||||||
|
|
||||||
|
if (self.pain_finished > time)
|
||||||
|
return;
|
||||||
|
|
||||||
|
r = random ();
|
||||||
|
if (r < 0.5)
|
||||||
|
sound (self, CHAN_VOICE, "enforcer/pain1.wav", 1, ATTN_NORM);
|
||||||
|
else
|
||||||
|
sound (self, CHAN_VOICE, "enforcer/pain2.wav", 1, ATTN_NORM);
|
||||||
|
|
||||||
|
self.pain_finished = time + 1;
|
||||||
|
if (r < 0.2)
|
||||||
|
enf_paina1 ();
|
||||||
|
else if (r < 0.4)
|
||||||
|
enf_painb1 ();
|
||||||
|
else if (r < 0.7)
|
||||||
|
enf_painc1 ();
|
||||||
|
else
|
||||||
|
enf_paind1 ();
|
||||||
|
};
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
void() enf_die1 =[ $death1, enf_die2 ] {};
|
||||||
|
void() enf_die2 =[ $death2, enf_die3 ] {};
|
||||||
|
void() enf_die3 =[ $death3, enf_die4 ]
|
||||||
|
{self.solid = SOLID_NOT;DropBackpack();};
|
||||||
|
void() enf_die4 =[ $death4, enf_die5 ] {ai_forward(14);};
|
||||||
|
void() enf_die5 =[ $death5, enf_die6 ] {ai_forward(2);};
|
||||||
|
void() enf_die6 =[ $death6, enf_die7 ] {};
|
||||||
|
void() enf_die7 =[ $death7, enf_die8 ] {};
|
||||||
|
void() enf_die8 =[ $death8, enf_die9 ] {};
|
||||||
|
void() enf_die9 =[ $death9, enf_die10 ] {ai_forward(3);};
|
||||||
|
void() enf_die10 =[ $death10, enf_die11 ] {ai_forward(5);};
|
||||||
|
void() enf_die11 =[ $death11, enf_die12 ] {ai_forward(5);};
|
||||||
|
void() enf_die12 =[ $death12, enf_die13 ] {ai_forward(5);};
|
||||||
|
void() enf_die13 =[ $death13, enf_die14 ] {};
|
||||||
|
void() enf_die14 =[ $death14, enf_die14 ] {};
|
||||||
|
|
||||||
|
void() enf_fdie1 =[ $fdeath1, enf_fdie2 ] {
|
||||||
|
|
||||||
|
};
|
||||||
|
void() enf_fdie2 =[ $fdeath2, enf_fdie3 ] {};
|
||||||
|
void() enf_fdie3 =[ $fdeath3, enf_fdie4 ]
|
||||||
|
{self.solid = SOLID_NOT;DropBackpack();};
|
||||||
|
void() enf_fdie4 =[ $fdeath4, enf_fdie5 ] {};
|
||||||
|
void() enf_fdie5 =[ $fdeath5, enf_fdie6 ] {};
|
||||||
|
void() enf_fdie6 =[ $fdeath6, enf_fdie7 ] {};
|
||||||
|
void() enf_fdie7 =[ $fdeath7, enf_fdie8 ] {};
|
||||||
|
void() enf_fdie8 =[ $fdeath8, enf_fdie9 ] {};
|
||||||
|
void() enf_fdie9 =[ $fdeath9, enf_fdie10 ] {};
|
||||||
|
void() enf_fdie10 =[ $fdeath10, enf_fdie11 ] {};
|
||||||
|
void() enf_fdie11 =[ $fdeath11, enf_fdie11 ] {};
|
||||||
|
|
||||||
|
|
||||||
|
void() enf_die =
|
||||||
|
{
|
||||||
|
// check for gib
|
||||||
|
if (self.health < -35)
|
||||||
|
{
|
||||||
|
sound (self, CHAN_VOICE, "player/udeath.wav", 1, ATTN_NORM);
|
||||||
|
ThrowHead ("progs/h_mega.mdl", self.health);
|
||||||
|
ThrowGib ("progs/gib1.mdl", self.health);
|
||||||
|
ThrowGib ("progs/gib2.mdl", self.health);
|
||||||
|
ThrowGib ("progs/gib3.mdl", self.health);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// regular death
|
||||||
|
sound (self, CHAN_VOICE, "enforcer/death1.wav", 1, ATTN_NORM);
|
||||||
|
if (random() > 0.5)
|
||||||
|
enf_die1 ();
|
||||||
|
else
|
||||||
|
enf_fdie1 ();
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
/*QUAKED monster_enforcer (1 0 0) (-16 -16 -24) (16 16 40) Ambush
|
||||||
|
|
||||||
|
*/
|
||||||
|
void() monster_enforcer =
|
||||||
|
{
|
||||||
|
if (deathmatch)
|
||||||
|
{
|
||||||
|
remove(self);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
precache_model2 ("progs/enforcer.mdl");
|
||||||
|
precache_model2 ("progs/h_mega.mdl");
|
||||||
|
precache_model2 ("progs/laser.mdl");
|
||||||
|
|
||||||
|
precache_sound2 ("enforcer/death1.wav");
|
||||||
|
precache_sound2 ("enforcer/enfire.wav");
|
||||||
|
precache_sound2 ("enforcer/enfstop.wav");
|
||||||
|
precache_sound2 ("enforcer/idle1.wav");
|
||||||
|
precache_sound2 ("enforcer/pain1.wav");
|
||||||
|
precache_sound2 ("enforcer/pain2.wav");
|
||||||
|
precache_sound2 ("enforcer/sight1.wav");
|
||||||
|
precache_sound2 ("enforcer/sight2.wav");
|
||||||
|
precache_sound2 ("enforcer/sight3.wav");
|
||||||
|
precache_sound2 ("enforcer/sight4.wav");
|
||||||
|
|
||||||
|
self.solid = SOLID_SLIDEBOX;
|
||||||
|
self.movetype = MOVETYPE_STEP;
|
||||||
|
|
||||||
|
setmodel (self, "progs/enforcer.mdl");
|
||||||
|
|
||||||
|
setsize (self, '-16 -16 -24', '16 16 40');
|
||||||
|
self.health = 80;
|
||||||
|
|
||||||
|
self.th_stand = enf_stand1;
|
||||||
|
self.th_walk = enf_walk1;
|
||||||
|
self.th_run = enf_run1;
|
||||||
|
self.th_pain = enf_pain;
|
||||||
|
self.th_die = enf_die;
|
||||||
|
self.th_missile = enf_atk1;
|
||||||
|
|
||||||
|
self.ammo_cells_real = 5; // drop 5 cells on death
|
||||||
|
|
||||||
|
walkmonster_start();
|
||||||
|
};
|
|
@ -119,14 +119,30 @@ string(string cv) stringserverinfokey =
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
// cdtrack wrapper
|
// cdtrack wrapper
|
||||||
|
#ifdef NETQUAKE
|
||||||
|
// only NetQuake supports loop track
|
||||||
void(float track, float looptrack) ENG_SwitchTrack =
|
void(float track, float looptrack) ENG_SwitchTrack =
|
||||||
{
|
{
|
||||||
WriteByte (MSG_ALL, SVC_CDTRACK);
|
WriteByte (MSG_ALL, SVC_CDTRACK);
|
||||||
WriteByte (MSG_ALL, track);
|
WriteByte (MSG_ALL, track);
|
||||||
#ifdef NETQUAKE
|
|
||||||
// only NetQuake supports loop track
|
|
||||||
WriteByte (MSG_ALL, looptrack);
|
WriteByte (MSG_ALL, looptrack);
|
||||||
|
};
|
||||||
|
#else
|
||||||
|
void(float track) _ENG_SwitchTrack =
|
||||||
|
{
|
||||||
|
WriteByte (MSG_ALL, SVC_CDTRACK);
|
||||||
|
WriteByte (MSG_ALL, track);
|
||||||
|
};
|
||||||
|
|
||||||
|
#define ENG_SwitchTrack(a,b) _ENG_SwitchTrack(a)
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
// finale wrapper
|
||||||
|
void(string s) ENG_Finale =
|
||||||
|
{
|
||||||
|
WriteByte (MSG_ALL, SVC_FINALE);
|
||||||
|
WriteString (MSG_ALL, s);
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
// engine check routine
|
// engine check routine
|
||||||
|
|
365
quakec/basemod/fight.qc
Normal file
365
quakec/basemod/fight.qc
Normal file
|
@ -0,0 +1,365 @@
|
||||||
|
|
||||||
|
/*
|
||||||
|
|
||||||
|
A monster is in fight mode if it thinks it can effectively attack its
|
||||||
|
enemy.
|
||||||
|
|
||||||
|
When it decides it can't attack, it goes into hunt mode.
|
||||||
|
|
||||||
|
*/
|
||||||
|
|
||||||
|
float(float v) anglemod;
|
||||||
|
|
||||||
|
void() ai_face;
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
/*
|
||||||
|
===========
|
||||||
|
CheckAttack
|
||||||
|
|
||||||
|
The player is in view, so decide to move or launch an attack
|
||||||
|
Returns FALSE if movement should continue
|
||||||
|
============
|
||||||
|
*/
|
||||||
|
float(float enemy_range) CheckAttack =
|
||||||
|
{
|
||||||
|
local vector spot1, spot2;
|
||||||
|
local entity targ;
|
||||||
|
local float chance;
|
||||||
|
|
||||||
|
targ = self.enemy;
|
||||||
|
|
||||||
|
// see if any entities are in the way of the shot
|
||||||
|
spot1 = self.origin + self.view_ofs;
|
||||||
|
spot2 = targ.origin + targ.view_ofs;
|
||||||
|
|
||||||
|
traceline (spot1, spot2, FALSE, self);
|
||||||
|
|
||||||
|
if (trace_ent != targ)
|
||||||
|
return FALSE; // don't have a clear shot
|
||||||
|
|
||||||
|
if (trace_inopen && trace_inwater)
|
||||||
|
return FALSE; // sight line crossed contents
|
||||||
|
|
||||||
|
if (enemy_range == RANGE_MELEE)
|
||||||
|
{ // melee attack
|
||||||
|
if (self.th_melee)
|
||||||
|
{
|
||||||
|
self.th_melee ();
|
||||||
|
return TRUE;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// missile attack
|
||||||
|
if (!self.th_missile)
|
||||||
|
return FALSE;
|
||||||
|
|
||||||
|
if (time < self.attack_finished)
|
||||||
|
return FALSE;
|
||||||
|
|
||||||
|
if (enemy_range == RANGE_FAR)
|
||||||
|
return FALSE;
|
||||||
|
|
||||||
|
if (enemy_range == RANGE_MELEE)
|
||||||
|
{
|
||||||
|
chance = 0.9;
|
||||||
|
self.attack_finished = 0;
|
||||||
|
}
|
||||||
|
else if (enemy_range == RANGE_NEAR)
|
||||||
|
{
|
||||||
|
if (self.th_melee)
|
||||||
|
chance = 0.2;
|
||||||
|
else
|
||||||
|
chance = 0.4;
|
||||||
|
}
|
||||||
|
else if (enemy_range == RANGE_MID)
|
||||||
|
{
|
||||||
|
if (self.th_melee)
|
||||||
|
chance = 0.05;
|
||||||
|
else
|
||||||
|
chance = 0.1;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
chance = 0;
|
||||||
|
|
||||||
|
if (random () < chance)
|
||||||
|
{
|
||||||
|
self.th_missile ();
|
||||||
|
SUB_AttackFinished (2*random());
|
||||||
|
return TRUE;
|
||||||
|
}
|
||||||
|
|
||||||
|
return FALSE;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
/*
|
||||||
|
=============
|
||||||
|
ai_face
|
||||||
|
|
||||||
|
Stay facing the enemy
|
||||||
|
=============
|
||||||
|
*/
|
||||||
|
void() ai_face =
|
||||||
|
{
|
||||||
|
self.ideal_yaw = vectoyaw(self.enemy.origin - self.origin);
|
||||||
|
ChangeYaw ();
|
||||||
|
};
|
||||||
|
|
||||||
|
/*
|
||||||
|
=============
|
||||||
|
ai_charge
|
||||||
|
|
||||||
|
The monster is in a melee attack, so get as close as possible to .enemy
|
||||||
|
=============
|
||||||
|
*/
|
||||||
|
float (entity targ) visible;
|
||||||
|
float(entity targ) infront;
|
||||||
|
float(entity targ) range;
|
||||||
|
|
||||||
|
void(float d) ai_charge =
|
||||||
|
{
|
||||||
|
ai_face ();
|
||||||
|
movetogoal (d); // done in C code...
|
||||||
|
};
|
||||||
|
|
||||||
|
void() ai_charge_side =
|
||||||
|
{
|
||||||
|
local vector dtemp;
|
||||||
|
local float heading;
|
||||||
|
|
||||||
|
// aim to the left of the enemy for a flyby
|
||||||
|
|
||||||
|
self.ideal_yaw = vectoyaw(self.enemy.origin - self.origin);
|
||||||
|
ChangeYaw ();
|
||||||
|
|
||||||
|
makevectors (self.angles);
|
||||||
|
dtemp = self.enemy.origin - 30*v_right;
|
||||||
|
heading = vectoyaw(dtemp - self.origin);
|
||||||
|
|
||||||
|
walkmove(heading, 20);
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
/*
|
||||||
|
=============
|
||||||
|
ai_melee
|
||||||
|
|
||||||
|
=============
|
||||||
|
*/
|
||||||
|
void(INTEGER mod) ai_melee =
|
||||||
|
{
|
||||||
|
local vector delta;
|
||||||
|
local float ldmg;
|
||||||
|
|
||||||
|
if (!self.enemy)
|
||||||
|
return; // removed before stroke
|
||||||
|
|
||||||
|
delta = self.enemy.origin - self.origin;
|
||||||
|
|
||||||
|
if (vlen(delta) > 60)
|
||||||
|
return;
|
||||||
|
|
||||||
|
ldmg = (random() + random() + random()) * 3;
|
||||||
|
T_Damage (self.enemy, self, self, ldmg, mod);
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
void(INTEGER mod) ai_melee_side =
|
||||||
|
{
|
||||||
|
local vector delta;
|
||||||
|
local float ldmg;
|
||||||
|
|
||||||
|
if (!self.enemy)
|
||||||
|
return; // removed before stroke
|
||||||
|
|
||||||
|
ai_charge_side();
|
||||||
|
|
||||||
|
delta = self.enemy.origin - self.origin;
|
||||||
|
|
||||||
|
if (vlen(delta) > 60)
|
||||||
|
return;
|
||||||
|
if (!CanDamage (self.enemy, self))
|
||||||
|
return;
|
||||||
|
ldmg = (random() + random() + random()) * 3;
|
||||||
|
T_Damage (self.enemy, self, self, ldmg, mod);
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
/*
|
||||||
|
===========
|
||||||
|
SoldierCheckAttack
|
||||||
|
|
||||||
|
The player is in view, so decide to move or launch an attack
|
||||||
|
Returns FALSE if movement should continue
|
||||||
|
============
|
||||||
|
*/
|
||||||
|
float(float enemy_range) SoldierCheckAttack =
|
||||||
|
{
|
||||||
|
local vector spot1, spot2;
|
||||||
|
local entity targ;
|
||||||
|
local float chance;
|
||||||
|
|
||||||
|
targ = self.enemy;
|
||||||
|
|
||||||
|
// see if any entities are in the way of the shot
|
||||||
|
spot1 = self.origin + self.view_ofs;
|
||||||
|
spot2 = targ.origin + targ.view_ofs;
|
||||||
|
|
||||||
|
traceline (spot1, spot2, FALSE, self);
|
||||||
|
|
||||||
|
if (trace_inopen && trace_inwater)
|
||||||
|
return FALSE; // sight line crossed contents
|
||||||
|
|
||||||
|
if (trace_ent != targ)
|
||||||
|
return FALSE; // don't have a clear shot
|
||||||
|
|
||||||
|
|
||||||
|
// missile attack
|
||||||
|
if (time < self.attack_finished)
|
||||||
|
return FALSE;
|
||||||
|
|
||||||
|
if (enemy_range == RANGE_FAR)
|
||||||
|
return FALSE;
|
||||||
|
|
||||||
|
if (enemy_range == RANGE_MELEE)
|
||||||
|
chance = 0.9;
|
||||||
|
else if (enemy_range == RANGE_NEAR)
|
||||||
|
chance = 0.4;
|
||||||
|
else if (enemy_range == RANGE_MID)
|
||||||
|
chance = 0.05;
|
||||||
|
else
|
||||||
|
chance = 0;
|
||||||
|
|
||||||
|
if (random() < chance)
|
||||||
|
{
|
||||||
|
self.th_missile ();
|
||||||
|
SUB_AttackFinished (1 + random());
|
||||||
|
return TRUE;
|
||||||
|
}
|
||||||
|
|
||||||
|
return FALSE;
|
||||||
|
};
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
/*
|
||||||
|
===========
|
||||||
|
ShamCheckAttack
|
||||||
|
|
||||||
|
The player is in view, so decide to move or launch an attack
|
||||||
|
Returns FALSE if movement should continue
|
||||||
|
============
|
||||||
|
*/
|
||||||
|
float(float enemy_range) ShamCheckAttack =
|
||||||
|
{
|
||||||
|
local vector spot1, spot2;
|
||||||
|
local entity targ;
|
||||||
|
// local float chance;
|
||||||
|
// local float enemy_yaw;
|
||||||
|
|
||||||
|
if (enemy_range == RANGE_MELEE)
|
||||||
|
{
|
||||||
|
if (CanDamage (self.enemy, self))
|
||||||
|
{
|
||||||
|
self.attack_state = AS_MELEE;
|
||||||
|
return TRUE;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (time < self.attack_finished)
|
||||||
|
return FALSE;
|
||||||
|
|
||||||
|
targ = self.enemy;
|
||||||
|
|
||||||
|
// see if any entities are in the way of the shot
|
||||||
|
spot1 = self.origin + self.view_ofs;
|
||||||
|
spot2 = targ.origin + targ.view_ofs;
|
||||||
|
|
||||||
|
if (vlen(spot1 - spot2) > 600)
|
||||||
|
return FALSE;
|
||||||
|
|
||||||
|
traceline (spot1, spot2, FALSE, self);
|
||||||
|
|
||||||
|
if (trace_inopen && trace_inwater)
|
||||||
|
return FALSE; // sight line crossed contents
|
||||||
|
|
||||||
|
if (trace_ent != targ)
|
||||||
|
{
|
||||||
|
return FALSE; // don't have a clear shot
|
||||||
|
}
|
||||||
|
|
||||||
|
// missile attack
|
||||||
|
if (enemy_range == RANGE_FAR)
|
||||||
|
return FALSE;
|
||||||
|
|
||||||
|
self.attack_state = AS_MISSILE;
|
||||||
|
SUB_AttackFinished (2 + 2*random());
|
||||||
|
return TRUE;
|
||||||
|
};
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
|
||||||
|
/*
|
||||||
|
===========
|
||||||
|
OgreCheckAttack
|
||||||
|
|
||||||
|
The player is in view, so decide to move or launch an attack
|
||||||
|
Returns FALSE if movement should continue
|
||||||
|
============
|
||||||
|
*/
|
||||||
|
float(float enemy_range) OgreCheckAttack =
|
||||||
|
{
|
||||||
|
local vector spot1, spot2;
|
||||||
|
local entity targ;
|
||||||
|
local float chance;
|
||||||
|
|
||||||
|
if (enemy_range == RANGE_MELEE)
|
||||||
|
{
|
||||||
|
if (CanDamage (self.enemy, self))
|
||||||
|
{
|
||||||
|
self.attack_state = AS_MELEE;
|
||||||
|
return TRUE;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (time < self.attack_finished)
|
||||||
|
return FALSE;
|
||||||
|
|
||||||
|
targ = self.enemy;
|
||||||
|
|
||||||
|
// see if any entities are in the way of the shot
|
||||||
|
spot1 = self.origin + self.view_ofs;
|
||||||
|
spot2 = targ.origin + targ.view_ofs;
|
||||||
|
|
||||||
|
traceline (spot1, spot2, FALSE, self);
|
||||||
|
|
||||||
|
if (trace_inopen && trace_inwater)
|
||||||
|
return FALSE; // sight line crossed contents
|
||||||
|
|
||||||
|
if (trace_ent != targ)
|
||||||
|
{
|
||||||
|
return FALSE; // don't have a clear shot
|
||||||
|
}
|
||||||
|
|
||||||
|
// missile attack
|
||||||
|
if (time < self.attack_finished)
|
||||||
|
return FALSE;
|
||||||
|
|
||||||
|
if (enemy_range == RANGE_FAR)
|
||||||
|
return FALSE;
|
||||||
|
|
||||||
|
else if (enemy_range == RANGE_NEAR)
|
||||||
|
chance = 0.10;
|
||||||
|
else if (enemy_range == RANGE_MID)
|
||||||
|
chance = 0.05;
|
||||||
|
else
|
||||||
|
chance = 0;
|
||||||
|
|
||||||
|
self.attack_state = AS_MISSILE;
|
||||||
|
SUB_AttackFinished (1 + 2*random());
|
||||||
|
return TRUE;
|
||||||
|
};
|
||||||
|
|
186
quakec/basemod/fish.qc
Normal file
186
quakec/basemod/fish.qc
Normal file
|
@ -0,0 +1,186 @@
|
||||||
|
$cd id1/models/fish
|
||||||
|
$origin 0 0 24
|
||||||
|
$base base
|
||||||
|
$skin skin
|
||||||
|
|
||||||
|
$frame attack1 attack2 attack3 attack4 attack5 attack6
|
||||||
|
$frame attack7 attack8 attack9 attack10 attack11 attack12 attack13
|
||||||
|
$frame attack14 attack15 attack16 attack17 attack18
|
||||||
|
|
||||||
|
$frame death1 death2 death3 death4 death5 death6 death7
|
||||||
|
$frame death8 death9 death10 death11 death12 death13 death14 death15
|
||||||
|
$frame death16 death17 death18 death19 death20 death21
|
||||||
|
|
||||||
|
$frame swim1 swim2 swim3 swim4 swim5 swim6 swim7 swim8
|
||||||
|
$frame swim9 swim10 swim11 swim12 swim13 swim14 swim15 swim16 swim17
|
||||||
|
$frame swim18
|
||||||
|
|
||||||
|
$frame pain1 pain2 pain3 pain4 pain5 pain6 pain7 pain8
|
||||||
|
$frame pain9
|
||||||
|
|
||||||
|
void() swimmonster_start;
|
||||||
|
|
||||||
|
void() f_stand1 =[ $swim1, f_stand2 ] {ai_stand();};
|
||||||
|
void() f_stand2 =[ $swim2, f_stand3 ] {ai_stand();};
|
||||||
|
void() f_stand3 =[ $swim3, f_stand4 ] {ai_stand();};
|
||||||
|
void() f_stand4 =[ $swim4, f_stand5 ] {ai_stand();};
|
||||||
|
void() f_stand5 =[ $swim5, f_stand6 ] {ai_stand();};
|
||||||
|
void() f_stand6 =[ $swim6, f_stand7 ] {ai_stand();};
|
||||||
|
void() f_stand7 =[ $swim7, f_stand8 ] {ai_stand();};
|
||||||
|
void() f_stand8 =[ $swim8, f_stand9 ] {ai_stand();};
|
||||||
|
void() f_stand9 =[ $swim9, f_stand10 ] {ai_stand();};
|
||||||
|
void() f_stand10 =[ $swim10, f_stand11 ] {ai_stand();};
|
||||||
|
void() f_stand11 =[ $swim11, f_stand12 ] {ai_stand();};
|
||||||
|
void() f_stand12 =[ $swim12, f_stand13 ] {ai_stand();};
|
||||||
|
void() f_stand13 =[ $swim13, f_stand14 ] {ai_stand();};
|
||||||
|
void() f_stand14 =[ $swim14, f_stand15 ] {ai_stand();};
|
||||||
|
void() f_stand15 =[ $swim15, f_stand16 ] {ai_stand();};
|
||||||
|
void() f_stand16 =[ $swim16, f_stand17 ] {ai_stand();};
|
||||||
|
void() f_stand17 =[ $swim17, f_stand18 ] {ai_stand();};
|
||||||
|
void() f_stand18 =[ $swim18, f_stand1 ] {ai_stand();};
|
||||||
|
|
||||||
|
void() f_walk1 =[ $swim1, f_walk2 ] {ai_walk(8);};
|
||||||
|
void() f_walk2 =[ $swim2, f_walk3 ] {ai_walk(8);};
|
||||||
|
void() f_walk3 =[ $swim3, f_walk4 ] {ai_walk(8);};
|
||||||
|
void() f_walk4 =[ $swim4, f_walk5 ] {ai_walk(8);};
|
||||||
|
void() f_walk5 =[ $swim5, f_walk6 ] {ai_walk(8);};
|
||||||
|
void() f_walk6 =[ $swim6, f_walk7 ] {ai_walk(8);};
|
||||||
|
void() f_walk7 =[ $swim7, f_walk8 ] {ai_walk(8);};
|
||||||
|
void() f_walk8 =[ $swim8, f_walk9 ] {ai_walk(8);};
|
||||||
|
void() f_walk9 =[ $swim9, f_walk10 ] {ai_walk(8);};
|
||||||
|
void() f_walk10 =[ $swim10, f_walk11 ] {ai_walk(8);};
|
||||||
|
void() f_walk11 =[ $swim11, f_walk12 ] {ai_walk(8);};
|
||||||
|
void() f_walk12 =[ $swim12, f_walk13 ] {ai_walk(8);};
|
||||||
|
void() f_walk13 =[ $swim13, f_walk14 ] {ai_walk(8);};
|
||||||
|
void() f_walk14 =[ $swim14, f_walk15 ] {ai_walk(8);};
|
||||||
|
void() f_walk15 =[ $swim15, f_walk16 ] {ai_walk(8);};
|
||||||
|
void() f_walk16 =[ $swim16, f_walk17 ] {ai_walk(8);};
|
||||||
|
void() f_walk17 =[ $swim17, f_walk18 ] {ai_walk(8);};
|
||||||
|
void() f_walk18 =[ $swim18, f_walk1 ] {ai_walk(8);};
|
||||||
|
|
||||||
|
void() f_run1 =[ $swim1, f_run2 ] {ai_run(12);
|
||||||
|
if (random() < 0.5)
|
||||||
|
sound (self, CHAN_VOICE, "fish/idle.wav", 1, ATTN_NORM);
|
||||||
|
};
|
||||||
|
void() f_run2 =[ $swim3, f_run3 ] {ai_run(12);};
|
||||||
|
void() f_run3 =[ $swim5, f_run4 ] {ai_run(12);};
|
||||||
|
void() f_run4 =[ $swim7, f_run5 ] {ai_run(12);};
|
||||||
|
void() f_run5 =[ $swim9, f_run6 ] {ai_run(12);};
|
||||||
|
void() f_run6 =[ $swim11, f_run7 ] {ai_run(12);};
|
||||||
|
void() f_run7 =[ $swim13, f_run8 ] {ai_run(12);};
|
||||||
|
void() f_run8 =[ $swim15, f_run9 ] {ai_run(12);};
|
||||||
|
void() f_run9 =[ $swim17, f_run1 ] {ai_run(12);};
|
||||||
|
|
||||||
|
void() fish_melee =
|
||||||
|
{
|
||||||
|
local vector delta;
|
||||||
|
local float ldmg;
|
||||||
|
|
||||||
|
if (!self.enemy)
|
||||||
|
return; // removed before stroke
|
||||||
|
|
||||||
|
delta = self.enemy.origin - self.origin;
|
||||||
|
|
||||||
|
if (vlen(delta) > 60)
|
||||||
|
return;
|
||||||
|
|
||||||
|
sound (self, CHAN_VOICE, "fish/bite.wav", 1, ATTN_NORM);
|
||||||
|
ldmg = (random() + random()) * 3;
|
||||||
|
T_Damage (self.enemy, self, self, ldmg, MOD_FISH);
|
||||||
|
};
|
||||||
|
|
||||||
|
void() f_attack1 =[ $attack1, f_attack2 ] {ai_charge(10);};
|
||||||
|
void() f_attack2 =[ $attack2, f_attack3 ] {ai_charge(10);};
|
||||||
|
void() f_attack3 =[ $attack3, f_attack4 ] {fish_melee();};
|
||||||
|
void() f_attack4 =[ $attack4, f_attack5 ] {ai_charge(10);};
|
||||||
|
void() f_attack5 =[ $attack5, f_attack6 ] {ai_charge(10);};
|
||||||
|
void() f_attack6 =[ $attack6, f_attack7 ] {ai_charge(10);};
|
||||||
|
void() f_attack7 =[ $attack7, f_attack8 ] {ai_charge(10);};
|
||||||
|
void() f_attack8 =[ $attack8, f_attack9 ] {ai_charge(10);};
|
||||||
|
void() f_attack9 =[ $attack9, f_attack10] {fish_melee();};
|
||||||
|
void() f_attack10 =[ $attack10, f_attack11] {ai_charge(10);};
|
||||||
|
void() f_attack11 =[ $attack11, f_attack12] {ai_charge(10);};
|
||||||
|
void() f_attack12 =[ $attack12, f_attack13] {ai_charge(10);};
|
||||||
|
void() f_attack13 =[ $attack13, f_attack14] {ai_charge(10);};
|
||||||
|
void() f_attack14 =[ $attack14, f_attack15] {ai_charge(10);};
|
||||||
|
void() f_attack15 =[ $attack15, f_attack16] {fish_melee();};
|
||||||
|
void() f_attack16 =[ $attack16, f_attack17] {ai_charge(10);};
|
||||||
|
void() f_attack17 =[ $attack17, f_attack18] {ai_charge(10);};
|
||||||
|
void() f_attack18 =[ $attack18, f_run1 ] {ai_charge(10);};
|
||||||
|
|
||||||
|
void() f_death1 =[ $death1, f_death2 ] {
|
||||||
|
sound (self, CHAN_VOICE, "fish/death.wav", 1, ATTN_NORM);
|
||||||
|
};
|
||||||
|
void() f_death2 =[ $death2, f_death3 ] {};
|
||||||
|
void() f_death3 =[ $death3, f_death4 ] {self.solid = SOLID_NOT;};
|
||||||
|
void() f_death4 =[ $death4, f_death5 ] {};
|
||||||
|
void() f_death5 =[ $death5, f_death6 ] {};
|
||||||
|
void() f_death6 =[ $death6, f_death7 ] {};
|
||||||
|
void() f_death7 =[ $death7, f_death8 ] {};
|
||||||
|
void() f_death8 =[ $death8, f_death9 ] {};
|
||||||
|
void() f_death9 =[ $death9, f_death10 ] {};
|
||||||
|
void() f_death10 =[ $death10, f_death11 ] {};
|
||||||
|
void() f_death11 =[ $death11, f_death12 ] {};
|
||||||
|
void() f_death12 =[ $death12, f_death13 ] {};
|
||||||
|
void() f_death13 =[ $death13, f_death14 ] {};
|
||||||
|
void() f_death14 =[ $death14, f_death15 ] {};
|
||||||
|
void() f_death15 =[ $death15, f_death16 ] {};
|
||||||
|
void() f_death16 =[ $death16, f_death17 ] {};
|
||||||
|
void() f_death17 =[ $death17, f_death18 ] {};
|
||||||
|
void() f_death18 =[ $death18, f_death19 ] {};
|
||||||
|
void() f_death19 =[ $death19, f_death20 ] {};
|
||||||
|
void() f_death20 =[ $death20, f_death21 ] {};
|
||||||
|
void() f_death21 =[ $death21, f_death21 ] {};
|
||||||
|
|
||||||
|
void() f_pain1 =[ $pain1, f_pain2 ] {};
|
||||||
|
void() f_pain2 =[ $pain2, f_pain3 ] {ai_pain(6);};
|
||||||
|
void() f_pain3 =[ $pain3, f_pain4 ] {ai_pain(6);};
|
||||||
|
void() f_pain4 =[ $pain4, f_pain5 ] {ai_pain(6);};
|
||||||
|
void() f_pain5 =[ $pain5, f_pain6 ] {ai_pain(6);};
|
||||||
|
void() f_pain6 =[ $pain6, f_pain7 ] {ai_pain(6);};
|
||||||
|
void() f_pain7 =[ $pain7, f_pain8 ] {ai_pain(6);};
|
||||||
|
void() f_pain8 =[ $pain8, f_pain9 ] {ai_pain(6);};
|
||||||
|
void() f_pain9 =[ $pain9, f_run1 ] {ai_pain(6);};
|
||||||
|
|
||||||
|
void(entity attacker, float damage) fish_pain =
|
||||||
|
{
|
||||||
|
|
||||||
|
// fish allways do pain frames
|
||||||
|
f_pain1 ();
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
/*QUAKED monster_fish (1 0 0) (-16 -16 -24) (16 16 24) Ambush
|
||||||
|
*/
|
||||||
|
void() monster_fish =
|
||||||
|
{
|
||||||
|
if (deathmatch)
|
||||||
|
{
|
||||||
|
remove(self);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
precache_model2 ("progs/fish.mdl");
|
||||||
|
|
||||||
|
precache_sound2 ("fish/death.wav");
|
||||||
|
precache_sound2 ("fish/bite.wav");
|
||||||
|
precache_sound2 ("fish/idle.wav");
|
||||||
|
|
||||||
|
self.solid = SOLID_SLIDEBOX;
|
||||||
|
self.movetype = MOVETYPE_STEP;
|
||||||
|
|
||||||
|
setmodel (self, "progs/fish.mdl");
|
||||||
|
|
||||||
|
setsize (self, '-16 -16 -24', '16 16 24');
|
||||||
|
self.health = 25;
|
||||||
|
|
||||||
|
self.th_stand = f_stand1;
|
||||||
|
self.th_walk = f_walk1;
|
||||||
|
self.th_run = f_run1;
|
||||||
|
self.th_die = f_death1;
|
||||||
|
self.th_pain = fish_pain;
|
||||||
|
self.th_melee = f_attack1;
|
||||||
|
|
||||||
|
swimmonster_start ();
|
||||||
|
};
|
||||||
|
|
442
quakec/basemod/hknight.qc
Normal file
442
quakec/basemod/hknight.qc
Normal file
|
@ -0,0 +1,442 @@
|
||||||
|
/*
|
||||||
|
==============================================================================
|
||||||
|
|
||||||
|
KNIGHT
|
||||||
|
|
||||||
|
==============================================================================
|
||||||
|
*/
|
||||||
|
|
||||||
|
$cd id1/models/knight2
|
||||||
|
$origin 0 0 24
|
||||||
|
$base base
|
||||||
|
$skin skin
|
||||||
|
|
||||||
|
$frame stand1 stand2 stand3 stand4 stand5 stand6 stand7 stand8 stand9
|
||||||
|
|
||||||
|
$frame walk1 walk2 walk3 walk4 walk5 walk6 walk7 walk8 walk9
|
||||||
|
$frame walk10 walk11 walk12 walk13 walk14 walk15 walk16 walk17
|
||||||
|
$frame walk18 walk19 walk20
|
||||||
|
|
||||||
|
$frame run1 run2 run3 run4 run5 run6 run7 run8
|
||||||
|
|
||||||
|
$frame pain1 pain2 pain3 pain4 pain5
|
||||||
|
|
||||||
|
$frame death1 death2 death3 death4 death5 death6 death7 death8
|
||||||
|
$frame death9 death10 death11 death12
|
||||||
|
|
||||||
|
$frame deathb1 deathb2 deathb3 deathb4 deathb5 deathb6 deathb7 deathb8
|
||||||
|
$frame deathb9
|
||||||
|
|
||||||
|
$frame char_a1 char_a2 char_a3 char_a4 char_a5 char_a6 char_a7 char_a8
|
||||||
|
$frame char_a9 char_a10 char_a11 char_a12 char_a13 char_a14 char_a15 char_a16
|
||||||
|
|
||||||
|
$frame magica1 magica2 magica3 magica4 magica5 magica6 magica7 magica8
|
||||||
|
$frame magica9 magica10 magica11 magica12 magica13 magica14
|
||||||
|
|
||||||
|
$frame magicb1 magicb2 magicb3 magicb4 magicb5 magicb6 magicb7 magicb8
|
||||||
|
$frame magicb9 magicb10 magicb11 magicb12 magicb13
|
||||||
|
|
||||||
|
$frame char_b1 char_b2 char_b3 char_b4 char_b5 char_b6
|
||||||
|
|
||||||
|
$frame slice1 slice2 slice3 slice4 slice5 slice6 slice7 slice8 slice9 slice10
|
||||||
|
|
||||||
|
$frame smash1 smash2 smash3 smash4 smash5 smash6 smash7 smash8 smash9 smash10
|
||||||
|
$frame smash11
|
||||||
|
|
||||||
|
$frame w_attack1 w_attack2 w_attack3 w_attack4 w_attack5 w_attack6 w_attack7
|
||||||
|
$frame w_attack8 w_attack9 w_attack10 w_attack11 w_attack12 w_attack13 w_attack14
|
||||||
|
$frame w_attack15 w_attack16 w_attack17 w_attack18 w_attack19 w_attack20
|
||||||
|
$frame w_attack21 w_attack22
|
||||||
|
|
||||||
|
$frame magicc1 magicc2 magicc3 magicc4 magicc5 magicc6 magicc7 magicc8
|
||||||
|
$frame magicc9 magicc10 magicc11
|
||||||
|
|
||||||
|
|
||||||
|
void() hknight_char_a1;
|
||||||
|
void() hknight_run1;
|
||||||
|
void() hk_idle_sound;
|
||||||
|
|
||||||
|
void(float offset) hknight_shot =
|
||||||
|
{
|
||||||
|
local vector offang;
|
||||||
|
local vector org, vec;
|
||||||
|
|
||||||
|
offang = vectoangles (self.enemy.origin - self.origin);
|
||||||
|
offang_y = offang_y + offset * 6;
|
||||||
|
|
||||||
|
makevectors (offang);
|
||||||
|
|
||||||
|
org = self.origin + self.mins + self.size*0.5 + v_forward * 20;
|
||||||
|
|
||||||
|
// set missile speed
|
||||||
|
vec = normalize (v_forward);
|
||||||
|
vec_z = 0 - vec_z + (random() - 0.5)*0.1;
|
||||||
|
|
||||||
|
sound (self, CHAN_WEAPON, "hknight/attack1.wav", 1, ATTN_NORM);
|
||||||
|
PRJ_FireProjectile(self, "progs/k_spike.mdl", org, vec * 300, PE_KNIGHTSPIKE, 9, MOD_HKNIGHT, 6);
|
||||||
|
};
|
||||||
|
|
||||||
|
void() CheckForCharge =
|
||||||
|
{
|
||||||
|
// check for mad charge
|
||||||
|
if (!visible(self.enemy))
|
||||||
|
return;
|
||||||
|
if (time < self.attack_finished)
|
||||||
|
return;
|
||||||
|
if ( fabs(self.origin_z - self.enemy.origin_z) > 20)
|
||||||
|
return; // too much height change
|
||||||
|
if ( vlen (self.origin - self.enemy.origin) < 80)
|
||||||
|
return; // use regular attack
|
||||||
|
|
||||||
|
// charge
|
||||||
|
SUB_AttackFinished (2);
|
||||||
|
hknight_char_a1 ();
|
||||||
|
};
|
||||||
|
|
||||||
|
void() CheckContinueCharge =
|
||||||
|
{
|
||||||
|
if (time > self.attack_finished)
|
||||||
|
{
|
||||||
|
SUB_AttackFinished (3);
|
||||||
|
hknight_run1 ();
|
||||||
|
return; // done charging
|
||||||
|
}
|
||||||
|
if (random() > 0.5)
|
||||||
|
sound (self, CHAN_WEAPON, "knight/sword2.wav", 1, ATTN_NORM);
|
||||||
|
else
|
||||||
|
sound (self, CHAN_WEAPON, "knight/sword1.wav", 1, ATTN_NORM);
|
||||||
|
};
|
||||||
|
|
||||||
|
//===========================================================================
|
||||||
|
|
||||||
|
void() hknight_stand1 =[ $stand1, hknight_stand2 ] {ai_stand();};
|
||||||
|
void() hknight_stand2 =[ $stand2, hknight_stand3 ] {ai_stand();};
|
||||||
|
void() hknight_stand3 =[ $stand3, hknight_stand4 ] {ai_stand();};
|
||||||
|
void() hknight_stand4 =[ $stand4, hknight_stand5 ] {ai_stand();};
|
||||||
|
void() hknight_stand5 =[ $stand5, hknight_stand6 ] {ai_stand();};
|
||||||
|
void() hknight_stand6 =[ $stand6, hknight_stand7 ] {ai_stand();};
|
||||||
|
void() hknight_stand7 =[ $stand7, hknight_stand8 ] {ai_stand();};
|
||||||
|
void() hknight_stand8 =[ $stand8, hknight_stand9 ] {ai_stand();};
|
||||||
|
void() hknight_stand9 =[ $stand9, hknight_stand1 ] {ai_stand();};
|
||||||
|
|
||||||
|
//===========================================================================
|
||||||
|
|
||||||
|
void() hknight_walk1 =[ $walk1, hknight_walk2 ] {
|
||||||
|
hk_idle_sound();
|
||||||
|
ai_walk(2);};
|
||||||
|
void() hknight_walk2 =[ $walk2, hknight_walk3 ] {ai_walk(5);};
|
||||||
|
void() hknight_walk3 =[ $walk3, hknight_walk4 ] {ai_walk(5);};
|
||||||
|
void() hknight_walk4 =[ $walk4, hknight_walk5 ] {ai_walk(4);};
|
||||||
|
void() hknight_walk5 =[ $walk5, hknight_walk6 ] {ai_walk(4);};
|
||||||
|
void() hknight_walk6 =[ $walk6, hknight_walk7 ] {ai_walk(2);};
|
||||||
|
void() hknight_walk7 =[ $walk7, hknight_walk8 ] {ai_walk(2);};
|
||||||
|
void() hknight_walk8 =[ $walk8, hknight_walk9 ] {ai_walk(3);};
|
||||||
|
void() hknight_walk9 =[ $walk9, hknight_walk10 ] {ai_walk(3);};
|
||||||
|
void() hknight_walk10 =[ $walk10, hknight_walk11 ] {ai_walk(4);};
|
||||||
|
void() hknight_walk11 =[ $walk11, hknight_walk12 ] {ai_walk(3);};
|
||||||
|
void() hknight_walk12 =[ $walk12, hknight_walk13 ] {ai_walk(4);};
|
||||||
|
void() hknight_walk13 =[ $walk13, hknight_walk14 ] {ai_walk(6);};
|
||||||
|
void() hknight_walk14 =[ $walk14, hknight_walk15 ] {ai_walk(2);};
|
||||||
|
void() hknight_walk15 =[ $walk15, hknight_walk16 ] {ai_walk(2);};
|
||||||
|
void() hknight_walk16 =[ $walk16, hknight_walk17 ] {ai_walk(4);};
|
||||||
|
void() hknight_walk17 =[ $walk17, hknight_walk18 ] {ai_walk(3);};
|
||||||
|
void() hknight_walk18 =[ $walk18, hknight_walk19 ] {ai_walk(3);};
|
||||||
|
void() hknight_walk19 =[ $walk19, hknight_walk20 ] {ai_walk(3);};
|
||||||
|
void() hknight_walk20 =[ $walk20, hknight_walk1 ] {ai_walk(2);};
|
||||||
|
|
||||||
|
//===========================================================================
|
||||||
|
|
||||||
|
void() hknight_run1 =[ $run1, hknight_run2 ] {
|
||||||
|
hk_idle_sound();
|
||||||
|
ai_run (20); CheckForCharge (); };
|
||||||
|
void() hknight_run2 =[ $run2, hknight_run3 ] {ai_run(25);};
|
||||||
|
void() hknight_run3 =[ $run3, hknight_run4 ] {ai_run(18);};
|
||||||
|
void() hknight_run4 =[ $run4, hknight_run5 ] {ai_run(16);};
|
||||||
|
void() hknight_run5 =[ $run5, hknight_run6 ] {ai_run(14);};
|
||||||
|
void() hknight_run6 =[ $run6, hknight_run7 ] {ai_run(25);};
|
||||||
|
void() hknight_run7 =[ $run7, hknight_run8 ] {ai_run(21);};
|
||||||
|
void() hknight_run8 =[ $run8, hknight_run1 ] {ai_run(13);};
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
|
||||||
|
void() hknight_pain1 =[ $pain1, hknight_pain2 ] {sound (self, CHAN_VOICE, "hknight/pain1.wav", 1, ATTN_NORM);};
|
||||||
|
void() hknight_pain2 =[ $pain2, hknight_pain3 ] {};
|
||||||
|
void() hknight_pain3 =[ $pain3, hknight_pain4 ] {};
|
||||||
|
void() hknight_pain4 =[ $pain4, hknight_pain5 ] {};
|
||||||
|
void() hknight_pain5 =[ $pain5, hknight_run1 ] {};
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
|
||||||
|
void() hknight_die1 =[ $death1, hknight_die2 ] {ai_forward(10);};
|
||||||
|
void() hknight_die2 =[ $death2, hknight_die3 ] {ai_forward(8);};
|
||||||
|
void() hknight_die3 =[ $death3, hknight_die4 ]
|
||||||
|
{self.solid = SOLID_NOT; ai_forward(7);};
|
||||||
|
void() hknight_die4 =[ $death4, hknight_die5 ] {};
|
||||||
|
void() hknight_die5 =[ $death5, hknight_die6 ] {};
|
||||||
|
void() hknight_die6 =[ $death6, hknight_die7 ] {};
|
||||||
|
void() hknight_die7 =[ $death7, hknight_die8 ] {};
|
||||||
|
void() hknight_die8 =[ $death8, hknight_die9 ] {ai_forward(10);};
|
||||||
|
void() hknight_die9 =[ $death9, hknight_die10 ] {ai_forward(11);};
|
||||||
|
void() hknight_die10 =[ $death10, hknight_die11 ] {};
|
||||||
|
void() hknight_die11 =[ $death11, hknight_die12 ] {};
|
||||||
|
void() hknight_die12 =[ $death12, hknight_die12 ] {};
|
||||||
|
|
||||||
|
void() hknight_dieb1 =[ $deathb1, hknight_dieb2 ] {};
|
||||||
|
void() hknight_dieb2 =[ $deathb2, hknight_dieb3 ] {};
|
||||||
|
void() hknight_dieb3 =[ $deathb3, hknight_dieb4 ]
|
||||||
|
{self.solid = SOLID_NOT;};
|
||||||
|
void() hknight_dieb4 =[ $deathb4, hknight_dieb5 ] {};
|
||||||
|
void() hknight_dieb5 =[ $deathb5, hknight_dieb6 ] {};
|
||||||
|
void() hknight_dieb6 =[ $deathb6, hknight_dieb7 ] {};
|
||||||
|
void() hknight_dieb7 =[ $deathb7, hknight_dieb8 ] {};
|
||||||
|
void() hknight_dieb8 =[ $deathb8, hknight_dieb9 ] {};
|
||||||
|
void() hknight_dieb9 =[ $deathb9, hknight_dieb9 ] {};
|
||||||
|
|
||||||
|
void() hknight_die =
|
||||||
|
{
|
||||||
|
// check for gib
|
||||||
|
if (self.health < -40)
|
||||||
|
{
|
||||||
|
sound (self, CHAN_VOICE, "player/udeath.wav", 1, ATTN_NORM);
|
||||||
|
ThrowHead ("progs/h_hellkn.mdl", self.health);
|
||||||
|
ThrowGib ("progs/gib1.mdl", self.health);
|
||||||
|
ThrowGib ("progs/gib2.mdl", self.health);
|
||||||
|
ThrowGib ("progs/gib3.mdl", self.health);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// regular death
|
||||||
|
sound (self, CHAN_VOICE, "hknight/death1.wav", 1, ATTN_NORM);
|
||||||
|
if (random() > 0.5)
|
||||||
|
hknight_die1 ();
|
||||||
|
else
|
||||||
|
hknight_dieb1 ();
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
#ifdef 0
|
||||||
|
// Not used
|
||||||
|
void() hknight_magica1 =[ $magica1, hknight_magica2 ] {ai_face();};
|
||||||
|
void() hknight_magica2 =[ $magica2, hknight_magica3 ] {ai_face();};
|
||||||
|
void() hknight_magica3 =[ $magica3, hknight_magica4 ] {ai_face();};
|
||||||
|
void() hknight_magica4 =[ $magica4, hknight_magica5 ] {ai_face();};
|
||||||
|
void() hknight_magica5 =[ $magica5, hknight_magica6 ] {ai_face();};
|
||||||
|
void() hknight_magica6 =[ $magica6, hknight_magica7 ] {ai_face();};
|
||||||
|
void() hknight_magica7 =[ $magica7, hknight_magica8 ] {hknight_shot(-2);};
|
||||||
|
void() hknight_magica8 =[ $magica8, hknight_magica9 ] {hknight_shot(-1);};
|
||||||
|
void() hknight_magica9 =[ $magica9, hknight_magica10] {hknight_shot(0);};
|
||||||
|
void() hknight_magica10 =[ $magica10, hknight_magica11] {hknight_shot(1);};
|
||||||
|
void() hknight_magica11 =[ $magica11, hknight_magica12] {hknight_shot(2);};
|
||||||
|
void() hknight_magica12 =[ $magica12, hknight_magica13] {hknight_shot(3);};
|
||||||
|
void() hknight_magica13 =[ $magica13, hknight_magica14] {ai_face();};
|
||||||
|
void() hknight_magica14 =[ $magica14, hknight_run1 ] {ai_face();};
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
|
||||||
|
void() hknight_magicb1 =[ $magicb1, hknight_magicb2 ] {ai_face();};
|
||||||
|
void() hknight_magicb2 =[ $magicb2, hknight_magicb3 ] {ai_face();};
|
||||||
|
void() hknight_magicb3 =[ $magicb3, hknight_magicb4 ] {ai_face();};
|
||||||
|
void() hknight_magicb4 =[ $magicb4, hknight_magicb5 ] {ai_face();};
|
||||||
|
void() hknight_magicb5 =[ $magicb5, hknight_magicb6 ] {ai_face();};
|
||||||
|
void() hknight_magicb6 =[ $magicb6, hknight_magicb7 ] {ai_face();};
|
||||||
|
void() hknight_magicb7 =[ $magicb7, hknight_magicb8 ] {hknight_shot(-2);};
|
||||||
|
void() hknight_magicb8 =[ $magicb8, hknight_magicb9 ] {hknight_shot(-1);};
|
||||||
|
void() hknight_magicb9 =[ $magicb9, hknight_magicb10] {hknight_shot(0);};
|
||||||
|
void() hknight_magicb10 =[ $magicb10, hknight_magicb11] {hknight_shot(1);};
|
||||||
|
void() hknight_magicb11 =[ $magicb11, hknight_magicb12] {hknight_shot(2);};
|
||||||
|
void() hknight_magicb12 =[ $magicb12, hknight_magicb13] {hknight_shot(3);};
|
||||||
|
void() hknight_magicb13 =[ $magicb13, hknight_run1] {ai_face();};
|
||||||
|
#endif
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
|
||||||
|
void() hknight_magicc1 =[ $magicc1, hknight_magicc2 ] {ai_face();};
|
||||||
|
void() hknight_magicc2 =[ $magicc2, hknight_magicc3 ] {ai_face();};
|
||||||
|
void() hknight_magicc3 =[ $magicc3, hknight_magicc4 ] {ai_face();};
|
||||||
|
void() hknight_magicc4 =[ $magicc4, hknight_magicc5 ] {ai_face();};
|
||||||
|
void() hknight_magicc5 =[ $magicc5, hknight_magicc6 ] {ai_face();};
|
||||||
|
void() hknight_magicc6 =[ $magicc6, hknight_magicc7 ] {hknight_shot(-2);};
|
||||||
|
void() hknight_magicc7 =[ $magicc7, hknight_magicc8 ] {hknight_shot(-1);};
|
||||||
|
void() hknight_magicc8 =[ $magicc8, hknight_magicc9 ] {hknight_shot(0);};
|
||||||
|
void() hknight_magicc9 =[ $magicc9, hknight_magicc10] {hknight_shot(1);};
|
||||||
|
void() hknight_magicc10 =[ $magicc10, hknight_magicc11] {hknight_shot(2);};
|
||||||
|
void() hknight_magicc11 =[ $magicc11, hknight_run1] {hknight_shot(3);};
|
||||||
|
|
||||||
|
//===========================================================================
|
||||||
|
|
||||||
|
void() hknight_char_a1 =[ $char_a1, hknight_char_a2 ] {ai_charge(20);};
|
||||||
|
void() hknight_char_a2 =[ $char_a2, hknight_char_a3 ] {ai_charge(25);};
|
||||||
|
void() hknight_char_a3 =[ $char_a3, hknight_char_a4 ] {ai_charge(18);};
|
||||||
|
void() hknight_char_a4 =[ $char_a4, hknight_char_a5 ] {ai_charge(16);};
|
||||||
|
void() hknight_char_a5 =[ $char_a5, hknight_char_a6 ] {ai_charge(14);};
|
||||||
|
void() hknight_char_a6 =[ $char_a6, hknight_char_a7 ] {ai_charge(20); ai_melee(MOD_HKNIGHT);};
|
||||||
|
void() hknight_char_a7 =[ $char_a7, hknight_char_a8 ] {ai_charge(21); ai_melee(MOD_HKNIGHT);};
|
||||||
|
void() hknight_char_a8 =[ $char_a8, hknight_char_a9 ] {ai_charge(13); ai_melee(MOD_HKNIGHT);};
|
||||||
|
void() hknight_char_a9 =[ $char_a9, hknight_char_a10 ] {ai_charge(20); ai_melee(MOD_HKNIGHT);};
|
||||||
|
void() hknight_char_a10=[ $char_a10, hknight_char_a11 ] {ai_charge(20); ai_melee(MOD_HKNIGHT);};
|
||||||
|
void() hknight_char_a11=[ $char_a11, hknight_char_a12 ] {ai_charge(18); ai_melee(MOD_HKNIGHT);};
|
||||||
|
void() hknight_char_a12=[ $char_a12, hknight_char_a13 ] {ai_charge(16);};
|
||||||
|
void() hknight_char_a13=[ $char_a13, hknight_char_a14 ] {ai_charge(14);};
|
||||||
|
void() hknight_char_a14=[ $char_a14, hknight_char_a15 ] {ai_charge(25);};
|
||||||
|
void() hknight_char_a15=[ $char_a15, hknight_char_a16 ] {ai_charge(21);};
|
||||||
|
void() hknight_char_a16=[ $char_a16, hknight_run1 ] {ai_charge(13);};
|
||||||
|
|
||||||
|
//===========================================================================
|
||||||
|
|
||||||
|
#ifdef 0
|
||||||
|
// Not used
|
||||||
|
void() hknight_char_b1 =[ $char_b1, hknight_char_b2 ]
|
||||||
|
{CheckContinueCharge (); ai_charge(23); ai_melee(MOD_HKNIGHT);};
|
||||||
|
void() hknight_char_b2 =[ $char_b2, hknight_char_b3 ] {ai_charge(17); ai_melee(MOD_HKNIGHT);};
|
||||||
|
void() hknight_char_b3 =[ $char_b3, hknight_char_b4 ] {ai_charge(12); ai_melee(MOD_HKNIGHT);};
|
||||||
|
void() hknight_char_b4 =[ $char_b4, hknight_char_b5 ] {ai_charge(22); ai_melee(MOD_HKNIGHT);};
|
||||||
|
void() hknight_char_b5 =[ $char_b5, hknight_char_b6 ] {ai_charge(18); ai_melee(MOD_HKNIGHT);};
|
||||||
|
void() hknight_char_b6 =[ $char_b6, hknight_char_b1 ] {ai_charge(8); ai_melee(MOD_HKNIGHT);};
|
||||||
|
#endif
|
||||||
|
|
||||||
|
//===========================================================================
|
||||||
|
|
||||||
|
void() hknight_slice1 =[ $slice1, hknight_slice2 ] {ai_charge(9);};
|
||||||
|
void() hknight_slice2 =[ $slice2, hknight_slice3 ] {ai_charge(6);};
|
||||||
|
void() hknight_slice3 =[ $slice3, hknight_slice4 ] {ai_charge(13);};
|
||||||
|
void() hknight_slice4 =[ $slice4, hknight_slice5 ] {ai_charge(4);};
|
||||||
|
void() hknight_slice5 =[ $slice5, hknight_slice6 ] {ai_charge(7); ai_melee(MOD_HKNIGHT);};
|
||||||
|
void() hknight_slice6 =[ $slice6, hknight_slice7 ] {ai_charge(15); ai_melee(MOD_HKNIGHT);};
|
||||||
|
void() hknight_slice7 =[ $slice7, hknight_slice8 ] {ai_charge(8); ai_melee(MOD_HKNIGHT);};
|
||||||
|
void() hknight_slice8 =[ $slice8, hknight_slice9 ] {ai_charge(2); ai_melee(MOD_HKNIGHT);};
|
||||||
|
void() hknight_slice9 =[ $slice9, hknight_slice10 ] {ai_melee(MOD_HKNIGHT);};
|
||||||
|
void() hknight_slice10 =[ $slice10, hknight_run1 ] {ai_charge(3);};
|
||||||
|
|
||||||
|
//===========================================================================
|
||||||
|
|
||||||
|
void() hknight_smash1 =[ $smash1, hknight_smash2 ] {ai_charge(1);};
|
||||||
|
void() hknight_smash2 =[ $smash2, hknight_smash3 ] {ai_charge(13);};
|
||||||
|
void() hknight_smash3 =[ $smash3, hknight_smash4 ] {ai_charge(9);};
|
||||||
|
void() hknight_smash4 =[ $smash4, hknight_smash5 ] {ai_charge(11);};
|
||||||
|
void() hknight_smash5 =[ $smash5, hknight_smash6 ] {ai_charge(10); ai_melee(MOD_HKNIGHT);};
|
||||||
|
void() hknight_smash6 =[ $smash6, hknight_smash7 ] {ai_charge(7); ai_melee(MOD_HKNIGHT);};
|
||||||
|
void() hknight_smash7 =[ $smash7, hknight_smash8 ] {ai_charge(12); ai_melee(MOD_HKNIGHT);};
|
||||||
|
void() hknight_smash8 =[ $smash8, hknight_smash9 ] {ai_charge(2); ai_melee(MOD_HKNIGHT);};
|
||||||
|
void() hknight_smash9 =[ $smash9, hknight_smash10 ] {ai_charge(3); ai_melee(MOD_HKNIGHT);};
|
||||||
|
void() hknight_smash10 =[ $smash10, hknight_smash11 ] {ai_charge(0);};
|
||||||
|
void() hknight_smash11 =[ $smash11, hknight_run1 ] {ai_charge(0);};
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
|
||||||
|
void() hknight_watk1 =[ $w_attack1, hknight_watk2 ] {ai_charge(2);};
|
||||||
|
void() hknight_watk2 =[ $w_attack2, hknight_watk3 ] {ai_charge(0);};
|
||||||
|
void() hknight_watk3 =[ $w_attack3, hknight_watk4 ] {ai_charge(0);};
|
||||||
|
void() hknight_watk4 =[ $w_attack4, hknight_watk5 ] {ai_melee(MOD_HKNIGHT);};
|
||||||
|
void() hknight_watk5 =[ $w_attack5, hknight_watk6 ] {ai_melee(MOD_HKNIGHT);};
|
||||||
|
void() hknight_watk6 =[ $w_attack6, hknight_watk7 ] {ai_melee(MOD_HKNIGHT);};
|
||||||
|
void() hknight_watk7 =[ $w_attack7, hknight_watk8 ] {ai_charge(1);};
|
||||||
|
void() hknight_watk8 =[ $w_attack8, hknight_watk9 ] {ai_charge(4);};
|
||||||
|
void() hknight_watk9 =[ $w_attack9, hknight_watk10 ] {ai_charge(5);};
|
||||||
|
void() hknight_watk10 =[ $w_attack10, hknight_watk11 ] {ai_charge(3); ai_melee(MOD_HKNIGHT);};
|
||||||
|
void() hknight_watk11 =[ $w_attack11, hknight_watk12 ] {ai_charge(2); ai_melee(MOD_HKNIGHT);};
|
||||||
|
void() hknight_watk12 =[ $w_attack12, hknight_watk13 ] {ai_charge(2); ai_melee(MOD_HKNIGHT);};
|
||||||
|
void() hknight_watk13 =[ $w_attack13, hknight_watk14 ] {ai_charge(0);};
|
||||||
|
void() hknight_watk14 =[ $w_attack14, hknight_watk15 ] {ai_charge(0);};
|
||||||
|
void() hknight_watk15 =[ $w_attack15, hknight_watk16 ] {ai_charge(0);};
|
||||||
|
void() hknight_watk16 =[ $w_attack16, hknight_watk17 ] {ai_charge(1);};
|
||||||
|
void() hknight_watk17 =[ $w_attack17, hknight_watk18 ] {ai_charge(1); ai_melee(MOD_HKNIGHT);};
|
||||||
|
void() hknight_watk18 =[ $w_attack18, hknight_watk19 ] {ai_charge(3); ai_melee(MOD_HKNIGHT);};
|
||||||
|
void() hknight_watk19 =[ $w_attack19, hknight_watk20 ] {ai_charge(4); ai_melee(MOD_HKNIGHT);};
|
||||||
|
void() hknight_watk20 =[ $w_attack20, hknight_watk21 ] {ai_charge(6);};
|
||||||
|
void() hknight_watk21 =[ $w_attack21, hknight_watk22 ] {ai_charge(7);};
|
||||||
|
void() hknight_watk22 =[ $w_attack22, hknight_run1 ] {ai_charge(3);};
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
|
||||||
|
void() hk_idle_sound =
|
||||||
|
{
|
||||||
|
if (random() < 0.2)
|
||||||
|
sound (self, CHAN_VOICE, "hknight/idle.wav", 1, ATTN_NORM);
|
||||||
|
};
|
||||||
|
|
||||||
|
void(entity attacker, float damage) hknight_pain =
|
||||||
|
{
|
||||||
|
if (self.pain_finished > time)
|
||||||
|
return;
|
||||||
|
|
||||||
|
sound (self, CHAN_VOICE, "hknight/pain1.wav", 1, ATTN_NORM);
|
||||||
|
|
||||||
|
if (time - self.pain_finished > 5)
|
||||||
|
{ // allways go into pain frame if it has been a while
|
||||||
|
hknight_pain1 ();
|
||||||
|
self.pain_finished = time + 1;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if ((random()*30 > damage) )
|
||||||
|
return; // didn't flinch
|
||||||
|
|
||||||
|
self.pain_finished = time + 1;
|
||||||
|
hknight_pain1 ();
|
||||||
|
};
|
||||||
|
|
||||||
|
void() hknight_melee =
|
||||||
|
{
|
||||||
|
self.hknightattack += 1;
|
||||||
|
|
||||||
|
sound (self, CHAN_WEAPON, "hknight/slash1.wav", 1, ATTN_NORM);
|
||||||
|
switch (self.hknightattack)
|
||||||
|
{
|
||||||
|
case 1:
|
||||||
|
hknight_slice1 ();
|
||||||
|
break;
|
||||||
|
case 2:
|
||||||
|
hknight_smash1 ();
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
hknight_watk1 ();
|
||||||
|
self.hknightattack = 0;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
/*QUAKED monster_hell_knight (1 0 0) (-16 -16 -24) (16 16 40) Ambush
|
||||||
|
*/
|
||||||
|
void() monster_hell_knight =
|
||||||
|
{
|
||||||
|
if (deathmatch)
|
||||||
|
{
|
||||||
|
remove(self);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
precache_model2 ("progs/hknight.mdl");
|
||||||
|
precache_model2 ("progs/k_spike.mdl");
|
||||||
|
precache_model2 ("progs/h_hellkn.mdl");
|
||||||
|
|
||||||
|
precache_sound2 ("hknight/attack1.wav");
|
||||||
|
precache_sound2 ("hknight/death1.wav");
|
||||||
|
precache_sound2 ("hknight/pain1.wav");
|
||||||
|
precache_sound2 ("hknight/sight1.wav");
|
||||||
|
precache_sound ("hknight/hit.wav"); // used by C code, so don't sound2
|
||||||
|
precache_sound2 ("hknight/slash1.wav");
|
||||||
|
precache_sound2 ("hknight/idle.wav");
|
||||||
|
precache_sound2 ("hknight/grunt.wav");
|
||||||
|
|
||||||
|
precache_sound ("knight/sword1.wav");
|
||||||
|
precache_sound ("knight/sword2.wav");
|
||||||
|
|
||||||
|
self.solid = SOLID_SLIDEBOX;
|
||||||
|
self.movetype = MOVETYPE_STEP;
|
||||||
|
|
||||||
|
setmodel (self, "progs/hknight.mdl");
|
||||||
|
|
||||||
|
setsize (self, '-16 -16 -24', '16 16 40');
|
||||||
|
self.health = 250;
|
||||||
|
|
||||||
|
self.th_stand = hknight_stand1;
|
||||||
|
self.th_walk = hknight_walk1;
|
||||||
|
self.th_run = hknight_run1;
|
||||||
|
self.th_melee = hknight_melee;
|
||||||
|
self.th_missile = hknight_magicc1;
|
||||||
|
self.th_pain = hknight_pain;
|
||||||
|
self.th_die = hknight_die;
|
||||||
|
|
||||||
|
self.hknightattack = floor(random() * 2.99);
|
||||||
|
|
||||||
|
walkmonster_start ();
|
||||||
|
};
|
278
quakec/basemod/knight.qc
Normal file
278
quakec/basemod/knight.qc
Normal file
|
@ -0,0 +1,278 @@
|
||||||
|
/*
|
||||||
|
==============================================================================
|
||||||
|
|
||||||
|
KNIGHT
|
||||||
|
|
||||||
|
==============================================================================
|
||||||
|
*/
|
||||||
|
|
||||||
|
$cd id1/models/knight
|
||||||
|
$origin 0 0 24
|
||||||
|
$base base
|
||||||
|
$skin badass3
|
||||||
|
|
||||||
|
$frame stand1 stand2 stand3 stand4 stand5 stand6 stand7 stand8 stand9
|
||||||
|
|
||||||
|
$frame runb1 runb2 runb3 runb4 runb5 runb6 runb7 runb8
|
||||||
|
|
||||||
|
//frame runc1 runc2 runc3 runc4 runc5 runc6
|
||||||
|
|
||||||
|
$frame runattack1 runattack2 runattack3 runattack4 runattack5
|
||||||
|
$frame runattack6 runattack7 runattack8 runattack9 runattack10
|
||||||
|
$frame runattack11
|
||||||
|
|
||||||
|
$frame pain1 pain2 pain3
|
||||||
|
|
||||||
|
$frame painb1 painb2 painb3 painb4 painb5 painb6 painb7 painb8 painb9
|
||||||
|
$frame painb10 painb11
|
||||||
|
|
||||||
|
//frame attack1 attack2 attack3 attack4 attack5 attack6 attack7
|
||||||
|
//frame attack8 attack9 attack10 attack11
|
||||||
|
|
||||||
|
$frame attackb0 attackb1 attackb2 attackb3 attackb4 attackb5
|
||||||
|
$frame attackb6 attackb7 attackb8 attackb9 attackb10
|
||||||
|
|
||||||
|
$frame walk1 walk2 walk3 walk4 walk5 walk6 walk7 walk8 walk9
|
||||||
|
$frame walk10 walk11 walk12 walk13 walk14
|
||||||
|
|
||||||
|
$frame kneel1 kneel2 kneel3 kneel4 kneel5
|
||||||
|
|
||||||
|
$frame standing2 standing3 standing4 standing5
|
||||||
|
|
||||||
|
$frame death1 death2 death3 death4 death5 death6 death7 death8
|
||||||
|
$frame death9 death10
|
||||||
|
|
||||||
|
$frame deathb1 deathb2 deathb3 deathb4 deathb5 deathb6 deathb7 deathb8
|
||||||
|
$frame deathb9 deathb10 deathb11
|
||||||
|
|
||||||
|
void() knight_stand1 =[ $stand1, knight_stand2 ] {ai_stand();};
|
||||||
|
void() knight_stand2 =[ $stand2, knight_stand3 ] {ai_stand();};
|
||||||
|
void() knight_stand3 =[ $stand3, knight_stand4 ] {ai_stand();};
|
||||||
|
void() knight_stand4 =[ $stand4, knight_stand5 ] {ai_stand();};
|
||||||
|
void() knight_stand5 =[ $stand5, knight_stand6 ] {ai_stand();};
|
||||||
|
void() knight_stand6 =[ $stand6, knight_stand7 ] {ai_stand();};
|
||||||
|
void() knight_stand7 =[ $stand7, knight_stand8 ] {ai_stand();};
|
||||||
|
void() knight_stand8 =[ $stand8, knight_stand9 ] {ai_stand();};
|
||||||
|
void() knight_stand9 =[ $stand9, knight_stand1 ] {ai_stand();};
|
||||||
|
|
||||||
|
void() knight_walk1 =[ $walk1, knight_walk2 ] {
|
||||||
|
if (random() < 0.2)
|
||||||
|
sound (self, CHAN_VOICE, "knight/idle.wav", 1, ATTN_IDLE);
|
||||||
|
ai_walk(3);};
|
||||||
|
void() knight_walk2 =[ $walk2, knight_walk3 ] {ai_walk(2);};
|
||||||
|
void() knight_walk3 =[ $walk3, knight_walk4 ] {ai_walk(3);};
|
||||||
|
void() knight_walk4 =[ $walk4, knight_walk5 ] {ai_walk(4);};
|
||||||
|
void() knight_walk5 =[ $walk5, knight_walk6 ] {ai_walk(3);};
|
||||||
|
void() knight_walk6 =[ $walk6, knight_walk7 ] {ai_walk(3);};
|
||||||
|
void() knight_walk7 =[ $walk7, knight_walk8 ] {ai_walk(3);};
|
||||||
|
void() knight_walk8 =[ $walk8, knight_walk9 ] {ai_walk(4);};
|
||||||
|
void() knight_walk9 =[ $walk9, knight_walk10 ] {ai_walk(3);};
|
||||||
|
void() knight_walk10 =[ $walk10, knight_walk11 ] {ai_walk(3);};
|
||||||
|
void() knight_walk11 =[ $walk11, knight_walk12 ] {ai_walk(2);};
|
||||||
|
void() knight_walk12 =[ $walk12, knight_walk13 ] {ai_walk(3);};
|
||||||
|
void() knight_walk13 =[ $walk13, knight_walk14 ] {ai_walk(4);};
|
||||||
|
void() knight_walk14 =[ $walk14, knight_walk1 ] {ai_walk(3);};
|
||||||
|
|
||||||
|
|
||||||
|
void() knight_run1 =[ $runb1, knight_run2 ] {
|
||||||
|
if (random() < 0.2)
|
||||||
|
sound (self, CHAN_VOICE, "knight/idle.wav", 1, ATTN_IDLE);
|
||||||
|
ai_run(16);};
|
||||||
|
void() knight_run2 =[ $runb2, knight_run3 ] {ai_run(20);};
|
||||||
|
void() knight_run3 =[ $runb3, knight_run4 ] {ai_run(13);};
|
||||||
|
void() knight_run4 =[ $runb4, knight_run5 ] {ai_run(7);};
|
||||||
|
void() knight_run5 =[ $runb5, knight_run6 ] {ai_run(16);};
|
||||||
|
void() knight_run6 =[ $runb6, knight_run7 ] {ai_run(20);};
|
||||||
|
void() knight_run7 =[ $runb7, knight_run8 ] {ai_run(14);};
|
||||||
|
void() knight_run8 =[ $runb8, knight_run1 ] {ai_run(6);};
|
||||||
|
|
||||||
|
|
||||||
|
void() knight_runatk1 =[ $runattack1, knight_runatk2 ]
|
||||||
|
{
|
||||||
|
if (random() > 0.5)
|
||||||
|
sound (self, CHAN_WEAPON, "knight/sword2.wav", 1, ATTN_NORM);
|
||||||
|
else
|
||||||
|
sound (self, CHAN_WEAPON, "knight/sword1.wav", 1, ATTN_NORM);
|
||||||
|
ai_charge(20);
|
||||||
|
};
|
||||||
|
void() knight_runatk2 =[ $runattack2, knight_runatk3 ] {ai_charge_side();};
|
||||||
|
void() knight_runatk3 =[ $runattack3, knight_runatk4 ] {ai_charge_side();};
|
||||||
|
void() knight_runatk4 =[ $runattack4, knight_runatk5 ] {ai_charge_side();};
|
||||||
|
void() knight_runatk5 =[ $runattack5, knight_runatk6 ] {ai_melee_side(MOD_KNIGHT);};
|
||||||
|
void() knight_runatk6 =[ $runattack6, knight_runatk7 ] {ai_melee_side(MOD_KNIGHT);};
|
||||||
|
void() knight_runatk7 =[ $runattack7, knight_runatk8 ] {ai_melee_side(MOD_KNIGHT);};
|
||||||
|
void() knight_runatk8 =[ $runattack8, knight_runatk9 ] {ai_melee_side(MOD_KNIGHT);};
|
||||||
|
void() knight_runatk9 =[ $runattack9, knight_runatk10 ] {ai_melee_side(MOD_KNIGHT);};
|
||||||
|
void() knight_runatk10 =[ $runattack10, knight_runatk11 ] {ai_charge_side();};
|
||||||
|
void() knight_runatk11 =[ $runattack11, knight_run1 ] {ai_charge(10);};
|
||||||
|
|
||||||
|
void() knight_atk1 =[ $attackb1, knight_atk2 ]
|
||||||
|
{
|
||||||
|
sound (self, CHAN_WEAPON, "knight/sword1.wav", 1, ATTN_NORM);
|
||||||
|
ai_charge(0);};
|
||||||
|
void() knight_atk2 =[ $attackb2, knight_atk3 ] {ai_charge(7);};
|
||||||
|
void() knight_atk3 =[ $attackb3, knight_atk4 ] {ai_charge(4);};
|
||||||
|
void() knight_atk4 =[ $attackb4, knight_atk5 ] {ai_charge(0);};
|
||||||
|
void() knight_atk5 =[ $attackb5, knight_atk6 ] {ai_charge(3);};
|
||||||
|
void() knight_atk6 =[ $attackb6, knight_atk7 ] {ai_charge(4); ai_melee(MOD_KNIGHT);};
|
||||||
|
void() knight_atk7 =[ $attackb7, knight_atk8 ] {ai_charge(1); ai_melee(MOD_KNIGHT);};
|
||||||
|
void() knight_atk8 =[ $attackb8, knight_atk9 ] {ai_charge(3); ai_melee(MOD_KNIGHT);};
|
||||||
|
void() knight_atk9 =[ $attackb9, knight_atk10] {ai_charge(1);};
|
||||||
|
void() knight_atk10=[ $attackb10, knight_run1 ] {ai_charge(5);};
|
||||||
|
|
||||||
|
//void() knight_atk9 =[ $attack9, knight_atk10 ] {};
|
||||||
|
//void() knight_atk10 =[ $attack10, knight_atk11 ] {};
|
||||||
|
//void() knight_atk11 =[ $attack11, knight_run1 ] {};
|
||||||
|
|
||||||
|
//===========================================================================
|
||||||
|
|
||||||
|
void() knight_pain1 =[ $pain1, knight_pain2 ] {};
|
||||||
|
void() knight_pain2 =[ $pain2, knight_pain3 ] {};
|
||||||
|
void() knight_pain3 =[ $pain3, knight_run1 ] {};
|
||||||
|
|
||||||
|
void() knight_painb1 =[ $painb1, knight_painb2 ] {ai_painforward(0);};
|
||||||
|
void() knight_painb2 =[ $painb2, knight_painb3 ] {ai_painforward(3);};
|
||||||
|
void() knight_painb3 =[ $painb3, knight_painb4 ] {};
|
||||||
|
void() knight_painb4 =[ $painb4, knight_painb5 ] {};
|
||||||
|
void() knight_painb5 =[ $painb5, knight_painb6 ] {ai_painforward(2);};
|
||||||
|
void() knight_painb6 =[ $painb6, knight_painb7 ] {ai_painforward(4);};
|
||||||
|
void() knight_painb7 =[ $painb7, knight_painb8 ] {ai_painforward(2);};
|
||||||
|
void() knight_painb8 =[ $painb8, knight_painb9 ] {ai_painforward(5);};
|
||||||
|
void() knight_painb9 =[ $painb9, knight_painb10 ] {ai_painforward(5);};
|
||||||
|
void() knight_painb10 =[ $painb10, knight_painb11 ] {ai_painforward(0);};
|
||||||
|
void() knight_painb11 =[ $painb11, knight_run1 ] {};
|
||||||
|
|
||||||
|
void(entity attacker, float damage) knight_pain =
|
||||||
|
{
|
||||||
|
local float r;
|
||||||
|
|
||||||
|
if (self.pain_finished > time)
|
||||||
|
return;
|
||||||
|
|
||||||
|
r = random();
|
||||||
|
|
||||||
|
sound (self, CHAN_VOICE, "knight/khurt.wav", 1, ATTN_NORM);
|
||||||
|
self.pain_finished = time + 1;
|
||||||
|
|
||||||
|
if (r < 0.85)
|
||||||
|
knight_pain1 ();
|
||||||
|
else
|
||||||
|
knight_painb1 ();
|
||||||
|
|
||||||
|
};
|
||||||
|
|
||||||
|
//===========================================================================
|
||||||
|
|
||||||
|
#ifdef 0
|
||||||
|
// Not used
|
||||||
|
void() knight_bow1 =[ $kneel1, knight_bow2 ] {ai_turn();};
|
||||||
|
void() knight_bow2 =[ $kneel2, knight_bow3 ] {ai_turn();};
|
||||||
|
void() knight_bow3 =[ $kneel3, knight_bow4 ] {ai_turn();};
|
||||||
|
void() knight_bow4 =[ $kneel4, knight_bow5 ] {ai_turn();};
|
||||||
|
|
||||||
|
void() knight_bow5 =[ $kneel5, knight_bow5 ] {ai_turn();};
|
||||||
|
|
||||||
|
void() knight_bow6 =[ $kneel4, knight_bow7 ] {ai_turn();};
|
||||||
|
void() knight_bow7 =[ $kneel3, knight_bow8 ] {ai_turn();};
|
||||||
|
void() knight_bow8 =[ $kneel2, knight_bow9 ] {ai_turn();};
|
||||||
|
void() knight_bow9 =[ $kneel1, knight_bow10 ] {ai_turn();};
|
||||||
|
void() knight_bow10 =[ $walk1, knight_walk1 ] {ai_turn();};
|
||||||
|
#endif
|
||||||
|
|
||||||
|
void() knight_die1 =[ $death1, knight_die2 ] {};
|
||||||
|
void() knight_die2 =[ $death2, knight_die3 ] {};
|
||||||
|
void() knight_die3 =[ $death3, knight_die4 ]
|
||||||
|
{self.solid = SOLID_NOT;};
|
||||||
|
void() knight_die4 =[ $death4, knight_die5 ] {};
|
||||||
|
void() knight_die5 =[ $death5, knight_die6 ] {};
|
||||||
|
void() knight_die6 =[ $death6, knight_die7 ] {};
|
||||||
|
void() knight_die7 =[ $death7, knight_die8 ] {};
|
||||||
|
void() knight_die8 =[ $death8, knight_die9 ] {};
|
||||||
|
void() knight_die9 =[ $death9, knight_die10] {};
|
||||||
|
void() knight_die10=[ $death10, knight_die10] {};
|
||||||
|
|
||||||
|
|
||||||
|
void() knight_dieb1 =[ $deathb1, knight_dieb2 ] {};
|
||||||
|
void() knight_dieb2 =[ $deathb2, knight_dieb3 ] {};
|
||||||
|
void() knight_dieb3 =[ $deathb3, knight_dieb4 ]
|
||||||
|
{self.solid = SOLID_NOT;};
|
||||||
|
void() knight_dieb4 =[ $deathb4, knight_dieb5 ] {};
|
||||||
|
void() knight_dieb5 =[ $deathb5, knight_dieb6 ] {};
|
||||||
|
void() knight_dieb6 =[ $deathb6, knight_dieb7 ] {};
|
||||||
|
void() knight_dieb7 =[ $deathb7, knight_dieb8 ] {};
|
||||||
|
void() knight_dieb8 =[ $deathb8, knight_dieb9 ] {};
|
||||||
|
void() knight_dieb9 =[ $deathb9, knight_dieb10] {};
|
||||||
|
void() knight_dieb10 = [ $deathb10, knight_dieb11] {};
|
||||||
|
void() knight_dieb11 = [ $deathb11, knight_dieb11] {};
|
||||||
|
|
||||||
|
|
||||||
|
void() knight_die =
|
||||||
|
{
|
||||||
|
// check for gib
|
||||||
|
if (self.health < -40)
|
||||||
|
{
|
||||||
|
sound (self, CHAN_VOICE, "player/udeath.wav", 1, ATTN_NORM);
|
||||||
|
ThrowHead ("progs/h_knight.mdl", self.health);
|
||||||
|
ThrowGib ("progs/gib1.mdl", self.health);
|
||||||
|
ThrowGib ("progs/gib2.mdl", self.health);
|
||||||
|
ThrowGib ("progs/gib3.mdl", self.health);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// regular death
|
||||||
|
sound (self, CHAN_VOICE, "knight/kdeath.wav", 1, ATTN_NORM);
|
||||||
|
if (random() < 0.5)
|
||||||
|
knight_die1 ();
|
||||||
|
else
|
||||||
|
knight_dieb1 ();
|
||||||
|
};
|
||||||
|
|
||||||
|
void() knight_attack =
|
||||||
|
{
|
||||||
|
local float len;
|
||||||
|
|
||||||
|
// decide if now is a good swing time
|
||||||
|
len = vlen(self.enemy.origin+self.enemy.view_ofs - (self.origin+self.view_ofs));
|
||||||
|
|
||||||
|
if (len<80)
|
||||||
|
knight_atk1 ();
|
||||||
|
else
|
||||||
|
knight_runatk1 ();
|
||||||
|
};
|
||||||
|
|
||||||
|
/*QUAKED monster_knight (1 0 0) (-16 -16 -24) (16 16 40) Ambush
|
||||||
|
*/
|
||||||
|
void() monster_knight =
|
||||||
|
{
|
||||||
|
if (deathmatch)
|
||||||
|
{
|
||||||
|
remove(self);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
precache_model ("progs/knight.mdl");
|
||||||
|
precache_model ("progs/h_knight.mdl");
|
||||||
|
|
||||||
|
precache_sound ("knight/kdeath.wav");
|
||||||
|
precache_sound ("knight/khurt.wav");
|
||||||
|
precache_sound ("knight/ksight.wav");
|
||||||
|
precache_sound ("knight/sword1.wav");
|
||||||
|
precache_sound ("knight/sword2.wav");
|
||||||
|
precache_sound ("knight/idle.wav");
|
||||||
|
|
||||||
|
self.solid = SOLID_SLIDEBOX;
|
||||||
|
self.movetype = MOVETYPE_STEP;
|
||||||
|
|
||||||
|
setmodel (self, "progs/knight.mdl");
|
||||||
|
|
||||||
|
setsize (self, '-16 -16 -24', '16 16 40');
|
||||||
|
self.health = 75;
|
||||||
|
|
||||||
|
self.th_stand = knight_stand1;
|
||||||
|
self.th_walk = knight_walk1;
|
||||||
|
self.th_run = knight_run1;
|
||||||
|
self.th_melee = knight_attack;
|
||||||
|
self.th_pain = knight_pain;
|
||||||
|
self.th_die = knight_die;
|
||||||
|
|
||||||
|
walkmonster_start ();
|
||||||
|
};
|
|
@ -2,7 +2,7 @@
|
||||||
/*QUAKED info_null (0 0.5 0) (-4 -4 -4) (4 4 4)
|
/*QUAKED info_null (0 0.5 0) (-4 -4 -4) (4 4 4)
|
||||||
Used as a positional target for spotlights, etc.
|
Used as a positional target for spotlights, etc.
|
||||||
*/
|
*/
|
||||||
void() info_null = SUB_Remove;
|
var void() info_null = SUB_Remove;
|
||||||
|
|
||||||
/*QUAKED info_notnull (0 0.5 0) (-4 -4 -4) (4 4 4)
|
/*QUAKED info_notnull (0 0.5 0) (-4 -4 -4) (4 4 4)
|
||||||
Used as a positional target for lightning.
|
Used as a positional target for lightning.
|
||||||
|
@ -361,7 +361,7 @@ void() trap_shooter =
|
||||||
|
|
||||||
if (self.wait == 0)
|
if (self.wait == 0)
|
||||||
self.wait = 1;
|
self.wait = 1;
|
||||||
self.nextthink = self.nextthink + self.wait + self.ltime;
|
self.nextthink = time + self.wait;
|
||||||
self.think = shooter_think;
|
self.think = shooter_think;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
217
quakec/basemod/monsters.qc
Normal file
217
quakec/basemod/monsters.qc
Normal file
|
@ -0,0 +1,217 @@
|
||||||
|
/* ALL MONSTERS SHOULD BE 1 0 0 IN COLOR */
|
||||||
|
|
||||||
|
/*
|
||||||
|
================
|
||||||
|
monster_use
|
||||||
|
|
||||||
|
Using a monster makes it angry at the current activator
|
||||||
|
================
|
||||||
|
*/
|
||||||
|
void() monster_use =
|
||||||
|
{
|
||||||
|
if (self.enemy)
|
||||||
|
return;
|
||||||
|
if (self.health <= 0)
|
||||||
|
return;
|
||||||
|
if (activator.items & IT_INVISIBILITY)
|
||||||
|
return;
|
||||||
|
if (activator.flags & FL_NOTARGET)
|
||||||
|
return;
|
||||||
|
if (activator.flags & FL_CLIENT)
|
||||||
|
return;
|
||||||
|
|
||||||
|
// delay reaction so if the monster is teleported, its sound is still
|
||||||
|
// heard
|
||||||
|
self.enemy = activator;
|
||||||
|
self.nextthink = time + 0.1;
|
||||||
|
self.think = FoundTarget;
|
||||||
|
};
|
||||||
|
|
||||||
|
/*
|
||||||
|
================
|
||||||
|
monster_death_use
|
||||||
|
|
||||||
|
When a mosnter dies, it fires all of its targets with the current
|
||||||
|
enemy as activator.
|
||||||
|
================
|
||||||
|
*/
|
||||||
|
void() monster_death_use =
|
||||||
|
{
|
||||||
|
// fall to ground
|
||||||
|
if (self.flags & FL_FLY)
|
||||||
|
self.flags = self.flags - FL_FLY;
|
||||||
|
if (self.flags & FL_SWIM)
|
||||||
|
self.flags = self.flags - FL_SWIM;
|
||||||
|
|
||||||
|
if (!self.target)
|
||||||
|
return;
|
||||||
|
|
||||||
|
activator = self.enemy;
|
||||||
|
SUB_UseTargets ();
|
||||||
|
};
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
|
||||||
|
void() walkmonster_start_go =
|
||||||
|
{
|
||||||
|
self.origin_z = self.origin_z + 1; // raise off floor a bit
|
||||||
|
droptofloor();
|
||||||
|
|
||||||
|
if (!walkmove(0,0))
|
||||||
|
{
|
||||||
|
dprint ("walkmonster in wall at: ");
|
||||||
|
dprint (vtos(self.origin));
|
||||||
|
dprint ("\n");
|
||||||
|
}
|
||||||
|
|
||||||
|
self.takedamage = DAMAGE_AIM;
|
||||||
|
|
||||||
|
self.ideal_yaw = self.angles * '0 1 0';
|
||||||
|
if (!self.yaw_speed)
|
||||||
|
self.yaw_speed = 20;
|
||||||
|
self.view_ofs = '0 0 25';
|
||||||
|
self.use = monster_use;
|
||||||
|
|
||||||
|
self.flags = self.flags | FL_MONSTER;
|
||||||
|
|
||||||
|
if (self.target)
|
||||||
|
{
|
||||||
|
self.goalentity = self.movetarget = find(world, targetname, self.target);
|
||||||
|
self.ideal_yaw = vectoyaw(self.goalentity.origin - self.origin);
|
||||||
|
if (!self.movetarget)
|
||||||
|
{
|
||||||
|
dprint ("Monster can't find target at ");
|
||||||
|
dprint (vtos(self.origin));
|
||||||
|
dprint ("\n");
|
||||||
|
}
|
||||||
|
// this used to be an objerror
|
||||||
|
if (self.movetarget.classname == "path_corner")
|
||||||
|
self.th_walk ();
|
||||||
|
else
|
||||||
|
self.pausetime = 99999999;
|
||||||
|
self.th_stand ();
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
self.pausetime = 99999999;
|
||||||
|
self.th_stand ();
|
||||||
|
}
|
||||||
|
|
||||||
|
// spread think times so they don't all happen at same time
|
||||||
|
self.nextthink = time + 0.1 + random()*0.5;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
void() walkmonster_start =
|
||||||
|
{
|
||||||
|
// delay drop to floor to make sure all doors have been spawned
|
||||||
|
// spread think times so they don't all happen at same time
|
||||||
|
self.nextthink = time + 0.1 + random()*0.5;
|
||||||
|
self.think = walkmonster_start_go;
|
||||||
|
total_monsters = total_monsters + 1;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
void() flymonster_start_go =
|
||||||
|
{
|
||||||
|
self.takedamage = DAMAGE_AIM;
|
||||||
|
|
||||||
|
self.ideal_yaw = self.angles * '0 1 0';
|
||||||
|
if (!self.yaw_speed)
|
||||||
|
self.yaw_speed = 10;
|
||||||
|
self.view_ofs = '0 0 25';
|
||||||
|
self.use = monster_use;
|
||||||
|
|
||||||
|
self.flags = self.flags | FL_FLY | FL_MONSTER;
|
||||||
|
|
||||||
|
if (!walkmove(0,0))
|
||||||
|
{
|
||||||
|
dprint ("flymonster in wall at: ");
|
||||||
|
dprint (vtos(self.origin));
|
||||||
|
dprint ("\n");
|
||||||
|
}
|
||||||
|
|
||||||
|
if (self.target)
|
||||||
|
{
|
||||||
|
self.goalentity = self.movetarget = find(world, targetname, self.target);
|
||||||
|
if (!self.movetarget)
|
||||||
|
{
|
||||||
|
dprint ("Monster can't find target at ");
|
||||||
|
dprint (vtos(self.origin));
|
||||||
|
dprint ("\n");
|
||||||
|
}
|
||||||
|
// this used to be an objerror
|
||||||
|
if (self.movetarget.classname == "path_corner")
|
||||||
|
self.th_walk ();
|
||||||
|
else
|
||||||
|
self.pausetime = 99999999;
|
||||||
|
self.th_stand ();
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
self.pausetime = 99999999;
|
||||||
|
self.th_stand ();
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
void() flymonster_start =
|
||||||
|
{
|
||||||
|
// spread think times so they don't all happen at same time
|
||||||
|
self.nextthink = time + 0.1 + random()*0.5;
|
||||||
|
self.think = flymonster_start_go;
|
||||||
|
total_monsters = total_monsters + 1;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
void() swimmonster_start_go =
|
||||||
|
{
|
||||||
|
if (deathmatch)
|
||||||
|
{
|
||||||
|
remove(self);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
self.takedamage = DAMAGE_AIM;
|
||||||
|
// total_monsters = total_monsters + 1;
|
||||||
|
|
||||||
|
self.ideal_yaw = self.angles * '0 1 0';
|
||||||
|
if (!self.yaw_speed)
|
||||||
|
self.yaw_speed = 10;
|
||||||
|
self.view_ofs = '0 0 10';
|
||||||
|
self.use = monster_use;
|
||||||
|
|
||||||
|
self.flags = self.flags | FL_SWIM | FL_MONSTER;
|
||||||
|
|
||||||
|
if (self.target)
|
||||||
|
{
|
||||||
|
self.goalentity = self.movetarget = find(world, targetname, self.target);
|
||||||
|
if (!self.movetarget)
|
||||||
|
{
|
||||||
|
dprint ("Monster can't find target at ");
|
||||||
|
dprint (vtos(self.origin));
|
||||||
|
dprint ("\n");
|
||||||
|
}
|
||||||
|
// this used to be an objerror
|
||||||
|
self.ideal_yaw = vectoyaw(self.goalentity.origin - self.origin);
|
||||||
|
self.th_walk ();
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
self.pausetime = 99999999;
|
||||||
|
self.th_stand ();
|
||||||
|
}
|
||||||
|
|
||||||
|
// spread think times so they don't all happen at same time
|
||||||
|
self.nextthink = time + 0.1 + random()*0.5;
|
||||||
|
};
|
||||||
|
|
||||||
|
void() swimmonster_start =
|
||||||
|
{
|
||||||
|
// spread think times so they don't all happen at same time
|
||||||
|
self.nextthink = time + 0.1 + random()*0.5;
|
||||||
|
self.think = swimmonster_start_go;
|
||||||
|
total_monsters = total_monsters + 1;
|
||||||
|
};
|
||||||
|
|
||||||
|
|
|
@ -25,7 +25,21 @@ enum {
|
||||||
MOD_EXIT,
|
MOD_EXIT,
|
||||||
MOD_LASER,
|
MOD_LASER,
|
||||||
MOD_SELFWATER,
|
MOD_SELFWATER,
|
||||||
MOD_HURT
|
MOD_HURT,
|
||||||
|
MOD_DOG,
|
||||||
|
MOD_SOLDIER,
|
||||||
|
MOD_ENFORCER,
|
||||||
|
MOD_OGRE,
|
||||||
|
MOD_WIZARD,
|
||||||
|
MOD_DEMON,
|
||||||
|
MOD_KNIGHT,
|
||||||
|
MOD_HKNIGHT,
|
||||||
|
MOD_SHALRATH,
|
||||||
|
MOD_SHAMBLER,
|
||||||
|
MOD_FISH,
|
||||||
|
MOD_TARBABY,
|
||||||
|
MOD_ZOMBIE,
|
||||||
|
MOD_CHTHON
|
||||||
};
|
};
|
||||||
|
|
||||||
void(string targ, INTEGER mod) SuicideMessage =
|
void(string targ, INTEGER mod) SuicideMessage =
|
||||||
|
@ -278,6 +292,64 @@ void(string targ, INTEGER mod) WorldKillMessage =
|
||||||
s = targ;
|
s = targ;
|
||||||
t = " was zapped";
|
t = " was zapped";
|
||||||
break;
|
break;
|
||||||
|
#ifdef MONSTERS
|
||||||
|
case MOD_DOG:
|
||||||
|
s = targ;
|
||||||
|
t = " was mauled by a Rottweiler";
|
||||||
|
break;
|
||||||
|
case MOD_SOLDIER:
|
||||||
|
s = targ;
|
||||||
|
t = " was shot by a Grunt";
|
||||||
|
break;
|
||||||
|
case MOD_ENFORCER:
|
||||||
|
s = targ;
|
||||||
|
t = " was blasted by an Enforcer";
|
||||||
|
break;
|
||||||
|
case MOD_OGRE:
|
||||||
|
s = targ;
|
||||||
|
t = " was destroyed by an Ogre";
|
||||||
|
break;
|
||||||
|
case MOD_WIZARD:
|
||||||
|
s = targ;
|
||||||
|
t = " was scragged by a Scrag";
|
||||||
|
break;
|
||||||
|
case MOD_DEMON:
|
||||||
|
s = targ;
|
||||||
|
t = " was eviscerated by a Fiend";
|
||||||
|
break;
|
||||||
|
case MOD_KNIGHT:
|
||||||
|
s = targ;
|
||||||
|
t = " was slashed by a Knight";
|
||||||
|
break;
|
||||||
|
case MOD_HKNIGHT:
|
||||||
|
s = targ;
|
||||||
|
t = " was slain by a Death Knight";
|
||||||
|
break;
|
||||||
|
case MOD_SHALRATH:
|
||||||
|
s = targ;
|
||||||
|
t = " was exploded by a Vore";
|
||||||
|
break;
|
||||||
|
case MOD_SHAMBLER:
|
||||||
|
s = targ;
|
||||||
|
t = " was smashed by a Shambler";
|
||||||
|
break;
|
||||||
|
case MOD_FISH:
|
||||||
|
s = targ;
|
||||||
|
t = " was fed to the Rotfish";
|
||||||
|
break;
|
||||||
|
case MOD_TARBABY:
|
||||||
|
s = targ;
|
||||||
|
t = " was slimed by a Spawn";
|
||||||
|
break;
|
||||||
|
case MOD_ZOMBIE:
|
||||||
|
s = targ;
|
||||||
|
t = " joins the Zombies";
|
||||||
|
break;
|
||||||
|
case MOD_CHTHON:
|
||||||
|
s = targ;
|
||||||
|
t = " fell to Chthon's wrath";
|
||||||
|
break;
|
||||||
|
#endif
|
||||||
default:
|
default:
|
||||||
s = targ;
|
s = targ;
|
||||||
t = " died";
|
t = " died";
|
||||||
|
|
407
quakec/basemod/ogre.qc
Normal file
407
quakec/basemod/ogre.qc
Normal file
|
@ -0,0 +1,407 @@
|
||||||
|
/*
|
||||||
|
==============================================================================
|
||||||
|
|
||||||
|
OGRE
|
||||||
|
|
||||||
|
==============================================================================
|
||||||
|
*/
|
||||||
|
|
||||||
|
$cd id1/models/ogre_c
|
||||||
|
$origin 0 0 24
|
||||||
|
$base base
|
||||||
|
$skin base
|
||||||
|
|
||||||
|
$frame stand1 stand2 stand3 stand4 stand5 stand6 stand7 stand8 stand9
|
||||||
|
|
||||||
|
$frame walk1 walk2 walk3 walk4 walk5 walk6 walk7
|
||||||
|
$frame walk8 walk9 walk10 walk11 walk12 walk13 walk14 walk15 walk16
|
||||||
|
|
||||||
|
$frame run1 run2 run3 run4 run5 run6 run7 run8
|
||||||
|
|
||||||
|
$frame swing1 swing2 swing3 swing4 swing5 swing6 swing7
|
||||||
|
$frame swing8 swing9 swing10 swing11 swing12 swing13 swing14
|
||||||
|
|
||||||
|
$frame smash1 smash2 smash3 smash4 smash5 smash6 smash7
|
||||||
|
$frame smash8 smash9 smash10 smash11 smash12 smash13 smash14
|
||||||
|
|
||||||
|
$frame shoot1 shoot2 shoot3 shoot4 shoot5 shoot6
|
||||||
|
|
||||||
|
$frame pain1 pain2 pain3 pain4 pain5
|
||||||
|
|
||||||
|
$frame painb1 painb2 painb3
|
||||||
|
|
||||||
|
$frame painc1 painc2 painc3 painc4 painc5 painc6
|
||||||
|
|
||||||
|
$frame paind1 paind2 paind3 paind4 paind5 paind6 paind7 paind8 paind9 paind10
|
||||||
|
$frame paind11 paind12 paind13 paind14 paind15 paind16
|
||||||
|
|
||||||
|
$frame paine1 paine2 paine3 paine4 paine5 paine6 paine7 paine8 paine9 paine10
|
||||||
|
$frame paine11 paine12 paine13 paine14 paine15
|
||||||
|
|
||||||
|
$frame death1 death2 death3 death4 death5 death6
|
||||||
|
$frame death7 death8 death9 death10 death11 death12
|
||||||
|
$frame death13 death14
|
||||||
|
|
||||||
|
$frame bdeath1 bdeath2 bdeath3 bdeath4 bdeath5 bdeath6
|
||||||
|
$frame bdeath7 bdeath8 bdeath9 bdeath10
|
||||||
|
|
||||||
|
$frame pull1 pull2 pull3 pull4 pull5 pull6 pull7 pull8 pull9 pull10 pull11
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
/*
|
||||||
|
================
|
||||||
|
OgreFireGrenade
|
||||||
|
================
|
||||||
|
*/
|
||||||
|
void() OgreFireGrenade =
|
||||||
|
{
|
||||||
|
local vector vel;
|
||||||
|
|
||||||
|
muzzleflash();
|
||||||
|
sound (self, CHAN_WEAPON, "weapons/grenade.wav", 1, ATTN_NORM);
|
||||||
|
|
||||||
|
vel = normalize(self.enemy.origin - self.origin) * 600;
|
||||||
|
vel_z = 200;
|
||||||
|
|
||||||
|
PRJ_FireProjectile(self, "progs/grenade.mdl", self.origin, vel, PE_EXPLOSIONGROUND, 0, 0, 2.5);
|
||||||
|
PRJ_SetRadiusDamage(40, 80, MOD_OGRE);
|
||||||
|
PRJ_SetBouncyProjectile();
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
/*
|
||||||
|
================
|
||||||
|
chainsaw
|
||||||
|
|
||||||
|
FIXME
|
||||||
|
================
|
||||||
|
*/
|
||||||
|
void(float side) chainsaw =
|
||||||
|
{
|
||||||
|
local vector delta;
|
||||||
|
local float ldmg;
|
||||||
|
|
||||||
|
if (!self.enemy)
|
||||||
|
return;
|
||||||
|
if (!CanDamage (self.enemy, self))
|
||||||
|
return;
|
||||||
|
|
||||||
|
ai_charge(10);
|
||||||
|
|
||||||
|
delta = self.enemy.origin - self.origin;
|
||||||
|
|
||||||
|
if (vlen(delta) > 100)
|
||||||
|
return;
|
||||||
|
|
||||||
|
ldmg = (random() + random() + random()) * 4;
|
||||||
|
T_Damage (self.enemy, self, self, ldmg, MOD_OGRE);
|
||||||
|
|
||||||
|
if (side)
|
||||||
|
{
|
||||||
|
makevectors (self.angles);
|
||||||
|
if (side == 1)
|
||||||
|
SpawnMeatSpray (self.origin + v_forward*16, crandom() * 100 * v_right);
|
||||||
|
else
|
||||||
|
SpawnMeatSpray (self.origin + v_forward*16, side * v_right);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
void() ogre_stand1 =[ $stand1, ogre_stand2 ] {ai_stand();};
|
||||||
|
void() ogre_stand2 =[ $stand2, ogre_stand3 ] {ai_stand();};
|
||||||
|
void() ogre_stand3 =[ $stand3, ogre_stand4 ] {ai_stand();};
|
||||||
|
void() ogre_stand4 =[ $stand4, ogre_stand5 ] {ai_stand();};
|
||||||
|
void() ogre_stand5 =[ $stand5, ogre_stand6 ] {
|
||||||
|
if (random() < 0.2)
|
||||||
|
sound (self, CHAN_VOICE, "ogre/ogidle.wav", 1, ATTN_IDLE);
|
||||||
|
ai_stand();
|
||||||
|
};
|
||||||
|
void() ogre_stand6 =[ $stand6, ogre_stand7 ] {ai_stand();};
|
||||||
|
void() ogre_stand7 =[ $stand7, ogre_stand8 ] {ai_stand();};
|
||||||
|
void() ogre_stand8 =[ $stand8, ogre_stand9 ] {ai_stand();};
|
||||||
|
void() ogre_stand9 =[ $stand9, ogre_stand1 ] {ai_stand();};
|
||||||
|
|
||||||
|
void() ogre_walk1 =[ $walk1, ogre_walk2 ] {ai_walk(3);};
|
||||||
|
void() ogre_walk2 =[ $walk2, ogre_walk3 ] {ai_walk(2);};
|
||||||
|
void() ogre_walk3 =[ $walk3, ogre_walk4 ] {
|
||||||
|
ai_walk(2);
|
||||||
|
if (random() < 0.2)
|
||||||
|
sound (self, CHAN_VOICE, "ogre/ogidle.wav", 1, ATTN_IDLE);
|
||||||
|
};
|
||||||
|
void() ogre_walk4 =[ $walk4, ogre_walk5 ] {ai_walk(2);};
|
||||||
|
void() ogre_walk5 =[ $walk5, ogre_walk6 ] {ai_walk(2);};
|
||||||
|
void() ogre_walk6 =[ $walk6, ogre_walk7 ] {
|
||||||
|
ai_walk(5);
|
||||||
|
if (random() < 0.1)
|
||||||
|
sound (self, CHAN_VOICE, "ogre/ogdrag.wav", 1, ATTN_IDLE);
|
||||||
|
};
|
||||||
|
void() ogre_walk7 =[ $walk7, ogre_walk8 ] {ai_walk(3);};
|
||||||
|
void() ogre_walk8 =[ $walk8, ogre_walk9 ] {ai_walk(2);};
|
||||||
|
void() ogre_walk9 =[ $walk9, ogre_walk10 ] {ai_walk(3);};
|
||||||
|
void() ogre_walk10 =[ $walk10, ogre_walk11 ] {ai_walk(1);};
|
||||||
|
void() ogre_walk11 =[ $walk11, ogre_walk12 ] {ai_walk(2);};
|
||||||
|
void() ogre_walk12 =[ $walk12, ogre_walk13 ] {ai_walk(3);};
|
||||||
|
void() ogre_walk13 =[ $walk13, ogre_walk14 ] {ai_walk(3);};
|
||||||
|
void() ogre_walk14 =[ $walk14, ogre_walk15 ] {ai_walk(3);};
|
||||||
|
void() ogre_walk15 =[ $walk15, ogre_walk16 ] {ai_walk(3);};
|
||||||
|
void() ogre_walk16 =[ $walk16, ogre_walk1 ] {ai_walk(4);};
|
||||||
|
|
||||||
|
void() ogre_run1 =[ $run1, ogre_run2 ] {ai_run(9);
|
||||||
|
if (random() < 0.2)
|
||||||
|
sound (self, CHAN_VOICE, "ogre/ogidle2.wav", 1, ATTN_IDLE);
|
||||||
|
};
|
||||||
|
void() ogre_run2 =[ $run2, ogre_run3 ] {ai_run(12);};
|
||||||
|
void() ogre_run3 =[ $run3, ogre_run4 ] {ai_run(8);};
|
||||||
|
void() ogre_run4 =[ $run4, ogre_run5 ] {ai_run(22);};
|
||||||
|
void() ogre_run5 =[ $run5, ogre_run6 ] {ai_run(16);};
|
||||||
|
void() ogre_run6 =[ $run6, ogre_run7 ] {ai_run(4);};
|
||||||
|
void() ogre_run7 =[ $run7, ogre_run8 ] {ai_run(13);};
|
||||||
|
void() ogre_run8 =[ $run8, ogre_run1 ] {ai_run(24);};
|
||||||
|
|
||||||
|
void() ogre_swing1 =[ $swing1, ogre_swing2 ] {ai_charge(11);
|
||||||
|
sound (self, CHAN_WEAPON, "ogre/ogsawatk.wav", 1, ATTN_NORM);
|
||||||
|
};
|
||||||
|
void() ogre_swing2 =[ $swing2, ogre_swing3 ] {ai_charge(1);};
|
||||||
|
void() ogre_swing3 =[ $swing3, ogre_swing4 ] {ai_charge(4);};
|
||||||
|
void() ogre_swing4 =[ $swing4, ogre_swing5 ] {ai_charge(13);};
|
||||||
|
void() ogre_swing5 =[ $swing5, ogre_swing6 ] {ai_charge(9); chainsaw(0);self.angles_y = self.angles_y + random()*25;};
|
||||||
|
void() ogre_swing6 =[ $swing6, ogre_swing7 ] {chainsaw(200);self.angles_y = self.angles_y + random()* 25;};
|
||||||
|
void() ogre_swing7 =[ $swing7, ogre_swing8 ] {chainsaw(0);self.angles_y = self.angles_y + random()* 25;};
|
||||||
|
void() ogre_swing8 =[ $swing8, ogre_swing9 ] {chainsaw(0);self.angles_y = self.angles_y + random()* 25;};
|
||||||
|
void() ogre_swing9 =[ $swing9, ogre_swing10 ] {chainsaw(0);self.angles_y = self.angles_y + random()* 25;};
|
||||||
|
void() ogre_swing10 =[ $swing10, ogre_swing11 ] {chainsaw(-200);self.angles_y = self.angles_y + random()* 25;};
|
||||||
|
void() ogre_swing11 =[ $swing11, ogre_swing12 ] {chainsaw(0);self.angles_y = self.angles_y + random()* 25;};
|
||||||
|
void() ogre_swing12 =[ $swing12, ogre_swing13 ] {ai_charge(3);};
|
||||||
|
void() ogre_swing13 =[ $swing13, ogre_swing14 ] {ai_charge(8);};
|
||||||
|
void() ogre_swing14 =[ $swing14, ogre_run1 ] {ai_charge(9);};
|
||||||
|
|
||||||
|
void() ogre_smash1 =[ $smash1, ogre_smash2 ] {ai_charge(6);
|
||||||
|
sound (self, CHAN_WEAPON, "ogre/ogsawatk.wav", 1, ATTN_NORM);
|
||||||
|
};
|
||||||
|
void() ogre_smash2 =[ $smash2, ogre_smash3 ] {ai_charge(0);};
|
||||||
|
void() ogre_smash3 =[ $smash3, ogre_smash4 ] {ai_charge(0);};
|
||||||
|
void() ogre_smash4 =[ $smash4, ogre_smash5 ] {ai_charge(1);};
|
||||||
|
void() ogre_smash5 =[ $smash5, ogre_smash6 ] {ai_charge(4);};
|
||||||
|
void() ogre_smash6 =[ $smash6, ogre_smash7 ] {ai_charge(4); chainsaw(0);};
|
||||||
|
void() ogre_smash7 =[ $smash7, ogre_smash8 ] {ai_charge(4); chainsaw(0);};
|
||||||
|
void() ogre_smash8 =[ $smash8, ogre_smash9 ] {ai_charge(10); chainsaw(0);};
|
||||||
|
void() ogre_smash9 =[ $smash9, ogre_smash10 ] {ai_charge(13); chainsaw(0);};
|
||||||
|
void() ogre_smash10 =[ $smash10, ogre_smash11 ] {chainsaw(1);};
|
||||||
|
void() ogre_smash11 =[ $smash11, ogre_smash12 ] {ai_charge(2); chainsaw(0);
|
||||||
|
self.nextthink = time + 0.1 + random()*0.1;}; // slight variation
|
||||||
|
//void() ogre_smash12 =[ $smash12, ogre_smash13 ] {ai_charge();};
|
||||||
|
void() ogre_smash12 =[$smash12, ogre_smash13] {ai_charge(0);};
|
||||||
|
void() ogre_smash13 =[ $smash13, ogre_smash14 ] {ai_charge(4);};
|
||||||
|
void() ogre_smash14 =[ $smash14, ogre_run1 ] {ai_charge(12);};
|
||||||
|
|
||||||
|
void() ogre_nail1 =[ $shoot1, ogre_nail2 ] {ai_face();};
|
||||||
|
void() ogre_nail2 =[ $shoot2, ogre_nail3 ] {ai_face();};
|
||||||
|
void() ogre_nail3 =[ $shoot2, ogre_nail4 ] {ai_face();};
|
||||||
|
void() ogre_nail4 =[ $shoot3, ogre_nail5 ] {ai_face();OgreFireGrenade();};
|
||||||
|
void() ogre_nail5 =[ $shoot4, ogre_nail6 ] {ai_face();};
|
||||||
|
void() ogre_nail6 =[ $shoot5, ogre_nail7 ] {ai_face();};
|
||||||
|
void() ogre_nail7 =[ $shoot6, ogre_run1 ] {ai_face();};
|
||||||
|
|
||||||
|
void() ogre_pain1 =[ $pain1, ogre_pain2 ] {};
|
||||||
|
void() ogre_pain2 =[ $pain2, ogre_pain3 ] {};
|
||||||
|
void() ogre_pain3 =[ $pain3, ogre_pain4 ] {};
|
||||||
|
void() ogre_pain4 =[ $pain4, ogre_pain5 ] {};
|
||||||
|
void() ogre_pain5 =[ $pain5, ogre_run1 ] {};
|
||||||
|
|
||||||
|
|
||||||
|
void() ogre_painb1 =[ $painb1, ogre_painb2 ] {};
|
||||||
|
void() ogre_painb2 =[ $painb2, ogre_painb3 ] {};
|
||||||
|
void() ogre_painb3 =[ $painb3, ogre_run1 ] {};
|
||||||
|
|
||||||
|
|
||||||
|
void() ogre_painc1 =[ $painc1, ogre_painc2 ] {};
|
||||||
|
void() ogre_painc2 =[ $painc2, ogre_painc3 ] {};
|
||||||
|
void() ogre_painc3 =[ $painc3, ogre_painc4 ] {};
|
||||||
|
void() ogre_painc4 =[ $painc4, ogre_painc5 ] {};
|
||||||
|
void() ogre_painc5 =[ $painc5, ogre_painc6 ] {};
|
||||||
|
void() ogre_painc6 =[ $painc6, ogre_run1 ] {};
|
||||||
|
|
||||||
|
|
||||||
|
void() ogre_paind1 =[ $paind1, ogre_paind2 ] {};
|
||||||
|
void() ogre_paind2 =[ $paind2, ogre_paind3 ] {ai_pain(10);};
|
||||||
|
void() ogre_paind3 =[ $paind3, ogre_paind4 ] {ai_pain(9);};
|
||||||
|
void() ogre_paind4 =[ $paind4, ogre_paind5 ] {ai_pain(4);};
|
||||||
|
void() ogre_paind5 =[ $paind5, ogre_paind6 ] {};
|
||||||
|
void() ogre_paind6 =[ $paind6, ogre_paind7 ] {};
|
||||||
|
void() ogre_paind7 =[ $paind7, ogre_paind8 ] {};
|
||||||
|
void() ogre_paind8 =[ $paind8, ogre_paind9 ] {};
|
||||||
|
void() ogre_paind9 =[ $paind9, ogre_paind10 ] {};
|
||||||
|
void() ogre_paind10=[ $paind10, ogre_paind11 ] {};
|
||||||
|
void() ogre_paind11=[ $paind11, ogre_paind12 ] {};
|
||||||
|
void() ogre_paind12=[ $paind12, ogre_paind13 ] {};
|
||||||
|
void() ogre_paind13=[ $paind13, ogre_paind14 ] {};
|
||||||
|
void() ogre_paind14=[ $paind14, ogre_paind15 ] {};
|
||||||
|
void() ogre_paind15=[ $paind15, ogre_paind16 ] {};
|
||||||
|
void() ogre_paind16=[ $paind16, ogre_run1 ] {};
|
||||||
|
|
||||||
|
void() ogre_paine1 =[ $paine1, ogre_paine2 ] {};
|
||||||
|
void() ogre_paine2 =[ $paine2, ogre_paine3 ] {ai_pain(10);};
|
||||||
|
void() ogre_paine3 =[ $paine3, ogre_paine4 ] {ai_pain(9);};
|
||||||
|
void() ogre_paine4 =[ $paine4, ogre_paine5 ] {ai_pain(4);};
|
||||||
|
void() ogre_paine5 =[ $paine5, ogre_paine6 ] {};
|
||||||
|
void() ogre_paine6 =[ $paine6, ogre_paine7 ] {};
|
||||||
|
void() ogre_paine7 =[ $paine7, ogre_paine8 ] {};
|
||||||
|
void() ogre_paine8 =[ $paine8, ogre_paine9 ] {};
|
||||||
|
void() ogre_paine9 =[ $paine9, ogre_paine10 ] {};
|
||||||
|
void() ogre_paine10=[ $paine10, ogre_paine11 ] {};
|
||||||
|
void() ogre_paine11=[ $paine11, ogre_paine12 ] {};
|
||||||
|
void() ogre_paine12=[ $paine12, ogre_paine13 ] {};
|
||||||
|
void() ogre_paine13=[ $paine13, ogre_paine14 ] {};
|
||||||
|
void() ogre_paine14=[ $paine14, ogre_paine15 ] {};
|
||||||
|
void() ogre_paine15=[ $paine15, ogre_run1 ] {};
|
||||||
|
|
||||||
|
|
||||||
|
void(entity attacker, float damage) ogre_pain =
|
||||||
|
{
|
||||||
|
local float r;
|
||||||
|
|
||||||
|
// don't make multiple pain sounds right after each other
|
||||||
|
if (self.pain_finished > time)
|
||||||
|
return;
|
||||||
|
|
||||||
|
sound (self, CHAN_VOICE, "ogre/ogpain1.wav", 1, ATTN_NORM);
|
||||||
|
|
||||||
|
r = random();
|
||||||
|
|
||||||
|
if (r < 0.25)
|
||||||
|
{
|
||||||
|
ogre_pain1 ();
|
||||||
|
self.pain_finished = time + 1;
|
||||||
|
}
|
||||||
|
else if (r < 0.5)
|
||||||
|
{
|
||||||
|
ogre_painb1 ();
|
||||||
|
self.pain_finished = time + 1;
|
||||||
|
}
|
||||||
|
else if (r < 0.75)
|
||||||
|
{
|
||||||
|
ogre_painc1 ();
|
||||||
|
self.pain_finished = time + 1;
|
||||||
|
}
|
||||||
|
else if (r < 0.88)
|
||||||
|
{
|
||||||
|
ogre_paind1 ();
|
||||||
|
self.pain_finished = time + 2;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
ogre_paine1 ();
|
||||||
|
self.pain_finished = time + 2;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
void() ogre_die1 =[ $death1, ogre_die2 ] {};
|
||||||
|
void() ogre_die2 =[ $death2, ogre_die3 ] {};
|
||||||
|
void() ogre_die3 =[ $death3, ogre_die4 ]
|
||||||
|
{self.solid = SOLID_NOT;DropBackpack();};
|
||||||
|
void() ogre_die4 =[ $death4, ogre_die5 ] {};
|
||||||
|
void() ogre_die5 =[ $death5, ogre_die6 ] {};
|
||||||
|
void() ogre_die6 =[ $death6, ogre_die7 ] {};
|
||||||
|
void() ogre_die7 =[ $death7, ogre_die8 ] {};
|
||||||
|
void() ogre_die8 =[ $death8, ogre_die9 ] {};
|
||||||
|
void() ogre_die9 =[ $death9, ogre_die10 ] {};
|
||||||
|
void() ogre_die10 =[ $death10, ogre_die11 ] {};
|
||||||
|
void() ogre_die11 =[ $death11, ogre_die12 ] {};
|
||||||
|
void() ogre_die12 =[ $death12, ogre_die13 ] {};
|
||||||
|
void() ogre_die13 =[ $death13, ogre_die14 ] {};
|
||||||
|
void() ogre_die14 =[ $death14, ogre_die14 ] {};
|
||||||
|
|
||||||
|
void() ogre_bdie1 =[ $bdeath1, ogre_bdie2 ] {};
|
||||||
|
void() ogre_bdie2 =[ $bdeath2, ogre_bdie3 ] {ai_forward(5);};
|
||||||
|
void() ogre_bdie3 =[ $bdeath3, ogre_bdie4 ]
|
||||||
|
{self.solid = SOLID_NOT;DropBackpack();};
|
||||||
|
void() ogre_bdie4 =[ $bdeath4, ogre_bdie5 ] {ai_forward(1);};
|
||||||
|
void() ogre_bdie5 =[ $bdeath5, ogre_bdie6 ] {ai_forward(3);};
|
||||||
|
void() ogre_bdie6 =[ $bdeath6, ogre_bdie7 ] {ai_forward(7);};
|
||||||
|
void() ogre_bdie7 =[ $bdeath7, ogre_bdie8 ] {ai_forward(25);};
|
||||||
|
void() ogre_bdie8 =[ $bdeath8, ogre_bdie9 ] {};
|
||||||
|
void() ogre_bdie9 =[ $bdeath9, ogre_bdie10 ] {};
|
||||||
|
void() ogre_bdie10 =[ $bdeath10, ogre_bdie10 ] {};
|
||||||
|
|
||||||
|
void() ogre_die =
|
||||||
|
{
|
||||||
|
// check for gib
|
||||||
|
if (self.health < -80)
|
||||||
|
{
|
||||||
|
sound (self, CHAN_VOICE, "player/udeath.wav", 1, ATTN_NORM);
|
||||||
|
ThrowHead ("progs/h_ogre.mdl", self.health);
|
||||||
|
ThrowGib ("progs/gib3.mdl", self.health);
|
||||||
|
ThrowGib ("progs/gib3.mdl", self.health);
|
||||||
|
ThrowGib ("progs/gib3.mdl", self.health);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
sound (self, CHAN_VOICE, "ogre/ogdth.wav", 1, ATTN_NORM);
|
||||||
|
|
||||||
|
if (random() < 0.5)
|
||||||
|
ogre_die1 ();
|
||||||
|
else
|
||||||
|
ogre_bdie1 ();
|
||||||
|
};
|
||||||
|
|
||||||
|
void() ogre_melee =
|
||||||
|
{
|
||||||
|
if (random() > 0.5)
|
||||||
|
ogre_smash1 ();
|
||||||
|
else
|
||||||
|
ogre_swing1 ();
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
/*QUAKED monster_ogre (1 0 0) (-32 -32 -24) (32 32 64) Ambush
|
||||||
|
|
||||||
|
*/
|
||||||
|
void() monster_ogre =
|
||||||
|
{
|
||||||
|
if (deathmatch)
|
||||||
|
{
|
||||||
|
remove(self);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
precache_model ("progs/ogre.mdl");
|
||||||
|
precache_model ("progs/h_ogre.mdl");
|
||||||
|
precache_model ("progs/grenade.mdl");
|
||||||
|
|
||||||
|
precache_sound ("ogre/ogdrag.wav");
|
||||||
|
precache_sound ("ogre/ogdth.wav");
|
||||||
|
precache_sound ("ogre/ogidle.wav");
|
||||||
|
precache_sound ("ogre/ogidle2.wav");
|
||||||
|
precache_sound ("ogre/ogpain1.wav");
|
||||||
|
precache_sound ("ogre/ogsawatk.wav");
|
||||||
|
precache_sound ("ogre/ogwake.wav");
|
||||||
|
|
||||||
|
self.solid = SOLID_SLIDEBOX;
|
||||||
|
self.movetype = MOVETYPE_STEP;
|
||||||
|
|
||||||
|
setmodel (self, "progs/ogre.mdl");
|
||||||
|
|
||||||
|
setsize (self, VEC_HULL2_MIN, VEC_HULL2_MAX);
|
||||||
|
self.health = 200;
|
||||||
|
|
||||||
|
self.th_stand = ogre_stand1;
|
||||||
|
self.th_walk = ogre_walk1;
|
||||||
|
self.th_run = ogre_run1;
|
||||||
|
self.th_die = ogre_die;
|
||||||
|
self.th_melee = ogre_melee;
|
||||||
|
self.th_missile = ogre_nail1;
|
||||||
|
self.th_pain = ogre_pain;
|
||||||
|
|
||||||
|
self.ammo_rockets_real = 2; // drop 2 rockets on death
|
||||||
|
|
||||||
|
walkmonster_start();
|
||||||
|
};
|
||||||
|
|
||||||
|
void() monster_ogre_marksman =
|
||||||
|
{
|
||||||
|
monster_ogre ();
|
||||||
|
};
|
||||||
|
|
||||||
|
|
278
quakec/basemod/oldone.qc
Normal file
278
quakec/basemod/oldone.qc
Normal file
|
@ -0,0 +1,278 @@
|
||||||
|
/*
|
||||||
|
==============================================================================
|
||||||
|
|
||||||
|
OLD ONE
|
||||||
|
|
||||||
|
==============================================================================
|
||||||
|
*/
|
||||||
|
$cd id1/models/old_one
|
||||||
|
$origin 0 0 24
|
||||||
|
$base base
|
||||||
|
$skin skin
|
||||||
|
$scale 1
|
||||||
|
|
||||||
|
void() finale_1;
|
||||||
|
void() finale_2;
|
||||||
|
void() finale_3;
|
||||||
|
void() finale_4;
|
||||||
|
|
||||||
|
$frame old1 old2 old3 old4 old5 old6 old7 old8 old9
|
||||||
|
$frame old10 old11 old12 old13 old14 old15 old16 old17 old18 old19
|
||||||
|
$frame old20 old21 old22 old23 old24 old25 old26 old27 old28 old29
|
||||||
|
$frame old30 old31 old32 old33 old34 old35 old36 old37 old38 old39
|
||||||
|
$frame old40 old41 old42 old43 old44 old45 old46
|
||||||
|
|
||||||
|
$frame shake1 shake2 shake3 shake4 shake5 shake6 shake7 shake8
|
||||||
|
$frame shake9 shake10 shake11 shakex shake12 shake13 shake14
|
||||||
|
$frame shake15 shake16 shake17 shake18 shake19 shake20
|
||||||
|
|
||||||
|
//void() old_stand =[ $old1, old_stand ] {};
|
||||||
|
|
||||||
|
void() old_idle1 =[ $old1, old_idle2 ] {};
|
||||||
|
void() old_idle2 =[ $old2, old_idle3 ] {};
|
||||||
|
void() old_idle3 =[ $old3, old_idle4 ] {};
|
||||||
|
void() old_idle4 =[ $old4, old_idle5 ] {};
|
||||||
|
void() old_idle5 =[ $old5, old_idle6 ] {};
|
||||||
|
void() old_idle6 =[ $old6, old_idle7 ] {};
|
||||||
|
void() old_idle7 =[ $old7, old_idle8 ] {};
|
||||||
|
void() old_idle8 =[ $old8, old_idle9 ] {};
|
||||||
|
void() old_idle9 =[ $old9, old_idle10 ] {};
|
||||||
|
void() old_idle10 =[ $old10, old_idle11 ] {};
|
||||||
|
void() old_idle11 =[ $old11, old_idle12 ] {};
|
||||||
|
void() old_idle12 =[ $old12, old_idle13 ] {};
|
||||||
|
void() old_idle13 =[ $old13, old_idle14 ] {};
|
||||||
|
void() old_idle14 =[ $old14, old_idle15 ] {};
|
||||||
|
void() old_idle15 =[ $old15, old_idle16 ] {};
|
||||||
|
void() old_idle16 =[ $old16, old_idle17 ] {};
|
||||||
|
void() old_idle17 =[ $old17, old_idle18 ] {};
|
||||||
|
void() old_idle18 =[ $old18, old_idle19 ] {};
|
||||||
|
void() old_idle19 =[ $old19, old_idle20 ] {};
|
||||||
|
void() old_idle20 =[ $old20, old_idle21 ] {};
|
||||||
|
void() old_idle21 =[ $old21, old_idle22 ] {};
|
||||||
|
void() old_idle22 =[ $old22, old_idle23 ] {};
|
||||||
|
void() old_idle23 =[ $old23, old_idle24 ] {};
|
||||||
|
void() old_idle24 =[ $old24, old_idle25 ] {};
|
||||||
|
void() old_idle25 =[ $old25, old_idle26 ] {};
|
||||||
|
void() old_idle26 =[ $old26, old_idle27 ] {};
|
||||||
|
void() old_idle27 =[ $old27, old_idle28 ] {};
|
||||||
|
void() old_idle28 =[ $old28, old_idle29 ] {};
|
||||||
|
void() old_idle29 =[ $old29, old_idle30 ] {};
|
||||||
|
void() old_idle30 =[ $old30, old_idle31 ] {};
|
||||||
|
void() old_idle31 =[ $old31, old_idle32 ] {};
|
||||||
|
void() old_idle32 =[ $old32, old_idle33 ] {};
|
||||||
|
void() old_idle33 =[ $old33, old_idle34 ] {};
|
||||||
|
void() old_idle34 =[ $old34, old_idle35 ] {};
|
||||||
|
void() old_idle35 =[ $old35, old_idle36 ] {};
|
||||||
|
void() old_idle36 =[ $old36, old_idle37 ] {};
|
||||||
|
void() old_idle37 =[ $old37, old_idle38 ] {};
|
||||||
|
void() old_idle38 =[ $old38, old_idle39 ] {};
|
||||||
|
void() old_idle39 =[ $old39, old_idle40 ] {};
|
||||||
|
void() old_idle40 =[ $old40, old_idle41 ] {};
|
||||||
|
void() old_idle41 =[ $old41, old_idle42 ] {};
|
||||||
|
void() old_idle42 =[ $old42, old_idle43 ] {};
|
||||||
|
void() old_idle43 =[ $old43, old_idle44 ] {};
|
||||||
|
void() old_idle44 =[ $old44, old_idle45 ] {};
|
||||||
|
void() old_idle45 =[ $old45, old_idle46 ] {};
|
||||||
|
void() old_idle46 =[ $old46, old_idle1 ] {};
|
||||||
|
|
||||||
|
|
||||||
|
void() old_thrash1 =[ $shake1, old_thrash2 ] {lightstyle(0, "m");};
|
||||||
|
void() old_thrash2 =[ $shake2, old_thrash3 ] {lightstyle(0, "k");};
|
||||||
|
void() old_thrash3 =[ $shake3, old_thrash4 ] {lightstyle(0, "k");};
|
||||||
|
void() old_thrash4 =[ $shake4, old_thrash5 ] {lightstyle(0, "i");};
|
||||||
|
void() old_thrash5 =[ $shake5, old_thrash6 ] {lightstyle(0, "g");};
|
||||||
|
void() old_thrash6 =[ $shake6, old_thrash7 ] {lightstyle(0, "e");};
|
||||||
|
void() old_thrash7 =[ $shake7, old_thrash8 ] {lightstyle(0, "c");};
|
||||||
|
void() old_thrash8 =[ $shake8, old_thrash9 ] {lightstyle(0, "a");};
|
||||||
|
void() old_thrash9 =[ $shake9, old_thrash10 ] {lightstyle(0, "c");};
|
||||||
|
void() old_thrash10 =[ $shake10, old_thrash11 ] {lightstyle(0, "e");};
|
||||||
|
void() old_thrash11 =[ $shake11, old_thrash12 ] {lightstyle(0, "g");};
|
||||||
|
void() old_thrash12 =[ $shake12, old_thrash13 ] {lightstyle(0, "i");};
|
||||||
|
void() old_thrash13 =[ $shake13, old_thrash14 ] {lightstyle(0, "k");};
|
||||||
|
void() old_thrash14 =[ $shake14, old_thrash15 ] {lightstyle(0, "m");};
|
||||||
|
void() old_thrash15 =[ $shake15, old_thrash16 ] {lightstyle(0, "m");
|
||||||
|
self.cnt = self.cnt + 1;
|
||||||
|
if (self.cnt < 3)
|
||||||
|
self.think = old_thrash1;
|
||||||
|
};
|
||||||
|
void() old_thrash16 =[ $shake16, old_thrash17 ] {lightstyle(0, "g");};
|
||||||
|
void() old_thrash17 =[ $shake17, old_thrash18 ] {lightstyle(0, "c");};
|
||||||
|
void() old_thrash18 =[ $shake18, old_thrash19 ] {lightstyle(0, "b");};
|
||||||
|
void() old_thrash19 =[ $shake19, old_thrash20 ] {lightstyle(0, "a");};
|
||||||
|
void() old_thrash20 =[ $shake20, old_thrash20 ] {finale_4();};
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
|
||||||
|
void() finale_1 =
|
||||||
|
{
|
||||||
|
local entity pos, pl;
|
||||||
|
local entity timer;
|
||||||
|
|
||||||
|
// TODO: Coop friendly finale goes here
|
||||||
|
|
||||||
|
killed_monsters = killed_monsters + 1;
|
||||||
|
WriteByte (MSG_ALL, SVC_KILLEDMONSTER); // FIXME: reliable broadcast
|
||||||
|
|
||||||
|
intermission_exittime = time + 10000000; // never allow exit
|
||||||
|
intermission_running = 1;
|
||||||
|
|
||||||
|
// find the intermission spot
|
||||||
|
pos = find (world, classname, "info_intermission");
|
||||||
|
if (!pos)
|
||||||
|
error ("no info_intermission");
|
||||||
|
pl = find (world, classname, "misc_teleporttrain");
|
||||||
|
if (!pl)
|
||||||
|
error ("no teleporttrain");
|
||||||
|
remove (pl);
|
||||||
|
|
||||||
|
ENG_Finale("");
|
||||||
|
|
||||||
|
pl = find (world, classname, "player");
|
||||||
|
while (pl != world)
|
||||||
|
{
|
||||||
|
pl.view_ofs = '0 0 0';
|
||||||
|
pl.angles = other.v_angle = pos.mangle;
|
||||||
|
pl.fixangle = TRUE; // turn this way immediately
|
||||||
|
pl.map = self.map;
|
||||||
|
pl.nextthink = time + 0.5;
|
||||||
|
pl.takedamage = DAMAGE_NO;
|
||||||
|
pl.solid = SOLID_NOT;
|
||||||
|
pl.movetype = MOVETYPE_NONE;
|
||||||
|
pl.modelindex = 0;
|
||||||
|
setorigin (pl, pos.origin);
|
||||||
|
pl = find (pl, classname, "player");
|
||||||
|
}
|
||||||
|
|
||||||
|
// make fake versions of all players as standins, and move the real
|
||||||
|
// players to the intermission spot
|
||||||
|
|
||||||
|
// wait for 1 second
|
||||||
|
timer = spawn();
|
||||||
|
timer.nextthink = time + 1;
|
||||||
|
timer.think = finale_2;
|
||||||
|
};
|
||||||
|
|
||||||
|
void() finale_2 =
|
||||||
|
{
|
||||||
|
local vector o;
|
||||||
|
|
||||||
|
// start a teleport splash inside shub
|
||||||
|
|
||||||
|
o = shub.origin - '0 100 0';
|
||||||
|
TE_teleport(o);
|
||||||
|
|
||||||
|
sound (shub, CHAN_VOICE, "misc/r_tele1.wav", 1, ATTN_NORM);
|
||||||
|
|
||||||
|
self.nextthink = time + 2;
|
||||||
|
self.think = finale_3;
|
||||||
|
};
|
||||||
|
|
||||||
|
void() finale_3 =
|
||||||
|
{
|
||||||
|
// start shub thrashing wildly
|
||||||
|
lightstyle(0, "a");
|
||||||
|
shub.think = old_thrash1;
|
||||||
|
sound (shub, CHAN_VOICE, "boss2/death.wav", 1, ATTN_NORM);
|
||||||
|
remove(self);
|
||||||
|
};
|
||||||
|
|
||||||
|
void() finale_4 =
|
||||||
|
{
|
||||||
|
// throw tons of meat chunks
|
||||||
|
local vector oldo;
|
||||||
|
local float x, y, z;
|
||||||
|
local float r;
|
||||||
|
local entity n;
|
||||||
|
|
||||||
|
sound (self, CHAN_VOICE, "boss2/pop2.wav", 1, ATTN_NORM);
|
||||||
|
|
||||||
|
oldo = self.origin;
|
||||||
|
|
||||||
|
z = 16;
|
||||||
|
while (z <= 144)
|
||||||
|
{
|
||||||
|
x = -64;
|
||||||
|
while (x <= 64)
|
||||||
|
{
|
||||||
|
y = -64;
|
||||||
|
while (y <= 64)
|
||||||
|
{
|
||||||
|
self.origin_x = oldo_x + x;
|
||||||
|
self.origin_y = oldo_y + y;
|
||||||
|
self.origin_z = oldo_z + z;
|
||||||
|
|
||||||
|
r = random();
|
||||||
|
if (r < 0.3)
|
||||||
|
ThrowGib ("progs/gib1.mdl", -999);
|
||||||
|
else if (r < 0.6)
|
||||||
|
ThrowGib ("progs/gib2.mdl", -999);
|
||||||
|
else
|
||||||
|
ThrowGib ("progs/gib3.mdl", -999);
|
||||||
|
y = y + 32;
|
||||||
|
}
|
||||||
|
x = x + 32;
|
||||||
|
}
|
||||||
|
z = z + 96;
|
||||||
|
}
|
||||||
|
// start the end text
|
||||||
|
ENG_Finale("Congratulations and well done! You have\nbeaten the hideous Shub-Niggurath, and\nher hundreds of ugly changelings and\nmonsters. You have proven that your\nskill and your cunning are greater than\nall the powers of Quake. You are the\nmaster now. Id Software salutes you.");
|
||||||
|
|
||||||
|
// put a player model down
|
||||||
|
n = spawn();
|
||||||
|
setmodel (n, "progs/player.mdl");
|
||||||
|
oldo = oldo - '32 264 0';
|
||||||
|
setorigin (n, oldo);
|
||||||
|
n.angles = '0 290 0';
|
||||||
|
n.frame = 1;
|
||||||
|
|
||||||
|
remove (self);
|
||||||
|
|
||||||
|
// switch cd track
|
||||||
|
ENG_SwitchTrack(3, 3);
|
||||||
|
lightstyle(0, "m");
|
||||||
|
};
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
|
||||||
|
void () nopain =
|
||||||
|
{
|
||||||
|
self.health = 40000;
|
||||||
|
};
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
|
||||||
|
|
||||||
|
/*QUAKED monster_oldone (1 0 0) (-16 -16 -24) (16 16 32)
|
||||||
|
*/
|
||||||
|
void() monster_oldone =
|
||||||
|
{
|
||||||
|
if (deathmatch)
|
||||||
|
{
|
||||||
|
remove(self);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
precache_model2 ("progs/oldone.mdl");
|
||||||
|
|
||||||
|
precache_sound2 ("boss2/death.wav");
|
||||||
|
precache_sound2 ("boss2/idle.wav");
|
||||||
|
precache_sound2 ("boss2/sight.wav");
|
||||||
|
precache_sound2 ("boss2/pop2.wav");
|
||||||
|
|
||||||
|
self.solid = SOLID_SLIDEBOX;
|
||||||
|
self.movetype = MOVETYPE_STEP;
|
||||||
|
|
||||||
|
setmodel (self, "progs/oldone.mdl");
|
||||||
|
setsize (self, '-160 -128 -24', '160 128 256');
|
||||||
|
|
||||||
|
self.health = 40000; // kill by telefrag
|
||||||
|
self.think = old_idle1;
|
||||||
|
self.nextthink = time + 0.1;
|
||||||
|
self.takedamage = DAMAGE_YES;
|
||||||
|
self.th_pain = nopain;
|
||||||
|
self.th_die = finale_1;
|
||||||
|
shub = self;
|
||||||
|
|
||||||
|
total_monsters = total_monsters + 1;
|
||||||
|
};
|
||||||
|
|
|
@ -123,13 +123,13 @@ void() player_run =[ $rockrun1, player_run ]
|
||||||
|
|
||||||
if (self.weapon == IT_AXE)
|
if (self.weapon == IT_AXE)
|
||||||
{
|
{
|
||||||
if (self.walkframe == 6)
|
if (self.walkframe >= 6)
|
||||||
self.walkframe = 0;
|
self.walkframe = 0;
|
||||||
self.frame = $axrun1 + self.walkframe;
|
self.frame = $axrun1 + self.walkframe;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
if (self.walkframe == 6)
|
if (self.walkframe >= 6)
|
||||||
self.walkframe = 0;
|
self.walkframe = 0;
|
||||||
self.frame = self.frame + self.walkframe;
|
self.frame = self.frame + self.walkframe;
|
||||||
}
|
}
|
||||||
|
@ -313,7 +313,7 @@ local entity bubble;
|
||||||
bubble.think = bubble_bob;
|
bubble.think = bubble_bob;
|
||||||
bubble.classname = "bubble";
|
bubble.classname = "bubble";
|
||||||
bubble.frame = 0;
|
bubble.frame = 0;
|
||||||
bubble.cnt = 0;
|
bubble.bubble_state = 0;
|
||||||
setsize (bubble, '-8 -8 -8', '8 8 8');
|
setsize (bubble, '-8 -8 -8', '8 8 8');
|
||||||
self.nextthink = time + 0.1;
|
self.nextthink = time + 0.1;
|
||||||
self.think = DeathBubblesSpawn;
|
self.think = DeathBubblesSpawn;
|
||||||
|
@ -428,7 +428,6 @@ void(string gibname, float dm) ThrowGib =
|
||||||
new.avelocity_y = random()*600;
|
new.avelocity_y = random()*600;
|
||||||
new.avelocity_z = random()*600;
|
new.avelocity_z = random()*600;
|
||||||
new.think = SUB_Remove;
|
new.think = SUB_Remove;
|
||||||
new.ltime = time;
|
|
||||||
new.nextthink = time + 10 + random()*10;
|
new.nextthink = time + 10 + random()*10;
|
||||||
new.frame = 0;
|
new.frame = 0;
|
||||||
new.flags = 0;
|
new.flags = 0;
|
||||||
|
|
|
@ -39,7 +39,24 @@
|
||||||
#include "misc.qc"
|
#include "misc.qc"
|
||||||
|
|
||||||
#ifdef MONSTERS
|
#ifdef MONSTERS
|
||||||
|
#include "fight.qc"
|
||||||
|
#include "ai.qc"
|
||||||
|
#include "monsters.qc"
|
||||||
|
#include "dog.qc"
|
||||||
|
#include "soldier.qc"
|
||||||
|
#include "enforcer.qc"
|
||||||
|
#include "ogre.qc"
|
||||||
|
#include "wizard.qc"
|
||||||
|
#include "demon.qc"
|
||||||
|
#include "knight.qc"
|
||||||
|
#include "hknight.qc"
|
||||||
|
#include "shalrath.qc"
|
||||||
|
#include "shambler.qc"
|
||||||
|
#include "fish.qc"
|
||||||
|
#include "tarbaby.qc"
|
||||||
|
#include "zombie.qc"
|
||||||
|
#include "boss.qc"
|
||||||
|
#include "oldone.qc"
|
||||||
#else
|
#else
|
||||||
#include "nomonst.qc"
|
#include "nomonst.qc"
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -10,7 +10,8 @@ enum {
|
||||||
PE_GUNSHOT,
|
PE_GUNSHOT,
|
||||||
PE_EXPLOSION,
|
PE_EXPLOSION,
|
||||||
PE_EXPLOSIONGROUND,
|
PE_EXPLOSIONGROUND,
|
||||||
PE_LASER
|
PE_LASER,
|
||||||
|
PE_ZOMBIEGIB
|
||||||
};
|
};
|
||||||
|
|
||||||
// functions used only by this QC file
|
// functions used only by this QC file
|
||||||
|
@ -26,6 +27,24 @@ float() _PRJ_Bounce =
|
||||||
return 1; // keep bouncing
|
return 1; // keep bouncing
|
||||||
};
|
};
|
||||||
|
|
||||||
|
float() _PRJ_Remove =
|
||||||
|
{
|
||||||
|
remove(self);
|
||||||
|
return 1; // stop execution within touch function
|
||||||
|
};
|
||||||
|
|
||||||
|
float() _PRJ_Stop =
|
||||||
|
{
|
||||||
|
if (other.takedamage)
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
sound (self, CHAN_WEAPON, "zombie/z_miss.wav", 1, ATTN_NORM); // bounce sound
|
||||||
|
self.velocity = '0 0 0';
|
||||||
|
self.avelocity = '0 0 0';
|
||||||
|
self.proj_touch = _PRJ_Remove;
|
||||||
|
return 1; // keep the entity alive
|
||||||
|
};
|
||||||
|
|
||||||
void() _PRJ_Touch =
|
void() _PRJ_Touch =
|
||||||
{
|
{
|
||||||
local entity ignore;
|
local entity ignore;
|
||||||
|
@ -56,14 +75,14 @@ void() _PRJ_Touch =
|
||||||
// do projectile damage
|
// do projectile damage
|
||||||
ignore = self;
|
ignore = self;
|
||||||
|
|
||||||
if (other.health && self.damage_direct)
|
if (other.health >= 1 && self.damage_direct)
|
||||||
{
|
{
|
||||||
T_Damage (other, self, self.owner, self.damage_direct, self.mod_direct);
|
T_Damage (other, self, self.owner, self.damage_direct, self.mod_direct);
|
||||||
ignore = other;
|
ignore = other;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (self.radius_exp)
|
if (self.radius_exp)
|
||||||
T_RadiusDamage (self, self.owner, self.damage_exp, self.radius_exp, other, self.mod_exp);
|
T_RadiusDamage (self, self.owner, self.damage_exp, self.radius_exp, ignore, self.mod_exp);
|
||||||
|
|
||||||
// run projectile effect
|
// run projectile effect
|
||||||
switch (self.proj_effect)
|
switch (self.proj_effect)
|
||||||
|
@ -107,6 +126,9 @@ void() _PRJ_Touch =
|
||||||
case PE_EXPLOSIONGROUND:
|
case PE_EXPLOSIONGROUND:
|
||||||
TE_explosion(self.origin);
|
TE_explosion(self.origin);
|
||||||
break;
|
break;
|
||||||
|
case PE_ZOMBIEGIB:
|
||||||
|
sound (self, CHAN_WEAPON, "zombie/z_hit.wav", 1, ATTN_NORM);
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
remove(self);
|
remove(self);
|
||||||
|
@ -126,8 +148,8 @@ void() _PRJ_Think =
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
newmis.proj_think();
|
self.nextthink = time + self.proj_think_time;
|
||||||
newmis.nextthink = time + newmis.proj_think_time;
|
self.proj_think(); // projectile could remove itself here
|
||||||
};
|
};
|
||||||
|
|
||||||
// functions used by outside QC files
|
// functions used by outside QC files
|
||||||
|
@ -139,6 +161,14 @@ void() PRJ_SetBouncyProjectile =
|
||||||
newmis.avelocity = '300 300 300';
|
newmis.avelocity = '300 300 300';
|
||||||
};
|
};
|
||||||
|
|
||||||
|
// set tossed projectile (zombie gib) function
|
||||||
|
void() PRJ_SetTossedProjectile =
|
||||||
|
{
|
||||||
|
newmis.proj_touch = _PRJ_Stop;
|
||||||
|
newmis.movetype = MOVETYPE_BOUNCE;
|
||||||
|
newmis.avelocity = '3000 1000 2000';
|
||||||
|
};
|
||||||
|
|
||||||
// set radius damage function
|
// set radius damage function
|
||||||
void(INTEGER damg, INTEGER damgrad, INTEGER damgmod) PRJ_SetRadiusDamage =
|
void(INTEGER damg, INTEGER damgrad, INTEGER damgmod) PRJ_SetRadiusDamage =
|
||||||
{
|
{
|
||||||
|
@ -148,14 +178,20 @@ void(INTEGER damg, INTEGER damgrad, INTEGER damgmod) PRJ_SetRadiusDamage =
|
||||||
};
|
};
|
||||||
|
|
||||||
// extra think function, should always be called ONCE after the main spawn function
|
// extra think function, should always be called ONCE after the main spawn function
|
||||||
void(void() thinkfunc, float thinkres) PRJ_SetThink =
|
void(void() thinkfunc, float thinktimeinit, float thinkres) PRJ_SetThink =
|
||||||
{
|
{
|
||||||
newmis.think = _PRJ_Think;
|
newmis.think = _PRJ_Think;
|
||||||
newmis.nextthink = time + thinkres;
|
newmis.nextthink = time + thinktimeinit;
|
||||||
newmis.proj_think = thinkfunc;
|
newmis.proj_think = thinkfunc;
|
||||||
newmis.proj_think_time = thinkres;
|
newmis.proj_think_time = thinkres;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
// extra touch function
|
||||||
|
void(float() touchfunc) PRJ_SetTouch =
|
||||||
|
{
|
||||||
|
newmis.proj_touch = touchfunc;
|
||||||
|
};
|
||||||
|
|
||||||
// main spawning function
|
// main spawning function
|
||||||
void(entity parent, string modl, vector org, vector vel, INTEGER effect, INTEGER damg, INTEGER damgmod, float expiretime) PRJ_FireProjectile =
|
void(entity parent, string modl, vector org, vector vel, INTEGER effect, INTEGER damg, INTEGER damgmod, float expiretime) PRJ_FireProjectile =
|
||||||
{
|
{
|
||||||
|
|
219
quakec/basemod/shalrath.qc
Normal file
219
quakec/basemod/shalrath.qc
Normal file
|
@ -0,0 +1,219 @@
|
||||||
|
/*
|
||||||
|
==============================================================================
|
||||||
|
|
||||||
|
SHAL-RATH
|
||||||
|
|
||||||
|
==============================================================================
|
||||||
|
*/
|
||||||
|
$cd id1/models/shalrath
|
||||||
|
$origin 0 0 24
|
||||||
|
$base base
|
||||||
|
$skin skin
|
||||||
|
$scale 0.7
|
||||||
|
|
||||||
|
$frame attack1 attack2 attack3 attack4 attack5 attack6 attack7 attack8
|
||||||
|
$frame attack9 attack10 attack11
|
||||||
|
|
||||||
|
$frame pain1 pain2 pain3 pain4 pain5
|
||||||
|
|
||||||
|
$frame death1 death2 death3 death4 death5 death6 death7
|
||||||
|
|
||||||
|
$frame walk1 walk2 walk3 walk4 walk5 walk6 walk7 walk8 walk9 walk10
|
||||||
|
$frame walk11 walk12
|
||||||
|
|
||||||
|
void() shalrath_pain;
|
||||||
|
void() ShalMissile;
|
||||||
|
void() shal_stand =[ $walk1, shal_stand ] {ai_stand();};
|
||||||
|
|
||||||
|
void() shal_walk1 =[ $walk2, shal_walk2 ] {
|
||||||
|
if (random() < 0.2)
|
||||||
|
sound (self, CHAN_VOICE, "shalrath/idle.wav", 1, ATTN_IDLE);
|
||||||
|
ai_walk(6);};
|
||||||
|
void() shal_walk2 =[ $walk3, shal_walk3 ] {ai_walk(4);};
|
||||||
|
void() shal_walk3 =[ $walk4, shal_walk4 ] {ai_walk(0);};
|
||||||
|
void() shal_walk4 =[ $walk5, shal_walk5 ] {ai_walk(0);};
|
||||||
|
void() shal_walk5 =[ $walk6, shal_walk6 ] {ai_walk(0);};
|
||||||
|
void() shal_walk6 =[ $walk7, shal_walk7 ] {ai_walk(0);};
|
||||||
|
void() shal_walk7 =[ $walk8, shal_walk8 ] {ai_walk(5);};
|
||||||
|
void() shal_walk8 =[ $walk9, shal_walk9 ] {ai_walk(6);};
|
||||||
|
void() shal_walk9 =[ $walk10, shal_walk10 ] {ai_walk(5);};
|
||||||
|
void() shal_walk10 =[ $walk11, shal_walk11 ] {ai_walk(0);};
|
||||||
|
void() shal_walk11 =[ $walk12, shal_walk12 ] {ai_walk(4);};
|
||||||
|
void() shal_walk12 =[ $walk1, shal_walk1 ] {ai_walk(5);};
|
||||||
|
|
||||||
|
void() shal_run1 =[ $walk2, shal_run2 ] {
|
||||||
|
if (random() < 0.2)
|
||||||
|
sound (self, CHAN_VOICE, "shalrath/idle.wav", 1, ATTN_IDLE);
|
||||||
|
ai_run(6);};
|
||||||
|
void() shal_run2 =[ $walk3, shal_run3 ] {ai_run(4);};
|
||||||
|
void() shal_run3 =[ $walk4, shal_run4 ] {ai_run(0);};
|
||||||
|
void() shal_run4 =[ $walk5, shal_run5 ] {ai_run(0);};
|
||||||
|
void() shal_run5 =[ $walk6, shal_run6 ] {ai_run(0);};
|
||||||
|
void() shal_run6 =[ $walk7, shal_run7 ] {ai_run(0);};
|
||||||
|
void() shal_run7 =[ $walk8, shal_run8 ] {ai_run(5);};
|
||||||
|
void() shal_run8 =[ $walk9, shal_run9 ] {ai_run(6);};
|
||||||
|
void() shal_run9 =[ $walk10, shal_run10 ] {ai_run(5);};
|
||||||
|
void() shal_run10 =[ $walk11, shal_run11 ] {ai_run(0);};
|
||||||
|
void() shal_run11 =[ $walk12, shal_run12 ] {ai_run(4);};
|
||||||
|
void() shal_run12 =[ $walk1, shal_run1 ] {ai_run(5);};
|
||||||
|
|
||||||
|
void() shal_attack1 =[ $attack1, shal_attack2 ] {
|
||||||
|
sound (self, CHAN_VOICE, "shalrath/attack.wav", 1, ATTN_NORM);
|
||||||
|
ai_face();
|
||||||
|
};
|
||||||
|
void() shal_attack2 =[ $attack2, shal_attack3 ] {ai_face();};
|
||||||
|
void() shal_attack3 =[ $attack3, shal_attack4 ] {ai_face();};
|
||||||
|
void() shal_attack4 =[ $attack4, shal_attack5 ] {ai_face();};
|
||||||
|
void() shal_attack5 =[ $attack5, shal_attack6 ] {ai_face();};
|
||||||
|
void() shal_attack6 =[ $attack6, shal_attack7 ] {ai_face();};
|
||||||
|
void() shal_attack7 =[ $attack7, shal_attack8 ] {ai_face();};
|
||||||
|
void() shal_attack8 =[ $attack8, shal_attack9 ] {ai_face();};
|
||||||
|
void() shal_attack9 =[ $attack9, shal_attack10 ] {ShalMissile();};
|
||||||
|
void() shal_attack10 =[ $attack10, shal_attack11 ] {ai_face();};
|
||||||
|
void() shal_attack11 =[ $attack11, shal_run1 ] {};
|
||||||
|
|
||||||
|
void() shal_pain1 =[ $pain1, shal_pain2 ] {};
|
||||||
|
void() shal_pain2 =[ $pain2, shal_pain3 ] {};
|
||||||
|
void() shal_pain3 =[ $pain3, shal_pain4 ] {};
|
||||||
|
void() shal_pain4 =[ $pain4, shal_pain5 ] {};
|
||||||
|
void() shal_pain5 =[ $pain5, shal_run1 ] {};
|
||||||
|
|
||||||
|
void() shal_death1 =[ $death1, shal_death2 ] {};
|
||||||
|
void() shal_death2 =[ $death2, shal_death3 ] {};
|
||||||
|
void() shal_death3 =[ $death3, shal_death4 ] {};
|
||||||
|
void() shal_death4 =[ $death4, shal_death5 ] {};
|
||||||
|
void() shal_death5 =[ $death5, shal_death6 ] {};
|
||||||
|
void() shal_death6 =[ $death6, shal_death7 ] {};
|
||||||
|
void() shal_death7 =[ $death7, shal_death7 ] {};
|
||||||
|
|
||||||
|
|
||||||
|
void() shalrath_pain =
|
||||||
|
{
|
||||||
|
if (self.pain_finished > time)
|
||||||
|
return;
|
||||||
|
|
||||||
|
sound (self, CHAN_VOICE, "shalrath/pain.wav", 1, ATTN_NORM);
|
||||||
|
shal_pain1();
|
||||||
|
self.pain_finished = time + 3;
|
||||||
|
};
|
||||||
|
|
||||||
|
void() shalrath_die =
|
||||||
|
{
|
||||||
|
// check for gib
|
||||||
|
if (self.health < -90)
|
||||||
|
{
|
||||||
|
sound (self, CHAN_VOICE, "player/udeath.wav", 1, ATTN_NORM);
|
||||||
|
ThrowHead ("progs/h_shal.mdl", self.health);
|
||||||
|
ThrowGib ("progs/gib1.mdl", self.health);
|
||||||
|
ThrowGib ("progs/gib2.mdl", self.health);
|
||||||
|
ThrowGib ("progs/gib3.mdl", self.health);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
sound (self, CHAN_VOICE, "shalrath/death.wav", 1, ATTN_NORM);
|
||||||
|
shal_death1();
|
||||||
|
self.solid = SOLID_NOT;
|
||||||
|
// insert death sounds here
|
||||||
|
};
|
||||||
|
|
||||||
|
/*
|
||||||
|
================
|
||||||
|
ShalMissile
|
||||||
|
================
|
||||||
|
*/
|
||||||
|
float() ShalMissileTouch;
|
||||||
|
void() ShalHome;
|
||||||
|
void() ShalMissile =
|
||||||
|
{
|
||||||
|
local vector dir;
|
||||||
|
local float dist, flytime;
|
||||||
|
|
||||||
|
dir = normalize((self.enemy.origin + '0 0 10') - self.origin);
|
||||||
|
dist = vlen (self.enemy.origin - self.origin);
|
||||||
|
flytime = dist * 0.002;
|
||||||
|
if (flytime < 0.1)
|
||||||
|
flytime = 0.1;
|
||||||
|
|
||||||
|
muzzleflash();
|
||||||
|
sound (self, CHAN_WEAPON, "shalrath/attack2.wav", 1, ATTN_NORM);
|
||||||
|
|
||||||
|
PRJ_FireProjectile(self,
|
||||||
|
"progs/v_spike.mdl",
|
||||||
|
self.origin + '0 0 10',
|
||||||
|
dir * 400,
|
||||||
|
PE_EXPLOSION,
|
||||||
|
0,
|
||||||
|
0,
|
||||||
|
30);
|
||||||
|
PRJ_SetRadiusDamage(40, 80, MOD_SHALRATH);
|
||||||
|
PRJ_SetThink(ShalHome, flytime, 0.2);
|
||||||
|
PRJ_SetTouch(ShalMissileTouch);
|
||||||
|
newmis.avelocity = '300 300 300';
|
||||||
|
newmis.enemy = self.enemy;
|
||||||
|
};
|
||||||
|
|
||||||
|
void() ShalHome =
|
||||||
|
{
|
||||||
|
local vector dir, vtemp;
|
||||||
|
vtemp = self.enemy.origin + '0 0 10';
|
||||||
|
if (self.enemy.health < 1)
|
||||||
|
{
|
||||||
|
remove(self);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
dir = normalize(vtemp - self.origin);
|
||||||
|
if (skill > 2)
|
||||||
|
self.velocity = dir * 350;
|
||||||
|
else
|
||||||
|
self.velocity = dir * 250;
|
||||||
|
};
|
||||||
|
|
||||||
|
float() ShalMissileTouch =
|
||||||
|
{
|
||||||
|
if (other.classname == "monster_zombie")
|
||||||
|
T_Damage (other, self, self, 110, MOD_SHALRATH);
|
||||||
|
|
||||||
|
return 0; // always explode on touch
|
||||||
|
};
|
||||||
|
|
||||||
|
//=================================================================
|
||||||
|
|
||||||
|
/*QUAKED monster_shalrath (1 0 0) (-32 -32 -24) (32 32 48) Ambush
|
||||||
|
*/
|
||||||
|
void() monster_shalrath =
|
||||||
|
{
|
||||||
|
if (deathmatch)
|
||||||
|
{
|
||||||
|
remove(self);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
precache_model2 ("progs/shalrath.mdl");
|
||||||
|
precache_model2 ("progs/h_shal.mdl");
|
||||||
|
precache_model2 ("progs/v_spike.mdl");
|
||||||
|
|
||||||
|
precache_sound2 ("shalrath/attack.wav");
|
||||||
|
precache_sound2 ("shalrath/attack2.wav");
|
||||||
|
precache_sound2 ("shalrath/death.wav");
|
||||||
|
precache_sound2 ("shalrath/idle.wav");
|
||||||
|
precache_sound2 ("shalrath/pain.wav");
|
||||||
|
precache_sound2 ("shalrath/sight.wav");
|
||||||
|
|
||||||
|
self.solid = SOLID_SLIDEBOX;
|
||||||
|
self.movetype = MOVETYPE_STEP;
|
||||||
|
|
||||||
|
setmodel (self, "progs/shalrath.mdl");
|
||||||
|
setsize (self, VEC_HULL2_MIN, VEC_HULL2_MAX);
|
||||||
|
self.health = 400;
|
||||||
|
|
||||||
|
self.th_stand = shal_stand;
|
||||||
|
self.th_walk = shal_walk1;
|
||||||
|
self.th_run = shal_run1;
|
||||||
|
self.th_die = shalrath_die;
|
||||||
|
self.th_pain = shalrath_pain;
|
||||||
|
self.th_missile = shal_attack1;
|
||||||
|
|
||||||
|
self.think = walkmonster_start;
|
||||||
|
self.nextthink = time + 0.1 + random ()*0.1;
|
||||||
|
|
||||||
|
};
|
339
quakec/basemod/shambler.qc
Normal file
339
quakec/basemod/shambler.qc
Normal file
|
@ -0,0 +1,339 @@
|
||||||
|
/*
|
||||||
|
==============================================================================
|
||||||
|
|
||||||
|
SHAMBLER
|
||||||
|
|
||||||
|
==============================================================================
|
||||||
|
*/
|
||||||
|
|
||||||
|
$cd id1/models/shams
|
||||||
|
$origin 0 0 24
|
||||||
|
$base base
|
||||||
|
$skin base
|
||||||
|
|
||||||
|
$frame stand1 stand2 stand3 stand4 stand5 stand6 stand7 stand8 stand9
|
||||||
|
$frame stand10 stand11 stand12 stand13 stand14 stand15 stand16 stand17
|
||||||
|
|
||||||
|
$frame walk1 walk2 walk3 walk4 walk5 walk6 walk7
|
||||||
|
$frame walk8 walk9 walk10 walk11 walk12
|
||||||
|
|
||||||
|
$frame run1 run2 run3 run4 run5 run6
|
||||||
|
|
||||||
|
$frame smash1 smash2 smash3 smash4 smash5 smash6 smash7
|
||||||
|
$frame smash8 smash9 smash10 smash11 smash12
|
||||||
|
|
||||||
|
$frame swingr1 swingr2 swingr3 swingr4 swingr5
|
||||||
|
$frame swingr6 swingr7 swingr8 swingr9
|
||||||
|
|
||||||
|
$frame swingl1 swingl2 swingl3 swingl4 swingl5
|
||||||
|
$frame swingl6 swingl7 swingl8 swingl9
|
||||||
|
|
||||||
|
$frame magic1 magic2 magic3 magic4 magic5
|
||||||
|
$frame magic6 magic7 magic8 magic9 magic10 magic11 magic12
|
||||||
|
|
||||||
|
$frame pain1 pain2 pain3 pain4 pain5 pain6
|
||||||
|
|
||||||
|
$frame death1 death2 death3 death4 death5 death6
|
||||||
|
$frame death7 death8 death9 death10 death11
|
||||||
|
|
||||||
|
void(float chrg, float damage, float side, float crnd) ShamClaw =
|
||||||
|
{
|
||||||
|
local vector delta;
|
||||||
|
local float ldmg;
|
||||||
|
|
||||||
|
if (!self.enemy)
|
||||||
|
return;
|
||||||
|
ai_charge(chrg);
|
||||||
|
|
||||||
|
delta = self.enemy.origin - self.origin;
|
||||||
|
|
||||||
|
if (vlen(delta) > 100)
|
||||||
|
return;
|
||||||
|
|
||||||
|
ldmg = (random() + random() + random()) * damage;
|
||||||
|
T_Damage (self.enemy, self, self, ldmg, MOD_SHAMBLER);
|
||||||
|
sound (self, CHAN_VOICE, "shambler/smack.wav", 1, ATTN_NORM);
|
||||||
|
|
||||||
|
if (side)
|
||||||
|
{
|
||||||
|
makevectors (self.angles);
|
||||||
|
SpawnMeatSpray (self.origin + v_forward*16, (crandom() * crnd + side) * v_right);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
void() sham_stand1 =[ $stand1, sham_stand2 ] {ai_stand();};
|
||||||
|
void() sham_stand2 =[ $stand2, sham_stand3 ] {ai_stand();};
|
||||||
|
void() sham_stand3 =[ $stand3, sham_stand4 ] {ai_stand();};
|
||||||
|
void() sham_stand4 =[ $stand4, sham_stand5 ] {ai_stand();};
|
||||||
|
void() sham_stand5 =[ $stand5, sham_stand6 ] {ai_stand();};
|
||||||
|
void() sham_stand6 =[ $stand6, sham_stand7 ] {ai_stand();};
|
||||||
|
void() sham_stand7 =[ $stand7, sham_stand8 ] {ai_stand();};
|
||||||
|
void() sham_stand8 =[ $stand8, sham_stand9 ] {ai_stand();};
|
||||||
|
void() sham_stand9 =[ $stand9, sham_stand10] {ai_stand();};
|
||||||
|
void() sham_stand10 =[ $stand10, sham_stand11] {ai_stand();};
|
||||||
|
void() sham_stand11 =[ $stand11, sham_stand12] {ai_stand();};
|
||||||
|
void() sham_stand12 =[ $stand12, sham_stand13] {ai_stand();};
|
||||||
|
void() sham_stand13 =[ $stand13, sham_stand14] {ai_stand();};
|
||||||
|
void() sham_stand14 =[ $stand14, sham_stand15] {ai_stand();};
|
||||||
|
void() sham_stand15 =[ $stand15, sham_stand16] {ai_stand();};
|
||||||
|
void() sham_stand16 =[ $stand16, sham_stand17] {ai_stand();};
|
||||||
|
void() sham_stand17 =[ $stand17, sham_stand1 ] {ai_stand();};
|
||||||
|
|
||||||
|
void() sham_walk1 =[ $walk1, sham_walk2 ] {ai_walk(10);};
|
||||||
|
void() sham_walk2 =[ $walk2, sham_walk3 ] {ai_walk(9);};
|
||||||
|
void() sham_walk3 =[ $walk3, sham_walk4 ] {ai_walk(9);};
|
||||||
|
void() sham_walk4 =[ $walk4, sham_walk5 ] {ai_walk(5);};
|
||||||
|
void() sham_walk5 =[ $walk5, sham_walk6 ] {ai_walk(6);};
|
||||||
|
void() sham_walk6 =[ $walk6, sham_walk7 ] {ai_walk(12);};
|
||||||
|
void() sham_walk7 =[ $walk7, sham_walk8 ] {ai_walk(8);};
|
||||||
|
void() sham_walk8 =[ $walk8, sham_walk9 ] {ai_walk(3);};
|
||||||
|
void() sham_walk9 =[ $walk9, sham_walk10] {ai_walk(13);};
|
||||||
|
void() sham_walk10 =[ $walk10, sham_walk11] {ai_walk(9);};
|
||||||
|
void() sham_walk11 =[ $walk11, sham_walk12] {ai_walk(7);};
|
||||||
|
void() sham_walk12 =[ $walk12, sham_walk1 ] {ai_walk(7);
|
||||||
|
if (random() > 0.8)
|
||||||
|
sound (self, CHAN_VOICE, "shambler/sidle.wav", 1, ATTN_IDLE);};
|
||||||
|
|
||||||
|
void() sham_run1 =[ $run1, sham_run2 ] {ai_run(20);};
|
||||||
|
void() sham_run2 =[ $run2, sham_run3 ] {ai_run(24);};
|
||||||
|
void() sham_run3 =[ $run3, sham_run4 ] {ai_run(20);};
|
||||||
|
void() sham_run4 =[ $run4, sham_run5 ] {ai_run(20);};
|
||||||
|
void() sham_run5 =[ $run5, sham_run6 ] {ai_run(24);};
|
||||||
|
void() sham_run6 =[ $run6, sham_run1 ] {ai_run(20);
|
||||||
|
if (random() > 0.8)
|
||||||
|
sound (self, CHAN_VOICE, "shambler/sidle.wav", 1, ATTN_IDLE);
|
||||||
|
};
|
||||||
|
|
||||||
|
void() sham_smash1 =[ $smash1, sham_smash2 ] {
|
||||||
|
sound (self, CHAN_VOICE, "shambler/melee1.wav", 1, ATTN_NORM);
|
||||||
|
ai_charge(2);};
|
||||||
|
void() sham_smash2 =[ $smash2, sham_smash3 ] {ai_charge(6);};
|
||||||
|
void() sham_smash3 =[ $smash3, sham_smash4 ] {ai_charge(6);};
|
||||||
|
void() sham_smash4 =[ $smash4, sham_smash5 ] {ai_charge(5);};
|
||||||
|
void() sham_smash5 =[ $smash5, sham_smash6 ] {ai_charge(4);};
|
||||||
|
void() sham_smash6 =[ $smash6, sham_smash7 ] {ai_charge(1);};
|
||||||
|
void() sham_smash7 =[ $smash7, sham_smash8 ] {ai_charge(0);};
|
||||||
|
void() sham_smash8 =[ $smash8, sham_smash9 ] {ai_charge(0);};
|
||||||
|
void() sham_smash9 =[ $smash9, sham_smash10 ] {ai_charge(0);};
|
||||||
|
void() sham_smash10 =[ $smash10, sham_smash11 ] {ShamClaw(0, 40, 0, 100);};
|
||||||
|
void() sham_smash11 =[ $smash11, sham_smash12 ] {ai_charge(5);};
|
||||||
|
void() sham_smash12 =[ $smash12, sham_run1 ] {ai_charge(4);};
|
||||||
|
|
||||||
|
void() sham_swingr1;
|
||||||
|
|
||||||
|
void() sham_swingl1 =[ $swingl1, sham_swingl2 ] {
|
||||||
|
sound (self, CHAN_VOICE, "shambler/melee2.wav", 1, ATTN_NORM);
|
||||||
|
ai_charge(5);};
|
||||||
|
void() sham_swingl2 =[ $swingl2, sham_swingl3 ] {ai_charge(3);};
|
||||||
|
void() sham_swingl3 =[ $swingl3, sham_swingl4 ] {ai_charge(7);};
|
||||||
|
void() sham_swingl4 =[ $swingl4, sham_swingl5 ] {ai_charge(3);};
|
||||||
|
void() sham_swingl5 =[ $swingl5, sham_swingl6 ] {ai_charge(7);};
|
||||||
|
void() sham_swingl6 =[ $swingl6, sham_swingl7 ] {ai_charge(9);};
|
||||||
|
void() sham_swingl7 =[ $swingl7, sham_swingl8 ] {ai_charge(5); ShamClaw(10, 20, 250, 0);};
|
||||||
|
void() sham_swingl8 =[ $swingl8, sham_swingl9 ] {ai_charge(4);};
|
||||||
|
void() sham_swingl9 =[ $swingl9, sham_run1 ] {
|
||||||
|
ai_charge(8);
|
||||||
|
if (random()<0.5)
|
||||||
|
self.think = sham_swingr1;
|
||||||
|
};
|
||||||
|
|
||||||
|
void() sham_swingr1 =[ $swingr1, sham_swingr2 ] {
|
||||||
|
sound (self, CHAN_VOICE, "shambler/melee1.wav", 1, ATTN_NORM);
|
||||||
|
ai_charge(1);};
|
||||||
|
void() sham_swingr2 =[ $swingr2, sham_swingr3 ] {ai_charge(8);};
|
||||||
|
void() sham_swingr3 =[ $swingr3, sham_swingr4 ] {ai_charge(14);};
|
||||||
|
void() sham_swingr4 =[ $swingr4, sham_swingr5 ] {ai_charge(7);};
|
||||||
|
void() sham_swingr5 =[ $swingr5, sham_swingr6 ] {ai_charge(3);};
|
||||||
|
void() sham_swingr6 =[ $swingr6, sham_swingr7 ] {ai_charge(6);};
|
||||||
|
void() sham_swingr7 =[ $swingr7, sham_swingr8 ] {ai_charge(6); ShamClaw(10, 20, -250, 0);};
|
||||||
|
void() sham_swingr8 =[ $swingr8, sham_swingr9 ] {ai_charge(3);};
|
||||||
|
void() sham_swingr9 =[ $swingr9, sham_run1 ] {ai_charge(1);
|
||||||
|
ai_charge(10);
|
||||||
|
if (random()<0.5)
|
||||||
|
self.think = sham_swingl1;
|
||||||
|
};
|
||||||
|
|
||||||
|
void() sham_melee =
|
||||||
|
{
|
||||||
|
local float chance;
|
||||||
|
|
||||||
|
chance = random();
|
||||||
|
if (chance > 0.6 || self.health == 600)
|
||||||
|
sham_smash1 ();
|
||||||
|
else if (chance > 0.3)
|
||||||
|
sham_swingr1 ();
|
||||||
|
else
|
||||||
|
sham_swingl1 ();
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
|
||||||
|
void() CastLightning =
|
||||||
|
{
|
||||||
|
local vector org, dir;
|
||||||
|
|
||||||
|
muzzleflash();
|
||||||
|
ai_face ();
|
||||||
|
|
||||||
|
org = self.origin + '0 0 40';
|
||||||
|
|
||||||
|
dir = self.enemy.origin + '0 0 16' - org;
|
||||||
|
dir = normalize (dir);
|
||||||
|
|
||||||
|
traceline (org, self.origin + dir*600, TRUE, self);
|
||||||
|
|
||||||
|
TE_lightning1(self, org, trace_endpos);
|
||||||
|
|
||||||
|
LightningDamage (org, trace_endpos, self, 10, MOD_SHAMBLER);
|
||||||
|
};
|
||||||
|
|
||||||
|
void() sham_magic1 =[ $magic1, sham_magic2 ] {ai_face();
|
||||||
|
sound (self, CHAN_WEAPON, "shambler/sattck1.wav", 1, ATTN_NORM);
|
||||||
|
};
|
||||||
|
void() sham_magic2 =[ $magic2, sham_magic3 ] {ai_face();};
|
||||||
|
void() sham_magic3 =[ $magic3, sham_magic4 ] {ai_face();self.nextthink = time + 0.2;
|
||||||
|
local entity o;
|
||||||
|
|
||||||
|
muzzleflash();
|
||||||
|
ai_face();
|
||||||
|
// TODO: Spawn as an effect
|
||||||
|
self.owner = spawn();
|
||||||
|
o = self.owner;
|
||||||
|
setmodel (o, "progs/s_light.mdl");
|
||||||
|
setorigin (o, self.origin);
|
||||||
|
o.angles = self.angles;
|
||||||
|
o.nextthink = time + 0.7;
|
||||||
|
o.think = SUB_Remove;
|
||||||
|
};
|
||||||
|
void() sham_magic4 =[ $magic4, sham_magic5 ]
|
||||||
|
{
|
||||||
|
self.effects = self.effects | EF_MUZZLEFLASH;
|
||||||
|
self.owner.frame = 1;
|
||||||
|
};
|
||||||
|
void() sham_magic5 =[ $magic5, sham_magic6 ]
|
||||||
|
{
|
||||||
|
self.effects = self.effects | EF_MUZZLEFLASH;
|
||||||
|
self.owner.frame = 2;
|
||||||
|
};
|
||||||
|
void() sham_magic6 =[ $magic6, sham_magic9 ]
|
||||||
|
{
|
||||||
|
remove (self.owner);
|
||||||
|
CastLightning();
|
||||||
|
sound (self, CHAN_WEAPON, "shambler/sboom.wav", 1, ATTN_NORM);
|
||||||
|
};
|
||||||
|
void() sham_magic9 =[ $magic9, sham_magic10 ]
|
||||||
|
{CastLightning();};
|
||||||
|
void() sham_magic10 =[ $magic10, sham_magic11 ]
|
||||||
|
{CastLightning();};
|
||||||
|
void() sham_magic11 =[ $magic11, sham_magic12 ]
|
||||||
|
{
|
||||||
|
if (skill > 2)
|
||||||
|
CastLightning();
|
||||||
|
};
|
||||||
|
void() sham_magic12 =[ $magic12, sham_run1 ] {};
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
void() sham_pain1 =[ $pain1, sham_pain2 ] {};
|
||||||
|
void() sham_pain2 =[ $pain2, sham_pain3 ] {};
|
||||||
|
void() sham_pain3 =[ $pain3, sham_pain4 ] {};
|
||||||
|
void() sham_pain4 =[ $pain4, sham_pain5 ] {};
|
||||||
|
void() sham_pain5 =[ $pain5, sham_pain6 ] {};
|
||||||
|
void() sham_pain6 =[ $pain6, sham_run1 ] {};
|
||||||
|
|
||||||
|
void(entity attacker, float damage) sham_pain =
|
||||||
|
{
|
||||||
|
sound (self, CHAN_VOICE, "shambler/shurt2.wav", 1, ATTN_NORM);
|
||||||
|
|
||||||
|
if (self.health <= 0)
|
||||||
|
return; // allready dying, don't go into pain frame
|
||||||
|
|
||||||
|
if (random()*400 > damage)
|
||||||
|
return; // didn't flinch
|
||||||
|
|
||||||
|
if (self.pain_finished > time)
|
||||||
|
return;
|
||||||
|
self.pain_finished = time + 2;
|
||||||
|
|
||||||
|
sham_pain1 ();
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
|
||||||
|
void() sham_death1 =[ $death1, sham_death2 ] {};
|
||||||
|
void() sham_death2 =[ $death2, sham_death3 ] {};
|
||||||
|
void() sham_death3 =[ $death3, sham_death4 ] {self.solid = SOLID_NOT;};
|
||||||
|
void() sham_death4 =[ $death4, sham_death5 ] {};
|
||||||
|
void() sham_death5 =[ $death5, sham_death6 ] {};
|
||||||
|
void() sham_death6 =[ $death6, sham_death7 ] {};
|
||||||
|
void() sham_death7 =[ $death7, sham_death8 ] {};
|
||||||
|
void() sham_death8 =[ $death8, sham_death9 ] {};
|
||||||
|
void() sham_death9 =[ $death9, sham_death10 ] {};
|
||||||
|
void() sham_death10 =[ $death10, sham_death11 ] {};
|
||||||
|
void() sham_death11 =[ $death11, sham_death11 ] {};
|
||||||
|
|
||||||
|
void() sham_die =
|
||||||
|
{
|
||||||
|
// check for gib
|
||||||
|
if (self.health < -60)
|
||||||
|
{
|
||||||
|
sound (self, CHAN_VOICE, "player/udeath.wav", 1, ATTN_NORM);
|
||||||
|
ThrowHead ("progs/h_shams.mdl", self.health);
|
||||||
|
ThrowGib ("progs/gib1.mdl", self.health);
|
||||||
|
ThrowGib ("progs/gib2.mdl", self.health);
|
||||||
|
ThrowGib ("progs/gib3.mdl", self.health);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// regular death
|
||||||
|
sound (self, CHAN_VOICE, "shambler/sdeath.wav", 1, ATTN_NORM);
|
||||||
|
sham_death1 ();
|
||||||
|
};
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
|
||||||
|
|
||||||
|
/*QUAKED monster_shambler (1 0 0) (-32 -32 -24) (32 32 64) Ambush
|
||||||
|
*/
|
||||||
|
void() monster_shambler =
|
||||||
|
{
|
||||||
|
if (deathmatch)
|
||||||
|
{
|
||||||
|
remove(self);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
precache_model ("progs/shambler.mdl");
|
||||||
|
precache_model ("progs/s_light.mdl");
|
||||||
|
precache_model ("progs/h_shams.mdl");
|
||||||
|
precache_model ("progs/bolt.mdl");
|
||||||
|
|
||||||
|
precache_sound ("shambler/sattck1.wav");
|
||||||
|
precache_sound ("shambler/sboom.wav");
|
||||||
|
precache_sound ("shambler/sdeath.wav");
|
||||||
|
precache_sound ("shambler/shurt2.wav");
|
||||||
|
precache_sound ("shambler/sidle.wav");
|
||||||
|
precache_sound ("shambler/ssight.wav");
|
||||||
|
precache_sound ("shambler/melee1.wav");
|
||||||
|
precache_sound ("shambler/melee2.wav");
|
||||||
|
precache_sound ("shambler/smack.wav");
|
||||||
|
|
||||||
|
self.solid = SOLID_SLIDEBOX;
|
||||||
|
self.movetype = MOVETYPE_STEP;
|
||||||
|
setmodel (self, "progs/shambler.mdl");
|
||||||
|
|
||||||
|
setsize (self, VEC_HULL2_MIN, VEC_HULL2_MAX);
|
||||||
|
self.health = 600;
|
||||||
|
|
||||||
|
self.th_stand = sham_stand1;
|
||||||
|
self.th_walk = sham_walk1;
|
||||||
|
self.th_run = sham_run1;
|
||||||
|
self.th_die = sham_die;
|
||||||
|
self.th_melee = sham_melee;
|
||||||
|
self.th_missile = sham_magic1;
|
||||||
|
self.th_pain = sham_pain;
|
||||||
|
|
||||||
|
walkmonster_start();
|
||||||
|
};
|
282
quakec/basemod/soldier.qc
Normal file
282
quakec/basemod/soldier.qc
Normal file
|
@ -0,0 +1,282 @@
|
||||||
|
/*
|
||||||
|
==============================================================================
|
||||||
|
|
||||||
|
SOLDIER / PLAYER
|
||||||
|
|
||||||
|
==============================================================================
|
||||||
|
*/
|
||||||
|
|
||||||
|
$cd id1/models/soldier3
|
||||||
|
$origin 0 -6 24
|
||||||
|
$base base
|
||||||
|
$skin skin
|
||||||
|
|
||||||
|
$frame stand1 stand2 stand3 stand4 stand5 stand6 stand7 stand8
|
||||||
|
|
||||||
|
$frame death1 death2 death3 death4 death5 death6 death7 death8
|
||||||
|
$frame death9 death10
|
||||||
|
|
||||||
|
$frame deathc1 deathc2 deathc3 deathc4 deathc5 deathc6 deathc7 deathc8
|
||||||
|
$frame deathc9 deathc10 deathc11
|
||||||
|
|
||||||
|
$frame load1 load2 load3 load4 load5 load6 load7 load8 load9 load10 load11
|
||||||
|
|
||||||
|
$frame pain1 pain2 pain3 pain4 pain5 pain6
|
||||||
|
|
||||||
|
$frame painb1 painb2 painb3 painb4 painb5 painb6 painb7 painb8 painb9 painb10
|
||||||
|
$frame painb11 painb12 painb13 painb14
|
||||||
|
|
||||||
|
$frame painc1 painc2 painc3 painc4 painc5 painc6 painc7 painc8 painc9 painc10
|
||||||
|
$frame painc11 painc12 painc13
|
||||||
|
|
||||||
|
$frame run1 run2 run3 run4 run5 run6 run7 run8
|
||||||
|
|
||||||
|
$frame shoot1 shoot2 shoot3 shoot4 shoot5 shoot6 shoot7 shoot8 shoot9
|
||||||
|
|
||||||
|
$frame prowl_1 prowl_2 prowl_3 prowl_4 prowl_5 prowl_6 prowl_7 prowl_8
|
||||||
|
$frame prowl_9 prowl_10 prowl_11 prowl_12 prowl_13 prowl_14 prowl_15 prowl_16
|
||||||
|
$frame prowl_17 prowl_18 prowl_19 prowl_20 prowl_21 prowl_22 prowl_23 prowl_24
|
||||||
|
|
||||||
|
/*
|
||||||
|
==============================================================================
|
||||||
|
SOLDIER CODE
|
||||||
|
==============================================================================
|
||||||
|
*/
|
||||||
|
|
||||||
|
void() army_fire;
|
||||||
|
|
||||||
|
void() army_stand1 =[ $stand1, army_stand2 ] {ai_stand();};
|
||||||
|
void() army_stand2 =[ $stand2, army_stand3 ] {ai_stand();};
|
||||||
|
void() army_stand3 =[ $stand3, army_stand4 ] {ai_stand();};
|
||||||
|
void() army_stand4 =[ $stand4, army_stand5 ] {ai_stand();};
|
||||||
|
void() army_stand5 =[ $stand5, army_stand6 ] {ai_stand();};
|
||||||
|
void() army_stand6 =[ $stand6, army_stand7 ] {ai_stand();};
|
||||||
|
void() army_stand7 =[ $stand7, army_stand8 ] {ai_stand();};
|
||||||
|
void() army_stand8 =[ $stand8, army_stand1 ] {ai_stand();};
|
||||||
|
|
||||||
|
void() army_walk1 =[ $prowl_1, army_walk2 ] {
|
||||||
|
if (random() < 0.2)
|
||||||
|
sound (self, CHAN_VOICE, "soldier/idle.wav", 1, ATTN_IDLE);
|
||||||
|
ai_walk(1);};
|
||||||
|
void() army_walk2 =[ $prowl_2, army_walk3 ] {ai_walk(1);};
|
||||||
|
void() army_walk3 =[ $prowl_3, army_walk4 ] {ai_walk(1);};
|
||||||
|
void() army_walk4 =[ $prowl_4, army_walk5 ] {ai_walk(1);};
|
||||||
|
void() army_walk5 =[ $prowl_5, army_walk6 ] {ai_walk(2);};
|
||||||
|
void() army_walk6 =[ $prowl_6, army_walk7 ] {ai_walk(3);};
|
||||||
|
void() army_walk7 =[ $prowl_7, army_walk8 ] {ai_walk(4);};
|
||||||
|
void() army_walk8 =[ $prowl_8, army_walk9 ] {ai_walk(4);};
|
||||||
|
void() army_walk9 =[ $prowl_9, army_walk10 ] {ai_walk(2);};
|
||||||
|
void() army_walk10 =[ $prowl_10, army_walk11 ] {ai_walk(2);};
|
||||||
|
void() army_walk11 =[ $prowl_11, army_walk12 ] {ai_walk(2);};
|
||||||
|
void() army_walk12 =[ $prowl_12, army_walk13 ] {ai_walk(1);};
|
||||||
|
void() army_walk13 =[ $prowl_13, army_walk14 ] {ai_walk(0);};
|
||||||
|
void() army_walk14 =[ $prowl_14, army_walk15 ] {ai_walk(1);};
|
||||||
|
void() army_walk15 =[ $prowl_15, army_walk16 ] {ai_walk(1);};
|
||||||
|
void() army_walk16 =[ $prowl_16, army_walk17 ] {ai_walk(1);};
|
||||||
|
void() army_walk17 =[ $prowl_17, army_walk18 ] {ai_walk(3);};
|
||||||
|
void() army_walk18 =[ $prowl_18, army_walk19 ] {ai_walk(3);};
|
||||||
|
void() army_walk19 =[ $prowl_19, army_walk20 ] {ai_walk(3);};
|
||||||
|
void() army_walk20 =[ $prowl_20, army_walk21 ] {ai_walk(3);};
|
||||||
|
void() army_walk21 =[ $prowl_21, army_walk22 ] {ai_walk(2);};
|
||||||
|
void() army_walk22 =[ $prowl_22, army_walk23 ] {ai_walk(1);};
|
||||||
|
void() army_walk23 =[ $prowl_23, army_walk24 ] {ai_walk(1);};
|
||||||
|
void() army_walk24 =[ $prowl_24, army_walk1 ] {ai_walk(1);};
|
||||||
|
|
||||||
|
void() army_run1 =[ $run1, army_run2 ] {
|
||||||
|
if (random() < 0.2)
|
||||||
|
sound (self, CHAN_VOICE, "soldier/idle.wav", 1, ATTN_IDLE);
|
||||||
|
ai_run(11);};
|
||||||
|
void() army_run2 =[ $run2, army_run3 ] {ai_run(15);};
|
||||||
|
void() army_run3 =[ $run3, army_run4 ] {ai_run(10);};
|
||||||
|
void() army_run4 =[ $run4, army_run5 ] {ai_run(10);};
|
||||||
|
void() army_run5 =[ $run5, army_run6 ] {ai_run(8);};
|
||||||
|
void() army_run6 =[ $run6, army_run7 ] {ai_run(15);};
|
||||||
|
void() army_run7 =[ $run7, army_run8 ] {ai_run(10);};
|
||||||
|
void() army_run8 =[ $run8, army_run1 ] {ai_run(8);};
|
||||||
|
|
||||||
|
void() army_atk1 =[ $shoot1, army_atk2 ] {ai_face();};
|
||||||
|
void() army_atk2 =[ $shoot2, army_atk3 ] {ai_face();};
|
||||||
|
void() army_atk3 =[ $shoot3, army_atk4 ] {ai_face();};
|
||||||
|
void() army_atk4 =[ $shoot4, army_atk5 ] {ai_face();};
|
||||||
|
void() army_atk5 =[ $shoot5, army_atk6 ] {ai_face(); army_fire(); muzzleflash();};
|
||||||
|
void() army_atk6 =[ $shoot6, army_atk7 ] {ai_face();};
|
||||||
|
void() army_atk7 =[ $shoot7, army_atk8 ] {ai_face();SUB_CheckRefire (army_atk1);};
|
||||||
|
void() army_atk8 =[ $shoot8, army_atk9 ] {ai_face();};
|
||||||
|
void() army_atk9 =[ $shoot9, army_run1 ] {ai_face();};
|
||||||
|
|
||||||
|
|
||||||
|
void() army_pain1 =[ $pain1, army_pain2 ] {};
|
||||||
|
void() army_pain2 =[ $pain2, army_pain3 ] {};
|
||||||
|
void() army_pain3 =[ $pain3, army_pain4 ] {};
|
||||||
|
void() army_pain4 =[ $pain4, army_pain5 ] {};
|
||||||
|
void() army_pain5 =[ $pain5, army_pain6 ] {};
|
||||||
|
void() army_pain6 =[ $pain6, army_run1 ] {ai_pain(1);};
|
||||||
|
|
||||||
|
void() army_painb1 =[ $painb1, army_painb2 ] {};
|
||||||
|
void() army_painb2 =[ $painb2, army_painb3 ] {ai_painforward(13);};
|
||||||
|
void() army_painb3 =[ $painb3, army_painb4 ] {ai_painforward(9);};
|
||||||
|
void() army_painb4 =[ $painb4, army_painb5 ] {};
|
||||||
|
void() army_painb5 =[ $painb5, army_painb6 ] {};
|
||||||
|
void() army_painb6 =[ $painb6, army_painb7 ] {};
|
||||||
|
void() army_painb7 =[ $painb7, army_painb8 ] {};
|
||||||
|
void() army_painb8 =[ $painb8, army_painb9 ] {};
|
||||||
|
void() army_painb9 =[ $painb9, army_painb10] {};
|
||||||
|
void() army_painb10=[ $painb10, army_painb11] {};
|
||||||
|
void() army_painb11=[ $painb11, army_painb12] {};
|
||||||
|
void() army_painb12=[ $painb12, army_painb13] {ai_pain(2);};
|
||||||
|
void() army_painb13=[ $painb13, army_painb14] {};
|
||||||
|
void() army_painb14=[ $painb14, army_run1 ] {};
|
||||||
|
|
||||||
|
void() army_painc1 =[ $painc1, army_painc2 ] {};
|
||||||
|
void() army_painc2 =[ $painc2, army_painc3 ] {ai_pain(1);};
|
||||||
|
void() army_painc3 =[ $painc3, army_painc4 ] {};
|
||||||
|
void() army_painc4 =[ $painc4, army_painc5 ] {};
|
||||||
|
void() army_painc5 =[ $painc5, army_painc6 ] {ai_painforward(1);};
|
||||||
|
void() army_painc6 =[ $painc6, army_painc7 ] {ai_painforward(1);};
|
||||||
|
void() army_painc7 =[ $painc7, army_painc8 ] {};
|
||||||
|
void() army_painc8 =[ $painc8, army_painc9 ] {ai_pain(1);};
|
||||||
|
void() army_painc9 =[ $painc9, army_painc10] {ai_painforward(4);};
|
||||||
|
void() army_painc10=[ $painc10, army_painc11] {ai_painforward(3);};
|
||||||
|
void() army_painc11=[ $painc11, army_painc12] {ai_painforward(6);};
|
||||||
|
void() army_painc12=[ $painc12, army_painc13] {ai_painforward(8);};
|
||||||
|
void() army_painc13=[ $painc13, army_run1] {};
|
||||||
|
|
||||||
|
void(entity attacker, float damage) army_pain =
|
||||||
|
{
|
||||||
|
local float r;
|
||||||
|
|
||||||
|
if (self.pain_finished > time)
|
||||||
|
return;
|
||||||
|
|
||||||
|
r = random();
|
||||||
|
|
||||||
|
if (r < 0.2)
|
||||||
|
{
|
||||||
|
self.pain_finished = time + 0.6;
|
||||||
|
army_pain1 ();
|
||||||
|
sound (self, CHAN_VOICE, "soldier/pain1.wav", 1, ATTN_NORM);
|
||||||
|
}
|
||||||
|
else if (r < 0.6)
|
||||||
|
{
|
||||||
|
self.pain_finished = time + 1.1;
|
||||||
|
army_painb1 ();
|
||||||
|
sound (self, CHAN_VOICE, "soldier/pain2.wav", 1, ATTN_NORM);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
self.pain_finished = time + 1.1;
|
||||||
|
army_painc1 ();
|
||||||
|
sound (self, CHAN_VOICE, "soldier/pain2.wav", 1, ATTN_NORM);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
void() army_fire =
|
||||||
|
{
|
||||||
|
local vector dir;
|
||||||
|
local entity en;
|
||||||
|
|
||||||
|
ai_face();
|
||||||
|
|
||||||
|
sound (self, CHAN_WEAPON, "soldier/sattck1.wav", 1, ATTN_NORM);
|
||||||
|
|
||||||
|
// fire somewhat behind the player, so a dodging player is harder to hit
|
||||||
|
en = self.enemy;
|
||||||
|
|
||||||
|
dir = en.origin - en.velocity*0.2;
|
||||||
|
dir = normalize (dir - self.origin);
|
||||||
|
|
||||||
|
FireBullets (4, dir, '0.1 0.1 0', MOD_SOLDIER);
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
void() army_die1 =[ $death1, army_die2 ] {};
|
||||||
|
void() army_die2 =[ $death2, army_die3 ] {};
|
||||||
|
void() army_die3 =[ $death3, army_die4 ] {self.solid = SOLID_NOT;DropBackpack();};
|
||||||
|
void() army_die4 =[ $death4, army_die5 ] {};
|
||||||
|
void() army_die5 =[ $death5, army_die6 ] {};
|
||||||
|
void() army_die6 =[ $death6, army_die7 ] {};
|
||||||
|
void() army_die7 =[ $death7, army_die8 ] {};
|
||||||
|
void() army_die8 =[ $death8, army_die9 ] {};
|
||||||
|
void() army_die9 =[ $death9, army_die10 ] {};
|
||||||
|
void() army_die10 =[ $death10, army_die10 ] {};
|
||||||
|
|
||||||
|
void() army_cdie1 =[ $deathc1, army_cdie2 ] {};
|
||||||
|
void() army_cdie2 =[ $deathc2, army_cdie3 ] {ai_back(5);};
|
||||||
|
void() army_cdie3 =[ $deathc3, army_cdie4 ] {self.solid = SOLID_NOT;DropBackpack();ai_back(4);};
|
||||||
|
void() army_cdie4 =[ $deathc4, army_cdie5 ] {ai_back(13);};
|
||||||
|
void() army_cdie5 =[ $deathc5, army_cdie6 ] {ai_back(3);};
|
||||||
|
void() army_cdie6 =[ $deathc6, army_cdie7 ] {ai_back(4);};
|
||||||
|
void() army_cdie7 =[ $deathc7, army_cdie8 ] {};
|
||||||
|
void() army_cdie8 =[ $deathc8, army_cdie9 ] {};
|
||||||
|
void() army_cdie9 =[ $deathc9, army_cdie10 ] {};
|
||||||
|
void() army_cdie10 =[ $deathc10, army_cdie11 ] {};
|
||||||
|
void() army_cdie11 =[ $deathc11, army_cdie11 ] {};
|
||||||
|
|
||||||
|
|
||||||
|
void() army_die =
|
||||||
|
{
|
||||||
|
// check for gib
|
||||||
|
if (self.health < -35)
|
||||||
|
{
|
||||||
|
sound (self, CHAN_VOICE, "player/udeath.wav", 1, ATTN_NORM);
|
||||||
|
ThrowHead ("progs/h_guard.mdl", self.health);
|
||||||
|
ThrowGib ("progs/gib1.mdl", self.health);
|
||||||
|
ThrowGib ("progs/gib2.mdl", self.health);
|
||||||
|
ThrowGib ("progs/gib3.mdl", self.health);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// regular death
|
||||||
|
sound (self, CHAN_VOICE, "soldier/death1.wav", 1, ATTN_NORM);
|
||||||
|
if (random() < 0.5)
|
||||||
|
army_die1 ();
|
||||||
|
else
|
||||||
|
army_cdie1 ();
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
/*QUAKED monster_army (1 0 0) (-16 -16 -24) (16 16 40) Ambush
|
||||||
|
*/
|
||||||
|
void() monster_army =
|
||||||
|
{
|
||||||
|
if (deathmatch)
|
||||||
|
{
|
||||||
|
remove(self);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
precache_model ("progs/soldier.mdl");
|
||||||
|
precache_model ("progs/h_guard.mdl");
|
||||||
|
precache_model ("progs/gib1.mdl");
|
||||||
|
precache_model ("progs/gib2.mdl");
|
||||||
|
precache_model ("progs/gib3.mdl");
|
||||||
|
|
||||||
|
precache_sound ("soldier/death1.wav");
|
||||||
|
precache_sound ("soldier/idle.wav");
|
||||||
|
precache_sound ("soldier/pain1.wav");
|
||||||
|
precache_sound ("soldier/pain2.wav");
|
||||||
|
precache_sound ("soldier/sattck1.wav");
|
||||||
|
precache_sound ("soldier/sight1.wav");
|
||||||
|
|
||||||
|
precache_sound ("player/udeath.wav"); // gib death
|
||||||
|
|
||||||
|
self.solid = SOLID_SLIDEBOX;
|
||||||
|
self.movetype = MOVETYPE_STEP;
|
||||||
|
|
||||||
|
setmodel (self, "progs/soldier.mdl");
|
||||||
|
|
||||||
|
setsize (self, '-16 -16 -24', '16 16 40');
|
||||||
|
self.health = 30;
|
||||||
|
|
||||||
|
self.th_stand = army_stand1;
|
||||||
|
self.th_walk = army_walk1;
|
||||||
|
self.th_run = army_run1;
|
||||||
|
self.th_missile = army_atk1;
|
||||||
|
self.th_pain = army_pain;
|
||||||
|
self.th_die = army_die;
|
||||||
|
|
||||||
|
self.ammo_shells_real = 5; // drop 5 shells on death
|
||||||
|
|
||||||
|
walkmonster_start ();
|
||||||
|
};
|
|
@ -282,3 +282,32 @@ void() SUB_UseTargets =
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
|
#ifdef MONSTERS
|
||||||
|
/*
|
||||||
|
|
||||||
|
in nightmare mode, all attack_finished times become 0
|
||||||
|
some monsters refire twice automatically
|
||||||
|
|
||||||
|
*/
|
||||||
|
|
||||||
|
void(float normal) SUB_AttackFinished =
|
||||||
|
{
|
||||||
|
self.cnt = 0; // refire count for nightmare
|
||||||
|
if (skill != 3)
|
||||||
|
self.attack_finished = time + normal;
|
||||||
|
};
|
||||||
|
|
||||||
|
float (entity targ) visible;
|
||||||
|
|
||||||
|
void (void() thinkst) SUB_CheckRefire =
|
||||||
|
{
|
||||||
|
if (skill != 3)
|
||||||
|
return;
|
||||||
|
if (self.cnt == 1)
|
||||||
|
return;
|
||||||
|
if (!visible (self.enemy))
|
||||||
|
return;
|
||||||
|
self.cnt = 1;
|
||||||
|
self.think = thinkst;
|
||||||
|
};
|
||||||
|
#endif
|
212
quakec/basemod/tarbaby.qc
Normal file
212
quakec/basemod/tarbaby.qc
Normal file
|
@ -0,0 +1,212 @@
|
||||||
|
/*
|
||||||
|
==============================================================================
|
||||||
|
|
||||||
|
BLOB
|
||||||
|
|
||||||
|
==============================================================================
|
||||||
|
*/
|
||||||
|
|
||||||
|
$cd id1/models/tarbaby
|
||||||
|
$origin 0 0 24
|
||||||
|
$base base
|
||||||
|
|
||||||
|
$skin skin
|
||||||
|
|
||||||
|
$frame walk1 walk2 walk3 walk4 walk5 walk6 walk7 walk8 walk9 walk10
|
||||||
|
$frame walk11 walk12 walk13 walk14 walk15 walk16 walk17 walk18 walk19
|
||||||
|
$frame walk20 walk21 walk22 walk23 walk24 walk25
|
||||||
|
|
||||||
|
$frame run1 run2 run3 run4 run5 run6 run7 run8 run9 run10 run11 run12 run13
|
||||||
|
$frame run14 run15 run16 run17 run18 run19 run20 run21 run22 run23
|
||||||
|
$frame run24 run25
|
||||||
|
|
||||||
|
$frame jump1 jump2 jump3 jump4 jump5 jump6
|
||||||
|
|
||||||
|
$frame fly1 fly2 fly3 fly4
|
||||||
|
|
||||||
|
$frame exp
|
||||||
|
|
||||||
|
void() tbaby_stand1 =[ $walk1, tbaby_stand1 ] {ai_stand();};
|
||||||
|
|
||||||
|
void() tbaby_hang1 =[ $walk1, tbaby_hang1 ] {ai_stand();};
|
||||||
|
|
||||||
|
void() tbaby_walk1 =[ $walk1, tbaby_walk2 ] {ai_turn();};
|
||||||
|
void() tbaby_walk2 =[ $walk2, tbaby_walk3 ] {ai_turn();};
|
||||||
|
void() tbaby_walk3 =[ $walk3, tbaby_walk4 ] {ai_turn();};
|
||||||
|
void() tbaby_walk4 =[ $walk4, tbaby_walk5 ] {ai_turn();};
|
||||||
|
void() tbaby_walk5 =[ $walk5, tbaby_walk6 ] {ai_turn();};
|
||||||
|
void() tbaby_walk6 =[ $walk6, tbaby_walk7 ] {ai_turn();};
|
||||||
|
void() tbaby_walk7 =[ $walk7, tbaby_walk8 ] {ai_turn();};
|
||||||
|
void() tbaby_walk8 =[ $walk8, tbaby_walk9 ] {ai_turn();};
|
||||||
|
void() tbaby_walk9 =[ $walk9, tbaby_walk10 ] {ai_turn();};
|
||||||
|
void() tbaby_walk10 =[ $walk10, tbaby_walk11 ] {ai_turn();};
|
||||||
|
void() tbaby_walk11 =[ $walk11, tbaby_walk12 ] {ai_walk(2);};
|
||||||
|
void() tbaby_walk12 =[ $walk12, tbaby_walk13 ] {ai_walk(2);};
|
||||||
|
void() tbaby_walk13 =[ $walk13, tbaby_walk14 ] {ai_walk(2);};
|
||||||
|
void() tbaby_walk14 =[ $walk14, tbaby_walk15 ] {ai_walk(2);};
|
||||||
|
void() tbaby_walk15 =[ $walk15, tbaby_walk16 ] {ai_walk(2);};
|
||||||
|
void() tbaby_walk16 =[ $walk16, tbaby_walk17 ] {ai_walk(2);};
|
||||||
|
void() tbaby_walk17 =[ $walk17, tbaby_walk18 ] {ai_walk(2);};
|
||||||
|
void() tbaby_walk18 =[ $walk18, tbaby_walk19 ] {ai_walk(2);};
|
||||||
|
void() tbaby_walk19 =[ $walk19, tbaby_walk20 ] {ai_walk(2);};
|
||||||
|
void() tbaby_walk20 =[ $walk20, tbaby_walk21 ] {ai_walk(2);};
|
||||||
|
void() tbaby_walk21 =[ $walk21, tbaby_walk22 ] {ai_walk(2);};
|
||||||
|
void() tbaby_walk22 =[ $walk22, tbaby_walk23 ] {ai_walk(2);};
|
||||||
|
void() tbaby_walk23 =[ $walk23, tbaby_walk24 ] {ai_walk(2);};
|
||||||
|
void() tbaby_walk24 =[ $walk24, tbaby_walk25 ] {ai_walk(2);};
|
||||||
|
void() tbaby_walk25 =[ $walk25, tbaby_walk1 ] {ai_walk(2);};
|
||||||
|
|
||||||
|
void() tbaby_run1 =[ $run1, tbaby_run2 ] {ai_face();};
|
||||||
|
void() tbaby_run2 =[ $run2, tbaby_run3 ] {ai_face();};
|
||||||
|
void() tbaby_run3 =[ $run3, tbaby_run4 ] {ai_face();};
|
||||||
|
void() tbaby_run4 =[ $run4, tbaby_run5 ] {ai_face();};
|
||||||
|
void() tbaby_run5 =[ $run5, tbaby_run6 ] {ai_face();};
|
||||||
|
void() tbaby_run6 =[ $run6, tbaby_run7 ] {ai_face();};
|
||||||
|
void() tbaby_run7 =[ $run7, tbaby_run8 ] {ai_face();};
|
||||||
|
void() tbaby_run8 =[ $run8, tbaby_run9 ] {ai_face();};
|
||||||
|
void() tbaby_run9 =[ $run9, tbaby_run10 ] {ai_face();};
|
||||||
|
void() tbaby_run10 =[ $run10, tbaby_run11 ] {ai_face();};
|
||||||
|
void() tbaby_run11 =[ $run11, tbaby_run12 ] {ai_run(2);};
|
||||||
|
void() tbaby_run12 =[ $run12, tbaby_run13 ] {ai_run(2);};
|
||||||
|
void() tbaby_run13 =[ $run13, tbaby_run14 ] {ai_run(2);};
|
||||||
|
void() tbaby_run14 =[ $run14, tbaby_run15 ] {ai_run(2);};
|
||||||
|
void() tbaby_run15 =[ $run15, tbaby_run16 ] {ai_run(2);};
|
||||||
|
void() tbaby_run16 =[ $run16, tbaby_run17 ] {ai_run(2);};
|
||||||
|
void() tbaby_run17 =[ $run17, tbaby_run18 ] {ai_run(2);};
|
||||||
|
void() tbaby_run18 =[ $run18, tbaby_run19 ] {ai_run(2);};
|
||||||
|
void() tbaby_run19 =[ $run19, tbaby_run20 ] {ai_run(2);};
|
||||||
|
void() tbaby_run20 =[ $run20, tbaby_run21 ] {ai_run(2);};
|
||||||
|
void() tbaby_run21 =[ $run21, tbaby_run22 ] {ai_run(2);};
|
||||||
|
void() tbaby_run22 =[ $run22, tbaby_run23 ] {ai_run(2);};
|
||||||
|
void() tbaby_run23 =[ $run23, tbaby_run24 ] {ai_run(2);};
|
||||||
|
void() tbaby_run24 =[ $run24, tbaby_run25 ] {ai_run(2);};
|
||||||
|
void() tbaby_run25 =[ $run25, tbaby_run1 ] {ai_run(2);};
|
||||||
|
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
|
||||||
|
|
||||||
|
void() tbaby_jump1;
|
||||||
|
|
||||||
|
void() Tar_JumpTouch =
|
||||||
|
{
|
||||||
|
local float ldmg;
|
||||||
|
|
||||||
|
if (other.takedamage && other.classname != self.classname)
|
||||||
|
{
|
||||||
|
if ( vlen(self.velocity) > 400 )
|
||||||
|
{
|
||||||
|
ldmg = 10 + 10*random();
|
||||||
|
T_Damage (other, self, self, ldmg, MOD_TARBABY);
|
||||||
|
sound (self, CHAN_WEAPON, "blob/hit1.wav", 1, ATTN_NORM);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
sound (self, CHAN_WEAPON, "blob/land1.wav", 1, ATTN_NORM);
|
||||||
|
|
||||||
|
|
||||||
|
if (!checkbottom(self))
|
||||||
|
{
|
||||||
|
if (self.flags & FL_ONGROUND)
|
||||||
|
{ // jump randomly to not get hung up
|
||||||
|
self.touch = SUB_Null;
|
||||||
|
self.think = tbaby_run1;
|
||||||
|
self.movetype = MOVETYPE_STEP;
|
||||||
|
self.nextthink = time + 0.1;
|
||||||
|
}
|
||||||
|
return; // not on ground yet
|
||||||
|
}
|
||||||
|
|
||||||
|
self.touch = SUB_Null;
|
||||||
|
self.think = tbaby_jump1;
|
||||||
|
self.nextthink = time + 0.1;
|
||||||
|
};
|
||||||
|
|
||||||
|
void() tbaby_jump5;
|
||||||
|
|
||||||
|
void() tbaby_fly1 =[ $fly1, tbaby_fly2 ] {};
|
||||||
|
void() tbaby_fly2 =[ $fly2, tbaby_fly3 ] {};
|
||||||
|
void() tbaby_fly3 =[ $fly3, tbaby_fly4 ] {};
|
||||||
|
void() tbaby_fly4 =[ $fly4, tbaby_fly1 ] {
|
||||||
|
self.cnt = self.cnt + 1;
|
||||||
|
if (self.cnt == 4)
|
||||||
|
{
|
||||||
|
//dprint ("spawn hop\n");
|
||||||
|
tbaby_jump5 ();
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
void() tbaby_jump1 =[ $jump1, tbaby_jump2 ] {ai_face();};
|
||||||
|
void() tbaby_jump2 =[ $jump2, tbaby_jump3 ] {ai_face();};
|
||||||
|
void() tbaby_jump3 =[ $jump3, tbaby_jump4 ] {ai_face();};
|
||||||
|
void() tbaby_jump4 =[ $jump4, tbaby_jump5 ] {ai_face();};
|
||||||
|
void() tbaby_jump5 =[ $jump5, tbaby_jump6 ]
|
||||||
|
{
|
||||||
|
self.movetype = MOVETYPE_BOUNCE;
|
||||||
|
self.touch = Tar_JumpTouch;
|
||||||
|
makevectors (self.angles);
|
||||||
|
self.origin_z = self.origin_z + 1;
|
||||||
|
self.velocity = v_forward * 600 + '0 0 200';
|
||||||
|
self.velocity_z = self.velocity_z + random()*150;
|
||||||
|
if (self.flags & FL_ONGROUND)
|
||||||
|
self.flags = self.flags - FL_ONGROUND;
|
||||||
|
self.cnt = 0;
|
||||||
|
};
|
||||||
|
void() tbaby_jump6 =[ $jump6,tbaby_fly1 ] {};
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
void() tbaby_die1 =[ $exp, tbaby_die2 ] {
|
||||||
|
self.takedamage = DAMAGE_NO;
|
||||||
|
};
|
||||||
|
void() tbaby_die2 =[ $exp, tbaby_run1 ]
|
||||||
|
{
|
||||||
|
T_RadiusDamage (self, self, 120, 160, world, MOD_TARBABY);
|
||||||
|
|
||||||
|
sound (self, CHAN_VOICE, "blob/death1.wav", 1, ATTN_NORM);
|
||||||
|
self.origin = self.origin - 8*normalize(self.velocity);
|
||||||
|
|
||||||
|
TE_tarexplosion(self.origin);
|
||||||
|
CreateExplosion(self.origin);
|
||||||
|
remove(self);
|
||||||
|
};
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
|
||||||
|
/*QUAKED monster_tarbaby (1 0 0) (-16 -16 -24) (16 16 24) Ambush
|
||||||
|
*/
|
||||||
|
void() monster_tarbaby =
|
||||||
|
{
|
||||||
|
if (deathmatch)
|
||||||
|
{
|
||||||
|
remove(self);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
precache_model2 ("progs/tarbaby.mdl");
|
||||||
|
|
||||||
|
precache_sound2 ("blob/death1.wav");
|
||||||
|
precache_sound2 ("blob/hit1.wav");
|
||||||
|
precache_sound2 ("blob/land1.wav");
|
||||||
|
precache_sound2 ("blob/sight1.wav");
|
||||||
|
|
||||||
|
self.solid = SOLID_SLIDEBOX;
|
||||||
|
self.movetype = MOVETYPE_STEP;
|
||||||
|
|
||||||
|
setmodel (self, "progs/tarbaby.mdl");
|
||||||
|
|
||||||
|
setsize (self, '-16 -16 -24', '16 16 40');
|
||||||
|
self.health = 80;
|
||||||
|
|
||||||
|
self.th_stand = tbaby_stand1;
|
||||||
|
self.th_walk = tbaby_walk1;
|
||||||
|
self.th_run = tbaby_run1;
|
||||||
|
self.th_missile = tbaby_jump1;
|
||||||
|
self.th_melee = tbaby_jump1;
|
||||||
|
self.th_die = tbaby_die1;
|
||||||
|
|
||||||
|
walkmonster_start ();
|
||||||
|
};
|
||||||
|
|
|
@ -348,11 +348,11 @@ LIGHTNING
|
||||||
===============================================================================
|
===============================================================================
|
||||||
*/
|
*/
|
||||||
|
|
||||||
void(entity from, float damage) LightningHit =
|
void(entity from, float damage, INTEGER lmod) LightningHit =
|
||||||
{
|
{
|
||||||
TE_lightningblood(trace_endpos);
|
TE_lightningblood(trace_endpos);
|
||||||
|
|
||||||
T_Damage (trace_ent, from, from, damage, MOD_SHAFT);
|
T_Damage (trace_ent, from, from, damage, lmod);
|
||||||
};
|
};
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
@ -360,7 +360,7 @@ void(entity from, float damage) LightningHit =
|
||||||
LightningDamage
|
LightningDamage
|
||||||
=================
|
=================
|
||||||
*/
|
*/
|
||||||
void(vector p1, vector p2, entity from, float damage) LightningDamage =
|
void(vector p1, vector p2, entity from, float damage, INTEGER lmod) LightningDamage =
|
||||||
{
|
{
|
||||||
local entity e1, e2;
|
local entity e1, e2;
|
||||||
local vector f;
|
local vector f;
|
||||||
|
@ -377,17 +377,17 @@ void(vector p1, vector p2, entity from, float damage) LightningDamage =
|
||||||
traceline (p1, p2, FALSE, self);
|
traceline (p1, p2, FALSE, self);
|
||||||
|
|
||||||
if (trace_ent.takedamage)
|
if (trace_ent.takedamage)
|
||||||
LightningHit (from, damage);
|
LightningHit (from, damage, lmod);
|
||||||
e1 = trace_ent;
|
e1 = trace_ent;
|
||||||
|
|
||||||
traceline (p1 + f, p2 + f, FALSE, self);
|
traceline (p1 + f, p2 + f, FALSE, self);
|
||||||
if (trace_ent != e1 && trace_ent.takedamage)
|
if (trace_ent != e1 && trace_ent.takedamage)
|
||||||
LightningHit (from, damage);
|
LightningHit (from, damage, lmod);
|
||||||
e2 = trace_ent;
|
e2 = trace_ent;
|
||||||
|
|
||||||
traceline (p1 - f, p2 - f, FALSE, self);
|
traceline (p1 - f, p2 - f, FALSE, self);
|
||||||
if (trace_ent != e1 && trace_ent != e2 && trace_ent.takedamage)
|
if (trace_ent != e1 && trace_ent != e2 && trace_ent.takedamage)
|
||||||
LightningHit (from, damage);
|
LightningHit (from, damage, lmod);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
@ -446,7 +446,7 @@ void() W_FireLightning =
|
||||||
|
|
||||||
TE_lightning2(self, org, trace_endpos);
|
TE_lightning2(self, org, trace_endpos);
|
||||||
|
|
||||||
LightningDamage (self.origin, trace_endpos + v_forward*4, self, 30);
|
LightningDamage (self.origin, trace_endpos + v_forward*4, self, 30, MOD_SHAFT);
|
||||||
};
|
};
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
|
319
quakec/basemod/wizard.qc
Normal file
319
quakec/basemod/wizard.qc
Normal file
|
@ -0,0 +1,319 @@
|
||||||
|
/*
|
||||||
|
==============================================================================
|
||||||
|
|
||||||
|
WIZARD
|
||||||
|
|
||||||
|
==============================================================================
|
||||||
|
*/
|
||||||
|
|
||||||
|
$cd id1/models/a_wizard
|
||||||
|
$origin 0 0 24
|
||||||
|
$base wizbase
|
||||||
|
$skin wizbase
|
||||||
|
|
||||||
|
$frame hover1 hover2 hover3 hover4 hover5 hover6 hover7 hover8
|
||||||
|
$frame hover9 hover10 hover11 hover12 hover13 hover14 hover15
|
||||||
|
|
||||||
|
$frame fly1 fly2 fly3 fly4 fly5 fly6 fly7 fly8 fly9 fly10
|
||||||
|
$frame fly11 fly12 fly13 fly14
|
||||||
|
|
||||||
|
$frame magatt1 magatt2 magatt3 magatt4 magatt5 magatt6 magatt7
|
||||||
|
$frame magatt8 magatt9 magatt10 magatt11 magatt12 magatt13
|
||||||
|
|
||||||
|
$frame pain1 pain2 pain3 pain4
|
||||||
|
|
||||||
|
$frame death1 death2 death3 death4 death5 death6 death7 death8
|
||||||
|
|
||||||
|
/*
|
||||||
|
==============================================================================
|
||||||
|
|
||||||
|
WIZARD
|
||||||
|
|
||||||
|
If the player moves behind cover before the missile is launched, launch it
|
||||||
|
at the last visible spot with no velocity leading, in hopes that the player
|
||||||
|
will duck back out and catch it.
|
||||||
|
==============================================================================
|
||||||
|
*/
|
||||||
|
|
||||||
|
void() wiz_run1;
|
||||||
|
void() wiz_side1;
|
||||||
|
|
||||||
|
/*
|
||||||
|
=================
|
||||||
|
WizardCheckAttack
|
||||||
|
=================
|
||||||
|
*/
|
||||||
|
float(float enemy_range) WizardCheckAttack =
|
||||||
|
{
|
||||||
|
local vector spot1, spot2;
|
||||||
|
local entity targ;
|
||||||
|
local float chance;
|
||||||
|
|
||||||
|
if (time < self.attack_finished)
|
||||||
|
return FALSE;
|
||||||
|
|
||||||
|
if (enemy_range == RANGE_FAR)
|
||||||
|
{
|
||||||
|
if (self.attack_state != AS_STRAIGHT)
|
||||||
|
{
|
||||||
|
self.attack_state = AS_STRAIGHT;
|
||||||
|
wiz_run1 ();
|
||||||
|
}
|
||||||
|
return FALSE;
|
||||||
|
}
|
||||||
|
|
||||||
|
targ = self.enemy;
|
||||||
|
|
||||||
|
// see if any entities are in the way of the shot
|
||||||
|
spot1 = self.origin + self.view_ofs;
|
||||||
|
spot2 = targ.origin + targ.view_ofs;
|
||||||
|
|
||||||
|
traceline (spot1, spot2, FALSE, self);
|
||||||
|
|
||||||
|
if (trace_ent != targ)
|
||||||
|
{ // don't have a clear shot, so move to a side
|
||||||
|
if (self.attack_state != AS_STRAIGHT)
|
||||||
|
{
|
||||||
|
self.attack_state = AS_STRAIGHT;
|
||||||
|
wiz_run1 ();
|
||||||
|
}
|
||||||
|
return FALSE;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (enemy_range == RANGE_MELEE)
|
||||||
|
chance = 0.9;
|
||||||
|
else if (enemy_range == RANGE_NEAR)
|
||||||
|
chance = 0.6;
|
||||||
|
else if (enemy_range == RANGE_MID)
|
||||||
|
chance = 0.2;
|
||||||
|
else
|
||||||
|
chance = 0;
|
||||||
|
|
||||||
|
if (random () < chance)
|
||||||
|
{
|
||||||
|
self.attack_state = AS_MISSILE;
|
||||||
|
return TRUE;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (enemy_range == RANGE_MID)
|
||||||
|
{
|
||||||
|
if (self.attack_state != AS_STRAIGHT)
|
||||||
|
{
|
||||||
|
self.attack_state = AS_STRAIGHT;
|
||||||
|
wiz_run1 ();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if (self.attack_state != AS_SLIDING)
|
||||||
|
{
|
||||||
|
self.attack_state = AS_SLIDING;
|
||||||
|
wiz_side1 ();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return FALSE;
|
||||||
|
};
|
||||||
|
|
||||||
|
/*
|
||||||
|
=================
|
||||||
|
WizardAttackFinished
|
||||||
|
=================
|
||||||
|
*/
|
||||||
|
void() WizardAttackFinished =
|
||||||
|
{
|
||||||
|
if (range(self.enemy) >= RANGE_MID || !visible(self.enemy))
|
||||||
|
{
|
||||||
|
self.attack_state = AS_STRAIGHT;
|
||||||
|
self.think = wiz_run1;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
self.attack_state = AS_SLIDING;
|
||||||
|
self.think = wiz_side1;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
/*
|
||||||
|
==============================================================================
|
||||||
|
|
||||||
|
FAST ATTACKS
|
||||||
|
|
||||||
|
==============================================================================
|
||||||
|
*/
|
||||||
|
|
||||||
|
void(float side) Wiz_FastFire =
|
||||||
|
{
|
||||||
|
local vector org, vec;
|
||||||
|
|
||||||
|
muzzleflash();
|
||||||
|
sound (self, CHAN_WEAPON, "wizard/wattack.wav", 1, ATTN_NORM);
|
||||||
|
|
||||||
|
makevectors (self.angles);
|
||||||
|
org = self.origin + '0 0 30' + v_forward*14 + v_right*side*14;
|
||||||
|
vec = normalize(self.enemy.origin - v_right*side*13 - org) * 600;
|
||||||
|
|
||||||
|
PRJ_FireProjectile (self, "progs/w_spike.mdl", org, vec, PE_WIZSPIKE, 9, MOD_WIZARD, 6);
|
||||||
|
};
|
||||||
|
|
||||||
|
void() Wiz_idlesound =
|
||||||
|
{
|
||||||
|
local float wr;
|
||||||
|
|
||||||
|
if (self.wizardidle < time)
|
||||||
|
{
|
||||||
|
wr = random();
|
||||||
|
|
||||||
|
if (wr > 0.9)
|
||||||
|
sound (self, CHAN_VOICE, "wizard/widle1.wav", 1, ATTN_IDLE);
|
||||||
|
else if (wr < 0.3)
|
||||||
|
sound (self, CHAN_VOICE, "wizard/widle2.wav", 1, ATTN_IDLE);
|
||||||
|
|
||||||
|
self.wizardidle = time + 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
return;
|
||||||
|
};
|
||||||
|
|
||||||
|
void() wiz_stand1 =[ $hover1, wiz_stand2 ] {ai_stand();};
|
||||||
|
void() wiz_stand2 =[ $hover2, wiz_stand3 ] {ai_stand();};
|
||||||
|
void() wiz_stand3 =[ $hover3, wiz_stand4 ] {ai_stand();};
|
||||||
|
void() wiz_stand4 =[ $hover4, wiz_stand5 ] {ai_stand();};
|
||||||
|
void() wiz_stand5 =[ $hover5, wiz_stand6 ] {ai_stand();};
|
||||||
|
void() wiz_stand6 =[ $hover6, wiz_stand7 ] {ai_stand();};
|
||||||
|
void() wiz_stand7 =[ $hover7, wiz_stand8 ] {ai_stand();};
|
||||||
|
void() wiz_stand8 =[ $hover8, wiz_stand1 ] {ai_stand();};
|
||||||
|
|
||||||
|
void() wiz_walk1 =[ $hover1, wiz_walk2 ] {ai_walk(8);
|
||||||
|
Wiz_idlesound();};
|
||||||
|
void() wiz_walk2 =[ $hover2, wiz_walk3 ] {ai_walk(8);};
|
||||||
|
void() wiz_walk3 =[ $hover3, wiz_walk4 ] {ai_walk(8);};
|
||||||
|
void() wiz_walk4 =[ $hover4, wiz_walk5 ] {ai_walk(8);};
|
||||||
|
void() wiz_walk5 =[ $hover5, wiz_walk6 ] {ai_walk(8);};
|
||||||
|
void() wiz_walk6 =[ $hover6, wiz_walk7 ] {ai_walk(8);};
|
||||||
|
void() wiz_walk7 =[ $hover7, wiz_walk8 ] {ai_walk(8);};
|
||||||
|
void() wiz_walk8 =[ $hover8, wiz_walk1 ] {ai_walk(8);};
|
||||||
|
|
||||||
|
void() wiz_side1 =[ $hover1, wiz_side2 ] {ai_run(8);
|
||||||
|
Wiz_idlesound();};
|
||||||
|
void() wiz_side2 =[ $hover2, wiz_side3 ] {ai_run(8);};
|
||||||
|
void() wiz_side3 =[ $hover3, wiz_side4 ] {ai_run(8);};
|
||||||
|
void() wiz_side4 =[ $hover4, wiz_side5 ] {ai_run(8);};
|
||||||
|
void() wiz_side5 =[ $hover5, wiz_side6 ] {ai_run(8);};
|
||||||
|
void() wiz_side6 =[ $hover6, wiz_side7 ] {ai_run(8);};
|
||||||
|
void() wiz_side7 =[ $hover7, wiz_side8 ] {ai_run(8);};
|
||||||
|
void() wiz_side8 =[ $hover8, wiz_side1 ] {ai_run(8);};
|
||||||
|
|
||||||
|
void() wiz_run1 =[ $fly1, wiz_run2 ] {ai_run(16);
|
||||||
|
Wiz_idlesound();
|
||||||
|
};
|
||||||
|
void() wiz_run2 =[ $fly2, wiz_run3 ] {ai_run(16);};
|
||||||
|
void() wiz_run3 =[ $fly3, wiz_run4 ] {ai_run(16);};
|
||||||
|
void() wiz_run4 =[ $fly4, wiz_run5 ] {ai_run(16);};
|
||||||
|
void() wiz_run5 =[ $fly5, wiz_run6 ] {ai_run(16);};
|
||||||
|
void() wiz_run6 =[ $fly6, wiz_run7 ] {ai_run(16);};
|
||||||
|
void() wiz_run7 =[ $fly7, wiz_run8 ] {ai_run(16);};
|
||||||
|
void() wiz_run8 =[ $fly8, wiz_run9 ] {ai_run(16);};
|
||||||
|
void() wiz_run9 =[ $fly9, wiz_run10 ] {ai_run(16);};
|
||||||
|
void() wiz_run10 =[ $fly10, wiz_run11 ] {ai_run(16);};
|
||||||
|
void() wiz_run11 =[ $fly11, wiz_run12 ] {ai_run(16);};
|
||||||
|
void() wiz_run12 =[ $fly12, wiz_run13 ] {ai_run(16);};
|
||||||
|
void() wiz_run13 =[ $fly13, wiz_run14 ] {ai_run(16);};
|
||||||
|
void() wiz_run14 =[ $fly14, wiz_run1 ] {ai_run(16);};
|
||||||
|
|
||||||
|
void() wiz_fast1 =[ $magatt1, wiz_fast2 ] {ai_face();};
|
||||||
|
void() wiz_fast2 =[ $magatt2, wiz_fast3 ] {ai_face();};
|
||||||
|
void() wiz_fast3 =[ $magatt3, wiz_fast4 ] {ai_face();};
|
||||||
|
void() wiz_fast4 =[ $magatt4, wiz_fast5 ] {ai_face();Wiz_FastFire(-1);};
|
||||||
|
void() wiz_fast5 =[ $magatt5, wiz_fast6 ] {ai_face();};
|
||||||
|
void() wiz_fast6 =[ $magatt6, wiz_fast7 ] {ai_face();};
|
||||||
|
void() wiz_fast7 =[ $magatt5, wiz_fast8 ] {ai_face();};
|
||||||
|
void() wiz_fast8 =[ $magatt4, wiz_fast9 ] {ai_face();};
|
||||||
|
void() wiz_fast9 =[ $magatt3, wiz_fast10 ] {ai_face();Wiz_FastFire(1);};
|
||||||
|
void() wiz_fast10 =[ $magatt2, wiz_run1 ] {ai_face();SUB_AttackFinished(2);WizardAttackFinished ();};
|
||||||
|
|
||||||
|
void() wiz_pain1 =[ $pain1, wiz_pain2 ] {};
|
||||||
|
void() wiz_pain2 =[ $pain2, wiz_pain3 ] {};
|
||||||
|
void() wiz_pain3 =[ $pain3, wiz_pain4 ] {};
|
||||||
|
void() wiz_pain4 =[ $pain4, wiz_run1 ] {};
|
||||||
|
|
||||||
|
void() wiz_death1 =[ $death1, wiz_death2 ] {
|
||||||
|
|
||||||
|
self.velocity_x = -200 + 400*random();
|
||||||
|
self.velocity_y = -200 + 400*random();
|
||||||
|
self.velocity_z = 100 + 100*random();
|
||||||
|
self.flags = self.flags - (self.flags & FL_ONGROUND);
|
||||||
|
sound (self, CHAN_VOICE, "wizard/wdeath.wav", 1, ATTN_NORM);
|
||||||
|
};
|
||||||
|
void() wiz_death2 =[ $death2, wiz_death3 ] {};
|
||||||
|
void() wiz_death3 =[ $death3, wiz_death4 ]{self.solid = SOLID_NOT;};
|
||||||
|
void() wiz_death4 =[ $death4, wiz_death5 ] {};
|
||||||
|
void() wiz_death5 =[ $death5, wiz_death6 ] {};
|
||||||
|
void() wiz_death6 =[ $death6, wiz_death7 ] {};
|
||||||
|
void() wiz_death7 =[ $death7, wiz_death8 ] {};
|
||||||
|
void() wiz_death8 =[ $death8, wiz_death8 ] {};
|
||||||
|
|
||||||
|
void() wiz_die =
|
||||||
|
{
|
||||||
|
// check for gib
|
||||||
|
if (self.health < -40)
|
||||||
|
{
|
||||||
|
sound (self, CHAN_VOICE, "player/udeath.wav", 1, ATTN_NORM);
|
||||||
|
ThrowHead ("progs/h_wizard.mdl", self.health);
|
||||||
|
ThrowGib ("progs/gib2.mdl", self.health);
|
||||||
|
ThrowGib ("progs/gib2.mdl", self.health);
|
||||||
|
ThrowGib ("progs/gib2.mdl", self.health);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
wiz_death1 ();
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
void(entity attacker, float damage) Wiz_Pain =
|
||||||
|
{
|
||||||
|
sound (self, CHAN_VOICE, "wizard/wpain.wav", 1, ATTN_NORM);
|
||||||
|
if (random()*70 > damage)
|
||||||
|
return; // didn't flinch
|
||||||
|
|
||||||
|
wiz_pain1 ();
|
||||||
|
};
|
||||||
|
|
||||||
|
/*QUAKED monster_wizard (1 0 0) (-16 -16 -24) (16 16 40) Ambush
|
||||||
|
*/
|
||||||
|
void() monster_wizard =
|
||||||
|
{
|
||||||
|
if (deathmatch)
|
||||||
|
{
|
||||||
|
remove(self);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
precache_model ("progs/wizard.mdl");
|
||||||
|
precache_model ("progs/h_wizard.mdl");
|
||||||
|
precache_model ("progs/w_spike.mdl");
|
||||||
|
|
||||||
|
precache_sound ("wizard/hit.wav"); // used by c code
|
||||||
|
precache_sound ("wizard/wattack.wav");
|
||||||
|
precache_sound ("wizard/wdeath.wav");
|
||||||
|
precache_sound ("wizard/widle1.wav");
|
||||||
|
precache_sound ("wizard/widle2.wav");
|
||||||
|
precache_sound ("wizard/wpain.wav");
|
||||||
|
precache_sound ("wizard/wsight.wav");
|
||||||
|
|
||||||
|
self.solid = SOLID_SLIDEBOX;
|
||||||
|
self.movetype = MOVETYPE_STEP;
|
||||||
|
|
||||||
|
setmodel (self, "progs/wizard.mdl");
|
||||||
|
|
||||||
|
setsize (self, '-16 -16 -24', '16 16 40');
|
||||||
|
self.health = 80;
|
||||||
|
|
||||||
|
self.th_stand = wiz_stand1;
|
||||||
|
self.th_walk = wiz_walk1;
|
||||||
|
self.th_run = wiz_run1;
|
||||||
|
self.th_missile = wiz_fast1;
|
||||||
|
self.th_pain = Wiz_Pain;
|
||||||
|
self.th_die = wiz_die;
|
||||||
|
|
||||||
|
flymonster_start ();
|
||||||
|
};
|
473
quakec/basemod/zombie.qc
Normal file
473
quakec/basemod/zombie.qc
Normal file
|
@ -0,0 +1,473 @@
|
||||||
|
/*
|
||||||
|
==============================================================================
|
||||||
|
|
||||||
|
ZOMBIE
|
||||||
|
|
||||||
|
==============================================================================
|
||||||
|
*/
|
||||||
|
$cd id1/models/zombie
|
||||||
|
|
||||||
|
$origin 0 0 24
|
||||||
|
|
||||||
|
$base base
|
||||||
|
$skin skin
|
||||||
|
|
||||||
|
$frame stand1 stand2 stand3 stand4 stand5 stand6 stand7 stand8
|
||||||
|
$frame stand9 stand10 stand11 stand12 stand13 stand14 stand15
|
||||||
|
|
||||||
|
$frame walk1 walk2 walk3 walk4 walk5 walk6 walk7 walk8 walk9 walk10 walk11
|
||||||
|
$frame walk12 walk13 walk14 walk15 walk16 walk17 walk18 walk19
|
||||||
|
|
||||||
|
$frame run1 run2 run3 run4 run5 run6 run7 run8 run9 run10 run11 run12
|
||||||
|
$frame run13 run14 run15 run16 run17 run18
|
||||||
|
|
||||||
|
$frame atta1 atta2 atta3 atta4 atta5 atta6 atta7 atta8 atta9 atta10 atta11
|
||||||
|
$frame atta12 atta13
|
||||||
|
|
||||||
|
$frame attb1 attb2 attb3 attb4 attb5 attb6 attb7 attb8 attb9 attb10 attb11
|
||||||
|
$frame attb12 attb13 attb14
|
||||||
|
|
||||||
|
$frame attc1 attc2 attc3 attc4 attc5 attc6 attc7 attc8 attc9 attc10 attc11
|
||||||
|
$frame attc12
|
||||||
|
|
||||||
|
$frame paina1 paina2 paina3 paina4 paina5 paina6 paina7 paina8 paina9 paina10
|
||||||
|
$frame paina11 paina12
|
||||||
|
|
||||||
|
$frame painb1 painb2 painb3 painb4 painb5 painb6 painb7 painb8 painb9 painb10
|
||||||
|
$frame painb11 painb12 painb13 painb14 painb15 painb16 painb17 painb18 painb19
|
||||||
|
$frame painb20 painb21 painb22 painb23 painb24 painb25 painb26 painb27 painb28
|
||||||
|
|
||||||
|
$frame painc1 painc2 painc3 painc4 painc5 painc6 painc7 painc8 painc9 painc10
|
||||||
|
$frame painc11 painc12 painc13 painc14 painc15 painc16 painc17 painc18
|
||||||
|
|
||||||
|
$frame paind1 paind2 paind3 paind4 paind5 paind6 paind7 paind8 paind9 paind10
|
||||||
|
$frame paind11 paind12 paind13
|
||||||
|
|
||||||
|
$frame paine1 paine2 paine3 paine4 paine5 paine6 paine7 paine8 paine9 paine10
|
||||||
|
$frame paine11 paine12 paine13 paine14 paine15 paine16 paine17 paine18 paine19
|
||||||
|
$frame paine20 paine21 paine22 paine23 paine24 paine25 paine26 paine27 paine28
|
||||||
|
$frame paine29 paine30
|
||||||
|
|
||||||
|
$frame cruc_1 cruc_2 cruc_3 cruc_4 cruc_5 cruc_6
|
||||||
|
|
||||||
|
float SPAWN_CRUCIFIED = 1;
|
||||||
|
|
||||||
|
//=============================================================================
|
||||||
|
|
||||||
|
void() zombie_stand1 =[ $stand1, zombie_stand2 ] {ai_stand();};
|
||||||
|
void() zombie_stand2 =[ $stand2, zombie_stand3 ] {ai_stand();};
|
||||||
|
void() zombie_stand3 =[ $stand3, zombie_stand4 ] {ai_stand();};
|
||||||
|
void() zombie_stand4 =[ $stand4, zombie_stand5 ] {ai_stand();};
|
||||||
|
void() zombie_stand5 =[ $stand5, zombie_stand6 ] {ai_stand();};
|
||||||
|
void() zombie_stand6 =[ $stand6, zombie_stand7 ] {ai_stand();};
|
||||||
|
void() zombie_stand7 =[ $stand7, zombie_stand8 ] {ai_stand();};
|
||||||
|
void() zombie_stand8 =[ $stand8, zombie_stand9 ] {ai_stand();};
|
||||||
|
void() zombie_stand9 =[ $stand9, zombie_stand10 ] {ai_stand();};
|
||||||
|
void() zombie_stand10 =[ $stand10, zombie_stand11 ] {ai_stand();};
|
||||||
|
void() zombie_stand11 =[ $stand11, zombie_stand12 ] {ai_stand();};
|
||||||
|
void() zombie_stand12 =[ $stand12, zombie_stand13 ] {ai_stand();};
|
||||||
|
void() zombie_stand13 =[ $stand13, zombie_stand14 ] {ai_stand();};
|
||||||
|
void() zombie_stand14 =[ $stand14, zombie_stand15 ] {ai_stand();};
|
||||||
|
void() zombie_stand15 =[ $stand15, zombie_stand1 ] {ai_stand();};
|
||||||
|
|
||||||
|
void() zombie_cruc1 = [ $cruc_1, zombie_cruc2 ] {
|
||||||
|
if (random() < 0.1)
|
||||||
|
sound (self, CHAN_VOICE, "zombie/idle_w2.wav", 1, ATTN_STATIC);};
|
||||||
|
void() zombie_cruc2 = [ $cruc_2, zombie_cruc3 ] {self.nextthink = time + 0.1 + random()*0.1;};
|
||||||
|
void() zombie_cruc3 = [ $cruc_3, zombie_cruc4 ] {self.nextthink = time + 0.1 + random()*0.1;};
|
||||||
|
void() zombie_cruc4 = [ $cruc_4, zombie_cruc5 ] {self.nextthink = time + 0.1 + random()*0.1;};
|
||||||
|
void() zombie_cruc5 = [ $cruc_5, zombie_cruc6 ] {self.nextthink = time + 0.1 + random()*0.1;};
|
||||||
|
void() zombie_cruc6 = [ $cruc_6, zombie_cruc1 ] {self.nextthink = time + 0.1 + random()*0.1;};
|
||||||
|
|
||||||
|
void() zombie_walk1 =[ $walk1, zombie_walk2 ] {ai_walk(0);};
|
||||||
|
void() zombie_walk2 =[ $walk2, zombie_walk3 ] {ai_walk(2);};
|
||||||
|
void() zombie_walk3 =[ $walk3, zombie_walk4 ] {ai_walk(3);};
|
||||||
|
void() zombie_walk4 =[ $walk4, zombie_walk5 ] {ai_walk(2);};
|
||||||
|
void() zombie_walk5 =[ $walk5, zombie_walk6 ] {ai_walk(1);};
|
||||||
|
void() zombie_walk6 =[ $walk6, zombie_walk7 ] {ai_walk(0);};
|
||||||
|
void() zombie_walk7 =[ $walk7, zombie_walk8 ] {ai_walk(0);};
|
||||||
|
void() zombie_walk8 =[ $walk8, zombie_walk9 ] {ai_walk(0);};
|
||||||
|
void() zombie_walk9 =[ $walk9, zombie_walk10 ] {ai_walk(0);};
|
||||||
|
void() zombie_walk10 =[ $walk10, zombie_walk11 ] {ai_walk(0);};
|
||||||
|
void() zombie_walk11 =[ $walk11, zombie_walk12 ] {ai_walk(2);};
|
||||||
|
void() zombie_walk12 =[ $walk12, zombie_walk13 ] {ai_walk(2);};
|
||||||
|
void() zombie_walk13 =[ $walk13, zombie_walk14 ] {ai_walk(1);};
|
||||||
|
void() zombie_walk14 =[ $walk14, zombie_walk15 ] {ai_walk(0);};
|
||||||
|
void() zombie_walk15 =[ $walk15, zombie_walk16 ] {ai_walk(0);};
|
||||||
|
void() zombie_walk16 =[ $walk16, zombie_walk17 ] {ai_walk(0);};
|
||||||
|
void() zombie_walk17 =[ $walk17, zombie_walk18 ] {ai_walk(0);};
|
||||||
|
void() zombie_walk18 =[ $walk18, zombie_walk19 ] {ai_walk(0);};
|
||||||
|
void() zombie_walk19 =[ $walk19, zombie_walk1 ] {
|
||||||
|
ai_walk(0);
|
||||||
|
if (random() < 0.2)
|
||||||
|
sound (self, CHAN_VOICE, "zombie/z_idle.wav", 1, ATTN_IDLE);};
|
||||||
|
|
||||||
|
void() zombie_run1 =[ $run1, zombie_run2 ] {ai_run(1);self.inpain = 0;};
|
||||||
|
void() zombie_run2 =[ $run2, zombie_run3 ] {ai_run(1);};
|
||||||
|
void() zombie_run3 =[ $run3, zombie_run4 ] {ai_run(0);};
|
||||||
|
void() zombie_run4 =[ $run4, zombie_run5 ] {ai_run(1);};
|
||||||
|
void() zombie_run5 =[ $run5, zombie_run6 ] {ai_run(2);};
|
||||||
|
void() zombie_run6 =[ $run6, zombie_run7 ] {ai_run(3);};
|
||||||
|
void() zombie_run7 =[ $run7, zombie_run8 ] {ai_run(4);};
|
||||||
|
void() zombie_run8 =[ $run8, zombie_run9 ] {ai_run(4);};
|
||||||
|
void() zombie_run9 =[ $run9, zombie_run10 ] {ai_run(2);};
|
||||||
|
void() zombie_run10 =[ $run10, zombie_run11 ] {ai_run(0);};
|
||||||
|
void() zombie_run11 =[ $run11, zombie_run12 ] {ai_run(0);};
|
||||||
|
void() zombie_run12 =[ $run12, zombie_run13 ] {ai_run(0);};
|
||||||
|
void() zombie_run13 =[ $run13, zombie_run14 ] {ai_run(2);};
|
||||||
|
void() zombie_run14 =[ $run14, zombie_run15 ] {ai_run(4);};
|
||||||
|
void() zombie_run15 =[ $run15, zombie_run16 ] {ai_run(6);};
|
||||||
|
void() zombie_run16 =[ $run16, zombie_run17 ] {ai_run(7);};
|
||||||
|
void() zombie_run17 =[ $run17, zombie_run18 ] {ai_run(3);};
|
||||||
|
void() zombie_run18 =[ $run18, zombie_run1 ] {
|
||||||
|
ai_run(8);
|
||||||
|
if (random() < 0.2)
|
||||||
|
sound (self, CHAN_VOICE, "zombie/z_idle.wav", 1, ATTN_IDLE);
|
||||||
|
if (random() > 0.8)
|
||||||
|
sound (self, CHAN_VOICE, "zombie/z_idle1.wav", 1, ATTN_IDLE);
|
||||||
|
};
|
||||||
|
|
||||||
|
/*
|
||||||
|
=============================================================================
|
||||||
|
|
||||||
|
ATTACKS
|
||||||
|
|
||||||
|
=============================================================================
|
||||||
|
*/
|
||||||
|
|
||||||
|
/*
|
||||||
|
================
|
||||||
|
ZombieFireGrenade
|
||||||
|
================
|
||||||
|
*/
|
||||||
|
void(vector st) ZombieFireGrenade =
|
||||||
|
{
|
||||||
|
local vector org, vel;
|
||||||
|
|
||||||
|
sound (self, CHAN_WEAPON, "zombie/z_shot1.wav", 1, ATTN_NORM);
|
||||||
|
|
||||||
|
org = self.origin + st_x * v_forward + st_y * v_right + (st_z - 24) * v_up;
|
||||||
|
vel = normalize(self.enemy.origin - org) * 600;
|
||||||
|
vel_z = 200;
|
||||||
|
PRJ_FireProjectile(self, "progs/zom_gib.mdl", org, vel, PE_ZOMBIEGIB, 10, MOD_ZOMBIE, 2.5);
|
||||||
|
PRJ_SetTossedProjectile();
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
void() zombie_atta1 =[ $atta1, zombie_atta2 ] {ai_face();};
|
||||||
|
void() zombie_atta2 =[ $atta2, zombie_atta3 ] {ai_face();};
|
||||||
|
void() zombie_atta3 =[ $atta3, zombie_atta4 ] {ai_face();};
|
||||||
|
void() zombie_atta4 =[ $atta4, zombie_atta5 ] {ai_face();};
|
||||||
|
void() zombie_atta5 =[ $atta5, zombie_atta6 ] {ai_face();};
|
||||||
|
void() zombie_atta6 =[ $atta6, zombie_atta7 ] {ai_face();};
|
||||||
|
void() zombie_atta7 =[ $atta7, zombie_atta8 ] {ai_face();};
|
||||||
|
void() zombie_atta8 =[ $atta8, zombie_atta9 ] {ai_face();};
|
||||||
|
void() zombie_atta9 =[ $atta9, zombie_atta10 ] {ai_face();};
|
||||||
|
void() zombie_atta10 =[ $atta10, zombie_atta11 ] {ai_face();};
|
||||||
|
void() zombie_atta11 =[ $atta11, zombie_atta12 ] {ai_face();};
|
||||||
|
void() zombie_atta12 =[ $atta12, zombie_atta13 ] {ai_face();};
|
||||||
|
void() zombie_atta13 =[ $atta13, zombie_run1 ] {ai_face();ZombieFireGrenade('-10 -22 30');};
|
||||||
|
|
||||||
|
void() zombie_attb1 =[ $attb1, zombie_attb2 ] {ai_face();};
|
||||||
|
void() zombie_attb2 =[ $attb2, zombie_attb3 ] {ai_face();};
|
||||||
|
void() zombie_attb3 =[ $attb3, zombie_attb4 ] {ai_face();};
|
||||||
|
void() zombie_attb4 =[ $attb4, zombie_attb5 ] {ai_face();};
|
||||||
|
void() zombie_attb5 =[ $attb5, zombie_attb6 ] {ai_face();};
|
||||||
|
void() zombie_attb6 =[ $attb6, zombie_attb7 ] {ai_face();};
|
||||||
|
void() zombie_attb7 =[ $attb7, zombie_attb8 ] {ai_face();};
|
||||||
|
void() zombie_attb8 =[ $attb8, zombie_attb9 ] {ai_face();};
|
||||||
|
void() zombie_attb9 =[ $attb9, zombie_attb10 ] {ai_face();};
|
||||||
|
void() zombie_attb10 =[ $attb10, zombie_attb11 ] {ai_face();};
|
||||||
|
void() zombie_attb11 =[ $attb11, zombie_attb12 ] {ai_face();};
|
||||||
|
void() zombie_attb12 =[ $attb12, zombie_attb13 ] {ai_face();};
|
||||||
|
void() zombie_attb13 =[ $attb13, zombie_attb14 ] {ai_face();};
|
||||||
|
void() zombie_attb14 =[ $attb13, zombie_run1 ] {ai_face();ZombieFireGrenade('-10 -24 29');};
|
||||||
|
|
||||||
|
void() zombie_attc1 =[ $attc1, zombie_attc2 ] {ai_face();};
|
||||||
|
void() zombie_attc2 =[ $attc2, zombie_attc3 ] {ai_face();};
|
||||||
|
void() zombie_attc3 =[ $attc3, zombie_attc4 ] {ai_face();};
|
||||||
|
void() zombie_attc4 =[ $attc4, zombie_attc5 ] {ai_face();};
|
||||||
|
void() zombie_attc5 =[ $attc5, zombie_attc6 ] {ai_face();};
|
||||||
|
void() zombie_attc6 =[ $attc6, zombie_attc7 ] {ai_face();};
|
||||||
|
void() zombie_attc7 =[ $attc7, zombie_attc8 ] {ai_face();};
|
||||||
|
void() zombie_attc8 =[ $attc8, zombie_attc9 ] {ai_face();};
|
||||||
|
void() zombie_attc9 =[ $attc9, zombie_attc10 ] {ai_face();};
|
||||||
|
void() zombie_attc10 =[ $attc10, zombie_attc11 ] {ai_face();};
|
||||||
|
void() zombie_attc11 =[ $attc11, zombie_attc12 ] {ai_face();};
|
||||||
|
void() zombie_attc12 =[ $attc12, zombie_run1 ] {ai_face();ZombieFireGrenade('-12 -19 29');};
|
||||||
|
|
||||||
|
void() zombie_missile =
|
||||||
|
{
|
||||||
|
local float r;
|
||||||
|
|
||||||
|
r = random();
|
||||||
|
|
||||||
|
if (r < 0.3)
|
||||||
|
zombie_atta1 ();
|
||||||
|
else if (r < 0.6)
|
||||||
|
zombie_attb1 ();
|
||||||
|
else
|
||||||
|
zombie_attc1 ();
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
|
/*
|
||||||
|
=============================================================================
|
||||||
|
|
||||||
|
PAIN
|
||||||
|
|
||||||
|
=============================================================================
|
||||||
|
*/
|
||||||
|
|
||||||
|
void() zombie_paina1 =[ $paina1, zombie_paina2 ] {sound (self, CHAN_VOICE, "zombie/z_pain.wav", 1, ATTN_NORM);};
|
||||||
|
void() zombie_paina2 =[ $paina2, zombie_paina3 ] {ai_painforward(3);};
|
||||||
|
void() zombie_paina3 =[ $paina3, zombie_paina4 ] {ai_painforward(1);};
|
||||||
|
void() zombie_paina4 =[ $paina4, zombie_paina5 ] {ai_pain(1);};
|
||||||
|
void() zombie_paina5 =[ $paina5, zombie_paina6 ] {ai_pain(3);};
|
||||||
|
void() zombie_paina6 =[ $paina6, zombie_paina7 ] {ai_pain(1);};
|
||||||
|
void() zombie_paina7 =[ $paina7, zombie_paina8 ] {};
|
||||||
|
void() zombie_paina8 =[ $paina8, zombie_paina9 ] {};
|
||||||
|
void() zombie_paina9 =[ $paina9, zombie_paina10 ] {};
|
||||||
|
void() zombie_paina10 =[ $paina10, zombie_paina11 ] {};
|
||||||
|
void() zombie_paina11 =[ $paina11, zombie_paina12 ] {};
|
||||||
|
void() zombie_paina12 =[ $paina12, zombie_run1 ] {};
|
||||||
|
|
||||||
|
void() zombie_painb1 =[ $painb1, zombie_painb2 ] {sound (self, CHAN_VOICE, "zombie/z_pain1.wav", 1, ATTN_NORM);};
|
||||||
|
void() zombie_painb2 =[ $painb2, zombie_painb3 ] {ai_pain(2);};
|
||||||
|
void() zombie_painb3 =[ $painb3, zombie_painb4 ] {ai_pain(8);};
|
||||||
|
void() zombie_painb4 =[ $painb4, zombie_painb5 ] {ai_pain(6);};
|
||||||
|
void() zombie_painb5 =[ $painb5, zombie_painb6 ] {ai_pain(2);};
|
||||||
|
void() zombie_painb6 =[ $painb6, zombie_painb7 ] {};
|
||||||
|
void() zombie_painb7 =[ $painb7, zombie_painb8 ] {};
|
||||||
|
void() zombie_painb8 =[ $painb8, zombie_painb9 ] {};
|
||||||
|
void() zombie_painb9 =[ $painb9, zombie_painb10 ] {sound (self, CHAN_BODY, "zombie/z_fall.wav", 1, ATTN_NORM);};
|
||||||
|
void() zombie_painb10 =[ $painb10, zombie_painb11 ] {};
|
||||||
|
void() zombie_painb11 =[ $painb11, zombie_painb12 ] {};
|
||||||
|
void() zombie_painb12 =[ $painb12, zombie_painb13 ] {};
|
||||||
|
void() zombie_painb13 =[ $painb13, zombie_painb14 ] {};
|
||||||
|
void() zombie_painb14 =[ $painb14, zombie_painb15 ] {};
|
||||||
|
void() zombie_painb15 =[ $painb15, zombie_painb16 ] {};
|
||||||
|
void() zombie_painb16 =[ $painb16, zombie_painb17 ] {};
|
||||||
|
void() zombie_painb17 =[ $painb17, zombie_painb18 ] {};
|
||||||
|
void() zombie_painb18 =[ $painb18, zombie_painb19 ] {};
|
||||||
|
void() zombie_painb19 =[ $painb19, zombie_painb20 ] {};
|
||||||
|
void() zombie_painb20 =[ $painb20, zombie_painb21 ] {};
|
||||||
|
void() zombie_painb21 =[ $painb21, zombie_painb22 ] {};
|
||||||
|
void() zombie_painb22 =[ $painb22, zombie_painb23 ] {};
|
||||||
|
void() zombie_painb23 =[ $painb23, zombie_painb24 ] {};
|
||||||
|
void() zombie_painb24 =[ $painb24, zombie_painb25 ] {};
|
||||||
|
void() zombie_painb25 =[ $painb25, zombie_painb26 ] {ai_painforward(1);};
|
||||||
|
void() zombie_painb26 =[ $painb26, zombie_painb27 ] {};
|
||||||
|
void() zombie_painb27 =[ $painb27, zombie_painb28 ] {};
|
||||||
|
void() zombie_painb28 =[ $painb28, zombie_run1 ] {};
|
||||||
|
|
||||||
|
void() zombie_painc1 =[ $painc1, zombie_painc2 ] {sound (self, CHAN_VOICE, "zombie/z_pain1.wav", 1, ATTN_NORM);};
|
||||||
|
void() zombie_painc2 =[ $painc2, zombie_painc3 ] {};
|
||||||
|
void() zombie_painc3 =[ $painc3, zombie_painc4 ] {ai_pain(3);};
|
||||||
|
void() zombie_painc4 =[ $painc4, zombie_painc5 ] {ai_pain(1);};
|
||||||
|
void() zombie_painc5 =[ $painc5, zombie_painc6 ] {};
|
||||||
|
void() zombie_painc6 =[ $painc6, zombie_painc7 ] {};
|
||||||
|
void() zombie_painc7 =[ $painc7, zombie_painc8 ] {};
|
||||||
|
void() zombie_painc8 =[ $painc8, zombie_painc9 ] {};
|
||||||
|
void() zombie_painc9 =[ $painc9, zombie_painc10 ] {};
|
||||||
|
void() zombie_painc10 =[ $painc10, zombie_painc11 ] {};
|
||||||
|
void() zombie_painc11 =[ $painc11, zombie_painc12 ] {ai_painforward(1);};
|
||||||
|
void() zombie_painc12 =[ $painc12, zombie_painc13 ] {ai_painforward(1);};
|
||||||
|
void() zombie_painc13 =[ $painc13, zombie_painc14 ] {};
|
||||||
|
void() zombie_painc14 =[ $painc14, zombie_painc15 ] {};
|
||||||
|
void() zombie_painc15 =[ $painc15, zombie_painc16 ] {};
|
||||||
|
void() zombie_painc16 =[ $painc16, zombie_painc17 ] {};
|
||||||
|
void() zombie_painc17 =[ $painc17, zombie_painc18 ] {};
|
||||||
|
void() zombie_painc18 =[ $painc18, zombie_run1 ] {};
|
||||||
|
|
||||||
|
void() zombie_paind1 =[ $paind1, zombie_paind2 ] {sound (self, CHAN_VOICE, "zombie/z_pain.wav", 1, ATTN_NORM);};
|
||||||
|
void() zombie_paind2 =[ $paind2, zombie_paind3 ] {};
|
||||||
|
void() zombie_paind3 =[ $paind3, zombie_paind4 ] {};
|
||||||
|
void() zombie_paind4 =[ $paind4, zombie_paind5 ] {};
|
||||||
|
void() zombie_paind5 =[ $paind5, zombie_paind6 ] {};
|
||||||
|
void() zombie_paind6 =[ $paind6, zombie_paind7 ] {};
|
||||||
|
void() zombie_paind7 =[ $paind7, zombie_paind8 ] {};
|
||||||
|
void() zombie_paind8 =[ $paind8, zombie_paind9 ] {};
|
||||||
|
void() zombie_paind9 =[ $paind9, zombie_paind10 ] {ai_pain(1);};
|
||||||
|
void() zombie_paind10 =[ $paind10, zombie_paind11 ] {};
|
||||||
|
void() zombie_paind11 =[ $paind11, zombie_paind12 ] {};
|
||||||
|
void() zombie_paind12 =[ $paind12, zombie_paind13 ] {};
|
||||||
|
void() zombie_paind13 =[ $paind13, zombie_run1 ] {};
|
||||||
|
|
||||||
|
void() zombie_paine1 =[ $paine1, zombie_paine2 ] {
|
||||||
|
sound (self, CHAN_VOICE, "zombie/z_pain.wav", 1, ATTN_NORM);
|
||||||
|
self.health = 60;
|
||||||
|
};
|
||||||
|
void() zombie_paine2 =[ $paine2, zombie_paine3 ] {ai_pain(8);};
|
||||||
|
void() zombie_paine3 =[ $paine3, zombie_paine4 ] {ai_pain(5);};
|
||||||
|
void() zombie_paine4 =[ $paine4, zombie_paine5 ] {ai_pain(3);};
|
||||||
|
void() zombie_paine5 =[ $paine5, zombie_paine6 ] {ai_pain(1);};
|
||||||
|
void() zombie_paine6 =[ $paine6, zombie_paine7 ] {ai_pain(2);};
|
||||||
|
void() zombie_paine7 =[ $paine7, zombie_paine8 ] {ai_pain(1);};
|
||||||
|
void() zombie_paine8 =[ $paine8, zombie_paine9 ] {ai_pain(1);};
|
||||||
|
void() zombie_paine9 =[ $paine9, zombie_paine10 ] {ai_pain(2);};
|
||||||
|
void() zombie_paine10 =[ $paine10, zombie_paine11 ] {
|
||||||
|
sound (self, CHAN_BODY, "zombie/z_fall.wav", 1, ATTN_NORM);
|
||||||
|
self.solid = SOLID_NOT;
|
||||||
|
};
|
||||||
|
void() zombie_paine11 =[ $paine11, zombie_paine12 ] {self.nextthink = time + 5;self.health = 60;};
|
||||||
|
void() zombie_paine12 =[ $paine12, zombie_paine13 ]{
|
||||||
|
// see if ok to stand up
|
||||||
|
self.health = 60;
|
||||||
|
sound (self, CHAN_VOICE, "zombie/z_idle.wav", 1, ATTN_IDLE);
|
||||||
|
self.solid = SOLID_SLIDEBOX;
|
||||||
|
if (!walkmove (0, 0))
|
||||||
|
{
|
||||||
|
self.think = zombie_paine11;
|
||||||
|
self.solid = SOLID_NOT;
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
void() zombie_paine13 =[ $paine13, zombie_paine14 ] {};
|
||||||
|
void() zombie_paine14 =[ $paine14, zombie_paine15 ] {};
|
||||||
|
void() zombie_paine15 =[ $paine15, zombie_paine16 ] {};
|
||||||
|
void() zombie_paine16 =[ $paine16, zombie_paine17 ] {};
|
||||||
|
void() zombie_paine17 =[ $paine17, zombie_paine18 ] {};
|
||||||
|
void() zombie_paine18 =[ $paine18, zombie_paine19 ] {};
|
||||||
|
void() zombie_paine19 =[ $paine19, zombie_paine20 ] {};
|
||||||
|
void() zombie_paine20 =[ $paine20, zombie_paine21 ] {};
|
||||||
|
void() zombie_paine21 =[ $paine21, zombie_paine22 ] {};
|
||||||
|
void() zombie_paine22 =[ $paine22, zombie_paine23 ] {};
|
||||||
|
void() zombie_paine23 =[ $paine23, zombie_paine24 ] {};
|
||||||
|
void() zombie_paine24 =[ $paine24, zombie_paine25 ] {};
|
||||||
|
void() zombie_paine25 =[ $paine25, zombie_paine26 ] {ai_painforward(5);};
|
||||||
|
void() zombie_paine26 =[ $paine26, zombie_paine27 ] {ai_painforward(3);};
|
||||||
|
void() zombie_paine27 =[ $paine27, zombie_paine28 ] {ai_painforward(1);};
|
||||||
|
void() zombie_paine28 =[ $paine28, zombie_paine29 ] {ai_pain(1);};
|
||||||
|
void() zombie_paine29 =[ $paine29, zombie_paine30 ] {};
|
||||||
|
void() zombie_paine30 =[ $paine30, zombie_run1 ] {};
|
||||||
|
|
||||||
|
void() zombie_die =
|
||||||
|
{
|
||||||
|
sound (self, CHAN_VOICE, "zombie/z_gib.wav", 1, ATTN_NORM);
|
||||||
|
ThrowHead ("progs/h_zombie.mdl", self.health);
|
||||||
|
ThrowGib ("progs/gib1.mdl", self.health);
|
||||||
|
ThrowGib ("progs/gib2.mdl", self.health);
|
||||||
|
ThrowGib ("progs/gib3.mdl", self.health);
|
||||||
|
};
|
||||||
|
|
||||||
|
/*
|
||||||
|
=================
|
||||||
|
zombie_pain
|
||||||
|
|
||||||
|
Zombies can only be killed (gibbed) by doing 60 hit points of damage
|
||||||
|
in a single frame (rockets, grenades, quad shotgun, quad nailgun).
|
||||||
|
|
||||||
|
A hit of 25 points or more (super shotgun, quad nailgun) will allways put it
|
||||||
|
down to the ground.
|
||||||
|
|
||||||
|
A hit of from 10 to 40 points in one frame will cause it to go down if it
|
||||||
|
has been twice in two seconds, otherwise it goes into one of the four
|
||||||
|
fast pain frames.
|
||||||
|
|
||||||
|
A hit of less than 10 points of damage (winged by a shotgun) will be ignored.
|
||||||
|
|
||||||
|
FIXME: don't use pain_finished because of nightmare hack
|
||||||
|
=================
|
||||||
|
*/
|
||||||
|
void(entity attacker, float take) zombie_pain =
|
||||||
|
{
|
||||||
|
local float r;
|
||||||
|
|
||||||
|
self.health = 60; // allways reset health
|
||||||
|
|
||||||
|
if (take < 9)
|
||||||
|
return; // totally ignore
|
||||||
|
|
||||||
|
if (self.inpain == 2)
|
||||||
|
return; // down on ground, so don't reset any counters
|
||||||
|
|
||||||
|
// go down immediately if a big enough hit
|
||||||
|
if (take >= 25)
|
||||||
|
{
|
||||||
|
self.inpain = 2;
|
||||||
|
zombie_paine1 ();
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (self.inpain)
|
||||||
|
{
|
||||||
|
// if hit again in next gre seconds while not in pain frames, definately drop
|
||||||
|
self.pain_finished = time + 3;
|
||||||
|
return; // currently going through an animation, don't change
|
||||||
|
}
|
||||||
|
|
||||||
|
if (self.pain_finished > time)
|
||||||
|
{
|
||||||
|
// hit again, so drop down
|
||||||
|
self.inpain = 2;
|
||||||
|
zombie_paine1 ();
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// gp into one of the fast pain animations
|
||||||
|
self.inpain = 1;
|
||||||
|
|
||||||
|
r = random();
|
||||||
|
if (r < 0.25)
|
||||||
|
zombie_paina1 ();
|
||||||
|
else if (r < 0.5)
|
||||||
|
zombie_painb1 ();
|
||||||
|
else if (r < 0.75)
|
||||||
|
zombie_painc1 ();
|
||||||
|
else
|
||||||
|
zombie_paind1 ();
|
||||||
|
};
|
||||||
|
|
||||||
|
//============================================================================
|
||||||
|
|
||||||
|
/*QUAKED monster_zombie (1 0 0) (-16 -16 -24) (16 16 32) Crucified ambush
|
||||||
|
|
||||||
|
If crucified, stick the bounding box 12 pixels back into a wall to look right.
|
||||||
|
*/
|
||||||
|
void() monster_zombie =
|
||||||
|
{
|
||||||
|
if (deathmatch)
|
||||||
|
{
|
||||||
|
remove(self);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
precache_model ("progs/zombie.mdl");
|
||||||
|
precache_model ("progs/h_zombie.mdl");
|
||||||
|
precache_model ("progs/zom_gib.mdl");
|
||||||
|
|
||||||
|
precache_sound ("zombie/z_idle.wav");
|
||||||
|
precache_sound ("zombie/z_idle1.wav");
|
||||||
|
precache_sound ("zombie/z_shot1.wav");
|
||||||
|
precache_sound ("zombie/z_gib.wav");
|
||||||
|
precache_sound ("zombie/z_pain.wav");
|
||||||
|
precache_sound ("zombie/z_pain1.wav");
|
||||||
|
precache_sound ("zombie/z_fall.wav");
|
||||||
|
precache_sound ("zombie/z_miss.wav");
|
||||||
|
precache_sound ("zombie/z_hit.wav");
|
||||||
|
precache_sound ("zombie/idle_w2.wav");
|
||||||
|
|
||||||
|
self.solid = SOLID_SLIDEBOX;
|
||||||
|
self.movetype = MOVETYPE_STEP;
|
||||||
|
|
||||||
|
setmodel (self, "progs/zombie.mdl");
|
||||||
|
|
||||||
|
setsize (self, '-16 -16 -24', '16 16 40');
|
||||||
|
self.health = 60;
|
||||||
|
|
||||||
|
self.th_stand = zombie_stand1;
|
||||||
|
self.th_walk = zombie_walk1;
|
||||||
|
self.th_run = zombie_run1;
|
||||||
|
self.th_pain = zombie_pain;
|
||||||
|
self.th_die = zombie_die;
|
||||||
|
self.th_missile = zombie_missile;
|
||||||
|
|
||||||
|
if (self.spawnflags & SPAWN_CRUCIFIED)
|
||||||
|
{
|
||||||
|
self.movetype = MOVETYPE_NONE;
|
||||||
|
zombie_cruc1 ();
|
||||||
|
}
|
||||||
|
else
|
||||||
|
walkmonster_start();
|
||||||
|
};
|
Loading…
Reference in a new issue