OLD | NEW |
1 // Copyright 2015 The Chromium Authors. All rights reserved. | 1 // Copyright 2015 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "core/paint/PrePaintTreeWalk.h" | 5 #include "core/paint/PrePaintTreeWalk.h" |
6 | 6 |
7 #include "core/dom/DocumentLifecycle.h" | 7 #include "core/dom/DocumentLifecycle.h" |
8 #include "core/frame/FrameView.h" | 8 #include "core/frame/FrameView.h" |
9 #include "core/frame/LocalFrame.h" | 9 #include "core/frame/LocalFrame.h" |
10 #include "core/layout/LayoutMultiColumnSpannerPlaceholder.h" | 10 #include "core/layout/LayoutMultiColumnSpannerPlaceholder.h" |
(...skipping 217 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
228 !object.needsPaintPropertyUpdate() && | 228 !object.needsPaintPropertyUpdate() && |
229 !object.descendantNeedsPaintPropertyUpdate() && | 229 !object.descendantNeedsPaintPropertyUpdate() && |
230 !context.treeBuilderContext.forceSubtreeUpdate && | 230 !context.treeBuilderContext.forceSubtreeUpdate && |
231 !context.paintInvalidatorContext.forcedSubtreeInvalidationFlags && | 231 !context.paintInvalidatorContext.forcedSubtreeInvalidationFlags && |
232 !object | 232 !object |
233 .shouldCheckForPaintInvalidationRegardlessOfPaintInvalidationState())
; | 233 .shouldCheckForPaintInvalidationRegardlessOfPaintInvalidationState())
; |
234 } | 234 } |
235 | 235 |
236 void PrePaintTreeWalk::walk(const LayoutObject& object, | 236 void PrePaintTreeWalk::walk(const LayoutObject& object, |
237 const PrePaintTreeWalkContext& parentContext) { | 237 const PrePaintTreeWalkContext& parentContext) { |
238 PrePaintTreeWalkContext context(parentContext); | |
239 | |
240 if (shouldEndWalkBefore(object, parentContext)) | 238 if (shouldEndWalkBefore(object, parentContext)) |
241 return; | 239 return; |
242 | 240 |
| 241 // PrePaintTreeWalkContext is large and can lead to stack overflows when |
| 242 // recursion is deep so this context object is allocated on the heap. |
| 243 // See: https://crbug.com/698653. |
| 244 std::unique_ptr<PrePaintTreeWalkContext> context = |
| 245 WTF::wrapUnique(new PrePaintTreeWalkContext(parentContext)); |
| 246 |
243 // This must happen before updatePropertiesForSelf, because the latter reads | 247 // This must happen before updatePropertiesForSelf, because the latter reads |
244 // some of the state computed here. | 248 // some of the state computed here. |
245 updateAuxiliaryObjectProperties(object, context); | 249 updateAuxiliaryObjectProperties(object, *context); |
246 | 250 |
247 m_propertyTreeBuilder.updatePropertiesForSelf(object, | 251 m_propertyTreeBuilder.updatePropertiesForSelf(object, |
248 context.treeBuilderContext); | 252 context->treeBuilderContext); |
249 m_paintInvalidator.invalidatePaintIfNeeded(object, | 253 m_paintInvalidator.invalidatePaintIfNeeded(object, |
250 context.paintInvalidatorContext); | 254 context->paintInvalidatorContext); |
251 m_propertyTreeBuilder.updatePropertiesForChildren(object, | 255 m_propertyTreeBuilder.updatePropertiesForChildren( |
252 context.treeBuilderContext); | 256 object, context->treeBuilderContext); |
253 | 257 |
254 invalidatePaintLayerOptimizationsIfNeeded(object, context); | 258 invalidatePaintLayerOptimizationsIfNeeded(object, *context); |
255 | 259 |
256 for (const LayoutObject* child = object.slowFirstChild(); child; | 260 for (const LayoutObject* child = object.slowFirstChild(); child; |
257 child = child->nextSibling()) { | 261 child = child->nextSibling()) { |
258 if (child->isLayoutMultiColumnSpannerPlaceholder()) { | 262 if (child->isLayoutMultiColumnSpannerPlaceholder()) { |
259 child->getMutableForPainting().clearPaintFlags(); | 263 child->getMutableForPainting().clearPaintFlags(); |
260 continue; | 264 continue; |
261 } | 265 } |
262 walk(*child, context); | 266 walk(*child, *context); |
263 } | 267 } |
264 | 268 |
265 if (object.isLayoutPart()) { | 269 if (object.isLayoutPart()) { |
266 const LayoutPart& layoutPart = toLayoutPart(object); | 270 const LayoutPart& layoutPart = toLayoutPart(object); |
267 FrameViewBase* frameViewBase = layoutPart.frameViewBase(); | 271 FrameViewBase* frameViewBase = layoutPart.frameViewBase(); |
268 if (frameViewBase && frameViewBase->isFrameView()) { | 272 if (frameViewBase && frameViewBase->isFrameView()) { |
269 context.treeBuilderContext.current.paintOffset += | 273 context->treeBuilderContext.current.paintOffset += |
270 layoutPart.replacedContentRect().location() - | 274 layoutPart.replacedContentRect().location() - |
271 frameViewBase->frameRect().location(); | 275 frameViewBase->frameRect().location(); |
272 context.treeBuilderContext.current.paintOffset = | 276 context->treeBuilderContext.current.paintOffset = |
273 roundedIntPoint(context.treeBuilderContext.current.paintOffset); | 277 roundedIntPoint(context->treeBuilderContext.current.paintOffset); |
274 walk(*toFrameView(frameViewBase), context); | 278 walk(*toFrameView(frameViewBase), *context); |
275 } | 279 } |
276 // TODO(pdr): Investigate RemoteFrameView (crbug.com/579281). | 280 // TODO(pdr): Investigate RemoteFrameView (crbug.com/579281). |
277 } | 281 } |
278 | 282 |
279 object.getMutableForPainting().clearPaintFlags(); | 283 object.getMutableForPainting().clearPaintFlags(); |
280 } | 284 } |
281 | 285 |
282 } // namespace blink | 286 } // namespace blink |
OLD | NEW |