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

Move beatmap specific logic out of EditorChangeHandler

This commit is contained in:
Dean Herbert 2023-02-03 17:53:54 +09:00
parent 554f14151c
commit 3345e34544
4 changed files with 54 additions and 33 deletions

View File

@ -1,8 +1,6 @@
// 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.
#nullable disable
using NUnit.Framework;
using osu.Game.Rulesets.Osu;
using osu.Game.Rulesets.Osu.Beatmaps;
@ -12,7 +10,7 @@ using osu.Game.Screens.Edit;
namespace osu.Game.Tests.Editing
{
[TestFixture]
public class EditorChangeHandlerTest
public class BeatmapEditorChangeHandlerTest
{
private int stateChangedFired;
@ -169,7 +167,7 @@ namespace osu.Game.Tests.Editing
},
});
var changeHandler = new EditorChangeHandler(beatmap);
var changeHandler = new BeatmapEditorChangeHandler(beatmap);
changeHandler.OnStateChange += () => stateChangedFired++;
return (changeHandler, beatmap);

View File

@ -0,0 +1,43 @@
// 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.IO;
using System.Text;
using osu.Game.Beatmaps.Formats;
using osu.Game.Rulesets.Objects;
namespace osu.Game.Screens.Edit
{
public partial class BeatmapEditorChangeHandler : EditorChangeHandler
{
private readonly LegacyEditorBeatmapPatcher patcher;
private readonly EditorBeatmap editorBeatmap;
/// <summary>
/// Creates a new <see cref="EditorChangeHandler"/>.
/// </summary>
/// <param name="editorBeatmap">The <see cref="EditorBeatmap"/> to track the <see cref="HitObject"/>s of.</param>
public BeatmapEditorChangeHandler(EditorBeatmap editorBeatmap)
{
this.editorBeatmap = editorBeatmap;
editorBeatmap.TransactionBegan += BeginChange;
editorBeatmap.TransactionEnded += EndChange;
editorBeatmap.SaveStateTriggered += SaveState;
patcher = new LegacyEditorBeatmapPatcher(editorBeatmap);
// Initial state.
SaveState();
}
protected override void WriteCurrentStateToStream(MemoryStream stream)
{
using (var sw = new StreamWriter(stream, Encoding.UTF8, 1024, true))
new LegacyBeatmapEncoder(editorBeatmap, editorBeatmap.BeatmapSkin).Encode(sw);
}
protected override void ApplyStateChange(byte[] previousState, byte[] newState) =>
patcher.Patch(previousState, newState);
}
}

View File

@ -240,7 +240,7 @@ namespace osu.Game.Screens.Edit
if (canSave)
{
changeHandler = new EditorChangeHandler(editorBeatmap);
changeHandler = new BeatmapEditorChangeHandler(editorBeatmap);
dependencies.CacheAs<IEditorChangeHandler>(changeHandler);
}

View File

@ -5,25 +5,21 @@ using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Text;
using osu.Framework.Bindables;
using osu.Framework.Extensions;
using osu.Game.Beatmaps.Formats;
using osu.Game.Rulesets.Objects;
namespace osu.Game.Screens.Edit
{
/// <summary>
/// Tracks changes to the <see cref="Editor"/>.
/// </summary>
public partial class EditorChangeHandler : TransactionalCommitComponent, IEditorChangeHandler
public abstract partial class EditorChangeHandler : TransactionalCommitComponent, IEditorChangeHandler
{
public readonly Bindable<bool> CanUndo = new Bindable<bool>();
public readonly Bindable<bool> CanRedo = new Bindable<bool>();
public event Action? OnStateChange;
private readonly LegacyEditorBeatmapPatcher patcher;
private readonly List<byte[]> savedStates = new List<byte[]>();
private int currentState = -1;
@ -40,29 +36,10 @@ namespace osu.Game.Screens.Edit
}
}
private readonly EditorBeatmap editorBeatmap;
private bool isRestoring;
public const int MAX_SAVED_STATES = 50;
/// <summary>
/// Creates a new <see cref="EditorChangeHandler"/>.
/// </summary>
/// <param name="editorBeatmap">The <see cref="EditorBeatmap"/> to track the <see cref="HitObject"/>s of.</param>
public EditorChangeHandler(EditorBeatmap editorBeatmap)
{
this.editorBeatmap = editorBeatmap;
editorBeatmap.TransactionBegan += BeginChange;
editorBeatmap.TransactionEnded += EndChange;
editorBeatmap.SaveStateTriggered += SaveState;
patcher = new LegacyEditorBeatmapPatcher(editorBeatmap);
// Initial state.
SaveState();
}
protected override void UpdateState()
{
if (isRestoring)
@ -70,9 +47,7 @@ namespace osu.Game.Screens.Edit
using (var stream = new MemoryStream())
{
using (var sw = new StreamWriter(stream, Encoding.UTF8, 1024, true))
new LegacyBeatmapEncoder(editorBeatmap, editorBeatmap.BeatmapSkin).Encode(sw);
WriteCurrentStateToStream(stream);
byte[] newState = stream.ToArray();
// if the previous state is binary equal we don't need to push a new one, unless this is the initial state.
@ -111,7 +86,8 @@ namespace osu.Game.Screens.Edit
isRestoring = true;
patcher.Patch(savedStates[currentState], savedStates[newState]);
ApplyStateChange(savedStates[currentState], savedStates[newState]);
currentState = newState;
isRestoring = false;
@ -120,6 +96,10 @@ namespace osu.Game.Screens.Edit
updateBindables();
}
protected abstract void WriteCurrentStateToStream(MemoryStream stream);
protected abstract void ApplyStateChange(byte[] previousState, byte[] newState);
private void updateBindables()
{
CanUndo.Value = savedStates.Count > 0 && currentState > 0;