为什么默认情况下,文本节点会呈现在其父级 ::before 下方?

And*_*hiu 3 css z-index pseudo-element

在写关于 SO 的另一个问题的答案时,我制作了以下片段:

@import url('https://fonts.googleapis.com/css?family=Shadows+Into+Light');

/* relevant CSS */
div {
  position: relative;
}

div::before {
  content: '';
  position: absolute;
  top: 0; left:0;
}
div>span {
  position:relative;
  z-index:0;
}

/* rest is just styling - should be irrelevant for the question */


div {
  font: normal normal normal 2rem/1 'Shadows Into Light', cursive;
  color: white;
  text-align:center;
  margin: 1rem;
  padding: 1rem;
  min-width: 15rem;
  cursor: pointer;
}
div::before {
  width: 100%;
  height: 100%;
  opacity: 1;
  transition: opacity .3s cubic-bezier(.4,0,.2,1);
  background-color: #bada55;
  border-radius: .4rem;
}
div[orange]:before {
  background-color: #f50;
}
div:hover::before {
  opacity:.65;
}

body {
  margin: 0; padding: 0;
}
center-me-please {
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  min-height: 100vh;
  background: transparent url(http://lorempixel.com/g/1200/800/fashion) no-repeat 50% 50% /cover;
}
Run Code Online (Sandbox Code Playgroud)
<center-me-please>
  
  <div><span>#bada55</span></div>
  <div orange>not so #bada55</div>
Run Code Online (Sandbox Code Playgroud)

我惊讶地发现该::before元素呈现在文本节点(橙色元素)之上,并且为了防止这种情况发生。我必须将文本节点包装在一个span元素中,并给它一个非负z-index和非静态position(#bada55 元素)。

经过检查,虽然该::before元素具有默认(预期)值z-index( auto),但文本节点似乎根本没有(或者至少 Chrome 无法显示它)。

到目前为止,我喜欢把自己想象成一个z-index小忍者,这个想法的部分支持是this toy为了帮助朋友和同事更好地理解堆叠上下文的原理和z-index一般情况。

正如您可能已经猜到的那样,我正在寻找关于为什么::before默认情况下不呈现在元素中其他所有内容下方的任何解释(它是第一个,因此在下面,对吧?)以及有关这是一个(已知?)错误的任何证据或预期(通过设计?)的行为。

我可能错过或误解的规范会很棒。

Bol*_*ock 6

::before 默认情况下绘制在文本内容下方 \xe2\x80\x94 ,默认情况是所有内容都未定位时

\n

但你的::before位置是绝对的。定位的盒子总是画在非定位的盒子前面。请参阅第 9.9.1 节(强调我的):

\n
\n

在每个堆叠上下文中,以下图层按从后到前的顺序绘制:

\n
    \n
  1. 形成堆叠上下文的元素的背景和边框。
  2. \n
  3. 具有负堆栈级别的子堆栈上下文(首先是最负的)。
  4. \n
  5. 流入、非内联级别、非定位后代。
  6. \n
  7. 非定位浮动。
  8. \n
  9. 流入、内联级、非定位后代,包括内联表和内联块。
  10. \n
  11. 堆栈级别为 0 的子堆栈上下文和堆栈级别为 0 的定位后代。
  12. \n
  13. 具有正堆栈级别的子堆栈上下文(首先是最不积极的)。
  14. \n
\n
\n

将文本内容包裹在定位中span会导致它按预期绘制在::before内容前面,因为这样您就有了两个按源顺序定位的框。

\n

  • @Andrei Gheorghiu:你总是可以在事后设置一个;) (2认同)