Mercurial > cosocket
view media/js/openwebchat.js @ 82:4b3c051d60c3
Added a mouseover overlay that shows metadata about the selected message.
author | Atul Varma <varmaa@toolness.com> |
---|---|
date | Thu, 30 Apr 2009 20:05:31 -0700 |
parents | 2fc520114ed4 |
children | a095f39117d9 |
line wrap: on
line source
var OpenWebStorage = { UnsupportedError: function UnsupportedError() {}, FakeStorage: function FakeStorage() { var contents = {}; function deepCopy(obj) { return JSON.parse(JSON.stringify(obj)); } this.set = function set(key, value) { contents[key] = deepCopy(value); }; this.get = function get(key, defaultValue) { if (key in contents) return deepCopy(contents[key]); return defaultValue; }; }, DOMLocalStorage: function DOMLocalStorage() { var self = this; var localStorage = window.localStorage; if (window.globalStorage) localStorage = window.globalStorage[document.location.hostname]; if (!localStorage) throw new OpenWebStorage.UnsupportedError('No local DOM storage'); self.set = function set(key, value) { localStorage[key] = JSON.stringify(value); }; self.get = function get(key, defaultValue) { var value = defaultValue; if (localStorage[key]) try { value = JSON.parse(localStorage[key].value); } catch (e) {} return value; }; } }; var OpenWebChat = { ClientStorage: function ClientStorage(owStorage, prefix) { var self = this; self.length = owStorage.get(prefix + 'length', 0); self.get = function get(id) { return owStorage.get(prefix + id); }; self.append = function append(msg) { owStorage.set(prefix + self.length, msg); self.length += 1; owStorage.set(prefix + 'length', self.length); }; }, SEND_TIMEOUT: 10000, LISTEN_TIMEOUT: 60000, listenForMessages: function listenForMessages(options) { var self = this; jQuery.ajax( {type: 'GET', url: 'listen', data: {start: options.storage.length}, dataType: 'json', timeout: self.LISTEN_TIMEOUT, error: function(xhr, textStatus, errorThrown) { if (textStatus == "timeout") // Start another long poll. self.listenForMessages(options); else options.onError([textStatus, errorThrown]); }, success: function(data, textStatus) { // TODO: Make sure data.messages is an array. for (var i = 0; i < data.messages.length; i++) options.storage.append(data.messages[i]); options.onMessages(data.messages); // Start another long poll. self.listenForMessages(options); } }); }, sendMessage: function sendMessage(options) { jQuery.ajax( {type: 'POST', url: 'send', contentType: 'application/json', data: JSON.stringify(options.message), processData: false, timeout: this.LISTEN_TIMEOUT, error: function(xhr, textStatus, errorThrown) { options.onError([textStatus, errorThrown]); } }); } }; $(window).ready( function() { var ENTER_KEYCODE = 13; var RETURN_KEYCODE = 10; var owStorage; try { owStorage = new OpenWebStorage.DOMLocalStorage(); } catch (e) { if (e instanceof OpenWebStorage.UnsupportedError) owStorage = new OpenWebStorage.FakeStorage(); else throw e; } var convStorage = new OpenWebChat.ClientStorage( owStorage, '/conv' + document.location.pathname ); $('#name').val(owStorage.get('name', $('#data .default-name').text())); $('#name').blur( function() { owStorage.set('name', $(this).val()); }); $('#outgoing-message').val(owStorage.get('lastMessage', '')); $('#outgoing-message').blur( function() { if ($(this).val()) owStorage.set('lastMessage', $(this).val()); }); $('#outgoing-message').focus(); function onKey(evt) { var self = this; var content = $(this).val(); var author = $('#name').val(); if (evt.keyCode == ENTER_KEYCODE || evt.keyCode == RETURN_KEYCODE) { if (content) { owStorage.set('lastMessage', content); $(this).val(''); var msg = {content: content, time: new Date()}; if (author) msg.author = author; OpenWebChat.sendMessage( {message: msg, onError: function(exception) { $(self).val(content); } }); } evt.preventDefault(); } } $('#outgoing-message').keydown(onKey); $('#outgoing-message').keyup(onKey); function scrollToBottom() { window.scrollTo(0, $('#bottom').position().top); } function msg2dom(msg) { var message = $('<div class="message"></div>'); message.append('<div class="author"></div>'); message.append('<div class="timestamp"></div>'); message.append('<div class="content"></div>'); message.append('<div class="raw-content"></div>'); $('.content', message).html(msg.content); $('.raw-content', message).text(msg.content); $('.author', message).text(msg.author); $('.timestamp', message).text(msg.time); return message; } var lastAuthor; function onMessage(msg, container) { if (owStorage.get('lastMessage') == msg.content) owStorage.set('lastMessage', ''); var message = msg2dom(msg); if (msg.author == lastAuthor) $('.author', message).hide(); else lastAuthor = msg.author; msg = null; message.mouseenter( function() { $(this).addClass('highlighted'); $('.overlay').css({top: $(this).position().top}); $('.overlay .sent').text($('.timestamp', this).text()); $('.overlay').show(); }); message.mouseleave( function() { $(this).removeClass('highlighted'); $('.overlay').hide(); }); container.append(message); } function onMessages(msgs) { var container = $('<div class="messages"></div>'); for (var i = 0; i < msgs.length; i++) onMessage(msgs[i], container); container.hide(); $('#incoming-messages').append(container); container.slideDown(scrollToBottom); } $('#incoming-messages').hide(); for (var i = 0; i < convStorage.length; i++) onMessage(convStorage.get(i), $('#incoming-messages')); $('#incoming-messages').slideDown(); var RECONNECT_SECONDS = 30; function startListening() { OpenWebChat.listenForMessages( {storage: convStorage, onMessages: onMessages, onError: function onError(exception) { var timeLeft = RECONNECT_SECONDS; if (window.console) window.console.log('The error', exception, 'occurred.'); $('.error .seconds-left').text(timeLeft); $('.error .plural').show(); $('.error').slideDown(); var intervalId = window.setInterval( function() { timeLeft -= 1; if (timeLeft == 1) $('.error .plural').hide(); if (!timeLeft) { window.clearInterval(intervalId); $('.error').slideUp(startListening); } else $('.error .seconds-left').text(timeLeft); }, 1000 ); } }); } startListening(); });