OLD | NEW |
---|---|
1 // Copyright 2011 The Chromium Authors. All rights reserved. | 1 // Copyright 2011 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 "cc/layer_tree_host_common.h" | 5 #include "cc/layer_tree_host_common.h" |
6 | 6 |
7 #include <algorithm> | 7 #include <algorithm> |
8 | 8 |
9 #include "base/debug/trace_event.h" | 9 #include "base/debug/trace_event.h" |
10 #include "cc/layer.h" | 10 #include "cc/layer.h" |
(...skipping 22 matching lines...) Expand all Loading... | |
33 NOTREACHED(); | 33 NOTREACHED(); |
34 } | 34 } |
35 | 35 |
36 static void sortLayers(std::vector<LayerImpl*>::iterator first, std::vector<Laye rImpl*>::iterator end, LayerSorter* layerSorter) | 36 static void sortLayers(std::vector<LayerImpl*>::iterator first, std::vector<Laye rImpl*>::iterator end, LayerSorter* layerSorter) |
37 { | 37 { |
38 DCHECK(layerSorter); | 38 DCHECK(layerSorter); |
39 TRACE_EVENT0("cc", "layer_tree_host_common::sortLayers"); | 39 TRACE_EVENT0("cc", "layer_tree_host_common::sortLayers"); |
40 layerSorter->sort(first, end); | 40 layerSorter->sort(first, end); |
41 } | 41 } |
42 | 42 |
43 gfx::Rect LayerTreeHostCommon::calculateVisibleRect(const gfx::Rect& targetSurfa ceRect, const gfx::Rect& layerBoundRect, const gfx::Transform& transform) | 43 static inline gfx::Rect calculateVisibleRectWithCachedLayerRect(const gfx::Rect& targetSurfaceRect, const gfx::Rect& layerBoundRect, const gfx::Rect& layerRectI nTargetSpace, const gfx::Transform& transform) |
jamesr
2012/12/11 19:13:21
i think the 'static' and 'inline' here are redunda
shawnsingh
2012/12/11 22:33:18
Done.
| |
44 { | 44 { |
45 // Is this layer fully contained within the target surface? | 45 // Is this layer fully contained within the target surface? |
46 gfx::Rect layerInSurfaceSpace = MathUtil::mapClippedRect(transform, layerBou ndRect); | 46 if (targetSurfaceRect.Contains(layerRectInTargetSpace)) |
47 if (targetSurfaceRect.Contains(layerInSurfaceSpace)) | |
48 return layerBoundRect; | 47 return layerBoundRect; |
49 | 48 |
50 // If the layer doesn't fill up the entire surface, then find the part of | 49 // If the layer doesn't fill up the entire surface, then find the part of |
51 // the surface rect where the layer could be visible. This avoids trying to | 50 // the surface rect where the layer could be visible. This avoids trying to |
52 // project surface rect points that are behind the projection point. | 51 // project surface rect points that are behind the projection point. |
53 gfx::Rect minimalSurfaceRect = targetSurfaceRect; | 52 gfx::Rect minimalSurfaceRect = targetSurfaceRect; |
54 minimalSurfaceRect.Intersect(layerInSurfaceSpace); | 53 minimalSurfaceRect.Intersect(layerRectInTargetSpace); |
55 | 54 |
56 // Project the corners of the target surface rect into the layer space. | 55 // Project the corners of the target surface rect into the layer space. |
57 // This bounding rectangle may be larger than it needs to be (being | 56 // This bounding rectangle may be larger than it needs to be (being |
58 // axis-aligned), but is a reasonable filter on the space to consider. | 57 // axis-aligned), but is a reasonable filter on the space to consider. |
59 // Non-invertible transforms will create an empty rect here. | 58 // Non-invertible transforms will create an empty rect here. |
60 const gfx::Transform surfaceToLayer = MathUtil::inverse(transform); | 59 const gfx::Transform surfaceToLayer = MathUtil::inverse(transform); |
61 gfx::Rect layerRect = gfx::ToEnclosingRect(MathUtil::projectClippedRect(surf aceToLayer, gfx::RectF(minimalSurfaceRect))); | 60 gfx::Rect layerRect = gfx::ToEnclosingRect(MathUtil::projectClippedRect(surf aceToLayer, gfx::RectF(minimalSurfaceRect))); |
62 layerRect.Intersect(layerBoundRect); | 61 layerRect.Intersect(layerBoundRect); |
63 return layerRect; | 62 return layerRect; |
64 } | 63 } |
65 | 64 |
65 gfx::Rect LayerTreeHostCommon::calculateVisibleRect(const gfx::Rect& targetSurfa ceRect, const gfx::Rect& layerBoundRect, const gfx::Transform& transform) | |
66 { | |
67 gfx::Rect layerInSurfaceSpace = MathUtil::mapClippedRect(transform, layerBou ndRect); | |
68 return calculateVisibleRectWithCachedLayerRect(targetSurfaceRect, layerBound Rect, layerInSurfaceSpace, transform); | |
69 } | |
70 | |
66 template <typename LayerType> | 71 template <typename LayerType> |
67 static inline bool isRootLayer(LayerType* layer) | 72 static inline bool isRootLayer(LayerType* layer) |
68 { | 73 { |
69 return !layer->parent(); | 74 return !layer->parent(); |
70 } | 75 } |
71 | 76 |
72 template<typename LayerType> | 77 template<typename LayerType> |
73 static inline bool layerIsInExisting3DRenderingContext(LayerType* layer) | 78 static inline bool layerIsInExisting3DRenderingContext(LayerType* layer) |
74 { | 79 { |
75 // According to current W3C spec on CSS transforms, a layer is part of an es tablished | 80 // According to current W3C spec on CSS transforms, a layer is part of an es tablished |
(...skipping 43 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
119 return false; | 124 return false; |
120 } | 125 } |
121 | 126 |
122 template<typename LayerType> | 127 template<typename LayerType> |
123 static inline bool layerClipsSubtree(LayerType* layer) | 128 static inline bool layerClipsSubtree(LayerType* layer) |
124 { | 129 { |
125 return layer->masksToBounds() || layer->maskLayer(); | 130 return layer->masksToBounds() || layer->maskLayer(); |
126 } | 131 } |
127 | 132 |
128 template<typename LayerType> | 133 template<typename LayerType> |
129 static gfx::Rect calculateVisibleContentRect(LayerType* layer) | 134 static gfx::Rect calculateVisibleContentRect(LayerType* layer, const gfx::Rect& ancestorClipRectInDescendantSurfaceSpace, const gfx::Rect& layerRectInTargetSpac e) |
130 { | 135 { |
131 DCHECK(layer->renderTarget()); | 136 DCHECK(layer->renderTarget()); |
132 | 137 |
133 // Nothing is visible if the layer bounds are empty. | 138 // Nothing is visible if the layer bounds are empty. |
134 if (!layer->drawsContent() || layer->contentBounds().IsEmpty() || layer->dra wableContentRect().IsEmpty()) | 139 if (!layer->drawsContent() || layer->contentBounds().IsEmpty() || layer->dra wableContentRect().IsEmpty()) |
135 return gfx::Rect(); | 140 return gfx::Rect(); |
136 | 141 |
137 gfx::Rect targetSurfaceClipRect; | 142 // Compute visible bounds in target surface space. |
143 gfx::Rect visibleRectInTargetSurfaceSpace = layer->drawableContentRect(); | |
138 | 144 |
139 // First, compute visible bounds in target surface space. | 145 if (!layer->renderTarget()->renderSurface()->clipRect().IsEmpty()) { |
140 if (layer->renderTarget()->renderSurface()->clipRect().IsEmpty()) | 146 //gfx::Rect ancestorSurfaceClipRect = gfx::ToEnclosingRect(MathUtil::pro jectClippedRect(MathUtil::inverse(layer->renderTarget()->renderSurface()->drawTr ansform()), layer->renderTarget()->renderSurface()->clipRect())); |
jamesr
2012/12/11 19:13:21
?
shawnsingh
2012/12/11 22:33:18
residue from debugging =) it's removed now
| |
141 targetSurfaceClipRect = layer->drawableContentRect(); | 147 //visibleRectInTargetSurfaceSpace.Intersect(ancestorSurfaceClipRect); |
142 else { | 148 |
143 // In this case the target surface does clip layers that contribute to i t. So, we | 149 // In this case the target surface does clip layers that contribute to i t. So, we |
144 // have convert the current surface's clipRect from its ancestor surface space to | 150 // have convert the current surface's clipRect from its ancestor surface space to |
145 // the current surface space. | 151 // the current surface space. |
146 targetSurfaceClipRect = gfx::ToEnclosingRect(MathUtil::projectClippedRec t(MathUtil::inverse(layer->renderTarget()->renderSurface()->drawTransform()), la yer->renderTarget()->renderSurface()->clipRect())); | 152 //gfx::Rect ancestorSurfaceClipRect = gfx::ToEnclosingRect(MathUtil::pro jectClippedRect(MathUtil::inverse(layer->renderTarget()->renderSurface()->drawTr ansform()), layer->renderTarget()->renderSurface()->clipRect())); |
147 targetSurfaceClipRect.Intersect(layer->drawableContentRect()); | 153 |
154 visibleRectInTargetSurfaceSpace.Intersect(ancestorClipRectInDescendantSu rfaceSpace); | |
148 } | 155 } |
149 | 156 |
150 if (targetSurfaceClipRect.IsEmpty()) | 157 if (visibleRectInTargetSurfaceSpace.IsEmpty()) |
151 return gfx::Rect(); | 158 return gfx::Rect(); |
152 | 159 |
153 return LayerTreeHostCommon::calculateVisibleRect(targetSurfaceClipRect, gfx: :Rect(gfx::Point(), layer->contentBounds()), layer->drawTransform()); | 160 return calculateVisibleRectWithCachedLayerRect(visibleRectInTargetSurfaceSpa ce, gfx::Rect(gfx::Point(), layer->contentBounds()), layerRectInTargetSpace, lay er->drawTransform()); |
154 } | 161 } |
155 | 162 |
156 static inline bool transformToParentIsKnown(LayerImpl*) | 163 static inline bool transformToParentIsKnown(LayerImpl*) |
157 { | 164 { |
158 return true; | 165 return true; |
159 } | 166 } |
160 | 167 |
161 static inline bool transformToParentIsKnown(Layer* layer) | 168 static inline bool transformToParentIsKnown(Layer* layer) |
162 { | 169 { |
163 return !layer->transformIsAnimating(); | 170 return !layer->transformIsAnimating(); |
(...skipping 230 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
394 | 401 |
395 Layer* maskLayer = layer->maskLayer(); | 402 Layer* maskLayer = layer->maskLayer(); |
396 if (maskLayer) | 403 if (maskLayer) |
397 maskLayer->setContentsScale(contentsScale); | 404 maskLayer->setContentsScale(contentsScale); |
398 | 405 |
399 Layer* replicaMaskLayer = layer->replicaLayer() ? layer->replicaLayer()->mas kLayer() : 0; | 406 Layer* replicaMaskLayer = layer->replicaLayer() ? layer->replicaLayer()->mas kLayer() : 0; |
400 if (replicaMaskLayer) | 407 if (replicaMaskLayer) |
401 replicaMaskLayer->setContentsScale(contentsScale); | 408 replicaMaskLayer->setContentsScale(contentsScale); |
402 } | 409 } |
403 | 410 |
411 template<typename LayerType, typename LayerList> | |
412 static inline void removeSurfaceForEarlyExit(LayerType* layerToRemove, LayerList & renderSurfaceLayerList) | |
413 { | |
414 DCHECK(layerToRemove->renderSurface()); | |
415 // Technically, we know that the layer we want to remove should be | |
416 // at the back of the renderSurfaceLayerList. However, we have had | |
417 // bugs before that added unnecessary layers here | |
418 // (https://bugs.webkit.org/show_bug.cgi?id=74147), but that causes | |
419 // things to crash. So here we proactively remove any additional | |
420 // layers from the end of the list. | |
421 while (renderSurfaceLayerList.back() != layerToRemove) { | |
422 renderSurfaceLayerList.back()->clearRenderSurface(); | |
423 renderSurfaceLayerList.pop_back(); | |
424 } | |
425 DCHECK(renderSurfaceLayerList.back() == layerToRemove); | |
426 renderSurfaceLayerList.pop_back(); | |
427 layerToRemove->clearRenderSurface(); | |
428 } | |
429 | |
404 // Recursively walks the layer tree starting at the given node and computes all the | 430 // Recursively walks the layer tree starting at the given node and computes all the |
405 // necessary transformations, clipRects, render surfaces, etc. | 431 // necessary transformations, clipRects, render surfaces, etc. |
406 template<typename LayerType, typename LayerList, typename RenderSurfaceType> | 432 template<typename LayerType, typename LayerList, typename RenderSurfaceType> |
407 static void calculateDrawPropertiesInternal(LayerType* layer, const gfx::Transfo rm& parentMatrix, | 433 static void calculateDrawPropertiesInternal(LayerType* layer, const gfx::Transfo rm& parentMatrix, |
408 const gfx::Transform& fullHierarchyMatrix, const gfx::Transform& currentScro llCompensationMatrix, | 434 const gfx::Transform& fullHierarchyMatrix, const gfx::Transform& currentScro llCompensationMatrix, |
409 const gfx::Rect& clipRectFromAncestor, bool ancestorClipsSubtree, | 435 const gfx::Rect& clipRectFromAncestor, const gfx::Rect& clipRectFromAncestor InDescendantSpace, bool ancestorClipsSubtree, |
410 RenderSurfaceType* nearestAncestorThatMovesPixels, LayerList& renderSurfaceL ayerList, LayerList& layerList, | 436 RenderSurfaceType* nearestAncestorThatMovesPixels, LayerList& renderSurfaceL ayerList, LayerList& layerList, |
411 LayerSorter* layerSorter, int maxTextureSize, float deviceScaleFactor, float pageScaleFactor, gfx::Rect& drawableContentRectOfSubtree) | 437 LayerSorter* layerSorter, int maxTextureSize, float deviceScaleFactor, float pageScaleFactor, gfx::Rect& drawableContentRectOfSubtree) |
412 { | 438 { |
413 // This function computes the new matrix transformations recursively for thi s | 439 // This function computes the new matrix transformations recursively for thi s |
414 // layer and all its descendants. It also computes the appropriate render su rfaces. | 440 // layer and all its descendants. It also computes the appropriate render su rfaces. |
415 // Some important points to remember: | 441 // Some important points to remember: |
416 // | 442 // |
417 // 0. Here, transforms are notated in Matrix x Vector order, and in words we describe what | 443 // 0. Here, transforms are notated in Matrix x Vector order, and in words we describe what |
418 // the transform does from left to right. | 444 // the transform does from left to right. |
419 // | 445 // |
(...skipping 81 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
501 | 527 |
502 // As this function proceeds, these are the properties for the current | 528 // As this function proceeds, these are the properties for the current |
503 // layer that actually get computed. To avoid unnecessary copies | 529 // layer that actually get computed. To avoid unnecessary copies |
504 // (particularly for matrices), we do computations directly on these values | 530 // (particularly for matrices), we do computations directly on these values |
505 // when possible. | 531 // when possible. |
506 DrawProperties<LayerType, RenderSurfaceType>& layerDrawProperties = layer->d rawProperties(); | 532 DrawProperties<LayerType, RenderSurfaceType>& layerDrawProperties = layer->d rawProperties(); |
507 | 533 |
508 gfx::Rect clipRectForSubtree; | 534 gfx::Rect clipRectForSubtree; |
509 bool subtreeShouldBeClipped = false; | 535 bool subtreeShouldBeClipped = false; |
510 | 536 |
537 // This value is cached on the stack so that we don't have to inverse-projec t | |
538 // the surface's clipRect redundantly for every layer. This value is the | |
539 // same as the surface's clipRect, except that instead of being described | |
540 // in the target surface space (i.e. the ancestor surface space), it is | |
541 // described in the current surface space. | |
542 gfx::Rect clipRectForSubtreeInDescendantSpace; | |
543 | |
511 float accumulatedDrawOpacity = layer->opacity(); | 544 float accumulatedDrawOpacity = layer->opacity(); |
512 bool drawOpacityIsAnimating = layer->opacityIsAnimating(); | 545 bool drawOpacityIsAnimating = layer->opacityIsAnimating(); |
513 if (layer->parent()) { | 546 if (layer->parent()) { |
514 accumulatedDrawOpacity *= layer->parent()->drawOpacity(); | 547 accumulatedDrawOpacity *= layer->parent()->drawOpacity(); |
515 drawOpacityIsAnimating |= layer->parent()->drawOpacityIsAnimating(); | 548 drawOpacityIsAnimating |= layer->parent()->drawOpacityIsAnimating(); |
516 } | 549 } |
517 | 550 |
518 bool animatingTransformToTarget = layer->transformIsAnimating(); | 551 bool animatingTransformToTarget = layer->transformIsAnimating(); |
519 bool animatingTransformToScreen = animatingTransformToTarget; | 552 bool animatingTransformToScreen = animatingTransformToTarget; |
520 if (layer->parent()) { | 553 if (layer->parent()) { |
521 animatingTransformToTarget |= layer->parent()->drawTransformIsAnimating( ); | 554 animatingTransformToTarget |= layer->parent()->drawTransformIsAnimating( ); |
522 animatingTransformToScreen |= layer->parent()->screenSpaceTransformIsAni mating(); | 555 animatingTransformToScreen |= layer->parent()->screenSpaceTransformIsAni mating(); |
523 } | 556 } |
524 | 557 |
525 gfx::Size bounds = layer->bounds(); | 558 gfx::Size bounds = layer->bounds(); |
526 gfx::PointF anchorPoint = layer->anchorPoint(); | 559 gfx::PointF anchorPoint = layer->anchorPoint(); |
527 gfx::PointF position = layer->position() - layer->scrollDelta(); | 560 gfx::PointF position = layer->position() - layer->scrollDelta(); |
528 | 561 |
529 gfx::Transform combinedTransform = parentMatrix; | 562 gfx::Transform combinedTransform = parentMatrix; |
530 // LT = Tr[origin] * Tr[origin2anchor] | 563 if (!layer->transform().IsIdentity()) { |
531 combinedTransform.Translate3d(position.x() + anchorPoint.x() * bounds.width( ), position.y() + anchorPoint.y() * bounds.height(), layer->anchorPointZ()); | 564 // LT = Tr[origin] * Tr[origin2anchor] |
532 // LT = Tr[origin] * Tr[origin2anchor] * M[layer] | 565 combinedTransform.Translate3d(position.x() + anchorPoint.x() * bounds.wi dth(), position.y() + anchorPoint.y() * bounds.height(), layer->anchorPointZ()); |
533 combinedTransform.PreconcatTransform(layer->transform()); | 566 // LT = Tr[origin] * Tr[origin2anchor] * M[layer] |
534 // LT = Tr[origin] * Tr[origin2anchor] * M[layer] * Tr[anchor2origin] | 567 combinedTransform.PreconcatTransform(layer->transform()); |
535 combinedTransform.Translate3d(-anchorPoint.x() * bounds.width(), -anchorPoin t.y() * bounds.height(), -layer->anchorPointZ()); | 568 // LT = Tr[origin] * Tr[origin2anchor] * M[layer] * Tr[anchor2origin] |
569 combinedTransform.Translate3d(-anchorPoint.x() * bounds.width(), -anchor Point.y() * bounds.height(), -layer->anchorPointZ()); | |
570 } else { | |
571 combinedTransform.Translate(position.x(), position.y()); | |
572 } | |
536 | 573 |
537 // The layer's contentsSize is determined from the combinedTransform, which then informs the | 574 // The layer's contentsSize is determined from the combinedTransform, which then informs the |
538 // layer's drawTransform. | 575 // layer's drawTransform. |
539 updateLayerContentsScale(layer, combinedTransform, deviceScaleFactor, pageSc aleFactor, animatingTransformToScreen); | 576 updateLayerContentsScale(layer, combinedTransform, deviceScaleFactor, pageSc aleFactor, animatingTransformToScreen); |
540 | 577 |
541 // If there is a transformation from the impl thread then it should be at | 578 // If there is a transformation from the impl thread then it should be at |
542 // the start of the combinedTransform, but we don't want it to affect the | 579 // the start of the combinedTransform, but we don't want it to affect the |
543 // computation of contentsScale above. | 580 // computation of contentsScale above. |
544 // Note carefully: this is Concat, not Preconcat (implTransform * combinedTr ansform). | 581 // Note carefully: this is Concat, not Preconcat (implTransform * combinedTr ansform). |
545 combinedTransform.ConcatTransform(layer->implTransform()); | 582 combinedTransform.ConcatTransform(layer->implTransform()); |
(...skipping 90 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
636 replicaMaskDrawProperties.visible_content_rect = gfx::Rect(gfx::Poin t(), layer->contentBounds()); | 673 replicaMaskDrawProperties.visible_content_rect = gfx::Rect(gfx::Poin t(), layer->contentBounds()); |
637 } | 674 } |
638 | 675 |
639 // FIXME: make this smarter for the SkImageFilter case (check for | 676 // FIXME: make this smarter for the SkImageFilter case (check for |
640 // pixel-moving filters) | 677 // pixel-moving filters) |
641 if (layer->filters().hasFilterThatMovesPixels() || layer->filter()) | 678 if (layer->filters().hasFilterThatMovesPixels() || layer->filter()) |
642 nearestAncestorThatMovesPixels = renderSurface; | 679 nearestAncestorThatMovesPixels = renderSurface; |
643 | 680 |
644 // The render surface clipRect is expressed in the space where this surf ace draws, i.e. the same space as clipRectFromAncestor. | 681 // The render surface clipRect is expressed in the space where this surf ace draws, i.e. the same space as clipRectFromAncestor. |
645 renderSurface->setIsClipped(ancestorClipsSubtree); | 682 renderSurface->setIsClipped(ancestorClipsSubtree); |
646 if (ancestorClipsSubtree) | 683 if (ancestorClipsSubtree) { |
647 renderSurface->setClipRect(clipRectFromAncestor); | 684 renderSurface->setClipRect(clipRectFromAncestor); |
648 else | 685 clipRectForSubtreeInDescendantSpace = gfx::ToEnclosingRect(MathUtil: :projectClippedRect(MathUtil::inverse(renderSurface->drawTransform()), renderSur face->clipRect())); |
686 } else { | |
649 renderSurface->setClipRect(gfx::Rect()); | 687 renderSurface->setClipRect(gfx::Rect()); |
688 clipRectForSubtreeInDescendantSpace = clipRectFromAncestorInDescenda ntSpace; | |
689 } | |
650 | 690 |
651 renderSurface->setNearestAncestorThatMovesPixels(nearestAncestorThatMove sPixels); | 691 renderSurface->setNearestAncestorThatMovesPixels(nearestAncestorThatMove sPixels); |
652 | 692 |
653 renderSurfaceLayerList.push_back(layer); | 693 renderSurfaceLayerList.push_back(layer); |
654 } else { | 694 } else { |
655 DCHECK(layer->parent()); | 695 DCHECK(layer->parent()); |
656 | 696 |
657 // Note: layerDrawProperties.target_space_transform is computed above, | 697 // Note: layerDrawProperties.target_space_transform is computed above, |
658 // before this if-else statement. | 698 // before this if-else statement. |
659 layerDrawProperties.target_space_transform_is_animating = animatingTrans formToTarget; | 699 layerDrawProperties.target_space_transform_is_animating = animatingTrans formToTarget; |
660 layerDrawProperties.screen_space_transform_is_animating = animatingTrans formToScreen; | 700 layerDrawProperties.screen_space_transform_is_animating = animatingTrans formToScreen; |
661 layerDrawProperties.opacity = accumulatedDrawOpacity; | 701 layerDrawProperties.opacity = accumulatedDrawOpacity; |
662 layerDrawProperties.opacity_is_animating = drawOpacityIsAnimating; | 702 layerDrawProperties.opacity_is_animating = drawOpacityIsAnimating; |
663 sublayerMatrix = combinedTransform; | 703 sublayerMatrix = combinedTransform; |
664 | 704 |
665 layer->clearRenderSurface(); | 705 layer->clearRenderSurface(); |
666 | 706 |
667 // Layers without renderSurfaces directly inherit the ancestor's clip st atus. | 707 // Layers without renderSurfaces directly inherit the ancestor's clip st atus. |
668 subtreeShouldBeClipped = ancestorClipsSubtree; | 708 subtreeShouldBeClipped = ancestorClipsSubtree; |
669 if (ancestorClipsSubtree) | 709 if (ancestorClipsSubtree) |
670 clipRectForSubtree = clipRectFromAncestor; | 710 clipRectForSubtree = clipRectFromAncestor; |
671 | 711 |
712 // The surface's cached clipRect value propagates regardless of what cli pping goes on between layers here. | |
713 clipRectForSubtreeInDescendantSpace = clipRectFromAncestorInDescendantSp ace; | |
714 | |
672 // Layers that are not their own renderTarget will render into the targe t of their nearest ancestor. | 715 // Layers that are not their own renderTarget will render into the targe t of their nearest ancestor. |
673 layerDrawProperties.render_target = layer->parent()->renderTarget(); | 716 layerDrawProperties.render_target = layer->parent()->renderTarget(); |
674 } | 717 } |
675 | 718 |
676 gfx::Rect rectInTargetSpace = ToEnclosingRect(MathUtil::mapClippedRect(layer ->drawTransform(), contentRect)); | 719 gfx::Rect rectInTargetSpace = ToEnclosingRect(MathUtil::mapClippedRect(layer ->drawTransform(), contentRect)); |
677 | 720 |
678 if (layerClipsSubtree(layer)) { | 721 if (layerClipsSubtree(layer)) { |
679 subtreeShouldBeClipped = true; | 722 subtreeShouldBeClipped = true; |
680 if (ancestorClipsSubtree && !layer->renderSurface()) { | 723 if (ancestorClipsSubtree && !layer->renderSurface()) { |
681 clipRectForSubtree = clipRectFromAncestor; | 724 clipRectForSubtree = clipRectFromAncestor; |
(...skipping 21 matching lines...) Expand all Loading... | |
703 if (!layerShouldBeSkipped(layer)) | 746 if (!layerShouldBeSkipped(layer)) |
704 descendants.push_back(layer); | 747 descendants.push_back(layer); |
705 | 748 |
706 gfx::Transform nextScrollCompensationMatrix = computeScrollCompensationMatri xForChildren(layer, parentMatrix, currentScrollCompensationMatrix);; | 749 gfx::Transform nextScrollCompensationMatrix = computeScrollCompensationMatri xForChildren(layer, parentMatrix, currentScrollCompensationMatrix);; |
707 | 750 |
708 gfx::Rect accumulatedDrawableContentRectOfChildren; | 751 gfx::Rect accumulatedDrawableContentRectOfChildren; |
709 for (size_t i = 0; i < layer->children().size(); ++i) { | 752 for (size_t i = 0; i < layer->children().size(); ++i) { |
710 LayerType* child = LayerTreeHostCommon::getChildAsRawPtr(layer->children (), i); | 753 LayerType* child = LayerTreeHostCommon::getChildAsRawPtr(layer->children (), i); |
711 gfx::Rect drawableContentRectOfChildSubtree; | 754 gfx::Rect drawableContentRectOfChildSubtree; |
712 calculateDrawPropertiesInternal<LayerType, LayerList, RenderSurfaceType> (child, sublayerMatrix, nextHierarchyMatrix, nextScrollCompensationMatrix, | 755 calculateDrawPropertiesInternal<LayerType, LayerList, RenderSurfaceType> (child, sublayerMatrix, nextHierarchyMatrix, nextScrollCompensationMatrix, |
713 clipRectForSubtree, subtreeShouldBeClipped, nearestAncestorThatMovesPixels, | 756 clipRectForSubtree, clipRectForSubtreeInDescendantSpace, subtreeShouldBeClipped , nearestAncestorThatMovesPixels, |
714 renderSurfaceLayerList, descendants, layerSorter, maxTextureSize, deviceScaleFa ctor, pageScaleFactor, drawableContentRectOfChildSubtree); | 757 renderSurfaceLayerList, descendants, layerSorter, maxTextureSize, deviceScaleFa ctor, pageScaleFactor, drawableContentRectOfChildSubtree); |
715 if (!drawableContentRectOfChildSubtree.IsEmpty()) { | 758 if (!drawableContentRectOfChildSubtree.IsEmpty()) { |
716 accumulatedDrawableContentRectOfChildren.Union(drawableContentRectOf ChildSubtree); | 759 accumulatedDrawableContentRectOfChildren.Union(drawableContentRectOf ChildSubtree); |
717 if (child->renderSurface()) | 760 if (child->renderSurface()) |
718 descendants.push_back(child); | 761 descendants.push_back(child); |
719 } | 762 } |
720 } | 763 } |
721 | 764 |
765 if (layer->renderSurface() && !isRootLayer(layer) && !layer->renderSurface() ->layerList().size()) { | |
766 removeSurfaceForEarlyExit(layer, renderSurfaceLayerList); | |
767 return; | |
768 } | |
769 | |
722 // Compute the total drawableContentRect for this subtree (the rect is in ta rgetSurface space) | 770 // Compute the total drawableContentRect for this subtree (the rect is in ta rgetSurface space) |
723 gfx::Rect localDrawableContentRectOfSubtree = accumulatedDrawableContentRect OfChildren; | 771 gfx::Rect localDrawableContentRectOfSubtree = accumulatedDrawableContentRect OfChildren; |
724 if (layer->drawsContent()) | 772 if (layer->drawsContent()) |
725 localDrawableContentRectOfSubtree.Union(rectInTargetSpace); | 773 localDrawableContentRectOfSubtree.Union(rectInTargetSpace); |
726 if (subtreeShouldBeClipped) | 774 if (subtreeShouldBeClipped) |
727 localDrawableContentRectOfSubtree.Intersect(clipRectForSubtree); | 775 localDrawableContentRectOfSubtree.Intersect(clipRectForSubtree); |
728 | 776 |
729 // Compute the layer's drawable content rect (the rect is in targetSurface s pace) | 777 // Compute the layer's drawable content rect (the rect is in targetSurface s pace) |
730 layerDrawProperties.drawable_content_rect = rectInTargetSpace; | 778 layerDrawProperties.drawable_content_rect = rectInTargetSpace; |
731 if (subtreeShouldBeClipped) | 779 if (subtreeShouldBeClipped) |
732 layerDrawProperties.drawable_content_rect.Intersect(clipRectForSubtree); | 780 layerDrawProperties.drawable_content_rect.Intersect(clipRectForSubtree); |
733 | 781 |
734 // Tell the layer the rect that is clipped by. In theory we could use a | 782 // Tell the layer the rect that is clipped by. In theory we could use a |
735 // tighter clipRect here (drawableContentRect), but that actually does not | 783 // tighter clipRect here (drawableContentRect), but that actually does not |
736 // reduce how much would be drawn, and instead it would create unnecessary | 784 // reduce how much would be drawn, and instead it would create unnecessary |
737 // changes to scissor state affecting GPU performance. | 785 // changes to scissor state affecting GPU performance. |
738 layerDrawProperties.is_clipped = subtreeShouldBeClipped; | 786 layerDrawProperties.is_clipped = subtreeShouldBeClipped; |
739 if (subtreeShouldBeClipped) | 787 if (subtreeShouldBeClipped) |
740 layerDrawProperties.clip_rect = clipRectForSubtree; | 788 layerDrawProperties.clip_rect = clipRectForSubtree; |
741 else { | 789 else { |
742 // Initialize the clipRect to a safe value that will not clip the | 790 // Initialize the clipRect to a safe value that will not clip the |
743 // layer, just in case clipping is still accidentally used. | 791 // layer, just in case clipping is still accidentally used. |
744 layerDrawProperties.clip_rect = rectInTargetSpace; | 792 layerDrawProperties.clip_rect = rectInTargetSpace; |
745 } | 793 } |
746 | 794 |
747 // Compute the layer's visible content rect (the rect is in content space) | 795 // Compute the layer's visible content rect (the rect is in content space) |
748 layerDrawProperties.visible_content_rect = calculateVisibleContentRect(layer ); | 796 layerDrawProperties.visible_content_rect = calculateVisibleContentRect(layer , clipRectForSubtreeInDescendantSpace, rectInTargetSpace); |
749 | 797 |
750 // Compute the remaining properties for the render surface, if the layer has one. | 798 // Compute the remaining properties for the render surface, if the layer has one. |
751 if (isRootLayer(layer)) { | 799 if (isRootLayer(layer)) { |
752 // The root layer's surface's contentRect is always the entire viewport. | 800 // The root layer's surface's contentRect is always the entire viewport. |
753 DCHECK(layer->renderSurface()); | 801 DCHECK(layer->renderSurface()); |
754 layer->renderSurface()->setContentRect(clipRectFromAncestor); | 802 layer->renderSurface()->setContentRect(clipRectFromAncestor); |
755 } else if (layer->renderSurface() && !isRootLayer(layer)) { | 803 } else if (layer->renderSurface() && !isRootLayer(layer)) { |
756 RenderSurfaceType* renderSurface = layer->renderSurface(); | 804 RenderSurfaceType* renderSurface = layer->renderSurface(); |
757 gfx::Rect clippedContentRect = localDrawableContentRectOfSubtree; | 805 gfx::Rect clippedContentRect = localDrawableContentRectOfSubtree; |
758 | 806 |
759 // Don't clip if the layer is reflected as the reflection shouldn't be | 807 // Don't clip if the layer is reflected as the reflection shouldn't be |
760 // clipped. If the layer is animating, then the surface's transform to | 808 // clipped. If the layer is animating, then the surface's transform to |
761 // its target is not known on the main thread, and we should not use it | 809 // its target is not known on the main thread, and we should not use it |
762 // to clip. | 810 // to clip. |
763 if (!layer->replicaLayer() && transformToParentIsKnown(layer)) { | 811 if (!layer->replicaLayer() && transformToParentIsKnown(layer)) { |
764 // Note, it is correct to use ancestorClipsSubtree here, because we are looking at this layer's renderSurface, not the layer itself. | 812 // Note, it is correct to use ancestorClipsSubtree here, because we are looking at this layer's renderSurface, not the layer itself. |
765 if (ancestorClipsSubtree && !clippedContentRect.IsEmpty()) { | 813 if (ancestorClipsSubtree && !clippedContentRect.IsEmpty()) { |
766 gfx::Rect surfaceClipRect = LayerTreeHostCommon::calculateVisibl eRect(renderSurface->clipRect(), clippedContentRect, renderSurface->drawTransfor m()); | 814 gfx::Rect surfaceClipRect = LayerTreeHostCommon::calculateVisibl eRect(renderSurface->clipRect(), clippedContentRect, renderSurface->drawTransfor m()); |
767 clippedContentRect.Intersect(surfaceClipRect); | 815 clippedContentRect.Intersect(surfaceClipRect); |
768 } | 816 } |
769 } | 817 } |
770 | 818 |
771 // The RenderSurfaceImpl backing texture cannot exceed the maximum suppo rted | 819 // The RenderSurfaceImpl backing texture cannot exceed the maximum suppo rted |
772 // texture size. | 820 // texture size. |
773 clippedContentRect.set_width(std::min(clippedContentRect.width(), maxTex tureSize)); | 821 clippedContentRect.set_width(std::min(clippedContentRect.width(), maxTex tureSize)); |
774 clippedContentRect.set_height(std::min(clippedContentRect.height(), maxT extureSize)); | 822 clippedContentRect.set_height(std::min(clippedContentRect.height(), maxT extureSize)); |
775 | 823 |
776 if (clippedContentRect.IsEmpty()) | 824 if (clippedContentRect.IsEmpty()) { |
777 renderSurface->clearLayerLists(); | 825 renderSurface->clearLayerLists(); |
778 | 826 removeSurfaceForEarlyExit(layer, renderSurfaceLayerList); |
827 return; | |
828 } | |
829 | |
779 renderSurface->setContentRect(clippedContentRect); | 830 renderSurface->setContentRect(clippedContentRect); |
780 | 831 |
781 // The owning layer's screenSpaceTransform has a scale from content to l ayer space which we need to undo and | 832 // The owning layer's screenSpaceTransform has a scale from content to l ayer space which we need to undo and |
782 // replace with a scale from the surface's subtree into layer space. | 833 // replace with a scale from the surface's subtree into layer space. |
783 gfx::Transform screenSpaceTransform = layer->screenSpaceTransform(); | 834 gfx::Transform screenSpaceTransform = layer->screenSpaceTransform(); |
784 screenSpaceTransform.Scale(layer->contentsScaleX() / renderSurfaceSublay erScale.x(), layer->contentsScaleY() / renderSurfaceSublayerScale.y()); | 835 screenSpaceTransform.Scale(layer->contentsScaleX() / renderSurfaceSublay erScale.x(), layer->contentsScaleY() / renderSurfaceSublayerScale.y()); |
785 renderSurface->setScreenSpaceTransform(screenSpaceTransform); | 836 renderSurface->setScreenSpaceTransform(screenSpaceTransform); |
786 | 837 |
787 if (layer->replicaLayer()) { | 838 if (layer->replicaLayer()) { |
788 gfx::Transform surfaceOriginToReplicaOriginTransform; | 839 gfx::Transform surfaceOriginToReplicaOriginTransform; |
789 surfaceOriginToReplicaOriginTransform.Scale(renderSurfaceSublayerSca le.x(), renderSurfaceSublayerScale.y()); | 840 surfaceOriginToReplicaOriginTransform.Scale(renderSurfaceSublayerSca le.x(), renderSurfaceSublayerScale.y()); |
790 surfaceOriginToReplicaOriginTransform.Translate(layer->replicaLayer( )->position().x() + layer->replicaLayer()->anchorPoint().x() * bounds.width(), | 841 surfaceOriginToReplicaOriginTransform.Translate(layer->replicaLayer( )->position().x() + layer->replicaLayer()->anchorPoint().x() * bounds.width(), |
791 layer->replicaLayer( )->position().y() + layer->replicaLayer()->anchorPoint().y() * bounds.height()); | 842 layer->replicaLayer( )->position().y() + layer->replicaLayer()->anchorPoint().y() * bounds.height()); |
792 surfaceOriginToReplicaOriginTransform.PreconcatTransform(layer->repl icaLayer()->transform()); | 843 surfaceOriginToReplicaOriginTransform.PreconcatTransform(layer->repl icaLayer()->transform()); |
793 surfaceOriginToReplicaOriginTransform.Translate(-layer->replicaLayer ()->anchorPoint().x() * bounds.width(), -layer->replicaLayer()->anchorPoint().y( ) * bounds.height()); | 844 surfaceOriginToReplicaOriginTransform.Translate(-layer->replicaLayer ()->anchorPoint().x() * bounds.width(), -layer->replicaLayer()->anchorPoint().y( ) * bounds.height()); |
794 surfaceOriginToReplicaOriginTransform.Scale(1 / renderSurfaceSublaye rScale.x(), 1 / renderSurfaceSublayerScale.y()); | 845 surfaceOriginToReplicaOriginTransform.Scale(1 / renderSurfaceSublaye rScale.x(), 1 / renderSurfaceSublayerScale.y()); |
795 | 846 |
796 // Compute the replica's "originTransform" that maps from the replic a's origin space to the target surface origin space. | 847 // Compute the replica's "originTransform" that maps from the replic a's origin space to the target surface origin space. |
797 gfx::Transform replicaOriginTransform = layer->renderSurface()->draw Transform() * surfaceOriginToReplicaOriginTransform; | 848 gfx::Transform replicaOriginTransform = layer->renderSurface()->draw Transform() * surfaceOriginToReplicaOriginTransform; |
798 renderSurface->setReplicaDrawTransform(replicaOriginTransform); | 849 renderSurface->setReplicaDrawTransform(replicaOriginTransform); |
799 | 850 |
800 // Compute the replica's "screenSpaceTransform" that maps from the r eplica's origin space to the screen's origin space. | 851 // Compute the replica's "screenSpaceTransform" that maps from the r eplica's origin space to the screen's origin space. |
801 gfx::Transform replicaScreenSpaceTransform = layer->renderSurface()- >screenSpaceTransform() * surfaceOriginToReplicaOriginTransform; | 852 gfx::Transform replicaScreenSpaceTransform = layer->renderSurface()- >screenSpaceTransform() * surfaceOriginToReplicaOriginTransform; |
802 renderSurface->setReplicaScreenSpaceTransform(replicaScreenSpaceTran sform); | 853 renderSurface->setReplicaScreenSpaceTransform(replicaScreenSpaceTran sform); |
803 } | 854 } |
804 | |
805 // If a render surface has no layer list, then it and none of its childr en needed to get drawn. | |
806 if (!layer->renderSurface()->layerList().size()) { | |
807 // FIXME: Originally we asserted that this layer was already at the end of the | |
808 // list, and only needed to remove that layer. For now, we re move the | |
809 // entire subtree of surfaces to fix a crash bug. The root ca use is | |
810 // https://bugs.webkit.org/show_bug.cgi?id=74147 and we shoul d be able | |
811 // to put the original assert after fixing that. | |
812 while (renderSurfaceLayerList.back() != layer) { | |
813 renderSurfaceLayerList.back()->clearRenderSurface(); | |
814 renderSurfaceLayerList.pop_back(); | |
815 } | |
816 DCHECK(renderSurfaceLayerList.back() == layer); | |
817 renderSurfaceLayerList.pop_back(); | |
818 layer->clearRenderSurface(); | |
819 return; | |
820 } | |
821 } | 855 } |
822 | 856 |
823 markLayerAsUpdated(layer); | 857 markLayerAsUpdated(layer); |
824 | 858 |
825 // If neither this layer nor any of its children were added, early out. | 859 // If neither this layer nor any of its children were added, early out. |
826 if (sortingStartIndex == descendants.size()) | 860 if (sortingStartIndex == descendants.size()) |
827 return; | 861 return; |
828 | 862 |
829 // If preserves-3d then sort all the descendants in 3D so that they can be | 863 // If preserves-3d then sort all the descendants in 3D so that they can be |
830 // drawn from back to front. If the preserves-3d property is also set on the parent then | 864 // drawn from back to front. If the preserves-3d property is also set on the parent then |
(...skipping 20 matching lines...) Expand all Loading... | |
851 | 885 |
852 // The root layer's renderSurface should receive the deviceViewport as the i nitial clipRect. | 886 // The root layer's renderSurface should receive the deviceViewport as the i nitial clipRect. |
853 bool subtreeShouldBeClipped = true; | 887 bool subtreeShouldBeClipped = true; |
854 gfx::Rect deviceViewportRect(gfx::Point(), deviceViewportSize); | 888 gfx::Rect deviceViewportRect(gfx::Point(), deviceViewportSize); |
855 | 889 |
856 // This function should have received a root layer. | 890 // This function should have received a root layer. |
857 DCHECK(isRootLayer(rootLayer)); | 891 DCHECK(isRootLayer(rootLayer)); |
858 | 892 |
859 cc::calculateDrawPropertiesInternal<Layer, std::vector<scoped_refptr<Layer> >, RenderSurface>( | 893 cc::calculateDrawPropertiesInternal<Layer, std::vector<scoped_refptr<Layer> >, RenderSurface>( |
860 rootLayer, deviceScaleTransform, identityMatrix, identityMatrix, | 894 rootLayer, deviceScaleTransform, identityMatrix, identityMatrix, |
861 deviceViewportRect, subtreeShouldBeClipped, 0, renderSurfaceLayerList, | 895 deviceViewportRect, deviceViewportRect, subtreeShouldBeClipped, 0, rende rSurfaceLayerList, |
862 dummyLayerList, 0, maxTextureSize, | 896 dummyLayerList, 0, maxTextureSize, |
863 deviceScaleFactor, pageScaleFactor, totalDrawableContentRect); | 897 deviceScaleFactor, pageScaleFactor, totalDrawableContentRect); |
864 | 898 |
865 // The dummy layer list should not have been used. | 899 // The dummy layer list should not have been used. |
866 DCHECK(dummyLayerList.size() == 0); | 900 DCHECK(dummyLayerList.size() == 0); |
867 // A root layer renderSurface should always exist after calculateDrawPropert ies. | 901 // A root layer renderSurface should always exist after calculateDrawPropert ies. |
868 DCHECK(rootLayer->renderSurface()); | 902 DCHECK(rootLayer->renderSurface()); |
869 } | 903 } |
870 | 904 |
871 void LayerTreeHostCommon::calculateDrawProperties(LayerImpl* rootLayer, const gf x::Size& deviceViewportSize, float deviceScaleFactor, float pageScaleFactor, int maxTextureSize, std::vector<LayerImpl*>& renderSurfaceLayerList) | 905 void LayerTreeHostCommon::calculateDrawProperties(LayerImpl* rootLayer, const gf x::Size& deviceViewportSize, float deviceScaleFactor, float pageScaleFactor, int maxTextureSize, std::vector<LayerImpl*>& renderSurfaceLayerList) |
872 { | 906 { |
873 gfx::Rect totalDrawableContentRect; | 907 gfx::Rect totalDrawableContentRect; |
874 gfx::Transform identityMatrix; | 908 gfx::Transform identityMatrix; |
875 gfx::Transform deviceScaleTransform; | 909 gfx::Transform deviceScaleTransform; |
876 deviceScaleTransform.Scale(deviceScaleFactor, deviceScaleFactor); | 910 deviceScaleTransform.Scale(deviceScaleFactor, deviceScaleFactor); |
877 std::vector<LayerImpl*> dummyLayerList; | 911 std::vector<LayerImpl*> dummyLayerList; |
878 LayerSorter layerSorter; | 912 LayerSorter layerSorter; |
879 | 913 |
880 // The root layer's renderSurface should receive the deviceViewport as the i nitial clipRect. | 914 // The root layer's renderSurface should receive the deviceViewport as the i nitial clipRect. |
881 bool subtreeShouldBeClipped = true; | 915 bool subtreeShouldBeClipped = true; |
882 gfx::Rect deviceViewportRect(gfx::Point(), deviceViewportSize); | 916 gfx::Rect deviceViewportRect(gfx::Point(), deviceViewportSize); |
883 | 917 |
884 // This function should have received a root layer. | 918 // This function should have received a root layer. |
885 DCHECK(isRootLayer(rootLayer)); | 919 DCHECK(isRootLayer(rootLayer)); |
886 | 920 |
887 cc::calculateDrawPropertiesInternal<LayerImpl, std::vector<LayerImpl*>, Rend erSurfaceImpl>( | 921 cc::calculateDrawPropertiesInternal<LayerImpl, std::vector<LayerImpl*>, Rend erSurfaceImpl>( |
888 rootLayer, deviceScaleTransform, identityMatrix, identityMatrix, | 922 rootLayer, deviceScaleTransform, identityMatrix, identityMatrix, |
889 deviceViewportRect, subtreeShouldBeClipped, 0, renderSurfaceLayerList, | 923 deviceViewportRect, deviceViewportRect, subtreeShouldBeClipped, 0, rende rSurfaceLayerList, |
890 dummyLayerList, &layerSorter, maxTextureSize, | 924 dummyLayerList, &layerSorter, maxTextureSize, |
891 deviceScaleFactor, pageScaleFactor, totalDrawableContentRect); | 925 deviceScaleFactor, pageScaleFactor, totalDrawableContentRect); |
892 | 926 |
893 // The dummy layer list should not have been used. | 927 // The dummy layer list should not have been used. |
894 DCHECK(dummyLayerList.size() == 0); | 928 DCHECK(dummyLayerList.size() == 0); |
895 // A root layer renderSurface should always exist after calculateDrawPropert ies. | 929 // A root layer renderSurface should always exist after calculateDrawPropert ies. |
896 DCHECK(rootLayer->renderSurface()); | 930 DCHECK(rootLayer->renderSurface()); |
897 } | 931 } |
898 | 932 |
899 static bool pointHitsRect(const gfx::PointF& screenSpacePoint, const gfx::Transf orm& localSpaceToScreenSpaceTransform, gfx::RectF localSpaceRect) | 933 static bool pointHitsRect(const gfx::PointF& screenSpacePoint, const gfx::Transf orm& localSpaceToScreenSpaceTransform, gfx::RectF localSpaceRect) |
(...skipping 113 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1013 | 1047 |
1014 foundLayer = currentLayer; | 1048 foundLayer = currentLayer; |
1015 break; | 1049 break; |
1016 } | 1050 } |
1017 | 1051 |
1018 // This can potentially return 0, which means the screenSpacePoint did not s uccessfully hit test any layers, not even the root layer. | 1052 // This can potentially return 0, which means the screenSpacePoint did not s uccessfully hit test any layers, not even the root layer. |
1019 return foundLayer; | 1053 return foundLayer; |
1020 } | 1054 } |
1021 | 1055 |
1022 } // namespace cc | 1056 } // namespace cc |
OLD | NEW |