js实现音频的录制
js实现音频的录制
·
<!DOCTYPE html>
<html lang="zh">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>录音</title>
</head>
<body>
<h1>录音</h1>
<div>
<button onclick="getDeviceList()">获取设备列表</button>
<button onclick="checkSupportType()">检查支持的类型</button>
<button id="start">开始录音</button>
<button id="pause">暂停录音</button>
<button id="resume">继续录音</button>
<button id="stop">停止录音</button>
<button id="play">播放录音</button>
<button id="download">下载录音</button>
</div>
<script>
const start = document.getElementById("start");
const pause = document.getElementById("pause");
const resume = document.getElementById("resume");
const stop = document.getElementById("stop");
const play = document.getElementById("play");
const download = document.getElementById("download");
const audioType = 'audio/webm';//audio/ogg和audio/webm两种格式通用
// 录音相关变量
let mediaRecorder;
let chunks = []
init();
//初始化
function init() {
//禁用按钮
setDisabled(start, startHandler);
setDisabled(pause, pauseHandler);
setDisabled(resume, resumeHandler);
setDisabled(stop, stopHandler);
setDisabled(play, playHandler);
setDisabled(download, downloadHandler);
// 检查浏览器兼容性
if (!navigator.mediaDevices || !navigator.mediaDevices.getUserMedia) {
alert("您的浏览器不支持录音功能,请更换浏览器后重试!");
return;
}
setEnabled(start, startHandler);
}
/**
* 获取设备列表
*/
function getDeviceList() {
if (!navigator.mediaDevices || !navigator.mediaDevices.enumerateDevices) {
console.log("enumerateDevices() not supported.");
} else {
navigator.mediaDevices
.enumerateDevices()
.then((devices) => {
devices.forEach((device) => {
//console.log(device);
//device.kind: videoinput audioinput audiooutput
console.log(`${device.kind}: ${device.label} id = ${device.deviceId}`);
});
})
.catch((err) => {
console.log(`${err.name}: ${err.message}`);
});
}
}
/**
* 元素禁用
*/
function setDisabled(element, removeFunction) {
element.disabled = true;
if (removeFunction) {
element.removeEventListener("click", removeFunction);
}
}
/**
* 元素启用
*/
function setEnabled(element, addFunction) {
console.log('setEnabled');
console.log(element);
element.disabled = false;
if (addFunction) {
element.addEventListener("click", addFunction);
}
}
function checkSupportType() {
const types = [
"video/webm",
"audio/webm",
"video/webm;codecs=vp8",
"video/webm;codecs=daala",
"video/webm;codecs=h264",
"audio/webm;codecs=opus",
"video/mp4",
];
for (const type of types) {
let res = MediaRecorder.isTypeSupported(type)
//true不一定表示一定可以使用
console.log(`${type}是否支持:${res}`);
}
}
/**
* 开始录音
*/
function startHandler() {
//开始录音
const constraints = { audio: true }
//const constraints = { audio: true, video: true }
//https://developer.mozilla.org/zh-CN/docs/Web/API/MediaDevices/getUserMedia
navigator.mediaDevices.getUserMedia(constraints).then((stream) => {
//mimeType支持webm和ogg,ogg不需要设置options的mineType
let options = {};
if (audioType == "audio/webm") {
options = { mimeType: 'audio/webm; codecs=opus' };
}
mediaRecorder = new MediaRecorder(stream, options);
//设置的mimeType类型
console.log(mediaRecorder.mimeType);
//状态inactive recording paused
console.log(mediaRecorder.state);
//navigator.mediaDevices.getUserMedia的stream 对象
console.log(stream);
//视频采用的编码比率
console.log(mediaRecorder.videoBitsPerSecond);
//音频采用的编码比率
console.log(mediaRecorder.audioBitsPerSecond);
if (mediaRecorder.state != "inactive") {
alert('麦克风正在使用中,请先关闭再试!');
return;
}
mediaRecorder.ondataavailable = (e) => {
console.log('接收到收据');
chunks.push(e.data)
}
chunks = [];
mediaRecorder.start();
console.log('开始录音');
setDisabled(start, startHandler);
setEnabled(pause, pauseHandler);
setEnabled(stop, stopHandler);
setDisabled(resume, resumeHandler);
setDisabled(play, playHandler);
setDisabled(download, downloadHandler);
}).catch((err) => {
console.log(err.name);
switch (err.name) {
case "AbortError":
alert("设备无法使用");
break;
case "NotAllowedError":
alert("您拒绝了访问您的设备!");
break;
case "NotFoundError":
alert("未找到设备");
break;
case "NotReadableError":
alert("设备不可读");
break;
case "OverconstrainedError":
alert("无法满足要求");
break;
case "SecurityError":
alert("安全错误");
break;
case "TypeError":
alert("类型错误");
break;
case "NotSupportedError":
alert("浏览器不支持");
break;
}
})
}
/**
* 暂停录音
*/
function pauseHandler() {
if (!mediaRecorder || mediaRecorder.state != "recording") {
alert('未开始录音');
return;
}
mediaRecorder.pause();
console.log('暂停录音');
setDisabled(start, startHandler);
setDisabled(pause, pauseHandler);
setDisabled(stop, stopHandler);
setEnabled(resume, resumeHandler);
setDisabled(play, playHandler);
setDisabled(download, downloadHandler);
}
/**
* 继续录音
*/
function resumeHandler() {
if (!mediaRecorder || mediaRecorder.state != "paused") {
alert('未暂停录音');
return;
}
mediaRecorder.resume();
console.log('继续录音');
setDisabled(start, startHandler);
setEnabled(pause, pauseHandler);
setEnabled(stop, stopHandler);
setDisabled(resume, resumeHandler);
setDisabled(play, playHandler);
setDisabled(download, downloadHandler);
}
/**
* 停止录音
*/
function stopHandler() {
if (!mediaRecorder || mediaRecorder.state != "recording") {
alert('未开始录音');
return;
}
mediaRecorder.stop();
console.log('停止录音');
setEnabled(start, startHandler);
setDisabled(pause, pauseHandler);
setDisabled(stop, stopHandler);
setDisabled(resume, resumeHandler);
setEnabled(play, playHandler);
setEnabled(download, downloadHandler);
}
/**
* 播放录音
*/
function playHandler() {
if (!chunks || chunks.length <= 0) {
alert('未有录音信息');
return;
}
console.log('播放录音');
// 创建音频文件
const audioBlob = new Blob(chunks, { type: audioType });
var audio = new Audio();
audio.src = URL.createObjectURL(audioBlob);
// 监听音频播放完毕的事件
audio.addEventListener('ended', function () {
// 销毁<audio>元素
console.log('音频播放完毕,销毁<audio>元素');
audio = null;
});
audio.play();
}
/**
* 下载录音
*/
function downloadHandler() {
if (!chunks || chunks.length <= 0) {
alert('未有录音信息');
return;
}
console.log('下载录音');
// 创建音频文件
const audioBlob = new Blob(chunks, { type: audioType });
const a = document.createElement('a');
a.href = URL.createObjectURL(audioBlob);
let audioExt = 'webm';
if (audioType == 'audio/webm') {
audioExt = 'webm';
}
if (audioType == 'audio/ogg') {
audioExt = 'ogg';
}
a.download = `recording_${new Date().toISOString().replace(/[:.]/g, '-')}.${audioExt}`;
document.body.appendChild(a);
a.click();
document.body.removeChild(a);
}
</script>
</body>
</html>
支持点击录制、暂停、继续录制、停止录制、播放、下载的功能,可以下载试试效果~~

参考
https://developer.mozilla.org/zh-CN/docs/Web/API/MediaDevices/getUserMedia
https://developer.mozilla.org/zh-CN/docs/Web/API/MediaStream
https://developer.mozilla.org/zh-CN/docs/Web/API/MediaRecorder
https://gitee.com/qxscj/js-demo/blob/master/html+css/38-1.html
魔乐社区(Modelers.cn) 是一个中立、公益的人工智能社区,提供人工智能工具、模型、数据的托管、展示与应用协同服务,为人工智能开发及爱好者搭建开放的学习交流平台。社区通过理事会方式运作,由全产业链共同建设、共同运营、共同享有,推动国产AI生态繁荣发展。
更多推荐

所有评论(0)