From b10912ba731144e8c41cbfa35fb1553ad04b2b88 Mon Sep 17 00:00:00 2001 From: Mitch Curtis Date: Mon, 3 Feb 2020 12:20:08 +0100 Subject: DialogButtonBox: don't change button text that has been explicitly set If a custom button is declared in a DialogButtonBox, qsTr() will take care of translation, and so we shouldn't touch it. Amends c18c7bd7f9596e5ad3d13876a91203e1ceba2544. Change-Id: I06221002cf850882f5318cf0a3ed86da35274d0c Fixes: QTBUG-81796 Reviewed-by: Andy Shaw --- src/quicktemplates2/qquickdialogbuttonbox.cpp | 7 +- .../data/dialogButtonBoxWithCustomButtons.qml | 75 ++++++++++++++++++++++ tests/auto/translation/tst_translation.cpp | 40 ++++++++++++ 3 files changed, 120 insertions(+), 2 deletions(-) create mode 100644 tests/auto/translation/data/dialogButtonBoxWithCustomButtons.qml diff --git a/src/quicktemplates2/qquickdialogbuttonbox.cpp b/src/quicktemplates2/qquickdialogbuttonbox.cpp index 33b720ed..d448aeed 100644 --- a/src/quicktemplates2/qquickdialogbuttonbox.cpp +++ b/src/quicktemplates2/qquickdialogbuttonbox.cpp @@ -455,8 +455,11 @@ void QQuickDialogButtonBoxPrivate::updateLanguage() qmlAttachedPropertiesObject(button, true)); const auto boxAttachedPrivate = QQuickDialogButtonBoxAttachedPrivate::get(attached); const QPlatformDialogHelper::StandardButton standardButton = boxAttachedPrivate->standardButton; - const QString buttonText = QGuiApplicationPrivate::platformTheme()->standardButtonText(standardButton); - button->setText(QPlatformTheme::removeMnemonics(buttonText)); + // The button might be a custom one with explicitly specified text, so we shouldn't change it in that case. + if (standardButton != QPlatformDialogHelper::NoButton) { + const QString buttonText = QGuiApplicationPrivate::platformTheme()->standardButtonText(standardButton); + button->setText(QPlatformTheme::removeMnemonics(buttonText)); + } } --i; } diff --git a/tests/auto/translation/data/dialogButtonBoxWithCustomButtons.qml b/tests/auto/translation/data/dialogButtonBoxWithCustomButtons.qml new file mode 100644 index 00000000..6f046cf1 --- /dev/null +++ b/tests/auto/translation/data/dialogButtonBoxWithCustomButtons.qml @@ -0,0 +1,75 @@ +/**************************************************************************** +** +** Copyright (C) 2020 The Qt Company Ltd. +** Contact: https://www.qt.io/licensing/ +** +** This file is part of the test suite of the Qt Toolkit. +** +** $QT_BEGIN_LICENSE:BSD$ +** Commercial License Usage +** Licensees holding valid commercial Qt licenses may use this file in +** accordance with the commercial license agreement provided with the +** Software or, alternatively, in accordance with the terms contained in +** a written agreement between you and The Qt Company. For licensing terms +** and conditions see https://www.qt.io/terms-conditions. For further +** information use the contact form at https://www.qt.io/contact-us. +** +** BSD License Usage +** Alternatively, you may use this file under the terms of the BSD license +** as follows: +** +** "Redistribution and use in source and binary forms, with or without +** modification, are permitted provided that the following conditions are +** met: +** * Redistributions of source code must retain the above copyright +** notice, this list of conditions and the following disclaimer. +** * Redistributions in binary form must reproduce the above copyright +** notice, this list of conditions and the following disclaimer in +** the documentation and/or other materials provided with the +** distribution. +** * Neither the name of The Qt Company Ltd nor the names of its +** contributors may be used to endorse or promote products derived +** from this software without specific prior written permission. +** +** +** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS +** "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT +** LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR +** A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT +** OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, +** SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT +** LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +** OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE." +** +** $QT_END_LICENSE$ +** +****************************************************************************/ + +import QtQuick 2.14 +import QtQuick.Controls 2.14 + +Item { + property Dialog dialog: Dialog { + width: 300 + height: 300 + visible: true + + footer: DialogButtonBox { + Button { + objectName: "okButton" + text: qsTr("OK") + + DialogButtonBox.buttonRole: DialogButtonBox.AcceptRole + } + Button { + objectName: "cancelButton" + text: qsTr("Cancel") + + DialogButtonBox.buttonRole: DialogButtonBox.RejectRole + } + } + } +} diff --git a/tests/auto/translation/tst_translation.cpp b/tests/auto/translation/tst_translation.cpp index 9cbca915..992c30a2 100644 --- a/tests/auto/translation/tst_translation.cpp +++ b/tests/auto/translation/tst_translation.cpp @@ -53,6 +53,7 @@ class tst_translation : public QQmlDataTest private slots: void dialogButtonBox(); + void dialogButtonBoxWithCustomButtons(); }; void tst_translation::dialogButtonBox() @@ -95,6 +96,45 @@ void tst_translation::dialogButtonBox() QCOMPARE(discardButton->text(), translatedDiscardText); } +// Test that custom buttons with explicitly specified text +// do not have that text overwritten on language changes. +void tst_translation::dialogButtonBoxWithCustomButtons() +{ + // This is just a way of simulating the translator going out of scope + // after the QML has been loaded. + QScopedPointer translator(new QTranslator); + // Doesn't matter which language it is, as we won't be using it anyway. + QVERIFY(translator->load(":/i18n/qtbase_fr.qm")); + QVERIFY(qApp->installTranslator(translator.data())); + + QQuickView view(testFileUrl("dialogButtonBoxWithCustomButtons.qml")); + if (view.status() != QQuickView::Ready) + QFAIL("Failed to load QML file"); + view.show(); + QVERIFY(QTest::qWaitForWindowActive(&view)); + + QQuickDialog *dialog = view.rootObject()->property("dialog").value(); + QVERIFY(dialog); + + QQuickDialogButtonBox *dialogButtonBox = qobject_cast(dialog->footer()); + QVERIFY(dialogButtonBox); + + auto okButton = dialogButtonBox->findChild("okButton"); + QVERIFY(okButton); + QCOMPARE(okButton->text(), QLatin1String("OK")); + + QQuickAbstractButton *cancelButton = dialogButtonBox->findChild("cancelButton"); + QVERIFY(cancelButton); + QCOMPARE(cancelButton->text(), QLatin1String("Cancel")); + + // Delete the translator and hence cause a LanguageChange event, + // but _without_ calling QQmlEngine::retranslate(), which would + // restore the original bindings and hence not reproduce the issue. + translator.reset(); + QCOMPARE(okButton->text(), QLatin1String("OK")); + QCOMPARE(cancelButton->text(), QLatin1String("Cancel")); +} + QTEST_MAIN(tst_translation) #include "tst_translation.moc" -- cgit v1.2.3