提起,z-index 你们脑海里可能会马上浮现这样的知识点:“z-index 的值大小控制元素在 Z 轴上显示的层级,z-index 越大显示的层级越高(也就是在最上层,离观察者越近),没有指定的按照出现顺序堆叠,此外 z-index 不能跨父元素比较。css
z-index 的使用彷佛就是这么简单,对吧?前端
咱们先看以下例 1:web
<div class="box box1">DIV#1,z-index为2</div>
<div class="box box2">DIV#2,z-index为auto</div>
复制代码
HTML 中有以下两个元素,DIV#1 的 z-index 为2
,DIV#2 向右向上偏移。问:它们谁会显示在上面?app
点击 CSS的“层”峦“叠”翠 - 示例1 - 用法导引 进行编辑 (@verymuch) on CodePen. 编辑器
如上所示,z-index 为 2 的元素并无显示在第二个元素上面。这彷佛很奇怪,那究竟是为何呢?wordpress
若是你也对此存在困扰,那就和我一块儿往下看吧。笔者将逐步引导你们深刻理解 z-index 的用法。布局
首先,咱们先了解下默认状况下,元素的堆叠,即在没有使用 z-index 时,元素是如何堆叠的。flex
若是没有给任何元素指定 z-index,则元素按照以下顺序进行堆叠(由下到上,由远及近)。spa
注:定位的元素即为 position 的值不是 static 的元素code
点击 CSS的“层”峦“叠”翠 - 示例2 - 无z-index时的默认堆叠 进行编辑 (@verymuch) on CodePen.
如上例 2 所示,定位的元素(DIV#一、DIV#二、DIV#3 与 DIV#4)按照出现的顺序堆叠。非定位的元素(DIV#5 与 DIV#6)虽然出如今后面,可是会被定位的元素遮盖,不过它们自己是按照出现顺序堆叠的。
注意,当使用order
属性改变flex
元素子元素的出现顺序时,对于堆叠规则也有一样的影响。
以下例 3 所示,当将 DIV#2 的 order 改成-1 后,它出现的位置为第一个,其堆叠顺序也被 DIV#1 所遮盖。
点击 CSS的“层”峦“叠”翠 - 示例3 - flex中order对出现顺序的影响 进行编辑 (@verymuch) on CodePen.
若是存在浮动块,浮动块的堆叠顺序会介于无定位元素和定位元素之间。即:
咱们稍微修改下示例 2 中的代码,将 DIV#1 和 DIV#3 改成浮动元素。能够看到以下例 4 所示,浮动元素的堆叠顺序高于非定位元素,低于定位元素。
点击 CSS的“层”峦“叠”翠 - 示例4 - 浮动块的堆叠 进行编辑 (@verymuch) on CodePen.
此外,还有一点小改动,不知道你有没有注意到,咱们将非定位元素中的文本内容改成了左对齐,但其内容并无被浮动元素覆盖。这实际上是浮动元素的标准效果——环绕效果。这一行为也能够列为堆叠顺序之一。顺序以下:
为了让你们清晰的理解上面所说的非定位元素的后代行内元素。你们能够看下例 5。DIV#1 为浮动元素,因此其层级高于在其后出现的 DIV#2。此时 DIV#1 向右偏移,能够看见 DIV#2 中的行内文字元素(能够为纯文字节点)层级高于 DIV#1。
点击 CSS的“层”峦“叠”翠 - 示例5 - 非定位元素的后代行内元素 进行编辑 (@verymuch) on CodePen.
以上是 CSS 中对于各种元素的默认排序,那咱们可否自定义排序呢?答案显然是确定的。使用 z-index 能够自定义堆叠顺序。
z-index 的值能够为整数(正数、负数、0 都可)。使用方法很简单。
须要注意如下三点:
以下例 6,咱们修改了例 2 中元素的 z-index。
咱们会发现 DIV#5 和 DIV#6 并不受 z-index 的影响。主要体如今两个方面,首先 DIV#5 的 z-index 大于 DIV#6,可是显示却低于#DIV#6;其次是 DIV#5 的 z-index 小于 DIV#4,可是仍显示在其上面。
而对于定位的元素,z-index 对其有影响,堆叠顺序与数字大小符合。
点击 CSS的“层”峦“叠”翠 - 示例6 - 使用z-index自定义堆叠顺序 进行编辑 (@verymuch) on CodePen.
好了,相信经过上述内容,你们对于 z-index 应该有了必定的了解,可是以上仅仅是基本知识,关于堆叠远远没有这么简单。
想要完全了解 z-index,咱们还要了解一下 CSS 堆叠的一个重要概念————堆叠上下文。
堆叠上下文是 HTML 中的三维概念,它抽象出了一个 z 轴,z 轴垂直于显示器,指向用户(假设用户面朝显示区域)。
在前面的内容中,之因此有些元素的渲染顺序会受到 z-index 影响,是由于它们都由于某种缘由产生了一个堆叠上下文,而不只仅是上文提到的定位的元素。
那么到底什么状况下会产生堆叠上下文呢?其实堆叠上下文的生成主要受到元素的属性所影响。
若是任何一个元素知足一下条件之一,就会生成一个堆叠上下文。
position
值为"absolute"或"relative",且 z-index 指定了除了 auto 之外值的元素
position
值为"fixed"或"sticky"
opacity
的值小于的元素
mix-blend-mode
的值不是
normal
的元素
isolation
值为"isolate"的元素
-webkit-overflow-scrolling
值为"touch"的元素
will-change
指定了除初始值之外的任何属性的元素
contain
值为"layout"/"paint"及含义其中之一的组合值的元素
如上所述,有 11 种状况会生成堆叠上下文,对于堆叠上下文能够经过 z-index 指定其堆叠的顺序(注意这里不是上面说的只对定位元素生效了)。
对于堆叠上下文咱们须要知道如下几点:
注意,第四条和文章开头提到的“z-index 不能跨父元素比较”是不等价的,由于其限制了必须是堆叠上下文。
针对这几点,咱们看一下例 7。你们能够先看一下是否理解。而后咱们再讲解一下。
点击 CSS的“层”峦“叠”翠 - 示例7 - 存在多级堆叠上下文时,元素的堆叠 进行编辑 (@verymuch) on CodePen.
示例 7 中,堆叠上下文的层级结构以下:
其中 DIV#4, DIV#5, DIV#6 是 DIV#2 的子元素,可见其堆叠顺序被限制在 DIV#2 中,z-index 的值只在 DIV#2 内部有效,而后 DIV#2 又做为一个总体与 DIV#1,DIV#3 按照上述规则进行堆叠。
DIV#7 被根元素同化,DIV#8 与 DIV#1, DIV#2, DIV#3 按照上述规则进行堆叠。在其三之上。
其实有个小方法可以帮助你们更好地判断如何堆叠,那就是把堆叠上下文的层级结构类比为版本号。以下:
如上,类比成版本号以后,咱们就能很方便的判断出谁上谁下啦。
z-index: 0
与z-index: auto
并不相同。一般状况下,相邻的两个元素,若是其 z-index 值分别为0
和auto
,看上去没什么区别的。以下例 8 所示。
DIV#1 的 z-index 值为 0,其堆叠顺序并无高于 DIV#2,而是和出现顺序相同。
点击 CSS的“层”峦“叠”翠 - 示例8 - zindex: 0 和 auto 的区别 进行编辑 (@verymuch) on CodePen.
可是实际上,这两种状况并不相同。上面提到,当元素“position
值为"absolute"或"relative",且 z-index 指定了除了 auto 之外值”时,元素会产生一个堆叠上下文,虽然元素自己堆叠顺序没有影响,可是其子元素的堆叠顺序会有影响。以下例 9 所示。
由于 DIV#1 的 z-index 值不为 auto,其产生了堆叠上下文,因此其子元素被限制在其内部,低于 DIV#2(若是 z-index 是 auto 的话,DIV#3 会高与 DIV#2)。
点击 CSS的“层”峦“叠”翠 - 示例9 - zindex: 0 和 auto 的区别(2) 进行编辑 (@verymuch) on CodePen.
z-index
,将堆叠上下文的层级结构打平笔者之因此这样建议,是由于当堆叠上下文的层级结构比较复杂时,简单的修改某个元素的 z-index 或者其余属性,会致使一些没法预知的影响。
以下例时所示,DIV#2 是 DIV#1 的子元素,DIV#4 是 DIV#3 的子元素,DIV#1 和 DIV#3 不是堆叠上下文,则 DIV#2 与 DIV#4 的堆叠顺序与它们的 z-index 值对应。
点击 CSS的“层”峦“叠”翠 - 示例10 - zindex形成的影响 进行编辑 (@verymuch) on CodePen.
但若是咱们在某些时候须要调整 DIV#3 的 z-index,如将其调整成z-index: 4;
,那么结果就彻底不同了。以下例 11 所示,DIV#4 高于 DIV#2 了。
See the Pen CSS的“层”峦“叠”翠 - 示例11 - zindex形成的影响(2) by verymuch (@verymuch) on CodePen.
因此笔者建议,你们必定要慎用,基于对堆叠上下文的理解基础上,把握好页面中堆叠上下文的层级结构,尽可能保持比较浅的层级结构,最好能与 HTML 层级结构一致,保证本身可以时刻知道如何进行修改与调整。
以上,笔者从元素的默认堆叠顺序,讲到了堆叠上下文的生成。对上述内容了解以后,就可以很好地应对开发中所遇到的层级问题了。不过仍是建议你们在开发前,提早规划好 z-index 的使用。避免最后本身没法掌控。
若是你喜欢,欢迎扫码关注个人公众号,我会按期陪读,并分享一些其余的前端知识。