Enable NRT

This commit is contained in:
Dan Balasescu
2022-08-22 21:52:43 +09:00
parent 5d3d8681d4
commit c59298f0ce
6 changed files with 27 additions and 41 deletions

View File

@ -17,15 +17,17 @@ namespace osu.Game.Screens.OnlinePlay.Multiplayer.Spectate
/// </summary> /// </summary>
public const double CATCHUP_RATE = 2; public const double CATCHUP_RATE = 2;
/// <summary> public IFrameBasedClock Source { get; set; }
/// The source clock.
/// </summary>
public IFrameBasedClock? Source { get; set; }
public double CurrentTime { get; private set; } public double CurrentTime { get; private set; }
public bool IsRunning { get; private set; } public bool IsRunning { get; private set; }
public CatchUpSpectatorPlayerClock(IFrameBasedClock source)
{
Source = source;
}
public void Reset() => CurrentTime = 0; public void Reset() => CurrentTime = 0;
public void Start() => IsRunning = true; public void Start() => IsRunning = true;
@ -67,9 +69,6 @@ namespace osu.Game.Screens.OnlinePlay.Multiplayer.Spectate
ElapsedFrameTime = 0; ElapsedFrameTime = 0;
FramesPerSecond = 0; FramesPerSecond = 0;
if (Source == null)
return;
Source.ProcessFrame(); Source.ProcessFrame();
if (IsRunning) if (IsRunning)

View File

@ -1,8 +1,6 @@
// Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the MIT Licence. // 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. // See the LICENCE file in the repository root for full licence text.
#nullable disable
using System; using System;
using System.Collections.Generic; using System.Collections.Generic;
using System.Linq; using System.Linq;
@ -32,7 +30,7 @@ namespace osu.Game.Screens.OnlinePlay.Multiplayer.Spectate
/// </summary> /// </summary>
public const double MAXIMUM_START_DELAY = 15000; public const double MAXIMUM_START_DELAY = 15000;
public event Action ReadyToStart; public event Action? ReadyToStart;
/// <summary> /// <summary>
/// The master clock which is used to control the timing of all player clocks clocks. /// The master clock which is used to control the timing of all player clocks clocks.
@ -58,7 +56,7 @@ namespace osu.Game.Screens.OnlinePlay.Multiplayer.Spectate
public ISpectatorPlayerClock AddClock() public ISpectatorPlayerClock AddClock()
{ {
var clock = new CatchUpSpectatorPlayerClock { Source = MasterClock }; var clock = new CatchUpSpectatorPlayerClock(MasterClock);
playerClocks.Add(clock); playerClocks.Add(clock);
return clock; return clock;
} }

View File

@ -1,8 +1,6 @@
// Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the MIT Licence. // 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. // See the LICENCE file in the repository root for full licence text.
#nullable disable
using osu.Framework.Bindables; using osu.Framework.Bindables;
using osu.Framework.Timing; using osu.Framework.Timing;

View File

@ -1,8 +1,6 @@
// Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the MIT Licence. // 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. // See the LICENCE file in the repository root for full licence text.
#nullable disable
using System; using System;
using osu.Framework.Bindables; using osu.Framework.Bindables;
using osu.Game.Screens.Play; using osu.Game.Screens.Play;
@ -17,7 +15,7 @@ namespace osu.Game.Screens.OnlinePlay.Multiplayer.Spectate
/// <summary> /// <summary>
/// An event which is invoked when gameplay is ready to start. /// An event which is invoked when gameplay is ready to start.
/// </summary> /// </summary>
event Action ReadyToStart; event Action? ReadyToStart;
/// <summary> /// <summary>
/// The master clock which player clocks should synchronise to. /// The master clock which player clocks should synchronise to.

View File

