diff --git a/Dalamud/Configuration/Internal/DalamudConfiguration.cs b/Dalamud/Configuration/Internal/DalamudConfiguration.cs
index a8e598e08..e6f77eadf 100644
--- a/Dalamud/Configuration/Internal/DalamudConfiguration.cs
+++ b/Dalamud/Configuration/Internal/DalamudConfiguration.cs
@@ -351,6 +351,26 @@ internal sealed class DalamudConfiguration : IServiceType
///
public bool WindowIsImmersive { get; set; } = false;
+ ///
+ /// Gets or sets hitch threshold for game network up in milliseconds.
+ ///
+ public double GameNetworkUpHitch { get; set; } = 30;
+
+ ///
+ /// Gets or sets hitch threshold for game network down in milliseconds.
+ ///
+ public double GameNetworkDownHitch { get; set; } = 30;
+
+ ///
+ /// Gets or sets hitch threshold for framework update in milliseconds.
+ ///
+ public double FrameworkUpdateHitch { get; set; } = 50;
+
+ ///
+ /// Gets or sets hitch threshold for ui builder in milliseconds.
+ ///
+ public double UiBuilderHitch { get; set; } = 100;
+
///
/// Load a configuration from the provided path.
///
diff --git a/Dalamud/Game/Framework.cs b/Dalamud/Game/Framework.cs
index dd610b988..16bed5696 100644
--- a/Dalamud/Game/Framework.cs
+++ b/Dalamud/Game/Framework.cs
@@ -28,7 +28,7 @@ public sealed class Framework : IDisposable, IServiceType
private static Stopwatch statsStopwatch = new();
private readonly Stopwatch updateStopwatch = new();
- private readonly HitchDetector hitchDetector = new("FrameworkUpdate", 50);
+ private readonly HitchDetector hitchDetector;
private readonly Hook updateHook;
private readonly Hook destroyHook;
@@ -39,9 +39,14 @@ public sealed class Framework : IDisposable, IServiceType
private Thread? frameworkUpdateThread;
+ [ServiceManager.ServiceDependency]
+ private readonly DalamudConfiguration configuration = Service.Get();
+
[ServiceManager.ServiceConstructor]
private Framework(SigScanner sigScanner)
{
+ this.hitchDetector = new HitchDetector("FrameworkUpdate", this.configuration.FrameworkUpdateHitch);
+
this.Address = new FrameworkAddressResolver();
this.Address.Setup(sigScanner);
diff --git a/Dalamud/Game/Network/GameNetwork.cs b/Dalamud/Game/Network/GameNetwork.cs
index 43205a361..767c9bc9a 100644
--- a/Dalamud/Game/Network/GameNetwork.cs
+++ b/Dalamud/Game/Network/GameNetwork.cs
@@ -1,12 +1,13 @@
using System;
using System.Collections.Generic;
using System.Runtime.InteropServices;
-
+using Dalamud.Configuration.Internal;
using Dalamud.Hooking;
using Dalamud.IoC;
using Dalamud.IoC.Internal;
using Dalamud.Utility;
using Serilog;
+using Serilog.Core;
namespace Dalamud.Game.Network;
@@ -22,14 +23,20 @@ public sealed class GameNetwork : IDisposable, IServiceType
private readonly Hook processZonePacketDownHook;
private readonly Hook processZonePacketUpHook;
- private readonly HitchDetector hitchDetectorUp = new("GameNetworkUp", 30);
- private readonly HitchDetector hitchDetectorDown = new("GameNetworkDown", 30);
+ private readonly HitchDetector hitchDetectorUp;
+ private readonly HitchDetector hitchDetectorDown;
private IntPtr baseAddress;
+ [ServiceManager.ServiceDependency]
+ private readonly DalamudConfiguration configuration = Service.Get();
+
[ServiceManager.ServiceConstructor]
private GameNetwork(SigScanner sigScanner)
{
+ this.hitchDetectorUp = new HitchDetector("GameNetworkUp", this.configuration.GameNetworkUpHitch);
+ this.hitchDetectorDown = new HitchDetector("GameNetworkDown", this.configuration.GameNetworkDownHitch);
+
this.address = new GameNetworkAddressResolver();
this.address.Setup(sigScanner);
diff --git a/Dalamud/Interface/Internal/DalamudInterface.cs b/Dalamud/Interface/Internal/DalamudInterface.cs
index c62fbb89c..746e31d4b 100644
--- a/Dalamud/Interface/Internal/DalamudInterface.cs
+++ b/Dalamud/Interface/Internal/DalamudInterface.cs
@@ -61,6 +61,7 @@ internal class DalamudInterface : IDisposable, IServiceType
private readonly TitleScreenMenuWindow titleScreenMenuWindow;
private readonly ProfilerWindow profilerWindow;
private readonly BranchSwitcherWindow branchSwitcherWindow;
+ private readonly HitchSettingsWindow hitchSettingsWindow;
private readonly TextureWrap logoTexture;
private readonly TextureWrap tsmLogoTexture;
@@ -108,6 +109,7 @@ internal class DalamudInterface : IDisposable, IServiceType
this.titleScreenMenuWindow = new TitleScreenMenuWindow() { IsOpen = false };
this.profilerWindow = new ProfilerWindow() { IsOpen = false };
this.branchSwitcherWindow = new BranchSwitcherWindow() { IsOpen = false };
+ this.hitchSettingsWindow = new HitchSettingsWindow() { IsOpen = false };
this.WindowSystem.AddWindow(this.changelogWindow);
this.WindowSystem.AddWindow(this.colorDemoWindow);
@@ -124,6 +126,7 @@ internal class DalamudInterface : IDisposable, IServiceType
this.WindowSystem.AddWindow(this.titleScreenMenuWindow);
this.WindowSystem.AddWindow(this.profilerWindow);
this.WindowSystem.AddWindow(this.branchSwitcherWindow);
+ this.WindowSystem.AddWindow(this.hitchSettingsWindow);
ImGuiManagedAsserts.AssertsEnabled = configuration.AssertsEnabledAtStartup;
this.isImGuiDrawDevMenu = this.isImGuiDrawDevMenu || configuration.DevBarOpenAtStartup;
@@ -307,6 +310,15 @@ internal class DalamudInterface : IDisposable, IServiceType
this.profilerWindow.IsOpen = true;
this.profilerWindow.BringToFront();
}
+
+ ///
+ /// Opens the .
+ ///
+ public void OpenHitchSettings()
+ {
+ this.hitchSettingsWindow.IsOpen = true;
+ this.hitchSettingsWindow.BringToFront();
+ }
///
/// Opens the .
@@ -676,6 +688,11 @@ internal class DalamudInterface : IDisposable, IServiceType
{
this.OpenProfiler();
}
+
+ if (ImGui.MenuItem("Open Hitch Settings"))
+ {
+ this.OpenHitchSettings();
+ }
ImGui.Separator();
diff --git a/Dalamud/Interface/Internal/Windows/HitchSettingsWindow.cs b/Dalamud/Interface/Internal/Windows/HitchSettingsWindow.cs
new file mode 100644
index 000000000..f229b1de3
--- /dev/null
+++ b/Dalamud/Interface/Internal/Windows/HitchSettingsWindow.cs
@@ -0,0 +1,58 @@
+using Dalamud.Configuration.Internal;
+using Dalamud.Interface.Windowing;
+using ImGuiNET;
+
+namespace Dalamud.Interface.Internal.Windows;
+
+///
+/// Window responsible for hitch settings.
+///
+public class HitchSettingsWindow : Window
+{
+ private const float MinHitch = 1;
+ private const float MaxHitch = 500;
+
+ ///
+ /// Initializes a new instance of the class.
+ ///
+ public HitchSettingsWindow()
+ : base("Hitch Settings", ImGuiWindowFlags.AlwaysAutoResize)
+ {
+ this.ShowCloseButton = true;
+ this.RespectCloseHotkey = true;
+ }
+
+ ///
+ public override void Draw()
+ {
+ var config = Service.Get();
+
+ var uiBuilderHitch = (float)config.UiBuilderHitch;
+ if (ImGui.SliderFloat("UiBuilderHitch", ref uiBuilderHitch, MinHitch, MaxHitch))
+ {
+ config.UiBuilderHitch = uiBuilderHitch;
+ config.QueueSave();
+ }
+
+ var frameworkUpdateHitch = (float)config.FrameworkUpdateHitch;
+ if (ImGui.SliderFloat("FrameworkUpdateHitch", ref frameworkUpdateHitch, MinHitch, MaxHitch))
+ {
+ config.FrameworkUpdateHitch = frameworkUpdateHitch;
+ config.QueueSave();
+ }
+
+ var gameNetworkUpHitch = (float)config.GameNetworkUpHitch;
+ if (ImGui.SliderFloat("GameNetworkUpHitch", ref gameNetworkUpHitch, MinHitch, MaxHitch))
+ {
+ config.GameNetworkUpHitch = gameNetworkUpHitch;
+ config.QueueSave();
+ }
+
+ var gameNetworkDownHitch = (float)config.GameNetworkDownHitch;
+ if (ImGui.SliderFloat("GameNetworkDownHitch", ref gameNetworkDownHitch, MinHitch, MaxHitch))
+ {
+ config.GameNetworkDownHitch = gameNetworkDownHitch;
+ config.QueueSave();
+ }
+ }
+}
diff --git a/Dalamud/Interface/UiBuilder.cs b/Dalamud/Interface/UiBuilder.cs
index 74d34f9ee..9b2b6620b 100644
--- a/Dalamud/Interface/UiBuilder.cs
+++ b/Dalamud/Interface/UiBuilder.cs
@@ -34,6 +34,9 @@ public sealed class UiBuilder : IDisposable
private bool hasErrorWindow = false;
private bool lastFrameUiHideState = false;
+ [ServiceManager.ServiceDependency]
+ private readonly DalamudConfiguration configuration = Service.Get();
+
///
/// Initializes a new instance of the class and registers it.
/// You do not have to call this manually.
@@ -42,7 +45,7 @@ public sealed class UiBuilder : IDisposable
internal UiBuilder(string namespaceName)
{
this.stopwatch = new Stopwatch();
- this.hitchDetector = new HitchDetector($"UiBuilder({namespaceName})", 100);
+ this.hitchDetector = new HitchDetector($"UiBuilder({namespaceName})", this.configuration.UiBuilderHitch);
this.namespaceName = namespaceName;
this.interfaceManager.Draw += this.OnDraw;