using System;
using System.Diagnostics;
using System.IO;
using System.Reflection;
using System.Runtime.CompilerServices;
using System.Runtime.Versioning;
using System.Security;
using System.Security.Permissions;
using BaboonAPI.Hooks.Initializer;
using BepInEx;
using BepInEx.Configuration;
using HarmonyLib;
using Microsoft.CodeAnalysis;
using TMPro;
using TootTallyCore;
using TootTallyCore.Utils.TootTallyGlobals;
using TootTallyCore.Utils.TootTallyModules;
using TootTallySettings;
using UnityEngine;
using UnityEngine.Events;
[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("TootTallyAutoToot")]
[assembly: AssemblyConfiguration("Debug")]
[assembly: AssemblyDescription("AutoToot module for TootTallyCore")]
[assembly: AssemblyFileVersion("1.0.0.0")]
[assembly: AssemblyInformationalVersion("1.0.0")]
[assembly: AssemblyProduct("TootTallyAutoToot")]
[assembly: AssemblyTitle("TootTallyAutoToot")]
[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.Module, AllowMultiple = false, Inherited = false)]
internal sealed class RefSafetyRulesAttribute : Attribute
{
public readonly int Version;
public RefSafetyRulesAttribute(int P_0)
{
Version = P_0;
}
}
}
namespace TootTallyAutoToot
{
public class AutoTootController : MonoBehaviour
{
private GameController _gameController;
private GameObject _pointer;
private RectTransform _pointerRect;
private Vector2 _pointerPosition;
private float _lastTimeSample;
private float _trackTime;
private float _lastTrackTime;
private float _estimatedTrackTime;
private float _lastNoteStartTime;
private float _lastNoteEndTime;
private float _currentNoteStartTime;
private float _currentNoteEndTime;
private float _lastNoteStartY;
private float _lastNoteEndY;
private float _currentNoteStartY;
private float _currentNoteEndY;
private bool _isSlider;
private int _noteIndex;
private float _timingAdjustValue;
private bool _releasedBetweenNotes;
public bool isEnabled;
public bool isTooting;
private static Func<float, float> _currentEasing;
public void Init(GameController gameController)
{
//IL_013f: Unknown result type (might be due to invalid IL or missing references)
//IL_0144: Unknown result type (might be due to invalid IL or missing references)
_gameController = gameController;
_pointer = _gameController.pointer;
_pointerRect = _gameController.pointerrect;
isEnabled = false;
isTooting = false;
_isSlider = false;
_noteIndex = -1;
if (_gameController.leveldata.Count > 0)
{
_currentNoteStartTime = B2s(_gameController.leveldata[0][0], _gameController.tempo);
_currentNoteEndTime = _currentNoteStartTime + B2s(_gameController.leveldata[0][1], _gameController.tempo);
_currentNoteStartY = _gameController.leveldata[0][2];
_currentNoteEndY = _gameController.leveldata[0][4];
}
_lastNoteStartY = 0f;
_lastNoteEndY = 0f;
_lastNoteEndTime = -1f;
_lastNoteStartTime = -1f;
_lastTrackTime = (_trackTime = 0f);
_lastTimeSample = 0f;
_pointerPosition = _pointerRect.anchoredPosition;
_currentEasing = EasingHelper.GetCurrentEasing(Plugin.Instance.EasingType.Value);
_timingAdjustValue = Plugin.Instance.TimingAdjust.Value / 1000f * TootTallyGlobalVariables.gameSpeedMultiplier;
}
public void Update()
{
//IL_001f: Unknown result type (might be due to invalid IL or missing references)
//IL_00e0: Unknown result type (might be due to invalid IL or missing references)
if (_gameController.freeplay)
{
return;
}
if (Input.GetKeyDown(Plugin.Instance.ToggleKey.Value))
{
ToggleEnable();
}
if (!_gameController.paused && !_gameController.quitting && _gameController.musictrack.isPlaying)
{
UpdateTrackData();
}
if (isEnabled)
{
TootTallyGlobalVariables.usedAutotoot = true;
if (Plugin.Instance.PerfectPlay.Value)
{
_gameController.breathcounter = 0f;
}
isTooting = ShouldToot();
if (!isTooting)
{
_releasedBetweenNotes = true;
}
_pointerPosition.y = GetPositionY();
_pointerRect.anchoredPosition = _pointerPosition;
}
}
private void UpdateTrackData()
{
_trackTime += Time.deltaTime * TootTallyGlobalVariables.gameSpeedMultiplier;
if (_lastTimeSample != (float)_gameController.musictrack.timeSamples)
{
_lastTrackTime = _gameController.musictrack.time - _gameController.noteoffset - _gameController.latency_offset;
_lastTimeSample = _gameController.musictrack.timeSamples;
}
_trackTime += (_lastTrackTime - _trackTime) / 60f;
if (_trackTime >= _currentNoteEndTime)
{
_noteIndex++;
if (_noteIndex + 1 < _gameController.leveldata.Count)
{
_lastNoteStartTime = _currentNoteStartTime;
_lastNoteEndTime = _currentNoteEndTime;
_lastNoteStartY = _currentNoteStartY;
_lastNoteEndY = _currentNoteEndY;
_isSlider = Mathf.Abs(_gameController.leveldata[_noteIndex + 1][0] - (_gameController.leveldata[_noteIndex][0] + _gameController.leveldata[_noteIndex][1])) < 0.05f;
_currentNoteStartTime = B2s(_gameController.leveldata[_noteIndex + 1][0], _gameController.tempo);
_currentNoteEndTime = _currentNoteStartTime + B2s(_gameController.leveldata[_noteIndex + 1][1], _gameController.tempo);
_currentNoteStartY = _gameController.leveldata[_noteIndex + 1][2];
_currentNoteEndY = _gameController.leveldata[_noteIndex + 1][4];
_releasedBetweenNotes = !isTooting;
}
else
{
_currentNoteStartTime = float.MaxValue;
}
}
}
public void ToggleEnable()
{
//IL_0034: Unknown result type (might be due to invalid IL or missing references)
isEnabled = !isEnabled;
_gameController.controllermode = isEnabled;
_lastNoteEndTime = _trackTime;
_lastNoteEndY = _pointerRect.anchoredPosition.y;
Plugin.LogInfo("AutoToot " + (isEnabled ? "Enabled" : "Disabled") + ".");
}
private bool ShouldToot()
{
return (_trackTime >= _currentNoteStartTime - (Plugin.Instance.SyncTootWithSong.Value ? _gameController.latency_offset : _timingAdjustValue) && _releasedBetweenNotes) || _trackTime <= _lastNoteEndTime + _timingAdjustValue || _isSlider;
}
private float GetPositionY()
{
float num;
if (_trackTime >= _currentNoteStartTime && _trackTime <= _currentNoteEndTime + _timingAdjustValue)
{
num = Mathf.Clamp(1f - (_currentNoteEndTime - (_trackTime + 0.005555f * TootTallyGlobalVariables.gameSpeedMultiplier)) / (_currentNoteEndTime - _currentNoteStartTime), 0f, 1f);
return _currentNoteStartY + _gameController.easeInOutVal(Mathf.Abs(num), 0f, _currentNoteEndY - _currentNoteStartY, 1f);
}
float num2 = _currentNoteStartTime - _timingAdjustValue;
float num3 = _lastNoteEndTime + _timingAdjustValue;
num = Mathf.Clamp(1f - (num2 - _trackTime) / (num2 - num3), 0f, 1f);
return Mathf.Lerp(_lastNoteEndY, _currentNoteStartY, _currentEasing(num));
}
public static float B2s(float time, float bpm)
{
return time / bpm * 60f;
}
}
public static class AutoTootManager
{
private static AutoTootController _controller;
[HarmonyPatch(typeof(GameController), "Start")]
[HarmonyPostfix]
public static void OnGameControllerStartSetEasingFunction(GameController __instance)
{
_controller = __instance.pointer.AddComponent<AutoTootController>();
_controller.Init(__instance);
TootTallyGlobalVariables.usedAutotoot = false;
}
[HarmonyPatch(typeof(GameController), "getScoreAverage")]
[HarmonyPrefix]
public static void OnGameControllerGetScoreAverageSetPerfectPlay(GameController __instance)
{
if (Plugin.Instance.PerfectPlay.Value && _controller.isEnabled)
{
__instance.notescoreaverage = 100f;
__instance.released_button_between_notes = true;
}
}
[HarmonyPatch(typeof(GameController), "doScoreText")]
[HarmonyPrefix]
public static void OnGameControllerDoScoreTextSetPerfectPlay(ref int whichtext, ref float notescore)
{
if (Plugin.Instance.PerfectPlay.Value && _controller.isEnabled)
{
whichtext = 4;
notescore = 100f;
}
}
[HarmonyPatch(typeof(GameController), "isNoteButtonPressed")]
[HarmonyPostfix]
public static void OnIsNoteButtonPressedOverwriteValue(GameController __instance, ref bool __result)
{
if (_controller.isEnabled && !__instance.freeplay && !__instance.paused && !__instance.quitting)
{
__result = _controller.isTooting;
}
}
}
public static class EasingHelper
{
public enum EasingType
{
Linear,
InQuad,
OutQuad,
InOutQuad,
InCubic,
OutCubic,
InOutCubic,
InQuart,
OutQuart,
InOutQuart,
InQuint,
OutQuint,
InOutQuint,
InSine,
OutSine,
InOutSine,
InExpo,
OutExpo,
InOutExpo,
InCirc,
OutCirc,
InOutCirc,
InElastic,
OutElastic,
InOutElastic,
InBack,
OutBack,
InOutBack,
InBounce,
OutBounce,
InOutBounce
}
public static Func<float, float> GetCurrentEasing(EasingType easing)
{
if (1 == 0)
{
}
Func<float, float> result = easing switch
{
EasingType.Linear => Linear,
EasingType.InQuad => InQuad,
EasingType.OutQuad => OutQuad,
EasingType.InOutQuad => InOutQuad,
EasingType.InCubic => InCubic,
EasingType.OutCubic => OutCubic,
EasingType.InOutCubic => InOutCubic,
EasingType.InQuart => InQuart,
EasingType.OutQuart => OutQuart,
EasingType.InOutQuart => InOutQuart,
EasingType.InQuint => InQuint,
EasingType.OutQuint => OutQuint,
EasingType.InOutQuint => InOutQuint,
EasingType.InSine => InSine,
EasingType.OutSine => OutSine,
EasingType.InOutSine => InOutSine,
EasingType.InExpo => InExpo,
EasingType.OutExpo => OutExpo,
EasingType.InOutExpo => InOutExpo,
EasingType.InCirc => InCirc,
EasingType.OutCirc => OutCirc,
EasingType.InOutCirc => InOutCirc,
EasingType.InElastic => InElastic,
EasingType.OutElastic => OutElastic,
EasingType.InOutElastic => InOutElastic,
EasingType.InBack => InBack,
EasingType.OutBack => OutBack,
EasingType.InOutBack => InOutBack,
EasingType.InBounce => InBounce,
EasingType.OutBounce => OutBounce,
_ => InOutBounce,
};
if (1 == 0)
{
}
return result;
}
public static float Linear(float t)
{
return t;
}
public static float InQuad(float t)
{
return t * t;
}
public static float OutQuad(float t)
{
return 1f - InQuad(1f - t);
}
public static float InOutQuad(float t)
{
if ((double)t < 0.5)
{
return InQuad(t * 2f) / 2f;
}
return 1f - InQuad((1f - t) * 2f) / 2f;
}
public static float InCubic(float t)
{
return t * t * t;
}
public static float OutCubic(float t)
{
return 1f - InCubic(1f - t);
}
public static float InOutCubic(float t)
{
if ((double)t < 0.5)
{
return InCubic(t * 2f) / 2f;
}
return 1f - InCubic((1f - t) * 2f) / 2f;
}
public static float InQuart(float t)
{
return t * t * t * t;
}
public static float OutQuart(float t)
{
return 1f - InQuart(1f - t);
}
public static float InOutQuart(float t)
{
if ((double)t < 0.5)
{
return InQuart(t * 2f) / 2f;
}
return 1f - InQuart((1f - t) * 2f) / 2f;
}
public static float InQuint(float t)
{
return t * t * t * t * t;
}
public static float OutQuint(float t)
{
return 1f - InQuint(1f - t);
}
public static float InOutQuint(float t)
{
if ((double)t < 0.5)
{
return InQuint(t * 2f) / 2f;
}
return 1f - InQuint((1f - t) * 2f) / 2f;
}
public static float InSine(float t)
{
return (float)(0.0 - Math.Cos((double)t * Math.PI / 2.0));
}
public static float OutSine(float t)
{
return (float)Math.Sin((double)t * Math.PI / 2.0);
}
public static float InOutSine(float t)
{
return (float)(Math.Cos((double)t * Math.PI) - 1.0) / -2f;
}
public static float InExpo(float t)
{
return (float)Math.Pow(2.0, 10f * (t - 1f));
}
public static float OutExpo(float t)
{
return 1f - InExpo(1f - t);
}
public static float InOutExpo(float t)
{
if ((double)t < 0.5)
{
return InExpo(t * 2f) / 2f;
}
return 1f - InExpo((1f - t) * 2f) / 2f;
}
public static float InCirc(float t)
{
return 0f - ((float)Math.Sqrt(1f - t * t) - 1f);
}
public static float OutCirc(float t)
{
return 1f - InCirc(1f - t);
}
public static float InOutCirc(float t)
{
if ((double)t < 0.5)
{
return InCirc(t * 2f) / 2f;
}
return 1f - InCirc((1f - t) * 2f) / 2f;
}
public static float InElastic(float t)
{
return 1f - OutElastic(1f - t);
}
public static float OutElastic(float t)
{
float num = 0.3f;
return (float)Math.Pow(2.0, -10f * t) * (float)Math.Sin((double)(t - num / 4f) * (Math.PI * 2.0) / (double)num) + 1f;
}
public static float InOutElastic(float t)
{
if ((double)t < 0.5)
{
return InElastic(t * 2f) / 2f;
}
return 1f - InElastic((1f - t) * 2f) / 2f;
}
public static float InBack(float t)
{
float num = 1.70158f;
return t * t * ((num + 1f) * t - num);
}
public static float OutBack(float t)
{
return 1f - InBack(1f - t);
}
public static float InOutBack(float t)
{
if ((double)t < 0.5)
{
return InBack(t * 2f) / 2f;
}
return 1f - InBack((1f - t) * 2f) / 2f;
}
public static float InBounce(float t)
{
return 1f - OutBounce(1f - t);
}
public static float OutBounce(float t)
{
float num = 2.75f;
float num2 = 7.5625f;
if (t < 1f / num)
{
return num2 * t * t;
}
if (t < 2f / num)
{
t -= 1.5f / num;
return num2 * t * t + 0.75f;
}
if ((double)t < 2.5 / (double)num)
{
t -= 2.25f / num;
return num2 * t * t + 0.9375f;
}
t -= 2.625f / num;
return num2 * t * t + 63f / 64f;
}
public static float InOutBounce(float t)
{
if ((double)t < 0.5)
{
return InBounce(t * 2f) / 2f;
}
return 1f - InBounce((1f - t) * 2f) / 2f;
}
}
[BepInPlugin("TootTallyAutoToot", "TootTallyAutoToot", "1.0.0")]
[BepInDependency(/*Could not decode attribute arguments.*/)]
[BepInDependency(/*Could not decode attribute arguments.*/)]
[BepInIncompatibility("AutoToot")]
public class Plugin : BaseUnityPlugin, ITootTallyModule
{
public static Plugin Instance;
private const string CONFIG_NAME = "TTAutoToot.cfg";
private Harmony _harmony;
public static TootTallySettingPage settingPage;
public ConfigEntry<bool> ModuleConfigEnabled { get; set; }
public bool IsConfigInitialized { get; set; }
public string Name
{
get
{
return "TootTallyAutoToot";
}
set
{
Name = value;
}
}
public ConfigEntry<KeyCode> ToggleKey { get; set; }
public ConfigEntry<EasingHelper.EasingType> EasingType { get; set; }
public ConfigEntry<float> TimingAdjust { get; set; }
public ConfigEntry<bool> SyncTootWithSong { get; set; }
public ConfigEntry<bool> PerfectPlay { 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()
{
ModuleConfigEnabled = ((BaseUnityPlugin)Plugin.Instance).Config.Bind<bool>("Module", "TTAutoToot", true, "Bot that automatically plays the song for you.");
TootTallyModuleManager.AddModule((ITootTallyModule)(object)this);
Plugin.Instance.AddModuleToSettingPage((ITootTallyModule)(object)this);
}
public void LoadModule()
{
//IL_001d: Unknown result type (might be due to invalid IL or missing references)
//IL_0022: Unknown result type (might be due to invalid IL or missing references)
//IL_002b: Expected O, but got Unknown
//IL_00e7: Unknown result type (might be due to invalid IL or missing references)
string text = Path.Combine(Paths.BepInExRootPath, "config/");
ConfigFile val = new ConfigFile(text + "TTAutoToot.cfg", true)
{
SaveOnConfigSet = true
};
ToggleKey = val.Bind<KeyCode>("General", "ToggleKey", (KeyCode)282, "Enable / Disable AutoToot.");
EasingType = val.Bind<EasingHelper.EasingType>("General", "EasingType", EasingHelper.EasingType.InOutQuad, "Easing function for transitions.\nRecommended to use EaseOut only smoothing functions for better results.");
TimingAdjust = val.Bind<float>("General", "TimingAdjust", 15f, "How early will it snap to notes and how late will it wait before moving.\n Defaulted at 5ms.");
SyncTootWithSong = val.Bind<bool>("General", "SyncTootWithSong", false, "Sync toot with the song instead of notes.\nIf trombone WAPS too much, lower Timing Adjust value.");
PerfectPlay = val.Bind<bool>("General", "PerfectPlay", false, "Forces perfect score on every notes.");
settingPage = TootTallySettingsManager.AddNewPage("TTAutoToot", "TTAutoToot", 40f, new Color(0f, 0f, 0f, 0f));
settingPage.AddLabel("Toggle Key", (FontStyles)0, (TextAlignmentOptions)4097);
settingPage.AddDropdown("Toggle Key", (ConfigEntryBase)(object)ToggleKey);
settingPage.AddLabel("Easing Type", (FontStyles)0, (TextAlignmentOptions)4097);
settingPage.AddDropdown("Easing Type", (ConfigEntryBase)(object)EasingType);
settingPage.AddSlider("Timing Adjust", 1f, 100f, TimingAdjust, true);
settingPage.AddToggle("Sync toot with song", SyncTootWithSong, (UnityAction<bool>)null);
settingPage.AddToggle("Perfect Play", PerfectPlay, (UnityAction<bool>)null);
_harmony.PatchAll(typeof(AutoTootManager));
LogInfo("Module loaded!");
}
public void UnloadModule()
{
_harmony.UnpatchSelf();
settingPage.Remove();
LogInfo("Module unloaded!");
}
}
public static class PluginInfo
{
public const string PLUGIN_GUID = "TootTallyAutoToot";
public const string PLUGIN_NAME = "TootTallyAutoToot";
public const string PLUGIN_VERSION = "1.0.0";
}
}