@ -1,13 +1,11 @@
// Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the MIT Licence. // 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. // See the LICENCE file in the repository root for full licence text.
#nullable disable
using System; using System;
using System.Linq; using System.Linq;
using JetBrains.Annotations;
using osu.Framework.Allocation; using osu.Framework.Allocation;
using osu.Framework.Bindables; using osu.Framework.Bindables;
using osu.Framework.Extensions.ObjectExtensions;
using osu.Framework.Graphics; using osu.Framework.Graphics;
using osu.Framework.Graphics.Containers; using osu.Framework.Graphics.Containers;
using osu.Game.Beatmaps; using osu.Game.Beatmaps;
@ -42,17 +40,17 @@ namespace osu.Game.Screens.OnlinePlay.Multiplayer.Spectate
protected override UserActivity InitialActivity => new UserActivity.SpectatingMultiplayerGame(Beatmap.Value.BeatmapInfo, Ruleset.Value); protected override UserActivity InitialActivity => new UserActivity.SpectatingMultiplayerGame(Beatmap.Value.BeatmapInfo, Ruleset.Value);
[Resolved] [Resolved]
private OsuColour colours { get; set; } private OsuColour colours { get; set; } = null!;
[Resolved] [Resolved]
private MultiplayerClient multiplayerClient { get; set; } private MultiplayerClient multiplayerClient { get; set; } = null!;
private readonly PlayerArea[] instances; private readonly PlayerArea[] instances;
private MasterGameplayClockContainer masterClockContainer; private MasterGameplayClockContainer masterClockContainer = null!;
private ISyncManager syncManager; private ISyncManager syncManager = null!;
private PlayerGrid grid; private PlayerGrid grid = null!;
private MultiSpectatorLeaderboard leaderboard; private MultiSpectatorLeaderboard leaderboard = null!;
private PlayerArea currentAudioSource; private PlayerArea? currentAudioSource;
private bool canStartMasterClock; private bool canStartMasterClock;
private readonly Room room; private readonly Room room;
@ -178,7 +176,7 @@ namespace osu.Game.Screens.OnlinePlay.Multiplayer.Spectate
} }
} }
private bool isCandidateAudioSource([CanBeNull] ISpectatorPlayerClock clock) private bool isCandidateAudioSource(ISpectatorPlayerClock? clock)
=> clock?.IsRunning == true && !clock.IsCatchingUp && !clock.WaitingOnFrames.Value; => clock?.IsRunning == true && !clock.IsCatchingUp && !clock.WaitingOnFrames.Value;
private void onReadyToStart() private void onReadyToStart()
@ -186,7 +184,7 @@ namespace osu.Game.Screens.OnlinePlay.Multiplayer.Spectate
// Seek the master clock to the gameplay time. // Seek the master clock to the gameplay time.
// This is chosen as the first available frame in the players' replays, which matches the seek by each individual SpectatorPlayer. // This is chosen as the first available frame in the players' replays, which matches the seek by each individual SpectatorPlayer.
double startTime = instances.Where(i => i.Score != null) double startTime = instances.Where(i => i.Score != null)
.SelectMany(i => i.Score.Replay.Frames) .SelectMany(i => i.Score.AsNonNull().Replay.Frames)
.Select(f => f.Time) .Select(f => f.Time)
.DefaultIfEmpty(0) .DefaultIfEmpty(0)
.Min(); .Min();

View File

@ -1,11 +1,8 @@
// Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the MIT Licence. // 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. // See the LICENCE file in the repository root for full licence text.
#nullable disable
using System; using System;
using System.Collections.Generic; using System.Collections.Generic;
using JetBrains.Annotations;
using osu.Framework.Allocation; using osu.Framework.Allocation;
using osu.Framework.Audio; using osu.Framework.Audio;
using osu.Framework.Bindables; using osu.Framework.Bindables;
@ -28,7 +25,7 @@ namespace osu.Game.Screens.OnlinePlay.Multiplayer.Spectate
/// <summary> /// <summary>
/// Raised after <see cref="Player.StartGameplay"/> is called on <see cref="Player"/>. /// Raised after <see cref="Player.StartGameplay"/> is called on <see cref="Player"/>.
/// </summary> /// </summary>
public event Action OnGameplayStarted; public event Action? OnGameplayStarted;
/// <summary> /// <summary>
/// Whether a <see cref="Player"/> is loaded in the area. /// Whether a <see cref="Player"/> is loaded in the area.
@ -43,21 +40,22 @@ namespace osu.Game.Screens.OnlinePlay.Multiplayer.Spectate
/// <summary> /// <summary>
/// The <see cref="ISpectatorPlayerClock"/> used to control the gameplay running state of a loaded <see cref="Player"/>. /// The <see cref="ISpectatorPlayerClock"/> used to control the gameplay running state of a loaded <see cref="Player"/>.
/// </summary> /// </summary>
[NotNull]
public readonly ISpectatorPlayerClock GameplayClock; public readonly ISpectatorPlayerClock GameplayClock;
/// <summary> /// <summary>
/// The currently-loaded score. /// The currently-loaded score.
/// </summary> /// </summary>
[CanBeNull] public Score? Score { get; private set; }
public Score Score { get; private set; }
[Resolved]
private IBindable<WorkingBeatmap> beatmap { get; set; } = null!;
private readonly BindableDouble volumeAdjustment = new BindableDouble(); private readonly BindableDouble volumeAdjustment = new BindableDouble();
private readonly Container gameplayContent; private readonly Container gameplayContent;
private readonly LoadingLayer loadingLayer; private readonly LoadingLayer loadingLayer;
private OsuScreenStack stack; private OsuScreenStack? stack;
public PlayerArea(int userId, [NotNull] ISpectatorPlayerClock clock) public PlayerArea(int userId, ISpectatorPlayerClock clock)
{ {
UserId = userId; UserId = userId;
GameplayClock = clock; GameplayClock = clock;
@ -79,10 +77,7 @@ namespace osu.Game.Screens.OnlinePlay.Multiplayer.Spectate
audioContainer.AddAdjustment(AdjustableProperty.Volume, volumeAdjustment); audioContainer.AddAdjustment(AdjustableProperty.Volume, volumeAdjustment);
} }
[Resolved] public void LoadScore(Score score)
private IBindable<WorkingBeatmap> beatmap { get; set; }
public void LoadScore([NotNull] Score score)
{ {
if (Score != null) if (Score != null)
throw new InvalidOperationException($"Cannot load a new score on a {nameof(PlayerArea)} that has an existing score."); throw new InvalidOperationException($"Cannot load a new score on a {nameof(PlayerArea)} that has an existing score.");