using System; using System.Diagnostics; using System.Reflection; using System.Runtime.CompilerServices; using System.Runtime.Versioning; using System.Security; using System.Security.Permissions; using System.Text; using BepInEx; using BepInEx.Configuration; using HarmonyLib; using Microsoft.CodeAnalysis; using TMPro; using UnityEngine; using UnityEngine.EventSystems; using UnityEngine.SceneManagement; using UnityEngine.UI; [assembly: CompilationRelaxations(8)] [assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)] [assembly: Debuggable(DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints)] [assembly: TargetFramework(".NETStandard,Version=v2.1", FrameworkDisplayName = ".NET Standard 2.1")] [assembly: AssemblyCompany("SessionStats")] [assembly: AssemblyConfiguration("Release")] [assembly: AssemblyFileVersion("1.0.0.0")] [assembly: AssemblyInformationalVersion("1.0.0")] [assembly: AssemblyProduct("SessionStats")] [assembly: AssemblyTitle("SessionStats")] [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.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] [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] [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 Ocewen.SessionStats { internal class DragHandler : MonoBehaviour, IBeginDragHandler, IEventSystemHandler, IDragHandler, IEndDragHandler { private RectTransform? _rect; private Vector2 _dragOffset; private void Awake() { _rect = ((Component)this).GetComponent(); } public void OnBeginDrag(PointerEventData data) { //IL_0020: Unknown result type (might be due to invalid IL or missing references) //IL_003a: Unknown result type (might be due to invalid IL or missing references) //IL_003f: Unknown result type (might be due to invalid IL or missing references) //IL_0040: Unknown result type (might be due to invalid IL or missing references) //IL_0045: Unknown result type (might be due to invalid IL or missing references) if (!((Object)(object)_rect == (Object)null)) { Transform parent = ((Transform)_rect).parent; Vector2 val = default(Vector2); RectTransformUtility.ScreenPointToLocalPointInRectangle((RectTransform)(object)((parent is RectTransform) ? parent : null), data.position, data.pressEventCamera, ref val); _dragOffset = _rect.anchoredPosition - val; } } public void OnDrag(PointerEventData data) { //IL_0020: Unknown result type (might be due to invalid IL or missing references) //IL_0039: Unknown result type (might be due to invalid IL or missing references) //IL_003b: Unknown result type (might be due to invalid IL or missing references) //IL_0040: Unknown result type (might be due to invalid IL or missing references) if (!((Object)(object)_rect == (Object)null)) { Transform parent = ((Transform)_rect).parent; Vector2 val = default(Vector2); RectTransformUtility.ScreenPointToLocalPointInRectangle((RectTransform)(object)((parent is RectTransform) ? parent : null), data.position, data.pressEventCamera, ref val); _rect.anchoredPosition = val + _dragOffset; } } public void OnEndDrag(PointerEventData data) { //IL_0015: Unknown result type (might be due to invalid IL or missing references) //IL_001a: Unknown result type (might be due to invalid IL or missing references) //IL_0020: Unknown result type (might be due to invalid IL or missing references) //IL_0030: Unknown result type (might be due to invalid IL or missing references) if (!((Object)(object)_rect == (Object)null)) { Vector2 anchoredPosition = _rect.anchoredPosition; ModConfig.PosX.Value = anchoredPosition.x; ModConfig.PosY.Value = 0f - anchoredPosition.y; } } } internal static class HudDisplay { private static GameObject? _root; private static RectTransform? _rootRect; private static Image? _borderImage; private static Image? _bgImage; private static RectTransform? _bgRect; private static TextMeshProUGUI? _label; internal static void Create() { //IL_0013: Unknown result type (might be due to invalid IL or missing references) //IL_0019: Expected O, but got Unknown //IL_0046: Unknown result type (might be due to invalid IL or missing references) //IL_0050: Expected O, but got Unknown //IL_009e: Unknown result type (might be due to invalid IL or missing references) //IL_00b7: Unknown result type (might be due to invalid IL or missing references) //IL_00d0: 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_00e4: Unknown result type (might be due to invalid IL or missing references) //IL_00fa: Unknown result type (might be due to invalid IL or missing references) //IL_0114: Unknown result type (might be due to invalid IL or missing references) //IL_0123: Unknown result type (might be due to invalid IL or missing references) //IL_0132: Unknown result type (might be due to invalid IL or missing references) //IL_0137: Unknown result type (might be due to invalid IL or missing references) //IL_014d: Unknown result type (might be due to invalid IL or missing references) //IL_0174: Unknown result type (might be due to invalid IL or missing references) //IL_017e: Unknown result type (might be due to invalid IL or missing references) if (!((Object)(object)_root != (Object)null)) { GameObject val = new GameObject("SessionStatsCanvas"); Object.DontDestroyOnLoad((Object)(object)val); Canvas obj = val.AddComponent(); obj.renderMode = (RenderMode)0; obj.sortingOrder = 100; val.AddComponent(); val.AddComponent(); _root = new GameObject("SessionStatsPanel"); _root.transform.SetParent(val.transform, false); _borderImage = _root.AddComponent(); _root.AddComponent(); _rootRect = _root.GetComponent(); _rootRect.anchorMin = new Vector2(0f, 1f); _rootRect.anchorMax = new Vector2(0f, 1f); _rootRect.pivot = new Vector2(0f, 1f); GameObject val2 = new GameObject("BG"); val2.transform.SetParent(_root.transform, false); _bgImage = val2.AddComponent(); _bgRect = val2.GetComponent(); _bgRect.anchorMin = Vector2.zero; _bgRect.anchorMax = Vector2.one; GameObject val3 = new GameObject("Label"); val3.transform.SetParent(_root.transform, false); _label = val3.AddComponent(); ((TMP_Text)_label).enableWordWrapping = false; ((TMP_Text)_label).overflowMode = (TextOverflowModes)0; RectTransform component = val3.GetComponent(); component.anchorMin = Vector2.zero; component.anchorMax = Vector2.one; UpdateLayout(); UpdateStyle(); } } internal static void Destroy() { if ((Object)(object)_root != (Object)null) { Object.Destroy((Object)(object)((Component)_root.transform.parent).gameObject); } _root = null; _rootRect = null; _borderImage = null; _bgImage = null; _bgRect = null; _label = null; } internal static void UpdateLayout() { //IL_0028: Unknown result type (might be due to invalid IL or missing references) if (!((Object)(object)_rootRect == (Object)null)) { _rootRect.anchoredPosition = new Vector2(ModConfig.PosX.Value, 0f - ModConfig.PosY.Value); } } internal static void UpdateStyle() { //IL_0017: Unknown result type (might be due to invalid IL or missing references) //IL_0040: Unknown result type (might be due to invalid IL or missing references) //IL_0053: Unknown result type (might be due to invalid IL or missing references) //IL_0074: Unknown result type (might be due to invalid IL or missing references) //IL_00c6: Unknown result type (might be due to invalid IL or missing references) //IL_00d4: Unknown result type (might be due to invalid IL or missing references) if ((Object)(object)_borderImage != (Object)null) { ((Graphic)_borderImage).color = ModConfig.BorderColor.Value; } float value = ModConfig.BorderSize.Value; if ((Object)(object)_bgRect != (Object)null) { _bgRect.offsetMin = new Vector2(value, value); _bgRect.offsetMax = new Vector2(0f - value, 0f - value); } if ((Object)(object)_bgImage != (Object)null) { ((Graphic)_bgImage).color = ModConfig.BgColor.Value; } if ((Object)(object)_label != (Object)null) { ((TMP_Text)_label).fontSize = ModConfig.FontSize.Value; } float num = ModConfig.BgPadding.Value + value; if ((Object)(object)_label != (Object)null) { RectTransform component = ((Component)_label).GetComponent(); component.offsetMin = new Vector2(num, num); component.offsetMax = new Vector2(0f - num, 0f - num); } Refresh(); } internal static void Refresh() { //IL_0025: Unknown result type (might be due to invalid IL or missing references) //IL_003f: Unknown result type (might be due to invalid IL or missing references) //IL_0251: Unknown result type (might be due to invalid IL or missing references) if ((Object)(object)_label == (Object)null || (Object)(object)_rootRect == (Object)null) { return; } string text = "#" + ColorUtility.ToHtmlStringRGBA(ModConfig.LabelColor.Value); string text2 = "#" + ColorUtility.ToHtmlStringRGBA(ModConfig.ValueColor.Value); bool value = ModConfig.ShowTotals.Value; StringBuilder stringBuilder = new StringBuilder(); if (ModConfig.ShowSession.Value) { TimeSpan elapsed = SessionData.Elapsed; stringBuilder.AppendLine($"Session {(int)elapsed.TotalHours:D2}:{elapsed.Minutes:D2}:{elapsed.Seconds:D2}"); } if (ModConfig.ShowXph.Value) { string text3 = $"XP/h {SessionData.XpPerHour:N0}"; if (value) { text3 += $" ({SessionData.XpGained:N0})"; } stringBuilder.AppendLine(text3); } if (ModConfig.ShowKph.Value) { string text4 = $"KPH {SessionData.Kph:N0}"; if (value) { text4 += $" ({SessionData.KillCount:N0})"; } stringBuilder.AppendLine(text4); } if (ModConfig.ShowGoldph.Value) { string text5 = $"Gold/h {SessionData.GoldPerHour:N0}"; if (value) { text5 += $" ({SessionData.GoldGained:N0})"; } stringBuilder.AppendLine(text5); } ((TMP_Text)_label).text = stringBuilder.ToString().TrimEnd(); int num = (ModConfig.ShowSession.Value ? 1 : 0) + (ModConfig.ShowXph.Value ? 1 : 0) + (ModConfig.ShowKph.Value ? 1 : 0) + (ModConfig.ShowGoldph.Value ? 1 : 0); float num2 = ModConfig.BgPadding.Value + ModConfig.BorderSize.Value; float num3 = ModConfig.FontSize.Value * 1.4f; float num4 = (ModConfig.ShowTotals.Value ? 220f : 160f); _rootRect.sizeDelta = new Vector2(num4, (float)num * num3 + num2 * 2f); } } internal static class ModConfig { internal static ConfigEntry ResetKey { get; private set; } internal static ConfigEntry PosX { get; private set; } internal static ConfigEntry PosY { get; private set; } internal static ConfigEntry FontSize { get; private set; } internal static ConfigEntry LabelColor { get; private set; } internal static ConfigEntry ValueColor { get; private set; } internal static ConfigEntry BgColor { get; private set; } internal static ConfigEntry BgPadding { get; private set; } internal static ConfigEntry BorderColor { get; private set; } internal static ConfigEntry BorderSize { get; private set; } internal static ConfigEntry ShowSession { get; private set; } internal static ConfigEntry ShowXph { get; private set; } internal static ConfigEntry ShowKph { get; private set; } internal static ConfigEntry ShowGoldph { get; private set; } internal static ConfigEntry ShowTotals { get; private set; } internal static void Bind(ConfigFile config) { //IL_0096: Unknown result type (might be due to invalid IL or missing references) //IL_00b5: 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_0126: Unknown result type (might be due to invalid IL or missing references) ResetKey = config.Bind("General", "ResetKey", (KeyCode)286, "Key to reset session stats"); PosX = config.Bind("Display", "PosX", 20f, "Horizontal position from left edge (also updated by drag)"); PosY = config.Bind("Display", "PosY", 200f, "Vertical position from top edge (also updated by drag)"); FontSize = config.Bind("Display", "FontSize", 13f, "Font size"); LabelColor = config.Bind("Display", "LabelColor", new Color(0.67f, 0.67f, 0.67f), "Color of the row labels"); ValueColor = config.Bind("Display", "ValueColor", Color.white, "Color of the stat values"); BgColor = config.Bind("Display", "BgColor", new Color(0f, 0f, 0f, 0.6f), "Background color"); BgPadding = config.Bind("Display", "BgPadding", 6f, "Inner padding in pixels"); BorderColor = config.Bind("Display", "BorderColor", Color.clear, "Border color"); BorderSize = config.Bind("Display", "BorderSize", 0f, "Border thickness in pixels"); ShowSession = config.Bind("Display", "ShowSession", true, "Show session time"); ShowXph = config.Bind("Display", "ShowXph", true, "Show XP/hour"); ShowKph = config.Bind("Display", "ShowKph", true, "Show kills/hour"); ShowGoldph = config.Bind("Display", "ShowGoldph", true, "Show gold/hour"); ShowTotals = config.Bind("Display", "ShowTotals", false, "Show total accumulated values next to rates"); PosX.SettingChanged += delegate { HudDisplay.UpdateLayout(); }; PosY.SettingChanged += delegate { HudDisplay.UpdateLayout(); }; FontSize.SettingChanged += delegate { HudDisplay.UpdateStyle(); }; LabelColor.SettingChanged += delegate { HudDisplay.Refresh(); }; ValueColor.SettingChanged += delegate { HudDisplay.Refresh(); }; BgColor.SettingChanged += delegate { HudDisplay.UpdateStyle(); }; BgPadding.SettingChanged += delegate { HudDisplay.UpdateStyle(); }; BorderColor.SettingChanged += delegate { HudDisplay.UpdateStyle(); }; BorderSize.SettingChanged += delegate { HudDisplay.UpdateStyle(); }; ShowTotals.SettingChanged += delegate { HudDisplay.Refresh(); }; } } [BepInPlugin("Ocewen.Session_Stats", "Session Stats", "1.0.0")] public class Plugin : BaseUnityPlugin { private Harmony? _harmony; private float _refreshTimer; private int _lastGold; private bool _hudReady; private void Awake() { //IL_0011: Unknown result type (might be due to invalid IL or missing references) //IL_001b: Expected O, but got Unknown ModConfig.Bind(((BaseUnityPlugin)this).Config); _harmony = new Harmony("Ocewen.Session_Stats"); _harmony.PatchAll(); ((BaseUnityPlugin)this).Logger.LogInfo((object)"Session Stats 1.0.0 loaded."); } private void Update() { //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_006b: Unknown result type (might be due to invalid IL or missing references) Scene activeScene = SceneManager.GetActiveScene(); bool flag = ((Scene)(ref activeScene)).name == "Hidden"; if (!_hudReady && flag) { _hudReady = true; HudDisplay.Create(); SessionData.Reset(); _lastGold = GameData.PlayerInv?.Gold ?? 0; } else if (_hudReady && !flag) { _hudReady = false; HudDisplay.Destroy(); } if (Input.GetKeyDown(ModConfig.ResetKey.Value)) { SessionData.Reset(); _lastGold = GameData.PlayerInv?.Gold ?? 0; } Inventory playerInv = GameData.PlayerInv; if ((Object)(object)playerInv != (Object)null) { int gold = playerInv.Gold; int num = gold - _lastGold; if (num > 0) { SessionData.GoldGained += num; } _lastGold = gold; } _refreshTimer += Time.deltaTime; if (_refreshTimer >= 1f) { _refreshTimer = 0f; HudDisplay.Refresh(); } } private void OnDestroy() { HudDisplay.Destroy(); Harmony? harmony = _harmony; if (harmony != null) { harmony.UnpatchAll("Ocewen.Session_Stats"); } } } internal static class SessionData { internal static DateTime Start = DateTime.Now; internal static int XpGained = 0; internal static int KillCount = 0; internal static int GoldGained = 0; internal static TimeSpan Elapsed => DateTime.Now - Start; private static double Hours => Math.Max(Elapsed.TotalHours, 0.0002777777777777778); internal static int XpPerHour => (int)((double)XpGained / Hours); internal static int Kph => (int)((double)KillCount / Hours); internal static int GoldPerHour => (int)((double)GoldGained / Hours); internal static void Reset() { Start = DateTime.Now; XpGained = 0; KillCount = 0; GoldGained = 0; } } } namespace Ocewen.SessionStats.Patches { [HarmonyPatch(typeof(GameData), "AddExperience")] internal static class AddExperience_Patch { private static void Prefix(int xp) { if (xp > 0) { SessionData.XpGained += xp; } } } [HarmonyPatch(typeof(Character), "DoDeath")] internal static class DoDeath_Patch { private static void Prefix(Character __instance) { if (__instance.isNPC && __instance.Alive && Traverse.Create((object)__instance).Field("damagedByPlayerEver").Value) { SessionData.KillCount++; } } } }