QT_BEGIN_NAMESPACE
+#ifdef FOCUS_DEBUG
+void printFocusTree(QQuickItem *item, QQuickItem *scope, int depth)
+{
+ qWarning()
+ << QByteArray(depth, '\t').constData()
+ << (scope && QQuickItemPrivate::get(scope)->subFocusItem == item ? '*' : ' ')
+ << item->hasFocus()
+ << item->hasActiveFocus()
+ << item->isFocusScope()
+ << item;
+ foreach (QQuickItem *child, item->childItems()) {
+ printFocusTree(
+ child,
+ item->isFocusScope() || !scope ? item : scope,
+ item->isFocusScope() || !scope ? depth + 1 : depth);
+ }
+}
+#endif
+
static void QQuickItem_parentNotifier(QObject *o, intptr_t, QQmlNotifier **n)
{
QQuickItemPrivate *d = QQuickItemPrivate::get(static_cast<QQuickItem *>(o));
while (!scopeItem->isFocusScope() && scopeItem->parentItem())
scopeItem = scopeItem->parentItem();
- if (scopeItem->scopedFocusItem()) {
+ if (QQuickItemPrivate::get(scopeItem)->subFocusItem
+ || (!scopeItem->isFocusScope() && scopeItem->hasFocus())) {
+ if (scopeFocusedItem != this)
+ QQuickItemPrivate::get(scopeFocusedItem)->updateSubFocusItem(this, false);
QQuickItemPrivate::get(scopeFocusedItem)->focus = false;
emit scopeFocusedItem->focusChanged(false);
} else {
void addedToCanvas();
void changeParent();
void multipleFocusClears();
+ void focusSubItemInNonFocusScope();
+ void parentItemWithFocus();
void constructor();
void setParentItem();
QTRY_VERIFY(QGuiApplication::focusWindow() == view);
}
+void tst_qquickitem::focusSubItemInNonFocusScope()
+{
+ QQuickView *view = new QQuickView;
+ view->setSource(testFileUrl("focusSubItemInNonFocusScope.qml"));
+ view->show();
+ qApp->processEvents();
+
+ QQuickItem *dummyItem = view->rootObject()->findChild<QQuickItem *>("dummyItem");
+ QVERIFY(dummyItem);
+
+ QQuickItem *textInput = view->rootObject()->findChild<QQuickItem *>("textInput");
+ QVERIFY(textInput);
+
+ QVERIFY(dummyItem->hasFocus());
+ QVERIFY(!textInput->hasFocus());
+ QVERIFY(dummyItem->hasActiveFocus());
+
+ QVERIFY(QMetaObject::invokeMethod(textInput, "forceActiveFocus"));
+
+ QVERIFY(!dummyItem->hasFocus());
+ QVERIFY(textInput->hasFocus());
+ QVERIFY(textInput->hasActiveFocus());
+
+ delete view;
+}
+
+void tst_qquickitem::parentItemWithFocus()
+{
+ QQuickCanvas canvas;
+ ensureFocus(&canvas);
+ QTRY_VERIFY(QGuiApplication::focusWindow() == &canvas);
+ {
+ QQuickItem parent;
+ QQuickItem child;
+
+ FocusState focusState;
+ focusState << &parent << &child;
+ FVERIFY();
+
+ parent.setFocus(true);
+ child.setFocus(true);
+ focusState[&parent].set(true, false);
+ focusState[&child].set(true, false);
+ FVERIFY();
+
+ child.setParentItem(&parent);
+ focusState[&parent].set(true, false);
+ focusState[&child].set(false, false);
+ FVERIFY();
+
+ parent.setParentItem(canvas.rootItem());
+ focusState[&parent].set(true, true);
+ focusState[&child].set(false, false);
+ focusState.active(&parent);
+ FVERIFY();
+
+ child.forceActiveFocus();
+ focusState[&parent].set(false, false);
+ focusState[&child].set(true, true);
+ focusState.active(&child);
+ FVERIFY();
+ } {
+ QQuickItem parent;
+ QQuickItem child;
+ QQuickItem grandchild(&child);
+
+ FocusState focusState;
+ focusState << &parent << &child << &grandchild;
+ FVERIFY();
+
+ parent.setFocus(true);
+ grandchild.setFocus(true);
+ focusState[&parent].set(true, false);
+ focusState[&child].set(false, false);
+ focusState[&grandchild].set(true, false);
+ FVERIFY();
+
+ child.setParentItem(&parent);
+ focusState[&parent].set(true, false);
+ focusState[&child].set(false, false);
+ focusState[&grandchild].set(false, false);
+ FVERIFY();
+
+ parent.setParentItem(canvas.rootItem());
+ focusState[&parent].set(true, true);
+ focusState[&child].set(false, false);
+ focusState[&grandchild].set(false, false);
+ focusState.active(&parent);
+ FVERIFY();
+
+ grandchild.forceActiveFocus();
+ focusState[&parent].set(false, false);
+ focusState[&child].set(false, false);
+ focusState[&grandchild].set(true, true);
+ focusState.active(&grandchild);
+ FVERIFY();
+ }
+}
+
void tst_qquickitem::constructor()
{
QQuickItem *root = new QQuickItem;