From c852cf9b8e152cba45cddae07f621c7563b30145 Mon Sep 17 00:00:00 2001 From: Dean Herbert Date: Fri, 15 Nov 2024 18:28:54 +0900 Subject: [PATCH 01/15] Remove macOS "borderless" recommendation As of SDL3, this is no longer a thing, and fullscreen should be the preferred execution mode. Probably hold off merging this until we're sure that macOS isn't broken for others in this mode (I had issues locally, such as alt-tabbing being broken sooo...) --- .../Overlays/Settings/Sections/Graphics/LayoutSettings.cs | 7 ------- 1 file changed, 7 deletions(-) diff --git a/osu.Game/Overlays/Settings/Sections/Graphics/LayoutSettings.cs b/osu.Game/Overlays/Settings/Sections/Graphics/LayoutSettings.cs index ce087f1807..b4b5e12922 100644 --- a/osu.Game/Overlays/Settings/Sections/Graphics/LayoutSettings.cs +++ b/osu.Game/Overlays/Settings/Sections/Graphics/LayoutSettings.cs @@ -269,14 +269,7 @@ namespace osu.Game.Overlays.Settings.Sections.Graphics private void updateScreenModeWarning() { if (RuntimeInfo.OS == RuntimeInfo.Platform.macOS) - { - if (windowModeDropdown.Current.Value == WindowMode.Fullscreen) - windowModeDropdown.SetNoticeText(LayoutSettingsStrings.FullscreenMacOSNote, true); - else - windowModeDropdown.ClearNoticeText(); - return; - } if (windowModeDropdown.Current.Value != WindowMode.Fullscreen) { From b4077fc8a2afa17cccfd43f9f8d8d4b507a1f55e Mon Sep 17 00:00:00 2001 From: Dean Herbert Date: Wed, 20 Nov 2024 16:28:11 +0900 Subject: [PATCH 02/15] Use `!FrameworkEnvironment.UseSDL3` instead of removing warning altogether --- .../Settings/Sections/Graphics/LayoutSettings.cs | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/osu.Game/Overlays/Settings/Sections/Graphics/LayoutSettings.cs b/osu.Game/Overlays/Settings/Sections/Graphics/LayoutSettings.cs index b4b5e12922..4362f383ee 100644 --- a/osu.Game/Overlays/Settings/Sections/Graphics/LayoutSettings.cs +++ b/osu.Game/Overlays/Settings/Sections/Graphics/LayoutSettings.cs @@ -268,8 +268,16 @@ namespace osu.Game.Overlays.Settings.Sections.Graphics private void updateScreenModeWarning() { - if (RuntimeInfo.OS == RuntimeInfo.Platform.macOS) + // Can be removed once we stop supporting SDL2. + if (!FrameworkEnvironment.UseSDL3) + { + if (windowModeDropdown.Current.Value == WindowMode.Fullscreen) + windowModeDropdown.SetNoticeText(LayoutSettingsStrings.FullscreenMacOSNote, true); + else + windowModeDropdown.ClearNoticeText(); + return; + } if (windowModeDropdown.Current.Value != WindowMode.Fullscreen) { From 945139635f99b827e405273dad54e80f2a606e3d Mon Sep 17 00:00:00 2001 From: Dean Herbert Date: Thu, 21 Nov 2024 02:23:42 +0900 Subject: [PATCH 03/15] Add failing test case --- .../Visual/Gameplay/TestScenePlayerLoader.cs | 21 ++++++++++++++++++- 1 file changed, 20 insertions(+), 1 deletion(-) diff --git a/osu.Game.Tests/Visual/Gameplay/TestScenePlayerLoader.cs b/osu.Game.Tests/Visual/Gameplay/TestScenePlayerLoader.cs index cf813cfd51..182193714b 100644 --- a/osu.Game.Tests/Visual/Gameplay/TestScenePlayerLoader.cs +++ b/osu.Game.Tests/Visual/Gameplay/TestScenePlayerLoader.cs @@ -18,6 +18,7 @@ using osu.Framework.Testing; using osu.Framework.Utils; using osu.Game.Beatmaps; using osu.Game.Configuration; +using osu.Game.Graphics.UserInterface; using osu.Game.Overlays; using osu.Game.Overlays.Notifications; using osu.Game.Rulesets.Mods; @@ -207,7 +208,25 @@ namespace osu.Game.Tests.Visual.Gameplay } [Test] - public void TestBlockLoadViaFocus() + public void TestLoadNotBlockedViaArbitraryFocus() + { + AddStep("load dummy beatmap", () => resetPlayer(false)); + AddUntilStep("wait for current", () => loader.IsCurrentScreen()); + + AddUntilStep("click settings slider", () => + { + InputManager.MoveMouseTo(loader.ChildrenOfType>().First()); + InputManager.Click(MouseButton.Left); + + return InputManager.FocusedDrawable is OsuSliderBar; + }); + + AddUntilStep("wait for load ready", () => player?.LoadState == LoadState.Ready); + AddUntilStep("loads", () => !loader.IsCurrentScreen()); + } + + [Test] + public void TestBlockLoadViaOverlayFocus() { AddStep("load dummy beatmap", () => resetPlayer(false)); AddUntilStep("wait for current", () => loader.IsCurrentScreen()); From ae98f63b511870c11aad3d4955a1a5454a0aad58 Mon Sep 17 00:00:00 2001 From: Dean Herbert Date: Thu, 21 Nov 2024 02:23:56 +0900 Subject: [PATCH 04/15] Fix beatmap load not continuing when when settings slider is focused Regressed with recent sliderbar focus changes. Closes #30716. --- osu.Game/Screens/Play/PlayerLoader.cs | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/osu.Game/Screens/Play/PlayerLoader.cs b/osu.Game/Screens/Play/PlayerLoader.cs index aedc268d70..3e36c630db 100644 --- a/osu.Game/Screens/Play/PlayerLoader.cs +++ b/osu.Game/Screens/Play/PlayerLoader.cs @@ -122,7 +122,9 @@ namespace osu.Game.Screens.Play // not ready if the user is dragging a slider or otherwise. && (inputManager.DraggedDrawable == null || inputManager.DraggedDrawable is OsuLogo) // not ready if a focused overlay is visible, like settings. - && inputManager.FocusedDrawable == null; + && inputManager.FocusedDrawable is not OsuFocusedOverlayContainer + // or if a child of a focused overlay is focused, like settings' search textbox. + && inputManager.FocusedDrawable?.FindClosestParent() == null; private readonly Func createPlayer; From 033b7c17d556d390a55db99228705cdb16b4b0bf Mon Sep 17 00:00:00 2001 From: Dean Herbert Date: Thu, 21 Nov 2024 18:13:00 +0900 Subject: [PATCH 05/15] Add back macOS precheck --- osu.Game/Overlays/Settings/Sections/Graphics/LayoutSettings.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/osu.Game/Overlays/Settings/Sections/Graphics/LayoutSettings.cs b/osu.Game/Overlays/Settings/Sections/Graphics/LayoutSettings.cs index 4362f383ee..f40a4c941f 100644 --- a/osu.Game/Overlays/Settings/Sections/Graphics/LayoutSettings.cs +++ b/osu.Game/Overlays/Settings/Sections/Graphics/LayoutSettings.cs @@ -269,7 +269,7 @@ namespace osu.Game.Overlays.Settings.Sections.Graphics private void updateScreenModeWarning() { // Can be removed once we stop supporting SDL2. - if (!FrameworkEnvironment.UseSDL3) + if (RuntimeInfo.OS == RuntimeInfo.Platform.macOS && !FrameworkEnvironment.UseSDL3) { if (windowModeDropdown.Current.Value == WindowMode.Fullscreen) windowModeDropdown.SetNoticeText(LayoutSettingsStrings.FullscreenMacOSNote, true); From f738fb2a89e2ceffa9b1cb6b5cde67b3d2f33202 Mon Sep 17 00:00:00 2001 From: Dan Balasescu Date: Thu, 21 Nov 2024 23:48:04 +0900 Subject: [PATCH 06/15] Populate rooms as soon as they're joined --- osu.Game/Online/Rooms/JoinRoomRequest.cs | 2 +- osu.Game/Screens/OnlinePlay/Components/RoomManager.cs | 6 +++++- 2 files changed, 6 insertions(+), 2 deletions(-) diff --git a/osu.Game/Online/Rooms/JoinRoomRequest.cs b/osu.Game/Online/Rooms/JoinRoomRequest.cs index 2ceb37fc01..dfc7a53fb2 100644 --- a/osu.Game/Online/Rooms/JoinRoomRequest.cs +++ b/osu.Game/Online/Rooms/JoinRoomRequest.cs @@ -7,7 +7,7 @@ using osu.Game.Online.API; namespace osu.Game.Online.Rooms { - public class JoinRoomRequest : APIRequest + public class JoinRoomRequest : APIRequest { public readonly Room Room; public readonly string? Password; diff --git a/osu.Game/Screens/OnlinePlay/Components/RoomManager.cs b/osu.Game/Screens/OnlinePlay/Components/RoomManager.cs index ca42e98e3c..73f980f0a3 100644 --- a/osu.Game/Screens/OnlinePlay/Components/RoomManager.cs +++ b/osu.Game/Screens/OnlinePlay/Components/RoomManager.cs @@ -72,9 +72,13 @@ namespace osu.Game.Screens.OnlinePlay.Components currentJoinRoomRequest?.Cancel(); currentJoinRoomRequest = new JoinRoomRequest(room, password); - currentJoinRoomRequest.Success += () => + currentJoinRoomRequest.Success += result => { joinedRoom.Value = room; + + AddOrUpdateRoom(result); + room.CopyFrom(result); // Also copy back to the source model, since this is likely to have been stored elsewhere. + onSuccess?.Invoke(room); }; From 2a7266cb233343ee71ebb4a1104dad4edac74ab5 Mon Sep 17 00:00:00 2001 From: Dan Balasescu Date: Fri, 22 Nov 2024 01:26:35 +0900 Subject: [PATCH 07/15] Fix tests --- osu.Game/Tests/Visual/OnlinePlay/TestRoomRequestsHandler.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/osu.Game/Tests/Visual/OnlinePlay/TestRoomRequestsHandler.cs b/osu.Game/Tests/Visual/OnlinePlay/TestRoomRequestsHandler.cs index 224bb90c8c..c9149bda22 100644 --- a/osu.Game/Tests/Visual/OnlinePlay/TestRoomRequestsHandler.cs +++ b/osu.Game/Tests/Visual/OnlinePlay/TestRoomRequestsHandler.cs @@ -71,7 +71,7 @@ namespace osu.Game.Tests.Visual.OnlinePlay return true; } - joinRoomRequest.TriggerSuccess(); + joinRoomRequest.TriggerSuccess(createResponseRoom(room, true)); return true; } From e59ac9e7c8e7af67e955c82865c5b422e21c8964 Mon Sep 17 00:00:00 2001 From: Dan Balasescu Date: Fri, 22 Nov 2024 17:19:26 +0900 Subject: [PATCH 08/15] No longer remove expired playlist items from `Room` model --- osu.Game/Online/Rooms/Room.cs | 11 ----------- .../OnlinePlay/Components/ListingPollingComponent.cs | 3 --- .../Components/SelectionPollingComponent.cs | 1 - 3 files changed, 15 deletions(-) diff --git a/osu.Game/Online/Rooms/Room.cs b/osu.Game/Online/Rooms/Room.cs index 486f70c0ed..729074c5b6 100644 --- a/osu.Game/Online/Rooms/Room.cs +++ b/osu.Game/Online/Rooms/Room.cs @@ -388,21 +388,10 @@ namespace osu.Game.Online.Rooms CurrentPlaylistItem = other.CurrentPlaylistItem; AutoSkip = other.AutoSkip; - other.RemoveExpiredPlaylistItems(); - Playlist = other.Playlist; RecentParticipants = other.RecentParticipants; } - public void RemoveExpiredPlaylistItems() - { - // Todo: This is not the best way/place to do this, but the intention is to display all playlist items when the room has ended, - // and display only the non-expired playlist items while the room is still active. In order to achieve this, all expired items are removed from the source Room. - // More refactoring is required before this can be done locally instead - DrawableRoomPlaylist is currently directly bound to the playlist to display items in the room. - if (Status is not RoomStatusEnded) - Playlist = Playlist.Where(i => !i.Expired).ToArray(); - } - [JsonObject(MemberSerialization.OptIn)] public class RoomPlaylistItemStats { diff --git a/osu.Game/Screens/OnlinePlay/Components/ListingPollingComponent.cs b/osu.Game/Screens/OnlinePlay/Components/ListingPollingComponent.cs index b10ce8ed1b..b213d424df 100644 --- a/osu.Game/Screens/OnlinePlay/Components/ListingPollingComponent.cs +++ b/osu.Game/Screens/OnlinePlay/Components/ListingPollingComponent.cs @@ -60,10 +60,7 @@ namespace osu.Game.Screens.OnlinePlay.Components } foreach (var incoming in result) - { - incoming.RemoveExpiredPlaylistItems(); RoomManager.AddOrUpdateRoom(incoming); - } initialRoomsReceived.Value = true; tcs.SetResult(true); diff --git a/osu.Game/Screens/OnlinePlay/Components/SelectionPollingComponent.cs b/osu.Game/Screens/OnlinePlay/Components/SelectionPollingComponent.cs index 8b80228ae1..7cee8b3546 100644 --- a/osu.Game/Screens/OnlinePlay/Components/SelectionPollingComponent.cs +++ b/osu.Game/Screens/OnlinePlay/Components/SelectionPollingComponent.cs @@ -36,7 +36,6 @@ namespace osu.Game.Screens.OnlinePlay.Components req.Success += result => { - result.RemoveExpiredPlaylistItems(); RoomManager.AddOrUpdateRoom(result); tcs.SetResult(true); }; From 39504c348dded475b64b6dbdb88b7abd6a7a1941 Mon Sep 17 00:00:00 2001 From: Dan Balasescu Date: Fri, 22 Nov 2024 17:22:30 +0900 Subject: [PATCH 09/15] Cleanup `CopyFrom()` method Though the code appears slightly different, it should be semantically equivalent. APIUser equality is implemented on `Id` and `Host` should never transition from non-null to null. --- osu.Game/Online/Rooms/Room.cs | 7 +------ 1 file changed, 1 insertion(+), 6 deletions(-) diff --git a/osu.Game/Online/Rooms/Room.cs b/osu.Game/Online/Rooms/Room.cs index 729074c5b6..e1813c7e4e 100644 --- a/osu.Game/Online/Rooms/Room.cs +++ b/osu.Game/Online/Rooms/Room.cs @@ -366,12 +366,8 @@ namespace osu.Game.Online.Rooms { RoomID = other.RoomID; Name = other.Name; - Category = other.Category; - - if (other.Host != null && Host?.Id != other.Host.Id) - Host = other.Host; - + Host = other.Host; ChannelId = other.ChannelId; Status = other.Status; Availability = other.Availability; @@ -387,7 +383,6 @@ namespace osu.Game.Online.Rooms PlaylistItemStats = other.PlaylistItemStats; CurrentPlaylistItem = other.CurrentPlaylistItem; AutoSkip = other.AutoSkip; - Playlist = other.Playlist; RecentParticipants = other.RecentParticipants; } From 04ed954387ce19c909940043861ef6bb83bfef27 Mon Sep 17 00:00:00 2001 From: Dean Herbert Date: Fri, 22 Nov 2024 18:17:53 +0900 Subject: [PATCH 10/15] Fix song ticker having very bad contrast against bright backgrounds Closes #30814. --- osu.Game/Screens/Menu/SongTicker.cs | 70 ++++++++++++++++++++++------- 1 file changed, 54 insertions(+), 16 deletions(-) diff --git a/osu.Game/Screens/Menu/SongTicker.cs b/osu.Game/Screens/Menu/SongTicker.cs index 3bdc0efe19..24d3e1a92c 100644 --- a/osu.Game/Screens/Menu/SongTicker.cs +++ b/osu.Game/Screens/Menu/SongTicker.cs @@ -8,8 +8,12 @@ using osu.Game.Graphics.Sprites; using osuTK; using osu.Game.Graphics; using osu.Framework.Bindables; +using osu.Framework.Extensions.Color4Extensions; +using osu.Framework.Graphics.Effects; +using osu.Framework.Graphics.Shapes; using osu.Framework.Localisation; using osu.Game.Beatmaps; +using osuTK.Graphics; namespace osu.Game.Screens.Menu { @@ -27,26 +31,60 @@ namespace osu.Game.Screens.Menu public SongTicker() { AutoSizeAxes = Axes.Both; - Child = new FillFlowContainer + InternalChildren = new Drawable[] { - AutoSizeAxes = Axes.Both, - Direction = FillDirection.Vertical, - Spacing = new Vector2(0, 3), - Children = new Drawable[] + new Container { - title = new OsuSpriteText + Anchor = Anchor.TopRight, + Origin = Anchor.TopRight, + Position = new Vector2(5, -5), + Padding = new MarginPadding(-5), + RelativeSizeAxes = Axes.Both, + Children = new Drawable[] { - Anchor = Anchor.TopRight, - Origin = Anchor.TopRight, - Font = OsuFont.GetFont(size: 24, weight: FontWeight.Light, italics: true) - }, - artist = new OsuSpriteText - { - Anchor = Anchor.TopRight, - Origin = Anchor.TopRight, - Font = OsuFont.GetFont(size: 16) + new CircularContainer + { + RelativeSizeAxes = Axes.Both, + Masking = true, + EdgeEffect = new EdgeEffectParameters + { + Radius = 75, + Type = EdgeEffectType.Shadow, + Colour = OsuColour.Gray(0.04f).Opacity(0.3f), + }, + Children = new Drawable[] + { + new Box + { + RelativeSizeAxes = Axes.Both, + AlwaysPresent = true, + Alpha = 0, + }, + } + }, } - } + }, + new FillFlowContainer + { + AutoSizeAxes = Axes.Both, + Direction = FillDirection.Vertical, + Spacing = new Vector2(0, 3), + Children = new Drawable[] + { + title = new OsuSpriteText + { + Anchor = Anchor.TopRight, + Origin = Anchor.TopRight, + Font = OsuFont.GetFont(size: 24, weight: FontWeight.Light, italics: true) + }, + artist = new OsuSpriteText + { + Anchor = Anchor.TopRight, + Origin = Anchor.TopRight, + Font = OsuFont.GetFont(size: 16) + } + } + }, }; } From 2f45ebeec84ad365e8a09e27c329746171575731 Mon Sep 17 00:00:00 2001 From: Salman Alshamrani Date: Sat, 23 Nov 2024 20:13:57 -0500 Subject: [PATCH 11/15] Remove using directive --- osu.Game/Screens/Menu/SongTicker.cs | 1 - 1 file changed, 1 deletion(-) diff --git a/osu.Game/Screens/Menu/SongTicker.cs b/osu.Game/Screens/Menu/SongTicker.cs index 24d3e1a92c..3aac365eee 100644 --- a/osu.Game/Screens/Menu/SongTicker.cs +++ b/osu.Game/Screens/Menu/SongTicker.cs @@ -13,7 +13,6 @@ using osu.Framework.Graphics.Effects; using osu.Framework.Graphics.Shapes; using osu.Framework.Localisation; using osu.Game.Beatmaps; -using osuTK.Graphics; namespace osu.Game.Screens.Menu { From 2f096f71d3b824d81148b1ed04a28c6c2ece217f Mon Sep 17 00:00:00 2001 From: SupDos <6813986+SupDos@users.noreply.github.com> Date: Sun, 24 Nov 2024 02:34:30 +0100 Subject: [PATCH 12/15] Remove FPS shortcut tip --- osu.Game/Screens/Menu/MenuTip.cs | 1 - 1 file changed, 1 deletion(-) diff --git a/osu.Game/Screens/Menu/MenuTip.cs b/osu.Game/Screens/Menu/MenuTip.cs index da349373c3..58eeb7e82d 100644 --- a/osu.Game/Screens/Menu/MenuTip.cs +++ b/osu.Game/Screens/Menu/MenuTip.cs @@ -118,7 +118,6 @@ namespace osu.Game.Screens.Menu "You can create mod presets to make toggling your favorite mod combinations easier!", "Many mods have customisation settings that drastically change how they function. Click the Mod Customisation button in mod select to view settings!", "Press Ctrl-Shift-R to switch to a random skin!", - "Press Ctrl-Shift-F to toggle the FPS Counter. But make sure not to pay too much attention to it!", "While watching a replay, press Ctrl-H to toggle replay settings!", "You can easily copy the mods from scores on a leaderboard by right-clicking on them!", "Ctrl-Enter at song select will start a beatmap in autoplay mode!" From 8f5d513d461affec8f3812beb18136d3228d08d4 Mon Sep 17 00:00:00 2001 From: Salman Alshamrani Date: Sat, 23 Nov 2024 22:16:11 -0500 Subject: [PATCH 13/15] Fix room auto start duration setting applied to the wrong component --- .../Multiplayer/Match/MultiplayerMatchSettingsOverlay.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/osu.Game/Screens/OnlinePlay/Multiplayer/Match/MultiplayerMatchSettingsOverlay.cs b/osu.Game/Screens/OnlinePlay/Multiplayer/Match/MultiplayerMatchSettingsOverlay.cs index 1dbef079d4..79617f172c 100644 --- a/osu.Game/Screens/OnlinePlay/Multiplayer/Match/MultiplayerMatchSettingsOverlay.cs +++ b/osu.Game/Screens/OnlinePlay/Multiplayer/Match/MultiplayerMatchSettingsOverlay.cs @@ -438,7 +438,7 @@ namespace osu.Game.Screens.OnlinePlay.Multiplayer.Match => MaxParticipantsField.Text = room.MaxParticipants?.ToString(); private void updateRoomAutoStartDuration() - => typeLabel.Text = room.AutoStartDuration.GetLocalisableDescription(); + => startModeDropdown.Current.Value = (StartMode)room.AutoStartDuration.TotalSeconds; private void updateRoomPlaylist() => drawablePlaylist.Items.ReplaceRange(0, drawablePlaylist.Items.Count, room.Playlist); From f3155bfc7d83029e9170562598c0dd6ec342f54c Mon Sep 17 00:00:00 2001 From: Salman Alshamrani Date: Sun, 24 Nov 2024 04:24:31 -0500 Subject: [PATCH 14/15] Fix pause shortcut on multiplayer not delayed --- osu.Game/Screens/Play/HUD/HoldForMenuButton.cs | 16 ++++++++++++++-- 1 file changed, 14 insertions(+), 2 deletions(-) diff --git a/osu.Game/Screens/Play/HUD/HoldForMenuButton.cs b/osu.Game/Screens/Play/HUD/HoldForMenuButton.cs index 806985e19d..5d3d5774d0 100644 --- a/osu.Game/Screens/Play/HUD/HoldForMenuButton.cs +++ b/osu.Game/Screens/Play/HUD/HoldForMenuButton.cs @@ -299,7 +299,13 @@ namespace osu.Game.Screens.Play.HUD { case GlobalAction.Back: if (!pendingAnimation) - Confirm(); + { + if (IsDangerousAction) + BeginConfirm(); + else + Confirm(); + } + return true; case GlobalAction.PauseGameplay: @@ -307,7 +313,13 @@ namespace osu.Game.Screens.Play.HUD if (ReplayLoaded.Value) return false; if (!pendingAnimation) - Confirm(); + { + if (IsDangerousAction) + BeginConfirm(); + else + Confirm(); + } + return true; } From 6d0d7f3e759fac5d5468089d79f0832730ed1088 Mon Sep 17 00:00:00 2001 From: Salman Alshamrani Date: Sun, 24 Nov 2024 04:45:48 -0500 Subject: [PATCH 15/15] Don't play fail animation if restarting on failure --- osu.Game/Screens/Play/Player.cs | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/osu.Game/Screens/Play/Player.cs b/osu.Game/Screens/Play/Player.cs index e9722350bd..2d1f602832 100644 --- a/osu.Game/Screens/Play/Player.cs +++ b/osu.Game/Screens/Play/Player.cs @@ -976,7 +976,9 @@ namespace osu.Game.Screens.Play if (PauseOverlay.State.Value == Visibility.Visible) PauseOverlay.Hide(); - failAnimationContainer.Start(); + bool restartOnFail = GameplayState.Mods.OfType().Any(m => m.RestartOnFail); + if (!restartOnFail) + failAnimationContainer.Start(); // Failures can be triggered either by a judgement, or by a mod. // @@ -990,7 +992,7 @@ namespace osu.Game.Screens.Play ScoreProcessor.FailScore(Score.ScoreInfo); OnFail(); - if (GameplayState.Mods.OfType().Any(m => m.RestartOnFail)) + if (restartOnFail) Restart(true); }); }