diff options
author | Oleg Oshmyan <chortos@inbox.lv> | 2020-10-18 18:08:39 +0300 |
---|---|---|
committer | Oleg Oshmyan <chortos@inbox.lv> | 2020-10-27 01:24:25 +0200 |
commit | b4303ad8c2142b8bdbedebb381a8ad4e6cd4feda (patch) | |
tree | 55f648b5ebf439d4ea58372153b1b85d8f08bd8d /libass/ass_parse.c | |
parent | 34cbd0f865bf4db3dbe335a3ae90b6aafd1c3192 (diff) | |
download | libass-b4303ad8c2142b8bdbedebb381a8ad4e6cd4feda.tar.bz2 libass-b4303ad8c2142b8bdbedebb381a8ad4e6cd4feda.tar.xz |
Handle \k0 \ko0 \kf0 \K0 like VSFilter
Don't break runs when zero-duration karaoke starts unless the karaoke
*type* differs. The zero-duration karaoke block ends up glued to the
previous block (if any). In case of subsequent karaoke override tags,
like {\k100\k0}, the intervening tags will advance the next karaoke
block's start time, but not this combined block's start or end time.
Of course, runs may still be broken in the same place if there's another
reason for a run break besides karaoke, so zero-duration karaoke blocks
can still occur. Run breaks that have no karaoke tags at all also still
produce zero-duration karaoke blocks (if there is karaoke at all).
Diffstat (limited to 'libass/ass_parse.c')
-rw-r--r-- | libass/ass_parse.c | 13 |
1 files changed, 10 insertions, 3 deletions
diff --git a/libass/ass_parse.c b/libass/ass_parse.c index 11d7f1be..5666ca6a 100644 --- a/libass/ass_parse.c +++ b/libass/ass_parse.c @@ -974,13 +974,19 @@ void process_karaoke_effects(ASS_Renderer *render_priv) { long long tm_current = render_priv->time - render_priv->state.event->Start; - int timing = 0; + int timing = 0, skip_timing = 0; Effect effect_type = EF_NONE; GlyphInfo *last_boundary = NULL; for (int i = 0; i <= render_priv->text_info.length; i++) { if (i < render_priv->text_info.length && - !render_priv->text_info.glyphs[i].starts_new_run) + !render_priv->text_info.glyphs[i].starts_new_run) { + // VSFilter compatibility: if we have \k12345\k0 without a run + // break, subsequent text is still part of the same karaoke word, + // the current word's starting and ending time stay unchanged, + // but the starting time of the next karaoke word is advanced. + skip_timing += render_priv->text_info.glyphs[i].effect_skip_timing; continue; + } GlyphInfo *start = last_boundary; GlyphInfo *end = render_priv->text_info.glyphs + i; @@ -995,7 +1001,8 @@ void process_karaoke_effects(ASS_Renderer *render_priv) long long tm_start = timing + start->effect_skip_timing; long long tm_end = tm_start + start->effect_timing; - timing = tm_end; + timing = tm_end + skip_timing; + skip_timing = 0; if (effect_type != EF_KARAOKE_KF) tm_end = tm_start; |