Decompiled source of FixedYippeeKeyMod v1.3.3

YippeeKey.dll

Decompiled 2 years ago
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.Reflection;
using System.Runtime.CompilerServices;
using System.Runtime.Serialization;
using System.Runtime.Versioning;
using System.Security;
using System.Security.Permissions;
using BepInEx;
using BepInEx.Configuration;
using CSync.Lib;
using CSync.Util;
using GameNetcodeStuff;
using HarmonyLib;
using Microsoft.CodeAnalysis;
using QMLCYipeeKey_plugin.NetcodePatcher;
using Unity.Netcode;
using UnityEngine;
using YippeeKey.ConfigSync;
using YippeeKey.LocalScripts;
using YippeeKey.Patches;

[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("QMLCYipeeKey_plugin")]
[assembly: AssemblyConfiguration("Debug")]
[assembly: AssemblyFileVersion("1.3.1.1")]
[assembly: AssemblyInformationalVersion("1.3.1.1")]
[assembly: AssemblyProduct("YippeeKey")]
[assembly: AssemblyTitle("QMLCYipeeKey_plugin")]
[assembly: SecurityPermission(SecurityAction.RequestMinimum, SkipVerification = true)]
[assembly: AssemblyVersion("1.3.1.1")]
[module: UnverifiableCode]
[module: RefSafetyRules(11)]
[module: NetcodePatchedAssembly]
internal class <Module>
{
	static <Module>()
	{
	}
}
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 YippeeKey
{
	public sealed class NetworkHandlerYP : NetworkBehaviour
	{
		public static NetworkHandlerYP Instance { get; private set; }

		public override void OnNetworkSpawn()
		{
			YippeeKeyPlugin.Instance.Log("Despawning NetworkObject");
			YippeeKeyPlugin.Instance.Log("NetworkManager existant? " + (((Object)(object)NetworkManager.Singleton != (Object)null) ? "Yes!" : "No"));
			if (NetworkManager.Singleton.IsHost || NetworkManager.Singleton.IsServer)
			{
				try
				{
					NetworkObject component = ((Component)this).gameObject.GetComponent<NetworkObject>();
					YippeeKeyPlugin.Instance.Log("networkObject existant? " + (((Object)(object)component != (Object)null) ? "Yes!" : "No"));
					if (component != null)
					{
						component.Spawn(false);
					}
				}
				catch (Exception)
				{
					YippeeKeyPlugin.Instance.Log("networkObject was already spawned.");
				}
			}
			Instance = this;
			((NetworkBehaviour)this).OnNetworkSpawn();
		}

		[ServerRpc(RequireOwnership = false)]
		public void ScreamYippeeServerRPC(string eventName, bool isCallerDead)
		{
			//IL_0024: Unknown result type (might be due to invalid IL or missing references)
			//IL_002e: Invalid comparison between Unknown and I4
			//IL_00e5: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ef: Invalid comparison between Unknown and I4
			//IL_005f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0068: Unknown result type (might be due to invalid IL or missing references)
			//IL_006d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0088: 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_00bb: Unknown result type (might be due to invalid IL or missing references)
			//IL_00c1: Unknown result type (might be due to invalid IL or missing references)
			//IL_00d5: Unknown result type (might be due to invalid IL or missing references)
			NetworkManager networkManager = ((NetworkBehaviour)this).NetworkManager;
			if (networkManager == null || !networkManager.IsListening)
			{
				return;
			}
			if ((int)base.__rpc_exec_stage != 1 && (networkManager.IsClient || networkManager.IsHost))
			{
				ServerRpcParams val = default(ServerRpcParams);
				FastBufferWriter val2 = ((NetworkBehaviour)this).__beginSendServerRpc(2687437084u, val, (RpcDelivery)0);
				bool flag = eventName != null;
				((FastBufferWriter)(ref val2)).WriteValueSafe<bool>(ref flag, default(ForPrimitives));
				if (flag)
				{
					((FastBufferWriter)(ref val2)).WriteValueSafe(eventName, false);
				}
				((FastBufferWriter)(ref val2)).WriteValueSafe<bool>(ref isCallerDead, default(ForPrimitives));
				((NetworkBehaviour)this).__endSendServerRpc(ref val2, 2687437084u, val, (RpcDelivery)0);
			}
			if ((int)base.__rpc_exec_stage == 1 && (networkManager.IsServer || networkManager.IsHost))
			{
				YippeeKeyPlugin.Instance.Log("Server event received");
				YippeeKeyPlugin.Instance.Log("Notifying Clients");
				ScreamYippeeClientRPC(eventName, isCallerDead);
			}
		}

		[ClientRpc]
		public void ScreamYippeeClientRPC(string eventName, bool isCallerDead)
		{
			//IL_0024: Unknown result type (might be due to invalid IL or missing references)
			//IL_002e: Invalid comparison between Unknown and I4
			//IL_00e5: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ef: Invalid comparison between Unknown and I4
			//IL_005f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0068: Unknown result type (might be due to invalid IL or missing references)
			//IL_006d: Unknown result type (might be due to invalid IL or missing references)
			//IL_0088: 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_00bb: Unknown result type (might be due to invalid IL or missing references)
			//IL_00c1: Unknown result type (might be due to invalid IL or missing references)
			//IL_00d5: Unknown result type (might be due to invalid IL or missing references)
			NetworkManager networkManager = ((NetworkBehaviour)this).NetworkManager;
			if (networkManager == null || !networkManager.IsListening)
			{
				return;
			}
			if ((int)base.__rpc_exec_stage != 2 && (networkManager.IsServer || networkManager.IsHost))
			{
				ClientRpcParams val = default(ClientRpcParams);
				FastBufferWriter val2 = ((NetworkBehaviour)this).__beginSendClientRpc(150389723u, val, (RpcDelivery)0);
				bool flag = eventName != null;
				((FastBufferWriter)(ref val2)).WriteValueSafe<bool>(ref flag, default(ForPrimitives));
				if (flag)
				{
					((FastBufferWriter)(ref val2)).WriteValueSafe(eventName, false);
				}
				((FastBufferWriter)(ref val2)).WriteValueSafe<bool>(ref isCallerDead, default(ForPrimitives));
				((NetworkBehaviour)this).__endSendClientRpc(ref val2, 150389723u, val, (RpcDelivery)0);
			}
			if ((int)base.__rpc_exec_stage == 2 && (networkManager.IsClient || networkManager.IsHost))
			{
				YippeeKeyPlugin.Instance.Log("Event received from Server for " + eventName);
				NetworkObjectManagerYK.playYippeeAtPlayer(ref eventName, ref isCallerDead);
			}
		}

		protected override void __initializeVariables()
		{
			((NetworkBehaviour)this).__initializeVariables();
		}

		[RuntimeInitializeOnLoadMethod]
		internal static void InitializeRPCS_NetworkHandlerYP()
		{
			//IL_0011: Unknown result type (might be due to invalid IL or missing references)
			//IL_001b: Expected O, but got Unknown
			//IL_002c: Unknown result type (might be due to invalid IL or missing references)
			//IL_0036: Expected O, but got Unknown
			NetworkManager.__rpc_func_table.Add(2687437084u, new RpcReceiveHandler(__rpc_handler_2687437084));
			NetworkManager.__rpc_func_table.Add(150389723u, new RpcReceiveHandler(__rpc_handler_150389723));
		}

		private static void __rpc_handler_2687437084(NetworkBehaviour target, FastBufferReader reader, __RpcParams rpcParams)
		{
			//IL_002f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0035: Unknown result type (might be due to invalid IL or missing references)
			//IL_0067: Unknown result type (might be due to invalid IL or missing references)
			//IL_006d: Unknown result type (might be due to invalid IL or missing references)
			//IL_007c: Unknown result type (might be due to invalid IL or missing references)
			//IL_009a: Unknown result type (might be due to invalid IL or missing references)
			NetworkManager networkManager = target.NetworkManager;
			if (networkManager != null && networkManager.IsListening)
			{
				bool flag = default(bool);
				((FastBufferReader)(ref reader)).ReadValueSafe<bool>(ref flag, default(ForPrimitives));
				string eventName = null;
				if (flag)
				{
					((FastBufferReader)(ref reader)).ReadValueSafe(ref eventName, false);
				}
				bool isCallerDead = default(bool);
				((FastBufferReader)(ref reader)).ReadValueSafe<bool>(ref isCallerDead, default(ForPrimitives));
				target.__rpc_exec_stage = (__RpcExecStage)1;
				((NetworkHandlerYP)(object)target).ScreamYippeeServerRPC(eventName, isCallerDead);
				target.__rpc_exec_stage = (__RpcExecStage)0;
			}
		}

		private static void __rpc_handler_150389723(NetworkBehaviour target, FastBufferReader reader, __RpcParams rpcParams)
		{
			//IL_002f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0035: Unknown result type (might be due to invalid IL or missing references)
			//IL_0067: Unknown result type (might be due to invalid IL or missing references)
			//IL_006d: Unknown result type (might be due to invalid IL or missing references)
			//IL_007c: Unknown result type (might be due to invalid IL or missing references)
			//IL_009a: Unknown result type (might be due to invalid IL or missing references)
			NetworkManager networkManager = target.NetworkManager;
			if (networkManager != null && networkManager.IsListening)
			{
				bool flag = default(bool);
				((FastBufferReader)(ref reader)).ReadValueSafe<bool>(ref flag, default(ForPrimitives));
				string eventName = null;
				if (flag)
				{
					((FastBufferReader)(ref reader)).ReadValueSafe(ref eventName, false);
				}
				bool isCallerDead = default(bool);
				((FastBufferReader)(ref reader)).ReadValueSafe<bool>(ref isCallerDead, default(ForPrimitives));
				target.__rpc_exec_stage = (__RpcExecStage)2;
				((NetworkHandlerYP)(object)target).ScreamYippeeClientRPC(eventName, isCallerDead);
				target.__rpc_exec_stage = (__RpcExecStage)0;
			}
		}

		[MethodImpl(MethodImplOptions.NoInlining)]
		protected internal override string __getTypeName()
		{
			return "NetworkHandlerYP";
		}
	}
	[BepInPlugin("QMLCYipeeKey_plugin", "Yippee key", "1.3.3")]
	[BepInDependency(/*Could not decode attribute arguments.*/)]
	internal sealed class YippeeKeyPlugin : BaseUnityPlugin
	{
		public const string GUID = "QMLCYipeeKey_plugin";

		public const string Name = "Yippee key";

		public const string Version = "1.3.3";

		public AssetBundle? MainAssetBundle;

		public static YippeeKeyPlugin Instance;

		public YippeeSyncedConfig GetConfig;

		private Harmony harmony = new Harmony("net.quadmesh.yippeekey.plugin");

		private void Awake()
		{
			//IL_00f2: Unknown result type (might be due to invalid IL or missing references)
			Instance = this;
			SetupNetworking();
			SetupConfigKeys();
			string directoryName = Path.GetDirectoryName(((BaseUnityPlugin)this).Info.Location);
			string text = Path.Combine(directoryName, "yippeekey");
			MainAssetBundle = AssetBundle.LoadFromFile(text);
			if ((Object)(object)MainAssetBundle != (Object)null)
			{
				((BaseUnityPlugin)this).Logger.LogInfo((object)(((Object)MainAssetBundle).name + " Should be loaded succesfully."));
			}
			Harmony.CreateAndPatchAll(Assembly.GetExecutingAssembly(), "QMLCYipeeKey_plugin");
			harmony.PatchAll(typeof(YippeeSyncedConfig));
			NetcodePatcher();
			((BaseUnityPlugin)this).Logger.LogInfo((object)"Yippe mod ready!");
			((BaseUnityPlugin)this).Logger.LogInfo((object)("Debugging? [" + BeautifyBool(SyncedInstance<YippeeSyncedConfig>.Instance.DebugKey.Value) + "]"));
			((BaseUnityPlugin)this).Logger.LogInfo((object)$"Key to use Yippe: '{SyncedInstance<YippeeSyncedConfig>.Instance.ConfigKey.Value}'");
		}

		private void SetupNetworking()
		{
			Type[] types = Assembly.GetExecutingAssembly().GetTypes();
			Type[] array = types;
			foreach (Type type in array)
			{
				MethodInfo[] methods = type.GetMethods(BindingFlags.Instance | BindingFlags.Static | BindingFlags.NonPublic);
				MethodInfo[] array2 = methods;
				foreach (MethodInfo methodInfo in array2)
				{
					object[] customAttributes = methodInfo.GetCustomAttributes(typeof(RuntimeInitializeOnLoadMethodAttribute), inherit: false);
					if (customAttributes.Length != 0)
					{
						methodInfo.Invoke(null, null);
					}
				}
			}
		}

		public void Log(string message)
		{
			if (SyncedInstance<YippeeSyncedConfig>.Default.DebugKey.Value)
			{
				((BaseUnityPlugin)this).Logger.LogInfo((object)message);
			}
		}

		public static string BeautifyBool(bool value)
		{
			return value ? "Yes!" : "Nope.";
		}

		public void LogError(string message)
		{
			((BaseUnityPlugin)this).Logger.LogError((object)message);
		}

		private void SetupConfigKeys()
		{
			GetConfig = new YippeeSyncedConfig("QMLCYipeeKey_plugin", ((BaseUnityPlugin)this).Config);
		}

		private static void NetcodePatcher()
		{
			Type[] types = Assembly.GetExecutingAssembly().GetTypes();
			Type[] array = types;
			foreach (Type type in array)
			{
				MethodInfo[] methods = type.GetMethods(BindingFlags.Instance | BindingFlags.Static | BindingFlags.NonPublic);
				MethodInfo[] array2 = methods;
				foreach (MethodInfo methodInfo in array2)
				{
					object[] customAttributes = methodInfo.GetCustomAttributes(typeof(RuntimeInitializeOnLoadMethodAttribute), inherit: false);
					if (customAttributes.Length != 0)
					{
						methodInfo.Invoke(null, null);
					}
				}
			}
		}
	}
	public static class MyPluginInfo
	{
		public const string PLUGIN_GUID = "QMLCYipeeKey_plugin";

		public const string PLUGIN_NAME = "YippeeKey";

		public const string PLUGIN_VERSION = "1.3.1.1";
	}
}
namespace YippeeKey.Patches
{
	[HarmonyPatch]
	internal class DeadBodyInfoPatch
	{
		[HarmonyPrefix]
		[HarmonyPatch(typeof(DeadBodyInfo), "DeactivateBody")]
		private static void ReparentOnRespawn(DeadBodyInfo __instance)
		{
			foreach (YippeeSoundManager value in NetworkObjectManagerYK.soundManagers.Values)
			{
				if (value.Player.isPlayerDead)
				{
					YippeeKeyPlugin.Instance.Log("Reparenting soundmanager to normal body");
					((Component)NetworkObjectManagerYK.soundManagers[((Object)((Component)__instance.playerScript).gameObject).name]).transform.SetParent(((Component)__instance.playerScript).transform);
					YippeeKeyPlugin.Instance.Log("Reparented " + ((Object)((Component)__instance).gameObject).name);
				}
			}
		}
	}
	[HarmonyPatch]
	public sealed class NetworkObjectManagerYK
	{
		public static Dictionary<string, YippeeSoundManager> soundManagers = new Dictionary<string, YippeeSoundManager>();

