]> git.ipfire.org Git - thirdparty/freeswitch.git/commitdiff
fold livetables into verto obj and expose moderator mode
authorAnthony Minessale <anthm@freeswitch.org>
Fri, 11 Jul 2014 22:27:03 +0000 (03:27 +0500)
committerAnthony Minessale <anthm@freeswitch.org>
Fri, 11 Jul 2014 22:27:08 +0000 (03:27 +0500)
html5/verto/demo/index.html
html5/verto/demo/js/verto-min.js
html5/verto/demo/verto.js
html5/verto/js/src/jquery.FSRTC.js
html5/verto/js/src/jquery.verto.js
src/mod/applications/mod_conference/mod_conference.c
src/mod/endpoints/mod_verto/mod_verto.c
src/mod/endpoints/mod_verto/ws.c
src/switch_event.c

index 78bcbe444c857b7c82b7abc54a892ff9cb81298c..3f665acd422c6de6ad851e74067216acbc7468be 100644 (file)
       <br><br>
 
       <div id="conf">
-       <div style="color:black;font-family: verdana" align="center" id="mcount"></div>
-       <table width="800" cellspacing="0" cellpadding="0" border="0" align="center" id="example" class="jsDataTable">
+       <div style="color:black;font-family: verdana" align="center" id="conf_count"></div>
+       <div id="conf_mod"></div>
+       <div id="conf_display"></div>
+       <table width="800" cellspacing="0" cellpadding="0" border="0" align="center" id="conf_list" class="jsDataTable">
        </table>
       </div>
 
