How to Use FFmpeg Split Filter for Multiple Outputs

In this article, you will learn how to use the FFmpeg split filter to duplicate a single video stream and route it to multiple filter chains simultaneously. We will cover the basic syntax of the split filter, explain how stream labeling works, and provide a practical, step-by-step example of applying different visual effects to the duplicated streams within a single command.

Understanding the Split Filter Syntax

The split filter takes a single video input and duplicates it into two or more identical output streams. This is highly efficient because FFmpeg only decodes the source video once before processing the multiple paths. For audio streams, the equivalent filter is asplit.

The basic anatomy of the split filter within a -filter_complex graph looks like this:

[input_stream] split=N [output_stream_1][output_stream_2]...[output_stream_N]
  • [input_stream]: The label of the incoming video stream (e.g., [0:v] for the video track of the first input file).
  • split=N: The filter name followed by the number of desired duplicates (\(N\)). If you omit =N, it defaults to 2.
  • [output_stream_1][output_stream_2]: The custom temporary labels you assign to each duplicated output stream. You will reference these labels in subsequent filter chains.

Practical Example: Scaling and Applying Effects

Suppose you want to take a single input video, duplicate it, and perform two different tasks:

  1. Resize the first stream to 720p.
  2. Apply a vintage vignette effect to the second stream.

Here is the FFmpeg command to achieve this:

ffmpeg -i input.mp4 -filter_complex \
"[0:v] split=2 [stream1][stream2]; \
 [stream1] scale=1280:720 [scaled_video]; \
 [stream2] vignette=PI/4 [vignette_video]" \
-map "[scaled_video]" output_720p.mp4 \
-map "[vignette_video]" output_vignette.mp4

Command Breakdown

  • -i input.mp4: Defines the source video file.
  • -filter_complex: Initiates the complex filtergraph, which is required when using filters with multiple inputs or outputs.
  • [0:v] split=2 [stream1][stream2]: Takes the first input video stream ([0:v]) and splits it into two identical streams, labeling them [stream1] and [stream2].
  • ;: The semicolon separates different filter chains within the filtergraph.
  • [stream1] scale=1280:720 [scaled_video]: Feeds the first split stream into the scale filter and labels the output [scaled_video].
  • [stream2] vignette=PI/4 [vignette_video]: Feeds the second split stream into the vignette filter and labels the output [vignette_video].
  • -map "[scaled_video]" output_720p.mp4: Maps the scaled stream to the first output file.
  • -map "[vignette_video]" output_vignette.mp4: Maps the vignetted stream to the second output file.

By using this approach, you can chain as many filters as needed to any of the split outputs, allowing for highly complex, single-pass video processing workflows.