mirror of
https://github.com/DrBeef/Raze.git
synced 2025-03-30 20:51:22 +00:00
- Move InputScale()
out of inputstate.cpp and into i_time.cpp
as I_GetInputFrac()
to make it available to GZDoom for potential future requirements.
* As part of this, feed the output of `I_GetInputFrac()` to `gi->GetInput()` instead of having each game's virtual override calling it locally.
This commit is contained in:
parent
08bc31e6e2
commit
e491d15ff9
20 changed files with 63 additions and 60 deletions
|
@ -46,6 +46,7 @@
|
|||
static uint64_t FirstFrameStartTime;
|
||||
static uint64_t CurrentFrameStartTime;
|
||||
static uint64_t FreezeTime;
|
||||
static double lastinputtime;
|
||||
int GameTicRate = 35; // make sure it is not 0, even if the client doesn't set it.
|
||||
|
||||
double TimeScale = 1.0;
|
||||
|
@ -195,3 +196,39 @@ void I_ResetFrameTime()
|
|||
I_SetFrameTime();
|
||||
FirstFrameStartTime += (CurrentFrameStartTime - ft);
|
||||
}
|
||||
|
||||
double I_GetInputFrac(bool const synchronised, double const ticrate)
|
||||
{
|
||||
if (!synchronised)
|
||||
{
|
||||
const double max = 1000. / ticrate;
|
||||
const double now = I_msTimeF();
|
||||
const double elapsedInputTicks = std::min(now - lastinputtime, max);
|
||||
lastinputtime = now;
|
||||
|
||||
if (elapsedInputTicks < max)
|
||||
{
|
||||
// Calculate an amplification to apply to the result before returning,
|
||||
// factoring in the game's ticrate and the value of the result.
|
||||
// This rectifies a deviation of 100+ ms or more depending on the length
|
||||
// of the operation to be within 1-2 ms of synchronised input
|
||||
// from 60 fps to at least 1000 fps at ticrates of 30 and 40 Hz.
|
||||
const double result = elapsedInputTicks * ticrate / 1000.;
|
||||
return result * (1. + 0.35 * (1. - ticrate / 50.) * (1. - result));
|
||||
}
|
||||
else
|
||||
{
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
|
||||
void I_ResetInputTime()
|
||||
{
|
||||
// Reset lastinputtime to current time.
|
||||
lastinputtime = I_msTimeF();
|
||||
}
|
||||
|
|
|
@ -38,3 +38,9 @@ uint64_t I_nsTime();
|
|||
|
||||
// Reset the timer after a lengthy operation
|
||||
void I_ResetFrameTime();
|
||||
|
||||
// Return a decimal fraction to scale input operations at framerate
|
||||
double I_GetInputFrac(bool const synchronised, double const ticrate = GameTicRate);
|
||||
|
||||
// Reset the last input check to after a lengthy operation
|
||||
void I_ResetInputTime();
|
||||
|
|
|
@ -1983,6 +1983,7 @@ void Net_SkipCommand (int cmd, uint8_t **stream)
|
|||
void Net_ClearFifo(void)
|
||||
{
|
||||
I_SetFrameTime();
|
||||
I_ResetInputTime();
|
||||
gametime = I_GetTime();
|
||||
}
|
||||
|
||||
|
|
|
@ -1024,7 +1024,6 @@ int RunGame()
|
|||
playername = userConfig.CommandName;
|
||||
}
|
||||
GameTicRate = 30;
|
||||
InputScalePercentage = 0.14125;
|
||||
CheckUserMap();
|
||||
|
||||
palindexmap[0] = 255;
|
||||
|
|
|
@ -89,7 +89,6 @@ CVARD(Bool, cl_bloodqavinterp, true, CVAR_ARCHIVE, "enable/disable Blood's QAV i
|
|||
CVARD(Bool, cl_bloodweapinterp, false, CVAR_ARCHIVE, "enable/disable Blood's weapon interpolation. Depends on 'cl_bloodqavinterp'")
|
||||
CVARD(Bool, cl_bloodoldweapbalance, false, CVAR_ARCHIVE, "enable/disable legacy 1.0 weapon handling for Blood")
|
||||
CVARD(Bool, cl_loadingscreens, true, CVAR_ARCHIVE, "enable/disable loading screens for games")
|
||||
CVARD(Bool, cl_preciseinputscaling, true, CVAR_ARCHIVE, "enable/disable precise scaling of unsynchronised input fraction")
|
||||
|
||||
|
||||
CUSTOM_CVARD(Int, cl_autoaim, 1, CVAR_ARCHIVE|CVAR_USERINFO, "enable/disable weapon autoaim")
|
||||
|
|
|
@ -34,7 +34,6 @@ EXTERN_CVAR(Bool, cl_bloodqavinterp)
|
|||
EXTERN_CVAR(Bool, cl_bloodweapinterp)
|
||||
EXTERN_CVAR(Bool, cl_bloodoldweapbalance)
|
||||
EXTERN_CVAR(Bool, cl_loadingscreens)
|
||||
EXTERN_CVAR(Bool, cl_preciseinputscaling)
|
||||
|
||||
EXTERN_CVAR(Bool, demorec_seeds_cvar)
|
||||
EXTERN_CVAR(Bool, demoplay_diffs)
|
||||
|
|
|
@ -188,16 +188,14 @@ void processMovement(InputPacket* const currInput, InputPacket* const inputBuffe
|
|||
|
||||
if (turnleft || turnright)
|
||||
{
|
||||
double const turnamount = hidspeed * turnscale;
|
||||
double const preambleturn = turnamount * (double(PREAMBLEBASE) / double(NORMALTURNBASE));
|
||||
|
||||
updateTurnHeldAmt(scaleAdjust);
|
||||
float const turnamount = float(scaleAdjust * hidspeed * turnscale * (isTurboTurnTime() ? 1. : double(PREAMBLEBASE) / double(NORMALTURNBASE)));
|
||||
|
||||
if (turnleft)
|
||||
currInput->avel -= float(scaleAdjust * (isTurboTurnTime() ? turnamount : preambleturn));
|
||||
currInput->avel -= turnamount;
|
||||
|
||||
if (turnright)
|
||||
currInput->avel += float(scaleAdjust * (isTurboTurnTime() ? turnamount : preambleturn));
|
||||
currInput->avel += turnamount;
|
||||
}
|
||||
else
|
||||
{
|
||||
|
|
|
@ -89,7 +89,7 @@ struct GameInterface
|
|||
virtual FString GetCoordString() { return "'stat coord' not implemented"; }
|
||||
virtual void ExitFromMenu() { throw CExitEvent(0); }
|
||||
virtual ReservedSpace GetReservedScreenSpace(int viewsize) { return { 0, 0 }; }
|
||||
virtual void GetInput(InputPacket* packet, ControlInfo* const hidInput) {}
|
||||
virtual void GetInput(ControlInfo* const hidInput, double const scaleAdjust, InputPacket* packet = nullptr) {}
|
||||
virtual void UpdateSounds() {}
|
||||
virtual void ErrorCleanup() {}
|
||||
virtual void Startup() {}
|
||||
|
|
|
@ -48,10 +48,8 @@
|
|||
static int WeaponToSend = 0;
|
||||
ESyncBits ActionsToSend = 0;
|
||||
static int dpad_lock = 0;
|
||||
double InputScalePercentage = 0;
|
||||
bool sendPause;
|
||||
bool crouch_toggle;
|
||||
static double lastCheck;
|
||||
|
||||
CVAR(Float, m_pitch, 1.f, CVAR_GLOBALCONFIG | CVAR_ARCHIVE) // Mouse speeds
|
||||
CVAR(Float, m_yaw, 1.f, CVAR_GLOBALCONFIG | CVAR_ARCHIVE)
|
||||
|
@ -122,7 +120,6 @@ void InputState::ClearAllInput()
|
|||
AnyKeyStatus = false;
|
||||
WeaponToSend = 0;
|
||||
dpad_lock = 0;
|
||||
lastCheck = 0;
|
||||
|
||||
if (gamestate != GS_LEVEL)
|
||||
{
|
||||
|
@ -471,30 +468,5 @@ void ApplyGlobalInput(InputPacket& input, ControlInfo* hidInput, bool const crou
|
|||
|
||||
if (buttonMap.ButtonDown(gamefunc_Look_Right))
|
||||
input.actions |= SB_LOOK_RIGHT;
|
||||
|
||||
}
|
||||
|
||||
double InputScale()
|
||||
{
|
||||
if (!SyncInput())
|
||||
{
|
||||
const double max = 1000. / GameTicRate;
|
||||
const double now = I_msTimeF();
|
||||
const double elapsedInputTicks = lastCheck > 0 ? min(now - lastCheck, max) : 1.;
|
||||
lastCheck = now;
|
||||
if (elapsedInputTicks == max) return 1;
|
||||
|
||||
// Calculate a scale increase of the percentage InputScalePercentage is set as to correct an
|
||||
// inherent drift in this function that progressively causes the actions that depend
|
||||
// on this fractional scale to increase by over 100 ms as the framerate increases.
|
||||
// This isn't pretty, but it's accurate to within 1-2 ms from 60 fps to at least 1000 fps.
|
||||
const double result = elapsedInputTicks * GameTicRate / 1000.;
|
||||
const double scaler = cl_preciseinputscaling ? 1. + InputScalePercentage * (1. - result) : 1.;
|
||||
return result * scaler;
|
||||
}
|
||||
else
|
||||
{
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -104,9 +104,7 @@ enum GameFunction_t
|
|||
void SetupGameButtons();
|
||||
void ApplyGlobalInput(InputPacket& input, ControlInfo* const hidInput, bool const crouchable = true, bool const disableToggle = false);
|
||||
extern ESyncBits ActionsToSend;
|
||||
double InputScale();
|
||||
extern bool gamesetinput;
|
||||
extern double InputScalePercentage;
|
||||
|
||||
inline bool SyncInput()
|
||||
{
|
||||
|
|
|
@ -133,7 +133,7 @@ void G_BuildTiccmd(ticcmd_t* cmd)
|
|||
cmd->ucmd = {};
|
||||
I_GetEvent();
|
||||
auto input = CONTROL_GetInput();
|
||||
gi->GetInput(&cmd->ucmd, &input);
|
||||
gi->GetInput(&input, I_GetInputFrac(SyncInput()), &cmd->ucmd);
|
||||
cmd->consistency = consistency[myconnectindex][(maketic / ticdup) % BACKUPTICS];
|
||||
}
|
||||
|
||||
|
@ -576,7 +576,7 @@ void TryRunTics (void)
|
|||
{
|
||||
I_GetEvent();
|
||||
auto input = CONTROL_GetInput();
|
||||
gi->GetInput(nullptr, &input);
|
||||
gi->GetInput(&input, I_GetInputFrac(SyncInput()));
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
|
|
@ -124,7 +124,7 @@ struct GameInterface : public ::GameInterface
|
|||
FString GetCoordString() override;
|
||||
ReservedSpace GetReservedScreenSpace(int viewsize) override;
|
||||
void UpdateSounds() override;
|
||||
void GetInput(InputPacket* packet, ControlInfo* const hidInput) override;
|
||||
void GetInput(ControlInfo* const hidInput, double const scaleAdjust, InputPacket* packet = nullptr) override;
|
||||
void Ticker() override;
|
||||
void DrawBackground() override;
|
||||
void Startup() override;
|
||||
|
|
|
@ -37,7 +37,7 @@ static InputPacket gInput;
|
|||
void UpdatePlayerSpriteAngle(PLAYER* pPlayer);
|
||||
void doslopetilting(PLAYER* pPlayer, double const scaleAdjust);
|
||||
|
||||
void GameInterface::GetInput(InputPacket* packet, ControlInfo* const hidInput)
|
||||
void GameInterface::GetInput(ControlInfo* const hidInput, double const scaleAdjust, InputPacket* packet)
|
||||
{
|
||||
if (paused || M_Active())
|
||||
{
|
||||
|
@ -46,7 +46,6 @@ void GameInterface::GetInput(InputPacket* packet, ControlInfo* const hidInput)
|
|||
}
|
||||
|
||||
PLAYER* pPlayer = &gPlayer[myconnectindex];
|
||||
double const scaleAdjust = InputScale();
|
||||
InputPacket input {};
|
||||
|
||||
ApplyGlobalInput(gInput, hidInput);
|
||||
|
|
|
@ -43,7 +43,7 @@ struct GameInterface : public ::GameInterface
|
|||
void ExitFromMenu() override;
|
||||
ReservedSpace GetReservedScreenSpace(int viewsize) override;
|
||||
void DrawPlayerSprite(const DVector2& origin, bool onteam) override;
|
||||
void GetInput(InputPacket* packet, ControlInfo* const hidInput) override;
|
||||
void GetInput(ControlInfo* const hidInput, double const scaleAdjust, InputPacket* packet = nullptr) override;
|
||||
void UpdateSounds() override;
|
||||
void Startup() override;
|
||||
void DrawBackground() override;
|
||||
|
|
|
@ -800,7 +800,7 @@ static void FinalizeInput(player_struct *p, InputPacket& input)
|
|||
//
|
||||
//---------------------------------------------------------------------------
|
||||
|
||||
void GameInterface::GetInput(InputPacket* packet, ControlInfo* const hidInput)
|
||||
void GameInterface::GetInput(ControlInfo* const hidInput, double const scaleAdjust, InputPacket* packet)
|
||||
{
|
||||
if (paused || gamestate != GS_LEVEL)
|
||||
{
|
||||
|
@ -809,13 +809,11 @@ void GameInterface::GetInput(InputPacket* packet, ControlInfo* const hidInput)
|
|||
}
|
||||
|
||||
auto const p = &ps[myconnectindex];
|
||||
bool const rrraVehicle = isRRRA() && (p->OnMotorcycle || p->OnBoat);
|
||||
double const scaleAdjust = InputScale();
|
||||
InputPacket input{};
|
||||
|
||||
processInputBits(p, hidInput);
|
||||
|
||||
if (rrraVehicle)
|
||||
if (isRRRA() && (p->OnMotorcycle || p->OnBoat))
|
||||
{
|
||||
processVehicleInput(p, hidInput, input, scaleAdjust);
|
||||
}
|
||||
|
|
|
@ -231,7 +231,7 @@ struct GameInterface : public ::GameInterface
|
|||
void Ticker() override;
|
||||
void DrawBackground() override;
|
||||
void Render() override;
|
||||
void GetInput(InputPacket* packet, ControlInfo* const hidInput) override;
|
||||
void GetInput(ControlInfo* const hidInput, double const scaleAdjust, InputPacket* packet = nullptr) override;
|
||||
void Startup() override;
|
||||
const char* GenericCheat(int player, int cheat) override;
|
||||
void NewGame(MapRecord *map, int skill, bool) override;
|
||||
|
|
|
@ -34,7 +34,7 @@ void ClearSpaceBar(short nPlayer)
|
|||
}
|
||||
|
||||
|
||||
void GameInterface::GetInput(InputPacket* packet, ControlInfo* const hidInput)
|
||||
void GameInterface::GetInput(ControlInfo* const hidInput, double const scaleAdjust, InputPacket* packet)
|
||||
{
|
||||
if (paused || M_Active())
|
||||
{
|
||||
|
@ -50,17 +50,16 @@ void GameInterface::GetInput(InputPacket* packet, ControlInfo* const hidInput)
|
|||
}
|
||||
|
||||
Player* pPlayer = &PlayerList[nLocalPlayer];
|
||||
double const scaleAdjust = InputScale();
|
||||
InputPacket input {};
|
||||
|
||||
if (PlayerList[nLocalPlayer].nHealth == 0)
|
||||
if (PlayerList[nLocalPlayer].nHealth != 0)
|
||||
{
|
||||
lPlayerYVel = 0;
|
||||
lPlayerXVel = 0;
|
||||
processMovement(&input, &localInput, hidInput, scaleAdjust);
|
||||
}
|
||||
else
|
||||
{
|
||||
processMovement(&input, &localInput, hidInput, scaleAdjust);
|
||||
lPlayerYVel = 0;
|
||||
lPlayerXVel = 0;
|
||||
}
|
||||
|
||||
if (!SyncInput())
|
||||
|
|
|
@ -179,7 +179,6 @@ void GameInterface::LoadGameTextures()
|
|||
void GameInterface::app_init()
|
||||
{
|
||||
GameTicRate = 40;
|
||||
InputScalePercentage = 0.070625;
|
||||
InitCheats();
|
||||
automapping = 1;
|
||||
|
||||
|
|
|
@ -2191,7 +2191,7 @@ struct GameInterface : public ::GameInterface
|
|||
ReservedSpace GetReservedScreenSpace(int viewsize) override;
|
||||
void UpdateSounds() override;
|
||||
void ErrorCleanup() override;
|
||||
void GetInput(InputPacket* input, ControlInfo* const hidInput) override;
|
||||
void GetInput(ControlInfo* const hidInput, double const scaleAdjust, InputPacket* input = nullptr) override;
|
||||
void DrawBackground(void) override;
|
||||
void Ticker(void) override;
|
||||
void Render() override;
|
||||
|
|
|
@ -160,7 +160,7 @@ static void processWeapon(PLAYERp const pp)
|
|||
}
|
||||
}
|
||||
|
||||
void GameInterface::GetInput(InputPacket *packet, ControlInfo* const hidInput)
|
||||
void GameInterface::GetInput(ControlInfo* const hidInput, double const scaleAdjust, InputPacket *packet)
|
||||
{
|
||||
PLAYERp pp = &Player[myconnectindex];
|
||||
|
||||
|
@ -170,7 +170,6 @@ void GameInterface::GetInput(InputPacket *packet, ControlInfo* const hidInput)
|
|||
return;
|
||||
}
|
||||
|
||||
double const scaleAdjust = InputScale();
|
||||
InputPacket input {};
|
||||
|
||||
ApplyGlobalInput(loc, hidInput);
|
||||
|
|
Loading…
Reference in a new issue