diff options
author | Volker Hilsheimer <volker.hilsheimer@qt.io> | 2020-04-23 13:12:06 +0200 |
---|---|---|
committer | Volker Hilsheimer <volker.hilsheimer@qt.io> | 2020-04-23 16:19:07 +0200 |
commit | 23b998fa454ca021aa595f66d2e1964da4a119a4 (patch) | |
tree | 999ae9da36d4a16c5142985b8bb5f82b15fb671f /src/widgets/kernel/qwidget.cpp | |
parent | 574898c9ebb1c05797afa80747bde3b5836f8a85 (diff) |
QWidget: fix regression when changing focus proxy while it has focus
This follows up on commits 3e7463411e549100eee7abe2a8fae16fd965f8f6 and
947883141d9d8b3079a8a21981ad8a5ce3c4798e.
The changing of the pointer of QApplicationPrivate does not transfer
focus properly. It updates the pointer, but it doesn't deliver events
or update the widget hierarchy's focus chain. The result is that
multiple line edits might show a blinking cursor.
Instead, use QWidget::setFocus when the focus proxy has changed while
it had focus, and pass OtherFocusReason rather than NoFocusReason.
Add a basic test for QWidget::focusProxy, which exercises this code
path and verifies that pointers are consistent when focus changes as
a side effect of modifying the focusProxy.
Change-Id: I15a4d868bab2b590cfe4a1daa6a3c8cebc9c9ca2
Fixes: QTBUG-83720
Fixes: QTBUG-79707
Pick-to: 5.15
Reviewed-by: David Faure <david.faure@kdab.com>
Diffstat (limited to 'src/widgets/kernel/qwidget.cpp')
-rw-r--r-- | src/widgets/kernel/qwidget.cpp | 11 |
1 files changed, 5 insertions, 6 deletions
diff --git a/src/widgets/kernel/qwidget.cpp b/src/widgets/kernel/qwidget.cpp index 8afacb9dab..06080a0f42 100644 --- a/src/widgets/kernel/qwidget.cpp +++ b/src/widgets/kernel/qwidget.cpp @@ -6197,18 +6197,17 @@ void QWidget::setFocusProxy(QWidget * w) } } - QWidget *oldDeepestFocusProxy = d_func()->deepestFocusProxy(); + QWidget *oldDeepestFocusProxy = d->deepestFocusProxy(); if (!oldDeepestFocusProxy) oldDeepestFocusProxy = this; - const bool changingAppFocusWidget = (QApplicationPrivate::focus_widget == oldDeepestFocusProxy); + + const bool focusProxyHadFocus = (QApplicationPrivate::focus_widget == oldDeepestFocusProxy); d->createExtra(); d->extra->focus_proxy = w; - if (changingAppFocusWidget) { - QWidget *newDeepestFocusProxy = d_func()->deepestFocusProxy(); - QApplicationPrivate::setFocusWidget(newDeepestFocusProxy ? newDeepestFocusProxy : this, Qt::NoFocusReason); - } + if (focusProxyHadFocus) + setFocus(Qt::OtherFocusReason); } |