]> de.git.xonotic.org Git - xonotic/xonotic-data.pk3dir.git/commitdiff
w_arc: various teleport/warp related fixes.
authorRudolf Polzer <rpolzer@localhost>
Fri, 16 May 2014 19:27:56 +0000 (21:27 +0200)
committerRudolf Polzer <rpolzer@localhost>
Sun, 18 May 2014 18:53:24 +0000 (20:53 +0200)
- Reset arc beam on warp/teleport.
- Lock arc beam for a RTT after reset (so the beam is straight at
  matching times/locations on client/server, after which everything is
  consistent again).
- Use unwarped view origin and angles on client to fix behaviour when
  the client is currently predicting the warp, as there's no signal for
  begin of warp prediction.
- Fix TrueAim-like logic on client when standing right against a wall
  (use the same avoid-shotorigin-poking-into-solid hack as other TrueAim
  code does).

warpzonelib: provide unwarped origin/angles in a variable.

qcsrc/client/View.qc
qcsrc/client/csqcmodel_hooks.qc
qcsrc/common/weapons/w_arc.qc
qcsrc/server/t_teleporters.qc
qcsrc/server/weapons/tracing.qc
qcsrc/warpzonelib/client.qc
qcsrc/warpzonelib/client.qh

index d1071309404cd0b78a2440cdfb2d12963dc3ddf4..ecc3fa126f05d62f1ea4df0a85f1bb1f610b62be 100644 (file)
@@ -269,7 +269,7 @@ float EnemyHitCheck()
 
 float TrueAimCheck()
 {
-       float nudge = 1; // added to traceline target and subtracted from result
+       float nudge = 1; // added to traceline target and subtracted from result TOOD(divVerent): do we still need this? Doesn't the engine do this now for us?
        vector vecs, trueaimpoint, w_shotorg;
        vector mi, ma, dv;
        float shottype;
index 120b6658df8792443433fc40d7192bc89c4e809b..077b7d9720a1501e6d9eb72e3a36dabd3c0ec54c 100644 (file)
@@ -470,8 +470,14 @@ void CSQCModel_Effects_PreUpdate(void)
        self.effects = self.csqcmodel_effects;
        self.modelflags = self.csqcmodel_modelflags;
 }
+void Reset_ArcBeam(void);
 void CSQCModel_Effects_PostUpdate(void)
 {
+       if (self == csqcplayer) {
+               if (self.csqcmodel_teleported) {
+                       Reset_ArcBeam();
+               }
+       }
        self.csqcmodel_effects = self.effects;
        self.csqcmodel_modelflags = self.modelflags;
        self.effects = 0;
index 74f51a54177232c3b288a494ceb055b33e4b4d24..e4376e8685325fafa7fa55ee63c9f6651af932d2 100644 (file)
@@ -81,6 +81,7 @@ ARC_SETTINGS(WEP_ADD_CVAR, WEP_ADD_PROP)
 .float beam_prev;
 .float beam_initialized;
 .float beam_bursting;
+.float beam_teleporttime;
 #endif
 #ifdef CSQC
 void Ent_ReadArcBeam(float isnew);
@@ -166,6 +167,15 @@ float W_Arc_Beam_Send(entity to, float sf)
        return TRUE;
 }
 
+void Reset_ArcBeam(entity player, vector forward)
+{
+       if (!player.arc_beam) {
+               return;
+       }
+       player.arc_beam.beam_dir = forward;
+       player.arc_beam.beam_teleporttime = time;
+}
+
 void W_Arc_Beam_Think(void)
 {
        if(self != self.owner.arc_beam)
@@ -234,6 +244,11 @@ void W_Arc_Beam_Think(void)
                WEP_CVAR(arc, beam_range)
        );
 
+       // After teleport, "lock" the beam until the teleport is confirmed.
+       if (time < self.beam_teleporttime + ANTILAG_LATENCY(self.owner)) {
+               w_shotdir = self.beam_dir;
+       }
+
        // network information: shot origin and want/aim direction
        if(self.beam_start != w_shotorg)
        {
@@ -472,6 +487,8 @@ void W_Arc_Beam_Think(void)
                }
        }
 
+       // te_explosion(trace_endpos);
+
        // if we're bursting, use burst visual effects
        new_beam_type += burst;
 
@@ -724,6 +741,17 @@ void Draw_ArcBeam_callback(vector start, vector hit, vector end)
        Draw_ArcBeam_callback_last_bottom = WarpZone_UnTransformOrigin(WarpZone_trace_transform, bottom);
 }
 
