summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--src/gui/kernel/qplatformdialoghelper.cpp24
-rw-r--r--src/gui/kernel/qplatformdialoghelper.h10
-rw-r--r--src/widgets/dialogs/qmessagebox.cpp98
-rw-r--r--src/widgets/dialogs/qmessagebox.h16
-rw-r--r--tests/auto/widgets/dialogs/qmessagebox/tst_qmessagebox.cpp17
5 files changed, 163 insertions, 2 deletions
diff --git a/src/gui/kernel/qplatformdialoghelper.cpp b/src/gui/kernel/qplatformdialoghelper.cpp
index 7038954ea0..c14c0f0142 100644
--- a/src/gui/kernel/qplatformdialoghelper.cpp
+++ b/src/gui/kernel/qplatformdialoghelper.cpp
@@ -778,6 +778,7 @@ public:
QPixmap iconPixmap;
QString checkBoxLabel;
Qt::CheckState checkBoxState = Qt::Unchecked;
+ QMessageDialogOptions::Options options;
};
QMessageDialogOptions::QMessageDialogOptions(QMessageDialogOptionsPrivate *dd)
@@ -924,6 +925,29 @@ Qt::CheckState QMessageDialogOptions::checkBoxState() const
return d->checkBoxState;
}
+void QMessageDialogOptions::setOption(QMessageDialogOptions::Option option, bool on)
+{
+ if (!(d->options & option) != !on)
+ setOptions(d->options ^ option);
+}
+
+bool QMessageDialogOptions::testOption(QMessageDialogOptions::Option option) const
+{
+ return d->options & option;
+}
+
+void QMessageDialogOptions::setOptions(QMessageDialogOptions::Options options)
+{
+ if (options != d->options)
+ d->options = options;
+}
+
+QMessageDialogOptions::Options QMessageDialogOptions::options() const
+{
+ return d->options;
+}
+
+
QPlatformDialogHelper::ButtonRole QPlatformDialogHelper::buttonRole(QPlatformDialogHelper::StandardButton button)
{
switch (button) {
diff --git a/src/gui/kernel/qplatformdialoghelper.h b/src/gui/kernel/qplatformdialoghelper.h
index 25543a70b8..fabc4985a3 100644
--- a/src/gui/kernel/qplatformdialoghelper.h
+++ b/src/gui/kernel/qplatformdialoghelper.h
@@ -403,6 +403,11 @@ protected:
~QMessageDialogOptions();
public:
+ // Keep in sync with QMessageBox Option
+ enum class Option : quint8 { DontUseNativeDialog = 0x00000001 };
+ Q_DECLARE_FLAGS(Options, Option);
+ Q_FLAG(Options);
+
// Keep in sync with QMessageBox::Icon
enum StandardIcon { NoIcon, Information, Warning, Critical, Question };
Q_ENUM(StandardIcon)
@@ -428,6 +433,11 @@ public:
void setDetailedText(const QString &text);
QString detailedText() const;
+ void setOption(Option option, bool on = true);
+ bool testOption(Option option) const;
+ void setOptions(Options options);
+ Options options() const;
+
void setStandardButtons(QPlatformDialogHelper::StandardButtons buttons);
QPlatformDialogHelper::StandardButtons standardButtons() const;
diff --git a/src/widgets/dialogs/qmessagebox.cpp b/src/widgets/dialogs/qmessagebox.cpp
index cb985ff145..58e846b16b 100644
--- a/src/widgets/dialogs/qmessagebox.cpp
+++ b/src/widgets/dialogs/qmessagebox.cpp
@@ -189,6 +189,7 @@ public:
void retranslateStrings();
void setVisible(bool visible) override;
+ bool canBeNativeDialog() const override;
static int showOldMessageBox(QWidget *parent, QMessageBox::Icon icon,
const QString &title, const QString &text,
@@ -770,6 +771,12 @@ void QMessageBoxPrivate::_q_clicked(QPlatformDialogHelper::StandardButton button
*/
/*!
+ \enum QMessageBox::Option
+ \since 6.6
+ \value DontUseNativeDialog Don't use the native message dialog.
+*/
+
+/*!
\fn void QMessageBox::buttonClicked(QAbstractButton *button)
This signal is emitted whenever a button is clicked inside the QMessageBox.
@@ -1225,6 +1232,78 @@ QCheckBox* QMessageBox::checkBox() const
}
/*!
+ \since 6.6
+ Sets the given \a option to be enabled if \a on is true; otherwise,
+ clears the given \a option.
+
+ Options (particularly the DontUseNativeDialogs option) should be set
+ before showing the dialog.
+
+ Setting options while the dialog is visible is not guaranteed to have
+ an immediate effect on the dialog.
+
+ Setting options after changing other properties may cause these
+ values to have no effect.
+
+ \sa options, testOption()
+*/
+void QMessageBox::setOption(QMessageBox::Option option, bool on)
+{
+ const QMessageBox::Options previousOptions = options();
+ if (!(previousOptions & option) != !on)
+ setOptions(previousOptions ^ option);
+}
+
+/*!
+ \since 6.6
+
+ Returns \c true if the given \a option is enabled; otherwise, returns
+ false.
+
+ \sa options, setOption()
+*/
+bool QMessageBox::testOption(QMessageBox::Option option) const
+{
+ Q_D(const QMessageBox);
+ return d->options->testOption(static_cast<QMessageDialogOptions::Option>(option));
+}
+
+void QMessageBox::setOptions(QMessageBox::Options options)
+{
+ Q_D(QMessageBox);
+
+ if (QMessageBox::options() == options)
+ return;
+
+ d->options->setOptions(QMessageDialogOptions::Option(int(options)));
+}
+
+QMessageBox::Options QMessageBox::options() const
+{
+ Q_D(const QMessageBox);
+ return QMessageBox::Options(int(d->options->options()));
+}
+
+/*!
+ \property QMessageBox::options
+ \brief options that affect the look and feel of the dialog
+ \since 6.6.
+
+ By default, these options are disabled.
+
+ The option DontUseNativeDialog should be set
+ before changing dialog properties or showing the dialog.
+
+ Setting options while the dialog is visible is not guaranteed to have
+ an immediate effect on the dialog.
+
+ Setting options after changing other properties may cause these
+ values to have no effect.
+
+ \sa setOption(), testOption()
+*/
+
+/*!
\property QMessageBox::text
\brief the message box text to be displayed.
@@ -2717,6 +2796,25 @@ static QPlatformDialogHelper::StandardButtons helperStandardButtons(QMessageBox
return buttons;
}
+bool QMessageBoxPrivate::canBeNativeDialog() const
+{
+ // Don't use Q_Q here! This function is called from ~QDialog,
+ // so Q_Q calling q_func() invokes undefined behavior (invalid cast in q_func()).
+ const QDialog * const q = static_cast<const QMessageBox*>(q_ptr);
+ if (nativeDialogInUse)
+ return true;
+ if (QCoreApplication::testAttribute(Qt::AA_DontUseNativeDialogs)
+ || q->testAttribute(Qt::WA_DontShowOnScreen)
+ || (options->options() & QMessageDialogOptions::Option::DontUseNativeDialog)) {
+ return false;
+ }
+
+ if (strcmp(QMessageBox::staticMetaObject.className(), q->metaObject()->className()) != 0)
+ return false;
+
+ return QDialogPrivate::canBeNativeDialog();
+}
+
void QMessageBoxPrivate::helperPrepareShow(QPlatformDialogHelper *)
{
Q_Q(QMessageBox);
diff --git a/src/widgets/dialogs/qmessagebox.h b/src/widgets/dialogs/qmessagebox.h
index cf8821bbd0..72f0840e80 100644
--- a/src/widgets/dialogs/qmessagebox.h
+++ b/src/widgets/dialogs/qmessagebox.h
@@ -31,8 +31,14 @@ class Q_WIDGETS_EXPORT QMessageBox : public QDialog
Q_PROPERTY(QString informativeText READ informativeText WRITE setInformativeText)
Q_PROPERTY(Qt::TextInteractionFlags textInteractionFlags READ textInteractionFlags
WRITE setTextInteractionFlags)
-
+ Q_PROPERTY(Options options READ options WRITE setOptions)
public:
+ // Keep in sync with MessageBoxOption in qplatformdialoghelper.h
+ enum class Option : quint8 {
+ DontUseNativeDialog = 0x00000001
+ };
+ Q_FLAG(Option)
+
enum Icon {
// keep this in sync with QMessageDialogOptions::StandardIcon
NoIcon = 0,
@@ -95,8 +101,9 @@ public:
#if QT_VERSION < QT_VERSION_CHECK(7, 0, 0)
typedef StandardButton Button;
#endif
-
+ Q_DECLARE_FLAGS(Options, Option)
Q_DECLARE_FLAGS(StandardButtons, StandardButton)
+
Q_FLAG(StandardButtons)
explicit QMessageBox(QWidget *parent = nullptr);
@@ -149,6 +156,11 @@ public:
void setCheckBox(QCheckBox *cb);
QCheckBox* checkBox() const;
+ void setOption(Option option, bool on = true);
+ bool testOption(Option option) const;
+ void setOptions(Options options);
+ Options options() const;
+
static StandardButton information(QWidget *parent, const QString &title,
const QString &text, StandardButtons buttons = Ok,
StandardButton defaultButton = NoButton);
diff --git a/tests/auto/widgets/dialogs/qmessagebox/tst_qmessagebox.cpp b/tests/auto/widgets/dialogs/qmessagebox/tst_qmessagebox.cpp
index 122170e91d..afdf18fedc 100644
--- a/tests/auto/widgets/dialogs/qmessagebox/tst_qmessagebox.cpp
+++ b/tests/auto/widgets/dialogs/qmessagebox/tst_qmessagebox.cpp
@@ -38,6 +38,9 @@ private slots:
void detailsButtonText();
void expandDetailsWithoutMoving();
+ void optionsEmptyByDefault();
+ void changeNativeOption();
+
#ifndef Q_OS_MAC
void shortcut();
#endif
@@ -584,6 +587,20 @@ void tst_QMessageBox::expandDetailsWithoutMoving() // QTBUG-32473
QCOMPARE(box.geometry().topLeft(), geom.topLeft());
}
+void tst_QMessageBox::optionsEmptyByDefault()
+{
+ QMessageBox b;
+ QCOMPARE(b.options(), QMessageBox::Options());
+ QVERIFY(!b.testOption(QMessageBox::Option::DontUseNativeDialog));
+}
+
+void tst_QMessageBox::changeNativeOption()
+{
+ QMessageBox b;
+ b.setOption(QMessageBox::Option::DontUseNativeDialog);
+ QCOMPARE(b.options(), QMessageBox::Options(QMessageBox::Option::DontUseNativeDialog));
+}
+
void tst_QMessageBox::incorrectDefaultButton()
{
ExecCloseHelper closeHelper;