Decompiled source of Prop Hunt v1.0.1
PropHuntMod.dll
Decompiled 2 weeks ago
The result has been truncated due to the large size, download it to view full contents!
using System; using System.CodeDom.Compiler; using System.Collections; using System.Collections.Generic; using System.ComponentModel; using System.Configuration; using System.Diagnostics; using System.Globalization; using System.IO; using System.Linq; using System.Reflection; using System.Resources; using System.Runtime.CompilerServices; using System.Runtime.InteropServices; using System.Runtime.Versioning; using System.Text.RegularExpressions; using System.Timers; using BepInEx; using BepInEx.Configuration; using BepInEx.Logging; using GlobalEnums; using HarmonyLib; using InControl; using Microsoft.CodeAnalysis; using Newtonsoft.Json; using NoRepeat; using PropHuntMod.Commands; using PropHuntMod.Modifications; using PropHuntMod.Server; using PropHuntMod.Utils; using PropHuntMod.Utils.Networking; using PropHuntMod.Utils.Networking.FromClient; using PropHuntMod.Utils.Networking.FromServer; using SSMP.Api.Client; using SSMP.Api.Client.Networking; using SSMP.Api.Command; using SSMP.Api.Command.Client; using SSMP.Api.Command.Server; using SSMP.Api.Server; using SSMP.Api.Server.Networking; using SSMP.Game.Settings; using SSMP.Networking.Packet; using SSMP.Networking.Packet.Data; using TeamCherry.Localization; using UnityEngine; using UnityEngine.EventSystems; using UnityEngine.SceneManagement; using UnityEngine.UI; [assembly: CompilationRelaxations(8)] [assembly: RuntimeCompatibility(WrapNonExceptionThrows = true)] [assembly: Debuggable(DebuggableAttribute.DebuggingModes.IgnoreSymbolStoreSequencePoints)] [assembly: AssemblyTitle("PropHuntMod")] [assembly: AssemblyDescription("")] [assembly: AssemblyConfiguration("")] [assembly: AssemblyCompany("")] [assembly: AssemblyProduct("PropHuntMod")] [assembly: AssemblyCopyright("Copyright © 2025")] [assembly: AssemblyTrademark("")] [assembly: ComVisible(false)] [assembly: Guid("ea9e15ba-4504-4c36-baa6-8f85bee1da18")] [assembly: AssemblyFileVersion("1.0.0.0")] [assembly: TargetFramework(".NETFramework,Version=v4.8", FrameworkDisplayName = ".NET Framework 4.8")] [assembly: AssemblyVersion("1.0.0.0")] 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; } } } namespace NoRepeat { public class NoRepeat<T> { private readonly Random random = new Random(); public List<T> used { get; private set; } public List<T> inputValues { get; private set; } public NoRepeat(List<T> values) { inputValues = values; used = new List<T>(); } public T GetRandom() { if (used.Count == 0 && inputValues.Count <= 1) { if (inputValues.Count == 0) { return default(T); } return inputValues[0]; } int index = random.Next(inputValues.Count); T val = inputValues[index]; inputValues.RemoveAt(index); if (inputValues.Count == 0) { inputValues.AddRange(used); used = new List<T>(); Log.LogInfo("Resetting NoRepeat"); } used.Add(val); return val; } public T GetSpecific(Func<T, bool> func) { T val = inputValues.FirstOrDefault(func); if (val != null) { return val; } return used.FirstOrDefault(func); } } } namespace PropHuntMod { public enum Teams { Hunter = 4, Seeker = 3 } public class PropHuntClient : ClientAddon { public static GameState GameState; public static bool isSeeker; public static ushort propSwaps; public static ushort maxPropSwaps; protected override string Name => "Prop Hunt"; protected override string Version => "1.0.1"; public override uint ApiVersion => 1u; public override bool NeedsNetwork => true; public override void Initialize(IClientApi clientApi) { PropHuntMod.Initialize(clientApi); Log.LogInfo("Prop Hunt Loaded."); ClientNetwork.Init(clientApi, (ClientAddon)(object)this); clientApi.ClientManager.ConnectEvent += delegate { string[] array = new string[4] { "Prop Hunt Commands:", "/hunt: starts a round", "/stop: stops a round", "/sync: syncs other player's props" }; for (int i = 0; i < array.Length; i++) { LocalMessage(array[i]); } }; clientApi.ClientManager.DisconnectEvent += delegate { GameState = GameState.NotStarted; isSeeker = false; propSwaps = 0; maxPropSwaps = 0; PropHuntMod.playerManager.Clear(); PropHuntServer.instance.Reset(disconnect: true); }; clientApi.ClientManager.PlayerConnectEvent += delegate(IClientPlayer player) { Log.LogInfo("Player " + player.Username + " connected"); PlayerManager.GetPlayerManager(player.Id); }; clientApi.ClientManager.PlayerDisconnectEvent += delegate(IClientPlayer player) { Log.LogInfo("Player " + player.Username + " disconnected"); PropHuntMod.playerManager.Remove(player.Id); }; clientApi.ClientManager.PlayerEnterSceneEvent += delegate(IClientPlayer player) { Log.LogInfo("Player " + player.Username + " entered your scene"); PlayerManager playerManager = PlayerManager.GetPlayerManager(player.Id); playerManager.hornetManager.SetHornet(); playerManager.EnsurePropCover(); }; ((ICommandManager<IClientCommand>)(object)clientApi.CommandManager).RegisterCommand((IClientCommand)(object)new ShowHitboxes()); ((ICommandManager<IClientCommand>)(object)clientApi.CommandManager).RegisterCommand((IClientCommand)(object)new global::PropHuntMod.Commands.Sync()); } public static void LocalMessage(string message) { PropHuntMod.client.UiManager.ChatBox.AddMessage(message); } } public class PropHuntServer : ServerAddon { public static PropHuntServer instance; public static GameState GameState = GameState.NotStarted; private static readonly Dictionary<ushort, ServerPlayer> players = new Dictionary<ushort, ServerPlayer>(); internal static IServerApi _serverApi = null; protected override string Name => "Prop Hunt"; protected override string Version => "1.0.1"; public override uint ApiVersion => 1u; public override bool NeedsNetwork => true; public SeekerTimer SeekerTimer { get; private set; } public override void Initialize(IServerApi serverApi) { instance = this; _serverApi = serverApi; ((ServerAddon)this).Logger.Info("Prop Hunt Loaded."); Reset(); ServerNetwork.Init(serverApi, (ServerAddon)(object)this); ((ICommandManager<IServerCommand>)(object)serverApi.CommandManager).RegisterCommand((IServerCommand)(object)new StartGameCommand()); ((ICommandManager<IServerCommand>)(object)serverApi.CommandManager).RegisterCommand((IServerCommand)(object)new StopGameCommand()); serverApi.ServerManager.PlayerConnectEvent += delegate(IServerPlayer player) { ServerPlayer player2 = GetPlayer(player.Id); if (GameState == GameState.SeekerWait) { player2.seeker = true; ServerNetwork.SendRoundStart(player.Id, GameState == GameState.Playing); } }; serverApi.ServerManager.PlayerDisconnectEvent += delegate(IServerPlayer player) { Log.LogInfo($"Player {player} disconnected"); players.Remove(player.Id); CheckGameOver(player); }; } public void Reset(bool disconnect = false) { Log.LogInfo("Resetting server"); GameState = GameState.NotStarted; SeekerTimer?.CancelTimer(); SeekerTimer = null; if (disconnect) { foreach (IServerPlayer player in _serverApi.ServerManager.Players) { _serverApi.ServerManager.DisconnectPlayer(player.Id, (DisconnectReason)0); } } players.Clear(); } internal static ServerPlayer GetPlayer(ushort playerID) { if (!players.TryGetValue(playerID, out var value)) { value = new ServerPlayer(playerID); players.Add(playerID, value); } return value; } public void Announce(string announcement) { Log.LogInfo("Announcement: " + announcement); _serverApi.ServerManager.BroadcastMessage(announcement); } public void Message(ushort recipientID, string message) { Log.LogInfo($"Message to {recipientID}: {message}"); _serverApi.ServerManager.SendMessage(recipientID, message); } public string DetermineWinner() { string text = null; foreach (ServerPlayer value in players.Values) { if (!string.IsNullOrEmpty(value.propName)) { if (text != null) { return null; } text = value.PlayerAvatar.Username; } } return text; } private void PickSeekers(int count = 1) { count = Mathf.Clamp(count, 1, players.Count - 1); Log.LogInfo($"Choosing {count} seekers"); for (int i = 0; i < count; i++) { List<ServerPlayer> list = players.Values.Where((ServerPlayer p) => !p.seeker).ToList(); if (list.Count == 0) { Log.LogInfo($"Ran out of seekers to choose (Picked {i}/{count})"); break; } ServerPlayer randomElement = Extensions.GetRandomElement<ServerPlayer>(list); randomElement.seeker = true; Log.LogDebug(randomElement.PlayerAvatar.Username + " is a seeker"); } } private void ResetPlayers() { //IL_003e: Unknown result type (might be due to invalid IL or missing references) //IL_0043: Unknown result type (might be due to invalid IL or missing references) foreach (ServerPlayer value in players.Values) { value.seeker = false; value.swapCount = 0; value.propName = ""; value.propRotation = 0f; value.propLocation = Vector3.zero; value.hidden = false; } } public void GameStart() { if (players.Count < 2) { Announce("...Well that's awkward. I can't start a game without two people!"); return; } ResetPlayers(); PickSeekers(); EnsureSettings(); GameState = GameState.SeekerWait; int num = 30; Announce($"The game has begun! Hiders have a {num} second head start. Good luck!"); SeekerTimer = new SeekerTimer(num); ServerNetwork.BroadcastRoundStart(); } public void CheckGameOver(IServerPlayer playerHit, bool canceled = false) { if (GameState != 0 && (players.Values.All((ServerPlayer p) => string.IsNullOrEmpty(p.propName)) || canceled)) { ServerNetwork.BroadcastGameOver(playerHit, canceled); if (canceled) { Announce("The game has been stopped early!"); SeekerTimer?.CancelTimer(); } else { Announce(playerHit.Username + " was the last bug standing! Congrats!"); } GameState = GameState.NotStarted; ResetPlayers(); } } private void EnsureSettings() { //IL_0011: Unknown result type (might be due to invalid IL or missing references) //IL_0016: 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_002e: Unknown result type (might be due to invalid IL or missing references) //IL_003a: Unknown result type (might be due to invalid IL or missing references) //IL_0046: 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_0055: Expected O, but got Unknown IServerSettings serverSettings = ((ServerAddon)this).ServerApi.ServerManager.ServerSettings; ServerSettings val = new ServerSettings { AllowSkins = serverSettings.AllowSkins, DisplayNames = serverSettings.DisplayNames, OnlyBroadcastMapIconWithCompass = serverSettings.OnlyBroadcastMapIconWithCompass, TeamsEnabled = serverSettings.TeamsEnabled, AlwaysShowMapIcons = false, IsPvpEnabled = false }; ((ServerAddon)this).ServerApi.ServerManager.ApplyServerSettings(val); } } [BepInPlugin("com.bobbythecatfish.prophunt", "Prop Hunt", "1.0.1")] [BepInDependency(/*Could not decode attribute arguments.*/)] [BepInDependency(/*Could not decode attribute arguments.*/)] [BepInProcess("Hollow Knight Silksong.exe")] public class PropHuntMod : BaseUnityPlugin { internal static PropHuntMod Instance; internal SelfHornetManager hornet = new SelfHornetManager(); internal SelfCoverManager cover = new SelfCoverManager(); private static readonly NoDamage noDamage = new NoDamage(); private static PropMovementControls movement; internal static Dictionary<ushort, PlayerManager> playerManager = new Dictionary<ushort, PlayerManager>(); internal static IClientApi client; internal static bool modEnabled = false; internal static bool showHitboxes = false; internal static string CurrentScene; internal static string PreviousScene; internal static int SceneTransitionTicket = -1; internal static List<Action> nextFrameActions = new List<Action>(); private static List<Action> _nextFrames = new List<Action>(); private int logged; private void Awake() { Instance = this; Config.LoadConfig(((BaseUnityPlugin)this).Config); Log.SetLogger(((BaseUnityPlugin)this).Logger); ClientAddon.RegisterAddon((ClientAddon)(object)new PropHuntClient()); ServerAddon.RegisterAddon((ServerAddon)(object)new PropHuntServer()); } public static void Initialize(IClientApi clientApi) { Log.LogInfo("Prop Hunt mod Loaded."); client = clientApi; Harmony.CreateAndPatchAll(typeof(PropHuntMod), "prophunt"); Harmony.CreateAndPatchAll(typeof(NoDamage), "prophunt"); Harmony.CreateAndPatchAll(typeof(BaseCoverManager), "prophunt"); modEnabled = true; } public static void Unload() { Harmony.UnpatchID("prophunt"); modEnabled = false; } private bool IsInputDisabled() { //IL_0028: Unknown result type (might be due to invalid IL or missing references) //IL_002e: Invalid comparison between Unknown and I4 HeroController instance = HeroController.instance; if (instance != null && instance.IsInputBlocked() && PropMovementControls.MovementState == MovementState.Normal) { return true; } GameManager silentInstance = GameManager.SilentInstance; if (silentInstance != null && (int)silentInstance.GameState == 1) { return true; } GameObject currentSelectedGameObject = EventSystem.current.currentSelectedGameObject; if ((Object)(object)currentSelectedGameObject != (Object)null) { InputField component = currentSelectedGameObject.GetComponent<InputField>(); if (component != null && ((Component)component).gameObject.activeInHierarchy) { return true; } } return false; } private void Update() { //IL_0108: Unknown result type (might be due to invalid IL or missing references) //IL_011f: Unknown result type (might be due to invalid IL or missing references) //IL_0136: Unknown result type (might be due to invalid IL or missing references) if (!modEnabled) { return; } if (_nextFrames.Count > 0) { Log.LogInfo($"Executing {_nextFrames.Count} late actions"); foreach (Action nextFrame in _nextFrames) { nextFrame(); } _nextFrames.Clear(); } if ((Object)(object)hornet.hornet != (Object)null) { hornet.EnsureHornetHidden(); } if ((Object)(object)hornet.hornet == (Object)null) { return; } movement?.Update(); if (IsInputDisabled()) { if (logged == 0) { Log.LogInfo("Input blocked"); } logged = 1; return; } if (logged == 1) { Log.LogInfo("Input restored"); logged = 0; } if (Input.GetKeyDown(Config.HideHornetKey)) { hornet.ToggleHornet(); } if (Input.GetKeyDown(Config.SwapPropKey)) { cover.EnableRandomProp(); } if (Input.GetKeyDown(Config.ResetKey)) { cover.DisableProp(hornet); } } private void LateUpdate() { if (nextFrameActions.Count > 0) { Log.LogInfo($"Adding {nextFrameActions.Count} actions"); _nextFrames = nextFrameActions.ToList(); nextFrameActions.Clear(); } } [HarmonyPrefix] [HarmonyPatch(typeof(SceneLoad), "Begin")] internal static void OnSceneChange(SceneLoad __instance) { //IL_000d: Unknown result type (might be due to invalid IL or missing references) //IL_0013: Invalid comparison between Unknown and I4 if (modEnabled && (int)GameManager.SilentInstance.GameState != 1) { if (movement == null) { movement = new PropMovementControls(); } SelfCoverManager.instance.DisableProp(logOnFail: false, isSceneChange: true); PreviousScene = CurrentScene; CurrentScene = __instance.TargetSceneName; PropValidation.ResetProps(); } } [HarmonyPostfix] [HarmonyPatch(typeof(GameManager), "OnNextLevelReady")] internal static void OnNextLevelReady() { //IL_000d: Unknown result type (might be due to invalid IL or missing references) //IL_0013: Invalid comparison between Unknown and I4 if (!modEnabled || (int)GameManager.SilentInstance.GameState == 1) { return; } PropValidation.GetAllProps(); if (PropHuntClient.GameState != 0 && !PropHuntClient.isSeeker) { if (SceneTransitionTicket != -1) { ClientErrorCorrection.RestoreLastProp(new FailedAction { AffectedID = 0, BypassTicketID = SceneTransitionTicket, FailedPacket = CustomPackets.PropSwap, FixMethod = CorrectionActions.PreviousScene }); SceneTransitionTicket = -1; } else { SelfCoverManager.instance.EnableRandomProp(); } } } [HarmonyPrefix] [HarmonyPatch(typeof(Breakable), "Break")] public static void OnBreak(Breakable __instance) { } } } namespace PropHuntMod.Utils { internal static class Log { private static ManualLogSource logger; public static void SetLogger(ManualLogSource log) { logger = log; } public static void LogInfo(params object[] data) { foreach (object obj in data) { logger.LogInfo(obj); } } public static void LogWarning(params object[] data) { foreach (object obj in data) { logger.LogWarning(obj); } } public static void LogError(params object[] data) { foreach (object obj in data) { logger.LogError(obj); } } public static void LogFatal(params object[] data) { foreach (object obj in data) { logger.LogFatal(obj); } } public static void LogDebug(params object[] data) { foreach (object obj in data) { logger.LogDebug(obj); } } public static void LogMessage(params object[] data) { foreach (object obj in data) { logger.LogMessage(obj); } } } internal static class Config { public const string ModName = "Prop Hunt"; public const string ModVersion = "1.0.1"; public const int SSMPApiVersion = 1; public const int MaxSwapCount = 0; public const int SeekerCountdown = 30; public static readonly bool AllowDebugFeatures; private static ConfigEntry<bool> _disableDamage; private static ConfigEntry<KeyCode> _swapPropKey; private static ConfigEntry<KeyCode> _hideHornetKey; private static ConfigEntry<KeyCode> _resetKey; private static ConfigEntry<KeyCode> _propPositionReset; private static ConfigEntry<MovementMethods> _movementMethod; public static bool DisableDamage { get { if (_disableDamage.Value) { return PropHuntClient.GameState != GameState.NotStarted; } return false; } } public static KeyCode SwapPropKey => _swapPropKey.Value; public static KeyCode HideHornetKey => (KeyCode)(((??)_hideHornetKey?.Value) ?? 104); public static KeyCode ResetKey => _resetKey.Value; public static KeyCode PropPositionReset => _propPositionReset.Value; public static MovementMethods MovementMethod => _movementMethod.Value; public static void LoadConfig(ConfigFile Config) { _disableDamage = Config.Bind<bool>("General", "DisableDamage", true, "Disables all damage to the player with the exception of other players and terrain"); _swapPropKey = Config.Bind<KeyCode>("General", "KeySwapProp", (KeyCode)112, "The key to swap props"); _resetKey = Config.Bind<KeyCode>("General", "KeyReset", (KeyCode)114, "The key to unhide and remove the active prop"); _movementMethod = Config.Bind<MovementMethods>("Prop Movement", "Movement Method", MovementMethods.Numpad, "Which control style to use for prop movement"); _movementMethod.SettingChanged += delegate { PropMovementControls.MovementState = MovementState.Normal; }; _propPositionReset = Config.Bind<KeyCode>("Prop Movement", "Reset Position", (KeyCode)261, "Resets the prop position"); if (AllowDebugFeatures) { _hideHornetKey = Config.Bind<KeyCode>("General", "KeyHideHornet", (KeyCode)104, "The key to hide hornet in the event that she becomes visible while hiding"); } } } public enum CustomPackets { PropSwap, RoundStart, PropLocation, HideStatus, PropFound, Sync, GameOver, SeekerStart, FailedAction } public enum GameState { NotStarted, SeekerWait, Playing } public enum CorrectionActions { None, DisableClientProp, DisablePlayerProp, PreviousScene, ToggleHornetTrue, ToggleHornetFalse, RestoreLastProp, RestoreTriggerHandler, BecomeSeeker } public enum MovementState { Normal, Move2D, MoveZ, Rotate } public enum MovementMethods { Numpad, KeyboardMovement, ControllerRightStick, ControllerLeftStick } internal class PropMovementControls { private static float StickThreshold = 0.02f; private static SpriteRenderer StateIndicator; private static Sprite MoveXY; private static Sprite MoveZ; private static Sprite Rotate; private bool moved; public static PropMovementControls Instance; internal static MovementState MovementState = MovementState.Normal; private InputBlockingMechanism blockingMechanism = new InputBlockingMechanism(); private bool ModeSwitchPressed; public PropMovementControls() { if (Instance == null) { Instance = this; } } private void ChangeModes() { if (MovementState == MovementState.Normal) { SetMovementState(MovementState.Move2D); } else if (MovementState == MovementState.Move2D) { SetMovementState(MovementState.MoveZ); } else if (MovementState == MovementState.MoveZ) { SetMovementState(MovementState.Rotate); } else { SetMovementState(MovementState.Normal); } } private bool ResetPosition() { //IL_0000: Unknown result type (might be due to invalid IL or missing references) if (Input.GetKeyDown(Config.PropPositionReset)) { MoveProp(Direction.Reset); SetMovementState(MovementState.Normal); moved = true; return true; } return false; } private bool CheckStick(OneAxisInputControl input, Direction direction, bool useValue = true) { if (input.IsPressed && input.Value > StickThreshold) { float num = 0.1f; if (useValue) { num = input.Value / 5f; } if (((OneAxisInputControl)ManagerSingleton<InputHandler>.Instance.inputActions.Dash).IsPressed) { num /= 2f; } MoveProp(direction, num); return true; } return false; } private void ControllerUpdate(bool rightStick = true) { TwoAxisInputControl val = (rightStick ? InputManager.ActiveDevice.RightStick : InputManager.ActiveDevice.LeftStick); if (val == null) { return; } val.Left.Enabled = true; val.Right.Enabled = true; val.Up.Enabled = true; val.Down.Enabled = true; InputControl val2 = (rightStick ? InputManager.ActiveDevice.RightStickButton : InputManager.ActiveDevice.LeftStickButton); ((OneAxisInputControl)val2).Enabled = true; if (((OneAxisInputControl)val2).IsPressed && !ModeSwitchPressed) { ChangeModes(); ModeSwitchPressed = true; } else if (!((OneAxisInputControl)val2).IsPressed) { ModeSwitchPressed = false; } if (MovementState == MovementState.Move2D) { if (!CheckStick(val.Left, Direction.Left)) { CheckStick(val.Right, Direction.Right); } if (!CheckStick(val.Up, Direction.Up)) { CheckStick(val.Down, Direction.Down); } } else if (MovementState == MovementState.MoveZ) { if (!CheckStick(val.Left, Direction.Back)) { CheckStick(val.Right, Direction.Front); } if (!CheckStick(val.Up, Direction.Back)) { CheckStick(val.Down, Direction.Front); } } else if (MovementState == MovementState.Rotate && !CheckStick(val.Left, Direction.RotateLeft)) { CheckStick(val.Right, Direction.RotateRight); } } private void NumpadUpdate() { SelfCoverManager instance = SelfCoverManager.instance; instance.MoveProp(Direction.Left, (KeyCode)260, ref moved); instance.MoveProp(Direction.Right, (KeyCode)262, ref moved); instance.MoveProp(Direction.Up, (KeyCode)264, ref moved); instance.MoveProp(Direction.Down, (KeyCode)258, ref moved); instance.MoveProp(Direction.Front, (KeyCode)263, ref moved); instance.MoveProp(Direction.Back, (KeyCode)265, ref moved); instance.MoveProp(Direction.RotateLeft, (KeyCode)257, ref moved); instance.MoveProp(Direction.RotateRight, (KeyCode)259, ref moved); } private void KeyboardUpdate() { HeroActions inputActions = ManagerSingleton<InputHandler>.Instance.inputActions; ((OneAxisInputControl)inputActions.Left).Enabled = true; ((OneAxisInputControl)inputActions.Right).Enabled = true; ((OneAxisInputControl)inputActions.Up).Enabled = true; ((OneAxisInputControl)inputActions.Down).Enabled = true; ((OneAxisInputControl)inputActions.Taunt).Enabled = true; ((OneAxisInputControl)inputActions.Dash).Enabled = true; if (((OneAxisInputControl)inputActions.Taunt).IsPressed && !ModeSwitchPressed) { ChangeModes(); ModeSwitchPressed = true; } else if (!((OneAxisInputControl)inputActions.Taunt).IsPressed) { ModeSwitchPressed = false; } if (MovementState == MovementState.Move2D) { if (!CheckStick((OneAxisInputControl)(object)inputActions.Left, Direction.Up, useValue: false)) { CheckStick((OneAxisInputControl)(object)inputActions.Right, Direction.Right, useValue: false); } if (!CheckStick((OneAxisInputControl)(object)inputActions.Up, Direction.Up, useValue: false)) { CheckStick((OneAxisInputControl)(object)inputActions.Down, Direction.Down, useValue: false); } } else if (MovementState == MovementState.MoveZ) { if (!CheckStick((OneAxisInputControl)(object)inputActions.Left, Direction.Back, useValue: false)) { CheckStick((OneAxisInputControl)(object)inputActions.Right, Direction.Front, useValue: false); } if (!CheckStick((OneAxisInputControl)(object)inputActions.Up, Direction.Back, useValue: false)) { CheckStick((OneAxisInputControl)(object)inputActions.Down, Direction.Front, useValue: false); } } else if (MovementState == MovementState.Rotate && !CheckStick((OneAxisInputControl)(object)inputActions.Left, Direction.RotateLeft, useValue: false)) { CheckStick((OneAxisInputControl)(object)inputActions.Right, Direction.RotateRight, useValue: false); } } public void Update() { if (!ResetPosition()) { switch (Config.MovementMethod) { case MovementMethods.ControllerRightStick: ControllerUpdate(); break; case MovementMethods.ControllerLeftStick: ControllerUpdate(rightStick: false); break; case MovementMethods.Numpad: NumpadUpdate(); break; case MovementMethods.KeyboardMovement: KeyboardUpdate(); break; } if (!moved) { SelfCoverManager.instance.SendPropPosition(); } moved = false; } } private void MoveProp(Direction direction, float distance = 0.1f) { moved = true; SelfCoverManager.instance.MoveProp(direction, distance); } public void SetMovementState(MovementState newState) { Log.LogDebug($"Movement State: {MovementState} -> {newState}"); MovementState = newState; switch (newState) { case MovementState.Move2D: HeroController.instance.AddInputBlocker((object)blockingMechanism); break; case MovementState.Normal: PropHuntMod.nextFrameActions.Add(delegate { HeroController.instance.RemoveInputBlocker((object)blockingMechanism); }); break; } if ((Object)(object)StateIndicator == (Object)null) { CreateMovementIndicator(); } switch (newState) { case MovementState.Normal: StateIndicator.sprite = null; break; case MovementState.Move2D: StateIndicator.sprite = MoveXY; break; case MovementState.MoveZ: StateIndicator.sprite = MoveZ; break; case MovementState.Rotate: StateIndicator.sprite = Rotate; break; } } private void CreateMovementIndicator() { //IL_0116: Unknown result type (might be due to invalid IL or missing references) AssetBundle val = AssetBundle.LoadFromFile(Path.Combine(Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location), "prophunt.bundle")); Sprite[] array = val.LoadAllAssets<Sprite>(); Sprite[] array2 = array; foreach (Sprite val2 in array2) { Log.LogInfo(((Object)val2).name, val2); } MoveXY = array.First((Sprite a) => ((Object)a).name == "MoveXY"); MoveZ = array.First((Sprite a) => ((Object)a).name == "MoveZ"); Rotate = array.First((Sprite a) => ((Object)a).name == "Rotate"); val.Unload(false); Transform val3 = ((Component)GameCameras.instance.hudCamera).transform.Find("In-game/Anchor TL/Hud Canvas Offset/Hud Canvas"); Transform val4 = val3.Find("Delivery Icon/Parent/Delivery Icon Sprite"); Transform obj = Object.Instantiate<Transform>(val4, val3); ((Component)obj).transform.position = val4.position; ((Component)obj).gameObject.SetActive(true); StateIndicator = ((Component)obj).GetComponent<SpriteRenderer>(); StateIndicator.sprite = null; } } internal class InputBlockingMechanism { } public class Prop { public string name; public string path; public GameObject go; } internal static class PropValidation { private static readonly string[] extraNames = new string[2] { "corpse", "quest_board" }; private static readonly PhysLayers[] invalidLayers = (PhysLayers[])(object)new PhysLayers[2] { (PhysLayers)11, (PhysLayers)17 }; private static GameObject PropParent; private static readonly Type[] allowedTypes = new Type[13] { typeof(Transform), typeof(MeshFilter), typeof(Renderer), typeof(MeshRenderer), typeof(SpriteRenderer), typeof(tk2dSprite), typeof(tk2dSpriteAnimator), typeof(tk2dSpriteAnimation), typeof(tk2dSpriteAnimationClip), typeof(tk2dSpriteAnimationFrame), typeof(tk2dLookAnimNPC), typeof(CurveRotationAnimation), typeof(JitterSelf) }; public static NoRepeat<Prop> currentSceneObjects { get; private set; } private static bool HasScript(GameObject obj) { if (!Object.op_Implicit((Object)(object)obj.GetComponent<Breakable>()) && !Object.op_Implicit((Object)(object)obj.GetComponent<PlayMakerNPC>()) && !Object.op_Implicit((Object)(object)obj.GetComponent<BasicNPC>()) && !Object.op_Implicit((Object)(object)obj.GetComponent<QuestBoardInteractable>())) { return Object.op_Implicit((Object)(object)obj.GetComponent<PushableRubble>()); } return true; } private static void LogSpecificObj(string objectName, string condition) { if (objectName == "Bonechurch_shop") { Log.LogInfo(condition); } } private static bool IsValidProp(string scene, GameObject gameObject) { //IL_007c: Unknown result type (might be due to invalid IL or missing references) //IL_012b: Unknown result type (might be due to invalid IL or missing references) //IL_0130: Unknown result type (might be due to invalid IL or missing references) if (!gameObject.activeInHierarchy) { LogSpecificObj(((Object)gameObject).name, "inactive"); return false; } if (Regex.IsMatch(((Object)gameObject).name, "^pebble$|^junk_push|^Small_bell_push|^weaver_corpse_shrine|^Weaver Corpse Glow", RegexOptions.IgnoreCase)) { return false; } if (((Object)gameObject).name.Contains("(Clone)")) { LogSpecificObj(((Object)gameObject).name, "clone"); return false; } if (invalidLayers.Contains((PhysLayers)gameObject.layer)) { string name2 = ((Object)gameObject).name; PhysLayers val = (PhysLayers)gameObject.layer; LogSpecificObj(name2, "layer " + ((object)(PhysLayers)(ref val)).ToString()); return false; } SpriteRenderer renderer = gameObject.GetComponent<SpriteRenderer>(); if ((Object)(object)renderer == (Object)null && (Object)(object)gameObject.GetComponent<tk2dSprite>() == (Object)null) { LogSpecificObj(((Object)gameObject).name, "no renderer"); return false; } SpriteRenderer obj = renderer; object obj2; if (obj == null) { obj2 = null; } else { Sprite sprite = obj.sprite; obj2 = ((sprite != null) ? ((Object)sprite).name : null); } if (obj2 != null && ExtraProps.banned.Any((string p) => p == ((Object)renderer.sprite).name)) { LogSpecificObj(((Object)gameObject).name, "black fader"); return false; } SpriteRenderer obj3 = renderer; float num; if (obj3 == null) { num = 1f; } else { Color color = obj3.color; num = ((Color)(ref color)).grayscale; } if (num < 0.75f) { LogSpecificObj(((Object)gameObject).name, "too dark"); return false; } LogSpecificObj(((Object)gameObject).name, "passed negative"); if (HasScript(gameObject)) { return true; } string name = ((Object)gameObject).name.ToLower(); if (extraNames.Any((string n) => name.Contains(n))) { return true; } if (ExtraProps.IsExtraProp(scene, gameObject)) { return true; } return false; } private static bool IsGameObjectDuplicate(SpriteRenderer newObjRenderer, GameObject existingGameObject) { try { SpriteRenderer renderer = GetRenderer(existingGameObject); if ((Object)(object)((renderer != null) ? renderer.sprite : null) == (Object)null || (Object)(object)((newObjRenderer != null) ? newObjRenderer.sprite : null) == (Object)null) { Log.LogInfo(((Object)newObjRenderer).name + " not duplicate, a sprite was null"); return false; } return ((Object)renderer.sprite).name == ((Object)newObjRenderer.sprite).name; } catch (Exception ex) { Log.LogError(((Object)existingGameObject).name + " failed, no sprite on one of the objects?"); Log.LogError(ex); return true; } } private static SpriteRenderer GetRenderer(GameObject gameObject) { SpriteRenderer val = gameObject.GetComponent<SpriteRenderer>(); if ((Object)(object)((val != null) ? val.sprite : null) == (Object)null) { val = ((IEnumerable<SpriteRenderer>)gameObject.GetComponentsInChildren<SpriteRenderer>()).FirstOrDefault((Func<SpriteRenderer, bool>)((SpriteRenderer s) => (Object)(object)s.sprite != (Object)null)); } return val; } public static void GetAllProps() { //IL_0000: Unknown result type (might be due to invalid IL or missing references) //IL_0005: Unknown result type (might be due to invalid IL or missing references) Scene activeScene = SceneManager.GetActiveScene(); string name = ((Scene)(ref activeScene)).name; Log.LogInfo("Preparing all props for scene " + name); GameObject[] array = Resources.FindObjectsOfTypeAll<GameObject>(); List<GameObject> list = new List<GameObject>(); ExtraProps.Init(); GameObject[] array2 = array; foreach (GameObject val in array2) { if (IsValidProp(name, val)) { LogSpecificObj(((Object)val).name, "valid prop"); SpriteRenderer renderer = GetRenderer(val); if ((Object)(object)renderer == (Object)null) { LogSpecificObj(((Object)val).name, "no renderer"); } else if (list.Any((GameObject o) => IsGameObjectDuplicate(renderer, o))) { LogSpecificObj(((Object)val).name, "duplicate object"); } else { list.Add(val); } } } PrepareAllProps(list); AddPropsToOutput(name); } private static void AddPropsToOutput(string scene) { List<Prop> inputValues = currentSceneObjects.inputValues; string value = string.Format("{0},{1},\"{2}\"", scene, inputValues.Count, string.Join("\n", inputValues.Select((Prop x) => x.name))); StreamWriter streamWriter = File.AppendText(Path.Combine(Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location), "PropReport.csv")); streamWriter.WriteLine(value); streamWriter.Close(); } private static void RemoveComponents<T>(GameObject gameObject, bool keepOnParent = false) where T : Component { T[] componentsInChildren = gameObject.GetComponentsInChildren<T>(); foreach (T val in componentsInChildren) { if (!keepOnParent || (Object)(object)((Component)val).gameObject != (Object)(object)gameObject.gameObject) { Object.Destroy((Object)(object)val); } } } private static void StripProp(GameObject gameObject) { MonoBehaviour[] componentsInChildren = gameObject.GetComponentsInChildren<MonoBehaviour>(true); foreach (MonoBehaviour val in componentsInChildren) { Type type = ((object)val).GetType(); if (!allowedTypes.Any((Type t) => type == t)) { Object.Destroy((Object)(object)val); } } RemoveComponents<Collider2D>(gameObject, keepOnParent: false); RemoveComponents<Rigidbody2D>(gameObject, keepOnParent: true); Transform[] componentsInChildren2 = gameObject.GetComponentsInChildren<Transform>(); foreach (Transform val2 in componentsInChildren2) { if (!Object.op_Implicit((Object)(object)((Component)val2).GetComponentInChildren<Renderer>()) && !Object.op_Implicit((Object)(object)((Component)val2).GetComponentInChildren<ParticleSystem>())) { Object.Destroy((Object)(object)((Component)val2).gameObject); } } } private static string GeneratePropPath(GameObject prop) { string text = ((Object)prop).name; _ = prop.transform.parent; while ((Object)(object)prop.transform.parent != (Object)null) { prop = ((Component)prop.transform.parent).gameObject; text = ((Object)prop).name + "/" + text; } return text; } public static Prop PrepareProp(GameObject prop, bool assignParent = true) { //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_00dd: Unknown result type (might be due to invalid IL or missing references) //IL_011b: Unknown result type (might be due to invalid IL or missing references) if ((Object)(object)prop == (Object)null) { Log.LogError("Unknown prop to prepare"); return null; } GameObject val; try { if (assignParent) { val = Object.Instantiate<GameObject>(prop, PropParent.transform); } else { val = Object.Instantiate<GameObject>(prop); val.SetActive(false); } val.layer = 20; ((Object)val).name = ((Object)prop).name; Breakable component = val.GetComponent<Breakable>(); if ((Object)(object)component != (Object)null && component.IsBroken) { SpriteRenderer component2 = val.GetComponent<SpriteRenderer>(); if ((Object)(object)component2 != (Object)null) { ((Renderer)component2).enabled = true; } } } catch (Exception ex) { Log.LogError("Ran into an error instantiating cover " + ((Object)prop).name + "."); Log.LogError(ex); return null; } StripProp(val); Quaternion rotation = val.transform.rotation; val.transform.rotation = Quaternion.identity; if (!AddPropHitbox(val)) { Log.LogInfo("Couldn't add hitbox for " + ((Object)prop).name); Object.Destroy((Object)(object)val); return null; } val.transform.rotation = rotation; return new Prop { name = ((Object)val).name, go = val, path = GeneratePropPath(prop) }; } private static bool AddPropHitbox(GameObject prop) { //IL_004d: Unknown result type (might be due to invalid IL or missing references) //IL_0052: Unknown result type (might be due to invalid IL or missing references) //IL_0136: Unknown result type (might be due to invalid IL or missing references) //IL_013b: Unknown result type (might be due to invalid IL or missing references) //IL_0140: Unknown result type (might be due to invalid IL or missing references) //IL_0158: Unknown result type (might be due to invalid IL or missing references) //IL_015d: Unknown result type (might be due to invalid IL or missing references) //IL_0162: Unknown result type (might be due to invalid IL or missing references) //IL_016d: Unknown result type (might be due to invalid IL or missing references) //IL_0178: Unknown result type (might be due to invalid IL or missing references) //IL_0183: Unknown result type (might be due to invalid IL or missing references) //IL_018e: Unknown result type (might be due to invalid IL or missing references) //IL_0094: Unknown result type (might be due to invalid IL or missing references) //IL_0099: Unknown result type (might be due to invalid IL or missing references) //IL_009d: Unknown result type (might be due to invalid IL or missing references) //IL_01b2: Unknown result type (might be due to invalid IL or missing references) //IL_01a0: Unknown result type (might be due to invalid IL or missing references) //IL_01e9: Unknown result type (might be due to invalid IL or missing references) //IL_01c4: Unknown result type (might be due to invalid IL or missing references) //IL_0113: Unknown result type (might be due to invalid IL or missing references) Renderer[] array = (from r in prop.GetComponentsInChildren<Renderer>(false) where !(r is LineRenderer) && !(r is ParticleSystemRenderer) select r).ToArray(); if (array.Length == 0) { Log.LogError("No renderers found"); return false; } Bounds bounds = array[0].bounds; Renderer[] array2 = array; foreach (Renderer val in array2) { string text = ((Object)val).name.ToLower(); if (((Object)prop).name == "Active") { object[] obj = new object[2] { text, null }; Bounds bounds2 = val.bounds; obj[1] = ((Bounds)(ref bounds2)).size; Log.LogInfo(obj); } if (!text.StartsWith("haze") && !text.StartsWith("light") && !text.StartsWith("vignette") && !text.EndsWith("fader") && !text.EndsWith("glow") && !text.EndsWith("cutout") && !(text == "lit")) { ((Bounds)(ref bounds)).Encapsulate(val.bounds); } } Vector3 val2 = prop.transform.InverseTransformVector(((Bounds)(ref bounds)).size); BoxCollider2D val3 = prop.AddComponent<BoxCollider2D>(); ((Collider2D)val3).isTrigger = true; ((Collider2D)val3).offset = Vector2.op_Implicit(prop.transform.InverseTransformPoint(((Bounds)(ref bounds)).center)); val3.size = new Vector2(Mathf.Abs(val2.x), Mathf.Abs(val2.y)); if ((val3.size.x > 20f && val3.size.y > 20f) || val3.size.x >= 30f || val3.size.y >= 30f) { Log.LogError($"Prop {((Object)prop).name} was too frickin big (${val3.size})"); return false; } Extensions.AddComponentIfNotPresent<Rigidbody2D>(prop).bodyType = (RigidbodyType2D)1; prop.AddComponent<LineRenderer>(); prop.AddComponent<DebugViewCollider>(); prop.AddComponent<TriggerHandler>(); array2 = array; foreach (Renderer val4 in array2) { if (!((Object)(object)((Component)val4).gameObject == (Object)(object)prop)) { Extensions.AddComponentIfNotPresent<LineRenderer>(((Component)val4).gameObject); ((Component)val4).gameObject.AddComponent<DebugViewBounds>(); } } return true; } private static void PrepareAllProps(List<GameObject> props) { //IL_001c: Unknown result type (might be due to invalid IL or missing references) //IL_0026: Expected O, but got Unknown if ((Object)(object)PropParent != (Object)null) { Object.Destroy((Object)(object)PropParent); } PropParent = new GameObject("PROP PARENT"); PropParent.SetActive(false); if (!SelfHornetManager.instance.HornetExists()) { return; } List<Prop> list = new List<Prop>(); foreach (GameObject prop2 in props) { Prop prop = PrepareProp(prop2); if (prop != null) { list.Add(prop); } } currentSceneObjects = new NoRepeat<Prop>(list); } public static void ResetProps() { Log.LogInfo("Resetting props"); currentSceneObjects = null; } public static GameObject FindGameObject(string path) { //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) string[] names = path.Split(new char[1] { '/' }); Scene activeScene = SceneManager.GetActiveScene(); GameObject val = ((IEnumerable<GameObject>)((Scene)(ref activeScene)).GetRootGameObjects()).FirstOrDefault((Func<GameObject, bool>)((GameObject go) => ((Object)go).name == names[0])); if ((Object)(object)val == (Object)null) { return null; } for (int i = 1; i < names.Length; i++) { GameObject val2 = FindGameObjectLayer(names[i], val); if ((Object)(object)val2 == (Object)null) { return null; } val = val2; } return val; } private static GameObject FindGameObjectLayer(string name, GameObject parent) { int childCount = parent.transform.childCount; for (int i = 0; i < childCount; i++) { Transform child = parent.transform.GetChild(i); if (((Object)child).name == name) { return ((Component)child).gameObject; } } return null; } } internal class DebugViewCollider : MonoBehaviour { private Color borderColor = Color.white; private readonly float lineWidth = 0.05f; private LineRenderer lineRenderer; private BoxCollider2D collider; private bool Show => PropHuntMod.showHitboxes; private void Awake() { //IL_0062: Unknown result type (might be due to invalid IL or missing references) //IL_006c: Expected O, but got Unknown //IL_0073: Unknown result type (might be due to invalid IL or missing references) //IL_0084: Unknown result type (might be due to invalid IL or missing references) collider = ((Component)this).GetComponent<BoxCollider2D>(); lineRenderer = ((Component)this).GetComponent<LineRenderer>(); lineRenderer.loop = true; lineRenderer.useWorldSpace = true; lineRenderer.startWidth = lineWidth; lineRenderer.endWidth = lineWidth; ((Renderer)lineRenderer).material = new Material(Shader.Find("Sprites/Default")); lineRenderer.startColor = borderColor; lineRenderer.endColor = borderColor; } private void LateUpdate() { if (Show) { DrawBox(collider); } else { lineRenderer.positionCount = 0; } } private void DrawBox(BoxCollider2D box) { //IL_0001: Unknown result type (might be due to invalid IL or missing references) //IL_000b: Unknown result type (might be due to invalid IL or missing references) //IL_0010: Unknown result type (might be due to invalid IL or missing references) //IL_0012: Unknown result type (might be due to invalid IL or missing references) //IL_0017: Unknown result type (might be due to invalid IL or missing references) //IL_0021: 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_0029: Unknown result type (might be due to invalid IL or missing references) //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) //IL_003a: 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_0046: Unknown result type (might be due to invalid IL or missing references) //IL_0047: 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_0054: Unknown result type (might be due to invalid IL or missing references) //IL_0059: Unknown result type (might be due to invalid IL or missing references) //IL_005e: Unknown result type (might be due to invalid IL or missing references) //IL_0063: Unknown result type (might be due to invalid IL or missing references) //IL_006a: Unknown result type (might be due to invalid IL or missing references) //IL_006b: Unknown result type (might be due to invalid IL or missing references) //IL_0071: Unknown result type (might be due to invalid IL or missing references) //IL_0077: 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_0081: Unknown result type (might be due to invalid IL or missing references) //IL_0086: Unknown result type (might be due to invalid IL or missing references) //IL_008d: 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_0095: 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_00a0: 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) //IL_00aa: Unknown result type (might be due to invalid IL or missing references) Vector2 val = box.size * 0.5f; Vector2 offset = ((Collider2D)box).offset; SetPositions((Vector3[])(object)new Vector3[4] { Vector2.op_Implicit(offset + new Vector2(0f - val.x, 0f - val.y)), Vector2.op_Implicit(offset + new Vector2(val.x, 0f - val.y)), Vector2.op_Implicit(offset + new Vector2(val.x, val.y)), Vector2.op_Implicit(offset + new Vector2(0f - val.x, val.y)) }); } private void SetPositions(Vector3[] localPoints) { //IL_0021: 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) lineRenderer.positionCount = localPoints.Length; for (int i = 0; i < localPoints.Length; i++) { lineRenderer.SetPosition(i, ((Component)this).transform.TransformPoint(localPoints[i])); } } } internal class DebugViewBounds : MonoBehaviour { private LineRenderer lineRenderer; private Renderer[] renderers; private Color borderColor = Color.red; private readonly float lineWidth = 0.05f; private bool Show => PropHuntMod.showHitboxes; private void Awake() { //IL_0056: Unknown result type (might be due to invalid IL or missing references) //IL_0060: Expected O, but got Unknown //IL_0067: Unknown result type (might be due to invalid IL or missing references) //IL_0078: Unknown result type (might be due to invalid IL or missing references) lineRenderer = ((Component)this).GetComponent<LineRenderer>(); lineRenderer.loop = true; lineRenderer.useWorldSpace = true; lineRenderer.startWidth = lineWidth; lineRenderer.endWidth = lineWidth; ((Renderer)lineRenderer).material = new Material(Shader.Find("Sprites/Default")); lineRenderer.startColor = borderColor; lineRenderer.endColor = borderColor; renderers = ((Component)this).GetComponents<Renderer>(); } private void LateUpdate() { if (Show) { Renderer[] array = renderers; foreach (Renderer renderer in array) { DrawBox(renderer); } } } private void DrawBox(Renderer renderer) { //IL_0001: Unknown result type (might be due to invalid IL or missing references) //IL_0006: Unknown result type (might be due to invalid IL or missing references) //IL_0009: Unknown result type (might be due to invalid IL or missing references) //IL_002c: Unknown result type (might be due to invalid IL or missing references) //IL_0031: Unknown result type (might be due to invalid IL or missing references) //IL_0036: Unknown result type (might be due to invalid IL or missing references) //IL_0038: Unknown result type (might be due to invalid IL or missing references) //IL_003d: Unknown result type (might be due to invalid IL or missing references) //IL_0040: Unknown result type (might be due to invalid IL or missing references) //IL_0045: 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) //IL_0054: Unknown result type (might be due to invalid IL or missing references) //IL_0055: 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_0063: 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_0072: Unknown result type (might be due to invalid IL or missing references) //IL_0079: 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) //IL_0080: Unknown result type (might be due to invalid IL or missing references) //IL_0087: Unknown result type (might be due to invalid IL or missing references) //IL_008c: 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_0096: Unknown result type (might be due to invalid IL or missing references) //IL_009d: Unknown result type (might be due to invalid IL or missing references) //IL_009e: Unknown result type (might be due to invalid IL or missing references) //IL_00a4: Unknown result type (might be due to invalid IL or missing references) //IL_00aa: Unknown result type (might be due to invalid IL or missing references) //IL_00af: Unknown result type (might be due to invalid IL or missing references) //IL_00b4: Unknown result type (might be due to invalid IL or missing references) //IL_00b9: Unknown result type (might be due to invalid IL or missing references) //IL_00c0: 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_00c8: Unknown result type (might be due to invalid IL or missing references) //IL_00ce: Unknown result type (might be due to invalid IL or missing references) //IL_00d3: Unknown result type (might be due to invalid IL or missing references) //IL_00d8: Unknown result type (might be due to invalid IL or missing references) //IL_00dd: Unknown result type (might be due to invalid IL or missing references) Bounds localBounds = renderer.localBounds; Vector2 val = Vector2.op_Implicit(Extensions.DivideElements(((Bounds)(ref localBounds)).size, (float?)2.1f, (float?)2.1f, (float?)null)); localBounds = renderer.localBounds; Vector2 val2 = Vector2.op_Implicit(((Bounds)(ref localBounds)).center); SetPositions((Vector3[])(object)new Vector3[4] { Vector2.op_Implicit(val2 + new Vector2(0f - val.x, 0f - val.y)), Vector2.op_Implicit(val2 + new Vector2(val.x, 0f - val.y)), Vector2.op_Implicit(val2 + new Vector2(val.x, val.y)), Vector2.op_Implicit(val2 + new Vector2(0f - val.x, val.y)) }); } private void SetPositions(Vector3[] localPoints) { //IL_0021: 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) lineRenderer.positionCount = localPoints.Length; for (int i = 0; i < localPoints.Length; i++) { lineRenderer.SetPosition(i, ((Component)this).transform.TransformPoint(localPoints[i])); } } } internal static class ExtraProps { private static string[] sceneProps; private static string[] scenePrefixes; private static string scenePrefix; public static string[] global = new string[0]; public static string[] banned = new string[0]; public static void Init() { //IL_0007: Unknown result type (might be due to invalid IL or missing references) //IL_000c: Unknown result type (might be due to invalid IL or missing references) Scene activeScene = SceneManager.GetActiveScene(); string scene = ((Scene)(ref activeScene)).name; if (scenePrefixes != null) { string text = scenePrefixes.FirstOrDefault((string p) => scene.StartsWith(p)); if (string.IsNullOrEmpty(text)) { Log.LogDebug("EPI: Scene not in extra props list"); Log.LogDebug(sceneProps?.Length); sceneProps = null; scenePrefix = null; return; } if (text == scenePrefix) { Log.LogDebug("EPI: Scene is same."); Log.LogDebug(sceneProps.Length); return; } } Log.LogInfo("Proceeding with extra prop loading"); Dictionary<string, string[]> dictionary = JsonConvert.DeserializeObject<Dictionary<string, string[]>>(File.ReadAllText(Path.Combine(Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location), "ExtraProps.json"))); scenePrefixes = dictionary.Keys.ToArray(); Log.LogInfo("Prefixes:", string.Join(", ", scenePrefixes)); string text2 = dictionary.Keys.FirstOrDefault((string s) => scene.StartsWith(s)); Log.LogInfo("Key: " + text2); global = dictionary["GLOBAL"]; if (string.IsNullOrEmpty(text2)) { Log.LogError("EPI: key not found"); sceneProps = null; scenePrefix = null; } else { sceneProps = dictionary[text2]; Log.LogInfo("Props:", string.Join(", ", sceneProps)); scenePrefix = text2; banned = dictionary["BANNED"]; } } public static bool IsExtraProp(string scene, GameObject gameObject) { //IL_006d: Unknown result type (might be due to invalid IL or missing references) //IL_0072: Unknown result type (might be due to invalid IL or missing references) if (string.IsNullOrEmpty(scene)) { Log.LogDebug("IEP: No scene name"); return false; } if (sceneProps == null) { Log.LogDebug("IEP: No scene props"); return false; } SpriteRenderer renderer = gameObject.GetComponent<SpriteRenderer>(); SpriteRenderer obj = renderer; if ((Object)(object)((obj != null) ? obj.sprite : null) == (Object)null) { return false; } Color color = renderer.color; if (((Color)(ref color)).grayscale < 0.75f) { return false; } bool flag = global.Any((string p) => ((Object)renderer.sprite).name.StartsWith(p)) || sceneProps.Any((string p) => ((Object)renderer.sprite).name.StartsWith(p)); if (flag && banned.Any((string p) => ((Object)renderer.sprite).name == p)) { flag = false; } return flag; } } } namespace PropHuntMod.Utils.Networking { internal static class ClientErrorCorrection { [CompilerGenerated] private sealed class <PreviousScene>d__2 : IEnumerator<object>, IDisposable, IEnumerator { private int <>1__state; private object <>2__current; public FailedAction data; private int <i>5__2; object IEnumerator<object>.Current { [DebuggerHidden] get { return <>2__current; } } object IEnumerator.Current { [DebuggerHidden] get { return <>2__current; } } [DebuggerHidden] public <PreviousScene>d__2(int <>1__state) { this.<>1__state = <>1__state; } [DebuggerHidden] void IDisposable.Dispose() { <>1__state = -2; } private bool MoveNext() { //IL_0057: Unknown result type (might be due to invalid IL or missing references) //IL_0061: Expected O, but got Unknown //IL_00b1: Unknown result type (might be due to invalid IL or missing references) //IL_00b6: 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_00c8: Unknown result type (might be due to invalid IL or missing references) //IL_00cf: 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_00dd: Unknown result type (might be due to invalid IL or missing references) //IL_00e5: Expected O, but got Unknown switch (<>1__state) { default: return false; case 0: <>1__state = -1; <i>5__2 = 0; break; case 1: <>1__state = -1; <i>5__2++; break; } if (<i>5__2 < 5 && string.IsNullOrEmpty(PropHuntMod.PreviousScene)) { Log.LogInfo($"Attempt {<i>5__2 + 1} to find previous scene failed"); <>2__current = (object)new WaitForSeconds(1f); <>1__state = 1; return true; } if (string.IsNullOrEmpty(PropHuntMod.PreviousScene)) { PropHuntMod.client.ClientManager.Disconnect(); PropHuntClient.LocalMessage("Fatal Error: Unable to find previous scene."); return false; } SceneLoadInfo val = new SceneLoadInfo { SceneName = PropHuntMod.PreviousScene, PreventCameraFadeOut = true, WaitForSceneTransitionCameraFade = false, Visualization = (SceneLoadVisualizations)0, AlwaysUnloadUnusedAssets = true, IsFirstLevelForPlayer = false }; PropHuntMod.SceneTransitionTicket = data.BypassTicketID; GameManager.instance.BeginSceneTransition(val); 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 static void DiagnoseError(FailedAction data) { switch (data.FixMethod) { case CorrectionActions.DisableClientProp: SelfCoverManager.instance.DisableProp(logOnFail: false, isSceneChange: false, data.BypassTicketID); break; case CorrectionActions.DisablePlayerProp: DisablePlayerProp(data); break; case CorrectionActions.PreviousScene: ((MonoBehaviour)PropHuntMod.Instance).StartCoroutine(PreviousScene(data)); break; case CorrectionActions.ToggleHornetTrue: SelfHornetManager.instance.ToggleHornet(show: true); break; case CorrectionActions.ToggleHornetFalse: SelfHornetManager.instance.ToggleHornet(show: false, data.BypassTicketID); break; case CorrectionActions.RestoreLastProp: RestoreLastProp(data); break; case CorrectionActions.RestoreTriggerHandler: RestoreTriggerHandler(data); break; case CorrectionActions.BecomeSeeker: BecomeSeeker(); break; default: throw new NotImplementedException(data.FixMethod.ToString()); case CorrectionActions.None: break; } } private static void DisablePlayerProp(FailedAction data) { PlayerManager.GetPlayerManager(data.AffectedID).SetProp("", ""); } [IteratorStateMachine(typeof(<PreviousScene>d__2))] private static IEnumerator PreviousScene(FailedAction data) { //yield-return decompiler failed: Unexpected instruction in Iterator.Dispose() return new <PreviousScene>d__2(0) { data = data }; } public static void RestoreLastProp(FailedAction data) { SelfCoverManager instance = SelfCoverManager.instance; GameObject obj = PropValidation.FindGameObject(instance.PrevCoverPath); Prop prop = PropValidation.PrepareProp(obj); if ((Object)(object)obj == (Object)null || prop == null) { Log.LogFatal("Couldn't restore previous prop " + instance.PrevCoverPath); } else { SelfCoverManager.instance.EnableProp(prop, data.BypassTicketID); } } private static void RestoreTriggerHandler(FailedAction data) { GameObject cover = PlayerManager.GetPlayerManager(data.AffectedID).coverManager.cover; if ((Object)(object)cover != (Object)null) { if ((Object)(object)cover.GetComponent<TriggerHandler>() == (Object)null) { TriggerHandler triggerHandler = cover.AddComponent<TriggerHandler>(); triggerHandler.isRemote = true; triggerHandler.playerID = data.AffectedID; } else { Log.LogInfo($"Player {data.AffectedID} still had their TriggerHandler. Not restoring."); } } else { Log.LogError($"Player {data.AffectedID}'s prop was already destroyed. Can't restore trigger handler"); } } private static void BecomeSeeker() { PropHuntClient.isSeeker = true; if (PropHuntClient.GameState == GameState.SeekerWait) { SelfHornetManager.instance.SetSeekerObscure(enabled: true); } } } internal static class ClientNetwork { private static IClientAddonNetworkSender<CustomPackets> sender; private static IClientAddonNetworkReceiver<CustomPackets> receiver; public static void SendPropSwap(Prop prop, int ticket = -1) { Log.LogInfo("Sending prop swap: " + prop?.name); sender.SendSingleData(CustomPackets.PropSwap, (IPacketData)(object)new global::PropHuntMod.Utils.Networking.FromClient.PropSwap { propName = (prop?.name ?? ""), propPath = (prop?.path ?? ""), TicketID = ticket }); } public static void SendPropLocation(Vector3 propPosition, float propRotation) { //IL_000d: Unknown result type (might be due to invalid IL or missing references) //IL_0030: Unknown result type (might be due to invalid IL or missing references) Log.LogInfo($"Sending prop location: {propPosition}, {propRotation}"); sender.SendSingleData(CustomPackets.PropLocation, (IPacketData)(object)new global::PropHuntMod.Utils.Networking.FromClient.PropLocation { PropPosition = propPosition, PropRotation = propRotation }); } public static void SendHideStatus(bool isHiding, int ticket = -1) { Log.LogInfo($"Sending hide status: {isHiding}"); sender.SendSingleData(CustomPackets.HideStatus, (IPacketData)(object)new global::PropHuntMod.Utils.Networking.FromClient.HideStatus { IsHiding = isHiding, TicketID = ticket }); } public static void SendPropFound(ushort propOwnerID) { Log.LogInfo($"Sending prop found: {propOwnerID}"); sender.SendSingleData(CustomPackets.PropFound, (IPacketData)(object)new global::PropHuntMod.Utils.Networking.FromClient.PropFound { PropOwnerID = propOwnerID }); } public static void SendSync(string propName, string propPath, Vector3 propPosition, float propRotation) { //IL_000e: 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) Log.LogInfo($"Sending sync data: {propName}, {propPosition}, {propRotation}"); sender.SendSingleData(CustomPackets.Sync, (IPacketData)(object)new global::PropHuntMod.Utils.Networking.FromClient.Sync { PropName = propName, PropPath = propPath, PropLocation = propPosition, PropRotation = propRotation }); } public static void Init(IClientApi clientApi, ClientAddon clientAddon) { sender = clientApi.NetClient.GetNetworkSender<CustomPackets>(clientAddon); receiver = clientApi.NetClient.GetNetworkReceiver<CustomPackets>(clientAddon, (Func<CustomPackets, IPacketData>)global::PropHuntMod.Utils.Networking.FromServer.Packets.Instantiate); receiver.RegisterPacketHandler<global::PropHuntMod.Utils.Networking.FromServer.PropSwap>(CustomPackets.PropSwap, (GenericClientPacketHandler<global::PropHuntMod.Utils.Networking.FromServer.PropSwap>)OnPropSwap); receiver.RegisterPacketHandler<global::PropHuntMod.Utils.Networking.FromServer.PropLocation>(CustomPackets.PropLocation, (GenericClientPacketHandler<global::PropHuntMod.Utils.Networking.FromServer.PropLocation>)OnPropLocation); receiver.RegisterPacketHandler<global::PropHuntMod.Utils.Networking.FromServer.PropFound>(CustomPackets.PropFound, (GenericClientPacketHandler<global::PropHuntMod.Utils.Networking.FromServer.PropFound>)OnPropFound); receiver.RegisterPacketHandler<RoundStart>(CustomPackets.RoundStart, (GenericClientPacketHandler<RoundStart>)OnRoundStart); receiver.RegisterPacketHandler<GameOver>(CustomPackets.GameOver, (GenericClientPacketHandler<GameOver>)OnGameOver); receiver.RegisterPacketHandler<SeekerStart>(CustomPackets.SeekerStart, (GenericClientPacketHandler<SeekerStart>)OnSeekerStart); receiver.RegisterPacketHandler<FailedAction>(CustomPackets.FailedAction, (GenericClientPacketHandler<FailedAction>)ClientErrorCorrection.DiagnoseError); if (Config.AllowDebugFeatures) { receiver.RegisterPacketHandler<global::PropHuntMod.Utils.Networking.FromServer.HideStatus>(CustomPackets.HideStatus, (GenericClientPacketHandler<global::PropHuntMod.Utils.Networking.FromServer.HideStatus>)OnHideStatus); } } private static void OnPropSwap(global::PropHuntMod.Utils.Networking.FromServer.PropSwap data) { PlayerManager.GetPlayerManager(data.Id).SetProp(data.propName, data.propPath); Log.LogInfo($"{data.Id} prop set to {data.propName}"); } private static void OnRoundStart(RoundStart data) { bool flag = data.SeekerWaitTime == 0; if (flag) { PropHuntClient.GameState = GameState.Playing; } else { PropHuntClient.GameState = GameState.SeekerWait; } PropHuntClient.isSeeker = data.IsSeeker; PropHuntClient.propSwaps = 0; PropHuntClient.maxPropSwaps = data.PropSwapLimit; if (data.IsSeeker) { PropHuntClient.LocalMessage("You're a seeker!"); SelfCoverManager.instance.DisableProp(logOnFail: false); if (!flag) { SelfHornetManager.instance.SetSeekerObscure(enabled: true); EffectsManager.SetTitle("SEEKER", $"Wait time: {data.SeekerWaitTime} seconds", "YOUR ROLE:", large: true, 10f); } else { EffectsManager.SetTitle("SEEKER", "It's go time!", "YOUR ROLE:", large: true, 10f); } } else { EffectsManager.SetTitle("HIDER", "", "YOUR ROLE:"); SelfCoverManager.instance.EnableRandomProp(); PropHuntClient.LocalMessage("You're hiding this round!"); } } private static void OnPropLocation(global::PropHuntMod.Utils.Networking.FromServer.PropLocation data) { //IL_000c: 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) PlayerManager.GetPlayerManager(data.Id).SetPropLocation(data.PropPosition, data.PropRotation); Log.LogInfo($"{data.Id} prop moved to {data.PropPosition}, {data.PropRotation}"); } private static void OnHideStatus(global::PropHuntMod.Utils.Networking.FromServer.HideStatus data) { PlayerManager.GetPlayerManager(data.Id).SetHideStatus(data.IsHiding); Log.LogInfo($"{data.Id} hiding status set to {data.IsHiding}"); } private static void OnPropFound(global::PropHuntMod.Utils.Networking.FromServer.PropFound data) { if (data.IsClientFound) { Log.LogInfo("I've been found!"); SelfCoverManager.instance.FindProp(SelfHornetManager.instance); if (PropHuntClient.GameState == GameState.Playing) { PropHuntClient.isSeeker = true; } } else { PlayerManager playerManager = PlayerManager.GetPlayerManager(data.PropOwnerID); playerManager.coverManager.FindProp(playerManager.hornetManager); playerManager.SetProp("", ""); Log.LogInfo(playerManager.PlayerAvatar.Username + " has been found"); } EffectsManager.PlayFoundSound(data.IsClientFound); } private static void OnGameOver(GameOver data) { PropHuntClient.GameState = GameState.NotStarted; PropHuntClient.isSeeker = false; PropHuntClient.propSwaps = 0; SelfHornetManager.instance.SetSeekerObscure(enabled: false); SelfCoverManager.instance.DisableProp(); EffectsManager.PlayGameOverSound(!data.WasCanceled && data.IsWinner); string main = (data.WasCanceled ? "Round Canceled" : (data.IsWinner ? "You Won!" : "Round Complete")); string sub = ((data.IsWinner || data.WasCanceled) ? "" : (data.WinnerUsername + " won!")); EffectsManager.SetTitle(main, sub); if (data.IsWinner) { EffectsManager.PlayConfetti(); } GameManager.instance.FreezeMoment((FreezeMomentTypes)10, (Action)null); } private static void OnSeekerStart(SeekerStart data) { PropHuntClient.GameState = GameState.Playing; if (PropHuntClient.isSeeker) { SelfHornetManager.instance.SetSeekerObscure(enabled: false); } } } internal struct BypassTicket { public int Id; public CorrectionActions action; public BypassTicket(int Id = -1, CorrectionActions action = CorrectionActions.None) { this.Id = Id; this.action = action; } } internal static class ServerNetwork { private static IServerAddonNetworkSender<CustomPackets> sender; private static IServerAddonNetworkReceiver<CustomPackets> receiver; private static readonly Dictionary<ushort, List<BypassTicket>> tickets = new Dictionary<ushort, List<BypassTicket>>(); private static int TicketID = 0; private static BypassTicket GenerateTicket(ushort playerID, CorrectionActions action) { if (!tickets.ContainsKey(playerID)) { tickets[playerID] = new List<BypassTicket>(); } BypassTicket bypassTicket = default(BypassTicket); bypassTicket.action = action; bypassTicket.Id = TicketID; BypassTicket bypassTicket2 = bypassTicket; tickets[playerID].Add(bypassTicket2); TicketID++; return bypassTicket2; } private static bool IsValidTicket(ushort playerID, int ticketID, params CorrectionActions[] action) { if (ticketID == -1) { return false; } if (!tickets.ContainsKey(playerID)) { return false; } int num = tickets[playerID].FindIndex((BypassTicket t) => t.Id == ticketID && action.Contains(t.action)); if (num == -1) { return false; } tickets[playerID].RemoveAt(num); return true; } public static void Broadcast(ushort senderID, CustomPackets packetID, IPacketData data) { foreach (IServerPlayer player in PropHuntServer._serverApi.ServerManager.Players) { if (player.Id != senderID) { sender.SendSingleData(packetID, data, player.Id); } } } private static void FailedAction(ushort senderID, ushort affectedID, CustomPackets packetType, CorrectionActions fix) { int bypassTicketID = -1; if (fix == CorrectionActions.ToggleHornetFalse || fix == CorrectionActions.PreviousScene || fix == CorrectionActions.RestoreLastProp) { bypassTicketID = GenerateTicket(senderID, fix).Id; } sender.SendSingleData(CustomPackets.FailedAction, (IPacketData)(object)new FailedAction { AffectedID = affectedID, FailedPacket = packetType, FixMethod = fix, BypassTicketID = bypassTicketID }, senderID); } public static void ForwardPropSwap(ushort id, string propName, string propPath) { Log.LogInfo($"Broadcasting prop swap from {id}: {propName}"); Broadcast(id, CustomPackets.PropSwap, (IPacketData)(object)new global::PropHuntMod.Utils.Networking.FromServer.PropSwap { Id = id, propName = propName, propPath = propPath }); } public static void BroadcastRoundStart() { Log.LogInfo("Broadcasting round start"); foreach (IServerPlayer player in PropHuntServer._serverApi.ServerManager.Players) { SendRoundStart(player.Id); } } public static void SendRoundStart(ushort id, bool started = false) { ServerPlayer player = PropHuntServer.GetPlayer(id); RoundStart roundStart = new RoundStart { IsSeeker = player.seeker, PropSwapLimit = 0, SeekerWaitTime = ((!started) ? PropHuntServer.instance.SeekerTimer.seconds : 0) }; sender.SendSingleData(CustomPackets.RoundStart, (IPacketData)(object)roundStart, id); } public static void ForwardPropLocation(ushort id, Vector3 propPosition, float propRotation) { //IL_0013: Unknown result type (might be due to invalid IL or missing references) //IL_0042: Unknown result type (might be due to invalid IL or missing references) Log.LogInfo($"Broadcasting prop location from {id}: {propPosition}, {propRotation}"); BaseCoverManager.ConstrainPropLocation(ref propPosition, ref propRotation); Broadcast(id, CustomPackets.PropLocation, (IPacketData)(object)new global::PropHuntMod.Utils.Networking.FromServer.PropLocation { Id = id, PropPosition = propPosition, PropRotation = propRotation }); } public static void ForwardHideStatus(ushort id, bool isHiding) { Log.LogInfo($"Broadcasting hide status from {id}: {isHiding}"); Broadcast(id, CustomPackets.HideStatus, (IPacketData)(object)new global::PropHuntMod.Utils.Networking.FromServer.HideStatus { Id = id, IsHiding = isHiding }); } public static void ForwardPropFound(ushort id, ushort propOwnerID) { Log.LogInfo($"Broadcasting prop found from {id}: {propOwnerID}"); foreach (IServerPlayer player in PropHuntServer._serverApi.ServerManager.Players) { global::PropHuntMod.Utils.Networking.FromServer.PropFound propFound = new global::PropHuntMod.Utils.Networking.FromServer.PropFound { IsClientFound = (player.Id == propOwnerID), PropOwnerID = propOwnerID }; sender.SendSingleData(CustomPackets.PropFound, (IPacketData)(object)propFound, player.Id); } } public static void BroadcastGameOver(IServerPlayer winner, bool canceled) { Log.LogInfo("Broadcasting game over"); foreach (IServerPlayer player in PropHuntServer._serverApi.ServerManager.Players) { GameOver gameOver = new GameOver { IsWinner = (!canceled && ((winner != null) ? new ushort?(winner.Id) : null) == player.Id), WasCanceled = canceled, WinnerUsername = (((winner != null) ? winner.Username : null) ?? "Nobody") }; sender.SendSingleData(CustomPackets.GameOver, (IPacketData)(object)gameOver, player.Id); } } public static void BroadcastSeekerStart() { Log.LogInfo("Broadcasting seeker start"); sender.BroadcastSingleData(CustomPackets.SeekerStart, (IPacketData)(object)new SeekerStart()); } public static void Init(IServerApi serverApi, ServerAddon serverAddon) { sender = serverApi.NetServer.GetNetworkSender<CustomPackets>(serverAddon); receiver = serverApi.NetServer.GetNetworkReceiver<CustomPackets>(serverAddon, (Func<CustomPackets, IPacketData>)global::PropHuntMod.Utils.Networking.FromClient.Packets.Instantiate); receiver.RegisterPacketHandler<global::PropHuntMod.Utils.Networking.FromClient.PropSwap>(CustomPackets.PropSwap, (GenericServerPacketHandler<global::PropHuntMod.Utils.Networking.FromClient.PropSwap>)OnPropSwap); receiver.RegisterPacketHandler<global::PropHuntMod.Utils.Networking.FromClient.PropLocation>(CustomPackets.PropLocation, (GenericServerPacketHandler<global::PropHuntMod.Utils.Networking.FromClient.PropLocation>)OnPropLocation); receiver.RegisterPacketHandler<global::PropHuntMod.Utils.Networking.FromClient.PropFound>(CustomPackets.PropFound, (GenericServerPacketHandler<global::PropHuntMod.Utils.Networking.FromClient.PropFound>)OnPropFound); receiver.RegisterPacketHandler<global::PropHuntMod.Utils.Networking.FromClient.Sync>(CustomPackets.Sync, (GenericServerPacketHandler<global::PropHuntMod.Utils.Networking.FromClient.Sync>)OnSync); if (Config.AllowDebugFeatures) { receiver.RegisterPacketHandler<global::PropHuntMod.Utils.Networking.FromClient.HideStatus>(CustomPackets.HideStatus, (GenericServerPacketHandler<global::PropHuntMod.Utils.Networking.FromClient.HideStatus>)OnHideStatus); } } private static void OnPropSwap(ushort id, global::PropHuntMod.Utils.Networking.FromClient.PropSwap data) { ServerPlayer player = PropHuntServer.GetPlayer(id); bool flag = string.IsNullOrEmpty(data.propPath); if (player.seeker && PropHuntServer.GameState != 0 && !flag) { PropHuntServer.instance.Message(id, "You're a seeker! You can't hide this round."); FailedAction(id, id, CustomPackets.PropSwap, CorrectionActions.DisableClientProp); return; } bool flag2 = IsValidTicket(id, data.TicketID, CorrectionActions.RestoreLastProp, CorrectionActions.PreviousScene); if (flag) { player.propName = null; player.propPath = null; } else { player.propName = data.propName; player.propPath = data.propPath; } if (!flag2) { player.swapCount++; } ForwardPropSwap(id, player.propName, player.propPath); } private static void OnPropLocation(ushort id, global::PropHuntMod.Utils.Networking.FromClient.PropLocation data) { //IL_0032: Unknown result type (might be due to invalid IL or missing references) //IL_0037: Unknown result type (might be due to invalid IL or missing references) //IL_005b: Unknown result type (might be due to invalid IL or missing references) ServerPlayer player = PropHuntServer.GetPlayer(id); if (player.seeker && PropHuntServer.GameState != 0) { PropHuntServer.instance.Message(id, "You're a seeker! You can't hide this round."); FailedAction(id, id, CustomPackets.PropSwap, CorrectionActions.DisableClientProp); return; } player.propLocation = data.PropPosition; player.propRotation = data.PropRotation; BaseCoverManager.ConstrainPropLocation(ref player.propLocation, ref player.propRotation); ForwardPropLocation(id, player.propLocation, player.propRotation); } private static void OnSync(ushort id, global::PropHuntMod.Utils.Networking.FromClient.Sync data) { //IL_0057: 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_0031: Unknown result type (might be due to invalid IL or missing references) //IL_0036: Unknown result type (might be due to invalid IL or missing references) //IL_0092: Unknown result type (might be due to invalid IL or missing references) ServerPlayer player = PropHuntServer.GetPlayer(id); if (player.seeker) { player.propName = ""; player.propPath = ""; player.propRotation = 0f; player.propLocation = Vector3.zero; } else { player.propName = data.PropName; player.propPath = data.PropPath; player.propLocation = data.PropLocation; player.propRotation = data.PropRotation; } BaseCoverManager.ConstrainPropLocation(ref player.propLocation, ref player.propRotation); ForwardPropSwap(id, player.propName, player.propPath); ForwardPropLocation(id, player.propLocation, player.propRotation); PropHuntServer.instance.CheckGameOver(player.PlayerAvatar); } private static void OnHideStatus(ushort id, global::PropHuntMod.Utils.Networking.FromClient.HideStatus data) { ServerPlayer player = PropHuntServer.GetPlayer(id); if (PropHuntServer.GameState != 0 && player.seeker && data.IsHiding && !IsValidTicket(id, data.TicketID, CorrectionActions.ToggleHornetFalse)) { PropHuntServer.instance.Message(id, "You're a seeker! You can't hide this round."); FailedAction(id, id, CustomPackets.HideStatus, CorrectionActions.ToggleHornetTrue); } else { player.hidden = data.IsHiding; ForwardHideStatus(id, data.IsHiding); } } private static void OnPropFound(ushort id, global::PropHuntMod.Utils.Networking.FromClient.PropFound data) { //IL_00cb: Unknown result type (might be due to invalid IL or missing references) //IL_00d0: Unknown result type (might be due to invalid IL or missing references) ServerPlayer player = PropHuntServer.GetPlayer(data.PropOwnerID); ServerPlayer player2 = PropHuntServer.GetPlayer(id); if (PropHuntServer.GameState == GameState.SeekerWait) { PropHuntServer.instance.Message(id, "You're still in the waiting period. No seeking yet!"); FailedAction(id, data.PropOwnerID, CustomPackets.PropFound, CorrectionActions.RestoreTriggerHandler); return; } if (PropHuntServer.GameState == GameState.Playing) { if (player.seeker) { PropHuntServer.instance.Message(id, "That player is a seeker!"); FailedAction(id, data.PropOwnerID, CustomPackets.PropFound, CorrectionActions.DisablePlayerProp); return; } if (!player2.seeker) { PropHuntServer.instance.Message(id, "You're not a seeker! You can't find people this round."); FailedAction(id, data.PropOwnerID, CustomPackets.PropFound, CorrectionActions.RestoreTriggerHandler); return; } player.seeker = true; } if (string.IsNullOrEmpty(player.propName)) { PropHuntServer.instance.Message(id, "That player has already been found. You might be out of sync."); FailedAction(id, data.PropOwnerID, CustomPackets.PropFound, CorrectionActions.DisablePlayerProp); return; } player.propName = null; player.propLocation = Vector3.zero; player.propRotation = 0f; ForwardPropFound(id, data.PropOwnerID); PropHuntServer.instance.Announce(player.PlayerAvatar.Username + " was found by " + player2.PlayerAvatar.Username + "!"); if (PropHuntServer.GameState == GameState.Playing) { PropHuntServer.instance.CheckGameOver(player.PlayerAvatar); } } } } namespace PropHuntMod.Utils.Networking.FromServer { public class PropSwap : global::PropHuntMod.Utils.Networking.FromClient.PropSwap { public ushort Id { get; set; } public override void WriteData(IPacket packet) { packet.Write(Id); base.WriteData(packet); } public override void ReadData(IPacket packet) { Id = packet.ReadUShort(); base.ReadData(packet); } } public class RoundStart : IPacketData { public bool IsSeeker; public ushort PropSwapLimit; public int SeekerWaitTime; public bool IsReliable => true; public bool DropReliableDataIfNewerExists => true; public void WriteData(IPacket packet) { packet.Write(IsSeeker); packet.Write(PropSwapLimit); packet.Write(SeekerWaitTime); } public void ReadData(IPacket packet) { IsSeeker = packet.ReadBool(); PropSwapLimit = packet.ReadUShort(); SeekerWaitTime = packet.ReadInt(); } } public class PropLocation : global::PropHuntMod.Utils.Networking.FromClient.PropLocation { public ushort Id { get; set; } public override void WriteData(IPacket packet) { packet.Write(Id); base.WriteData(packet); } public override void ReadData(IPacket packet) { Id = packet.ReadUShort(); base.ReadData(packet); } } public class HideStatus : global::PropHuntMod.Utils.Networking.FromClient.HideStatus { public ushort Id { get; set; } public override void WriteData(IPacket packet) { packet.Write(Id); base.WriteData(packet); } public override void ReadData(IPacket packet) { Id = packet.ReadUShort(); base.ReadData(packet); } } public class PropFound : global::PropHuntMod.Utils.Networking.FromClient.PropFound { public bool IsClientFound { get; set; } public override void WriteData(IPacket packet) { packet.Write(IsClientFound); base.WriteData(packet); } public override void ReadData(IPacket packet) { IsClientFound = packet.ReadBool(); base.ReadData(packet); } } public class SeekerStart : IPacketData { public bool IsReliable => true; public bool DropReliableDataIfNewerExists => true; public void WriteData(IPacket packet) { } public void ReadData(IPacket packet) { } } public class GameOver : IPacketData { public bool IsReliable => true; public bool DropReliableDataIfNewerExists => true; public string WinnerUsername { get; set; } public bool IsWinner { get; set; } public bool WasCanceled { get; set; } public void WriteData(IPacket packet) { packet.Write(WinnerUsername); packet.Write(IsWinner); packet.Write(WasCanceled); } public void ReadData(IPacket packet) { WinnerUsername = packet.ReadString(); IsWinner = packet.ReadBool(); WasCanceled = packet.ReadBool(); } } public class FailedAction : IPacketData { public CustomPackets FailedPacket; public CorrectionActions FixMethod; public ushort AffectedID; public int BypassTicketID; public bool IsReliable => true; public bool DropReliableDataIfNewerExists => true; public void WriteData(IPacket packet) { packet.Write((int)FailedPacket); packet.Write((int)FixMethod); packet.Write(AffectedID); packet.Write(BypassTicketID); } public void ReadData(IPacket packet) { FailedPacket = (CustomPackets)packet.ReadInt(); FixMethod = (CorrectionActions)packet.ReadInt(); AffectedID = packet.ReadUShort(); BypassTicketID = packet.ReadUShort(); } } public static class Packets { internal static IPacketData Instantiate(CustomPackets packetID) { return (IPacketData)(packetID switch { CustomPackets.PropSwap => new PropSwap(), CustomPackets.RoundStart => new RoundStart(), CustomPackets.PropLocation => new PropLocation(), CustomPackets.HideStatus => new HideStatus(), CustomPackets.PropFound => new PropFound(), CustomPackets.GameOver => new GameOver(), CustomPackets.SeekerStart => new SeekerStart(), CustomPackets.FailedAction => new FailedAction(), _ => throw new NotImplementedException(packetID.ToString()), }); } } } namespace PropHuntMod.Utils.Networking.FromClient { public class PropSwap : IPacketData { public string propName = ""; public string propPath = ""; public int TicketID = -1; public bool IsReliable => true; public bool DropReliableDataIfNewerExists => true; public virtual void WriteData(IPacket packet) { packet.Write(propName); packet.Write(propPath); packet.Write(TicketID); } public virtual void ReadData(IPacket packet) { propName = packet.ReadString(); propPath = packet.ReadString(); TicketID = packet.ReadInt(); } } public class PropLocation : IPacketData { public bool IsReliable => true; public bool DropReliableDataIfNewerExists => true; public Vector3 PropPosition { get; set; } public float PropRotation { get; set; } public virtual void WriteData(IPacket packet) { //IL_0002: Unknown result type (might be due to invalid IL or missing references) //IL_0013: Unknown result type (might be due to invalid IL or missing references) //IL_0024: Unknown result type (might be due to invalid IL or missing references) packet.Write(PropPosition.x); packet.Write(PropPosition.y); packet.Write(PropPosition.z); packet.Write(PropRotation); } public virtual void ReadData(IPacket packet) { //IL_0013: Unknown result type (might be due to invalid IL or missing references) PropPosition = new Vector3(packet.ReadFloat(), packet.ReadFloat(), packet.ReadFloat()); PropRotation = packet.ReadFloat(); } } public class HideStatus : IPacketData { public int TicketID = -1; public bool IsReliable => true; public bool DropReliableDataIfNewerExists => true; public bool IsHiding { get; set; } public virtual void WriteData(IPacket packet) { packet.Write(IsHiding); packet.Write(TicketID); } public virtual void ReadData(IPacket packet) { IsHiding = packet.ReadBool(); TicketID = packet.ReadInt(); } } public class PropFound : IPacketData { public bool IsReliable => true; public bool DropReliableDataIfNewerExists => true; public ushort PropOwnerID { get; set; } public virtual void WriteData(IPacket packet) { packet.Write(PropOwnerID); } public virtual void ReadData(IPacket packet) { PropOwnerID = packet.ReadUShort(); } } public class Sync : IPacketData { public bool IsReliable => true; public bool DropReliableDataIfNewerExists => true; public string PropName { get; set; } public string PropPath { get; set; } public Vector3 PropLocation { get; set; } public float PropRotation { get; set; } public virtual void WriteData(IPacket packet) { //IL_001a: Unknown result type (might be due to invalid IL or missing references) //IL_002b: Unknown result type (might be due to invalid IL or missing references) //IL_003c: Unknown result type (might be due to invalid IL or missing references) packet.Write(PropName); packet.Write(PropPath); packet.Write(PropLocation.x); packet.Write(PropLocation.y); packet.Write(PropLocation.z); packet.Write(PropRotation); } public virtual void ReadData(IPacket packet) { //IL_002b: Unknown result type (might be due to invalid IL or missing references) PropName = packet.ReadString(); PropPath = packet.ReadString(); PropLocation = new Vector3(packet.ReadFloat(), packet.ReadFloat(), packet.ReadFloat()); PropRotation = packet.ReadFloat(); } } public static class Packets { internal static IPacketData Instantiate(CustomPackets packetID) { return (IPacketData)(packetID switch { CustomPackets.PropSwap => new PropSwap(), CustomPackets.PropLocation => new PropLocation(), CustomPackets.HideStatus => new HideStatus(), CustomPackets.PropFound => new PropFound(), CustomPackets.Sync => new Sync(), _ => throw new NotImplementedException(packetID.ToString()), }); } } } namespace PropHuntMod.Server { public class SeekerTimer { public int seconds; private Timer timer; private void SetTimer(int seconds) { this.seconds = seconds; timer = new Timer(1000.0); timer.Elapsed += delegate { OnSecond(); }; timer.AutoReset = true; timer.Start(); } private void OnSecond() { seconds--; if (seconds <= 0) { timer.Stop(); timer = null; PropHuntServer.instance.Announce("[Seekers]: Ready or not, here we come!"); PropHuntServer.GameState = GameState.Playing; ServerNetwork.BroadcastSeekerStart(); } else if (seconds <= 5) { PropHuntServer.instance.Announce($"[Seekers]: {seconds}..."); } } public void CancelTimer() { if (timer != null) { timer.Stop(); timer = null; } } public SeekerTimer(int seconds) { SetTimer(seconds); } } internal class ServerPlayer { public ushort id; public bool hidden; public bool seeker; public string propName; public string propPath; public Vector3 propLocation = Vector3.zero; public float propRotation; public int swapCount; public IServerPlayer PlayerAvatar => PropHuntServer._serverApi.ServerManager.GetPlayer(id); public ServerPlayer(ushort id) { //IL_0001: Unknown result type (might be due to invalid IL or missing references) //IL_0006: Unknown result type (might be due to invalid IL or missing references) this.id = id; } } } namespace PropHuntMod.Properties { [GeneratedCode("System.Resources.Tools.StronglyTypedResourceBuilder", "17.0.0.0")] [DebuggerNonUserCode] [CompilerGenerated] internal class Resources { private static ResourceManager resourceMan; private static CultureInfo resourceCulture; [EditorBrowsable(EditorBrowsableState.Advanced)] internal static ResourceManager ResourceManager { get { if (resourceMan == null) { resourceMan = new ResourceManager("PropHuntMod.Properties.Resources", typeof(Resources).Assembly); } return resourceMan; } } [EditorBrowsable(EditorBrowsableState.Advanced)] internal static CultureInfo Culture { get { return resourceCulture; } set { resourceCulture = value; } } internal static byte[] bundle => (byte[])ResourceManager.GetObject("bundle", resourceCulture); internal static byte[] icon => (byte[])ResourceManager.GetObject("icon", resourceCulture); internal static byte[] manifest => (byte[])ResourceManager.GetObject("manifest", resourceCulture); internal Resources() { } } internal sealed class Settings { private void SettingChangingEventHandler(object sender, SettingChangingEventArgs e) { } private void SettingsSavingEventHandler(object sender, CancelEventArgs e) { } } } namespace PropHuntMod.Modifications { internal class AttackCooldownPatches { private readonly TraceListener listener = new ConsoleTraceListener(); public AttackCooldownPatches() { Trace.Listeners.Add(listener); } public static void SetAttackCooldown(ref float cooldown) { float num = 0f; cooldown = num; Log.LogInfo("cooled down"); } [HarmonyPrefix] [HarmonyPatch(typeof(HeroController), "CanAttack")] public static void Attack(HeroController __instance) { Console.WriteLine(new StackTrace(fNeedFileInfo: true).ToString()); } } internal class EffectVerticalSweep : MonoBehaviour { [CompilerGenerated] private sealed class <Sweep>d__13 : IEnumerator<object>, IDisposable, IEnumerator { private int <>1__state; private object <>2__current; public EffectVerticalSweep <>4__this; private int <i>5__2; private float <t>5__3; object IEnumerator<object>.Current { [DebuggerHidden] get { return <>2__current; } } object IEnumerator.Current { [DebuggerHidden] get { return <>2__current; } } [DebuggerHidden] public <Sweep>d__13(int <>1__state) { this.<>1__state = <>1__state; } [DebuggerHidden] void IDisposable.Dispose() { <>1__state = -2; } private bool MoveNext() { //IL_00b5: Unknown result type (might be due to invalid IL or missing references) //IL_00bf: Expected O, but got Unknown int num = <>1__state; EffectVerticalSweep effectVerticalSweep = <>4__this; switch (num) { default: return false; case 0: <>1__state = -1; <i>5__2 = 0; goto IL_00ea; case 1: <>1__state = -1; goto IL_0085; case 2: { <>1__state = -1; effectVerticalSweep.SetSweep(0f); goto IL_00da; } IL_00ea: if (<i>5__2 < effectVerticalSweep.sweepCount) { <t>5__3 = 0f; goto IL_0085; } effectVerticalSweep.onComplete?.Invoke(); Debug.Log((object)"Sweep finished"); return false; IL_0085: if (<t>5__3 < effectVerticalSweep.duration) { <t>5__3 += Time.deltaTime; float sweep = Mathf.Clamp01(<t>5__3 / effectVerticalSweep.duration); effectVerticalSweep.SetSweep(sweep); <>2__current = null; <>1__state = 1; return true; } effectVerticalSweep.SetSweep(1f); if (<i>5__2 < effectVerticalSweep.sweepCount - 1) { <>2__current = (object)new WaitForSeconds(effectVerticalSweep.delayBetweenSweeps); <>1__state = 2; return true; } goto IL_00da; IL_00da: <i>5__2++; goto IL_00ea; } } 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 int sweepCount = 3; public float duration = 1f; public float delayBetweenSweeps = 0.3f; public Action onComplete; private SpriteRenderer[] renderers; private MaterialPropertyBlock block; private static int MinY; private static int MaxY; private static int SweepID; private void Awake() { //IL_000d: Unknown result type (might be due to invalid IL or missing references) //IL_0017: Expected O, but got Unknown //IL_002a: Unknown result type (might be due to invalid IL or missing references) //IL_0034: Expected O, but got Unknown renderers = ((Component)this).GetComponentsInChildren<SpriteRenderer>(); block = new MaterialPropertyBlock(); SpriteRenderer[] array = renderers; for (int i = 0; i < array.Length; i++) { ((Renderer)array[i]).material = new Material(EffectsManager.SweepShader); } MinY = Shader.PropertyToID("_BoundsMinY"); MaxY = Shader.PropertyToID("_BoundsMaxY"); SweepID = Shader.PropertyToID("_SweepPosition"); ComputeAndApplyBounds(); } private void ComputeAndApplyBounds() { //IL_001a: Unknown result type (might be due to invalid IL or missing references) //IL_001f: Unknown result type (might be due to invalid IL or missing references) //IL_0024: Unknown result type (might be due to invalid IL or missing references) //IL_0037: Unknown result type (might be due to invalid IL or missing references) float num = float.PositiveInfinity; float num2 = float.NegativeInfinity; SpriteRenderer[] array = renderers; for (int i = 0; i < array.Length; i++) { Bounds bounds = ((Renderer)array[i]).bounds; num = Mathf.Min(num, ((Bounds)(ref bounds)).min.y); num2 = Mathf.Max(num2, ((Bounds)(ref bounds)).max.y); } array = renderers; foreach (SpriteRenderer obj in array) { ((Renderer)obj).GetPropertyBlock(block); block.SetFloat(MinY, num); block.SetFloat(MaxY, num2); ((Renderer)obj).SetPropertyBlock(block); } } private void Start() { Play(); } private void Play() { ((MonoBehaviour)this).StopAllCoroutines(); ((MonoBehaviour)this).StartCoroutine(Sweep()); } [IteratorStateMachine(typeof(<Sweep>d__13))] private IEnumerator Sweep() { //yield-return decompiler failed: Unexpected instruction in Iterator.Dispose() return new <Sweep>d__13(0) { <>4__this = this }; } private void SetSweep(float value) { SpriteRenderer[] array