ffmpeg Convert Video Audio Examples
Install ffmpeg
On Mac OS X, install with brew :
$ brew install ffmpeg
On Debian Linux:
$ sudo apt-get install ffmpeg
Convert audio file format to .mp3
Convert to mp3 format with libmp3lame
LAME (libmp3lame) is a high quality MPEG Audio Layer III (MP3) encoder. LAME is now regarded as the top MP3 encoder for mid-high bitrates and variable bit rate (VBR). Quality and speed enhancements continue to be made, making LAME likely the only MP3 encoder still actively developed.
Use libmp3lame
to encode mp3 file, ffmpeg
need compiled with --enable-libmp3lame
.
Note: After converted to mp3
, the mp3tag also updated to keep the original audio info.
Encoding mp3 with a fixed bitrate
Convert .wav
, .ape
to .mp3
with 320kb/s bitrate (the highest quality) example:
$ ffmpeg -i foo.ape -codec:a libmp3lame -b:a 320k output.mp3
Input #0, ape, from 'foo.ape':
Metadata:
Title : xx
Artist : xx
Album : xx
Track : xx
Genre : xx
ALBUM ARTIST : xx
Duration: 00:04:13.19, start: 0.000000, bitrate: 774 kb/s
Stream #0:0: Audio: ape (APE / 0x20455041), 44100 Hz, stereo, s16p
Stream mapping:
Stream #0:0 -> #0:0 (ape (native) -> mp3 (libmp3lame))
Press [q] to stop, [?] for help
Output #0, mp3, to 'output.mp3':
Metadata:
TIT2 : xx
TPE1 : xx
TALB : xx
TRCK : xx
TCON : xx
ALBUM ARTIST : xx
TSSE : Lavf59.16.100
Stream #0:0: Audio: mp3, 44100 Hz, stereo, s16p, 320 kb/s
Metadata:
encoder : Lavc59.18.100 libmp3lame
size= 9893kB time=00:04:13.20 bitrate= 320.1kbits/s speed=49.7x
video:0kB audio:9892kB subtitle:0kB other streams:0kB global headers:0kB muxing overhead: 0.012410%
Convert any audio format (.wav
, .ape
, .aiff
, .flac
etc) to .mp3
with 320kb/s bitrate (the highest quality) and also keep metadata example:
ffmpeg -i "$filename" -codec:a libmp3lame -b:a 320k -map_metadata 0 -id3v2_version 3 "$output"
Encoding mp3 with variable bitrate
Use the best variable rate with -q:a 0
, the bitrate range is 220-260kb/s, example:
$ ffmpeg -i foo.ape -codec:a libmp3lame -q:a 0 output.mp3
Input #0, ape, from 'foo.ape':
Metadata:
Title : xx
Artist : xx
Album : xx
Track : xx
Genre : xx
ALBUM ARTIST : xx
Duration: 00:04:13.19, start: 0.000000, bitrate: 774 kb/s
Stream #0:0: Audio: ape (APE / 0x20455041), 44100 Hz, stereo, s16p
Stream mapping:
Stream #0:0 -> #0:0 (ape (native) -> mp3 (libmp3lame))
Press [q] to stop, [?] for help
Output #0, mp3, to 'output.mp3':
Metadata:
TIT2 : xx
TPE1 : xx
TALB : xx
TRCK : xx
TCON : xx
ALBUM ARTIST : xx
TSSE : Lavf59.27.100
Stream #0:0: Audio: mp3, 44100 Hz, stereo, s16p
Metadata:
encoder : Lavc59.37.100 libmp3lame
size= 7545kB time=00:04:13.20 bitrate= 244.1kbits/s speed=55.8x
video:0kB audio:7544kB subtitle:0kB other streams:0kB global headers:0kB muxing overhead: 0.005450%
Note: Since mp3
format is lossy encoding, use best variable bitrate -q:a 0
can get similar quality with fixed bitrate -b:a 320k
but smaller file size.
Default mp3 encoding quality
If do not specific encoding quality, the default is 128kb/s, see the last two lines of following example:
$ ffmpeg -i foo.ape output.mp3
Input #0, ape, from 'foo.ape':
Metadata:
Title : xx
Artist : xx
Album : xx
Track : xx
Genre : xx
ALBUM ARTIST : xx
Duration: 00:04:13.19, start: 0.000000, bitrate: 774 kb/s
Stream #0:0: Audio: ape (APE / 0x20455041), 44100 Hz, stereo, s16p
Stream mapping:
Stream #0:0 -> #0:0 (ape (native) -> mp3 (libmp3lame))
Press [q] to stop, [?] for help
Output #0, mp3, to 'output.mp3':
Metadata:
TIT2 : xx
TPE1 : xx
TALB : xx
TRCK : xx
TCON : xx
ALBUM ARTIST : xx
TSSE : Lavf59.16.100
Stream #0:0: Audio: mp3, 44100 Hz, stereo, s16p
Metadata:
encoder : Lavc59.18.100 libmp3lame
size= 3957kB time=00:04:13.20 bitrate= 128.0kbits/s speed= 48x
video:0kB audio:3957kB subtitle:0kB other streams:0kB global headers:0kB muxing overhead: 0.010391%
Extract audio from video file
$ ffmpeg -i foo.webm -vn -acodec libmp3lame -q:a 0 output.mp3
-vn disable video
-acodec libmp3lame force audio use libmp3lame codec
Convert any video format to .mp4
MP4 is widely used because it is highly compatible with most devices and platforms, offers efficient compression for small file sizes without sacrificing quality, and supports various types of multimedia content including video, audio, text, and images. It is ideal for streaming, editing, and general multimedia use, making it a versatile and standardized format.
Convert to .mp4 may also compress video and save space, suitable transfer to mobile device.
To convert a video to MP4 using FFmpeg with x264 encoding, you can use the following command in the terminal:
ffmpeg -i "$input" -map_metadata 0 -crf 17 -c:v libx264 -c:a aac -b:a 256k "$output"
-i "$input"
: Specifies the input file, where$input
is a variable representing the path to the source video.-map_metadata 0
: Maps all metadata from the input file to the output file, preserving information such as title, author, and other tags.-crf 17
: Sets the Constant Rate Factor (CRF) for the video encoding to 17. CRF controls the quality and size of the output video; lower values result in higher quality. A CRF of 17 typically produces visually lossless quality.-c:v libx264
: Specifies the video codec to be used for encoding as H.264 (libx264), which is a widely used video compression standard known for its balance of quality and file size.-c:a aac
: Specifies the audio codec to be used for encoding as Advanced Audio Coding (AAC), which is a standard for lossy audio compression.-b:a 256k
: Sets the audio bitrate to 256 kbps, which determines the quality and size of the audio stream. Higher bitrates provide better audio quality."$output"
: Specifies the output file name and path, where$output
is a variable representing the destination for the converted video file.
More how to choose crf
value:
- The range of the
CRF
scale is 0–51, where 0 is lossless (for 8 bit only, for 10 bit use -qp 0), 23 is the default, and 51 is worst quality possible. - A lower value generally leads to higher quality, and a subjectively sane range is 17–28.
- Consider 17 or 18 to be visually lossless or nearly so; it should look the same or nearly the same as the input but it isn’t technically lossless.
Trim a video to specific time range
The following command takes input.mp4
, starts extracting at 5 minutes and 20 seconds, and continues for 10 minutes, copying both the video and audio streams without re-encoding, and saves the result as output.mp4
:
ffmpeg -i input.mp4 -ss 00:05:20 -t 00:10:00 -c:v copy -c:a copy output.mp4
-i input.mp4
: This specifies the input file, which in this case is input.mp4.-ss 00:05:20
: This sets the start time of the extraction. The video will start from 5 minutes and 20 seconds into theinput.mp4
file.-t 00:10:00
: This specifies the duration of the extraction. The command will extract a segment that is 10 minutes long starting from the-ss
time (5 minutes and 20 seconds).-c:v copy
: This tellsffmpeg
to copy the video codec, meaning it will not re-encode the video stream but just copy it as is.-c:a copy
: This tellsffmpeg
to copy the audio codec, meaning it will not re-encode the audio stream but just copy it as is.output.mp4
: This is the name of the output file that will contain the extracted video segment.
The -c:v copy -c:a copy
commands copy the original video and audio streams without re-encoding.
To specify the time, you can use two different time unit formats: sexagesimal (HOURS:MM:SS.MILLISECONDS, e.g., 01:23:45.678
) or in seconds. When using the former, you can omit the milliseconds and use HOURS:MM:SS
, as shown in our example.
If you specify a duration that extends beyond the length of the input video, the output video will end when the input video ends.
Resize video retain aspect ratio
To resize a video using FFmpeg, you can use the following command:
ffmpeg -i input.ext -vf scale=width:height output.mp4
Replace input.ext
with the name of your source video file, width
and height
with the desired dimensions, and output.mp4
with the desired name for the resized video file.
For example, to resize a video to 1280x720 resolution, you can use:
ffmpeg -i inputfile.ext -vf scale=1280:720 outputfile.mp4
If you want to maintain the aspect ratio while resizing, you can use:
ffmpeg -i inputfile.ext -vf scale=1280:-1 outputfile.mp4
Here, -1
automatically adjusts the height to maintain the aspect ratio based on the specified width.
However it may run into issue height not divisible by 2
like below:
libx264 @ 0x12a905e60] height not divisible by 2 (320x693)
To resize a video using FFmpeg and keep aspect ratio, you can use the following script to avoid height not divisible by 2
issue:
#!/bin/sh -x
# desired video width
WIDTH=480
INPUT=$1
BASENAME="${INPUT%.*}" # without extension, e.g. "foo.mp4" -> "foo"
OUTPUT="$BASENAME-${WIDTH}p.mp4" # output as .mp4
# not use`scale=width:-1` to avoid [libx264 @ 0x12a905e60] height not divisible by 2 (320x693)
ffmpeg -i "$INPUT" -vf "scale=$WIDTH:ceil(ih*$WIDTH/iw/2)*2" -y "$OUTPUT"
Explanation:
-vf "scale=$WIDTH:ceil(ih*$WIDTH/iw/2)*2"
: Applies a video filter (-vf
) to resize the video. Thescale
filter resizes the video to a specified width and calculates the height to maintain the aspect ratio.$WIDTH
: The desired width of the output video.ceil(ih*$WIDTH/iw/2)*2
: Calculates the height while maintaining the aspect ratio. Here,ih
is the input height, andiw
is the input width.ih*$WIDTH/iw
computes the new height maintaining the aspect ratio./2)*2
ensures the height is an even number, which is required by many video codecs. Theceil
function rounds up to the nearest integer.
-y
: Overwrites the output file without asking for confirmation if it already exists.
Extract video cover image with exiftool
Use exiftool -json example.mp4
to get cover image tag name. The name may “CoverArt”, “Picture” etc. e.g.
$ exiftool -json example.mp4
"CoverArt": "(Binary data 31650 bytes, use -b option to extract)",
Here the tag name is CoverArt
, then extract with -b
, by default it dump the image binary on screen, use >
to redirect to a file:
exiftool -b -CoverArt example.mp4 > cover.jpg
Add covert image (thumbnail) to a video
To add an embedded cover/thumbnail:
ffmpeg -i example.mp4 -i cover.jpg -map 0 -map 1 -c copy -c:v:1 png -disposition:v:1 attached_pic out.mp4
Not all muxers support embedded thumbnails, and those who do, only support a few formats, like JPEG
or PNG
.
Note: Use png
even your cover.jpg
is jpg format, otherwise you may not able to see it in Finder Preview.
References
- wikipedia: MP3
- FFmpeg Codecs Documentation for libmp3lame
- FFmpeg MP3 Encoding Guide
- The LAME Project
- ffmpeg Command Options
OmniLock - Block / Hide App on iOS
Block distractive apps from appearing on the Home Screen and App Library, enhance your focus and reduce screen time.
DNS Firewall for iOS and Mac OS
Encrypted your DNS to protect your privacy and firewall to block phishing, malicious domains, block ads in all browsers and apps