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 PingDescriptions v1.0.0
plugins\PingDescriptions\PingDescriptions.dll
Decompiled 13 hours agousing System; using System.Diagnostics; using System.IO; using System.Linq; using System.Reflection; using System.Runtime.CompilerServices; using System.Runtime.Versioning; using System.Security; using System.Security.Permissions; using System.Text.RegularExpressions; using BepInEx; using BepInEx.Bootstrap; using BepInEx.Logging; using Microsoft.CodeAnalysis; using MonoMod.RuntimeDetour; using RoR2; using UnityEngine; using UnityEngine.Networking; [assembly: CompilationRelaxations(8)] [assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)] [assembly: Debuggable(DebuggableAttribute.DebuggingModes.Default | DebuggableAttribute.DebuggingModes.DisableOptimizations | DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints | DebuggableAttribute.DebuggingModes.EnableEditAndContinue)] [assembly: TargetFramework(".NETStandard,Version=v2.1", FrameworkDisplayName = ".NET Standard 2.1")] [assembly: AssemblyCompany("PingDescriptions")] [assembly: AssemblyConfiguration("Debug")] [assembly: AssemblyFileVersion("1.0.0.0")] [assembly: AssemblyInformationalVersion("1.0.0+396cce5d96502f9f851f89c266705a1398a7827e")] [assembly: AssemblyProduct("PingDescriptions")] [assembly: AssemblyTitle("PingDescriptions")] [assembly: SecurityPermission(SecurityAction.RequestMinimum, SkipVerification = true)] [assembly: AssemblyVersion("1.0.0.0")] [module: UnverifiableCode] [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 PingDescriptions { internal static class Log { private static ManualLogSource _logSource; internal static void Init(ManualLogSource logSource) { _logSource = logSource; } private static string Format(object data, string file, int line) { string fileName = Path.GetFileName(file); return $"[{fileName}:{line}] {data}"; } internal static void Debug(object data, [CallerFilePath] string file = "", [CallerLineNumber] int line = 0) { _logSource.LogDebug((object)Format(data, file, line)); } internal static void Error(object data, [CallerFilePath] string file = "", [CallerLineNumber] int line = 0) { _logSource.LogError((object)Format(data, file, line)); } internal static void Fatal(object data, [CallerFilePath] string file = "", [CallerLineNumber] int line = 0) { _logSource.LogFatal((object)Format(data, file, line)); } internal static void Info(object data, [CallerFilePath] string file = "", [CallerLineNumber] int line = 0) { _logSource.LogInfo((object)Format(data, file, line)); } internal static void Message(object data, [CallerFilePath] string file = "", [CallerLineNumber] int line = 0) { _logSource.LogMessage((object)Format(data, file, line)); } internal static void Warning(object data, [CallerFilePath] string file = "", [CallerLineNumber] int line = 0) { _logSource.LogWarning((object)Format(data, file, line)); } } [BepInDependency(/*Could not decode attribute arguments.*/)] [BepInPlugin("timoh.PingDescriptions", "PingDescriptions", "1.0.0")] public class PingDescriptionsPlugin : BaseUnityPlugin { public const string PluginGUID = "timoh.PingDescriptions"; public const string PluginName = "PingDescriptions"; public const string PluginVersion = "1.0.0"; private static MethodInfo _lgGetItemDescription; private static readonly Regex _tagRegex = new Regex("<[^>]+>", RegexOptions.Compiled); public void Awake() { //IL_0113: Unknown result type (might be due to invalid IL or missing references) Log.Init(((BaseUnityPlugin)this).Logger); Log.Info("Loading PingDescriptions v1.0.0...", "C:\\Users\\timoh\\Dropbox\\Programming\\RiskOfRain2Mods\\PingDescriptions-main\\PingDescriptions\\PingDescriptions.cs", 26); if (Chainloader.PluginInfos.ContainsKey("droppod.lookingglass")) { try { _lgGetItemDescription = Type.GetType("LookingGlass.ItemStatsNameSpace.ItemStats, LookingGlass")?.GetMethod("GetItemDescription", BindingFlags.Static | BindingFlags.Public); if (_lgGetItemDescription != null) { Log.Info("LookingGlass detected — will use enhanced item descriptions with stat calculations.", "C:\\Users\\timoh\\Dropbox\\Programming\\RiskOfRain2Mods\\PingDescriptions-main\\PingDescriptions\\PingDescriptions.cs", 37); } else { Log.Warning("LookingGlass found but GetItemDescription method could not be located. Falling back to vanilla descriptions.", "C:\\Users\\timoh\\Dropbox\\Programming\\RiskOfRain2Mods\\PingDescriptions-main\\PingDescriptions\\PingDescriptions.cs", 39); } } catch (Exception ex) { Log.Warning("Failed to access LookingGlass methods: " + ex.Message, "C:\\Users\\timoh\\Dropbox\\Programming\\RiskOfRain2Mods\\PingDescriptions-main\\PingDescriptions\\PingDescriptions.cs", 43); } } else { Log.Info("LookingGlass not detected — using vanilla item descriptions.", "C:\\Users\\timoh\\Dropbox\\Programming\\RiskOfRain2Mods\\PingDescriptions-main\\PingDescriptions\\PingDescriptions.cs", 48); } MethodInfo method = typeof(PingerController).GetMethod("SetCurrentPing", BindingFlags.Instance | BindingFlags.NonPublic); if (method == null) { Log.Error("Could not find PingerController.SetCurrentPing — ping hook will not be installed.", "C:\\Users\\timoh\\Dropbox\\Programming\\RiskOfRain2Mods\\PingDescriptions-main\\PingDescriptions\\PingDescriptions.cs", 58); return; } new Hook((MethodBase)method, (Delegate)new Action<Action<PingerController, PingInfo>, PingerController, PingInfo>(OnPing)); Log.Info("PingDescriptions loaded successfully. All players' item pings will be broadcast to chat.", "C:\\Users\\timoh\\Dropbox\\Programming\\RiskOfRain2Mods\\PingDescriptions-main\\PingDescriptions\\PingDescriptions.cs", 65); } private static void OnPing(Action<PingerController, PingInfo> orig, PingerController self, PingInfo newPingInfo) { //IL_0003: Unknown result type (might be due to invalid IL or missing references) //IL_008b: Unknown result type (might be due to invalid IL or missing references) //IL_0090: Unknown result type (might be due to invalid IL or missing references) //IL_00ac: Unknown result type (might be due to invalid IL or missing references) //IL_00b1: Unknown result type (might be due to invalid IL or missing references) //IL_012c: Unknown result type (might be due to invalid IL or missing references) //IL_012d: Unknown result type (might be due to invalid IL or missing references) //IL_0142: Unknown result type (might be due to invalid IL or missing references) //IL_0125: Unknown result type (might be due to invalid IL or missing references) //IL_012a: Unknown result type (might be due to invalid IL or missing references) //IL_015b: Unknown result type (might be due to invalid IL or missing references) //IL_00f0: Unknown result type (might be due to invalid IL or missing references) //IL_00f5: Unknown result type (might be due to invalid IL or missing references) //IL_018f: Unknown result type (might be due to invalid IL or missing references) //IL_0194: Unknown result type (might be due to invalid IL or missing references) //IL_01a1: Expected O, but got Unknown //IL_01ad: Unknown result type (might be due to invalid IL or missing references) orig(self, newPingInfo); if (!NetworkServer.active || (Object)(object)((PingInfo)(ref newPingInfo)).targetGameObject == (Object)null) { return; } CharacterMaster component = ((Component)self).gameObject.GetComponent<CharacterMaster>(); object obj; if (component == null) { obj = null; } else { PlayerCharacterMasterController playerCharacterMasterController = component.playerCharacterMasterController; obj = ((playerCharacterMasterController == null) ? null : playerCharacterMasterController.networkUser?.userName); } if (obj == null) { if (component == null) { obj = null; } else { CharacterBody body = component.GetBody(); obj = ((body != null) ? body.GetDisplayName() : null); } if (obj == null) { obj = "Unknown"; } } string text = (string)obj; PickupIndex val = PickupIndex.none; GenericPickupController val2 = default(GenericPickupController); ShopTerminalBehavior val3 = default(ShopTerminalBehavior); PickupDistributorBehavior val4 = default(PickupDistributorBehavior); if (((PingInfo)(ref newPingInfo)).targetGameObject.TryGetComponent<GenericPickupController>(ref val2)) { val = val2._pickupState.pickupIndex; } else if (((PingInfo)(ref newPingInfo)).targetGameObject.TryGetComponent<ShopTerminalBehavior>(ref val3)) { if (!val3.hidden && (Object)(object)val3.pickupDisplay != (Object)null) { val = val3.pickup.pickupIndex; } } else if (((PingInfo)(ref newPingInfo)).targetGameObject.TryGetComponent<PickupDistributorBehavior>(ref val4) && !val4.hidden) { val = val4.pickup.pickupIndex; } if (val == PickupIndex.none) { return; } PickupDef pickupDef = PickupCatalog.GetPickupDef(val); if (pickupDef == null) { Log.Warning($"OnPing: PickupCatalog returned null for pickupIndex={val}", "C:\\Users\\timoh\\Dropbox\\Programming\\RiskOfRain2Mods\\PingDescriptions-main\\PingDescriptions\\PingDescriptions.cs", 113); return; } string text2 = BuildChatMessage(pickupDef, component, text); if (!string.IsNullOrEmpty(text2)) { Chat.SendBroadcastChat((ChatMessageBase)new SimpleChatMessage { baseToken = text2 }); Log.Info("Broadcast ping description: '" + text + "' pinged " + Language.GetString(PickupCatalog.GetPickupDef(val)?.nameToken ?? ""), "C:\\Users\\timoh\\Dropbox\\Programming\\RiskOfRain2Mods\\PingDescriptions-main\\PingDescriptions\\PingDescriptions.cs", 126); } } private static string BuildChatMessage(PickupDef pickupDef, CharacterMaster pingerMaster, string pingerName) { //IL_0002: Unknown result type (might be due to invalid IL or missing references) //IL_0008: Invalid comparison between Unknown and I4 //IL_0078: Unknown result type (might be due to invalid IL or missing references) //IL_007e: Invalid comparison between Unknown and I4 //IL_0013: Unknown result type (might be due to invalid IL or missing references) //IL_008e: Unknown result type (might be due to invalid IL or missing references) //IL_0034: Unknown result type (might be due to invalid IL or missing references) //IL_00af: Unknown result type (might be due to invalid IL or missing references) //IL_0116: Unknown result type (might be due to invalid IL or missing references) string text; string text2; if ((int)pickupDef.itemIndex != -1) { ItemDef itemDef = ItemCatalog.GetItemDef(pickupDef.itemIndex); if ((Object)(object)itemDef == (Object)null) { Log.Warning($"BuildChatMessage: ItemCatalog returned null for itemIndex={pickupDef.itemIndex}", "C:\\Users\\timoh\\Dropbox\\Programming\\RiskOfRain2Mods\\PingDescriptions-main\\PingDescriptions\\PingDescriptions.cs", 139); return null; } text = Language.GetString(itemDef.nameToken); text2 = GetItemDescriptionText(itemDef, pingerMaster); } else { if ((int)pickupDef.equipmentIndex == -1) { return null; } EquipmentDef equipmentDef = EquipmentCatalog.GetEquipmentDef(pickupDef.equipmentIndex); if ((Object)(object)equipmentDef == (Object)null) { Log.Warning($"BuildChatMessage: EquipmentCatalog returned null for equipmentIndex={pickupDef.equipmentIndex}", "C:\\Users\\timoh\\Dropbox\\Programming\\RiskOfRain2Mods\\PingDescriptions-main\\PingDescriptions\\PingDescriptions.cs", 150); return null; } text = Language.GetString(equipmentDef.nameToken); text2 = (Language.IsTokenInvalid(equipmentDef.descriptionToken) ? Language.GetString(equipmentDef.pickupToken) : Language.GetString(equipmentDef.descriptionToken)); } string text3 = ColorUtility.ToHtmlStringRGB(pickupDef.baseColor); return "<color=#f0e68c>[Ping]</color> " + pingerName + " → <color=#" + text3 + ">" + text + "</color>: " + CompactForChat(text2); } private static string GetItemDescriptionText(ItemDef itemDef, CharacterMaster master) { //IL_0039: Unknown result type (might be due to invalid IL or missing references) if (_lgGetItemDescription != null) { try { int? obj; if (master == null) { obj = null; } else { Inventory inventory = master.inventory; obj = ((inventory != null) ? new int?(inventory.GetItemCountEffective(itemDef.itemIndex)) : ((int?)null)); } int num = obj ?? 1; if (num < 1) { num = 1; } string text = (string)_lgGetItemDescription.Invoke(null, new object[5] { itemDef, num, master, false, false }); if (!string.IsNullOrEmpty(text)) { return text; } } catch (Exception ex) { Log.Warning("GetItemDescriptionText: LookingGlass call failed — " + ex.Message, "C:\\Users\\timoh\\Dropbox\\Programming\\RiskOfRain2Mods\\PingDescriptions-main\\PingDescriptions\\PingDescriptions.cs", 186); } } return Language.IsTokenInvalid(itemDef.descriptionToken) ? Language.GetString(itemDef.pickupToken) : Language.GetString(itemDef.descriptionToken); } private static string CompactForChat(string text) { string text2 = _tagRegex.Replace(text ?? string.Empty, string.Empty); string[] array = (from l in text2.Split('\n') select l.Trim() into l where !string.IsNullOrEmpty(l) select l).ToArray(); if (array.Length == 0) { return string.Empty; } if (array.Length == 1) { return array[0]; } string text3 = array[0]; string text4 = string.Join(" | ", array.Skip(1)); return text3 + " [" + text4 + "]"; } } }