Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(30)

Side by Side Diff: Source/core/rendering/RenderLayer.cpp

Issue 206283003: Avoid tree walks when computing RenderLayer::scrollParent (Closed) Base URL: svn://svn.chromium.org/blink/trunk
Patch Set: . Created 6 years, 9 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
1 /* 1 /*
2 * Copyright (C) 2006, 2007, 2008, 2009, 2010, 2011, 2012 Apple Inc. All rights reserved. 2 * Copyright (C) 2006, 2007, 2008, 2009, 2010, 2011, 2012 Apple Inc. All rights reserved.
3 * 3 *
4 * Portions are Copyright (C) 1998 Netscape Communications Corporation. 4 * Portions are Copyright (C) 1998 Netscape Communications Corporation.
5 * 5 *
6 * Other contributors: 6 * Other contributors:
7 * Robert O'Callahan <roc+@cs.cmu.edu> 7 * Robert O'Callahan <roc+@cs.cmu.edu>
8 * David Baron <dbaron@fas.harvard.edu> 8 * David Baron <dbaron@fas.harvard.edu>
9 * Christian Biesinger <cbiesinger@web.de> 9 * Christian Biesinger <cbiesinger@web.de>
10 * Randall Jesup <rjesup@wgate.com> 10 * Randall Jesup <rjesup@wgate.com>
(...skipping 1115 matching lines...) Expand 10 before | Expand all | Expand 10 after
1126 return const_cast<RenderLayer*>(this); 1126 return const_cast<RenderLayer*>(this);
1127 1127
1128 for (const RenderLayer* curr = compositingContainer(); curr; curr = curr->co mpositingContainer()) { 1128 for (const RenderLayer* curr = compositingContainer(); curr; curr = curr->co mpositingContainer()) {
1129 if (curr->compositingState() == PaintsIntoOwnBacking || curr->compositin gState() == PaintsIntoGroupedBacking) 1129 if (curr->compositingState() == PaintsIntoOwnBacking || curr->compositin gState() == PaintsIntoGroupedBacking)
1130 return const_cast<RenderLayer*>(curr); 1130 return const_cast<RenderLayer*>(curr);
1131 } 1131 }
1132 1132
1133 return 0; 1133 return 0;
1134 } 1134 }
1135 1135
1136 void RenderLayer::clearAncestorDependentPropertyCache()
1137 {
1138 ASSERT(isInCompositingUpdate());
1139 m_ancestorDependentPropertyCache.clear();
1140 }
1141
1142 void RenderLayer::ensureAncestorDependentPropertyCache() const
1143 {
1144 ASSERT(isInCompositingUpdate());
1145 m_ancestorDependentPropertyCache = adoptPtr(new AncestorDependentPropertyCac he());
abarth-chromium 2014/03/20 21:36:45 Should we just return if the cache already exists?
Ian Vollick 2014/03/20 21:57:00 Done.
1146 }
1147
1136 RenderLayer* RenderLayer::ancestorCompositedScrollingLayer() const 1148 RenderLayer* RenderLayer::ancestorCompositedScrollingLayer() const
1137 { 1149 {
1138 ASSERT(isAllowedToQueryCompositingState());
1139
1140 if (!renderer()->acceleratedCompositingForOverflowScrollEnabled()) 1150 if (!renderer()->acceleratedCompositingForOverflowScrollEnabled())
1141 return 0; 1151 return 0;
1142 1152
1153 ASSERT(isInCompositingUpdate() || !m_ancestorDependentPropertyCache);
1154
1155 if (m_ancestorDependentPropertyCache && m_ancestorDependentPropertyCache->co ntainingBlock)
1156 return m_ancestorDependentPropertyCache->ancestorCompositedScrollingLaye r;
1157
1143 RenderObject* containingBlock = renderer()->containingBlock(); 1158 RenderObject* containingBlock = renderer()->containingBlock();
1144 if (!containingBlock) 1159 if (!containingBlock)
1145 return 0; 1160 return 0;
1146 1161
1147 for (RenderLayer* ancestorLayer = containingBlock->enclosingLayer(); ancesto rLayer; ancestorLayer = ancestorLayer->parent()) { 1162 if (isInCompositingUpdate()) {
1148 if (ancestorLayer->needsCompositedScrolling()) 1163 ensureAncestorDependentPropertyCache();
1149 return ancestorLayer; 1164 m_ancestorDependentPropertyCache->containingBlock = containingBlock;
1150 } 1165 }
1151 1166
1152 return 0; 1167 RenderLayer* ancestorCompositedScrollingLayer = 0;
1168 for (RenderLayer* ancestorLayer = containingBlock->enclosingLayer(); ancesto rLayer; ancestorLayer = ancestorLayer->parent()) {
1169 if (ancestorLayer->needsCompositedScrolling()) {
1170 ancestorCompositedScrollingLayer = ancestorLayer;
1171 break;
1172 }
1173 }
1174
1175 if (m_ancestorDependentPropertyCache)
1176 m_ancestorDependentPropertyCache->ancestorCompositedScrollingLayer = anc estorCompositedScrollingLayer;
1177 return ancestorCompositedScrollingLayer;
1153 } 1178 }
1154 1179
1155 RenderLayer* RenderLayer::ancestorScrollingLayer() const 1180 RenderLayer* RenderLayer::ancestorScrollingLayer() const
1156 { 1181 {
1157 RenderObject* containingBlock = renderer()->containingBlock(); 1182 RenderObject* containingBlock = renderer()->containingBlock();
1158 if (!containingBlock) 1183 if (!containingBlock)
1159 return 0; 1184 return 0;
1160 1185
1161 for (RenderLayer* ancestorLayer = containingBlock->enclosingLayer(); ancesto rLayer; ancestorLayer = ancestorLayer->parent()) { 1186 for (RenderLayer* ancestorLayer = containingBlock->enclosingLayer(); ancesto rLayer; ancestorLayer = ancestorLayer->parent()) {
1162 if (ancestorLayer->scrollsOverflow()) 1187 if (ancestorLayer->scrollsOverflow())
(...skipping 507 matching lines...) Expand 10 before | Expand all | Expand 10 after
1670 RenderLayer* RenderLayer::scrollParent() const 1695 RenderLayer* RenderLayer::scrollParent() const
1671 { 1696 {
1672 if (!renderer()->compositorDrivenAcceleratedScrollingEnabled()) 1697 if (!renderer()->compositorDrivenAcceleratedScrollingEnabled())
1673 return 0; 1698 return 0;
1674 1699
1675 // Normal flow elements will be parented under the main scrolling layer, so 1700 // Normal flow elements will be parented under the main scrolling layer, so
1676 // we don't need a scroll parent/child relationship to get them to scroll. 1701 // we don't need a scroll parent/child relationship to get them to scroll.
1677 if (stackingNode()->isNormalFlowOnly()) 1702 if (stackingNode()->isNormalFlowOnly())
1678 return 0; 1703 return 0;
1679 1704
1705 // We should never have an ancestor dependent property cache outside of the
1706 // compositing update phase.
1707 ASSERT(isInCompositingUpdate() || !m_ancestorDependentPropertyCache);
1708
1680 // A layer scrolls with its containing block. So to find the overflow scroll ing layer 1709 // A layer scrolls with its containing block. So to find the overflow scroll ing layer
1681 // that we scroll with respect to, we must ascend the layer tree until we re ach the 1710 // that we scroll with respect to, we must ascend the layer tree until we re ach the
1682 // first overflow scrolling div at or above our containing block. I will ref er to this 1711 // first overflow scrolling div at or above our containing block. I will ref er to this
1683 // layer as our 'scrolling ancestor'. 1712 // layer as our 'scrolling ancestor'.
1684 // 1713 //
1685 // Now, if we reside in a normal flow list, then we will naturally scroll wi th our scrolling 1714 // Now, if we reside in a normal flow list, then we will naturally scroll wi th our scrolling
1686 // ancestor, and we need not be composited. If, on the other hand, we reside in a z-order 1715 // ancestor, and we need not be composited. If, on the other hand, we reside in a z-order
1687 // list, and on our walk upwards to our scrolling ancestor we find no layer that is a stacking 1716 // list, and on our walk upwards to our scrolling ancestor we find no layer that is a stacking
1688 // context, then we know that in the stacking tree, we will not be in the su btree rooted at 1717 // context, then we know that in the stacking tree, we will not be in the su btree rooted at
1689 // our scrolling ancestor, and we will therefore not scroll with it. In this case, we must 1718 // our scrolling ancestor, and we will therefore not scroll with it. In this case, we must
1690 // be a composited layer since the compositor will need to take special meas ures to ensure 1719 // be a composited layer since the compositor will need to take special meas ures to ensure
1691 // that we scroll with our scrolling ancestor and it cannot do this if we do not promote. 1720 // that we scroll with our scrolling ancestor and it cannot do this if we do not promote.
1721 if (m_ancestorDependentPropertyCache && m_ancestorDependentPropertyCache->co ntainingBlock)
abarth-chromium 2014/03/20 21:36:45 Why is checking for containingBlock correct here?
Ian Vollick 2014/03/20 21:57:00 Oof. It isn't! It was only correct if you call scr
1722 return m_ancestorDependentPropertyCache->scrollParent;
1723
1692 RenderLayer* scrollParent = ancestorCompositedScrollingLayer(); 1724 RenderLayer* scrollParent = ancestorCompositedScrollingLayer();
1693
1694 if (!scrollParent || scrollParent->stackingNode()->isStackingContainer()) 1725 if (!scrollParent || scrollParent->stackingNode()->isStackingContainer())
1695 return 0; 1726 return 0;
1696 1727
1697 // If we hit a stacking context on our way up to the ancestor scrolling laye r, it will already 1728 // If we hit a stacking context on our way up to the ancestor scrolling laye r, it will already
1698 // be composited due to an overflow scrolling parent, so we don't need to. 1729 // be composited due to an overflow scrolling parent, so we don't need to.
1699 for (RenderLayer* ancestor = parent(); ancestor && ancestor != scrollParent; ancestor = ancestor->parent()) { 1730 for (RenderLayer* ancestor = parent(); ancestor && ancestor != scrollParent; ancestor = ancestor->parent()) {
1700 if (ancestor->stackingNode()->isStackingContainer()) 1731 if (ancestor->stackingNode()->isStackingContainer())
1701 return 0; 1732 return 0;
1733 if (!isInCompositingUpdate())
1734 continue;
1735 if (AncestorDependentPropertyCache* ancestorCache = ancestor->m_ancestor DependentPropertyCache.get()) {
1736 if (ancestorCache->ancestorCompositedScrollingLayer == scrollParent) {
1737 scrollParent = ancestorCache->scrollParent;
1738 break;
1739 }
1740 }
1702 } 1741 }
1703 1742
1743 if (m_ancestorDependentPropertyCache)
1744 m_ancestorDependentPropertyCache->scrollParent = scrollParent;
1745
1704 return scrollParent; 1746 return scrollParent;
1705 } 1747 }
1706 1748
1707 RenderLayer* RenderLayer::clipParent() const 1749 RenderLayer* RenderLayer::clipParent() const
1708 { 1750 {
1709 if (compositingReasons() & CompositingReasonOutOfFlowClipping && !compositor ()->clippedByAncestor(this)) { 1751 if (compositingReasons() & CompositingReasonOutOfFlowClipping && !compositor ()->clippedByAncestor(this)) {
1710 if (RenderObject* containingBlock = renderer()->containingBlock()) 1752 if (RenderObject* containingBlock = renderer()->containingBlock())
1711 return containingBlock->enclosingLayer()->enclosingCompositingLayer( ); 1753 return containingBlock->enclosingLayer()->enclosingCompositingLayer( );
1712 } 1754 }
1713 return 0; 1755 return 0;
(...skipping 1799 matching lines...) Expand 10 before | Expand all | Expand 10 after
3513 return PaintsIntoOwnBacking; 3555 return PaintsIntoOwnBacking;
3514 } 3556 }
3515 3557
3516 bool RenderLayer::isAllowedToQueryCompositingState() const 3558 bool RenderLayer::isAllowedToQueryCompositingState() const
3517 { 3559 {
3518 if (gCompositingQueryMode == CompositingQueriesAreAllowed) 3560 if (gCompositingQueryMode == CompositingQueriesAreAllowed)
3519 return true; 3561 return true;
3520 return renderer()->document().lifecycle().state() >= DocumentLifecycle::InCo mpositingUpdate; 3562 return renderer()->document().lifecycle().state() >= DocumentLifecycle::InCo mpositingUpdate;
3521 } 3563 }
3522 3564
3565 bool RenderLayer::isInCompositingUpdate() const
3566 {
3567 return renderer()->document().lifecycle().state() == DocumentLifecycle::InCo mpositingUpdate;
3568 }
3569
3523 CompositedLayerMappingPtr RenderLayer::compositedLayerMapping() const 3570 CompositedLayerMappingPtr RenderLayer::compositedLayerMapping() const
3524 { 3571 {
3525 ASSERT(isAllowedToQueryCompositingState()); 3572 ASSERT(isAllowedToQueryCompositingState());
3526 return m_compositedLayerMapping.get(); 3573 return m_compositedLayerMapping.get();
3527 } 3574 }
3528 3575
3529 CompositedLayerMappingPtr RenderLayer::ensureCompositedLayerMapping() 3576 CompositedLayerMappingPtr RenderLayer::ensureCompositedLayerMapping()
3530 { 3577 {
3531 if (!m_compositedLayerMapping) { 3578 if (!m_compositedLayerMapping) {
3532 m_compositedLayerMapping = adoptPtr(new CompositedLayerMapping(*this)); 3579 m_compositedLayerMapping = adoptPtr(new CompositedLayerMapping(*this));
(...skipping 519 matching lines...) Expand 10 before | Expand all | Expand 10 after
4052 rects.set(this, rect); 4099 rects.set(this, rect);
4053 } 4100 }
4054 } 4101 }
4055 } 4102 }
4056 4103
4057 DisableCompositingQueryAsserts::DisableCompositingQueryAsserts() 4104 DisableCompositingQueryAsserts::DisableCompositingQueryAsserts()
4058 : m_disabler(gCompositingQueryMode, CompositingQueriesAreAllowed) { } 4105 : m_disabler(gCompositingQueryMode, CompositingQueriesAreAllowed) { }
4059 4106
4060 COMPILE_ASSERT(1 << RenderLayer::ViewportConstrainedNotCompositedReasonBits >= R enderLayer::NumNotCompositedReasons, too_many_viewport_constrained_not_compositi ng_reasons); 4107 COMPILE_ASSERT(1 << RenderLayer::ViewportConstrainedNotCompositedReasonBits >= R enderLayer::NumNotCompositedReasons, too_many_viewport_constrained_not_compositi ng_reasons);
4061 4108
4109 RenderLayer::AncestorDependentPropertyCache::AncestorDependentPropertyCache()
4110 : containingBlock(0)
4111 , ancestorCompositedScrollingLayer(0)
4112 , scrollParent(0) { }
4113
4062 } // namespace WebCore 4114 } // namespace WebCore
4063 4115
4064 #ifndef NDEBUG 4116 #ifndef NDEBUG
4065 void showLayerTree(const WebCore::RenderLayer* layer) 4117 void showLayerTree(const WebCore::RenderLayer* layer)
4066 { 4118 {
4067 if (!layer) 4119 if (!layer)
4068 return; 4120 return;
4069 4121
4070 if (WebCore::LocalFrame* frame = layer->renderer()->frame()) { 4122 if (WebCore::LocalFrame* frame = layer->renderer()->frame()) {
4071 WTF::String output = externalRepresentation(frame, WebCore::RenderAsText ShowAllLayers | WebCore::RenderAsTextShowLayerNesting | WebCore::RenderAsTextSho wCompositedLayers | WebCore::RenderAsTextShowAddresses | WebCore::RenderAsTextSh owIDAndClass | WebCore::RenderAsTextDontUpdateLayout | WebCore::RenderAsTextShow LayoutState); 4123 WTF::String output = externalRepresentation(frame, WebCore::RenderAsText ShowAllLayers | WebCore::RenderAsTextShowLayerNesting | WebCore::RenderAsTextSho wCompositedLayers | WebCore::RenderAsTextShowAddresses | WebCore::RenderAsTextSh owIDAndClass | WebCore::RenderAsTextDontUpdateLayout | WebCore::RenderAsTextShow LayoutState);
4072 fprintf(stderr, "%s\n", output.utf8().data()); 4124 fprintf(stderr, "%s\n", output.utf8().data());
4073 } 4125 }
4074 } 4126 }
4075 4127
4076 void showLayerTree(const WebCore::RenderObject* renderer) 4128 void showLayerTree(const WebCore::RenderObject* renderer)
4077 { 4129 {
4078 if (!renderer) 4130 if (!renderer)
4079 return; 4131 return;
4080 showLayerTree(renderer->enclosingLayer()); 4132 showLayerTree(renderer->enclosingLayer());
4081 } 4133 }
4082 #endif 4134 #endif
OLDNEW
« no previous file with comments | « Source/core/rendering/RenderLayer.h ('k') | Source/core/rendering/compositing/RenderLayerCompositor.cpp » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698