1
0
mirror of https://github.com/ppy/osu.git synced 2024-12-24 04:52:56 +08:00
osu-lazer/osu.Game/Screens/Edit/Compose/Components/Timeline/TimelineBreakDisplay.cs

Ignoring revisions in .git-blame-ignore-revs. Click here to bypass and see the normal blame view.

92 lines
2.8 KiB
C#
Raw Normal View History

2024-06-18 20:55:59 +08:00
// 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.
2024-06-19 15:01:33 +08:00
using System.Collections.Specialized;
2024-06-18 20:55:59 +08:00
using osu.Framework.Allocation;
using osu.Framework.Bindables;
using osu.Framework.Caching;
using osu.Game.Beatmaps.Timing;
using osu.Game.Screens.Edit.Components.Timelines.Summary.Parts;
namespace osu.Game.Screens.Edit.Compose.Components.Timeline
{
public partial class TimelineBreakDisplay : TimelinePart<TimelineBreak>
{
[Resolved]
private Timeline timeline { get; set; } = null!;
[Resolved]
2024-07-03 14:17:00 +08:00
private IEditorChangeHandler? editorChangeHandler { get; set; }
2024-06-18 20:55:59 +08:00
/// <summary>
/// The visible time/position range of the timeline.
/// </summary>
private (float min, float max) visibleRange = (float.MinValue, float.MaxValue);
private readonly Cached breakCache = new Cached();
private readonly BindableList<BreakPeriod> breaks = new BindableList<BreakPeriod>();
protected override void LoadBeatmap(EditorBeatmap beatmap)
{
base.LoadBeatmap(beatmap);
2024-06-19 13:31:53 +08:00
breaks.UnbindAll();
breaks.BindTo(beatmap.Breaks);
2024-06-19 15:01:33 +08:00
breaks.BindCollectionChanged((_, e) =>
{
if (e.Action != NotifyCollectionChangedAction.Replace)
breakCache.Invalidate();
});
2024-06-18 20:55:59 +08:00
}
protected override void Update()
{
base.Update();
if (DrawWidth <= 0) return;
(float, float) newRange = (
(ToLocalSpace(timeline.ScreenSpaceDrawQuad.TopLeft).X) / DrawWidth * Content.RelativeChildSize.X,
(ToLocalSpace(timeline.ScreenSpaceDrawQuad.TopRight).X) / DrawWidth * Content.RelativeChildSize.X);
if (visibleRange != newRange)
{
visibleRange = newRange;
breakCache.Invalidate();
}
if (!breakCache.IsValid)
{
recreateBreaks();
breakCache.Validate();
}
}
private void recreateBreaks()
{
2024-06-19 15:01:33 +08:00
Clear();
2024-06-18 20:55:59 +08:00
for (int i = 0; i < breaks.Count; i++)
{
var breakPeriod = breaks[i];
if (!shouldBeVisible(breakPeriod))
continue;
Add(new TimelineBreak(breakPeriod)
{
OnDeleted = b =>
{
2024-07-03 14:17:00 +08:00
editorChangeHandler?.BeginChange();
breaks.Remove(b);
2024-07-03 14:17:00 +08:00
editorChangeHandler?.EndChange();
},
});
2024-06-18 20:55:59 +08:00
}
}
private bool shouldBeVisible(BreakPeriod breakPeriod) => breakPeriod.EndTime >= visibleRange.min && breakPeriod.StartTime <= visibleRange.max;
}
}