summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--src/gui/graphicsview/qgraphicsitem.cpp2
-rw-r--r--src/gui/graphicsview/qgraphicsitem_p.h68
-rw-r--r--src/gui/graphicsview/qgraphicsscenebsptreeindex.cpp68
-rw-r--r--src/gui/graphicsview/qgraphicsscenebsptreeindex_p.h2
-rw-r--r--tests/auto/qgraphicsitem/tst_qgraphicsitem.cpp43
5 files changed, 113 insertions, 70 deletions
diff --git a/src/gui/graphicsview/qgraphicsitem.cpp b/src/gui/graphicsview/qgraphicsitem.cpp
index 1ebee45..4b2ff52 100644
--- a/src/gui/graphicsview/qgraphicsitem.cpp
+++ b/src/gui/graphicsview/qgraphicsitem.cpp
@@ -4737,7 +4737,7 @@ bool QGraphicsItem::isObscuredBy(const QGraphicsItem *item) const
{
if (!item)
return false;
- return QGraphicsSceneBspTreeIndexPrivate::closestItemFirst_withoutCache(item, this)
+ return qt_closestItemFirst(item, this)
&& qt_QGraphicsItem_isObscured(this, item, boundingRect());
}
diff --git a/src/gui/graphicsview/qgraphicsitem_p.h b/src/gui/graphicsview/qgraphicsitem_p.h
index 6550362..38145ac 100644
--- a/src/gui/graphicsview/qgraphicsitem_p.h
+++ b/src/gui/graphicsview/qgraphicsitem_p.h
@@ -623,6 +623,72 @@ public:
/*!
+ Returns true if \a item1 is on top of \a item2.
+ The items dont need to be siblings.
+
+ \internal
+*/
+inline bool qt_closestItemFirst(const QGraphicsItem *item1, const QGraphicsItem *item2)
+{
+ // Siblings? Just check their z-values.
+ const QGraphicsItemPrivate *d1 = item1->d_ptr.data();
+ const QGraphicsItemPrivate *d2 = item2->d_ptr.data();
+ if (d1->parent == d2->parent)
+ return qt_closestLeaf(item1, item2);
+
+ // Find common ancestor, and each item's ancestor closest to the common
+ // ancestor.
+ int item1Depth = d1->depth();
+ int item2Depth = d2->depth();
+ const QGraphicsItem *p = item1;
+ const QGraphicsItem *t1 = item1;
+ while (item1Depth > item2Depth && (p = p->d_ptr->parent)) {
+ if (p == item2) {
+ // item2 is one of item1's ancestors; item1 is on top
+ return !(t1->d_ptr->flags & QGraphicsItem::ItemStacksBehindParent);
+ }
+ t1 = p;
+ --item1Depth;
+ }
+ p = item2;
+ const QGraphicsItem *t2 = item2;
+ while (item2Depth > item1Depth && (p = p->d_ptr->parent)) {
+ if (p == item1) {
+ // item1 is one of item2's ancestors; item1 is not on top
+ return (t2->d_ptr->flags & QGraphicsItem::ItemStacksBehindParent);
+ }
+ t2 = p;
+ --item2Depth;
+ }
+
+ // item1Ancestor is now at the same level as item2Ancestor, but not the same.
+ const QGraphicsItem *a1 = t1;
+ const QGraphicsItem *a2 = t2;
+ while (a1) {
+ const QGraphicsItem *p1 = a1;
+ const QGraphicsItem *p2 = a2;
+ a1 = a1->parentItem();
+ a2 = a2->parentItem();
+ if (a1 && a1 == a2)
+ return qt_closestLeaf(p1, p2);
+ }
+
+ // No common ancestor? Then just compare the items' toplevels directly.
+ return qt_closestLeaf(t1->topLevelItem(), t2->topLevelItem());
+}
+
+/*!
+ Returns true if \a item2 is on top of \a item1.
+ The items dont need to be siblings.
+
+ \internal
+*/
+inline bool qt_closestItemLast(const QGraphicsItem *item1, const QGraphicsItem *item2)
+{
+ return qt_closestItemFirst(item2, item1);
+}
+
+/*!
\internal
*/
inline bool qt_closestLeaf(const QGraphicsItem *item1, const QGraphicsItem *item2)
@@ -642,7 +708,7 @@ inline bool qt_closestLeaf(const QGraphicsItem *item1, const QGraphicsItem *item
/*!
\internal
*/
-static inline bool qt_notclosestLeaf(const QGraphicsItem *item1, const QGraphicsItem *item2)
+inline bool qt_notclosestLeaf(const QGraphicsItem *item1, const QGraphicsItem *item2)
{ return qt_closestLeaf(item2, item1); }
/*
diff --git a/src/gui/graphicsview/qgraphicsscenebsptreeindex.cpp b/src/gui/graphicsview/qgraphicsscenebsptreeindex.cpp
index e21183a..47ae3f1 100644
--- a/src/gui/graphicsview/qgraphicsscenebsptreeindex.cpp
+++ b/src/gui/graphicsview/qgraphicsscenebsptreeindex.cpp
@@ -405,70 +405,6 @@ QList<QGraphicsItem *> QGraphicsSceneBspTreeIndexPrivate::estimateItems(const QR
}
/*!
- Returns true if \a item1 is on top of \a item2.
-
- \internal
-*/
-bool QGraphicsSceneBspTreeIndexPrivate::closestItemFirst_withoutCache(const QGraphicsItem *item1, const QGraphicsItem *item2)
-{
- // Siblings? Just check their z-values.
- const QGraphicsItemPrivate *d1 = item1->d_ptr.data();
- const QGraphicsItemPrivate *d2 = item2->d_ptr.data();
- if (d1->parent == d2->parent)
- return qt_closestLeaf(item1, item2);
-
- // Find common ancestor, and each item's ancestor closest to the common
- // ancestor.
- int item1Depth = d1->depth();
- int item2Depth = d2->depth();
- const QGraphicsItem *p = item1;
- const QGraphicsItem *t1 = item1;
- while (item1Depth > item2Depth && (p = p->d_ptr->parent)) {
- if (p == item2) {
- // item2 is one of item1's ancestors; item1 is on top
- return !(t1->d_ptr->flags & QGraphicsItem::ItemStacksBehindParent);
- }
- t1 = p;
- --item1Depth;
- }
- p = item2;
- const QGraphicsItem *t2 = item2;
- while (item2Depth > item1Depth && (p = p->d_ptr->parent)) {
- if (p == item1) {
- // item1 is one of item2's ancestors; item1 is not on top
- return (t2->d_ptr->flags & QGraphicsItem::ItemStacksBehindParent);
- }
- t2 = p;
- --item2Depth;
- }
-
- // item1Ancestor is now at the same level as item2Ancestor, but not the same.
- const QGraphicsItem *a1 = t1;
- const QGraphicsItem *a2 = t2;
- while (a1) {
- const QGraphicsItem *p1 = a1;
- const QGraphicsItem *p2 = a2;
- a1 = a1->parentItem();
- a2 = a2->parentItem();
- if (a1 && a1 == a2)
- return qt_closestLeaf(p1, p2);
- }
-
- // No common ancestor? Then just compare the items' toplevels directly.
- return qt_closestLeaf(t1->topLevelItem(), t2->topLevelItem());
-}
-
-/*!
- Returns true if \a item2 is on top of \a item1.
-
- \internal
-*/
-bool QGraphicsSceneBspTreeIndexPrivate::closestItemLast_withoutCache(const QGraphicsItem *item1, const QGraphicsItem *item2)
-{
- return closestItemFirst_withoutCache(item2, item1);
-}
-
-/*!
Sort a list of \a itemList in a specific \a order and use the cache if requested.
\internal
@@ -495,9 +431,9 @@ void QGraphicsSceneBspTreeIndexPrivate::sortItems(QList<QGraphicsItem *> *itemLi
}
} else {
if (order == Qt::DescendingOrder) {
- qSort(itemList->begin(), itemList->end(), closestItemFirst_withoutCache);
+ qSort(itemList->begin(), itemList->end(), qt_closestItemFirst);
} else if (order == Qt::AscendingOrder) {
- qSort(itemList->begin(), itemList->end(), closestItemLast_withoutCache);
+ qSort(itemList->begin(), itemList->end(), qt_closestItemLast);
}
}
}
diff --git a/src/gui/graphicsview/qgraphicsscenebsptreeindex_p.h b/src/gui/graphicsview/qgraphicsscenebsptreeindex_p.h
index 0a86bb7..c130190 100644
--- a/src/gui/graphicsview/qgraphicsscenebsptreeindex_p.h
+++ b/src/gui/graphicsview/qgraphicsscenebsptreeindex_p.h
@@ -145,8 +145,6 @@ public:
QList<QGraphicsItem *> estimateItems(const QRectF &, Qt::SortOrder, bool b = false);
static void climbTree(QGraphicsItem *item, int *stackingOrder);
- static bool closestItemFirst_withoutCache(const QGraphicsItem *item1, const QGraphicsItem *item2);
- static bool closestItemLast_withoutCache(const QGraphicsItem *item1, const QGraphicsItem *item2);
static inline bool closestItemFirst_withCache(const QGraphicsItem *item1, const QGraphicsItem *item2)
{
diff --git a/tests/auto/qgraphicsitem/tst_qgraphicsitem.cpp b/tests/auto/qgraphicsitem/tst_qgraphicsitem.cpp
index 0a6f60e..dcad8e1 100644
--- a/tests/auto/qgraphicsitem/tst_qgraphicsitem.cpp
+++ b/tests/auto/qgraphicsitem/tst_qgraphicsitem.cpp
@@ -398,6 +398,7 @@ private slots:
void modality_mouseGrabber();
void modality_clickFocus();
void modality_keyEvents();
+ void itemIsInFront();
// task specific tests below me
void task141694_textItemEnsureVisible();
@@ -9541,5 +9542,47 @@ void tst_QGraphicsItem::modality_keyEvents()
QCOMPARE(rect1Spy.counts[QEvent::KeyRelease], 0);
}
+void tst_QGraphicsItem::itemIsInFront()
+{
+ QGraphicsScene scene;
+ QGraphicsRectItem *rect1 = new QGraphicsRectItem;
+ rect1->setData(0, "rect1");
+ scene.addItem(rect1);
+
+ QGraphicsRectItem *rect1child1 = new QGraphicsRectItem(rect1);
+ rect1child1->setZValue(1);
+ rect1child1->setData(0, "rect1child1");
+
+ QGraphicsRectItem *rect1child2 = new QGraphicsRectItem(rect1);
+ rect1child2->setParentItem(rect1);
+ rect1child2->setData(0, "rect1child2");
+
+ QGraphicsRectItem *rect1child1_1 = new QGraphicsRectItem(rect1child1);
+ rect1child1_1->setData(0, "rect1child1_1");
+
+ QGraphicsRectItem *rect1child1_2 = new QGraphicsRectItem(rect1child1);
+ rect1child1_2->setFlag(QGraphicsItem::ItemStacksBehindParent);
+ rect1child1_2->setData(0, "rect1child1_2");
+
+ QGraphicsRectItem *rect2 = new QGraphicsRectItem;
+ rect2->setData(0, "rect2");
+ scene.addItem(rect2);
+
+ QGraphicsRectItem *rect2child1 = new QGraphicsRectItem(rect2);
+ rect2child1->setData(0, "rect2child1");
+
+ QCOMPARE(qt_closestItemFirst(rect1, rect1), false);
+ QCOMPARE(qt_closestItemFirst(rect1, rect2), false);
+ QCOMPARE(qt_closestItemFirst(rect1child1, rect2child1), false);
+ QCOMPARE(qt_closestItemFirst(rect1child1, rect1child2), true);
+ QCOMPARE(qt_closestItemFirst(rect1child1_1, rect1child2), true);
+ QCOMPARE(qt_closestItemFirst(rect1child1_1, rect1child1), true);
+ QCOMPARE(qt_closestItemFirst(rect1child1_2, rect1child2), true);
+ QCOMPARE(qt_closestItemFirst(rect1child1_2, rect1child1), false);
+ QCOMPARE(qt_closestItemFirst(rect1child1_2, rect1), true);
+ QCOMPARE(qt_closestItemFirst(rect1child1_2, rect2), false);
+ QCOMPARE(qt_closestItemFirst(rect1child1_2, rect2child1), false);
+}
+
QTEST_MAIN(tst_QGraphicsItem)
#include "tst_qgraphicsitem.moc"