summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorTony J. White <tjw@tjw.org>2006-12-09 05:12:31 +0000
committerTony J. White <tjw@tjw.org>2006-12-09 05:12:31 +0000
commit74db521aeb93d7e706d9e3745dd3462e8d5f90eb (patch)
treefa6d52f0722bb48fa57612f9bf91aee5c81c0721
parent3b9e1e27a21cef8b3b1fa0a14c47299622e29609 (diff)
* (bug 2937) adds cg_projectileNudge. This is originally from Neil Toronto's
unlagged project. kevlarman added automatic latency detection so the nudge time doesn't have to be set manually. Defaults to 1 (on).
-rw-r--r--src/cgame/cg_draw.c32
-rw-r--r--src/cgame/cg_ents.c31
-rw-r--r--src/cgame/cg_local.h2
-rw-r--r--src/cgame/cg_main.c2
-rw-r--r--src/qcommon/q_shared.h3
5 files changed, 55 insertions, 15 deletions
diff --git a/src/cgame/cg_draw.c b/src/cgame/cg_draw.c
index 7aa724b9..ed7ba1d8 100644
--- a/src/cgame/cg_draw.c
+++ b/src/cgame/cg_draw.c
@@ -2030,8 +2030,13 @@ the number of snapshots that were dropped before it.
Pass NULL for a dropped packet.
==============
*/
+#define PING_FRAMES 40
void CG_AddLagometerSnapshotInfo( snapshot_t *snap )
{
+ static int previousPings[ PING_FRAMES ];
+ static int index;
+ int i;
+
// dropped packet
if( !snap )
{
@@ -2044,6 +2049,19 @@ void CG_AddLagometerSnapshotInfo( snapshot_t *snap )
lagometer.snapshotSamples[ lagometer.snapshotCount & ( LAG_SAMPLES - 1 ) ] = snap->ping;
lagometer.snapshotFlags[ lagometer.snapshotCount & ( LAG_SAMPLES - 1 ) ] = snap->snapFlags;
lagometer.snapshotCount++;
+
+ // now used by cg_projectileNudge, so we need to move this where it will get
+ // called even if cg_lagometer = 0
+ cg.ping = 0;
+ previousPings[ index++ ] = cg.snap->ping;
+ index = index % PING_FRAMES;
+
+ for( i = 0; i < PING_FRAMES; i++ )
+ {
+ cg.ping += previousPings[ i ];
+ }
+
+ cg.ping /= PING_FRAMES;
}
/*
@@ -2088,7 +2106,6 @@ static void CG_DrawDisconnect( void )
#define MAX_LAGOMETER_PING 900
#define MAX_LAGOMETER_RANGE 300
-#define PING_FRAMES 40
/*
==============
@@ -2230,20 +2247,9 @@ static void CG_DrawLagometer( rectDef_t *rect, float text_x, float text_y,
CG_Text_Paint( ax, ay, 0.5, white, "snc", 0, 0, ITEM_TEXTSTYLE_NORMAL );
else
{
- static int previousPings[ PING_FRAMES ];
- static int index;
- int i, ping = 0;
char *s;
- previousPings[ index++ ] = cg.snap->ping;
- index = index % PING_FRAMES;
-
- for( i = 0; i < PING_FRAMES; i++ )
- ping += previousPings[ i ];
-
- ping /= PING_FRAMES;
-
- s = va( "%d", ping );
+ s = va( "%d", cg.ping );
ax = rect->x + ( rect->w / 2.0f ) - ( CG_Text_Width( s, scale, 0 ) / 2.0f ) + text_x;
ay = rect->y + ( rect->h / 2.0f ) + ( CG_Text_Height( s, scale, 0 ) / 2.0f ) + text_y;
diff --git a/src/cgame/cg_ents.c b/src/cgame/cg_ents.c
index 02972a51..2d2e8089 100644
--- a/src/cgame/cg_ents.c
+++ b/src/cgame/cg_ents.c
@@ -918,6 +918,9 @@ CG_CalcEntityLerpPositions
*/
static void CG_CalcEntityLerpPositions( centity_t *cent )
{
+ // this will be set to how far forward projectiles will be extrapolated
+ int timeshift = 0;
+
// if this player does not want to see extrapolated players
if( !cg_smoothClients.integer )
{
@@ -944,9 +947,33 @@ static void CG_CalcEntityLerpPositions( centity_t *cent )
return;
}
+ if( cg_projectileNudge.integer > 0 &&
+ cent->currentState.eType == ET_MISSILE &&
+ !( cg.snap->ps.pm_flags & PMF_FOLLOW ) )
+ {
+ timeshift = cg.ping;
+ }
+
// just use the current frame and evaluate as best we can
- BG_EvaluateTrajectory( &cent->currentState.pos, cg.time, cent->lerpOrigin );
- BG_EvaluateTrajectory( &cent->currentState.apos, cg.time, cent->lerpAngles );
+ BG_EvaluateTrajectory( &cent->currentState.pos,
+ ( cg.time + timeshift ), cent->lerpOrigin );
+ BG_EvaluateTrajectory( &cent->currentState.apos,
+ ( cg.time + timeshift ), cent->lerpAngles );
+
+ if( timeshift )
+ {
+ trace_t tr;
+ vec3_t lastOrigin;
+
+ BG_EvaluateTrajectory( &cent->currentState.pos, cg.time, lastOrigin );
+
+ CG_Trace( &tr, lastOrigin, vec3_origin, vec3_origin, cent->lerpOrigin,
+ cent->currentState.number, MASK_SHOT );
+
+ // don't let the projectile go through the floor
+ if( tr.fraction < 1.0f )
+ VectorLerp( tr.fraction, lastOrigin, cent->lerpOrigin, cent->lerpOrigin );
+ }
// adjust for riding a mover if it wasn't rolled into the predicted
// player state
diff --git a/src/cgame/cg_local.h b/src/cgame/cg_local.h
index 882a348d..27d89d24 100644
--- a/src/cgame/cg_local.h
+++ b/src/cgame/cg_local.h
@@ -1135,6 +1135,7 @@ typedef struct
int lastServerTime;
playerState_t savedPmoveStates[ NUM_SAVED_STATES ];
int stateHead, stateTail;
+ int ping;
} cg_t;
@@ -1508,6 +1509,7 @@ extern vmCvar_t ui_humanTeamVoteActive;
extern vmCvar_t cg_debugRandom;
extern vmCvar_t cg_optimizePrediction;
+extern vmCvar_t cg_projectileNudge;
//
// cg_main.c
diff --git a/src/cgame/cg_main.c b/src/cgame/cg_main.c
index c3d52527..926ccd88 100644
--- a/src/cgame/cg_main.c
+++ b/src/cgame/cg_main.c
@@ -238,6 +238,7 @@ vmCvar_t ui_humanTeamVoteActive;
vmCvar_t cg_debugRandom;
vmCvar_t cg_optimizePrediction;
+vmCvar_t cg_projectileNudge;
typedef struct
@@ -354,6 +355,7 @@ static cvarTable_t cvarTable[ ] =
{ &cg_debugRandom, "cg_debugRandom", "0", 0 },
{ &cg_optimizePrediction, "cg_optimizePrediction", "1", CVAR_ARCHIVE },
+ { &cg_projectileNudge, "cg_projectileNudge", "1", CVAR_ARCHIVE },
// the following variables are created in other parts of the system,
// but we also reference them here
diff --git a/src/qcommon/q_shared.h b/src/qcommon/q_shared.h
index f7a8b43e..3f0ae9a2 100644
--- a/src/qcommon/q_shared.h
+++ b/src/qcommon/q_shared.h
@@ -426,6 +426,9 @@ void ByteToDir( int b, vec3_t dir );
#define VectorCopy(a,b) ((b)[0]=(a)[0],(b)[1]=(a)[1],(b)[2]=(a)[2])
#define VectorScale(v, s, o) ((o)[0]=(v)[0]*(s),(o)[1]=(v)[1]*(s),(o)[2]=(v)[2]*(s))
#define VectorMA(v, s, b, o) ((o)[0]=(v)[0]+(b)[0]*(s),(o)[1]=(v)[1]+(b)[1]*(s),(o)[2]=(v)[2]+(b)[2]*(s))
+#define VectorLerp( f, s, e, r ) ((r)[0]=(s)[0]+(f)*((e)[0]-(s)[0]),\
+ (r)[1]=(s)[1]+(f)*((e)[1]-(s)[1]),\
+ (r)[2]=(s)[2]+(f)*((e)[2]-(s)[2]))
#else