App-Alice
view release on metacpan or search on metacpan
share/static/alice.js view on Meta::CPAN
observeButtonClick: observeButtonClick,
buttonStateHandler: buttonStateHandler,
observeStateChanges: observeStateChanges,
updateButtonState: updateButtonState
};
})());
WysiHat.Toolbar.ButtonSets = {};
WysiHat.Toolbar.ButtonSets.Basic = $A([
{ label: "Bold" },
{ label: "Underline" },
{ label: "Italic" }
]);
var Alice = { };
Object.extend(Alice, {
uncacheGravatar: function(content) {
if (!this.timestamp) {
var date = new Date();
this.timestamp = date.getTime();
}
return content.replace(
/(src=".*?gravatar.com\/avatar\/[^?]*\?)/gi,
"$1time=" + this.timestamp + "&"
);
},
epochToLocal: function(epoch, format) {
var date = new Date(parseInt(epoch) * 1000);
if (!date) return epoch;
var hours = date.getHours();
if (format == "12") {
var ap;
if (hours > 12) {
hours -= 12;
ap = "p";
} else {
ap = "a"
}
return sprintf("%d:%02d%s", hours, date.getMinutes(), ap);
}
return sprintf("%02d:%02d", hours, date.getMinutes());
},
stripNick: function(html) {
return html.replace(/<div class="left">.*<\/div>/, '');
},
growlNotify: function(message) {
if (window.fluid) {
window.fluid.showGrowlNotification({
title: message.window.title + ": " + message.nick,
description: message.body.unescapeHTML(),
priority: 1,
sticky: false,
identifier: message.msgid
});
}
else if (window.webkitNotifications) {
if (window.webkitNotifications.checkPermission() == 0) {
var popup = window.webkitNotifications.createNotification(
"http://static.usealice.org/image/alice.png",
message.window.title + ": " + message.nick,
message.body.unescapeHTML()
);
popup.ondisplay = function() {
setTimeout(function () {popup.cancel();}, 3000);
};
popup.show();
}
}
},
isSpecialKey: function(keyCode) {
var special_keys = [
16,27,9,32,13,8,145,20,144,19,45,36,46,35,33,34,37,38,39,
40,17,18,91,112,113,114,115,116,117,118,119,120,121,122,123
];
return special_keys.indexOf(keyCode) > -1;
},
loadInlineImage: function(image) {
var maxWidth = arguments.callee.maxWidth || 300;
var maxHeight = arguments.callee.maxHeight || 300;
image.style.visibility = 'hidden';
if (image.height > image.width && image.height > maxHeight) {
image.style.width = 'auto';
image.style.height = maxHeight + 'px';
}
else if (image.width > maxWidth) {
image.style.height = 'auto';
image.style.width = maxWidth + 'px';
}
else {
image.style.height = 'auto';
}
image.style.display = 'block';
image.style.visibility = 'visible';
setTimeout(function () {
var messagelist = image.up(".message_wrap");
messagelist.scrollTop = messagelist.scrollHeight;
}, 50);
},
playAudio: function(image, audio) {
image.src = '/static/image/pause.png';
if (! audio) {
var url = image.nextSibling.href;
audio = new Audio(url);
audio.addEventListener('ended', function () {
image.src = '/static/image/play.png';
image.onclick = function () { Alice.playAudio(image, audio) };
});
}
share/static/alice.js view on Meta::CPAN
var win = this.getWindow(message['window'].id);
if (win) {
win.addMessage(message);
} else {
this.connection.requestWindow(
message['window'].title, message['window'].id, message
);
}
},
focusHash: function(hash) {
if (!hash) hash = window.location.hash;
if (hash) {
hash = decodeURIComponent(hash);
hash = hash.replace(/^#/, "");
var windows = this.windows();
for (var i = 0; i < windows.length; i++) {
var win = windows[i];
if (win.hashtag == hash) {
if (win && !win.active) win.focus();
return;
}
}
}
},
makeSortable: function() {
Sortable.create('tabs', {
overlap: 'horizontal',
constraint: 'horizontal',
format: /(.+)/,
onUpdate: function (res) {
var tabs = res.childElements();
var order = tabs.collect(function(t){
var m = t.id.match(/([^_]+)_tab/);
if (m) return m[1]
});
if (order.length) this.connection.sendTabOrder(order);
}.bind(this)
});
},
addMissed: function() {
if (!window.fluid) return;
window.fluid.dockBadge ? window.fluid.dockBadge++ :
window.fluid.dockBadge = 1;
},
clearMissed: function() {
if (!window.fluid) return;
window.fluid.dockBadge = "";
}
});
Alice.Connection = Class.create({
initialize: function(application) {
this.application = application;
this.len = 0;
this.aborting = false;
this.request = null;
this.seperator = "--xalicex\n";
this.msgid = 0;
this.reconnect_count = 0;
this.reconnecting = false;
},
closeConnection: function() {
this.aborting = true;
if (this.request && this.request.transport)
this.request.transport.abort();
this.aborting = false;
},
connect: function() {
if (this.reconnect_count > 3) {
this.aborting = true;
this.application.activeWindow().showAlert("Alice server is not responding (<a href='javascript:alice.connection.reconnect()'>reconnect</a>)");
return;
}
this.closeConnection();
this.len = 0;
this.reconnect_count++;
var now = new Date();
console.log("opening new connection starting at message " + this.msgid);
this.request = new Ajax.Request('/stream', {
method: 'get',
parameters: {msgid: this.msgid, t: now.getTime() / 1000},
onException: this.handleException.bind(this),
onInteractive: this.handleUpdate.bind(this),
onComplete: this.handleComplete.bind(this)
});
},
reconnect: function () {
this.reconnecting = true;
this.reconnect_count = 0;
this.connect();
},
handleException: function(request, exception) {
console.log("encountered an error with stream.");
if (!this.aborting)
setTimeout(this.connect.bind(this), 2000);
},
handleComplete: function(transport) {
console.log("connection was closed cleanly.");
if (!this.aborting)
setTimeout(this.connect.bind(this), 2000);
},
handleUpdate: function(transport) {
if (this.reconnecting) {
this.application.activeWindow().showHappyAlert("Reconnected to the Alice server");
this.reconnecting = false;
}
this.reconnect_count = 0;
var time = new Date();
var data = transport.responseText.slice(this.len);
var start, end;
start = data.indexOf(this.seperator);
if (start > -1) {
start += this.seperator.length;
end = data.indexOf(this.seperator, start);
if (end == -1) return;
}
else return;
this.len += (end + this.seperator.length) - start;
data = data.slice(start, end);
try {
data = data.evalJSON();
var queue = data.queue;
var length = queue.length;
for (var i=0; i<length; i++) {
if (queue[i].type == "action")
this.application.handleAction(queue[i]);
else if (queue[i].type == "message") {
if (queue[i].msgid) this.msgid = queue[i].msgid;
if (queue[i].timestamp)
queue[i].timestamp = Alice.epochToLocal(queue[i].timestamp);
this.application.displayMessage(queue[i]);
}
}
}
catch (e) {
console.log(e.toString());
}
var lag = time / 1000 - data.time;
if (lag > 5) {
console.log("lag is " + Math.round(lag) + "s, reconnecting.");
this.connect();
}
},
requestWindow: function(title, windowId, message) {
new Ajax.Request('/say', {
method: 'post',
parameters: {source: windowId, msg: "/create " + title},
onSuccess: function (transport) {
this.handleUpdate(transport);
if (message) {
setTimeout(function() {
this.application.displayMessage(message)
}.bind(this), 1000);
}
}.bind(this)
});
},
closeWindow: function(win) {
new Ajax.Request('/say', {
method: 'post',
parameters: {source: win.id, msg: "/close"}
});
},
getConfig: function(callback) {
new Ajax.Request('/config', {
method: 'get',
onSuccess: callback
});
},
getPrefs: function(callback) {
new Ajax.Request('/prefs', {
method: 'get',
onSuccess: callback
});
},
getLog: function(callback) {
new Ajax.Request('/logs', {
method: 'get',
onSuccess: callback
});
},
( run in 0.674 second using v1.01-cache-2.11-cpan-5735350b133 )