aboutsummaryrefslogtreecommitdiff
path: root/NorthstarDLL/latencyflex.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'NorthstarDLL/latencyflex.cpp')
-rw-r--r--NorthstarDLL/latencyflex.cpp76
1 files changed, 76 insertions, 0 deletions
diff --git a/NorthstarDLL/latencyflex.cpp b/NorthstarDLL/latencyflex.cpp
new file mode 100644
index 00000000..3e2cecd7
--- /dev/null
+++ b/NorthstarDLL/latencyflex.cpp
@@ -0,0 +1,76 @@
+#include "pch.h"
+#include "latencyflex.h"
+#include "hookutils.h"
+#include "convar.h"
+
+typedef void (*OnRenderStartType)();
+OnRenderStartType OnRenderStart;
+
+ConVar* Cvar_r_latencyflex;
+
+HMODULE m_lfxModule {};
+typedef void (*PFN_lfx_WaitAndBeginFrame)();
+PFN_lfx_WaitAndBeginFrame m_lfx_WaitAndBeginFrame {};
+
+void OnRenderStartHook()
+{
+ // Sleep before next frame as needed to reduce latency.
+ if (Cvar_r_latencyflex->GetInt())
+ {
+ if (m_lfx_WaitAndBeginFrame)
+ {
+ m_lfx_WaitAndBeginFrame();
+ }
+ }
+
+ OnRenderStart();
+}
+
+void InitialiseLatencyFleX(HMODULE baseAddress)
+{
+ // Connect to the LatencyFleX service
+ // LatencyFleX is an open source vendor agnostic replacement for Nvidia Reflex input latency reduction technology.
+ // https://ishitatsuyuki.github.io/post/latencyflex/
+ const auto lfxModuleName = "latencyflex_layer.dll";
+ const auto lfxModuleNameFallback = "latencyflex_wine.dll";
+ auto useFallbackEntrypoints = false;
+
+ // Load LatencyFleX library.
+ m_lfxModule = ::LoadLibraryA(lfxModuleName);
+ if (m_lfxModule == nullptr && ::GetLastError() == ERROR_MOD_NOT_FOUND)
+ {
+ spdlog::info("LFX: Primary LatencyFleX library not found, trying fallback.");
+
+ m_lfxModule = ::LoadLibraryA(lfxModuleNameFallback);
+ if (m_lfxModule == nullptr)
+ {
+ if (::GetLastError() == ERROR_MOD_NOT_FOUND)
+ {
+ spdlog::info("LFX: Fallback LatencyFleX library not found.");
+ }
+ else
+ {
+ spdlog::info("LFX: Error loading fallback LatencyFleX library - Code: {}", ::GetLastError());
+ }
+
+ return;
+ }
+
+ useFallbackEntrypoints = true;
+ }
+ else if (m_lfxModule == nullptr)
+ {
+ spdlog::info("LFX: Error loading primary LatencyFleX library - Code: {}", ::GetLastError());
+ return;
+ }
+
+ m_lfx_WaitAndBeginFrame = reinterpret_cast<PFN_lfx_WaitAndBeginFrame>(reinterpret_cast<void*>(
+ GetProcAddress(m_lfxModule, !useFallbackEntrypoints ? "lfx_WaitAndBeginFrame" : "winelfx_WaitAndBeginFrame")));
+
+ spdlog::info("LFX: Initialized.");
+
+ Cvar_r_latencyflex = new ConVar("r_latencyflex", "1", FCVAR_ARCHIVE, "Whether or not to use LatencyFleX input latency reduction.");
+
+ HookEnabler hook;
+ ENABLER_CREATEHOOK(hook, (char*)baseAddress + 0x1952C0, &OnRenderStartHook, reinterpret_cast<LPVOID*>(&OnRenderStart));
+} \ No newline at end of file