Adds support for etherpad in meet.jit.si. Issue #36.
This commit is contained in:
parent
4ef199304d
commit
4ff1f4a30e
32
app.js
32
app.js
|
@ -86,6 +86,7 @@ function doJoin() {
|
||||||
window.history.pushState('VideoChat', 'Room: ' + roomnode, window.location.pathname + roomnode);
|
window.history.pushState('VideoChat', 'Room: ' + roomnode, window.location.pathname + roomnode);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
roomjid = roomnode + '@' + config.hosts.muc;
|
roomjid = roomnode + '@' + config.hosts.muc;
|
||||||
|
|
||||||
if (config.useNicks) {
|
if (config.useNicks) {
|
||||||
|
@ -111,7 +112,9 @@ $(document).bind('mediaready.jingle', function (event, stream) {
|
||||||
updateLargeVideo(localVideoSrc, true, 0);
|
updateLargeVideo(localVideoSrc, true, 0);
|
||||||
|
|
||||||
$('#localVideo').click(function () {
|
$('#localVideo').click(function () {
|
||||||
|
$(document).trigger("video.selected", [false]);
|
||||||
updateLargeVideo($(this).attr('src'), true, 0);
|
updateLargeVideo($(this).attr('src'), true, 0);
|
||||||
|
|
||||||
$('video').each(function (idx, el) {
|
$('video').each(function (idx, el) {
|
||||||
if (el.id.indexOf('mixedmslabel') != -1) {
|
if (el.id.indexOf('mixedmslabel') != -1) {
|
||||||
el.volume = 0;
|
el.volume = 0;
|
||||||
|
@ -217,6 +220,7 @@ $(document).bind('remotestreamadded.jingle', function (event, data, sid) {
|
||||||
};
|
};
|
||||||
sel.click(
|
sel.click(
|
||||||
function () {
|
function () {
|
||||||
|
$(document).trigger("video.selected", [false]);
|
||||||
updateLargeVideo($(this).attr('src'), false, 1);
|
updateLargeVideo($(this).attr('src'), false, 1);
|
||||||
}
|
}
|
||||||
);
|
);
|
||||||
|
@ -282,6 +286,10 @@ $(document).bind('joined.muc', function (event, jid, info) {
|
||||||
focus = new ColibriFocus(connection, config.hosts.bridge);
|
focus = new ColibriFocus(connection, config.hosts.bridge);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (focus && config.etherpad_base) {
|
||||||
|
Etherpad.init();
|
||||||
|
}
|
||||||
|
|
||||||
showFocusIndicator();
|
showFocusIndicator();
|
||||||
|
|
||||||
// Once we've joined the muc show the toolbar
|
// Once we've joined the muc show the toolbar
|
||||||
|
@ -338,13 +346,13 @@ $(document).bind('left.muc', function (event, jid) {
|
||||||
$(container).hide();
|
$(container).hide();
|
||||||
resizeThumbnails();
|
resizeThumbnails();
|
||||||
}
|
}
|
||||||
|
|
||||||
if (focus === null && connection.emuc.myroomjid == connection.emuc.list_members[0]) {
|
if (focus === null && connection.emuc.myroomjid == connection.emuc.list_members[0]) {
|
||||||
console.log('welcome to our new focus... myself');
|
console.log('welcome to our new focus... myself');
|
||||||
focus = new ColibriFocus(connection, config.hosts.bridge);
|
focus = new ColibriFocus(connection, config.hosts.bridge);
|
||||||
if (Object.keys(connection.emuc.members).length > 0) {
|
if (Object.keys(connection.emuc.members).length > 0) {
|
||||||
focus.makeConference(Object.keys(connection.emuc.members));
|
focus.makeConference(Object.keys(connection.emuc.members));
|
||||||
}
|
}
|
||||||
|
$(document).trigger('focusechanged.muc', [focus]);
|
||||||
}
|
}
|
||||||
else if (focus && Object.keys(connection.emuc.members).length === 0) {
|
else if (focus && Object.keys(connection.emuc.members).length === 0) {
|
||||||
console.log('everyone left');
|
console.log('everyone left');
|
||||||
|
@ -437,11 +445,11 @@ $(document).bind('presentationadded.muc', function (event, jid, presUrl, current
|
||||||
setPresentationVisible(true);
|
setPresentationVisible(true);
|
||||||
$('#largeVideoContainer').hover(
|
$('#largeVideoContainer').hover(
|
||||||
function (event) {
|
function (event) {
|
||||||
if ($('#largeVideo').css('visibility') == 'hidden')
|
if (isPresentationVisible())
|
||||||
$('#reloadPresentation').css({display:'inline-block'});
|
$('#reloadPresentation').css({display:'inline-block'});
|
||||||
},
|
},
|
||||||
function (event) {
|
function (event) {
|
||||||
if ($('#largeVideo').css('visibility') == 'visible')
|
if (!isPresentationVisible())
|
||||||
$('#reloadPresentation').css({display:'none'});
|
$('#reloadPresentation').css({display:'none'});
|
||||||
else {
|
else {
|
||||||
var e = event.toElement || event.relatedTarget;
|
var e = event.toElement || event.relatedTarget;
|
||||||
|
@ -519,6 +527,9 @@ function reloadPresentation() {
|
||||||
*/
|
*/
|
||||||
function setPresentationVisible(visible) {
|
function setPresentationVisible(visible) {
|
||||||
if (visible) {
|
if (visible) {
|
||||||
|
// Trigger the video.selected event to indicate a change in the large video.
|
||||||
|
$(document).trigger("video.selected", [true]);
|
||||||
|
|
||||||
$('#largeVideo').fadeOut(300, function () {
|
$('#largeVideo').fadeOut(300, function () {
|
||||||
$('#largeVideo').css({visibility:'hidden'});
|
$('#largeVideo').css({visibility:'hidden'});
|
||||||
$('#presentation>iframe').fadeIn(300, function() {
|
$('#presentation>iframe').fadeIn(300, function() {
|
||||||
|
@ -538,6 +549,10 @@ function setPresentationVisible(visible) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
var isPresentationVisible = function () {
|
||||||
|
return ($('#presentation>iframe') != null && $('#presentation>iframe').css('opacity') == 1);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Updates the large video with the given new video source.
|
* Updates the large video with the given new video source.
|
||||||
*/
|
*/
|
||||||
|
@ -608,14 +623,19 @@ function resizeLarge() {
|
||||||
$('#presentation>iframe').height(availableWidth / aspectRatio);
|
$('#presentation>iframe').height(availableWidth / aspectRatio);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if ($('#etherpad>iframe')) {
|
||||||
|
$('#etherpad>iframe').width(availableWidth);
|
||||||
|
$('#etherpad>iframe').height(availableWidth / aspectRatio);
|
||||||
|
}
|
||||||
|
|
||||||
resizeThumbnails();
|
resizeThumbnails();
|
||||||
}
|
}
|
||||||
|
|
||||||
function resizeThumbnails() {
|
function resizeThumbnails() {
|
||||||
// Calculate the available height, which is the inner window height minus 39px for the header
|
// Calculate the available height, which is the inner window height minus 39px for the header
|
||||||
// minus 4px for the delimiter lines on the top and bottom of the large video,
|
// minus 2px for the delimiter lines on the top and bottom of the large video,
|
||||||
// minus the 36px space inside the remoteVideos container used for highlighting shadow.
|
// minus the 36px space inside the remoteVideos container used for highlighting shadow.
|
||||||
var availableHeight = window.innerHeight - $('#largeVideo').height() - 79;
|
var availableHeight = window.innerHeight - $('#largeVideo').height() - 59;
|
||||||
var numvids = $('#remoteVideos>span:visible').length;
|
var numvids = $('#remoteVideos>span:visible').length;
|
||||||
|
|
||||||
// Remove the 1px borders arround videos and the chat width.
|
// Remove the 1px borders arround videos and the chat width.
|
||||||
|
@ -629,7 +649,7 @@ function resizeThumbnails() {
|
||||||
}
|
}
|
||||||
|
|
||||||
// size videos so that while keeping AR and max height, we have a nice fit
|
// size videos so that while keeping AR and max height, we have a nice fit
|
||||||
$('#remoteVideos').height(availableHeight+26); // add the 2*18px-padding-top border used for highlighting shadow.
|
$('#remoteVideos').height(availableHeight);
|
||||||
$('#remoteVideos>span').width(availableWidth);
|
$('#remoteVideos>span').width(availableWidth);
|
||||||
$('#remoteVideos>span').height(availableHeight);
|
$('#remoteVideos>span').height(availableHeight);
|
||||||
}
|
}
|
||||||
|
|
|
@ -22,7 +22,7 @@ html, body{
|
||||||
margin-left: auto;
|
margin-left: auto;
|
||||||
margin-right: auto;
|
margin-right: auto;
|
||||||
}
|
}
|
||||||
#presentation, .videocontainer>video {
|
#presentation, #etherpad, .videocontainer>video {
|
||||||
position: absolute;
|
position: absolute;
|
||||||
left: 0px;
|
left: 0px;
|
||||||
top: 0px;
|
top: 0px;
|
||||||
|
@ -53,7 +53,7 @@ html, body{
|
||||||
position:relative;
|
position:relative;
|
||||||
text-align:center;
|
text-align:center;
|
||||||
height:196px;
|
height:196px;
|
||||||
padding-top:10px;
|
padding: 5px 0px;
|
||||||
width:auto;
|
width:auto;
|
||||||
overflow: hidden;
|
overflow: hidden;
|
||||||
border:1px solid transparent;
|
border:1px solid transparent;
|
||||||
|
@ -415,5 +415,5 @@ form {
|
||||||
background-clip: padding-box;
|
background-clip: padding-box;
|
||||||
-webkit-border-radius: 5px;
|
-webkit-border-radius: 5px;
|
||||||
-webkit-background-clip: padding-box;
|
-webkit-background-clip: padding-box;
|
||||||
z-index: 2;
|
z-index: 3;
|
||||||
}
|
}
|
||||||
|
|
|
@ -0,0 +1,136 @@
|
||||||
|
var Etherpad = (function (my) {
|
||||||
|
var etherpadName = null;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Initializes the etherpad.
|
||||||
|
*/
|
||||||
|
my.init = function (name) {
|
||||||
|
|
||||||
|
if (config.etherpad_base && !etherpadName) {
|
||||||
|
|
||||||
|
if (!name) {
|
||||||
|
// In case we're the focus we generate the name.
|
||||||
|
etherpadName = Math.random().toString(36).substring(7) + '_' + (new Date().getTime()).toString();
|
||||||
|
shareEtherpad();
|
||||||
|
}
|
||||||
|
else
|
||||||
|
etherpadName = name;
|
||||||
|
|
||||||
|
this.domain = config.etherpad_base;
|
||||||
|
this.options = "?showControls=true&showChat=false&showLineNumbers=true&useMonospaceFont=false";
|
||||||
|
|
||||||
|
createEtherpadButton();
|
||||||
|
|
||||||
|
this.iframe = document.createElement('iframe');
|
||||||
|
this.iframe.src = this.domain + etherpadName + this.options;
|
||||||
|
this.iframe.frameBorder = 0;
|
||||||
|
this.iframe.scrolling = "no";
|
||||||
|
this.iframe.width = $('#largeVideoContainer').width() || 640;
|
||||||
|
this.iframe.height = $('#largeVideoContainer').height() || 480;
|
||||||
|
this.iframe.setAttribute('style', 'visibility: hidden;');
|
||||||
|
|
||||||
|
document.getElementById('etherpad').appendChild(this.iframe);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Opens/hides the Etherpad.
|
||||||
|
*/
|
||||||
|
my.toggleEtherpad = function (isPresentation) {
|
||||||
|
var largeVideo = null;
|
||||||
|
if (isPresentationVisible())
|
||||||
|
largeVideo = $('#presentation>iframe');
|
||||||
|
else
|
||||||
|
largeVideo = $('#largeVideo');
|
||||||
|
|
||||||
|
if ($('#etherpad>iframe').css('visibility') == 'hidden') {
|
||||||
|
largeVideo.fadeOut(300, function () {
|
||||||
|
if (isPresentationVisible())
|
||||||
|
largeVideo.css({opacity:'0'});
|
||||||
|
else
|
||||||
|
largeVideo.css({visibility:'hidden'});
|
||||||
|
|
||||||
|
$('#etherpad>iframe').fadeIn(300, function() {
|
||||||
|
$('#etherpad>iframe').css({visibility:'visible'});
|
||||||
|
$('#etherpad').css({zIndex:2});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
}
|
||||||
|
else if ($('#etherpad>iframe')) {
|
||||||
|
$('#etherpad>iframe').fadeOut(300, function () {
|
||||||
|
$('#etherpad>iframe').css({visibility:'hidden'});
|
||||||
|
$('#etherpad').css({zIndex:0});
|
||||||
|
if (!isPresentation) {
|
||||||
|
$('#largeVideo').fadeIn(300, function() {
|
||||||
|
$('#largeVideo').css({visibility:'visible'});
|
||||||
|
});
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Shares the Etherpad name with other participants.
|
||||||
|
*/
|
||||||
|
function shareEtherpad() {
|
||||||
|
connection.emuc.addEtherpadToPresence(etherpadName);
|
||||||
|
connection.emuc.sendPresence();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Creates the Etherpad button and adds it to the toolbar.
|
||||||
|
*/
|
||||||
|
function createEtherpadButton() {
|
||||||
|
//<div class="header_button_separator"></div>
|
||||||
|
//<a class="button" onclick='Etherpad.openEtherpad("teeest");'>
|
||||||
|
//<i title="Open shared document" class="fa fa-file-text fa-lg"></i></a>
|
||||||
|
var separator = document.createElement('div');
|
||||||
|
separator.className = 'header_button_separator';
|
||||||
|
|
||||||
|
var button = document.createElement('a');
|
||||||
|
button.className = 'button';
|
||||||
|
button.setAttribute('onclick', 'Etherpad.toggleEtherpad(0);');
|
||||||
|
|
||||||
|
var buttonImage = document.createElement('i');
|
||||||
|
buttonImage.setAttribute('title', 'Open shared document');
|
||||||
|
buttonImage.className = 'fa fa-file-text fa-lg';
|
||||||
|
|
||||||
|
button.appendChild(buttonImage);
|
||||||
|
|
||||||
|
var toolbar = document.getElementById('toolbar');
|
||||||
|
toolbar.insertBefore(button, toolbar.childNodes[toolbar.childNodes.length - 4]);
|
||||||
|
toolbar.insertBefore(separator, button);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* On Etherpad added to muc.
|
||||||
|
*/
|
||||||
|
$(document).bind('etherpadadded.muc', function (event, jid, etherpadName) {
|
||||||
|
console.log("Etherpad added", etherpadName);
|
||||||
|
if (config.etherpad_base && !focus) {
|
||||||
|
Etherpad.init(etherpadName);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
/**
|
||||||
|
* On focus changed event.
|
||||||
|
*/
|
||||||
|
$(document).bind('focusechanged.muc', function (event, focus) {
|
||||||
|
console.log("Focus changed");
|
||||||
|
if (config.etherpad_base)
|
||||||
|
shareEtherpad();
|
||||||
|
});
|
||||||
|
|
||||||
|
/**
|
||||||
|
* On video selected event.
|
||||||
|
*/
|
||||||
|
$(document).bind('video.selected', function (event, isPresentation) {
|
||||||
|
if (!config.etherpad_base)
|
||||||
|
return;
|
||||||
|
|
||||||
|
if ($('#etherpad>iframe').css('visibility') != 'hidden')
|
||||||
|
Etherpad.toggleEtherpad(isPresentation);
|
||||||
|
});
|
||||||
|
|
||||||
|
return my;
|
||||||
|
}(Etherpad || {}));
|
14
index.html
14
index.html
|
@ -5,13 +5,14 @@
|
||||||
<script src="libs/strophejingle.bundle.js?v=7"></script><!-- strophe.jingle bundle -->
|
<script src="libs/strophejingle.bundle.js?v=7"></script><!-- strophe.jingle bundle -->
|
||||||
<script src="libs/colibri.js?v=7"></script><!-- colibri focus implementation -->
|
<script src="libs/colibri.js?v=7"></script><!-- colibri focus implementation -->
|
||||||
<script src="//code.jquery.com/ui/1.10.4/jquery-ui.js"></script>
|
<script src="//code.jquery.com/ui/1.10.4/jquery-ui.js"></script>
|
||||||
<script src="muc.js?v=5"></script><!-- simple MUC library -->
|
<script src="muc.js?v=6"></script><!-- simple MUC library -->
|
||||||
<script src="estos_log.js?v=2"></script><!-- simple stanza logger -->
|
<script src="estos_log.js?v=2"></script><!-- simple stanza logger -->
|
||||||
<script src="app.js?v=19"></script><!-- application logic -->
|
<script src="app.js?v=20"></script><!-- application logic -->
|
||||||
|
<script src="etherpad.js?v=1"></script><!-- etherpad plugin -->
|
||||||
<script src="smileys.js?v=1"></script><!-- smiley images -->
|
<script src="smileys.js?v=1"></script><!-- smiley images -->
|
||||||
<script src="replacement.js?v=5"></script><!-- link and smiley replacement -->
|
<script src="replacement.js?v=5"></script><!-- link and smiley replacement -->
|
||||||
<link href="//netdna.bootstrapcdn.com/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?v=15"/>
|
<link rel="stylesheet" type="text/css" media="screen" href="css/main.css?v=16"/>
|
||||||
<link rel="stylesheet" href="css/jquery-impromptu.css?v=4">
|
<link rel="stylesheet" href="css/jquery-impromptu.css?v=4">
|
||||||
<link rel="stylesheet" href="css/modaldialog.css?v=3">
|
<link rel="stylesheet" href="css/modaldialog.css?v=3">
|
||||||
<script src="libs/jquery-impromptu.js"></script>
|
<script src="libs/jquery-impromptu.js"></script>
|
||||||
|
@ -36,11 +37,7 @@
|
||||||
<div class="header_button_separator"></div>
|
<div class="header_button_separator"></div>
|
||||||
<a class="button" onclick='openPreziDialog();'><i title="Share prezi" class="fa fa-desktop fa-lg"></i></a>
|
<a class="button" onclick='openPreziDialog();'><i title="Share prezi" class="fa fa-desktop fa-lg"></i></a>
|
||||||
<div class="header_button_separator"></div>
|
<div class="header_button_separator"></div>
|
||||||
<a class="button" onclick='toggleFullScreen();'><i title="Enter / Exit Full Screen" class="fa fa-arrows-alt"></i></a>
|
<a class="button" onclick='toggleFullScreen();'><i title="Enter / Exit Full Screen" class="fa fa-arrows-alt fa-lg"></i></a>
|
||||||
<!--span id="settingsButton">
|
|
||||||
<div class="header_button_separator"></div>
|
|
||||||
<a class="button" onclick='openSettingsDialog();'><i title="Settings" class="fa fa-cog fa-lg"></i></a>
|
|
||||||
</span-->
|
|
||||||
</span>
|
</span>
|
||||||
</div>
|
</div>
|
||||||
<div id="settings">
|
<div id="settings">
|
||||||
|
@ -58,6 +55,7 @@
|
||||||
<div id="largeVideoContainer" class="videocontainer">
|
<div id="largeVideoContainer" class="videocontainer">
|
||||||
<div id="reloadPresentation"><a onclick='reloadPresentation();'><i title="Reload Prezi" class="fa fa-repeat fa-lg"></i></a></div>
|
<div id="reloadPresentation"><a onclick='reloadPresentation();'><i title="Reload Prezi" class="fa fa-repeat fa-lg"></i></a></div>
|
||||||
<div id="presentation"></div>
|
<div id="presentation"></div>
|
||||||
|
<div id="etherpad"></div>
|
||||||
<video id="largeVideo" autoplay oncontextmenu="return false;"></video>
|
<video id="largeVideo" autoplay oncontextmenu="return false;"></video>
|
||||||
</div>
|
</div>
|
||||||
<div class="fade_line"></div>
|
<div class="fade_line"></div>
|
||||||
|
|
15
muc.js
15
muc.js
|
@ -43,6 +43,13 @@ Strophe.addConnectionPlugin('emuc', {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Parse etherpad tag.
|
||||||
|
var etherpad = $(pres).find('>etherpad');
|
||||||
|
if (etherpad.length) {
|
||||||
|
$(document).trigger('etherpadadded.muc', [from, etherpad.text()]);
|
||||||
|
}
|
||||||
|
|
||||||
|
// Parse prezi tag.
|
||||||
var presentation = $(pres).find('>prezi');
|
var presentation = $(pres).find('>prezi');
|
||||||
if (presentation.length)
|
if (presentation.length)
|
||||||
{
|
{
|
||||||
|
@ -188,6 +195,10 @@ Strophe.addConnectionPlugin('emuc', {
|
||||||
c('current').t(this.presMap['prezicurrent']).up().up();
|
c('current').t(this.presMap['prezicurrent']).up().up();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (this.presMap['etherpadns']) {
|
||||||
|
pres.c('etherpad', {xmlns: this.presMap['etherpadns']}).t(this.presMap['etherpadname']).up();
|
||||||
|
}
|
||||||
|
|
||||||
if (this.presMap['medians'])
|
if (this.presMap['medians'])
|
||||||
{
|
{
|
||||||
pres.c('media', {xmlns: this.presMap['medians']});
|
pres.c('media', {xmlns: this.presMap['medians']});
|
||||||
|
@ -232,5 +243,9 @@ Strophe.addConnectionPlugin('emuc', {
|
||||||
},
|
},
|
||||||
getPrezi: function (roomjid) {
|
getPrezi: function (roomjid) {
|
||||||
return this.preziMap[roomjid];
|
return this.preziMap[roomjid];
|
||||||
|
},
|
||||||
|
addEtherpadToPresence: function(etherpadName) {
|
||||||
|
this.presMap['etherpadns'] = 'http://jitsi.org/jitmeet/etherpad';
|
||||||
|
this.presMap['etherpadname'] = etherpadName;
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
Loading…
Reference in New Issue