1
0
mirror of https://github.com/ppy/osu.git synced 2024-09-21 17:27:24 +08:00

Change inheritance of taiko hit pieces to better allow for skinning

This commit is contained in:
Dean Herbert 2020-04-11 13:14:34 +09:00
parent 3a36c0008f
commit 7fba291134
13 changed files with 209 additions and 112 deletions

View File

@ -0,0 +1,54 @@
// 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 System;
using System.Collections.Generic;
using System.Linq;
using NUnit.Framework;
using osu.Framework.Allocation;
using osu.Framework.Graphics;
using osu.Game.Beatmaps;
using osu.Game.Beatmaps.ControlPoints;
using osu.Game.Rulesets.Taiko.Objects;
using osu.Game.Rulesets.Taiko.Objects.Drawables;
namespace osu.Game.Rulesets.Taiko.Tests
{
[TestFixture]
public class TestSceneDrawableHit : TaikoSkinnableTestScene
{
public override IReadOnlyList<Type> RequiredTypes => base.RequiredTypes.Concat(new[]
{
typeof(DrawableHit),
typeof(DrawableCentreHit),
typeof(DrawableRimHit),
}).ToList();
[BackgroundDependencyLoader]
private void load()
{
AddStep("Centre hit", () => SetContents(() => new DrawableCentreHit(createHitAtCurrentTime())
{
Anchor = Anchor.Centre,
Origin = Anchor.Centre,
}));
AddStep("Rim hit", () => SetContents(() => new DrawableRimHit(createHitAtCurrentTime())
{
Anchor = Anchor.Centre,
Origin = Anchor.Centre,
}));
}
private Hit createHitAtCurrentTime()
{
var hit = new Hit
{
StartTime = Time.Current + 3000,
};
hit.ApplyDefaults(new ControlPointInfo(), new BeatmapDifficulty());
return hit;
}
}
}

View File

@ -1,8 +1,7 @@
// Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the MIT Licence. // 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. // See the LICENCE file in the repository root for full licence text.
using osu.Framework.Allocation; using osu.Framework.Graphics.Containers;
using osu.Game.Graphics;
using osu.Game.Rulesets.Taiko.Objects.Drawables.Pieces; using osu.Game.Rulesets.Taiko.Objects.Drawables.Pieces;
namespace osu.Game.Rulesets.Taiko.Objects.Drawables namespace osu.Game.Rulesets.Taiko.Objects.Drawables
@ -14,13 +13,8 @@ namespace osu.Game.Rulesets.Taiko.Objects.Drawables
public DrawableCentreHit(Hit hit) public DrawableCentreHit(Hit hit)
: base(hit) : base(hit)
{ {
MainPiece.Add(new CentreHitSymbolPiece());
} }
[BackgroundDependencyLoader] protected override CompositeDrawable CreateMainPiece() => new CentreHitCirclePiece();
private void load(OsuColour colours)
{
MainPiece.AccentColour = colours.PinkDarker;
}
} }
} }

View File

@ -34,17 +34,19 @@ namespace osu.Game.Rulesets.Taiko.Objects.Drawables
private Color4 colourIdle; private Color4 colourIdle;
private Color4 colourEngaged; private Color4 colourEngaged;
private ElongatedCirclePiece elongatedPiece;
public DrawableDrumRoll(DrumRoll drumRoll) public DrawableDrumRoll(DrumRoll drumRoll)
: base(drumRoll) : base(drumRoll)
{ {
RelativeSizeAxes = Axes.Y; RelativeSizeAxes = Axes.Y;
MainPiece.Add(tickContainer = new Container<DrawableDrumRollTick> { RelativeSizeAxes = Axes.Both }); elongatedPiece.Add(tickContainer = new Container<DrawableDrumRollTick> { RelativeSizeAxes = Axes.Both });
} }
[BackgroundDependencyLoader] [BackgroundDependencyLoader]
private void load(OsuColour colours) private void load(OsuColour colours)
{ {
MainPiece.AccentColour = colourIdle = colours.YellowDark; elongatedPiece.AccentColour = colourIdle = colours.YellowDark;
colourEngaged = colours.YellowDarker; colourEngaged = colours.YellowDarker;
} }
@ -84,7 +86,7 @@ namespace osu.Game.Rulesets.Taiko.Objects.Drawables
return base.CreateNestedHitObject(hitObject); return base.CreateNestedHitObject(hitObject);
} }
protected override TaikoPiece CreateMainPiece() => new ElongatedCirclePiece(); protected override CompositeDrawable CreateMainPiece() => elongatedPiece = new ElongatedCirclePiece();
public override bool OnPressed(TaikoAction action) => false; public override bool OnPressed(TaikoAction action) => false;
@ -101,7 +103,7 @@ namespace osu.Game.Rulesets.Taiko.Objects.Drawables
rollingHits = Math.Clamp(rollingHits, 0, rolling_hits_for_engaged_colour); rollingHits = Math.Clamp(rollingHits, 0, rolling_hits_for_engaged_colour);
Color4 newColour = Interpolation.ValueAt((float)rollingHits / rolling_hits_for_engaged_colour, colourIdle, colourEngaged, 0, 1); Color4 newColour = Interpolation.ValueAt((float)rollingHits / rolling_hits_for_engaged_colour, colourIdle, colourEngaged, 0, 1);
MainPiece.FadeAccent(newColour, 100); (MainPiece as IHasAccentColour)?.FadeAccent(newColour, 100);
} }
protected override void CheckForResult(bool userTriggered, double timeOffset) protected override void CheckForResult(bool userTriggered, double timeOffset)

