Android使用AudioRecord录制通话遇异常:未初始化时调用startRecording()
解决Android 6.0/7.0上AudioRecord使用VOICE_CALL源录制通话失败的问题
我之前也踩过一模一样的坑!这种情况在Android 6.0(API 23)和7.0(API 24)的设备上特别普遍,核心原因绕不开系统权限、厂商定制限制以及AudioSource的特殊约束,咱们一步步拆解解决:
为什么VOICE_CALL会抛出IllegalStateException?
- 系统权限层级限制:从Android 6.0开始,
RECORD_AUDIO成为危险权限,你既要在Manifest里声明,还要在运行时动态申请。但就算拿到这个权限,VOICE_CALL属于系统级专属音频源,普通第三方APP默认无法获取访问权限——很多厂商(比如华为、小米)在定制系统里直接锁死了这个权限,底层根本不会给APP初始化AudioRecord的机会。 - 初始化未完成就调用startRecording:当你指定
MediaRecorder.AudioSource.VOICE_CALL时,系统因为权限或硬件不支持,压根没成功初始化AudioRecord对象,这时候调用startRecording()自然会抛出「未初始化」的异常。
替代方案:用MIC源实现通话录制的折中思路
你提到MIC源能正常工作,但只能录自己的声音对吧?要实现双向通话录制,有几个可行的方向:
- 扬声器+MIC组合录制:把通话切换到扬声器模式,让MIC同时捕捉你和对方的声音。缺点是隐私性差,环境噪音会被一并录入,但这是老版本系统最容易实现的方案。
- ROOT设备下监听系统音频流:如果目标用户是ROOT过的设备,可以尝试监听
VOICE_COMMUNICATION或系统音频输出流,但这种方法兼容性极差,而且ROOT权限会把大量普通用户挡在门外。 - 引导用户使用系统自带录制功能:很多厂商在6.0/7.0系统里保留了自带的通话录制功能,你可以做个引导,让用户开启系统原生录制,比第三方APP折腾靠谱得多。
关键代码注意事项
不管用哪种方案,动态权限申请是必须的,给你一段基础的权限检查代码:
// 检查RECORD_AUDIO权限 if (ContextCompat.checkSelfPermission(this, Manifest.permission.RECORD_AUDIO) != PackageManager.PERMISSION_GRANTED) { ActivityCompat.requestPermissions(this, new String[]{Manifest.permission.RECORD_AUDIO}, REQUEST_RECORD_AUDIO_PERMISSION); }
另外,初始化AudioRecord时一定要先校验状态,避免直接调用startRecording:
AudioRecord audioRecord = new AudioRecord(MediaRecorder.AudioSource.MIC, 44100, AudioFormat.CHANNEL_IN_MONO, AudioFormat.ENCODING_PCM_16BIT, bufferSize); if (audioRecord.getState() != AudioRecord.STATE_INITIALIZED) { Log.e("RecordError", "AudioRecord初始化失败,请检查权限或设备兼容性"); return; } // 确认初始化成功后再启动录制 audioRecord.startRecording();
最后提醒
Android不同版本、不同厂商对通话录制的限制差异极大,尤其是6.0-7.0这个区间,隐私管控严格的厂商直接禁用了第三方APP的通话录制能力。如果你的APP核心功能是通话录制,建议在启动时就检测系统版本和权限情况,给用户明确的提示,避免出现崩溃或无响应的尴尬情况。
内容的提问来源于stack exchange,提问作者hisham
相关产品推荐
相关产品推荐

