Decompiled source of Structure Tweaks v1.33.0
StructureTweaks.dll
Decompiled 3 weeks ago
The result has been truncated due to the large size, download it to view full contents!
using System; using System.Collections; using System.Collections.Generic; using System.Diagnostics; using System.Globalization; using System.IO; using System.IO.Compression; using System.Linq; using System.Reflection; using System.Reflection.Emit; using System.Runtime.CompilerServices; using System.Runtime.Serialization; using System.Runtime.Versioning; using System.Security; using System.Security.Permissions; using BepInEx; using BepInEx.Configuration; using HarmonyLib; using JetBrains.Annotations; using Microsoft.CodeAnalysis; using ServerSync; using Service; using StructureTweaksPlugin; using TMPro; using UnityEngine; [assembly: CompilationRelaxations(8)] [assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)] [assembly: Debuggable(DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints)] [assembly: TargetFramework(".NETFramework,Version=v4.8", FrameworkDisplayName = ".NET Framework 4.8")] [assembly: AssemblyCompany("StructureTweaks")] [assembly: AssemblyConfiguration("Release")] [assembly: AssemblyFileVersion("1.0.0.0")] [assembly: AssemblyInformationalVersion("1.0.0+cb91456d6ad96af5c56045221069dd640dd5c4ae")] [assembly: AssemblyProduct("StructureTweaks")] [assembly: AssemblyTitle("StructureTweaks")] [assembly: SecurityPermission(SecurityAction.RequestMinimum, SkipVerification = true)] [assembly: AssemblyVersion("1.0.0.0")] [module: UnverifiableCode] [module: RefSafetyRules(11)] namespace Microsoft.CodeAnalysis { [CompilerGenerated] [Microsoft.CodeAnalysis.Embedded] internal sealed class EmbeddedAttribute : Attribute { } } namespace System.Runtime.CompilerServices { [CompilerGenerated] [Microsoft.CodeAnalysis.Embedded] [AttributeUsage(AttributeTargets.Class | AttributeTargets.Property | AttributeTargets.Field | AttributeTargets.Event | AttributeTargets.Parameter | AttributeTargets.ReturnValue | AttributeTargets.GenericParameter, AllowMultiple = false, Inherited = false)] internal sealed class NullableAttribute : Attribute { public readonly byte[] NullableFlags; public NullableAttribute(byte P_0) { NullableFlags = new byte[1] { P_0 }; } public NullableAttribute(byte[] P_0) { NullableFlags = P_0; } } [CompilerGenerated] [Microsoft.CodeAnalysis.Embedded] [AttributeUsage(AttributeTargets.Class | AttributeTargets.Struct | AttributeTargets.Method | AttributeTargets.Interface | AttributeTargets.Delegate, AllowMultiple = false, Inherited = false)] internal sealed class NullableContextAttribute : Attribute { public readonly byte Flag; public NullableContextAttribute(byte P_0) { Flag = P_0; } } [CompilerGenerated] [Microsoft.CodeAnalysis.Embedded] [AttributeUsage(AttributeTargets.Module, AllowMultiple = false, Inherited = false)] internal sealed class RefSafetyRulesAttribute : Attribute { public readonly int Version; public RefSafetyRulesAttribute(int P_0) { Version = P_0; } } } namespace Service { public class ConfigWrapper { private readonly ConfigFile ConfigFile; private readonly ConfigSync ConfigSync; private readonly Dictionary<string, Action<Terminal, string>> SettingHandlers = new Dictionary<string, Action<Terminal, string>>(); private static readonly HashSet<string> Truthies = new HashSet<string> { "1", "true", "yes", "on" }; private static readonly HashSet<string> Falsies = new HashSet<string> { "0", "false", "no", "off" }; public ConfigWrapper(string command, ConfigFile configFile, ConfigSync configSync) { //IL_002c: 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_004a: Expected O, but got Unknown //IL_004a: Expected O, but got Unknown //IL_0045: Unknown result type (might be due to invalid IL or missing references) ConfigFile = configFile; ConfigSync = configSync; new ConsoleCommand(command, "[key] [value] - Toggles or sets a config value.", (ConsoleEvent)delegate(ConsoleEventArgs args) { if (args.Length >= 2 && SettingHandlers.TryGetValue(args[1].ToLower(), out Action<Terminal, string> value)) { if (args.Length == 2) { value(args.Context, ""); } else { value(args.Context, string.Join(" ", args.Args.Skip(2))); } } }, false, false, false, false, false, (ConsoleOptionsFetcher)(() => SettingHandlers.Keys.ToList()), false, false, false); } public ConfigEntry<bool> BindLocking(string group, string name, bool value, ConfigDescription description) { ConfigEntry<bool> val = ConfigFile.Bind<bool>(group, name, value, description); Register(val); ConfigSync.AddLockingConfigEntry<bool>(val).SynchronizedConfig = true; return val; } public ConfigEntry<bool> BindLocking(string group, string name, bool value, string description) { //IL_000c: Unknown result type (might be due to invalid IL or missing references) //IL_0016: Expected O, but got Unknown return BindLocking(group, name, value, new ConfigDescription(description, (AcceptableValueBase)null, Array.Empty<object>())); } public ConfigEntry<T> Bind<T>(string group, string name, T value, ConfigDescription description, bool synchronizedSetting = true) { ConfigEntry<T> val = ConfigFile.Bind<T>(group, name, value, description); Register<T>(val); ConfigSync.AddConfigEntry<T>(val).SynchronizedConfig = synchronizedSetting; return val; } public ConfigEntry<T> Bind<T>(string group, string name, T value, string description, bool synchronizedSetting = true) { //IL_000c: Unknown result type (might be due to invalid IL or missing references) //IL_0018: Expected O, but got Unknown return Bind(group, name, value, new ConfigDescription(description, (AcceptableValueBase)null, Array.Empty<object>()), synchronizedSetting); } private static void AddMessage(Terminal context, string message) { context.AddString(message); Player localPlayer = Player.m_localPlayer; if (localPlayer != null) { ((Character)localPlayer).Message((MessageType)1, message, 0, (Sprite)null); } } private void Register(ConfigEntry<bool> setting) { ConfigEntry<bool> setting2 = setting; string name = ((ConfigEntryBase)setting2).Definition.Key; string key = name.ToLower().Replace(' ', '_'); SettingHandlers.Add(key, delegate(Terminal terminal, string value) { Toggle(terminal, setting2, name, value); }); } private void Register<T>(ConfigEntry<T> setting) { ConfigEntry<T> setting2 = setting; string name = ((ConfigEntryBase)setting2).Definition.Key; string key = name.ToLower().Replace(' ', '_'); SettingHandlers.Add(key, delegate(Terminal terminal, string value) { SetValue<T>(terminal, setting2, name, value); }); } private static string State(bool value) { if (!value) { return "disabled"; } return "enabled"; } private static bool IsTruthy(string value) { return Truthies.Contains(value); } private static bool IsFalsy(string value) { return Falsies.Contains(value); } private static void Toggle(Terminal context, ConfigEntry<bool> setting, string name, string value) { if (value == "") { setting.Value = !setting.Value; } else if (IsTruthy(value)) { setting.Value = true; } else if (IsFalsy(value)) { setting.Value = false; } AddMessage(context, name + " " + State(setting.Value) + "."); } public static int TryParseInt(string value, int defaultValue) { if (int.TryParse(value, NumberStyles.Integer, CultureInfo.InvariantCulture, out var result)) { return result; } return defaultValue; } public static int TryParseInt(ConfigEntry<string> setting) { if (int.TryParse(setting.Value, NumberStyles.Integer, CultureInfo.InvariantCulture, out var result)) { return result; } return TryParseInt((string)((ConfigEntryBase)setting).DefaultValue, 0); } private static float TryParseFloat(string value, float defaultValue) { if (float.TryParse(value, NumberStyles.Float, CultureInfo.InvariantCulture, out var result)) { return result; } return defaultValue; } public static float TryParseFloat(ConfigEntry<string> setting) { if (float.TryParse(setting.Value, NumberStyles.Float, CultureInfo.InvariantCulture, out var result)) { return result; } return TryParseFloat((string)((ConfigEntryBase)setting).DefaultValue, 0f); } private static void SetValue<T>(Terminal context, ConfigEntry<T> setting, string name, string value) { if (value == "") { AddMessage(context, $"{name}: {setting.Value}."); return; } setting.Value = (T)(object)value; AddMessage(context, name + " set to " + value + "."); } } public static class Hash { public static readonly int Name = StringExtensionMethods.GetStableHashCode("override_name"); public static readonly int Destroy = StringExtensionMethods.GetStableHashCode("override_destroy"); public static readonly int DestroyEffect = StringExtensionMethods.GetStableHashCode("override_destroy_effect"); public static readonly int DungeonWeather = StringExtensionMethods.GetStableHashCode("override_dungeon_weather"); public static readonly int EnterText = StringExtensionMethods.GetStableHashCode("override_dungeon_enter_text"); public static readonly int EnterHover = StringExtensionMethods.GetStableHashCode("override_dungeon_enter_hover"); public static readonly int ExitText = StringExtensionMethods.GetStableHashCode("override_dungeon_exit_text"); public static readonly int ExitHover = StringExtensionMethods.GetStableHashCode("override_dungeon_exit_hover"); public static readonly int DoorKey = StringExtensionMethods.GetStableHashCode("override_door_key"); public static readonly int DoorNoClose = StringExtensionMethods.GetStableHashCode("override_door_no_close"); public static readonly int DoorConsume = StringExtensionMethods.GetStableHashCode("override_door_consume"); public static readonly int DoorOpenEffect = StringExtensionMethods.GetStableHashCode("override_open_effect"); public static readonly int DoorCloseEffect = StringExtensionMethods.GetStableHashCode("override_close_effect"); public static readonly int DoorLockedEffect = StringExtensionMethods.GetStableHashCode("override_locked_effect"); public static readonly int Weather = StringExtensionMethods.GetStableHashCode("override_weather"); public static readonly int Event = StringExtensionMethods.GetStableHashCode("override_event"); public static readonly int Effect = StringExtensionMethods.GetStableHashCode("override_effect"); public static readonly int Status = StringExtensionMethods.GetStableHashCode("override_status"); public static readonly int Component = StringExtensionMethods.GetStableHashCode("override_component"); public static readonly int Water = StringExtensionMethods.GetStableHashCode("override_water"); public static readonly int Fall = StringExtensionMethods.GetStableHashCode("override_fall"); public static readonly int Unlock = StringExtensionMethods.GetStableHashCode("override_unlock"); public static readonly int Growth = StringExtensionMethods.GetStableHashCode("override_growth"); public static readonly int Radius = StringExtensionMethods.GetStableHashCode("override_music_radius"); public static readonly int Condition = StringExtensionMethods.GetStableHashCode("override_music_condition"); public static readonly int Audio = StringExtensionMethods.GetStableHashCode("override_music_audio"); public static readonly int NoCollision = StringExtensionMethods.GetStableHashCode("override_collision"); public static readonly int Portal = StringExtensionMethods.GetStableHashCode("portal_wood"); public static readonly int NoInteract = StringExtensionMethods.GetStableHashCode("override_interact"); public static readonly int NoRender = StringExtensionMethods.GetStableHashCode("override_render"); public static readonly int Text = StringExtensionMethods.GetStableHashCode("override_text"); public static readonly int Topic = StringExtensionMethods.GetStableHashCode("override_topic"); public static readonly int Compendium = StringExtensionMethods.GetStableHashCode("override_compendium"); public static readonly int Discover = StringExtensionMethods.GetStableHashCode("override_discover"); public static readonly int Smoke = StringExtensionMethods.GetStableHashCode("override_smoke"); public static readonly int Restrict = StringExtensionMethods.GetStableHashCode("override_restrict"); public static readonly int Wear = StringExtensionMethods.GetStableHashCode("override_wear"); } public struct Discovery { public string name; public string pin; public PinType type; public bool showMap; } public class Helper { private static readonly HashSet<string> Truthies = new HashSet<string> { "1", "true", "yes", "on" }; private static readonly HashSet<string> Falsies = new HashSet<string> { "0", "false", "no", "off", "" }; public static bool IsFinite(ZNetView view, float defaultValue) { if (view.IsValid()) { return IsFinite(view.GetZDO().GetFloat(ZDOVars.s_health, defaultValue)); } return false; } public static bool IsFinite(float value) { if (0f <= value) { return value < 1E+19f; } return false; } public static void AddMessage(Terminal context, string message, bool priority = true) { context.AddString(message); MessageHud instance = MessageHud.instance; if (!Object.op_Implicit((Object)(object)instance)) { return; } if (priority) { MsgData[] array = instance.m_msgQeue.ToArray(); instance.m_msgQeue.Clear(); Player localPlayer = Player.m_localPlayer; if (localPlayer != null) { ((Character)localPlayer).Message((MessageType)1, message, 0, (Sprite)null); } MsgData[] array2 = array; foreach (MsgData item in array2) { instance.m_msgQeue.Enqueue(item); } instance.m_msgQueueTimer = 10f; } else { Player localPlayer2 = Player.m_localPlayer; if (localPlayer2 != null) { ((Character)localPlayer2).Message((MessageType)1, message, 0, (Sprite)null); } } } public static ZNetView GetHover(string mode) { GameObject val = Player.m_localPlayer?.m_hovering; if (!Object.op_Implicit((Object)(object)val) || (Object)(object)val == (Object)null) { throw new InvalidOperationException("Not hovering anything."); } Piece component = val.GetComponent<Piece>(); if (!Object.op_Implicit((Object)(object)component)) { throw new InvalidOperationException("Not hovering anything."); } ZNetView nview = component.m_nview; if (!Object.op_Implicit((Object)(object)nview)) { throw new InvalidOperationException("Not hovering anything."); } if (!CanEdit(nview, mode)) { throw new InvalidOperationException("Not allowed to edit."); } return nview; } public static void Command(string name, string description, ConsoleEvent action, ConsoleOptionsFetcher? fetcher = null) { //IL_0011: Unknown result type (might be due to invalid IL or missing references) new ConsoleCommand(name, description, Catch(action), false, false, false, false, false, fetcher, false, false, false); } public static void AddError(Terminal context, string message, bool priority = true) { AddMessage(context, "Error: " + message, priority); } public static ConsoleEvent Catch(ConsoleEvent action) { //IL_0012: Unknown result type (might be due to invalid IL or missing references) //IL_0018: Expected O, but got Unknown ConsoleEvent action2 = action; return (ConsoleEvent)delegate(ConsoleEventArgs args) { try { if (!Object.op_Implicit((Object)(object)Player.m_localPlayer)) { throw new InvalidOperationException("Player not found."); } action2.Invoke(args); } catch (InvalidOperationException ex) { AddError(args.Context, ex.Message); } }; } public static float Float(string arg, float defaultValue = 0f) { if (!float.TryParse(arg, NumberStyles.Float, CultureInfo.InvariantCulture, out var result)) { return defaultValue; } return result; } public static int Int(string arg, int defaultValue = 0) { if (!int.TryParse(arg, NumberStyles.Integer, CultureInfo.InvariantCulture, out var result)) { return defaultValue; } return result; } public static GameObject? GetPrefab(string hashStr) { if (int.TryParse(hashStr, out var result)) { return GetPrefab(result); } return GetPrefab(StringExtensionMethods.GetStableHashCode(hashStr)); } public static GameObject? GetPrefab(int hash) { if (hash == 0) { return null; } GameObject prefab = ZNetScene.instance.GetPrefab(hash); if (!Object.op_Implicit((Object)(object)prefab)) { return null; } return prefab; } public static Discovery ParseDiscovery(string data) { //IL_0033: 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_0060: Unknown result type (might be due to invalid IL or missing references) string[] array = data.Split(new char[1] { ',' }); Discovery discovery = default(Discovery); discovery.name = array[0]; discovery.pin = ""; discovery.type = (PinType)8; Discovery result = discovery; if (array.Length > 1) { result.pin = array[1]; } if (array.Length > 2 && Enum.TryParse<PinType>(array[2], ignoreCase: true, out PinType result2)) { result.type = result2; } if (array.Length > 3) { result.showMap = Int(array[3]) > 0; } return result; } public static void Float(ZNetView? view, int hash, Action<float> action) { if (!((Object)(object)view == (Object)null) && view.IsValid()) { float @float = view.GetZDO().GetFloat(hash, 0f); if (@float != 0f) { action(@float); } } } public static void Int(ZNetView? view, int hash, Action<int> action) { if (!((Object)(object)view == (Object)null) && view.IsValid()) { int @int = view.GetZDO().GetInt(hash, 0); if (@int != 0) { action(@int); } } } public static void Bool(ZNetView? view, int hash, Action action) { if (!((Object)(object)view == (Object)null) && view.IsValid() && view.GetZDO().GetBool(hash, false)) { action(); } } public static bool Bool(ZNetView? view, int hash) { if ((Object)(object)view == (Object)null || !view.IsValid()) { return false; } return view.GetZDO().GetBool(hash, false); } public static int Int(ZNetView? view, int hash) { if ((Object)(object)view == (Object)null || !view.IsValid()) { return 0; } return view.GetZDO().GetInt(hash, 0); } public static void String(ZNetView? view, int hash, Action<string> action) { if (!((Object)(object)view == (Object)null) && view.IsValid()) { string @string = view.GetZDO().GetString(hash, ""); if (!(@string == "")) { action(@string); } } } public static bool Prefab(ZNetView? view, int hash, Action<GameObject> action) { if ((Object)(object)view == (Object)null || !view.IsValid()) { return false; } int num = view.GetZDO().GetInt(hash, 0); if (num == 0) { num = StringExtensionMethods.GetStableHashCode(view.GetZDO().GetString(hash, "")); } GameObject prefab = GetPrefab(num); if ((Object)(object)prefab == (Object)null) { return false; } action(prefab); return true; } public static ItemDrop? GetItem(int hash) { GameObject? prefab = GetPrefab(hash); if (prefab == null) { return null; } return prefab.GetComponent<ItemDrop>(); } public static void Item(ZNetView view, int hash, Action<ItemDrop> action) { if (!((Object)(object)view == (Object)null) && view.IsValid()) { int num = view.GetZDO().GetInt(hash, 0); if (num == 0) { num = StringExtensionMethods.GetStableHashCode(view.GetZDO().GetString(hash, "")); } ItemDrop item = GetItem(num); if (!((Object)(object)item == (Object)null)) { action(item); } } } public static bool CanEdit(ZNetView? view, string mode) { if ((Object)(object)view == (Object)null || !view.IsValid()) { return false; } if (ZNet.instance.IsServer() || Plugin.ConfigSync.IsAdmin || mode == "All") { return true; } long playerID = Game.instance.GetPlayerProfile().GetPlayerID(); return view.GetZDO().GetLong(ZDOVars.s_creator, 0L) == playerID; } public static float TryFloat(string[] args, int index, float defaultValue = 1f) { if (args.Length <= index) { return defaultValue; } return Float(args[index], defaultValue); } public static Vector3 TryVectorXZY(string[] args, int index, Vector3 defaultValue) { //IL_0000: Unknown result type (might be due to invalid IL or missing references) //IL_0005: Unknown result type (might be due to invalid IL or missing references) //IL_000a: Unknown result type (might be due to invalid IL or missing references) //IL_0020: Unknown result type (might be due to invalid IL or missing references) //IL_0036: 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) Vector3 zero = Vector3.zero; zero.x = TryFloat(args, index, defaultValue.x); zero.y = TryFloat(args, index + 2, defaultValue.y); zero.z = TryFloat(args, index + 1, defaultValue.z); return zero; } public static Vector3 TryScale(string[] args, int index) { //IL_0002: Unknown result type (might be due to invalid IL or missing references) //IL_0007: Unknown result type (might be due to invalid IL or missing references) //IL_000c: Unknown result type (might be due to invalid IL or missing references) return SanityCheck(TryVectorXZY(args, index, Vector3.zero)); } private static Vector3 SanityCheck(Vector3 scale) { //IL_0000: 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_0033: Unknown result type (might be due to invalid IL or missing references) //IL_0028: Unknown result type (might be due to invalid IL or missing references) //IL_004d: Unknown result type (might be due to invalid IL or missing references) //IL_0042: Unknown result type (might be due to invalid IL or missing references) if (scale.x == 0f) { scale.x = 1f; } if (scale.y == 0f) { scale.y = scale.x; } if (scale.z == 0f) { scale.z = scale.x; } return scale; } public static bool IsTruthy(string value) { return Truthies.Contains(value); } public static bool IsFalsy(string value) { return Falsies.Contains(value); } public static T Get<T>(ZNetView view) where T : Component { T result = default(T); if (((Component)view).TryGetComponent<T>(ref result)) { return result; } return ((Component)view).gameObject.AddComponent<T>(); } public static EffectList ParseEffects(string data) { //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_006c: Expected O, but got Unknown IEnumerable<EffectData> source = from effect in data.Split(new char[1] { '|' }) select ParseEffect(effect) into effect where effect != null select effect; return new EffectList { m_effectPrefabs = source.ToArray() }; } public static EffectData? ParseEffect(string data) { //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_0026: Expected O, but got Unknown string[] array = data.Split(new char[1] { ',' }); EffectData val = new EffectData { m_prefab = GetPrefab(array[0]) }; if ((Object)(object)val.m_prefab == (Object)null) { return null; } if (array.Length > 1 && int.TryParse(array[1], out var result)) { val.m_randomRotation = (result & 1) > 0; val.m_inheritParentRotation = (result & 2) > 0; val.m_scale = (result & 4) > 0; val.m_inheritParentScale = (result & 8) > 0; val.m_attach = (result & 0x10) > 0; } if (array.Length > 2 && int.TryParse(array[2], out var result2)) { val.m_variant = result2; } if (array.Length > 3) { val.m_childTransform = array[3]; } return val; } } } namespace StructureTweaksPlugin { [HarmonyPatch(typeof(ZNetScene), "Awake")] public class AllScalable { private static readonly Dictionary<int, bool> Originals = new Dictionary<int, bool>(); public static readonly HashSet<int> HasSystems = new HashSet<int>(); public static void Update() { Update(ZNetScene.instance); } public static void UpdateParticles(ZNetScene scene) { //IL_005d: Unknown result type (might be due to invalid IL or missing references) //IL_0062: Unknown result type (might be due to invalid IL or missing references) //IL_0066: Unknown result type (might be due to invalid IL or missing references) //IL_006c: Invalid comparison between Unknown and I4 //IL_0070: Unknown result type (might be due to invalid IL or missing references) //IL_0075: Unknown result type (might be due to invalid IL or missing references) GameObject[] array = scene.m_namedPrefabs.Values.Where((GameObject v) => Object.op_Implicit((Object)(object)v.GetComponent<Fireplace>())).ToArray(); List<ParticleSystem> list = new List<ParticleSystem>(); GameObject[] array2 = array; for (int i = 0; i < array2.Length; i++) { array2[i].GetComponentsInChildren<ParticleSystem>(true, list); foreach (ParticleSystem item in list) { MainModule main = item.main; if ((int)((MainModule)(ref main)).scalingMode == 1) { MainModule main2 = item.main; ((MainModule)(ref main2)).scalingMode = (ParticleSystemScalingMode)0; } } } } public static void Update(int prefab, ZNetView obj) { bool value; if (Configuration.configAllScalable.Value) { obj.m_syncInitialScale = true; } else if (Originals.TryGetValue(prefab, out value)) { obj.m_syncInitialScale = value; } } public static void Update(ZNetScene scene) { Dictionary<int, bool> dictionary = new Dictionary<int, bool>(); foreach (KeyValuePair<int, GameObject> namedPrefab in scene.m_namedPrefabs) { ZNetView component = namedPrefab.Value.GetComponent<ZNetView>(); if (component != null) { Update(namedPrefab.Key, component); dictionary[namedPrefab.Key] = component.m_syncInitialScale; } } foreach (KeyValuePair<ZDO, ZNetView> instance in scene.m_instances) { int prefab = instance.Key.GetPrefab(); if (dictionary.ContainsKey(prefab)) { ZNetView component2 = ((Component)instance.Value).GetComponent<ZNetView>(); if (component2 != null) { component2.m_syncInitialScale = dictionary[prefab]; } } } } [HarmonyPriority(0)] private static void Postfix(ZNetScene __instance) { foreach (KeyValuePair<int, GameObject> namedPrefab in __instance.m_namedPrefabs) { if (!Originals.ContainsKey(namedPrefab.Key)) { ZNetView component = namedPrefab.Value.GetComponent<ZNetView>(); if (component != null) { Originals[namedPrefab.Key] = component.m_syncInitialScale; } } } Update(__instance); UpdateParticles(__instance); } } [HarmonyPatch(typeof(Container), "Awake")] public class ChestAwake { private static void Postfix(Container __instance) { Container __instance2 = __instance; if (Configuration.configRuneStone.Value) { Helper.String(__instance2.m_nview, Hash.Name, delegate(string value) { __instance2.m_name = value; }); } } } public class Configuration { public static ConfigEntry<bool> configAllScalable; public static ConfigEntry<bool> configNoTargeting; public static ConfigEntry<bool> configDisableStructureSystems; public static ConfigEntry<bool> configDisableFalling; public static ConfigEntry<bool> configGrowth; public static ConfigEntry<bool> configWear; public static ConfigEntry<bool> configCollision; public static ConfigEntry<bool> configRuneStone; public static ConfigEntry<bool> configMusic; public static ConfigEntry<string> configRuneStoneEditing; public static ConfigEntry<bool> configInteract; public static ConfigEntry<bool> configWardUnlock; public static ConfigEntry<bool> configToggleContainerUnlock; public static ConfigEntry<bool> configToggleDoorUnlock; public static ConfigEntry<bool> configRendering; public static ConfigEntry<bool> configFalling; public static ConfigEntry<bool> configEffects; public static ConfigEntry<bool> configTeleportable; public static ConfigEntry<bool> configSmokeBlock; public static ConfigEntry<string> configGrowthEditing; public static ConfigEntry<string> configWearEditing; public static ConfigEntry<bool> configIgnoreDamage; public static ConfigEntry<bool> configIgnoreRemove; public static ConfigEntry<bool> configIgnoreSupport; public static ConfigEntry<bool> configWaterHideParent; public static void Init(ConfigWrapper wrapper) { //IL_0279: Unknown result type (might be due to invalid IL or missing references) //IL_0284: Expected O, but got Unknown //IL_02a5: Unknown result type (might be due to invalid IL or missing references) //IL_02b0: Expected O, but got Unknown //IL_02d1: Unknown result type (might be due to invalid IL or missing references) //IL_02dc: Expected O, but got Unknown string group = "1. General"; configAllScalable = wrapper.Bind(group, "All objects can be scaled", value: true, "Scaling works for every object."); configAllScalable.SettingChanged += delegate { AllScalable.Update(); }; configIgnoreDamage = wrapper.Bind(group, "Ignore damage when infinite health", value: true, "Damage is fully ignored for objects with infinite health."); configIgnoreRemove = wrapper.Bind(group, "Protect pieces with infinite health", value: true, "Pieces with infinite health can't be deconstructed with the hammer."); configIgnoreSupport = wrapper.Bind(group, "Max support with infinite health", value: true, "Pieces with infinite health have max structure support."); configDisableStructureSystems = wrapper.Bind(group, "Disable structure system", value: false, "Structure systems are disabled for all pieces."); configDisableFalling = wrapper.Bind(group, "Disable falling", value: false, "Falling is disabled for all static objects."); configNoTargeting = wrapper.Bind(group, "No enemy targeting when no creator", value: true, "Enemies won't target neutral structure."); configNoTargeting.SettingChanged += delegate { NoTargeting.Update(); }; configCollision = wrapper.Bind(group, "Override collision", value: true, "Collision can be overridden (requires reloading the area)."); configGrowth = wrapper.Bind(group, "Override growth", value: true, "Growth visual can be overridden."); configRuneStone = wrapper.Bind(group, "Override runestones", value: true, "Runestone properties can be overridden."); configMusic = wrapper.Bind(group, "Override music", value: true, "Music properties can be overridden."); configInteract = wrapper.Bind(group, "Override interact", value: true, "Interactability can be overridden."); configRendering = wrapper.Bind(group, "Override rendering", value: true, "Rendering can be overridden (requires reloading the area)."); configFalling = wrapper.Bind(group, "Override falling", value: true, "Falling can be overridden (requires reloading the area)."); configTeleportable = wrapper.Bind(group, "Override portal restrictions", value: true, "Teleporting with restricted items can be overridden."); configSmokeBlock = wrapper.Bind(group, "Override smoke restrictions", value: true, "Fireplaces going out can be overridden."); configWear = wrapper.Bind(group, "Override wear", value: true, "Wear visual can be overridden."); configEffects = wrapper.Bind(group, "Override effects", value: true, "New area effects can be added."); configWardUnlock = wrapper.Bind(group, "Override unlock", value: true, "Chests and doors can be force unlocked."); configWaterHideParent = wrapper.Bind(group, "Water hides the parent object", value: false, "If enabled, adding water hides and removes the collider of the parent object."); group = "2. Commands"; string[] array = new string[3] { "Admin only", "Owned", "All" }; configGrowthEditing = wrapper.Bind(group, "Command growth", "Owned", new ConfigDescription("Growth editing", (AcceptableValueBase)(object)new AcceptableValueList<string>(array), Array.Empty<object>())); configWearEditing = wrapper.Bind(group, "Command wear", "Owned", new ConfigDescription("Wear editing", (AcceptableValueBase)(object)new AcceptableValueList<string>(array), Array.Empty<object>())); configRuneStoneEditing = wrapper.Bind(group, "Allow editing runestones", "Admin only", new ConfigDescription("Runestone editing", (AcceptableValueBase)(object)new AcceptableValueList<string>(array), Array.Empty<object>())); configToggleContainerUnlock = wrapper.Bind(group, "Allow unlocking chests", value: true, "Players can unlock chests to ignore wards."); configToggleDoorUnlock = wrapper.Bind(group, "Allow unlocking doors", value: true, "Players can unlock doors to ignore wards."); } } [HarmonyPatch(typeof(TimedDestruction), "DestroyNow")] public class Destroy { public static void Handle(ZNetView view) { ZNetView view2 = view; Helper.Float(view2, Hash.Destroy, delegate(float value) { TimedDestruction obj = Helper.Get<TimedDestruction>(view2); obj.m_triggerOnAwake = true; obj.m_timeout = value; ((MonoBehaviour)obj).CancelInvoke("DestroyNow"); obj.Trigger(); }); } private static void Prefix(TimedDestruction __instance) { TimedDestruction __instance2 = __instance; Helper.String(__instance2.m_nview, Hash.DestroyEffect, delegate(string value) { //IL_0011: 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) Helper.ParseEffects(value).Create(((Component)__instance2).transform.position, ((Component)__instance2).transform.rotation, ((Component)__instance2).transform, 1f, -1); }); } } [HarmonyPatch(typeof(LocationProxy), "SpawnLocation")] public class LocationAwake { private static void Postfix(LocationProxy __instance) { LocationProxy __instance2 = __instance; if (!Object.op_Implicit((Object)(object)__instance2.m_instance)) { return; } Helper.String(__instance2.m_nview, Hash.DungeonWeather, delegate(string value) { EnvZone componentInChildren = __instance2.m_instance.GetComponentInChildren<EnvZone>(); if (Object.op_Implicit((Object)(object)componentInChildren)) { componentInChildren.m_environment = value; } }); Teleport[] portals = Array.Empty<Teleport>(); Helper.String(__instance2.m_nview, Hash.EnterText, delegate(string value) { if (portals.Length == 0) { portals = __instance2.m_instance.GetComponentsInChildren<Teleport>(); } Teleport val4 = ((IEnumerable<Teleport>)portals).FirstOrDefault((Func<Teleport, bool>)((Teleport p) => ((Component)p).transform.position.y <= 3000f)); if (Object.op_Implicit((Object)(object)val4)) { val4.m_enterText = value; } }); Helper.String(__instance2.m_nview, Hash.EnterHover, delegate(string value) { if (portals.Length == 0) { portals = __instance2.m_instance.GetComponentsInChildren<Teleport>(); } Teleport val3 = ((IEnumerable<Teleport>)portals).FirstOrDefault((Func<Teleport, bool>)((Teleport p) => ((Component)p).transform.position.y <= 3000f)); if (Object.op_Implicit((Object)(object)val3)) { val3.m_hoverText = value; } }); Helper.String(__instance2.m_nview, Hash.ExitText, delegate(string value) { if (portals.Length == 0) { portals = __instance2.m_instance.GetComponentsInChildren<Teleport>(); } Teleport val2 = ((IEnumerable<Teleport>)portals).FirstOrDefault((Func<Teleport, bool>)((Teleport p) => ((Component)p).transform.position.y > 3000f)); if (Object.op_Implicit((Object)(object)val2)) { val2.m_enterText = value; } }); Helper.String(__instance2.m_nview, Hash.ExitHover, delegate(string value) { if (portals.Length == 0) { portals = __instance2.m_instance.GetComponentsInChildren<Teleport>(); } Teleport val = ((IEnumerable<Teleport>)portals).FirstOrDefault((Func<Teleport, bool>)((Teleport p) => ((Component)p).transform.position.y > 3000f)); if (Object.op_Implicit((Object)(object)val)) { val.m_hoverText = value; } }); } } [HarmonyPatch(typeof(ZNetView), "Awake")] public class ZNetViewAwake { private static readonly int RoomCrypt = StringExtensionMethods.GetStableHashCode("sunkencrypt_new_Corridor1"); private static readonly string WaterCrypt = "WaterCube_sunkencrypt"; private static readonly int RoomCave = StringExtensionMethods.GetStableHashCode("cave_new_deeproom_bottom_lake"); private static readonly string WaterCave = "WaterCube_cave"; private static void HandleWeather(ZNetView view) { //IL_00a5: Unknown result type (might be due to invalid IL or missing references) //IL_00aa: Unknown result type (might be due to invalid IL or missing references) //IL_00bd: 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_00e8: Unknown result type (might be due to invalid IL or missing references) //IL_00ee: Unknown result type (might be due to invalid IL or missing references) //IL_00fd: Unknown result type (might be due to invalid IL or missing references) //IL_0079: Unknown result type (might be due to invalid IL or missing references) //IL_007f: Unknown result type (might be due to invalid IL or missing references) string @string = view.GetZDO().GetString(Hash.Weather, ""); if (@string == "") { return; } string[] array = @string.Split(new char[1] { ',' }); if (array.Length < 2) { return; } float num = Helper.Float(array[0]); bool force = array.Length > 2 && !Helper.IsFalsy(array[2]); EnvZone val = default(EnvZone); if (((Component)view).TryGetComponent<EnvZone>(ref val)) { if (num != 0f) { ((Component)val).transform.localScale = Vector3.one * num; } val.m_force = force; val.m_environment = array[1]; } else if (num != 0f) { GameObject val2 = new GameObject(); SphereCollider obj = val2.AddComponent<SphereCollider>(); ((Collider)obj).isTrigger = true; obj.radius = num; val = val2.AddComponent<EnvZone>(); val.m_force = force; val.m_environment = array[1]; val2.transform.parent = ((Component)view).transform; val2.transform.localPosition = Vector3.zero; val2.transform.localRotation = Quaternion.identity; } } private static void HandleEvent(ZNetView view) { //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_009e: Unknown result type (might be due to invalid IL or missing references) //IL_00ac: Unknown result type (might be due to invalid IL or missing references) //IL_00bd: Unknown result type (might be due to invalid IL or missing references) //IL_00c3: Unknown result type (might be due to invalid IL or missing references) //IL_00d2: 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_0069: Unknown result type (might be due to invalid IL or missing references) string @string = view.GetZDO().GetString(Hash.Event, ""); if (@string == "") { return; } string[] array = @string.Split(new char[1] { ',' }); if (array.Length < 2) { return; } float num = Helper.Float(array[0]); EventZone val = default(EventZone); if (((Component)view).TryGetComponent<EventZone>(ref val)) { if (num != 0f) { ((Component)val).transform.localScale = Vector3.one * num; } val.m_event = array[1]; } else if (num != 0f) { GameObject val2 = new GameObject(); SphereCollider obj = val2.AddComponent<SphereCollider>(); ((Collider)obj).isTrigger = true; obj.radius = num; val2.AddComponent<EventZone>().m_event = array[1]; val2.transform.parent = ((Component)view).transform; val2.transform.localPosition = Vector3.zero; val2.transform.localRotation = Quaternion.identity; } } private static Type ParseType(string[] values) { //IL_0001: 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_0015: Unknown result type (might be due to invalid IL or missing references) //IL_0018: Unknown result type (might be due to invalid IL or missing references) //IL_0019: 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_001b: Unknown result type (might be due to invalid IL or missing references) Type val = (Type)0; for (int i = 0; i < values.Length; i++) { if (Enum.TryParse<Type>(values[i], ignoreCase: true, out Type result) && (int)result != 0) { val |= result; } } return val; } private static void HandleEffect(ZNetView view) { string @string = view.GetZDO().GetString(Hash.Status, ""); string string2 = view.GetZDO().GetString(Hash.Effect, ""); if (!(@string == "") || !(string2 == "")) { EffectArea[] componentsInChildren = ((Component)view).GetComponentsInChildren<EffectArea>(true); EffectArea[] array = componentsInChildren; foreach (EffectArea obj in array) { Transform parent = ((Component)obj).transform.parent; Object.Destroy((Object)(object)obj.m_collider); Object.Destroy((Object)(object)obj); AddEffect(parent, @string, string2); } if (componentsInChildren.Length == 0) { AddEffect(((Component)view).transform, @string, string2); } } } private static void AddEffect(Transform parent, string statusStr, string effectStr) { //IL_0000: Unknown result type (might be due to invalid IL or missing references) //IL_0005: Unknown result type (might be due to invalid IL or missing references) //IL_0013: 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_002d: Unknown result type (might be due to invalid IL or missing references) //IL_0033: Unknown result type (might be due to invalid IL or missing references) //IL_0042: Unknown result type (might be due to invalid IL or missing references) //IL_0173: Unknown result type (might be due to invalid IL or missing references) //IL_0178: Unknown result type (might be due to invalid IL or missing references) //IL_00d3: Unknown result type (might be due to invalid IL or missing references) GameObject val = new GameObject(); SphereCollider val2 = val.AddComponent<SphereCollider>(); ((Collider)val2).isTrigger = true; CustomEffectArea customEffectArea = val.AddComponent<CustomEffectArea>(); ((EffectArea)customEffectArea).m_collider = (Collider)(object)val2; val.transform.parent = parent; val.transform.localPosition = Vector3.zero; val.transform.localRotation = Quaternion.identity; if (statusStr != "") { string[] array = statusStr.Split(new char[1] { ',' }); if (array.Length > 1) { val2.radius = Math.Max(val2.radius, Helper.Float(array[0])); ((EffectArea)customEffectArea).m_playerOnly = ((EffectArea)customEffectArea).m_playerOnly || (array.Length > 2 && Helper.IsTruthy(array[2])); ((EffectArea)customEffectArea).m_statusEffect = array[1]; ((EffectArea)customEffectArea).m_statusEffectHash = StringExtensionMethods.GetStableHashCode(((EffectArea)customEffectArea).m_statusEffect); ((EffectArea)customEffectArea).m_type = (Type)0; if (array.Length > 3) { customEffectArea.m_duration = Helper.Float(array[3]); } if (array.Length > 4) { customEffectArea.m_damage = Helper.Float(array[4]); } if (array.Length > 5) { customEffectArea.m_interval = Helper.Float(array[5]); } } } if (effectStr != "") { string[] array2 = effectStr.Split(new char[1] { ',' }); if (array2.Length > 1) { val2.radius = Math.Max(val2.radius, Helper.Float(array2[0])); ((EffectArea)customEffectArea).m_type = ParseType(array2.Skip(1).ToArray()); ((EffectArea)customEffectArea).m_playerOnly = ((EffectArea)customEffectArea).m_playerOnly || (array2.Length > 2 && Helper.IsTruthy(array2[^1])); } } } private static void HandleComponent(ZNetView view) { if (Object.op_Implicit((Object)(object)((Component)view).gameObject.GetComponent<DungeonGenerator>())) { return; } string text = view.GetZDO().GetString(Hash.Component, "").ToLower(); if (text == "") { return; } string[] array = text.Split(new char[1] { ',' }); foreach (string obj in array) { if (obj == "runestone" && !Object.op_Implicit((Object)(object)((Component)view).gameObject.GetComponent<RuneStone>())) { ((Component)view).gameObject.AddComponent<RuneStone>(); } if (obj == "chest" && !Object.op_Implicit((Object)(object)((Component)view).gameObject.GetComponent<Container>())) { ((Component)view).gameObject.AddComponent<Container>(); } if (obj == "door" && !Object.op_Implicit((Object)(object)((Component)view).gameObject.GetComponent<Door>())) { ((Component)view).gameObject.AddComponent<Door>(); } if (obj == "destroy" && !Object.op_Implicit((Object)(object)((Component)view).gameObject.GetComponent<TimedDestruction>())) { Object.Destroy((Object)(object)((Component)view).gameObject.GetComponent<Growup>()); ((Component)view).gameObject.AddComponent<TimedDestruction>(); } if (obj == "portal" && !Object.op_Implicit((Object)(object)((Component)view).gameObject.GetComponent<TeleportWorld>())) { ((Component)view).gameObject.AddComponent<TeleportWorld>(); } } } private static void HandleWater(ZNetView view) { ZNetView view2 = view; Helper.String(view2, Hash.Water, delegate(string value) { //IL_0013: Unknown result type (might be due to invalid IL or missing references) //IL_0018: Unknown result type (might be due to invalid IL or missing references) //IL_00a0: Unknown result type (might be due to invalid IL or missing references) //IL_0149: Unknown result type (might be due to invalid IL or missing references) //IL_0159: Unknown result type (might be due to invalid IL or missing references) //IL_0168: Unknown result type (might be due to invalid IL or missing references) string[] array = value.Split(new char[1] { ',' }); Vector3 localScale = Helper.TryScale(array, 1); int key = 0; string text = ""; if (array[0] == "crypt") { key = RoomCrypt; text = WaterCrypt; localScale.x *= 2f; localScale.z *= 2f; } if (array[0] == "cave") { key = RoomCave; text = WaterCave; } if (DungeonDB.instance.m_roomByHash.TryGetValue(key, out var value2)) { if (!value2.m_prefab.IsLoaded) { value2.m_prefab.Load(); } Transform val = value2.m_prefab.Asset.transform.Find(text); if (Object.op_Implicit((Object)(object)val)) { if (Configuration.configWaterHideParent.Value) { Renderer[] componentsInChildren = ((Component)view2).GetComponentsInChildren<Renderer>(); for (int i = 0; i < componentsInChildren.Length; i++) { componentsInChildren[i].enabled = false; } Collider[] componentsInChildren2 = ((Component)view2).GetComponentsInChildren<Collider>(); for (int i = 0; i < componentsInChildren2.Length; i++) { componentsInChildren2[i].isTrigger = true; } } GameObject obj = Object.Instantiate<GameObject>(((Component)val).gameObject, ((Component)view2).transform); obj.transform.localPosition = Vector3.zero; obj.transform.localRotation = Quaternion.identity; obj.transform.localScale = localScale; } } }); } private static void Postfix(ZNetView __instance) { if (Configuration.configEffects.Value && Object.op_Implicit((Object)(object)__instance) && __instance.IsValid()) { HandleWeather(__instance); HandleEvent(__instance); HandleEffect(__instance); HandleComponent(__instance); HandleWater(__instance); Destroy.Handle(__instance); } } } public class CustomEffectArea : EffectArea { public float m_duration; public float m_damage; public float m_interval; private static readonly int HashBurning = StringExtensionMethods.GetStableHashCode("Burning"); public void OnTriggerExit(Collider collider) { if ((Object)(object)ZNet.instance == (Object)null || string.IsNullOrEmpty(base.m_statusEffect)) { return; } Character component = ((Component)collider).GetComponent<Character>(); if (Object.op_Implicit((Object)(object)component) && component.IsOwner() && (!base.m_playerOnly || component.IsPlayer())) { SEMan sEMan = component.GetSEMan(); StatusEffect statusEffect = sEMan.GetStatusEffect(base.m_statusEffectHash); if (Object.op_Implicit((Object)(object)statusEffect) && statusEffect.m_ttl == 0f) { sEMan.RemoveStatusEffect(base.m_statusEffectHash, false); } } } public void OnTriggerStay(Collider collider) { //IL_0221: Unknown result type (might be due to invalid IL or missing references) //IL_0227: Unknown result type (might be due to invalid IL or missing references) //IL_0231: Unknown result type (might be due to invalid IL or missing references) //IL_01b7: Unknown result type (might be due to invalid IL or missing references) //IL_01bc: Unknown result type (might be due to invalid IL or missing references) //IL_01c4: 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_00d7: Unknown result type (might be due to invalid IL or missing references) //IL_00df: Unknown result type (might be due to invalid IL or missing references) //IL_0141: Unknown result type (might be due to invalid IL or missing references) //IL_0146: Unknown result type (might be due to invalid IL or missing references) //IL_014e: Unknown result type (might be due to invalid IL or missing references) Character component = ((Component)collider).GetComponent<Character>(); if (!Object.op_Implicit((Object)(object)component) || !component.IsOwner() || (base.m_playerOnly && !component.IsPlayer())) { return; } if (!string.IsNullOrEmpty(base.m_statusEffect)) { SEMan sEMan = component.GetSEMan(); StatusEffect val = sEMan.GetStatusEffect(base.m_statusEffectHash); if ((Object)(object)val == (Object)null) { val = sEMan.AddStatusEffect(base.m_statusEffectHash, true, 0, 0f); } else { val.ResetTime(); } if (m_damage == 0f && m_duration != 0f) { val.m_ttl = m_duration; } if (m_damage != 0f) { SE_Burning val2 = (SE_Burning)(object)((val is SE_Burning) ? val : null); if (val2 != null) { if (val2.m_fireDamageLeft > 0f || val.m_nameHash == HashBurning) { DamageModifier damageModifier = component.GetDamageModifier((DamageType)32); float num = m_damage * ModToMultiplier(damageModifier); if (val2.m_fireDamageLeft < num) { val.m_ttl = m_duration; if (m_interval != 0f) { val2.m_damageInterval = m_interval; } val2.m_fireDamageLeft = num; val2.m_fireDamagePerHit = num * val2.m_damageInterval / val.m_ttl; } } else { DamageModifier damageModifier2 = component.GetDamageModifier((DamageType)512); float num2 = m_damage * ModToMultiplier(damageModifier2); if (val2.m_spiritDamageLeft < num2) { val.m_ttl = m_duration; if (m_interval != 0f) { val2.m_damageInterval = m_interval; } val2.m_spiritDamageLeft = num2; val2.m_spiritDamagePerHit = num2 * val2.m_damageInterval / val.m_ttl; } } } SE_Poison val3 = (SE_Poison)(object)((val is SE_Poison) ? val : null); if (val3 != null) { DamageModifier damageModifier3 = component.GetDamageModifier((DamageType)256); float num3 = m_damage * ModToMultiplier(damageModifier3); if (val3.m_damageLeft < num3) { val.m_ttl = m_duration; if (m_interval != 0f) { val3.m_damageInterval = m_interval; } val3.m_damageLeft = num3; val3.m_damagePerHit = num3 * val3.m_damageInterval / val.m_ttl; } } } } if ((base.m_type & 1) != 0) { component.OnNearFire(((Component)this).transform.position); } } private static float ModToMultiplier(DamageModifier mod) { //IL_0000: Unknown result type (might be due to invalid IL or missing references) //IL_0002: Invalid comparison between Unknown and I4 //IL_000a: Unknown result type (might be due to invalid IL or missing references) //IL_000c: Invalid comparison between Unknown and I4 //IL_0014: Unknown result type (might be due to invalid IL or missing references) //IL_0016: Invalid comparison between Unknown and I4 //IL_001e: Unknown result type (might be due to invalid IL or missing references) //IL_0020: Invalid comparison between Unknown and I4 //IL_0028: Unknown result type (might be due to invalid IL or missing references) //IL_002a: Invalid comparison between Unknown and I4 //IL_0032: Unknown result type (might be due to invalid IL or missing references) //IL_0034: Invalid comparison between Unknown and I4 if ((int)mod == 1) { return 0.5f; } if ((int)mod == 5) { return 0.25f; } if ((int)mod == 2) { return 1.5f; } if ((int)mod == 6) { return 2f; } if ((int)mod == 3) { return 0f; } if ((int)mod == 4) { return 0f; } return 1f; } } [HarmonyPatch(typeof(StaticPhysics), "Awake")] public class Fall { private static void Postfix(StaticPhysics __instance) { StaticPhysics __instance2 = __instance; if (Configuration.configFalling.Value) { Helper.Int(__instance2.m_nview, Hash.Fall, delegate(int value) { __instance2.m_fall = value == 1 || value == 2; __instance2.m_pushUp = value == 1 || value == 2; __instance2.m_checkSolids = value == 2; }); } } } [HarmonyPatch(typeof(StaticPhysics), "SUpdate")] public class GlobalFall { private static bool Prefix() { return !Configuration.configDisableFalling.Value; } } [HarmonyPatch] public class Unlock { private static bool CheckAccess(Component obj, float radius, bool flash, bool wardCheck) { //IL_0045: Unknown result type (might be due to invalid IL or missing references) ZNetView componentInParent = obj.GetComponentInParent<ZNetView>(); bool force = false; if (Configuration.configWardUnlock.Value) { Helper.Bool(componentInParent, Hash.Unlock, delegate { force = true; }); } if (!force) { return PrivateArea.CheckAccess(obj.transform.position, radius, flash, wardCheck); } return true; } private static IEnumerable<CodeInstruction> ReplacePrivateCheck(IEnumerable<CodeInstruction> instructions) { //IL_0002: 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_0037: Expected O, but got Unknown //IL_0080: Unknown result type (might be due to invalid IL or missing references) //IL_0086: Expected O, but got Unknown return new CodeMatcher(instructions, (ILGenerator)null).MatchForward(false, (CodeMatch[])(object)new CodeMatch[1] { new CodeMatch((OpCode?)OpCodes.Call, (object)AccessTools.Method(typeof(PrivateArea), "CheckAccess", (Type[])null, (Type[])null), (string)null) }).Set(OpCodes.Call, Transpilers.EmitDelegate<Func<Component, float, bool, bool, bool>>((Func<Component, float, bool, bool, bool>)CheckAccess).operand).MatchBack(false, (CodeMatch[])(object)new CodeMatch[1] { new CodeMatch((OpCode?)OpCodes.Ldarg_0, (object)null, (string)null) }) .Advance(1) .SetOpcodeAndAdvance(OpCodes.Nop) .SetOpcodeAndAdvance(OpCodes.Nop) .InstructionEnumeration(); } [HarmonyPatch(typeof(Door), "Interact")] [HarmonyTranspiler] private static IEnumerable<CodeInstruction> DoorInteract(IEnumerable<CodeInstruction> instructions) { return ReplacePrivateCheck(instructions); } [HarmonyPatch(typeof(Container), "Interact")] [HarmonyTranspiler] private static IEnumerable<CodeInstruction> ContainerInteract(IEnumerable<CodeInstruction> instructions) { return ReplacePrivateCheck(instructions); } [HarmonyPatch(typeof(Door), "GetHoverText")] [HarmonyTranspiler] private static IEnumerable<CodeInstruction> DoorGetHoverText(IEnumerable<CodeInstruction> instructions) { return ReplacePrivateCheck(instructions); } [HarmonyPatch(typeof(Container), "GetHoverText")] [HarmonyTranspiler] private static IEnumerable<CodeInstruction> ContainerGetHoverText(IEnumerable<CodeInstruction> instructions) { return ReplacePrivateCheck(instructions); } private static string OverrideHoverText(string result, ZNetView view, Vector3 point) { //IL_0016: Unknown result type (might be due to invalid IL or missing references) if (!Configuration.configWardUnlock.Value || !Object.op_Implicit((Object)(object)view)) { return result; } if (!PrivateArea.CheckAccess(point, 0f, false, false)) { return result; } if (view.GetZDO().GetBool(Hash.Unlock, false)) { return result + Localization.instance.Localize("\n[<color=yellow><b>$KEY_AltPlace + $KEY_Use</b></color>] Remove unlock"); } return result + Localization.instance.Localize("\n[<color=yellow><b>$KEY_AltPlace + $KEY_Use</b></color>] Force unlock"); } [HarmonyPatch(typeof(Door), "GetHoverText")] [HarmonyPostfix] private static string DoorGetHoverText(string result, Door __instance) { //IL_002d: Unknown result type (might be due to invalid IL or missing references) if (!Configuration.configToggleDoorUnlock.Value || !__instance.CanInteract()) { return result; } if (string.IsNullOrEmpty(result)) { return result; } return OverrideHoverText(result, __instance.m_nview, ((Component)__instance).transform.position); } [HarmonyPatch(typeof(Container), "GetHoverText")] [HarmonyPostfix] private static string ContainerGetHoverText(string result, Container __instance) { //IL_002d: Unknown result type (might be due to invalid IL or missing references) if (!Configuration.configToggleContainerUnlock.Value || !__instance.m_checkGuardStone) { return result; } if (string.IsNullOrEmpty(result)) { return result; } return OverrideHoverText(result, __instance.m_nview, ((Component)__instance).transform.position); } private static bool OverrideInteract(ZNetView view, Vector3 point, bool alt, bool hold, ref bool __result) { //IL_0016: Unknown result type (might be due to invalid IL or missing references) if (!Configuration.configWardUnlock.Value || !alt) { return true; } if (hold) { return false; } if (!PrivateArea.CheckAccess(point, 0f, false, false)) { return true; } if (!view.HasOwner()) { view.ClaimOwnership(); } view.InvokeRPC("ST_ForceUnlock", new object[1] { !view.GetZDO().GetBool(Hash.Unlock, false) }); __result = true; return false; } [HarmonyPatch(typeof(Door), "Interact")] [HarmonyPrefix] private static bool DoorInteract(Door __instance, bool alt, bool hold, ref bool __result) { //IL_0022: Unknown result type (might be due to invalid IL or missing references) if (!Configuration.configToggleDoorUnlock.Value || !__instance.CanInteract()) { return true; } return OverrideInteract(__instance.m_nview, ((Component)__instance).transform.position, alt, hold, ref __result); } [HarmonyPatch(typeof(Container), "Interact")] [HarmonyPrefix] private static bool ContainerInteract(Container __instance, bool alt, bool hold, ref bool __result) { //IL_0022: Unknown result type (might be due to invalid IL or missing references) if (!Configuration.configToggleContainerUnlock.Value || !__instance.m_checkGuardStone) { return true; } return OverrideInteract(__instance.m_nview, ((Component)__instance).transform.position, alt, hold, ref __result); } private static void ForceUnlock(ZNetView view, bool value) { view.GetZDO().Set(Hash.Unlock, value); } private static void Register(ZNetView view) { ZNetView view2 = view; if (Object.op_Implicit((Object)(object)view2)) { view2.Unregister("ST_ForceUnlock"); view2.Register<bool>("ST_ForceUnlock", (Action<long, bool>)delegate(long uid, bool value) { ForceUnlock(view2, value); }); } } [HarmonyPatch(typeof(Door), "Awake")] [HarmonyPostfix] private static void DoorAwake(Door __instance) { Door __instance2 = __instance; Register(__instance2.m_nview); Helper.Item(__instance2.m_nview, Hash.DoorKey, delegate(ItemDrop item) { __instance2.m_keyItem = item; }); Helper.Int(__instance2.m_nview, Hash.DoorNoClose, delegate(int value) { __instance2.m_canNotBeClosed = value > 0; }); Helper.String(__instance2.m_nview, Hash.DoorOpenEffect, delegate(string value) { __instance2.m_openEffects = Helper.ParseEffects(value); }); Helper.String(__instance2.m_nview, Hash.DoorCloseEffect, delegate(string value) { __instance2.m_closeEffects = Helper.ParseEffects(value); }); Helper.String(__instance2.m_nview, Hash.DoorLockedEffect, delegate(string value) { __instance2.m_lockedEffects = Helper.ParseEffects(value); }); } [HarmonyPatch(typeof(Container), "Awake")] [HarmonyPostfix] private static void ContainerAwake(Container __instance) { Register(__instance.m_nview); } [HarmonyPatch(typeof(Door), "Open")] [HarmonyPostfix] private static void DoorOpen(Door __instance) { Door __instance2 = __instance; Helper.Bool(__instance2.m_nview, Hash.DoorConsume, delegate { string text = __instance2.m_keyItem?.m_itemData?.m_shared.m_name; if (text != null) { Player localPlayer = Player.m_localPlayer; if (localPlayer != null) { ((Humanoid)localPlayer).GetInventory().RemoveItem(text, 1, -1, true); } } }); } } [HarmonyPatch(typeof(Plant))] public class Growth { public static int Number(string value) { return value switch { "small" => 4, "small_bad" => 1, "big" => 2, "big_bad" => 3, _ => 0, }; } [HarmonyPatch(typeof(Plant), "SUpdate")] [HarmonyPrefix] private static void StoreTime(Plant __instance, ref float __state) { __state = __instance.m_updateTime; } [HarmonyPatch(typeof(Plant), "SUpdate")] [HarmonyPostfix] private static void OverrideGrowth(Plant __instance, float __state) { Plant __instance2 = __instance; if (!Configuration.configGrowth.Value || !Object.op_Implicit((Object)(object)__instance2) || !__instance2.m_nview.IsValid() || __state == __instance2.m_updateTime) { return; } Helper.Int(__instance2.m_nview, Hash.Growth, delegate(int growth) { bool flag = growth == 4; bool flag2 = growth == 1; bool flag3 = growth == 2; bool flag4 = growth == 3; if (Object.op_Implicit((Object)(object)__instance2.m_healthyGrown)) { __instance2.m_healthy.SetActive(flag); __instance2.m_unhealthy.SetActive(flag2); __instance2.m_healthyGrown.SetActive(flag3); __instance2.m_unhealthyGrown.SetActive(flag4); } else { __instance2.m_healthy.SetActive(flag || flag3); __instance2.m_unhealthy.SetActive(flag2 || flag4); } }); } public static void SetGrowth(ZNetView view, string value) { if (view.IsOwner()) { int num = Number(value); view.GetZDO().Set(Hash.Growth, num, false); long num2; if (num >= 0) { DateTime maxValue = DateTime.MaxValue; num2 = maxValue.Ticks / 2; } else { num2 = ZNet.instance.GetTime().Ticks; } long num3 = num2; view.GetZDO().Set(ZDOVars.s_plantTime, num3); } } private static void Register(ZNetView view) { ZNetView view2 = view; if (Object.op_Implicit((Object)(object)view2)) { view2.Unregister("ST_SetGrowth"); view2.Register<string>("ST_SetGrowth", (Action<long, string>)delegate(long uid, string value) { SetGrowth(view2, value); }); } } [HarmonyPatch(typeof(Plant), "Awake")] [HarmonyPostfix] private static void RegisterRPC(Plant __instance) { Register(__instance.m_nview); } } public class GrowthCommand { private void Execute(Terminal terminal, ZNetView view, string value) { if (view.IsOwner()) { Growth.SetGrowth(view, value); } else { view.InvokeRPC("ST_SetGrowth", new object[1] { value }); } Plant val = default(Plant); if (((Component)view).TryGetComponent<Plant>(ref val)) { val.m_updateTime = 0f; } if (Growth.Number(value) < 0) { Helper.AddMessage(terminal, "Removed growth override."); } else { Helper.AddMessage(terminal, "Growth set to " + value + "."); } } public GrowthCommand() { //IL_0054: Unknown result type (might be due to invalid IL or missing references) //IL_0060: Unknown result type (might be due to invalid IL or missing references) //IL_006a: Expected O, but got Unknown //IL_006a: Expected O, but got Unknown List<string> values = new List<string> { "big", "big_bad", "small", "small_bad" }; Helper.Command("growth", "[big/big_bad/small/small_bad] - Overrides the plant growth.", (ConsoleEvent)delegate(ConsoleEventArgs args) { ZNetView hover = Helper.GetHover(Configuration.configGrowthEditing.Value); Execute(args.Context, hover, (args.Length > 1) ? args[1] : ""); }, (ConsoleOptionsFetcher)(() => values)); } } [HarmonyPatch] public class IgnoreDamage { private static bool Check(ZNetView view, float defaultValue) { if (Configuration.configIgnoreDamage.Value) { return Helper.IsFinite(view, defaultValue); } return true; } [HarmonyPatch(typeof(Character), "IsDodgeInvincible")] [HarmonyPostfix] private static bool Character_IsDodgeInvincible(bool result, Character __instance) { return !Check(__instance.m_nview, 0f) || result; } [HarmonyPatch(typeof(MineRock5), "RPC_Damage")] [HarmonyPrefix] private static bool MineRock5_RPC_Damage(MineRock5 __instance) { return Check(__instance.m_nview, 0f); } [HarmonyPatch(typeof(TreeLog), "RPC_Damage")] [HarmonyPrefix] private static bool TreeLog_RPC_Damage(TreeLog __instance) { return Check(__instance.m_nview, 0f); } [HarmonyPatch(typeof(WearNTear), "RPC_Damage")] [HarmonyPrefix] private static bool WearNTear_RPC_Damage(WearNTear __instance) { return Check(__instance.m_nview, __instance.m_health); } [HarmonyPatch(typeof(TreeBase), "RPC_Damage")] [HarmonyPrefix] private static bool TreeBase_RPC_Damage(TreeBase __instance) { return Check(__instance.m_nview, __instance.m_health); } [HarmonyPatch(typeof(Destructible), "RPC_Damage")] [HarmonyPrefix] private static bool Destructible_RPC_Damage(Destructible __instance) { return Check(__instance.m_nview, __instance.m_health); } [HarmonyPatch(typeof(Character), "RPC_Damage")] [HarmonyPrefix] private static bool Character_RPC_Damage(Character __instance) { return Check(__instance.m_nview, __instance.GetMaxHealth()); } [HarmonyPatch(typeof(MineRock), "GetDestructibleType")] [HarmonyPostfix] private static DestructibleType MineRock_GetDestructibleType(DestructibleType type, MineRock __instance) { //IL_0015: Unknown result type (might be due to invalid IL or missing references) if (!Check(__instance.m_nview, __instance.m_health)) { return (DestructibleType)0; } return type; } [HarmonyPatch(typeof(MineRock5), "GetDestructibleType")] [HarmonyPostfix] private static DestructibleType MineRock5_GetDestructibleType(DestructibleType type, MineRock5 __instance) { //IL_0015: Unknown result type (might be due to invalid IL or missing references) if (!Check(__instance.m_nview, __instance.m_health)) { return (DestructibleType)0; } return type; } [HarmonyPatch(typeof(TreeLog), "GetDestructibleType")] [HarmonyPostfix] private static DestructibleType TreeLog_GetDestructibleType(DestructibleType type, TreeLog __instance) { //IL_0015: Unknown result type (might be due to invalid IL or missing references) if (!Check(__instance.m_nview, __instance.m_health)) { return (DestructibleType)0; } return type; } [HarmonyPatch(typeof(WearNTear), "GetDestructibleType")] [HarmonyPostfix] private static DestructibleType WearNTear_GetDestructibleType(DestructibleType type, WearNTear __instance) { //IL_0015: Unknown result type (might be due to invalid IL or missing references) if (!Check(__instance.m_nview, __instance.m_health)) { return (DestructibleType)0; } return type; } [HarmonyPatch(typeof(TreeBase), "GetDestructibleType")] [HarmonyPostfix] private static DestructibleType TreeBase_GetDestructibleType(DestructibleType type, TreeBase __instance) { //IL_0015: Unknown result type (might be due to invalid IL or missing references) if (!Check(__instance.m_nview, __instance.m_health)) { return (DestructibleType)0; } return type; } [HarmonyPatch(typeof(Destructible), "GetDestructibleType")] [HarmonyPostfix] private static DestructibleType Destructible_GetDestructibleType(DestructibleType type, Destructible __instance) { //IL_0015: Unknown result type (might be due to invalid IL or missing references) if (!Check(__instance.m_nview, __instance.m_health)) { return (DestructibleType)0; } return type; } [HarmonyPatch(typeof(Character), "GetDestructibleType")] [HarmonyPostfix] private static DestructibleType Character_GetDestructibleType(DestructibleType type, Character __instance) { //IL_0015: Unknown result type (might be due to invalid IL or missing references) if (!Check(__instance.m_nview, __instance.GetMaxHealth())) { return (DestructibleType)0; } return type; } } [HarmonyPatch(typeof(WearNTear))] public class IgnoreSupport { public const float INFITE = 1E+19f; [HarmonyPatch("UpdateWear")] [HarmonyPrefix] private static bool UpdateWear() { return !Configuration.configDisableStructureSystems.Value; } [HarmonyPatch("UpdateSupport")] [HarmonyPrefix] private static bool UpdateSupport(WearNTear __instance) { if (!Configuration.configIgnoreSupport.Value) { return true; } if (!Object.op_Implicit((Object)(object)__instance) || !__instance.m_nview.IsValid()) { return true; } ZNetView nview = __instance.m_nview; if (Helper.IsFinite(nview, __instance.m_health)) { return true; } if (__instance.m_support == 1E+19f) { return false; } __instance.m_support = 1E+19f; nview.GetZDO().Set(ZDOVars.s_support, 1E+19f); return false; } } [HarmonyPatch(typeof(MusicLocation), "Awake")] public class MusicLocationAwake { private static Dictionary<string, AudioClip> Clips = new Dictionary<string, AudioClip>(); private static void Postfix(MusicLocation __instance) { if (!Configuration.configMusic.Value) { return; } MusicLocation obj = __instance; ZNetView nview = obj.m_nview; Helper.Float(nview, Hash.Radius, delegate(float value) { obj.m_radius = value; }); Helper.Int(nview, Hash.Condition, delegate(int value) { obj.m_oneTime = (value & 1) > 0; obj.m_notIfEnemies = (value & 2) > 0; obj.m_forceFade = (value & 3) > 0; }); Helper.String(nview, Hash.Audio, delegate(string value) { if (Clips.Count == 0) { Clips = Resources.FindObjectsOfTypeAll<AudioClip>().ToDictionary((AudioClip x) => ((Object)x).name, (AudioClip x) => x); } if (Clips.TryGetValue(value, out AudioClip value2)) { obj.m_audioSource.clip = value2; } else { Debug.LogWarning((object)("Audio clip " + value + " not found")); } }); } } [HarmonyPatch(typeof(ZNetScene), "CreateObject")] public class NoCollision { private static void Postfix(ZDO zdo, GameObject __result) { if (!Object.op_Implicit((Object)(object)__result) || !Configuration.configCollision.Value || zdo == null || !zdo.GetBool(Hash.NoCollision, false)) { return; } Collider[] componentsInChildren = __result.GetComponentsInChildren<Collider>(); if (zdo.GetPrefab() == Hash.Portal) { Collider[] array = componentsInChildren; for (int i = 0; i < array.Length; i++) { array[i].enabled = false; } } else { Collider[] array = componentsInChildren; for (int i = 0; i < array.Length; i++) { array[i].isTrigger = true; } } } } [HarmonyPatch(typeof(Player), "UpdateHover")] public class NoHover { private static void Postfix(Player __instance) { Player __instance2 = __instance; if (!Configuration.configInteract.Value) { return; } GameObject hovering = __instance2.m_hovering; if (Object.op_Implicit((Object)(object)hovering)) { Helper.Bool(((Component)hovering.transform.root).GetComponent<ZNetView>(), Hash.NoInteract, delegate { __instance2.m_hovering = null; }); } } } [HarmonyPatch(typeof(Player), "CheckCanRemovePiece")] public class NoRemove { private static bool Postfix(bool result, Piece piece) { if (!Configuration.configIgnoreRemove.Value) { return result; } if (!result) { return result; } if (!Object.op_Implicit((Object)(object)piece) || !piece.m_nview.IsValid()) { return true; } if (Game.instance.GetPlayerProfile().GetPlayerID() == piece.GetCreator()) { return true; } WearNTear val = default(WearNTear); return Helper.IsFinite(piece.m_nview, ((Component)piece).TryGetComponent<WearNTear>(ref val) ? val.m_health : 0f); } } [HarmonyPatch(typeof(ZNetScene), "CreateObject")] public class NoRender { private static void Postfix(ZDO zdo, GameObject __result) { if (Object.op_Implicit((Object)(object)__result) && Configuration.configRendering.Value && zdo != null && zdo.GetBool(Hash.NoRender, false)) { Renderer[] componentsInChildren = __result.GetComponentsInChildren<Renderer>(); for (int i = 0; i < componentsInChildren.Length; i++) { componentsInChildren[i].enabled = false; } } } } [HarmonyPatch(typeof(ZNetScene), "Awake")] public class NoTargeting { private static readonly Dictionary<int, bool> Originals = new Dictionary<int, bool>(); public static void Update() { Update(ZNetScene.instance); } public static void Update(int prefab, Piece obj) { bool value; if (Configuration.configNoTargeting.Value) { obj.m_targetNonPlayerBuilt = false; } else if (Originals.TryGetValue(prefab, out value)) { obj.m_targetNonPlayerBuilt = value; } } public static void Update(ZNetScene scene) { Dictionary<int, bool> dictionary = new Dictionary<int, bool>(); foreach (KeyValuePair<int, GameObject> namedPrefab in scene.m_namedPrefabs) { Piece component = namedPrefab.Value.GetComponent<Piece>(); if (component != null) { Update(namedPrefab.Key, component); dictionary[namedPrefab.Key] = component.m_targetNonPlayerBuilt; } } foreach (KeyValuePair<ZDO, ZNetView> instance in scene.m_instances) { int prefab = instance.Key.GetPrefab(); if (dictionary.ContainsKey(prefab)) { Piece component2 = ((Component)instance.Value).GetComponent<Piece>(); if (component2 != null) { component2.m_targetNonPlayerBuilt = dictionary[prefab]; } } } } [HarmonyPriority(0)] private static void Postfix(ZNetScene __instance) { foreach (KeyValuePair<int, GameObject> namedPrefab in __instance.m_namedPrefabs) { if (!Originals.ContainsKey(namedPrefab.Key)) { Piece component = namedPrefab.Value.GetComponent<Piece>(); if (component != null) { Originals[namedPrefab.Key] = component.m_targetNonPlayerBuilt; } } } Update(__instance); } } public class ZdoTextReceiver : MonoBehaviour, TextReceiver { private int Index; private readonly int[] Hashes = new int[4] { Hash.Name, Hash.Text, Hash.Topic, Hash.Compendium }; private readonly string[] Topics = new string[4] { "Enter name", "$piece_sign_input", "Enter topic", "Enter compendium topic" }; private ZNetView? m_nview; private bool Queued; public void Awake() { m_nview = ((Component)this).GetComponentInParent<ZNetView>(); } public void LateUpdate() { if (Queued) { TextInput.instance.RequestText((TextReceiver)(object)this, Topics[Index], 1000); } Queued = false; } public void Show() { Index = 0; Queued = true; } public string GetText() { string text = ""; Helper.String(m_nview, Hashes[Index], delegate(string value) { text = value; }); return text; } public void SetText(string text) { ZNetView? nview = m_nview; if (nview != null) { nview.GetZDO().Set(Hashes[Index], text); } Index++; if (Index == Hashes.Length) { Index = 0; } else { Queued = true; } } } [HarmonyPatch(typeof(RuneStone))] public class RuneStoneText { private static readonly int Name = StringExtensionMethods.GetStableHashCode("override_name"); private static readonly int Text = StringExtensionMethods.GetStableHashCode("override_text"); private static readonly int Topic = StringExtensionMethods.GetStableHashCode("override_topic"); private static readonly int Compendium = StringExtensionMethods.GetStableHashCode("override_compendium"); private static readonly int Discover = StringExtensionMethods.GetStableHashCode("override_discover"); [HarmonyPatch(typeof(RuneStone), "GetHoverText")] [HarmonyPrefix] private static void GetHoverText(RuneStone __instance) { RuneStone __instance2 = __instance; if (Configuration.configRuneStone.Value) { Helper.String(((Component)__instance2).GetComponentInParent<ZNetView>(), Name, delegate(string value) { __instance2.m_name = value; }); } } [HarmonyPatch(typeof(RuneStone), "GetHoverText")] [HarmonyPostfix] private static string GetHoverTextUseKey(string result, RuneStone __instance) { if (!Configuration.configRuneStone.Value) { return result; } if (!Helper.CanEdit(((Component)__instance).GetComponentInParent<ZNetView>(), Configuration.configRuneStoneEditing.Value)) { return result; } return result + Localization.instance.Localize("\n[<color=yellow><b>$KEY_AltPlace + $KEY_Use</b></color>] Edit"); } [HarmonyPatch(typeof(RuneStone), "GetHoverName")] [HarmonyPrefix] private static void GetHoverName(RuneStone __instance) { RuneStone __instance2 = __instance; if (Configuration.configRuneStone.Value) { Helper.String(((Component)__instance2).GetComponentInParent<ZNetView>(), Name, delegate(string value) { __instance2.m_name = value; }); } } [HarmonyPatch(typeof(RuneStone), "Interact")] [HarmonyPrefix] private static bool Interact(RuneStone __instance, bool alt, ref bool __result) { RuneStone __instance2 = __instance; if (!Configuration.configRuneStone.Value) { return true; } ZNetView componentInParent = ((Component)__instance2).GetComponentInParent<ZNetView>(); bool flag = Helper.CanEdit(componentInParent, Configuration.configRuneStoneEditing.Value); if (alt && flag) { __result = true; ZdoTextReceiver zdoTextReceiver = ((Component)__instance2).GetComponent<ZdoTextReceiver>(); if (!Object.op_Implicit((Object)(object)zdoTextReceiver)) { zdoTextReceiver = ((Component)__instance2).gameObject.AddComponent<ZdoTextReceiver>(); } zdoTextReceiver.Show(); return false; } RuneStone val = __instance2; if (val.m_randomTexts == null) { val.m_randomTexts = new List<RandomRuneText>(); } Helper.String(componentInParent, Text, delegate(string value) { __instance2.m_randomTexts = new List<RandomRuneText>(); __instance2.m_text = value; }); Helper.String(componentInParent, Topic, delegate(string value) { __instance2.m_randomTexts = new List<RandomRuneText>(); __instance2.m_topic = value; }); Helper.String(componentInParent, Compendium, delegate(string value) { __instance2.m_randomTexts = new List<RandomRuneText>(); __instance2.m_label = value; }); Helper.String(componentInParent, Discover, delegate(string value) { //IL_0030: Unknown result type (might be due to invalid IL or missing references) //IL_0035: Unknown result type (might be due to invalid IL or missing references) Discovery discovery = Helper.ParseDiscovery(value); __instance2.m_locationName = discovery.name; __instance2.m_pinName = discovery.pin; __instance2.m_pinType = discovery.type; __instance2.m_showMap = discovery.showMap; }); return true; } } [HarmonyPatch(typeof(Player), "AddKnownText")] public class AddKnownText { private static bool Prefix(Player __instance, string label, string text) { string[] array = label.Split(new char[1] { '|' }); if (array.Length > 1) { string[] array2 = array; foreach (string text2 in array2) { __instance.AddKnownText(text2, text); } return false; } if (label.StartsWith("-", StringComparison.Ordinal)) { __instance.m_knownTexts.Remove(label.Substring(1)); return false; } return true; } } [HarmonyPatch(typeof(SmokeSpawner), "IsBlocked")] public class SmokeBlock { private static bool Postfix(bool result, SmokeSpawner __instance) { if (!Configuration.configSmokeBlock.Value) { return result; } if (!result) { return result; } return Helper.Int(((Component)__instance).GetComponentInParent<ZNetView>(), Hash.Smoke) == 0; } } [HarmonyPatch(typeof(SmokeSpawner), "Spawn")] public class SmokeSpawn { private static bool Prefix(SmokeSpawner __instance) { if (!Configuration.configSmokeBlock.Value) { return true; } return Helper.Int(((Component)__instance).GetComponentInParent<ZNetView>(), Hash.Smoke) != 1; } } [HarmonyPatch] [BepInPlugin("structure_tweaks", "Structure Tweaks", "1.33")] public class Plugin : BaseUnityPlugin { private const string GUID = "structure_tweaks"; private const string NAME = "Structure Tweaks"; private const string VERSION = "1.33"; public static ConfigSync ConfigSync = new ConfigSync("structure_tweaks") { DisplayName = "Structure Tweaks", CurrentVersion = "1.33", IsLocked = true, ModRequired = true }; public void Awake() { //IL_001f: Unknown result type (might be due to invalid IL or missing references) Configuration.Init(new ConfigWrapper("structure_config", ((BaseUnityPlugin)this).Config, ConfigSync)); new Harmony("structure_tweaks").PatchAll(); } } [HarmonyPatch(typeof(Terminal), "InitTerminal")] public class SetCommands { private static void Postfix() { new GrowthCommand(); new WearCommand(); } } [HarmonyPatch(typeof(TeleportWorld), "Teleport")] public class Teleportable { private static void Prefix(TeleportWorld __instance) { if (Configuration.configTeleportable.Value) { Helper.Bool(__instance.m_nview, Hash.Restrict, delegate { ForceTeleportable.Force = true; }); } } private static void Postfix() { ForceTeleportable.Force = false; } } [HarmonyPatch(typeof(Humanoid), "IsTeleportable")] public class ForceTeleportable { public static bool Force; private static bool Postfix(bool result) { if (!result) { return Force; } return true; } } [HarmonyPatch(typeof(Vegvisir))] public class VegvisirText { private static void Setup(Vegvisir obj) { Vegvisir obj2 = obj; if (!Configuration.configRuneStone.Value) { return; } ZNetView componentInParent = ((Component)obj2).GetComponentInParent<ZNetView>(); Helper.String(componentInParent, Hash.Name, delegate(string value) { obj2.m_name = value; }); Helper.String(componentInParent, Hash.Discover, delegate(string value) { //IL_0058: Unknown result type (might be due to invalid IL or missing references) //IL_005d: Unknown result type (might be due to invalid IL or missing references) //IL_0024: Unknown result type (might be due to invalid IL or missing references) //IL_002e: Expected O, but got Unknown Discovery discovery = Helper.ParseDiscovery(value); if (obj2.m_locations.Count == 0) { obj2.m_locations.Add(new VegvisrLocation()); } VegvisrLocation obj3 = obj2.m_locations[0]; obj3.m_locationName = discovery.name; obj3.m_pinName = discovery.pin; obj3.m_pinType = discovery.type; }); } [HarmonyPatch(typeof(Vegvisir), "GetHoverText")] [HarmonyPrefix] private static void GetHoverText(Vegvisir __instance) { Setup(__instance); } [HarmonyPatch(typeof(Vegvisir), "GetHoverName")] [HarmonyPrefix] private static void GetHoverName(Vegvisir __instance) { Setup(__instance); } [HarmonyPatch(typeof(Vegvisir), "Interact")] [HarmonyPrefix] private static void Interact(Vegvisir __instance) { Setup(__instance); } } [HarmonyPatch(typeof(WearNTear))] public class Wear { public static int Number(string value) { return value switch { "broken" => 3, "damaged" => 1, "healthy" => 2, _ => 0, }; } public static void SetWear(ZNetView view, string value) { if (view.IsOwner()) { int num = Number(value); view.GetZDO().Set(Hash.Wear, num, false); } } private static void Register(ZNetView view) { ZNetView view2 = view; if (Object.op_Implicit((Object)(object)view2)) { view2.Unregister("TC_SetWear"); view2.Register<string>("TC_SetWear", (Action<long, string>)delegate(long uid, string value) { SetWear(view2, value); }); } } [HarmonyPatch(typeof(WearNTear), "Awake")] [HarmonyPostfix] private static void RegisterRPC(WearNTear __instance) { Register(__instance.m_nview); } private static float Convert(int value, float defaultValue) { return value switch { 3 => 0.1f, 1 => 0.5f, 2 => 1f, _ => defaultValue, }; } [HarmonyPatch("SetHealthVisual")] [HarmonyPrefix] private static void OverrideWear(WearNTear __instance, ref float health) { if (Configuration.configWear.Value && Object.op_Implicit((Object)(object)__instance.m_nview)) { int @int = __instance.m_nview.GetZDO().GetInt(Hash.Wear, 0); health = Convert(@int, health); } } } public class WearCommand { private void Execute(Terminal terminal, ZNetView view, string value) { Wear.SetWear(view, value); if (view.IsOwner()) { Wear.SetWear(view, value); } else { view.InvokeRPC("TC_SetWear", new object[1] { value }); } if (Wear.Number(value) < 0) { Helper.AddMessage(terminal, "Removed wear override."); } else { Helper.AddMessage(terminal, "Wear set to " + value + "."); } } public WearCommand() { //IL_0049: Unknown result type (might be due to invalid IL or missing references) //IL_0055: Unknown result type (might be due to invalid IL or missing references) //IL_005f: Expected O, but got Unknown //IL_005f: Expected O, but got Unknown List<string> values = new List<string> { "broken", "damaged", "healthy" }; Helper.Command("wear", "[broken/damaged/healthy] - Overrides the wear health.", (ConsoleEvent)delegate(ConsoleEventArgs args) { ZNetView hover = Helper.GetHover(Configuration.configGrowthEditing.Value); Execute(args.Context, hover, (args.Length > 1) ? args[1] : ""); }, (ConsoleOptionsFetcher)(() => values)); } } } namespace ServerSync { [PublicAPI] public abstract class OwnConfigEntryBase { public object? LocalBaseValue; public bool SynchronizedConfig = true; public abstract ConfigEntryBase BaseConfig { get; } } [PublicAPI] public class SyncedConfigEntry<T> : OwnConfigEntryBase { public readonly ConfigEntry<T> SourceConfig; public override ConfigEntryBase BaseConfig => (ConfigEntryBase)(object)SourceConfig; public T Value { get { return SourceConfig.Value; } set { SourceConfig.Value = value; } } public SyncedConfigEntry(ConfigEntry<T> sourceConfig) { SourceConfig = sourceConfig; } public void AssignLocalValue(T value) { if (LocalBaseValue == null) { Value = value; } else { LocalBaseValue = value; } } } internal abstract class CustomSyncedValueBase { public object? LocalBaseValue; public readonly string Identifier; public readonly Type Type; private object? boxedValue; protected bool localIsOwner; public readonly int Priority; public object? BoxedValue { get { return boxedValue; } set { boxedValue = value; this.ValueChanged?.Invoke(); } } public event Action? ValueChanged; protected CustomSyncedValueBase(ConfigSync configSync, string identifier, Type type, int priority) { Priority = priority; Identifier = identifier; Type = type; configSync.AddCustomValue(this); localIsOwner = configSync.IsSourceOfTruth; configSync.SourceOfTruthChanged += delegate(bool truth) { localIsOwner = truth; }; } } [PublicAPI] internal sealed class CustomSyncedValue<T> : CustomSyncedValueBase { public T Value { get { return (T)base.BoxedValue; } set { base.BoxedValue = value; } } public CustomSyncedValue(ConfigSync configSync, string identifier, T value = default(T), int priority = 0) : base(configSync, identifier, typeof(T), priority) { Value = value; } public void AssignLocalValue(T value) { if (localIsOwner) { Value = value; } else { LocalBaseValue = value; } } } internal class ConfigurationManagerAttributes { [UsedImplicitly] public bool? ReadOnly = false; } [PublicAPI] public class ConfigSync { [HarmonyPatch(typeof(ZRpc), "HandlePackage")] private static class SnatchCurrentlyHandlingRPC { public static ZRpc? currentRpc; [HarmonyPrefix] private static void Prefix(ZRpc __instance) { currentRpc = __instance; } } [HarmonyPatch(typeof(ZNet), "Awake")] internal static class RegisterRPCPatch { [HarmonyPostfix] private static void Postfix(ZNet __instance) { isServer = __instance.IsServer(); foreach (ConfigSync configSync2 in configSyncs) { ZRoutedRpc.instance.Register<ZPackage>(configSync2.Name + " ConfigSync", (Action<long, ZPackage>)configSync2.RPC_FromOtherClientConfigSync); if (isServer) { configSync2.InitialSyncDone = true; Debug.Log((object)("Registered '" + configSync2.Name + " ConfigSync' RPC - waiting for incoming connections")); } } if (isServer) { ((MonoBehaviour)__instance).StartCoroutine(WatchAdminListChanges()); } static void SendAdmin(List<ZNetPeer> peers, bool isAdmin) { ZPackage package = ConfigsToPackage(null, null, new PackageEntry[1] { new PackageEntry { section = "Internal", key = "lockexempt", type = typeof(bool), value = isAdmin } }); ConfigSync configSync = configSyncs.First(); if (configSync != null) { ((MonoBehaviour)ZNet.instance).StartCoroutine(configSync.sendZPackage(peers, package)); } } static IEnumerator WatchAdminListChanges() { MethodInfo listContainsId = AccessTools.DeclaredMethod(typeof(ZNet), "ListContainsId", (Type[])null, (Type[])null); SyncedList adminList = (SyncedList)AccessTools.DeclaredField(typeof(ZNet), "m_adminList").GetValue(ZNet.instance); List<string> CurrentList = new List<string>(adminList.GetList()); while (true) { yield return (object)new WaitForSeconds(30f); if (!adminList.GetList().SequenceEqual(CurrentList)) { CurrentList = new List<string>(adminList.GetList()); List<ZNetPeer> adminPeer = ZNet.instance.GetPeers().Where(delegate(ZNetPeer p) { string hostName = p.m_rpc.GetSocket().GetHostName(); return ((object)listContainsId == null) ? adminList.Contains(hostName) : ((bool)listContainsId.Invoke(ZNet.instance, new object[2] { adminList, hostName })); }).ToList(); List<ZNetPeer> nonAdminPeer = ZNet.instance.GetPeers().Except(adminPeer).ToList(); SendAdmin(nonAdminPeer, isAdmin: false); SendAdmin(adminPeer, isAdmin: true); } } } } } [HarmonyPatch(typeof(ZNet), "OnNewConnection")] private static class RegisterClientRPCPatch { [HarmonyPostfix] private static void Postfix(ZNet __instance, ZNetPeer peer) { if (__instance.IsServer()) { return; } foreach (ConfigSync configSync in configSyncs) { peer.m_rpc.Register<ZPackage>(configSync.Name + " ConfigSync", (Action<ZRpc, ZPackage>)configSync.RPC_FromServerConfigSync); } } } private class ParsedConfigs { public readonly Dictionary<OwnConfigEntryBase, object?> configValues = new Dictionary<OwnConfigEntryBase, object>(); public readonly Dictionary<CustomSyncedValueBase, object?> customValues = new Dictionary<CustomSyncedValueBase, object>(); } [HarmonyPatch(typeof(ZNet), "Shutdown")] private class ResetConfigsOnShutdown { [HarmonyPostfix] private static void Postfix() { ProcessingServerUpdate = true; foreach (ConfigSync configSync in configSyncs) { configSync.resetConfigsFromServer(); configSync.IsSourceOfTruth = true; configSync.InitialSyncDone = false; } ProcessingServerUpdate = false; } } [HarmonyPatch(typeof(ZNet), "RPC_PeerInfo")] private class SendConfigsAfterLogin { private class BufferingSocket : ISocket { public volatile bool finished = false; public volatile int versionMatchQueued = -1; public readonly List<ZPackage> Package = new List<ZPackage>(); public readonly ISocket Original; public BufferingSocket(ISocket original) { Original = original; } public bool IsConnected() { return Original.IsConnected(); } public ZPackage Recv() { return Original.Recv(); } public int GetSendQueueSize() { return Original.GetSendQueueSize(); } public int GetCurrentSendRate() { return Original.GetCurrentSendRate(); } public bool IsHost() { return Original.IsHost(); } public void Dispose() { Original.Dispose(); } public bool GotNewData() { return Original.GotNewData(); } public void Close() { Original.Close(); } public string GetEndPointString() { return Original.GetEndPointString(); } public void GetAndResetStats(out int totalSent, out int totalRecv) { Original.GetAndResetStats(ref totalSent, ref totalRecv); } public void GetConnectionQuality(out float localQuality, out float remoteQuality, out int ping, out float outByteSec, out float inByteSec) { Original.GetConnectionQuality(ref localQuality, ref remoteQuality, ref ping, ref outByteSec, ref inByteSec); } public ISocket Accept() { return Original.Accept(); } public int GetHostPort() { return Original.GetHostPort(); } public bool Flush() { return Original.Flush(); } public string GetHostName() { return Original.GetHostName(); } public void VersionMatch() { if (finished) { Original.VersionMatch(); } else { versionMatchQueued = Package.Count; } } public void Send(ZPackage pkg) { //IL_0057: Unknown result type (might be due to invalid IL or missing references) //IL_005d: Expected O, but got Unknown int pos = pkg.GetPos(); pkg.SetPos(0); int num = pkg.ReadInt(); if ((num == StringExtensionMethods.GetStableHashCode("PeerInfo") || num == StringExtensionMethods.GetStableHashCode("RoutedRPC") || num == StringExtensionMethods.GetStableHashCode("ZDOData")) && !finished) { ZPackage val = new ZPackage(pkg.GetArray()); val.SetPos(pos); Package.Add(val); } else { pkg.SetPos(pos); Original.Send(pkg); } } } [HarmonyPriority(800)] [HarmonyPrefix] private static void Prefix(ref Dictionary<Assembly, BufferingSocket>? __state, ZNet __instance, ZRpc rpc) { //IL_0078: Unknown result type (might be due to invalid IL or missing references) //IL_007e: Invalid comparison between Unknown and I4 if (__instance.IsServer()) { BufferingSocket value = new BufferingSocket(rpc.GetSocket()); AccessTools.DeclaredField(typeof(ZRpc), "m_socket").SetValue(rpc, value); object? obj = AccessTools.DeclaredMethod(typeof(ZNet), "GetPeer", new Type[1] { typeof(ZRpc) }, (Type[])null).Invoke(__instance, new object[1] { rpc }); ZNetPeer val = (ZNetPeer)((obj is ZNetPeer) ? obj : null); if (val != null && (int)ZNet.m_onlineBackend > 0) { AccessTools.DeclaredField(typeof(ZNetPeer), "m_socket").SetValue(val, value); } if (__state == null) { __state = new Dictionary<Assembly, BufferingSocket>(); } __state[Assembly.GetExecutingAssembly()] = value; } } [HarmonyPostfix] private static void Postfix(Dictionary<Assembly, BufferingSocket> __state, ZNet __instance, ZRpc rpc) { ZRpc rpc2 = rpc; ZNet __instance2 = __instance; Dictionary<Assembly, BufferingSocket> __state2 = __state; ZNetPeer peer; if (__instance2.IsServer()) { object obj = AccessTools.DeclaredMethod(typeof(ZNet), "GetPeer", new Type[1] { typeof(ZRpc) }, (Type[])null).Invoke(__instance2, new object[1] { rpc2 }); peer = (ZNetPeer)((obj is ZNetPeer) ? obj : null); if (peer == null) { SendBufferedData(); } else { ((MonoBehaviour)__instance2).StartCoroutine(sendAsync()); } } void SendBufferedData() { if (rpc2.GetSocket() is BufferingSocket bufferingSocket) { AccessTools.DeclaredField(typeof(ZRpc), "m_socket").SetValue(rpc2, bufferingSocket.Original); object? obj2 = AccessTools.DeclaredMethod(typeof(ZNet), "GetPeer", new Type[1] { typeof(ZRpc) }, (Type[])null).Invoke(__instance2, new object[1] { rpc2 }); ZNetPeer val = (ZNetPeer)((obj2 is ZNetPeer) ? obj2 : null); if (val != null) { AccessTools.DeclaredField(typeof(ZNetPeer), "m_socket").SetValue(val, bufferingSocket.Original); } } BufferingSocket bufferingSocket2 = __state2[Assembly.GetExecutingAssembly()]; bufferingSocket2.finished = true; for (int i = 0; i < bufferingSocket2.Package.Count; i++) { if (i == bufferingSocket2.versionMatchQueued) { bufferingSocket2.Original.VersionMatch(); } bufferingSocket2.Original.Send(bufferingSocket2.Package[i]); } if (bufferingSocket2.Package.Count == bufferingSocket2.versionMatchQueued) { bufferingSocket2.Original.VersionMatch(); } } IEnumerator sendAsync() { foreach (ConfigSync configSync in configSyncs) { List<PackageEntry> entries = new List<PackageEntry>(); if (configSync.CurrentVersion != null) { entries.Add(new PackageEntry { section = "Internal", key = "serverversion", type = typeof(string), value = configSync.CurrentVersion }); } MethodInfo listContainsId = AccessTools.DeclaredMethod(typeof(ZNet), "ListContainsId", (Type[])null, (Type[])null); SyncedList adminList = (SyncedList)AccessTools.DeclaredField(typeof(ZNet), "m_adminList").GetValue(ZNet.instance); entries.Add(new PackageEntry { section = "Internal", key = "lockexempt", type = typeof(bool), value = (((object)listContainsId == null) ? ((object)adminList.Contains(rpc2.GetSocket().GetHostName())) : listContainsId.Invoke(ZNet.instance, new object[2] { adminList, rpc2.GetSocket().GetHostName() })) }); ZPackage package = ConfigsToPackage(configSync.allConfigs.Select((OwnConfigEntryBase c) => c.BaseConfig), configSync.allCustomValues, entries, partial: false); yield return ((MonoBehaviour)__instance2).S