diff --git a/project/SPT.SinglePlayer/Patches/RaidFix/EmptyInfilFixPatch.cs b/project/SPT.SinglePlayer/Patches/RaidFix/EmptyInfilFixPatch.cs new file mode 100644 index 0000000..c36d76c --- /dev/null +++ b/project/SPT.SinglePlayer/Patches/RaidFix/EmptyInfilFixPatch.cs @@ -0,0 +1,75 @@ +using System.Collections.Generic; +using System.Linq; +using System.Reflection; +using SPT.Reflection.Patching; +using SPT.Reflection.Utils; +using Comfort.Common; +using EFT; +using EFT.Game.Spawning; +using UnityEngine; + +namespace SPT.SinglePlayer.Patches.RaidFix +{ + /// + /// An empty EntryPoint string (string_0 in BaseLocalGame) causes exfil point initialization to be skipped. + /// This patch sets an EntryPoint string if it's missing. + /// + public class EmptyInfilFixPatch : ModulePatch + { + protected override MethodBase GetTargetMethod() + { + var desiredType = PatchConstants.LocalGameType.BaseType; + var desiredMethod = desiredType + .GetMethods(BindingFlags.Public | BindingFlags.Instance | BindingFlags.DeclaredOnly | BindingFlags.CreateInstance) + .SingleCustom(IsTargetMethod); + + Logger.LogDebug($"{this.GetType().Name} Type: {desiredType?.Name}"); + Logger.LogDebug($"{this.GetType().Name} Method: {desiredMethod?.Name}"); + + return desiredMethod; + } + + private static bool IsTargetMethod(MethodInfo methodInfo) + { + return (methodInfo.IsVirtual + && methodInfo.GetParameters().Length == 0 + && methodInfo.ReturnType == typeof(void) + && methodInfo.GetMethodBody().LocalVariables.Count > 0); + } + + [PatchPrefix] + public static void PatchPrefix(ref string ___string_0) + { + if (!string.IsNullOrWhiteSpace(___string_0)) return; + + var spawnPoints = Resources.FindObjectsOfTypeAll().ToList(); + + List filtered = new List(); + + foreach (var spawn in spawnPoints) + { + if (!string.IsNullOrEmpty(spawn?.SpawnPoint?.Infiltration?.Trim())) + { + filtered.Add(spawn); + } + } + + var playerPos = Singleton.Instance.MainPlayer.Transform.position; + SpawnPointMarker closestSpawn = null; + var minDist = Mathf.Infinity; + + foreach (var filter in filtered) + { + var dist = Vector3.Distance(filter.gameObject.transform.position, playerPos); + + if (dist < minDist) + { + closestSpawn = filter; + minDist = dist; + } + } + + ___string_0 = closestSpawn.SpawnPoint.Infiltration; + } + } +} \ No newline at end of file diff --git a/project/SPT.SinglePlayer/SPTSingleplayerPlugin.cs b/project/SPT.SinglePlayer/SPTSingleplayerPlugin.cs index 7d3a787..ddcfa00 100644 --- a/project/SPT.SinglePlayer/SPTSingleplayerPlugin.cs +++ b/project/SPT.SinglePlayer/SPTSingleplayerPlugin.cs @@ -20,7 +20,7 @@ namespace SPT.SinglePlayer { // TODO: check if these patches are needed new TinnitusFixPatch().Enable(); // Probably needed - //new EmptyInfilFixPatch().Enable(); + new EmptyInfilFixPatch().Enable(); new OverrideMaxAiAliveInRaidValuePatch().Enable(); //new PostRaidHealingPricePatch().Enable(); // Client handles this now //new HideoutQuestIgnorePatch().Enable(); // Was only needed because FixQuestAchieveControllersPatch was causing issues