Add a CaptureBox that encloses hitobjects from the drag selection

This commit is contained in:
smoogipoo
2018-02-14 14:38:37 +09:00
parent fcbeb97a54
commit 344da5965c
2 changed files with 59 additions and 12 deletions

View File

@ -15,17 +15,26 @@ namespace osu.Game.Rulesets.Edit.Layers.Selection
/// <summary> /// <summary>
/// A box which encapsulates captured <see cref="DrawableHitObject"/>s. /// A box which encapsulates captured <see cref="DrawableHitObject"/>s.
/// </summary> /// </summary>
public class CaptureBox : VisibilityContainer public abstract class CaptureBox : VisibilityContainer
{ {
/// <summary>
/// Top-left corner of the rectangle that encloses the <see cref="DrawableHitObject"/>s.
/// </summary>
protected Vector2 FinalPosition { get; private set; }
/// <summary>
/// Size of the rectangle that encloses the <see cref="DrawableHitObject"/>s.
/// </summary>
protected Vector2 FinalSize { get; private set; }
private readonly IDrawable captureArea; private readonly IDrawable captureArea;
private readonly IReadOnlyList<DrawableHitObject> capturedObjects; private readonly IReadOnlyList<DrawableHitObject> capturedObjects;
public CaptureBox(IDrawable captureArea, IReadOnlyList<DrawableHitObject> capturedObjects) protected CaptureBox(IDrawable captureArea, IReadOnlyList<DrawableHitObject> capturedObjects)
{ {
this.captureArea = captureArea; this.captureArea = captureArea;
this.capturedObjects = capturedObjects; this.capturedObjects = capturedObjects;
Origin = Anchor.Centre;
Masking = true; Masking = true;
BorderThickness = 3; BorderThickness = 3;
@ -57,13 +66,47 @@ namespace osu.Game.Rulesets.Edit.Layers.Selection
topLeft -= new Vector2(5); topLeft -= new Vector2(5);
bottomRight += new Vector2(5); bottomRight += new Vector2(5);
Size = bottomRight - topLeft; FinalSize = bottomRight - topLeft;
Position = topLeft + Size / 2f; FinalPosition = topLeft;
} }
protected override void PopIn() => this.ScaleTo(1.1f) protected override void PopIn() => this.MoveTo(FinalPosition).ResizeTo(FinalSize).FadeIn();
.Then() protected override void PopOut() => this.FadeOut();
.ScaleTo(1f, 300, Easing.OutQuint).FadeIn(300, Easing.OutQuint); }
/// <summary>
/// A <see cref="CaptureBox"/> which fully encloses the <see cref="DrawableHitObject"/>s from the start.
/// </summary>
public class InstantCaptureBox : CaptureBox
{
public InstantCaptureBox(IDrawable captureArea, IReadOnlyList<DrawableHitObject> capturedObjects)
: base(captureArea, capturedObjects)
{
Origin = Anchor.Centre;
}
protected override void PopIn()
=> this.MoveTo(FinalPosition + FinalSize / 2f).ResizeTo(FinalSize).ScaleTo(1.1f)
.Then()
.ScaleTo(1f, 300, Easing.OutQuint).FadeIn(300, Easing.OutQuint);
protected override void PopOut() => this.FadeOut(300, Easing.OutQuint);
}
/// <summary>
/// A <see cref="CaptureBox"/> which moves from an initial position + size to enclose <see cref="DrawableHitObject"/>s.
/// </summary>
public class DragCaptureBox : CaptureBox
{
public DragCaptureBox(IDrawable captureArea, IReadOnlyList<DrawableHitObject> capturedObjects, Vector2 initialPosition, Vector2 initialSize)
: base(captureArea, capturedObjects)
{
Position = initialPosition;
Size = initialSize;
}
protected override void PopIn()
=> this.MoveTo(FinalPosition, 300, Easing.OutQuint).ResizeTo(FinalSize, 300, Easing.OutQuint).FadeIn(300, Easing.OutQuint);
protected override void PopOut() => this.FadeOut(300, Easing.OutQuint); protected override void PopOut() => this.FadeOut(300, Easing.OutQuint);
} }

View File

@ -58,7 +58,7 @@ namespace osu.Game.Rulesets.Edit.Layers.Selection
protected override bool OnDragEnd(InputState state) protected override bool OnDragEnd(InputState state)
{ {
selectionBox.Hide(); selectionBox.Hide();
finishCapture(); finishCapture(true);
return true; return true;
} }
@ -66,7 +66,7 @@ namespace osu.Game.Rulesets.Edit.Layers.Selection
protected override bool OnClick(InputState state) protected override bool OnClick(InputState state)
{ {
capturePoint(state.Mouse.NativeState.Position); capturePoint(state.Mouse.NativeState.Position);
finishCapture(); finishCapture(false);
return true; return true;
} }
@ -94,7 +94,7 @@ namespace osu.Game.Rulesets.Edit.Layers.Selection
capturedHitObjects.Add(captured); capturedHitObjects.Add(captured);
} }
private void finishCapture() private void finishCapture(bool fromDrag)
{ {
if (capturedHitObjects.Count == 0) if (capturedHitObjects.Count == 0)
return; return;
@ -102,7 +102,11 @@ namespace osu.Game.Rulesets.Edit.Layers.Selection
// Due to https://github.com/ppy/osu-framework/issues/1382, we may get here through both // Due to https://github.com/ppy/osu-framework/issues/1382, we may get here through both
// OnDragEnd and OnClick methods within a single frame, OnMouseDown doesn't help us here // OnDragEnd and OnClick methods within a single frame, OnMouseDown doesn't help us here
captureBox?.Hide(); captureBox?.Hide();
AddInternal(captureBox = new CaptureBox(this, capturedHitObjects.ToList()));
if (fromDrag)
AddInternal(captureBox = new DragCaptureBox(this, capturedHitObjects.ToList(), selectionBox.Position, selectionBox.Size));
else
AddInternal(captureBox = new InstantCaptureBox(this, capturedHitObjects.ToList()));
} }
} }
} }