10 | | There are two methods within ffmpeg that can be used to concatenate files of the same type: [#demuxer the concat ''demuxer''] and [#protocol the concat ''protocol'']. The demuxer is more flexible - it requires the same codecs, but different container formats can be used; and it can be used with any container formats, while the protocol only works with a select few containers. However, the concat protocol is available in older versions of ffmpeg, where the demuxer isn't. |
| 10 | There are two methods within ffmpeg that can be used to concatenate files of the same type: |
| 11 | |
| 12 | 1. [#demuxer the concat ''demuxer''] |
| 13 | 2. [#protocol the concat ''protocol''] |
| 14 | |
| 15 | The demuxer is more flexible – it requires the same codecs, but different container formats can be used; and it can be used with any container formats, while the protocol only works with a select few containers. |
137 | | {{{ |
138 | | ffmpeg -i "concat:input1.mpg|input2.mpg|input3.mpg" -c copy output.mpg |
139 | | }}} |
140 | | |
141 | | If you have MP4 files, these could be losslessly concatenated by first transcoding them to mpeg transport streams. With h.264 video and AAC audio, the following can be used: |
| 145 | The following command concatenates three MPEG-2 TS files and concatenates them without re-encoding: |
| 146 | |
| 147 | {{{ |
| 148 | ffmpeg -i "concat:input1.ts|input2.ts|input3.ts" -c copy output.ts |
| 149 | }}} |
| 150 | |
| 151 | ==== Using intermediate files ==== |
| 152 | |
| 153 | If you have MP4 files, these could be losslessly concatenated by first transcoding them to MPEG-2 transport streams. With H.264 video and AAC audio, the following can be used: |
158 | | All MPEG codecs (H.264, MPEG4/divx/xvid, MPEG2; MP2, MP3, AAC) are supported in the mpegts container format, though the commands above would require some alteration (the `-bsf` bitstream filters will have to be changed). |
| 172 | All MPEG codecs (MPEG-4 Part 10 / AVC, MPEG-4 Part 2, MPEG-2 Video, MPEG-1 Audio Layer II, MPEG-2 Audio Layer III (MP3), MPEG-4 Part III (AAC)) are supported in the MPEG-TS container format, although the commands above would require some alteration (e.g., the `-bsf` bitstream filters will have to be changed). |
164 | | The concat filter is available in recent versions of ffmpeg. See the [https://ffmpeg.org/ffmpeg-filters.html#concat concat filter documentation] for more info. |
| 180 | See the [https://ffmpeg.org/ffmpeg-filters.html#concat concat filter documentation] for more info. The filter works on segments of synchronized video and audio streams. All segments must have the same number of streams of each type, and that will also be the number of streams at output. |
| 181 | |
| 182 | {{{ |
| 183 | #!div style="border: 1px solid #e5e5c7; margin: 1em; background-color: #ffd;" |
| 184 | '''Note:''' Filters are incompatible with [https://ffmpeg.org/ffmpeg.html#Stream-copy stream copying]; you can't use `-c copy` with this method. Since you have to re-encode the video and audio stream(s), and since re-encoding may introduce compression artifacts, make sure to add proper target bitrate or quality settings. See the [[Encode|encoding guides]] for more info. |
| 185 | }}} |
| 186 | |
| 187 | For the concat filter to work, the inputs have to be of the same frame dimensions (e.g., 1920⨉1080 pixels) and should have the same framerate. Therefore, you may at least have to add a [http://ffmpeg.org/ffmpeg-filters.html#scale-1 scale] or [http://ffmpeg.org/ffmpeg-filters.html#scale2ref scale2ref] filter before concatenating videos. A handful of other attributes have to match as well, like the stream aspect ratio. Refer to the documentation of the filter for more info. |
168 | | This is easiest to explain using an example: |
169 | | |
170 | | {{{ |
171 | | ffmpeg -i input1.mp4 -i input2.webm \ |
172 | | -filter_complex "[0:v:0] [0:a:0] [1:v:0] [1:a:0] concat=n=2:v=1:a=1 [v] [a]" \ |
173 | | -map "[v]" -map "[a]" <encoding options> output.mkv |
174 | | }}} |
175 | | |
176 | | On the `-filter_complex` line, the following: |
177 | | |
178 | | {{{ |
179 | | [0:v:0] [0:a:0] [1:v:0] [1:a:0] |
180 | | }}} |
181 | | |
182 | | tells ffmpeg what streams to send to the concat filter; in this case, video stream 0 [0:v:0] and audio stream 0 [0:a:0] from input 0 (`input1.mp4` in this example), and video stream 0 [1:v:0] and audio stream 0 [1:v:0] from input 1 (`input2.webm`). |
183 | | |
184 | | {{{ |
185 | | concat=n=2:v=1:a=1 [v] [a]' |
186 | | }}} |
187 | | |
188 | | This is the concat filter itself. `n=2` is telling the filter that there are two input files; `v=1` is telling it that there will be one video stream; `a=1` is telling it that there will be one audio stream. `[v]` and `[a]` are names for the output streams to allow the rest of the ffmpeg line to use the output of the concat filter. |
189 | | |
190 | | Note that the single quotes around the whole filter section are required. |
191 | | |
192 | | {{{ |
193 | | -map '[v]' -map '[a]' |
| 191 | Let's say we have three files that we want to concatenate – each of them with one video and audio stream. The concat filter command would look like this: |
| 192 | |
| 193 | {{{ |
| 194 | ffmpeg -i input1.mp4 -i input2.webm -i input3.mov \ |
| 195 | -filter_complex "[0:v:0][0:a:0][1:v:0][1:a:0][2:v:0][2:a:0]concat=n=3:v=1:a=1[outv][outa]" \ |
| 196 | -map "[outv]" -map "[outa]" output.mkv |
| 197 | }}} |
| 198 | |
| 199 | Now, let's dissect that command. We first specify all the input files, then instantiate a `-filter_complex` filtergraph – this is needed instead of `-filter:v` because it has multiple inputs and outputs. |
| 200 | |
| 201 | The following line: |
| 202 | |
| 203 | {{{ |
| 204 | [0:v:0][0:a:0][1:v:0][1:a:0][2:v:0][2:a:0] |
| 205 | }}} |
| 206 | |
| 207 | tells ffmpeg which streams to take from the input files and send as input to the concat filter. In this case, video stream 0 [0:v:0] and audio stream 0 [0:a:0] from input 0 (`input1.mp4` in this example), and video stream 0 [1:v:0] and audio stream 0 [1:v:0] from input 1 (`input2.webm`), etc. |
| 208 | |
| 209 | {{{ |
| 210 | concat=n=3:v=1:a=1[outv][outa]' |
| 211 | }}} |
| 212 | |
| 213 | This is the concat filter itself. `n=3` is telling the filter that there are three input segments; `v=1` is telling it that there will be one video stream per segment; `a=1` is telling it that there will be one audio stream per segment. The filter then concatenates these segments and produces two output streams. `[outv]` and `[outa]` are names for these output streams. Note that the quotes around the filter section are required. |
| 214 | |
| 215 | The following image shows the stream mapping to and from the filter in the above example: |
| 216 | |
| 217 | [[Image(concat_filter.png)]] |
| 218 | |
| 219 | You can then either re-use these streams in other filters, or [[Map|map them to the output file]]: |
| 220 | |
| 221 | {{{ |
| 222 | -map "[outv]" -map "[outa]" output.mkv |