Skip to content

Commit ab4f024

Browse files
committed
Improve performance
- Improved performance of ModuleAutoCutDrogue by harmony patching events to fire when the chutes deploy instead of polling every frame.
1 parent 63ad0b4 commit ab4f024

File tree

3 files changed

+69
-21
lines changed

3 files changed

+69
-21
lines changed

GameData/KSPCommunityPartModules/KSPCommunityPartModules.ckan

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,8 @@ description: >-
99

1010
This mod is meant as community project, so feel free to propose additional module ideas by opening an issue, or contribute with a pull request on GitHub.
1111
ksp_version_min: '1.12.3'
12+
depends:
13+
- name: Harmony2
1214
supports:
1315
- name: BoringCrewServices
1416
- name: BluedogDB

Source/KSPCommunityPartModules.csproj

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -31,7 +31,7 @@
3131
<WarningLevel>4</WarningLevel>
3232
</PropertyGroup>
3333
<ItemGroup>
34-
<PackageReference Include="KSPBuildTools" Version="0.0.2-alpha.5" />
34+
<PackageReference Include="KSPBuildTools" Version="0.0.2-alpha.7" />
3535
</ItemGroup>
3636
<ItemGroup>
3737
<Compile Include="Modules\ModuleAutoCutDrogue.cs" />
@@ -41,6 +41,11 @@
4141
<ItemGroup>
4242
<Content Include="HOW_TO_BUILD.txt" />
4343
</ItemGroup>
44-
<ItemGroup />
44+
<ItemGroup>
45+
<Reference Include="$(KSPRoot)/GameData/000_Harmony/0Harmony.dll">
46+
<Private>False</Private>
47+
<CKANIdentifier>Harmony2</CKANIdentifier>
48+
</Reference>
49+
</ItemGroup>
4550
<Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
4651
</Project>

Source/Modules/ModuleAutoCutDrogue.cs

Lines changed: 60 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,8 @@
44
Originally By: Jsolson
55
Originally For: Bluedog Design Bureau
66
*/
7+
using HarmonyLib;
8+
using System;
79
using System.Linq;
810
using UnityEngine;
911

@@ -22,6 +24,10 @@ class ModuleAutoCutDrogue : PartModule
2224
public bool triggered = false;
2325

2426
private ModuleParachute chute = null;
27+
28+
// Technically this creates an edge case where if two loaded vessels deploy a main parachute at the same time only one of the vessels will cut its drogue chutes,
29+
// but I feel like its unlikely enough to not warrent the effort required to fix it.
30+
private static int lastFrame;
2531
private bool IsChuteDeployed(ModuleParachute pParachute) => pParachute.deploymentState == ModuleParachute.deploymentStates.DEPLOYED
2632
|| pParachute.deploymentState == ModuleParachute.deploymentStates.SEMIDEPLOYED;
2733
public override void OnStart(StartState state)
@@ -32,33 +38,68 @@ public override void OnStart(StartState state)
3238

3339
Fields[nameof(autoCutDrogue)].guiActive = !isDrogueChute;
3440
Fields[nameof(autoCutDrogue)].guiActiveEditor = !isDrogueChute;
41+
42+
if (!isDrogueChute) ModuleParachuteEvents.OnDeployed += OnParachuteDeployed;
43+
if (!isDrogueChute) ModuleParachuteEvents.OnRepacked += OnParachuteRepacked;
3544
}
3645

37-
public void FixedUpdate()
46+
public void OnDestroy()
3847
{
39-
if (isDrogueChute || chute == null)
40-
{
41-
this.isEnabled = false;
42-
this.enabled = false;
43-
return;
44-
}
48+
ModuleParachuteEvents.OnDeployed -= OnParachuteDeployed;
49+
ModuleParachuteEvents.OnRepacked -= OnParachuteRepacked;
50+
}
4551

46-
if (IsChuteDeployed(chute))
52+
private void OnParachuteDeployed(ModuleParachute pChute)
53+
{
54+
if (pChute == chute && !triggered && lastFrame != Time.frameCount)
4755
{
48-
if (!triggered)
56+
var drogues = vessel.FindPartModulesImplementing<ModuleAutoCutDrogue>().Where(d => d.isDrogueChute && d.chute != null);
57+
foreach (ModuleAutoCutDrogue d in drogues)
4958
{
50-
var drogues = vessel.FindPartModulesImplementing<ModuleAutoCutDrogue>().Where(d => d.isDrogueChute && d.chute != null);
51-
foreach (ModuleAutoCutDrogue d in drogues)
52-
{
53-
if (IsChuteDeployed(d.chute)) d.chute.CutParachute();
54-
}
55-
triggered = true;
59+
if (IsChuteDeployed(d.chute)) d.chute.CutParachute();
5660
}
61+
lastFrame = Time.frameCount;
62+
triggered = true;
5763
}
58-
else if (chute.deploymentState == ModuleParachute.deploymentStates.STOWED)
59-
{
60-
triggered = false;
61-
}
64+
}
65+
66+
private void OnParachuteRepacked(ModuleParachute pChute)
67+
{
68+
if (pChute == chute && triggered) triggered = false;
69+
}
70+
}
71+
72+
[HarmonyPatch(typeof(ModuleParachute))]
73+
internal class ModuleParachuteEvents
74+
{
75+
public static void ModuleManagerPostLoad()
76+
{
77+
Harmony harmony = new Harmony("KSPCommunityPartModules");
78+
harmony.PatchAll();
79+
}
80+
81+
public static event Action<ModuleParachute> OnDeployed;
82+
public static event Action<ModuleParachute> OnRepacked;
83+
84+
[HarmonyPostfix]
85+
[HarmonyPatch("OnParachuteSemiDeployed")]
86+
static void RaiseEventOnSemiDeployed(ModuleParachute __instance)
87+
{
88+
OnDeployed?.Invoke(__instance);
89+
}
90+
91+
[HarmonyPostfix]
92+
[HarmonyPatch("OnParachuteFullyDeployed")]
93+
static void RaiseEventOnFullyDeployed(ModuleParachute __instance)
94+
{
95+
OnDeployed?.Invoke(__instance);
96+
}
97+
98+
[HarmonyPostfix]
99+
[HarmonyPatch("Repack")]
100+
static void RaiseEventOnRepack(ModuleParachute __instance)
101+
{
102+
OnRepacked?.Invoke(__instance);
62103
}
63104
}
64105
}

0 commit comments

Comments
 (0)