| Index: Source/core/rendering/RenderObject.h
|
| diff --git a/Source/core/rendering/RenderObject.h b/Source/core/rendering/RenderObject.h
|
| index 1975ed16046eecbe6ed469f16e300cd38c25f069..7c9717008de3519e17991f67362e203be307240d 100644
|
| --- a/Source/core/rendering/RenderObject.h
|
| +++ b/Source/core/rendering/RenderObject.h
|
| @@ -250,6 +250,29 @@ public:
|
| renderer->assertRendererLaidOut();
|
| }
|
|
|
| + void assertRendererClearedPaintInvalidationState() const
|
| + {
|
| +#ifndef NDEBUG
|
| + if (paintInvalidationStateIsDirty()) {
|
| + showRenderTreeForThis();
|
| + ASSERT_NOT_REACHED();
|
| + }
|
| +#endif
|
| + }
|
| +
|
| + void assertSubtreeClearedPaintInvalidationState() const
|
| + {
|
| + for (const RenderObject* renderer = this; renderer; renderer = renderer->nextInPreOrder()) {
|
| + renderer->assertRendererClearedPaintInvalidationState();
|
| +
|
| + // Currently we skip some SVG containers for performance (see RenderSVGModelObject::invalidateTreeAfterLayout)
|
| + // so we just skip the underlying subtree. This is not strictly the condition in the previous function but
|
| + // it makes little sense to cover SVG subtrees if we know they are skipped anyway.
|
| + if (renderer->isSVGContainer())
|
| + return;
|
| + }
|
| + }
|
| +
|
| #endif
|
|
|
| bool skipInvalidationWhenLaidOutChildren() const;
|
| @@ -1002,11 +1025,24 @@ public:
|
| void setPreviousPositionFromPaintInvalidationContainer(const LayoutPoint& location) { m_previousPositionFromPaintInvalidationContainer = location; }
|
|
|
| bool shouldDoFullPaintInvalidation() const { return m_bitfields.shouldDoFullPaintInvalidation(); }
|
| - void setShouldDoFullPaintInvalidation(bool b) { m_bitfields.setShouldDoFullPaintInvalidation(b); }
|
| + void setShouldDoFullPaintInvalidation(bool b, MarkingBehavior markBehavior = MarkContainingBlockChain)
|
| + {
|
| + m_bitfields.setShouldDoFullPaintInvalidation(b);
|
| +
|
| + if (markBehavior == MarkContainingBlockChain && b)
|
| + markContainingBlockChainForPaintInvalidation();
|
| + }
|
| +
|
| bool shouldInvalidateOverflowForPaint() const { return m_bitfields.shouldInvalidateOverflowForPaint(); }
|
|
|
| bool shouldDoFullPaintInvalidationIfSelfPaintingLayer() const { return m_bitfields.shouldDoFullPaintInvalidationIfSelfPaintingLayer(); }
|
| - void setShouldDoFullPaintInvalidationIfSelfPaintingLayer(bool b) { m_bitfields.setShouldDoFullPaintInvalidationIfSelfPaintingLayer(b); }
|
| + void setShouldDoFullPaintInvalidationIfSelfPaintingLayer(bool b)
|
| + {
|
| + m_bitfields.setShouldDoFullPaintInvalidationIfSelfPaintingLayer(b);
|
| +
|
| + if (b)
|
| + markContainingBlockChainForPaintInvalidation();
|
| + }
|
|
|
| bool onlyNeededPositionedMovementLayout() const { return m_bitfields.onlyNeededPositionedMovementLayout(); }
|
| void setOnlyNeededPositionedMovementLayout(bool b) { m_bitfields.setOnlyNeededPositionedMovementLayout(b); }
|
| @@ -1015,17 +1051,17 @@ public:
|
|
|
| // layoutDidGetCalled indicates whether this render object was re-laid-out
|
| // since the last call to setLayoutDidGetCalled(false) on this object.
|
| - bool layoutDidGetCalled() { return m_bitfields.layoutDidGetCalled(); }
|
| + bool layoutDidGetCalled() const { return m_bitfields.layoutDidGetCalled(); }
|
| void setLayoutDidGetCalled(bool b) { m_bitfields.setLayoutDidGetCalled(b); }
|
|
|
| - bool mayNeedPaintInvalidation() { return m_bitfields.mayNeedPaintInvalidation(); }
|
| + bool mayNeedPaintInvalidation() const { return m_bitfields.mayNeedPaintInvalidation(); }
|
| void setMayNeedPaintInvalidation(bool b)
|
| {
|
| m_bitfields.setMayNeedPaintInvalidation(b);
|
|
|
| // Make sure our parent is marked as needing invalidation.
|
| - if (b && parent() && !parent()->mayNeedPaintInvalidation())
|
| - parent()->setMayNeedPaintInvalidation(b);
|
| + if (b)
|
| + markContainingBlockChainForPaintInvalidation();
|
| }
|
|
|
| bool neededLayoutBecauseOfChildren() const { return m_bitfields.neededLayoutBecauseOfChildren(); }
|
| @@ -1033,7 +1069,7 @@ public:
|
|
|
| bool shouldCheckForPaintInvalidation()
|
| {
|
| - return layoutDidGetCalled() || mayNeedPaintInvalidation();
|
| + return layoutDidGetCalled() || mayNeedPaintInvalidation() || shouldDoFullPaintInvalidation() || shouldDoFullPaintInvalidationIfSelfPaintingLayer();
|
| }
|
|
|
| bool supportsLayoutStateCachedOffsets() const { return !hasColumns() && !hasTransform() && !hasReflection() && !style()->isFlippedBlocksWritingMode(); }
|
| @@ -1119,9 +1155,21 @@ private:
|
|
|
| #if ENABLE(ASSERT)
|
| void checkBlockPositionedObjectsNeedLayout();
|
| +
|
| + bool paintInvalidationStateIsDirty() const
|
| + {
|
| + return layoutDidGetCalled() || shouldDoFullPaintInvalidation() || shouldDoFullPaintInvalidationIfSelfPaintingLayer()
|
| + || onlyNeededPositionedMovementLayout() || neededLayoutBecauseOfChildren() || mayNeedPaintInvalidation();
|
| + }
|
| #endif
|
| const char* invalidationReasonToString(InvalidationReason) const;
|
|
|
| + void markContainingBlockChainForPaintInvalidation()
|
| + {
|
| + for (RenderObject* container = this->container(); container && !container->shouldCheckForPaintInvalidation(); container = container->container())
|
| + container->setMayNeedPaintInvalidation(true);
|
| + }
|
| +
|
| static bool isAllowedToModifyRenderTreeStructure(Document&);
|
|
|
| RefPtr<RenderStyle> m_style;
|
|
|