Merge pull request #1052 from nullworks/aim_improve

Fix certain client side animation desyncs
This commit is contained in:
LightCat 2020-06-09 20:48:14 +02:00 committed by GitHub
commit a806c61af8
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
6 changed files with 61 additions and 5 deletions

View File

@ -177,6 +177,7 @@ public:
offset_t m_angEyeAnglesLocal;
offset_t m_nSequence;
offset_t m_flSimulationTime;
offset_t m_flAnimTime;
offset_t m_angRotation;
offset_t m_hOwnerEntity;

View File

@ -17,6 +17,7 @@ public:
static InvalidateBoneCache_t InvalidateBoneCache = InvalidateBoneCache_t(addr);
InvalidateBoneCache(self);
}
// Currently unused, might be useful in the near future though
inline static bool Interpolate(IClientEntity *self, float time)
{
typedef bool (*fn_t)(IClientEntity *, float);

View File

@ -29,6 +29,7 @@ void NetVars::Init()
this->m_iClip2 = gNetvars.get_offset("DT_BaseCombatWeapon", "LocalWeaponData", "m_iClip2");
this->m_Collision = gNetvars.get_offset("DT_BaseEntity", "m_Collision");
this->m_flSimulationTime = gNetvars.get_offset("DT_BaseEntity", "m_flSimulationTime");
this->m_flAnimTime = gNetvars.get_offset("DT_BaseEntity", "AnimTimeMustBeFirst", "m_flAnimTime");
this->m_angRotation = gNetvars.get_offset("DT_BaseEntity", "m_angRotation");
IF_GAME(IsTF2())

View File

@ -129,12 +129,7 @@ matrix3x4_t *EntityHitboxCache::GetBones(int numbones)
{
// Reset game cache
if (!bonecache_enabled && CE_GOOD(parent_ref))
{
re::C_BaseAnimating::InvalidateBoneCache(RAW_ENT(parent_ref));
// Only use when nolerp is on as this breaks game visuals a tad
if (nolerp)
re::C_BaseAnimating::Interpolate(RAW_ENT(parent_ref), bones_setup_time);
}
// If numbones is not set, get it from some terrible and unnamed variable
if (numbones == -1)

View File

@ -10,6 +10,7 @@ set(files "${CMAKE_CURRENT_LIST_DIR}/CanPacket.cpp"
"${CMAKE_CURRENT_LIST_DIR}/nographics.cpp"
"${CMAKE_CURRENT_LIST_DIR}/others.cpp"
"${CMAKE_CURRENT_LIST_DIR}/Paint.cpp"
"${CMAKE_CURRENT_LIST_DIR}/PlayerAnimFix.cpp"
"${CMAKE_CURRENT_LIST_DIR}/PreDataUpdate.cpp"
"${CMAKE_CURRENT_LIST_DIR}/RandomInt.cpp"
"${CMAKE_CURRENT_LIST_DIR}/RunCommand.cpp"

View File

@ -0,0 +1,57 @@
#include "common.hpp"
#include "DetourHook.hpp"
namespace hacks::tf2::animfix
{
DetourHook frameadvance_detour{};
typedef float (*FrameAdvance_t)(IClientEntity *, float);
std::vector<float> previous_simtimes;
// Credits to Blackfire62 for telling me how this could be realized
float FrameAdvance_hook(IClientEntity *self, float flInterval)
{
float newInterval = flInterval;
// Check if the entity is valid
if (self && IDX_GOOD(self->entindex()) && self->entindex() > 0 && self->entindex() <= (int) previous_simtimes.size())
{
// Check if they are an alive player
CachedEntity *ent = ENTITY(self->entindex());
// Set new interval based on their simtime
if (CE_GOOD(ent) && ent->m_Type() == ENTITY_PLAYER && ent->m_bAlivePlayer())
{
float simtime = CE_FLOAT(ent, netvar.m_flSimulationTime);
// Calculate the time we need to animate by
float time_difference = simtime - previous_simtimes.at(ent->m_IDX - 1);
if (time_difference > 0.0f)
newInterval = time_difference;
previous_simtimes.at(ent->m_IDX - 1) = simtime;
// If the simtime didn't update we need to make sure that the original function also does not update
if (newInterval == 0.0f)
CE_FLOAT(ent, netvar.m_flAnimTime) = g_GlobalVars->curtime;
}
}
FrameAdvance_t original = (FrameAdvance_t) frameadvance_detour.GetOriginalFunc();
float return_value = original(self, newInterval);
frameadvance_detour.RestorePatch();
return return_value;
}
void LevelInit()
{
previous_simtimes.clear();
previous_simtimes.resize(g_IEngine->GetMaxClients());
}
static InitRoutine init([]() {
static auto FrameAdvance_signature = gSignatures.GetClientSignature("55 89 E5 57 56 53 83 EC 4C 8B 5D ? 80 BB ? ? ? ? 00 0F 85 ? ? ? ? 8B B3");
frameadvance_detour.Init(FrameAdvance_signature, (void *) FrameAdvance_hook);
EC::Register(EC::LevelInit, LevelInit, "levelinit_animfix");
LevelInit();
EC::Register(
EC::Shutdown, []() { frameadvance_detour.Shutdown(); }, "shutdown_animfix");
});
} // namespace hacks::tf2::animfix