問題描述
我有一個項目,我在本地使用影子 DOM(而不是通過 polyfill).我想檢測給定的 element
是否包含在 shadow DOM 或 light DOM 中.
我查看了元素的所有屬性,但似乎沒有任何根據(jù)元素所在的 DOM 類型而有所不同.
如何確定一個元素是陰影 DOM 還是光 DOM 的一部分?
<小時>以下是出于本問題的目的被認(rèn)為是shadow DOM"和light DOM"的示例.
<上一頁>(輕根) ? 文檔(淺色) ? HTML(光) |? 身體(光) |? DIV(影根) |? 影子根(影子)|? 分區(qū)(影子)|? 框架(輕根) |? 文檔(光) |? HTML(光) ||? 身體(光) ||? 分區(qū)(影根) ||? 影子根(影子)||? 分區(qū)(無)|? [第二個文檔的未附加 DIV](無) ? [第一個文檔的未附加 DIV]<!doctype html><標(biāo)題>isInShadow() 測試文檔 - 無法在 Stack Exchange 的沙箱中運(yùn)行</標(biāo)題><iframe src="about:blank"></iframe><腳本>函數(shù)isInShadow(元素){//去做}功能測試() {//(輕根) ? 文檔//(淺色) ? HTMLvar html = document.documentElement;console.assert(isInShadow(html) === false);//(光)|? 身體var body = document.body;console.assert(isInShadow(body) === false);//(光)|? DIVvar div = document.createElement('div');body.appendChild(div);console.assert(isInShadow(div) === false);//(影子根) |? 影子根var divShadow = div.createShadowRoot();var shadowDiv = document.createElement('div');divShadow.appendChild(shadowDiv);//(陰影) |? 分區(qū)console.assert(isInShadow(shadowDiv) === true);//(陰影) |? 框架var iframe = document.querySelector('iframe');shadowDiv.appendChild(iframe);console.assert(isInShadow(iframe) === true);//(輕根) |? 文檔var iframeDocument = iframe.contentWindow.document;//(光)|? HTMLvar iframeHtml = iframeDocument.documentElement;console.assert(isInShadow(iframeHtml) === false);//(光)||? 身體var iframeBody = iframeDocument.body;//console.assert(isInShadow(iframeHtml) === false);//(光)||? 分區(qū)var iframeDiv = iframeDocument.createElement('div');iframeBody.appendChild(iframeDiv);console.assert(isInShadow(iframeDiv) === false);//(影子根) ||? 影子根var iframeDivShadow = iframeDiv.createShadowRoot();//(陰影) ||? 分區(qū)var iframeDivShadowDiv = iframeDocument.createElement('div');iframeDivShadow.appendChild(iframeDivShadowDiv);console.assert(isInShadow(iframeDivShadowDiv) === true);//(無) |? [第二個文檔的未附加 DIV]var iframeUnattached = iframeDocument.createElement('div');console.assert(Boolean(isInShadow(iframeUnattached)) === false);//(無) ? [第一個文檔的未附加 DIV]var rootUnattached = document.createElement('div');console.assert(Boolean(isInShadow(rootUnattached)) === false);}加載 = 函數(shù) main() {console.group('測試');嘗試 {測試();console.log('測試完成.');} 最后 {控制臺.groupEnd();}}</script>
如果調(diào)用ShadowRoot的toString()
方法,會返回"[object ShadowRoot]"
.根據(jù)這個事實,這是我的方法:
function isInShadow(node) {var parent = (node && node.parentNode);而(父){if(parent.toString() === "[object ShadowRoot]") {返回真;}父 = 父節(jié)點;}返回假;}
<小時>
編輯
Jeremy Banks 提出了另一種循環(huán)方式的方法.這種方法和我的有點不同:它還會檢查傳遞的節(jié)點本身,而我沒有這樣做.
function isInShadow(node) {for (; node; node = node.parentNode) {if (node.toString() === "[object ShadowRoot]") {返回真;}}返回假;}
function isInShadow(node) {for (; node; node = node.parentNode) {if (node.toString() === "[object ShadowRoot]") {返回真;}}返回假;}console.group('測試');var lightElement = document.querySelector('div');console.assert(isInShadow(lightElement) === false);var shadowChild = document.createElement('div');lightElement.createShadowRoot().appendChild(shadowChild);console.assert(isInShadow(shadowChild) === true);var orphanedElement = document.createElement('div');console.assert(isInShadow(orphanedElement) === false);var orphanedShadowChild = document.createElement('div');orphanedElement.createShadowRoot().appendChild(orphanedShadowChild);console.assert(isInShadow(orphanedShadowChild) === true);var fragmentChild = document.createElement('div');document.createDocumentFragment().appendChild(fragmentChild);console.assert(isInShadow(fragmentChild) === false);console.log('完成.');console.groupEnd();
<div></div>
I have a project where I'm using the shadow DOM natively (not through a polyfill). I'd like to detect if a given element
is contained within a shadow DOM or a light DOM.
I've looked through all of the properties on the elements, but there don't seem to be any which vary based on the type of DOM an element is in.
How can I determine if an element is part of a shadow DOM or a light DOM?
Here is an example of what is considered "shadow DOM" and "light DOM" for the purpose of this question.
(light root) ? Document (light) ? HTML (light) | ? BODY (light) | ??DIV (shadow root) | ? ShadowRoot (shadow) | ? DIV (shadow) | ? IFRAME (light root) | ? Document (light) | ? HTML (light) | | ? BODY (light) | | ? DIV (shadow root) | | ? ShadowRoot (shadow) | | ? DIV (none) | ? [Unattached DIV of second Document] (none) ? [Unattached DIV of first Document]
<!doctype html>
<title>
isInShadow() test document - can not run in Stack Exchange's sandbox
</title>
<iframe src="about:blank"></iframe>
<script>
function isInShadow(element) {
// TODO
}
function test() {
// (light root) ? Document
// (light) ? HTML
var html = document.documentElement;
console.assert(isInShadow(html) === false);
// (light) | ? BODY
var body = document.body;
console.assert(isInShadow(body) === false);
// (light) | ??DIV
var div = document.createElement('div');
body.appendChild(div);
console.assert(isInShadow(div) === false);
// (shadow root) | ? ShadowRoot
var divShadow = div.createShadowRoot();
var shadowDiv = document.createElement('div');
divShadow.appendChild(shadowDiv);
// (shadow) | ? DIV
console.assert(isInShadow(shadowDiv) === true);
// (shadow) | ? IFRAME
var iframe = document.querySelector('iframe');
shadowDiv.appendChild(iframe);
console.assert(isInShadow(iframe) === true);
// (light root) | ? Document
var iframeDocument = iframe.contentWindow.document;
// (light) | ? HTML
var iframeHtml = iframeDocument.documentElement;
console.assert(isInShadow(iframeHtml) === false);
// (light) | | ? BODY
var iframeBody = iframeDocument.body;
//
console.assert(isInShadow(iframeHtml) === false);
// (light) | | ? DIV
var iframeDiv = iframeDocument.createElement('div');
iframeBody.appendChild(iframeDiv);
console.assert(isInShadow(iframeDiv) === false);
// (shadow root) | | ? ShadowRoot
var iframeDivShadow = iframeDiv.createShadowRoot();
// (shadow) | | ? DIV
var iframeDivShadowDiv = iframeDocument.createElement('div');
iframeDivShadow.appendChild(iframeDivShadowDiv);
console.assert(isInShadow(iframeDivShadowDiv) === true);
// (none) | ? [Unattached DIV of second Document]
var iframeUnattached = iframeDocument.createElement('div');
console.assert(Boolean(isInShadow(iframeUnattached)) === false);
// (none) ? [Unattached DIV of first Document]
var rootUnattached = document.createElement('div');
console.assert(Boolean(isInShadow(rootUnattached)) === false);
}
onload = function main() {
console.group('Testing');
try {
test();
console.log('Testing complete.');
} finally {
console.groupEnd();
}
}
</script>
If you call a ShadowRoot's toString()
method, it will return "[object ShadowRoot]"
. According to this fact, here's my approach:
function isInShadow(node) {
var parent = (node && node.parentNode);
while(parent) {
if(parent.toString() === "[object ShadowRoot]") {
return true;
}
parent = parent.parentNode;
}
return false;
}
EDIT
Jeremy Banks suggests an approach in another style of looping. This approach is a little different from mine: it also checks the passed node itself, which I didn't do.
function isInShadow(node) {
for (; node; node = node.parentNode) {
if (node.toString() === "[object ShadowRoot]") {
return true;
}
}
return false;
}
function isInShadow(node) {
for (; node; node = node.parentNode) {
if (node.toString() === "[object ShadowRoot]") {
return true;
}
}
return false;
}
console.group('Testing');
var lightElement = document.querySelector('div');
console.assert(isInShadow(lightElement) === false);
var shadowChild = document.createElement('div');
lightElement.createShadowRoot().appendChild(shadowChild);
console.assert(isInShadow(shadowChild) === true);
var orphanedElement = document.createElement('div');
console.assert(isInShadow(orphanedElement) === false);
var orphanedShadowChild = document.createElement('div');
orphanedElement.createShadowRoot().appendChild(orphanedShadowChild);
console.assert(isInShadow(orphanedShadowChild) === true);
var fragmentChild = document.createElement('div');
document.createDocumentFragment().appendChild(fragmentChild);
console.assert(isInShadow(fragmentChild) === false);
console.log('Complete.');
console.groupEnd();
<div></div>
這篇關(guān)于如何判斷一個元素是否在影子 DOM 中?的文章就介紹到這了,希望我們推薦的答案對大家有所幫助,也希望大家多多支持html5模板網(wǎng)!