Skip to content

Commit af901c9

Browse files
committed
Fix OAB TWR and DeltaV calculations if celestial body is changed in the stock dv tool - reported by @Deadly_Laser
Explanation: if another body is selected in the game's dv tool, then Micro Engineer's body dropdown will be locked to that selected body. If body in the game's dv tool is switched back to Kerbin, then Micro Engineer's body dropdown will be unlocked too.
1 parent 7ca4614 commit af901c9

File tree

5 files changed

+59
-26
lines changed

5 files changed

+59
-26
lines changed

MicroEngineerProject/MicroEngineer/Entries/OabStageInfoEntries.cs

Lines changed: 13 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -191,6 +191,10 @@ public override void RefreshData()
191191
var stage = new DeltaVStageInfo_OAB()
192192
{
193193
Index = i,
194+
// if stock stage info celestial body is set to any other body than the home body (Kerbin), set it here.
195+
// TWR and DeltaV recalculations won't be done for other bodies since the game already does this
196+
SituationCelestialBody = retrieved.DeltaVSituation.CelestialBody == MicroCelestialBodies.HomeWorld
197+
? string.Empty : retrieved.DeltaVSituation.CelestialBody,
194198
DeltaVActual = retrieved.DeltaVActual,
195199
DeltaVASL = retrieved.DeltaVatASL,
196200
DeltaVVac = retrieved.DeltaVinVac,
@@ -231,9 +235,14 @@ public override void RefreshData()
231235
}
232236

233237
// Apply TWR factor to the value and recalculate sea level TWR and DeltaV
234-
stage.Recalculate_TWR();
235-
stage.Recalculate_SLT();
236-
stage.Recalculate_DeltaVSeaLevel();
238+
// Do this only if stock body readout is set to home body (Kerbin) since the game already does this for other bodies
239+
if (string.IsNullOrEmpty(stage.SituationCelestialBody))
240+
{
241+
stage.Recalculate_TWR();
242+
stage.Recalculate_SLT();
243+
stage.Recalculate_DeltaVSeaLevel();
244+
}
245+
237246

238247
// KSP2 has a strange way of displaying stage numbers, so we need a little hack
239248
stage.Recalculate_StageNumber(Utility.VesselDeltaVComponentOAB.StageInfo.Count);
@@ -270,6 +279,7 @@ public class DeltaVStageInfo_OAB
270279
/// When stages are refreshed, DeltaVStageInfo_OAB grabs the CelestialBodyForStage at the same Index.
271280
/// </summary>
272281
public int Index;
282+
public string SituationCelestialBody;
273283
public double DeltaVActual;
274284
public double DeltaVASL;
275285
public double DeltaVVac;

MicroEngineerProject/MicroEngineer/Managers/MicroCelestialBodies.cs

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,8 @@ public class MicroCelestialBodies
1111

1212
public List<CelestialBody> Bodies = new();
1313

14+
public static string HomeWorld { get; set; }
15+
1416
public static MicroCelestialBodies Instance
1517
{
1618
get
@@ -58,6 +60,12 @@ public void InitializeBodies()
5860
IsHomeWorld = body.isHomeWorld,
5961
CelestialBodyComponent = body,
6062
});
63+
64+
// set the HomeWorld body that will be read by the StageInfoOAB update patch
65+
if (body.isHomeWorld)
66+
{
67+
HomeWorld = body.Name;
68+
}
6169
}
6270

6371
// Reorder and format all celestial bodies so they form a tree-like structure

MicroEngineerProject/MicroEngineer/MicroEngineerMod.cs

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,3 @@
1-
using System.Collections;
21
using BepInEx;
32
using UnityEngine;
43
using SpaceWarp;
@@ -11,7 +10,7 @@
1110

