ffmpeg examples

screen capture

from Windows

ffmpeg -f gdigrab -show_region 1 -framerate 30 -video_size 942x1003 -offset_x 8 -offset_y 30 -i desktop out.avi

With h264 compression but not a lot of it:
ffmpeg -f gdigrab -show_region 1 -framerate 25 -video_size 800x600 -offset_x 1 -offset_y 30 -i desktop -c:v libx264 -crf 18 -preset veryfast out.mp4

!

gluing video files together

inline, with different-sized video inputs:
ffmpeg -i IMG_3198.MOV -i IMG_3199.MOV -i IMG_3201.MOV -i IMG_3202.MOV -i IMG_3203.MOV -i title.mp4 -filter_complex "[0:0] [0:1] [1:0] [1:1] [2:0] [2:1] [3:0] [3:1] [4:0] [4:1] [5:0] [5:1] concat=n=6:v=1:a=1:unsafe=1 [v] [a]" -map "[v]" -map "[a]" -s 960x540 output.mp4

inline, with similar inputs:
ffmpeg -hide_banner -i "Wow-64 2015-01-19 22-08-49-73.avi" -i "Wow-64 2015-01-19 22-08-49-73.avi" -filter concat=n=2:v=1:a=1 -c:v libx264 -crf 24 -preset slow -b:a 96k turning_in_10_onyx_eggs.mp4

with a file:
ffmpeg -f concat -i filelist.txt output.webm

video size

specifying resolution: ffmpeg -i large.avi -s 1280x720 out_small.webm

scaling while keeping aspect ratio: ffmpeg -i large.avi -vf "scale=w=-1:h=320" out_small.webm (relevant doc section)

resolution as memnonics: ffmpeg -i large.avi -s hvga "480 by 320.mp4" | relevant doc section | vga, hvga, qvga, cif, qcif [super tiny], hd480, hd720, hd1080, qhd (960x540)

cropping: ffmpeg -i in.avi -filter:v "crop=out_w=702:out_h=540:x=129:y=0" out.avi | relevant doc section

an example with everything: ffmpeg -i cbnxcn.mp4 -filter:v "crop=x=115:y=145:out_w=(in_w-405-115):out_h=(in_h-115-145), scale=w=1280:h=720" -c:v libx264 -crf 24 -preset slow -c:a copy -t 15 -ss 2.3 ekjkbdko.mp4

video quality

specifying bitrate: ffmpeg -i in.avi -b:v 500k out.avi | documentation doesn't like this though

specifying quality, for h.264: ffmpeg -i in.avi -c:v libx264 -crf 23 out.mp4 | crf values of 18-28 are considered "sane" | crf 0 is lossless, 23 default, 51 worst | relevant wiki link

generic quality options: ffmpeg -i in.avi -q:v N out.avi | ffmpeg -i in.avi qscale:v N out.avi | meaning of -q and -qscale is codec-dependent

video duration and filesize

stop encoding after output duration reaches 1 minute: ffmpeg -i longvid.avi -t 00:01:00 "first minute.mp4"

stop encoding after reading 1 minute from input: ffmpeg -t 00:01:00 longvid.avi "first minute.mp4"

stop writing output at 4 minutes: ffmpeg -i longvid.avi -t 00:04:00 out.avi

stop encoding after N frames have been output: ffmpeg -i vid.avi -frames:v N out.mp4

seek past the first ~20.3 seconds of input: ffmpeg -ss 00:00:20.3 -i infile.avi outfile.avi
send first 20.4 seconds processed to /dev/null: ffmpeg -i infile.avi -ss 20.4 outfile.avi

drawtext

relevant doc section | an example where the video's timecode is burned in in seconds.frame format:
ffmpeg -i infile.avi -filter:v drawtext=" fix_bounds=1: fontfile='//COMPUTER/Users/oatcookies/Desktop/DejaVuSansMono-Bold.ttf': fontcolor=white: fontsize=24: bordercolor=black: borderw=1: textfile=burn-in.txt: x=1: y=main_h-line_h-1:" outfile.avi
where burn-in.txt has the following contents: %{expr: (floor(n/30)) + (mod(n, 30)/100)}
of course, that specific expression applies to a 30 fps video. the odd fontfile path is because ffmpeg doesn't exactly like windows' drive letters: trying 'C\:\\Windows\\Fonts\\x.ttf' (with varying amounts of (back)slashes) always resulted in an error.

a different burn-in.txt: %{expr_int_format: floor((n/30)/60) : d : 2}:%{eif: mod(floor(n/30), 60) :d:2}.%{eif: mod(n, 30)+1 :d:2} | this shows the timecode in minutes:seconds.frames format.

time code for text-burning filters

%{expr_int_format:floor((n/60)/60):d:2}:%{eif:mod(floor(n/60),60):d:2}

sound

making louder: ffmpeg -hide_banner -i "quiet input.mp4" -af "volume=40dB" -vcodec copy "louder output.mp4"

removing entirely: ffmpeg -i with_sound.mp4 -vcodec copy -an no_sound.mp4

sound quality: ffmpeg -i in.mp4 -b:a 64k out.mp4

example filelist.txt

file 'G:\ff\day1\2015-05-15 21-53-49-96.avi'
file 'G:\ff\day1\2015-05-15 22-03-57-86.avi'
file 'G:\ff\day2\2015-05-16 22-08-42-72.avi'

perl script to generate a file list:

my $prefix = 'G:\\ff\\';
foreach my $subdir (("day1", "day2")) {
	my $dirname = "$prefix\\$subdir";
	print("# $dirname\n");
	
	opendir(my $dirhandle, $dirname) || die "Can't opendir $dirname: $!\n";

	open(my $outfile, '>', "$subdir.txt") || die "Can't open > $subdir.txt: $!\n";

	my $i = 1;
	while (readdir $dirhandle) {
		if ($_ =~ /*.avi$/ ) {
			print( $outfile "file '$dirname\\$_'\n");
			$i++;
		}
	}

	closedir($dirhandle);
	close($outfile);
}

viewing file information

ffprobe infile.mp4

framerate acceleration

example: input was recorded at 5 fps. output should be the same frames but at 25 fps, making the output video 5x faster.

ffmpeg -i input_5fps.mp4 -r 25 -filter setpts=PTS/5 output_25fps.mp4

example: a web rip had borders and a speedup to avoid algorims.

ffmpeg -i inrip.mp4 -r 30 -ar 44100 -filter:v "crop=out_w=640:out_h=360:x=345:y=235, setpts=PTS/0.9" -filter:a "asetrate=39690" -c:v libx264 -crf 24 "output.mp4"

selective muting

ffmpeg -i copyright_trolled.mp4 -c:v copy -filter:a "volume='ifnot(between(t,20834,20987),1)':eval=frame" part_muted.mp4

mp3 metadata

ffmpeg -i in.mp3 -c:a copy -metadata TSOT="sort by this string" out.mp3

posted , last edited · oatcookies.tx0.org