djcev.com

//

Git Repos / fte_dogmode / qc / triggers / teleport.qc

Last update to this file was on 2024-07-03 at 07:20.

Show teleport.qc

//==============================================================================
// TELEPORT TRIGGERS with added functions from Zerstrorer and Qmaster
// -- dumptruck_ds
//==============================================================================

//======================================================================
// constants
//======================================================================

#ifdef SSQC
const float TRIGGER_TELEPORT_ONLYPLAYER = 1;
const float TRIGGER_TELEPORT_SILENT = 2;
const float TRIGGER_TELEPORT_RANDOM = 4;
const float TRIGGER_TELEPORT_STEALTH = 8;
const float TRIGGER_TELEPORT_ONLYMONSTER = 16;
const float TRIGGER_TELEPORT_DD = 32;
#endif

//======================================================================
// forward declarations
//======================================================================

#ifdef SSQC
// tfog & tdeath
void() spawn_tfog_think;
void(vector org) spawn_tfog;
void() spawn_tdeath_touch;
void(vector org, entity death_owner) spawn_tdeath;
#endif

#ifdef SSQC
// trigger_teleport
entity() trigger_teleport_randomspot;
void() trigger_teleport_touch;
void() trigger_teleport_use;
void(entity e) trigger_teleport_init;
void() trigger_teleport;
#endif

//------------------------------------------------------------------------------

//======================================================================
// teleporter fog & teleporter death
//======================================================================

#ifdef SSQC
//----------------------------------------------------------------------
void() spawn_tfog_think =
{
local float v;
local string tmpstr;

v = random() * 5;
if (v < 1)
tmpstr = "misc/r_tele1.wav";
else if (v < 2)
tmpstr = "misc/r_tele2.wav";
else if (v < 3)
tmpstr = "misc/r_tele3.wav";
else if (v < 4)
tmpstr = "misc/r_tele4.wav";
else
tmpstr = "misc/r_tele5.wav";

sound (self, CHAN_VOICE, tmpstr, VOL_HIGH, ATTN_NORM);
remove (self);
};

//----------------------------------------------------------------------
void(vector org) spawn_tfog =
{
local entity s;

s = spawn ();
s.origin = org;
s.spawnflags = self.spawnflags; // dumptruck_ds
s.nextthink = time + 0.2;
s.think = spawn_tfog_think;

WriteByte (MSG_BROADCAST, SVC_TEMPENTITY);
WriteByte (MSG_BROADCAST, TE_TELEPORT);
WriteCoord (MSG_BROADCAST, org_x);
WriteCoord (MSG_BROADCAST, org_y);
WriteCoord (MSG_BROADCAST, org_z);
};

//----------------------------------------------------------------------
void() spawn_tdeath_touch =
{
if (other == self.owner)
return;

// frag anyone who teleports in on top of an invincible player
if (other.classtype == CT_PLAYER)
{
// 1998-07-26 Pentagram telefrag fix by Zoid/Maddes start
if (self.owner.classtype != CT_PLAYER)
{
// other monsters explode themselves
t_damage2 (self.owner, self, self, 50000);
return;
}
// 1998-07-26 Pentagram telefrag fix by Zoid/Maddes end

// 1998-07-26 Pentagram telefrag fix by Zoid/Maddes start
if (other.invincible_finished > time)
{
// player on spot has active pentagram
if (self.owner.invincible_finished > time)
{
// teleported player has active pentagram too
// can happen often in deathmatch 4
// and levels with more than one pentagram
self.classname = "teledeath3";
other.invincible_finished = 0;
// kill player on spot
t_damage2 (other, self, self, 50000);

/*
// 1998-07-26 only telefrag player on spot
// by Maddes
local entity other2;
other2 = self.owner;
self.owner = other;
other2.invincible_finished = 0;
// kill teleported player
T_Damage (other2, self, self, 50000);
*/
}
else
{
// 1998-07-26 Pentagram telefrag fix by
// Zoid/Maddes end
self.classname = "teledeath2";
// 1998-07-26 Pentagram telefrag fix by
// Zoid/Maddes start
t_damage2 (self.owner, self, self, 50000);
}
return;
}

/*
if (self.owner.classtype != CT_PLAYER)
{ // other monsters explode themselves
T_Damage (self.owner, self, self, 50000);
return;
}
*/
// 1998-07-26 Pentagram telefrag fix by Zoid/Maddes end
}

if (other.health)
t_damage2 (other, self, self, 50000);
};

