2022-08-05 10:17:01 +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.
|
|
|
|
|
|
|
|
using System.Collections.Generic;
|
|
|
|
using System.Linq;
|
2022-08-09 03:27:46 +08:00
|
|
|
using osu.Framework.Allocation;
|
|
|
|
using osu.Framework.Graphics;
|
2022-08-05 10:17:01 +08:00
|
|
|
using osu.Game.Rulesets.UI;
|
|
|
|
|
2022-08-15 02:12:11 +08:00
|
|
|
namespace osu.Game.Screens.Play.HUD.ClicksPerSecond
|
2022-08-05 10:17:01 +08:00
|
|
|
{
|
2022-08-15 02:12:11 +08:00
|
|
|
public class ClicksPerSecondCalculator : Component
|
2022-08-05 10:17:01 +08:00
|
|
|
{
|
2022-08-07 06:53:00 +08:00
|
|
|
private readonly List<double> timestamps;
|
2022-08-05 10:17:01 +08:00
|
|
|
|
2022-08-09 03:27:46 +08:00
|
|
|
[Resolved]
|
2022-08-24 23:12:52 +08:00
|
|
|
private IGameplayClock gameplayClock { get; set; } = null!;
|
2022-08-05 10:17:01 +08:00
|
|
|
|
2022-08-24 23:12:52 +08:00
|
|
|
[Resolved]
|
|
|
|
private DrawableRuleset drawableRuleset { get; set; } = null!;
|
2022-08-05 10:17:01 +08:00
|
|
|
|
2022-08-24 23:12:52 +08:00
|
|
|
private double rate;
|
2022-08-05 10:17:01 +08:00
|
|
|
|
2022-08-24 23:12:52 +08:00
|
|
|
// The latest timestamp GC seeked. Does not affect normal gameplay
|
|
|
|
// but prevents duplicate inputs on replays.
|
|
|
|
private double latestTime = double.NegativeInfinity;
|
2022-08-07 06:53:00 +08:00
|
|
|
|
2022-08-24 23:12:52 +08:00
|
|
|
public int Value { get; private set; }
|
2022-08-05 10:17:01 +08:00
|
|
|
|
2022-08-15 02:12:11 +08:00
|
|
|
public ClicksPerSecondCalculator()
|
2022-08-05 10:17:01 +08:00
|
|
|
{
|
2022-08-09 03:27:46 +08:00
|
|
|
RelativeSizeAxes = Axes.Both;
|
2022-08-05 10:17:01 +08:00
|
|
|
timestamps = new List<double>();
|
|
|
|
}
|
|
|
|
|
2022-08-24 23:12:52 +08:00
|
|
|
protected override void Update()
|
2022-08-05 10:17:01 +08:00
|
|
|
{
|
2022-08-24 23:12:52 +08:00
|
|
|
base.Update();
|
2022-08-07 06:53:00 +08:00
|
|
|
|
2022-08-24 23:12:52 +08:00
|
|
|
// When pausing in replays (using the space bar) GC.TrueGameplayRate returns 0
|
|
|
|
// To prevent CPS value being 0, we store and use the last non-zero TrueGameplayRate
|
|
|
|
if (gameplayClock.TrueGameplayRate > 0)
|
2022-08-05 10:17:01 +08:00
|
|
|
{
|
2022-08-24 23:12:52 +08:00
|
|
|
rate = gameplayClock.TrueGameplayRate;
|
2022-08-05 10:17:01 +08:00
|
|
|
}
|
|
|
|
|
2022-08-24 23:12:52 +08:00
|
|
|
Value = timestamps.Count(timestamp =>
|
|
|
|
{
|
|
|
|
double window = 1000 * rate;
|
|
|
|
double relativeTime = drawableRuleset.FrameStableClock.CurrentTime - timestamp;
|
|
|
|
return relativeTime > 0 && relativeTime <= window;
|
|
|
|
});
|
2022-08-05 10:17:01 +08:00
|
|
|
}
|
2022-08-09 03:27:46 +08:00
|
|
|
|
2022-08-24 23:12:52 +08:00
|
|
|
public void AddTimestamp()
|
2022-08-09 03:27:46 +08:00
|
|
|
{
|
2022-08-24 23:12:52 +08:00
|
|
|
// Discard inputs if current gameplay time is not the latest
|
|
|
|
// to prevent duplicate inputs
|
|
|
|
if (drawableRuleset.FrameStableClock.CurrentTime >= latestTime)
|
2022-08-09 03:27:46 +08:00
|
|
|
{
|
2022-08-24 23:12:52 +08:00
|
|
|
timestamps.Add(drawableRuleset.FrameStableClock.CurrentTime);
|
|
|
|
latestTime = drawableRuleset.FrameStableClock.CurrentTime;
|
2022-08-09 03:27:46 +08:00
|
|
|
}
|
|
|
|
}
|
2022-08-05 10:17:01 +08:00
|
|
|
}
|
|
|
|
}
|