我有一个自定义组件,它只显示一张塔罗牌。
在自定义元素之前我定义了一个模板。
在我的 wc 的 connectedCallback 中,我将模板本身附加到 shadowroot,然后通过在 shadowroot 中克隆它来将其删除。我这样做有两个原因:
- 我希望我的 wc 组件是一个独立的模块;因此我想在与自定义元素相同的位置定义我的模板。
这似乎是唯一可以消除我的模板以使其可用而无需将其粘贴在所有者文档中的方法。
var tmpl = ` <template id="tmpl"> <h1 class="tarot-title"><slot name="title">NEED TITLE</slot> </h1> <img src="${this.imageurl}" alt=""> <p><slot name="subtitle">NEED A SUBTITLE</slot></p> </template>`; class BdTarot extends HTMLElement { ...constructor etc... connectedCallback() { this._shadowRoot.innerHTML = tmpl; var _tmpl = this._shadowRoot.querySelector('#tmpl'); this._shadowRoot.appendChild(_tmpl.content.cloneNode(true)); } } customElements.define('bd-tarot', BdTarot);
这造成的问题是我在页面上使用的每个塔罗牌组件都有相同的模板是子组件,都具有相同的 ID。既然他们在 shadowroot 中,这有关系吗?虽然闻起来很有趣...
我的目标只是试图了解 Web 组件规范是如何组合在一起的。我的问题是,是否有更好的方法可以将我的组件代码保持在一起并且不引用所有者文档?由于大多数浏览器 vendor 未采用 html 导入,模板规范是否主要与自定义元素不兼容?
最佳答案
简而言之:如果您使用 template literals那么你不应该使用 <template>
元素。
您无需复制模板即可将自定义元素和模板代码放在一起。
您可以简单地将您的代码包含在一个自执行函数中,以确保 tmpl 变量不会被覆盖。
(function () {
var tmpl = `
<h1 class="tarot-title"><slot name="title">NEED TITLE</slot></h1>
<img src="${this.imageurl}" alt="">
<p><slot name="subtitle">NEED A SUBTITLE</slot></p>`;
class BdTarot extends HTMLElement {
constructor() {
super()
this.attachShadow( { mode: 'open' } )
.innerHTML = tmpl;
}
}
customElements.define('bd-tarot', BdTarot);
})()
<bd-tarot>
<span slot="title">Queen</span>
</bd-tarot>
如果您想保留模板的本地副本,可以将其复制到实例变量 ( this.tmpl
) 中。
关于javascript - 如何使用 vanilla js 在自包含的自定义元素中剔除模板?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/46097077/