This is a start to lag compensate the local player.

Normally,
this would be needed to be inside StartLagCompensation,
but for now, this is enough.
This commit is contained in:
unknown 2024-08-28 00:48:05 +02:00
parent 22cfdaabc9
commit 956d26bcb3
9 changed files with 70 additions and 36 deletions

View file

@ -2655,9 +2655,18 @@ void _Host_RunFrame_Input( float accumulated_extra_samples, bool bFinalTick )
g_HostTimes.EndFrameSegment( FRAME_SEGMENT_CMD_EXECUTE );
// TODO_ENHANCED: HACKHACK:
// the player is one frame in late because interpolation amount is calculated after CreateMove
// Just in case, we set it there too to interpolate with correct data!
float old_interpolation_amount = g_ClientGlobalVariables.interpolation_amount;
g_ClientGlobalVariables.interpolation_amount = cl.m_tickRemainder / host_state.interval_per_tick;
// Send any current movement commands to server and flush reliable buffer even if not moving yet.
CL_Move( accumulated_extra_samples, bFinalTick );
g_ClientGlobalVariables.interpolation_amount = old_interpolation_amount;
#endif
g_HostTimes.EndFrameSegment( FRAME_SEGMENT_INPUT );

View file

@ -649,6 +649,7 @@ public:
float m_fLastUpdateServerTime;
int m_nLastUpdateTickBase;
int m_nLastUpdateServerTickCount;
Vector m_vecPreviousShootPosition;
};
EXTERN_RECV_TABLE(DT_BasePlayer);

View file

@ -15,6 +15,8 @@
#include <cstdio>
#include "bone_setup.h"
#include "convar.h"
#include "imovehelper.h"
#include "ipredictionsystem.h"
#include "studio.h"
#include "util_shared.h"
#include "c_baseplayer.h"
@ -1330,16 +1332,7 @@ void CInput::CreateMove ( int sequence_number, float input_sample_frametime, boo
}
#endif
C_BasePlayer* pPlayer = C_BasePlayer::GetLocalPlayer();
if (pPlayer)
{
cmd->interpolated_shoot_position = pPlayer->Weapon_ShootPosition();
}
else
{
cmd->interpolated_shoot_position.Init();
}
cmd->interpolated_amount = gpGlobals->interpolation_amount;
pVerified->m_cmd = *cmd;
pVerified->m_crc = cmd->GetChecksum();

View file

@ -769,6 +769,8 @@ void CPrediction::StartCommand( C_BasePlayer *player, CUserCmd *cmd )
#if !defined( NO_ENTITY_PREDICTION )
VPROF( "CPrediction::StartCommand" );
player->m_vecPreviousShootPosition = player->Weapon_ShootPosition();
CPredictableId::ResetInstanceCounters();
player->m_pCurrentCommand = cmd;
@ -919,12 +921,6 @@ void CPrediction::RunCommand( C_BasePlayer *player, CUserCmd *ucmd, IMoveHelper
player->SetLocalViewAngles( ucmd->viewangles );
}
moveHelper->ProcessImpacts();
RunPostThink( player );
ServiceEventQueue( player );
// TODO
// TODO: Check for impulse predicted?
@ -994,6 +990,12 @@ void CPrediction::RunCommand( C_BasePlayer *player, CUserCmd *ucmd, IMoveHelper
FinishMove( player, ucmd, g_pMoveData );
moveHelper->ProcessImpacts();
RunPostThink( player );
ServiceEventQueue( player );
g_pGameMovement->FinishTrackPredictionErrors( player );
FinishCommand( player );

View file

@ -1211,6 +1211,7 @@ private:
public:
virtual unsigned int PlayerSolidMask( bool brushOnly = false ) const; // returns the solid mask for the given player, so bots can have a more-restrictive set
Vector m_vecPreviousShootPosition;
};
typedef CHandle<CBasePlayer> CBasePlayerHandle;

View file

