diff --git a/html5/verto/demo/js/verto-min.js b/html5/verto/demo/js/verto-min.js index 45c9a0771a..35bb6d96be 100644 --- a/html5/verto/demo/js/verto-min.js +++ b/html5/verto/demo/js/verto-min.js @@ -6,16 +6,16 @@ function getCodecPayloadType(sdpLine){var pattern=new RegExp('a=rtpmap:(\\d+) \\ function setDefaultCodec(mLine,payload){var elements=mLine.split(' ');var newLine=[];var index=0;for(var i=0;i=28)TURN={url:'turn:turn.bistri.com:80',credential:'homeo',username:'homeo'};iceServers.iceServers=[STUN];}} var optional={optional:[]};if(!moz){optional.optional=[{DtlsSrtpKeyAgreement:true},{RtpDataChannels:options.onChannelMessage?true:false}];} @@ -57,7 +68,7 @@ function onSdpSuccess(){} function onSdpError(e){if(options.onChannelError){options.onChannelError(e);} console.error('sdp error:',e);} return{addAnswerSDP:function(sdp,cbSuccess,cbError){peer.setRemoteDescription(new SessionDescription(sdp),cbSuccess?cbSuccess:onSdpSuccess,cbError?cbError:onSdpError);},addICE:function(candidate){peer.addIceCandidate(new IceCandidate({sdpMLineIndex:candidate.sdpMLineIndex,candidate:candidate.candidate}));},peer:peer,channel:channel,sendData:function(message){if(channel){channel.send(message);}},stop:function(){peer.close();if(options.attachStream){options.attachStream.stop();}}};} -var video_constraints={mandatory:{},optional:[]};function getUserMedia(options){var n=navigator,media;n.getMedia=n.webkitGetUserMedia||n.mozGetUserMedia;n.getMedia(options.constraints||{audio:true,video:video_constraints},streaming,options.onerror||function(e){console.error(e);});function streaming(stream){var video=options.video;if(video){video[moz?'mozSrcObject':'src']=moz?stream:window.webkitURL.createObjectURL(stream);} +var video_constraints={mandatory:{},optional:[]};function getUserMedia(options){var n=navigator,media;n.getMedia=n.webkitGetUserMedia||n.mozGetUserMedia;n.getMedia(options.constraints||{audio:true,video:video_constraints},streaming,options.onerror||function(e){console.error(e);});function streaming(stream){if(options.localVideo){options.localVideo[moz?'mozSrcObject':'src']=moz?stream:window.webkitURL.createObjectURL(stream);options.localVideo.style.display='block';} if(options.onsuccess){options.onsuccess(stream);} media=stream;} return media;}})(jQuery);(function($){$.JsonRpcClient=function(options){var self=this;this.options=$.extend({ajaxUrl:null,socketUrl:null,onmessage:null,login:null,passwd:null,sessid:null,loginParams:null,getSocket:function(onmessage_cb){return self._getSocket(onmessage_cb);}},options);self.ws_cnt=0;this.wsOnMessage=function(event){self._wsOnMessage(event);};};$.JsonRpcClient.prototype._ws_socket=null;$.JsonRpcClient.prototype._ws_callbacks={};$.JsonRpcClient.prototype._current_id=1;$.JsonRpcClient.prototype.call=function(method,params,success_cb,error_cb){if(!params){params={};} @@ -197,7 +208,7 @@ if(success){} break;default:break;}};$.verto.dialog.prototype.hangup=function(params){var dialog=this;if(params){if(params.causeCode){dialog.causeCode=params.causeCode;} if(params.cause){dialog.cause=params.cause;}} if(dialog.state.val>=$.verto.enum.state.new.val&&dialog.state.val<$.verto.enum.state.hangup.val){dialog.setState($.verto.enum.state.hangup);}else if(dialog.state.val<$.verto.enum.state.destroy){dialog.setState($.verto.enum.state.destroy);}};$.verto.dialog.prototype.stopRinging=function(){var dialog=this;if(dialog.verto.ringer){dialog.verto.ringer.stop();}};$.verto.dialog.prototype.indicateRing=function(){var dialog=this;if(dialog.verto.ringer){dialog.verto.ringer.attr("src",dialog.verto.options.ringFile)[0].play();setTimeout(function(){dialog.stopRinging();if(dialog.state==$.verto.enum.state.ringing){dialog.indicateRing();}},dialog.verto.options.ringSleep);}};$.verto.dialog.prototype.ring=function(){var dialog=this;dialog.setState($.verto.enum.state.ringing);dialog.indicateRing();};$.verto.dialog.prototype.useVideo=function(on){var dialog=this;dialog.params.useVideo=on;if(on){dialog.videoStream=dialog.audioStream;}else{dialog.videoStream=null;} -dialog.rtc.useVideo(dialog.videoStream);};$.verto.dialog.prototype.useStereo=function(on){var dialog=this;dialog.params.useStereo=on;dialog.rtc.useStereo(on);};$.verto.dialog.prototype.dtmf=function(digits){var dialog=this;if(digits){dialog.sendMethod("verto.info",{dtmf:digits});}};$.verto.dialog.prototype.transfer=function(dest,params){var dialog=this;if(dest){dialog.sendMethod("verto.modify",{action:"transfer",destination:dest,params:params});}};$.verto.dialog.prototype.hold=function(params){var dialog=this;dialog.sendMethod("verto.modify",{action:"hold",params:params});};$.verto.dialog.prototype.unhold=function(params){var dialog=this;dialog.sendMethod("verto.modify",{action:"unhold",params:params});};$.verto.dialog.prototype.toggleHold=function(params){var dialog=this;dialog.sendMethod("verto.modify",{action:"toggleHold",params:params});};$.verto.dialog.prototype.message=function(msg){var dialog=this;var err=0;msg.from=dialog.params.login;if(!msg.to){console.error("Missing To");err++;} +dialog.rtc.useVideo(dialog.videoStream);};$.verto.dialog.prototype.setMute=function(what){var dialog=this;return dialog.rtc.setMute(what);};$.verto.dialog.prototype.getMute=function(what){var dialog=this;return dialog.rtc.getMute(what);};$.verto.dialog.prototype.useStereo=function(on){var dialog=this;dialog.params.useStereo=on;dialog.rtc.useStereo(on);};$.verto.dialog.prototype.dtmf=function(digits){var dialog=this;if(digits){dialog.sendMethod("verto.info",{dtmf:digits});}};$.verto.dialog.prototype.transfer=function(dest,params){var dialog=this;if(dest){dialog.sendMethod("verto.modify",{action:"transfer",destination:dest,params:params});}};$.verto.dialog.prototype.hold=function(params){var dialog=this;dialog.sendMethod("verto.modify",{action:"hold",params:params});};$.verto.dialog.prototype.unhold=function(params){var dialog=this;dialog.sendMethod("verto.modify",{action:"unhold",params:params});};$.verto.dialog.prototype.toggleHold=function(params){var dialog=this;dialog.sendMethod("verto.modify",{action:"toggleHold",params:params});};$.verto.dialog.prototype.message=function(msg){var dialog=this;var err=0;msg.from=dialog.params.login;if(!msg.to){console.error("Missing To");err++;} if(!msg.body){console.error("Missing Body");err++;} if(err){return false;} dialog.sendMethod("verto.info",{msg:msg});return true;};$.verto.dialog.prototype.answer=function(params){var dialog=this;if(!dialog.answered){if(params){if(params.useVideo){dialog.useVideo(true);} diff --git a/html5/verto/js/src/jquery.FSRTC.js b/html5/verto/js/src/jquery.FSRTC.js index 82348fe140..a01a4b40f8 100644 --- a/html5/verto/js/src/jquery.FSRTC.js +++ b/html5/verto/js/src/jquery.FSRTC.js @@ -77,6 +77,9 @@ useVideo: null, useStereo: false, userData: null, + localVideo: null, + screenShare: false, + useCamera: "any", iceServers: false, videoParams: {}, audioParams: {}, @@ -84,9 +87,11 @@ onICEComplete: function() {}, onICE: function() {}, onOfferSDP: function() {} - } + }, }, options); + this.enabled = true; + this.mediaData = { SDP: null, profile: {}, @@ -118,11 +123,12 @@ checkCompat(); }; - $.FSRTC.prototype.useVideo = function(obj) { + $.FSRTC.prototype.useVideo = function(obj, local) { var self = this; if (obj) { self.options.useVideo = obj; + self.options.localVideo = local; if (moz) { self.constraints.offerToReceiveVideo = true; } else { @@ -130,6 +136,7 @@ } } else { self.options.useVideo = null; + self.options.localVideo = null; if (moz) { self.constraints.offerToReceiveVideo = false; } else { @@ -196,8 +203,9 @@ doCallback(self, "onError", e); } - function onStreamSuccess(self) { + function onStreamSuccess(self, stream) { console.log("Stream Success"); + doCallback(self, "onStream", stream); } function onICE(self, candidate) { @@ -281,6 +289,7 @@ if (self.options.useVideo) { self.options.useVideo.style.display = 'none'; + self.options.useVideo[moz ? 'mozSrcObject' : 'src'] = ""; } if (self.localStream) { @@ -288,17 +297,58 @@ self.localStream = null; } + if (self.options.localVideo) { + self.options.localVideo.style.display = 'none'; + self.options.localVideo[moz ? 'mozSrcObject' : 'src'] = ""; + } + + if (self.options.localVideoStream) { + self.options.localVideoStream.stop(); + } + if (self.peer) { console.log("stopping peer"); self.peer.stop(); } }; - $.FSRTC.prototype.createAnswer = function(sdp) { + $.FSRTC.prototype.getMute = function() { + var self = this; + return self.enabled; + } + + $.FSRTC.prototype.setMute = function(what) { + var self = this; + var audioTracks = self.localStream.getAudioTracks(); + + for (var i = 0, len = audioTracks.length; i < len; i++ ) { + switch(what) { + case "on": + audioTracks[i].enabled = true; + break; + case "off": + audioTracks[i].enabled = false; + break; + case "toggle": + audioTracks[i].enabled = !audioTracks[i].enabled; + default: + break; + } + + self.enabled = audioTracks[i].enabled; + } + + return !self.enabled; + } + + $.FSRTC.prototype.createAnswer = function(params) { var self = this; self.type = "answer"; - self.remoteSDP = sdp; - console.debug("inbound sdp: ", sdp); + self.remoteSDP = params.sdp; + console.debug("inbound sdp: ", params.sdp); + + self.options.useCamera = params.useCamera || "any"; + self.options.useMic = params.useMic || "any"; function onSuccess(stream) { self.localStream = stream; @@ -336,53 +386,117 @@ onStreamError(self, e); } + var mediaParams = getMediaParams(self); + + console.log("Audio constraints", mediaParams.audio); + console.log("Video constraints", mediaParams.video); + + if (self.options.useVideo && self.options.localVideo) { + getUserMedia({ + constraints: { + audio: false, + video: { + mandatory: self.options.videoParams, + optional: [] + }, + }, + localVideo: self.options.localVideo, + onsuccess: function(e) {self.options.localVideoStream = e; console.log("local video ready");}, + onerror: function(e) {console.error("local video error!");} + }); + } + + getUserMedia({ + constraints: { + audio: mediaParams.audio, + video: mediaParams.video + }, + video: mediaParams.useVideo, + onsuccess: onSuccess, + onerror: onError + }); + + + + }; + + function getMediaParams(obj) { var audio; - if (this.options.videoParams && this.options.videoParams.chromeMediaSource == 'screen') { + if (obj.options.videoParams && obj.options.screenShare) {//obj.options.videoParams.chromeMediaSource == 'desktop') { - this.options.videoParams = { - chromeMediaSource: 'screen', - maxWidth:screen.width, - maxHeight:screen.height - }; + //obj.options.videoParams = { + // chromeMediaSource: 'screen', + // maxWidth:screen.width, + // maxHeight:screen.height + // chromeMediaSourceId = sourceId; + // }; console.error("SCREEN SHARE"); audio = false; } else { audio = { - mandatory: this.options.audioParams, + mandatory: obj.options.audioParams, optional: [] }; + + if (obj.options.useMic !== "any") { + audio.optional = [{sourceId: obj.options.useMic}] + } + } - console.log("Mandatory audio constraints", this.options.audioParams); - console.log("Mandatory video constraints", this.options.videoParams); + if (obj.options.useVideo && obj.options.localVideo) { + getUserMedia({ + constraints: { + audio: false, + video: { + mandatory: obj.options.videoParams, + optional: [] + }, + }, + localVideo: obj.options.localVideo, + onsuccess: function(e) {self.options.localVideoStream = e; console.log("local video ready");}, + onerror: function(e) {console.error("local video error!");} + }); + } - getUserMedia({ - constraints: { - audio: audio, - video: this.options.useVideo ? { - mandatory: this.options.videoParams, - optional: [] - } : null - }, - video: this.options.useVideo ? true : false, - onsuccess: onSuccess, - onerror: onError - }); + var video = { + mandatory: obj.options.videoParams, + optional: [] + } + + var useVideo = obj.options.useVideo; + + if (useVideo && obj.options.useCamera && obj.options.useCamera !== "none") { + if (obj.options.useCamera !== "any") { + video.optional = [{sourceId: obj.options.useCamera}] + } + } else { + video = null; + useVideo = null; + } + + return {audio: audio, video: video, useVideo: useVideo}; + } + - }; $.FSRTC.prototype.call = function(profile) { checkCompat(); - + var self = this; + var screen = false; self.type = "offer"; + if (self.options.videoParams && self.options.screenShare) { //self.options.videoParams.chromeMediaSource == 'desktop') { + screen = true; + } + function onSuccess(stream) { - self.localStream = stream; + self.localStream = stream; self.peer = RTCPeerConnection({ type: self.type, @@ -393,7 +507,7 @@ onICEComplete: function() { return onICEComplete(self); }, - onRemoteStream: function(stream) { + onRemoteStream: screen ? function(stream) {console.error("SKIP");} : function(stream) { return onRemoteStream(self, stream); }, onOfferSDP: function(sdp) { @@ -409,53 +523,35 @@ iceServers: self.options.iceServers, }); - onStreamSuccess(self); + onStreamSuccess(self, stream); } function onError(e) { onStreamError(self, e); } + var mediaParams = getMediaParams(self); - var audio; - - if (this.options.videoParams && this.options.videoParams.chromeMediaSource == 'screen') { - - this.options.videoParams = { - chromeMediaSource: 'screen', - maxWidth:screen.width, - maxHeight:screen.height - }; - - console.error("SCREEN SHARE"); - audio = false; - } else { - audio = { - mandatory: this.options.audioParams, - optional: [] - }; - } - - console.log("Mandatory audio constraints", this.options.audioParams); - console.log("Mandatory video constraints", this.options.videoParams); + console.log("Audio constraints", mediaParams.audio); + console.log("Video constraints", mediaParams.video); getUserMedia({ constraints: { - audio: audio, - video: this.options.useVideo ? { - mandatory: this.options.videoParams, - optional: [] - } : null + audio: mediaParams.audio, + video: mediaParams.video }, - video: this.options.useVideo ? true : false, + video: mediaParams.useVideo, onsuccess: onSuccess, onerror: onError }); + + + /* navigator.getUserMedia({ - video: this.options.useVideo, + video: self.options.useVideo, audio: true }, onSuccess, onError); */ @@ -823,14 +919,22 @@ }); function streaming(stream) { - var video = options.video; - if (video) { - video[moz ? 'mozSrcObject' : 'src'] = moz ? stream : window.webkitURL.createObjectURL(stream); + //var video = options.video; + //var localVideo = options.localVideo; + //if (video) { + // video[moz ? 'mozSrcObject' : 'src'] = moz ? stream : window.webkitURL.createObjectURL(stream); //video.play(); + //} + + if (options.localVideo) { + options.localVideo[moz ? 'mozSrcObject' : 'src'] = moz ? stream : window.webkitURL.createObjectURL(stream); + options.localVideo.style.display = 'block'; } + if (options.onsuccess) { options.onsuccess(stream); } + media = stream; } diff --git a/html5/verto/js/src/jquery.verto.js b/html5/verto/js/src/jquery.verto.js index 12b1409db9..3547255207 100644 --- a/html5/verto/js/src/jquery.verto.js +++ b/html5/verto/js/src/jquery.verto.js @@ -1726,6 +1726,16 @@ }; + $.verto.dialog.prototype.setMute = function(what) { + var dialog = this; + return dialog.rtc.setMute(what); + }; + + $.verto.dialog.prototype.getMute = function(what) { + var dialog = this; + return dialog.rtc.getMute(what); + }; + $.verto.dialog.prototype.useStereo = function(on) { var dialog = this;