在openwrt上使用ALSA播放语音, 因为要适应不同的采样率的声音源
alsa声卡播出统一使用48k采样率,声音源不是48K的, 需要使用 libsamplerate库进行resample
这里有下载:
https://src.fedoraproject.org/repo/pkgs/libsamplerate/libsamplerate-0.1.8.tar.gz/1c7fb25191b4e6e3628d198a66a84f47/libsamplerate-0.1.8.tar.gz
在openwrt SDK环境下make menuconfig -> Libraries->libsamplerate 就可以编译出动态库和静态库
我用的静态库libsamplerate.a直接link到程序中。
1)使用src_simple单个函数就可以了:
SRC_DATA src_data;
src_data.end_of_input = 0 ; /* Set this later. */
/* Start with zero to force load in while loop. */
src_data.input_frames = payload_bytes ;//待转数据帧数
src_data.output_frames = AUDIO_FRAME_SIZE ;//转换结果数据缓冲区帧数
src_data.data_in = pcm_resample_in ;//转换输入缓冲区
src_data.data_out = pcm_resample_out ;//转换输出缓冲区
src_data.src_ratio = 1.0*AUDIO_FRAME_SIZE/payload_bytes ;//等同于新采样率除以原采样率
if(0 == src_simple(&src_data, SRC_LINEAR, 1)){
memset(pcm16R, 0, sizeof(pcm16R));
for(i=0;i<AUDIO_FRAME_SIZE; i++){
pcm16L[i] = (int16_t)pcm_resample_out[i];
}
play_sound(pcm16L, pcm16R, AUDIO_FRAME_SIZE);
}
//---------------在连续转换多个AUDIO_FRAME_SIZE时,播放由咔咔声
2)使用src_process进行连续转换可以消除咔咔声(参考代码在库自带的exaple/sndfile-resample.c)
初始化:
static SRC_STATE *src_state =NULL;
static SRC_DATA src_data ;
int error =-1;
src_state = src_new (SRC_LINEAR, 1, &error);
src_data.data_in = pcm_resample_in ;
src_data.src_ratio = 1.0*AUDIO_FRAME_SIZE/payload_bytes ; //等同于新采样率除以原采样率
src_data.data_out = pcm_resample_out ;//转换输出缓冲区
src_data.output_frames = AUDIO_FRAME_SIZE /1/*channels*/ ;//转换输出缓冲区的大小
2) 连续转换
while(1) {
if (src_data.input_frames == 0) {
src_data.input_frames = payload_bytes; //下一段待转数据缓冲区,
src_data.data_in = pcm_resample_in ;//待转数据帧数,也就是采样次数
}
//这种resample方法效率比src_simple()高点, 不 容易出现咔咔声音
if ((0 == src_process (src_state, &src_data)) && (src_data.output_frames_gen >0)){
memset(pcm16R, 0, sizeof(pcm16R));
for(i=0;i<src_data.output_frames_gen; i++){//src_data.output_frames_gen 是转换成功的帧数(新采样率为标准)
pcm16L[i] = (int16_t)pcm_resample_out[i];
}
play_sound(pcm16L, pcm16R, src_data.output_frames_gen);
src_data.data_in += src_data.input_frames_used * 1/*channel*/ ;
src_data.input_frames -= src_data.input_frames_used ;
src_data.output_frames_gen = 0;
}
}
分析: 2)不带咔咔声, 因为每次转换衔接处实现了平滑过渡, 而1)做不到平滑过渡