Please disclose if any significant portion of your mod was created using AI tools by adding the 'AI Generated' category. Failing to do so may result in the mod being removed from Thunderstore.
Decompiled source of ValheimPlus Grantapher Temporary v10.2.0
BepInEx/plugins/ValheimPlus.dll
Decompiled 4 days ago
The result has been truncated due to the large size, download it to view full contents!
using System; using System.Collections; using System.Collections.Concurrent; using System.Collections.Generic; using System.Collections.ObjectModel; using System.Diagnostics; using System.Globalization; using System.IO; using System.IO.Compression; using System.Linq; using System.Net; using System.Net.Http; using System.Reflection; using System.Reflection.Emit; using System.Runtime.CompilerServices; using System.Runtime.InteropServices; using System.Runtime.Serialization; using System.Runtime.Versioning; using System.Security; using System.Security.Cryptography; using System.Security.Permissions; using System.Text; using System.Text.RegularExpressions; using System.Timers; using BepInEx; using BepInEx.Bootstrap; using BepInEx.Configuration; using BepInEx.Logging; using HarmonyLib; using IniParser; using IniParser.Exceptions; using IniParser.Model; using IniParser.Model.Configuration; using IniParser.Model.Formatting; using IniParser.Parser; using JetBrains.Annotations; using Microsoft.CodeAnalysis; using PlayFab.MultiplayerModels; using PlayFab.Party; using ServerSync; using Splatform; using TMPro; using UnityEngine; using UnityEngine.EventSystems; using UnityEngine.UI; using Valheim.SettingsGui; using ValheimPlus.Configurations; using ValheimPlus.Configurations.Sections; using ValheimPlus.GameClasses; using ValheimPlus.Http; using ValheimPlus.RPC; using ValheimPlus.Utility; [assembly: CompilationRelaxations(8)] [assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)] [assembly: Debuggable(DebuggableAttribute.DebuggingModes.Default | DebuggableAttribute.DebuggingModes.DisableOptimizations | DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints | DebuggableAttribute.DebuggingModes.EnableEditAndContinue)] [assembly: AssemblyTitle("ValheimPlus")] [assembly: AssemblyDescription("")] [assembly: AssemblyConfiguration("")] [assembly: AssemblyCompany("")] [assembly: AssemblyProduct("ValheimPlus")] [assembly: AssemblyCopyright("")] [assembly: AssemblyTrademark("")] [assembly: ComVisible(false)] [assembly: Guid("2a837100-a030-4d0c-bffb-b38356118d9a")] [assembly: AssemblyFileVersion("0.10.2.0")] [assembly: TargetFramework(".NETFramework,Version=v4.8", FrameworkDisplayName = ".NET Framework 4.8")] [assembly: SecurityPermission(SecurityAction.RequestMinimum, SkipVerification = true)] [assembly: AssemblyVersion("0.10.2.0")] [module: UnverifiableCode] internal sealed class ConfigurationManagerAttributes { public delegate void CustomHotkeyDrawerFunc(ConfigEntryBase setting, ref bool isCurrentlyAcceptingInput); public bool? ShowRangeAsPercent; public Action<ConfigEntryBase> CustomDrawer; public CustomHotkeyDrawerFunc CustomHotkeyDrawer; public bool? Browsable; public string Category; public object DefaultValue; public bool? HideDefaultButton; public bool? HideSettingName; public string Description; public string DispName; public int? Order; public bool? ReadOnly; public bool? IsAdvanced; public Func<object, string> ObjToStr; public Func<string, object> StrToObj; } public static class ZNetExtensions { public enum ZNetInstanceType { Local, Client, Server } public static bool IsLocalInstance(this ZNet znet) { return znet.IsServer() && !znet.IsDedicated(); } public static bool IsClientInstance(this ZNet znet) { return !znet.IsServer() && !znet.IsDedicated(); } public static bool IsServerInstance(this ZNet znet) { return znet.IsServer() && znet.IsDedicated(); } public static ZNetInstanceType GetInstanceType(this ZNet znet) { if (znet.IsLocalInstance()) { return ZNetInstanceType.Local; } if (znet.IsClientInstance()) { return ZNetInstanceType.Client; } return ZNetInstanceType.Server; } } namespace ValheimPlus { internal class ABM { public static bool isActive; private static Player PlayerInstance; private static bool controlFlag; private static bool shiftFlag; private static bool altFlag; public static bool exitOnNextIteration; private static Piece component; private const float BASE_TRANSLATION_DISTANCE = 0.1f; private const float BASE_ROTATION_ANGLE_DEGREES = 3f; private static float currentModificationSpeed = 1f; private const float MIN_MODIFICATION_SPEED = 1f; private const float MAX_MODIFICATION_SPEED = 30f; private static Quaternion savedRotation; public static void Run(ref Player __instance) { //IL_0032: Unknown result type (might be due to invalid IL or missing references) //IL_016f: Unknown result type (might be due to invalid IL or missing references) //IL_0122: 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) PlayerInstance = __instance; if (AEM.isActive) { if (isActive) { exitMode(); } return; } if (Input.GetKeyDown(Configuration.Current.AdvancedBuildingMode.exitAdvancedBuildingMode)) { if (isActive) { exitMode(); } return; } if (exitOnNextIteration) { isActive = false; exitOnNextIteration = false; component = null; } if (isActive && (Object)(object)component == (Object)null) { exitMode(); } else if ((Object)(object)selectedPrefab() == (Object)null || (Object)(object)PlayerInstance.m_placementGhost == (Object)null) { if (isActive) { exitMode(); } } else if (isInBuildMode() && IsHoeOrTerrainTool(selectedPrefab())) { if (isActive) { exitMode(); } } else if (isActive) { if (Vector3.Distance(((Component)PlayerInstance).transform.position, ((Component)component).transform.position) > PlayerInstance.m_maxPlaceDistance) { exitMode(); } isRunning(); listenToHotKeysAndDoWork(); } else if (Input.GetKeyDown(Configuration.Current.AdvancedBuildingMode.enterAdvancedBuildingMode)) { startMode(); } } private static void listenToHotKeysAndDoWork() { //IL_00b3: Unknown result type (might be due to invalid IL or missing references) //IL_00e3: Unknown result type (might be due to invalid IL or missing references) //IL_00ce: Unknown result type (might be due to invalid IL or missing references) //IL_00d3: Unknown result type (might be due to invalid IL or missing references) //IL_00fe: Unknown result type (might be due to invalid IL or missing references) //IL_014f: Unknown result type (might be due to invalid IL or missing references) //IL_0167: Unknown result type (might be due to invalid IL or missing references) //IL_017b: 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_018a: Unknown result type (might be due to invalid IL or missing references) //IL_028d: Unknown result type (might be due to invalid IL or missing references) //IL_02a5: 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) //IL_02c3: Unknown result type (might be due to invalid IL or missing references) //IL_02c8: 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_0217: Unknown result type (might be due to invalid IL or missing references) //IL_022f: Unknown result type (might be due to invalid IL or missing references) //IL_0239: Unknown result type (might be due to invalid IL or missing references) //IL_023e: 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) //IL_01c4: Unknown result type (might be due to invalid IL or missing references) //IL_01d8: Unknown result type (might be due to invalid IL or missing references) //IL_01e6: Unknown result type (might be due to invalid IL or missing references) //IL_01eb: Unknown result type (might be due to invalid IL or missing references) //IL_024b: Unknown result type (might be due to invalid IL or missing references) //IL_03e6: Unknown result type (might be due to invalid IL or missing references) //IL_03ed: Unknown result type (might be due to invalid IL or missing references) //IL_03c6: Unknown result type (might be due to invalid IL or missing references) //IL_03cd: Unknown result type (might be due to invalid IL or missing references) //IL_0341: Unknown result type (might be due to invalid IL or missing references) //IL_0355: Unknown result type (might be due to invalid IL or missing references) //IL_036d: Unknown result type (might be due to invalid IL or missing references) //IL_0377: Unknown result type (might be due to invalid IL or missing references) //IL_037c: Unknown result type (might be due to invalid IL or missing references) //IL_02ee: Unknown result type (might be due to invalid IL or missing references) //IL_0302: Unknown result type (might be due to invalid IL or missing references) //IL_0316: Unknown result type (might be due to invalid IL or missing references) //IL_0324: Unknown result type (might be due to invalid IL or missing references) //IL_0329: Unknown result type (might be due to invalid IL or missing references) //IL_0389: Unknown result type (might be due to invalid IL or missing references) //IL_0470: Unknown result type (might be due to invalid IL or missing references) //IL_0477: Unknown result type (might be due to invalid IL or missing references) //IL_0441: Unknown result type (might be due to invalid IL or missing references) //IL_0448: Unknown result type (might be due to invalid IL or missing references) //IL_0421: Unknown result type (might be due to invalid IL or missing references) //IL_0428: Unknown result type (might be due to invalid IL or missing references) //IL_049e: Unknown result type (might be due to invalid IL or missing references) //IL_04a5: Unknown result type (might be due to invalid IL or missing references) float num = 0f; float num2 = 0f; float num3 = 0f; if (Input.GetKeyDown((KeyCode)306)) { controlFlag = true; } if (Input.GetKeyUp((KeyCode)306)) { controlFlag = false; } if (Input.GetKeyDown((KeyCode)304)) { shiftFlag = true; } if (Input.GetKeyUp((KeyCode)304)) { shiftFlag = false; } if (Input.GetKeyDown((KeyCode)308)) { altFlag = true; } if (Input.GetKeyUp((KeyCode)308)) { altFlag = false; } changeModificationSpeed(); if (Input.GetKeyUp(Configuration.Current.AdvancedBuildingMode.copyObjectRotation)) { savedRotation = ((Component)component).transform.rotation; } if (Input.GetKeyUp(Configuration.Current.AdvancedBuildingMode.pasteObjectRotation)) { ((Component)component).transform.rotation = savedRotation; } float num4 = 3f * currentModificationSpeed; if (Input.GetAxis("Mouse ScrollWheel") > 0f) { Quaternion rotation; if (controlFlag) { num += 1f; rotation = Quaternion.Euler(((Component)component).transform.eulerAngles.x + num4 * num, ((Component)component).transform.eulerAngles.y, ((Component)component).transform.eulerAngles.z); } else if (altFlag) { num2 += 1f; rotation = Quaternion.Euler(((Component)component).transform.eulerAngles.x, ((Component)component).transform.eulerAngles.y, ((Component)component).transform.eulerAngles.z + num4 * num2); } else { num3 += 1f; rotation = Quaternion.Euler(((Component)component).transform.eulerAngles.x, ((Component)component).transform.eulerAngles.y + num4 * num3, ((Component)component).transform.eulerAngles.z); } ((Component)component).transform.rotation = rotation; } if (Input.GetAxis("Mouse ScrollWheel") < 0f) { Quaternion rotation2; if (controlFlag) { num -= 1f; rotation2 = Quaternion.Euler(((Component)component).transform.eulerAngles.x + num4 * num, ((Component)component).transform.eulerAngles.y, ((Component)component).transform.eulerAngles.z); } else if (altFlag) { num2 -= 1f; rotation2 = Quaternion.Euler(((Component)component).transform.eulerAngles.x, ((Component)component).transform.eulerAngles.y, ((Component)component).transform.eulerAngles.z + num4 * num2); } else { num3 -= 1f; rotation2 = Quaternion.Euler(((Component)component).transform.eulerAngles.x, ((Component)component).transform.eulerAngles.y + num4 * num3, ((Component)component).transform.eulerAngles.z); } ((Component)component).transform.rotation = rotation2; } float num5 = 0.1f * currentModificationSpeed; if (Input.GetKeyDown((KeyCode)273)) { if (controlFlag) { ((Component)component).transform.Translate(Vector3.up * num5); } else { ((Component)component).transform.Translate(Vector3.forward * num5); } } if (Input.GetKeyDown((KeyCode)274)) { if (controlFlag) { ((Component)component).transform.Translate(Vector3.down * num5); } else { ((Component)component).transform.Translate(Vector3.back * num5); } } if (Input.GetKeyDown((KeyCode)276)) { ((Component)component).transform.Translate(Vector3.left * num5); } if (Input.GetKeyDown((KeyCode)275)) { ((Component)component).transform.Translate(Vector3.right * num5); } try { isValidPlacement(); } catch { } } private static void isValidPlacement() { //IL_0007: 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_00e3: 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_010c: Unknown result type (might be due to invalid IL or missing references) //IL_00c6: Unknown result type (might be due to invalid IL or missing references) //IL_0128: Unknown result type (might be due to invalid IL or missing references) //IL_015f: Unknown result type (might be due to invalid IL or missing references) //IL_014a: Unknown result type (might be due to invalid IL or missing references) //IL_0176: Unknown result type (might be due to invalid IL or missing references) //IL_01b3: 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_01e1: Invalid comparison between Unknown and I4 //IL_01d0: Unknown result type (might be due to invalid IL or missing references) PlayerInstance.m_placementStatus = (PlacementStatus)0; if (component.m_groundOnly || component.m_groundPiece || component.m_cultivatedGroundOnly) { PlayerInstance.m_placementMarkerInstance.SetActive(false); } StationExtension val = ((Component)component).GetComponent<StationExtension>(); if ((Object)(object)val != (Object)null) { CraftingStation val2 = val.FindClosestStationInRange(((Component)component).transform.position); if (Object.op_Implicit((Object)(object)val2)) { val.StartConnectionEffect(val2, 1f); } else { val.StopConnectionEffect(); PlayerInstance.m_placementStatus = (PlacementStatus)7; } if (val.OtherExtensionInRange(component.m_spaceRequirement)) { PlayerInstance.m_placementStatus = (PlacementStatus)5; } } if (component.m_onlyInTeleportArea && !Object.op_Implicit((Object)(object)EffectArea.IsPointInsideArea(((Component)component).transform.position, (Type)16, 0f))) { PlayerInstance.m_placementStatus = (PlacementStatus)6; } if (!component.m_allowedInDungeons && ((Component)component).transform.position.y > 3000f) { PlayerInstance.m_placementStatus = (PlacementStatus)11; } if (Location.IsInsideNoBuildLocation(PlayerInstance.m_placementGhost.transform.position)) { PlayerInstance.m_placementStatus = (PlacementStatus)3; } float num = (Object.op_Implicit((Object)(object)((Component)component).GetComponent<PrivateArea>()) ? ((Component)component).GetComponent<PrivateArea>().m_radius : 0f); if (!PrivateArea.CheckAccess(PlayerInstance.m_placementGhost.transform.position, num, true, false)) { PlayerInstance.m_placementStatus = (PlacementStatus)4; } if ((int)PlayerInstance.m_placementStatus > 0) { component.SetInvalidPlacementHeightlight(true); } else { component.SetInvalidPlacementHeightlight(false); } } private static void startMode() { notifyUser("Starting ABM", (MessageType)1); isActive = true; component = PlayerInstance.m_placementGhost.GetComponent<Piece>(); } private static void exitMode() { notifyUser("Exiting ABM", (MessageType)1); exitOnNextIteration = true; isActive = false; component = null; } private static bool isInBuildMode() { return ((Character)PlayerInstance).InPlaceMode(); } private static GameObject selectedPrefab() { if ((Object)(object)PlayerInstance.m_buildPieces != (Object)null) { try { return PlayerInstance.m_buildPieces.GetSelectedPrefab(); } catch { return null; } } return null; } private static bool IsHoeOrTerrainTool(GameObject selectedPrefab) { string[] source = new string[4] { "paved_road", "mud_road", "raise", "path" }; string[] source2 = new string[2] { "cultivate", "replant" }; if (((Object)selectedPrefab).name.ToLower().Contains("sapling")) { return true; } if (source.Contains(((Object)selectedPrefab).name) || source2.Contains(((Object)selectedPrefab).name)) { return true; } return false; } private static void notifyUser(string Message, MessageType position = (MessageType)1) { //IL_0006: Unknown result type (might be due to invalid IL or missing references) MessageHud.instance.ShowMessage(position, "ABM: " + Message, 0, (Sprite)null, false, true); } private static void isRunning() { if (isActive) { MessageHud.instance.ShowMessage((MessageType)2, "ABM is active", 0, (Sprite)null, false, true); } } private static void changeModificationSpeed() { //IL_0022: Unknown result type (might be due to invalid IL or missing references) //IL_0072: Unknown result type (might be due to invalid IL or missing references) float num = 1f; if (shiftFlag) { num = 10f; } if (Input.GetKeyDown(Configuration.Current.AdvancedBuildingMode.increaseScrollSpeed)) { currentModificationSpeed = Mathf.Clamp(currentModificationSpeed + num, 1f, 30f); notifyUser("Modification Speed: " + currentModificationSpeed, (MessageType)1); } if (Input.GetKeyDown(Configuration.Current.AdvancedBuildingMode.decreaseScrollSpeed)) { currentModificationSpeed = Mathf.Clamp(currentModificationSpeed - num, 1f, 30f); notifyUser("Modification Speed: " + currentModificationSpeed, (MessageType)1); } } } internal class AEM { public static bool isActive; public static Player PlayerInstance; private static bool controlFlag; private static bool shiftFlag; private static bool altFlag; public static Vector3 HitPoint; public static Vector3 HitNormal; public static Piece HitPiece; public static GameObject HitObject; public static Heightmap HitHeightmap; private static Quaternion InitialRotation; private static Vector3 InitialPosition; private static bool isInExistence; private const float BASE_TRANSLATION_DISTANCE = 0.1f; private const float BASE_ROTATION_ANGLE_DEGREES = 3f; private static float currentModificationSpeed = 1f; private const float MIN_MODIFICATION_SPEED = 1f; private const float MAX_MODIFICATION_SPEED = 30f; private static Quaternion savedRotation; public static bool forceExitNextIteration; public static bool ExecuteRayCast(Player playerInstance) { //IL_0012: 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_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_0090: Unknown result type (might be due to invalid IL or missing references) //IL_0095: Unknown result type (might be due to invalid IL or missing references) //IL_00d7: Unknown result type (might be due to invalid IL or missing references) //IL_00dc: Unknown result type (might be due to invalid IL or missing references) //IL_00eb: Unknown result type (might be due to invalid IL or missing references) //IL_00f0: Unknown result type (might be due to invalid IL or missing references) //IL_0061: Unknown result type (might be due to invalid IL or missing references) //IL_0068: Unknown result type (might be due to invalid IL or missing references) int placeRayMask = playerInstance.m_placeRayMask; RaycastHit val = default(RaycastHit); if (Physics.Raycast(((Component)GameCamera.instance).transform.position, ((Component)GameCamera.instance).transform.forward, ref val, 50f, placeRayMask) && Object.op_Implicit((Object)(object)((RaycastHit)(ref val)).collider) && !Object.op_Implicit((Object)(object)((RaycastHit)(ref val)).collider.attachedRigidbody) && Vector3.Distance(Helper.getPlayerCharacter(playerInstance).m_eye.position, ((RaycastHit)(ref val)).point) < playerInstance.m_maxPlaceDistance) { HitPoint = ((RaycastHit)(ref val)).point; HitNormal = ((RaycastHit)(ref val)).normal; HitPiece = ((Component)((RaycastHit)(ref val)).collider).GetComponentInParent<Piece>(); HitObject = ((Component)((RaycastHit)(ref val)).collider).gameObject; HitHeightmap = ((Component)((RaycastHit)(ref val)).collider).GetComponent<Heightmap>(); InitialRotation = ((Component)HitPiece).transform.rotation; InitialPosition = ((Component)HitPiece).transform.position; return isValidRayCastTarget(); } resetObjectInfo(); return false; } public static bool checkForObject() { if ((Object)(object)PlayerInstance == (Object)null) { return false; } if (!ExecuteRayCast(PlayerInstance)) { return false; } return true; } public static void run() { //IL_00bb: 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) if (forceExitNextIteration) { forceExitNextIteration = false; resetObjectInfo(); isActive = false; return; } if (isInBuildMode()) { if (isActive) { exitMode(); resetObjectTransform(); } return; } if (ABM.isActive) { if (isActive) { exitMode(); resetObjectTransform(); } return; } if (!isActive && Input.GetKeyDown(Configuration.Current.AdvancedEditingMode.enterAdvancedEditingMode)) { if (checkForObject()) { startMode(); } return; } if (Input.GetKeyDown(Configuration.Current.AdvancedEditingMode.abortAndExitAdvancedEditingMode)) { exitMode(); resetObjectTransform(); } if (!isActive) { return; } if (hitPieceStillExists()) { try { ZNetView component = ((Component)HitPiece).GetComponent<ZNetView>(); if ((Object)(object)component == (Object)null) { ValheimPlusPlugin.Logger.LogWarning((object)"AEM: Error, network object empty. Code: 2."); exitMode(); return; } } catch { ValheimPlusPlugin.Logger.LogWarning((object)"AEM: Error, network object empty. Code: 3."); exitMode(); } isRunning(); listenToHotKeysAndDoWork(); } else { exitMode(); } } private static void listenToHotKeysAndDoWork() { //IL_001d: Unknown result type (might be due to invalid IL or missing references) //IL_003f: Unknown result type (might be due to invalid IL or missing references) //IL_007a: 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_00a9: Unknown result type (might be due to invalid IL or missing references) //IL_00b8: Unknown result type (might be due to invalid IL or missing references) //IL_00cc: Unknown result type (might be due to invalid IL or missing references) //IL_00d2: Unknown result type (might be due to invalid IL or missing references) //IL_01ee: Unknown result type (might be due to invalid IL or missing references) //IL_021e: Unknown result type (might be due to invalid IL or missing references) //IL_0209: Unknown result type (might be due to invalid IL or missing references) //IL_020e: Unknown result type (might be due to invalid IL or missing references) //IL_024f: Unknown result type (might be due to invalid IL or missing references) //IL_025e: Unknown result type (might be due to invalid IL or missing references) //IL_0239: Unknown result type (might be due to invalid IL or missing references) //IL_02cd: Unknown result type (might be due to invalid IL or missing references) //IL_02e5: Unknown result type (might be due to invalid IL or missing references) //IL_02f9: Unknown result type (might be due to invalid IL or missing references) //IL_0303: Unknown result type (might be due to invalid IL or missing references) //IL_0308: Unknown result type (might be due to invalid IL or missing references) //IL_040b: Unknown result type (might be due to invalid IL or missing references) //IL_0423: Unknown result type (might be due to invalid IL or missing references) //IL_0437: Unknown result type (might be due to invalid IL or missing references) //IL_0441: Unknown result type (might be due to invalid IL or missing references) //IL_0446: Unknown result type (might be due to invalid IL or missing references) //IL_0381: Unknown result type (might be due to invalid IL or missing references) //IL_0395: Unknown result type (might be due to invalid IL or missing references) //IL_03ad: Unknown result type (might be due to invalid IL or missing references) //IL_03b7: Unknown result type (might be due to invalid IL or missing references) //IL_03bc: Unknown result type (might be due to invalid IL or missing references) //IL_032e: Unknown result type (might be due to invalid IL or missing references) //IL_0342: Unknown result type (might be due to invalid IL or missing references) //IL_0356: Unknown result type (might be due to invalid IL or missing references) //IL_0364: 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_03c9: Unknown result type (might be due to invalid IL or missing references) //IL_0564: Unknown result type (might be due to invalid IL or missing references) //IL_056b: Unknown result type (might be due to invalid IL or missing references) //IL_0544: Unknown result type (might be due to invalid IL or missing references) //IL_054b: Unknown result type (might be due to invalid IL or missing references) //IL_04bf: Unknown result type (might be due to invalid IL or missing references) //IL_04d3: Unknown result type (might be due to invalid IL or missing references) //IL_04eb: Unknown result type (might be due to invalid IL or missing references) //IL_04f5: Unknown result type (might be due to invalid IL or missing references) //IL_04fa: Unknown result type (might be due to invalid IL or missing references) //IL_046c: Unknown result type (might be due to invalid IL or missing references) //IL_0480: Unknown result type (might be due to invalid IL or missing references) //IL_0494: Unknown result type (might be due to invalid IL or missing references) //IL_04a2: Unknown result type (might be due to invalid IL or missing references) //IL_04a7: Unknown result type (might be due to invalid IL or missing references) //IL_0507: Unknown result type (might be due to invalid IL or missing references) //IL_05ee: Unknown result type (might be due to invalid IL or missing references) //IL_05f5: Unknown result type (might be due to invalid IL or missing references) //IL_05bf: Unknown result type (might be due to invalid IL or missing references) //IL_05c6: Unknown result type (might be due to invalid IL or missing references) //IL_059f: Unknown result type (might be due to invalid IL or missing references) //IL_05a6: Unknown result type (might be due to invalid IL or missing references) //IL_061c: Unknown result type (might be due to invalid IL or missing references) //IL_0623: Unknown result type (might be due to invalid IL or missing references) float num = 0f; float num2 = 0f; float num3 = 0f; if (Input.GetKeyDown(Configuration.Current.AdvancedEditingMode.resetAdvancedEditingMode)) { resetObjectTransform(); } if (Input.GetKeyDown(Configuration.Current.AdvancedEditingMode.confirmPlacementOfAdvancedEditingMode)) { if (isContainer()) { dropContainerContents(); } GameObject val = Object.Instantiate<GameObject>(((Component)HitPiece).gameObject, ((Component)HitPiece).transform.position, ((Component)HitPiece).transform.rotation); HitPiece.m_placeEffect.Create(((Component)HitPiece).transform.position, ((Component)HitPiece).transform.rotation, val.transform, 1f, -1, default(ZDOID)); ZNetView component = ((Component)HitPiece).GetComponent<ZNetView>(); if ((Object)(object)component == (Object)null) { ValheimPlusPlugin.Logger.LogWarning((object)"AEM: Error, network object empty."); resetObjectTransform(); exitMode(); } else { component.ClaimOwnership(); ZNetScene.instance.Destroy(((Component)HitPiece).gameObject); ValheimPlusPlugin.Logger.LogDebug((object)"AEM: Executed."); exitMode(); } return; } if (Input.GetKeyDown((KeyCode)306)) { controlFlag = true; } if (Input.GetKeyUp((KeyCode)306)) { controlFlag = false; } if (Input.GetKeyDown((KeyCode)304)) { shiftFlag = true; } if (Input.GetKeyUp((KeyCode)304)) { shiftFlag = false; } if (Input.GetKeyDown((KeyCode)308)) { altFlag = true; } if (Input.GetKeyUp((KeyCode)308)) { altFlag = false; } changeModificationSpeed(); if (Input.GetKeyUp(Configuration.Current.AdvancedEditingMode.copyObjectRotation)) { savedRotation = ((Component)HitPiece).transform.rotation; } if (Input.GetKeyUp(Configuration.Current.AdvancedEditingMode.pasteObjectRotation)) { ((Component)HitPiece).transform.rotation = savedRotation; } if (Vector3.Distance(((Component)PlayerInstance).transform.position, ((Component)HitPiece).transform.position) > PlayerInstance.m_maxPlaceDistance) { resetObjectTransform(); exitMode(); } float num4 = 3f * currentModificationSpeed; if (Input.GetAxis("Mouse ScrollWheel") > 0f) { Quaternion rotation; if (controlFlag) { num += 1f; rotation = Quaternion.Euler(((Component)HitPiece).transform.eulerAngles.x + num4 * num, ((Component)HitPiece).transform.eulerAngles.y, ((Component)HitPiece).transform.eulerAngles.z); } else if (altFlag) { num2 += 1f; rotation = Quaternion.Euler(((Component)HitPiece).transform.eulerAngles.x, ((Component)HitPiece).transform.eulerAngles.y, ((Component)HitPiece).transform.eulerAngles.z + num4 * num2); } else { num3 += 1f; rotation = Quaternion.Euler(((Component)HitPiece).transform.eulerAngles.x, ((Component)HitPiece).transform.eulerAngles.y + num4 * num3, ((Component)HitPiece).transform.eulerAngles.z); } ((Component)HitPiece).transform.rotation = rotation; } if (Input.GetAxis("Mouse ScrollWheel") < 0f) { Quaternion rotation2; if (controlFlag) { num -= 1f; rotation2 = Quaternion.Euler(((Component)HitPiece).transform.eulerAngles.x + num4 * num, ((Component)HitPiece).transform.eulerAngles.y, ((Component)HitPiece).transform.eulerAngles.z); } else if (altFlag) { num2 -= 1f; rotation2 = Quaternion.Euler(((Component)HitPiece).transform.eulerAngles.x, ((Component)HitPiece).transform.eulerAngles.y, ((Component)HitPiece).transform.eulerAngles.z + num4 * num2); } else { num3 -= 1f; rotation2 = Quaternion.Euler(((Component)HitPiece).transform.eulerAngles.x, ((Component)HitPiece).transform.eulerAngles.y + num4 * num3, ((Component)HitPiece).transform.eulerAngles.z); } ((Component)HitPiece).transform.rotation = rotation2; } float num5 = 0.1f * currentModificationSpeed; if (Input.GetKeyDown((KeyCode)273)) { if (controlFlag) { ((Component)HitPiece).transform.Translate(Vector3.up * num5); } else { ((Component)HitPiece).transform.Translate(Vector3.forward * num5); } } if (Input.GetKeyDown((KeyCode)274)) { if (controlFlag) { ((Component)HitPiece).transform.Translate(Vector3.down * num5); } else { ((Component)HitPiece).transform.Translate(Vector3.back * num5); } } if (Input.GetKeyDown((KeyCode)276)) { ((Component)HitPiece).transform.Translate(Vector3.left * num5); } if (Input.GetKeyDown((KeyCode)275)) { ((Component)HitPiece).transform.Translate(Vector3.right * num5); } } private static bool hitPieceStillExists() { try { if (isActive) { isInExistence = true; } } catch { isInExistence = false; } return isInExistence; } private static bool isValidRayCastTarget() { //IL_0019: Unknown result type (might be due to invalid IL or missing references) //IL_0053: Unknown result type (might be due to invalid IL or missing references) //IL_0079: Unknown result type (might be due to invalid IL or missing references) //IL_00bf: Unknown result type (might be due to invalid IL or missing references) bool result = true; if (HitPiece.m_onlyInTeleportArea && !Object.op_Implicit((Object)(object)EffectArea.IsPointInsideArea(((Component)HitPiece).transform.position, (Type)16, 0f))) { result = false; } if (!HitPiece.m_allowedInDungeons && ((Component)HitPiece).transform.position.y > 3000f) { result = false; } if (Location.IsInsideNoBuildLocation(((Component)HitPiece).transform.position)) { result = false; } float num = (Object.op_Implicit((Object)(object)((Component)HitPiece).GetComponent<PrivateArea>()) ? ((Component)HitPiece).GetComponent<PrivateArea>().m_radius : 0f); if (!PrivateArea.CheckAccess(((Component)HitPiece).transform.position, num, true, false)) { result = false; } return result; } private static bool isInBuildMode() { return ((Character)PlayerInstance).InPlaceMode(); } private static void resetObjectTransform() { //IL_0017: Unknown result type (might be due to invalid IL or missing references) //IL_002c: Unknown result type (might be due to invalid IL or missing references) notifyUser("Object has been reset to initial position & rotation.", (MessageType)1); ((Component)HitPiece).transform.position = InitialPosition; ((Component)HitPiece).transform.rotation = InitialRotation; } private static void resetObjectInfo() { //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_000b: Unknown result type (might be due to invalid IL or missing references) //IL_0010: Unknown result type (might be due to invalid IL or missing references) //IL_002c: Unknown result type (might be due to invalid IL or missing references) //IL_0037: Unknown result type (might be due to invalid IL or missing references) HitPoint = Vector3.zero; HitNormal = Vector3.zero; HitObject = null; HitPiece = null; HitHeightmap = null; InitialRotation = default(Quaternion); InitialPosition = default(Vector3); } private static void startMode() { notifyUser("Entering AEM", (MessageType)1); isActive = true; } private static void exitMode() { notifyUser("Exiting AEM", (MessageType)1); forceExitNextIteration = true; } private static void notifyUser(string Message, MessageType position = (MessageType)1) { //IL_0006: Unknown result type (might be due to invalid IL or missing references) MessageHud.instance.ShowMessage(position, "AEM: " + Message, 0, (Sprite)null, false, true); } private static void isRunning() { if (isActive) { MessageHud.instance.ShowMessage((MessageType)2, "AEM is active", 0, (Sprite)null, false, true); } } private static bool isContainer() { Container component = ((Component)HitPiece).GetComponent<Container>(); return (Object)(object)component != (Object)null; } private static void dropContainerContents() { Container component = ((Component)HitPiece).GetComponent<Container>(); component.DropAllItems(); } private static void changeModificationSpeed() { //IL_0022: Unknown result type (might be due to invalid IL or missing references) //IL_0072: Unknown result type (might be due to invalid IL or missing references) float num = 1f; if (shiftFlag) { num = 10f; } if (Input.GetKeyDown(Configuration.Current.AdvancedEditingMode.increaseScrollSpeed)) { currentModificationSpeed = Mathf.Clamp(currentModificationSpeed + num, 1f, 30f); notifyUser("Modification Speed: " + currentModificationSpeed, (MessageType)1); } if (Input.GetKeyDown(Configuration.Current.AdvancedEditingMode.decreaseScrollSpeed)) { currentModificationSpeed = Mathf.Clamp(currentModificationSpeed - num, 1f, 30f); notifyUser("Modification Speed: " + currentModificationSpeed, (MessageType)1); } } } [HarmonyPatch(typeof(Player), "UpdatePlacementGhost")] public static class Player_UpdatePlacementGhost_Transpile { private static readonly MethodInfo Method_Quaternion_Euler = AccessTools.Method(typeof(Quaternion), "Euler", new Type[3] { typeof(float), typeof(float), typeof(float) }, (Type[])null); private static readonly MethodInfo Method_GetRotation = AccessTools.Method(typeof(Player_UpdatePlacementGhost_Transpile), "GetRotation", (Type[])null, (Type[])null); [UsedImplicitly] [HarmonyTranspiler] public static IEnumerable<CodeInstruction> Transpiler(IEnumerable<CodeInstruction> instructions) { //IL_0084: Unknown result type (might be due to invalid IL or missing references) //IL_008a: Expected O, but got Unknown //IL_0093: Unknown result type (might be due to invalid IL or missing references) //IL_0099: Expected O, but got Unknown //IL_00a5: Unknown result type (might be due to invalid IL or missing references) //IL_00ab: Expected O, but got Unknown //IL_00b4: Unknown result type (might be due to invalid IL or missing references) //IL_00ba: Expected O, but got Unknown if (!Configuration.Current.FreePlacementRotation.IsEnabled) { return instructions; } List<CodeInstruction> list = instructions.ToList(); for (int i = 0; i < list.Count; i++) { if (CodeInstructionExtensions.Calls(list[i], Method_Quaternion_Euler) && list[i + 1].opcode == OpCodes.Stloc_S) { object operand = list[i + 1].operand; list.InsertRange(i + 2, (IEnumerable<CodeInstruction>)(object)new CodeInstruction[4] { new CodeInstruction(OpCodes.Ldarg_0, (object)null), new CodeInstruction(OpCodes.Ldloc_S, operand), new CodeInstruction(OpCodes.Call, (object)Method_GetRotation), new CodeInstruction(OpCodes.Stloc_S, operand) }); return list.AsEnumerable(); } } PatchLog.Failed("Player_UpdatePlacementGhost_Transpile", "Free placement rotation will not work."); return list.AsEnumerable(); } public static Quaternion GetRotation(Player __instance, Quaternion quaternion) { //IL_000a: Unknown result type (might be due to invalid IL or missing references) //IL_000b: Unknown result type (might be due to invalid IL or missing references) //IL_0037: Unknown result type (might be due to invalid IL or missing references) //IL_002a: Unknown result type (might be due to invalid IL or missing references) //IL_002f: Unknown result type (might be due to invalid IL or missing references) //IL_0046: Unknown result type (might be due to invalid IL or missing references) //IL_003c: Unknown result type (might be due to invalid IL or missing references) //IL_003d: Unknown result type (might be due to invalid IL or missing references) //IL_003e: Unknown result type (might be due to invalid IL or missing references) //IL_0043: Unknown result type (might be due to invalid IL or missing references) if (ABM.isActive) { return quaternion; } FreePlacementRotation.PlayerData value; Vector3 val = (FreePlacementRotation.PlayersData.TryGetValue(__instance, out value) ? value.PlaceRotation : ((float)__instance.m_placeRotation * 22.5f * Vector3.up)); return Quaternion.Euler(val); } } public static class FreePlacementRotation { public class PlayerData { public Vector3 PlaceRotation = Vector3.zero; public bool Opposite; public Piece LastPiece; public KeyCode LastKeyCode; } [HarmonyPatch(typeof(Player), "UpdatePlacement")] public static class ModifyPUpdatePlacement { [UsedImplicitly] private static void Postfix(Player __instance, bool takeInput, float dt) { //IL_007c: Unknown result type (might be due to invalid IL or missing references) //IL_008a: Unknown result type (might be due to invalid IL or missing references) FreePlacementRotationConfiguration freePlacementRotation = Configuration.Current.FreePlacementRotation; if (freePlacementRotation.IsEnabled && !ABM.isActive && ((Character)__instance).InPlaceMode() && takeInput && !Hud.IsPieceSelectionVisible()) { if (!PlayersData.ContainsKey(__instance)) { PlayersData[__instance] = new PlayerData(); } RotateWithWheel(__instance); SyncRotationWithTargetInFront(__instance, freePlacementRotation.copyRotationParallel, perpendicular: false); SyncRotationWithTargetInFront(__instance, freePlacementRotation.copyRotationPerpendicular, perpendicular: true); } } private static void RotateWithWheel(Player __instance) { //IL_0049: 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_005a: Unknown result type (might be due to invalid IL or missing references) //IL_005f: Unknown result type (might be due to invalid IL or missing references) //IL_006a: Unknown result type (might be due to invalid IL or missing references) //IL_006f: Unknown result type (might be due to invalid IL or missing references) //IL_0074: Unknown result type (might be due to invalid IL or missing references) //IL_00e0: Unknown result type (might be due to invalid IL or missing references) //IL_00b4: Unknown result type (might be due to invalid IL or missing references) //IL_00b9: Unknown result type (might be due to invalid IL or missing references) //IL_00c4: Unknown result type (might be due to invalid IL or missing references) //IL_00c9: Unknown result type (might be due to invalid IL or missing references) //IL_00ce: Unknown result type (might be due to invalid IL or missing references) //IL_014c: Unknown result type (might be due to invalid IL or missing references) //IL_0151: Unknown result type (might be due to invalid IL or missing references) //IL_0156: Unknown result type (might be due to invalid IL or missing references) //IL_013f: Unknown result type (might be due to invalid IL or missing references) //IL_0144: Unknown result type (might be due to invalid IL or missing references) //IL_00f3: Unknown result type (might be due to invalid IL or missing references) //IL_00f8: Unknown result type (might be due to invalid IL or missing references) //IL_0103: 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_010d: Unknown result type (might be due to invalid IL or missing references) float axis = Input.GetAxis("Mouse ScrollWheel"); PlayerData playerData = PlayersData[__instance]; if (!axis.Equals(0f) || ZInput.GetButton("JoyRotate")) { if (Input.GetKey(Configuration.Current.FreePlacementRotation.rotateY)) { playerData.PlaceRotation += Vector3.up * Mathf.Sign(axis); __instance.m_placeRotation = (int)(playerData.PlaceRotation.y / 22.5f); } else if (Input.GetKey(Configuration.Current.FreePlacementRotation.rotateX)) { playerData.PlaceRotation += Vector3.right * Mathf.Sign(axis); } else if (Input.GetKey(Configuration.Current.FreePlacementRotation.rotateZ)) { playerData.PlaceRotation += Vector3.forward * Mathf.Sign(axis); } else { __instance.m_placeRotation = ClampPlaceRotation(__instance.m_placeRotation); playerData.PlaceRotation = new Vector3(0f, (float)__instance.m_placeRotation * 22.5f, 0f); } playerData.PlaceRotation = ClampAngles(playerData.PlaceRotation); } } private static void SyncRotationWithTargetInFront(Player __instance, KeyCode keyCode, bool perpendicular) { //IL_0016: Unknown result type (might be due to invalid IL or missing references) //IL_0064: Unknown result type (might be due to invalid IL or missing references) //IL_0069: Unknown result type (might be due to invalid IL or missing references) //IL_008d: Unknown result type (might be due to invalid IL or missing references) //IL_0092: Unknown result type (might be due to invalid IL or missing references) //IL_0071: Unknown result type (might be due to invalid IL or missing references) //IL_0081: Unknown result type (might be due to invalid IL or missing references) //IL_0086: Unknown result type (might be due to invalid IL or missing references) //IL_008b: Unknown result type (might be due to invalid IL or missing references) //IL_00b2: Unknown result type (might be due to invalid IL or missing references) //IL_00b3: Unknown result type (might be due to invalid IL or missing references) //IL_00f8: Unknown result type (might be due to invalid IL or missing references) //IL_00fd: 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_00db: Unknown result type (might be due to invalid IL or missing references) //IL_00e0: Unknown result type (might be due to invalid IL or missing references) //IL_00e5: Unknown result type (might be due to invalid IL or missing references) Vector3 val = default(Vector3); Vector3 val2 = default(Vector3); Piece val3 = default(Piece); Heightmap val4 = default(Heightmap); Collider val5 = default(Collider); if (!((Object)(object)__instance.m_placementGhost == (Object)null) && Input.GetKeyUp(keyCode) && __instance.PieceRayTest(ref val, ref val2, ref val3, ref val4, ref val5, false) && !((Object)(object)val3 == (Object)null)) { PlayerData playerData = PlayersData[__instance]; Quaternion val6 = ((Component)val3).transform.rotation; if (perpendicular) { val6 *= Quaternion.Euler(0f, 90f, 0f); } if (playerData.LastKeyCode != keyCode || (Object)(object)playerData.LastPiece != (Object)(object)val3) { playerData.Opposite = false; } playerData.LastKeyCode = keyCode; playerData.LastPiece = val3; if (playerData.Opposite) { val6 *= Quaternion.Euler(0f, 180f, 0f); } playerData.Opposite = !playerData.Opposite; playerData.PlaceRotation = ((Quaternion)(ref val6)).eulerAngles; } } } public static readonly Dictionary<Player, PlayerData> PlayersData = new Dictionary<Player, PlayerData>(); private const int MaxIndex = 16; private static Vector3 ClampAngles(Vector3 angles) { //IL_0000: Unknown result type (might be due to invalid IL or missing references) //IL_000b: Unknown result type (might be due to invalid IL or missing references) //IL_0016: Unknown result type (might be due to invalid IL or missing references) //IL_0021: Unknown result type (might be due to invalid IL or missing references) return new Vector3(ClampAngle(angles.x), ClampAngle(angles.y), ClampAngle(angles.z)); } private static int ClampPlaceRotation(int index) { if (1 == 0) { } int result = ((index < 0) ? (16 + index) : ((index < 16) ? index : (index - 16))); if (1 == 0) { } return result; } private static float ClampAngle(float angle) { if (1 == 0) { } float result = ((angle < 0f) ? (360f + angle) : ((!(angle >= 360f)) ? angle : (angle - 360f))); if (1 == 0) { } return result; } } [HarmonyPatch(typeof(CharacterDrop), "GenerateDropList")] public static class CharacterDrop_GenerateDropList_Patch { private static void Prefix(ref List<Drop> ___m_drops, ref List<Drop> __state) { if (Configuration.Current.LootDrop.IsEnabled) { __state = ___m_drops; ItemDrop val = default(ItemDrop); ___m_drops = ___m_drops.ConvertAll((Drop originalDrop) => (Drop)((!originalDrop.m_prefab.TryGetComponent<ItemDrop>(ref val)) ? ((object)originalDrop) : ((object)new Drop { m_prefab = originalDrop.m_prefab, m_amountMin = (int)Helper.applyModifierValue(originalDrop.m_amountMin, Configuration.Current.LootDrop.lootDropAmountMultiplier), m_amountMax = (int)Helper.applyModifierValue(originalDrop.m_amountMax, Configuration.Current.LootDrop.lootDropAmountMultiplier), m_chance = Helper.applyModifierValue(originalDrop.m_chance, Configuration.Current.LootDrop.lootDropChanceMultiplier), m_onePerPlayer = originalDrop.m_onePerPlayer, m_levelMultiplier = originalDrop.m_levelMultiplier, m_dontScale = originalDrop.m_dontScale }))); } } private static void Postfix(ref List<Drop> ___m_drops, List<Drop> __state) { if (Configuration.Current.LootDrop.IsEnabled) { ___m_drops = __state; } } } [HarmonyPatch(typeof(Piece), "DropResources")] public static class Piece_DropResources_Transpiler { private static MethodInfo method_Piece_IsPlacedByPlayer = AccessTools.Method(typeof(Piece), "IsPlacedByPlayer", (Type[])null, (Type[])null); private static FieldInfo field_Requirement_m_recover = AccessTools.Field(typeof(Requirement), "m_recover"); [HarmonyTranspiler] public static IEnumerable<CodeInstruction> Transpiler(IEnumerable<CodeInstruction> instructions) { //IL_0061: Unknown result type (might be due to invalid IL or missing references) //IL_006b: Expected O, but got Unknown if (!Configuration.Current.Building.IsEnabled) { return instructions; } List<CodeInstruction> list = instructions.ToList(); if (Configuration.Current.Building.alwaysDropResources) { for (int i = 0; i < list.Count; i++) { if (CodeInstructionExtensions.Calls(list[i], method_Piece_IsPlacedByPlayer)) { list[i] = new CodeInstruction(OpCodes.Ldc_I4_1, (object)null); list.RemoveAt(i - 1); } } } if (Configuration.Current.Building.alwaysDropExcludedResources) { for (int j = 0; j < list.Count; j++) { if (CodeInstructionExtensions.LoadsField(list[j], field_Requirement_m_recover, false)) { list.RemoveRange(j - 1, 3); } } } return list.AsEnumerable(); } } [HarmonyPatch(typeof(StationExtension), "Awake")] public static class StationExtension_Awake_Patch { [HarmonyPrefix] public static void Prefix(ref float ___m_maxStationDistance) { if (Configuration.Current.Workbench.IsEnabled) { ___m_maxStationDistance = Configuration.Current.Workbench.workbenchAttachmentRange; } } } internal static class InventoryAssistant { private struct ChestPrefab { public bool IsPublicPieceContainer; public bool IsCart; public bool IsShip; } private const float ChestRangeSlack = 2f; private static readonly List<ZDO> NearbyZdos = new List<ZDO>(); private static readonly Dictionary<int, ChestPrefab> ChestPrefabs = new Dictionary<int, ChestPrefab>(); public static List<Container> GetNearbyChests(GameObject target, float range, bool checkWard = true, bool includeVehicles = true) { if (!Object.op_Implicit((Object)(object)Player.m_localPlayer)) { return new List<Container>(); } long playerId = Player.m_localPlayer.GetPlayerID(); return FindNearbyChests(target, range, includeVehicles, (Container container, Vector3 position) => container.CheckAccess(playerId) && (!checkWard || PrivateArea.CheckAccess(position, 0f, false, true))); } public static List<Container> GetNearbyChestsForMachine(GameObject machine, float range, bool checkWard = true) { //IL_0015: 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) Vector3 machinePosition = machine.transform.position; return FindNearbyChests(machine, range, includeVehicles: true, (Container container, Vector3 position) => (int)container.m_privacy == 2 && (!checkWard || SharesWards(machinePosition, position))); } private static bool SharesWards(Vector3 machine, Vector3 chest) { //IL_0029: Unknown result type (might be due to invalid IL or missing references) //IL_0037: Unknown result type (might be due to invalid IL or missing references) foreach (PrivateArea allArea in PrivateArea.m_allAreas) { if (Object.op_Implicit((Object)(object)allArea) && allArea.IsEnabled() && allArea.IsInside(chest, 0f) && !allArea.IsInside(machine, 0f)) { return false; } } return true; } public static bool NearbyChestsLoaded(Vector3 position, float range) { //IL_0011: Unknown result type (might be due to invalid IL or missing references) //IL_0012: Unknown result type (might be due to invalid IL or missing references) //IL_001a: 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_004c: Unknown result type (might be due to invalid IL or missing references) //IL_004d: Unknown result type (might be due to invalid IL or missing references) //IL_0064: Unknown result type (might be due to invalid IL or missing references) NearbyZdos.Clear(); ZDOMan.instance.FindSectorObjects(ZoneSystem.GetZone(position), new SimulationDistance(1, 0, false), NearbyZdos, (List<ZDO>)null); foreach (ZDO nearbyZdo in NearbyZdos) { Vector3 position2 = nearbyZdo.GetPosition(); if (!(Vector3.Distance(position, position2) > range + 2f) && MachineCouldUseChest(nearbyZdo) && SpawnsOnThisPeer(position2)) { ZNetView val = ZNetScene.instance.FindInstance(nearbyZdo); if (!Object.op_Implicit((Object)(object)val)) { return false; } Container componentInChildren = ((Component)val).GetComponentInChildren<Container>(); if (Object.op_Implicit((Object)(object)componentInChildren) && componentInChildren.m_lastRevision == uint.MaxValue) { return false; } } } return true; } public static bool SpawnsOnThisPeer(Vector3 position) { //IL_0006: Unknown result type (might be due to invalid IL or missing references) //IL_000b: Unknown result type (might be due to invalid IL or missing references) //IL_0011: Unknown result type (might be due to invalid IL or missing references) //IL_0016: Unknown result type (might be due to invalid IL or missing references) //IL_001b: 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_001d: Unknown result type (might be due to invalid IL or missing references) //IL_0022: Unknown result type (might be due to invalid IL or missing references) //IL_002b: Unknown result type (might be due to invalid IL or missing references) //IL_0031: Unknown result type (might be due to invalid IL or missing references) //IL_0040: 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_0063: Unknown result type (might be due to invalid IL or missing references) //IL_0064: Unknown result type (might be due to invalid IL or missing references) SimulationDistance syncedSimulationDistance = ZNet.instance.GetSyncedSimulationDistance(); Vector2s zone = ZoneSystem.GetZone(ZNet.instance.GetReferencePosition()); Vector2s zone2 = ZoneSystem.GetZone(position); int nearSimulationDistance = ((SimulationDistance)(ref syncedSimulationDistance)).NearSimulationDistance; return Mathf.Abs(zone2.x - zone.x) <= nearSimulationDistance && Mathf.Abs(zone2.y - zone.y) <= nearSimulationDistance && (((SimulationDistance)(ref syncedSimulationDistance)).IsClassic || ZoneSystem.instance.ZonesWithinRadius(zone, zone2, nearSimulationDistance, false)); } public static bool MachineCouldUseChest(ZDO zdo) { //IL_0057: Unknown result type (might be due to invalid IL or missing references) //IL_005d: Invalid comparison between Unknown and I4 int prefab = zdo.GetPrefab(); if (!ChestPrefabs.TryGetValue(prefab, out var value)) { GameObject prefab2 = ZNetScene.instance.GetPrefab(prefab); Container val = (((Object)(object)prefab2 != (Object)null) ? prefab2.GetComponentInChildren<Container>(true) : null); if ((Object)(object)val != (Object)null) { value.IsPublicPieceContainer = (int)val.m_privacy == 2 && (Object)(object)((Component)val).GetComponentInParent<Piece>(true) != (Object)null; value.IsCart = (Object)(object)((Component)val).GetComponentInParent<Vagon>(true) != (Object)null; value.IsShip = (Object)(object)((Component)val).GetComponentInParent<Ship>(true) != (Object)null; } ChestPrefabs[prefab] = value; } if (!value.IsPublicPieceContainer) { return false; } CraftFromChestConfiguration craftFromChest = Configuration.Current.CraftFromChest; if (value.IsShip) { return craftFromChest.allowCraftingFromShips; } if (value.IsCart && !craftFromChest.allowCraftingFromCarts) { return false; } return zdo.GetLong(ZDOVars.s_creator, 0L) != 0; } public static int RemoveItemInAmountFromChests(List<Container> chests, ItemData needle, int amount) { int num = 0; foreach (Container chest in chests) { if (amount <= 0) { break; } int num2 = RemoveItemFromChest(chest, needle, amount); num += num2; amount -= num2; } return num; } private static List<Container> FindNearbyChests(GameObject target, float range, bool includeVehicles, Func<Container, Vector3, bool> hasAccessAt) { //IL_0076: Unknown result type (might be due to invalid IL or missing references) //IL_0111: Unknown result type (might be due to invalid IL or missing references) string[] array = new string[1] { "piece" }; if (includeVehicles && (Configuration.Current.CraftFromChest.allowCraftingFromCarts || Configuration.Current.CraftFromChest.allowCraftingFromShips)) { array = new string[3] { "piece", "item", "vehicle" }; } Collider[] source = Physics.OverlapSphere(target.transform.position, range, LayerMask.GetMask(array)); IOrderedEnumerable<Collider> orderedEnumerable = source.OrderBy((Collider x) => Vector3.Distance(((Component)x).gameObject.transform.position, target.transform.position)); List<Container> list = new List<Container>(); foreach (Collider item in orderedEnumerable) { try { Container componentInParent = ((Component)item).GetComponentInParent<Container>(); if (Object.op_Implicit((Object)(object)componentInParent) && componentInParent.m_lastRevision != uint.MaxValue && !list.Contains(componentInParent)) { bool flag = hasAccessAt(componentInParent, ((Component)item).gameObject.transform.position); Piece componentInParent2 = ((Component)componentInParent).GetComponentInParent<Piece>(); bool flag2 = (Object)(object)((Component)componentInParent).GetComponentInParent<Vagon>() != (Object)null; bool flag3 = (Object)(object)((Component)componentInParent).GetComponentInParent<Ship>() != (Object)null; if ((Object)(object)componentInParent2 != (Object)null && flag && componentInParent.GetInventory() != null && (!flag2 || (includeVehicles && Configuration.Current.CraftFromChest.allowCraftingFromCarts)) && (!flag3 || (includeVehicles && Configuration.Current.CraftFromChest.allowCraftingFromShips)) && (componentInParent2.IsPlacedByPlayer() || (flag3 && Configuration.Current.CraftFromChest.allowCraftingFromShips))) { list.Add(componentInParent); } } } catch (Exception arg) { ValheimPlusPlugin.Logger.LogDebug((object)$"GetNearbyChests skipped '{((Object)((Component)item).gameObject).name}': {arg}"); } } return list; } public static List<Container> GetNearbyChestsWithItem(GameObject target, float range, ItemData itemInfo, bool checkWard = true) { List<Container> nearbyChests = GetNearbyChests(target, range, checkWard); List<Container> list = new List<Container>(); foreach (Container item in nearbyChests) { if (ChestContainsItem(item, itemInfo)) { list.Add(item); } } return list; } public static bool ChestContainsItem(Container chest, ItemData needle) { List<ItemData> allItems = chest.GetInventory().GetAllItems(); foreach (ItemData item in allItems) { if (item.m_shared.m_name == needle.m_shared.m_name) { return true; } } return false; } public static bool ChestContainsItem(Container chest, string needle) { List<ItemData> allItems = chest.GetInventory().GetAllItems(); foreach (ItemData item in allItems) { if (item.m_shared.m_name == needle) { return true; } } return false; } public static List<ItemData> GetNearbyChestItems(GameObject target, float range = 10f, bool checkWard = true) { List<ItemData> list = new List<ItemData>(); List<Container> nearbyChests = GetNearbyChests(target, range, checkWard); foreach (Container item in nearbyChests) { List<ItemData> allItems = item.GetInventory().GetAllItems(); foreach (ItemData item2 in allItems) { list.Add(item2); } } return list; } public static List<ItemData> GetNearbyChestItemsByContainerList(List<Container> nearbyChests) { List<ItemData> list = new List<ItemData>(); foreach (Container nearbyChest in nearbyChests) { List<ItemData> allItems = nearbyChest.GetInventory().GetAllItems(); foreach (ItemData item in allItems) { list.Add(item); } } return list; } public static int GetItemAmountInItemList(List<ItemData> itemList, ItemData item, int quality = -1, bool matchWorldLevel = true) { return itemList.Where((ItemData current) => current.m_shared.m_name == item.m_shared.m_name && (quality < 0 || quality == current.m_quality) && (!matchWorldLevel || current.m_worldLevel >= Game.m_worldLevel)).Sum((ItemData current) => current.m_stack); } public static int GetItemAmountInItemList(List<ItemData> itemList, string name, int quality = -1, bool matchWorldLevel = true) { return itemList.Where((ItemData current) => current.m_shared.m_name == name && (quality < 0 || quality == current.m_quality) && (!matchWorldLevel || current.m_worldLevel >= Game.m_worldLevel)).Sum((ItemData current) => current.m_stack); } public static int RemoveItemInAmountFromAllNearbyChests(GameObject target, float range, ItemData needle, int amount, bool checkWard = true) { List<Container> nearbyChests = GetNearbyChests(target, range, checkWard); List<ItemData> nearbyChestItemsByContainerList = GetNearbyChestItemsByContainerList(nearbyChests); int itemAmountInItemList = GetItemAmountInItemList(nearbyChestItemsByContainerList, needle); if (amount == 0) { return 0; } int num = 0; foreach (Container item in nearbyChests) { if (num != amount) { int num2 = RemoveItemFromChest(item, needle, amount); num += num2; amount -= num2; } } return num; } public static int RemoveItemInAmountFromAllNearbyChests(GameObject target, float range, string needle, int amount, bool checkWard = true) { List<Container> nearbyChests = GetNearbyChests(target, range, checkWard); List<ItemData> nearbyChestItemsByContainerList = GetNearbyChestItemsByContainerList(nearbyChests); int itemAmountInItemList = GetItemAmountInItemList(nearbyChestItemsByContainerList, needle); if (amount == 0) { return 0; } int num = 0; foreach (Container item in nearbyChests) { if (num != amount) { int num2 = RemoveItemFromChest(item, needle, amount); num += num2; amount -= num2; } } return num; } public static int RemoveItemFromChest(Container chest, ItemData needle, int amount = 1) { if (!ChestContainsItem(chest, needle)) { return 0; } int num = 0; List<ItemData> allItems = chest.GetInventory().GetAllItems(); foreach (ItemData item in allItems) { if (item.m_shared.m_name == needle.m_shared.m_name) { int num2 = Mathf.Min(item.m_stack, amount); item.m_stack -= num2; amount -= num2; num += num2; if (amount <= 0) { break; } } } if (num == 0) { return 0; } allItems.RemoveAll((ItemData x) => x.m_stack <= 0); chest.m_inventory.m_inventory = allItems; ConveyContainerToNetwork(chest); return num; } public static int RemoveItemFromChest(Container chest, string needle, int amount = 1) { if (!ChestContainsItem(chest, needle)) { return 0; } int num = 0; List<ItemData> allItems = chest.GetInventory().GetAllItems(); foreach (ItemData item in allItems) { if (item.m_shared.m_name == needle) { int num2 = Mathf.Min(item.m_stack, amount); item.m_stack -= num2; amount -= num2; num += num2; if (amount <= 0) { break; } } } if (num == 0) { return 0; } allItems.RemoveAll((ItemData x) => x.m_stack <= 0); chest.m_inventory.m_inventory = allItems; ConveyContainerToNetwork(chest); return num; } public static void ConveyContainerToNetwork(Container c) { c.Save(); c.GetInventory().Changed(false, false); } } [BepInPlugin("org.bepinex.plugins.valheim_plus", "Valheim Plus", "0.10.2.0")] [BepInDependency(/*Could not decode attribute arguments.*/)] [BepInDependency(/*Could not decode attribute arguments.*/)] public class ValheimPlusPlugin : BaseUnityPlugin { internal const string ValheimPlusGuid = "org.bepinex.plugins.valheim_plus"; private const string ValheimPlusName = "Valheim Plus"; public const string NumericVersion = "0.10.2.0"; private const string VersionExtra = ""; public const string FullVersion = "0.10.2.0"; internal const string MinRequiredNumericVersion = "0.10.2.0"; private static readonly GameVersion MinSupportedGameVersion = new GameVersion(1, 0, 12); private static readonly GameVersion TargetGameVersion = new GameVersion(1, 0, 15); private static readonly Dictionary<GameVersion, string> ExcludeGameVersions = new Dictionary<GameVersion, string>(); public static readonly Timer MapSyncSaveTimer = new Timer(TimeSpan.FromMinutes(5.0).TotalMilliseconds); public static readonly string VPlusDataDirectoryPath; private static readonly Harmony Harmony; private static bool configLoaded; public const string Repository = "https://github.com/Grantapher/ValheimPlus/releases/latest"; private const string ApiRepository = "https://api.github.com/repos/grantapher/valheimPlus/releases/latest"; internal static string newestVersion { get; private set; } = ""; internal static bool isUpToDate { get; private set; } public static ManualLogSource Logger { get; private set; } private void Awake() { Logger = ((BaseUnityPlugin)this).Logger; Logger.LogInfo((object)("Valheim game version: " + Version.GetVersionString(false))); Logger.Log((LogLevel)(("".Length > 0) ? 16 : 32), (object)"Valheim Plus full version: 0.10.2.0"); Logger.LogInfo((object)("Valheim Plus dll file location: '" + ((object)this).GetType().Assembly.Location + "'")); bool flag = IsGameVersionTooOld(); if (flag) { LogTooOld(); } bool flag2 = CheckIsGameVersionExcluded(); if (flag || flag2) { Logger.LogFatal((object)"Aborting loading of Valheim Plus due to incompatible version."); return; } try { BepInExConfig.Load(((BaseUnityPlugin)this).Config); configLoaded = true; Logger.LogInfo((object)("Configuration loaded successfully from '" + ((BaseUnityPlugin)this).Config.ConfigFilePath + "'.")); PatchAll(); isUpToDate = !IsNewVersionAvailable(); if (!isUpToDate) { Logger.LogWarning((object)"There is a newer version available of ValheimPlus. Please visit https://github.com/Grantapher/ValheimPlus/releases/latest."); } else { Logger.LogInfo((object)"ValheimPlus [0.10.2.0] is up to date."); } if (!Directory.Exists(VPlusDataDirectoryPath)) { Directory.CreateDirectory(VPlusDataDirectoryPath); } if (ZNet.m_isServer && Configuration.Current.Map.IsEnabled && Configuration.Current.Map.shareMapProgression) { MapSyncSaveTimer.AutoReset = true; MapSyncSaveTimer.Elapsed += delegate { VPlusMapSync.SaveMapDataToDisk(); }; } } catch (Exception arg) { Logger.LogError((object)$"Error while loading the configuration: {arg}"); } } private void Start() { if (configLoaded) { BepInExConfig.ResolveModConflicts(); } } private static bool IsGameVersionTooOld() { //IL_0000: Unknown result type (might be due to invalid IL or missing references) //IL_0005: Unknown result type (might be due to invalid IL or missing references) return Version.CurrentVersion < MinSupportedGameVersion; } private static bool IsGameVersionNewerThanTarget() { //IL_0000: Unknown result type (might be due to invalid IL or missing references) //IL_0005: Unknown result type (might be due to invalid IL or missing references) return Version.CurrentVersion > TargetGameVersion; } private static bool CheckIsGameVersionExcluded() { //IL_0006: Unknown result type (might be due to invalid IL or missing references) string value; bool flag = ExcludeGameVersions.TryGetValue(Version.CurrentVersion, out value); if (flag) { Logger.LogError((object)value); } return flag; } private static bool IsNewVersionAvailable() { try { string input = HttpHelper.DownloadString("https://api.github.com/repos/grantapher/valheimPlus/releases/latest"); newestVersion = new Regex("\"tag_name\":\"([^\"]*)?\"").Match(input).Groups[1].Value; } catch { Logger.LogWarning((object)"The newest version could not be determined."); newestVersion = "Unknown"; } if (Version.TryParse(newestVersion, out Version result)) { if (Version.TryParse("0.10.2.0", out Version result2)) { if (result2 < result) { return true; } } else { Logger.LogWarning((object)"Couldn't parse current version"); } } else { Logger.LogWarning((object)"Couldn't parse newest version, comparing version strings with equality."); if (newestVersion != "0.10.2.0") { return true; } } return false; } public static void PatchAll() { //IL_0137: Unknown result type (might be due to invalid IL or missing references) //IL_0141: Unknown result type (might be due to invalid IL or missing references) //IL_00bc: Unknown result type (might be due to invalid IL or missing references) //IL_00ca: Expected O, but got Unknown Logger.LogDebug((object)"Applying patches."); try { Type[] typesFromAssembly = AccessTools.GetTypesFromAssembly(typeof(ValheimPlusPlugin).Assembly); foreach (Type type in typesFromAssembly) { if (!ConfigSyncGlue.IsServerSyncType(type)) { Harmony.CreateClassProcessor(type).Patch(); } } if (AppDomain.CurrentDomain.GetAssemblies().Any((Assembly assembly) => assembly.FullName.Contains("assembly_steamworks"))) { Harmony.Patch((MethodBase)AccessTools.TypeByName("SteamGameServer").GetMethod("SetMaxPlayerCount"), new HarmonyMethod(typeof(ChangeSteamServerVariables).GetMethod("Prefix")), (HarmonyMethod)null, (HarmonyMethod)null, (HarmonyMethod)null, (HarmonyMethod)null); } ConfigSyncGlue.SetModRequired(Configuration.Current.Server.enforceMod); Logger.LogDebug((object)"Patches successfully applied."); } catch (Exception) { Logger.LogError((object)"Failed to apply patches."); if (IsGameVersionTooOld()) { LogTooOld(); } else if (IsGameVersionNewerThanTarget()) { Logger.LogWarning((object)("This version of Valheim Plus (0.10.2.0) was compiled with a game version of " + $"\"{TargetGameVersion}\", but this game version is newer at \"{Version.CurrentVersion}\". " + "If you are using the PTB, you likely need to use the non-beta version of the game. Otherwise, the errors seen above likely will require the Valheim Plus mod to be updated. If a game update just came out for Valheim, this may take some time for the mod to be updated. See https://github.com/Grantapher/ValheimPlus/blob/grantapher-development/COMPATIBILITY.md for what game versions are compatible with what mod versions.")); } else { Logger.LogWarning((object)("Valheim Plus failed to apply patches. Please ensure the game version (" + Version.GetVersionString(false) + ") is compatible with the Valheim Plus version (0.10.2.0) at https://github.com/Grantapher/ValheimPlus/blob/grantapher-development/COMPATIBILITY.md. If it already is, please report a bug at https://github.com/Grantapher/ValheimPlus/issues.")); } throw; } } private static void LogTooOld() { //IL_0010: 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) Logger.LogError((object)("This version of Valheim Plus (0.10.2.0) expects a minimum game version of " + $"\"{MinSupportedGameVersion}\", but this game version is older at \"{Version.CurrentVersion}\". " + "Please either update the Valheim game, or use an older version of Valheim Plus as per https://github.com/Grantapher/ValheimPlus/blob/grantapher-development/COMPATIBILITY.md.")); } public static void UnpatchSelf() { Logger.LogDebug((object)"Unpatching."); try { Harmony.UnpatchSelf(); Logger.LogDebug((object)"Successfully unpatched."); } catch (Exception arg) { Logger.LogError((object)$"Failed to unpatch. Exception: {arg}"); } } static ValheimPlusPlugin() { //IL_0004: Unknown result type (might be due to invalid IL or missing references) //IL_0009: 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_0017: 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_0080: Expected O, but got Unknown string bepInExRootPath = Paths.BepInExRootPath; char directorySeparatorChar = Path.DirectorySeparatorChar; VPlusDataDirectoryPath = bepInExRootPath + directorySeparatorChar + "vplus-data"; Harmony = new Harmony("mod.valheim_plus"); } } internal static class Helper { private const BindingFlags FieldBindingFlags = BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic; public static Character getPlayerCharacter(Player __instance) { return (Character)(object)__instance; } public static Player getPlayerBySenderId(long id) { //IL_0020: Unknown result type (might be due to invalid IL or missing references) //IL_0025: Unknown result type (might be due to invalid IL or missing references) //IL_0026: Unknown result type (might be due to invalid IL or missing references) //IL_002a: Unknown result type (might be due to invalid IL or missing references) List<Player> allPlayers = Player.GetAllPlayers(); foreach (Player item in allPlayers) { ZDOID zDOID = getPlayerCharacter(item).GetZDOID(); if (zDOID != new ZDOID(0L, 0u) && ((ZDOID)(ref zDOID)).UserID == id) { return item; } } return null; } public static bool IsSenderPlayerInRange(long senderId, float range) { //IL_000e: Unknown result type (might be due to invalid IL or missing references) //IL_001d: Unknown result type (might be due to invalid IL or missing references) Player playerBySenderId = getPlayerBySenderId(senderId); float num = Vector3.Distance(((Component)playerBySenderId).transform.position, ((Component)Player.m_localPlayer).transform.position); return num <= range; } public static float tFloat(this float value, int digits) { double num = Math.Pow(10.0, digits); double num2 = Math.Truncate(num * (double)value) / num; return (float)num2; } public static float applyModifierValue(float targetValue, float value) { return (value <= -100f) ? 0f : (targetValue + targetValue / 100f * value); } public static void applyModifierValueTo(ref float targetValue, float modifier) { targetValue = ((modifier <= -100f) ? 0f : (targetValue + targetValue / 100f * modifier)); } public static int applyModifierValueWithChance(float targetValue, float value) { float num = applyModifierValue(targetValue, value); if (num == 0f) { return 0; } int num2 = (int)Math.Floor(num); return num2 + (((double)(num - (float)num2) > 1.0 - new Random().NextDouble()) ? 1 : 0); } public static string CreateMD5(string input) { using MD5 mD = MD5.Create(); byte[] bytes = Encoding.ASCII.GetBytes(input); byte[] array = mD.ComputeHash(bytes); StringBuilder stringBuilder = new StringBuilder(); for (int i = 0; i < array.Length; i++) { stringBuilder.Append(array[i].ToString("X2")); } return stringBuilder.ToString(); } public static void ResizeChildEffectArea(MonoBehaviour parent, Type includedTypes, float newRadius) { //IL_0021: Unknown result type (might be due to invalid IL or missing references) //IL_0026: Unknown result type (might be due to invalid IL or missing references) //IL_0027: Unknown result type (might be due to invalid IL or missing references) //IL_0029: Invalid comparison between Unknown and I4 if (!((Object)(object)parent != (Object)null)) { return; } EffectArea componentInChildren = ((Component)parent).GetComponentInChildren<EffectArea>(); if ((Object)(object)componentInChildren != (Object)null && (componentInChildren.m_type & includedTypes) > 0) { SphereCollider component = ((Component)componentInChildren).GetComponent<SphereCollider>(); if ((Object)(object)component != (Object)null) { component.radius = newRadius; } } } public static int Clamp(int value, int min, int max) { return Math.Min(max, Math.Max(min, value)); } public static float Clamp(float value, float min, float max) { return Math.Min(max, Math.Max(min, value)); } public static bool SetFieldIfFound(object obj, string field, object value) { FieldInfo field2 = obj.GetType().GetField(field, BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic); if (field2 == null) { return false; } field2.SetValue(obj, value); return true; } } public static class VPlusDataObjects { public class MapRange { public int StartingX; public int EndingX; public int Y; } } } namespace ValheimPlus.Http { public static class HttpHelper { private const string UserAgent = "ValheimPlusClient/1.0"; public static string DownloadString(string url, TimeSpan? timeout = null) { //IL_0089: Unknown result type (might be due to invalid IL or missing references) //IL_008e: Unknown result type (might be due to invalid IL or missing references) //IL_0097: Expected O, but got Unknown //IL_0098: Unknown result type (might be due to invalid IL or missing references) //IL_009f: Expected O, but got Unknown if (string.IsNullOrWhiteSpace(url)) { throw new ArgumentException("url is null or empty", "url"); } if (!Uri.TryCreate(url, UriKind.Absolute, out Uri result) || (result.Scheme != Uri.UriSchemeHttp && result.Scheme != Uri.UriSchemeHttps)) { throw new ArgumentException("Invalid URL scheme: '" + url + "'", "url"); } try { ServicePointManager.SecurityProtocol |= SecurityProtocolType.Tls12; } catch { } HttpClientHandler val = new HttpClientHandler { AllowAutoRedirect = true }; try { HttpClient val2 = new HttpClient((HttpMessageHandler)(object)val); try { val2.Timeout = timeout ?? TimeSpan.FromSeconds(20.0); val2.DefaultRequestHeaders.UserAgent.Clear(); val2.DefaultRequestHeaders.UserAgent.ParseAdd("ValheimPlusClient/1.0"); val2.DefaultRequestHeaders.Accept.Clear(); val2.DefaultRequestHeaders.Accept.ParseAdd("*/*"); HttpResponseMessage result2 = val2.GetAsync(result).GetAwaiter().GetResult(); result2.EnsureSuccessStatusCode(); return result2.Content.ReadAsStringAsync().GetAwaiter().GetResult(); } finally { ((IDisposable)val2)?.Dispose(); } } finally { ((IDisposable)val)?.Dispose(); } } } } namespace ValheimPlus.Utility { internal static class GameObjectAssistant { private static readonly ConcurrentDictionary<float, Stopwatch> Stopwatches = new ConcurrentDictionary<float, Stopwatch>(); private static readonly MethodInfo InvokeRepeatingMethod = AccessTools.Method(typeof(MonoBehaviour), "InvokeRepeating", (Type[])null, (Type[])null); private const float ChestPollInterval = 1f; private const float MaxChestWait = 10f; public static Stopwatch GetStopwatch(GameObject o) { float gameObjectPositionHash = GetGameObjectPositionHash(o); if (Stopwatches.TryGetValue(gameObjectPositionHash, out var value)) { return value; } value = new Stopwatch(); Stopwatches.TryAdd(gameObjectPositionHash, value); return value; } public static float GetGameObjectPositionHash(GameObject obj) { //IL_0007: Unknown result type (might be due to invalid IL or missing references) //IL_000c: Unknown result type (might be due to invalid IL or missing references) //IL_0012: Unknown result type (might be due to invalid IL or missing references) //IL_0019: Unknown result type (might be due to invalid IL or missing references) //IL_0025: Unknown result type (might be due to invalid IL or missing references) Vector3 position = obj.transform.position; return 1000f * position.x + position.y + 0.001f * position.z; } public static IEnumerable<CodeInstruction> ReplaceInvokeRepeating(IEnumerable<CodeInstruction> instructions, string patchName, string methodName, MethodInfo replacement) { //IL_001d: Unknown result type (might be due to invalid IL or missing references) //IL_003b: Unknown result type (might be due to invalid IL or missing references) //IL_0041: Expected O, but got Unknown return new CodeMatcher(instructions, (ILGenerator)null).MatchStartForward((CodeMatch[])(object)new CodeMatch[1] { new CodeMatch((OpCode?)OpCodes.Ldstr, (object)methodName, (string)null) }).Repeat((Action<CodeMatcher>)delegate(CodeMatcher matcher) { matcher.SearchForward((Func<CodeInstruction, bool>)((CodeInstruction instruction) => CodeInstructionExtensions.Calls(instruction, InvokeRepeatingMethod))).SetOperandAndAdvance((object)replacement); }, (Action<string>)delegate { PatchLog.Failed(patchName, methodName + " will not wait for nearby chests to load before auto-depositing."); }).InstructionEnumeration(); } public static void InvokeRepeatingWhenChestsLoaded(MonoBehaviour machine, string methodName, float delay, float rate, float chestRange) { //IL_0010: Unknown result type (might be due to invalid IL or missing references) if (chestRange <= 0f || InventoryAssistant.NearbyChestsLoaded(((Component)machine).transform.position, chestRange)) { machine.InvokeRepeating(methodName, delay, rate); } else { machine.StartCoroutine(InvokeRepeatingOnceChestsLoaded(machine, methodName, delay, rate, chestRange)); } } private static IEnumerator InvokeRepeatingOnceChestsLoaded(MonoBehaviour machine, string methodName, float delay, float rate, float chestRange) { float waited; for (waited = 0f; waited < 10f; waited += 1f) { if (InventoryAssistant.NearbyChestsLoaded(((Component)machine).transform.position, chestRange)) { break; } yield return (object)new WaitForSeconds(1f); } if (waited >= 10f && !InventoryAssistant.NearbyChestsLoaded(((Component)machine).transform.position, chestRange)) { ValheimPlusPlugin.Logger.LogDebug((object)$"{((Object)machine).name} at {((Component)machine).transform.position} gave up waiting {10f}s for nearby chests to load, starting {methodName} anyway."); } machine.InvokeRepeating(methodName, delay, rate); } public static T GetChildComponentByName<T>(string name, GameObject objected) where T : Component { T[] componentsInChildren = objected.GetComponentsInChildren<T>(true); foreach (T val in componentsInChildren) { if (((Object)((Component)val).gameObject).name == name) { return val; } } return default(T); } } public static class ListExtensions { public static List<List<T>> ChunkBy<T>(this List<T> source, int chunkSize) { return (from x in source.Select((T x, int i) => new { Index = i, Value = x }) group x by x.Index / chunkSize into x select x.Select(v => v.Value).ToList()).ToList(); } } public static class PatchLog { public static void Failed(string patch, string detail = null, Exception exception = null) { string text = "Failed to apply `" + patch + "`."; if (detail != null) { text = text + " " + detail; } if (exception != null) { text += $" Exception is:\n{exception}"; } ValheimPlusPlugin.Logger.LogError((object)text); } } public class RpcData { public string Name; public long Target = 0L; public object[] Payload; } public static class RpcQueue { private static Queue<RpcData> _rpcQueue = new Queue<RpcData>(); private static bool _ack = true; public static void Enqueue(RpcData rpc) { _rpcQueue.Enqueue(rpc); } public static bool SendNextRpc() { if (_rpcQueue.Count == 0 || !_ack) { return false; } RpcData rpcData = _rpcQueue.Dequeue(); if (Utility.IsNullOrWhiteSpace(rpcData.Name) || rpcData.Payload == null) { return false; } ZRoutedRpc.instance.InvokeRoutedRPC(rpcData.Target, rpcData.Name, rpcData.Payload); _ack = false; return true; } public static void GotAck() { _ack = true; } } public static class ZPackageExtensions { public static VPlusDataObjects.MapRange ReadVPlusMapRange(this ZPackage pkg) { return new VPlusDataObjects.MapRange { StartingX = pkg.m_reader.ReadInt32(), EndingX = pkg.m_reader.ReadInt32(), Y = pkg.m_reader.ReadInt32() }; } public static void WriteVPlusMapRange(this ZPackage pkg, VPlusDataObjects.MapRange mapRange) { pkg.m_writer.Write(mapRange.StartingX); pkg.m_writer.Write(mapRange.EndingX); pkg.m_writer.Write(mapRange.Y); } } } namespace ValheimPlus.RPC { public class VPlusAck { public static void RPC_VPlusAck(long sender) { RpcQueue.GotAck(); } public static void SendAck(long target) { ZRoutedRpc.instance.InvokeRoutedRPC(target, "VPlusAck", Array.Empty<object>()); } } public class VPlusMapSync { public static BitArray ServerMapData; public static bool ShouldSyncOnSpawn = true; public static void RPC_VPlusMapSync(long sender, ZPackage mapPkg) { if (ZNet.m_isServer) { if (sender == ZRoutedRpc.instance.GetServerPeerID() || mapPkg == null || ServerMapData == null) { return; } int num = mapPkg.ReadInt(); if (num > 0) { for (int i = 0; i < num; i++) { VPlusDataObjects.MapRange mapRange = mapPkg.ReadVPlusMapRange(); for (int j = mapRange.StartingX; j < mapRange.EndingX; j++) { ServerMapData[mapRange.Y * Minimap.instance.m_textureSize + j] = true; } } ValheimPlusPlugin.Logger.LogDebug((object)$"Received {num} map ranges from peer #{sender}."); VPlusAck.SendAck(sender); } if (!mapPkg.ReadBool()) { return; } List<VPlusDataObjects.MapRange> list = ExplorationDataToMapRanges(ServerMapData); List<ZPackage> list2 = ChunkMapData(list); foreach (ZPackage item in list2) { RpcData rpcData = new RpcData(); rpcData.Name = "VPlusMapSync"; rpcData.Payload = new object[1] { item }; rpcData.Target = 0L; RpcQueue.Enqueue(rpcData); } ValheimPlusPlugin.Logger.LogDebug((object)$"Sent map updates to all clients ({list.Count} map ranges, {list2.Count} chunks)"); } else { if (sender != ZRoutedRpc.instance.GetServerPeerID()) { return; } if (mapPkg == null) { ValheimPlusPlugin.Logger.LogWarning((object)"Warning: Got empty map sync package from server."); return; } int num2 = mapPkg.ReadInt(); if (num2 > 0) { for (int k = 0; k < num2; k++) { VPlusDataObjects.MapRange mapRange2 = mapPkg.ReadVPlusMapRange(); for (int l = mapRange2.StartingX; l < mapRange2.EndingX; l++) { Minimap.instance.Explore(l, mapRange2.Y); } } Minimap.instance.m_fogTexture.Apply(); ValheimPlusPlugin.Logger.LogDebug((object)$"I got {num2} map ranges from the server!"); VPlusAck.SendAck(sender); } else { ValheimPlusPlugin.Logger.LogDebug((object)"Server has no explored areas to sync, continuing."); } } } public static void SendMapToServer() { //IL_001f: Unknown result type (might be due to invalid IL or missing references) //IL_0025: Expected O, but got Unknown List<VPlusDataObjects.MapRange> list = ExplorationDataToMapRanges(Minimap.instance.m_explored); if (list.Count == 0) { ZPackage val = new ZPackage(); val.Write(0); val.Write(true); ZRoutedRpc.instance.InvokeRoutedRPC(ZRoutedRpc.instance.GetServerPeerID(), "VPlusMapSync", new object[1] { val }); return; } List<ZPackage> list2 = ChunkMapData(list); foreach (ZPackage item in list2) { RpcData rpcData = new RpcData(); rpcData.Name = "VPlusMapSync"; rpcData.Payload = new object[1] { item }; rpcData.Target = ZRoutedRpc.instance.GetServerPeerID(); RpcQueue.Enqueue(rpcData); } ValheimPlusPlugin.Logger.LogDebug((object)$"Sent my map data to the server ({list.Count} map ranges, {list2.Count} chunks)"); } public static void LoadMapDataFromDisk() { if (ServerMapData == null) { return; } string vPlusDataDirectoryPath = ValheimPlusPlugin.VPlusDataDirectoryPath; char directorySeparatorChar = Path.DirectorySeparatorChar; if (!File.Exists(vPlusDataDirectoryPath + directorySeparatorChar + ZNet.instance.GetWorldName() + "_mapSync.dat")) { return; } try { string vPlusDataDirectoryPath2 = ValheimPlusPlugin.VPlusDataDirectoryPath; directorySeparatorChar = Path.DirectorySeparatorChar; string text = File.ReadAllText(vPlusDataDirectoryPath2 + directorySeparatorChar + ZNet.instance.GetWorldName() + "_mapSync.dat"); string[] array = text.Split(new char[1] { ',' }); string[] array2 = array; foreach (string s in array2) { if (int.TryParse(s, out var result)) { ServerMapData[result] = true; } } ValheimPlusPlugin.Logger.LogDebug((object)$"Loaded {array.Length} map points from disk."); } catch (Exception ex) { ValheimPlusPlugin.Logger.LogError((object)"Failed to load synchronized map data."); ValheimPlusPlugin.Logger.LogError((object)ex); } } public static void SaveMapDataToDisk() { if (ServerMapData == null) { return; } List<int> list = new List<int>(); for (int i = 0; i < Minimap.instance.m_textureSize; i++) { for (int j = 0; j < Minimap.instance.m_textureSize; j++) { if (ServerMapData[i * Minimap.instance.m_textureSize + j]) { list.Add(i * Minimap.instance.m_textureSize + j); } } } if (list.Count > 0) { string vPlusDataDirectoryPath = ValheimPlusPlugin.VPlusDataDirectoryPath; char directorySeparatorChar = Path.DirectorySeparatorChar; File.Delete(vPlusDataDirectoryPath + directorySeparatorChar + ZNet.instance.GetWorldName() + "_mapSync.dat"); string vPlusDataDirectoryPath2 = ValheimPlusPlugin.VPlusDataDirectoryPath; directorySeparatorChar = Path.DirectorySeparatorChar; File.WriteAllText(vPlusDataDirectoryPath2 + directorySeparatorChar + ZNet.instance.GetWorldName() + "_mapSync.dat", string.Join(",", list)); ValheimPlusPlugin.Logger.LogDebug((object)$"Saved {list.Count} map points to disk."); } } private static List<VPlusDataObjects.MapRange> ExplorationDataToMapRanges(BitArray explorationData) { List<VPlusDataObjects.MapRange> list = new List<VPlusDataObjects.MapRange>(); for (int i = 0; i < Minimap.instance.m_textureSize; i++) { int num = -1; int num2 = -1; for (int j = 0; j < Minimap.instance.m_textureSize; j++) { if (explorationData[i * Minimap.instance.m_textureSize + j] && num == -1 && num2 == -1) { num = j; } else if (!explorationData[i * Minimap.instance.m_textureSize + j] && num > -1 && num2 == -1) { num2 = j - 1; } else if (num > -1 && num2 > -1) { list.Add(new VPlusDataObjects.MapRange { StartingX = num, EndingX = num2, Y = i }); num = -1; num2 = -1; } } if (num > -1 && num2 == -1) { list.Add(new VPlusDataObjects.MapRange { StartingX = num, EndingX = Minimap.instance.m_textureSize, Y = i }); } } return list; } private static List<ZPackage> ChunkMapData(List<VPlusDataObjects.MapRange> mapData, int chunkSize = 10000) { //IL_0041: Unknown result type (might be due to invalid IL or missing references) //IL_0048: Expected O, but got Unknown if (mapData == null || mapData.Count == 0) { return null; } List<List<VPlusDataObjects.MapRange>> list = mapData.ChunkBy(chunkSize); List<ZPackage> list2 = new List<ZPackage>(); foreach (List<VPlusDataObjects.MapRange> item in list) { ZPackage val = new ZPackage(); val.Write(item.Count); foreach (VPlusDataObjects.MapRange item2 in item) { val.WriteVPlusMapRange(item2); } if (item == list.Last()) { val.Write(true); } else { val.Write(false); } list2.Add(val); } return list2; } } } namespace ValheimPlus.UI { [HarmonyPatch(typeof(HotkeyBar), "UpdateIcons")] public static class HotkeyBar_UpdateIcons_Patch { private const string hudObjectNamePrefix = "BowAmmoCounts"; private const string noAmmoDisplay = "No Ammo"; private static readonly GameObject[] ammoCounters = (GameObject[])(object)new GameObject[8]; private static int elementCount = -1; private static bool IsEnabled() { return Configuration.Current.Hud.IsEnabled && Configuration.Current.Hud.displayBowAmmoCounts > 0; } private static void Prefix(HotkeyBar __instance, Player player) { if (IsEnabled()) { elementCount = __instance.m_elements.Count; if ((Object)(object)player == (Object)null || ((Character)player).IsDead()) { DestroyAllAmmoCounters(); } } } private static void Postfix(HotkeyBar __instance, Player player) { if (IsEnabled()) { if (elementCount != __instance.m_elements.Count) { DestroyAllAmmoCounters(); } if (!((Object)(object)player == (Object)null) && !((Character)player).IsDead()) { DisplayAmmoCountsUnderBowHotbarIcons(__instance, player); } } } private static void DisplayAmmoCountsUnderBowHotbarIcons(HotkeyBar __instance, Player player) { HashSet<int> hashSet = new HashSet<int> { 0, 1, 2, 3, 4, 5, 6, 7 }; foreach (ItemData item in __instance.m_items) { if (item != null) { hashSet.Remove(item.m_gridPos.x); DisplayAmmoCountsUnderBowHotbarIcon(__instance, player, item); } } foreach (int item2 in hashSet) { DestroyAmmoCounter(item2); } } private static void DisplayAmmoCountsUnderBowHotbarIcon(HotkeyBar __instance, Player player, ItemData item) { //IL_001b: Unknown result type (might be due to invalid IL or missing references) //IL_0021: Invalid comparison between Unknown and I4 //IL_00cd: Unknown result type (might be due to invalid IL or missing references) //IL_00dd: Unknown result type (might be due to invalid IL or missing references) //IL_00e2: Unknown result type (might be due to invalid IL or missing references) //IL_00f1: Unknown result type (might be due to invalid IL or missing references) //IL_00f6: Unknown result type (might be due to invalid IL or missing references) //IL_00fb: Unknown result type (might be due to invalid IL or missing references) //IL_0103: Unknown result type (might be due to invalid IL or missing references) //IL_01fd: Unknown result type (might be due to invalid IL or missing references) //IL_0204: Invalid comparison between Unknown and I4 //IL_020d: Unknown result type (might be due to invalid IL or missing references) //IL_0213: Invalid comparison between Unknown and I4 int x = item.m_gridPos.x; GameObject val = ammoCounters[x]; if ((int)item.m_shared.m_itemType != 4 || (Configuration.Current.Hud.displayBowAmmoCounts == 1 && !((Humanoid)player).IsItemEquiped(item)) || x >= __instance.m_elements.Count || x < 0) { DestroyAmmoCounter(x); return; } ElementData val2 = __instance.m_elements[x]; TMP_Text componentInChildren; if ((Object)(object)val == (Object)null) { GameObject gameObject = ((Component)val2.m_amount).gameObject; val = Object.Instantiate<GameObject>(gameObject, gameObject.transform.parent, false); ((Object)val).name = "BowAmmoCounts" + x; val.SetActive(true); Vector3 val3 = gameObject.transform.position - ((Component)val2.m_icon).transform.position - new Vector3(0f, 15f); val.transform.Translate(val3); componentInChildren = val.GetComponentInChildren<TMP_Text>(); TMP_Text obj = componentInChildren; obj.fontSize -= 2f; ammoCounters[x] = val; } else { componentInChildren = val.GetComponentInChildren<TMP_Text>(); } val.gameObject.transform.SetParent(((Component)val2.m_amount).gameObject.transform.parent, false); ItemData ammoItem = ((Humanoid)player).m_ammoItem; if (ammoItem == null || ammoItem.m_shared.m_ammoType != item.m_shared.m_ammoType) { ammoItem = ((Humanoid)player).GetInventory().GetAmmoItem(item.m_shared.m_ammoType, (string)null); } int num = 0; int num2 = 0; List<ItemData> allItems = ((Humanoid)player).GetInventory().GetAllItems(); foreach (ItemData item2 in allItems) { if (item2.m_shared.m_ammoType == item.m_shared.m_ammoType && ((int)item2.m_shared.m_itemType == 9 || (int)item2.m_shared.m_itemType == 2)) { num2 += item2.m_stack; if (item2.m_shared.m_name == ammoItem.m_shared.m_name) { num += item2.m_stack; } } } if (num2 == 0) { componentInChildren.text = "No Ammo"; return; } componentInChildren.text = ammoItem.m_shared.m_name.Split(new char[1] { '_' }).Last() + "\n" + num + "/" + num2; } private static void DestroyAllAmmoCounters() { for (int i = 0; i < 8; i++) { DestroyAmmoCounter(i); } } private static void DestroyAmmoCounter(int index) { GameObject val = ammoCounters[index]; if ((Object)(object)val != (Object)null) { Object.Destroy((Object)(object)val); ammoCounters[index] = null; } } } } namespace ValheimPlus.GameClasses { public static class BedHelper { public static bool CanSleepWithoutSpawn(this Bed bed) { return Configuration.Current.Bed.IsEnabled && Configuration.Current.Bed.sleepWithoutSpawn && !bed.IsCurrent() && (!Configuration.Current.Bed.unclaimedBedsOnly || bed.GetOwner() == 0); } public static void InteractWithoutOwnershipReadWrite(this Bed bed, Player player) { //IL_0072: Unknown result type (might be due to invalid IL or missing references) if (!EnvMan.CanSleep()) { ((Character)player).Message((MessageType)2, "$msg_cantsleep", 0, (Sprite)null, false); } else if (bed.CheckEnemies(player) && bed.CheckExposure(player) && bed.CheckFire(player) && bed.CheckWet(player)) { ((Character)player).AttachStart(bed.m_spawnPoint, ((Component)bed).gameObject, true, true, false, "attach_bed", new Vector3(0f, 0.5f, 0f), (Transform)null); } } } [HarmonyPatch(typeof(Bed), "GetHoverText")] public static class Bed_GetHoverText_Patch {