本文是我学习层叠上下文的总结。主要从以下途径学习:
MDN: https://developer.mozilla.org...
张鑫旭大大的博文:http://www.zhangxinxu.com/wor...
层叠顺序
层叠顺序遵循下图的规则,其中在张鑫旭大大的博文中提到inline-block的层叠顺序与图中inline box是一个level的;z-index:auto实际上和z-index:0单纯从层叠水平上
看,可以认为是同一level(两者在层叠上下文领域有着根本性的差异)。(如要看完整图片请移步到张鑫旭大大博文)
层叠准则
根据上图,层叠水平越大,就显示在越上面。
当层叠水平一样时,在DOM中位置越后,就显示在越上面。
层叠上下文的特性
层叠上下文的层叠水平比普通元素高;
层叠上下文可以嵌套,内部层叠上下文及其所有子元素都受限于外部的层叠上下文;
层叠上下文和兄弟元素独立,只需要考虑后代元素;
每个层叠上下文是自包含的:当元素的内容发生层叠后,整个该元素将会 在父层叠上下文中 按顺序进行层叠。
层叠上下文创建的条件
html元素
z-index的值不为auto的相对/绝对定位元素
position: fixed的元素
-
应用了某些CSS3的元素
z-index的值不为auto的flex项(即父元素display: flex | inline-flex)
opacity小于1的元素
transform值不为none元素
min-blend-mode值不为none的元素
filter值不为none的元素
perspective值不为none的元素
isloation值为isolate的元素
will-change指定了任意属性
-webkit-overflow-scrolling值为touch的元素
demo
先放MDN的例子的效果图(点击查看代码与效果)
下面是我自己写的一些demo,主要与z-index属性相关。
demo通用HTML代码
<div class="outter">outter
<div class="inner">inner</div>
</div>
基础CSS(没有创建层叠上下文)。所有demo都是在这份CSS的基础上写出来的。
.outter {
width: 200px;height: 300px;background: red;
}
.inner {
position: relative; z-index: -1;
width: 300px;height: 200px;background: blue;
}
当outter的position值为relative或absolute,并且不设置z-index值或者z-index值为auto时,outter没有创建层叠上下文。此时根据层叠顺序表,负的z-index元素在block元素下面,所以,inner被outter覆盖了。
查看demo
相对/绝对定位
.outter {
position: relative;z-index: auto;
width: 200px;height: 300px;background: red;
}
.inner {
position: relative; z-index: -1;
width: 300px;height: 200px;background: blue;
}
虽然outter的position值设置为absolute或者relative,但z-index值设置为auto,此时,outter并没有创建层叠上下文,所以,效果与基础demo一致。
查看demo
.outter {
position: relative;z-index: 0;
width: 200px;height: 300px;background: red;
}
.inner {
position: relative; z-index: -1;
width: 300px;height: 200px;background: blue;
}
当outter的z-index值设置为数值,甚至为0时,outter会创建层叠上下文,此时inner会覆盖outter。
查看demo
position: fixed的元素
.outter {
position: fixed;
width: 200px;height: 300px;background: red;color: #fff;
}
.inner {
position: relative;z-index: -1;
width: 300px;height: 200px;background: blue;
}
当outter的position值设置为fixed时,outter会创建层叠上下文,此时inner会覆盖outter。
查看demo
opacity小于1的元素
.outter {
opacity: .5;
width: 200px;height: 300px;background: red;color: #fff;
}
.inner {
position: relative;z-index: -1;
width: 300px;height: 200px;background: blue;
}
当outter的opacity值设置小于1时,outter会创建层叠上下文,此时inner会覆盖outter。
查看demo
transform值不为none元素
.outter {
transform: rotate(15deg);
width: 200px;height: 300px;background: red;color: #fff;
}
.inner {
position: relative;z-index: -1;
width: 300px;height: 200px;background: blue;
}
当outter的opacity值设置不为none时,outter会创建层叠上下文,此时inner会覆盖outter。
查看demo
will-change指定了任意属性
.outter {
will-change: transform;
width: 200px;height: 300px;background: red;color: #fff;
}
.inner {
position: relative;z-index: -1;
width: 300px;height: 200px;background: blue;
}
当outter的will-change值设置为任何值时,outter会创建层叠上下文,此时inner会覆盖outter。
查看demo
z-index的值不为auto的flex项(即父元素display: flex | inline-flex)
此处的HTML结构有点不同。
<div class="box">
<div class="outter">outter
<div class="inner">inner</div>
</div>
</div>
.box {
display: flex;
}
.outter {
z-index: 1;
width: 200px;height: 300px;background: red;color: #fff;
}
.inner {
position: relative;z-index: -1;
width: 300px;height: 200px;background: blue;
}
在原来的HTML外层加一个class为box的div,并设置display值为flex或者inline-flex,此时outter为flex项,会创建层叠上下文,此时inner会覆盖outter。
查看demo
其他
由于暂时对mix-blend-mode、filter、isolation、-webkit-overflow-scrolling属性了解不多,所以没有做demo。如果想看demo效果,可以看张鑫旭大大的博文。
结语
学习了层叠上下文之后,对于元素覆盖这个问题有了比较清晰的认识,有时候可以不依赖z-index来解决问题了。
**粗体** _斜体_ [链接](http://example.com) `代码` - 列表 > 引用
。你还可以使用@
来通知其他用户。