Decompiled source of BetterArchery v1.9.5
BetterArchery/plugins/BetterArchery.dll
Decompiled 2 weeks 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.Collections.Specialized; using System.Diagnostics; using System.Globalization; using System.IO; using System.Linq; using System.Reflection; using System.Reflection.Emit; using System.Runtime.CompilerServices; using System.Runtime.InteropServices; using System.Runtime.Versioning; using System.Security; using System.Security.Permissions; using System.Text; using Auga; using BepInEx; using BepInEx.Configuration; using Common; using HarmonyLib; using JetBrains.Annotations; using LitJson; using Microsoft.CodeAnalysis; using TMPro; using UnityEngine; using UnityEngine.Networking; using UnityEngine.UI; [assembly: AssemblyFileVersion("1.0.1.0")] [assembly: Guid("04f6ef99-721d-41d7-86e2-59ced874c902")] [assembly: ComVisible(false)] [assembly: AssemblyTrademark("")] [assembly: AssemblyCopyright("Copyright © 2021")] [assembly: AssemblyProduct("BetterArchery")] [assembly: AssemblyConfiguration("")] [assembly: AssemblyDescription("")] [assembly: AssemblyTitle("BetterArchery")] [assembly: Debuggable(DebuggableAttribute.DebuggingModes.Default | DebuggableAttribute.DebuggingModes.DisableOptimizations | DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints | DebuggableAttribute.DebuggingModes.EnableEditAndContinue)] [assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)] [assembly: CompilationRelaxations(8)] [assembly: TargetFramework(".NETFramework,Version=v4.8.1", FrameworkDisplayName = ".NET Framework 4.8.1")] [assembly: AssemblyCompany("")] [assembly: SecurityPermission(SecurityAction.RequestMinimum, SkipVerification = true)] [assembly: AssemblyVersion("1.0.1.0")] [module: RefSafetyRules(11)] [module: UnverifiableCode] namespace Microsoft.CodeAnalysis { [CompilerGenerated] [Microsoft.CodeAnalysis.Embedded] internal sealed class EmbeddedAttribute : Attribute { } } namespace System.Runtime.CompilerServices { [CompilerGenerated] [Microsoft.CodeAnalysis.Embedded] [AttributeUsage(AttributeTargets.Module, AllowMultiple = false, Inherited = false)] internal sealed class RefSafetyRulesAttribute : Attribute { public readonly int Version; public RefSafetyRulesAttribute(int P_0) { Version = P_0; } } } namespace Common { [Serializable] public class RecipeRequirementConfig { public string item = ""; public int amount = 1; } [Serializable] public class RecipeConfig { public string name = ""; public string item = ""; public int amount = 1; public string craftingStation = ""; public int minStationLevel = 1; public bool enabled = true; public string repairStation = ""; public List<RecipeRequirementConfig> resources = new List<RecipeRequirementConfig>(); } [Serializable] public class RecipesConfig { public List<RecipeConfig> recipes = new List<RecipeConfig>(); } internal class CustomSlotItem : MonoBehaviour { public string m_slotName; } public static class CustomSlotCreator { public static readonly Dictionary<Humanoid, Dictionary<string, ItemData>> customSlotItemData = new Dictionary<Humanoid, Dictionary<string, ItemData>>(); public static string GetCustomSlotName(ItemData item) { return item.m_dropPrefab.GetComponent<CustomSlotItem>().m_slotName; } public static bool IsCustomSlotItem(ItemData item) { return item != null && Object.op_Implicit((Object)(object)item.m_dropPrefab) && Object.op_Implicit((Object)(object)item.m_dropPrefab.GetComponent<CustomSlotItem>()); } public static ItemData GetPrefabItemData(Humanoid humanoid, string slotName) { if (!DoesSlotExist(humanoid, slotName)) { return null; } return customSlotItemData[humanoid][slotName].m_dropPrefab.GetComponent<ItemDrop>().m_itemData; } public static ItemData GetSlotItem(Humanoid humanoid, string slotName) { if (DoesSlotExist(humanoid, slotName)) { return customSlotItemData[humanoid][slotName]; } return null; } public static void SetSlotItem(Humanoid humanoid, string slotName, ItemData item) { customSlotItemData[humanoid][slotName] = item; } public static bool DoesSlotExist(Humanoid humanoid, string slotName) { return customSlotItemData[humanoid] != null && customSlotItemData[humanoid].ContainsKey(slotName); } public static bool IsSlotOccupied(Humanoid humanoid, string slotName) { return customSlotItemData[humanoid] != null && customSlotItemData[humanoid].ContainsKey(slotName) && customSlotItemData[humanoid][slotName] != null; } public static void ApplyCustomSlotItem(GameObject prefab, string slotName) { //IL_0039: Unknown result type (might be due to invalid IL or missing references) if (!Object.op_Implicit((Object)(object)prefab.GetComponent<CustomSlotItem>())) { prefab.AddComponent<CustomSlotItem>(); } prefab.GetComponent<CustomSlotItem>().m_slotName = slotName; prefab.GetComponent<ItemDrop>().m_itemData.m_shared.m_itemType = (ItemType)0; Debug.Log((object)("[CustomSlotCreator] Created " + slotName + " slot for " + ((Object)prefab).name + ".")); } } public static class PrefabCreator { public static Dictionary<string, CraftingStation> CraftingStations; public static T RequireComponent<T>(GameObject go) where T : Component { T val = go.GetComponent<T>(); if ((Object)(object)val == (Object)null) { val = go.AddComponent<T>(); } return val; } public static void Reset() { CraftingStations = null; } private static void InitCraftingStations() { if (CraftingStations != null) { return; } CraftingStations = new Dictionary<string, CraftingStation>(); foreach (Recipe recipe in ObjectDB.instance.m_recipes) { if ((Object)(object)recipe.m_craftingStation != (Object)null && !CraftingStations.ContainsKey(((Object)recipe.m_craftingStation).name)) { CraftingStations.Add(((Object)recipe.m_craftingStation).name, recipe.m_craftingStation); } } } public static Recipe CreateRecipe(string name, string itemId, RecipeConfig recipeConfig) { //IL_0203: Unknown result type (might be due to invalid IL or missing references) //IL_0208: Unknown result type (might be due to invalid IL or missing references) //IL_0215: Unknown result type (might be due to invalid IL or missing references) //IL_0227: Expected O, but got Unknown InitCraftingStations(); GameObject itemPrefab = ObjectDB.instance.GetItemPrefab(itemId); if ((Object)(object)itemPrefab == (Object)null) { Debug.LogWarning((object)("[PrefabCreator] Could not find item prefab (" + itemId + ")")); return null; } Recipe val = ScriptableObject.CreateInstance<Recipe>(); ((Object)val).name = name; val.m_amount = recipeConfig.amount; val.m_minStationLevel = recipeConfig.minStationLevel; val.m_item = itemPrefab.GetComponent<ItemDrop>(); val.m_enabled = recipeConfig.enabled; if (!string.IsNullOrEmpty(recipeConfig.craftingStation)) { if (!CraftingStations.ContainsKey(recipeConfig.craftingStation)) { Debug.LogWarning((object)("[PrefabCreator] Could not find crafting station (" + itemId + "): " + recipeConfig.craftingStation)); string text = string.Join(", ", CraftingStations.Keys); Debug.Log((object)("[PrefabCreator] Available Stations: " + text)); } else { val.m_craftingStation = CraftingStations[recipeConfig.craftingStation]; } } if (!string.IsNullOrEmpty(recipeConfig.repairStation)) { if (!CraftingStations.ContainsKey(recipeConfig.repairStation)) { Debug.LogWarning((object)("[PrefabCreator] Could not find repair station (" + itemId + "): " + recipeConfig.repairStation)); string text2 = string.Join(", ", CraftingStations.Keys); Debug.Log((object)("[PrefabCreator] Available Stations: " + text2)); } else { val.m_repairStation = CraftingStations[recipeConfig.repairStation]; } } List<Requirement> list = new List<Requirement>(); foreach (RecipeRequirementConfig resource in recipeConfig.resources) { GameObject itemPrefab2 = ObjectDB.instance.GetItemPrefab(resource.item); if ((Object)(object)itemPrefab2 == (Object)null) { Debug.LogError((object)("[PrefabCreator] Could not find requirement item (" + itemId + "): " + resource.item)); continue; } list.Add(new Requirement { m_amount = resource.amount, m_resItem = itemPrefab2.GetComponent<ItemDrop>() }); } val.m_resources = list.ToArray(); return val; } public static Recipe AddNewRecipe(string name, string itemId, RecipeConfig recipeConfig) { Recipe val = CreateRecipe(name, itemId, recipeConfig); if ((Object)(object)val == (Object)null) { Debug.LogError((object)("[PrefabCreator] Failed to create recipe (" + name + ")")); return null; } return AddNewRecipe(val); } public static Recipe AddNewRecipe(Recipe recipe) { int num = ObjectDB.instance.m_recipes.RemoveAll((Recipe x) => ((Object)x).name == ((Object)recipe).name); if (num > 0) { Debug.Log((object)$"[PrefabCreator] Removed recipe ({((Object)recipe).name}): {num}"); } ObjectDB.instance.m_recipes.Add(recipe); Debug.Log((object)("[PrefabCreator] Added recipe: " + ((Object)recipe).name)); return recipe; } } public static class Utils { public static void PrintObject(object o) { if (o == null) { Debug.Log((object)"null"); } else { Debug.Log((object)(o?.ToString() + ":\n" + GetObjectString(o, " "))); } } public static string GetObjectString(object obj, string indent) { string text = ""; Type type = obj.GetType(); IEnumerable<FieldInfo> enumerable = from f in type.GetFields() where f.IsPublic select f; foreach (FieldInfo item in enumerable) { object value = item.GetValue(obj); string text2 = ((value == null) ? "null" : value.ToString()); text = text + "\n" + indent + item.Name + ": " + text2; } return text; } public static Sprite LoadSpriteFromFile(string spritePath) { //IL_0024: Unknown result type (might be due to invalid IL or missing references) //IL_002a: Expected O, but got Unknown //IL_004f: 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_005c: Unknown result type (might be due to invalid IL or missing references) spritePath = Path.Combine(Paths.PluginPath, spritePath); if (File.Exists(spritePath)) { byte[] array = File.ReadAllBytes(spritePath); Texture2D val = new Texture2D(20, 20); if (ImageConversion.LoadImage(val, array)) { return Sprite.Create(val, new Rect(0f, 0f, (float)((Texture)val).width, (float)((Texture)val).height), default(Vector2), 100f); } } return null; } public static Sprite LoadSpriteFromFile(string modFolder, string iconName) { string spritePath = Path.Combine(modFolder, iconName); return LoadSpriteFromFile(spritePath); } public static bool IsServer() { //IL_0019: Unknown result type (might be due to invalid IL or missing references) //IL_001f: Invalid comparison between Unknown and I4 return ZNet.instance.IsServer() || ZNet.instance.IsDedicated() || (int)SystemInfo.graphicsDeviceType == 4; } } } namespace BetterArchery { public class Arrow { public float SpawnChance { get; set; } public string SpawnArrow { get; set; } } [BepInPlugin("ishid4.mods.betterarchery", "Better Archery", "1.9.5")] [BepInDependency(/*Could not decode attribute arguments.*/)] public class BetterArchery : BaseUnityPlugin { public enum ZoomState { Fixed, ZoomingIn, ZoomingOut } public static bool zoomSFX; public static Dictionary<string, Dictionary<string, AudioClip>> customSFXDict = new Dictionary<string, Dictionary<string, AudioClip>>(); public static bool speedReduction; public static bool isContainerOpen; public static float ZoomInTimer = 0.1f; public static float ZoomOutTimer; public static float ZoomOutDelayTimer = 0f; public static float __BaseFov; public static float __LastZoomFov; public static float __NewZoomFov = 0f; public static ZoomState __ZoomState; public const int QuiverUseSlotCount = 3; public static int QuiverRowIndex = 0; public static ConfigEntry<KeyboardShortcut> HoldingKeyCode; public static ConfigEntry<KeyboardShortcut>[] KeyCodes = new ConfigEntry<KeyboardShortcut>[3]; public static ConfigEntry<float>[] ArrowRetrieveChance = new ConfigEntry<float>[11]; public static ConfigEntry<string>[] ArrowRetrieveSpawnType = new ConfigEntry<string>[11]; public static List<Arrow> ArrowRetrieves = new List<Arrow>(); public static ConfigEntry<float> ArrowDisappearTime; public static ConfigEntry<bool> ArrowDisappearOnHit; public static ConfigEntry<bool> ArrowRetrieveOldVersion; public static ConfigEntry<Vector2> InventoryQuiverSlotLocation; public static ConfigEntry<Vector2> InventoryQuiverSlotLocationWithContainer; public static ConfigEntry<bool> QuiverHudEnabled; public static ConfigEntry<float> ArrowVelocity; public static ConfigEntry<float> ArrowGravity; public static ConfigEntry<float> ArrowAccuracy; public static ConfigEntry<Vector3> ArrowAimDir; public static ConfigEntry<bool> configQuiverEnabled; public static ConfigEntry<bool> configArrowImprovementsEnabled; public static ConfigEntry<bool> configRetrievableArrowsEnabled; public static ConfigEntry<bool> configBowZoomEnabled; public static ConfigEntry<KeyboardShortcut> BowDrawCancelKey; public static ConfigEntry<float> BowZoomFactor; public static ConfigEntry<bool> AutomaticBowZoom; public static ConfigEntry<KeyboardShortcut> BowZoomKey; public static ConfigEntry<float> BowZoomConstantTime; public static ConfigEntry<bool> BowZoomSFXEnabled; public static ConfigEntry<float> StayInZoomTime; public static ConfigEntry<bool> IsCrosshairVisible; public static ConfigEntry<bool> IsBowCrosshairVisible; public static ConfigEntry<bool> ShowSneakDamage; public static ConfigEntry<bool> BowDrawMovementSpeedReductionEnabled; public static ConfigEntry<int> _DebugLevel; public static RecipesConfig Recipes; public static ConfigEntry<bool> WoodenArrowEverywhereEnabled; public static readonly Dictionary<string, GameObject> Prefabs = new Dictionary<string, GameObject>(); public static ConfigEntry<int> nexusID; public static AudioSource playerAudioSource; private Harmony _harmony; public static BetterArchery _instance; public static bool HasAuga { get; private set; } public static void Log(string str = "", int warningType = 2) { if (_DebugLevel.Value == 0) { return; } if (warningType == 0) { Debug.LogError((object)("[" + typeof(BetterArchery).Namespace + "]: " + str)); } if (_DebugLevel.Value > 1) { if (warningType == 1) { Debug.LogWarning((object)("[" + typeof(BetterArchery).Namespace + "]: " + str)); } if (_DebugLevel.Value > 2 && warningType == 2) { Debug.Log((object)("[" + typeof(BetterArchery).Namespace + "]: " + str)); } } } private void Awake() { //IL_0041: 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_00bd: Unknown result type (might be due to invalid IL or missing references) //IL_00ee: Unknown result type (might be due to invalid IL or missing references) //IL_011b: Unknown result type (might be due to invalid IL or missing references) //IL_0148: Unknown result type (might be due to invalid IL or missing references) //IL_0203: Unknown result type (might be due to invalid IL or missing references) //IL_02d9: Unknown result type (might be due to invalid IL or missing references) //IL_0304: Unknown result type (might be due to invalid IL or missing references) _instance = this; configQuiverEnabled = ((BaseUnityPlugin)this).Config.Bind<bool>("Quiver", "Enable Quiver", true, "Enable the quiver. Don't change this value while in the game. If you disable this while arrows are in the quiver, you will LOSE ALL OF THEM!"); InventoryQuiverSlotLocation = ((BaseUnityPlugin)this).Config.Bind<Vector2>("Quiver", "Change location of inventory quiver slot", new Vector2(3f, -25f), "Change quiver slot inventory location. For 'More Slots' you can use this location, 'x:3.0, y:-167.0'."); InventoryQuiverSlotLocationWithContainer = ((BaseUnityPlugin)this).Config.Bind<Vector2>("Quiver", "Change location of inventory quiver slot when a chest opened", new Vector2(3f, -425f), "Change quiver slot inventory location when a chest opened."); QuiverHudEnabled = ((BaseUnityPlugin)this).Config.Bind<bool>("Quiver", "Enable Quiver Hud", true, "Enable the quiver's hotbar on the screen/hud. This doesn't affect inventory."); HoldingKeyCode = ((BaseUnityPlugin)this).Config.Bind<KeyboardShortcut>("Quiver", "Quiver slot hotkey holding key", new KeyboardShortcut((KeyCode)308, Array.Empty<KeyCode>()), "Change holding key. For the inputs: https://docs.unity3d.com/ScriptReference/KeyCode.html"); KeyCodes[0] = ((BaseUnityPlugin)this).Config.Bind<KeyboardShortcut>("Quiver", "Quiver slot hotkey 1", new KeyboardShortcut((KeyCode)49, Array.Empty<KeyCode>()), "Hotkey for Quiver Slot 1. For the inputs: https://docs.unity3d.com/ScriptReference/KeyCode.html"); KeyCodes[1] = ((BaseUnityPlugin)this).Config.Bind<KeyboardShortcut>("Quiver", "Quiver slot hotkey 2", new KeyboardShortcut((KeyCode)50, Array.Empty<KeyCode>()), "Hotkey for Quiver Slot 2. For the inputs: https://docs.unity3d.com/ScriptReference/KeyCode.html"); KeyCodes[2] = ((BaseUnityPlugin)this).Config.Bind<KeyboardShortcut>("Quiver", "Quiver slot hotkey 3", new KeyboardShortcut((KeyCode)51, Array.Empty<KeyCode>()), "Hotkey for Quiver Slot 3. For the inputs: https://docs.unity3d.com/ScriptReference/KeyCode.html"); configArrowImprovementsEnabled = ((BaseUnityPlugin)this).Config.Bind<bool>("Arrow Improvements", "Enable Arrow Improvements", true, "Arrow improvements including aim problems fixes, gravity changes."); ArrowVelocity = ((BaseUnityPlugin)this).Config.Bind<float>("Arrow Improvements", "Set Arrow Velocity", 70f, "Change the arrow's velocity. Vanilla is '60'."); ArrowGravity = ((BaseUnityPlugin)this).Config.Bind<float>("Arrow Improvements", "Set Arrow Gravity", 15f, "Change the arrow's gravity. Vanilla is '5'."); ArrowAccuracy = ((BaseUnityPlugin)this).Config.Bind<float>("Arrow Improvements", "Set Arrow Accuracy", 0f, "Change the arrow's accuracy. Vanilla is '-1'."); ArrowAimDir = ((BaseUnityPlugin)this).Config.Bind<Vector3>("Arrow Improvements", "Set Aim Direction", new Vector3(0f, 0.05f, 0f), "Change the aim direction. Vanilla is 'x:0.0, y:0.0, z: 0.0'."); configBowZoomEnabled = ((BaseUnityPlugin)this).Config.Bind<bool>("Bow Zoom", "Enable Bow Zoom", true, "Enable the zooming with bow."); AutomaticBowZoom = ((BaseUnityPlugin)this).Config.Bind<bool>("Bow Zoom", "Automatic Bow Zoom", false, "Zoom while drawing bow automatically."); BowZoomSFXEnabled = ((BaseUnityPlugin)this).Config.Bind<bool>("Bow Zoom", "Enable Bow Zoom SFX", true, "Sound effects for zoom-in and zoom-out."); BowZoomFactor = ((BaseUnityPlugin)this).Config.Bind<float>("Bow Zoom", "Zoom Factor", 2f, "Max zoom."); BowZoomConstantTime = ((BaseUnityPlugin)this).Config.Bind<float>("Bow Zoom", "Bow Zoom Constant Time", -1f, "Change this value to '-1' if you don't want constant time while zooming. '1' is recommended."); BowZoomKey = ((BaseUnityPlugin)this).Config.Bind<KeyboardShortcut>("Bow Zoom", "Bow Zoom Hotkey", new KeyboardShortcut((KeyCode)324, Array.Empty<KeyCode>()), "Mouse0: Left Click, Mouse1: Right Click, Mouse2: Middle Click. For the other inputs: https://docs.unity3d.com/ScriptReference/KeyCode.html"); BowDrawCancelKey = ((BaseUnityPlugin)this).Config.Bind<KeyboardShortcut>("Bow Zoom", "Bow Draw Cancel Hotkey", new KeyboardShortcut((KeyCode)101, Array.Empty<KeyCode>()), "Mouse0: Left Click, Mouse1: Right Click, Mouse2: Middle Click. For the other inputs: https://docs.unity3d.com/ScriptReference/KeyCode.html"); StayInZoomTime = ((BaseUnityPlugin)this).Config.Bind<float>("Bow Zoom", "Stay In-Zoom Time", 2f, "Set the max time of staying on zoom while holding RMB after releasing an arrow."); IsCrosshairVisible = ((BaseUnityPlugin)this).Config.Bind<bool>("Other", "Enable Crosshair", true, "You can hide your crosshair."); IsBowCrosshairVisible = ((BaseUnityPlugin)this).Config.Bind<bool>("Other", "Enable Bow Crosshair", true, "You can hide your bow crosshair, circle one."); ShowSneakDamage = ((BaseUnityPlugin)this).Config.Bind<bool>("Other", "Enable Sneak Damage Showing", true, "Show sneak damage at top left."); BowDrawMovementSpeedReductionEnabled = ((BaseUnityPlugin)this).Config.Bind<bool>("Other", "Enable Bow Draw Movement Speed Reduction", true, "Set walk speed while drawing bow."); WoodenArrowEverywhereEnabled = ((BaseUnityPlugin)this).Config.Bind<bool>("Other", "Enable Crafting Wooden Arrow Everywhere", true, "Enable to crafting wooden arrows without a crafting table."); configRetrievableArrowsEnabled = ((BaseUnityPlugin)this).Config.Bind<bool>("Retrievable Arrows", "Enable Retrievable Arrows", true, "Enable the retrievable arrows."); ArrowDisappearTime = ((BaseUnityPlugin)this).Config.Bind<float>("Retrievable Arrows", "Arrow Disappear Time", 60f, "Set arrow's disappear countdown time."); ArrowDisappearOnHit = ((BaseUnityPlugin)this).Config.Bind<bool>("Retrievable Arrows", "Arrow Disappear On Hit", false, "Make arrows disappear when they are not retrievable."); ArrowRetrieveOldVersion = ((BaseUnityPlugin)this).Config.Bind<bool>("Retrievable Arrows", "Enable Old Retrievable Version", false, "Instantly arrow drops to the ground on hit if retrievable. Enabling this will ignore 'Arrow Disappear On Hit' and 'Arrow Disappear Time' settings."); ArrowRetrieveChance[0] = ((BaseUnityPlugin)this).Config.Bind<float>("Retrievable Arrows", "ArrowRetrieveChance for Wooden Arrow", 0.2f, "Example: 0.9 for 90% chance to retrieve."); ArrowRetrieveChance[1] = ((BaseUnityPlugin)this).Config.Bind<float>("Retrievable Arrows", "ArrowRetrieveChance for Flint Arrow", 0.3f, "Example: 0.9 for 90% chance to retrieve."); ArrowRetrieveChance[2] = ((BaseUnityPlugin)this).Config.Bind<float>("Retrievable Arrows", "ArrowRetrieveChance for Bronze Arrow", 0.5f, "Example: 0.9 for 90% chance to retrieve."); ArrowRetrieveChance[3] = ((BaseUnityPlugin)this).Config.Bind<float>("Retrievable Arrows", "ArrowRetrieveChance for Iron Arrow", 0.7f, "Example: 0.9 for 90% chance to retrieve."); ArrowRetrieveChance[4] = ((BaseUnityPlugin)this).Config.Bind<float>("Retrievable Arrows", "ArrowRetrieveChance for Obsidian Arrow", 0.7f, "Example: 0.9 for 90% chance to retrieve."); ArrowRetrieveChance[5] = ((BaseUnityPlugin)this).Config.Bind<float>("Retrievable Arrows", "ArrowRetrieveChance for Needle Arrow", 0.1f, "Example: 0.9 for 90% chance to retrieve."); ArrowRetrieveChance[6] = ((BaseUnityPlugin)this).Config.Bind<float>("Retrievable Arrows", "ArrowRetrieveChance for Fire Arrow", 0f, "Example: 0.9 for 90% chance to retrieve."); ArrowRetrieveChance[7] = ((BaseUnityPlugin)this).Config.Bind<float>("Retrievable Arrows", "ArrowRetrieveChance for Poison Arrow", 0.7f, "Example: 0.9 for 90% chance to retrieve."); ArrowRetrieveChance[8] = ((BaseUnityPlugin)this).Config.Bind<float>("Retrievable Arrows", "ArrowRetrieveChance for Silver Arrow", 0.5f, "Example: 0.9 for 90% chance to retrieve."); ArrowRetrieveChance[9] = ((BaseUnityPlugin)this).Config.Bind<float>("Retrievable Arrows", "ArrowRetrieveChance for Frost Arrow", 0.7f, "Example: 0.9 for 90% chance to retrieve."); ArrowRetrieveChance[10] = ((BaseUnityPlugin)this).Config.Bind<float>("Retrievable Arrows", "ArrowRetrieveChance for Carapace Arrow", 0.7f, "Example: 0.9 for 90% chance to retrieve."); ArrowRetrieveSpawnType[0] = ((BaseUnityPlugin)this).Config.Bind<string>("Retrievable Arrows", "ArrowRetrieveSpawnType for Wooden Arrow", "ArrowWood", "https://valheim.fandom.com/wiki/Category:Arrows use internal ids."); ArrowRetrieveSpawnType[1] = ((BaseUnityPlugin)this).Config.Bind<string>("Retrievable Arrows", "ArrowRetrieveSpawnType for Flint Arrow", "ArrowFlint", "https://valheim.fandom.com/wiki/Category:Arrows use internal ids."); ArrowRetrieveSpawnType[2] = ((BaseUnityPlugin)this).Config.Bind<string>("Retrievable Arrows", "ArrowRetrieveSpawnType for Bronze Arrow", "ArrowBronze", "https://valheim.fandom.com/wiki/Category:Arrows use internal ids."); ArrowRetrieveSpawnType[3] = ((BaseUnityPlugin)this).Config.Bind<string>("Retrievable Arrows", "ArrowRetrieveSpawnType for Iron Arrow", "ArrowIron", "https://valheim.fandom.com/wiki/Category:Arrows use internal ids."); ArrowRetrieveSpawnType[4] = ((BaseUnityPlugin)this).Config.Bind<string>("Retrievable Arrows", "ArrowRetrieveSpawnType for Obsidian Arrow", "ArrowObsidian", "https://valheim.fandom.com/wiki/Category:Arrows use internal ids."); ArrowRetrieveSpawnType[5] = ((BaseUnityPlugin)this).Config.Bind<string>("Retrievable Arrows", "ArrowRetrieveSpawnType for Needle Arrow", "ArrowNeedle", "https://valheim.fandom.com/wiki/Category:Arrows use internal ids."); ArrowRetrieveSpawnType[6] = ((BaseUnityPlugin)this).Config.Bind<string>("Retrievable Arrows", "ArrowRetrieveSpawnType for Fire Arrow", "ArrowFire", "https://valheim.fandom.com/wiki/Category:Arrows use internal ids."); ArrowRetrieveSpawnType[7] = ((BaseUnityPlugin)this).Config.Bind<string>("Retrievable Arrows", "ArrowRetrieveSpawnType for Poison Arrow", "ArrowObsidian", "https://valheim.fandom.com/wiki/Category:Arrows use internal ids."); ArrowRetrieveSpawnType[8] = ((BaseUnityPlugin)this).Config.Bind<string>("Retrievable Arrows", "ArrowRetrieveSpawnType for Silver Arrow", "ArrowSilver", "https://valheim.fandom.com/wiki/Category:Arrows use internal ids."); ArrowRetrieveSpawnType[9] = ((BaseUnityPlugin)this).Config.Bind<string>("Retrievable Arrows", "ArrowRetrieveSpawnType for Frost Arrow", "ArrowObsidian", "https://valheim.fandom.com/wiki/Category:Arrows use internal ids."); ArrowRetrieveSpawnType[10] = ((BaseUnityPlugin)this).Config.Bind<string>("Retrievable Arrows", "ArrowRetrieveSpawnType for Carapace Arrow", "ArrowCarapace", "https://valheim.fandom.com/wiki/Category:Arrows use internal ids."); for (int i = 0; i < ArrowRetrieveSpawnType.Length; i++) { ArrowRetrieves.Add(new Arrow { SpawnChance = ArrowRetrieveChance[i].Value, SpawnArrow = ArrowRetrieveSpawnType[i].Value }); } nexusID = ((BaseUnityPlugin)this).Config.Bind<int>("Other", "NexusID", 348, "Nexus mod ID for updates."); _DebugLevel = ((BaseUnityPlugin)this).Config.Bind<int>("Other", "Set Debug Log Level", 1, "0: Nothing, 1: Only Errors, 2: Errors and Warnings, 3: Everyting"); Recipes = LoadJsonFile<RecipesConfig>("BetterArcheryRecipes.json"); if (configQuiverEnabled.Value) { AssetBundle val = LoadAssetBundle("quiverassets"); if (Recipes != null && (Object)(object)val != (Object)null) { foreach (RecipeConfig recipe in Recipes.recipes) { if (val.Contains(recipe.item)) { GameObject value = val.LoadAsset<GameObject>(recipe.item); Prefabs.Add(recipe.item, value); } } } if (val != null) { val.Unload(false); } } Dictionary<string, object> dictionary = LoadTranslationJsonFile<Dictionary<string, object>>("translations.json"); if (dictionary.Count > 0) { LoadTranslations(dictionary); } _harmony = Harmony.CreateAndPatchAll(Assembly.GetExecutingAssembly(), (string)null); HasAuga = API.IsLoaded(); } public void Start() { HasAuga = API.IsLoaded(); if (HasAuga) { Log("Auga Loaded."); } } private void OnDestroy() { Harmony harmony = _harmony; if (harmony != null) { harmony.UnpatchAll((string)null); } foreach (GameObject value in Prefabs.Values) { Object.Destroy((Object)(object)value); } Prefabs.Clear(); } private void Update() { if (!configQuiverEnabled.Value) { return; } Player localPlayer = Player.m_localPlayer; if ((Object)(object)localPlayer != (Object)null && ((Character)localPlayer).TakeInput()) { for (int i = 0; i < 3; i++) { CheckQuiverUseInput(localPlayer, i); } } } private static void LoadTranslations(Dictionary<string, object> translations) { if (translations == null) { Log("Could not parse translations.json!", 3); return; } List<KeyValuePair<string, string>> list = Localization.instance.m_translations.Where((KeyValuePair<string, string> instanceMTranslation) => instanceMTranslation.Key.StartsWith("mod_betterarchery_")).ToList(); foreach (KeyValuePair<string, string> item in list) { Localization.instance.m_translations.Remove(item.Key); } foreach (KeyValuePair<string, object> translation in translations) { Localization.instance.AddWord(translation.Key, translation.Value.ToString()); } } public static string GetBindingLabel(int index) { //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) index = Mathf.Clamp(index, 0, 2); KeyCode bindingKeycode = GetBindingKeycode(index); if (((object)(KeyCode)(ref bindingKeycode)).ToString().Contains("Alpha")) { return ((object)(KeyCode)(ref bindingKeycode)).ToString().Replace("Alpha", ""); } return ((object)(KeyCode)(ref bindingKeycode)).ToString().ToUpperInvariant(); } public static KeyCode GetBindingKeycode(int index) { //IL_0012: 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_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_0022: Unknown result type (might be due to invalid IL or missing references) index = Mathf.Clamp(index, 0, 2); KeyboardShortcut value = KeyCodes[index].Value; return ((KeyboardShortcut)(ref value)).MainKey; } public static int GetBonusInventoryRowIndex() { if ((Object)(object)Player.m_localPlayer != (Object)null && QuiverRowIndex != 0) { return QuiverRowIndex; } return 0; } public static void CheckQuiverUseInput(Player player, int index) { //IL_0002: Unknown result type (might be due to invalid IL or missing references) //IL_0007: Unknown result type (might be due to invalid IL or missing references) //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_0026: Unknown result type (might be due to invalid IL or missing references) //IL_002b: Unknown result type (might be due to invalid IL or missing references) //IL_0069: Unknown result type (might be due to invalid IL or missing references) //IL_0049: 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_0051: Unknown result type (might be due to invalid IL or missing references) //IL_005d: Unknown result type (might be due to invalid IL or missing references) KeyCode bindingKeycode = GetBindingKeycode(index); KeyboardShortcut value = HoldingKeyCode.Value; bool flag; if (!string.IsNullOrEmpty(((KeyboardShortcut)(ref value)).Serialize())) { value = HoldingKeyCode.Value; if (((KeyboardShortcut)(ref value)).Serialize() != "None") { value = HoldingKeyCode.Value; flag = Input.GetKey(((KeyboardShortcut)(ref value)).MainKey) && Input.GetKeyDown(bindingKeycode); goto IL_0070; } } flag = Input.GetKeyDown(bindingKeycode); goto IL_0070; IL_0070: if (flag) { int bonusInventoryRowIndex = GetBonusInventoryRowIndex(); ItemData itemAt = ((Humanoid)player).GetInventory().GetItemAt(index, bonusInventoryRowIndex); if (itemAt != null) { ((Humanoid)player).UseItem((Inventory)null, itemAt, false); } } } public static bool IsQuiverSlot(Vector2i pos) { //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) return IsQuiverSlot(pos.x, pos.y); } public static bool IsQuiverSlot(int x, int y) { int bonusInventoryRowIndex = GetBonusInventoryRowIndex(); return y == bonusInventoryRowIndex && x >= 0 && x < 3; } public static Vector2i GetQuiverSlotPosition(int index) { //IL_0009: Unknown result type (might be due to invalid IL or missing references) //IL_000e: Unknown result type (might be due to invalid IL or missing references) //IL_0011: Unknown result type (might be due to invalid IL or missing references) int bonusInventoryRowIndex = GetBonusInventoryRowIndex(); return new Vector2i(index, bonusInventoryRowIndex); } public static bool IsQuiverEquipped() { if ((Object)(object)Player.m_localPlayer == (Object)null) { return false; } return CustomSlotCreator.IsSlotOccupied((Humanoid)(object)Player.m_localPlayer, "quiver"); } private static T LoadJsonFile<T>(string filename) where T : class { string assetPath = GetAssetPath(filename); if (!string.IsNullOrEmpty(assetPath)) { string json = File.ReadAllText(assetPath); return JsonMapper.ToObject<T>(json); } return null; } private static Dictionary<string, object> LoadTranslationJsonFile<T>(string filename) where T : class { string assetPath = GetAssetPath(filename); if (!string.IsNullOrEmpty(assetPath)) { string json = File.ReadAllText(assetPath); return JsonMapper.ToObject<Dictionary<string, object>>(json); } return null; } public static AssetBundle LoadAssetBundle(string filename) { Assembly callingAssembly = Assembly.GetCallingAssembly(); AssetBundle result = AssetBundle.LoadFromStream(callingAssembly.GetManifestResourceStream(callingAssembly.GetName().Name + "." + filename)); Log("Loaded AssetBundle (" + filename + ").", 3); Log(callingAssembly.GetName().Name); return result; } public static string GetAssetPath(string assetName, bool isDirectory = false) { string text = Path.Combine(Paths.PluginPath, "BetterArchery", assetName); if (isDirectory) { if (!Directory.Exists(text)) { Assembly assembly = typeof(BetterArchery).Assembly; text = Path.Combine(Path.GetDirectoryName(assembly.Location), assetName); if (!Directory.Exists(text)) { Log("Could not find directory (" + assetName + ").", 1); return null; } } return text; } if (!File.Exists(text)) { Assembly assembly2 = typeof(BetterArchery).Assembly; text = Path.Combine(Path.GetDirectoryName(assembly2.Location), assetName); if (!File.Exists(text)) { Log("Could not find asset (" + assetName + ").", 1); return null; } } return text; } public static void TryCreateCustomSlot(ZNetScene zNetScene) { if (!((Object)(object)zNetScene == (Object)null) && configQuiverEnabled.Value) { GameObject prefab = zNetScene.GetPrefab("LeatherQuiver"); CustomSlotCreator.ApplyCustomSlotItem(prefab, "quiver"); } } public static void TryCreateCustomSFX() { if (!configBowZoomEnabled.Value || !BowZoomSFXEnabled.Value) { return; } string assetPath = GetAssetPath("SFX", isDirectory: true); if (string.IsNullOrEmpty(assetPath)) { Log("SFX folder not found."); return; } Log("path: " + assetPath); string[] directories = Directory.GetDirectories(assetPath); foreach (string path in directories) { Log("Checking folder " + Path.GetFileName(path)); customSFXDict[Path.GetFileName(path)] = new Dictionary<string, AudioClip>(); string[] files = Directory.GetFiles(path); foreach (string path2 in files) { if (Path.GetExtension(path2).ToLower().Equals(".wav")) { Log("Checking file " + Path.GetFileName(path2)); ((MonoBehaviour)_instance).StartCoroutine(LoadSFXCoroutine(path2, customSFXDict[Path.GetFileName(path)])); } } } } public static void PlayCustomSFX(string name, bool checkIfPlaying = true) { if ((Object)(object)playerAudioSource == (Object)null || !BowZoomSFXEnabled.Value) { return; } ZSFX component = ((Component)playerAudioSource).GetComponent<ZSFX>(); if (!(component.IsPlaying() && checkIfPlaying)) { if (customSFXDict.ContainsKey(name)) { component.m_audioClips = customSFXDict[name].Values.ToArray(); component.Play(); } else { Log("SFX not found.", 0); } } } public static IEnumerator LoadSFXCoroutine(string path, Dictionary<string, AudioClip> dict) { path = "file:///" + path; UnityWebRequest www = UnityWebRequestMultimedia.GetAudioClip(path, (AudioType)20); try { yield return www.SendWebRequest(); if (www == null) { Log("ww error.", 0); yield break; } DownloadHandlerAudioClip dh = (DownloadHandlerAudioClip)www.downloadHandler; if (dh != null) { AudioClip ac = dh.audioClip; if ((Object)(object)ac != (Object)null) { ((Object)ac).name = Path.GetFileNameWithoutExtension(path); if (!dict.ContainsKey(((Object)ac).name)) { dict[((Object)ac).name] = ac; } Log("Added " + ((Object)ac).name + " SFX."); yield break; } } Log("Error while adding custom SFX.", 0); } finally { ((IDisposable)www)?.Dispose(); } } public static void TryRegisterPrefabs(ZNetScene zNetScene) { if ((Object)(object)zNetScene == (Object)null) { return; } foreach (GameObject value in Prefabs.Values) { if (!configQuiverEnabled.Value) { Log(((Object)value).name); if (((Object)value).name.Contains("Quiver")) { Debug.Log((object)("[PrefabCreator] " + ((Object)value).name + " prefab skipped.")); continue; } } if (!zNetScene.m_prefabs.Contains(value)) { zNetScene.m_prefabs.Add(value); } } } public static bool IsObjectDBReady() { return (Object)(object)ObjectDB.instance != (Object)null && ObjectDB.instance.m_items.Count != 0 && (Object)(object)ObjectDB.instance.GetItemPrefab("Amber") != (Object)null; } public static void TryRegisterItems() { if (!IsObjectDBReady()) { return; } foreach (GameObject value in Prefabs.Values) { ItemDrop component = value.GetComponent<ItemDrop>(); if ((Object)(object)component != (Object)null) { if (!configQuiverEnabled.Value && ((Object)component.m_itemData.m_dropPrefab).name.Contains("Quiver")) { Debug.Log((object)("[PrefabCreator] Skipped prefab: " + ((Object)component.m_itemData.m_dropPrefab).name)); } else if ((Object)(object)ObjectDB.instance.GetItemPrefab(StringExtensionMethods.GetStableHashCode(((Object)value).name)) == (Object)null) { component.m_itemData.m_dropPrefab = value; ObjectDB.instance.m_items.Add(value); } } } ObjectDB.instance.UpdateItemHashes(); } public static void TryRegisterRecipes() { if (!IsObjectDBReady()) { return; } PrefabCreator.Reset(); foreach (RecipeConfig recipe in Recipes.recipes) { if (!configQuiverEnabled.Value && recipe.item.Contains("Quiver")) { Debug.Log((object)("[PrefabCreator] Skipped recipe: " + recipe.name)); } else if (!WoodenArrowEverywhereEnabled.Value && recipe.name == "Recipe_ArrowWoodAnywhere") { Debug.Log((object)("[PrefabCreator] Skipped recipe: " + recipe.name)); } else { PrefabCreator.AddNewRecipe(recipe.name, recipe.item, recipe); } } } } [HarmonyPatch(typeof(Terminal), "InitTerminal")] public static class TerminalAwake_Patch { [Serializable] [CompilerGenerated] private sealed class <>c { public static readonly <>c <>9 = new <>c(); public static ConsoleEvent <>9__0_0; internal void <Postfix>b__0_0(ConsoleEventArgs args) { //IL_01c7: Unknown result type (might be due to invalid IL or missing references) if (args.Length < 2) { args.Context.AddString("Syntax: ba [action]"); return; } switch (args.FullLine.Substring(args[0].Length + 1)) { case "reload": ((BaseUnityPlugin)BetterArchery._instance).Config.Reload(); args.Context.AddString("Better Archery Reloaded."); args.Context.AddString(Localization.instance.Localize("$mod_betterarchery_test")); break; case "drop": { Inventory inventory = ((Humanoid)Player.m_localPlayer).m_inventory; for (int num = inventory.m_inventory.Count - 1; num >= 0; num--) { ItemData val = inventory.m_inventory[num]; if (val.m_gridPos.y >= 5 && !BetterArchery.IsQuiverSlot(val.m_gridPos)) { BetterArchery.Log($"Found {((Object)val.m_dropPrefab).name} x {val.m_stack} in invisible slots; attempting to drop."); ((Humanoid)Player.m_localPlayer).DropItem(inventory, val, val.m_stack); } } break; } case "god": Player.m_localPlayer.SetGodMode(!Player.m_localPlayer.m_godMode); Player.m_localPlayer.SetNoPlacementCost(!Player.m_localPlayer.m_noPlacementCost); Player.m_localPlayer.m_staminaRegenDelay = 0.05f; Player.m_localPlayer.m_staminaRegen = 999f; Player.m_localPlayer.m_runStaminaDrain = 0f; Player.m_localPlayer.SetMaxStamina(9999f, true); ((Character)Player.m_localPlayer).AddStamina(999f); break; case "clear": ((Humanoid)Player.m_localPlayer).GetInventory().RemoveAll(); break; case "sfx": BetterArchery.PlayCustomSFX("exhale"); break; case "kill": ((Character)Player.m_localPlayer).SetHealth(0f); break; case "fill": { for (int i = 0; i < 32; i++) { ((Humanoid)Player.m_localPlayer).m_inventory.AddItem(ObjectDB.instance.GetItemPrefab("Wood"), 100); } break; } default: args.Context.AddString("Syntax: ba [action]"); break; } } } public static void Postfix() { //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_0040: Expected O, but got Unknown //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_002a: Expected O, but got Unknown object obj = <>c.<>9__0_0; if (obj == null) { ConsoleEvent val = delegate(ConsoleEventArgs args) { //IL_01c7: Unknown result type (might be due to invalid IL or missing references) if (args.Length < 2) { args.Context.AddString("Syntax: ba [action]"); } else { switch (args.FullLine.Substring(args[0].Length + 1)) { case "reload": ((BaseUnityPlugin)BetterArchery._instance).Config.Reload(); args.Context.AddString("Better Archery Reloaded."); args.Context.AddString(Localization.instance.Localize("$mod_betterarchery_test")); break; case "drop": { Inventory inventory = ((Humanoid)Player.m_localPlayer).m_inventory; for (int num = inventory.m_inventory.Count - 1; num >= 0; num--) { ItemData val3 = inventory.m_inventory[num]; if (val3.m_gridPos.y >= 5 && !BetterArchery.IsQuiverSlot(val3.m_gridPos)) { BetterArchery.Log($"Found {((Object)val3.m_dropPrefab).name} x {val3.m_stack} in invisible slots; attempting to drop."); ((Humanoid)Player.m_localPlayer).DropItem(inventory, val3, val3.m_stack); } } break; } case "god": Player.m_localPlayer.SetGodMode(!Player.m_localPlayer.m_godMode); Player.m_localPlayer.SetNoPlacementCost(!Player.m_localPlayer.m_noPlacementCost); Player.m_localPlayer.m_staminaRegenDelay = 0.05f; Player.m_localPlayer.m_staminaRegen = 999f; Player.m_localPlayer.m_runStaminaDrain = 0f; Player.m_localPlayer.SetMaxStamina(9999f, true); ((Character)Player.m_localPlayer).AddStamina(999f); break; case "clear": ((Humanoid)Player.m_localPlayer).GetInventory().RemoveAll(); break; case "sfx": BetterArchery.PlayCustomSFX("exhale"); break; case "kill": ((Character)Player.m_localPlayer).SetHealth(0f); break; case "fill": { for (int i = 0; i < 32; i++) { ((Humanoid)Player.m_localPlayer).m_inventory.AddItem(ObjectDB.instance.GetItemPrefab("Wood"), 100); } break; } default: args.Context.AddString("Syntax: ba [action]"); break; } } }; <>c.<>9__0_0 = val; obj = (object)val; } ConsoleCommand val2 = new ConsoleCommand("ba", "[action]", (ConsoleEvent)obj, false, false, false, false, false, (ConsoleOptionsFetcher)null, false, false, false) { IsCheat = false }; } } [HarmonyPatch] public class Patches { [HarmonyPatch(typeof(ItemData), "IsEquipable")] [HarmonyPostfix] private static void IsEquipablePostfix(ref bool __result, ref ItemData __instance) { __result = __result || CustomSlotCreator.IsCustomSlotItem(__instance); } [HarmonyPatch(typeof(Humanoid), "Awake")] [HarmonyPostfix] private static void HumanoidEntryPostfix(ref Humanoid __instance) { CustomSlotCreator.customSlotItemData[__instance] = new Dictionary<string, ItemData>(); } [HarmonyPatch(typeof(Player), "Load")] [HarmonyPostfix] private static void InventoryLoadPostfix(ref Player __instance) { foreach (ItemData equippedItem in ((Humanoid)__instance).m_inventory.GetEquippedItems()) { if (CustomSlotCreator.IsCustomSlotItem(equippedItem)) { string customSlotName = CustomSlotCreator.GetCustomSlotName(equippedItem); CustomSlotCreator.SetSlotItem((Humanoid)(object)__instance, customSlotName, equippedItem); } } } [HarmonyPostfix] [HarmonyPatch(typeof(Humanoid), "EquipItem")] private static void EquipItemPostfix(ref bool __result, ref Humanoid __instance, ItemData item, bool triggerEquipEffects = true) { if (CustomSlotCreator.IsCustomSlotItem(item)) { string customSlotName = CustomSlotCreator.GetCustomSlotName(item); if (CustomSlotCreator.IsSlotOccupied(__instance, customSlotName)) { __instance.UnequipItem(CustomSlotCreator.GetSlotItem(__instance, customSlotName), triggerEquipEffects); } CustomSlotCreator.SetSlotItem(__instance, customSlotName, item); if (__instance.IsItemEquiped(item)) { item.m_equipped = true; } __instance.SetupEquipment(); if (triggerEquipEffects) { __instance.TriggerEquipEffect(item); } __result = true; } } [HarmonyPostfix] [HarmonyPatch(typeof(Humanoid), "UnequipItem")] private static void UnequipItemPostfix(ref Humanoid __instance, ItemData item, bool triggerEquipEffects = true) { if (CustomSlotCreator.IsCustomSlotItem(item)) { string customSlotName = CustomSlotCreator.GetCustomSlotName(item); if (item == CustomSlotCreator.GetSlotItem(__instance, customSlotName)) { CustomSlotCreator.SetSlotItem(__instance, customSlotName, null); } __instance.UpdateEquipmentStatusEffects(); } } [HarmonyPatch(typeof(Humanoid), "IsItemEquiped")] [HarmonyPostfix] private static void IsItemEquipedPostfix(ref bool __result, ref Humanoid __instance, ItemData item) { if (CustomSlotCreator.IsCustomSlotItem(item)) { string customSlotName = CustomSlotCreator.GetCustomSlotName(item); bool flag = CustomSlotCreator.DoesSlotExist(__instance, customSlotName) && CustomSlotCreator.GetSlotItem(__instance, customSlotName) == item; __result |= flag; } } [HarmonyPatch(typeof(Humanoid), "GetEquipmentWeight")] [HarmonyPostfix] private static void GetEquipmentWeightPostfix(ref float __result, ref Humanoid __instance) { foreach (string key in CustomSlotCreator.customSlotItemData[__instance].Keys) { if (CustomSlotCreator.IsSlotOccupied(__instance, key)) { __result += CustomSlotCreator.GetSlotItem(__instance, key).m_shared.m_weight; } } } [HarmonyPostfix] [HarmonyPatch(typeof(Humanoid), "UnequipAllItems")] private static void UnequipAllItemsPostfix(ref Humanoid __instance) { foreach (string item in CustomSlotCreator.customSlotItemData[__instance].Keys.ToList()) { if (CustomSlotCreator.IsSlotOccupied(__instance, item)) { __instance.UnequipItem(CustomSlotCreator.GetSlotItem(__instance, item), false); } } } [HarmonyPostfix] [HarmonyPatch(typeof(Humanoid), "GetSetCount")] private static void GetSetCountPostfix(ref int __result, ref Humanoid __instance, string setName) { foreach (string item in CustomSlotCreator.customSlotItemData[__instance].Keys.ToList()) { if (CustomSlotCreator.IsSlotOccupied(__instance, item) && CustomSlotCreator.GetSlotItem(__instance, item).m_shared.m_setName == setName) { __result++; } } } public static HashSet<StatusEffect> GetStatusEffectsFromCustomSlotItems(Humanoid __instance) { HashSet<StatusEffect> hashSet = new HashSet<StatusEffect>(); foreach (string key in CustomSlotCreator.customSlotItemData[__instance].Keys) { if (CustomSlotCreator.IsSlotOccupied(__instance, key)) { if (Object.op_Implicit((Object)(object)CustomSlotCreator.GetSlotItem(__instance, key).m_shared.m_equipStatusEffect)) { StatusEffect equipStatusEffect = CustomSlotCreator.GetSlotItem(__instance, key).m_shared.m_equipStatusEffect; hashSet.Add(equipStatusEffect); } if (__instance.HaveSetEffect(CustomSlotCreator.GetSlotItem(__instance, key))) { StatusEffect setStatusEffect = CustomSlotCreator.GetSlotItem(__instance, key).m_shared.m_setStatusEffect; hashSet.Add(setStatusEffect); } } } return hashSet; } } [HarmonyPatch(typeof(InventoryGrid), "OnLeftClick")] public static class InventoryGrid_OnLeftClick_Patch { public static bool Prefix(InventoryGrid __instance, UIInputHandler clickHandler) { //IL_0024: 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_0030: 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) if (!BetterArchery.configQuiverEnabled.Value) { return true; } GameObject gameObject = ((Component)clickHandler).gameObject; Vector2i buttonPos = __instance.GetButtonPos(gameObject); ItemData itemAt = __instance.m_inventory.GetItemAt(buttonPos.x, buttonPos.y); if ((Input.GetKey((KeyCode)306) || Input.GetKey((KeyCode)305)) && itemAt != null && itemAt.m_equipped && ((Object)itemAt.m_dropPrefab).name.Contains("Quiver")) { MessageHud.instance.ShowMessage((MessageType)2, "$mod_betterarchery_quiver_equipped_error", 0, (Sprite)null); return false; } return true; } } [HarmonyPatch(typeof(InventoryGrid), "UpdateGui", new Type[] { typeof(Player), typeof(ItemData) })] public static class InventoryGrid_UpdateGui_Patch { public static Vector2 customLocation; private static void Postfix(InventoryGrid __instance, Player player, ItemData dragItem, List<Element> ___m_elements) { if (((Object)__instance).name != "PlayerGrid" || !BetterArchery.configQuiverEnabled.Value) { return; } if (__instance.GetInventory().GetHeight() > 5) { if (GetElement(___m_elements, 7, __instance.GetInventory().GetHeight() - 1).m_go.activeSelf) { for (int i = __instance.GetInventory().GetHeight() - 2; i < __instance.GetInventory().GetHeight(); i++) { for (int j = 0; j < 8; j++) { Element element = GetElement(___m_elements, j, i); element.m_go.SetActive(false); } } } } else if (GetElement(___m_elements, 7, __instance.GetInventory().GetHeight() - 1).m_go.activeSelf) { for (int k = __instance.GetInventory().GetHeight() - 1; k < __instance.GetInventory().GetHeight(); k++) { for (int l = 0; l < 8; l++) { Element element2 = GetElement(___m_elements, l, k); element2.m_go.SetActive(false); } } } if (BetterArchery.IsQuiverEquipped()) { CreateQuiverSlots(__instance, ___m_elements); } else { RemoveQuiverSlots(__instance, ___m_elements); } } public static void CreateQuiverSlots(InventoryGrid __instance, List<Element> ___m_elements) { //IL_0019: 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_001e: 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_0042: 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_0067: Unknown result type (might be due to invalid IL or missing references) //IL_0078: Unknown result type (might be due to invalid IL or missing references) //IL_02fd: Unknown result type (might be due to invalid IL or missing references) //IL_030d: Unknown result type (might be due to invalid IL or missing references) //IL_0312: Unknown result type (might be due to invalid IL or missing references) //IL_0433: Unknown result type (might be due to invalid IL or missing references) //IL_046b: Unknown result type (might be due to invalid IL or missing references) //IL_0108: Unknown result type (might be due to invalid IL or missing references) //IL_0118: Unknown result type (might be due to invalid IL or missing references) //IL_011d: Unknown result type (might be due to invalid IL or missing references) //IL_022e: Unknown result type (might be due to invalid IL or missing references) //IL_0266: Unknown result type (might be due to invalid IL or missing references) //IL_0327: Unknown result type (might be due to invalid IL or missing references) //IL_032c: Unknown result type (might be due to invalid IL or missing references) //IL_0132: 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_0360: Unknown result type (might be due to invalid IL or missing references) //IL_0365: Unknown result type (might be due to invalid IL or missing references) //IL_0369: Unknown result type (might be due to invalid IL or missing references) //IL_036e: Unknown result type (might be due to invalid IL or missing references) //IL_016b: Unknown result type (might be due to invalid IL or missing references) //IL_0170: Unknown result type (might be due to invalid IL or missing references) //IL_0174: Unknown result type (might be due to invalid IL or missing references) //IL_0179: Unknown result type (might be due to invalid IL or missing references) //IL_0394: Unknown result type (might be due to invalid IL or missing references) //IL_0399: Unknown result type (might be due to invalid IL or missing references) //IL_03ca: Unknown result type (might be due to invalid IL or missing references) //IL_03cc: Unknown result type (might be due to invalid IL or missing references) //IL_03ce: Unknown result type (might be due to invalid IL or missing references) //IL_019f: Unknown result type (might be due to invalid IL or missing references) //IL_01a4: Unknown result type (might be due to invalid IL or missing references) //IL_01db: Unknown result type (might be due to invalid IL or missing references) //IL_01dd: Unknown result type (might be due to invalid IL or missing references) //IL_01df: Unknown result type (might be due to invalid IL or missing references) Vector2 val = (BetterArchery.isContainerOpen ? BetterArchery.InventoryQuiverSlotLocationWithContainer.Value : BetterArchery.InventoryQuiverSlotLocation.Value); Transform val2 = ((Component)__instance).transform.parent.Find("QuiverSlotBkg"); if (Object.op_Implicit((Object)(object)val2) && customLocation == val) { return; } int bonusInventoryRowIndex = BetterArchery.GetBonusInventoryRowIndex(); customLocation = (BetterArchery.isContainerOpen ? BetterArchery.InventoryQuiverSlotLocationWithContainer.Value : BetterArchery.InventoryQuiverSlotLocation.Value); KeyboardShortcut value; KeyCode mainKey; if (BetterArchery.HasAuga) { int num; Element element; Vector2 val3; Vector2 val4 = default(Vector2); Transform transform; for (int i = 0; i < 3; val3 = customLocation, ((Vector2)(ref val4))..ctor((float)num * __instance.m_elementSpace, 4f * (0f - __instance.m_elementSpace) + 30f), transform = element.m_go.transform, ((RectTransform)((transform is RectTransform) ? transform : null)).anchoredPosition = val3 + val4, i++) { num = i; element = GetElement(___m_elements, num, bonusInventoryRowIndex); element.m_go.SetActive(true); TMP_Text component = ((Component)element.m_go.transform.Find("binding")).GetComponent<TMP_Text>(); ((Behaviour)component).enabled = true; component.overflowMode = (TextOverflowModes)0; component.fontSize = 11f; component.autoSizeTextContainer = true; component.rectTransform.anchoredPosition = new Vector2(1f, 14f); value = BetterArchery.HoldingKeyCode.Value; if (!string.IsNullOrEmpty(((KeyboardShortcut)(ref value)).Serialize())) { value = BetterArchery.HoldingKeyCode.Value; if (!(((KeyboardShortcut)(ref value)).Serialize() == "None")) { value = BetterArchery.HoldingKeyCode.Value; mainKey = ((KeyboardShortcut)(ref value)).MainKey; component.text = ((object)(KeyCode)(ref mainKey)).ToString() + " + " + BetterArchery.GetBindingLabel(i); continue; } } component.text = BetterArchery.GetBindingLabel(i); } RectTransform orCreateBackground = GetOrCreateBackground(__instance, "QuiverSlotBkg"); orCreateBackground.anchoredPosition = new Vector2(-174f + customLocation.x, -235f + customLocation.y); orCreateBackground.SetSizeWithCurrentAnchors((Axis)0, 235f); orCreateBackground.SetSizeWithCurrentAnchors((Axis)1, 90f); ((Transform)orCreateBackground).localScale = new Vector3(1f, 1f, 1f); return; } int num2; Element element2; Vector2 val5; Vector2 val6 = default(Vector2); Transform transform2; for (int j = 0; j < 3; val5 = customLocation, ((Vector2)(ref val6))..ctor((float)num2 * __instance.m_elementSpace, 4f * (0f - __instance.m_elementSpace)), transform2 = element2.m_go.transform, ((RectTransform)((transform2 is RectTransform) ? transform2 : null)).anchoredPosition = val5 + val6, j++) { num2 = j; element2 = GetElement(___m_elements, num2, bonusInventoryRowIndex); element2.m_go.SetActive(true); TMP_Text component2 = ((Component)element2.m_go.transform.Find("binding")).GetComponent<TMP_Text>(); ((Behaviour)component2).enabled = true; component2.overflowMode = (TextOverflowModes)0; component2.horizontalAlignment = (HorizontalAlignmentOptions)2; component2.fontSize = 11f; component2.autoSizeTextContainer = true; component2.rectTransform.anchoredPosition = new Vector2(28f, -7f); value = BetterArchery.HoldingKeyCode.Value; if (!string.IsNullOrEmpty(((KeyboardShortcut)(ref value)).Serialize())) { value = BetterArchery.HoldingKeyCode.Value; if (!(((KeyboardShortcut)(ref value)).Serialize() == "None")) { value = BetterArchery.HoldingKeyCode.Value; mainKey = ((KeyboardShortcut)(ref value)).MainKey; component2.text = ((object)(KeyCode)(ref mainKey)).ToString() + " + " + BetterArchery.GetBindingLabel(j); continue; } } component2.text = BetterArchery.GetBindingLabel(j); } RectTransform orCreateBackground2 = GetOrCreateBackground(__instance, "QuiverSlotBkg"); float num3 = 3f - customLocation.x; float num4 = -25f - customLocation.y; orCreateBackground2.anchoredPosition = new Vector2(-176f + (0f - num3), -200f + (0f - num4)); orCreateBackground2.SetSizeWithCurrentAnchors((Axis)0, 235f); orCreateBackground2.SetSizeWithCurrentAnchors((Axis)1, 90f); ((Transform)orCreateBackground2).localScale = new Vector3(1f, 1f, 1f); } public static void RemoveQuiverSlots(InventoryGrid __instance, List<Element> ___m_elements) { int bonusInventoryRowIndex = BetterArchery.GetBonusInventoryRowIndex(); for (int i = 0; i < 3; i++) { int x = i; Element element = GetElement(___m_elements, x, bonusInventoryRowIndex); element.m_go.SetActive(false); } Transform val = ((Component)__instance).transform.parent.Find("QuiverSlotBkg"); if ((Object)(object)val != (Object)null) { Object.Destroy((Object)(object)((Component)val).gameObject); } } private static RectTransform GetOrCreateBackground(InventoryGrid __instance, string name) { //IL_0061: 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_00ca: Unknown result type (might be due to invalid IL or missing references) //IL_00d9: 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) Transform val = ((Component)__instance).transform.parent.Find(name); if ((Object)(object)val != (Object)null) { return (RectTransform)(object)((val is RectTransform) ? val : null); } if (BetterArchery.HasAuga) { BetterArchery.Log("GetOrCreateBackground: Auga is Active!"); Transform parent = ((Component)__instance).transform.parent; GameObject val2 = API.Panel_Create(((Component)parent).transform, new Vector2(10f, 10f), name, withCornerDecoration: true); Transform val3 = ((Component)__instance).transform.Find("Main"); ((Behaviour)((Component)val3).GetComponent<RectMask2D>()).enabled = false; ((Behaviour)((Component)((Component)val3).transform.Find("Grid")).GetComponent<GridLayoutGroup>()).enabled = false; if (val3.localPosition.y > -40f) { val3.localPosition = Vector2.op_Implicit(new Vector2(val3.localPosition.x, -64f)); } val2.transform.SetSiblingIndex(((Component)val3).transform.GetSiblingIndex() + 1); val = val2.transform; return (RectTransform)(object)((val is RectTransform) ? val : null); } GameObject gameObject = ((Component)((Component)__instance).transform.parent.Find("Bkg")).gameObject; GameObject val4 = Object.Instantiate<GameObject>(gameObject, gameObject.transform.parent); ((Object)val4).name = name; val4.transform.SetSiblingIndex(gameObject.transform.GetSiblingIndex() + 1); val = val4.transform; return (RectTransform)(object)((val is RectTransform) ? val : null); } private static Element GetElement(List<Element> elements, int x, int y) { int width = ((Humanoid)Player.m_localPlayer).GetInventory().GetWidth(); return elements[y * width + x]; } } [HarmonyPatch(typeof(InventoryGui), "OnSelectedItem", new Type[] { typeof(InventoryGrid), typeof(ItemData), typeof(Vector2i), typeof(Modifier) })] public static class InventoryGui_OnSelectedItem_Patch { public static bool Prefix(InventoryGui __instance, InventoryGrid grid, ItemData item, Vector2i pos, Modifier mod, GameObject ___m_dragGo, ItemData ___m_dragItem) { //IL_003c: 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_005c: Invalid comparison between Unknown and I4 //IL_0078: Unknown result type (might be due to invalid IL or missing references) //IL_007f: Invalid comparison between Unknown and I4 //IL_0110: Unknown result type (might be due to invalid IL or missing references) //IL_0117: Invalid comparison between Unknown and I4 //IL_011b: Unknown result type (might be due to invalid IL or missing references) if (!BetterArchery.configQuiverEnabled.Value) { return true; } BetterArchery.isContainerOpen = __instance.IsContainerOpen(); if (grid.m_inventory.m_name.Equals("Inventory") && BetterArchery.IsQuiverSlot(pos)) { if (___m_dragItem != null && (int)___m_dragItem.m_shared.m_itemType == 9) { return true; } if (___m_dragItem != null && (int)___m_dragItem.m_shared.m_itemType != 9) { MessageHud.instance.ShowMessage((MessageType)2, "$mod_betterarchery_quiver_wrong_item_error", 0, (Sprite)null); return false; } } if (Object.op_Implicit((Object)(object)__instance.m_dragGo)) { if (item != null && item.m_equipped && __instance.m_dragInventory != grid.GetInventory()) { MessageHud.instance.ShowMessage((MessageType)2, "$mod_betterarchery_quiver_transfer_chest_error", 0, (Sprite)null); return false; } if (item != null && (int)___m_dragItem.m_shared.m_itemType == 9 && BetterArchery.IsQuiverSlot(___m_dragItem.m_gridPos)) { BetterArchery.Log("$mod_betterarchery_quiver_item_swap_error"); return false; } } if (___m_dragItem != null && ___m_dragItem.m_equipped && __instance.m_dragInventory != grid.GetInventory()) { MessageHud.instance.ShowMessage((MessageType)2, "$mod_betterarchery_quiver_swap_chest_error", 0, (Sprite)null); return false; } return true; } } [HarmonyPatch(typeof(InventoryGui), "UpdateContainer")] public static class InventoryGui_UpdateContainer_Patch { public static bool Prefix(InventoryGui __instance, Player player) { if (!BetterArchery.configQuiverEnabled.Value) { return true; } BetterArchery.isContainerOpen = Object.op_Implicit((Object)(object)__instance.m_currentContainer) && __instance.m_currentContainer.IsOwner(); return true; } } [HarmonyPatch(typeof(InventoryGui), "OnDropOutside")] public static class InventoryGui_OnDropOutside_Patch { public static bool Prefix(GameObject ___m_dragGo, ItemData ___m_dragItem) { if (___m_dragItem != null && ___m_dragItem.m_equipped && BetterArchery.configQuiverEnabled.Value) { MessageHud.instance.ShowMessage((MessageType)2, "$mod_betterarchery_quiver_drop_outside_error", 0, (Sprite)null); return false; } return true; } } [HarmonyPatch(typeof(InventoryGui), "OnCraftPressed")] public static class InventoryGui_OnCraftPressed_Patch { public static void Prefix(InventoryGui __instance) { if (Object.op_Implicit((Object)(object)__instance.m_selectedRecipe.Key)) { __instance.m_craftRecipe = __instance.m_selectedRecipe.Key; if ((Object)(object)__instance.m_craftRecipe != (Object)null && ((Object)__instance.m_craftRecipe).name == "Recipe_ArrowWoodAnywhere") { __instance.m_craftDuration = 7f; } else { __instance.m_craftDuration = 2f; } } } } [HarmonyPatch(typeof(InventoryGui), "UpdateRecipeList")] public static class InventoryGui_UpdateRecipeList_Patch { public static void Prefix(InventoryGui __instance, List<Recipe> recipes) { Player localPlayer = Player.m_localPlayer; if (Object.op_Implicit((Object)(object)localPlayer.GetCurrentCraftingStation())) { Recipe val = recipes.Find((Recipe e) => ((Object)e).name == "Recipe_ArrowWoodAnywhere"); if ((Object)(object)val != (Object)null) { recipes.Remove(val); } } } } [HarmonyPatch(typeof(Inventory), "HaveEmptySlot")] public static class Inventory_HaveEmptySlot_Patch { [HarmonyPriority(800)] public static bool Prefix(Inventory __instance, ref bool __result) { //IL_0065: 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_006d: 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) if (__instance.GetName() != "Inventory" || !BetterArchery.configQuiverEnabled.Value) { return true; } int num = __instance.m_width * __instance.m_height - 3 - 5; if (__instance.GetHeight() > 5) { num -= 8; } int num2 = __instance.m_inventory.Count; for (int i = 0; i < 3; i++) { Vector2i quiverSlotPosition = BetterArchery.GetQuiverSlotPosition(i); ItemData itemAt = __instance.GetItemAt(quiverSlotPosition.x, quiverSlotPosition.y); num2 -= ((itemAt != null) ? 1 : 0); } __result = num2 < num; return false; } } [HarmonyPatch(typeof(Inventory), "FindEmptySlot")] public static class Inventory_FindEmptySlot_Patch { [HarmonyPriority(800)] public static bool Prefix(Inventory __instance, ref Vector2i __result, bool topFirst, int ___m_height, int ___m_width) { //IL_012c: Unknown result type (might be due to invalid IL or missing references) //IL_0131: Unknown result type (might be due to invalid IL or missing references) //IL_00f4: Unknown result type (might be due to invalid IL or missing references) //IL_00f9: Unknown result type (might be due to invalid IL or missing references) //IL_0076: 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 (__instance.GetName() != "Inventory" || !BetterArchery.configQuiverEnabled.Value) { return true; } if (topFirst) { int num = __instance.GetHeight() - 1; if (__instance.GetHeight() > 5) { num--; } for (int i = 0; i < num; i++) { for (int j = 0; j < ___m_width; j++) { if (__instance.GetItemAt(j, i) == null) { __result = new Vector2i(j, i); return false; } } } } else { int num2 = __instance.GetHeight() - 1; if (__instance.GetHeight() > 5) { num2--; } for (int k = 1; k < num2; k++) { for (int l = 0; l < ___m_width; l++) { if (__instance.GetItemAt(l, k) == null) { __result = new Vector2i(l, k); return false; } } } } __result = new Vector2i(-1, -1); return false; } } [HarmonyPatch(typeof(ObjectDB), "CopyOtherDB")] public static class ObjectDB_CopyOtherDB_Patch { public static void Postfix() { BetterArchery.TryRegisterItems(); BetterArchery.TryRegisterRecipes(); } } [HarmonyPatch(typeof(ObjectDB), "Awake")] public static class ObjectDB_Awake_Patch { public static void Postfix() { BetterArchery.TryRegisterItems(); BetterArchery.TryRegisterRecipes(); } } public static class PlayerBody { public static Transform spine; public static Transform leftHand; public static bool onBowDrawing; } [HarmonyPatch(typeof(Player), "Awake")] public static class Player_Awake_Patch { [HarmonyPriority(0)] private static void Prefix(ref Player __instance) { //IL_0036: Unknown result type (might be due to invalid IL or missing references) //IL_0040: Expected O, but got Unknown if (BetterArchery.configQuiverEnabled.Value) { Traverse.Create((object)__instance).Field("m_inventory").SetValue((object)new Inventory("Inventory", (Sprite)null, 8, ((Humanoid)__instance).m_inventory.m_height + 2)); BetterArchery.Log($"Inventory h: {((Humanoid)__instance).m_inventory.m_height}"); BetterArchery.QuiverRowIndex = ((Humanoid)__instance).m_inventory.m_height - 1; } } } [HarmonyPatch(typeof(Player), "OnSpawned")] public static class ModifyOnSpawned { private static void Prefix(Player __instance) { //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_0011: 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_0027: Unknown result type (might be due to invalid IL or missing references) //IL_0033: Expected O, but got Unknown TutorialText item = new TutorialText { m_label = "BetterArchery", m_name = "betterarchery", m_text = "Thank you for using this mod! Don't forget to change configurations to get your own taste!", m_topic = "Welcome to BetterArchery" }; if (!Tutorial.instance.m_texts.Contains(item)) { Tutorial.instance.m_texts.Add(item); } Player localPlayer = Player.m_localPlayer; if (!Object.op_Implicit((Object)(object)localPlayer)) { return; } localPlayer.ShowTutorial("betterarchery", false); if (BetterArchery.configQuiverEnabled.Value) { foreach (ItemData equippedItem in ((Humanoid)__instance).m_inventory.GetEquippedItems()) { if (CustomSlotCreator.IsCustomSlotItem(equippedItem)) { equippedItem.m_equipped = true; } equippedItem.m_equipped = true; } } if (!BetterArchery.BowZoomSFXEnabled.Value) { return; } try { BetterArchery.playerAudioSource = ((Component)((Component)localPlayer).transform).gameObject.AddComponent<AudioSource>(); ((Component)((Component)localPlayer).transform).gameObject.AddComponent<ZSFX>(); } catch (Exception ex) { BetterArchery.Log(ex.ToString(), 0); } } } [HarmonyPatch(typeof(Player), "LateUpdate")] public static class Player_LateUpdate_Patch { public static float spineTimer = 0.5f; private static void Postfix(Player __instance, Transform ___m_head, ref Rigidbody ___m_body, ref VisEquipment ___m_visEquipment, ItemData ___m_rightItem, ItemData ___m_leftItem) { //IL_006b: Unknown result type (might be due to invalid IL or missing references) //IL_0071: Invalid comparison between Unknown and I4 //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_00a7: Unknown result type (might be due to invalid IL or missing references) //IL_00c2: 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_00cb: 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_00e6: 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_00f4: 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_013c: Unknown result type (might be due to invalid IL or missing references) //IL_0140: Unknown result type (might be due to invalid IL or missing references) //IL_015c: Unknown result type (might be due to invalid IL or missing references) //IL_0161: Unknown result type (might be due to invalid IL or missing references) //IL_0165: Unknown result type (might be due to invalid IL or missing references) //IL_017c: Unknown result type (might be due to invalid IL or missing references) //IL_0181: Unknown result type (might be due to invalid IL or missing references) //IL_0185: Unknown result type (might be due to invalid IL or missing references) //IL_018f: Unknown result type (might be due to invalid IL or missing references) if ((Object)(object)Player.m_localPlayer != (Object)(object)__instance) { return; } if ((Object)(object)PlayerBody.spine == (Object)null) { PlayerBody.spine = ((IEnumerable<Transform>)((Humanoid)__instance).m_visEquipment.m_bodyModel.bones).SingleOrDefault((Func<Transform, bool>)((Transform x) => ((Object)x).name == "Spine")); } Quaternion rotation; if (___m_leftItem != null && (int)___m_leftItem.m_shared.m_itemType == 4 && Object.op_Implicit((Object)(object)___m_body) && PlayerBody.onBowDrawing) { spineTimer = 0.5f; rotation = ((Component)((Character)__instance).m_eye).transform.rotation; float num = ((Quaternion)(ref rotation)).eulerAngles.y + 90f; Transform spine = PlayerBody.spine; rotation = PlayerBody.spine.rotation; float x2 = ((Quaternion)(ref rotation)).eulerAngles.x; rotation = ((Component)((Character)__instance).m_eye).transform.rotation; spine.rotation = Quaternion.Euler(x2, num, ((Quaternion)(ref rotation)).eulerAngles.x); } else if (spineTimer > 0f) { spineTimer -= Time.deltaTime; rotation = ((Component)((Character)__instance).m_eye).transform.rotation; float num2 = ((Quaternion)(ref rotation)).eulerAngles.y + 90f; Transform spine2 = PlayerBody.spine; rotation = PlayerBody.spine.rotation; float x3 = ((Quaternion)(ref rotation)).eulerAngles.x; rotation = ((Component)((Character)__instance).m_eye).transform.rotation; spine2.rotation = Quaternion.Euler(x3, num2, ((Quaternion)(ref rotation)).eulerAngles.x); } } } [HarmonyPatch(typeof(Player), "UseHotbarItem")] public static class Player_UseHotbarItem_Patch { public static bool Prefix(Player __instance) { //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_0035: Unknown result type (might be due to invalid IL or missing references) //IL_003a: Unknown result type (might be due to invalid IL or missing references) //IL_0059: Unknown result type (might be due to invalid IL or missing references) //IL_005e: Unknown result type (might be due to invalid IL or missing references) //IL_0061: Unknown result type (might be due to invalid IL or missing references) if (!BetterArchery.configQuiverEnabled.Value) { return true; } KeyboardShortcut value = BetterArchery.HoldingKeyCode.Value; if (!string.IsNullOrEmpty(((KeyboardShortcut)(ref value)).Serialize())) { value = BetterArchery.HoldingKeyCode.Value; if (((KeyboardShortcut)(ref value)).Serialize() != "None") { value = BetterArchery.HoldingKeyCode.Value; if (Input.GetKey(((KeyboardShortcut)(ref value)).MainKey)) { return false; } } } return true; } } [HarmonyPatch(typeof(Player), "QueueUnequipAction")] public static class Player_QueueUnequipAction_Patch { public static bool Prefix(ItemData item, Player __instance) { //IL_005e: Unknown result type (might be due to invalid IL or missing references) if (!BetterArchery.configQuiverEnabled.Value) { return true; } if (((Object)item.m_dropPrefab).name.Contains("Quiver")) { Inventory inventory = ((Humanoid)Player.m_localPlayer).m_inventory; foreach (ItemData item2 in inventory.m_inventory) { if (BetterArchery.IsQuiverSlot(item2.m_gridPos) && item2.GetWeight() > 0f) { MessageHud.instance.ShowMessage((MessageType)2, "$mod_betterarchery_quiver_unequip_error", 0, (Sprite)null); return false; } } } return true; } } [HarmonyPatch(typeof(Player), "SetControls")] public static class Player_SetControls_Patch { private static void Prefix(Player __instance, ref Vector3 movedir, ref bool attack, ref bool attackHold, ref bool secondaryAttack, ref bool block, ref bool blockHold, ref bool jump, ref bool crouch, ref bool run, ref bool autoRun) { //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_0024: Unknown result type (might be due to invalid IL or missing references) if (!BetterArchery.configBowZoomEnabled.Value) { return; } if (attackHold) { KeyboardShortcut value = BetterArchery.BowDrawCancelKey.Value; if (Input.GetKey(((KeyboardShortcut)(ref value)).MainKey)) { blockHold = true; } else { blockHold = false; } } else { ItemData leftItem = ((Humanoid)__instance).GetLeftItem(); if (leftItem != null && ((Object)leftItem.m_dropPrefab).name.Contains("Bow") && BetterArchery.__ZoomState == BetterArchery.ZoomState.ZoomingIn) { blockHold = false; } } } } [HarmonyPatch(typeof(GameCamera), "GetCameraPosition")] public static class Player_GameCamera_Patch { [HarmonyPriority(100)] private static void Postfix(GameCamera __instance, float dt, Vector3 pos, Quaternion rot) { if (!((Object)(object)__instance == (Object)null) && BetterArchery.configBowZoomEnabled.Value && BetterArchery.__BaseFov == 0f) { BetterArchery.__BaseFov = __instance.m_fov; } } } [HarmonyPatch(typeof(GameCamera), "UpdateCamera")] public static class Player_GameCamera_UpdateCamera { [HarmonyPriority(0)] public static void Prefix(GameCamera __instance) { if (BetterArchery.configBowZoomEnabled.Value && (BetterArchery.__ZoomState == BetterArchery.ZoomState.ZoomingOut || BetterArchery.__ZoomState == BetterArchery.ZoomState.ZoomingIn)) { __instance.m_fov = BetterArchery.__NewZoomFov; } } } [HarmonyPriority(0)] [HarmonyPatch(typeof(Hud), "UpdateCrosshair")] public static class Player_UpdateCrosshair_Patch { private static void Postfix(Hud __instance, Player player, float bowDrawPercentage) { //IL_0115: Unknown result type (might be due to invalid IL or missing references) //IL_011b: Invalid comparison between Unknown and I4 //IL_013c: Unknown result type (might be due to invalid IL or missing references) //IL_0173: Unknown result type (might be due to invalid IL or missing references) //IL_0178: Unknown result type (might be due to invalid IL or missing references) //IL_017c: Unknown result type (might be due to invalid IL or missing references) if (((Behaviour)__instance.m_crosshair).enabled != BetterArchery.IsCrosshairVisible.Value) { ((Behaviour)__instance.m_crosshair).enabled = BetterArchery.IsCrosshairVisible.Value; } if (((Behaviour)__instance.m_crosshairBow).enabled != BetterArchery.IsBowCrosshairVisible.Value) { ((Behaviour)__instance.m_crosshairBow).enabled = BetterArchery.IsBowCrosshairVisible.Value; } PlayerBody.onBowDrawing = bowDrawPercentage > 0.1f; if (BetterArchery.BowDrawMovementSpeedReductionEnabled.Value) { if (PlayerBody.onBowDrawing) { ((Character)player).SetWalk(true); BetterArchery.speedReduction = true; } else if (((Character)player).GetWalk() && BetterArchery.speedReduction) { BetterArchery.speedReduction = false; ((Character)player).SetWalk(false); } } if (!BetterArchery.configBowZoomEnabled.Value || BetterArchery.__BaseFov == 0f) { return; } ItemData currentWeapon = ((Humanoid)player).GetCurrentWeapon(); if (currentWeapon == null || (int)currentWeapon.m_shared.m_itemType != 4) { ZoomOut(); return; } float skillFactor = ((Character)player).GetSkillFactor(currentWeapon.m_shared.m_skillType); float num = 2f * (1f - skillFactor); if (num <= 0.1f) { num = 0.1f; } KeyboardShortcut value = BetterArchery.BowZoomKey.Value; bool key = Input.GetKey(((KeyboardShortcut)(ref value)).MainKey); if (BetterArchery.__ZoomState == BetterArchery.ZoomState.ZoomingIn && !BetterArchery.zoomSFX) { BetterArchery.PlayCustomSFX("inhale", checkIfPlaying: false); BetterArchery.zoomSFX = true; } else if (BetterArchery.__ZoomState == BetterArchery.ZoomState.ZoomingOut && BetterArchery.zoomSFX) { BetterArchery.PlayCustomSFX("exhale", checkIfPlaying: false); BetterArchery.zoomSFX = false; } if (BetterArchery.AutomaticBowZoom.Value) { if (bowDrawPercentage > 0.01f) { BetterArchery.ZoomInTimer += Time.deltaTime; BetterArchery.__ZoomState = BetterArchery.ZoomState.ZoomingIn; float num2 = ((!(BetterArchery.BowZoomConstantTime.Value > 0f)) ? Mathf.InverseLerp(0.05f, num, BetterArchery.ZoomInTimer) : Mathf.InverseLerp(0.05f, BetterArchery.BowZoomConstantTime.Value, BetterArchery.ZoomInTimer)); GameCamera.instance.m_fov = (BetterArchery.__LastZoomFov = Mathf.Lerp(BetterArchery.__BaseFov, BetterArchery.__BaseFov / BetterArchery.BowZoomFactor.Value, num2)); BetterArchery.__NewZoomFov = (BetterArchery.__LastZoomFov = Mathf.Lerp(BetterArchery.__BaseFov, BetterArchery.__BaseFov / BetterArchery.BowZoomFactor.Value, num2)); return; } ZoomOut(); } if (key) { if (!PlayerBody.onBowDrawing) { BetterArchery.ZoomOutDelayTimer += Time.deltaTime; if (BetterArchery.ZoomOutDelayTimer > BetterArchery.StayInZoomTime.Value) { ZoomOut(); } } else { BetterArchery.ZoomInTimer += Time.deltaTime; BetterArchery.ZoomOutDelayTimer = 0f; BetterArchery.__ZoomState = BetterArchery.ZoomState.ZoomingIn; float num3 = ((!(BetterArchery.BowZoomConstantTime.Value > 0f)) ? Mathf.InverseLerp(0.05f, num, BetterArchery.ZoomInTimer) : Mathf.InverseLerp(0.05f, BetterArchery.BowZoomConstantTime.Value, BetterArchery.ZoomInTimer)); GameCamera.instance.m_fov = (BetterArchery.__LastZoomFov = Mathf.Lerp(BetterArchery.__BaseFov, BetterArchery.__BaseFov / BetterArchery.BowZoomFactor.Value, num3)); BetterArchery.__NewZoomFov = (BetterArchery.__LastZoomFov = Mathf.Lerp(BetterArchery.__BaseFov, BetterArchery.__BaseFov / BetterArchery.BowZoomFactor.Value, num3)); } } else { BetterArchery.ZoomOutDelayTimer = 1f; ZoomOut(); } } public static void ZoomOut() { if (BetterArchery.__ZoomState != 0) { if (BetterArchery.__ZoomState == BetterArchery.ZoomState.ZoomingIn) { BetterArchery.__ZoomState = BetterArchery.ZoomState.ZoomingOut; BetterArchery.ZoomOutTimer = 0f; BetterArchery.ZoomInTimer = 0f; } else { BetterArchery.ZoomOutTimer += Time.deltaTime; if (BetterArchery.ZoomOutTimer > 1f) { GameCamera.instance.m_fov = BetterArchery.__BaseFov; BetterArchery.__ZoomState = BetterArchery.ZoomState.Fixed; BetterArchery.ZoomOutDelayTimer = 0f; return; } } float num = Mathf.InverseLerp(0f, 0.3f, BetterArchery.ZoomOutTimer); GameCamera.instance.m_fov = Mathf.Lerp(BetterArchery.__LastZoomFov, BetterArchery.__BaseFov, num); BetterArchery.__NewZoomFov = Mathf.Lerp(BetterArchery.__LastZoomFov, BetterArchery.__BaseFov, num); } else if (GameCamera.instance.m_fov != BetterArchery.__BaseFov) { GameCamera.instance.m_fov = BetterArchery.__BaseFov; } } } [HarmonyPatch(typeof(Player), "CreateTombStone")] public static class Player_CreateTombStone_Patch { public static bool Prefix(Player __instance) { //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_004b: 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_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_0070: Unknown result type (might be due to invalid IL or missing references) //IL_00ef: Unknown result type (might be due to invalid IL or missing references) //IL_0112: Unknown result type (might be due to invalid IL or missing references) //IL_0117: 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) //IL_012b: Unknown result type (might be due to invalid IL or missing references) if (((Humanoid)__instance).GetInventory().GetAllItems().Count == 0) { return true; } if (!BetterArchery.IsQuiverEquipped()) { return true; } GameObject val = Object.Instantiate<GameObject>(__instance.m_tombstone, ((Character)__instance).GetCenterPoint() + Vector3.up + ((Component)__instance).transform.forward * -0.5f, ((Component)__instance).transform.rotation); TombStone component = val.GetComponent<TombStone>(); PlayerProfile playerProfile = Game.instance.GetPlayerProfile(); string name = playerProfile.GetName(); long playerID = playerProfile.GetPlayerID(); component.Setup(name + "'s Quiver", playerID); Container component2 = val.GetComponent<Container>(); Inventory inventory = component2.GetInventory(); Inventory inventory2 = ((Humanoid)__instance).GetInventory(); List<ItemData> list = new List<ItemData>(); foreach (ItemData item in inventory2.m_inventory) { if (!BetterArchery.IsQuiverSlot(item.m_gridPos)) { list.Add(item); continue; } Vector2i val2 = inventory.FindEmptySlot(false); inventory.AddItem(item, item.m_stack, val2.x, val2.y); } inventory2.m_inventory = list; inventory2.Changed(); inventory.Changed(); return true; } } [HarmonyPatch(typeof(Projectile), "Setup")] public static class RetrieveArrows { public static bool Prefix(ref Projectile __instance, Character owner, Vector3 velocity, float hitNoise, HitData hitData, ItemData item) { //IL_006c: Unknown result type (might be due to invalid IL or missing references) //IL_0072: Invalid comparison between Unknown and I4 //IL_01bd: Unknown result type (might be due to invalid IL or missing references) //IL_01c2: Unknown result type (might be due to invalid IL or missing references) //IL_02b9: Unknown result type (might be due to invalid IL or missing references) if ((Object)(object)__instance == (Object)null || item == null) { return true; } Player localPlayer = Player.m_localPlayer; if ((Object)(object)localPlayer == (Object)null || (Object)(object)owner != (Object)(object)Player.m_localPlayer) { return true; } if (!((Object)__instance).name.Contains("bow_projectile") || (int)item.m_shared.m_itemType != 4) { return true; } if (BetterArchery.configArrowImprovementsEnabled.Value) { __instance.m_gravity = BetterArchery.ArrowGravity.Value; } if (!BetterArchery.configRetrievableArrowsEnabled.Value) { return true; } string arrowType = ((Object)((Humanoid)localPlayer).GetAmmoItem().m_dropPrefab).name; if (string.IsNullOrEmpty(arrowType)) { return true; } Arrow arrow = BetterArchery.ArrowRetrieves.Find((Arrow e) => e.SpawnArrow == arrowType); if (arrow == null) { return true; } float num = Random.Range(0f, 1f); BetterArchery.Log($"m_dropPrefab: {arrowType}, x.SpawnChance: {arrow.SpawnChance}, x.SpawnArrow: {arrow.SpawnArrow}"); BetterArchery.Log($"spawnChance: {num}, currentArrow.SpawnChance: {arrow.SpawnChance}"); if (BetterArchery.ArrowRetrieveOldVersion.Value) { if (num < arrow.SpawnChance) { GameObject itemPrefab = ObjectDB.instance.GetItemPrefab(arrow.SpawnArrow); __instance.m_spawnOffset = new Vector3(0.5f, 0.05f, -0.5f); __instance.m_spawnOnHitChance = 1f; __instance.m_spawnOnHit = itemPrefab; __instance.m_hideOnHit = ((Component)__instance).gameObject; } else { __instance.m_spawnOnHitChance = 0f; __instance.m_ttl = BetterArchery.ArrowDisappearTime.Value; } } else if (num < arrow.SpawnChance) { GameObject itemPrefab2 = ObjectDB.instance.GetItemPrefab(arrow.SpawnArrow); Pickable val = ((Component)__instance).gameObject.AddComponent<Pickable>(); val.m_hideWhenPicked = ((Component)__instance).gameObject; val.m_amount = 1; val.m_itemPrefab = itemPrefab2; } else if (BetterArchery.ArrowDisappearOnHit.Value) { __instance.m_hideOnHit = ((Component)__instance).gameObject; } else { __instance.m_stayTTL = BetterArchery.ArrowDisappearTime.Value; if (Object.op_Implicit((Object)(object)((Component)__instance).GetComponentInChildren<MeshRenderer>())) { ((Renderer)((Component)__instance).GetComponentInChildren<MeshRenderer>()).material.color = Color.black; } } return true; } } [HarmonyPatch(typeof(Projectile), "OnHit")] public static class Projectile_OnHit_Patch { public static void Prefix(Projectile __instance, Collider collider, Vector3 hitPoint, bool water) { if (BetterArchery.ArrowRetrieveOldVersion.Value || !BetterArchery.configRetrievableArrowsEnabled.Value || !Object.op_Implicit((Object)(object)((Component)__instance).gameObject.GetComponent<Pickable>()) || !((Object)__instance).name.Contains("bow_projectile")) { return; } GameObject val = (Object.op_Implicit((Object)(object)collider) ? Projectile.FindHitObject(collider) : null); bool flag = false; IDestructible val2 = (Object.op_Implicit((Object)(object)val) ? val.GetComponent<IDestructible>() : null); if (val2 != null) { flag = val2 is Character; if (!__instance.IsValidTarget(val2)) { return; } } BoxCollider val3 = null; val3 = ((((Object)__instance).name == "bow_projectile_needle(Clone)") ? ((Component)((Component)((Component)__instance).transform.GetChild(0)).gameObject.transform.GetChild(0)).gameObject.AddComponent<BoxCollider>() : ((!(((Object)__instance).name == "bow_projectile_frost(Clone)")) ? ((Component)((Component)__instance).transform.GetChild(0)).gameObject.AddComponent<BoxCollider>() : ((Component)((Component)__instance).transform.GetChild(3)).gameObject.AddComponent<BoxCollider>())); if ((Object)(object)val3 != (Object)null) { ((Collider)val3).enabled = true; __instance.m_stayTTL = BetterArchery.ArrowDisappearTime.Value; } } } [HarmonyPatch(typeof(Attack), "FireProjectileBurst")] public static class Attack_FireProjectileBurst_Patch { public static bool Prefix(ref Attack __instance) { //IL_0056: Unknown result type (might be due to invalid IL or missing references) //IL_005c: Invalid comparison between Unknown and I4 if (!((Character)__instance.m_character).IsPlayer() || !BetterArchery.configArrowImprovementsEnabled.Value) { return true; } ItemData ammoItem = ((Humanoid)Player.m_localPlayer).m_ammoItem; ItemData leftItem = ((Humanoid)Player.m_localPlayer).GetLeftItem(); if (leftItem == null) { return true; } if ((int)leftItem.m_shared.m_itemType != 4) { return true; } if (ammoItem != null) { __instance.m_projectileVel = BetterArchery.ArrowVelocity.Value; if (BetterArchery.ArrowAccuracy.Value >= 0f) { __instance.m_projectileAccuracy = BetterArchery.ArrowAccuracy.Value; } } return true; } } [HarmonyPatch(typeof(Attack), "GetProjectileSpawnPoint")] public static class Attack_GetProjectileSpawnPoint_Patch { public static void Postfix(ref Attack __instance, ref Vector3 spawnPoint, ref Vector3 aimDir) { //IL_004c: Unknown result type (might be due to invalid IL or missing references) //IL_0052: Invalid comparison between Unknown and I4 //IL_0084: Unknown result type (might be due to invalid IL or missing references) //IL_0089: Unknown result type (might be due to invalid IL or missing references) //IL_0097: 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_00a1: 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_00cd: Unknown result type (might be due to invalid IL or missing references) //IL_00d9: 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_00e4: Unknown result type (might be due to invalid IL or missing references) //IL_00ee: 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_00f9: 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_010a: 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_011d: Unknown result type (might be due to invalid IL or missing references) //IL_0122: 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_013b: Unknown result type (might be due to invalid IL or missing references) //IL_0140: Unknown result type (might be due to invalid IL or missing references) //IL_0160: Unknown result type (might be due to invalid IL or missing references) //IL_0162: Unknown result type (might be due to invalid IL or missing references) //IL_0167: Unknown result type (might be due to invalid IL or missing references) //IL_019c: 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_01ab: Unknown result type (might be due to invalid IL or missing references) //IL_01b0: Unknown result type (might be due to invalid IL or missing references) if (!((Character)__instance.m_character).IsPlayer() || !BetterArchery.configArrowImprovementsEnabled.Value) { return; } ItemData leftItem = ((Humanoid)Player.m_localPlayer).GetLeftItem(); if (leftItem == null || (int)leftItem.m_shared.m_itemType != 4) { return; } Transform leftHand = __instance.m_character.m_visEquipment.m_leftHand; Transform transform = ((Component)__instance.m_character).transform; spawnPoint = leftHand.position; aimDir = __instance.m_character.GetAimDir(spawnPoint); if (aimDir.y <= -0.8f) { leftHand = __instance.GetAttackOrigin(); spawnPoint = leftHand.position + transform.up * __instance.m_attackHeight + transform.forward * 0.7f + transform.right * __instance.m_attackOffset; aimDir = __instance.m_character.GetAimDir(spawnPoint); } if (__instance.m_useCharacterFacing) { Vector3 forward = Vector3.forward; if (__instance.m_useCharacterFacingYAim) { forward.y = aimDir.y; } aimDir = transform.TransformDirection(forward); } ItemData ammoItem = ((Humanoid)Player.m_localPlayer).m_ammoItem; if (ammoItem != null && Object.op_Implicit((Object)(object)ammoItem.m_shared.m_attack.m_attackProjectile)) { aimDir += BetterArchery.ArrowAimDir.Value; } } } [HarmonyPatch(typeof(Humanoid), "OnDamaged")] public static class Humanoid_OnDamaged_Patch { public static void Postfix(ref Humanoid __instance, HitData hit) { if (Object.op_Implicit((Object)(object)__instance) && hit.HaveAttacker() && hit.GetAttacker().IsPlayer() && BetterArchery.ShowSneakDamage.Value) { BetterArchery.Log($"(Humanoid) - __instance.m_name: {((Character)__instance).m_name}, __instance.InAttack(): {((Character)__instance).InAttack()}, __instance.m_baseAI.IsAlerted(): {((Character)__instance).m_baseAI.IsAlerted()}, __instance.m_baseAI.m_alerted: {((Character)__instance).m_baseAI.m_alerted}"); BetterArchery.Log($"(Humanoid) - GetTotalPhysicalDamage: {hit.GetTotalPhysicalDamage()}, GetTotalDamage: {hit.GetTotalDamage()}"); if (!((Character)__instance).InAttack() && !((Character)__instance).m_baseAI.IsAlerted()) { hit.GetAttacker().Message((MessageType)1, string.Format("<size=25>Sneak attack for {0}X ({1}) damage!</size>", hit.m_backstabBonus, hit.GetTotalDamage().ToString("0.0")), 0, (Sprite)null); } } } } [HarmonyPatch(typeof(Character), "OnDamaged")] public static class Character_OnDamaged_Patch { public static void Postfix(ref Character __instance, HitData hit) { if (Object.op_Implicit((Object)(object)__instance) && hit.HaveAttacker() && hit.GetAttacker().IsPlayer() && BetterArchery.ShowSneakDamage.Value) { BetterArchery.Log($"(Character) - __instance.m_name: {__instance.m_name}, __instance.InAttack(): {__instance.InAttack()}, __instance.m_baseAI.IsAlerted(): {__instance.m_baseAI.IsAlerted()}, __instance.m_baseAI.m_alerted: {__instance.m_baseAI.m_alerted}"); BetterArchery.Log($"(Character) - GetTotalPhysicalDamage: {hit.GetTotalPhysicalDamage()}, GetTotalDamage: {hit.GetTotalDamage()}"); if (!__instance.InAttack() && !__instance.m_baseAI.IsAlerted()) { hit.GetAttacker().Message((MessageType)1, string.Format("<size=25>Sneak attack for {0}X ({1}) damage!</size>", hit.m_backstabBonus, hit.GetTotalDamage().ToString("0.0")), 0, (Sprite)null); } } } } internal class Tombstone { [HarmonyPriority(0)] [HarmonyPatch(typeof(TombStone), "OnTakeAllSuccess")] public static class TombStone_OnTakeAllSuccess_Patch { public static void Postfix() { //IL_0172: Unknown result type (might be due to invalid IL or missing references) //IL_017d: Unknown result type (might be due to invalid IL or missing references) //IL_0187: Unknown result type (might be due to invalid IL or missing references) //IL_018c: Unknown result type (might be due to invalid IL or missing references) //IL_0191: Unknown result type (might be due to invalid IL or missing references) //IL_0196: Unknown result type (might be due to invalid IL or missing references) //IL_019b: Unknown result type (might be due to invalid IL or missing references)