WebRTC系列(1)-手把手教你实现一个浏览器拍照室Demo
1.WebRTC开发背景
由于业务需求,需要在项目中实现实时音视频通话功能,之前基于浏览器开发的Web项目要进行音视频通话,需要安装flash插件才能实现或者使用C/S客户端进行通信。随着互联网技术的驱动下,在很多场景下需要进行音视频通信,在生活中我们现在使用电话越来越少,使用微信和视频越来越多。在一些行业也需要进行音视频实时通信,如:在线教育,远程医疗,保险理赔等等。有了WebRTC,可以开发一些好的网页应用,使得音视频通话越来越简单,无需安装任何插件,只需打开网页,就能实现音视频通话,方然也能实现消息收发,文件收发等等,下面,根据自己平时的项目开发与,对WebRTC就行一个简单的理解与概述,最终实现一个简单的拍照室Demo。
2.WebRTC历史和概述
WebRTC是“网络实时通信”(Web Real Time Communication)的缩写。它最初是为了解决浏览器上视频通话而提出的,即两个浏览器之间直接进行视频和音频的通信,不经过服务器。后来发展到除了音频和视频,还可以传输文字和其他数据。2010年5月,Google以6820万美元收购VoIP软件开发商Global IP Solutions的GIPS引擎,并改为名为“WebRTC”。WebRTC使用GIPS引擎,实现了基于网页的视频会议,并支持722,PCM,ILBC,ISAC等编码,同时使用谷歌自家的VP8视频解码器;同时支持RTP/SRTP传输等。Google是WebRTC的主要支持者和开发者,它推动了WebRTC标准的确立。
WebRTC是一门年轻的技术,从2011推出到2017年,一直发展的不温不火。根据一段时间的开发,个人认为主要原因有:各个浏览器的支持兼容程度和在互联网环境下点对点能够连接的成功率。从2017年苹果公司宣布iOS11的Safari浏览器支持WebRTC,一些云通信产品例如腾讯云通信和网易云通信也是基于WebRTC上进行封装二次开发,也间接的说明了WebRTC发展会越来越好。
3.基本概念的了解
为了简化开发,WebRTC在浏览器中API集成了大量的技术,解决了一些繁重的问题,如捕捉摄像头和麦克风,处理音视频流,传输层等等。
- 捕捉摄像头和麦克风
建立通信平台第一步要检测用户设备的摄像头和麦克风权限,先检测设备的可用性,然后在获取用户授权并与设备建立连接,最后获取一段数据流。
- 音频与视频的编解码
在互联网要发送一段音视频数据,技术优化了网络数据,数据尺寸也还是很大,所以要对数据在发送端编码,然后在接收端解码。WebRTC内置的几种编解码器包括:H.264,Opcus,iSAC,VP8。作为前端开发的我,最这些编解码技术当然不是很了解。幸运的是,当两个浏览器回话时,会综合两端情况选择最优的编解码器。
- 传输层
主要处理数据丢包,数据包排序以及建立用户之间的连接问题
- 会话管理
通常来说就是信令(Signaling),负责在浏览器中建立并管理多个连接。
4.获取用户媒体
创建一个基于WebRTC的通信平台,首先要通过用户的网络摄像头和麦克风获取实时的视频和音频流,可以通过调用浏览器的getUserMedia API来实现。
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>获取媒体流</title>
</head>
<body>
<div id="app">
<h1>获取媒体流</h1>
<video autoplay></video>
</div>
<script>
function hasUserMedia() {
return !!(navigator.getUserMedia || navigator.webkitGetUserMedia || navigator.mozGetUserMedia || navigator.msGetUserMedia);
} if (hasUserMedia()) {
navigator.getUserMedia = navigator.getUserMedia || navigator.webkitGetUserMedia || navigator.mozGetUserMedia || navigator.msGetUserMedia;
navigator.getUserMedia({video: true, audio: false}, function (stream) {
console.log(stream);
var video = document.querySelector('video');
video.src=window.URL.createObjectURL(stream);
}, function (err) {
console.log(err);
});
} else {
alert("Sorry, your browser does not support getUserMedia.");
}
</script>
</body>
</html>
是否打开使用摄像头权限
注意:打开摄像头后获取到的视频流展示在Video标签中,video标签需要加上autoplay属性视频才可以播放,在调试中可以把getUserMedia方法参数中的audio设置为:false,避免杂音太大,同理,把video设置为false只能听到自己说话而没有画面,可以代替普通电话使用。
5.限制视频流
我们可以通过设置参数来控制视频和音频是否使用,除此之外,我们可以传入一个对象做更复杂的限制,如分辨率,视频宽高比等等。
navigator.getUserMedia({video: {
width: 320,
/*height:240,*/
aspectRatio:1.77
}, audio: false}, function (stream) {
console.log(stream);
var video = document.querySelector('video');
video.src=window.URL.createObjectURL(stream);
}, function (err) {
console.log(err);
});
可以根据自己业务需求来设置固定的宽高或分辨率等等。
6.完成一个拍照室Demo
通过调用摄像头获取到的视频流以及H5的canvas标签我们可以完成一个简易的拍照功能。
增加一个拍照按钮以及一个canvas,修改后的整个页面代码如下:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>获取媒体流</title>
</head>
<body>
<div id="app">
<h1>获取媒体流</h1>
<video id="video" autoplay></video>
<button type="button" onclick="capture()">点击拍照</button>
<canvas id="canvas" width="320" height="240"></canvas>
</div>
<script>
function hasUserMedia() {
return !!(navigator.getUserMedia || navigator.webkitGetUserMedia || navigator.mozGetUserMedia || navigator.msGetUserMedia);
} if (hasUserMedia()) {
navigator.getUserMedia = navigator.getUserMedia || navigator.webkitGetUserMedia || navigator.mozGetUserMedia || navigator.msGetUserMedia;
navigator.getUserMedia({video: {
width: 320,
height:240,
}, audio: false}, function (stream) {
console.log(stream);
var video = document.querySelector('video');
video.src=window.URL.createObjectURL(stream);
}, function (err) {
console.log(err);
});
} else {
alert("Sorry, your browser does not support getUserMedia.");
} function capture(){
console.log('capture...');
var cxt=document.getElementById('canvas').getContext('2d');
var video=document.getElementById('video');
cxt.drawImage(video,0,0);
}
</script>
</body>
</html>
现在单击一个点击拍照按钮,可以捕捉视频的某一帧并同时绘制到canvas上,加上canvas功能本来就很强大,后期对照片的旋转,剪裁,滤镜也都是可以实现的。
延伸:现在很多WebApp上要实时上传证件功能,我们通过这种WebRTC+canvas也是可以实现的,而且是浏览器直接调的硬件拍照,有没有很溜。
7.开发中遇到的问题
在直接用http打开本地服务器页面是调用不了摄像头的,浏览器的限制认为http下是不安全的,但是可以用127.0.0.1或者localhost来代替本机ip。网页部署到服务器时也得使用https协议来返回页面,否则,无法调用摄像头。
以上简单的介绍了WebRTC的发展历史以及一些基本概念,让大家对其有个初步的了解,最后通过调用摄像头完成一个拍照室的Demo。后续文章再详细的写如何通过WebRTC来实现点对点通信,相信WebRTC功能会越来越强大,这只是第一步。
参考资料:
《Learning WebRTC 中文版》
《JavaScript 标准参考教程(alpha) 阮一峰》
转载请注明出处,谢谢。
WebRTC系列(1)-手把手教你实现一个浏览器拍照室Demo的更多相关文章
- Android应用系列:手把手教你做一个小米通讯录(附图附源码)
前言 最近心血来潮,突然想搞点仿制品玩玩,很不幸小米成为我苦逼的第一个试验品.既然雷布斯的MIUI挺受欢迎的(本人就是其的屌丝用户),所以就拿其中的一些小功能做一些小demo来玩玩.小米的通讯录大家估 ...
- Go语言系列之手把手教你撸一个ORM(一)
项目地址:https://github.com/yoyofxteam/yoyodata 欢迎星星,感谢 前言:最近在学习Go语言,就出于学习目的手撸个小架子,欢迎提出宝贵意见,项目使用Mysql数据库 ...
- 只有20行Javascript代码!手把手教你写一个页面模板引擎
http://www.toobug.net/article/how_to_design_front_end_template_engine.html http://barretlee.com/webs ...
- iOS回顾笔记(05) -- 手把手教你封装一个广告轮播图框架
html,body,div,span,applet,object,iframe,h1,h2,h3,h4,h5,h6,p,blockquote,pre,a,abbr,acronym,address,bi ...
- PWA入门:手把手教你制作一个PWA应用
摘要: PWA图文教程 原文:PWA入门:手把手教你制作一个PWA应用 作者:MudOnTire Fundebug经授权转载,版权归原作者所有. 简介 Web前端的同学是否想过学习app开发,以弥补自 ...
- R数据分析:跟随top期刊手把手教你做一个临床预测模型
临床预测模型也是大家比较感兴趣的,今天就带着大家看一篇临床预测模型的文章,并且用一个例子给大家过一遍做法. 这篇文章来自护理领域顶级期刊的文章,文章名在下面 Ballesta-Castillejos ...
- 大数据江湖之即席查询与分析(下篇)--手把手教你搭建即席查询与分析Demo
上篇小弟分享了几个“即席查询与分析”的典型案例,引起了不少共鸣,好多小伙伴迫不及待地追问我们:说好的“手把手教你搭建即席查询与分析Demo”啥时候能出?说到就得做到,差啥不能差人品,本篇只分享技术干货 ...
- 手把手教你画一个 逼格满满圆形水波纹loadingview Android
才没有完结呢o( ̄︶ ̄)n .大家好,这里是番外篇. 拜读了爱哥的博客,又学到不少东西.爱哥曾经说过: 要站在巨人的丁丁上. 那么今天,我们就站在爱哥的丁丁上来学习制作一款自定义view(开个玩笑,爱 ...
- 用Python手把手教你搭一个Transformer!
来源商业新知网,原标题:百闻不如一码!手把手教你用Python搭一个Transformer 与基于RNN的方法相比,Transformer 不需要循环,主要是由Attention 机制组成,因而可以充 ...
随机推荐
- JSF-使用JSF标记
使用JSF标记 基于Facelets技术的JSF页面是一个 XHTML页面,文件扩展名为 .xhtml 1)JSF页面可用html标记,但必须满足: ①所有标记都必须闭合.如<p>开始,& ...
- AndroidStudio 快捷键 Ctrl+Q查询过慢的问题
Ctrl+Q快捷键的作用是快速查找文档注释 但是有时候会一直fetching 需要等很长时间这时候 打开本地文件 C:\Users\Adminastration\.AndroidStudi ...
- 前端工程化(三)---Vue的开发模式
从0开始,构建前后端分离应用 导航 前端工程化(一)---工程基础目录搭建 前端工程化(二)---webpack配置 前端工程化(三)---Vue的开发模式 前端工程化(四)---helloWord ...
- zabbix监控mysql性能
使用zabbix监控mysql的三种方式 1.只是安装agent 2.启用模板监控 3.启用自定义脚本的模板监控 zabbix中默认有mysql的监控模板.默认已经在zabbix2.2及以上的版本中. ...
- Java 8 Optional类深度解析(转)
经常会遇到这样的问题,调用一个方法得到了返回值却不能直接将返回值作为参数去调用别的方法.我们首先要判断这个返回值是否为null,只有在非空的前提下才能将其作为其他方法的参数. 新版本的Java,比如J ...
- mysql管理工具navicat的快捷键
1. ctrl + q 或者 ctrl+n: 打开新查询窗口 2. ctrl + r: 运行当前窗口内的所有语句 3. ctrl + shit + r: 只运行选中的语句 4. ctrl + w: ...
- mpvue-编写微信小程序总结
一.写在前面: .....最近在写一个微信小程序项目,在看完官方微信小程序开发文档后,有一种直接想"放弃"的念头: .....使用微信小程序原生框架可以快速,方便,简洁的搭建项目, ...
- golang自定义路由控制实现(二)-流式注册接口以及支持RESTFUL
先简单回顾一下在上一篇的文章中,上一篇我主要是结合了数组和Map完成路由映射,数组的大小为8,下标为0的代表Get方法,以此类推,而数组的值则是Map,键为URL,值则是我们编写对应的接口.但 ...
- CentOS下使用命令行Web浏览器Links
前言: Links是一个运行在命令行模式下的Web浏览器,只能查看字符.Links的官网是Click here. 安装Links yum install links 使用Links links URL ...
- 如何在js或者jquery中操作EL表达式的一个List集合
------------吾亦无他,唯手熟尔,谦卑若愚,好学若饥------------- 先说明此篇博客看明白了可以干嘛: 就是在js或者jquery中操作一个EL表达式的一个list集合或者复杂类型 ...