		private static GameObject? networkPrefab = null;

		[HarmonyPostfix]
		[HarmonyPatch(typeof(GameNetworkManager), "Start")]
		public static void Init()
		{
			//IL_0046: Unknown result type (might be due to invalid IL or missing references)
			//IL_0050: Expected O, but got Unknown
			if ((Object)(object)networkPrefab != (Object)null)
			{
				YippeeKeyPlugin.Instance.Log("Networkmanager already exist");
			}
			YippeeKeyPlugin.Instance.Log("Getting network prefab setup");
			networkPrefab = (GameObject)YippeeKeyPlugin.Instance.MainAssetBundle.LoadAsset("NetworkHandlerYippeeKey");
			YippeeKeyPlugin.Instance.Log("Adding NetworkHandlerYP");
			networkPrefab.AddComponent<NetworkHandlerYP>();
			YippeeKeyPlugin.Instance.Log("Adding Networked prefab");
			NetworkManager.Singleton.AddNetworkPrefab(networkPrefab);
		}

		[HarmonyPostfix]
		[HarmonyPatch(typeof(StartOfRound), "Awake")]
		private static void SpawnNetworkHandler()
		{
			//IL_0075: Unknown result type (might be due to invalid IL or missing references)
			//IL_007a: Unknown result type (might be due to invalid IL or missing references)
			YippeeKeyPlugin.Instance.Log("Spawning NetworkHandler");
			if (NetworkManager.Singleton.IsHost || NetworkManager.Singleton.IsServer)
			{
				YippeeKeyPlugin.Instance.Log("NetworkHandler spawned!");
				YippeeKeyPlugin.Instance.Log("Is networkPrefab existant? " + (((Object)(object)networkPrefab != (Object)null) ? "Yes!" : "Nope"));
				GameObject val = Object.Instantiate<GameObject>(networkPrefab, Vector3.zero, Quaternion.identity);
				YippeeKeyPlugin.Instance.Log("Is NetworkHandler existant? " + (((Object)(object)val != (Object)null) ? "Yes!" : "Nope"));
				NetworkObject component = val.GetComponent<NetworkObject>();
				if (component != null)
				{
					component.Spawn(false);
				}
			}
		}