View File

@ -3,6 +3,7 @@
using System; using System;
using osu.Framework.Graphics; using osu.Framework.Graphics;
using osu.Framework.Graphics.Containers;
using osu.Game.Rulesets.Objects.Drawables; using osu.Game.Rulesets.Objects.Drawables;
using osu.Game.Rulesets.Scoring; using osu.Game.Rulesets.Scoring;
using osu.Game.Rulesets.Taiko.Objects.Drawables.Pieces; using osu.Game.Rulesets.Taiko.Objects.Drawables.Pieces;
@ -19,7 +20,7 @@ namespace osu.Game.Rulesets.Taiko.Objects.Drawables
public override bool DisplayResult => false; public override bool DisplayResult => false;
protected override TaikoPiece CreateMainPiece() => new TickPiece protected override CompositeDrawable CreateMainPiece() => new TickPiece
{ {
Filled = HitObject.FirstTick Filled = HitObject.FirstTick
}; };

View File

@ -1,8 +1,7 @@
// Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the MIT Licence. // 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. // See the LICENCE file in the repository root for full licence text.
using osu.Framework.Allocation; using osu.Framework.Graphics.Containers;
using osu.Game.Graphics;
using osu.Game.Rulesets.Taiko.Objects.Drawables.Pieces; using osu.Game.Rulesets.Taiko.Objects.Drawables.Pieces;
namespace osu.Game.Rulesets.Taiko.Objects.Drawables namespace osu.Game.Rulesets.Taiko.Objects.Drawables
@ -14,13 +13,8 @@ namespace osu.Game.Rulesets.Taiko.Objects.Drawables
public DrawableRimHit(Hit hit) public DrawableRimHit(Hit hit)
: base(hit) : base(hit)
{ {
MainPiece.Add(new RimHitSymbolPiece());
} }
[BackgroundDependencyLoader] protected override CompositeDrawable CreateMainPiece() => new RimHitCirclePiece();
private void load(OsuColour colours)
{
MainPiece.AccentColour = colours.BlueDarker;
}
} }
} }

View File

