FFmpeg 和音量

一、概述

本文整理一些使用 FFmpeg 进行音量控制的 Demo 。

二、音量检测

我录制了一段“唱歌跳舞Rap打篮球”的语音,其波形图如下:

图1:《唱歌跳舞Rap打篮球》的语音波形图

肉眼可见该音频的最大音量是 -3dB。

1
ffmpeg -i 唱歌跳舞Rap打篮球.mp3 -af "volumedetect" -f null /dev/null

或者:

1
ffmpeg -i 唱歌跳舞Rap打篮球.wav -filter_complex volumedetect -c:v copy -f null /dev/null


图2:FFmpeg 获取音量

从输出信息可以看到平均(均方:mean square)音量是 -23.5dB;最大音量是 -2.8dB;7个采样是 -2dB,28个采样是 -3dB,29个采样是 -4dB,48个采样是 -5dB,84个采样是 -6dB。

三、简单音量调整

1
2
# 增大 10dB
ffmpeg -i 唱歌跳舞Rap打篮球.wav -af volume=10dB 唱歌跳舞Rap打篮球+10dB.wav
1
2
# 减小 10dB
ffmpeg -i 唱歌跳舞Rap打篮球.wav -af volume=-10dB 唱歌跳舞Rap打篮球-10dB.wav
1
2
# 设置为原音量的1/2(没有dB单位)
ffmpeg -i 唱歌跳舞Rap打篮球.wav -af volume=0.5 唱歌跳舞Rap打篮球(0.5).wav
1
2
# 设置为原音量的2倍(没有dB单位)
ffmpeg -i 唱歌跳舞Rap打篮球.wav -af volume=2 唱歌跳舞Rap打篮球(2).wav

四、淡入淡出

为了方便实验,我从歌曲《追光者》截取了一段,其波形图如下:

图3:《追光者》节选波形图

故意留了一个突兀的结尾。

1
2
# 从开头5秒淡入,从18秒5秒淡出;在淡出之后剩余部分将静音
ffmpeg -i 追光者01.mp3 -filter_complex "[0:a]afade=t=in:ss=0:d=5[a1];[a1]afade=t=out:st=18:d=5" 追光者02.mp3


图4:《追光者》节选淡入淡出后的波形图

对比原波形图可以看出,在有声部分呈三角形。

五、复杂音量调整

需求:

1、《追光者》前4秒淡入
2、继续播放3秒(此时音量为原音量)
3、3秒淡出为原来的1/10(不是完全淡出)
4、播放4.5秒(此时音量为原音量1/10)
5、4秒淡入
6、继续播放(此时音量为原音量)
7、最后5秒淡出

1
ffmpeg -y -i 追光者01.mp3 -filter_complex "volume=enable='between(t,0,4)':volume='t/4.0':eval=frame,volume=enable='between(t,4,7)':volume='1.0':eval=frame,volume=enable='between(t,7,10)':volume='0.1+(0.9-0.9*(t-7.0)/3.0)':eval=frame,volume=enable='between(t,10,14.5)':volume='0.1':eval=frame,volume=enable='between(t,14.5,18.5)':volume='0.1+(0.9*(t-14.5)/4.0)':eval=frame,volume=enable='between(t,18.5,23.292)':volume='1.0':eval=frame,volume=enable='between(t,23.292,28.292)':volume='1.0-(t-23.292)/5.0':eval=frame" 且听且吟01.mp3


图5:《追光者》节选经复杂音量调整后的波形图

备注:《追光者》节选时长为 28.292s 。

六、混缩

需求:

1、《追光者》前4秒淡入
2、继续播放3秒(此时音量为原音量)
3、3秒淡出为原来的1/10(不是完全淡出)
4、播放4.5秒,与之前录制的《唱歌跳舞Rap打篮球》混缩
5、4秒淡入
6、继续播放(此时音量为原音量)
7、最后5秒淡出

1
ffmpeg -y -i 追光者01.mp3 -i 唱歌跳舞Rap打篮球.wav -filter_complex "[0:a]volume=enable='between(t,0,4)':volume='t/4.0':eval=frame,volume=enable='between(t,4,7)':volume='1.0':eval=frame,volume=enable='between(t,7,10)':volume='0.1+(0.9-0.9*(t-7.0)/3.0)':eval=frame,volume=enable='between(t,10,14.5)':volume='0.1':eval=frame,volume=enable='between(t,14.5,18.5)':volume='0.1+(0.9*(t-14.5)/4.0)':eval=frame,volume=enable='between(t,18.5,23.292)':volume='1.0':eval=frame,volume=enable='between(t,23.292,28.292)':volume='1.0-(t-23.292)/5.0':eval=frame[a0];[1:a]adelay=10000|10000[a1];[a0][a1]amix=inputs=2:duration=longest:dropout_transition=10000,volume=2,pan=stereo|c0<c0+c2|c1<c1+c3[a]" -map "[a]" 且听且吟02.mp3

备注:1.《唱歌跳舞Rap打篮球》时长为 4.5s ;2. adelay 为《唱歌跳舞Rap打篮球》添加了 10s 的静音;3. dropout_transition 设置为 10000 避免了混缩音量降低。


图6:混缩后的波形图

参考资料

http://ffmpeg.org/ffmpeg-all.html#volumedetect
http://ffmpeg.org/ffmpeg-all.html#volume
http://ffmpeg.org/ffmpeg-all.html#afade-1
https://stackoverflow.com/questions/38085408/complex-audio-volume-changes-with-ffmpeg
https://stackoverflow.com/questions/23218906/multiple-fadein-fadeout-effects-in-one-audio-file-with-ffmpeg