The presentation of a web page typically involves the following steps:
This article will only focus on the "Composite" stage of web development.
The following section briefly describes the rendering principles of browsers (Use of Chrome is in the form of an example in this document) before introducing compositing to facilitate understanding of concepts. For more information, see GPU Accelerated Compositing in Chrome.
NOTE: As Chrome has modified some implementations of the Blank engine, there is a change in many known class names. For example, replacing RenderObject with LayoutObject and RenderLayer with PaintLayer. For more information, see Slimming Paint.
The browser stores the content of a page as a tree consisting of Node objects called the DOM tree. There is an association of each HTML element with a Node object. Similarly, the root node of the DOM tree is always a Document Node. Everyone knows this. However, there is a requirement for the conversion mapping from the DOM tree to the final rendering.
Each Node in the DOM tree has a corresponding LayoutObject, which knows how to paint the Node content on the screen.
Generally, LayoutObjects with the same coordinate space belong to the same PaintLayer. The original use of PaintLayer was stacking context to ensure that page elements are composite in the correct order so that overlapping and semi-transparent elements can be correctly displayed. Therefore, the creation of PaintLayer must be for LayoutObjects that meet the stacking context conditions and for special LayoutObjects in special cases, such as elements of overflow != visible. The following is the classification of the PaintLayers into three types based on the creation reasons:
A LayoutObject meeting the above conditions have a separated PaintLayer, while other LayoutObjects share the PaintLayer with the first parent element that owns the PaintLayer.
Some special PaintLayers are considerable as Compositing Layers. A Compositing Layer has its own GraphicsLayer, and other PaintLayers that are not Compositing Layers share the GraphicsLayer with the first parent layer that owns the GraphicsLayer.
Each GraphicsLayer has a GraphicsContext, which outputs the bitmap of the layer. The shared memory stores the bitmap which gets uploaded to the GPU as a texture. Then, the GPU combines multiple bitmaps and draws them on the screen. In this case, the page gets displayed on the screen.
Upgrading PaintLayer to a Compositing Layer occurs due to the following reasons:
NOTE: To upgrade a PaintLayer to a Compositing Layer, the PaintLayer must be a SelfPaintingLayer (which can get considered as the above mentioned NormalPaintLayer). In the following cases, all upgraded PaintLayers are SelfPaintingLayers.
Why does overlap generate a Compositing Layer? The following is a simple example.
As shown in the preceding figure, the blue rectangle overlaps the green one, and their parent element is a GraphicsLayer. Assume that the green rectangle is a GraphicsLayer. If it cannot be upgraded to a Compositing Layer by overlap, the blue rectangle does not upgrade to a Compositing Layer. The blue rectangle shares the GraphicsLayer with its parent element.
In this case, the rendering order is incorrect. Overlap becomes one of the reasons for generating the Compositing Layer to ensure the correct rendering order. The following figure shows the right order.
The overlap has the following situations:
However, this seems confusing. What is assumedOverlap? It is easy to understand. For example, if an element has a CSS animation effect. During animating, the element may overlap other elements. In this case, assumedOverlap gets generated. In this demo, the animated element does not visually overlap its brother element. However, due to assumedOverlap, the brother element is upgraded to the Compositing Layer.
Note the following particular case of this reason: If the Compositing Layer has the inline transform attribute, assumedOverlap occurs for the brother PaintLayer, which gets upgraded to the Compositing Layer.
The preceding are common reasons for upgrading a layer to a Compositing Layer. However, due to the overlap, a large number of Compositing Layers may be randomly generated, which consume CPU and memory resources and may seriously affect the page performance. The browser has considered this problem and implemented layer squashing. If multiple PaintLayers overlap the same Compositing Layer, the PaintLayers are squashed into a GraphicsLayer to avoid the "layer explosion" due to the overlap. The blue square is upgraded to a Compositing Layer by translateZ, and other overlapping squares get squashed. The squashed element size is the total size of the three squares.
When the green square hovers, it sets its translateZ attribute. In this case, the green square gets upgraded to a Compositing Layer, and the other two squares get squashed. The squashed element size is the total size of the two squares.
Of course, the browser is unable to automatically detect squash layers in many particular scenarios, as shown below. Such scenarios are avoidable. (NOTE: Overlap is the basis of the following scenarios.)
Squashing that may break the rendering order is not allowed (squashingWouldBreakPaintOrder).
<style>
#ancestor {
-webkit-mask-image: -webkit-linear-gradient(rgba(0,0,0,1), rgba(0,0,0,0));
}
#composited {
width: 100%;
height: 100%;
transform: translateZ(0);
}
#container {
position: relative;
width: 400px;
height: 60px;
border: 1px solid black;
}
#overlap-child {
position: absolute;
left: 0;
top: 0 ;
bottom: 0px;
width: 100%;
height: 60px;
background-color: orange;
}
</style>
<div id="container">
<div id="composited">Text behind the orange box.</div>
<div id="ancestor">
<div id="overlap-child"></div>
</div>
</div>
In this example, #overlap-child
overlaps the Compositing Layer. If it is squashed, the rendering order changes, and the mask attribute of the parent element #ancestor
is invalid. Therefore, layer squashing is not applicable. Currently, this scenario often occurs when the preceding ancestor element uses the master or filter attribute. The PaintLayer of the video element cannot be squashed or squash other PaintLayers to the Compositing Layer of the video (squashingVideoIsDisallowed).
The PaintLayer of the iframe or plug-in cannot be squashed or squash other PaintLayers to the Compositing Layer of the iframe or plug-in (squashingLayoutPartIsDisallowed).
The PaintLayer with the reflection attribute cannot be squashed (squashingReflectionDisallowed).
The PaintLayer with the blend mode attribute cannot be squashed (squashingBlendingDisallowed).
When the PaintLayer and Compositing Layer have different clipping containers, the PaintLayer cannot be squashed (squashingClippingContainerMismatch).
<style>
.clipping-container {
overflow: hidden;
height: 10px;
background-color: blue;
}
.composited {
transform: translateZ(0);
height: 10px;
background-color: red;
}
.target {
position:absolute;
top: 0px;
height:100px;
width:100px;
background-color: green;
color: #fff;
}
</style>
<div class="clipping-container">
<div class="composited"></div>
</div>
<div class="target">Not squashed to composited div</div>
In this example, .target
overlaps the Compositing Layer .composited
. However, as .composited
is in the overflow: hidden
container, .target
and the Compositing Layer have different clipping containers, and .target
cannot be squashed. The PaintLayer that scrolls with respect to the Compositing Layer cannot be squashed (scrollsWithRespectToSquashingLayer).
<style>
body {
height: 1500px;
overflow-x: hidden;
}
.composited {
width: 50px;
height: 50px;
background-color: red;
position: absolute;
left: 50px;
top: 400px;
transform: translateZ(0);
}
.overlap {
width: 200px;
height: 200px;
background-color: green;
position: fixed;
left: 0px;
top: 0px;
}
</style>
<div class="composited"></div>
<div class="overlap"></div>
In this example, the red .composited
layer is upgraded to a Compositing Layer, and the green .overlap
layer is fixed at the top of the page. Only .composited
is the Compositing Layer.
When the page is scrolled and .overlap
overlaps .composited
, .overlap
is upgraded to a Compositing Layer. At the same time, it cannot get squashed because it gets scrolled concerning the Compositing Layer.
When the PaintLayer and Compositing Layer have different ancestor layers with the opacity attribute, the PaintLayer cannot get squashed (squashingOpacityAncestorMismatch, same as squashingClippingContainerMismatch). This rule is applicable if the opacity attribute of one ancestor layer is smaller than 1 and is not set for the other ancestor layer.
When the PaintLayer and Compositing Layer have different ancestor layers with the transform attribute, the PaintLayer cannot be squashed (squashingTransformAncestorMismatch, same as above).
When the PaintLayer and Compositing Layer have different ancestor layers with the filter attribute, the PaintLayer cannot be squashed (squashingFilterAncestorMismatch, same as above).
When the overlapped Compositing Layer is animating, the PaintLayer cannot get squashed (squashingLayerIsAnimating). The PaintLayer can get squashed only when the animation is not started or gets finished.
Understanding Human/Computer Symbiosis for Artificial Intelligence
Front-End Performance Optimization with Accelerated Compositing Part 2
2,599 posts | 762 followers
FollowAlibaba Clouder - November 19, 2018
Alibaba Clouder - February 8, 2021
Alibaba Clouder - November 10, 2020
Alibaba Clouder - May 27, 2019
amap_tech - March 16, 2021
Alibaba Cloud Serverless - July 17, 2023
2,599 posts | 762 followers
FollowElastic and secure virtual cloud servers to cater all your cloud hosting needs.
Learn MoreAn encrypted and secure cloud storage service which stores, processes and accesses massive amounts of data from anywhere in the world
Learn MoreLearn More
More Posts by Alibaba Clouder