1
0
mirror of https://github.com/ppy/osu.git synced 2025-02-22 05:23:05 +08:00

Split out the base design of sheared overlay into its own abstract class

This will allow for reuse with the first-run overlay.
This commit is contained in:
Dean Herbert 2022-04-20 15:05:07 +09:00
parent 27d4982a79
commit 8d31b0bc01
3 changed files with 165 additions and 76 deletions

View File

@ -21,6 +21,8 @@ namespace osu.Game.Graphics.UserInterface
{ {
public class PopupScreenTitle : CompositeDrawable public class PopupScreenTitle : CompositeDrawable
{ {
public const float HEIGHT = main_area_height + 2 * corner_radius;
public LocalisableString Title public LocalisableString Title
{ {
set => titleSpriteText.Text = value; set => titleSpriteText.Text = value;
@ -67,7 +69,7 @@ namespace osu.Game.Graphics.UserInterface
underlayContainer = new Container underlayContainer = new Container
{ {
RelativeSizeAxes = Axes.X, RelativeSizeAxes = Axes.X,
Height = main_area_height + 2 * corner_radius, Height = HEIGHT,
CornerRadius = corner_radius, CornerRadius = corner_radius,
Masking = true, Masking = true,
BorderThickness = 2, BorderThickness = 2,

View File

@ -9,7 +9,6 @@ using osu.Framework.Allocation;
using osu.Framework.Bindables; using osu.Framework.Bindables;
using osu.Framework.Graphics; using osu.Framework.Graphics;
using osu.Framework.Graphics.Containers; using osu.Framework.Graphics.Containers;
using osu.Framework.Graphics.Shapes;
using osu.Framework.Input.Events; using osu.Framework.Input.Events;
using osu.Framework.Layout; using osu.Framework.Layout;
using osu.Game.Configuration; using osu.Game.Configuration;
@ -21,39 +20,27 @@ using osuTK.Input;
namespace osu.Game.Overlays.Mods namespace osu.Game.Overlays.Mods
{ {
public class ModSelectScreen : OsuFocusedOverlayContainer public class ModSelectScreen : ShearedOverlayContainer
{ {
[Cached] protected override OverlayColourScheme ColourScheme => OverlayColourScheme.Green;
private OverlayColourProvider colourProvider = new OverlayColourProvider(OverlayColourScheme.Green);
[Cached] [Cached]
public Bindable<IReadOnlyList<Mod>> SelectedMods { get; private set; } = new Bindable<IReadOnlyList<Mod>>(Array.Empty<Mod>()); public Bindable<IReadOnlyList<Mod>> SelectedMods { get; private set; } = new Bindable<IReadOnlyList<Mod>>(Array.Empty<Mod>());
protected override bool StartHidden => true;
private readonly BindableBool customisationVisible = new BindableBool(); private readonly BindableBool customisationVisible = new BindableBool();
private DifficultyMultiplierDisplay multiplierDisplay; private DifficultyMultiplierDisplay multiplierDisplay;
private ModSettingsArea modSettingsArea; private ModSettingsArea modSettingsArea;
private FillFlowContainer<ModColumn> columnFlow; private FillFlowContainer<ModColumn> columnFlow;
private GridContainer grid; private GridContainer grid;
private Container mainContent;
private PopupScreenTitle header;
private Container footer;
[BackgroundDependencyLoader] [BackgroundDependencyLoader]
private void load() private void load()
{ {
RelativeSizeAxes = Axes.Both; MainAreaContent.AddRange(new Drawable[]
RelativePositionAxes = Axes.Both;
InternalChildren = new Drawable[]
{ {
mainContent = new Container new Container
{ {
Origin = Anchor.BottomCentre,
Anchor = Anchor.BottomCentre,
RelativeSizeAxes = Axes.Both, RelativeSizeAxes = Axes.Both,
Children = new Drawable[] Children = new Drawable[]
{ {
@ -62,24 +49,11 @@ namespace osu.Game.Overlays.Mods
RelativeSizeAxes = Axes.Both, RelativeSizeAxes = Axes.Both,
RowDimensions = new[] RowDimensions = new[]
{ {
new Dimension(GridSizeMode.AutoSize),
new Dimension(GridSizeMode.AutoSize), new Dimension(GridSizeMode.AutoSize),
new Dimension(), new Dimension(),
new Dimension(GridSizeMode.Absolute, 75),
}, },
Content = new[] Content = new[]
{ {
new Drawable[]
{
header = new PopupScreenTitle
{
Anchor = Anchor.TopCentre,
Origin = Anchor.TopCentre,
Title = "Mod Select",
Description = "Mods provide different ways to enjoy gameplay. Some have an effect on the score you can achieve during ranked play. Others are just for fun.",
Close = Hide
}
},
new Drawable[] new Drawable[]
{ {
new Container new Container
@ -120,6 +94,7 @@ namespace osu.Game.Overlays.Mods
Child = columnFlow = new ModColumnContainer Child = columnFlow = new ModColumnContainer
{ {
Direction = FillDirection.Horizontal, Direction = FillDirection.Horizontal,
Shear = new Vector2(ModPanel.SHEAR_X, 0),
RelativeSizeAxes = Axes.Y, RelativeSizeAxes = Axes.Y,
AutoSizeAxes = Axes.X, AutoSizeAxes = Axes.X,
Spacing = new Vector2(10, 0), Spacing = new Vector2(10, 0),
@ -137,42 +112,28 @@ namespace osu.Game.Overlays.Mods
} }
} }
}, },
new[] { Empty() }
} }
}, },
footer = new Container }
{
RelativeSizeAxes = Axes.X,
AutoSizeAxes = Axes.Y,
Anchor = Anchor.BottomCentre,
Origin = Anchor.BottomCentre,
Children = new Drawable[]
{
new Box
{
RelativeSizeAxes = Axes.X,
Height = 50,
Anchor = Anchor.BottomCentre,
Origin = Anchor.BottomCentre,
Colour = colourProvider.Background5
}, },
new ShearedToggleButton(200) });
Footer.Add(new ShearedToggleButton(200)
{ {
Anchor = Anchor.BottomLeft, Anchor = Anchor.BottomLeft,
Origin = Anchor.BottomLeft, Origin = Anchor.BottomLeft,
Margin = new MarginPadding { Vertical = 14, Left = 70 }, Margin = new MarginPadding { Vertical = 14, Left = 70 },
Text = "Mod Customisation", Text = "Mod Customisation",
Active = { BindTarget = customisationVisible } Active = { BindTarget = customisationVisible }
} });
}
}, AddRange(new Drawable[]
{
new ClickToReturnContainer new ClickToReturnContainer
{ {
RelativeSizeAxes = Axes.Both, RelativeSizeAxes = Axes.Both,
HandleMouse = { BindTarget = customisationVisible }, HandleMouse = { BindTarget = customisationVisible },
OnClicked = () => customisationVisible.Value = false OnClicked = () => customisationVisible.Value = false
}
}
}, },
modSettingsArea = new ModSettingsArea modSettingsArea = new ModSettingsArea
{ {
@ -180,9 +141,7 @@ namespace osu.Game.Overlays.Mods
Origin = Anchor.BottomCentre, Origin = Anchor.BottomCentre,
Height = 0 Height = 0
} }
}; });
columnFlow.Shear = new Vector2(ModPanel.SHEAR_X, 0);
} }
protected override void LoadComplete() protected override void LoadComplete()
@ -252,7 +211,7 @@ namespace osu.Game.Overlays.Mods
float modAreaHeight = customisationVisible.Value ? ModSettingsArea.HEIGHT : 0; float modAreaHeight = customisationVisible.Value ? ModSettingsArea.HEIGHT : 0;
modSettingsArea.ResizeHeightTo(modAreaHeight, transition_duration, Easing.InOutCubic); modSettingsArea.ResizeHeightTo(modAreaHeight, transition_duration, Easing.InOutCubic);
mainContent.TransformTo(nameof(Margin), new MarginPadding { Bottom = modAreaHeight }, transition_duration, Easing.InOutCubic); TopLevelContent.MoveToY(-modAreaHeight, transition_duration, Easing.InOutCubic);
} }
private bool selectionBindableSyncInProgress; private bool selectionBindableSyncInProgress;
@ -287,10 +246,6 @@ namespace osu.Game.Overlays.Mods
const double fade_in_duration = 400; const double fade_in_duration = 400;
base.PopIn(); base.PopIn();
this.FadeIn(fade_in_duration, Easing.OutQuint);
header.MoveToY(0, fade_in_duration, Easing.OutQuint);
footer.MoveToY(0, fade_in_duration, Easing.OutQuint);
multiplierDisplay multiplierDisplay
.Delay(fade_in_duration * 0.65f) .Delay(fade_in_duration * 0.65f)
@ -311,15 +266,11 @@ namespace osu.Game.Overlays.Mods
const double fade_out_duration = 500; const double fade_out_duration = 500;
base.PopOut(); base.PopOut();
this.FadeOut(fade_out_duration, Easing.OutQuint);
multiplierDisplay multiplierDisplay
.FadeOut(fade_out_duration / 2, Easing.OutQuint) .FadeOut(fade_out_duration / 2, Easing.OutQuint)
.ScaleTo(0.75f, fade_out_duration, Easing.OutQuint); .ScaleTo(0.75f, fade_out_duration, Easing.OutQuint);
header.MoveToY(-header.DrawHeight, fade_out_duration, Easing.OutQuint);
footer.MoveToY(footer.DrawHeight, fade_out_duration, Easing.OutQuint);
for (int i = 0; i < columnFlow.Count; i++) for (int i = 0; i < columnFlow.Count; i++)
{ {
const float distance = 700; const float distance = 700;

View File

@ -0,0 +1,136 @@
// Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the MIT Licence.
// See the LICENCE file in the repository root for full licence text.
using osu.Framework.Allocation;
using osu.Framework.Graphics;
using osu.Framework.Graphics.Containers;
using osu.Framework.Graphics.Shapes;
using osu.Game.Graphics.Containers;
using osu.Game.Graphics.UserInterface;
namespace osu.Game.Overlays.Mods
{
/// <summary>
/// A sheared overlay which provides a header and footer and basic animations.
/// Exposes <see cref="TopLevelContent"/>, <see cref="MainAreaContent"/> and <see cref="Footer"/> as valid targets for content.
/// </summary>
public abstract class ShearedOverlayContainer : OsuFocusedOverlayContainer
{
[Cached]
protected readonly OverlayColourProvider ColourProvider;
/// <summary>
/// The overlay's header.
/// </summary>
protected PopupScreenTitle Header { get; private set; }
/// <summary>
/// The overlay's footer.
/// </summary>
protected Container Footer { get; private set; }
/// <summary>
/// A container containing all content, including the header and footer.
/// May be used for overlay-wide animations.
/// </summary>
protected Container TopLevelContent { get; private set; }
/// <summary>
/// A container for content that is to be displayed between the header and footer.
/// </summary>
protected Container MainAreaContent { get; private set; }
/// <summary>
/// A container for content that is to be displayed inside the footer.
/// </summary>
protected Container FooterContent { get; private set; }
protected abstract OverlayColourScheme ColourScheme { get; }
protected override bool StartHidden => true;
protected override bool BlockNonPositionalInput => true;
protected ShearedOverlayContainer()
{
RelativeSizeAxes = Axes.Both;
ColourProvider = new OverlayColourProvider(ColourScheme);
}
[BackgroundDependencyLoader]
private void load()
{
const float footer_height = 50;
Child = TopLevelContent = new Container
{
RelativeSizeAxes = Axes.Both,
Children = new Drawable[]
{
Header = new PopupScreenTitle
{
Anchor = Anchor.TopCentre,
Depth = float.MinValue,
Origin = Anchor.TopCentre,
Title = "Mod Select",
Description = "Mods provide different ways to enjoy gameplay. Some have an effect on the score you can achieve during ranked play. Others are just for fun.",
Close = Hide
},
MainAreaContent = new Container
{
RelativeSizeAxes = Axes.Both,
Padding = new MarginPadding
{
Top = PopupScreenTitle.HEIGHT,
Bottom = footer_height,
}
},
Footer = new Container
{
RelativeSizeAxes = Axes.X,
Depth = float.MinValue,
Height = footer_height,
Margin = new MarginPadding { Top = 10 },
Anchor = Anchor.BottomCentre,
Origin = Anchor.BottomCentre,
Children = new Drawable[]
{
new Box
{
RelativeSizeAxes = Axes.Both,
Colour = ColourProvider.Background5
},
FooterContent = new Container
{
RelativeSizeAxes = Axes.Both,
},
}
}
}
};
}
protected override void PopIn()
{
const double fade_in_duration = 400;
base.PopIn();
this.FadeIn(fade_in_duration, Easing.OutQuint);
Header.MoveToY(0, fade_in_duration, Easing.OutQuint);
Footer.MoveToY(0, fade_in_duration, Easing.OutQuint);
}
protected override void PopOut()
{
const double fade_out_duration = 500;
base.PopOut();
this.FadeOut(fade_out_duration, Easing.OutQuint);
Header.MoveToY(-Header.DrawHeight, fade_out_duration, Easing.OutQuint);
Footer.MoveToY(Footer.DrawHeight, fade_out_duration, Easing.OutQuint);
}
}
}