1
0
mirror of https://github.com/ppy/osu.git synced 2024-09-29 21:07:27 +08:00
osu-lazer/osu.Game/Screens/OnlinePlay/Multiplayer/Match/MultiplayerReadyButton.cs

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

222 lines
6.7 KiB
C#
Raw Normal View History

2022-03-23 09:37:53 +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;
using System.Linq;
using JetBrains.Annotations;
using osu.Framework.Allocation;
2022-04-01 20:33:57 +08:00
using osu.Framework.Audio;
using osu.Framework.Audio.Sample;
2022-03-23 09:37:53 +08:00
using osu.Framework.Localisation;
using osu.Framework.Threading;
2022-03-23 09:37:53 +08:00
using osu.Game.Graphics;
using osu.Game.Graphics.Backgrounds;
using osu.Game.Online.Multiplayer;
using osu.Game.Screens.OnlinePlay.Components;
2022-03-23 09:37:53 +08:00
namespace osu.Game.Screens.OnlinePlay.Multiplayer.Match
{
public class MultiplayerReadyButton : ReadyButton
2022-03-23 09:37:53 +08:00
{
public new Triangles Triangles => base.Triangles;
[Resolved]
private MultiplayerClient multiplayerClient { get; set; }
[Resolved]
private OsuColour colours { get; set; }
[CanBeNull]
private MultiplayerRoom room => multiplayerClient.Room;
2022-04-01 20:33:57 +08:00
private Sample countdownTickSample;
private Sample countdownTickFinalSample;
[BackgroundDependencyLoader]
private void load(AudioManager audio)
{
countdownTickSample = audio.Samples.Get(@"Multiplayer/countdown-tick");
countdownTickFinalSample = audio.Samples.Get(@"Multiplayer/countdown-tick-final");
}
2022-03-23 09:37:53 +08:00
protected override void LoadComplete()
{
base.LoadComplete();
2022-03-24 16:11:08 +08:00
multiplayerClient.RoomUpdated += onRoomUpdated;
2022-03-23 09:37:53 +08:00
onRoomUpdated();
}
private MultiplayerCountdown countdown;
private DateTimeOffset countdownChangeTime;
private ScheduledDelegate countdownUpdateDelegate;
2022-03-23 09:37:53 +08:00
2022-03-24 16:11:08 +08:00
private void onRoomUpdated() => Scheduler.AddOnce(() =>
2022-03-23 09:37:53 +08:00
{
if (countdown != room?.Countdown)
{
countdown = room?.Countdown;
countdownChangeTime = DateTimeOffset.Now;
}
scheduleNextCountdownUpdate();
updateButtonText();
updateButtonColour();
});
private void scheduleNextCountdownUpdate()
{
if (countdown != null)
{
// If a countdown is active, schedule relevant components to update on the next whole second.
double timeToNextSecond = countdownTimeRemaining.TotalMilliseconds % 1000;
countdownUpdateDelegate = Scheduler.AddDelayed(onCountdownTick, timeToNextSecond);
}
else
{
countdownUpdateDelegate?.Cancel();
countdownUpdateDelegate = null;
}
void onCountdownTick()
{
updateButtonText();
int secondsRemaining = countdownTimeRemaining.Seconds;
if (secondsRemaining < 10) countdownTickSample?.Play();
if (secondsRemaining <= 3) countdownTickFinalSample?.Play();
scheduleNextCountdownUpdate();
}
}
2022-03-23 09:37:53 +08:00
private void updateButtonText()
{
if (room == null)
{
Text = "Ready";
return;
}
var localUser = multiplayerClient.LocalUser;
int countReady = room.Users.Count(u => u.State == MultiplayerUserState.Ready);
int countTotal = room.Users.Count(u => u.State != MultiplayerUserState.Spectating);
string countText = $"({countReady} / {countTotal} ready)";
if (countdown != null)
2022-03-23 09:37:53 +08:00
{
string countdownText = $"Starting in {countdownTimeRemaining:mm\\:ss}";
2022-03-23 09:37:53 +08:00
switch (localUser?.State)
{
default:
Text = $"Ready ({countdownText.ToLowerInvariant()})";
break;
case MultiplayerUserState.Spectating:
case MultiplayerUserState.Ready:
Text = $"{countdownText} {countText}";
break;
}
}
else
{
switch (localUser?.State)
{
default:
Text = "Ready";
break;
case MultiplayerUserState.Spectating:
case MultiplayerUserState.Ready:
Text = room.Host?.Equals(localUser) == true
? $"Start match {countText}"
: $"Waiting for host... {countText}";
break;
}
}
}
private TimeSpan countdownTimeRemaining
{
get
{
TimeSpan timeElapsed = DateTimeOffset.Now - countdownChangeTime;
TimeSpan remaining;
if (timeElapsed > countdown.TimeRemaining)
remaining = TimeSpan.Zero;
else
remaining = countdown.TimeRemaining - timeElapsed;
return remaining;
}
}
2022-03-23 09:37:53 +08:00
private void updateButtonColour()
{
if (room == null)
{
setGreen();
return;
}
var localUser = multiplayerClient.LocalUser;
switch (localUser?.State)
{
default:
setGreen();
break;
case MultiplayerUserState.Spectating:
case MultiplayerUserState.Ready:
if (room?.Host?.Equals(localUser) == true && room.Countdown == null)
setGreen();
else
setYellow();
break;
}
void setYellow()
{
BackgroundColour = colours.YellowDark;
Triangles.ColourDark = colours.YellowDark;
Triangles.ColourLight = colours.Yellow;
}
void setGreen()
{
BackgroundColour = colours.Green;
Triangles.ColourDark = colours.Green;
Triangles.ColourLight = colours.GreenLight;
}
}
protected override void Dispose(bool isDisposing)
{
base.Dispose(isDisposing);
if (multiplayerClient != null)
multiplayerClient.RoomUpdated -= onRoomUpdated;
}
public override LocalisableString TooltipText
{
get
{
2022-03-25 14:41:01 +08:00
if (room?.Countdown != null && multiplayerClient.IsHost && multiplayerClient.LocalUser?.State == MultiplayerUserState.Ready && !room.Settings.AutoStartEnabled)
2022-03-23 09:37:53 +08:00
return "Cancel countdown";
return base.TooltipText;
}
}
}
}