		[HarmonyPostfix]
		[HarmonyPatch(typeof(GameNetworkManager), "StartDisconnect")]
		private static void UnsubscribeFromHandler()
		{
			YippeeKeyPlugin.Instance.Log("UnSyncing config");
			soundManagers.Clear();
			((SyncedInstance<YippeeSyncedConfig>)(object)YippeeKeyPlugin.Instance.GetConfig).RevertSync();
		}

		public static void SendYippeeEventToServer(string eventName, bool isCallerDead)
		{
			YippeeKeyPlugin.Instance.Log("Sending event to rest of lobby.");
			NetworkHandlerYP.Instance.ScreamYippeeServerRPC(eventName, isCallerDead);
		}

		public static void playYippeeAtPlayer(ref string playerName, ref bool isCallerDead)
		{
			//IL_0130: Unknown result type (might be due to invalid IL or missing references)
			if (!soundManagers.ContainsKey(playerName))
			{
				YippeeKeyPlugin.Instance.LogError("Unable to get sound manager for " + playerName + "!");
			}
			else if (SyncedInstance<YippeeSyncedConfig>.Instance.DeadPlayersYippeeAlivePlayers.Value || GameNetworkManager.Instance.localPlayerController.isPlayerDead)
			{
				GameObject gameObject = ((Component)soundManagers[playerName]).gameObject;
				Transform transform = gameObject.transform;
				YippeeKeyPlugin.Instance.Log(playerName + "'s transform gotten from dictionary.");
				soundManagers[playerName].Play(isCallerDead);
				if (!SyncedInstance<YippeeSyncedConfig>.Instance.NotifyEnemies.Value)
				{
					YippeeKeyPlugin.Instance.Log("Host-synced config dictates enemies are not alerted.");
					return;
				}
				if ((isCallerDead && !SyncedInstance<YippeeSyncedConfig>.Instance.DeadPlayerAlertsEnemyAI.Value) || !SyncedInstance<YippeeSyncedConfig>.Instance.DeadPlayersYippeeAlivePlayers.Value)
				{
					YippeeKeyPlugin.Instance.Log("Host-synced config dictates Dead players cannot alert enemies.");
					return;
				}
				YippeeKeyPlugin.Instance.Log("Host-synced config dictates enemies are alerted.");
				RoundManager.Instance.PlayAudibleNoise(transform.position, (float)SyncedInstance<YippeeSyncedConfig>.Instance.EnemyAIDetectionRange.Value, SyncedInstance<YippeeSyncedConfig>.Instance.EnemyAIDetectionVolume.Value, 0, false, 0);
			}
		}
	}
	[HarmonyPatch]
	internal sealed class PlayerControllerBPatch
	{
		[HarmonyPostfix]
		[HarmonyPatch(typeof(PlayerControllerB), "OnEnable")]
		private static void AddInputter(PlayerControllerB __instance)
		{
			YippeeInputter yippeeInputter = default(YippeeInputter);
			((Component)__instance).gameObject.TryGetComponent<YippeeInputter>(ref yippeeInputter);
			if ((Object)(object)yippeeInputter == (Object)null)
			{
				YippeeKeyPlugin.Instance.Log("YippeInputter added!");
				((Component)__instance).gameObject.AddComponent<YippeeInputter>();
			}
			YippeeKeyPlugin.Instance.Log("Setting SoundManager");
			AddSoundManagerToPlayer(__instance);
		}

