Please disclose if any significant portion of your mod was created using AI tools by adding the 'AI Generated' category. Failing to do so may result in the mod being removed from Thunderstore.
Decompiled source of AreaRepair v1.0.2
BepInEx/plugins/AreaRepair.dll
Decompiled 16 hours agousing System; using System.Collections.Generic; using System.Diagnostics; using System.Linq; using System.Reflection; using System.Runtime.CompilerServices; using System.Runtime.Versioning; using BepInEx; using BepInEx.Configuration; using BepInEx.Logging; using ConditionalConfigSync; using HarmonyLib; using Microsoft.CodeAnalysis; 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("AreaRepair")] [assembly: AssemblyConfiguration("Release")] [assembly: AssemblyFileVersion("1.0.0.0")] [assembly: AssemblyInformationalVersion("1.0.0")] [assembly: AssemblyProduct("AreaRepair")] [assembly: AssemblyTitle("AreaRepair")] [assembly: AssemblyVersion("1.0.0.0")] [module: RefSafetyRules(11)] namespace Microsoft.CodeAnalysis { [CompilerGenerated] [Embedded] internal sealed class EmbeddedAttribute : Attribute { } } namespace System.Runtime.CompilerServices { [CompilerGenerated] [Embedded] [AttributeUsage(AttributeTargets.Module, AllowMultiple = false, Inherited = false)] internal sealed class RefSafetyRulesAttribute : Attribute { public readonly int Version; public RefSafetyRulesAttribute(int P_0) { Version = P_0; } } } namespace Wabbaka.AreaRepair { internal static class AreaRepairRuntime { private static readonly FieldInfo HoveringPieceField = AccessTools.Field(typeof(Player), "m_hoveringPiece"); private static readonly MethodInfo CreatorMethod = AccessTools.Method(typeof(Piece), "GetCreator", (Type[])null, (Type[])null); private static readonly MethodInfo HealthMethod = AccessTools.Method(typeof(WearNTear), "GetHealthPercentage", (Type[])null, (Type[])null); private static readonly Type LocalizationType = AccessTools.TypeByName("Localization"); private static readonly PropertyInfo LocalizationInstanceProperty = ((LocalizationType == null) ? null : AccessTools.Property(LocalizationType, "instance")); private static readonly FieldInfo LocalizationInstanceField = ((LocalizationType == null) ? null : (AccessTools.Field(LocalizationType, "instance") ?? AccessTools.Field(LocalizationType, "m_instance"))); private static readonly MethodInfo GetSelectedLanguageMethod = ((LocalizationType == null) ? null : AccessTools.Method(LocalizationType, "GetSelectedLanguage", (Type[])null, (Type[])null)); private static readonly MethodInfo CharacterMessageMethod = AccessTools.GetDeclaredMethods(typeof(Character)).FirstOrDefault(delegate(MethodInfo method) { ParameterInfo[] parameters = method.GetParameters(); return method.Name == "Message" && parameters.Length >= 2 && parameters[0].ParameterType.IsEnum && parameters[1].ParameterType == typeof(string); }); internal static MethodInfo PlayerRepairMethod; internal static int AreaDepth; internal static bool SuppressMessages; internal static WearNTear DirectTarget; internal static bool DirectRepairSucceeded; internal static int RepairedCount; internal static Piece GetHoveringPiece(Player player) { object? obj = HoveringPieceField?.GetValue(player); return (Piece)((obj is Piece) ? obj : null); } internal static void SetHoveringPiece(Player player, Piece piece) { HoveringPieceField?.SetValue(player, piece); } internal static bool IsDamaged(WearNTear wear) { if ((Object)(object)wear == (Object)null || HealthMethod == null) { return (Object)(object)wear != (Object)null; } try { return Convert.ToSingle(HealthMethod.Invoke(wear, null)) < 0.9999f; } catch { return true; } } internal static bool IsPlayerBuilt(Piece piece) { if (!Plugin.OnlyPlayerBuilt.Value || CreatorMethod == null) { return true; } try { object obj = CreatorMethod.Invoke(piece, null); return obj != null && Convert.ToInt64(obj) != 0; } catch { return true; } } internal static bool CanContinue(Player player, ItemData tool) { try { if ((Object)(object)player == (Object)null || tool == null || ((Character)player).IsDead()) { return false; } if (tool.m_shared.m_useDurability && tool.m_durability <= 0f) { return false; } return ((Character)player).HaveStamina(tool.m_shared.m_attack.m_attackStamina); } catch { return true; } } internal static string SummaryText(int count) { string text = GetCurrentLanguage().Replace("_", string.Empty).Replace("-", string.Empty).Replace(" ", string.Empty) .ToLowerInvariant(); string format = ((text.Contains("traditional") && text.Contains("chinese")) ? "已修復建築部件:{0}" : (text.Contains("chinese") ? "已修复建筑部件:{0}" : (text.Contains("french") ? "Éléments réparés : {0}" : (text.Contains("german") ? "Reparierte Bauteile: {0}" : (text.Contains("spanish") ? "Piezas reparadas: {0}" : (text.Contains("russian") ? "Починено объектов: {0}" : (text.Contains("turkish") ? "Onarılan parçalar: {0}" : (text.Contains("japanese") ? "修理した建築パーツ: {0}" : ((text.Contains("portuguese") || text.Contains("brazil")) ? "Peças reparadas: {0}" : (text.Contains("polish") ? "Naprawione elementy: {0}" : (text.Contains("ukrain") ? "Відремонтовано об'єктів: {0}" : (text.Contains("italian") ? "Elementi riparati: {0}" : ((!text.Contains("korean")) ? "Pieces repaired: {0}" : "수리한 건축 부품: {0}"))))))))))))); return string.Format(format, count); } private static string GetCurrentLanguage() { //IL_005b: Unknown result type (might be due to invalid IL or missing references) //IL_0060: Unknown result type (might be due to invalid IL or missing references) try { object obj = LocalizationInstanceProperty?.GetValue(null, null) ?? LocalizationInstanceField?.GetValue(null); string text = GetSelectedLanguageMethod?.Invoke(obj, null)?.ToString(); if (!string.IsNullOrWhiteSpace(text)) { return text; } } catch { } return ((object)Application.systemLanguage/*cast due to .constrained prefix*/).ToString(); } internal static void ShowSummary(Player player, string text) { if ((Object)(object)player == (Object)null || CharacterMessageMethod == null) { return; } try { ParameterInfo[] parameters = CharacterMessageMethod.GetParameters(); object[] array = new object[parameters.Length]; array[0] = Enum.Parse(parameters[0].ParameterType, "TopLeft"); array[1] = text; for (int i = 2; i < parameters.Length; i++) { if (parameters[i].HasDefaultValue) { array[i] = parameters[i].DefaultValue; continue; } Type parameterType = parameters[i].ParameterType; array[i] = (parameterType.IsValueType ? Activator.CreateInstance(parameterType) : null); } CharacterMessageMethod.Invoke(player, array); } catch (Exception ex) { Plugin.Log.LogWarning((object)("Unable to show repair summary: " + ex.Message)); } } } [HarmonyPatch] internal static class PlayerRepairPatch { private sealed class RepairState { internal ItemData Tool; internal Piece TargetPiece; internal object[] Arguments; } private static MethodBase TargetMethod() { return AreaRepairRuntime.PlayerRepairMethod = AccessTools.GetDeclaredMethods(typeof(Player)).FirstOrDefault((MethodInfo candidate) => candidate.Name == "Repair" && candidate.GetParameters().Any((ParameterInfo parameter) => parameter.ParameterType == typeof(ItemData))); } private static void Prefix(Player __instance, object[] __args, out RepairState __state) { //IL_0029: Unknown result type (might be due to invalid IL or missing references) //IL_002e: Unknown result type (might be due to invalid IL or missing references) __state = null; if (AreaRepairRuntime.AreaDepth > 0 || !Plugin.Enabled.Value || (Object)(object)__instance != (Object)(object)Player.m_localPlayer) { return; } KeyboardShortcut value = Plugin.SingleRepairKey.Value; if (!((KeyboardShortcut)(ref value)).IsPressed()) { ItemData val = __args?.OfType<ItemData>().FirstOrDefault(); Piece hoveringPiece = AreaRepairRuntime.GetHoveringPiece(__instance); WearNTear val2 = ((hoveringPiece != null) ? ((Component)hoveringPiece).GetComponent<WearNTear>() : null); if (val != null && !((Object)(object)hoveringPiece == (Object)null) && !((Object)(object)val2 == (Object)null)) { __state = new RepairState { Tool = val, TargetPiece = hoveringPiece, Arguments = __args }; AreaRepairRuntime.DirectTarget = val2; AreaRepairRuntime.DirectRepairSucceeded = false; } } } private static void Postfix(Player __instance, RepairState __state) { if (__state == null) { return; } try { if (AreaRepairRuntime.PlayerRepairMethod != null) { RunAreaRepair(__instance, __state); } } catch (Exception arg) { Plugin.Log.LogError((object)$"Area repair failed: {arg}"); } finally { AreaRepairRuntime.DirectTarget = null; AreaRepairRuntime.DirectRepairSucceeded = false; } } private static void RunAreaRepair(Player player, RepairState state) { //IL_0023: Unknown result type (might be due to invalid IL or missing references) List<Piece> list = new List<Piece>(); Piece.GetAllPiecesInRadius(((Component)state.TargetPiece).transform.position, Plugin.Radius.Value, list); List<Piece> list2 = (from piece in list where (Object)(object)piece != (Object)null && (Object)(object)piece != (Object)(object)state.TargetPiece group piece by ((Object)piece).GetInstanceID() into @group select @group.First()).OrderBy(delegate(Piece piece) { //IL_0006: Unknown result type (might be due to invalid IL or missing references) //IL_001b: Unknown result type (might be due to invalid IL or missing references) //IL_0020: Unknown result type (might be due to invalid IL or missing references) //IL_0025: Unknown result type (might be due to invalid IL or missing references) Vector3 val = ((Component)piece).transform.position - ((Component)state.TargetPiece).transform.position; return ((Vector3)(ref val)).sqrMagnitude; }).Take(Plugin.MaximumPieces.Value).ToList(); Piece hoveringPiece = AreaRepairRuntime.GetHoveringPiece(player); AreaRepairRuntime.AreaDepth++; AreaRepairRuntime.SuppressMessages = true; AreaRepairRuntime.RepairedCount = 0; try { foreach (Piece item in list2) { if (!AreaRepairRuntime.CanContinue(player, state.Tool)) { break; } if (!((Object)(object)item == (Object)null) && ((Component)item).gameObject.activeInHierarchy) { WearNTear component = ((Component)item).GetComponent<WearNTear>(); if (!((Object)(object)component == (Object)null) && AreaRepairRuntime.IsDamaged(component) && AreaRepairRuntime.IsPlayerBuilt(item)) { AreaRepairRuntime.SetHoveringPiece(player, item); AreaRepairRuntime.PlayerRepairMethod.Invoke(player, state.Arguments); } } } } finally { AreaRepairRuntime.SetHoveringPiece(player, hoveringPiece); AreaRepairRuntime.SuppressMessages = false; AreaRepairRuntime.AreaDepth--; } int num = AreaRepairRuntime.RepairedCount + (AreaRepairRuntime.DirectRepairSucceeded ? 1 : 0); if (Plugin.ShowCount.Value && num > 1) { AreaRepairRuntime.ShowSummary(player, AreaRepairRuntime.SummaryText(num)); } Plugin.Log.LogDebug((object)$"Area repair: {num} piece(s), radius {Plugin.Radius.Value:0.##} m."); } } [HarmonyPatch(typeof(WearNTear), "Repair")] internal static class WearNTearRepairPatch { private static void Postfix(WearNTear __instance, bool __result) { if (__result) { if (AreaRepairRuntime.AreaDepth > 0) { AreaRepairRuntime.RepairedCount++; } else if ((Object)(object)__instance == (Object)(object)AreaRepairRuntime.DirectTarget) { AreaRepairRuntime.DirectRepairSucceeded = true; } } } } [HarmonyPatch] internal static class CharacterMessagePatch { private static IEnumerable<MethodBase> TargetMethods() { return from method in AccessTools.GetDeclaredMethods(typeof(Character)) where method.Name == "Message" select method; } private static bool Prefix(Character __instance) { if (AreaRepairRuntime.SuppressMessages) { return (Object)(object)__instance != (Object)(object)Player.m_localPlayer; } return true; } } [BepInPlugin("Wabbaka.AreaRepair", "AreaRepair", "1.0.1")] [BepInDependency(/*Could not decode attribute arguments.*/)] public sealed class Plugin : BaseUnityPlugin { public const string Guid = "Wabbaka.AreaRepair"; public const string Name = "AreaRepair"; public const string Version = "1.0.1"; private static readonly ConfigSync ConfigSync = new ConfigSync("Wabbaka.AreaRepair") { DisplayName = "AreaRepair", CurrentVersion = "1.0.1", MinimumRequiredVersion = "1.0.1", ModRequired = true }; internal static ConfigEntry<bool> LockConfiguration; internal static ConfigEntry<bool> Enabled; internal static ConfigEntry<float> Radius; internal static ConfigEntry<int> MaximumPieces; internal static ConfigEntry<bool> OnlyPlayerBuilt; internal static ConfigEntry<KeyboardShortcut> SingleRepairKey; internal static ConfigEntry<bool> ShowCount; internal static ManualLogSource Log; private Harmony _harmony; private void Awake() { //IL_007f: Unknown result type (might be due to invalid IL or missing references) //IL_0089: Expected O, but got Unknown //IL_00b3: Unknown result type (might be due to invalid IL or missing references) //IL_00bd: Expected O, but got Unknown //IL_00f2: Unknown result type (might be due to invalid IL or missing references) //IL_0127: Unknown result type (might be due to invalid IL or missing references) //IL_0131: Expected O, but got Unknown Log = ((BaseUnityPlugin)this).Logger; LockConfiguration = ((BaseUnityPlugin)this).Config.Bind<bool>("Server", "LockConfiguration", true, "Only server administrators may change synchronized settings."); ((ConditionalConfigSync)ConfigSync).AddLockingConfigEntry<bool>(LockConfiguration); Enabled = BindServer("General", "Enabled", defaultValue: true, "Enable area repair."); Radius = BindServer("Repair", "Radius", 7.5f, new ConfigDescription("Repair radius in metres.", (AcceptableValueBase)(object)new AcceptableValueRange<float>(1f, 100f), Array.Empty<object>())); MaximumPieces = BindServer("Repair", "MaximumPieces", 250, new ConfigDescription("Safety limit per hammer action.", (AcceptableValueBase)(object)new AcceptableValueRange<int>(1, 2000), Array.Empty<object>())); OnlyPlayerBuilt = BindServer("Repair", "OnlyPlayerBuilt", defaultValue: false, "Ignore generated ruins and other pieces with no player creator."); SingleRepairKey = BindClient<KeyboardShortcut>("Controls", "SingleRepairKey", new KeyboardShortcut((KeyCode)308, Array.Empty<KeyCode>()), "Hold for normal single-piece repair."); ShowCount = BindClient("Interface", "ShowRepairCount", defaultValue: true, "Show the total number of repaired pieces."); _harmony = new Harmony("Wabbaka.AreaRepair"); _harmony.PatchAll(typeof(Plugin).Assembly); ((BaseUnityPlugin)this).Logger.LogInfo((object)"AreaRepair 1.0.1 loaded."); } private ConfigEntry<T> BindServer<T>(string section, string key, T defaultValue, string description) { //IL_000c: Unknown result type (might be due to invalid IL or missing references) //IL_0016: Expected O, but got Unknown return BindServer(section, key, defaultValue, new ConfigDescription(description, (AcceptableValueBase)null, Array.Empty<object>())); } private ConfigEntry<T> BindServer<T>(string section, string key, T defaultValue, ConfigDescription description) { ConfigEntry<T> val = ((BaseUnityPlugin)this).Config.Bind<T>(section, key, defaultValue, description); ((ConditionalConfigSync)ConfigSync).AddConfigEntry<T>(val, (ConfigSyncMode)0); return val; } private ConfigEntry<T> BindClient<T>(string section, string key, T defaultValue, string description) { ConfigEntry<T> val = ((BaseUnityPlugin)this).Config.Bind<T>(section, key, defaultValue, description); ((ConditionalConfigSync)ConfigSync).AddConfigEntry<T>(val, (ConfigSyncMode)2); return val; } private void OnDestroy() { Harmony harmony = _harmony; if (harmony != null) { harmony.UnpatchSelf(); } } } }