出处:http://www.cnblogs.com/fangkm/p/4370492.html

上一篇文章简单地介绍了下WebRTC的协议流程,这一篇就开始介绍框架与接口。

一提到框架,本能地不知道从什么地方入手了。曾经直接从Chromium项目对WebRTC的源码的集成方面入手,后来发现这个步子迈的太大了,看的越多,概念越混乱,看了半个月感觉也没啥沉淀。还是从WebRTC提供的示例工程peerconnection_client入手比较轻便。先抛开音视频流的构建和渲染流程,示例工程核心的代码结构如下:

从面向对象的视角来看,WebRTC的设计还是非常棒的,真正地做到了接口编程的概念,对WebRTC功能的使用都通过接口来进行,这样最大程度上保证了WebRTC模块的可定制性,这样就可以让WebRTC更多地回归到描述协议的本质。如果WebRTC对这些接口的实现不能满足你的业务需求,理论上你可以提供自己的实现逻辑。本图中的PeerConnectionFactoryInterface和PeerConnectionInterface没有这种定制的代表性,因为重新提供它们的实现逻辑的需求场景基本上不存在(即便不用重写,但也支持参数的定制,具体请参见CreatePeerConnectionFactory的重载方法)。但是音视频相关的接口定制的场景就很普遍了,比如Chromium浏览器集成WebRTC,但是音视频采集需要走Chromium自己的音视频模块,所以Chromium对WebRTC音视频的采集接口重新做了实现适配,以后有机会肯定非常乐意分享下Chromium源码对WebRTC的集成,不过那也是在对WebRTC熟悉完之后的工作了。

图中Conductor是该示例工程提供的核心业务类,整个WebRTC的使用都浓缩在这个类中。Conductor通过CreatePeerConnectionFactory方法创建了一个PeerConnectionFactoryInterface接口的实现对象,通过这个接口,可以创建关键的PeerConnectionInterface接口,PeerConnectionInterface接口是WebRTC的协议核心。此外,PeerConnectionFactoryInterface接口还提供了创建本地音视频流的功能接口,这个部分稍后再述。根据图中PeerConnectionInterface接口的成员方法可以看出,WebRTC通信流程的交互接口基本上都在这里面了,给Conductor的回调通知是通过PeerConnectionObserver接口来完成。具体的交互流程请参见上一篇博文。

接下来分析本地音视频的相关接口,由于音视频内容较多,这里先介绍下接口概念,不谈具体实现(下一节专门讲解WebRTC原生的音视频采集),还是以peerconnection_client工程为例:

这里涉及到非常多的音视频相关接口,基本上都是概念性的,最怕遇到新的设计概念,主要是怕自己理解有误差,下面谈一下我对这些接口概念的理解:

MediaStream概念: 表示媒体流,由MediaStreamInterface接口抽象,每个媒体流都有一个唯一的标识(通过label成员方法返回),它由一系列的音频Track(由AudioTrackInterface接口抽象)和视频Track组成(由VideoTrackInterface接口抽象)。

Track概念:具体指上图结构中AudioTrackInterface和VideoTrackInterface接口,Track表示的是在媒体流中轨的概念,AudioTrackInterface标识的是音频轨,VideoTrackInterface标识的是视频轨,一个MediaStreamInterface标识的媒体流中允许携带多个媒体轨数据,它们之间是独立的,在编码渲染的流程中各自处理。如果概念还很模糊,轨的概念就相当于音频数据中的声道概念(左声道、右声道)、视频数据中的YUV场的概念。Track既然封装了媒体轨数据,那就必然有个媒体源做为数据的提供者,如音频Track由AudioSourceInterface接口作为数据源提供者,视频Track由VideoSourceInterface接口作为数据的提供者。有输入接口就必然有输出接口,这部分在该图中只展示了视频数据的输出接口VideoRendererInterface,这里的Render命名的意思并不是仅限于将视频和音频数据渲染出来,应该理解成输出接口。

VideoSourceInterface:抽象视频源接口供VideoTracks使用,同一个源可以被多个VideoTracks共用。视频源接纳了一个VideoCapturer接口,抽象视频采集的逻辑,我们可以提供自己的VideoCapturer实现做为视频数据的采集源。VideoCapturer是个关键的定制接口,比如Chromium源码就是自己实现了VideoCapturer接口而没用原生的WebRTC采集实现,但Chromium的音视频采集都在browser进程,因此它对VideoCapturer接口的实现要比想象的复杂,它需要从主进程接收到视频帧数据然后触发VideoCapturer的SignalFrameCaptured信号。

AudioSourceInterface:概念上同VideoSourceInterface类似,抽象音频源接口供AudioTracks使用,但是从源码中理解,这是个伪概念,因为没有提供一个类似于VideoCapturer的AudioCapturer接口,这里没有音频的采集逻辑,实际上WebRTC的音频采集接口使用的是AudioDeviceModule,在创建PeerConnectionFactory的时候可以由外界定制,如果没有,则内部创建AudioDeviceModuleImpl来实现此接口完成音频设备的采集工作。可能是功力不够,反正我是不太理解音频采集和视频采集这种设计的不对称性。如果也封装一个AudioCapturer接口的概念,这样可定制性是不是可以更高。