		public static void AddSoundManagerToPlayer(PlayerControllerB playerController)
		{
			//IL_003f: Unknown result type (might be due to invalid IL or missing references)
			//IL_0045: Expected O, but got Unknown
			//IL_0061: Unknown result type (might be due to invalid IL or missing references)
			//IL_0076: Unknown result type (might be due to invalid IL or missing references)
			//IL_0091: Unknown result type (might be due to invalid IL or missing references)
			//IL_009b: Unknown result type (might be due to invalid IL or missing references)
			//IL_00ab: Unknown result type (might be due to invalid IL or missing references)
			if (Object.op_Implicit((Object)(object)((Component)playerController).gameObject.GetComponentInChildren<YippeeSoundManager>()))
			{
				YippeeKeyPlugin.Instance.Log("You already have a soundManager, there is no need to add another.");
				return;
			}
			GameObject val = (GameObject)YippeeKeyPlugin.Instance.MainAssetBundle.LoadAsset("YippeSound");
			YippeeKeyPlugin.Instance.Log("Prefab for use, loaded!");
			GameObject val2 = Object.Instantiate<GameObject>(val, new Vector3(((Component)playerController).gameObject.transform.position.x, ((Component)playerController).gameObject.transform.position.y + 2f, ((Component)playerController).gameObject.transform.position.z), ((Component)playerController).gameObject.transform.rotation, ((Component)playerController).gameObject.transform);
			YippeeSoundManager yippeeSoundManager = val2.AddComponent<YippeeSoundManager>();
			yippeeSoundManager.Player = playerController;
			NetworkObjectManagerYK.soundManagers.Add(((Object)((Component)playerController).gameObject).name, yippeeSoundManager);
			YippeeKeyPlugin.Instance.Log("Soundmanager set for " + ((Object)((Component)playerController).gameObject).name);
		}

