1
0
mirror of https://github.com/ppy/osu.git synced 2024-12-14 15:26:07 +08:00

Merge pull request #2735 from DrabWeb/beatmap-set-downloader

Centralise downloaded beatmap set logic
This commit is contained in:
Dean Herbert 2018-06-08 21:03:21 +09:00 committed by GitHub
commit 4e1b801dd8
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
8 changed files with 221 additions and 130 deletions

View File

@ -0,0 +1,84 @@
// 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.Linq;
using osu.Framework.Allocation;
using osu.Framework.Configuration;
using osu.Framework.Graphics;
namespace osu.Game.Beatmaps.Drawables
{
/// <summary>
/// A component to allow downloading of a beatmap set. Automatically handles state syncing between other instances.
/// </summary>
public class BeatmapSetDownloader : Component
{
private readonly BeatmapSetInfo set;
private readonly bool noVideo;
private BeatmapManager beatmaps;
/// <summary>
/// Whether the associated beatmap set has been downloading (by this instance or any other instance).
/// </summary>
public readonly BindableBool Downloaded = new BindableBool();
public BeatmapSetDownloader(BeatmapSetInfo set, bool noVideo = false)
{
this.set = set;
this.noVideo = noVideo;
}
[BackgroundDependencyLoader]
private void load(BeatmapManager beatmaps)
{
this.beatmaps = beatmaps;
beatmaps.ItemAdded += setAdded;
beatmaps.ItemRemoved += setRemoved;
// initial value
if (set.OnlineBeatmapSetID != null)
Downloaded.Value = beatmaps.QueryBeatmapSets(s => s.OnlineBeatmapSetID == set.OnlineBeatmapSetID && !s.DeletePending).Any();
}
protected override void Dispose(bool isDisposing)
{
base.Dispose(isDisposing);
if (beatmaps != null)
{
beatmaps.ItemAdded -= setAdded;
beatmaps.ItemRemoved -= setRemoved;
}
}
/// <summary>
/// Begin downloading the associated beatmap set.
/// </summary>
/// <returns>True if downloading began. False if an existing download is active or completed.</returns>
public bool Download()
{
if (Downloaded.Value)
return false;
if (beatmaps.GetExistingDownload(set) != null)
return false;
beatmaps.Download(set, noVideo);
return true;
}
private void setAdded(BeatmapSetInfo s)
{
if (s.OnlineBeatmapSetID == set.OnlineBeatmapSetID)
Downloaded.Value = true;
}
private void setRemoved(BeatmapSetInfo s)
{
if (s.OnlineBeatmapSetID == set.OnlineBeatmapSetID)
Downloaded.Value = false;
}
}
}

View File

