Git Repos / fte_dogmode / commit 5b4a9d6
Commit: 5b4a9d6f6aeb8222378215d455ccec45d498795a
Parent: 7472ec54954781085e2524e76329e70a4392791e
Author: Cameron Vanderzanden, 2023-11-16 15:13
Committer: Cameron Vanderzanden, 2023-11-16 15:13
Commit Message
pmove bug fixes, moved q3 compat code, cleanup Fixed the handling of roof planes in the pmove stepup code (storing an extra plane normal & fraction now but I don't see a way around it). Also moved some code out of client.qc and into pmove.qc to centralize and simplify movement flag handling. Also changed the way trace_ents are touched in the slidemove. Tracked down & identified the source of player jitteriness - PM_Nudge adjusting origin on the client side due to lack of data precision when the server sends player coordinates. This is now solved by setting sv_bigcoords to 1 in autoexec.cfg, and the PM_Nudge check at the top of PM_Move now only runs when sv_bigcoords is 0. Moved some q3 specific entrypoints into their own file compat_quake3.qc. Enabled additional fteqcc warnings then cleaned up some code to silence those new warnings. Moved individual trigger_name.qc files into their own subdirectory, triggers/. Plus more changes I'm sure I'm forgetting.
Change List
? | File | Add | Del |
---|---|---|---|
A | autoexec.cfg | +2 | |
M | build.sh | +2 | -2 |
M | qc/ai.qc | +6 | -4 |
M | qc/client.qc | +16 | -35 |
A | qc/compat_quake3.qc | +76 | |
M | qc/cshift.qc | +48 | -44 |
M | qc/csqc/csqc_defsbuiltins.qc | -8 | |
M | qc/csqc/csqc_defsclient.qc | -1 | |
M | qc/csqc/csqc_entrypoints.qc | -11 | |
M | qc/csqc/csqc_hudvanilla.qc | +7 | -5 |
M | qc/csqc/csqc_player.qc | +5 | -5 |
M | qc/cutscene.qc | +6 | -5 |
M | qc/defs_misc.qc | +3 | |
M | qc/fight.qc | +3 | -3 |
M | qc/func_fall2.qc | +7 | -6 |
M | qc/items_armor.qc | -13 | |
M | qc/items_health.qc | -7 | |
M | qc/lights.qc | +82 | -95 |
M | qc/monsters/oldone.qc | +3 | -2 |
M | qc/plats.qc | +5 | -2 |
M | qc/pmove.qc | +167 | -123 |
M | qc/progs.src | +8 | -6 |
A | qc/triggers/heal.qc | +179 | |
A | qc/triggers/ladder.qc | +67 | |
A | qc/triggers/push.qc | +429 | |
A | qc/triggers/shake.qc | +122 | |
A | qc/triggers/teleport.qc | +493 | |
A | qc/triggers/textstory.qc | +225 | |
D | qc/triggers_heal.qc | -179 | |
D | qc/triggers_ladder.qc | -67 | |
D | qc/triggers_push.qc | -452 | |
D | qc/triggers_shake.qc | -122 | |
D | qc/triggers_teleport.qc | -512 | |
D | qc/triggers_textstory.qc | -225 | |
M | qc/weapons.qc | +2 | -2 |
Diff autoexec.cfg
diff --git a/autoexec.cfg b/autoexec.cfg
new file mode 100644
index 0000000..d7796bc
--- /dev/null
+++ b/autoexec.cfg
@@ -0,0 +1,2 @@
+pm_airstep 1
+sv_bigcoords 1
Return to the top of this page or return to the overview of this repo.
Diff build.sh
diff --git a/build.sh b/build.sh
index 9f27b6f..f905f62 100755
--- a/build.sh
+++ b/build.sh
@@ -6,6 +6,6 @@ CLIENTQCDIR=$SRCDIR/qc/csqc
SERVERQCDIR=$SRCDIR/qc
cd $CLIENTQCDIR
-$FTEQCC csqc_progs.src
+$FTEQCC -Wall -O2 csqc_progs.src
cd $SERVERQCDIR
-$FTEQCC progs.src
+$FTEQCC -Wall -O2 progs.src
Return to the top of this page or return to the overview of this repo.
Diff qc/ai.qc
diff --git a/qc/ai.qc b/qc/ai.qc
index 0d8f18a..f123707 100644
--- a/qc/ai.qc
+++ b/qc/ai.qc
@@ -91,16 +91,18 @@ Monsters will continue walking towards the next target corner.
*/
void() path_corner =
{
- if (SUB_Inhibit ()) // new spawnflags for all entities -- iw
+ // new spawnflags for all entities -- iw
+ if (SUB_Inhibit())
return;
- if (self.noise) precache_sound(self.noise);
- if (self.noise2) precache_sound(self.noise2);
+ if (self.noise != __NULL__ && self.noise != "")
+ precache_sound (self.noise);
+ if (self.noise2 != __NULL__ && self.noise2 != "")
+ precache_sound (self.noise2);
movetarget_f ();
};
-
/*
=============
t_movetarget
Return to the top of this page or return to the overview of this repo.
Diff qc/client.qc
diff --git a/qc/client.qc b/qc/client.qc
index 208459d..605d26d 100644
--- a/qc/client.qc
+++ b/qc/client.qc
@@ -601,16 +601,23 @@ void() PlayerJump =
}
if (!(self.flags & FL_ONGROUND))
+ {
+ dprint ("PlayerJump: player is not on ground, returning\n");
return;
+ }
if (!(self.flags & FL_JUMPRELEASED))
+ {
// don't pogo stick
+ dprint ("PlayerJump: player is holding jump, returning\n");
return;
+ }
- self.flags = self.flags - (self.flags & FL_JUMPRELEASED);
+ self.flags &= ~FL_JUMPRELEASED;
+ // self.flags = self.flags - (self.flags & FL_JUMPRELEASED);
// don't stairwalk (not yet anyway)
- self.flags = self.flags - FL_ONGROUND;
+ self.flags &= ~FL_ONGROUND;
self.button2 = 0;
// player jumping sound
@@ -723,8 +730,6 @@ void() WaterMove =
//======================================================================
void() PlayerPreThink =
{
- local float do_ladder_physics;
-
if (intermission_running)
{
// otherwise a button could be missed between the think tics
@@ -740,27 +745,7 @@ void() PlayerPreThink =
return;
}
- // note that this code block is here, before the tests which check
- // whether the player is dead, so that the player's gravity will be
- // correctly updated even if they e.g. fell off a ladder because
- // they died -- iw
- // TODO CEV hacking on ladders
- /*
- if (self.onladder)
- {
- do_ladder_physics = TRUE;
- // not zero because zero means "default"
- self.gravity = 0.0000001;
- self.onladder = 0;
- }
- else
- {
- do_ladder_physics = FALSE;
- */
- self.gravity = self.wantedgravity;
- /*
- }
- */
+ self.gravity = self.wantedgravity;
// If just spawned in, try to recover previous fog values from
// own client entity, if any
@@ -784,11 +769,12 @@ void() PlayerPreThink =
return;
// johnfitz ladder conditions, added from Rubicon2 -- dumptruck_ds
+ /* TODO CEV
if (do_ladder_physics)
{
if (self.button2)
{
- /* no ladder footsteps for now
+ // no ladder footsteps for now
if (time > self.ladder_step_finished)
{
r = random();
@@ -800,20 +786,13 @@ void() PlayerPreThink =
sound (self, CHAN_BODY, "ladder/metal3.wav", 0.5, ATTN_NORM);
self.ladder_step_finished = time + 0.3;
}
- */
}
else
{
self.flags = self.flags | FL_JUMPRELEASED;
}
}
- else
- {
- if (self.button2)
- PlayerJump ();
- else
- self.flags = self.flags | FL_JUMPRELEASED;
- }
+ */
// teleporters can force a non-moving pause time
if (time < self.pausetime)
@@ -833,7 +812,7 @@ void() PlayerPreThink =
}
// TODO CEV
- if (!self.groundboost_timer && (self.teleport_time > time - 0.1))
+ if (self.groundboost_timer <= 0 && (self.teleport_time > time - 0.1))
self.groundboost_timer = PM_GROUNDBOOST_WINDOW;
};
@@ -1098,7 +1077,9 @@ void(entity targ, entity inflictor, entity attacker) ClientObituary =
{
local float rnum;
local string deathstring, deathstring2;
+
rnum = random();
+ deathstring = deathstring2 = "";
// refactored to remove one level of indentation -- CEV
if (targ.classname != "player") return;
Return to the top of this page or return to the overview of this repo.
Diff qc/compat_quake3.qc
diff --git a/qc/compat_quake3.qc b/qc/compat_quake3.qc
new file mode 100644
index 0000000..67f6035
--- /dev/null
+++ b/qc/compat_quake3.qc
@@ -0,0 +1,76 @@
+//==============================================================================
+// Quake 3 compatibility entrypoints / functions
+//==============================================================================
+
+void() item_armor2;
+void() item_armorInv;
+void() item_health_vial;
+void() info_teleport_destination;
+
+//======================================================================
+// Quake 3 armor item support -- CEV
+//----------------------------------------------------------------------
+
+// Yellow Armor -- CEV
+void() item_armor_combat =
+{
+ item_armor2();
+};
+
+// Red Armor -- CEV
+void() item_armor_body =
+{
+ item_armorInv();
+};
+
+//======================================================================
+// Quake 3 health item support -- CEV
+//----------------------------------------------------------------------
+
+void() item_health_small =
+{
+ item_health_vial ();
+};
+
+//======================================================================
+// Quake 3 push target entities -- CEV
+//----------------------------------------------------------------------
+void() target_push =
+{
+ // new spawnflags for all entities -- iw
+ if (SUB_Inhibit ())
+ return;
+
+ if (!self.targetname)
+ if (self.target != __NULL__ && self.target != "")
+ // quake 3 compat -- CEV
+ self.targetname = self.target;
+ else
+ objerror ("no targetname");
+};
+
+//----------------------------------------------------------------------
+void() target_position =
+{
+ target_push ();
+};
+
+//======================================================================
+// Quake 3 Teleporter targets -- CEV
+//----------------------------------------------------------------------
+void() misc_teleporter_dest =
+{
+ info_teleport_destination ();
+};
+
+//----------------------------------------------------------------------
+void() misc_teleporter_destination =
+{
+ info_teleport_destination ();
+};
+
+//----------------------------------------------------------------------
+void() target_teleporter =
+{
+ info_teleport_destination ();
+};
Return to the top of this page or return to the overview of this repo.
Diff qc/cshift.qc
diff --git a/qc/cshift.qc b/qc/cshift.qc
index f7410a7..95c4406 100644
--- a/qc/cshift.qc
+++ b/qc/cshift.qc
@@ -1,65 +1,73 @@
-
-inline void(entity client, float density, vector color) csf_save = {
+inline void(entity client, float density, vector color) csf_save =
+{
client.csf_color = color;
client.csf_density = density;
-}
-
-inline void(entity client) csf_apply = {
- stuffcmd(client, "\nv_cshift ");
- stuffcmd(client, ftos(client.csf_color_x));
- stuffcmd(client, " ");
- stuffcmd(client, ftos(client.csf_color_y));
- stuffcmd(client, " ");
- stuffcmd(client, ftos(client.csf_color_z));
- stuffcmd(client, " ");
- stuffcmd(client, ftos(client.csf_density));
- stuffcmd(client, "\n");
-}
-
-void(entity client, float density, vector color) csf_set = {
- csf_save(client, density, color);
- csf_apply(client);
-}
-
-void() csfcontroller_think = {
-
+};
+
+inline void(entity client) csf_apply =
+{
+ stuffcmd (client, "\nv_cshift ");
+ stuffcmd (client, ftos(client.csf_color_x));
+ stuffcmd (client, " ");
+ stuffcmd (client, ftos(client.csf_color_y));
+ stuffcmd (client, " ");
+ stuffcmd (client, ftos(client.csf_color_z));
+ stuffcmd (client, " ");
+ stuffcmd (client, ftos(client.csf_density));
+ stuffcmd (client, "\n");
+};
+
+void(entity client, float density, vector color) csf_set =
+{
+ csf_save (client, density, color);
+ csf_apply (client);
+};
+
+void() csfcontroller_think =
+{
entity e = self.owner;
- if (self.pain_finished > time && e.csf_density != self.csf_density) {
+ if (self.pain_finished > time && e.csf_density != self.csf_density)
+ {
float density;
vector color;
-
- float fraction = 1 - (self.pain_finished - time) / self.speed; //wat
- density = lerpHermite(e.csf_density, self.csf_density, fraction);
- color = lerpVectorHermite(e.csf_color, self.csf_color, fraction);
+ // wat
+ float fraction = 1 - (self.pain_finished - time) / self.speed;
+
+ density = lerpHermite (e.csf_density, self.csf_density,
+ fraction);
+ color = lerpVectorHermite (e.csf_color, self.csf_color,
+ fraction);
- csf_set(e, density, color);
+ csf_set (e, density, color);
self.nextthink = time + 0.04;
}
- else {
+ else
+ {
csf_set(e, self.csf_density, self.csf_color);
}
-}
+};
-
-void(entity client) csfcontroller_start = {
- if (client.csfcontroller.classname == "csfcontroller" && client.csfcontroller.owner == client)
+void(entity client) csfcontroller_start =
+{
+ if (client.csfcontroller.classname == "csfcontroller" &&
+ client.csfcontroller.owner == client)
return;
- entity e = spawn();
+ entity e = spawn ();
client.csfcontroller = e;
e.owner = client;
e.classname = "csfcontroller";
e.think = csfcontroller_think;
-}
-
+};
-void(entity client, float density, vector color, float spd) csf_fade = {
- csfcontroller_start(client);
+void(entity client, float density, vector color, float spd) csf_fade =
+{
+ csfcontroller_start (client);
entity ct = client.csfcontroller;
@@ -68,8 +76,4 @@ void(entity client, float density, vector color, float spd) csf_fade = {
ct.csf_color = color;
ct.csf_density = density;
ct.nextthink = time + 0.04;
-}
-
-
-
-
+};
Return to the top of this page or return to the overview of this repo.
Diff qc/csqc/csqc_defsbuiltins.qc
diff --git a/qc/csqc/csqc_defsbuiltins.qc b/qc/csqc/csqc_defsbuiltins.qc
index f144c5a..18eb713 100644
--- a/qc/csqc/csqc_defsbuiltins.qc
+++ b/qc/csqc/csqc_defsbuiltins.qc
@@ -108,9 +108,6 @@ string(entity ent) etos = #65;
// userinfo string. There are a few special exceptions, like 'ip' which is not
// technically part of the userinfo.
string(entity e, string key) infokey = #80;
-// Identical to regular infokey, but returns it as a float instead of
-// creating new tempstrings.
-float(entity e, string key) infokeyf = #0;
float(string) stof = #81;
#define unicast(pl,reli) do{msg_entity = pl; multicast('0 0 0', reli?MULITCAST_ONE_R:MULTICAST_ONE);}while(0)
// Once the MSG_MULTICAST network message buffer has been filled with data,
@@ -296,11 +293,6 @@ void(float num, float type, .__variant fld) clientstat = #232;
// string (pass "foo").
void(float num, float type, string name) globalstat = #233;
-// Specifies what data to use in order to send various stats, in a
-// non-client-specific way. num and type are as in clientstat, address
-// however, is the address of the variable you would like to use (pass &foo).
-void(float num, float type, __variant *address) pointerstat = #0;
-
// Returns if the given player's network buffer will take multiple network
// frames in order to clear. If this builtin returns non-zero, you should
// delay or reduce the amount of reliable (and also unreliable) data that
Return to the top of this page or return to the overview of this repo.
Diff qc/csqc/csqc_defsclient.qc
diff --git a/qc/csqc/csqc_defsclient.qc b/qc/csqc/csqc_defsclient.qc
index fd0eeec..0a11eb6 100644
--- a/qc/csqc/csqc_defsclient.qc
+++ b/qc/csqc/csqc_defsclient.qc
@@ -23,7 +23,6 @@ void(float isnew) CSQC_Ent_Update;
// globals
float nocsqc; // CSQC State (0=on, 1=off)
-float detectDP; // Detect DP engine (using wrapper)
float sitems; // CSQC copy of .items
float sitems2; // CSQC copy of .items2 (or serverflags)
float sweapon; // CSQC copy of .weapon
Return to the top of this page or return to the overview of this repo.
Diff qc/csqc/csqc_entrypoints.qc
diff --git a/qc/csqc/csqc_entrypoints.qc b/qc/csqc/csqc_entrypoints.qc
index 2d6f838..f6d838e 100644
--- a/qc/csqc/csqc_entrypoints.qc
+++ b/qc/csqc/csqc_entrypoints.qc
@@ -154,13 +154,6 @@ void(float vwidth, float vheight, float notmenu) CSQC_UpdateView =
if (nocsqc > 0)
return;
- // Required for DP engine
- if (detectDP == TRUE)
- {
- ssize_x = cvar ("vid_conwidth");
- ssize_y = cvar ("vid_conheight");
- }
-
// Used on intermission screen later
if (!intermission)
intermission_time = time;
@@ -315,10 +308,6 @@ void(float apilevel, string enginename, float engineversion) CSQC_Init =
//----------------------------------------------------------------------
__wrap void(float apilevel, string enginename, float engineversion) CSQC_Init =
{
- // Try to detect DP engine (needed for CSQC_UpdateView later)
- if (!apilevel && !enginename && !engineversion)
- detectDP = TRUE;
-
// Execute previous CSQC_Init function
prior (apilevel, enginename, engineversion);
Return to the top of this page or return to the overview of this repo.
Diff qc/csqc/csqc_hudvanilla.qc
diff --git a/qc/csqc/csqc_hudvanilla.qc b/qc/csqc/csqc_hudvanilla.qc
index c03b537..3ececaf 100644
--- a/qc/csqc/csqc_hudvanilla.qc
+++ b/qc/csqc/csqc_hudvanilla.qc
@@ -142,16 +142,18 @@ void(vector pos, float value, float threshhold) Hud_DrawNoFont24 =
else if (value > 999)
value = 999;
- // Work out which number colour to use
- if (value <= threshhold)
- disp_col = TRUE;
-
+ disp_col = FALSE;
+
// Round number down (floor) and work out length
val_str = ftos (floor(value));
disp_len = strlen (val_str);
// Move to the lowest digit position first
pos_x = pos_x + (3 * HUDSIZE_24_x);
-
+
+ // Work out which number colour to use
+ if (value <= threshhold)
+ disp_col = TRUE;
+
while (disp_len > 0)
{
// Countdown early (range is 0-2, strlen returns 1-3)
Return to the top of this page or return to the overview of this repo.
Diff qc/csqc/csqc_player.qc
diff --git a/qc/csqc/csqc_player.qc b/qc/csqc/csqc_player.qc
index e63b5bc..ab3a326 100644
--- a/qc/csqc/csqc_player.qc
+++ b/qc/csqc/csqc_player.qc
@@ -245,16 +245,16 @@ void(float isnew) PlayerUpdate =
// this is us; save for later
player_local = self;
o = self.origin;
- if (intermission)
- // zero out velocity if in intermission -- CEV
- o = self.velocity = '0 0 0';
- else
- v = self.velocity;
+ v = self.velocity;
djt = self.doublejump_timer;
gbt = self.groundboost_timer;
tempflags = self.flags;
pmflags = self.pmove_flags;
+ if (intermission)
+ // zero out velocity if in intermission -- CEV
+ o = self.velocity = '0 0 0';
+
// PlayerRunMovement calls ResetPrediction -- CEV
// PlayerResetPrediction (self);
PlayerRunMovement (self, servercommandframe + 1);
Return to the top of this page or return to the overview of this repo.
Diff qc/cutscene.qc
diff --git a/qc/cutscene.qc b/qc/cutscene.qc
index bbc416c..d113c71 100644
--- a/qc/cutscene.qc
+++ b/qc/cutscene.qc
@@ -373,9 +373,10 @@ local vector looky;
self.cnt = -1; // remove control entity in DHM_CalcMoveDone
//return;
}
- if (cpt.focal_point) //is there a new focal point?
+ if (cpt.focal_point != __NULL__ && cpt.focal_point != "")
{
- fpt = find (world, targetname, cpt.focal_point);
+ // is there a new focal point?
+ fpt = find (world, targetname, cpt.focal_point);
if (!fpt)
objerror("Couldn't find new focal point!");
@@ -461,7 +462,7 @@ local vector looky;
// PM: Solid cannot be 0 or else camera can't trigger stuff by touch.
// Spawn a control function to handle moving the camera
- if (self.enemy.target)
+ if (self.enemy.target != __NULL__ && self.enemy.target != "")
{
local entity control;
@@ -596,7 +597,7 @@ void(entity who) camera_activate =
void() camera_touch =
{
- if (self.targetname)
+ if (self.targetname != __NULL__ && self.targetname != "")
if (self.nextthink < time)
return;
if (self.cnt == -1)
@@ -749,7 +750,7 @@ local entity scrpt;
// If script has a target, trigger it once.
// if (!vision)
- if (scrpt.target)
+ if (scrpt.target != __NULL__ && scrpt.target != "")
{
local entity temp;
Return to the top of this page or return to the overview of this repo.
Diff qc/defs_misc.qc
diff --git a/qc/defs_misc.qc b/qc/defs_misc.qc
index faa3059..f6d10c7 100644
--- a/qc/defs_misc.qc
+++ b/qc/defs_misc.qc
@@ -678,3 +678,6 @@ void(entity client, float density, vector color) csf_set;
.float SendFlags;
#endif
+// TESTING TODO CEV
+.float light_level;
+
Return to the top of this page or return to the overview of this repo.
Diff qc/fight.qc
diff --git a/qc/fight.qc b/qc/fight.qc
index 78882f5..9ecea5e 100644
--- a/qc/fight.qc
+++ b/qc/fight.qc
@@ -56,9 +56,9 @@ Returns FALSE if movement should continue
*/
float() CheckAttack =
{
- local vector spot1, spot2;
- local entity targ;
- local float chance;
+ local vector spot1, spot2;
+ local entity targ;
+ local float chance;
if (self.spawnflags & I_AM_TURRET) //dumptruck_ds
{
Return to the top of this page or return to the overview of this repo.
Diff qc/func_fall2.qc
diff --git a/qc/func_fall2.qc b/qc/func_fall2.qc
index ac97023..000f95d 100644
--- a/qc/func_fall2.qc
+++ b/qc/func_fall2.qc
@@ -13,7 +13,8 @@ void() func_fall2_think =
if (self.attack_finished < time)
{
- if (self.target) // fire other targets
+ if (self.target != __NULL__ && self.target != "")
+ // fire other targets
SUB_UseAndForgetTargets();
// SUB_UseTargets();
@@ -54,7 +55,7 @@ void() func_fall2_think =
self.alpha = self.alpha - self.pain_finished;
else
{
- if (self.noise2)
+ if (self.noise2 != __NULL__ &&self.noise2 != "")
sound (self, CHAN_AUTO, self.noise2, 1, ATTN_NORM);
remove(self);
return;
@@ -97,7 +98,7 @@ void() fall2_touch =
// else
// self.solid = SOLID_NOT;
- if (self.noise)
+ if (self.noise != __NULL__ && self.noise != "")
sound (self, CHAN_AUTO, self.noise, 1, ATTN_NORM);
self.touch = SUB_Null; // disable touch, only do this once!
@@ -120,7 +121,7 @@ void() func_fall2_use =
// self.solid = SOLID_NOT;
self.attack_finished = time + self.wait;
- if (self.noise)
+ if (self.noise != __NULL__ && self.noise != "")
sound (self, CHAN_AUTO, self.noise, 1, ATTN_NORM);
};
@@ -189,9 +190,9 @@ void() func_fall2 =
func_fall2_field.touch = func_fall2_field_touch;
}
- if (self.noise)
+ if (self.noise != __NULL__ && self.noise != "")
precache_sound(self.noise);
- if (self.noise2)
+ if (self.noise2 != __NULL__ && self.noise2 != "")
precache_sound(self.noise2);
self.alpha = 1;
Return to the top of this page or return to the overview of this repo.
Diff qc/items_armor.qc
diff --git a/qc/items_armor.qc b/qc/items_armor.qc
index 31f87ce..f686488 100644
--- a/qc/items_armor.qc
+++ b/qc/items_armor.qc
@@ -258,12 +258,6 @@ void() item_armor2 =
StartItem ();
};
-// for Quake3 entity compatibility -- CEV
-void() item_armor_combat =
-{
- item_armor2();
-};
-
/*QUAKED item_armorInv (0 .5 .8) (-16 -16 0) (16 16 32) X X X X X SPAWN_SILENT TRIGGER_SPAWNED SUSPENDED_IN_AIR NOT_ON_EASY NOT_ON_NORMAL NOT_ON_HARD_OR_NIGHTMARE NOT_IN_DEATHMATCH NOT_IN_COOP NOT_IN_SINGLEPLAYER RESPAWN_WITH_DM_EFFECTS NOT_ON_HARD_ONLY NOT_ON_NIGHTMARE_ONLY
{
model({ "path": ":progs/armor.mdl", "skin": 2 });
@@ -294,10 +288,3 @@ void() item_armorInv =
setsize (self, '-16 -16 0', '16 16 56');
StartItem ();
};
-
-// for Quake3 entity compatibility -- CEV
-void() item_armor_body =
-{
- item_armorInv();
-};
-
Return to the top of this page or return to the overview of this repo.
Diff qc/items_health.qc
diff --git a/qc/items_health.qc b/qc/items_health.qc
index 72f2ba9..2aac1ff 100644
--- a/qc/items_health.qc
+++ b/qc/items_health.qc
@@ -269,10 +269,3 @@ void() health_touch =
// fire all targets / killtargets
SUB_UseTargets ();
};
-
-// Quake 3 entity support -- CEV
-void() item_health_small =
-{
- item_health_vial ();
-};
-
Return to the top of this page or return to the overview of this repo.
Diff qc/lights.qc
diff --git a/qc/lights.qc b/qc/lights.qc
index c2fd36a..f693524 100644
--- a/qc/lights.qc
+++ b/qc/lights.qc
@@ -2,9 +2,9 @@
lights.qc taken from c0burn's Slipgate mod -- dumptruck_ds
========================================*/
-float START_OFF = 1;
-float FADE_IN_OUT = 2;
-float SILENT_TORCH = 4; // for silent torch -- dumptruck_ds
+float START_OFF = 1;
+float FADE_IN_OUT= 2;
+float SILENT_TORCH = 4; // for silent torch -- dumptruck_ds
/*QUAKED info_null (0 0.5 0) (-4 -4 -4) (4 4 4) X X X X 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
@@ -12,7 +12,8 @@ Used as a positional target for spotlights, etc.
*/
void() info_null =
{
- if (SUB_Inhibit ()) // new spawnflags for all entities -- iw
+ // new spawnflags for all entities -- iw
+ if (SUB_Inhibit())
return;
remove(self);
@@ -24,7 +25,8 @@ Never used in the or
*/
void() info_notnull =
{
- if (SUB_Inhibit ()) // new spawnflags for all entities -- iw
+ // new spawnflags for all entities -- iw
+ if (SUB_Inhibit())
return;
};
@@ -35,62 +37,51 @@ string(float num) lightstyle_lookup =
{
switch (num)
{
- // 0 normal
case 0:
+ // 0 normal
return "m";
- break;
- // 1 FLICKER (first variety)
case 1:
+ // 1 FLICKER (first variety)
return "mmnmmommommnonmmonqnmmo";
- break;
- // 2 SLOW STRONG PULSE
case 2:
+ // 2 SLOW STRONG PULSE
return "abcdefghijklmnopqrstuvwxyzyxwvutsrqponmlkjihgfedcba";
- break;
- // 3 CANDLE (first variety)
case 3:
+ // 3 CANDLE (first variety)
return "mmmmmaaaaammmmmaaaaaabcdefgabcdefg";
- break;
- // 4 FAST STROBE
case 4:
+ // 4 FAST STROBE
return "mamamamamama";
- break;
- // 5 GENTLE PULSE 1
case 5:
+ // 5 GENTLE PULSE 1
return "jklmnopqrstuvwxyzyxwvutsrqponmlkj";
- break;
- // 6 FLICKER (second variety)
case 6:
+ // 6 FLICKER (second variety)
return "nmonqnmomnmomomno";
- break;
- // 7 CANDLE (second variety)
case 7:
+ // 7 CANDLE (second variety)
return "mmmaaaabcdefgmmmmaaaammmaamm";
- break;
- // 8 CANDLE (third variety)
case 8:
+ // 8 CANDLE (third variety)
return "mmmaaammmaaammmabcdefaaaammmmabcdefmmmaaaa";
- break;
- // 9 SLOW STROBE (fourth variety)
case 9:
+ // 9 SLOW STROBE (fourth variety)
return "aaaaaaaazzzzzzzz";
- break;
- // 10 FLUORESCENT FLICKER
case 10:
+ // 10 FLUORESCENT FLICKER
return "mmamammmmammamamaaamammma";
- break;
- // 11 SLOW PULSE NOT FADE TO BLACK
case 11:
+ // 11 SLOW PULSE NOT FADE TO BLACK
return "abcdefghijklmnopqrrqponmlkjihgfedcba";
- break;
- // 12 BLINK OFF / ON (can be synced with animated textures, e.g. +0light and +1light)
case 12:
- return "aamm"; // textures animate at 5fps but lights are 10fps...
- break;
- // DEFAULT
+ // 12 BLINK OFF / ON (can be synced with animated
+ // textures, e.g. +0light and +1light)
+ // textures animate at 5fps but lights are
+ // 10fps...
+ return "aamm";
default:
+ // DEFAULT
return "a";
- break;
}
};
@@ -104,7 +95,7 @@ void() setup_lightstyles =
{
for (float i = 0; i <= 12; i++)
{
- lightstyle(i, lightstyle_lookup(i));
+ lightstyle (i, lightstyle_lookup(i));
}
};
@@ -117,43 +108,30 @@ string(float num) lightstyle_fade_lookup =
{
case 0:
return "a";
- break;
case 1:
return "b";
- break;
case 2:
return "c";
- break;
case 3:
return "d";
- break;
case 4:
return "e";
- break;
case 5:
return "f";
- break;
case 6:
return "g";
- break;
case 7:
return "h";
- break;
case 8:
return "i";
- break;
case 9:
return "j";
- break;
case 10:
return "k";
- break;
case 11:
return "l";
- break;
case 12:
return "m";
- break;
default:
error("count out of range\n");
break;
@@ -170,7 +148,7 @@ void() light_fade_in =
if (self.count > 12)
self.count = 12;
- lightstyle(self.style, lightstyle_fade_lookup(self.count));
+ lightstyle (self.style, lightstyle_fade_lookup(self.count));
self.count = self.count + 1;
if (self.count > 12)
return;
@@ -189,7 +167,7 @@ void() light_fade_out =
if (self.count > 12)
self.count = 12;
- lightstyle(self.style, lightstyle_fade_lookup(self.count));
+ lightstyle (self.style, lightstyle_fade_lookup(self.count));
self.count = self.count - 1;
if (self.count < 0)
return;
@@ -209,17 +187,17 @@ void() light_use =
{
self.spawnflags = self.spawnflags - START_OFF;
if (self.spawnflags & FADE_IN_OUT && !self.style2)
- light_fade_in();
+ light_fade_in ();
else
- lightstyle(self.style, lightstyle_lookup(self.style2));
+ lightstyle (self.style, lightstyle_lookup(self.style2));
}
else
{
self.spawnflags = self.spawnflags + START_OFF;
if (self.spawnflags & FADE_IN_OUT && !self.style2)
- light_fade_out();
+ light_fade_out ();
else
- lightstyle(self.style, "a");
+ lightstyle (self.style, "a");
}
};
@@ -336,7 +314,8 @@ _anglescale => _anglescale
*/
void() light =
{
- if (SUB_Inhibit ()) // new spawnflags for all entities -- iw
+ // new spawnflags for all entities -- iw
+ if (SUB_Inhibit())
return;
// default speed for fading in/out
@@ -346,7 +325,7 @@ void() light =
// non-switchable light
if (!self.targetname)
{
- remove(self);
+ remove (self);
return;
}
@@ -357,12 +336,12 @@ void() light =
if (self.spawnflags & START_OFF)
{
self.count = 0;
- lightstyle(self.style, "a");
+ lightstyle (self.style, "a");
}
else
{
self.count = 12;
- lightstyle(self.style, lightstyle_lookup(self.style2));
+ lightstyle (self.style, lightstyle_lookup(self.style2));
}
}
};
@@ -375,11 +354,12 @@ See the "light" entity for a full description.
*/
void() light_fluoro =
{
- if (SUB_Inhibit ()) // new spawnflags for all entities -- iw
+ // new spawnflags for all entities -- iw
+ if (SUB_Inhibit())
return;
- ambient_light_buzz();
- light();
+ ambient_light_buzz ();
+ light ();
};
/*QUAKED light_fluorospark (0 1 0) (-8 -8 -8) (8 8 8) START_OFF FADE_IN_OUT X X 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
@@ -392,13 +372,14 @@ See the "light" entity for a full description.
*/
void() light_fluorospark =
{
- if (SUB_Inhibit ()) // new spawnflags for all entities -- iw
+ // new spawnflags for all entities -- iw
+ if (SUB_Inhibit())
return;
if (!self.style)
self.style = 10;
- ambient_flouro_buzz();
- remove(self);
+ ambient_flouro_buzz ();
+ remove (self);
};
/*QUAKED light_globe (0 1 0) (-8 -8 -8) (8 8 8) X X X X 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
@@ -408,12 +389,13 @@ See the "light" entity for a full description.
*/
void() light_globe =
{
- if (SUB_Inhibit ()) // new spawnflags for all entities -- iw
+ // new spawnflags for all entities -- iw
+ if (SUB_Inhibit())
return;
- precache_model("progs/s_light.spr");
- setmodel(self, "progs/s_light.spr");
- makestatic(self);
+ precache_model ("progs/s_light.spr");
+ setmodel (self, "progs/s_light.spr");
+ makestatic (self);
};
/*QUAKED light_torch_small_walltorch (0 .5 0) (-10 -10 -20) (10 10 20) X X X X 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
@@ -423,16 +405,18 @@ See the "light" entity for a full description.
*/
void() light_torch_small_walltorch =
{
- if (SUB_Inhibit ()) // new spawnflags for all entities -- iw
+ // new spawnflags for all entities -- iw
+ if (SUB_Inhibit())
return;
- // precache_model("progs/flame.mdl");
- precache_body_model("progs/flame.mdl");
- // setmodel(self, "progs/flame.mdl");
- body_model("progs/flame.mdl");
- if !(self.spawnflags && SILENT_TORCH) // for silent torch -- dumptruck_ds
+ // precache_model ("progs/flame.mdl");
+ precache_body_model ("progs/flame.mdl");
+ // setmodel (self, "progs/flame.mdl");
+ body_model ("progs/flame.mdl");
+ // for silent torch -- dumptruck_ds
+ if !(self.spawnflags && SILENT_TORCH)
FireAmbient ();
- makestatic(self);
+ makestatic (self);
};
/*QUAKED light_flame_large_yellow (0 1 0) (-10 -10 -12) (12 12 18) X X X X 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
@@ -442,14 +426,15 @@ See the "light" entity for a full description.
*/
void() light_flame_large_yellow =
{
- if (SUB_Inhibit ()) // new spawnflags for all entities -- iw
+ // new spawnflags for all entities -- iw
+ if (SUB_Inhibit())
return;
- precache_model("progs/flame2.mdl");
+ precache_model ("progs/flame2.mdl");
setmodel (self, "progs/flame2.mdl");
self.frame = 1;
FireAmbient ();
- makestatic(self);
+ makestatic (self);
};
/*QUAKED light_flame_small_yellow (0 1 0) (-8 -8 -8) (8 8 8) X X X X 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
@@ -459,13 +444,14 @@ See the "light" entity for a full description.
*/
void() light_flame_small_yellow =
{
- if (SUB_Inhibit ()) // new spawnflags for all entities -- iw
+ // new spawnflags for all entities -- iw
+ if (SUB_Inhibit())
return;
- precache_model("progs/flame2.mdl");
- setmodel(self, "progs/flame2.mdl");
+ precache_model ("progs/flame2.mdl");
+ setmodel (self, "progs/flame2.mdl");
FireAmbient ();
- makestatic(self);
+ makestatic (self);
};
/*QUAKED light_flame_small_white (0 1 0) (-8 -8 -8) (8 8 8) X X X X 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
@@ -475,10 +461,11 @@ Identical to "light_flame_small_yellow"
*/
void() light_flame_small_white =
{
- if (SUB_Inhibit ()) // new spawnflags for all entities -- iw
+ // new spawnflags for all entities -- iw
+ if (SUB_Inhibit())
return;
- light_flame_small_yellow();
+ light_flame_small_yellow ();
};
/*QUAKED light_sprite_flame (0 1 0) (-8 -8 -8) (8 8 8) X X X X 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
@@ -486,18 +473,18 @@ void() light_flame_small_white =
Large flame spite*/
void() light_sprite_flame =
{
- if (SUB_Inhibit ()) // new spawnflags for all entities -- iw
+ // new spawnflags for all entities -- iw
+ if (SUB_Inhibit())
return;
- precache_model("progs/s_flame.spr");
- setmodel(self, "progs/s_flame.spr");
- FireAmbient ();
-
- self.frame = rint(random() * 13);
- self.first_frame = 0;
- self.last_frame = 13;
- self.speed = 0.05;
- self.think = misc_model_think;
- self.nextthink = time + 0.1;
+ precache_model ("progs/s_flame.spr");
+ setmodel (self, "progs/s_flame.spr");
+ FireAmbient ();
+ self.frame = rint(random() * 13);
+ self.first_frame = 0;
+ self.last_frame = 13;
+ self.speed = 0.05;
+ self.think = misc_model_think;
+ self.nextthink = time + 0.1;
};
Return to the top of this page or return to the overview of this repo.
Diff qc/monsters/oldone.qc
diff --git a/qc/monsters/oldone.qc b/qc/monsters/oldone.qc
index de100c6..2e6ba03 100644
--- a/qc/monsters/oldone.qc
+++ b/qc/monsters/oldone.qc
@@ -256,7 +256,8 @@ void(entity attacker, float damage) nopain =
*/
void() monster_oldone =
{
- if (SUB_Inhibit ()) // new spawnflags for all entities -- iw
+ // new spawnflags for all entities -- iw
+ if (SUB_Inhibit())
return;
if (self.spawnflags & I_AM_TURRET)
@@ -272,7 +273,7 @@ void() monster_oldone =
// precache_model2 ("progs/oldone.mdl");
precache_sound2_death ("boss2/death.wav");
-// precache_sound2_idle ("boss2/idle.wav");
+ // precache_sound2_idle ("boss2/idle.wav");
precache_sound2_sight ("boss2/sight.wav");
precache_sound2_misc ("boss2/pop2.wav");
Return to the top of this page or return to the overview of this repo.
Diff qc/plats.qc
diff --git a/qc/plats.qc b/qc/plats.qc
index ef4d56a..022041b 100644
--- a/qc/plats.qc
+++ b/qc/plats.qc
@@ -345,6 +345,8 @@ void() train_next = {
local entity targ;
vector destang, displ;
+ destang = displ = '0 0 0';
+
targ = find(world, targetname, self.target);
if (!targ || self.target == "")
@@ -397,7 +399,8 @@ void() train_next = {
if (self.spawnflags & TRAIN_CUSTOMALIGN) doDisplace = 0.0;
else doDisplace = 1.0;
- if (self.classname != "misc_modeltrain") displ = self.mins;
+ if (self.classname != "misc_modeltrain")
+ displ = self.mins;
SUB_CalcMove(targ.origin - (displ * doDisplace), self.speed2, train_wait);
};
@@ -406,7 +409,7 @@ void() train_next = {
void() func_train_find = {
local entity targ;
float localtime;
- vector displ;
+ vector displ = '0 0 0';
if (self.movetype == MOVETYPE_PUSH) localtime = self.ltime;
else localtime = time;
Return to the top of this page or return to the overview of this repo.
Diff qc/pmove.qc
diff --git a/qc/pmove.qc b/qc/pmove.qc
index 2571402..7743253 100644
--- a/qc/pmove.qc
+++ b/qc/pmove.qc
@@ -8,7 +8,7 @@
// globals managed by FTEQW
float input_buttons;
-float input_impulse;
+// float input_impulse;
float input_timelength; // from fteextensions.qc -- CEV
vector input_angles; // +x = DOWN
vector input_movevalues;
@@ -69,12 +69,16 @@ const int WATERLEVEL_FEET = 1;
const int WATERLEVEL_WAIST = 2;
const int WATERLEVEL_EYES = 3;
+// from Nexuiz; less precise than theirs, but this should be fine. -- CEV
+const float RAD2DEG = 57.295779;
+
// pmove_flags
enumflags
{
PMF_ONGROUND, // entity is on ground
PMF_STARTGROUND, // entity started the move on ground
PMF_ONLADDER, // entity is on a ladder
+ PMF_INWATER, // entity is in water
PMF_JUMP_HELD, // player is holding the jump key
PMF_DOUBLEJUMPED, // entity has doublejumped
PMF_WALLJUMP, // entity has walljumped
@@ -84,7 +88,6 @@ enumflags
// prototypes
float() PM_Nudge;
void(float dogravity, float sticky, float dostep, float doskim) PM_DanceMove;
-void(entity ground_e, vector ground_v, int docheck) PM_SetOnground;
void() PM_CategorizePosition;
void(float friction, float move_time) PM_Friction;
void(vector wishdir, float wishspeed, float accel, float move_time)
@@ -102,9 +105,8 @@ void(entity target) PM_Move;
//======================================================================
// PM_Nudge
-//
-// from the GPL2 CSQCTest code that comes with FTEQW
-// This isn't working correctly from what I can tell. Not sure why. -- TODO CEV
+// from the GPL2 CSQCTest code that comes with FTEQW; is called often
+// to nudge player origin due to float/network precision errors -- CEV
//----------------------------------------------------------------------
float() PM_Nudge =
{
@@ -168,6 +170,10 @@ void(float dogravity, float sticky, float dostep, float doskim) PM_DanceMove =
int i;
entity touched_ent;
+ // silence some FTEQCC warnings -- CEV
+ end = prev_plane = prev_plane2 = plane = start_v = '0 0 0';
+ backoff = grav = stepsize = time_left = 0;
+
if (dogravity)
{
if (self.gravity)
@@ -183,13 +189,13 @@ void(float dogravity, float sticky, float dostep, float doskim) PM_DanceMove =
start_v = self.velocity;
+ // Borrowing FTEQW's pm_airstep cvar here. If false, don't step up
+ // while in the air (changes stairs) -- CEV
if (!(autocvar(pm_airstep, TRUE)) && !(self.pmove_flags & PMF_ONGROUND))
- // Borrowing FTEQW's pm_airstep cvar here. If false, don't
- // step up while in the air (changes stairs) -- CEV
dostep = FALSE;
+ // no stepping. useful for testing -- CEV
if (autocvar(pm_nostep, FALSE))
- // no stepping. useful for testing -- CEV
dostep = FALSE;
// we need to bounce off surfaces (in order to slide along them),
@@ -210,8 +216,13 @@ void(float dogravity, float sticky, float dostep, float doskim) PM_DanceMove =
// nah, we're stuck. don't build up falling damage
// but allow sideways acceleration -- CEV
- #ifdef SSQC
- dprint ("PM_DanceMove: entity trapped in a solid\n");
+ #ifdef CSQC
+ dprint ("PM_DanceMove: client ");
+ #elif SSQC
+ dprint ("PM_DanceMove: server ");
+ #endif
+ #if defined(CSQC) || defined(SSQC)
+ dprint ("entity trapped in a solid!\n");
#endif
self.velocity_z = 0;
break;
@@ -242,67 +253,78 @@ void(float dogravity, float sticky, float dostep, float doskim) PM_DanceMove =
tracebox (self.origin, self.mins, self.maxs,
trace_endpos, FALSE, self);
+ // don't like having to store another float & vector
+ // but this solves more interactions (ztndm3) -- CEV
+ local float roof_fraction = trace_fraction;
+ local vector roof_plane = trace_plane_normal;
+
+ // second: move forward
+ stepsize = trace_endpos_z - self.origin_z;
+ end = trace_endpos + (self.velocity * time_left);
+ end_z = trace_endpos_z;
+ tracebox (trace_endpos, self.mins, self.maxs, end,
+ FALSE, self);
+
if (trace_fraction >= 1.0f)
{
- // up move didn't hit anything
- // second: move forward
- stepsize = trace_endpos_z - self.origin_z;
- end = trace_endpos +
- (self.velocity * time_left);
- end_z = trace_endpos_z;
+ // forward move didn't hit anything
+ // third: move down
+ end = trace_endpos;
+ end_z -= stepsize + 1;
tracebox (trace_endpos, self.mins, self.maxs,
end, FALSE, self);
- if (trace_fraction >= 1.0f)
+ if (trace_fraction < 1.0f &&
+ trace_plane_normal_z > 0.7f)
{
- // forward move didn't hit anything
- // third: move down
- end = trace_endpos;
- end_z -= stepsize;
- tracebox (trace_endpos, self.mins,
- self.maxs, end, FALSE, self);
-
- if (trace_fraction < 1.0f &&
- trace_plane_normal_z > 0.7f)
+ // good ground, accept the move
+ if (roof_fraction < 1.0f)
{
- // good ground, accept the move
- // laugh at my 80 column term
- stepsize = trace_endpos_z -
- self.origin_z;
- self.origin = trace_endpos;
- time_left -= time_left *
- trace_fraction;
- plane = trace_plane_normal;
- touched_ent = trace_ent;
- // don't attempt to step again
- dostep = FALSE;
+ // we hit the ceiling, store
+ // its plane as prev_plane so
+ // we'll clip to it below -- CEV
+ prev_plane2 = plane;
+ prev_plane = roof_plane;
}
- else
- {
- // down move didn't hit and/or
- // it hit a plane too steep to
- // be ground -- CEV
- stepsize = 0;
- }
- }
- else if (trace_plane_normal_z == 0)
- {
- // raised forward move hit something
- // so clip to it. solves issues with
- // complex movement on stairs. note
- // that we're not updating origin.
- // -- CEV
- stepsize = 0;
+
+ stepsize = trace_endpos_z -
+ self.origin_z;
+ self.origin = trace_endpos;
time_left -= time_left * trace_fraction;
plane = trace_plane_normal;
touched_ent = trace_ent;
+ // don't attempt to step again
+ dostep = FALSE;
+ }
+ else
+ {
+ // down move didn't hit and/or
+ // it hit a plane too steep to
+ // be ground -- CEV
+ stepsize = 0;
}
}
- else
+ else if (trace_plane_normal_z == 0)
{
- // up move hit something (the roof?)
- // ignore the step attempt entirely -- CEV
- stepsize = 0;
+ // raised forward move hit something
+ // so clip to it. solves issues with
+ // complex movement on stairs. note
+ // that we're not updating origin.
+ // -- CEV
+ if (roof_fraction < 1.0f)
+ {
+ // save ceiling for later if we hit it
+ prev_plane2 = plane;
+ prev_plane = roof_plane;
+ }
+
+ // stepsize = 0;
+ stepsize = trace_endpos_z - self.origin_z;
+ time_left -= time_left * trace_fraction;
+ plane = trace_plane_normal;
+ // save trace_ent if it has a touch function
+ if (trace_ent && trace_ent.touch != __NULL__)
+ touched_ent = trace_ent;
}
}
@@ -430,15 +452,19 @@ void(float dogravity, float sticky, float dostep, float doskim) PM_DanceMove =
self.velocity_z -= grav * 0.5;
// if stepsize is nonzero and we changed from inair to onground then
- // we've airstepped -- CEV
+ // we've airstepped. this check is here as a placeholder for possible
+ // functionality later -- CEV
+ #ifdef SSQC
if (stepsize && !(self.pmove_flags & PMF_STARTGROUND) &&
self.pmove_flags & PMF_ONGROUND)
{
// more debugging -- CEV
- #ifdef SSQC
dprint (sprintf("PM_DanceMove: airstep: %g\n", stepsize));
- #endif
}
+ #endif
+
+ // a final call to setorigin to update links -- CEV
+ setorigin (self, self.origin);
/*
#ifdef SSQC
@@ -449,17 +475,35 @@ void(float dogravity, float sticky, float dostep, float doskim) PM_DanceMove =
*/
};
+//======================================================================
+// PM_CategorizePosition
+// Based on similarly-named function in the GPL2 purecsqc pmove.qc
//----------------------------------------------------------------------
-void(entity ground_e, vector ground_v, int docheck) PM_SetOnground =
+void() PM_CategorizePosition =
{
- // look for ground with tracebox if requested
- if (docheck)
+ vector point;
+ float contents;
+
+ if (self.movetype == MOVETYPE_NOCLIP || self.movetype == MOVETYPE_FLY)
{
+ // noclip is never on ground
+ self.groundentity = __NULL__;
+ self.groundnormal = __NULL__;
+ self.pmove_flags &= ~PMF_ONGROUND;
+ self.flags &= ~FL_ONGROUND;
+ }
+ else
+ {
+ // TODO CEV there must be a way to optimize out this
+ // tracebox ground check some of the time
+
+ // do a trace to check for ground
tracebox (self.origin, self.mins, self.maxs,
self.origin - PM_GROUNDDIST_V, FALSE, self);
// only onground if we hit it, it faces upwards,
// and we're actually moving towards it
- // if (trace_fraction < 1 && trace_plane_normal_z > 0.7 &&
+ // if (trace_fraction < 1 &&
+ // trace_plane_normal_z > 0.7 &&
// self.velocity * trace_plane_normal < 0.01)
if (trace_fraction < 1 && trace_plane_normal_z > 0.7)
{
@@ -473,53 +517,24 @@ void(entity ground_e, vector ground_v, int docheck) PM_SetOnground =
self.groundnormal = __NULL__;
}
}
- else
- {
- self.groundentity = ground_e;
- self.groundnormal = ground_v;
- }
// assume we're on ground if we have a groundnormal field -- CEV
if (self.groundnormal != __NULL__)
{
// on ground
+ self.flags |= FL_ONGROUND;
self.pmove_flags |= PMF_ONGROUND;
self.pmove_flags &= ~PMF_WALLJUMP;
}
else
{
// not on ground
+ self.flags &= ~FL_ONGROUND;
self.pmove_flags &= ~PMF_ONGROUND;
}
- if (self.pmove_flags & PMF_ONGROUND)
- self.flags |= FL_ONGROUND;
- else
- self.flags &= ~FL_ONGROUND;
-};
-
-//======================================================================
-// PM_CategorizePosition
-// Based on similarly-named function in the GPL2 purecsqc pmove.qc
-//----------------------------------------------------------------------
-void() PM_CategorizePosition =
-{
- vector point;
- float contents;
-
- if (self.movetype == MOVETYPE_NOCLIP || self.movetype == MOVETYPE_FLY)
- // noclip is never on ground
- PM_SetOnground (__NULL__, __NULL__, FALSE);
- else
- // do a trace to check
- PM_SetOnground (__NULL__, __NULL__, TRUE);
-
- // clear timers that have gone negative
- PM_ManageTimers (0);
-
// check water levels
- point = self.origin;
- point_z = self.origin_z + self.mins_z + 1;
+ point = [self.origin_x, self.origin_y, self.origin_z + self.mins_z + 1];
contents = pointcontents (point);
if (contents < CONTENT_SOLID)
{
@@ -710,13 +725,12 @@ void() PM_Jump =
dprint (sprintf("PM_Jump: doublejump %g, ",
self.velocity_z));
#endif
- // the groundnormal is weird - some kind of ramp -
- // so we want an additive doublejump here -- CEV
+ // the groundnormal might be weird - some kind of
+ // ramp - so we want an additive doublejump here -- CEV
self.velocity_z += PM_DOUBLEJUMPSPEED;
}
- // set the doublejump countdown timer -- CEV
- self.doublejump_timer = PM_DOUBLEJUMP_WINDOW;
+ // set the doublejump flag -- CEV
self.pmove_flags |= PMF_DOUBLEJUMPED;
}
else
@@ -726,10 +740,8 @@ void() PM_Jump =
dprint (sprintf("PM_Jump: jump %g, ", self.velocity_z));
#endif
+ // do an additive jump -- CEV
self.velocity_z += PM_JUMPSPEED;
-
- // timers for normal jumps -- CEV
- self.doublejump_timer = PM_DOUBLEJUMP_WINDOW;
}
// report new Z velocity
@@ -738,10 +750,19 @@ void() PM_Jump =
#endif
// manage flags -- CEV
- PM_SetOnground (__NULL__, __NULL__, FALSE);
+ self.groundentity = __NULL__;
+ self.groundnormal = __NULL__;
+ self.pmove_flags &= ~PMF_ONGROUND;
+ self.flags &= ~FL_ONGROUND;
self.pmove_flags |= PMF_JUMP_HELD;
+ #ifdef SSQC
+ self.button2 = 0;
+ // player jumping sound; copied into pmove from client.qc -- CEV
+ sound (self, CHAN_BODY, "player/plyrjmp8.wav", 1, ATTN_NORM);
+ #endif
// timers for all jumps -- CEV
+ self.doublejump_timer = PM_DOUBLEJUMP_WINDOW;
self.groundboost_timer = PM_GROUNDBOOST_WINDOW;
};
@@ -769,9 +790,6 @@ void(vector checkdir) PM_WallJump =
if (self.pmove_flags & PMF_JUMP_HELD)
return;
- // TODO CEV
- return;
-
// don't walljump if within 32 units of ground
tracebox (self.origin, self.mins, self.maxs,
self.origin - PM_WALLDIST_V, FALSE, self);
@@ -849,6 +867,13 @@ void(float premove, float move_time) PM_WalkAccelerate =
if (wishyaw >= 180)
wishyaw = fabs (wishyaw - 360);
+ /*
+ #ifdef SSQC
+ dprint (sprintf("PM_WalkAccelerate: wishyaw %g\n",
+ RAD2DEG * atan2 (vectoyaw(wishvel), vectoyaw(self.velocity))));
+ #endif
+ */
+
if (premove)
{
if (self.pmove_flags & PMF_ONLADDER)
@@ -884,12 +909,18 @@ void(float premove, float move_time) PM_WalkAccelerate =
{
// +jump was pressed
if (self.pmove_flags & PMF_ONGROUND)
+ {
// normal jump
PM_Jump ();
+ }
// TODO CEV
// else
// PM_WallJump (right);
}
+ else
+ {
+ self.flags |= FL_JUMPRELEASED;
+ }
}
if (self.pmove_flags & PMF_ONGROUND)
@@ -1026,6 +1057,24 @@ void(float move_time) PM_SwimAccelerate =
}
}
+ #ifdef SSQC
+ // functionality copied into pmove from client.qc -- CEV
+ if (self.waterlevel >= WATERLEVEL_WAIST)
+ {
+ if (self.swim_flag < time)
+ {
+ // play swimming sound
+ self.swim_flag = time + 1;
+ if (random() < 0.5)
+ sound (self, CHAN_BODY, "misc/water1.wav",
+ 1, ATTN_NORM);
+ else
+ sound (self, CHAN_BODY, "misc/water2.wav",
+ 1, ATTN_NORM);
+ }
+ }
+ #endif
+
if (input_buttons & 2 && !(self.pmove_flags & PMF_WATERJUMP))
// smartjump
wishvel_z = max (PM_MAXSPEED, wishvel_z);
@@ -1078,14 +1127,12 @@ void(float scale, float move_time) PM_NoClipAccelerate =
void(float move_time) PM_ManageTimers =
{
if (self.doublejump_timer > 0 && move_time > 0)
- {
self.doublejump_timer -= move_time;
- }
- else if (self.doublejump_timer <= 0)
- {
+ else if (self.doublejump_timer < 0)
self.doublejump_timer = 0;
+
+ if (self.doublejump_timer == 0)
self.pmove_flags &= ~PMF_DOUBLEJUMPED;
- }
if (self.groundboost_timer > 0 && move_time > 0)
self.groundboost_timer -= move_time;
@@ -1102,29 +1149,29 @@ void(entity target) PM_Move =
if (input_timelength <= 0)
// don't process partial frames -- CEV
- /*
- dprint (sprintf("PM_Move: returning, input_timelength: %g\n",
- input_timelength));
- */
return;
oldself = self;
self = target;
- PM_Nudge ();
+ // Nudge player's origin if the server is sending low-precision
+ // (16 bit?) player coordinates. This can be fixed by setting
+ // sv_bigcoords to 1 (so the server sends float coords). -- CEV
+ if (!autocvar(sv_bigcoords, FALSE))
+ PM_Nudge ();
// TODO CEV this is the wrong place to clear PMF_JUMP_HELD
if (!(input_buttons & 2))
self.pmove_flags &= ~PMF_JUMP_HELD;
PM_CategorizePosition ();
+ PM_ManageTimers (0);
switch (self.movetype)
{
case MOVETYPE_WALK:
- local float dogravity, doskim, dostep, sticky;
+ local float dogravity, doskim, sticky;
- dostep = TRUE;
doskim = FALSE;
sticky = FALSE;
@@ -1136,7 +1183,6 @@ void(entity target) PM_Move =
// or sticky clips underwater -- CEV
dogravity = FALSE;
doskim = FALSE;
- dostep = TRUE;
sticky = FALSE;
// swim acceleration
PM_SwimAccelerate (input_timelength * 0.5f);
@@ -1180,7 +1226,6 @@ void(entity target) PM_Move =
// feature set for ladders -- CEV
dogravity = FALSE;
doskim = FALSE;
- dostep = TRUE;
sticky = FALSE;
}
}
@@ -1189,7 +1234,7 @@ void(entity target) PM_Move =
PM_ManageTimers (input_timelength * 0.5f);
// Do the move. Bounce, Rock, Skate, Roll -- CEV
- PM_DanceMove (dogravity, sticky, dostep, doskim);
+ PM_DanceMove (dogravity, sticky, TRUE, doskim);
// second pass at acceleration
if (self.waterlevel >= WATERLEVEL_WAIST)
@@ -1227,7 +1272,6 @@ void(entity target) PM_Move =
break;
}
- PM_SetOnground (self.groundentity, self.groundnormal, TRUE);
touchtriggers (self);
self = oldself;
};
Return to the top of this page or return to the overview of this repo.
Diff qc/progs.src
diff --git a/qc/progs.src b/qc/progs.src
index c426f56..cbc2056 100644
--- a/qc/progs.src
+++ b/qc/progs.src
@@ -37,12 +37,12 @@ keylock.qc // common code for entities unlockable with keys
doors.qc
buttons.qc
triggers.qc // added trigger_push_custom based on Hipnotic
-triggers_heal.qc // trigger_heal (was in dtmisc.qc) -- CEV
-triggers_ladder.qc // ladders (from rubicon2) -- CEV
-triggers_push.qc // wind/push brushes, jumppads -- CEV
-triggers_shake.qc // triggerable shake from Zer cutscenes; was dtquake.qc
-triggers_teleport.qc // was in triggers.qc -- CEV
-triggers_textstory.qc // textstory (was in misc.qc) -- CEV
+triggers/heal.qc // trigger_heal (was in dtmisc.qc) -- CEV
+triggers/ladder.qc // ladders (from rubicon2) -- CEV
+triggers/push.qc // wind/push brushes, jumppads -- CEV
+triggers/shake.qc // triggerable shake from Zer cutscenes; was dtquake.qc
+triggers/teleport.qc // was in triggers.qc -- CEV
+triggers/textstory.qc // textstory (was in misc.qc) -- CEV
plats.qc
misc.qc
lights.qc // c0burn's excellent switchable lights
@@ -86,4 +86,6 @@ rubicon2.qc // selections from Rubicon2 QC
func_bob.qc // RennyC's stand alone version based on AD
func_fall2.qc // Renny's improved version.
mobot.qc // Using "bot" creation code for func_monster_spawner
+
+compat_quake3.qc // entrypoints & support for Quake 3 entities
#endlist
Return to the top of this page or return to the overview of this repo.
Diff qc/triggers/heal.qc
diff --git a/qc/triggers/heal.qc b/qc/triggers/heal.qc
new file mode 100644
index 0000000..52c1912
--- /dev/null
+++ b/qc/triggers/heal.qc
@@ -0,0 +1,179 @@
+//==============================================================================
+// HEAL TRIGGER
+//==============================================================================
+
+// from custents, modified by dumptruck_ds
+// Original entity submitted by Jan Martin Mathiassen, aka. TGR
+
+// was in dtmisc.qc -- CEV
+
+//----------------------------------------------------------------------
+void() heal_think =
+{
+ if (self.cnt == self.count)
+ {
+ dprint ("trigger_heal think: full\n");
+ self.think = SUB_Null;
+ return;
+ }
+
+ local float recharge_amount = self.speed;
+
+ if (self.count < (self.cnt + self.speed))
+ recharge_amount = self.count - self.cnt;
+
+ dprint ("trigger_heal think: [max: ");
+ dprint (ftos(self.count));
+ dprint (", current: ");
+ dprint (ftos(self.cnt));
+ dprint (", recharging: ");
+ dprint (ftos(recharge_amount));
+ dprint ("]\n");
+
+ self.cnt = self.cnt + recharge_amount;
+ self.nextthink = time + self.delay;
+};
+
+//----------------------------------------------------------------------
+void() heal_touch =
+{
+ if (self.estate != STATE_ACTIVE)
+ return;
+
+ // from Copper -- dumptruck_ds
+ if (other.movetype == MOVETYPE_NOCLIP)
+ return;
+ if (self.spawnflags & HEAL_PLAYER_ONLY && other.classname != "player")
+ return;
+ if (self.spawnflags & HEAL_MONSTER_ONLY && !(other.flags & FL_MONSTER))
+ return;
+ if (other.classname != "player" && !(other.flags & FL_MONSTER))
+ return;
+ if (other.heal_timer > time)
+ return;
+
+ if (self.count && self.cnt <= 0)
+ {
+ if (self.message2 != __NULL__ && self.message2 != "")
+ centerprint (other, self.message2);
+ return;
+ }
+
+ if ((other.takedamage) && (other.health < self.health_max))
+ {
+ if (self.noise != "")
+ sound (self, CHAN_AUTO, self.noise, 1, ATTN_NORM);
+ else
+ sound (self, CHAN_AUTO, "items/r_item1.wav", 1,
+ ATTN_NORM);
+
+ local float calculated_healing;
+
+ if ((other.health + self.heal_amount) > self.health_max)
+ calculated_healing = self.health_max - other.health;
+ else
+ calculated_healing = self.heal_amount;
+
+ if (self.count)
+ {
+ if (calculated_healing > self.cnt)
+ calculated_healing = self.cnt;
+
+ self.cnt = self.cnt - calculated_healing;
+
+ if (self.delay)
+ {
+ self.think = heal_think;
+ self.nextthink = time + self.delay;
+ }
+
+ dprint ("trigger_heal used: [max: ");
+ dprint (ftos(self.count));
+ dprint (", current: ");
+ dprint (ftos(self.cnt));
+ dprint (", using: ");
+ dprint (ftos(calculated_healing));
+ dprint ("]\n");
+ }
+
+ if (self.message != __NULL__ && self.message != "")
+ centerprint (other, self.message);
+
+ T_Heal (other, calculated_healing, 1);
+ other.heal_timer = time + self.wait;
+ }
+};
+
+//----------------------------------------------------------------------
+void() heal_toggle =
+{
+ if (self.touch == SUB_Null)
+ self.touch = heal_touch;
+ else
+ self.touch = SUB_Null;
+};
+
+/*QUAKED trigger_heal (.5 .5 .5) ? HEAL_START_ON HEAL_PLAYER_ONLY HEAL_MONSTER_ONLY X 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 healed
+heal_amount -- the amount to heal each time (default 5)
+wait -- the time between each healing (default 1)
+health_max -- the upper limit for the healing (default 100, max 250)
+sounds -- set to 1 to enable the noise1 field for custom healing sound
+noise -- path to custom sound file
+message -- message to print on heal
+count -- maximum heal before exhausted
+speed -- amount to recharge at a time
+delay -- time before recharging
+message2 -- message to print when exhausted
+*/
+void() trigger_heal =
+{
+ // new spawnflags for all entities -- iw
+ if (SUB_Inhibit ())
+ return;
+
+ // play custom sound for healing if noise key exists
+ precache_sound ("items/r_item1.wav");
+ if (self.noise != "")
+ precache_sound (self.noise);
+
+ InitTrigger ();
+
+ if (self.wait == 0)
+ self.wait = 1;
+
+ if (self.heal_amount == 0)
+ self.heal_amount = 5;
+
+ if (self.health_max == 0)
+ self.health_max = 100;
+ else if (self.health_max > 250)
+ self.health_max = 250;
+
+ if (self.count)
+ {
+ self.cnt = self.count;
+
+ if (self.speed && !self.delay)
+ self.delay = 10;
+ else if (!self.speed && self.delay)
+ self.speed = 5;
+ }
+
+ /*
+ if (self.targetname)
+ {
+ self.use = heal_toggle;
+ if (self.spawnflags & HEAL_START_ON)
+ self.touch = heal_touch;
+ else
+ self.touch = SUB_Null;
+ }
+ else
+ */
+
+ self.touch = heal_touch;
+
+ SUB_CheckWaiting ();
+};
Return to the top of this page or return to the overview of this repo.
Diff qc/triggers/ladder.qc
diff --git a/qc/triggers/ladder.qc b/qc/triggers/ladder.qc
new file mode 100644
index 0000000..fa397be
--- /dev/null
+++ b/qc/triggers/ladder.qc
@@ -0,0 +1,67 @@
+//==============================================================================
+// LADDERS (from rubicon2.qc)
+//==============================================================================
+
+// selections from Rubicon 2 qc by john fitzgibbons
+
+//======================================================================
+// ladder_touch
+//----------------------------------------------------------------------
+void() ladder_touch =
+{
+ // from Copper -- dumptruck_ds
+ if (!CheckValidTouch())
+ return;
+
+ // prevent the player "sticking" to a ladder if they are standing on
+ // the platform at the top of the ladder with the bottom of their
+ // bounding box flush with the top of the trigger -- iw
+ if (other.absmin_z + 1 >= self.absmax_z - 1)
+ return;
+
+ // if the trigger has an angles field, check player's facing direction
+ if (self.movedir != '0 0 0')
+ {
+ makevectors (other.angles);
+ if (v_forward * self.movedir < 0)
+ // not facing the right way
+ return;
+ }
+
+ // changed to PMFLAGS -- CEV
+ other.pmove_flags |= PMF_ONLADDER;
+}
+
+//======================================================================
+// trigger_ladder
+//----------------------------------------------------------------------
+
+/*QUAKED trigger_ladder (.5 .5 .5) ? X X X X 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
+invisible ladder entity. when player is touching this entity, he can climb by pushing 'jump'
+
+Keys:
+
+"angle" the direction player must be facing to climb ladder
+*/
+void() trigger_ladder =
+{
+ if (SUB_Inhibit())
+ // new spawnflags for all entities -- iw
+ return;
+
+ // ignore an "up" or "down" angle (doesn't make sense for a ladder)
+ if (self.angles_y == -1 || self.angles_y == -2)
+ {
+ dprint ("WARNING: trigger_ladder ignored bad 'angle' value: ");
+ dprint (ftos (self.angles_y));
+ dprint ("\n");
+
+ self.angles_y = 0;
+ }
+
+ InitTrigger ();
+ self.touch = ladder_touch;
+
+ SUB_CheckWaiting ();
+};
+
Return to the top of this page or return to the overview of this repo.
Diff qc/triggers/push.qc
diff --git a/qc/triggers/push.qc b/qc/triggers/push.qc
new file mode 100644
index 0000000..df5e0d0
--- /dev/null
+++ b/qc/triggers/push.qc
@@ -0,0 +1,429 @@
+//==============================================================================
+// TRIGGER PUSH
+//==============================================================================
+
+////////////////////////////////////////////////////////////////////////
+// start dumptruck_ds additions ////////////////////////////////////////
+////////////////////////////////////////////////////////////////////////
+
+float PUSH_ONCE = 1;
+float DT_STARTOFF = 8; // trigger will start off
+float DT_SILENT = 16; // push silently
+float DT_NOISE = 32; // use custom sound via noise key/value
+
+////////////////////////////////////////////////////////////////////////
+// start code CEV copied from Nexuiz ///////////////////////////////////
+////////////////////////////////////////////////////////////////////////
+
+//======================================================================
+// solve_quadratic
+//
+// from Nexuiz source code; copied from
+// https://github.com/smlinux/nexuiz/blob/master/data/qcsrc/common/util.qc
+// ax^2 + bx + c = 0
+//----------------------------------------------------------------------
+vector(float a, float b, float c) solve_quadratic =
+{
+ vector v;
+ float D;
+ v = '0 0 0';
+ if (a == 0)
+ {
+ if (b != 0)
+ {
+ v_x = v_y = -c / b;
+ v_z = 1;
+ }
+ else
+ {
+ if (c == 0)
+ {
+ // actually, every number solves the equation!
+ v_z = 1;
+ }
+ }
+ }
+ else
+ {
+ D = b*b - 4*a*c;
+ if (D >= 0)
+ {
+ D = sqrt (D);
+ if (a > 0)
+ {
+ // put the smaller solution first
+ v_x = ((-b)-D) / (2*a);
+ v_y = ((-b)+D) / (2*a);
+ }
+ else
+ {
+ v_x = (-b+D) / (2*a);
+ v_y = (-b-D) / (2*a);
+ }
+ v_z = 1;
+ }
+ else
+ {
+ // complex solutions!
+ D = sqrt (-D);
+ v_x = -b / (2*a);
+ if (a > 0)
+ v_y = D / (2*a);
+ else
+ v_y = -D / (2*a);
+ v_z = 0;
+ }
+ }
+ return v;
+};
+
+//======================================================================
+// trigger_push_calculatevelocity
+//
+// Arguments:
+// org - origin of the object which is to be pushed
+// tgt - target entity (can be either a point or a model entity; if it
+// is the latter, its midpoint is used)
+// ht - jump height, measured from the higher one of org and tgt's
+// midpoint
+//
+// Returns: velocity for the jump
+// the global trigger_push_calculatevelocity_flighttime is set to the
+// total jump time
+//
+// from Nexuiz source code; copied from
+// https://github.com/smlinux/nexuiz/blob/master/data/qcsrc/server/t_jumppads.qc
+//----------------------------------------------------------------------
+vector(vector org, entity tgt, float ht) trigger_push_calculatevelocity =
+{
+ local float grav, sdist, zdist, vs, vz, jumpheight;
+ local vector sdir, torg;
+ vector solution;
+ float trigger_push_calculatevelocity_flighttime;
+
+ torg = tgt.origin + (tgt.mins + tgt.maxs) * 0.5;
+
+ grav = autocvar (sv_gravity, PM_GRAVITY);
+
+ zdist = torg_z - org_z;
+ sdist = vlen (torg - org - zdist * '0 0 1');
+ sdir = normalize (torg - org - zdist * '0 0 1');
+
+ // how high do we need to push the player?
+ jumpheight = fabs (ht);
+ if (zdist > 0)
+ jumpheight = jumpheight + zdist;
+
+ /*
+ STOP.
+
+ You will not understand the following equations anyway...
+ But here is what I did to get them.
+
+ I used the functions
+
+ s(t) = t * vs
+ z(t) = t * vz - 1/2 grav t^2
+
+ and solved for:
+
+ s(ti) = sdist
+ z(ti) = zdist
+ max(z, ti) = jumpheight
+
+ From these three equations, you will find the three
+ parameters vs, vz and ti.
+ */
+
+ // push him so high... NOTE: sqrt(positive)!
+ vz = sqrt (2 * grav * jumpheight);
+
+ // we start with downwards velocity only if it's a downjump
+ // and the jump apex should be outside the jump!
+ if (ht < 0)
+ if (zdist < 0)
+ vz = -vz;
+
+ // equation "z(ti) = zdist"
+ solution = solve_quadratic (0.5 * grav, -vz, zdist);
+ // ALWAYS solvable because jumpheight >= zdist
+ if (!solution_z)
+ // just in case it is not solvable due to roundoff errors,
+ // assume two equal solutions at their center (this is
+ // mainly for the usual case with ht == 0)
+ solution_y = solution_x;
+ if (zdist == 0)
+ // solution_x is 0 in this case, so don't use it, but rather
+ // use solution_y (which will be sqrt(0.5 * jumpheight / grav),
+ // actually)
+ solution_x = solution_y;
+
+ if (zdist < 0)
+ {
+ // down-jump
+ if (ht < 0)
+ {
+ // almost straight line type
+ // jump apex is before the jump
+ // we must take the larger one
+ trigger_push_calculatevelocity_flighttime = solution_y;
+ }
+ else
+ {
+ // regular jump
+ // jump apex is during the jump
+ // we must take the larger one too
+ trigger_push_calculatevelocity_flighttime = solution_y;
+ }
+ }
+ else
+ {
+ // up-jump
+ if (ht < 0)
+ {
+ // almost straight line type
+ // jump apex is after the jump
+ // we must take the smaller one
+ trigger_push_calculatevelocity_flighttime = solution_x;
+ }
+ else
+ {
+ // regular jump
+ // jump apex is during the jump
+ // we must take the larger one
+ trigger_push_calculatevelocity_flighttime = solution_y;
+ }
+ }
+ vs = sdist / trigger_push_calculatevelocity_flighttime;
+
+ // finally calculate the velocity
+ return sdir * vs + '0 0 1' * vz;
+};
+
+//----------------------------------------------------------------------
+void() trigger_push_findtarget =
+{
+ self.enemy = find (world, targetname, self.target);
+ if (self.enemy)
+ {
+ local vector org;
+ org = (self.absmin + self.absmax) * 0.5;
+ org_z = self.absmax_z - -24; // - PL_MIN_z;
+ self.movedir = trigger_push_calculatevelocity (org,
+ self.enemy, self.height);
+ }
+};
+
+////////////////////////////////////////////////////////////////////////
+// end code CEV copied from Nexuiz /////////////////////////////////////
+////////////////////////////////////////////////////////////////////////
+
+//----------------------------------------------------------------------
+void() trigger_push_touch =
+{
+ if (self.estate != STATE_ACTIVE)
+ return;
+
+ // from Copper -- dumptruck_ds
+ if (other.movetype == MOVETYPE_NOCLIP)
+ return;
+
+ // try to find target again if necessary
+ if (self.target && (!self.enemy))
+ trigger_push_findtarget ();
+
+ // we have a target, set movedir accordingly
+ if (self.target && self.enemy)
+ self.movedir = trigger_push_calculatevelocity (other.origin,
+ self.enemy, self.height);
+
+ if (other.classname == "grenade")
+ {
+ if (self.target && self.enemy)
+ other.velocity = self.movedir;
+ else
+ other.velocity = self.speed * self.movedir * 10;
+ }
+ else if (other.health > 0)
+ {
+ if (self.target && self.enemy)
+ other.velocity = self.movedir;
+ else
+ other.velocity = self.speed * self.movedir * 10;
+
+ if (other.classname == "player")
+ {
+ if (!(self.spawnflags & DT_SILENT))
+ {
+ if (other.fly_sound < time)
+ {
+ if (!(self.spawnflags & DT_NOISE))
+ {
+ other.fly_sound = time + 1.5;
+ sound (other, CHAN_AUTO,
+ "ambience/windfly.wav",
+ 1, ATTN_NORM);
+ }
+ else
+ {
+ other.fly_sound = time + 1.5;
+ sound (other, CHAN_AUTO,
+ self.noise,
+ 1, ATTN_NORM);
+ }
+ }
+ }
+ }
+ }
+
+ if (self.spawnflags & PUSH_ONCE)
+ remove (self);
+};
+
+// // dumptruck_ds
+// void() trigger_push_use =
+// {
+// self.is_waiting = !self.is_waiting;
+// }
+
+/*QUAKED trigger_push (.5 .5 .5) ? PUSH_ONCE X X X 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
+Pushes the player
+*/
+void() trigger_push =
+{
+ // dumptruck_ds
+ // new spawnflags for all entities -- iw
+ if (SUB_Inhibit ())
+ return;
+
+ InitTrigger ();
+ precache_sound ("ambience/windfly.wav");
+ self.touch = trigger_push_touch;
+
+ if (!self.speed)
+ self.speed = 1000;
+
+ if (self.target != __NULL__ && self.target != "")
+ {
+ // attempt to find the target
+ trigger_push_findtarget ();
+ if (!self.enemy)
+ if (!self.movedir)
+ // TODO CEV is this up? I don't remember
+ self.movedir = '0 0 180';
+ }
+
+ SUB_CheckWaiting ();
+};
+
+//======================================================================
+// dumptruck_ds was based on hipnotic blocker_use now Alklaine estate
+//----------------------------------------------------------------------
+void() push_toggle =
+{
+ if (self.estate != STATE_ACTIVE)
+ self.estate = STATE_ACTIVE;
+ else
+ self.estate = STATE_INACTIVE;
+};
+
+/*QUAKED trigger_push_custom (.5 .5 .5) ? PUSH_ONCE DT_STARTOFF DT_SILENT X 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
+
+
+dumptruck_ds
+
+trigger_push_custom is a new entity. This can be used to create traps,
+jumppads, currents in water and more.
+
+If DT_STARTOFF flag is set, this disables the trigger. This can be targeted
+and toggled off and on. If the DT_SILENT flag is set it won't make the windfly
+sound. Use DT_CUSTOM spawnflag and the noise key/value to use a custom push
+sound. Custom sounds should be "one off" sounds NOT be looping.
+
+Adapted from Hipnotic's func_togglewall */
+void() trigger_push_custom =
+{
+ // new spawnflags for all entities -- iw
+ if (SUB_Inhibit ())
+ return;
+
+ InitTrigger ();
+ precache_sound ("ambience/windfly.wav");
+ self.use = push_toggle;
+ self.touch = trigger_push_touch;
+
+ if (self.spawnflags & DT_STARTOFF)
+ self.estate = STATE_INACTIVE;
+
+ if (self.noise != "")
+ precache_sound(self.noise);
+
+ if (!self.speed)
+ self.speed = 1000;
+
+ SUB_CheckWaiting ();
+};
+
+//======================================================================
+// monsterjump
+//----------------------------------------------------------------------
+void() trigger_monsterjump_touch =
+{
+ if (self.estate != STATE_ACTIVE)
+ return;
+
+ if (other.flags & (FL_MONSTER | FL_FLY | FL_SWIM) != FL_MONSTER)
+ return;
+
+ // set XY even if not on ground, so the jump will clear lips
+ other.velocity_x = self.movedir_x * self.speed;
+ other.velocity_y = self.movedir_y * self.speed;
+
+ if (!(other.flags & FL_ONGROUND))
+ return;
+
+ other.flags = other.flags - FL_ONGROUND;
+
+ other.velocity_z = self.height;
+};
+
+/*QUAKED trigger_monsterjump (.5 .5 .5) ? X X X DT_STARTOFF 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
+
+Walking monsters that touch this will jump in the direction of the
+trigger's angle
+"speed" default to 200, the speed thrown forward
+"height" default to 200, the speed thrown upwards
+
+If DT_STARTOFF flag is set, this makes the trigger inactive. This can
+be targeted and toggled off and on.
+*/
+void() trigger_monsterjump =
+{
+ // new spawnflags for all entities -- iw
+ if (SUB_Inhibit ())
+ return;
+
+ self.use = push_toggle;
+
+ // dumptruck_ds
+ if (self.spawnflags & DT_STARTOFF)
+ {
+ self.estate = STATE_INACTIVE;
+ }
+
+ if (!self.speed)
+ self.speed = 200;
+ if (!self.height)
+ self.height = 200;
+ if (self.angles == '0 0 0')
+ self.angles = '0 360 0';
+
+ InitTrigger ();
+ self.touch = trigger_monsterjump_touch;
+
+ SUB_CheckWaiting ();
+};
+
+////////////////////////////////////////////////////////////////////////
+// end dumptruck_ds additions //////////////////////////////////////////
+////////////////////////////////////////////////////////////////////////
Return to the top of this page or return to the overview of this repo.
Diff qc/triggers/shake.qc
diff --git a/qc/triggers/shake.qc b/qc/triggers/shake.qc
new file mode 100644
index 0000000..b6b1675
--- /dev/null
+++ b/qc/triggers/shake.qc
@@ -0,0 +1,122 @@
+//==============================================================================
+// TRIGGER_SHAKE
+//==============================================================================
+
+// this is a point entity from Rubicon Rumble Pack Devkit
+// REQUIRES A TARGETNAME
+
+// constants
+float VIEWONLY = 1;
+
+//----------------------------------------------------------------------
+void() shake_think =
+{
+ if (self.attack_finished < time)
+ {
+ // Done
+ self.nextthink = -1;
+
+ if (self.noise1 != "")
+ sound (self, CHAN_VOICE, self.noise1, 1, ATTN_NORM);
+
+ return;
+ }
+
+ // Shake all players in the effect radius...
+
+ local entity plyr;
+ plyr = findradius (self.origin, self.count);
+
+ while (plyr)
+ {
+ if (plyr.flags & FL_CLIENT)
+ {
+ local float d;
+
+ // Scale effect by distance
+ d = vlen (self.origin - plyr.origin);
+ d = (self.count - d) / self.count;
+
+ if (d > 0)
+ {
+ // shake up the view
+ plyr.punchangle_x = -1 *
+ (random() + (0.025 * self.dmg * d));
+
+ // push the player around
+ if (plyr.flags & FL_ONGROUND
+ && !(self.spawnflags & VIEWONLY))
+ {
+ d = self.dmg * d;
+ plyr.velocity_x = plyr.velocity_x +
+ (random() * d * 2 - d);
+ plyr.velocity_y = plyr.velocity_y +
+ (random() * d * 2 - d);
+ // always push up
+ plyr.velocity_z = plyr.velocity_z +
+ (random() * d);
+ }
+ }
+ }
+ plyr = plyr.chain;
+ }
+
+ // keep going
+ self.nextthink = time + 0.1;
+};
+
+//----------------------------------------------------------------------
+void() shake_use =
+{
+ // already active
+ if (self.attack_finished > time)
+ return;
+
+ // Start...
+ if (self.noise != "")
+ sound (self, CHAN_VOICE, self.noise, 1, ATTN_NORM);
+
+ self.attack_finished = time + self.wait;
+ self.nextthink = time + 0.1;
+};
+
+/*QUAKED trigger_shake (.5 0 .5) (-8 -8 -8) (8 8 8) VIEWONLY X X X 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
+
+Earthquake trigger - shakes players in it's radius when active.
+Strength of tremor is greatest at the centre.
+dmg Strength at center (default is 120)
+wait Duration of shake (default is 1)
+count Affect radius (defalt is 200)
+noise Noise to play when starting to shake
+noise1 Noise to play when stopping
+targetname Must be triggered
+Spawnflags
+VIEWONL Shakes the view, but player movement is not affected
+*/
+void() trigger_shake =
+{
+ // new spawnflags for all entities -- iw
+ if (SUB_Inhibit ())
+ return;
+
+ if (!self.targetname)
+ objerror("trigger_shake without name");
+
+ if (self.noise != "")
+ precache_sound (self.noise);
+ if (self.noise1 != "")
+ precache_sound (self.noise1);
+
+ if (!self.dmg)
+ self.dmg = 120;
+ if (self.count <= 0)
+ self.count = 200;
+ if (self.wait <= 0)
+ self.wait = 1.0;
+
+ setorigin (self, self.origin);
+
+ self.nextthink = -1;
+ self.think = shake_think;
+ self.use = shake_use;
+};
Return to the top of this page or return to the overview of this repo.
Diff qc/triggers/teleport.qc
diff --git a/qc/triggers/teleport.qc b/qc/triggers/teleport.qc
new file mode 100644
index 0000000..303aa2b
--- /dev/null
+++ b/qc/triggers/teleport.qc
@@ -0,0 +1,493 @@
+//==============================================================================
+// TRIGGER_TELEPORT
+//==============================================================================
+
+// TELEPORT TRIGGERS with added functions from Zerstrorer and Qmaster
+// -- dumptruck_ds
+
+// constants
+float PLAYER_ONLY = 1;
+float SILENT = 2;
+float RANDOM = 4;
+float TELE_STEALTH = 8;
+float MONSTER_ONLY = 16;
+float TELE_DD = 32;
+
+//----------------------------------------------------------------------
+void() play_teleport =
+{
+ 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, 1, 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 = play_teleport;
+
+ 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() tdeath_touch =
+{
+ if (other == self.owner)
+ return;
+
+ // frag anyone who teleports in on top of an invincible player
+ if (other.classname == "player")
+ {
+ // 1998-07-26 Pentagram telefrag fix by Zoid/Maddes start
+ if (self.owner.classname != "player")
+ {
+ // other monsters explode themselves
+ T_Damage (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_Damage (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_Damage (self.owner, self, self, 50000);
+ }
+ return;
+ }
+
+ /*
+ if (self.owner.classname != "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_Damage (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 = 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;
+};
+
+//======================================================================
+// 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() teleport_randomspot =
+{
+ local float rndm;
+ // local float rndm, num1;
+ local entity spot,first;
+
+ rndm = rint (random() * (self.count - 1));
+ spot = find (world, classname, "info_teleport_random");
+ if (!spot)
+ dprint ("No random teleport points found!\n");
+ first = spot;
+
+ while (rndm > 0)
+ {
+ rndm = rndm - 1;
+ spot = find (spot, classname, "info_teleport_random");
+ }
+
+ if (spot == world)
+ {
+ dprint ("Random spot found world!!\n");
+ spot = first;
+ }
+
+ return spot;
+};
+// end dumptruck_ds
+
+//----------------------------------------------------------------------
+void() 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 & PLAYER_ONLY)
+ if (other.classname != "player")
+ return;
+
+ // is this going to work? dumptruck_ds
+ if (self.spawnflags & MONSTER_ONLY)
+ if (other.classname == "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
+ if (other.health <= 0 || other.solid != SOLID_SLIDEBOX)
+ return;
+
+ SUB_UseTargets ();
+
+ // put a tfog where the player was
+ // ### dhm - if stealth, don't spawn a fog
+ if (!(self.spawnflags & TELE_STEALTH))
+ spawn_tfog (other.origin);
+
+ // dhm - if this is a random teleporter, pick a random spot!
+ if (self.spawnflags & RANDOM)
+ t = teleport_randomspot ();
+ else if ((self.spawnflags & TELE_DD) && other.classname == "player")
+ t = find (world, targetname, self.noise);
+ else
+ t = find (world, targetname, self.target);
+
+ if (!t)
+ objerror ("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 & TELE_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.classname == "player")
+ {
+ // retrieves fog values from teleport destination, if any
+ fog_setFromEnt (other, t);
+
+ // turn this way immediately
+ other.fixangle = 1;
+ other.teleport_time = time + 0.7;
+ // push player out at PM_TELEEXITSPEED -- CEV
+ other.velocity = v_forward * PM_TELEEXITSPEED;
+ // TODO CEV commented out the next line
+ // other.flags = other.flags - other.flags & FL_ONGROUND;
+ }
+
+ if ((self.spawnflags & MONSTER_ONLY) && other.classname != "player")
+ {
+ // turn this way immediately
+ other.fixangle = 1;
+ other.teleport_time = time + 0.7;
+ if (other.flags & FL_ONGROUND)
+ other.flags = other.flags - FL_ONGROUND;
+ other.velocity = v_forward * PM_TELEEXITSPEED;
+ other.flags = other.flags - other.flags & FL_ONGROUND;
+ }
+};
+
+// this is from Qmaster:
+
+// "I created an info_teleport_changedest
+// target = targetname of trigger_teleport to affect
+// message = targetname of new info_teleport_destination (or whatever entity
+// really) to now teleport to
+
+// So that I can automatically update the teleporter under my coagula map as you
+// progress rather than have a bunch of triggers that I need to killtarget.
+// Falling is not fatal then, but it does put you back some. Works as a sorta
+// checkpoint system but also builds on my older idea for saving time in coop
+// implemented in my Terracity map eons ago.
+
+// looking at vanilla, you would only need to change trig.target to match
+// self.message if you were to add this."
+
+//----------------------------------------------------------------------
+void() teleport_destchange =
+{
+ local entity trig;
+
+ trig = find(world,targetname,self.target);
+ if (!trig || trig.classname != "trigger_teleport")
+ {
+ dprint ("\b[TELEPORT_DESTCHANGE]\b ");
+ dprint ("Cannot find trigger_teleport\n");
+ return;
+ }
+
+ trig.goalentity = find (world, targetname, self.message);
+ if (!trig.goalentity)
+ {
+ dprint ("\b[TELEPORT_DESTCHANGE]\b ");
+ dprint ("Cannot find teleport destination\n");
+ return;
+ }
+
+ makevectors (trig.goalentity.mangle);
+ trig.goalentity.movedir = v_forward;
+ trig.goalentity.pos1 = trig.goalentity.origin + 32 *
+ trig.goalentity.movedir;
+
+ // dumptruck_ds see comment above
+ trig.target = self.message;
+};
+
+/*QUAKED info_teleport_changedest (0 0.5 0) (-4 -4 -4) (4 4 4) X X X X 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
+Allows a mapper to change the target of a teleport_trigger. Useful in maps where
+the player may fall into a void and the mapper wants to update where they "respawn"
+as they progress through the level. Could also be used for teleport puzzles and more.
+target = trigger_teleport to change
+message = new info_teleport_destination's targetname to switch to
+targetname = name of this entity so we can use it
+*/
+void() info_teleport_changedest =
+{
+ // new spawnflags for all entities -- iw
+ if (SUB_Inhibit ())
+ return;
+
+ self.use = teleport_destchange;
+ if (self.targetname == "")
+ {
+ dprint ("\b[ERROR]\b info_teleport_changedest ");
+ dprint ("with no targetname\n");
+ remove (self);
+ }
+
+ if (self.target == "")
+ {
+ dprint ("\b[ERROR]\b info_teleport_changedest ");
+ dprint ("with no target\n");
+ remove(self);
+ }
+
+ if (self.message == "")
+ {
+ dprint ("\b[ERROR]\b info_teleport_changedest ");
+ dprint ("with no message set for new destination\n");
+ remove (self);
+ }
+};
+
+/*QUAKED info_teleport_destination (.5 .5 .5) (-8 -8 -8) (8 8 32) X X X X 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
+{
+model ("progs/player.mdl");
+}
+This is the destination marker for a teleporter. It should have a "targetname"
+field with the same value as a teleporter's "target" field.
+*/
+void() info_teleport_destination =
+{
+ // new spawnflags for all entities -- iw
+ if (SUB_Inhibit ())
+ return;
+
+ local vector end;
+
+ // this does nothing, just serves as a target spot
+ self.mangle = self.angles;
+ self.angles = '0 0 0';
+ self.model = "";
+
+ // drop teleporter exit to the floor if it's PM_TELEDROP units
+ // away -- CEV
+ end = self.origin + PM_TELEDROP;
+ tracebox (self.origin, self.mins, self.maxs, end, FALSE, self);
+ if (trace_allsolid || trace_startsolid || trace_fraction < 1)
+ {
+ droptofloor ();
+ // bump origin up so player won't exit into the floor -- CEV
+ // This was '0 0 24' but that was causing issues -- CEV
+ self.origin = self.origin + '0 0 27';
+ }
+ else
+ {
+ // instead apply the standard fixed Z offset -- CEV
+ self.origin = self.origin + '0 0 27';
+ }
+
+ if (!self.targetname)
+ if (self.target != __NULL__ && self.target != "")
+ // quake 3 compat -- CEV
+ self.targetname = self.target;
+ else
+ objerror ("no targetname");
+};
+
+/*QUAKED info_teleport_random (.5 .5 .5) (-8 -8 -8) (8 8 32) X X X X 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
+{
+model ("progs/player.mdl");
+}
+This is a random destination marker for a teleporter.
+*/
+void() info_teleport_random =
+{
+ // this does nothing, just serves as a target spot
+ self.mangle = self.angles;
+ self.angles = '0 0 0';
+ self.model = "";
+ self.origin = self.origin + '0 0 27';
+};
+
+//----------------------------------------------------------------------
+void() teleport_use =
+{
+ self.nextthink = time + 0.2;
+ // make sure even still objects get hit
+ force_retouch = 2;
+ self.think = SUB_Null;
+};
+
+/*QUAKED trigger_teleport (.5 .5 .5) ? PLAYER_ONLY SILENT RANDOM 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.
+
+SILENT(2) eliminates the teleporter ambient noise (good for hidden monster teleporters.
+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.
+STEALTH(8) eliminates the particle flash and noise when an entity is teleported.
+MONSTER_ONLY(16) will only teleport monsters
+*/
+void() trigger_teleport =
+{
+ // new spawnflags for all entities -- iw
+ if (SUB_Inhibit ())
+ return;
+
+ local vector o;
+
+ InitTrigger ();
+ self.touch = teleport_touch;
+
+ // find the destination
+ if (!self.target)
+ objerror ("no target");
+
+ self.use = teleport_use;
+
+ if (!(self.spawnflags & SILENT))
+ {
+ precache_sound ("ambience/hum1.wav");
+ o = (self.mins + self.maxs) * 0.5;
+ ambientsound (o, "ambience/hum1.wav", 0.5, ATTN_STATIC);
+ }
+
+ SUB_CheckWaiting ();
+};
Return to the top of this page or return to the overview of this repo.
Diff qc/triggers/textstory.qc
diff --git a/qc/triggers/textstory.qc b/qc/triggers/textstory.qc
new file mode 100644
index 0000000..5156eec
--- /dev/null
+++ b/qc/triggers/textstory.qc
@@ -0,0 +1,225 @@
+//==============================================================================
+// TRIGGER_TEXTSTORY
+//==============================================================================
+
+// constants
+float TEXTSTORY_SILENT = 1;
+float TEXTSTORY_NOFADE = 2;
+
+//----------------------------------------------------------------------
+void(entity controller) textstory_hide =
+{
+ if (!self.enemy || !(self.enemy.flags & FL_CLIENT))
+ return;
+
+ self.enemy.suppressCenterPrint = FALSE;
+ centerprint (self.enemy, "");
+
+ if (controller.noise2 != __NULL__ && controller.noise2 != "")
+ sound (self.enemy, CHAN_BODY, controller.noise2, 1, ATTN_NORM);
+
+ if (!(controller.spawnflags & TEXTSTORY_NOFADE))
+ csf_fade (self.enemy, 0, '0 0 0', 0.5);
+
+};
+
+//----------------------------------------------------------------------
+void(entity controller) textstory_show =
+{
+ if (!self.enemy || !(self.enemy.flags & FL_CLIENT))
+ return;
+
+ self.enemy.suppressCenterPrint = TRUE;
+
+ centerprint_builtin (self.enemy, controller.message);
+
+ if (!self.state)
+ {
+ if (controller.noise1 != __NULL__ && controller.noise1 != "")
+ {
+ sound (self.enemy, CHAN_BODY, controller.noise1,
+ 1, ATTN_NORM);
+ }
+
+ if (!(controller.spawnflags & TEXTSTORY_NOFADE))
+ {
+ //custom fade amount --dumptruck_ds
+ if (!self.fade_amt)
+ csf_fade (self.enemy, 160, '0 0 0', 1);
+ else
+ csf_fade (self.enemy, self.fade_amt,
+ '0 0 0', 1);
+ }
+ }
+
+ self.state = 1;
+};
+
+//----------------------------------------------------------------------
+void() trigger_textstory_hide =
+{
+ textstory_hide (self);
+
+ self.enemy = world;
+ self.state = 0;
+};
+
+//----------------------------------------------------------------------
+void() trigger_textstory_show =
+{
+ textstory_show (self);
+
+ self.think = trigger_textstory_hide;
+ self.nextthink = time + 0.2;
+
+};
+
+//----------------------------------------------------------------------
+void() trigger_textstory_touch =
+{
+
+ if (!(other.flags & FL_CLIENT))
+ return;
+ if (self.estate != STATE_ACTIVE)
+ return;
+
+ // don't show message if another player is already triggering it
+ if (other != self.enemy && self.state == 1)
+ return;
+
+ if (self.mangle &&
+ !isInAngle (other.v_angle, self.mangle, self.view_ofs))
+ return;
+
+ if (self.attack_finished < time)
+ {
+
+ self.attack_finished = time + 0.1;
+ self.enemy = other;
+
+ trigger_textstory_show ();
+ }
+};
+
+//----------------------------------------------------------------------
+void() trigger_textstory =
+{
+ InitTrigger ();
+ self.touch = trigger_textstory_touch;
+
+ if (self.view_ofs == '0 0 0')
+ self.view_ofs = '90 90 0';
+
+ if (self.mangle)
+ self.mangle = normalizeAngles180(self.mangle);
+
+ if (self.noise1 == "")
+ self.noise1 = "misc/talk.wav";
+
+ if (self.noise2 == "")
+ self.noise2 = "misc/null.wav";
+
+ if (self.spawnflags & TEXTSTORY_SILENT)
+ {
+ self.noise1 = "";
+ self.noise2 = "";
+ }
+
+
+ if (self.noise1 != "")
+ precache_sound (self.noise1);
+ if (self.noise2 != "")
+ precache_sound (self.noise2);
+
+ SUB_CheckWaiting ();
+};
+
+//----------------------------------------------------------------------
+void() target_textstory_helper_hide =
+{
+
+ textstory_hide (self.owner);
+ remove (self);
+};
+
+//----------------------------------------------------------------------
+void() target_textstory_helper_show =
+{
+ if (!self.enemy || !(self.enemy.flags & FL_CLIENT))
+ {
+ remove (self);
+ return;
+ }
+
+ textstory_show (self.owner);
+
+ if (self.attack_finished < time)
+ self.think = target_textstory_helper_hide;
+
+ self.nextthink = time + 0.1;
+};
+
+//----------------------------------------------------------------------
+void(entity tgt) target_textstory_spawn_helper =
+{
+ entity e;
+
+ e = spawn();
+ e.classname = "target_textstory_helper";
+ e.owner = self;
+ e.think = target_textstory_helper_show;
+ e.nextthink = time + 0.1;
+ e.attack_finished = time + self.wait;
+ e.enemy = tgt;
+};
+
+//----------------------------------------------------------------------
+void() target_textstory_use =
+{
+
+ if (!(activator.flags & FL_CLIENT))
+ return;
+ if (self.estate != STATE_ACTIVE)
+ return;
+
+ entity t;
+
+ if (self.spawnflags & TRIGGER_CENTERPRINTALL)
+ {
+ t = find (world, classname, "player");
+ while (t)
+ {
+ target_textstory_spawn_helper (t);
+ t = find (t, classname, "player");
+ }
+ }
+ else
+ {
+ target_textstory_spawn_helper (activator);
+ }
+};
+
+//----------------------------------------------------------------------
+void() target_textstory =
+{
+ if (self.noise1 == "")
+ self.noise1 = "misc/talk.wav";
+
+ if (self.noise2 == "")
+ self.noise2 = "misc/null.wav";
+
+ if (self.spawnflags & TEXTSTORY_SILENT) {
+ self.noise1 = "";
+ self.noise2 = "";
+ }
+
+ if (self.noise1 != "")
+ precache_sound (self.noise1);
+ if (self.noise2 != "")
+ precache_sound (self.noise2);
+
+ if (!self.wait)
+ self.wait = 5;
+
+ self.use = target_textstory_use;
+};
Return to the top of this page or return to the overview of this repo.
Diff qc/triggers_heal.qc
diff --git a/qc/triggers_heal.qc b/qc/triggers_heal.qc
deleted file mode 100644
index 8bac914..0000000
--- a/qc/triggers_heal.qc
+++ /dev/null
@@ -1,179 +0,0 @@
-//==============================================================================
-// HEAL TRIGGER
-//==============================================================================
-
-// from custents, modified by dumptruck_ds
-// Original entity submitted by Jan Martin Mathiassen, aka. TGR
-
-// was in dtmisc.qc -- CEV
-
-//----------------------------------------------------------------------
-void() heal_think =
-{
- if (self.cnt == self.count)
- {
- dprint ("trigger_heal think: full\n");
- self.think = SUB_Null;
- return;
- }
-
- local float recharge_amount = self.speed;
-
- if (self.count < (self.cnt + self.speed))
- recharge_amount = self.count - self.cnt;
-
- dprint ("trigger_heal think: [max: ");
- dprint (ftos(self.count));
- dprint (", current: ");
- dprint (ftos(self.cnt));
- dprint (", recharging: ");
- dprint (ftos(recharge_amount));
- dprint ("]\n");
-
- self.cnt = self.cnt + recharge_amount;
- self.nextthink = time + self.delay;
-};
-
-//----------------------------------------------------------------------
-void() heal_touch =
-{
- if (self.estate != STATE_ACTIVE)
- return;
-
- // from Copper -- dumptruck_ds
- if (other.movetype == MOVETYPE_NOCLIP)
- return;
- if (self.spawnflags & HEAL_PLAYER_ONLY && other.classname != "player")
- return;
- if (self.spawnflags & HEAL_MONSTER_ONLY && !(other.flags & FL_MONSTER))
- return;
- if (other.classname != "player" && !(other.flags & FL_MONSTER))
- return;
- if (other.heal_timer > time)
- return;
-
- if (self.count && self.cnt <= 0)
- {
- if (self.message2)
- centerprint (other, self.message2);
- return;
- }
-
- if ((other.takedamage) && (other.health < self.health_max))
- {
- if (self.noise != "")
- sound (self, CHAN_AUTO, self.noise, 1, ATTN_NORM);
- else
- sound (self, CHAN_AUTO, "items/r_item1.wav", 1,
- ATTN_NORM);
-
- local float calculated_healing;
-
- if ((other.health + self.heal_amount) > self.health_max)
- calculated_healing = self.health_max - other.health;
- else
- calculated_healing = self.heal_amount;
-
- if (self.count)
- {
- if (calculated_healing > self.cnt)
- calculated_healing = self.cnt;
-
- self.cnt = self.cnt - calculated_healing;
-
- if (self.delay)
- {
- self.think = heal_think;
- self.nextthink = time + self.delay;
- }
-
- dprint ("trigger_heal used: [max: ");
- dprint (ftos(self.count));
- dprint (", current: ");
- dprint (ftos(self.cnt));
- dprint (", using: ");
- dprint (ftos(calculated_healing));
- dprint ("]\n");
- }
-
- if (self.message)
- centerprint (other, self.message);
-
- T_Heal (other, calculated_healing, 1);
- other.heal_timer = time + self.wait;
- }
-};
-
-//----------------------------------------------------------------------
-void() heal_toggle =
-{
- if (self.touch == SUB_Null)
- self.touch = heal_touch;
- else
- self.touch = SUB_Null;
-};
-
-/*QUAKED trigger_heal (.5 .5 .5) ? HEAL_START_ON HEAL_PLAYER_ONLY HEAL_MONSTER_ONLY X 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 healed
-heal_amount -- the amount to heal each time (default 5)
-wait -- the time between each healing (default 1)
-health_max -- the upper limit for the healing (default 100, max 250)
-sounds -- set to 1 to enable the noise1 field for custom healing sound
-noise -- path to custom sound file
-message -- message to print on heal
-count -- maximum heal before exhausted
-speed -- amount to recharge at a time
-delay -- time before recharging
-message2 -- message to print when exhausted
-*/
-void() trigger_heal =
-{
- // new spawnflags for all entities -- iw
- if (SUB_Inhibit ())
- return;
-
- // play custom sound for healing if noise key exists
- precache_sound ("items/r_item1.wav");
- if (self.noise != "")
- precache_sound (self.noise);
-
- InitTrigger ();
-
- if (self.wait == 0)
- self.wait = 1;
-
- if (self.heal_amount == 0)
- self.heal_amount = 5;
-
- if (self.health_max == 0)
- self.health_max = 100;
- else if (self.health_max > 250)
- self.health_max = 250;
-
- if (self.count)
- {
- self.cnt = self.count;
-
- if (self.speed && !self.delay)
- self.delay = 10;
- else if (!self.speed && self.delay)
- self.speed = 5;
- }
-
- /*
- if (self.targetname)
- {
- self.use = heal_toggle;
- if (self.spawnflags & HEAL_START_ON)
- self.touch = heal_touch;
- else
- self.touch = SUB_Null;
- }
- else
- */
-
- self.touch = heal_touch;
-
- SUB_CheckWaiting ();
-};
Return to the top of this page or return to the overview of this repo.
Diff qc/triggers_ladder.qc
diff --git a/qc/triggers_ladder.qc b/qc/triggers_ladder.qc
deleted file mode 100644
index fa397be..0000000
--- a/qc/triggers_ladder.qc
+++ /dev/null
@@ -1,67 +0,0 @@
-//==============================================================================
-// LADDERS (from rubicon2.qc)
-//==============================================================================
-
-// selections from Rubicon 2 qc by john fitzgibbons
-
-//======================================================================
-// ladder_touch
-//----------------------------------------------------------------------
-void() ladder_touch =
-{
- // from Copper -- dumptruck_ds
- if (!CheckValidTouch())
- return;
-
- // prevent the player "sticking" to a ladder if they are standing on
- // the platform at the top of the ladder with the bottom of their
- // bounding box flush with the top of the trigger -- iw
- if (other.absmin_z + 1 >= self.absmax_z - 1)
- return;
-
- // if the trigger has an angles field, check player's facing direction
- if (self.movedir != '0 0 0')
- {
- makevectors (other.angles);
- if (v_forward * self.movedir < 0)
- // not facing the right way
- return;
- }
-
- // changed to PMFLAGS -- CEV
- other.pmove_flags |= PMF_ONLADDER;
-}
-
-//======================================================================
-// trigger_ladder
-//----------------------------------------------------------------------
-
-/*QUAKED trigger_ladder (.5 .5 .5) ? X X X X 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
-invisible ladder entity. when player is touching this entity, he can climb by pushing 'jump'
-
-Keys:
-
-"angle" the direction player must be facing to climb ladder
-*/
-void() trigger_ladder =
-{
- if (SUB_Inhibit())
- // new spawnflags for all entities -- iw
- return;
-
- // ignore an "up" or "down" angle (doesn't make sense for a ladder)
- if (self.angles_y == -1 || self.angles_y == -2)
- {
- dprint ("WARNING: trigger_ladder ignored bad 'angle' value: ");
- dprint (ftos (self.angles_y));
- dprint ("\n");
-
- self.angles_y = 0;
- }
-
- InitTrigger ();
- self.touch = ladder_touch;
-
- SUB_CheckWaiting ();
-};
-
Return to the top of this page or return to the overview of this repo.
Diff qc/triggers_push.qc
diff --git a/qc/triggers_push.qc b/qc/triggers_push.qc
deleted file mode 100644
index 1c20db0..0000000
--- a/qc/triggers_push.qc
+++ /dev/null
@@ -1,452 +0,0 @@
-//==============================================================================
-// TRIGGER PUSH
-//==============================================================================
-
-////////////////////////////////////////////////////////////////////////
-// start dumptruck_ds additions ////////////////////////////////////////
-////////////////////////////////////////////////////////////////////////
-
-float PUSH_ONCE = 1;
-float DT_STARTOFF = 8; // trigger will start off
-float DT_SILENT = 16; // push silently
-float DT_NOISE = 32; // use custom sound via noise key/value
-
-////////////////////////////////////////////////////////////////////////
-// start code CEV copied from Nexuiz ///////////////////////////////////
-////////////////////////////////////////////////////////////////////////
-
-//======================================================================
-// solve_quadratic
-//
-// from Nexuiz source code; copied from
-// https://github.com/smlinux/nexuiz/blob/master/data/qcsrc/common/util.qc
-// ax^2 + bx + c = 0
-//----------------------------------------------------------------------
-vector(float a, float b, float c) solve_quadratic =
-{
- vector v;
- float D;
- v = '0 0 0';
- if (a == 0)
- {
- if (b != 0)
- {
- v_x = v_y = -c / b;
- v_z = 1;
- }
- else
- {
- if (c == 0)
- {
- // actually, every number solves the equation!
- v_z = 1;
- }
- }
- }
- else
- {
- D = b*b - 4*a*c;
- if (D >= 0)
- {
- D = sqrt (D);
- if (a > 0)
- {
- // put the smaller solution first
- v_x = ((-b)-D) / (2*a);
- v_y = ((-b)+D) / (2*a);
- }
- else
- {
- v_x = (-b+D) / (2*a);
- v_y = (-b-D) / (2*a);
- }
- v_z = 1;
- }
- else
- {
- // complex solutions!
- D = sqrt (-D);
- v_x = -b / (2*a);
- if (a > 0)
- v_y = D / (2*a);
- else
- v_y = -D / (2*a);
- v_z = 0;
- }
- }
- return v;
-};
-
-//======================================================================
-// trigger_push_calculatevelocity
-//
-// Arguments:
-// org - origin of the object which is to be pushed
-// tgt - target entity (can be either a point or a model entity; if it
-// is the latter, its midpoint is used)
-// ht - jump height, measured from the higher one of org and tgt's
-// midpoint
-//
-// Returns: velocity for the jump
-// the global trigger_push_calculatevelocity_flighttime is set to the
-// total jump time
-//
-// from Nexuiz source code; copied from
-// https://github.com/smlinux/nexuiz/blob/master/data/qcsrc/server/t_jumppads.qc
-//----------------------------------------------------------------------
-vector(vector org, entity tgt, float ht) trigger_push_calculatevelocity =
-{
- local float grav, sdist, zdist, vs, vz, jumpheight;
- local vector sdir, torg;
- vector solution;
- float trigger_push_calculatevelocity_flighttime;
-
- torg = tgt.origin + (tgt.mins + tgt.maxs) * 0.5;
-
- grav = autocvar (sv_gravity, PM_GRAVITY);
-
- zdist = torg_z - org_z;
- sdist = vlen (torg - org - zdist * '0 0 1');
- sdir = normalize (torg - org - zdist * '0 0 1');
-
- // how high do we need to push the player?
- jumpheight = fabs (ht);
- if (zdist > 0)
- jumpheight = jumpheight + zdist;
-
- /*
- STOP.
-
- You will not understand the following equations anyway...
- But here is what I did to get them.
-
- I used the functions
-
- s(t) = t * vs
- z(t) = t * vz - 1/2 grav t^2
-
- and solved for:
-
- s(ti) = sdist
- z(ti) = zdist
- max(z, ti) = jumpheight
-
- From these three equations, you will find the three
- parameters vs, vz and ti.
- */
-
- // push him so high... NOTE: sqrt(positive)!
- vz = sqrt (2 * grav * jumpheight);
-
- // we start with downwards velocity only if it's a downjump
- // and the jump apex should be outside the jump!
- if (ht < 0)
- if (zdist < 0)
- vz = -vz;
-
- // equation "z(ti) = zdist"
- solution = solve_quadratic (0.5 * grav, -vz, zdist);
- // ALWAYS solvable because jumpheight >= zdist
- if (!solution_z)
- // just in case it is not solvable due to roundoff errors,
- // assume two equal solutions at their center (this is
- // mainly for the usual case with ht == 0)
- solution_y = solution_x;
- if (zdist == 0)
- // solution_x is 0 in this case, so don't use it, but rather
- // use solution_y (which will be sqrt(0.5 * jumpheight / grav),
- // actually)
- solution_x = solution_y;
-
- if (zdist < 0)
- {
- // down-jump
- if (ht < 0)
- {
- // almost straight line type
- // jump apex is before the jump
- // we must take the larger one
- trigger_push_calculatevelocity_flighttime = solution_y;
- }
- else
- {
- // regular jump
- // jump apex is during the jump
- // we must take the larger one too
- trigger_push_calculatevelocity_flighttime = solution_y;
- }
- }
- else
- {
- // up-jump
- if (ht < 0)
- {
- // almost straight line type
- // jump apex is after the jump
- // we must take the smaller one
- trigger_push_calculatevelocity_flighttime = solution_x;
- }
- else
- {
- // regular jump
- // jump apex is during the jump
- // we must take the larger one
- trigger_push_calculatevelocity_flighttime = solution_y;
- }
- }
- vs = sdist / trigger_push_calculatevelocity_flighttime;
-
- // finally calculate the velocity
- return sdir * vs + '0 0 1' * vz;
-};
-
-//----------------------------------------------------------------------
-void() trigger_push_findtarget =
-{
- self.enemy = find (world, targetname, self.target);
- if (self.enemy)
- {
- local vector org;
- org = (self.absmin + self.absmax) * 0.5;
- org_z = self.absmax_z - -24; // - PL_MIN_z;
- self.movedir = trigger_push_calculatevelocity (org,
- self.enemy, self.height);
- }
-};
-
-////////////////////////////////////////////////////////////////////////
-// end code CEV copied from Nexuiz /////////////////////////////////////
-////////////////////////////////////////////////////////////////////////
-
-//----------------------------------------------------------------------
-void() trigger_push_touch =
-{
- if (self.estate != STATE_ACTIVE)
- return;
-
- // from Copper -- dumptruck_ds
- if (other.movetype == MOVETYPE_NOCLIP)
- return;
-
- // try to find target again if necessary
- if (self.target && (!self.enemy))
- trigger_push_findtarget ();
-
- // we have a target, set movedir accordingly
- if (self.target && self.enemy)
- self.movedir = trigger_push_calculatevelocity (other.origin,
- self.enemy, self.height);
-
- if (other.classname == "grenade")
- {
- if (self.target && self.enemy)
- other.velocity = self.movedir;
- else
- other.velocity = self.speed * self.movedir * 10;
- }
- else if (other.health > 0)
- {
- if (self.target && self.enemy)
- other.velocity = self.movedir;
- else
- other.velocity = self.speed * self.movedir * 10;
-
- if (other.classname == "player")
- {
- if (!(self.spawnflags & DT_SILENT))
- {
- if (other.fly_sound < time)
- {
- if (!(self.spawnflags & DT_NOISE))
- {
- other.fly_sound = time + 1.5;
- sound (other, CHAN_AUTO,
- "ambience/windfly.wav",
- 1, ATTN_NORM);
- }
- else
- {
- other.fly_sound = time + 1.5;
- sound (other, CHAN_AUTO,
- self.noise,
- 1, ATTN_NORM);
- }
- }
- }
- }
- }
-
- if (self.spawnflags & PUSH_ONCE)
- remove (self);
-};
-
-// // dumptruck_ds
-// void() trigger_push_use =
-// {
-// self.is_waiting = !self.is_waiting;
-// }
-
-/*QUAKED trigger_push (.5 .5 .5) ? PUSH_ONCE X X X 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
-Pushes the player
-*/
-void() trigger_push =
-{
- // dumptruck_ds
- // new spawnflags for all entities -- iw
- if (SUB_Inhibit ())
- return;
-
- InitTrigger ();
- precache_sound ("ambience/windfly.wav");
- self.touch = trigger_push_touch;
-
- if (!self.speed)
- self.speed = 1000;
-
- if (self.target)
- {
- // attempt to find the target
- trigger_push_findtarget ();
- if (!self.enemy)
- if (!self.movedir)
- // TODO CEV is this up? I don't remember
- self.movedir = '0 0 180';
- }
-
- SUB_CheckWaiting ();
-};
-
-//======================================================================
-// dumptruck_ds was based on hipnotic blocker_use now Alklaine estate
-//----------------------------------------------------------------------
-void() push_toggle =
-{
- if (self.estate != STATE_ACTIVE)
- self.estate = STATE_ACTIVE;
- else
- self.estate = STATE_INACTIVE;
-};
-
-/*QUAKED trigger_push_custom (.5 .5 .5) ? PUSH_ONCE DT_STARTOFF DT_SILENT X 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
-
-
-dumptruck_ds
-
-trigger_push_custom is a new entity. This can be used to create traps,
-jumppads, currents in water and more.
-
-If DT_STARTOFF flag is set, this disables the trigger. This can be targeted
-and toggled off and on. If the DT_SILENT flag is set it won't make the windfly
-sound. Use DT_CUSTOM spawnflag and the noise key/value to use a custom push
-sound. Custom sounds should be "one off" sounds NOT be looping.
-
-Adapted from Hipnotic's func_togglewall */
-void() trigger_push_custom =
-{
- // new spawnflags for all entities -- iw
- if (SUB_Inhibit ())
- return;
-
- InitTrigger ();
- precache_sound ("ambience/windfly.wav");
- self.use = push_toggle;
- self.touch = trigger_push_touch;
-
- if (self.spawnflags & DT_STARTOFF)
- self.estate = STATE_INACTIVE;
-
- if (self.noise != "")
- precache_sound(self.noise);
-
- if (!self.speed)
- self.speed = 1000;
-
- SUB_CheckWaiting ();
-};
-
-//======================================================================
-// push target entities for Quake 3 compatibility -- CEV
-//----------------------------------------------------------------------
-void() target_push =
-{
- // new spawnflags for all entities -- iw
- if (SUB_Inhibit ())
- return;
-
- if (!self.targetname)
- if (self.target)
- // quake 3 compat -- CEV
- self.targetname = self.target;
- else
- objerror ("no targetname");
-};
-
-//----------------------------------------------------------------------
-void() target_position =
-{
- target_push ();
-};
-
-//======================================================================
-// monsterjump
-//----------------------------------------------------------------------
-void() trigger_monsterjump_touch =
-{
- if (self.estate != STATE_ACTIVE)
- return;
-
- if (other.flags & (FL_MONSTER | FL_FLY | FL_SWIM) != FL_MONSTER)
- return;
-
- // set XY even if not on ground, so the jump will clear lips
- other.velocity_x = self.movedir_x * self.speed;
- other.velocity_y = self.movedir_y * self.speed;
-
- if (!(other.flags & FL_ONGROUND))
- return;
-
- other.flags = other.flags - FL_ONGROUND;
-
- other.velocity_z = self.height;
-};
-
-/*QUAKED trigger_monsterjump (.5 .5 .5) ? X X X DT_STARTOFF 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
-
-Walking monsters that touch this will jump in the direction of the
-trigger's angle
-"speed" default to 200, the speed thrown forward
-"height" default to 200, the speed thrown upwards
-
-If DT_STARTOFF flag is set, this makes the trigger inactive. This can
-be targeted and toggled off and on.
-*/
-void() trigger_monsterjump =
-{
- // new spawnflags for all entities -- iw
- if (SUB_Inhibit ())
- return;
-
- self.use = push_toggle;
-
- // dumptruck_ds
- if (self.spawnflags & DT_STARTOFF)
- {
- self.estate = STATE_INACTIVE;
- }
-
- if (!self.speed)
- self.speed = 200;
- if (!self.height)
- self.height = 200;
- if (self.angles == '0 0 0')
- self.angles = '0 360 0';
-
- InitTrigger ();
- self.touch = trigger_monsterjump_touch;
-
- SUB_CheckWaiting ();
-};
-
-////////////////////////////////////////////////////////////////////////
-// end dumptruck_ds additions //////////////////////////////////////////
-////////////////////////////////////////////////////////////////////////
Return to the top of this page or return to the overview of this repo.
Diff qc/triggers_shake.qc
diff --git a/qc/triggers_shake.qc b/qc/triggers_shake.qc
deleted file mode 100644
index b6b1675..0000000
--- a/qc/triggers_shake.qc
+++ /dev/null
@@ -1,122 +0,0 @@
-//==============================================================================
-// TRIGGER_SHAKE
-//==============================================================================
-
-// this is a point entity from Rubicon Rumble Pack Devkit
-// REQUIRES A TARGETNAME
-
-// constants
-float VIEWONLY = 1;
-
-//----------------------------------------------------------------------
-void() shake_think =
-{
- if (self.attack_finished < time)
- {
- // Done
- self.nextthink = -1;
-
- if (self.noise1 != "")
- sound (self, CHAN_VOICE, self.noise1, 1, ATTN_NORM);
-
- return;
- }
-
- // Shake all players in the effect radius...
-
- local entity plyr;
- plyr = findradius (self.origin, self.count);
-
- while (plyr)
- {
- if (plyr.flags & FL_CLIENT)
- {
- local float d;
-
- // Scale effect by distance
- d = vlen (self.origin - plyr.origin);
- d = (self.count - d) / self.count;
-
- if (d > 0)
- {
- // shake up the view
- plyr.punchangle_x = -1 *
- (random() + (0.025 * self.dmg * d));
-
- // push the player around
- if (plyr.flags & FL_ONGROUND
- && !(self.spawnflags & VIEWONLY))
- {
- d = self.dmg * d;
- plyr.velocity_x = plyr.velocity_x +
- (random() * d * 2 - d);
- plyr.velocity_y = plyr.velocity_y +
- (random() * d * 2 - d);
- // always push up
- plyr.velocity_z = plyr.velocity_z +
- (random() * d);
- }
- }
- }
- plyr = plyr.chain;
- }
-
- // keep going
- self.nextthink = time + 0.1;
-};
-
-//----------------------------------------------------------------------
-void() shake_use =
-{
- // already active
- if (self.attack_finished > time)
- return;
-
- // Start...
- if (self.noise != "")
- sound (self, CHAN_VOICE, self.noise, 1, ATTN_NORM);
-
- self.attack_finished = time + self.wait;
- self.nextthink = time + 0.1;
-};
-
-/*QUAKED trigger_shake (.5 0 .5) (-8 -8 -8) (8 8 8) VIEWONLY X X X 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
-
-Earthquake trigger - shakes players in it's radius when active.
-Strength of tremor is greatest at the centre.
-dmg Strength at center (default is 120)
-wait Duration of shake (default is 1)
-count Affect radius (defalt is 200)
-noise Noise to play when starting to shake
-noise1 Noise to play when stopping
-targetname Must be triggered
-Spawnflags
-VIEWONL Shakes the view, but player movement is not affected
-*/
-void() trigger_shake =
-{
- // new spawnflags for all entities -- iw
- if (SUB_Inhibit ())
- return;
-
- if (!self.targetname)
- objerror("trigger_shake without name");
-
- if (self.noise != "")
- precache_sound (self.noise);
- if (self.noise1 != "")
- precache_sound (self.noise1);
-
- if (!self.dmg)
- self.dmg = 120;
- if (self.count <= 0)
- self.count = 200;
- if (self.wait <= 0)
- self.wait = 1.0;
-
- setorigin (self, self.origin);
-
- self.nextthink = -1;
- self.think = shake_think;
- self.use = shake_use;
-};
Return to the top of this page or return to the overview of this repo.
Diff qc/triggers_teleport.qc
diff --git a/qc/triggers_teleport.qc b/qc/triggers_teleport.qc
deleted file mode 100644
index 4b4365c..0000000
--- a/qc/triggers_teleport.qc
+++ /dev/null
@@ -1,512 +0,0 @@
-//==============================================================================
-// TRIGGER_TELEPORT
-//==============================================================================
-
-// TELEPORT TRIGGERS with added functions from Zerstrorer and Qmaster
-// -- dumptruck_ds
-
-// constants
-float PLAYER_ONLY = 1;
-float SILENT = 2;
-float RANDOM = 4;
-float TELE_STEALTH = 8;
-float MONSTER_ONLY = 16;
-float TELE_DD = 32;
-
-//----------------------------------------------------------------------
-void() play_teleport =
-{
- 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, 1, 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 = play_teleport;
-
- 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() tdeath_touch =
-{
- if (other == self.owner)
- return;
-
- // frag anyone who teleports in on top of an invincible player
- if (other.classname == "player")
- {
- // 1998-07-26 Pentagram telefrag fix by Zoid/Maddes start
- if (self.owner.classname != "player")
- {
- // other monsters explode themselves
- T_Damage (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_Damage (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_Damage (self.owner, self, self, 50000);
- }
- return;
- }
-
- /*
- if (self.owner.classname != "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_Damage (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 = 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;
-};
-
-//======================================================================
-// 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() teleport_randomspot =
-{
- local float rndm;
- // local float rndm, num1;
- local entity spot,first;
-
- rndm = rint (random() * (self.count - 1));
- spot = find (world, classname, "info_teleport_random");
- if (!spot)
- dprint ("No random teleport points found!\n");
- first = spot;
-
- while (rndm > 0)
- {
- rndm = rndm - 1;
- spot = find (spot, classname, "info_teleport_random");
- }
-
- if (spot == world)
- {
- dprint ("Random spot found world!!\n");
- spot = first;
- }
-
- return spot;
-};
-// end dumptruck_ds
-
-//----------------------------------------------------------------------
-void() 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 & PLAYER_ONLY)
- if (other.classname != "player")
- return;
-
- // is this going to work? dumptruck_ds
- if (self.spawnflags & MONSTER_ONLY)
- if (other.classname == "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
- if (other.health <= 0 || other.solid != SOLID_SLIDEBOX)
- return;
-
- SUB_UseTargets ();
-
- // put a tfog where the player was
- // ### dhm - if stealth, don't spawn a fog
- if (!(self.spawnflags & TELE_STEALTH))
- spawn_tfog (other.origin);
-
- // dhm - if this is a random teleporter, pick a random spot!
- if (self.spawnflags & RANDOM)
- t = teleport_randomspot ();
- else if ((self.spawnflags & TELE_DD) && other.classname == "player")
- t = find (world, targetname, self.noise);
- else
- t = find (world, targetname, self.target);
-
- if (!t)
- objerror ("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 & TELE_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.classname == "player")
- {
- // retrieves fog values from teleport destination, if any
- fog_setFromEnt (other, t);
-
- // turn this way immediately
- other.fixangle = 1;
- other.teleport_time = time + 0.7;
- // push player out at PM_TELEEXITSPEED -- CEV
- other.velocity = v_forward * PM_TELEEXITSPEED;
- }
- other.flags = other.flags - other.flags & FL_ONGROUND;
-
- if ((self.spawnflags & MONSTER_ONLY) && other.classname != "player")
- {
- // turn this way immediately
- other.fixangle = 1;
- other.teleport_time = time + 0.7;
- if (other.flags & FL_ONGROUND)
- other.flags = other.flags - FL_ONGROUND;
- other.velocity = v_forward * PM_TELEEXITSPEED;
- }
- other.flags = other.flags - other.flags & FL_ONGROUND;
-};
-
-// this is from Qmaster:
-
-// "I created an info_teleport_changedest
-// target = targetname of trigger_teleport to affect
-// message = targetname of new info_teleport_destination (or whatever entity
-// really) to now teleport to
-
-// So that I can automatically update the teleporter under my coagula map as you
-// progress rather than have a bunch of triggers that I need to killtarget.
-// Falling is not fatal then, but it does put you back some. Works as a sorta
-// checkpoint system but also builds on my older idea for saving time in coop
-// implemented in my Terracity map eons ago.
-
-// looking at vanilla, you would only need to change trig.target to match
-// self.message if you were to add this."
-
-//----------------------------------------------------------------------
-void() teleport_destchange =
-{
- local entity trig;
-
- trig = find(world,targetname,self.target);
- if (!trig || trig.classname != "trigger_teleport")
- {
- dprint ("\b[TELEPORT_DESTCHANGE]\b ");
- dprint ("Cannot find trigger_teleport\n");
- return;
- }
-
- trig.goalentity = find (world, targetname, self.message);
- if (!trig.goalentity)
- {
- dprint ("\b[TELEPORT_DESTCHANGE]\b ");
- dprint ("Cannot find teleport destination\n");
- return;
- }
-
- makevectors (trig.goalentity.mangle);
- trig.goalentity.movedir = v_forward;
- trig.goalentity.pos1 = trig.goalentity.origin + 32 *
- trig.goalentity.movedir;
-
- // dumptruck_ds see comment above
- trig.target = self.message;
-};
-
-/*QUAKED info_teleport_changedest (0 0.5 0) (-4 -4 -4) (4 4 4) X X X X 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
-Allows a mapper to change the target of a teleport_trigger. Useful in maps where
-the player may fall into a void and the mapper wants to update where they "respawn"
-as they progress through the level. Could also be used for teleport puzzles and more.
-target = trigger_teleport to change
-message = new info_teleport_destination's targetname to switch to
-targetname = name of this entity so we can use it
-*/
-void() info_teleport_changedest =
-{
- // new spawnflags for all entities -- iw
- if (SUB_Inhibit ())
- return;
-
- self.use = teleport_destchange;
- if (self.targetname == "")
- {
- dprint ("\b[ERROR]\b info_teleport_changedest ");
- dprint ("with no targetname\n");
- remove (self);
- }
-
- if (self.target == "")
- {
- dprint ("\b[ERROR]\b info_teleport_changedest ");
- dprint ("with no target\n");
- remove(self);
- }
-
- if (self.message == "")
- {
- dprint ("\b[ERROR]\b info_teleport_changedest ");
- dprint ("with no message set for new destination\n");
- remove (self);
- }
-};
-
-/*QUAKED info_teleport_destination (.5 .5 .5) (-8 -8 -8) (8 8 32) X X X X 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
-{
-model ("progs/player.mdl");
-}
-This is the destination marker for a teleporter. It should have a "targetname"
-field with the same value as a teleporter's "target" field.
-*/
-void() info_teleport_destination =
-{
- // new spawnflags for all entities -- iw
- if (SUB_Inhibit ())
- return;
-
- local vector end;
-
- // this does nothing, just serves as a target spot
- self.mangle = self.angles;
- self.angles = '0 0 0';
- self.model = "";
-
- // drop teleporter exit to the floor if it's PM_TELEDROP units
- // away -- CEV
- end = self.origin + PM_TELEDROP;
- tracebox (self.origin, self.mins, self.maxs, end, FALSE, self);
- if (trace_allsolid || trace_startsolid || trace_fraction < 1)
- {
- droptofloor ();
- // bump origin up so player won't exit into the floor -- CEV
- // This was '0 0 24' but that was causing issues -- CEV
- self.origin = self.origin + '0 0 27';
- }
- else
- {
- // instead apply the standard fixed Z offset -- CEV
- self.origin = self.origin + '0 0 27';
- }
-
- if (!self.targetname)
- if (self.target)
- // quake 3 compat -- CEV
- self.targetname = self.target;
- else
- objerror ("no targetname");
-};
-
-//======================================================================
-// Quake 3 compat (I think) -- CEV
-//----------------------------------------------------------------------
-void() misc_teleporter_dest =
-{
- info_teleport_destination ();
-};
-
-//----------------------------------------------------------------------
-void() misc_teleporter_destination =
-{
- info_teleport_destination ();
-};
-
-//----------------------------------------------------------------------
-void() target_teleporter =
-{
- info_teleport_destination ();
-};
-
-/*QUAKED info_teleport_random (.5 .5 .5) (-8 -8 -8) (8 8 32) X X X X 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
-{
-model ("progs/player.mdl");
-}
-This is a random destination marker for a teleporter.
-*/
-void() info_teleport_random =
-{
- // this does nothing, just serves as a target spot
- self.mangle = self.angles;
- self.angles = '0 0 0';
- self.model = "";
- self.origin = self.origin + '0 0 27';
-};
-
-//----------------------------------------------------------------------
-void() teleport_use =
-{
- self.nextthink = time + 0.2;
- // make sure even still objects get hit
- force_retouch = 2;
- self.think = SUB_Null;
-};
-
-/*QUAKED trigger_teleport (.5 .5 .5) ? PLAYER_ONLY SILENT RANDOM 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.
-
-SILENT(2) eliminates the teleporter ambient noise (good for hidden monster teleporters.
-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.
-STEALTH(8) eliminates the particle flash and noise when an entity is teleported.
-MONSTER_ONLY(16) will only teleport monsters
-*/
-void() trigger_teleport =
-{
- // new spawnflags for all entities -- iw
- if (SUB_Inhibit ())
- return;
-
- local vector o;
-
- InitTrigger ();
- self.touch = teleport_touch;
-
- // find the destination
- if (!self.target)
- objerror ("no target");
-
- self.use = teleport_use;
-
- if (!(self.spawnflags & SILENT))
- {
- precache_sound ("ambience/hum1.wav");
- o = (self.mins + self.maxs) * 0.5;
- ambientsound (o, "ambience/hum1.wav", 0.5, ATTN_STATIC);
- }
-
- SUB_CheckWaiting ();
-};
Return to the top of this page or return to the overview of this repo.
Diff qc/triggers_textstory.qc
diff --git a/qc/triggers_textstory.qc b/qc/triggers_textstory.qc
deleted file mode 100644
index 7d62443..0000000
--- a/qc/triggers_textstory.qc
+++ /dev/null
@@ -1,225 +0,0 @@
-//==============================================================================
-// TRIGGER_TEXTSTORY
-//==============================================================================
-
-// constants
-float TEXTSTORY_SILENT = 1;
-float TEXTSTORY_NOFADE = 2;
-
-//----------------------------------------------------------------------
-void(entity controller) textstory_hide =
-{
- if (!self.enemy || !(self.enemy.flags & FL_CLIENT))
- return;
-
- self.enemy.suppressCenterPrint = FALSE;
- centerprint (self.enemy, "");
-
- if (controller.noise2)
- sound (self.enemy, CHAN_BODY, controller.noise2, 1, ATTN_NORM);
-
- if (!(controller.spawnflags & TEXTSTORY_NOFADE))
- csf_fade (self.enemy, 0, '0 0 0', 0.5);
-
-};
-
-//----------------------------------------------------------------------
-void(entity controller) textstory_show =
-{
- if (!self.enemy || !(self.enemy.flags & FL_CLIENT))
- return;
-
- self.enemy.suppressCenterPrint = TRUE;
-
- centerprint_builtin (self.enemy, controller.message);
-
- if (!self.state)
- {
- if (controller.noise1)
- {
- sound (self.enemy, CHAN_BODY, controller.noise1,
- 1, ATTN_NORM);
- }
-
- if (!(controller.spawnflags & TEXTSTORY_NOFADE))
- {
- //custom fade amount --dumptruck_ds
- if (!self.fade_amt)
- csf_fade (self.enemy, 160, '0 0 0', 1);
- else
- csf_fade (self.enemy, self.fade_amt,
- '0 0 0', 1);
- }
- }
-
- self.state = 1;
-};
-
-//----------------------------------------------------------------------
-void() trigger_textstory_hide =
-{
- textstory_hide (self);
-
- self.enemy = world;
- self.state = 0;
-};
-
-//----------------------------------------------------------------------
-void() trigger_textstory_show =
-{
- textstory_show (self);
-
- self.think = trigger_textstory_hide;
- self.nextthink = time + 0.2;
-
-};
-
-//----------------------------------------------------------------------
-void() trigger_textstory_touch =
-{
-
- if (!(other.flags & FL_CLIENT))
- return;
- if (self.estate != STATE_ACTIVE)
- return;
-
- // don't show message if another player is already triggering it
- if (other != self.enemy && self.state == 1)
- return;
-
- if (self.mangle &&
- !isInAngle (other.v_angle, self.mangle, self.view_ofs))
- return;
-
- if (self.attack_finished < time)
- {
-
- self.attack_finished = time + 0.1;
- self.enemy = other;
-
- trigger_textstory_show ();
- }
-};
-
-//----------------------------------------------------------------------
-void() trigger_textstory =
-{
- InitTrigger ();
- self.touch = trigger_textstory_touch;
-
- if (self.view_ofs == '0 0 0')
- self.view_ofs = '90 90 0';
-
- if (self.mangle)
- self.mangle = normalizeAngles180(self.mangle);
-
- if (self.noise1 == "")
- self.noise1 = "misc/talk.wav";
-
- if (self.noise2 == "")
- self.noise2 = "misc/null.wav";
-
- if (self.spawnflags & TEXTSTORY_SILENT)
- {
- self.noise1 = "";
- self.noise2 = "";
- }
-
-
- if (self.noise1 != "")
- precache_sound (self.noise1);
- if (self.noise2 != "")
- precache_sound (self.noise2);
-
- SUB_CheckWaiting ();
-};
-
-//----------------------------------------------------------------------
-void() target_textstory_helper_hide =
-{
-
- textstory_hide (self.owner);
- remove (self);
-};
-
-//----------------------------------------------------------------------
-void() target_textstory_helper_show =
-{
- if (!self.enemy || !(self.enemy.flags & FL_CLIENT))
- {
- remove (self);
- return;
- }
-
- textstory_show (self.owner);
-
- if (self.attack_finished < time)
- self.think = target_textstory_helper_hide;
-
- self.nextthink = time + 0.1;
-};
-
-//----------------------------------------------------------------------
-void(entity tgt) target_textstory_spawn_helper =
-{
- entity e;
-
- e = spawn();
- e.classname = "target_textstory_helper";
- e.owner = self;
- e.think = target_textstory_helper_show;
- e.nextthink = time + 0.1;
- e.attack_finished = time + self.wait;
- e.enemy = tgt;
-};
-
-//----------------------------------------------------------------------
-void() target_textstory_use =
-{
-
- if (!(activator.flags & FL_CLIENT))
- return;
- if (self.estate != STATE_ACTIVE)
- return;
-
- entity t;
-
- if (self.spawnflags & TRIGGER_CENTERPRINTALL)
- {
- t = find (world, classname, "player");
- while (t)
- {
- target_textstory_spawn_helper (t);
- t = find (t, classname, "player");
- }
- }
- else
- {
- target_textstory_spawn_helper (activator);
- }
-};
-
-//----------------------------------------------------------------------
-void() target_textstory =
-{
- if (self.noise1 == "")
- self.noise1 = "misc/talk.wav";
-
- if (self.noise2 == "")
- self.noise2 = "misc/null.wav";
-
- if (self.spawnflags & TEXTSTORY_SILENT) {
- self.noise1 = "";
- self.noise2 = "";
- }
-
- if (self.noise1 != "")
- precache_sound (self.noise1);
- if (self.noise2 != "")
- precache_sound (self.noise2);
-
- if (!self.wait)
- self.wait = 5;
-
- self.use = target_textstory_use;
-};
Return to the top of this page or return to the overview of this repo.
Diff qc/weapons.qc
diff --git a/qc/weapons.qc b/qc/weapons.qc
index 5729d49..5d80257 100644
--- a/qc/weapons.qc
+++ b/qc/weapons.qc
@@ -1054,7 +1054,7 @@ void() spike_touch =
{
WriteByte (MSG_BROADCAST, SVC_TEMPENTITY);
- if (self.owner.snd_hit)
+ if (self.owner.snd_hit != __NULL__ && self.owner.snd_hit != "")
{
sound (self, CHAN_WEAPON, self.owner.snd_hit, 1, ATTN_STATIC); //dumptruck_ds
WriteByte(MSG_BROADCAST, TE_GUNSHOT);
@@ -1097,7 +1097,7 @@ void() superspike_touch =
}
else
{
- if (self.owner.snd_hit)
+ if (self.owner.snd_hit != __NULL__ && self.owner.snd_hit != "")
{
sound (self, CHAN_WEAPON, self.owner.snd_hit, 1, ATTN_STATIC); //dumptruck_ds
WriteByte (MSG_BROADCAST, SVC_TEMPENTITY);
Return to the top of this page or return to the overview of this repo.