不得不提的RTCPeerConnection

1,102 阅读5分钟

1、它是啥?

RTCPeerConnection接口代表一个由本地计算机到远程的WebRTC连接。该接口提供了创建、保持、监控、关闭连接的方法的实现。

// RTCPeerConnection和RTCSessionDescription是很多浏览器中使用的名称。强烈使用补充库,如Adapter.js,以确保您网站或Web应用程序的兼容性。如下
var PeerConnection = window.RTCPeerConnection || window.mozRTCPeerConnection || window.webkitRTCPeerConnection
var SessionDescription = window.RTCSessionDescription || window.mozRTCSessionDescription || window.webkitRTCSessionDescription;
var GET_USER_MEDIA = navigator.getUserMedia ? "getUserMedia" :
                     navigator.mozGetUserMedia ? "mozGetUserMedia" :
                     navigator.webkitGetUserMedia ? "webkitGetUserMedia" : "getUserMedia";
var v = document.createElement("video");
var SRC_OBJECT = 'srcObject' in v ? "srcObject" :
                 'mozSrcObject' in v ? "mozSrcObject" :
                 'webkitSrcObject' in v ? "webkitSrcObject" : "srcObject";

2、它的构造函数

pc = new RTCPeerConnection([configuration])
// 参数: 一个RTCPeerConnection dictionary提供了一条新建连接的可选参数
// 返回值:一个新生成的RTCPeerConnection对象

3、它有哪些属性?

  • 1、canTrickleCandiates【readonly】: 如果远端支持UDP打洞或支持通过中继服务器连接,则该属性值为true。否则,为false。该属性的值依赖于远端设置且仅在本地的RTCPeerConnection.setRemoteDescription()方法被调用时有效,如果该方法没有调用,其值则为null
  • 2、connectionState【readlony】:只读connectionState属性通过返回由枚举RTCPeerConnection指定的字符串值之一来指示对等连接的当前状态
  • 3、currentLocalDescription【readonly】: 返回一个描述连接本地端的 RTCSessionDescription 对象
  • 4、defaultIceServers【readonly】
  • 5、iceConnectionState: 返回与RTCPeerConnection关联的ICE代理的状态类型为RTCIceConnectionState的枚举,当这个状态改变是,会触发iceconnectionstatechange事件,状态类型如下:
        new:
        cheking:
        connected:
        completed:
        failed:
        disconnected:
        closed:
    
  • 6、iceGatheringState: 返回一个iceGatheringState类型的结构体,描述了这条连接的ICE收集状态,有以下状态:
        new
        gathering
        complete
    
  • 7、localDescription【readonly】:描述了这条连接的本地端的会话控制(用户会话所需的属性以及配置信息)。如果本地的会话控制还没有被设置,它的值就会是null。
  • 8、remoteDescription: 描述了这条连接的远端机器的会话控制,如果远端机器还未被设置,它的值为null。
  • peerIdentity:
  • signalingState:返回一个RTC通信状态的结构体,这个结构体描述了本地连接的通信状态。这个状态描述了一个定义连接配置的SDP offer。它包含了下列信息,与MediaStream类型本地相关的对象的描述,媒体流编码方式或RTP和RTCP协议的选项,以及被ICE服务器收集到的candiates(连接候选者).
        stable:
        have-local-offer:
        have-remote-offer:
        have-local-pranswer:
        have-remote-pranswer:
        closed
    

4、它有哪些事件?

  • onaddstream
  • ondatachannel: 收到datachannel事件时调用的事件处理器。当一个RTCDataChannel被添加到连接时,这个事件被触发。
  • onicediate
  • oniceconnectionstatechange
  • onnegotiationneeded
  • onremovestream
  • onsignalingstatechange
  • onidentityresult
  • onidpassertionerror
  • onidpvalidationerror
  • onpeeridentity

