How to add additional key frames to video using ffmpeg?

9,164

Solution 1

force_key_frames has an option to mirror source stream's keyframe cadence (as yet undocumented - on my todo), however this can't be combined with other expressions in f_k_f.

However, what you can use, is

-force_key_frames source -x264-params keyint=20:scenecut=0

This will set a keyframe if the source frame was a keyframe. However keyint is always measured from the last keyframe set, so if your source had KFs at n=0,34,55,64 then result will have KFs at n=0,20,34,54,55,64,84 - note the lack of KFs at 40,60,80. Also note the consecutive KFs at 54,55, so it's best to ignore the source KFs and let scenecut work.

Solution 2

Short answer: You can't

Long answer: When using FFMpeg with reencoding (i.e. any other codec than copy), every single image in the input stream will be decompressed and available as a full bitmap. This implies, that at this point in the pipeline, frames 1, 12 and 89 are no longer "special" - they are images like any other.

When now compressing via libx264, you create a video that has key frames - these will be put at the places you configure, in you case every 20 frames.

Share:
9,164
jjulianf
Author by

jjulianf

Updated on September 18, 2022

Comments

  • jjulianf
    jjulianf over 1 year

    I want to add key frames on the base of a specific interval (20 frames) to my video.

    Therefore I used the following command in ffmpeg:

    ffmpeg -i <input> -vcodec libx264 -x264-params keyint=20:scenecut=0 -acodec copy out.mp4
    

    Output is, that I get key frames every 20 frames.

    But the original video had a key frame e.g. at frame 1, 12, 89....

    Now I have key frames at frame 1, 21, 41....

    I don't want to replace the key frames which were already there. I want to add additional key frames, so it looks like this:

    frame 1, 12, 21, 41, 89....
    

    How can I do this?

  • jjulianf
    jjulianf over 5 years
    That seems to make sense, thanks for your answer! But what happens, when I have a complete scene change between frame 11 and 12 and I only get keyframes at frame 1, 21, ... ? Don't I need a keyframe at frame 12 in that case?
  • jjulianf
    jjulianf over 5 years
    But I could add the previous keyframes by hand afterwards, using force_key_frame, right?
  • Eugen Rieck
    Eugen Rieck over 5 years
    Why then use scencut=0 ? Let scencut do its magic!
  • slhck
    slhck over 5 years
    @jjulianf It seems you need to rewrite your question to ask about the actual problem you're having, not what you think the solution is. (See xyproblem.info) Do you need regular intervals for streaming purposes?
  • Gyan
    Gyan over 5 years
    Note: scenecut value doesn't represent the delta measurement between adjoining frames. scenecut also takes into consideration the distance from the last keyframe, so with a low keyint value, scenecut may never be triggered unless the latter is set very high.
  • jjulianf
    jjulianf over 5 years
    Thanks, it's good to know about this option! But it's not exactly what I wanted since I need the key frames at the exact frames. But still, interesting option!
  • Gyan
    Gyan over 5 years
    -force_key_frames source, as it says, sets the key frames at the exact frames.
  • jjulianf
    jjulianf over 5 years
    I thought that I woul still need the original keyframes. Thought that the video would run stuttery or something like that when a scene completly changes and the original keyframes are not there anymore. But it turned out that it still plays very well somehow.. :-)
  • jjulianf
    jjulianf over 5 years
    Yes, but I mean n=0, 20, 34, 40, 55, 60, 64, 80... . But as I said in the upper comment, the video still plays great with my initial solution.
  • Gyan
    Gyan over 5 years
    That's due to your keyint=20. If you set it to a very large value (9999), source KFs will be exactly replicated.