JavaScript实现页面中录音功能的方法


Posted in Javascript onJune 04, 2019

前言

页面中实现录音需要使用浏览器提供的 Media​Recorder API,所以前提是需要浏览器支持 MediaStream Recording 相关的功能。

以下代码默认工作在 Chrome 环境中。

准备页面

首先准备一个页面,其中内容很简单,一个录音按钮,一个用于播放的 <audio> 标签。

<!DOCTYPE html>
<html lang="en">
<head>
 <meta charset="UTF-8">
 <meta name="viewport" content="width=device-width, initial-scale=1.0">
 <meta http-equiv="X-UA-Compatible" content="ie=edge">
 <title>audio record</title>
</head>
<body>
 <div class="app">
  <button class="record-btn">record</button>
  <audio controls class="audio-player"></audio>
 </div>
 <script src="./recorder.js"></script>
</body>
</html>

获取录音权限

因为录音需要使用设备的话筒,所以第一步应该是向用户索要录音的权限。这是通过 Media​Devices​.get​User​Media()
来完成的,其用法为:

var promise = navigator.mediaDevices.getUserMedia(constraints);

其中 constraints 为需要获取的权限列表,这里只需要指定音频 audio 即可。

其返回是个 Promise,因为用户何时进行授权是不确定的。通过在 Promise 的回调中进行授权成功或失败的处理。

在使用前需要判断浏览器是否已经支持相应的 API,此时得到如下的代码:

if (navigator.mediaDevices.getUserMedia) {
 const constraints = { audio: true };
 navigator.mediaDevices.getUserMedia(constraints).then(
 stream => {
  console.log("授权成功!");
 },
 () => {
  console.error("授权失败!");
 }
 );
} else {
 console.error("浏览器不支持 getUserMedia");
}

其中成功回调里得到的入参 stream 为 MediaStream 对象。

此时运行后可看到浏览器展示出了让用户授权使用麦克风的提示。

JavaScript实现页面中录音功能的方法

向用户索要麦克风使用权限

创建录音实例

将上一步获取到的 MediaStream 传入 Media​Recorder 的构造器创建一个录音器的实例。

var mediaRecorder = new MediaRecorder(stream);

启动录音

通过监听页面中录音按钮的点击来启动录音。

const recordBtn = document.querySelector(".record-btn");
const mediaRecorder = new MediaRecorder(stream);
recordBtn.onclick = () => {
 mediaRecorder.start();
 console.log("录音中...");
};

MediaRecorder 实例上有个 state 状态,可用来判断录音器当前的活动状态,总共有三种值:

  • inactive:处于休息状态,要么是没开始,要么是开始后已经停止。
  • recording:录音中
  • paused:已经开始,但被暂停了,不是停止也没有被恢复。

所以通过这个状态,我们可以实现再次点击按钮时,结束录音。

recordBtn.onclick = () => {
 if (mediaRecorder.state === "recording") {
  mediaRecorder.stop();
  recordBtn.textContent = "record";
  console.log("录音结束");
 } else {
  mediaRecorder.start();
  console.log("录音中...");
  recordBtn.textContent = "stop";
 }
 console.log("录音器状态:", mediaRecorder.state);
};

音频数据的获取

上面按钮处理来自用户的交互,只负责启动或停止录音。音频的数据还是从 Media​Recorder 实例上通过监听其相应的事件来完成的。

当录音开始时,会触发其 MediaRecorder.ondataavailable 事件,从该事件回调的入参为 BlobEvent,从它身上取到 event.data 便是我们需要的音频数据。因为数据是一段一段产生的,所以需要暂存到一个数组中。

const chunks = [];
mediaRecorder.ondataavailable = function(e) {
 chunks.push(e.data);
};

目前为止完成的代码应该是这样的:

 recorder.js

JavaScript实现页面中录音功能的方法

录音状态的查看

录音结束及音频的播放

通过监听 MediaRecorder.onstop 事件,将收集好的音频数据创建成Blob 对象,然后 通过 URL.createObjectURL 创建成 HTML 中 <audio> 标签可使用的资源链接。

mediaRecorder.onstop = e => {
 var blob = new Blob(chunks, { type: "audio/ogg; codecs=opus" });
 chunks = [];
 var audioURL = window.URL.createObjectURL(blob);
 audio.src = audioURL;
};

其中,在使用完收到到的音频数据后,将 chunks 置空方便下次录音时使用。

目前为止完成的代码应该是这样的:

 recorder.js

运行