		[HarmonyPostfix]
		[HarmonyPatch(typeof(PlayerControllerB), "SpawnDeadBody")]
		private static void ReparentOnDeath(PlayerControllerB __instance)
		{
			if ((Object)(object)__instance.deadBody != (Object)null && ((Behaviour)__instance.deadBody).enabled)
			{
				YippeeKeyPlugin.Instance.Log("Reparenting soundmanager to dead body");
				try
				{
					((Component)NetworkObjectManagerYK.soundManagers[((Object)((Component)__instance).gameObject).name]).transform.SetParent(((Component)__instance.deadBody).transform);
					YippeeKeyPlugin.Instance.Log("Reparented " + ((Object)((Component)__instance).gameObject).name);
				}
				catch
				{
					YippeeKeyPlugin.Instance.LogError("Unable to set the YippeeSoundManager to the dead body, most likey Nullref.");
				}
			}
		}
	}
}
namespace YippeeKey.LocalScripts
{
	public class YippeeInputter : MonoBehaviour
	{
		private PlayerControllerB _localPlayer;

		private bool cooldownActive = false;

		private float cooldown = SyncedInstance<YippeeSyncedConfig>.Instance.CooldownTime.Value;

		private float CoolDownStartTime => SyncedInstance<YippeeSyncedConfig>.Instance.CooldownTime.Value;

