1 /**************************************************************************** |
1 /**************************************************************************** |
2 ** |
2 ** |
3 ** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies). |
3 ** Copyright (C) 2010 Nokia Corporation and/or its subsidiary(-ies). |
4 ** All rights reserved. |
4 ** All rights reserved. |
5 ** Contact: Nokia Corporation (qt-info@nokia.com) |
5 ** Contact: Nokia Corporation (qt-info@nokia.com) |
6 ** |
6 ** |
7 ** This file is part of the QtGui module of the Qt Toolkit. |
7 ** This file is part of the QtGui module of the Qt Toolkit. |
8 ** |
8 ** |
68 #if !defined(QT_NO_GRAPHICSVIEW) || (QT_EDITION & QT_MODULE_GRAPHICSVIEW) != QT_MODULE_GRAPHICSVIEW |
68 #if !defined(QT_NO_GRAPHICSVIEW) || (QT_EDITION & QT_MODULE_GRAPHICSVIEW) != QT_MODULE_GRAPHICSVIEW |
69 |
69 |
70 QT_BEGIN_NAMESPACE |
70 QT_BEGIN_NAMESPACE |
71 |
71 |
72 class QGraphicsItemPrivate; |
72 class QGraphicsItemPrivate; |
|
73 |
|
74 #ifndef QDECLARATIVELISTPROPERTY |
|
75 #define QDECLARATIVELISTPROPERTY |
|
76 template<typename T> |
|
77 struct QDeclarativeListProperty { |
|
78 typedef void (*AppendFunction)(QDeclarativeListProperty<T> *, T*); |
|
79 typedef int (*CountFunction)(QDeclarativeListProperty<T> *); |
|
80 typedef T *(*AtFunction)(QDeclarativeListProperty<T> *, int); |
|
81 typedef void (*ClearFunction)(QDeclarativeListProperty<T> *); |
|
82 |
|
83 QDeclarativeListProperty() |
|
84 : object(0), data(0), append(0), count(0), at(0), clear(0), dummy1(0), dummy2(0) {} |
|
85 QDeclarativeListProperty(QObject *o, QList<T *> &list) |
|
86 : object(o), data(&list), append(qlist_append), count(qlist_count), at(qlist_at), |
|
87 clear(qlist_clear), dummy1(0), dummy2(0) {} |
|
88 QDeclarativeListProperty(QObject *o, void *d, AppendFunction a, CountFunction c = 0, AtFunction t = 0, |
|
89 ClearFunction r = 0) |
|
90 : object(o), data(d), append(a), count(c), at(t), clear(r), dummy1(0), dummy2(0) {} |
|
91 |
|
92 bool operator==(const QDeclarativeListProperty &o) const { |
|
93 return object == o.object && |
|
94 data == o.data && |
|
95 append == o.append && |
|
96 count == o.count && |
|
97 at == o.at && |
|
98 clear == o.clear; |
|
99 } |
|
100 |
|
101 QObject *object; |
|
102 void *data; |
|
103 |
|
104 AppendFunction append; |
|
105 |
|
106 CountFunction count; |
|
107 AtFunction at; |
|
108 |
|
109 ClearFunction clear; |
|
110 |
|
111 void *dummy1; |
|
112 void *dummy2; |
|
113 |
|
114 private: |
|
115 static void qlist_append(QDeclarativeListProperty *p, T *v) { |
|
116 ((QList<T *> *)p->data)->append(v); |
|
117 } |
|
118 static int qlist_count(QDeclarativeListProperty *p) { |
|
119 return ((QList<T *> *)p->data)->count(); |
|
120 } |
|
121 static T *qlist_at(QDeclarativeListProperty *p, int idx) { |
|
122 return ((QList<T *> *)p->data)->at(idx); |
|
123 } |
|
124 static void qlist_clear(QDeclarativeListProperty *p) { |
|
125 return ((QList<T *> *)p->data)->clear(); |
|
126 } |
|
127 }; |
|
128 #endif |
73 |
129 |
74 class QGraphicsItemCache |
130 class QGraphicsItemCache |
75 { |
131 { |
76 public: |
132 public: |
77 QGraphicsItemCache() : allExposed(false) { } |
133 QGraphicsItemCache() : allExposed(false) { } |
151 isWidget(0), |
207 isWidget(0), |
152 dirty(0), |
208 dirty(0), |
153 dirtyChildren(0), |
209 dirtyChildren(0), |
154 localCollisionHack(0), |
210 localCollisionHack(0), |
155 inSetPosHelper(0), |
211 inSetPosHelper(0), |
156 needSortChildren(1), // ### can be 0 by default? |
212 needSortChildren(0), |
157 allChildrenDirty(0), |
213 allChildrenDirty(0), |
158 fullUpdatePending(0), |
214 fullUpdatePending(0), |
159 flags(0), |
215 flags(0), |
160 dirtyChildrenBoundingRect(1), |
216 dirtyChildrenBoundingRect(1), |
161 paintedViewBoundingRectsNeedRepaint(0), |
217 paintedViewBoundingRectsNeedRepaint(0), |
176 wantsActive(0), |
232 wantsActive(0), |
177 holesInSiblingIndex(0), |
233 holesInSiblingIndex(0), |
178 sequentialOrdering(1), |
234 sequentialOrdering(1), |
179 updateDueToGraphicsEffect(0), |
235 updateDueToGraphicsEffect(0), |
180 scenePosDescendants(0), |
236 scenePosDescendants(0), |
|
237 pendingPolish(0), |
|
238 mayHaveChildWithGraphicsEffect(0), |
181 globalStackingOrder(-1), |
239 globalStackingOrder(-1), |
182 q_ptr(0) |
240 q_ptr(0) |
183 { |
241 { |
184 } |
242 } |
185 |
243 |
193 static QGraphicsItemPrivate *get(QGraphicsItem *item) |
251 static QGraphicsItemPrivate *get(QGraphicsItem *item) |
194 { |
252 { |
195 return item->d_ptr.data(); |
253 return item->d_ptr.data(); |
196 } |
254 } |
197 |
255 |
|
256 void updateChildWithGraphicsEffectFlagRecursively(); |
198 void updateAncestorFlag(QGraphicsItem::GraphicsItemFlag childFlag, |
257 void updateAncestorFlag(QGraphicsItem::GraphicsItemFlag childFlag, |
199 AncestorFlag flag = NoFlag, bool enabled = false, bool root = true); |
258 AncestorFlag flag = NoFlag, bool enabled = false, bool root = true); |
|
259 void updateAncestorFlags(); |
200 void setIsMemberOfGroup(bool enabled); |
260 void setIsMemberOfGroup(bool enabled); |
201 void remapItemPos(QEvent *event, QGraphicsItem *item); |
261 void remapItemPos(QEvent *event, QGraphicsItem *item); |
202 QPointF genericMapFromScene(const QPointF &pos, const QWidget *viewport) const; |
262 QPointF genericMapFromScene(const QPointF &pos, const QWidget *viewport) const; |
203 inline bool itemIsUntransformable() const |
263 inline bool itemIsUntransformable() const |
204 { |
264 { |
221 void setEnabledHelper(bool newEnabled, bool explicitly, bool update = true); |
281 void setEnabledHelper(bool newEnabled, bool explicitly, bool update = true); |
222 bool discardUpdateRequest(bool ignoreVisibleBit = false, |
282 bool discardUpdateRequest(bool ignoreVisibleBit = false, |
223 bool ignoreDirtyBit = false, bool ignoreOpacity = false) const; |
283 bool ignoreDirtyBit = false, bool ignoreOpacity = false) const; |
224 int depth() const; |
284 int depth() const; |
225 #ifndef QT_NO_GRAPHICSEFFECT |
285 #ifndef QT_NO_GRAPHICSEFFECT |
226 void invalidateGraphicsEffectsRecursively(); |
286 enum InvalidateReason { |
|
287 OpacityChanged |
|
288 }; |
|
289 void invalidateParentGraphicsEffectsRecursively(); |
|
290 void invalidateChildGraphicsEffectsRecursively(InvalidateReason reason); |
227 #endif //QT_NO_GRAPHICSEFFECT |
291 #endif //QT_NO_GRAPHICSEFFECT |
228 void invalidateDepthRecursively(); |
292 void invalidateDepthRecursively(); |
229 void resolveDepth(); |
293 void resolveDepth(); |
230 void addChild(QGraphicsItem *child); |
294 void addChild(QGraphicsItem *child); |
231 void removeChild(QGraphicsItem *child); |
295 void removeChild(QGraphicsItem *child); |
232 void setParentItemHelper(QGraphicsItem *parent); |
296 QDeclarativeListProperty<QGraphicsObject> childrenList(); |
|
297 void setParentItemHelper(QGraphicsItem *parent, const QVariant *newParentVariant, |
|
298 const QVariant *thisPointerVariant); |
233 void childrenBoundingRectHelper(QTransform *x, QRectF *rect); |
299 void childrenBoundingRectHelper(QTransform *x, QRectF *rect); |
234 void initStyleOption(QStyleOptionGraphicsItem *option, const QTransform &worldTransform, |
300 void initStyleOption(QStyleOptionGraphicsItem *option, const QTransform &worldTransform, |
235 const QRegion &exposedRegion, bool allItems = false) const; |
301 const QRegion &exposedRegion, bool allItems = false) const; |
236 QRectF effectiveBoundingRect() const; |
302 QRectF effectiveBoundingRect() const; |
237 QRectF sceneEffectiveBoundingRect() const; |
303 QRectF sceneEffectiveBoundingRect() const; |
347 myFlags = parentFlags; |
413 myFlags = parentFlags; |
348 } |
414 } |
349 return o; |
415 return o; |
350 } |
416 } |
351 |
417 |
|
418 inline bool isOpacityNull() const |
|
419 { return (opacity < qreal(0.001)); } |
|
420 |
|
421 static inline bool isOpacityNull(qreal opacity) |
|
422 { return (opacity < qreal(0.001)); } |
|
423 |
352 inline bool isFullyTransparent() const |
424 inline bool isFullyTransparent() const |
353 { |
425 { |
354 if (opacity < 0.001) |
426 if (isOpacityNull()) |
355 return true; |
427 return true; |
356 if (!parent) |
428 if (!parent) |
357 return false; |
429 return false; |
358 |
430 |
359 return calcEffectiveOpacity() < 0.001; |
431 return isOpacityNull(calcEffectiveOpacity()); |
360 } |
432 } |
361 |
433 |
362 inline qreal effectiveOpacity() const { |
434 inline qreal effectiveOpacity() const { |
363 if (!parent || !opacity) |
435 if (!parent || !opacity) |
364 return opacity; |
436 return opacity; |
395 inline bool isInvisible() const |
467 inline bool isInvisible() const |
396 { |
468 { |
397 return !visible || (childrenCombineOpacity() && isFullyTransparent()); |
469 return !visible || (childrenCombineOpacity() && isFullyTransparent()); |
398 } |
470 } |
399 |
471 |
400 void setFocusHelper(Qt::FocusReason focusReason, bool climb); |
472 inline void markParentDirty(bool updateBoundingRect = false); |
|
473 |
|
474 void setFocusHelper(Qt::FocusReason focusReason, bool climb, bool focusFromShow); |
|
475 void clearFocusHelper(bool giveFocusToParent); |
401 void setSubFocus(QGraphicsItem *rootItem = 0); |
476 void setSubFocus(QGraphicsItem *rootItem = 0); |
402 void clearSubFocus(QGraphicsItem *rootItem = 0); |
477 void clearSubFocus(QGraphicsItem *rootItem = 0); |
403 void resetFocusProxy(); |
478 void resetFocusProxy(); |
404 virtual void subFocusItemChange(); |
479 virtual void subFocusItemChange(); |
405 |
480 |
406 inline QTransform transformToParent() const; |
481 inline QTransform transformToParent() const; |
407 inline void ensureSortedChildren(); |
482 inline void ensureSortedChildren(); |
|
483 static void append(QDeclarativeListProperty<QGraphicsObject> *list, QGraphicsObject *item); |
408 static inline bool insertionOrder(QGraphicsItem *a, QGraphicsItem *b); |
484 static inline bool insertionOrder(QGraphicsItem *a, QGraphicsItem *b); |
409 void ensureSequentialSiblingIndex(); |
485 void ensureSequentialSiblingIndex(); |
410 inline void sendScenePosChange(); |
486 inline void sendScenePosChange(); |
411 virtual void siblingOrderChange(); |
487 virtual void siblingOrderChange(); |
|
488 |
|
489 // Private Properties |
|
490 virtual qreal width() const; |
|
491 virtual void setWidth(qreal); |
|
492 virtual void resetWidth(); |
|
493 |
|
494 virtual qreal height() const; |
|
495 virtual void setHeight(qreal); |
|
496 virtual void resetHeight(); |
412 |
497 |
413 QRectF childrenBoundingRect; |
498 QRectF childrenBoundingRect; |
414 QRectF needsRepaint; |
499 QRectF needsRepaint; |
415 QMap<QWidget *, QRect> paintedViewBoundingRects; |
500 QMap<QWidget *, QRect> paintedViewBoundingRects; |
416 QPointF pos; |
501 QPointF pos; |
482 quint32 wantsActive : 1; |
567 quint32 wantsActive : 1; |
483 quint32 holesInSiblingIndex : 1; |
568 quint32 holesInSiblingIndex : 1; |
484 quint32 sequentialOrdering : 1; |
569 quint32 sequentialOrdering : 1; |
485 quint32 updateDueToGraphicsEffect : 1; |
570 quint32 updateDueToGraphicsEffect : 1; |
486 quint32 scenePosDescendants : 1; |
571 quint32 scenePosDescendants : 1; |
|
572 quint32 pendingPolish : 1; |
|
573 quint32 mayHaveChildWithGraphicsEffect : 1; |
487 |
574 |
488 // Optional stacking order |
575 // Optional stacking order |
489 int globalStackingOrder; |
576 int globalStackingOrder; |
490 QGraphicsItem *q_ptr; |
577 QGraphicsItem *q_ptr; |
491 }; |
578 }; |
607 QRectF boundingRect(Qt::CoordinateSystem system) const; |
694 QRectF boundingRect(Qt::CoordinateSystem system) const; |
608 void draw(QPainter *); |
695 void draw(QPainter *); |
609 QPixmap pixmap(Qt::CoordinateSystem system, |
696 QPixmap pixmap(Qt::CoordinateSystem system, |
610 QPoint *offset, |
697 QPoint *offset, |
611 QGraphicsEffect::PixmapPadMode mode) const; |
698 QGraphicsEffect::PixmapPadMode mode) const; |
|
699 QRect paddedEffectRect(Qt::CoordinateSystem system, QGraphicsEffect::PixmapPadMode mode, const QRectF &sourceRect, bool *unpadded = 0) const; |
612 |
700 |
613 QGraphicsItem *item; |
701 QGraphicsItem *item; |
614 QGraphicsItemPaintInfo *info; |
702 QGraphicsItemPaintInfo *info; |
615 QTransform lastEffectTransform; |
703 QTransform lastEffectTransform; |
616 }; |
704 }; |
718 \internal |
806 \internal |
719 */ |
807 */ |
720 inline void QGraphicsItemPrivate::ensureSortedChildren() |
808 inline void QGraphicsItemPrivate::ensureSortedChildren() |
721 { |
809 { |
722 if (needSortChildren) { |
810 if (needSortChildren) { |
723 qSort(children.begin(), children.end(), qt_notclosestLeaf); |
|
724 needSortChildren = 0; |
811 needSortChildren = 0; |
725 sequentialOrdering = 1; |
812 sequentialOrdering = 1; |
|
813 if (children.isEmpty()) |
|
814 return; |
|
815 qSort(children.begin(), children.end(), qt_notclosestLeaf); |
726 for (int i = 0; i < children.size(); ++i) { |
816 for (int i = 0; i < children.size(); ++i) { |
727 if (children[i]->d_ptr->siblingIndex != i) { |
817 if (children.at(i)->d_ptr->siblingIndex != i) { |
728 sequentialOrdering = 0; |
818 sequentialOrdering = 0; |
729 break; |
819 break; |
730 } |
820 } |
731 } |
821 } |
732 } |
822 } |
738 inline bool QGraphicsItemPrivate::insertionOrder(QGraphicsItem *a, QGraphicsItem *b) |
828 inline bool QGraphicsItemPrivate::insertionOrder(QGraphicsItem *a, QGraphicsItem *b) |
739 { |
829 { |
740 return a->d_ptr->siblingIndex < b->d_ptr->siblingIndex; |
830 return a->d_ptr->siblingIndex < b->d_ptr->siblingIndex; |
741 } |
831 } |
742 |
832 |
|
833 /*! |
|
834 \internal |
|
835 */ |
|
836 inline void QGraphicsItemPrivate::markParentDirty(bool updateBoundingRect) |
|
837 { |
|
838 QGraphicsItemPrivate *parentp = this; |
|
839 while (parentp->parent) { |
|
840 parentp = parentp->parent->d_ptr.data(); |
|
841 parentp->dirtyChildren = 1; |
|
842 |
|
843 if (updateBoundingRect) { |
|
844 parentp->dirtyChildrenBoundingRect = 1; |
|
845 // ### Only do this if the parent's effect applies to the entire subtree. |
|
846 parentp->notifyBoundingRectChanged = 1; |
|
847 } |
|
848 #ifndef QT_NO_GRAPHICSEFFECT |
|
849 if (parentp->graphicsEffect) { |
|
850 if (updateBoundingRect) { |
|
851 parentp->notifyInvalidated = 1; |
|
852 static_cast<QGraphicsItemEffectSourcePrivate *>(parentp->graphicsEffect->d_func() |
|
853 ->source->d_func())->invalidateCache(); |
|
854 } |
|
855 if (parentp->graphicsEffect->isEnabled()) { |
|
856 parentp->dirty = 1; |
|
857 parentp->fullUpdatePending = 1; |
|
858 } |
|
859 } |
|
860 #endif |
|
861 } |
|
862 } |
|
863 |
743 QT_END_NAMESPACE |
864 QT_END_NAMESPACE |
744 |
865 |
745 #endif // QT_NO_GRAPHICSVIEW |
866 #endif // QT_NO_GRAPHICSVIEW |
746 |
867 |
747 #endif |
868 #endif |