+void Server::handleUserNick(QString bufname, QString msg) {
+ QString nick = msg.section(' ', 0, 0);
+ putCmd("NICK", QStringList(nick));
+}
+
+void Server::handleUserOp(QString bufname, QString msg) {
+ QStringList nicks = msg.split(' ', QString::SkipEmptyParts);
+ QString m = "+"; for(int i = 0; i < nicks.count(); i++) m += 'o';
+ QStringList params;
+ params << bufname << m << nicks;
+ putCmd("MODE", params);
+}
+
+void Server::handleUserPart(QString bufname, QString msg) {
+ QStringList params;
+ params << bufname << msg;
+ putCmd("PART", params);
+}
+
+void Server::handleUserQuit(QString bufname, QString msg) {
+ putCmd("QUIT", QStringList(msg));
+}
+
+void Server::handleUserQuote(QString bufname, QString msg) {
+ putRawLine(msg);
+}
+
+void Server::handleUserSay(QString bufname, QString msg) {
+ if(bufname.isEmpty()) return; // server buffer
+ QStringList params;
+ params << bufname << msg;
+ putCmd("PRIVMSG", params);
+ emit displayMsg(params[0], Message(Message::Msg, msg, currentNick, Message::Self));
+}
+
+void Server::handleUserVoice(QString bufname, QString msg) {
+ QStringList nicks = msg.split(' ', QString::SkipEmptyParts);
+ QString m = "+"; for(int i = 0; i < nicks.count(); i++) m += 'v';
+ QStringList params;
+ params << bufname << m << nicks;
+ putCmd("MODE", params);
+}
+
+/**********************************************************************************/
+
+void Server::handleServerJoin(QString prefix, QStringList params) {
+ Q_ASSERT(params.count() == 1);
+ QString nick = updateNickFromMask(prefix);
+ if(nick == currentNick) {
+ // Q_ASSERT(!buffers.contains(params[0])); // cannot join a buffer twice!
+ // Buffer *buf = new Buffer(params[0]);
+ // buffers[params[0]] = buf;
+ } else {
+ VarMap n;
+ if(nicks.contains(nick)) {
+ n = nicks[nick].toMap();
+ VarMap chans = n["Channels"].toMap();
+ // Q_ASSERT(!chans.keys().contains(params[0])); TODO uncomment
+ chans[params[0]] = VarMap();
+ n["Channels"] = chans;
+ nicks[nick] = n;
+ emit nickUpdated(network, nick, n);
+ } else {
+ VarMap chans;
+ chans[params[0]] = VarMap();
+ n["Channels"] = chans;
+ n["User"] = userFromMask(prefix);
+ n["Host"] = hostFromMask(prefix);
+ nicks[nick] = n;
+ emit nickAdded(network, nick, n);
+ }
+ emit displayMsg(params[0], Message(Message::Join, params[0], prefix));
+ }
+}
+
+void Server::handleServerKick(QString prefix, QStringList params) {
+ QString kicker = updateNickFromMask(prefix);
+ QString nick = params[1];
+ Q_ASSERT(nicks.contains(nick));
+ VarMap n = nicks[nick].toMap();
+ VarMap chans = n["Channels"].toMap();
+ Q_ASSERT(chans.contains(params[0]));
+ chans.remove(params[0]);
+ QString msg = nick;
+ if(params.count() > 2) msg = QString("%1 %2").arg(msg).arg(params[2]);
+ emit displayMsg(params[0], Message(Message::Kick, msg, prefix));
+ if(chans.count() > 0) {
+ n["Channels"] = chans;
+ nicks[nick] = n;
+ emit nickUpdated(network, nick, n);
+ } else {
+ nicks.remove(nick);
+ emit nickRemoved(network, nick);
+ }
+}
+
+void Server::handleServerMode(QString prefix, QStringList params) {
+ if(isChannelName(params[0])) {
+ // TODO only channel-user modes supported by now
+ QString prefixes = serverSupports["PrefixModes"].toString();
+ QString modes = params[1];
+ int p = 2;
+ int m = 0;
+ bool add = true;
+ while(m < modes.length()) {
+ if(modes[m] == '+') { add = true; m++; continue; }
+ if(modes[m] == '-') { add = false; m++; continue; }
+ if(prefixes.contains(modes[m])) { // it's a user channel mode
+ Q_ASSERT(params.count() > m && nicks.contains(params[p]));
+ QString nick = params[p++];
+ VarMap n = nicks[nick].toMap(); VarMap clist = n["Channels"].toMap(); VarMap chan = clist[params[0]].toMap();
+ QString mstr = chan["Mode"].toString();
+ add ? mstr += modes[m] : mstr.remove(modes[m]);
+ chan["Mode"] = mstr; clist[params[0]] = chan; n["Channels"] = clist; nicks[nick] = n;
+ emit nickUpdated(network, nick, n);
+ m++;
+ } else {
+ // TODO add more modes
+ m++;
+ }
+ }
+ emit displayMsg(params[0], Message(Message::Mode, params.join(" "), prefix));
+ } else {
+ //Q_ASSERT(nicks.contains(params[0]));
+ //VarMap n = nicks[params[0]].toMap();
+ //QString mode = n["Mode"].toString();
+ emit displayMsg("", Message(Message::Mode, params.join(" ")));
+ }
+}
+
+void Server::handleServerNick(QString prefix, QStringList params) {
+ QString oldnick = updateNickFromMask(prefix);
+ QString newnick = params[0];
+ QVariant v = nicks.take(oldnick);
+ nicks[newnick] = v;
+ VarMap chans = v.toMap()["Channels"].toMap();
+ foreach(QString c, chans.keys()) {
+ if(oldnick != currentNick) { emit displayMsg(c, Message(Message::Nick, newnick, prefix)); }
+ else { emit displayMsg(c, Message(Message::Nick, newnick, newnick)); }
+ }
+ emit nickRenamed(network, oldnick, newnick);
+ if(oldnick == currentNick) {
+ currentNick = newnick;
+ emit ownNickSet(network, newnick);
+ }
+}
+
+void Server::handleServerNotice(QString prefix, QStringList params) {
+ //Message msg(Message::Notice, params[1], prefix);
+ if(prefix == currentServer) emit displayMsg("", Message(Message::Server, params[1], prefix));
+ else emit displayMsg("", Message(Message::Notice, params[1], prefix));
+}
+
+void Server::handleServerPart(QString prefix, QStringList params) {
+ QString nick = updateNickFromMask(prefix);
+ Q_ASSERT(nicks.contains(nick));
+ VarMap n = nicks[nick].toMap();
+ VarMap chans = n["Channels"].toMap();
+ Q_ASSERT(chans.contains(params[0]));
+ chans.remove(params[0]);
+ QString msg;
+ if(params.count() > 1) msg = params[1];
+ emit displayMsg(params[0], Message(Message::Part, msg, prefix));
+ if(chans.count() > 0) {
+ n["Channels"] = chans;
+ nicks[nick] = n;
+ emit nickUpdated(network, nick, n);
+ } else {
+ nicks.remove(nick);
+ emit nickRemoved(network, nick);
+ }
+}
+
+void Server::handleServerPing(QString prefix, QStringList params) {
+ putCmd("PONG", params);
+}
+
+void Server::handleServerPrivmsg(QString prefix, QStringList params) {
+ updateNickFromMask(prefix);
+ emit displayMsg(params[0], Message(Message::Msg, params[1], prefix));
+
+}
+
+void Server::handleServerQuit(QString prefix, QStringList params) {
+ QString nick = updateNickFromMask(prefix);
+ Q_ASSERT(nicks.contains(nick));
+ VarMap chans = nicks[nick].toMap()["Channels"].toMap();
+ foreach(QString c, chans.keys()) {
+ emit displayMsg(c, Message(Message::Quit, params[0], prefix));
+ }
+ nicks.remove(nick);
+ emit nickRemoved(network, nick);
+}
+
+/* RPL_WELCOME */
+void Server::handleServer001(QString prefix, QStringList params) {
+ currentServer = prefix;
+ currentNick = params[0];
+ VarMap n;
+ n["Channels"] = VarMap();
+ nicks[currentNick] = n;
+ emit ownNickSet(network, currentNick);
+ emit nickAdded(network, currentNick, VarMap());
+ emit displayMsg("", Message(Message::Server, params[1], prefix));
+}
+
+/* RPL_ISUPPORT */
+void Server::handleServer005(QString prefix, QStringList params) {
+ foreach(QString p, params) {
+ QString key = p.section("=", 0, 0);
+ QString val = p.section("=", 1);
+ serverSupports[key] = val;
+ // handle some special cases
+ if(key == "PREFIX") {
+ VarMap foo; QString modes, prefixes;
+ Q_ASSERT(val.contains(')') && val.startsWith('('));
+ int m = 1, p;
+ for(p = 2; p < val.length(); p++) if(val[p] == ')') break;
+ p++;
+ for(; val[m] != ')'; m++, p++) {
+ Q_ASSERT(p < val.length());
+ foo[QString(val[m])] = QString(val[p]);
+ modes += val[m]; prefixes += val[p];
+ }
+ serverSupports["PrefixModes"] = modes; serverSupports["Prefixes"] = prefixes;
+ serverSupports["ModePrefixMap"] = foo;
+ }
+ }
+}