html5 webrtc 录音,HTML5录音实践总结(Preact)

本文详细介绍了如何使用HTML5的WebRTC进行录音,包括获取PCM数据、处理数据、转换成Int16、Base64编码、PCM文件播放、重采样、转换为MP3和WAV格式。还讨论了短时能量计算、Web Worker优化性能、音频存储在IndexedDB以及在WebView中开启WebRTC的方法。
摘要由CSDN通过智能技术生成

获取 PCM 数据

处理 PCM 数据

Float32 转 Int16

ArrayBuffer 转 Base64

PCM 文件播放

重采样

PCM 转 MP3

PCM 转 WAV

短时能量计算

Web Worker优化性能

音频存储(IndexedDB)

WebView 开启 WebRTC

获取 PCM 数据

a53a28a7a71f443ab59b8d7df770857a.png

样例代码:

const mediaStream = await window.navigator.mediaDevices.getUserMedia({

audio: {

// sampleRate: 44100, // 采样率 不生效需要手动重采样

channelCount: 1, // 声道

// echoCancellation: true,

// noiseSuppression: true, // 降噪 实测效果不错

},

})

const audioContext = new window.AudioContext()

const inputSampleRate = audioContext.sampleRate

const mediaNode = audioContext.createMediaStreamSource(mediaStream)

if (!audioContext.createScriptProcessor) {

audioContext.createScriptProcessor = audioContext.createJavaScriptNode

}

// 创建一个jsNode

const jsNode = audioContext.createScriptProcessor(4096, 1, 1)

jsNode.connect(audioContext.destination)

jsNode.onaudioprocess = (e) => {

// e.inputBuffer.getChannelData(0) (left)

// 双通道通过e.inputBuffer.getChannelData(1)获取 (right)

}

mediaNode.connect(jsNode)

简要流程如下:

start=>start: 开始

getUserMedia=>operation: 获取MediaStream

audioContext=>operation: 创建AudioContext

scriptNode=>operation: 创建scriptNode并关联AudioContext

onaudioprocess=>operation: 设置onaudioprocess并处理数据

end=>end: 结束

start->getUserMedia->audioContext->scriptNode->onaudioprocess->end

停止录制只需要把 audioContext 挂在的 node 卸载即可,然后把存储的每一帧数据合并即可产出 PCM 数据

jsNode.disconnect()

mediaNode.disconnect()

jsNode.onaudioprocess = null

PCM 数据处理

通过 WebRTC 获取的 PCM 数据格式是 Float32 的, 如果是双通道录音的话, 还需要增加合并通道

const leftDataList = [];

const rightDataList = [];

function onAudioProcess(event) {

// 一帧的音频PCM数据

let audioBuffer = event.inputBuffer;

leftDataList.push(audioBuffer.getChannelData(0).slice(0));

rightDataList.push(audioBuffer.getChannelData(1).slice(0));

}

// 交叉合并左右声道的数据

function interleaveLeftAndRight(left, right) {

let totalLength = left.length + right.length;

let data = new Float32Array(totalLength);

for (let i = 0; i < left.length; i++) {

let k = i * 2;

data[k] = left[i];

data[k + 1] = right[i];

}

return data;

}

Float32 转 Int16

const float32 = new Float32Array(1)

const int16 = Int16Array.from(

float32.map(x => (x > 0 ? x * 0x7fff : x * 0x8000)),

)

arrayBuffe

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值