		private void Awake()
		{
			_localPlayer = ((Component)this).GetComponent<PlayerControllerB>();
		}

		public void Update()
		{
			//IL_003a: Unknown result type (might be due to invalid IL or missing references)
			ManageCooldown();
			if ((!SyncedInstance<YippeeSyncedConfig>.Instance.CooldownEnabled.Value || !cooldownActive) && UnityInput.Current.GetKeyDown(SyncedInstance<YippeeSyncedConfig>.Default.ConfigKey.Value) && IsLocal() && !GameNetworkManager.Instance.localPlayerController.inTerminalMenu && !GameNetworkManager.Instance.localPlayerController.quickMenuManager.isMenuOpen && !GameNetworkManager.Instance.localPlayerController.isTypingChat)
			{
				NetworkObjectManagerYK.SendYippeeEventToServer(((Object)((Component)GameNetworkManager.Instance.localPlayerController).gameObject).name, GameNetworkManager.Instance.localPlayerController.isPlayerDead);
				if (SyncedInstance<YippeeSyncedConfig>.Instance.CooldownEnabled.Value)
				{
					cooldownActive = true;
					YippeeKeyPlugin.Instance.Log("Cooldown active");
				}
			}
		}

		private void ManageCooldown()
		{
			if (cooldownActive)
			{
				cooldown -= Time.deltaTime;
				YippeeKeyPlugin.Instance.Log($"{cooldown}");
				if (cooldown <= 0f)
				{
					cooldownActive = false;
					cooldown = CoolDownStartTime;
					YippeeKeyPlugin.Instance.Log("Cooldown has wore off, time to Yippee!");
				}
			}
		}

		private bool IsLocal()
		{
			return ((object)_localPlayer).Equals((object?)GameNetworkManager.Instance.localPlayerController);
		}
	}
	public sealed class YippeeSoundManager : MonoBehaviour
	{
		private PlayerControllerB player;

		public DeadBodyInfo DeadBody;

		public AudioSource YippeeAudio { get; private set; } = null;


		public ParticleSystem[] ParticleSystems { get; private set; } = (ParticleSystem[])(object)new ParticleSystem[3];


		public PlayerControllerB Player
		{
			get
			{
				return player;
			}
			set
			{
				player = value;
				DeadBody = player.deadBody;
			}
		}

		private bool IsLocalPlayerDead => GameNetworkManager.Instance.localPlayerController.isPlayerDead;

