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

Merge pull request #10180 from smoogipoo/beatmap-conversion-cancellation

Make beatmap conversion support cancellation tokens
This commit is contained in:
Dean Herbert 2020-09-17 22:30:46 +09:00 committed by GitHub
commit 141fbbf5bb
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
9 changed files with 62 additions and 22 deletions

View File

@ -5,6 +5,7 @@ using osu.Game.Beatmaps;
using osu.Game.Rulesets.Catch.Objects;
using System.Collections.Generic;
using System.Linq;
using System.Threading;
using osu.Game.Rulesets.Objects.Types;
using osu.Game.Rulesets.Objects;
using osu.Framework.Extensions.IEnumerableExtensions;
@ -20,7 +21,7 @@ namespace osu.Game.Rulesets.Catch.Beatmaps
public override bool CanConvert() => Beatmap.HitObjects.All(h => h is IHasXPosition);
protected override IEnumerable<CatchHitObject> ConvertHitObject(HitObject obj, IBeatmap beatmap)
protected override IEnumerable<CatchHitObject> ConvertHitObject(HitObject obj, IBeatmap beatmap, CancellationToken cancellationToken)
{
var positionData = obj as IHasXPosition;
var comboData = obj as IHasCombo;

View File

@ -5,6 +5,7 @@ using osu.Game.Rulesets.Mania.Objects;
using System;
using System.Linq;
using System.Collections.Generic;
using System.Threading;
using osu.Game.Audio;
using osu.Game.Beatmaps;
using osu.Game.Rulesets.Objects;
@ -68,14 +69,14 @@ namespace osu.Game.Rulesets.Mania.Beatmaps
public override bool CanConvert() => Beatmap.HitObjects.All(h => h is IHasXPosition);
protected override Beatmap<ManiaHitObject> ConvertBeatmap(IBeatmap original)
protected override Beatmap<ManiaHitObject> ConvertBeatmap(IBeatmap original, CancellationToken cancellationToken)
{
BeatmapDifficulty difficulty = original.BeatmapInfo.BaseDifficulty;
int seed = (int)MathF.Round(difficulty.DrainRate + difficulty.CircleSize) * 20 + (int)(difficulty.OverallDifficulty * 41.2) + (int)MathF.Round(difficulty.ApproachRate);
Random = new FastRandom(seed);
return base.ConvertBeatmap(original);
return base.ConvertBeatmap(original, cancellationToken);
}
protected override Beatmap<ManiaHitObject> CreateBeatmap()
@ -88,7 +89,7 @@ namespace osu.Game.Rulesets.Mania.Beatmaps
return beatmap;
}
protected override IEnumerable<ManiaHitObject> ConvertHitObject(HitObject original, IBeatmap beatmap)
protected override IEnumerable<ManiaHitObject> ConvertHitObject(HitObject original, IBeatmap beatmap, CancellationToken cancellationToken)
{
if (original is ManiaHitObject maniaOriginal)
{

View File

@ -8,6 +8,7 @@ using osu.Game.Rulesets.Osu.Objects;
using System.Collections.Generic;
using osu.Game.Rulesets.Objects.Types;
using System.Linq;
using System.Threading;
using osu.Game.Rulesets.Osu.UI;
using osu.Framework.Extensions.IEnumerableExtensions;
@ -22,7 +23,7 @@ namespace osu.Game.Rulesets.Osu.Beatmaps
public override bool CanConvert() => Beatmap.HitObjects.All(h => h is IHasPosition);
protected override IEnumerable<OsuHitObject> ConvertHitObject(HitObject original, IBeatmap beatmap)
protected override IEnumerable<OsuHitObject> ConvertHitObject(HitObject original, IBeatmap beatmap, CancellationToken cancellationToken)
{
var positionData = original as IHasPosition;
var comboData = original as IHasCombo;

View File

@ -8,6 +8,7 @@ using osu.Game.Rulesets.Taiko.Objects;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading;
using osu.Game.Audio;
using osu.Game.Beatmaps.ControlPoints;
using osu.Game.Beatmaps.Formats;
@ -48,14 +49,14 @@ namespace osu.Game.Rulesets.Taiko.Beatmaps
public override bool CanConvert() => true;
protected override Beatmap<TaikoHitObject> ConvertBeatmap(IBeatmap original)
protected override Beatmap<TaikoHitObject> ConvertBeatmap(IBeatmap original, CancellationToken cancellationToken)
{
// Rewrite the beatmap info to add the slider velocity multiplier
original.BeatmapInfo = original.BeatmapInfo.Clone();
original.BeatmapInfo.BaseDifficulty = original.BeatmapInfo.BaseDifficulty.Clone();
original.BeatmapInfo.BaseDifficulty.SliderMultiplier *= LEGACY_VELOCITY_MULTIPLIER;
Beatmap<TaikoHitObject> converted = base.ConvertBeatmap(original);
Beatmap<TaikoHitObject> converted = base.ConvertBeatmap(original, cancellationToken);
if (original.BeatmapInfo.RulesetID == 3)
{
@ -72,7 +73,7 @@ namespace osu.Game.Rulesets.Taiko.Beatmaps
return converted;
}
protected override IEnumerable<TaikoHitObject> ConvertHitObject(HitObject obj, IBeatmap beatmap)
protected override IEnumerable<TaikoHitObject> ConvertHitObject(HitObject obj, IBeatmap beatmap, CancellationToken cancellationToken)
{
// Old osu! used hit sounding to determine various hit type information
IList<HitSampleInfo> samples = obj.Samples;

View File

@ -4,6 +4,7 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading;
using NUnit.Framework;
using osu.Framework.Bindables;
using osu.Framework.Graphics;
@ -276,7 +277,7 @@ namespace osu.Game.Tests.Visual.Gameplay
public override bool CanConvert() => true;
protected override IEnumerable<TestHitObject> ConvertHitObject(HitObject original, IBeatmap beatmap)
protected override IEnumerable<TestHitObject> ConvertHitObject(HitObject original, IBeatmap beatmap, CancellationToken cancellationToken)
{
yield return new TestHitObject
{

View File

@ -4,6 +4,7 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading;
using osu.Game.Rulesets;
using osu.Game.Rulesets.Objects;
@ -26,6 +27,8 @@ namespace osu.Game.Beatmaps
public IBeatmap Beatmap { get; }
private CancellationToken cancellationToken;
protected BeatmapConverter(IBeatmap beatmap, Ruleset ruleset)
{
Beatmap = beatmap;
@ -36,14 +39,25 @@ namespace osu.Game.Beatmaps
/// </summary>
public abstract bool CanConvert();
/// <summary>
/// Converts <see cref="Beatmap"/>.
/// </summary>
/// <returns>The converted Beatmap.</returns>
public IBeatmap Convert()
public IBeatmap Convert(CancellationToken cancellationToken = default)
{
this.cancellationToken = cancellationToken;
// We always operate on a clone of the original beatmap, to not modify it game-wide
return ConvertBeatmap(Beatmap.Clone());
return ConvertBeatmap(Beatmap.Clone(), cancellationToken);
}
/// <summary>
/// Performs the conversion of a Beatmap using this Beatmap Converter.
/// </summary>
/// <param name="original">The un-converted Beatmap.</param>
/// <param name="cancellationToken">The cancellation token.</param>
/// <returns>The converted Beatmap.</returns>
protected virtual Beatmap<T> ConvertBeatmap(IBeatmap original, CancellationToken cancellationToken)
{
#pragma warning disable 618
return ConvertBeatmap(original);
#pragma warning restore 618
}
/// <summary>
@ -51,19 +65,20 @@ namespace osu.Game.Beatmaps
/// </summary>
/// <param name="original">The un-converted Beatmap.</param>
/// <returns>The converted Beatmap.</returns>
[Obsolete("Use the cancellation-supporting override")] // Can be removed 20210318
protected virtual Beatmap<T> ConvertBeatmap(IBeatmap original)
{
var beatmap = CreateBeatmap();
beatmap.BeatmapInfo = original.BeatmapInfo;
beatmap.ControlPointInfo = original.ControlPointInfo;
beatmap.HitObjects = convertHitObjects(original.HitObjects, original).OrderBy(s => s.StartTime).ToList();
beatmap.HitObjects = convertHitObjects(original.HitObjects, original, cancellationToken).OrderBy(s => s.StartTime).ToList();
beatmap.Breaks = original.Breaks;
return beatmap;
}
private List<T> convertHitObjects(IReadOnlyList<HitObject> hitObjects, IBeatmap beatmap)
private List<T> convertHitObjects(IReadOnlyList<HitObject> hitObjects, IBeatmap beatmap, CancellationToken cancellationToken)
{
var result = new List<T>(hitObjects.Count);
@ -75,7 +90,7 @@ namespace osu.Game.Beatmaps
continue;
}
var converted = ConvertHitObject(obj, beatmap);
var converted = ConvertHitObject(obj, beatmap, cancellationToken);
if (ObjectConverted != null)
{
@ -104,7 +119,23 @@ namespace osu.Game.Beatmaps
/// </summary>
/// <param name="original">The hit object to convert.</param>
/// <param name="beatmap">The un-converted Beatmap.</param>
/// <param name="cancellationToken">The cancellation token.</param>
/// <returns>The converted hit object.</returns>
protected abstract IEnumerable<T> ConvertHitObject(HitObject original, IBeatmap beatmap);
protected virtual IEnumerable<T> ConvertHitObject(HitObject original, IBeatmap beatmap, CancellationToken cancellationToken)
{
#pragma warning disable 618
return ConvertHitObject(original, beatmap);
#pragma warning restore 618
}
/// <summary>
/// Performs the conversion of a hit object.
/// This method is generally executed sequentially for all objects in a beatmap.
/// </summary>
/// <param name="original">The hit object to convert.</param>
/// <param name="beatmap">The un-converted Beatmap.</param>
/// <returns>The converted hit object.</returns>
[Obsolete("Use the cancellation-supporting override")] // Can be removed 20210318
protected virtual IEnumerable<T> ConvertHitObject(HitObject original, IBeatmap beatmap) => Enumerable.Empty<T>();
}
}

View File

@ -3,6 +3,7 @@
using System;
using System.Collections.Generic;
using System.Threading;
using JetBrains.Annotations;
using osu.Framework.Audio;
using osu.Framework.Audio.Track;
@ -76,7 +77,7 @@ namespace osu.Game.Beatmaps
public bool CanConvert() => true;
public IBeatmap Convert()
public IBeatmap Convert(CancellationToken cancellationToken = default)
{
foreach (var obj in Beatmap.HitObjects)
ObjectConverted?.Invoke(obj, obj.Yield());

View File

@ -3,6 +3,7 @@
using System;
using System.Collections.Generic;
using System.Threading;
using osu.Game.Rulesets;
using osu.Game.Rulesets.Objects;
@ -30,6 +31,8 @@ namespace osu.Game.Beatmaps
/// <summary>
/// Converts <see cref="Beatmap"/>.
/// </summary>
IBeatmap Convert();
/// <param name="cancellationToken">The cancellation token.</param>
/// <returns>The converted Beatmap.</returns>
IBeatmap Convert(CancellationToken cancellationToken = default);
}
}

View File

@ -109,7 +109,7 @@ namespace osu.Game.Beatmaps
}
// Convert
IBeatmap converted = converter.Convert();
IBeatmap converted = converter.Convert(cancellationSource.Token);
// Apply conversion mods to the result
foreach (var mod in mods.OfType<IApplicableAfterBeatmapConversion>())