Merge Multiple Video Segments with FFmpeg Select

This article demonstrates how to use FFmpeg's select and aselect filters to extract multiple non-continuous segments from a video and merge them into a single output file. You will learn the exact command-line syntax required to define your time ranges, synchronize the audio, and reconstruct the video timeline to prevent frozen frames or playback gaps.

To cut and join multiple disjoint segments of a video using the select filter, you must filter both the video and audio streams simultaneously and then reset their presentation timestamps (PTS). If you do not reset the timestamps, the output video will contain frozen frames or empty gaps where the discarded segments used to be.

The FFmpeg Command

Below is the standard template command to select and merge two segments: from 0 to 10 seconds and from 30 to 40 seconds.

ffmpeg -i input.mp4 -vf "select='between(t,0,10)+between(t,30,40)',setpts=N/FRAME_RATE/TB" -af "aselect='between(t,0,10)+between(t,30,40)',asetpts=N/SR/TB" output.mp4

Command Breakdown

  • -i input.mp4: Specifies the input video file.
  • -vf "...": Applies the video filtergraph.
    • select='between(t,0,10)+between(t,30,40)': This tells FFmpeg to only keep video frames where the timestamp t is between 0 and 10 seconds, OR (represented by +) between 30 and 40 seconds.
    • setpts=N/FRAME_RATE/TB: This re-calculates the presentation timestamps for the selected video frames sequentially. It removes the temporal gap between the two segments, ensuring smooth playback.
  • -af "...": Applies the audio filtergraph.
    • aselect='between(t,0,10)+between(t,30,40)': Selects the audio samples corresponding to the same time segments to keep the audio in sync with the video.
    • asetpts=N/SR/TB: Resets the audio timestamps sequentially based on the sample rate (SR) and timebase (TB), matching the video timeline adjustment.

Adding More Segments

You can add as many segments as you need by appending more between(t,start,end) statements separated by the + operator.

For example, to select three segments (0-10s, 30-40s, and 60-70s), use the following syntax:

ffmpeg -i input.mp4 -vf "select='between(t,0,10)+between(t,30,40)+between(t,60,70)',setpts=N/FRAME_RATE/TB" -af "aselect='between(t,0,10)+between(t,30,40)+between(t,60,70)',asetpts=N/SR/TB" output.mp4