如何用FFmpeg调整视频的码率、分辨率和帧率?
在视频处理中,调整码率、分辨率和帧率是最常见的需求。无论是压缩视频体积、适配不同设备,还是优化流媒体传输,FFmpeg 都能通过命令行参数精确控制这三个核心参数。但参数设置不当容易导致画质劣化、播放卡顿甚至编码失败,所以需要理解每个参数的含义和适用场景。
码率调整:控制视频体积与画质的平衡
码率(bitrate)决定视频每秒的数据量,单位为 kbit/s 或 Mbit/s。码率越高画质越好,但文件体积也越大。FFmpeg 提供三种码率控制模式,适用场景各不相同。
CBR:恒定码率
CBR 保持码率不变,适合直播等对带宽要求稳定的场景:
bashffmpeg -i input.mp4 -c:v libx264 -b:v 5000k -minrate 5000k -maxrate 5000k -bufsize 10000k output.mp4
将 -minrate、-maxrate 设为相同值即为 CBR 模式。-bufsize 设为码率的 2 倍可以保证码率稳定。
VBR:可变码率
VBR 根据画面复杂度动态调整码率,简单场景省码率、复杂场景多分配,适合点播和本地存储:
bashffmpeg -i input.mp4 -c:v libx264 -b:v 5000k -maxrate 8000k -bufsize 10000k output.mp4
-b:v 设定平均码率,-maxrate 限制峰值码率防止突发流量。
CRF:恒定质量(推荐)
CRF(Constant Rate Factor)是 libx264/libx265 最推荐的码率控制方式,它按目标画质自动分配码率,无需手动指定码率值:
bashffmpeg -i input.mp4 -c:v libx264 -crf 23 -preset medium output.mp4
CRF 取值范围 0-51,默认 23。常用范围:
- 18-22:高质量,接近视觉无损
- 23-28:质量与体积的平衡点,日常使用推荐
- 28-32:明显压缩,适合对体积敏感的场景
-preset 控制编码速度与压缩效率的平衡,从快到慢:ultrafast < superfast < veryfast < faster < fast < medium < slow < slower < veryslow。slow 压缩率更高但编码更慢,fast 编码快但文件更大。
两遍编码(Two-Pass)
对体积有严格要求的场景(如视频网站),使用两遍编码可以在精确控制文件大小的同时获得最佳画质:
bash# 第一遍:分析视频内容 ffmpeg -i input.mp4 -c:v libx264 -b:v 5000k -pass 1 -an -f null /dev/null # 第二遍:基于分析结果编码 ffmpeg -i input.mp4 -c:v libx264 -b:v 5000k -pass 2 -c:a aac -b:a 128k output.mp4
码率参考值
不同分辨率下的推荐码率(H.264 编码):
| 分辨率 | 建议码率范围 | 适用场景 |
|---|---|---|
| 480p (854x480) | 1000-2000 kbit/s | 移动端低清 |
| 720p (1280x720) | 2500-5000 kbit/s | 移动端高清 |
| 1080p (1920x1080) | 5000-8000 kbit/s | PC 端高清 |
| 4K (3840x2160) | 15000-30000 kbit/s | 大屏/专业用途 |
分辨率调整:适配不同设备与带宽
分辨率即画面的宽高像素数,直接影响清晰度。调整分辨率有两种方式,推荐使用滤镜方式。
使用 scale 滤镜(推荐)
bash# 固定分辨率 ffmpeg -i input.mp4 -vf "scale=1280:720" -c:v libx264 -crf 23 output.mp4 # 指定高度,宽度自动计算(保持宽高比) ffmpeg -i input.mp4 -vf "scale=-2:720" -c:v libx264 -crf 23 output.mp4
-2 表示自动计算,保证宽度为偶数(编码器要求)。推荐这种写法,避免画面变形。
使用 lanczos 算法提升缩放质量
bashffmpeg -i input.mp4 -vf "scale=1280:720:flags=lanczos" -c:v libx264 -crf 23 output.mp4
lanczos 是高质量的缩放算法,下采样时比默认的 bicubic 更清晰,适合降低分辨率的场景。
保持宽高比并补黑边
目标容器有固定尺寸但不想裁剪画面时:
bashffmpeg -i input.mp4 -vf "scale=1280:720:force_original_aspect_ratio=decrease,pad=1280:720:(ow-iw)/2:(oh-ih)/2" -c:v libx264 -crf 23 output.mp4
使用 -s 参数(不推荐)
bashffmpeg -i input.mp4 -s 1280x720 -c:v libx264 -crf 23 output.mp4
-s 直接指定分辨率,但无法保持宽高比,容易导致画面拉伸变形。仅在源视频比例已知时使用。
帧率调整:匹配播放场景的需求
帧率(fps)影响画面流畅度。常见帧率:24fps(电影)、25fps(PAL 制式)、30fps(网络视频)、60fps(游戏/运动画面)。
直接设置帧率
bashffmpeg -i input.mp4 -r 24 -c:v libx264 -crf 23 output.mp4
-r 直接指定输出帧率,FFmpeg 会自动丢帧或复制帧来匹配目标帧率。
使用 fps 滤镜(推荐降帧场景)
bashffmpeg -i input.mp4 -vf "fps=24" -c:v libx264 -crf 23 output.mp4
fps 滤镜比 -r 更精确,会均匀选取帧而非简单丢弃,画面过渡更平滑。
使用 setpts 调整播放速度
bash# 1.5 倍速播放(帧率相应提高) ffmpeg -i input.mp4 -vf "setpts=PTS/1.5" -c:v libx264 -crf 23 output.mp4 # 0.5 倍速播放(慢放) ffmpeg -i input.mp4 -vf "setpts=2*PTS" -c:v libx264 -crf 23 output.mp4
setpts 改变帧的时间戳,实现变速效果。注意变速时音频也需要同步处理(使用 atempo 滤镜)。
使用 -vsync 控制同步模式
bashffmpeg -i input.mp4 -r 24 -vsync cfr -c:v libx264 -crf 23 output.mp4
cfr:恒定帧率,不足的帧会复制,多余的帧丢弃,输出帧率严格恒定vfr:可变帧率,保持原始时间戳,不插帧不丢帧auto:根据输入自动选择(默认)
直播和流媒体推荐 cfr,保证播放器解码稳定。
查看视频信息:调整前先了解源文件
调整参数前,先用 ffprobe 查看源视频信息:
bash# 查看完整流信息 ffprobe -v error -show_streams input.mp4 # 只看码率 ffprobe -v error -select_streams v:0 -show_entries stream=bit_rate -of default=noprint_wrappers=1 input.mp4 # 只看分辨率和帧率 ffprobe -v error -select_streams v:0 -show_entries stream=width,height,r_frame_rate -of default=noprint_wrappers=1 input.mp4
组合使用:常见场景的完整命令
压缩视频体积(保持画质)
bashffmpeg -i input.mp4 -c:v libx264 -crf 28 -preset slow -c:a aac -b:a 128k output.mp4
适配移动端(720p + 适中码率)
bashffmpeg -i input.mp4 -vf "scale=-2:720" -c:v libx264 -crf 26 -preset medium -c:a aac -b:a 128k output.mp4
流媒体推送(固定码率 + 720p + 30fps)
bashffmpeg -i input.mp4 -vf "scale=-2:720" -c:v libx264 -b:v 3000k -maxrate 3500k -bufsize 6000k -r 30 -vsync cfr -c:a aac -b:a 128k output.mp4
H.265 编码(同画质体积减半)
bashffmpeg -i input.mp4 -c:v libx265 -crf 28 -preset medium -c:a aac -b:a 128k output.mp4
H.265/HEVC 比 H.264 在同等画质下节省约 40-50% 码率,但编码速度慢、兼容性稍差。
常见问题
调整后画质明显下降
码率不足是主因。如果是用 -b:v 控制码率,尝试提高码率或改用 CRF 模式(-crf 23)。降分辨率时指定 lanczos 算法可以减少模糊。
分辨率调整后画面变形
没有保持宽高比。用 scale=-2:720 替代 scale=1280:720,让宽度自动计算。-2 保证宽度为偶数,满足编码器要求。
帧率调整后播放抖动
源帧率与目标帧率不匹配导致丢帧不均匀。使用 fps 滤镜(-vf "fps=24")替代 -r 参数,前者会均匀选帧;或加 -vsync cfr 强制恒定帧率输出。
编码速度太慢
降低 -preset 参数值(如从 slow 改为 fast),或使用硬件加速编码器(如 -c:v h264_videotoolbox macOS / -c:v h264_nvenc NVIDIA / -c:v h264_qsv Intel)。
-vbr 参数不生效
libx264 不支持 -vbr 参数。码率控制应使用 -crf(推荐)、-b:v + -maxrate(VBR 限峰)或两遍编码(-pass)。-vbr 仅适用于部分编码器(如 libvpx)。