1
0
mirror of https://github.com/ppy/osu.git synced 2025-01-18 20:13:21 +08:00

Make Room.Status non-bindable

This commit is contained in:
Dan Balasescu 2024-11-13 18:48:13 +09:00
parent 81e4cb348f
commit 5d4838a08b
No known key found for this signature in database
9 changed files with 84 additions and 44 deletions

View File

@ -76,7 +76,7 @@ namespace osu.Game.Tests.Visual.Multiplayer
createLoungeRoom(new Room createLoungeRoom(new Room
{ {
Name = "Multiplayer room", Name = "Multiplayer room",
Status = { Value = new RoomStatusOpen() }, Status = new RoomStatusOpen(),
EndDate = { Value = DateTimeOffset.Now.AddDays(1) }, EndDate = { Value = DateTimeOffset.Now.AddDays(1) },
Type = MatchType.HeadToHead, Type = MatchType.HeadToHead,
Playlist = { item1 }, Playlist = { item1 },
@ -85,7 +85,7 @@ namespace osu.Game.Tests.Visual.Multiplayer
createLoungeRoom(new Room createLoungeRoom(new Room
{ {
Name = "Private room", Name = "Private room",
Status = { Value = new RoomStatusOpenPrivate() }, Status = new RoomStatusOpenPrivate(),
HasPassword = { Value = true }, HasPassword = { Value = true },
EndDate = { Value = DateTimeOffset.Now.AddDays(1) }, EndDate = { Value = DateTimeOffset.Now.AddDays(1) },
Type = MatchType.HeadToHead, Type = MatchType.HeadToHead,
@ -95,7 +95,7 @@ namespace osu.Game.Tests.Visual.Multiplayer
createLoungeRoom(new Room createLoungeRoom(new Room
{ {
Name = "Playlist room with multiple beatmaps", Name = "Playlist room with multiple beatmaps",
Status = { Value = new RoomStatusPlaying() }, Status = new RoomStatusPlaying(),
EndDate = { Value = DateTimeOffset.Now.AddDays(1) }, EndDate = { Value = DateTimeOffset.Now.AddDays(1) },
Playlist = { item1, item2 }, Playlist = { item1, item2 },
CurrentPlaylistItem = item1 CurrentPlaylistItem = item1
@ -103,19 +103,19 @@ namespace osu.Game.Tests.Visual.Multiplayer
createLoungeRoom(new Room createLoungeRoom(new Room
{ {
Name = "Finished room", Name = "Finished room",
Status = { Value = new RoomStatusEnded() }, Status = new RoomStatusEnded(),
EndDate = { Value = DateTimeOffset.Now }, EndDate = { Value = DateTimeOffset.Now },
}), }),
createLoungeRoom(new Room createLoungeRoom(new Room
{ {
Name = "Spotlight room", Name = "Spotlight room",
Status = { Value = new RoomStatusOpen() }, Status = new RoomStatusOpen(),
Category = RoomCategory.Spotlight, Category = RoomCategory.Spotlight,
}), }),
createLoungeRoom(new Room createLoungeRoom(new Room
{ {
Name = "Featured artist room", Name = "Featured artist room",
Status = { Value = new RoomStatusOpen() }, Status = new RoomStatusOpen(),
Category = RoomCategory.FeaturedArtist, Category = RoomCategory.FeaturedArtist,
}), }),
} }
@ -136,7 +136,7 @@ namespace osu.Game.Tests.Visual.Multiplayer
AddStep("create room", () => Child = drawableRoom = createLoungeRoom(room = new Room AddStep("create room", () => Child = drawableRoom = createLoungeRoom(room = new Room
{ {
Name = "Room with password", Name = "Room with password",
Status = { Value = new RoomStatusOpen() }, Status = new RoomStatusOpen(),
Type = MatchType.HeadToHead, Type = MatchType.HeadToHead,
})); }));

View File

@ -397,15 +397,15 @@ namespace osu.Game.Online.Multiplayer
switch (state) switch (state)
{ {
case MultiplayerRoomState.Open: case MultiplayerRoomState.Open:
APIRoom.Status.Value = APIRoom.HasPassword.Value ? new RoomStatusOpenPrivate() : new RoomStatusOpen(); APIRoom.Status = APIRoom.HasPassword.Value ? new RoomStatusOpenPrivate() : new RoomStatusOpen();
break; break;
case MultiplayerRoomState.Playing: case MultiplayerRoomState.Playing:
APIRoom.Status.Value = new RoomStatusPlaying(); APIRoom.Status = new RoomStatusPlaying();
break; break;
case MultiplayerRoomState.Closed: case MultiplayerRoomState.Closed:
APIRoom.Status.Value = new RoomStatusEnded(); APIRoom.Status = new RoomStatusEnded();
break; break;
} }
@ -843,7 +843,7 @@ namespace osu.Game.Online.Multiplayer
Room.Settings = settings; Room.Settings = settings;
APIRoom.Name = Room.Settings.Name; APIRoom.Name = Room.Settings.Name;
APIRoom.Password.Value = Room.Settings.Password; APIRoom.Password.Value = Room.Settings.Password;
APIRoom.Status.Value = string.IsNullOrEmpty(Room.Settings.Password) ? new RoomStatusOpen() : new RoomStatusOpenPrivate(); APIRoom.Status = string.IsNullOrEmpty(Room.Settings.Password) ? new RoomStatusOpen() : new RoomStatusOpenPrivate();
APIRoom.Type = Room.Settings.MatchType; APIRoom.Type = Room.Settings.MatchType;
APIRoom.QueueMode.Value = Room.Settings.QueueMode; APIRoom.QueueMode.Value = Room.Settings.QueueMode;
APIRoom.AutoStartDuration.Value = Room.Settings.AutoStartDuration; APIRoom.AutoStartDuration.Value = Room.Settings.AutoStartDuration;

View File

@ -45,11 +45,11 @@ namespace osu.Game.Online.Rooms
foreach (var room in Response) foreach (var room in Response)
{ {
if (room.EndDate.Value != null && DateTimeOffset.Now >= room.EndDate.Value) if (room.EndDate.Value != null && DateTimeOffset.Now >= room.EndDate.Value)
room.Status.Value = new RoomStatusEnded(); room.Status = new RoomStatusEnded();
else if (room.HasPassword.Value) else if (room.HasPassword.Value)
room.Status.Value = new RoomStatusOpenPrivate(); room.Status = new RoomStatusOpenPrivate();
else else
room.Status.Value = new RoomStatusOpen(); room.Status = new RoomStatusOpen();
} }
} }
} }

View File

@ -78,6 +78,15 @@ namespace osu.Game.Online.Rooms
set => SetField(ref currentPlaylistItem, value); set => SetField(ref currentPlaylistItem, value);
} }
/// <summary>
/// The current room status.
/// </summary>
public RoomStatus Status
{
get => status;
set => SetField(ref status, value);
}
[JsonProperty("id")] [JsonProperty("id")]
private long? roomId; private long? roomId;
@ -98,6 +107,9 @@ namespace osu.Game.Online.Rooms
[JsonProperty("current_playlist_item")] [JsonProperty("current_playlist_item")]
private PlaylistItem? currentPlaylistItem; private PlaylistItem? currentPlaylistItem;
// Not serialised (see: GetRoomsRequest).
private RoomStatus status = new RoomStatusOpen();
[Cached] [Cached]
[JsonProperty("playlist")] [JsonProperty("playlist")]
public readonly BindableList<PlaylistItem> Playlist = new BindableList<PlaylistItem>(); public readonly BindableList<PlaylistItem> Playlist = new BindableList<PlaylistItem>();
@ -117,9 +129,6 @@ namespace osu.Game.Online.Rooms
[Cached] [Cached]
public readonly Bindable<int?> MaxAttempts = new Bindable<int?>(); public readonly Bindable<int?> MaxAttempts = new Bindable<int?>();
[Cached]
public readonly Bindable<RoomStatus> Status = new Bindable<RoomStatus>(new RoomStatusOpen());
[Cached] [Cached]
public readonly Bindable<RoomAvailability> Availability = new Bindable<RoomAvailability>(); public readonly Bindable<RoomAvailability> Availability = new Bindable<RoomAvailability>();
@ -231,7 +240,7 @@ namespace osu.Game.Online.Rooms
Host = other.Host; Host = other.Host;
ChannelId.Value = other.ChannelId.Value; ChannelId.Value = other.ChannelId.Value;
Status.Value = other.Status.Value; Status = other.Status;
Availability.Value = other.Availability.Value; Availability.Value = other.Availability.Value;
HasPassword.Value = other.HasPassword.Value; HasPassword.Value = other.HasPassword.Value;
Type = other.Type; Type = other.Type;
@ -266,7 +275,7 @@ namespace osu.Game.Online.Rooms
// Todo: This is not the best way/place to do this, but the intention is to display all playlist items when the room has ended, // Todo: This is not the best way/place to do this, but the intention is to display all playlist items when the room has ended,
// and display only the non-expired playlist items while the room is still active. In order to achieve this, all expired items are removed from the source Room. // and display only the non-expired playlist items while the room is still active. In order to achieve this, all expired items are removed from the source Room.
// More refactoring is required before this can be done locally instead - DrawableRoomPlaylist is currently directly bound to the playlist to display items in the room. // More refactoring is required before this can be done locally instead - DrawableRoomPlaylist is currently directly bound to the playlist to display items in the room.
if (!(Status.Value is RoomStatusEnded)) if (Status is not RoomStatusEnded)
Playlist.RemoveAll(i => i.Expired); Playlist.RemoveAll(i => i.Expired);
} }

View File

@ -1,22 +1,21 @@
// 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.
using System.ComponentModel;
using osu.Framework.Allocation; using osu.Framework.Allocation;
using osu.Framework.Bindables;
using osu.Framework.Graphics; using osu.Framework.Graphics;
using osu.Framework.Graphics.Containers;
using osu.Game.Graphics; using osu.Game.Graphics;
using osu.Game.Online.Rooms; using osu.Game.Online.Rooms;
using Container = osu.Framework.Graphics.Containers.Container;
namespace osu.Game.Screens.OnlinePlay.Components namespace osu.Game.Screens.OnlinePlay.Components
{ {
public partial class StatusColouredContainer : Container public partial class StatusColouredContainer : Container
{ {
[Resolved]
private OsuColour colours { get; set; } = null!;
private readonly double transitionDuration; private readonly double transitionDuration;
[Resolved(typeof(Room), nameof(Room.Status))]
private Bindable<RoomStatus> status { get; set; } = null!;
private readonly Room room; private readonly Room room;
public StatusColouredContainer(Room room, double transitionDuration = 100) public StatusColouredContainer(Room room, double transitionDuration = 100)
@ -25,13 +24,29 @@ namespace osu.Game.Screens.OnlinePlay.Components
this.transitionDuration = transitionDuration; this.transitionDuration = transitionDuration;
} }
[BackgroundDependencyLoader] protected override void LoadComplete()
private void load(OsuColour colours)
{ {
status.BindValueChanged(s => base.LoadComplete();
{
this.FadeColour(colours.ForRoomCategory(room.Category) ?? s.NewValue.GetAppropriateColour(colours), transitionDuration); room.PropertyChanged += onRoomPropertyChanged;
}, true); updateRoomStatus();
}
private void onRoomPropertyChanged(object? sender, PropertyChangedEventArgs e)
{
if (e.PropertyName == nameof(Room.Status))
updateRoomStatus();
}
private void updateRoomStatus()
{
this.FadeColour(colours.ForRoomCategory(room.Category) ?? room.Status.GetAppropriateColour(colours), transitionDuration);
}
protected override void Dispose(bool isDisposing)
{
base.Dispose(isDisposing);
room.PropertyChanged -= onRoomPropertyChanged;
} }
} }
} }

