How to Modulate FFmpeg Contrast Based on Time

This article explains how to dynamically adjust video contrast over time using the FFmpeg eq filter. You will learn how to write mathematical expressions using time-based variables, understand the syntax requirements, and explore practical examples such as creating pulsating contrast effects or gradual transitions.

Understanding the FFmpeg eq Filter

The FFmpeg eq (equalizer) filter is used to adjust video brightness, contrast, saturation, and gamma. Most of these parameters accept expressions that are evaluated for each frame.

To modulate contrast based on the current time of the video, you must use the contrast parameter in conjunction with the t variable, which represents the current timestamp of the frame in seconds.

Key Variables for Time-Based Equations

  • t: The current time in seconds (e.g., 1.5 for one and a half seconds).
  • n: The frame number, starting from 0.
  • pos: The position in the input file in bytes.

Syntax for Modulating Contrast

The default contrast value is 1.0. A value of 0.0 results in a completely gray image, while values greater than 1.0 increase the contrast.

To apply a time-based equation, define the expression inside single quotes within the eq filter:

-vf "eq=contrast='EXPRESSION'"

Practical Examples

1. Pulsating Contrast (Sine Wave Modulation)

To make the contrast rise and fall continuously like a wave, you can use the sin() function.

The following command oscillates the contrast between 0.5 and 1.5 every few seconds:

ffmpeg -i input.mp4 -vf "eq=contrast='1.0+0.5*sin(2*PI*0.5*t)'" -c:a copy output.mp4
  • 1.0: The baseline contrast.
  • 0.5: The amplitude (how much the contrast deviates from the baseline).
  • sin(2*PI*0.5*t): Creates a smooth wave. The 0.5 inside the sine function represents the frequency in Hertz (one full cycle every 2 seconds).

2. Gradual Contrast Fade-In (Linear Increase)

To gradually increase the contrast from 0.0 (flat gray) to 1.5 over the first 5 seconds of the video, you can use a linear equation combined with the clip() function to cap the maximum value.

ffmpeg -i input.mp4 -vf "eq=contrast='clip(0.3*t, 0.0, 1.5)'" -c:a copy output.mp4
  • 0.3*t: Increases the contrast by 0.3 every second.
  • clip(val, min, max): Keeps the evaluated value within the range of 0.0 and 1.5 so the video does not become overly distorted after 5 seconds.

3. Contrast Flash Effect (Sudden Spike)

If you want to create a periodic flash effect where the contrast suddenly spikes and decays, you can combine the absolute value of a cosine wave or use exponential decay.

ffmpeg -i input.mp4 -vf "eq=contrast='1.0+2.0*exp(-mod(t,2))'" -c:a copy output.mp4
  • mod(t,2): Resets the timer to 0 every 2 seconds.
  • exp(-mod(t,2)): Creates a sharp spike that rapidly decays, resulting in a camera flash effect every 2 seconds.