javascript七基础学习系列二千九百八十七:事件重定向

如果影子DOM 中发生了浏览器事件(如click),那么浏览器需要一种方式以让父DOM处理事件。
不过,实现也必须考虑影子DOM 的边界。为此,事件会逃出影子DOM 并经过事件重定向(event retarget)
在外部被处理。逃出后,事件就好像是由影子宿主本身而非真正的包装元素触发的一样。下面的代码演
示了这个过程:
// 创建一个元素作为影子宿主
document.body.innerHTML = `

`; // 添加影子DOM 并向其中插入HTML document.querySelector('div') .attachShadow({ mode: 'open' }) .innerHTML = ` Foo `; // 点击按钮时: // Handled inside: // Handled outside:
注意,事件重定向只会发生在影子DOM中实际存在的元素上。使用标签从外部投射进来的 元素不会发生事件重定向,因为从技术上讲,这些元素仍然存在于影子DOM 外部。 自定义元素 如果你使用JavaScript 框架,那么很可能熟悉自定义元素的概念。这是因为所有主流框架都以某种 形式提供了这个特性。自定义元素为HTML 元素引入了面向对象编程的风格。基于这种风格,可以创 建自定义的、复杂的和可重用的元素,而且只要使用简单的HTML 标签或属性就可以创建相应的实例。 创建自定义元素 浏览器会尝试将无法识别的元素作为通用元素整合进DOM。当然,这些元素默认也不会做任何通用HTML 元素不能做的事。来看下面的例子,其中胡乱编的HTML 标签会变成一个HTMLElement 实例: document.body.innerHTML = ` I'm inside a nonsense element. `; console.log(document.querySelector('x-foo') instanceof HTMLElement); // true 自定义元素在此基础上更进一步。利用自定义元素,可以在标签出现时为它定义复杂的行 为,同样也可以在DOM 中将其纳入元素生命周期管理。自定义元素要使用全局属性customElements, 这个属性会返回CustomElementRegistry 对象。 console.log(customElements); // CustomElementRegistry {} 调用customElements.define()方法可以创建自定义元素。下面的代码创建了一个简单的自定 义元素,这个元素继承HTMLElement: class FooElement extends HTMLElement {} customElements.define('x-foo', FooElement); document.body.innerHTML = ` I'm inside a nonsense element. `; console.log(document.querySelector('x-foo') instanceof FooElement); // true 自定义元素的威力源自类定义。例如,可以通过调用自定义元素的构造函数来控制这个类在DOM 中每个实例的行为: class FooElement extends HTMLElement { constructor() { super(); console.log('x-foo') } } customElements.define('x-foo', FooElement); document.body.innerHTML = ` `; // x-foo // x-foo // x-foo 如果自定义元素继承了一个元素类,那么可以使用is 属性和extends 选项将标签指定为该自定义 元素的实例: class FooElement extends HTMLDivElement { constructor() { super(); console.log('x-foo') } } customElements.define('x-foo', FooElement, { extends: 'div' }); document.body.innerHTML = `
`; // x-foo // x-foo // x-foo

猜你喜欢

转载自blog.csdn.net/m0_68635815/article/details/143415156