AudioRecord类优点是能录制到缓冲区,能够实现边录边播(AudioRecord + AudioTrack)以及对音频的实时处理(如QQ电话)。缺点是输出是PCM格式的原始采集数据,如果直接保存成音频文件,不能够被播放器播放,所以必须用代码实现数据编码以及压缩。
使用AudioRecord录音的基本步骤是:确定录音参数、申请缓冲区、创建AudioRecord对象、开始录制、循环读取数据到缓冲区并处理数据、停止录制、释放资源。
需要确定的录音参数包括:采样率、声道、格式。申请缓冲区时需要根据录音参数计算最小缓冲区大小。有了缓冲区以后才能创建AudioRecord对象。录制过程中,需要不停地读取采样到的音频数据,并进行处理。流程和对应的代码如下图:
下面编写一个例子,用AudioRecord采集音频数据,并以原始PCM格式存入文件。读取数据和处理数据是需要循环进行的操作,所以放入单独线程执行。例子运行在Android8.0以上。
例子界面和主要代码如下:
因为要录音,所以在配置文件里需要声明录音权限。同时,Android将文件写入应用在外部存储上的私有目录不需要再申请读写存储的权限。
<uses-permission android:name="android.permission.RECORD_AUDIO" />
同时,使用AudioRecord录音需要动态申请权限,即在实际录音时需要检查用户是否允许应用使用录音权限。如果没有允许,就弹出一个对话框询问用户。代码如下:
if (ActivityCompat.checkSelfPermission(this, Manifest.permission.RECORD_AUDIO) != PackageManager.PERMISSION_GRANTED) {
ActivityCompat.requestPermissions(this, new String[]{Manifest.permission.RECORD_AUDIO}, 1);
return;
}
这里用到的AudioRecord类的主要方法有:
1)构造函数:AudioRecord(int audioSource, int sampleRateInHz, int channelConfig, int audioFormat, int bufferSizeInBytes)
- audioSource:音频来源,一般取麦克风MediaRecorder.AudioSource.MIC
- sampleRateInHz:采样率
- channelConfig:声道配置,一般取AudioFormat.CHANNEL_IN_MONO 、CHANNEL_IN_DEFAULT、CHANNEL_IN_STEREO等
- audioFormat:音频格式,取AudioFormat.ENCODING_PCM_16BIT、AudioFormat.ENCODING_PCM_8BIT
- bufferSizeInBytes:缓冲区字节数,不得小于getMinBufferSize计算出的最小缓冲区大小
2)static int getMinBufferSize(int sampleRateInHz, int channelConfig, int audioFormat):计算最小缓冲区大小,参数同构造函数中三个参数。
3)从硬件读取音频数据保存到缓冲区有三个方法,都返回读取的数据个数
- int read(byte[] audioData, int offsetInBytes, int sizeInBytes)
- int read(ByteBuffer audioBuffer, int