index 7b2bf2c083cec224335676a932e2bb977b6a9de0..abc2ec45f9c9cb85651c11a43f60aa491b835dd2 100644 (file)
@@ -34,7 +34,7 @@ getUserMedia({constraints:{audio:true,video:this.options.useVideo?{mandatory:thi
 function onError(){onStreamError(self);}
 getUserMedia({constraints:{audio:true,video:this.options.useVideo?{mandatory:this.options.videoParams,optional:[]}:null},video:this.options.useVideo?true:false,onsuccess:onSuccess,onerror:onError});};window.moz=!!navigator.mozGetUserMedia;function RTCPeerConnection(options){var w=window,PeerConnection=w.mozRTCPeerConnection||w.webkitRTCPeerConnection,SessionDescription=w.mozRTCSessionDescription||w.RTCSessionDescription,IceCandidate=w.mozRTCIceCandidate||w.RTCIceCandidate;var STUN={url:!moz?'stun:stun.l.google.com:19302':'stun:23.21.150.121'};var TURN={url:'turn:homeo@turn.bistri.com:80',credential:'homeo'};var iceServers={iceServers:options.iceServers||[STUN]};if(!moz&&!options.iceServers){if(parseInt(navigator.userAgent.match(/Chrom(e|ium)\/([0-9]+)\./)[2])>=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}];}
-var peer=new PeerConnection(iceServers,optional);openOffererChannel();var x=0;peer.onicecandidate=function(event){console.log("WTF ICE",event);if(event.candidate){options.onICE(event.candidate);}else{if(options.onICEComplete){options.onICEComplete();}
+var peer=new PeerConnection(iceServers,optional);openOffererChannel();var x=0;peer.onicecandidate=function(event){if(event.candidate){options.onICE(event.candidate);}else{if(options.onICEComplete){options.onICEComplete();}
 if(options.type=="offer"){if(!moz&&!x&&options.onICESDP){options.onICESDP(peer.localDescription);}}else{if(!x&&options.onICESDP){options.onICESDP(peer.localDescription);}}}};if(options.attachStream)peer.addStream(options.attachStream);if(options.attachStreams&&options.attachStream.length){var streams=options.attachStreams;for(var i=0;i<streams.length;i++){peer.addStream(streams[i]);}}
 peer.onaddstream=function(event){var remoteMediaStream=event.stream;remoteMediaStream.onended=function(){if(options.onRemoteStreamEnded)options.onRemoteStreamEnded(remoteMediaStream);};if(options.onRemoteStream)options.onRemoteStream(remoteMediaStream);};var constraints=options.constraints||{optional:[],mandatory:{OfferToReceiveAudio:true,OfferToReceiveVideo:true}};function createOffer(){if(!options.onOfferSDP)return;peer.createOffer(function(sessionDescription){sessionDescription.sdp=serializeSdp(sessionDescription.sdp);peer.setLocalDescription(sessionDescription);options.onOfferSDP(sessionDescription);if(moz&&options.onICESDP){options.onICESDP(sessionDescription);}},onSdpError,constraints);}
 function createAnswer(){if(options.type!="answer")return;peer.setRemoteDescription(new SessionDescription(options.offerSDP),onSdpSuccess,onSdpError);peer.createAnswer(function(sessionDescription){sessionDescription.sdp=serializeSdp(sessionDescription.sdp);peer.setLocalDescription(sessionDescription);if(options.onAnswerSDP){options.onAnswerSDP(sessionDescription);}},onSdpError,constraints);}
@@ -128,7 +128,7 @@ if(data.params.sdp&&data.params.sdp.indexOf("stereo=1")>0){data.params.useStereo
 dialog=new $.verto.dialog($.verto.enum.direction.inbound,verto,data.params);break;default:console.debug("INVALID METHOD OR NON-EXISTANT CALL REFERENCE IGNORED");break;}}
 return{method:data.method};}else{switch(data.method){case'verto.event':var list=null;var key=null;if(data.params){key=data.params.eventChannel;}
 if(key){list=verto.eventSUBS[key];if(!list){list=verto.eventSUBS[key.split(".")[0]];}}
-if(!list&&key&&verto.dialogs[key]){verto.dialogs[key].sendMessage($.verto.enum.message.pvtEvent,data.params);}else if(!list){if(!key){key="UNDEFINED";}
+if(!list&&key&&key===verto.sessid){if(verto.callbacks.onMessage){verto.callbacks.onMessage(verto,null,$.verto.enum.message.pvtEvent,data.params);}}else if(!list&&key&&verto.dialogs[key]){verto.dialogs[key].sendMessage($.verto.enum.message.pvtEvent,data.params);}else if(!list){if(!key){key="UNDEFINED";}
 console.error("UNSUBBED or invalid EVENT "+key+" IGNORED");}else{for(var i in list){var sub=list[i];if(!sub||!sub.ready){console.error("invalid EVENT for "+key+" IGNORED");}else if(sub.handler){sub.handler(verto,data.params,sub.userData);}else if(verto.callbacks.onEvent){verto.callbacks.onEvent(verto,data.params,sub.userData);}else{console.log("EVENT:",data.params);}}}
 break;case"verto.info":if(verto.callbacks.onMessage){verto.callbacks.onMessage(verto,null,$.verto.enum.message.info,data.params.msg);}
 console.error(data);console.debug("MESSAGE from: "+data.params.msg.from,data.params.msg.body);break;default:console.error("INVALID METHOD OR NON-EXISTANT CALL REFERENCE IGNORED",data.method);break;}}};var del_array=function(array,name){var r=[];var len=array.length;for(var i=0;i<len;i++){if(array[i]!=name){r.push(array[i]);}}
@@ -147,25 +147,39 @@ if(la.onChange){la.onChange(la,{serno:serno,action:"bootObj",data:val,redraw:tru
 if(la.checkSerno(serno)){var redraw=la._add(key,val,index);if(la.onChange){la.onChange(la,{serno:serno,action:"add",index:index,key:key,data:val,redraw:redraw});}}};la.modify=function(serno,val,key,index){if(key===null||key===undefined){key=serno;}
 if(la.checkSerno(serno)){la._add(key,val,index);if(la.onChange){la.onChange(la,{serno:serno,action:"modify",key:key,data:val,index:index});}}};la.del=function(serno,key,index){if(key===null||key===undefined){key=serno;}
 if(la.checkSerno(serno)){if(index===null||index<0||index===undefined){index=la.indexOf(key);}
-var ok=la._del(key);if(ok&&la.onChange){la.onChange(la,{serno:serno,action:"del",key:key,index:index});}}};var eventHandler=function(v,e,la){var packet=e.data;if(packet.name!=la.name){return;}
-console.error("READ:",packet);switch(packet.action){case"init":la.init(packet.wireSerno,packet.data,packet.hashKey,packet.arrIndex);break;case"bootObj":la.bootObj(packet.wireSerno,packet.data);break;case"add":la.add(packet.wireSerno,packet.data,packet.hashKey,packet.arrIndex);break;case"modify":if(!(packet.arrIndex||packet.hashKey)){console.error("Invalid Packet",packet);}else{la.modify(packet.wireSerno,packet.data,packet.hashKey,packet.arrIndex);}
+var ok=la._del(key);if(ok&&la.onChange){la.onChange(la,{serno:serno,action:"del",key:key,index:index});}}};var eventHandler=function(v,e,la){var packet=e.data;console.error("READ:",packet);if(packet.name!=la.name){return;}
+switch(packet.action){case"init":la.init(packet.wireSerno,packet.data,packet.hashKey,packet.arrIndex);break;case"bootObj":la.bootObj(packet.wireSerno,packet.data);break;case"add":la.add(packet.wireSerno,packet.data,packet.hashKey,packet.arrIndex);break;case"modify":if(!(packet.arrIndex||packet.hashKey)){console.error("Invalid Packet",packet);}else{la.modify(packet.wireSerno,packet.data,packet.hashKey,packet.arrIndex);}
 break;case"del":if(!(packet.arrIndex||packet.hashKey)){console.error("Invalid Packet",packet);}else{la.del(packet.wireSerno,packet.hashKey,packet.arrIndex);}
 break;case"clear":la.clear();break;case"reorder":la.reorder(packet.wireSerno,packet.order);break;default:if(la.checkSerno(packet.wireSerno)){if(la.onChange){la.onChange(la,{serno:packet.wireSerno,action:packet.action,data:packet.data});}}
 break;}};if(la.context){binding=la.verto.subscribe(la.context,{handler:eventHandler,userData:la,subParams:config.subParams});}
-la.destroy=function(){la._clear();la.verto.unsubscribe(binding);};la.bootstrap=function(obj){var self=la;self.clear();self.broadcast(self.context,{liveArray:{command:"bootstrap",context:self.context,name:self.name,obj:obj}});};la.changepage=function(obj){var self=la;self.clear();self.broadcast(self.context,{liveArray:{command:"changepage",context:la.context,name:la.name,obj:obj}});};la.heartbeat=function(obj){var self=la;var callback=function(){self.heartbeat.call(self,obj);};self.broadcast(self.context,{liveArray:{command:"heartbeat",context:self.context,name:self.name,obj:obj}});self.hb_pid=setTimeout(callback,30000);};la.bootstrap(la.user_obj);};$.verto.liveTable=function(verto,context,name,jq,config){var dt;var la=new $.verto.liveArray(verto,context,name,{subParams:config.subParams});var lt=this;lt.liveArray=la;lt.dataTable=dt;lt.verto=verto;lt.destroy=function(){if(dt){dt.fnDestroy();}
+la.destroy=function(){la._clear();la.verto.unsubscribe(binding);};la.sendCommand=function(cmd,obj){var self=la;self.broadcast(self.context,{liveArray:{command:cmd,context:self.context,name:self.name,obj:obj}});};la.bootstrap=function(obj){var self=la;la.sendCommand("bootstrap",obj);};la.changepage=function(obj){var self=la;self.clear();self.broadcast(self.context,{liveArray:{command:"changepage",context:la.context,name:la.name,obj:obj}});};la.heartbeat=function(obj){var self=la;var callback=function(){self.heartbeat.call(self,obj);};self.broadcast(self.context,{liveArray:{command:"heartbeat",context:self.context,name:self.name,obj:obj}});self.hb_pid=setTimeout(callback,30000);};la.bootstrap(la.user_obj);};$.verto.liveTable=function(verto,context,name,jq,config){var dt;var la=new $.verto.liveArray(verto,context,name,{subParams:config.subParams});var lt=this;lt.liveArray=la;lt.dataTable=dt;lt.verto=verto;lt.destroy=function(){if(dt){dt.fnDestroy();}
 if(la){la.destroy();}
 dt=null;la=null;};la.onErr=function(obj,args){console.error("Error: ",obj,args);};la.onChange=function(obj,args){var index=0;var iserr=0;if(!dt){if(!config.aoColumns){if(args.action!="init"){return;}
 config.aoColumns=[];for(var i in args.data){config.aoColumns.push({"sTitle":args.data[i]});}}
 dt=jq.dataTable(config);}
 if(dt&&(args.action=="del"||args.action=="modify")){index=args.index;if(index===undefined&&args.key){index=la.indexOf(args.key);}
 if(index===undefined){console.error("INVALID PACKET Missing INDEX\n",args);return;}}
+if(config.onChange){config.onChange(obj,args);}
 try{switch(args.action){case"bootObj":if(!args.data){console.error("missing data");return;}
 dt.fnClearTable();dt.fnAddData(obj.asArray());dt.fnAdjustColumnSizing();break;case"add":if(!args.data){console.error("missing data");return;}
 if(args.redraw>-1){dt.fnClearTable();dt.fnAddData(obj.asArray());}else{dt.fnAddData(args.data);}
 dt.fnAdjustColumnSizing();break;case"modify":if(!args.data){return;}
 console.debug(args,index);dt.fnUpdate(args.data,index);dt.fnAdjustColumnSizing();break;case"del":dt.fnDeleteRow(index);dt.fnAdjustColumnSizing();break;case"clear":dt.fnClearTable();break;case"reorder":dt.fnClearTable();dt.fnAddData(obj.asArray());break;case"hide":jq.hide();break;case"show":jq.show();break;}}catch(err){console.error("ERROR: "+err);iserr++;}
-if(iserr){obj.errs++;if(obj.errs<3){obj.bootstrap(obj.user_obj);}}else{obj.errs=0;}
-if(config.onChange){config.onChange(obj,args);}};la.onChange(la,{action:"init"});};$.verto.dialog=function(direction,verto,params){var dialog=this;dialog.params=$.extend({useVideo:verto.options.useVideo,useStereo:verto.options.useStereo,tag:verto.options.tag},params);dialog.verto=verto;dialog.direction=direction;dialog.lastState=null;dialog.state=dialog.lastState=$.verto.enum.state.new;dialog.callbacks=verto.callbacks;dialog.answered=false;dialog.attach=params.attach||false;if(dialog.params.callID){dialog.callID=dialog.params.callID;}else{dialog.callID=dialog.params.callID=generateGUID();}
+if(iserr){obj.errs++;if(obj.errs<3){obj.bootstrap(obj.user_obj);}}else{obj.errs=0;}};la.onChange(la,{action:"init"});};var CONFMAN_SERNO=1;$.verto.confMan=function(verto,params){var confMan=this;conf
+confMan.params=$.extend({tableID:null,statusID:null,mainModID:null,dialog:null,hasVid:false,laData:null,onBroadcast:null,onLaChange:null,onLaRow:null},params);confMan.verto=verto;confMan.serno=CONFMAN_SERNO++;function genMainMod(jq){var play_id="play_"+confMan.serno;var stop_id="stop_"+confMan.serno;var recording_id="recording_"+confMan.serno;var rec_stop_id="recording_stop"+confMan.serno;var div_id="confman_"+confMan.serno;var html="<div id='"+div_id+"'><br>"+"<button id='"+play_id+"'>Play</button>"+"<button id='"+stop_id+"'>Stop</button>"+"<button id='"+recording_id+"'>Record</button>"+"<button id='"+rec_stop_id+"'>Record Stop</button>"
++"<br><br></div>";jq.html(html);$("#"+play_id).click(function(){var file=prompt("Please enter file name","");confMan.modCommand("play",null,file);});$("#"+stop_id).click(function(){confMan.modCommand("stop",null,"all");});$("#"+recording_id).click(function(){var file=prompt("Please enter file name","");confMan.modCommand("recording",null,["start",file]);});$("#"+rec_stop_id).click(function(){confMan.modCommand("recording",null,["stop","all"]);});}
+function genControls(jq,rowid){var x=parseInt(rowid);var kick_id="kick_"+x;var tmute_id="tmute_"+x;var box_id="box_"+x;var volup_id="volume_in_up"+x;var voldn_id="volume_in_dn"+x;var html="<div id='"+box_id+"'>"+"<button id='"+kick_id+"'>KICK</button>"+"<button id='"+tmute_id+"'>MUTE</button>"+"<button id='"+voldn_id+"'>vol -</button>"+"<button id='"+volup_id+"'>vol +</button>"+"</div>";jq.html(html);if(!jq.data("mouse")){$("#"+box_id).hide();}
+jq.mouseover(function(e){jq.data({"mouse":true});$("#"+box_id).show();});jq.mouseout(function(e){jq.data({"mouse":false});$("#"+box_id).hide();});$("#"+kick_id).click(function(){confMan.modCommand("kick",x);});$("#"+tmute_id).click(function(){confMan.modCommand("tmute",x);});$("#"+volup_id).click(function(){confMan.modCommand("volume_in",x,"up");});$("#"+voldn_id).click(function(){confMan.modCommand("volume_in",x,"down");});return html;}
+var atitle="";var awidth=0;$(".jsDataTable").width(confMan.params.hasVid?"900px":"800px");if(confMan.params.laData.role==="moderator"){atitle="Action";awidth=200;if(confMan.params.mainModID){genMainMod($(confMan.params.mainModID));}else{$(confMan.params.mainModID).html("");}
+verto.subscribe(confMan.params.laData.modChannel,{handler:function(v,e){console.error("MODDATA:",e.data);if(confMan.params.onBroadcast){confMan.params.onBroadcast(verto,confMan,e.data);}
+if(confMan.params.displayID){$(confMan.params.displayID).html(e.data.response+"<br><br>");if(confMan.lastTimeout){clearTimeout(confMan.lastTimeout);confMan.lastTimeout=0;}
+confMan.lastTimeout=setTimeout(function(){$(confMan.params.displayID).html("")},4000);}}});}
+confMan.lt=new $.verto.liveTable(verto,confMan.params.laData.laChannel,confMan.params.laData.laName,$(confMan.params.tableID),{subParams:{callID:confMan.params.dialog?confMan.params.dialog.callID:null},"onChange":function(obj,args){$(confMan.params.statusID).text("Conference Members: "+" ("+obj.arrayLen()+" Total)");if(confMan.params.onLaChange){confMan.params.onLaChange(verto,confMan,$.verto.enum.confEvent.laChange,obj,args);}},"aaData":[],"aoColumns":[{"sTitle":"ID"},{"sTitle":"Number"},{"sTitle":"Name"},{"sTitle":"Codec"},{"sTitle":"Status","sWidth":confMan.params.hasVid?"300px":"150px"},{"sTitle":atitle,"sWidth":awidth,}],"bAutoWidth":true,"bDestroy":true,"bSort":false,"bInfo":false,"bFilter":false,"bLengthChange":false,"bPaginate":false,"iDisplayLength":1000,"oLanguage":{"sEmptyTable":"The Conference is Empty....."},"fnRowCallback":function(nRow,aData,iDisplayIndex,iDisplayIndexFull){if(!aData[5]){var $row=$('td:eq(5)',nRow);genControls($row,aData);if(confMan.params.onLaRow){confMan.params.onLaRow(verto,confMan,$row,aData);}}},});}
+$.verto.confMan.prototype.modCommand=function(cmd,id,value){var confMan=this;confMan.verto.sendMethod("verto.broadcast",{"eventChannel":confMan.params.laData.modChannel,"data":{"application":"conf-control","command":cmd,"id":id,"value":value}});}
+$.verto.confMan.prototype.destroy=function(){var confMan=this;if(confMan.lt){confMan.lt.destroy();}
+if(confMan.params.laData.modChannel){confMan.verto.unsubscribe(confMan.params.laData.modChannel);}
+if(confMan.params.mainModID){$(confMan.params.mainModID).html("");}}
+$.verto.dialog=function(direction,verto,params){var dialog=this;dialog.params=$.extend({useVideo:verto.options.useVideo,useStereo:verto.options.useStereo,tag:verto.options.tag},params);dialog.verto=verto;dialog.direction=direction;dialog.lastState=null;dialog.state=dialog.lastState=$.verto.enum.state.new;dialog.callbacks=verto.callbacks;dialog.answered=false;dialog.attach=params.attach||false;if(dialog.params.callID){dialog.callID=dialog.params.callID;}else{dialog.callID=dialog.params.callID=generateGUID();}
 if(dialog.params.tag){dialog.audioStream=document.getElementById(dialog.params.tag);if(dialog.params.useVideo){dialog.videoStream=dialog.audioStream;}}
 dialog.verto.dialogs[dialog.callID]=dialog;var RTCcallbacks={};if(dialog.direction==$.verto.enum.direction.inbound){dialog.params.remote_caller_id_name=dialog.params.caller_id_name;dialog.params.remote_caller_id_number=dialog.params.caller_id_number;if(!dialog.params.remote_caller_id_name){dialog.params.remote_caller_id_name="Nobody";}
 if(!dialog.params.remote_caller_id_number){dialog.params.remote_caller_id_number="UNKNOWN";}
index 1aa29f8558c84f33eff9900b11b7b0684d5be4e9..1dfbeb84c9811a5aed5771cf100be5af87bd1ec3 100644 (file)
@@ -1,6 +1,6 @@
 'use strict';
 var cur_call = null;
-var la = null;
+var confMan = null;
 var $display = $("#display");
 var verto;
 var ringing = false;
@@ -9,10 +9,10 @@ function display(msg) {
     $("#calltitle").html(msg);
 }
 
-function clearLa() {
-    if (la) {
-        la.destroy();
-        la = null;
+function clearConfMan() {
+    if (confMan) {
+        confMan.destroy();
+        confMan = null;
     }
 
     $("#conf").hide();
@@ -61,53 +61,21 @@ var callbacks = {
             console.error("pvtEvent", data.pvtData.action);
             if (data.pvtData) {
                 switch (data.pvtData.action) {
+
                 case "conference-liveArray-part":
-                    clearLa();
+                    clearConfMan();
                     break;
                 case "conference-liveArray-join":
-
-                    $(".jsDataTable").width(check_vid() ? "650px" : "550px");
-
-                    la = new $.verto.liveTable(verto, data.pvtData.laChannel, data.pvtData.laName, $('#example'), {
-                        subParams: {
-                            callID: dialog.callID
-                        },
-
-                        "onChange": function(obj, args) {
-                            //var len = obj.asArray().length;
-                            $("#mcount").text("Conference Members: " + " (" + obj.arrayLen() + " Total)");
-                        },
-
-                        "aaData": [],
-                        "aoColumns": [{
-                            "sTitle": "ID"
-                        },
-                        {
-                            "sTitle": "Number"
-                        },
-                        {
-                            "sTitle": "Name"
-                        },
-                        {
-                            "sTitle": "Codec"
-                        },
-                        {
-                            "sTitle": "Status",
-                            "sWidth": check_vid() ? "300px" : "150px"
-                        }],
-                        "bAutoWidth": true,
-                        "bDestroy": true,
-                        "bSort": false,
-                        "bInfo": false,
-                        "bFilter": false,
-                        "bLengthChange": false,
-                        "bPaginate": false,
-                        "iDisplayLength": 1000,
-
-                        "oLanguage": {
-                            "sEmptyTable": "The Conference is Empty....."
-                        }
-                    });
+                    clearConfMan();
+                   confMan = new $.verto.confMan(verto, {
+                       tableID: "#conf_list",
+                       statusID: "#conf_count",
+                       mainModID: "#conf_mod",
+                       displayID: "#conf_display",
+                       dialog: dialog,
+                       hasVid: check_vid(),
+                       laData: data.pvtData
+                   });
 
                     $("#conf").show();
 
@@ -177,7 +145,7 @@ var callbacks = {
             break;
         case $.verto.enum.state.hangup:
         case $.verto.enum.state.destroy:
-            clearLa();
+            clearConfMan();
             goto_page("main");
             cur_call = null;
             break;
@@ -306,6 +274,8 @@ function pop(id, cname, dft) {
 
 
 function init() {
+    cur_call = null;
+
     pop("#ext", "verto_demo_ext", "3500");
     pop("#name", "verto_demo_name", "FreeSWITCH User");
     pop("#cid", "verto_demo_cid", "1008");
@@ -351,8 +321,7 @@ function init() {
             "minWidth": "1280",
             "minHeight": "720"
         }
-    },
-    callbacks);
+    },callbacks);
 
     $("#login").change(function(e) {
         $("#cid").val(e.currentTarget.value);
index 28f9306b9e2308a85c4ed1715e044639c242b390..a90d79feba855674dab6c6e2f5f17a21cba1bd36 100644 (file)
         var x = 0;
 
         peer.onicecandidate = function(event) {
-            console.log("WTF ICE", event);
-
             if (event.candidate) {
                 options.onICE(event.candidate);
             } else {
index 54e24e46512dcd63697155a0bc38e689d85bb48b..4377ae5eef71064eeb42a2a66febb70ce6da80aa 100644 (file)
     }
 
     var SERNO = 1;
-
+    
     function do_subscribe(verto, channel, subChannels, sparams) {
         var params = sparams || {};
 
                     }
                 }
 
-                if (!list && key && verto.dialogs[key]) {
+               if (!list && key && key === verto.sessid) {
+                   if (verto.callbacks.onMessage) { 
+                       verto.callbacks.onMessage(verto, null, $.verto.enum.message.pvtEvent, data.params);
+                   }
+                } else if (!list && key && verto.dialogs[key]) {
                     verto.dialogs[key].sendMessage($.verto.enum.message.pvtEvent, data.params);
                 } else if (!list) {
                     if (!key) {
         var eventHandler = function(v, e, la) {
             var packet = e.data;
 
+            console.error("READ:", packet);
+
             if (packet.name != la.name) {
                 return;
             }
 
-            console.error("READ:", packet);
-
             switch (packet.action) {
 
             case "init":
             la.verto.unsubscribe(binding);
         };
 
-        la.bootstrap = function(obj) {
+       la.sendCommand = function(cmd, obj) {
             var self = la;
-
-            self.clear();
-            self.broadcast(self.context, {
-                liveArray: {
-                    command: "bootstrap",
+           self.broadcast(self.context, {
+               liveArray: {
+                    command: cmd,
                     context: self.context,
                     name: self.name,
                     obj: obj
                 }
-            });
+           });
+       };
 
+        la.bootstrap = function(obj) {
+            var self = la;
+           la.sendCommand("bootstrap", obj);
             //self.heartbeat();
         };
 
                 }
             }
 
+            if (config.onChange) {
+                config.onChange(obj, args);
+            }
+
             try {
                 switch (args.action) {
                 case "bootObj":
             } else {
                 obj.errs = 0;
             }
-
-            if (config.onChange) {
-                config.onChange(obj, args);
-            }
-
+           
         };
 
         la.onChange(la, {
 
     };
 
+    var CONFMAN_SERNO = 1;
+    
+    $.verto.confMan = function(verto, params) {
+       var confMan = this;
+       conf
+        confMan.params = $.extend({
+           tableID: null,
+           statusID: null,
+           mainModID: null,
+           dialog: null,
+           hasVid: false,
+           laData: null,
+           onBroadcast: null,
+           onLaChange: null,
+           onLaRow: null
+        },
+        params);
+
+       confMan.verto = verto;
+       confMan.serno = CONFMAN_SERNO++;
+
+       function genMainMod(jq) {
+           var play_id = "play_" + confMan.serno;
+           var stop_id = "stop_" + confMan.serno;
+           var recording_id = "recording_" + confMan.serno;
+           var rec_stop_id = "recording_stop" + confMan.serno;
+           var div_id = "confman_" + confMan.serno;
+
+           var html =  "<div id='" + div_id + "'><br>" +
+               "<button id='" + play_id + "'>Play</button>" +
+               "<button id='" + stop_id + "'>Stop</button>" +
+               "<button id='" + recording_id + "'>Record</button>" +
+               "<button id='" + rec_stop_id + "'>Record Stop</button>" 
+
+           + "<br><br></div>";
+
+           jq.html(html);
+
+           $("#" + play_id).click(function() {
+               var file = prompt("Please enter file name", "");
+               confMan.modCommand("play", null, file);
+           });
+
+           $("#" + stop_id).click(function() {
+               confMan.modCommand("stop", null, "all");
+           });
+
+           $("#" + recording_id).click(function() {
+               var file = prompt("Please enter file name", "");
+               confMan.modCommand("recording", null, ["start", file]);
+           });
+
+           $("#" + rec_stop_id).click(function() {
+               confMan.modCommand("recording", null, ["stop", "all"]);
+           });
+
+       }
+
+       function genControls(jq, rowid) {
+           var x = parseInt(rowid);
+           var kick_id = "kick_" + x;
+           var tmute_id = "tmute_" + x;
+           var box_id = "box_" + x;
+           var volup_id = "volume_in_up" + x;
+           var voldn_id = "volume_in_dn" + x;
+
+           
+           var html = "<div id='" + box_id + "'>" + 
+               "<button id='" + kick_id + "'>KICK</button>" + 
+               "<button id='" + tmute_id + "'>MUTE</button>" +
+               "<button id='" + voldn_id + "'>vol -</button>" +
+               "<button id='" + volup_id + "'>vol +</button>" +
+               "</div>"
+           ;
+           
+           jq.html(html);
+           
+           if (!jq.data("mouse")) {
+               $("#" + box_id).hide();
+           }
+
+           jq.mouseover(function(e) {
+               jq.data({"mouse": true});
+               $("#" + box_id).show();
+           });
+
+           jq.mouseout(function(e) {
+               jq.data({"mouse": false});
+               $("#" + box_id).hide();
+           });
+
+           $("#" + kick_id).click(function() {
+               confMan.modCommand("kick", x);
+           });
+
+           $("#" + tmute_id).click(function() {
+               confMan.modCommand("tmute", x);
+           });
+
+           $("#" + volup_id).click(function() {
+               confMan.modCommand("volume_in", x, "up");
+           });
+
+           $("#" + voldn_id).click(function() {
+               confMan.modCommand("volume_in", x, "down");
+           });
+
+           return html;
+       }
+
+
+
+       var atitle = "";
+       var awidth = 0;
+                   
+        $(".jsDataTable").width(confMan.params.hasVid ? "900px" : "800px");
+       
+       if (confMan.params.laData.role === "moderator") {
+           atitle = "Action";
+           awidth = 200;
+           
+           if (confMan.params.mainModID) {
+               genMainMod($(confMan.params.mainModID));
+           } else {
+               $(confMan.params.mainModID).html("");
+           }
+
+           verto.subscribe(confMan.params.laData.modChannel, {
+               handler: function(v, e) {
+                   console.error("MODDATA:", e.data);
+                   if (confMan.params.onBroadcast) {
+                       confMan.params.onBroadcast(verto, confMan, e.data);
+                   }
+                   if (confMan.params.displayID) {
+                       $(confMan.params.displayID).html(e.data.response + "<br><br>");
+                       if (confMan.lastTimeout) {
+                           clearTimeout(confMan.lastTimeout);
+                           confMan.lastTimeout = 0;
+                       }
+                       confMan.lastTimeout = setTimeout(function() { $(confMan.params.displayID).html("")}, 4000);
+                   }
+
+               }
+           });
+           
+       }
+       
+        confMan.lt = new $.verto.liveTable(verto, confMan.params.laData.laChannel, confMan.params.laData.laName, $(confMan.params.tableID), {
+            subParams: {
+                callID: confMan.params.dialog ? confMan.params.dialog.callID : null
+            },
+           
+           
+            "onChange": function(obj, args) {
+                $(confMan.params.statusID).text("Conference Members: " + " (" + obj.arrayLen() + " Total)");
+               if (confMan.params.onLaChange) {
+                   confMan.params.onLaChange(verto, confMan, $.verto.enum.confEvent.laChange, obj, args);
+               }
+            },
+
+            "aaData": [],
+            "aoColumns": [{
+                "sTitle": "ID"
+            },
+                          {
+                              "sTitle": "Number"
+                          },
+                          {
+                              "sTitle": "Name"
+                          },
+                          {
+                              "sTitle": "Codec"
+                          },
+                          {
+                              "sTitle": "Status",
+                              "sWidth": confMan.params.hasVid ? "300px" : "150px"
+                         },
+                          {
+                             "sTitle": atitle,
+                             "sWidth": awidth,
+                             
+                          }],
+            "bAutoWidth": true,
+            "bDestroy": true,
+            "bSort": false,
+            "bInfo": false,
+            "bFilter": false,
+            "bLengthChange": false,
+            "bPaginate": false,
+            "iDisplayLength": 1000,
+
+            "oLanguage": {
+                "sEmptyTable": "The Conference is Empty....."
+            },
+
+
+           "fnRowCallback": function(nRow, aData, iDisplayIndex, iDisplayIndexFull) {
+
+               if (!aData[5]) {
+                   var $row = $('td:eq(5)', nRow);
+                   genControls($row, aData);
+                   
+                   if (confMan.params.onLaRow) {
+                       confMan.params.onLaRow(verto, confMan, $row, aData);
+                   }
+
+               }
+           },
+
+        });
+    }
+
+    $.verto.confMan.prototype.modCommand = function(cmd, id, value) {
+       var confMan = this;
+       
+       confMan.verto.sendMethod("verto.broadcast", {
+           "eventChannel": confMan.params.laData.modChannel,
+           "data": {
+               "application": "conf-control",
+               "command": cmd,
+               "id": id, 
+               "value": value
+           }
+       });
+    }
+
+    $.verto.confMan.prototype.destroy = function() {
+       var confMan = this;
+
+       if (confMan.lt) {
+           confMan.lt.destroy();
+       }
+
+       if (confMan.params.laData.modChannel) {
+           confMan.verto.unsubscribe(confMan.params.laData.modChannel);
+       }
+
+       if (confMan.params.mainModID) {
+           $(confMan.params.mainModID).html("");
+       }
+    }
+
     $.verto.dialog = function(direction, verto, params) {
         var dialog = this;
 
             dialog.setState($.verto.enum.state.destroy);
             break;
         case $.verto.enum.state.destroy:
-            delete verto.dialogs[dialog.callID];
+           delete verto.dialogs[dialog.callID];
             dialog.rtc.stop();
             break;
         }
index 6ce838f3522f04dcd7e76cc82a9710d0d312eebb..a4ac240577e8f986ef4abd9838c7687a659c4822 100644 (file)
@@ -343,6 +343,7 @@ typedef struct conference_obj {
        char *name;
        char *la_name;
        char *la_event_channel;
+       char *mod_event_channel;
        char *desc;
        char *timer_name;
        char *tts_engine;
@@ -1517,6 +1518,102 @@ static cJSON *conference_json_render(conference_obj_t *conference, cJSON *req)
        return json;
 }
 
+static void conference_mod_event_channel_handler(const char *event_channel, cJSON *json, const char *key, switch_event_channel_id_t id)
+{
+       cJSON *data; 
+       const char *action = NULL;
+       char *value = NULL;
+       cJSON *jid = 0;
+       char *conf_name = strdup(event_channel + 15);
+       int cid = 0;
+       char *p;
+       switch_stream_handle_t stream = { 0 };
+       char *exec = NULL;
+       cJSON *msg, *jdata, *jvalue;
+       char *argv[10] = {0};
+       int argc = 0;
+
+       if (conf_name && (p = strchr(conf_name, '@'))) {
+               *p = '\0';
+       }
+
+       if ((data = cJSON_GetObjectItem(json, "data"))) {
+               action = cJSON_GetObjectCstr(data, "command");
+               if ((jid = cJSON_GetObjectItem(data, "id"))) {
+                       cid = jid->valueint;
+               }
+
+               if ((jvalue = cJSON_GetObjectItem(data, "value"))) {
+
+                       if (jvalue->type == cJSON_Array) {
+                               int i;
+                               argc = cJSON_GetArraySize(jvalue);
+                               if (argc > 10) argc = 10;
+
+                               for (i = 0; i < argc; i++) {
+                                       cJSON *str = cJSON_GetArrayItem(jvalue, i);
+                                       if (str->type == cJSON_String) {
+                                               argv[i] = str->valuestring;
+                                       }
+                               }
+                       } else if (jvalue->type == cJSON_String) { 
+                               value = jvalue->valuestring;
+                               argv[argc++] = value;
+                       }
+               }
+       }
+
+       switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ALERT, "conf %s CMD %s [%s] %d\n", conf_name, key, action, cid);
+
+       if (zstr(action)) {
+               goto end;
+       }
+
+       SWITCH_STANDARD_STREAM(stream);
+       
+       if (!strcasecmp(action, "kick") || !strcasecmp(action, "mute") || !strcasecmp(action, "unmute") || !strcasecmp(action, "tmute")) {
+               exec = switch_mprintf("%s %s %d", conf_name, action, cid);
+       } else if (!strcasecmp(action, "volume_in") || !strcasecmp(action, "volume_out")) {
+               exec = switch_mprintf("%s %s %d %s", conf_name, action, cid, argv[0]);
+       } else if (!strcasecmp(action, "play") || !strcasecmp(action, "stop")) {
+               exec = switch_mprintf("%s %s %s", conf_name, action, argv[0]);
+       } else if (!strcasecmp(action, "recording")) {
+               if (!argv[1]) {
+                       argv[1] = "all";
+               }
+               exec = switch_mprintf("%s %s %s %s", conf_name, action, argv[0], argv[1]);
+       }
+
+       if (exec) {
+               conf_api_main(exec, NULL, &stream);
+       }
+
+ end:
+
+       msg = cJSON_CreateObject();
+       jdata = json_add_child_obj(msg, "data", NULL);
+
+       cJSON_AddItemToObject(msg, "eventChannel", cJSON_CreateString(event_channel));
+       cJSON_AddItemToObject(jdata, "action", cJSON_CreateString("response"));
+       
+       if (exec) {
+               cJSON_AddItemToObject(jdata, "conf-command", cJSON_CreateString(exec));
+               cJSON_AddItemToObject(jdata, "response", cJSON_CreateString((char *)stream.data));
+               switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ALERT,"RES [%s][%s]\n", exec, (char *)stream.data);
+       } else {
+               cJSON_AddItemToObject(jdata, "error", cJSON_CreateString("Invalid Command"));
+       }
+
+       switch_event_channel_broadcast(event_channel, &msg, __FILE__, globals.event_channel_id);
+
+
+       switch_safe_free(stream.data);
+       switch_safe_free(exec);
+
+       switch_safe_free(conf_name);
+
+}
+
 static void conference_la_event_channel_handler(const char *event_channel, cJSON *json, const char *key, switch_event_channel_id_t id)
 {
        switch_live_array_parse_json(json, globals.event_channel_id);
@@ -1995,22 +2092,28 @@ static void adv_la(conference_obj_t *conference, conference_member_t *member, sw
                cJSON *msg, *data;
                const char *uuid = switch_core_session_get_uuid(member->session);
                const char *cookie = switch_channel_get_variable(member->channel, "event_channel_cookie");
+               const char *event_channel = cookie ? cookie : uuid;
 
                msg = cJSON_CreateObject();
                data = json_add_child_obj(msg, "pvtData", NULL);
 
-               cJSON_AddItemToObject(msg, "eventChannel", cJSON_CreateString(uuid));
+               cJSON_AddItemToObject(msg, "eventChannel", cJSON_CreateString(event_channel));
                cJSON_AddItemToObject(msg, "eventType", cJSON_CreateString("channelPvtData"));
 
                cJSON_AddItemToObject(data, "action", cJSON_CreateString(join ? "conference-liveArray-join" : "conference-liveArray-part"));
                cJSON_AddItemToObject(data, "laChannel", cJSON_CreateString(conference->la_event_channel));
                cJSON_AddItemToObject(data, "laName", cJSON_CreateString(conference->la_name));
+               cJSON_AddItemToObject(data, "role", cJSON_CreateString(switch_test_flag(member, MFLAG_MOD) ? "moderator" : "participant"));
+               if (switch_test_flag(member, MFLAG_MOD)) {
+                       cJSON_AddItemToObject(data, "modChannel", cJSON_CreateString(conference->mod_event_channel));
+               }
+               
+               switch_event_channel_broadcast(event_channel, &msg, modname, globals.event_channel_id);
 
                if (cookie) {
                        switch_event_channel_permission_modify(cookie, conference->la_event_channel, join);
+                       switch_event_channel_permission_modify(cookie, conference->mod_event_channel, join);
                }
-
-               switch_event_channel_broadcast(uuid, &msg, modname, globals.event_channel_id);
        }
 }
 
@@ -2279,8 +2382,14 @@ static switch_status_t conference_add_member(conference_obj_t *conference, confe
                                                                                                                                        switch_channel_get_variable(member->channel, "original_read_rate")
                                                                                                                                        ));
 
+
+
+
                member->status_field = cJSON_CreateString("");
                cJSON_AddItemToArray(member->json, member->status_field);
+
+               cJSON_AddItemToArray(member->json, cJSON_CreateNull());
+
                member_update_status_field(member);
                //switch_live_array_add_alias(conference->la, switch_core_session_get_uuid(member->session), "conference");
                adv_la(conference, member, SWITCH_TRUE);
@@ -2875,7 +2984,6 @@ static void *SWITCH_THREAD_FUNC conference_video_thread_run(switch_thread_t *thr
 
 static void conference_command_handler(switch_live_array_t *la, const char *cmd, const char *sessid, cJSON *jla, void *user_data)
 {
-       
 }
 
 /* Main monitor thread (1 per distinct conference room) */
@@ -2930,8 +3038,10 @@ static void *SWITCH_THREAD_FUNC conference_thread_run(switch_thread_t *thread, v
 
                if (strchr(conference->name, '@')) {
                        conference->la_event_channel = switch_core_sprintf(conference->pool, "conference-liveArray.%s", conference->name);
+                       conference->mod_event_channel = switch_core_sprintf(conference->pool, "conference-mod.%s", conference->name);
                } else {
                        conference->la_event_channel = switch_core_sprintf(conference->pool, "conference-liveArray.%s@%s", conference->name, conference->domain);
+                       conference->mod_event_channel = switch_core_sprintf(conference->pool, "conference-mod.%s@%s", conference->name, conference->domain);
                }
 
                conference->la_name = switch_core_strdup(conference->pool, conference->name);
@@ -6279,7 +6389,19 @@ static switch_status_t conf_api_sub_energy(conference_member_t *member, switch_s
 
        if (data) {
                lock_member(member);
-               member->energy_level = atoi((char *) data);
+               if (!strcasecmp(data, "up")) {
+                       member->energy_level += 200;
+                       if (member->energy_level > 1800) {
+                               member->energy_level = 1800;
+                       }
+               } else if (!strcasecmp(data, "down")) {
+                       member->energy_level -= 200;
+                       if (member->energy_level < 0) {
+                               member->energy_level = 0;
+                       }
+               } else {
+                       member->energy_level = atoi((char *) data);
+               }
                unlock_member(member);
        }
        if (stream != NULL) {
@@ -6397,9 +6519,18 @@ static switch_status_t conf_api_sub_volume_in(conference_member_t *member, switc
 
        if (data) {
                lock_member(member);
-               member->volume_in_level = atoi((char *) data);
-               switch_normalize_volume(member->volume_in_level);
+               if (!strcasecmp(data, "up")) {
+                       member->volume_in_level++;
+                       switch_normalize_volume(member->volume_in_level);
+               } else if (!strcasecmp(data, "down")) {
+                       member->volume_in_level--;
+                       switch_normalize_volume(member->volume_in_level);
+               } else {
+                       member->volume_in_level = atoi((char *) data);
+                       switch_normalize_volume(member->volume_in_level);
+               }
                unlock_member(member);
+
        }
        if (stream != NULL) {
                stream->write_function(stream, "Volume IN %u = %d\n", member->id, member->volume_in_level);
@@ -6424,8 +6555,16 @@ static switch_status_t conf_api_sub_volume_out(conference_member_t *member, swit
 
        if (data) {
                lock_member(member);
-               member->volume_out_level = atoi((char *) data);
-               switch_normalize_volume(member->volume_out_level);
+               if (!strcasecmp(data, "up")) {
+                       member->volume_out_level++;
+                       switch_normalize_volume(member->volume_out_level);
+               } else if (!strcasecmp(data, "down")) {
+                       member->volume_out_level--;
+                       switch_normalize_volume(member->volume_out_level);
+               } else {
+                       member->volume_out_level = atoi((char *) data);
+                       switch_normalize_volume(member->volume_out_level);
+               }
                unlock_member(member);
        }
        if (stream != NULL) {
@@ -10752,6 +10891,7 @@ SWITCH_MODULE_LOAD_FUNCTION(mod_conference_load)
 
        switch_event_channel_bind("conference", conference_event_channel_handler, &globals.event_channel_id);
        switch_event_channel_bind("conference-liveArray", conference_la_event_channel_handler, &globals.event_channel_id);
+       switch_event_channel_bind("conference-mod", conference_mod_event_channel_handler, &globals.event_channel_id);
 
        /* build api interface help ".syntax" field string */
        p = strdup("");
index ffa95cd5467e94f765a320107d36e34abc033428..8de51dc5b2542ee0ad7892b91f9c2480862e8e9e 100644 (file)
@@ -3861,6 +3861,7 @@ static switch_call_cause_t verto_outgoing_channel(switch_core_session_t *session
                switch_channel_set_variable(channel, "jsock_uuid_str", tech_pvt->jsock_uuid);
                switch_channel_set_variable(channel, "event_channel_cookie", tech_pvt->jsock_uuid);
 
+
                if ((caller_profile = switch_caller_profile_dup(switch_core_session_get_pool(*new_session), outbound_profile))) {
                        switch_channel_set_caller_profile(channel, caller_profile);        
                } 
@@ -3880,7 +3881,7 @@ static switch_call_cause_t verto_outgoing_channel(switch_core_session_t *session
 
 void verto_broadcast(const char *event_channel, cJSON *json, const char *key, switch_event_channel_id_t id)
 {
-       if (globals.debug > 10) {
+       if (globals.debug > 9) {
                char *json_text;
                if ((json_text = cJSON_Print(json))) {
                        switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_ALERT, "EVENT BROADCAST %s %s\n", event_channel, json_text);
index 11b92945c890f03207e669175a43075b83bdaca3..0ee867dba52adab50842ab65efb0debb3bfcc502 100644 (file)
@@ -368,18 +368,25 @@ ssize_t ws_raw_read(wsh_t *wsh, void *data, size_t bytes, int block)
 ssize_t ws_raw_write(wsh_t *wsh, void *data, size_t bytes)
 {
        size_t r;
+       int sanity = 2000;
 
        if (wsh->ssl) {
                do {
                        r = SSL_write(wsh->ssl, data, bytes);
-               } while (r == -1 && SSL_get_error(wsh->ssl, r) == SSL_ERROR_WANT_WRITE);
+                       if (sanity < 2000) {
+                               ms_sleep(1);
+                       }
+               } while (--sanity > 0 && r == -1 && SSL_get_error(wsh->ssl, r) == SSL_ERROR_WANT_WRITE);
 
                return r;
        }
 
        do {
                r = send(wsh->sock, data, bytes, 0);
-       } while (r == -1 && xp_is_blocking(xp_errno()));
+               if (sanity < 2000) {
+                       ms_sleep(1);
+               }
+       } while (--sanity > 0 && r == -1 && xp_is_blocking(xp_errno()));
 
        //if (r<0) {
                //printf("wRITE FAIL: %s\n", strerror(errno));
index a2a68fdb68c0048009b3cb587d0a5e2da8c2d0b5..b108ac1be5822ba8febed44128e2857d5a91f7f9 100644 (file)
@@ -2823,6 +2823,7 @@ static uint32_t _switch_event_channel_broadcast(const char *event_channel, const
                        if (np->id == id) {
                                continue;
                        }
+                       
                        np->func(broadcast_channel, json, key, id);
                        x++;
                }