CSS 播客 - 019:Z-index 和堆叠上下文
假设您有几个元素已绝对定位,且本应位于彼此上方。您可能会像下面这样编写一些 HTML 代码:
<div class="stacked-items">
<div class="item-1">Item 1</div>
<div class="item-2">Item 2</div>
</div>
但默认情况下,哪一个会叠放在另一个上? 如需知道哪个项会执行此操作,您需要了解 Z-index 和堆叠上下文。
Z-index
z-index
属性可基于浏览器的 3D 空间(Z 轴)明确设置 HTML 的图层顺序。这条轴表示哪些图层离您更近一些,哪些图层离您更远。Web 上的纵轴是 Y 轴,横轴是 X 轴。
z-index
属性接受数值,可以是正数,也可以是负数。如果元素的 z-index
值较高,它们将显示在另一个元素上方。如果元素上未设置 z-index
,则默认行为是文档来源顺序决定 Z 轴。也就是说,文档靠下的元素会位于在其前面显示的元素之上。
在普通流程中,如果您为 z-index
设置了特定值但该值不起作用,则需将该元素的 position
值设置为 static
以外的任何值。这是人们与 z-index
斗争的常见地方。
不过,在 Flexbox 或网格环境中则并非如此,因为您无需添加 position: relative
即可修改 flex 或网格项的 Z-index。
Z-index 为负
如需将某个元素设置为位于另一个元素的后面,请为 z-index
添加一个负值。
.my-element {
background: rgb(232 240 254 / 0.4);
}
.my-element .child {
position: relative;
z-index: -1;
}
只要 .my-element
的 z-index
的初始值为 auto
,.child
元素就会位于其后面。
将以下 CSS 添加到 .my-element
,这样 .child
元素就不会位于其后面了。
.my-element {
position: relative;
z-index: 0;
background: rgb(232 240 254 / 0.4);
}
由于 .my-element
现在的 position
值不是 static
,z-index
值不是 auto
,因此它创建了新的堆叠上下文。这意味着,即使将 .child
的 z-index
设置为 -999
,它也不会位于 .my-parent
之后。
叠加上下文
堆叠上下文是一组具有共同父项的元素,并一起沿 z 轴上下移动。
在此示例中,第一个父元素的 z-index
为 1
,因此系统会创建一个新的堆叠上下文。
其子元素的 z-index
为 999
。此父元素旁边还有另一个父元素,该父元素包含一个子元素。父元素的 z-index
为 2
,子元素的 z-index
也为 2
。由于两个父项都会创建堆叠上下文,因此所有子项的 z-index
均基于其父项的上下文。
堆叠上下文内元素的 z-index
始终相对于父项在其自己的堆叠上下文中的当前顺序。
创建堆叠上下文
您无需应用 z-index
和 position
即可创建新的堆叠上下文。您可以通过为用于创建新的复合层(如 opacity
、will-change
和 transform
)的属性添加值来创建新的堆叠上下文。您可以在此处查看完整的属性列表。
为了解释复合层是什么,我们先假设网页是一张画布。浏览器会获取您的 HTML 和 CSS 并使用这些信息来计算画布的大小。 然后,它会在该画布上绘制页面。 如果要更改某个元素(例如,它的位置发生变化),浏览器必须返回并重新确定要绘制的内容。
为提高性能,浏览器会创建新的复合图层,这些图层叠加在画布之上。这有点像便利贴:四处移动并更改它对整体画布没有太大影响。系统会为具有 opacity
、transform
和 will-change
的元素创建新的复合图层,因为这些元素很可能会发生变化,因此浏览器会使用 GPU 应用样式调整,确保更改的效果尽可能好。
资源
检查您的掌握程度
测试您对 Z-index 知识的掌握情况
<section> <article>1</article> <article>2</article> <article>3</article> <article>4</article> </section>
哪篇文章默认显示在顶部?
如果 Z-index 不起作用,您应该检查元素的哪个属性?
display
relative
position
static
以外的值。animation
Flexbox 和网格是否需要 position: relative
?
position: relative
即可在 Flexbox 或网格布局中使用 Z-index。