FFmpeg - Overlay one video onto another video?

27,329

If you just want a ffmpeg command, try

ffmpeg -i input.mov -i overlay.mov \
-filter_complex "[1:v]setpts=PTS-10/TB[a]; \
                 [0:v][a]overlay=enable=gte(t\,5):shortest=1[out]" \
-map [out] -map 0:a \
-c:v libx264 -crf 18 -pix_fmt yuv420p \
-c:a copy \
output.mov

This starts the overlay at 5 seconds with the overlaid video start point being 00:15.

setpts=PTS-10/TB is setpts=PTS+(overlay_delay-video_trim_in)/TB

overlay=enable=gte(t\,5) is overlay=enable=gte(t\,overlay_delay)

Share:
27,329
cdrev
Author by

cdrev

Developer based in London.

Updated on November 18, 2020

Comments

  • cdrev
    cdrev over 3 years

    I understand that this is a very open ended question. I have done some initial reading into FFmpeg, but now require some guidance.

    Problem

    • I have a video input.mov.
    • I would like to overlay another video on top of overlay.wov.
    • The result should be a single video (output.mov).

    Notes

    Thanks - C.

    Edits

    1. Backend is Go/Ruby. Open to using a new language.
    2. The audio from the first video should be kept.
    3. Setting the interval at which the overlay starts would be great.

    Current Solution

    ffmpeg -i input.mov -i overlay.mov -filter_complex "[0:0][1:0]overlay[out]" -shortest -map [out] -map 0:1 -pix_fmt yuv420p -c:a copy -c:v libx264 -crf 18  output.mov
    

    This nearly works, however:

    • Overlay is cut short even though the two videos (input.mov & overlay.mov) are the same length.
    • I cannot start the overlay at any interval apart from 0:00.
    • Tarunn
      Tarunn about 8 years
      what backend technology you are using? PHP, .NET, struts, python!!?
    • cdrev
      cdrev about 8 years
      @Tarunn - added answer to post.
    • cdrev
      cdrev about 8 years
      @LordNeckbeard thanks for the comment, have added quite a lot more detail and included my current solution. I believe it is different due to the audio and interval requirements.
  • cdrev
    cdrev about 8 years
    Thanks for the answer! Slightly confused by the interval. Could you explain it with these parameters if possible? input.mov is 10 secs long. overlay.mov is 3 secs long. output.mov should be 10 secs long. overlay.mov should start at 7 seconds into input.mov
  • Gyan
    Gyan about 8 years
    Overlay starts at 7, so overlay=enable=gte(t\,7). Overlay.mov is shown from its beginning, so setpts=PTS+7-0/TB == setpts=PTS+7/TB
  • gabo
    gabo over 7 years
    How about if i want to have also the audio kept in both videos? Because now when i try it, the audio from the overlay is gone. Thanks!
  • Gyan
    Gyan over 7 years
    Insert [0][1]amix[a] into the filtergraph after the overlay and change -map 0:a to -map [a]
  • Qandeel Abbassi
    Qandeel Abbassi over 5 years
    @Gyan can you please give an example of how to add this [0][1]amix[a] Is it supposed to be added in the same chain as overlay command?
  • Qandeel Abbassi
    Qandeel Abbassi over 5 years
    I got it working but i had to remove -c:a copy since copy can't be used with filters, right?
  • Tina J
    Tina J over 5 years
    @Gyan what should we change (in your command) if we want the overlay start at 0, like what OP was doing? I did gte(t\,0) and setpts=PTS+0/TB but that didn't work.
  • Basj
    Basj about 3 years
    @Gyan I have a very similar question and I have found a working solution, however it seems overly complex, if you have an idea (because you seems to be a ffmpeg guru!), it would be great :) stackoverflow.com/questions/66256414/…