Decompiled source of SkipShop v1.0.0

SkipShop.dll

Decompiled a day ago
using System;
using System.Collections;
using System.Collections.Generic;
using System.Diagnostics;
using System.Reflection;
using System.Runtime.CompilerServices;
using System.Runtime.Versioning;
using System.Security;
using System.Security.Permissions;
using BepInEx;
using BepInEx.Configuration;
using BepInEx.Logging;
using HarmonyLib;
using Microsoft.CodeAnalysis;
using Photon.Pun;
using UnityEngine;

[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: IgnoresAccessChecksTo("")]
[assembly: AssemblyCompany("zabu")]
[assembly: AssemblyConfiguration("Debug")]
[assembly: AssemblyFileVersion("1.0.0.0")]
[assembly: AssemblyInformationalVersion("1.0.0")]
[assembly: AssemblyProduct("zabumod")]
[assembly: AssemblyTitle("zabumod")]
[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.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]
	[Microsoft.CodeAnalysis.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]
	[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 REPOJP.SkipShop
{
	[BepInPlugin("REPOJP.SkipShop", "SkipShop", "1.0.0")]
	public sealed class SkipShopPlugin : BaseUnityPlugin
	{
		[HarmonyPatch(typeof(RunManager), "ChangeLevel")]
		private static class RunManager_ChangeLevel_Patch
		{
			private static void Prefix(RunManager __instance, bool _completedLevel, bool _levelFailed, ChangeLevelType _changeLevelType, ref bool __state)
			{
				//IL_0036: Unknown result type (might be due to invalid IL or missing references)
				//IL_0038: Invalid comparison between Unknown and I4
				__state = false;
				try
				{
					if (CfgEnableMod.Value && _completedLevel && !_levelFailed && (int)_changeLevelType <= 0 && !((Object)(object)__instance.levelCurrent == (Object)(object)__instance.levelLobby) && !((Object)(object)__instance.levelCurrent == (Object)(object)__instance.levelShop) && !((Object)(object)__instance.levelCurrent == (Object)(object)__instance.levelArena) && !((Object)(object)__instance.levelCurrent == (Object)(object)__instance.levelMainMenu) && !((Object)(object)__instance.levelCurrent == (Object)(object)__instance.levelLobbyMenu) && !((Object)(object)__instance.levelCurrent == (Object)(object)__instance.levelTutorial) && !((Object)(object)__instance.levelCurrent == (Object)(object)__instance.levelRecording) && !((Object)(object)__instance.levelCurrent == (Object)(object)__instance.levelSplashScreen))
					{
						__state = true;
					}
				}
				catch (Exception ex)
				{
					Log.LogError((object)"Failed in ChangeLevel Prefix");
					Log.LogError((object)ex);
				}
			}

			private static void Postfix(RunManager __instance, bool _completedLevel, bool _levelFailed, ChangeLevelType _changeLevelType, bool __state)
			{
				try
				{
					if (!CfgEnableMod.Value)
					{
						PendingSkipShop = false;
					}
					else if (__state && (Object)(object)__instance.levelCurrent == (Object)(object)__instance.levelShop)
					{
						PendingSkipShop = true;
						Log.LogInfo((object)"Detected normal level clear -> schedule skip after shop fully loads");
					}
				}
				catch (Exception ex)
				{
					Log.LogError((object)"Failed in ChangeLevel Postfix");
					Log.LogError((object)ex);
				}
			}
		}

		[HarmonyPatch(typeof(RunManagerPUN), "Start")]
		private static class RunManagerPUN_Start_Patch
		{
			private static void Postfix()
			{
				try
				{
					if (CfgEnableMod.Value && PendingSkipShop && !((Object)(object)Instance == (Object)null) && Object.op_Implicit((Object)(object)RunManager.instance) && SemiFunc.RunIsShop() && (!GameManager.Multiplayer() || PhotonNetwork.IsMasterClient))
					{
						Instance.StartSkipShopCoroutine();
					}
				}
				catch (Exception ex)
				{
					Log.LogError((object)"Failed in RunManagerPUN.Start Postfix");
					Log.LogError((object)ex);
				}
			}
		}

		[HarmonyPatch(typeof(RunManager), "UpdateLevel")]
		private static class RunManager_UpdateLevel_Patch
		{
			private static void Postfix(string _levelName)
			{
				try
				{
					if (CfgEnableMod.Value && PendingSkipShop && (!GameManager.Multiplayer() || PhotonNetwork.IsMasterClient) && Object.op_Implicit((Object)(object)RunManager.instance) && !(_levelName != ((Object)RunManager.instance.levelShop).name) && !((Object)(object)Instance == (Object)null))
					{
						Instance.StartSkipShopCoroutine();
					}
				}
				catch (Exception ex)
				{
					Log.LogError((object)"Failed in UpdateLevel Postfix");
					Log.LogError((object)ex);
				}
			}
		}

		[CompilerGenerated]
		private sealed class <CoSkipShopToLobby>d__14 : IEnumerator<object>, IEnumerator, IDisposable
		{
			private int <>1__state;

			private object <>2__current;

			public SkipShopPlugin <>4__this;

			private float <elapsed>5__1;

			private bool <ready>5__2;

			private float <extraWait>5__3;

			private float <extraElapsed>5__4;

			object IEnumerator<object>.Current
			{
				[DebuggerHidden]
				get
				{
					return <>2__current;
				}
			}

			object IEnumerator.Current
			{
				[DebuggerHidden]
				get
				{
					return <>2__current;
				}
			}

			[DebuggerHidden]
			public <CoSkipShopToLobby>d__14(int <>1__state)
			{
				this.<>1__state = <>1__state;
			}

			[DebuggerHidden]
			void IDisposable.Dispose()
			{
				<>1__state = -2;
			}

			private bool MoveNext()
			{
				switch (<>1__state)
				{
				default:
					return false;
				case 0:
					<>1__state = -1;
					SkipCoroutineRunning = true;
					<>2__current = null;
					<>1__state = 1;
					return true;
				case 1:
					<>1__state = -1;
					<>2__current = null;
					<>1__state = 2;
					return true;
				case 2:
					<>1__state = -1;
					if (GameManager.Multiplayer() && !PhotonNetwork.IsMasterClient)
					{
						SkipCoroutineRunning = false;
						return false;
					}
					<elapsed>5__1 = 0f;
					<ready>5__2 = false;
					goto IL_00fd;
				case 3:
					<>1__state = -1;
					goto IL_00fd;
				case 4:
					{
						<>1__state = -1;
						break;
					}
					IL_00fd:
					if (<elapsed>5__1 < 10f)
					{
						if (!CanContinueWaitingInShop())
						{
							PendingSkipShop = false;
							SkipCoroutineRunning = false;
							return false;
						}
						if (!IsShopFullyReady())
						{
							<elapsed>5__1 += Time.unscaledDeltaTime;
							<>2__current = null;
							<>1__state = 3;
							return true;
						}
						<ready>5__2 = true;
					}
					if (!<ready>5__2)
					{
						Log.LogWarning((object)"Shop ready wait timed out. Proceeding with skip anyway.");
					}
					else
					{
						Log.LogInfo((object)"Shop fully ready detected. Waiting extra delay before moving to truck phase.");
					}
					<extraWait>5__3 = Mathf.Max(0f, 0f);
					<extraElapsed>5__4 = 0f;
					break;
				}
				if (<extraElapsed>5__4 < <extraWait>5__3)
				{
					if (!CanContinueWaitingInShop())
					{
						PendingSkipShop = false;
						SkipCoroutineRunning = false;
						return false;
					}
					<extraElapsed>5__4 += Time.unscaledDeltaTime;
					<>2__current = null;
					<>1__state = 4;
					return true;
				}
				TrySkipShopToLobby();
				SkipCoroutineRunning = false;
				return false;
			}

			bool IEnumerator.MoveNext()
			{
				//ILSpy generated this explicit interface implementation from .override directive in MoveNext
				return this.MoveNext();
			}

			[DebuggerHidden]
			void IEnumerator.Reset()
			{
				throw new NotSupportedException();
			}
		}

		public const string PluginGuid = "REPOJP.SkipShop";

		public const string PluginName = "SkipShop";

		public const string PluginVersion = "1.0.0";

		private const float ExtraWaitSecondsAfterShopReady = 0f;

		private const float MaxWaitSecondsForShopReady = 10f;

		internal static SkipShopPlugin Instance;

		internal static ManualLogSource Log;

		private Harmony harmony;

		internal static ConfigEntry<bool> CfgEnableMod;

		internal static bool PendingSkipShop;

		internal static bool SkipCoroutineRunning;

		private void Awake()
		{
			//IL_0071: Unknown result type (might be due to invalid IL or missing references)
			//IL_007b: Expected O, but got Unknown
			Instance = this;
			Log = ((BaseUnityPlugin)this).Logger;
			((BaseUnityPlugin)this).Logger.LogInfo((object)"\r\n████████████████████████████████████████████████████\r\n ▄▄▄▄▄▄▄                   ▄▄▄▄▄▄▄ ▄▄               \r\n█████▀▀▀ ▄▄     ▀▀        █████▀▀▀ ██               \r\n ▀████▄  ██ ▄█▀ ██  ████▄  ▀████▄  ████▄ ▄███▄ ████▄\r\n   ▀████ ████   ██  ██ ██    ▀████ ██ ██ ██ ██ ██ ██\r\n███████▀ ██ ▀█▄ ██▄ ████▀ ███████▀ ██ ██ ▀███▀ ████▀\r\n                    ██                         ██   \r\n                    ▀▀                         ▀▀   \r\n████████████████████████████████████████████████████\r\n");
			try
			{
				((Component)this).transform.parent = null;
				((Object)((Component)this).gameObject).hideFlags = (HideFlags)61;
				Object.DontDestroyOnLoad((Object)(object)((Component)this).gameObject);
				CfgEnableMod = ((BaseUnityPlugin)this).Config.Bind<bool>("General", "EnableMod", true, "Enable or disable this mod.このMODの有効無効");
				harmony = new Harmony("REPOJP.SkipShop");
				harmony.PatchAll();
				((BaseUnityPlugin)this).Logger.LogInfo((object)"SkipShop loaded");
			}
			catch (Exception ex)
			{
				((BaseUnityPlugin)this).Logger.LogError((object)"Failed to initialize SkipShop");
				((BaseUnityPlugin)this).Logger.LogError((object)ex);
			}
		}

		private void OnDestroy()
		{
			try
			{
				if (harmony != null)
				{
					harmony.UnpatchSelf();
				}
			}
			catch (Exception ex)
			{
				((BaseUnityPlugin)this).Logger.LogError((object)"Failed to unpatch SkipShop");
				((BaseUnityPlugin)this).Logger.LogError((object)ex);
			}
		}

		internal void StartSkipShopCoroutine()
		{
			if (!SkipCoroutineRunning)
			{
				((MonoBehaviour)this).StartCoroutine(CoSkipShopToLobby());
			}
		}

		[IteratorStateMachine(typeof(<CoSkipShopToLobby>d__14))]
		private IEnumerator CoSkipShopToLobby()
		{
			//yield-return decompiler failed: Unexpected instruction in Iterator.Dispose()
			return new <CoSkipShopToLobby>d__14(0)
			{
				<>4__this = this
			};
		}

		private static bool CanContinueWaitingInShop()
		{
			if (!CfgEnableMod.Value)
			{
				return false;
			}
			if (!Object.op_Implicit((Object)(object)RunManager.instance))
			{
				return false;
			}
			if (!SemiFunc.RunIsShop())
			{
				return false;
			}
			if (RunManager.instance.restarting)
			{
				return false;
			}
			return true;
		}

		private static bool IsShopFullyReady()
		{
			//IL_005e: Unknown result type (might be due to invalid IL or missing references)
			//IL_0064: Invalid comparison between Unknown and I4
			bool flag = (Object)(object)LevelGenerator.Instance != (Object)null;
			bool flag2 = flag && LevelGenerator.Instance.Generated;
			bool flag3 = (Object)(object)ShopManager.instance != (Object)null;
			bool flag4 = (Object)(object)LoadingUI.instance != (Object)null;
			bool flag5 = flag4 && LoadingUI.instance.levelAnimationCompleted;
			bool flag6 = (Object)(object)GameDirector.instance != (Object)null;
			bool flag7 = flag6 && (int)GameDirector.instance.currentState == 2;
			return flag && flag2 && flag3 && flag4 && flag5 && flag6 && flag7;
		}

		private static void TrySkipShopToLobby()
		{
			try
			{
				if (!CfgEnableMod.Value)
				{
					PendingSkipShop = false;
					return;
				}
				if (!Object.op_Implicit((Object)(object)RunManager.instance))
				{
					PendingSkipShop = false;
					return;
				}
				if (!SemiFunc.RunIsShop())
				{
					PendingSkipShop = false;
					return;
				}
				if (RunManager.instance.restarting)
				{
					PendingSkipShop = false;
					return;
				}
				PendingSkipShop = false;
				Log.LogInfo((object)"Auto skip shop after full shop load -> move to truck phase");
				RunManager.instance.ChangeLevel(false, false, (ChangeLevelType)0);
			}
			catch (Exception ex)
			{
				Log.LogError((object)"Failed to auto skip shop");
				Log.LogError((object)ex);
			}
		}
	}
}