z-index只对非static定位元素生效,需配合position: relative/absolute/fixed/sticky使用;其层级受堆叠上下文限制,父级创建新上下文后子元素z-index仅在内部有效。

z-index只对定位元素生效
给一个 div 写了 z-index: 999 却没效果?八成是因为漏了 position。z-index 完全不认 position: static(也就是默认状态),哪怕你写了也等于没写。
必须显式设置 position 为以下之一才起作用:
-
position: relative—— 最常用,不脱离文档流,适合微调位置+控层级 -
position: absolute或position: fixed—— 脱离流,常用于弹窗、提示层 -
position: sticky—— 滚动时粘住,也支持z-index
错误写法:div { z-index: 10; }(无 position)→ 浏览器直接忽略。
z-index不是全局数字比大小
两个元素 z-index 分别是 100 和 1,但小的那个反而盖在上面?问题不在数值,而在「堆叠上下文」(stacking context)。
只要父容器满足以下任一条件,就会创建独立的堆叠上下文:
-
position不是static且z-index为具体数值(包括 0) -
opacity小于 1 -
transform不是none -
will-change设为某些值
一旦父级创建了新上下文,子元素的 z-index 只在它内部有效;跨上下文比较毫无意义。比如两个弹窗分别属于不同 position: relative 的父容器,谁在上,取决于父容器自身的 z-index,而不是它们内部子元素的数值。
HTML结构本身决定默认层级顺序
没设 z-index 的定位元素,按 HTML 中的书写顺序渲染:后出现的盖在先出现的上面。
非定位元素(position: static)完全不参与 z-index 排序,它们始终处于「auto 层级」,默认在所有定位元素之下(除非父级堆叠上下文被压低)。
注意几个典型场景:
-
z-index: -1的定位元素会被同级非定位元素盖住(因为后者在 auto 层,而 -1 在更下层) - 父元素
z-index很高,但子元素没设position→ 子元素不受控,层级由其自身是否定位决定 -
body上直接加z-index无效,因为body默认position: static
main / section / article 这些标签不控制视觉层级
别被“层级”这个词带偏:<main></main>、<section></section>、<article></article> 是语义标签,影响的是 DOM 结构、辅助技术识别和 SEO,**不改变 CSS 堆叠顺序**。
它们不会自动创建堆叠上下文,也不等价于加了 z-index。想让某个 <section></section> 浮在其他内容上,仍然得手动加 position 和 z-index。
真正容易被忽略的点是:这些语义标签一旦被加上 position + z-index,就可能意外创建堆叠上下文——进而把里面所有子元素拖进一个新的局部层级体系里。调试时如果发现某块区域内的元素突然“不听使唤”,先查它的最近定位父级有没有悄悄建了上下文。
前端入门到VUE实战笔记:立即使用
在学习笔记中,你将探索 前端 的入门与实战技巧!











