1 /***************************************************************************
2 * Copyright (C) 2005 by The Quassel Team *
3 * devel@quassel-irc.org *
5 * This program is free software; you can redistribute it and/or modify *
6 * it under the terms of the GNU General Public License as published by *
7 * the Free Software Foundation; either version 2 of the License, or *
8 * (at your option) any later version. *
10 * This program is distributed in the hope that it will be useful, *
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of *
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
13 * GNU General Public License for more details. *
15 * You should have received a copy of the GNU General Public License *
16 * along with this program; if not, write to the *
17 * Free Software Foundation, Inc., *
18 * 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. *
19 ***************************************************************************/
21 #include "serverlist.h"
24 /* NOTE: This dialog holds not only the server list, but also the identities.
25 * This makes perfect sense given the fact that connections are initiated from
26 * this dialog, and that the dialog exists during the lifetime of the program.
29 ServerListDlg::ServerListDlg(QWidget *parent) : QDialog(parent) {
33 settings.beginGroup("GUI");
34 ui.showOnStartup->setChecked(settings.value("ShowServerListOnStartup", true).toBool());
35 // create some default entries
36 VarMap s1, s2, s3, s4;
38 s1["group"] = "Private Servers";
39 networks["mindNet"] = s1;
40 s2["group"] = "Private Servers";
41 networks["fooBar"] = s2;
43 networks["Single"] = s3;
44 s4["group"] = "Public Servers";
45 networks["public"] = s4;
47 // load networks from QSettings here instead
50 // Construct tree widget (and its items) from networks
52 headers << "Network" << "Autoconnect";
53 ui.networkTree->setHeaderLabels(headers);
54 QHash<QString, QTreeWidgetItem *> groups;
55 foreach(QString net, networks.keys()) {
56 VarMap s = networks[net].toMap();
57 QString gr = s["group"].toString();
58 QTreeWidgetItem *item = 0;
60 item = new QTreeWidgetItem(ui.networkTree);
62 if(groups.contains(gr)) {
63 item = new QTreeWidgetItem(groups[gr]);
65 QTreeWidgetItem *newgr = new QTreeWidgetItem(ui.networkTree);
66 newgr->setText(0, gr);
67 newgr->setFlags(newgr->flags() & ~Qt::ItemIsSelectable);
68 ui.networkTree->expandItem(newgr);
70 item = new QTreeWidgetItem(newgr);
73 item->setText(0, net);
74 //item->setFlags(item->flags() | Qt::ItemIsUserCheckable);
75 item->setCheckState(1, Qt::Unchecked);
77 connect(ui.networkTree, SIGNAL(itemSelectionChanged()), this, SLOT(updateButtons()));
83 ServerListDlg::~ServerListDlg() {
87 void ServerListDlg::updateButtons() {
88 QList<QTreeWidgetItem *> selected = ui.networkTree->selectedItems();
89 ui.editButton->setEnabled(selected.size() == 1);
90 ui.deleteButton->setEnabled(selected.size() >= 1);
91 ui.connectButton->setEnabled(selected.size() >= 1);
95 bool ServerListDlg::showOnStartup() {
96 return ui.showOnStartup->isChecked();
99 void ServerListDlg::on_addButton_clicked() {
100 NetworkEditDlg dlg(this, VarMap(), identities);
101 if(dlg.exec() == QDialog::Accepted) {
106 void ServerListDlg::loadNetworks() {
110 void ServerListDlg::storeNetworks() {
114 void ServerListDlg::loadIdentities() {
115 identities = global->getData("Identities", VarMap()).toMap();
116 while(!identities.contains("Default")) {
121 void ServerListDlg::storeIdentities() {
122 global->putData("Identities", identities);
125 void ServerListDlg::editIdentities() {
126 IdentitiesDlg dlg(this, identities);
127 if(dlg.exec() == QDialog::Accepted) {
128 identities = dlg.getIdentities();
129 QMap<QString, QString> mapping = dlg.getNameMapping();
130 // add mapping here <-- well, I don't fucking know anymore what I meant by this back in 2005...
134 storeNetworks(); // ? how to treat mapping and NOT save changes not yet applied to the server list?
138 void ServerListDlg::on_showOnStartup_stateChanged(int) {
140 s.setValue("GUI/ShowServerListOnStartup", ui.showOnStartup->isChecked());
143 /***************************************************************************/
145 NetworkEditDlg::NetworkEditDlg(QWidget *parent, VarMap _network, VarMap _identities) : QDialog(parent) {
148 identities = _identities;
150 ui.identityList->addItem(tr("Default Identity"));
152 foreach(QString id, identities.keys()) {
153 if(id != "Default") ui.identityList->addItem(id);
158 VarMap NetworkEditDlg::createDefaultNetwork() {
166 /***************************************************************************/
168 IdentitiesDlg::IdentitiesDlg(QWidget *parent, VarMap _identities) : QDialog(parent) {
170 connect(global, SIGNAL(dataUpdatedRemotely(QString)), this, SLOT(globalDataUpdated(QString)));
172 connect(ui.enableAutoAway, SIGNAL(stateChanged(int)), this, SLOT(autoAwayChecked()));
174 identities = _identities;
175 foreach(QString name, identities.keys()) {
176 nameMapping[name] = name;
178 if(identities.size() == 0) {
179 VarMap id = createDefaultIdentity();
180 id["IdName"] = "Default";
181 identities["Default"] = id;
183 ui.identityList->addItem(tr("Default Identity"));
185 foreach(QString id, identities.keys()) {
186 if(id != "Default") ui.identityList->addItem(id);
189 lastIdentity = getCurIdentity();
190 connect(ui.identityList, SIGNAL(activated(QString)), this, SLOT(identityChanged(QString)));
191 connect(ui.editIdentitiesButton, SIGNAL(clicked()), this, SLOT(editIdentities()));
192 connect(ui.nickList, SIGNAL(itemSelectionChanged()), this, SLOT(nickSelectionChanged()));
193 connect(ui.addNickButton, SIGNAL(clicked()), this, SLOT(addNick()));
194 connect(ui.editNickButton, SIGNAL(clicked()), this, SLOT(editNick()));
195 connect(ui.delNickButton, SIGNAL(clicked()), this, SLOT(delNick()));
196 connect(ui.upNickButton, SIGNAL(clicked()), this, SLOT(upNick()));
197 connect(ui.downNickButton, SIGNAL(clicked()), this, SLOT(downNick()));
200 void IdentitiesDlg::globalDataUpdated(QString key) {
201 if(key == "Identities") {
202 if(QMessageBox::warning(this, tr("Data changed remotely!"), tr("<b>Some other GUI client changed the identities data!</b><br>"
203 "Apply updated settings, losing all changes done locally?"),
204 QMessageBox::Apply|QMessageBox::Discard) == QMessageBox::Apply) {
205 identities = global->getData(key).toMap();
211 VarMap IdentitiesDlg::createDefaultIdentity() {
213 id["RealName"] = "foo";
215 id["NickList"] = QStringList();
216 id["enableAwayNick"] = false;
218 id["enableAwayReason"] = false;
219 id["AwayReason"] = "";
220 id["enableReturnMessage"] = false;
221 id["ReturnMessage"] = "";
222 id["enableAutoAway"] = false;
223 id["AutoAwayTime"] = 10;
224 id["enableAutoAwayReason"] = false;
225 id["AutoAwayReason"] = "";
226 id["enableAutoAwayReturn"] = false;
227 id["AutoAwayReturn"] = "";
228 id["PartReason"] = "Quasseling elsewhere.";
229 id["QuitReason"] = "Every Quassel comes to its end.";
230 id["KickReason"] = "No more quasseling for you!";
235 QString IdentitiesDlg::getCurIdentity() {
236 if(ui.identityList->currentIndex() == 0) return "Default";
237 return ui.identityList->currentText();
240 void IdentitiesDlg::updateWidgets() {
241 VarMap id = identities[getCurIdentity()].toMap();
242 ui.realNameEdit->setText(id["RealName"].toString());
243 ui.identEdit->setText(id["Ident"].toString());
244 ui.nickList->clear();
245 ui.nickList->addItems(id["NickList"].toStringList());
246 if(ui.nickList->count()>0) ui.nickList->setCurrentRow(0);
247 ui.enableAwayNick->setChecked(id["enableAwayNick"].toBool());
248 ui.awayNickEdit->setText(id["AwayNick"].toString());
249 ui.awayNickEdit->setEnabled(ui.enableAwayNick->isChecked());
250 ui.enableAwayReason->setChecked(id["enableAwayReason"].toBool());
251 ui.awayReasonEdit->setText(id["AwayReason"].toString());
252 ui.awayReasonEdit->setEnabled(ui.enableAwayReason->isChecked());
253 ui.enableReturnMessage->setChecked(id["enableReturnMessage"].toBool());
254 ui.returnMessageEdit->setText(id["ReturnMessage"].toString());
255 ui.returnMessageEdit->setEnabled(ui.enableReturnMessage->isChecked());
256 ui.enableAutoAway->setChecked(id["enableAutoAway"].toBool());
257 ui.autoAwayTime->setValue(id["AutoAwayTime"].toInt());
258 ui.enableAutoAwayReason->setChecked(id["enableAutoAwayReason"].toBool());
259 ui.autoAwayReasonEdit->setText(id["AutoAwayReason"].toString());
260 ui.enableAutoAwayReturn->setChecked(id["enableAutoAwayReturn"].toBool());
261 ui.autoAwayReturnEdit->setText(id["AutoAwayReturn"].toString());
262 ui.partReasonEdit->setText(id["PartReason"].toString());
263 ui.kickReasonEdit->setText(id["KickReason"].toString());
264 ui.quitReasonEdit->setText(id["QuitReason"].toString());
265 // set enabled states correctly
267 nickSelectionChanged();
270 void IdentitiesDlg::updateIdentity(QString idName) {
272 id["RealName"] = ui.realNameEdit->text();
273 id["Ident"] = ui.identEdit->text();
275 for(int i = 0; i < ui.nickList->count(); i++) nicks << ui.nickList->item(i)->text();
276 id["NickList"] = nicks;
277 id["enableAwayNick"] = ui.enableAwayNick->isChecked();
278 id["AwayNick"] = ui.awayNickEdit->text();
279 id["enableAwayReason"] = ui.enableAwayReason->isChecked();
280 id["AwayReason"] = ui.awayReasonEdit->text();
281 id["enableReturnMessage"] = ui.enableReturnMessage->isChecked();
282 id["ReturnMessage"] = ui.returnMessageEdit->text();
283 id["enableAutoAway"] = ui.enableAutoAway->isChecked();
284 id["AutoAwayTime"] = ui.autoAwayTime->value();
285 id["enableAutoAwayReason"] = ui.enableAutoAwayReason->isChecked();
286 id["AutoAwayReason"] = ui.autoAwayReasonEdit->text();
287 id["enableAutoAwayReturn"] = ui.enableAutoAwayReturn->isChecked();
288 id["AutoAwayReturn"] = ui.autoAwayReturnEdit->text();
289 id["PartReason"] = ui.partReasonEdit->text();
290 id["KickReason"] = ui.kickReasonEdit->text();
291 id["QuitReason"] = ui.quitReasonEdit->text();
293 id["IdName"] = idName;
294 identities[idName] = id;
297 void IdentitiesDlg::identityChanged(QString) {
298 updateIdentity(lastIdentity);
299 lastIdentity = getCurIdentity();
303 void IdentitiesDlg::autoAwayChecked() {
304 if(ui.enableAutoAway->isChecked()) {
305 ui.autoAwayLabel_1->setEnabled(1);
306 ui.autoAwayLabel_2->setEnabled(1);
307 ui.autoAwayTime->setEnabled(1);
308 ui.enableAutoAwayReason->setEnabled(1);
309 ui.enableAutoAwayReturn->setEnabled(1);
310 ui.autoAwayReasonEdit->setEnabled(ui.enableAutoAwayReason->isChecked());
311 ui.autoAwayReturnEdit->setEnabled(ui.enableAutoAwayReturn->isChecked());
313 ui.autoAwayLabel_1->setEnabled(0);
314 ui.autoAwayLabel_2->setEnabled(0);
315 ui.autoAwayTime->setEnabled(0);
316 ui.enableAutoAwayReason->setEnabled(0);
317 ui.enableAutoAwayReturn->setEnabled(0);
318 ui.autoAwayReasonEdit->setEnabled(0);
319 ui.autoAwayReturnEdit->setEnabled(0);
323 void IdentitiesDlg::nickSelectionChanged() {
324 Q_ASSERT(ui.nickList->selectedItems().size() == 1);
325 int curidx = ui.nickList->row(ui.nickList->selectedItems()[0]);
326 ui.editNickButton->setEnabled(curidx >= 0);
327 ui.delNickButton->setEnabled(curidx >= 0);
328 ui.upNickButton->setEnabled(curidx > 0);
329 ui.downNickButton->setEnabled(curidx >= 0 && curidx < ui.nickList->count() - 1);
332 void IdentitiesDlg::addNick() {
333 NickEditDlg dlg(this);
334 if(dlg.exec() == QDialog::Accepted) {
335 QListWidgetItem *item = new QListWidgetItem(ui.nickList);
336 item->setText(dlg.getNick());
337 item->setFlags(item->flags() | Qt::ItemIsEditable);
338 ui.nickList->setCurrentItem(item);
339 nickSelectionChanged();
343 void IdentitiesDlg::editNick() {
344 NickEditDlg dlg(this, ui.nickList->currentItem()->text());
345 if(dlg.exec() == QDialog::Accepted) {
346 ui.nickList->currentItem()->setText(dlg.getNick());
350 void IdentitiesDlg::delNick() {
351 int row = ui.nickList->currentRow();
352 delete ui.nickList->takeItem(row);
353 if(row <= ui.nickList->count() - 1) ui.nickList->setCurrentRow(row);
354 else if(row > 0) ui.nickList->setCurrentRow(ui.nickList->count()-1);
355 nickSelectionChanged();
358 void IdentitiesDlg::upNick() {
359 int row = ui.nickList->currentRow();
360 QListWidgetItem *item = ui.nickList->takeItem(row);
361 ui.nickList->insertItem(row-1, item);
362 ui.nickList->setCurrentRow(row-1);
363 nickSelectionChanged();
366 void IdentitiesDlg::downNick() {
367 int row = ui.nickList->currentRow();
368 QListWidgetItem *item = ui.nickList->takeItem(row);
369 ui.nickList->insertItem(row+1, item);
370 ui.nickList->setCurrentRow(row+1);
371 nickSelectionChanged();
374 void IdentitiesDlg::accept() {
375 updateIdentity(getCurIdentity());
376 QString result = checkValidity();
377 if(result.length() == 0) QDialog::accept();
379 QMessageBox::warning(this, tr("Invalid Identity!"),
380 tr("One or more of your identities do not contain all necessary information:\n\n%1\n"
381 "Please fill in any missing information.").arg(result));
385 QString IdentitiesDlg::checkValidity() {
387 foreach(QString name, identities.keys()) {
389 VarMap id = identities[name].toMap();
390 if(name == "Default") name = tr("Default Identity");
391 if(id["RealName"].toString().length() == 0) {
392 r += tr(" You have not set a real name.");
394 if(id["Ident"].toString().length() == 0) {
395 r += tr(" You have to specify an Ident.");
397 if(id["NickList"].toStringList().size() == 0) {
398 r += tr(" You haven't entered any nicknames.");
401 reason += tr("[%1]%2\n").arg(name).arg(r);
407 void IdentitiesDlg::editIdentities() {
408 updateIdentity(getCurIdentity());
409 IdentitiesEditDlg dlg(this, identities, nameMapping, createDefaultIdentity());
410 if(dlg.exec() == QDialog::Accepted) {
411 identities = dlg.getIdentities();
412 nameMapping = dlg.getMapping();
413 ui.identityList->clear();
414 ui.identityList->addItem(tr("Default Identity"));
415 foreach(QString id, identities.keys()) {
416 if(id != "Default") ui.identityList->addItem(id);
418 lastIdentity = getCurIdentity();
423 /******************************************************************************/
425 IdentitiesEditDlg::IdentitiesEditDlg(QWidget *parent, VarMap _identities, QMap<QString, QString> _mapping, VarMap templ)
428 identities = _identities;
430 identTemplate = templ;
432 foreach(QString name, identities.keys()) {
433 if(name == "Default") continue;
434 ui.identList->addItem(name);
436 ui.identList->sortItems();
437 ui.identList->insertItem(0, tr("Default Identity"));
438 ui.identList->setCurrentRow(0);
440 connect(ui.identList, SIGNAL(itemSelectionChanged()), this, SLOT(selectionChanged()));
441 connect(ui.addButton, SIGNAL(clicked()), this, SLOT(addIdentity()));
442 connect(ui.duplicateButton, SIGNAL(clicked()), this, SLOT(duplicateIdentity()));
443 connect(ui.renameButton, SIGNAL(clicked()), this, SLOT(renameIdentity()));
444 connect(ui.deleteButton, SIGNAL(clicked()), this, SLOT(deleteIdentity()));
447 void IdentitiesEditDlg::selectionChanged() {
448 Q_ASSERT(ui.identList->selectedItems().size() == 1);
449 int idx = ui.identList->row(ui.identList->selectedItems()[0]);
450 ui.duplicateButton->setEnabled(idx >= 0);
451 ui.renameButton->setEnabled(idx > 0);
452 ui.deleteButton->setEnabled(idx > 0);
455 void IdentitiesEditDlg::addIdentity() {
456 RenameIdentityDlg dlg(this, identities.keys());
457 if(dlg.exec() == QDialog::Accepted) {
458 VarMap id = identTemplate;
459 identities[dlg.getName()] = id;
460 QListWidgetItem *item = new QListWidgetItem(dlg.getName(), ui.identList);
462 ui.identList->setCurrentItem(item);
467 void IdentitiesEditDlg::duplicateIdentity() {
468 RenameIdentityDlg dlg(this, identities.keys());
469 if(dlg.exec() == QDialog::Accepted) {
470 QString curname = ui.identList->currentRow() == 0 ? "Default" : ui.identList->currentItem()->text();
471 QVariant id = identities[curname];
472 identities[dlg.getName()] = id;
473 QListWidgetItem *item = new QListWidgetItem(dlg.getName(), ui.identList);
475 ui.identList->setCurrentItem(item);
480 void IdentitiesEditDlg::renameIdentity() {
481 QList<QString> names;
482 QString curname = ui.identList->currentItem()->text();
483 foreach(QString n, identities.keys()) {
484 if(n != curname) names.append(n);
486 RenameIdentityDlg dlg(this, names, curname);
487 if(dlg.exec() == QDialog::Accepted) {
488 QString newname = dlg.getName();
489 foreach(QString key, mapping.keys()) {
490 if(mapping[key] == curname) {
491 mapping[key] = newname;
495 QVariant id = identities.take(curname);
496 identities[newname] = id;
497 QListWidgetItem *item = ui.identList->currentItem();
498 item->setText(newname);
500 ui.identList->setCurrentItem(item);
505 void IdentitiesEditDlg::deleteIdentity() {
506 QString curname = ui.identList->currentItem()->text();
507 if(QMessageBox::question(this, tr("Delete Identity?"),
508 tr("Do you really want to delete identity \"%1\"?\nNetworks using this identity "
509 "will be reset to use the default identity.").arg(curname),
510 tr("&Delete"), tr("&Cancel"), QString(), 1, 1) == 0) {
511 delete ui.identList->takeItem(ui.identList->currentRow());
512 foreach(QString key, mapping.keys()) {
513 if(mapping[key] == curname) {
514 mapping.remove(key); break;
517 identities.remove(curname);
522 void IdentitiesEditDlg::sortList() {
523 QListWidgetItem *def = ui.identList->takeItem(0);
524 ui.identList->sortItems();
525 ui.identList->insertItem(0, def);
528 /******************************************************************************/
530 NickEditDlg::NickEditDlg(QWidget *parent, QString nick) : QDialog(parent) {
532 ui.lineEdit->setText(nick);
533 connect(ui.lineEdit, SIGNAL(textChanged(QString)), this, SLOT(textChanged(QString)));
537 void NickEditDlg::textChanged(QString text) {
538 ui.buttonBox->button(QDialogButtonBox::Ok)->setDisabled(text.isEmpty() || text == "");
541 QString NickEditDlg::getNick() {
542 return ui.lineEdit->text();
545 /*******************************************************************************/
547 RenameIdentityDlg::RenameIdentityDlg(QWidget *parent, QList<QString> _reserved, QString name) : QDialog(parent) {
549 reserved = _reserved;
550 setWindowTitle(tr("Edit Identity Name"));
551 ui.label->setText(tr("Identity:"));
552 ui.lineEdit->setText(name);
553 connect(ui.lineEdit, SIGNAL(textChanged(QString)), this, SLOT(textChanged(QString)));
557 void RenameIdentityDlg::textChanged(QString text) {
558 if(text.length() == 0) { ui.buttonBox->button(QDialogButtonBox::Ok)->setDisabled(true); return; }
559 ui.buttonBox->button(QDialogButtonBox::Ok)->setDisabled(reserved.contains(text));
562 QString RenameIdentityDlg::getName() {
563 return ui.lineEdit->text();