Javascript Web组件转换发生得太晚
在下面的(简化)代码中,第一个Tester实例使用预定义的模板,而第二个使用直接编码的模板。插值适用于第二个,因为html包含正确的html代码。在插值期间,第一个Tester实例仍然具有的innerHTML。如何更改代码概念以同时插入第一个示例Javascript Web组件转换发生得太晚,javascript,interpolation,web-component,Javascript,Interpolation,Web Component,在下面的(简化)代码中,第一个Tester实例使用预定义的模板,而第二个使用直接编码的模板。插值适用于第二个,因为html包含正确的html代码。在插值期间,第一个Tester实例仍然具有的innerHTML。如何更改代码概念以同时插入第一个示例 <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title&g
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Web Components Demo</title>
</head>
<body>
<div id="tc"></div>
<div id="tc2"></div>
<script>
class TestComponent extends HTMLElement {
constructor () {
super();
this.attachShadow({mode: "open"});
this.shadowRoot.appendChild(this.createTemplate().content.cloneNode(true));
}
createTemplate () {
const template = document.createElement("template");
template.innerHTML = "<h1>{{title}}</h1><p>{{text}}</p>";
return template;
}
}
window.customElements.define("test-component", TestComponent);
class Tester {
constructor ({selector, stuff, template}) {
this.selector = Array.from(document.querySelectorAll(selector));
this.template = template || null;
this.stuff = stuff;
this.render();
this.interpolate();
}
render () {
this.selector.forEach(s => {if (this.template) s.innerHTML = this.template});
}
interpolate () {
this.selector.forEach(s => {
for (let key in this.stuff) {
const regex = new RegExp(`{{ *${key} *}}`, "g");
s.innerHTML = s.innerHTML.replace(regex, this.stuff[key]);;
}
});
}
}
new Tester ({
selector: "#tc",
stuff: {title: "Test Title", text: "Lorem ipsum dolor sit amet"},
template: "<test-component>"
});
new Tester ({
selector: "#tc2",
stuff: {title: "Title that works", text: "Lorem ipsum dolor sit amet"},
template: "<h1>{{title}}</h1><p>{{text}}</p>"
})
</script>
</body>
</html>
Web组件演示
类TestComponent扩展了HtmleElement{
构造函数(){
超级();
this.attachShadow({mode:“open”});
this.shadowRoot.appendChild(this.createTemplate().content.cloneNode(true));
}
createTemplate(){
const template=document.createElement(“模板”);
template.innerHTML=“{{title}}{{{text}}”;
返回模板;
}
}
定义(“测试组件”,TestComponent);
类测试员{
构造函数({selector,stuff,template}){
this.selector=Array.from(document.querySelectorAll(selector));
this.template=template | | null;
this.stuff=东西;
这个。render();
这个。插值();
}
渲染(){
this.selector.forEach(s=>{if(this.template)s.innerHTML=this.template});
}
插入(){
this.selector.forEach(s=>{
对于(让我们输入这个.stuff){
const regex=new RegExp(`{*${key}*}}`,g”);
s、 innerHTML=s.innerHTML.replace(regex,this.stuff[key]);;
}
});
}
}
新测试仪({
选择器:“#tc”,
材料:{标题:“测试标题”,文本:“Lorem ipsum dolor sit amet”},
模板:“”
});
新测试仪({
选择器:“#tc2”,
材料:{标题:“有效的标题”,文本:“Lorem ipsum dolor sit amet”},
模板:“{title}}{{text}}”
})
您的主要问题是:
s.innerHTML = s.innerHTML.replace(regex, this.stuff[key]);
s
是外部DIV,而不是
内部html
constructor () {
super() // returns 'this'
.attachShadow({mode: "open"}) // returns shadowRoot
.innerHTML = "<h1>{{title}}</h1><p>{{text}}</p>";
}
有效地销毁和重新创建每个密钥
因此,constructor()
总是再次将默认模板设置为(元素)innerHTML:
控制台记录在第一个示例上运行的代码:
注
构造函数(){
超级();
this.attachShadow({mode:“open”});
this.shadowRoot.appendChild(this.createTemplate().content.cloneNode(true));
}
createTemplate(){
const template=document.createElement(“模板”);
template.innerHTML=“{{title}}{{{text}}”;
返回模板;
}
有点臃肿:您正在模板内创建HTML,然后将克隆的模板内容(即:HTML)添加到空的shadowRoot innerHTML中
constructor () {
super() // returns 'this'
.attachShadow({mode: "open"}) // returns shadowRoot
.innerHTML = "<h1>{{title}}</h1><p>{{text}}</p>";
}
构造函数(){
super()//返回“this”
.attachShadow({mode:“open”})//返回shadowRoot
.innerHTML=“{title}}{{text}}”;
}
仅当需要重新使用原始(模板)时,才需要克隆(模板)
解决方案:在元素内部移动{}解析
define(“测试组件”,类扩展HtmleElement{
构造函数(){
super().attachShadow({mode:“open”});
这个.setTemplate(`{{title}}{{text}}`);
}
setTemplate(html,数据={}){
this.shadowRoot.innerHTML=html;
解析(数据);
}
解析(数据){
让html=this.shadowRoot.innerHTML;
for(让我们输入数据){
const regex=new RegExp(`{${key}}}}`,g”);
html=html.replace(regex,data[key]);
}
this.shadowRoot.innerHTML=html;
}
});
一、解析({
标题:“测试标题”,
正文:“Lorem ipsum dolor sit amet”
})
两个.setTemplate({{title}}{{subtitle}}}){
标题:“测试二”,
副标题:“副标题”
})
设三=document.createElement('test-component');
解析({//在shadowDOM innerHTML中解析!
标题:“标题三”,
正文:“正文三”
})
document.body.append(三个)
如果我想访问HTML组件,我该怎么做?有没有办法从另一个对象解析组件?使用模式:“open”
shadowDOM是。。。打开内容是document.querySelector(…).shadowRoot.innerHTML