@ -9,11 +9,11 @@ using osu.Framework.Graphics;
using osu.Framework.Graphics.Containers; using osu.Framework.Graphics.Containers;
using osu.Game.Graphics; using osu.Game.Graphics;
using osu.Game.Rulesets.Objects.Drawables; using osu.Game.Rulesets.Objects.Drawables;
using osu.Game.Rulesets.Taiko.Objects.Drawables.Pieces;
using osuTK.Graphics; using osuTK.Graphics;
using osu.Framework.Graphics.Shapes; using osu.Framework.Graphics.Shapes;
using osu.Game.Rulesets.Objects; using osu.Game.Rulesets.Objects;
using osu.Game.Rulesets.Scoring; using osu.Game.Rulesets.Scoring;
using osu.Game.Rulesets.Taiko.Objects.Drawables.Pieces;
namespace osu.Game.Rulesets.Taiko.Objects.Drawables namespace osu.Game.Rulesets.Taiko.Objects.Drawables
{ {
@ -34,8 +34,6 @@ namespace osu.Game.Rulesets.Taiko.Objects.Drawables
private readonly CircularContainer targetRing; private readonly CircularContainer targetRing;
private readonly CircularContainer expandingRing; private readonly CircularContainer expandingRing;
private readonly SwellSymbolPiece symbol;
public DrawableSwell(Swell swell) public DrawableSwell(Swell swell)
: base(swell) : base(swell)
{ {
@ -107,18 +105,22 @@ namespace osu.Game.Rulesets.Taiko.Objects.Drawables
}); });
AddInternal(ticks = new Container<DrawableSwellTick> { RelativeSizeAxes = Axes.Both }); AddInternal(ticks = new Container<DrawableSwellTick> { RelativeSizeAxes = Axes.Both });
MainPiece.Add(symbol = new SwellSymbolPiece());
} }
[BackgroundDependencyLoader] [BackgroundDependencyLoader]
private void load(OsuColour colours) private void load(OsuColour colours)
{ {
MainPiece.AccentColour = colours.YellowDark;
expandingRing.Colour = colours.YellowLight; expandingRing.Colour = colours.YellowLight;
targetRing.BorderColour = colours.YellowDark.Opacity(0.25f); targetRing.BorderColour = colours.YellowDark.Opacity(0.25f);
} }
protected override CompositeDrawable CreateMainPiece() => new SwellCirclePiece
{
// to allow for rotation transform
Anchor = Anchor.Centre,
Origin = Anchor.Centre,
};
protected override void LoadComplete() protected override void LoadComplete()
{ {
base.LoadComplete(); base.LoadComplete();
@ -182,7 +184,7 @@ namespace osu.Game.Rulesets.Taiko.Objects.Drawables
.Then() .Then()
.FadeTo(completion / 8, 2000, Easing.OutQuint); .FadeTo(completion / 8, 2000, Easing.OutQuint);
symbol.RotateTo((float)(completion * HitObject.Duration / 8), 4000, Easing.OutQuint); MainPiece.RotateTo((float)(completion * HitObject.Duration / 8), 4000, Easing.OutQuint);
expandingRing.ScaleTo(1f + Math.Min(target_ring_scale - 1f, (target_ring_scale - 1f) * completion * 1.3f), 260, Easing.OutQuint); expandingRing.ScaleTo(1f + Math.Min(target_ring_scale - 1f, (target_ring_scale - 1f) * completion * 1.3f), 260, Easing.OutQuint);

View File

@ -2,7 +2,9 @@
// See the LICENCE file in the repository root for full licence text. // See the LICENCE file in the repository root for full licence text.
using osu.Framework.Graphics; using osu.Framework.Graphics;
using osu.Framework.Graphics.Containers;
using osu.Game.Rulesets.Scoring; using osu.Game.Rulesets.Scoring;
using osu.Game.Rulesets.Taiko.Objects.Drawables.Pieces;
namespace osu.Game.Rulesets.Taiko.Objects.Drawables namespace osu.Game.Rulesets.Taiko.Objects.Drawables
{ {
@ -28,5 +30,7 @@ namespace osu.Game.Rulesets.Taiko.Objects.Drawables
} }
public override bool OnPressed(TaikoAction action) => false; public override bool OnPressed(TaikoAction action) => false;
protected override CompositeDrawable CreateMainPiece() => new TickPiece();
} }
} }

View File

