From 20f4c9988b3b747d9ca41d1a362ee5d1dc7f443c Mon Sep 17 00:00:00 2001 From: metalgearsloth <31366439+metalgearsloth@users.noreply.github.com> Date: Mon, 4 Jul 2022 16:00:51 +1000 Subject: [PATCH] Fix station announcements (#9380) * Fix station announcements Doesn't just get what's on the grid. Also made it generic so other systems can use a station filter. * bumped * a --- .../Administration/UI/AdminAnnounceEui.cs | 2 +- .../Announcements/AnnounceCommand.cs | 4 +- Content.Server/Chat/Systems/ChatSystem.cs | 12 ++-- .../CommunicationsConsoleSystem.cs | 2 +- .../GameTicking/GameTicker.RoundFlow.cs | 2 +- Content.Server/Nuke/NukeCodeSystem.cs | 2 +- Content.Server/RoundEnd/RoundEndSystem.cs | 4 +- .../Systems/ShuttleSystem.EmergencyConsole.cs | 8 +-- .../Station/Systems/StationSystem.cs | 56 ++++++++++++++++++- .../StationEvents/Events/StationEvent.cs | 4 +- 10 files changed, 72 insertions(+), 24 deletions(-) diff --git a/Content.Server/Administration/UI/AdminAnnounceEui.cs b/Content.Server/Administration/UI/AdminAnnounceEui.cs index 2a42c0ac8a..f316642a77 100644 --- a/Content.Server/Administration/UI/AdminAnnounceEui.cs +++ b/Content.Server/Administration/UI/AdminAnnounceEui.cs @@ -51,7 +51,7 @@ namespace Content.Server.Administration.UI break; // TODO: Per-station announcement support case AdminAnnounceType.Station: - _chatSystem.DispatchGlobalStationAnnouncement(doAnnounce.Announcement, doAnnounce.Announcer, colorOverride: Color.Gold); + _chatSystem.DispatchGlobalAnnouncement(doAnnounce.Announcement, doAnnounce.Announcer, colorOverride: Color.Gold); break; } diff --git a/Content.Server/Announcements/AnnounceCommand.cs b/Content.Server/Announcements/AnnounceCommand.cs index d51ea19ab0..2f5cb1c010 100644 --- a/Content.Server/Announcements/AnnounceCommand.cs +++ b/Content.Server/Announcements/AnnounceCommand.cs @@ -24,12 +24,12 @@ namespace Content.Server.Announcements if (args.Length == 1) { - chat.DispatchGlobalStationAnnouncement(args[0], colorOverride: Color.Gold); + chat.DispatchGlobalAnnouncement(args[0], colorOverride: Color.Gold); } else { var message = string.Join(' ', new ArraySegment(args, 1, args.Length-1)); - chat.DispatchGlobalStationAnnouncement(message, args[0], colorOverride: Color.Gold); + chat.DispatchGlobalAnnouncement(message, args[0], colorOverride: Color.Gold); } shell.WriteLine("Sent!"); } diff --git a/Content.Server/Chat/Systems/ChatSystem.cs b/Content.Server/Chat/Systems/ChatSystem.cs index 4c7ad5e9b0..3de90663e1 100644 --- a/Content.Server/Chat/Systems/ChatSystem.cs +++ b/Content.Server/Chat/Systems/ChatSystem.cs @@ -165,13 +165,13 @@ public sealed partial class ChatSystem : SharedChatSystem #region Announcements /// - /// Dispatches an announcement to all stations + /// Dispatches an announcement to all. /// /// The contents of the message /// The sender (Communications Console in Communications Console Announcement) /// Play the announcement sound /// Optional color for the announcement message - public void DispatchGlobalStationAnnouncement(string message, string sender = "Central Command", + public void DispatchGlobalAnnouncement(string message, string sender = "Central Command", bool playDefaultSound = true, Color? colorOverride = null) { var messageWrap = Loc.GetString("chat-manager-sender-announcement-wrap-message", ("sender", sender)); @@ -195,7 +195,6 @@ public sealed partial class ChatSystem : SharedChatSystem { var messageWrap = Loc.GetString("chat-manager-sender-announcement-wrap-message", ("sender", sender)); var station = _stationSystem.GetOwningStation(source); - var filter = Filter.Empty(); if (station == null) { @@ -205,10 +204,7 @@ public sealed partial class ChatSystem : SharedChatSystem if (!EntityManager.TryGetComponent(station, out var stationDataComp)) return; - foreach (var gridEnt in stationDataComp.Grids) - { - filter.AddInGrid(gridEnt); - } + var filter = _stationSystem.GetInStation(stationDataComp); _chatManager.ChatMessageToManyFiltered(filter, ChatChannel.Radio, message, messageWrap, source, false, colorOverride); @@ -422,7 +418,7 @@ public sealed partial class ChatSystem : SharedChatSystem private IEnumerable GetDeadChatClients() { return Filter.Empty() - .AddWhereAttachedEntity(uid => HasComp(uid)) + .AddWhereAttachedEntity(HasComp) .Recipients .Union(_adminManager.ActiveAdmins) .Select(p => p.ConnectedClient); diff --git a/Content.Server/Communications/CommunicationsConsoleSystem.cs b/Content.Server/Communications/CommunicationsConsoleSystem.cs index f36fa7f351..af270af9ab 100644 --- a/Content.Server/Communications/CommunicationsConsoleSystem.cs +++ b/Content.Server/Communications/CommunicationsConsoleSystem.cs @@ -249,7 +249,7 @@ namespace Content.Server.Communications msg += "\n" + Loc.GetString("comms-console-announcement-sent-by") + " " + author; if (comp.AnnounceGlobal) { - _chatSystem.DispatchGlobalStationAnnouncement(msg, title, colorOverride: comp.AnnouncementColor); + _chatSystem.DispatchGlobalAnnouncement(msg, title, colorOverride: comp.AnnouncementColor); return; } _chatSystem.DispatchStationAnnouncement(uid, msg, title, colorOverride: comp.AnnouncementColor); diff --git a/Content.Server/GameTicking/GameTicker.RoundFlow.cs b/Content.Server/GameTicking/GameTicker.RoundFlow.cs index 95a7dd6b9b..789d67d1fb 100644 --- a/Content.Server/GameTicking/GameTicker.RoundFlow.cs +++ b/Content.Server/GameTicking/GameTicker.RoundFlow.cs @@ -483,7 +483,7 @@ namespace Content.Server.GameTicking if (!proto.GamePresets.Contains(Preset.ID)) continue; if (proto.Message != null) - _chatSystem.DispatchGlobalStationAnnouncement(Loc.GetString(proto.Message), playDefaultSound: true); + _chatSystem.DispatchGlobalAnnouncement(Loc.GetString(proto.Message), playDefaultSound: true); if (proto.Sound != null) SoundSystem.Play(proto.Sound.GetSound(), Filter.Broadcast()); diff --git a/Content.Server/Nuke/NukeCodeSystem.cs b/Content.Server/Nuke/NukeCodeSystem.cs index 80f2a42bf8..8c478cff3e 100644 --- a/Content.Server/Nuke/NukeCodeSystem.cs +++ b/Content.Server/Nuke/NukeCodeSystem.cs @@ -80,7 +80,7 @@ namespace Content.Server.Nuke if (wasSent) { var msg = Loc.GetString("nuke-component-announcement-send-codes"); - _chatSystem.DispatchGlobalStationAnnouncement(msg, colorOverride: Color.Red); + _chatSystem.DispatchGlobalAnnouncement(msg, colorOverride: Color.Red); } return wasSent; diff --git a/Content.Server/RoundEnd/RoundEndSystem.cs b/Content.Server/RoundEnd/RoundEndSystem.cs index 46785bf928..effbbdef9a 100644 --- a/Content.Server/RoundEnd/RoundEndSystem.cs +++ b/Content.Server/RoundEnd/RoundEndSystem.cs @@ -128,7 +128,7 @@ namespace Content.Server.RoundEnd units = "eta-units-minutes"; } - _chatSystem.DispatchGlobalStationAnnouncement(Loc.GetString("round-end-system-shuttle-called-announcement", + _chatSystem.DispatchGlobalAnnouncement(Loc.GetString("round-end-system-shuttle-called-announcement", ("time", time), ("units", Loc.GetString(units))), Loc.GetString("Station"), @@ -163,7 +163,7 @@ namespace Content.Server.RoundEnd _adminLogger.Add(LogType.ShuttleRecalled, LogImpact.High, $"Shuttle recalled"); } - _chatSystem.DispatchGlobalStationAnnouncement(Loc.GetString("round-end-system-shuttle-recalled-announcement"), + _chatSystem.DispatchGlobalAnnouncement(Loc.GetString("round-end-system-shuttle-recalled-announcement"), Loc.GetString("Station"), false, colorOverride: Color.Gold); SoundSystem.Play("/Audio/Announcements/shuttlerecalled.ogg", Filter.Broadcast()); diff --git a/Content.Server/Shuttles/Systems/ShuttleSystem.EmergencyConsole.cs b/Content.Server/Shuttles/Systems/ShuttleSystem.EmergencyConsole.cs index a77582aafa..a08c899c9f 100644 --- a/Content.Server/Shuttles/Systems/ShuttleSystem.EmergencyConsole.cs +++ b/Content.Server/Shuttles/Systems/ShuttleSystem.EmergencyConsole.cs @@ -133,7 +133,7 @@ public sealed partial class ShuttleSystem if (_consoleAccumulator <= 0f) { _launchedShuttles = true; - _chatSystem.DispatchGlobalStationAnnouncement(Loc.GetString("emergency-shuttle-left", ("transitTime", $"{_transitTime:0}"))); + _chatSystem.DispatchGlobalAnnouncement(Loc.GetString("emergency-shuttle-left", ("transitTime", $"{_transitTime:0}"))); _roundEndCancelToken = new CancellationTokenSource(); Timer.Spawn((int) (_transitTime * 1000) + _bufferTime.Milliseconds, () => _roundEnd.EndRound(), _roundEndCancelToken.Token); @@ -174,7 +174,7 @@ public sealed partial class ShuttleSystem _logger.Add(LogType.EmergencyShuttle, LogImpact.High, $"Emergency shuttle early launch REPEAL by {args.Session:user}"); var remaining = component.AuthorizationsRequired - component.AuthorizedEntities.Count; - _chatSystem.DispatchGlobalStationAnnouncement(Loc.GetString("emergency-shuttle-console-auth-revoked", ("remaining", remaining))); + _chatSystem.DispatchGlobalAnnouncement(Loc.GetString("emergency-shuttle-console-auth-revoked", ("remaining", remaining))); CheckForLaunch(component); UpdateAllEmergencyConsoles(); } @@ -197,7 +197,7 @@ public sealed partial class ShuttleSystem var remaining = component.AuthorizationsRequired - component.AuthorizedEntities.Count; if (remaining > 0) - _chatSystem.DispatchGlobalStationAnnouncement( + _chatSystem.DispatchGlobalAnnouncement( Loc.GetString("emergency-shuttle-console-auth-left", ("remaining", remaining)), playDefaultSound: false, colorOverride: DangerColor); @@ -261,7 +261,7 @@ public sealed partial class ShuttleSystem _consoleAccumulator = MathF.Max(1f, MathF.Min(_consoleAccumulator, _authorizeTime)); EarlyLaunchAuthorized = true; RaiseLocalEvent(new EmergencyShuttleAuthorizedEvent()); - _chatSystem.DispatchGlobalStationAnnouncement( + _chatSystem.DispatchGlobalAnnouncement( Loc.GetString("emergency-shuttle-launch-time", ("consoleAccumulator", $"{_consoleAccumulator:0}")), playDefaultSound: false, colorOverride: DangerColor); diff --git a/Content.Server/Station/Systems/StationSystem.cs b/Content.Server/Station/Systems/StationSystem.cs index 953c5c2c59..0d5e7a2aaa 100644 --- a/Content.Server/Station/Systems/StationSystem.cs +++ b/Content.Server/Station/Systems/StationSystem.cs @@ -6,8 +6,11 @@ using Content.Server.GameTicking; using Content.Server.Station.Components; using Content.Shared.CCVar; using JetBrains.Annotations; +using Robust.Server.Player; +using Robust.Shared.Collections; using Robust.Shared.Configuration; using Robust.Shared.Map; +using Robust.Shared.Player; using Robust.Shared.Random; namespace Content.Server.Station.Systems; @@ -24,9 +27,11 @@ public sealed class StationSystem : EntitySystem [Dependency] private readonly IConfigurationManager _configurationManager = default!; [Dependency] private readonly ILogManager _logManager = default!; [Dependency] private readonly IMapManager _mapManager = default!; + [Dependency] private readonly IPlayerManager _player = default!; [Dependency] private readonly IRobustRandom _random = default!; [Dependency] private readonly ChatSystem _chatSystem = default!; [Dependency] private readonly GameTicker _gameTicker = default!; + [Dependency] private readonly SharedTransformSystem _transform = default!; private ISawmill _sawmill = default!; @@ -153,12 +158,59 @@ public sealed class StationSystem : EntitySystem #endregion Event handlers + /// + /// Retrieves a filter for everything in a particular station or near its member grids. + /// + public Filter GetInStation(StationDataComponent dataComponent, float range = 32f) + { + // Could also use circles if you wanted. + var bounds = new ValueList(dataComponent.Grids.Count); + var filter = Filter.Empty(); + var mapIds = new ValueList(); + var xformQuery = GetEntityQuery(); + + foreach (var gridUid in dataComponent.Grids) + { + if (!_mapManager.TryGetGrid(gridUid, out var grid) || + !xformQuery.TryGetComponent(gridUid, out var xform)) continue; + + var mapId = xform.MapID; + var position = _transform.GetWorldPosition(xform, xformQuery); + var bound = grid.LocalAABB.Enlarged(range).Translated(position); + + bounds.Add(bound); + if (!mapIds.Contains(mapId)) + { + mapIds.Add(grid.ParentMapId); + } + } + + foreach (var session in Filter.GetAllPlayers(_player)) + { + var entity = session.AttachedEntity; + if (entity == null || !xformQuery.TryGetComponent(entity, out var xform)) continue; + + var mapId = xform.MapID; + + if (!mapIds.Contains(mapId)) continue; + + var position = _transform.GetWorldPosition(xform, xformQuery); + + foreach (var bound in bounds) + { + if (!bound.Contains(position)) continue; + + filter.AddPlayer(session); + break; + } + } + + return filter; + } /// /// Generates a station name from the given config. /// - /// - /// public static string GenerateStationName(StationConfig config) { return config.NameGenerator is not null diff --git a/Content.Server/StationEvents/Events/StationEvent.cs b/Content.Server/StationEvents/Events/StationEvent.cs index 8218c29231..fbdec9ed98 100644 --- a/Content.Server/StationEvents/Events/StationEvent.cs +++ b/Content.Server/StationEvents/Events/StationEvent.cs @@ -148,7 +148,7 @@ namespace Content.Server.StationEvents.Events if (AnnounceEvent && StartAnnouncement != null) { var chatSystem = IoCManager.Resolve().GetEntitySystem(); - chatSystem.DispatchGlobalStationAnnouncement(StartAnnouncement, playDefaultSound: false, colorOverride: Color.Gold); + chatSystem.DispatchGlobalAnnouncement(StartAnnouncement, playDefaultSound: false, colorOverride: Color.Gold); } if (AnnounceEvent && StartAudio != null) @@ -171,7 +171,7 @@ namespace Content.Server.StationEvents.Events if (AnnounceEvent && EndAnnouncement != null) { var chatSystem = IoCManager.Resolve().GetEntitySystem(); - chatSystem.DispatchGlobalStationAnnouncement(EndAnnouncement, playDefaultSound: false, colorOverride: Color.Gold); + chatSystem.DispatchGlobalAnnouncement(EndAnnouncement, playDefaultSound: false, colorOverride: Color.Gold); } if (AnnounceEvent && EndAudio != null)