You've already forked FFmpeg
mirror of
https://github.com/FFmpeg/FFmpeg.git
synced 2025-07-11 14:30:22 +02:00
avconv: change semantics of -map
New syntax contains an optional stream type, allowing to refer to n-th stream of specific type. Omitting stream number now maps all streams of the given type.
This commit is contained in:
110
avconv.c
110
avconv.c
@ -79,6 +79,7 @@ const int program_birth_year = 2000;
|
|||||||
|
|
||||||
/* select an input stream for an output stream */
|
/* select an input stream for an output stream */
|
||||||
typedef struct StreamMap {
|
typedef struct StreamMap {
|
||||||
|
int disabled; /** 1 is this mapping is disabled by a negative map */
|
||||||
int file_index;
|
int file_index;
|
||||||
int stream_index;
|
int stream_index;
|
||||||
int sync_file_index;
|
int sync_file_index;
|
||||||
@ -2780,27 +2781,82 @@ static int opt_codec_tag(const char *opt, const char *arg)
|
|||||||
|
|
||||||
static int opt_map(const char *opt, const char *arg)
|
static int opt_map(const char *opt, const char *arg)
|
||||||
{
|
{
|
||||||
StreamMap *m;
|
StreamMap *m = NULL;
|
||||||
char *p;
|
int i, negative = 0, file_idx;
|
||||||
|
int sync_file_idx = -1, sync_stream_idx;
|
||||||
|
char *p, *sync;
|
||||||
|
char *map;
|
||||||
|
|
||||||
stream_maps = grow_array(stream_maps, sizeof(*stream_maps), &nb_stream_maps, nb_stream_maps + 1);
|
if (*arg == '-') {
|
||||||
m = &stream_maps[nb_stream_maps-1];
|
negative = 1;
|
||||||
|
arg++;
|
||||||
m->file_index = strtol(arg, &p, 0);
|
|
||||||
if (*p)
|
|
||||||
p++;
|
|
||||||
|
|
||||||
m->stream_index = strtol(p, &p, 0);
|
|
||||||
if (*p) {
|
|
||||||
p++;
|
|
||||||
m->sync_file_index = strtol(p, &p, 0);
|
|
||||||
if (*p)
|
|
||||||
p++;
|
|
||||||
m->sync_stream_index = strtol(p, &p, 0);
|
|
||||||
} else {
|
|
||||||
m->sync_file_index = m->file_index;
|
|
||||||
m->sync_stream_index = m->stream_index;
|
|
||||||
}
|
}
|
||||||
|
map = av_strdup(arg);
|
||||||
|
|
||||||
|
/* parse sync stream first, just pick first matching stream */
|
||||||
|
if (sync = strchr(map, ',')) {
|
||||||
|
*sync = 0;
|
||||||
|
sync_file_idx = strtol(sync + 1, &sync, 0);
|
||||||
|
if (sync_file_idx >= nb_input_files || sync_file_idx < 0) {
|
||||||
|
av_log(NULL, AV_LOG_ERROR, "Invalid sync file index: %d.\n", sync_file_idx);
|
||||||
|
exit_program(1);
|
||||||
|
}
|
||||||
|
if (*sync)
|
||||||
|
sync++;
|
||||||
|
for (i = 0; i < input_files[sync_file_idx].ctx->nb_streams; i++)
|
||||||
|
if (check_stream_specifier(input_files[sync_file_idx].ctx,
|
||||||
|
input_files[sync_file_idx].ctx->streams[i], sync) == 1) {
|
||||||
|
sync_stream_idx = i;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
if (i == input_files[sync_file_idx].ctx->nb_streams) {
|
||||||
|
av_log(NULL, AV_LOG_ERROR, "Sync stream specification in map %s does not "
|
||||||
|
"match any streams.\n", arg);
|
||||||
|
exit_program(1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
file_idx = strtol(map, &p, 0);
|
||||||
|
if (file_idx >= nb_input_files || file_idx < 0) {
|
||||||
|
av_log(NULL, AV_LOG_ERROR, "Invalid input file index: %d.\n", file_idx);
|
||||||
|
exit_program(1);
|
||||||
|
}
|
||||||
|
if (negative)
|
||||||
|
/* disable some already defined maps */
|
||||||
|
for (i = 0; i < nb_stream_maps; i++) {
|
||||||
|
m = &stream_maps[i];
|
||||||
|
if (check_stream_specifier(input_files[m->file_index].ctx,
|
||||||
|
input_files[m->file_index].ctx->streams[m->stream_index],
|
||||||
|
*p == ':' ? p + 1 : p) > 0)
|
||||||
|
m->disabled = 1;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
for (i = 0; i < input_files[file_idx].ctx->nb_streams; i++) {
|
||||||
|
if (check_stream_specifier(input_files[file_idx].ctx, input_files[file_idx].ctx->streams[i],
|
||||||
|
*p == ':' ? p + 1 : p) <= 0)
|
||||||
|
continue;
|
||||||
|
stream_maps = grow_array(stream_maps, sizeof(*stream_maps), &nb_stream_maps, nb_stream_maps + 1);
|
||||||
|
m = &stream_maps[nb_stream_maps - 1];
|
||||||
|
|
||||||
|
m->file_index = file_idx;
|
||||||
|
m->stream_index = i;
|
||||||
|
|
||||||
|
if (sync_file_idx >= 0) {
|
||||||
|
m->sync_file_index = sync_file_idx;
|
||||||
|
m->sync_stream_index = sync_stream_idx;
|
||||||
|
} else {
|
||||||
|
m->sync_file_index = file_idx;
|
||||||
|
m->sync_stream_index = i;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!m) {
|
||||||
|
av_log(NULL, AV_LOG_ERROR, "Stream map '%s' matches no streams.\n", arg);
|
||||||
|
exit_program(1);
|
||||||
|
}
|
||||||
|
|
||||||
|
av_freep(&map);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -3514,21 +3570,9 @@ static void opt_output_file(const char *filename)
|
|||||||
} else {
|
} else {
|
||||||
for (i = 0; i < nb_stream_maps; i++) {
|
for (i = 0; i < nb_stream_maps; i++) {
|
||||||
StreamMap *map = &stream_maps[i];
|
StreamMap *map = &stream_maps[i];
|
||||||
int fi = map->file_index;
|
|
||||||
int si = map->stream_index;
|
|
||||||
|
|
||||||
if (fi < 0 || fi >= nb_input_files ||
|
if (map->disabled)
|
||||||
si < 0 || si >= input_files[fi].ctx->nb_streams) {
|
continue;
|
||||||
av_log(NULL, AV_LOG_ERROR, "Input stream #%d.%d does not exist.\n", fi, si);
|
|
||||||
exit_program(1);
|
|
||||||
}
|
|
||||||
fi = map->sync_file_index;
|
|
||||||
si = map->sync_stream_index;
|
|
||||||
if (fi < 0 || fi >= nb_input_files ||
|
|
||||||
si < 0 || si >= input_files[fi].ctx->nb_streams) {
|
|
||||||
av_log(NULL, AV_LOG_ERROR, "Sync stream #%d.%d does not exist.\n", fi, si);
|
|
||||||
exit_program(1);
|
|
||||||
}
|
|
||||||
|
|
||||||
ist = &input_streams[input_files[map->file_index].ist_index + map->stream_index];
|
ist = &input_streams[input_files[map->file_index].ist_index + map->stream_index];
|
||||||
switch (ist->st->codec->codec_type) {
|
switch (ist->st->codec->codec_type) {
|
||||||
|
@ -634,35 +634,60 @@ Synchronize read on input.
|
|||||||
@section Advanced options
|
@section Advanced options
|
||||||
|
|
||||||
@table @option
|
@table @option
|
||||||
@item -map @var{input_file_id}.@var{input_stream_id}[:@var{sync_file_id}.@var{sync_stream_id}]
|
@item -map [-]@var{input_file_id}[:@var{input_stream_type}][:@var{input_stream_id}][,@var{sync_file_id}[:@var{sync_stream_type}][:@var{sync_stream_id}]]
|
||||||
|
|
||||||
Designate an input stream as a source for the output file. Each input
|
Designate one or more input streams as a source for the output file. Each input
|
||||||
stream is identified by the input file index @var{input_file_id} and
|
stream is identified by the input file index @var{input_file_id} and
|
||||||
the input stream index @var{input_stream_id} within the input
|
the input stream index @var{input_stream_id} within the input
|
||||||
file. Both indexes start at 0. If specified,
|
file. Both indices start at 0. If specified,
|
||||||
@var{sync_file_id}.@var{sync_stream_id} sets which input stream
|
@var{sync_file_id}:@var{sync_stream_id} sets which input stream
|
||||||
is used as a presentation sync reference.
|
is used as a presentation sync reference.
|
||||||
|
|
||||||
|
If @var{input_stream_type} is specified -- 'v' for video, 'a' for audio, 's' for
|
||||||
|
subtitle and 'd' for data -- then @var{input_stream_id} counts only the streams
|
||||||
|
of this type. Same for @var{sync_stream_type}.
|
||||||
|
|
||||||
|
@var{input_stream_id} may be omitted, in which case all streams of the given
|
||||||
|
type are mapped (or all streams in the file, if no type is specified).
|
||||||
|
|
||||||
The first @code{-map} option on the command line specifies the
|
The first @code{-map} option on the command line specifies the
|
||||||
source for output stream 0, the second @code{-map} option specifies
|
source for output stream 0, the second @code{-map} option specifies
|
||||||
the source for output stream 1, etc.
|
the source for output stream 1, etc.
|
||||||
|
|
||||||
|
A @code{-} character before the stream identifier creates a "negative" mapping.
|
||||||
|
It disables matching streams from already created mappings.
|
||||||
|
|
||||||
|
For example, to map ALL streams from the first input file to output
|
||||||
|
@example
|
||||||
|
av -i INPUT -map 0 output
|
||||||
|
@end example
|
||||||
|
|
||||||
For example, if you have two audio streams in the first input file,
|
For example, if you have two audio streams in the first input file,
|
||||||
these streams are identified by "0.0" and "0.1". You can use
|
these streams are identified by "0:0" and "0:1". You can use
|
||||||
@code{-map} to select which streams to place in an output file. For
|
@code{-map} to select which streams to place in an output file. For
|
||||||
example:
|
example:
|
||||||
@example
|
@example
|
||||||
avconv -i INPUT -map 0.1 out.wav
|
avconv -i INPUT -map 0:1 out.wav
|
||||||
@end example
|
@end example
|
||||||
will map the input stream in @file{INPUT} identified by "0.1" to
|
will map the input stream in @file{INPUT} identified by "0:1" to
|
||||||
the (single) output stream in @file{out.wav}.
|
the (single) output stream in @file{out.wav}.
|
||||||
|
|
||||||
For example, to select the stream with index 2 from input file
|
For example, to select the stream with index 2 from input file
|
||||||
@file{a.mov} (specified by the identifier "0.2"), and stream with
|
@file{a.mov} (specified by the identifier "0:2"), and stream with
|
||||||
index 6 from input @file{b.mov} (specified by the identifier "1.6"),
|
index 6 from input @file{b.mov} (specified by the identifier "1:6"),
|
||||||
and copy them to the output file @file{out.mov}:
|
and copy them to the output file @file{out.mov}:
|
||||||
@example
|
@example
|
||||||
avconv -i a.mov -i b.mov -vcodec copy -acodec copy -map 0.2 -map 1.6 out.mov
|
avconv -i a.mov -i b.mov -vcodec copy -acodec copy -map 0:2 -map 1:6 out.mov
|
||||||
|
@end example
|
||||||
|
|
||||||
|
To select all video and the third audio stream from an input file:
|
||||||
|
@example
|
||||||
|
avconv -i INPUT -map 0:v -map 0:a:2 OUTPUT
|
||||||
|
@end example
|
||||||
|
|
||||||
|
To map all the streams except the second audio, use negative mappings
|
||||||
|
@example
|
||||||
|
avconv -i INPUT -map 0 -map -0:a:1 OUTPUT
|
||||||
@end example
|
@end example
|
||||||
|
|
||||||
Note that using this option disables the default mappings for this output file.
|
Note that using this option disables the default mappings for this output file.
|
||||||
@ -943,7 +968,7 @@ You can encode to several formats at the same time and define a
|
|||||||
mapping from input stream to output streams:
|
mapping from input stream to output streams:
|
||||||
|
|
||||||
@example
|
@example
|
||||||
avconv -i /tmp/a.wav -ab 64k /tmp/a.mp2 -ab 128k /tmp/b.mp2 -map 0:0 -map 0:0
|
avconv -i /tmp/a.wav -map 0:a -ab 64k /tmp/a.mp2 -map 0:a -ab 128k /tmp/b.mp2
|
||||||
@end example
|
@end example
|
||||||
|
|
||||||
Converts a.wav to a.mp2 at 64 kbits and to b.mp2 at 128 kbits. '-map
|
Converts a.wav to a.mp2 at 64 kbits and to b.mp2 at 128 kbits. '-map
|
||||||
|
Reference in New Issue
Block a user