diff options
-rw-r--r-- | DOCS/man/en/mplayer.1 | 11 | ||||
-rw-r--r-- | cfg-mplayer.h | 1 | ||||
-rw-r--r-- | defaultopts.c | 1 | ||||
-rw-r--r-- | mplayer.c | 24 | ||||
-rw-r--r-- | options.h | 1 |
5 files changed, 32 insertions, 6 deletions
diff --git a/DOCS/man/en/mplayer.1 b/DOCS/man/en/mplayer.1 index 29c1ba9eba..5de2a32749 100644 --- a/DOCS/man/en/mplayer.1 +++ b/DOCS/man/en/mplayer.1 @@ -798,6 +798,17 @@ With this option MPlayer will also ignore frame duration when playing only video (you can think of that as infinite fps). . .TP +.B \-chapter\-merge\-threshold <number> +Threshold for merging almost consecutive ordered chapter parts +in milliseconds (default: 100). +Some Matroska files with ordered chapters have inaccurate chapter +end timestamps, causing a small gap between the end of one chapter and +the start of the next one when they should match. +If the end of one playback part is less than the given threshold away +from the start of the next one then keep playing video normally over the +chapter change instead of doing a seek. +. +.TP .B \-colorkey <number> Changes the colorkey to an RGB value of your choice. 0x000000 is black and 0xffffff is white. diff --git a/cfg-mplayer.h b/cfg-mplayer.h index 0584957215..be52df881a 100644 --- a/cfg-mplayer.h +++ b/cfg-mplayer.h @@ -305,6 +305,7 @@ const m_option_t mplayer_opts[]={ {"playlist", NULL, CONF_TYPE_STRING, 0, 0, 0, NULL}, OPT_MAKE_FLAGS("ordered-chapters", ordered_chapters, 0), + OPT_INTRANGE("chapter-merge-threshold", chapter_merge_threshold, 0, 0, 10000), // a-v sync stuff: OPT_MAKE_FLAGS("correct-pts", user_correct_pts, 0), diff --git a/defaultopts.c b/defaultopts.c index e8f842cd47..aabe0effe1 100644 --- a/defaultopts.c +++ b/defaultopts.c @@ -23,6 +23,7 @@ void set_default_mplayer_options(struct MPOpts *opts) .stream_dump_name = "stream.dump", .loop_times = -1, .ordered_chapters = 1, + .chapter_merge_threshold = 100, .stream_cache_min_percent = 20.0, .stream_cache_seek_min_percent = 50.0, .chapterrange = {-1, -1}, @@ -3100,7 +3100,9 @@ static int find_ordered_chapter_sources(struct MPContext *mpctx, static void build_ordered_chapter_timeline(struct MPContext *mpctx) { - if (!mpctx->opts.ordered_chapters) { + struct MPOpts *opts = &mpctx->opts; + + if (!opts->ordered_chapters) { mp_msg(MSGT_CPLAYER, MSGL_INFO, "File uses ordered chapters, but " "you have disabled support for them. Ignoring.\n"); return; @@ -3162,21 +3164,31 @@ static void build_ordered_chapter_timeline(struct MPContext *mpctx) missing_time += c->end - c->start; continue; found2:; - chapters[num_chapters].start = starttime / 1000.; - chapters[num_chapters].name = talloc_strdup(chapters, c->name); /* Only add a separate part if the time or file actually changes. * Matroska files have chapter divisions that are redundant from * timeline point of view because the same chapter structure is used * both to specify the timeline and for normal chapter information. - * Removing a missing inserted external chapter can also cause this. */ - if (part_count == 0 || c->start != starttime + prev_part_offset + * Removing a missing inserted external chapter can also cause this. + * We allow for a configurable fudge factor because of files which + * specify chapter end times that are one frame too early; + * we don't want to try seeking over a one frame gap. */ + int64_t join_diff = c->start - starttime - prev_part_offset; + if (part_count == 0 || FFABS(join_diff) > opts->chapter_merge_threshold || sources + j != timeline[part_count - 1].source) { timeline[part_count].source = sources + j; - timeline[part_count].start = chapters[num_chapters].start; + timeline[part_count].start = starttime / 1000.; timeline[part_count].source_start = c->start / 1000.; prev_part_offset = c->start - starttime; part_count++; + } else if (part_count > 0 && join_diff) { + /* Chapter was merged at an inexact boundary; + * adjust timestamps to match. */ + mp_msg(MSGT_CPLAYER, MSGL_V, "Merging timeline part %d with " + "offset %d ms.\n", i, (int) join_diff); + starttime += join_diff; } + chapters[num_chapters].start = starttime / 1000.; + chapters[num_chapters].name = talloc_strdup(chapters, c->name); starttime += c->end - c->start; num_chapters++; } @@ -37,6 +37,7 @@ typedef struct MPOpts { int capture_dump; int loop_times; int ordered_chapters; + int chapter_merge_threshold; int quiet; float stream_cache_min_percent; float stream_cache_seek_min_percent; |