构建媒体流的过程基本上就是构建Video Track和Audio Track,并将其添加到Media Stream里。在peerconnection_client工程中,Conductor依赖DeviceManagerInterface接口的CreateVideoCapturer方法创建一个当前可用的视频设备采集对象VideoCapturer,将它作为视频采集源中的数据来源(通过挂接VideoCapturer的SignalVideoFrame信号来接收视频数据),此外MainWnd还创建了一个内部类VideoRenderer从VideoRendererInterface接口派生,并将其添加到Video Track中, VideoRenderer的实现就是将接收到的视频帧数据渲染到窗口上。

下一篇开始分析WebRTC原生的音视频本地采集模块。

WebRTC之框架与接口的更多相关文章

  1. (二)WebRTC手记之框架与接口

    转自:http://www.cnblogs.com/fangkm/p/4370492.html 转载请注明出处:http://www.cnblogs.com/fangkm/p/4370492.html ...

  2. WebRTC手记之框架与接口

    转载请注明出处:http://www.cnblogs.com/fangkm/p/4370492.html 上一篇文章简单地介绍了下WebRTC的协议流程,这一篇就开始介绍框架与接口. 一提到框架,本能 ...

  3. 跨平台的WebRTC客户端框架:OpenWebRTC

    Webrtc的ios框架编译 http://www.th7.cn/Program/IOS/201502/390418.shtml WebRTC in WebKit : http://www.webrt ...

  4. [自制操作系统] BMP格式文件读取&图形界面系统框架/应用接口设计

    本文将介绍在本人JOS中实现的简单图形界面应用程序接口,应用程序启动器,以及一些利用了图形界面的示例应用程序. 本文主要涉及以下部分: 内核/用户RW/RW调色板framebuffer共享区域 8bi ...

  5. Linux Framebuffer驱动剖析之二—驱动框架、接口实现和使用

    深入分析LinuxFramebuffer子系统的驱动框架.接口实现和使用. 一.LinuxFramebuffer的软件需求 上一篇文章详细阐述了LinuxFramebuffer的软件需求(请先理解第一 ...

  6. robotframework - 框架做接口自动化post请求

    1.做get请求之前先安装 Request库,参考github上链接 :https://github.com/bulkan/robotframework-requests/#readme 2.请求&a ...

  7. Java集合框架——Set接口

    第三阶段 JAVA常见对象的学习 集合框架--Set接口 List集合的特点是有序的,可重复的,是不是存在这一种无序,且能保证元素唯一的集合呢?(HashSet )这就涉及到我们今天所要讲的Set集合 ...

  8. Java集合框架——List接口

    第三阶段 JAVA常见对象的学习 集合框架--List接口 按照集合框架的继承体系,我们先从Collection中的List接口开始学习 (一) 概述及功能(ArrayList演示) (1) 概述 L ...

  9. Java集合框架Map接口

    集合框架Map接口 Map接口: 键值对存储一组对象 key不能重复(唯一),value可以重复 常用具体实现类:HashMap.LinkedHashMap.TreeMap.Hashtable Has ...

随机推荐

  1. maven 学习---转换基于Maven的Web应用程序支持Eclipse IDE

    在上一节教程中,使用Maven创建了一个Web应用程序.这里有一个指南,告诉你如何转换Web应用程序到Eclipse IDE支持的形式. 注意,通过WTP工具Eclipse IDE支持Web应用程序, ...

  2. vue3.0创建项目和基本配置

    借鉴博客:https://www.jianshu.com/p/6307c568832d/ https://www.cnblogs.com/KenFine/p/10850386.html 项目创建好后, ...

  3. Jetty启动报Error scanning entry META-INF/versions/9/org/apache/logging/log4j/util/ProcessIdUtil.class

    近日在项目中集成Elasticsearch后,Jetty启动报错. 错误日志如下: Suppressed: |java.lang.RuntimeException: Error scanning en ...

  4. Linux学习之常用命令(三)

    常用命令之工作目录 显示当前目录 pwd[选项] 切换目录 cd [文件路径] cd /root 注意:可以使用Tab键进行路径补齐 cd .. >>返回上次的目录 显示目录以及文件信息 ...

  5. UVa 202 Repeating Decimals 题解

    The decimal expansion of the fraction 1/33 is 0.03, where the 03 is used to indicate that the cycle ...

  6. ZooKeeper架构原理你学会了吗?

    Zookeeper是分布式一致性问题的工业解决方案,是Apache Hadoop下解决分布式一致性的一个组件,后被分离出来成为Apache的顶级项目. 工程来源:是雅虎公司内部项目,据说雅虎内部很多项 ...

  7. LOJ 546: 「LibreOJ β Round #7」网格图

    题目传送门:LOJ #546. 题意简述: 题目说的很清楚了. 题解: 将不包含起点或障碍物的连续的行或列缩成一行或一列,不会影响答案. 处理过后,新的网格图的行数和列数最多为 \(2k + 3\). ...

  8. 第 33课 C++中的字符串(下)

    字符串与数字转换-标准库中提供了相关的类对字符串和数字进行转换-字符串流类(sstream)用于string的转换.<sstream>-相关头文件.istringstream-字符串输入流 ...

  9. centos7 下安装rpm的mysql 5.7

    在centos7下安装mysql5.7 一:下载mysql 去官网上去下载:这里我下载的二进制格式的 https://dev.mysql.com/downloads/mysql/ 去下载对应平台的my ...

  10. centos 下 gradle 编译打包 apk

    由于Jenkins 装在centos环境下,想实现Android程序的编译,只能通过gradle 命令去打包版本apk,以下记录了如何在centos下使用gradle 打包apk 一.安装 gradl ...