android 多通道音频,支持多通道录音

原生Android仅支持2通道录音,但通过研究AudioRecord的构造函数和相关API,可以实现多通道录音。涉及的关键步骤包括:修改AudioRecord构造函数参数、调整channelConfiguration、处理frameCount和bufferSize,以及在HAL层和audio_policy.conf配置文件中添加对多通道的支持。通过这些修改,可以支持如7.1声道的多通道录音。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

原生Android只支持2 channel的录音。可是偏偏会有多mic的需求,比如说语音识别。目前已知TDM协议可以将多mic数据从kernel送到hal,从内核空间搬运到用户空间中。可是原生AudioRecord接口是完全不支持多channel录音数据的采集的,怎么修改,才能让原生进行支持呢?

我们就从AudioRecord的构造函数开始往下研究。无论行不行,都要研究出个所以然来!​我们如果写个录音app,我们一般这么使用AudioRecord:

int sampleRateInHz = 8000;

int audioEncodingBits = AudioFormat.ENCODING_PCM_16BIT;

int recordBufferSize = AudioRecord.getMinBufferSize(sampleRateInHz, channelConfiguration, audioEncodingBits);

mAudioRecord = new AudioRecord(MediaRecorder.AudioSource.MIC,

sampleRateInHz, channelConfiguration, audioEncodingBits,

recordBufferSize);

先说AudioRecord构造函数最后一个参数recordBufferSize。来自:

getMinBufferSize

//AudioRecord.java

static public int getMinBufferSize(int sampleRateInHz, int channelConfig, int audioFormat) {

int channelCount = 0;

...

//根据channelMask得出channelCount

//这里竟然有个6声道的,估计可以参考下

case AudioFormat.CHANNEL_IN_5POINT1:

channelCount = 6;

...

int size = native_get_min_buff_size(sampleRateInHz, channelCount, audioFormat);

...

}

native_get_min_buff_size对应android_media_AudioRecord_get_min_buff_size:

//android_media_AudioRecord.cpp

static jint android_media_AudioRecord_get_min_buff_size(JNIEnv *env,  jobject thiz,jint sampleRateInHertz, jint channelCount, jint audioFormat) {

size_t frameCount = 0;

audio_format_t format = audioFormatToNative(audioFormat);

status_t result = AudioRecord::getMinFrameCount(&frameCount,

sampleRateInHertz,

format,

audio_channel_in_mask_from_count(channelCount));

return frameCount * channelCount * audio_bytes_per_sample(format);

}

这里传入的format是AudioFormat.ENCODING_PCM_16BIT,根据audio_bytes_per_sample:

//audio.h

static inline size_t audio_bytes_per_sample(audio_format_t format)

{

...

case AUDIO_FORMAT_PCM_16_BIT:

case AUDIO_FORMAT_IEC61937:

size = sizeof(int16_t);

...

}

audio_bytes_per_sample返回的是sizeof(signed short) = 2.

status_t AudioRecord::getMinFrameCount(

size_t* frameCount,

uint32_t sampleRate,

audio_format_t format,

audio_channel_mask_t channelMask)

{

status_t status = AudioSystem::getInputBufferSize(sampleRate, format, channelMask, &size);

...

//这里需要double一下

// We double the size of input buffer for ping pong use of record buffer.

// Assumes audio_is_linear_pcm(format)

if ((*frameCount = (size * 2) / (audio_channel_count_from_in_mask(channelMask) *

audio_bytes_per_sample(format))) == 0) {

ALOGE("Unsupported configuration: sampleRate %u, format %#x, channelMask %#x",

sampleRate, format, channelMask);

return BAD_VALUE;

}

}

getInputBufferSize直接看hal层:

//audio_hw.c

static size_t get_input_buffer_size(uint32_t sample_rate,

audio_format_t format,

int channel_count,

bool is_low_latency)

{

...

//这里是(8000*20)/1000

size = (sample_rate * AUDIO_CAPTURE_PERIOD_DURATION_MSEC) / 1000;

size *= sizeof(short) * channel_count;

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值