		public void Play(bool isCallerDead)
		{
			if ((Object)(object)YippeeAudio == (Object)null)
			{
				YippeeAudio = ((Component)this).GetComponent<AudioSource>();
			}
			ResetEffects();
			RandomPitch();
			if (isCallerDead)
			{
				PostMortem();
			}
			PlayYippee();
			WalkieTalkie.TransmitOneShotAudio(YippeeAudio, YippeeAudio.clip, 1f);
			if (!SyncedInstance<YippeeSyncedConfig>.Default.AllowVisuals.Value || (isCallerDead && !IsLocalPlayerDead))
			{
				return;
			}
			if ((Object)(object)ParticleSystems[0] == (Object)null)
			{
				GetParticleSystems();
			}
			ParticleSystem[] particleSystems = ParticleSystems;
			foreach (ParticleSystem val in particleSystems)
			{
				if (SyncedInstance<YippeeSyncedConfig>.Default.AllowParticeSpam.Value)
				{
					val.Stop(false);
				}
				else
				{
					val.Stop(false, (ParticleSystemStopBehavior)0);
				}
				val.Play();
			}
		}

		public void OnDestroy()
		{
			if (!((Object)(object)Player == (Object)null) && !((Object)(object)((Component)Player).gameObject == (Object)null))
			{
				NetworkObjectManagerYK.soundManagers.Remove(((Object)((Component)Player).gameObject).name);
				PlayerControllerBPatch.AddSoundManagerToPlayer(Player);
			}
		}

		private void PlayYippee()
		{
			if (SyncedInstance<YippeeSyncedConfig>.Default.AllowYippeeOverlap.Value)
			{
				YippeeAudio.PlayOneShot(YippeeAudio.clip);
			}
			else
			{
				YippeeAudio.Stop();
				YippeeAudio.Play();
			}
			YippeeKeyPlugin.Instance.Log($"Playing Yippee {((Behaviour)YippeeAudio).enabled}");
		}

		private void GetParticleSystems()
		{
			//IL_0018: Unknown result type (might be due to invalid IL or missing references)
			//IL_001e: Expected O, but got Unknown
			int num = 0;
			foreach (Transform item in ((Component)this).transform)
			{
				Transform val = item;
				ParticleSystems[num] = ((Component)val).GetComponent<ParticleSystem>();
				num++;
			}
		}

		private void RandomPitch()
		{
			if (SyncedInstance<YippeeSyncedConfig>.Default.RandomPitchedYippee.Value)
			{
				YippeeAudio.pitch = Random.Range(0.95f, 1.05f);
			}
		}

		private void PostMortem()
		{
			if (IsLocalPlayerDead)
			{
				YippeeAudio.spatialBlend = 0f;
				YippeeAudio.reverbZoneMix = 0f;
			}
			else
			{
				YippeeAudio.volume *= 0.25f;
				YippeeAudio.pitch *= 0.75f;
			}
		}

		private void ResetEffects()
		{
			YippeeAudio.pitch = 1f;
			YippeeAudio.volume = SyncedInstance<YippeeSyncedConfig>.Default.YippeeVolume.Value;
			YippeeAudio.spatialBlend = 1f;
			YippeeAudio.reverbZoneMix = 1f;
		}
	}
}
namespace YippeeKey.ConfigSync
{
	[DataContract]
	public class YippeeSyncedConfig : SyncedConfig<YippeeSyncedConfig>
	{
		public ConfigEntry<float> DisplayDebugInfo { get; private set; }

		[DataMember]
		public SyncedEntry<bool> NotifyEnemies { get; private set; }

		[DataMember]
		public SyncedEntry<int> EnemyAIDetectionRange { get; private set; }

		[DataMember]
		public SyncedEntry<float> EnemyAIDetectionVolume { get; private set; }

		[DataMember]
		public SyncedEntry<bool> CooldownEnabled { get; private set; }

		[DataMember]
		public SyncedEntry<float> CooldownTime { get; private set; }

		[DataMember]
		public SyncedEntry<bool> DeadPlayersYippeeAlivePlayers { get; private set; }

		[DataMember]
		public SyncedEntry<bool> DeadPlayerAlertsEnemyAI { get; private set; }

		public ConfigEntry<KeyCode> ConfigKey { get; private set; }

		public ConfigEntry<bool> DebugKey { get; private set; }

		public ConfigEntry<bool> AllowVisuals { get; private set; }

