什么是:: content / :: slotted伪元素,它是如何工作的?
这对于Google来说是不可能的,因为每篇文章都谈到:before
和:after
伪元素似乎都使用了“内容”这个词。
我在这篇 CSS-Tricks文章中听说过它,解释了如何实现图像滑块作为Web组件的示例用例。 它出现在内部的代码示例是这样的:
CSS
#slides ::content img { width: 25%; float: left; }
HTML
<template> ... <div class="inner"> <content select="img"></content> </div> </template>
它似乎是指这个<content>
标记,它用于允许用户包含Web组件,但是我更想深入了解这一点。
编辑:
在进一步阅读之后,在前面的文章中,我发现了一个链接作者的“Shadow DOM CSS Cheatsheet”,其中包含一段解释::content
伪元素的内容:
select元素内部的分布式节点。 需要与不支持本地select器的浏览器的polyfill-next-selector配合使用。
::content h1 { color: red; }
资料来源: http : //robdodson.me/blog/2014/04/10/shadow-dom-css-cheat-sheet/
这是有帮助的,但我仍然觉得整个事情是不透明的。 任何额外的见解?
::content
伪元素在将来的Web Components / Shadow DOM实现中将被replace为::slotted
。 同样,在最新版本的Shadow DOM规范中 ,此伪元素所针对的元素已从<content
>更改为<slot
>。 你可以在这里看到有关这个变化的相关讨论。
目前浏览器仍然支持<content>
和::content
。
原始答案:
概要:
::content
从本质上来说是一种深入挖掘ShadowHost
后代的ShadowHost
,通常不能用于风格化,因为你的CSS不知道在没有::content
情况下寻找ShadowDOM片段。
这个答案假设您至less对<template>
元素和Web组件 (特别是ShadowDOM)熟悉 ,它处理ShadowTree
及其两个主要元素ShadowHost
和ShadowRoot
。
注意 – 在撰写本文时,五大浏览器中对于Web组件的支持不足50%(甚至是前缀默认支持)。 虽然所有现代浏览器都支持<template>
,但只有最新版本的Chrome和Opera才支持ShadowDOM; 在Firefox的about:config
( dom.webcomponents.enabled
)中将必要的function切换为true之后,Firefox会支持它的dom.webcomponents.enabled
。
使用ShadowDOM
的目标类似于MVC的关注点分离 。 也就是说,我们希望将我们的内容与我们的演示文稿分开,并允许在我们的代码中封装模板,以使其更易于pipe理。 我们已经有了各种编程语言,但是在HTML和CSS中这个问题还是有一段时间了。 此外,在Web应用程序中对元素进行样式化时,可能会与类名称发生冲突。
通常情况下,我们与LightDOM
(一种“Light Realm”)进行交互,但是有时利用封装会有所帮助。 进入这种“影子领域”(Web组件的一部分)是一种通过允许封装来防止上述问题的新方法。 即使使用完全相同的类或select器,在ShadowTree
应用于标记的任何样式也不适用于标记。
当ShadowTree
(它位于ShadowDOM
)中有一个来自LightDOM
分布在树内的树,或者当ShadowTree
被渲染时,结果被浏览器转换成所谓的组合树 。
当浏览器呈现您的代码时,内容将被分发并插入新的位置, 而不是物理input的位置。 这个分布式输出就是你所看到的(以及浏览器所看到的),被称为composed tree
。 实际上,内容并不是按照它现在出现的顺序input的,但是你不会知道这一点,浏览器也不会。 如果你愿意,“最终结果”和“原始代码”之间的这种分离是封装的主要优点之一。
Web组件和CSS的未来是一个伟大的40分钟的Web组件的video,特别是ShadowDOM,由ZachSaucier指出。
具体到你的问题, ::content
伪元素适用于所谓的分布式节点 。 分布式节点是放在<content></content>
标记中的任何一个词。 内容将从原始标记中的位置分发到您将模板中的<content>
标记放置到的任何位置。
所以,当你在CSS中需要特殊性的时候,你可以正常处理select器的一种方法就是去父元素并将其作为select器的一部分join。 例如:如果.container {}
不够具体,可以使用div .container {}
或.main .container {}
来使select器工作。
考虑到ShadowDOM(这是范围和封装)的重点,你必须认识到,你创build的这个新的ShadowTree是一个全新的(离散的)DOM片段。 它和其他内容不在同一个“光之境界”中; 它在一个“阴影领域”。 那么,CSS如何知道这个“暗影领域”呢? 通过使用::content
伪元素!
::content
伪元素select器充当分布式节点的父元素。
HTML5Rocks 在这里有一个很好的教程序列, 这里覆盖更多的信息,并给出一些很好的例子(一定要使用Chrome或Opera访问,直到更多的浏览器支持这些function)。
例如,请参阅由HTML5Rocks修改并改进(由Leo )的代码版本:
var div = document.querySelector('div'); var root = div.createShadowRoot(); var template = document.querySelector('template'); root.appendChild(template.content);
<template> <style> h3 { color: red; } content[select="h3"]::content > h3 { color: green; } ::content section p { text-decoration: underline; } </style> <h3>Shadow DOM</h3> <content select="h3"></content> <content select="section"></content> </template> <div> <h3>Light DOM</h3> <section> <div>I'm not underlined</div> <p>I'm underlined in Shadow DOM!</p> </section> </div>
太糟糕了! 不幸的是::content
是v0 ,并被弃用。
你现在应该使用v1 ::slotted
。
此外, <content>
已被弃用,以支持<slot>
。
请参阅: http : //hayato.io/2016/shadowdomv1/
另请参阅: Web组件 – 为什么将<内容>replace为<插槽>