diff --git a/NewHorizons/Builder/Props/ProjectionBuilder.cs b/NewHorizons/Builder/Props/ProjectionBuilder.cs index 8d9eaca6..1a406d2b 100644 --- a/NewHorizons/Builder/Props/ProjectionBuilder.cs +++ b/NewHorizons/Builder/Props/ProjectionBuilder.cs @@ -1,4 +1,5 @@ using HarmonyLib; +using NewHorizons.Components.EOTE; using NewHorizons.External.Modules.Props; using NewHorizons.External.Modules.Props.EchoesOfTheEye; using NewHorizons.Handlers; @@ -137,7 +138,10 @@ namespace NewHorizons.Builder.Props slideReel.SetSector(sector); slideReel.SetVisible(true); - var slideCollectionContainer = slideReelObj.GetRequiredComponent(); + var toDestroy = slideReelObj.GetComponent(); + var slideCollectionContainer = slideReelObj.AddComponent(); + slideReel._slideCollectionContainer = slideCollectionContainer; + Component.DestroyImmediate(toDestroy); foreach (var renderer in slideReelObj.GetComponentsInChildren()) { @@ -342,7 +346,10 @@ namespace NewHorizons.Builder.Props var autoProjector = projectorObj.GetComponent(); autoProjector._sector = sector; - var slideCollectionContainer = autoProjector.GetRequiredComponent(); + var toDestroy = autoProjector.GetComponent(); + var slideCollectionContainer = autoProjector.gameObject.AddComponent(); + autoProjector._slideCollectionItem = slideCollectionContainer; + Component.DestroyImmediate(toDestroy); // Now we replace the slides int slidesCount = info.slides.Length; @@ -419,7 +426,7 @@ namespace NewHorizons.Builder.Props // attach a component to store all the data for the slides that play when a vision torch scans this target var target = g.AddComponent(); - var slideCollectionContainer = g.AddComponent(); + var slideCollectionContainer = g.AddComponent(); slideCollectionContainer.slideCollection = slideCollection; target.slideCollection = g.AddComponent(); target.slideCollection._slideCollectionContainer = slideCollectionContainer; @@ -486,7 +493,7 @@ namespace NewHorizons.Builder.Props ); // Set up the containers for the slides - var slideCollectionContainer = standingTorch.AddComponent(); + var slideCollectionContainer = standingTorch.AddComponent(); slideCollectionContainer.slideCollection = slideCollection; var mindSlideCollection = standingTorch.AddComponent(); @@ -658,12 +665,15 @@ namespace NewHorizons.Builder.Props Slide.WriteModules(modules, ref slide._modulesList, ref slide._modulesData, ref slide.lengths); } - private static void LinkShipLogFacts(ProjectionInfo info, SlideCollectionContainer slideCollectionContainer) + private static void LinkShipLogFacts(ProjectionInfo info, NHSlideCollectionContainer slideCollectionContainer) { // Idk why but it wants reveals to be comma delimited not a list if (info.reveals != null) slideCollectionContainer._shipLogOnComplete = string.Join(",", info.reveals); // Don't use null value, NRE in SlideCollectionContainer.Initialize slideCollectionContainer._playWithShipLogFacts = info.playWithShipLogFacts ?? Array.Empty(); + + slideCollectionContainer.conditionsToSet = info.conditionsToSet; + slideCollectionContainer.persistentConditionsToSet = info.persistentConditionsToSet; } } diff --git a/NewHorizons/Builder/ShipLog/MapModeBuilder.cs b/NewHorizons/Builder/ShipLog/MapModeBuilder.cs index c51ece61..6f0e9636 100644 --- a/NewHorizons/Builder/ShipLog/MapModeBuilder.cs +++ b/NewHorizons/Builder/ShipLog/MapModeBuilder.cs @@ -440,6 +440,11 @@ namespace NewHorizons.Builder.ShipLog private static MapModeObject ConstructPrimaryNode(List bodies) { + float DistanceFromPrimary(NewHorizonsBody body) + { + return Mathf.Max(body.Config.Orbit.semiMajorAxis, body.Config.Orbit.staticPosition?.Length() ?? 0f); + } + foreach (NewHorizonsBody body in bodies.Where(b => b.Config.Base.centerOfSolarSystem)) { bodies.Sort((b, o) => b.Config.Orbit.semiMajorAxis.CompareTo(o.Config.Orbit.semiMajorAxis)); diff --git a/NewHorizons/Components/EOTE/NHSlideCollectionContainer.cs b/NewHorizons/Components/EOTE/NHSlideCollectionContainer.cs new file mode 100644 index 00000000..bcf979ec --- /dev/null +++ b/NewHorizons/Components/EOTE/NHSlideCollectionContainer.cs @@ -0,0 +1,62 @@ +using HarmonyLib; + +namespace NewHorizons.Components.EOTE; + +[HarmonyPatch(typeof(SlideCollectionContainer))] +public class NHSlideCollectionContainer : SlideCollectionContainer +{ + public string[] conditionsToSet; + public string[] persistentConditionsToSet; + + [HarmonyPrefix] + [HarmonyPatch(typeof(SlideCollectionContainer), nameof(SlideCollectionContainer.Initialize))] + public static bool SlideCollectionContainer_Initialize(SlideCollectionContainer __instance) + { + if (__instance is NHSlideCollectionContainer) + { + if (__instance._initialized) + return false; + __instance.SetupReadFlags(); + __instance.RegisterPerSlideCompletion(); + if (__instance.streamingTexturesAvailable) + __instance.SetupStreaming(); + __instance.BuildMusicRangesIndex(); + __instance._changeSlidesAllowed = true; + __instance._initialized = true; + __instance._slideCollection.isVision = __instance._owningItem == null; + foreach (var factID in __instance._playWithShipLogFacts) + { + var fact = Locator.GetShipLogManager().GetFact(factID); + fact?.RegisterSlideCollection(__instance._slideCollection); + } + return false; + } + return true; + } + + [HarmonyPostfix] + [HarmonyPatch(typeof(SlideCollectionContainer), nameof(SlideCollectionContainer.SetReadFlag))] + public static void SlideCollectionContainer_SetReadFlag(SlideCollectionContainer __instance) + { + if (__instance is NHSlideCollectionContainer container) + { + if (container._unreadSlideIndices.Count == 0) + { + if (container.conditionsToSet != null) + { + foreach (var condition in container.conditionsToSet) + { + DialogueConditionManager.SharedInstance.SetConditionState(condition, true); + } + } + if (container.persistentConditionsToSet != null) + { + foreach (var condition in container.persistentConditionsToSet) + { + PlayerData.SetPersistentCondition(condition, true); + } + } + } + } + } +} diff --git a/NewHorizons/External/Configs/PlanetConfig.cs b/NewHorizons/External/Configs/PlanetConfig.cs index 6119e1a6..1989ffdc 100644 --- a/NewHorizons/External/Configs/PlanetConfig.cs +++ b/NewHorizons/External/Configs/PlanetConfig.cs @@ -287,6 +287,14 @@ namespace NewHorizons.External.Configs // Disable map marker for dream dimensions if (Dream != null && Dream.inDreamWorld) MapMarker.enabled = false; + + // User error #983 + // This will not catch if they wrote the two names slightly differently but oh well don't be stupid + // Ideally we should just check for loops in PlanetGraph + if (Orbit.primaryBody == name) + { + throw new Exception($"You set {name} to orbit itself, that is invalid. The planet will not load."); + } } public void Migrate() diff --git a/NewHorizons/External/Modules/Props/EchoesOfTheEye/ProjectionInfo.cs b/NewHorizons/External/Modules/Props/EchoesOfTheEye/ProjectionInfo.cs index ba6a98d4..c61ef06b 100644 --- a/NewHorizons/External/Modules/Props/EchoesOfTheEye/ProjectionInfo.cs +++ b/NewHorizons/External/Modules/Props/EchoesOfTheEye/ProjectionInfo.cs @@ -48,6 +48,16 @@ namespace NewHorizons.External.Modules.Props.EchoesOfTheEye /// public string[] reveals; + /// + /// The dialogue conditions to set after finishing this slide reel. + /// + public string[] conditionsToSet; + + /// + /// The persistent conditions to set after finishing this slide reel. + /// + public string[] persistentConditionsToSet; + /// /// The ship log facts that make the reel play when they are displayed in the computer (by selecting entries or arrows). /// You should probably include facts from `reveals` here. diff --git a/NewHorizons/External/SerializableData/MVector3.cs b/NewHorizons/External/SerializableData/MVector3.cs index 33100bc1..f61cb87b 100644 --- a/NewHorizons/External/SerializableData/MVector3.cs +++ b/NewHorizons/External/SerializableData/MVector3.cs @@ -27,6 +27,8 @@ namespace NewHorizons.External.SerializableData return new Vector3(vec.x, vec.y, vec.z); } + public float Length() => Mathf.Sqrt(x * x + y * y + z * z); + public override string ToString() => $"{x}, {y}, {z}"; } } diff --git a/NewHorizons/Patches/ShipLogPatches/SlideCollectionContainerPatches.cs b/NewHorizons/Patches/ShipLogPatches/SlideCollectionContainerPatches.cs deleted file mode 100644 index d3c4cae7..00000000 --- a/NewHorizons/Patches/ShipLogPatches/SlideCollectionContainerPatches.cs +++ /dev/null @@ -1,30 +0,0 @@ -using HarmonyLib; - -namespace NewHorizons.Patches.ShipLogPatches -{ - [HarmonyPatch(typeof(SlideCollectionContainer))] - public static class SlideCollectionContainerPatches - { - [HarmonyPrefix] - [HarmonyPatch(typeof(SlideCollectionContainer), nameof(SlideCollectionContainer.Initialize))] - public static bool SlideCollectionContainer_Initialize(SlideCollectionContainer __instance) - { - if (__instance._initialized) - return false; - __instance.SetupReadFlags(); - __instance.RegisterPerSlideCompletion(); - if (__instance.streamingTexturesAvailable) - __instance.SetupStreaming(); - __instance.BuildMusicRangesIndex(); - __instance._changeSlidesAllowed = true; - __instance._initialized = true; - __instance._slideCollection.isVision = __instance._owningItem == null; - foreach (var factID in __instance._playWithShipLogFacts) - { - var fact = Locator.GetShipLogManager().GetFact(factID); - fact?.RegisterSlideCollection(__instance._slideCollection); - } - return false; - } - } -} \ No newline at end of file diff --git a/NewHorizons/Schemas/body_schema.json b/NewHorizons/Schemas/body_schema.json index b8489188..616b0ea2 100644 --- a/NewHorizons/Schemas/body_schema.json +++ b/NewHorizons/Schemas/body_schema.json @@ -2263,6 +2263,20 @@ "type": "string" } }, + "conditionsToSet": { + "type": "array", + "description": "The dialogue conditions to set after finishing this slide reel.", + "items": { + "type": "string" + } + }, + "persistentConditionsToSet": { + "type": "array", + "description": "The persistent conditions to set after finishing this slide reel.", + "items": { + "type": "string" + } + }, "playWithShipLogFacts": { "type": "array", "description": "The ship log facts that make the reel play when they are displayed in the computer (by selecting entries or arrows).\nYou should probably include facts from `reveals` here.\nIf you only specify a rumor fact, then it would only play in its ship log entry if this has revealed only\nrumor facts because an entry with revealed explore facts doesn't display rumor facts.",