@ -3,6 +3,8 @@
using osu.Framework.Graphics;
using osu.Framework.Graphics.Containers;
using osu.Game.Beatmaps;
using osu.Game.Beatmaps.Drawables;
using osu.Game.Graphics;
using osu.Game.Graphics.Sprites;
using OpenTK;
@ -11,10 +13,11 @@ namespace osu.Game.Overlays.BeatmapSet.Buttons
{
public class DownloadButton : HeaderButton
{
public DownloadButton(string title, string subtitle)
public DownloadButton(BeatmapSetInfo set, bool noVideo = false)
{
Width = 120;
BeatmapSetDownloader downloader;
Add(new Container
{
Depth = -1,
@ -22,6 +25,7 @@ namespace osu.Game.Overlays.BeatmapSet.Buttons
Padding = new MarginPadding { Horizontal = 10 },
Children = new Drawable[]
{
downloader = new BeatmapSetDownloader(set, noVideo),
new FillFlowContainer
{
Anchor = Anchor.CentreLeft,
@ -32,13 +36,13 @@ namespace osu.Game.Overlays.BeatmapSet.Buttons
{
new OsuSpriteText
{
Text = title,
Text = "Download",
TextSize = 13,
Font = @"Exo2.0-Bold",
},
new OsuSpriteText
{
Text = subtitle,
Text = set.OnlineInfo.HasVideo && noVideo ? "without Video" : string.Empty,
TextSize = 11,
Font = @"Exo2.0-Bold",
},
@ -54,6 +58,25 @@ namespace osu.Game.Overlays.BeatmapSet.Buttons
},
},
});
Action = () =>
{
if (!downloader.Download())
{
Content.MoveToX(-5, 50, Easing.OutSine).Then()
.MoveToX(5, 100, Easing.InOutSine).Then()
.MoveToX(-5, 100, Easing.InOutSine).Then()
.MoveToX(0, 50, Easing.InSine);
}
};
downloader.Downloaded.ValueChanged += d =>
{
if (d)
this.FadeOut(200);
else
this.FadeIn(200);
};
}
}
}

View File

@ -35,8 +35,6 @@ namespace osu.Game.Overlays.BeatmapSet
private readonly BeatmapSetOnlineStatusPill onlineStatusPill;
public Details Details;
private BeatmapManager beatmaps;
public readonly BeatmapPicker Picker;
private BeatmapSetInfo beatmapSet;
@ -68,8 +66,24 @@ namespace osu.Game.Overlays.BeatmapSet
downloadButtonsContainer.FadeIn(transition_duration);
favouriteButton.FadeIn(transition_duration);
noVideoButtons.FadeTo(BeatmapSet.OnlineInfo.HasVideo ? 0 : 1, transition_duration);
videoButtons.FadeTo(BeatmapSet.OnlineInfo.HasVideo ? 1 : 0, transition_duration);
if (BeatmapSet.OnlineInfo.HasVideo)
{
videoButtons.Children = new[]
{
new DownloadButton(BeatmapSet),
new DownloadButton(BeatmapSet, true),
};
videoButtons.FadeIn(transition_duration);
noVideoButtons.FadeOut(transition_duration);
}
else
{
noVideoButtons.Child = new DownloadButton(BeatmapSet);
noVideoButtons.FadeIn(transition_duration);
videoButtons.FadeOut(transition_duration);
}
}
else
{
@ -192,27 +206,12 @@ namespace osu.Game.Overlays.BeatmapSet
{
RelativeSizeAxes = Axes.Both,
Alpha = 0f,
Child = new DownloadButton("Download", @"")
{
Action = () => download(false),
},
},
videoButtons = new FillFlowContainer
{
RelativeSizeAxes = Axes.Both,
Spacing = new Vector2(buttons_spacing),
Alpha = 0f,
Children = new[]
{
new DownloadButton("Download", "with Video")
{
Action = () => download(false),
},
new DownloadButton("Download", "without Video")
{
Action = () => download(true),
},
},
},
},
},
@ -248,41 +247,10 @@ namespace osu.Game.Overlays.BeatmapSet
}
[BackgroundDependencyLoader]
private void load(OsuColour colours, BeatmapManager beatmaps)
private void load(OsuColour colours)
{
tabsBg.Colour = colours.Gray3;
this.beatmaps = beatmaps;
beatmaps.ItemAdded += handleBeatmapAdd;
updateDisplay();
}
protected override void Dispose(bool isDisposing)
{
base.Dispose(isDisposing);
if (beatmaps != null) beatmaps.ItemAdded -= handleBeatmapAdd;
}
private void handleBeatmapAdd(BeatmapSetInfo beatmap) => Schedule(() =>
{
if (beatmap.OnlineBeatmapSetID == BeatmapSet?.OnlineBeatmapSetID)
downloadButtonsContainer.FadeOut(transition_duration);
});
private void download(bool noVideo)
{
if (beatmaps.GetExistingDownload(BeatmapSet) != null)
{
downloadButtonsContainer.MoveToX(-5, 50, Easing.OutSine).Then()
.MoveToX(5, 100, Easing.InOutSine).Then()
.MoveToX(-5, 100, Easing.InOutSine).Then()
.MoveToX(0, 50, Easing.InSine).Then();
return;
}
beatmaps.Download(BeatmapSet, noVideo);
}
}
}

View File

@ -166,14 +166,13 @@ namespace osu.Game.Overlays.Direct
},
},
},
new DownloadButton
new DownloadButton(SetInfo)
{
Size = new Vector2(30),
Margin = new MarginPadding(horizontal_padding),
Anchor = Anchor.CentreRight,
Origin = Anchor.CentreRight,
Colour = colours.Gray5,
Action = StartDownload
},
},
},

View File

