
本文共 2793 字,大约阅读时间需要 9 分钟。
webrtc 获取音视频设备
通过enumerateDevices()获取到所有的音频和视频设备,返回的值是一个promise,这是javaScript中一个特有的对象,在promsie中有一个特有的结构体:MediaDevicesInfo,在这个结构体中存放了非常重要的几个信息,deviceid为这个设备的唯一标志符,第二个label就是设备的名字,比如内置音频设备,内置音频输入设备等
首先解释一个背景,JavaScript中是使用单线程去处理整个逻辑的,为了防止被阻塞,大量使用了异步调用,而promise就是异步调用的一种方式,也是目前大家比较认可的一种方式,下面了解一下它的基本思想,首先创建一个promise时要传给它一个handle的处理函数,handle的处理函数处理它的主要逻辑,处理完成后,如果成功了,就会调用resolve这个函数,如果失败了就会调用reject这个函数,这样就创建了一个promise,promise可以注册两个方法,then和catch,then就是当整个逻辑处理成功后,会收到on_resolve 这个处理事件,当收到这个事件时,就可以处理一些逻辑,catch就是当失败了,收到失败事件的时候,处理一些失败的逻辑,当然then是依赖式的,如果失败了还可以返回一个promise,可以继续then,一直做好几个处理,它的核心是在prmise里存放了几个状态,第一个是没有执行的handing的状态,第二个当开始执行handle这个逻辑时的运行状态,当处理成功后进入resolve里,会改为成功状态,如果失败了,进入到reject里,把它设置为出错状态。当你注册这个函数之后,就可以根据promise里面的状态机,它如果成功了,就可以调用then里面注册的方法,如果失败了,就可以调用catch注册的方法,这就是它的基本逻辑。
我们接着看enumerateDevices这个函数,在这个函数里就运用了promise,注册了一个handle,所以当这个函数执行的时候就返回一个promise,在我们用的时候,拿到这个promise,我们就给他注册两个函数,一个是then方法,一个是catch方法,如果成功了,它就会调用我们注册的then调用我们成功的逻辑,如果失败了,就会调用失败的逻辑。
在页面中显示获取到的设备
目录结构
client.js
'use strict'var audioSource = document.querySelector("select#audioSource");var audioOutput = document.querySelector("select#audioOutput");var videoSource = document.querySelector("select#videoSource");//首次运行引导用户,信任域名var first = window.localStorage.getItem('first');if(first == null ){ if (navigator.mediaDevices.getUserMedia) { //调用用户媒体设备, 访问摄像头 var p = navigator.mediaDevices.getUserMedia({ audio: true, video: true }); } else { alert('不支持访问用户媒体'); }}//判断方法是否存在if(!navigator.mediaDevices || !navigator.mediaDevices.enumerateDevices){ console.log('enumerateDevices is not supported!');}else { //返回是一个promise 有then 成功 获取设备 catch 失败 navigator.mediaDevices.enumerateDevices() .then(gotDevices) .catch(handleError);}function gotDevices(deviceInfos){ //function(deviceInfo) 匿名函数 deviceInfos.forEach( function(deviceInfo){ console.log(deviceInfo.kind + ": label = " + deviceInfo.label + ": id = " + deviceInfo.deviceId + ": groupId = " + deviceInfo.groupId); var option = document.createElement('option'); option.text = deviceInfo.label; option.value = deviceInfo.deviceId; if(deviceInfo.kind === 'audioinput'){ audioSource.appendChild(option); }else if(deviceInfo.kind === 'audiooutput'){ audioOutput.appendChild(option); }else if(deviceInfo.kind === 'videoinput'){ videoSource.appendChild(option); } });}function handleError(err){ console.log(err.name + " : " + err.message);}
index.js
WebRTC get audio and video devices
页面显示效果:
其中:第1列显示的是kind:设备种类,分别由audioinput,audiooutput,videoinput,
第2列显示的是label:设备名字;
第3列显示的是deviceID:设备id
第4列显示的是goupID:两个设备groupID相同说明是同一个设备
如果使用HTTP协议:
则获取不到label id,
发表评论
最新留言
关于作者