+void Reset_ArcBeam(void)
+{
+       entity e;
+       for (e = world; (e = findfloat(e, beam_usevieworigin, 1)); ) {
+               e.beam_initialized = FALSE;
+       }
+       for (e = world; (e = findfloat(e, beam_usevieworigin, 2)); ) {
+               e.beam_initialized = FALSE;
+       }
+}
+
 void Draw_ArcBeam(void)
 {
        if(!self.beam_usevieworigin)
@@ -749,44 +777,43 @@ void Draw_ArcBeam(void)
                // into a weapon system for client code. 
 
                // find where we are aiming
-               makevectors(view_angles);
+               makevectors(warpzone_save_view_angles);
+               vector forward = v_forward;
+               vector right = v_right;
+               vector up = v_up;
 
                // decide upon start position
                if(self.beam_usevieworigin == 2)
-                       { start_pos = view_origin; }
+                       { start_pos = warpzone_save_view_origin; }
                else
                        { start_pos = self.origin; }
 
                // trace forward with an estimation
                WarpZone_TraceLine(
                        start_pos,
-                       start_pos + view_forward * self.beam_range,
+                       start_pos + forward * self.beam_range,
                        MOVE_NOMONSTERS,
                        self
                );
 
                // untransform in case our trace went through a warpzone
-               vector vf, vr, vu;
-               vf = view_forward;
-               vr = view_right;
-               vu = view_up;
                vector end_pos = WarpZone_UnTransformOrigin(WarpZone_trace_transform, trace_endpos);
-               view_forward = vf;
-               view_right = vr;
-               view_up = vu;
 
                // un-adjust trueaim if shotend is too close
-               if(vlen(end_pos - view_origin) < g_trueaim_minrange)
-                       end_pos = view_origin + (view_forward * g_trueaim_minrange);
+               if(vlen(end_pos - start_pos) < g_trueaim_minrange)
+                       end_pos = start_pos + (forward * g_trueaim_minrange);
 
                // move shot origin to the actual gun muzzle origin
                vector origin_offset =
-                       view_forward * self.beam_shotorigin_x
-                       + view_right * -self.beam_shotorigin_y 
-                       + view_up * self.beam_shotorigin_z;
+                         right * -self.beam_shotorigin_y 
+                       + up * self.beam_shotorigin_z;
 
                start_pos = start_pos + origin_offset;
 
+               // Move it also forward, but only as far as possible without hitting anything. Don't poke into walls!
+               traceline(start_pos, start_pos + forward * self.beam_shotorigin_x, MOVE_NORMAL, self);
+               start_pos = trace_endpos;
+
                // calculate the aim direction now
                wantdir = normalize(end_pos - start_pos);
 
@@ -861,7 +888,7 @@ void Draw_ArcBeam(void)
                beamdir = self.beam_dir;
 
                // finally, set self.angles to the proper direction so that muzzle attachment points in proper direction
-               self.angles = fixedvectoangles2(view_forward, view_up);
+               self.angles = fixedvectoangles2(forward, up); // TODO(Samual): is this == warpzone_save_view_angles?
        }
        else
        {
@@ -962,6 +989,9 @@ void Draw_ArcBeam(void)
        // visual effects for startpoint and endpoint
        if(self.beam_hiteffect)
        {
+               // FIXME we really should do this on the server so it actually
+               // matches gameplay. What this client side stuff is doing is no
+               // more than guesswork.
                pointparticles(
                        self.beam_hiteffect,
                        last_origin,
index 8f15a4f820c428c976ca17d5871ce178d99b9b6e..943f01ae392a2ef0620923b1f7355e9c81c7c3eb 100644 (file)
@@ -80,6 +80,7 @@ void spawn_tdeath(vector v0, entity e, vector v)
 #define TELEPORT_NORMAL 1 // play sounds/effects etc
 #define TELEPORT_SIMPLE 2 // only do teleport, nothing special
 
+void Reset_ArcBeam(entity player, vector forward);
 void TeleportPlayer(entity teleporter, entity player, vector to, vector to_angles, vector to_velocity, vector telefragmin, vector telefragmax, float tflags)
 {
        entity telefragger;
@@ -117,6 +118,8 @@ void TeleportPlayer(entity teleporter, entity player, vector to, vector to_angle
        player.velocity = to_velocity;
        BITXOR_ASSIGN(player.effects, EF_TELEPORT_BIT);
 
+       makevectors(player.angles);
+       Reset_ArcBeam(player, v_forward);
        UpdateCSQCProjectileAfterTeleport(player);
 
        if(IS_PLAYER(player))
@@ -337,6 +340,8 @@ void spawnfunc_trigger_teleport (void)
 
 void WarpZone_PostTeleportPlayer_Callback(entity pl)
 {
+       makevectors(pl.angles);
+       Reset_ArcBeam(pl, v_forward);
        UpdateCSQCProjectileAfterTeleport(pl);
        // "disown" projectiles after teleport
        if(pl.owner)
index 467da632b0924e0e93644557a0ea0cbfd7ff7cb1..75cf5b1d4c8fa016a07c4cabc6426a6253a9b9da 100644 (file)
@@ -3,7 +3,7 @@
 // make sure you call makevectors first (FIXME?)
 void W_SetupShot_Dir_ProjectileSize_Range(entity ent, vector s_forward, vector mi, vector ma, float antilag, float recoil, string snd, float chan, float maxdamage, float range)
 {
-       float nudge = 1; // added to traceline target and subtracted from result
+       float nudge = 1; // added to traceline target and subtracted from result  TOOD(divVerent): do we still need this? Doesn't the engine do this now for us?
        float oldsolid;
        vector vecs, dv;
        oldsolid = ent.dphitcontentsmask;
index f55cec1d52ea16ac280a04e44f3f1f496d85f9f1..c2a110b4a14dd829fdc06618e6c669653e29074f 100644 (file)
@@ -239,8 +239,8 @@ void WarpZone_FixView()
        vector org, ang, nearclip, corner0, corner1, corner2, corner3, o;
        float f;
 
-       org = getpropertyvec(VF_ORIGIN);
-       ang = getpropertyvec(VF_ANGLES);
+       warpzone_save_view_origin = org = getpropertyvec(VF_ORIGIN);
+       warpzone_save_view_angles = ang = getpropertyvec(VF_ANGLES);
 #ifdef WORKAROUND_XON010
        float dirty;
        dirty = checkextension("DP_CSQC_ROTATEMOVES");
index 446c917dbfdb86ee4c50e20e9a29660b9fba8dd0..c0a4ca0f0a70d07caebd9fa4d86aef57db98dbc9 100644 (file)
@@ -7,3 +7,6 @@ void WarpZone_FixView();
 
 void WarpZone_Init();
 void WarpZone_Shutdown();
+
+vector warpzone_save_view_origin;
+vector warpzone_save_view_angles;