Skip to content

Commit

Permalink
Merge pull request #150 from andy840119/fix-playback-issue
Browse files Browse the repository at this point in the history
Fix playback issue.
  • Loading branch information
andy840119 authored Apr 23, 2022
2 parents 80e4e85 + 92e673c commit c3fa6b4
Showing 1 changed file with 43 additions and 47 deletions.
90 changes: 43 additions & 47 deletions osu.Framework.Font/Graphics/Sprites/KaraokeSpriteText.cs
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
// Copyright (c) karaoke.dev <[email protected]>. Licensed under the MIT Licence.
// Copyright (c) karaoke.dev <[email protected]>. Licensed under the MIT Licence.
// See the LICENCE file in the repository root for full licence text.

using System;
Expand Down Expand Up @@ -421,56 +421,52 @@ protected override bool OnInvalidate(Invalidation invalidation, InvalidationSour
if (!invalidation.HasFlag(Invalidation.Presence) || !hasTimeTag || !hasText)
return result;

Schedule(() =>
{
// set initial width.
// we should get width from child object because draw width haven't updated.
var width = frontLyricText.Width;
frontLyricTextContainer.Width = 0;
backLyricTextContainer.Width = width;

// reset masking transform.
frontLyricTextContainer.ClearTransforms();
backLyricTextContainer.ClearTransforms();

// filter valid time-tag with order.
var characters = frontLyricText.Characters;
var validTimeTag = TimeTags
.Where(x => x.Key.Index >= 0 && x.Key.Index < Text.Length)
.OrderBy(x => x.Value).ToArray();

// get first time-tag relative start time.
var currentTime = Time.Current;
var relativeTime = validTimeTag.FirstOrDefault().Value;

// should use absolute time to process time-tags.
using (frontLyricTextContainer.BeginAbsoluteSequence(currentTime))
using (frontLyricTextContainer.BeginAbsoluteSequence(currentTime))
{
// get transform sequence and set initial delay time.
var frontTransformSequence = frontLyricTextContainer.Delay(relativeTime - currentTime).Then();
var backTransformSequence = backLyricTextContainer.Delay(relativeTime - currentTime).Then();
Schedule(RefreshStateTransforms);

foreach (var (textIndex, time) in validTimeTag)
{
// calculate position and duration relative to precious time-tag time.
var characterRectangle = characters[textIndex.Index].DrawRectangle;
var position = textIndex.State == TextIndex.IndexState.Start ? characterRectangle.Left : characterRectangle.Right;
var duration = Math.Max(time - relativeTime, 0);
return true;
}

// apply the position with delay time.
frontTransformSequence.ResizeWidthTo(position, duration).Then();
backTransformSequence.ResizeWidthTo(DrawWidth - position, duration).Then();
public virtual void RefreshStateTransforms()
{
// set initial width.
// we should get width from child object because draw width haven't updated.
var width = frontLyricText.Width;
frontLyricTextContainer.Width = 0;
backLyricTextContainer.Width = width;

// reset masking transform.
frontLyricTextContainer.ClearTransforms();
backLyricTextContainer.ClearTransforms();

// filter valid time-tag with order.
var characters = frontLyricText.Characters;
var validTimeTag = TimeTags
.Where(x => x.Key.Index >= 0 && x.Key.Index < Text.Length)
.OrderBy(x => x.Value).ToArray();

// get first time-tag relative start time.
var currentTime = Time.Current;
var relativeTime = validTimeTag.FirstOrDefault().Value;

// get transform sequence and set initial delay time.
var delay = relativeTime - currentTime;
var frontTransformSequence = frontLyricTextContainer.Delay(delay).ResizeWidthTo(0).Then();
var backTransformSequence = backLyricTextContainer.Delay(delay).ResizeWidthTo(width).Then();

foreach ((var textIndex, double time) in validTimeTag)
{
// calculate position and duration relative to precious time-tag time.
var characterRectangle = characters[textIndex.Index].DrawRectangle;
var position = textIndex.State == TextIndex.IndexState.Start ? characterRectangle.Left : characterRectangle.Right;
var duration = Math.Max(time - relativeTime, 0);

// save current time-tag time for letting next time-tag able to calculate duration.
relativeTime = time;
}
}
});
// apply the position with delay time.
frontTransformSequence.ResizeWidthTo(position, duration).Then();
backTransformSequence.ResizeWidthTo(width - position, duration).Then();

return true;
// save current time-tag time for letting next time-tag able to calculate duration.
relativeTime = time;
}
}

public override bool RemoveCompletedTransforms => false;
}
}

0 comments on commit c3fa6b4

Please sign in to comment.