5、它有哪些方法呢?

  • 构造方法 RTCPeerConnection()
  • createOffer():生成一个offer,他是一个带有特定的配置信息寻找远程匹配机器(peer)的请求。这个方法的前两个参数分别是方法调用成功以及失败的回调,可选的第三个参数是用户对视频流以及音频流的定制选项
  • createAnswer():在协调一跳连接中的两端offer/answers时,根据从远端发出来的offer生成一个answer。前两个参数分别时成功、失败回调函数,第三个可选参数是生成的answer可供选择项。
  • setLocalDescription():改变与连接相关的本地描述。这个描述定义了连接的属性,例如:连接的编码方式。连接会收到它的改变的影响,而且连接必须能同时支持新的以及旧的描述。接受三个参数,第一个是RTCSessionDescription对象包含设置信息,另外两个是成功、失败回调函数
  • setRemoteDescription():改变与连接相关的远程描述。
  • addIceCandiate()
  • getConfiguration()
  • getLocalStreams():返回连接的本地媒体流数组。这个数组可能是空数组。
  • getRemoteStreams():返回连接的远端媒体流组。
  • getStreamById():返回连接中与所给id匹配的媒体流,如果没有匹配项,返回null
  • addStream():添加一个媒体流作为本地音频或视频源。如果本地端与远程协调已经发生了,那么需要一个新的媒体流,这样远端才可以使用它。
  • removeStream():将一个作为本地音频或视频源的媒体流移除。
  • close(): 关闭一个RTCPeerConnection实例所调用的方法。
  • createDataChannel():在一条连接上建立一个新的RTCDataChannel(用于数据发送)。这个方法把一个数据对象作为参数,数据对象中包含必要的配置信息。
  • getStats():生成一个新的RTCStatsReport,它包含连接相关的统计信息。
  • setIdentityProvider():
  • getIdentityAssertion()
  • createDTMFSender()
  • updateIce()

5.1 用法示例

// 1、void createOffer(RTCSessionDescriptionCallback successCallback, RTCPeerConnectionErrorCallback failureCallback, opitional MediaConstrains constraints): createOffer会生成描述信息的一个blob对象,它会帮助连接到本地机器。
var pc = new RTCPeerConnection()
pc.addStream(video)
pc.createOffer(function(desc){
    pc.setLocalDescription(desc, function(){
    // send the offer to a server that can negotiate with a remote client
    })
})
// 2、void createAnswer(RTCSessionDescriptionCallback successCallback, RTCPeerConnectionErrorCallback failureCallback, optional MediaConstraints constraints)
var pc = new PeerConnection()
pc.setRemoteDescription(new RTCSessionDescription(offer), function(){
    pc.createAnswer(function(answer) {
        pc.setLocalDescription(answer, funciton(){
        })
    })
})
// 3、RTCDataChannel createDataChannel(DOMString label, optional RTCDataChannelInit dataChannelDict)
var pc = new PeerConnection()
var channel = pc.createDataChannel('MyData')
channel.onopen = function(event) {
    channel.send('sending a message')
}
channel.onmessage = function(event){console.log(event.data}

6、基本用法

// 一个基本的RTCPeerConnection使用需要协调本地机器以及远端机器的连接,它可以通过两台机器间生成Session Decription的数据交换协议来实现。呼叫方发送一个offer(请求),被呼叫方发出一个answer(应答)来回答请求。双方-呼叫方以及被呼叫方,最开始的时候都要建立他们各自的RTCPeerConnection对象。
var pc = new RTCPeerConnection()
pc.onaddstream = function(obj) {
    var vid = document.createElement("video");
    document.appendChild(vid);
    vid.srcObject = obj.stream;
}

// Helper functions
function endCall() {
  var videos = document.getElementsByTagName("video");
  for (var i = 0; i < videos.length; i++) {
    videos[i].pause();
  }

  pc.close();
}

function error(err) { endCall(); }

//////
navigator.getUserMedia({video: true}, function(stream){
    pc.onaddstream({stream})
    pc.addStream(stream)
    pc.createOffer(function(offer){
        pc.setLocalDecription(new RTCSessionDescription(offer),function(){
        
        }, error)
    }, error)
})

////
var offer = getOfferFromFriend()
navigater.getUserMedia({video: true}, function(stream){
    pc.onaddstream({stream: stream})
    pc.addStream(stream)
    pc.setRemoteDescription(new RTCSessionDescription(offer), function(){
        pc.createAnswer(function(answer){
            pc.setLocalDescription(new RTCSessionDescription(answer), function() {}, error)
        },error)
    }, error)
})

//// 同时在呼叫发起方,你会收到这个应答(前面被呼叫方发出的offer),你需要将它设置为你的远程连接
var offer = getResponseFromFriend()
pc.setRemoteDescription(new RTCSessionDescription(offer), function(){}, error)

7、浏览器兼容性

图片.png