Decompiled source of TootTallyTootScoreVisualizer v1.0.2

plugins/TootTallyTootScoreVisualizer.dll

Decompiled 4 months ago
using System;
using System.Collections.Generic;
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.Xml.Serialization;
using BaboonAPI.Hooks.Initializer;
using BepInEx;
using BepInEx.Configuration;
using HarmonyLib;
using Microsoft.CodeAnalysis;
using TootTallyCore;
using TootTallyCore.Utils.Helpers;
using TootTallyCore.Utils.TootTallyModules;
using TootTallySettings;
using UnityEngine;
using UnityEngine.UI;

[assembly: CompilationRelaxations(8)]
[assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)]
[assembly: Debuggable(DebuggableAttribute.DebuggingModes.Default | DebuggableAttribute.DebuggingModes.DisableOptimizations | DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints | DebuggableAttribute.DebuggingModes.EnableEditAndContinue)]
[assembly: TargetFramework(".NETFramework,Version=v4.7.2", FrameworkDisplayName = ".NET Framework 4.7.2")]
[assembly: AssemblyCompany("TootTallyTootScoreVisualizer")]
[assembly: AssemblyConfiguration("Debug")]
[assembly: AssemblyDescription("Customize the text popup score after playing a note")]
[assembly: AssemblyFileVersion("1.0.2.0")]
[assembly: AssemblyInformationalVersion("1.0.2")]
[assembly: AssemblyProduct("TootTallyTootScoreVisualizer")]
[assembly: AssemblyTitle("TootTallyTootScoreVisualizer")]
[assembly: SecurityPermission(SecurityAction.RequestMinimum, SkipVerification = true)]
[assembly: AssemblyVersion("1.0.2.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.Module, AllowMultiple = false, Inherited = false)]
	internal sealed class RefSafetyRulesAttribute : Attribute
	{
		public readonly int Version;

		public RefSafetyRulesAttribute(int P_0)
		{
			Version = P_0;
		}
	}
}
namespace TootTallyTootScoreVisualizer
{
	[BepInPlugin("TootTallyTootScoreVisualizer", "TootTallyTootScoreVisualizer", "1.0.2")]
	[BepInDependency(/*Could not decode attribute arguments.*/)]
	[BepInDependency(/*Could not decode attribute arguments.*/)]
	public class Plugin : BaseUnityPlugin, ITootTallyModule
	{
		public static class TSVPatches
		{
			public static int noteParticles_index;

			public static float noteScoreAverage;

			private static int _lastNoteEffectIndex;

			[HarmonyPatch(typeof(GameController), "Start")]
			[HarmonyPostfix]
			public static void OnLoadControllerLoadGameplayAsyncPostfix(GameController __instance)
			{
				ResolvePresets();
			}

			[HarmonyPatch(typeof(GameController), "getScoreAverage")]
			[HarmonyPrefix]
			public static void OnGameControllerGetScoreAveragePrefix(GameController __instance)
			{
				noteScoreAverage = __instance.notescoreaverage;
			}

			[HarmonyPatch(typeof(GameController), "animateOutNote")]
			[HarmonyPrefix]
			public static void OnGameControllerAnimateOutNotePrefix(GameController __instance)
			{
				_lastNoteEffectIndex = __instance.noteparticles_index;
			}

			[HarmonyPatch(typeof(GameController), "animateOutNote")]
			[HarmonyPostfix]
			public static void OnGameControllerAnimateOutNotePostfix(GameController __instance, ref noteendeffect[] ___allnoteendeffects)
			{
				//IL_0038: 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_0054: Unknown result type (might be due to invalid IL or missing references)
				//IL_005c: Unknown result type (might be due to invalid IL or missing references)
				//IL_00a5: Unknown result type (might be due to invalid IL or missing references)
				if (TSVConfig.configLoaded)
				{
					Threshold scoreThreshold = TSVConfig.GetScoreThreshold(noteScoreAverage);
					noteendeffect noteendeffect = ___allnoteendeffects[_lastNoteEffectIndex];
					Text combotext_txt_front = noteendeffect.combotext_txt_front;
					Text combotext_txt_shadow = noteendeffect.combotext_txt_shadow;
					HorizontalWrapMode horizontalOverflow = (HorizontalWrapMode)1;
					combotext_txt_shadow.horizontalOverflow = (HorizontalWrapMode)1;
					combotext_txt_front.horizontalOverflow = horizontalOverflow;
					Text combotext_txt_front2 = noteendeffect.combotext_txt_front;
					Text combotext_txt_shadow2 = noteendeffect.combotext_txt_shadow;
					VerticalWrapMode verticalOverflow = (VerticalWrapMode)1;
					combotext_txt_shadow2.verticalOverflow = (VerticalWrapMode)1;
					combotext_txt_front2.verticalOverflow = verticalOverflow;
					noteendeffect.combotext_txt_front.text = scoreThreshold.GetFormattedText(noteScoreAverage, __instance.multiplier);
					noteendeffect.combotext_txt_shadow.text = scoreThreshold.GetFormattedTextNoColor(noteScoreAverage, __instance.multiplier);
					((Graphic)noteendeffect.combotext_txt_front).color = scoreThreshold.color;
				}
			}
		}

		public struct noteendeffect
		{
			public GameObject noteeffect_obj;

			public RectTransform noteeffect_rect;

			public GameObject burst_obj;

			public Image burst_img;

			public CanvasGroup burst_canvasg;

			public ParticleSystem burst_particles;

			public GameObject drops_obj;

			public CanvasGroup drops_canvasg;

			public GameObject combotext_obj;

			public RectTransform combotext_rect;

			public Text combotext_txt_front;

			public Text combotext_txt_shadow;
		}

		public static Plugin Instance;

		public const string CONFIGS_FOLDER_NAME = "/TootScoreVisualizer/";

		private const string CONFIG_NAME = "TootScoreVisualizer.cfg";

		private const string SETTINGS_PAGE_NAME = "TootScoreVisualizer";

		public static string currentLoadedConfigName;

		private Harmony _harmony;

		public static TootTallySettingPage settingPage;

		public ConfigEntry<bool> ModuleConfigEnabled { get; set; }

		public bool IsConfigInitialized { get; set; }

		public string Name
		{
			get
			{
				return "TootScoreVisualizer";
			}
			set
			{
				Name = value;
			}
		}

		public ConfigEntry<string> TSVName { get; set; }

		public static void LogInfo(string msg)
		{
			((BaseUnityPlugin)Instance).Logger.LogInfo((object)msg);
		}

		public static void LogError(string msg)
		{
			((BaseUnityPlugin)Instance).Logger.LogError((object)msg);
		}

		private void Awake()
		{
			//IL_0029: Unknown result type (might be due to invalid IL or missing references)
			//IL_0033: Expected O, but got Unknown
			if (!((Object)(object)Instance != (Object)null))
			{
				Instance = this;
				_harmony = new Harmony(((BaseUnityPlugin)this).Info.Metadata.GUID);
				GameInitializationEvent.Register(((BaseUnityPlugin)this).Info, (Action)TryInitialize);
			}
		}

		private void TryInitialize()
		{
			if (Application.version.CompareTo("1.19A") < 0)
			{
				LogInfo("Please install Trombone Champ 1.19A version or later.");
				return;
			}
			ModuleConfigEnabled = ((BaseUnityPlugin)Plugin.Instance).Config.Bind<bool>("Modules", "TootScoreVisualizer", true, "Enables text popup customization when playing notes.");
			TootTallyModuleManager.AddModule((ITootTallyModule)(object)this);
			Plugin.Instance.AddModuleToSettingPage((ITootTallyModule)(object)this);
		}

		public void LoadModule()
		{
			//IL_0023: Unknown result type (might be due to invalid IL or missing references)
			//IL_0029: Expected O, but got Unknown
			//IL_00ba: Unknown result type (might be due to invalid IL or missing references)
			string text = Path.Combine(Paths.BepInExRootPath, "config/");
			ConfigFile val = new ConfigFile(text + "TootScoreVisualizer.cfg", true);
			TSVName = val.Bind<string>("Generic", "TSVName", "Default", "Enter the name of your config here. Do not put the .xml extension.");
			val.SettingChanged += Config_SettingChanged;
			string text2 = Path.Combine(Path.GetDirectoryName(((BaseUnityPlugin)Instance).Info.Location), "TootScoreVisualizer");
			string text3 = Path.Combine(Paths.BepInExRootPath, "TootScoreVisualizer");
			FileHelper.TryMigrateFolder(text2, text3, true);
			settingPage = TootTallySettingsManager.AddNewPage("TootScoreVisualizer", "TootScoreVisualizer", 40f, new Color(0.1f, 0.1f, 0.1f, 0.1f));
			List<string> fileNames = new List<string>();
			if (Directory.Exists(text3))
			{
				string[] files = Directory.GetFiles(text3);
				files.ToList().ForEach(delegate(string d)
				{
					fileNames.Add(Path.GetFileNameWithoutExtension(d));
				});
			}
			settingPage.AddDropdown("TSVDropdown", TSVName, fileNames.ToArray());
			ResolvePresets();
			Plugin.TryAddThunderstoreIconToPageButton(((BaseUnityPlugin)Instance).Info.Location, Name, settingPage);
			_harmony.PatchAll(typeof(TSVPatches));
			LogInfo("Module loaded!");
		}

		private void Config_SettingChanged(object sender, SettingChangedEventArgs e)
		{
			ResolvePresets();
		}

		public void UnloadModule()
		{
			_harmony.UnpatchSelf();
			settingPage.Remove();
			LogInfo("Module unloaded!");
		}

		public static void ResolvePresets()
		{
			if (currentLoadedConfigName != Instance.TSVName.Value)
			{
				LogInfo("Config file changed, loading new config");
				TSVConfig.LoadConfig(Instance.TSVName.Value);
			}
		}
	}
	[XmlRoot("tsv")]
	public class SerializableTSVConfig
	{
		public class ThresholdData
		{
			[XmlAttribute("value")]
			public float threshold;

			[XmlAttribute("textsize")]
			public int size;

			[XmlElement("text")]
			public string text;

			[XmlElement("color")]
			public string color;
		}

		[XmlAttribute("modversion")]
		public string modversion;

		[XmlAttribute("decimalprecision")]
		public int decimalprecision;

		[XmlArray("scorethresholdlist")]
		[XmlArrayItem("threshold")]
		public List<ThresholdData> scoreThreshold;

		[XmlArray("multiplierthresholdlist")]
		[XmlArrayItem("threshold")]
		public List<ThresholdData> multiplierThreshold;
	}
	public static class TSVConfig
	{
		public static List<Threshold> scoreThresholdList;

		public static bool configLoaded;

		public static string GetHardCodedDefaultConfigString => "<!--\r\n        %P = Accuracy score (0 to 100)\r\n        %m = Uses the text that matches the threshold as specified in multiplierthresholdlist\r\n        %M = In-game value of multiplier (1x to 10x)\r\n        threshold = if the value is greater than the given threshold\r\n        decimalprecision = number of digits \r\n        textsize = the size of the text (defaulted at 20)\r\n        -->\r\n        <tsv modversion = \"1.0.0\" decimalprecision=\"2\">\r\n\t        <scorethresholdlist>\r\n\t\t        <threshold value = \"88\" textsize=\"20\" >\r\n                    <text>%MX</text>\r\n\t\t\t        <color>#FFFFFFFF</color>\r\n\t\t        </threshold>\r\n\t\t\t\t<threshold value = \"79\" textsize=\"20\">\r\n\t\t\t\t\t<text>OK</text>\r\n\t\t\t\t\t<color>#FFFFFFFF</color>\r\n\t\t\t\t</threshold>\r\n\t\t\t\t<threshold value = \"70\" textsize=\"20\" >\r\n\t\t\t\t\t<text>MEH</text>\r\n\t\t\t\t\t<color>#FFFFFFFF</color>\r\n\t\t\t\t</threshold>\r\n\t\t\t\t<threshold value = \"0\" textsize=\"20\">\r\n\t\t\t\t\t<text>x</text>\r\n\t\t\t\t\t<color>#FF0000FF</color>\r\n\t\t\t\t</threshold>\r\n\t        </scorethresholdlist>\r\n\t        <multiplierthresholdlist>\r\n\t\t        <threshold value = \"0\">\r\n                    <text></text>\r\n                    <color>#FFFFFFFF</color>\r\n\t\t        </threshold>\r\n            </multiplierthresholdlist>\r\n        </tsv>";

		public static void LoadConfig(string configName)
		{
			//IL_01ab: Unknown result type (might be due to invalid IL or missing references)
			configLoaded = false;
			string text = configName + ".xml";
			string text2 = Path.Combine(Paths.BepInExRootPath + "/TootScoreVisualizer/");
			if (!Directory.Exists(text2))
			{
				Directory.CreateDirectory(text2);
			}
			if (!File.Exists(text2 + text))
			{
				Plugin.LogError("TSV config " + text + " not found, using default config");
				text = "Default.xml";
				Plugin.Instance.TSVName.Value = "Default";
				if (!File.Exists(text2 + text))
				{
					Plugin.LogError("Couldn't find " + text + ". Generating new Default config");
					File.WriteAllText(text2 + text, GetHardCodedDefaultConfigString);
				}
			}
			try
			{
				XmlSerializer xmlSerializer = new XmlSerializer(typeof(SerializableTSVConfig));
				SerializableTSVConfig serializableTSVConfig = (SerializableTSVConfig)xmlSerializer.Deserialize(File.OpenRead(text2 + text));
				List<MultiplierThreshold> list = new List<MultiplierThreshold>();
				foreach (SerializableTSVConfig.ThresholdData item in serializableTSVConfig.multiplierThreshold)
				{
					list.Add(new MultiplierThreshold(item.threshold, item.text, item.size, item.color));
				}
				scoreThresholdList = new List<Threshold>();
				Color color = default(Color);
				foreach (SerializableTSVConfig.ThresholdData item2 in serializableTSVConfig.scoreThreshold)
				{
					ColorUtility.TryParseHtmlString(item2.color, ref color);
					scoreThresholdList.Add(new Threshold(item2.threshold, item2.text, item2.size, color, serializableTSVConfig.decimalprecision, list));
				}
				scoreThresholdList.Sort((Threshold x, Threshold y) => (x.value > y.value) ? 1 : 0);
				Plugin.currentLoadedConfigName = configName;
				Plugin.LogInfo("TSV config " + configName + " has been loaded");
				configLoaded = true;
			}
			catch (Exception ex)
			{
				Plugin.LogError(ex.Message);
			}
		}

		public static Threshold GetScoreThreshold(float value)
		{
			for (int i = 0; i < scoreThresholdList.Count; i++)
			{
				if (value > scoreThresholdList[i].value)
				{
					return scoreThresholdList[i];
				}
			}
			return scoreThresholdList.Last();
		}
	}
	public class Threshold
	{
		public float value;

		public string text;

		public int size;

		public Color color;

		public int decimalprecision;

		public List<MultiplierThreshold> multiplierThresholdList;

		public Threshold(float value, string text, int size, Color color, int decimalprecision, List<MultiplierThreshold> multiplierThresholdList)
		{
			//IL_001e: 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)
			this.value = value;
			this.text = text;
			this.size = size;
			this.color = color;
			this.decimalprecision = decimalprecision;
			this.multiplierThresholdList = multiplierThresholdList;
			if (this.size == 0)
			{
				this.size = 20;
			}
		}

		public string GetFormattedText(float notescoreaverage, int multiplier)
		{
			string text = this.text.Replace("%P", $"<size={size}>" + notescoreaverage.ToString($"F{decimalprecision}") + "</size>");
			text = text.Replace("%m", GetMultiplierThreshold(multiplier).GetFormattedMultiplierText(multiplier));
			text = text.Replace("%M", $"<size={size}>" + multiplier + "</size>");
			return text.Replace("%n", "\n");
		}

		public string GetFormattedTextNoColor(float notescoreaverage, int multiplier)
		{
			string text = this.text.Replace("%P", $"<size={size}>" + notescoreaverage.ToString($"F{decimalprecision}") + "</size>");
			text = text.Replace("%m", GetMultiplierThreshold(multiplier).GetFormattedMultiplierTextNoColor(multiplier));
			text = text.Replace("%M", $"<size={size}>" + multiplier + "</size>");
			return text.Replace("%n", "\n");
		}

		public MultiplierThreshold GetMultiplierThreshold(float value)
		{
			for (int i = 0; i < multiplierThresholdList.Count; i++)
			{
				if (value >= multiplierThresholdList[i].value)
				{
					return multiplierThresholdList[i];
				}
			}
			return multiplierThresholdList.Last();
		}
	}
	public class MultiplierThreshold
	{
		public float value;

		public string text;

		public int size;

		public string color;

		public MultiplierThreshold(float value, string text, int size, string color)
		{
			this.value = value;
			this.text = text;
			this.size = size;
			this.color = color;
			if (this.size == 0)
			{
				this.size = 20;
			}
		}

		public string GetFormattedMultiplierText(int multiplier)
		{
			return $"<size={size}><color={color}>" + text.Replace("%M", multiplier.ToString()) + "</color></size>";
		}

		public string GetFormattedMultiplierTextNoColor(int multiplier)
		{
			return $"<size={size}>" + text.Replace("%M", multiplier.ToString()) + "</size>";
		}
	}
	public static class PluginInfo
	{
		public const string PLUGIN_GUID = "TootTallyTootScoreVisualizer";

		public const string PLUGIN_NAME = "TootTallyTootScoreVisualizer";

		public const string PLUGIN_VERSION = "1.0.2";
	}
}