mirror of
https://github.com/ppy/osu
synced 2024-12-27 01:12:45 +00:00
Merge branch 'master' into catch-combo-counter
This commit is contained in:
commit
c5717d8e41
44
osu.Game.Rulesets.Taiko.Tests/DrawableTestStrongHit.cs
Normal file
44
osu.Game.Rulesets.Taiko.Tests/DrawableTestStrongHit.cs
Normal file
@ -0,0 +1,44 @@
|
||||
// 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.Linq;
|
||||
using osu.Game.Beatmaps;
|
||||
using osu.Game.Beatmaps.ControlPoints;
|
||||
using osu.Game.Rulesets.Scoring;
|
||||
using osu.Game.Rulesets.Taiko.Objects;
|
||||
using osu.Game.Rulesets.Taiko.Objects.Drawables;
|
||||
|
||||
namespace osu.Game.Rulesets.Taiko.Tests
|
||||
{
|
||||
public class DrawableTestStrongHit : DrawableHit
|
||||
{
|
||||
private readonly HitResult type;
|
||||
private readonly bool hitBoth;
|
||||
|
||||
public DrawableTestStrongHit(double startTime, HitResult type = HitResult.Great, bool hitBoth = true)
|
||||
: base(new Hit
|
||||
{
|
||||
IsStrong = true,
|
||||
StartTime = startTime,
|
||||
})
|
||||
{
|
||||
// in order to create nested strong hit
|
||||
HitObject.ApplyDefaults(new ControlPointInfo(), new BeatmapDifficulty());
|
||||
|
||||
this.type = type;
|
||||
this.hitBoth = hitBoth;
|
||||
}
|
||||
|
||||
protected override void LoadAsyncComplete()
|
||||
{
|
||||
base.LoadAsyncComplete();
|
||||
|
||||
Result.Type = type;
|
||||
|
||||
var nestedStrongHit = (DrawableStrongNestedHit)NestedHitObjects.Single();
|
||||
nestedStrongHit.Result.Type = hitBoth ? type : HitResult.Miss;
|
||||
}
|
||||
|
||||
public override bool OnPressed(TaikoAction action) => false;
|
||||
}
|
||||
}
|
@ -2,7 +2,6 @@
|
||||
// See the LICENCE file in the repository root for full licence text.
|
||||
|
||||
using NUnit.Framework;
|
||||
using osu.Framework.Allocation;
|
||||
using osu.Framework.Graphics;
|
||||
using osu.Framework.Graphics.Containers;
|
||||
using osu.Game.Rulesets.Scoring;
|
||||
@ -15,24 +14,29 @@ namespace osu.Game.Rulesets.Taiko.Tests.Skinning
|
||||
[TestFixture]
|
||||
public class TestSceneHitExplosion : TaikoSkinnableTestScene
|
||||
{
|
||||
[BackgroundDependencyLoader]
|
||||
private void load()
|
||||
[Test]
|
||||
public void TestNormalHit()
|
||||
{
|
||||
AddStep("Great", () => SetContents(() => getContentFor(HitResult.Great)));
|
||||
AddStep("Good", () => SetContents(() => getContentFor(HitResult.Good)));
|
||||
AddStep("Miss", () => SetContents(() => getContentFor(HitResult.Miss)));
|
||||
AddStep("Great", () => SetContents(() => getContentFor(createHit(HitResult.Great))));
|
||||
AddStep("Good", () => SetContents(() => getContentFor(createHit(HitResult.Good))));
|
||||
AddStep("Miss", () => SetContents(() => getContentFor(createHit(HitResult.Miss))));
|
||||
}
|
||||
|
||||
private Drawable getContentFor(HitResult type)
|
||||
[Test]
|
||||
public void TestStrongHit([Values(false, true)] bool hitBoth)
|
||||
{
|
||||
DrawableTaikoHitObject hit;
|
||||
AddStep("Great", () => SetContents(() => getContentFor(createStrongHit(HitResult.Great, hitBoth))));
|
||||
AddStep("Good", () => SetContents(() => getContentFor(createStrongHit(HitResult.Good, hitBoth))));
|
||||
}
|
||||
|
||||
private Drawable getContentFor(DrawableTaikoHitObject hit)
|
||||
{
|
||||
return new Container
|
||||
{
|
||||
RelativeSizeAxes = Axes.Both,
|
||||
Children = new Drawable[]
|
||||
{
|
||||
hit = createHit(type),
|
||||
hit,
|
||||
new HitExplosion(hit)
|
||||
{
|
||||
Anchor = Anchor.Centre,
|
||||
@ -43,5 +47,8 @@ namespace osu.Game.Rulesets.Taiko.Tests.Skinning
|
||||
}
|
||||
|
||||
private DrawableTaikoHitObject createHit(HitResult type) => new DrawableTestHit(new Hit { StartTime = Time.Current }, type);
|
||||
|
||||
private DrawableTaikoHitObject createStrongHit(HitResult type, bool hitBoth)
|
||||
=> new DrawableTestStrongHit(Time.Current, type, hitBoth);
|
||||
}
|
||||
}
|
||||
|
@ -174,7 +174,9 @@ namespace osu.Game.Rulesets.Taiko.Tests
|
||||
|
||||
private void addMissJudgement()
|
||||
{
|
||||
((TaikoPlayfield)drawableRuleset.Playfield).OnNewResult(new DrawableTestHit(new Hit()), new JudgementResult(new HitObject(), new TaikoJudgement()) { Type = HitResult.Miss });
|
||||
DrawableTestHit h;
|
||||
Add(h = new DrawableTestHit(new Hit(), HitResult.Miss));
|
||||
((TaikoPlayfield)drawableRuleset.Playfield).OnNewResult(h, new JudgementResult(new HitObject(), new TaikoJudgement()) { Type = HitResult.Miss });
|
||||
}
|
||||
|
||||
private void addBarLine(bool major, double delay = scroll_time)
|
||||
|
@ -75,7 +75,9 @@ namespace osu.Game.Rulesets.Taiko.Skinning
|
||||
return null;
|
||||
|
||||
case TaikoSkinComponents.TaikoExplosionGood:
|
||||
case TaikoSkinComponents.TaikoExplosionGoodStrong:
|
||||
case TaikoSkinComponents.TaikoExplosionGreat:
|
||||
case TaikoSkinComponents.TaikoExplosionGreatStrong:
|
||||
case TaikoSkinComponents.TaikoExplosionMiss:
|
||||
|
||||
var sprite = this.GetAnimation(getHitName(taikoComponent.Component), true, false);
|
||||
@ -107,8 +109,14 @@ namespace osu.Game.Rulesets.Taiko.Skinning
|
||||
case TaikoSkinComponents.TaikoExplosionGood:
|
||||
return "taiko-hit100";
|
||||
|
||||
case TaikoSkinComponents.TaikoExplosionGoodStrong:
|
||||
return "taiko-hit100k";
|
||||
|
||||
case TaikoSkinComponents.TaikoExplosionGreat:
|
||||
return "taiko-hit300";
|
||||
|
||||
case TaikoSkinComponents.TaikoExplosionGreatStrong:
|
||||
return "taiko-hit300k";
|
||||
}
|
||||
|
||||
throw new ArgumentOutOfRangeException(nameof(component), "Invalid result type");
|
||||
|
@ -17,7 +17,9 @@ namespace osu.Game.Rulesets.Taiko
|
||||
BarLine,
|
||||
TaikoExplosionMiss,
|
||||
TaikoExplosionGood,
|
||||
TaikoExplosionGoodStrong,
|
||||
TaikoExplosionGreat,
|
||||
TaikoExplosionGreatStrong,
|
||||
Scroller,
|
||||
Mascot,
|
||||
}
|
||||
|
@ -2,6 +2,7 @@
|
||||
// See the LICENCE file in the repository root for full licence text.
|
||||
|
||||
using System;
|
||||
using System.Linq;
|
||||
using osuTK;
|
||||
using osu.Framework.Allocation;
|
||||
using osu.Framework.Graphics;
|
||||
@ -9,6 +10,7 @@ using osu.Framework.Graphics.Containers;
|
||||
using osu.Game.Rulesets.Objects.Drawables;
|
||||
using osu.Game.Rulesets.Scoring;
|
||||
using osu.Game.Rulesets.Taiko.Objects;
|
||||
using osu.Game.Rulesets.Taiko.Objects.Drawables;
|
||||
using osu.Game.Skinning;
|
||||
|
||||
namespace osu.Game.Rulesets.Taiko.UI
|
||||
@ -45,24 +47,41 @@ namespace osu.Game.Rulesets.Taiko.UI
|
||||
[BackgroundDependencyLoader]
|
||||
private void load()
|
||||
{
|
||||
Child = skinnable = new SkinnableDrawable(new TaikoSkinComponent(getComponentName(JudgedObject.Result?.Type ?? HitResult.Great)), _ => new DefaultHitExplosion());
|
||||
Child = skinnable = new SkinnableDrawable(new TaikoSkinComponent(getComponentName(JudgedObject)), _ => new DefaultHitExplosion());
|
||||
}
|
||||
|
||||
private TaikoSkinComponents getComponentName(HitResult resultType)
|
||||
private TaikoSkinComponents getComponentName(DrawableHitObject judgedObject)
|
||||
{
|
||||
var resultType = judgedObject.Result?.Type ?? HitResult.Great;
|
||||
|
||||
switch (resultType)
|
||||
{
|
||||
case HitResult.Miss:
|
||||
return TaikoSkinComponents.TaikoExplosionMiss;
|
||||
|
||||
case HitResult.Good:
|
||||
return TaikoSkinComponents.TaikoExplosionGood;
|
||||
return useStrongExplosion(judgedObject)
|
||||
? TaikoSkinComponents.TaikoExplosionGoodStrong
|
||||
: TaikoSkinComponents.TaikoExplosionGood;
|
||||
|
||||
case HitResult.Great:
|
||||
return TaikoSkinComponents.TaikoExplosionGreat;
|
||||
return useStrongExplosion(judgedObject)
|
||||
? TaikoSkinComponents.TaikoExplosionGreatStrong
|
||||
: TaikoSkinComponents.TaikoExplosionGreat;
|
||||
}
|
||||
|
||||
throw new ArgumentOutOfRangeException(nameof(resultType), "Invalid result type");
|
||||
throw new ArgumentOutOfRangeException(nameof(judgedObject), "Invalid result type");
|
||||
}
|
||||
|
||||
private bool useStrongExplosion(DrawableHitObject judgedObject)
|
||||
{
|
||||
if (!(judgedObject.HitObject is Hit))
|
||||
return false;
|
||||
|
||||
if (!(judgedObject.NestedHitObjects.SingleOrDefault() is DrawableStrongNestedHit nestedHit))
|
||||
return false;
|
||||
|
||||
return judgedObject.Result.Type == nestedHit.Result.Type;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
@ -205,9 +205,6 @@ namespace osu.Game.Rulesets.Taiko.UI
|
||||
X = result.IsHit ? judgedObject.Position.X : 0,
|
||||
});
|
||||
|
||||
if (!result.IsHit)
|
||||
break;
|
||||
|
||||
var type = (judgedObject.HitObject as Hit)?.Type ?? HitType.Centre;
|
||||
|
||||
addExplosion(judgedObject, type);
|
||||
@ -218,12 +215,16 @@ namespace osu.Game.Rulesets.Taiko.UI
|
||||
private void addDrumRollHit(DrawableDrumRollTick drawableTick) =>
|
||||
drumRollHitContainer.Add(new DrawableFlyingHit(drawableTick));
|
||||
|
||||
private void addExplosion(DrawableHitObject drawableObject, HitType type)
|
||||
/// <remarks>
|
||||
/// As legacy skins have different explosions for singular and double strong hits,
|
||||
/// explosion addition is scheduled to ensure that both hits are processed if they occur on the same frame.
|
||||
/// </remarks>
|
||||
private void addExplosion(DrawableHitObject drawableObject, HitType type) => Schedule(() =>
|
||||
{
|
||||
hitExplosionContainer.Add(new HitExplosion(drawableObject));
|
||||
if (drawableObject.HitObject.Kiai)
|
||||
kiaiExplosionContainer.Add(new KiaiHitExplosion(drawableObject, type));
|
||||
}
|
||||
});
|
||||
|
||||
private class ProxyContainer : LifetimeManagementContainer
|
||||
{
|
||||
|
Loading…
Reference in New Issue
Block a user