完成上面步骤后,实现了一个简单的录音功能,可通过此地址在线体验。完整的代码可在仓库 wayou/audio-recorder 中获取到。

相关资源

  • Media​Recorder
  • MediaRecorder.onstop
  • URL.createObjectURL

总结

以上就是这篇文章的全部内容了,希望本文的内容对大家的学习或者工作具有一定的参考学习价值,谢谢大家对三水点靠木的支持。

Javascript 相关文章推荐
xss文件页面内容读取(解决)
Nov 28 Javascript
Jquery下:nth-child(an+b)的使用注意
May 28 Javascript
ASP.NET jQuery 实例9  通过控件hyperlink实现返回顶部效果
Feb 03 Javascript
javascript作用域链(Scope Chain)用法实例解析
Nov 30 Javascript
JavaScript实现仿淘宝商品购买数量的增减效果
Jan 22 Javascript
jQuery中通过ajax的get()函数读取页面的方法
Feb 29 Javascript
javascript闭包概念简单解析(推荐)
Jun 03 Javascript
jQuery提示插件qTip2用法分析(支持ajax及多种样式)
Jun 08 Javascript
详解Angular 自定义结构指令
Jun 21 Javascript
使用VScode 插件debugger for chrome 调试react源码的方法
Sep 13 Javascript
Vuex,iView UI面包屑导航使用扩展详解
Nov 04 Javascript
Vue SPA 首屏优化方案
Feb 26 Vue.js
vue elementUI 表单校验功能之数组多层嵌套
Jun 04 #Javascript
小程序根据手机机型设置自定义底部导航距离
Jun 04 #Javascript
js回文数的4种判断方法示例
Jun 04 #Javascript
Vue对象赋值视图不更新问题及解决方法
Jun 03 #Javascript
在 Vue 应用中使用 Netlify 表单功能的方法详解
Jun 03 #Javascript
JavaScript之数组扁平化详解
Jun 03 #Javascript
JavaScript从原型到原型链深入理解
Jun 03 #Javascript
You might like
PHP数据流应用的一个简单实例
2012/09/14 PHP
学习php设计模式 php实现单例模式(singleton)
2015/12/07 PHP
PHP正则删除HTML代码中宽高样式的方法
2017/06/12 PHP
Ext JS Grid在IE6 下宽度的问题解决方法
2009/02/15 Javascript
javascript Demo模态窗口
2009/12/06 Javascript
jquery 注意事项与常用语法小结
2010/06/07 Javascript
JavaScript学习笔记(一) js基本语法
2011/10/25 Javascript
分析Node.js connect ECONNREFUSED错误
2013/04/09 Javascript
javascript用户注册提示效果的简单实例
2013/08/17 Javascript
JavaScript实现的图像模糊算法代码分享
2014/04/22 Javascript
js用Date对象的setDate()函数对日期进行加减操作
2014/09/18 Javascript
javascript实现数字倒计时特效
2016/03/30 Javascript
AngularJs 60分钟入门基础教程
2016/04/03 Javascript
基于JS组件实现拖动滑块验证功能(代码分享)
2016/11/18 Javascript
用jQuery.ajaxSetup实现对请求和响应数据的过滤
2016/12/20 Javascript
详解JavaScript的闭包、IIFE、apply、函数与对象
2016/12/21 Javascript
js实现简单的计算器功能
2017/01/16 Javascript
JavaScript你不知道的一些数组方法
2017/08/18 Javascript
vue使用iframe嵌入网页的示例代码
2020/06/09 Javascript
js+html5实现手机九宫格密码解锁功能
2018/07/30 Javascript
如何在JavaScript中优雅的提取循环内数据详解
2019/03/04 Javascript
js实现三角形粒子运动
2020/09/22 Javascript
跟老齐学Python之Import 模块
2014/10/13 Python
python的mysqldb安装步骤详解
2017/08/14 Python
python实现移位加密和解密
2019/03/22 Python
python类中super() 的使用解析
2019/12/19 Python
python中把元组转换为namedtuple方法
2020/12/09 Python
python中编写函数并调用的知识点总结
2021/01/13 Python
Spartoo荷兰:鞋子、包包和服装
2018/07/12 全球购物
测绘专业大学生职业生涯规划书
2014/02/10 职场文书
推广普通话标语
2014/06/27 职场文书
英文道歉信
2015/01/20 职场文书
实施意见格式范本
2015/06/05 职场文书
创业计划书之美容店
2019/09/16 职场文书
详解Python函数print用法
2021/06/18 Python
ant design charts 获取后端接口数据展示
2022/05/25 Javascript