User Tools

Site Tools


ffmpeg

Differences

This shows you the differences between two versions of the page.

Link to this comparison view

Both sides previous revision Previous revision
Next revision
Previous revision
ffmpeg [2020/03/13 15:30]
sdbs add streaming portion
ffmpeg [2021/12/11 23:21] (current)
sdbs improve commando
Line 8: Line 8:
 If you're on Windows, it's technically possible to install ''ffmpeg'' and use it directly ((from https://ffmpeg.zeranoe.com/builds/)), but since the windows Command Prompt sucks ass comfort-wise and scripting-wise, it's recommended to just [[https://docs.microsoft.com/en-us/windows/wsl/install-win10|install Ubuntu as part of the Windows Subsystem for Linux]], and then ''apt-get install ffmpeg''. If you're on Windows, it's technically possible to install ''ffmpeg'' and use it directly ((from https://ffmpeg.zeranoe.com/builds/)), but since the windows Command Prompt sucks ass comfort-wise and scripting-wise, it's recommended to just [[https://docs.microsoft.com/en-us/windows/wsl/install-win10|install Ubuntu as part of the Windows Subsystem for Linux]], and then ''apt-get install ffmpeg''.
  
-If you're on Linux, you know what to do 8-)+If you're on Linux, you already know what to do 8-)
  
 ===== Techniques ===== ===== Techniques =====
Line 16: Line 16:
 ==== Basic conversions ==== ==== Basic conversions ====
  
-''fffmpeg'' is pretty clever, it can correctly guess the codecs and reasonable default settings by the file extension, so all of the following will work as expected (and retain metadata((like ID3 tags and their FLAC, OGG, WAV, etc. equivalents))!):+''ffmpeg'' is pretty clever, it can correctly guess the codecs and reasonable default settings by the file extension, so all of the following will work as expected (and retain metadata((like ID3 tags and their FLAC, OGG, WAV, etc. equivalents))!):
  
 <code bash> <code bash>
Line 60: Line 60:
  
 <code bash> <code bash>
-ls *.jpg | xargs -I xyz echo "file 'xyz'" > list.txt+ls -1 | grep 'jpg$' | xargs -I xyz echo "file 'xyz'" > list.txt
 </code> </code>
  
Line 67: Line 67:
 </code> </code>
  
-It's up to preference, all end up with a list of all JPGs in current directory, in ''list.txt''.+It's up to preference, all end up with a list of all JPGs in current directory, in ''list.txt''(Though the first command can handle a bit more files.)
  
 == 2. list to video == == 2. list to video ==
Line 102: Line 102:
 ffmpeg -i "https://example.com/playlist.m3u8" -vframes 1 capture.jpg ffmpeg -i "https://example.com/playlist.m3u8" -vframes 1 capture.jpg
 </code> </code>
 +
 +
 +==== dropped frame re-interpolation ====
 +
 +''ffmpeg'' also has a [[https://ffmpeg.org/ffmpeg-filters.html|rich set of filters]], two of which are of interest for us now:
 +
 +  * [[https://ffmpeg.org/ffmpeg-filters.html#mpdecimate|mpdecimate]] - //Drop frames that do not differ greatly from the previous frame in order to reduce frame rate.//
 +  * [[https://ffmpeg.org/ffmpeg-filters.html#minterpolate|minterpolate]] - //Convert the video to specified frame rate using motion interpolation.//
 +
 +The idea is that ''mpdecimate'' drops all near-duplicate frames, and ''minterpolate'' re-calculates them using non-duplicate frames that were left.
 +
 +''mpdecimate'''s defaults are pretty okay, but the result may not look too good if the frame drops are frequent and long. I've had pretty good results using its ''max'' parameter which limits the amount of frames dropped in a single stretch of video, e.g. ''-vf mpdecimate=max=15'' which drops at most 15 frames (i.e. half a second assuming 30 FPS), meaning interpolation won't happen everywhere and the video will remain faithfully choppy.
 +
 +''minterpolate'', on the other hand, defaults to semi-smart motion compensated interpolation, and that //might// just be what you want, but it generally gives pretty funky results. Fortunately, it also has a "blend" mode, which just averages the start and end frames and crossfades them, which gives much more agreeable outputs for simple frame drop situations. It is also generally much faster, I was getting near or above real-time speeds using "blend", whereas motion compensation dropped the processing speed to 0.01x.
 +
 +**TL;DR**: Full command(s) including the filter pipeline:
 +
 +<code bash>
 +# Fill out all frame drop gaps
 +ffmpeg -i choppy_video.mp4 -vf mpdecimate,minterpolate=mi_mode=blend smoother_video.mp4
 +
 +# Fill out all frame drop gaps no longer than 10 frames:
 +ffmpeg -i choppy_video.mp4 -vf mpdecimate=max=10,minterpolate=mi_mode=blend smoother_video.mp4
 +
 +# Motion interpolate the gaps and replicate a bad ketamine trip
 +ffmpeg -i choppy_video.mp4 -vf mpdecimate,minterpolate smoother_video.mp4
 +</code>
 +
 +ffmpeg - skipping - remove duplicate frames after effects
 +
 +=== what is `N/FRAME_RATE/TB` ===
 +
 +  *  except the use of `FRAME_RATE` variable the `N/FRAME_RATE/TB` is equal to the example below from ffmpeg documentation ([source](https://ffmpeg.org/ffmpeg-filters.html#Examples-123))
 +  * 
 +<code>    
 +    > Set fixed rate of 25 frames per second:  
 +    > `setpts=N/(25*TB)`
 +</code>    
 +
 +  *   the math behind it perfectly explained in What is video timescale, timebase, or timestamp in ffmpeg? 
 +       it basically calculates timestamp for each frame and multiplies it with timebase `TB` to enhance precision
 +
 +==== mp4 compatibility ====
 +
 +h264 also has "profiles", basically [[https://en.wikipedia.org/wiki/Advanced_Video_Coding#Profiles|sets of features]] - and it turns out this can make the difference between a file working and not working on some crappy embedded media players, like TVs or pico projectors.
 +
 +>>The ''-profile:v'' option limits the output to a specific H.264 profile. Some devices (mostly very old or obsolete) only support the more limited Constrained Baseline or Main profiles. You can set these profiles with ''-profile:v baseline'' or ''-profile:v main''.
 +>https://trac.ffmpeg.org/wiki/Encode/H.264#Profile
 +
 +<code bash>
 +ffmpeg -i original.mp4 -profile:v baseline output.mp4
 +</code>
 +
 +And apparently, some players are also sensitive to the pixel format((https://trac.ffmpeg.org/wiki/Encode/H.264#Encodingfordumbplayers)), i.e. can't handle anything else than YUV w/ 4:2:0 chroma subsampling, to fix this use the ''-pix_fmt'' option as follows:
 +
 +<code bash>
 +ffmpeg -i original.mp4 -pix_fmt yuv420p output.mp4
 +# or, with the profile settings...
 +ffmpeg -i original.mp4 -profile:v baseline -pix_fmt yuv420p output.mp4
 +</code>
 +
 +
 +No silver bullet, you'll just have to try different things for different devices. A database of crappy players and appropriate ''ffmpeg'' settings would be great.
 +
 +
 +==== random ====
 +
 +https://ottverse.com/ffmpeg-drawtext-filter-dynamic-overlays-timecode-scrolling-text-credits/
 +
 +===== Other cheatsheets =====
 +  * [[https://gist.github.com/steven2358/ba153c642fe2bb1e47485962df07c730|FFmpeg cheat sheet]]
 +  * [[https://devhints.io/ffmpeg]]
 +  * [[https://gist.github.com/nickkraakman/e351f3c917ab1991b7c9339e10578049|FFmpeg Cheat Sheet for 360º video]]
ffmpeg.1584109844.txt.gz · Last modified: 2020/03/13 15:30 by sdbs