From c1429f8159e97ca18c710972c5fe2fc6b33f5030 Mon Sep 17 00:00:00 2001 From: siimav Date: Wed, 16 Oct 2024 20:30:33 +0300 Subject: [PATCH] Implement faster lookup of PartModules. This means adding a dependency for KSPCF though. --- FerramAerospaceResearch/FARAPI.cs | 20 ++++------ .../FARAeroComponents/FARAeroPartModule.cs | 20 +++++----- .../FARAeroComponents/FARVesselAero.cs | 7 ++-- .../ModularFlightIntegratorRegisterer.cs | 13 +++--- .../FARAeroComponents/VehicleAerodynamics.cs | 39 +++++++----------- .../FARAeroComponents/VesselIntakeRamDrag.cs | 11 +++-- FerramAerospaceResearch/FARAeroUtil.cs | 3 +- .../FARGUI/FAREditorGUI/EditorGUI.cs | 15 +++---- .../FARGUI/FARFlightGUI/PhysicsCalcs.cs | 39 +++++++++--------- .../FARPartGeometry/GeometryPartModule.cs | 40 +++++++++---------- .../FARPartGeometry/PartGeometryExtensions.cs | 5 ++- .../FARPartGeometry/VehicleVoxel.cs | 9 +++-- .../FerramAerospaceResearch.csproj | 4 ++ .../LEGACYferram4/FARBaseAerodynamics.cs | 9 +++-- .../LEGACYferram4/FARControllableSurface.cs | 11 ++--- .../LEGACYferram4/FARPartModule.cs | 6 +-- .../LEGACYferram4/FARWingAerodynamicModel.cs | 11 ++--- .../RealChuteLite/ChuteCalculator.cs | 4 +- .../RealChuteLite/RealChuteFAR.cs | 9 +++-- .../Settings/FARAeroStress.cs | 3 +- 20 files changed, 136 insertions(+), 142 deletions(-) diff --git a/FerramAerospaceResearch/FARAPI.cs b/FerramAerospaceResearch/FARAPI.cs index 479115c82..88fd775fd 100644 --- a/FerramAerospaceResearch/FARAPI.cs +++ b/FerramAerospaceResearch/FARAPI.cs @@ -46,6 +46,7 @@ You should have received a copy of the GNU General Public License using ferram4; using FerramAerospaceResearch.FARAeroComponents; using FerramAerospaceResearch.FARGUI.FARFlightGUI; +using KSPCommunityFixes; using UnityEngine; // ReSharper disable UnusedMember.Global @@ -222,9 +223,8 @@ public static void VesselIncreaseFlapDeflection(Vessel v) { foreach (Part p in v.parts) { - if (!p.Modules.Contains()) + if (!(p.FindModuleImplementingFast() is FARControllableSurface surface)) continue; - FARControllableSurface surface = p.Modules.GetModule(); surface.SetDeflection(surface.flapDeflectionLevel + 1); } } @@ -236,9 +236,8 @@ public static void VesselDecreaseFlapDeflection(Vessel v) { foreach (Part p in v.parts) { - if (!p.Modules.Contains()) + if (!(p.FindModuleImplementingFast() is FARControllableSurface surface)) continue; - FARControllableSurface surface = p.Modules.GetModule(); surface.SetDeflection(surface.flapDeflectionLevel - 1); } } @@ -252,9 +251,8 @@ public static int VesselFlapSetting(Vessel v) { foreach (Part p in v.parts) { - if (!p.Modules.Contains()) + if (!(p.FindModuleImplementingFast() is FARControllableSurface surface)) continue; - FARControllableSurface surface = p.Modules.GetModule(); if (surface.isFlap) return surface.flapDeflectionLevel; } @@ -269,9 +267,8 @@ public static void VesselSetSpoilers(Vessel v, bool spoilerActive) { foreach (Part p in v.parts) { - if (!p.Modules.Contains()) + if (!(p.FindModuleImplementingFast() is FARControllableSurface surface)) continue; - FARControllableSurface surface = p.Modules.GetModule(); surface.brake = spoilerActive; } } @@ -285,9 +282,8 @@ public static bool VesselSpoilerSetting(Vessel v) { foreach (Part p in v.parts) { - if (!p.Modules.Contains()) + if (!(p.FindModuleImplementingFast() is FARControllableSurface surface)) continue; - FARControllableSurface surface = p.Modules.GetModule(); if (surface.isSpoiler) return surface.brake; } @@ -430,7 +426,7 @@ public static bool VesselVoxelizationCompletedAndValid(Vessel vessel) /// Signature is (part, (drag, lift, torque)) -> (new_drag, new_lift, new_torque) public static void SetPartAeroForceModifier(Part part, Func modifier) { - part.FindModuleImplementing().AeroForceModifier = modifier; + part.FindModuleImplementingFast().AeroForceModifier = modifier; } /// @@ -441,7 +437,7 @@ public static void SetPartAeroForceModifier(Part part, Func (new_drag, new_lift, new_torque) public static Func GetPartAeroForceModifier(Part part) { - return part.FindModuleImplementing()?.AeroForceModifier; + return part.FindModuleImplementingFast()?.AeroForceModifier; } } } diff --git a/FerramAerospaceResearch/FARAeroComponents/FARAeroPartModule.cs b/FerramAerospaceResearch/FARAeroComponents/FARAeroPartModule.cs index 5fe91fd9a..672d4b003 100644 --- a/FerramAerospaceResearch/FARAeroComponents/FARAeroPartModule.cs +++ b/FerramAerospaceResearch/FARAeroComponents/FARAeroPartModule.cs @@ -51,6 +51,7 @@ You should have received a copy of the GNU General Public License using FerramAerospaceResearch.RealChuteLite; using FerramAerospaceResearch.Settings; using KSP.Localization; +using KSPCommunityFixes; using UnityEngine; namespace FerramAerospaceResearch.FARAeroComponents @@ -238,8 +239,8 @@ public void SetProjectedArea(ProjectedArea areas, Matrix4x4 vesselToWorldMatrix) double areaForStress = projectedArea.totalArea / 6; if (!FARDebugValues.allowStructuralFailures || areaForStress <= 0.1 || - part.Modules.Contains() || - part.Modules.Contains()) + part.HasModuleImplementingFast() || + part.HasModuleImplementingFast()) { partForceMaxY = double.MaxValue; partForceMaxXZ = double.MaxValue; @@ -303,17 +304,15 @@ private void Start() partTransform = part.partTransform; materialColorUpdater = new MaterialColorUpdater(partTransform, PhysicsGlobals.TemperaturePropertyID); - if (part.Modules.Contains()) - LegacyWingModel = part.Modules.GetModule(); - else if (part.Modules.Contains()) - LegacyWingModel = part.Modules.GetModule(); + if (part.FindModuleImplementingFast() is FARWingAerodynamicModel pm) + LegacyWingModel = pm; + else if (part.FindModuleImplementingFast() is FARControllableSurface pm2) + LegacyWingModel = pm2; else LegacyWingModel = null; // For handling airbrakes aero visualization - stockAeroSurfaceModule = part.Modules.Contains() - ? part.Modules.GetModule() - : null; + stockAeroSurfaceModule = part.FindModuleImplementingFast(); } public double ProjectedAreaWorld(Vector3 normalizedDirectionVector) @@ -581,9 +580,8 @@ private void CheckAeroStressFailure() private void ApplyAeroStressFailure() { bool failureOccured = false; - if (part.Modules.Contains()) + if (part.FindModuleImplementingFast() is ModuleProceduralFairing fairing) { - ModuleProceduralFairing fairing = part.Modules.GetModule(); fairing.ejectionForce = 0.5f; fairing.DeployFairing(); diff --git a/FerramAerospaceResearch/FARAeroComponents/FARVesselAero.cs b/FerramAerospaceResearch/FARAeroComponents/FARVesselAero.cs index 8fb1752a4..708f75d6f 100644 --- a/FerramAerospaceResearch/FARAeroComponents/FARVesselAero.cs +++ b/FerramAerospaceResearch/FARAeroComponents/FARVesselAero.cs @@ -47,6 +47,7 @@ You should have received a copy of the GNU General Public License using FerramAerospaceResearch.FARGUI.FARFlightGUI; using FerramAerospaceResearch.FARPartGeometry; using FerramAerospaceResearch.FARThreading; +using KSPCommunityFixes; using UnityEngine; namespace FerramAerospaceResearch.FARAeroComponents @@ -145,7 +146,7 @@ protected override void OnStart() geoModulesReady++; } - if (!p.Modules.Contains() && !p.Modules.Contains()) + if (!p.HasModuleImplementingFast() && !p.HasModuleImplementingFast()) continue; FARLogger.Info("Handling Stuff for KerbalEVA / Flag"); g = (GeometryPartModule)p.AddModule("GeometryPartModule"); @@ -435,7 +436,7 @@ public void VesselUpdate(bool recalcGeoModules) _updateRateLimiter = 0; _updateQueued = false; - if (vessel.rootPart.Modules.Contains()) + if (vessel.rootPart.HasModuleImplementingFast()) { DisableModule(); return; @@ -447,7 +448,7 @@ public void VesselUpdate(bool recalcGeoModules) geoModulesReady = 0; foreach (Part p in vessel.Parts) { - GeometryPartModule g = p.Modules.GetModule(); + GeometryPartModule g = p.FindModuleImplementingFast(); if (g is null) continue; _currentGeoModules.Add(g); diff --git a/FerramAerospaceResearch/FARAeroComponents/ModularFlightIntegratorRegisterer.cs b/FerramAerospaceResearch/FARAeroComponents/ModularFlightIntegratorRegisterer.cs index 598ca6e57..575a5523a 100644 --- a/FerramAerospaceResearch/FARAeroComponents/ModularFlightIntegratorRegisterer.cs +++ b/FerramAerospaceResearch/FARAeroComponents/ModularFlightIntegratorRegisterer.cs @@ -45,6 +45,7 @@ You should have received a copy of the GNU General Public License using System; using FerramAerospaceResearch.Settings; using ModularFI; +using KSPCommunityFixes; using UnityEngine; namespace FerramAerospaceResearch.FARAeroComponents @@ -75,7 +76,7 @@ private static void UpdateThermodynamicsPre(ModularFlightIntegrator fi) { PartThermalData ptd = fi.partThermalDataList[i]; Part part = ptd.part; - FARAeroPartModule aeroModule = part.Modules.GetModule(); + FARAeroPartModule aeroModule = part.FindModuleImplementingFast(); if (aeroModule is null) continue; @@ -106,7 +107,7 @@ private static void UpdateThermodynamicsPre(ModularFlightIntegrator fi) private static void UpdateAerodynamics(ModularFlightIntegrator fi, Part part) { //FIXME Proper model for airbrakes - if (part.Modules.Contains() || + if (part.HasModuleImplementingFast() || part.Modules.Contains("MissileLauncher") && part.vessel.rootPart == part) { fi.BaseFIUpdateAerodynamics(part); @@ -185,7 +186,7 @@ private static void CalculateLocalDynPresAndAngularDrag(ModularFlightIntegrator private static double CalculateAreaRadiative(ModularFlightIntegrator fi, Part part) { - FARAeroPartModule module = part.Modules.GetModule(); + FARAeroPartModule module = part.FindModuleImplementingFast(); return CalculateAreaRadiative(fi, part, module); } @@ -204,7 +205,7 @@ FARAeroPartModule aeroModule private static double CalculateAreaExposed(ModularFlightIntegrator fi, Part part) { - FARAeroPartModule module = part.Modules.GetModule(); + FARAeroPartModule module = part.FindModuleImplementingFast(); return CalculateAreaExposed(fi, part, module); } @@ -224,7 +225,7 @@ private static double CalculateAreaExposed(ModularFlightIntegrator fi, Part part private static double CalculateSunArea(ModularFlightIntegrator fi, PartThermalData ptd) { - FARAeroPartModule module = ptd.part.Modules.GetModule(); + FARAeroPartModule module = ptd.part.FindModuleImplementingFast(); if (module is null) return fi.BaseFIGetSunArea(ptd); @@ -235,7 +236,7 @@ private static double CalculateSunArea(ModularFlightIntegrator fi, PartThermalDa private static double CalculateBodyArea(ModularFlightIntegrator fi, PartThermalData ptd) { - FARAeroPartModule module = ptd.part.Modules.GetModule(); + FARAeroPartModule module = ptd.part.FindModuleImplementingFast(); if (module is null) return fi.BaseFIBodyArea(ptd); diff --git a/FerramAerospaceResearch/FARAeroComponents/VehicleAerodynamics.cs b/FerramAerospaceResearch/FARAeroComponents/VehicleAerodynamics.cs index 4ad2f3d91..563e7c0ae 100644 --- a/FerramAerospaceResearch/FARAeroComponents/VehicleAerodynamics.cs +++ b/FerramAerospaceResearch/FARAeroComponents/VehicleAerodynamics.cs @@ -49,6 +49,7 @@ You should have received a copy of the GNU General Public License using FerramAerospaceResearch.FARPartGeometry; using FerramAerospaceResearch.FARPartGeometry.GeometryModification; using FerramAerospaceResearch.FARThreading; +using KSPCommunityFixes; using UnityEngine; namespace FerramAerospaceResearch.FARAeroComponents @@ -223,23 +224,17 @@ private List LEGACY_UpdateWingAerodynamicModels() Part p = aeroModule.part; if (!p) continue; - if (p.Modules.Contains()) + if (p.FindModuleImplementingFast() is FARWingAerodynamicModel w) { - var w = p.Modules.GetModule(); - if (w is null) - continue; w.isShielded = false; w.NUFAR_ClearExposedAreaFactor(); _legacyWingModels.Add(w); } - else if (p.Modules.Contains()) + else if (p.FindModuleImplementingFast() is FARControllableSurface c) { - FARWingAerodynamicModel w = p.Modules.GetModule(); - if (w is null) - continue; - w.isShielded = false; - w.NUFAR_ClearExposedAreaFactor(); - _legacyWingModels.Add(w); + c.isShielded = false; + c.NUFAR_ClearExposedAreaFactor(); + _legacyWingModels.Add(c); } } @@ -440,7 +435,7 @@ private Vector3 CalculateVehicleMainAxis() continue; // Could be left null if a launch clamp - var geoModule = p.Modules.GetModule(); + var geoModule = p.FindModuleImplementingFast(); hitParts.Add(p); @@ -448,9 +443,8 @@ private Vector3 CalculateVehicleMainAxis() Vector3 candVector = Vector3.zero; //intakes are probably pointing in the direction we're gonna be going in - if (p.Modules.Contains()) + if (p.FindModuleImplementingFast() is ModuleResourceIntake intake) { - var intake = p.Modules.GetModule(); Transform intakeTrans = p.FindModelTransform(intake.intakeTransformName); if (!(intakeTrans is null)) candVector = intakeTrans.TransformDirection(Vector3.forward); @@ -458,9 +452,9 @@ private Vector3 CalculateVehicleMainAxis() //aggregate wings for later calc... else if (geoModule == null || geoModule.IgnoreForMainAxis || - p.Modules.Contains() || - p.Modules.Contains() || - p.Modules.Contains() || + p.HasModuleImplementingFast() || + p.HasModuleImplementingFast() || + p.HasModuleImplementingFast() || p.Modules.Contains("KSPWheelBase")) { continue; @@ -500,10 +494,9 @@ private Vector3 CalculateVehicleMainAxis() hitParts.Add(q); //intakes are probably pointing in the direction we're gonna be going in - if (q.Modules.Contains()) + if (q.FindModuleImplementingFast() is ModuleResourceIntake intake2) { - var intake = q.Modules.GetModule(); - Transform intakeTrans = q.FindModelTransform(intake.intakeTransformName); + Transform intakeTrans = q.FindModelTransform(intake2.intakeTransformName); if (!(intakeTrans is null)) candVector += intakeTrans.TransformDirection(Vector3.forward); } @@ -1457,12 +1450,10 @@ private void CalculateVesselAeroProperties() if (key is null) continue; - if (!key.Modules.Contains()) + if (!(key.FindModuleImplementingFast() is FARAeroPartModule m)) continue; - var m = key.Modules.GetModule(); - if (!(m is null)) - includedModules.Add(m); + includedModules.Add(m); if (_moduleAndAreasDict.ContainsKey(m)) _moduleAndAreasDict[m] += areas; diff --git a/FerramAerospaceResearch/FARAeroComponents/VesselIntakeRamDrag.cs b/FerramAerospaceResearch/FARAeroComponents/VesselIntakeRamDrag.cs index dd78a3797..71b220b4e 100644 --- a/FerramAerospaceResearch/FARAeroComponents/VesselIntakeRamDrag.cs +++ b/FerramAerospaceResearch/FARAeroComponents/VesselIntakeRamDrag.cs @@ -44,6 +44,7 @@ You should have received a copy of the GNU General Public License using System; using System.Collections.Generic; +using KSPCommunityFixes; using UnityEngine; namespace FerramAerospaceResearch.FARAeroComponents @@ -83,10 +84,9 @@ public void UpdateAeroData(List allUsedAeroModules) continue; Part p = aeroModule.part; - foreach (PartModule m in p.Modules) + var intakeModules = p.FindModulesImplementingReadOnly(); + foreach (ModuleResourceIntake intake in intakeModules) { - if (!(m is ModuleResourceIntake intake)) - continue; if (intake.node != null && intake.node.attachedPart != null) continue; @@ -105,10 +105,9 @@ public void UpdateAeroData(List allUsedAeroModules) continue; Part p = aeroModule.part; - foreach (PartModule m in p.Modules) + var engineModules = p.FindModulesImplementingReadOnly(); + foreach (ModuleEngines e in engineModules) { - if (!(m is ModuleEngines e)) - continue; if (FARAeroUtil.AJELoaded) if (e.ClassID == AJE_JET_CLASS_ID || e.ClassID == AJE_PROP_CLASS_ID) { diff --git a/FerramAerospaceResearch/FARAeroUtil.cs b/FerramAerospaceResearch/FARAeroUtil.cs index 6c88cc72a..7a9abead6 100644 --- a/FerramAerospaceResearch/FARAeroUtil.cs +++ b/FerramAerospaceResearch/FARAeroUtil.cs @@ -47,6 +47,7 @@ You should have received a copy of the GNU General Public License using System.IO; using ferram4; using FerramAerospaceResearch.Settings; +using KSPCommunityFixes; using UnityEngine; namespace FerramAerospaceResearch @@ -366,7 +367,7 @@ public static double MachBehindShockCalc(double M) public static bool IsNonphysical(Part p) { return p.physicalSignificance == Part.PhysicalSignificance.NONE || - p.Modules.Contains() || + p.HasModuleImplementingFast() || HighLogic.LoadedSceneIsEditor && p != EditorLogic.RootPart && p.PhysicsSignificance == (int)Part.PhysicalSignificance.NONE; diff --git a/FerramAerospaceResearch/FARGUI/FAREditorGUI/EditorGUI.cs b/FerramAerospaceResearch/FARGUI/FAREditorGUI/EditorGUI.cs index a6762fe5b..f78f0ba73 100644 --- a/FerramAerospaceResearch/FARGUI/FAREditorGUI/EditorGUI.cs +++ b/FerramAerospaceResearch/FARGUI/FAREditorGUI/EditorGUI.cs @@ -56,6 +56,7 @@ You should have received a copy of the GNU General Public License using FerramAerospaceResearch.Resources; using KSP.Localization; using KSP.UI.Screens; +using KSPCommunityFixes; using ModuleWheels; using PreFlightTests; using UnityEngine; @@ -330,16 +331,14 @@ private void LEGACY_UpdateWingAeroModels(bool updateWingInteractions) { if (p == null) continue; - if (p.Modules.Contains()) + if (p.FindModuleImplementingFast() is FARWingAerodynamicModel w) { - FARWingAerodynamicModel w = p.Modules.GetModule(); if (updateWingInteractions) w.EditorUpdateWingInteractions(); _wingAerodynamicModel.Add(w); } - else if (p.Modules.Contains()) + else if (p.FindModuleImplementingFast() is FARControllableSurface c) { - FARControllableSurface c = p.Modules.GetModule(); if (updateWingInteractions) c.EditorUpdateWingInteractions(); _wingAerodynamicModel.Add(c); @@ -424,10 +423,7 @@ private void RecalculateVoxel() foreach (Part p in partList) { - if (!p.Modules.Contains()) - continue; - GeometryPartModule g = p.Modules.GetModule(); - if (g == null) + if (!(p.FindModuleImplementingFast() is GeometryPartModule g)) continue; if (g.Ready) { @@ -715,9 +711,8 @@ private void ToggleGear() List partsList = EditorLogic.SortedShipList; foreach (Part p in partsList) { - if (p.Modules.Contains()) + if (p.FindModuleImplementingFast() is ModuleWheelDeployment l) { - ModuleWheelDeployment l = p.Modules.GetModule(); l.ActionToggle(new KSPActionParam(KSPActionGroup.Gear, gearToggle ? KSPActionType.Activate : KSPActionType.Deactivate)); } diff --git a/FerramAerospaceResearch/FARGUI/FARFlightGUI/PhysicsCalcs.cs b/FerramAerospaceResearch/FARGUI/FARFlightGUI/PhysicsCalcs.cs index 84965f021..cbd350f1b 100644 --- a/FerramAerospaceResearch/FARGUI/FARFlightGUI/PhysicsCalcs.cs +++ b/FerramAerospaceResearch/FARGUI/FARFlightGUI/PhysicsCalcs.cs @@ -47,6 +47,7 @@ You should have received a copy of the GNU General Public License using ferram4; using FerramAerospaceResearch.FARAeroComponents; using KSP.UI.Screens.Flight; +using KSPCommunityFixes; using UnityEngine; using Object = UnityEngine.Object; @@ -276,28 +277,26 @@ private void CalculateEngineAndIntakeBasedParameters(double vesselSpeed) vesselInfo.dryMass += p.mass; } - foreach (PartModule m in p.Modules) - switch (m) + var engineModules = p.FindModulesImplementingReadOnly(); + foreach (ModuleEngines e in engineModules) + { + FuelConsumptionFromEngineModule(e, + ref totalThrust, + ref totalThrust_Isp, + ref fuelConsumptionVol, + ref airDemandVol, + invDeltaTime); + } + + var intakeModules = p.FindModulesImplementingReadOnly(); + foreach (ModuleResourceIntake intake in intakeModules) + { + if (intake.intakeEnabled) { - case ModuleEngines e: - FuelConsumptionFromEngineModule(e, - ref totalThrust, - ref totalThrust_Isp, - ref fuelConsumptionVol, - ref airDemandVol, - invDeltaTime); - break; - case ModuleResourceIntake intake: - { - if (intake.intakeEnabled) - { - airAvailableVol += intake.airFlow * intakeAirDensity / invDeltaTime; - vesselInfo.fullMass -= p.Resources[intake.resourceName].amount * intakeAirDensity; - } - - break; - } + airAvailableVol += intake.airFlow * intakeAirDensity / invDeltaTime; + vesselInfo.fullMass -= p.Resources[intake.resourceName].amount * intakeAirDensity; } + } } if (totalThrust > 0) diff --git a/FerramAerospaceResearch/FARPartGeometry/GeometryPartModule.cs b/FerramAerospaceResearch/FARPartGeometry/GeometryPartModule.cs index d30f03243..43ce581c8 100644 --- a/FerramAerospaceResearch/FARPartGeometry/GeometryPartModule.cs +++ b/FerramAerospaceResearch/FARPartGeometry/GeometryPartModule.cs @@ -52,6 +52,7 @@ You should have received a copy of the GNU General Public License using FerramAerospaceResearch.FARPartGeometry.GeometryModification; using FerramAerospaceResearch.Settings; using KSP.UI.Screens; +using KSPCommunityFixes; using TweakScale; using UnityEngine; @@ -240,14 +241,14 @@ public override void OnStart(StartState state) if (ignoreLayer0 < 0) ignoreLayer0 = LayerMask.NameToLayer("TransparentFX"); - GeometryPartModule modulePrefab = part.partInfo.partPrefab.FindModuleImplementing(); + GeometryPartModule modulePrefab = part.partInfo.partPrefab.FindModuleImplementingFast(); if (modulePrefab is not null) config = modulePrefab.config; if (part.collider == null && - !part.Modules.Contains() && - !part.Modules.Contains() && - !part.Modules.Contains()) + !part.HasModuleImplementingFast() && + !part.HasModuleImplementingFast() && + !part.HasModuleImplementingFast()) return; if (HighLogic.LoadedSceneIsEditor) @@ -490,28 +491,27 @@ private void SetupIGeometryUpdaters() geometryUpdaters.Add(compoundUpdate); } - if (part.Modules.Contains()) + if (part.FindModulesImplementingReadOnly() is List pmList && + pmList.Count > 0) { - List fairings = part.Modules.GetModules(); - foreach (ModuleProceduralFairing fairing in fairings) + foreach (ModuleProceduralFairing fairing in pmList) { var fairingUpdater = new StockProcFairingGeoUpdater(fairing, this); geometryUpdaters.Add(fairingUpdater); } } - if (part.Modules.Contains()) - + if (part.FindModulesImplementingReadOnly() is List pmList2 && + pmList2.Count > 0) { - List engineFairings = part.Modules.GetModules(); - foreach (ModuleJettison engineFairing in engineFairings) + foreach (ModuleJettison engineFairing in pmList2) { var fairingUpdater = new StockJettisonTransformGeoUpdater(engineFairing, this); geometryUpdaters.Add(fairingUpdater); } } - if (!part.Modules.Contains()) + if (!part.HasModuleImplementingFast()) return; var asteroidUpdater = new StockProcAsteroidGeoUpdater(this); geometryUpdaters.Add(asteroidUpdater); @@ -804,7 +804,7 @@ private MeshData GetVisibleMeshData(Transform t, bool skipIfNoRenderer, bool onl m = mf.sharedMesh; - if (part.Modules.Contains() || part.Modules.Contains()) + if (part.HasModuleImplementingFast() || part.HasModuleImplementingFast()) return new MeshData(m.vertices, m.triangles, m.bounds); return new MeshData(m.vertices, m.triangles, m.bounds); @@ -827,7 +827,7 @@ private List CreateMeshListFromTransforms(ref List meshTran var meshList = new List(); var validTransformList = new List(); - if (part.Modules.Contains() || part.Modules.Contains()) + if (part.HasModuleImplementingFast() || part.HasModuleImplementingFast()) { FARLogger.Info("Adding vox box to Kerbal / Flag"); meshList.Add(CreateBoxMeshForKerbalEVA()); @@ -841,10 +841,10 @@ private List CreateMeshListFromTransforms(ref List meshTran Bounds colliderBounds = part.GetPartColliderBoundsInBasis(worldToLocalMatrix); bool cantUseColliders = true; - bool isFairing = part.Modules.Contains() || + bool isFairing = part.HasModuleImplementingFast() || part.Modules.Contains("ProceduralFairingSide"); - bool isDrill = part.Modules.Contains() || - part.Modules.Contains(); + bool isDrill = part.HasModuleImplementingFast() || + part.HasModuleImplementingFast(); //Voxelize colliders if ((config.forceUseColliders || @@ -867,10 +867,10 @@ private List CreateMeshListFromTransforms(ref List meshTran } - if (part.Modules.Contains()) + if (part.FindModulesImplementingReadOnly() is List jettisons && + jettisons.Count > 0) { - bool variants = part.Modules.Contains(); - List jettisons = part.Modules.GetModules(); + bool variants = part.HasModuleImplementingFast(); var jettisonTransforms = new HashSet(); foreach (ModuleJettison j in jettisons) { diff --git a/FerramAerospaceResearch/FARPartGeometry/PartGeometryExtensions.cs b/FerramAerospaceResearch/FARPartGeometry/PartGeometryExtensions.cs index 641b6ac3b..a0117f05c 100644 --- a/FerramAerospaceResearch/FARPartGeometry/PartGeometryExtensions.cs +++ b/FerramAerospaceResearch/FARPartGeometry/PartGeometryExtensions.cs @@ -45,6 +45,7 @@ You should have received a copy of the GNU General Public License using System.Collections.Generic; using System.Reflection; using FerramAerospaceResearch.Settings; +using KSPCommunityFixes; using UnityEngine; namespace FerramAerospaceResearch.FARPartGeometry @@ -186,7 +187,7 @@ public static List PartModelTransformList(this Part p) returnList.AddRange(p.FindModelComponents()); - if (p.Modules.Contains()) + if (p.HasModuleImplementingFast()) ProceduralAsteroidTransforms(p, returnList); foreach (Transform t in ignoredModelTransforms) @@ -197,7 +198,7 @@ public static List PartModelTransformList(this Part p) private static void ProceduralAsteroidTransforms(Part p, List transformList) { - var asteroid = (ModuleAsteroid)p.Modules["ModuleAsteroid"]; + var asteroid = p.FindModuleImplementingFast(); FieldInfo[] fields = asteroid.GetType().GetFields(BindingFlags.NonPublic | BindingFlags.Instance); var procAsteroid = (PAsteroid)fields[2].GetValue(asteroid); diff --git a/FerramAerospaceResearch/FARPartGeometry/VehicleVoxel.cs b/FerramAerospaceResearch/FARPartGeometry/VehicleVoxel.cs index ea256fbc9..2038d2a06 100644 --- a/FerramAerospaceResearch/FARPartGeometry/VehicleVoxel.cs +++ b/FerramAerospaceResearch/FARPartGeometry/VehicleVoxel.cs @@ -50,6 +50,7 @@ You should have received a copy of the GNU General Public License using ferram4; using FerramAerospaceResearch.FARThreading; using FerramAerospaceResearch.Geometry; +using KSPCommunityFixes; using UnityEngine; namespace FerramAerospaceResearch.FARPartGeometry @@ -280,13 +281,13 @@ private static int PartPriorityLevel(GeometryPartModule g) if (g.HasCrossSectionAdjusters && g.MaxCrossSectionAdjusterArea > 0) return int.MaxValue; - if (modules.Contains("ProceduralFairingSide") || modules.Contains()) + if (modules.Contains("ProceduralFairingSide") || g.part.HasModuleImplementingFast()) return 3; if (modules.Contains("ProceduralFairingBase")) return 2; - if (modules.Contains() || - modules.Contains() || - modules.Contains()) + if (g.part.HasModuleImplementingFast() || + g.part.HasModuleImplementingFast() || + g.part.HasModuleImplementingFast()) return 1; return -1; diff --git a/FerramAerospaceResearch/FerramAerospaceResearch.csproj b/FerramAerospaceResearch/FerramAerospaceResearch.csproj index 3873eb24b..96636691f 100644 --- a/FerramAerospaceResearch/FerramAerospaceResearch.csproj +++ b/FerramAerospaceResearch/FerramAerospaceResearch.csproj @@ -65,6 +65,10 @@ False $(KSP_DIR_BUILD)\$(KSP_DATA_DIRNAME)\Managed\KSPAssets.dll + + $(KSP_DIR_BUILD)GameData\KSPCommunityFixes\Plugins\KSPCommunityFixes.dll + False + False $(KSP_DIR_BUILD)\GameData\ModularFlightIntegrator\ModularFlightIntegrator.dll diff --git a/FerramAerospaceResearch/LEGACYferram4/FARBaseAerodynamics.cs b/FerramAerospaceResearch/LEGACYferram4/FARBaseAerodynamics.cs index 60ae32122..a3a2d4fa7 100644 --- a/FerramAerospaceResearch/LEGACYferram4/FARBaseAerodynamics.cs +++ b/FerramAerospaceResearch/LEGACYferram4/FARBaseAerodynamics.cs @@ -45,6 +45,7 @@ You should have received a copy of the GNU General Public License using System.Collections.Generic; using FerramAerospaceResearch; using FerramAerospaceResearch.FARGUI.FAREditorGUI; +using KSPCommunityFixes; using UnityEngine; // ReSharper disable once CheckNamespace @@ -152,9 +153,11 @@ public static List GetAllEditorModules() var parts = new List(); foreach (Part p in EditorLogic.SortedShipList) - foreach (PartModule m in p.Modules) - if (m is FARBaseAerodynamics aerodynamics) - parts.Add(aerodynamics); + { + var modules = p.FindModulesImplementingReadOnly(); + foreach (FARBaseAerodynamics m in modules) + parts.Add(m); + } return parts; } diff --git a/FerramAerospaceResearch/LEGACYferram4/FARControllableSurface.cs b/FerramAerospaceResearch/LEGACYferram4/FARControllableSurface.cs index d44d26285..a4dffd90d 100644 --- a/FerramAerospaceResearch/LEGACYferram4/FARControllableSurface.cs +++ b/FerramAerospaceResearch/LEGACYferram4/FARControllableSurface.cs @@ -45,6 +45,7 @@ You should have received a copy of the GNU General Public License using System; using FerramAerospaceResearch; using FerramAerospaceResearch.Settings; +using KSPCommunityFixes; using UnityEngine; // ReSharper disable once CheckNamespace @@ -325,9 +326,9 @@ private void UpdateFlapDeflect() { foreach (Part p in part.symmetryCounterparts) { - foreach (PartModule m in p.Modules) - if (m is FARControllableSurface controllableSurface) - controllableSurface.SetDeflection(flapDeflectionLevel); + var modules = p.FindModulesImplementingReadOnly(); + foreach (FARControllableSurface controllableSurface in modules) + controllableSurface.SetDeflection(flapDeflectionLevel); } } @@ -413,8 +414,8 @@ public void UpdateEvents() public override void Initialization() { base.Initialization(); - if (part.Modules.GetModule()) - part.RemoveModule(part.Modules.GetModule()); + if (part.FindModuleImplementingFast() is ModuleControlSurface mcs) + part.RemoveModule(mcs); OnVesselPartsChange += CalculateSurfaceFunctions; UpdateEvents(); diff --git a/FerramAerospaceResearch/LEGACYferram4/FARPartModule.cs b/FerramAerospaceResearch/LEGACYferram4/FARPartModule.cs index 97dbf3cbf..720b6042a 100644 --- a/FerramAerospaceResearch/LEGACYferram4/FARPartModule.cs +++ b/FerramAerospaceResearch/LEGACYferram4/FARPartModule.cs @@ -45,6 +45,7 @@ You should have received a copy of the GNU General Public License using System; using System.Collections.Generic; using FerramAerospaceResearch; +using KSPCommunityFixes; using UnityEngine; // ReSharper disable once CheckNamespace @@ -85,10 +86,9 @@ public virtual void Initialization() public void TriggerPartColliderUpdate() { //Set up part collider list to easy runtime overhead with memory churning - foreach (PartModule m in part.Modules) + var modules = part.FindModulesImplementingReadOnly(); + foreach (FARPartModule farModule in modules) { - if (!(m is FARPartModule farModule)) - continue; if (farModule.partColliders == null) continue; partColliders = farModule.partColliders; diff --git a/FerramAerospaceResearch/LEGACYferram4/FARWingAerodynamicModel.cs b/FerramAerospaceResearch/LEGACYferram4/FARWingAerodynamicModel.cs index e296a4b1e..82889a4e5 100644 --- a/FerramAerospaceResearch/LEGACYferram4/FARWingAerodynamicModel.cs +++ b/FerramAerospaceResearch/LEGACYferram4/FARWingAerodynamicModel.cs @@ -48,6 +48,7 @@ You should have received a copy of the GNU General Public License using FerramAerospaceResearch.FARAeroComponents; using FerramAerospaceResearch.Settings; using KSP.Localization; +using KSPCommunityFixes; using TweakScale; using UnityEngine; @@ -226,7 +227,7 @@ public void NUFAR_ClearExposedAreaFactor() public void NUFAR_CalculateExposedAreaFactor() { - FARAeroPartModule a = part.Modules.GetModule(); + FARAeroPartModule a = part.FindModuleImplementingFast(); NUFAR_areaExposedFactor = Math.Min(a.ProjectedAreas.kN, a.ProjectedAreas.kP); NUFAR_totalExposedAreaFactor = Math.Max(a.ProjectedAreas.kN, a.ProjectedAreas.kP); @@ -244,8 +245,8 @@ public void NUFAR_SetExposedAreaFactor() if (p == null) continue; FARWingAerodynamicModel model = this is FARControllableSurface - ? p.Modules.GetModule() - : p.Modules.GetModule(); + ? p.FindModuleImplementingFast() + : p.FindModuleImplementingFast(); ++counterpartsCount; sum += model.NUFAR_areaExposedFactor; @@ -264,8 +265,8 @@ public void NUFAR_SetExposedAreaFactor() if (p == null) continue; FARWingAerodynamicModel model = this is FARControllableSurface - ? p.Modules.GetModule() - : p.Modules.GetModule(); + ? p.FindModuleImplementingFast() + : p.FindModuleImplementingFast(); model.NUFAR_areaExposedFactor = sum; model.NUFAR_totalExposedAreaFactor = totalExposedSum; diff --git a/FerramAerospaceResearch/RealChuteLite/ChuteCalculator.cs b/FerramAerospaceResearch/RealChuteLite/ChuteCalculator.cs index 4f595612c..435bbdde2 100644 --- a/FerramAerospaceResearch/RealChuteLite/ChuteCalculator.cs +++ b/FerramAerospaceResearch/RealChuteLite/ChuteCalculator.cs @@ -1,4 +1,5 @@ using System; +using KSPCommunityFixes; using UnityEngine; /* RealChuteLite is the work of Christophe Savard (stupid_chris), and is licensed the same way than the rest of FAR is. @@ -16,10 +17,9 @@ private void Start() foreach (AvailablePart part in PartLoader.Instance.loadedParts) { Part prefab = part.partPrefab; - if (prefab == null || !prefab.Modules.Contains()) + if (prefab == null || !(prefab.FindModuleImplementingFast() is RealChuteFAR module)) continue; //Updates the part's GetInfo. - RealChuteFAR module = prefab.Modules.GetModule(); DragCubeSystem.Instance.LoadDragCubes(prefab); DragCube semi = prefab.DragCubes.Cubes.Find(c => c.Name == "SEMIDEPLOYED"), deployed = prefab.DragCubes.Cubes.Find(c => c.Name == "DEPLOYED"); diff --git a/FerramAerospaceResearch/RealChuteLite/RealChuteFAR.cs b/FerramAerospaceResearch/RealChuteLite/RealChuteFAR.cs index 595ea3270..176657637 100644 --- a/FerramAerospaceResearch/RealChuteLite/RealChuteFAR.cs +++ b/FerramAerospaceResearch/RealChuteLite/RealChuteFAR.cs @@ -6,6 +6,7 @@ using FerramAerospaceResearch.PartExtensions; using KSP.Localization; using KSP.UI.Screens; +using KSPCommunityFixes; using UnityEngine; using Random = System.Random; @@ -594,8 +595,8 @@ public void GUIToggleWindow() { var parachutes = new List(); if (HighLogic.LoadedSceneIsEditor) - parachutes.AddRange(EditorLogic.SortedShipList.Where(p => p.Modules.Contains()) - .Select(p => p.Modules.GetModule())); + parachutes.AddRange(EditorLogic.SortedShipList.Where(p => p.HasModuleImplementingFast()) + .Select(p => p.FindModuleImplementingFast())); else if (HighLogic.LoadedSceneIsFlight) parachutes.AddRange(vessel.FindPartModulesImplementing()); if (parachutes.Count > 1 && parachutes.Exists(p => p.visible)) @@ -658,7 +659,7 @@ private void CopyToCounterparts() { foreach (Part p in part.symmetryCounterparts) { - var module = (RealChuteFAR)p.Modules["RealChuteFAR"]; + var module = p.FindModuleImplementingFast(); module.minAirPressureToOpen = minAirPressureToOpen; module.deployAltitude = deployAltitude; } @@ -1267,7 +1268,7 @@ public override void OnLoad(ConfigNode node) Part prefab = part.partInfo.partPrefab; massDelta = prefab == null ? 0 : TotalMass - prefab.mass; - shieldedCanDeploy = prefab.FindModuleImplementing().shieldedCanDeploy; + shieldedCanDeploy = prefab.FindModuleImplementingFast().shieldedCanDeploy; } public override void OnActive() diff --git a/FerramAerospaceResearch/Settings/FARAeroStress.cs b/FerramAerospaceResearch/Settings/FARAeroStress.cs index 48e312fb6..efdc96d79 100644 --- a/FerramAerospaceResearch/Settings/FARAeroStress.cs +++ b/FerramAerospaceResearch/Settings/FARAeroStress.cs @@ -1,5 +1,6 @@ using System.Collections.Generic; using FerramAerospaceResearch.Reflection; +using KSPCommunityFixes; namespace FerramAerospaceResearch.Settings { @@ -86,7 +87,7 @@ public static FARPartStressTemplate DetermineStressTemplate(Part p) int resCount = p.Resources.Count; bool crewed = p.CrewCapacity > 0; - if (p.Modules.Contains() || p.Resources.Contains("Ablator")) + if (p.HasModuleImplementingFast() || p.Resources.Contains("Ablator")) return template; foreach (FARPartStressTemplate candidate in StressTemplates)