View File

@ -159,7 +159,7 @@ namespace osu.Game.Screens.OnlinePlay.Lounge.Components
Spacing = new Vector2(5), Spacing = new Vector2(5),
Children = new Drawable[] Children = new Drawable[]
{ {
new RoomStatusPill new RoomStatusPill(Room)
{ {
Anchor = Anchor.CentreLeft, Anchor = Anchor.CentreLeft,
Origin = Anchor.CentreLeft Origin = Anchor.CentreLeft

View File

@ -1,6 +1,7 @@
// 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.
using System.ComponentModel;
using osu.Framework.Allocation; using osu.Framework.Allocation;
using osu.Framework.Graphics; using osu.Framework.Graphics;
using osu.Framework.Graphics.Sprites; using osu.Framework.Graphics.Sprites;
@ -19,25 +20,43 @@ namespace osu.Game.Screens.OnlinePlay.Lounge.Components
protected override FontUsage Font => base.Font.With(weight: FontWeight.SemiBold); protected override FontUsage Font => base.Font.With(weight: FontWeight.SemiBold);
private readonly Room room;
public RoomStatusPill(Room room)
{
this.room = room;
}
protected override void LoadComplete() protected override void LoadComplete()
{ {
base.LoadComplete(); base.LoadComplete();
EndDate.BindValueChanged(_ => updateDisplay());
Status.BindValueChanged(_ => updateDisplay(), true);
FinishTransforms(true);
TextFlow.Colour = Colour4.Black; TextFlow.Colour = Colour4.Black;
Pill.Background.Alpha = 1; Pill.Background.Alpha = 1;
EndDate.BindValueChanged(_ => updateDisplay());
room.PropertyChanged += onRoomPropertyChanged;
updateDisplay();
FinishTransforms(true);
}
private void onRoomPropertyChanged(object? sender, PropertyChangedEventArgs e)
{
if (e.PropertyName == nameof(Room.Status))
updateDisplay();
} }
private void updateDisplay() private void updateDisplay()
{ {
RoomStatus status = Status.Value; Pill.Background.FadeColour(room.Status.GetAppropriateColour(colours), 100);
TextFlow.Text = room.Status.Message;
}
Pill.Background.FadeColour(status.GetAppropriateColour(colours), 100); protected override void Dispose(bool isDisposing)
TextFlow.Text = status.Message; {
base.Dispose(isDisposing);
room.PropertyChanged -= onRoomPropertyChanged;
} }
} }
} }

