From ba0ab3bc31063996fce377e92435d9e581c8442c Mon Sep 17 00:00:00 2001
From: gotmachine <24925209+gotmachine@users.noreply.github.com>
Date: Sat, 8 Mar 2025 15:06:29 +0100
Subject: [PATCH 1/2] More sensible implementation of the CommNetThrottling
patch. CommNet updates are now occuring at a configurable in-game seconds
interval (default is 2.5 seconds), instead of a real time interval with a
hard minimum of 0.5s. This mean simulation precision will stay consistent
when timewarping, as updates will happen more frequently as the timewarp rate
goes up, up to every fixed frame when crossing the 125x warp threshold (for
the default 2.5s). We also put a upper bound on the update frequency at 50 Hz
by checking the fixed/physics frame count (no point in running at stupidly
high update rates on high frequency monitors or if framerate isn't locked).
---
GameData/KSPCommunityFixes/Settings.cfg | 22 ++++-----
.../Performance/CommNetThrottling.cs | 48 +++++++------------
README.md | 2 +-
3 files changed, 27 insertions(+), 45 deletions(-)
diff --git a/GameData/KSPCommunityFixes/Settings.cfg b/GameData/KSPCommunityFixes/Settings.cfg
index a2cca41..e92f232 100644
--- a/GameData/KSPCommunityFixes/Settings.cfg
+++ b/GameData/KSPCommunityFixes/Settings.cfg
@@ -372,20 +372,14 @@ KSP_COMMUNITY_FIXES
LogGameEventsSubscribers = false
}
- // Fix CommNet update throttling mechanism that exists in stock but doesn't work correctly.
- // This is supposed to prevent full CommNet network updates from happening every frame, but instead to
- // to happen at a regular real-world time interval of 5 seconds while in flight. Enabling this throttling
- // mechanism has an detrimental impact on the precision of the simulation, so this patch isn't enabled by
- // default to avoid issues in mods relying on the stock behavior. Enabling this can provide a decent
- // performance uplift in games having a large amount of celestial bodies and/or vessels.
- CommNetThrottling = false
-
- // Interval in real-world seconds between full CommNet network updates.
- COMMNET_THROTTLING_SETTINGS
- {
- unpackedInterval = 5 // interval when the active vessel is not timewarping
- packedInterval = 0.5 // interval when the active vessel is timewarping
- }
+ // Implement a throttling mechanism preventing CommNet network updates from happening every frame.
+ // When this patch is enabled, network updates will only happen at a set interval of in-game seconds,
+ // defined by the `CommNetThrottlingUpdateInterval` setting (default is 2.5s). This patch will cause
+ // events such as line of sight loss or acquisition, or comm link changes to happen with a delay, but
+ // provide a significant performance uplift in games having a large amount of celestial bodies and/or
+ // vessels.
+ CommNetThrottling = true
+ CommNetThrottlingUpdateInterval = 2.5
// This tweak eliminates KSP's stock behavior of saving every time
// you exit a UI-only space center building (AC, MC, etc)
diff --git a/KSPCommunityFixes/Performance/CommNetThrottling.cs b/KSPCommunityFixes/Performance/CommNetThrottling.cs
index 04c977c..5f25eb7 100644
--- a/KSPCommunityFixes/Performance/CommNetThrottling.cs
+++ b/KSPCommunityFixes/Performance/CommNetThrottling.cs
@@ -1,45 +1,33 @@
-using HarmonyLib;
-using System.Collections.Generic;
-using UnityEngine;
-
-namespace KSPCommunityFixes.Performance
+namespace KSPCommunityFixes.Performance
{
class CommNetThrottling : BasePatch
{
- private static double packedInterval = 0.5;
- private static double unpackedInterval = 5.0;
+ private static double updateInterval = 2.5;
+ private static long lastUpdateFixedFrame = 0L;
protected override void ApplyPatches()
{
- ConfigNode settingsNode = KSPCommunityFixes.SettingsNode.GetNode("COMMNET_THROTTLING_SETTINGS");
-
- if (settingsNode != null)
- {
- settingsNode.TryGetValue("packedInterval", ref packedInterval);
- settingsNode.TryGetValue("unpackedInterval", ref unpackedInterval);
- }
-
- AddPatch(PatchType.Prefix, typeof(CommNet.CommNetNetwork), nameof(CommNet.CommNetNetwork.Update));
+ KSPCommunityFixes.SettingsNode.TryGetValue("CommNetThrottlingUpdateInterval", ref updateInterval);
+ AddPatch(PatchType.Override, typeof(CommNet.CommNetNetwork), nameof(CommNet.CommNetNetwork.Update));
}
- static bool CommNetNetwork_Update_Prefix(CommNet.CommNetNetwork __instance)
+ static void CommNetNetwork_Update_Override(CommNet.CommNetNetwork commNetNetwork)
{
- if (!__instance.queueRebuild && !__instance.commNet.IsDirty)
+ double currentTime = Planetarium.GetUniversalTime();
+ double interval = currentTime - commNetNetwork.prevUpdate;
+ if (!commNetNetwork.queueRebuild && !commNetNetwork.commNet.IsDirty
+ && interval >= 0.0
+ && (interval < updateInterval || KSPCommunityFixes.FixedUpdateCount == lastUpdateFixedFrame))
{
- double timeSinceLastUpdate = Time.timeSinceLevelLoad - __instance.prevUpdate;
-
- if (FlightGlobals.ActiveVessel != null)
- {
- double interval = FlightGlobals.ActiveVessel.packed ? packedInterval : unpackedInterval;
- if (timeSinceLastUpdate < interval)
- {
- __instance.graphDirty = true;
- return false;
- }
- }
+ commNetNetwork.graphDirty = true;
+ return;
}
- return true;
+ lastUpdateFixedFrame = KSPCommunityFixes.FixedUpdateCount;
+ commNetNetwork.commNet.Rebuild();
+ commNetNetwork.prevUpdate = currentTime;
+ commNetNetwork.graphDirty = false;
+ commNetNetwork.queueRebuild = false;
}
}
}
diff --git a/README.md b/README.md
index 30b5f26..349853f 100644
--- a/README.md
+++ b/README.md
@@ -121,7 +121,7 @@ User options are available from the "ESC" in-game settings menu :
= 0.0
- && (interval < updateInterval || KSPCommunityFixes.FixedUpdateCount == lastUpdateFixedFrame))
+ && currentGameTimeInterval >= 0.0
+ && (currentGameTimeInterval < maxGameTimeInterval || realTimeUpdateTimer.ElapsedMilliseconds < minRealTimeInterval))
{
commNetNetwork.graphDirty = true;
return;
}
- lastUpdateFixedFrame = KSPCommunityFixes.FixedUpdateCount;
+ // UnityEngine.Debug.Log($"CommNet update interval : {realTimeUpdateTimer.Elapsed.TotalMilliseconds:F0}ms");
+
commNetNetwork.commNet.Rebuild();
- commNetNetwork.prevUpdate = currentTime;
+ realTimeUpdateTimer.Restart();
+ commNetNetwork.prevUpdate = currentGameTime;
commNetNetwork.graphDirty = false;
commNetNetwork.queueRebuild = false;
}
diff --git a/README.md b/README.md
index 349853f..b432edd 100644
--- a/README.md
+++ b/README.md
@@ -121,7 +121,7 @@ User options are available from the "ESC" in-game settings menu :
 [KSP 1.12.0 - 1.12.5]<br/>Fix a bunch of managed memory leaks, mainly by proactively removing `GameEvents` delegates originating from destroyed `UnityEngine.Object` instances on scene switches. Will log detected leaks and memory usage. Also see`Settings.cfg` to enable advanced logging options that can be useful to hunt down memory leaks in mods.