//----------------------------------------------------------------------
void(vector org, entity death_owner) spawn_tdeath =
{
local entity death;

death = spawn ();
death.classname = "teledeath";
death.movetype = MOVETYPE_NONE;
death.solid = SOLID_TRIGGER;
death.angles = '0 0 0';
setsize (death, death_owner.mins - '1 1 1', death_owner.maxs + '1 1 1');
setorigin (death, org);
death.touch = spawn_tdeath_touch;
death.nextthink = time + 0.2;
death.think = sub_remove;
death.owner = death_owner;

// make sure even still objects get hit
force_retouch = 2;
};
#endif

//======================================================================
// trigger_teleport
//======================================================================

#ifdef SSQC
/*QUAKED trigger_teleport (.5 .5 .5) ? TRIGGER_TELEPORT_ONLYPLAYER TRIGGER_TELEPORT_SILENT TRIGGER_TELEPORT_RANDOM TRIGGER_TELEPORT_STEALTH X X X X NOT_ON_EASY NOT_ON_NORMAL NOT_ON_HARD_OR_NIGHTMARE NOT_IN_DEATHMATCH NOT_IN_COOP NOT_IN_SINGLEPLAYER X NOT_ON_HARD_ONLY NOT_ON_NIGHTMARE_ONLY

Any object touching this will be transported to the corresponding
info_teleport_destination entity. You must set the "target" field,
and create an object with a "targetname" field that matches.

If the trigger_teleport has a targetname, it will only teleport entities
when it has been fired.

TRIGGER_TELEPORT_SILENT(2) eliminates the teleporter ambient noise (good
for hidden monster teleporters.

TRIGGER_TELEPORT_RANDOM(4) causes the teleporter to send the player to a
random destination among the info_teleport_random markers in the level.
You MUST place a "count" field that is the number of info_teleport_random
entities you placed.

TRIGGER_TELEPORT_STEALTH(8) eliminates the particle flash and noise when
an entity is teleported.

TRIGGER_TELEPORT_ONLYMONSTER(16) will only teleport monsters
*/
//----------------------------------------------------------------------
// class trigger_teleport: base_trigger
// {
//--------------------------------------------------------------
// trigger_teleport_randomspot -- more Zerstrorer -- dumptruck_ds
// teleport_randomspot - returns a random spot to teleport to
// among all of the "info_teleport_random" entities in the level.
// self.count is the number of spots
//--------------------------------------------------------------
entity() trigger_teleport_randomspot =
{
local float rndm;
// local float rndm, num1;
local entity spot, first;

rndm = rint (random() * (self.count - 1));
spot = findfloat (world, classtype, CT_INFO_TELEPORT_RANDOM);
if (!spot)
dprint ("trigger_teleport_randomspot: "
"no random teleport points found!\n");
first = spot;

while (rndm > 0)
{
rndm = rndm - 1;
spot = findfloat (spot, classtype,
CT_INFO_TELEPORT_RANDOM);
}

if (spot == world)
{
dprint ("trigger_teleport_randomspot: "
"random spot found world!!\n");
spot = first;
}

return spot;
};
// end dumptruck_ds

