mirror of
https://github.com/ppy/osu.git
synced 2024-12-14 23:12:56 +08:00
Add SpotlightsLayout to RankingsOverlay
This commit is contained in:
parent
b04a4b5c8a
commit
0b6558dc40
@ -5,7 +5,6 @@ using System;
|
||||
using System.Collections.Generic;
|
||||
using osu.Framework.Allocation;
|
||||
using osu.Framework.Bindables;
|
||||
using osu.Game.Online.API.Requests.Responses;
|
||||
using osu.Game.Overlays;
|
||||
using osu.Game.Overlays.Rankings;
|
||||
using osu.Game.Rulesets;
|
||||
@ -35,25 +34,7 @@ namespace osu.Game.Tests.Visual.Online
|
||||
{
|
||||
Current = { BindTarget = scope },
|
||||
Country = { BindTarget = countryBindable },
|
||||
Ruleset = { BindTarget = ruleset },
|
||||
Spotlights = new[]
|
||||
{
|
||||
new APISpotlight
|
||||
{
|
||||
Id = 1,
|
||||
Name = "Spotlight 1"
|
||||
},
|
||||
new APISpotlight
|
||||
{
|
||||
Id = 2,
|
||||
Name = "Spotlight 2"
|
||||
},
|
||||
new APISpotlight
|
||||
{
|
||||
Id = 3,
|
||||
Name = "Spotlight 3"
|
||||
}
|
||||
}
|
||||
Ruleset = { BindTarget = ruleset }
|
||||
});
|
||||
|
||||
var country = new Country
|
||||
|
@ -35,6 +35,12 @@ namespace osu.Game.Tests.Visual.Online
|
||||
Add(selector = new SpotlightSelector());
|
||||
}
|
||||
|
||||
[Test]
|
||||
public void TestVisibility()
|
||||
{
|
||||
AddStep("Toggle Visibility", selector.ToggleVisibility);
|
||||
}
|
||||
|
||||
[Test]
|
||||
public void TestLocalSpotlights()
|
||||
{
|
||||
|
@ -6,24 +6,14 @@ using osu.Framework.Bindables;
|
||||
using osu.Game.Graphics.UserInterface;
|
||||
using osu.Game.Rulesets;
|
||||
using osu.Game.Users;
|
||||
using System.Collections.Generic;
|
||||
using osu.Framework.Graphics.Containers;
|
||||
using osu.Game.Online.API.Requests.Responses;
|
||||
|
||||
namespace osu.Game.Overlays.Rankings
|
||||
{
|
||||
public class RankingsOverlayHeader : TabControlOverlayHeader<RankingsScope>
|
||||
{
|
||||
public readonly Bindable<RulesetInfo> Ruleset = new Bindable<RulesetInfo>();
|
||||
public readonly Bindable<APISpotlight> Spotlight = new Bindable<APISpotlight>();
|
||||
public readonly Bindable<Country> Country = new Bindable<Country>();
|
||||
|
||||
public IEnumerable<APISpotlight> Spotlights
|
||||
{
|
||||
get => SpotlightSelector.Spotlights;
|
||||
set => SpotlightSelector.Spotlights = value;
|
||||
}
|
||||
|
||||
protected override ScreenTitle CreateTitle() => new RankingsTitle
|
||||
{
|
||||
Scope = { BindTarget = Current }
|
||||
@ -34,37 +24,11 @@ namespace osu.Game.Overlays.Rankings
|
||||
Current = Ruleset
|
||||
};
|
||||
|
||||
public SpotlightSelector SpotlightSelector;
|
||||
|
||||
protected override Drawable CreateContent() => new FillFlowContainer
|
||||
protected override Drawable CreateContent() => new CountryFilter
|
||||
{
|
||||
RelativeSizeAxes = Axes.X,
|
||||
AutoSizeAxes = Axes.Y,
|
||||
Direction = FillDirection.Vertical,
|
||||
Children = new Drawable[]
|
||||
{
|
||||
new CountryFilter
|
||||
{
|
||||
Current = Country
|
||||
},
|
||||
SpotlightSelector = new SpotlightSelector
|
||||
{
|
||||
Current = { BindTarget = Spotlight }
|
||||
}
|
||||
}
|
||||
Current = Country
|
||||
};
|
||||
|
||||
protected override void LoadComplete()
|
||||
{
|
||||
Current.BindValueChanged(onCurrentChanged, true);
|
||||
base.LoadComplete();
|
||||
}
|
||||
|
||||
private void onCurrentChanged(ValueChangedEvent<RankingsScope> scope)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
private class RankingsTitle : ScreenTitle
|
||||
{
|
||||
public readonly Bindable<RankingsScope> Scope = new Bindable<RankingsScope>();
|
||||
|
@ -18,8 +18,10 @@ using osu.Game.Online.API.Requests;
|
||||
|
||||
namespace osu.Game.Overlays.Rankings
|
||||
{
|
||||
public class SpotlightSelector : CompositeDrawable, IHasCurrentValue<APISpotlight>
|
||||
public class SpotlightSelector : VisibilityContainer, IHasCurrentValue<APISpotlight>
|
||||
{
|
||||
private const int duration = 300;
|
||||
|
||||
private readonly Box background;
|
||||
private readonly SpotlightsDropdown dropdown;
|
||||
|
||||
@ -37,52 +39,59 @@ namespace osu.Game.Overlays.Rankings
|
||||
set => dropdown.Items = value;
|
||||
}
|
||||
|
||||
protected override bool StartHidden => true;
|
||||
|
||||
private readonly InfoColumn startDateColumn;
|
||||
private readonly InfoColumn endDateColumn;
|
||||
private readonly InfoColumn mapCountColumn;
|
||||
private readonly InfoColumn participantsColumn;
|
||||
private readonly Container content;
|
||||
|
||||
public SpotlightSelector()
|
||||
{
|
||||
RelativeSizeAxes = Axes.X;
|
||||
Height = 100;
|
||||
AddRangeInternal(new Drawable[]
|
||||
Add(content = new Container
|
||||
{
|
||||
background = new Box
|
||||
RelativeSizeAxes = Axes.Both,
|
||||
Children = new Drawable[]
|
||||
{
|
||||
RelativeSizeAxes = Axes.Both,
|
||||
},
|
||||
new Container
|
||||
{
|
||||
RelativeSizeAxes = Axes.Both,
|
||||
Padding = new MarginPadding { Horizontal = UserProfileOverlay.CONTENT_X_MARGIN, Vertical = 10 },
|
||||
Children = new Drawable[]
|
||||
background = new Box
|
||||
{
|
||||
dropdown = new SpotlightsDropdown
|
||||
RelativeSizeAxes = Axes.Both,
|
||||
},
|
||||
new Container
|
||||
{
|
||||
RelativeSizeAxes = Axes.Both,
|
||||
Padding = new MarginPadding { Horizontal = UserProfileOverlay.CONTENT_X_MARGIN, Vertical = 10 },
|
||||
Children = new Drawable[]
|
||||
{
|
||||
Anchor = Anchor.TopCentre,
|
||||
Origin = Anchor.TopCentre,
|
||||
RelativeSizeAxes = Axes.X,
|
||||
Current = Current,
|
||||
Depth = -float.MaxValue
|
||||
},
|
||||
new FillFlowContainer
|
||||
{
|
||||
Anchor = Anchor.BottomRight,
|
||||
Origin = Anchor.BottomRight,
|
||||
AutoSizeAxes = Axes.Both,
|
||||
Direction = FillDirection.Horizontal,
|
||||
Spacing = new Vector2(15, 0),
|
||||
Children = new Drawable[]
|
||||
dropdown = new SpotlightsDropdown
|
||||
{
|
||||
startDateColumn = new InfoColumn(@"Start Date"),
|
||||
endDateColumn = new InfoColumn(@"End Date"),
|
||||
mapCountColumn = new InfoColumn(@"Map Count"),
|
||||
participantsColumn = new InfoColumn(@"Participants")
|
||||
Anchor = Anchor.TopCentre,
|
||||
Origin = Anchor.TopCentre,
|
||||
RelativeSizeAxes = Axes.X,
|
||||
Current = Current,
|
||||
Depth = -float.MaxValue
|
||||
},
|
||||
new FillFlowContainer
|
||||
{
|
||||
Anchor = Anchor.BottomRight,
|
||||
Origin = Anchor.BottomRight,
|
||||
AutoSizeAxes = Axes.Both,
|
||||
Direction = FillDirection.Horizontal,
|
||||
Spacing = new Vector2(15, 0),
|
||||
Children = new Drawable[]
|
||||
{
|
||||
startDateColumn = new InfoColumn(@"Start Date"),
|
||||
endDateColumn = new InfoColumn(@"End Date"),
|
||||
mapCountColumn = new InfoColumn(@"Map Count"),
|
||||
participantsColumn = new InfoColumn(@"Participants")
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
@ -100,6 +109,10 @@ namespace osu.Game.Overlays.Rankings
|
||||
participantsColumn.Value = response.Spotlight.Participants?.ToString("N0");
|
||||
}
|
||||
|
||||
protected override void PopIn() => content.FadeIn(duration, Easing.OutQuint);
|
||||
|
||||
protected override void PopOut() => content.FadeOut(duration, Easing.OutQuint);
|
||||
|
||||
private string dateToString(DateTimeOffset date) => date.ToString("yyyy-MM-dd");
|
||||
|
||||
private class InfoColumn : FillFlowContainer
|
||||
|
@ -35,11 +35,12 @@ namespace osu.Game.Overlays.Rankings
|
||||
private GetSpotlightRankingsRequest getRankingsRequest;
|
||||
private GetSpotlightsRequest spotlightsRequest;
|
||||
|
||||
private readonly SpotlightSelector selector;
|
||||
private readonly Container content;
|
||||
private readonly DimmedLoadingLayer loading;
|
||||
private SpotlightSelector selector;
|
||||
private Container content;
|
||||
private DimmedLoadingLayer loading;
|
||||
|
||||
public SpotlightsLayout()
|
||||
[BackgroundDependencyLoader]
|
||||
private void load()
|
||||
{
|
||||
RelativeSizeAxes = Axes.X;
|
||||
AutoSizeAxes = Axes.Y;
|
||||
@ -48,7 +49,6 @@ namespace osu.Game.Overlays.Rankings
|
||||
RelativeSizeAxes = Axes.X,
|
||||
AutoSizeAxes = Axes.Y,
|
||||
Direction = FillDirection.Vertical,
|
||||
Spacing = new Vector2(0, 20),
|
||||
Children = new Drawable[]
|
||||
{
|
||||
selector = new SpotlightSelector
|
||||
@ -65,8 +65,9 @@ namespace osu.Game.Overlays.Rankings
|
||||
{
|
||||
RelativeSizeAxes = Axes.X,
|
||||
AutoSizeAxes = Axes.Y,
|
||||
Margin = new MarginPadding { Vertical = 10 }
|
||||
},
|
||||
loading = new DimmedLoadingLayer(),
|
||||
loading = new DimmedLoadingLayer()
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -77,6 +78,8 @@ namespace osu.Game.Overlays.Rankings
|
||||
{
|
||||
base.LoadComplete();
|
||||
|
||||
selector.Show();
|
||||
|
||||
selectedSpotlight.BindValueChanged(onSpotlightChanged);
|
||||
Ruleset.BindValueChanged(onRulesetChanged);
|
||||
|
||||
|
@ -14,10 +14,6 @@ using osu.Game.Online.API;
|
||||
using System.Threading;
|
||||
using osu.Game.Online.API.Requests;
|
||||
using osu.Game.Overlays.Rankings.Tables;
|
||||
using osu.Game.Online.API.Requests.Responses;
|
||||
using System.Linq;
|
||||
using osuTK;
|
||||
using osu.Game.Overlays.Direct;
|
||||
|
||||
namespace osu.Game.Overlays
|
||||
{
|
||||
@ -26,13 +22,11 @@ namespace osu.Game.Overlays
|
||||
protected readonly Bindable<Country> Country = new Bindable<Country>();
|
||||
protected readonly Bindable<RankingsScope> Scope = new Bindable<RankingsScope>();
|
||||
private readonly Bindable<RulesetInfo> ruleset = new Bindable<RulesetInfo>();
|
||||
private readonly Bindable<APISpotlight> spotlight = new Bindable<APISpotlight>();
|
||||
|
||||
private readonly BasicScrollContainer scrollFlow;
|
||||
private readonly Container contentContainer;
|
||||
private readonly DimmedLoadingLayer loading;
|
||||
private readonly Box background;
|
||||
private readonly RankingsOverlayHeader header;
|
||||
|
||||
private APIRequest lastRequest;
|
||||
private CancellationTokenSource cancellationToken;
|
||||
@ -40,9 +34,6 @@ namespace osu.Game.Overlays
|
||||
[Resolved]
|
||||
private IAPIProvider api { get; set; }
|
||||
|
||||
[Resolved]
|
||||
private RulesetStore rulesets { get; set; }
|
||||
|
||||
public RankingsOverlay()
|
||||
: base(OverlayColourScheme.Green)
|
||||
{
|
||||
@ -63,15 +54,14 @@ namespace osu.Game.Overlays
|
||||
Direction = FillDirection.Vertical,
|
||||
Children = new Drawable[]
|
||||
{
|
||||
header = new RankingsOverlayHeader
|
||||
new RankingsOverlayHeader
|
||||
{
|
||||
Anchor = Anchor.TopCentre,
|
||||
Origin = Anchor.TopCentre,
|
||||
Depth = -float.MaxValue,
|
||||
Country = { BindTarget = Country },
|
||||
Current = { BindTarget = Scope },
|
||||
Ruleset = { BindTarget = ruleset },
|
||||
Spotlight = { BindTarget = spotlight }
|
||||
Ruleset = { BindTarget = ruleset }
|
||||
},
|
||||
new Container
|
||||
{
|
||||
@ -85,7 +75,7 @@ namespace osu.Game.Overlays
|
||||
Origin = Anchor.TopCentre,
|
||||
AutoSizeAxes = Axes.Y,
|
||||
RelativeSizeAxes = Axes.X,
|
||||
Margin = new MarginPadding { Vertical = 10 }
|
||||
Margin = new MarginPadding { Bottom = 10 }
|
||||
},
|
||||
loading = new DimmedLoadingLayer(),
|
||||
}
|
||||
@ -110,30 +100,25 @@ namespace osu.Game.Overlays
|
||||
if (Country.Value != null)
|
||||
Scope.Value = RankingsScope.Performance;
|
||||
|
||||
if (Scope.Value != RankingsScope.Spotlights)
|
||||
Scheduler.AddOnce(loadNewContent);
|
||||
Scheduler.AddOnce(loadNewContent);
|
||||
}, true);
|
||||
|
||||
Scope.BindValueChanged(_ =>
|
||||
{
|
||||
spotlightsRequest?.Cancel();
|
||||
|
||||
// country filtering is only valid for performance scope.
|
||||
if (Scope.Value != RankingsScope.Performance)
|
||||
Country.Value = null;
|
||||
|
||||
if (Scope.Value == RankingsScope.Spotlights && !header.Spotlights.Any())
|
||||
{
|
||||
getSpotlights();
|
||||
return;
|
||||
}
|
||||
|
||||
Scheduler.AddOnce(loadNewContent);
|
||||
}, true);
|
||||
|
||||
ruleset.BindValueChanged(_ => Scheduler.AddOnce(loadNewContent), true);
|
||||
ruleset.BindValueChanged(_ =>
|
||||
{
|
||||
if (Scope.Value == RankingsScope.Spotlights)
|
||||
return;
|
||||
|
||||
spotlight.BindValueChanged(_ => Scheduler.AddOnce(loadNewContent), true);
|
||||
Scheduler.AddOnce(loadNewContent);
|
||||
}, true);
|
||||
|
||||
base.LoadComplete();
|
||||
}
|
||||
@ -148,16 +133,6 @@ namespace osu.Game.Overlays
|
||||
Country.Value = requested;
|
||||
}
|
||||
|
||||
private GetSpotlightsRequest spotlightsRequest;
|
||||
|
||||
private void getSpotlights()
|
||||
{
|
||||
loading.Show();
|
||||
spotlightsRequest = new GetSpotlightsRequest();
|
||||
spotlightsRequest.Success += response => header.Spotlights = response.Spotlights;
|
||||
api.Queue(spotlightsRequest);
|
||||
}
|
||||
|
||||
private void loadNewContent()
|
||||
{
|
||||
loading.Show();
|
||||
@ -165,6 +140,15 @@ namespace osu.Game.Overlays
|
||||
cancellationToken?.Cancel();
|
||||
lastRequest?.Cancel();
|
||||
|
||||
if (Scope.Value == RankingsScope.Spotlights)
|
||||
{
|
||||
loadContent(new SpotlightsLayout
|
||||
{
|
||||
Ruleset = { BindTarget = ruleset }
|
||||
});
|
||||
return;
|
||||
}
|
||||
|
||||
var request = createScopedRequest();
|
||||
lastRequest = request;
|
||||
|
||||
@ -174,8 +158,9 @@ namespace osu.Game.Overlays
|
||||
return;
|
||||
}
|
||||
|
||||
request.Success += () => loadContent(createContentFromResponse(request));
|
||||
request.Success += () => loadContent(createTableFromResponse(request));
|
||||
request.Failure += _ => loadContent(null);
|
||||
|
||||
api.Queue(request);
|
||||
}
|
||||
|
||||
@ -191,15 +176,12 @@ namespace osu.Game.Overlays
|
||||
|
||||
case RankingsScope.Score:
|
||||
return new GetUserRankingsRequest(ruleset.Value, UserRankingsType.Score);
|
||||
|
||||
case RankingsScope.Spotlights:
|
||||
return new GetSpotlightRankingsRequest(ruleset.Value, header.Spotlight.Value.Id);
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
private Drawable createContentFromResponse(APIRequest request)
|
||||
private Drawable createTableFromResponse(APIRequest request)
|
||||
{
|
||||
switch (request)
|
||||
{
|
||||
@ -217,42 +199,11 @@ namespace osu.Game.Overlays
|
||||
|
||||
case GetCountryRankingsRequest countryRequest:
|
||||
return new CountriesTable(1, countryRequest.Result.Countries);
|
||||
|
||||
case GetSpotlightRankingsRequest spotlightRequest:
|
||||
return getSpotlightContent(spotlightRequest.Result);
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
private Drawable getSpotlightContent(GetSpotlightRankingsResponse response)
|
||||
{
|
||||
header.SpotlightSelector.ShowInfo(response);
|
||||
|
||||
return new FillFlowContainer
|
||||
{
|
||||
AutoSizeAxes = Axes.Y,
|
||||
RelativeSizeAxes = Axes.X,
|
||||
Direction = FillDirection.Vertical,
|
||||
Spacing = new Vector2(0, 20),
|
||||
Children = new Drawable[]
|
||||
{
|
||||
new ScoresTable(1, response.Users),
|
||||
new FillFlowContainer
|
||||
{
|
||||
AutoSizeAxes = Axes.Y,
|
||||
RelativeSizeAxes = Axes.X,
|
||||
Spacing = new Vector2(10),
|
||||
Children = response.BeatmapSets.Select(b => new DirectGridPanel(b.ToBeatmapSet(rulesets))
|
||||
{
|
||||
Anchor = Anchor.TopCentre,
|
||||
Origin = Anchor.TopCentre,
|
||||
}).ToList()
|
||||
}
|
||||
}
|
||||
};
|
||||
}
|
||||
|
||||
private void loadContent(Drawable content)
|
||||
{
|
||||
scrollFlow.ScrollToStart();
|
||||
@ -264,10 +215,10 @@ namespace osu.Game.Overlays
|
||||
return;
|
||||
}
|
||||
|
||||
LoadComponentAsync(content, t =>
|
||||
LoadComponentAsync(content, loaded =>
|
||||
{
|
||||
loading.Hide();
|
||||
contentContainer.Child = content;
|
||||
contentContainer.Child = loaded;
|
||||
}, (cancellationToken = new CancellationTokenSource()).Token);
|
||||
}
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user