		public ConfigEntry<bool> AllowParticeSpam { get; private set; }

		public ConfigEntry<bool> AllowYippeeOverlap { get; private set; }

		public ConfigEntry<float> YippeeVolume { get; private set; }

		public ConfigEntry<bool> RandomPitchedYippee { get; private set; }

		public YippeeSyncedConfig(string guid, ConfigFile cfg)
			: base(guid)
		{
			//IL_00c9: Unknown result type (might be due to invalid IL or missing references)
			//IL_00d3: Expected O, but got Unknown
			ConfigManager.Register<YippeeSyncedConfig>(this);
			YippeeVolume = cfg.Bind<float>("Gameplay", "Yippee Audio Volume", 1f, "Volume of the Yippee sound itself.\nNote: This will not affect AI detection, only local sound.");
			NotifyEnemies = Extensions.BindSyncedEntry<bool>(cfg, "Gameplay", "Notify Enemy AI (HOST ONLY)", true, "Notify Enemies when someone shouts 'Yippee!'. This setting will only apply if you are the host.");
			CooldownEnabled = Extensions.BindSyncedEntry<bool>(cfg, "Gameplay", "Yippee cooldown (HOST ONLY)", false, "Enables cooldowns when you are hosting the instance");
			CooldownTime = Extensions.BindSyncedEntry<float>(cfg, "Gameplay", "Yippee cooldown time (HOST ONLY)", 2f, "The time (in seconds) it will take for the cooldown to stop");
			DeadPlayersYippeeAlivePlayers = Extensions.BindSyncedEntry<bool>(cfg, "Gameplay", "Dead players can Yippee (HOST ONLY)", true, "Allow dead players to yippee");
			EnemyAIDetectionRange = Extensions.ToSyncedEntry<int>(cfg.Bind<int>("Gameplay Advanced", "EnemyAI detection range (HOST ONLY)", 10, new ConfigDescription("DetectionRange for EnemyAI when shouting 'Yippee!' (HOST ONLY)\nDo not mess with this value unless you know what you're doing!", (AcceptableValueBase)(object)new AcceptableValueRange<int>(1, 100), Array.Empty<object>())));
			EnemyAIDetectionVolume = Extensions.BindSyncedEntry<float>(cfg, "Gameplay Advanced", "EnemyAI detection volume (HOST ONLY)", 1f, "Detection volume for EnemyAI when shouting 'Yippee!' (HOST ONLY)\nNote: This is NOT the volume of the sound, only the volume of which the EnemyAI component hears the sound.\nDo not mess with this value unless you know what you're doing!");
			DeadPlayerAlertsEnemyAI = Extensions.BindSyncedEntry<bool>(cfg, "Gameplay Advanced", "Dead players Yippee alerts AI (HOST ONLY)", false, "Dead players can yippe and alert AI (reduced range)");
			ConfigKey = cfg.Bind<KeyCode>("Input", "Yippee Key Binding", (KeyCode)105, "The keybind you're using to shout 'Yippee!'");
			RandomPitchedYippee = cfg.Bind<bool>("Audio", "Randomly pitched yippee", true, "Makes the pitch of the 'Yippee' when shouting be randomized");
			AllowYippeeOverlap = cfg.Bind<bool>("Audio", "Allow overlapping Yippee", false, "Make the audio when spamming Yippe overlap instead of restarting\n(useful with 'Spam Particles')");
			AllowVisuals = cfg.Bind<bool>("Visual", "Add visuals", true, "Adds visuals like particles when shouting 'Yippee!'");
			AllowParticeSpam = cfg.Bind<bool>("Visual", "Spam particles", false, "Allows particles to be spammed\n(useful with 'Allow Yippee Overlap')");
			DebugKey = cfg.Bind<bool>("Misc", "Show Debug Messages", false, "Whether or not debug messages appear inside the log");
			RemoveOrphans(cfg);
		}

		private void RemoveOrphans(ConfigFile config)
		{
			PropertyInfo property = ((object)config).GetType().GetProperty("OrphanedEntries", BindingFlags.Instance | BindingFlags.NonPublic);
			Dictionary<ConfigDefinition, string> dictionary = (Dictionary<ConfigDefinition, string>)property.GetValue(config, null);
			dictionary.Clear();
			config.Save();
		}
	}
}
namespace QMLCYipeeKey_plugin.NetcodePatcher
{
	[AttributeUsage(AttributeTargets.Module)]
	internal class NetcodePatchedAssemblyAttribute : Attribute
	{
	}
}