From 559f94aa02a138154a136fbb1708ca01d83b3b5b Mon Sep 17 00:00:00 2001 From: Aurelian Date: Fri, 7 Jun 2024 21:57:12 +0200 Subject: [PATCH] Moved HitObject adjustments to TimingControlPoint --- .../ControlPoints/TimingControlPoint.cs | 35 +++++++++++++++ .../Screens/Edit/Timing/TapTimingControl.cs | 44 ++++--------------- 2 files changed, 43 insertions(+), 36 deletions(-) diff --git a/osu.Game/Beatmaps/ControlPoints/TimingControlPoint.cs b/osu.Game/Beatmaps/ControlPoints/TimingControlPoint.cs index 4e69486e2d..a3224a6ab9 100644 --- a/osu.Game/Beatmaps/ControlPoints/TimingControlPoint.cs +++ b/osu.Game/Beatmaps/ControlPoints/TimingControlPoint.cs @@ -2,9 +2,14 @@ // See the LICENCE file in the repository root for full licence text. using System; +using System.Collections.Generic; +using System.Linq; using osu.Framework.Bindables; +using osu.Framework.Utils; using osu.Game.Beatmaps.Timing; using osu.Game.Graphics; +using osu.Game.Rulesets.Objects; +using osu.Game.Rulesets.Objects.Types; using osuTK.Graphics; namespace osu.Game.Beatmaps.ControlPoints @@ -105,5 +110,35 @@ namespace osu.Game.Beatmaps.ControlPoints && BeatLength.Equals(other.BeatLength); public override int GetHashCode() => HashCode.Combine(base.GetHashCode(), TimeSignature, BeatLength, OmitFirstBarLine); + + public List HitObjectsInTimingRange(IBeatmap beatmap) + { + // If the first group, we grab all hitobjects prior to the next, if the last group, we grab all remaining hitobjects + double startTime = beatmap.ControlPointInfo.TimingPoints.Any(x => x.Time < Time) ? Time : double.MinValue; + double endTime = beatmap.ControlPointInfo.TimingPoints.FirstOrDefault(x => x.Time > Time)?.Time ?? double.MaxValue; + + return beatmap.HitObjects.Where(x => Precision.AlmostBigger(x.StartTime, startTime) && Precision.DefinitelyBigger(endTime, x.StartTime)).ToList(); + } + + public void AdjustHitObjectOffset(IBeatmap beatmap, double adjust) + { + foreach (HitObject hitObject in HitObjectsInTimingRange(beatmap)) + { + hitObject.StartTime += adjust; + } + } + + public void SetHitObjectBPM(IBeatmap beatmap, double newBeatLength) + { + foreach (HitObject hitObject in HitObjectsInTimingRange(beatmap)) + { + double beat = (hitObject.StartTime - Time) / BeatLength; + + hitObject.StartTime = (beat * newBeatLength) + Time; + + if (hitObject is not IHasRepeats && hitObject is IHasDuration hitObjectWithDuration) + hitObjectWithDuration.Duration *= newBeatLength / BeatLength; + } + } } } diff --git a/osu.Game/Screens/Edit/Timing/TapTimingControl.cs b/osu.Game/Screens/Edit/Timing/TapTimingControl.cs index 1c7f89c80d..49d3df4aef 100644 --- a/osu.Game/Screens/Edit/Timing/TapTimingControl.cs +++ b/osu.Game/Screens/Edit/Timing/TapTimingControl.cs @@ -211,15 +211,6 @@ namespace osu.Game.Screens.Edit.Timing editorClock.Seek(selectedGroup.Value.Time); } - private static List hitObjectsInTimingRange(EditorBeatmap beatmap, ControlPointGroup selectedGroup) - { - // If the first group, we grab all hitobjects prior to the next, if the last group, we grab all remaining hitobjects - double startTime = beatmap.ControlPointInfo.TimingPoints.Any(x => x.Time < selectedGroup.Time) ? selectedGroup.Time : double.MinValue; - double endTime = beatmap.ControlPointInfo.TimingPoints.FirstOrDefault(x => x.Time > selectedGroup.Time)?.Time ?? double.MaxValue; - - return beatmap.HitObjects.Where(x => Precision.AlmostBigger(x.StartTime, startTime) && Precision.DefinitelyBigger(endTime, x.StartTime)).ToList(); - } - private void adjustOffset(double adjust) { if (selectedGroup.Value == null) @@ -227,8 +218,6 @@ namespace osu.Game.Screens.Edit.Timing bool wasAtStart = editorClock.CurrentTimeAccurate == selectedGroup.Value.Time; - List hitObjectsInRange = hitObjectsInTimingRange(beatmap, selectedGroup.Value); - // VERY TEMPORARY var currentGroupItems = selectedGroup.Value.ControlPoints.ToArray(); @@ -237,26 +226,22 @@ namespace osu.Game.Screens.Edit.Timing double newOffset = selectedGroup.Value.Time + adjust; foreach (var cp in currentGroupItems) + { + if (adjustPlacedNotes.Current.Value && cp is TimingControlPoint tp) + tp.AdjustHitObjectOffset(beatmap, adjust); beatmap.ControlPointInfo.Add(newOffset, cp); + } // the control point might not necessarily exist yet, if currentGroupItems was empty. selectedGroup.Value = beatmap.ControlPointInfo.GroupAt(newOffset, true); - if (adjustPlacedNotes.Current.Value) - { - foreach (HitObject hitObject in hitObjectsInRange) - { - hitObject.StartTime += adjust; - } - } - if (!editorClock.IsRunning && wasAtStart) editorClock.Seek(newOffset); - foreach (HitObject hitObject in hitObjectsInRange) - beatmap.Update(hitObject); + beatmap.UpdateAllHitObjects(); } + private void adjustBpm(double adjust) { var timing = selectedGroup.Value?.ControlPoints.OfType().FirstOrDefault(); @@ -266,25 +251,12 @@ namespace osu.Game.Screens.Edit.Timing double newBeatLength = 60000 / (timing.BPM + adjust); - List hitObjectsInRange = hitObjectsInTimingRange(beatmap, selectedGroup.Value!); - if (adjustPlacedNotes.Current.Value) - { - foreach (HitObject hitObject in hitObjectsInRange) - { - double beat = (hitObject.StartTime - selectedGroup.Value!.Time) / timing.BeatLength; - - hitObject.StartTime = (beat * newBeatLength) + selectedGroup.Value.Time; - - if (hitObject is not IHasRepeats && hitObject is IHasDuration hitObjectWithDuration) - hitObjectWithDuration.Duration *= newBeatLength / timing.BeatLength; - } - } + timing.SetHitObjectBPM(beatmap, newBeatLength); timing.BeatLength = newBeatLength; - foreach (HitObject hitObject in hitObjectsInRange) - beatmap.Update(hitObject); + beatmap.UpdateAllHitObjects(); } private partial class InlineButton : OsuButton