diff --git a/osu.Game.Tests/Visual/Gameplay/TestSceneArgonHealthDisplay.cs b/osu.Game.Tests/Visual/Gameplay/TestSceneArgonHealthDisplay.cs index 06a7763711..7bad623d7f 100644 --- a/osu.Game.Tests/Visual/Gameplay/TestSceneArgonHealthDisplay.cs +++ b/osu.Game.Tests/Visual/Gameplay/TestSceneArgonHealthDisplay.cs @@ -3,6 +3,7 @@ using NUnit.Framework; using osu.Framework.Allocation; +using osu.Framework.Extensions.ObjectExtensions; using osu.Framework.Graphics; using osu.Framework.Graphics.Shapes; using osu.Framework.Testing; @@ -12,7 +13,6 @@ using osu.Game.Rulesets.Osu.Judgements; using osu.Game.Rulesets.Osu.Objects; using osu.Game.Rulesets.Scoring; using osu.Game.Screens.Play.HUD; -using osuTK; using osuTK.Graphics; namespace osu.Game.Tests.Visual.Gameplay @@ -22,6 +22,8 @@ namespace osu.Game.Tests.Visual.Gameplay [Cached(typeof(HealthProcessor))] private HealthProcessor healthProcessor = new DrainingHealthProcessor(0); + private ArgonHealthDisplay healthDisplay = null!; + [SetUpSteps] public void SetUpSteps() { @@ -37,14 +39,25 @@ namespace osu.Game.Tests.Visual.Gameplay RelativeSizeAxes = Axes.Both, Colour = Color4.Gray, }, - new ArgonHealthDisplay + healthDisplay = new ArgonHealthDisplay { Anchor = Anchor.Centre, Origin = Anchor.Centre, - Scale = new Vector2(2f), }, }; }); + + AddSliderStep("Width", 0, 1f, 1f, val => + { + if (healthDisplay.IsNotNull()) + healthDisplay.BarLength.Value = val; + }); + + AddSliderStep("Height", 0, 64, 0, val => + { + if (healthDisplay.IsNotNull()) + healthDisplay.BarHeight.Value = val; + }); } [Test] diff --git a/osu.Game/Screens/Play/HUD/ArgonHealthDisplay.cs b/osu.Game/Screens/Play/HUD/ArgonHealthDisplay.cs index 62a4b958c2..7af7fd9487 100644 --- a/osu.Game/Screens/Play/HUD/ArgonHealthDisplay.cs +++ b/osu.Game/Screens/Play/HUD/ArgonHealthDisplay.cs @@ -5,14 +5,16 @@ using System; using System.Collections.Generic; using System.Linq; using osu.Framework.Allocation; +using osu.Framework.Bindables; using osu.Framework.Extensions.Color4Extensions; using osu.Framework.Graphics; using osu.Framework.Graphics.Colour; using osu.Framework.Graphics.Containers; using osu.Framework.Graphics.Lines; -using osu.Framework.Graphics.Shapes; +using osu.Framework.Layout; using osu.Framework.Threading; using osu.Framework.Utils; +using osu.Game.Configuration; using osu.Game.Graphics; using osu.Game.Rulesets.Judgements; using osu.Game.Rulesets.Objects; @@ -27,6 +29,22 @@ namespace osu.Game.Screens.Play.HUD { public bool UsesFixedAnchor { get; set; } + [SettingSource("Bar height")] + public BindableFloat BarHeight { get; } = new BindableFloat(20) + { + MinValue = 0, + MaxValue = 64, + Precision = 1 + }; + + [SettingSource("Bar length")] + public BindableFloat BarLength { get; } = new BindableFloat(0.98f) + { + MinValue = 0.2f, + MaxValue = 1, + Precision = 0.01f, + }; + private BarPath mainBar = null!; /// @@ -76,59 +94,46 @@ namespace osu.Game.Screens.Play.HUD } } + private const float main_path_radius = 10f; + [BackgroundDependencyLoader] private void load() { - AutoSizeAxes = Axes.Both; + RelativeSizeAxes = Axes.X; + AutoSizeAxes = Axes.Y; - InternalChild = new FillFlowContainer + InternalChild = new Container { AutoSizeAxes = Axes.Both, - Direction = FillDirection.Horizontal, - Spacing = new Vector2(4f, 0f), Children = new Drawable[] { - new Circle + background = new BackgroundPath { - Margin = new MarginPadding { Top = 8.5f, Left = -2 }, - Size = new Vector2(50f, 3f), + PathRadius = main_path_radius, }, - new Container + glowBar = new BarPath { - AutoSizeAxes = Axes.Both, - Children = new Drawable[] - { - background = new BackgroundPath - { - PathRadius = 10f, - }, - glowBar = new BarPath - { - BarColour = Color4.White, - GlowColour = OsuColour.Gray(0.5f), - Blending = BlendingParameters.Additive, - Colour = ColourInfo.GradientHorizontal(Color4.White.Opacity(0.8f), Color4.White), - PathRadius = 40f, - // Kinda hacky, but results in correct positioning with increased path radius. - Margin = new MarginPadding(-30f), - GlowPortion = 0.9f, - }, - mainBar = new BarPath - { - AutoSizeAxes = Axes.None, - RelativeSizeAxes = Axes.Both, - Blending = BlendingParameters.Additive, - BarColour = main_bar_colour, - GlowColour = main_bar_glow_colour, - PathRadius = 10f, - GlowPortion = 0.6f, - }, - } - } - }, + BarColour = Color4.White, + GlowColour = OsuColour.Gray(0.5f), + Blending = BlendingParameters.Additive, + Colour = ColourInfo.GradientHorizontal(Color4.White.Opacity(0.8f), Color4.White), + PathRadius = 40f, + // Kinda hacky, but results in correct positioning with increased path radius. + Margin = new MarginPadding(-30f), + GlowPortion = 0.9f, + }, + mainBar = new BarPath + { + AutoSizeAxes = Axes.None, + RelativeSizeAxes = Axes.Both, + Blending = BlendingParameters.Additive, + BarColour = main_bar_colour, + GlowColour = main_bar_glow_colour, + PathRadius = main_path_radius, + GlowPortion = 0.6f, + }, + } }; - - updatePath(); } protected override void LoadComplete() @@ -140,10 +145,24 @@ namespace osu.Game.Screens.Play.HUD if (v.NewValue >= GlowBarValue) finishMissDisplay(); - this.TransformTo(nameof(HealthBarValue), v.NewValue, 300, Easing.OutQuint); + double time = v.NewValue > GlowBarValue ? 500 : 250; + + this.TransformTo(nameof(HealthBarValue), v.NewValue, time, Easing.OutQuint); if (resetMissBarDelegate == null) - this.TransformTo(nameof(GlowBarValue), v.NewValue, 300, Easing.OutQuint); + this.TransformTo(nameof(GlowBarValue), v.NewValue, time, Easing.OutQuint); }, true); + + BarLength.BindValueChanged(l => Width = l.NewValue, true); + BarHeight.BindValueChanged(_ => updatePath()); + updatePath(); + } + + protected override bool OnInvalidate(Invalidation invalidation, InvalidationSource source) + { + if ((invalidation & Invalidation.DrawSize) > 0) + updatePath(); + + return base.OnInvalidate(invalidation, source); } protected override void Update() @@ -214,25 +233,24 @@ namespace osu.Game.Screens.Play.HUD private void updatePath() { - const float curve_start = 280; - const float curve_end = 310; + float barLength = DrawWidth - main_path_radius * 2; + float curveStart = barLength - 70; + float curveEnd = barLength - 40; + const float curve_smoothness = 10; - const float bar_length = 350; - const float bar_verticality = 32.5f; - - Vector2 diagonalDir = (new Vector2(curve_end, bar_verticality) - new Vector2(curve_start, 0)).Normalized(); + Vector2 diagonalDir = (new Vector2(curveEnd, BarHeight.Value) - new Vector2(curveStart, 0)).Normalized(); barPath = new SliderPath(new[] { new PathControlPoint(new Vector2(0, 0), PathType.Linear), - new PathControlPoint(new Vector2(curve_start - curve_smoothness, 0), PathType.Bezier), - new PathControlPoint(new Vector2(curve_start, 0)), - new PathControlPoint(new Vector2(curve_start, 0) + diagonalDir * curve_smoothness, PathType.Linear), - new PathControlPoint(new Vector2(curve_end, bar_verticality) - diagonalDir * curve_smoothness, PathType.Bezier), - new PathControlPoint(new Vector2(curve_end, bar_verticality)), - new PathControlPoint(new Vector2(curve_end + curve_smoothness, bar_verticality), PathType.Linear), - new PathControlPoint(new Vector2(bar_length, bar_verticality)), + new PathControlPoint(new Vector2(curveStart - curve_smoothness, 0), PathType.Bezier), + new PathControlPoint(new Vector2(curveStart, 0)), + new PathControlPoint(new Vector2(curveStart, 0) + diagonalDir * curve_smoothness, PathType.Linear), + new PathControlPoint(new Vector2(curveEnd, BarHeight.Value) - diagonalDir * curve_smoothness, PathType.Bezier), + new PathControlPoint(new Vector2(curveEnd, BarHeight.Value)), + new PathControlPoint(new Vector2(curveEnd + curve_smoothness, BarHeight.Value), PathType.Linear), + new PathControlPoint(new Vector2(barLength, BarHeight.Value)), }); List vertices = new List(); @@ -267,7 +285,7 @@ namespace osu.Game.Screens.Play.HUD { protected override Color4 ColourAt(float position) { - if (position <= 0.128f) + if (position <= 0.16f) return Color4.White.Opacity(0.8f); return Interpolation.ValueAt(position, diff --git a/osu.Game/Skinning/ArgonSkin.cs b/osu.Game/Skinning/ArgonSkin.cs index 6e17458082..d530efbfdd 100644 --- a/osu.Game/Skinning/ArgonSkin.cs +++ b/osu.Game/Skinning/ArgonSkin.cs @@ -109,6 +109,7 @@ namespace osu.Game.Skinning case SkinComponentsContainerLookup.TargetArea.MainHUDComponents: var skinnableTargetWrapper = new DefaultSkinComponentsContainer(container => { + var health = container.OfType().FirstOrDefault(); var score = container.OfType().FirstOrDefault(); var accuracy = container.OfType().FirstOrDefault(); var combo = container.OfType().FirstOrDefault(); @@ -128,6 +129,13 @@ namespace osu.Game.Skinning score.Position = new Vector2(0, vertical_offset); + if (health != null) + { + health.Origin = Anchor.TopCentre; + health.Anchor = Anchor.TopCentre; + health.Y = 5; + } + if (ppCounter != null) { ppCounter.Y = score.Position.Y + ppCounter.ScreenSpaceDeltaToParentSpace(score.ScreenSpaceDrawQuad.Size).Y - 4; @@ -191,7 +199,7 @@ namespace osu.Game.Skinning new DefaultComboCounter(), new DefaultScoreCounter(), new DefaultAccuracyCounter(), - new DefaultHealthDisplay(), + new ArgonHealthDisplay(), new ArgonSongProgress(), new ArgonKeyCounterDisplay(), new BarHitErrorMeter(),