Added tab completion

This commit is contained in:
Mattias Erming 2014-04-07 23:19:20 +02:00
parent e0a004259a
commit dd4c9a400a
6 changed files with 113 additions and 2034 deletions

View file

@ -180,6 +180,7 @@ h2 {
padding: 0 8px; padding: 0 8px;
} }
#chat .messages { #chat .messages {
border-left: 8px solid #f0f0f0;
bottom: 30px; bottom: 30px;
left: 0; left: 0;
overflow-y: auto; overflow-y: auto;
@ -192,7 +193,7 @@ h2 {
} }
#chat .message { #chat .message {
line-height: 1.4em; line-height: 1.4em;
padding: 0 6px; padding: 0 8px;
} }
#chat .message div { #chat .message div {
display: inline; display: inline;
@ -203,6 +204,7 @@ h2 {
#chat .message .user { #chat .message .user {
color: #f00; color: #f00;
} }
#chat .message .type,
#chat .message .text { #chat .message .text {
color: inherit; color: inherit;
} }

View file

@ -1,24 +1,24 @@
<!doctype html> <!doctype html>
<html> <html>
<head> <head>
<title>Chat</title> <title>Chat</title>
<meta charset="utf-8"> <meta charset="utf-8">
<meta name="viewport" content="width=device-width, user-scalable=no"> <meta name="viewport" content="width=device-width, user-scalable=no">
<link rel="stylesheet" href="/css/bootstrap.css"> <link rel="stylesheet" href="/css/bootstrap.css">
<link rel="stylesheet" href="/css/style.css"> <link rel="stylesheet" href="/css/style.css">
</head> </head>
<body> <body>
<div id="wrap"> <div id="wrap">
<div id="viewport"> <div id="viewport">
<aside id="sidebar"> <aside id="sidebar">
<header class="header"> <header class="header">
<ul class="nav nav-tabs"> <ul class="nav nav-tabs">
<li class="active"><a href="#list" data-toggle="tab">Channels</a></li> <li class="active"><a href="#list" data-toggle="tab">Channels</a></li>
<li><a href="#settings" data-toggle="tab">Settings</a></li> <li><a href="#settings" data-toggle="tab">Settings</a></li>
@ -26,7 +26,7 @@
</header> </header>
<div class="tab-content"> <div class="tab-content">
<div id="list" class="tab-pane active"></div> <div id="list" class="tab-pane active"></div>
<div id="settings" class="tab-pane"> <div id="settings" class="tab-pane">
<div class="panel panel-default"> <div class="panel panel-default">
@ -41,7 +41,7 @@
</div> </div>
</div> </div>
</div> </div>
</div> </div>
</aside> </aside>
<div id="chat"> <div id="chat">
@ -53,7 +53,7 @@
</div> </div>
<div id="scripts"> <div id="scripts">
<script type="text/html" id="network"> <script type="text/html" id="network">
{{#networks}} {{#networks}}
<div id="network-{{id}}" class="network list-group"> <div id="network-{{id}}" class="network list-group">
@ -61,7 +61,6 @@
</div> </div>
{{/networks}} {{/networks}}
</script> </script>
<script type="text/html" id="channel"> <script type="text/html" id="channel">
{{#channels}} {{#channels}}
<a href="{{name}}" id="channel-{{id}}" class="channel list-group-item"> <a href="{{name}}" id="channel-{{id}}" class="channel list-group-item">
@ -70,7 +69,6 @@
</a> </a>
{{/channels}} {{/channels}}
</script> </script>
<script type="text/html" id="window"> <script type="text/html" id="window">
{{#channels}} {{#channels}}
<div id="window-{{id}}" class="window {{type}}"> <div id="window-{{id}}" class="window {{type}}">
@ -97,7 +95,6 @@
</div> </div>
{{/channels}} {{/channels}}
</script> </script>
<script type="text/html" id="user"> <script type="text/html" id="user">
{{#users}} {{#users}}
<a href="{{name}}" class="user"> <a href="{{name}}" class="user">
@ -105,13 +102,13 @@
</a> </a>
{{/users}} {{/users}}
</script> </script>
<script type="text/html" id="message"> <script type="text/html" id="message">
{{#messages}} {{#messages}}
<div class="message {{type}}"> <div class="message {{type}}">
<div class="time">{{time}}</div> <div class="time">{{time}}</div>
<div class="user">{{from}}</div> <div class="user">{{from}}</div>
<div class="text">{{type}} {{message}}</div> <div class="type">{{type}}</div>
<div class="text">{{message}}</div>
</div> </div>
{{/messages}} {{/messages}}
</script> </script>
@ -122,11 +119,12 @@
<script src="//cdnjs.cloudflare.com/ajax/libs/URI.js/1.11.2/URI.min.js"></script> <script src="//cdnjs.cloudflare.com/ajax/libs/URI.js/1.11.2/URI.min.js"></script>
<script src="/socket.io/socket.io.js"></script> <script src="/socket.io/socket.io.js"></script>
<script src="/js/lib/jquery.scrollGlue.js"></script>
<script src="/js/lib/bootstrap.js"></script> <script src="/js/lib/bootstrap.js"></script>
<script src="/js/lib/jquery.scrollGlue.js"></script>
<script src="/js/lib/jquery.tabComplete.js"></script>
<script src="/js/chat.js"></script> <script src="/js/chat.js"></script>
</div> </div>
</body> </body>
</html> </html>

View file

@ -1,4 +1,24 @@
$(function() { $(function() {
var commands = [
"/connect",
"/deop",
"/devoice",
"/disconnect",
"/join",
"/kick",
"/leave",
"/mode",
"/nick",
"/op",
"/part",
"/query",
"/quit",
"/server",
"/topic",
"/voice",
"/whois",
];
var socket = io.connect(""); var socket = io.connect("");
$.each(["network", "channel", "message", "user"], function(i, type) { $.each(["network", "channel", "message", "user"], function(i, type) {
socket.on(type, function(json) { socket.on(type, function(json) {
@ -46,8 +66,12 @@ $(function() {
chat.find(".messages").scrollGlue({animate: 400}).scrollToBottom(); chat.find(".messages").scrollGlue({animate: 400}).scrollToBottom();
chat.find(".window") chat.find(".window")
.find("input")
.tabComplete(commands)
.end()
.first() .first()
.bringToTop(); .bringToTop()
.end();
break; break;
case "channel": case "channel":
@ -69,9 +93,13 @@ $(function() {
render("#window", {channels: json.data}) render("#window", {channels: json.data})
).find(".window") ).find(".window")
.last() .last()
.find("input")
.tabComplete(commands)
.end()
.bringToTop() .bringToTop()
.find(".messages") .find(".messages")
.scrollGlue({animate: 400}); .scrollGlue({animate: 400})
.end();
break; break;
case "user": case "user":

File diff suppressed because it is too large Load diff

View file

@ -0,0 +1,51 @@
/*!
* jquery-tab-complete
* https://github.com/erming/jquery-tab-complete
*
* Copyright (c) 2014 Mattias Erming <mattias@mattiaserming.com>
* Licensed under the MIT License.
*
* Version 0.1.0
*/
(function($) {
$.fn.tabComplete = function(list) {
var self = this;
if (self.size() > 1) {
return self.each(function() {
$(this).tabComplete(list);
});
}
var match = [];
self.on('keydown', function(e) {
var key = e.which;
if (key != 9) {
match = [];
return;
}
var text = self.val().split(' ');
var last = text.splice(-1)[0];
if (!match.length) {
match = $.grep(list, function(w) {
return last != '' && w.indexOf(last) !== -1;
});
}
var i = match.indexOf(last) + 1;
if (i == match.length) {
i = 0;
}
if (match.length) {
last = match[i];
}
text.push(last);
self.val(text.join(' '));
return false;
});
};
})(jQuery);

View file

@ -195,20 +195,6 @@ function event(event, data) {
}); });
break; break;
case "part":
var chan = channels.findWhere({name: data[0].channels[0]});
if (data[0].nick == this.get("client").me) {
channels.remove(chan);
return;
}
var users = chan.get("users");
users.remove(users.findWhere({name: data[0].nick}));
chan.addMessage({
from: data[0].nick,
type: "part",
});
break;
case "kick": case "kick":
var chan = channels.findWhere({name: data[0].channel}); var chan = channels.findWhere({name: data[0].channel});
var users = chan.get("users"); var users = chan.get("users");
@ -281,6 +267,20 @@ function event(event, data) {
channels.first().addMessage(data[0]); channels.first().addMessage(data[0]);
break; break;
case "part":
var chan = channels.findWhere({name: data[0].channels[0]});
if (data[0].nick == this.get("client").me) {
channels.remove(chan);
return;
}
var users = chan.get("users");
users.remove(users.findWhere({name: data[0].nick}));
chan.addMessage({
from: data[0].nick,
type: "part",
});
break;
case "quit": case "quit":
channels.each(function(chan) { channels.each(function(chan) {
var users = chan.get("users"); var users = chan.get("users");