diff --git a/OpenRA.Game/Game.cs b/OpenRA.Game/Game.cs index 711dcb4479..1695325d92 100644 --- a/OpenRA.Game/Game.cs +++ b/OpenRA.Game/Game.cs @@ -83,6 +83,9 @@ namespace OpenRA static void JoinInner(OrderManager om) { + // Refresh TextNotificationsManager before the game starts. + TextNotificationsManager.Clear(); + // HACK: The shellmap World and OrderManager are owned by the main menu's WorldRenderer instead of Game. // This allows us to switch Game.OrderManager from the shellmap to the new network connection when joining // a lobby, while keeping the OrderManager that runs the shellmap intact. diff --git a/OpenRA.Game/Network/OrderManager.cs b/OpenRA.Game/Network/OrderManager.cs index 3786a5533f..37c4e11a03 100644 --- a/OpenRA.Game/Network/OrderManager.cs +++ b/OpenRA.Game/Network/OrderManager.cs @@ -51,10 +51,6 @@ namespace OpenRA.Network readonly List processClientOrders = new List(); readonly List processClientsToRemove = new List(); - readonly List notificationsCache = new List(); - - public IReadOnlyList NotificationsCache => notificationsCache; - bool disposed; bool generateSyncReport = false; int sentOrdersFrame = 0; @@ -108,7 +104,6 @@ namespace OpenRA.Network { Connection = conn; syncReport = new SyncReport(this); - AddTextNotification += CacheTextNotification; LastTickTime = new TickTime(() => SuggestedTimestep, Game.RunTime); } @@ -127,12 +122,6 @@ namespace OpenRA.Network localOrders.Add(order); } - public Action AddTextNotification = (notification) => { }; - void CacheTextNotification(TextNotification notification) - { - notificationsCache.Add(notification); - } - void SendImmediateOrders() { if (localImmediateOrders.Count != 0 && GameSaveLastFrame < NetFrameNumber) diff --git a/OpenRA.Game/TextNotificationsManager.cs b/OpenRA.Game/TextNotificationsManager.cs index 6c0a7bbb35..e709f76329 100644 --- a/OpenRA.Game/TextNotificationsManager.cs +++ b/OpenRA.Game/TextNotificationsManager.cs @@ -9,6 +9,7 @@ */ #endregion +using System.Collections.Generic; using OpenRA.Primitives; using OpenRA.Widgets; @@ -20,6 +21,8 @@ namespace OpenRA static readonly string SystemMessageLabel; public static long ChatDisabledUntil { get; internal set; } + static readonly List NotificationsCache = new List(); + public static IReadOnlyList Notifications => NotificationsCache; static TextNotificationsManager() { @@ -69,7 +72,12 @@ namespace OpenRA static void AddTextNotification(TextNotificationPool pool, int clientId, string prefix, string text, Color? prefixColor = null, Color? textColor = null) { if (IsPoolEnabled(pool)) - Game.OrderManager.AddTextNotification(new TextNotification(pool, clientId, prefix, text, prefixColor, textColor)); + { + var textNotification = new TextNotification(pool, clientId, prefix, text, prefixColor, textColor); + + NotificationsCache.Add(textNotification); + Ui.Send(textNotification); + } } static bool IsPoolEnabled(TextNotificationPool pool) @@ -82,5 +90,10 @@ namespace OpenRA (pool == TextNotificationPool.Transients && filters.HasFlag(TextNotificationPoolFilters.Transients)) || (pool == TextNotificationPool.Feedback && filters.HasFlag(TextNotificationPoolFilters.Feedback)); } + + public static void Clear() + { + NotificationsCache.Clear(); + } } } diff --git a/OpenRA.Mods.Common/Widgets/Logic/Ingame/IngameChatLogic.cs b/OpenRA.Mods.Common/Widgets/Logic/Ingame/IngameChatLogic.cs index b9764e9231..231a498856 100644 --- a/OpenRA.Mods.Common/Widgets/Logic/Ingame/IngameChatLogic.cs +++ b/OpenRA.Mods.Common/Widgets/Logic/Ingame/IngameChatLogic.cs @@ -21,9 +21,8 @@ using OpenRA.Widgets; namespace OpenRA.Mods.Common.Widgets.Logic { [ChromeLogicArgsHotkeys("OpenTeamChat", "OpenGeneralChat")] - public class IngameChatLogic : ChromeLogic + public class IngameChatLogic : ChromeLogic, INotificationHandler { - readonly OrderManager orderManager; readonly Ruleset modRules; readonly World world; @@ -47,7 +46,6 @@ namespace OpenRA.Mods.Common.Widgets.Logic [ObjectCreator.UseCtor] public IngameChatLogic(Widget widget, OrderManager orderManager, World world, ModData modData, bool isMenuChat, Dictionary logicArgs) { - this.orderManager = orderManager; modRules = modData.DefaultRules; this.isMenuChat = isMenuChat; this.world = world; @@ -209,12 +207,10 @@ namespace OpenRA.Mods.Common.Widgets.Logic chatScrollPanel.RemoveChildren(); chatScrollPanel.ScrollToBottom(); - foreach (var notification in orderManager.NotificationsCache) + foreach (var notification in TextNotificationsManager.Notifications) if (IsNotificationEligible(notification)) AddNotification(notification, true); - orderManager.AddTextNotification += AddNotificationWrapper; - chatText.IsDisabled = () => !chatEnabled || (world.IsReplay && !Game.Settings.Debug.EnableDebugCommandsInReplays); if (!isMenuChat) @@ -260,7 +256,7 @@ namespace OpenRA.Mods.Common.Widgets.Logic Ui.ResetTooltips(); } - public void AddNotificationWrapper(TextNotification notification) + void INotificationHandler.Handle(TextNotification notification) { if (!IsNotificationEligible(notification)) return; @@ -315,18 +311,6 @@ namespace OpenRA.Mods.Common.Widgets.Logic notification.Pool == TextNotificationPool.Mission; } - bool disposed = false; - protected override void Dispose(bool disposing) - { - if (!disposed) - { - orderManager.AddTextNotification -= AddNotificationWrapper; - disposed = true; - } - - base.Dispose(disposing); - } - bool IsNotificationMuted(TextNotification notification) { return Game.Settings.Game.HideReplayChat && world.IsReplay && notification.ClientId != TextNotificationsManager.SystemClientId; diff --git a/OpenRA.Mods.Common/Widgets/Logic/Ingame/IngameTransientNotificationsLogic.cs b/OpenRA.Mods.Common/Widgets/Logic/Ingame/IngameTransientNotificationsLogic.cs index fee6a14c41..5f111b838a 100644 --- a/OpenRA.Mods.Common/Widgets/Logic/Ingame/IngameTransientNotificationsLogic.cs +++ b/OpenRA.Mods.Common/Widgets/Logic/Ingame/IngameTransientNotificationsLogic.cs @@ -10,14 +10,12 @@ #endregion using System.Collections.Generic; -using OpenRA.Network; using OpenRA.Widgets; namespace OpenRA.Mods.Common.Widgets.Logic { - public class IngameTransientNotificationsLogic : ChromeLogic + public class IngameTransientNotificationsLogic : ChromeLogic, INotificationHandler { - readonly OrderManager orderManager; readonly Ruleset modRules; readonly TextNotificationsDisplayWidget displayWidget; @@ -28,22 +26,19 @@ namespace OpenRA.Mods.Common.Widgets.Logic int repetitions; [ObjectCreator.UseCtor] - public IngameTransientNotificationsLogic(Widget widget, OrderManager orderManager, ModData modData, Dictionary logicArgs) + public IngameTransientNotificationsLogic(Widget widget, ModData modData, Dictionary logicArgs) { - this.orderManager = orderManager; modRules = modData.DefaultRules; displayWidget = widget.Get("TRANSIENTS_DISPLAY"); - orderManager.AddTextNotification += AddNotificationWrapper; - if (logicArgs.TryGetValue("TransientLineSound", out var yaml)) transientLineSound = yaml.Value; else ChromeMetrics.TryGet("TransientLineSound", out transientLineSound); } - public void AddNotificationWrapper(TextNotification notification) + void INotificationHandler.Handle(TextNotification notification) { if (!IsNotificationEligible(notification)) return; @@ -83,17 +78,5 @@ namespace OpenRA.Mods.Common.Widgets.Logic { return notification.Pool == TextNotificationPool.Transients || notification.Pool == TextNotificationPool.Feedback; } - - bool disposed = false; - protected override void Dispose(bool disposing) - { - if (!disposed) - { - orderManager.AddTextNotification -= AddNotificationWrapper; - disposed = true; - } - - base.Dispose(disposing); - } } } diff --git a/OpenRA.Mods.Common/Widgets/Logic/Lobby/LobbyLogic.cs b/OpenRA.Mods.Common/Widgets/Logic/Lobby/LobbyLogic.cs index 7942b83b50..a5627d56fb 100644 --- a/OpenRA.Mods.Common/Widgets/Logic/Lobby/LobbyLogic.cs +++ b/OpenRA.Mods.Common/Widgets/Logic/Lobby/LobbyLogic.cs @@ -20,7 +20,7 @@ using OpenRA.Widgets; namespace OpenRA.Mods.Common.Widgets.Logic { - public class LobbyLogic : ChromeLogic + public class LobbyLogic : ChromeLogic, INotificationHandler { static readonly Action DoNothing = () => { }; @@ -125,7 +125,6 @@ namespace OpenRA.Mods.Common.Widgets.Logic services = modData.Manifest.Get(); - orderManager.AddTextNotification += AddChatLine; Game.LobbyInfoChanged += UpdateCurrentMap; Game.LobbyInfoChanged += UpdatePlayerList; Game.LobbyInfoChanged += UpdateDiscordStatus; @@ -493,7 +492,6 @@ namespace OpenRA.Mods.Common.Widgets.Logic if (disposing && !disposed) { disposed = true; - orderManager.AddTextNotification -= AddChatLine; Game.LobbyInfoChanged -= UpdateCurrentMap; Game.LobbyInfoChanged -= UpdatePlayerList; Game.LobbyInfoChanged -= UpdateDiscordStatus; @@ -535,7 +533,7 @@ namespace OpenRA.Mods.Common.Widgets.Logic } } - void AddChatLine(TextNotification notification) + void INotificationHandler.Handle(TextNotification notification) { var chatLine = chatTemplates[notification.Pool].Clone(); WidgetUtils.SetupTextNotification(chatLine, notification, lobbyChatPanel.Bounds.Width - lobbyChatPanel.ScrollbarWidth, true);