diff --git a/CTA/CustomTeamAssigner/CustomRoles.cs b/CTA/CustomTeamAssigner/CustomRoles.cs index 019722aa7..346db06d8 100644 --- a/CTA/CustomTeamAssigner/CustomRoles.cs +++ b/CTA/CustomTeamAssigner/CustomRoles.cs @@ -575,7 +575,6 @@ public enum CustomRoles Physicist, Rascal, Reach, - Recruit, Rookie, Trainee, Schizophrenic, diff --git a/EHR.csproj b/EHR.csproj index 307458e3a..3ea6601bd 100644 --- a/EHR.csproj +++ b/EHR.csproj @@ -8,8 +8,8 @@ EHR Gurge44 preview - - C:\Program Files\Epic Games\AmongUs + D:\SteamLibrary\steamapps\common\Among Us + true True $(MSBuildProjectName) diff --git a/GameMode/BedWars.cs b/GameMode/BedWars.cs index ce5897657..1c2255a1d 100644 --- a/GameMode/BedWars.cs +++ b/GameMode/BedWars.cs @@ -600,7 +600,7 @@ public static class BedWars public static void Postfix(PlayerControl __instance) { - if (!AmongUsClient.Instance.AmHost || !GameStates.IsInTask || ExileController.Instance || Options.CurrentGameMode != CustomGameMode.BedWars || !Main.IntroDestroyed || GameStates.IsEnded || __instance == null || __instance.PlayerId >= 254 || Utils.GameStartTimeStamp + 25 > Utils.TimeStamp) return; + if (!AmongUsClient.Instance.AmHost || !GameStates.IsInTask || ExileController.Instance || Options.CurrentGameMode != CustomGameMode.BedWars || !Main.IntroDestroyed || GameStates.IsEnded || __instance == null || __instance.PlayerId >= 254 || IntroCutsceneDestroyPatch.IntroDestroyTS + 10 > Utils.TimeStamp) return; long now = Utils.TimeStamp; diff --git a/GameMode/CaptureTheFlag.cs b/GameMode/CaptureTheFlag.cs index 50547a8ec..64e6530a6 100644 --- a/GameMode/CaptureTheFlag.cs +++ b/GameMode/CaptureTheFlag.cs @@ -711,7 +711,7 @@ public static class CaptureTheFlag { public static void Postfix(PlayerControl __instance) { - if (!AmongUsClient.Instance.AmHost || !GameStates.IsInTask || ExileController.Instance || Options.CurrentGameMode != CustomGameMode.CaptureTheFlag || !Main.IntroDestroyed || __instance.PlayerId >= 254 || WinnerData.Team != "No one wins" || Utils.GameStartTimeStamp + 15 > Utils.TimeStamp) return; + if (!AmongUsClient.Instance.AmHost || !GameStates.IsInTask || ExileController.Instance || Options.CurrentGameMode != CustomGameMode.CaptureTheFlag || !Main.IntroDestroyed || __instance.PlayerId >= 254 || WinnerData.Team != "No one wins" || IntroCutsceneDestroyPatch.IntroDestroyTS + 5 > Utils.TimeStamp) return; if (__instance.IsHost()) { diff --git a/GameMode/HotPotato.cs b/GameMode/HotPotato.cs index 3d7a26ade..705e5cd2c 100644 --- a/GameMode/HotPotato.cs +++ b/GameMode/HotPotato.cs @@ -136,7 +136,7 @@ internal static class HotPotato public static void Postfix(PlayerControl __instance) { - if (Options.CurrentGameMode != CustomGameMode.HotPotato || !Main.IntroDestroyed || !AmongUsClient.Instance.AmHost || !GameStates.IsInTask || ExileController.Instance || __instance.PlayerId >= 254 || Utils.GameStartTimeStamp + 15 > Utils.TimeStamp) return; + if (Options.CurrentGameMode != CustomGameMode.HotPotato || !Main.IntroDestroyed || !AmongUsClient.Instance.AmHost || !GameStates.IsInTask || ExileController.Instance || __instance.PlayerId >= 254 || IntroCutsceneDestroyPatch.IntroDestroyTS + 5 > Utils.TimeStamp) return; PlayerControl holder = Utils.GetPlayerById(HotPotatoState.HolderID); diff --git a/GameMode/NaturalDisasters.cs b/GameMode/NaturalDisasters.cs index cb715d06e..f9a6bb199 100644 --- a/GameMode/NaturalDisasters.cs +++ b/GameMode/NaturalDisasters.cs @@ -26,7 +26,6 @@ public static class NaturalDisasters public static readonly Dictionary SurvivalTimes = []; private static ((float Left, float Right) X, (float Bottom, float Top) Y) MapBounds; - private static long GameStartTimeStamp; private static OptionItem DisasterFrequency; private static OptionItem DisasterWarningTime; @@ -132,8 +131,6 @@ public static class NaturalDisasters const float extend = 5f; MapBounds = ((x.Min() - extend, x.Max() + extend), (y.Min() - extend, y.Max() + extend)); - GameStartTimeStamp = Utils.TimeStamp; - LateTask.New(() => { Main.AllPlayerSpeed = Main.PlayerStates.Keys.ToDictionary(k => k, _ => Main.RealOptionsData.GetFloat(FloatOptionNames.PlayerSpeedMod)); @@ -160,7 +157,7 @@ public static class NaturalDisasters public static void RecordDeath(PlayerControl pc, PlayerState.DeathReason deathReason) { - SurvivalTimes[pc.PlayerId] = (int)(Utils.TimeStamp - GameStartTimeStamp - 15); + SurvivalTimes[pc.PlayerId] = (int)(Utils.TimeStamp - IntroCutsceneDestroyPatch.IntroDestroyTS); string message = Translator.GetString($"ND_DRLaughMessage.{deathReason}"); message = Utils.ColorString(DeathReasonColor(deathReason), message); @@ -205,7 +202,7 @@ public static class NaturalDisasters public static void Postfix( /*PlayerControl __instance*/) { - if (!AmongUsClient.Instance.AmHost || !GameStates.IsInTask || ExileController.Instance || AntiBlackout.SkipTasks || (Options.CurrentGameMode != CustomGameMode.NaturalDisasters && !Options.IntegrateNaturalDisasters.GetBool()) || !Main.IntroDestroyed || Main.HasJustStarted || GameStartTimeStamp + 15 > Utils.TimeStamp /* || __instance.PlayerId >= 254 || !__instance.IsHost()*/) return; + if (!AmongUsClient.Instance.AmHost || !GameStates.IsInTask || ExileController.Instance || AntiBlackout.SkipTasks || (Options.CurrentGameMode != CustomGameMode.NaturalDisasters && !Options.IntegrateNaturalDisasters.GetBool()) || !Main.IntroDestroyed || Main.HasJustStarted || IntroCutsceneDestroyPatch.IntroDestroyTS + 5 > Utils.TimeStamp /* || __instance.PlayerId >= 254 || !__instance.IsHost()*/) return; if (Options.CurrentGameMode != CustomGameMode.NaturalDisasters) { @@ -220,7 +217,7 @@ public static class NaturalDisasters _ => (0, false) }; - if (shouldWait || GameStartTimeStamp + minimumWaitTime > Utils.TimeStamp) return; + if (shouldWait || IntroCutsceneDestroyPatch.IntroDestroyTS + minimumWaitTime > Utils.TimeStamp) return; } UpdatePreparingDisasters(); diff --git a/Modules/CustomNetObject.cs b/Modules/CustomNetObject.cs index d303298f9..29cbea795 100644 --- a/Modules/CustomNetObject.cs +++ b/Modules/CustomNetObject.cs @@ -5,6 +5,7 @@ using AmongUs.InnerNet.GameDataMessages; using EHR.Crewmate; using EHR.Impostor; using EHR.Modules; +using HarmonyLib; using Hazel; using InnerNet; using UnityEngine; @@ -77,6 +78,9 @@ namespace EHR sender.EndMessage(); sender.SendMessage(); + + playerControl.transform.FindChild("Names").FindChild("NameText_TMP").gameObject.SetActive(true); + LateTask.New(() => Utils.SendRPC(CustomRPC.FixModdedClientCNO, playerControl, true), 0.3f); } public void TP(Vector2 position) @@ -168,7 +172,7 @@ namespace EHR Logger.Info($" Create Custom Net Object {GetType().Name} (ID {MaxId + 1}) at {position} - Time since game start: {Utils.TimeStamp - IntroCutsceneDestroyPatch.IntroDestroyTS}s", "CNO.CreateNetObject"); - if (!GameStates.InGame || !Main.IntroDestroyed || Utils.TimeStamp - IntroCutsceneDestroyPatch.IntroDestroyTS < 10) + if (Options.CurrentGameMode == CustomGameMode.Standard && (!GameStates.InGame || !Main.IntroDestroyed || Utils.TimeStamp - IntroCutsceneDestroyPatch.IntroDestroyTS < 10)) { if (GameStates.InGame && (!Main.IntroDestroyed || Utils.TimeStamp - IntroCutsceneDestroyPatch.IntroDestroyTS < 10)) { @@ -673,7 +677,15 @@ namespace EHR protected override void OnFixedUpdate() { base.OnFixedUpdate(); + int oldTime = Time; + + if (oldTime <= 0) + { + Despawn(); + return; + } + Timer -= UnityEngine.Time.fixedDeltaTime; if (Time != oldTime) RpcChangeSprite($"{Time:N0}\n{Disaster}"); } @@ -966,4 +978,24 @@ namespace EHR Active = true; } } +} + +// This method sometimes throws an exception, preventing further code from running +// Fixed by wrapping each line in try-catch +[HarmonyPatch(typeof(PlayerControl), nameof(PlayerControl.RawSetName))] +static class RawSetNameErrorFixPatch +{ + public static bool Prefix(PlayerControl __instance, [HarmonyArgument(0)] string name) + { + try { __instance.gameObject.name = name; } + catch { } + + try { __instance.cosmetics.SetName(name); } + catch { } + + try { __instance.cosmetics.SetNameMask(true); } + catch { } + + return false; + } } \ No newline at end of file diff --git a/Modules/Statistics.cs b/Modules/Statistics.cs index 5ad2e15c7..e2f129660 100644 --- a/Modules/Statistics.cs +++ b/Modules/Statistics.cs @@ -133,7 +133,7 @@ public static class Statistics if (addons.Contains(CustomRoles.Spurt) && Spurt.LocalPlayerAvoidsZeroAndOneHundredPrecent) Achievements.Type.ExpertControl.CompleteAfterGameEnd(); - if (Utils.GameStartTimeStamp + 90 > Utils.TimeStamp) + if (IntroCutsceneDestroyPatch.IntroDestroyTS + 60 > Utils.TimeStamp) Achievements.Type.Speedrun.CompleteAfterGameEnd(); if (won && CustomWinnerHolder.WinnerTeam == CustomWinner.Impostor && lp.IsMadmate() && !aapc.Any(x => x.IsImpostor())) diff --git a/Modules/Utils.cs b/Modules/Utils.cs index edac9a5c6..669b13916 100644 --- a/Modules/Utils.cs +++ b/Modules/Utils.cs @@ -2363,7 +2363,7 @@ public static class Utils longInfo = $"<#ffffff>{longInfo}"; int lines = longInfo.Count(x => x == '\n'); - int readTime = 20 + (lines * 5); + int readTime = 10 + (lines * 5); LongRoleDescriptions[seer.PlayerId] = (longInfo, readTime, tooLong); } @@ -2678,11 +2678,11 @@ public static class Utils } else if (Options.CurrentGameMode == CustomGameMode.HideAndSeek) { - if (GameStartTimeStamp + 40 > now) seerRealName = CustomHnS.GetRoleInfoText(seer); + if (IntroCutsceneDestroyPatch.IntroDestroyTS + 15 > now) seerRealName = CustomHnS.GetRoleInfoText(seer); } else if (Options.ChangeNameToRoleInfo.GetBool() && !seer.IsModdedClient() && Options.CurrentGameMode == CustomGameMode.Standard) { - bool showLongInfo = LongRoleDescriptions.TryGetValue(seer.PlayerId, out (string Text, int Duration, bool Long) description) && GameStartTimeStamp + description.Duration > now; + bool showLongInfo = LongRoleDescriptions.TryGetValue(seer.PlayerId, out (string Text, int Duration, bool Long) description) && IntroCutsceneDestroyPatch.IntroDestroyTS + description.Duration > now; string mHelp = !showLongInfo || description.Long ? "\n" + GetString("MyRoleCommandHelp") : string.Empty; string color = seerTeam.GetTextColor(); string teamStr = seerTeam == Team.Impostor && seer.IsMadmate() ? "Madmate" : seerTeam.ToString(); diff --git a/Patches/PlayerControlPatch.cs b/Patches/PlayerControlPatch.cs index 657a32ce1..4bc1a46eb 100644 --- a/Patches/PlayerControlPatch.cs +++ b/Patches/PlayerControlPatch.cs @@ -1564,8 +1564,8 @@ internal static class FixedUpdatePatch if (self) { - if (QuizMaster.On && inTask && !lowLoad && QuizMaster.AllSabotages.Any(IsActive)) - QuizMaster.Data.LastSabotage = QuizMaster.AllSabotages.FirstOrDefault(IsActive); + if (QuizMaster.On && inTask && !lowLoad && QuizMaster.AllSabotages.FindFirst(IsActive, out SystemTypes active)) + QuizMaster.Data.LastSabotage = active; } if (!lowLoad && player.IsModdedClient() && player.Is(CustomRoles.Haste)) diff --git a/Roles/Crewmate/Adventurer.cs b/Roles/Crewmate/Adventurer.cs index a669a477a..a662497bc 100644 --- a/Roles/Crewmate/Adventurer.cs +++ b/Roles/Crewmate/Adventurer.cs @@ -338,6 +338,9 @@ internal class Adventurer : RoleBase public override void AfterMeetingTasks() { + long now = Utils.TimeStamp; + LastGroupingResourceTimeStamp = now; + LastRandomResourceTimeStamp = now; ActiveWeapons.Remove(Weapon.Proxy); } diff --git a/Roles/Impostor/Abyssbringer.cs b/Roles/Impostor/Abyssbringer.cs index 1177dd8ed..6b7ac97da 100644 --- a/Roles/Impostor/Abyssbringer.cs +++ b/Roles/Impostor/Abyssbringer.cs @@ -97,6 +97,14 @@ public class Abyssbringer : RoleBase Main.AllPlayerKillCooldown[id] = KillCooldown.GetInt(); } + public override void OnMurder(PlayerControl killer, PlayerControl target) + { + if (Options.UsePets.GetBool() && !Options.UsePhantomBasis.GetBool()) + killer.AddAbilityCD(); + else + killer.RpcResetAbilityCooldown(); + } + public override bool OnShapeshift(PlayerControl shapeshifter, PlayerControl target, bool shapeshifting) { if (!shapeshifting) return true; @@ -123,6 +131,7 @@ public class Abyssbringer : RoleBase string roomName = room == null ? string.Empty : Translator.GetString($"{room.RoomId}"); BlackHoles.Add(new(new(pos), Utils.TimeStamp, pos, roomName, 0)); Utils.SendRPC(CustomRPC.SyncRoleData, AbyssbringerId, 1, pos, roomName); + shapeshifter.SetKillCooldown(KillCooldown.GetInt()); } public override void OnReportDeadBody()