单独编译和使用webrtc音频回声消除模块(附完整源码+测试音频文件)

单独编译和使用webrtc音频降噪模块(附完整源码+测试音频文件)html

单独编译和使用webrtc音频增益模块(附完整源码+测试音频文件)web

说实话很不想写这篇文章,由于这和我一向推崇的最好所有编译并使用webrtc音频处理模块相悖。但是不知不觉已经把降噪和增益写出来,回声消除若是用户能够获得完美利用也不失为一个很好的方法。可是仍是那句话,最好仍是所有编译和使用webrtc的整个音频处理模块。另外这篇文章已经不仅仅的回声消除模块了,其中包括了降噪,增益,静音检测,若是有须要能够选择其中的一部分单独提取调试。函数

相对而言回声消除比起其余模块要复杂不少,不光光是计算量大(以前在一部380MHz的摄像头中测试过,其消耗的时间为降噪的三倍以上,若是音频延迟更大甚至根本跑不起来),并且其中也涉及到一个delay的计算,delay计算是否精确彻底影响回声消除的效果。post

至于delay的计算,网上有不少说明,有复杂也有简单的。在这里我仍是简单的提一下:测试


这张图不少东西能够无视,咱们重点看T0,T1,T2三项。
T0表明着声音从扬声器传到麦克风的时间,这个时间能够忽略,由于通常来讲话筒和扬声器之间距离不会太远,考虑到声音340米每秒的速度,这个时间都不会超过1毫秒。spa

T1表明远处传到你这来的声音,这个声音被传递到回声消除远端接口(WebRtcAec_BufferFarend)的到播放出来的时间。通常来讲接收到的音频数据传入这个接口的时候也就是上层传入扬声器的时刻,因此能够理解成该声音防到播放队列中开始计时,到播放出来的时间。调试

T2表明一段声音被扬声器采集到,而后到被送到近端处理函数(WebRtcAec_Process)的时刻,因为声音被采集到立刻会作回声消除处理,因此这个时间能够理解成麦克风采集到声音开始计时,而后到你的代码拿到音频PCM数据所用的时间。code

好了,delay=T0+T1+T2,其实也就是T1+T2。htm

通常来讲,一个设备若是能找到合适的delay,那么这个设备再作回声消除处理就和降噪增益同样几乎没什么难度了。从网上看iPhone的固定delay是60ms,不过不肯定,MacBook挂了,在等四季度新MacBook上市,因此暂时没办法作验证。blog

由于回声消除过程,能够理解成已经把蓝黑两种颜色的墨水彻底混合,而后分离出来所须要的蓝色或者黑色颜色。事实上彻底混在一块儿的音频数据是没法完全分开的,可是咱们能够把混在一块儿的声音理解成两段声音,其中有一段声音能够找到一段几乎相近的对比原声,而后在混音中找到和原声近似的数据,这样就能够分离了。delay的意义显而易见就是要把原声和混在一块儿的声音数据做对比时,校订时刻所用,这个时刻越是精确,那么回声消除的效果越好。不过从实际效果来看这个delay也并不须要特别精确,在这段测试音频数据里面范围能够接近100毫秒。

从两段音频波形起始位置看delay的时间应该超过100毫秒,那么能够用一段代码作测试,测试代码和音频文件来自于网上:

 1 int WebRtcAecTest()
 2 {
 3 #define  NN 160
 4     short far_frame[NN];
 5     short near_frame[NN];
 6     short out_frame[NN];
 7 
 8     void *aecmInst = NULL;
 9     FILE *fp_far  = fopen("speaker.pcm", "rb");
10     FILE *fp_near = fopen("micin.pcm", "rb");
11     FILE *fp_out  = fopen("out.pcm", "wb");
12 
13     do 
14     {
15         if(!fp_far || !fp_near || !fp_out)
16         {
17             printf("WebRtcAecTest open file err \n");
18             break;
19         }
20 
21         WebRtcAec_Create(&aecmInst);
22         WebRtcAec_Init(aecmInst, 8000, 8000);
23 
24         AecConfig config;
25         config.nlpMode = kAecNlpConservative;
26         WebRtcAec_set_config(aecmInst, config);
27 
28         while(1)
29         {
30             if (NN == fread(far_frame, sizeof(short), NN, fp_far))
31             {
32                 fread(near_frame, sizeof(short), NN, fp_near);
33                 WebRtcAec_BufferFarend(aecmInst, far_frame, NN);//对参考声音(回声)的处理
34 
35                 WebRtcAec_Process(aecmInst, near_frame, NULL, out_frame, NULL, NN,109,0);//回声消除
36                 fwrite(out_frame, sizeof(short), NN, fp_out);
37             }
38             else
39             {
40                 break;
41             }
42         }
43     } while (0);
44 
45     fclose(fp_far);
46     fclose(fp_near);
47     fclose(fp_out);
48     WebRtcAec_Free(aecmInst);
49     return 0;
50 }

 

源码下载(VS2010编译版本,也能够移植到其余平台无缝编译):WebRtcAudioAllTest.rar

相关文章
相关标签/搜索