DEV Community

Alex Shev
Alex Shev

Posted on

8 FFmpeg Recipes I Use Every Week (That Most Developers Don't Know Exist)

I've been using FFmpeg almost every day for the past year.

Mostly for boring real work: cutting Shorts, cleaning voice tracks, exporting web versions, generating thumbnails, and fixing weird media issues at the last minute when something breaks five minutes before publish.

Most FFmpeg tutorials cover the basics and stop there. These are the commands I actually come back to in production.

Here are 8 recipes I use constantly. Copy-paste ready.


1. Extract Audio from Video (and Clean It Up)

# Extract audio only
ffmpeg -i video.mp4 -vn -acodec libmp3lame -q:a 2 audio.mp3

# Extract + normalize loudness to broadcast standard
ffmpeg -i video.mp4 -vn -af "loudnorm=I=-16:TP=-1.5:LRA=11" -ar 44100 clean_audio.mp3
Enter fullscreen mode Exit fullscreen mode

When I use it: Podcast edits, voiceover cleanup, and those annoying cases where a track sounds fine in headphones but way too quiet after upload. The loudnorm filter saved me from re-exporting more than once.


2. Create a GIF from a Video Clip (That Doesn't Look Terrible)

Most GIF conversions look like they were made in 2004. The trick is a two-pass approach with a custom palette.

# Generate optimized palette first
ffmpeg -ss 00:00:05 -t 3 -i video.mp4 \
    -vf "fps=15,scale=480:-1:flags=lanczos,palettegen" \
    palette.png

# Then use that palette for the GIF
ffmpeg -ss 00:00:05 -t 3 -i video.mp4 -i palette.png \
    -filter_complex "fps=15,scale=480:-1:flags=lanczos[x];[x][1:v]paletteuse" \
    output.gif

# Cleanup
rm palette.png
Enter fullscreen mode Exit fullscreen mode

Why it matters: Single-pass GIFs use a generic 256-color palette. The two-pass method generates a palette optimized for your specific clip.

I learned this the hard way after making a product GIF that looked fine in preview and terrible after export. Washed-out gradients, ugly banding, weird skin tones. Two-pass fixed it immediately.


3. Batch Convert an Entire Folder

# Convert all MKV files to MP4 (preserving quality)
for f in *.mkv; do
    ffmpeg -i "$f" -c:v libx264 -crf 18 -c:a aac "${f%.mkv}.mp4"
done

# Convert all WAV to MP3 at 192kbps
for f in *.wav; do
    ffmpeg -i "$f" -codec:a libmp3lame -b:a 192k "${f%.wav}.mp3"
done
Enter fullscreen mode Exit fullscreen mode

The pattern: ${f%.ext} strips the original extension. This is bash string manipulation, not FFmpeg — but it's the glue that makes FFmpeg scriptable.

This one saved me the most time in practice. Converting one file is nothing. Converting 40 files before lunch is where FFmpeg starts earning its keep.


4. Split a Video into Equal Chunks

Perfect for breaking long recordings into social-media-sized pieces.

# Split into 60-second chunks
ffmpeg -i long_video.mp4 -c copy -map 0 \
    -segment_time 60 -f segment \
    -reset_timestamps 1 \
    chunk_%03d.mp4
Enter fullscreen mode Exit fullscreen mode

Output: chunk_000.mp4, chunk_001.mp4, chunk_002.mp4, etc.

The -c copy flag means no re-encoding — it's almost instant regardless of file size. The split happens at keyframes, so chunks might be slightly longer or shorter than 60 seconds.


5. Add Subtitles (Burned In)

# From an SRT file
ffmpeg -i video.mp4 -vf "subtitles=captions.srt:force_style='FontSize=24,FontName=Arial,PrimaryColour=&HFFFFFF,OutlineColour=&H000000,Outline=2'" output.mp4

# Quick one-liner subtitle (no SRT file needed)
ffmpeg -i video.mp4 -vf "drawtext=text='Hello World':fontsize=36:fontcolor=white:x=(w-text_w)/2:y=h-th-40:box=1:boxcolor=black@0.6:boxborderw=8" output.mp4
Enter fullscreen mode Exit fullscreen mode

Pro tip: The force_style parameter in the SRT method lets you override subtitle styling without editing the SRT file. Useful when you get captions from auto-transcription services and need them to look consistent.


6. Picture-in-Picture (Two Videos Overlaid)

# Main video with small webcam overlay in bottom-right
ffmpeg -i main.mp4 -i webcam.mp4 \
    -filter_complex "[1:v]scale=320:240[pip];[0:v][pip]overlay=W-w-20:H-h-20" \
    -c:a copy \
    pip_output.mp4
Enter fullscreen mode Exit fullscreen mode

Variations:

  • Top-left: overlay=20:20
  • Center: overlay=(W-w)/2:(H-h)/2
  • Animated (slide in): overlay='if(lt(t,1),W,W-w-20)':H-h-20

I use this for tutorial videos — screen recording as the main video, webcam as the PiP.


7. Speed Up / Slow Down Video

# 2x speed (video + audio)
ffmpeg -i input.mp4 -filter_complex "[0:v]setpts=0.5*PTS[v];[0:a]atempo=2.0[a]" -map "[v]" -map "[a]" fast.mp4

# 0.5x speed (slow motion)
ffmpeg -i input.mp4 -filter_complex "[0:v]setpts=2.0*PTS[v];[0:a]atempo=0.5[a]" -map "[v]" -map "[a]" slow.mp4

# 4x speed (atempo max is 2.0, so chain them)
ffmpeg -i input.mp4 -filter_complex "[0:v]setpts=0.25*PTS[v];[0:a]atempo=2.0,atempo=2.0[a]" -map "[v]" -map "[a]" 4x.mp4
Enter fullscreen mode Exit fullscreen mode

The gotcha: setpts changes video speed, atempo changes audio speed. They're separate filters. If you only use setpts, you get a fast video with normal-speed audio — which is funny exactly once.

Also: atempo only accepts values between 0.5 and 2.0. For 4x, you chain two atempo=2.0 filters. I still have to look that up sometimes because it’s one of those FFmpeg details that never stays in my head.


8. Generate a Video from Images (Slideshow / Timelapse)

# From numbered images (img001.png, img002.png, etc.)
ffmpeg -framerate 24 -i img%03d.png -c:v libx264 -pix_fmt yuv420p slideshow.mp4

# From a folder of images (simple slideshow)
ffmpeg -framerate 1/3 -pattern_type glob -i '*.jpg' \
    -c:v libx264 -vf "fps=25,format=yuv420p" -pix_fmt yuv420p \
    slideshow.mp4
Enter fullscreen mode Exit fullscreen mode

When I use it: Generating timelapse videos from screenshot sequences. Also useful for turning design mockups into a quick presentation video.

The -framerate 1/3 means each image shows for 3 seconds. Change the denominator to control display time.


The Cheat Sheet

Task Key flags
Extract audio -vn (no video)
No re-encode -c copy
Quality control -crf 18 (lower = better, 0-51)
Normalize audio -af "loudnorm=I=-16"
Scale video -vf "scale=1920:1080"
Trim -ss START -to END
Overwrite -y

If you want more of these, I keep a small collection of terminal-first FFmpeg patterns on terminalskills.io.


What's your go-to FFmpeg recipe? Mine is still the two-pass GIF trick — not glamorous, but I use it constantly because bad GIF exports are way more common than they should be. If you have a better one, drop it in the comments 👇

Top comments (0)