]> jfr.im git - irc/quakenet/qwebirc.git/blame - js/ui/baseui.js
Fix feedback backspace not-working bug.
[irc/quakenet/qwebirc.git] / js / ui / baseui.js
CommitLineData
e20e5a6b
CP
1qwebirc.ui.WINDOW_STATUS = 1;
2qwebirc.ui.WINDOW_QUERY = 2;
3qwebirc.ui.WINDOW_CHANNEL = 3;
4qwebirc.ui.WINDOW_CUSTOM = 4;
5qwebirc.ui.WINDOW_CONNECT = 5;
f74802c5 6qwebirc.ui.WINDOW_MESSAGES = 6;
e20e5a6b 7qwebirc.ui.CUSTOM_CLIENT = "custom";
9e769c12 8
e20e5a6b 9qwebirc.ui.BaseUI = new Class({
2cad083e 10 Implements: [Events],
a59dc700 11 initialize: function(parentElement, windowClass, uiName, options) {
2cad083e 12 this.options = options;
a59dc700 13
9e769c12 14 this.windows = {};
ffbb638d 15 this.clients = {};
e20e5a6b 16 this.windows[qwebirc.ui.CUSTOM_CLIENT] = {};
9e769c12
CP
17 this.windowArray = [];
18 this.windowClass = windowClass;
19 this.parentElement = parentElement;
20 this.parentElement.addClass("qwebirc");
21 this.parentElement.addClass("qwebirc-" + uiName);
e8db8558 22 this.firstClient = false;
e20e5a6b 23 this.commandhistory = new qwebirc.irc.CommandHistory();
ffbb638d 24 this.clientId = 0;
9e769c12
CP
25 },
26 newClient: function(client) {
ffbb638d 27 client.id = this.clientId++;
96f28062
CP
28 client.hilightController = new qwebirc.ui.HilightController(client);
29
ffbb638d
CP
30 this.windows[client.id] = {}
31 this.clients[client.id] = client;
e20e5a6b 32 var w = this.newWindow(client, qwebirc.ui.WINDOW_STATUS, "Status");
9e769c12 33 this.selectWindow(w);
e8db8558
CP
34 if(!this.firstClient) {
35 this.firstClient = true;
e20e5a6b 36 w.addLine("", "qwebirc v" + qwebirc.VERSION);
391f51ff 37 w.addLine("", "Copyright (C) 2008-2009 Chris Porter. All rights reserved.");
e8db8558 38 w.addLine("", "http://webchat.quakenet.org/");
4094890f 39 w.addLine("", "This is BETA quality software, please report bugs to slug@quakenet.org");
e8db8558 40 }
9e769c12
CP
41 return w;
42 },
ffbb638d
CP
43 getClientId: function(client) {
44 if(client == qwebirc.ui.CUSTOM_CLIENT) {
45 return qwebirc.ui.CUSTOM_CLIENT;
46 } else {
47 return client.id;
48 }
49 },
f74802c5
CP
50 getWindowIdentifier: function(type, name) {
51 if(type == qwebirc.ui.WINDOW_MESSAGES)
52 return "-M";
e20e5a6b 53 if(type == qwebirc.ui.WINDOW_STATUS)
f74802c5 54 return "";
26c81b65 55 return "_" + name.toIRCLower();
f74802c5
CP
56 },
57 newWindow: function(client, type, name) {
58 var w = this.getWindow(client, type, name);
59 if($defined(w))
60 return w;
9e769c12 61
f74802c5
CP
62 var wId = this.getWindowIdentifier(type, name);
63 var w = this.windows[this.getClientId(client)][wId] = new this.windowClass(this, client, type, name, wId);
9e769c12
CP
64 this.windowArray.push(w);
65
66 return w;
67 },
f74802c5
CP
68 getWindow: function(client, type, name) {
69 var c = this.windows[this.getClientId(client)];
70 if(!$defined(c))
71 return null;
72
73 return c[this.getWindowIdentifier(type, name)];
74 },
9e769c12
CP
75 getActiveWindow: function() {
76 return this.active;
77 },
1d42a76f
CP
78 getActiveIRCWindow: function(client) {
79 if(!this.active || this.active.type == qwebirc.ui.WINDOW_CUSTOM) {
f74802c5 80 return this.windows[this.getClientId(client)][this.getWindowIdentifier(qwebirc.ui.WINDOW_STATUS)];
1d42a76f
CP
81 } else {
82 return this.active;
83 }
84 },
9e769c12
CP
85 __setActiveWindow: function(window) {
86 this.active = window;
87 },
88 selectWindow: function(window) {
89 if(this.active)
90 this.active.deselect();
91 window.select(); /* calls setActiveWindow */
a59dc700 92 document.title = window.name + " - " + this.options.appTitle;
9e769c12 93 },
ff4befd8
CP
94 nextWindow: function(direction) {
95 if(this.windowArray.length == 0 || !this.active)
96 return;
97
98 if(!direction)
99 direction = 1;
100
101 var index = this.windowArray.indexOf(this.active);
102 if(index == -1)
103 return;
104
105 index = index + direction;
106 if(index < 0) {
107 index = this.windowArray.length - 1;
108 } else if(index >= this.windowArray.length) {
109 index = 0;
110 }
111
112 this.selectWindow(this.windowArray[index]);
113 },
114 prevWindow: function() {
115 this.nextWindow(-1);
116 },
9e769c12
CP
117 __closed: function(window) {
118 if(window.active) {
119 this.active = undefined;
120 if(this.windowArray.length == 1) {
121 this.windowArray = [];
122 } else {
123 var index = this.windowArray.indexOf(window);
6f2e4a37
CP
124 if(index == -1) {
125 return;
126 } else if(index == 0) {
9e769c12
CP
127 this.selectWindow(this.windowArray[1]);
128 } else {
129 this.selectWindow(this.windowArray[index - 1]);
130 }
9e769c12
CP
131 }
132 }
133
404cfb58 134 this.windowArray = this.windowArray.erase(window);
ffbb638d 135 delete this.windows[this.getClientId(window.client)][window.identifier];
eb9b087b 136 },
eb9b087b
CP
137 /*
138 this shouldn't be called by overriding classes!
66de775f 139 they should implement their own!
eb9b087b
CP
140 some form of user input MUST be received before an
141 IRC connection is made, else users are going to get
142 tricked into getting themselves glined
143 */
66de775f 144 loginBox: function(callback, initialNickname, initialChannels, autoConnect, autoNick) {
2cad083e 145 qwebirc.ui.GenericLoginBox(this.parentElement, callback, initialNickname, initialChannels, autoConnect, autoNick, this.options.networkName);
9e769c12
CP
146 }
147});
381fddfd 148
e20e5a6b
CP
149qwebirc.ui.StandardUI = new Class({
150 Extends: qwebirc.ui.BaseUI,
43cb8910
CP
151 UICommands: [
152 ["Options", "options"],
153 ["Add webchat to your site", "embedded"],
154 ["Privacy policy", "privacy"],
391f51ff 155 ["Feedback", "feedback"],
43cb8910
CP
156 ["About qwebirc", "about"]
157 ],
381fddfd
CP
158 initialize: function(parentElement, windowClass, uiName, options) {
159 this.parent(parentElement, windowClass, uiName, options);
3184781b
CP
160
161 this.tabCompleter = new qwebirc.ui.TabCompleterFactory(this);
fb71087a 162 this.uiOptions = new qwebirc.ui.DefaultOptionsClass(this);
ebb21d2e
CP
163 this.customWindows = {};
164
20157c51
CP
165 if(Browser.Engine.trident) {
166 ev = "keydown";
167 } else {
168 ev = "keypress";
169 }
170 document.addEvent(ev, this.__handleHotkey.bind(this));
171 },
172 __handleHotkey: function(x) {
173 if(!x.alt || x.control) {
174 if(x.key == "backspace" || x.key == "/")
175 if(!this.getInputFocused(x))
176 new Event(x).stop();
177 return;
178 }
179 var success = false;
180 if(x.key == "a" || x.key == "A") {
181 var highestNum = 0;
182 var highestIndex = -1;
183 success = true;
184
185 new Event(x).stop();
186 for(var i=0;i<this.windowArray.length;i++) {
187 var h = this.windowArray[i].hilighted;
188 if(h > highestNum) {
189 highestIndex = i;
190 highestNum = h;
381fddfd 191 }
20157c51
CP
192 }
193 if(highestIndex > -1)
194 this.selectWindow(this.windowArray[highestIndex]);
195 } else if(x.key >= '0' && x.key <= '9') {
196 success = true;
197
198 number = x.key - '0';
199 if(number == 0)
200 number = 10
424608ac 201
20157c51
CP
202 number = number - 1;
203
204 if(number >= this.windowArray.length)
205 return;
381fddfd 206
20157c51
CP
207 this.selectWindow(this.windowArray[number]);
208 } else if(x.key == "left") {
209 this.prevWindow();
210 success = true;
211 } else if(x.key == "right") {
212 this.nextWindow();
213 success = true;
214 }
215 if(success)
216 new Event(x).stop();
217 },
218 getInputFocused: function(x) {
deebe19a
CP
219 if($$("input").indexOf(x.target) == -1 && $$("textarea").indexOf(x.target) == -1)
220 return false;
221 return true;
841a451d 222 },
8af49135
CP
223 newCustomWindow: function(name, select, type) {
224 if(!type)
e20e5a6b 225 type = qwebirc.ui.WINDOW_CUSTOM;
8af49135 226
e20e5a6b 227 var w = this.newWindow(qwebirc.ui.CUSTOM_CLIENT, type, name);
8af49135 228 w.addEvent("close", function(w) {
f74802c5 229 delete this.windows[qwebirc.ui.CUSTOM_CLIENT][w.identifier];
8af49135
CP
230 }.bind(this));
231
232 if(select)
233 this.selectWindow(w);
6c19eb8f 234
8af49135
CP
235 return w;
236 },
ebb21d2e
CP
237 addCustomWindow: function(windowName, class_, cssClass, options) {
238 if(!$defined(options))
239 options = {};
240
241 if(this.customWindows[windowName]) {
242 this.selectWindow(this.customWindows[windowName]);
8af49135 243 return;
841a451d 244 }
8af49135 245
ebb21d2e
CP
246 var d = this.newCustomWindow(windowName, true);
247 this.customWindows[windowName] = d;
248
249 d.addEvent("close", function() {
250 this.customWindows[windowName] = null;
8af49135
CP
251 }.bind(this));
252
ebb21d2e 253 if(cssClass)
e1a91a8a 254 d.lines.addClass("qwebirc-" + cssClass);
ebb21d2e
CP
255
256 var ew = new class_(d.lines, options);
8af49135 257 ew.addEvent("close", function() {
ebb21d2e 258 d.close();
8af49135 259 }.bind(this));
841a451d 260 },
ebb21d2e 261 embeddedWindow: function() {
b35116e2 262 this.addCustomWindow("Embedding wizard", qwebirc.ui.EmbedWizard, "embeddedwizard");
ebb21d2e
CP
263 },
264 optionsWindow: function() {
265 this.addCustomWindow("Options", qwebirc.ui.OptionsPane, "optionspane", this.uiOptions);
266 },
e1a91a8a
CP
267 aboutWindow: function() {
268 this.addCustomWindow("About", qwebirc.ui.AboutPane, "aboutpane", this.uiOptions);
269 },
b35116e2
CP
270 privacyWindow: function() {
271 this.addCustomWindow("Privacy policy", qwebirc.ui.PrivacyPolicyPane, "privacypolicypane", this.uiOptions);
272 },
391f51ff
CP
273 feedbackWindow: function() {
274 this.addCustomWindow("Feedback", qwebirc.ui.FeedbackPane, "feedbackpane", this.uiOptions);
275 },
8af49135
CP
276 urlDispatcher: function(name) {
277 if(name == "embedded")
925fc357 278 return ["a", this.embeddedWindow.bind(this)];
ebb21d2e
CP
279
280 if(name == "options")
281 return ["a", this.optionsWindow.bind(this)];
8af49135
CP
282
283 return null;
3184781b
CP
284 },
285 tabComplete: function(element) {
286 this.tabCompleter.tabComplete(element);
287 },
288 resetTabComplete: function() {
289 this.tabCompleter.reset();
8af49135 290 }
381fddfd 291});
6f2e4a37 292
fb71087a 293qwebirc.ui.SoundUI = new Class({
e20e5a6b 294 Extends: qwebirc.ui.StandardUI,
fb71087a
CP
295 initialize: function(parentElement, windowClass, uiName, options) {
296 this.parent(parentElement, windowClass, uiName, options);
297
127631e0 298 this.soundInited = false;
fb71087a 299 this.soundReady = false;
fb71087a 300
127631e0 301 this.setBeepOnMention(this.uiOptions.BEEP_ON_MENTION);
fb71087a 302 },
127631e0
CP
303 soundInit: function() {
304 if(this.soundInited)
fb71087a 305 return;
127631e0
CP
306 if(!$defined(Browser.Plugins.Flash) || Browser.Plugins.Flash.version < 8)
307 return;
308 this.soundInited = true;
309
310 this.soundPlayer = new qwebirc.sound.SoundPlayer();
311 this.soundPlayer.addEvent("ready", function() {
312 this.soundReady = true;
313 }.bind(this));
314 this.soundPlayer.go();
fb71087a 315 },
127631e0
CP
316 setBeepOnMention: function(value) {
317 if(value)
318 this.soundInit();
319 this.beepOnMention = value;
320 },
321 beep: function() {
322 if(!this.soundReady || !this.beepOnMention)
fb71087a 323 return;
127631e0
CP
324
325 this.soundPlayer.beep();
fb71087a
CP
326 }
327});
328
329qwebirc.ui.QuakeNetUI = new Class({
330 Extends: qwebirc.ui.SoundUI,
2cd9e32d
CP
331 urlDispatcher: function(name, window) {
332 if(name == "qwhois") {
7cb09779 333 return ["span", function(auth) {
2cd9e32d 334 this.client.exec("/MSG Q whois #" + auth);
925fc357
CP
335 }.bind(window)];
336 }
337 if(name == "whois") {
338 return ["span", function(nick) {
339 this.client.exec("/WHOIS " + nick);
340 }.bind(window)];
2cd9e32d 341 }
2cd9e32d 342 return this.parent(name);
ffbb638d
CP
343 },
344 logout: function() {
345 if(!qwebirc.auth.loggedin())
346 return;
347 if(confirm("Log out?")) {
348 for(var client in this.clients) {
349 this.clients[client].quit("Logged out");
350 };
351 document.location = "/auth?logout=1";
352 }
2cd9e32d
CP
353 }
354});
355
356qwebirc.ui.NewLoginUI = new Class({
357 Extends: qwebirc.ui.QuakeNetUI,
6f2e4a37
CP
358 loginBox: function(callbackfn, initialNickname, initialChannels, autoConnect, autoNick) {
359 this.postInitialize();
c38a0240 360
e20e5a6b 361 var w = this.newCustomWindow("Connect", true, qwebirc.ui.WINDOW_CONNECT);
6f2e4a37
CP
362 var callback = function(args) {
363 w.close();
364 callbackfn(args);
365 };
366
2cad083e 367 qwebirc.ui.GenericLoginBox(w.lines, callback, initialNickname, initialChannels, autoConnect, autoNick, this.options.networkName);
6f2e4a37
CP
368 }
369});