@ -12,28 +12,31 @@ using osu.Game.Graphics.Sprites;
using osu.Framework.Allocation;
using osu.Framework.Localisation;
using osu.Framework.Graphics.Shapes;
using osu.Framework.Input;
using osu.Game.Beatmaps;
namespace osu.Game.Overlays.Direct
{
public class DirectListPanel : DirectPanel
{
private const float transition_duration = 120;
private const float horizontal_padding = 10;
private const float vertical_padding = 5;
private const float height = 70;
private PlayButton playButton;
private Box progressBar;
private Container downloadContainer;
protected override PlayButton PlayButton => playButton;
protected override Box PreviewBar => progressBar;
public DirectListPanel(BeatmapSetInfo beatmap) : base(beatmap)
{
RelativeSizeAxes = Axes.X;
Height = height;
}
private PlayButton playButton;
private Box progressBar;
protected override PlayButton PlayButton => playButton;
protected override Box PreviewBar => progressBar;
[BackgroundDependencyLoader]
private void load(LocalisationEngine localisation, OsuColour colours)
{
@ -59,7 +62,7 @@ namespace osu.Game.Overlays.Direct
AutoSizeAxes = Axes.Both,
Direction = FillDirection.Horizontal,
LayoutEasing = Easing.OutQuint,
LayoutDuration = 120,
LayoutDuration = transition_duration,
Spacing = new Vector2(10, 0),
Children = new Drawable[]
{
@ -104,53 +107,69 @@ namespace osu.Game.Overlays.Direct
Anchor = Anchor.TopRight,
Origin = Anchor.TopRight,
AutoSizeAxes = Axes.Both,
Direction = FillDirection.Vertical,
Margin = new MarginPadding { Right = height - vertical_padding * 2 + vertical_padding },
Direction = FillDirection.Horizontal,
LayoutEasing = Easing.OutQuint,
LayoutDuration = transition_duration,
Children = new Drawable[]
{
new Statistic(FontAwesome.fa_play_circle, SetInfo.OnlineInfo?.PlayCount ?? 0)
downloadContainer = new Container
{
Margin = new MarginPadding { Right = 1 },
Anchor = Anchor.TopRight,
Origin = Anchor.TopRight,
AutoSizeAxes = Axes.Both,
Alpha = 0,
Child = new DownloadButton(SetInfo)
{
Size = new Vector2(height - vertical_padding * 2),
Margin = new MarginPadding { Left = vertical_padding },
},
},
new Statistic(FontAwesome.fa_heart, SetInfo.OnlineInfo?.FavouriteCount ?? 0),
new FillFlowContainer
{
Anchor = Anchor.TopRight,
Origin = Anchor.TopRight,
AutoSizeAxes = Axes.Both,
Direction = FillDirection.Horizontal,
Children = new[]
Direction = FillDirection.Vertical,
Children = new Drawable[]
{
new OsuSpriteText
new Statistic(FontAwesome.fa_play_circle, SetInfo.OnlineInfo?.PlayCount ?? 0)
{
Text = "mapped by ",
TextSize = 14,
Margin = new MarginPadding { Right = 1 },
},
new Statistic(FontAwesome.fa_heart, SetInfo.OnlineInfo?.FavouriteCount ?? 0),
new FillFlowContainer
{
Anchor = Anchor.TopRight,
Origin = Anchor.TopRight,
AutoSizeAxes = Axes.Both,
Direction = FillDirection.Horizontal,
Children = new[]
{
new OsuSpriteText
{
Text = "mapped by ",
TextSize = 14,
},
new OsuSpriteText
{
Text = SetInfo.Metadata.Author.Username,
TextSize = 14,
Font = @"Exo2.0-SemiBoldItalic",
},
},
},
new OsuSpriteText
{
Text = SetInfo.Metadata.Author.Username,
Text = $"from {SetInfo.Metadata.Source}",
Anchor = Anchor.TopRight,
Origin = Anchor.TopRight,
TextSize = 14,
Font = @"Exo2.0-SemiBoldItalic",
Alpha = string.IsNullOrEmpty(SetInfo.Metadata.Source) ? 0f : 1f,
},
},
},
new OsuSpriteText
{
Text = $"from {SetInfo.Metadata.Source}",
Anchor = Anchor.TopRight,
Origin = Anchor.TopRight,
TextSize = 14,
Alpha = string.IsNullOrEmpty(SetInfo.Metadata.Source) ? 0f : 1f,
},
},
},
new DownloadButton
{
Anchor = Anchor.TopRight,
Origin = Anchor.TopRight,
Size = new Vector2(height - vertical_padding * 2),
Action = StartDownload
},
},
},
progressBar = new Box
@ -165,5 +184,17 @@ namespace osu.Game.Overlays.Direct
},
});
}
protected override bool OnHover(InputState state)
{
downloadContainer.FadeIn(transition_duration, Easing.InOutQuint);
return base.OnHover(state);
}
protected override void OnHoverLost(InputState state)
{
downloadContainer.FadeOut(transition_duration, Easing.InOutQuint);
base.OnHoverLost(state);
}
}
}

View File

