javascript - 自定义元素 getRootNode.closest() 函数跨越多个(父)shadowDOM 边界

标签 javascript shadow-dom custom-element native-web-component

我花了一些时间进行搜索,但只看到太多常规的“遍历 DOM”博客或答案,这些博客或答案仅比 getRootnode()一个级别

伪代码:

HTML

<element-x>
//# shadow-root
    <element-y>
        <element-z>
        //# shadow-root
        let container = this.closest('element-x');
        </element-z>
    </element-y>
</element-x>

标准element.closest()函数穿透阴影边界;

所以 this.closest('element-x')返回 null因为没有没有 <element-x><element-z> 内shadowDom

目标:

查找<element-x>来自后代 <element z> (任何嵌套级别)

必需:

A(递归).closest()遍历 (shadow) DOMs 并找到 <element-x> 的函数

注意:元素可能有也可能没有 ShadowDOM(参见 <element y>:仅 lightDOM)

我明天可以而且会自己做;只是想知道是否有聪明的头脑已经做到了。

资源:

更新

这是来自以下答案的未压缩代码:

        closestElement(selector, base = this) {
            function __closestFrom(el) {
                if (!el || el === document || el === window) return null;
                let found = el.closest(selector);
                if (found)
                  return found;
                else
                  __closestFrom(el.getRootNode().host);
            }

            return __closestFrom(base);
        }

更新 #2

我将它更改为我的 BaseElement 上的一个方法:

  closestElement(selector, el = this) {
    return (
      (el && el != document && el != window && el.closest(selector)) ||
      this.closestElement(selector, el.getRootNode().host)
    );
  }

事件

如 Intervalia 评论;是的,事件是另一种解决方案。
但是……一个事件需要附加到一个祖先……如何知道要使用哪个祖先?

最佳答案

这与 .closest() 相同从任何子(影子)DOM 中

但是沿着 DOM 走穿越 shadowroot 边界

针对(极端)缩小进行了优化

//declared as method on a Custom Element:
closestElement(
    selector,      // selector like in .closest()
    base = this,   // extra functionality to skip a parent
    __Closest = (el, found = el && el.closest(selector)) => 
        !el || el === document || el === window
            ? null // standard .closest() returns null for non-found selectors also
            : found 
                ? found // found a selector INside this element
                : __Closest(el.getRootNode().host) // recursion!! break out to parent DOM
) {
    return __Closest(base);
}

注意:__Closest 函数被声明为“参数”以避免额外的 let 声明...更适合缩小,并防止您的 IDE 报错

从自定义元素内部调用:

<element-x>
//# shadow-root
    <element-y>
        <element-z>
        //# shadow-root
        let container = this.closestElement('element-x');
        </element-z>
    </element-y>
</element-x>

关于javascript - 自定义元素 getRootNode.closest() 函数跨越多个(父)shadowDOM 边界,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/54520554/

相关文章:

javascript - JavaScript 中的 Font Awesome 错误 : Uncaught SyntaxError: Unexpected identifier ​

javascript - 如何动态包含样式表以应用于 Polymer 2 元素?

html - 隔离 WebComponent JS 库

javascript - 自定义元素和 connectedCallback() : wait for parent node to be available before firing a function

javascript - 与自定义 HTML 元素共享样式?

javascript - 滑出侧工具栏

javascript - 遍历 html 表

javascript - Angular 1 按钮而不是 3

javascript - 如何在 Shadow DOM 上应用样式

ecmascript-6 - 如何为 Polymer 2 创建自定义元素 "resize"mixin?