Configure libx265 for Lowest Latency in FFmpeg
Achieving real-time, low-latency video streaming using the HEVC/H.265
codec requires specific tuning of the FFmpeg encoder. This article
provides a direct, step-by-step guide on how to configure the
libx265 encoder to minimize latency, highlighting the
critical parameters, presets, and flags needed to eliminate frame
buffering and encoding delays.
The Core Low-Latency Command
To achieve the lowest possible latency with libx265, you
must disable B-frames, lookahead buffers, and frame reordering. Below is
the optimized FFmpeg command template for ultra-low latency
streaming:
ffmpeg -i input.mp4 -c:v libx265 -preset ultrafast -tune zerolatency -x265-params keyint=30:bframes=0:rc-lookahead=0:sliced-threads=1 -c:a copy output.m3u8Key Parameter Breakdown
To customize this configuration for your specific use case, understand how each parameter impacts latency:
1. The Zero Latency
Tune (-tune zerolatency)
This is the most critical setting. Applying
-tune zerolatency instructs the encoder to immediately
output packets as soon as they are processed, rather than buffering them
to optimize compression. It automatically disables features that
introduce delay, such as frame-lookahead.
2. Encoder Preset
(-preset ultrafast)
Encoding speed directly impacts latency. Using
-preset ultrafast or -preset superfast ensures
the CPU processes frames as quickly as possible. While faster presets
result in slightly larger file sizes for the same quality, they
drastically reduce pipeline delay.
3. Disabling B-Frames
(bframes=0)
B-frames (bi-directional predictive frames) require the encoder to
look ahead at future frames before encoding the current one. This
introduces a mandatory delay equal to the B-frame buffer size. Setting
bframes=0 via -x265-params ensures zero frame
reordering delay.
4. Eliminating Lookahead
(rc-lookahead=0)
By default, libx265 analyzes upcoming frames to plan
rate control (bitrate distribution). Setting rc-lookahead=0
inside -x265-params disables this buffer, forcing the
encoder to make rate control decisions on a frame-by-frame basis
instantly.
5. Sliced Threading
(sliced-threads=1)
Standard frame-based multithreading introduces latency because
multiple frames must be buffered to be distributed across CPU threads.
Enabling sliced-threads=1 forces the encoder to parallelize
the encoding of a single frame across multiple CPU cores simultaneously,
reducing per-frame processing time without adding buffer delay.
6. Low GOP/Keyframe Interval
(keyint)
A shorter intra-frame interval (GOP size) allows players to start
decoding the stream faster upon connection. For low-latency streaming,
set the keyframe interval to match your frame rate or double your frame
rate (e.g., keyint=30 or keyint=60 for a 30fps
stream).