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 GatheringTorch v0.3.3
plugins/GatheringTorch.dll
Decompiled 3 months agousing System; using System.Collections; using System.Collections.Generic; using System.Diagnostics; using System.IO; using System.Reflection; using System.Runtime.CompilerServices; using System.Runtime.Versioning; using BepInEx; using BepInEx.Configuration; using BepInEx.Logging; using GatheringTorch.AI; using GatheringTorch.Items; using GatheringTorch.Skills; using GatheringTorch.Summons; using GatheringTorch.UI; using GatheringTorch.Util; using HarmonyLib; using Jotunn.Configs; using Jotunn.Entities; using Jotunn.Managers; using Jotunn.Utils; using Microsoft.CodeAnalysis; using UnityEngine; [assembly: CompilationRelaxations(8)] [assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)] [assembly: Debuggable(DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints)] [assembly: TargetFramework(".NETFramework,Version=v4.6.2", FrameworkDisplayName = ".NET Framework 4.6.2")] [assembly: AssemblyCompany("GatheringTorch")] [assembly: AssemblyConfiguration("Release")] [assembly: AssemblyFileVersion("1.0.0.0")] [assembly: AssemblyInformationalVersion("1.0.0")] [assembly: AssemblyProduct("GatheringTorch")] [assembly: AssemblyTitle("GatheringTorch")] [assembly: AssemblyVersion("1.0.0.0")] [module: RefSafetyRules(11)] namespace Microsoft.CodeAnalysis { [CompilerGenerated] [Embedded] internal sealed class EmbeddedAttribute : Attribute { } } namespace System.Runtime.CompilerServices { [CompilerGenerated] [Embedded] [AttributeUsage(AttributeTargets.Module, AllowMultiple = false, Inherited = false)] internal sealed class RefSafetyRulesAttribute : Attribute { public readonly int Version; public RefSafetyRulesAttribute(int P_0) { Version = P_0; } } } namespace GatheringTorch { [BepInPlugin("yoon.valheim.gatheringtorch", "Gathering Torch", "0.3.3")] [BepInDependency(/*Could not decode attribute arguments.*/)] [NetworkCompatibility(/*Could not decode attribute arguments.*/)] public sealed class Plugin : BaseUnityPlugin { public const string ModGuid = "yoon.valheim.gatheringtorch"; public const string ModName = "Gathering Torch"; public const string ModVersion = "0.3.3"; internal static ConfigEntry<KeyCode> MiningKey; internal static ConfigEntry<KeyCode> WoodKey; internal static ConfigEntry<KeyCode> CombatKey; internal static ConfigEntry<float> WorkRadius; internal static ConfigEntry<float> WorkDuration; internal static ConfigEntry<float> CombatDuration; internal static ConfigEntry<float> Cooldown; internal static ConfigEntry<float> WorkDamage; internal static ConfigEntry<int> GoblinLevel; internal static ConfigEntry<int> CombatGoblinCount; internal static ButtonConfig MiningButton; internal static ButtonConfig WoodButton; internal static ButtonConfig CombatButton; private Harmony _harmony; private SkillController _skills; private SkillHud _hud; internal static Plugin Instance { get; private set; } internal static ManualLogSource Log { get; private set; } private void Awake() { //IL_0034: Unknown result type (might be due to invalid IL or missing references) //IL_003e: Expected O, but got Unknown Instance = this; Log = ((BaseUnityPlugin)this).Logger; BindConfig(); RegisterInputs(); PrefabManager.OnVanillaPrefabsAvailable += OnVanillaPrefabsAvailable; _harmony = new Harmony("yoon.valheim.gatheringtorch"); _harmony.PatchAll(); _skills = ((Component)this).gameObject.AddComponent<SkillController>(); _hud = ((Component)this).gameObject.AddComponent<SkillHud>(); ((BaseUnityPlugin)this).Logger.LogInfo((object)"Gathering Torch 0.3.3 loaded"); } private void OnDestroy() { PrefabManager.OnVanillaPrefabsAvailable -= OnVanillaPrefabsAvailable; Harmony harmony = _harmony; if (harmony != null) { harmony.UnpatchSelf(); } } private void OnVanillaPrefabsAvailable() { try { GatheringTorchItems.Register(); DumpSummonFxPrefabs(); DumpMonsterDeathEffects(); ((BaseUnityPlugin)this).Logger.LogInfo((object)"Gathering Torch items registered after vanilla prefabs became available."); } catch (Exception arg) { ((BaseUnityPlugin)this).Logger.LogError((object)$"Failed to register Gathering Torch items: {arg}"); } finally { PrefabManager.OnVanillaPrefabsAvailable -= OnVanillaPrefabsAvailable; } } private void DumpSummonFxPrefabs() { try { if (!(typeof(PrefabManager).GetField("Prefabs", BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic)?.GetValue(PrefabManager.Instance) is IDictionary dictionary)) { return; } foreach (DictionaryEntry item in dictionary) { string text = item.Key?.ToString() ?? ""; string text2 = text.ToLowerInvariant(); if ((text2.Contains("skeleton") || text2.Contains("troll")) && (text2.Contains("vfx") || text2.Contains("sfx") || text2.Contains("death") || text2.Contains("ragdoll"))) { ((BaseUnityPlugin)this).Logger.LogInfo((object)("[GT-FX] " + text)); } } } catch (Exception ex) { ((BaseUnityPlugin)this).Logger.LogWarning((object)("[GT-FX] dump failed: " + ex.Message)); } } private void DumpMonsterDeathEffects() { string[] array = new string[2] { "Skeleton", "Troll" }; foreach (string text in array) { try { GameObject prefab = PrefabManager.Instance.GetPrefab(text); if ((Object)(object)prefab == (Object)null) { ((BaseUnityPlugin)this).Logger.LogWarning((object)("[GT-DEATHFX] prefab missing: " + text)); continue; } Character component = prefab.GetComponent<Character>(); if ((Object)(object)component == (Object)null) { ((BaseUnityPlugin)this).Logger.LogWarning((object)("[GT-DEATHFX] Character missing: " + text)); continue; } FieldInfo[] fields = typeof(Character).GetFields(BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic); foreach (FieldInfo fieldInfo in fields) { string text2 = fieldInfo.Name.ToLowerInvariant(); if (text2.Contains("death") || text2.Contains("effect")) { object value = fieldInfo.GetValue(component); if (value != null) { ((BaseUnityPlugin)this).Logger.LogInfo((object)("[GT-DEATHFX] " + text + " | " + fieldInfo.Name + " = " + value)); } } } } catch (Exception ex) { ((BaseUnityPlugin)this).Logger.LogWarning((object)("[GT-DEATHFX] " + text + " failed: " + ex.Message)); } } } private void BindConfig() { MiningKey = ((BaseUnityPlugin)this).Config.Bind<KeyCode>("Keys", "Mining skill", (KeyCode)120, "채광 고블린 작업반"); WoodKey = ((BaseUnityPlugin)this).Config.Bind<KeyCode>("Keys", "Woodcut skill", (KeyCode)122, "벌목 고블린 작업반"); CombatKey = ((BaseUnityPlugin)this).Config.Bind<KeyCode>("Keys", "Combat skill", (KeyCode)99, "전투 고블린 10마리"); WorkRadius = ((BaseUnityPlugin)this).Config.Bind<float>("Balance", "Work radius", 100f, "사용 지점 기준 작업 반경(m)"); WorkDuration = ((BaseUnityPlugin)this).Config.Bind<float>("Balance", "Worker duration", 45f, "채광/벌목/채집 고블린 지속시간(초)"); CombatDuration = ((BaseUnityPlugin)this).Config.Bind<float>("Balance", "Combat duration", 30f, "전투 고블린 지속시간(초)"); Cooldown = ((BaseUnityPlugin)this).Config.Bind<float>("Balance", "Skill cooldown", 60f, "X/Z/C 각각의 독립 쿨타임(초)"); WorkDamage = ((BaseUnityPlugin)this).Config.Bind<float>("Balance", "Worker damage", 200f, "벌목 Chop / 채광 Pickaxe 피해량"); GoblinLevel = ((BaseUnityPlugin)this).Config.Bind<int>("Balance", "Goblin level", 16, "15성 = 기본값 16 (0성이 level 1)"); CombatGoblinCount = ((BaseUnityPlugin)this).Config.Bind<int>("Balance", "Combat goblins", 10, "C 스킬 소환 수"); } private void RegisterInputs() { //IL_0000: Unknown result type (might be due to invalid IL or missing references) //IL_0005: Unknown result type (might be due to invalid IL or missing references) //IL_0010: 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_002b: Expected O, but got Unknown //IL_002b: 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_003b: Unknown result type (might be due to invalid IL or missing references) //IL_0046: Unknown result type (might be due to invalid IL or missing references) //IL_0056: Expected O, but got Unknown //IL_0056: 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_0066: 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_0081: Expected O, but got Unknown MiningButton = new ButtonConfig { Name = "GT_Mining", Config = MiningKey, Hint = "채광 고블린" }; WoodButton = new ButtonConfig { Name = "GT_Woodcut", Config = WoodKey, Hint = "벌목 고블린" }; CombatButton = new ButtonConfig { Name = "GT_Combat", Config = CombatKey, Hint = "전투 고블린" }; InputManager.Instance.AddButton("yoon.valheim.gatheringtorch", MiningButton); InputManager.Instance.AddButton("yoon.valheim.gatheringtorch", WoodButton); InputManager.Instance.AddButton("yoon.valheim.gatheringtorch", CombatButton); } } } namespace GatheringTorch.Util { internal static class PlayerItemUtil { private static readonly MethodInfo GetRightItemMethod = typeof(Humanoid).GetMethod("GetRightItem", BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic); internal static ItemData GetRightItem(Player player) { if ((Object)(object)player == (Object)null || GetRightItemMethod == null) { return null; } try { object? obj = GetRightItemMethod.Invoke(player, null); return (ItemData)((obj is ItemData) ? obj : null); } catch { return null; } } } } namespace GatheringTorch.UI { internal sealed class SkillHud : MonoBehaviour { private Texture2D _troll; private Texture2D _skeleton; private GUIStyle _label; private GUIStyle _key; private GUIStyle _cooldown; private GUIStyle _stateOn; private GUIStyle _stateOff; private GUIStyle _count; private static readonly Rect FlippedTexCoords = new Rect(0f, 1f, 1f, -1f); private void OnDestroy() { if ((Object)(object)_troll != (Object)null) { Object.Destroy((Object)(object)_troll); } if ((Object)(object)_skeleton != (Object)null) { Object.Destroy((Object)(object)_skeleton); } } private void OnGUI() { //IL_0069: Unknown result type (might be due to invalid IL or missing references) //IL_00b5: Unknown result type (might be due to invalid IL or missing references) //IL_00fc: Unknown result type (might be due to invalid IL or missing references) Player localPlayer = Player.m_localPlayer; SkillController instance = SkillController.Instance; if (!((Object)(object)localPlayer == (Object)null) && !((Object)(object)instance == (Object)null) && instance.HasSummonStaff) { int equippedTier = instance.EquippedTier; EnsureIcons(); EnsureStyles(); float num = 176f; float num2 = ((float)Screen.width - num) * 0.5f; float num3 = (float)Screen.height - 195f; DrawSkill(new Rect(num2, num3, 78f, 78f), (Texture)(object)_troll, "Z", "트롤 소환", instance.RemainingTroll, instance.TrollUiOn, instance.CurrentTrolls, instance.MaxTrolls); DrawSkill(new Rect(num2 + 78f + 20f, num3, 78f, 78f), (Texture)(object)_skeleton, "C", "해골 소환", instance.RemainingSkeleton, instance.SkeletonUiOn, instance.CurrentSkeletons, instance.MaxSkeletons); GUI.Label(new Rect(num2, num3 + 78f + 25f, num, 25f), $"고블린 지팡이 {equippedTier}단계", _label); } } private void DrawSkill(Rect r, Texture icon, string key, string name, float cd, bool ready, int current, int max) { //IL_0000: 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_0010: 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_0029: 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_00ae: 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_0077: 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_0133: Unknown result type (might be due to invalid IL or missing references) //IL_0183: Unknown result type (might be due to invalid IL or missing references) //IL_01b2: Unknown result type (might be due to invalid IL or missing references) //IL_01bc: Unknown result type (might be due to invalid IL or missing references) //IL_01c7: Unknown result type (might be due to invalid IL or missing references) //IL_01cd: Unknown result type (might be due to invalid IL or missing references) GUI.Box(r, GUIContent.none); Color color = GUI.color; GUI.color = (Color)(ready ? Color.white : new Color(0.38f, 0.38f, 0.38f, 0.85f)); if ((Object)(object)icon != (Object)null) { GUI.DrawTextureWithTexCoords(new Rect(((Rect)(ref r)).x + 3f, ((Rect)(ref r)).y + 3f, ((Rect)(ref r)).width - 6f, ((Rect)(ref r)).height - 6f), icon, FlippedTexCoords, true); } GUI.color = color; GUI.Label(new Rect(((Rect)(ref r)).x, ((Rect)(ref r)).y - 21f, ((Rect)(ref r)).width, 19f), key, _key); GUI.Label(new Rect(((Rect)(ref r)).x, ((Rect)(ref r)).y + 5f, ((Rect)(ref r)).width, 24f), ready ? "ON" : "OFF", ready ? _stateOn : _stateOff); GUI.Label(new Rect(((Rect)(ref r)).x, ((Rect)(ref r)).y + ((Rect)(ref r)).height - 28f, ((Rect)(ref r)).width, 23f), $"{current} / {max}", _count); GUI.Label(new Rect(((Rect)(ref r)).x, ((Rect)(ref r)).y + ((Rect)(ref r)).height + 3f, ((Rect)(ref r)).width, 18f), name, _label); if (cd > 0f) { GUI.color = new Color(0f, 0f, 0f, 0.42f); GUI.DrawTexture(r, (Texture)(object)Texture2D.whiteTexture); GUI.color = color; GUI.Label(r, Mathf.CeilToInt(cd).ToString(), _cooldown); } } private void EnsureIcons() { if ((Object)(object)_troll == (Object)null) { _troll = LoadEmbeddedRgba("GatheringTorch.Resources.woodcutting.rgba"); } if ((Object)(object)_skeleton == (Object)null) { _skeleton = LoadEmbeddedRgba("GatheringTorch.Resources.combat.rgba"); } } private static Texture2D LoadEmbeddedRgba(string resourceName) { //IL_0060: Unknown result type (might be due to invalid IL or missing references) //IL_0065: 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_0073: Unknown result type (might be due to invalid IL or missing references) //IL_007a: 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_008a: Expected O, but got Unknown using Stream stream = Assembly.GetExecutingAssembly().GetManifestResourceStream(resourceName); if (stream == null) { return null; } byte[] array = new byte[stream.Length]; int num; for (int i = 0; i < array.Length; i += num) { num = stream.Read(array, i, array.Length - i); if (num <= 0) { break; } } if (array.Length != 262144) { return null; } Texture2D val = new Texture2D(256, 256, (TextureFormat)4, false) { name = resourceName, wrapMode = (TextureWrapMode)1, filterMode = (FilterMode)1 }; val.LoadRawTextureData(array); val.Apply(false, false); return val; } private void EnsureStyles() { //IL_0014: 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_0028: Unknown result type (might be due to invalid IL or missing references) //IL_0034: Expected O, but got Unknown //IL_003f: Unknown result type (might be due to invalid IL or missing references) //IL_0050: Unknown result type (might be due to invalid IL or missing references) //IL_0055: Unknown result type (might be due to invalid IL or missing references) //IL_0062: Expected O, but got Unknown //IL_0069: Unknown result type (might be due to invalid IL or missing references) //IL_006e: Unknown result type (might be due to invalid IL or missing references) //IL_0076: Unknown result type (might be due to invalid IL or missing references) //IL_0082: Expected O, but got Unknown //IL_008d: 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_00a3: Unknown result type (might be due to invalid IL or missing references) //IL_00ab: Unknown result type (might be due to invalid IL or missing references) //IL_00b7: Expected O, but got Unknown //IL_00c2: Unknown result type (might be due to invalid IL or missing references) //IL_00d3: Unknown result type (might be due to invalid IL or missing references) //IL_00d8: Unknown result type (might be due to invalid IL or missing references) //IL_00e0: Unknown result type (might be due to invalid IL or missing references) //IL_00ec: Expected O, but got Unknown //IL_010b: Unknown result type (might be due to invalid IL or missing references) //IL_011c: Unknown result type (might be due to invalid IL or missing references) //IL_0121: Unknown result type (might be due to invalid IL or missing references) //IL_0129: Unknown result type (might be due to invalid IL or missing references) //IL_0135: Expected O, but got Unknown //IL_0140: Unknown result type (might be due to invalid IL or missing references) if (_label == null) { _label = new GUIStyle(GUI.skin.label) { alignment = (TextAnchor)4, fontSize = 14, fontStyle = (FontStyle)1 }; _label.normal.textColor = Color.white; _key = new GUIStyle(_label) { fontSize = 15 }; _cooldown = new GUIStyle(_label) { fontSize = 30, fontStyle = (FontStyle)1 }; _cooldown.normal.textColor = Color.white; _stateOn = new GUIStyle(_label) { fontSize = 20, fontStyle = (FontStyle)1 }; _stateOn.normal.textColor = Color.white; _stateOff = new GUIStyle(_label) { fontSize = 15, fontStyle = (FontStyle)1 }; _stateOff.normal.textColor = new Color(0.68f, 0.68f, 0.68f, 1f); _count = new GUIStyle(_label) { fontSize = 16, fontStyle = (FontStyle)1 }; _count.normal.textColor = Color.white; } } } } namespace GatheringTorch.Summons { internal sealed class SummonedGoblin : MonoBehaviour { private ZNetView _nview; internal long OwnerPlayerId { get; private set; } internal Vector3 WorkCenter { get; private set; } internal WorkerRole Role { get; private set; } internal float ExpiresAt { get; private set; } internal void Initialize(long ownerId, Vector3 center, WorkerRole role, float duration) { //IL_0008: Unknown result type (might be due to invalid IL or missing references) OwnerPlayerId = ownerId; WorkCenter = center; Role = role; ExpiresAt = Time.time + duration; _nview = ((Component)this).GetComponent<ZNetView>(); } private void Update() { if (!(Time.time < ExpiresAt) && ((Object)(object)_nview == (Object)null || !_nview.IsValid() || _nview.IsOwner())) { ZNetScene instance = ZNetScene.instance; if (instance != null) { instance.Destroy(((Component)this).gameObject); } } } internal Player FindOwner() { foreach (Player allPlayer in Player.GetAllPlayers()) { if ((Object)(object)allPlayer != (Object)null && allPlayer.GetPlayerID() == OwnerPlayerId) { return allPlayer; } } return null; } internal bool InWorkArea(Vector3 point) { //IL_0000: 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_0011: 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_0029: Unknown result type (might be due to invalid IL or missing references) //IL_0038: Unknown result type (might be due to invalid IL or missing references) Vector3 val = new Vector3(point.x, 0f, point.z); Vector3 val2 = default(Vector3); ((Vector3)(ref val2))..ctor(WorkCenter.x, 0f, WorkCenter.z); return Vector3.Distance(val, val2) <= Plugin.WorkRadius.Value; } } internal sealed class SummonedSkeleton : MonoBehaviour { internal long OwnerPlayerId { get; private set; } internal int StaffTier { get; private set; } internal bool Ranged { get; private set; } internal void Initialize(long ownerId, int staffTier, bool ranged) { OwnerPlayerId = ownerId; StaffTier = staffTier; Ranged = ranged; } internal Player FindOwner() { foreach (Player allPlayer in Player.GetAllPlayers()) { if ((Object)(object)allPlayer != (Object)null && allPlayer.GetPlayerID() == OwnerPlayerId) { return allPlayer; } } return null; } } internal static class SummonEffects { internal static void PlayTroll(Vector3 pos) { //IL_0000: Unknown result type (might be due to invalid IL or missing references) //IL_0015: Unknown result type (might be due to invalid IL or missing references) //IL_002e: Unknown result type (might be due to invalid IL or missing references) CreateBurst(pos, new Color(1f, 0.2f, 0.05f, 1f), new Color(0.55f, 0.05f, 0.02f, 0f), 55, 1.15f, 5.5f, 0.25f, 0.85f); } internal static void PlaySkeleton(Vector3 pos) { //IL_0000: Unknown result type (might be due to invalid IL or missing references) //IL_0015: Unknown result type (might be due to invalid IL or missing references) //IL_002e: Unknown result type (might be due to invalid IL or missing references) CreateBurst(pos, new Color(0.15f, 1f, 0.28f, 1f), new Color(0.35f, 0.05f, 0.65f, 0f), 42, 1f, 4f, 0.18f, 0.65f); } internal static void PlayDismiss(Vector3 pos) { //IL_0000: Unknown result type (might be due to invalid IL or missing references) //IL_0015: Unknown result type (might be due to invalid IL or missing references) //IL_002e: Unknown result type (might be due to invalid IL or missing references) CreateBurst(pos, new Color(0.15f, 0.85f, 0.25f, 1f), new Color(0.08f, 0.02f, 0.12f, 0f), 25, 0.75f, 2.8f, 0.15f, 0.5f); } private static void CreateBurst(Vector3 pos, Color start, Color end, int count, float lifetime, float speed, float minSize, float maxSize) { //IL_0005: Unknown result type (might be due to invalid IL or missing references) //IL_000b: Expected O, but got Unknown //IL_0011: 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_001c: Unknown result type (might be due to invalid IL or missing references) //IL_0021: Unknown result type (might be due to invalid IL or missing references) //IL_0033: Unknown result type (might be due to invalid IL or missing references) //IL_0038: Unknown result type (might be due to invalid IL or missing references) //IL_0059: Unknown result type (might be due to invalid IL or missing references) //IL_006f: Unknown result type (might be due to invalid IL or missing references) //IL_007f: Unknown result type (might be due to invalid IL or missing references) //IL_008b: Unknown result type (might be due to invalid IL or missing references) //IL_008c: Unknown result type (might be due to invalid IL or missing references) //IL_00b0: Unknown result type (might be due to invalid IL or missing references) //IL_00bb: Unknown result type (might be due to invalid IL or missing references) //IL_00c0: 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_00e3: Unknown result type (might be due to invalid IL or missing references) //IL_00e8: Unknown result type (might be due to invalid IL or missing references) //IL_00f3: Unknown result type (might be due to invalid IL or missing references) //IL_00f8: 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_0114: Unknown result type (might be due to invalid IL or missing references) //IL_011e: Unknown result type (might be due to invalid IL or missing references) //IL_0125: Expected O, but got Unknown //IL_012f: Unknown result type (might be due to invalid IL or missing references) //IL_0135: Unknown result type (might be due to invalid IL or missing references) //IL_013a: Unknown result type (might be due to invalid IL or missing references) //IL_0141: Unknown result type (might be due to invalid IL or missing references) //IL_0147: Unknown result type (might be due to invalid IL or missing references) //IL_014c: Unknown result type (might be due to invalid IL or missing references) //IL_0153: Unknown result type (might be due to invalid IL or missing references) //IL_0159: Unknown result type (might be due to invalid IL or missing references) //IL_015e: Unknown result type (might be due to invalid IL or missing references) //IL_0175: Unknown result type (might be due to invalid IL or missing references) //IL_017a: Unknown result type (might be due to invalid IL or missing references) //IL_018b: Unknown result type (might be due to invalid IL or missing references) //IL_0190: Unknown result type (might be due to invalid IL or missing references) //IL_01a1: Unknown result type (might be due to invalid IL or missing references) //IL_01a6: Unknown result type (might be due to invalid IL or missing references) //IL_01b4: Unknown result type (might be due to invalid IL or missing references) //IL_020e: Unknown result type (might be due to invalid IL or missing references) //IL_01f6: Unknown result type (might be due to invalid IL or missing references) //IL_0200: Expected O, but got Unknown GameObject val = new GameObject("GT_SummonFX"); val.transform.position = pos + Vector3.up * 0.35f; ParticleSystem val2 = val.AddComponent<ParticleSystem>(); MainModule main = val2.main; ((MainModule)(ref main)).duration = 0.25f; ((MainModule)(ref main)).loop = false; ((MainModule)(ref main)).startLifetime = new MinMaxCurve(lifetime * 0.65f, lifetime); ((MainModule)(ref main)).startSpeed = new MinMaxCurve(speed * 0.45f, speed); ((MainModule)(ref main)).startSize = new MinMaxCurve(minSize, maxSize); ((MainModule)(ref main)).startColor = MinMaxGradient.op_Implicit(start); ((MainModule)(ref main)).maxParticles = count + 10; ((MainModule)(ref main)).simulationSpace = (ParticleSystemSimulationSpace)1; ((MainModule)(ref main)).gravityModifier = MinMaxCurve.op_Implicit(-0.1f); EmissionModule emission = val2.emission; ((EmissionModule)(ref emission)).rateOverTime = MinMaxCurve.op_Implicit(0f); ((EmissionModule)(ref emission)).SetBursts((Burst[])(object)new Burst[1] { new Burst(0f, (short)count) }); ShapeModule shape = val2.shape; ((ShapeModule)(ref shape)).shapeType = (ParticleSystemShapeType)2; ((ShapeModule)(ref shape)).radius = 0.75f; ColorOverLifetimeModule colorOverLifetime = val2.colorOverLifetime; ((ColorOverLifetimeModule)(ref colorOverLifetime)).enabled = true; Gradient val3 = new Gradient(); val3.SetKeys((GradientColorKey[])(object)new GradientColorKey[3] { new GradientColorKey(start, 0f), new GradientColorKey(start, 0.3f), new GradientColorKey(end, 1f) }, (GradientAlphaKey[])(object)new GradientAlphaKey[3] { new GradientAlphaKey(1f, 0f), new GradientAlphaKey(0.85f, 0.45f), new GradientAlphaKey(0f, 1f) }); ((ColorOverLifetimeModule)(ref colorOverLifetime)).color = MinMaxGradient.op_Implicit(val3); ParticleSystemRenderer component = val.GetComponent<ParticleSystemRenderer>(); Shader val4 = Shader.Find("Particles/Standard Unlit"); if ((Object)(object)val4 == (Object)null) { val4 = Shader.Find("Legacy Shaders/Particles/Additive"); } if ((Object)(object)val4 != (Object)null) { ((Renderer)component).material = new Material(val4); } Light obj = val.AddComponent<Light>(); obj.type = (LightType)2; obj.color = start; obj.range = 5f; obj.intensity = 2.2f; val2.Play(); Object.Destroy((Object)(object)obj, 0.18f); Object.Destroy((Object)(object)val, lifetime + 0.5f); } } internal static class SummonManager { private const string TrollPrefab = "Troll"; private const string SkeletonPrefab = "Skeleton"; private static void PlayDeathEffect(GameObject prefab, Vector3 pos, Quaternion rot) { //IL_0022: 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) if ((Object)(object)prefab == (Object)null) { return; } Character component = prefab.GetComponent<Character>(); if ((Object)(object)component == (Object)null) { return; } try { component.m_deathEffects.Create(pos, rot, (Transform)null, 1f, -1); } catch (Exception ex) { ManualLogSource log = Plugin.Log; if (log != null) { log.LogWarning((object)("[GT-FX] death effect failed: " + ex.Message)); } } } internal static bool CastCombatGroup(Player owner, Vector3 center, int count) { //IL_0008: Unknown result type (might be due to invalid IL or missing references) bool flag = false; for (int i = 0; i < count; i++) { flag |= (Object)(object)SpawnTroll(owner, center, i, 1, 1) != (Object)null; } return flag; } internal static GameObject SpawnTroll(Player owner, Vector3 center, int index, int staffTier, int quality) { //IL_0064: Unknown result type (might be due to invalid IL or missing references) //IL_0069: Unknown result type (might be due to invalid IL or missing references) //IL_006e: Unknown result type (might be due to invalid IL or missing references) //IL_0074: Unknown result type (might be due to invalid IL or missing references) //IL_0079: Unknown result type (might be due to invalid IL or missing references) //IL_007a: Unknown result type (might be due to invalid IL or missing references) //IL_007b: Unknown result type (might be due to invalid IL or missing references) //IL_007c: 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_008b: Unknown result type (might be due to invalid IL or missing references) //IL_0090: Unknown result type (might be due to invalid IL or missing references) //IL_0095: 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_009f: Unknown result type (might be due to invalid IL or missing references) //IL_00a1: Unknown result type (might be due to invalid IL or missing references) //IL_00ab: Unknown result type (might be due to invalid IL or missing references) //IL_00b3: Unknown result type (might be due to invalid IL or missing references) //IL_00b5: Unknown result type (might be due to invalid IL or missing references) //IL_00e7: Unknown result type (might be due to invalid IL or missing references) //IL_00ec: Unknown result type (might be due to invalid IL or missing references) //IL_0135: Unknown result type (might be due to invalid IL or missing references) //IL_0147: Unknown result type (might be due to invalid IL or missing references) //IL_0120: Unknown result type (might be due to invalid IL or missing references) GameObject prefab = PrefabManager.Instance.GetPrefab("Troll"); if ((Object)(object)prefab == (Object)null) { ManualLogSource log = Plugin.Log; if (log != null) { log.LogError((object)"Troll prefab not found."); } return null; } float num = (float)index * 47.5f + Random.Range(-15f, 15f); float num2 = Random.Range(4f, 7f); Vector3 val = Quaternion.Euler(0f, num, 0f) * Vector3.forward * num2; Vector3 val2 = center + val + Vector3.up * 0.3f; SummonEffects.PlayTroll(val2); PlayDeathEffect(prefab, val2, Quaternion.identity); SummonEffects.PlayTroll(val2); GameObject obj = Object.Instantiate<GameObject>(prefab, val2, Quaternion.identity); MonsterAI component = obj.GetComponent<MonsterAI>(); if ((Object)(object)component != (Object)null) { component.m_attackPlayerObjects = false; } Character component2 = obj.GetComponent<Character>(); Vector3 localScale = obj.transform.localScale; if ((Object)(object)component2 != (Object)null) { component2.SetLevel(16); component2.m_group = $"GT_TROLL_{owner.GetPlayerID()}"; component2.m_faction = (Faction)0; } SummonedGoblin summonedGoblin = obj.AddComponent<SummonedGoblin>(); summonedGoblin.Initialize(owner.GetPlayerID(), center, WorkerRole.Combat, 315360000f); obj.AddComponent<TrollStatScaler>().Initialize(localScale, staffTier, quality); obj.AddComponent<CombatSummonAI>().Initialize(summonedGoblin); return obj; } internal static bool CastSkeletonGroup(Player owner, Vector3 center, int meleeCount, int rangedCount, int staffTier) { //IL_000a: Unknown result type (might be due to invalid IL or missing references) //IL_002e: Unknown result type (might be due to invalid IL or missing references) bool flag = false; int num = 0; for (int i = 0; i < meleeCount; i++) { flag |= (Object)(object)SpawnSkeleton(owner, center, num++, staffTier, ranged: false) != (Object)null; } for (int j = 0; j < rangedCount; j++) { flag |= (Object)(object)SpawnSkeleton(owner, center, num++, staffTier, ranged: true) != (Object)null; } return flag; } private static GameObject SpawnSkeleton(Player owner, Vector3 center, int index, int staffTier, bool ranged) { //IL_0064: Unknown result type (might be due to invalid IL or missing references) //IL_0069: Unknown result type (might be due to invalid IL or missing references) //IL_006e: Unknown result type (might be due to invalid IL or missing references) //IL_0074: Unknown result type (might be due to invalid IL or missing references) //IL_0079: Unknown result type (might be due to invalid IL or missing references) //IL_007a: Unknown result type (might be due to invalid IL or missing references) //IL_007b: Unknown result type (might be due to invalid IL or missing references) //IL_007c: 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_008b: Unknown result type (might be due to invalid IL or missing references) //IL_0090: Unknown result type (might be due to invalid IL or missing references) //IL_0095: 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_009e: Unknown result type (might be due to invalid IL or missing references) //IL_00a6: Unknown result type (might be due to invalid IL or missing references) //IL_00a8: Unknown result type (might be due to invalid IL or missing references) //IL_00b2: 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_00bc: Unknown result type (might be due to invalid IL or missing references) //IL_010e: Unknown result type (might be due to invalid IL or missing references) GameObject prefab = PrefabManager.Instance.GetPrefab("Skeleton"); if ((Object)(object)prefab == (Object)null) { ManualLogSource log = Plugin.Log; if (log != null) { log.LogError((object)"Skeleton prefab not found."); } return null; } float num = (float)index * 31f + Random.Range(-12f, 12f); float num2 = Random.Range(2.5f, 6f); Vector3 val = Quaternion.Euler(0f, num, 0f) * Vector3.forward * num2; Vector3 val2 = center + val + Vector3.up * 0.2f; SummonEffects.PlaySkeleton(val2); SummonEffects.PlaySkeleton(val2); PlayDeathEffect(prefab, val2, Quaternion.identity); SummonEffects.PlayTroll(val2); GameObject obj = Object.Instantiate<GameObject>(prefab, val2, Quaternion.identity); MonsterAI component = obj.GetComponent<MonsterAI>(); if ((Object)(object)component != (Object)null) { component.m_attackPlayerObjects = false; } Character component2 = obj.GetComponent<Character>(); Humanoid component3 = obj.GetComponent<Humanoid>(); if ((Object)(object)component2 != (Object)null) { component2.SetLevel(Mathf.Clamp(staffTier, 1, 6) + 1); component2.m_faction = (Faction)0; component2.m_group = $"GT_SKELETON_{owner.GetPlayerID()}"; } if ((Object)(object)component3 != (Object)null) { string text = (ranged ? "SkeletonBow" : "SkeletonSword"); GameObject prefab2 = PrefabManager.Instance.GetPrefab(text); ItemDrop val3 = (((Object)(object)prefab2 != (Object)null) ? prefab2.GetComponent<ItemDrop>() : null); if ((Object)(object)val3 != (Object)null) { ItemData val4 = val3.m_itemData.Clone(); component3.EquipItem(val4, false); } else { ManualLogSource log2 = Plugin.Log; if (log2 != null) { log2.LogWarning((object)("Skeleton weapon not found: " + text)); } } } SummonedSkeleton summonedSkeleton = obj.AddComponent<SummonedSkeleton>(); summonedSkeleton.Initialize(owner.GetPlayerID(), staffTier, ranged); obj.AddComponent<SkeletonStatScaler>().Initialize(summonedSkeleton); return obj; } internal static int DismissSkeletons(long ownerId) { //IL_0032: Unknown result type (might be due to invalid IL or missing references) //IL_007f: Unknown result type (might be due to invalid IL or missing references) //IL_008a: Unknown result type (might be due to invalid IL or missing references) int num = 0; SummonedSkeleton[] array = Object.FindObjectsByType<SummonedSkeleton>((FindObjectsSortMode)0); foreach (SummonedSkeleton summonedSkeleton in array) { if ((Object)(object)summonedSkeleton == (Object)null || summonedSkeleton.OwnerPlayerId != ownerId) { continue; } SummonEffects.PlayDismiss(((Component)summonedSkeleton).transform.position); ZNetView component = ((Component)summonedSkeleton).GetComponent<ZNetView>(); if (!((Object)(object)component == (Object)null) && component.IsValid() && !component.IsOwner()) { continue; } Character component2 = ((Component)summonedSkeleton).GetComponent<Character>(); if ((Object)(object)component2 != (Object)null) { try { component2.m_deathEffects.Create(((Component)summonedSkeleton).transform.position, ((Component)summonedSkeleton).transform.rotation, (Transform)null, 1f, -1); } catch { } } ZNetScene instance = ZNetScene.instance; if (instance != null) { instance.Destroy(((Component)summonedSkeleton).gameObject); } num++; } return num; } internal static bool HasSkeletons(long ownerId) { SummonedSkeleton[] array = Object.FindObjectsByType<SummonedSkeleton>((FindObjectsSortMode)0); foreach (SummonedSkeleton summonedSkeleton in array) { if ((Object)(object)summonedSkeleton != (Object)null && summonedSkeleton.OwnerPlayerId == ownerId) { return true; } } return false; } } internal static class SummonRuntime { internal static int TrollCount(long ownerId) { int num = 0; SummonedGoblin[] array = Object.FindObjectsOfType<SummonedGoblin>(); foreach (SummonedGoblin summonedGoblin in array) { if (!((Object)(object)summonedGoblin == (Object)null) && summonedGoblin.OwnerPlayerId == ownerId && (!((Object)(object)((Component)summonedGoblin).GetComponent<TrollStatScaler>() == (Object)null) || !((Object)(object)((Component)summonedGoblin).GetComponent<CombatSummonAI>() == (Object)null))) { Character component = ((Component)summonedGoblin).GetComponent<Character>(); if (!((Object)(object)component != (Object)null) || !component.IsDead()) { num++; } } } return num; } internal static int SkeletonCount(long ownerId) { int num = 0; SummonedSkeleton[] array = Object.FindObjectsOfType<SummonedSkeleton>(); foreach (SummonedSkeleton summonedSkeleton in array) { if (!((Object)(object)summonedSkeleton == (Object)null) && summonedSkeleton.OwnerPlayerId == ownerId) { Character component = ((Component)summonedSkeleton).GetComponent<Character>(); if (!((Object)(object)component != (Object)null) || !component.IsDead()) { num++; } } } return num; } internal static int DismissTrolls(long ownerId) { int num = 0; SummonedGoblin[] array = Object.FindObjectsOfType<SummonedGoblin>(); foreach (SummonedGoblin summonedGoblin in array) { if ((Object)(object)summonedGoblin == (Object)null || summonedGoblin.OwnerPlayerId != ownerId || ((Object)(object)((Component)summonedGoblin).GetComponent<TrollStatScaler>() == (Object)null && (Object)(object)((Component)summonedGoblin).GetComponent<CombatSummonAI>() == (Object)null)) { continue; } GameObject gameObject = ((Component)summonedGoblin).gameObject; ZNetView component = gameObject.GetComponent<ZNetView>(); if ((Object)(object)component == (Object)null || !component.IsValid() || component.IsOwner()) { if ((Object)(object)ZNetScene.instance != (Object)null && (Object)(object)component != (Object)null && component.IsValid()) { ZNetScene.instance.Destroy(gameObject); } else { Object.Destroy((Object)(object)gameObject); } num++; } } return num; } internal static void CleanupTrollCorpseFx(Vector3 center, float radius) { //IL_006a: Unknown result type (might be due to invalid IL or missing references) //IL_006f: Unknown result type (might be due to invalid IL or missing references) GameObject[] array = Object.FindObjectsOfType<GameObject>(); foreach (GameObject val in array) { if ((Object)(object)val == (Object)null) { continue; } string text = ((Object)val).name.ToLowerInvariant(); bool num = text.Contains("troll"); bool flag = text.Contains("ragdoll") || text.Contains("corpse") || text.Contains("death"); if (!num || !flag || Vector3.Distance(val.transform.position, center) > radius) { continue; } ZNetView component = val.GetComponent<ZNetView>(); if ((Object)(object)component != (Object)null && component.IsValid()) { if (component.IsOwner() && (Object)(object)ZNetScene.instance != (Object)null) { ZNetScene.instance.Destroy(val); } } else { Object.Destroy((Object)(object)val); } } } } internal enum WorkerRole { Mining, Woodcutting, Gathering, Combat } } namespace GatheringTorch.Skills { internal sealed class SkillController : MonoBehaviour { private const float TrollCooldown = 60f; private const float SkeletonCooldown = 30f; private const float CountRefreshInterval = 5f; private const float EquipRefreshInterval = 0.5f; private static readonly MethodInfo GetLeftItemMethod = typeof(Humanoid).GetMethod("GetLeftItem", BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic); private bool _castingTroll; private bool _castingSkeleton; private int _cachedTrolls; private int _cachedSkeletons; private float _nextCountRefreshAt; private ItemData _cachedStaff; private int _cachedTier; private float _nextEquipRefreshAt; internal static SkillController Instance { get; private set; } internal float TrollReadyAt { get; private set; } internal float SkeletonReadyAt { get; private set; } internal bool HasSummonStaff { get { Player localPlayer = Player.m_localPlayer; if ((Object)(object)localPlayer == (Object)null) { return false; } RefreshEquippedStaff(localPlayer, force: false); if (_cachedStaff != null) { return _cachedTier > 0; } return false; } } internal int EquippedTier => _cachedTier; internal ItemData EquippedStaff => _cachedStaff; internal bool TrollUiOn { get { if (!_castingTroll && _cachedTrolls <= 0) { return Time.time >= TrollReadyAt; } return false; } } internal bool SkeletonUiOn { get { if (!_castingSkeleton && _cachedSkeletons <= 0) { return Time.time >= SkeletonReadyAt; } return false; } } internal int CurrentTrolls => _cachedTrolls; internal int MaxTrolls => 1; internal int CurrentSkeletons => _cachedSkeletons; internal int MaxSkeletons { get { ItemData cachedStaff = _cachedStaff; if (cachedStaff == null) { return 0; } int num = Mathf.Max(1, cachedStaff.m_quality); return 10 + (num - 1) * 3; } } internal float RemainingTroll => Mathf.Max(0f, TrollReadyAt - Time.time); internal float RemainingSkeleton => Mathf.Max(0f, SkeletonReadyAt - Time.time); private void Awake() { Instance = this; } private void Update() { //IL_0036: 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) Player localPlayer = Player.m_localPlayer; if ((Object)(object)localPlayer == (Object)null) { return; } RefreshEquippedStaff(localPlayer, force: false); if (_cachedStaff == null || _cachedTier <= 0) { return; } RefreshCounts(force: false); if (Input.GetKeyDown(Plugin.WoodKey.Value)) { RefreshEquippedStaff(localPlayer, force: true); if (_cachedStaff != null) { TryTrollToggle(localPlayer, _cachedStaff, _cachedTier); } } if (Input.GetKeyDown(Plugin.CombatKey.Value)) { RefreshEquippedStaff(localPlayer, force: true); if (_cachedStaff != null) { TrySkeletonToggle(localPlayer, _cachedStaff, _cachedTier); } } } private void RefreshEquippedStaff(Player player, bool force) { if ((Object)(object)player == (Object)null) { _cachedStaff = null; _cachedTier = 0; } else { if (!force && Time.time < _nextEquipRefreshAt) { return; } _nextEquipRefreshAt = Time.time + 0.5f; _cachedStaff = null; _cachedTier = 0; ItemData rightItem = PlayerItemUtil.GetRightItem(player); if (rightItem != null && GatheringTorchItems.TryGetTier(rightItem, out var tier)) { _cachedStaff = rightItem; _cachedTier = tier; return; } ItemData leftItem = GetLeftItem(player); if (leftItem != null && GatheringTorchItems.TryGetTier(leftItem, out var tier2)) { _cachedStaff = leftItem; _cachedTier = tier2; } } } private static ItemData GetLeftItem(Player player) { if ((Object)(object)player == (Object)null || GetLeftItemMethod == null) { return null; } try { object? obj = GetLeftItemMethod.Invoke(player, null); return (ItemData)((obj is ItemData) ? obj : null); } catch { return null; } } private void RefreshCounts(bool force) { Player localPlayer = Player.m_localPlayer; if ((Object)(object)localPlayer == (Object)null) { _cachedTrolls = 0; _cachedSkeletons = 0; _nextCountRefreshAt = Time.time + 5f; } else if (force || !(Time.time < _nextCountRefreshAt)) { long playerID = localPlayer.GetPlayerID(); _cachedTrolls = SummonRuntime.TrollCount(playerID); _cachedSkeletons = SummonRuntime.SkeletonCount(playerID); _nextCountRefreshAt = Time.time + 5f; } } private void TryTrollToggle(Player player, ItemData staff, int tier) { RefreshCounts(force: true); long playerID = player.GetPlayerID(); if (_cachedTrolls > 0) { int num = SummonRuntime.DismissTrolls(playerID); _cachedTrolls = 0; _nextCountRefreshAt = Time.time + 5f; MessageHud instance = MessageHud.instance; if (instance != null) { instance.ShowMessage((MessageType)2, $"트롤 소환 해제 ({num}마리)", 0, (Sprite)null, false); } } else if (!_castingTroll) { if (Time.time < TrollReadyAt) { ShowCooldown("트롤 소환", TrollReadyAt - Time.time); } else { ((MonoBehaviour)this).StartCoroutine(CastTroll(player, staff, tier)); } } } private IEnumerator CastTroll(Player player, ItemData staff, int tier) { _castingTroll = true; PlayCastAnimation(player, "staff_trollsummon"); yield return (object)new WaitForSeconds(0.45f); if ((Object)(object)player == (Object)null) { _castingTroll = false; yield break; } Vector3 center = ((Component)player).transform.position; int quality = ((staff == null) ? 1 : Mathf.Max(1, staff.m_quality)); GameObject troll = SummonManager.SpawnTroll(player, center, 0, tier, quality); SummonRuntime.CleanupTrollCorpseFx(center, 14f); yield return (object)new WaitForSeconds(0.25f); SummonRuntime.CleanupTrollCorpseFx(center, 14f); if ((Object)(object)troll != (Object)null) { TrollReadyAt = Time.time + 60f; MessageHud instance = MessageHud.instance; if (instance != null) { instance.ShowMessage((MessageType)2, "트롤 소환", 0, (Sprite)null, false); } } _castingTroll = false; yield return null; RefreshCounts(force: true); } private void TrySkeletonToggle(Player player, ItemData staff, int tier) { RefreshCounts(force: true); long playerID = player.GetPlayerID(); if (_cachedSkeletons > 0) { int num = SummonManager.DismissSkeletons(playerID); _cachedSkeletons = 0; _nextCountRefreshAt = Time.time + 5f; MessageHud instance = MessageHud.instance; if (instance != null) { instance.ShowMessage((MessageType)2, $"해골 소환 해제 ({num}마리)", 0, (Sprite)null, false); } } else if (!_castingSkeleton) { if (Time.time < SkeletonReadyAt) { ShowCooldown("해골 소환", SkeletonReadyAt - Time.time); } else { ((MonoBehaviour)this).StartCoroutine(CastSkeletons(player, staff, tier)); } } } private IEnumerator CastSkeletons(Player player, ItemData staff, int tier) { _castingSkeleton = true; PlayCastAnimation(player, "staff_summon"); yield return (object)new WaitForSeconds(0.35f); if ((Object)(object)player == (Object)null || staff == null) { _castingSkeleton = false; yield break; } int num = Mathf.Max(1, staff.m_quality); int num2 = 5 + (num - 1) * 2; int num3 = 5 + (num - 1); Vector3 position = ((Component)player).transform.position; if (SummonManager.CastSkeletonGroup(player, position, num2, num3, tier)) { SkeletonReadyAt = Time.time + 30f; MessageHud instance = MessageHud.instance; if (instance != null) { instance.ShowMessage((MessageType)2, $"해골 소환 ({num2 + num3}마리)", 0, (Sprite)null, false); } } _castingSkeleton = false; yield return null; RefreshCounts(force: true); } private static void PlayCastAnimation(Player player, string trigger) { if ((Object)(object)player == (Object)null) { return; } try { ZSyncAnimation component = ((Component)player).GetComponent<ZSyncAnimation>(); if ((Object)(object)component != (Object)null) { component.SetTrigger(trigger); return; } } catch { } try { Animator componentInChildren = ((Component)player).GetComponentInChildren<Animator>(); if ((Object)(object)componentInChildren != (Object)null) { componentInChildren.SetTrigger(trigger); } } catch { } } private static void ShowCooldown(string skill, float remain) { MessageHud instance = MessageHud.instance; if (instance != null) { instance.ShowMessage((MessageType)2, $"{skill} 쿨타임 {Mathf.CeilToInt(remain)}초", 0, (Sprite)null, false); } } } } namespace GatheringTorch.Items { internal static class GatheringTorchItems { private const string BasePrefab = "Torch"; internal static readonly string[] Prefabs = new string[6] { "GT_GatheringTorch_T1", "GT_GatheringTorch_T2", "GT_GatheringTorch_T3", "GT_GatheringTorch_T4", "GT_GatheringTorch_T5", "GT_GatheringTorch_T6" }; private static readonly int[] WorkerCounts = new int[6] { 1, 2, 3, 4, 6, 9 }; private static readonly Dictionary<string, int> TierByPrefab = new Dictionary<string, int>(); internal static void Register() { //IL_0001: 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_0029: 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) //IL_0066: Unknown result type (might be due to invalid IL or missing references) //IL_008c: Unknown result type (might be due to invalid IL or missing references) RegisterTier(1, Color.red, "AxeWood", null); RegisterTier(2, Color.blue, "AxeStone", Prefabs[0]); RegisterTier(3, Color.yellow, "AxeFlint", Prefabs[1]); RegisterTier(4, Color.green, "AxeBronze", Prefabs[2]); RegisterTier(5, new Color(1f, 0.5f, 0f), "AxeIron", Prefabs[3]); RegisterTier(6, new Color(0.62f, 0.2f, 1f), "AxeBlackMetal", Prefabs[4]); } private static void RegisterTier(int tier, Color flameColor, string axePrefab, string previousTier) { //IL_0000: Unknown result type (might be due to invalid IL or missing references) //IL_0005: 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_0027: 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_003d: 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_004c: Expected O, but got Unknown //IL_00d0: Unknown result type (might be due to invalid IL or missing references) //IL_00d6: Expected O, but got Unknown //IL_0119: Unknown result type (might be due to invalid IL or missing references) //IL_012b: Unknown result type (might be due to invalid IL or missing references) //IL_012c: Unknown result type (might be due to invalid IL or missing references) //IL_0137: Unknown result type (might be due to invalid IL or missing references) //IL_0154: Unknown result type (might be due to invalid IL or missing references) ItemConfig val = new ItemConfig { Name = $"채집의 지팡이 {tier}", Description = GetDescription(tier), CraftingStation = CraftingStations.Workbench, RepairStation = CraftingStations.Workbench, MinStationLevel = 1, Amount = 1 }; switch (tier) { case 1: val.AddRequirement("Torch", 1, 0); val.AddRequirement(axePrefab, 1, 0); break; case 6: val.AddRequirement(previousTier, 1, 0); val.AddRequirement("Stone", 10, 5); val.AddRequirement("Iron", 10, 5); val.AddRequirement("BlackMetal", 10, 5); val.AddRequirement("Bronze", 10, 5); break; default: val.AddRequirement(previousTier, 1, 0); val.AddRequirement(axePrefab, 1, 0); break; } CustomItem val2 = new CustomItem(Prefabs[tier - 1], "Torch", val); SharedData shared = val2.ItemDrop.m_itemData.m_shared; shared.m_name = $"채집의 지팡이 {tier}"; shared.m_description = GetDescription(tier); shared.m_maxStackSize = 1; shared.m_maxQuality = 5; shared.m_damages = new DamageTypes { m_blunt = 1f }; shared.m_damagesPerLevel = default(DamageTypes); shared.m_attackForce = 0f; shared.m_toolTier = 0; RecolorTorch(val2.ItemPrefab, flameColor); if (ItemManager.Instance.AddItem(val2)) { TierByPrefab[Prefabs[tier - 1]] = tier; Plugin.Log.LogInfo((object)$"Registered staff T{tier}: {Prefabs[tier - 1]}"); } else { Plugin.Log.LogError((object)$"Failed to register staff T{tier}"); } } private static string GetDescription(int tier) { int num = WorkerCounts[tier - 1]; return $"X: 채광 {num}+채집1 / Z: 벌목 {num}+채집1 / C: 전투10\n" + "작업 45초, 전투 30초, 각 쿨타임 60초, 반경 100m"; } private static void RecolorTorch(GameObject prefab, Color c) { //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_0017: 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_003b: Unknown result type (might be due to invalid IL or missing references) ParticleSystem[] componentsInChildren = prefab.GetComponentsInChildren<ParticleSystem>(true); for (int i = 0; i < componentsInChildren.Length; i++) { MainModule main = componentsInChildren[i].main; ((MainModule)(ref main)).startColor = MinMaxGradient.op_Implicit(c); } Light[] componentsInChildren2 = prefab.GetComponentsInChildren<Light>(true); for (int i = 0; i < componentsInChildren2.Length; i++) { componentsInChildren2[i].color = c; } } internal static bool TryGetTier(ItemData item, out int tier) { tier = 0; if (item == null || (Object)(object)item.m_dropPrefab == (Object)null) { return false; } string key = ((Object)item.m_dropPrefab).name.Replace("(Clone)", ""); return TierByPrefab.TryGetValue(key, out tier); } internal static int WorkerCount(int tier) { if (tier < 1 || tier > WorkerCounts.Length) { return 0; } return WorkerCounts[tier - 1]; } } } namespace GatheringTorch.Patches { [HarmonyPatch(typeof(Character), "Damage")] internal static class CombatGoblinDamagePatch { private static void Prefix(HitData hit) { if (hit == null) { return; } Character attacker = hit.GetAttacker(); if ((Object)(object)attacker == (Object)null) { return; } TrollStatScaler component = ((Component)attacker).GetComponent<TrollStatScaler>(); if (!((Object)(object)component == (Object)null)) { float attackMultiplier = component.AttackMultiplier; if (!(attackMultiplier <= 0f) && !Mathf.Approximately(attackMultiplier, 1f)) { ((DamageTypes)(ref hit.m_damage)).Modify(attackMultiplier); } } } } [HarmonyPatch(typeof(Character), "Damage")] internal static class SkeletonSummonDamagePatch { private static void Prefix(HitData hit) { if (hit == null) { return; } Character attacker = hit.GetAttacker(); if (!((Object)(object)attacker == (Object)null)) { SummonedSkeleton component = ((Component)attacker).GetComponent<SummonedSkeleton>(); if (!((Object)(object)component == (Object)null)) { float attackMultiplier = SkeletonStatScaler.GetAttackMultiplier(component); hit.m_damage.m_damage *= attackMultiplier; hit.m_damage.m_blunt *= attackMultiplier; hit.m_damage.m_slash *= attackMultiplier; hit.m_damage.m_pierce *= attackMultiplier; hit.m_damage.m_chop *= attackMultiplier; hit.m_damage.m_pickaxe *= attackMultiplier; hit.m_damage.m_fire *= attackMultiplier; hit.m_damage.m_frost *= attackMultiplier; hit.m_damage.m_lightning *= attackMultiplier; hit.m_damage.m_poison *= attackMultiplier; hit.m_damage.m_spirit *= attackMultiplier; } } } } [HarmonyPatch(typeof(CharacterDrop), "GenerateDropList")] internal static class SummonNoDropPatch { [HarmonyPostfix] [HarmonyPriority(0)] private static void Postfix(CharacterDrop __instance, ref List<KeyValuePair<GameObject, int>> __result) { if (!((Object)(object)__instance == (Object)null) && __result != null) { GameObject gameObject = ((Component)__instance).gameObject; bool num = (Object)(object)gameObject.GetComponent<SummonedSkeleton>() != (Object)null; bool flag = (Object)(object)gameObject.GetComponent<SummonedGoblin>() != (Object)null && ((Object)(object)gameObject.GetComponent<TrollStatScaler>() != (Object)null || (Object)(object)gameObject.GetComponent<CombatSummonAI>() != (Object)null); if (num || flag) { __result.Clear(); } } } } } namespace GatheringTorch.AI { internal sealed class CombatSummonAI : MonoBehaviour { private SummonedGoblin _meta; private MonsterAI _ai; private Character _character; private Animator _animator; private float _nextFollow; private MethodInfo _inAttackMethod; internal void Initialize(SummonedGoblin meta) { //IL_0040: Unknown result type (might be due to invalid IL or missing references) _meta = meta; _ai = ((Component)this).GetComponent<MonsterAI>(); _character = ((Component)this).GetComponent<Character>(); _animator = ((Component)this).GetComponentInChildren<Animator>(); if ((Object)(object)_character != (Object)null) { _character.m_faction = (Faction)0; _character.m_group = $"GT_COMBAT_{meta.OwnerPlayerId}"; _inAttackMethod = ((object)_character).GetType().GetMethod("InAttack", BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic); } } private void Update() { if ((Object)(object)_character == (Object)null || (Object)(object)_animator == (Object)null) { return; } bool flag = false; if (_inAttackMethod != null) { try { if (_inAttackMethod.Invoke(_character, null) is bool flag2) { flag = flag2; } } catch { } } _animator.speed = (flag ? 2f : 1f); } private void FixedUpdate() { if (!((Object)(object)_meta == (Object)null) && !((Object)(object)_ai == (Object)null) && !(Time.time < _nextFollow)) { _nextFollow = Time.time + 1f; Player val = _meta.FindOwner(); if ((Object)(object)val != (Object)null && (Object)(object)_ai.GetFollowTarget() == (Object)null) { _ai.SetFollowTarget(((Component)val).gameObject); } } } private void OnDestroy() { if ((Object)(object)_animator != (Object)null) { _animator.speed = 1f; } } } internal sealed class GatherWorkerAI : WorkerBase { protected override GameObject FindTarget() { //IL_003d: 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_005b: Unknown result type (might be due to invalid IL or missing references) //IL_0060: Unknown result type (might be due to invalid IL or missing references) //IL_00bd: 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) //IL_00e0: Unknown result type (might be due to invalid IL or missing references) GameObject result = null; float num = float.MaxValue; Pickable[] array = Object.FindObjectsByType<Pickable>((FindObjectsSortMode)0); foreach (Pickable val in array) { if (!((Object)(object)val == (Object)null) && ((Component)val).gameObject.activeInHierarchy && Meta.InWorkArea(((Component)val).transform.position)) { float num2 = Vector3.SqrMagnitude(((Component)this).transform.position - ((Component)val).transform.position); if (num2 < num) { num = num2; result = ((Component)val).gameObject; } } } PickableItem[] array2 = Object.FindObjectsByType<PickableItem>((FindObjectsSortMode)0); foreach (PickableItem val2 in array2) { if (!((Object)(object)val2 == (Object)null) && ((Component)val2).gameObject.activeInHierarchy && Meta.InWorkArea(((Component)val2).transform.position)) { float num3 = Vector3.SqrMagnitude(((Component)this).transform.position - ((Component)val2).transform.position); if (num3 < num) { num = num3; result = ((Component)val2).gameObject; } } } return result; } protected override bool IsTargetStillValid(GameObject go) { //IL_001d: Unknown result type (might be due to invalid IL or missing references) if ((Object)(object)go != (Object)null && go.activeInHierarchy) { return Meta.InWorkArea(go.transform.position); } return false; } protected override void PerformWork(GameObject go) { if ((Object)(object)go == (Object)null || (Object)(object)Humanoid == (Object)null) { ClearTarget(); return; } Pickable componentInParent = go.GetComponentInParent<Pickable>(); if ((Object)(object)componentInParent != (Object)null) { componentInParent.Interact(Humanoid, false, false); ClearTarget(); return; } PickableItem componentInParent2 = go.GetComponentInParent<PickableItem>(); if ((Object)(object)componentInParent2 != (Object)null) { componentInParent2.Interact(Humanoid, false, false); ClearTarget(); } else { ClearTarget(); } } } internal sealed class HarvestLootForwarder : MonoBehaviour { private SummonedGoblin _meta; private ZNetView _nview; private float _nextScan; private void Awake() { _meta = ((Component)this).GetComponent<SummonedGoblin>(); _nview = ((Component)this).GetComponent<ZNetView>(); } private void FixedUpdate() { //IL_0080: Unknown result type (might be due to invalid IL or missing references) if ((Object)(object)_meta == (Object)null || _meta.Role == WorkerRole.Combat || Time.time < _nextScan) { return; } _nextScan = Time.time + 0.35f; if ((Object)(object)_nview != (Object)null && _nview.IsValid() && !_nview.IsOwner()) { return; } Player val = _meta.FindOwner(); if ((Object)(object)val == (Object)null) { return; } Collider[] array = Physics.OverlapSphere(((Component)this).transform.position, 7f); HashSet<ItemDrop> hashSet = new HashSet<ItemDrop>(); Collider[] array2 = array; foreach (Collider val2 in array2) { if (!((Object)(object)val2 == (Object)null)) { ItemDrop componentInParent = ((Component)val2).GetComponentInParent<ItemDrop>(); if (!((Object)(object)componentInParent == (Object)null) && hashSet.Add(componentInParent)) { TryTransfer(componentInParent, val); } } } } private static void TryTransfer(ItemDrop drop, Player owner) { if ((Object)(object)drop == (Object)null || (Object)(object)owner == (Object)null || drop.m_itemData == null) { return; } ZNetView component = ((Component)drop).GetComponent<ZNetView>(); if ((Object)(object)component != (Object)null && component.IsValid() && !component.IsOwner()) { drop.RequestOwn(); return; } Inventory inventory = ((Humanoid)owner).GetInventory(); ItemData val = drop.m_itemData.Clone(); if (!inventory.CanAddItem(val, val.m_stack) || !inventory.AddItem(val)) { return; } if ((Object)(object)component != (Object)null && component.IsValid()) { ZNetScene instance = ZNetScene.instance; if (instance != null) { instance.Destroy(((Component)drop).gameObject); } } else { Object.Destroy((Object)(object)((Component)drop).gameObject); } } } internal sealed class LaborTrollAI : MonoBehaviour { private SummonedGoblin _meta; private MonsterAI _ai; private Character _character; private Animator _animator; private GameObject _target; private float _nextSearch; private float _nextSwing; private int _swingsRemaining; private bool _swinging; private const float SearchInterval = 0.75f; private const float WorkDistance = 4f; private const float SwingInterval = 0.85f; internal void Initialize(SummonedGoblin meta) { //IL_0040: Unknown result type (might be due to invalid IL or missing references) _meta = meta; _ai = ((Component)this).GetComponent<MonsterAI>(); _character = ((Component)this).GetComponent<Character>(); _animator = ((Component)this).GetComponentInChildren<Animator>(); if ((Object)(object)_character != (Object)null) { _character.m_faction = (Faction)0; _character.m_group = $"GT_LABOR_{meta.OwnerPlayerId}"; } } private void Update() { //IL_007a: 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_00aa: Unknown result type (might be due to invalid IL or missing references) //IL_00e4: Unknown result type (might be due to invalid IL or missing references) //IL_00cd: Unknown result type (might be due to invalid IL or missing references) if ((Object)(object)_meta == (Object)null || (Object)(object)_character == (Object)null) { return; } if ((Object)(object)_target == (Object)null || !_target.activeInHierarchy) { StopSwinging(); if (Time.time >= _nextSearch) { _nextSearch = Time.time + 0.75f; _target = FindNearestTarget(); } return; } if (!_meta.InWorkArea(_target.transform.position)) { _target = null; StopSwinging(); return; } if (Vector3.Distance(((Component)this).transform.position, _target.transform.position) > 4f) { StopSwinging(); MoveToward(_target.transform.position); return; } FaceTarget(_target.transform.position); if (!_swinging) { _swinging = true; _swingsRemaining = 3; _nextSwing = Time.time; } if (_swingsRemaining > 0 && Time.time >= _nextSwing) { Swing(); _swingsRemaining--; _nextSwing = Time.time + 0.85f; } if (_swingsRemaining <= 0) { StopSwinging(); _target = null; _nextSearch = Time.time + 0.25f; } } private GameObject FindNearestTarget() { GameObject best = null; float bestDistance = float.MaxValue; TreeBase[] array = Object.FindObjectsByType<TreeBase>((FindObjectsSortMode)0); foreach (TreeBase val in array) { if ((Object)(object)val != (Object)null) { Consider(((Component)val).gameObject, ref best, ref bestDistance); } } TreeLog[] array2 = Object.FindObjectsByType<TreeLog>((FindObjectsSortMode)0); foreach (TreeLog val2 in array2) { if ((Object)(object)val2 != (Object)null) { Consider(((Component)val2).gameObject, ref best, ref bestDistance); } } MineRock5[] array3 = Object.FindObjectsByType<MineRock5>((FindObjectsSortMode)0); foreach (MineRock5 val3 in array3) { if ((Object)(object)val3 != (Object)null && IsOre(((Object)((Component)val3).gameObject).name)) { Consider(((Component)val3).gameObject, ref best, ref bestDistance); } } MineRock[] array4 = Object.FindObjectsByType<MineRock>((FindObjectsSortMode)0); foreach (MineRock val4 in array4) { if ((Object)(object)val4 != (Object)null && IsOre(((Object)((Component)val4).gameObject).name)) { Consider(((Component)val4).gameObject, ref best, ref bestDistance); } } return best; } private void Consider(GameObject go, ref GameObject best, ref float bestDistance) { //IL_001e: Unknown result type (might be due to invalid IL or missing references) //IL_0031: 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_0041: Unknown result type (might be due to invalid IL or missing references) if (!((Object)(object)go == (Object)null) && go.activeInHierarchy && _meta.InWorkArea(go.transform.position)) { float num = Vector3.SqrMagnitude(((Component)this).transform.position - go.transform.position); if (num < bestDistance) { bestDistance = num; best = go; } } } private static bool IsOre(string objectName) { if (string.IsNullOrEmpty(objectName)) { return false; } string text = objectName.ToLowerInvariant(); if ((text.Contains("rock") || text.Contains("stone")) && !text.Contains("copper") && !text.Contains("tin") && !text.Contains("silver") && !text.Contains("obsidian") && !text.Contains("iron") && !text.Contains("scrap") && !text.Contains("mud") && !text.Contains("marble") && !text.Contains("ancient")) { return false; } if (!text.Contains("copper") && !text.Contains("tin") && !text.Contains("silver") && !text.Contains("obsidian") && !text.Contains("iron") && !text.Contains("scrap") && !text.Contains("mudpile") && !text.Contains("mudpile") && !text.Contains("blackmarble") && !text.Contains("marble") && !text.Contains("ancientarmor")) { return text.Contains("ancientsword"); } return true; } private void MoveToward(Vector3 target) { //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_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_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_009e: Unknown result type (might be due to invalid IL or missing references) //IL_00a8: Unknown result type (might be due to invalid IL or missing references) //IL_00ad: 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) Vector3 val = target - ((Component)this).transform.position; val.y = 0f; if (((Vector3)(ref val)).sqrMagnitude < 0.01f) { return; } ((Vector3)(ref val)).Normalize(); if ((Object)(object)_ai != (Object)null) { MethodInfo method = typeof(BaseAI).GetMethod("MoveTowards", BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic); if (method != null) { try { method.Invoke(_ai, new object[2] { val, true }); return; } catch { } } } Transform transform = ((Component)this).transform; transform.position += val * 3f * Time.deltaTime; } private void FaceTarget(Vector3 target) { //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_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_0039: 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_003f: 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) Vector3 val = target - ((Component)this).transform.position; val.y = 0f; if (!(((Vector3)(ref val)).sqrMagnitude < 0.01f)) { ((Component)this).transform.rotation = Quaternion.Slerp(((Component)this).transform.rotation, Quaternion.LookRotation(val), Time.deltaTime * 10f); } } private void Swing() { if ((Object)(object)_animator != (Object)null) { _animator.speed = 2f; _animator.SetTrigger("attack"); } ((MonoBehaviour)this).Invoke("ApplySwingHit", 0.25f); } private void ApplySwingHit() { //IL_000f: Unknown result type (might be due to invalid IL or missing references) //IL_0015: Expected O, but got Unknown //IL_0021: Unknown result type (might be due to invalid IL or missing references) //IL_0026: Unknown result type (might be due to invalid IL or missing references) //IL_0032: Unknown result type (might be due to invalid IL or missing references) //IL_0037: Unknown result type (might be due to invalid IL or missing references) //IL_00d8: 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) //IL_00ed: Unknown result type (might be due to invalid IL or missing references) //IL_00f2: Unknown result type (might be due to invalid IL or missing references) //IL_0127: Unknown result type (might be due to invalid IL or missing references) //IL_012e: Unknown result type (might be due to invalid IL or missing references) //IL_0135: Expected O, but got Unknown //IL_013d: Unknown result type (might be due to invalid IL or missing references) //IL_0142: Unknown result type (might be due to invalid IL or missing references) //IL_014f: Unknown result type (might be due to invalid IL or missing references) //IL_0154: Unknown result type (might be due to invalid IL or missing references) if ((Object)(object)_target == (Object)null) { return; } HitData val = new HitData(); val.m_point = _target.transform.position; val.m_dir = ((Component)this).transform.forward; val.m_damage.m_blunt = 250f; if ((Object)(object)_target.GetComponent<TreeBase>() != (Object)null || (Object)(object)_target.GetComponent<TreeLog>() != (Object)null || (Object)(object)_target.GetComponentInParent<TreeBase>() != (Object)null || (Object)(object)_target.GetComponentInParent<TreeLog>() != (Object)null) { val.m_damage.m_chop = 500f; } else { val.m_damage.m_pickaxe = 500f; val.m_toolTier = 99; } TryDamage(_target, val); Collider[] array = Physics.OverlapSphere(((Component)this).transform.position + ((Component)this).transform.forward * 2f, 3f); for (int i = 0; i < array.Length; i++) { Character componentInParent = ((Component)array[i]).GetComponentInParent<Character>(); if (!((Object)(object)componentInParent == (Object)null) && !((Object)(object)componentInParent == (Object)(object)_character) && (int)componentInParent.m_faction != 0) { HitData val2 = new HitData(); val2.m_point = ((Component)componentInParent).transform.position; val2.m_dir = ((Component)this).transform.forward; val2.m_damage.m_blunt = 500f; val2.SetAttacker(_character); componentInParent.Damage(val2); } } } private static bool TryDamage(GameObject go, HitData hit) { if ((Object)(object)go == (Object)null) { return false; } Component[] componentsInChildren = go.GetComponentsInChildren<Component>(true); foreach (Component val in componentsInChildren) { if ((Object)(object)val == (Object)null) { continue; } MethodInfo method = ((object)val).GetType().GetMethod("Damage", BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic, null, new Type[1] { typeof(HitData) }, null); if (!(method == null)) { try { method.Invoke(val, new object[1] { hit }); return true; } catch { } } } return false; } private void StopSwinging() { _swinging = false; _swingsRemaining = 0; if ((Object)(object)_animator != (Object)null) { _animator.speed = 1f; } } private void OnDestroy() { if ((Object)(object)_animator != (Object)null) { _animator.speed = 1f; } } } internal sealed class MiningWorkerAI : WorkerBase { protected override GameObject FindTarget() { GameObject best = null; float bestScore = float.MaxValue; MineRock5[] array = Object.FindObjectsByType<MineRock5>((FindObjectsSortMode)0); foreach (MineRock5 val in array) { if ((Object)(object)val != (Object)null) { Consider(((Component)val).gameObject, ref best, ref bestScore); } } MineRock[] array2 = Object.FindObjectsByType<MineRock>((FindObjectsSortMode)0); foreach (MineRock val2 in array2) { if ((Object)(object)val2 != (Object)null) { Consider(((Component)val2).gameObject, ref best, ref bestScore); } } Destructible[] array3 = Object.FindObjectsByType<Destructible>((FindObjectsSortMode)0); foreach (Destructible val3 in array3) { if (!((Object)(object)val3 == (Object)null)) { string text = ((Object)((Component)val3).gameObject).name.ToLowerInvariant(); if (text.Contains("rock") || text.Contains("stone") || text.Contains("ore") || text.Contains("copper") || text.Contains("tin") || text.Contains("silver") || text.Contains("obsidian") || text.Contains("iron") || text.Contains("scrap") || text.Contains("mud") || text.Contains("meteor")) { Consider(((Component)val3).gameObject, ref best, ref bestScore); } } } return best; } private void Consider(GameObject go, ref GameObject best, ref float bestScore) { //IL_001d: 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_003b: 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) if (!((Object)(object)go == (Object)null) && go.activeInHierarchy && Meta.InWorkArea(go.transform.position)) { float num = Vector3.SqrMagnitude(((Component)this).transform.position - go.transform.position); if (num < bestScore) { bestScore = num; best = go; } } } protected override bool IsTargetStillValid(GameObject go) { //IL_001d: Unknown result type (might be due to invalid IL or missing references) if ((Object)(object)go != (Object)null && go.activeInHierarchy) { return Meta.InWorkArea(go.transform.position); } return false; } protected override void PerformWork(GameObject go) { //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_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) if ((Object)(object)go == (Object)null) { ClearTarget(); return; } HitData val = MakeHit(0f, 1000f); val.m_toolTier = 99; val.m_point = go.transform.position; bool flag = TryApplyDamage(go, val); if (!flag) { Transform[] componentsInChildren = go.GetComponentsInChildren<Transform>(true); foreach (Transform val2 in componentsInChildren) { if (!((Object)(object)val2 == (Object)null) && !((Object)(object)((Component)val2).gameObject == (Object)(object)go)) { HitData val3 = MakeHit(0f, 1000f); val3.m_toolTier = 99; val3.m_point = val2.position; if (TryApplyDamage(((Component)val2).gameObject, val3)) { flag = true; break; } } } } if (!flag) { ManualLogSource log = Plugin.Log; if (log != null) { log.LogWarning((object)("No mining Damage(HitData) receiver found on " + ((Object)go).name)); } ClearTarget(); } } } internal sealed class SkeletonStatScaler : MonoBehaviour { private Character _character; private SummonedSkeleton _meta; internal void Initialize(SummonedSkeleton meta) { _meta = meta; _character = ((Component)this).GetComponent<Character>(); if (!((Object)(object)_character == (Object)null) && !((Object)(object)_meta == (Object)null)) { ApplyHealth(); } } private void ApplyHealth() { float num = Mathf.Pow(2f, (float)Mathf.Max(0, _meta.StaffTier - 1)); float num2 = 262.5f * num; MethodInfo method = typeof(Character).GetMethod("SetMaxHealth", BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic, null, new Type[1] { typeof(float) }, null); if (method != null) { try { method.Invoke(_character, new object[1] { num2 }); } catch { } } MethodInfo method2 = typeof(Character).GetMethod("SetHealth", BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic, null, new Type[1] { typeof(float) }, null); if (method2 != null) { try { method2.Invoke(_character, new object[1] { num2 }); } catch { } } } internal static float GetAttackMultiplier(SummonedSkeleton meta) { if ((Object)(object)meta == (Object)null) { return 1f; } return Mathf.Pow(2f, (float)Mathf.Max(0, meta.StaffTier - 1)); } } internal sealed class TrollStatScaler : MonoBehaviour { private Character _character; internal float AttackMultiplier { get; private set; } = 1f; internal void Initialize(Vector3 baseScale, int staffTier, int quality) { //IL_0021: 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) _character = ((Component)this).GetComponent<Character>(); if (!((Object)(object)_character == (Object)null)) { ((Component)this).transform.localScale = baseScale * 1.2f; int num = Mathf.Clamp(staffTier, 1, 6); int num2 = Mathf.Clamp(quality, 1, 5); float tierMultiplier = GetTierMultiplier(num); float num3 = 1f + 0.25f * (float)(num2 - 1); float num4 = tierMultiplier * num3; float maxHealth = GetMaxHealth(); _character.SetLevel(num + 1); float maxHealth2 = GetMaxHealth(); float num5 = 1f; if (maxHealth > 0f && maxHealth2 > 0f) { num5 = maxHealth / maxHealth2; } if (maxHealth > 0f) { float num6 = maxHealth * num4; SetMaxHealth(num6); SetHealth(num6); } AttackMultiplier = num5 * num4; } } private float GetMaxHealth() { MethodInfo method = typeof(Character).GetMethod("GetMaxHealth", BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic, null, Type.EmptyTypes, null); if (method == null) { return 0f; } try { object obj = method.Invoke(_character, null); if (obj is float) { return (float)obj; } } catch { } return 0f; } private void SetMaxHealth(float value) { MethodInfo method = typeof(Character).GetMethod("SetMaxHealth", BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic, null, new Type[1] { typeof(float) }, null); if (method == null) { return; } try { method.Invoke(_character, new object[1] { value }); } catch { } } private void SetHealth(float value) { MethodInfo method = typeof(Character).GetMethod("SetHealth", BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic, null, new Type[1] { typeof(float) }, null); if (method == null) { return; } try { method.Invoke(_character, new object[1] { value }); } catch { } } private static float GetTierMultiplier(int tier) { return Mathf.Clamp(tier, 1, 6) switch { 1 => 2f, 2 => 2.9f, 3 => 4.2f, 4 => 6.1f, 5 => 8.84f, 6 => 12.8f, _ => 1f, }; } } internal sealed class WoodcutWorkerAI : WorkerBase { protected override GameObject FindTarget() { GameObject best = null; float bestDist = float.MaxValue; TreeBase[] array = Object.FindObjectsByType<TreeBase>((FindObjectsSortMode)0); foreach (TreeBase val in array) { Consider(((Object)(object)val != (Object)null) ? ((Component)val).gameObject : null, ref best, ref bestDist); } TreeLog[] array2 = Object.FindObjectsByType<TreeLog>((FindObjectsSortMode)0); foreach (TreeLog val2 in array2) { Consider(((Object)(object)val2 != (Object)null) ? ((Component)val2).gameObject : null, ref best, ref bestDist); } Destructible[] array3 = Object.FindObjectsByType<Destructible>((FindObjectsSortMode)0); foreach (Destructible val3 in array3) { if (!((Object)(object)val3 == (Object)null)) { string text = ((Object)((Component)val3).gameObject).name.ToLowerInvariant(); if (text.Contains("stump") || text.Contains("tree") || text.Contains("log")) { Consider(((Component)val3).gameObject, ref best, ref bestDist); } } } return best; } private void Consider(GameObject go, ref GameObject best, ref float bestDist) { //IL_001d: 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_003b: 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) if (!((Object)(object)go == (Object)null) && go.activeInHierarchy && Meta.InWorkArea(go.transform.position)) { float num = Vector3.SqrMagnitude(((Component)this).transform.position - go.transform.position); if (num < bestDist) { bestDist = num; best = go; } } } protected override bool IsTargetStillValid(GameObject go) { //IL_001d: Unknown result type (might be due to invalid IL or missing references) if ((Object)(object)go != (Object)null && go.activeInHierarchy) { return Meta.InWorkArea(go.transform.position); } return false; } protected override void PerformWork(GameObject go) { //IL_002d: 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) if ((Object)(object)go == (Object)null) { ClearTarget(); return; } HitData val = MakeHit(Plugin.WorkDamage.Value, 0f); val.m_point = go.transform.position; if (!TryApplyDamage(go, val)) { ManualLogSource log = Plugin.Log; if (log != null) { log.LogWarning((object)("No woodcut Damage(HitData) receiver found on " + ((Object)go).name)); } ClearTarget(); } } } internal abstract class WorkerBase : MonoBehaviour { protected SummonedGoblin Meta; protected MonsterAI AI; private bool _speedBoosted; protected Humanoid Humanoid; protected ZNetView NView; protected float NextSearch; protected float NextWork; protected GameObject Target; protected const float SearchInterval = 1.25f; protected const float WorkInterval = 1.1f; protected const float InteractionDistance = 2.25f; internal virtual void Initialize(SummonedGoblin meta) { //IL_0086: Unknown result type (might be due to invalid IL or missing references) Meta = meta; AI = ((Component)this).GetComponent<MonsterAI>(); Humanoid = ((Component)this).GetComponent<Humanoid>(); NView = ((Component)this).GetComponent<ZNetView>(); if ((Object)(object)AI != (Object)null) { AI.m_alertRange = 0f; ((BaseAI)AI).m_viewRange = 0f; ((BaseAI)AI).m_hearRange = 0f; } Character component = ((Component)this).GetComponent<Character>(); if ((Object)(object)component != (Object)null) { component.m_group = "GT_WORKER"; component.m_faction = (Faction)0; } } protected virtual void FixedUpdate() { //IL_0068: Unknown result type (might be due to invalid IL or missing references) //IL_0096: Unknown result type (might be due to invalid IL or missing references) //IL_009b: Unknown result type (might be due to invalid IL or missing references) //IL_00a4: Unknown result type (might be due to invalid IL or missing references) //IL_00b9: Unknown result type (might be due to invalid IL or missing references) //IL_00c5: 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) if ((Object)(object)Meta == (Object)null || (Object)(object)AI == (Object)null || ((Object)(object)NView != (Object)null && NView.IsValid() && !NView.IsOwner())) { return; } if ((Object)(object)Target != (Object)null) { if (!Meta.InWorkArea(Target.transform.position)) { ClearTarget(); } else { MoveTowardTarget(Target); Vector3 position = Target.transform.position; position.y = ((Component)this).transform.position.y; ((Component)this).transform.LookAt(position); if (Vector3.Distance(((Component)this).transform.position, Target.transform.position) <= 2.25f && Time.time >= NextWork) { NextWork = Time.time + 1.1f; PerformWork(Target); } } } if (((Object)(object)Target == (Object)null || !IsTargetStillValid(Target)) && Time.time >= NextSearch) { NextSearch = Time.time + 1.25f + Random.Range(0f, 0.35f); Target = FindTarget(); MoveTowardTarget(Target); } } private void MoveTowardTarget(GameObject go) { //IL_001e: 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_00e1: Unknown result type (might be due to invalid IL or missing references) //IL_00e8: Unknown result type (might be due to invalid IL or missing references) //IL_00ed: Unknown result type (might be due to invalid IL or missing references) //IL_00f2: 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_011a: Unknown result type (might be due to invalid IL or missing references) if ((Object)(object)go == (Object)null || (Object)(object)AI == (Object)null) { return; } Vector3 position = go.transform.position; MethodInfo methodInfo = AccessTools.Method(typeof(BaseAI), "MoveTo", new Type[4] { typeof(float), typeof(Vector3), typeof(float), typeof(bool) }, (Type[])null); if (methodInfo != null) { try { methodInfo.Invoke(AI, new object[4] { Time.fixedDeltaTime, position, 1.8000001f, true }); return; } catch (Exception ex) { ManualLogSource log = Plugin.Log; if (log != null) { log.LogError((object)("Worker MoveTo failed: " + ex.Message)); } } } Vector3 val = position - ((Component)this).transform.position; val.y = 0f; if (((Vector3)(ref val)).sqrMagnitude > 0.01f) { ((Vector3)(ref val)).Normalize(); ((BaseAI)AI).MoveTowards(val, true); } } protected void ClearTarget() { Target = null; if ((Object)(object)AI != (Object)null) { AI.SetFollowTarget((GameObject)null); } } protected abstract GameObject FindTarget(); protected abstract bool IsTargetStillValid(GameObject go); protected abstract void PerformWork(GameObject go); protected T FindClosestInRadius<T>() where T : Component { //IL_0059: 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_007c: 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) T[] array = Object.FindObjectsByType<T>((FindObjectsSortMode)0); T result = default(T); float num = float.MaxValue; T[] array2 = array; foreach (T val in array2) { if (!((Object)(object)val == (Object)null) && ((Component)val).gameObject.activeInHierarchy && Meta.InWorkArea(((Component)val).transform.position)) { float num2 = Vector3.SqrMagnitude(((Component)this).transform.position - ((Component)val).transform.position); if (num2 < num) { num = num2; result = val; } } } return result; } protected bool TryApplyDamage(GameObject go, HitData hit) { if ((Object)(object)go == (Object)null || hit == null) { return false; } Component[] componentsInChildren = go.GetComponentsInChildren<Component>(true); for (int i = 0; i < componentsInChildren.Length; i++) { if (TryInvokeDamage(componentsInChildren[i], hit)) { return true; } } Transform parent = go.transform.parent; while ((Object)(object)parent != (Object)null) { componentsInChildren = ((Component)parent).GetComponents<Component>(); for (int i = 0; i < componentsInChildren.Length; i++) { if (TryInvokeDamage(componentsInChildren[i], hit)) { return true; } } parent = parent.parent; } return false; } private static bool TryInvokeDamage(Component component, HitData hit) { if ((Object)(object)component == (Object)null) { return false; } MethodInfo method = ((object)component).GetType().GetMethod("Damage", BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic, null, new Type[1] { typeof(HitData) }, null); if (method == null) { return false; } try { method.Invoke(component, new object[1] { hit }); return true; } catch { return false; } } protected HitData MakeHit(float chop, float pickaxe) { //IL_0000: Unknown result type (might be due to invalid IL or missing references) //IL_0006: Expected O, but got Unknown //IL_002d: 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) HitData val = new HitData(); val.m_damage.m_chop = chop; val.m_damage.m_pickaxe = pickaxe; val.m_toolTier = 99; val.m_point = ((Component)this).transform.position; Humanoid component = ((Component)this).GetComponent<Humanoid>(); if ((Object)(object)component != (Object)null) { val.SetAttacker((Character)(object)component); } return val; } } }