File indexing completed on 2023-09-24 04:18:15

0001 /*
0002     SPDX-FileCopyrightText: 2001-2003 Nicolas Hadacek <hadacek@kde.org>
0003 
0004     SPDX-License-Identifier: LGPL-2.0-only
0005 */
0006 
0007 #include "kexthighscore_gui.h"
0008 
0009 #include <QApplication>
0010 #include <QFileDialog>
0011 #include <QGridLayout>
0012 #include <QGroupBox>
0013 #include <QHBoxLayout>
0014 #include <QHeaderView>
0015 #include <QIcon>
0016 #include <QLabel>
0017 #include <QPushButton>
0018 #include <QTabWidget>
0019 #include <QTemporaryFile>
0020 #include <QTextStream>
0021 #include <QVBoxLayout>
0022 
0023 #include <KIO/OpenUrlJob>
0024 #include <kio_version.h>
0025 #if KIO_VERSION >= QT_VERSION_CHECK(5, 98, 0)
0026 #include <KIO/JobUiDelegateFactory>
0027 #else
0028 #include <KIO/JobUiDelegate>
0029 #endif
0030 #include <KGuiItem>
0031 #include <KIO/StatJob>
0032 #include <KIO/CopyJob>
0033 #include <KJobWidgets>
0034 #include <KMessageBox>
0035 #include <KUrlLabel>
0036 
0037 #include "kexthighscore_internal.h"
0038 #include "kexthighscore_tab.h"
0039 
0040 
0041 namespace KExtHighscore
0042 {
0043 
0044 //-----------------------------------------------------------------------------
0045 ShowItem::ShowItem(QTreeWidget *list, bool highlight)
0046     : QTreeWidgetItem(list), _highlight(highlight)
0047 {
0048 //   kDebug(11001) ;
0049   if (_highlight) {
0050     for (int i=0; i < columnCount();i++) {
0051       setForeground(i, Qt::red);
0052     }
0053   }
0054 }
0055 
0056 //-----------------------------------------------------------------------------
0057 ScoresList::ScoresList(QWidget *parent)
0058     : QTreeWidget(parent)
0059 {
0060 //   kDebug(11001) ;
0061     setSelectionMode(QTreeWidget::NoSelection);
0062 //     setItemMargin(3);
0063     setAllColumnsShowFocus(true);
0064 //     setSorting(-1);
0065     header()->setSectionsClickable(false);
0066     header()->setSectionsMovable(false);
0067 }
0068 
0069 void ScoresList::addHeader(const ItemArray &items)
0070 {
0071 //   kDebug(11001) ;
0072     addLineItem(items, 0, nullptr);
0073 }
0074 
0075 QTreeWidgetItem *ScoresList::addLine(const ItemArray &items,
0076                                    uint index, bool highlight)
0077 {
0078 //   kDebug(11001) ;
0079     QTreeWidgetItem *item = new ShowItem(this, highlight);
0080     addLineItem(items, index, item);
0081     return item;
0082 }
0083 
0084 void ScoresList::addLineItem(const ItemArray &items,
0085                              uint index, QTreeWidgetItem *line)
0086 {
0087 //   kDebug(11001) ;
0088     uint k = 0;
0089     for (int i=0; i<items.size(); i++) {
0090         const ItemContainer& container = *items[i];
0091         if ( !container.item()->isVisible() ) {
0092       continue;
0093     }
0094         if (line) {
0095       line->setText(k, itemText(container, index));
0096       line->setTextAlignment(k, container.item()->alignment());
0097     }
0098         else {
0099         headerItem()->setText(k, container.item()->label() );
0100             headerItem()->setTextAlignment(k, container.item()->alignment());
0101         }
0102         k++;
0103     }
0104     update();
0105 }
0106 
0107 //-----------------------------------------------------------------------------
0108 HighscoresList::HighscoresList(QWidget *parent)
0109     : ScoresList(parent)
0110 {
0111 //   kDebug(11001) ;
0112 }
0113 
0114 QString HighscoresList::itemText(const ItemContainer &item, uint row) const
0115 {
0116 //   kDebug(11001) ;
0117     return item.pretty(row);
0118 }
0119 
0120 void HighscoresList::load(const ItemArray &items, int highlight)
0121 {
0122 //     kDebug(11001) ;
0123     clear();
0124     QTreeWidgetItem *line = nullptr;
0125     for (int j=items.nbEntries()-1; j>=0; j--) {
0126         QTreeWidgetItem *item = addLine(items, j, j==highlight);
0127         if ( j==highlight ) line = item;
0128     }
0129     scrollTo(indexFromItem(line));
0130 }
0131 
0132 //-----------------------------------------------------------------------------
0133 HighscoresWidget::HighscoresWidget(QWidget *parent)
0134     : QWidget(parent)
0135 {
0136 //     kDebug(11001) << ": HighscoresWidget";
0137 
0138     setObjectName( QStringLiteral("show_highscores_widget" ));
0139     const ScoreInfos &s = internal->scoreInfos();
0140     const PlayerInfos &p = internal->playerInfos();
0141 
0142     QVBoxLayout *vbox = new QVBoxLayout(this);
0143     vbox->setSpacing(fontMetrics().lineSpacing());
0144 
0145     _tw = new QTabWidget(this);
0146     connect(_tw, &QTabWidget::currentChanged, this, &HighscoresWidget::handleTabChanged);
0147     vbox->addWidget(_tw);
0148 
0149     // scores tab
0150     _scoresList = new HighscoresList(nullptr);
0151     _scoresList->addHeader(s);
0152     _tw->addTab(_scoresList, i18n("Best &Scores"));
0153 
0154     // players tab
0155     _playersList = new HighscoresList(nullptr);
0156     _playersList->addHeader(p);
0157     _tw->addTab(_playersList, i18n("&Players"));
0158 
0159     // statistics tab
0160     if ( internal->showStatistics ) {
0161         _statsTab = new StatisticsTab(nullptr);
0162         _tw->addTab(_statsTab, i18n("Statistics"));
0163     }
0164 
0165     // histogram tab
0166     if ( p.histogram().size()!=0 ) {
0167         _histoTab = new HistogramTab(nullptr);
0168         _tw->addTab(_histoTab, i18n("Histogram"));
0169     }
0170 
0171     // url labels
0172     if ( internal->isWWHSAvailable() ) {
0173         QUrl url = internal->queryUrl(ManagerPrivate::Scores);
0174         _scoresUrl = new KUrlLabel(url.url(),
0175                                    i18n("View world-wide highscores"), this);
0176         connect(_scoresUrl, qOverload<>(&KUrlLabel::leftClickedUrl), this,
0177                 &HighscoresWidget::handleUrlClicked);
0178         vbox->addWidget(_scoresUrl);
0179 
0180         url = internal->queryUrl(ManagerPrivate::Players);
0181         _playersUrl = new KUrlLabel(url.url(),
0182                                     i18n("View world-wide players"), this);
0183         connect(_playersUrl, qOverload<>(&KUrlLabel::leftClickedUrl), this,
0184                 &HighscoresWidget::handleUrlClicked);
0185         vbox->addWidget(_playersUrl);
0186     }
0187     load(-1);
0188 }
0189 
0190 void HighscoresWidget::changeTab(int i)
0191 {
0192 //   kDebug(11001) ;
0193     if ( i!=_tw->currentIndex() )
0194         _tw->setCurrentIndex(i);
0195 }
0196 
0197 void HighscoresWidget::handleUrlClicked()
0198 {
0199     auto* label = qobject_cast<KUrlLabel*>(sender());
0200     if (!label) {
0201         return;
0202     }
0203 //   kDebug(11001) ;
0204     auto *job = new KIO::OpenUrlJob(QUrl(label->url()));
0205 #if KIO_VERSION >= QT_VERSION_CHECK(5, 98, 0)
0206     job->setUiDelegate(KIO::createDefaultJobUiDelegate(KJobUiDelegate::AutoHandlingEnabled, this));
0207 #else
0208     job->setUiDelegate(new KIO::JobUiDelegate(KJobUiDelegate::AutoHandlingEnabled, this));
0209 #endif
0210     job->start();
0211 }
0212 
0213 void HighscoresWidget::load(int rank)
0214 {
0215 //   kDebug(11001) << rank;
0216     _scoresList->load(internal->scoreInfos(), rank);
0217     _playersList->load(internal->playerInfos(), internal->playerInfos().id());
0218     if (_scoresUrl)
0219         _scoresUrl->setUrl(internal->queryUrl(ManagerPrivate::Scores).url());
0220     if (_playersUrl)
0221         _playersUrl->setUrl(internal->queryUrl(ManagerPrivate::Players).url());
0222     if (_statsTab) _statsTab->load();
0223     if (_histoTab) _histoTab->load();
0224 }
0225 
0226 //-----------------------------------------------------------------------------
0227 HighscoresDialog::HighscoresDialog(int rank, QWidget *parent)
0228     : KPageDialog(parent), _rank(rank), _tab(0)
0229 {
0230 //     kDebug(11001) << ": HighscoresDialog";
0231 
0232     setWindowTitle(i18nc("@title:window", "Highscores"));
0233 // TODO    setButtons( Close|User1|User2 );
0234 // TODO    setDefaultButton( Close );
0235     if ( internal->nbGameTypes()>1 )
0236         setFaceType( KPageDialog::Tree );
0237     else
0238         setFaceType( KPageDialog::Plain );
0239 // TODO    setButtonGuiItem( User1, KGuiItem(i18n("Configure..."), QLatin1String( "configure" )) );
0240 // TODO    setButtonGuiItem( User2, KGuiItem(i18n("Export...")) );
0241 
0242     for (uint i=0; i<internal->nbGameTypes(); i++) {
0243         QString title = internal->manager.gameTypeLabel(i, Manager::I18N);
0244         QString icon = internal->manager.gameTypeLabel(i, Manager::Icon);
0245         HighscoresWidget *hsw = new HighscoresWidget(nullptr);
0246         KPageWidgetItem *pageItem = new KPageWidgetItem( hsw, title);
0247         const int iconSize = style()->pixelMetric(QStyle::PM_ToolBarIconSize);
0248         pageItem->setIcon(QIcon::fromTheme(icon).pixmap(iconSize));
0249         addPage( pageItem );
0250         _pages.append(pageItem);
0251         connect(hsw, &HighscoresWidget::tabChanged, this, &HighscoresDialog::tabChanged);
0252     }
0253 
0254     connect(this, &KPageDialog::currentPageChanged,
0255             this, &HighscoresDialog::highscorePageChanged);
0256     setCurrentPage(_pages[internal->gameType()]);
0257 
0258     setStandardButtons(QDialogButtonBox::Close);
0259 }
0260 
0261 void HighscoresDialog::highscorePageChanged(KPageWidgetItem* page, KPageWidgetItem* pageold)
0262 {
0263     Q_UNUSED(pageold);
0264 //   kDebug(11001) ;
0265     int idx = _pages.indexOf( page );
0266     Q_ASSERT(idx != -1);
0267 
0268     internal->hsConfig().readCurrentConfig();
0269     uint type = internal->gameType();
0270     bool several = ( internal->nbGameTypes()>1 );
0271     if (several)
0272         internal->setGameType(idx);
0273     HighscoresWidget *hsw = static_cast<HighscoresWidget*>(page->widget());
0274     hsw->load(uint(idx)==type ? _rank : -1);
0275     if (several) setGameType(type);
0276     hsw->changeTab(_tab);
0277 }
0278 
0279 void HighscoresDialog::slotUser1()
0280 {
0281 //   kDebug(11001) ;
0282     if ( KExtHighscore::configure(this) )
0283         highscorePageChanged(currentPage(), nullptr);//update data
0284 }
0285 
0286 void HighscoresDialog::slotUser2()
0287 {
0288 //   kDebug(11001) ;
0289     QUrl url = QFileDialog::getSaveFileUrl(this, tr("HighscoresDialog"), QUrl(), QString());
0290     if ( url.isEmpty() ) return;
0291 #if KIO_VERSION >= QT_VERSION_CHECK(5, 240, 0)
0292     auto job = KIO::stat(url, KIO::StatJob::SourceSide, KIO::StatNoDetails);
0293 #else
0294     auto job = KIO::statDetails(url, KIO::StatJob::SourceSide, KIO::StatNoDetails);
0295 #endif
0296     KJobWidgets::setWindow(job, this);
0297     job->exec();
0298     if (!job->error()) {
0299         KGuiItem gi = KStandardGuiItem::save();
0300         gi.setText(i18n("Overwrite"));
0301         int res = KMessageBox::warningContinueCancel(this,
0302                                  i18n("The file already exists. Overwrite?"),
0303                                  i18n("Export"), gi);
0304         if ( res==KMessageBox::Cancel ) return;
0305     }
0306     QTemporaryFile tmp;
0307     tmp.open();
0308     QTextStream stream(&tmp);
0309     internal->exportHighscores(stream);
0310     stream.flush();
0311 //     KIO::NetAccess::upload(tmp.fileName(), url, this);
0312     auto copyJob = KIO::copy(QUrl::fromLocalFile(tmp.fileName()), url);
0313     copyJob->exec();
0314 }
0315 
0316 //-----------------------------------------------------------------------------
0317 LastMultipleScoresList::LastMultipleScoresList(
0318                             const QVector<Score> &scores, QWidget *parent)
0319     : ScoresList(parent), _scores(scores)
0320 {
0321 //     kDebug(11001) << ": LastMultipleScoresList";
0322 
0323     const ScoreInfos &s = internal->scoreInfos();
0324     addHeader(s);
0325     for (int i=0; i<scores.size(); i++) addLine(s, i, false);
0326 }
0327 
0328 void LastMultipleScoresList::addLineItem(const ItemArray &si,
0329                                          uint index, QTreeWidgetItem *line)
0330 {
0331 //   kDebug(11001) ;
0332     uint k = 1; // skip "id"
0333     for (int i=0; i<si.size()-2; i++) {
0334         if ( i==3 ) k = 5; // skip "date"
0335         const ItemContainer& container = *si[k];
0336         k++;
0337         if (line) {
0338       line->setText(i, itemText(container, index));
0339       line->setTextAlignment(i, container.item()->alignment());
0340     }
0341         else {
0342         headerItem()->setText(i, container.item()->label() );
0343             headerItem()->setTextAlignment(i, container.item()->alignment());
0344         }
0345     }
0346 }
0347 
0348 QString LastMultipleScoresList::itemText(const ItemContainer &item,
0349                                          uint row) const
0350 {
0351 //   kDebug(11001) ;
0352     QString name = item.name();
0353     if ( name==QLatin1String( "rank" ) )
0354         return (_scores[row].type()==Won ? i18n("Winner") : QString());
0355     QVariant v = _scores[row].data(name);
0356     if ( name==QLatin1String( "name" ) ) return v.toString();
0357     return item.item()->pretty(row, v);
0358 }
0359 
0360 //-----------------------------------------------------------------------------
0361 TotalMultipleScoresList::TotalMultipleScoresList(
0362                             const QVector<Score> &scores, QWidget *parent)
0363     : ScoresList(parent), _scores(scores)
0364 {
0365 //     kDebug(11001) << ": TotalMultipleScoresList";
0366     const ScoreInfos &s = internal->scoreInfos();
0367     addHeader(s);
0368     for (int i=0; i<scores.size(); i++) addLine(s, i, false);
0369 }
0370 
0371 void TotalMultipleScoresList::addLineItem(const ItemArray &si,
0372                                           uint index, QTreeWidgetItem *line)
0373 {
0374 //   kDebug(11001) ;
0375     const PlayerInfos &pi = internal->playerInfos();
0376     uint k = 1; // skip "id"
0377     for (uint i=0; i<4; i++) { // skip additional fields
0378         const ItemContainer *container;
0379         if ( i==2 ) container = pi.item(QStringLiteral( "nb games" ));
0380         else if ( i==3 ) container = pi.item(QStringLiteral( "mean score" ));
0381         else {
0382             container = si[k];
0383             k++;
0384         }
0385 
0386         if (line) {
0387       line->setText(i, itemText(*container, index));
0388       line->setTextAlignment(i, container->item()->alignment());
0389     }
0390         else {
0391             QString label =
0392                 (i==2 ? i18n("Won Games") : container->item()->label());
0393         headerItem()->setText(i, label );
0394             headerItem()->setTextAlignment(i, container->item()->alignment());
0395         }
0396     }
0397 }
0398 
0399 QString TotalMultipleScoresList::itemText(const ItemContainer &item,
0400                                           uint row) const
0401 {
0402 //   kDebug(11001) ;
0403     QString name = item.name();
0404     if ( name==QLatin1String( "rank" ) ) return QString::number(_scores.size()-row);
0405     else if ( name==QLatin1String( "nb games" ) )
0406         return QString::number( _scores[row].data(QStringLiteral( "nb won games" )).toUInt() );
0407     QVariant v = _scores[row].data(name);
0408     if ( name==QLatin1String( "name" ) ) return v.toString();
0409     return item.item()->pretty(row, v);
0410 }
0411 
0412 
0413 //-----------------------------------------------------------------------------
0414 ConfigDialog::ConfigDialog(QWidget *parent)
0415     : QDialog(parent),
0416       _saved(false), _WWHEnabled(nullptr)
0417 {
0418 //     kDebug(11001) << ": ConfigDialog";
0419     
0420     setWindowTitle(i18nc("@title:window", "Configure Highscores"));
0421     setModal( true );
0422     
0423     QWidget *page = nullptr;
0424     QTabWidget *tab = nullptr;
0425     
0426     QVBoxLayout *layout = new QVBoxLayout;
0427     setLayout(layout);
0428     
0429     if ( internal->isWWHSAvailable() ) {
0430         tab = new QTabWidget(this);
0431         layout->addWidget(tab);
0432         page = new QWidget;
0433         tab->addTab(page, i18n("Main"));
0434     } 
0435     
0436     else {
0437         page = new QWidget(this);
0438         layout->addWidget(page);
0439     }
0440 
0441     QGridLayout *pageTop =
0442         new QGridLayout(page);
0443     //pageTop->setMargin(QApplication::style()->pixelMetric(QStyle::PM_DefaultLayoutSpacing));
0444     //pageTop->setSpacing(QApplication::style()->pixelMetric(QStyle::PM_DefaultLayoutSpacing));
0445     
0446     layout->addLayout(pageTop);
0447 
0448     QLabel *label = new QLabel(i18n("Nickname:"), page);
0449     pageTop->addWidget(label, 0, 0);
0450     _nickname = new QLineEdit(page);
0451     connect(_nickname, &QLineEdit::textChanged,
0452             this, &ConfigDialog::modifiedSlot);
0453     connect(_nickname, &QLineEdit::textChanged,
0454             this, &ConfigDialog::nickNameChanged);
0455 
0456     _nickname->setMaxLength(16);
0457     pageTop->addWidget(_nickname, 0, 1);
0458 
0459     label = new QLabel(i18n("Comment:"), page);
0460     pageTop->addWidget(label, 1, 0);
0461     _comment = new QLineEdit(page);
0462     connect(_comment, &QLineEdit::textChanged,
0463             this, &ConfigDialog::modifiedSlot);
0464     _comment->setMaxLength(50);
0465     pageTop->addWidget(_comment, 1, 1);
0466 
0467     if (tab) {
0468         _WWHEnabled
0469             = new QCheckBox(i18n("World-wide highscores enabled"), page);
0470         connect(_WWHEnabled, &QAbstractButton::toggled,
0471                 this, &ConfigDialog::modifiedSlot);
0472         pageTop->addWidget(_WWHEnabled, 2, 0, 1, 2 );
0473 
0474         // advanced tab
0475         QWidget *page = new QWidget;
0476         tab->addTab(page, i18n("Advanced"));
0477         QVBoxLayout *pageTop = new QVBoxLayout(page);
0478         //pageTop->setMargin(QApplication::style()->pixelMetric(QStyle::PM_DefaultChildMargin));
0479         //pageTop->setSpacing(QApplication::style()->pixelMetric(QStyle::PM_DefaultLayoutSpacing));
0480 
0481         QGroupBox *group = new QGroupBox(page);
0482         group->setTitle( i18n("Registration Data") );
0483         pageTop->addWidget(group);
0484         QGridLayout *groupLayout = new QGridLayout(group);
0485         //groupLayout->setSpacing(QApplication::style()->pixelMetric(QStyle::PM_DefaultLayoutSpacing));
0486 
0487         label = new QLabel(i18n("Nickname:"), group);
0488         groupLayout->addWidget(label, 0, 0);
0489         _registeredName = new QLineEdit(group);
0490         _registeredName->setReadOnly(true);
0491         groupLayout->addWidget(_registeredName, 0, 1);
0492 
0493         label = new QLabel(i18n("Key:"), group);
0494         groupLayout->addWidget(label, 1, 0);
0495         _key = new QLineEdit(group);
0496         _key->setReadOnly(true);
0497         groupLayout->addWidget(_key, 1, 1);
0498 
0499         KGuiItem gi = KStandardGuiItem::clear();
0500         gi.setText(i18n("Remove"));
0501         _removeButton = new QPushButton(group);
0502     KGuiItem::assign(_removeButton, gi);
0503     groupLayout->addWidget(_removeButton, 2, 0);
0504         connect(_removeButton, &QAbstractButton::clicked, this, &ConfigDialog::removeSlot);
0505     }
0506     
0507     buttonBox = new QDialogButtonBox(this);
0508     
0509     buttonBox->setStandardButtons(QDialogButtonBox::Ok | QDialogButtonBox::Apply | QDialogButtonBox::Cancel); 
0510     connect(buttonBox, &QDialogButtonBox::accepted, this, &QDialog::accept);
0511     connect(buttonBox, &QDialogButtonBox::rejected, this, &QDialog::reject);
0512     // TODO mapping for Apply button
0513     pageTop->addWidget(buttonBox);
0514 
0515     load();
0516     buttonBox->button(QDialogButtonBox::Ok)->setEnabled( !_nickname->text().isEmpty() );
0517     buttonBox->button(QDialogButtonBox::Apply)->setEnabled( false );
0518     
0519 }
0520 
0521 void ConfigDialog::nickNameChanged(const QString &text)
0522 {
0523     buttonBox->button(QDialogButtonBox::Ok)->setEnabled( !text.isEmpty() );
0524 }
0525 
0526 
0527 void ConfigDialog::modifiedSlot()
0528 {
0529     buttonBox->button(QDialogButtonBox::Apply)->setEnabled(true && !_nickname->text().isEmpty() );
0530 }
0531 
0532 void ConfigDialog::accept()
0533 {
0534     if ( save() ) {
0535         QDialog::accept();
0536         KSharedConfig::openConfig()->sync(); // safer
0537     }
0538 }
0539 
0540 void ConfigDialog::removeSlot()
0541 {
0542     KGuiItem gi = KStandardGuiItem::clear();
0543     gi.setText(i18n("Remove"));
0544     int res = KMessageBox::warningContinueCancel(this,
0545                                i18n("This will permanently remove your "
0546                                "registration key. You will not be able to use "
0547                                "the currently registered nickname anymore."),
0548                                QString(), gi);
0549     if ( res==KMessageBox::Continue ) {
0550         internal->playerInfos().removeKey();
0551         _registeredName->clear();
0552         _key->clear();
0553         _removeButton->setEnabled(false);
0554         _WWHEnabled->setChecked(false);
0555         modifiedSlot();
0556     }
0557 }
0558 
0559 void ConfigDialog::load()
0560 {
0561     internal->hsConfig().readCurrentConfig();
0562     const PlayerInfos &infos = internal->playerInfos();
0563     _nickname->setText(infos.isAnonymous() ? QString() : infos.name());
0564     _comment->setText(infos.comment());
0565     if (_WWHEnabled) {
0566         _WWHEnabled->setChecked(infos.isWWEnabled());
0567         if ( !infos.key().isEmpty() ) {
0568             _registeredName->setText(infos.registeredName());
0569             _registeredName->home(false);
0570             _key->setText(infos.key());
0571             _key->home(false);
0572         }
0573         _removeButton->setEnabled(!infos.key().isEmpty());
0574     }
0575 }
0576 
0577 bool ConfigDialog::save()
0578 {
0579     bool enabled = (_WWHEnabled ? _WWHEnabled->isChecked() : false);
0580 
0581     // do not bother the user with "nickname empty" if he has not
0582     // messed with nickname settings ...
0583     QString newName = _nickname->text();
0584     if ( newName.isEmpty() && !internal->playerInfos().isAnonymous()
0585          && !enabled ) return true;
0586 
0587     if ( newName.isEmpty() ) {
0588         KMessageBox::error(this, i18n("Please choose a non empty nickname."));
0589         return false;
0590     }
0591     if ( internal->playerInfos().isNameUsed(newName) ) {
0592         KMessageBox::error(this, i18n("Nickname already in use. Please "
0593                                       "choose another one"));
0594         return false;
0595     }
0596 
0597     int res =
0598         internal->modifySettings(newName, _comment->text(), enabled, this);
0599     if (res) {
0600         load(); // needed to update view when "apply" is clicked
0601         buttonBox->button(QDialogButtonBox::Apply)->setEnabled(false);
0602     }
0603     _saved = true;
0604     return res;
0605 }
0606 
0607 //-----------------------------------------------------------------------------
0608 AskNameDialog::AskNameDialog(QWidget *parent)
0609     : QDialog(parent)
0610 {
0611 //     kDebug(11001) << ": AskNameDialog";
0612 
0613     setWindowTitle(i18nc("@title:window", "Enter Your Nickname"));
0614 
0615     internal->hsConfig().readCurrentConfig();
0616     QVBoxLayout *top = new QVBoxLayout;
0617     //top->setMargin( QApplication::style()->pixelMetric(QStyle::PM_DefaultChildMargin) );
0618     //top->setSpacing( QApplication::style()->pixelMetric(QStyle::PM_DefaultLayoutSpacing) );
0619     setLayout(top);
0620         
0621     QLabel *label =
0622         new QLabel(i18n("Congratulations, you have won!"), this);
0623     top->addWidget(label);
0624 
0625     QHBoxLayout *hbox = new QHBoxLayout;
0626     top->addLayout(hbox);
0627     label = new QLabel(i18n("Enter your nickname:"), this);
0628     hbox->addWidget(label);
0629     _edit = new QLineEdit(this);
0630     _edit->setFocus();
0631     connect(_edit, &QLineEdit::textChanged, this, &AskNameDialog::nameChanged);
0632     hbox->addWidget(_edit);
0633 
0634     //top->addSpacing(QApplication::style()->pixelMetric(QStyle::PM_DefaultLayoutSpacing));
0635     _checkbox = new QCheckBox(i18n("Do not ask again."),  this);
0636     top->addWidget(_checkbox);
0637     
0638     _buttonBox = new QDialogButtonBox(this);
0639     
0640     _buttonBox->setStandardButtons(QDialogButtonBox::Ok | QDialogButtonBox::Cancel);
0641     connect(_buttonBox, &QDialogButtonBox::accepted, this, &QDialog::accept);
0642     connect(_buttonBox, &QDialogButtonBox::rejected, this, &QDialog::reject);
0643     top->addWidget(_buttonBox);
0644 
0645     nameChanged();
0646 }
0647 
0648 void AskNameDialog::nameChanged()
0649 {
0650     _buttonBox->button(QDialogButtonBox::Ok)->setEnabled( !name().isEmpty()
0651                       && !internal->playerInfos().isNameUsed(name())); 
0652 }
0653 
0654 } // namespace
0655 
0656 #include "moc_kexthighscore_gui.cpp"