Please disclose if any significant portion of your mod was created using AI tools by adding the 'AI Generated' category. Failing to do so may result in the mod being removed from Thunderstore.
Decompiled source of LethalMon v0.4.7
plugins/LethalMon/LethalMon.dll
Decompiled 2 years ago
The result has been truncated due to the large size, download it to view full contents!
using System; using System.Collections; using System.Collections.Generic; using System.Diagnostics; using System.Globalization; using System.IO; using System.Linq; using System.Reflection; using System.Runtime.CompilerServices; using System.Runtime.Versioning; using System.Security; using System.Security.Permissions; using BepInEx; using BepInEx.Bootstrap; using BepInEx.Configuration; using BepInEx.Logging; using DigitalRuby.ThunderAndLightning; using GameNetcodeStuff; using HarmonyLib; using LethalCompanyInputUtils.Api; using LethalCompanyInputUtils.BindingPathEnums; using LethalLib.Modules; using LethalMon; using LethalMon.Behaviours; using LethalMon.CatchableEnemy; using LethalMon.Compatibility; using LethalMon.CustomPasses; using LethalMon.Items; using LethalMon.NetcodePatcher; using LethalMon.Patches; using LethalMon.Throw; using Microsoft.CodeAnalysis; using ModelReplacement; using ModelReplacement.Monobehaviors.Enemies; using Newtonsoft.Json; using TMPro; using TerminalApi; using TerminalApi.Classes; using Unity.Collections; using Unity.Netcode; using UnityEngine; using UnityEngine.AI; using UnityEngine.Events; using UnityEngine.InputSystem; using UnityEngine.Rendering; using UnityEngine.Rendering.HighDefinition; using UnityEngine.Rendering.RendererUtils; using UnityEngine.UI; [assembly: CompilationRelaxations(8)] [assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)] [assembly: Debuggable(DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints)] [assembly: TargetFramework(".NETStandard,Version=v2.1", FrameworkDisplayName = ".NET Standard 2.1")] [assembly: AssemblyCompany("LethalMon")] [assembly: AssemblyConfiguration("Release")] [assembly: AssemblyFileVersion("1.0.0.0")] [assembly: AssemblyInformationalVersion("1.0.0+4aca66cbd2fa774e84486d5ec3c4493a5dd7efe3")] [assembly: AssemblyProduct("LethalMon")] [assembly: AssemblyTitle("LethalMon")] [assembly: SecurityPermission(SecurityAction.RequestMinimum, SkipVerification = true)] [assembly: AssemblyVersion("1.0.0.0")] [module: UnverifiableCode] [module: RefSafetyRules(11)] [module: NetcodePatchedAssembly] internal class <Module> { static <Module>() { NetworkVariableSerializationTypes.InitializeSerializer_FixedString<FixedString64Bytes>(); NetworkVariableSerializationTypes.InitializeEqualityChecker_UnmanagedIEquatable<FixedString64Bytes>(); NetworkVariableSerializationTypes.InitializeSerializer_FixedString<FixedString512Bytes>(); NetworkVariableSerializationTypes.InitializeEqualityChecker_UnmanagedIEquatable<FixedString512Bytes>(); NetworkVariableSerializationTypes.InitializeSerializer_UnmanagedByMemcpy<float>(); NetworkVariableSerializationTypes.InitializeEqualityChecker_UnmanagedIEquatable<float>(); } } namespace Microsoft.CodeAnalysis { [CompilerGenerated] [Microsoft.CodeAnalysis.Embedded] internal sealed class EmbeddedAttribute : Attribute { } } namespace System.Runtime.CompilerServices { [CompilerGenerated] [Microsoft.CodeAnalysis.Embedded] [AttributeUsage(AttributeTargets.Class | AttributeTargets.Property | AttributeTargets.Field | AttributeTargets.Event | AttributeTargets.Parameter | AttributeTargets.ReturnValue | AttributeTargets.GenericParameter, AllowMultiple = false, Inherited = false)] internal sealed class NullableAttribute : Attribute { public readonly byte[] NullableFlags; public NullableAttribute(byte P_0) { NullableFlags = new byte[1] { P_0 }; } public NullableAttribute(byte[] P_0) { NullableFlags = P_0; } } [CompilerGenerated] [Microsoft.CodeAnalysis.Embedded] [AttributeUsage(AttributeTargets.Class | AttributeTargets.Struct | AttributeTargets.Method | AttributeTargets.Interface | AttributeTargets.Delegate, AllowMultiple = false, Inherited = false)] internal sealed class NullableContextAttribute : Attribute { public readonly byte Flag; public NullableContextAttribute(byte P_0) { Flag = P_0; } } [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; } } } internal class SeeThroughCustomPass : CustomPass { public Material seeThroughMaterial = new Material(Utils.WireframeMaterial); public LayerMask seeThroughLayer; public float maxVisibilityDistance = 20f; [SerializeField] private Shader stencilShader = Utils.SeeThroughShader; private Material stencilMaterial; private ShaderTagId[] shaderTags; protected override bool executeInSceneView => true; public void ConfigureMaterial(Color edgeColor, Color fillColor, float thickness) { //IL_000b: 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) seeThroughMaterial.SetColor("_EdgeColor", edgeColor); seeThroughMaterial.SetColor("_MainColor", fillColor); seeThroughMaterial.SetFloat("_WireframeVal", thickness); } protected override void Setup(ScriptableRenderContext renderContext, CommandBuffer cmd) { //IL_001f: Unknown result type (might be due to invalid IL or missing references) //IL_0024: Unknown result type (might be due to invalid IL or missing references) //IL_0030: 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_0041: Unknown result type (might be due to invalid IL or missing references) //IL_0046: Unknown result type (might be due to invalid IL or missing references) //IL_0052: Unknown result type (might be due to invalid IL or missing references) //IL_0057: Unknown result type (might be due to invalid IL or missing references) stencilMaterial = CoreUtils.CreateEngineMaterial(stencilShader); shaderTags = (ShaderTagId[])(object)new ShaderTagId[4] { new ShaderTagId("Forward"), new ShaderTagId("ForwardOnly"), new ShaderTagId("SRPDefaultUnlit"), new ShaderTagId("FirstPass") }; } protected override void Execute(CustomPassContext ctx) { //IL_0029: Unknown result type (might be due to invalid IL or missing references) //IL_002a: Unknown result type (might be due to invalid IL or missing references) //IL_002f: Unknown result type (might be due to invalid IL or missing references) //IL_003d: 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_0043: Unknown result type (might be due to invalid IL or missing references) //IL_006b: 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_0071: 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_008f: Unknown result type (might be due to invalid IL or missing references) //IL_0094: 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) stencilMaterial.SetInt("_StencilWriteMask", 64); seeThroughMaterial.SetFloat("_MaxVisibilityDistance", maxVisibilityDistance); RenderObjects(ctx.renderContext, ctx.cmd, stencilMaterial, 0, (CompareFunction)4, ctx.cullingResults, ctx.hdCamera); StencilState value = default(StencilState); ((StencilState)(ref value))..ctor(true, (byte)64, byte.MaxValue, (CompareFunction)3, (StencilOp)0, (StencilOp)0, (StencilOp)0); RenderObjects(ctx.renderContext, ctx.cmd, seeThroughMaterial, seeThroughMaterial.FindPass("ForwardOnly"), (CompareFunction)7, ctx.cullingResults, ctx.hdCamera, value); } public override IEnumerable<Material> RegisterMaterialForInspector() { yield return seeThroughMaterial; } private void RenderObjects(ScriptableRenderContext renderContext, CommandBuffer cmd, Material overrideMaterial, int passIndex, CompareFunction depthCompare, CullingResults cullingResult, HDCamera hdCamera, StencilState? overrideStencil = null) { //IL_0008: Unknown result type (might be due to invalid IL or missing references) //IL_0019: Unknown result type (might be due to invalid IL or missing references) //IL_0020: Unknown result type (might be due to invalid IL or missing references) //IL_0025: Unknown result type (might be due to invalid IL or missing references) //IL_002d: Unknown result type (might be due to invalid IL or missing references) //IL_004e: 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_006c: Unknown result type (might be due to invalid IL or missing references) //IL_0076: Unknown result type (might be due to invalid IL or missing references) //IL_0081: Unknown result type (might be due to invalid IL or missing references) //IL_0082: 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_00c7: Unknown result type (might be due to invalid IL or missing references) //IL_00c8: Unknown result type (might be due to invalid IL or missing references) //IL_0093: Unknown result type (might be due to invalid IL or missing references) //IL_0098: Unknown result type (might be due to invalid IL or missing references) //IL_009c: Unknown result type (might be due to invalid IL or missing references) //IL_00a2: Unknown result type (might be due to invalid IL or missing references) //IL_00ac: Unknown result type (might be due to invalid IL or missing references) //IL_00b8: Unknown result type (might be due to invalid IL or missing references) RendererListDesc val = default(RendererListDesc); ((RendererListDesc)(ref val))..ctor(shaderTags, cullingResult, hdCamera.camera); val.rendererConfiguration = (PerObjectData)0; val.renderQueueRange = RenderQueueRange.all; val.sortingCriteria = (SortingCriteria)4; val.excludeObjectMotionVectors = false; val.overrideMaterial = overrideMaterial; val.overrideMaterialPassIndex = passIndex; val.layerMask = LayerMask.op_Implicit(seeThroughLayer); RenderStateBlock value = default(RenderStateBlock); ((RenderStateBlock)(ref value))..ctor((RenderStateMask)4); ((RenderStateBlock)(ref value)).depthState = new DepthState(true, depthCompare); val.stateBlock = value; RendererListDesc val2 = val; if (overrideStencil.HasValue) { RenderStateBlock value2 = val2.stateBlock.Value; ((RenderStateBlock)(ref value2)).mask = (RenderStateMask)(((RenderStateBlock)(ref value2)).mask | 8); ((RenderStateBlock)(ref value2)).stencilState = overrideStencil.Value; val2.stateBlock = value2; } CoreUtils.DrawRendererList(renderContext, cmd, ((ScriptableRenderContext)(ref renderContext)).CreateRendererList(val2)); } protected override void Cleanup() { } } namespace LethalMon { public sealed class ModConfig : LcInputActions { public struct ConfigValues { public int Tier1BallSpawnWeight { get; set; } public int Tier2BallSpawnWeight { get; set; } public int Tier3BallSpawnWeight { get; set; } public int Tier4BallSpawnWeight { get; set; } public int Tier1BallCost { get; set; } public int Tier2BallCost { get; set; } public int Tier3BallCost { get; set; } public int Tier4BallCost { get; set; } public string KeepBallsIfAllPlayersDead { get; set; } public int CaptureRateModifier { get; set; } public string[] DisabledMonsters { get; set; } public bool MonstersReactToFailedCaptures { get; set; } public float BrackenGrabCooldown { get; set; } public float DressGirlTeleportCooldown { get; set; } public float HoardingBugBringItemCooldown { get; set; } public float FoxTongueHitCooldown { get; set; } public float EyelessDogHowlCooldown { get; set; } public float MaskedLendCooldown { get; set; } } [HarmonyPatch] public class SyncHandshake { private const string REQUEST_MESSAGE = "LethalMon_HostConfigRequested"; private const string RECEIVE_MESSAGE = "LethalMon_HostConfigReceived"; [HarmonyPatch(typeof(PlayerControllerB), "ConnectClientToPlayerObject")] [HarmonyPostfix] public static void Initialize(PlayerControllerB __instance) { //IL_0078: Unknown result type (might be due to invalid IL or missing references) //IL_0082: Expected O, but got Unknown //IL_0034: Unknown result type (might be due to invalid IL or missing references) //IL_003e: Expected O, but got Unknown if ((Object)(object)Utils.CurrentPlayer == (Object)(object)__instance) { if (Utils.IsHost) { Debug.Log((object)"Current player is the host."); NetworkManager.Singleton.CustomMessagingManager.RegisterNamedMessageHandler("LethalMon_HostConfigRequested", new HandleNamedMessageDelegate(HostConfigRequested)); Instance.values = Instance.originalValues; ProcessValues(); } else { Debug.Log((object)"Current player is not the host."); NetworkManager.Singleton.CustomMessagingManager.RegisterNamedMessageHandler("LethalMon_HostConfigReceived", new HandleNamedMessageDelegate(HostConfigReceived)); RequestHostConfig(); } } } public static void RequestHostConfig() { //IL_0025: Unknown result type (might be due to invalid IL or missing references) if (!Utils.IsHost) { Debug.Log((object)"Sending config request to host."); NetworkManager.Singleton.CustomMessagingManager.SendNamedMessage("LethalMon_HostConfigRequested", 0uL, new FastBufferWriter(0, (Allocator)2, -1), (NetworkDelivery)3); } else { Debug.Log((object)"Config request not required. No other player available."); } } public static void HostConfigRequested(ulong clientId, FastBufferReader reader) { //IL_0064: Unknown result type (might be due to invalid IL or missing references) if (!Utils.IsHost) { return; } string text = JsonConvert.SerializeObject((object)Instance.values); Debug.Log((object)("Client [" + clientId + "] requested host config. Sending own config: " + text)); int writeSize = FastBufferWriter.GetWriteSize(text, false); FastBufferWriter val = default(FastBufferWriter); ((FastBufferWriter)(ref val))..ctor(writeSize, (Allocator)2, -1); try { ((FastBufferWriter)(ref val)).WriteValueSafe(text, false); NetworkManager.Singleton.CustomMessagingManager.SendNamedMessage("LethalMon_HostConfigReceived", clientId, val, (NetworkDelivery)4); } finally { ((IDisposable)(FastBufferWriter)(ref val)).Dispose(); } } public static void HostConfigReceived(ulong clientId, FastBufferReader reader) { string text = default(string); ((FastBufferReader)(ref reader)).ReadValueSafe(ref text, false); Debug.Log((object)("Received host config: " + text)); ConfigValues values = JsonConvert.DeserializeObject<ConfigValues>(text); Instance.values = values; ProcessValues(); } } public ConfigValues values; public ConfigValues originalValues; private static ModConfig instance; public InputAction RetrieveBallKey => ((LcInputActions)this).Asset["retreiveBallKey"]; public InputAction ActionKey1 => ((LcInputActions)this).Asset["actionKey1"]; public static ModConfig Instance { get { if (instance == null) { instance = new ModConfig(); } return instance; } } public void Setup() { values.Tier1BallCost = ((BaseUnityPlugin)LethalMon.Instance).Config.Bind<int>("Items", "Tier1BallCost", 40, "The cost of the tier 1 ball (pokeball) item in the shop. -1 to disable").Value; values.Tier2BallCost = ((BaseUnityPlugin)LethalMon.Instance).Config.Bind<int>("Items", "Tier2BallCost", 125, "The cost of the tier 1 ball (great ball) item in the shop. -1 to disable").Value; values.Tier3BallCost = ((BaseUnityPlugin)LethalMon.Instance).Config.Bind<int>("Items", "Tier3BallCost", 375, "The cost of the tier 1 ball (ultra ball) item in the shop. -1 to disable").Value; values.Tier4BallCost = ((BaseUnityPlugin)LethalMon.Instance).Config.Bind<int>("Items", "Tier4BallCost", 700, "The cost of the tier 1 ball (master ball) item in the shop. -1 to disable").Value; values.Tier1BallSpawnWeight = ((BaseUnityPlugin)LethalMon.Instance).Config.Bind<int>("Items", "Tier1BallSpawnWeight", 20, "The spawn weight of the tier 1 ball (pokeball). Higher = more common").Value; values.Tier2BallSpawnWeight = ((BaseUnityPlugin)LethalMon.Instance).Config.Bind<int>("Items", "Tier2BallSpawnWeight", 10, "The spawn weight of the tier 2 ball (great ball). Higher = more common").Value; values.Tier3BallSpawnWeight = ((BaseUnityPlugin)LethalMon.Instance).Config.Bind<int>("Items", "Tier3BallSpawnWeight", 6, "The spawn weight of the tier 3 ball (ultra ball). Higher = more common").Value; values.Tier4BallSpawnWeight = ((BaseUnityPlugin)LethalMon.Instance).Config.Bind<int>("Items", "Tier4BallSpawnWeight", 2, "The spawn weight of the tier 4 ball (master ball). Higher = more common").Value; values.KeepBallsIfAllPlayersDead = ((BaseUnityPlugin)LethalMon.Instance).Config.Bind<string>("Items", "KeepBallsIfAllPlayersDead", "no", "Make the balls don't despawn even if all the players are dead. Values are: no, fullOnly, all").Value; values.DisabledMonsters = ((BaseUnityPlugin)LethalMon.Instance).Config.Bind<string>("Monsters", "DisabledMonsters", "", "Disabled monsters types. Separate with a comma and don't put spaces. Example: Monster1,Monster2. Available monsters: " + string.Join(", ", Enum.GetNames(typeof(Utils.Enemy)))).Value.Split(","); values.MonstersReactToFailedCaptures = ((BaseUnityPlugin)LethalMon.Instance).Config.Bind<bool>("Monsters", "MonstersReactToFailedCaptures", true, "Make the monsters react aggressively if a capture fails").Value; values.CaptureRateModifier = ((BaseUnityPlugin)LethalMon.Instance).Config.Bind<int>("Monsters", "CaptureRateModifier", 0, "Modifier for the capture rate. Each monster have a difficulty to catch between 1 and 10. You can modify all the monsters difficulty by adding this modifier to the base difficulty. Negative = easier to catch, positive = harder to catch").Value; values.BrackenGrabCooldown = ((BaseUnityPlugin)LethalMon.Instance).Config.Bind<float>("Cooldowns", "BrackenGrabCooldown", 20f, "Grab cooldown time in seconds for the bracken").Value; values.DressGirlTeleportCooldown = ((BaseUnityPlugin)LethalMon.Instance).Config.Bind<float>("Cooldowns", "DressGirlTeleportCooldown", 60f, "Teleport cooldown time in seconds for the dress girl").Value; values.HoardingBugBringItemCooldown = ((BaseUnityPlugin)LethalMon.Instance).Config.Bind<float>("Cooldowns", "HoardingBugBringItemCooldown", 5f, "Bring item cooldown time in seconds for the hoarder bug").Value; values.FoxTongueHitCooldown = ((BaseUnityPlugin)LethalMon.Instance).Config.Bind<float>("Cooldowns", "FoxTongueHitCooldown", 5f, "Tongue hit cooldown time in seconds for the fox").Value; values.EyelessDogHowlCooldown = ((BaseUnityPlugin)LethalMon.Instance).Config.Bind<float>("Cooldowns", "EyelessDogHowlCooldown", 5f, "Howl cooldown time in seconds for the eyeless dog").Value; values.MaskedLendCooldown = ((BaseUnityPlugin)LethalMon.Instance).Config.Bind<float>("Cooldowns", "MaskedLendCooldown", 7f, "Mask lending cooldown time in seconds for the masked").Value; originalValues = values; } public override void CreateInputActions(in InputActionMapBuilder builder) { //IL_001b: Unknown result type (might be due to invalid IL or missing references) //IL_0059: Unknown result type (might be due to invalid IL or missing references) //IL_00cb: Unknown result type (might be due to invalid IL or missing references) //IL_010a: Unknown result type (might be due to invalid IL or missing references) ConfigFile config = ((BaseUnityPlugin)LethalMon.Instance).Config; KeyboardControl val = (KeyboardControl)36; string value = config.Bind<string>("Controls", "RetrieveBallKeyKeyboard", "<Keyboard>/" + ((object)(KeyboardControl)(ref val)).ToString(), "Key for retrieving the tamed enemy inside its ball. Requires a restart after changing.").Value; ConfigFile config2 = ((BaseUnityPlugin)LethalMon.Instance).Config; GamepadControl val2 = (GamepadControl)7; string value2 = config2.Bind<string>("Controls", "RetrieveBallKeyGamepad", "<Gamepad>/" + ((object)(GamepadControl)(ref val2)).ToString(), "Gamepad key for retrieving the tamed enemy inside its ball. Requires a restart after changing.").Value; builder.NewActionBinding().WithActionId("retreiveBallKey").WithActionType((InputActionType)1) .WithBindingName("RetrieveBallKey") .WithKbmPath(value) .WithGamepadPath(value2) .Finish(); ConfigFile config3 = ((BaseUnityPlugin)LethalMon.Instance).Config; val = (KeyboardControl)22; string value3 = config3.Bind<string>("Controls", "ActionKey1Keyboard", "<Keyboard>/" + ((object)(KeyboardControl)(ref val)).ToString(), "Key for the first custom action on a tamed enemy. Requires a restart after changing.").Value; ConfigFile config4 = ((BaseUnityPlugin)LethalMon.Instance).Config; val2 = (GamepadControl)9; string value4 = config4.Bind<string>("Controls", "ActionKey1Gamepad", "<Gamepad>/" + ((object)(GamepadControl)(ref val2)).ToString(), "Gamepad key for the first custom action on a tamed enemy. Requires a restart after changing.").Value; builder.NewActionBinding().WithActionId("actionKey1").WithActionType((InputActionType)1) .WithBindingName("ActionKey1") .WithKbmPath(value3) .WithGamepadPath(value4) .Finish(); } public static void ProcessValues() { LethalMon.Log("Processing config"); if ((Object)(object)Pokeball.BallItem != (Object)null) { if (Instance.values.Tier1BallCost >= 0) { Items.UpdateShopItemPrice(Pokeball.BallItem, Instance.values.Tier1BallCost); } else { Items.RemoveShopItem(Pokeball.BallItem); } } if ((Object)(object)Greatball.BallItem != (Object)null) { if (Instance.values.Tier2BallCost >= 0) { Items.UpdateShopItemPrice(Greatball.BallItem, Instance.values.Tier2BallCost); } else { Items.RemoveShopItem(Greatball.BallItem); } } if ((Object)(object)Ultraball.BallItem != (Object)null) { if (Instance.values.Tier3BallCost >= 0) { Items.UpdateShopItemPrice(Ultraball.BallItem, Instance.values.Tier3BallCost); } else { Items.RemoveShopItem(Ultraball.BallItem); } } if ((Object)(object)Masterball.BallItem != (Object)null) { if (Instance.values.Tier4BallCost >= 0) { Items.UpdateShopItemPrice(Masterball.BallItem, Instance.values.Tier4BallCost); } else { Items.RemoveShopItem(Masterball.BallItem); } } string[] disabledMonsters = Instance.values.DisabledMonsters; foreach (string key in disabledMonsters) { Data.CatchableMonsters.Remove(key); } if (Chainloader.PluginInfos.ContainsKey("atomic.terminalapi")) { LethalDex.Register(); } } } public static class Data { public static readonly Random Random = new Random(); public static readonly float[][] CaptureProbabilities = new float[4][] { new float[10] { 0.95f, 0.9f, 0.8f, 0.65f, 0.5f, 0.3f, 0.1f, 0.05f, 0.02f, 0.01f }, new float[10] { 1f, 0.97f, 0.95f, 0.85f, 0.7f, 0.5f, 0.3f, 0.2f, 0.15f, 0.1f }, new float[10] { 1f, 1f, 1f, 0.97f, 0.95f, 0.9f, 0.8f, 0.7f, 0.6f, 0.5f }, new float[10] { 1f, 1f, 1f, 1f, 1f, 1f, 1f, 1f, 1f, 1f } }; public static readonly Dictionary<string, global::LethalMon.CatchableEnemy.CatchableEnemy> CatchableMonsters = new Dictionary<string, global::LethalMon.CatchableEnemy.CatchableEnemy> { { Utils.Enemy.Flowerman.ToString(), new CatchableFlowerman() }, { Utils.Enemy.HoarderBug.ToString(), new CatchableHoarderBug() }, { Utils.Enemy.RedLocustBees.ToString(), new CatchableRedLocustBees() }, { Utils.Enemy.Puffer.ToString(), new CatchableSporeLizard() }, { Utils.Enemy.MouthDog.ToString(), new CatchableMouthDog() }, { Utils.Enemy.FlowerSnake.ToString(), new CatchableTulipSnake() }, { Utils.Enemy.DressGirl.ToString(), new CatchableGhostGirl() }, { Utils.Enemy.Nutcracker.ToString(), new CatchableNutcracker() }, { Utils.Enemy.Butler.ToString(), new CatchableButler() }, { Utils.Enemy.BushWolf.ToString(), new CatchableKidnapperFox() }, { Utils.Enemy.Crawler.ToString(), new CatchableCrawler() }, { Utils.Enemy.MaskedPlayerEnemy.ToString(), new CatchableMasked() } }; } public class LethalDex { private const string TopLeftJoint = "+"; private const string TopRightJoint = "+"; private const string BottomLeftJoint = "+"; private const string BottomRightJoint = "+"; private const string TopJoint = "+"; private const string BottomJoint = "+"; private const string LeftJoint = "+"; private const string MiddleJoint = "+"; private const string RightJoint = "+"; private const char HorizontalLine = '-'; private const string VerticalLine = "|"; private static string _commandText = "Something went wrong :("; public static void Register() { //IL_000f: Unknown result type (might be due to invalid IL or missing references) //IL_0014: Unknown result type (might be due to invalid IL or missing references) //IL_001f: Unknown result type (might be due to invalid IL or missing references) //IL_002a: 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_0061: Expected O, but got Unknown _commandText = InitCommandText(); TerminalApi.AddCommand("lethaldex", new CommandInfo { Title = "LethalDex", Category = "Other", Description = "Shows LethalMon's monsters details", DisplayTextSupplier = () => _commandText }, (string)null, true); LethalMon.Log("Registered LethalDex terminal command"); } private static string InitCommandText() { string text = "Capture probabilities:\n\nPB = Pokeball, GB = Great ball, UB = Ultra ball, MB = Master ball\n"; global::LethalMon.CatchableEnemy.CatchableEnemy[] array = Data.CatchableMonsters.Values.OrderBy((global::LethalMon.CatchableEnemy.CatchableEnemy enemy) => enemy.CatchDifficulty).ToArray(); int num = array.Max((global::LethalMon.CatchableEnemy.CatchableEnemy enemy) => enemy.DisplayName.Length); string text2 = " PB "; string text3 = " GB "; string text4 = " UB "; string text5 = " MB "; text = text + "+" + new string('-', num + 2) + "+" + new string('-', text2.Length + 2) + "+" + new string('-', text3.Length + 2) + "+" + new string('-', text4.Length + 2) + "+" + new string('-', text5.Length + 2) + "+\n"; text = text + "|" + new string(' ', num + 2) + "| " + text2 + " | " + text3 + " | " + text4 + " | " + text5 + " |\n"; string text6 = "+" + new string('-', num + 2) + "+" + new string('-', text2.Length + 2) + "+" + new string('-', text3.Length + 2) + "+" + new string('-', text4.Length + 2) + "+" + new string('-', text5.Length + 2) + "+"; foreach (global::LethalMon.CatchableEnemy.CatchableEnemy catchableEnemy in array) { text = text + text6 + "\n"; string text7 = ((int)Mathf.Floor(catchableEnemy.GetCaptureProbability(0) * 100f)).ToString(); string text8 = ((int)Mathf.Floor(catchableEnemy.GetCaptureProbability(1) * 100f)).ToString(); string text9 = ((int)Mathf.Floor(catchableEnemy.GetCaptureProbability(2) * 100f)).ToString(); string text10 = ((int)Mathf.Floor(catchableEnemy.GetCaptureProbability(3) * 100f)).ToString(); text = text + "| " + catchableEnemy.DisplayName + new string(' ', num - catchableEnemy.DisplayName.Length) + " | " + new string(' ', Math.Clamp(3 - text7.Length, 0, 3)) + text7 + "% | " + new string(' ', Math.Clamp(3 - text8.Length, 0, 3)) + text8 + "% | " + new string(' ', Math.Clamp(3 - text9.Length, 0, 3)) + text9 + "% | " + new string(' ', Math.Clamp(3 - text10.Length, 0, 3)) + text10 + "% |\n"; } return text + "+" + new string('-', num + 2) + "+" + new string('-', text2.Length + 2) + "+" + new string('-', text3.Length + 2) + "+" + new string('-', text4.Length + 2) + "+" + new string('-', text5.Length + 2) + "+\n\n"; } } [BepInDependency(/*Could not decode attribute arguments.*/)] [BepInDependency(/*Could not decode attribute arguments.*/)] [BepInPlugin("LethalMon", "LethalMon", "1.0.0")] public class LethalMon : BaseUnityPlugin { public enum LogType { Message, Warning, Error, Fatal, Debug } internal static GameObject hudPrefab; internal static Dictionary<string, Sprite> monstersSprites = new Dictionary<string, Sprite>(); public static LethalMon Instance { get; private set; } = null; internal static ManualLogSource Logger { get; private set; } = null; internal static Harmony? Harmony { get; set; } private void Awake() { Logger = ((BaseUnityPlugin)this).Logger; Instance = this; ModConfig.Instance.Setup(); LoadAssetBundle(); NetcodePatching(); ApplyHarmonyPatches(); PlayerControllerBPatch.InitializeRPCS(); Logger.LogInfo((object)"LethalMon v1.0.0 has loaded!"); } private void NetcodePatching() { Type[] types = Assembly.GetExecutingAssembly().GetTypes(); Type[] array = types; foreach (Type type in array) { MethodInfo[] methods = type.GetMethods(BindingFlags.Instance | BindingFlags.Static | BindingFlags.NonPublic); MethodInfo[] array2 = methods; foreach (MethodInfo methodInfo in array2) { object[] customAttributes = methodInfo.GetCustomAttributes(typeof(RuntimeInitializeOnLoadMethodAttribute), inherit: false); if (customAttributes.Length != 0) { methodInfo.Invoke(null, null); } } } } private void LoadAssetBundle() { AssetBundle assetBundle = AssetBundle.LoadFromFile(Path.Combine(Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location), "lethalmon")); Pokeball.Setup(assetBundle); Greatball.Setup(assetBundle); Ultraball.Setup(assetBundle); Masterball.Setup(assetBundle); Utils.LoadSeeThroughShader(assetBundle); Utils.LoadWireframeMaterial(assetBundle); MaskedTamedBehaviour.LoadGhostAudio(assetBundle); HoarderBugTamedBehaviour.LoadAudio(assetBundle); hudPrefab = assetBundle.LoadAsset<GameObject>("Assets/UI/MonsterInfo.prefab"); monstersSprites = (from assetName in assetBundle.GetAllAssetNames() where assetName.StartsWith("assets/ui/monstersicons/") && assetName.EndsWith(".png") select assetName).ToDictionary((string assetName) => assetName.Substring("assets/ui/monstersicons/".Length, assetName.Length - "assets/ui/monstersicons/".Length - 4), (string assetName) => assetBundle.LoadAsset<Sprite>(assetName)); } private void ApplyHarmonyPatches() { Harmony = Harmony.CreateAndPatchAll(Assembly.GetExecutingAssembly(), (string)null); Harmony.PatchAll(typeof(DebugPatches)); Harmony.PatchAll(typeof(ModConfig.SyncHandshake)); Harmony.PatchAll(typeof(PlayerControllerBPatch)); Harmony.PatchAll(typeof(StartOfRoundPatch)); Harmony.PatchAll(typeof(RoundManagerPatch)); Harmony.PatchAll(typeof(HUDManagerPatch)); Harmony.PatchAll(typeof(EnemyAIPatch)); Harmony.PatchAll(typeof(RedLocustBeesPatch)); Harmony.PatchAll(typeof(MouthDogPatch)); Harmony.PatchAll(typeof(FlowermanAIPatch)); Harmony.PatchAll(typeof(BushWolfEnemyPatch)); Harmony.PatchAll(typeof(MaskedPlayerEnemyPatch)); Harmony.PatchAll(typeof(TamedEnemyBehaviour)); Harmony.PatchAll(typeof(KidnapperFoxTamedBehaviour)); } private static void Unpatch() { Logger.LogDebug((object)"Unpatching..."); Harmony? harmony = Harmony; if (harmony != null) { harmony.UnpatchSelf(); } Logger.LogDebug((object)"Finished unpatching!"); } internal static void Log(string message, LogType type = LogType.Debug) { switch (type) { case LogType.Debug: break; case LogType.Warning: Logger.LogWarning((object)message); break; case LogType.Error: Logger.LogError((object)message); break; case LogType.Fatal: Logger.LogFatal((object)message); break; default: Logger.LogMessage((object)message); break; } } } public class Utils { public enum Enemy { BaboonHawk, Blob, BushWolf, Butler, ButlerBees, Centipede, ClaySurgeon, Crawler, DocileLocustBees, Doublewing, FlowerSnake, RedLocustBees, DressGirl, Flowerman, ForestGiant, HoarderBug, Jester, LassoMan, MaskedPlayerEnemy, MouthDog, Nutcracker, Puffer, RadMech, RedPillEnemyType, SandSpider, SandWorm, SpringMan } internal class LayerMasks { internal enum Mask { All = -1, Default, TransparentFX, Ignore_Raycast, Player, Water, UI, Props, HelmetVisor, Room, InteractableObject, Foliage, Colliders, PhysicsObject, Triggers, MapRadar, NavigationSurface, RoomLight, Anomaly, LineOfSight, Enemies, PlayerRagdoll, MapHazards, ScanNode, EnemiesNotRendered, MiscLevelGeometry, Terrain, PlaceableShipObjects, PlacementBlocker, Railing, DecalStickableSurface, CompanyCruiser } internal static int ToInt(Mask[] masks) { int num = 0; foreach (Mask mask in masks) { num |= 1 << (int)mask; } return num; } } public static readonly Random Random = new Random(); private static Dictionary<string, TerminalNode> infoNodes = new Dictionary<string, TerminalNode>(); public static readonly float DefaultJumpForce = 13f; private static Item? _giftBoxItem; public static Shader? SeeThroughShader; public static readonly Color EnemyHighlightOutline = Color.red; public static readonly Color EnemyHighlightInline = new Color(0.8f, 0f, 0f, 0.8f); public static readonly Color ItemHighlightOutline = Color.yellow; public static readonly Color ItemHighlightInline = new Color(0.8f, 0.8f, 0f, 0.5f); public static readonly Color PlayerHighlightOutline = Color.green; public static readonly Color PlayerHighlightInline = new Color(0f, 0.8f, 0f, 0.6f); public static Material? WireframeMaterial; private static readonly string GlassName = "LethalMonGlass"; private static Material? _glassMaterial = null; private static Material? _ghostMaterial = null; private static Material? _ghostEyesMaterial = null; public static List<PlayerControllerB>? AllPlayers => StartOfRound.Instance?.allPlayerScripts?.Where((PlayerControllerB pcb) => (Object)(object)pcb != (Object)null && (pcb.isPlayerControlled || pcb.isPlayerDead)).ToList(); public static List<PlayerControllerB>? AlivePlayers => AllPlayers?.Where((PlayerControllerB pcb) => !pcb.isPlayerDead).ToList(); public static PlayerControllerB CurrentPlayer => GameNetworkManager.Instance.localPlayerController; public static ulong? CurrentPlayerID => CurrentPlayer?.playerClientId; public static bool IsHost { get { if ((Object)(object)NetworkManager.Singleton != (Object)null) { if (!NetworkManager.Singleton.IsHost) { return NetworkManager.Singleton.IsServer; } return true; } if (CurrentPlayerID.HasValue) { return CurrentPlayerID.Value == 0; } return false; } } public static float DefaultPlayerSpeed { get { if (!CurrentPlayer.isSprinting) { return 1f; } return 2.25f; } } public static List<EnemyType> EnemyTypes => Resources.FindObjectsOfTypeAll<EnemyType>().ToList(); public static Item? GiftBoxItem { get { if ((Object)(object)_giftBoxItem != (Object)null) { return _giftBoxItem; } _giftBoxItem = ((IEnumerable<Item>)Resources.FindObjectsOfTypeAll<Item>()).FirstOrDefault((Func<Item, bool>)((Item item) => item.itemName == "Gift")); return _giftBoxItem; } } public static Material Glass { get { //IL_001a: Unknown result type (might be due to invalid IL or missing references) //IL_0024: Expected O, but got Unknown //IL_003d: Unknown result type (might be due to invalid IL or missing references) if ((Object)(object)_glassMaterial == (Object)null) { _glassMaterial = new Material(Shader.Find("HDRP/Lit")); _glassMaterial.color = new Color(0.5f, 0.5f, 0.6f, 0.6f); _glassMaterial.renderQueue = 3300; _glassMaterial.shaderKeywords = new string[5] { "_SURFACE_TYPE_TRANSPARENT", "_DISABLE_SSR_TRANSPARENT", "_REFRACTION_THIN", "_NORMALMAP_TANGENT_SPACE", "_ENABLE_FOG_ON_TRANSPARENT" }; ((Object)_glassMaterial).name = GlassName; } return _glassMaterial; } } internal static Material GhostMaterial { get { //IL_0012: Unknown result type (might be due to invalid IL or missing references) //IL_001c: Expected O, but got Unknown //IL_003a: Unknown result type (might be due to invalid IL or missing references) if ((Object)(object)_ghostMaterial == (Object)null) { _ghostMaterial = new Material(WireframeMaterial); _ghostMaterial.SetColor("_EdgeColor", new Color(0.8f, 0.9f, 1f, 0.15f)); _ghostMaterial.SetFloat("_WireframeVal", 1f); _ghostMaterial.SetFloat("_MaxVisibilityDistance", 15f); } return _ghostMaterial; } } internal static Material GhostEyesMaterial { get { //IL_0017: Unknown result type (might be due to invalid IL or missing references) //IL_0021: Expected O, but got Unknown //IL_0035: Unknown result type (might be due to invalid IL or missing references) if ((Object)(object)_ghostEyesMaterial == (Object)null) { _ghostEyesMaterial = new Material(Shader.Find("HDRP/Unlit")); _ghostEyesMaterial.color = new Color(0.8f, 0.9f, 1f); } return _ghostEyesMaterial; } } public static void CallNextFrame(Action action) { ((MonoBehaviour)GameNetworkManager.Instance).StartCoroutine(CallNextFrameCoroutine(action)); } public static IEnumerator CallNextFrameCoroutine(Action action) { yield return null; action(); } public static TamedEnemyBehaviour? GetPlayerPet(PlayerControllerB player) { PlayerControllerB player2 = player; return Object.FindObjectsOfType<TamedEnemyBehaviour>().FirstOrDefault((TamedEnemyBehaviour tamedBehaviour) => (Object)(object)tamedBehaviour.ownerPlayer == (Object)(object)player2); } public static Vector3 GetPositionInFrontOfPlayerEyes(PlayerControllerB player) { //IL_0006: Unknown result type (might be due to invalid IL or missing references) //IL_0011: 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) //IL_0020: Unknown result type (might be due to invalid IL or missing references) return player.playerEye.position + player.playerEye.forward * 2.5f; } public static Vector3 GetPositionBehindPlayer(PlayerControllerB player) { //IL_0006: Unknown result type (might be due to invalid IL or missing references) //IL_0011: 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) //IL_0020: Unknown result type (might be due to invalid IL or missing references) return ((Component)player).transform.position + ((Component)player).transform.forward * -2f; } public static EnemyAI? GetMostProbableAttackerEnemy(PlayerControllerB player, StackTrace stackTrace) { //IL_0085: Unknown result type (might be due to invalid IL or missing references) //IL_00cf: Unknown result type (might be due to invalid IL or missing references) //IL_00db: Unknown result type (might be due to invalid IL or missing references) StackFrame[] frames = stackTrace.GetFrames(); StackFrame[] subArray = frames[1..]; foreach (StackFrame stackFrame in subArray) { Type declaringType = stackFrame.GetMethod().DeclaringType; LethalMon.Log("Stackframe type: " + declaringType); if (!declaringType.IsSubclassOf(typeof(EnemyAI))) { continue; } LethalMon.Log("Class is assignable from EnemyAI"); EnemyAI val = null; float? num = float.MaxValue; Collider[] array = Physics.OverlapSphere(((Component)player).transform.position, 10f); Collider[] array2 = array; foreach (Collider val2 in array2) { EnemyAI componentInParent = ((Component)val2).GetComponentInParent<EnemyAI>(); if ((Object)(object)componentInParent != (Object)null && ((object)componentInParent).GetType() == declaringType) { float num2 = Vector3.Distance(((Component)player).transform.position, ((Component)componentInParent).transform.position); if (num > num2) { val = componentInParent; num = num2; } } } if ((Object)(object)val != (Object)null) { return val; } } return null; } public static TerminalNode CreateTerminalNode(string name, string description) { if (infoNodes.TryGetValue(name, out TerminalNode value)) { return value; } TerminalNode val = ScriptableObject.CreateInstance<TerminalNode>(); Object.DontDestroyOnLoad((Object)(object)val); val.clearPreviousText = true; ((Object)val).name = name + "InfoNode"; val.displayText = description + "\n\n"; infoNodes.Add(name, val); return val; } public static Vector3 GetRandomNavMeshPositionOnRadius(Vector3 pos, float radius, NavMeshHit navHit = default(NavMeshHit)) { //IL_0000: Unknown result type (might be due to invalid IL or missing references) //IL_0007: Unknown result type (might be due to invalid IL or missing references) //IL_000d: Unknown result type (might be due to invalid IL or missing references) //IL_0012: Unknown result type (might be due to invalid IL or missing references) //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_0022: Unknown result type (might be due to invalid IL or missing references) //IL_0036: Unknown result type (might be due to invalid IL or missing references) //IL_0030: Unknown result type (might be due to invalid IL or missing references) float y = pos.y; pos = Random.onUnitSphere * radius + pos; pos.y = y; if (NavMesh.SamplePosition(pos, ref navHit, radius, -1)) { return ((NavMeshHit)(ref navHit)).position; } return pos; } public static void PlaySoundAtPosition(Vector3 position, AudioClip clip, float volume = 1f) { //IL_002e: Unknown result type (might be due to invalid IL or missing references) AudioSource val = (SoundManager.Instance.tempAudio1.isPlaying ? SoundManager.Instance.tempAudio2 : SoundManager.Instance.tempAudio1); ((Component)val).transform.position = position; val.PlayOneShot(clip, volume); } public static void PlaySoundAtPosition(Vector3 position, AudioClip clip) { //IL_000f: Unknown result type (might be due to invalid IL or missing references) ((Component)SoundManager.Instance.tempAudio1).transform.position = position; SoundManager.Instance.tempAudio1.PlayOneShot(clip); } public static void EnableShotgunHeldByEnemyAi(EnemyAI enemyAI, bool enable) { ShotgunItem[] array = Object.FindObjectsOfType<ShotgunItem>(); ShotgunItem[] array2 = array; foreach (ShotgunItem val in array2) { if ((Object)(object)val.heldByEnemy == (Object)(object)enemyAI) { ((GrabbableObject)val).EnableItemMeshes(enable); } } } public static void DestroyShotgunHeldByEnemyAi(EnemyAI enemyAI) { ShotgunItem[] array = Object.FindObjectsOfType<ShotgunItem>(); ShotgunItem[] array2 = array; foreach (ShotgunItem val in array2) { if ((Object)(object)val.heldByEnemy == (Object)(object)enemyAI) { ((Component)val).GetComponent<NetworkObject>().Despawn(true); } } } public static void OpenDoorsAsEnemyAroundPosition(Vector3 position) { //IL_0000: Unknown result type (might be due to invalid IL or missing references) //IL_003f: Unknown result type (might be due to invalid IL or missing references) //IL_0040: Unknown result type (might be due to invalid IL or missing references) Collider[] array = Physics.OverlapSphere(position, 0.5f); Collider[] array2 = array; AnimatedObjectTrigger val3 = default(AnimatedObjectTrigger); foreach (Collider val in array2) { DoorLock componentInParent = ((Component)val).GetComponentInParent<DoorLock>(); if ((Object)(object)componentInParent != (Object)null && !componentInParent.isDoorOpened && !componentInParent.isLocked) { Vector3 val2 = position; LethalMon.Log("Door opened at " + ((object)(Vector3)(ref val2)).ToString()); if (((Component)componentInParent).gameObject.TryGetComponent<AnimatedObjectTrigger>(ref val3)) { val3.TriggerAnimationNonPlayer(false, true, false); } componentInParent.OpenDoorAsEnemyServerRpc(); } } } public static bool TryGetRealEnemyBounds(EnemyAI enemy, out Bounds bounds) { //IL_0001: Unknown result type (might be due to invalid IL or missing references) //IL_0027: 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_0039: Unknown result type (might be due to invalid IL or missing references) bounds = default(Bounds); if ((Object)(object)enemy == (Object)null) { return false; } Renderer[] componentsInChildren = ((Component)enemy).gameObject.GetComponentsInChildren<Renderer>(); if (componentsInChildren == null) { return false; } bounds = componentsInChildren[0].bounds; for (int i = 1; i < componentsInChildren.Length; i++) { ((Bounds)(ref bounds)).Encapsulate(componentsInChildren[i].bounds); } return true; } private static GameObject? TrySpawnItemAtPosition(SpawnableItemWithRarity spawnableItemWithRarity, Vector3 position) { //IL_003a: 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) if (!IsHost) { LethalMon.Log("TrySpawnItemAtPosition: Not a valid item or not the host."); return null; } LethalMon.Log("Instantiating item " + ((Object)spawnableItemWithRarity.spawnableItem).name); GameObject val = Object.Instantiate<GameObject>(spawnableItemWithRarity.spawnableItem.spawnPrefab, position, Quaternion.identity, StartOfRound.Instance.elevatorTransform); NetworkObject component = val.GetComponent<NetworkObject>(); if (component != null) { component.Spawn(false); } return val; } public static GameObject? TrySpawnRandomItemAtPosition(Vector3 position, out SpawnableItemWithRarity spawnableItemWithRarity) { //IL_005e: Unknown result type (might be due to invalid IL or missing references) LethalMon.Log("Spawnable items: " + RoundManager.Instance.currentLevel.spawnableScrap.Count); spawnableItemWithRarity = RoundManager.Instance.currentLevel.spawnableScrap[Random.RandomRangeInt(0, RoundManager.Instance.currentLevel.spawnableScrap.Count)]; return TrySpawnItemAtPosition(spawnableItemWithRarity, position); } public static void SpawnPoofCloudAt(Vector3 position) { //IL_003b: Unknown result type (might be due to invalid IL or missing references) Item giftBoxItem = GiftBoxItem; if ((Object)(object)giftBoxItem != (Object)null && (Object)(object)giftBoxItem.spawnPrefab != (Object)null) { GiftBoxItem component = giftBoxItem.spawnPrefab.GetComponent<GiftBoxItem>(); ParticleSystem val = Object.Instantiate<ParticleSystem>(component.PoofParticle); ((Component)val).transform.position = position; val.Play(); } } public static List<Renderer> GetRenderers(GameObject? g) { List<Renderer> list = new List<Renderer>(); if ((Object)(object)g != (Object)null) { Renderer[] componentsInChildren = g.GetComponentsInChildren<Renderer>(); foreach (Renderer item in componentsInChildren) { list.Add(item); } } return list; } public static void ReplaceAllMaterialsWith(GameObject g, Func<Material, Material> materialReplacer) { List<Renderer> renderers = GetRenderers(g); foreach (Renderer item in renderers) { ReplaceAllMaterialsWith(item, materialReplacer); } } public static Material[] ReplaceAllMaterialsWith(Renderer mr, Func<Material, Material> materialReplacer) { List<Material> list = new List<Material>(); Material[] materials = mr.materials; foreach (Material arg in materials) { list.Add(materialReplacer(arg)); } Material[] materials2 = mr.materials; mr.materials = list.ToArray(); return materials2; } public static void LoadSeeThroughShader(AssetBundle assetBundle) { SeeThroughShader = assetBundle.LoadAsset<Shader>("Assets/SeeThrough/SeeThroughStencil.shader"); if ((Object)(object)SeeThroughShader == (Object)null) { LethalMon.Log("Unable to load seethrough shader!", LethalMon.LogType.Error); } } public static void LoadWireframeMaterial(AssetBundle assetBundle) { //IL_0022: Unknown result type (might be due to invalid IL or missing references) //IL_002c: Expected O, but got Unknown Shader val = assetBundle.LoadAsset<Shader>("Assets/SeeThrough/wireframe.shader"); if ((Object)(object)val == (Object)null) { LethalMon.Log("Unable to load wireframe shader!", LethalMon.LogType.Error); } else { WireframeMaterial = new Material(val); } } } public static class MyPluginInfo { public const string PLUGIN_GUID = "LethalMon"; public const string PLUGIN_NAME = "LethalMon"; public const string PLUGIN_VERSION = "1.0.0"; } } namespace LethalMon.Throw { public class FallCurve { internal static readonly Keyframe[] fallCurveKeyframes = (Keyframe[])(object)new Keyframe[2] { new Keyframe(0f, 0f, 2f, 2f), new Keyframe(1f, 1f, 0f, 0f) }; internal static readonly Keyframe[] verticalFallCurveKeyframes = (Keyframe[])(object)new Keyframe[5] { new Keyframe(0f, 0f, 0.116908506f, 0.116908506f, 0f, 0.27230743f), new Keyframe(0.49081117f, 1f, 4.1146584f, -1.81379f, 0.07234045f, 0.28319725f), new Keyframe(0.7587703f, 1f, 1.4123471f, -1.3678839f, 0.31997186f, 0.56917864f), new Keyframe(0.9393898f, 1f, 0.82654804f, -0.029021755f, 0.53747445f, 1f), new Keyframe(1f, 1f) }; internal static readonly Keyframe[] verticalFallCurveNoBounceKeyFrames = (Keyframe[])(object)new Keyframe[4] { new Keyframe(0f, 0f, 0.116908506f, 0.116908506f, 0f, 0.27230743f), new Keyframe(0.69081116f, 1f, 0.1146584f, 0.06098772f, 0.07234045f, 0.20768756f), new Keyframe(0.9393898f, 1f, 0.06394797f, -0.029021755f, 0.1980713f, 1f), new Keyframe(1f, 1f) }; internal static readonly AnimationCurve fallCurve = new AnimationCurve(fallCurveKeyframes); internal static readonly AnimationCurve verticalFallCurve = new AnimationCurve(verticalFallCurveKeyframes); internal static readonly AnimationCurve verticalFallCurveNoBounce = new AnimationCurve(verticalFallCurveNoBounceKeyFrames); } public abstract class ThrowableItem : GrabbableObject { public AnimationCurve itemFallCurve; public AnimationCurve itemVerticalFallCurve; public AnimationCurve itemVerticalFallCurveNoBounce; public RaycastHit itemHit; public Ray itemThrowRay; public PlayerControllerB playerThrownBy; public PlayerControllerB lastThrower; [ServerRpc(RequireOwnership = false)] public void ThrowServerRpc(NetworkObjectReference playerThrownByReference) { //IL_0024: Unknown result type (might be due to invalid IL or missing references) //IL_002e: Invalid comparison between Unknown and I4 //IL_00a7: Unknown result type (might be due to invalid IL or missing references) //IL_00b1: Invalid comparison between Unknown and I4 //IL_005f: Unknown result type (might be due to invalid IL or missing references) //IL_0068: Unknown result type (might be due to invalid IL or missing references) //IL_006d: Unknown result type (might be due to invalid IL or missing references) //IL_007d: 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_0097: Unknown result type (might be due to invalid IL or missing references) //IL_00d7: Unknown result type (might be due to invalid IL or missing references) NetworkManager networkManager = ((NetworkBehaviour)this).NetworkManager; if (networkManager != null && networkManager.IsListening) { if ((int)((NetworkBehaviour)this).__rpc_exec_stage != 1 && (networkManager.IsClient || networkManager.IsHost)) { ServerRpcParams val = default(ServerRpcParams); FastBufferWriter val2 = ((NetworkBehaviour)this).__beginSendServerRpc(2923164452u, val, (RpcDelivery)0); ((FastBufferWriter)(ref val2)).WriteValueSafe<NetworkObjectReference>(ref playerThrownByReference, default(ForNetworkSerializable)); ((NetworkBehaviour)this).__endSendServerRpc(ref val2, 2923164452u, val, (RpcDelivery)0); } if ((int)((NetworkBehaviour)this).__rpc_exec_stage == 1 && (networkManager.IsServer || networkManager.IsHost)) { ThrowClientRpc(playerThrownByReference); } } } [ClientRpc] public void ThrowClientRpc(NetworkObjectReference playerThrownByReference) { //IL_0024: Unknown result type (might be due to invalid IL or missing references) //IL_002e: Invalid comparison between Unknown and I4 //IL_00a7: Unknown result type (might be due to invalid IL or missing references) //IL_00b1: Invalid comparison between Unknown and I4 //IL_005f: Unknown result type (might be due to invalid IL or missing references) //IL_0068: Unknown result type (might be due to invalid IL or missing references) //IL_006d: Unknown result type (might be due to invalid IL or missing references) //IL_007d: 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_0097: Unknown result type (might be due to invalid IL or missing references) NetworkManager networkManager = ((NetworkBehaviour)this).NetworkManager; if (networkManager == null || !networkManager.IsListening) { return; } if ((int)((NetworkBehaviour)this).__rpc_exec_stage != 2 && (networkManager.IsServer || networkManager.IsHost)) { ClientRpcParams val = default(ClientRpcParams); FastBufferWriter val2 = ((NetworkBehaviour)this).__beginSendClientRpc(3841692620u, val, (RpcDelivery)0); ((FastBufferWriter)(ref val2)).WriteValueSafe<NetworkObjectReference>(ref playerThrownByReference, default(ForNetworkSerializable)); ((NetworkBehaviour)this).__endSendClientRpc(ref val2, 3841692620u, val, (RpcDelivery)0); } if ((int)((NetworkBehaviour)this).__rpc_exec_stage == 2 && (networkManager.IsClient || networkManager.IsHost)) { LethalMon.Log("SendThrowRpc server rpc received"); NetworkObject val3 = default(NetworkObject); PlayerControllerB val4 = default(PlayerControllerB); if (!((NetworkObjectReference)(ref playerThrownByReference)).TryGet(ref val3, (NetworkManager)null)) { LethalMon.Log(((Object)((Component)this).gameObject).name + ": Failed to get player component (SendThrowRpc)", LethalMon.LogType.Error); } else if (((Component)val3).TryGetComponent<PlayerControllerB>(ref val4)) { playerThrownBy = val4; lastThrower = playerThrownBy; } } } public override void ItemActivate(bool used, bool buttonDown = true) { //IL_0031: Unknown result type (might be due to invalid IL or missing references) //IL_0048: Unknown result type (might be due to invalid IL or missing references) ((GrabbableObject)this).ItemActivate(used, buttonDown); if (((NetworkBehaviour)this).IsOwner) { playerThrownBy = base.playerHeldBy; lastThrower = playerThrownBy; base.playerHeldBy.DiscardHeldObject(true, (NetworkObject)null, GetItemThrowDestination(), true); ThrowServerRpc(NetworkObjectReference.op_Implicit(((Component)playerThrownBy).GetComponent<NetworkObject>())); } } public override void EquipItem() { ((GrabbableObject)this).EnableItemMeshes(true); base.isPocketed = false; } public abstract void TouchGround(); public override void FallWithCurve() { //IL_0001: Unknown result type (might be due to invalid IL or missing references) //IL_0007: Unknown result type (might be due to invalid IL or missing references) //IL_000c: Unknown result type (might be due to invalid IL or missing references) //IL_0011: 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_0041: Unknown result type (might be due to invalid IL or missing references) //IL_005b: Unknown result type (might be due to invalid IL or missing references) //IL_006d: 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_0084: Unknown result type (might be due to invalid IL or missing references) //IL_0099: Unknown result type (might be due to invalid IL or missing references) //IL_013f: Unknown result type (might be due to invalid IL or missing references) //IL_015a: Unknown result type (might be due to invalid IL or missing references) //IL_0164: Unknown result type (might be due to invalid IL or missing references) //IL_016f: Unknown result type (might be due to invalid IL or missing references) //IL_018a: Unknown result type (might be due to invalid IL or missing references) //IL_0194: Unknown result type (might be due to invalid IL or missing references) //IL_01a9: Unknown result type (might be due to invalid IL or missing references) //IL_00ba: Unknown result type (might be due to invalid IL or missing references) //IL_00d5: Unknown result type (might be due to invalid IL or missing references) //IL_00df: Unknown result type (might be due to invalid IL or missing references) //IL_00ea: 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_010f: Unknown result type (might be due to invalid IL or missing references) //IL_0124: Unknown result type (might be due to invalid IL or missing references) Vector3 val = base.startFallingPosition - base.targetFloorPosition; float magnitude = ((Vector3)(ref val)).magnitude; ((Component)this).transform.rotation = Quaternion.Lerp(((Component)this).transform.rotation, Quaternion.Euler(base.itemProperties.restingRotation.x, ((Component)this).transform.eulerAngles.y, base.itemProperties.restingRotation.z), 14f * Time.deltaTime / magnitude); ((Component)this).transform.localPosition = Vector3.Lerp(base.startFallingPosition, base.targetFloorPosition, FallCurve.fallCurve.Evaluate(base.fallTime)); if (magnitude > 5f) { ((Component)this).transform.localPosition = Vector3.Lerp(new Vector3(((Component)this).transform.localPosition.x, base.startFallingPosition.y, ((Component)this).transform.localPosition.z), new Vector3(((Component)this).transform.localPosition.x, base.targetFloorPosition.y, ((Component)this).transform.localPosition.z), FallCurve.verticalFallCurveNoBounce.Evaluate(base.fallTime)); } else { ((Component)this).transform.localPosition = Vector3.Lerp(new Vector3(((Component)this).transform.localPosition.x, base.startFallingPosition.y, ((Component)this).transform.localPosition.z), new Vector3(((Component)this).transform.localPosition.x, base.targetFloorPosition.y, ((Component)this).transform.localPosition.z), FallCurve.verticalFallCurve.Evaluate(base.fallTime)); } base.fallTime += Mathf.Abs(Time.deltaTime * 12f / magnitude); if (base.fallTime > 1f) { TouchGround(); playerThrownBy = null; } } public override void Update() { ((GrabbableObject)this).Update(); } public Vector3 GetItemThrowDestination() { //IL_0006: Unknown result type (might be due to invalid IL or missing references) //IL_000b: Unknown result type (might be due to invalid IL or missing references) //IL_001d: Unknown result type (might be due to invalid IL or missing references) //IL_0032: Unknown result type (might be due to invalid IL or missing references) //IL_0037: Unknown result type (might be due to invalid IL or missing references) //IL_003c: Unknown result type (might be due to invalid IL or missing references) //IL_0042: Unknown result type (might be due to invalid IL or missing references) //IL_0088: Unknown result type (might be due to invalid IL or missing references) //IL_0076: Unknown result type (might be due to invalid IL or missing references) //IL_008d: Unknown result type (might be due to invalid IL or missing references) //IL_008f: 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_0095: 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_00a0: 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_00c3: Unknown result type (might be due to invalid IL or missing references) //IL_00c8: Unknown result type (might be due to invalid IL or missing references) //IL_00de: Unknown result type (might be due to invalid IL or missing references) //IL_00e3: Unknown result type (might be due to invalid IL or missing references) Vector3 position = ((Component)this).transform.position; itemThrowRay = new Ray(((Component)base.playerHeldBy.gameplayCamera).transform.position, ((Component)base.playerHeldBy.gameplayCamera).transform.forward); position = ((!Physics.Raycast(itemThrowRay, ref itemHit, 12f, 268437761, (QueryTriggerInteraction)1)) ? ((Ray)(ref itemThrowRay)).GetPoint(10f) : ((Ray)(ref itemThrowRay)).GetPoint(((RaycastHit)(ref itemHit)).distance - 0.05f)); itemThrowRay = new Ray(position, Vector3.down); if (Physics.Raycast(itemThrowRay, ref itemHit, 30f, 268437761, (QueryTriggerInteraction)1)) { return ((RaycastHit)(ref itemHit)).point + Vector3.up * (base.itemProperties.verticalOffset + 0.05f); } return ((Ray)(ref itemThrowRay)).GetPoint(30f); } protected override void __initializeVariables() { ((GrabbableObject)this).__initializeVariables(); } [RuntimeInitializeOnLoadMethod] internal static void InitializeRPCS_ThrowableItem() { //IL_0011: Unknown result type (might be due to invalid IL or missing references) //IL_001b: Expected O, but got Unknown //IL_002c: Unknown result type (might be due to invalid IL or missing references) //IL_0036: Expected O, but got Unknown NetworkManager.__rpc_func_table.Add(2923164452u, new RpcReceiveHandler(__rpc_handler_2923164452)); NetworkManager.__rpc_func_table.Add(3841692620u, new RpcReceiveHandler(__rpc_handler_3841692620)); } private static void __rpc_handler_2923164452(NetworkBehaviour target, FastBufferReader reader, __RpcParams rpcParams) { //IL_002f: 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_0044: Unknown result type (might be due to invalid IL or missing references) //IL_004f: Unknown result type (might be due to invalid IL or missing references) //IL_005e: Unknown result type (might be due to invalid IL or missing references) NetworkManager networkManager = target.NetworkManager; if (networkManager != null && networkManager.IsListening) { NetworkObjectReference playerThrownByReference = default(NetworkObjectReference); ((FastBufferReader)(ref reader)).ReadValueSafe<NetworkObjectReference>(ref playerThrownByReference, default(ForNetworkSerializable)); target.__rpc_exec_stage = (__RpcExecStage)1; ((ThrowableItem)(object)target).ThrowServerRpc(playerThrownByReference); target.__rpc_exec_stage = (__RpcExecStage)0; } } private static void __rpc_handler_3841692620(NetworkBehaviour target, FastBufferReader reader, __RpcParams rpcParams) { //IL_002f: 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_0044: Unknown result type (might be due to invalid IL or missing references) //IL_004f: Unknown result type (might be due to invalid IL or missing references) //IL_005e: Unknown result type (might be due to invalid IL or missing references) NetworkManager networkManager = target.NetworkManager; if (networkManager != null && networkManager.IsListening) { NetworkObjectReference playerThrownByReference = default(NetworkObjectReference); ((FastBufferReader)(ref reader)).ReadValueSafe<NetworkObjectReference>(ref playerThrownByReference, default(ForNetworkSerializable)); target.__rpc_exec_stage = (__RpcExecStage)2; ((ThrowableItem)(object)target).ThrowClientRpc(playerThrownByReference); target.__rpc_exec_stage = (__RpcExecStage)0; } } [MethodImpl(MethodImplOptions.NoInlining)] protected internal override string __getTypeName() { return "ThrowableItem"; } } } namespace LethalMon.Patches { public class BushWolfEnemyPatch { [HarmonyPatch(typeof(BushWolfEnemy), "Start")] [HarmonyPostfix] public static void OnStartPostfix(BushWolfEnemy __instance) { KidnapperFoxTamedBehaviour component = ((Component)__instance).GetComponent<KidnapperFoxTamedBehaviour>(); if ((Object)(object)component != (Object)null && (Object)(object)component.ownerPlayer != (Object)null) { ((EnemyAI)__instance).inSpecialAnimation = false; ((EnemyAI)__instance).EnableEnemyMesh(true, false); ((Behaviour)((EnemyAI)__instance).agent).enabled = true; ((EnemyAI)__instance).agent.speed = 5f; } } } [HarmonyPatch] internal class DebugPatches : NetworkBehaviour { protected override void __initializeVariables() { ((NetworkBehaviour)this).__initializeVariables(); } [MethodImpl(MethodImplOptions.NoInlining)] protected internal override string __getTypeName() { return "DebugPatches"; } } public class EnemyAIPatch { [HarmonyPatch(typeof(EnemyAI), "OnDestroy")] [HarmonyPrefix] private static void OnDestroyPreFix(EnemyAI __instance) { TamedEnemyBehaviour component = ((Component)__instance).GetComponent<TamedEnemyBehaviour>(); if ((Object)(object)component != (Object)null) { LethalMon.Log("Destroying TamedEnemyBehaviour component"); Object.Destroy((Object)(object)component); } else { LethalMon.Log("No TamedEnemyBehaviour component found before EnemyAI OnDestroy", LethalMon.LogType.Warning); } } [HarmonyPatch(typeof(EnemyAI), "SwitchToBehaviourStateOnLocalClient")] [HarmonyPrefix] private static void SwitchToBehaviourStateOnLocalClientPrefix(EnemyAI __instance) { TamedEnemyBehaviour component = ((Component)__instance).GetComponent<TamedEnemyBehaviour>(); if ((Object)(object)component != (Object)null && __instance.currentBehaviourStateIndex > component.LastDefaultBehaviourIndex) { if (__instance.currentBehaviourStateIndex <= component.LastDefaultBehaviourIndex + TamedEnemyBehaviour.TamedBehaviourCount) { component.LeaveTamingBehaviour((TamedEnemyBehaviour.TamingBehaviour)(__instance.currentBehaviourStateIndex - component.LastDefaultBehaviourIndex)); } else { component.LeaveCustomBehaviour(__instance.currentBehaviourStateIndex - TamedEnemyBehaviour.TamedBehaviourCount - component.LastDefaultBehaviourIndex); } } } [HarmonyPatch(typeof(EnemyAI), "SwitchToBehaviourStateOnLocalClient")] [HarmonyPostfix] private static void SwitchToBehaviourStateOnLocalClientPostfix(EnemyAI __instance, int stateIndex) { TamedEnemyBehaviour component = ((Component)__instance).GetComponent<TamedEnemyBehaviour>(); if ((Object)(object)component != (Object)null) { if (stateIndex > component.LastDefaultBehaviourIndex) { if (stateIndex <= component.LastDefaultBehaviourIndex + TamedEnemyBehaviour.TamedBehaviourCount) { component.InitTamingBehaviour((TamedEnemyBehaviour.TamingBehaviour)(stateIndex - component.LastDefaultBehaviourIndex)); } else { component.InitCustomBehaviour(stateIndex - TamedEnemyBehaviour.TamedBehaviourCount - component.LastDefaultBehaviourIndex); } } if ((Object)(object)component.ownerPlayer == (Object)(object)Utils.CurrentPlayer) { HUDManagerPatch.UpdateTamedMonsterAction(component.GetCurrentStateDescription()); } } else { LethalMon.Log("No TamedEnemyBehaviour component found after EnemyAI SwitchToBehaviourStateOnLocalClient", LethalMon.LogType.Warning); } } [HarmonyPatch(typeof(EnemyAI), "HitEnemy")] [HarmonyPrefix] private static bool HitEnemyPrefix(EnemyAI __instance, int force = -1, PlayerControllerB playerWhoHit = null, bool playHitSFX = false, int hitID = -1) { TamedEnemyBehaviour component = ((Component)__instance).GetComponent<TamedEnemyBehaviour>(); if (!((Object)(object)component == (Object)null)) { return (Object)(object)component.ownerPlayer == (Object)null; } return true; } [HarmonyPatch(typeof(EnemyAI), "KillEnemy")] [HarmonyPrefix] private static bool KillEnemyPrefix(EnemyAI __instance, bool destroy = false) { TamedEnemyBehaviour component = ((Component)__instance).GetComponent<TamedEnemyBehaviour>(); if (!((Object)(object)component == (Object)null)) { return (Object)(object)component.ownerPlayer == (Object)null; } return true; } [HarmonyPatch(typeof(EnemyAI), "KillEnemyClientRpc")] [HarmonyPrefix] private static bool KillEnemyClientRpcPrefix(EnemyAI __instance, bool destroy) { TamedEnemyBehaviour component = ((Component)__instance).GetComponent<TamedEnemyBehaviour>(); if (!((Object)(object)component == (Object)null)) { return (Object)(object)component.ownerPlayer == (Object)null; } return true; } [HarmonyPatch(typeof(EnemyAI), "KillEnemyServerRpc")] [HarmonyPrefix] private static bool KillEnemyServerRpcPrefix(EnemyAI __instance, bool destroy) { TamedEnemyBehaviour component = ((Component)__instance).GetComponent<TamedEnemyBehaviour>(); if (!((Object)(object)component == (Object)null)) { return (Object)(object)component.ownerPlayer == (Object)null; } return true; } [HarmonyPatch(typeof(EnemyAI), "KillEnemyOnOwnerClient")] [HarmonyPrefix] private static bool KillEnemyOnOwnerClientPrefix(EnemyAI __instance, bool overrideDestroy = false) { TamedEnemyBehaviour component = ((Component)__instance).GetComponent<TamedEnemyBehaviour>(); if (!((Object)(object)component == (Object)null)) { return (Object)(object)component.ownerPlayer == (Object)null; } return true; } } public class FlowermanAIPatch { [HarmonyPatch(typeof(FlowermanAI), "HitEnemy")] [HarmonyPrefix] private static bool HitEnemyPrefix(FlowermanAI __instance, int force = -1, PlayerControllerB playerWhoHit = null, bool playHitSFX = false, int hitID = -1) { TamedEnemyBehaviour component = ((Component)__instance).GetComponent<TamedEnemyBehaviour>(); if (!((Object)(object)component == (Object)null)) { return (Object)(object)component.ownerPlayer == (Object)null; } return true; } } public class HUDManagerPatch { private static HUDElement monsterHudElement; private static Image monsterIcon; private static TextMeshProUGUI monsterName; private static TextMeshProUGUI pressKeyTip; private static TextMeshProUGUI monsterAction; private static Image cooldownCircle1; private static TextMeshProUGUI cooldownTime1; private static TextMeshProUGUI cooldownName1; private static Image cooldownCircle2; private static TextMeshProUGUI cooldownTime2; private static TextMeshProUGUI cooldownName2; public static void UpdatePressKeyTip() { if ((Object)(object)pressKeyTip != (Object)null) { ((TMP_Text)pressKeyTip).text = "[" + InputActionRebindingExtensions.GetBindingDisplayString(ModConfig.Instance.RetrieveBallKey, (DisplayStringOptions)0, (string)null) + "]\nto retrieve"; } } public static void ChangeToTamedBehaviour(TamedEnemyBehaviour behaviour) { string name = ((Object)behaviour.Enemy.enemyType).name; monsterIcon.sprite = (Sprite)(LethalMon.monstersSprites.TryGetValue(name.ToLower(), out Sprite value) ? ((object)value) : ((object)LethalMon.monstersSprites["unknown"])); ((TMP_Text)monsterName).text = Data.CatchableMonsters[name].DisplayName; CooldownNetworkBehaviour[] components = ((Component)behaviour).GetComponents<CooldownNetworkBehaviour>(); if (components.Length >= 1) { ((Component)cooldownCircle1).gameObject.SetActive(true); ((Component)cooldownTime1).gameObject.SetActive(true); ((Component)cooldownName1).gameObject.SetActive(true); components[0].BindToHUD(cooldownCircle1, cooldownTime1, cooldownName1); } else { ((Component)cooldownCircle1).gameObject.SetActive(false); ((Component)cooldownTime1).gameObject.SetActive(false); ((Component)cooldownName1).gameObject.SetActive(false); } if (components.Length >= 2) { ((Component)cooldownCircle2).gameObject.SetActive(true); ((Component)cooldownTime2).gameObject.SetActive(true); ((Component)cooldownName2).gameObject.SetActive(true); components[1].BindToHUD(cooldownCircle2, cooldownTime2, cooldownName2); } else { ((Component)cooldownCircle2).gameObject.SetActive(false); ((Component)cooldownTime2).gameObject.SetActive(false); ((Component)cooldownName2).gameObject.SetActive(false); } } public static void EnableHUD(bool enable) { ((Component)monsterHudElement.canvasGroup).gameObject.SetActive(enable); } public static void UpdateTamedMonsterAction(string action) { ((TMP_Text)monsterAction).text = action; } [HarmonyPostfix] [HarmonyPatch(typeof(HUDManager), "Awake")] private static void AwakePostfix(HUDManager __instance) { //IL_0099: Unknown result type (might be due to invalid IL or missing references) //IL_009e: Unknown result type (might be due to invalid IL or missing references) //IL_00aa: Unknown result type (might be due to invalid IL or missing references) //IL_00b6: Unknown result type (might be due to invalid IL or missing references) //IL_00c7: Expected O, but got Unknown //IL_02e3: Unknown result type (might be due to invalid IL or missing references) //IL_02fc: Unknown result type (might be due to invalid IL or missing references) //IL_0301: Unknown result type (might be due to invalid IL or missing references) //IL_030f: Unknown result type (might be due to invalid IL or missing references) //IL_0314: Unknown result type (might be due to invalid IL or missing references) FieldInfo field = typeof(HUDManager).GetField("HUDElements", BindingFlags.Instance | BindingFlags.NonPublic); if (field == null) { LethalMon.Log("Unable to instantiate HUD, HUDElements array not found", LethalMon.LogType.Error); return; } HUDElement[] array = (HUDElement[])field.GetValue(__instance); if (array.Length == 0) { LethalMon.Log("NO HUD element found (probably because of another mod), cannot instantiate LethalMon HUD", LethalMon.LogType.Error); return; } HUDElement val = ((IEnumerable<HUDElement>)array).FirstOrDefault((Func<HUDElement, bool>)((HUDElement e) => ((Component)e.canvasGroup).GetComponents<Component>().Any((Component c) => ((Object)c).name == "TopRightCorner"))); if (val == null) { LethalMon.Log("Top left corner HUDElement not found, cannot instantiate LethalMon HUD", LethalMon.LogType.Error); return; } GameObject val2 = Object.Instantiate<GameObject>(LethalMon.hudPrefab, ((Component)val.canvasGroup).transform.parent); monsterHudElement = new HUDElement { canvasGroup = val2.GetComponent<CanvasGroup>(), targetAlpha = val.targetAlpha, fadeCoroutine = val.fadeCoroutine }; Component[] componentsInChildren = val2.GetComponentsInChildren<Component>(); monsterIcon = componentsInChildren.First((Component c) => ((Object)c).name == "Icon").GetComponent<Image>(); monsterName = componentsInChildren.First((Component c) => ((Object)c).name == "Name").GetComponent<TextMeshProUGUI>(); pressKeyTip = componentsInChildren.First((Component c) => ((Object)c).name == "PressKeyTip").GetComponent<TextMeshProUGUI>(); monsterAction = componentsInChildren.First((Component c) => ((Object)c).name == "Action").GetComponent<TextMeshProUGUI>(); cooldownCircle1 = componentsInChildren.First((Component c) => ((Object)c).name == "CooldownCircle1").GetComponent<Image>(); cooldownName1 = componentsInChildren.First((Component c) => ((Object)c).name == "CooldownName1").GetComponent<TextMeshProUGUI>(); cooldownTime1 = componentsInChildren.First((Component c) => ((Object)c).name == "CooldownTime1").GetComponent<TextMeshProUGUI>(); cooldownCircle2 = componentsInChildren.First((Component c) => ((Object)c).name == "CooldownCircle2").GetComponent<Image>(); cooldownName2 = componentsInChildren.First((Component c) => ((Object)c).name == "CooldownName2").GetComponent<TextMeshProUGUI>(); cooldownTime2 = componentsInChildren.First((Component c) => ((Object)c).name == "CooldownTime2").GetComponent<TextMeshProUGUI>(); UpdatePressKeyTip(); EnableHUD(enable: false); field.SetValue(__instance, new List<HUDElement>(array) { monsterHudElement }.ToArray()); Transform transform = ((Component)val.canvasGroup).transform; Vector3 localPosition = transform.localPosition; Rect rect = ((Component)monsterHudElement.canvasGroup).GetComponent<RectTransform>().rect; transform.localPosition = localPosition - new Vector3(0f, ((Rect)(ref rect)).height, 0f); LethalMon.Log("HUD initialized"); } } internal class MaskedPlayerEnemyPatch { internal static Dictionary<int, int> lastColliderIDs = new Dictionary<int, int>(); [HarmonyPrefix] [HarmonyPatch(typeof(MaskedPlayerEnemy), "OnCollideWithPlayer")] public static void OnCollideWithPlayerPrefix(MaskedPlayerEnemy __instance, Collider other) { if (lastColliderIDs.GetValueOrDefault(((Object)__instance).GetInstanceID(), -1) == ((Object)other).GetInstanceID()) { return; } lastColliderIDs[((Object)__instance).GetInstanceID()] = ((Object)other).GetInstanceID(); PlayerControllerB component = ((Component)other).gameObject.GetComponent<PlayerControllerB>(); MaskedTamedBehaviour maskedTamedBehaviour = default(MaskedTamedBehaviour); if ((Object)(object)component == (Object)null || !((Component)__instance).TryGetComponent<MaskedTamedBehaviour>(ref maskedTamedBehaviour) || (Object)(object)maskedTamedBehaviour.targetPlayer == (Object)null) { return; } if (maskedTamedBehaviour.CurrentCustomBehaviour.GetValueOrDefault(-1) == 2) { LethalMon.Log("Ghost hitting player " + component.playerClientId); maskedTamedBehaviour.Masked.startingKillAnimationLocalClient = true; maskedTamedBehaviour.GhostHitPlayerServerRpc(component.playerClientId); } else if (maskedTamedBehaviour.escapeFromBallEventRunning && (Object)(object)component == (Object)(object)maskedTamedBehaviour.targetPlayer) { LethalMon.Log("Player " + component.playerClientId + " ran into the masked that does the escape event."); maskedTamedBehaviour.CleanUp(); maskedTamedBehaviour.Masked.maskEyesGlowLight.intensity = 0.6f; if ((Object)(object)((EnemyAI)maskedTamedBehaviour.Masked).agent != (Object)null) { ((Behaviour)((EnemyAI)maskedTamedBehaviour.Masked).agent).enabled = true; } ((Behaviour)maskedTamedBehaviour.Masked).enabled = true; maskedTamedBehaviour.EscapeFromBallEventEndedServerRpc(); if (Time.realtimeSinceStartup - maskedTamedBehaviour.Masked.timeAtLastUsingEntrance < 1.75f) { maskedTamedBehaviour.Masked.timeAtLastUsingEntrance = Time.realtimeSinceStartup - 2f; } } } } public class MouthDogPatch { [HarmonyPatch(typeof(MouthDogAI), "ReactToOtherDogHowl")] [HarmonyPrefix] private static bool ReactToOtherDogHowlPreFix(MouthDogAI __instance, Vector3 howlPosition) { return !((Object)(object)((Component)__instance).GetComponentInParent<MouthDogTamedBehaviour>()?.ownerPlayer != (Object)null); } } public class PlayerControllerBPatch { [CompilerGenerated] private static class <>O { public static RpcReceiveHandler <0>____rpc_handler_346187524u; public static Action<CallbackContext> <1>__RetrieveBallKeyPressed; public static Action<CallbackContext> <2>__ActionKey1Pressed; } private static bool lastTestPressed = false; private static int currentTestEnemyTypeIndex = 0; private static string[] testEnemyTypes = new List<string>(Data.CatchableMonsters.Keys).ToArray(); private static bool SentBallScanTip = false; internal static void InitializeRPCS() { //IL_001a: Unknown result type (might be due to invalid IL or missing references) //IL_001f: Unknown result type (might be due to invalid IL or missing references) //IL_0025: Expected O, but got Unknown Dictionary<uint, RpcReceiveHandler> _rpc_func_table = NetworkManager.__rpc_func_table; object obj = <>O.<0>____rpc_handler_346187524u; if (obj == null) { RpcReceiveHandler val = __rpc_handler_346187524u; <>O.<0>____rpc_handler_346187524u = val; obj = (object)val; } _rpc_func_table.Add(346187524u, (RpcReceiveHandler)obj); } public static void SendPetRetrievePacket(PlayerControllerB player) { //IL_0002: Unknown result type (might be due to invalid IL or missing references) //IL_0030: Unknown result type (might be due to invalid IL or missing references) //IL_0045: 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_0051: 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_0072: Unknown result type (might be due to invalid IL or missing references) //IL_0088: Unknown result type (might be due to invalid IL or missing references) ServerRpcParams val = default(ServerRpcParams); FastBufferWriter val2 = (FastBufferWriter)((object)player).GetType().GetMethod("__beginSendServerRpc", BindingFlags.Instance | BindingFlags.NonPublic).Invoke(player, new object[3] { 346187524u, val, (object)(RpcDelivery)0 }); NetworkObjectReference val3 = NetworkObjectReference.op_Implicit(((Component)player).GetComponent<NetworkObject>()); ((object)player).GetType().GetMethod("__endSendServerRpc", BindingFlags.Instance | BindingFlags.NonPublic).Invoke(player, new object[4] { val2, 346187524u, val, (object)(RpcDelivery)0 }); LethalMon.Log("Send pet retrieve server rpc send finished"); } private static void __rpc_handler_346187524u(NetworkBehaviour target, FastBufferReader reader, __RpcParams rpcParams) { //IL_0033: Unknown result type (might be due to invalid IL or missing references) //IL_0039: Expected O, but got Unknown NetworkManager networkManager = target.NetworkManager; if ((Object)(object)networkManager != (Object)null && networkManager.IsListening) { LethalMon.Log("Execute RPC handler " + MethodBase.GetCurrentMethod().Name); PlayerControllerB val = (PlayerControllerB)target; TamedEnemyBehaviour playerPet = Utils.GetPlayerPet(val); if ((Object)(object)playerPet != (Object)null) { PetRetrieve(val, playerPet); } else { LethalMon.Log("No tamed enemy found for " + ((object)val)?.ToString() + " but they sent a retrieve ball RPC"); } } } private static void PetRetrieve(PlayerControllerB player, TamedEnemyBehaviour tamedEnemyBehaviour) { //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_0008: Unknown result type (might be due to invalid IL or missing references) //IL_0023: Unknown result type (might be due to invalid IL or missing references) //IL_0028: 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) Vector3 positionInFrontOfPlayerEyes = Utils.GetPositionInFrontOfPlayerEyes(player); PokeballItem pokeballItem = tamedEnemyBehaviour.RetrieveInBall(positionInFrontOfPlayerEyes); if (!((Object)(object)pokeballItem == (Object)null)) { Bounds bounds = StartOfRound.Instance.shipBounds.bounds; bool flag = ((Bounds)(ref bounds)).Contains(positionInFrontOfPlayerEyes); player.SetItemInElevator(flag, flag, (GrabbableObject)(object)pokeballItem); ((Component)pokeballItem).transform.SetParent(StartOfRound.Instance.elevatorTransform, true); } } [HarmonyPatch(typeof(PlayerControllerB), "ConnectClientToPlayerObject")] [HarmonyPostfix] public static void ConnectPlayerPostfix(PlayerControllerB __instance) { ModConfig.Instance.RetrieveBallKey.performed += RetrieveBallKeyPressed; ModConfig.Instance.ActionKey1.performed += ActionKey1Pressed; } [HarmonyPatch(typeof(GameNetworkManager), "Disconnect")] [HarmonyPrefix] public static void DisconnectPlayerPrefix() { ModConfig.Instance.RetrieveBallKey.performed -= RetrieveBallKeyPressed; ModConfig.Instance.ActionKey1.performed -= ActionKey1Pressed; } internal static void RetrieveBallKeyPressed(CallbackContext dashContext) { if (Utils.IsHost) { LethalMon.Log("RetrieveBallKeyPressed"); TamedEnemyBehaviour playerPet = Utils.GetPlayerPet(Utils.CurrentPlayer); if ((Object)(object)playerPet != (Object)null) { PetRetrieve(Utils.CurrentPlayer, playerPet); } } else { SendPetRetrievePacket(Utils.CurrentPlayer); } } internal static void ActionKey1Pressed(CallbackContext dashContext) { LethalMon.Log("ActionKey1Pressed"); TamedEnemyBehaviour playerPet = Utils.GetPlayerPet(Utils.CurrentPlayer); if ((Object)(object)playerPet != (Object)null) { playerPet.ActionKey1Pressed(); } } [HarmonyPatch(typeof(PlayerControllerB), "Update")] [HarmonyPostfix] private static void UpdatePostfix(PlayerControllerB __instance) { if (__instance == null || !__instance.isPlayerControlled || !((NetworkBehaviour)__instance).IsOwner || !((Object)(object)StartOfRound.Instance.testRoom != (Object)null) || (!((NetworkBehaviour)__instance).IsHost && !((NetworkBehaviour)__instance).IsServer)) { return; } bool flag = InputControlExtensions.IsPressed((InputControl)(object)Keyboard.current[(Key)29], 0f); if (flag && !lastTestPressed) { lastTestPressed = true; GrabbableObject val = __instance.ItemSlots[__instance.currentItemSlot]; if (!((Object)(object)val != (Object)null)) { return; } PokeballItem component = ((Component)val).GetComponent<PokeballItem>(); if ((Object)(object)component != (Object)null) { EnemyType val2 = Resources.FindObjectsOfTypeAll<EnemyType>().First((EnemyType enemyType) => ((Object)enemyType).name == testEnemyTypes[currentTestEnemyTypeIndex]); component.SetCaughtEnemyServerRpc(((Object)val2).name); HUDManager.Instance.AddTextMessageClientRpc("Caught enemy: " + ((Object)val2).name); currentTestEnemyTypeIndex++; if (currentTestEnemyTypeIndex >= testEnemyTypes.Length) { currentTestEnemyTypeIndex = 0; } } } else if (!flag) { lastTestPressed = false; } } [HarmonyPatch(typeof(PlayerControllerB), "TeleportPlayer")] [HarmonyPostfix] private static void TeleportPlayer(PlayerControllerB __instance, Vector3 pos) { //IL_001d: 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_0053: Unknown result type (might be due to invalid IL or missing references) //IL_0070: Unknown result type (might be due to invalid IL or missing references) //IL_0071: Unknown result type (might be due to invalid IL or missing references) TamedEnemyBehaviour playerPet = Utils.GetPlayerPet(__instance); if ((Object)(object)playerPet != (Object)null && playerPet.CanBeTeleported()) { Vector3 val = pos; LethalMon.Log("Teleport tamed enemy to " + ((object)(Vector3)(ref val)).ToString()); ((Behaviour)playerPet.Enemy.agent).enabled = false; ((Component)playerPet.Enemy).transform.position = pos; ((Behaviour)playerPet.Enemy.agent).enabled = true; playerPet.Enemy.serverPosition = pos; playerPet.Enemy.SetEnemyOutside(!__instance.isInsideFactory); } } [HarmonyPatch(typeof(PlayerControllerB), "KillPlayerServerRpc")] [HarmonyPostfix] private static void KillPlayerServerRpcPostfix(PlayerControllerB __instance) { //IL_0036: Unknown result type (might be due to invalid IL or missing references) TamedEnemyBehaviour playerPet = Utils.GetPlayerPet(__instance); if ((Object)(object)playerPet != (Object)null && Utils.IsHost && !playerPet.hasBeenRetrieved) { LethalMon.Log("Owner is dead, go back to the ball"); playerPet.RetrieveInBall(((Component)playerPet.Enemy).transform.position); } } [HarmonyPatch(typeof(PlayerControllerB), "DamagePlayer")] [HarmonyPostfix] private static void DamagePlayerPostfix(PlayerControllerB __instance, int damageNumber, bool hasDamageSFX, bool callRPC, CauseOfDeath causeOfDeath, int deathAnimation, bool fallDamage, Vector3 force) { TamedEnemyBehaviour playerPet = Utils.GetPlayerPet(__instance); if ((Object)(object)playerPet != (Object)null && playerPet.CanDefend) { EnemyAI mostProbableAttackerEnemy = Utils.GetMostProbableAttackerEnemy(__instance, new StackTrace()); TamedEnemyBehaviour componentInParent = ((Component)mostProbableAttackerEnemy).GetComponentInParent<TamedEnemyBehaviour>(); if ((Object)(object)mostProbableAttackerEnemy != (Object)null && (Object)(object)mostProbableAttackerEnemy != (Object)(object)playerPet.Enemy && ((Object)(object)componentInParent == (Object)null || (Object)(object)componentInParent.ownerPlayer == (Object)null)) { playerPet.targetEnemy = mostProbableAttackerEnemy; playerPet.SwitchToTamingBehaviour(TamedEnemyBehaviour.TamingBehaviour.TamedDefending); } } } [HarmonyPatch(typeof(PlayerControllerB), "DamagePlayerFromOtherClientServerRpc")] [HarmonyPostfix] private static void DamagePlayerFromOtherClientServerRpcPostFix(PlayerControllerB __instance, Vector3 hitDirection, int playerWhoHit) { //IL_0070: 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) if ((int)__instance.playerClientId == playerWhoHit) { return; } TamedEnemyBehaviour playerPet = Utils.GetPlayerPet(__instance); if ((Object)(object)playerPet != (Object)null && (((NetworkBehaviour)__instance).IsServer || ((NetworkBehaviour)__instance).IsHost) && playerPet.CanDefend) { PlayerControllerB val = StartOfRound.Instance.allPlayerScripts[playerWhoHit]; LethalMon.Log("Player " + val.playerUsername + " hit " + __instance.playerUsername); if ((Object)(object)__instance != (Object)(object)val && Vector3.Distance(((Component)__instance).transform.position, ((Component)val).transform.position) < 5f) { playerPet.targetPlayer = val; playerPet.SwitchToTamingBehaviour(TamedEnemyBehaviour.TamingBehaviour.TamedDefending); } } } [HarmonyPatch(typeof(PlayerControllerB), "SwitchToItemSlot")] [HarmonyPostfix] private static void SwitchToItemSlotPostFix(PlayerControllerB __instance, int slot, GrabbableObject fillSlotWithItem = null) { if (!SentBallScanTip && StartOfRound.Instance.shipHasLanded && !((Object)(object)__instance != (Object)(object)Utils.CurrentPlayer)) { GrabbableObject val = __instance.ItemSlots[slot]; if ((Object)(object)val != (Object)null && ((object)val).GetType().IsSubclassOf(typeof(PokeballItem)) && !((PokeballItem)(object)val).enemyCaptured) { HUDManager.Instance.DisplayTip("LethalMon Tip", "Scan base game enemies to know if they are catchable or not. Modded enemies are not catchable.", false, false, "LC_Tip1"); SentBallScanTip = true; } } } } public class RedLocustBeesPatch { public static readonly Dictionary<int, DateTime> AngryUntil = new Dictionary<int, DateTime>(); [HarmonyPatch(typeof(RedLocustBees), "IsHivePlacedAndInLOS")] [HarmonyPrefix] private static bool IsHivePlacedAndInLOSPrefix(RedLocustBees __instance, ref bool __result) { int instanceID = ((Object)__instance).GetInstanceID(); if (AngryUntil.TryGetValue(instanceID, out var value)) { if (value < DateTime.Now) { AngryUntil.Remove(instanceID); return true; } __result = false; LethalMon.Log("ANGRY BEES!!!!"); return false; } return true; } [HarmonyPatch(typeof(RedLocustBees), "SpawnHiveNearEnemy")] [HarmonyPrefix] public static bool SpawnHiveNearEnemyPrefix(RedLocustBees __instance) { TamedEnemyBehaviour component = ((Component)__instance).GetComponent<TamedEnemyBehaviour>(); if ((Object)(object)component != (Object)null) { return !component.IsOwnedByAPlayer(); } return true; } } public class RoundManagerPatch { private static void ChangeIsScrapForBalls(bool isScrap, bool fullOnly) { GrabbableObject[] array = Object.FindObjectsOfType<GrabbableObject>(); GrabbableObject[] array2 = array; foreach (GrabbableObject val in array2) { if (((object)val).GetType().IsSubclassOf(typeof(PokeballItem)) && (!fullOnly || ((PokeballItem)(object)val).enemyCaptured)) { val.itemProperties.isScrap = isScrap; } } } [HarmonyPatch(typeof(RoundManager), "DespawnPropsAtEndOfRound")] [HarmonyPrefix] private static void DespawnPropsAtEndOfRoundPrefix(RoundManager __instance, bool despawnAllItems = false) { if (ModConfig.Instance.values.KeepBallsIfAllPlayersDead != "no") { ChangeIsScrapForBalls(isScrap: false, ModConfig.Instance.values.KeepBallsIfAllPlayersDead == "fullOnly"); } } [HarmonyPatch(typeof(RoundManager), "DespawnPropsAtEndOfRound")] [HarmonyPostfix] private static void DespawnPropsAtEndOfRoundPostfix(RoundManager __instance, bool despawnAllItems = false) { if (ModConfig.Instance.values.KeepBallsIfAllPlayersDead != "no") { ChangeIsScrapForBalls(isScrap: true, ModConfig.Instance.values.KeepBallsIfAllPlayersDead == "fullOnly"); } } } public class StartOfRoundPatch { [HarmonyPatch(typeof(StartOfRound), "ShipHasLeft")] [HarmonyPrefix] private static void OnShipHasLeftPreFix(StartOfRound __instance) { //IL_006f: Unknown result type (might be due to invalid IL or missing references) TamedEnemyBehaviour[] array = Object.FindObjectsOfType<TamedEnemyBehaviour>(); LethalMon.Log($"End of game, processing {array.Length} tamed enemies"); TamedEnemyBehaviour[] array2 = array; foreach (TamedEnemyBehaviour tamedEnemyBehaviour in array2) { if (!((Object)(object)tamedEnemyBehaviour.ownerPlayer == (Object)null)) { LethalMon.Log("Player is in hangar ship room: " + tamedEnemyBehaviour.ownerPlayer.isInHangarShipRoom); if (tamedEnemyBehaviour.ownerPlayer.isInHangarShipRoom) { PokeballItem pokeballItem = tamedEnemyBehaviour.RetrieveInBall(((Component)tamedEnemyBehaviour.ownerPlayer).transform.position); tamedEnemyBehaviour.ownerPlayer.SetItemInElevator(true, true, (GrabbableObject)(object)pokeballItem); ((Component)pokeballItem).transform.SetParent(__instance.elevatorTransform, true); } } } } [HarmonyPatch(typeof(StartOfRound), "OnPlayerDC")] [HarmonyPrefix] private static void OnPlayerDCPrefix(StartOfRound __instance, int playerObjectNumber, ulong clientId) { //IL_0060: Unknown result type (might be due to invalid IL or missing references) LethalMon.Log($"Client with ID {clientId} disconnected. Starting to delete its pets"); TamedEnemyBehaviour[] array = Object.FindObjectsOfType<TamedEnemyBehaviour>(); TamedEnemyBehaviour[] array2 = array; foreach (TamedEnemyBehaviour tamedEnemyBehaviour in array2) { if (tamedEnemyBehaviour.ownClientId == clientId) { LethalMon.Log("Found " + ((Object)tamedEnemyBehaviour.Enemy.enemyType).name + ", retrieving in ball"); tamedEnemyBehaviour.RetrieveInBall(((Component)tamedEnemyBehaviour.Enemy).transform.position); } } } } } namespace LethalMon.Items { public enum BallType { POKEBALL, GREAT_BALL, ULTRA_BALL, MASTER_BALL } public class BallTypeMethods { public static GameObject? GetPrefab(BallType ballType) { return (GameObject?)(ballType switch { BallType.GREAT_BALL => Greatball.SpawnPrefab, BallType.ULTRA_BALL => Ultraball.SpawnPrefab, BallType.MASTER_BALL => Masterball.SpawnPrefab, _ => Pokeball.SpawnPrefab, }); } } public class Greatball : PokeballItem { public static GameObject? SpawnPrefab; public static Item? BallItem; public Greatball() : base(BallType.GREAT_BALL, 1) { } internal static void Setup(AssetBundle assetBundle) { Item val = PokeballItem.InitBallPrefab<Greatball>(assetBundle, "Greatball/Greatball.asset", ModConfig.Instance.values.Tier2BallSpawnWeight); if (!((Object)(object)val == (Object)null)) { BallItem = val; SpawnPrefab = val.spawnPrefab; Item? ballItem = BallItem; int tier2BallCost = ModConfig.Instance.values.Tier2BallCost; Items.RegisterShopItem(ballItem, (TerminalNode)null, (TerminalNode)null, Utils.CreateTerminalNode("Great ball", "Use it to capture monsters. Second ball tier with a medium capture rate."), tier2BallCost); LethalMon.Log("Great ball added to shop"); } } protected override void __initializeVariables() { base.__initializeVariables(); } [MethodImpl(MethodImplOptions.NoInlining)] protected internal override string? __getTypeName() { return "Greatball"; } } public class Masterball : PokeballItem { public static GameObject? SpawnPrefab; public static Item? BallItem; public Masterball() : base(BallType.MASTER_BALL, 3) { } internal static void Setup(AssetBundle assetBundle) { Item val = PokeballItem.InitBallPrefab<Masterball>(assetBundle, "Masterball/Masterball.asset", ModConfig.Instance.values.Tier4BallSpawnWeight); if (!((Object)(object)val == (Object)null)) { BallItem = val; SpawnPrefab = val.spawnPrefab; Item? ballItem = BallItem; int tier4BallCost = ModConfig.Instance.values.Tier4BallCost; Items.RegisterShopItem(ballItem, (TerminalNode)null, (TerminalNode)null, Utils.CreateTerminalNode("Master ball", "Use it to capture monsters. Fourth ball tier with a 100% capture rate."), tier4BallCost); LethalMon.Log("Master ball added to shop"); } } protected override void __initializeVariables() { base.__initializeVariables(); } [MethodImpl(MethodImplOptions.NoInlining)] protected internal override string? __getTypeName() { return "Masterball"; } } public class Pokeball : PokeballItem { public static GameObject? SpawnPrefab; public static Item? BallItem; public Pokeball() : base(BallType.POKEBALL, 0) { } internal static void Setup(AssetBundle assetBundle) { Item val = PokeballItem.InitBallPrefab<Pokeball>(assetBundle, "Pokeball/Pokeball.asset", ModConfig.Instance.values.Tier1BallSpawnWeight); if (!((Object)(object)val == (Object)null)) { BallItem = val; SpawnPrefab = val.spawnPrefab; Item? ballItem = BallItem; int tier1BallCost = ModConfig.Instance.values.Tier1BallCost; Items.RegisterShopItem(ballItem, (TerminalNode)null, (TerminalNode)null, Utils.CreateTerminalNode("Pokeball", "Use it to capture monsters. First ball tier with a low capture rate."), tier1BallCost); LethalMon.Log("Pokeball added to shop"); } } protected override void __initializeVariables() { base.__initializeVariables(); } [MethodImpl(MethodImplOptions.NoInlining)] protected internal override string? __getTypeName() { return "Pokeball"; } } public abstract class PokeballItem : ThrowableItem { private EnemyAI? enemyAI; private EnemyType? enemyType; private global::LethalMon.CatchableEnemy.CatchableEnemy? catchableEnemy; private bool captureSuccess; private int captureRounds = 1; private int currentCaptureRound; internal bool enemyCaptured; private int captureStrength; private BallType ballType; public Dictionary<string, Tuple<float, DateTime>> cooldowns = new Dictionary<string, Tuple<float, DateTime>>(); public PokeballItem(BallType ballType, int captureStrength) { this.ballType = ballType; this.captureStrength = captureStrength; } internal static Item? InitBallPrefab<T>(AssetBundle assetBundle, string assetPath, int scrapRarity = 1) where T : PokeballItem { if ((Object)(object)assetBundle == (Object)null) { return null; } Item val = assetBundle.LoadAsset<Item>(Path.Combine("As