diff --git a/Content.Server/Chat/Systems/ChatSystem.cs b/Content.Server/Chat/Systems/ChatSystem.cs index b3128a6702..581b678b84 100644 --- a/Content.Server/Chat/Systems/ChatSystem.cs +++ b/Content.Server/Chat/Systems/ChatSystem.cs @@ -270,6 +270,12 @@ public sealed partial class ChatSystem : SharedChatSystem if (!_critLoocEnabled && _mobStateSystem.IsCritical(source)) return; + // Systems can differentiate Looc and DeadChat by type, and cancel the speak attempt if necessary. + var ev = new InGameOocMessageAttemptEvent(player, sendType); + RaiseLocalEvent(source, ref ev, true); + if (ev.Cancelled) + return; + switch (sendType) { case InGameOOCChatType.Dead: @@ -419,18 +425,18 @@ public sealed partial class ChatSystem : SharedChatSystem if (originalMessage == message) { if (name != Name(source)) - _adminLogger.Add(LogType.Chat, LogImpact.Low, $"Say from {ToPrettyString(source):user} as {name}: {originalMessage}."); + _adminLogger.Add(LogType.Chat, LogImpact.Low, $"Say from {source} as {name}: {originalMessage}."); else - _adminLogger.Add(LogType.Chat, LogImpact.Low, $"Say from {ToPrettyString(source):user}: {originalMessage}."); + _adminLogger.Add(LogType.Chat, LogImpact.Low, $"Say from {source}: {originalMessage}."); } else { if (name != Name(source)) _adminLogger.Add(LogType.Chat, LogImpact.Low, - $"Say from {ToPrettyString(source):user} as {name}, original: {originalMessage}, transformed: {message}."); + $"Say from {source} as {name}, original: {originalMessage}, transformed: {message}."); else _adminLogger.Add(LogType.Chat, LogImpact.Low, - $"Say from {ToPrettyString(source):user}, original: {originalMessage}, transformed: {message}."); + $"Say from {source}, original: {originalMessage}, transformed: {message}."); } } @@ -508,18 +514,18 @@ public sealed partial class ChatSystem : SharedChatSystem if (originalMessage == message) { if (name != Name(source)) - _adminLogger.Add(LogType.Chat, LogImpact.Low, $"Whisper from {ToPrettyString(source):user} as {name}: {originalMessage}."); + _adminLogger.Add(LogType.Chat, LogImpact.Low, $"Whisper from {source} as {name}: {originalMessage}."); else - _adminLogger.Add(LogType.Chat, LogImpact.Low, $"Whisper from {ToPrettyString(source):user}: {originalMessage}."); + _adminLogger.Add(LogType.Chat, LogImpact.Low, $"Whisper from {source}: {originalMessage}."); } else { if (name != Name(source)) _adminLogger.Add(LogType.Chat, LogImpact.Low, - $"Whisper from {ToPrettyString(source):user} as {name}, original: {originalMessage}, transformed: {message}."); + $"Whisper from {source} as {name}, original: {originalMessage}, transformed: {message}."); else _adminLogger.Add(LogType.Chat, LogImpact.Low, - $"Whisper from {ToPrettyString(source):user}, original: {originalMessage}, transformed: {message}."); + $"Whisper from {source}, original: {originalMessage}, transformed: {message}."); } } @@ -554,9 +560,9 @@ public sealed partial class ChatSystem : SharedChatSystem SendInVoiceRange(ChatChannel.Emotes, action, wrappedMessage, source, range, author); if (!hideLog) if (name != Name(source)) - _adminLogger.Add(LogType.Chat, LogImpact.Low, $"Emote from {ToPrettyString(source):user} as {name}: {action}"); + _adminLogger.Add(LogType.Chat, LogImpact.Low, $"Emote from {source} as {name}: {action}"); else - _adminLogger.Add(LogType.Chat, LogImpact.Low, $"Emote from {ToPrettyString(source):user}: {action}"); + _adminLogger.Add(LogType.Chat, LogImpact.Low, $"Emote from {source}: {action}"); } // ReSharper disable once InconsistentNaming @@ -579,7 +585,7 @@ public sealed partial class ChatSystem : SharedChatSystem ("message", FormattedMessage.EscapeText(message))); SendInVoiceRange(ChatChannel.LOOC, message, wrappedMessage, source, hideChat ? ChatTransmitRange.HideChat : ChatTransmitRange.Normal, player.UserId); - _adminLogger.Add(LogType.Chat, LogImpact.Low, $"LOOC from {player:Player}: {message}"); + _adminLogger.Add(LogType.Chat, LogImpact.Low, $"LOOC from {source}: {message}"); } private void SendDeadChat(EntityUid source, ICommonSession player, string message, bool hideChat) @@ -593,7 +599,7 @@ public sealed partial class ChatSystem : SharedChatSystem ("adminChannelName", Loc.GetString("chat-manager-admin-channel-name")), ("userName", player.Channel.UserName), ("message", FormattedMessage.EscapeText(message))); - _adminLogger.Add(LogType.Chat, LogImpact.Low, $"Admin dead chat from {player:Player}: {message}"); + _adminLogger.Add(LogType.Chat, LogImpact.Low, $"Admin dead chat from {source}: {message}"); } else { @@ -601,7 +607,7 @@ public sealed partial class ChatSystem : SharedChatSystem ("deadChannelName", Loc.GetString("chat-manager-dead-channel-name")), ("playerName", (playerName)), ("message", FormattedMessage.EscapeText(message))); - _adminLogger.Add(LogType.Chat, LogImpact.Low, $"Dead chat from {player:Player}: {message}"); + _adminLogger.Add(LogType.Chat, LogImpact.Low, $"Dead chat from {source}: {message}"); } _chatManager.ChatMessageToMany(ChatChannel.Dead, message, wrappedMessage, source, hideChat, true, clients.ToList(), author: player.UserId); diff --git a/Content.Shared/Administration/AdminFrozenSystem.cs b/Content.Shared/Administration/AdminFrozenSystem.cs index 7419137da8..ee0afb543a 100644 --- a/Content.Shared/Administration/AdminFrozenSystem.cs +++ b/Content.Shared/Administration/AdminFrozenSystem.cs @@ -1,4 +1,5 @@ using Content.Shared.ActionBlocker; +using Content.Shared.Chat; using Content.Shared.Emoting; using Content.Shared.Interaction.Events; using Content.Shared.Item; @@ -31,6 +32,8 @@ public sealed class AdminFrozenSystem : EntitySystem SubscribeLocalEvent(OnAttempt); SubscribeLocalEvent(OnEmoteAttempt); SubscribeLocalEvent(OnSpeakAttempt); + SubscribeLocalEvent(OnInGameOocMessageAttempt); + SubscribeLocalEvent(OnInGameOocMessageAttemptBroadcast); } /// @@ -56,6 +59,20 @@ public sealed class AdminFrozenSystem : EntitySystem args.Cancel(); } + private void OnInGameOocMessageAttempt(Entity ent, ref InGameOocMessageAttemptEvent args) + { + if (!ent.Comp.Muted) + return; + + // Despite Type being available, Admin Mute does not care to differentiate. If you are out, you are out. + args.Cancelled = true; + } + + private void OnInGameOocMessageAttemptBroadcast(ref InGameOocMessageAttemptEvent args) + { + //TODO Player LOOC mute/ban. Session is in the args, but where to store/check the muted state? + } + private void OnAttempt(EntityUid uid, AdminFrozenComponent component, CancellableEntityEventArgs args) { args.Cancel(); diff --git a/Content.Shared/Chat/InGameOocMessageAttemptEvent.cs b/Content.Shared/Chat/InGameOocMessageAttemptEvent.cs new file mode 100644 index 0000000000..926b4046b8 --- /dev/null +++ b/Content.Shared/Chat/InGameOocMessageAttemptEvent.cs @@ -0,0 +1,9 @@ +using Robust.Shared.Player; + +namespace Content.Shared.Chat; + +/// +/// Event fired before a player's entity speaks on LOOC or Deadchat. +/// +[ByRefEvent] +public record struct InGameOocMessageAttemptEvent(ICommonSession Session, InGameOOCChatType Type, bool Cancelled = false);