关于前端:移动端实现HTML5录音踩坑指南系统播放音量变小一些机型录音断断续续-MediaRecorder和AudioWorklet

H5录音见坑填坑

在2022-06-19那天,Recorder H5录音开源库(https://github.com/xiangyuecn/Recorder)群里有用户反馈手机上录音有bug,前后反馈过去几段测试过程残缺录像;剖析后初步发现在他那个手机上体现的确是断断续续的,从而音质十分差;此版本的Recorder采纳的浏览器AudioContext.createScriptProcessorAudioWorklet 接口对getUserMedia返回的音频流进行音频采集,在线测试地址:https://xiangyuecn.gitee.io/recorder/。

但用另外一个录音库 collab-project/videojs-record 录制的却没有这个问题,过后初步剖析了下一,发现collab-project在手机上应用的是MediaStreamRecorder来录制webm格局音频,底层应用的是浏览器的MediaRecorder接口对getUserMedia返回的音频流进行音频采集。

采纳MediaRecorder采集音频

曾经晓得了浏览器的MediaRecorder接口录制进去的音频不会有ScriptProcessorAudioWorklet 接口录制进去的那种断断续续景象;并且前面两个除了在挪动端外,在PC端录制进去的音频也会有爆音的景象,只不过要距离比拟久才偶然呈现,对音质影响不显著,这些问题MediaRecorder通通没有!

因而很有必要应用MediaRecorder来进行录音,来取得更好的音质ScriptProcessorAudioWorklet 靠边站。

音频格式:WebM和PCM

MediaRecorder个别录制进去的是WebM格局的音视频文件,可通过MediaRecorder.isTypeSupported办法判断反对的格局:

[ //胡乱拼接一些类型 不同浏览器反对的不同
    'audio/webm; codecs=opus' //都反对的格局
    ,'audio/webm; codecs=pcm' //Chrome/Safari反对
    ,'audio/pcm'
    ,'audio/webm; codecs=wav'
    ,'audio/wav'
    ,'audio/webm; codecs=ogg'
    ,'audio/ogg' //FireFox反对
].forEach(v=>console.log( MediaRecorder.isTypeSupported(v) +" : "+ v ))

能够看到MediaRecorder对opus编码的WebM格局反对的最好;pcm编码的WebM在Chrome/Safari里失去了反对;wav、ogg不做参考。

Recorder只想得到浏览器采集到的PCM音频数据(易于转换成其余格局,比方mp3、wav),或者能简略的解码失去PCM也行,opus编码的WebM对咱们须要实现的录音性能帮忙不大;好在还有pcm编码的WebM反对,简略的从WebM容器中提取出PCM即可,目前能反对在Chrome/Safari浏览器上运行就能解决绝大部分用户终端的适配。

从WebM封装容器中提取PCM数据

MediaRecorder录制了audio/webm; codecs=pcm数据后,会依据设定的时长距离,将音频片段通过回调传给js;好在WebM容器格局简略,很好的做到实时的提取PCM数据。

WebM格局(.webm.weba)和常见的 .mkv 视频格式都应用的:Matroska开源多媒体容器规范;Matroska封装格局官网文档:https://www.matroska.org/inde…。

学习一下Matroska文档,就很容易提取出WebM中蕴含的音频轨道数据了,PCM编码的WebM中的音频轨道中的数据个别为32位浮点数pcm数据。

我写了一段解析和提取WebM音频的代码,代码正文外面具体介绍了WebM格局合成过程,源代码在这里 (能够间接测试运行)。

录音的兼容性

MediaRecorder只反对在Chrome/Safari里对getUserMedia返回的音频流录制成audio/webm; codecs=pcm格局,其余浏览器FireFox不反对此编码的录制,须要降级应用 ScriptProcessorAudioWorklet 来对getUserMedia音频流的采集录制。

好在这些性能在Recorder H5录音开源库都是反对的,降级加一个MediaRecorder反对也用不了多少代码,不论是MediaRecorder还是ScriptProcessorAudioWorklet,Recorder通通实时的返回16位PCM数据;有了PCM数据后:实时转码、实时上传、语音辨认、音频可视化等等性能均可实现。

所有已失常反对getUserMedia的浏览器均能录音,录音音质依据浏览器反对状况主动优先采纳最佳音频采集计划;反对的包含但不限于:Chrome、Firefox、Safari、iOS 14.3+、Android WebView、腾讯Android X5内核(QQ、微信、小程序WebView)、大部分2021年后更新的Android手机自带浏览器。

困扰已久的H5录音时零碎播放音量变小的问题

从Recorder开源之初就发现了这个问题,手机上只有关上了录音,同时播放音频的时候,零碎声音会十分的小,甚至跑到了听筒播放,但有时又失常 毫无法则,几年始终大刀阔斧,基本没有文档有这方面的形容或文章参考。

在本次Recorder降级反对MediaRecorder的时候,因为须要getUserMedia参数外面设置audio的采样率sampleRate,棘手就把noiseSuppression降噪、echoCancellation回声打消都默认设成了false,没想到测试的时候再也没有零碎播放声音变小的景象。

降噪、回声打消这两个参数很早以前就在测试页面中提供了设置选项,不过之前默认是未配置状态,以前也常常设为false进行测试,居然没有发现这些参数能解决零碎音量变小。

最初通过重复测试,只有noiseSuppression+echoCancellation同时失效时,关上录音后再播放音频,零碎音量肯定会变小,很惨的是getUserMedia只有你没有配置这两个参数,默认就是同时开启的;只有你给这两参数任意一个设为false,或者都设为false,就不会影响手机零碎音量。

目前Recorder已默认禁用了noiseSuppression和echoCancellation,应用原声录制(低音甜、中音准、高音沉,总之一句话就是通透 — 陈永仁(梁朝伟 饰))。


Recorder H5录音开源库:https://github.com/xiangyuecn/Recorder

Recorder H5在线测试页:https://xiangyuecn.gitee.io/recorder/
【完】

评论

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注

这个站点使用 Akismet 来减少垃圾评论。了解你的评论数据如何被处理