mirror of
https://github.com/ppy/osu.git
synced 2026-05-22 19:41:06 +08:00
Merge pull request #32315 from bdach/copy-db-data-more-granularly
Apply more granular copying from database when retrieving working beatmap
This commit is contained in:
@@ -22,6 +22,8 @@ namespace osu.Game.Rulesets.Catch.Tests.Editor
|
||||
{
|
||||
public abstract partial class CatchPlacementBlueprintTestScene : PlacementBlueprintTestScene
|
||||
{
|
||||
protected sealed override Ruleset CreateRuleset() => new CatchRuleset();
|
||||
|
||||
protected const double TIME_SNAP = 100;
|
||||
|
||||
protected DrawableCatchHitObject LastObject;
|
||||
|
||||
@@ -22,6 +22,8 @@ namespace osu.Game.Rulesets.Mania.Tests.Editor
|
||||
{
|
||||
public abstract partial class ManiaPlacementBlueprintTestScene : PlacementBlueprintTestScene
|
||||
{
|
||||
protected sealed override Ruleset CreateRuleset() => new ManiaRuleset();
|
||||
|
||||
private readonly Column column;
|
||||
|
||||
[Cached(typeof(IReadOnlyList<Mod>))]
|
||||
|
||||
@@ -13,6 +13,7 @@ namespace osu.Game.Rulesets.Osu.Tests.Editor
|
||||
{
|
||||
public partial class TestSceneHitCirclePlacementBlueprint : PlacementBlueprintTestScene
|
||||
{
|
||||
protected sealed override Ruleset CreateRuleset() => new OsuRuleset();
|
||||
protected override DrawableHitObject CreateHitObject(HitObject hitObject) => new DrawableHitCircle((HitCircle)hitObject);
|
||||
protected override HitObjectPlacementBlueprint CreateBlueprint() => new HitCirclePlacementBlueprint();
|
||||
}
|
||||
|
||||
@@ -23,6 +23,8 @@ namespace osu.Game.Rulesets.Osu.Tests.Editor
|
||||
{
|
||||
public partial class TestSceneSliderPlacementBlueprint : PlacementBlueprintTestScene
|
||||
{
|
||||
protected sealed override Ruleset CreateRuleset() => new OsuRuleset();
|
||||
|
||||
[SetUp]
|
||||
public void Setup() => Schedule(() =>
|
||||
{
|
||||
|
||||
@@ -13,6 +13,8 @@ namespace osu.Game.Rulesets.Osu.Tests.Editor
|
||||
{
|
||||
public partial class TestSceneSpinnerPlacementBlueprint : PlacementBlueprintTestScene
|
||||
{
|
||||
protected sealed override Ruleset CreateRuleset() => new OsuRuleset();
|
||||
|
||||
protected override DrawableHitObject CreateHitObject(HitObject hitObject) => new DrawableSpinner((Spinner)hitObject);
|
||||
|
||||
protected override HitObjectPlacementBlueprint CreateBlueprint() => new SpinnerPlacementBlueprint();
|
||||
|
||||
@@ -1,15 +1,28 @@
|
||||
// Copyright (c) ppy Pty Ltd <contact@ppy.sh>. Licensed under the MIT Licence.
|
||||
// See the LICENCE file in the repository root for full licence text.
|
||||
|
||||
using System.Linq;
|
||||
using osu.Framework.Localisation;
|
||||
using osu.Game.Online.API;
|
||||
using osu.Game.Rulesets;
|
||||
using osu.Game.Rulesets.Objects.Types;
|
||||
using osu.Game.Screens.Select;
|
||||
|
||||
namespace osu.Game.Beatmaps
|
||||
{
|
||||
public static class BeatmapInfoExtensions
|
||||
{
|
||||
/// <summary>
|
||||
/// Given an <see cref="IBeatmap"/>, update length, BPM and object counts.
|
||||
/// </summary>
|
||||
public static void UpdateStatisticsFromBeatmap(this BeatmapInfo beatmapInfo, IBeatmap beatmap)
|
||||
{
|
||||
beatmapInfo.Length = beatmap.CalculatePlayableLength();
|
||||
beatmapInfo.BPM = 60000 / beatmap.GetMostCommonBeatLength();
|
||||
beatmapInfo.EndTimeObjectCount = beatmap.HitObjects.Count(h => h is IHasDuration);
|
||||
beatmapInfo.TotalObjectCount = beatmap.HitObjects.Count;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// A user-presentable display title representing this beatmap.
|
||||
/// </summary>
|
||||
|
||||
@@ -51,7 +51,7 @@ namespace osu.Game.Beatmaps
|
||||
if (lookupScope != MetadataLookupScope.None)
|
||||
metadataLookup.Update(beatmapSet, lookupScope == MetadataLookupScope.OnlineFirst);
|
||||
|
||||
foreach (var beatmap in beatmapSet.Beatmaps)
|
||||
foreach (BeatmapInfo beatmap in beatmapSet.Beatmaps)
|
||||
{
|
||||
difficultyCache.Invalidate(beatmap);
|
||||
|
||||
@@ -63,10 +63,7 @@ namespace osu.Game.Beatmaps
|
||||
var calculator = ruleset.CreateDifficultyCalculator(working);
|
||||
|
||||
beatmap.StarRating = calculator.Calculate().StarRating;
|
||||
beatmap.Length = working.Beatmap.CalculatePlayableLength();
|
||||
beatmap.BPM = 60000 / working.Beatmap.GetMostCommonBeatLength();
|
||||
beatmap.EndTimeObjectCount = working.Beatmap.HitObjects.Count(h => h is IHasDuration);
|
||||
beatmap.TotalObjectCount = working.Beatmap.HitObjects.Count;
|
||||
beatmap.UpdateStatisticsFromBeatmap(working.Beatmap);
|
||||
}
|
||||
|
||||
// And invalidate again afterwards as re-fetching the most up-to-date database metadata will be required.
|
||||
|
||||
@@ -235,11 +235,18 @@ namespace osu.Game.Beatmaps
|
||||
// Todo: Handle cancellation during beatmap parsing
|
||||
var b = GetBeatmap() ?? new Beatmap();
|
||||
|
||||
// The original beatmap version needs to be preserved as the database doesn't contain it
|
||||
BeatmapInfo.BeatmapVersion = b.BeatmapInfo.BeatmapVersion;
|
||||
|
||||
// Use the database-backed info for more up-to-date values (beatmap id, ranked status, etc)
|
||||
b.BeatmapInfo = BeatmapInfo;
|
||||
// Copy across values of key properties for which the database-backed model has data that the decoded beatmap isn't going to.
|
||||
b.BeatmapInfo.ID = BeatmapInfo.ID;
|
||||
b.BeatmapInfo.UserSettings = BeatmapInfo.UserSettings;
|
||||
b.BeatmapInfo.BeatmapSet = BeatmapInfo.BeatmapSet;
|
||||
b.BeatmapInfo.Status = BeatmapInfo.Status;
|
||||
b.BeatmapInfo.OnlineID = BeatmapInfo.OnlineID;
|
||||
b.BeatmapInfo.OnlineMD5Hash = BeatmapInfo.OnlineMD5Hash;
|
||||
b.BeatmapInfo.LastLocalUpdate = BeatmapInfo.LastLocalUpdate;
|
||||
b.BeatmapInfo.LastOnlineUpdate = BeatmapInfo.LastOnlineUpdate;
|
||||
b.BeatmapInfo.LastPlayed = BeatmapInfo.LastPlayed;
|
||||
b.BeatmapInfo.EditorTimestamp = BeatmapInfo.EditorTimestamp;
|
||||
b.BeatmapInfo.StarRating = BeatmapInfo.StarRating; // this could be recomputed in the decoding process but it's a bit annoying to do.
|
||||
|
||||
return b;
|
||||
}, loadCancellationSource.Token, TaskCreationOptions.LongRunning, TaskScheduler.Default);
|
||||
|
||||
@@ -152,14 +152,25 @@ namespace osu.Game.Beatmaps
|
||||
return null;
|
||||
}
|
||||
|
||||
if (stream.ComputeMD5Hash() != BeatmapInfo.MD5Hash)
|
||||
string streamMD5 = stream.ComputeMD5Hash();
|
||||
string streamSHA2 = stream.ComputeSHA2Hash();
|
||||
|
||||
if (streamMD5 != BeatmapInfo.MD5Hash)
|
||||
{
|
||||
Logger.Log($"Beatmap failed to load (file {BeatmapInfo.Path} does not have the expected hash).", level: LogLevel.Error);
|
||||
return null;
|
||||
}
|
||||
|
||||
using (var reader = new LineBufferedReader(stream))
|
||||
return Decoder.GetDecoder<Beatmap>(reader).Decode(reader);
|
||||
{
|
||||
var beatmap = Decoder.GetDecoder<Beatmap>(reader).Decode(reader);
|
||||
|
||||
beatmap.BeatmapInfo.MD5Hash = streamMD5;
|
||||
beatmap.BeatmapInfo.Hash = streamSHA2;
|
||||
beatmap.BeatmapInfo.UpdateStatisticsFromBeatmap(beatmap);
|
||||
|
||||
return beatmap;
|
||||
}
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
|
||||
@@ -51,7 +51,9 @@ namespace osu.Game.Tests.Visual
|
||||
|
||||
protected virtual IBeatmap GetPlayableBeatmap()
|
||||
{
|
||||
var playable = Beatmap.Value.GetPlayableBeatmap(Beatmap.Value.BeatmapInfo.Ruleset);
|
||||
var rulesetInfo = CreateRuleset()!.RulesetInfo;
|
||||
var playable = Beatmap.Value.GetPlayableBeatmap(rulesetInfo);
|
||||
playable.BeatmapInfo.Ruleset = rulesetInfo;
|
||||
playable.Difficulty.CircleSize = 2;
|
||||
return playable;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user