using System; using System.Collections.Generic; using System.Diagnostics; using System.Linq; using System.Reflection; using System.Runtime.CompilerServices; using System.Runtime.Versioning; using System.Security; using System.Security.Permissions; using BepInEx; using BepInEx.Configuration; using GameNetcodeStuff; using HarmonyLib; using LethalCompanyInputUtils.Api; using Microsoft.CodeAnalysis; using SpectateEnemy.NetcodePatcher; using TMPro; using Unity.Netcode; using UnityEngine; using UnityEngine.InputSystem; [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("SpectateEnemy")] [assembly: AssemblyConfiguration("Debug")] [assembly: AssemblyDescription("My first plugin")] [assembly: AssemblyFileVersion("2.8.0.0")] [assembly: AssemblyInformationalVersion("2.8.0+a3ed3cf0019765ad4d80e7c9e3c122bf84650c2f")] [assembly: AssemblyProduct("SpectateEnemy")] [assembly: AssemblyTitle("SpectateEnemy")] [assembly: SecurityPermission(SecurityAction.RequestMinimum, SkipVerification = true)] [assembly: AssemblyVersion("2.8.0.0")] [module: UnverifiableCode] [module: RefSafetyRules(11)] [module: NetcodePatchedAssembly] 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 SpectateEnemy { internal class Inputs : LcInputActions { [InputAction("/e", Name = "Swap between Players/Enemies")] public InputAction SwapKey { get; set; } [InputAction("/insert", Name = "Open Config Menu")] public InputAction MenuKey { get; set; } [InputAction("/rightButton", Name = "Toggle Flashlight")] public InputAction FlashlightKey { get; set; } [InputAction("/scroll/down", Name = "Zoom Out")] public InputAction ZoomOutKey { get; set; } [InputAction("/scroll/up", Name = "Zoom In")] public InputAction ZoomInKey { get; set; } } [BepInPlugin("SpectateEnemy", "SpectateEnemy", "2.9.1")] [BepInDependency(/*Could not decode attribute arguments.*/)] internal class Plugin : BaseUnityPlugin { public static MethodInfo raycastSpectate = null; public static MethodInfo displaySpectatorTip = null; public static Inputs Inputs = new Inputs(); public static ConfigFile Configuration; private Harmony harmony; private void Awake() { //IL_0012: Unknown result type (might be due to invalid IL or missing references) //IL_001c: Expected O, but got Unknown Configuration = ((BaseUnityPlugin)this).Config; harmony = new Harmony("SpectateEnemy"); harmony.PatchAll(); raycastSpectate = AccessTools.Method(typeof(PlayerControllerB), "RaycastSpectateCameraAroundPivot", (Type[])null, (Type[])null); displaySpectatorTip = AccessTools.Method(typeof(HUDManager), "DisplaySpectatorTip", (Type[])null, (Type[])null); ((BaseUnityPlugin)this).Logger.LogInfo((object)"SpectateEnemy loaded!"); } } internal class Spectatable : MonoBehaviour { public SpectatableType type = SpectatableType.Enemy; public string enemyName = "Enemy"; public string maskedName = string.Empty; public EnemyAI enemyInstance = null; } internal enum SpectatableType { Enemy, Turret, Landmine, Masked, GhostGirl } internal class SpectateEnemies : MonoBehaviour { public static SpectateEnemies Instance; private static readonly Dictionary> settings = new Dictionary>(); private bool WindowOpen = false; private Rect window = new Rect(10f, 10f, 500f, 400f); private Vector2 scrollPos = Vector2.zero; public int SpectatedEnemyIndex = -1; public bool SpectatingEnemies = false; public Spectatable[] SpectatorList; public float ZoomLevel = 1f; public ConfigEntry HideControls; private void Awake() { if ((Object)(object)Instance != (Object)null) { Object.Destroy((Object)(object)((Component)this).gameObject); } SetupKeybinds(); Instance = this; Object.DontDestroyOnLoad((Object)(object)((Component)this).gameObject); HideControls = Plugin.Configuration.Bind("Config", "Hide Controls", false, "Hides the controls toolip on the right hand side."); } private void SetupKeybinds() { Plugin.Inputs.SwapKey.performed += OnSwapKeyPressed; Plugin.Inputs.MenuKey.performed += OnMenuKeyPressed; Plugin.Inputs.FlashlightKey.performed += OnFlashlightKeyPressed; Plugin.Inputs.ZoomOutKey.performed += OnZoomOutPressed; Plugin.Inputs.ZoomInKey.performed += OnZoomInPressed; } private void OnSwapKeyPressed(CallbackContext context) { if (((CallbackContext)(ref context)).performed && (Object)(object)GameNetworkManager.Instance != (Object)null && (Object)(object)GameNetworkManager.Instance.localPlayerController != (Object)null) { PlayerControllerB localPlayerController = GameNetworkManager.Instance.localPlayerController; if (((NetworkBehaviour)localPlayerController).IsOwner && localPlayerController.isPlayerDead && !StartOfRound.Instance.shipIsLeaving && (!((NetworkBehaviour)localPlayerController).IsServer || localPlayerController.isHostPlayerObject)) { ToggleSpectatingMode(localPlayerController); } } } private void OnMenuKeyPressed(CallbackContext context) { if (((CallbackContext)(ref context)).performed && (Object)(object)GameNetworkManager.Instance != (Object)null && (Object)(object)GameNetworkManager.Instance.localPlayerController != (Object)null) { PlayerControllerB localPlayerController = GameNetworkManager.Instance.localPlayerController; if (((NetworkBehaviour)localPlayerController).IsOwner && localPlayerController.isPlayerDead && !StartOfRound.Instance.shipIsLeaving && (!((NetworkBehaviour)localPlayerController).IsServer || localPlayerController.isHostPlayerObject)) { Toggle(); } } } private void OnFlashlightKeyPressed(CallbackContext context) { if (!((CallbackContext)(ref context)).performed || !((Object)(object)GameNetworkManager.Instance != (Object)null) || !((Object)(object)GameNetworkManager.Instance.localPlayerController != (Object)null)) { return; } PlayerControllerB localPlayerController = GameNetworkManager.Instance.localPlayerController; if ((Object)(object)HUDManager.Instance != (Object)null && ((NetworkBehaviour)localPlayerController).IsOwner && localPlayerController.isPlayerDead && !StartOfRound.Instance.shipIsLeaving && (!((NetworkBehaviour)localPlayerController).IsServer || localPlayerController.isHostPlayerObject)) { Light component = ((Component)HUDManager.Instance.playersManager.spectateCamera).GetComponent(); if ((Object)(object)component != (Object)null) { ((Behaviour)component).enabled = !((Behaviour)component).enabled; } } } private void OnZoomOutPressed(CallbackContext context) { if (((CallbackContext)(ref context)).performed && SpectatingEnemies) { ZoomLevel += 0.1f; if (ZoomLevel > 10f) { ZoomLevel = 10f; } } } private void OnZoomInPressed(CallbackContext context) { if (((CallbackContext)(ref context)).performed && SpectatingEnemies) { ZoomLevel -= 0.1f; if (ZoomLevel < 1f) { ZoomLevel = 1f; } } } private void LateUpdate() { //IL_0101: Unknown result type (might be due to invalid IL or missing references) //IL_0266: Unknown result type (might be due to invalid IL or missing references) //IL_0277: Unknown result type (might be due to invalid IL or missing references) if (!SpectatingEnemies) { return; } if (SpectatorList.Length == 0) { SpectatingEnemies = false; return; } Spectatable obj = SpectatorList.ElementAtOrDefault(SpectatedEnemyIndex); if ((Object)(object)obj == (Object)null) { GetNextValidSpectatable(); return; } if ((obj.type == SpectatableType.Enemy || obj.type == SpectatableType.Masked || obj.type == SpectatableType.GhostGirl) && (Object)(object)obj.enemyInstance != (Object)null && obj.enemyInstance.isEnemyDead) { GetNextValidSpectatable(); return; } Vector3? spectatePosition = GetSpectatePosition(obj); if (!spectatePosition.HasValue) { GetNextValidSpectatable(); return; } if (obj.enemyName == "Enemy") { TryFixName(ref obj); } GameNetworkManager.Instance.localPlayerController.spectateCameraPivot.position = spectatePosition.Value; if (obj.type == SpectatableType.Masked && obj.maskedName != string.Empty) { ((TMP_Text)HUDManager.Instance.spectatingPlayerText).text = $"(Spectating: {obj.maskedName}) [{ZoomLevel:F1}x]"; } else if (obj.type == SpectatableType.GhostGirl) { DressGirlAI component = ((Component)obj).gameObject.GetComponent(); ((EnemyAI)component).EnableEnemyMesh(true, true, true); PlayerControllerB targetPlayer = ((EnemyAI)component).targetPlayer; if ((Object)(object)targetPlayer != (Object)null) { ((TMP_Text)HUDManager.Instance.spectatingPlayerText).text = $"(Spectating: {obj.maskedName}) [{ZoomLevel:F1}x]\n(Targeting: {targetPlayer.playerUsername})"; } else { ((TMP_Text)HUDManager.Instance.spectatingPlayerText).text = $"(Spectating: {obj.maskedName}) [{ZoomLevel:F1}x]\n(No Target)"; } } else { ((TMP_Text)HUDManager.Instance.spectatingPlayerText).text = $"(Spectating: {obj.enemyName}) [{ZoomLevel:F1}x]"; } Plugin.raycastSpectate.Invoke(GameNetworkManager.Instance.localPlayerController, Array.Empty()); ((Component)((Component)GameNetworkManager.Instance.localPlayerController.spectateCameraPivot).GetComponentInChildren()).transform.localPosition = Vector3.back * (ZoomLevel + 0.5f); } private Vector3? GetSpectatePosition(Spectatable obj) { //IL_00c6: Unknown result type (might be due to invalid IL or missing references) //IL_00a0: Unknown result type (might be due to invalid IL or missing references) //IL_0057: Unknown result type (might be due to invalid IL or missing references) //IL_004a: Unknown result type (might be due to invalid IL or missing references) if (obj.type == SpectatableType.Enemy || obj.type == SpectatableType.Masked || obj.type == SpectatableType.GhostGirl) { EnemyAI enemyInstance = obj.enemyInstance; if ((Object)(object)enemyInstance != (Object)null) { return ((Object)(object)enemyInstance.eye == (Object)null) ? ((Component)enemyInstance).transform.position : enemyInstance.eye.position; } } else if (obj.type == SpectatableType.Turret) { Turret component = ((Component)obj).GetComponent(); if ((Object)(object)component != (Object)null) { return ((Component)component.centerPoint).transform.position; } } else { if (obj.type == SpectatableType.Landmine) { return ((Component)obj).transform.position; } Debug.LogError((object)("[SpectateEnemy]: Error when spectating: no handler for SpectatableType " + obj.type)); } return null; } private void TryFixName(ref Spectatable obj) { MaskedPlayerEnemy val = default(MaskedPlayerEnemy); EnemyAI val2 = default(EnemyAI); Turret val3 = default(Turret); Landmine val4 = default(Landmine); if (((Component)obj).gameObject.TryGetComponent(ref val)) { if ((Object)(object)val.mimickingPlayer != (Object)null) { obj.enemyName = val.mimickingPlayer.playerUsername; } else { obj.enemyName = ((EnemyAI)val).enemyType.enemyName; } } else if (((Component)obj).gameObject.TryGetComponent(ref val2)) { obj.enemyName = val2.enemyType.enemyName; } else if (((Component)obj).gameObject.TryGetComponent(ref val3)) { obj.enemyName = "Turret"; } else if (((Component)obj).gameObject.TryGetComponent(ref val4)) { obj.enemyName = "Landmine"; } } public void ToggleSpectatingMode(PlayerControllerB __instance) { //IL_00da: Unknown result type (might be due to invalid IL or missing references) //IL_00ea: Unknown result type (might be due to invalid IL or missing references) //IL_00ef: Unknown result type (might be due to invalid IL or missing references) //IL_00f4: Unknown result type (might be due to invalid IL or missing references) SpectatingEnemies = !SpectatingEnemies; if (SpectatingEnemies) { SpectatorList = (from x in Object.FindObjectsByType((FindObjectsSortMode)0) where GetSetting(SanitizeEnemyName(x.enemyName)) select x).ToArray(); if (SpectatorList.Length == 0) { SpectatingEnemies = false; Plugin.displaySpectatorTip.Invoke(HUDManager.Instance, new object[1] { "No enemies to spectate" }); return; } if (SpectatedEnemyIndex == -1 || SpectatedEnemyIndex >= SpectatorList.Length) { if ((Object)(object)__instance.spectatedPlayerScript == (Object)null) { GetNextValidSpectatable(); } else { float num = 999999f; int spectatedEnemyIndex = 0; for (int i = 0; i < SpectatorList.Length; i++) { Vector3 val = ((Component)SpectatorList[i]).transform.position - ((Component)__instance.spectatedPlayerScript).transform.position; float sqrMagnitude = ((Vector3)(ref val)).sqrMagnitude; if (sqrMagnitude < num * num) { num = sqrMagnitude; spectatedEnemyIndex = i; } } SpectatedEnemyIndex = spectatedEnemyIndex; } } __instance.spectatedPlayerScript = null; } else { __instance.spectatedPlayerScript = ((IEnumerable)__instance.playersManager.allPlayerScripts).FirstOrDefault((Func)((PlayerControllerB x) => !x.isPlayerDead && x.isPlayerControlled)); ((TMP_Text)HUDManager.Instance.spectatingPlayerText).text = "(Spectating: " + __instance.spectatedPlayerScript.playerUsername + ")"; } } public void PopulateSettings() { EnemyType[] array = Resources.FindObjectsOfTypeAll(); EnemyType[] array2 = array; foreach (EnemyType val in array2) { if (!(val.enemyName == "Red pill") && !(val.enemyName == "Lasso")) { string text = SanitizeEnemyName(val.enemyName); settings.TryAdd(text, Plugin.Configuration.Bind("Enemies", text, !val.isDaytimeEnemy, "Enables spectating " + text)); } } settings.TryAdd("Landmine", Plugin.Configuration.Bind("Enemies", "Landmine", false, "Enables spectating Landmines")); settings.TryAdd("Turret", Plugin.Configuration.Bind("Enemies", "Turret", false, "Enables spectating Turrets")); Debug.LogWarning((object)"[SpectateEnemies]: Config loaded"); AssertSettings(); } public bool SpectateNextEnemy() { if (SpectatorList.Length == 0) { SpectatingEnemies = false; return true; } GetNextValidSpectatable(); return false; } private string SanitizeEnemyName(string enemyName) { return enemyName.Replace("\\", "").Replace("\"", "").Replace("'", "") .Replace("[", "") .Replace("]", ""); } private void GetNextValidSpectatable() { SpectatorList = (from x in Object.FindObjectsByType((FindObjectsSortMode)0) where GetSetting(SanitizeEnemyName(x.enemyName)) select x).ToArray(); int num = 0; int num2 = SpectatedEnemyIndex; while (num < SpectatorList.Length) { num2++; if (num2 >= SpectatorList.Length) { num2 = 0; } Spectatable spectatable = SpectatorList.ElementAtOrDefault(num2); if ((Object)(object)spectatable != (Object)null) { if ((spectatable.type == SpectatableType.Enemy || spectatable.type == SpectatableType.Masked || spectatable.type == SpectatableType.GhostGirl) && (Object)(object)spectatable.enemyInstance != (Object)null && spectatable.enemyInstance.isEnemyDead) { num++; continue; } if (settings.ContainsKey(SanitizeEnemyName(spectatable.enemyName))) { SpectatedEnemyIndex = num2; return; } } num++; } SpectatingEnemies = false; Plugin.displaySpectatorTip.Invoke(HUDManager.Instance, new object[1] { "No enemies to spectate" }); } private void AssertSettings() { foreach (KeyValuePair> setting in settings) { Debug.LogWarning((object)$"{setting.Key} : {setting.Value.Value}"); } } public bool GetSetting(string name) { if (settings.ContainsKey(name)) { return settings[name].Value; } return false; } public void Toggle() { WindowOpen = !WindowOpen; } public void Hide() { WindowOpen = false; } public bool IsMenuOpen() { return WindowOpen; } private void OnGUI() { //IL_000c: 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_0026: Unknown result type (might be due to invalid IL or missing references) //IL_0035: Expected O, but got Unknown //IL_0030: 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) if (WindowOpen) { GUI.color = Color.gray; window = GUI.Window(0, window, new WindowFunction(DrawGUI), "Spectator Settings"); } } private void DrawGUI(int windowID) { //IL_0135: 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_0028: Unknown result type (might be due to invalid IL or missing references) //IL_0041: Unknown result type (might be due to invalid IL or missing references) //IL_0048: Unknown result type (might be due to invalid IL or missing references) //IL_004d: Unknown result type (might be due to invalid IL or missing references) //IL_0066: Unknown result type (might be due to invalid IL or missing references) //IL_00c5: Unknown result type (might be due to invalid IL or missing references) if (windowID == 0) { scrollPos = GUI.BeginScrollView(new Rect(5f, 20f, 490f, 370f), scrollPos, new Rect(5f, 20f, 490f, 370f), false, true); GUI.Label(new Rect(10f, 30f, 500f, 100f), "Tip: Checking the box next to an enemy name will enable spectating it."); int num = 0; int num2 = 0; foreach (string item in settings.Keys.ToList()) { settings[item].Value = GUI.Toggle(new Rect((float)(10 + 150 * num), (float)(60 + 30 * num2), 150f, 20f), settings[item].Value, item); num++; if (num == 3) { num = 0; num2++; } } GUI.EndScrollView(true); } GUI.DragWindow(new Rect(0f, 0f, 10000f, 10000f)); } } public class SpectateEnemiesAPI { public static bool IsLoaded => (Object)(object)SpectateEnemies.Instance != (Object)null; public static bool IsSpectatingEnemies => SpectateEnemies.Instance.SpectatingEnemies; public static GameObject CurrentEnemySpectating() { if (IsSpectatingEnemies && SpectateEnemies.Instance.SpectatedEnemyIndex > -1) { return ((Component)SpectateEnemies.Instance.SpectatorList[SpectateEnemies.Instance.SpectatedEnemyIndex]).gameObject; } return null; } } public static class MyPluginInfo { public const string PLUGIN_GUID = "SpectateEnemy"; public const string PLUGIN_NAME = "SpectateEnemy"; public const string PLUGIN_VERSION = "2.8.0"; } } namespace SpectateEnemy.Patches { [HarmonyPatch(typeof(DressGirlAI), "Start")] internal class DressGirlAI_Patches { private static void Postfix(DressGirlAI __instance) { Spectatable spectatable = ((Component)__instance).gameObject.GetComponent(); if ((Object)(object)spectatable == (Object)null) { spectatable = ((Component)__instance).gameObject.AddComponent(); spectatable.enemyName = ((EnemyAI)__instance).enemyType.enemyName; spectatable.enemyInstance = (EnemyAI)(object)__instance; } spectatable.type = SpectatableType.GhostGirl; } } [HarmonyPatch(typeof(EnemyAI), "Start")] internal class EnemyAI_Patches { private static void Postfix(EnemyAI __instance) { Spectatable spectatable = ((Component)__instance).gameObject.AddComponent(); spectatable.enemyName = __instance.enemyType.enemyName; spectatable.enemyInstance = __instance; } } [HarmonyPatch(typeof(GameNetworkManager), "Disconnect")] internal class GameNetworkManager_Disconnect { private static void Postfix() { if ((Object)(object)SpectateEnemies.Instance != (Object)null) { SpectateEnemies.Instance.SpectatedEnemyIndex = -1; SpectateEnemies.Instance.SpectatingEnemies = false; SpectateEnemies.Instance.Hide(); } } } [HarmonyPatch(typeof(GameNetworkManager), "OnApplicationQuit")] internal class GameNetworkManager_Quit { private static void Prefix() { if ((Object)(object)SpectateEnemies.Instance != (Object)null) { Plugin.Configuration.Save(); Debug.LogWarning((object)"[SpectateEnemies]: Config saved"); } } } [HarmonyPatch(typeof(HUDManager), "Update")] internal class HUDManager_Patches { private static void Postfix(HUDManager __instance) { //IL_009d: Unknown result type (might be due to invalid IL or missing references) //IL_00a2: Unknown result type (might be due to invalid IL or missing references) //IL_00a7: Unknown result type (might be due to invalid IL or missing references) //IL_00ac: Unknown result type (might be due to invalid IL or missing references) //IL_00c7: Unknown result type (might be due to invalid IL or missing references) //IL_00cc: Unknown result type (might be due to invalid IL or missing references) //IL_00d1: Unknown result type (might be due to invalid IL or missing references) //IL_00d6: Unknown result type (might be due to invalid IL or missing references) //IL_00f2: Unknown result type (might be due to invalid IL or missing references) //IL_00f7: Unknown result type (might be due to invalid IL or missing references) //IL_00fc: Unknown result type (might be due to invalid IL or missing references) //IL_0101: Unknown result type (might be due to invalid IL or missing references) //IL_011d: Unknown result type (might be due to invalid IL or missing references) //IL_0122: Unknown result type (might be due to invalid IL or missing references) //IL_0127: Unknown result type (might be due to invalid IL or missing references) //IL_012c: Unknown result type (might be due to invalid IL or missing references) //IL_0148: 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_0152: Unknown result type (might be due to invalid IL or missing references) //IL_0157: Unknown result type (might be due to invalid IL or missing references) if (!((Object)(object)GameNetworkManager.Instance.localPlayerController != (Object)null) || !((Object)(object)GameNetworkManager.Instance.localPlayerController != (Object)null)) { return; } PlayerControllerB localPlayerController = GameNetworkManager.Instance.localPlayerController; if (!localPlayerController.isPlayerDead) { return; } if (StartOfRound.Instance.shipIsLeaving) { SpectateEnemies.Instance.Hide(); Light component = ((Component)__instance.playersManager.spectateCamera).GetComponent(); if ((Object)(object)component != (Object)null) { ((Behaviour)component).enabled = false; } return; } InputBinding val = Plugin.Inputs.SwapKey.bindings[0]; string text = InputControlPath.ToHumanReadableString(((InputBinding)(ref val)).effectivePath, (HumanReadableStringOptions)2, (InputControl)null); val = Plugin.Inputs.MenuKey.bindings[0]; string text2 = InputControlPath.ToHumanReadableString(((InputBinding)(ref val)).effectivePath, (HumanReadableStringOptions)2, (InputControl)null); val = Plugin.Inputs.FlashlightKey.bindings[0]; string text3 = InputControlPath.ToHumanReadableString(((InputBinding)(ref val)).effectivePath, (HumanReadableStringOptions)2, (InputControl)null); val = Plugin.Inputs.ZoomOutKey.bindings[0]; string text4 = InputControlPath.ToHumanReadableString(((InputBinding)(ref val)).effectivePath, (HumanReadableStringOptions)2, (InputControl)null); val = Plugin.Inputs.ZoomInKey.bindings[0]; string text5 = InputControlPath.ToHumanReadableString(((InputBinding)(ref val)).effectivePath, (HumanReadableStringOptions)2, (InputControl)null); if (!SpectateEnemies.Instance.HideControls.Value) { if (SpectateEnemies.Instance.SpectatingEnemies) { TextMeshProUGUI holdButtonToEndGameEarlyText = __instance.holdButtonToEndGameEarlyText; ((TMP_Text)holdButtonToEndGameEarlyText).text = ((TMP_Text)holdButtonToEndGameEarlyText).text + "\n\n\n\n\nSpectate Players : [" + text + "]\nFlashlight : [" + text3 + "]\nZoom Out : [" + text4 + "]\nZoom In : [" + text5 + "]\nConfig Menu : [" + text2 + "]"; } else { TextMeshProUGUI holdButtonToEndGameEarlyText = __instance.holdButtonToEndGameEarlyText; ((TMP_Text)holdButtonToEndGameEarlyText).text = ((TMP_Text)holdButtonToEndGameEarlyText).text + "\n\n\n\n\nSpectate Enemies : [" + text + "]\nFlashlight : [" + text3 + "]\nConfig Menu : [" + text2 + "]"; } } } } [HarmonyPatch(typeof(Landmine), "Start")] internal class Landmine_Patches { private static void Postfix(Landmine __instance) { Spectatable spectatable = ((Component)__instance).gameObject.AddComponent(); spectatable.type = SpectatableType.Landmine; spectatable.enemyName = "Landmine"; } } [HarmonyPatch(typeof(MaskedPlayerEnemy), "Start")] internal class MaskedPlayerEnemy_Patches { private static void Postfix(MaskedPlayerEnemy __instance) { Spectatable spectatable = ((Component)__instance).gameObject.AddComponent(); spectatable.type = SpectatableType.Masked; spectatable.enemyName = ((EnemyAI)__instance).enemyType.enemyName; if ((Object)(object)__instance.mimickingPlayer != (Object)null) { spectatable.maskedName = __instance.mimickingPlayer.playerUsername; } spectatable.enemyInstance = (EnemyAI)(object)__instance; } } [HarmonyPatch(typeof(PlayerControllerB), "ActivateItem_performed")] internal class PlayerControllerB_Use { private static bool Prefix(PlayerControllerB __instance) { if (((NetworkBehaviour)__instance).IsOwner && __instance.isPlayerDead && !StartOfRound.Instance.shipIsLeaving && (!((NetworkBehaviour)__instance).IsServer || __instance.isHostPlayerObject)) { if (SpectateEnemies.Instance.IsMenuOpen()) { return false; } if (SpectateEnemies.Instance.SpectatingEnemies) { SpectateEnemies.Instance.SpectateNextEnemy(); } return true; } return true; } } [HarmonyPatch(typeof(PlayerControllerB), "SpectateNextPlayer")] internal class PlayerControllerB_SpectateNext { private static bool Prefix() { return !SpectateEnemies.Instance.SpectatingEnemies; } } [HarmonyPatch(typeof(QuickMenuManager), "Start")] internal class QuickMenuManager_Patches { private static void Postfix() { //IL_0016: Unknown result type (might be due to invalid IL or missing references) //IL_001c: Expected O, but got Unknown if ((Object)(object)SpectateEnemies.Instance == (Object)null) { GameObject val = new GameObject("SpectateEnemiesObject"); SpectateEnemies spectateEnemies = val.AddComponent(); spectateEnemies.PopulateSettings(); } } } [HarmonyPatch(typeof(StartOfRound), "ShipLeave")] internal class StartOfRound_Patches { private static void Postfix() { SpectateEnemies.Instance.SpectatedEnemyIndex = -1; SpectateEnemies.Instance.SpectatingEnemies = false; SpectateEnemies.Instance.Hide(); } } [HarmonyPatch(typeof(Turret), "Start")] internal class Turret_Patches { private static void Postfix(Turret __instance) { Spectatable spectatable = ((Component)__instance).gameObject.AddComponent(); spectatable.type = SpectatableType.Turret; spectatable.enemyName = "Turret"; } } } namespace __GEN { internal class NetworkVariableSerializationHelper { [RuntimeInitializeOnLoadMethod] internal static void InitializeSerialization() { } } } namespace SpectateEnemy.NetcodePatcher { [AttributeUsage(AttributeTargets.Module)] internal class NetcodePatchedAssemblyAttribute : Attribute { } }