File indexing completed on 2024-05-12 16:39:55

0001 /* This file is part of the KDE project
0002    Copyright (C) 2011-2018 Jarosław Staniek <staniek@kde.org>
0003 
0004    This program is free software; you can redistribute it and/or
0005    modify it under the terms of the GNU Library General Public
0006    License as published by the Free Software Foundation; either
0007    version 2 of the License, or (at your option) any later version.
0008 
0009    This program is distributed in the hope that it will be useful,
0010    but WITHOUT ANY WARRANTY; without even the implied warranty of
0011    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
0012    Library General Public License for more details.
0013 
0014    You should have received a copy of the GNU Library General Public License
0015    along with this program; see the file COPYING.  If not, write to
0016    the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
0017  * Boston, MA 02110-1301, USA.
0018  */
0019 
0020 #include "KexiAssistantPage.h"
0021 
0022 #include "utils.h"
0023 #include "KexiTitleLabel.h"
0024 #include "KexiLinkWidget.h"
0025 #include "KexiLinkButton.h"
0026 #include "KexiCloseButton.h"
0027 
0028 #include <KexiIcon.h>
0029 
0030 #include <KAcceleratorManager>
0031 #include <KStandardGuiItem>
0032 #include <KLocalizedString>
0033 
0034 #include <QGridLayout>
0035 #include <QLineEdit>
0036 #include <QPointer>
0037 
0038 class Q_DECL_HIDDEN KexiAssistantPage::Private {
0039 public:
0040     explicit Private(KexiAssistantPage* q_) : q(q_), backButton(0), nextButton(0)
0041     {
0042     }
0043     void setButtonVisible(KexiLinkWidget** button, bool back, bool set,
0044                           int x, int y);
0045     QColor linkColor() const;
0046 
0047     QLineEdit *recentFocusLineEdit() { return qobject_cast<QLineEdit*>(recentFocusWidget); }
0048 
0049     KexiAssistantPage * const q;
0050     QGridLayout* mainLyr;
0051     KexiTitleLabel* titleLabel;
0052     QLabel* descriptionLabel;
0053     KexiLinkWidget* backButton;
0054     KexiLinkWidget* nextButton;
0055     KexiCloseButton* cancelButton;
0056     QPointer<QWidget> recentFocusWidget;
0057     int recentFocusLineEditSelectionStart = -1;
0058     int recentFocusLineEditSelectionLength = -1;
0059     int recentFocusLineEditCursorPosition = -1;
0060 };
0061 
0062 void KexiAssistantPage::Private::setButtonVisible(KexiLinkWidget** button,
0063                                                   bool back, /* or next */
0064                                                   bool set, int x, int y)
0065 {
0066     if (set) {
0067         if (*button) {
0068             (*button)->show();
0069         }
0070         else {
0071             if (back) {
0072                 *button = new KexiLinkWidget(
0073                     QLatin1String("KexiAssistantPage:back"),
0074                     KStandardGuiItem::back().plainText(), q);
0075                 (*button)->setFormat(
0076                     xi18nc("Back button arrow: back button in assistant (wizard)", "‹ %L"));
0077             }
0078             else {
0079                 *button = new KexiLinkWidget(
0080                     QLatin1String("KexiAssistantPage:next"),
0081                     xi18nc("Button text: Next page in assistant (wizard)", "Next"), q);
0082                 (*button)->setFormat(
0083                     xi18nc("Next button arrow: next button in assistant (wizard)", "%L ›"));
0084             }
0085             int space = (*button)->fontMetrics().height() / 2;
0086             Qt::Alignment align;
0087             if (back) {
0088                 (*button)->setContentsMargins(0, 0, space, 0);
0089                 align = Qt::AlignTop | Qt::AlignLeft;
0090             }
0091             else {
0092                 (*button)->setContentsMargins(space, 0, 0, 0);
0093                 align = Qt::AlignTop | Qt::AlignRight;
0094             }
0095             KAcceleratorManager::setNoAccel(*button);
0096             mainLyr->addWidget(*button, x, y, align);
0097             connect(*button, SIGNAL(linkActivated(QString)),
0098                     q, SLOT(slotLinkActivated(QString)));
0099         }
0100     }
0101     else {
0102         if (*button)
0103             (*button)->hide();
0104     }
0105 }
0106 
0107 // ----
0108 
0109 KexiAssistantPage::KexiAssistantPage(const QString& title, const QString& description, QWidget* parent)
0110  : QWidget(parent)
0111  , d(new Private(this))
0112 {
0113 /*0         [titleLabel]       [cancel]
0114   1  [back] [descriptionLabel]   [next]
0115   2         [contents]                 */
0116     d->mainLyr = new QGridLayout(this);
0117     d->mainLyr->setContentsMargins(0, 0, 0, 0);
0118     d->mainLyr->setColumnStretch(1, 1);
0119     d->mainLyr->setRowStretch(2, 1);
0120     d->titleLabel = new KexiTitleLabel(title);
0121     d->mainLyr->addWidget(d->titleLabel, 0, 1, Qt::AlignTop);
0122     d->descriptionLabel = new QLabel(description);
0123     int space = d->descriptionLabel->fontMetrics().height();
0124     d->descriptionLabel->setContentsMargins(2, 0, 0, space);
0125     d->descriptionLabel->setWordWrap(true);
0126     d->mainLyr->addWidget(d->descriptionLabel, 1, 1, Qt::AlignTop);
0127 
0128     d->cancelButton = new KexiCloseButton;
0129     connect(d->cancelButton, SIGNAL(clicked()), this, SLOT(slotCancel()));
0130     d->mainLyr->addWidget(d->cancelButton, 0, 2, Qt::AlignTop|Qt::AlignRight);
0131 }
0132 
0133 KexiAssistantPage::~KexiAssistantPage()
0134 {
0135     delete d;
0136 }
0137 
0138 void KexiAssistantPage::setDescription(const QString& text)
0139 {
0140     d->descriptionLabel->setText(text);
0141 }
0142 
0143 void KexiAssistantPage::setBackButtonVisible(bool set)
0144 {
0145     d->setButtonVisible(&d->backButton, true/*back*/, set, 1, 0);
0146 }
0147 
0148 void KexiAssistantPage::setNextButtonVisible(bool set)
0149 {
0150     d->setButtonVisible(&d->nextButton, false/*next*/, set, 1, 2);
0151 }
0152 
0153 void KexiAssistantPage::setContents(QWidget* widget)
0154 {
0155     widget->setContentsMargins(0, 0, 0, 0);
0156     d->mainLyr->addWidget(widget, 2, 1, 2, 2);
0157 }
0158 
0159 void KexiAssistantPage::setContents(QLayout* layout)
0160 {
0161     layout->setContentsMargins(0, 0, 0, 0);
0162     d->mainLyr->addLayout(layout, 2, 1);
0163 }
0164 
0165 void KexiAssistantPage::slotLinkActivated(const QString& link)
0166 {
0167     if (d->backButton && link == d->backButton->link()) {
0168         back();
0169     }
0170     else if (d->nextButton && link == d->nextButton->link()) {
0171         next();
0172     }
0173 }
0174 
0175 void KexiAssistantPage::slotCancel()
0176 {
0177     emit cancelledRequested(this);
0178     if (parentWidget()) {
0179         parentWidget()->deleteLater();
0180     }
0181 }
0182 
0183 KexiLinkWidget* KexiAssistantPage::backButton()
0184 {
0185     if (!d->backButton) {
0186         setBackButtonVisible(true);
0187         d->backButton->hide();
0188     }
0189     return d->backButton;
0190 }
0191 
0192 KexiLinkWidget* KexiAssistantPage::nextButton()
0193 {
0194     if (!d->nextButton) {
0195         setNextButtonVisible(true);
0196         d->nextButton->hide();
0197     }
0198     return d->nextButton;
0199 }
0200 
0201 void KexiAssistantPage::tryBack()
0202 {
0203     emit tryBackRequested(this);
0204 }
0205 
0206 void KexiAssistantPage::back()
0207 {
0208     emit backRequested(this);
0209 }
0210 
0211 void KexiAssistantPage::next()
0212 {
0213     emit nextRequested(this);
0214 }
0215 
0216 QWidget* KexiAssistantPage::recentFocusWidget() const
0217 {
0218     return d->recentFocusWidget;
0219 }
0220 
0221 void KexiAssistantPage::setRecentFocusWidget(QWidget* widget)
0222 {
0223     d->recentFocusWidget = widget;
0224     QLineEdit *edit = d->recentFocusLineEdit();
0225     d->recentFocusLineEditSelectionStart = edit ? edit->selectionStart() : -1;
0226     d->recentFocusLineEditSelectionLength = (edit && edit->hasSelectedText()) ? edit->selectedText().length() : -1;
0227     d->recentFocusLineEditCursorPosition = edit ? edit->cursorPosition() : -1;
0228 }
0229 
0230 void KexiAssistantPage::focusRecentFocusWidget()
0231 {
0232     if (!d->recentFocusWidget) {
0233         return;
0234     }
0235     d->recentFocusWidget->setFocus();
0236     QLineEdit *edit = d->recentFocusLineEdit();
0237     if (edit && d->recentFocusLineEditSelectionStart >= 0
0238         && d->recentFocusLineEditSelectionLength >= 0)
0239     {
0240         edit->setCursorPosition(d->recentFocusLineEditCursorPosition);
0241         edit->setSelection(d->recentFocusLineEditSelectionStart, d->recentFocusLineEditSelectionLength);
0242     }
0243 }
0244 
0245 QString KexiAssistantPage::title() const
0246 {
0247     return d->titleLabel->text();
0248 }
0249 
0250 QString KexiAssistantPage::description() const
0251 {
0252     return d->descriptionLabel->text();
0253 }
0254