我正在尝试创建一个可以采用其他 HTML 元素的自定义组件,但是,它必须灵活,不必使用 <template>
每次使用该组件时,都会在 HTML 文件中插入模板。已经尝试在每次渲染后使用 const children = this.shadow.querySelectorAll('.menu > *')
进行查询connectedCallback()
内函数,但结果是空 NodeList
class SideMenu extends HTMLElement {
constructor() {
super();
this.shadow = this.attachShadow({mode:'open'});
}
render() {
this.shadow.innerHTML = `
<style>
.menu {
display: flex;
flex-direction: column;
height: 100vh;
padding: 2em;
width: 33vw;
gap: 10px;
background-color: #2C2B2B;
}
</style>
<div class="menu">
</div>
`;
}
connectedCallback() {
this.render();
}
}
customElements.define('side-menu', SideMenu);
<side-menu>
<div>Element1</div>
<div>Element2</div>
<div>Element3</div>
<div>ElementN</div>
</side-menu>
基本上,自定义元素必须能够包含任意数量的元素,例如无序列表 ( <ul>
),它可以包含多个 <li>
里面。
最佳答案
您有一个 ShadowDOM,因此当您使用
:host
设置组件样式时不需要额外的div
您可以手动将ligthDOM元素移动到shadowDOM
super()
设置并返回“this”范围attachShadow
设置并返回this.shadowRoot
中做了什么append
在 Internet Explorer 中不可用(“老式”开发人员仍然使用appendChild
)
请注意,它将 DOM 元素从 lightDOM 移动到 ShadowDOM。如果您移动 Web 组件,connectedCallback
将再次运行(但 lightDOM 将为空),因此知道您在connectedCallback
customElements.define('side-menu', class extends HTMLElement {
constructor() {
super().attachShadow({mode:'open'}).innerHTML = `
<style>
:host {
display: flex; flex-direction: column; gap: 10px;
height: 100vh; width: 33vw;
padding: 2em;
background-color: #2C2B2B; color: gold;
}
</style>`;
}
connectedCallback() {
this.shadowRoot.append(...this.children);
}
});
<side-menu>
<div>Element1</div>
<div>Element2</div>
<div>Element3</div>
<div>ElementN</div>
</side-menu>
关于javascript - 是否可以在不使用 `<template>` 和模板槽的情况下在自定义元素中添加元素?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/73430896/