-
Notifications
You must be signed in to change notification settings - Fork 2k
New issue
Have a question about this project? # for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “#”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? # to your account
CSS新特性contain,控制页面的重绘与重排 #23
Comments
没了?= =没懂 |
@shellphon |
写一个实例会好很多 |
催更 |
太监了?拖了好久了,催更催更😂 |
没懂。求解释! |
求补全这个文章,催更啦 @chokcoco |
催更催更 |
在github上写博客就是好,一堆人给你催更,有没有动力满满~ |
催更催更 |
1 similar comment
催更催更 |
吹更 |
催更 |
1 similar comment
催更 |
作者,我还是不明白到底有啥用,没有demo 代码呀,差评 |
contain 可以用在所有元素上,是提升页面性能的属性。 |
那这么说就可以无脑堆这个属性了吗 |
@1998yyh 不能无脑堆,会引起一些其他问题,譬如元素只绘制了一半(类似于 overflow hidden,部分内容超出了元素的边界) |
mark |
|
在介绍新的 CSS 属性
contain
之前,读者首先需要了解什么是页面的重绘与重排。之前已经描述过很多次了,还不太了解的可以先看看这个提高 CSS 动画性能的正确姿势。
OK,下面进入本文正题,
contain
为何?contain
属性允许我们指定特定的 DOM 元素和它的子元素,让它们能够独立于整个 DOM 树结构之外。目的是能够让浏览器有能力只对部分元素进行重绘、重排,而不必每次都针对整个页面。contain
语法看看它的语法:
除去
none
,取值还有 6 个,我们一个一个来看看。contain: size
contain: size: 设定了
contain: size
的元素的渲染不会受到其子元素内容的影响。我开始看到这个定义也是一头雾水,光看定义很难明白到底是什么意思。还需实践一番:
假设我们有如下简单结构:
并且,借助 jQuery 实现每次点击容器添加一个
<p>Coco</p>
结构:那么会得到如下结果:
可以看到,容器
.container
的高度是会随着元素的增加而增加的,这是正常的现象。此刻,我们给容器
.container
添加一个contain: size
,也就会出现上述说的:设定了contain: size
的元素的渲染不会受到其子元素内容的影响。再看看会发生什么:
正常而言,父元素的高度会因为子元素的增多而被撑高,而现在,子元素的变化不再影响父元素的样式布局,这就是
contain: size
的作用。contain: style
接下来再说说
contain: style
、contain: layout
、contain: paint
。先看看 contain: style。截止至本文书写的过程中,
contain: style
暂时被移除了。嗯,官方说辞是因为存在某些风险,暂时被移除,可能在规范的第二版会重新定义吧,那这个属性也暂且放一放。
contain: paint
contain: paint:设定了
contain: paint
的元素即是设定了布局限制,也就是说告知 User Agent,此元素的子元素不会在此元素的边界之外被展示,因此,如果元素不在屏幕上或以其他方式设定为不可见,则还可以保证其后代不可见不被渲染。这个稍微好理解一点,先来看第一个特性:
设定了
contain: paint
的元素的子元素不会在此元素的边界之外被展示contain: paint
的元素的子元素不会在此元素的边界之外被展示这个特点有点类似与
overflow: hidden
,也就是明确告知用户代理,子元素的内容不会超出元素的边界,所以超出部分无需渲染。简单示例,假设元素结构如下:
我们来看看,设定了
contain: paint
与没设定时会发生什么:CodePen Demo -- contain: paint Demo
设定了
contain: paint
的元素在屏幕之外时不会渲染绘制通过使用
contain: paint
, 如果元素处于屏幕外,那么用户代理就会忽略渲染这些元素,从而能更快的渲染其它内容。contain: layout
contain: layout:设定了
contain: layout
的元素即是设定了布局限制,也就是说告知 User Agent,此元素内部的样式变化不会引起元素外部的样式变化,反之亦然。启用
contain: layout
可以潜在地将每一帧需要渲染的元素数量减少到少数,而不是重新渲染整个文档,从而为浏览器节省了大量不必要的工作,并显着提高了性能。使用
contain:layout
,开发人员可以指定对该元素任何后代的任何更改都不会影响任何外部元素的布局,反之亦然。因此,浏览器仅计算内部元素的位置(如果对其进行了修改),而其余DOM保持不变。因此,这意味着帧渲染管道中的布局过程将加快。
存在的问题
描述很美好,但是在实际 Demo 测试的过程中(截止至2021/04/27,Chrome 90.0.4430.85),仅仅单独使用
contain:layout
并没有验证得到上述那么美好的结果。设定了
contain: layout
的指定元素,改元素的任何后代的任何更改还是会影响任何外部元素的布局,点击红框会增加一条<p>Coco<p>
元素插入到container
中:简单的代码如下:
CodePen Demo -- contain: layout Demo
目前看来,
contain: layout
的实际作用不那么明显,更多的关于它的用法,你可以再看看这篇文章:CSS-tricks - containcontain: strict | contain: content
这两个属性稍微有点特殊,效果是上述介绍的几个属性的聚合效果:
contain: strict
:同时开启 layout、style、paint 以及 size 的功能,它相当于contain: size layout paint
contain: content
:同时开启 layout、style 以及 paint 的功能,它相当于contain: layout paint
所以,这里也提一下,contain 属性是可以同时定义几个的。
Can i Use -- CSS Contain
截止至 2021-04-27,Can i Use 上的 CSS Contain 兼容性,已经可以开始使用起来:
参考文献
最后
好了,本文到此结束,希望对你有帮助 :)
更多精彩 CSS 技术文章汇总在我的 Github -- iCSS ,持续更新,欢迎点个 star 订阅收藏。
如果还有什么疑问或者建议,可以多多交流,原创文章,文笔有限,才疏学浅,文中若有不正之处,万望告知。
The text was updated successfully, but these errors were encountered: