webrtc Android WebRtcNs降噪算法的使用

平臺: Rk3399Pro_Android8.1_SDK

如之前文章 https://blog.csdn.net/piaozhiye/article/details/90716782
編譯 出libwebrtc_audio_preprocessing.so

在external/webrtc 目錄下面新建test 目錄編寫測試程序代碼

3399/Rk3399Pro_Android8.1_SDK_Beta_V0.1_20181130/external/webrtc$ git diff ./
@@ -51,6 +51,23 @@ LOCAL_SHARED_LIBRARIES := \
 include $(BUILD_SHARED_LIBRARY)
 
+
+include $(CLEAR_VARS)
+LOCAL_CFLAGS += -Wno-error
+LOCAL_C_INCLUDES := \
+    $(LOCAL_PATH)/webrtc/modules/audio_processing/include \
+    $(LOCAL_PATH)/webrtc/modules/audio_processing/aec \
+    $(LOCAL_PATH)/webrtc/modules/audio_processing/aecm \
+    $(LOCAL_PATH)/webrtc/modules/audio_processing/agc \
+    $(LOCAL_PATH)/webrtc/modules/audio_processing/ns
+       
+LOCAL_SRC_FILES:= test/webrtc_test.c 
+LOCAL_MODULE:= webrtc_test
+LOCAL_PROPRIETARY_MODULE := true
+LOCAL_SHARED_LIBRARIES := liblog libc libcutils libwebrtc_audio_preprocessing 
+LOCAL_MODULE_TAGS:= debug
+include $(BUILD_EXECUTABLE)
+

WebRtcNs 支持8k 16k 32k,
8K 以及16k 的可直接將buf 傳入WebRtcNsx_Process,

int webrtc_ns_8k_16k_test(char *in, char *out, int rate, int ns_mode)
{
	webrtc_ec *webrtc_state;
	int status = 0;
	int file_size = 0;
	FILE *fp_in  = fopen(in, "rb");
	FILE *fp_out  = fopen(out, "wb");
	const sample * buf_ptr;
	sample * out_buf_ptr;
	
    if (rate != 8000 && rate != 16000){
        ALOGE("webrtc_ns_8k_16k_test not support rate =%d", rate);
        return -1;
    }	
	
	
	webrtc_state = (struct webrtc_ec *)calloc(1, sizeof(struct webrtc_ec));
	if(!webrtc_state){
		ALOGE("malloc webrtc_state no mem");
		return -ENOMEM;
	}
	webrtc_state->channel_count = 1;

	webrtc_state->NS_inst = WebRtcNs_Create();
    if (webrtc_state->NS_inst) {
        status = WebRtcNs_Init(webrtc_state->NS_inst, rate);
        if (status != 0) {
            WebRtcNs_Free(webrtc_state->NS_inst);
            webrtc_state->NS_inst = NULL;
        }
    }
    if (!webrtc_state->NS_inst) {
        ALOGE("webrtc_aec_create Unable to create WebRTC noise suppressor");
		return -1;
    }
	WebRtcNs_set_policy(webrtc_state->NS_inst,ns_mode);
	ALOGE("starting WebRtcNsx_Process...");
	while(1){
		if (NN_LEN == fread(webrtc_state->tmp_buf, sizeof(short), NN_LEN, fp_in)){
			buf_ptr = webrtc_state->tmp_buf;
			out_buf_ptr = webrtc_state->tmp_buf2;
			ALOGE("WebRtcNsx_Process...");
			WebRtcNsx_Process(webrtc_state->NS_inst, &buf_ptr, webrtc_state->channel_count, &out_buf_ptr);
			fwrite(out_buf_ptr, sizeof(short), NN_LEN, fp_out);
		}else{
			break;
		}
	}
	if (webrtc_state->NS_inst) {
        WebRtcNs_Free(webrtc_state->NS_inst);
        webrtc_state->NS_inst = NULL;
    }

	fclose(fp_in);
	fclose(fp_out);	
	return status;
}

32K WebRtcNs 需要分高頻 低頻部分傳入參數WebRtcNsx_Process如下:

int webrtc_ns_32k_test(char *in, char *out, int rate, int ns_mode)
{
	webrtc_ec *webrtc_state;
	int status = 0;
	int file_size = 0;
	FILE *fp_in  = fopen(in, "rb");
	FILE *fp_out  = fopen(out, "wb");

	short *Arr=NULL;

	int  filter_state1[60],filter_state12[60];
	int  Synthesis_state1[60],Synthesis_state12[60];

	memset(filter_state1,0,sizeof(filter_state1));
	memset(filter_state12,0,sizeof(filter_state12));
	memset(Synthesis_state1,0,sizeof(Synthesis_state1));
	memset(Synthesis_state12,0,sizeof(Synthesis_state12));	
	Arr = (short*)malloc(2*sizeof(short*));
	short **outA=&Arr;
	
    if (rate != 32000){
        ALOGE("webrtc_ns_32k_48k_test not support rate =%d", rate);
        return -1;
    }
	webrtc_state = (struct webrtc_ec *)calloc(1, sizeof(struct webrtc_ec));
	if(!webrtc_state){
		ALOGE("malloc webrtc_state no mem");
		return -ENOMEM;
	}
	webrtc_state->channel_count = 2;

	webrtc_state->NS_inst = WebRtcNs_Create();
    if (webrtc_state->NS_inst) {
        status = WebRtcNs_Init(webrtc_state->NS_inst, rate);
        if (status != 0) {
            WebRtcNs_Free(webrtc_state->NS_inst);
            webrtc_state->NS_inst = NULL;
        }
    }
    if (!webrtc_state->NS_inst) {
        ALOGE("webrtc_aec_create Unable to create WebRTC noise suppressor");
		return -1;
    }
	WebRtcNs_set_policy(webrtc_state->NS_inst,ns_mode);
	ALOGE("starting WebRtcNsx_Process...");

	if(rate == 32000){
		while(1){
			sample in32k_buf[SAMPLES32k_10ms] = {0};
			sample out32k_buf[SAMPLES32k_10ms] = {0};
			sample in32k_buf_low[SAMPLES32k_10ms/2], in32k_buf_high[SAMPLES32k_10ms/2];
			if (SAMPLES32k_10ms == fread(in32k_buf, sizeof(sample), SAMPLES32k_10ms, fp_in)){
			
				WebRtcSpl_AnalysisQMF(in32k_buf, SAMPLES32k_10ms, in32k_buf_low, in32k_buf_high, filter_state1, filter_state12);
				//將需要降噪的數據以高頻和低頻傳入對應接口,同時需要注意返回數據也是分高頻和低頻
				const short* InA[2]={in32k_buf_low, in32k_buf_high};
				ALOGE("WebRtcNsx_Process...9*9");
				WebRtcNsx_Process(webrtc_state->NS_inst, InA, webrtc_state->channel_count, outA);
				//如果降噪成功,則根據降噪後高頻和低頻數據傳入濾波接口,然後用將返回的數據寫入文件
				WebRtcSpl_SynthesisQMF(outA[0], outA[1], SAMPLES32k_10ms/2, out32k_buf, Synthesis_state1, Synthesis_state12);
				fwrite(out32k_buf, sizeof(short), SAMPLES32k_10ms, fp_out);
			}else{
					break;
			}
		}
	}
	if (webrtc_state->NS_inst) {
        WebRtcNs_Free(webrtc_state->NS_inst);
        webrtc_state->NS_inst = NULL;
    }

	fclose(fp_in);
	fclose(fp_out);	
	return status;		
}

編譯生成
Rk3399Pro_Android8.1_SDK_Beta_V0.1_20181130$ mmm external/webrtc/ -j32
out/target/product/rk3399pro/vendor/bin/webrtc_test

adb root
adb remount
adb push webrtc_test /system/bin/
adb shell chmod 777 /system/bin/webrtc_test
./webrtc_test 運行測試
源碼下載,https://download.csdn.net/download/piaozhiye/11235847
參考
參考
參考

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章