diff options
author | James Almer <jamrial@gmail.com> | 2013-09-20 22:15:49 -0300 |
---|---|---|
committer | Michael Niedermayer <michaelni@gmx.at> | 2013-09-21 14:33:01 +0200 |
commit | 56f17407bc4673dad263982d6fad5ef3ae8c9240 (patch) | |
tree | 099a7e1f59da26a57b91e3498ce19643951fbb7d | |
parent | 8ad2465987d31bb818235303c0b02b897cd02133 (diff) | |
download | ffmpeg-56f17407bc4673dad263982d6fad5ef3ae8c9240.tar.gz |
matroska: Add the CueDuration element
Use it only on subtitle CuePoints.
With proper demuxer/splitter support this should improve the display
of subtitles right after seeking to a given point in the stream.
Signed-off-by: James Almer <jamrial@gmail.com>
Signed-off-by: Michael Niedermayer <michaelni@gmx.at>
-rw-r--r-- | libavformat/matroska.h | 1 | ||||
-rw-r--r-- | libavformat/matroskadec.c | 1 | ||||
-rw-r--r-- | libavformat/matroskaenc.c | 16 | ||||
-rw-r--r-- | tests/ref/lavf/mkv | 4 |
4 files changed, 15 insertions, 7 deletions
diff --git a/libavformat/matroska.h b/libavformat/matroska.h index 0c3dc29e19..3bb5aee080 100644 --- a/libavformat/matroska.h +++ b/libavformat/matroska.h @@ -159,6 +159,7 @@ #define MATROSKA_ID_CUETRACK 0xF7 #define MATROSKA_ID_CUECLUSTERPOSITION 0xF1 #define MATROSKA_ID_CUERELATIVEPOSITION 0xF0 +#define MATROSKA_ID_CUEDURATION 0xB2 #define MATROSKA_ID_CUEBLOCKNUMBER 0x5378 /* IDs in the tags master */ diff --git a/libavformat/matroskadec.c b/libavformat/matroskadec.c index 2482c6d390..a1b7f56634 100644 --- a/libavformat/matroskadec.c +++ b/libavformat/matroskadec.c @@ -476,6 +476,7 @@ static EbmlSyntax matroska_index_pos[] = { { MATROSKA_ID_CUETRACK, EBML_UINT, 0, offsetof(MatroskaIndexPos,track) }, { MATROSKA_ID_CUECLUSTERPOSITION, EBML_UINT, 0, offsetof(MatroskaIndexPos,pos) }, { MATROSKA_ID_CUERELATIVEPOSITION,EBML_NONE }, + { MATROSKA_ID_CUEDURATION, EBML_NONE }, { MATROSKA_ID_CUEBLOCKNUMBER, EBML_NONE }, { 0 } }; diff --git a/libavformat/matroskaenc.c b/libavformat/matroskaenc.c index c1e7f1fed2..b9848b66a5 100644 --- a/libavformat/matroskaenc.c +++ b/libavformat/matroskaenc.c @@ -70,6 +70,7 @@ typedef struct { int tracknum; int64_t cluster_pos; ///< file offset of the cluster containing the block int64_t relative_pos; ///< relative offset from the position of the cluster containing the block + int64_t duration; ///< duration of the block according to time base } mkv_cuepoint; typedef struct { @@ -119,9 +120,9 @@ typedef struct MatroskaMuxContext { * offset, 4 bytes for target EBML ID */ #define MAX_SEEKENTRY_SIZE 21 -/** per-cuepoint-track - 4 1-byte EBML IDs, 4 1-byte EBML sizes, 3 +/** per-cuepoint-track - 5 1-byte EBML IDs, 5 1-byte EBML sizes, 4 * 8-byte uint max */ -#define MAX_CUETRACKPOS_SIZE 32 +#define MAX_CUETRACKPOS_SIZE 42 /** per-cuepoint - 2 1-byte EBML IDs, 2 1-byte EBML sizes, 8-byte uint max */ #define MAX_CUEPOINT_SIZE(num_tracks) 12 + MAX_CUETRACKPOS_SIZE*num_tracks @@ -381,7 +382,8 @@ static mkv_cues * mkv_start_cues(int64_t segment_offset) return cues; } -static int mkv_add_cuepoint(mkv_cues *cues, int stream, int64_t ts, int64_t cluster_pos, int64_t relative_pos) +static int mkv_add_cuepoint(mkv_cues *cues, int stream, int64_t ts, int64_t cluster_pos, int64_t relative_pos, + int64_t duration) { mkv_cuepoint *entries = cues->entries; @@ -396,7 +398,8 @@ static int mkv_add_cuepoint(mkv_cues *cues, int stream, int64_t ts, int64_t clus cues->entries[cues->num_entries].pts = ts; cues->entries[cues->num_entries].tracknum = stream + 1; cues->entries[cues->num_entries].cluster_pos = cluster_pos - cues->segment_offset; - cues->entries[cues->num_entries++].relative_pos= relative_pos; + cues->entries[cues->num_entries].relative_pos = relative_pos; + cues->entries[cues->num_entries++].duration = duration; return 0; } @@ -432,6 +435,8 @@ static int64_t mkv_write_cues(AVIOContext *pb, mkv_cues *cues, mkv_track *tracks put_ebml_uint(pb, MATROSKA_ID_CUETRACK , entry[j].tracknum ); put_ebml_uint(pb, MATROSKA_ID_CUECLUSTERPOSITION , entry[j].cluster_pos); put_ebml_uint(pb, MATROSKA_ID_CUERELATIVEPOSITION, entry[j].relative_pos); + if (entry[j].duration != -1) + put_ebml_uint(pb, MATROSKA_ID_CUEDURATION , entry[j].duration); end_ebml_master(pb, track_positions); } i += j - 1; @@ -1521,7 +1526,8 @@ static int mkv_write_packet_internal(AVFormatContext *s, AVPacket *pkt) } if ((codec->codec_type == AVMEDIA_TYPE_VIDEO && keyframe) || codec->codec_type == AVMEDIA_TYPE_SUBTITLE) { - ret = mkv_add_cuepoint(mkv->cues, pkt->stream_index, ts, mkv->cluster_pos, relative_packet_pos); + ret = mkv_add_cuepoint(mkv->cues, pkt->stream_index, ts, mkv->cluster_pos, relative_packet_pos, + codec->codec_type == AVMEDIA_TYPE_SUBTITLE ? duration : -1); if (ret < 0) return ret; } diff --git a/tests/ref/lavf/mkv b/tests/ref/lavf/mkv index 72e20b780e..51fd2e71b3 100644 --- a/tests/ref/lavf/mkv +++ b/tests/ref/lavf/mkv @@ -1,5 +1,5 @@ -9e68abfecce533f200d9409bf7a38122 *./tests/data/lavf/lavf.mkv -472556 ./tests/data/lavf/lavf.mkv +5e3e58192b11644477474a25bef2e022 *./tests/data/lavf/lavf.mkv +472559 ./tests/data/lavf/lavf.mkv ./tests/data/lavf/lavf.mkv CRC=0xec6c3c68 6aac0de39634046f23a3447b08380efe *./tests/data/lavf/lavf.mkv 320288 ./tests/data/lavf/lavf.mkv |