Javascript 附加新web组件时的线程问题

Javascript 附加新web组件时的线程问题,javascript,settimeout,web-component,Javascript,Settimeout,Web Component,我目前正在尝试构建一个webcomponent,它将另一个组件作为其模板的一部分附加到该组件中。但是当尝试访问该子组件的JSAPI时,我得到一个functionName是未定义的错误 将模板附加到DOM时,我可以使用querySelector访问新添加的节点,但不能访问其组件API(即publicAPI)。显然,元素尚未完全初始化。即使我将一个DomainNodeInserted绑定到该元素,API仍然没有定义 但是,只要我将其包装成延迟为0毫秒的setTimeout(这是在不同线程中运行代码的

我目前正在尝试构建一个webcomponent,它将另一个组件作为其模板的一部分附加到该组件中。但是当尝试访问该子组件的JSAPI时,我得到一个functionName是未定义的错误

将模板附加到DOM时,我可以使用
querySelector
访问新添加的节点,但不能访问其组件API(即publicAPI)。显然,元素尚未完全初始化。即使我将一个DomainNodeInserted绑定到该元素,API仍然没有定义

但是,只要我将其包装成延迟为0毫秒的setTimeout(这是在不同线程中运行代码的一种方式),它就会工作

在Chrome和Firefox中启用webcomponent功能时,加载带有HTML导入的组件脚本时,这种情况不会发生

我想找出这个线程问题的原因,并尽可能避免任何设置超时

这是我的代码,或者


测试
var XDiv=document.registerement('x-div'{
扩展:“div”,
prototype:Object.create(htmldevelment.prototype{
createdCallback:{
值:函数(){
var_this=这个,
template=document.querySelector(“#x-div-tmpl”),
wrapper=template.content.querySelector('.wrapper');
//移动模板包装容器中的所有子节点
而(这是第一个孩子){
appendChild(this.firstChild);
}
var tmpl=document.importNode(template.content,true);
this.wrapper=tmpl.querySelector('.wrapper');
this.wrapper.addEventListener('DomainNodeInserted',函数(e){
if(e.target===\u此.wrapper){
console.log('domandeinserted',_this.wrapper',+typeof _this.wrapper.publicAPI);//HTMLElement,未定义
}
});
这是一个新的孩子(tmpl);
console.log(this.wrapper,typeof this.wrapper.publicAPI);//HTMLElement,未定义
setTimeout(函数(){
console.log('setTimeout',_this.wrapper,typeof _this.wrapper.publicAPI);//HTMLElement,函数
}, 0);
}
}
})
});
var XComponent=document.registerElement('x-component'{
扩展:“节”,
prototype:Object.create(htmldevelment.prototype{
createdCallback:{
值:函数(){
log('XComponent:createdCallback');
}
},
附件回调:{
值:函数(){
log('XComponent::attachedCallback');
}
},
publicAPI:{
值:函数(){
log('XComponent::publicAPI');
}
}
})
});

内部组件的
板条箱回调
附件回调
应发出一个事件:

attachedCallback: {
    value: function () {
        var event = document.createEvent("HTMLEvents");
        event.initEvent("attached", true, true);
        event.eventName = "attached";
        this.dispatchEvent(event);
        }
然后外部组件将侦听它:

this.wrapper.addEventListener('attached',
    function (e) {
        console.log(_this.wrapper, ' ' + typeof _this.wrapper.publicAPI); 
    });
您的完整工作代码:

<!DOCTYPE html>
<html>
<head>
    <meta charset="utf-8">
    <script src="https://cdnjs.cloudflare.com/ajax/libs/webcomponentsjs/0.5.5-rc1/webcomponents-lite.min.js"></script>
</head>
<body>

<div is="x-div"><b>test</b></div>

<template id="x-div-tmpl">
    <section is="x-component" class="wrapper"></section>
</template>

<script>
    var XDiv = document.registerElement('x-div', {
        extends: 'div',
        prototype: Object.create(HTMLDivElement.prototype, {
            createdCallback: {
                value: function ()
                    {
                    var _this = this,
                            template = document.querySelector('#x-div-tmpl'),
                            wrapper = template.content.querySelector('.wrapper');

                    // move all child nodes inside the template wrapper container
                    while (this.firstChild)
                        {
                        wrapper.appendChild(this.firstChild);
                        }
                    var tmpl = document.importNode(template.content, true);
                    this.wrapper = tmpl.querySelector('.wrapper');

                    this.wrapper.addEventListener('attached', function (e)
                    {
                    if (e.target === _this.wrapper)
                        {
                        console.log(_this.wrapper, ' ' + typeof _this.wrapper.publicAPI); // HTMLElement, function
                        }
                    });

                    this.appendChild(tmpl);
                    }
            }
        })
    });

    var XComponent = document.registerElement('x-component', {
        extends: 'section',
        prototype: Object.create(HTMLDivElement.prototype, {
            createdCallback: {
                value: function ()
                    {
                    console.log('XComponent:createdCallback');
                    }
            },
            attachedCallback: {
                value: function ()
                    {
                    console.log('XComponent::attachedCallback');

                    var event = document.createEvent("HTMLEvents");
                    event.initEvent("attached", true, true);
                    event.eventName = "attached";
                    this.dispatchEvent(event);
                    }
            },
            publicAPI: {
                value: function ()
                    {
                    console.log('XComponent::publicAPI');
                    }
            }
        })
    });
</script>
</body>
</html>

测试
var XDiv=document.registerement('x-div'{
扩展:“div”,
prototype:Object.create(htmldevelment.prototype{
createdCallback:{
值:函数()
{
var_this=这个,
template=document.querySelector(“#x-div-tmpl”),
wrapper=template.content.querySelector('.wrapper');
//移动模板包装容器中的所有子节点
而(这是第一个孩子)
{
appendChild(this.firstChild);
}
var tmpl=document.importNode(template.content,true);
this.wrapper=tmpl.querySelector('.wrapper');
this.wrapper.addEventListener('attached',函数(e)
{
if(e.target===\u此.wrapper)
{
console.log(_this.wrapper,“+typeof _this.wrapper.publicAPI);//HTMLElement,函数
}
});
这是一个新的孩子(tmpl);
}
}
})
});
var XComponent=document.registerElement('x-component'{
扩展:“节”,
prototype:Object.create(htmldevelment.prototype{
createdCallback:{
值:函数()
{
log('XComponent:createdCallback');
}
},
附件回调:{
值:函数()
{
log('XComponent::attachedCallback');
var event=document.createEvent(“HTMLEvents”);
event.initEvent(“已附加”,true,true);
event.eventName=“已附加”;
本次调度事件(事件);
}
},
publicAPI:{
值:函数()
{
log('XComponent::publicAPI');
}
}