Chromium Code Reviews| 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/PaintPropertyTreeBuilder.h" | 5 #include "core/paint/PaintPropertyTreeBuilder.h" |
| 6 | 6 |
| 7 #include "core/dom/DOMNodeIds.h" | 7 #include "core/dom/DOMNodeIds.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/frame/Settings.h" | 10 #include "core/frame/Settings.h" |
| (...skipping 20 matching lines...) Expand all Loading... | |
| 31 context.currentEffect = EffectPaintPropertyNode::root(); | 31 context.currentEffect = EffectPaintPropertyNode::root(); |
| 32 context.inputClipOfCurrentEffect = ClipPaintPropertyNode::root(); | 32 context.inputClipOfCurrentEffect = ClipPaintPropertyNode::root(); |
| 33 context.current.transform = context.absolutePosition.transform = | 33 context.current.transform = context.absolutePosition.transform = |
| 34 context.fixedPosition.transform = TransformPaintPropertyNode::root(); | 34 context.fixedPosition.transform = TransformPaintPropertyNode::root(); |
| 35 context.current.scroll = context.absolutePosition.scroll = | 35 context.current.scroll = context.absolutePosition.scroll = |
| 36 context.fixedPosition.scroll = ScrollPaintPropertyNode::root(); | 36 context.fixedPosition.scroll = ScrollPaintPropertyNode::root(); |
| 37 return context; | 37 return context; |
| 38 } | 38 } |
| 39 | 39 |
| 40 // True if a new property was created, false if an existing one was updated. | 40 // True if a new property was created, false if an existing one was updated. |
| 41 bool updatePreTranslation(FrameView& frameView, | 41 static inline bool updatePreTranslation( |
| 42 PassRefPtr<const TransformPaintPropertyNode> parent, | 42 FrameView& frameView, |
| 43 const TransformationMatrix& matrix, | 43 PassRefPtr<const TransformPaintPropertyNode> parent, |
| 44 const FloatPoint3D& origin) { | 44 const TransformationMatrix& matrix, |
| 45 const FloatPoint3D& origin) { | |
| 45 DCHECK(!RuntimeEnabledFeatures::rootLayerScrollingEnabled()); | 46 DCHECK(!RuntimeEnabledFeatures::rootLayerScrollingEnabled()); |
| 46 if (auto* existingPreTranslation = frameView.preTranslation()) { | 47 if (auto* existingPreTranslation = frameView.preTranslation()) { |
| 47 existingPreTranslation->update(std::move(parent), matrix, origin); | 48 existingPreTranslation->update(std::move(parent), matrix, origin); |
| 48 return false; | 49 return false; |
| 49 } | 50 } |
| 50 frameView.setPreTranslation( | 51 frameView.setPreTranslation( |
| 51 TransformPaintPropertyNode::create(std::move(parent), matrix, origin)); | 52 TransformPaintPropertyNode::create(std::move(parent), matrix, origin)); |
| 52 return true; | 53 return true; |
| 53 } | 54 } |
| 54 | 55 |
| 55 // True if a new property was created, false if an existing one was updated. | 56 // True if a new property was created, false if an existing one was updated. |
| 56 bool updateContentClip( | 57 static inline bool updateContentClip( |
| 57 FrameView& frameView, | 58 FrameView& frameView, |
| 58 PassRefPtr<const ClipPaintPropertyNode> parent, | 59 PassRefPtr<const ClipPaintPropertyNode> parent, |
| 59 PassRefPtr<const TransformPaintPropertyNode> localTransformSpace, | 60 PassRefPtr<const TransformPaintPropertyNode> localTransformSpace, |
| 60 const FloatRoundedRect& clipRect) { | 61 const FloatRoundedRect& clipRect) { |
| 61 DCHECK(!RuntimeEnabledFeatures::rootLayerScrollingEnabled()); | 62 DCHECK(!RuntimeEnabledFeatures::rootLayerScrollingEnabled()); |
| 62 if (auto* existingContentClip = frameView.contentClip()) { | 63 if (auto* existingContentClip = frameView.contentClip()) { |
| 63 existingContentClip->update(std::move(parent), | 64 existingContentClip->update(std::move(parent), |
| 64 std::move(localTransformSpace), clipRect); | 65 std::move(localTransformSpace), clipRect); |
| 65 return false; | 66 return false; |
| 66 } | 67 } |
| 67 frameView.setContentClip(ClipPaintPropertyNode::create( | 68 frameView.setContentClip(ClipPaintPropertyNode::create( |
| 68 std::move(parent), std::move(localTransformSpace), clipRect)); | 69 std::move(parent), std::move(localTransformSpace), clipRect)); |
| 69 return true; | 70 return true; |
| 70 } | 71 } |
| 71 | 72 |
| 72 // True if a new property was created, false if an existing one was updated. | 73 // True if a new property was created, false if an existing one was updated. |
| 73 bool updateScrollTranslation( | 74 static inline bool updateScrollTranslation( |
| 74 FrameView& frameView, | 75 FrameView& frameView, |
| 75 PassRefPtr<const TransformPaintPropertyNode> parent, | 76 PassRefPtr<const TransformPaintPropertyNode> parent, |
| 76 const TransformationMatrix& matrix, | 77 const TransformationMatrix& matrix, |
| 77 const FloatPoint3D& origin) { | 78 const FloatPoint3D& origin) { |
| 78 DCHECK(!RuntimeEnabledFeatures::rootLayerScrollingEnabled()); | 79 DCHECK(!RuntimeEnabledFeatures::rootLayerScrollingEnabled()); |
| 79 if (auto* existingScrollTranslation = frameView.scrollTranslation()) { | 80 if (auto* existingScrollTranslation = frameView.scrollTranslation()) { |
| 80 existingScrollTranslation->update(std::move(parent), matrix, origin); | 81 existingScrollTranslation->update(std::move(parent), matrix, origin); |
| 81 return false; | 82 return false; |
| 82 } | 83 } |
| 83 frameView.setScrollTranslation( | 84 frameView.setScrollTranslation( |
| 84 TransformPaintPropertyNode::create(std::move(parent), matrix, origin)); | 85 TransformPaintPropertyNode::create(std::move(parent), matrix, origin)); |
| 85 return true; | 86 return true; |
| 86 } | 87 } |
| 87 | 88 |
| 88 // True if a new property was created or a main thread scrolling reason changed | 89 // True if a new property was created or a main thread scrolling reason changed |
| 89 // (which can affect descendants), false if an existing one was updated. | 90 // (which can affect descendants), false if an existing one was updated. |
| 90 bool updateScroll(FrameView& frameView, | 91 static inline bool updateScroll( |
| 91 PassRefPtr<const ScrollPaintPropertyNode> parent, | 92 FrameView& frameView, |
| 92 PassRefPtr<const TransformPaintPropertyNode> scrollOffset, | 93 PassRefPtr<const ScrollPaintPropertyNode> parent, |
| 93 const IntSize& clip, | 94 PassRefPtr<const TransformPaintPropertyNode> scrollOffset, |
| 94 const IntSize& bounds, | 95 const IntSize& clip, |
| 95 bool userScrollableHorizontal, | 96 const IntSize& bounds, |
| 96 bool userScrollableVertical, | 97 bool userScrollableHorizontal, |
| 97 MainThreadScrollingReasons mainThreadScrollingReasons) { | 98 bool userScrollableVertical, |
| 99 MainThreadScrollingReasons mainThreadScrollingReasons) { | |
| 98 DCHECK(!RuntimeEnabledFeatures::rootLayerScrollingEnabled()); | 100 DCHECK(!RuntimeEnabledFeatures::rootLayerScrollingEnabled()); |
| 99 if (auto* existingScroll = frameView.scroll()) { | 101 if (auto* existingScroll = frameView.scroll()) { |
| 100 auto existingReasons = existingScroll->mainThreadScrollingReasons(); | 102 auto existingReasons = existingScroll->mainThreadScrollingReasons(); |
| 101 existingScroll->update(std::move(parent), std::move(scrollOffset), clip, | 103 existingScroll->update(std::move(parent), std::move(scrollOffset), clip, |
| 102 bounds, userScrollableHorizontal, | 104 bounds, userScrollableHorizontal, |
| 103 userScrollableVertical, mainThreadScrollingReasons); | 105 userScrollableVertical, mainThreadScrollingReasons); |
| 104 return existingReasons != mainThreadScrollingReasons; | 106 return existingReasons != mainThreadScrollingReasons; |
| 105 } | 107 } |
| 106 frameView.setScroll(ScrollPaintPropertyNode::create( | 108 frameView.setScroll(ScrollPaintPropertyNode::create( |
| 107 std::move(parent), std::move(scrollOffset), clip, bounds, | 109 std::move(parent), std::move(scrollOffset), clip, bounds, |
| 108 userScrollableHorizontal, userScrollableVertical, | 110 userScrollableHorizontal, userScrollableVertical, |
| 109 mainThreadScrollingReasons)); | 111 mainThreadScrollingReasons)); |
| 110 return true; | 112 return true; |
| 111 } | 113 } |
| 112 | 114 |
| 113 MainThreadScrollingReasons mainThreadScrollingReasons( | 115 static inline MainThreadScrollingReasons mainThreadScrollingReasons( |
| 114 const FrameView& frameView, | 116 const FrameView& frameView, |
| 115 MainThreadScrollingReasons ancestorReasons) { | 117 MainThreadScrollingReasons ancestorReasons) { |
| 116 auto reasons = ancestorReasons; | 118 auto reasons = ancestorReasons; |
| 117 if (!frameView.frame().settings()->getThreadedScrollingEnabled()) | 119 if (!frameView.frame().settings()->getThreadedScrollingEnabled()) |
| 118 reasons |= MainThreadScrollingReason::kThreadedScrollingDisabled; | 120 reasons |= MainThreadScrollingReason::kThreadedScrollingDisabled; |
| 119 if (frameView.hasBackgroundAttachmentFixedObjects()) | 121 if (frameView.hasBackgroundAttachmentFixedObjects()) |
| 120 reasons |= MainThreadScrollingReason::kHasBackgroundAttachmentFixedObjects; | 122 reasons |= MainThreadScrollingReason::kHasBackgroundAttachmentFixedObjects; |
| 121 return reasons; | 123 return reasons; |
| 122 } | 124 } |
| 123 | 125 |
| (...skipping 88 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 212 context.fixedPosition = context.current; | 214 context.fixedPosition = context.current; |
| 213 context.fixedPosition.transform = fixedTransformNode; | 215 context.fixedPosition.transform = fixedTransformNode; |
| 214 context.fixedPosition.scroll = fixedScrollNode; | 216 context.fixedPosition.scroll = fixedScrollNode; |
| 215 | 217 |
| 216 std::unique_ptr<PropertyTreeState> contentsState( | 218 std::unique_ptr<PropertyTreeState> contentsState( |
| 217 new PropertyTreeState(context.current.transform, context.current.clip, | 219 new PropertyTreeState(context.current.transform, context.current.clip, |
| 218 context.currentEffect, context.current.scroll)); | 220 context.currentEffect, context.current.scroll)); |
| 219 frameView.setTotalPropertyTreeStateForContents(std::move(contentsState)); | 221 frameView.setTotalPropertyTreeStateForContents(std::move(contentsState)); |
| 220 } | 222 } |
| 221 | 223 |
| 222 void PaintPropertyTreeBuilder::updatePaintOffsetTranslation( | 224 inline void PaintPropertyTreeBuilder::updatePaintOffsetTranslation( |
| 223 const LayoutObject& object, | 225 const LayoutObject& object, |
| 224 PaintPropertyTreeBuilderContext& context) { | 226 PaintPropertyTreeBuilderContext& context) { |
| 225 bool usesPaintOffsetTranslation = false; | 227 bool usesPaintOffsetTranslation = false; |
| 226 if (RuntimeEnabledFeatures::rootLayerScrollingEnabled() && | 228 if (RuntimeEnabledFeatures::rootLayerScrollingEnabled() && |
| 227 object.isLayoutView()) { | 229 object.isLayoutView()) { |
| 228 // Root layer scrolling always creates a translation node for LayoutView to | 230 // Root layer scrolling always creates a translation node for LayoutView to |
| 229 // ensure fixed and absolute contexts use the correct transform space. | 231 // ensure fixed and absolute contexts use the correct transform space. |
| 230 usesPaintOffsetTranslation = true; | 232 usesPaintOffsetTranslation = true; |
| 231 } else if (object.isBoxModelObject() && | 233 } else if (object.isBoxModelObject() && |
| 232 context.current.paintOffset != LayoutPoint()) { | 234 context.current.paintOffset != LayoutPoint()) { |
| (...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 271 context.absolutePosition.transform = properties->paintOffsetTranslation(); | 273 context.absolutePosition.transform = properties->paintOffsetTranslation(); |
| 272 context.fixedPosition.transform = properties->paintOffsetTranslation(); | 274 context.fixedPosition.transform = properties->paintOffsetTranslation(); |
| 273 context.absolutePosition.paintOffset = LayoutPoint(); | 275 context.absolutePosition.paintOffset = LayoutPoint(); |
| 274 context.fixedPosition.paintOffset = LayoutPoint(); | 276 context.fixedPosition.paintOffset = LayoutPoint(); |
| 275 } | 277 } |
| 276 } | 278 } |
| 277 } | 279 } |
| 278 | 280 |
| 279 // SVG does not use the general transform update of |updateTransform|, instead | 281 // SVG does not use the general transform update of |updateTransform|, instead |
| 280 // creating a transform node for SVG-specific transforms without 3D. | 282 // creating a transform node for SVG-specific transforms without 3D. |
| 281 void PaintPropertyTreeBuilder::updateTransformForNonRootSVG( | 283 inline void PaintPropertyTreeBuilder::updateTransformForNonRootSVG( |
| 282 const LayoutObject& object, | 284 const LayoutObject& object, |
| 283 PaintPropertyTreeBuilderContext& context) { | 285 PaintPropertyTreeBuilderContext& context) { |
| 284 DCHECK(object.isSVGChild()); | 286 DCHECK(object.isSVGChild()); |
| 285 // SVG does not use paint offset internally, except for SVGForeignObject which | 287 // SVG does not use paint offset internally, except for SVGForeignObject which |
| 286 // has different SVG and HTML coordinate spaces. | 288 // has different SVG and HTML coordinate spaces. |
| 287 DCHECK(object.isSVGForeignObject() || | 289 DCHECK(object.isSVGForeignObject() || |
| 288 context.current.paintOffset == LayoutPoint()); | 290 context.current.paintOffset == LayoutPoint()); |
| 289 | 291 |
| 290 if (object.needsPaintPropertyUpdate() || context.forceSubtreeUpdate) { | 292 if (object.needsPaintPropertyUpdate() || context.forceSubtreeUpdate) { |
| 291 AffineTransform transform = object.localToSVGParentTransform(); | 293 AffineTransform transform = object.localToSVGParentTransform(); |
| (...skipping 13 matching lines...) Expand all Loading... | |
| 305 } | 307 } |
| 306 } | 308 } |
| 307 | 309 |
| 308 if (object.paintProperties() && object.paintProperties()->transform()) { | 310 if (object.paintProperties() && object.paintProperties()->transform()) { |
| 309 context.current.transform = object.paintProperties()->transform(); | 311 context.current.transform = object.paintProperties()->transform(); |
| 310 context.current.shouldFlattenInheritedTransform = false; | 312 context.current.shouldFlattenInheritedTransform = false; |
| 311 context.current.renderingContextId = 0; | 313 context.current.renderingContextId = 0; |
| 312 } | 314 } |
| 313 } | 315 } |
| 314 | 316 |
| 315 static CompositingReasons compositingReasonsForTransform(const LayoutBox& box) { | 317 static inline CompositingReasons compositingReasonsForTransform( |
| 318 const LayoutBox& box) { | |
| 316 const ComputedStyle& style = box.styleRef(); | 319 const ComputedStyle& style = box.styleRef(); |
| 317 CompositingReasons compositingReasons = CompositingReasonNone; | 320 CompositingReasons compositingReasons = CompositingReasonNone; |
| 318 if (CompositingReasonFinder::requiresCompositingForTransform(box)) | 321 if (CompositingReasonFinder::requiresCompositingForTransform(box)) |
| 319 compositingReasons |= CompositingReason3DTransform; | 322 compositingReasons |= CompositingReason3DTransform; |
| 320 | 323 |
| 321 if (CompositingReasonFinder::requiresCompositingForTransformAnimation(style)) | 324 if (CompositingReasonFinder::requiresCompositingForTransformAnimation(style)) |
| 322 compositingReasons |= CompositingReasonActiveAnimation; | 325 compositingReasons |= CompositingReasonActiveAnimation; |
| 323 | 326 |
| 324 if (style.hasWillChangeCompositingHint() && | 327 if (style.hasWillChangeCompositingHint() && |
| 325 !style.subtreeWillChangeContents()) | 328 !style.subtreeWillChangeContents()) |
| 326 compositingReasons |= CompositingReasonWillChangeCompositingHint; | 329 compositingReasons |= CompositingReasonWillChangeCompositingHint; |
| 327 | 330 |
| 328 if (box.hasLayer() && box.layer()->has3DTransformedDescendant()) { | 331 if (box.hasLayer() && box.layer()->has3DTransformedDescendant()) { |
| 329 if (style.hasPerspective()) | 332 if (style.hasPerspective()) |
| 330 compositingReasons |= CompositingReasonPerspectiveWith3DDescendants; | 333 compositingReasons |= CompositingReasonPerspectiveWith3DDescendants; |
| 331 if (style.usedTransformStyle3D() == TransformStyle3DPreserve3D) | 334 if (style.usedTransformStyle3D() == TransformStyle3DPreserve3D) |
| 332 compositingReasons |= CompositingReasonPreserve3DWith3DDescendants; | 335 compositingReasons |= CompositingReasonPreserve3DWith3DDescendants; |
| 333 } | 336 } |
| 334 | 337 |
| 335 return compositingReasons; | 338 return compositingReasons; |
| 336 } | 339 } |
| 337 | 340 |
| 338 static FloatPoint3D transformOrigin(const LayoutBox& box) { | 341 static inline FloatPoint3D transformOrigin(const LayoutBox& box) { |
| 339 const ComputedStyle& style = box.styleRef(); | 342 const ComputedStyle& style = box.styleRef(); |
| 340 // Transform origin has no effect without a transform or motion path. | 343 // Transform origin has no effect without a transform or motion path. |
| 341 if (!style.hasTransform()) | 344 if (!style.hasTransform()) |
| 342 return FloatPoint3D(); | 345 return FloatPoint3D(); |
| 343 FloatSize borderBoxSize(box.size()); | 346 FloatSize borderBoxSize(box.size()); |
| 344 return FloatPoint3D( | 347 return FloatPoint3D( |
| 345 floatValueForLength(style.transformOriginX(), borderBoxSize.width()), | 348 floatValueForLength(style.transformOriginX(), borderBoxSize.width()), |
| 346 floatValueForLength(style.transformOriginY(), borderBoxSize.height()), | 349 floatValueForLength(style.transformOriginY(), borderBoxSize.height()), |
| 347 style.transformOriginZ()); | 350 style.transformOriginZ()); |
| 348 } | 351 } |
| 349 | 352 |
| 350 namespace { | 353 static inline CompositorElementId createDomNodeBasedCompositorElementId( |
| 351 | |
| 352 CompositorElementId createDomNodeBasedCompositorElementId( | |
| 353 const LayoutObject& object) { | 354 const LayoutObject& object) { |
| 354 return createCompositorElementId(DOMNodeIds::idForNode(object.node()), | 355 return createCompositorElementId(DOMNodeIds::idForNode(object.node()), |
| 355 CompositorSubElementId::Primary); | 356 CompositorSubElementId::Primary); |
| 356 } | 357 } |
| 357 | 358 |
| 358 } // namespace | 359 inline void PaintPropertyTreeBuilder::updateTransform( |
|
Xianzhu
2017/01/18 18:37:55
Alternately we can enclose all local static functi
| |
| 359 | |
| 360 void PaintPropertyTreeBuilder::updateTransform( | |
| 361 const LayoutObject& object, | 360 const LayoutObject& object, |
| 362 PaintPropertyTreeBuilderContext& context) { | 361 PaintPropertyTreeBuilderContext& context) { |
| 363 if (object.isSVGChild()) { | 362 if (object.isSVGChild()) { |
| 364 updateTransformForNonRootSVG(object, context); | 363 updateTransformForNonRootSVG(object, context); |
| 365 return; | 364 return; |
| 366 } | 365 } |
| 367 | 366 |
| 368 if (object.needsPaintPropertyUpdate() || context.forceSubtreeUpdate) { | 367 if (object.needsPaintPropertyUpdate() || context.forceSubtreeUpdate) { |
| 369 const ComputedStyle& style = object.styleRef(); | 368 const ComputedStyle& style = object.styleRef(); |
| 370 | 369 |
| (...skipping 52 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 423 context.current.renderingContextId = | 422 context.current.renderingContextId = |
| 424 properties->transform()->renderingContextId(); | 423 properties->transform()->renderingContextId(); |
| 425 context.current.shouldFlattenInheritedTransform = false; | 424 context.current.shouldFlattenInheritedTransform = false; |
| 426 } else { | 425 } else { |
| 427 context.current.renderingContextId = 0; | 426 context.current.renderingContextId = 0; |
| 428 context.current.shouldFlattenInheritedTransform = true; | 427 context.current.shouldFlattenInheritedTransform = true; |
| 429 } | 428 } |
| 430 } | 429 } |
| 431 } | 430 } |
| 432 | 431 |
| 433 void PaintPropertyTreeBuilder::updateEffect( | 432 inline void PaintPropertyTreeBuilder::updateEffect( |
| 434 const LayoutObject& object, | 433 const LayoutObject& object, |
| 435 PaintPropertyTreeBuilderContext& context) { | 434 PaintPropertyTreeBuilderContext& context) { |
| 436 const ComputedStyle& style = object.styleRef(); | 435 const ComputedStyle& style = object.styleRef(); |
| 437 | 436 |
| 438 const bool isCSSIsolatedGroup = | 437 const bool isCSSIsolatedGroup = |
| 439 object.isBoxModelObject() && style.isStackingContext(); | 438 object.isBoxModelObject() && style.isStackingContext(); |
| 440 if (!isCSSIsolatedGroup && !object.isSVGChild()) { | 439 if (!isCSSIsolatedGroup && !object.isSVGChild()) { |
| 441 if (object.needsPaintPropertyUpdate() || context.forceSubtreeUpdate) { | 440 if (object.needsPaintPropertyUpdate() || context.forceSubtreeUpdate) { |
| 442 if (auto* properties = object.getMutableForPainting().paintProperties()) | 441 if (auto* properties = object.getMutableForPainting().paintProperties()) |
| 443 context.forceSubtreeUpdate |= properties->clearEffect(); | 442 context.forceSubtreeUpdate |= properties->clearEffect(); |
| (...skipping 95 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 539 // TODO(trchen): Change input clip to expansion hint once implemented. | 538 // TODO(trchen): Change input clip to expansion hint once implemented. |
| 540 const ClipPaintPropertyNode* inputClip = | 539 const ClipPaintPropertyNode* inputClip = |
| 541 properties->effect()->outputClip(); | 540 properties->effect()->outputClip(); |
| 542 context.inputClipOfCurrentEffect = context.current.clip = | 541 context.inputClipOfCurrentEffect = context.current.clip = |
| 543 context.absolutePosition.clip = context.fixedPosition.clip = | 542 context.absolutePosition.clip = context.fixedPosition.clip = |
| 544 inputClip; | 543 inputClip; |
| 545 } | 544 } |
| 546 } | 545 } |
| 547 } | 546 } |
| 548 | 547 |
| 549 void PaintPropertyTreeBuilder::updateCssClip( | 548 inline void PaintPropertyTreeBuilder::updateCssClip( |
| 550 const LayoutObject& object, | 549 const LayoutObject& object, |
| 551 PaintPropertyTreeBuilderContext& context) { | 550 PaintPropertyTreeBuilderContext& context) { |
| 552 if (object.needsPaintPropertyUpdate() || context.forceSubtreeUpdate) { | 551 if (object.needsPaintPropertyUpdate() || context.forceSubtreeUpdate) { |
| 553 if (object.hasClip()) { | 552 if (object.hasClip()) { |
| 554 // Create clip node for descendants that are not fixed position. | 553 // Create clip node for descendants that are not fixed position. |
| 555 // We don't have to setup context.absolutePosition.clip here because this | 554 // We don't have to setup context.absolutePosition.clip here because this |
| 556 // object must be a container for absolute position descendants, and will | 555 // object must be a container for absolute position descendants, and will |
| 557 // copy from in-flow context later at updateOutOfFlowContext() step. | 556 // copy from in-flow context later at updateOutOfFlowContext() step. |
| 558 DCHECK(object.canContainAbsolutePositionObjects()); | 557 DCHECK(object.canContainAbsolutePositionObjects()); |
| 559 LayoutRect clipRect = | 558 LayoutRect clipRect = |
| 560 toLayoutBox(object).clipRect(context.current.paintOffset); | 559 toLayoutBox(object).clipRect(context.current.paintOffset); |
| 561 auto& properties = object.getMutableForPainting().ensurePaintProperties(); | 560 auto& properties = object.getMutableForPainting().ensurePaintProperties(); |
| 562 context.forceSubtreeUpdate |= properties.updateCssClip( | 561 context.forceSubtreeUpdate |= properties.updateCssClip( |
| 563 context.current.clip, context.current.transform, | 562 context.current.clip, context.current.transform, |
| 564 FloatRoundedRect(FloatRect(clipRect))); | 563 FloatRoundedRect(FloatRect(clipRect))); |
| 565 } else { | 564 } else { |
| 566 if (auto* properties = object.getMutableForPainting().paintProperties()) | 565 if (auto* properties = object.getMutableForPainting().paintProperties()) |
| 567 context.forceSubtreeUpdate |= properties->clearCssClip(); | 566 context.forceSubtreeUpdate |= properties->clearCssClip(); |
| 568 } | 567 } |
| 569 } | 568 } |
| 570 | 569 |
| 571 const auto* properties = object.paintProperties(); | 570 const auto* properties = object.paintProperties(); |
| 572 if (properties && properties->cssClip()) | 571 if (properties && properties->cssClip()) |
| 573 context.current.clip = properties->cssClip(); | 572 context.current.clip = properties->cssClip(); |
| 574 } | 573 } |
| 575 | 574 |
| 576 void PaintPropertyTreeBuilder::updateLocalBorderBoxContext( | 575 inline void PaintPropertyTreeBuilder::updateLocalBorderBoxContext( |
| 577 const LayoutObject& object, | 576 const LayoutObject& object, |
| 578 PaintPropertyTreeBuilderContext& context) { | 577 PaintPropertyTreeBuilderContext& context) { |
| 579 if (!object.needsPaintPropertyUpdate() && !context.forceSubtreeUpdate) | 578 if (!object.needsPaintPropertyUpdate() && !context.forceSubtreeUpdate) |
| 580 return; | 579 return; |
| 581 | 580 |
| 582 // Avoid adding an ObjectPaintProperties for non-boxes to save memory, since | 581 // Avoid adding an ObjectPaintProperties for non-boxes to save memory, since |
| 583 // we don't need them at the moment. | 582 // we don't need them at the moment. |
| 584 if (!object.isBox() && !object.hasLayer()) { | 583 if (!object.isBox() && !object.hasLayer()) { |
| 585 if (auto* properties = object.getMutableForPainting().paintProperties()) | 584 if (auto* properties = object.getMutableForPainting().paintProperties()) |
| 586 properties->clearLocalBorderBoxProperties(); | 585 properties->clearLocalBorderBoxProperties(); |
| 587 } else { | 586 } else { |
| 588 auto& properties = object.getMutableForPainting().ensurePaintProperties(); | 587 auto& properties = object.getMutableForPainting().ensurePaintProperties(); |
| 589 properties.updateLocalBorderBoxProperties( | 588 properties.updateLocalBorderBoxProperties( |
| 590 context.current.transform, context.current.clip, context.currentEffect, | 589 context.current.transform, context.current.clip, context.currentEffect, |
| 591 context.current.scroll); | 590 context.current.scroll); |
| 592 } | 591 } |
| 593 } | 592 } |
| 594 | 593 |
| 595 // TODO(trchen): Remove this once we bake the paint offset into frameRect. | 594 // TODO(trchen): Remove this once we bake the paint offset into frameRect. |
| 596 void PaintPropertyTreeBuilder::updateScrollbarPaintOffset( | 595 inline void PaintPropertyTreeBuilder::updateScrollbarPaintOffset( |
| 597 const LayoutObject& object, | 596 const LayoutObject& object, |
| 598 PaintPropertyTreeBuilderContext& context) { | 597 PaintPropertyTreeBuilderContext& context) { |
| 599 if (!object.needsPaintPropertyUpdate() && !context.forceSubtreeUpdate) | 598 if (!object.needsPaintPropertyUpdate() && !context.forceSubtreeUpdate) |
| 600 return; | 599 return; |
| 601 | 600 |
| 602 bool needsScrollbarPaintOffset = false; | 601 bool needsScrollbarPaintOffset = false; |
| 603 IntPoint roundedPaintOffset = roundedIntPoint(context.current.paintOffset); | 602 IntPoint roundedPaintOffset = roundedIntPoint(context.current.paintOffset); |
| 604 if (roundedPaintOffset != IntPoint() && object.isBoxModelObject()) { | 603 if (roundedPaintOffset != IntPoint() && object.isBoxModelObject()) { |
| 605 if (auto* area = toLayoutBoxModelObject(object).getScrollableArea()) { | 604 if (auto* area = toLayoutBoxModelObject(object).getScrollableArea()) { |
| 606 if (area->horizontalScrollbar() || area->verticalScrollbar()) { | 605 if (area->horizontalScrollbar() || area->verticalScrollbar()) { |
| 607 auto paintOffset = TransformationMatrix().translate( | 606 auto paintOffset = TransformationMatrix().translate( |
| 608 roundedPaintOffset.x(), roundedPaintOffset.y()); | 607 roundedPaintOffset.x(), roundedPaintOffset.y()); |
| 609 auto& properties = | 608 auto& properties = |
| 610 object.getMutableForPainting().ensurePaintProperties(); | 609 object.getMutableForPainting().ensurePaintProperties(); |
| 611 context.forceSubtreeUpdate |= properties.updateScrollbarPaintOffset( | 610 context.forceSubtreeUpdate |= properties.updateScrollbarPaintOffset( |
| 612 context.current.transform, paintOffset, FloatPoint3D()); | 611 context.current.transform, paintOffset, FloatPoint3D()); |
| 613 needsScrollbarPaintOffset = true; | 612 needsScrollbarPaintOffset = true; |
| 614 } | 613 } |
| 615 } | 614 } |
| 616 } | 615 } |
| 617 | 616 |
| 618 auto* properties = object.getMutableForPainting().paintProperties(); | 617 auto* properties = object.getMutableForPainting().paintProperties(); |
| 619 if (!needsScrollbarPaintOffset && properties) | 618 if (!needsScrollbarPaintOffset && properties) |
| 620 context.forceSubtreeUpdate |= properties->clearScrollbarPaintOffset(); | 619 context.forceSubtreeUpdate |= properties->clearScrollbarPaintOffset(); |
| 621 } | 620 } |
| 622 | 621 |
| 623 void PaintPropertyTreeBuilder::updateOverflowClip( | 622 inline void PaintPropertyTreeBuilder::updateOverflowClip( |
| 624 const LayoutObject& object, | 623 const LayoutObject& object, |
| 625 PaintPropertyTreeBuilderContext& context) { | 624 PaintPropertyTreeBuilderContext& context) { |
| 626 if (!object.isBox()) | 625 if (!object.isBox()) |
| 627 return; | 626 return; |
| 628 | 627 |
| 629 if (object.needsPaintPropertyUpdate() || context.forceSubtreeUpdate) { | 628 if (object.needsPaintPropertyUpdate() || context.forceSubtreeUpdate) { |
| 630 const LayoutBox& box = toLayoutBox(object); | 629 const LayoutBox& box = toLayoutBox(object); |
| 631 // The <input> elements can't have contents thus CSS overflow property | 630 // The <input> elements can't have contents thus CSS overflow property |
| 632 // doesn't apply. However for layout purposes we do generate child layout | 631 // doesn't apply. However for layout purposes we do generate child layout |
| 633 // objects for them, e.g. button label. We should clip the overflow from | 632 // objects for them, e.g. button label. We should clip the overflow from |
| (...skipping 28 matching lines...) Expand all Loading... | |
| 662 context.forceSubtreeUpdate |= | 661 context.forceSubtreeUpdate |= |
| 663 properties.updateOverflowClip(currentClip, context.current.transform, | 662 properties.updateOverflowClip(currentClip, context.current.transform, |
| 664 FloatRoundedRect(FloatRect(clipRect))); | 663 FloatRoundedRect(FloatRect(clipRect))); |
| 665 } | 664 } |
| 666 | 665 |
| 667 const auto* properties = object.paintProperties(); | 666 const auto* properties = object.paintProperties(); |
| 668 if (properties && properties->overflowClip()) | 667 if (properties && properties->overflowClip()) |
| 669 context.current.clip = properties->overflowClip(); | 668 context.current.clip = properties->overflowClip(); |
| 670 } | 669 } |
| 671 | 670 |
| 672 static FloatPoint perspectiveOrigin(const LayoutBox& box) { | 671 static inline FloatPoint perspectiveOrigin(const LayoutBox& box) { |
| 673 const ComputedStyle& style = box.styleRef(); | 672 const ComputedStyle& style = box.styleRef(); |
| 674 // Perspective origin has no effect without perspective. | 673 // Perspective origin has no effect without perspective. |
| 675 DCHECK(style.hasPerspective()); | 674 DCHECK(style.hasPerspective()); |
| 676 FloatSize borderBoxSize(box.size()); | 675 FloatSize borderBoxSize(box.size()); |
| 677 return FloatPoint( | 676 return FloatPoint( |
| 678 floatValueForLength(style.perspectiveOriginX(), borderBoxSize.width()), | 677 floatValueForLength(style.perspectiveOriginX(), borderBoxSize.width()), |
| 679 floatValueForLength(style.perspectiveOriginY(), borderBoxSize.height())); | 678 floatValueForLength(style.perspectiveOriginY(), borderBoxSize.height())); |
| 680 } | 679 } |
| 681 | 680 |
| 682 void PaintPropertyTreeBuilder::updatePerspective( | 681 inline void PaintPropertyTreeBuilder::updatePerspective( |
| 683 const LayoutObject& object, | 682 const LayoutObject& object, |
| 684 PaintPropertyTreeBuilderContext& context) { | 683 PaintPropertyTreeBuilderContext& context) { |
| 685 if (object.needsPaintPropertyUpdate() || context.forceSubtreeUpdate) { | 684 if (object.needsPaintPropertyUpdate() || context.forceSubtreeUpdate) { |
| 686 const ComputedStyle& style = object.styleRef(); | 685 const ComputedStyle& style = object.styleRef(); |
| 687 if (object.isBox() && style.hasPerspective()) { | 686 if (object.isBox() && style.hasPerspective()) { |
| 688 // The perspective node must not flatten (else nothing will get | 687 // The perspective node must not flatten (else nothing will get |
| 689 // perspective), but it should still extend the rendering context as | 688 // perspective), but it should still extend the rendering context as |
| 690 // most transform nodes do. | 689 // most transform nodes do. |
| 691 TransformationMatrix matrix = | 690 TransformationMatrix matrix = |
| 692 TransformationMatrix().applyPerspective(style.perspective()); | 691 TransformationMatrix().applyPerspective(style.perspective()); |
| (...skipping 10 matching lines...) Expand all Loading... | |
| 703 } | 702 } |
| 704 } | 703 } |
| 705 | 704 |
| 706 const auto* properties = object.paintProperties(); | 705 const auto* properties = object.paintProperties(); |
| 707 if (properties && properties->perspective()) { | 706 if (properties && properties->perspective()) { |
| 708 context.current.transform = properties->perspective(); | 707 context.current.transform = properties->perspective(); |
| 709 context.current.shouldFlattenInheritedTransform = false; | 708 context.current.shouldFlattenInheritedTransform = false; |
| 710 } | 709 } |
| 711 } | 710 } |
| 712 | 711 |
| 713 void PaintPropertyTreeBuilder::updateSvgLocalToBorderBoxTransform( | 712 inline void PaintPropertyTreeBuilder::updateSvgLocalToBorderBoxTransform( |
| 714 const LayoutObject& object, | 713 const LayoutObject& object, |
| 715 PaintPropertyTreeBuilderContext& context) { | 714 PaintPropertyTreeBuilderContext& context) { |
| 716 if (!object.isSVGRoot()) | 715 if (!object.isSVGRoot()) |
| 717 return; | 716 return; |
| 718 | 717 |
| 719 if (object.needsPaintPropertyUpdate() || context.forceSubtreeUpdate) { | 718 if (object.needsPaintPropertyUpdate() || context.forceSubtreeUpdate) { |
| 720 AffineTransform transformToBorderBox = | 719 AffineTransform transformToBorderBox = |
| 721 SVGRootPainter(toLayoutSVGRoot(object)) | 720 SVGRootPainter(toLayoutSVGRoot(object)) |
| 722 .transformToPixelSnappedBorderBox(context.current.paintOffset); | 721 .transformToPixelSnappedBorderBox(context.current.paintOffset); |
| 723 if (!transformToBorderBox.isIdentity()) { | 722 if (!transformToBorderBox.isIdentity()) { |
| (...skipping 13 matching lines...) Expand all Loading... | |
| 737 if (properties && properties->svgLocalToBorderBoxTransform()) { | 736 if (properties && properties->svgLocalToBorderBoxTransform()) { |
| 738 context.current.transform = properties->svgLocalToBorderBoxTransform(); | 737 context.current.transform = properties->svgLocalToBorderBoxTransform(); |
| 739 context.current.shouldFlattenInheritedTransform = false; | 738 context.current.shouldFlattenInheritedTransform = false; |
| 740 context.current.renderingContextId = 0; | 739 context.current.renderingContextId = 0; |
| 741 } | 740 } |
| 742 // The paint offset is included in |transformToBorderBox| so SVG does not need | 741 // The paint offset is included in |transformToBorderBox| so SVG does not need |
| 743 // to handle paint offset internally. | 742 // to handle paint offset internally. |
| 744 context.current.paintOffset = LayoutPoint(); | 743 context.current.paintOffset = LayoutPoint(); |
| 745 } | 744 } |
| 746 | 745 |
| 747 MainThreadScrollingReasons mainThreadScrollingReasons( | 746 static inline MainThreadScrollingReasons mainThreadScrollingReasons( |
| 748 const LayoutObject& object, | 747 const LayoutObject& object, |
| 749 MainThreadScrollingReasons ancestorReasons) { | 748 MainThreadScrollingReasons ancestorReasons) { |
| 750 // The current main thread scrolling reasons implementation only changes | 749 // The current main thread scrolling reasons implementation only changes |
| 751 // reasons at frame boundaries, so we can early-out when not at a LayoutView. | 750 // reasons at frame boundaries, so we can early-out when not at a LayoutView. |
| 752 // TODO(pdr): Need to find a solution to the style-related main thread | 751 // TODO(pdr): Need to find a solution to the style-related main thread |
| 753 // scrolling reasons such as opacity and transform which violate this. | 752 // scrolling reasons such as opacity and transform which violate this. |
| 754 if (!object.isLayoutView()) | 753 if (!object.isLayoutView()) |
| 755 return ancestorReasons; | 754 return ancestorReasons; |
| 756 return mainThreadScrollingReasons(*object.frameView(), ancestorReasons); | 755 return mainThreadScrollingReasons(*object.frameView(), ancestorReasons); |
| 757 } | 756 } |
| 758 | 757 |
| 759 void PaintPropertyTreeBuilder::updateScrollAndScrollTranslation( | 758 inline void PaintPropertyTreeBuilder::updateScrollAndScrollTranslation( |
| 760 const LayoutObject& object, | 759 const LayoutObject& object, |
| 761 PaintPropertyTreeBuilderContext& context) { | 760 PaintPropertyTreeBuilderContext& context) { |
| 762 if (object.needsPaintPropertyUpdate() || context.forceSubtreeUpdate) { | 761 if (object.needsPaintPropertyUpdate() || context.forceSubtreeUpdate) { |
| 763 bool needsScrollProperties = false; | 762 bool needsScrollProperties = false; |
| 764 if (object.hasOverflowClip()) { | 763 if (object.hasOverflowClip()) { |
| 765 auto ancestorReasons = | 764 auto ancestorReasons = |
| 766 context.current.scroll->mainThreadScrollingReasons(); | 765 context.current.scroll->mainThreadScrollingReasons(); |
| 767 auto reasons = mainThreadScrollingReasons(object, ancestorReasons); | 766 auto reasons = mainThreadScrollingReasons(object, ancestorReasons); |
| 768 bool scrollNodeNeededForMainThreadReasons = ancestorReasons != reasons; | 767 bool scrollNodeNeededForMainThreadReasons = ancestorReasons != reasons; |
| 769 | 768 |
| (...skipping 42 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 812 } | 811 } |
| 813 } | 812 } |
| 814 | 813 |
| 815 if (object.paintProperties() && object.paintProperties()->scroll()) { | 814 if (object.paintProperties() && object.paintProperties()->scroll()) { |
| 816 context.current.transform = object.paintProperties()->scrollTranslation(); | 815 context.current.transform = object.paintProperties()->scrollTranslation(); |
| 817 context.current.scroll = object.paintProperties()->scroll(); | 816 context.current.scroll = object.paintProperties()->scroll(); |
| 818 context.current.shouldFlattenInheritedTransform = false; | 817 context.current.shouldFlattenInheritedTransform = false; |
| 819 } | 818 } |
| 820 } | 819 } |
| 821 | 820 |
| 822 void PaintPropertyTreeBuilder::updateOutOfFlowContext( | 821 inline void PaintPropertyTreeBuilder::updateOutOfFlowContext( |
| 823 const LayoutObject& object, | 822 const LayoutObject& object, |
| 824 PaintPropertyTreeBuilderContext& context) { | 823 PaintPropertyTreeBuilderContext& context) { |
| 825 if (object.isLayoutBlock()) | 824 if (object.isLayoutBlock()) |
| 826 context.paintOffsetForFloat = context.current.paintOffset; | 825 context.paintOffsetForFloat = context.current.paintOffset; |
| 827 | 826 |
| 828 if (object.canContainAbsolutePositionObjects()) { | 827 if (object.canContainAbsolutePositionObjects()) { |
| 829 context.absolutePosition = context.current; | 828 context.absolutePosition = context.current; |
| 830 context.containerForAbsolutePosition = &object; | 829 context.containerForAbsolutePosition = &object; |
| 831 } | 830 } |
| 832 | 831 |
| (...skipping 152 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 985 updateOverflowClip(object, context); | 984 updateOverflowClip(object, context); |
| 986 updatePerspective(object, context); | 985 updatePerspective(object, context); |
| 987 updateSvgLocalToBorderBoxTransform(object, context); | 986 updateSvgLocalToBorderBoxTransform(object, context); |
| 988 updateScrollAndScrollTranslation(object, context); | 987 updateScrollAndScrollTranslation(object, context); |
| 989 updateOutOfFlowContext(object, context); | 988 updateOutOfFlowContext(object, context); |
| 990 | 989 |
| 991 context.forceSubtreeUpdate |= object.subtreeNeedsPaintPropertyUpdate(); | 990 context.forceSubtreeUpdate |= object.subtreeNeedsPaintPropertyUpdate(); |
| 992 } | 991 } |
| 993 | 992 |
| 994 } // namespace blink | 993 } // namespace blink |
| OLD | NEW |