1211
namespace MicroMod
1312
{
14-
[BepInPlugin("com.micrologist.microengineer", "MicroEngineer", "1.7.0")]
13+
[BepInPlugin("com.micrologist.microengineer", "MicroEngineer", "1.7.1")]
1514
[BepInDependency(SpaceWarpPlugin.ModGuid, SpaceWarpPlugin.ModVer)]
1615
public class MicroEngineerMod : BaseSpaceWarpPlugin
1716
{

MicroEngineerProject/MicroEngineer/UI/Controllers/StageInfoOABController.cs

Lines changed: 34 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -96,32 +96,46 @@ private void BuildStages(List<DeltaVStageInfo_OAB> stages)
9696
stage.Stage, stage.TWRVac, stage.TWRASL, stage.DeltaVASL,
9797
stage.DeltaVVac, stage.StageBurnTime.Days, stage.StageBurnTime.Hours,
9898
stage.StageBurnTime.Minutes, stage.StageBurnTime.Seconds,
99-
MicroCelestialBodies.Instance.Bodies.Select(b => b.DisplayName).ToList(),
100-
stage.CelestialBody.Name
99+
// if stock body selector is set to a body different than the home body (Kerbin)
100+
// then pass only this body to the control
101+
bodies: string.IsNullOrEmpty(stage.SituationCelestialBody)
102+
? MicroCelestialBodies.Instance.Bodies.Select(b => b.DisplayName).ToList()
103+
: new List<string> { stage.SituationCelestialBody},
104+
selectedBody: string.IsNullOrEmpty(stage.SituationCelestialBody)
105+
? stage.CelestialBody.Name
106+
: stage.SituationCelestialBody
101107
);
102108

103109
_totalDeltaVASL += stage.DeltaVASL;
104110
_totalDeltaVVac += stage.DeltaVVac;
105111

106-
var celestialBodyDropdown = control.Q<DropdownField>("body-dropdown");
107-
celestialBodyDropdown.RegisterCallback<MouseDownEvent>(evt =>
112+
// check if SituationCelestialBody contains data
113+
// if it does, it means that stock body selector is set to a body different than the home body (Kerbin)
114+
// in that case we will not allow body changing here since the game already does recalculations for TWR and DeltaV
115+
if (string.IsNullOrEmpty(stage.SituationCelestialBody))
108116
{
109-
// When user clicks on the celestialBodyDropdown control we lock stage info refresh from happening
110-
// and unlock it again when user selects something from the dropdown.
111-
// We do this because if VesselDeltaVCalculationMessage is triggered between the user first clicking
112-
// on the control and selection something from it, the event will cause the UI to refresh (destroy
113-
// and rebuild the controls) and thus the original dropdown control will no longer exist and
114-
// celestialBody will not be selectable.
115-
_lockUiRefresh = true;
116-
});
117-
// Update entry's CelestialBody at the same index as the stage
118-
celestialBodyDropdown.RegisterValueChangedCallback(evt =>
119-
{
120-
StageEntry.UpdateCelestialBodyAtIndex(stage.Index, celestialBodyDropdown.value);
121-
_lockUiRefresh = false;
122-
StageEntry.RefreshData();
123-
});
124-
117+
// SituationCelestialBody does not contain data, perform body dropdown logic normally
118+
119+
var celestialBodyDropdown = control.Q<DropdownField>("body-dropdown");
120+
celestialBodyDropdown.RegisterCallback<MouseDownEvent>(evt =>
121+
{
122+
// When user clicks on the celestialBodyDropdown control we lock stage info refresh from happening
123+
// and unlock it again when user selects something from the dropdown.
124+
// We do this because if VesselDeltaVCalculationMessage is triggered between the user first clicking
125+
// on the control and selection something from it, the event will cause the UI to refresh (destroy
126+
// and rebuild the controls) and thus the original dropdown control will no longer exist and
127+
// celestialBody will not be selectable.
128+
_lockUiRefresh = true;
129+
});
130+
// Update entry's CelestialBody at the same index as the stage
131+
celestialBodyDropdown.RegisterValueChangedCallback(evt =>
132+
{
133+
StageEntry.UpdateCelestialBodyAtIndex(stage.Index, celestialBodyDropdown.value);
134+
_lockUiRefresh = false;
135+
StageEntry.RefreshData();
136+
});
137+
}
138+
125139
Body.Add(control);
126140
}
127141

MicroEngineerProject/MicroEngineer/UI/Controls/StageInfoOABEntryControl.cs

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -134,7 +134,9 @@ public void SetValue(int stageNumber, float twr, float slt, double aslDeltaV, do
134134

135135
Body = bodies;
136136
BodyDropdown.SetValueWithoutNotify(selectedBody);
137-
BodyDropdown.SetEnabled(true);
137+
138+
// enabled the dropdown control only if there is more than one option
139+
BodyDropdown.SetEnabled(bodies.Count > 1);
138140
}
139141

140142
public StageInfoOABEntryControl(int stageNumber, float twr, float slt, double aslDeltaV, double vacDeltaV, int burnDays, int burnHours, int burnMinutes, int burnSeconds, List<string> bodies, string selectedBody) : this()

0 commit comments

Comments
 (0)