Skip to content

Commit

Permalink
Implement lyric assign to singer logic in singer manager.
Browse files Browse the repository at this point in the history
  • Loading branch information
andy840119 committed Nov 8, 2020
1 parent bcba0aa commit 56a2d47
Show file tree
Hide file tree
Showing 5 changed files with 71 additions and 13 deletions.
2 changes: 1 addition & 1 deletion osu.Game.Rulesets.Karaoke.Tests/Edit/TestSceneSinger.cs
Original file line number Diff line number Diff line change
Expand Up @@ -88,7 +88,7 @@ public void SetUp() => Schedule(() =>
public void HoverToSingerArea()
{
// todo : add this step because description is not showing.
AddStep("Move mouse to singer area", () => InputManager.MoveMouseTo(Child, new Vector2(-400,-100)));
AddStep("Move mouse to singer area", () => InputManager.MoveMouseTo(Child, new Vector2(-450,-90)));
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -24,8 +24,6 @@ protected override void AddBlueprintFor(HitObject hitObject)
if (!(hitObject is Lyric))
return;

// todo : check lyric is at the same singer.

base.AddBlueprintFor(hitObject);
}

Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
// Copyright (c) andy840119 <[email protected]>. Licensed under the GPL Licence.
// See the LICENCE file in the repository root for full licence text.

using osu.Framework.Allocation;
using osu.Framework.Extensions.IEnumerableExtensions;
using osu.Framework.Graphics;
using osu.Framework.Graphics.Containers;
Expand All @@ -24,6 +25,8 @@ public class LyricTimelineHitObjectBlueprint : TimelineHitObjectBlueprint, IHasC
public LyricTimelineHitObjectBlueprint(HitObject hitObject, Singer singer)
: base(hitObject)
{
this.singer = singer;

// Use tricty way to hide the timeline's component.
InternalChildren.ForEach(x => x.Alpha = 0);

Expand Down Expand Up @@ -52,13 +55,17 @@ public LyricTimelineHitObjectBlueprint(HitObject hitObject, Singer singer)
}
}
});
}

if (hitObject is Lyric lyric)
[BackgroundDependencyLoader]
private void load(SingerManager singerManager)
{
if (HitObject is Lyric lyric)
{
lyric.SingersBindable.BindValueChanged(e =>
{
// Check is lyric contains this singer, or default singer
var isSingerMatch = e.NewValue?.Contains(singer.ID) ?? singer.ID == 0;
var isSingerMatch = singerManager.SingerInLyric(singer, lyric);
if (isSingerMatch)
{
Show();
Expand Down
Original file line number Diff line number Diff line change
@@ -1,27 +1,27 @@
// Copyright (c) andy840119 <[email protected]>. Licensed under the GPL Licence.
// See the LICENCE file in the repository root for full licence text.

using Lucene.Net.Support;
using osu.Framework.Allocation;
using osu.Framework.Graphics.UserInterface;
using osu.Game.Graphics.UserInterface;
using osu.Game.Rulesets.Edit;
using osu.Game.Rulesets.Karaoke.Objects;
using osu.Game.Screens.Edit.Compose.Components;
using System.Collections.Generic;
using System.Linq;
using static osu.Game.Rulesets.Karaoke.Edit.Components.Timeline.TimelineBlueprintContainer;

namespace osu.Game.Rulesets.Karaoke.Edit.Singers.Components.Timeline
{
internal class LyricTimelineSelectionHandler : TimelineSelectionHandler
{
[Resolved]
private SingerManager singerManager { get; set; }

public override bool HandleMovement(MoveSelectionEvent moveEvent) => false;

protected override IEnumerable<MenuItem> GetContextMenuItemsForSelection(IEnumerable<SelectionBlueprint> selection)
{
// todo : make implementation of singers selection.
var menu = new List<MenuItem>
{
new OsuMenuItem("Test1", MenuItemType.Standard, () => { })
};
return menu.ToArray();
}
=> singerManager.CreateSingerContextMenu(selection.Select(x => x.HitObject).OfType<Lyric>().ToList());
}
}
53 changes: 53 additions & 0 deletions osu.Game.Rulesets.Karaoke/Edit/Singers/SingerManager.cs
Original file line number Diff line number Diff line change
@@ -1,12 +1,18 @@
// Copyright (c) andy840119 <[email protected]>. Licensed under the GPL Licence.
// See the LICENCE file in the repository root for full licence text.

using Microsoft.EntityFrameworkCore.Internal;
using osu.Framework.Allocation;
using osu.Framework.Bindables;
using osu.Framework.Graphics;
using osu.Framework.Graphics.UserInterface;
using osu.Game.Graphics.UserInterface;
using osu.Game.Rulesets.Karaoke.Beatmaps;
using osu.Game.Rulesets.Karaoke.Beatmaps.Metadatas;
using osu.Game.Rulesets.Karaoke.Objects;
using osu.Game.Screens.Edit;
using System.Collections.Generic;
using System.Linq;

namespace osu.Game.Rulesets.Karaoke.Edit.Singers
{
Expand All @@ -27,5 +33,52 @@ private void load()
Singers.AddRange(karaokeBeatmap.SingerMetadata.Singers);
}
}

public IEnumerable<MenuItem> CreateSingerContextMenu(List<Lyric> lyrics)
{
return Singers.Select(singer => new OsuMenuItem(singer.Name, anySingerInLyric(singer) ? MenuItemType.Highlighted : MenuItemType.Standard, () =>
{
// if only one lyric
if (allSingerInLyric(singer))
{
lyrics.ForEach(lyric => RemoveSingerToLyric(singer, lyric));
}
else
{
lyrics.ForEach(lyric => AddSingerToLyric(singer, lyric));
}
}));

bool anySingerInLyric(Singer singer) => lyrics.Any(lyric => SingerInLyric(singer, lyric));

bool allSingerInLyric(Singer singer) => lyrics.All(lyric => SingerInLyric(singer, lyric));
}

public void AddSingerToLyric(Singer singer, Lyric lyric)
{
if (SingerInLyric(singer, lyric))
return;

var existSingerList = lyric.Singers?.ToList() ?? new List<int>();
existSingerList.Add(singer.ID);
lyric.Singers = existSingerList.ToArray();
}

public void RemoveSingerToLyric(Singer singer, Lyric lyric)
{
if (!SingerInLyric(singer, lyric))
return;

lyric.Singers = lyric.Singers?.Where(x => x != singer.ID).ToArray();
}

public bool SingerInLyric(Singer singer, Lyric lyric)
{
// lyric belongs to default singer if no any singer in lyric.
if (lyric.Singers == null || !lyric.Singers.Any())
return singer.ID == 0;

return lyric.Singers?.Contains(singer.ID) ?? false;
}
}
}

0 comments on commit 56a2d47

Please sign in to comment.