From 1980d31c6c48cc3f5658eb1f514aa9f37983fef5 Mon Sep 17 00:00:00 2001 From: andy840119 Date: Sat, 17 Aug 2024 00:49:29 +0800 Subject: [PATCH 1/2] Should be gap index. --- .../Lyrics/IPreviewLyricPositionProvider.cs | 2 +- .../Content/Components/Lyrics/LyricLayer.cs | 4 ++-- .../Lyrics/PreviewKaraokeSpriteText.cs | 18 +++++++++--------- 3 files changed, 12 insertions(+), 12 deletions(-) diff --git a/osu.Game.Rulesets.Karaoke/Screens/Edit/Beatmaps/Lyrics/Content/Components/Lyrics/IPreviewLyricPositionProvider.cs b/osu.Game.Rulesets.Karaoke/Screens/Edit/Beatmaps/Lyrics/Content/Components/Lyrics/IPreviewLyricPositionProvider.cs index dd194f4ac..9e91a26c4 100644 --- a/osu.Game.Rulesets.Karaoke/Screens/Edit/Beatmaps/Lyrics/Content/Components/Lyrics/IPreviewLyricPositionProvider.cs +++ b/osu.Game.Rulesets.Karaoke/Screens/Edit/Beatmaps/Lyrics/Content/Components/Lyrics/IPreviewLyricPositionProvider.cs @@ -15,7 +15,7 @@ public interface IPreviewLyricPositionProvider int GetCharIndicatorByPosition(float position); - RectangleF GetRectByCharIndicator(int charIndex); + RectangleF GetRectByCharIndicator(int gapIndex); RectangleF? GetRubyTagByPosition(RubyTag rubyTag); diff --git a/osu.Game.Rulesets.Karaoke/Screens/Edit/Beatmaps/Lyrics/Content/Components/Lyrics/LyricLayer.cs b/osu.Game.Rulesets.Karaoke/Screens/Edit/Beatmaps/Lyrics/Content/Components/Lyrics/LyricLayer.cs index 3e1a07fb5..3a35c4ae4 100644 --- a/osu.Game.Rulesets.Karaoke/Screens/Edit/Beatmaps/Lyrics/Content/Components/Lyrics/LyricLayer.cs +++ b/osu.Game.Rulesets.Karaoke/Screens/Edit/Beatmaps/Lyrics/Content/Components/Lyrics/LyricLayer.cs @@ -69,8 +69,8 @@ public RectangleF GetRectByCharIndex(int charIndex) public int GetCharIndicatorByPosition(float position) => previewKaraokeSpriteText.GetCharIndicatorByPosition(position - LyricPosition.X); - public RectangleF GetRectByCharIndicator(int charIndex) - => previewKaraokeSpriteText.GetRectByCharIndicator(charIndex).Offset(LyricPosition); + public RectangleF GetRectByCharIndicator(int gapIndex) + => previewKaraokeSpriteText.GetRectByCharIndicator(gapIndex).Offset(LyricPosition); #endregion diff --git a/osu.Game.Rulesets.Karaoke/Screens/Edit/Beatmaps/Lyrics/Content/Components/Lyrics/PreviewKaraokeSpriteText.cs b/osu.Game.Rulesets.Karaoke/Screens/Edit/Beatmaps/Lyrics/Content/Components/Lyrics/PreviewKaraokeSpriteText.cs index 141bf10aa..867eb3ce9 100644 --- a/osu.Game.Rulesets.Karaoke/Screens/Edit/Beatmaps/Lyrics/Content/Components/Lyrics/PreviewKaraokeSpriteText.cs +++ b/osu.Game.Rulesets.Karaoke/Screens/Edit/Beatmaps/Lyrics/Content/Components/Lyrics/PreviewKaraokeSpriteText.cs @@ -113,27 +113,27 @@ float getTriggerPositionByTimeIndex(int charIndex) } } - public RectangleF GetRectByCharIndicator(int charIndex) + public RectangleF GetRectByCharIndicator(int gapIndex) { - if (charIndex < 0 || charIndex > Text.Length) - throw new ArgumentOutOfRangeException(nameof(charIndex)); + if (gapIndex < 0 || gapIndex > Text.Length) + throw new ArgumentOutOfRangeException(nameof(gapIndex)); const float min_spacing_width = 1; - if (charIndex == 0) + if (gapIndex == 0) { - var referenceRectangle = spriteText.GetCharacterDrawRectangle(charIndex); + var referenceRectangle = spriteText.GetCharacterDrawRectangle(gapIndex); return new RectangleF(referenceRectangle.X - min_spacing_width, referenceRectangle.Y, min_spacing_width, referenceRectangle.Height); } - if (charIndex == Text.Length) + if (gapIndex == Text.Length) { - var referenceRectangle = spriteText.GetCharacterDrawRectangle(charIndex - 1); + var referenceRectangle = spriteText.GetCharacterDrawRectangle(gapIndex - 1); return new RectangleF(referenceRectangle.Right, referenceRectangle.Top, min_spacing_width, referenceRectangle.Height); } - var leftRectangle = spriteText.GetCharacterDrawRectangle(charIndex - 1); - var rightRectangle = spriteText.GetCharacterDrawRectangle(charIndex); + var leftRectangle = spriteText.GetCharacterDrawRectangle(gapIndex - 1); + var rightRectangle = spriteText.GetCharacterDrawRectangle(gapIndex); return new RectangleF(leftRectangle.Right, leftRectangle.Top, rightRectangle.X - leftRectangle.Right, leftRectangle.Y); } From 9b39895473e290789a7d3b84058032a4ebbdd2eb Mon Sep 17 00:00:00 2001 From: andy840119 Date: Fri, 16 Aug 2024 23:35:35 +0800 Subject: [PATCH 2/2] Make the interface support vector2. --- .../TestScenePreviewKaraokeSpriteText.cs | 50 ++++++++++------ .../Blueprints/RubyBlueprintContainer.cs | 4 +- .../Components/Lyrics/EditLyricLayer.cs | 10 ++-- .../Lyrics/IPreviewLyricPositionProvider.cs | 6 +- .../Content/Components/Lyrics/LyricLayer.cs | 12 ++-- .../Lyrics/PreviewKaraokeSpriteText.cs | 57 ++++++++++++------- 6 files changed, 84 insertions(+), 55 deletions(-) diff --git a/osu.Game.Rulesets.Karaoke.Tests/Screens/Edit/Beatmap/Lyrics/Content/TestScenePreviewKaraokeSpriteText.cs b/osu.Game.Rulesets.Karaoke.Tests/Screens/Edit/Beatmap/Lyrics/Content/TestScenePreviewKaraokeSpriteText.cs index 6c97fa4b7..866650e43 100644 --- a/osu.Game.Rulesets.Karaoke.Tests/Screens/Edit/Beatmap/Lyrics/Content/TestScenePreviewKaraokeSpriteText.cs +++ b/osu.Game.Rulesets.Karaoke.Tests/Screens/Edit/Beatmap/Lyrics/Content/TestScenePreviewKaraokeSpriteText.cs @@ -57,20 +57,29 @@ private void load(OsuColour colour) RelativeSizeAxes = Axes.Both, Colour = colour.BlueDarker, }, - karaokeSpriteText = new PreviewKaraokeSpriteText(lyric) + new Container { - Position = new Vector2(24, 8), - }, - mask = new Container - { - Masking = true, - BorderThickness = 1, - BorderColour = colour.RedDarker, - Child = new Box + Padding = new MarginPadding + { + Vertical = 8, + Horizontal = 24, + }, + RelativeSizeAxes = Axes.Both, + Children = new Drawable[] { - RelativeSizeAxes = Axes.Both, - Colour = colour.RedDarker, - Alpha = 0.3f, + karaokeSpriteText = new PreviewKaraokeSpriteText(lyric), + mask = new Container + { + Masking = true, + BorderThickness = 1, + BorderColour = colour.RedDarker, + Child = new Box + { + RelativeSizeAxes = Axes.Both, + Colour = colour.RedDarker, + Alpha = 0.3f, + }, + }, }, }, spriteText = new OsuSpriteText @@ -105,7 +114,7 @@ public void TestGetCharIndexByPosition() triggerUpdate(() => { var mousePosition = getMousePosition(); - int? charIndex = karaokeSpriteText.GetCharIndexByPosition(mousePosition.X); + int? charIndex = karaokeSpriteText.GetCharIndexByPosition(mousePosition); updateText(charIndex.ToString()); if (charIndex == null) @@ -147,11 +156,18 @@ public void TestGetCharIndicatorByPosition() triggerUpdate(() => { var mousePosition = getMousePosition(); - int charIndex = karaokeSpriteText.GetCharIndicatorByPosition(mousePosition.X); + int? charIndex = karaokeSpriteText.GetCharIndicatorByPosition(mousePosition); updateText(charIndex.ToString()); - var position = karaokeSpriteText.GetRectByCharIndicator(charIndex); - showPosition(position); + if (charIndex == null) + { + hidePosition(); + } + else + { + var position = karaokeSpriteText.GetRectByCharIndicator(charIndex.Value); + showPosition(position); + } }); }); } @@ -199,7 +215,7 @@ public void TestGetTimeTagByPosition() triggerUpdate(() => { var mousePosition = getMousePosition(); - var timeTag = karaokeSpriteText.GetTimeTagByPosition(mousePosition.X); + var timeTag = karaokeSpriteText.GetTimeTagByPosition(mousePosition); updateText(timeTag != null ? TimeTagUtils.FormattedString(timeTag) : null); if (timeTag == null) diff --git a/osu.Game.Rulesets.Karaoke/Screens/Edit/Beatmaps/Lyrics/Content/Components/Lyrics/Blueprints/RubyBlueprintContainer.cs b/osu.Game.Rulesets.Karaoke/Screens/Edit/Beatmaps/Lyrics/Content/Components/Lyrics/Blueprints/RubyBlueprintContainer.cs index 909589bb9..58a38fa0c 100644 --- a/osu.Game.Rulesets.Karaoke/Screens/Edit/Beatmaps/Lyrics/Content/Components/Lyrics/Blueprints/RubyBlueprintContainer.cs +++ b/osu.Game.Rulesets.Karaoke/Screens/Edit/Beatmaps/Lyrics/Content/Components/Lyrics/Blueprints/RubyBlueprintContainer.cs @@ -143,11 +143,11 @@ void setRubyTagIndex(RubyTag rubyTag, int? startPosition, int? endPosition) switch (anchor) { case Anchor.CentreLeft: - float leftPosition = rect.Value.Left + offset; + var leftPosition = rect.Value.BottomLeft + new Vector2(offset, 0); return previewLyricPositionProvider.GetCharIndexByPosition(leftPosition); case Anchor.CentreRight: - float rightPosition = rect.Value.Right + offset; + var rightPosition = rect.Value.BottomRight + new Vector2(offset, 0); return previewLyricPositionProvider.GetCharIndexByPosition(rightPosition); default: diff --git a/osu.Game.Rulesets.Karaoke/Screens/Edit/Beatmaps/Lyrics/Content/Components/Lyrics/EditLyricLayer.cs b/osu.Game.Rulesets.Karaoke/Screens/Edit/Beatmaps/Lyrics/Content/Components/Lyrics/EditLyricLayer.cs index 6fea55240..1d3c6b630 100644 --- a/osu.Game.Rulesets.Karaoke/Screens/Edit/Beatmaps/Lyrics/Content/Components/Lyrics/EditLyricLayer.cs +++ b/osu.Game.Rulesets.Karaoke/Screens/Edit/Beatmaps/Lyrics/Content/Components/Lyrics/EditLyricLayer.cs @@ -118,14 +118,14 @@ protected override void OnDragEnd(DragEndEvent e) private object? getCaretIndexByPosition(UIEvent mouseEvent) { var algorithm = lyricCaretState.CaretPositionAlgorithm; - float xPosition = ToLocalSpace(mouseEvent.ScreenSpaceMousePosition).X; + var position = ToLocalSpace(mouseEvent.ScreenSpaceMousePosition); return algorithm switch { - CuttingCaretPositionAlgorithm => previewLyricPositionProvider.GetCharIndicatorByPosition(xPosition), - TypingCaretPositionAlgorithm => previewLyricPositionProvider.GetCharIndicatorByPosition(xPosition), + CuttingCaretPositionAlgorithm => previewLyricPositionProvider.GetCharIndicatorByPosition(position), + TypingCaretPositionAlgorithm => previewLyricPositionProvider.GetCharIndicatorByPosition(position), NavigateCaretPositionAlgorithm => null, - CreateRubyTagCaretPositionAlgorithm => previewLyricPositionProvider.GetCharIndexByPosition(xPosition), - CreateRemoveTimeTagCaretPositionAlgorithm => previewLyricPositionProvider.GetCharIndexByPosition(xPosition), + CreateRubyTagCaretPositionAlgorithm => previewLyricPositionProvider.GetCharIndexByPosition(position), + CreateRemoveTimeTagCaretPositionAlgorithm => previewLyricPositionProvider.GetCharIndexByPosition(position), _ => null, }; } diff --git a/osu.Game.Rulesets.Karaoke/Screens/Edit/Beatmaps/Lyrics/Content/Components/Lyrics/IPreviewLyricPositionProvider.cs b/osu.Game.Rulesets.Karaoke/Screens/Edit/Beatmaps/Lyrics/Content/Components/Lyrics/IPreviewLyricPositionProvider.cs index 9e91a26c4..ac3e4ed08 100644 --- a/osu.Game.Rulesets.Karaoke/Screens/Edit/Beatmaps/Lyrics/Content/Components/Lyrics/IPreviewLyricPositionProvider.cs +++ b/osu.Game.Rulesets.Karaoke/Screens/Edit/Beatmaps/Lyrics/Content/Components/Lyrics/IPreviewLyricPositionProvider.cs @@ -9,17 +9,17 @@ namespace osu.Game.Rulesets.Karaoke.Screens.Edit.Beatmaps.Lyrics.Content.Compone public interface IPreviewLyricPositionProvider { - int? GetCharIndexByPosition(float position); + int? GetCharIndexByPosition(Vector2 position); RectangleF GetRectByCharIndex(int charIndex); - int GetCharIndicatorByPosition(float position); + int? GetCharIndicatorByPosition(Vector2 position); RectangleF GetRectByCharIndicator(int gapIndex); RectangleF? GetRubyTagByPosition(RubyTag rubyTag); - TimeTag? GetTimeTagByPosition(float position); + TimeTag? GetTimeTagByPosition(Vector2 position); Vector2 GetPositionByTimeTag(TimeTag timeTag); } diff --git a/osu.Game.Rulesets.Karaoke/Screens/Edit/Beatmaps/Lyrics/Content/Components/Lyrics/LyricLayer.cs b/osu.Game.Rulesets.Karaoke/Screens/Edit/Beatmaps/Lyrics/Content/Components/Lyrics/LyricLayer.cs index 3a35c4ae4..34f62d51f 100644 --- a/osu.Game.Rulesets.Karaoke/Screens/Edit/Beatmaps/Lyrics/Content/Components/Lyrics/LyricLayer.cs +++ b/osu.Game.Rulesets.Karaoke/Screens/Edit/Beatmaps/Lyrics/Content/Components/Lyrics/LyricLayer.cs @@ -56,8 +56,8 @@ public override void TriggerDisallowEditEffect(LyricEditorMode editorMode) #region Text char index - public int? GetCharIndexByPosition(float position) - => previewKaraokeSpriteText.GetCharIndexByPosition(position - LyricPosition.X); + public int? GetCharIndexByPosition(Vector2 position) + => previewKaraokeSpriteText.GetCharIndexByPosition(position - LyricPosition); public RectangleF GetRectByCharIndex(int charIndex) => previewKaraokeSpriteText.GetRectByCharIndex(charIndex).Offset(LyricPosition); @@ -66,8 +66,8 @@ public RectangleF GetRectByCharIndex(int charIndex) #region Text indicator - public int GetCharIndicatorByPosition(float position) - => previewKaraokeSpriteText.GetCharIndicatorByPosition(position - LyricPosition.X); + public int? GetCharIndicatorByPosition(Vector2 position) + => previewKaraokeSpriteText.GetCharIndicatorByPosition(position - LyricPosition); public RectangleF GetRectByCharIndicator(int gapIndex) => previewKaraokeSpriteText.GetRectByCharIndicator(gapIndex).Offset(LyricPosition); @@ -83,8 +83,8 @@ public RectangleF GetRectByCharIndicator(int gapIndex) #region Time tag - public TimeTag? GetTimeTagByPosition(float position) - => previewKaraokeSpriteText.GetTimeTagByPosition(position - LyricPosition.X); + public TimeTag? GetTimeTagByPosition(Vector2 position) + => previewKaraokeSpriteText.GetTimeTagByPosition(position - LyricPosition); public Vector2 GetPositionByTimeTag(TimeTag timeTag) => previewKaraokeSpriteText.GetPositionByTimeTag(timeTag) + LyricPosition; diff --git a/osu.Game.Rulesets.Karaoke/Screens/Edit/Beatmaps/Lyrics/Content/Components/Lyrics/PreviewKaraokeSpriteText.cs b/osu.Game.Rulesets.Karaoke/Screens/Edit/Beatmaps/Lyrics/Content/Components/Lyrics/PreviewKaraokeSpriteText.cs index 867eb3ce9..4524523fd 100644 --- a/osu.Game.Rulesets.Karaoke/Screens/Edit/Beatmaps/Lyrics/Content/Components/Lyrics/PreviewKaraokeSpriteText.cs +++ b/osu.Game.Rulesets.Karaoke/Screens/Edit/Beatmaps/Lyrics/Content/Components/Lyrics/PreviewKaraokeSpriteText.cs @@ -65,22 +65,16 @@ private void triggerSizeChangedEvent() #region Text char index - public int? GetCharIndexByPosition(float position) + public int? GetCharIndexByPosition(Vector2 position) { for (int i = 0; i < Text.Length; i++) { - (double startX, double endX) = getTriggerPositionByTimeIndex(i); - if (position >= startX && position <= endX) + var rectangle = spriteText.GetCharacterDrawRectangle(i); + if (rectangle.Contains(position)) return i; } return null; - - Tuple getTriggerPositionByTimeIndex(int charIndex) - { - var rectangle = spriteText.GetCharacterDrawRectangle(charIndex); - return new Tuple(rectangle.Left, rectangle.Right); - } } public RectangleF GetRectByCharIndex(int charIndex) @@ -95,21 +89,40 @@ public RectangleF GetRectByCharIndex(int charIndex) #region Text indicator - public int GetCharIndicatorByPosition(float position) + public int? GetCharIndicatorByPosition(Vector2 position) { - for (int i = 0; i < Text.Length; i++) + for (int i = 0; i < Text.Length + 1; i++) { - float textCenterPosition = getTriggerPositionByTimeIndex(i); - if (position < textCenterPosition) + var rect = getTriggerPositionByTimeIndex(i); + if (rect.Contains(position)) return i; } - return Text.Length; + return null; - float getTriggerPositionByTimeIndex(int charIndex) + RectangleF getTriggerPositionByTimeIndex(int gapIndex) { - var rectangle = spriteText.GetCharacterDrawRectangle(charIndex); - return rectangle.Centre.X; + if (gapIndex == 0) + { + var rectangle = spriteText.GetCharacterDrawRectangle(gapIndex); + return new RectangleF(rectangle.Left, rectangle.Top, rectangle.Width / 2, rectangle.Height); + } + + if (gapIndex == Text.Length) + { + var rectangle = spriteText.GetCharacterDrawRectangle(gapIndex - 1); + return new RectangleF(rectangle.Centre.X, rectangle.Top, rectangle.Width / 2, rectangle.Height); + } + + var leftRectangle = spriteText.GetCharacterDrawRectangle(gapIndex - 1); + var rightRectangle = spriteText.GetCharacterDrawRectangle(gapIndex); + + float x = leftRectangle.Centre.X; + float y = Math.Min(leftRectangle.Y, rightRectangle.Y); + float width = rightRectangle.Centre.X - leftRectangle.Centre.X; + float height = Math.Max(leftRectangle.Height, rightRectangle.Height); + + return new RectangleF(x, y, width, height); } } @@ -148,7 +161,7 @@ public RectangleF GetRectByCharIndicator(int gapIndex) #region Time tag - public TimeTag? GetTimeTagByPosition(float position) + public TimeTag? GetTimeTagByPosition(Vector2 position) { var hoverIndex = getHoverIndex(); if (hoverIndex == null) @@ -165,7 +178,7 @@ public RectangleF GetRectByCharIndicator(int gapIndex) { var textIndex = new TextIndex(i, indexState); var triggerRange = getTriggerRange(textIndex); - if (position >= triggerRange.Item1 && position <= triggerRange.Item2) + if (triggerRange.Contains(position)) return textIndex; } } @@ -173,12 +186,12 @@ public RectangleF GetRectByCharIndicator(int gapIndex) // hover the last time-tag if exceed the range. return null; - Tuple getTriggerRange(TextIndex textIndex) + RectangleF getTriggerRange(TextIndex textIndex) { var rect = spriteText.GetCharacterDrawRectangle(textIndex.Index); return TextIndexUtils.GetValueByState(textIndex, - () => new Tuple(rect.Left, rect.Centre.X), - () => new Tuple(rect.Centre.X, rect.Right)); + () => new RectangleF(rect.Left, rect.Top, rect.Width / 2, rect.Height), + () => new RectangleF(rect.Centre.X, rect.Top, rect.Width / 2, rect.Height)); } } }