Versions Compared

Key

  • This line was added.
  • This line was removed.
  • Formatting was changed.

FFmpeg is frequently used by different studios for encoding their media, however the documentation for ffmpeg is often poor, or cryptic so its often harder than it should be to come up with a good starting point. We are aiming to come up with recommendations for different scenarios as well as document what the different flags are doing with the aim to make this easier to get to a good baseline.

Table of Contents

Overview

We are looking for recommendations for the following:

  • Best color preservation for output to:
    • Web, OSX, IOS and Windows.
    • Common applications: e.g. RV, Nuke.
    • Rec709 and sRGB displays to start with, but eventually, P3, rec2020 and HDR displays.
    • Web browser - Firefox reviewing mp4. - use firefox plugin.
    • RV
  • Codec recommendations for:
    • Proxy H264 playback (e.g. web streaming), should be setup for web streaming.
    • Animation/Modelling/Layout movie playback. - somewhat lower quality playback, but should always provide smooth motion.
    • Lookdev/lighting/compositing movie playback - should have excellent color fidelity and minimal encoding artifacts
      • Should any filmlook be baked in, or should we assume that is always applied during viewing.
      • How much should we be able to adjust color and have the image hold up? (Or rely on exr's for that?).
    • Export to editorial.
    • High-resolution or frame rate - e.g. 4k, 8k, 60fps, 120fps.
    • Stereo or VR.
  • Q: Which container should we be considering: mov, mp4, mxf.

Where ffmpeg arguments, it would be great to document why we are using them, rather than ending up with a recipe. 

View file
nameFFMPEG defaults.pdf
height250

Overall workflow

For this paper, we are assuming that we are encoding from a file-sequence of frames into a movie (rather than re-encoding a movie), but we are also assuming almost all of the colorspace work would be done outside of ffmpeg, with tools using the OCIO library. Examples could include nuke and oiio. Once we get to ffmpeg, the goal being that the pixel data we get in, should be as close as possible to the data we get out of ffmpeg. However, there are still quite a few areas that a ffmpeg user could go wrong, which we break down below. 

TODO: Find examples of overall workflow. 

Codec Selection.

...

DnxHD

...

-pix_fmt yuv422p10le -c:v prores_ks -profile:v 3 -vendor ap10 -sws_flags spline+accurate_rnd+full_chroma_int -vf "colorspace=bt709:iall=bt601-6-625:fast=1" -color_range 1 -colorspace 1 -color_primaries 1 -color_trc 1

...

Note the -vendor ap10 part below is only needed if working with Final Cut, but it does no harm otherwise.

-profile:v 3 is equivalent to -profile:v hq

h264

Key flags (see https://trac.ffmpeg.org/wiki/Encode/H.264 ) 

-preset slow -crf 18   level 4 profile high.

RV - 10bit YUV444.

Better to stick with yuv – 

FFMPEG.

TODO:

  • Suggestions for max-bitrate?
  • Suggestions for preset - ? slow
  • Suggestions for tune

h265/HVEC

Support: https://caniuse.com/hevc (or https://www.chromium.org/audio-video ) currently no support for h265 on chrome or chromium based browsers.

links:

...

FFmpeg is frequently used by different studios for encoding their media, however the documentation for ffmpeg is often poor, or cryptic so its often harder than it should be to come up with a good starting point. We are aiming to come up with recommendations for different scenarios as well as document what the different flags are doing with the aim to make this easier to get to a good baseline.


Table of Contents

Overview

We are looking for recommendations for the following:

  • Best color preservation for output to:
    • Web, OSX, IOS and Windows.
    • Common applications: e.g. RV, Nuke.
    • Rec709 and sRGB displays to start with, but eventually, P3, rec2020 and HDR displays.
    • Web browser - Firefox reviewing mp4. - use firefox plugin.
    • RV
  • Codec recommendations for:
    • Proxy H264 playback (e.g. web streaming), should be setup for web streaming.
    • Animation/Modelling/Layout movie playback. - somewhat lower quality playback, but should always provide smooth motion.
    • Lookdev/lighting/compositing movie playback - should have excellent color fidelity and minimal encoding artifacts
      • Should any filmlook be baked in, or should we assume that is always applied during viewing.
      • How much should we be able to adjust color and have the image hold up? (Or rely on exr's for that?).
    • Export to editorial.
    • High-resolution or frame rate - e.g. 4k, 8k, 60fps, 120fps.
    • Stereo or VR.
  • Q: Which container should we be considering: mov, mp4, mxf.

Where ffmpeg arguments, it would be great to document why we are using them, rather than ending up with a recipe. 

View file
nameFFMPEG defaults.pdf
height250

Overall workflow

For this paper, we are assuming that we are encoding from a file-sequence of frames into a movie (rather than re-encoding a movie), but we are also assuming almost all of the colorspace work would be done outside of ffmpeg, with tools using the OCIO library. Examples could include nuke and oiio. Once we get to ffmpeg, the goal being that the pixel data we get in, should be as close as possible to the data we get out of ffmpeg. However, there are still quite a few areas that a ffmpeg user could go wrong, which we break down below. 

TODO: Find examples of overall workflow. 

Codec Selection.


NameTarget UsageSourceffmpeg flagsDescriptionSize
libx264 -pix_fmt yuv420pProxy playback, for web review, and non-color critical workflows, e.g. animation, modeling, etc.

This should be a lightweight compression, capable of supporting HD with a reasonable bit-rate, hopefully supporting a wide range of web browsers.
Final review, e.g. lighting

libx264 -pix_fmt yuv444p10leFinal review, e.g. lightinghttps://trac.ffmpeg.org/wiki/colorspace-c:v libx264 -preset placebo -qp 0 -x264-params "keyint=15:no-deblock=1" -pix_fmt yuv444p10le -sws_flags spline+accurate_rnd+full_chroma_int -vf "colorspace=bt709:iall=bt601-6-625:fast=1" -color_range 1 -colorspace 1 -color_primaries 1 -color_trc 1

libx264rgbFinal review, e.g. lighting

This is a variant of the above, its essentially using x264, but not converting to YCrCb.
libx265

-c:v libx264

Prores 4444For delivery to editorial
-c:v prores_ks -profile:v 4444 -qscale:v 1 -pix_fmt yuv444p10le -sws_flags spline+accurate_rnd+full_chroma_int -vf "colorspace=bt709:iall=bt601-6-625:fast=1" -color_range 1 -colorspace 1 -color_primaries 1 -color_trc 1

-profile:v 4444 is equivalent to -profile:v 4
shotgun_diy_encode
https://support.shotgunsoftware.com/hc/en-us/articles/219030418-Do-it-yourself-DIY-transcoding',-vcodec libx264 -pix_fmt yuv420p -g 30 -vprofile high -bf 0 -crf 2

DnxHDFor delivery to editorial



Prores 422 HQFor delivery to editorialSome FFMpeg commands I need to remember for converting footage for video editing. http://bit.ly/vidsnippets · GitHub

-pix_fmt yuv422p10le -c:v prores_ks -profile:v 3 -vendor ap10 -sws_flags spline+accurate_rnd+full_chroma_int -vf "colorspace=bt709:iall=bt601-6-625:fast=1" -color_range 1 -colorspace 1 -color_primaries 1 -color_trc 1



Note the -vendor ap10 part below is only needed if working with Final Cut, but it does no harm otherwise.

-profile:v 3 is equivalent to -profile:v hq

h264

Key flags (see https://trac.ffmpeg.org/wiki/Encode/H.264 ) 

-preset slow -crf 18   level 4 profile high.

RV - 10bit YUV444.

Better to stick with yuv – 

FFMPEG.

TODO:

  • Suggestions for max-bitrate?
  • Suggestions for preset - ? slow
  • Suggestions for tune

h265/HVEC

Support: https://caniuse.com/hevc (or https://www.chromium.org/audio-video ) currently no support for h265 on chrome or chromium based browsers.

links:

HDR

ProRes

There are four Prores encoders, Prores, Prores_ks, Prores_aw and now with ffmpeg 5 VideoToolBox Prores, which is a hardware based OSX M1 encoder/decoder. 

From https://trac.ffmpeg.org/wiki/Encode/VFX the recommendation is to use Prores_ks with -profile:v 3 and the qscale of 11

Options that can be used include:

  • -profile:v values can be one of.
    • proxy (0)
    • lt (1)
    • standard (2)
    • hq (3)
    • 4444 (4)
    • 4444xq (5)
  • -qscale:v between values of 9 - 13 give a good result, 0 being best.
  • -vendor apl0 - tricks the codec into believing its from an Apple codec.

Using this with the usual color space flags, seems to work well with the exception of ffmpeg itself, which needs the flags:-vf scale=in_color_matrix=bt709:out_color_matrix=bt709 added to the command to ensure the right input colorspace is recognised, e.g.:

ffmpeg.exe -i INPUTFILE.mov -compression_level 10 -pred mixed -pix_fmt rgba64be -sws_flags spline+accurate_rnd+full_chroma_int -vframes 1 -vf scale=in_color_matrix=bt709:out_color_matrix=bt709 OUTPUTFILE.png


However, other encoders seem to be recognised correctly, so there is clearly some metadata missing. I did try using the prores_metadata filter to try adding some additional parameters, but it didnt seem to help.

ffmpeg.exe -i ./chip-chart-yuvconvert\basicnclc.mov -c copy -bsf:v prores_metadata=color_primaries=bt709:color_trc=bt709:colorspace=bt709 chip-chart-yuvconvert\basicnclcmetadata.mov

TODO:

  • Figure out the missing metadata.
  • Wedge qscale values
  • Do some colorspace tests with different qscale values to see where color breaks down.

VMAF

I did explore using VMAF - Video Multi-Method Assessment Fusion as a way to quantify the compression, the notes for setting this up are below, however I think we are going with a fairly high compression factor , so I think this is probably not really going to help us much.

...

Q: Currently focusing just on color matching in vs. out, but should also do EXR ACEScg in to resulting movie. Feels like we should also bless full pipeline, e.g.: Reference  Reference "Dailies script" https://github.com/jedypod/generate-dailies

Test Sources

SMPTE test chart: https://commons.wikimedia.org/wiki/File:SMPTE_Color_Bars_16x9.svg 

...

Explore netflix: https://opencontent.netflix.com/

Test Results:

taurich.org/encodingTests/results.html

Links

Notes

The big issue here is that by default if you start converting images to another format, and  and ffmpeg cannot determine the colorspace  colorspace  it will default to bt601. So many of the flags below are to:

...

C: Do as clean a conversion from RGB to YUV as possible.

RGB/YCrCb Colorspace Conversion  

As a rule of thumb, we would like ffmpeg to do as little as possible in terms of color space conversion. i.e. what comes in goes out. The problem is that most of the codecs are doing some sort of RGB to YUV conversion (technically YCrCb). The notable exception is x264rgb (see above). For more information, see: https://trac.ffmpeg.org/wiki/colorspace 

For examples comparing these see: https://richardssam.github.io/ffmpeg-tests/tests/chip-chart-yuvconvert/compare.html

colormatrix filter

ffmpeg -y -i ../sourceimages/chip-chart-1080-noicc.png -sws_flags spline+accurate_rnd+full_chroma_int -vf "colormatrix=bt470bg:bt709" -c:v libx264 -preset placebo -qp 0 -x264-params "keyint=15:no-deblock=1" -pix_fmt yuv444p10le -qscale:v 1 -color_range 1 -colorspace 1 -color_primaries 1 -color_trc 1 ./chip-chart-yuvconvert/spline444colormatrix2.mp4

This is the most basic colorspace filtering. bt470bg is essentially part of the bt601 spec.  See: https://www.ffmpeg.org/ffmpeg-filters.html#colormatrix

colorspace filter

ffmpeg -y -i ../sourceimages/chip-chart-1080-noicc.png -sws_flags spline+accurate_rnd+full_chroma_int -vf "colorspace=bt709:iall=bt601-6-625:fast=1" -c:v libx264 -preset placebo -qp 0 -x264-params "keyint=15:no-deblock=1" -pix_fmt yuv444p10le -qscale:v 1 -color_range 1 -colorspace 1 -color_primaries 1 -color_trc 1 ./chip-chart-yuvconvert/spline444colorspace.mp4

Using colorspace filter, better quality filter, SIMD so faster too, can support 10-bit too.  The second part -vf "colorspace=bt709:iall=bt601-6-625:fast=1" encodes for the output being bt709, rather than the default bt601 matrix. iall=bt601-6-625 says to treat all the input (colorspace, primaries and transfer function) with the bt601-6-625 label). fast=1 skips gamma/primary conversion in a mathematically correct way.  See:  https://ffmpeg.org/ffmpeg-filters.html#colorspace

libswscale filter

ffmpeg -y -i ../sourceimages/chip-chart-1080-noicc.png -sws_flags spline+accurate_rnd+full_chroma_int+full_chroma_inp -vf "scale=in_range=full:in_color_matrix=bt709:out_range=tv:out_color_matrix=bt709" -c:v libx264 -preset placebo -qp 0 -x264-params "keyint=15:no-deblock=1" -pix_fmt yuv444p10le -qscale:v 1 -color_range 1 -colorspace 1 -color_primaries 1 -color_trc 1 ./chip-chart-yuvconvert/spline444out_color_matrix.mp4

Using the libswscale library. Seems similar to colorspace, but with image resizing, and levels built in.  resizing, and levels built in.  https://www.ffmpeg.org/ffmpeg-filters.html#scale-1

This is the recommended filter.

Color Metadata NCLC/NCLX

The above gets the underlying data stored correctly, but there are additional metadata flags that can be set that are interpreted by some players, these are the NCLC color tags for color primaries, transfer function and conversion matrix.  This is defined as a ISO spec here (see https://www.ffmpegiso.org/ffmpeg-filters.html#scale-1

This is the recommended filter.

Color Metadata NCLC

The above gets the underlying data stored correctly, but there are additional metadata flags that can be set that are interpreted by some players, these are the NCLC color tags for color primaries, transfer function and conversion matrix.  This is defined as a ISO spec here (see https://www.iso.org/standard/73412.html). The numbers below are part of the definition.standard/73412.html). The numbers below are part of the definition.

NCLC stands for Non-Consistent Luminance Coding, a brief overview of its history is here. For MP4 files, its also known as NCLX. Additionally this metadata can also be represented in the h264 metadata stream in the video usability Information (VUI) block. 

You can read the metadata using mp4box.js which is a visual browser of the mp4 metadata, and look at moov/trak/mdia/minf/stbl/stsd/avc1/colr

NOTE: None of the flags below affect the encoding of the source imagery, they are meant to be used to guide how the mp4 file is decoded.

...

bt2020
Numeric ValueString ValuesDescription1bt7099
1bt709
9bt2020
11
DCI P3
12
P3 D65 / Display P3


Multimedia
nameScreen Recording 2022-02-28 at 8.02.05 PM.mov


Color Transfer Characteristic aka color_trc

...

Numeric ValueString ValuesDescription
1bt709Note this is the camera gamma i.e. ~1.95 this is NOT bt1886
2
Image characteristics are unknown or are determined by the
application.
4gamma22
5gamma28
8linearLinear
9

log

log100


13iec61966_2_1IEC 61966-2-1 or sRGB or sYCC
14

bt2020_10

bt2020_10bit

Note this is the camera gamma i.e. ~1.95 
15

bt2020_12

bt2020_12bit

Note this is the camera gamma i.e. ~1.95 
16smpte2084bt2100-1 perceptual quantization (PQ) system.
17smpte428SMPTE ST 428-1 - DCI  ?
18arib-std-b67ARIB STD-B67 bg2100-1 hybrid log-gamma (HLG) system



NOTE: -color_trc 1 - is not bt1886, but is actually the camera gamma, so has a gamma of ~1.95 rather than the 2.4 that is defined by bt1886. In order to get a gamma 2.4, you will need to use a quicktime hack (see below), but this only works on OSX. However, we suspect that chrome ignores the setting (see the following tests).

...