diff --git a/CTA/CustomTeamAssigner/CustomRoles.cs b/CTA/CustomTeamAssigner/CustomRoles.cs index 03da76733..1c8a3cfd0 100644 --- a/CTA/CustomTeamAssigner/CustomRoles.cs +++ b/CTA/CustomTeamAssigner/CustomRoles.cs @@ -136,6 +136,7 @@ Alchemist, Altruist, Analyst, + Ankylosaurus, Autocrat, Bane, Beacon, @@ -300,6 +301,7 @@ Maverick, Medusa, Mycologist, + NecroGuesser, Necromancer, Nonplus, NoteKiller, @@ -351,6 +353,7 @@ Wraith, Werewolf, WeaponMaster, + Weatherman, Workaholic, // Solo Kombat diff --git a/GameMode/AllInOneGameMode.cs b/GameMode/AllInOneGameMode.cs new file mode 100644 index 000000000..217eca7c8 --- /dev/null +++ b/GameMode/AllInOneGameMode.cs @@ -0,0 +1,56 @@ +using System.Collections.Generic; +using System.Diagnostics.CodeAnalysis; +using System.Linq; +using HarmonyLib; + +namespace EHR +{ + public static class AllInOneGameMode + { + public static HashSet Taskers = []; + + public static void Init() + { + Taskers = []; + } + + [HarmonyPatch(typeof(PlayerControl), nameof(PlayerControl.FixedUpdate))] + private static class FixedUpdatePatch + { + [SuppressMessage("ReSharper", "UnusedMember.Local")] + public static void Postfix(PlayerControl __instance) + { + if (!AmongUsClient.Instance.AmHost || !GameStates.IsInTask || GameStates.IsEnded || !CustomGameMode.AllInOne.IsActiveOrIntegrated() || Main.HasJustStarted) return; + + bool doneWithTasks = Taskers.Contains(__instance.PlayerId) && __instance.GetTaskState().IsTaskFinished; + + if (doneWithTasks && !__instance.Is(CustomRoles.Killer)) + { + Taskers.Remove(__instance.PlayerId); + __instance.RpcChangeRoleBasis(CustomRoles.Killer); + __instance.RpcSetCustomRole(CustomRoles.Killer); + Logger.Info($"{__instance.GetRealName()} has completed all tasks, changing role to Killer", "AllInOneGameMode"); + return; + } + + Vector2 pos = __instance.Pos(); + + bool nearTask = __instance.myTasks.ToArray().Where(x => !x.IsComplete).SelectMany(x => x.FindValidConsolesPositions().ToArray()).Any(x => Vector2.Distance(x, pos) <= DisableDevice.UsableDistance); + + switch (nearTask) + { + case true when Taskers.Add(__instance.PlayerId): + __instance.RpcChangeRoleBasis(CustomRoles.Tasker); + __instance.RpcSetCustomRole(CustomRoles.Tasker); + Logger.Info($"{__instance.GetRealName()} is near an incomplete task, changing role to Tasker", "AllInOneGameMode"); + break; + case false when Taskers.Remove(__instance.PlayerId): + __instance.RpcChangeRoleBasis(CustomRoles.KB_Normal); + __instance.RpcSetCustomRole(CustomRoles.KB_Normal); + Logger.Info($"{__instance.GetRealName()} is no longer near an incomplete task, changing role to KB_Normal", "AllInOneGameMode"); + break; + } + } + } + } +} \ No newline at end of file diff --git a/GameMode/CTFManager.cs b/GameMode/CTFManager.cs index ccdd31ee8..3bac72ec2 100644 --- a/GameMode/CTFManager.cs +++ b/GameMode/CTFManager.cs @@ -1,5 +1,6 @@ using System; using System.Collections.Generic; +using System.Diagnostics.CodeAnalysis; using System.Linq; using AmongUs.GameOptions; using EHR.Modules; @@ -205,7 +206,7 @@ namespace EHR ValidTag = false; // Check if the current game mode is Capture The Flag - if (Options.CurrentGameMode != CustomGameMode.CaptureTheFlag) return; + if (!CustomGameMode.CaptureTheFlag.IsActiveOrIntegrated()) return; LateTask.New(() => { @@ -474,9 +475,10 @@ namespace EHR [HarmonyPatch(typeof(PlayerControl), nameof(PlayerControl.FixedUpdate))] private static class FixedUpdatePatch { + [SuppressMessage("ReSharper", "UnusedMember.Local")] public static void Postfix(PlayerControl __instance) { - if (!AmongUsClient.Instance.AmHost || !GameStates.IsInTask || Options.CurrentGameMode != CustomGameMode.CaptureTheFlag || Main.HasJustStarted || !__instance.IsHost()) return; + if (!AmongUsClient.Instance.AmHost || !GameStates.IsInTask || !CustomGameMode.CaptureTheFlag.IsActiveOrIntegrated() || Main.HasJustStarted || !__instance.IsHost()) return; TeamData.Values.Do(x => x.Update()); } diff --git a/GameMode/FFAManager.cs b/GameMode/FFAManager.cs index bf61f25c5..7d741d5da 100644 --- a/GameMode/FFAManager.cs +++ b/GameMode/FFAManager.cs @@ -130,7 +130,7 @@ namespace EHR public static void Init() { - if (Options.CurrentGameMode != CustomGameMode.FFA) return; + if (!CustomGameMode.FFA.IsActiveOrIntegrated()) return; FFADecreasedSpeedList = []; FFAIncreasedSpeedList = []; @@ -185,7 +185,7 @@ namespace EHR public static void OnPlayerAttack(PlayerControl killer, PlayerControl target) { - if (killer == null || target == null || Options.CurrentGameMode != CustomGameMode.FFA) return; + if (killer == null || target == null || !CustomGameMode.FFA.IsActiveOrIntegrated()) return; if (target.inVent) { @@ -391,7 +391,7 @@ namespace EHR [SuppressMessage("ReSharper", "UnusedMember.Local")] public static void Postfix() { - if (!GameStates.IsInTask || ExileController.Instance || Options.CurrentGameMode != CustomGameMode.FFA || !AmongUsClient.Instance.AmHost) return; + if (!GameStates.IsInTask || ExileController.Instance || !CustomGameMode.FFA.IsActiveOrIntegrated() || !AmongUsClient.Instance.AmHost) return; long now = Utils.TimeStamp; if (LastFixedUpdate == now) return; diff --git a/GameMode/HnSManager.cs b/GameMode/HnSManager.cs index 18812a7f9..85ca17cbb 100644 --- a/GameMode/HnSManager.cs +++ b/GameMode/HnSManager.cs @@ -299,7 +299,7 @@ namespace EHR public static string GetSuffixText(PlayerControl seer, PlayerControl target, bool hud = false) { - if (GameStates.IsLobby || Options.CurrentGameMode != CustomGameMode.HideAndSeek || Main.HasJustStarted) return string.Empty; + if (GameStates.IsLobby || !CustomGameMode.HideAndSeek.IsActiveOrIntegrated() || Main.HasJustStarted) return string.Empty; if (seer.PlayerId != target.PlayerId || (seer.IsHost() && !hud) || TimeLeft < 0) return string.Empty; @@ -484,7 +484,7 @@ namespace EHR { public static void Postfix() { - if (!AmongUsClient.Instance.AmHost || !GameStates.IsInTask || Options.CurrentGameMode != CustomGameMode.HideAndSeek || Main.HasJustStarted) return; + if (!AmongUsClient.Instance.AmHost || !GameStates.IsInTask || !CustomGameMode.HideAndSeek.IsActiveOrIntegrated() || Main.HasJustStarted) return; long now = Utils.TimeStamp; if (LastUpdate == now) return; diff --git a/GameMode/HotPotatoManager.cs b/GameMode/HotPotatoManager.cs index 6b57ed060..587aeae3a 100644 --- a/GameMode/HotPotatoManager.cs +++ b/GameMode/HotPotatoManager.cs @@ -46,7 +46,7 @@ namespace EHR { FixedUpdatePatch.Return = true; - HotPotatoState = (byte.MaxValue, byte.MaxValue, Time.GetInt() + 50, 1); + HotPotatoState = (byte.MaxValue, byte.MaxValue, Time.GetInt() + 60, 1); SurvivalTimes = []; foreach (PlayerControl pc in Main.AllPlayerControls) SurvivalTimes[pc.PlayerId] = 0; @@ -56,7 +56,7 @@ namespace EHR public static void OnGameStart() { LateTask.New(() => { FixedUpdatePatch.Return = false; }, 7f, log: false); - HotPotatoState = (byte.MaxValue, byte.MaxValue, Time.GetInt() + 30, 1); + HotPotatoState = (byte.MaxValue, byte.MaxValue, Time.GetInt() + 40, 1); } public static int GetSurvivalTime(byte id) @@ -71,6 +71,7 @@ namespace EHR public static string GetSuffixText(byte id) { + if (!Main.PlayerStates.TryGetValue(id, out var state) || state.IsDead) return string.Empty; return $"{(HotPotatoState.HolderID == id ? $"{Translator.GetString("HotPotato_HoldingNotify")}\n" : string.Empty)}{Translator.GetString("HotPotato_TimeLeftSuffix")}{HotPotatoState.TimeLeft}s"; } @@ -84,7 +85,7 @@ namespace EHR [SuppressMessage("ReSharper", "UnusedMember.Local")] public static void Postfix(PlayerControl __instance) { - if (Options.CurrentGameMode != CustomGameMode.HotPotato || Return || !AmongUsClient.Instance.AmHost || !GameStates.IsInTask) return; + if (!CustomGameMode.HotPotato.IsActiveOrIntegrated() || Return || !AmongUsClient.Instance.AmHost || !GameStates.IsInTask || __instance.PlayerId == 255) return; PlayerControl Holder = Utils.GetPlayerById(HotPotatoState.HolderID); @@ -136,7 +137,8 @@ namespace EHR if (resetTime) { - HotPotatoState.TimeLeft = Time.GetInt(); + int time = Time.GetInt(); + HotPotatoState.TimeLeft = Options.CurrentGameMode == CustomGameMode.AllInOne ? time * 3 : time; HotPotatoState.RoundNum++; } diff --git a/GameMode/MoveAndStop.cs b/GameMode/MoveAndStop.cs index f886928dc..2a862a87e 100644 --- a/GameMode/MoveAndStop.cs +++ b/GameMode/MoveAndStop.cs @@ -159,14 +159,14 @@ namespace EHR public static int RoundTime { get; set; } - private static bool HasJustStarted => GameTime.GetInt() - RoundTime < 25; + private static bool HasJustStarted => GameTime.GetInt() - RoundTime < 20; private static int ExtraGreenTime => (MapNames)Main.NormalOptions.MapId switch { MapNames.Airship => ExtraGreenTimeOnAirhip.GetInt(), MapNames.Fungle => ExtraGreenTimeOnFungle.GetInt(), _ => 0 - }; + } + (Options.CurrentGameMode == CustomGameMode.AllInOne ? 15 : 0); private static IntegerValueRule CounterValueRule => new(1, 100, 1); private static IntegerValueRule ExtraTimeValue => new(0, 50, 1); @@ -177,7 +177,8 @@ namespace EHR private static int StartingGreenTime(PlayerControl pc) { - return (MapNames)Main.NormalOptions.MapId == MapNames.Airship ? EnableTutorial.GetBool() && !HasPlayed.Contains(pc.FriendCode) ? 70 : 50 : EnableTutorial.GetBool() && !HasPlayed.Contains(pc.FriendCode) ? 60 : 40; + bool tutorial = EnableTutorial.GetBool() && !HasPlayed.Contains(pc.FriendCode) && Options.CurrentGameMode != CustomGameMode.AllInOne; + return Main.CurrentMap == MapNames.Airship ? tutorial ? 57 : 47 : tutorial ? 47 : 37; } private static int RandomRedTime(char direction) @@ -268,7 +269,7 @@ namespace EHR public static void Init() { - if (Options.CurrentGameMode != CustomGameMode.MoveAndStop) return; + if (!CustomGameMode.MoveAndStop.IsActiveOrIntegrated()) return; FixedUpdatePatch.LastSuffix = []; FixedUpdatePatch.Limit = []; @@ -276,7 +277,7 @@ namespace EHR RoundTime = GameTime.GetInt() + 8; FixedUpdatePatch.DoChecks = false; - LateTask.New(() => { FixedUpdatePatch.DoChecks = true; }, 10f, log: false); + LateTask.New(() => FixedUpdatePatch.DoChecks = true, 10f, log: false); long now = Utils.TimeStamp; @@ -329,7 +330,7 @@ namespace EHR var text = timers.ToString(); - if (HasJustStarted && EnableTutorial.GetBool() && !HasPlayed.Contains(pc.FriendCode)) + if (HasJustStarted && EnableTutorial.GetBool() && !HasPlayed.Contains(pc.FriendCode) && Options.CurrentGameMode != CustomGameMode.AllInOne) text += $"\n\n{GetString("MoveAndStop_Tutorial")}"; return text; @@ -348,7 +349,7 @@ namespace EHR [SuppressMessage("ReSharper", "UnusedMember.Local")] public static void Postfix(PlayerControl __instance) { - if (!GameStates.IsInTask || Options.CurrentGameMode != CustomGameMode.MoveAndStop || !__instance.IsAlive() || !AmongUsClient.Instance.AmHost || !DoChecks) return; + if (!GameStates.IsInTask || !CustomGameMode.MoveAndStop.IsActiveOrIntegrated() || !__instance.IsAlive() || !AmongUsClient.Instance.AmHost || !DoChecks || __instance.PlayerId == 255) return; PlayerControl pc = __instance; diff --git a/GameMode/NaturalDisasters.cs b/GameMode/NaturalDisasters.cs index 9688ff2a3..564f0cc51 100644 --- a/GameMode/NaturalDisasters.cs +++ b/GameMode/NaturalDisasters.cs @@ -108,7 +108,7 @@ namespace EHR BuildingCollapse.CollapsedRooms.Clear(); BuildingCollapse.LastPosition.Clear(); - if (Options.CurrentGameMode != CustomGameMode.NaturalDisasters) return; + if (!CustomGameMode.NaturalDisasters.IsActiveOrIntegrated()) return; Dictionary.ValueCollection rooms = RoomLocations()?.Values; if (rooms == null) return; @@ -206,7 +206,7 @@ namespace EHR [SuppressMessage("ReSharper", "UnusedMember.Local")] public static void Postfix(PlayerControl __instance) { - if (!AmongUsClient.Instance.AmHost || !GameStates.IsInTask || Options.CurrentGameMode != CustomGameMode.NaturalDisasters || Main.HasJustStarted || GameStartTimeStamp + 5 > Utils.TimeStamp || !__instance.IsHost()) return; + if (!AmongUsClient.Instance.AmHost || !GameStates.IsInTask || !CustomGameMode.NaturalDisasters.IsActiveOrIntegrated() || Main.HasJustStarted || GameStartTimeStamp + 5 > Utils.TimeStamp || !__instance.IsHost()) return; UpdatePreparingDisasters(); @@ -254,7 +254,10 @@ namespace EHR long now = Utils.TimeStamp; - if (now - LastDisaster >= DisasterFrequency.GetInt()) + int frequency = DisasterFrequency.GetInt(); + if (Options.CurrentGameMode == CustomGameMode.AllInOne && frequency < 10) frequency = 10; + + if (now - LastDisaster >= frequency) { LastDisaster = now; List disasters = AllDisasters.ToList(); @@ -273,12 +276,17 @@ namespace EHR }; SystemTypes? room = disaster.Name == "BuildingCollapse" ? roomKvp.Key : null; - PreparingDisasters.Add(new(position, DisasterWarningTime.GetFloat(), Sprite(disaster.Name), disaster.Name, room)); + float warningTime = DisasterWarningTime.GetFloat(); + if (Options.CurrentGameMode == CustomGameMode.AllInOne && warningTime < 30) warningTime = 30; + PreparingDisasters.Add(new(position, warningTime, Sprite(disaster.Name), disaster.Name, room)); } if (now - LastSync >= 10) { LastSync = now; + BuildingCollapse.CollapsedRooms.Clear(); + Sinkhole.RemoveRandomSinkhole(); + Utils.NotifyRoles(); Utils.MarkEveryoneDirtySettings(); } } diff --git a/GameMode/RoomRush.cs b/GameMode/RoomRush.cs index 7a65f4347..680c24bfb 100644 --- a/GameMode/RoomRush.cs +++ b/GameMode/RoomRush.cs @@ -162,7 +162,7 @@ namespace EHR public static void OnGameStart() { - if (Options.CurrentGameMode != CustomGameMode.RoomRush) return; + if (!CustomGameMode.RoomRush.IsActiveOrIntegrated()) return; Main.Instance.StartCoroutine(GameStartTasks()); } @@ -197,7 +197,7 @@ namespace EHR PlayerControl[] aapc = Main.AllAlivePlayerControls; aapc.Do(x => x.RpcSetCustomRole(CustomRoles.RRPlayer)); - bool showTutorial = aapc.ExceptBy(HasPlayedFriendCodes, x => x.FriendCode).Count() >= aapc.Length / 3; + bool showTutorial = aapc.ExceptBy(HasPlayedFriendCodes, x => x.FriendCode).Count() >= aapc.Length / 3 && Options.CurrentGameMode != CustomGameMode.AllInOne; if (showTutorial) { @@ -287,6 +287,7 @@ namespace EHR } TimeLeft = Math.Max((int)Math.Round(time * GlobalTimeMultiplier.GetFloat()), 4); + if (Options.CurrentGameMode == CustomGameMode.AllInOne) TimeLeft *= 2; Logger.Info($"Starting a new round - Goal = from: {Translator.GetString(previous.ToString())}, to: {Translator.GetString(RoomGoal.ToString())} - Time: {TimeLeft} ({Main.CurrentMap})", "RoomRush"); Main.AllPlayerControls.Do(x => LocateArrow.RemoveAllTarget(x.PlayerId)); if (DisplayArrowToRoom.GetBool()) Main.AllPlayerControls.Do(x => LocateArrow.Add(x.PlayerId, goalPos)); @@ -317,15 +318,15 @@ namespace EHR bool done = dead || DonePlayers.Contains(seer.PlayerId); Color color = done ? Color.green : Color.yellow; - if (DisplayRoomName.GetBool()) sb.AppendLine(Utils.ColorString(color, Translator.GetString(RoomGoal.ToString()))); - if (DisplayArrowToRoom.GetBool()) sb.AppendLine(Utils.ColorString(color, LocateArrow.GetArrows(seer))); + if (DisplayRoomName.GetBool()) sb.Append(Utils.ColorString(color, Translator.GetString(RoomGoal.ToString())) + "\n"); + if (DisplayArrowToRoom.GetBool()) sb.Append(Utils.ColorString(color, LocateArrow.GetArrows(seer)) + "\n"); color = done ? Color.white : Color.yellow; - sb.AppendLine(Utils.ColorString(color, TimeLeft.ToString())); + sb.Append(Utils.ColorString(color, TimeLeft.ToString()) + "\n"); if (VentTimes.GetInt() == 0 || dead || seer.IsModClient()) return sb.ToString(); - sb.AppendLine(); + sb.Append('\n'); int vents = VentLimit.GetValueOrDefault(seer.PlayerId); sb.Append(string.Format(Translator.GetString("RR_VentsRemaining"), vents)); @@ -357,7 +358,7 @@ namespace EHR [SuppressMessage("ReSharper", "UnusedMember.Local")] public static void Postfix(PlayerControl __instance) { - if (!GameGoing || Main.HasJustStarted || Options.CurrentGameMode != CustomGameMode.RoomRush || !AmongUsClient.Instance.AmHost || !GameStates.IsInTask || !__instance.IsHost()) return; + if (!GameGoing || Main.HasJustStarted || !CustomGameMode.RoomRush.IsActiveOrIntegrated() || !AmongUsClient.Instance.AmHost || !GameStates.IsInTask || !__instance.IsHost()) return; long now = Utils.TimeStamp; PlayerControl[] aapc = Main.AllAlivePlayerControls; @@ -366,6 +367,8 @@ namespace EHR { PlainShipRoom room = pc.GetPlainShipRoom(); + bool notAllInOne = Options.CurrentGameMode != CustomGameMode.AllInOne; + if (pc.IsAlive() && !pc.inMovingPlat && room != null && room.RoomId == RoomGoal && DonePlayers.Add(pc.PlayerId)) { Logger.Info($"{pc.GetRealName()} entered the correct room", "RoomRush"); @@ -373,7 +376,7 @@ namespace EHR int timeLeft = TimeWhenFirstPlayerEntersRoom.GetInt(); - if (DonePlayers.Count == 2 && timeLeft < TimeLeft) + if (DonePlayers.Count == 2 && timeLeft < TimeLeft && notAllInOne) { Logger.Info($"Two players entered the correct room, setting the timer to {timeLeft}", "RoomRush"); TimeLeft = timeLeft; @@ -383,7 +386,7 @@ namespace EHR Achievements.Type.WheresTheBlueShell.CompleteAfterGameEnd(); } - if (DonePlayers.Count == aapc.Length - 1) + if (DonePlayers.Count == aapc.Length - 1 && notAllInOne) { PlayerControl last = aapc.First(x => !DonePlayers.Contains(x.PlayerId)); Logger.Info($"All players entered the correct room except one, killing the last player ({last.GetRealName()})", "RoomRush"); @@ -393,7 +396,8 @@ namespace EHR return; } } - else if (room == null || room.RoomId != RoomGoal) DonePlayers.Remove(pc.PlayerId); + else if ((room == null || room.RoomId != RoomGoal) && notAllInOne) + DonePlayers.Remove(pc.PlayerId); } if (LastUpdate == now) return; @@ -422,7 +426,7 @@ namespace EHR public class RRPlayer : RoleBase { - public override bool IsEnable => Options.CurrentGameMode == CustomGameMode.RoomRush; + public override bool IsEnable => CustomGameMode.RoomRush.IsActiveOrIntegrated(); public override void Init() { } diff --git a/GameMode/SoloKombatManager.cs b/GameMode/SoloKombatManager.cs index 06388cc5b..6a9b7f78c 100644 --- a/GameMode/SoloKombatManager.cs +++ b/GameMode/SoloKombatManager.cs @@ -1,5 +1,6 @@ using System; using System.Collections.Generic; +using System.Diagnostics.CodeAnalysis; using System.Linq; using EHR.Modules; using EHR.Neutral; @@ -81,7 +82,7 @@ namespace EHR public static void Init() { - if (Options.CurrentGameMode != CustomGameMode.SoloKombat) return; + if (!CustomGameMode.SoloKombat.IsActiveOrIntegrated()) return; PlayerHPMax = []; PlayerHP = []; @@ -131,7 +132,7 @@ namespace EHR public static void GetNameNotify(PlayerControl player, ref string name) { - if (Options.CurrentGameMode != CustomGameMode.SoloKombat || player == null) return; + if (!CustomGameMode.SoloKombat.IsActiveOrIntegrated() || player == null) return; if (BackCountdown.TryGetValue(player.PlayerId, out int value)) { @@ -165,7 +166,7 @@ namespace EHR public static void OnPlayerAttack(PlayerControl killer, PlayerControl target) { - if (killer == null || target == null || Options.CurrentGameMode != CustomGameMode.SoloKombat) return; + if (killer == null || target == null || !CustomGameMode.SoloKombat.IsActiveOrIntegrated()) return; if (!killer.SoloAlive() || !target.SoloAlive() || target.inVent) return; @@ -228,6 +229,7 @@ namespace EHR OriginalSpeed.Remove(target.PlayerId); OriginalSpeed.Add(target.PlayerId, Main.AllPlayerSpeed[target.PlayerId]); + PetsPatch.RpcRemovePet(target); target.TP(Pelican.GetBlackRoomPS()); Main.AllPlayerSpeed[target.PlayerId] = Main.MinSpeed; target.MarkDirtySettings(); @@ -242,6 +244,9 @@ namespace EHR KBScore[killer.PlayerId]++; + if (Options.CurrentGameMode == CustomGameMode.AllInOne) + SpeedrunManager.ResetTimer(killer); + float addRate = IRandom.Instance.Next(3, 5 + GetRankOfScore(killer.PlayerId)) / 100f; addRate *= KB_KillBonusMultiplier.GetFloat(); if (killer.IsHost()) addRate /= 2f; @@ -285,62 +290,58 @@ namespace EHR { private static long LastFixedUpdate; - public static void Postfix( /*PlayerControl __instance*/) + [SuppressMessage("ReSharper", "UnusedMember.Local")] + public static void Postfix(PlayerControl __instance) { - if (!GameStates.IsInTask || Options.CurrentGameMode != CustomGameMode.SoloKombat || !AmongUsClient.Instance.AmHost) return; + byte id = __instance.PlayerId; + if (!GameStates.IsInTask || !CustomGameMode.SoloKombat.IsActiveOrIntegrated() || !AmongUsClient.Instance.AmHost || id == 255) return; - foreach (PlayerControl pc in Main.AllPlayerControls) + if (!__instance.SoloAlive()) { - if (!pc.SoloAlive()) - { - if (pc.inVent && KB_BootVentWhenDead.GetBool()) pc.MyPhysics.RpcExitVent(2); + if (__instance.inVent && KB_BootVentWhenDead.GetBool()) __instance.MyPhysics.RpcExitVent(2); - Vector2 pos = Pelican.GetBlackRoomPS(); - float dis = Vector2.Distance(pos, pc.Pos()); - if (dis > 1f) pc.TP(pos); - } + Vector2 pos = Pelican.GetBlackRoomPS(); + float dis = Vector2.Distance(pos, __instance.Pos()); + if (dis > 1f) __instance.TP(pos); } - if (LastFixedUpdate == Utils.TimeStamp) return; + var notifyRoles = false; + if (LastHurt[id] + KB_RecoverAfterSecond.GetInt() < Utils.TimeStamp && PlayerHP[id] < PlayerHPMax[id] && __instance.SoloAlive() && !__instance.inVent) + { + PlayerHP[id] += PlayerHPReco[id]; + PlayerHP[id] = Math.Min(PlayerHPMax[id], PlayerHP[id]); + notifyRoles = true; + } + + if (__instance.SoloAlive() && !__instance.inVent) + { + Vector2 pos = Pelican.GetBlackRoomPS(); + float dis = Vector2.Distance(pos, __instance.Pos()); + if (dis < 1.1f) PlayerRandomSpwan(__instance); + } + + if (BackCountdown.ContainsKey(id)) + { + BackCountdown[id]--; + if (BackCountdown[id] <= 0) OnPlayerBack(__instance); + + notifyRoles = true; + } + + if (NameNotify.ContainsKey(id) && NameNotify[id].TimeStamp < Utils.TimeStamp) + { + NameNotify.Remove(id); + notifyRoles = true; + } + + if (notifyRoles) Utils.NotifyRoles(SpecifySeer: __instance, SpecifyTarget: __instance); + + + if (LastFixedUpdate == Utils.TimeStamp) return; LastFixedUpdate = Utils.TimeStamp; RoundTime--; - - foreach (PlayerControl pc in Main.AllPlayerControls) - { - var notifyRoles = false; - - if (LastHurt[pc.PlayerId] + KB_RecoverAfterSecond.GetInt() < Utils.TimeStamp && PlayerHP[pc.PlayerId] < PlayerHPMax[pc.PlayerId] && pc.SoloAlive() && !pc.inVent) - { - PlayerHP[pc.PlayerId] += PlayerHPReco[pc.PlayerId]; - PlayerHP[pc.PlayerId] = Math.Min(PlayerHPMax[pc.PlayerId], PlayerHP[pc.PlayerId]); - notifyRoles = true; - } - - if (pc.SoloAlive() && !pc.inVent) - { - Vector2 pos = Pelican.GetBlackRoomPS(); - float dis = Vector2.Distance(pos, pc.Pos()); - if (dis < 1.1f) PlayerRandomSpwan(pc); - } - - if (BackCountdown.ContainsKey(pc.PlayerId)) - { - BackCountdown[pc.PlayerId]--; - if (BackCountdown[pc.PlayerId] <= 0) OnPlayerBack(pc); - - notifyRoles = true; - } - - if (NameNotify.ContainsKey(pc.PlayerId) && NameNotify[pc.PlayerId].TimeStamp < Utils.TimeStamp) - { - NameNotify.Remove(pc.PlayerId); - notifyRoles = true; - } - - if (notifyRoles) Utils.NotifyRoles(SpecifySeer: pc, SpecifyTarget: pc); - } } } diff --git a/GameMode/SpeedrunManager.cs b/GameMode/SpeedrunManager.cs index d0f5d65bd..3b79cd2bd 100644 --- a/GameMode/SpeedrunManager.cs +++ b/GameMode/SpeedrunManager.cs @@ -1,4 +1,5 @@ using System.Collections.Generic; +using System.Diagnostics.CodeAnalysis; using System.Linq; using EHR.Modules; using HarmonyLib; @@ -16,7 +17,7 @@ namespace EHR public static HashSet CanKill = []; - private static Dictionary Timers = []; + public static Dictionary Timers = []; public static void SetupCustomOption() { @@ -49,15 +50,18 @@ namespace EHR public static void Init() { CanKill = []; - Timers = Main.AllAlivePlayerControls.ToDictionary(x => x.PlayerId, _ => TimeLimit.GetInt() + 5); + Timers = Main.AllAlivePlayerControls.ToDictionary(x => x.PlayerId, _ => TimeLimit.GetInt() + 7); } public static void ResetTimer(PlayerControl pc) { + int timer = TimeLimit.GetInt(); + if (Options.CurrentGameMode == CustomGameMode.AllInOne) timer *= 2; + if (TimeStacksUp.GetBool()) - Timers[pc.PlayerId] += TimeLimit.GetInt(); + Timers[pc.PlayerId] += timer; else - Timers[pc.PlayerId] = TimeLimit.GetInt(); + Timers[pc.PlayerId] = timer; Logger.Info($" Timer for {pc.GetRealName()} set to {Timers[pc.PlayerId]}", "Speedrun"); } @@ -97,7 +101,6 @@ namespace EHR // ReSharper disable once ConvertIfStatementToReturnStatement if (CanKill.Contains(pc.PlayerId)) return string.Format(Translator.GetString("Speedrun_CanKillSuffixInfo"), alive, apc, killers - 1, time); - return string.Format(Translator.GetString("Speedrun_DoTasksSuffixInfo"), pc.GetTaskState().RemainingTasksCount, alive, apc, killers, time); } @@ -146,9 +149,10 @@ namespace EHR { private static long LastUpdate; + [SuppressMessage("ReSharper", "UnusedMember.Local")] public static void Postfix(PlayerControl __instance) { - if (!AmongUsClient.Instance.AmHost || !GameStates.IsInTask || Options.CurrentGameMode != CustomGameMode.Speedrun || Main.HasJustStarted) return; + if (!AmongUsClient.Instance.AmHost || !GameStates.IsInTask || !CustomGameMode.Speedrun.IsActiveOrIntegrated() || Main.HasJustStarted || __instance.PlayerId == 255) return; if (__instance.IsAlive() && Timers[__instance.PlayerId] <= 0) { diff --git a/Modules/CustomNetObject.cs b/Modules/CustomNetObject.cs index be7c55a11..2ee54b0cf 100644 --- a/Modules/CustomNetObject.cs +++ b/Modules/CustomNetObject.cs @@ -101,7 +101,7 @@ namespace EHR } catch (Exception e) { - if (Options.CurrentGameMode == CustomGameMode.NaturalDisasters) + if (CustomGameMode.NaturalDisasters.IsActiveOrIntegrated()) { if (HiddenList.Contains(PlayerControl.LocalPlayer.PlayerId)) return; @@ -774,7 +774,7 @@ internal static class RawSetNamePatch { public static bool Prefix(PlayerControl __instance, [HarmonyArgument(0)] string name) { - if (Options.CurrentGameMode != CustomGameMode.NaturalDisasters) return true; + if (!CustomGameMode.NaturalDisasters.IsActiveOrIntegrated()) return true; var exception = false; diff --git a/Modules/CustomRoleSelector.cs b/Modules/CustomRoleSelector.cs index e97821ff3..edaaa0dc0 100644 --- a/Modules/CustomRoleSelector.cs +++ b/Modules/CustomRoleSelector.cs @@ -36,6 +36,7 @@ namespace EHR.Modules switch (Options.CurrentGameMode) { + case CustomGameMode.AllInOne: case CustomGameMode.SoloKombat: AssignRoleToEveryone(CustomRoles.KB_Normal); return; @@ -629,7 +630,7 @@ namespace EHR.Modules public static void SelectAddonRoles() { - if (Options.CurrentGameMode != CustomGameMode.Standard) return; + if (!CustomGameMode.Standard.IsActiveOrIntegrated()) return; foreach (byte id in Main.SetAddOns.Keys.Where(id => Utils.GetPlayerById(id) == null).ToArray()) Main.SetAddOns.Remove(id); diff --git a/Modules/CustomRolesHelper.cs b/Modules/CustomRolesHelper.cs index 235863154..7378a5578 100644 --- a/Modules/CustomRolesHelper.cs +++ b/Modules/CustomRolesHelper.cs @@ -743,7 +743,7 @@ namespace EHR public static bool PetActivatedAbility(this CustomRoles role) { - if (Options.CurrentGameMode == CustomGameMode.CaptureTheFlag) return true; + if (CustomGameMode.CaptureTheFlag.IsActiveOrIntegrated()) return true; if (!Options.UsePets.GetBool()) return false; diff --git a/Modules/EAC.cs b/Modules/EAC.cs index 0208b6d41..a230b747d 100644 --- a/Modules/EAC.cs +++ b/Modules/EAC.cs @@ -729,7 +729,7 @@ namespace EHR public static void Postfix(PlayerControl __instance) { - if (!GameStates.IsInTask || ExileController.Instance || !Options.EnableMovementChecking.GetBool() || Main.HasJustStarted || MeetingStates.FirstMeeting || Main.RealOptionsData.GetFloat(FloatOptionNames.PlayerSpeedMod) >= 1.9f || AmongUsClient.Instance.Ping >= 300 || Options.CurrentGameMode == CustomGameMode.NaturalDisasters || Utils.GetRegionName() is not ("EU" or "NA" or "AS") || __instance == null || __instance.PlayerId == 255 || !__instance.IsAlive() || __instance.inVent) return; + if (!GameStates.IsInTask || ExileController.Instance || !Options.EnableMovementChecking.GetBool() || Main.HasJustStarted || MeetingStates.FirstMeeting || Main.RealOptionsData.GetFloat(FloatOptionNames.PlayerSpeedMod) >= 1.9f || AmongUsClient.Instance.Ping >= 300 || CustomGameMode.NaturalDisasters.IsActiveOrIntegrated() || Utils.GetRegionName() is not ("EU" or "NA" or "AS") || __instance == null || __instance.PlayerId == 255 || !__instance.IsAlive() || __instance.inVent) return; Vector2 pos = __instance.Pos(); long now = Utils.TimeStamp; diff --git a/Modules/ExtendedPlayerControl.cs b/Modules/ExtendedPlayerControl.cs index 2dcdf853b..3db98c349 100644 --- a/Modules/ExtendedPlayerControl.cs +++ b/Modules/ExtendedPlayerControl.cs @@ -1,4 +1,5 @@ using System; +using System.Collections; using System.Collections.Generic; using System.Diagnostics; using System.Linq; @@ -67,7 +68,7 @@ namespace EHR public static bool CanUseVent(this PlayerControl player, int ventId) { - if (Options.CurrentGameMode == CustomGameMode.RoomRush) return true; + if (CustomGameMode.RoomRush.IsActiveOrIntegrated()) return true; if (player.Is(CustomRoles.Trainee) && MeetingStates.FirstMeeting) return false; return GameStates.IsInTask && ((player.inVent && player.GetClosestVent()?.Id == ventId) || ((player.CanUseImpostorVentButton() || player.GetRoleTypes() == RoleTypes.Engineer) && Main.PlayerStates.Values.All(x => x.Role.CanUseVent(player, ventId)))); } @@ -364,7 +365,7 @@ namespace EHR Main.Instance.StartCoroutine(DelayBasisChange()); return; - System.Collections.IEnumerator DelayBasisChange() + IEnumerator DelayBasisChange() { while (AntiBlackout.SkipTasks || ExileController.Instance) yield return null; yield return new WaitForSeconds(1f); @@ -892,7 +893,8 @@ namespace EHR pc.Kill(pc); - if (Options.CurrentGameMode == CustomGameMode.NaturalDisasters) NaturalDisasters.RecordDeath(pc, deathReason); + if (Options.CurrentGameMode == CustomGameMode.NaturalDisasters) + NaturalDisasters.RecordDeath(pc, deathReason); } public static void SetKillCooldown(this PlayerControl player, float time = -1f, PlayerControl target = null, bool forceAnime = false) @@ -1062,7 +1064,7 @@ namespace EHR public static string GetNameWithRole(this PlayerControl player, bool forUser = false) { - return $"{player?.Data?.PlayerName}" + (GameStates.IsInGame && Options.CurrentGameMode is not CustomGameMode.FFA and not CustomGameMode.MoveAndStop and not CustomGameMode.HotPotato and not CustomGameMode.Speedrun and not CustomGameMode.CaptureTheFlag and not CustomGameMode.NaturalDisasters and not CustomGameMode.RoomRush ? $" ({player?.GetAllRoleName(forUser).RemoveHtmlTags().Replace('\n', ' ')})" : string.Empty); + return $"{player?.Data?.PlayerName}" + (GameStates.IsInGame && Options.CurrentGameMode is not CustomGameMode.FFA and not CustomGameMode.MoveAndStop and not CustomGameMode.HotPotato and not CustomGameMode.Speedrun and not CustomGameMode.CaptureTheFlag and not CustomGameMode.NaturalDisasters and not CustomGameMode.RoomRush and not CustomGameMode.AllInOne ? $" ({player?.GetAllRoleName(forUser).RemoveHtmlTags().Replace('\n', ' ')})" : string.Empty); } public static string GetRoleColorCode(this PlayerControl player) @@ -1226,6 +1228,8 @@ namespace EHR return false; case CustomGameMode.CaptureTheFlag: return true; + case CustomGameMode.AllInOne: + return !AllInOneGameMode.Taskers.Contains(pc.PlayerId); } if (Mastermind.ManipulatedPlayers.ContainsKey(pc.PlayerId)) return true; @@ -1284,6 +1288,7 @@ namespace EHR CustomGameMode.CaptureTheFlag => false, CustomGameMode.NaturalDisasters => false, CustomGameMode.RoomRush => false, + CustomGameMode.AllInOne => false, CustomGameMode.Standard when CopyCat.Instances.Any(x => x.CopyCatPC.PlayerId == pc.PlayerId) => true, CustomGameMode.Standard when pc.Is(CustomRoles.Nimble) || Options.EveryoneCanVent.GetBool() => true, @@ -1511,7 +1516,7 @@ namespace EHR public static void Kill(this PlayerControl killer, PlayerControl target) { - if (Options.CurrentGameMode == CustomGameMode.SoloKombat) return; + if (CustomGameMode.SoloKombat.IsActiveOrIntegrated()) return; if (target == null) target = killer; @@ -1536,7 +1541,7 @@ namespace EHR Main.DiedThisRound.Add(target.PlayerId); - if (killer.IsLocalPlayer() && !killer.HasKillButton() && killer.PlayerId != target.PlayerId && Options.CurrentGameMode == CustomGameMode.Standard) + if (killer.IsLocalPlayer() && !killer.HasKillButton() && killer.PlayerId != target.PlayerId && CustomGameMode.Standard.IsActiveOrIntegrated()) Achievements.Type.InnocentKiller.Complete(); switch (killer.PlayerId == target.PlayerId) diff --git a/Modules/GameOptionsSender/PlayerGameOptionsSender.cs b/Modules/GameOptionsSender/PlayerGameOptionsSender.cs index bd2c5edf6..f6e33fbe2 100644 --- a/Modules/GameOptionsSender/PlayerGameOptionsSender.cs +++ b/Modules/GameOptionsSender/PlayerGameOptionsSender.cs @@ -145,6 +145,7 @@ namespace EHR.Modules switch (Options.CurrentGameMode) { + case CustomGameMode.AllInOne: case CustomGameMode.FFA: if (FFAManager.FFALowerVisionList.ContainsKey(player.PlayerId)) { @@ -155,6 +156,7 @@ namespace EHR.Modules else SetMaxVision(); + if (Options.CurrentGameMode == CustomGameMode.AllInOne) goto case CustomGameMode.NaturalDisasters; break; case CustomGameMode.CaptureTheFlag: CTFManager.ApplyGameOptions(opt); @@ -163,6 +165,7 @@ namespace EHR.Modules case CustomGameMode.NaturalDisasters: SetMaxVision(); NaturalDisasters.ApplyGameOptions(opt, player.PlayerId); + if (Options.CurrentGameMode == CustomGameMode.AllInOne) goto case CustomGameMode.RoomRush; break; case CustomGameMode.RoomRush when RoomRush.VentLimit[player.PlayerId] > 0: AURoleOptions.EngineerCooldown = 0.01f; diff --git a/Modules/GameState.cs b/Modules/GameState.cs index 126c86286..d4480aa8c 100644 --- a/Modules/GameState.cs +++ b/Modules/GameState.cs @@ -162,7 +162,7 @@ namespace EHR LateTask.New(() => Player.CheckAndSetUnshiftState(), 1f, log: false); - if (Options.CurrentGameMode == CustomGameMode.Standard && GameStates.IsInTask && !AntiBlackout.SkipTasks) + if (CustomGameMode.Standard.IsActiveOrIntegrated() && GameStates.IsInTask && !AntiBlackout.SkipTasks) Player.Notify(string.Format(Translator.GetString("RoleChangedNotify"), role.ToColoredString()), 10f); if (Options.UsePets.GetBool()) Player.RpcSetPetDesync(PetsPatch.GetPetId(), Player); @@ -340,7 +340,7 @@ namespace EHR RPC.SendDeathReason(PlayerId, deathReason); Utils.CheckAndSpawnAdditionalRefugee(Utils.GetPlayerInfoById(PlayerId)); - if (Utils.DoRPC && Options.CurrentGameMode != CustomGameMode.Standard) + if (Utils.DoRPC && !CustomGameMode.Standard.IsActiveOrIntegrated()) Main.AllPlayerControls.DoIf(x => x.IsNonHostModClient(), x => Player.RpcSetRoleDesync(RoleTypes.CrewmateGhost, x.GetClientId())); } } @@ -405,7 +405,7 @@ namespace EHR { bool alive = player.IsAlive(); - if (alive && Options.CurrentGameMode == CustomGameMode.Speedrun) + if (alive && CustomGameMode.Speedrun.IsActiveOrIntegrated()) { if (CompletedTasksCount + 1 >= AllTasksCount) SpeedrunManager.OnTaskFinish(player); diff --git a/Modules/GhostRolesManager.cs b/Modules/GhostRolesManager.cs index a40c928ee..311527318 100644 --- a/Modules/GhostRolesManager.cs +++ b/Modules/GhostRolesManager.cs @@ -93,7 +93,7 @@ namespace EHR.Modules { try { - if (Options.CurrentGameMode != CustomGameMode.Standard) return false; + if (!CustomGameMode.Standard.IsActiveOrIntegrated()) return false; if (AssignedGhostRoles.Count >= GhostRoles.Count) return false; diff --git a/Modules/GuessManager.cs b/Modules/GuessManager.cs index aa5511991..497527224 100644 --- a/Modules/GuessManager.cs +++ b/Modules/GuessManager.cs @@ -377,6 +377,7 @@ namespace EHR { if (!isUI) Utils.SendMessage(GetString("CantGuessJailed"), pc.PlayerId, Utils.ColorString(Utils.GetRoleColor(CustomRoles.Jailor), GetString("JailorTitle"))); else pc.ShowPopUp($"{Utils.ColorString(Utils.GetRoleColor(CustomRoles.Jailor), GetString("JailorTitle"))}\n{GetString("CantGuessJailed")}"); + return true; } @@ -384,6 +385,7 @@ namespace EHR { if (!isUI) Utils.SendMessage(GetString("JailedCanOnlyGuessJailor"), pc.PlayerId, Utils.ColorString(Utils.GetRoleColor(CustomRoles.Jailor), GetString("JailorTitle"))); else pc.ShowPopUp($"{Utils.ColorString(Utils.GetRoleColor(CustomRoles.Jailor), GetString("JailorTitle"))}\n{GetString("JailedCanOnlyGuessJailor")}"); + return true; } @@ -442,12 +444,14 @@ namespace EHR { if (!isUI) Utils.SendMessage(GetString("GuessCrewRole"), pc.PlayerId, Utils.ColorString(Color.cyan, GetString("MessageFromGurge44"))); else pc.ShowPopUp($"{Utils.ColorString(Color.cyan, GetString("MessageFromGurge44"))}\n{GetString("GuessCrewRole")}"); + return true; } else if (pc.Is(CustomRoles.EvilGuesser) && target.IsImpostor() && !Options.EGCanGuessImp.GetBool()) { if (!isUI) Utils.SendMessage(GetString("GuessImpRole"), pc.PlayerId, Utils.ColorString(Color.cyan, GetString("MessageFromGurge44"))); else pc.ShowPopUp($"{Utils.ColorString(Color.cyan, GetString("MessageFromGurge44"))}\n{GetString("GuessImpRole")}"); + return true; } else if (!target.Is(role)) @@ -462,6 +466,7 @@ namespace EHR { if (!isUI) Utils.SendMessage(GetString("MisguessButNoSuicide"), pc.PlayerId, Utils.ColorString(Color.yellow, GetString("MessageFromGurge44"))); else pc.ShowPopUp($"{Utils.ColorString(Color.yellow, GetString("MessageFromGurge44"))}\n{GetString("MisguessButNoSuicide")}"); + return true; } @@ -586,7 +591,7 @@ namespace EHR pc.Data.IsDead = true; pc.RpcExileV2(); Main.PlayerStates[pc.PlayerId].SetDead(); - + var meetingHud = MeetingHud.Instance; ProcessGuess(pc, meetingHud); @@ -595,9 +600,9 @@ namespace EHR if (playerVoteArea.VotedFor != pc.PlayerId) continue; playerVoteArea.UnsetVote(); - + PlayerControl voteAreaPlayer = Utils.GetPlayerById(playerVoteArea.TargetPlayerId); - + if (!voteAreaPlayer.AmOwner) meetingHud.RpcClearVote(voteAreaPlayer.GetClientId()); else meetingHud.ClearVote(); } @@ -651,10 +656,10 @@ namespace EHR if (playerVoteArea.VotedFor != pc.PlayerId) continue; playerVoteArea.UnsetVote(); - + PlayerControl voteAreaPlayer = Utils.GetPlayerById(playerVoteArea.TargetPlayerId); if (!voteAreaPlayer.AmOwner) continue; - + meetingHud.ClearVote(); } } @@ -979,7 +984,7 @@ namespace EHR if (!role.IsEnable() && !role.RoleExist(true) && !role.IsConverted()) continue; - if (Options.CurrentGameMode != CustomGameMode.Standard || HnSManager.AllHnSRoles.Contains(role)) continue; + if (!CustomGameMode.Standard.IsActiveOrIntegrated() || HnSManager.AllHnSRoles.Contains(role)) continue; CreateRole(role); } diff --git a/Modules/NameColorManager.cs b/Modules/NameColorManager.cs index 358a59479..574a79c61 100644 --- a/Modules/NameColorManager.cs +++ b/Modules/NameColorManager.cs @@ -46,6 +46,7 @@ namespace EHR case CustomGameMode.MoveAndStop: color = "#ffffff"; return true; + case CustomGameMode.AllInOne: case CustomGameMode.HotPotato: (byte HolderID, byte LastHolderID) = HotPotatoManager.GetState(); @@ -53,6 +54,8 @@ namespace EHR color = "#000000"; else if (target.PlayerId == LastHolderID) color = "#00ffff"; + else if (Options.CurrentGameMode == CustomGameMode.AllInOne && SpeedrunManager.CanKill.Contains(target.PlayerId)) + color = Main.ImpostorColor; else color = "#ffffff"; diff --git a/Modules/OptionHolder.cs b/Modules/OptionHolder.cs index cf9991af1..6f6a7f0d7 100644 --- a/Modules/OptionHolder.cs +++ b/Modules/OptionHolder.cs @@ -27,6 +27,7 @@ namespace EHR CaptureTheFlag = 0x08, NaturalDisasters = 0x09, RoomRush = 0x0A, + AllInOne = 0x0B, All = int.MaxValue } @@ -62,7 +63,8 @@ namespace EHR "Speedrun", "CaptureTheFlag", "NaturalDisasters", - "RoomRush" + "RoomRush", + "AllInOne" ]; private static Dictionary roleCounts; @@ -71,7 +73,7 @@ namespace EHR public static Dictionary CustomRoleSpawnChances; public static Dictionary CustomAdtRoleSpawnRate; - public static Dictionary RoleSubCategoryLimits = []; + public static readonly Dictionary RoleSubCategoryLimits = []; public static readonly string[] Rates = [ @@ -175,7 +177,7 @@ namespace EHR public static OptionItem DisableMeeting; public static OptionItem DisableCloseDoor; public static OptionItem DisableSabotage; - + public static OptionItem DisableWhisperCommand; public static OptionItem DisableReactorOnSkeldAndMira; @@ -794,20 +796,22 @@ namespace EHR CustomRolesHelper.CanCheck = true; } - public static CustomGameMode CurrentGameMode - => GameMode.GetInt() switch - { - 1 => CustomGameMode.SoloKombat, - 2 => CustomGameMode.FFA, - 3 => CustomGameMode.MoveAndStop, - 4 => CustomGameMode.HotPotato, - 5 => CustomGameMode.HideAndSeek, - 6 => CustomGameMode.Speedrun, - 7 => CustomGameMode.CaptureTheFlag, - 8 => CustomGameMode.NaturalDisasters, - 9 => CustomGameMode.RoomRush, - _ => CustomGameMode.Standard - }; + public static CustomGameMode CurrentGameMode => GameMode.GetInt() switch + { + 1 => CustomGameMode.SoloKombat, + 2 => CustomGameMode.FFA, + 3 => CustomGameMode.MoveAndStop, + 4 => CustomGameMode.HotPotato, + 5 => CustomGameMode.HideAndSeek, + 6 => CustomGameMode.Speedrun, + 7 => CustomGameMode.CaptureTheFlag, + 8 => CustomGameMode.NaturalDisasters, + 9 => CustomGameMode.RoomRush, + 10 => CustomGameMode.AllInOne, + _ => CustomGameMode.Standard + }; + + public static bool IsActiveOrIntegrated(this CustomGameMode customGameMode) => CurrentGameMode == customGameMode || (CurrentGameMode == CustomGameMode.AllInOne && customGameMode is not CustomGameMode.FFA and not CustomGameMode.CaptureTheFlag and not CustomGameMode.HideAndSeek and not CustomGameMode.Standard and not CustomGameMode.AllInOne); [HarmonyPatch(typeof(TranslationController), nameof(TranslationController.Initialize))] [HarmonyPostfix] @@ -1590,43 +1594,43 @@ namespace EHR .SetGameMode(CustomGameMode.Standard) .SetParent(CommsCamouflage) .SetColor(new Color32(243, 96, 96, byte.MaxValue)); - + CommsCamouflageLimit = new BooleanOptionItem(22203, "CommsCamouflageLimit", false, TabGroup.GameSettings) .SetGameMode(CustomGameMode.Standard) .SetParent(CommsCamouflage) .SetColor(new Color32(243, 96, 96, byte.MaxValue)); - + CommsCamouflageLimitSetChance = new BooleanOptionItem(22204, "CommsCamouflageLimitSetChance", false, TabGroup.GameSettings) .SetGameMode(CustomGameMode.Standard) .SetParent(CommsCamouflageLimit) .SetColor(new Color32(243, 96, 96, byte.MaxValue)); - + CommsCamouflageLimitChance = new IntegerOptionItem(22205, "CommsCamouflageLimitChance", new(0, 100, 5), 50, TabGroup.GameSettings) .SetGameMode(CustomGameMode.Standard) .SetParent(CommsCamouflageLimit) .SetValueFormat(OptionFormat.Percent) .SetColor(new Color32(243, 96, 96, byte.MaxValue)); - + CommsCamouflageLimitSetFrequency = new BooleanOptionItem(22206, "CommsCamouflageLimitSetFrequency", false, TabGroup.GameSettings) .SetGameMode(CustomGameMode.Standard) .SetParent(CommsCamouflageLimit) .SetColor(new Color32(243, 96, 96, byte.MaxValue)); - + CommsCamouflageLimitFrequency = new IntegerOptionItem(22207, "CommsCamouflageLimitFrequency", new(1, 10, 1), 2, TabGroup.GameSettings) .SetGameMode(CustomGameMode.Standard) .SetParent(CommsCamouflageLimit) .SetColor(new Color32(243, 96, 96, byte.MaxValue)); - + CommsCamouflageLimitSetMaxTimes = new BooleanOptionItem(22208, "CommsCamouflageLimitSetMaxTimes", false, TabGroup.GameSettings) .SetGameMode(CustomGameMode.Standard) .SetParent(CommsCamouflageLimit) .SetColor(new Color32(243, 96, 96, byte.MaxValue)); - + CommsCamouflageLimitMaxTimesPerGame = new IntegerOptionItem(22209, "CommsCamouflageLimitMaxTimesPerGame", new(1, 30, 1), 3, TabGroup.GameSettings) .SetGameMode(CustomGameMode.Standard) .SetParent(CommsCamouflageLimit) .SetColor(new Color32(243, 96, 96, byte.MaxValue)); - + CommsCamouflageLimitMaxTimesPerRound = new IntegerOptionItem(22210, "CommsCamouflageLimitMaxTimesPerRound", new(1, 10, 1), 1, TabGroup.GameSettings) .SetGameMode(CustomGameMode.Standard) .SetParent(CommsCamouflageLimit) @@ -1807,7 +1811,7 @@ namespace EHR DisableCloseDoor = new BooleanOptionItem(22810, "DisableCloseDoor", false, TabGroup.GameSettings) .SetParent(DisableSabotage) .SetColor(new Color32(255, 153, 153, byte.MaxValue)); - + DisableWhisperCommand = new BooleanOptionItem(22811, "DisableWhisperCommand", false, TabGroup.GameSettings) .SetColor(new Color32(255, 153, 153, byte.MaxValue)); diff --git a/Modules/OptionItem/OptionItem.cs b/Modules/OptionItem/OptionItem.cs index f931eb37a..d7fb985cc 100644 --- a/Modules/OptionItem/OptionItem.cs +++ b/Modules/OptionItem/OptionItem.cs @@ -171,14 +171,14 @@ namespace EHR } // Getter - public virtual string GetName(bool disableColor = false, bool console = false) + public string GetName(bool disableColor = false, bool console = false) { if (Name.Contains("CTA.FLAG")) return Utils.ColorString(NameColor, Translator.GetString("CTA.TeamEnabled.Prefix") + Name[8..] + Translator.GetString("CTA.TeamEnabled.Suffix")); return disableColor ? Translator.GetString(Name, ReplacementDictionary, console) : Utils.ColorString(NameColor, Translator.GetString(Name, ReplacementDictionary)); } - public virtual bool GetBool() + public bool GetBool() { return (Parent == null || Parent.GetBool()) && Name switch { @@ -209,9 +209,10 @@ namespace EHR return IsSingleValue ? SingleValue : AllValues[CurrentPreset]; } - public virtual bool IsHiddenOn(CustomGameMode mode) + public bool IsCurrentlyHidden() { - return CheckHidden() || (GameMode != CustomGameMode.All && GameMode != mode); + var mode = EHR.Options.CurrentGameMode; + return CheckHidden() || (GameMode != CustomGameMode.All && GameMode != mode && !(mode == CustomGameMode.AllInOne && GameMode is CustomGameMode.SoloKombat or CustomGameMode.MoveAndStop or CustomGameMode.HotPotato or CustomGameMode.Speedrun or CustomGameMode.NaturalDisasters or CustomGameMode.RoomRush)); } private bool CheckHidden() @@ -235,7 +236,7 @@ namespace EHR return string.Format(Translator.GetString("Format." + ValueFormat), value); } - protected virtual void Refresh() + protected void Refresh() { if (OptionBehaviour is StringOption opt) { diff --git a/Modules/OptionShower.cs b/Modules/OptionShower.cs index 79a2b0ef3..9741c6893 100644 --- a/Modules/OptionShower.cs +++ b/Modules/OptionShower.cs @@ -41,7 +41,7 @@ namespace EHR sb.Append($"{GetString("Message.HideGameSettings")}"); else { - if (Options.CurrentGameMode == CustomGameMode.Standard) + if (CustomGameMode.Standard.IsActiveOrIntegrated()) { sb.Append($"{Utils.GetRoleName(CustomRoles.GM)}: {(Main.GM.Value ? GetString("RoleRate") : GetString("RoleOff"))}\n\n"); sb.Append(GetString("ActiveRolesList")).Append('\n'); @@ -70,11 +70,11 @@ namespace EHR Pages.Add(""); sb.Append($"{Utils.GetRoleName(CustomRoles.GM)}: {(Main.GM.Value ? GetString("RoleRate") : GetString("RoleOff"))}\n\n"); - if (Options.CurrentGameMode != CustomGameMode.HideAndSeek) + if (!CustomGameMode.HideAndSeek.IsActiveOrIntegrated()) { foreach (KeyValuePair kvp in Options.CustomRoleSpawnChances) { - if (!kvp.Key.IsEnable() || kvp.Value.IsHiddenOn(Options.CurrentGameMode)) continue; + if (!kvp.Key.IsEnable() || kvp.Value.IsCurrentlyHidden()) continue; sb.Append('\n'); sb.Append($"{Utils.ColorString(Utils.GetRoleColor(kvp.Key), Utils.GetRoleName(kvp.Key))}: {kvp.Value.GetString()} ×{kvp.Key.GetCount()}\n"); @@ -84,7 +84,7 @@ namespace EHR foreach (OptionItem opt in OptionItem.AllOptions) { - if (opt.Id is >= 90000 and (< 600000 or > 700000) && !opt.IsHiddenOn(Options.CurrentGameMode) && opt.Parent == null && !opt.IsText) + if (opt.Id is >= 90000 and (< 600000 or > 700000) && !opt.IsCurrentlyHidden() && opt.Parent == null && !opt.IsText) { if (opt.IsHeader) sb.Append('\n'); diff --git a/Modules/RPC.cs b/Modules/RPC.cs index 7a3979b81..cc55422a5 100644 --- a/Modules/RPC.cs +++ b/Modules/RPC.cs @@ -1096,7 +1096,7 @@ namespace EHR.Modules } case CustomRPC.FFAKill: { - if (Options.CurrentGameMode != CustomGameMode.FFA) + if (!CustomGameMode.FFA.IsActiveOrIntegrated()) { EAC.WarnHost(); EAC.Report(__instance, "FFA RPC when game mode is not FFA"); diff --git a/Modules/Statistics.cs b/Modules/Statistics.cs index ff645bc1a..9a2f1657c 100644 --- a/Modules/Statistics.cs +++ b/Modules/Statistics.cs @@ -175,7 +175,7 @@ namespace EHR.Modules { try { - if (Options.CurrentGameMode != CustomGameMode.Standard || Main.AllPlayerControls.Length <= MinPlayers) return; + if (!CustomGameMode.Standard.IsActiveOrIntegrated() || Main.AllPlayerControls.Length <= MinPlayers) return; PlayerControl lp = PlayerControl.LocalPlayer; @@ -258,7 +258,7 @@ namespace EHR.Modules { try { - if (Options.CurrentGameMode != CustomGameMode.Standard || killer.PlayerId == target.PlayerId || Main.AllPlayerControls.Length <= MinPlayers) return; + if (!CustomGameMode.Standard.IsActiveOrIntegrated() || killer.PlayerId == target.PlayerId || Main.AllPlayerControls.Length <= MinPlayers) return; if (killer.IsLocalPlayer()) { @@ -316,7 +316,7 @@ namespace EHR.Modules { try { - if (Options.CurrentGameMode != CustomGameMode.Standard || Main.AllPlayerControls.Length <= MinPlayers) return; + if (!CustomGameMode.Standard.IsActiveOrIntegrated() || Main.AllPlayerControls.Length <= MinPlayers) return; if (shapeshifter.IsLocalPlayer() && shapeshifting && animated) { diff --git a/Modules/Utils.cs b/Modules/Utils.cs index d68a7ec73..b8c3eaf81 100644 --- a/Modules/Utils.cs +++ b/Modules/Utils.cs @@ -503,7 +503,7 @@ other: ∟ ⌠ ⌡ ╬ ╨ ▓ ▒ ░ « » █ ▄ ▌▀▐│ ┤ ╡ ╢ if (!self && Main.DiedThisRound.Contains(seerId)) return (string.Empty, Color.white); - bool isHnsAgentOverride = Options.CurrentGameMode == CustomGameMode.HideAndSeek && targetMainRole == CustomRoles.Agent && HnSManager.PlayerRoles[seerId].Interface.Team != Team.Impostor; + bool isHnsAgentOverride = CustomGameMode.HideAndSeek.IsActiveOrIntegrated() && targetMainRole == CustomRoles.Agent && HnSManager.PlayerRoles[seerId].Interface.Team != Team.Impostor; var loversShowDifferentRole = false; if (!GameStates.IsEnded && targetMainRole == CustomRoles.LovingImpostor && !self && seerMainRole != CustomRoles.LovingCrewmate && !seerSubRoles.Contains(CustomRoles.Lovers)) @@ -773,6 +773,7 @@ other: ∟ ⌠ ⌡ ╬ ╨ ▓ ▒ ░ « » █ ▄ ▌▀▐│ ┤ ╡ ╢ case CustomGameMode.NaturalDisasters: return false; case CustomGameMode.RoomRush: return false; case CustomGameMode.HideAndSeek: return HnSManager.HasTasks(p); + case CustomGameMode.AllInOne: return AllInOneGameMode.Taskers.Contains(p.PlayerId); } CustomRoles role = state.MainRole; @@ -975,7 +976,7 @@ other: ∟ ⌠ ⌡ ╬ ╨ ▓ ▒ ░ « » █ ▄ ▌▀▐│ ┤ ╡ ╢ case CustomGameMode.CaptureTheFlag or CustomGameMode.NaturalDisasters or CustomGameMode.RoomRush: case CustomGameMode.Standard when CustomRoles.Altruist.RoleExist() && Main.DiedThisRound.Contains(PlayerControl.LocalPlayer.PlayerId): return PlayerControl.LocalPlayer.Is(CustomRoles.GM); - case CustomGameMode.FFA or CustomGameMode.SoloKombat or CustomGameMode.MoveAndStop or CustomGameMode.HotPotato or CustomGameMode.Speedrun: + case CustomGameMode.FFA or CustomGameMode.SoloKombat or CustomGameMode.MoveAndStop or CustomGameMode.HotPotato or CustomGameMode.Speedrun or CustomGameMode.AllInOne: case CustomGameMode.HideAndSeek when HnSManager.IsRoleTextEnabled(PlayerControl.LocalPlayer, __instance): return true; } @@ -1194,7 +1195,7 @@ other: ∟ ⌠ ⌡ ╬ ╨ ▓ ▒ ░ « » █ ▄ ▌▀▐│ ┤ ╡ ╢ void CheckAndAppendOptionString(OptionItem item) { - if (item.GetBool() && item.Parent == null && !item.IsHiddenOn(Options.CurrentGameMode)) + if (item.GetBool() && item.Parent == null && !item.IsCurrentlyHidden()) { sb.Append($"\n{item.GetName(true)}: {item.GetString()}"); } @@ -1244,7 +1245,7 @@ other: ∟ ⌠ ⌡ ╬ ╨ ▓ ▒ ░ « » █ ▄ ▌▀▐│ ┤ ╡ ╢ foreach (OptionItem opt in OptionItem.AllOptions) { - if (opt.GetBool() && opt.Parent == null && opt.Id is >= 80000 and < 640000 && !opt.IsHiddenOn(Options.CurrentGameMode)) + if (opt.GetBool() && opt.Parent == null && opt.Id is >= 80000 and < 640000 && !opt.IsCurrentlyHidden()) { if (opt.Name is "KillFlashDuration" or "RoleAssigningAlgorithm") sb.Append($"\n【{opt.GetName(true)}: {opt.GetString()}】\n"); @@ -1295,7 +1296,7 @@ other: ∟ ⌠ ⌡ ╬ ╨ ▓ ▒ ░ « » █ ▄ ▌▀▐│ ┤ ╡ ╢ sb.Append($"━━━━━━━━━━━━【{GetString("Settings")}】━━━━━━━━━━━━"); - foreach (OptionItem opt in OptionItem.AllOptions.Where(x => x.GetBool() && x.Parent == null && x.Id is >= 80000 and < 640000 && !x.IsHiddenOn(Options.CurrentGameMode))) + foreach (OptionItem opt in OptionItem.AllOptions.Where(x => x.GetBool() && x.Parent == null && x.Id is >= 80000 and < 640000 && !x.IsCurrentlyHidden())) { if (opt.Name == "KillFlashDuration") sb.Append($"\n【{opt.GetName(true)}: {opt.GetString()}】\n"); @@ -1326,7 +1327,7 @@ other: ∟ ⌠ ⌡ ╬ ╨ ▓ ▒ ░ « » █ ▄ ▌▀▐│ ┤ ╡ ╢ StringBuilder addonsb = new(); StringBuilder ghostsb = new(); - foreach (CustomRoles role in Options.CurrentGameMode == CustomGameMode.HideAndSeek ? HnSManager.AllHnSRoles : Enum.GetValues().Except(HnSManager.AllHnSRoles)) + foreach (CustomRoles role in CustomGameMode.HideAndSeek.IsActiveOrIntegrated() ? HnSManager.AllHnSRoles : Enum.GetValues().Except(HnSManager.AllHnSRoles)) { string mode; @@ -1484,6 +1485,7 @@ other: ∟ ⌠ ⌡ ╬ ╨ ▓ ▒ ░ « » █ ▄ ▌▀▐│ ┤ ╡ ╢ } break; + case CustomGameMode.AllInOne: case CustomGameMode.RoomRush: case CustomGameMode.NaturalDisasters: case CustomGameMode.CaptureTheFlag: @@ -1547,7 +1549,7 @@ other: ∟ ⌠ ⌡ ╬ ╨ ▓ ▒ ░ « » █ ▄ ▌▀▐│ ┤ ╡ ╢ return; } - if (Options.CurrentGameMode != CustomGameMode.Standard) return; + if (!CustomGameMode.Standard.IsActiveOrIntegrated()) return; StringBuilder sb = new(); if (SetEverythingUpPatch.LastWinsText != string.Empty) sb.Append($"{GetString("LastResult")} {SetEverythingUpPatch.LastWinsText}"); @@ -1565,7 +1567,7 @@ other: ∟ ⌠ ⌡ ╬ ╨ ▓ ▒ ░ « » █ ▄ ▌▀▐│ ┤ ╡ ╢ return; } - if (Options.CurrentGameMode != CustomGameMode.Standard) return; + if (!CustomGameMode.Standard.IsActiveOrIntegrated()) return; string result = Main.LastAddOns.Values.Join(delimiter: "\n"); SendMessage("\n", PlayerId, result); @@ -1717,7 +1719,7 @@ other: ∟ ⌠ ⌡ ╬ ╨ ▓ ▒ ░ « » █ ▄ ▌▀▐│ ┤ ╡ ╢ { try { - if (Options.CurrentGameMode != CustomGameMode.Standard || deadPlayer == null || deadPlayer.Object.Is(CustomRoles.Refugee) || Main.HasJustStarted || !GameStates.InGame || !Options.SpawnAdditionalRefugeeOnImpsDead.GetBool() || Main.AllAlivePlayerControls.Length < Options.SpawnAdditionalRefugeeMinAlivePlayers.GetInt() || CustomRoles.Refugee.RoleExist(true) || Main.AllAlivePlayerControls == null || Main.AllAlivePlayerControls.Length == 0 || Main.AllAlivePlayerControls.Any(x => x.PlayerId != deadPlayer.PlayerId && (x.Is(CustomRoleTypes.Impostor) || (x.IsNeutralKiller() && !Options.SpawnAdditionalRefugeeWhenNKAlive.GetBool())))) return; + if (!CustomGameMode.Standard.IsActiveOrIntegrated() || deadPlayer == null || deadPlayer.Object.Is(CustomRoles.Refugee) || Main.HasJustStarted || !GameStates.InGame || !Options.SpawnAdditionalRefugeeOnImpsDead.GetBool() || Main.AllAlivePlayerControls.Length < Options.SpawnAdditionalRefugeeMinAlivePlayers.GetInt() || CustomRoles.Refugee.RoleExist(true) || Main.AllAlivePlayerControls == null || Main.AllAlivePlayerControls.Length == 0 || Main.AllAlivePlayerControls.Any(x => x.PlayerId != deadPlayer.PlayerId && (x.Is(CustomRoleTypes.Impostor) || (x.IsNeutralKiller() && !Options.SpawnAdditionalRefugeeWhenNKAlive.GetBool())))) return; PlayerControl[] ListToChooseFrom = Main.AllAlivePlayerControls.Where(x => x.PlayerId != deadPlayer.PlayerId && x.Is(CustomRoleTypes.Crewmate) && !x.Is(CustomRoles.Loyal)).ToArray(); @@ -1854,6 +1856,7 @@ other: ∟ ⌠ ⌡ ╬ ╨ ▓ ▒ ░ « » █ ▄ ▌▀▐│ ┤ ╡ ╢ CustomGameMode.CaptureTheFlag => $"{modeText}\r\n{name}", CustomGameMode.NaturalDisasters => $"{modeText}\r\n{name}", CustomGameMode.RoomRush => $"{modeText}\r\n{name}", + CustomGameMode.AllInOne => $"{modeText}\r\n{name}", CustomGameMode.Speedrun => ColorString(GetRoleColor(CustomRoles.Speedrunner), $"{modeText}\r\n") + name, _ => name }; @@ -2016,7 +2019,7 @@ other: ∟ ⌠ ⌡ ╬ ╨ ▓ ▒ ░ « » █ ▄ ▌▀▐│ ┤ ╡ ╢ public static void NotifyRoles(bool isForMeeting = false, PlayerControl SpecifySeer = null, PlayerControl SpecifyTarget = null, bool NoCache = false, bool ForceLoop = false, bool CamouflageIsForMeeting = false, bool GuesserIsForMeeting = false, bool MushroomMixup = false) { - if (!SetUpRoleTextPatch.IsInIntro && ((SpecifySeer != null && SpecifySeer.IsModClient() && (Options.CurrentGameMode == CustomGameMode.Standard || SpecifySeer.IsHost())) || !AmongUsClient.Instance.AmHost || Main.AllPlayerControls == null || (GameStates.IsMeeting && !isForMeeting))) return; + if (!SetUpRoleTextPatch.IsInIntro && ((SpecifySeer != null && SpecifySeer.IsModClient() && (CustomGameMode.Standard.IsActiveOrIntegrated() || SpecifySeer.IsHost())) || !AmongUsClient.Instance.AmHost || Main.AllPlayerControls == null || (GameStates.IsMeeting && !isForMeeting))) return; DoNotifyRoles(isForMeeting, SpecifySeer, SpecifyTarget, NoCache, ForceLoop, CamouflageIsForMeeting, GuesserIsForMeeting, MushroomMixup); } @@ -2036,14 +2039,14 @@ other: ∟ ⌠ ⌡ ╬ ╨ ▓ ▒ ░ « » █ ▄ ▌▀▐│ ┤ ╡ ╢ { try { - if (seer == null || seer.Data.Disconnected || (seer.IsModClient() && (seer.IsHost() || Options.CurrentGameMode == CustomGameMode.Standard))) continue; + if (seer == null || seer.Data.Disconnected || (seer.IsModClient() && (seer.IsHost() || CustomGameMode.Standard.IsActiveOrIntegrated()))) continue; // During intro scene, set team name for non-modded clients and skip the rest. string SelfName; Team seerTeam = seer.GetTeam(); CustomRoles seerRole = seer.GetCustomRole(); - if (SetUpRoleTextPatch.IsInIntro && (seerRole.IsDesyncRole() || seer.Is(CustomRoles.Bloodlust)) && Options.CurrentGameMode == CustomGameMode.Standard) + if (SetUpRoleTextPatch.IsInIntro && (seerRole.IsDesyncRole() || seer.Is(CustomRoles.Bloodlust)) && CustomGameMode.Standard.IsActiveOrIntegrated()) { const string iconTextLeft = "\u21e8"; const string iconTextRight = "\u21e6"; @@ -2082,7 +2085,7 @@ other: ∟ ⌠ ⌡ ╬ ╨ ▓ ▒ ░ « » █ ▄ ▌▀▐│ ┤ ╡ ╢ { if (AntiBlackout.SkipTasks) SelfSuffix.AppendLine(GetString("AntiBlackoutSkipTasks")); - if (Options.CurrentGameMode != CustomGameMode.Standard) goto GameMode0; + if (!CustomGameMode.Standard.IsActiveOrIntegrated()) goto GameMode0; SelfMark.Append(Snitch.GetWarningArrow(seer)); if (Main.LoversPlayers.Exists(x => x.PlayerId == seer.PlayerId)) SelfMark.Append(ColorString(GetRoleColor(CustomRoles.Lovers), " ♥")); @@ -2160,7 +2163,7 @@ other: ∟ ⌠ ⌡ ╬ ╨ ▓ ▒ ░ « » █ ▄ ▌▀▐│ ┤ ╡ ╢ case CustomGameMode.MoveAndStop: SelfSuffix.Append(MoveAndStop.GetSuffixText(seer)); break; - case CustomGameMode.HotPotato when seer.IsAlive(): + case CustomGameMode.HotPotato: SelfSuffix.Append(HotPotatoManager.GetSuffixText(seer.PlayerId)); break; case CustomGameMode.Speedrun: @@ -2178,6 +2181,15 @@ other: ∟ ⌠ ⌡ ╬ ╨ ▓ ▒ ░ « » █ ▄ ▌▀▐│ ┤ ╡ ╢ case CustomGameMode.RoomRush: SelfSuffix.Append(RoomRush.GetSuffix(seer)); break; + case CustomGameMode.AllInOne: + SelfSuffix.Append(SoloKombatManager.GetDisplayHealth(seer) + "\n"); + SelfSuffix.Append(MoveAndStop.GetSuffixText(seer) + "\n"); + SelfSuffix.Append(HotPotatoManager.GetSuffixText(seer.PlayerId) + "\n"); + SelfSuffix.Append(string.Format(GetString("DamoclesTimeLeft"), SpeedrunManager.Timers[seer.PlayerId]) + "\n"); + SelfSuffix.Append(NaturalDisasters.SuffixText() + "\n"); + const StringSplitOptions splitFlags = StringSplitOptions.RemoveEmptyEntries | StringSplitOptions.TrimEntries; + SelfSuffix.Append(RoomRush.GetSuffix(seer).Split('\n', splitFlags).Join(delimiter: " - ")); + break; } } @@ -2185,10 +2197,10 @@ other: ∟ ⌠ ⌡ ╬ ╨ ▓ ▒ ░ « » █ ▄ ▌▀▐│ ┤ ╡ ╢ if (!GameStates.IsLobby) { - if ((Options.CurrentGameMode == CustomGameMode.FFA && FFAManager.FFATeamMode.GetBool()) || Options.CurrentGameMode == CustomGameMode.HotPotato) + if ((CustomGameMode.FFA.IsActiveOrIntegrated() && FFAManager.FFATeamMode.GetBool()) || CustomGameMode.HotPotato.IsActiveOrIntegrated()) SeerRealName = SeerRealName.ApplyNameColorData(seer, seer, isForMeeting); - if (!isForMeeting && MeetingStates.FirstMeeting && Options.ChangeNameToRoleInfo.GetBool() && Options.CurrentGameMode is not CustomGameMode.FFA and not CustomGameMode.MoveAndStop and not CustomGameMode.HotPotato and not CustomGameMode.Speedrun and not CustomGameMode.CaptureTheFlag and not CustomGameMode.NaturalDisasters and not CustomGameMode.RoomRush) + if (!isForMeeting && MeetingStates.FirstMeeting && Options.ChangeNameToRoleInfo.GetBool() && Options.CurrentGameMode is not CustomGameMode.FFA and not CustomGameMode.MoveAndStop and not CustomGameMode.HotPotato and not CustomGameMode.Speedrun and not CustomGameMode.CaptureTheFlag and not CustomGameMode.NaturalDisasters and not CustomGameMode.RoomRush and not CustomGameMode.AllInOne) { CustomTeamManager.CustomTeam team = CustomTeamManager.GetCustomTeam(seer.PlayerId); @@ -2207,14 +2219,14 @@ other: ∟ ⌠ ⌡ ╬ ╨ ▓ ▒ ░ « » █ ▄ ▌▀▐│ ┤ ╡ ╢ ? string.Empty : team.RoleRevealScreenSubtitle)); } - else if (Options.CurrentGameMode == CustomGameMode.HideAndSeek) + else if (CustomGameMode.HideAndSeek.IsActiveOrIntegrated()) { if (GameStartTimeStamp + 40 > now) SeerRealName = HnSManager.GetRoleInfoText(seer); } else if (Options.ChangeNameToRoleInfo.GetBool() && !seer.IsModClient()) { bool showLongInfo = LongRoleDescriptions.TryGetValue(seer.PlayerId, out (string Text, int Duration, bool Long) description) && GameStartTimeStamp + description.Duration > now; - string mHelp = (!showLongInfo || description.Long) && Options.CurrentGameMode == CustomGameMode.Standard ? "\n" + GetString("MyRoleCommandHelp") : string.Empty; + string mHelp = (!showLongInfo || description.Long) && CustomGameMode.Standard.IsActiveOrIntegrated() ? "\n" + GetString("MyRoleCommandHelp") : string.Empty; SeerRealName = seerTeam switch { @@ -2233,7 +2245,7 @@ other: ∟ ⌠ ⌡ ╬ ╨ ▓ ▒ ░ « » █ ▄ ▌▀▐│ ┤ ╡ ╢ string SelfDeathReason = seer.KnowDeathReason(seer) && !GameStates.IsLobby ? $"\n『{ColorString(GetRoleColor(CustomRoles.Doctor), GetVitalText(seer.PlayerId))}』" : string.Empty; SelfName = $"{ColorString(GameStates.IsLobby ? Color.white : seer.GetRoleColor(), SeerRealName)}{SelfDeathReason}{SelfMark}"; - if (Options.CurrentGameMode != CustomGameMode.Standard || GameStates.IsLobby) goto GameMode2; + if (!CustomGameMode.Standard.IsActiveOrIntegrated() || GameStates.IsLobby) goto GameMode2; SelfName = seerRole switch { @@ -2299,7 +2311,7 @@ other: ∟ ⌠ ⌡ ╬ ╨ ▓ ▒ ░ « » █ ▄ ▌▀▐│ ┤ ╡ ╢ { TargetMark.Clear(); - if (Options.CurrentGameMode != CustomGameMode.Standard || GameStates.IsLobby) goto BeforeEnd2; + if (!CustomGameMode.Standard.IsActiveOrIntegrated() || GameStates.IsLobby) goto BeforeEnd2; TargetMark.Append(Witch.GetSpelledMark(target.PlayerId, isForMeeting)); if (isForMeeting) TargetMark.Append(Wasp.GetStungMark(target.PlayerId)); @@ -2381,7 +2393,7 @@ other: ∟ ⌠ ⌡ ╬ ╨ ▓ ▒ ░ « » █ ▄ ▌▀▐│ ┤ ╡ ╢ Main.PlayerStates.Values.Any(x => x.Role.KnowRole(seer, target)) || Markseeker.PlayerIdList.Any(x => Main.PlayerStates[x].Role is Markseeker { IsEnable: true, TargetRevealed: true } ms && ms.MarkedId == target.PlayerId) || Options.CurrentGameMode is CustomGameMode.FFA or CustomGameMode.MoveAndStop or CustomGameMode.HotPotato or CustomGameMode.Speedrun || - (Options.CurrentGameMode == CustomGameMode.HideAndSeek && HnSManager.IsRoleTextEnabled(seer, target)) || + (CustomGameMode.HideAndSeek.IsActiveOrIntegrated() && HnSManager.IsRoleTextEnabled(seer, target)) || (seer.IsRevealedPlayer(target) && !target.Is(CustomRoles.Trickster)) || (seer.Is(CustomRoles.God) && God.KnowInfo.GetValue() == 2) || target.Is(CustomRoles.GM) @@ -2400,7 +2412,7 @@ other: ∟ ⌠ ⌡ ╬ ╨ ▓ ▒ ░ « » █ ▄ ▌▀▐│ ┤ ╡ ╢ TargetRoleText += Farseer.GetTaskState(); } - if (Options.CurrentGameMode == CustomGameMode.SoloKombat) TargetRoleText = $"{GetProgressText(target)}\r\n"; + if (CustomGameMode.SoloKombat.IsActiveOrIntegrated()) TargetRoleText = $"{GetProgressText(target)}\r\n"; } else TargetRoleText = string.Empty; @@ -2409,7 +2421,7 @@ other: ∟ ⌠ ⌡ ╬ ╨ ▓ ▒ ░ « » █ ▄ ▌▀▐│ ┤ ╡ ╢ if (GameStates.IsLobby) goto End; - if (Options.CurrentGameMode != CustomGameMode.Standard) goto BeforeEnd; + if (!CustomGameMode.Standard.IsActiveOrIntegrated()) goto BeforeEnd; if (GuesserIsForMeeting || isForMeeting || (seerRole == CustomRoles.Mafia && !seer.IsAlive() && Options.MafiaCanKillNum.GetInt() >= 1)) TargetPlayerName = $"{ColorString(GetRoleColor(seerRole), target.PlayerId.ToString())} {TargetPlayerName}"; @@ -2429,8 +2441,6 @@ other: ∟ ⌠ ⌡ ╬ ╨ ▓ ▒ ░ « » █ ▄ ▌▀▐│ ┤ ╡ ╢ TargetPlayerName = ColorString(GetRoleColor(CustomRoles.Impostor), TargetPlayerName); break; case CustomRoles.HeadHunter when (Main.PlayerStates[seer.PlayerId].Role as HeadHunter).Targets.Contains(target.PlayerId) && seer.IsAlive(): - TargetPlayerName = $"{TargetPlayerName}"; - break; case CustomRoles.BountyHunter when (Main.PlayerStates[seer.PlayerId].Role as BountyHunter).GetTarget(seer) == target.PlayerId && seer.IsAlive(): TargetPlayerName = $"{TargetPlayerName}"; break; @@ -2443,7 +2453,7 @@ other: ∟ ⌠ ⌡ ╬ ╨ ▓ ▒ ░ « » █ ▄ ▌▀▐│ ┤ ╡ ╢ TargetPlayerName = TargetPlayerName.ApplyNameColorData(seer, target, isForMeeting); - if (Options.CurrentGameMode != CustomGameMode.Standard) goto End; + if (!CustomGameMode.Standard.IsActiveOrIntegrated()) goto End; if (seer.Is(CustomRoleTypes.Impostor) && target.Is(CustomRoles.Snitch) && target.Is(CustomRoles.Madmate) && target.GetTaskState().IsTaskFinished) TargetMark.Append(ColorString(GetRoleColor(CustomRoles.Impostor), "★")); @@ -2517,7 +2527,7 @@ other: ∟ ⌠ ⌡ ╬ ╨ ▓ ▒ ░ « » █ ▄ ▌▀▐│ ┤ ╡ ╢ } } - if (Options.CurrentGameMode != CustomGameMode.Standard) return; + if (!CustomGameMode.Standard.IsActiveOrIntegrated()) return; string seers = seerList.Length == apc.Length ? "Everyone" : string.Join(", ", seerList.Select(x => x.GetRealName())); string targets = targetList.Length == apc.Length ? "Everyone" : string.Join(", ", targetList.Select(x => x.GetRealName())); @@ -2749,7 +2759,7 @@ other: ∟ ⌠ ⌡ ╬ ╨ ▓ ▒ ░ « » █ ▄ ▌▀▐│ ┤ ╡ ╢ if (loversChat && Lovers.PrivateChatForLoversOnly.GetBool()) Main.LoversPlayers.ForEach(x => x.SetChatVisible()); - else if (!Lovers.IsChatActivated && loversChat && !GameStates.IsEnded && Options.CurrentGameMode == CustomGameMode.Standard) + else if (!Lovers.IsChatActivated && loversChat && !GameStates.IsEnded && CustomGameMode.Standard.IsActiveOrIntegrated()) { LateTask.New(SetChatVisibleForAll, 0.5f, log: false); Lovers.IsChatActivated = true; @@ -2975,7 +2985,7 @@ other: ∟ ⌠ ⌡ ╬ ╨ ▓ ▒ ░ « » █ ▄ ▌▀▐│ ┤ ╡ ╢ { StringBuilder sb = new(100); - if (Options.CurrentGameMode == CustomGameMode.Standard) + if (CustomGameMode.Standard.IsActiveOrIntegrated()) { foreach (CountTypes countTypes in Enum.GetValues()) { @@ -3145,7 +3155,10 @@ other: ∟ ⌠ ⌡ ╬ ╨ ▓ ▒ ░ « » █ ▄ ▌▀▐│ ┤ ╡ ╢ case CustomGameMode.CaptureTheFlag: summary = $"{ColorString(Main.PlayerColors[id], name)}: {CTFManager.GetStatistics(id)}"; if (CTFManager.IsDeathPossible) summary += $" ({GetVitalText(id, true)})"; - + break; + case CustomGameMode.AllInOne: + string survivalTimeText = !Main.PlayerStates[id].IsDead ? string.Empty : $" ({GetString("SurvivedTimePrefix")}: <#f542ad>{RoomRush.GetSurvivalTime(id)}s)"; + summary = $"{ColorString(Main.PlayerColors[id], name)} -{TaskCount}{GetKillCountText(id, true)} ({GetVitalText(id, true)}){survivalTimeText}"; break; } @@ -3373,7 +3386,7 @@ other: ∟ ⌠ ⌡ ╬ ╨ ▓ ▒ ░ « » █ ▄ ▌▀▐│ ┤ ╡ ╢ public static float CalculatePingDelay() { // The value of AmongUsClient.Instance.Ping is in milliseconds (ms), so ÷1000 to convert to seconds - float divice = Options.CurrentGameMode != CustomGameMode.Standard ? 3000f : 2000f; + float divice = !CustomGameMode.Standard.IsActiveOrIntegrated() ? 3000f : 2000f; float minTime = Mathf.Max(0.02f, AmongUsClient.Instance.Ping / divice * 6f); return minTime; } diff --git a/Patches/ChatCommandPatch.cs b/Patches/ChatCommandPatch.cs index 04ac245a9..5daed433f 100644 --- a/Patches/ChatCommandPatch.cs +++ b/Patches/ChatCommandPatch.cs @@ -347,12 +347,12 @@ namespace EHR RequestCommandProcessingFromHost(nameof(WhisperCommand), text); return; } - + if (args.Length < 3 || !byte.TryParse(args[1], out byte targetId)) return; if (!player.IsLocalPlayer()) ChatManager.SendPreviousMessagesToAll(); Utils.SendMessage(args[2..].Join(delimiter: " "), targetId, string.Format(GetString("WhisperTitle"), player.PlayerId.ColoredPlayerName())); } - + private static void DeathNoteCommand(ChatController __instance, PlayerControl player, string text, string[] args) { if (!AmongUsClient.Instance.AmHost) @@ -2241,19 +2241,18 @@ namespace EHR private static void SendRolesInfo(string role, byte playerId, bool isDev = false, bool isUp = false) { - if (Options.CurrentGameMode != CustomGameMode.Standard) + if (!CustomGameMode.Standard.IsActiveOrIntegrated()) { - Utils.SendMessage(GetString($"ModeDescribe.{Options.CurrentGameMode}"), playerId); - if (Options.CurrentGameMode != CustomGameMode.HideAndSeek) return; + string text = GetString($"ModeDescribe.{Options.CurrentGameMode}"); + bool allInOne = Options.CurrentGameMode == CustomGameMode.AllInOne; + Utils.SendMessage(allInOne ? "\n" : text, playerId, allInOne ? text : ""); + if (!CustomGameMode.HideAndSeek.IsActiveOrIntegrated()) return; } role = role.Trim().ToLower(); if (role.StartsWith("/r")) _ = role.Replace("/r", string.Empty); - if (role.StartsWith("/up")) _ = role.Replace("/up", string.Empty); - if (role.EndsWith("\r\n")) _ = role.Replace("\r\n", string.Empty); - if (role.EndsWith("\n")) _ = role.Replace("\n", string.Empty); if (role == "") @@ -2325,7 +2324,9 @@ namespace EHR if (role.Equals(match, StringComparison.OrdinalIgnoreCase)) { - Utils.SendMessage(GetString($"ModeDescribe.{gameMode}"), playerId, gmString); + string text = GetString($"ModeDescribe.{gameMode}"); + bool allInOne = gameMode == CustomGameMode.AllInOne; + Utils.SendMessage(allInOne ? "\n" : text, playerId, allInOne ? text : gmString); return; } } @@ -2433,7 +2434,7 @@ namespace EHR else LateTask.New(() => Utils.SendMessage(GetString("LoversChatCannotTalkMsg"), player.PlayerId, GetString("LoversChatCannotTalkTitle")), 0.5f, log: false); } - + if (!canceled) ChatManager.SendMessage(player, text); if (isCommand) LastSentCommand[player.PlayerId] = now; diff --git a/Patches/ChatControlPatch.cs b/Patches/ChatControlPatch.cs index 8a3af2e7b..af30426b7 100644 --- a/Patches/ChatControlPatch.cs +++ b/Patches/ChatControlPatch.cs @@ -202,7 +202,7 @@ namespace EHR break; } - if (Options.CurrentGameMode == CustomGameMode.FFA && GameStates.InGame && !message.StartsWith('/')) + if (CustomGameMode.FFA.IsActiveOrIntegrated() && GameStates.InGame && !message.StartsWith('/')) FFAManager.UpdateLastChatMessage(player.GetRealName(), message); } diff --git a/Patches/CheckGameEndPatch.cs b/Patches/CheckGameEndPatch.cs index 2fab8602e..082ab2dd7 100644 --- a/Patches/CheckGameEndPatch.cs +++ b/Patches/CheckGameEndPatch.cs @@ -40,7 +40,7 @@ namespace EHR Predicate.CheckForGameEnd(out GameOverReason reason); - if (Options.CurrentGameMode != CustomGameMode.Standard) + if (!CustomGameMode.Standard.IsActiveOrIntegrated()) { if (WinnerIds.Count > 0 || WinnerTeam != CustomWinner.Default) { @@ -467,6 +467,11 @@ namespace EHR Predicate = new RoomRushGameEndPredicate(); } + public static void SetPredicateToAllInOne() + { + Predicate = new AllInOneGameEndPredicate(); + } + private class NormalGameEndPredicate : GameEndPredicate { public override bool CheckForGameEnd(out GameOverReason reason) @@ -898,6 +903,38 @@ namespace EHR } } + private class AllInOneGameEndPredicate : GameEndPredicate + { + public override bool CheckForGameEnd(out GameOverReason reason) + { + reason = GameOverReason.ImpostorByKill; + return WinnerIds.Count <= 0 && CheckGameEndByLivingPlayers(out reason); + } + + private static bool CheckGameEndByLivingPlayers(out GameOverReason reason) + { + reason = GameOverReason.ImpostorByKill; + + PlayerControl[] appc = Main.AllAlivePlayerControls; + + switch (appc.Length) + { + case 1: + PlayerControl winner = appc[0]; + Logger.Info($"Winner: {winner.GetRealName().RemoveHtmlTags()}", "AllInOne"); + WinnerIds = [winner.PlayerId]; + Main.DoBlockNameChange = true; + return true; + case 0: + ResetAndSetWinner(CustomWinner.None); + Logger.Warn("No players alive. Force ending the game", "AllInOne"); + return true; + default: + return false; + } + } + } + public abstract class GameEndPredicate { /// Checks the game ending condition and stores the value in CustomWinnerHolder. diff --git a/Patches/ControlPatch.cs b/Patches/ControlPatch.cs index 31f8de6e5..7508bd731 100644 --- a/Patches/ControlPatch.cs +++ b/Patches/ControlPatch.cs @@ -35,7 +35,7 @@ namespace EHR if (KeysDown(KeyCode.LeftAlt, KeyCode.Return)) LateTask.New(SetResolutionManager.Postfix, 0.01f, "Fix Button Position"); - if (GameStates.IsInGame && (GameStates.IsCanMove || GameStates.IsMeeting) && Options.CurrentGameMode == CustomGameMode.Standard) + if (GameStates.IsInGame && (GameStates.IsCanMove || GameStates.IsMeeting) && CustomGameMode.Standard.IsActiveOrIntegrated()) { if (Input.GetKey(KeyCode.F1)) { diff --git a/Patches/ExilePatch.cs b/Patches/ExilePatch.cs index 0ac65dcb3..0ba9be037 100644 --- a/Patches/ExilePatch.cs +++ b/Patches/ExilePatch.cs @@ -130,7 +130,7 @@ namespace EHR.Patches if (AmongUsClient.Instance.AmHost) { Utils.NotifyRoles(); - + LateTask.New(() => { AntiBlackout.SendGameData(); @@ -142,7 +142,7 @@ namespace EHR.Patches if (!GameStates.IsEnded) { AntiBlackout.ResetAfterMeeting(); - + Main.AfterMeetingDeathPlayers.Do(x => { PlayerControl player = Utils.GetPlayerById(x.Key); @@ -175,7 +175,7 @@ namespace EHR.Patches bool appendEjectionNotify = CheckForEndVotingPatch.EjectionText != string.Empty; Logger.Msg($"Ejection Text: {CheckForEndVotingPatch.EjectionText}", "ExilePatch"); - if ((showRemainingKillers || appendEjectionNotify) && Options.CurrentGameMode == CustomGameMode.Standard) + if ((showRemainingKillers || appendEjectionNotify) && CustomGameMode.Standard.IsActiveOrIntegrated()) { string text = showRemainingKillers ? Utils.GetRemainingKillers(true) : string.Empty; text = $"<#ffffff>{text}"; diff --git a/Patches/GameOptionsMenuPatch.cs b/Patches/GameOptionsMenuPatch.cs index 5f3fbe51c..0e407ab39 100644 --- a/Patches/GameOptionsMenuPatch.cs +++ b/Patches/GameOptionsMenuPatch.cs @@ -110,7 +110,7 @@ namespace EHR OptionItem option = OptionItem.AllOptions[index]; if (option.Tab != modTab) continue; - bool enabled = !option.IsHiddenOn(Options.CurrentGameMode) && (option.Parent == null || (!option.Parent.IsHiddenOn(Options.CurrentGameMode) && option.Parent.GetBool())) && (option.Parent?.Parent == null || (!option.Parent.Parent.IsHiddenOn(Options.CurrentGameMode) && option.Parent.Parent.GetBool())) && (option.Parent?.Parent?.Parent == null || (!option.Parent.Parent.Parent.IsHiddenOn(Options.CurrentGameMode) && option.Parent.Parent.Parent.GetBool())); + bool enabled = !option.IsCurrentlyHidden() && (option.Parent == null || (!option.Parent.IsCurrentlyHidden() && option.Parent.GetBool())) && (option.Parent?.Parent == null || (!option.Parent.Parent.IsCurrentlyHidden() && option.Parent.Parent.GetBool())) && (option.Parent?.Parent?.Parent == null || (!option.Parent.Parent.Parent.IsCurrentlyHidden() && option.Parent.Parent.Parent.GetBool())); if (option is TextOptionItem) { @@ -214,7 +214,7 @@ namespace EHR { if (option.Tab != (TabGroup)(ModGameOptionsMenu.TabIndex - 3)) continue; - bool enabled = !option.IsHiddenOn(Options.CurrentGameMode) && (option.Parent == null || (!option.Parent.IsHiddenOn(Options.CurrentGameMode) && option.Parent.GetBool())); + bool enabled = !option.IsCurrentlyHidden() && (option.Parent == null || (!option.Parent.IsCurrentlyHidden() && option.Parent.GetBool())); if (option is TextOptionItem) num -= 0.63f; @@ -331,7 +331,7 @@ namespace EHR OptionItem option = OptionItem.AllOptions[index]; if (option.Tab != modTab) continue; - bool enabled = !option.IsHiddenOn(Options.CurrentGameMode) && (option.Parent == null || (!option.Parent.IsHiddenOn(Options.CurrentGameMode) && option.Parent.GetBool())); + bool enabled = !option.IsCurrentlyHidden() && (option.Parent == null || (!option.Parent.IsCurrentlyHidden() && option.Parent.GetBool())); if (ModGameOptionsMenu.CategoryHeaderList.TryGetValue(index, out CategoryHeaderMasked categoryHeaderMasked)) { @@ -1117,9 +1117,9 @@ namespace EHR HiddenBySearch.Do(x => x.SetHidden(false)); string text = textField.textArea.text.Trim().ToLower(); - System.Collections.Generic.List Result = OptionItem.AllOptions.Where(x => x.Parent == null && !x.IsHiddenOn(Options.CurrentGameMode) && !Translator.GetString($"{x.Name}").Contains(text, StringComparison.OrdinalIgnoreCase) && x.Tab == (TabGroup)(ModGameOptionsMenu.TabIndex - 3)).ToList(); + System.Collections.Generic.List Result = OptionItem.AllOptions.Where(x => x.Parent == null && !x.IsCurrentlyHidden() && !Translator.GetString($"{x.Name}").Contains(text, StringComparison.OrdinalIgnoreCase) && x.Tab == (TabGroup)(ModGameOptionsMenu.TabIndex - 3)).ToList(); HiddenBySearch = Result; - System.Collections.Generic.List SearchWinners = OptionItem.AllOptions.Where(x => x.Parent == null && !x.IsHiddenOn(Options.CurrentGameMode) && x.Tab == (TabGroup)(ModGameOptionsMenu.TabIndex - 3) && !Result.Contains(x)).ToList(); + System.Collections.Generic.List SearchWinners = OptionItem.AllOptions.Where(x => x.Parent == null && !x.IsCurrentlyHidden() && x.Tab == (TabGroup)(ModGameOptionsMenu.TabIndex - 3) && !Result.Contains(x)).ToList(); if (SearchWinners.Count == 0 || !ModSettingsTabs.TryGetValue((TabGroup)(ModGameOptionsMenu.TabIndex - 3), out GameOptionsMenu GameSettings) || GameSettings == null) { diff --git a/Patches/GameOptionsPatch.cs b/Patches/GameOptionsPatch.cs index 6e2135717..356209160 100644 --- a/Patches/GameOptionsPatch.cs +++ b/Patches/GameOptionsPatch.cs @@ -71,6 +71,7 @@ namespace EHR.Patches switch (Options.CurrentGameMode) { + case CustomGameMode.AllInOne: case CustomGameMode.SoloKombat: case CustomGameMode.FFA: case CustomGameMode.RoomRush: diff --git a/Patches/HudPatch.cs b/Patches/HudPatch.cs index 019c9877c..9a6b550cf 100644 --- a/Patches/HudPatch.cs +++ b/Patches/HudPatch.cs @@ -149,7 +149,7 @@ namespace EHR.Patches __instance.SabotageButton }.Do(x => x?.Hide()); } - else if (Options.CurrentGameMode != CustomGameMode.Standard) __instance.ReportButton?.Hide(); + else if (!CustomGameMode.Standard.IsActiveOrIntegrated()) __instance.ReportButton?.Hide(); // The following will not be executed unless the game is in progress if (!AmongUsClient.Instance.IsGameStarted) return; @@ -160,7 +160,7 @@ namespace EHR.Patches if (SetHudActivePatch.IsActive) { - if (player.IsAlive() || Options.CurrentGameMode != CustomGameMode.Standard) + if (player.IsAlive() || !CustomGameMode.Standard.IsActiveOrIntegrated()) { if (player.Data.Role is ShapeshifterRole ssrole) { @@ -228,7 +228,7 @@ namespace EHR.Patches break; } - if (role.PetActivatedAbility() && Options.CurrentGameMode == CustomGameMode.Standard && !role.OnlySpawnsWithPets() && !role.AlwaysUsesUnshift() && !player.GetCustomSubRoles().Any(StartGameHostPatch.BasisChangingAddons.ContainsKey) && role != CustomRoles.Changeling && !Options.UseUnshiftTrigger.GetBool() && !(player.IsNeutralKiller() && Options.UseUnshiftTriggerForNKs.GetBool())) + if (role.PetActivatedAbility() && CustomGameMode.Standard.IsActiveOrIntegrated() && !role.OnlySpawnsWithPets() && !role.AlwaysUsesUnshift() && !player.GetCustomSubRoles().Any(StartGameHostPatch.BasisChangingAddons.ContainsKey) && role != CustomRoles.Changeling && !Options.UseUnshiftTrigger.GetBool() && !(player.IsNeutralKiller() && Options.UseUnshiftTriggerForNKs.GetBool())) __instance.AbilityButton?.Hide(); if (LowerInfoText == null) @@ -626,7 +626,7 @@ namespace EHR.Patches string roleInfo = player.GetRoleInfo(); var RoleWithInfo = $"{role.ToColoredString()}:\r\n{roleInfo}"; - if (Options.CurrentGameMode != CustomGameMode.Standard) + if (!CustomGameMode.Standard.IsActiveOrIntegrated()) { string[] splitted = roleInfo.Split(' '); diff --git a/Patches/HudSpritePatch.cs b/Patches/HudSpritePatch.cs index e6d33d411..62c75ab89 100644 --- a/Patches/HudSpritePatch.cs +++ b/Patches/HudSpritePatch.cs @@ -37,7 +37,7 @@ namespace EHR if (player == null) return; if (!Main.EnableCustomButton.Value || !Main.ProcessShapeshifts || Mastermind.ManipulatedPlayers.ContainsKey(player.PlayerId)) return; - if (!SetHudActivePatch.IsActive || !player.IsAlive() || Options.CurrentGameMode != CustomGameMode.Standard) return; + if (!SetHudActivePatch.IsActive || !player.IsAlive() || !CustomGameMode.Standard.IsActiveOrIntegrated()) return; if (!AmongUsClient.Instance.IsGameStarted || !Main.IntroDestroyed) { diff --git a/Patches/IntroPatch.cs b/Patches/IntroPatch.cs index 101d8623e..25a934c8c 100644 --- a/Patches/IntroPatch.cs +++ b/Patches/IntroPatch.cs @@ -101,7 +101,6 @@ namespace EHR case CustomGameMode.RoomRush: { Color color = ColorUtility.TryParseHtmlString("#ffab1b", out Color c) ? c : new(255, 255, 255, 255); - CustomRoles role = lp.GetCustomRole(); __instance.YouAreText.color = color; __instance.RoleText.text = GetString("RRPlayer"); __instance.RoleText.color = color; @@ -109,6 +108,16 @@ namespace EHR __instance.RoleBlurbText.text = GetString("RRPlayerInfo"); break; } + case CustomGameMode.AllInOne: + { + Color color = ColorUtility.TryParseHtmlString("#f542ad", out Color c) ? c : new(255, 255, 255, 255); + __instance.YouAreText.color = color; + __instance.RoleText.text = GetString("AllInOne"); + __instance.RoleText.color = color; + __instance.RoleBlurbText.color = color; + __instance.RoleBlurbText.text = GetString("AllInOneInfo"); + break; + } default: { CustomRoles role = lp.GetCustomRole(); @@ -193,7 +202,7 @@ namespace EHR sb.Append("------------Modded Settings------------\n"); foreach (OptionItem o in OptionItem.AllOptions) - if (!o.IsHiddenOn(Options.CurrentGameMode) && (o.Parent?.GetBool() ?? !o.GetString().Equals("0%"))) + if (!o.IsCurrentlyHidden() && (o.Parent?.GetBool() ?? !o.GetString().Equals("0%"))) sb.Append($"{(o.Parent == null ? o.GetName(true, true).RemoveHtmlTags().PadRightV2(40) : $"┗ {o.GetName(true, true).RemoveHtmlTags()}".PadRightV2(41))}:{o.GetString().RemoveHtmlTags()}\n"); sb.Append("-------------Other Information-------------\n"); @@ -316,7 +325,7 @@ namespace EHR } } - if (Options.CurrentGameMode == CustomGameMode.FFA && FFAManager.FFATeamMode.GetBool() && FFAManager.PlayerTeams.TryGetValue(PlayerControl.LocalPlayer.PlayerId, out int ffaTeam)) + if (CustomGameMode.FFA.IsActiveOrIntegrated() && FFAManager.FFATeamMode.GetBool() && FFAManager.PlayerTeams.TryGetValue(PlayerControl.LocalPlayer.PlayerId, out int ffaTeam)) { teamToDisplay = new(); @@ -667,6 +676,15 @@ namespace EHR __instance.ImpostorText.text = GetString("RRPlayerInfo"); break; } + case CustomGameMode.AllInOne: + { + __instance.TeamTitle.text = GetString("AllInOne"); + __instance.TeamTitle.color = __instance.BackgroundBar.material.color = new Color32(245, 66, 173, byte.MaxValue); + PlayerControl.LocalPlayer.Data.Role.IntroSound = GetIntroSound(RoleTypes.Shapeshifter); + __instance.ImpostorText.gameObject.SetActive(true); + __instance.ImpostorText.text = GetString("AllInOneInfo"); + break; + } } // if (Input.GetKey(KeyCode.RightShift)) @@ -810,7 +828,7 @@ namespace EHR int kcd = Options.StartingKillCooldown.GetInt(); - if (kcd is not 10 and > 0 && Options.CurrentGameMode != CustomGameMode.FFA) + if (kcd is not 10 and > 0 && !CustomGameMode.FFA.IsActiveOrIntegrated()) { LateTask.New(() => { @@ -821,7 +839,7 @@ namespace EHR } }, 2f, "FixKillCooldownTask"); } - else if (Options.FixFirstKillCooldown.GetBool() && Options.CurrentGameMode == CustomGameMode.Standard) + else if (Options.FixFirstKillCooldown.GetBool() && CustomGameMode.Standard.IsActiveOrIntegrated()) { LateTask.New(() => { @@ -904,7 +922,7 @@ namespace EHR { lp.RpcExile(); Main.PlayerStates[lp.PlayerId].SetDead(); - }, Options.CurrentGameMode == CustomGameMode.FFA && FFAManager.FFAChatDuringGame.GetBool() ? 12.5f : 1f, "Set GM Dead"); + }, CustomGameMode.FFA.IsActiveOrIntegrated() && FFAManager.FFAChatDuringGame.GetBool() ? 12.5f : 1f, "Set GM Dead"); } if (Options.RandomSpawn.GetBool()) diff --git a/Patches/OnGameStartedPatch.cs b/Patches/OnGameStartedPatch.cs index 1fb8e76ce..7700f1c7c 100644 --- a/Patches/OnGameStartedPatch.cs +++ b/Patches/OnGameStartedPatch.cs @@ -352,6 +352,7 @@ namespace EHR HotPotatoManager.Init(); HnSManager.Init(); SpeedrunManager.Init(); + AllInOneGameMode.Init(); } catch (Exception e) { @@ -500,7 +501,7 @@ namespace EHR var random = IRandom.Instance; - if (Options.CurrentGameMode == CustomGameMode.Standard) + if (CustomGameMode.Standard.IsActiveOrIntegrated()) { bool bloodlustSpawn = random.Next(1, 100) <= (Options.CustomAdtRoleSpawnRate.TryGetValue(CustomRoles.Bloodlust, out IntegerOptionItem option0) ? option0.GetFloat() : 0) && CustomRoles.Bloodlust.IsEnable(); bool physicistSpawn = random.Next(100) < (Options.CustomAdtRoleSpawnRate.TryGetValue(CustomRoles.Physicist, out IntegerOptionItem option1) ? option1.GetFloat() : 0) && CustomRoles.Physicist.IsEnable(); @@ -636,7 +637,7 @@ namespace EHR Main.PlayerStates[kv.Key].SetMainRole(kv.Value); } - if (Options.CurrentGameMode != CustomGameMode.Standard) + if (!CustomGameMode.Standard.IsActiveOrIntegrated()) { foreach (KeyValuePair pair in Main.PlayerStates) ExtendedPlayerControl.RpcSetCustomRole(pair.Key, pair.Value.MainRole); @@ -775,8 +776,10 @@ namespace EHR switch (Options.CurrentGameMode) { + case CustomGameMode.AllInOne: case CustomGameMode.HotPotato: HotPotatoManager.OnGameStart(); + if (Options.CurrentGameMode == CustomGameMode.AllInOne) goto case CustomGameMode.NaturalDisasters; break; case CustomGameMode.HideAndSeek: HnSManager.StartSeekerBlindTime(); @@ -786,6 +789,7 @@ namespace EHR break; case CustomGameMode.NaturalDisasters: NaturalDisasters.OnGameStart(); + if (Options.CurrentGameMode == CustomGameMode.AllInOne) goto case CustomGameMode.RoomRush; break; case CustomGameMode.RoomRush: RoomRush.OnGameStart(); @@ -837,6 +841,9 @@ namespace EHR case CustomGameMode.RoomRush: GameEndChecker.SetPredicateToRoomRush(); break; + case CustomGameMode.AllInOne: + GameEndChecker.SetPredicateToAllInOne(); + break; } // Add players with unclassified roles to the list of players who require ResetCam. @@ -1088,7 +1095,7 @@ namespace EHR bool ForceImp(byte id) { - return IsBasisChangingPlayer(id, CustomRoles.Bloodlust) || (Options.CurrentGameMode == CustomGameMode.Speedrun && SpeedrunManager.CanKill.Contains(id)); + return IsBasisChangingPlayer(id, CustomRoles.Bloodlust) || (CustomGameMode.Speedrun.IsActiveOrIntegrated() && SpeedrunManager.CanKill.Contains(id)); } } @@ -1104,7 +1111,7 @@ namespace EHR PlayerControl player = Utils.GetPlayerById(playerId); if (player == null || role.IsDesyncRole()) continue; - if (Options.CurrentGameMode == CustomGameMode.Speedrun && SpeedrunManager.CanKill.Contains(playerId)) continue; + if (CustomGameMode.Speedrun.IsActiveOrIntegrated() && SpeedrunManager.CanKill.Contains(playerId)) continue; RoleTypes roleType = role.GetRoleTypes(); diff --git a/Patches/OutroPatch.cs b/Patches/OutroPatch.cs index 26d37114c..52fe68014 100644 --- a/Patches/OutroPatch.cs +++ b/Patches/OutroPatch.cs @@ -65,7 +65,7 @@ namespace EHR byte killerId = value.GetRealKiller(); bool gmIsFM = Options.CurrentGameMode is CustomGameMode.FFA or CustomGameMode.MoveAndStop; - bool gmIsFMHH = gmIsFM || Options.CurrentGameMode is CustomGameMode.HotPotato or CustomGameMode.HideAndSeek or CustomGameMode.Speedrun or CustomGameMode.CaptureTheFlag or CustomGameMode.NaturalDisasters or CustomGameMode.RoomRush; + bool gmIsFMHH = gmIsFM || Options.CurrentGameMode is CustomGameMode.HotPotato or CustomGameMode.HideAndSeek or CustomGameMode.Speedrun or CustomGameMode.CaptureTheFlag or CustomGameMode.NaturalDisasters or CustomGameMode.RoomRush or CustomGameMode.AllInOne; sb.Append($"\n{date:T} {Main.AllPlayerNames[key]} ({(gmIsFMHH ? string.Empty : Utils.GetDisplayRoleName(key, true))}{(gmIsFM ? string.Empty : Utils.GetSubRolesText(key, summary: true))}) [{Utils.GetVitalText(key)}]"); if (killerId != byte.MaxValue && killerId != key) sb.Append($"\n\t⇐ {Main.AllPlayerNames[killerId]} ({(gmIsFMHH ? string.Empty : Utils.GetDisplayRoleName(killerId, true))}{(gmIsFM ? string.Empty : Utils.GetSubRolesText(killerId, summary: true))})"); } @@ -288,6 +288,14 @@ namespace EHR WinnerText.color = Main.PlayerColors[winnerId]; goto EndOfText; } + case CustomGameMode.AllInOne: + { + byte winnerId = CustomWinnerHolder.WinnerIds.FirstOrDefault(); + __instance.BackgroundBar.material.color = new Color32(245, 66, 173, 255); + WinnerText.text = Main.AllPlayerNames[winnerId] + GetString("Win"); + WinnerText.color = Main.PlayerColors[winnerId]; + goto EndOfText; + } } if (CustomWinnerHolder.WinnerTeam == CustomWinner.CustomTeam) diff --git a/Patches/PetActionsPatch.cs b/Patches/PetActionsPatch.cs index 3804f0c3c..3b9fd4ff8 100644 --- a/Patches/PetActionsPatch.cs +++ b/Patches/PetActionsPatch.cs @@ -111,7 +111,7 @@ namespace EHR.Patches ) return; - if (Options.CurrentGameMode == CustomGameMode.CaptureTheFlag) + if (CustomGameMode.CaptureTheFlag.IsActiveOrIntegrated()) { CTFManager.TryPickUpFlag(pc); return; @@ -150,7 +150,7 @@ namespace EHR.Patches if (role.UsesPetInsteadOfKill() && hasKillTarget && (pc.Data.RoleType != RoleTypes.Impostor || alwaysPetRole)) { - if (Options.CurrentGameMode != CustomGameMode.Speedrun) + if (!CustomGameMode.Speedrun.IsActiveOrIntegrated()) pc.AddKCDAsAbilityCD(); if (Main.PlayerStates[pc.PlayerId].Role.OnCheckMurder(pc, target)) diff --git a/Patches/PlayerControlPatch.cs b/Patches/PlayerControlPatch.cs index 949edc03c..ea6d6c3b2 100644 --- a/Patches/PlayerControlPatch.cs +++ b/Patches/PlayerControlPatch.cs @@ -88,7 +88,7 @@ namespace EHR { if (AmongUsClient.Instance.AmHost) __instance.CheckMurder(target); - else if (Options.CurrentGameMode != CustomGameMode.FFA) + else if (!CustomGameMode.FFA.IsActiveOrIntegrated()) { MessageWriter messageWriter = AmongUsClient.Instance.StartRpcImmediately(__instance.NetId, (byte)RpcCalls.CheckMurder, SendOption.Reliable); messageWriter.WriteNetObject(target); @@ -221,9 +221,11 @@ namespace EHR case CustomGameMode.HotPotato: case CustomGameMode.RoomRush: case CustomGameMode.NaturalDisasters: - return false; case CustomGameMode.Speedrun when !SpeedrunManager.OnCheckMurder(killer, target): return false; + case CustomGameMode.AllInOne: + if (killer.Is(CustomRoles.Killer)) killer.Kill(target); + return false; case CustomGameMode.Speedrun: killer.Kill(target); return false; @@ -660,7 +662,7 @@ namespace EHR Chef.SpitOutFood(killer); - if (Options.CurrentGameMode == CustomGameMode.Speedrun) SpeedrunManager.ResetTimer(killer); + if (CustomGameMode.Speedrun.IsActiveOrIntegrated()) SpeedrunManager.ResetTimer(killer); if (killer.Is(CustomRoles.TicketsStealer) && killer.PlayerId != target.PlayerId) killer.Notify(string.Format(GetString("TicketsStealerGetTicket"), ((Main.AllPlayerControls.Count(x => x.GetRealKiller()?.PlayerId == killer.PlayerId) + 1) * Options.TicketsPerKill.GetFloat()).ToString("0.0#####"))); @@ -793,7 +795,7 @@ namespace EHR isSSneeded = false; } - bool ctf = Options.CurrentGameMode == CustomGameMode.CaptureTheFlag; + bool ctf = CustomGameMode.CaptureTheFlag.IsActiveOrIntegrated(); if (ctf) CTFManager.TryPickUpFlag(shapeshifter); CustomRoles role = shapeshifter.GetCustomRole(); @@ -900,7 +902,7 @@ namespace EHR if (Options.DisableMeeting.GetBool()) return false; - if (Options.CurrentGameMode != CustomGameMode.Standard) return false; + if (!CustomGameMode.Standard.IsActiveOrIntegrated()) return false; if (Options.DisableReportWhenCC.GetBool() && Camouflage.IsCamouflage) return false; @@ -1236,7 +1238,7 @@ namespace EHR else if (!Main.HasJustStarted && GameStates.IsInTask && !ExileController.Instance && GhostRolesManager.ShouldHaveGhostRole(__instance)) GhostRolesManager.AssignGhostRole(__instance); } - if (GameStates.InGame && Options.DontUpdateDeadPlayers.GetBool() && !__instance.IsAlive() && !__instance.GetCustomRole().NeedsUpdateAfterDeath() && Options.CurrentGameMode != CustomGameMode.RoomRush) + if (GameStates.InGame && Options.DontUpdateDeadPlayers.GetBool() && !__instance.IsAlive() && !__instance.GetCustomRole().NeedsUpdateAfterDeath() && !CustomGameMode.RoomRush.IsActiveOrIntegrated()) { int buffer = Options.DeepLowLoad.GetBool() ? 30 : 10; DeadBufferTime.TryAdd(id, buffer); @@ -1499,7 +1501,7 @@ namespace EHR if (GameStates.IsInGame) { - if (!AmongUsClient.Instance.AmHost && Options.CurrentGameMode != CustomGameMode.Standard) + if (!AmongUsClient.Instance.AmHost && !CustomGameMode.Standard.IsActiveOrIntegrated()) { RoleText.text = string.Empty; RoleText.enabled = false; @@ -1540,7 +1542,7 @@ namespace EHR if (Main.VisibleTasksCount) { - if (Options.CurrentGameMode == CustomGameMode.MoveAndStop) RoleText.text = RoleText.text.Insert(0, progressText); + if (CustomGameMode.MoveAndStop.IsActiveOrIntegrated()) RoleText.text = RoleText.text.Insert(0, progressText); else RoleText.text += progressText; } @@ -1713,16 +1715,16 @@ namespace EHR Suffix.Append(Bloodmoon.GetSuffix(seer)); Suffix.Append(Haunter.GetSuffix(seer)); if (seer.Is(CustomRoles.Asthmatic)) Suffix.Append(Asthmatic.GetSuffixText(seer.PlayerId)); - if (seer.Is(CustomRoles.Sonar)) Suffix.Append(Sonar.GetSuffix(seer, GameStates.IsMeeting)); - if (seer.Is(CustomRoles.Deadlined)) Suffix.Append(Deadlined.GetSuffix(seer)); - if (seer.Is(CustomRoles.Allergic)) Suffix.Append(Allergic.GetSelfSuffix(seer)); } switch (Options.CurrentGameMode) { + case CustomGameMode.SoloKombat: + Suffix.Append(SoloKombatManager.GetDisplayHealth(target)); + break; case CustomGameMode.FFA: Suffix.Append(FFAManager.GetPlayerArrow(seer, target)); break; @@ -1738,13 +1740,17 @@ namespace EHR case CustomGameMode.CaptureTheFlag: Suffix.Append(CTFManager.GetSuffixText(seer, target)); break; - case CustomGameMode.RoomRush when self: + case CustomGameMode.RoomRush: Suffix.Append(RoomRush.GetSuffix(seer)); break; + case CustomGameMode.AllInOne: + Suffix.Append(SoloKombatManager.GetDisplayHealth(target)); + if (self) Suffix.Append(MoveAndStop.GetSuffixText(seer) + "\n"); + if (self) Suffix.Append(string.Format(GetString("DamoclesTimeLeft"), SpeedrunManager.Timers[seer.PlayerId]) + "\n"); + if (self) Suffix.Append(RoomRush.GetSuffix(seer).Replace("\n", " - ")); + break; } - if (Options.CurrentGameMode == CustomGameMode.SoloKombat) Suffix.Append(SoloKombatManager.GetDisplayHealth(target)); - if (MeetingStates.FirstMeeting && Main.ShieldPlayer == target.FriendCode && !string.IsNullOrEmpty(target.FriendCode) && !self && Options.CurrentGameMode is CustomGameMode.Standard or CustomGameMode.SoloKombat or CustomGameMode.FFA) Suffix.Append(GetString("DiedR1Warning")); // Devourer @@ -1782,7 +1788,7 @@ namespace EHR if (isProgressTextLong) offset += 0.3f; - if (Options.CurrentGameMode == CustomGameMode.MoveAndStop) offset += 0.2f; + if (CustomGameMode.MoveAndStop.IsActiveOrIntegrated()) offset += 0.2f; RoleText.transform.SetLocalY(offset); } @@ -1964,6 +1970,7 @@ namespace EHR }, 0.5f, "FFA-NoVentingWhenKCDIsUP"); return true; + case CustomGameMode.AllInOne: case CustomGameMode.MoveAndStop: case CustomGameMode.HotPotato: case CustomGameMode.Speedrun: @@ -2039,7 +2046,7 @@ namespace EHR if (((__instance.myPlayer.Data.Role.Role != RoleTypes.Engineer && !__instance.myPlayer.CanUseImpostorVentButton()) || (__instance.myPlayer.Is(CustomRoles.Mayor) && Mayor.MayorUsedButtonCount.TryGetValue(__instance.myPlayer.PlayerId, out int count) && count >= Mayor.MayorNumOfUseButton.GetInt()) || (__instance.myPlayer.Is(CustomRoles.Paranoia) && Paranoia.ParaUsedButtonCount.TryGetValue(__instance.myPlayer.PlayerId, out int count2) && count2 >= Options.ParanoiaNumOfUseButton.GetInt())) - && !__instance.myPlayer.Is(CustomRoles.Nimble) && !__instance.myPlayer.Is(CustomRoles.Bloodlust) && Options.CurrentGameMode == CustomGameMode.Standard) + && !__instance.myPlayer.Is(CustomRoles.Nimble) && !__instance.myPlayer.Is(CustomRoles.Bloodlust) && CustomGameMode.Standard.IsActiveOrIntegrated()) { try { @@ -2103,7 +2110,7 @@ namespace EHR NotifyRoles(SpecifySeer: __instance, ForceLoop: true); } - if (Options.CurrentGameMode == CustomGameMode.HideAndSeek && HnSManager.PlayerRoles[__instance.PlayerId].Interface.Team == Team.Crewmate && __instance.IsAlive()) Hider.OnSpecificTaskComplete(__instance, task); + if (CustomGameMode.HideAndSeek.IsActiveOrIntegrated() && HnSManager.PlayerRoles[__instance.PlayerId].Interface.Team == Team.Crewmate && __instance.IsAlive()) Hider.OnSpecificTaskComplete(__instance, task); } } diff --git a/Patches/PlayerJoinAndLeftPatch.cs b/Patches/PlayerJoinAndLeftPatch.cs index 49489494b..38e39cd3d 100644 --- a/Patches/PlayerJoinAndLeftPatch.cs +++ b/Patches/PlayerJoinAndLeftPatch.cs @@ -204,7 +204,7 @@ namespace EHR if (GameStates.IsInGame && data != null && data.Character != null) { - if (Options.CurrentGameMode == CustomGameMode.HideAndSeek) HnSManager.PlayerRoles.Remove(data.Character.PlayerId); + if (CustomGameMode.HideAndSeek.IsActiveOrIntegrated()) HnSManager.PlayerRoles.Remove(data.Character.PlayerId); if (data.Character.Is(CustomRoles.Lovers) && !data.Character.Data.IsDead) { diff --git a/Patches/SabotageSystemPatch.cs b/Patches/SabotageSystemPatch.cs index 1d107caf4..5c64c6565 100644 --- a/Patches/SabotageSystemPatch.cs +++ b/Patches/SabotageSystemPatch.cs @@ -309,7 +309,7 @@ namespace EHR public static bool Prefix([HarmonyArgument(0)] PlayerControl player, [HarmonyArgument(1)] MessageReader msgReader) { - if (Options.CurrentGameMode != CustomGameMode.Standard) return false; + if (!CustomGameMode.Standard.IsActiveOrIntegrated()) return false; if (Options.DisableSabotage.GetBool()) { diff --git a/Patches/ShipStatusPatch.cs b/Patches/ShipStatusPatch.cs index 6805cbad2..a9215732f 100644 --- a/Patches/ShipStatusPatch.cs +++ b/Patches/ShipStatusPatch.cs @@ -82,7 +82,7 @@ namespace EHR if (!AmongUsClient.Instance.AmHost) return true; // Execute the following only on the host - if ((Options.CurrentGameMode != CustomGameMode.Standard || Options.DisableSabotage.GetBool()) && systemType == SystemTypes.Sabotage) return false; + if ((!CustomGameMode.Standard.IsActiveOrIntegrated() || Options.DisableSabotage.GetBool()) && systemType == SystemTypes.Sabotage) return false; if (player.Is(CustomRoles.Fool) && systemType is SystemTypes.Comms or SystemTypes.Electrical) return false; @@ -176,7 +176,7 @@ namespace EHR break; } case SystemTypes.Sabotage when AmongUsClient.Instance.NetworkMode != NetworkModes.FreePlay: - if (Options.CurrentGameMode != CustomGameMode.Standard) return false; + if (!CustomGameMode.Standard.IsActiveOrIntegrated()) return false; if (SecurityGuard.BlockSabo.Count > 0) return false; @@ -264,7 +264,7 @@ namespace EHR { public static bool Prefix( /*ShipStatus __instance, */ [HarmonyArgument(0)] SystemTypes room) { - bool allow = !Options.DisableSabotage.GetBool() && Options.CurrentGameMode is not CustomGameMode.SoloKombat and not CustomGameMode.FFA and not CustomGameMode.MoveAndStop and not CustomGameMode.HotPotato and not CustomGameMode.Speedrun and not CustomGameMode.CaptureTheFlag and not CustomGameMode.NaturalDisasters and not CustomGameMode.RoomRush; + bool allow = !Options.DisableSabotage.GetBool() && Options.CurrentGameMode is not CustomGameMode.SoloKombat and not CustomGameMode.FFA and not CustomGameMode.MoveAndStop and not CustomGameMode.HotPotato and not CustomGameMode.Speedrun and not CustomGameMode.CaptureTheFlag and not CustomGameMode.NaturalDisasters and not CustomGameMode.RoomRush and not CustomGameMode.AllInOne; if (SecurityGuard.BlockSabo.Count > 0) allow = false; @@ -314,7 +314,7 @@ namespace EHR { public static bool Prefix(ref bool __result) { - if (Options.DisableTaskWin.GetBool() || Options.NoGameEnd.GetBool() || TaskState.InitialTotalTasks == 0 || (Options.DisableTaskWinIfAllCrewsAreDead.GetBool() && !Main.AllAlivePlayerControls.Any(x => x.Is(CustomRoleTypes.Crewmate))) || (Options.DisableTaskWinIfAllCrewsAreConverted.GetBool() && Main.AllAlivePlayerControls.Where(x => x.Is(Team.Crewmate) && x.GetRoleTypes() is RoleTypes.Crewmate or RoleTypes.Engineer or RoleTypes.Scientist or RoleTypes.CrewmateGhost or RoleTypes.GuardianAngel).All(x => x.IsConverted())) || Options.CurrentGameMode != CustomGameMode.Standard) + if (Options.DisableTaskWin.GetBool() || Options.NoGameEnd.GetBool() || TaskState.InitialTotalTasks == 0 || (Options.DisableTaskWinIfAllCrewsAreDead.GetBool() && !Main.AllAlivePlayerControls.Any(x => x.Is(CustomRoleTypes.Crewmate))) || (Options.DisableTaskWinIfAllCrewsAreConverted.GetBool() && Main.AllAlivePlayerControls.Where(x => x.Is(Team.Crewmate) && x.GetRoleTypes() is RoleTypes.Crewmate or RoleTypes.Engineer or RoleTypes.Scientist or RoleTypes.CrewmateGhost or RoleTypes.GuardianAngel).All(x => x.IsConverted())) || !CustomGameMode.Standard.IsActiveOrIntegrated()) { __result = false; return false; @@ -537,7 +537,7 @@ namespace EHR public static bool BlockVentInteraction(PlayerControl pc) { - return !pc.AmOwner && (!pc.IsModClient() || (!pc.IsHost() && Options.CurrentGameMode == CustomGameMode.RoomRush)) && !pc.Data.IsDead && (pc.IsImpostor() || pc.GetRoleTypes() is RoleTypes.Engineer or RoleTypes.Impostor or RoleTypes.Shapeshifter or RoleTypes.Phantom) && ShipStatus.Instance.AllVents.Any(vent => !pc.CanUseVent(vent.Id)); + return !pc.AmOwner && (!pc.IsModClient() || (!pc.IsHost() && CustomGameMode.RoomRush.IsActiveOrIntegrated())) && !pc.Data.IsDead && (pc.IsImpostor() || pc.GetRoleTypes() is RoleTypes.Engineer or RoleTypes.Impostor or RoleTypes.Shapeshifter or RoleTypes.Phantom) && ShipStatus.Instance.AllVents.Any(vent => !pc.CanUseVent(vent.Id)); } public static void SerializeV2(VentilationSystem __instance, PlayerControl player = null) diff --git a/Patches/TaskAssignPatch.cs b/Patches/TaskAssignPatch.cs index 9ae8b6a3e..dccacbeb9 100644 --- a/Patches/TaskAssignPatch.cs +++ b/Patches/TaskAssignPatch.cs @@ -99,7 +99,7 @@ namespace EHR }; } - if (!Options.DisableShortTasks.GetBool() && !Options.DisableCommonTasks.GetBool() && !Options.DisableLongTasks.GetBool() && !Options.DisableOtherTasks.GetBool() && Options.CurrentGameMode == CustomGameMode.Standard) return; + if (!Options.DisableShortTasks.GetBool() && !Options.DisableCommonTasks.GetBool() && !Options.DisableLongTasks.GetBool() && !Options.DisableOtherTasks.GetBool() && CustomGameMode.Standard.IsActiveOrIntegrated()) return; List disabledTasks = []; @@ -117,15 +117,15 @@ namespace EHR bool IsTaskAlwaysDisabled(TaskTypes type) => type switch { - TaskTypes.FuelEngines => Options.CurrentGameMode is CustomGameMode.MoveAndStop or CustomGameMode.Speedrun, - TaskTypes.VentCleaning => Options.CurrentGameMode == CustomGameMode.RoomRush, + TaskTypes.FuelEngines => Options.CurrentGameMode is CustomGameMode.MoveAndStop or CustomGameMode.Speedrun or CustomGameMode.AllInOne, + TaskTypes.VentCleaning => CustomGameMode.RoomRush.IsActiveOrIntegrated(), _ => false }; } } [HarmonyPatch(typeof(NetworkedPlayerInfo), nameof(NetworkedPlayerInfo.RpcSetTasks))] - internal class RpcSetTasksPatch + internal static class RpcSetTasksPatch { // Patch that overwrites the task just before assigning the task and sending the RPC // Do not interfere with vanilla task allocation process itself diff --git a/Patches/UsablesPatch.cs b/Patches/UsablesPatch.cs index 5e30feb7e..8a2525842 100644 --- a/Patches/UsablesPatch.cs +++ b/Patches/UsablesPatch.cs @@ -32,7 +32,7 @@ namespace EHR { public static void Postfix(EmergencyMinigame __instance) { - if (Options.DisableMeeting.GetBool() || Options.CurrentGameMode != CustomGameMode.Standard) __instance.Close(); + if (Options.DisableMeeting.GetBool() || !CustomGameMode.Standard.IsActiveOrIntegrated()) __instance.Close(); } } diff --git a/Resources/Lang/en_US.json b/Resources/Lang/en_US.json index 461cdb881..0c505fafa 100644 --- a/Resources/Lang/en_US.json +++ b/Resources/Lang/en_US.json @@ -4533,6 +4533,10 @@ "RRPlayer": "Room Rush", "RRPlayerInfo": "GET TO THE ROOM ASAP", "RRPlayerInfoLong": "GET TO THE ROOM ASAP", + "AllInOne": "ALL IN ONE", + "ModeAllInOne": "Gamemode: All In One", + "ModeDescribe.AllInOne": "In the All In One gamemode, all the gamemodes are combined into one. Here's how they're integrated:\\n<#f55252>- Solo PVP: You can attack players, reducing their health. When someone's health reaches 0, they're teleported out of the map for some time, then come back with full HP.\\n<#00ffa5>- Stop And Go: You have 3 timers, each with a symbol. You can only move in directions in which you have a green symbol. The timers indicate when the color changes from green to red and vice versa. If you move in a direction with a red symbol, you die.\\n<#e8cd46>- Hot Potato: Someone always holds the hot potato and must pass it to someone by going near them. The holder of the hot potato is killed every X seconds and the hot potato is given to a random player.\\n<#800080>- Speedrun: Everyone must complete a task or kill someone before the end of the time limit. Both of these actions reset it. When you're done with tasks, you're able to kill normally.\\n<#03fc4a>- Natural Disasters: Random natural disasters spawn on the map. You must avoid all of them while moving around the ship.\\n<#ffab1b>- Room Rush: You must get to the specified room in the time limit shown next to it. If you don't, you die.\\n\\nThe winner is the last player alive!\\n\\nGood luck! (- The Dev)", + "AllInOneInfo": "ALL GAME MODES IN ONE", "HideAndSeek": "HIDE AND SEEK", "ModeHideAndSeek": "Gamemode: Hide And Seek", "ModeDescribe.HideAndSeek": "In the Hide And Seek gamemode, seekers have to kill all hiders, while hiders have to complete all tasks without being killed in order to win.\\nIf the time limit reaches 0, hiders win.\\n\\nRoles: Hider, Seeker, Fox, Troll, Jumper, Detector, Jet, Dasher, Locator, Venter, Agent, Taskinator", diff --git a/Roles/AddOns/Impostor/LastImpostor.cs b/Roles/AddOns/Impostor/LastImpostor.cs index 015288b08..c0c540f27 100644 --- a/Roles/AddOns/Impostor/LastImpostor.cs +++ b/Roles/AddOns/Impostor/LastImpostor.cs @@ -47,7 +47,7 @@ namespace EHR.AddOns.Impostor { if (CurrentId != byte.MaxValue || !AmongUsClient.Instance.AmHost) return; - if (Options.CurrentGameMode != CustomGameMode.Standard || !CustomRoles.LastImpostor.IsEnable() || Main.AliveImpostorCount != 1) return; + if (!CustomGameMode.Standard.IsActiveOrIntegrated() || !CustomRoles.LastImpostor.IsEnable() || Main.AliveImpostorCount != 1) return; foreach (PlayerControl pc in Main.AllAlivePlayerControls) {