chr*_*ahl 2 javascript events dom web-component shadow-dom
<a>当用户与Web组件进行交互时,将创建锚元素()。问题是,单击锚点后,无法从Web组件的“外部”返回锚点元素。
我添加了一个事件监听器来document监听点击事件。当单击DOM中某处的元素时,我希望成为e.target被单击的元素。在Web组件内部某处单击的情况下,<fancy-list></fancy-list>将返回自定义元素()-而不是单击的元素。
当影子DOM的模式设置为openDOM时,应该可以访问。
class Fancylist extends HTMLElement {
constructor() {
super();
const shadow = this.attachShadow({ mode: 'open' });
const wrapper = document.createElement('div');
wrapper.innerHTML = `<ul></ul><button>Add item</button>`;
shadow.appendChild(wrapper);
this.on_root_click = this.on_root_click.bind(this);
}
connectedCallback() {
this.ul_elm = this.shadowRoot.querySelector('ul');
this.shadowRoot.addEventListener('click', this.on_root_click, false);
}
on_root_click(e){
switch(e.target.nodeName){
case 'BUTTON':
this.ul_elm.innerHTML += '<li><a href="p1">List item</a></li>';
break;
case 'A':
e.preventDefault();
console.log('You clicked a link!');
break;
}
}
}
customElements.define('fancy-list', Fancylist);
Run Code Online (Sandbox Code Playgroud)
<!DOCTYPE html>
<html>
<head>
<title>List</title>
<meta charset="utf-8" />
<script type="text/javascript">
document.addEventListener('DOMContentLoaded', e => {
document.body.addEventListener('click', e => {
//console.log(e.composedPath());
console.log(e.target); // why is this not returning an anchor element when an anchor is clickend inside the <fancy-list>?
}, false);
}, false);
</script>
</head>
<body>
<h1>List</h1>
<fancy-list></fancy-list>
</body>
</html>
Run Code Online (Sandbox Code Playgroud)
Run Code Online (Sandbox Code Playgroud)
Shadow DOM 的目的正是从容器的角度掩盖 HTML内容Shadow DOM。
这就是为什么要重新定位内部事件以公开Shadow DOM主机的原因。
但是,您仍然可以通过获取Event.pathArray属性的第一项来获得实际目标。
event.path[0]
Run Code Online (Sandbox Code Playgroud)
注意:当然,它仅适用于openShadow DOM。
event.path[0]
Run Code Online (Sandbox Code Playgroud)
class Fancylist extends HTMLElement {
constructor() {
super();
const shadow = this.attachShadow({ mode: 'open' });
const wrapper = document.createElement('div');
wrapper.innerHTML = `<ul></ul><button>Add item</button>`;
shadow.appendChild(wrapper);
this.on_root_click = this.on_root_click.bind(this);
}
connectedCallback() {
this.ul_elm = this.shadowRoot.querySelector('ul');
this.shadowRoot.addEventListener('click', this.on_root_click, false);
}
on_root_click(e){
switch(e.target.nodeName){
case 'BUTTON':
this.ul_elm.innerHTML += '<li><a href="p1">List item</a></li>';
break;
case 'A':
e.preventDefault();
break;
}
}
}
customElements.define('fancy-list', Fancylist);
Run Code Online (Sandbox Code Playgroud)
-
谢谢你的回答。它在 Firefox 中不起作用,它让我寻找更多答案 - 我发现了这个:/sf/answers/2747194691/ 显然我们对该功能有不同的实现,Event.path 和 Event.composedPath( )。 (2认同)
-
使用“event.composedPath()”代替“event.path” (2认同)
归档时间:
查看次数:
81 次
最近记录:
jQuery可以提供标签名称吗? 115
每秒更新React组件 89
承诺中的重新抛出错误 68
如何在JavaScript中打印呈现的HTML页面的一部分? 64
问:事件循环开始时是否有通知? 18
如何从事件处理程序中删除自己? 8
Qt响应子QWidget中的keyPressEvent 7
ReactJs:是否可以按类名称将DOM呈现给文档? 4
jQuery + MarkItUp + Polymer - 让它发挥作用? 3
Javascript preventDefault无效,也不返回false; 0
如何动态合并两个JavaScript对象的属性? 2338
如何使用Maven创建具有依赖关系的可执行JAR? 2276
在Windows命令行上是否有相应的"哪个"? 2231
当键盘出现时 - 如何开始编辑时,如何让UITextField向上移动? 1674
如何在Linux shell脚本中提示是/否/取消输入? 1352
varchar和nvarchar有什么区别? 1300
最优雅的方法来检查Python中的字符串是否为空? 1282
如何从Git的暂存区域中删除单个文件,但不将其从索引中删除或撤消对文件本身的更改? 1177
将绘图保存到图像文件,而不是使用Matplotlib显示它 1060
shell脚本中的YYYY-MM-DD格式日期 1045