Decompiled source of TOA Heavy Industries v1.1.74
BeplnEx/plugins/TOA Heavy Industries/Custom/Net.6/TOA_Heavy_Industries_2.2.0.dll
Decompiled a week ago
The result has been truncated due to the large size, download it to view full contents!
using System; using System.Collections; using System.Collections.Generic; using System.Diagnostics; using System.Globalization; using System.IO; using System.Linq; using System.Reflection; using System.Runtime.CompilerServices; using System.Runtime.InteropServices; using System.Runtime.Versioning; using System.Security; using System.Security.Permissions; using System.Text; using System.Text.Json; using System.Text.Json.Nodes; using System.Text.Json.Serialization; using System.Text.RegularExpressions; using System.Threading; using AIGraph; using Agents; using BepInEx; using BepInEx.Bootstrap; using BepInEx.Core.Logging.Interpolation; using BepInEx.Logging; using BepInEx.Unity.IL2CPP; using BepInEx.Unity.IL2CPP.Utils.Collections; using CellMenu; using ChainedPuzzles; using EOSExt.TacticalBigPickup.Definitions.Generic.BigPickup.Definition; using EOSExt.TacticalBigPickup.FogBeacon.Generic; using EOSExt.TacticalBigPickup.Functions.FogBeacon.BigPickup; using EOSExt.TacticalBigPickup.Functions.FogBeacon.LevelSpawned; using EOSExt.TacticalBigPickup.Functions.Generic.BigPickup; using EOSExt.TacticalBigPickup.Functions.Generic.BigPickup.Definition; using EOSExt.TacticalBigPickup.Impl; using EOSExt.TacticalBigPickup.Impl.FogBeacon.LeveSpawned; using EOSExt.TacticalBigPickup.Managers; using Enemies; using ExtraObjectiveSetup; using ExtraObjectiveSetup.BaseClasses; using ExtraObjectiveSetup.ExtendedWardenEvents; using ExtraObjectiveSetup.JSON; using ExtraObjectiveSetup.Utils; using FloLib.Networks.Replications; using GTFO.API; using GTFO.API.Extensions; using GTFO.API.Utilities; using GameData; using Gear; using HarmonyLib; using Il2CppInterop.Runtime.Injection; using Il2CppInterop.Runtime.InteropTypes; using Il2CppInterop.Runtime.InteropTypes.Arrays; using Il2CppSystem; using Il2CppSystem.Collections.Generic; using LevelGeneration; using Localization; using Microsoft.CodeAnalysis; using Player; using SNetwork; using ScanPosOverride.Managers; using StateMachines; using TMPro; using TOA_Heavy_Industries; using UnityEngine; using UnityEngine.Rendering; [assembly: CompilationRelaxations(8)] [assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)] [assembly: Debuggable(DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints)] [assembly: TargetFramework(".NETCoreApp,Version=v6.0", FrameworkDisplayName = ".NET 6.0")] [assembly: AssemblyCompany("TOA_Heavy_Industries")] [assembly: AssemblyConfiguration("Release")] [assembly: AssemblyFileVersion("2.2.0.0")] [assembly: AssemblyInformationalVersion("2.2.0")] [assembly: AssemblyProduct("TOA_Heavy_Industries")] [assembly: AssemblyTitle("TOA_Heavy_Industries")] [assembly: SecurityPermission(SecurityAction.RequestMinimum, SkipVerification = true)] [assembly: AssemblyVersion("2.2.0.0")] [module: UnverifiableCode] namespace Microsoft.CodeAnalysis { [CompilerGenerated] [Embedded] internal sealed class EmbeddedAttribute : Attribute { } } namespace System.Runtime.CompilerServices { [CompilerGenerated] [Embedded] [AttributeUsage(AttributeTargets.Class | AttributeTargets.Property | AttributeTargets.Field | AttributeTargets.Event | AttributeTargets.Parameter | AttributeTargets.ReturnValue | AttributeTargets.GenericParameter, AllowMultiple = false, Inherited = false)] internal sealed class NullableAttribute : Attribute { public readonly byte[] NullableFlags; public NullableAttribute(byte P_0) { NullableFlags = new byte[1] { P_0 }; } public NullableAttribute(byte[] P_0) { NullableFlags = P_0; } } [CompilerGenerated] [Embedded] [AttributeUsage(AttributeTargets.Class | AttributeTargets.Struct | AttributeTargets.Method | AttributeTargets.Interface | AttributeTargets.Delegate, AllowMultiple = false, Inherited = false)] internal sealed class NullableContextAttribute : Attribute { public readonly byte Flag; public NullableContextAttribute(byte P_0) { Flag = P_0; } } } namespace EOSExt.TacticalBigPickup.Patches { [HarmonyPatch] internal static class FixLevelSpawnedFogBeaconRange { [HarmonyPostfix] [HarmonyPatch(typeof(HeavyFogRepellerGlobalState), "AttemptInteract")] private static void Post_HeavyFogRepellerGlobalState_AttemptInteract(HeavyFogRepellerGlobalState __instance) { LevelSpawnedFogBeaconSettings lSFBDef = LevelSpawnedFogBeaconSettingManager.Current.GetLSFBDef(__instance); if (lSFBDef != null) { __instance.m_repellerSphere.Range = lSFBDef.Range; } } } [HarmonyPatch] public static class SetupBigPickupItemWithItemId { public const string BIG_PICKUP_FOG_BEACON_NAME = "Carry_FogBeacon - ConstantFog"; public const string BIG_PICKUP_OBSERVER_NAME = "Carry_Observer"; [HarmonyPostfix] [HarmonyPatch(typeof(LG_PickupItem), "SetupBigPickupItemWithItemId")] private static void Post_Setup(LG_PickupItem __instance, uint itemId) { BigPickupItemManager.Current.Register(__instance); } } } namespace EOSExt.TacticalBigPickup.FogBeacon.Generic { public abstract class TOAGenericDefinitionManager<T> where T : new() { protected readonly Dictionary<uint, GenericDefinition<T>> definitions = new Dictionary<uint, GenericDefinition<T>>(); protected abstract string DEFINITION_NAME { get; } protected string DEFINITION_PATH { get; } protected TOAGenericDefinitionManager() { //IL_0061: Unknown result type (might be due to invalid IL or missing references) //IL_006b: Expected O, but got Unknown DEFINITION_PATH = Path.Combine(TOAConfigPaths.GetCustomPath(), "TOA_Heavy_Industries", "FogBeacon", DEFINITION_NAME); Directory.CreateDirectory(DEFINITION_PATH); EnsureTemplate(); LoadDefinitions(); LiveEdit.CreateListener(DEFINITION_PATH, "*.json", true).FileChanged += new LiveEditEventHandler(FileChanged); } private void EnsureTemplate() { string path = Path.Combine(DEFINITION_PATH, "Template.json"); if (!File.Exists(path)) { File.WriteAllText(path, EOSJson.Serialize<GenericDefinition<T>>(new GenericDefinition<T>())); } } private void LoadDefinitions() { foreach (string item in Directory.EnumerateFiles(DEFINITION_PATH, "*.json", SearchOption.AllDirectories)) { try { AddDefinitions(EOSJson.Deserialize<GenericDefinition<T>>(File.ReadAllText(item))); } catch (Exception value) { EOSLogger.Error($"TOA Fog Beacon definition load failed for '{item}': {value}"); } } } private void FileChanged(LiveEditEventArgs e) { EOSLogger.Warning("LiveEdit File Changed: " + e.FullPath); LiveEdit.TryReadFileContent(e.FullPath, (Action<string>)delegate(string content) { AddDefinitions(EOSJson.Deserialize<GenericDefinition<T>>(content)); }); } private void AddDefinitions(GenericDefinition<T> definition) { if (definition != null) { definitions[definition.ID] = definition; } } public GenericDefinition<T> GetDefinition(uint id) { if (!definitions.TryGetValue(id, out GenericDefinition<T> value)) { return null; } return value; } public virtual void Init() { } } public abstract class TOAExpeditionDefinitionManager<T> where T : new() { protected readonly Dictionary<uint, GenericExpeditionDefinition<T>> definitions = new Dictionary<uint, GenericExpeditionDefinition<T>>(); protected abstract string DEFINITION_NAME { get; } protected string DEFINITION_PATH { get; } protected TOAExpeditionDefinitionManager() { //IL_0061: Unknown result type (might be due to invalid IL or missing references) //IL_006b: Expected O, but got Unknown DEFINITION_PATH = Path.Combine(TOAConfigPaths.GetCustomPath(), "TOA_Heavy_Industries", "FogBeacon", DEFINITION_NAME); Directory.CreateDirectory(DEFINITION_PATH); EnsureTemplate(); LoadDefinitions(); LiveEdit.CreateListener(DEFINITION_PATH, "*.json", true).FileChanged += new LiveEditEventHandler(FileChanged); } private void EnsureTemplate() { string path = Path.Combine(DEFINITION_PATH, "Template.json"); if (!File.Exists(path)) { File.WriteAllText(path, EOSJson.Serialize<GenericExpeditionDefinition<T>>(new GenericExpeditionDefinition<T>())); } } private void LoadDefinitions() { foreach (string item in Directory.EnumerateFiles(DEFINITION_PATH, "*.json", SearchOption.AllDirectories)) { try { AddDefinitions(EOSJson.Deserialize<GenericExpeditionDefinition<T>>(File.ReadAllText(item))); } catch (Exception value) { EOSLogger.Error($"TOA Fog Beacon definition load failed for '{item}': {value}"); } } } private void FileChanged(LiveEditEventArgs e) { EOSLogger.Warning("LiveEdit File Changed: " + e.FullPath); LiveEdit.TryReadFileContent(e.FullPath, (Action<string>)delegate(string content) { AddDefinitions(EOSJson.Deserialize<GenericExpeditionDefinition<T>>(content)); }); } private void AddDefinitions(GenericExpeditionDefinition<T> definition) { if (definition != null) { definitions[definition.MainLevelLayout] = definition; } } public GenericExpeditionDefinition<T> GetDefinition(uint levelLayout) { if (!definitions.TryGetValue(levelLayout, out GenericExpeditionDefinition<T> value)) { return null; } return value; } public virtual void Init() { } } } namespace EOSExt.TacticalBigPickup.Definitions.Generic.BigPickup.Definition { public class BigPickupFunction { public string Type { get; set; } = string.Empty; public uint SettingID { get; set; } } } namespace EOSExt.TacticalBigPickup.Managers { public class BigPickupItemManager : PickupItemManager<CarryItemPickup_Core> { public static BigPickupItemManager Current { get; } private BigPickupItemManager() { } static BigPickupItemManager() { Current = new BigPickupItemManager(); } } internal static class ItemInLevelUtils { internal static (eDimensionIndex dim, LG_LayerType layer, eLocalZoneIndex localIndex) GetGlobalZoneIndex(this ItemInLevel item) { //IL_0001: Unknown result type (might be due to invalid IL or missing references) //IL_0006: Unknown result type (might be due to invalid IL or missing references) //IL_001d: Unknown result type (might be due to invalid IL or missing references) //IL_0023: Unknown result type (might be due to invalid IL or missing references) //IL_002e: Unknown result type (might be due to invalid IL or missing references) pItemData pItemData = ((Item)item).pItemData; AIG_CourseNode val = default(AIG_CourseNode); if (((pCourseNode)(ref pItemData.originCourseNode)).TryGet(ref val)) { return (dim: val.m_dimension.DimensionIndex, layer: val.LayerType, localIndex: val.m_zone.LocalIndex); } throw new NullReferenceException("originCourseNode is null"); } internal static LG_PickupItem GetLGPickupItem(this ItemInLevel item) { return ((Component)item).GetComponentInParent<LG_PickupItem>(); } } public abstract class PickupItemManager<T> where T : ItemInLevel { protected Dictionary<uint, List<T>> RegisteredItems { get; private set; } = new Dictionary<uint, List<T>>(); public virtual void Register(LG_PickupItem item) { T componentInChildren = ((Component)item.m_root).GetComponentInChildren<T>(); Register(componentInChildren); } public virtual void Register(T item) { ItemDataBlock itemDataBlock = ((Item)(object)item).ItemDataBlock; if (!RegisteredItems.TryGetValue(((GameDataBlockBase<ItemDataBlock>)(object)itemDataBlock).persistentID, out List<T> value)) { value = new List<T>(); RegisteredItems[((GameDataBlockBase<ItemDataBlock>)(object)itemDataBlock).persistentID] = value; } value.Add(item); } public virtual Dictionary<(eDimensionIndex dim, LG_LayerType layer, eLocalZoneIndex localIndex), List<T>> GetItemsOf(uint itemId) { if (!RegisteredItems.TryGetValue(itemId, out List<T> value)) { return null; } return (from item in value group item by ((ItemInLevel)(object)item).GetGlobalZoneIndex()).ToDictionary((IGrouping<(eDimensionIndex dim, LG_LayerType layer, eLocalZoneIndex localIndex), T> g) => g.Key, (IGrouping<(eDimensionIndex dim, LG_LayerType layer, eLocalZoneIndex localIndex), T> g) => g.ToList()); } protected virtual void OnBuildDone() { } protected virtual void Clear() { RegisteredItems.Clear(); } protected PickupItemManager() { LevelAPI.OnBuildDone += OnBuildDone; LevelAPI.OnBuildStart += Clear; LevelAPI.OnLevelCleanup += Clear; } static PickupItemManager() { } } } namespace EOSExt.TacticalBigPickup.Functions.Generic.BigPickup { public class BigPickupCustomHelper : MonoBehaviour { private Dictionary<ePickupItemStatus, List<WardenObjectiveEventData>> eventsOnState = new Dictionary<ePickupItemStatus, List<WardenObjectiveEventData>>(); public ItemInLevel Item { get; private set; } private void Setup(ItemInLevel item) { Item = item; item.GetSyncComponent().OnSyncStateChange += Action<ePickupItemStatus, pPickupPlacement, PlayerAgent, bool>.op_Implicit((Action<ePickupItemStatus, pPickupPlacement, PlayerAgent, bool>)OnSyncStateChange); } public bool TryGetEvents(ePickupItemStatus state, out List<WardenObjectiveEventData> events) { //IL_0006: Unknown result type (might be due to invalid IL or missing references) return eventsOnState.TryGetValue(state, out events); } private void OnSyncStateChange(ePickupItemStatus state, pPickupPlacement placement, PlayerAgent player, bool isRecall) { //IL_000d: Unknown result type (might be due to invalid IL or missing references) //IL_0050: Unknown result type (might be due to invalid IL or missing references) if (!isRecall && SNet.IsMaster && TryGetEvents(state, out List<WardenObjectiveEventData> events)) { EOSLogger.Log($"item {((Item)Item).PublicName} on state {state}, executing {events.Count} events"); WardenObjectiveManager.CheckAndExecuteEventsOnTrigger(ListExtensions.ToIl2Cpp<WardenObjectiveEventData>(events), (eWardenObjectiveEventTrigger)0, true, 0f, (Il2CppStructArray<eWardenObjectiveEventType>)null); } } private void OnDestroy() { eventsOnState.Clear(); eventsOnState = null; } private BigPickupCustomHelper() { } public static void Setup(ItemInLevel item, BigPickupCustomization states) { //IL_0045: Unknown result type (might be due to invalid IL or missing references) //IL_0060: Unknown result type (might be due to invalid IL or missing references) BigPickupCustomHelper bigPickupCustomHelper = ((Component)item).gameObject.GetComponent<BigPickupCustomHelper>(); if ((Object)(object)bigPickupCustomHelper == (Object)null) { bigPickupCustomHelper = ((Component)item).gameObject.AddComponent<BigPickupCustomHelper>(); bigPickupCustomHelper.Setup(item); } foreach (BigPickupStateEvent item2 in states.OnState) { if (!bigPickupCustomHelper.eventsOnState.TryGetValue(item2.State, out List<WardenObjectiveEventData> value)) { value = new List<WardenObjectiveEventData>(); bigPickupCustomHelper.eventsOnState[item2.State] = value; } value.AddRange(item2.EventsOnState); } } static BigPickupCustomHelper() { ClassInjector.RegisterTypeInIl2Cpp<BigPickupCustomHelper>(); } } public class BigPickupCustomizationManager : TOAExpeditionDefinitionManager<BigPickups> { public static BigPickupCustomizationManager Current { get; } = new BigPickupCustomizationManager(); protected override string DEFINITION_NAME => "BigPickupCustomization"; private void Build(BigPickups def) { Dictionary<(eDimensionIndex, LG_LayerType, eLocalZoneIndex), List<CarryItemPickup_Core>> itemsOf = BigPickupItemManager.Current.GetItemsOf(def.ItemId); foreach (BigPickupCustomization bigPickupItem in def.BigPickupItems) { if (!itemsOf.TryGetValue(((GlobalZoneIndex)bigPickupItem).GlobalZoneIndexTuple(), out var value)) { EOSLogger.Error($"EventsOnBigPickup: zone not found {((GlobalZoneIndex)bigPickupItem).GlobalZoneIndexTuple()}"); } else if (bigPickupItem.Index < 0 || bigPickupItem.Index >= value.Count) { EOSLogger.Error($"EventsOnBigPickup: itemID {def.ItemId}, index {bigPickupItem.Index} is invalid - there're {value.Count} items in {((GlobalZoneIndex)bigPickupItem).GlobalZoneIndexTuple()} - valid value falls in range [0, {value.Count - 1})"); } else { CarryItemPickup_Core item = value[bigPickupItem.Index]; BigPickupCustomHelper.Setup((ItemInLevel)(object)item, bigPickupItem); CustomBigPickupFunctionImplementor.SetupCustomBigPickupFunctions(((ItemInLevel)(object)item).GetLGPickupItem(), bigPickupItem.Functions); } } } private void Build() { if (definitions.TryGetValue(RundownManager.ActiveExpedition.LevelLayoutData, out GenericExpeditionDefinition<BigPickups> value)) { value.Definitions.ForEach(Build); } } public BigPickupCustomizationManager() { LevelAPI.OnBuildDone += Build; } } } namespace EOSExt.TacticalBigPickup.Functions.Generic.BigPickup.Definition { public class BigPickupCustomization : GlobalZoneIndex { public int Index { get; set; } public List<BigPickupFunction> Functions { get; set; } = new List<BigPickupFunction> { new BigPickupFunction() }; public List<BigPickupStateEvent> OnState { get; set; } = new List<BigPickupStateEvent> { new BigPickupStateEvent() }; } public class BigPickups { public uint ItemId { get; set; } public List<BigPickupCustomization> BigPickupItems { get; set; } = new List<BigPickupCustomization> { new BigPickupCustomization() }; } public class BigPickupStateEvent { public ePickupItemStatus State { get; set; } public List<WardenObjectiveEventData> EventsOnState { get; set; } = new List<WardenObjectiveEventData>(); } } namespace EOSExt.TacticalBigPickup.Functions.FogBeacon.LevelSpawned { public class LevelSpawnedFogBeaconSettings { public int AreaIndex { get; set; } public float GrowDuration { get; set; } = 10f; public float ShrinkDuration { get; set; } = 10f; public float Range { get; set; } = 11f; public string WorldEventObjectFilter { get; set; } = string.Empty; public Vec3 Position { get; set; } = new Vec3(); } public class LevelSpawnedFogBeaconDefinition : GlobalZoneIndex { public List<LevelSpawnedFogBeaconSettings> SpawnedBeaconsInZone { get; set; } = new List<LevelSpawnedFogBeaconSettings> { new LevelSpawnedFogBeaconSettings() }; } public class LevelSpawnedFogBeaconSettingManager : TOAExpeditionDefinitionManager<LevelSpawnedFogBeaconDefinition> { public enum LSFBEvent { ToggleLevelSpawnedFogBeaconState = 922 } private Dictionary<IntPtr, LevelSpawnedFogBeaconSettings> LSFBGlobalStatesSet = new Dictionary<IntPtr, LevelSpawnedFogBeaconSettings>(); public static LevelSpawnedFogBeaconSettingManager Current { get; } protected override string DEFINITION_NAME => "LevelSpawnedFogBeacon_EOS"; private Dictionary<string, LevelSpawnedFogBeacon> LevelSpawnedFogBeacons { get; } = new Dictionary<string, LevelSpawnedFogBeacon>(); private void Build(LevelSpawnedFogBeaconDefinition def) { //IL_0066: Unknown result type (might be due to invalid IL or missing references) //IL_006c: Unknown result type (might be due to invalid IL or missing references) //IL_0072: Unknown result type (might be due to invalid IL or missing references) foreach (LevelSpawnedFogBeaconSettings item in def.SpawnedBeaconsInZone) { if (item.WorldEventObjectFilter == null || item.WorldEventObjectFilter == string.Empty || LevelSpawnedFogBeacons.ContainsKey(item.WorldEventObjectFilter)) { EOSLogger.Error("LevelSpawnedFogBeaconManager: WorldEventObjectFilter '" + item.WorldEventObjectFilter + "' is either unassigned or has already been assigned."); continue; } LevelSpawnedFogBeacon levelSpawnedFogBeacon = LevelSpawnedFogBeacon.Instantiate(((GlobalZoneIndex)def).DimensionIndex, ((GlobalZoneIndex)def).LayerType, ((GlobalZoneIndex)def).LocalIndex, item); if (levelSpawnedFogBeacon != null) { LevelSpawnedFogBeacons[item.WorldEventObjectFilter] = levelSpawnedFogBeacon; LSFBGlobalStatesSet[((Il2CppObjectBase)levelSpawnedFogBeacon.GlobalState).Pointer] = item; EOSLogger.Debug($"LevelSpawnedFogBeaconManager: spawned '{item.WorldEventObjectFilter}' in {((GlobalZoneIndex)def).GlobalZoneIndexTuple()}, Area_{(ushort)(65 + item.AreaIndex)}"); } } } public LevelSpawnedFogBeaconSettings GetLSFBDef(HeavyFogRepellerGlobalState h) { if (!LSFBGlobalStatesSet.TryGetValue(((Il2CppObjectBase)h).Pointer, out LevelSpawnedFogBeaconSettings value)) { return null; } return value; } public void ToggleLSFBState(string worldEventgObjectFilter, bool enable) { //IL_0035: Unknown result type (might be due to invalid IL or missing references) //IL_004c: Unknown result type (might be due to invalid IL or missing references) //IL_0054: Unknown result type (might be due to invalid IL or missing references) //IL_0059: Unknown result type (might be due to invalid IL or missing references) //IL_005e: Unknown result type (might be due to invalid IL or missing references) if (!LevelSpawnedFogBeacons.TryGetValue(worldEventgObjectFilter, out LevelSpawnedFogBeacon value)) { EOSLogger.Error("ToggleLSFBState: '" + worldEventgObjectFilter + "' is not defined"); } else if (SNet.IsMaster) { value.GlobalState.AttemptInteract(new pCarryItemWithGlobalState_Interaction { type = ((!enable) ? ((byte)1) : ((byte)0)), owner = (eCarryItemWithGlobalStateOwner)2, staticPosition = value.Position }); } } private void Clear() { foreach (LevelSpawnedFogBeacon value in LevelSpawnedFogBeacons.Values) { value.Destroy(); } LSFBGlobalStatesSet.Clear(); LevelSpawnedFogBeacons.Clear(); } private void BuildLevelSpawnedFogBeacons() { if (definitions.ContainsKey(RundownManager.ActiveExpedition.LevelLayoutData)) { definitions[RundownManager.ActiveExpedition.LevelLayoutData].Definitions.ForEach(Build); } } private LevelSpawnedFogBeaconSettingManager() { LevelAPI.OnBuildStart += Clear; LevelAPI.OnLevelCleanup += Clear; LevelAPI.OnBuildDone += BuildLevelSpawnedFogBeacons; EOSWardenEventManager.Current.AddEventDefinition(LSFBEvent.ToggleLevelSpawnedFogBeaconState.ToString(), 922u, (Action<WardenObjectiveEventData>)ToggleLevelSpawnedFogBeaconState); } static LevelSpawnedFogBeaconSettingManager() { Current = new LevelSpawnedFogBeaconSettingManager(); } private static void ToggleLevelSpawnedFogBeaconState(WardenObjectiveEventData e) { Current.ToggleLSFBState(e.WorldEventObjectFilter, e.Enabled); } } } namespace EOSExt.TacticalBigPickup.Functions.FogBeacon.BigPickup { public class RepellerSphereSetting { public bool InfiniteDuration { get; set; } public float GrowDuration { get; set; } = 10f; public float ShrinkDuration { get; set; } = 10f; public float Range { get; set; } = 11f; } public class BigPickupFogBeaconSetting { public float TimeToPickup { get; set; } = 1f; public float TimeToPlace { get; set; } = 1f; public RepellerSphereSetting RSHold { get; set; } = new RepellerSphereSetting(); public RepellerSphereSetting RSPlaced { get; set; } = new RepellerSphereSetting(); } internal class BigPickupFogBeaconSettingManager : TOAGenericDefinitionManager<BigPickupFogBeaconSetting> { public static BigPickupFogBeaconSettingManager Current { get; private set; } protected override string DEFINITION_NAME => "BigPickupFogBeacon_EOS"; public override void Init() { } private BigPickupFogBeaconSettingManager() { } static BigPickupFogBeaconSettingManager() { Current = new BigPickupFogBeaconSettingManager(); } } } namespace EOSExt.TacticalBigPickup.Impl { public abstract class CustomBigPickupFunctionImplementor { private static Dictionary<string, CustomBigPickupFunctionImplementor> s_implementors; protected abstract string FunctionName { get; } public static void SetupCustomBigPickupFunctions(LG_PickupItem item, List<BigPickupFunction> functions) { foreach (BigPickupFunction function in functions) { if (s_implementors.TryGetValue(function.Type, out CustomBigPickupFunctionImplementor value)) { value.SetupCustomBigPickupFunction(item, function.SettingID); EOSLogger.Log("ICustomBigPickupFunctionImplementor: function '" + function.Type + "' applied to " + ((Object)item).name); } else { EOSLogger.Error("ICustomBigPickupFunctionImplementor: function '" + function.Type + "' not found"); } } } static CustomBigPickupFunctionImplementor() { s_implementors = new Dictionary<string, CustomBigPickupFunctionImplementor>(); foreach (Type item in from x in typeof(CustomBigPickupFunctionImplementor).Assembly.GetTypes() where !x.IsAbstract where x.IsAssignableTo(typeof(CustomBigPickupFunctionImplementor)) select x) { CustomBigPickupFunctionImplementor customBigPickupFunctionImplementor = (CustomBigPickupFunctionImplementor)Activator.CreateInstance(item, nonPublic: true); if (s_implementors.TryGetValue(customBigPickupFunctionImplementor.FunctionName, out CustomBigPickupFunctionImplementor _)) { EOSLogger.Error("CustomBigPickupFunctionImplementor: Duplicate " + customBigPickupFunctionImplementor.FunctionName + "!"); continue; } EOSLogger.Log("CustomBigPickupFunctionImplementor: registered " + customBigPickupFunctionImplementor.FunctionName + "!"); s_implementors[customBigPickupFunctionImplementor.FunctionName] = customBigPickupFunctionImplementor; } } public abstract void SetupCustomBigPickupFunction(LG_PickupItem item, uint settingID); } } namespace EOSExt.TacticalBigPickup.Impl.FogBeacon.LeveSpawned { public class LevelSpawnedFogBeacon { public static uint LSFB_ITEM_DB_ID { get; private set; } public static bool HasFogBeaconItemDBDefinition => LSFB_ITEM_DB_ID != 0; public string WorldEventObjectFilter => def?.WorldEventObjectFilter ?? string.Empty; public LevelSpawnedFogBeaconSettings def { get; private set; } public HeavyFogRepellerGlobalState GlobalState { get; private set; } public LG_PickupItem LG_PickupItem { get; private set; } public NavMarker NavMarker { get; private set; } public Vector3 Position { get { //IL_0015: Unknown result type (might be due to invalid IL or missing references) //IL_000a: Unknown result type (might be due to invalid IL or missing references) LG_PickupItem lG_PickupItem = LG_PickupItem; if (lG_PickupItem == null) { return Vector3.zero; } return ((Component)lG_PickupItem).transform.position; } } public Color NAV_MARKER_COLOR { get; } = new Color(1f, 0.75686276f, 0.14509805f); public static LevelSpawnedFogBeacon Instantiate(eDimensionIndex dimensionIndex, LG_LayerType layer, eLocalZoneIndex localIndex, LevelSpawnedFogBeaconSettings def) { //IL_0018: Unknown result type (might be due to invalid IL or missing references) //IL_0019: Unknown result type (might be due to invalid IL or missing references) //IL_001a: Unknown result type (might be due to invalid IL or missing references) //IL_0061: Unknown result type (might be due to invalid IL or missing references) //IL_0062: Unknown result type (might be due to invalid IL or missing references) //IL_0063: Unknown result type (might be due to invalid IL or missing references) if (!HasFogBeaconItemDBDefinition) { EOSLogger.Error("LevelSpawnedFogBeaconManager: ItemDatablock Definition of vanilla Fog Repeller Turbine is not found..."); return null; } LG_Zone val = default(LG_Zone); if (!Builder.CurrentFloor.TryGetZoneByLocalIndex(dimensionIndex, layer, localIndex, ref val) || (Object)(object)val == (Object)null || def.AreaIndex < 0 || def.AreaIndex >= val.m_areas.Count) { EOSLogger.Error($"LevelSpawnedFogBeacon: cannot find {(dimensionIndex, layer, localIndex)}, Area_{(ushort)(65 + def.AreaIndex)}"); return null; } AIG_CourseNode courseNode = val.m_areas[def.AreaIndex].m_courseNode; return new LevelSpawnedFogBeacon(def, courseNode) { def = def }; } internal void Destroy() { Object.Destroy((Object)(object)((Component)LG_PickupItem.m_root).gameObject); GlobalState = null; LG_PickupItem = null; def = null; } private LevelSpawnedFogBeacon(LevelSpawnedFogBeaconSettings def, AIG_CourseNode node) { //IL_0010: Unknown result type (might be due to invalid IL or missing references) //IL_0015: Unknown result type (might be due to invalid IL or missing references) //IL_006e: Unknown result type (might be due to invalid IL or missing references) //IL_0074: Expected O, but got Unknown //IL_0080: Unknown result type (might be due to invalid IL or missing references) //IL_0085: Unknown result type (might be due to invalid IL or missing references) //IL_0100: Unknown result type (might be due to invalid IL or missing references) //IL_0105: Unknown result type (might be due to invalid IL or missing references) //IL_017d: Unknown result type (might be due to invalid IL or missing references) this.def = def; GameObject val = new GameObject($"LSBF_{def.WorldEventObjectFilter}-Area_{(ushort)(65 + def.AreaIndex)}"); val.transform.SetPositionAndRotation(def.Position.ToVector3(), Quaternion.identity); LG_PickupItem = LG_PickupItem.SpawnGenericPickupItem(val.transform); LG_PickupItem.SpawnNode = node; int count = ((Il2CppArrayBase<Dictionary<byte, iCarryItemWithGlobalState>>)(object)CarryItemWithGlobalStateManager.Current.m_carryItemGlobalStatesInstancesPerType)[0].Count; LG_PickupItem.SetupAsBigPickupItem(1, LSFB_ITEM_DB_ID, false, -1); CarryItemPickup_Core componentInChildren = ((Component)LG_PickupItem.m_root).GetComponentInChildren<CarryItemPickup_Core>(); LG_PickupItem_Sync val2 = ((Il2CppObjectBase)componentInChildren.m_sync).Cast<LG_PickupItem_Sync>(); if ((Object)(object)val2 != (Object)null) { pPickupItemState state = val2.m_stateReplicator.State; ((pCourseNode)(ref state.placement.node)).Set(LG_PickupItem.SpawnNode); } ((Component)((Il2CppObjectBase)componentInChildren.m_interact).Cast<Interact_Pickup_PickupItem>()).gameObject.SetActive(false); iTerminalItem componentInChildren2 = ((Component)LG_PickupItem).GetComponentInChildren<iTerminalItem>(); if (componentInChildren2 != null) { LG_LevelInteractionManager.DeregisterTerminalItem(componentInChildren2); } NavMarker = GuiManager.NavMarkerLayer.PrepareGenericMarker(((Component)LG_PickupItem).gameObject); if ((Object)(object)NavMarker != (Object)null) { NavMarker.SetColor(NAV_MARKER_COLOR); NavMarker.SetStyle((eNavMarkerStyle)14); NavMarker.SetVisible(false); } iCarryItemWithGlobalState val3 = default(iCarryItemWithGlobalState); if (!CarryItemWithGlobalStateManager.TryGetItemInstance((eCarryItemWithGlobalStateType)0, (byte)count, ref val3)) { EOSLogger.Error("LevelSpawnedFogBeaconManager: Didn't find GlobalState of '" + def.WorldEventObjectFilter + "'"); return; } GlobalState = ((Il2CppObjectBase)val3).Cast<HeavyFogRepellerGlobalState>(); FogRepeller_Sphere repellerSphere = GlobalState.m_repellerSphere; repellerSphere.GrowDuration = def.GrowDuration; repellerSphere.ShrinkDuration = def.ShrinkDuration; repellerSphere.Range = def.Range; HeavyFogRepellerGlobalState globalState = GlobalState; globalState.CallbackOnStateChange += Action<pCarryItemWithGlobalState_State, pCarryItemWithGlobalState_State, bool>.op_Implicit((Action<pCarryItemWithGlobalState_State, pCarryItemWithGlobalState_State, bool>)delegate(pCarryItemWithGlobalState_State oldState, pCarryItemWithGlobalState_State newState, bool isRecall) { //IL_0000: Unknown result type (might be due to invalid IL or missing references) //IL_0006: Unknown result type (might be due to invalid IL or missing references) //IL_0007: Unknown result type (might be due to invalid IL or missing references) //IL_0019: Expected I4, but got Unknown //IL_0036: Unknown result type (might be due to invalid IL or missing references) //IL_003b: Unknown result type (might be due to invalid IL or missing references) //IL_0046: Unknown result type (might be due to invalid IL or missing references) //IL_0052: Unknown result type (might be due to invalid IL or missing references) //IL_0059: Unknown result type (might be due to invalid IL or missing references) //IL_0070: Expected O, but got Unknown eHeavyFogRepellerStatus val4 = (eHeavyFogRepellerStatus)newState.status; switch ((int)val4) { case 0: case 2: NavMarker.SetVisible(false); break; case 1: NavMarker.SetVisible(true); if (isRecall) { WardenObjectiveManager.CheckAndExecuteEventsOnTrigger(new WardenObjectiveEventData { Type = (eWardenObjectiveEventType)922, WorldEventObjectFilter = WorldEventObjectFilter, Enabled = true, Delay = 1.1f }, (eWardenObjectiveEventTrigger)0, true, 0f); } break; } }); } private static void FindFogTurbineItemDBID() { if (!HasFogBeaconItemDBDefinition) { LSFB_ITEM_DB_ID = ((GameDataBlockBase<ItemDataBlock>)(object)GameDataBlockBase<ItemDataBlock>.GetBlock("Carry_HeavyFogRepeller"))?.persistentID ?? 0; if (LSFB_ITEM_DB_ID == 0) { EOSLogger.Error("LevelSpawnedFogBeaconManager: ItemDatablock Definition of vanilla Fog Repeller Turbine is not found..."); } } } static LevelSpawnedFogBeacon() { FindFogTurbineItemDBID(); LevelAPI.OnBuildStart += FindFogTurbineItemDBID; } } } namespace EOSExt.TacticalBigPickup.Impl.FogBeacon.BigPickup { internal class BigPickupFogBeaconImplementor : CustomBigPickupFunctionImplementor { protected override string FunctionName => "FogBeacon"; public override void SetupCustomBigPickupFunction(LG_PickupItem item, uint settingID) { //IL_0065: Unknown result type (might be due to invalid IL or missing references) //IL_00a9: Unknown result type (might be due to invalid IL or missing references) //IL_012a: Unknown result type (might be due to invalid IL or missing references) //IL_013a: Unknown result type (might be due to invalid IL or missing references) //IL_01bb: Unknown result type (might be due to invalid IL or missing references) //IL_0252: Unknown result type (might be due to invalid IL or missing references) //IL_025c: Expected O, but got Unknown //IL_0262: Unknown result type (might be due to invalid IL or missing references) //IL_026c: Expected O, but got Unknown //IL_01ed: Unknown result type (might be due to invalid IL or missing references) //IL_01f2: Unknown result type (might be due to invalid IL or missing references) //IL_01fd: Unknown result type (might be due to invalid IL or missing references) //IL_01ff: Unknown result type (might be due to invalid IL or missing references) //IL_0203: Unknown result type (might be due to invalid IL or missing references) GenericDefinition<BigPickupFogBeaconSetting> definition = BigPickupFogBeaconSettingManager.Current.GetDefinition(settingID); if (definition == null || definition.Definition == null) { EOSLogger.Error($"BigPickupFogBeacon: setting ID {settingID} not found"); return; } BigPickupFogBeaconSetting setting = definition.Definition; FogRepeller_Sphere val = new GameObject("FogInstance_Beacon_Fake").AddComponent<FogRepeller_Sphere>(); val.InfiniteDuration = false; val.LifeDuration = 99999f; val.GrowDuration = 99999f; val.ShrinkDuration = 99999f; val.Range = 1f; FogRepeller_Sphere fogRepHold = new GameObject("FogInstance_Beacon_SmallLayer").AddComponent<FogRepeller_Sphere>(); fogRepHold.InfiniteDuration = setting.RSHold.InfiniteDuration; fogRepHold.GrowDuration = setting.RSHold.GrowDuration; fogRepHold.ShrinkDuration = setting.RSHold.ShrinkDuration; fogRepHold.Range = setting.RSHold.Range; fogRepHold.Offset = Vector3.zero; FogRepeller_Sphere fogRepPlaced = new GameObject("FogInstance_Beacon_BigLayer").AddComponent<FogRepeller_Sphere>(); fogRepPlaced.InfiniteDuration = setting.RSPlaced.InfiniteDuration; fogRepPlaced.GrowDuration = setting.RSPlaced.GrowDuration; fogRepPlaced.ShrinkDuration = setting.RSPlaced.ShrinkDuration; fogRepPlaced.Range = setting.RSPlaced.Range; fogRepPlaced.Offset = Vector3.zero; CarryItemPickup_Core componentInChildren = ((Component)item.m_root).GetComponentInChildren<CarryItemPickup_Core>(); HeavyFogRepellerPickup val2 = ((Il2CppObjectBase)componentInChildren).Cast<HeavyFogRepellerPickup>(); iCarryItemWithGlobalState val3 = default(iCarryItemWithGlobalState); byte byteId = default(byte); if (CarryItemWithGlobalStateManager.TryCreateItemInstance((eCarryItemWithGlobalStateType)0, item.m_root, ref val3, ref byteId)) { pItemData_Custom customData = ((Item)val2).GetCustomData(); customData.byteId = byteId; pItemData_Custom val4 = customData; ((Item)val2).SetCustomData(val4, true); } HeavyFogRepellerGlobalState val5 = ((Il2CppObjectBase)val3).Cast<HeavyFogRepellerGlobalState>(); ((Component)fogRepHold).transform.SetParent(((Component)val5).transform, false); ((Component)fogRepPlaced).transform.SetParent(((Component)val5).transform, false); val5.m_repellerSphere = val; fogRepHold.m_sphereAllocator = new FogSphereAllocator(); fogRepPlaced.m_sphereAllocator = new FogSphereAllocator(); Interact_Pickup_PickupItem interact = ((Il2CppObjectBase)componentInChildren.m_interact).Cast<Interact_Pickup_PickupItem>(); ((Interact_Timed)interact).InteractDuration = setting.TimeToPickup; val5.CallbackOnStateChange += Action<pCarryItemWithGlobalState_State, pCarryItemWithGlobalState_State, bool>.op_Implicit((Action<pCarryItemWithGlobalState_State, pCarryItemWithGlobalState_State, bool>)delegate(pCarryItemWithGlobalState_State oldState, pCarryItemWithGlobalState_State newState, bool isRecall) { //IL_0025: Unknown result type (might be due to invalid IL or missing references) //IL_002b: Unknown result type (might be due to invalid IL or missing references) //IL_002c: Unknown result type (might be due to invalid IL or missing references) //IL_002e: Invalid comparison between Unknown and I4 //IL_0030: Unknown result type (might be due to invalid IL or missing references) //IL_0032: Invalid comparison between Unknown and I4 //IL_0046: Unknown result type (might be due to invalid IL or missing references) if (isRecall) { FogRepeller_Sphere obj = fogRepHold; if (obj != null) { obj.KillRepellerInstantly(); } FogRepeller_Sphere obj2 = fogRepPlaced; if (obj2 != null) { obj2.KillRepellerInstantly(); } } else { eHeavyFogRepellerStatus val6 = (eHeavyFogRepellerStatus)newState.status; if ((int)val6 != 1) { if ((int)val6 == 2) { FogRepeller_Sphere obj3 = fogRepHold; if (obj3 != null) { obj3.StopRepelling(); } FogRepeller_Sphere obj4 = fogRepPlaced; if (obj4 != null) { obj4.StartRepelling(); } ((Interact_Timed)interact).InteractDuration = setting.TimeToPickup; } } else { FogRepeller_Sphere obj5 = fogRepHold; if (obj5 != null) { obj5.StartRepelling(); } if (oldState.status != 0) { FogRepeller_Sphere obj6 = fogRepPlaced; if (obj6 != null) { obj6.StopRepelling(); } } ((Interact_Timed)interact).InteractDuration = setting.TimeToPlace; } } }); } internal BigPickupFogBeaconImplementor() { } } } namespace TOA_Heavy_Industries { internal static class MTFOPartialDataIdResolver { private const string PartialDataPluginGuid = "MTFO.Extension.PartialBlocks"; private const string IdFileName = "_persistentID.json"; private static readonly object Sync = new object(); private static Dictionary<string, uint>? _guidToId; private static bool _loadAttempted; internal static bool TryResolve(string guid, out uint id) { id = 0u; if (string.IsNullOrWhiteSpace(guid)) { return false; } EnsureLoaded(); lock (Sync) { return _guidToId != null && _guidToId.TryGetValue(guid.Trim(), out id); } } private static void EnsureLoaded() { lock (Sync) { if (_loadAttempted) { return; } _loadAttempted = true; try { string text = TryGetPartialDataPathFromPlugin(); if (string.IsNullOrWhiteSpace(text)) { return; } string text2 = Path.Combine(text, "_persistentID.json"); if (File.Exists(text2)) { Dictionary<string, uint> dictionary = ReadPersistentIdFile(text2); if (dictionary.Count > 0) { _guidToId = dictionary; } } } catch (Exception ex) { TOARuntime.LogThrottled("MTFO PartialData persistentID resolver failed: " + ex.Message); } } } private static string TryGetPartialDataPathFromPlugin() { try { if (((BaseChainloader<BasePlugin>)(object)IL2CPPChainloader.Instance).Plugins.TryGetValue("MTFO.Extension.PartialBlocks", out var value)) { Assembly assembly = ((value == null) ? null : value.Instance?.GetType()?.Assembly); if (assembly != null && (assembly.GetTypes().FirstOrDefault((Type t) => string.Equals(t.Name, "PartialDataManager", StringComparison.Ordinal))?.GetProperty("PartialDataPath", BindingFlags.Static | BindingFlags.Public))?.GetValue(null) is string text && !string.IsNullOrWhiteSpace(text)) { return text; } } } catch { } return DiscoverPartialDataPathFromFileSystem(); } private static string DiscoverPartialDataPathFromFileSystem() { try { foreach (string item in Directory.EnumerateFiles(Paths.PluginPath, "_persistentID.json", SearchOption.AllDirectories)) { string directoryName = Path.GetDirectoryName(item); if (!string.IsNullOrWhiteSpace(directoryName)) { return directoryName; } } } catch { } return string.Empty; } private static Dictionary<string, uint> ReadPersistentIdFile(string idFilePath) { Dictionary<string, uint> dictionary = new Dictionary<string, uint>(StringComparer.OrdinalIgnoreCase); string text = File.ReadAllText(idFilePath); try { using JsonDocument jsonDocument = JsonDocument.Parse(text, new JsonDocumentOptions { CommentHandling = JsonCommentHandling.Skip, AllowTrailingCommas = true }); if (jsonDocument.RootElement.ValueKind == JsonValueKind.Array) { foreach (JsonElement item in jsonDocument.RootElement.EnumerateArray()) { if (TryReadGuidEntry(item, out string guid, out uint id)) { dictionary[guid] = id; } } } else if (jsonDocument.RootElement.ValueKind == JsonValueKind.Object) { foreach (JsonProperty item2 in jsonDocument.RootElement.EnumerateObject()) { if (TryReadUIntElement(item2.Value, out var id2) && !string.IsNullOrWhiteSpace(item2.Name)) { dictionary[item2.Name.Trim()] = id2; } } } } catch { foreach (Match item3 in Regex.Matches(text, "\\{[^{}]*\\\"GUID\\\"\\s*:\\s*\\\"(?<guid>(?:\\\\.|[^\\\"])*)\\\"[^{}]*\\\"ID\\\"\\s*:\\s*(?<id>\\d+)[^{}]*\\}", RegexOptions.IgnoreCase | RegexOptions.Singleline | RegexOptions.CultureInvariant)) { string text2 = TOAJsonConfig.UnescapeJsonStringForRuntime(item3.Groups["guid"].Value).Trim(); if (!string.IsNullOrWhiteSpace(text2) && uint.TryParse(item3.Groups["id"].Value, out var result)) { dictionary[text2] = result; } } } return dictionary; } private static bool TryReadGuidEntry(JsonElement entry, out string guid, out uint id) { guid = string.Empty; id = 0u; if (entry.ValueKind != JsonValueKind.Object) { return false; } foreach (JsonProperty item in entry.EnumerateObject()) { if (string.Equals(item.Name, "GUID", StringComparison.OrdinalIgnoreCase) || string.Equals(item.Name, "Guid", StringComparison.OrdinalIgnoreCase) || string.Equals(item.Name, "persistentID", StringComparison.OrdinalIgnoreCase)) { guid = ((item.Value.ValueKind == JsonValueKind.String) ? (item.Value.GetString() ?? string.Empty).Trim() : item.Value.ToString().Trim()); } else if (string.Equals(item.Name, "ID", StringComparison.OrdinalIgnoreCase) || string.Equals(item.Name, "Id", StringComparison.OrdinalIgnoreCase)) { TryReadUIntElement(item.Value, out id); } } if (!string.IsNullOrWhiteSpace(guid)) { return id != 0; } return false; } private static bool TryReadUIntElement(JsonElement element, out uint id) { id = 0u; if (element.ValueKind == JsonValueKind.Number && element.TryGetUInt32(out var value)) { id = value; return true; } if (element.ValueKind == JsonValueKind.String && uint.TryParse(element.GetString(), out var result)) { id = result; return true; } return false; } } internal static class TOAConfigPaths { internal const string CustomRootFolderName = "TOA_Heavy_Industries"; internal static string GetFeaturePath(string featureName) { return Path.Combine(GetCustomPath(), "TOA_Heavy_Industries", featureName); } internal static string GetCustomPath() { if (TryGetMTFOCustomPath(out string customPath)) { return customPath; } return Path.Combine(Paths.BepInExRootPath, "Custom"); } private static bool TryGetMTFOCustomPath(out string customPath) { customPath = string.Empty; try { Type type = FindLoadedType("MTFO.API.MTFOPathAPI"); if (type == null) { return false; } if (type.GetProperty("CustomPath", BindingFlags.Static | BindingFlags.Public | BindingFlags.NonPublic)?.GetValue(null) is string text && !string.IsNullOrWhiteSpace(text)) { customPath = Path.GetFullPath(text); return true; } } catch (Exception ex) { TOARuntime.LogThrottled("Could not read MTFOPathAPI.CustomPath, falling back to BepInEx/Custom: " + ex.Message); } return false; } private static Type? FindLoadedType(string fullName) { Assembly[] assemblies = AppDomain.CurrentDomain.GetAssemblies(); for (int i = 0; i < assemblies.Length; i++) { Type type = assemblies[i].GetType(fullName, throwOnError: false, ignoreCase: false); if (type != null) { return type; } } return null; } } internal sealed class TOALevelRule { internal string Name = string.Empty; internal string ButtonText = string.Empty; internal readonly HashSet<uint> OfflineIDs = new HashSet<uint>(); internal readonly HashSet<string> LevelLayoutIDStrings = new HashSet<string>(StringComparer.OrdinalIgnoreCase); internal bool HasAnySelector { get { if (OfflineIDs.Count <= 0) { return LevelLayoutIDStrings.Count > 0; } return true; } } } internal sealed class TOAConfigDocument { internal string FilePath = string.Empty; internal bool Enabled = true; internal bool EnableInstantReload; internal readonly List<TOALevelRule> Levels = new List<TOALevelRule>(); } internal static class TOAJsonConfig { internal const string ConfigFolderName = "TOA_Heavy_Industries"; internal const string GearSwapFeatureFolderName = "GearSwap"; internal const string ConfigFileName = "GearSwap.json"; internal const string ConfigSearchPattern = "*.json"; private static readonly object _sync = new object(); private static readonly List<TOAConfigDocument> _configs = new List<TOAConfigDocument>(); private static readonly List<string> _configPaths = new List<string>(); private static readonly List<FileSystemWatcher> _watchers = new List<FileSystemWatcher>(); private static string _lastConfigStamp = string.Empty; private static long _reloadPending; private static float _nextFallbackFileCheckTime; internal static string ConfigPathSummary { get { lock (_sync) { return (_configPaths.Count == 0) ? "<none>" : string.Join(" | ", _configPaths); } } } internal static IReadOnlyList<TOAConfigDocument> Configs { get { lock (_sync) { return _configs.ToArray(); } } } internal static bool IsInstantReloadEnabled { get { lock (_sync) { return _configs.Any((TOAConfigDocument c) => c.Enabled && c.EnableInstantReload); } } } internal static void LoadOrCreate(ManualLogSource? log, bool force = false) { //IL_0070: Unknown result type (might be due to invalid IL or missing references) //IL_0077: Expected O, but got Unknown //IL_013d: Unknown result type (might be due to invalid IL or missing references) //IL_0144: Expected O, but got Unknown bool flag = default(bool); try { List<string> list = DiscoverExistingConfigPaths().ToList(); if (list.Count == 0) { list = CreateDefaultConfigsInCandidateRundownFolders(log).ToList(); } string text = BuildConfigStamp(list); if (!force && text == _lastConfigStamp) { return; } List<TOAConfigDocument> list2 = new List<TOAConfigDocument>(); foreach (string item in list) { try { list2.Add(LoadConfigFile(item)); } catch (Exception ex) { ManualLogSource val = log; if (val != null) { BepInExErrorLogInterpolatedStringHandler val2 = new BepInExErrorLogInterpolatedStringHandler(46, 2, ref flag); if (flag) { ((BepInExLogInterpolatedStringHandler)val2).AppendLiteral("Failed to read TOA_Heavy_Industries JSON at "); ((BepInExLogInterpolatedStringHandler)val2).AppendFormatted<string>(item); ((BepInExLogInterpolatedStringHandler)val2).AppendLiteral(": "); ((BepInExLogInterpolatedStringHandler)val2).AppendFormatted<Exception>(ex); } val.LogError(val2); } } } lock (_sync) { _configs.Clear(); _configs.AddRange(list2); _configPaths.Clear(); _configPaths.AddRange(list); _lastConfigStamp = text; } Interlocked.Exchange(ref _reloadPending, 0L); ApplyInstantReloadMode(log); } catch (Exception ex2) { ManualLogSource val = log; if (val != null) { BepInExErrorLogInterpolatedStringHandler val2 = new BepInExErrorLogInterpolatedStringHandler(52, 1, ref flag); if (flag) { ((BepInExLogInterpolatedStringHandler)val2).AppendLiteral("Failed to load TOA_Heavy_Industries JSON config(s): "); ((BepInExLogInterpolatedStringHandler)val2).AppendFormatted<Exception>(ex2); } val.LogError(val2); } } } internal static void ApplyInstantReloadMode(ManualLogSource? log) { if (IsInstantReloadEnabled) { RestartWatchers(log); } else { StopWatchers(); } } internal static void ReloadIfChanged(ManualLogSource? log) { if (IsInstantReloadEnabled) { bool flag = Interlocked.Read(in _reloadPending) != 0; bool flag2 = Time.realtimeSinceStartup >= _nextFallbackFileCheckTime; if (flag || flag2) { _nextFallbackFileCheckTime = Time.realtimeSinceStartup + 5f; LoadOrCreate(log, flag); } } } private static TOAConfigDocument LoadConfigFile(string configPath) { string json = StripJsonLineComments(File.ReadAllText(configPath)); TOAConfigDocument tOAConfigDocument = new TOAConfigDocument { FilePath = configPath, Enabled = ReadBool(json, "Enabled", defaultValue: true), EnableInstantReload = ReadBool(json, "EnableInstantReload", defaultValue: false) }; TOALevelRule tOALevelRule = new TOALevelRule { Name = "MainLevelLayoutIDs", ButtonText = "Switch Gear" }; AddUIntOrStringValue(json, "MainLevelLayoutIDs", tOALevelRule.OfflineIDs, tOALevelRule.LevelLayoutIDStrings); if (tOALevelRule.HasAnySelector) { tOAConfigDocument.Levels.Add(tOALevelRule); } return tOAConfigDocument; } private static IEnumerable<TOALevelRule> ReadLevelRules(string json) { List<string> list = new List<string>(); string[] array = new string[6] { "Levels", "LevelLayouts", "Rundowns", "Entries", "Groups", "AllowedLevels" }; foreach (string propertyName in array) { string text = ExtractNamedArrayContent(json, propertyName); if (!string.IsNullOrWhiteSpace(text)) { list.AddRange(ExtractTopLevelObjectBlocksFromArray(text)); } } if (list.Count == 0 && json.TrimStart().StartsWith("[", StringComparison.Ordinal)) { list.AddRange(ExtractTopLevelObjectBlocksFromArray(json)); } foreach (string item in list) { TOALevelRule tOALevelRule = new TOALevelRule { Name = ReadString(item, "Name", string.Empty), ButtonText = ReadString(item, "ButtonText", "Switch Gear") }; AddUIntArray(item, "OfflineIDs", tOALevelRule.OfflineIDs, tOALevelRule.LevelLayoutIDStrings); AddUIntArray(item, "LevelLayoutIDs", tOALevelRule.OfflineIDs, tOALevelRule.LevelLayoutIDStrings); AddUIntArray(item, "AllowedLevelLayoutIDs", tOALevelRule.OfflineIDs, tOALevelRule.LevelLayoutIDStrings); AddUIntOrStringValue(item, "MainLevelLayoutIDs", tOALevelRule.OfflineIDs, tOALevelRule.LevelLayoutIDStrings); AddStringArray(item, "PartialDataIDs", tOALevelRule.LevelLayoutIDStrings); AddStringArray(item, "PartialDataLevelLayoutIDs", tOALevelRule.LevelLayoutIDStrings); AddStringArray(item, "LevelLayoutIDStrings", tOALevelRule.LevelLayoutIDStrings); AddStringArray(item, "AllowedLevelLayoutIDStrings", tOALevelRule.LevelLayoutIDStrings); AddStringArray(item, "AllowedPartialDataLevelLayoutIDs", tOALevelRule.LevelLayoutIDStrings); AddStringArray(item, "BlockNames", tOALevelRule.LevelLayoutIDStrings); AddStringArray(item, "LevelLayoutNames", tOALevelRule.LevelLayoutIDStrings); if (tOALevelRule.HasAnySelector) { yield return tOALevelRule; } } } private static void RestartWatchers(ManualLogSource? log) { //IL_0181: Unknown result type (might be due to invalid IL or missing references) //IL_0188: Expected O, but got Unknown try { StopWatchers(); lock (_sync) { HashSet<string> hashSet = new HashSet<string>(StringComparer.OrdinalIgnoreCase); foreach (string configPath in _configPaths) { string directoryName = Path.GetDirectoryName(configPath); if (!string.IsNullOrWhiteSpace(directoryName) && Directory.Exists(directoryName)) { hashSet.Add(directoryName); } } using HashSet<string>.Enumerator enumerator2 = hashSet.GetEnumerator(); while (enumerator2.MoveNext()) { FileSystemWatcher fileSystemWatcher = new FileSystemWatcher(enumerator2.Current, "*.json") { NotifyFilter = (NotifyFilters.FileName | NotifyFilters.Size | NotifyFilters.LastWrite | NotifyFilters.CreationTime), IncludeSubdirectories = false, EnableRaisingEvents = true }; fileSystemWatcher.Changed += delegate { MarkReloadPending(); }; fileSystemWatcher.Created += delegate { MarkReloadPending(); }; fileSystemWatcher.Renamed += delegate { MarkReloadPending(); }; fileSystemWatcher.Deleted += delegate { MarkReloadPending(); }; _watchers.Add(fileSystemWatcher); } } } catch (Exception ex) { if (log != null) { bool flag = default(bool); BepInExWarningLogInterpolatedStringHandler val = new BepInExWarningLogInterpolatedStringHandler(84, 2, ref flag); if (flag) { ((BepInExLogInterpolatedStringHandler)val).AppendLiteral("Could not start instant JSON reload watcher. Falling back to passive file checks. "); ((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>(ex.GetType().Name); ((BepInExLogInterpolatedStringHandler)val).AppendLiteral(": "); ((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>(ex.Message); } log.LogWarning(val); } } } private static void StopWatchers() { lock (_sync) { foreach (FileSystemWatcher watcher in _watchers) { try { watcher.Dispose(); } catch { } } _watchers.Clear(); } } private static void MarkReloadPending() { Interlocked.Exchange(ref _reloadPending, 1L); } private static IEnumerable<string> DiscoverExistingConfigPaths() { HashSet<string> hashSet = new HashSet<string>(StringComparer.OrdinalIgnoreCase); foreach (string item in EnumerateFilesSafe(TOAConfigPaths.GetFeaturePath("GearSwap"), "*.json", SearchOption.TopDirectoryOnly)) { hashSet.Add(Path.GetFullPath(item)); } return hashSet.OrderBy<string, string>((string p) => p, StringComparer.OrdinalIgnoreCase); } private static IEnumerable<string> CreateDefaultConfigsInCandidateRundownFolders(ManualLogSource? log) { HashSet<string> hashSet = new HashSet<string>(StringComparer.OrdinalIgnoreCase); hashSet.Add(TOAConfigPaths.GetFeaturePath("GearSwap")); foreach (string item in hashSet.OrderBy<string, string>((string p) => p, StringComparer.OrdinalIgnoreCase)) { Directory.CreateDirectory(item); string path = Path.Combine(item, "GearSwap.json"); if (!File.Exists(path)) { File.WriteAllText(path, CreateDefaultJson()); } yield return Path.GetFullPath(path); } } private static IEnumerable<string> DiscoverRundownCustomRoots() { HashSet<string> hashSet = new HashSet<string>(StringComparer.OrdinalIgnoreCase); foreach (string item in EnumerateDirectoriesSafe(Paths.PluginPath, "Custom", SearchOption.AllDirectories)) { string fullPath = Path.GetFullPath(item); if (fullPath.IndexOf(Path.DirectorySeparatorChar + "TOA_Heavy_Industries" + Path.DirectorySeparatorChar, StringComparison.OrdinalIgnoreCase) < 0) { hashSet.Add(fullPath); } } return hashSet.OrderBy<string, string>((string p) => p, StringComparer.OrdinalIgnoreCase); } private static IEnumerable<string> EnumerateDirectoriesSafe(string root, string searchPattern, SearchOption option) { if (!Directory.Exists(root)) { return Array.Empty<string>(); } try { return Directory.EnumerateDirectories(root, searchPattern, option).ToArray(); } catch { return Array.Empty<string>(); } } private static IEnumerable<string> EnumerateFilesSafe(string root, string searchPattern, SearchOption option) { if (!Directory.Exists(root)) { return Array.Empty<string>(); } try { return (from path in Directory.EnumerateFiles(root, searchPattern, option) where !ShouldIgnoreConfigFile(path) select path).ToArray(); } catch { return Array.Empty<string>(); } } private static bool ShouldIgnoreConfigFile(string path) { string fileName = Path.GetFileName(path); if (!fileName.StartsWith("Template", StringComparison.OrdinalIgnoreCase) && !fileName.StartsWith("README", StringComparison.OrdinalIgnoreCase)) { return fileName.StartsWith("Example", StringComparison.OrdinalIgnoreCase); } return true; } private static string GetPluginAssemblyDirectory() { try { string location = Assembly.GetExecutingAssembly().Location; string text = (string.IsNullOrWhiteSpace(location) ? null : Path.GetDirectoryName(location)); if (!string.IsNullOrWhiteSpace(text)) { return text; } } catch { } return Paths.PluginPath; } private static string BuildConfigStamp(IEnumerable<string> configPaths) { StringBuilder stringBuilder = new StringBuilder(); foreach (string item in configPaths.OrderBy<string, string>((string p) => p, StringComparer.OrdinalIgnoreCase)) { DateTime dateTime = (File.Exists(item) ? File.GetLastWriteTimeUtc(item) : DateTime.MinValue); long value = (File.Exists(item) ? new FileInfo(item).Length : (-1)); stringBuilder.Append(item).Append('|').Append(dateTime.Ticks) .Append('|') .Append(value) .Append('\n'); } return stringBuilder.ToString(); } private static bool ReadBool(string json, string propertyName, bool defaultValue) { Match match = Regex.Match(json, "\\\"" + Regex.Escape(propertyName) + "\\\"\\s*:\\s*(true|false)", RegexOptions.IgnoreCase | RegexOptions.CultureInvariant); if (!match.Success) { return defaultValue; } return string.Equals(match.Groups[1].Value, "true", StringComparison.OrdinalIgnoreCase); } private static string ReadString(string json, string propertyName, string defaultValue) { Match match = Regex.Match(json, "\\\"" + Regex.Escape(propertyName) + "\\\"\\s*:\\s*\\\"(?<value>(?:\\\\.|[^\\\"])*)\\\"", RegexOptions.Singleline | RegexOptions.CultureInvariant); if (!match.Success) { return defaultValue; } string text = UnescapeJsonString(match.Groups["value"].Value).Trim(); if (!string.IsNullOrWhiteSpace(text)) { return text; } return defaultValue; } private static void AddUIntOrStringValue(string json, string propertyName, HashSet<uint> numericTarget, HashSet<string> stringTarget) { if (!TryReadScalarValue(json, propertyName, out string value)) { return; } string text = value.Trim(); if (!string.IsNullOrWhiteSpace(text)) { if (uint.TryParse(text, out var result)) { numericTarget.Add(result); } else { stringTarget.Add(text); } } } private static bool TryReadScalarValue(string json, string propertyName, out string value) { value = string.Empty; Match match = Regex.Match(json, "\\\"" + Regex.Escape(propertyName) + "\\\"\\s*:", RegexOptions.IgnoreCase | RegexOptions.CultureInvariant); if (!match.Success) { return false; } int i; for (i = match.Index + match.Length; i < json.Length && char.IsWhiteSpace(json[i]); i++) { } if (i >= json.Length) { return false; } if (json[i] == '[' || json[i] == '{') { return false; } if (json[i] == '"') { StringBuilder stringBuilder = new StringBuilder(); bool flag = false; for (i++; i < json.Length; i++) { char c = json[i]; if (flag) { stringBuilder.Append('\\').Append(c); flag = false; continue; } switch (c) { case '\\': flag = true; break; case '"': value = UnescapeJsonString(stringBuilder.ToString()); return true; default: stringBuilder.Append(c); break; } } return false; } int num = i; for (; i < json.Length && !char.IsWhiteSpace(json[i]) && json[i] != ',' && json[i] != '}' && json[i] != ']'; i++) { } value = json.Substring(num, i - num).Trim(); return !string.IsNullOrWhiteSpace(value); } private static void AddUIntArray(string json, string propertyName, HashSet<uint> numericTarget, HashSet<string> stringTarget) { string text = ExtractNamedArrayContent(json, propertyName); if (string.IsNullOrWhiteSpace(text)) { return; } foreach (string item in ReadTopLevelArrayScalarItems(text)) { string text2 = item.Trim(); if (uint.TryParse(text2, out var result)) { numericTarget.Add(result); } else if (!string.IsNullOrWhiteSpace(text2)) { stringTarget.Add(text2); } } } private static void AddStringArray(string json, string propertyName, HashSet<string> target) { string text = ExtractNamedArrayContent(json, propertyName); if (string.IsNullOrWhiteSpace(text)) { return; } foreach (string item in ReadArrayStringItems(text)) { string text2 = item.Trim(); if (!string.IsNullOrWhiteSpace(text2)) { target.Add(text2); } } } private static IEnumerable<string> ReadArrayStringItems(string arrayContent) { foreach (string item in ReadTopLevelArrayScalarItems(arrayContent)) { if (!uint.TryParse(item.Trim(), out var _)) { yield return item; } } } private static IEnumerable<string> ReadTopLevelArrayScalarItems(string arrayContent) { string text = arrayContent.Trim(); if (text.StartsWith("[", StringComparison.Ordinal)) { int num = FindMatchingBracket(text, 0, '[', ']'); if (num > 0) { text = text.Substring(1, num - 1); } } bool inString = false; bool escaped = false; int objectDepth = 0; int arrayDepth = 0; int tokenStart = -1; StringBuilder stringBuilder = null; for (int i = 0; i <= text.Length; i++) { char c = ((i < text.Length) ? text[i] : ','); if (inString) { if (escaped) { stringBuilder?.Append('\\').Append(c); escaped = false; continue; } switch (c) { case '\\': escaped = true; break; case '"': inString = false; if (objectDepth == 0 && arrayDepth == 0 && stringBuilder != null) { yield return UnescapeJsonString(stringBuilder.ToString()); } stringBuilder = null; break; default: stringBuilder?.Append(c); break; } continue; } switch (c) { case '"': inString = true; escaped = false; stringBuilder = ((objectDepth == 0 && arrayDepth == 0) ? new StringBuilder() : null); tokenStart = -1; continue; case '{': objectDepth++; tokenStart = -1; continue; case '}': if (objectDepth > 0) { objectDepth--; } tokenStart = -1; continue; case '[': arrayDepth++; tokenStart = -1; continue; case ']': if (arrayDepth > 0) { arrayDepth--; } tokenStart = -1; continue; } if (objectDepth != 0 || arrayDepth != 0) { tokenStart = -1; } else if (char.IsWhiteSpace(c) || c == ',') { if (tokenStart >= 0) { string text2 = text.Substring(tokenStart, i - tokenStart).Trim(); if (!string.IsNullOrWhiteSpace(text2)) { yield return text2; } tokenStart = -1; } } else if (tokenStart < 0) { tokenStart = i; } } } private static string? ExtractNamedArrayContent(string json, string propertyName) { Match match = Regex.Match(json, "\\\"" + Regex.Escape(propertyName) + "\\\"\\s*:", RegexOptions.IgnoreCase | RegexOptions.CultureInvariant); if (!match.Success) { return null; } int num = json.IndexOf('[', match.Index + match.Length); if (num < 0) { return null; } int num2 = FindMatchingBracket(json, num, '[', ']'); if (num2 <= num) { return null; } return json.Substring(num + 1, num2 - num - 1); } private static IEnumerable<string> ExtractTopLevelObjectBlocksFromArray(string arrayOrArrayContent) { string text = arrayOrArrayContent.Trim(); if (text.StartsWith("[", StringComparison.Ordinal)) { int num = FindMatchingBracket(text, 0, '[', ']'); if (num > 0) { text = text.Substring(1, num - 1); } } bool inString = false; bool escaped = false; int depth = 0; int num2 = -1; for (int i = 0; i < text.Length; i++) { char c = text[i]; if (inString) { if (escaped) { escaped = false; continue; } switch (c) { case '\\': escaped = true; break; case '"': inString = false; break; } continue; } switch (c) { case '"': inString = true; break; case '{': if (depth == 0) { num2 = i; } depth++; break; case '}': depth--; if (depth == 0 && num2 >= 0) { yield return text.Substring(num2, i - num2 + 1); num2 = -1; } break; } } } private static int FindMatchingBracket(string text, int openIndex, char openChar, char closeChar) { bool flag = false; bool flag2 = false; int num = 0; for (int i = openIndex; i < text.Length; i++) { char c = text[i]; if (flag) { if (flag2) { flag2 = false; continue; } switch (c) { case '\\': flag2 = true; break; case '"': flag = false; break; } } else if (c == '"') { flag = true; } else if (c == openChar) { num++; } else if (c == closeChar) { num--; if (num == 0) { return i; } } } return -1; } private static string StripJsonLineComments(string json) { StringBuilder stringBuilder = new StringBuilder(json.Length); bool flag = false; bool flag2 = false; for (int i = 0; i < json.Length; i++) { char c = json[i]; if (flag) { stringBuilder.Append(c); if (flag2) { flag2 = false; continue; } switch (c) { case '\\': flag2 = true; break; case '"': flag = false; break; } continue; } switch (c) { case '"': flag = true; stringBuilder.Append(c); continue; case '/': if (i + 1 < json.Length && json[i + 1] == '/') { for (; i < json.Length && json[i] != '\n'; i++) { } if (i < json.Length) { stringBuilder.Append(json[i]); } continue; } break; } stringBuilder.Append(c); } return stringBuilder.ToString(); } internal static string UnescapeJsonStringForRuntime(string value) { return UnescapeJsonString(value); } private static string UnescapeJsonString(string value) { return value.Replace("\\\"", "\"").Replace("\\\\", "\\").Replace("\\/", "/") .Replace("\\n", "\n") .Replace("\\r", "\r") .Replace("\\t", "\t"); } private static string CreateDefaultJson() { return "{\n \"Enabled\": true,\n \"EnableInstantReload\": false,\n \"MainLevelLayoutIDs\": \"Level_10_L1\"\n}\n"; } } internal static class TOATextResolver { internal static string Resolve(string text) { if (string.IsNullOrWhiteSpace(text)) { return string.Empty; } string text2 = text.Trim(); try { if (uint.TryParse(text2, out var result) && result != 0) { return Text.Get(result); } if (MTFOPartialDataIdResolver.TryResolve(text2, out var id) && id != 0) { return Text.Get(id); } } catch (Exception ex) { TOARuntime.LogThrottled("TOA text resolver failed for '" + text2 + "': " + ex.Message); } return text; } internal static string ResolveObject(object? value) { if (value == null) { return string.Empty; } try { uint num = ReadUInt(value, "Id"); if (num != 0) { string text = Text.Get(num); if (!string.IsNullOrWhiteSpace(text) && !text.Equals("Localization.LocalizedText", StringComparison.Ordinal)) { return text; } } string text2 = ReadMember(value, "UntranslatedText")?.ToString() ?? string.Empty; if (!string.IsNullOrWhiteSpace(text2)) { return text2; } string text3 = value.ToString() ?? string.Empty; return text3.Equals("Localization.LocalizedText", StringComparison.Ordinal) ? string.Empty : text3; } catch (Exception ex) { TOARuntime.LogThrottled("TOA localized object resolver failed: " + ex.Message); return string.Empty; } } private static uint ReadUInt(object value, string name) { object obj = ReadMember(value, name); if (obj != null) { return Convert.ToUInt32(obj); } return 0u; } private static object? ReadMember(object value, string name) { Type type = value.GetType(); object obj = type.GetProperty(name, BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic)?.GetValue(value); if (obj != null) { return obj; } return type.GetField(name, BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic)?.GetValue(value); } } internal sealed class TOAEventScanComponent : MonoBehaviour { public const float UPDATE_INTERVAL = 0.3f; public const string VANILLA_CP_PREFAB_PATH = "Assets/AssetPrefabs/Complex/Generic/ChainedPuzzles/CP_Bioscan_sustained_RequireAll.prefab"; private GameObject _root; private GameObject _cylinder; private GameObject _visual; private GameObject _information; private readonly List<Renderer> _visualRenderers = new List<Renderer>(); private float time = float.NaN; private float m_colorLerpDelta; private const float LERP_DURATION = 0.5f; public GameObject Cylinder => _cylinder; public GameObject Visual => _visual; public GameObject Information => _information; public GameObject TextMeshProGO { get { if (Information.transform.childCount <= 0) { return Information; } return ((Component)Information.transform.GetChild(0)).gameObject; } } public Renderer VisualRenderer { get; private set; } public TextMeshPro DisplayText { get; private set; } private Vector3 Position => ((Component)this).gameObject.transform.position; public StateReplicator<TOAEventScanStatus> StateReplicator { get; private set; } public TOAEventScanDefinition def { get; internal set; } internal bool ExecuteEventsLocally { get; set; } = true; internal bool IsActive { get { if (StateReplicator != null) { return StateReplicator.State.Status == TOAEventScanState.Active; } return false; } } internal bool IsInactive { get { if (StateReplicator != null) { return StateReplicator.State.Status != TOAEventScanState.Active; } return false; } } public Color Color_Waiting { get; private set; } public Color Color_Active { get; private set; } private bool TryBindAssetHierarchy() { //IL_0016: Unknown result type (might be due to invalid IL or missing references) //IL_001c: Expected O, but got Unknown if (!TryBindLegacyHierarchy()) { ManualLogSource log = TOARuntime.Log; if (log != null) { bool flag = default(bool); BepInExErrorLogInterpolatedStringHandler val = new BepInExErrorLogInterpolatedStringHandler(108, 2, ref flag); if (flag) { ((BepInExLogInterpolatedStringHandler)val).AppendLiteral("EventScan '"); ((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>(def.WorldEventObjectFilter); ((BepInExLogInterpolatedStringHandler)val).AppendLiteral("' asset hierarchy mismatch. Expected TOA/Legacy shape root/Cylinder+Visual(+Information). Actual="); ((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>(DescribeHierarchy(((Component)this).gameObject.transform, 4)); } log.LogError(val); } return false; } DisplayText = _information.GetComponentInChildren<TextMeshPro>(true) ?? _root.GetComponentInChildren<TextMeshPro>(true); _visualRenderers.Clear(); foreach (Renderer componentsInChild in _visual.GetComponentsInChildren<Renderer>(true)) { if ((Object)(object)componentsInChild != (Object)null) { _visualRenderers.Add(componentsInChild); } } if (_visualRenderers.Count == 0) { foreach (Renderer componentsInChild2 in _root.GetComponentsInChildren<Renderer>(true)) { if ((Object)(object)componentsInChild2 != (Object)null) { _visualRenderers.Add(componentsInChild2); } } } VisualRenderer = _visual.GetComponentInChildren<Renderer>(true); return _visualRenderers.Count > 0; } private bool TryBindLegacyHierarchy() { //IL_010b: Unknown result type (might be due to invalid IL or missing references) //IL_0111: Expected O, but got Unknown if (((Component)this).gameObject.transform.childCount == 0) { return false; } _root = ((Component)((Component)this).gameObject.transform.GetChild(0)).gameObject; if (_root.transform.childCount >= 3) { _cylinder = ((Component)_root.transform.GetChild(0)).gameObject; _visual = ((Component)_root.transform.GetChild(1)).gameObject; _information = ((Component)_root.transform.GetChild(2)).gameObject; return true; } if (_root.transform.childCount >= 2) { _cylinder = ((Component)_root.transform.GetChild(0)).gameObject; _visual = ((Component)_root.transform.GetChild(1)).gameObject; _information = EnsureInformationObject(_root.transform); ManualLogSource log = TOARuntime.Log; if (log != null) { bool flag = default(bool); BepInExWarningLogInterpolatedStringHandler val = new BepInExWarningLogInterpolatedStringHandler(123, 1, ref flag); if (flag) { ((BepInExLogInterpolatedStringHandler)val).AppendLiteral("EventScan '"); ((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>(def.WorldEventObjectFilter); ((BepInExLogInterpolatedStringHandler)val).AppendLiteral("' asset has no Information child. A TOA Information container was created so the Legacy EventScan logic can run."); } log.LogWarning(val); } return true; } return false; } private static GameObject EnsureInformationObject(Transform root) { //IL_0042: Unknown result type (might be due to invalid IL or missing references) //IL_0047: Unknown result type (might be due to invalid IL or missing references) //IL_0055: Expected O, but got Unknown for (int i = 0; i < root.childCount; i++) { Transform child = root.GetChild(i); if ((Object)(object)child != (Object)null && ((Object)child).name.IndexOf("Information", StringComparison.OrdinalIgnoreCase) >= 0) { return ((Component)child).gameObject; } } GameObject val = new GameObject("Information"); val.transform.SetParent(root, false); return val; } private static string DescribeHierarchy(Transform transform, int depth) { if (depth <= 0 || (Object)(object)transform == (Object)null) { return string.Empty; } StringBuilder stringBuilder = new StringBuilder(); stringBuilder.Append(((Object)transform).name); stringBuilder.Append('('); stringBuilder.Append(transform.childCount); stringBuilder.Append(')'); if (transform.childCount > 0) { stringBuilder.Append(": "); for (int i = 0; i < transform.childCount; i++) { if (i > 0) { stringBuilder.Append(", "); } stringBuilder.Append(DescribeHierarchy(transform.GetChild(i), depth - 1)); } } return stringBuilder.ToString(); } public void Setup() { //IL_0033: Unknown result type (might be due to invalid IL or missing references) //IL_0038: Unknown result type (might be due to invalid IL or missing references) //IL_005d: Unknown result type (might be due to invalid IL or missing references) //IL_0064: Expected O, but got Unknown //IL_0207: Unknown result type (might be due to invalid IL or missing references) //IL_020e: Expected O, but got Unknown //IL_01b6: Unknown result type (might be due to invalid IL or missing references) //IL_01bd: Expected O, but got Unknown //IL_03a5: Unknown result type (might be due to invalid IL or missing references) //IL_03c2: Unknown result type (might be due to invalid IL or missing references) //IL_03f6: Unknown result type (might be due to invalid IL or missing references) //IL_040c: Unknown result type (might be due to invalid IL or missing references) //IL_0411: Unknown result type (might be due to invalid IL or missing references) //IL_0417: Unknown result type (might be due to invalid IL or missing references) //IL_041c: Unknown result type (might be due to invalid IL or missing references) //IL_0428: Unknown result type (might be due to invalid IL or missing references) //IL_0299: Unknown result type (might be due to invalid IL or missing references) //IL_02a0: Expected O, but got Unknown //IL_0249: Unknown result type (might be due to invalid IL or missing references) //IL_04e7: Unknown result type (might be due to invalid IL or missing references) //IL_04ee: Expected O, but got Unknown if (def == null) { ManualLogSource? log = TOARuntime.Log; if (log != null) { log.LogError((object)"EventScan Setup: assign a EventScanDefinition before calling Setup()!"); } return; } ((Component)this).gameObject.transform.SetPositionAndRotation(def.Position.ToVector3(), Quaternion.identity); bool flag = default(bool); ManualLogSource log2; if (!TryBindAssetHierarchy()) { log2 = TOARuntime.Log; if (log2 != null) { BepInExErrorLogInterpolatedStringHandler val = new BepInExErrorLogInterpolatedStringHandler(137, 1, ref flag); if (flag) { ((BepInExLogInterpolatedStringHandler)val).AppendLiteral("EventScan '"); ((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>(def.WorldEventObjectFilter); ((BepInExLogInterpolatedStringHandler)val).AppendLiteral("' setup failed because the TOA EventScan AssetBundle prefab does not expose the required TOA/Legacy EventScan visual children."); } log2.LogError(val); } return; } ((Component)this).gameObject.SetActiveRecursively(true); if ((Object)(object)DisplayText == (Object)null && def.ShowDisplayText) { TryCreateDisplayTextFromVanillaCP(); } if ((Object)(object)DisplayText != (Object)null) { if (def.ShowDisplayText) { ((TMP_Text)DisplayText).SetText(LocalizedText.op_Implicit(def.DisplayText), true); ((TMP_Text)DisplayText).ForceMeshUpdate(false, false); Information.SetActive(true); ((Component)DisplayText).gameObject.SetActive(true); } else { foreach (TMP_Text componentsInChild in _root.GetComponentsInChildren<TMP_Text>(true)) { if ((Object)(object)componentsInChild != (Object)null) { componentsInChild.SetText(string.Empty, true); ((Component)componentsInChild).gameObject.SetActive(false); } } Information.SetActive(false); } } else if (def.ShowDisplayText) { log2 = TOARuntime.Log; if (log2 != null) { BepInExWarningLogInterpolatedStringHandler val2 = new BepInExWarningLogInterpolatedStringHandler(122, 1, ref flag); if (flag) { ((BepInExLogInterpolatedStringHandler)val2).AppendLiteral("EventScan '"); ((BepInExLogInterpolatedStringHandler)val2).AppendFormatted<string>(def.WorldEventObjectFilter); ((BepInExLogInterpolatedStringHandler)val2).AppendLiteral("' has ShowDisplayText=true but neither TOA EventScan nor vanilla CP text could provide a TextMeshPro component."); } log2.LogWarning(val2); } } log2 = TOARuntime.Log; if (log2 != null) { BepInExMessageLogInterpolatedStringHandler val3 = new BepInExMessageLogInterpolatedStringHandler(65, 3, ref flag); if (flag) { ((BepInExLogInterpolatedStringHandler)val3).AppendLiteral("EventScan '"); ((BepInExLogInterpolatedStringHandler)val3).AppendFormatted<string>(def.WorldEventObjectFilter); ((BepInExLogInterpolatedStringHandler)val3).AppendLiteral("': using TOA EventScan AssetBundle prefab at "); ((BepInExLogInterpolatedStringHandler)val3).AppendFormatted<Vector3>(((Component)this).gameObject.transform.position); ((BepInExLogInterpolatedStringHandler)val3).AppendLiteral(" radius="); ((BepInExLogInterpolatedStringHandler)val3).AppendFormatted<float>(def.Radius); ((BepInExLogInterpolatedStringHandler)val3).AppendLiteral("."); } log2.LogMessage(val3); } log2 = TOARuntime.Log; if (log2 != null) { BepInExMessageLogInterpolatedStringHandler val3 = new BepInExMessageLogInterpolatedStringHandler(80, 6, ref flag); if (flag) { ((BepInExLogInterpolatedStringHandler)val3).AppendLiteral("EventScan '"); ((BepInExLogInterpolatedStringHandler)val3).AppendFormatted<string>(def.WorldEventObjectFilter); ((BepInExLogInterpolatedStringHandler)val3).AppendLiteral("': bound Root='"); ((BepInExLogInterpolatedStringHandler)val3).AppendFormatted<string>(((Object)_root).name); ((BepInExLogInterpolatedStringHandler)val3).AppendLiteral("', Visual='"); ((BepInExLogInterpolatedStringHandler)val3).AppendFormatted<string>(((Object)_visual).name); ((BepInExLogInterpolatedStringHandler)val3).AppendLiteral("', Cylinder='"); ((BepInExLogInterpolatedStringHandler)val3).AppendFormatted<string>(((Object)_cylinder).name); ((BepInExLogInterpolatedStringHandler)val3).AppendLiteral("', Information='"); ((BepInExLogInterpolatedStringHandler)val3).AppendFormatted<string>(((Object)_information).name); ((BepInExLogInterpolatedStringHandler)val3).AppendLiteral("', Renderers="); ((BepInExLogInterpolatedStringHandler)val3).AppendFormatted<int>(_visualRenderers.Count); ((BepInExLogInterpolatedStringHandler)val3).AppendLiteral("."); } log2.LogMessage(val3); } TOAVec3 waiting = def.ColorSetting.Waiting; TOAVec3 active = def.ColorSetting.Active; Color_Waiting = new Color(waiting.x, waiting.y, waiting.z); Color_Active = new Color(active.x, active.y, active.z); float num = 0.16216217f; float num2 = Mathf.Max(0.01f, def.Radius); ((Component)this).gameObject.transform.localScale = new Vector3(num2, num2, num2); Transform transform = ((Component)this).gameObject.transform; transform.localPosition += Vector3.up * num; SetVisualColor(Color_Waiting); uint num3 = EOSNetworking.AllotReplicatorID(); if (num3 == 0) { TOANetworkStateAudit.Current.ReplicatorFailed("EventScan:" + def.WorldEventObjectFilter, "Replicator ID depleted"); ManualLogSource? log3 = TOARuntime.Log; if (log3 != null) { log3.LogError((object)"EventScan: Replicator ID depleted, cannot setup"); } return; } StateReplicator = TOAStateReplicatorCompat.Create(num3, new TOAEventScanStatus { Status = TOAEventScanState.Waiting }, (LifeTimeType)1, "EventScan:" + def.WorldEventObjectFilter); if (StateReplicator == null) { TOANetworkStateAudit.Current.ReplicatorFailed("EventScan:" + def.WorldEventObjectFilter, "StateReplicator creation failed"); log2 = TOARuntime.Log; if (log2 != null) { BepInExErrorLogInterpolatedStringHandler val = new BepInExErrorLogInterpolatedStringHandler(57, 1, ref flag); if (flag) { ((BepInExLogInterpolatedStringHandler)val).AppendLiteral("EventScan:"); ((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>(def.WorldEventObjectFilter); ((BepInExLogInterpolatedStringHandler)val).AppendLiteral(": StateReplicator creation failed, cannot setup"); } log2.LogError(val); } } else { StateReplicator.OnStateChanged += OnStateChange; TOANetworkStateAudit.Current.ReplicatorCreated("EventScan:" + def.WorldEventObjectFilter, num3, "Level"); } } private void TryCreateDisplayTextFromVanillaCP() { //IL_016d: Unknown result type (might be due to invalid IL or missing references) //IL_0174: Expected O, but got Unknown //IL_0031: Unknown result type (might be due to invalid IL or missing references) //IL_0038: Expected O, but got Unknown //IL_0142: Unknown result type (might be due to invalid IL or missing references) //IL_009a: Unknown result type (might be due to invalid IL or missing references) //IL_00a1: Expected O, but got Unknown bool flag = default(bool); try { GameObject loadedAsset = AssetAPI.GetLoadedAsset<GameObject>("Assets/AssetPrefabs/Complex/Generic/ChainedPuzzles/CP_Bioscan_sustained_RequireAll.prefab"); if ((Object)(object)loadedAsset == (Object)null || loadedAsset.transform.childCount == 0) { ManualLogSource log = TOARuntime.Log; if (log != null) { BepInExWarningLogInterpolatedStringHandler val = new BepInExWarningLogInterpolatedStringHandler(83, 1, ref flag); if (flag) { ((BepInExLogInterpolatedStringHandler)val).AppendLiteral("EventScan '"); ((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>(def.WorldEventObjectFilter); ((BepInExLogInterpolatedStringHandler)val).AppendLiteral("' could not clone display text because vanilla CP prefab was not loaded."); } log.LogWarning(val); } return; } Transform child = loadedAsset.transform.GetChild(0); if (child.childCount <= 1) { ManualLogSource log = TOARuntime.Log; if (log != null) { BepInExWarningLogInterpolatedStringHandler val = new BepInExWarningLogInterpolatedStringHandler(92, 1, ref flag); if (flag) { ((BepInExLogInterpolatedStringHandler)val).AppendLiteral("EventScan '"); ((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>(def.WorldEventObjectFilter); ((BepInExLogInterpolatedStringHandler)val).AppendLiteral("' could not clone display text because vanilla CP prefab hierarchy is unexpected."); } log.LogWarning(val); } } else { GameObject val2 = Object.Instantiate<GameObject>(((Component)child.GetChild(1)).gameObject); ((Object)val2).name = "TOA_EventScan_DisplayText"; val2.transform.SetParent(_information.transform, false); float num = Mathf.Max(0.01f, def.Radius); val2.transform.localScale = new Vector3(1f / num, 1f / num, 1f / num); DisplayText = val2.GetComponentInChildren<TextMeshPro>(true); } } catch (Exception ex) { ManualLogSource log = TOARuntime.Log; if (log != null) { BepInExWarningLogInterpolatedStringHandler val = new BepInExWarningLogInterpolatedStringHandler(61, 3, ref flag); if (flag) { ((BepInExLogInterpolatedStringHandler)val).AppendLiteral("EventScan '"); ((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>(def.WorldEventObjectFilter); ((BepInExLogInterpolatedStringHandler)val).AppendLiteral("' failed to clone display text from vanilla CP: "); ((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>(ex.GetType().Name); ((BepInExLogInterpolatedStringHandler)val).AppendLiteral(": "); ((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>(ex.Message); } log.LogWarning(val); } } } private void SetVisualColor(Color color) { //IL_0050: Unknown result type (might be due to invalid IL or missing references) //IL_0070: Unknown result type (might be due to invalid IL or missing references) //IL_0069: Unknown result type (might be due to invalid IL or missing references) if (_visualRenderers.Count == 0) { return; } foreach (Renderer visualRenderer in _visualRenderers) { if ((Object)(object)visualRenderer == (Object)null) { continue; } Material material = visualRenderer.material; if (!((Object)(object)material == (Object)null)) { if (material.HasProperty("_ColorA")) { material.SetColor("_ColorA", color); } if (material.HasProperty("_Color")) { material.SetColor("_Color", color); } material.color = color; } } } private void OnStateChange(TOAEventScanStatus oldState, TOAEventScanStatus newState, bool isRecall) { //IL_000e: Unknown result type (might be due to invalid IL or missing references) //IL_0014: Expected O, but got Unknown //IL_017d: Unknown result type (might be due to invalid IL or missing references) //IL_022f: Unknown result type (might be due to invalid IL or missing references) ManualLogSource log = TOARuntime.Log; if (log != null) { bool flag = default(bool); BepInExWarningLogInterpolatedStringHandler val = new BepInExWarningLogInterpolatedStringHandler(15, 2, ref flag); if (flag) { ((BepInExLogInterpolatedStringHandler)val).AppendLiteral("EventScan: "); ((BepInExLogInterpolatedStringHandler)val).AppendFormatted<TOAEventScanState>(oldState.Status); ((BepInExLogInterpolatedStringHandler)val).AppendLiteral(" => "); ((BepInExLogInterpolatedStringHandler)val).AppendFormatted<TOAEventScanState>(newState.Status); } log.LogWarning(val); } if (isRecall) { TOANetworkStateAudit.Current.StateRecall("EventScan:" + def.WorldEventObjectFilter, oldState.Status.ToString(), newState.Status.ToString()); } switch (newState.Status) { case TOAEventScanState.Disabled: { m_colorLerpDelta = 0f; TextMeshPro displayText3 = DisplayText; if (displayText3 != null) { ((Component)displayText3).gameObject.SetActive(false); } Information.SetActive(false); Cylinder.SetActive(false); CoroutineManager.BlinkOut(Visual, 0f); break; } case TOAEventScanState.Waiting: if (!Visual.active) { CoroutineManager.BlinkIn(Visual, 0f); Cylinder.SetActive(true); if (def.ShowDisplayText) { Information.SetActive(true); TextMeshPro displayText2 = DisplayText; if (displayText2 != null) { ((Component)displayText2).gameObject.SetActive(true); } } } if (!isRecall && ExecuteEventsLocally && oldState.Status == TOAEventScanState.Active) { using (TOAType2003TriggerScope.PushRadius("TOA_EventScan_Deactivate", Position, def.Radius)) { ExecuteConfiguredEvents(def.EventsOnDeactivate, "Deactivate"); } } break; case TOAEventScanState.Active: if (!Visual.active) { CoroutineManager.BlinkIn(Visual, 0f); Cylinder.SetActive(true); if (def.ShowDisplayText) { Information.SetActive(true); TextMeshPro displayText = DisplayText; if (displayText != null) { ((Component)displayText).gameObject.SetActive(true); } } } if (!isRecall && ExecuteEventsLocally && oldState.Status == TOAEventScanState.Waiting) { using (TOAType2003TriggerScope.PushRadius("TOA_EventScan_Activate", Position, def.Radius)) { ExecuteConfiguredEvents(def.EventsOnActivate, "Activate"); } } break; } TOAEventScanManager.Current.EvaluateIndexGroups(!isRecall); } private void ExecuteConfiguredEvents(List<WardenObjectiveEventData> events, string transition) { //IL_0022: Unknown result type (might be due to invalid IL or missing references) //IL_0028: Expected O, but got Unknown bool flag = default(bool); foreach (WardenObjectiveEventData @event in events) { ManualLogSource log = TOARuntime.Log; if (log != null) { BepInExMessageLogInterpolatedStringHandler val = new BepInExMessageLogInterpolatedStringHandler(86, 4, ref flag); if (flag) { ((BepInExLogInterpolatedStringHandler)val).AppendLiteral("EventScan "); ((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>(transition); ((BepInExLogInterpolatedStringHandler)val).AppendLiteral(": dispatching configured vanilla/custom event. Filter='"); ((BepInExLogInterpolatedStringHandler)val).AppendFormatted<string>(@event.WorldEventObjectFilter); ((BepInExLogInterpolatedStringHandler)val).AppendLiteral("', Count="); ((BepInExLogInterpolatedStringHandler)val).AppendFormatted<int>(@event.Count); ((BepInExLogInterpolatedStringHandler)val).AppendLiteral(", Duration="); ((BepInExLogInterpolatedStringHandler)val).AppendFormatted<float>(@event.Duration, "0.###"); ((BepInExLogInterpolatedStringHandler)val).AppendLiteral("."); } log.LogMessage(val); } WardenObjectiveManager.CheckAndExecuteEventsOnTrigger(@event, (eWardenObjectiveEventTrigger)0, true, 0f); } } public void ChangeToState(TOAEventScanState newState) { ChangedToStateUnsynced(newState); if (StateReplicator != null && TOANetworkStateAudit.Current.CanMasterWrite("EventScan:" + def.WorldEventObjectFilter, $"SetState:{newState}")) { StateReplicator.SetState(new TOAEventScanStatus { Status = newState }); } } private void ChangedToStateUnsynced(TOAEventScanState newState) { } private void Update() { //IL_0058: Unknown result type (might be due to invalid IL or missing references) //IL_005e: Unknown result type (might be due to invalid IL or missing references) //IL_0073: Unknown result type (might be due to invalid IL or missing references) //IL_0078: Unknown result type (might be due to invalid IL or missing references) //IL_007b: Unknown result type (might be due to invalid IL or missing references) //IL_0123: Unknown result type (might be due to invalid IL or missing references) //IL_012a: Unknown result type (might be due to invalid IL or missing references) //IL_012f: Unknown result type (might be due to invalid IL or missing references) //IL_0134: Unknown result type (might be due to invalid IL or missing references) //IL_01de: Unknown result type (might be due to invalid IL or missing references) //IL_01e3: Unknown result type (might be due to invalid IL or missing references) //IL_01e5: Unknown result type (might be due to invalid IL or missing references) //IL_01ea: Unknown result type (might be due to invalid IL or missing references) //IL_01ec: Unknown result type (might be due to invalid IL or missing references) //IL_01ee: Unknown result type (might be due to invalid IL or missing references) //IL_01f3: Unknown result type (might be due to invalid IL or missing references) //IL_01f5: Unknown result type (might be due to invalid IL or missing references) //IL_0207: Unknown result type (might be due to invalid IL or missing references) //IL_020c: Unknown result type (might be due to invalid IL or missing references) //IL_01f9: Unknown result type (might be due to invalid IL or missing references) //IL_01fc: Invalid comparison between Unknown and I4 //IL_0266: Unknown result type (might be due to invalid IL or missing references) //IL_026b: Unknown result type (might be due to invalid IL or missing references) //IL_026d: Unknown result type (might be due to invalid IL or missing references) //IL_0272: Unknown result type (might be due to invalid IL or missing references) //IL_021c: Unknown result type (might be due to invalid IL or missing references) //IL_0221: Unknown result type (might be due to invalid IL or missing references) //IL_0235: Unknown result type (might be due to invalid IL or missing references) //IL_023c: Expected O, but got Unknown //IL_024e: Unknown result type (might be due to invalid IL or missing references) //IL_0250: Unknown result type (might be due to invalid IL or missing references) if (StateReplicator == null) { return; } TOAEventScanState status = StateReplicator.State.Status; if (status == TOAEventScanState.Disabled) { return; } float num = Clock.Delta / 0.5f; if (status == TOAEventScanState.Waiting) { num = 0f - num; } float colorLerpDelta = m_colorLerpDelta; m_colorLerpDelta = Mathf.Clamp01(m_colorLerpDelta + num); if (!Mathf.Approximately(colorLerpDelta, m_colorLerpDelta)) { Color visualColor = Color.Lerp(Color_Waiting, Color_Active, Mathf.Pow(m_colorLerpDelta, 5f)); SetVisualColor(visualColor); } if (!float.IsNaN(time) && Clock.Time < time + 0.3f) { return; } time = Clock.Time + 0.3f; if (def.ActiveCondition.RequiredPlayerCount == 0 && def.ActiveCondition.RequiredBigPickupIndices.Count == 0) { return; } bool flag = false; bool flag2 = false; Vector3 val; if (def.ActiveCondition.RequiredPlayerCount > 0) { int num2 = 0; Enumerator<PlayerAgent> enumerator = PlayerManager.PlayerAgentsInLevel.GetEnumerator(); while (enumerator.MoveNext()) { PlayerAgent current = enumerator.Current; if (!((Object)(object)current != (Object)null) || !((Agent)current).Alive) { continue; } val = Position - ((Agent)current).Position; if (((Vector3)(ref val)).magnitude < def.Radius) { num2++; if (num2 >= def.ActiveCondition.RequiredPlayerCount) { flag = true; break; } } } } else { flag = true; } if (flag) { List<int> requiredBigPickupIndices = def.ActiveCondition.RequiredBigPickupIndices; if (requiredBigPickupIndices.Count > 0) { int num3 = 0; bool flag3 = default(bool); foreach (int item in requiredBigPickupIndices) { CarryItemPickup_Core bigPickupItem = PuzzleReqItemManager.Current.GetBigPickupItem(item); if ((Object)(object)bigPickupItem == (Object)null) { num3++; continue; } pPickupItemState currentState = bigPickupItem.m_sync.GetCurrentState(); Vector3 zero = Vector3.zero; ePickupItemStatus status2 = currentState.status; if ((int)status2 != 0) { if ((int)status2 != 1) { ManualLogSource log = TOARuntime.Log; if (log != null) { BepInExErrorLogInterpolatedStringHandler val2 = new BepInExErrorLogInterpolatedStringHandler(24, 1, ref flag3); if (flag3) { ((BepInExLogInterpolatedStringHandler)val2).AppendLiteral("Item has invalid state: "); ((BepInExLogInterpolatedStringHandler)val2).AppendFormatted<ePickupItemStatus>(currentState.status); } log.LogError(val2); } continue; } zero = ((Component)bigPickupItem.PickedUpByPlayer).transform.position; } else { zero = ((Component)bigPickupItem).transform.position; } val = Position - zero; if (((Vector3)(ref val)).magnitude < def.Radius) { num3++; } } flag2 = num3 >= requiredBigPickupIndices.Count; } else { flag2 = true; } } switch (status) { case TOAEventScanState.Waiting: if (flag && flag2) { ChangeToState(TOAEventScanState.Active); } break; case TOAEventScanState.Active: if (!flag || !flag2) { ChangeToState(TOAEventScanState.Waiting); } break; } } private void OnDestroy() { def = null; VisualRenderer = null;