diff --git a/OpenRA.Mods.Common/WebServices.cs b/OpenRA.Mods.Common/WebServices.cs index 4e90e51f91..dc4344ceef 100644 --- a/OpenRA.Mods.Common/WebServices.cs +++ b/OpenRA.Mods.Common/WebServices.cs @@ -19,5 +19,6 @@ namespace OpenRA public readonly string ServerAdvertise = "http://master.openra.net/ping"; public readonly string MapRepository = "http://resource.openra.net/map/"; public readonly string GameNews = "http://master.openra.net/gamenews"; + public readonly string MPNotices = "http://master.openra.net/notices"; } } diff --git a/OpenRA.Mods.Common/Widgets/Logic/MultiplayerLogic.cs b/OpenRA.Mods.Common/Widgets/Logic/MultiplayerLogic.cs index 2d2866ced1..40853f4924 100644 --- a/OpenRA.Mods.Common/Widgets/Logic/MultiplayerLogic.cs +++ b/OpenRA.Mods.Common/Widgets/Logic/MultiplayerLogic.cs @@ -38,8 +38,11 @@ namespace OpenRA.Mods.Common.Widgets.Logic readonly ModData modData; readonly WebServices services; readonly Probe lanGameProbe; + + readonly Widget serverList; readonly ScrollItemWidget serverTemplate; readonly ScrollItemWidget headerTemplate; + readonly Widget noticeContainer; readonly Widget clientContainer; readonly ScrollPanelWidget clientList; readonly ScrollItemWidget clientTemplate, clientHeader; @@ -54,9 +57,12 @@ namespace OpenRA.Mods.Common.Widgets.Logic Action onExit; enum SearchStatus { Fetching, Failed, NoGames, Hidden } + enum NoticeType { None, Outdated, Unknown, PlaytestAvailable } + SearchStatus searchStatus = SearchStatus.Fetching; + NoticeType notice = NoticeType.None; + Download currentQuery; - Widget serverList; IEnumerable lanGameLocations; public string ProgressLabelText() @@ -91,6 +97,15 @@ namespace OpenRA.Mods.Common.Widgets.Logic headerTemplate = serverList.Get("HEADER_TEMPLATE"); serverTemplate = serverList.Get("SERVER_TEMPLATE"); + noticeContainer = widget.GetOrNull("NOTICE_CONTAINER"); + if (noticeContainer != null) + { + noticeContainer.IsVisible = () => notice != NoticeType.None; + noticeContainer.Get("OUTDATED_VERSION_LABEL").IsVisible = () => notice == NoticeType.Outdated; + noticeContainer.Get("UNKNOWN_VERSION_LABEL").IsVisible = () => notice == NoticeType.Unknown; + noticeContainer.Get("PLAYTEST_AVAILABLE_LABEL").IsVisible = () => notice == NoticeType.PlaytestAvailable; + } + joinButton = widget.Get("JOIN_BUTTON"); joinButton.IsVisible = () => currentServer != null; joinButton.IsDisabled = () => !currentServer.IsJoinable; @@ -256,6 +271,7 @@ namespace OpenRA.Mods.Common.Widgets.Logic } RefreshServerList(); + QueryNotices(); if (directConnectHost != null) { @@ -285,6 +301,48 @@ namespace OpenRA.Mods.Common.Widgets.Logic game.Spectators > 0 ? ", {0} Spectator{1}".F(game.Spectators, game.Spectators != 1 ? "s" : "") : ""); } + void QueryNotices() + { + if (noticeContainer == null) + return; + + Action onComplete = i => + { + if (i.Error != null) + return; + try + { + var data = Encoding.UTF8.GetString(i.Result); + var n = NoticeType.None; + switch (data) + { + case "outdated": n = NoticeType.Outdated; break; + case "unknown": n = NoticeType.Unknown; break; + case "playtest": n = NoticeType.PlaytestAvailable; break; + } + + if (n == NoticeType.None) + return; + + Game.RunAfterTick(() => + { + notice = n; + serverList.Bounds.Y += noticeContainer.Bounds.Height; + serverList.Bounds.Height -= noticeContainer.Bounds.Height; + }); + } + catch { } + }; + + var queryURL = services.MPNotices + "?protocol={0}&engine={1}&mod={2}&version={3}".F( + GameServer.ProtocolVersion, + Uri.EscapeUriString(Game.EngineVersion), + Uri.EscapeUriString(Game.ModData.Manifest.Id), + Uri.EscapeUriString(Game.ModData.Manifest.Metadata.Version)); + + new Download(queryURL, _ => { }, onComplete); + } + void RefreshServerList() { // Query in progress diff --git a/mods/cnc/chrome/multiplayer-browser.yaml b/mods/cnc/chrome/multiplayer-browser.yaml index 17f0f24e87..7df537e3f6 100644 --- a/mods/cnc/chrome/multiplayer-browser.yaml +++ b/mods/cnc/chrome/multiplayer-browser.yaml @@ -48,6 +48,38 @@ Container@MULTIPLAYER_PANEL: Height: 25 Text: Status Font: Bold + Container@NOTICE_CONTAINER: + X: 15 + Y: 30 + Width: 582 + Height: 19 + Children: + Background@bg: + Width: PARENT_RIGHT + Height: 20 + Background: panel-black + Children: + Label@OUTDATED_VERSION_LABEL: + X: 5 + Width: PARENT_RIGHT-10 + Height: 18 + Align: Center + Text: You are running an outdated version of OpenRA. Download the latest version from www.openra.net + Font: TinyBold + Label@UNKNOWN_VERSION_LABEL: + X: 5 + Width: PARENT_RIGHT-10 + Height: 18 + Align: Center + Text: You are running an unrecognized version of OpenRA. Download the latest version from www.openra.net + Font: TinyBold + Label@PLAYTEST_AVAILABLE_LABEL: + X: 5 + Width: PARENT_RIGHT-10 + Height: 18 + Align: Center + Text: A pre-release version of OpenRA is available for testing. Download the playtest from www.openra.net + Font: TinyBold ScrollPanel@SERVER_LIST: X: 15 Y: 30 diff --git a/mods/common/chrome/multiplayer-browser.yaml b/mods/common/chrome/multiplayer-browser.yaml index af0d470609..eedee72fbf 100644 --- a/mods/common/chrome/multiplayer-browser.yaml +++ b/mods/common/chrome/multiplayer-browser.yaml @@ -43,6 +43,34 @@ Background@MULTIPLAYER_PANEL: Height: 25 Text: Status Font: Bold + Background@NOTICE_CONTAINER: + X: 20 + Y: 67 + Width: 583 + Height: 20 + Background: dialog2 + Children: + Label@OUTDATED_VERSION_LABEL: + X: 5 + Width: PARENT_RIGHT-10 + Height: 18 + Align: Center + Text: You are running an outdated version of OpenRA. Download the latest version from www.openra.net + Font: TinyBold + Label@UNKNOWN_VERSION_LABEL: + X: 5 + Width: PARENT_RIGHT-10 + Height: 18 + Align: Center + Text: You are running an unrecognized version of OpenRA. Download the latest version from www.openra.net + Font: TinyBold + Label@PLAYTEST_AVAILABLE_LABEL: + X: 5 + Width: PARENT_RIGHT-10 + Height: 18 + Align: Center + Text: A pre-release version of OpenRA is available for testing. Download the playtest from www.openra.net + Font: TinyBold ScrollPanel@SERVER_LIST: X: 20 Y: 67