1 /** 2 * IMPORTANT NOTES ON CLASS 3 * 4 5 Used to listen to call control Zebra 6 Should be off by default to avoid interfering with Flash / Mobile existing implementations 7 Should be enabled as needed 8 Methods called in Platform in case in future used on other platforms. 9 ZEBRA <?xml version="1.0" encoding="UTF-8" ?><zebra fmt="2.0" username="VB2ZHDKROEBXZA7U5HCS2QROAP92WZ9RZT6SL7W7PO" service="saypage" event="SERVER_REDIRECT" error_code="0" anchor="" seq=""><zconfig></zconfig><zevent><connectmode>2</connectmode><destination>zen:VS7</destination><isP2P>true</isP2P><openfire></openfire><tracker>ZBE</tracker><type>VIDEODIAL</type><zenonserver></zenonserver></zevent></zebra> 10 11 **/ 12 /** 13 @name CallManager 14 @class This class allows you to place and receive voice and video calls as well as mute and speaker controls. 15 **/ 16 CallManager = EventDispatcher.extendAsSingleton({ 17 AUTO_ANSWER: true, 18 ZUID: 1, 19 CALL_HANDLING: false, 20 CAM_MIC: "cammic", 21 MIC: "mic", 22 VOICE: "VOICE", 23 VIDEO: "VIDEO", 24 W2SPort: "10060", 25 _callToken: null, 26 _ss_window: null, 27 _type: "VIDEO", 28 _destination: null, 29 _mcuCall: false, 30 _initCallInner: null, 31 _initCallInnerSetTime: null, 32 _initCallInnerTimeout: 60 * 1000, 33 _establishMonitorId: null, 34 _showLVDelayId: null, 35 _establishMonitorTimeout: 1 * 60 * 1000, 36 _showLVDelayIdTimeout: 1.3 * 1000, 37 _keepConnected: null, 38 _sendPhoneParam: true, 39 _videoMuted: false, 40 _playMedia: false, 41 _selfX: -1, 42 _selfY: -1, 43 _selfWidth: -1, 44 _selfHeight: -1, 45 _selfXCache: -1, 46 _selfYCache: -1, 47 _selfWidthCache: -1, 48 _selfHeightCache: -1, 49 _videoWidth: -1, 50 _videoHeight: -1, 51 _hangUpIfNoSR: false, 52 _hangUpIfNoSRTS: 10000, 53 _flashEnabled: false, 54 _establish:false, 55 _srCommandID:-1, 56 recordwb:true, 57 58 Event: { 59 /** 60 @name CallManager#Event_INCOMING_CALL 61 @description Event fired on incoming call 62 @type object 63 **/ 64 INCOMING_CALL: "INCOMING_CALL", //data: nil 65 /** 66 @name CallManager#Event_CONNECTED 67 @description Event fired on call connected 68 @type object 69 **/ 70 CONNECTED: "CONNECTED", //data: nil 71 /** 72 @name CallManager#Event_CONNECTING 73 @description Event fired on call connecting 74 @type object 75 **/ 76 CONNECTING: "CONNECTING", //data: nil 77 /** 78 @name CallManager#Event_INIT 79 @description Event fired on call manager initialized 80 @type object 81 **/ 82 INIT: "INIT", //data: nil 83 /** 84 @name CallManager#Event_FAILED 85 @description Event fired on call failed 86 @type object 87 **/ 88 FAILED: "FAILED", //data: nil 89 /** 90 @name CallManager#Event_ENDED 91 @description Event fired on call ended 92 @type object 93 **/ 94 ENDED: "ENDED", //data: nil 95 /** 96 @name CallManager#Event_RINGING 97 @description Event fired on remote ringing 98 @type object 99 **/ 100 RINGING: "RINGING", //data: nil 101 SET_LV: "SET_LV", //data: nil 102 HIDE_LV: "HIDE_LV", //data: nil 103 /** 104 @name CallManager#Event_RECONNECTING 105 @description Event fired on call switching between p2p and server 106 @type object 107 **/ 108 TIME_ELAPSED: "TIME_ELAPSED", 109 /** 110 @name CallManager#Event_TIME_ELAPSED 111 @description Event fired as call time changes 112 @type object 113 **/ 114 RECONNECTING: "RECONNECTING",//data: nil 115 /** 116 @name CallManager#Event_RECONNECTED 117 @description Event fired on call switching between p2p and server 118 @type object 119 **/ 120 RECONNECTED: "RECONNECTED", //data: nil 121 ZEBRA: function(zebraEvent) { 122 return "ZEBRA:" + zebraEvent; 123 } //data: zebra 124 }, 125 /** 126 * Constructor 127 **/ 128 init: function() { 129 this._super(); 130 //public APIs to add/remove listeners 131 this.addListener = this._addListener; 132 this.removeListener = this._removeListener; 133 this.removeAllListenersForEvent = this._removeAllListenersForEvent; 134 // listen for incoming Zebra, if auto answer do it else fireevent 135 ConnectionManager.addListener("ZEBRA:IncomingCall", this, this.incomingCall); 136 ConnectionManager.addListener("ZEBRA:SERVER_REDIRECT", this, this.serverRedirect); 137 ConnectionManager.addListener("MCUDISCONNECT", this, this.disconnectCall); 138 ConnectionManager.addListener("ZENONWAKEFAIL", this, this.disconnectCall); 139 ConnectionManager.addListener("ZWRTC_SIP_CALL_FAILED", this, this.endCall); 140 ConnectionManager.addListener("ZWRTC_SIP_CALL_TERMINATED", this, this.endCall); 141 ConnectionManager.addListener("FLASH_CALL_TERMINATED", this, this.endCall); 142 ConnectionManager.addListener("ZWRTC_P2P_ESTABLISHED", this, this.p2pEstablished); 143 ConnectionManager.addListener("ZWRTC_CALL_ESTABLISHED", this, this.callEstablished); 144 ConnectionManager.addListener("RECORDING_CALL", this, this.recordingCall); 145 ConnectionManager.addListener("ZWRTC_P2P_FAILED", this, this.p2pFailed); 146 ConnectionManager.addListener("ZWRTC_SET_WEBCAM_ACTIVE", this, this.setWebCamActive); 147 ConnectionManager.addListener("ZWRTC_AUDIO_MUTE_TOGGLED", this, this.audioToggled); 148 ConnectionManager.addListener("ZWRTC_VIDEO_MUTE_TOGGLED", this, this.videoToggled); 149 ConnectionManager.addListener("SHARE_SCREEN_START", this, this.shareScreenStart); 150 ConnectionManager.addListener("SHARE_SCREEN_STOP", this, this.shareScreenStop); 151 ConnectionManager.addListener("ZEBRA:SHARE_SCREEN_STOPPED", this, this.shareScreenStopped); 152 ConnectionManager.addListener("SHARE_SCREEN_STOPPED", this, this.shareScreenStopped); 153 ConnectionManager.addListener(ConnectionManager.Event.ZS_STATE_CHANGED, this, this.checkCall); 154 ConnectionManager.addListener("ZEBRA:RESET_OCCURRED", this, this.checkCall); 155 ConnectionManager.addListener("ZEBRA:MULTI_ALTERNATIVE_STREAM", this, this.mapt); 156 this.addListener(this.Event.CONNECTING, this, this.mapt); 157 this.addListener(this.Event.CONNECTED, this, this.mapt); 158 this.addListener(this.Event.RECONNECTING, this, this.mapt); 159 this.addListener(this.Event.RECONNECTED, this, this.mapt); 160 }, 161 mapt: function(zebra) { 162 163 var isZebra=false; 164 if (zebra && (typeof zebra.getZEvent !='undefined')) 165 isZebra=true; 166 167 var pauseMove=false; 168 if (isZebra) { 169 if (zebra.getZEvent("view_mode") && zebra.getZEvent("view_mode").value=="media") { 170 CallManager._playMedia=true; 171 } else { 172 CallManager._playMedia=false; 173 } 174 pauseMove=true; 175 if ( zebra.getZEvent("selfX") && zebra.getZEvent("selfX").value && parseInt(zebra.getZEvent("selfX").value)>=0 ) { 176 CallManager._selfXCache=parseInt(zebra.getZEvent("selfX").value); 177 CallManager._selfYCache=parseInt(zebra.getZEvent("selfY").value); 178 CallManager._selfWidthCache=parseInt(zebra.getZEvent("selfWidth").value); 179 CallManager._selfHeightCache=parseInt(zebra.getZEvent("selfHeight").value); 180 } else { 181 CallManager._selfXCache=-1; 182 CallManager._selfYCache=-1; 183 CallManager._selfWidthCache=-1; 184 CallManager._selfHeightCache=-1; 185 } 186 if (zebra.getZEvent("videoWidth") && zebra.getZEvent("videoWidth").value && parseInt(zebra.getZEvent("videoWidth").value)>=0) { 187 CallManager._videoWidth=parseInt(zebra.getZEvent("videoWidth").value); 188 CallManager._videoHeight=parseInt(zebra.getZEvent("videoHeight").value); 189 } 190 } 191 192 if (CallManager._videoWidth==-1) { 193 CallManager._videoWidth=zwrtc.cam_width; 194 CallManager._videoHeight=zwrtc.cam_height; 195 } 196 197 if (zwrtc._video && zwrtc.isConnected() && zwrtc.isMCU()) { 198 CallManager._selfX=CallManager._selfXCache; 199 CallManager._selfY=CallManager._selfYCache; 200 CallManager._selfWidth=CallManager._selfWidthCache; 201 CallManager._selfHeight=CallManager._selfHeightCache; 202 }else{ 203 CallManager._selfX=-1; 204 CallManager._selfY=-1; 205 CallManager._selfWidth=-1; 206 CallManager._selfHeight=-1; 207 } 208 209 210 // if pauseMove send hide LV and schedule a set LV time out which can be cancelled if another comes along in time 211 212 if (pauseMove) { 213 CallManager._showLVDelayId = DateTimeUtil.getNow(); 214 var update_ = CallManager._showLVDelayId; 215 setTimeout(function() { 216 if (update_ == CallManager._showLVDelayId) { 217 CallManager._dispatchEvent(CallManager.Event.SET_LV); 218 } 219 }, CallManager._showLVDelayIdTimeout); 220 CallManager._dispatchEvent(CallManager.Event.HIDE_LV); 221 } else { 222 CallManager._dispatchEvent(CallManager.Event.SET_LV); 223 } 224 }, 225 startScreenShare: function(username) { 226 if (username == null) 227 username = DataStore.getUserData("username", ""); 228 var mcuIPPort = this.getServerIP() + ":" + DataStore.getUserData("mcu_sip_port", ""); 229 var screenURL = "https://" + window.location.host + "/user/portal/share.jsp?session=" + "SHADOW_SCREEN_" + username + "&port=" + CallManager.W2SPort + "&mcu=" + mcuIPPort; 230 this._ss_window = window.open(screenURL, 'tr', 'directories=no,titlebar=no,toolbar=no,location=no,status=no,menubar=no,scrollbars=no,resizable=no,left=60,top=60,width=450,height=200'); 231 CallManager._videoMuted = webRTC.isVideoMuted; 232 if (!webRTC.isVideoMuted) { 233 webRTC.disableVideo(); 234 } 235 }, 236 switchViewOnly: function() { 237 //we can directly call zwrtc.switchViewOnly() or dispatch SWITCH_VIEW_ONLY event 238 ConnectionManager._dispatchEvent("SWITCH_VIEW_ONLY", { 239 'msg': '' 240 }); 241 }, 242 shareScreenStart: function(evt) { 243 this.shareScreenStop(); 244 this.startScreenShare(null); 245 }, 246 isSharingScreen: function() { 247 return (this._ss_window != null); 248 }, 249 shareScreenStop: function(evt) { 250 if (this._ss_window) { 251 this._ss_window.close(); 252 this._ss_window = null; 253 } 254 }, 255 shareScreenStopped: function(evt) { 256 showMessage("Screen Share Ended", "", false, null, null, null, true, 1500); 257 if (!CallManager._videoMuted) { 258 webRTC.enableVideo(); 259 CallManager._videoMuted = false; 260 } 261 }, 262 setWebCamActive: function(evt) { 263 Platform.log("CallManager setWebCamActive:" + evt.isVideoMuted); 264 var active = "yes"; 265 if (evt.isVideoMuted) 266 active = "no"; 267 Platform.httpRequest( 268 "POST", CallManager.getEndPoint() + (ConnectionManager.ZSServlet || ""), 269 null, 270 "comm=sendMessageToMCU" + 271 "&command=setwebcamactive" + 272 "&value=" + active + 273 "&username=" + (DataStore.getUserData("username", "")) + 274 "&service=" + (ConnectionManager.service || ""), 275 null 276 ); 277 }, 278 videoToggled: function(evt) { 279 var zebra = new Zebra("com.requestec.smg.apps.ZenDevice#setCam"); 280 if (evt.mute) 281 zebra.setZEvent("cam", "false"); 282 else 283 zebra.setZEvent("cam", "true"); 284 ConnectionManager.sendZebra(zebra); 285 }, 286 audioToggled: function(evt) { 287 var zebra = new Zebra("com.requestec.smg.apps.ZenDevice#setMic"); 288 if (evt.mute) 289 zebra.setZEvent("mic", "false"); 290 else 291 zebra.setZEvent("mic", "true"); 292 ConnectionManager.sendZebra(zebra); 293 }, 294 p2pEstablished: function() { 295 if(zwrtc.isMCU()){ 296 //mcu call going on 297 Platform.log("CallManager p2pEstablished:Sending SERVER_REDIRECT_STATUS:OK to mcu"); 298 var zebra = new Zebra("SERVER_REDIRECT_STATUS"); 299 zebra.setZEvent("status", "OK"); 300 zebra.setZEvent("command_id", this._srCommandID); 301 ConnectionManager.sendZebraToMCU(zebra); 302 Platform.log("_srCommandID:"+this._srCommandID); 303 zwrtc.switchedToP2P(); 304 CallManager._dispatchEvent(CallManager.Event.RECONNECTED, {'type':'p2p'}); 305 }else 306 CallManager._dispatchEvent(CallManager.Event.CONNECTED, {'type':'p2p'}); 307 Platform.log("CallManager p2pEstablished"); 308 this.sendPlaceCall(true); 309 this.callEstablished(); 310 }, 311 p2pFailed: function() { 312 Platform.log("CallManager p2pFailed"); 313 var video = true; 314 if (CallManager._type == "VOICE") 315 video = false; 316 this.connectToMCU(video); 317 this.sendPlaceCall(false); 318 }, 319 getZEvent:function(zebra,param){ 320 var val=null; 321 try{ 322 val=zebra.getZEvent(param).value; 323 }catch(err){} 324 return val; 325 }, 326 serverRedirect: function(zebra) { 327 if (!CallManager.CALL_HANDLING || CallManager._flashEnabled) return; 328 Platform.log("CallManager serverRedirect"); 329 if(zebra) 330 Platform.log("CallManager serverRedirect:"+zebra.toXML()); 331 var video = true; 332 if (zebra.getZEvent("mcu") && zebra.getZEvent("mcu").value == "true") { 333 ConnectionManager._dispatchEvent('MCU_SR_RECVD', { 334 'msg': 'Connecting to mcu' 335 }); 336 CallManager._hangUpIfNoSR = false; 337 if (ConnectionManager.inCall()) { 338 zwrtc.hangup(true); 339 CallManager._dispatchEvent(CallManager.Event.RECONNECTING, {'type':'mcu'}); 340 }else 341 CallManager._dispatchEvent(CallManager.Event.CONNECTING, {'type':'mcu'}); 342 if (CallManager._type == "VOICE") 343 video = false; 344 this.connectToMCU(video); 345 } else { 346 CallManager._mcuCall = false; 347 var type = this.getZEvent(zebra,"type"); 348 var connectmode = this.getZEvent(zebra,"connectmode"); 349 var destination = this.getZEvent(zebra,"destination"); 350 var isP2P = this.getZEvent(zebra,"isP2P"); 351 var zenonserver = this.getZEvent(zebra,"zenonserver"); 352 var callerP2PAddress = this.getZEvent(zebra,"callerP2PAddress"); 353 var srCommandID = this.getZEvent(zebra,"command_id"); 354 355 if(srCommandID) 356 CallManager._srCommandID=srCommandID; 357 else 358 CallManager._srCommandID=-1; 359 360 if(type==null) 361 type=CallManager.VIDEO; 362 type = type.replace("DIAL", ""); 363 if (type == "NONE" || type == "VOICE") { 364 video = false; 365 } 366 CallManager._type = type; 367 if(ConnectionManager.inCall()){ 368 //already in call and mcu want to establish p2p 369 var p2pAddr = CallManager.getWrtcAddress(callerP2PAddress); 370 if (p2pAddr != null) { 371 zwrtc.placeP2PCall(p2pAddr, video); 372 } 373 }else if (connectmode == "2" || connectmode == "0") { 374 var p2p = zwrtc.getP2PAddress(); 375 destination = destination.replace("VS7", "VS1"); 376 if (destination.indexOf("#") == -1 && destination.indexOf("%23") == -1) { 377 destination = destination + "%23" + LineStatesModel.getNextAvailableLine(); 378 } 379 Platform.log("Calling initiateCall:" + p2p); 380 zwrtc.updateCallType(video); 381 this.initCall(type, destination, "-1", true, 0, "Demo Call", null, p2p); 382 } else if (connectmode == "1") { 383 this.endCall(); 384 } 385 } 386 }, 387 /** 388 @name CallManager#setZUI 389 @function 390 @description 391 Initialize the CallManager for being able to place and receive calls using a ZUI object. 392 393 @param {string} zui The ZUI Object which renders the UI components 394 @param {string} confirmAV prompt user for cam and mic (CallManager.CAM_MIC) or just mic (CallManager.MIC) 395 @param {string} viewOnly call using viewOnly mode, i.e. no media access or transmission 396 397 **/ 398 setZUI: function(zui,confirmAV,viewOnly) { 399 if(zui.getAttribute("forceFlash")=="true"){ 400 CallManager._flashEnabled=true; 401 } 402 if(zui.getAttribute("flashBgColor")){ 403 flashClient.setBGColor(zui.getAttribute("flashBgColor")); 404 } 405 flashClient.setTimerOnRV(true); 406 flashClient.showToolBar(); 407 CallManager.zinit(zui.getLV(),zui.getRV(),zui.getAudio(),confirmAV,viewOnly,$("#sp_flash_container"),"sp_flash"); 408 }, 409 onStatusMsg: function(msg){ 410 flashClient.onStatusMsg(msg); 411 }, 412 413 /** 414 @name CallManager#zinit 415 @function 416 @description 417 Initialize the CallManager for being able to place and receive calls 418 419 @param {string} localVideo DOM element to display the local video 420 @param {string} remoteVideoArray Array of DOM elements for displaying the remote video streams 421 @param {string} remoteAudio element to play remote audio 422 @param {string} confirmAV prompt user for cam and mic (CallManager.CAM_MIC) or just mic (CallManager.MIC) 423 @param {string} viewOnly call using viewOnly mode, i.e. no media access or transmission 424 425 **/ 426 zinit: function(localVideo,remoteVideoArray,remoteAudio,confirmAV,viewOnly,flashClientContainer,flashContainerName) { 427 CallManager.CALL_HANDLING = true; 428 if(ConnectionManager.isLoggedIn()) { 429 CallManager.zinitInner(localVideo,remoteVideoArray,remoteAudio,confirmAV,viewOnly,flashClientContainer,flashContainerName); 430 }else{ 431 ConnectionManager.addListener("LOGIN_SUCCESS", this, function(){ 432 CallManager.zinitInner(localVideo,remoteVideoArray,remoteAudio,confirmAV,viewOnly,flashClientContainer,flashContainerName); 433 }); 434 } 435 }, 436 zinitInner: function(localVideo,remoteVideoArray,remoteAudio,confirmAV,viewOnly,flashClientContainer,flashContainerName) { 437 if(!CallManager._flashEnabled){ 438 //check if webrtc supported by browser or not 439 try{ 440 if(((typeof mozRTCPeerConnection!="undefined") && mozRTCPeerConnection) || ((typeof webkitRTCPeerConnection!="undefined") && webkitRTCPeerConnection)){ 441 //webrtc supported 442 }else 443 CallManager._flashEnabled=true; 444 }catch(err){ 445 CallManager._flashEnabled=true; 446 } 447 } 448 if(CallManager._flashEnabled){ 449 flashClient.init(flashClientContainer,flashClient,false); 450 }else{ 451 if(viewOnly) 452 zwrtc.viewOnly=true; 453 454 var uname=DataStore.getUserData("username", ""); 455 DataStore.getUserData("username", ""); 456 if(uname && uname.indexOf("SHADOW_")==-1) 457 uname="SHADOW_"+uname; 458 var turn=DataStore.getUserData("stun_turn", "[{ url: 'stun:stun.l.google.com:19302'}]"); 459 eval("turn = "+turn); 460 zwrtc.init(uname,null,null,localVideo,remoteVideoArray,remoteAudio,null,true,"both",confirmAV,turn,""); 461 } 462 }, 463 /** 464 @name CallManager#placeCall 465 @function 466 @description Place a call 467 @param {string} type CallManager.VIDEO | CallManager.VOICE 468 @param {string} destination Addrress to dial. Can be a user or room. 469 @param {string} displayName String to display e.g. Meeting title 470 @param {boolean} keepConnected Redial if connection dropped due to poor internet. Default false. 471 472 **/ 473 placeCall: function(type, dest, displayName, keepConnected) { 474 if(CallManager._flashEnabled){ 475 flashClient.placeCall(type, dest); 476 }else{ 477 CallManager.initCall(type, dest, "-1", true, 0, displayName, null, zwrtc.getP2PAddress(), keepConnected); 478 } 479 }, 480 initCall: function(type, dest, chat_session_id, showVS, itemId, displayName, alternative_username, p2pAddress, keepConnected) { 481 // ensure safe placing of call when state waiting - allow up to 60 seconds to happen 482 CallManager._initCallInner = function() { 483 CallManager._type = type; 484 CallManager._destination = dest; 485 CallManager._mcuCall = false; 486 // 1) monitor call is actually placed 487 // allow time to establish else initCall again 488 CallManager._establishMonitorId = DateTimeUtil.getNow(); 489 var update_ = CallManager._establishMonitorId; 490 setTimeout(function() { 491 if (update_ == CallManager._establishMonitorId) { 492 Platform.log("CallManager CallManager._establishMonitorId starting Call again"); 493 ConnectionManager._dispatchEvent("ZWRTC_PLACING_CALL_STEPS", { 494 'msg': ' ESTABLISH MONITOR ALARM' 495 }); 496 CallManager.sendEndCall(); 497 zwrtc.hangup(); 498 CallManager.initCall(type, dest, chat_session_id, showVS, itemId, displayName, alternative_username, p2pAddress, keepConnected); 499 } 500 }, CallManager._establishMonitorTimeout); 501 if (dest && dest.indexOf("#") == -1 && dest.indexOf("%23") == -1) { 502 dest = dest + "%23" + LineStatesModel.getNextAvailableLine(); 503 } 504 Platform.initiateCall(type, dest, chat_session_id, showVS, itemId, displayName, alternative_username, p2pAddress); 505 ConnectionManager._dispatchEvent('PLACECALL_ZEBRA_SENT', { 506 'msg': 'inner' 507 }); 508 }; 509 CallManager._initCallInnerSetTime = new Date().getTime(); 510 CallManager.checkCall(); 511 // 2) once established 512 CallManager._keepConnected = null; 513 if (keepConnected) { 514 CallManager._keepConnected = function() { 515 Platform.log("CallManager CallManager._keepConnected starting Call again"); 516 ConnectionManager._dispatchEvent("ZWRTC_PLACING_CALL_STEPS", { 517 'msg': ' KEEP CONNECTED MONITOR ALARM' 518 }); 519 zwrtc.hangup(); 520 CallManager.initCall(type, dest, chat_session_id, showVS, itemId, displayName, alternative_username, p2pAddress, keepConnected); 521 }; 522 } 523 }, 524 checkCall: function() { 525 Platform.log("checkCall:"+ConnectionManager.zsState); 526 if (ConnectionManager.zsState == "waiting") { 527 if (CallManager._initCallInner != null) { 528 if ((new Date().getTime()) - CallManager._initCallInnerSetTime < CallManager._initCallInnerTimeout) 529 CallManager._initCallInner(); 530 else 531 Platform.log("CallManager checkCall timed out"); 532 CallManager._initCallInner = null; 533 } else if (CallManager._keepConnected && CallManager._establishMonitorId == null) { 534 // if waiting or reset && CallManager._keepConnected && its established 535 Platform.log("CallManager call keep connected"); 536 CallManager._keepConnected(); 537 } 538 } 539 }, 540 cancelCall: function() { 541 Platform.log("CallManager CallManager.cancelCall"); 542 CallManager._establishMonitorId = null; 543 CallManager._keepConnected = null; 544 CallManager._establish=false; 545 }, 546 isEstablished: function() { 547 return CallManager._establish; 548 }, 549 550 callEstablished: function() { 551 Platform.log("CallManager CallManager._establishMonitorId callEstablished"); 552 CallManager._establishMonitorId = null; 553 CallManager._establish=true; 554 }, 555 recordingCall: function() { 556 this.callEstablished(); 557 }, 558 disconnectCall: function() { 559 if (!CallManager.CALL_HANDLING) return; 560 CallManager._mcuCall = false; 561 CallManager._callToken = null; 562 CallManager._hangUpIfNoSR = false; 563 CallManager._type = CallManager.VIDEO; 564 Platform.log("CallManager disconnectCall"); 565 zwrtc.hangup(); 566 CallManager.cancelCall(); 567 CallManager._dispatchEvent(CallManager.Event.ENDED); 568 CallManager.shareScreenStop(); 569 }, 570 connectToMCU: function(videoCall) { 571 if (CallManager._mcuCall) { 572 Platform.log("CallManager connectToMCU, ignoring as mcu call already going on"); 573 return; 574 } 575 CallManager._mcuCall = true; 576 var dest = "rtcshadow"; 577 if (!videoCall) 578 dest = "rtcshadowaudio"; 579 Platform.log("sip:" + dest + "@" + this.getServerIP() + ":" + DataStore.getUserData("mcu_sip_port", "")); 580 zwrtc.placeCall(videoCall, "sip:" + dest + "@" + this.getServerIP() + ":" + DataStore.getUserData("mcu_sip_port", ""), 1, this.getServerIP()); 581 }, 582 getEndPoint: function() { 583 return (window.zcallerHostname || DataStore.getUserData("endpoint", "") || ConnectionManager.CLS); 584 }, 585 getServerIP: function() { 586 //var endpoint = (window.zcallerHostname || DataStore.getUserData("endpoint", "") || ConnectionManager.CLS); 587 var endpoint = CallManager.getEndPoint(); 588 endpoint = endpoint.replace("http://", ""); 589 endpoint = endpoint.replace("https://", ""); 590 endpoint = endpoint.replace(":80", ""); 591 return endpoint; 592 }, 593 hangUpLine: function(lineNumber) { 594 var zebra = new Zebra("CALL_CONTROL"); 595 zebra.setZEvent("action", "HANGUP"); 596 zebra.setZEvent("line_number", lineNumber); 597 ConnectionManager.sendZebraToMCU(zebra); 598 }, 599 onUnload: function(){ 600 if (!CallManager.CALL_HANDLING) return; 601 Platform.log("CallManager onUnload"); 602 CallManager.clearCall(); 603 Platform.httpRequest( 604 "POST", CallManager.getEndPoint() + (ConnectionManager.ZSServlet || ""), 605 null, 606 "comm=unregister" + 607 "&username=" + (DataStore.getUserData("username", "")) + 608 "&service=" + (ConnectionManager.service || ""), 609 null 610 ); 611 }, 612 clearCall: function(){ 613 CallManager.cancelCall(); 614 CallManager._dispatchEvent(CallManager.Event.ENDED); 615 ConnectionManager._dispatchEvent('MCUDISCONNECT', { 616 'reason': '0' 617 }); 618 }, 619 sendEndCall:function(){ 620 Platform.httpRequest( 621 "POST", CallManager.getEndPoint() + (ConnectionManager.ZSServlet || ""), 622 null, 623 "comm=endcall" + 624 "&username=" + (DataStore.getUserData("username", "")) + 625 "&service=" + (ConnectionManager.service || ""), 626 null 627 ); 628 }, 629 /** 630 @name CallManager#endCall 631 @function 632 @description End the current call 633 634 **/ 635 endCall: function() { 636 if (!CallManager.CALL_HANDLING) return; 637 Platform.log("CallManager endCall"); 638 CallManager.clearCall(); 639 CallManager.sendEndCall(); 640 }, 641 incomingCall: function(zebra) { 642 if (!CallManager.CALL_HANDLING) return; 643 Platform.log("CallManager incomingCall"); 644 var callToken = zebra.getZEvent("callToken").value; // b0530111-dfcb-e211-883d-0050569f2828 645 var caller = zebra.getZEvent("caller").value; // Gonzo Clone 646 var callerAudioCodecs = zebra.getZEvent("callerAudioCodecs").value; // SPEEX,ASAO 647 var callerMaxDownload = zebra.getZEvent("callerMaxDownload").value; // 400000 648 var callerP2PAddress = zebra.getZEvent("callerP2PAddress").value; // apt:1801751084_6632 649 var callerVBSession = zebra.getZEvent("callerVBSession").value; // VB7SNDUZ0FFB5LWJO7OTNYHTTECL7BZBFHOP9LW0ZSSPWNZ0WYUYIR2URNWMI3 650 var callerVideoCodecs = zebra.getZEvent("callerVideoCodecs").value; // SORENSON,H264 651 var callerVideoHeight = zebra.getZEvent("callerVideoHeight").value; // 288 652 var callerVideoWidth = zebra.getZEvent("callerVideoWidth").value; // 352 653 var chat_session_id = zebra.getZEvent("chat_session_id").value; // 654 var contactaddress = zebra.getZEvent("contactaddress").value; // 655 var contactid = zebra.getZEvent("contactid").value; // 100381084 656 var contactname = zebra.getZEvent("contactname").value; // 657 var contacttype = zebra.getZEvent("contacttype").value; // 658 var type = zebra.getZEvent("type").value; // VIDEO 659 var zenonserver = zebra.getZEvent("zenonserver").value; // 660 CallManager._dispatchEvent(CallManager.Event.INCOMING_CALL); 661 if (this.AUTO_ANSWER) 662 CallManager.acceptCall(callToken, caller, callerAudioCodecs, callerMaxDownload, callerP2PAddress, callerVBSession, callerVideoCodecs, callerVideoHeight, callerVideoWidth, chat_session_id, contactaddress, contactid, contactname, contacttype, type, zenonserver); 663 else { 664 // play audio 665 // showDialog 666 // if ok call accept and stop ringing 667 // if not ok or cancel stop ringing 668 if (ConnectionManager.Platform.isSayPageApp) { 669 showMessage("Incoming Call", "Call from " + caller, true, null, "Answer", function() { 670 CallManager.acceptCall(callToken, caller, callerAudioCodecs, callerMaxDownload, callerP2PAddress, callerVBSession, callerVideoCodecs, callerVideoHeight, callerVideoWidth, chat_session_id, contactaddress, contactid, contactname, contacttype, type, zenonserver) 671 }, false, null, "Ignore"); 672 } else { 673 Z.jqm.showNJQMChoiceDialog("Accept call from " + caller, function() { 674 CallManager.acceptCall(callToken, caller, callerAudioCodecs, callerMaxDownload, callerP2PAddress, callerVBSession, callerVideoCodecs, callerVideoHeight, callerVideoWidth, chat_session_id, contactaddress, contactid, contactname, contacttype, type, zenonserver) 675 }, 60 * 1000); 676 } 677 } 678 }, 679 getWrtcAddress: function(p2pAddress) { 680 if (p2pAddress) { 681 var addresses = p2pAddress.split(","); 682 for (var i = 0; i < addresses.length; i++) { 683 var addr = addresses[i].split(":"); 684 if (addr[0] == "wrtc") 685 return addr[1]; 686 } 687 } 688 return null; 689 }, 690 acceptCall: function(callToken, caller, callerAudioCodecs, callerMaxDownload, callerP2PAddress, callerVBSession, callerVideoCodecs, callerVideoHeight, callerVideoWidth, chat_session_id, contactaddress, contactid, contactname, contacttype, type, zenonserver) { 691 //send ACCEPT first before placing call 692 Platform.httpRequest( 693 "POST", CallManager.getEndPoint() + (ConnectionManager.ZSServlet || ""), 694 null, 695 "comm=zsmessage" + 696 "&command=ZENONWAKERESPONSE" + 697 "&value=ACCEPT%23" + LineStatesModel.getNextAvailableLine() + 698 "&username=" + (DataStore.getUserData("username", "")) + 699 "&service=" + (ConnectionManager.service || ""), 700 null 701 ); 702 zwrtc.stopSound(); 703 // placeCall with token and possible isP2P true/false depending on ding dong 704 if (!ConnectionManager.inCall()) { 705 var p2pAddr = CallManager.getWrtcAddress(callerP2PAddress); 706 CallManager._callToken = callToken; 707 CallManager._type = type; 708 var video = true; 709 if (type == "VOICE") 710 video = false; 711 if (CallManager._flashEnabled) { 712 ConnectionManager._dispatchEvent("FLASH_INIT_INCOMING_CALL", { 713 'callerP2PAddress': callerP2PAddress, 714 'type': type, 715 'zenonserver': zenonserver, 716 'callToken': callToken 717 }); 718 } else { 719 if (p2pAddr != null) { 720 CallManager._mcuCall = false; 721 zwrtc.placeP2PCall(p2pAddr, video); 722 } else { 723 this.connectToMCU(video); 724 this.sendPlaceCall(false); 725 } 726 } 727 } 728 }, 729 sendPlaceCall: function(isP2P) { 730 Platform.log("CallManager sendPlaceCall:" + CallManager._callToken + " p2p:" + isP2P); 731 if (CallManager._callToken != null) { 732 var zebra = new Zebra("org.zenon.server.zebra.ZebraHandler#placeCall"); 733 zebra.setZEvent("callToken", CallManager._callToken); 734 zebra.setZEvent("avfrw", "false"); 735 zebra.setZEvent("isP2P", isP2P); 736 var wid = 176; 737 var hei = 144; 738 try { 739 wid = zwrtc.in_video_width; 740 hei = zwrtc.in_video_height; 741 } catch (err) {} 742 zebra.setZEvent("width", wid); 743 zebra.setZEvent("height", hei); 744 zebra.setZEvent("client", "webrtc"); 745 //ConnectionManager.sendZebraToZS(zebra); 746 ConnectionManager.sendZSZebraCommand("placeCall", zebra); 747 CallManager._callToken = null; 748 } 749 } 750 }); 751