@ -4,7 +4,6 @@
using osu.Framework.Graphics; using osu.Framework.Graphics;
using osu.Framework.Input.Bindings; using osu.Framework.Input.Bindings;
using osu.Game.Rulesets.Objects.Drawables; using osu.Game.Rulesets.Objects.Drawables;
using osu.Game.Rulesets.Taiko.Objects.Drawables.Pieces;
using osuTK; using osuTK;
using System.Linq; using System.Linq;
using osu.Game.Audio; using osu.Game.Audio;
@ -108,19 +107,19 @@ namespace osu.Game.Rulesets.Taiko.Objects.Drawables
} }
} }
public abstract class DrawableTaikoHitObject<TTaikoHit> : DrawableTaikoHitObject public abstract class DrawableTaikoHitObject<TObject> : DrawableTaikoHitObject
where TTaikoHit : TaikoHitObject where TObject : TaikoHitObject
{ {
public override Vector2 OriginPosition => new Vector2(DrawHeight / 2); public override Vector2 OriginPosition => new Vector2(DrawHeight / 2);
public new TTaikoHit HitObject; public new TObject HitObject;
protected readonly Vector2 BaseSize; protected readonly Vector2 BaseSize;
protected readonly TaikoPiece MainPiece; protected readonly CompositeDrawable MainPiece;
private readonly Container<DrawableStrongNestedHit> strongHitContainer; private readonly Container<DrawableStrongNestedHit> strongHitContainer;
protected DrawableTaikoHitObject(TTaikoHit hitObject) protected DrawableTaikoHitObject(TObject hitObject)
: base(hitObject) : base(hitObject)
{ {
HitObject = hitObject; HitObject = hitObject;
@ -132,7 +131,6 @@ namespace osu.Game.Rulesets.Taiko.Objects.Drawables
Size = BaseSize = new Vector2(HitObject.IsStrong ? TaikoHitObject.DEFAULT_STRONG_SIZE : TaikoHitObject.DEFAULT_SIZE); Size = BaseSize = new Vector2(HitObject.IsStrong ? TaikoHitObject.DEFAULT_STRONG_SIZE : TaikoHitObject.DEFAULT_SIZE);
Content.Add(MainPiece = CreateMainPiece()); Content.Add(MainPiece = CreateMainPiece());
MainPiece.KiaiMode = HitObject.Kiai;
AddInternal(strongHitContainer = new Container<DrawableStrongNestedHit>()); AddInternal(strongHitContainer = new Container<DrawableStrongNestedHit>());
} }
@ -169,7 +167,7 @@ namespace osu.Game.Rulesets.Taiko.Objects.Drawables
// Normal and clap samples are handled by the drum // Normal and clap samples are handled by the drum
protected override IEnumerable<HitSampleInfo> GetSamples() => HitObject.Samples.Where(s => s.Name != HitSampleInfo.HIT_NORMAL && s.Name != HitSampleInfo.HIT_CLAP); protected override IEnumerable<HitSampleInfo> GetSamples() => HitObject.Samples.Where(s => s.Name != HitSampleInfo.HIT_NORMAL && s.Name != HitSampleInfo.HIT_CLAP);
protected virtual TaikoPiece CreateMainPiece() => new CirclePiece(); protected abstract CompositeDrawable CreateMainPiece();
/// <summary> /// <summary>
/// Creates the handler for this <see cref="DrawableHitObject"/>'s <see cref="StrongHitObject"/>. /// Creates the handler for this <see cref="DrawableHitObject"/>'s <see cref="StrongHitObject"/>.

View File

@ -1,13 +1,28 @@
// Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the MIT Licence. // 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. // See the LICENCE file in the repository root for full licence text.
using osu.Framework.Allocation;
using osu.Framework.Graphics; using osu.Framework.Graphics;
using osu.Framework.Graphics.Containers; using osu.Framework.Graphics.Containers;
using osuTK; using osuTK;
using osu.Framework.Graphics.Shapes; using osu.Framework.Graphics.Shapes;
using osu.Game.Graphics;
namespace osu.Game.Rulesets.Taiko.Objects.Drawables.Pieces namespace osu.Game.Rulesets.Taiko.Objects.Drawables.Pieces
{ {
public class CentreHitCirclePiece : CirclePiece
{
public CentreHitCirclePiece()
{
Add(new CentreHitSymbolPiece());
}
[BackgroundDependencyLoader]
private void load(OsuColour colours)
{
AccentColour = colours.PinkDarker;
}
/// <summary> /// <summary>
/// The symbol used for centre hit pieces. /// The symbol used for centre hit pieces.
/// </summary> /// </summary>
@ -19,8 +34,8 @@ namespace osu.Game.Rulesets.Taiko.Objects.Drawables.Pieces
Origin = Anchor.Centre; Origin = Anchor.Centre;
RelativeSizeAxes = Axes.Both; RelativeSizeAxes = Axes.Both;
Size = new Vector2(CirclePiece.SYMBOL_SIZE); Size = new Vector2(SYMBOL_SIZE);
Padding = new MarginPadding(CirclePiece.SYMBOL_BORDER); Padding = new MarginPadding(SYMBOL_BORDER);
Children = new[] Children = new[]
{ {
@ -34,3 +49,4 @@ namespace osu.Game.Rulesets.Taiko.Objects.Drawables.Pieces
} }
} }
} }
}

View File

@ -0,0 +1,55 @@
// 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;
using osuTK;
using osuTK.Graphics;
namespace osu.Game.Rulesets.Taiko.Objects.Drawables.Pieces
{
public class RimHitCirclePiece : CirclePiece
{
public RimHitCirclePiece()
{
Add(new RimHitSymbolPiece());
}
[BackgroundDependencyLoader]
private void load(OsuColour colours)
{
AccentColour = colours.BlueDarker;
}
/// <summary>
/// The symbol used for rim hit pieces.
/// </summary>
public class RimHitSymbolPiece : CircularContainer
{
public RimHitSymbolPiece()
{
Anchor = Anchor.Centre;
Origin = Anchor.Centre;
RelativeSizeAxes = Axes.Both;
Size = new Vector2(SYMBOL_SIZE);
BorderThickness = SYMBOL_BORDER;
BorderColour = Color4.White;
Masking = true;
Children = new[]
{
new Box
{
RelativeSizeAxes = Axes.Both,
Alpha = 0,
AlwaysPresent = true
}
};
}
}
}
}

View File

@ -1,39 +0,0 @@
// 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.Graphics;
using osu.Framework.Graphics.Containers;
using osuTK;
using osuTK.Graphics;
using osu.Framework.Graphics.Shapes;
namespace osu.Game.Rulesets.Taiko.Objects.Drawables.Pieces
{
/// <summary>
/// The symbol used for rim hit pieces.
/// </summary>
public class RimHitSymbolPiece : CircularContainer
{
public RimHitSymbolPiece()
{
Anchor = Anchor.Centre;
Origin = Anchor.Centre;
RelativeSizeAxes = Axes.Both;
Size = new Vector2(CirclePiece.SYMBOL_SIZE);
BorderThickness = CirclePiece.SYMBOL_BORDER;
BorderColour = Color4.White;
Masking = true;
Children = new[]
{
new Box
{
RelativeSizeAxes = Axes.Both,
Alpha = 0,
AlwaysPresent = true
}
};
}
}
}

View File

@ -1,13 +1,28 @@
// Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the MIT Licence. // 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. // See the LICENCE file in the repository root for full licence text.
using osu.Framework.Allocation;
using osuTK; using osuTK;
using osu.Framework.Graphics; using osu.Framework.Graphics;
using osu.Framework.Graphics.Containers; using osu.Framework.Graphics.Containers;
using osu.Framework.Graphics.Sprites; using osu.Framework.Graphics.Sprites;
using osu.Game.Graphics;
namespace osu.Game.Rulesets.Taiko.Objects.Drawables.Pieces namespace osu.Game.Rulesets.Taiko.Objects.Drawables.Pieces
{ {
public class SwellCirclePiece : CirclePiece
{
public SwellCirclePiece()
{
Add(new SwellSymbolPiece());
}
[BackgroundDependencyLoader]
private void load(OsuColour colours)
{
AccentColour = colours.YellowDark;
}
/// <summary> /// <summary>
/// The symbol used for swell pieces. /// The symbol used for swell pieces.
/// </summary> /// </summary>
@ -19,8 +34,8 @@ namespace osu.Game.Rulesets.Taiko.Objects.Drawables.Pieces
Origin = Anchor.Centre; Origin = Anchor.Centre;
RelativeSizeAxes = Axes.Both; RelativeSizeAxes = Axes.Both;
Size = new Vector2(CirclePiece.SYMBOL_SIZE); Size = new Vector2(SYMBOL_SIZE);
Padding = new MarginPadding(CirclePiece.SYMBOL_BORDER); Padding = new MarginPadding(SYMBOL_BORDER);
Children = new[] Children = new[]
{ {
@ -34,3 +49,4 @@ namespace osu.Game.Rulesets.Taiko.Objects.Drawables.Pieces
} }
} }
} }
}

View File

@ -9,7 +9,7 @@ using osu.Framework.Graphics.Shapes;
namespace osu.Game.Rulesets.Taiko.Objects.Drawables.Pieces namespace osu.Game.Rulesets.Taiko.Objects.Drawables.Pieces
{ {
public class TickPiece : TaikoPiece public class TickPiece : CompositeDrawable
{ {
/// <summary> /// <summary>
/// Any tick that is not the first for a drumroll is not filled, but is instead displayed /// Any tick that is not the first for a drumroll is not filled, but is instead displayed
@ -45,7 +45,7 @@ namespace osu.Game.Rulesets.Taiko.Objects.Drawables.Pieces
FillMode = FillMode.Fit; FillMode = FillMode.Fit;
Size = new Vector2(tick_size); Size = new Vector2(tick_size);
Add(new CircularContainer InternalChild = new CircularContainer
{ {
RelativeSizeAxes = Axes.Both, RelativeSizeAxes = Axes.Both,
Masking = true, Masking = true,
@ -60,7 +60,7 @@ namespace osu.Game.Rulesets.Taiko.Objects.Drawables.Pieces
AlwaysPresent = true AlwaysPresent = true
} }
} }
}); };
} }
} }
} }