From 8928aa6d92990ce761c205e80ac3c20b1a4feffe Mon Sep 17 00:00:00 2001 From: Dean Herbert Date: Fri, 30 Oct 2020 14:19:40 +0900 Subject: [PATCH 1/3] Add key binding to show HUD while held --- .../Input/Bindings/GlobalActionContainer.cs | 4 +++ osu.Game/Screens/Play/HUDOverlay.cs | 36 ++++++++++++++++++- 2 files changed, 39 insertions(+), 1 deletion(-) diff --git a/osu.Game/Input/Bindings/GlobalActionContainer.cs b/osu.Game/Input/Bindings/GlobalActionContainer.cs index 41be4cfcc3..3de4bb1f9d 100644 --- a/osu.Game/Input/Bindings/GlobalActionContainer.cs +++ b/osu.Game/Input/Bindings/GlobalActionContainer.cs @@ -67,6 +67,7 @@ namespace osu.Game.Input.Bindings new KeyBinding(new[] { InputKey.Control, InputKey.Plus }, GlobalAction.IncreaseScrollSpeed), new KeyBinding(new[] { InputKey.Control, InputKey.Minus }, GlobalAction.DecreaseScrollSpeed), new KeyBinding(InputKey.MouseMiddle, GlobalAction.PauseGameplay), + new KeyBinding(InputKey.Control, GlobalAction.HoldForHUD), }; public IEnumerable AudioControlKeyBindings => new[] @@ -187,5 +188,8 @@ namespace osu.Game.Input.Bindings [Description("Timing Mode")] EditorTimingMode, + + [Description("Hold for HUD")] + HoldForHUD, } } diff --git a/osu.Game/Screens/Play/HUDOverlay.cs b/osu.Game/Screens/Play/HUDOverlay.cs index b047d44f8a..c38c2ee5f7 100644 --- a/osu.Game/Screens/Play/HUDOverlay.cs +++ b/osu.Game/Screens/Play/HUDOverlay.cs @@ -8,8 +8,10 @@ using osu.Framework.Bindables; using osu.Framework.Extensions.IEnumerableExtensions; using osu.Framework.Graphics; using osu.Framework.Graphics.Containers; +using osu.Framework.Input.Bindings; using osu.Framework.Input.Events; using osu.Game.Configuration; +using osu.Game.Input.Bindings; using osu.Game.Overlays; using osu.Game.Overlays.Notifications; using osu.Game.Rulesets.Mods; @@ -22,7 +24,7 @@ using osuTK.Input; namespace osu.Game.Screens.Play { [Cached] - public class HUDOverlay : Container + public class HUDOverlay : Container, IKeyBindingHandler { public const float FADE_DURATION = 400; @@ -67,6 +69,8 @@ namespace osu.Game.Screens.Play internal readonly IBindable IsBreakTime = new Bindable(); + private bool holdingForHUD; + private IEnumerable hideTargets => new Drawable[] { visibilityContainer, KeyCounter }; public HUDOverlay(ScoreProcessor scoreProcessor, HealthProcessor healthProcessor, DrawableRuleset drawableRuleset, IReadOnlyList mods) @@ -217,6 +221,12 @@ namespace osu.Game.Screens.Play if (ShowHud.Disabled) return; + if (holdingForHUD) + { + ShowHud.Value = true; + return; + } + switch (configVisibilityMode.Value) { case HUDVisibilityMode.Never: @@ -351,5 +361,29 @@ namespace osu.Game.Screens.Play HealthDisplay?.BindHealthProcessor(processor); FailingLayer?.BindHealthProcessor(processor); } + + public bool OnPressed(GlobalAction action) + { + switch (action) + { + case GlobalAction.HoldForHUD: + holdingForHUD = true; + updateVisibility(); + return true; + } + + return false; + } + + public void OnReleased(GlobalAction action) + { + switch (action) + { + case GlobalAction.HoldForHUD: + holdingForHUD = false; + updateVisibility(); + break; + } + } } } From bd7871d9f511b09ddd224759e3b9365f043c27d4 Mon Sep 17 00:00:00 2001 From: Dean Herbert Date: Fri, 30 Oct 2020 14:20:00 +0900 Subject: [PATCH 2/3] Update test scene to be non-skinnable (and add test covering momentary display) --- .../Visual/Gameplay/TestSceneHUDOverlay.cs | 66 ++++++++++--------- 1 file changed, 34 insertions(+), 32 deletions(-) diff --git a/osu.Game.Tests/Visual/Gameplay/TestSceneHUDOverlay.cs b/osu.Game.Tests/Visual/Gameplay/TestSceneHUDOverlay.cs index 6ec673704c..136c9e191d 100644 --- a/osu.Game.Tests/Visual/Gameplay/TestSceneHUDOverlay.cs +++ b/osu.Game.Tests/Visual/Gameplay/TestSceneHUDOverlay.cs @@ -2,29 +2,23 @@ // See the LICENCE file in the repository root for full licence text. using System; -using System.Collections.Generic; using System.Linq; using NUnit.Framework; using osu.Framework.Allocation; -using osu.Framework.Extensions.IEnumerableExtensions; using osu.Framework.Graphics; using osu.Framework.Graphics.Containers; using osu.Framework.Testing; using osu.Game.Configuration; -using osu.Game.Rulesets; using osu.Game.Rulesets.Mods; -using osu.Game.Rulesets.Osu; using osu.Game.Screens.Play; using osuTK.Input; namespace osu.Game.Tests.Visual.Gameplay { - public class TestSceneHUDOverlay : SkinnableTestScene + public class TestSceneHUDOverlay : OsuManualInputManagerTestScene { private HUDOverlay hudOverlay; - private IEnumerable hudOverlays => CreatedDrawables.OfType(); - // best way to check without exposing. private Drawable hideTarget => hudOverlay.KeyCounter; private FillFlowContainer keyCounterFlow => hudOverlay.KeyCounter.ChildrenOfType>().First(); @@ -37,17 +31,9 @@ namespace osu.Game.Tests.Visual.Gameplay { createNew(); - AddRepeatStep("increase combo", () => - { - foreach (var hud in hudOverlays) - hud.ComboCounter.Current.Value++; - }, 10); + AddRepeatStep("increase combo", () => { hudOverlay.ComboCounter.Current.Value++; }, 10); - AddStep("reset combo", () => - { - foreach (var hud in hudOverlays) - hud.ComboCounter.Current.Value = 0; - }); + AddStep("reset combo", () => { hudOverlay.ComboCounter.Current.Value = 0; }); } [Test] @@ -77,7 +63,7 @@ namespace osu.Game.Tests.Visual.Gameplay { createNew(); - AddStep("set showhud false", () => hudOverlays.ForEach(h => h.ShowHud.Value = false)); + AddStep("set showhud false", () => hudOverlay.ShowHud.Value = false); AddUntilStep("hidetarget is hidden", () => !hideTarget.IsPresent); AddAssert("pause button is still visible", () => hudOverlay.HoldToQuit.IsPresent); @@ -86,6 +72,27 @@ namespace osu.Game.Tests.Visual.Gameplay AddAssert("key counter flow not affected", () => keyCounterFlow.IsPresent); } + [Test] + public void TestMomentaryShowHUD() + { + createNew(); + + HUDVisibilityMode originalConfigValue = HUDVisibilityMode.HideDuringBreaks; + AddStep("get original config value", () => originalConfigValue = config.Get(OsuSetting.HUDVisibilityMode)); + + AddStep("set hud to never show", () => config.Set(OsuSetting.HUDVisibilityMode, HUDVisibilityMode.Never)); + + AddUntilStep("wait for fade", () => !hideTarget.IsPresent); + + AddStep("trigger momentary show", () => InputManager.PressKey(Key.ControlLeft)); + AddUntilStep("wait for visible", () => hideTarget.IsPresent); + + AddStep("stop trigering", () => InputManager.ReleaseKey(Key.ControlLeft)); + AddUntilStep("wait for fade", () => !hideTarget.IsPresent); + + AddStep("set original config value", () => config.Set(OsuSetting.HUDVisibilityMode, originalConfigValue)); + } + [Test] public void TestExternalHideDoesntAffectConfig() { @@ -113,14 +120,14 @@ namespace osu.Game.Tests.Visual.Gameplay AddStep("set keycounter visible false", () => { config.Set(OsuSetting.KeyOverlay, false); - hudOverlays.ForEach(h => h.KeyCounter.AlwaysVisible.Value = false); + hudOverlay.KeyCounter.AlwaysVisible.Value = false; }); - AddStep("set showhud false", () => hudOverlays.ForEach(h => h.ShowHud.Value = false)); + AddStep("set showhud false", () => hudOverlay.ShowHud.Value = false); AddUntilStep("hidetarget is hidden", () => !hideTarget.IsPresent); AddAssert("key counters hidden", () => !keyCounterFlow.IsPresent); - AddStep("set showhud true", () => hudOverlays.ForEach(h => h.ShowHud.Value = true)); + AddStep("set showhud true", () => hudOverlay.ShowHud.Value = true); AddUntilStep("hidetarget is visible", () => hideTarget.IsPresent); AddAssert("key counters still hidden", () => !keyCounterFlow.IsPresent); @@ -131,22 +138,17 @@ namespace osu.Game.Tests.Visual.Gameplay { AddStep("create overlay", () => { - SetContents(() => - { - hudOverlay = new HUDOverlay(null, null, null, Array.Empty()); + hudOverlay = new HUDOverlay(null, null, null, Array.Empty()); - // Add any key just to display the key counter visually. - hudOverlay.KeyCounter.Add(new KeyCounterKeyboard(Key.Space)); + // Add any key just to display the key counter visually. + hudOverlay.KeyCounter.Add(new KeyCounterKeyboard(Key.Space)); - hudOverlay.ComboCounter.Current.Value = 1; + hudOverlay.ComboCounter.Current.Value = 1; - action?.Invoke(hudOverlay); + action?.Invoke(hudOverlay); - return hudOverlay; - }); + Child = hudOverlay; }); } - - protected override Ruleset CreateRulesetForSkinProvider() => new OsuRuleset(); } } From 984a243eff796505ee9f2ca6e85ae2a00233e3a4 Mon Sep 17 00:00:00 2001 From: Dean Herbert Date: Fri, 30 Oct 2020 14:23:24 +0900 Subject: [PATCH 3/3] Add skinnable test scene for HUD overlay --- .../Gameplay/TestSceneSkinnableHUDOverlay.cs | 99 +++++++++++++++++++ 1 file changed, 99 insertions(+) create mode 100644 osu.Game.Tests/Visual/Gameplay/TestSceneSkinnableHUDOverlay.cs diff --git a/osu.Game.Tests/Visual/Gameplay/TestSceneSkinnableHUDOverlay.cs b/osu.Game.Tests/Visual/Gameplay/TestSceneSkinnableHUDOverlay.cs new file mode 100644 index 0000000000..fec1610160 --- /dev/null +++ b/osu.Game.Tests/Visual/Gameplay/TestSceneSkinnableHUDOverlay.cs @@ -0,0 +1,99 @@ +// Copyright (c) ppy Pty Ltd . Licensed under the MIT Licence. +// See the LICENCE file in the repository root for full licence text. + +using System; +using System.Collections.Generic; +using System.Linq; +using NUnit.Framework; +using osu.Framework.Allocation; +using osu.Framework.Extensions.IEnumerableExtensions; +using osu.Framework.Graphics; +using osu.Framework.Graphics.Containers; +using osu.Framework.Testing; +using osu.Game.Configuration; +using osu.Game.Rulesets; +using osu.Game.Rulesets.Mods; +using osu.Game.Rulesets.Osu; +using osu.Game.Screens.Play; +using osuTK.Input; + +namespace osu.Game.Tests.Visual.Gameplay +{ + public class TestSceneSkinnableHUDOverlay : SkinnableTestScene + { + private HUDOverlay hudOverlay; + + private IEnumerable hudOverlays => CreatedDrawables.OfType(); + + // best way to check without exposing. + private Drawable hideTarget => hudOverlay.KeyCounter; + private FillFlowContainer keyCounterFlow => hudOverlay.KeyCounter.ChildrenOfType>().First(); + + [Resolved] + private OsuConfigManager config { get; set; } + + [Test] + public void TestComboCounterIncrementing() + { + createNew(); + + AddRepeatStep("increase combo", () => + { + foreach (var hud in hudOverlays) + hud.ComboCounter.Current.Value++; + }, 10); + + AddStep("reset combo", () => + { + foreach (var hud in hudOverlays) + hud.ComboCounter.Current.Value = 0; + }); + } + + [Test] + public void TestFadesInOnLoadComplete() + { + float? initialAlpha = null; + + createNew(h => h.OnLoadComplete += _ => initialAlpha = hideTarget.Alpha); + AddUntilStep("wait for load", () => hudOverlay.IsAlive); + AddAssert("initial alpha was less than 1", () => initialAlpha < 1); + } + + [Test] + public void TestHideExternally() + { + createNew(); + + AddStep("set showhud false", () => hudOverlays.ForEach(h => h.ShowHud.Value = false)); + + AddUntilStep("hidetarget is hidden", () => !hideTarget.IsPresent); + AddAssert("pause button is still visible", () => hudOverlay.HoldToQuit.IsPresent); + + // Key counter flow container should not be affected by this, only the key counter display will be hidden as checked above. + AddAssert("key counter flow not affected", () => keyCounterFlow.IsPresent); + } + + private void createNew(Action action = null) + { + AddStep("create overlay", () => + { + SetContents(() => + { + hudOverlay = new HUDOverlay(null, null, null, Array.Empty()); + + // Add any key just to display the key counter visually. + hudOverlay.KeyCounter.Add(new KeyCounterKeyboard(Key.Space)); + + hudOverlay.ComboCounter.Current.Value = 1; + + action?.Invoke(hudOverlay); + + return hudOverlay; + }); + }); + } + + protected override Ruleset CreateRulesetForSkinProvider() => new OsuRuleset(); + } +}