fteqw/quakec/fallout2/doors.qc

760 lines
15 KiB
C++
Raw Normal View History

float DOOR_START_OPEN = 1;
float DOOR_DONT_LINK = 4;
float DOOR_GOLD_KEY = 8;
float DOOR_SILVER_KEY = 16;
float DOOR_TOGGLE = 32;
void () door_go_down;
void () door_go_up;
void () door_blocked =
{
if (other.classname == "treasure_chest")
{
remove(other);
return;
}
T_Damage (other, self, self, self.dmg);
if ((self.wait >= MULTICAST_ALL))
{
if ((self.state == STATE_DOWN))
{
door_go_up ();
}
else
{
door_go_down ();
}
}
};
void () door_hit_top =
{
sound (self, (CHAN_NO_PHS_ADD + CHAN_VOICE), self.noise1, DOOR_START_OPEN, ATTN_NORM);
self.state = STATE_TOP;
if ((self.spawnflags & DOOR_TOGGLE))
{
return;
}
if (self.owner.rtime == 0)
{
self.think = door_go_down;
self.nextthink = (self.ltime + self.wait);
}
};
void () door_hit_bottom =
{
sound (self, (CHAN_NO_PHS_ADD + CHAN_VOICE), self.noise1, DOOR_START_OPEN, ATTN_NORM);
self.state = STATE_BOTTOM;
};
void () door_go_down =
{
sound (self, CHAN_VOICE, self.noise2, DOOR_START_OPEN, ATTN_NORM);
if (self.max_health)
{
self.takedamage = DAMAGE_YES;
self.health = self.max_health;
}
self.state = STATE_DOWN;
SUB_CalcMove (self.pos1, self.speed, door_hit_bottom);
};
void () door_go_up =
{
if (self.state == STATE_UP)
return; // allready going up
if (self.state == STATE_TOP)
{ // reset top wait time
self.nextthink = self.ltime + self.wait;
return;
}
sound (self, CHAN_VOICE, self.noise2, 1, ATTN_NORM);
self.state = STATE_UP;
SUB_CalcMove (self.pos2, self.speed, door_hit_top);
SUB_UseTargets();
};
void () door_fire =
{
local entity oself;
local entity starte;
if ((self.owner != self))
{
objerror ("door_fire: self.owner != self");
}
if (self.items)
{
sound (self, CHAN_VOICE, self.noise4, DOOR_START_OPEN, ATTN_NORM);
}
self.message = string_null;
oself = self;
if ((self.spawnflags & DOOR_TOGGLE))
{
if (((self.state == STATE_UP) || (self.state == STATE_TOP)))
{
starte = self;
do
{
door_go_down ();
self = self.enemy;
} while (((self != starte) && (self != world)));
self = oself;
return;
}
}
starte = self;
do
{
door_go_up ();
self = self.enemy;
} while (((self != starte) && (self != world)));
self = oself;
};
void () door_use =
{
local entity oself;
self.message = "";
self.owner.message = "";
self.enemy.message = "";
oself = self;
self = self.owner;
door_fire ();
self = oself;
};
void () door_trigger_touch =
{
if (!triggercantouch(self, other))
return;
if ((other.health <= MULTICAST_ALL))
{
return;
}
if ((time < self.attack_finished))
{
return;
}
self.attack_finished = (time + DOOR_START_OPEN);
activator = other;
self = self.owner;
door_use ();
};
void () door_killed =
{
local entity oself;
oself = self;
self = self.owner;
self.health = self.max_health;
self.takedamage = DAMAGE_NO;
door_use ();
self = oself;
};
void () OpenDoorBeep =
{
local float r,x;
r = range (self.enemy);
if (r != RANGE_MELEE)
{
self.owner.owner.rtime = 0;
remove(self);
return;
}
if (random()*3<1.5)
sound (self, CHAN_BODY, "items/lockpick1.wav", 1, ATTN_NORM);
else
sound (self, CHAN_BODY, "items/lockpick2.wav", 1, ATTN_NORM);
x = (2.51 - (2.5*(self.enemy.skill_sneak/30)));
self.think = OpenDoorBeep;
self.nextthink = time + x;
if (ToIID(self.enemy.islot4) == IID_EQUIP_TOOLKIT)
self.owner.owner.rtime = self.owner.owner.rtime + 3;
else
self.owner.owner.rtime = self.owner.owner.rtime + 1;
self.frame = floor ((self.owner.owner.rtime / 12) * 7);
if (self.owner.owner.rtime >= 12)
{
sound (self, CHAN_BODY, "misc/basekey.wav", 1, ATTN_NORM);
self.think = SUB_Remove;
self.nextthink = time + 1;
return;
}
};
void (entity portal, entity toucher) SpawnOpenDoor =
{
local entity open;
open = spawn();
setorigin (open, toucher.origin + '0 0 48');
setmodel (open, "progs/hbar.spr");
setsize (open, VEC_ORIGIN, VEC_ORIGIN);
open.think = OpenDoorBeep;
open.nextthink = time + 1;
open.enemy = toucher;
open.owner = portal;
};
void () door_touch =
{
if (!triggercantouch(self, other))
return;
if (other.classname != "player")
return;
if (self.owner.attack_finished > time)
return;
if (self.state != STATE_BOTTOM)
return;
if (self.size_y > 64 && self.size_x > 64)
return;
self.owner.attack_finished = (time + WEAPON_ROCKET);
if ((self.owner.message != ""))
{
centerprint (other, self.owner.message);
sound (other, CHAN_VOICE, "misc/talk.wav", DOOR_START_OPEN, ATTN_NORM);
}
if (!self.items)
return;
if (self.owner.rtime > 0 && self.owner.rtime < 12)
return;
if ((self.size_z <= 160) && self.owner.rtime == 0 && self.items & other.items != self.items)
{
if (self.size_y <= 128 && self.size_x <= 128)
{
if (other.perk1 == 4 || other.perk2 == 4)
{
self.owner.rtime = 12;
sound (other, CHAN_VOICE, "player/berserk.wav", 1, ATTN_NORM);
door_use ();
loud_noise(200);
}
else if (self.owner.items == IT_KEY1)
{
SpawnOpenDoor(self, other);
return;
}
else if (self.owner.items == IT_KEY2)
{
sprint(other, 2, "picking...\n");
other.attack_finished = time + 7;
other.rtime = time + 7.5;
SpawnOpenDoor(self, other);
return;
}
if (self.owner.items == IT_KEY1)
sound (self, CHAN_VOICE, self.noise3, 1, ATTN_NORM);
if (self.owner.items == IT_KEY2)
sound (self, CHAN_VOICE, self.noise3, 1, ATTN_NORM);
return;
}
}
if (self.owner.rtime >= 12)
{
door_use ();
return;
}
door_use ();
};
entity (vector fmins, vector fmaxs) spawn_field =
{
local entity trigger;
local vector t1;
local vector t2;
trigger = spawn ();
trigger.team = self.team;
trigger.movetype = MOVETYPE_NONE;
trigger.solid = SOLID_TRIGGER;
trigger.owner = self;
trigger.touch = door_trigger_touch;
t1 = fmins;
t2 = fmaxs;
setsize (trigger, (t1 - '60 60 8'), (t2 + '60 60 8'));
return (trigger);
};
float (entity e1, entity e2) EntitiesTouching =
{
if ((e1.mins_x > e2.maxs_x))
{
return (FALSE);
}
if ((e1.mins_y > e2.maxs_y))
{
return (FALSE);
}
if ((e1.mins_z > e2.maxs_z))
{
return (FALSE);
}
if ((e1.maxs_x < e2.mins_x))
{
return (FALSE);
}
if ((e1.maxs_y < e2.mins_y))
{
return (FALSE);
}
if ((e1.maxs_z < e2.mins_z))
{
return (FALSE);
}
return (TRUE);
};
void () LinkDoors =
{
local entity t;
local entity starte;
local vector cmins;
local vector cmaxs;
if (self.enemy)
{
return;
}
if ((self.spawnflags & DOOR_DONT_LINK))
{
self.enemy = self;
self.owner = self;
return;
}
cmins = self.mins;
cmaxs = self.maxs;
starte = self;
t = self;
do
{
self.owner = starte;
if (self.health)
{
starte.health = self.health;
}
if (self.targetname)
{
starte.targetname = self.targetname;
}
if ((self.message != ""))
{
starte.message = self.message;
}
t = find (t, classname, self.classname);
if (!t)
{
self.enemy = starte;
self = self.owner;
if (self.health)
{
return;
}
if (self.targetname)
{
return;
}
if (self.items)
{
return;
}
self.owner.trigger_field = spawn_field (cmins, cmaxs);
return;
}
if (EntitiesTouching (self, t))
{
if (t.enemy)
{
objerror ("cross connected doors");
}
self.enemy = t;
self = t;
if ((t.mins_x < cmins_x))
{
cmins_x = t.mins_x;
}
if ((t.mins_y < cmins_y))
{
cmins_y = t.mins_y;
}
if ((t.mins_z < cmins_z))
{
cmins_z = t.mins_z;
}
if ((t.maxs_x > cmaxs_x))
{
cmaxs_x = t.maxs_x;
}
if ((t.maxs_y > cmaxs_y))
{
cmaxs_y = t.maxs_y;
}
if ((t.maxs_z > cmaxs_z))
{
cmaxs_z = t.maxs_z;
}
}
} while (DOOR_START_OPEN);
};
void () func_door =
{
local float r;
if ((world.worldtype == MULTICAST_ALL))
{
precache_sound ("doors/medtry.wav");
precache_sound ("doors/meduse.wav");
self.noise3 = "doors/medtry.wav";
self.noise4 = "doors/meduse.wav";
}
else
{
if ((world.worldtype == DOOR_START_OPEN))
{
precache_sound ("doors/runetry.wav");
precache_sound ("doors/runeuse.wav");
self.noise3 = "doors/runetry.wav";
self.noise4 = "doors/runeuse.wav";
}
else
{
if ((world.worldtype == WEAPON_ROCKET))
{
precache_sound ("doors/basetry.wav");
precache_sound ("doors/baseuse.wav");
self.noise3 = "doors/basetry.wav";
self.noise4 = "doors/baseuse.wav";
}
else
{
dprint ("no worldtype set!\n");
}
}
}
if ((self.sounds == MULTICAST_ALL))
{
precache_sound ("misc/null.wav");
precache_sound ("misc/null.wav");
self.noise1 = "misc/null.wav";
self.noise2 = "misc/null.wav";
}
if ((self.sounds == DOOR_START_OPEN))
{
precache_sound ("doors/drclos4.wav");
precache_sound ("doors/doormv1.wav");
self.noise1 = "doors/drclos4.wav";
self.noise2 = "doors/doormv1.wav";
}
if ((self.sounds == WEAPON_ROCKET))
{
precache_sound ("doors/hydro1.wav");
precache_sound ("doors/hydro2.wav");
self.noise2 = "doors/hydro1.wav";
self.noise1 = "doors/hydro2.wav";
}
if ((self.sounds == AS_MELEE))
{
precache_sound ("doors/stndr1.wav");
precache_sound ("doors/stndr2.wav");
self.noise2 = "doors/stndr1.wav";
self.noise1 = "doors/stndr2.wav";
}
if ((self.sounds == DOOR_DONT_LINK))
{
precache_sound ("doors/ddoor1.wav");
precache_sound ("doors/ddoor2.wav");
self.noise1 = "doors/ddoor2.wav";
self.noise2 = "doors/ddoor1.wav";
}
SetMovedir ();
self.max_health = self.health;
self.solid = SOLID_BSP;
self.movetype = MOVETYPE_PUSH;
setorigin (self, self.origin);
setmodel (self, self.model);
self.classname = "door";
self.blocked = door_blocked;
self.use = door_use;
if (random()<0.20)
self.items = IT_KEY1; //easy-to-pick lock
else if (random()<0.60)
self.items = IT_KEY2; //hard-to-pick lock
if (!self.speed)
{
self.speed = 100;
}
if (!self.wait)
{
self.wait = AS_MELEE;
}
if (!self.lip)
{
self.lip = DOOR_GOLD_KEY;
}
if (!self.dmg)
{
self.dmg = WEAPON_ROCKET;
}
self.pos1 = self.origin;
self.pos2 = (self.pos1 + (self.movedir * (fabs ((self.movedir * self.size)) - self.lip)));
if ((self.spawnflags & DOOR_START_OPEN))
{
setorigin (self, self.pos2);
self.pos2 = self.pos1;
self.pos1 = self.origin;
}
self.state = STATE_BOTTOM;
if (self.health)
{
self.takedamage = DAMAGE_YES;
self.th_die = door_killed;
}
self.touch = door_touch;
self.think = LinkDoors;
self.nextthink = (self.ltime + 0.1);
};
void () fd_secret_move1;
void () fd_secret_move2;
void () fd_secret_move3;
void () fd_secret_move4;
void () fd_secret_move5;
void () fd_secret_move6;
void () fd_secret_done;
float SECRET_OPEN_ONCE = 1;
float SECRET_1ST_LEFT = 2;
float SECRET_1ST_DOWN = 4;
float SECRET_NO_SHOOT = 8;
float SECRET_YES_SHOOT = 16;
void () fd_secret_use =
{
local float temp;
self.health = 10000;
if ((self.origin != self.oldorigin))
{
return;
}
self.message = string_null;
SUB_UseTargets ();
if (!(self.spawnflags & SECRET_NO_SHOOT))
{
self.th_pain = SUB_Null;
self.takedamage = DAMAGE_NO;
}
self.velocity = VEC_ORIGIN;
sound (self, CHAN_VOICE, self.noise1, SECRET_OPEN_ONCE, ATTN_NORM);
self.nextthink = (self.ltime + 0.1);
temp = (SECRET_OPEN_ONCE - (self.spawnflags & SECRET_1ST_LEFT));
makevectors (self.mangle);
if (!self.t_width)
{
if ((self.spawnflags & SECRET_1ST_DOWN))
{
self.t_width = fabs ((v_up * self.size));
}
else
{
self.t_width = fabs ((v_right * self.size));
}
}
if (!self.t_length)
{
self.t_length = fabs ((v_forward * self.size));
}
if ((self.spawnflags & SECRET_1ST_DOWN))
{
self.dest1 = (self.origin - (v_up * self.t_width));
}
else
{
self.dest1 = (self.origin + (v_right * (self.t_width * temp)));
}
self.dest2 = (self.dest1 + (v_forward * self.t_length));
SUB_CalcMove (self.dest1, self.speed, fd_secret_move1);
sound (self, CHAN_VOICE, self.noise2, SECRET_OPEN_ONCE, ATTN_NORM);
};
void () fd_secret_move1 =
{
self.nextthink = (self.ltime + SECRET_OPEN_ONCE);
self.think = fd_secret_move2;
sound (self, CHAN_VOICE, self.noise3, SECRET_OPEN_ONCE, ATTN_NORM);
};
void () fd_secret_move2 =
{
sound (self, CHAN_VOICE, self.noise2, SECRET_OPEN_ONCE, ATTN_NORM);
SUB_CalcMove (self.dest2, self.speed, fd_secret_move3);
};
void () fd_secret_move3 =
{
sound (self, CHAN_VOICE, self.noise3, SECRET_OPEN_ONCE, ATTN_NORM);
if (!(self.spawnflags & SECRET_OPEN_ONCE))
{
self.nextthink = (self.ltime + self.wait);
self.think = fd_secret_move4;
}
};
void () fd_secret_move4 =
{
sound (self, CHAN_VOICE, self.noise2, SECRET_OPEN_ONCE, ATTN_NORM);
SUB_CalcMove (self.dest1, self.speed, fd_secret_move5);
};
void () fd_secret_move5 =
{
self.nextthink = (self.ltime + SECRET_OPEN_ONCE);
self.think = fd_secret_move6;
sound (self, CHAN_VOICE, self.noise3, SECRET_OPEN_ONCE, ATTN_NORM);
};
void () fd_secret_move6 =
{
sound (self, CHAN_VOICE, self.noise2, SECRET_OPEN_ONCE, ATTN_NORM);
SUB_CalcMove (self.oldorigin, self.speed, fd_secret_done);
};
void () fd_secret_done =
{
if ((!self.targetname || (self.spawnflags & SECRET_YES_SHOOT)))
{
self.health = 10000;
self.takedamage = DAMAGE_YES;
self.th_pain = fd_secret_use;
self.th_die = fd_secret_use;
}
sound (self, (CHAN_NO_PHS_ADD + CHAN_VOICE), self.noise3, SECRET_OPEN_ONCE, ATTN_NORM);
};
void () secret_blocked =
{
if ((time < self.attack_finished))
{
return;
}
self.attack_finished = (time + 0.5);
T_Damage (other, self, self, self.dmg);
};
void () secret_touch =
{
if (!triggercantouch(self, other))
return;
if ((other.classname != "player"))
{
return;
}
if ((self.attack_finished > time))
{
return;
}
self.attack_finished = (time + SECRET_1ST_LEFT);
if (self.message)
{
centerprint (other, self.message);
sound (other, CHAN_BODY, "misc/talk.wav", SECRET_OPEN_ONCE, ATTN_NORM);
}
};
void () func_door_secret =
{
if ((self.sounds == MULTICAST_ALL))
{
self.sounds = AS_MELEE;
}
if ((self.sounds == SECRET_OPEN_ONCE))
{
precache_sound ("doors/latch2.wav");
precache_sound ("doors/winch2.wav");
precache_sound ("doors/drclos4.wav");
self.noise1 = "doors/latch2.wav";
self.noise2 = "doors/winch2.wav";
self.noise3 = "doors/drclos4.wav";
}
if ((self.sounds == SECRET_1ST_LEFT))
{
precache_sound ("doors/airdoor1.wav");
precache_sound ("doors/airdoor2.wav");
self.noise2 = "doors/airdoor1.wav";
self.noise1 = "doors/airdoor2.wav";
self.noise3 = "doors/airdoor2.wav";
}
if ((self.sounds == AS_MELEE))
{
precache_sound ("doors/basesec1.wav");
precache_sound ("doors/basesec2.wav");
self.noise2 = "doors/basesec1.wav";
self.noise1 = "doors/basesec2.wav";
self.noise3 = "doors/basesec2.wav";
}
if (!self.dmg)
{
self.dmg = SECRET_1ST_LEFT;
}
self.mangle = self.angles;
self.angles = VEC_ORIGIN;
self.solid = SOLID_BSP;
self.movetype = MOVETYPE_PUSH;
self.classname = "door";
setmodel (self, self.model);
setorigin (self, self.origin);
self.touch = secret_touch;
self.blocked = secret_blocked;
self.speed = 50;
self.use = fd_secret_use;
if ((!self.targetname || (self.spawnflags & SECRET_YES_SHOOT)))
{
self.health = 10000;
self.takedamage = DAMAGE_YES;
self.th_pain = fd_secret_use;
}
self.oldorigin = self.origin;
if (!self.wait)
{
self.wait = MULTICAST_PVS_R;
}
};