View File

@ -31,7 +31,7 @@ namespace osu.Game.Screens.OnlinePlay.Multiplayer
// this is done here as a pre-check to avoid clicking on already closed rooms in the lounge from triggering a server join. // this is done here as a pre-check to avoid clicking on already closed rooms in the lounge from triggering a server join.
// should probably be done at a higher level, but due to the current structure of things this is the easiest place for now. // should probably be done at a higher level, but due to the current structure of things this is the easiest place for now.
if (room.Status.Value is RoomStatusEnded) if (room.Status is RoomStatusEnded)
{ {
onError?.Invoke("Cannot join an ended room."); onError?.Invoke("Cannot join an ended room.");
return; return;

View File

@ -16,9 +16,6 @@ namespace osu.Game.Screens.OnlinePlay
/// </summary> /// </summary>
public partial class OnlinePlayComposite : CompositeDrawable public partial class OnlinePlayComposite : CompositeDrawable
{ {
[Resolved(typeof(Room))]
protected Bindable<RoomStatus> Status { get; private set; } = null!;
[Resolved(typeof(Room))] [Resolved(typeof(Room))]
protected Bindable<Room.RoomPlaylistItemStats> PlaylistItemStats { get; private set; } = null!; protected Bindable<Room.RoomPlaylistItemStats> PlaylistItemStats { get; private set; } = null!;