//--------------------------------------------------------------
void() trigger_teleport_touch =
{
local entity t;
local vector org;

if (self.estate != STATE_ACTIVE)
return;

if (self.targetname != "")
if (self.nextthink < time)
// not fired yet
return;

if (self.spawnflags & TRIGGER_TELEPORT_ONLYPLAYER)
if (other.classtype != CT_PLAYER &&
other.classtype != CT_PROJECTILE_GRENADE)
return;

// is this going to work? dumptruck_ds
if (self.spawnflags & TRIGGER_TELEPORT_ONLYMONSTER)
if (other.classtype == CT_PLAYER)
return;

// from Copper -- dumptruck_ds
if (other.movetype == MOVETYPE_NOCLIP)
return;

// Supa, is this trigger waiting to be activated?
if (self.is_waiting == TRUE)
return;

// Special case
if (self.is_waiting != -1)
if (self.targetname != "")
if (self.nextthink < time)
// not fired yet
return;

// only teleport living creatures (and projectiles)
if (other.health <= 0 || (other.solid != SOLID_SLIDEBOX &&
other.solid != SOLID_BBOX))
return;

sub_usetargets ();

// put a tfog where the player was
// ### dhm - if stealth, don't spawn a fog
if (!(self.spawnflags & TRIGGER_TELEPORT_STEALTH))
spawn_tfog (other.origin);

// dhm - if this is a random teleporter, pick a random spot!
if (self.spawnflags & TRIGGER_TELEPORT_RANDOM)
{
t = trigger_teleport_randomspot ();
}
else if ((self.spawnflags & TRIGGER_TELEPORT_DD) &&
other.classtype == CT_PLAYER)
{
t = find (world, targetname, self.noise);
}
else
{
t = find (world, targetname, self.target);
}

if (!t)
objerror ("trigger_teleport_touch: couldn't "
"find target");

// put a tfog where the player was
/*
spawn_tfog (other.origin);

t = find (world, targetname, self.target);
if (!t)
objerror ("couldn't find target");
*/

// spawn a tfog flash in front of the destination
makevectors (t.mangle);
org = t.origin + 32 * v_forward;

// ### dhm - if stealth, don't spawn a fog
if (!(self.spawnflags & TRIGGER_TELEPORT_STEALTH))
spawn_tfog (org);

spawn_tdeath (t.origin, other);

// move the player and lock him down for a little while
if (!other.health)
{
other.origin = t.origin;
other.velocity = (v_forward * other.velocity_x) +
(v_forward * other.velocity_y);
return;
}

setorigin (other, t.origin);
other.angles = t.mangle;

if (other.classtype == CT_PLAYER)
{
// retrieves fog values from teleport destination,
// if any
fog_set_from_ent (other, t);

// turn this way immediately
other.fixangle = 1;
other.teleport_time = time + 0.7;
other.velocity = v_forward * PM_MAXSPEED;
// TODO CEV commented out the next line
// other.flags -= other.flags & FL_ONGROUND;
}

if ((self.spawnflags & TRIGGER_TELEPORT_ONLYMONSTER) &&
other.classtype != CT_PLAYER)
{
// turn this way immediately
other.fixangle = 1;
other.teleport_time = time + 0.7;
other.velocity = v_forward * 300;
if (other.flags & FL_ONGROUND)
other.flags -= other.flags & FL_ONGROUND;
}
};

//--------------------------------------------------------------
void() trigger_teleport_use =
{
self.nextthink = time + 0.2;
// make sure even still objects get hit
force_retouch = 2;
self.think = sub_null;
};

//--------------------------------------------------------------
void(entity e) trigger_teleport_init =
{
e.classname = "trigger_teleport";
e.classtype = CT_TRIGGER_TELEPORT;
base_trigger_init (e);

e.touch = trigger_teleport_touch;
e.use = trigger_teleport_use;

// find the destination
if (!e.target)
objerror ("trigger_teleport_init: no target");

if (!(e.spawnflags & TRIGGER_TELEPORT_SILENT))
{
precache_sound ("ambience/hum1.wav");
// volume was 0.5 -- CEV
ambientsound ((e.mins + e.maxs) * 0.5,
"ambience/hum1.wav", VOL_LOW, ATTN_STATIC);
}

sub_checkwaiting (e);
};

//--------------------------------------------------------------
void() trigger_teleport =
{
// new spawnflags for all entities -- iw
if (SUB_Inhibit())
return;

trigger_teleport_init (self);
};
// };
#endif

Return to the top of this page or return to the overview of this repo.

Log teleport.qc

Return to the top of this page or return to the overview of this repo.