3

I have a video and I'm trying to replicate some CSS filters for a video with FFMPEG.

Here is a screenshot from a video in CSS with the property filter: contrast(150%):

CSS Filtered contrast

I tried to recreate this effect in FFMPEG with the eq filter, setting contrast to 1.5

ffmpeg -y -i ./input.mp4 -vf "eq=contrast=1.5:brightness=0:saturation=1" -pix_fmt yuv420p ./filtered_input.mp4

And my output looks like this:

enter image description here

Here is an image of those two screenshots side by side:

enter image description here

You can see that the image on the left (filtered with CSS) is a little whiter / bluer if you look at the snow in between the images.

Here is a link to the original video: https://i.imgur.com/dDmp16s.mp4

I also found this comment here that discusses a relationship between contrast and saturation, but I found that there was a still a difference even if I adjusted the saturation, or even just adjusted the saturation by itself.

My meta point is that the eq filters by FFMPEG yield very different results from the corresponding CSS filters. Does anyone know why this might be happening, and how I can get them to match up?

justswim
  • 155

3 Answers3

5

My meta point is that the eq filters by FFMPEG yield very different results from the corresponding CSS filters. Does anyone know why this might be happening

There is no single consensus among all software providers of how brightness, contrast and saturation should work.

The CSS filters will have precise mathematical definitions, determined by the W3C. They need to be precise so that different browsers from different vendors can display the same rendered image. The current specification for CSS filters is here: https://www.w3.org/TR/filter-effects-1/

On the other hand, ffmpeg filters are implemented in an 'ad hoc' way by a collection of (very smart) engineers, and are not required to conform to any standard. They merely have to be useful in the view of the ffmpeg developers.

and how I can get them to match up?

I expect the only way to know exactly what an ffmpeg filter does is to read the source code (in other words, the source code is the specification). By doing that, you may be able to determine input parameters which will give you the same mathematical result as the CSS filters do. Or maybe not.

Since ffmpeg filters are not required to conform to any standard, there's a risk that a future ffmpeg update could change the result.

EDIT: Another thing to be wary of is that, even if the numerical colour values in both video files are the same, they might display differently when played. One reason is if metadata about the colour space was lost or changed during processing, so that the ffmpeg output is in a different colour space to the original video, causing the player to interpret the numerical colour values differently. Another reason is if one player supports colour space conversions that the other does not support. Based on the screenshots above, it looks like they are being viewed in different players (a browser vs something else). It would be best to view both videos in the same player.

Chungzuwalla
  • 166
  • 3
1

I know this is a very old question, but figured I would contribute back and it's still very useful. I matched up CSS filter:brightness pretty well to ffmpeg using the colorlevels filter:

For CSS brightness values between 1 - 2 (Brighter) I used: colorlevels=rimax=" + brightness + ":gimax=" + brightness + ":bimax=" + brightness where "brightness" was translated to a value of .5 - 1 in the ffmpeg filter. For CSS brightness values between 0 - 1 (Darker) I used colorlevels=romax=" + brightness + ":gomax=" + brightness + ":bomax=" + brightness where "brightness" was used directly as a value of 0 - 1

This translated very well from ffmpeg to CSS brightness filter.

0

From another thread

filter: contrast(c) saturate(s);

is equivalent to

eq=contrast=c:saturation=c*s

Not sure about the brightness parameter.

maxpaj
  • 101