Commit f2443ecb authored by Jakub Adam's avatar Jakub Adam
Browse files

Recover WebRTC player after network failure

parent 7b05657c
......@@ -2,14 +2,18 @@
class Client {
constructor() {
this.__requestId = 0
this.onopen = undefined
this.onerror = undefined
this.onoffer = undefined
this.oncandidate = undefined
this.__reset();
this.__ws = undefined
}
connect() {
if (this.__ws) {
this.__ws.close()
}
this.__ws = new WebSocket(`ws://${window.location.host}/ws`)
this.__ws.onopen = () => {
......@@ -30,64 +34,61 @@ class Client {
break
}
}
}
hello(callback) {
this.__sendRequest('hello', undefined, callback)
}
register(offer, callback) {
let args = {}
if (offer) {
args.type = offer.type
args.sdp = offer.sdp
this.__ws.onerror = (error) => {
console.log(`websocket error: ${error.message}`)
if (this.onerror) {
this.onerror()
}
}
this.__sendRequest('register', args, callback)
}
bye(callback) {
this.__sendRequest('bye', undefined, callback)
this.__reset()
}
answer(sdp) {
this.__sendRequest('answer', { sdp: sdp })
}
candidate(candidate, callback) {
this.__sendRequest('candidate', {candidate: candidate.toJSON()}, callback)
candidate(candidate) {
this.__sendRequest('candidate', {candidate: candidate.toJSON()})
}
__sendRequest(type, args, callback) {
var request = Object.assign({
msg: type,
}, args)
__sendRequest(type, args) {
var request = Object.assign({msg: type}, args)
this.__ws.send(JSON.stringify(request))
if (callback) {
this.__pendingRequests[request.id] = {
callback: callback
}
}
}
__reset() {
this.__pendingRequests = {}
if (this.__ws) {
this.__ws.close()
}
this.__ws = undefined
}
}
export class WebRTCStream {
constructor(video) {
this.__webrtc = new RTCPeerConnection()
this.__videoElement = video
this.__webrtc = undefined
this.__signaling = new Client()
this.__signaling.onopen = () => {
this.__webrtc = new RTCPeerConnection()
this.__webrtc.onicecandidate = (c) => {
if (c.candidate) {
this.__signaling.candidate(c.candidate)
}
}
this.__webrtc.ontrack = (event) => {
console.log(event)
this.__videoElement.srcObject = event.streams[0];
}
this.__webrtc.onconnectionstatechange = (event) => {
switch (this.__webrtc.connectionState) {
case 'disconnected':
case 'failed':
this.__videoElement.srcObject = undefined
this.__signaling.connect()
break;
}
console.log(`WebRTC state changed: ${this.__webrtc.connectionState}`)
}
}
this.__signaling.onoffer = async (msg) => {
try {
console.log(msg.sdp)
......@@ -104,15 +105,8 @@ export class WebRTCStream {
console.log(c)
this.__webrtc.addIceCandidate(c)
}
this.__webrtc.onicecandidate = (c) => {
if (c.candidate) {
this.__signaling.candidate(c.candidate)
}
}
this.__webrtc.ontrack = (event) => {
console.log(event)
video.srcObject = event.streams[0];
this.__signaling.onerror = () => {
setTimeout(() => this.__signaling.connect(), 1000)
}
this.__signaling.connect()
......@@ -124,11 +118,14 @@ export class HLSStream {
this.__hls = new Hls({liveDurationInfinity: true});
this.__hls.on(Hls.Events.ERROR, (e, data) => {
if (data.type == "networkError") {
setTimeout(() => {
this.__hls.recoverMediaError()
this.__hls.loadSource('hls/playlist.m3u8')
}, 1000)
switch (data.type) {
case 'networkError':
case 'mediaError':
setTimeout(() => {
this.__hls.recoverMediaError()
this.__hls.loadSource('hls/playlist.m3u8')
}, 1000)
break;
}
console.log(data)
})
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment