0
点赞
收藏
分享

微信扫一扫

WebRTC基础实践 - 4. 获取摄像头的视频流


本节内容

在本节课程中, 我们将学习以下知识点:


从摄像头(webcam)获取视频流(video stream)控制视频内容的回显通过CSS和SVG处理视频内容。

本节的完整版代码位于 ​​step-01​​ 文件夹中。

HTML代码

在 ​​work​​​ 目录下的 ​​index.html​​​ 文件中, 增加 ​​video​​​ 标签和 ​​script​​ 标签:

<!DOCTYPE html>
<html>
<head>
<title>Realtime communication with WebRTC</title>
<link rel="stylesheet" href="css/main.css" />
</head>

<body>
<h1>Realtime communication with WebRTC</h1>
<!-- 增加的代码在下面这里: -->
<video autoplay playsinline></video>
<script src="js/main.js"></script>
</body>

</html>


注意: 如果有中文字符, 则 ​​.html​​ 文件需要使用 UTF-8 编码保存/另存。


JavaScript代码

在 ​​js​​​ 目录下的 ​​main.js​​ 文件中, 加入以下的代码:

'use strict';

// 本节只需要使用到 video (video: true).
const mediaStreamConstraints = {
video: true
};

// 用于播放视频流stream 的 video元素.
const localVideo = document.querySelector('video');

// Local stream that will be reproduced on the video.
let localStream;

// success 处理函数; by adding the MediaStream to the video element.
function gotLocalMediaStream(mediaStream) {
localStream = mediaStream;
localVideo.srcObject = mediaStream;
}

// error 处理函数; 将 error 信息打印到 console.
function handleLocalMediaStreamError(error) {
console.log('navigator.getUserMedia error: ', error);
}

// 初始化 media stream.
navigator.mediaDevices.getUserMedia(mediaStreamConstraints)
.then(gotLocalMediaStream).catch(handleLocalMediaStreamError);


本教程中的 JavaScript 代码, 都在起始处加上 ​​'use strict';​​ ,这样可以避免很多新手经常碰到的编程错误。

关于严格模式的更多信息, 请参考 ​​ECMAScript 5 Strict Mode, JSON, and More​​。


运行示例

在浏览器中打开对应的 ​​index.html​​ 页面, 效果类似如下:

WebRTC基础实践 - 4. 获取摄像头的视频流_webrtc

当然, 页面中展示的你本地摄像头实时拍摄到的内容。

原理解析

navigator.mediaDevices.getUserMedia(mediaStreamConstraints)
.then(gotLocalMediaStream).catch(handleLocalMediaStreamError);

}

调用 ​​getUserMedia()​​ 方法之后, 浏览器会判断当前域名(domain)是否具有调用摄像头的权限, 如果是第一次请求授权, 则会弹出对话框, 要求用户手动选择允许。 如下图所示:

WebRTC基础实践 - 4. 获取摄像头的视频流_摄像头_02

如果权限验证通过, 则返回 ​​MediaStream​​​ 对象, 可以将该对象赋值给 media 元素的 ​​srcObject​​ 属性:

function gotLocalMediaStream(mediaStream) {
localVideo.srcObject = mediaStream;
}

参数 ​​constraints​​ 可以指定要获取哪些 media 信息。如果不指定, 声音(audio) 默认配置是禁用的, 所以此处实际上只获取了 video 流:

const mediaStreamConstraints = {
video: true
};

还可以加上更多的约束条件, 例如设置视频分辨率:

const hdConstraints = {
video: {
width: {
min: 1280
},
height: {
min: 720
}
}
}

​​MediaTrackConstraints 规范文档​​​ 列出了所有可用的约束类型, 虽然有一些浏览器不兼容其中的某些选项。如果当前选择的摄像头不支持给定的约束选项, 调用 ​​getUserMedia()​​​ 时则会抛出 ​​OverconstrainedError​​ 错误。默认也不会提示用户进行再次授权。

当然, 用户随时可以管理授权信息, 或者切换摄像头, 如下图所示:

WebRTC基础实践 - 4. 获取摄像头的视频流_摄像头_03

各个版本的浏览器界面可能略有不同, 但应该都能找到管理授权的地方。搞不定的就上网搜索。


关于限制不同分辨率的demo, 请参考 ​​https://simpl.info/getusermedia/constraints/​​​, 选择摄像头和麦克风的demo请参考: ​​https://simpl.info/getusermedia/sources/​​。


如果 ​​getUserMedia()​​ 调用成功, 则将摄像头传过来的视频流, 作为 video 的来源:

function gotLocalMediaStream(mediaStream) {
localVideo.srcObject = mediaStream;
}

练习与实践


  • 此处 ​​localStream​​​ 是一个全局变量, 所以可以通过 console 来查看: 打开浏览器控制台, 输入 ​​localStream​​​ 并按回车。 (打开控制台的方式: Windows系统按F12并选择; 或者组合快捷键: ​​Ctrl-Shift-J​​​; Mac系统则是 ​​Command-Option-J​​)。
  • ​localStream.getVideoTracks()​​ 返回的是什么值呢?
  • 查看 constraints 对象: 如果设置为 ​​{audio: true, video: true}​​, 有什么效果呢?
  • video 元素的大小是多少? 如何通过JavaScript获得视频的原生尺寸? 而不是仅仅获取显示出来的尺寸? 尝试使用 Chrome开发工具来查看相关API。
  • 尝试对 video 元素添加 CSS 过滤器。例如:

video {
filter: blur(4px) invert(1) opacity(0.5);
}
  • 尝试添加SVG过滤器。例如:
video {
filter: hue-rotate(180deg) saturate(200%);
}

知识点回顾

在本节课程中, 我们学到了:


  • 从网络摄像头获取视频。
  • 设置媒体约束条件(media constraint)。
  • 混合视频元素。

本节的完整版代码位于 ​​step-01​​ 文件夹中。

提示


  • 记得设置 ​​video​​​ 元素的 ​​autoplay​​ 属性。如果没有设置, 则只能看到第一帧画面!
  • ​getUserMedia()​​​方法提供了很多可选参数, 请参考 ​​https://webrtc.github.io/samples/src/content/peerconnection/constraints/​​. 当然, 其中也有一些有趣的 WebRTC 示例。

最佳实践

  • 请确保 video 元素的内容不会溢出包裹容器。通过 ​​width​​​ 和 ​​max-width​​ 样式可以设置 video 的默认尺寸、最大尺寸。 浏览器会自动计算对应的 height 属性:
video {
max-width: 100%;
width: 320px;
}

后续内容

既然获取到了 video, 那要如何使用呢? 我们将在下一小节讲解!

翻译日期: 2018年07月04日


举报

相关推荐

0 条评论