From fa74a99c8e7476727f5c6bd0a417042896f9a07b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Tor=20Arne=20Vestb=C3=B8?= Date: Sun, 22 Oct 2023 16:22:27 +0200 Subject: [PATCH] QMessageBox: Do last minute setup in setVisible instead of showEvent The native message dialogs are shown in QMessageBox::setVisible, instead of plumbed via e.g. QWidgetPrivate::show_sys (which is not virtual). And we try to show the native dialog before we call the base class QDialog::setVisible(), where we end up sending the show event. As the native dialogs might rely on the last minute setup of adding an OK button or detecting the escape button, we need to do it in setVisible instead. We can not switch the order of showing the native dialogs after calling the base class setVisible (and getting showEvent), as we need to know whether the native dialog could be shown or not to decide whether to show the fallback widget dialog. The part from showEvent that added the detailsButton has been removed, as we're already doing that in setDetailsText(). Pick-to: 6.5 Change-Id: I23f1d87d542d9dadfd71924f8119c22720f4b276 Reviewed-by: Oliver Eftevaag (cherry picked from commit b0ddca18d73430771f52c034e3d5a1bb92363f64) Reviewed-by: Qt Cherry-pick Bot --- src/plugins/platforms/cocoa/qcocoamessagedialog.mm | 10 ---------- src/widgets/dialogs/qmessagebox.cpp | 11 +++++------ 2 files changed, 5 insertions(+), 16 deletions(-) diff --git a/src/plugins/platforms/cocoa/qcocoamessagedialog.mm b/src/plugins/platforms/cocoa/qcocoamessagedialog.mm index 56c3fceed25..5ea21e7b8af 100644 --- a/src/plugins/platforms/cocoa/qcocoamessagedialog.mm +++ b/src/plugins/platforms/cocoa/qcocoamessagedialog.mm @@ -182,16 +182,6 @@ bool QCocoaMessageDialog::show(Qt::WindowFlags windowFlags, Qt::WindowModality w for (auto customButton : customButtons) addButton(customButton.label, customButton.id, customButton.role); - - // QMessageDialog's logic for adding a fallback OK button if no other buttons - // are added depends on QMessageBox::showEvent(), which is too late when - // native dialogs are in use. To ensure there's always an OK button with a tag - // we recognize we add it explicitly here as a fallback. - if (!m_alert.buttons.count) { - addButton(platformTheme->standardButtonText(StandardButton::Ok), - StandardButton::Ok, ButtonRole::AcceptRole); - } - if (auto checkBoxLabel = options()->checkBoxLabel(); !checkBoxLabel.isNull()) { checkBoxLabel = QPlatformTheme::removeMnemonics(checkBoxLabel); m_alert.suppressionButton.title = checkBoxLabel.toNSString(); diff --git a/src/widgets/dialogs/qmessagebox.cpp b/src/widgets/dialogs/qmessagebox.cpp index efe846900db..596bc9968ae 100644 --- a/src/widgets/dialogs/qmessagebox.cpp +++ b/src/widgets/dialogs/qmessagebox.cpp @@ -1662,6 +1662,11 @@ void QMessageBoxPrivate::setVisible(bool visible) if (q->testAttribute(Qt::WA_WState_ExplicitShowHide) && q->testAttribute(Qt::WA_WState_Hidden) != visible) return; + // Last minute setup + if (autoAddOkButton) + q->addButton(QMessageBox::Ok); + detectEscapeButton(); + if (canBeNativeDialog()) setNativeDialogVisible(visible); @@ -1706,13 +1711,7 @@ QMessageBox::ButtonRole QMessageBox::buttonRole(QAbstractButton *button) const void QMessageBox::showEvent(QShowEvent *e) { Q_D(QMessageBox); - if (d->autoAddOkButton) { - addButton(Ok); - } - if (d->detailsButton) - addButton(d->detailsButton, QMessageBox::ActionRole); d->clickedButton = nullptr; - d->detectEscapeButton(); d->updateSize(); #if QT_CONFIG(accessibility)