Skip to content

Commit

Permalink
Merge pull request #1845 from andy840119/implement-items-section
Browse files Browse the repository at this point in the history
Implement items editor for the section.
  • Loading branch information
andy840119 authored Jan 18, 2023
2 parents 766a8d8 + ee86be3 commit 6afd1e0
Show file tree
Hide file tree
Showing 9 changed files with 457 additions and 306 deletions.
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
// Copyright (c) andy840119 <[email protected]>. Licensed under the GPL Licence.
// See the LICENCE file in the repository root for full licence text.

using System;
using osu.Framework.Bindables;
using osu.Game.Rulesets.Karaoke.Objects;

namespace osu.Game.Rulesets.Karaoke.Screens.Edit.Beatmaps.Lyrics.Settings;

public abstract partial class LyricPropertiesSection<TModel> : LyricPropertySection where TModel : class
{
private readonly LyricPropertiesEditor itemsEditor;

protected LyricPropertiesSection()
{
Add(itemsEditor = CreateLyricPropertiesEditor());
}

protected sealed override void OnLyricChanged(Lyric? lyric)
{
itemsEditor.OnLyricChanged(lyric);
}

protected abstract LyricPropertiesEditor CreateLyricPropertiesEditor();

protected abstract partial class LyricPropertiesEditor : SectionItemsEditor<TModel>
{
private Lyric? currentLyric;

protected Lyric CurrentLyric => currentLyric ?? throw new InvalidOperationException();

public void OnLyricChanged(Lyric? lyric)
{
currentLyric = lyric;

Items.UnbindBindings();

if (lyric != null)
Items.BindTo(GetItems(lyric));
}

protected abstract IBindableList<TModel> GetItems(Lyric lyric);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -4,85 +4,24 @@
#nullable disable

using System;
using System.Linq;
using osu.Framework.Allocation;
using osu.Framework.Bindables;
using osu.Framework.Graphics;
using osu.Framework.Localisation;
using osu.Game.Graphics.UserInterfaceV2;
using osu.Game.Rulesets.Karaoke.Edit.ChangeHandlers.Notes;
using osu.Game.Rulesets.Karaoke.Edit.Utils;
using osu.Game.Rulesets.Karaoke.Extensions;
using osu.Game.Rulesets.Karaoke.Objects;
using osu.Game.Rulesets.Karaoke.Screens.Edit.Beatmaps.Lyrics.States.Modes;
using osu.Game.Screens.Edit;

namespace osu.Game.Rulesets.Karaoke.Screens.Edit.Beatmaps.Lyrics.Settings.Notes
{
public partial class NoteEditPropertySection : LyricPropertySection
public partial class NoteEditPropertySection : LyricPropertiesSection<Note>
{
protected override LocalisableString Title => "Properties";

private readonly Bindable<Note[]> notes = new();
private readonly Bindable<NoteEditPropertyMode> bindableNoteEditPropertyMode = new();

[Resolved]
private EditorBeatmap beatmap { get; set; }

public NoteEditPropertySection()
{
bindableNoteEditPropertyMode.BindValueChanged(e =>
{
reCreateEditComponents();
});

notes.BindValueChanged(e =>
{
reCreateEditComponents();
});

void reCreateEditComponents()
{
RemoveAll(x => x is LabelledObjectFieldTextBox<Note>, true);
RemoveAll(x => x is LabelledSwitchButton, true);

if (notes.Value == null)
return;

AddRange(notes.Value.Select(x =>
{
int index = Array.IndexOf(notes.Value, x);
return bindableNoteEditPropertyMode.Value switch
{
NoteEditPropertyMode.Text => new LabelledNoteTextTextBox(x)
{
Label = $"#{index + 1}",
TabbableContentContainer = this
} as Drawable,
NoteEditPropertyMode.RubyText => new LabelledNoteRubyTextTextBox(x)
{
Label = x.Text,
TabbableContentContainer = this
},
NoteEditPropertyMode.Display => new LabelledNoteDisplaySwitchButton(x)
{
Label = x.Text,
},
_ => throw new ArgumentOutOfRangeException(nameof(bindableNoteEditPropertyMode.Value))
};
}));
}
}

[BackgroundDependencyLoader]
private void load(IEditNoteModeState editNoteModeState)
{
bindableNoteEditPropertyMode.BindTo(editNoteModeState.NoteEditPropertyMode);
}

protected override void OnLyricChanged(Lyric lyric)
{
notes.Value = EditorBeatmapUtils.GetNotesByLyric(beatmap, lyric).ToArray();
}
protected override LyricPropertiesEditor CreateLyricPropertiesEditor() => new NotePropertiesEditor();

protected override LockLyricPropertyBy? IsWriteLyricPropertyLocked(Lyric lyric)
=> HitObjectWritableUtils.GetCreateOrRemoveNoteLockedBy(lyric); //todo: should reference by another utils.
Expand All @@ -103,6 +42,60 @@ protected override LocalisableString GetWriteLyricPropertyLockedTooltip(LockLyri
_ => throw new ArgumentOutOfRangeException(nameof(lockLyricPropertyBy), lockLyricPropertyBy, null)
};

private partial class NotePropertiesEditor : LyricPropertiesEditor
{
private readonly Bindable<NoteEditPropertyMode> bindableNoteEditPropertyMode = new();

[Resolved]
private EditorBeatmap beatmap { get; set; }

public NotePropertiesEditor()
{
bindableNoteEditPropertyMode.BindValueChanged(e =>
{
RedrewContent();
});
}

[BackgroundDependencyLoader]
private void load(IEditNoteModeState editNoteModeState)
{
bindableNoteEditPropertyMode.BindTo(editNoteModeState.NoteEditPropertyMode);
}

protected override Drawable CreateDrawable(Note item)
{
// todo: deal with create or remove the notes.
int index = Items.IndexOf(item);
return bindableNoteEditPropertyMode.Value switch
{
NoteEditPropertyMode.Text => new LabelledNoteTextTextBox(item)
{
Label = $"#{index + 1}",
TabbableContentContainer = this
},
NoteEditPropertyMode.RubyText => new LabelledNoteRubyTextTextBox(item)
{
Label = item.Text,
TabbableContentContainer = this
},
NoteEditPropertyMode.Display => new LabelledNoteDisplaySwitchButton(item)
{
Label = item.Text,
},
_ => throw new ArgumentOutOfRangeException(nameof(bindableNoteEditPropertyMode.Value))
};
}

protected override EditorSectionButton CreateCreateNewItemButton() => null;

protected override IBindableList<Note> GetItems(Lyric lyric)
{
var notes = EditorBeatmapUtils.GetNotesByLyric(beatmap, lyric);
return new BindableList<Note>(notes);
}
}

private partial class LabelledNoteTextTextBox : LabelledObjectFieldTextBox<Note>
{
[Resolved]
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -20,26 +20,7 @@ public partial class RomajiTagEditSection : TextTagEditSection<RomajiTag>
{
protected override LocalisableString Title => "Romaji";

[Resolved]
private ILyricRomajiTagsChangeHandler romajiTagsChangeHandler { get; set; }

protected override IBindableList<RomajiTag> GetBindableTextTags(Lyric lyric)
=> lyric.RomajiTagsBindable;

protected override LabelledTextTagTextBox<RomajiTag> CreateLabelledTextTagTextBox(Lyric lyric, RomajiTag textTag)
=> new LabelledRomajiTagTextBox(lyric, textTag);

protected override void AddTextTag(RomajiTag textTag)
=> romajiTagsChangeHandler.Add(textTag);

protected override LocalisableString CreateNewTextTagButtonText()
=> "Create new romaji";

protected override LocalisableString CreateNewTextTagTitle()
=> "Romaji";

protected override LocalisableString CreateNewTextTagDescription()
=> "Please enter the romaji.";
protected override LyricPropertiesEditor CreateLyricPropertiesEditor() => new RomajiTagsEditor();

protected override LockLyricPropertyBy? IsWriteLyricPropertyLocked(Lyric lyric)
=> HitObjectWritableUtils.GetLyricPropertyLockedBy(lyric, nameof(Lyric.RomajiTags));
Expand All @@ -60,6 +41,30 @@ protected override LocalisableString GetWriteLyricPropertyLockedTooltip(LockLyri
_ => throw new ArgumentOutOfRangeException(nameof(lockLyricPropertyBy), lockLyricPropertyBy, null)
};

private partial class RomajiTagsEditor : TextTagsEditor
{
[Resolved]
private ILyricRomajiTagsChangeHandler romajiTagsChangeHandler { get; set; }

protected override IBindableList<RomajiTag> GetItems(Lyric lyric)
=> lyric.RomajiTagsBindable;

protected override LabelledTextTagTextBox<RomajiTag> CreateLabelledTextTagTextBox(Lyric lyric, RomajiTag textTag)
=> new LabelledRomajiTagTextBox(lyric, textTag);

protected override void AddTextTag(RomajiTag textTag)
=> romajiTagsChangeHandler.Add(textTag);

protected override LocalisableString CreateNewTextTagButtonText()
=> "Create new romaji";

protected override LocalisableString CreateNewTextTagTitle()
=> "Romaji";

protected override LocalisableString CreateNewTextTagDescription()
=> "Please enter the romaji.";
}

protected partial class LabelledRomajiTagTextBox : LabelledTextTagTextBox<RomajiTag>
{
[Resolved]
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -20,26 +20,7 @@ public partial class RubyTagEditSection : TextTagEditSection<RubyTag>
{
protected override LocalisableString Title => "Ruby";

[Resolved]
private ILyricRubyTagsChangeHandler rubyTagsChangeHandler { get; set; }

protected override IBindableList<RubyTag> GetBindableTextTags(Lyric lyric)
=> lyric.RubyTagsBindable;

protected override LabelledTextTagTextBox<RubyTag> CreateLabelledTextTagTextBox(Lyric lyric, RubyTag textTag)
=> new LabelledRubyTagTextBox(lyric, textTag);

protected override void AddTextTag(RubyTag textTag)
=> rubyTagsChangeHandler.Add(textTag);

protected override LocalisableString CreateNewTextTagButtonText()
=> "Create new ruby";

protected override LocalisableString CreateNewTextTagTitle()
=> "Ruby";

protected override LocalisableString CreateNewTextTagDescription()
=> "Please enter the ruby.";
protected override LyricPropertiesEditor CreateLyricPropertiesEditor() => new RubyTagsEditor();

protected override LockLyricPropertyBy? IsWriteLyricPropertyLocked(Lyric lyric)
=> HitObjectWritableUtils.GetLyricPropertyLockedBy(lyric, nameof(Lyric.RubyTags));
Expand All @@ -60,6 +41,30 @@ protected override LocalisableString GetWriteLyricPropertyLockedTooltip(LockLyri
_ => throw new ArgumentOutOfRangeException(nameof(lockLyricPropertyBy), lockLyricPropertyBy, null)
};

private partial class RubyTagsEditor : TextTagsEditor
{
[Resolved]
private ILyricRubyTagsChangeHandler rubyTagsChangeHandler { get; set; }

protected override IBindableList<RubyTag> GetItems(Lyric lyric)
=> lyric.RubyTagsBindable;

protected override LabelledTextTagTextBox<RubyTag> CreateLabelledTextTagTextBox(Lyric lyric, RubyTag textTag)
=> new LabelledRubyTagTextBox(lyric, textTag);

protected override void AddTextTag(RubyTag textTag)
=> rubyTagsChangeHandler.Add(textTag);

protected override LocalisableString CreateNewTextTagButtonText()
=> "Create new ruby";

protected override LocalisableString CreateNewTextTagTitle()
=> "Ruby";

protected override LocalisableString CreateNewTextTagDescription()
=> "Please enter the ruby.";
}

protected partial class LabelledRubyTagTextBox : LabelledTextTagTextBox<RubyTag>
{
[Resolved]
Expand Down
Loading

0 comments on commit 6afd1e0

Please sign in to comment.