Send the LanguageChange event to all top level windows, not just widgets

By sending it to all top level windows it will make it possible for
non widget based controls to listen for this event if it cares about it
so it can handle translation updates as appropriate.

Task-number: QTBUG-78141
Task-number: QTBUG-82020
Change-Id: I8f35cdcccd81a199ff780c3f4f3d2c663480d638
Reviewed-by: Mitch Curtis <mitch.curtis@qt.io>
bb10
Andy Shaw 2020-02-13 15:33:00 +01:00
parent 274b6f3c13
commit 9029c55864
5 changed files with 60 additions and 1 deletions

View File

@ -1882,6 +1882,10 @@ bool QGuiApplication::event(QEvent *e)
{
if(e->type() == QEvent::LanguageChange) {
setLayoutDirection(qt_detectRTLLanguage()?Qt::RightToLeft:Qt::LeftToRight);
for (auto *topLevelWindow : QGuiApplication::topLevelWindows()) {
if (topLevelWindow->flags() != Qt::Desktop)
postEvent(topLevelWindow, new QEvent(QEvent::LanguageChange));
}
} else if (e->type() == QEvent::Quit) {
// Close open windows. This is done in order to deliver de-expose
// events while the event loop is still running.

View File

@ -1904,9 +1904,12 @@ bool QApplication::event(QEvent *e)
}
if(e->type() == QEvent::LanguageChange) {
// QGuiApplication::event does not account for the cases where
// there is a top level widget without a window handle. So they
// need to have the event posted here
const QWidgetList list = topLevelWidgets();
for (auto *w : list) {
if (!(w->windowType() == Qt::Desktop))
if (!w->windowHandle() && (w->windowType() != Qt::Desktop))
postEvent(w, new QEvent(QEvent::LanguageChange));
}
}

Binary file not shown.

View File

@ -3,5 +3,6 @@
<file>geometry.dat</file>
<file>geometry-maximized.dat</file>
<file>geometry-fullscreen.dat</file>
<file>hellotr_la.qm</file>
</qresource>
</RCC>

View File

@ -410,6 +410,7 @@ private slots:
void closeWithChildWindow();
void winIdAfterClose();
void receivesLanguageChangeEvent();
private:
bool ensureScreenSize(int width, int height);
@ -11360,5 +11361,55 @@ void tst_QWidget::winIdAfterClose()
delete spy;
}
class LanguageChangeEventWidget : public QWidget
{
public:
LanguageChangeEventWidget(QWidget *parent = nullptr) : QWidget(parent) {}
int languageChangeCount = 0;
protected:
bool event(QEvent *e) override
{
if (e->type() == QEvent::LanguageChange)
languageChangeCount++;
return QWidget::event(e);
}
};
class LanguageChangeEventWindow : public QWindow
{
public:
LanguageChangeEventWindow(QWindow *parent = nullptr) : QWindow(parent) {}
int languageChangeCount = 0;
protected:
bool event(QEvent *e) override
{
if (e->type() == QEvent::LanguageChange)
languageChangeCount++;
return QWindow::event(e);
}
};
void tst_QWidget::receivesLanguageChangeEvent()
{
// Confirm that any QWindow or QWidget only gets a single
// LanguageChange event when a translator is installed
LanguageChangeEventWidget topLevel;
auto childWidget = new LanguageChangeEventWidget(&topLevel);
topLevel.show();
QVERIFY(QTest::qWaitForWindowExposed(&topLevel));
LanguageChangeEventWindow ww;
ww.show();
QVERIFY(QTest::qWaitForWindowExposed(&ww));
LanguageChangeEventWidget topLevelNotShown;
QTranslator t;
QVERIFY(t.load("hellotr_la.qm", ":/"));
QVERIFY(qApp->installTranslator(&t));
QCoreApplication::sendPostedEvents(0, QEvent::LanguageChange);
QCOMPARE(topLevel.languageChangeCount, 1);
QCOMPARE(topLevelNotShown.languageChangeCount, 1);
QCOMPARE(childWidget->languageChangeCount, 1);
QCOMPARE(ww.languageChangeCount, 1);
}
QTEST_MAIN(tst_QWidget)
#include "tst_qwidget.moc"