- [**ProgressTrackingSpeedBoost**](https://github.com/KSPModdingLibs/KSPCommunityFixes/pull/57) [KSP 1.12.0 - 1.12.5]<br/>Remove unused ProgressTracking update handlers. Provides a very noticeable performance uplift in career games having a large amount of celestial bodies and/or vessels.
- [**DisableMapUpdateInFlight**](https://github.com/KSPModdingLibs/KSPCommunityFixes/issues/59) [KSP 1.8.0 - 1.12.5]<br/>Disable the update of orbit lines and markers in flight when the map view isn't shown. Provides decent performance gains in games having a large amount of celestial bodies and/or vessels.
-- [**CommNetThrottling**](https://github.com/KSPModdingLibs/KSPCommunityFixes/issues/56) [KSP 1.12.0 - 1.12.5]<br/>Implement a throttling mechanism preventing CommNet network updates from happening every frame. When this patch is enabled, network updates will only happen at a set interval of in-game seconds, defined by the `CommNetThrottlingUpdateInterval` setting (default is 2.5s). This patch will cause events such as line of sight loss or acquisition, or comm link changes to happen with a delay, but provide a significant performance uplift in games having a large amount of celestial bodies and/or vessels.
+- [**CommNetThrottling**](https://github.com/KSPModdingLibs/KSPCommunityFixes/issues/56) [KSP 1.12.0 - 1.12.5]<br/>Implement a throttling mechanism preventing CommNet network updates from happening every frame. When this patch is enabled, network updates will only happen at a set interval of in-game seconds (default is 2.5s, configurable in `Settings.cfg`). This patch will cause events such as line of sight loss or acquisition, or comm link changes to happen with a slight delay, but provide a significant performance uplift in games having a large amount of celestial bodies and/or vessels.
- [**AsteroidAndCometDrillCache**](https://github.com/KSPModdingLibs/KSPCommunityFixes/pull/67) [KSP 1.12.5]<br/>Reduce constant overhead of ModuleAsteroidDrill and ModuleCometDrill by using the cached asteroid/comet part lookup results from ModuleResourceHarvester. Improves performance with large part count vessels having at least one drill part.
- [**FewerSaves**](https://github.com/KSPModdingLibs/KSPCommunityFixes/pull/80) [KSP 1.8.0 - KSP 1.12.5]<br/>Disables saving on exiting Space Center minor buildings (Mission Control etc) and when deleting vessels in Tracking Station. Disabled by default.
- [**ConfigNodePerf**](https://github.com/KSPModdingLibs/KSPCommunityFixes/pull/88) [see also](https://github.com/KSPModdingLibs/KSPCommunityFixes/pull/90) [KSP 1.8.0 - KSP 1.12.5]<br/>Speeds up many ConfigNode methods, especially reading and writing ConfigNodes.
)