Decompiled source of CustomCampaignTools v1.1.0
Mods/CustomCampaignTools.dll
Decompiled 3 days 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.IO; using System.Linq; using System.Reflection; using System.Runtime.CompilerServices; using System.Runtime.Serialization; using System.Runtime.Versioning; using BoneLib; using BoneLib.BoneMenu; using BoneLib.Notifications; using BrowsingPlus; using BrowsingPlus.OverrideImplements; using BrowsingPlus.PanelUI; using CustomCampaignTools; using CustomCampaignTools.Bonemenu; using CustomCampaignTools.Debug; using CustomCampaignTools.Patching; using CustomCampaignTools.SDK; using CustomCampaignTools.Timing; using HarmonyLib; using Il2CppCysharp.Threading.Tasks; using Il2CppInterop.Runtime.InteropTypes; using Il2CppInterop.Runtime.InteropTypes.Arrays; using Il2CppInterop.Runtime.InteropTypes.Fields; using Il2CppSLZ.Bonelab; using Il2CppSLZ.Bonelab.SaveData; using Il2CppSLZ.Marrow; using Il2CppSLZ.Marrow.AI; using Il2CppSLZ.Marrow.Audio; using Il2CppSLZ.Marrow.Interaction; using Il2CppSLZ.Marrow.Pool; using Il2CppSLZ.Marrow.SaveData; using Il2CppSLZ.Marrow.SceneStreaming; using Il2CppSLZ.Marrow.Utilities; using Il2CppSLZ.Marrow.Warehouse; using Il2CppSLZ.UI; using Il2CppSystem; using Il2CppSystem.Collections.Generic; using Il2CppTMPro; using Il2CppUltEvents; using MelonLoader; using MelonLoader.Utils; using Microsoft.CodeAnalysis; using Newtonsoft.Json; using UnityEngine; using UnityEngine.Events; using UnityEngine.UI; [assembly: CompilationRelaxations(8)] [assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)] [assembly: Debuggable(DebuggableAttribute.DebuggingModes.Default | DebuggableAttribute.DebuggingModes.DisableOptimizations | DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints | DebuggableAttribute.DebuggingModes.EnableEditAndContinue)] [assembly: AssemblyTitle("Allows Modders to add their own Campaign functionality to Marrow Campaigns.")] [assembly: AssemblyDescription("Allows Modders to add their own Campaign functionality to Marrow Campaigns.")] [assembly: AssemblyCompany("LabWorks")] [assembly: AssemblyProduct("Custom Campain Tools")] [assembly: AssemblyCopyright("Developed by EvroDev")] [assembly: AssemblyTrademark("LabWorks")] [assembly: AssemblyFileVersion("1.1.0")] [assembly: MelonInfo(typeof(Main), "Custom Campain Tools", "1.1.0", "EvroDev", "")] [assembly: MelonOptionalDependencies(new string[] { "BrowsingPlus" })] [assembly: MelonGame("Stress Level Zero", "BONELAB")] [assembly: TargetFramework(".NETFramework,Version=v4.7.2", FrameworkDisplayName = ".NET Framework 4.7.2")] [assembly: AssemblyVersion("1.1.0.0")] [module: RefSafetyRules(11)] namespace Microsoft.CodeAnalysis { [CompilerGenerated] [Microsoft.CodeAnalysis.Embedded] internal sealed class EmbeddedAttribute : Attribute { } } namespace System.Runtime.CompilerServices { [CompilerGenerated] [Microsoft.CodeAnalysis.Embedded] [AttributeUsage(AttributeTargets.Module, AllowMultiple = false, Inherited = false)] internal sealed class RefSafetyRulesAttribute : Attribute { public readonly int Version; public RefSafetyRulesAttribute(int P_0) { Version = P_0; } } } namespace CustomCampaignTools { public static class AmmoFunctions { public static void ClearAmmo(Campaign campaign) { if (CampaignUtilities.IsCampaignLevel(((Scannable)SceneStreamer.Session.Level).Barcode.ID, out var _, out var _)) { AmmoInventory.Instance.ClearAmmo(); } campaign.saveData.LoadedAmmoSaves.Clear(); campaign.saveData.SaveToDisk(); } public static void LoadAmmoFromLevel(string levelBarcode, bool isLoadCheckpoint) { if (CampaignUtilities.IsCampaignLevel(levelBarcode, out var campaign, out var levelType) && campaign.SaveLevelAmmo && levelType == CampaignLevelType.MainLevel) { int levelIndex = campaign.GetLevelIndex(levelBarcode); try { AmmoInventory.Instance.ClearAmmo(); } catch { } CampaignLevel[] mainLevels = campaign.mainLevels; for (int i = 0; i < levelIndex; i++) { CampaignLevel level = mainLevels[i]; AmmoInventory.Instance.AddCartridge(AmmoInventory.Instance.lightAmmoGroup, campaign.saveData.GetSavedAmmo(level).LightAmmo); AmmoInventory.Instance.AddCartridge(AmmoInventory.Instance.mediumAmmoGroup, campaign.saveData.GetSavedAmmo(level).MediumAmmo); AmmoInventory.Instance.AddCartridge(AmmoInventory.Instance.heavyAmmoGroup, campaign.saveData.GetSavedAmmo(level).HeavyAmmo); } } } } [HarmonyPatch(typeof(AmmoInventory), "Awake")] public static class AmmoInventoryAwake { public static void Postfix() { string iD = ((Scannable)SceneStreamer.Session.Level).Barcode.ID; if (CampaignUtilities.IsCampaignLevel(iD, out var campaign, out var levelType) && levelType == CampaignLevelType.MainLevel) { int levelIndex = campaign.GetLevelIndex(iD); AmmoInventory.Instance.ClearAmmo(); for (int i = 0; i < levelIndex; i++) { AmmoInventory.Instance.AddCartridge(AmmoInventory.Instance.lightAmmoGroup, campaign.saveData.GetSavedAmmo(campaign.GetLevelBarcodeByIndex(i)).LightAmmo); AmmoInventory.Instance.AddCartridge(AmmoInventory.Instance.mediumAmmoGroup, campaign.saveData.GetSavedAmmo(campaign.GetLevelBarcodeByIndex(i)).MediumAmmo); AmmoInventory.Instance.AddCartridge(AmmoInventory.Instance.heavyAmmoGroup, campaign.saveData.GetSavedAmmo(campaign.GetLevelBarcodeByIndex(i)).HeavyAmmo); } if (SavepointFunctions.CurrentLevelLoadedByContinue) { CampaignSaveData.SavePoint loadedSavePoint = Campaign.Session.saveData.LoadedSavePoint; AmmoInventory.Instance.AddCartridge(AmmoInventory.Instance.lightAmmoGroup, loadedSavePoint.MidLevelAmmoSave.LightAmmo); AmmoInventory.Instance.AddCartridge(AmmoInventory.Instance.mediumAmmoGroup, loadedSavePoint.MidLevelAmmoSave.MediumAmmo); AmmoInventory.Instance.AddCartridge(AmmoInventory.Instance.heavyAmmoGroup, loadedSavePoint.MidLevelAmmoSave.HeavyAmmo); } } } } public class Campaign { public string Name; public string PalletBarcode; public CampaignLevel IntroLevel; public CampaignLevel MenuLevel; public CampaignLevel[] mainLevels; public CampaignLevel[] extraLevels; public string LoadScene; private MonoDisc _loadMusicDatacard; private AudioClip _loadSceneMusic; public bool ShowInMenu; public bool PrioritizeInLevelPanel = true; public bool RestrictDevTools; public AvatarRestrictionType AvatarRestrictionType = AvatarRestrictionType.DisableBodyLog | AvatarRestrictionType.RestrictAvatar; private string defaultCampaignAvatar; private string fallbackAvatar; private string _cachedAvatar; public string[] WhitelistedAvatars; public bool SaveLevelInventory; public List<string> InventorySaveLimit = new List<string>(); public bool SaveLevelAmmo; private MonoDisc _achievementUnlockSoundDatacard; private AudioClip _achievementUnlockSound; public List<AchievementData> Achievements = new List<AchievementData>(); public bool LockInCampaign; public bool LockLevelsUntilEntered; public List<string> CampaignUnlockCrates = new List<string>(); public CampaignSaveData saveData; public static Campaign Session; public static string lastLoadedCampaignLevel; private static bool _sessionLocked; public static List<string> RegisteredJsonPaths = new List<string>(); public AudioClip LoadSceneMusic => _loadSceneMusic; public string CampaignAvatar { get { //IL_002f: Unknown result type (might be due to invalid IL or missing references) //IL_0039: Expected O, but got Unknown if (_cachedAvatar == string.Empty || _cachedAvatar == null) { if (MarrowGame.assetWarehouse.HasCrate(new Barcode(defaultCampaignAvatar))) { _cachedAvatar = defaultCampaignAvatar; } else { _cachedAvatar = fallbackAvatar; } } return _cachedAvatar; } } public AudioClip AchievementUnlockSound => _achievementUnlockSound; public bool DEVMODE { get; private set; } = false; public CampaignLevel[] AllLevels { get { CampaignLevel[] array = mainLevels; CampaignLevel[] array2 = extraLevels; int num = 0; CampaignLevel[] array3 = new CampaignLevel[2 + (array.Length + array2.Length)]; CampaignLevel[] array4 = array; foreach (CampaignLevel campaignLevel in array4) { array3[num] = campaignLevel; num++; } CampaignLevel[] array5 = array2; foreach (CampaignLevel campaignLevel in array5) { array3[num] = campaignLevel; num++; } array3[num] = MenuLevel; num++; array3[num] = IntroLevel; return array3; } } public static bool SessionActive => Session != null; public static bool SessionLocked => SessionActive && _sessionLocked; internal static Campaign RegisterCampaign(CampaignLoadingData data) { //IL_01cf: Unknown result type (might be due to invalid IL or missing references) //IL_01e4: Expected O, but got Unknown //IL_0359: Unknown result type (might be due to invalid IL or missing references) //IL_036e: Expected O, but got Unknown Campaign campaign = new Campaign(); try { campaign.Name = data.Name; if (data.InitialLevel.levelBarcode == "null.empty.barcode") { campaign.MenuLevel = new CampaignLevel(data.MainLevels[0], CampaignLevelType.MainLevel); } else { campaign.MenuLevel = new CampaignLevel(data.InitialLevel, CampaignLevelType.Menu); } if (data.IntroLevel == null || data.IntroLevel.levelBarcode == "null.empty.barcode") { campaign.IntroLevel = new CampaignLevel(campaign.MenuLevel.sBarcode, campaign.MenuLevel.Title, CampaignLevelType.Intro); } else { campaign.IntroLevel = new CampaignLevel(data.IntroLevel, CampaignLevelType.Intro); } campaign.mainLevels = data.MainLevels.Select((SerializedLevelSetup l) => new CampaignLevel(l, CampaignLevelType.MainLevel)).ToArray(); campaign.extraLevels = data.ExtraLevels.Select((SerializedLevelSetup l) => new CampaignLevel(l, CampaignLevelType.ExtraLevel)).ToArray(); if (data.LoadScene == "null.empty.barcode") { campaign.LoadScene = "SLZ.BONELAB.CORE.Level.LevelModLevelLoad"; } else { campaign.LoadScene = data.LoadScene; } campaign.saveData = new CampaignSaveData(campaign); if (data.LoadSceneMusic != null && data.LoadSceneMusic != "null.empty.barcode") { MarrowGame.assetWarehouse.TryGetDataCard<MonoDisc>(new Barcode(data.LoadSceneMusic), ref campaign._loadMusicDatacard); campaign._loadMusicDatacard.AudioClip.LoadAsset(Action<AudioClip>.op_Implicit((Action<AudioClip>)delegate(AudioClip a) { campaign._loadSceneMusic = a; ((Object)campaign._loadSceneMusic).hideFlags = (HideFlags)32; })); } campaign.ShowInMenu = data.ShowInMenu; if (data.Version == 0) { campaign.PrioritizeInLevelPanel = true; } else { campaign.PrioritizeInLevelPanel = data.PrioritizeInLevelPanel; } campaign.LockLevelsUntilEntered = data.UnlockableLevels; campaign.AvatarRestrictionType = data.AvatarRestrictionType; campaign.WhitelistedAvatars = data.WhitelistedAvatars.ToArray(); campaign.RestrictDevTools = data.RestrictDevTools; campaign.defaultCampaignAvatar = data.CampaignAvatar; campaign.fallbackAvatar = data.BaseGameFallbackAvatar; campaign.SaveLevelInventory = data.SaveLevelWeapons; campaign.InventorySaveLimit = data.InventorySaveLimit; campaign.SaveLevelAmmo = data.SaveLevelAmmo; campaign.Achievements = data.Achievements; campaign.LockInCampaign = data.LockInCampaign; if (data.CampaignUnlockCrates != null) { campaign.CampaignUnlockCrates = data.CampaignUnlockCrates; } if (data.AchievementUnlockSound != null && data.AchievementUnlockSound != "null.empty.barcode") { MarrowGame.assetWarehouse.TryGetDataCard<MonoDisc>(new Barcode(data.AchievementUnlockSound), ref campaign._achievementUnlockSoundDatacard); campaign._achievementUnlockSoundDatacard.AudioClip.LoadAsset(Action<AudioClip>.op_Implicit((Action<AudioClip>)delegate(AudioClip a) { campaign._achievementUnlockSound = a; ((Object)campaign._achievementUnlockSound).hideFlags = (HideFlags)32; })); } if (campaign.Achievements != null) { foreach (AchievementData achievement in campaign.Achievements) { achievement.Init(); } } campaign.DEVMODE = data.DevBuild; if (data.HideCratesFromGachapon != null) { GashaponHider.AddCratesToHide(data.HideCratesFromGachapon); } CampaignUtilities.LoadedCampaigns.Add(campaign); CampaignBoneMenu.CreateCampaignPage(BoneMenuCreator.campaignCategory, campaign); } catch (Exception arg) { MelonLogger.Error($"Failed to register campaign {data.Name}: {arg}"); } return campaign; } public static Campaign RegisterCampaignFromJson(string json) { //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_000e: Unknown result type (might be due to invalid IL or missing references) //IL_0017: Expected O, but got Unknown JsonSerializerSettings val = new JsonSerializerSettings { ReferenceLoopHandling = (ReferenceLoopHandling)2, PreserveReferencesHandling = (PreserveReferencesHandling)1 }; CampaignLoadingData data = JsonConvert.DeserializeObject<CampaignLoadingData>(json, val); return RegisterCampaign(data); } public void Enter() { //IL_0067: Unknown result type (might be due to invalid IL or missing references) //IL_0071: Expected O, but got Unknown //IL_0049: Unknown result type (might be due to invalid IL or missing references) //IL_0053: Expected O, but got Unknown if (LockInCampaign) { _sessionLocked = true; } Session = this; if (!saveData.SkipIntro && IntroLevel.IsValid()) { FadeLoader.Load(IntroLevel.Barcode, new Barcode(LoadScene)); } else { FadeLoader.Load(MenuLevel.Barcode, new Barcode(LoadScene)); } } public void Exit() { //IL_000c: Unknown result type (might be due to invalid IL or missing references) //IL_0016: Unknown result type (might be due to invalid IL or missing references) //IL_0020: Expected O, but got Unknown //IL_0020: Expected O, but got Unknown _sessionLocked = false; FadeLoader.Load(new Barcode("fa534c5a868247138f50c62e424c4144.Level.VoidG114"), new Barcode("fa534c5a83ee4ec6bd641fec424c4142.Level.DefaultLoad")); } public int GetLevelIndex(string levelBarcode, CampaignLevelType levelType = CampaignLevelType.MainLevel) { return Array.IndexOf(GetBarcodeArrayOfLevelType(levelType), levelBarcode); } public string GetLevelBarcodeByIndex(int index, CampaignLevelType levelType = CampaignLevelType.MainLevel) { return GetBarcodeArrayOfLevelType(levelType)[index]; } private string[] GetBarcodeArrayOfLevelType(CampaignLevelType type) { return type switch { CampaignLevelType.Intro => new string[1] { IntroLevel.sBarcode }, CampaignLevelType.Menu => new string[1] { MenuLevel.sBarcode }, CampaignLevelType.MainLevel => mainLevels.ToBarcodeStrings().ToArray(), CampaignLevelType.ExtraLevel => extraLevels.ToBarcodeStrings().ToArray(), _ => AllLevels.ToBarcodeStrings().ToArray(), }; } public CampaignLevelType TypeOfLevel(string barcode) { if (IntroLevel.Barcode.ID == barcode) { return CampaignLevelType.Intro; } if (MenuLevel.Barcode.ID == barcode) { return CampaignLevelType.Menu; } if (mainLevels.ToBarcodeStrings().Contains(barcode)) { return CampaignLevelType.MainLevel; } return CampaignLevelType.ExtraLevel; } public CampaignLevel[] GetUnlockedLevels() { List<CampaignLevel> list = new List<CampaignLevel>(); list.Add(MenuLevel); CampaignLevel[] array = mainLevels; foreach (CampaignLevel campaignLevel in array) { if (saveData.UnlockedLevels.Contains(campaignLevel.sBarcode) || !LockLevelsUntilEntered) { list.Add(campaignLevel); } } CampaignLevel[] array2 = extraLevels; foreach (CampaignLevel campaignLevel2 in array2) { if (saveData.UnlockedLevels.Contains(campaignLevel2.sBarcode) || !LockLevelsUntilEntered) { list.Add(campaignLevel2); } } return list.ToArray(); } public static void OnInitialize() { Hooking.OnLevelLoaded += OnLevelLoaded; AssetWarehouse._onReady += Action.op_Implicit((Action)delegate { try { LoadCampaignsFromMods(); } catch (Exception ex) { MelonLogger.Error("Coudnt load the campaigns from the mods folder: " + ex.Message); } AssetWarehouse instance = AssetWarehouse.Instance; instance.OnPalletAdded += Action<Barcode>.op_Implicit((Action<Barcode>)delegate { LoadCampaignsFromMods(); }); }); } public static void LoadCampaignsFromMods() { string[] directories = Directory.GetDirectories(MarrowSDK.RuntimeModsPath); string[] array = directories; foreach (string path in array) { string[] files = Directory.GetFiles(path, "campaign.json.bundle"); if (files.Length != 0 && !RegisteredJsonPaths.Contains(files[0])) { RegisteredJsonPaths.Add(files[0]); string json = File.ReadAllText(files[0]); try { RegisterCampaignFromJson(json); } catch { } } } } public static void OnLevelLoaded(LevelInfo info) { //IL_0001: Unknown result type (might be due to invalid IL or missing references) //IL_001c: Unknown result type (might be due to invalid IL or missing references) if (CampaignUtilities.IsCampaignLevel(info.barcode, out Session, out var _)) { lastLoadedCampaignLevel = info.barcode; } } public static void OnUIRigCreated() { //IL_0046: Unknown result type (might be due to invalid IL or missing references) //IL_0050: Expected O, but got Unknown //IL_004b: Unknown result type (might be due to invalid IL or missing references) //IL_0055: Expected O, but got Unknown //IL_005c: Unknown result type (might be due to invalid IL or missing references) //IL_0066: Expected O, but got Unknown //IL_0061: Unknown result type (might be due to invalid IL or missing references) //IL_006b: Expected O, but got Unknown if (SessionActive) { PopUpMenuView popUpMenu = Player.UIRig.popUpMenu; if (Session.RestrictDevTools && !Session.saveData.DevToolsUnlocked) { popUpMenu.crate_SpawnGun = new GenericCrateReference(new Barcode("null.empty.barcode")); popUpMenu.crate_Nimbus = new GenericCrateReference(new Barcode("null.empty.barcode")); } } } } public static class CampaignUtilities { public static List<Campaign> LoadedCampaigns = new List<Campaign>(); private static List<Campaign> _menuCampaigns; public static List<Campaign> CampaignsToShowInMenu { get { if (_menuCampaigns == null) { _menuCampaigns = LoadedCampaigns.Where((Campaign c) => c.ShowInMenu).ToList(); } return _menuCampaigns; } } public static Campaign GetFromName(string name) { return LoadedCampaigns.FirstOrDefault((Campaign x) => x.Name == name); } public static Campaign GetFromLevel(string barcode) { return LoadedCampaigns.FirstOrDefault((Campaign x) => x.AllLevels.Select((CampaignLevel l) => l.Barcode.ID).Contains(barcode)); } public static Campaign GetFromLevel(Barcode barcode) { return GetFromLevel(barcode.ID); } public static Campaign GetFromLevel(LevelCrateReference level) { return GetFromLevel(((ScannableReference)level).Barcode.ID); } public static Campaign GetFromLevel() { return GetFromLevel(((Scannable)SceneStreamer.Session.Level).Barcode.ID); } public static bool IsCampaignLevel(string levelBarcode) { return GetFromLevel(levelBarcode) != null; } public static bool IsCampaignLevel(string levelBarcode, out Campaign campaign, out CampaignLevelType levelType) { campaign = GetFromLevel(levelBarcode); if (campaign != null) { levelType = campaign.TypeOfLevel(levelBarcode); } else { levelType = CampaignLevelType.None; } return campaign != null; } } public enum CampaignLevelType { None, Intro, Menu, MainLevel, ExtraLevel } public class CampaignLevel { public Campaign campaign; public Barcode Barcode; private string overrideName = ""; public CampaignLevelType type; private LevelCrate _crate; public string Title { get { if (overrideName == string.Empty) { return ((Scannable)crate).Title; } return overrideName; } } public string sBarcode => Barcode.ID; public LevelCrate crate { get { if ((Object)(object)_crate != (Object)null) { return _crate; } MarrowGame.assetWarehouse.TryGetCrate<LevelCrate>(Barcode, ref _crate); return _crate; } } public bool isUnlocked => !campaign.LockLevelsUntilEntered || campaign.saveData.UnlockedLevels.Contains(sBarcode); public CampaignLevel(string barcode, string name, CampaignLevelType type) { //IL_0015: Unknown result type (might be due to invalid IL or missing references) //IL_001f: Expected O, but got Unknown Barcode = new Barcode(barcode); overrideName = name; this.type = type; } public CampaignLevel(SerializedLevelSetup levelSetup, CampaignLevelType type) { //IL_001a: Unknown result type (might be due to invalid IL or missing references) //IL_0024: Expected O, but got Unknown Barcode = new Barcode(levelSetup.levelBarcode); overrideName = levelSetup.levelName; this.type = type; } public CampaignLevel(CampaignLevel copy) { Barcode = copy.Barcode; overrideName = copy.overrideName; type = copy.type; } public bool IsValid() { Crate val = default(Crate); return AssetWarehouse.Instance.TryGetCrate(Barcode, ref val); } public static implicit operator Barcode(CampaignLevel c) { return c.Barcode; } public static implicit operator LevelCrate(CampaignLevel c) { return c.crate; } } public static class CampaignLevelListManipulation { public static List<string> ToBarcodeStrings(this CampaignLevel[] list) { return list.Select((CampaignLevel c) => c.Barcode.ID).ToList(); } public static List<Barcode> ToBarcodes(this CampaignLevel[] list) { return list.Select((CampaignLevel c) => c.Barcode).ToList(); } public static List<string> ToNames(this List<CampaignLevel> list) { return list.Select((CampaignLevel c) => c.Title).ToList(); } public static List<LevelCrate> ToCrates(this CampaignLevel[] list) { return (from c in list select c.crate into c where (Object)(object)c != (Object)null select c).ToList(); } } public class CampaignSaveData { public class SaveData { public SavePoint SavePoint { get; set; } public List<AmmoSave> AmmoSaves { get; set; } = new List<AmmoSave>(); public Dictionary<string, InventoryData> InventorySaves { get; set; } = new Dictionary<string, InventoryData>(); public List<FloatData> FloatData { get; set; } = new List<FloatData>(); public bool DevToolsUnlocked { get; set; } public bool AvatarUnlocked { get; set; } public List<string> UnlockedAchievements { get; set; } = new List<string>(); public List<string> UnlockedLevels { get; set; } = new List<string>(); public bool SkipIntro { get; set; } public List<LevelTime> LevelTimes { get; set; } = new List<LevelTime>(); public List<TrialTime> TrialTimes { get; set; } = new List<TrialTime>(); public SaveData() { } public SaveData(CampaignSaveData parent) { SavePoint = parent.LoadedSavePoint; AmmoSaves = parent.LoadedAmmoSaves; InventorySaves = parent.LoadedInventorySaves; FloatData = parent.LoadedFloatDatas; DevToolsUnlocked = parent.DevToolsUnlocked; AvatarUnlocked = parent.AvatarUnlocked; SkipIntro = parent.SkipIntro; UnlockedAchievements = parent.UnlockedAchievements; UnlockedLevels = parent.UnlockedLevels; LevelTimes = parent.LevelTimes; TrialTimes = parent.TrialTimes; CleanData(); } private void CleanData() { List<AmmoSave> list = new List<AmmoSave>(); foreach (AmmoSave ammoSafe in AmmoSaves) { if (string.IsNullOrEmpty(ammoSafe.LevelBarcode)) { list.Add(ammoSafe); } } foreach (AmmoSave item in list) { AmmoSaves.Remove(item); } List<LevelTime> list2 = new List<LevelTime>(); foreach (LevelTime levelTime in LevelTimes) { if (string.IsNullOrEmpty(levelTime.LevelBarcode)) { list2.Add(levelTime); } } foreach (LevelTime item2 in list2) { LevelTimes.Remove(item2); } } public void LoadSaveData(CampaignSaveData parent) { parent.LoadedSavePoint = SavePoint; parent.LoadedAmmoSaves = AmmoSaves; parent.LoadedInventorySaves = InventorySaves ?? new Dictionary<string, InventoryData>(); parent.LoadedFloatDatas = FloatData ?? new List<FloatData>(); parent.DevToolsUnlocked = DevToolsUnlocked; parent.AvatarUnlocked = AvatarUnlocked; parent.SkipIntro = SkipIntro; parent.UnlockedAchievements = UnlockedAchievements ?? new List<string>(); parent.UnlockedLevels = UnlockedLevels ?? new List<string>(); parent.LevelTimes = LevelTimes ?? new List<LevelTime>(); parent.TrialTimes = TrialTimes ?? new List<TrialTime>(); } } public class FloatData { public string Key; public float Value; public FloatData(string key) { Key = key; Value = 0f; base..ctor(); } } public struct AmmoSave { public string LevelBarcode { get; set; } public int LightAmmo { get; set; } public int MediumAmmo { get; set; } public int HeavyAmmo { get; set; } public int GetCombinedTotal() { return LightAmmo + MediumAmmo + HeavyAmmo; } } public struct SavePoint { public string LevelBarcode; public float PositionX; public float PositionY; public float PositionZ; public InventoryData InventoryData; public AmmoSave MidLevelAmmoSave; public List<BarcodePosRot> BoxContainedBarcodes; public List<string> DespawnedSpawners; public Dictionary<int, bool> ObjectEnabledSaves; public SavePoint() { LevelBarcode = null; PositionX = 0f; PositionY = 0f; PositionZ = 0f; InventoryData = null; MidLevelAmmoSave = default(AmmoSave); BoxContainedBarcodes = null; DespawnedSpawners = null; ObjectEnabledSaves = null; } public SavePoint(string levelBarcode, Vector3 position, InventoryData inventoryData, AmmoSave ammoSave, List<BarcodePosRot> boxContainedBarcodes, List<string> savedDespawns, Dictionary<int, bool> savedEnableds) { //IL_0009: 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_0021: Unknown result type (might be due to invalid IL or missing references) LevelBarcode = levelBarcode; PositionX = position.x; PositionY = position.y; PositionZ = position.z; InventoryData = inventoryData; MidLevelAmmoSave = ammoSave; BoxContainedBarcodes = boxContainedBarcodes; DespawnedSpawners = savedDespawns; ObjectEnabledSaves = savedEnableds; } public bool IsValid(out bool hasSpawnPoint) { //IL_0002: 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) if (GetPosition() == Vector3.zero) { hasSpawnPoint = false; } else { hasSpawnPoint = true; } if (LevelBarcode == null || LevelBarcode == string.Empty) { return false; } return true; } public void LoadContinue(Campaign campaign) { //IL_0008: Unknown result type (might be due to invalid IL or missing references) //IL_0012: Expected O, but got Unknown LoadContinue(new Barcode(campaign.LoadScene)); } public void LoadContinue(Barcode loadScene) { //IL_001e: Unknown result type (might be due to invalid IL or missing references) //IL_0029: Expected O, but got Unknown if (IsValid(out var _)) { SavepointFunctions.WasLastLoadByContinue = true; FadeLoader.Load(new Barcode(LevelBarcode), loadScene); } } public bool GetEnabledStateFromID(int id, bool defaultEnabled) { if (ObjectEnabledSaves.Keys.Contains(id)) { return ObjectEnabledSaves[id]; } return defaultEnabled; } public Vector3 GetPosition() { //IL_0013: Unknown result type (might be due to invalid IL or missing references) //IL_0018: Unknown result type (might be due to invalid IL or missing references) //IL_001b: Unknown result type (might be due to invalid IL or missing references) return new Vector3(PositionX, PositionY, PositionZ); } } public struct BarcodePosRot { public string barcode; public float x; public float y; public float z; public float qX; public float qY; public float qZ; public float qW; public float sX; public float sY; public float sZ; public BarcodePosRot(Barcode barcode, Vector3 position, Quaternion rotation, Vector3 scale) { //IL_000e: 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_0026: Unknown result type (might be due to invalid IL or missing references) //IL_0032: Unknown result type (might be due to invalid IL or missing references) //IL_003e: Unknown result type (might be due to invalid IL or missing references) //IL_004a: Unknown result type (might be due to invalid IL or missing references) //IL_0056: 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_006f: Unknown result type (might be due to invalid IL or missing references) //IL_007c: Unknown result type (might be due to invalid IL or missing references) this.barcode = barcode.ID; x = position.x; y = position.y; z = position.z; qX = rotation.x; qY = rotation.y; qZ = rotation.z; qW = rotation.w; sX = scale.x; sY = scale.y; sZ = scale.z; } public Vector3 GetPosition() { //IL_0013: Unknown result type (might be due to invalid IL or missing references) //IL_0018: Unknown result type (might be due to invalid IL or missing references) //IL_001b: Unknown result type (might be due to invalid IL or missing references) return new Vector3(x, y, z); } public Quaternion GetRotation() { //IL_0019: Unknown result type (might be due to invalid IL or missing references) //IL_001e: Unknown result type (might be due to invalid IL or missing references) //IL_0021: Unknown result type (might be due to invalid IL or missing references) return new Quaternion(qX, qY, qZ, qW); } public Vector3 GetScale() { //IL_0013: Unknown result type (might be due to invalid IL or missing references) //IL_0018: Unknown result type (might be due to invalid IL or missing references) //IL_001b: Unknown result type (might be due to invalid IL or missing references) return new Vector3(sX, sY, sZ); } } public Campaign campaign; internal List<FloatData> LoadedFloatDatas = new List<FloatData>(); internal bool DevToolsUnlocked = false; internal bool AvatarUnlocked = false; internal bool SkipIntro = false; internal List<string> UnlockedAchievements = new List<string>(); internal List<string> UnlockedLevels = new List<string>(); internal List<AmmoSave> LoadedAmmoSaves = new List<AmmoSave>(); internal Dictionary<string, InventoryData> LoadedInventorySaves = new Dictionary<string, InventoryData>(); internal SavePoint LoadedSavePoint; public List<LevelTime> LevelTimes = new List<LevelTime>(); public List<TrialTime> TrialTimes = new List<TrialTime>(); public string SaveFolder => Path.Combine(Application.persistentDataPath, "Saves"); public string SavePath => SaveFolder + "/slot_Campaign_" + campaign.Name + ".save.json"; public string BackupSavePath => SaveFolder + "/slot_Campaign." + campaign.Name + ".save_backup.json"; public string LegacySaveFolder => MelonEnvironment.UserDataDirectory + "/Campaigns/" + campaign.Name; public string LegacySavePath => LegacySaveFolder + "/save.json"; public CampaignSaveData(Campaign c) { campaign = c; LoadFromDisk(); } public void ResetSave() { //IL_0084: Unknown result type (might be due to invalid IL or missing references) //IL_008e: Expected O, but got Unknown SaveToDisk(BackupSavePath); ClearAmmoSave(); ClearSavePoint(); LoadedInventorySaves = new Dictionary<string, InventoryData>(); LoadedFloatDatas = new List<FloatData>(); DevToolsUnlocked = false; AvatarUnlocked = false; SkipIntro = false; UnlockedAchievements = new List<string>(); UnlockedLevels = new List<string>(); foreach (string campaignUnlockCrate in campaign.CampaignUnlockCrates) { DataManager.ActiveSave.Unlocks.ClearUnlockForBarcode(new Barcode(campaignUnlockCrate)); } DataManager.TrySaveActiveSave((SaveFlags)0); SaveToDisk(); } public void SetValue(string key, float value) { GetFloatDataEntry(key).Value = value; SaveToDisk(); } public float GetValue(string key) { return GetFloatDataEntry(key).Value; } private FloatData GetFloatDataEntry(string key) { FloatData floatData = null; try { floatData = LoadedFloatDatas.First((FloatData f) => f.Key == key); } catch { floatData = new FloatData(key); LoadedFloatDatas.Add(floatData); } return floatData; } public void UnlockDevTools() { DevToolsUnlocked = true; SaveToDisk(); } public void UnlockAvatar() { AvatarUnlocked = true; SaveToDisk(); } public bool UnlockAchievement(string key) { //IL_0121: Unknown result type (might be due to invalid IL or missing references) //IL_0126: Unknown result type (might be due to invalid IL or missing references) //IL_0138: Unknown result type (might be due to invalid IL or missing references) //IL_013d: Unknown result type (might be due to invalid IL or missing references) //IL_0142: Unknown result type (might be due to invalid IL or missing references) //IL_014a: Unknown result type (might be due to invalid IL or missing references) //IL_014f: Unknown result type (might be due to invalid IL or missing references) //IL_0154: Unknown result type (might be due to invalid IL or missing references) //IL_0156: Unknown result type (might be due to invalid IL or missing references) //IL_015b: Unknown result type (might be due to invalid IL or missing references) //IL_0166: Unknown result type (might be due to invalid IL or missing references) //IL_0172: Expected O, but got Unknown //IL_00be: Unknown result type (might be due to invalid IL or missing references) //IL_00c3: Unknown result type (might be due to invalid IL or missing references) //IL_00d0: Unknown result type (might be due to invalid IL or missing references) //IL_00e2: Unknown result type (might be due to invalid IL or missing references) //IL_00e7: Unknown result type (might be due to invalid IL or missing references) //IL_00ec: Unknown result type (might be due to invalid IL or missing references) //IL_00f4: Unknown result type (might be due to invalid IL or missing references) //IL_00f9: Unknown result type (might be due to invalid IL or missing references) //IL_00fe: 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_0110: Unknown result type (might be due to invalid IL or missing references) //IL_011c: Expected O, but got Unknown if (UnlockedAchievements == null) { UnlockedAchievements = new List<string>(); } if (UnlockedAchievements.Contains(key)) { return false; } foreach (AchievementData achievement in campaign.Achievements) { if (achievement.Key != key) { continue; } if ((Object)(object)campaign.AchievementUnlockSound != (Object)null) { Audio3dManager.Play2dOneShot(campaign.AchievementUnlockSound, Audio3dManager.ui, new Nullable<float>(1f), new Nullable<float>(1f)); } if ((Object)(object)achievement.cachedTexture != (Object)null) { Notifier.Send(new Notification { CustomIcon = achievement.cachedTexture, Title = NotificationText.op_Implicit("Achievement Get: " + achievement.Name), Message = NotificationText.op_Implicit(achievement.Description), Type = (NotificationType)4, PopupLength = 5f, ShowTitleOnPopup = true }); } else { Notifier.Send(new Notification { Title = NotificationText.op_Implicit("Achievement Get: " + achievement.Name), Message = NotificationText.op_Implicit(achievement.Description), Type = (NotificationType)0, PopupLength = 5f, ShowTitleOnPopup = true }); } UnlockedAchievements.Add(key); SaveToDisk(); CampaignBoneMenu.RefreshCampaignPage(campaign); return true; } return false; } public void LockAchievement(string key) { if (UnlockedAchievements.Contains(key)) { UnlockedAchievements.Remove(key); } } public void UnlockLevel(string barcode) { if (!UnlockedLevels.Contains(barcode)) { UnlockedLevels.Add(barcode); } } internal void SaveToDisk(string overwritePath = "") { //IL_0026: 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_0033: Unknown result type (might be due to invalid IL or missing references) //IL_003c: Expected O, but got Unknown if (!Directory.Exists(SaveFolder)) { Directory.CreateDirectory(SaveFolder); } SaveData saveData = new SaveData(this); JsonSerializerSettings val = new JsonSerializerSettings { ReferenceLoopHandling = (ReferenceLoopHandling)2, PreserveReferencesHandling = (PreserveReferencesHandling)1 }; string contents = JsonConvert.SerializeObject((object)saveData, val); File.WriteAllText((overwritePath != string.Empty) ? overwritePath : SavePath, contents); } internal void LoadFromDisk() { //IL_009b: Unknown result type (might be due to invalid IL or missing references) //IL_00a0: Unknown result type (might be due to invalid IL or missing references) //IL_00a8: Unknown result type (might be due to invalid IL or missing references) //IL_00b1: Expected O, but got Unknown if (!Directory.Exists(SaveFolder)) { Directory.CreateDirectory(SaveFolder); } string path = SavePath; if (!File.Exists(SavePath)) { if (!File.Exists(LegacySavePath)) { ClearAmmoSave(); LoadedSavePoint = new SavePoint(); LoadedFloatDatas = new List<FloatData>(); DevToolsUnlocked = false; AvatarUnlocked = false; SaveToDisk(); return; } path = LegacySavePath; } string text = File.ReadAllText(path); JsonSerializerSettings val = new JsonSerializerSettings { ReferenceLoopHandling = (ReferenceLoopHandling)2, PreserveReferencesHandling = (PreserveReferencesHandling)1 }; SaveData saveData = JsonConvert.DeserializeObject<SaveData>(text, val); saveData.LoadSaveData(this); } public void SaveAmmoForLevel(string levelBarcode) { if (!campaign.SaveLevelAmmo || string.IsNullOrEmpty(levelBarcode)) { return; } AmmoSave previousLevelsAmmoSave = GetPreviousLevelsAmmoSave(levelBarcode); if (!DoesSavedAmmoExist(levelBarcode)) { LoadedAmmoSaves.Add(new AmmoSave { LevelBarcode = levelBarcode, LightAmmo = AmmoInventory.Instance.GetCartridgeCount("light") - previousLevelsAmmoSave.LightAmmo, MediumAmmo = AmmoInventory.Instance.GetCartridgeCount("medium") - previousLevelsAmmoSave.MediumAmmo, HeavyAmmo = AmmoInventory.Instance.GetCartridgeCount("heavy") - previousLevelsAmmoSave.HeavyAmmo }); } else { AmmoSave savedAmmo = GetSavedAmmo(levelBarcode); for (int i = 0; i < LoadedAmmoSaves.Count; i++) { if (LoadedAmmoSaves[i].LevelBarcode == levelBarcode) { LoadedAmmoSaves[i] = new AmmoSave { LevelBarcode = levelBarcode, LightAmmo = Mathf.Max(AmmoInventory.Instance.GetCartridgeCount("light") - previousLevelsAmmoSave.LightAmmo, savedAmmo.LightAmmo), MediumAmmo = Mathf.Max(AmmoInventory.Instance.GetCartridgeCount("medium") - previousLevelsAmmoSave.MediumAmmo, savedAmmo.MediumAmmo), HeavyAmmo = Mathf.Max(AmmoInventory.Instance.GetCartridgeCount("heavy") - previousLevelsAmmoSave.HeavyAmmo, savedAmmo.HeavyAmmo) }; } } } campaign.saveData.SaveToDisk(); } public AmmoSave GetPreviousLevelsAmmoSave(string levelBarcode) { int levelIndex = campaign.GetLevelIndex(levelBarcode); AmmoSave result = default(AmmoSave); for (int i = 0; i < levelIndex; i++) { result.LightAmmo += GetSavedAmmo(campaign.mainLevels[i]).LightAmmo; result.MediumAmmo += GetSavedAmmo(campaign.mainLevels[i]).MediumAmmo; result.HeavyAmmo += GetSavedAmmo(campaign.mainLevels[i]).HeavyAmmo; } return result; } public AmmoSave GetSavedAmmo(CampaignLevel level) { return GetSavedAmmo(level.sBarcode); } public AmmoSave GetSavedAmmo(string levelBarcode) { return LoadedAmmoSaves.FirstOrDefault((AmmoSave x) => x.LevelBarcode == levelBarcode); } public bool DoesSavedAmmoExist(string levelBarcode) { if (LoadedAmmoSaves == null) { return false; } if (LoadedAmmoSaves.Count == 0) { return false; } if (LoadedAmmoSaves.Any((AmmoSave x) => x.LevelBarcode == levelBarcode)) { return true; } return false; } public void ClearAmmoSave() { LoadedAmmoSaves.Clear(); CampaignLevel[] mainLevels = campaign.mainLevels; foreach (CampaignLevel campaignLevel in mainLevels) { LoadedAmmoSaves.Add(new AmmoSave { LevelBarcode = campaignLevel.sBarcode, LightAmmo = 0, MediumAmmo = 0, HeavyAmmo = 0 }); } } public void SaveInventoryForLevel(string nextLevelBarcode) { if (campaign.SaveLevelInventory) { InventoryData fromRigmanager = InventoryData.GetFromRigmanager(Player.RigManager, campaign.InventorySaveLimit); LoadedInventorySaves[nextLevelBarcode] = fromRigmanager; } } public void ClearSavePoint() { LoadedSavePoint = new SavePoint(); CampaignBoneMenu.RefreshCampaignPage(campaign); SaveToDisk(); } public void SavePlayer(string levelBarcode, Vector3 position, List<BarcodePosRot> boxBarcodes = null) { //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_0166: Unknown result type (might be due to invalid IL or missing references) InventoryData fromRigmanager = InventoryData.GetFromRigmanager(Player.RigManager); if (boxBarcodes == null) { boxBarcodes = new List<BarcodePosRot>(); } AmmoSave ammoSave = default(AmmoSave); if (campaign.SaveLevelAmmo && position != Vector3.zero) { AmmoSave previousLevelsAmmoSave = GetPreviousLevelsAmmoSave(levelBarcode); AmmoSave ammoSave2 = default(AmmoSave); ammoSave2.LevelBarcode = levelBarcode; ammoSave2.LightAmmo = AmmoInventory.Instance.GetCartridgeCount("light") - previousLevelsAmmoSave.LightAmmo; ammoSave2.MediumAmmo = AmmoInventory.Instance.GetCartridgeCount("medium") - previousLevelsAmmoSave.MediumAmmo; ammoSave2.HeavyAmmo = AmmoInventory.Instance.GetCartridgeCount("heavy") - previousLevelsAmmoSave.HeavyAmmo; ammoSave = ammoSave2; } List<string> list = new List<string>(); foreach (SpawnerDespawnSaver item in Object.FindObjectsOfType<SpawnerDespawnSaver>()) { if (item.DontSpawnAgain(out var id)) { list.Add(id); } } Dictionary<int, bool> dictionary = new Dictionary<int, bool>(); foreach (ObjectEnabledSaver item2 in Object.FindObjectsOfType<ObjectEnabledSaver>()) { dictionary.Add(item2.uniqueID.Get(), ((Component)item2).gameObject.activeSelf); } LoadedSavePoint = new SavePoint(levelBarcode, position, fromRigmanager, ammoSave, boxBarcodes, list, dictionary); SaveToDisk(); CampaignBoneMenu.RefreshCampaignPage(campaign); } public int GetLevelTime(string levelBarcode) { return LevelTimes.Find((LevelTime lt) => lt.LevelBarcode == levelBarcode)?.TimeInSeconds ?? 0; } public int GetTotalCampaignTime() { int num = 0; foreach (LevelTime levelTime in LevelTimes) { num += levelTime.TimeInSeconds; } return num; } public void AddTimeToLevel(string levelBarcode, int seconds) { if (!string.IsNullOrEmpty(levelBarcode)) { LevelTime levelTime = LevelTimes.Find((LevelTime lt) => lt.LevelBarcode == levelBarcode); if (levelTime == null) { levelTime = new LevelTime { LevelBarcode = levelBarcode, TimeInSeconds = 0 }; LevelTimes.Add(levelTime); } levelTime.TimeInSeconds += seconds; SaveToDisk(); } } public bool AddTrialTime(string trialKey, float time) { TrialTime trialTime = GetTrialTimeData(trialKey); if (trialTime == null) { trialTime = new TrialTime { TrialKey = trialKey }; TrialTimes.Add(trialTime); } bool result = trialTime.AddTime(time); SaveToDisk(); return result; } public float GetTrialBest(string trialKey) { TrialTime trialTimeData = GetTrialTimeData(trialKey); if (trialTimeData == null) { return 0f; } return Mathf.Max(trialTimeData.BestTime, 0f); } public float GetTrialAverage(string trialKey) { TrialTime trialTimeData = GetTrialTimeData(trialKey); if (trialTimeData == null) { return 0f; } return Mathf.Max(trialTimeData.AverageTime, 0f); } public float GetTrialLatest(string trialKey) { TrialTime trialTimeData = GetTrialTimeData(trialKey); return trialTimeData?.PreviousTimes[trialTimeData.PreviousTimes.Count - 1] ?? 0f; } internal TrialTime GetTrialTimeData(string trialKey) { return TrialTimes.Find((TrialTime t) => t.TrialKey == trialKey); } } public class TrialTime { public string TrialKey; public List<float> PreviousTimes = new List<float>(); [JsonIgnore] public float BestTime { get; private set; } [JsonIgnore] public float AverageTime { get; private set; } [OnDeserialized] public void OnDeserialize(StreamingContext context) { if (PreviousTimes == null || PreviousTimes.Count == 0) { BestTime = -1f; AverageTime = 0f; return; } float num = PreviousTimes[0]; float num2 = 0f; foreach (float previousTime in PreviousTimes) { if (previousTime < num) { num = previousTime; } num2 += previousTime; } BestTime = num; AverageTime = num2 / (float)PreviousTimes.Count; } public void UpdateAverageTime() { if (PreviousTimes == null || PreviousTimes.Count == 0) { AverageTime = 0f; return; } float num = 0f; foreach (float previousTime in PreviousTimes) { num += previousTime; } AverageTime = num / (float)PreviousTimes.Count; } public bool AddTime(float time) { PreviousTimes.Add(time); if (time < BestTime || BestTime < 0f) { BestTime = time; return true; } UpdateAverageTime(); return false; } } public class LevelTime { public string LevelBarcode; public int TimeInSeconds; } public class InventoryData { public List<InventoryItem> InventoryItems = new List<InventoryItem>(); public void ApplyToRigmanager(RigManager rm) { for (int i = 0; i < InventoryItems.Count; i++) { InventoryItem item = InventoryItems[i]; try { InventorySlotReceiver inventorySlotReceiver = ((IEnumerable<SlotContainer>)rm.inventory.bodySlots).Where((SlotContainer s) => ((Object)((Component)s).gameObject).name == item.SlotName).First().inventorySlotReceiver; if ((Object)(object)inventorySlotReceiver != (Object)null) { item.SpawnInSlot(inventorySlotReceiver); } } catch { } } } public static InventoryData GetFromRigmanager(RigManager rm) { return GetFromRigmanager(rm, new List<string>()); } public static InventoryData GetFromRigmanager(RigManager rm, List<string> itemFilter) { InventoryData inventoryData = new InventoryData(); foreach (SlotContainer item in (Il2CppArrayBase<SlotContainer>)(object)rm.inventory.bodySlots) { if (!((Object)(object)item.inventorySlotReceiver == (Object)null)) { InventoryItem fromBodyslot = InventoryItem.GetFromBodyslot(item); if (!(fromBodyslot.Barcode == string.Empty) && (itemFilter.Count == 0 || itemFilter.Contains(fromBodyslot.Barcode))) { inventoryData.InventoryItems.Add(fromBodyslot); } } } return inventoryData; } } public struct InventoryItem { public string SlotName { get; set; } public string Barcode { get; set; } public InventoryItem(string SlotName, string Barcode) { this.SlotName = SlotName; this.Barcode = Barcode; } public InventoryItem() { SlotName = string.Empty; Barcode = string.Empty; } public void SpawnInSlot(InventorySlotReceiver slot) { //IL_0031: Unknown result type (might be due to invalid IL or missing references) //IL_003b: Expected O, but got Unknown if (Barcode != null && Barcode != string.Empty && (Object)(object)slot != (Object)null) { UniTask<bool> val = slot.SpawnInSlotAsync(new Barcode(Barcode)); } } public static InventoryItem GetFromBodyslot(SlotContainer slot) { if (slot.inventorySlotReceiver._weaponHost == null) { return new InventoryItem(); } Poolee poolee = ((MarrowBehaviour)slot.inventorySlotReceiver._slottedWeapon.interactableHost).marrowEntity._poolee; if ((Object)(object)poolee == (Object)null) { return new InventoryItem(); } if ((Object)(object)poolee.SpawnableCrate == (Object)null) { return new InventoryItem(); } return new InventoryItem(((Object)((Component)slot).gameObject).name, ((Scannable)poolee.SpawnableCrate).Barcode.ID); } } public struct GunInfo { public bool MagInserted; public bool MagAmmoCount; public bool RoundChambered; } [RegisterTypeInIl2Cpp] public class CrateDespawnerHook : MonoBehaviour { public Action<GameObject> OnDespawnDelegate { get; set; } public CrateDespawnerHook(IntPtr ptr) : base(ptr) { } private void OnDisable() { MarrowEntity componentInChildren = ((Component)this).gameObject.GetComponentInChildren<MarrowEntity>(); if (Object.op_Implicit((Object)(object)componentInChildren) && componentInChildren.IsDespawned) { OnDespawnDelegate(((Component)this).gameObject); Object.Destroy((Object)(object)this); } } } public static class PlayerMenuMangler { private static PreferencesPanelView panelView; public static GameObject optionsPanel; private static Transform _optionsGrid; private static GameObject _optionButton; private static Button _optionButtonComponent; public static Transform OptionsGrid { get { if (_optionsGrid == null || ((Il2CppObjectBase)_optionsGrid).WasCollected) { return null; } return _optionsGrid; } } public static void Initialize() { if (Campaign.SessionActive) { panelView = Player.UIRig.popUpMenu.preferencesPanelView; optionsPanel = ((Il2CppArrayBase<GameObject>)(object)panelView.pages)[panelView.defaultPage]; _optionsGrid = optionsPanel.transform.Find("grid_Options"); _optionButton = Object.Instantiate<GameObject>(((Component)_optionsGrid.GetChild(4)).gameObject, _optionsGrid); _optionButton.SetActive(true); TMP_Text componentInChildren = _optionButton.GetComponentInChildren<TMP_Text>(true); componentInChildren.text = "Exit Campaign"; _optionButton.transform.SetSiblingIndex(_optionsGrid.childCount - 1); _optionButtonComponent = _optionButton.GetComponent<Button>(); ((UnityEventBase)_optionButtonComponent.onClick).m_PersistentCalls.Clear(); ((UnityEventBase)_optionButtonComponent.onClick).m_Calls.ClearPersistent(); ((UnityEventBase)_optionButtonComponent.onClick).m_Calls.Clear(); ((UnityEvent)_optionButtonComponent.onClick).AddListener(UnityAction.op_Implicit((Action)Campaign.Session.Exit)); Transform val = _optionsGrid.Find("button_MainMenu"); Button componentInChildren2 = ((Component)val.Find("panel_MAINMENU")).GetComponentInChildren<Button>(true); ((UnityEventBase)componentInChildren2.onClick).m_PersistentCalls.Clear(); ((UnityEventBase)componentInChildren2.onClick).m_Calls.ClearPersistent(); ((UnityEventBase)componentInChildren2.onClick).m_Calls.Clear(); ((UnityEvent)componentInChildren2.onClick).AddListener(UnityAction.op_Implicit((Action)delegate { //IL_0019: Unknown result type (might be due to invalid IL or missing references) //IL_0023: Expected O, but got Unknown FadeLoader.Load(Campaign.Session.MenuLevel, new Barcode(Campaign.Session.LoadScene)); })); } } } public class FadeLoader { [CompilerGenerated] private sealed class <FadeCoroutine>d__2 : IEnumerator<object>, IDisposable, IEnumerator { private int <>1__state; private object <>2__current; public Barcode level; public Barcode loadScene; object IEnumerator<object>.Current { [DebuggerHidden] get { return <>2__current; } } object IEnumerator.Current { [DebuggerHidden] get { return <>2__current; } } [DebuggerHidden] public <FadeCoroutine>d__2(int <>1__state) { this.<>1__state = <>1__state; } [DebuggerHidden] void IDisposable.Dispose() { <>1__state = -2; } private bool MoveNext() { //IL_0025: 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_0032: Unknown result type (might be due to invalid IL or missing references) //IL_0035: 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_004b: Unknown result type (might be due to invalid IL or missing references) //IL_0055: Expected O, but got Unknown //IL_0073: Unknown result type (might be due to invalid IL or missing references) //IL_007d: Expected O, but got Unknown switch (<>1__state) { default: return false; case 0: <>1__state = -1; HelperMethods.SpawnCrate(LoadFadeBarcode, Vector3.zero, default(Quaternion), default(Vector3), false, (Action<GameObject>)null, (Action<GameObject>)null); <>2__current = (object)new WaitForSeconds(2f); <>1__state = 1; return true; case 1: <>1__state = -1; if (loadScene == null) { loadScene = new Barcode("fa534c5a83ee4ec6bd641fec424c4142.Level.DefaultLoad"); } SceneStreamer.Load(level, loadScene); return false; } } bool IEnumerator.MoveNext() { //ILSpy generated this explicit interface implementation from .override directive in MoveNext return this.MoveNext(); } [DebuggerHidden] void IEnumerator.Reset() { throw new NotSupportedException(); } } public static readonly string LoadFadeBarcode = "c1534c5a-dac0-44a1-b656-6c235646584c"; public static void Load(Barcode level, Barcode loadScene) { MelonCoroutines.Start(FadeCoroutine(level, loadScene)); } [IteratorStateMachine(typeof(<FadeCoroutine>d__2))] public static IEnumerator FadeCoroutine(Barcode level, Barcode loadScene) { //yield-return decompiler failed: Unexpected instruction in Iterator.Dispose() return new <FadeCoroutine>d__2(0) { level = level, loadScene = loadScene }; } } public static class GashaponHider { public static HashSet<Crate> HiddenCrates = new HashSet<Crate>(); public static void AddCratesToHide(List<string> crateBarcodes) { //IL_001a: Unknown result type (might be due to invalid IL or missing references) //IL_0026: Expected O, but got Unknown Crate item = default(Crate); foreach (string crateBarcode in crateBarcodes) { if (AssetWarehouse.Instance.TryGetCrate(new Barcode(crateBarcode), ref item)) { HiddenCrates.Add(item); } } } } [HarmonyPatch(typeof(Control_Gashapon))] public static class GashaponPatches { [HarmonyPatch("Start")] [HarmonyPrefix] public static void StartPrefix(Control_Gashapon __instance) { foreach (Crate hiddenCrate in GashaponHider.HiddenCrates) { __instance.blackList.Add(hiddenCrate); __instance.blackListStrings.Add(((Scannable)hiddenCrate).Barcode); } } } public class MainMenuMangler { public static Sprite CampaignSprite; public static void OnLevelLoaded(LevelInfo info) { //IL_0001: Unknown result type (might be due to invalid IL or missing references) if (info.barcode == "fa534c5a868247138f50c62e424c4144.Level.VoidG114") { MangleMainMenu(); } } public static void MangleMainMenu() { //IL_005f: 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) GameObject gameObject = ((Component)GameObject.Find("CANVAS_UX").transform.Find("MENU").GetChild(8)).gameObject; GameObject CampaignGrid = Object.Instantiate<GameObject>(gameObject, gameObject.transform.parent); ((Object)CampaignGrid).name = "group_CAMPAIGNS"; CampaignGrid.transform.localPosition = Vector3.zero; CampaignGrid.transform.localRotation = gameObject.transform.localRotation; ((Component)CampaignGrid.transform.GetChild(0).GetChild(1)).GetComponent<TMP_Text>().text = "CAMPAIGNS"; BonelabLevelsPanelView componentInChildren = CampaignGrid.GetComponentInChildren<BonelabLevelsPanelView>(true); CampaignPanelView cPanel = ((Component)componentInChildren).gameObject.AddComponent<CampaignPanelView>(); cPanel.Buttons = Il2CppArrayBase<GameObject>.op_Implicit((Il2CppArrayBase<GameObject>)(object)componentInChildren.items); cPanel.nextButton = componentInChildren.forwardButton; cPanel.backButton = componentInChildren.backButton; cPanel.pageText = (TMP_Text)(object)componentInChildren.pageText; cPanel.SetupButtons(); Object.Destroy((Object)(object)componentInChildren); GameObject MainGrid = ((Component)GameObject.Find("CANVAS_UX").transform.Find("MENU").GetChild(3)).gameObject; GameObject gameObject2 = ((Component)MainGrid.transform.GetChild(4)).gameObject; GameObject val = Object.Instantiate<GameObject>(gameObject2, gameObject2.transform.parent); val.GetComponentInChildren<TMP_Text>(true).text = "CAMPAIGNS"; ButtonClickedEvent onClick = val.GetComponentInChildren<Button>(true).onClick; ((UnityEventBase)onClick).m_PersistentCalls.Clear(); ((UnityEventBase)onClick).m_Calls.ClearPersistent(); ((UnityEventBase)onClick).m_Calls.Clear(); ((UnityEvent)onClick).AddListener(UnityAction.op_Implicit((Action)delegate { MainGrid.SetActive(false); CampaignGrid.SetActive(true); cPanel.Activate(); })); Image component = ((Component)((Selectable)val.GetComponentInChildren<Button>(true)).targetGraphic).GetComponent<Image>(); if ((Object)(object)CampaignSprite != (Object)null && (Object)(object)component != (Object)null) { component.sprite = CampaignSprite; } CampaignGrid.SetActive(false); } public static void LoadSpriteFromEmbeddedResource(string resourceName, Assembly assembly, Vector2 pivot, float pixelsPerUnit = 100f) { //IL_0080: Unknown result type (might be due to invalid IL or missing references) //IL_0086: Expected O, but got Unknown //IL_00cb: Unknown result type (might be due to invalid IL or missing references) //IL_00d0: Unknown result type (might be due to invalid IL or missing references) byte[] array = Array.Empty<byte>(); string[] manifestResourceNames = assembly.GetManifestResourceNames(); foreach (string text in manifestResourceNames) { if (!text.Contains(resourceName)) { continue; } using Stream stream = assembly.GetManifestResourceStream(text); if (stream == null) { return; } byte[] array2 = new byte[stream.Length]; stream.Read(array2, 0, array2.Length); array = array2; } Texture2D val = new Texture2D(2, 2); if (!ImageConversion.LoadImage(val, Il2CppStructArray<byte>.op_Implicit(array))) { MelonLogger.Error("Failed to load texture from embedded resource."); return; } ((Object)val).hideFlags = (HideFlags)32; CampaignSprite = Sprite.Create(val, new Rect(0f, 0f, (float)((Texture)val).width, (float)((Texture)val).height), pivot, pixelsPerUnit); ((Object)CampaignSprite).hideFlags = (HideFlags)32; } } [RegisterTypeInIl2Cpp] public class CampaignPanelView : MonoBehaviour { private int _currentPage; public GameObject[] Buttons; public GameObject backButton; public GameObject nextButton; public TMP_Text pageText; private bool _hasSelected = false; private int _lastPage => Mathf.FloorToInt((float)(CampaignUtilities.CampaignsToShowInMenu.Count / Buttons.Length)); public CampaignPanelView(IntPtr ptr) : base(ptr) { } public void SetupButtons() { for (int i = 0; i < Buttons.Length; i++) { Button component = Buttons[i].GetComponent<Button>(); ((UnityEventBase)component.onClick).m_PersistentCalls.Clear(); ((UnityEventBase)component.onClick).m_Calls.ClearPersistent(); ((UnityEventBase)component.onClick).m_Calls.Clear(); int selection = i; ((UnityEvent)component.onClick).AddListener(UnityAction.op_Implicit((Action)delegate { Select(selection); })); } } public void NextPage() { _currentPage = Mathf.Min(_lastPage, _currentPage + 1); UpdateVisualization(); } public void BackPage() { _currentPage = Mathf.Max(0, _currentPage - 1); UpdateVisualization(); } public void Select(int index) { if (!_hasSelected) { CampaignLogger.Msg(index); int index2 = Buttons.Length * _currentPage + index; Campaign campaign = CampaignUtilities.CampaignsToShowInMenu[index2]; _hasSelected = true; campaign.Enter(); } } public void Activate() { UpdateVisualization(); } private void UpdateVisualization() { if (_currentPage <= 0) { backButton.SetActive(false); } else { backButton.SetActive(true); } if (_currentPage >= _lastPage) { nextButton.SetActive(false); } else { nextButton.SetActive(true); } pageText.text = $"{_currentPage + 1}/{_lastPage + 1}"; for (int i = 0; i < Buttons.Length; i++) { GameObject val = Buttons[i]; int num = Buttons.Length * _currentPage + i; if (num < CampaignUtilities.CampaignsToShowInMenu.Count) { val.SetActive(true); val.GetComponentInChildren<TMP_Text>(true).text = CampaignUtilities.CampaignsToShowInMenu[num].Name; } else { val.SetActive(false); } } } } public class CampaignSelectionView : MonoBehaviour { public TMP_Text campaignTitle; public TMP_Text avatar; public Button menuButton; public Button continueButton; public Button backButton; public Campaign targetCampaign; public void SetupButtons() { ((UnityEventBase)menuButton.onClick).m_PersistentCalls.Clear(); ((UnityEventBase)menuButton.onClick).m_Calls.ClearPersistent(); ((UnityEventBase)menuButton.onClick).m_Calls.Clear(); ((UnityEvent)menuButton.onClick).AddListener(UnityAction.op_Implicit((Action)delegate { Enter(); })); ((UnityEventBase)continueButton.onClick).m_PersistentCalls.Clear(); ((UnityEventBase)continueButton.onClick).m_Calls.ClearPersistent(); ((UnityEventBase)continueButton.onClick).m_Calls.Clear(); ((UnityEvent)continueButton.onClick).AddListener(UnityAction.op_Implicit((Action)delegate { Continue(); })); } public void Activate(Campaign campaign) { targetCampaign = campaign; campaignTitle.text = campaign.Name; ((Component)continueButton).gameObject.SetActive(campaign.saveData.LoadedSavePoint.IsValid(out var _)); } public void Enter() { //IL_001c: Unknown result type (might be due to invalid IL or missing references) //IL_0026: Expected O, but got Unknown FadeLoader.Load(targetCampaign.MenuLevel.Barcode, new Barcode(targetCampaign.LoadScene)); } public void Continue() { targetCampaign.saveData.LoadedSavePoint.LoadContinue(targetCampaign); } } public class AchievementData { public Texture2D cachedTexture; public Sprite cachedSprite; public string Key { get; set; } public bool Hidden { get; set; } public byte[] IconBytes { get; set; } public string IconGUID { get; set; } public string Name { get; set; } public string Description { get; set; } public void Init() { LoadIcon(); } public void LoadIcon() { //IL_0017: Unknown result type (might be due to invalid IL or missing references) //IL_0021: Expected O, but got Unknown //IL_00e5: Unknown result type (might be due to invalid IL or missing references) //IL_00f4: Unknown result type (might be due to invalid IL or missing references) if (IconBytes.Length == 0) { return; } cachedTexture = new Texture2D(2, 2); if (IconBytes.Length != 0) { if (!ImageConversion.LoadImage(cachedTexture, Il2CppStructArray<byte>.op_Implicit(IconBytes), false)) { MelonLogger.Error("Failed to load texture from embedded resource."); return; } } else if (!(IconGUID != "")) { MelonLogger.Error("No valid icon data found for achievement: " + Key); return; } cachedTexture = cachedTexture.ProperResize(336, 336); ((Object)cachedTexture).hideFlags = (HideFlags)32; cachedSprite = Sprite.Create(cachedTexture, new Rect(0f, 0f, (float)((Texture)cachedTexture).width, (float)((Texture)cachedTexture).height), new Vector2(0.5f, 0.5f)); ((Object)cachedSprite).hideFlags = (HideFlags)32; } } internal class CampaignLoadingData { public int Version { get; set; } = 0; public string Name { get; set; } public SerializedLevelSetup IntroLevel { get; set; } public SerializedLevelSetup InitialLevel { get; set; } public List<SerializedLevelSetup> MainLevels { get; set; } public List<SerializedLevelSetup> ExtraLevels { get; set; } public string LoadScene { get; set; } public string LoadSceneMusic { get; set; } public bool UnlockableLevels { get; set; } public bool ShowInMenu { get; set; } public bool PrioritizeInLevelPanel { get; set; } public bool RestrictDevTools { get; set; } public AvatarRestrictionType AvatarRestrictionType { get; set; } public string CampaignAvatar { get; set; } public string BaseGameFallbackAvatar { get; set; } public List<string> WhitelistedAvatars { get; set; } public bool SaveLevelWeapons { get; set; } public List<string> InventorySaveLimit { get; set; } public bool SaveLevelAmmo { get; set; } public string AchievementUnlockSound { get; set; } public List<AchievementData> Achievements { get; set; } public bool LockInCampaign { get; set; } public List<string> CampaignUnlockCrates { get; set; } public List<string> HideCratesFromGachapon { get; set; } public bool DevBuild { get; set; } = false; } public class SerializedLevelSetup { public string levelBarcode; public string levelName; } [Flags] public enum AvatarRestrictionType { None = 0, DisableBodyLog = 1, RestrictAvatar = 2, EnforceWhitelist = 4 } internal class BuildInfo { internal const string Name = "Custom Campain Tools"; internal const string Description = "Allows Modders to add their own Campaign functionality to Marrow Campaigns."; internal const string Author = "EvroDev"; internal const string Company = "LabWorks"; internal const string Version = "1.1.0"; internal const string DownloadLink = ""; } internal class Main : MelonMod { public override void OnLateInitializeMelon() { //IL_008e: Unknown result type (might be due to invalid IL or missing references) BoneMenuCreator.CreateBoneMenu(); Campaign.OnInitialize(); Hooking.OnLevelLoaded += LevelInitialized; Hooking.OnLevelUnloaded += LevelUnloaded; Hooking.OnUIRigCreated += OnUIRigCreated; string resourceName = "CampaignIcon.png"; Assembly assembly = ((MelonBase)this).MelonAssembly.Assembly; MainMenuMangler.LoadSpriteFromEmbeddedResource(resourceName, assembly, new Vector2(0.5f, 0.5f)); foreach (MelonMod registeredMelon in MelonTypeBase<MelonMod>.RegisteredMelons) { if (HelperMethods.CheckIfAssemblyLoaded("BrowsingPlus")) { PatchSwipezBecauseLemonloaderKeepsFuckingFailingIfIPutThisMethodInOnLateInitializeMelonForSomeReason(); } } } private void PatchSwipezBecauseLemonloaderKeepsFuckingFailingIfIPutThisMethodInOnLateInitializeMelonForSomeReason() { SwipezPanelPatches.ManualPatch(); } internal static void LevelInitialized(LevelInfo info) { //IL_0001: Unknown result type (might be due to invalid IL or missing references) //IL_0008: Unknown result type (might be due to invalid IL or missing references) //IL_0055: Unknown result type (might be due to invalid IL or missing references) string barcode = info.barcode; MainMenuMangler.OnLevelLoaded(info); if (!CampaignUtilities.IsCampaignLevel(barcode, out var campaign, out var levelType)) { return; } LevelTiming.OnCampaignLevelLoaded(campaign, barcode); if (levelType != CampaignLevelType.MainLevel) { return; } if (SavepointFunctions.CurrentLevelLoadedByContinue) { SavepointFunctions.LoadPlayerFromSave(); return; } campaign.saveData.SavePlayer(barcode, Vector3.zero); if (campaign.SaveLevelInventory && campaign.saveData.LoadedInventorySaves.ContainsKey(barcode)) { MelonCoroutines.Start(SavepointFunctions.ApplyInventoryDataAfterTime(campaign.saveData.LoadedInventorySaves[barcode])); } } private static void LevelUnloaded() { if (Campaign.SessionActive) { Campaign.Session.saveData.SaveAmmoForLevel(Campaign.lastLoadedCampaignLevel); LevelTiming.OnCampaignLevelUnloaded(Campaign.Session, Campaign.lastLoadedCampaignLevel); } } private static void OnUIRigCreated() { PlayerMenuMangler.Initialize(); Campaign.OnUIRigCreated(); } } public static class SavepointFunctions { [CompilerGenerated] private sealed class <ApplyInventoryDataAfterTime>d__3 : IEnumerator<object>, IDisposable, IEnumerator { private int <>1__state; private object <>2__current; public InventoryData invData; object IEnumerator<object>.Current { [DebuggerHidden] get { return <>2__current; } } object IEnumerator.Current { [DebuggerHidden] get { return <>2__current; } } [DebuggerHidden] public <ApplyInventoryDataAfterTime>d__3(int <>1__state) { this.<>1__state = <>1__state; } [DebuggerHidden] void IDisposable.Dispose() { <>1__state = -2; } private bool MoveNext() { //IL_0026: Unknown result type (might be due to invalid IL or missing references) //IL_0030: Expected O, but got Unknown switch (<>1__state) { default: return false; case 0: <>1__state = -1; <>2__current = (object)new WaitForSeconds(2f); <>1__state = 1; return true; case 1: <>1__state = -1; invData.ApplyToRigmanager(Player.RigManager); return false; } } bool IEnumerator.MoveNext() { //ILSpy generated this explicit interface implementation from .override directive in MoveNext return this.MoveNext(); } [DebuggerHidden] void IEnumerator.Reset() { throw new NotSupportedException(); } } public static bool WasLastLoadByContinue; public static bool CurrentLevelLoadedByContinue; public static void LoadPlayerFromSave() { //IL_0049: Unknown result type (might be due to invalid IL or missing references) //IL_008e: 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_009f: Unknown result type (might be due to invalid IL or missing references) WasLastLoadByContinue = false; Campaign fromLevel = CampaignUtilities.GetFromLevel(); CampaignSaveData.SavePoint loadedSavePoint = fromLevel.saveData.LoadedSavePoint; if (!fromLevel.saveData.LoadedSavePoint.IsValid(out var hasSpawnPoint)) { return; } if (hasSpawnPoint) { Player.RigManager.Teleport(loadedSavePoint.GetPosition(), true); foreach (CampaignSaveData.BarcodePosRot barcode in loadedSavePoint.BoxContainedBarcodes) { HelperMethods.SpawnCrate(barcode.barcode, barcode.GetPosition(), barcode.GetRotation(), Vector3.one, false, (Action<GameObject>)delegate { CampaignLogger.Msg($"Successfully Spawned {barcode} in Box"); }, (Action<GameObject>)null); } } MelonCoroutines.Start(ApplyInventoryDataAfterTime(loadedSavePoint.InventoryData)); } [IteratorStateMachine(typeof(<ApplyInventoryDataAfterTime>d__3))] public static IEnumerator ApplyInventoryDataAfterTime(InventoryData invData) { //yield-return decompiler failed: Unexpected instruction in Iterator.Dispose() return new <ApplyInventoryDataAfterTime>d__3(0) { invData = invData }; } } public static class Texture2DResizeExtension { public static Texture2D ProperResize(this Texture2D texture2D, int width, int height) { //IL_0005: Unknown result type (might be due to invalid IL or missing references) //IL_000b: Expected O, but got Unknown //IL_001c: Unknown result type (might be due to invalid IL or missing references) //IL_0022: Expected O, but got Unknown //IL_0031: Unknown result type (might be due to invalid IL or missing references) RenderTexture val2 = (RenderTexture.active = new RenderTexture(width, height, 24)); Graphics.Blit((Texture)(object)texture2D, val2); Texture2D val3 = new Texture2D(width, height); val3.ReadPixels(new Rect(0f, 0f, (float)width, (float)height), 0, 0); val3.Apply(); Object.Destroy((Object)(object)val2); return val3; } } } namespace CustomCampaignTools.Timing { public static class LevelTiming { private static Timer MainTimer = new Timer(); private static Dictionary<string, Timer> TrialTimers = new Dictionary<string, Timer>(); public static void OnCampaignLevelLoaded(Campaign c, string levelBarcode) { MainTimer.StartTimer(); } public static void OnCampaignLevelUnloaded(Campaign c, string levelBarcode) { int seconds = (int)MainTimer.GetTimeSinceStart(); c.saveData.AddTimeToLevel(levelBarcode, seconds); } public static int GetMainTime() { return (int)MainTimer.GetTimeSinceStart(); } public static float GetRunningTrialTime(string key) { Timer timer = TrialTimers[key]; return timer.GetTimeSinceStart(); } public static void StartTrialTimer(string key) { if (!TrialTimers.ContainsKey(key)) { TrialTimers[key] = new Timer(); Timer timer = TrialTimers[key]; timer.StartTimer(); } else { TrialTimers[key].ResetTimer(); } } public static void PauseTrialTimer(string key) { if (TrialTimers.ContainsKey(key)) { Timer timer = TrialTimers[key]; timer.PauseTimer(); } } public static void ResumeTrialTimer(string key) { if (TrialTimers.ContainsKey(key)) { Timer timer = TrialTimers[key]; timer.ResumeTimer(); } } public static float EndTrialTimer(string key, out bool isBest, bool save = true) { Timer timer = TrialTimers[key]; TrialTimers.Remove(key); float timeSinceStart = timer.GetTimeSinceStart(); isBest = false; if (save && Campaign.SessionActive) { isBest = SaveTrialTime(Campaign.Session, key, timeSinceStart); } return timeSinceStart; } public static bool SaveTrialTime(Campaign c, string key, float time) { return c.saveData.AddTrialTime(key, time); } public static void ONGAMEPAUSE() { MainTimer.PauseTimer(); foreach (Timer value in TrialTimers.Values) { value.PauseTimer(); } } public static void ONGAMERESUME() { MainTimer.ResumeTimer(); foreach (Timer value in TrialTimers.Values) { value.ResumeTimer(); } } } public class Timer { private float startTime; private bool running = false; private float accumulatedTime = 0f; private int pauseCount = 0; public void StartTimer() { startTime = Time.time; running = true; pauseCount = 0; } public void ResetTimer() { startTime = Time.time; } public void PauseTimer() { if (running) { running = false; accumulatedTime += Time.time - startTime; } pauseCount++; } public void ResumeTimer() { if (!running) { pauseCount--; if (pauseCount <= 0) { startTime = Time.time; running = true; } } } public float GetTimeSinceStart() { if (!running) { return accumulatedTime; } return accumulatedTime + (Time.time - startTime); } } } namespace CustomCampaignTools.LabWorks { [RegisterTypeInIl2Cpp] public class Control_MonoMat : MonoBehaviour { private CrateSpawner[] _loots; private List<Rigidbody> _lootBodies = new List<Rigidbody>(); private int _multiplier; private int _itemPrice; private int _lightBullets; private int _mediumBullets; private int _heavyBullets; private bool _opened; private bool _unlocked; private TMP_Text _bulletBalanceTextmesh; private TMP_Text _refundTextmesh; private AmmoReciever reciever; private string lightRefundSpawnable; private string mediumRefundSpawnable; private string heavyRefundSpawnable; private AudioClip _openedClip; private AudioClip _unlockedClip; private AudioClip _lockedClip; private Transform giveChangeTransform; private UltEventHolder OnAmountRose; private UltEventHolder OnAmountDropped; private UltEventHolder OnItemBought; private bool _hasFields = false; private int _trueItemPrice => _itemPrice; private int _totalBullets => _lightBullets + _mediumBullets + _heavyBullets; public Control_MonoMat(IntPtr ptr) : base(ptr) { } public void SetLootsFromParent(GameObject parent) { _loots = Il2CppArrayBase<CrateSpawner>.op_Implicit(parent.GetComponentsInChildren<CrateSpawner>()); } public void StartFields(GameObject lootParent, int itemPrice, int multiplier, TMP_Text _bulletBalanceTextmesh, TMP_Text _refundTextmesh, AmmoReciever reciever, string lightRefundSpawnable, string mediumRefundSpawnable, string heavyRefundSpawnable, AudioClip openedClip, AudioClip unlockedClip, AudioClip lockedClip, Transform giveChangeTransform, UltEventHolder AmountRoseEvent, UltEventHolder AmountDroppedEvent, UltEventHolder ItemBoughtEvent) { SetLootsFromParent(lootParent); foreach (Rigidbody componentsInChild in lootParent.GetComponentsInChildren<Rigidbody>()) { componentsInChild.isKinematic = true; _lootBodies.Add(componentsInChild); } _itemPrice = itemPrice; _multiplier = multiplier; this._bulletBalanceTextmesh = _bulletBalanceTextmesh; this._refundTextmesh = _refundTextmesh; this.reciever = reciever; this.lightRefundSpawnable = lightRefundSpawnable; this.mediumRefundSpawnable = mediumRefundSpawnable; this.heavyRefundSpawnable = heavyRefundSpawnable; _openedClip = openedClip; _unlockedClip = unlockedClip; _lockedClip = lockedClip; this.giveChangeTransform = giveChangeTransform; OnAmountRose = AmountRoseEvent; OnAmountDropped = AmountDroppedEvent; OnItemBought = ItemBoughtEvent; _hasFields = true; SafeStart(); } private void SafeStart() { AmmoReciever obj = reciever; obj.OnInserted += Action<Magazine>.op_Implicit((Action<Magazine>)delegate(Magazine g) { InsertMagazine(g); }); UpdateTMP(); } private void UpdateTMP() { _refundTextmesh.text = $"{_totalBullets}"; int num = Mathf.Max(0, _trueItemPrice - _totalBullets); _bulletBalanceTextmesh.text = (_opened ? "0" : $"{num}"); } public void OnLootSpawned(CrateSpawner spawner, GameObject entity) { foreach (Rigidbody componentsInChild in entity.GetComponentsInChildren<Rigidbody>()) { componentsInChild.isKinematic = true; _lootBodies.Add(componentsInChild); } } public void GiveChange() { //IL_001b: Unknown result type (might be due to invalid IL or missing references) //IL_0026: 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_005f: Unknown result type (might be due to invalid IL or missing references) //IL_006a: Unknown result type (might be due to invalid IL or missing references) //IL_006f: Unknown result type (might be due to invalid IL or missing references) //IL_00a3: Unknown result type (might be due to invalid IL or missing references) //IL_00ae: Unknown result type (might be due to invalid IL or missing references) //IL_00b3: Unknown result type (might be due to invalid IL or missing references) if (_lightBullets > 0) { HelperMethods.SpawnCrate(lightRefundSpawnable, giveChangeTransform.position, giveChangeTransform.rotation, Vector3.one, false, (Action<GameObject>)delegate(GameObject gobj) { gobj.GetComponent<AmmoPickupProxy>().ammoPickup.ammoCount = _lightBullets; }, (Action<GameObject>)null); } if (_mediumBullets > 0) { HelperMethods.SpawnCrate(mediumRefundSpawnable, giveChangeTransform.position, giveChangeTransform.rotation, Vector3.one, false, (Action<GameObject>)delegate(GameObject gobj) { gobj.GetComponent<AmmoPickupProxy>().ammoPickup.ammoCount = _mediumBullets; }, (Action<GameObject>)null); } if (_heavyBullets > 0) { HelperMethods.SpawnCrate(heavyRefundSpawnable, giveChangeTransform.position, giveChangeTransform.rotation, Vector3.one, false, (Action<GameObject>)delegate(GameObject gobj) { gobj.GetComponent<AmmoPickupProxy>().ammoPickup.ammoCount = _heavyBullets; }, (Action<GameObject>)null); } _lightBullets = 0; _mediumBullets = 0; _heavyBullets = 0; if (!_opened && (Object)(object)OnAmountDropped != (Object)null) { OnAmountDropped.Invoke(); } UpdateTMP(); } public void PurchaseItem() { if (_totalBullets < _trueItemPrice) { return; } int trueItemPrice = _trueItemPrice; trueItemPrice = CleanupLight(trueItemPrice); trueItemPrice = CleanupMedium(trueItemPrice); CleanupHeavy(trueItemPrice); foreach (Rigidbody lootBody in _lootBodies) { lootBody.isKinematic = false; } _opened = true; if ((Object)(object)OnItemBought != (Object)null) { OnItemBought.Invoke(); } UpdateTMP(); } private int CleanupLight(int ammoToRemove) { if (ammoToRemove > _lightBullets) { ammoToRemove -= _lightBullets; _lightBullets = 0; } else { _lightBullets -= ammoToRemove; ammoToRemove = 0; } return ammoToRemove; } private int CleanupMedium(int ammoToRemove) { if (ammoToRemove > _lightBullets) { ammoToRemove -= _mediumBullets; _mediumBullets = 0; } else { _mediumBullets -= ammoToRemove; ammoToRemove = 0; } return ammoToRemove; } private int CleanupHeavy(int ammoToRemove) { if (ammoToRemove > _heavyBullets) { ammoToRemove -= _heavyBullets; _heavyBullets = 0; } else { _heavyBullets -= ammoToRemove; ammoToRemove = 0; } return ammoToRemove; } public void InsertMagazine(Magazine magazine) { int ammoTypeFromMagazine = GetAmmoTypeFromMagazine(magazine); string groupByCartridge = AmmoInventory.Instance.GetGroupByCartridge(magazine.magazineState.cartridgeData); int num = magazine.magazineState.AmmoCount * _multiplier; int num2 = Mathf.Min(AmmoInventory.Instance.GetCartridgeCount(groupByCartridge), num); AddBullets(num2, ammoTypeFromMagazine); AmmoInventory.Instance.RemoveCartridge(magazine.magazineState.cartridgeData, num2); if (_totalBullets >= _trueItemPrice && !_unlocked && !_opened) { _unlocked = true; } } public int GetAmmoTypeFromMagazine(Magazine mag) { return AmmoInventory.Instance.GetGroupByCartridge(mag.magazineState.cartridgeData) switch { "light" => 0, "medium" => 1, "heavy" => 2, _ => -1, }; } public void AddBullets(int addedBullets, int type) { int totalBullets = _totalBullets; switch (type) { case 0: _lightBullets += addedBullets; break; case 1: _mediumBullets += addedBullets; break; case 2: _heavyBullets += addedBullets; break; } if (totalBullets < _trueItemPrice && _totalBullets >= _trueItemPrice && (Object)(object)OnAmountRose != (Object)null) { OnAmountRose.Invoke(); } UpdateTMP(); } public Rigidbody[] GetLoots() { return _lootBodies.ToArray(); } public void SetPrice(int price, int mult) { _itemPrice = price; _multiplier = mult; } public void SetLoots(Rigidbody[] loots) { } } } namespace CustomCampaignTools.Patching { [HarmonyPatch(typeof(SceneStreamer))] public static class LevelLoadingPatches { [HarmonyPatch("LoadAsync", new Type[] { typeof(LevelCrateReference), typeof(LevelCrateReference) })] [HarmonyPrefix] public static bool LoadPrefixPatch(LevelCrateReference level, ref LevelCrateReference loadLevel, ref UniTask __result) { //IL_0116: Unknown result type (might be due to invalid IL or missing references) //IL_0120: Expected O, but got Unknown //IL_011b: Unknown result type (might be due to invalid IL or missing references) //IL_0121: Expected O, but got Unknown Campaign fromLevel = CampaignUtilities.GetFromLevel(level); SavepointFunctions.CurrentLevelLoadedByContinue = SavepointFunctions.WasLastLoadByContinue; SavepointFunctions.WasLastLoadByContinue = false; if (Campaign.SessionActive && fromLevel == Campaign.Session && Campaign.Session.TypeOfLevel(((ScannableReference)level).Barcode.ID) == CampaignLevelType.MainLevel && Campaign.Session.TypeOfLevel(((Scannable)SceneStreamer.Session.Level).Barcode.ID) == CampaignLevelType.MainLevel && Campaign.Session.GetLevelIndex(((ScannableReference)level).Barcode.ID) == Campaign.Session.GetLevelIndex(((Scannable)SceneStreamer.Session.Level).Barcode.ID) + 1) { Campaign.Session.saveData.SaveInventoryForLevel(((ScannableReference)level).Barcode.ID); } if (fromLevel != null) { fromLevel.saveData.UnlockLevel(((ScannableReference)level).Barcode.ID); if (((ScannableReference)loadLevel).Barcode.ID != fromLevel.LoadScene) { loadLevel = new LevelCrateReference(new Barcode(fromLevel.LoadScene)); } Campaign.Session = fromLevel; } return true; } } [HarmonyPatch(typeof(Audio2dManager))] public static class LoadMusicPatches { [HarmonyPatch("CueMusicInternal")] [HarmonyPrefix] public static void CueMusicPatch(Audio2dManager __instance, ref AudioClip musicClip) { if (((Object)musicClip).name == "music_LoadingSplash" && Campaign.SessionActive && (Object)(object)Campaign.Session.LoadSceneMusic != (Object)null) { musicClip = Campaign.Session.LoadSceneMusic; } } [HarmonyPatch("StopSpecificMusic")] [HarmonyPrefix] public static void StopMusicPatch(Audio2dManager __instance, ref AudioClip specificClip) { if (((Object)specificClip).name == "music_LoadingSplash" && Campaign.SessionActive && (Object)(object)Campaign.Session.LoadSceneMusic != (Object)null) { specificClip = Campaign.Session.LoadSceneMusic; } } } [HarmonyPatch(typeof(LevelsPanelView))] public static class LevelsPanelPatches { public static bool SwipezActive; [HarmonyPatch("CalculateSceneList")] [HarmonyPostfix] public static void PopulatePostfix(LevelsPanelView __instance) { ForceLevelList(__instance); } public static void ForceLevelList(LevelsPanelView __instance) { if (SwipezActive) { return; } if (Campaign.SessionLocked) { __instance._levelCrates.Clear(); CampaignLevel[] unlockedLevels = Campaign.Session.GetUnlockedLevels(); CampaignLevel[] array = unlockedLevels; foreach (CampaignLevel campaignLevel in array) { if (!((Scannable)campaignLevel.crate).Redacted) { __instance._levelCrates.Add(campaignLevel.crate); } } __instance._totalScenes = __instance._levelCrates.Count; __instance._numberOfPages = __instance._levelCrates.Count / ((Il2CppArrayBase<GameObject>)(object)__instance.items).Length + 1; return; } Campaign campaign = null; if (Campaign.SessionActive && Campaign.Session.PrioritizeInLevelPanel) { campaign = Campaign.Session; } List<LevelCrate> levelCrates = __instance._levelCrates; List<LevelCrate> list = new List<LevelCrate>(levelCrates.Count); Enumerator<LevelCrate> enumerator = levelCrates.GetEnumerator(); while (enumerator.MoveNext()) { LevelCrate current = enumerator.Current; list.Add(current); } List<LevelCrate> source = list; List<LevelCrate> list2 = source.Where((LevelCrate crate) => ((Scannable)((Crate)crate).Pallet).Barcode.ID.StartsWith("SLZ")).ToList(); List<LevelCrate> list3 = source.Where((LevelCrate crate) => !((Scannable)((Crate)crate).Pallet).Barcode.ID.StartsWith("SLZ") && !CampaignUtilities.IsCampaignLevel(((Scannable)crate).Barcode.ID)).ToList(); List<LevelCrate> list4 = new List<LevelCrate>(); foreach (Campaign loadedCampaign in CampaignUtilities.LoadedCampaigns) { if (campaign == null || campaign != loadedCampaign) { list4.AddRange(loadedCampaign.GetUnlockedLevels().ToCrates()); } } List<LevelCrate> list5 = list2; List<LevelCrate> list6 = list4; List<LevelCrate> list7 = list3; List<LevelCrate> list8 = new List<LevelCrate>(list5.Count + list6.Count + list7.Count); list8.AddRange(list5); list8.AddRange(list6); list8.AddRange(list7); List<LevelCrate> list9 = list8; if (campaign != null) { list9.InsertRange(0, campaign.GetUnlockedLevels().ToCrates()); } __instance._levelCrates.Clear(); foreach (LevelCrate item in list9) { __instance._levelCrates.Add(item); } __instance._totalScenes = list9.Count; __instance._numberOfPages = list9.Count / ((Il2CppArrayBase<GameObject>)(object)__instance.items).Length + 1; } } public static class SwipezPanelPatches { private static Dictionary<Campaign, PanelContainer> campaignToContainerOpen = new Dictionary<Campaign, PanelContainer>(); private static Dictionary<LevelPanelOverride, PanelContainer> mainToCampaignContainer = new Dictionary<LevelPanelOverride, PanelContainer>(); public static void ManualPatch() { //IL_0006: Unknown result type (might be due to invalid IL or missing references) //IL_000c: Expected O, but got Unknown //IL_0032: Unknown result type (might be due to invalid IL or missing references) //IL_003f: Expected O, but got Unknown //IL_0066: Unknown result type (might be due to invalid IL or missing references) //IL_0073: Expected O, but got Unknown Harmony val = new Harmony("swipez.panel.populate"); val.Patch((MethodBase)typeof(LevelPanelOverride).GetMethod("PopulateMenus"), (HarmonyMethod)null, new HarmonyMethod(typeof(SwipezPanelPatches), "MenuPopulationOverride", (Type[])null), (HarmonyMethod)null, (HarmonyMethod)null, (HarmonyMethod)null); val.Patch((MethodBase)typeof(LevelPanelOverride).GetMethod("OnInitialized"), (HarmonyMethod)null, new HarmonyMethod(typeof(SwipezPanelPatches), "MenuInitContainerOverride", (Type[])null), (HarmonyMethod)null, (HarmonyMethod)null, (HarmonyMethod)null); LevelsPanelPatches.SwipezActive = true; } public static void MenuPopulationOverride(LevelPanelOverride __instance) { PanelContainer orMakeCampaignContainer = __instance.GetOrMakeCampaignContainer("Campaigns"); orMakeCampaignContainer.Clear(); campaignToContainerOpen.Clear(); foreach (Campaign c in CampaignUtilities.CampaignsToShowInMenu) { PanelContainer val = orMakeCampaignContainer.MakeContainer(c.Name); campaignToContainerOpen.Add(c, val); CampaignLevel[] unlockedLevels = c.GetUnlockedLevels(); foreach (CampaignLevel level in unlockedLevels) { if (Object.op_Implicit((Object)(object)level.crate) && !((Scannable)level.crate).Redacted) { val.AddEntry(level.Title, (Action)delegate { //IL_001b: Unknown result type (might be due to invalid IL or missing references) //IL_0025: Expected O, but got Unknown FadeLoader.Load(level.Barcode, new Barcode(c.LoadScene)); }); } } } } public static PanelContainer GetOrMakeCampaignContainer(this LevelPanelOverride container, string name) { if (!mainToCampaignContainer.ContainsKey(container)) { mainToCampaignContainer.Add(container, container.mainContainer.MakeContainer(name)); } return mainToCampaignContainer[container]; } public static void MenuInitContainerOverride(LevelPanelOverride __instance) { if (Campaign.SessionActive) { if (campaignToContainerOpen.Keys.Contains(Campaign.Session)) { ((PanelOverrider)__instance).OpenContainer(campaignToContainerOpen[Campaign.Session], 0); } if (Campaign.SessionLocked) { campaignToContainerOpen[Campaign.Session].parent = null; } else { campaignToContainerOpen[Campaign.Session].parent = __instance.mainContainer; } } } } [HarmonyPatch(typeof(HideOnAwake))] public static class HideOnAwakePatches { [HarmonyPatch("Awake")] [HarmonyPostfix] public static void UnhideInCampaign(HideOnAwake __instance) { UnhideInCampaign unhideInCampaign = default(UnhideInCampaign); if (((Component)__instance).TryGetComponent<UnhideInCampaign>(ref unhideInCampaign)) { ((Component)__instance).gameObject.SetActive(true); Object.Destroy((Object)(object)__instance); } } } [HarmonyPatch(typeof(PullCordDevice))] public static class BodylogEnablePatches { [HarmonyPatch("OnEnable")] [HarmonyPostfix] public static void OnBodyLogEnabled(PullCordDevice __instance) { if (Campaign.SessionActive && !Campaign.Session.saveData.AvatarUnlocked && Campaign.Session.AvatarRestrictionType.HasFlag(AvatarRestrictionType.DisableBodyLog)) { ((Component)__instance).gameObject.SetActive(false); } } } [HarmonyPatch(typeof(AvatarsPanelView))] public static class AvatarPanelEnable { [HarmonyPatch("Activate")] [HarmonyPostfix] public static void OnPanelEnabled(AvatarsPanelView __instance) { //IL_0052: Unknown result type (might be due to invalid IL or missing references) //IL_0057: 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_0067: 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) //IL_0077: Unknown result type (might be due to invalid IL or missing references) //IL_007c: Unknown result type (might be due to invalid IL or missing references) //IL_007e: Unknown result type (might be due to invalid IL or missing references) //IL_0083: Unknown result type (might be due to invalid IL or missing references) //IL_008f: Expected O, but got Unknown if (Campaign.SessionActive && !Campaign.Session.saveData.AvatarUnlocked && Campaign.Session.AvatarRestrictionType.HasFlag(AvatarRestrictionType.RestrictAvatar)) { ((PanelView)__instance).Deactivate(); ((PanelView)__instance).popUpMenu.Deactivate(); Notifier.Send(new Notification { Title = NotificationText.op_Implicit(Campaign.Session.Name), Message = NotificationText.op_Implicit("Avatar switching is currently locked"), Type = (NotificationType)2, ShowTitleOnPopup = true }); } } } [HarmonyPatch(typeof(RigManager))] public static class ForceAvatarSwitch { public static void OnAvatarSwapped(RigManager __instance, Barcode barcode) { //IL_005f: Unknown result type (might be due to invalid IL or missing references) //IL_0064: Unknown result type (might be due to invalid IL or missing references) //IL_006f: Unknown result type (might be due to invalid IL or missing references) //IL_0074: Unknown result type (might be due to invalid IL or missing references) //IL_0079: Unknown result type (might be due to invalid IL or missing references) //IL_007f: Unknown result type (might be due to invalid IL or missing references) //IL_0084: Unknown result type (might be due to invalid IL or missing references) //IL_0089: Unknown result type (might be due to invalid IL or missing references) //IL_008b: Unknown result type (might be due to invalid IL or missing references) //IL_0090: Unknown result type (might be due to invalid IL or missing references) //IL_009c: Expected O, but got Unknown //IL_00aa: Unknown result type (might be due to invalid IL or missing references) //IL_00b6: Expected O, but got Unknown //IL_00f6: Unknown result type (might be due to invalid IL or missing references) //IL_0102: Expected O, but got Unknown if (!Campaign.SessionActive || Campaign.Session.saveData.AvatarUnlocked) { return; } if (Campaign.Session.AvatarRestrictionType.HasFlag(AvatarRestrictionType.EnforceWhitelist)) { if (!Campaign.Session.WhitelistedAvatars.Contains(barcode.ID)) { Notifier.Send(new Notification { Title = NotificationText.op_Implicit(Campaign.Session.Name), Message = NotificationText.op_Implicit("This avatar is not allowed at this time"), Type = (NotificationType)2, ShowTitleOnPopup = true }); __instance.SwapAvatarCrate(new Barcode(Campaign.Session.WhitelistedAvatars[0]), false, (Action<bool>)null); } } else if ((Campaign.Session.AvatarRestrictionType & AvatarRestrictionType.RestrictAvatar) != 0 && barcode.ID != Campaign.Session.CampaignAvatar) { __instance.SwapAvatarCrate(new Barcode(Campaign.Session.CampaignAvatar), false, (Action<bool>)null); } } [HarmonyPatch("Awake")] [HarmonyPrefix] public static void OnRigmanagerAwake(RigManager __instance) { RigManager obj = __instance; obj.onAvatarSwapped2 += Action<Barcode>.op_Implicit((Action<Barcode>)delegate(Barcode b) { OnAvatarSwapped(__instance, b); }); } } } namespace CustomCampaignTools.SDK { [RegisterTypeInIl2Cpp] public class ObjectEnabledSaver : MonoBehaviour { public Il2CppValueField<int> uniqueID; public ObjectEnabledSaver(IntPtr ptr) : base(ptr) { } public void Awake() { if (SavepointFunctions.CurrentLevelLoadedByContinue) { RestoreActiveState(Campaign.Session.saveData.LoadedSavePoint); } } public void RestoreActiveState(CampaignSaveData.SavePoint savePoint) { ((Component)this).gameObject.SetActive(savePoint.GetEnabledStateFromID(uniqueID.Get(), ((Component)this).gameObject.activeSelf)); } } [RegisterTypeInIl2Cpp] public class SpawnerDespawnSaver : MonoBehaviour { public bool LoadedFromSave = false; private GameObject _objectToSave; private bool saveDontSpawn; public SpawnerDespawnSaver(IntPtr ptr) : base(ptr) { } public void Awake() { if (SavepointFunctions.CurrentLevelLoadedByContinue) { LoadedFromSave = true; } } public bool DontSpawnAgain(out string id) { id = GetCrateID(); return saveDontSpawn; } public string GetCrateID() { //IL_0007: Unknown result type (might be due to invalid IL or missing references) //IL_000c: Unknown result type (might be due to invalid IL or missing references) Vector3 position = ((Component)this).transform.position; return ((Vector3)(ref position)).ToString("F2"); } public void Setup(CrateSpawner c, GameObject g) { _objectToSave = g; Poolee val = default(Poolee); if (g.TryGetComponent<Poolee>(ref val)) { CrateDespawnerHook crateDespawnerHook = g.AddComponent<CrateDespawnerHook>(); crateDespawnerHook.OnDespawnDelegate = (Action<GameObject>)Delegate.Combine(crateDespawnerHook.OnDespawnDelegate, (Action<GameObject>)delegate { saveDontSpawn = true; }); } AIBrain componentInChildren = g.GetComponentInChildren<AIBrain>(); if (Object.op_Implicit((Object)(object)componentInChildren)) { componentInChildren.onDeathDelegate += Action<AIBrain>.op_Implicit((Action<AIBrain>)delegate { saveDontSpawn = true; }); } Poolee val2 = default(Poolee); if (LoadedFromSave && Campaign.Session.saveData.LoadedSavePoint.DespawnedSpawners.Contains(GetCrateID()) && g.TryGetComponent<Poolee>(ref val2)) { val2.Despawn(); } } } [RegisterTypeInIl2Cpp] public class HideInCampaign : MonoBehaviour { public HideInCampaign(IntPtr ptr) : base(ptr) { } private void Awake() { ((Component)this).gameObject.SetActive(false); } } [RegisterTypeInIl2Cpp] public class TriggerableNotification : MonoBehaviour { public TriggerableNotification(IntPtr ptr) : base(ptr) { } public void SendNotificat