mirror of
https://github.com/osukey/osukey.git
synced 2025-05-17 03:27:21 +09:00
Merge branch 'timeshift-api-integration'
This commit is contained in:
commit
2aafaf9ce2
@ -1,135 +0,0 @@
|
|||||||
// Copyright (c) 2007-2018 ppy Pty Ltd <contact@ppy.sh>.
|
|
||||||
// Licensed under the MIT Licence - https://raw.githubusercontent.com/ppy/osu/master/LICENCE
|
|
||||||
|
|
||||||
using NUnit.Framework;
|
|
||||||
using osu.Framework.Allocation;
|
|
||||||
using osu.Framework.Graphics;
|
|
||||||
using osu.Framework.Graphics.Containers;
|
|
||||||
using osu.Game.Beatmaps;
|
|
||||||
using osu.Game.Graphics.UserInterface;
|
|
||||||
using osu.Game.Online.Multiplayer;
|
|
||||||
using osu.Game.Rulesets;
|
|
||||||
using osu.Game.Screens.Multi.Lounge.Components;
|
|
||||||
using osu.Game.Users;
|
|
||||||
|
|
||||||
namespace osu.Game.Tests.Visual
|
|
||||||
{
|
|
||||||
[TestFixture]
|
|
||||||
public class TestCaseDrawableRoom : OsuTestCase
|
|
||||||
{
|
|
||||||
private RulesetStore rulesets;
|
|
||||||
|
|
||||||
protected override void LoadComplete()
|
|
||||||
{
|
|
||||||
base.LoadComplete();
|
|
||||||
|
|
||||||
DrawableRoom first;
|
|
||||||
Add(new FillFlowContainer
|
|
||||||
{
|
|
||||||
Anchor = Anchor.Centre,
|
|
||||||
Origin = Anchor.Centre,
|
|
||||||
AutoSizeAxes = Axes.Y,
|
|
||||||
Width = 580f,
|
|
||||||
Direction = FillDirection.Vertical,
|
|
||||||
Children = new Drawable[]
|
|
||||||
{
|
|
||||||
first = new DrawableRoom(new Room
|
|
||||||
{
|
|
||||||
Name = { Value = @"Great Room Right Here" },
|
|
||||||
Host = { Value = new User { Username = @"Naeferith", Id = 9492835, Country = new Country { FlagName = @"FR" } } },
|
|
||||||
Status = { Value = new RoomStatusOpen() },
|
|
||||||
Type = { Value = new GameTypeTeamVersus() },
|
|
||||||
Beatmap =
|
|
||||||
{
|
|
||||||
Value = new BeatmapInfo
|
|
||||||
{
|
|
||||||
StarDifficulty = 4.65,
|
|
||||||
Ruleset = rulesets.GetRuleset(3),
|
|
||||||
Metadata = new BeatmapMetadata
|
|
||||||
{
|
|
||||||
Title = @"Critical Crystal",
|
|
||||||
Artist = @"Seiryu",
|
|
||||||
},
|
|
||||||
BeatmapSet = new BeatmapSetInfo
|
|
||||||
{
|
|
||||||
OnlineInfo = new BeatmapSetOnlineInfo
|
|
||||||
{
|
|
||||||
Covers = new BeatmapSetOnlineCovers
|
|
||||||
{
|
|
||||||
Cover = @"https://assets.ppy.sh//beatmaps/376340/covers/cover.jpg?1456478455",
|
|
||||||
},
|
|
||||||
},
|
|
||||||
},
|
|
||||||
},
|
|
||||||
},
|
|
||||||
Participants =
|
|
||||||
{
|
|
||||||
Value = new[]
|
|
||||||
{
|
|
||||||
new User { Statistics = new UserStatistics { Ranks = new UserStatistics.UserRanks { Global = 1355 } } },
|
|
||||||
new User { Statistics = new UserStatistics { Ranks = new UserStatistics.UserRanks { Global = 8756 } } },
|
|
||||||
},
|
|
||||||
},
|
|
||||||
}),
|
|
||||||
new DrawableRoom(new Room
|
|
||||||
{
|
|
||||||
Name = { Value = @"Relax It's The Weekend" },
|
|
||||||
Host = { Value = new User { Username = @"peppy", Id = 2, Country = new Country { FlagName = @"AU" } } },
|
|
||||||
Status = { Value = new RoomStatusPlaying() },
|
|
||||||
Type = { Value = new GameTypeTagTeam() },
|
|
||||||
Beatmap =
|
|
||||||
{
|
|
||||||
Value = new BeatmapInfo
|
|
||||||
{
|
|
||||||
StarDifficulty = 1.96,
|
|
||||||
Ruleset = rulesets.GetRuleset(0),
|
|
||||||
Metadata = new BeatmapMetadata
|
|
||||||
{
|
|
||||||
Title = @"Serendipity",
|
|
||||||
Artist = @"ZAQ",
|
|
||||||
},
|
|
||||||
BeatmapSet = new BeatmapSetInfo
|
|
||||||
{
|
|
||||||
OnlineInfo = new BeatmapSetOnlineInfo
|
|
||||||
{
|
|
||||||
Covers = new BeatmapSetOnlineCovers
|
|
||||||
{
|
|
||||||
Cover = @"https://assets.ppy.sh//beatmaps/526839/covers/cover.jpg?1493815706",
|
|
||||||
},
|
|
||||||
},
|
|
||||||
},
|
|
||||||
},
|
|
||||||
},
|
|
||||||
Participants =
|
|
||||||
{
|
|
||||||
Value = new[]
|
|
||||||
{
|
|
||||||
new User { Statistics = new UserStatistics { Ranks = new UserStatistics.UserRanks { Global = 578975 } } },
|
|
||||||
new User { Statistics = new UserStatistics { Ranks = new UserStatistics.UserRanks { Global = 24554 } } },
|
|
||||||
},
|
|
||||||
},
|
|
||||||
}),
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
AddStep(@"select", () => first.State = SelectionState.Selected);
|
|
||||||
AddStep(@"change title", () => first.Room.Name.Value = @"I Changed Name");
|
|
||||||
AddStep(@"change host", () => first.Room.Host.Value = new User { Username = @"DrabWeb", Id = 6946022, Country = new Country { FlagName = @"CA" } });
|
|
||||||
AddStep(@"change status", () => first.Room.Status.Value = new RoomStatusPlaying());
|
|
||||||
AddStep(@"change type", () => first.Room.Type.Value = new GameTypeVersus());
|
|
||||||
AddStep(@"change beatmap", () => first.Room.Beatmap.Value = null);
|
|
||||||
AddStep(@"change participants", () => first.Room.Participants.Value = new[]
|
|
||||||
{
|
|
||||||
new User { Statistics = new UserStatistics { Ranks = new UserStatistics.UserRanks { Global = 1254 } } },
|
|
||||||
new User { Statistics = new UserStatistics { Ranks = new UserStatistics.UserRanks { Global = 123189 } } },
|
|
||||||
});
|
|
||||||
AddStep(@"deselect", () => first.State = SelectionState.NotSelected);
|
|
||||||
}
|
|
||||||
|
|
||||||
[BackgroundDependencyLoader]
|
|
||||||
private void load(RulesetStore rulesets)
|
|
||||||
{
|
|
||||||
this.rulesets = rulesets;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,208 +0,0 @@
|
|||||||
// Copyright (c) 2007-2018 ppy Pty Ltd <contact@ppy.sh>.
|
|
||||||
// Licensed under the MIT Licence - https://raw.githubusercontent.com/ppy/osu/master/LICENCE
|
|
||||||
|
|
||||||
using NUnit.Framework;
|
|
||||||
using osu.Framework.Allocation;
|
|
||||||
using osu.Game.Beatmaps;
|
|
||||||
using osu.Game.Online.Multiplayer;
|
|
||||||
using osu.Game.Rulesets;
|
|
||||||
using osu.Game.Screens;
|
|
||||||
using osu.Game.Screens.Backgrounds;
|
|
||||||
using osu.Game.Screens.Multi;
|
|
||||||
using osu.Game.Screens.Multi.Lounge;
|
|
||||||
using osu.Game.Screens.Multi.Lounge.Components;
|
|
||||||
using osu.Game.Users;
|
|
||||||
using osuTK.Input;
|
|
||||||
|
|
||||||
namespace osu.Game.Tests.Visual
|
|
||||||
{
|
|
||||||
[TestFixture]
|
|
||||||
public class TestCaseLounge : ManualInputManagerTestCase
|
|
||||||
{
|
|
||||||
private TestLoungeScreen loungeScreen;
|
|
||||||
|
|
||||||
[BackgroundDependencyLoader]
|
|
||||||
private void load(RulesetStore rulesets)
|
|
||||||
{
|
|
||||||
loungeScreen = new TestLoungeScreen();
|
|
||||||
|
|
||||||
Room[] rooms =
|
|
||||||
{
|
|
||||||
new Room
|
|
||||||
{
|
|
||||||
Name = { Value = @"Just Another Room" },
|
|
||||||
Host = { Value = new User { Username = @"DrabWeb", Id = 6946022, Country = new Country { FlagName = @"CA" } } },
|
|
||||||
Status = { Value = new RoomStatusPlaying() },
|
|
||||||
Availability = { Value = RoomAvailability.Public },
|
|
||||||
Type = { Value = new GameTypeTagTeam() },
|
|
||||||
Beatmap =
|
|
||||||
{
|
|
||||||
Value = new BeatmapInfo
|
|
||||||
{
|
|
||||||
StarDifficulty = 5.65,
|
|
||||||
Ruleset = rulesets.GetRuleset(0),
|
|
||||||
Metadata = new BeatmapMetadata
|
|
||||||
{
|
|
||||||
Title = @"Sidetracked Day (Short Ver.)",
|
|
||||||
Artist = @"VINXIS",
|
|
||||||
AuthorString = @"Hobbes2",
|
|
||||||
},
|
|
||||||
BeatmapSet = new BeatmapSetInfo
|
|
||||||
{
|
|
||||||
OnlineInfo = new BeatmapSetOnlineInfo
|
|
||||||
{
|
|
||||||
Covers = new BeatmapSetOnlineCovers
|
|
||||||
{
|
|
||||||
Cover = @"https://assets.ppy.sh/beatmaps/767600/covers/cover.jpg?1526243446",
|
|
||||||
},
|
|
||||||
},
|
|
||||||
},
|
|
||||||
}
|
|
||||||
},
|
|
||||||
MaxParticipants = { Value = 10 },
|
|
||||||
Participants =
|
|
||||||
{
|
|
||||||
Value = new[]
|
|
||||||
{
|
|
||||||
new User { Username = @"flyte", Id = 3103765, Statistics = new UserStatistics { Ranks = new UserStatistics.UserRanks { Global = 142 } } },
|
|
||||||
new User { Username = @"Cookiezi", Id = 124493, Statistics = new UserStatistics { Ranks = new UserStatistics.UserRanks { Global = 546 } } },
|
|
||||||
new User { Username = @"Angelsim", Id = 1777162, Statistics = new UserStatistics { Ranks = new UserStatistics.UserRanks { Global = 287 } } },
|
|
||||||
new User { Username = @"Rafis", Id = 2558286, Statistics = new UserStatistics { Ranks = new UserStatistics.UserRanks { Global = 468 } } },
|
|
||||||
new User { Username = @"hvick225", Id = 50265, Statistics = new UserStatistics { Ranks = new UserStatistics.UserRanks { Global = 325 } } },
|
|
||||||
new User { Username = @"peppy", Id = 2, Statistics = new UserStatistics { Ranks = new UserStatistics.UserRanks { Global = 625 } } },
|
|
||||||
}
|
|
||||||
}
|
|
||||||
},
|
|
||||||
new Room
|
|
||||||
{
|
|
||||||
Name = { Value = @"Not Just Any Room" },
|
|
||||||
Host = { Value = new User { Username = @"Monstrata", Id = 2706438, Country = new Country { FlagName = @"CA" } } },
|
|
||||||
Status = { Value = new RoomStatusOpen() },
|
|
||||||
Availability = { Value = RoomAvailability.FriendsOnly },
|
|
||||||
Type = { Value = new GameTypeTeamVersus() },
|
|
||||||
Beatmap =
|
|
||||||
{
|
|
||||||
Value = new BeatmapInfo
|
|
||||||
{
|
|
||||||
StarDifficulty = 2.73,
|
|
||||||
Ruleset = rulesets.GetRuleset(0),
|
|
||||||
Metadata = new BeatmapMetadata
|
|
||||||
{
|
|
||||||
Title = @"lit(var)",
|
|
||||||
Artist = @"kensuke ushio",
|
|
||||||
AuthorString = @"Monstrata",
|
|
||||||
},
|
|
||||||
BeatmapSet = new BeatmapSetInfo
|
|
||||||
{
|
|
||||||
OnlineInfo = new BeatmapSetOnlineInfo
|
|
||||||
{
|
|
||||||
Covers = new BeatmapSetOnlineCovers
|
|
||||||
{
|
|
||||||
Cover = @"https://assets.ppy.sh/beatmaps/623972/covers/cover.jpg?1521167183",
|
|
||||||
},
|
|
||||||
},
|
|
||||||
},
|
|
||||||
}
|
|
||||||
},
|
|
||||||
Participants =
|
|
||||||
{
|
|
||||||
Value = new[]
|
|
||||||
{
|
|
||||||
new User { Username = @"Jeby", Id = 3136279, Statistics = new UserStatistics { Ranks = new UserStatistics.UserRanks { Global = 3497 } } },
|
|
||||||
new User { Username = @"DualAkira", Id = 5220933, Statistics = new UserStatistics { Ranks = new UserStatistics.UserRanks { Global = 643 } } },
|
|
||||||
new User { Username = @"Datenshi Yohane", Id = 7171857, Statistics = new UserStatistics { Ranks = new UserStatistics.UserRanks { Global = 10555 } } },
|
|
||||||
}
|
|
||||||
}
|
|
||||||
},
|
|
||||||
new Room
|
|
||||||
{
|
|
||||||
Name = { Value = @"room THE FINAL" },
|
|
||||||
Host = { Value = new User { Username = @"Delis", Id = 1603923, Country = new Country { FlagName = @"JP" } } },
|
|
||||||
Status = { Value = new RoomStatusPlaying() },
|
|
||||||
Availability = { Value = RoomAvailability.Public },
|
|
||||||
Type = { Value = new GameTypeTagTeam() },
|
|
||||||
Beatmap =
|
|
||||||
{
|
|
||||||
Value = new BeatmapInfo
|
|
||||||
{
|
|
||||||
StarDifficulty = 4.48,
|
|
||||||
Ruleset = rulesets.GetRuleset(3),
|
|
||||||
Metadata = new BeatmapMetadata
|
|
||||||
{
|
|
||||||
Title = @"ONIGIRI FREEWAY",
|
|
||||||
Artist = @"OISHII",
|
|
||||||
AuthorString = @"Mentholzzz",
|
|
||||||
},
|
|
||||||
BeatmapSet = new BeatmapSetInfo
|
|
||||||
{
|
|
||||||
OnlineInfo = new BeatmapSetOnlineInfo
|
|
||||||
{
|
|
||||||
Covers = new BeatmapSetOnlineCovers
|
|
||||||
{
|
|
||||||
Cover = @"https://assets.ppy.sh/beatmaps/663098/covers/cover.jpg?1521898837",
|
|
||||||
},
|
|
||||||
},
|
|
||||||
},
|
|
||||||
}
|
|
||||||
},
|
|
||||||
MaxParticipants = { Value = 30 },
|
|
||||||
Participants =
|
|
||||||
{
|
|
||||||
Value = new[]
|
|
||||||
{
|
|
||||||
new User { Username = @"KizuA", Id = 6510442, Statistics = new UserStatistics { Ranks = new UserStatistics.UserRanks { Global = 5372 } } },
|
|
||||||
new User { Username = @"Colored", Id = 827563, Statistics = new UserStatistics { Ranks = new UserStatistics.UserRanks { Global = 810 } } },
|
|
||||||
new User { Username = @"Beryl", Id = 3817591, Statistics = new UserStatistics { Ranks = new UserStatistics.UserRanks { Global = 10096 } } },
|
|
||||||
}
|
|
||||||
}
|
|
||||||
},
|
|
||||||
};
|
|
||||||
|
|
||||||
AddStep(@"show", () => Add(loungeScreen));
|
|
||||||
selectAssert(0);
|
|
||||||
AddAssert(@"no room selected", () => loungeScreen.SelectedRoom == null);
|
|
||||||
selectAssert(1);
|
|
||||||
AddStep(@"open room 1", () => clickRoom(1));
|
|
||||||
AddUntilStep(() => loungeScreen.ChildScreen?.IsCurrentScreen == true, "wait until room current");
|
|
||||||
AddStep(@"make lounge current", loungeScreen.MakeCurrent);
|
|
||||||
filterAssert(@"THE FINAL", LoungeTab.Public, 1);
|
|
||||||
filterAssert(string.Empty, LoungeTab.Public, 2);
|
|
||||||
filterAssert(string.Empty, LoungeTab.Private, 1);
|
|
||||||
filterAssert(string.Empty, LoungeTab.Public, 2);
|
|
||||||
filterAssert(@"no matches", LoungeTab.Public, 0);
|
|
||||||
filterAssert(string.Empty, LoungeTab.Public, 2);
|
|
||||||
AddStep(@"exit", loungeScreen.Exit);
|
|
||||||
}
|
|
||||||
|
|
||||||
private void clickRoom(int n)
|
|
||||||
{
|
|
||||||
InputManager.Click(MouseButton.Left);
|
|
||||||
}
|
|
||||||
|
|
||||||
private void selectAssert(int n)
|
|
||||||
{
|
|
||||||
AddStep($@"select room {n}", () => clickRoom(n));
|
|
||||||
}
|
|
||||||
|
|
||||||
private void filterAssert(string filter, LoungeTab tab, int endCount)
|
|
||||||
{
|
|
||||||
AddStep($@"filter '{filter}', {tab}", () => loungeScreen.SetFilter(filter, tab));
|
|
||||||
}
|
|
||||||
|
|
||||||
private class TestLoungeScreen : LoungeScreen
|
|
||||||
{
|
|
||||||
protected override BackgroundScreen CreateBackground() => new BackgroundScreenDefault();
|
|
||||||
|
|
||||||
[Resolved]
|
|
||||||
private RoomManager manager { get; set; }
|
|
||||||
|
|
||||||
public Room SelectedRoom => manager.Current.Value;
|
|
||||||
|
|
||||||
public void SetFilter(string filter, LoungeTab tab)
|
|
||||||
{
|
|
||||||
Filter.Search.Current.Value = filter;
|
|
||||||
Filter.Tabs.Current.Value = tab;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,152 +0,0 @@
|
|||||||
// Copyright (c) 2007-2018 ppy Pty Ltd <contact@ppy.sh>.
|
|
||||||
// Licensed under the MIT Licence - https://raw.githubusercontent.com/ppy/osu/master/LICENCE
|
|
||||||
|
|
||||||
using System;
|
|
||||||
using System.Collections.Generic;
|
|
||||||
using NUnit.Framework;
|
|
||||||
using osu.Framework.Allocation;
|
|
||||||
using osu.Game.Beatmaps;
|
|
||||||
using osu.Game.Online.Multiplayer;
|
|
||||||
using osu.Game.Rulesets;
|
|
||||||
using osu.Game.Screens.Multi.Match;
|
|
||||||
using osu.Game.Screens.Multi.Match.Components;
|
|
||||||
using osu.Game.Users;
|
|
||||||
|
|
||||||
namespace osu.Game.Tests.Visual
|
|
||||||
{
|
|
||||||
[TestFixture]
|
|
||||||
public class TestCaseMatch : OsuTestCase
|
|
||||||
{
|
|
||||||
public override IReadOnlyList<Type> RequiredTypes => new[]
|
|
||||||
{
|
|
||||||
typeof(TestCaseMatch),
|
|
||||||
typeof(GameTypePicker),
|
|
||||||
typeof(RoomSettingsOverlay)
|
|
||||||
};
|
|
||||||
|
|
||||||
[BackgroundDependencyLoader]
|
|
||||||
private void load(RulesetStore rulesets)
|
|
||||||
{
|
|
||||||
Room room = new Room
|
|
||||||
{
|
|
||||||
Name = { Value = @"One Awesome Room" },
|
|
||||||
Status = { Value = new RoomStatusOpen() },
|
|
||||||
Availability = { Value = RoomAvailability.Public },
|
|
||||||
Type = { Value = new GameTypeTeamVersus() },
|
|
||||||
Beatmap =
|
|
||||||
{
|
|
||||||
Value = new BeatmapInfo
|
|
||||||
{
|
|
||||||
StarDifficulty = 5.02,
|
|
||||||
Ruleset = rulesets.GetRuleset(1),
|
|
||||||
Metadata = new BeatmapMetadata
|
|
||||||
{
|
|
||||||
Title = @"Paradigm Shift",
|
|
||||||
Artist = @"Morimori Atsushi",
|
|
||||||
AuthorString = @"eiri-",
|
|
||||||
},
|
|
||||||
BeatmapSet = new BeatmapSetInfo
|
|
||||||
{
|
|
||||||
OnlineInfo = new BeatmapSetOnlineInfo
|
|
||||||
{
|
|
||||||
Covers = new BeatmapSetOnlineCovers
|
|
||||||
{
|
|
||||||
Cover = @"https://assets.ppy.sh/beatmaps/765055/covers/cover.jpg?1526955337",
|
|
||||||
},
|
|
||||||
},
|
|
||||||
},
|
|
||||||
},
|
|
||||||
},
|
|
||||||
MaxParticipants = { Value = 5 },
|
|
||||||
Participants =
|
|
||||||
{
|
|
||||||
Value = new[]
|
|
||||||
{
|
|
||||||
new User
|
|
||||||
{
|
|
||||||
Username = @"eiri-",
|
|
||||||
Id = 3388410,
|
|
||||||
Country = new Country { FlagName = @"US" },
|
|
||||||
CoverUrl = @"https://assets.ppy.sh/user-profile-covers/3388410/00a8486a247831e1cc4375db519f611ac970bda8bc0057d78b0f540ea38c3e58.jpeg",
|
|
||||||
IsSupporter = true,
|
|
||||||
},
|
|
||||||
new User
|
|
||||||
{
|
|
||||||
Username = @"Nepuri",
|
|
||||||
Id = 6637817,
|
|
||||||
Country = new Country { FlagName = @"DE" },
|
|
||||||
CoverUrl = @"https://assets.ppy.sh/user-profile-covers/6637817/9085fc60248b6b5327a72c1dcdecf2dbedba810ae0ab6bcf7224e46b1339632a.jpeg",
|
|
||||||
IsSupporter = true,
|
|
||||||
},
|
|
||||||
new User
|
|
||||||
{
|
|
||||||
Username = @"goheegy",
|
|
||||||
Id = 8057655,
|
|
||||||
Country = new Country { FlagName = @"GB" },
|
|
||||||
CoverUrl = @"https://assets.ppy.sh/user-profile-covers/8057655/21cec27c25a11dc197a4ec6a74253dbabb495949b0e0697113352f12007018c5.jpeg",
|
|
||||||
},
|
|
||||||
new User
|
|
||||||
{
|
|
||||||
Username = @"Alumetri",
|
|
||||||
Id = 5371497,
|
|
||||||
Country = new Country { FlagName = @"RU" },
|
|
||||||
CoverUrl = @"https://assets.ppy.sh/user-profile-covers/5371497/e023b8c7fbe3613e64bd4856703517ea50fbed8a5805dc9acda9efe9897c67e2.jpeg",
|
|
||||||
},
|
|
||||||
}
|
|
||||||
},
|
|
||||||
};
|
|
||||||
|
|
||||||
MatchScreen matchScreen = new MatchScreen(room);
|
|
||||||
|
|
||||||
AddStep(@"show", () => Add(matchScreen));
|
|
||||||
AddStep(@"null beatmap", () => room.Beatmap.Value = null);
|
|
||||||
AddStep(@"change name", () => room.Name.Value = @"Two Awesome Rooms");
|
|
||||||
AddStep(@"change status", () => room.Status.Value = new RoomStatusPlaying());
|
|
||||||
AddStep(@"change availability", () => room.Availability.Value = RoomAvailability.FriendsOnly);
|
|
||||||
AddStep(@"change type", () => room.Type.Value = new GameTypeTag());
|
|
||||||
AddStep(@"change beatmap", () => room.Beatmap.Value = new BeatmapInfo
|
|
||||||
{
|
|
||||||
StarDifficulty = 4.33,
|
|
||||||
Ruleset = rulesets.GetRuleset(2),
|
|
||||||
Metadata = new BeatmapMetadata
|
|
||||||
{
|
|
||||||
Title = @"Yasashisa no Riyuu",
|
|
||||||
Artist = @"ChouCho",
|
|
||||||
AuthorString = @"celerih",
|
|
||||||
},
|
|
||||||
BeatmapSet = new BeatmapSetInfo
|
|
||||||
{
|
|
||||||
OnlineInfo = new BeatmapSetOnlineInfo
|
|
||||||
{
|
|
||||||
Covers = new BeatmapSetOnlineCovers
|
|
||||||
{
|
|
||||||
Cover = @"https://assets.ppy.sh/beatmaps/685391/covers/cover.jpg?1524597970",
|
|
||||||
},
|
|
||||||
},
|
|
||||||
},
|
|
||||||
});
|
|
||||||
|
|
||||||
AddStep(@"null max participants", () => room.MaxParticipants.Value = null);
|
|
||||||
AddStep(@"change participants", () => room.Participants.Value = new[]
|
|
||||||
{
|
|
||||||
new User
|
|
||||||
{
|
|
||||||
Username = @"Spectator",
|
|
||||||
Id = 702598,
|
|
||||||
Country = new Country { FlagName = @"KR" },
|
|
||||||
CoverUrl = @"https://assets.ppy.sh/user-profile-covers/702598/3bbf4cb8b8d2cf8b03145000a975ff27e191ab99b0920832e7dd67386280e288.jpeg",
|
|
||||||
IsSupporter = true,
|
|
||||||
},
|
|
||||||
new User
|
|
||||||
{
|
|
||||||
Username = @"celerih",
|
|
||||||
Id = 4696296,
|
|
||||||
Country = new Country { FlagName = @"CA" },
|
|
||||||
CoverUrl = @"https://assets.ppy.sh/user-profile-covers/4696296/7f8500731d0ac66d5472569d146a7be07d9460273361913f22c038867baddaef.jpeg",
|
|
||||||
},
|
|
||||||
});
|
|
||||||
|
|
||||||
AddStep(@"exit", matchScreen.Exit);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
144
osu.Game.Tests/Visual/TestCasePollingComponent.cs
Normal file
144
osu.Game.Tests/Visual/TestCasePollingComponent.cs
Normal file
@ -0,0 +1,144 @@
|
|||||||
|
// Copyright (c) 2007-2018 ppy Pty Ltd <contact@ppy.sh>.
|
||||||
|
// Licensed under the MIT Licence - https://raw.githubusercontent.com/ppy/osu/master/LICENCE
|
||||||
|
|
||||||
|
using System;
|
||||||
|
using System.Threading.Tasks;
|
||||||
|
using NUnit.Framework;
|
||||||
|
using osu.Framework.Graphics;
|
||||||
|
using osu.Framework.Graphics.Containers;
|
||||||
|
using osu.Framework.Graphics.Shapes;
|
||||||
|
using osu.Framework.Logging;
|
||||||
|
using osu.Game.Graphics.Sprites;
|
||||||
|
using osu.Game.Online;
|
||||||
|
using osuTK;
|
||||||
|
using osuTK.Graphics;
|
||||||
|
|
||||||
|
namespace osu.Game.Tests.Visual
|
||||||
|
{
|
||||||
|
public class TestCasePollingComponent : OsuTestCase
|
||||||
|
{
|
||||||
|
private Container pollBox;
|
||||||
|
private TestPoller poller;
|
||||||
|
|
||||||
|
private const float safety_adjust = 1f;
|
||||||
|
private int count;
|
||||||
|
|
||||||
|
[SetUp]
|
||||||
|
public void SetUp() => Schedule(() =>
|
||||||
|
{
|
||||||
|
count = 0;
|
||||||
|
|
||||||
|
Children = new Drawable[]
|
||||||
|
{
|
||||||
|
pollBox = new Container
|
||||||
|
{
|
||||||
|
Alpha = 0,
|
||||||
|
RelativeSizeAxes = Axes.Both,
|
||||||
|
Children = new Drawable[]
|
||||||
|
{
|
||||||
|
new Box
|
||||||
|
{
|
||||||
|
Anchor = Anchor.Centre,
|
||||||
|
Origin = Anchor.Centre,
|
||||||
|
Scale = new Vector2(0.4f),
|
||||||
|
Colour = Color4.LimeGreen,
|
||||||
|
RelativeSizeAxes = Axes.Both,
|
||||||
|
},
|
||||||
|
new OsuSpriteText
|
||||||
|
{
|
||||||
|
Anchor = Anchor.Centre,
|
||||||
|
Origin = Anchor.Centre,
|
||||||
|
Text = "Poll!",
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
};
|
||||||
|
});
|
||||||
|
|
||||||
|
//[Test]
|
||||||
|
public void TestInstantPolling()
|
||||||
|
{
|
||||||
|
createPoller(true);
|
||||||
|
|
||||||
|
AddStep("set poll interval to 1", () => poller.TimeBetweenPolls = TimePerAction * safety_adjust);
|
||||||
|
checkCount(1);
|
||||||
|
checkCount(2);
|
||||||
|
checkCount(3);
|
||||||
|
|
||||||
|
AddStep("set poll interval to 5", () => poller.TimeBetweenPolls = TimePerAction * safety_adjust * 5);
|
||||||
|
checkCount(4);
|
||||||
|
checkCount(4);
|
||||||
|
checkCount(4);
|
||||||
|
|
||||||
|
skip();
|
||||||
|
|
||||||
|
checkCount(5);
|
||||||
|
checkCount(5);
|
||||||
|
|
||||||
|
AddStep("set poll interval to 1", () => poller.TimeBetweenPolls = TimePerAction * safety_adjust);
|
||||||
|
checkCount(6);
|
||||||
|
checkCount(7);
|
||||||
|
}
|
||||||
|
|
||||||
|
[Test]
|
||||||
|
public void TestSlowPolling()
|
||||||
|
{
|
||||||
|
createPoller(false);
|
||||||
|
|
||||||
|
AddStep("set poll interval to 1", () => poller.TimeBetweenPolls = TimePerAction * safety_adjust * 5);
|
||||||
|
checkCount(0);
|
||||||
|
skip();
|
||||||
|
checkCount(0);
|
||||||
|
skip();
|
||||||
|
skip();
|
||||||
|
skip();
|
||||||
|
skip();
|
||||||
|
checkCount(0);
|
||||||
|
skip();
|
||||||
|
skip();
|
||||||
|
checkCount(0);
|
||||||
|
}
|
||||||
|
|
||||||
|
private void skip() => AddStep("skip", () =>
|
||||||
|
{
|
||||||
|
// could be 4 or 5 at this point due to timing discrepancies (safety_adjust @ 0.2 * 5 ~= 1)
|
||||||
|
// easiest to just ignore the value at this point and move on.
|
||||||
|
});
|
||||||
|
|
||||||
|
private void checkCount(int checkValue)
|
||||||
|
{
|
||||||
|
Logger.Log($"value is {count}");
|
||||||
|
AddAssert($"count is {checkValue}", () => count == checkValue);
|
||||||
|
}
|
||||||
|
|
||||||
|
private void createPoller(bool instant) => AddStep("create poller", () =>
|
||||||
|
{
|
||||||
|
poller?.Expire();
|
||||||
|
|
||||||
|
Add(poller = instant ? new TestPoller() : new TestSlowPoller());
|
||||||
|
poller.OnPoll += () =>
|
||||||
|
{
|
||||||
|
pollBox.FadeOutFromOne(500);
|
||||||
|
count++;
|
||||||
|
};
|
||||||
|
});
|
||||||
|
|
||||||
|
protected override double TimePerAction => 5000;
|
||||||
|
|
||||||
|
public class TestPoller : PollingComponent
|
||||||
|
{
|
||||||
|
public event Action OnPoll;
|
||||||
|
|
||||||
|
protected override Task Poll()
|
||||||
|
{
|
||||||
|
Schedule(() => OnPoll?.Invoke());
|
||||||
|
return base.Poll();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public class TestSlowPoller : TestPoller
|
||||||
|
{
|
||||||
|
protected override Task Poll() => Task.Delay((int)(TimeBetweenPolls / 2f / Clock.Rate)).ContinueWith(_ => base.Poll());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@ -1,141 +0,0 @@
|
|||||||
// Copyright (c) 2007-2018 ppy Pty Ltd <contact@ppy.sh>.
|
|
||||||
// Licensed under the MIT Licence - https://raw.githubusercontent.com/ppy/osu/master/LICENCE
|
|
||||||
|
|
||||||
using NUnit.Framework;
|
|
||||||
using osu.Framework.Allocation;
|
|
||||||
using osu.Framework.Graphics;
|
|
||||||
using osu.Game.Beatmaps;
|
|
||||||
using osu.Game.Online.Multiplayer;
|
|
||||||
using osu.Game.Rulesets;
|
|
||||||
using osu.Game.Screens.Multi.Lounge.Components;
|
|
||||||
using osu.Game.Users;
|
|
||||||
|
|
||||||
namespace osu.Game.Tests.Visual
|
|
||||||
{
|
|
||||||
[TestFixture]
|
|
||||||
public class TestCaseRoomInspector : OsuTestCase
|
|
||||||
{
|
|
||||||
private RulesetStore rulesets;
|
|
||||||
|
|
||||||
protected override void LoadComplete()
|
|
||||||
{
|
|
||||||
base.LoadComplete();
|
|
||||||
|
|
||||||
Room room = new Room
|
|
||||||
{
|
|
||||||
Name = { Value = @"My Awesome Room" },
|
|
||||||
Host = { Value = new User { Username = @"flyte", Id = 3103765, Country = new Country { FlagName = @"JP" } } },
|
|
||||||
Status = { Value = new RoomStatusOpen() },
|
|
||||||
Type = { Value = new GameTypeTeamVersus() },
|
|
||||||
Beatmap =
|
|
||||||
{
|
|
||||||
Value = new BeatmapInfo
|
|
||||||
{
|
|
||||||
StarDifficulty = 3.7,
|
|
||||||
Ruleset = rulesets.GetRuleset(3),
|
|
||||||
Metadata = new BeatmapMetadata
|
|
||||||
{
|
|
||||||
Title = @"Platina",
|
|
||||||
Artist = @"Maaya Sakamoto",
|
|
||||||
AuthorString = @"uwutm8",
|
|
||||||
},
|
|
||||||
BeatmapSet = new BeatmapSetInfo
|
|
||||||
{
|
|
||||||
OnlineInfo = new BeatmapSetOnlineInfo
|
|
||||||
{
|
|
||||||
Covers = new BeatmapSetOnlineCovers
|
|
||||||
{
|
|
||||||
Cover = @"https://assets.ppy.sh/beatmaps/560573/covers/cover.jpg?1492722343",
|
|
||||||
},
|
|
||||||
},
|
|
||||||
},
|
|
||||||
}
|
|
||||||
},
|
|
||||||
MaxParticipants = { Value = 200 },
|
|
||||||
Participants =
|
|
||||||
{
|
|
||||||
Value = new[]
|
|
||||||
{
|
|
||||||
new User { Username = @"flyte", Id = 3103765, Statistics = new UserStatistics { Ranks = new UserStatistics.UserRanks { Global = 142 } } },
|
|
||||||
new User { Username = @"Cookiezi", Id = 124493, Statistics = new UserStatistics { Ranks = new UserStatistics.UserRanks { Global = 546 } } },
|
|
||||||
new User { Username = @"Angelsim", Id = 1777162, Statistics = new UserStatistics { Ranks = new UserStatistics.UserRanks { Global = 287 } } },
|
|
||||||
new User { Username = @"Rafis", Id = 2558286, Statistics = new UserStatistics { Ranks = new UserStatistics.UserRanks { Global = 468 } } },
|
|
||||||
new User { Username = @"hvick225", Id = 50265, Statistics = new UserStatistics { Ranks = new UserStatistics.UserRanks { Global = 325 } } },
|
|
||||||
new User { Username = @"peppy", Id = 2, Statistics = new UserStatistics { Ranks = new UserStatistics.UserRanks { Global = 625 } } },
|
|
||||||
}
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
Add(new RoomInspector
|
|
||||||
{
|
|
||||||
Anchor = Anchor.Centre,
|
|
||||||
Origin = Anchor.Centre,
|
|
||||||
RelativeSizeAxes = Axes.Both,
|
|
||||||
Width = 0.5f,
|
|
||||||
});
|
|
||||||
|
|
||||||
AddStep(@"change title", () => room.Name.Value = @"A Better Room Than The Above");
|
|
||||||
AddStep(@"change host", () => room.Host.Value = new User { Username = @"DrabWeb", Id = 6946022, Country = new Country { FlagName = @"CA" } });
|
|
||||||
AddStep(@"change status", () => room.Status.Value = new RoomStatusPlaying());
|
|
||||||
AddStep(@"change type", () => room.Type.Value = new GameTypeTag());
|
|
||||||
AddStep(@"change beatmap", () => room.Beatmap.Value = null);
|
|
||||||
AddStep(@"change max participants", () => room.MaxParticipants.Value = null);
|
|
||||||
AddStep(@"change participants", () => room.Participants.Value = new[]
|
|
||||||
{
|
|
||||||
new User { Username = @"filsdelama", Id = 2831793, Statistics = new UserStatistics { Ranks = new UserStatistics.UserRanks { Global = 854 } } },
|
|
||||||
new User { Username = @"_index", Id = 652457, Statistics = new UserStatistics { Ranks = new UserStatistics.UserRanks { Global = 150 } } }
|
|
||||||
});
|
|
||||||
|
|
||||||
AddStep(@"change room", () =>
|
|
||||||
{
|
|
||||||
Room newRoom = new Room
|
|
||||||
{
|
|
||||||
Name = { Value = @"My New, Better Than Ever Room" },
|
|
||||||
Host = { Value = new User { Username = @"Angelsim", Id = 1777162, Country = new Country { FlagName = @"KR" } } },
|
|
||||||
Status = { Value = new RoomStatusOpen() },
|
|
||||||
Type = { Value = new GameTypeTagTeam() },
|
|
||||||
Beatmap =
|
|
||||||
{
|
|
||||||
Value = new BeatmapInfo
|
|
||||||
{
|
|
||||||
StarDifficulty = 7.07,
|
|
||||||
Ruleset = rulesets.GetRuleset(0),
|
|
||||||
Metadata = new BeatmapMetadata
|
|
||||||
{
|
|
||||||
Title = @"FREEDOM DIVE",
|
|
||||||
Artist = @"xi",
|
|
||||||
AuthorString = @"Nakagawa-Kanon",
|
|
||||||
},
|
|
||||||
BeatmapSet = new BeatmapSetInfo
|
|
||||||
{
|
|
||||||
OnlineInfo = new BeatmapSetOnlineInfo
|
|
||||||
{
|
|
||||||
Covers = new BeatmapSetOnlineCovers
|
|
||||||
{
|
|
||||||
Cover = @"https://assets.ppy.sh/beatmaps/39804/covers/cover.jpg?1456506845",
|
|
||||||
},
|
|
||||||
},
|
|
||||||
},
|
|
||||||
},
|
|
||||||
},
|
|
||||||
MaxParticipants = { Value = 10 },
|
|
||||||
Participants =
|
|
||||||
{
|
|
||||||
Value = new[]
|
|
||||||
{
|
|
||||||
new User { Username = @"Angelsim", Id = 1777162, Statistics = new UserStatistics { Ranks = new UserStatistics.UserRanks { Global = 4 } } },
|
|
||||||
new User { Username = @"HappyStick", Id = 256802, Statistics = new UserStatistics { Ranks = new UserStatistics.UserRanks { Global = 752 } } },
|
|
||||||
new User { Username = @"-Konpaku-", Id = 2258797, Statistics = new UserStatistics { Ranks = new UserStatistics.UserRanks { Global = 571 } } }
|
|
||||||
}
|
|
||||||
}
|
|
||||||
};
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
[BackgroundDependencyLoader]
|
|
||||||
private void load(RulesetStore rulesets)
|
|
||||||
{
|
|
||||||
this.rulesets = rulesets;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
@ -9,21 +9,28 @@ using osu.Framework.Graphics.Sprites;
|
|||||||
|
|
||||||
namespace osu.Game.Beatmaps.Drawables
|
namespace osu.Game.Beatmaps.Drawables
|
||||||
{
|
{
|
||||||
public class UpdateableBeatmapBackgroundSprite : ModelBackedDrawable<WorkingBeatmap>
|
public class UpdateableBeatmapBackgroundSprite : ModelBackedDrawable<BeatmapInfo>
|
||||||
{
|
{
|
||||||
public readonly IBindable<WorkingBeatmap> Beatmap = new Bindable<WorkingBeatmap>();
|
public readonly IBindable<BeatmapInfo> Beatmap = new Bindable<BeatmapInfo>();
|
||||||
|
|
||||||
[Resolved]
|
[Resolved]
|
||||||
private OsuGameBase game { get; set; }
|
private BeatmapManager beatmaps { get; set; }
|
||||||
|
|
||||||
public UpdateableBeatmapBackgroundSprite()
|
public UpdateableBeatmapBackgroundSprite()
|
||||||
{
|
{
|
||||||
Beatmap.BindValueChanged(b => Schedule(() => Model = b));
|
Beatmap.BindValueChanged(b => Schedule(() => Model = b));
|
||||||
}
|
}
|
||||||
|
|
||||||
protected override Drawable CreateDrawable(WorkingBeatmap model)
|
protected override Drawable CreateDrawable(BeatmapInfo model)
|
||||||
{
|
{
|
||||||
Drawable drawable = model == null ? (Drawable)new DefaultSprite() : new BeatmapBackgroundSprite(model);
|
Drawable drawable;
|
||||||
|
|
||||||
|
if (model == null)
|
||||||
|
drawable = new DefaultSprite();
|
||||||
|
else if (model.BeatmapSet?.OnlineInfo != null)
|
||||||
|
drawable = new BeatmapSetCover(model.BeatmapSet);
|
||||||
|
else
|
||||||
|
drawable = new BeatmapBackgroundSprite(beatmaps.GetWorkingBeatmap(model));
|
||||||
|
|
||||||
drawable.RelativeSizeAxes = Axes.Both;
|
drawable.RelativeSizeAxes = Axes.Both;
|
||||||
drawable.Anchor = Anchor.Centre;
|
drawable.Anchor = Anchor.Centre;
|
||||||
|
@ -40,7 +40,7 @@ namespace osu.Game.Online.API
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
public int Timeout = WebRequest.DEFAULT_TIMEOUT;
|
public int Timeout = WebRequest.DEFAULT_TIMEOUT;
|
||||||
|
|
||||||
protected virtual string Target => string.Empty;
|
protected abstract string Target { get; }
|
||||||
|
|
||||||
protected virtual WebRequest CreateWebRequest() => new WebRequest(Uri);
|
protected virtual WebRequest CreateWebRequest() => new WebRequest(Uri);
|
||||||
|
|
||||||
|
@ -67,11 +67,7 @@ namespace osu.Game.Online.API.Requests.Responses
|
|||||||
OnlineBeatmapID = OnlineBeatmapID,
|
OnlineBeatmapID = OnlineBeatmapID,
|
||||||
Version = version,
|
Version = version,
|
||||||
Status = Status,
|
Status = Status,
|
||||||
BeatmapSet = new BeatmapSetInfo
|
BeatmapSet = BeatmapSet.ToBeatmapSet(rulesets),
|
||||||
{
|
|
||||||
OnlineBeatmapSetID = OnlineBeatmapSetID,
|
|
||||||
Status = BeatmapSet?.Status ?? BeatmapSetOnlineStatus.None
|
|
||||||
},
|
|
||||||
BaseDifficulty = new BeatmapDifficulty
|
BaseDifficulty = new BeatmapDifficulty
|
||||||
{
|
{
|
||||||
DrainRate = drainRate,
|
DrainRate = drainRate,
|
||||||
|
@ -4,11 +4,10 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
|
using System.Threading.Tasks;
|
||||||
using osu.Framework.Allocation;
|
using osu.Framework.Allocation;
|
||||||
using osu.Framework.Configuration;
|
using osu.Framework.Configuration;
|
||||||
using osu.Framework.Graphics;
|
|
||||||
using osu.Framework.Logging;
|
using osu.Framework.Logging;
|
||||||
using osu.Framework.Threading;
|
|
||||||
using osu.Game.Online.API;
|
using osu.Game.Online.API;
|
||||||
using osu.Game.Online.API.Requests;
|
using osu.Game.Online.API.Requests;
|
||||||
using osu.Game.Users;
|
using osu.Game.Users;
|
||||||
@ -18,7 +17,7 @@ namespace osu.Game.Online.Chat
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// Manages everything channel related
|
/// Manages everything channel related
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public class ChannelManager : Component, IOnlineComponent
|
public class ChannelManager : PollingComponent
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// The channels the player joins on startup
|
/// The channels the player joins on startup
|
||||||
@ -49,11 +48,14 @@ namespace osu.Game.Online.Chat
|
|||||||
public IBindableCollection<Channel> AvailableChannels => availableChannels;
|
public IBindableCollection<Channel> AvailableChannels => availableChannels;
|
||||||
|
|
||||||
private IAPIProvider api;
|
private IAPIProvider api;
|
||||||
private ScheduledDelegate fetchMessagesScheduleder;
|
|
||||||
|
public readonly BindableBool HighPollRate = new BindableBool();
|
||||||
|
|
||||||
public ChannelManager()
|
public ChannelManager()
|
||||||
{
|
{
|
||||||
CurrentChannel.ValueChanged += currentChannelChanged;
|
CurrentChannel.ValueChanged += currentChannelChanged;
|
||||||
|
|
||||||
|
HighPollRate.BindValueChanged(high => TimeBetweenPolls = high ? 1000 : 6000, true);
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
@ -360,73 +362,60 @@ namespace osu.Game.Online.Chat
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public void APIStateChanged(APIAccess api, APIState state)
|
|
||||||
{
|
|
||||||
switch (state)
|
|
||||||
{
|
|
||||||
case APIState.Online:
|
|
||||||
fetchUpdates();
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
fetchMessagesScheduleder?.Cancel();
|
|
||||||
fetchMessagesScheduleder = null;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private long lastMessageId;
|
private long lastMessageId;
|
||||||
private const int update_poll_interval = 1000;
|
|
||||||
|
|
||||||
private bool channelsInitialised;
|
private bool channelsInitialised;
|
||||||
|
|
||||||
private void fetchUpdates()
|
protected override Task Poll()
|
||||||
{
|
{
|
||||||
fetchMessagesScheduleder?.Cancel();
|
if (!api.IsLoggedIn)
|
||||||
fetchMessagesScheduleder = Scheduler.AddDelayed(() =>
|
return base.Poll();
|
||||||
|
|
||||||
|
var fetchReq = new GetUpdatesRequest(lastMessageId);
|
||||||
|
|
||||||
|
var tcs = new TaskCompletionSource<bool>();
|
||||||
|
|
||||||
|
fetchReq.Success += updates =>
|
||||||
{
|
{
|
||||||
var fetchReq = new GetUpdatesRequest(lastMessageId);
|
if (updates?.Presence != null)
|
||||||
|
|
||||||
fetchReq.Success += updates =>
|
|
||||||
{
|
{
|
||||||
if (updates?.Presence != null)
|
foreach (var channel in updates.Presence)
|
||||||
{
|
{
|
||||||
foreach (var channel in updates.Presence)
|
// we received this from the server so should mark the channel already joined.
|
||||||
{
|
JoinChannel(channel, true);
|
||||||
// we received this from the server so should mark the channel already joined.
|
|
||||||
JoinChannel(channel, true);
|
|
||||||
}
|
|
||||||
|
|
||||||
//todo: handle left channels
|
|
||||||
|
|
||||||
handleChannelMessages(updates.Messages);
|
|
||||||
|
|
||||||
foreach (var group in updates.Messages.GroupBy(m => m.ChannelId))
|
|
||||||
JoinedChannels.FirstOrDefault(c => c.Id == group.Key)?.AddNewMessages(group.ToArray());
|
|
||||||
|
|
||||||
lastMessageId = updates.Messages.LastOrDefault()?.Id ?? lastMessageId;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!channelsInitialised)
|
//todo: handle left channels
|
||||||
{
|
|
||||||
channelsInitialised = true;
|
|
||||||
// we want this to run after the first presence so we can see if the user is in any channels already.
|
|
||||||
initializeChannels();
|
|
||||||
}
|
|
||||||
|
|
||||||
fetchUpdates();
|
handleChannelMessages(updates.Messages);
|
||||||
};
|
|
||||||
|
|
||||||
fetchReq.Failure += delegate { fetchUpdates(); };
|
foreach (var group in updates.Messages.GroupBy(m => m.ChannelId))
|
||||||
|
JoinedChannels.FirstOrDefault(c => c.Id == group.Key)?.AddNewMessages(group.ToArray());
|
||||||
|
|
||||||
api.Queue(fetchReq);
|
lastMessageId = updates.Messages.LastOrDefault()?.Id ?? lastMessageId;
|
||||||
}, update_poll_interval);
|
}
|
||||||
|
|
||||||
|
if (!channelsInitialised)
|
||||||
|
{
|
||||||
|
channelsInitialised = true;
|
||||||
|
// we want this to run after the first presence so we can see if the user is in any channels already.
|
||||||
|
initializeChannels();
|
||||||
|
}
|
||||||
|
|
||||||
|
tcs.SetResult(true);
|
||||||
|
};
|
||||||
|
|
||||||
|
fetchReq.Failure += _ => tcs.SetResult(false);
|
||||||
|
|
||||||
|
api.Queue(fetchReq);
|
||||||
|
|
||||||
|
return tcs.Task;
|
||||||
}
|
}
|
||||||
|
|
||||||
[BackgroundDependencyLoader]
|
[BackgroundDependencyLoader]
|
||||||
private void load(IAPIProvider api)
|
private void load(IAPIProvider api)
|
||||||
{
|
{
|
||||||
this.api = api;
|
this.api = api;
|
||||||
api.Register(this);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -3,23 +3,154 @@
|
|||||||
|
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
|
using Newtonsoft.Json;
|
||||||
using osu.Framework.Configuration;
|
using osu.Framework.Configuration;
|
||||||
using osu.Game.Beatmaps;
|
using osu.Game.Beatmaps;
|
||||||
|
using osu.Game.Online.API.Requests.Responses;
|
||||||
|
using osu.Game.Rulesets;
|
||||||
|
using osu.Game.Rulesets.Mods;
|
||||||
using osu.Game.Users;
|
using osu.Game.Users;
|
||||||
|
|
||||||
namespace osu.Game.Online.Multiplayer
|
namespace osu.Game.Online.Multiplayer
|
||||||
{
|
{
|
||||||
public class Room
|
public class Room
|
||||||
{
|
{
|
||||||
public Bindable<string> Name = new Bindable<string>("My awesome room!");
|
[JsonProperty("id")]
|
||||||
public Bindable<User> Host = new Bindable<User>();
|
public Bindable<int?> RoomID { get; } = new Bindable<int?>();
|
||||||
|
|
||||||
|
[JsonIgnore]
|
||||||
|
public readonly Bindable<BeatmapInfo> Beatmap = new Bindable<BeatmapInfo>();
|
||||||
|
|
||||||
|
[JsonProperty("name")]
|
||||||
|
public readonly Bindable<string> Name = new Bindable<string>("My awesome room!");
|
||||||
|
|
||||||
|
[JsonProperty("host")]
|
||||||
|
public readonly Bindable<User> Host = new Bindable<User>();
|
||||||
|
|
||||||
|
public bool ShouldSerializeHost() => false;
|
||||||
|
|
||||||
|
[JsonProperty("playlist")]
|
||||||
|
public readonly BindableCollection<PlaylistItem> Playlist = new BindableCollection<PlaylistItem>();
|
||||||
|
|
||||||
|
[JsonProperty("duration")]
|
||||||
|
public readonly Bindable<int> Duration = new Bindable<int>(100);
|
||||||
|
|
||||||
|
[JsonIgnore]
|
||||||
|
public readonly Bindable<int?> MaxAttempts = new Bindable<int?>();
|
||||||
|
|
||||||
|
// Todo: Find a better way to do this (https://github.com/ppy/osu-framework/issues/1930)
|
||||||
|
[JsonProperty("max_attempts", DefaultValueHandling = DefaultValueHandling.Ignore)]
|
||||||
|
private int? maxAttempts
|
||||||
|
{
|
||||||
|
get => MaxAttempts;
|
||||||
|
set => MaxAttempts.Value = value;
|
||||||
|
}
|
||||||
|
|
||||||
public Bindable<RoomStatus> Status = new Bindable<RoomStatus>(new RoomStatusOpen());
|
public Bindable<RoomStatus> Status = new Bindable<RoomStatus>(new RoomStatusOpen());
|
||||||
public Bindable<RoomAvailability> Availability = new Bindable<RoomAvailability>();
|
public Bindable<RoomAvailability> Availability = new Bindable<RoomAvailability>();
|
||||||
public Bindable<GameType> Type = new Bindable<GameType>(new GameTypeTimeshift());
|
public Bindable<GameType> Type = new Bindable<GameType>(new GameTypeTimeshift());
|
||||||
public Bindable<BeatmapInfo> Beatmap = new Bindable<BeatmapInfo>();
|
|
||||||
public Bindable<int?> MaxParticipants = new Bindable<int?>();
|
public Bindable<int?> MaxParticipants = new Bindable<int?>();
|
||||||
public Bindable<IEnumerable<User>> Participants = new Bindable<IEnumerable<User>>(Enumerable.Empty<User>());
|
public Bindable<IEnumerable<User>> Participants = new Bindable<IEnumerable<User>>(Enumerable.Empty<User>());
|
||||||
|
|
||||||
public Bindable<bool> Created = new Bindable<bool>();
|
public Room()
|
||||||
|
{
|
||||||
|
Beatmap.BindValueChanged(b =>
|
||||||
|
{
|
||||||
|
Playlist.Clear();
|
||||||
|
Playlist.Add(new PlaylistItem { Beatmap = b });
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
public void CopyFrom(Room other)
|
||||||
|
{
|
||||||
|
RoomID.Value = other.RoomID;
|
||||||
|
Name.Value = other.Name;
|
||||||
|
Host.Value = other.Host;
|
||||||
|
Status.Value = other.Status;
|
||||||
|
Availability.Value = other.Availability;
|
||||||
|
Type.Value = other.Type;
|
||||||
|
MaxParticipants.Value = other.MaxParticipants;
|
||||||
|
Participants.Value = other.Participants.Value.ToArray();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public class PlaylistItem
|
||||||
|
{
|
||||||
|
[JsonProperty("beatmap")]
|
||||||
|
private APIBeatmap beatmap { get; set; }
|
||||||
|
|
||||||
|
public bool ShouldSerializebeatmap() => false;
|
||||||
|
|
||||||
|
[JsonIgnore]
|
||||||
|
public BeatmapInfo Beatmap { get; set; }
|
||||||
|
|
||||||
|
[JsonProperty("beatmap_id")]
|
||||||
|
public int BeatmapID => 847296; //Beatmap.OnlineBeatmapID ?? 0;
|
||||||
|
|
||||||
|
[JsonProperty("ruleset_id")]
|
||||||
|
public int RulesetID { get; set; }
|
||||||
|
|
||||||
|
[JsonIgnore]
|
||||||
|
public readonly BindableCollection<Mod> AllowedMods = new BindableCollection<Mod>();
|
||||||
|
|
||||||
|
[JsonIgnore]
|
||||||
|
public readonly BindableCollection<Mod> RequiredMods = new BindableCollection<Mod>();
|
||||||
|
|
||||||
|
private APIMod[] _allowedMods;
|
||||||
|
|
||||||
|
[JsonProperty("allowed_mods")]
|
||||||
|
private APIMod[] allowedMods
|
||||||
|
{
|
||||||
|
get => AllowedMods.Select(m => new APIMod { Acronym = m.Acronym }).ToArray();
|
||||||
|
set => _allowedMods = value;
|
||||||
|
}
|
||||||
|
|
||||||
|
private APIMod[] _requiredMods;
|
||||||
|
|
||||||
|
[JsonProperty("required_mods")]
|
||||||
|
private APIMod[] requiredMods
|
||||||
|
{
|
||||||
|
get => RequiredMods.Select(m => new APIMod { Acronym = m.Acronym }).ToArray();
|
||||||
|
set => _requiredMods = value;
|
||||||
|
}
|
||||||
|
|
||||||
|
private RulesetInfo ruleset;
|
||||||
|
|
||||||
|
[JsonIgnore]
|
||||||
|
public RulesetInfo Ruleset
|
||||||
|
{
|
||||||
|
get => ruleset;
|
||||||
|
set
|
||||||
|
{
|
||||||
|
ruleset = value;
|
||||||
|
|
||||||
|
if (_allowedMods != null)
|
||||||
|
{
|
||||||
|
AllowedMods.Clear();
|
||||||
|
AllowedMods.AddRange(value.CreateInstance().GetAllMods().Where(mod => _allowedMods.Any(m => m.Acronym == mod.Acronym)));
|
||||||
|
|
||||||
|
_allowedMods = null;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (_requiredMods != null)
|
||||||
|
{
|
||||||
|
RequiredMods.Clear();
|
||||||
|
RequiredMods.AddRange(value.CreateInstance().GetAllMods().Where(mod => _requiredMods.Any(m => m.Acronym == mod.Acronym)));
|
||||||
|
|
||||||
|
_requiredMods = null;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void SetRulesets(RulesetStore rulesets)
|
||||||
|
{
|
||||||
|
Beatmap = beatmap.ToBeatmap(rulesets);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Todo: Move this elsewhere for reusability
|
||||||
|
private class APIMod : IMod
|
||||||
|
{
|
||||||
|
public string Acronym { get; set; }
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
108
osu.Game/Online/PollingComponent.cs
Normal file
108
osu.Game/Online/PollingComponent.cs
Normal file
@ -0,0 +1,108 @@
|
|||||||
|
// Copyright (c) 2007-2018 ppy Pty Ltd <contact@ppy.sh>.
|
||||||
|
// Licensed under the MIT Licence - https://raw.githubusercontent.com/ppy/osu/master/LICENCE
|
||||||
|
|
||||||
|
using System;
|
||||||
|
using System.Threading.Tasks;
|
||||||
|
using osu.Framework.Graphics;
|
||||||
|
using osu.Framework.Threading;
|
||||||
|
|
||||||
|
namespace osu.Game.Online
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// A component which requires a constant polling process.
|
||||||
|
/// </summary>
|
||||||
|
public abstract class PollingComponent : Component
|
||||||
|
{
|
||||||
|
private double? lastTimePolled;
|
||||||
|
|
||||||
|
private ScheduledDelegate scheduledPoll;
|
||||||
|
|
||||||
|
private bool pollingActive;
|
||||||
|
|
||||||
|
private double timeBetweenPolls;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// The time that should be waited between polls.
|
||||||
|
/// </summary>
|
||||||
|
public double TimeBetweenPolls
|
||||||
|
{
|
||||||
|
get => timeBetweenPolls;
|
||||||
|
set
|
||||||
|
{
|
||||||
|
timeBetweenPolls = value;
|
||||||
|
scheduledPoll?.Cancel();
|
||||||
|
pollIfNecessary();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
protected override void LoadComplete()
|
||||||
|
{
|
||||||
|
base.LoadComplete();
|
||||||
|
pollIfNecessary();
|
||||||
|
}
|
||||||
|
|
||||||
|
private bool pollIfNecessary()
|
||||||
|
{
|
||||||
|
// we must be loaded so we have access to clock.
|
||||||
|
if (!IsLoaded) return false;
|
||||||
|
|
||||||
|
// there's already a poll process running.
|
||||||
|
if (pollingActive) return false;
|
||||||
|
|
||||||
|
// don't try polling if the time between polls hasn't been set.
|
||||||
|
if (timeBetweenPolls == 0) return false;
|
||||||
|
|
||||||
|
if (!lastTimePolled.HasValue)
|
||||||
|
{
|
||||||
|
doPoll();
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (Time.Current - lastTimePolled.Value > timeBetweenPolls)
|
||||||
|
{
|
||||||
|
doPoll();
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
// not ennough time has passed since the last poll. we do want to schedule a poll to happen, though.
|
||||||
|
scheduleNextPoll();
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
private void doPoll()
|
||||||
|
{
|
||||||
|
scheduledPoll = null;
|
||||||
|
pollingActive = true;
|
||||||
|
Poll().ContinueWith(_ => pollComplete());
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Perform the polling in this method. Call <see cref="pollComplete"/> when done.
|
||||||
|
/// </summary>
|
||||||
|
protected virtual Task Poll()
|
||||||
|
{
|
||||||
|
return Task.CompletedTask;
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Call when a poll operation has completed.
|
||||||
|
/// </summary>
|
||||||
|
private void pollComplete()
|
||||||
|
{
|
||||||
|
lastTimePolled = Time.Current;
|
||||||
|
pollingActive = false;
|
||||||
|
|
||||||
|
if (scheduledPoll == null)
|
||||||
|
scheduleNextPoll();
|
||||||
|
}
|
||||||
|
|
||||||
|
private void scheduleNextPoll()
|
||||||
|
{
|
||||||
|
scheduledPoll?.Cancel();
|
||||||
|
|
||||||
|
double lastPollDuration = lastTimePolled.HasValue ? Time.Current - lastTimePolled.Value : 0;
|
||||||
|
|
||||||
|
scheduledPoll = Scheduler.AddDelayed(doPoll, Math.Max(0, timeBetweenPolls - lastPollDuration));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@ -418,6 +418,8 @@ namespace osu.Game
|
|||||||
dependencies.Cache(notifications);
|
dependencies.Cache(notifications);
|
||||||
dependencies.Cache(dialogOverlay);
|
dependencies.Cache(dialogOverlay);
|
||||||
|
|
||||||
|
chatOverlay.StateChanged += state => channelManager.HighPollRate.Value = state == Visibility.Visible;
|
||||||
|
|
||||||
Add(externalLinkOpener = new ExternalLinkOpener());
|
Add(externalLinkOpener = new ExternalLinkOpener());
|
||||||
|
|
||||||
var singleDisplaySideOverlays = new OverlayContainer[] { settings, notifications };
|
var singleDisplaySideOverlays = new OverlayContainer[] { settings, notifications };
|
||||||
|
@ -8,6 +8,7 @@ using osuTK.Graphics;
|
|||||||
using osu.Framework.Allocation;
|
using osu.Framework.Allocation;
|
||||||
using osu.Framework.Graphics;
|
using osu.Framework.Graphics;
|
||||||
using osu.Framework.Graphics.Containers;
|
using osu.Framework.Graphics.Containers;
|
||||||
|
using osu.Framework.Graphics.Sprites;
|
||||||
using osu.Framework.Input.Events;
|
using osu.Framework.Input.Events;
|
||||||
using osu.Framework.Localisation;
|
using osu.Framework.Localisation;
|
||||||
using osu.Game.Beatmaps;
|
using osu.Game.Beatmaps;
|
||||||
|
@ -1,6 +1,8 @@
|
|||||||
// Copyright (c) 2007-2018 ppy Pty Ltd <contact@ppy.sh>.
|
// Copyright (c) 2007-2018 ppy Pty Ltd <contact@ppy.sh>.
|
||||||
// Licensed under the MIT Licence - https://raw.githubusercontent.com/ppy/osu/master/LICENCE
|
// Licensed under the MIT Licence - https://raw.githubusercontent.com/ppy/osu/master/LICENCE
|
||||||
|
|
||||||
|
using Newtonsoft.Json;
|
||||||
|
|
||||||
namespace osu.Game.Rulesets.Mods
|
namespace osu.Game.Rulesets.Mods
|
||||||
{
|
{
|
||||||
public interface IMod
|
public interface IMod
|
||||||
@ -8,6 +10,7 @@ namespace osu.Game.Rulesets.Mods
|
|||||||
/// <summary>
|
/// <summary>
|
||||||
/// The shortened name of this mod.
|
/// The shortened name of this mod.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
|
[JsonProperty]
|
||||||
string Acronym { get; }
|
string Acronym { get; }
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -213,8 +213,6 @@ namespace osu.Game.Screens.Multi.Lounge.Components
|
|||||||
d.FadeColour(s.GetAppropriateColour(colours), transition_duration);
|
d.FadeColour(s.GetAppropriateColour(colours), transition_duration);
|
||||||
};
|
};
|
||||||
|
|
||||||
background.Beatmap.BindTo(beatmap);
|
|
||||||
|
|
||||||
beatmapBind.BindValueChanged(b => beatmap.Value = beatmaps.GetWorkingBeatmap(b));
|
beatmapBind.BindValueChanged(b => beatmap.Value = beatmaps.GetWorkingBeatmap(b));
|
||||||
nameBind.BindValueChanged(n => name.Text = n);
|
nameBind.BindValueChanged(n => name.Text = n);
|
||||||
|
|
||||||
@ -224,6 +222,7 @@ namespace osu.Game.Screens.Multi.Lounge.Components
|
|||||||
typeBind.BindTo(Room.Type);
|
typeBind.BindTo(Room.Type);
|
||||||
beatmapBind.BindTo(Room.Beatmap);
|
beatmapBind.BindTo(Room.Beatmap);
|
||||||
participantsBind.BindTo(Room.Participants);
|
participantsBind.BindTo(Room.Participants);
|
||||||
|
background.Beatmap.BindTo(beatmapBind);
|
||||||
|
|
||||||
modeTypeInfo.Beatmap.BindTo(beatmapBind);
|
modeTypeInfo.Beatmap.BindTo(beatmapBind);
|
||||||
modeTypeInfo.Type.BindTo(typeBind);
|
modeTypeInfo.Type.BindTo(typeBind);
|
||||||
|
@ -180,7 +180,7 @@ namespace osu.Game.Screens.Multi.Lounge.Components
|
|||||||
|
|
||||||
nameBind.BindValueChanged(n => name.Text = n);
|
nameBind.BindValueChanged(n => name.Text = n);
|
||||||
|
|
||||||
background.Beatmap.BindTo(beatmap);
|
background.Beatmap.BindTo(beatmapBind);
|
||||||
|
|
||||||
participantInfo.Host.BindTo(hostBind);
|
participantInfo.Host.BindTo(hostBind);
|
||||||
participantInfo.Participants.BindTo(participantsBind);
|
participantInfo.Participants.BindTo(participantsBind);
|
||||||
|
@ -23,7 +23,7 @@ namespace osu.Game.Screens.Multi.Match.Components
|
|||||||
{
|
{
|
||||||
public const float HEIGHT = 200;
|
public const float HEIGHT = 200;
|
||||||
|
|
||||||
public readonly IBindable<WorkingBeatmap> Beatmap = new Bindable<WorkingBeatmap>();
|
public readonly IBindable<BeatmapInfo> Beatmap = new Bindable<BeatmapInfo>();
|
||||||
|
|
||||||
private readonly Box tabStrip;
|
private readonly Box tabStrip;
|
||||||
|
|
||||||
@ -100,7 +100,7 @@ namespace osu.Game.Screens.Multi.Match.Components
|
|||||||
|
|
||||||
private class BeatmapSelectButton : TriangleButton
|
private class BeatmapSelectButton : TriangleButton
|
||||||
{
|
{
|
||||||
private readonly IBindable<bool> createdBind = new Bindable<bool>();
|
private readonly IBindable<int?> roomIDBind = new Bindable<int?>();
|
||||||
|
|
||||||
[Resolved]
|
[Resolved]
|
||||||
private Room room { get; set; }
|
private Room room { get; set; }
|
||||||
@ -113,8 +113,8 @@ namespace osu.Game.Screens.Multi.Match.Components
|
|||||||
[BackgroundDependencyLoader]
|
[BackgroundDependencyLoader]
|
||||||
private void load()
|
private void load()
|
||||||
{
|
{
|
||||||
createdBind.BindTo(room.Created);
|
roomIDBind.BindTo(room.RoomID);
|
||||||
createdBind.BindValueChanged(v => Enabled.Value = !v, true);
|
roomIDBind.BindValueChanged(v => Enabled.Value = !v.HasValue, true);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -14,7 +14,7 @@ namespace osu.Game.Screens.Multi.Match.Components
|
|||||||
{
|
{
|
||||||
public class MatchTabControl : PageTabControl<MatchPage>
|
public class MatchTabControl : PageTabControl<MatchPage>
|
||||||
{
|
{
|
||||||
private readonly IBindable<bool> created = new Bindable<bool>();
|
private readonly IBindable<int?> roomIdBind = new Bindable<int?>();
|
||||||
|
|
||||||
[Resolved]
|
[Resolved]
|
||||||
private Room room { get; set; }
|
private Room room { get; set; }
|
||||||
@ -28,10 +28,10 @@ namespace osu.Game.Screens.Multi.Match.Components
|
|||||||
[BackgroundDependencyLoader]
|
[BackgroundDependencyLoader]
|
||||||
private void load()
|
private void load()
|
||||||
{
|
{
|
||||||
created.BindTo(room.Created);
|
roomIdBind.BindTo(room.RoomID);
|
||||||
created.BindValueChanged(v =>
|
roomIdBind.BindValueChanged(v =>
|
||||||
{
|
{
|
||||||
if (v)
|
if (v.HasValue)
|
||||||
{
|
{
|
||||||
Items.ForEach(t => t.Enabled.Value = !(t is SettingsMatchPage));
|
Items.ForEach(t => t.Enabled.Value = !(t is SettingsMatchPage));
|
||||||
Current.Value = new RoomMatchPage();
|
Current.Value = new RoomMatchPage();
|
||||||
|
@ -97,7 +97,7 @@ namespace osu.Game.Screens.Multi.Match
|
|||||||
};
|
};
|
||||||
|
|
||||||
header.OnRequestSelectBeatmap = () => Push(new MatchSongSelect());
|
header.OnRequestSelectBeatmap = () => Push(new MatchSongSelect());
|
||||||
header.Beatmap.BindTo(Beatmap);
|
header.Beatmap.BindTo(beatmapBind);
|
||||||
|
|
||||||
header.Tabs.Current.ValueChanged += t =>
|
header.Tabs.Current.ValueChanged += t =>
|
||||||
{
|
{
|
||||||
|
@ -1,15 +1,24 @@
|
|||||||
// Copyright (c) 2007-2018 ppy Pty Ltd <contact@ppy.sh>.
|
// Copyright (c) 2007-2018 ppy Pty Ltd <contact@ppy.sh>.
|
||||||
// Licensed under the MIT Licence - https://raw.githubusercontent.com/ppy/osu/master/LICENCE
|
// Licensed under the MIT Licence - https://raw.githubusercontent.com/ppy/osu/master/LICENCE
|
||||||
|
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Linq;
|
||||||
|
using System.Net.Http;
|
||||||
|
using System.Threading.Tasks;
|
||||||
|
using Newtonsoft.Json;
|
||||||
using osu.Framework.Allocation;
|
using osu.Framework.Allocation;
|
||||||
using osu.Framework.Configuration;
|
using osu.Framework.Configuration;
|
||||||
using osu.Framework.Graphics;
|
using osu.Framework.IO.Network;
|
||||||
|
using osu.Framework.Logging;
|
||||||
|
using osu.Game.Beatmaps;
|
||||||
|
using osu.Game.Online;
|
||||||
using osu.Game.Online.API;
|
using osu.Game.Online.API;
|
||||||
using osu.Game.Online.Multiplayer;
|
using osu.Game.Online.Multiplayer;
|
||||||
|
using osu.Game.Rulesets;
|
||||||
|
|
||||||
namespace osu.Game.Screens.Multi
|
namespace osu.Game.Screens.Multi
|
||||||
{
|
{
|
||||||
public class RoomManager : Component
|
public class RoomManager : PollingComponent
|
||||||
{
|
{
|
||||||
public IBindableCollection<Room> Rooms => rooms;
|
public IBindableCollection<Room> Rooms => rooms;
|
||||||
private readonly BindableCollection<Room> rooms = new BindableCollection<Room>();
|
private readonly BindableCollection<Room> rooms = new BindableCollection<Room>();
|
||||||
@ -19,14 +28,104 @@ namespace osu.Game.Screens.Multi
|
|||||||
[Resolved]
|
[Resolved]
|
||||||
private APIAccess api { get; set; }
|
private APIAccess api { get; set; }
|
||||||
|
|
||||||
|
[Resolved]
|
||||||
|
private RulesetStore rulesets { get; set; }
|
||||||
|
|
||||||
|
[Resolved]
|
||||||
|
private BeatmapManager beatmaps { get; set; }
|
||||||
|
|
||||||
|
public RoomManager()
|
||||||
|
{
|
||||||
|
TimeBetweenPolls = 5000;
|
||||||
|
}
|
||||||
|
|
||||||
public void CreateRoom(Room room)
|
public void CreateRoom(Room room)
|
||||||
{
|
{
|
||||||
room.Host.Value = api.LocalUser;
|
room.Host.Value = api.LocalUser;
|
||||||
|
|
||||||
// Todo: Perform API request
|
var req = new CreateRoomRequest(room);
|
||||||
|
|
||||||
room.Created.Value = true;
|
req.Success += result => addRoom(room, result);
|
||||||
rooms.Add(room);
|
req.Failure += exception => Logger.Log($"Failed to create room: {exception}");
|
||||||
|
api.Queue(req);
|
||||||
|
}
|
||||||
|
|
||||||
|
protected override Task Poll()
|
||||||
|
{
|
||||||
|
if (!api.IsLoggedIn)
|
||||||
|
return base.Poll();
|
||||||
|
|
||||||
|
var tcs = new TaskCompletionSource<bool>();
|
||||||
|
|
||||||
|
var pollReq = new GetRoomsRequest();
|
||||||
|
|
||||||
|
pollReq.Success += result =>
|
||||||
|
{
|
||||||
|
foreach (var r in result)
|
||||||
|
{
|
||||||
|
foreach (var pi in r.Playlist)
|
||||||
|
{
|
||||||
|
pi.Ruleset = rulesets.GetRuleset(pi.RulesetID);
|
||||||
|
pi.SetRulesets(rulesets);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Temporarily
|
||||||
|
r.Beatmap.Value = r.Playlist.FirstOrDefault()?.Beatmap;
|
||||||
|
|
||||||
|
var existing = rooms.FirstOrDefault(e => e.RoomID.Value == r.RoomID.Value);
|
||||||
|
if (existing == null)
|
||||||
|
rooms.Add(r);
|
||||||
|
else
|
||||||
|
existing.CopyFrom(r);
|
||||||
|
}
|
||||||
|
|
||||||
|
tcs.SetResult(true);
|
||||||
|
};
|
||||||
|
|
||||||
|
pollReq.Failure += _ => tcs.SetResult(false);
|
||||||
|
|
||||||
|
api.Queue(pollReq);
|
||||||
|
|
||||||
|
return tcs.Task;
|
||||||
|
}
|
||||||
|
|
||||||
|
private void addRoom(Room local, Room remote)
|
||||||
|
{
|
||||||
|
local.CopyFrom(remote);
|
||||||
|
|
||||||
|
var existing = rooms.FirstOrDefault(e => e.RoomID.Value == local.RoomID.Value);
|
||||||
|
if (existing != null)
|
||||||
|
rooms.Remove(existing);
|
||||||
|
rooms.Add(local);
|
||||||
|
}
|
||||||
|
|
||||||
|
private class CreateRoomRequest : APIRequest<Room>
|
||||||
|
{
|
||||||
|
private readonly Room room;
|
||||||
|
|
||||||
|
public CreateRoomRequest(Room room)
|
||||||
|
{
|
||||||
|
this.room = room;
|
||||||
|
}
|
||||||
|
|
||||||
|
protected override WebRequest CreateWebRequest()
|
||||||
|
{
|
||||||
|
var req = base.CreateWebRequest();
|
||||||
|
|
||||||
|
req.ContentType = "application/json";
|
||||||
|
req.Method = HttpMethod.Post;
|
||||||
|
|
||||||
|
req.AddRaw(JsonConvert.SerializeObject(room));
|
||||||
|
|
||||||
|
return req;
|
||||||
|
}
|
||||||
|
|
||||||
|
protected override string Target => "rooms";
|
||||||
|
}
|
||||||
|
|
||||||
|
private class GetRoomsRequest : APIRequest<List<Room>>
|
||||||
|
{
|
||||||
|
protected override string Target => "rooms";
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user