From 9bc2e91de01864e16711765869e264ade0cd1ae0 Mon Sep 17 00:00:00 2001 From: Dean Herbert Date: Mon, 15 Aug 2022 19:17:41 +0900 Subject: [PATCH] Fix incorrect handling of reference clocks when no parent `IGameplayClock` is available --- .../Rulesets/UI/FrameStabilityContainer.cs | 42 +++++++++++++------ 1 file changed, 29 insertions(+), 13 deletions(-) diff --git a/osu.Game/Rulesets/UI/FrameStabilityContainer.cs b/osu.Game/Rulesets/UI/FrameStabilityContainer.cs index c115a0b6ac..411217e314 100644 --- a/osu.Game/Rulesets/UI/FrameStabilityContainer.cs +++ b/osu.Game/Rulesets/UI/FrameStabilityContainer.cs @@ -10,6 +10,7 @@ using osu.Framework.Bindables; using osu.Framework.Graphics; using osu.Framework.Graphics.Containers; using osu.Framework.Timing; +using osu.Framework.Utils; using osu.Game.Input.Handlers; using osu.Game.Screens.Play; @@ -56,6 +57,8 @@ namespace osu.Game.Rulesets.UI private IGameplayClock? parentGameplayClock; + private IClock referenceClock = null!; + /// /// The current direction of playback to be exposed to frame stable children. /// @@ -65,18 +68,15 @@ namespace osu.Game.Rulesets.UI private int direction = 1; [BackgroundDependencyLoader] - private void load(IGameplayClock? clock) + private void load(IGameplayClock? gameplayClock) { - if (clock != null) + if (gameplayClock != null) { - parentGameplayClock = clock; + parentGameplayClock = gameplayClock; IsPaused.BindTo(parentGameplayClock.IsPaused); } - } - protected override void LoadComplete() - { - base.LoadComplete(); + referenceClock = gameplayClock ?? Clock; Clock = this; } @@ -128,7 +128,7 @@ namespace osu.Game.Rulesets.UI state = PlaybackState.Valid; } - double proposedTime = Clock.CurrentTime; + double proposedTime = referenceClock.CurrentTime; if (FrameStablePlayback) // if we require frame stability, the proposed time will be adjusted to move at most one known @@ -148,14 +148,14 @@ namespace osu.Game.Rulesets.UI if (state == PlaybackState.Valid && proposedTime != manualClock.CurrentTime) direction = proposedTime >= manualClock.CurrentTime ? 1 : -1; - double timeBehind = Math.Abs(proposedTime - Clock.CurrentTime); + double timeBehind = Math.Abs(proposedTime - CurrentTime); IsCatchingUp.Value = timeBehind > 200; WaitingOnFrames.Value = state == PlaybackState.NotValid; manualClock.CurrentTime = proposedTime; - manualClock.Rate = Math.Abs(Clock.Rate) * direction; - manualClock.IsRunning = Clock.IsRunning; + manualClock.Rate = Math.Abs(referenceClock.Rate) * direction; + manualClock.IsRunning = referenceClock.IsRunning; // determine whether catch-up is required. if (state == PlaybackState.Valid && timeBehind > 0) @@ -244,7 +244,7 @@ namespace osu.Game.Rulesets.UI public bool IsRunning => framedClock.IsRunning; - public void ProcessFrame() => framedClock.ProcessFrame(); + public void ProcessFrame() { } public double ElapsedFrameTime => framedClock.ElapsedFrameTime; @@ -256,7 +256,23 @@ namespace osu.Game.Rulesets.UI #region Delegation of IGameplayClock - public double TrueGameplayRate => parentGameplayClock?.TrueGameplayRate ?? 1; + public double TrueGameplayRate + { + get + { + double baseRate = Rate; + + foreach (double adjustment in NonGameplayAdjustments) + { + if (Precision.AlmostEquals(adjustment, 0)) + return 0; + + baseRate /= adjustment; + } + + return baseRate; + } + } public double? StartTime => parentGameplayClock?.StartTime;