@ -147,22 +147,6 @@ namespace osu.Game.Overlays.Direct
protected void ShowInformation() => beatmapSetOverlay?.ShowBeatmapSet(SetInfo);
protected void StartDownload()
{
if (beatmaps.GetExistingDownload(SetInfo) != null)
{
// we already have an active download running.
content.MoveToX(-5, 50, Easing.OutSine).Then()
.MoveToX(5, 100, Easing.InOutSine).Then()
.MoveToX(-5, 100, Easing.InOutSine).Then()
.MoveToX(0, 50, Easing.InSine).Then();
return;
}
beatmaps.Download(SetInfo);
}
private void attachDownload(DownloadBeatmapSetRequest request)
{
if (request.BeatmapSet.OnlineBeatmapSetID != SetInfo.OnlineBeatmapSetID)

View File

@ -3,6 +3,8 @@
using osu.Framework.Graphics;
using osu.Framework.Input;
using osu.Game.Beatmaps;
using osu.Game.Beatmaps.Drawables;
using osu.Game.Graphics;
using osu.Game.Graphics.Containers;
using OpenTK;
@ -13,10 +15,12 @@ namespace osu.Game.Overlays.Direct
{
private readonly SpriteIcon icon;
public DownloadButton()
public DownloadButton(BeatmapSetInfo set, bool noVideo = false)
{
BeatmapSetDownloader downloader;
Children = new Drawable[]
{
downloader = new BeatmapSetDownloader(set, noVideo),
icon = new SpriteIcon
{
Anchor = Anchor.Centre,
@ -25,6 +29,25 @@ namespace osu.Game.Overlays.Direct
Icon = FontAwesome.fa_osu_chevron_down_o,
},
};
Action = () =>
{
if (!downloader.Download())
{
Content.MoveToX(-5, 50, Easing.OutSine).Then()
.MoveToX(5, 100, Easing.InOutSine).Then()
.MoveToX(-5, 100, Easing.InOutSine).Then()
.MoveToX(0, 50, Easing.InSine);
}
};
downloader.Downloaded.ValueChanged += d =>
{
if (d)
this.FadeOut(200);
else
this.FadeIn(200);
};
}
protected override bool OnMouseDown(InputState state, MouseDownEventArgs args)

View File

@ -28,7 +28,6 @@ namespace osu.Game.Overlays
private APIAccess api;
private RulesetStore rulesets;
private BeatmapManager beatmaps;
private readonly FillFlowContainer resultCountsContainer;
private readonly OsuSpriteText resultCountsText;
@ -177,24 +176,14 @@ namespace osu.Game.Overlays
}
[BackgroundDependencyLoader]
private void load(OsuColour colours, APIAccess api, RulesetStore rulesets, BeatmapManager beatmaps)
private void load(OsuColour colours, APIAccess api, RulesetStore rulesets)
{
this.api = api;
this.rulesets = rulesets;
this.beatmaps = beatmaps;
resultCountsContainer.Colour = colours.Yellow;
beatmaps.ItemAdded += setAdded;
}
private void setAdded(BeatmapSetInfo set) => Schedule(() =>
{
// if a new map was imported, we should remove it from search results (download completed etc.)
panels?.FirstOrDefault(p => p.SetInfo.OnlineBeatmapSetID == set.OnlineBeatmapSetID)?.FadeOut(400).Expire();
BeatmapSets = BeatmapSets?.Where(b => b.OnlineBeatmapSetID != set.OnlineBeatmapSetID);
});
private void updateResultCounts()
{
resultCountsContainer.FadeTo(ResultAmounts == null ? 0f : 1f, 200, Easing.OutQuint);
@ -297,9 +286,7 @@ namespace osu.Game.Overlays
{
Task.Run(() =>
{
var onlineIds = response.Select(r => r.OnlineBeatmapSetID).ToList();
var presentOnlineIds = beatmaps.QueryBeatmapSets(s => onlineIds.Contains(s.OnlineBeatmapSetID) && !s.DeletePending).Select(r => r.OnlineBeatmapSetID).ToList();
var sets = response.Select(r => r.ToBeatmapSet(rulesets)).Where(b => !presentOnlineIds.Contains(b.OnlineBeatmapSetID)).ToList();
var sets = response.Select(r => r.ToBeatmapSet(rulesets)).ToList();
// may not need scheduling; loads async internally.
Schedule(() =>
@ -323,14 +310,6 @@ namespace osu.Game.Overlays
private int distinctCount(List<string> list) => list.Distinct().ToArray().Length;
protected override void Dispose(bool isDisposing)
{
base.Dispose(isDisposing);
if (beatmaps != null)
beatmaps.ItemAdded -= setAdded;
}
public class ResultCounts
{
public readonly int Artists;