Commit dd5f8282 authored by Dele Olajide's avatar Dele Olajide Committed by dele

Jitsi Videobridge plugin code refresh

git-svn-id: http://svn.igniterealtime.org/svn/repos/openfire/trunk@13841 b35dd754-fafc-0310-a699-88a17e54d16e
parent ff3733c7
...@@ -47,7 +47,7 @@ Jitsi Video Bridge Plugin Changelog ...@@ -47,7 +47,7 @@ Jitsi Video Bridge Plugin Changelog
<p><b>1.1</b> -- Dec 4th, 2013</p> <p><b>1.1</b> -- Dec 4th, 2013</p>
<ul> <ul>
<li>OF-716 Added to Openfire plugins with webrtc demo video application</li> <li>OF-716 Added to Openfire plugins with jitmeet web video conference application</li>
</ul> </ul>
<p><b>1.0</b> -- Apr 12, 2013</p> <p><b>1.0</b> -- Apr 12, 2013</p>
......
...@@ -63,7 +63,7 @@ Jitsi Videobridge does not mix the video channels into a composite video stream, ...@@ -63,7 +63,7 @@ Jitsi Videobridge does not mix the video channels into a composite video stream,
but only relays the received video channels to all call participants. but only relays the received video channels to all call participants.
Therefore, while it does need to run on a server with good network bandwidth, Therefore, while it does need to run on a server with good network bandwidth,
CPU horsepower is not that critical for performance. CPU horsepower is not that critical for performance.
A demo video conference application using WebRTC is included. The JitMeet video conference application using WebRTC is included.
</p> </p>
...@@ -79,7 +79,7 @@ Under Server settings -> Jitsi Videobridge tab you can configure it. ...@@ -79,7 +79,7 @@ Under Server settings -> Jitsi Videobridge tab you can configure it.
<h2>How to use</h2> <h2>How to use</h2>
To run the demo video conference application, point your browser at https://your_server:7443/videobridge To run the demo video conference application, point your browser at https://your_server:7443/jitmeet
</body> </body>
</html> </html>
...@@ -168,6 +168,7 @@ $(document).bind('callterminated.jingle', function (event, sid, reason) { ...@@ -168,6 +168,7 @@ $(document).bind('callterminated.jingle', function (event, sid, reason) {
$(document).bind('joined.muc', function (event, jid, info) { $(document).bind('joined.muc', function (event, jid, info) {
console.log('onJoinComplete', info); console.log('onJoinComplete', info);
updateRoomUrl(window.location.href); updateRoomUrl(window.location.href);
showToolbar();
if (Object.keys(connection.emuc.members).length < 1) { if (Object.keys(connection.emuc.members).length < 1) {
focus = new ColibriFocus(connection, config.hosts.bridge); focus = new ColibriFocus(connection, config.hosts.bridge);
return; return;
...@@ -177,6 +178,7 @@ $(document).bind('joined.muc', function (event, jid, info) { ...@@ -177,6 +178,7 @@ $(document).bind('joined.muc', function (event, jid, info) {
$(document).bind('entered.muc', function (event, jid, info) { $(document).bind('entered.muc', function (event, jid, info) {
console.log('entered', jid, info); console.log('entered', jid, info);
console.log(focus); console.log(focus);
if (focus !== null) { if (focus !== null) {
// FIXME: this should prepare the video // FIXME: this should prepare the video
if (focus.confid === null) { if (focus.confid === null) {
...@@ -428,6 +430,10 @@ function openChat() { ...@@ -428,6 +430,10 @@ function openChat() {
$('#usermsg').focus(); $('#usermsg').focus();
} }
function showToolbar() {
$('#toolbar').css({visibility:"visible"});
}
function updateRoomUrl(newRoomUrl) { function updateRoomUrl(newRoomUrl) {
roomUrl = newRoomUrl; roomUrl = newRoomUrl;
} }
Sorry, this currently only works with chrome because it uses "Plan B". <html>
<head>
<title></title>
<link rel="stylesheet" type="text/css" media="screen" href="css/chromeonly.css" />
</head>
<body>
<!-- wrap starts here -->
<div id="wrap">
<a href="http://google.com/chrome"><div id="left"></div></a>
<div id="middle"></div>
<div id="text">
<p>This service only works with Chrome.</p>
<p><a href="http://google.com/chrome">Download Chrome</a></p>
</div>
<!-- wrap ends here -->
</div>
</body>
</html>
body {
width:100%;
height:100%;
background-color: white;
color: #424242;
font-family:'YanoneKaffeesatzLight',Verdana,Tahoma,Arial;
margin:0;
padding:0;
}
#wrap{
display: block;
position: absolute;
width:766px;
height: 262px;
overflow:hidden;
text-align: center;
margin: auto;
top: 0; left: 0; bottom: 0; right: 0;
}
#left{
display:inline-block;
background-image:url(../images/chromelogo.png);
background-repeat:no-repeat;
width:246px;
height:262px;
float: left;
}
#middle{
display:inline-block;
background-image:url(../images/chromepointer.png);
background-repeat:no-repeat;
width:53px;
height:262px;
float: left;
}
#text{
display:inline-block;
font-size: 20pt;
width: 400px;
vertical-align:middle;
padding-top: 30px;
}
a {
color: #087dba;
text-decoration:none;
}
...@@ -92,11 +92,11 @@ html, body{ ...@@ -92,11 +92,11 @@ html, body{
visibility:hidden; visibility:hidden;
} }
div.localuser { .localuser {
color: #087dba; color: #087dba;
} }
div.remoteuser { .remoteuser {
color: #424242; color: #424242;
} }
...@@ -128,7 +128,7 @@ div.remoteuser { ...@@ -128,7 +128,7 @@ div.remoteuser {
font-size: 14; font-size: 14;
} }
div#spacer { #spacer {
height:5px; height:5px;
} }
...@@ -140,17 +140,15 @@ div#spacer { ...@@ -140,17 +140,15 @@ div#spacer {
display:none; display:none;
} }
div#header{ #header{
display:block; display:block;
position:relative;
width:100%;
height:39px; height:39px;
z-index: 1; z-index: 1;
text-align:center; text-align:center;
background-color:#087dba; background-color:#087dba;
} }
div#left { #left {
display:block; display:block;
position: absolute; position: absolute;
left: 0px; left: 0px;
...@@ -163,7 +161,7 @@ div#left { ...@@ -163,7 +161,7 @@ div#left {
padding: 0; padding: 0;
} }
div#leftlogo { #leftlogo {
position:absolute; position:absolute;
top: 5px; top: 5px;
left: 15px; left: 15px;
...@@ -174,13 +172,14 @@ div#leftlogo { ...@@ -174,13 +172,14 @@ div#leftlogo {
z-index:1; z-index:1;
} }
div#link { #toolbar {
display:block; display:block;
position:relative; position:relative;
height:39px; height:39px;
width:auto; width:auto;
overflow: hidden; overflow: hidden;
z-index:0; z-index:0;
visibility: hidden;
} }
.button { .button {
...@@ -189,10 +188,9 @@ div#link { ...@@ -189,10 +188,9 @@ div#link {
color: #FFFFFF; color: #FFFFFF;
top: 0; top: 0;
padding: 10px 0px; padding: 10px 0px;
height: 19px;
width: 39px; width: 39px;
cursor: pointer; cursor: pointer;
font-size: 19px; font-size: 11pt;
text-align: center; text-align: center;
text-shadow: 0px 1px 0px rgba(255,255,255,.3), 0px -1px 0px rgba(0,0,0,.7); text-shadow: 0px 1px 0px rgba(255,255,255,.3), 0px -1px 0px rgba(0,0,0,.7);
} }
...@@ -227,7 +225,7 @@ a.button:hover { ...@@ -227,7 +225,7 @@ a.button:hover {
background: -webkit-gradient(linear, 0 0, 0 100%, from(#087dba), to(#087dba), color-stop(50%, white)); background: -webkit-gradient(linear, 0 0, 0 100%, from(#087dba), to(#087dba), color-stop(50%, white));
} }
div#right { #right {
display:block; display:block;
position:absolute; position:absolute;
right: 0px; right: 0px;
...@@ -239,7 +237,8 @@ div#right { ...@@ -239,7 +237,8 @@ div#right {
width:100px; width:100px;
height:39px; height:39px;
} }
div#rightlogo {
#rightlogo {
position:absolute; position:absolute;
top: 6px; top: 6px;
right: 15px; right: 15px;
......
.jqistates {
font-size: 14px;
}
.jqistates h2 { .jqistates h2 {
padding-bottom: 10px; padding-bottom: 10px;
border-bottom: 1px solid #eee; border-bottom: 1px solid #eee;
...@@ -5,18 +9,18 @@ ...@@ -5,18 +9,18 @@
line-height: 25px; line-height: 25px;
text-align: center; text-align: center;
color: #424242; color: #424242;
} }
.jqistates input { .jqistates input {
width: 100%; width: 100%;
margin: 20px 0; margin: 20px 0;
} }
.jqibuttons button { .jqibuttons button {
margin-right: 5px; margin-right: 5px;
float:right; float:right;
} }
button.jqidefaultbutton #inviteLinkRef { button.jqidefaultbutton #inviteLinkRef {
color: #2c8ad2; color: #2c8ad2;
} }
\ No newline at end of file \ No newline at end of file
<html> <html>
<head> <head>
<title>WebRTC, meet the Jitsi Videobridge</title> <title>JitMeet</title>
<script src="jquery.min.js"></script> <script src="//ajax.googleapis.com/ajax/libs/jquery/2.0.3/jquery.min.js"></script>
<script src="libs/strophejingle.bundle.js"></script><!-- strophe.jingle bundle --> <script src="libs/strophejingle.bundle.js"></script><!-- strophe.jingle bundle -->
<script src="libs/colibri.js"></script><!-- colibri focus implementation --> <script src="libs/colibri.js"></script><!-- colibri focus implementation -->
<script src="muc.js"></script><!-- simple MUC library --> <script src="muc.js"></script><!-- simple MUC library -->
<script src="app.js"></script><!-- application logic --> <script src="app.js"></script><!-- application logic -->
<link href="font-awesome-4.0.3/css/font-awesome.css" rel="stylesheet"> <link href="//netdna.bootstrapcdn.com/font-awesome/4.0.3/css/font-awesome.css" rel="stylesheet">
<link rel="stylesheet" type="text/css" media="screen" href="css/main.css" /> <link rel="stylesheet" type="text/css" media="screen" href="css/main.css" />
<link rel="stylesheet" href="css/jquery-impromptu.css"> <link rel="stylesheet" href="css/jquery-impromptu.css">
<link rel="stylesheet" href="css/modaldialog.css"> <link rel="stylesheet" href="css/modaldialog.css">
...@@ -18,7 +18,7 @@ ...@@ -18,7 +18,7 @@
<div id="header"> <div id="header">
<a href="http://jitsi.org" target="_blank"><div id="leftlogo"></div></a> <a href="http://jitsi.org" target="_blank"><div id="leftlogo"></div></a>
<a href="http://www.estos.com/" target="_blank"><div id="rightlogo"></div></a> <a href="http://www.estos.com/" target="_blank"><div id="rightlogo"></div></a>
<div id="link"> <div id="toolbar">
<a class="button" onclick='buttonClick("#mute", "fa fa-microphone fa-lg fa fa-microphone-slash fa-lg");toggleAudio();'><i id="mute" title="Mute / unmute" class="fa fa-microphone fa-lg"></i></a> <a class="button" onclick='buttonClick("#mute", "fa fa-microphone fa-lg fa fa-microphone-slash fa-lg");toggleAudio();'><i id="mute" title="Mute / unmute" class="fa fa-microphone fa-lg"></i></a>
<div class="header_button_separator"></div> <div class="header_button_separator"></div>
<a class="button" onclick='buttonClick("#video", "fa fa-video-camera fa-lg fa fa-video-camera no-fa-video-camera fa-lg");toggleVideo();'><i id="video" title="Start / stop camera" class="fa fa-video-camera fa-lg"></i></a> <a class="button" onclick='buttonClick("#video", "fa fa-video-camera fa-lg fa fa-video-camera no-fa-video-camera fa-lg");toggleVideo();'><i id="video" title="Start / stop camera" class="fa fa-video-camera fa-lg"></i></a>
......
package com.rayo.core.verb; package com.rayo.core.verb;
import org.xmpp.packet.*;
import org.dom4j.*;
public class AddSourceEvent extends AbstractVerbEvent { public class AddSourceEvent extends AbstractVerbEvent {
private JID muc;
private String nickname;
private JID participant;
private Element conference;
public AddSourceEvent() {} public AddSourceEvent() {}
public AddSourceEvent(Verb verb) { public AddSourceEvent(Verb verb) {
super(verb); super(verb);
} }
public Element getConference() {
return conference;
}
public void setConference(Element conference) {
this.conference = conference;
}
public JID getParticipant() {
return participant;
}
public void setParticipant(JID participant) {
this.participant = participant;
}
public JID getMuc() {
return muc;
}
public void setMuc(JID muc) {
this.muc = muc;
}
public String getNickname() {
return nickname;
}
public void setNickname(String nickname) {
this.nickname = nickname;
}
} }
package com.rayo.core.verb; package com.rayo.core.verb;
import org.dom4j.Element;
public class ColibriCommand extends AbstractVerbCommand { public class ColibriCommand extends AbstractVerbCommand {
private String videobridge; private String videobridge;
private Element conference;
public void setVideobridge(String videobridge) { public ColibriCommand(String videobridge, Element conference)
{
this.videobridge = videobridge; this.videobridge = videobridge;
this.conference = conference;
} }
public String getVideobridge() { public String getVideobridge()
{
return this.videobridge; return this.videobridge;
} }
public Element getConference()
{
return this.conference;
}
} }
package com.rayo.core.verb;
import org.xmpp.packet.*;
import org.dom4j.*;
public class ColibriOfferEvent extends AbstractVerbEvent {
private JID muc;
private String nickname;
private JID participant;
private Element conference;
public ColibriOfferEvent() {}
public ColibriOfferEvent(Verb verb) {
super(verb);
}
public Element getConference() {
return conference;
}
public void setConference(Element conference) {
this.conference = conference;
}
public JID getParticipant() {
return participant;
}
public void setParticipant(JID participant) {
this.participant = participant;
}
public JID getMuc() {
return muc;
}
public void setMuc(JID muc) {
this.muc = muc;
}
public String getNickname() {
return nickname;
}
public void setNickname(String nickname) {
this.nickname = nickname;
}
}
package com.rayo.core.verb; package com.rayo.core.verb;
import org.xmpp.packet.*;
public class RemoveSourceEvent extends AbstractVerbEvent { public class RemoveSourceEvent extends AbstractVerbEvent {
private JID muc;
private String nickname;
private JID participant;
private boolean active;
public RemoveSourceEvent() {} public RemoveSourceEvent() {}
public RemoveSourceEvent(Verb verb) { public RemoveSourceEvent(Verb verb) {
super(verb); super(verb);
} }
public JID getParticipant() {
return participant;
}
public void setParticipant(JID participant) {
this.participant = participant;
}
public JID getMuc() {
return muc;
}
public void setMuc(JID muc) {
this.muc = muc;
}
public String getNickname() {
return nickname;
}
public void setNickname(String nickname) {
this.nickname = nickname;
}
public void setActive(boolean active) {
this.active = active;
}
public boolean isActive() {
return active;
}
} }
...@@ -46,8 +46,9 @@ public class ColibriProvider extends BaseProvider { ...@@ -46,8 +46,9 @@ public class ColibriProvider extends BaseProvider {
private Object buildColibriCommand(Element element) throws URISyntaxException private Object buildColibriCommand(Element element) throws URISyntaxException
{ {
String videobridge = element.attributeValue("videobridge"); String videobridge = element.attributeValue("videobridge");
ColibriCommand command = new ColibriCommand(); Element conference = element.element("conference").createCopy();
command.setVideobridge(videobridge);
ColibriCommand command = new ColibriCommand(videobridge, conference);
return command; return command;
} }
...@@ -62,6 +63,9 @@ public class ColibriProvider extends BaseProvider { ...@@ -62,6 +63,9 @@ public class ColibriProvider extends BaseProvider {
if (object instanceof ColibriCommand) { if (object instanceof ColibriCommand) {
createColibriCommand((ColibriCommand) object, document); createColibriCommand((ColibriCommand) object, document);
} else if (object instanceof ColibriOfferEvent) {
createColibriOfferEvent((ColibriOfferEvent) object, document);
} else if (object instanceof AddSourceEvent) { } else if (object instanceof AddSourceEvent) {
createAddSourceEvent((AddSourceEvent) object, document); createAddSourceEvent((AddSourceEvent) object, document);
...@@ -82,14 +86,34 @@ public class ColibriProvider extends BaseProvider { ...@@ -82,14 +86,34 @@ public class ColibriProvider extends BaseProvider {
root.addAttribute("videobridge", command.getVideobridge()); root.addAttribute("videobridge", command.getVideobridge());
} }
private void createColibriOfferEvent(ColibriOfferEvent event, Document document)
{
Element root = document.addElement(new QName("offer", NAMESPACE));
root.addAttribute("muc", event.getMuc().toString());
root.addAttribute("videobridge", event.getMuc().getNode());
root.addAttribute("nickname", event.getNickname());
root.addAttribute("participant", event.getParticipant().toString());
root.add(event.getConference().createCopy());
}
private void createAddSourceEvent(AddSourceEvent event, Document document) private void createAddSourceEvent(AddSourceEvent event, Document document)
{ {
document.addElement(new QName("addsource", NAMESPACE)); Element root = document.addElement(new QName("addsource", NAMESPACE));
root.addAttribute("muc", event.getMuc().toString());
root.addAttribute("videobridge", event.getMuc().getNode());
root.addAttribute("nickname", event.getNickname());
root.addAttribute("participant", event.getParticipant().toString());
root.add(event.getConference().createCopy());
} }
private void createRemoveSourceEvent(RemoveSourceEvent event, Document document) private void createRemoveSourceEvent(RemoveSourceEvent event, Document document)
{ {
document.addElement(new QName("removesource", NAMESPACE)); Element root = document.addElement(new QName("removesource", NAMESPACE));
root.addAttribute("muc", event.getMuc().toString());
root.addAttribute("videobridge", event.getMuc().getNode());
root.addAttribute("nickname", event.getNickname());
root.addAttribute("participant", event.getParticipant().toString());
root.addAttribute("active", event.isActive() ? "true" : "false");
} }
private void createMutedEvent(MutedEvent muted, Document document) private void createMutedEvent(MutedEvent muted, Document document)
......
...@@ -7,6 +7,7 @@ Strophe.addConnectionPlugin('emuc', { ...@@ -7,6 +7,7 @@ Strophe.addConnectionPlugin('emuc', {
roomjid: null, roomjid: null,
myroomjid: null, myroomjid: null,
members: {}, members: {},
joined: false,
isOwner: false, isOwner: false,
init: function (conn) { init: function (conn) {
this.connection = conn; this.connection = conn;
...@@ -23,7 +24,7 @@ Strophe.addConnectionPlugin('emuc', { ...@@ -23,7 +24,7 @@ Strophe.addConnectionPlugin('emuc', {
} }
var join = $pres({to: this.myroomjid }).c('x', {xmlns: 'http://jabber.org/protocol/muc'}); var join = $pres({to: this.myroomjid }).c('x', {xmlns: 'http://jabber.org/protocol/muc'});
if (password !== null) { if (password !== undefined) {
join.c('password').t(password); join.c('password').t(password);
} }
this.connection.send(join); this.connection.send(join);
...@@ -47,10 +48,14 @@ Strophe.addConnectionPlugin('emuc', { ...@@ -47,10 +48,14 @@ Strophe.addConnectionPlugin('emuc', {
member.show = $(pres).find('>show').text(); member.show = $(pres).find('>show').text();
member.status = $(pres).find('>status').text(); member.status = $(pres).find('>status').text();
var tmp = $(pres).find('>x[xmlns="http://jabber.org/protocol/muc#user"]>item'); var tmp = $(pres).find('>x[xmlns="http://jabber.org/protocol/muc#user"]>item');
member.affilication = tmp.attr('affiliation'); member.affiliation = tmp.attr('affiliation');
member.role = tmp.attr('role'); member.role = tmp.attr('role');
if (from == this.myroomjid) { if (from == this.myroomjid) {
$(document).trigger('joined.muc', [from, member]); if (member.affiliation == 'owner') this.isOwner = true;
if (!this.joined) {
this.joined = true;
$(document).trigger('joined.muc', [from, member]);
}
} else if (this.members[from] === undefined) { } else if (this.members[from] === undefined) {
// new participant // new participant
this.members[from] = member; this.members[from] = member;
......
Sorry, webrtc is required for this and your browser does not seem to support it. <html>
<head>
<title></title>
<link rel="stylesheet" type="text/css" media="screen" href="css/chromeonly.css" />
</head>
<body>
<!-- wrap starts here -->
<div id="wrap">
<a href="http://google.com/chrome"><div id="left"></div></a>
<div id="middle"></div>
<div id="text">
<p>This service only works with Chrome.</p>
<p><a href="http://google.com/chrome">Download Chrome</a></p>
</div>
<!-- wrap ends here -->
</div>
</body>
</html>
\ No newline at end of file
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment