WebRTC-检测可用的音视频设备

音视频设备检测

在打开摄像头或者麦克风的时候,需要首先对其进行检测,检测的内容包括:

  • 电脑/手机上都有哪些音视频设备?
  • 选中的音视频设备是否可用?

WebRTC处理过程

本节主要讲解图中红色框内容。

音频有采样率和采样大小的概念。

视频通过摄像头采集光照后通过RGB表示,每个通道8位,最终就是24位真彩色。

RGB图像只是临时数据,因为最终的图像数据还要进行压缩、传输,而编码器一般使用的输入格式为YUV I420,所以在摄像头内部还有一个专门的模块用于将RGB图像转化为YUV格式的图像。

YUV是一种色彩编码方法, 主要用于电视系统以及模拟视频领域,将色度信息(Y)与色彩信息(UV)分离,即使没有UV信息一样可以显示完整的图像,只不过是黑白的,这样的设计很好地解决了彩色电视机与黑白电视的兼容问题。

WebRTC设备管理的基本概念

MediaDevices, 该接口提供了访问(连接到计算机上的)媒体设备(如摄像头、麦克风)以及截取屏幕的方法。

MediaDeviceInfo, 它表示的是每个输入/输出设备的信息,包含以下三个重要的属性:

  • deviceId: 设备的唯一标识
  • label: 设备名称
  • kind: 设备种类,可用于识别出是音频设备还是视频设备,是输入设备还是输出设备

注:出于安全原因,除非用户已被授予访问媒体设备的权限(要想授予权限需要使用HTTPS请求),后者label字段始终为空。label可以用作指纹识别机制的一部分,以识别是否是合法用户。

Promise,是一种JavaScript异步处理机制。其思想是,首先执行指定的业务逻辑,而不管逻辑的对错,然后再根据结果做具体的操作:如果成功了做些什么,失败了做些什么。

如何检测音视频设备

通过调用MediaDevices的enumerateDevices()方法就可以获取到媒体输入和输出设备列表,列如:麦克风、相机、耳机等。该函数返回的是一个Promise对象,我们只需要向它的then部分传入一个函数,就可以通过该函数获得所有的音视频设备信息了。

传入的函数有一个参数,是一个MediaDeviceInfo类型的数组,用来存放WebRTC获取到的每一个音视频设备信息。

...

// 判断浏览器是否支持这些 API
if (!navigator.mediaDevices || !navigator.mediaDevices.enumerateDevices) {
  console.log("enumerateDevices() not supported.");
  return;
}

// 枚举 cameras and microphones.
navigator.mediaDevices.enumerateDevices()  // 获取音视频设备列表,返回一个Promise对象
.then(function(deviceInfos) { // 如果返回Promise对象成功,就执行then中的函数

  // 打印出每一个设备的信息
  deviceInfos.forEach(function(deviceInfo) {
    console.log(deviceInfo.kind + ": " + deviceInfo.label +
                " id = " + deviceInfo.deviceId);
  });
})
.catch(function(err) {  // 获取音视频设备失败
  console.log(err.name + ": " + err.message);
});

可以利用MediaDeviceInfo结构中的kind字段,将设备分类为音频设备或视频设备,可以再细分为输入设备和输出设备。对于区分的音频设备和视频设备,每种不同种类的设备还会设置各自的默认设备

需要调用两次getUserMedia API进行设备检测,即先排查视频设备,然后再排查音频设备。

  • 调用getUserMedia API只采集视频数据并将其展示出来,如果用户能看到自己的视频,说明视频设备是有效的;反之,设备无效,继续选择不同的视频设备进行重新检测。

  • 如果视频检测通过,再次调用getUserMedia API时,则只采集音频数据,由于音频数据不能直接演示,所以需要使用JavaScript中的AudioContext对象,将采集得到的音频计算后绘制到页面上,这样用户就可以确定音频设备是否可用。

注:本文是《从0打造音视频直播系统》的读书笔记,配套代码地址GitHub。本文仅限个人学习,请勿用作商业用途,谢谢。

强烈建议购买李超老师的课,扫描下方二维码还有优惠:

Note: Cover Picture