Compare commits

...
6 Commits
31 changed files with 429 additions and 410 deletions

No files matched your search

+3 -15
View File
@@ -1,6 +1,7 @@
using System;
using System.Collections.Generic;
using System.Linq;
using Hazel;
using UnityEngine;
namespace EHR;
@@ -242,6 +243,7 @@ public static class Snowdown
public static void OnCheckMurder(PlayerControl killer, PlayerControl target)
{
killer.SetKillCooldown(5f);
if (!Data.TryGetValue(killer.PlayerId, out PlayerData killerData) || !Data.TryGetValue(target.PlayerId, out PlayerData targetData) || killerData.SnowballsReady < 1 || targetData.SnowballsReady >= targetData.MaxSnowballsReady) return;
killerData.SnowballsReady--;
targetData.SnowballsReady++;
@@ -279,20 +281,7 @@ public static class Snowdown
data.LastPosition = pos;
}
foreach (PlayerControl target in Main.AllAlivePlayerControls)
{
string suffix = GetSuffix(__instance, target);
if (!data.LastSuffix.TryGetValue(target.PlayerId, out string lastSuffix))
goto Skip;
if (lastSuffix != suffix)
Utils.NotifyRoles(SpecifySeer: __instance, SpecifyTarget: target);
Skip:
data.LastSuffix[target.PlayerId] = suffix;
}
Utils.NotifyRoles(SpecifySeer: __instance, SendOption: SendOption.None);
}
}
@@ -310,7 +299,6 @@ public static class Snowdown
private int ShopSelectedIndex;
public int Points;
private bool ShowHelp;
public readonly Dictionary<byte, string> LastSuffix = [];
public void OnSabotage(PlayerControl pc)
{
+2 -2
View File
@@ -42,8 +42,8 @@ public class Main : BasePlugin
private const string DebugKeyHash = "c0fd562955ba56af3ae20d7ec9e64c664f0facecef4b3e366e109306adeae29d";
private const string DebugKeySalt = "59687b";
private const string PluginGuid = "com.gurge44.endlesshostroles";
public const string PluginVersion = "7.0.1";
public const string PluginDisplayVersion = "7.0.1";
public const string PluginVersion = "7.0.2";
public const string PluginDisplayVersion = "7.0.2";
public const bool TestBuild = false;
public const string NeutralColor = "#ffab1b";
+6 -3
View File
@@ -2,6 +2,7 @@
using System.Collections.Generic;
using System.Linq;
using AmongUs.GameOptions;
using EHR.Modules;
using EHR.Patches;
using Hazel;
@@ -50,7 +51,7 @@ public static class AntiBlackout
dummyImp.RpcSetRoleGlobal(RoleTypes.Impostor);
players.Without(dummyImp).Where(x => x.GetRoleMap().RoleType != RoleTypes.Detective).Do(x => x.RpcSetRoleGlobal(RoleTypes.Crewmate));
Main.AllPlayerControls.DoIf(x => !x.IsAlive() && x.Data != null && x.Data.IsDead, x => x.RpcSetRoleGlobal(x.HasGhostRole() ? RoleTypes.GuardianAngel : RoleTypes.CrewmateGhost));
Main.AllPlayerControls.DoIf(x => !x.IsAlive() && x.Data != null && x.Data.IsDead, x => x.RpcSetRoleGlobal(GhostRolesManager.AssignedGhostRoles.TryGetValue(x.PlayerId, out var ghostRole) ? ghostRole.Instance.RoleTypes : RoleTypes.CrewmateGhost));
}
// After the ejection screen, we revert the role types to their actual values.
@@ -89,7 +90,7 @@ public static class AntiBlackout
if (seer == null || target == null) continue;
if (target.IsAlive()) target.RpcSetRoleDesync(roleType, seer.OwnerId);
else target.RpcSetRoleDesync(target.HasGhostRole() ? RoleTypes.GuardianAngel : seer.PlayerId == target.PlayerId && !(target.Is(CustomRoleTypes.Impostor) && Options.DeadImpCantSabotage.GetBool()) && Main.PlayerStates.TryGetValue(target.PlayerId, out var state) && state.Role.CanUseSabotage(target) ? RoleTypes.ImpostorGhost : RoleTypes.CrewmateGhost, seer.OwnerId);
else target.RpcSetRoleDesync(GhostRolesManager.AssignedGhostRoles.TryGetValue(targetId, out var ghostRole) ? ghostRole.Instance.RoleTypes : seerId == targetId && !(target.Is(CustomRoleTypes.Impostor) && Options.DeadImpCantSabotage.GetBool()) && Main.PlayerStates.TryGetValue(targetId, out var state) && state.Role.CanUseSabotage(target) ? RoleTypes.ImpostorGhost : RoleTypes.CrewmateGhost, seer.OwnerId);
}
catch (Exception e) { Utils.ThrowException(e); }
}
@@ -126,7 +127,9 @@ public static class AntiBlackout
pc.Exiled();
MessageWriter writer = AmongUsClient.Instance.StartRpcImmediately(pc.NetId, 4, SendOption.Reliable);
AmongUsClient.Instance.FinishRpcImmediately(writer);
if (pc.HasGhostRole()) pc.RpcResetAbilityCooldown();
if (GhostRolesManager.AssignedGhostRoles.TryGetValue(pc.PlayerId, out var ghostRole) && ghostRole.Instance.RoleTypes == RoleTypes.GuardianAngel)
pc.RpcResetAbilityCooldown();
}
}
catch (Exception e) { Utils.ThrowException(e); }
+3 -2
View File
@@ -33,12 +33,13 @@ internal static class GhostRolesManager
IGhostRole instance = CreateGhostRoleInstance(suitableRole);
pc.RpcSetCustomRole(suitableRole);
pc.RpcSetRoleDesync(RoleTypes.GuardianAngel, pc.OwnerId);
pc.RpcSetRoleDesync(instance.RoleTypes, pc.OwnerId);
instance.OnAssign(pc);
Main.ResetCamPlayerList.Add(pc.PlayerId);
AssignedGhostRoles[pc.PlayerId] = (suitableRole, instance);
if (suitableRole == CustomRoles.Haunter) GhostRoles.Remove(suitableRole);
if (suitableRole == CustomRoles.Haunter)
GhostRoles.Remove(suitableRole);
NotifyAboutGhostRole(pc, true);
}
+2 -2
View File
@@ -1026,7 +1026,7 @@ public static class Options
sb.AppendLine("| Command | Description | Arguments | Usage Level | Usage Time | Hidden |");
sb.AppendLine("|---------|-------------|-----------|-------------|------------|--------|");
foreach (Command command in ChatCommands.AllCommands)
foreach ((String key, Command command) in Command.AllCommands)
{
string forms = command.CommandForms.TakeWhile(x => x.All(char.IsAscii)).Join(x => $"/{x}", "<br>");
string description = command.Description;
@@ -1077,7 +1077,7 @@ public static class Options
}
sb.AppendLine("| | | | | | |");
sb.Append($"| {ChatCommands.AllCommands.Count} | | | | | |");
sb.Append($"| {Command.AllCommands.Count} | | | | | |");
const string path = "./commands.txt";
if (!File.Exists(path)) File.Create(path).Close();
+15 -10
View File
@@ -666,18 +666,23 @@ internal static class RPCHandlerPatch
{
if (!AmongUsClient.Instance.AmHost) break;
string methodName = reader.ReadString();
string commandKey = reader.ReadString();
PlayerControl player = reader.ReadByte().GetPlayer();
string text = reader.ReadString();
bool modCommand = reader.ReadBoolean();
bool adminCommand = reader.ReadBoolean();
if (modCommand && !ChatCommands.IsPlayerModerator(player.FriendCode)) break;
if (adminCommand && !ChatCommands.IsPlayerAdmin(player.FriendCode)) break;
if (!Command.AllCommands.TryGetValue(commandKey, out Command command))
{
Logger.Error($"Invalid Command {commandKey}.", "RequestCommandProcessingFromHost");
break;
}
const BindingFlags flags = BindingFlags.Static | BindingFlags.NonPublic | BindingFlags.Public;
typeof(ChatCommands).GetMethod(methodName, flags)?.Invoke(null, [player, text, text.Split(' ')]);
Logger.Info($"Invoke Command: {methodName} ({player?.Data?.PlayerName}, {text})", "RequestCommandProcessing");
if (!command.CanUseCommand(player)) break;
command.Action(player, commandKey, text, text.Split(' '));
// const BindingFlags flags = BindingFlags.Static | BindingFlags.NonPublic | BindingFlags.Public;
// typeof(ChatCommands).GetMethod(methodName, flags)?.Invoke(null, [player, text, text.Split(' ')]);
Logger.Info($"Invoke Command: {command.Action.Method.Name} ({player?.Data?.PlayerName}, {text})", "RequestCommandProcessing");
break;
}
case CustomRPC.SyncPostman:
@@ -1360,13 +1365,13 @@ internal static class RPCHandlerPatch
{
int playerId = reader.ReadByte();
var command = $"/retribute {playerId}";
ChatCommands.RetributeCommand(__instance, command, command.Split(' '));
ChatCommands.RetributeCommand(__instance, "Command.Retribute", command, command.Split(' '));
break;
}
case CustomRPC.StarspawnClick:
{
var command = $"/daybreak";
ChatCommands.DayBreakCommand(__instance, command, command.Split(' '));
ChatCommands.DayBreakCommand(__instance, "Command.DayBreak", command, command.Split(' '));
break;
}
case CustomRPC.VentriloquistClick:
+2 -5
View File
@@ -1721,7 +1721,7 @@ public static class Utils
public static void ShowHelp(byte id)
{
PlayerControl player = GetPlayerById(id);
SendMessage(ChatCommands.AllCommands.Where(x => x.CanUseCommand(player, false) && !x.CommandForms.Contains("help")).Aggregate("<size=70%>", (s, c) => s + $"\n<b>/{c.CommandForms.TakeWhile(f => f.All(char.IsAscii)).MinBy(f => f.Length)}{(c.Arguments.Length == 0 ? string.Empty : $" {c.Arguments.Split(' ').Select((x, i) => id == 0 ? ColorString(GetColor(i), x) : x).Join(delimiter: " ")}")}</b> \u2192 {c.Description}"), id, GetString("CommandList"));
SendMessage(Command.AllCommands.Values.Where(x => x.CanUseCommand(player, false) && !x.CommandForms.Contains("help")).Aggregate("<size=70%>", (s, c) => s + $"\n<b>/{c.CommandForms.TakeWhile(f => f.All(char.IsAscii)).MinBy(f => f.Length)}{(c.Arguments.Length == 0 ? string.Empty : $" {c.Arguments.Split(' ').Select((x, i) => id == 0 ? ColorString(GetColor(i), x) : x).Join(delimiter: " ")}")}</b> \u2192 {c.Description}"), id, GetString("CommandList"));
return;
Color GetColor(int i) =>
@@ -3539,16 +3539,13 @@ public static class Utils
}
Main.PlayerStates[pc.PlayerId].Role.AfterMeetingTasks();
if (pc.Is(CustomRoles.Phantasm) || pc.Is(CustomRoles.Haunter))
pc.RpcResetAbilityCooldown();
if (pc.Is(CustomRoles.TaskMaster))
TaskMaster.AfterMeetingTasks(pc);
Main.CheckShapeshift[pc.PlayerId] = false;
}
catch (System.Exception e) { ThrowException(e); }
catch (Exception e) { ThrowException(e); }
}
LateTask.New(() => Main.ProcessShapeshifts = true, 1f, log: false);
File diff suppressed because it is too large. Load diff
-13
View File
@@ -1,7 +1,5 @@
using System;
using System.Linq;
using HarmonyLib;
using InnerNet;
using TMPro;
using UnityEngine;
@@ -79,16 +77,6 @@ public static class HostInfoPanelSetUpPatch
}
}
public static class LobbyPatch
{
public static bool IsGlitchedRoomCode()
{
string roomCode = GameCode.IntToGameName(AmongUsClient.Instance.GameId).ToUpper();
string[] badEndings = ["IJPG", "SZAF", "LDQG", "ALGG", "UMPG", "GFXG", "JTFG", "PATG", "WMPG", "FUGG", "YTHG", "UFLG", "FBGG", "ZCQG", "RGGG", "ZHLG", "PJDG", "KJQG", "VDXG", "LCAF"];
return badEndings.Any(roomCode.EndsWith);
}
}
// https://github.com/SuperNewRoles/SuperNewRoles/blob/master/SuperNewRoles/Patches/LobbyBehaviourPatch.cs
//[HarmonyPatch(typeof(LobbyBehaviour), nameof(LobbyBehaviour.Update))]
internal static class LobbyBehaviourUpdatePatch
@@ -110,5 +98,4 @@ internal static class LobbyBehaviourUpdatePatch
SoundManager.Instance.CrossFadeSound("MapTheme", __instance.MapTheme, 0.5f);
}
}
}
+8 -2
View File
@@ -108,7 +108,7 @@ internal static class CheckForEndVotingPatch
}
}
if (!shouldSkip && !__instance.playerStates.All(ps => ps == null || !Main.PlayerStates.TryGetValue(ps.TargetPlayerId, out PlayerState st) || st.IsDead || ps.AmDead || ps.DidVote || Utils.GetPlayerById(ps.TargetPlayerId) == null || Utils.GetPlayerById(ps.TargetPlayerId).Data == null || Utils.GetPlayerById(ps.TargetPlayerId).Data.Disconnected)) return false;
if (!shouldSkip && !__instance.playerStates.All(ps => ps == null || Silencer.ForSilencer.Contains(ps.TargetPlayerId) || !Main.PlayerStates.TryGetValue(ps.TargetPlayerId, out PlayerState st) || st.IsDead || ps.AmDead || ps.DidVote || Utils.GetPlayerById(ps.TargetPlayerId) == null || Utils.GetPlayerById(ps.TargetPlayerId).Data == null || Utils.GetPlayerById(ps.TargetPlayerId).Data.Disconnected)) return false;
NetworkedPlayerInfo exiledPlayer = PlayerControl.LocalPlayer.Data;
var tie = false;
@@ -1372,6 +1372,12 @@ internal static class MeetingHudCastVotePatch
voteCanceled = true;
}
if (Silencer.ForSilencer.Contains(srcPlayerId))
{
ShouldCancelVoteList.TryAdd(srcPlayerId, (__instance, pvaSrc, pcSrc));
voteCanceled = true;
}
Logger.Info($"{pcSrc.GetNameWithRole()} => {(skip ? "Skip" : pcTarget.GetNameWithRole())}{(voteCanceled ? " (Canceled)" : string.Empty)}", "Vote");
return skip || !voteCanceled; // return false to use the vote as a trigger; skips and invalid votes are never canceled
@@ -1545,7 +1551,7 @@ internal static class ExileControllerBeginPatch
{
public static void Postfix(ExileController __instance, [HarmonyArgument(0)] ExileController.InitProperties init)
{
if (Options.CurrentGameMode is CustomGameMode.Standard or CustomGameMode.TheMindGame && init is { outfit: not null })
if (CheckForEndVotingPatch.EjectionText.EndsWith("<size=0>") && Options.CurrentGameMode is CustomGameMode.Standard or CustomGameMode.TheMindGame && init is { outfit: not null })
__instance.completeString = CheckForEndVotingPatch.EjectionText[..^8];
}
+33 -2
View File
@@ -1542,7 +1542,7 @@ internal static class FixedUpdatePatch
if (!BanManager.TempBanWhiteList.Contains(hashedPuid)) BanManager.TempBanWhiteList.Add(hashedPuid);
}
if (!Main.AllPlayerControls.All(x => x.Data.PlayerLevel <= 1) && !LobbyPatch.IsGlitchedRoomCode())
if (!Main.AllPlayerControls.All(x => x.Data.PlayerLevel <= 1))
{
string msg = string.Format(GetString("KickBecauseLowLevel"), player.GetRealName().RemoveHtmlTags());
Logger.SendInGame(msg, Color.yellow);
@@ -2259,6 +2259,35 @@ internal static class PlayerControlCompleteTaskPatch
}
}
[HarmonyPatch(typeof(GameManager), nameof(GameManager.OnPlayerDeath))]
static class GameManagerOnPlayerDeathPatch
{
public static void Prefix([HarmonyArgument(0)] PlayerControl player, [HarmonyArgument(1)] ref bool assignGhostRole)
{
if (!ReportDeadBodyPatch.MeetingStarted && !GameStates.IsMeeting && Main.PlayerStates.Values.Any(x => x.Role is SoulCollector sc && sc.ToExile.Contains(player.PlayerId)))
assignGhostRole = false;
}
}
[HarmonyPatch(typeof(LogicRoleSelectionNormal), nameof(LogicRoleSelectionNormal.OnPlayerDeath))]
static class LogicRoleSelectionNormalOnPlayerDeathPatch
{
public static void Prefix([HarmonyArgument(0)] PlayerControl player, [HarmonyArgument(1)] ref bool assignGhostRole)
{
if (!ReportDeadBodyPatch.MeetingStarted && !GameStates.IsMeeting && Main.PlayerStates.Values.Any(x => x.Role is SoulCollector sc && sc.ToExile.Contains(player.PlayerId)))
assignGhostRole = false;
}
}
[HarmonyPatch(typeof(RoleManager), nameof(RoleManager.AssignRoleOnDeath))]
static class RoleManagerAssignRoleOnDeathPatch
{
public static bool Prefix([HarmonyArgument(0)] PlayerControl player)
{
return ReportDeadBodyPatch.MeetingStarted || GameStates.IsMeeting || !Main.PlayerStates.Values.Any(x => x.Role is SoulCollector sc && sc.ToExile.Contains(player.PlayerId));
}
}
[HarmonyPatch(typeof(PlayerControl), nameof(PlayerControl.Die))]
public static class PlayerControlDiePatch
{
@@ -2345,7 +2374,9 @@ internal static class PlayerControlSetRolePatch
if (roleType is RoleTypes.CrewmateGhost or RoleTypes.ImpostorGhost)
{
if (__instance.HasGhostRole() || GhostRolesManager.ShouldHaveGhostRole(__instance))
if (GhostRolesManager.AssignedGhostRoles.TryGetValue(__instance.PlayerId, out var ghostRole))
roleType = ghostRole.Instance.RoleTypes;
else if (GhostRolesManager.ShouldHaveGhostRole(__instance))
roleType = RoleTypes.GuardianAngel;
else if (!(__instance.Is(CustomRoleTypes.Impostor) && Options.DeadImpCantSabotage.GetBool()) && Main.PlayerStates.TryGetValue(__instance.PlayerId, out var state) && state.Role.CanUseSabotage(__instance))
roleType = RoleTypes.ImpostorGhost;
+4 -4
View File
@@ -141,7 +141,7 @@ internal static class OnGameJoinedPatch
}
if (Options.AutoGMPollCommandAfterJoin.GetBool() && !Options.AutoGMRotationEnabled)
ChatCommands.GameModePollCommand(PlayerControl.LocalPlayer, "/gmpoll", ["/gmpoll"]);
ChatCommands.GameModePollCommand(PlayerControl.LocalPlayer, "Command.GameModePoll", "/gmpoll", ["/gmpoll"]);
}
}
@@ -161,7 +161,7 @@ internal static class OnGameJoinedPatch
}
if (Options.AutoMPollCommandAfterJoin.GetBool() && !Options.RandomMapsMode.GetBool())
ChatCommands.MapPollCommand(PlayerControl.LocalPlayer, "/mpoll", ["/mpoll"]);
ChatCommands.MapPollCommand(PlayerControl.LocalPlayer, "Command.MapPoll", "/mpoll", ["/mpoll"]);
}
}
@@ -181,7 +181,7 @@ internal static class OnGameJoinedPatch
}
if (Options.AutoDraftStartCommandAfterJoin.GetBool())
ChatCommands.DraftStartCommand(PlayerControl.LocalPlayer, "/draftstart", ["/draftstart"]);
ChatCommands.DraftStartCommand(PlayerControl.LocalPlayer, "Command.DraftStart", "/draftstart", ["/draftstart"]);
}
}
@@ -217,7 +217,7 @@ internal static class OnGameJoinedPatch
if (Options.AutoGMRotationEnabled)
{
if (nextGM == CustomGameMode.All) ChatCommands.GameModePollCommand(PlayerControl.LocalPlayer, "/gmpoll", ["/gmpoll"]);
if (nextGM == CustomGameMode.All) ChatCommands.GameModePollCommand(PlayerControl.LocalPlayer, "Command.GameModePoll", "/gmpoll", ["/gmpoll"]);
else Options.GameMode.SetValue((int)nextGM - 1);
Logger.Info($"Auto GM Rotation: Next Game Mode = {nextGM}", "Auto GM Rotation");
+2 -2
View File
@@ -132,9 +132,9 @@ public static class TextBoxPatch
var exactMatch = false;
bool english = TranslationController.Instance.currentLanguage.languageID == SupportedLangs.English;
foreach (Command cmd in ChatCommands.AllCommands)
foreach ((string key, Command cmd) in Command.AllCommands)
{
string[] commandForms = english ? cmd.CommandForms.TakeWhile(x => x.All(char.IsAscii)).ToArray() : cmd.CommandForms;
string[] commandForms = english ? [.. cmd.CommandForms.TakeWhile(x => x.All(char.IsAscii))] : cmd.CommandForms;
foreach (string form in commandForms)
{
+3 -2
View File
@@ -92,8 +92,9 @@ pinbrittle#1538 | 4955c179f | Moralmaser | Cheating | Cheating and disrupting lo
dollfly#4791 | 5ba449454 | Mari | Cheating | Spamming RPCs to crash lobbies
byechic#6270 | 91e0145f1 | (Contains n word) | Harassing a streamer with a slur in the IGN |
waiverfore#0496 | b493df896 | | Hacking in syl's lobby |
whaleutter#4768 | 9e04dc5d5 | | Cheaing in syl's lobby | no name hacker
waiverfore#0496 | b493df896 | | Cheating in Syl's lobby |
whaleutter#4768 | 9e04dc5d5 | | Cheating in Syl's lobby | No name cheater
whimrecent#6558 | f8452a9d1 | | Cheating | no name cheater
## Griefers, Toxic, harrasing, morons
setmolar#4374 | | 藏族顶针 | Toxic |
overtfeast#5802 | | 黑影 | Toxic |
+2
View File
@@ -1,5 +1,6 @@
using System.Collections.Generic;
using System.Linq;
using AmongUs.GameOptions;
using Hazel;
namespace EHR.AddOns.GhostRoles;
@@ -18,6 +19,7 @@ internal class Bloodmoon : IGhostRole
private byte BloodmoonID;
public Team Team => Team.Impostor | Team.Neutral;
public RoleTypes RoleTypes => RoleTypes.GuardianAngel;
public int Cooldown => CD.GetInt() + Main.PlayerStates.Values.Count(x => x.GetRealKiller() == BloodmoonID && x.deathReason == PlayerState.DeathReason.LossOfBlood) * CDIncreasePerUse.GetInt();
public void OnAssign(PlayerControl pc)
+4 -1
View File
@@ -1,10 +1,13 @@
namespace EHR.AddOns.GhostRoles;
using AmongUs.GameOptions;
namespace EHR.AddOns.GhostRoles;
public class Facilitator : IGhostRole
{
private static OptionItem CD;
public Team Team => Team.Coven;
public RoleTypes RoleTypes => RoleTypes.GuardianAngel;
public int Cooldown => CD.GetInt();
public void OnProtect(PlayerControl pc, PlayerControl target)
+2
View File
@@ -1,4 +1,5 @@
using System.Collections.Generic;
using AmongUs.GameOptions;
namespace EHR.AddOns.GhostRoles;
@@ -10,6 +11,7 @@ internal class GA : IGhostRole
public HashSet<byte> ProtectionList = [];
public Team Team => Team.Crewmate;
public RoleTypes RoleTypes => RoleTypes.GuardianAngel;
public int Cooldown => CD.GetInt();
public void OnProtect(PlayerControl pc, PlayerControl target)
+10 -8
View File
@@ -14,7 +14,7 @@ internal class Haunter : IGhostRole
private static OptionItem RevealNeutralKillers;
private static OptionItem RevealMadmates;
private static OptionItem NumberOfReveals;
public static OptionItem CanWinWithCrewmates;
private static OptionItem CanWinWithCrewmates;
private static readonly string[] WinWithCrewOpts =
[
@@ -28,6 +28,7 @@ internal class Haunter : IGhostRole
private long WarnTimeStamp;
public Team Team => Team.Crewmate | Team.Neutral;
public RoleTypes RoleTypes => RoleTypes.CrewmateGhost;
public int Cooldown => 900;
public void OnProtect(PlayerControl pc, PlayerControl target) { }
@@ -47,7 +48,6 @@ internal class Haunter : IGhostRole
pc.RpcResetTasks();
pc.SyncSettings();
pc.RpcResetAbilityCooldown();
Utils.NotifyRoles(SpecifySeer: pc, SpecifyTarget: pc);
}, 1f, "Haunter Assign");
}
@@ -95,14 +95,14 @@ internal class Haunter : IGhostRole
};
});
WarnTimeStamp = Utils.TimeStamp + 2;
foreach (PlayerControl imp in filtered)
{
TargetArrow.Add(imp.PlayerId, pc.PlayerId);
WarnedImps.Add(imp.PlayerId);
imp.Notify(Translator.GetString("Haunter1TaskLeft"), 10f);
}
WarnTimeStamp = Utils.TimeStamp;
}
public void OnFinishedTasks(PlayerControl pc)
@@ -123,15 +123,17 @@ internal class Haunter : IGhostRole
AllHauntedPlayers.UnionWith(targets);
targets.ForEach(x => Utils.GetPlayerById(x)?.Notify(Translator.GetString("HaunterRevealedYou"), 7f));
WarnedImps.ForEach(x => Utils.GetPlayerById(x)?.Notify(Translator.GetString("HaunterFinishedTasks"), 7f));
var targetPcs = targets.ToValidPlayers();
targets.ToValidPlayers().ForEach(x => Utils.NotifyRoles(SpecifyTarget: x));
targetPcs.ForEach(x => x.Notify(Translator.GetString("HaunterRevealedYou"), 10f));
WarnedImps.ToValidPlayers().ForEach(x => x.Notify(Translator.GetString("HaunterFinishedTasks"), 10f));
targetPcs.ForEach(x => Utils.NotifyRoles(SpecifyTarget: x));
}
public void Update(PlayerControl pc)
{
if (WarnedImps.Count == 0 || WarnTimeStamp == Utils.TimeStamp) return;
if (WarnedImps.Count == 0 || WarnTimeStamp >= Utils.TimeStamp) return;
if (WarnedImps.Any(imp => TargetArrow.GetArrows(Utils.GetPlayerById(imp), pc.PlayerId) == "・"))
{
+4 -1
View File
@@ -1,8 +1,11 @@
namespace EHR.AddOns.GhostRoles;
using AmongUs.GameOptions;
namespace EHR.AddOns.GhostRoles;
public interface IGhostRole
{
public Team Team { get; }
public RoleTypes RoleTypes { get; }
public int Cooldown { get; }
public void OnProtect(PlayerControl pc, PlayerControl target);
public void OnAssign(PlayerControl pc);
+2
View File
@@ -1,4 +1,5 @@
using System.Collections.Generic;
using AmongUs.GameOptions;
using EHR.Modules;
namespace EHR.AddOns.GhostRoles;
@@ -11,6 +12,7 @@ internal class Minion : IGhostRole
private static OptionItem CD;
public Team Team => Team.Impostor;
public RoleTypes RoleTypes => RoleTypes.GuardianAngel;
public int Cooldown => CD.GetInt();
public void OnProtect(PlayerControl pc, PlayerControl target)
+1 -1
View File
@@ -10,6 +10,7 @@ internal class Phantasm : IGhostRole
public bool IsWon;
public Team Team => Team.Neutral;
public RoleTypes RoleTypes => RoleTypes.CrewmateGhost;
public int Cooldown => 900;
public void OnAssign(PlayerControl pc)
@@ -27,7 +28,6 @@ internal class Phantasm : IGhostRole
pc.RpcResetTasks();
pc.SyncSettings();
pc.RpcResetAbilityCooldown();
Utils.NotifyRoles(SpecifySeer: pc, SpecifyTarget: pc);
}, 1f, "Phantasm Assign");
}
+2
View File
@@ -1,4 +1,5 @@
using System.Collections.Generic;
using AmongUs.GameOptions;
namespace EHR.AddOns.GhostRoles;
@@ -9,6 +10,7 @@ public class Shade : IGhostRole
public HashSet<byte> Protected = [];
public Team Team => Team.Neutral;
public RoleTypes RoleTypes => RoleTypes.GuardianAngel;
public int Cooldown => CD.GetInt();
public void OnProtect(PlayerControl pc, PlayerControl target)
+2
View File
@@ -1,5 +1,6 @@
using System;
using System.Collections.Generic;
using AmongUs.GameOptions;
namespace EHR.AddOns.GhostRoles;
@@ -13,6 +14,7 @@ internal class Warden : IGhostRole
private readonly Dictionary<byte, (long StartTimeStamp, float OriginalSpeed)> SpeedList = [];
public Team Team => Team.Crewmate;
public RoleTypes RoleTypes => RoleTypes.GuardianAngel;
public int Cooldown => CD.GetInt();
public void OnProtect(PlayerControl pc, PlayerControl target)
+2 -2
View File
@@ -63,7 +63,7 @@ public class Imitator : RoleBase
{
int playerId = reader.ReadByte();
var command = $"/imitate {playerId}";
ChatCommands.ImitateCommand(pc, command, command.Split(' '));
ChatCommands.ImitateCommand(pc, "Command.Imitate", command, command.Split(' '));
}
private static void ImitatorOnClick(byte playerId /*, MeetingHud __instance*/)
@@ -75,7 +75,7 @@ public class Imitator : RoleBase
if (AmongUsClient.Instance.AmHost)
{
var command = $"/imitate {playerId}";
ChatCommands.ImitateCommand(PlayerControl.LocalPlayer, command, command.Split(' '));
ChatCommands.ImitateCommand(PlayerControl.LocalPlayer, "Command.Imitate", command, command.Split(' '));
if (ImitatingRole.ContainsKey(PlayerControl.LocalPlayer.PlayerId))
{
+2 -2
View File
@@ -107,7 +107,7 @@ public class Retributionist : RoleBase
public override void OnMeetingShapeshift(PlayerControl shapeshifter, PlayerControl target)
{
var command = $"/retribute {target.PlayerId}";
ChatCommands.RetributeCommand(shapeshifter, command, command.Split(' '));
ChatCommands.RetributeCommand(shapeshifter, "Command.Retribute", command, command.Split(' '));
}
public void ReceiveRPC(MessageReader reader)
@@ -124,7 +124,7 @@ public class Retributionist : RoleBase
if (AmongUsClient.Instance.AmHost)
{
var command = $"/retribute {playerId}";
ChatCommands.RetributeCommand(PlayerControl.LocalPlayer, command, command.Split(' '));
ChatCommands.RetributeCommand(PlayerControl.LocalPlayer, "Command.Retribute", command, command.Split(' '));
}
else
{
-5
View File
@@ -91,11 +91,6 @@ public class Sapper : RoleBase
return PlaceBomb(shapeshifter);
}
public override bool OnCheckMurder(PlayerControl killer, PlayerControl target)
{
return false;
}
public override bool CanUseKillButton(PlayerControl pc)
{
return CanKill.GetBool();
+1 -15
View File
@@ -34,7 +34,7 @@ public class Silencer : RoleBase
public override void SetupCustomOption()
{
SetupRoleOptions(Id, TabGroup.ImpostorRoles, CustomRoles.Silencer, zeroOne: true);
SetupSingleRoleOptions(Id, TabGroup.ImpostorRoles, CustomRoles.Silencer);
SkillCooldown = new FloatOptionItem(Id + 5, "AbilityCooldown", new(2.5f, 60f, 0.5f), 30f, TabGroup.ImpostorRoles)
.SetParent(CustomRoleSpawnChances[CustomRoles.Silencer])
@@ -169,18 +169,4 @@ public class Silencer : RoleBase
ForSilencer.Clear();
PlayerIdList.ForEach(x => Utils.SendRPC(CustomRPC.SyncRoleData, x, 2));
}
public override void OnReportDeadBody()
{
if (ForSilencer.Count == 0) return;
Main.Instance.StartCoroutine(WaitForVote());
return;
System.Collections.IEnumerator WaitForVote()
{
while (MeetingHud.Instance && MeetingHud.Instance.state is not (MeetingHud.VoteStates.NotVoted or MeetingHud.VoteStates.Voted) && !GameStates.IsEnded && GameStates.InGame && !ExileController.Instance) yield return null;
if (!MeetingHud.Instance || GameStates.IsEnded || !GameStates.InGame || ExileController.Instance) yield break;
ForSilencer.ForEach(x => MeetingHud.Instance.CastVote(x, 253)); // 253 is skip vote
}
}
}
+3 -3
View File
@@ -44,14 +44,14 @@ public class Ventriloquist : RoleBase
public override void OnMeetingShapeshift(PlayerControl shapeshifter, PlayerControl target)
{
var command = $"/target {target.PlayerId}";
ChatCommands.TargetCommand(shapeshifter, command, command.Split(' '));
ChatCommands.TargetCommand(shapeshifter, "Command.Target", command, command.Split(' '));
}
public static void ReceiveRPC(MessageReader reader, PlayerControl pc)
{
int playerId = reader.ReadByte();
var command = $"/target {playerId}";
ChatCommands.TargetCommand(pc, command, command.Split(' '));
ChatCommands.TargetCommand(pc, "Command.Target", command, command.Split(' '));
}
private static void VentriloquisttOnClick(byte playerId /*, MeetingHud __instance*/)
@@ -63,7 +63,7 @@ public class Ventriloquist : RoleBase
if (AmongUsClient.Instance.AmHost)
{
var command = $"/target {playerId}";
ChatCommands.TargetCommand(PlayerControl.LocalPlayer, command, command.Split(' '));
ChatCommands.TargetCommand(PlayerControl.LocalPlayer, "Command.Target", command, command.Split(' '));
}
else
{
+4 -2
View File
@@ -109,14 +109,16 @@ public class SoulCollector : RoleBase
{
var sender = CustomRpcSender.Create("SoulCollector Post Exile", SendOption.Reliable);
sender.StartMessage();
ToExile.ToValidPlayers().ForEach(x =>
List<PlayerControl> toExile = ToExile.ToValidPlayers();
ToExile = [];
toExile.ForEach(x =>
{
Main.AllPlayerSpeed[x.PlayerId] = Main.RealOptionsData.GetFloat(FloatOptionNames.PlayerSpeedMod);
x.Exiled();
sender.StartRpc(x.NetId, RpcCalls.Exiled)
.EndRpc();
});
sender.SendMessage();
ToExile = [];
}
}
}
+2 -2
View File
@@ -77,7 +77,7 @@ public class Starspawn : RoleBase
public override void OnMeetingShapeshift(PlayerControl shapeshifter, PlayerControl target)
{
const string command = "/daybreak";
ChatCommands.DayBreakCommand(shapeshifter, command, command.Split(' '));
ChatCommands.DayBreakCommand(shapeshifter, "Command.Daybreak", command, command.Split(' '));
}
public void ReceiveRPC(MessageReader reader)
@@ -93,7 +93,7 @@ public class Starspawn : RoleBase
if (AmongUsClient.Instance.AmHost)
{
var command = $"/daybreak";
ChatCommands.DayBreakCommand(PlayerControl.LocalPlayer, command, command.Split(' '));
ChatCommands.DayBreakCommand(PlayerControl.LocalPlayer, "Command.Daybreak", command, command.Split(' '));
}
else
{
+1 -1
View File
@@ -134,7 +134,7 @@ public abstract class RoleBase : IComparable<RoleBase>
if (Imitator.PlayerIdList.Contains(pc.PlayerId))
{
string command = $"/imitate {target.PlayerId}";
ChatCommands.ImitateCommand(pc, command, command.Split(' '));
ChatCommands.ImitateCommand(pc, "Command.Imitate", command, command.Split(' '));
}
}