#include "userlist.h" #include "tab_userlists.h" #include "tab_supervisor.h" #include "abstractclient.h" #include "pixmapgenerator.h" #include "userinfobox.h" #include "user_context_menu.h" #include "gameselector.h" #include #include #include #include #include #include #include #include #include #include #include #include #include #include "pending_command.h" #include "pb/session_commands.pb.h" #include "pb/moderator_commands.pb.h" #include "pb/response_get_games_of_user.pb.h" #include "pb/response_get_user_info.pb.h" BanDialog::BanDialog(const ServerInfo_User &info, QWidget *parent) : QDialog(parent) { setAttribute(Qt::WA_DeleteOnClose); nameBanCheckBox = new QCheckBox(tr("ban &user name")); nameBanCheckBox->setChecked(true); nameBanEdit = new QLineEdit(QString::fromStdString(info.name())); ipBanCheckBox = new QCheckBox(tr("ban &IP address")); ipBanCheckBox->setChecked(true); ipBanEdit = new QLineEdit(QString::fromStdString(info.address())); QGridLayout *banTypeGrid = new QGridLayout; banTypeGrid->addWidget(nameBanCheckBox, 0, 0); banTypeGrid->addWidget(nameBanEdit, 0, 1); banTypeGrid->addWidget(ipBanCheckBox, 1, 0); banTypeGrid->addWidget(ipBanEdit, 1, 1); QGroupBox *banTypeGroupBox = new QGroupBox(tr("Ban type")); banTypeGroupBox->setLayout(banTypeGrid); permanentRadio = new QRadioButton(tr("&permanent ban")); temporaryRadio = new QRadioButton(tr("&temporary ban")); temporaryRadio->setChecked(true); connect(temporaryRadio, SIGNAL(toggled(bool)), this, SLOT(enableTemporaryEdits(bool))); daysLabel = new QLabel(tr("&Days:")); daysEdit = new QSpinBox; daysEdit->setMinimum(0); daysEdit->setValue(0); daysEdit->setMaximum(10000); daysLabel->setBuddy(daysEdit); hoursLabel = new QLabel(tr("&Hours:")); hoursEdit = new QSpinBox; hoursEdit->setMinimum(0); hoursEdit->setValue(0); hoursEdit->setMaximum(24); hoursLabel->setBuddy(hoursEdit); minutesLabel = new QLabel(tr("&Minutes:")); minutesEdit = new QSpinBox; minutesEdit->setMinimum(0); minutesEdit->setValue(5); minutesEdit->setMaximum(60); minutesLabel->setBuddy(minutesEdit); QGridLayout *durationLayout = new QGridLayout; durationLayout->addWidget(permanentRadio, 0, 0, 1, 6); durationLayout->addWidget(temporaryRadio, 1, 0, 1, 6); durationLayout->addWidget(daysLabel, 2, 0); durationLayout->addWidget(daysEdit, 2, 1); durationLayout->addWidget(hoursLabel, 2, 2); durationLayout->addWidget(hoursEdit, 2, 3); durationLayout->addWidget(minutesLabel, 2, 4); durationLayout->addWidget(minutesEdit, 2, 5); QGroupBox *durationGroupBox = new QGroupBox(tr("Duration of the ban")); durationGroupBox->setLayout(durationLayout); QLabel *reasonLabel = new QLabel(tr("Please enter the reason for the ban.\nThis is only saved for moderators and cannot be seen by the banned person.")); reasonEdit = new QPlainTextEdit; QLabel *visibleReasonLabel = new QLabel(tr("Please enter the reason for the ban that will be visible to the banned person.")); visibleReasonEdit = new QPlainTextEdit; QPushButton *okButton = new QPushButton(tr("&OK")); okButton->setAutoDefault(true); connect(okButton, SIGNAL(clicked()), this, SLOT(okClicked())); QPushButton *cancelButton = new QPushButton(tr("&Cancel")); connect(cancelButton, SIGNAL(clicked()), this, SLOT(reject())); QHBoxLayout *buttonLayout = new QHBoxLayout; buttonLayout->addStretch(); buttonLayout->addWidget(okButton); buttonLayout->addWidget(cancelButton); QVBoxLayout *vbox = new QVBoxLayout; vbox->addWidget(banTypeGroupBox); vbox->addWidget(durationGroupBox); vbox->addWidget(reasonLabel); vbox->addWidget(reasonEdit); vbox->addWidget(visibleReasonLabel); vbox->addWidget(visibleReasonEdit); vbox->addLayout(buttonLayout); setLayout(vbox); setWindowTitle(tr("Ban user from server")); } void BanDialog::okClicked() { if (!nameBanCheckBox->isChecked() && !ipBanCheckBox->isChecked()) { QMessageBox::critical(this, tr("Error"), tr("You have to select a name-based or IP-based ban, or both.")); return; } accept(); } void BanDialog::enableTemporaryEdits(bool enabled) { daysLabel->setEnabled(enabled); daysEdit->setEnabled(enabled); hoursLabel->setEnabled(enabled); hoursEdit->setEnabled(enabled); minutesLabel->setEnabled(enabled); minutesEdit->setEnabled(enabled); } QString BanDialog::getBanName() const { return nameBanCheckBox->isChecked() ? nameBanEdit->text() : QString(); } QString BanDialog::getBanIP() const { return ipBanCheckBox->isChecked() ? ipBanEdit->text() : QString(); } int BanDialog::getMinutes() const { return permanentRadio->isChecked() ? 0 : (daysEdit->value() * 24 * 60 + hoursEdit->value() * 60 + minutesEdit->value()); } QString BanDialog::getReason() const { return reasonEdit->toPlainText(); } QString BanDialog::getVisibleReason() const { return visibleReasonEdit->toPlainText(); } UserListItemDelegate::UserListItemDelegate(QObject *const parent) : QStyledItemDelegate(parent) { } bool UserListItemDelegate::editorEvent(QEvent *event, QAbstractItemModel *model, const QStyleOptionViewItem &option, const QModelIndex &index) { if ((event->type() == QEvent::MouseButtonPress) && index.isValid()) { QMouseEvent *const mouseEvent = static_cast(event); if (mouseEvent->button() == Qt::RightButton) { static_cast(parent())->showContextMenu(mouseEvent->globalPos(), index); return true; } } return QStyledItemDelegate::editorEvent(event, model, option, index); } UserListTWI::UserListTWI(const ServerInfo_User &_userInfo) : QTreeWidgetItem(Type) { setUserInfo(_userInfo); } void UserListTWI::setUserInfo(const ServerInfo_User &_userInfo) { userInfo = _userInfo; setData(0, Qt::UserRole, userInfo.user_level()); setIcon(0, QIcon(UserLevelPixmapGenerator::generatePixmap(12, UserLevelFlags(userInfo.user_level())))); setIcon(1, QIcon(CountryPixmapGenerator::generatePixmap(12, QString::fromStdString(userInfo.country())))); setData(2, Qt::UserRole, QString::fromStdString(userInfo.name())); setData(2, Qt::DisplayRole, QString::fromStdString(userInfo.name())); } void UserListTWI::setOnline(bool online) { setData(0, Qt::UserRole + 1, online); setData(2, Qt::ForegroundRole, online ? QBrush() : QBrush(Qt::gray)); } bool UserListTWI::operator<(const QTreeWidgetItem &other) const { // Sort by online/offline if (data(0, Qt::UserRole + 1) != other.data(0, Qt::UserRole + 1)) return data(0, Qt::UserRole + 1).toBool(); // Sort by user level if (data(0, Qt::UserRole) != other.data(0, Qt::UserRole)) return data(0, Qt::UserRole).toInt() > other.data(0, Qt::UserRole).toInt(); // Sort by name return QString::localeAwareCompare(data(2, Qt::UserRole).toString(), other.data(2, Qt::UserRole).toString()) < 0; } UserList::UserList(TabSupervisor *_tabSupervisor, AbstractClient *_client, UserListType _type, QWidget *parent) : QGroupBox(parent), tabSupervisor(_tabSupervisor), client(_client), type(_type), onlineCount(0) { itemDelegate = new UserListItemDelegate(this); userContextMenu = new UserContextMenu(tabSupervisor, this); connect(userContextMenu, SIGNAL(openMessageDialog(QString, bool)), this, SIGNAL(openMessageDialog(QString, bool))); userTree = new QTreeWidget; userTree->setColumnCount(3); #if QT_VERSION < 0x050000 userTree->header()->setResizeMode(QHeaderView::ResizeToContents); #else userTree->header()->setSectionResizeMode(QHeaderView::ResizeToContents); #endif userTree->setHeaderHidden(true); userTree->setRootIsDecorated(false); userTree->setIconSize(QSize(20, 12)); userTree->setItemDelegate(itemDelegate); userTree->setAlternatingRowColors(true); connect(userTree, SIGNAL(itemActivated(QTreeWidgetItem *, int)), this, SLOT(userClicked(QTreeWidgetItem *, int))); QVBoxLayout *vbox = new QVBoxLayout; vbox->addWidget(userTree); setLayout(vbox); retranslateUi(); } void UserList::retranslateUi() { userContextMenu->retranslateUi(); switch (type) { case AllUsersList: titleStr = tr("Users online: %1"); break; case RoomList: titleStr = tr("Users in this room: %1"); break; case BuddyList: titleStr = tr("Buddies online: %1 / %2"); break; case IgnoreList: titleStr = tr("Ignored users online: %1 / %2"); break; } updateCount(); } void UserList::processUserInfo(const ServerInfo_User &user, bool online) { const QString userName = QString::fromStdString(user.name()); UserListTWI *item = users.value(userName); if (item) item->setUserInfo(user); else { item = new UserListTWI(user); users.insert(userName, item); userTree->addTopLevelItem(item); if (online) ++onlineCount; updateCount(); } item->setOnline(online); } bool UserList::deleteUser(const QString &userName) { UserListTWI *twi = users.value(userName); if (twi) { users.remove(userName); userTree->takeTopLevelItem(userTree->indexOfTopLevelItem(twi)); if (twi->data(0, Qt::UserRole + 1).toBool()) --onlineCount; delete twi; updateCount(); return true; } return false; } void UserList::setUserOnline(const QString &userName, bool online) { UserListTWI *twi = users.value(userName); if (!twi) return; twi->setOnline(online); if (online) ++onlineCount; else --onlineCount; updateCount(); } void UserList::updateCount() { QString str = titleStr; if ((type == BuddyList) || (type == IgnoreList)) str = str.arg(onlineCount); setTitle(str.arg(userTree->topLevelItemCount())); } void UserList::userClicked(QTreeWidgetItem *item, int /*column*/) { emit openMessageDialog(item->data(2, Qt::UserRole).toString(), true); } void UserList::showContextMenu(const QPoint &pos, const QModelIndex &index) { const ServerInfo_User &userInfo = static_cast(userTree->topLevelItem(index.row()))->getUserInfo(); userContextMenu->showContextMenu(pos, QString::fromStdString(userInfo.name()), UserLevelFlags(userInfo.user_level())); } void UserList::sortItems() { userTree->sortItems(1, Qt::AscendingOrder); }