@ -48,6 +48,8 @@ void CPlayerMove::StartCommand( CBasePlayer *player, CUserCmd *cmd )
{
VPROF( "CPlayerMove::StartCommand" );
player->m_vecPreviousShootPosition = player->Weapon_ShootPosition();
#if !defined( NO_ENTITY_PREDICTION )
CPredictableId::ResetInstanceCounters();
#endif
@ -353,15 +355,6 @@ void CPlayerMove::RunCommand ( CBasePlayer *player, CUserCmd *ucmd, IMoveHelper
ucmd->viewangles = vec3_angle;
}
// Let server invoke any needed impact functions
VPROF_SCOPE_BEGIN( "moveHelper->ProcessImpacts" );
moveHelper->ProcessImpacts();
VPROF_SCOPE_END();
RunPostThink( player );
ServiceEventQueue( player );
// Add and subtract buttons we're forcing on the player
ucmd->buttons |= player->m_afButtonForced;
ucmd->buttons &= ~player->m_afButtonDisabled;
@ -457,6 +450,15 @@ void CPlayerMove::RunCommand ( CBasePlayer *player, CUserCmd *ucmd, IMoveHelper
// Copy output
FinishMove( player, ucmd, g_pMoveData );
// Let server invoke any needed impact functions
VPROF_SCOPE_BEGIN( "moveHelper->ProcessImpacts" );
moveHelper->ProcessImpacts();
VPROF_SCOPE_END();
RunPostThink( player );
ServiceEventQueue( player );
g_pGameMovement->FinishTrackPredictionErrors( player );
FinishCommand( player );

View file

@ -7,6 +7,8 @@
#include "cbase.h"
#include "fx_cs_shared.h"
#include "convar.h"
#include "mathlib/vector.h"
#include "usercmd.h"
#include "weapon_csbase.h"
#ifndef CLIENT_DLL
@ -135,19 +137,26 @@ void FX_FireBullets(
CCSPlayer *pPlayer = ToCSPlayer( UTIL_PlayerByIndex( iPlayerIndex) );
#endif
// TODO_ENHANCED:
// Check if interpolated_shoot_position is within interpolation bounds! (between old shoot pos and new)
// This is to check for cheaters abusing the shooting position.
// DevMsg("original shoot pos: %f %f %f\n", vHookedOrigin.x, vHookedOrigin.y, vHookedOrigin.z );
CUserCmd* playerCmd = NULL;
if (pPlayer)
{
#ifdef CLIENT_DLL
if (pPlayer->m_pCurrentCommand) { vHookedOrigin = pPlayer->m_pCurrentCommand->interpolated_shoot_position; }
playerCmd = pPlayer->m_pCurrentCommand;
#else
if (pPlayer->GetCurrentCommand()) { vHookedOrigin = pPlayer->GetCurrentCommand()->interpolated_shoot_position; }
playerCmd = pPlayer->GetCurrentCommand();
#endif
}
if (playerCmd)
{
vHookedOrigin = VectorLerp(pPlayer->m_vecPreviousShootPosition, vOrigin, playerCmd->interpolated_amount);
}
// DevMsg("new shoot pos: %f %f %f, has command: %s\n", vHookedOrigin.x, vHookedOrigin.y, vHookedOrigin.z, playerCmd ? "true" : "false" );
const char * weaponAlias = WeaponIDToAlias( iWeaponID );
if ( !weaponAlias )

View file

@ -339,7 +339,24 @@ bool CKnife::SwingOrStab( bool bStab )
float fRange = bStab ? 32 : 48; // knife range
Vector vForward; AngleVectors( pPlayer->EyeAngles(), &vForward );
Vector vecSrc = pPlayer->Weapon_ShootPosition();
CUserCmd* playerCmd = NULL;
if (pPlayer)
{
#ifdef CLIENT_DLL
playerCmd = pPlayer->m_pCurrentCommand;
#else
playerCmd = pPlayer->GetCurrentCommand();
#endif
}
if (playerCmd)
{
vecSrc = VectorLerp(pPlayer->m_vecPreviousShootPosition, vecSrc, playerCmd->interpolated_amount);
}
Vector vecEnd = vecSrc + vForward * fRange;
trace_t tr;

View file

@ -106,7 +106,7 @@ public:
entitygroundcontact.RemoveAll();
#endif
interpolated_shoot_position.Init();
interpolated_amount = 0.0f;
}
CUserCmd& operator =( const CUserCmd& src )
@ -139,7 +139,7 @@ public:
entitygroundcontact = src.entitygroundcontact;
#endif
interpolated_shoot_position = src.interpolated_shoot_position;
interpolated_amount = src.interpolated_amount;
return *this;
}
@ -168,7 +168,7 @@ public:
CRC32_ProcessBuffer(&crc, &mousedy, sizeof(mousedy));
CRC32_ProcessBuffer(&crc, simulationdata, sizeof(simulationdata));
CRC32_ProcessBuffer(&crc, &debug_hitboxes, sizeof(debug_hitboxes));
CRC32_ProcessBuffer( &crc, &interpolated_shoot_position, sizeof(interpolated_shoot_position));
CRC32_ProcessBuffer(&crc, &interpolated_amount, sizeof(interpolated_amount));
CRC32_Final( &crc );
return crc;
@ -184,7 +184,7 @@ public:
buttons = 0;
impulse = 0;
debug_hitboxes = DEBUG_HITBOXES_OFF;
interpolated_shoot_position.Init();
interpolated_amount = 0.0f;
}
// For matching server and client commands for debugging
@ -232,7 +232,7 @@ public:
uint8 debug_hitboxes;
// TODO_ENHANCED: check README_ENHANCED in host.cpp!
Vector interpolated_shoot_position;
float interpolated_amount;
// Back channel to communicate IK state
#if defined( HL2_DLL ) || defined( HL2_CLIENT_DLL )