summaryrefslogtreecommitdiffstats
path: root/core/mplayer.c
diff options
context:
space:
mode:
Diffstat (limited to 'core/mplayer.c')
-rw-r--r--core/mplayer.c110
1 files changed, 32 insertions, 78 deletions
diff --git a/core/mplayer.c b/core/mplayer.c
index d28b5fdc4c..3cdd83021d 100644
--- a/core/mplayer.c
+++ b/core/mplayer.c
@@ -71,7 +71,6 @@
#include "core/mplayer.h"
#include "core/m_property.h"
-#include "sub/subreader.h"
#include "sub/find_subfiles.h"
#include "sub/dec_sub.h"
#include "sub/sd.h"
@@ -197,9 +196,6 @@ static const char av_desync_help_text[] = _(
static void reset_subtitles(struct MPContext *mpctx);
static void reinit_subs(struct MPContext *mpctx);
-static struct track *open_external_file(struct MPContext *mpctx, char *filename,
- char *demuxer_name, int stream_cache,
- enum stream_type filter);
static double get_relative_time(struct MPContext *mpctx)
{
@@ -982,6 +978,9 @@ static struct track *add_stream_track(struct MPContext *mpctx,
};
MP_TARRAY_APPEND(mpctx, mpctx->tracks, mpctx->num_tracks, track);
+ if (stream->type == STREAM_SUB)
+ track->preloaded = !!stream->sub->track;
+
// Needed for DVD and Blu-ray.
if (!track->lang) {
struct stream_lang_req req = {
@@ -1028,69 +1027,6 @@ static void add_dvd_tracks(struct MPContext *mpctx)
#endif
}
-#ifdef CONFIG_ASS
-static int free_sub_data(void *ptr)
-{
- struct sh_sub *sh_sub = *(struct sh_sub **)ptr;
- if (sh_sub->track)
- ass_free_track(sh_sub->track);
- talloc_free(sh_sub->sub_data);
- return 1;
-}
-#endif
-
-struct track *mp_add_subtitles(struct MPContext *mpctx, char *filename,
- float fps, int noerr)
-{
- struct MPOpts *opts = &mpctx->opts;
- struct ass_track *asst = NULL;
- sub_data *subd = NULL;
-
- if (filename == NULL)
- return NULL;
-
- // Note: no text subtitles without libass. This is mainly because sd_ass is
- // used for rendering. Even when showing subtitles with term-osd, going
- // through sd_ass makes the code much simpler, as sd_ass can handle all
- // the weird special-cases.
-#ifdef CONFIG_ASS
- asst = mp_ass_read_stream(mpctx->ass_library, filename, opts->sub_cp);
- if (!asst)
- subd = sub_read_file(filename, fps, &mpctx->opts);
- if (asst || subd) {
- struct demuxer *d = new_sub_pseudo_demuxer(opts);
- assert(d->num_streams == 1);
- struct sh_stream *s = d->streams[0];
- assert(s->type == STREAM_SUB);
-
- s->codec = asst ? "ass" : subd->codec;
- s->sub->track = asst;
- s->sub->sub_data = subd;
-
- struct sh_sub **pptr = talloc(d, struct sh_sub*);
- *pptr = s->sub;
- talloc_set_destructor(pptr, free_sub_data);
-
- struct track *t = add_stream_track(mpctx, s, false);
- t->is_external = true;
- t->preloaded = true;
- t->title = talloc_strdup(t, filename);
- t->external_filename = talloc_strdup(t, filename);
- MP_TARRAY_APPEND(NULL, mpctx->sources, mpctx->num_sources, d);
- return t;
- }
-#endif
-
- // Used with libavformat subtitles.
- struct track *ext = open_external_file(mpctx, filename, NULL, 0, STREAM_SUB);
- if (ext)
- return ext;
-
- mp_tmsg(MSGT_CPLAYER, noerr ? MSGL_WARN : MSGL_ERR,
- "Cannot load subtitles: %s\n", filename);
- return NULL;
-}
-
int mp_get_cache_percent(struct MPContext *mpctx)
{
if (mpctx->stream) {
@@ -2001,7 +1937,8 @@ static void reinit_subs(struct MPContext *mpctx)
if (!mpctx->sh_sub->dec_sub)
mpctx->sh_sub->dec_sub = sub_create(opts);
- if (track->demuxer && !track->stream) {
+ assert(track->demuxer);
+ if (!track->stream) {
// Lazily added DVD track - we must not miss the first subtitle packet,
// which makes the demuxer create the sh_stream, and contains the first
// subtitle event.
@@ -2016,7 +1953,6 @@ static void reinit_subs(struct MPContext *mpctx)
return;
}
- assert(track->demuxer && track->stream);
mpctx->initialized_flags |= INITIALIZED_SUB;
@@ -2027,12 +1963,22 @@ static void reinit_subs(struct MPContext *mpctx)
if (!sub_is_initialized(dec_sub)) {
int w = mpctx->sh_video ? mpctx->sh_video->disp_w : 0;
int h = mpctx->sh_video ? mpctx->sh_video->disp_h : 0;
+ float fps = mpctx->sh_video ? mpctx->sh_video->fps : 25;
set_dvdsub_fake_extradata(dec_sub, track->demuxer->stream, w, h);
sub_set_video_res(dec_sub, w, h);
+ sub_set_video_fps(dec_sub, fps);
sub_set_ass_renderer(dec_sub, mpctx->osd->ass_library,
mpctx->osd->ass_renderer);
sub_init_from_sh(dec_sub, sh_sub);
+
+ // Don't do this if the file has video/audio streams. Don't do it even
+ // if it has only sub streams, because reading packets will change the
+ // demuxer position.
+ if (!track->preloaded && track->is_external) {
+ demux_seek(track->demuxer, 0, 0, SEEK_ABSOLUTE);
+ track->preloaded = sub_read_all_packets(dec_sub, sh_sub);
+ }
}
mpctx->osd->dec_sub = dec_sub;
@@ -3920,16 +3866,15 @@ static void open_subtitles_from_options(struct MPContext *mpctx)
// after reading video params we should load subtitles because
// we know fps so now we can adjust subtitle time to ~6 seconds AST
// check .sub
- double sub_fps = mpctx->sh_video ? mpctx->sh_video->fps : 25;
if (mpctx->opts.sub_name) {
for (int i = 0; mpctx->opts.sub_name[i] != NULL; ++i)
- mp_add_subtitles(mpctx, mpctx->opts.sub_name[i], sub_fps, 0);
+ mp_add_subtitles(mpctx, mpctx->opts.sub_name[i], 0);
}
if (mpctx->opts.sub_auto) { // auto load sub file ...
char **tmp = find_text_subtitles(&mpctx->opts, mpctx->filename);
int nsub = MP_TALLOC_ELEMS(tmp);
for (int i = 0; i < nsub; i++) {
- struct track *track = mp_add_subtitles(mpctx, tmp[i], sub_fps, 1);
+ struct track *track = mp_add_subtitles(mpctx, tmp[i], 1);
if (track)
track->auto_loaded = true;
}
@@ -3959,9 +3904,12 @@ static struct track *open_external_file(struct MPContext *mpctx, char *filename,
case STREAM_SUB: ss = -1; break;
}
vs = -1; // avi can't go without video
+ struct demuxer_params params = {
+ .ass_library = mpctx->ass_library, // demux_libass requires it
+ };
struct demuxer *demuxer =
demux_open_withparams(&mpctx->opts, stream, format, demuxer_name,
- as, vs, ss, filename, NULL);
+ as, vs, ss, filename, &params);
if (!demuxer) {
free_stream(stream);
goto err_out;
@@ -3999,12 +3947,11 @@ static void open_audiofiles_from_options(struct MPContext *mpctx)
opts->audio_stream_cache, STREAM_AUDIO);
}
-// Just for -subfile. open_subtitles_from_options handles -sub text sub files.
-static void open_subfiles_from_options(struct MPContext *mpctx)
+struct track *mp_add_subtitles(struct MPContext *mpctx, char *filename, int noerr)
{
struct MPOpts *opts = &mpctx->opts;
- open_external_file(mpctx, opts->sub_stream, opts->sub_demuxer_name,
- 0, STREAM_SUB);
+ return open_external_file(mpctx, filename, opts->sub_demuxer_name, 0,
+ STREAM_SUB);
}
static void print_timeline(struct MPContext *mpctx)
@@ -4293,13 +4240,20 @@ goto_reopen_demuxer: ;
if (mpctx->timeline)
timeline_set_part(mpctx, mpctx->timeline_part, true);
+ // Decide correct-pts mode based on first segment of video track
+ opts->correct_pts = opts->user_correct_pts;
+ if (opts->correct_pts < 0) {
+ opts->correct_pts =
+ demux_control(mpctx->demuxer, DEMUXER_CTRL_CORRECT_PTS,
+ NULL) == DEMUXER_CTRL_OK;
+ }
+
mpctx->initialized_flags |= INITIALIZED_DEMUXER;
add_subtitle_fonts_from_sources(mpctx);
open_subtitles_from_options(mpctx);
open_audiofiles_from_options(mpctx);
- open_subfiles_from_options(mpctx);
check_previous_track_selection(mpctx);