Jam*_*lly 29 javascript html5 web-component shadow-dom
这个问题更多的是针对用户创建的shadow DOM元素,但是对于可访问性,我将使用date输入类型来解决这个问题:
比方说,date我的页面上有一个输入.编辑完几个位后,阴影DOM标记(使用Chrome)看起来像:
<input type="date">
#document-fragment
<div pseudo="-webkit-datetime-edit">
<div pseudo="-webkit-datetime-edit-fields-wrapper">
<span role="spinbutton">dd</span>
<div pseudo="-webkit-datetime-edit-text">/</div>
<span role="spinbutton">mm</span>
<div pseudo="-webkit-datetime-edit-text">/</div>
<span role="spinbutton">yyyy</span>
</div>
</div>
<div></div>
<div pseudo="-webkit-calendar-picker-indicator"></div>
Run Code Online (Sandbox Code Playgroud)
与date输入相关的方法和属性似乎根本没有引用shadow DOM(JSFiddle),所以我想知道如何(如果有的话)可以访问这些shadow DOM元素?
Cle*_*usW 18
date根据定义,Shadow DOM是一种用DOM填充节点的方法,你想要从外部源中隐藏(Encapsulation).关键是你作为组件的作者可以准确地选择哪些部分将暴露给外部CSS或JavaScript,哪些不会.
遗憾的是,如果不使用另一个名为Custom Elements的前沿规范,则无法为Shadow DOM创建公共JavaScript界面.如果您选择这样做,就像向元素的原型添加自定义公共方法一样简单.从这些中,您可以访问Shadow DOM的内部(请参阅此处的第三个示例).
但是,您可以为CSS公开挂钩,以便在不使用自定义元素的情况下访问Shadow DOM的内部.有两种方法可以做到这一点:
Chrome和Firefox通过特殊的伪元素将其Shadow DOM的某些部分暴露给CSS.这是您-webkit-datetime-edit输入的示例,其中添加了一条CSS规则,该规则仅通过使用Chrome提供的Show Shadow DOM伪元素应用于日期字段的数字部分.
这是可用的WebKit伪元素的部分列表.您也pseudo可以在DevTools中启用该选项并查找名为的属性Enable experimental WebKit features.
组件作者还可以创建自己的伪元素以暴露其Shadow DOM的部分(请参阅此处的第2个示例).
一个更好的方法是使用CSS变量,你可以启用about:flags在dateChrome浏览器.然后看看这个小提琴,它使用CSS变量向Shadow DOM传达它应该用于"主题"的颜色.
Sup*_*arp 17
现在(2016)您可以使用Shadow DOM根目录上的方法访问开放的用户创建的 shadow DOM元素(但没有用户代理创建的shadow DOM!)querySelector:
<body>
<div id="container"></div>
<script>
//Shadow Root
?v?a?r? ?r?o?o?t? ?=? ?c?o?n?t?a?i?n?e?r?.?c?r?e?a?t?e?S?h?a?d?o?w?R?o?o?t?(?)?
//new syntax:
var root = container.attachShadow( { mode: "open" } )
//Inside element
var span = document.createElement( "span" )
span.textContent = "i'm inside the Shadow DOM"
span.id = "inside"
root.appendChild( span )
//Access inside element
console.log( container.shadowRoot.querySelector( "#inside" ) )
</script>
</body>
Run Code Online (Sandbox Code Playgroud)
//Shadow Root
var root = container.createShadowRoot()
//Inside element
var span = document.createElement( "span" )
span.textContent = "i'm inside the Shadow DOM"
span.id = "inside"
root.appendChild( span )
//Access inside element
function get()
{
alert( container.shadowRoot.querySelector( "#inside" ).id )
}Run Code Online (Sandbox Code Playgroud)
<!DOCTYPE html>
<html>
<head>
<title></title>
<meta charset="utf-8" />
</head>
<body>
<div id="container"></div>
<button onclick="get()">Get</button>
<script>
</script>
</body>
</html>Run Code Online (Sandbox Code Playgroud)
是的。您只需调用 .root 或 .shadowRoot 即可。这是一个例子,
document.getElementById('itemId').root
Run Code Online (Sandbox Code Playgroud)
如果父 dom 元素上没有innerText或innerHTML,您将无法获得影子dom元素。