首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >HTML5 5/webcomponents:从模板代码调用原型函数

HTML5 5/webcomponents:从模板代码调用原型函数
EN

Stack Overflow用户
提问于 2015-10-02 22:57:21
回答 2查看 1.2K关注 0票数 4

我正在为在我正在创建的一个页面应用程序中使用(或不使用) web组件进行一些测试。

下面是这个问题的一个例子:

代码语言:javascript
复制
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
</head>
<body>

<template id="aTemplate">
    <div style="border:1px solid red">
        <p>text <input type="text"></p>
        <button>ClickMe</button>
    </div>
</template>

<script>
    var Proto = Object.create(HTMLElement.prototype);

    Proto.createdCallback = function () {
        var t = document.querySelector('#aTemplate');
        var clone = document.importNode(t.content, true);
        this.createShadowRoot().appendChild(clone);
    };

    Proto.aFunction = function() {
        alert("proto " + "text value?");
    }

    document.registerElement('x-proto', {prototype: Proto});

    var ProtoChild = Object.create(Proto);

    ProtoChild.createdCallback = function () {
        Proto.createdCallback.call(this)
    };

    ProtoChild.aFunction = function() {
        alert("child " + "text value?");
    }

    document.registerElement('x-proto-child', {
        prototype: Proto
    });

</script>

<x-proto></x-proto>

<x-proto-child></x-proto-child>

</body>

问题是,我无法在按钮(模板内)中设置一个"onclick“处理程序,该处理程序调用使用原型创建的对象中的方法"aFunction”。应该在正确的对象实例中调用该方法,并访问内部DOM组件以及原型中的属性和函数。

我尝试了很多东西,(构建后绑定事件,使用JS或JQuery,使用创建/附加回调,a),但我没有想法了。

提前谢谢。

编辑:

感谢MinusFour的回答。这句话:

( clone.querySelector('button').addEventListener('click',this.aFunction);

不管怎么说,在我试图做的事情上,结果(与JQuery一样,用于兼容性测试):

$(this.showButton).on("click",this.aFunction.bind(this));

"bind“使'this‘AKA成为容器,完整的组件,在JS代码中可用,这是我所需要的。

下面是最后一个完整的例子,有人可能会发现它很有帮助:

代码语言:javascript
复制
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <script src="http://code.jquery.com/jquery-2.1.4.min.js"></script>
</head>
<body>

<template id="aTemplate">
    <div style="border:1px solid darkgray;padding:10px;margin: 10px;">
        <h2 class="theCaption"></h2>
        <p>text <input class="theText" type="text"></p>
        <button class="showButton">Show val</button>
        <button class="closeButton">Close</button>
    </div>
</template>

<script>

    // The .bind method from Prototype.js
    if (!Function.prototype.bind) { // check if native implementation available
        Function.prototype.bind = function () {
            var fn = this, args = Array.prototype.slice.call(arguments),
                    object = args.shift();
            return function () {
                return fn.apply(object,
                        args.concat(Array.prototype.slice.call(arguments)));
            };
        };
    }

    function createProto() {
       $("#spawnPoint").append("<x-proto x-caption='proto'></x-proto>");
    }

    function createChild() {
        $("#spawnPoint").append("<x-proto-child x-caption='a child of proto'></x-proto-child>");
    }

    var Proto = Object.create(HTMLElement.prototype);

    Object.defineProperty(Proto, "x-caption", {value: "no caption"});

    Proto.createdCallback = function () {
        var t = document.querySelector('#aTemplate');
        var clone = document.importNode(t.content, true);
        this.shadowRoot = this.createShadowRoot();
        this.shadowRoot.appendChild(clone);
        $(clone).children("div").append("<p>ssss</p>")
        this.showButton = this.shadowRoot.querySelector('.showButton');
        this.closeButton = this.shadowRoot.querySelector('.closeButton');
        this.shadowRoot.querySelector('.theCaption').textContent = $(this).attr("x-caption");
        this.theText = this.shadowRoot.querySelector('.theText');
        $(this.showButton).on("click", this.aFunction.bind(this));
        $(this.closeButton).on("click", this.close.bind(this));
    };

    Proto.aFunction = function () {
        alert("in proto = " + $(this.theText).val());
    }

    Proto.close = function () {
        $(this).detach();
    }

    document.registerElement('x-proto', {prototype: Proto});

    var ProtoChild = Object.create(Proto);

    ProtoChild.createdCallback = function () {
        Proto.createdCallback.call(this);
    };

    ProtoChild.aFunction = function () {
        alert("overrided in child = " + $(this.theText).val());
    }

    document.registerElement('x-proto-child', {
        prototype: ProtoChild
    });

</script>

<button onclick="javascript:createProto()">Create proto</button>
<button onclick="javascript:createChild()">Create child</button>

<div id="spawnPoint">

</div>

</body>

EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2015-10-02 23:05:08

我相信您可以添加来自importedNode的侦听器(在您的例子中是clone)。

代码语言:javascript
复制
clone.querySelector('button').addEventListener('click', function(){
  //code logic here
});

你也可能是指:

代码语言:javascript
复制
document.registerElement('x-proto-child', {
        prototype: ProtoChild
    });

下面是它的样子:

代码语言:javascript
复制
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
</head>
<body>

<template id="aTemplate">
    <div style="border:1px solid red">
        <p>text <input type="text"></p>
        <button>ClickMe</button>
    </div>
</template>
<script src="https://cdnjs.cloudflare.com/ajax/libs/webcomponentsjs/0.7.14/webcomponents.min.js"></script>
<script>
    var Proto = Object.create(HTMLElement.prototype);
  
    Proto.createdCallback = function () {
        var t = document.querySelector('#aTemplate');
        var clone = document.importNode(t.content, true);
        clone.querySelector('button').addEventListener('click', this.aFunction);
        this.createShadowRoot().appendChild(clone);
    };

    Proto.aFunction = function() {
        alert("proto " + "text value?");
    }

    document.registerElement('x-proto', {prototype: Proto});

    var ProtoChild = Object.create(Proto);

    ProtoChild.createdCallback = function () {
        Proto.createdCallback.call(this);
        console.log(this.template);
        /*this.template.querySelector('button').addEventListener('click', function(){
          console.log('child');
          });*/
    };

    ProtoChild.aFunction = function() {
        alert("child " + "text value?");
    }

    document.registerElement('x-proto-child', {
        prototype: ProtoChild
    });

</script>

<x-proto></x-proto>

<x-proto-child></x-proto-child>

</body>

票数 2
EN

Stack Overflow用户

发布于 2015-10-02 23:10:31

不久前,我也有过类似的问题:

http://www.davevoyles.com/accessing-member-functions-in-polymer/

你是在使用聚合物,还是仅仅使用网络组件?

只要你把你试图在聚合物准备事件中调用的函数包装起来,你应该做得很好,并且可以从你的聚合物元素中调用函数。

聚合物解析元素定义并异步处理它们的升级。如果在DOM有机会升级之前过早地从DOM获取元素,那么您将使用普通的HTMLElement,而不是自定义元素。

或者,您可以任意查询自定义元素(通过ID、类、attr或元素名称)并获取相同的内容。下面是他的例子:http://jsbin.com/qikaya/2/edit

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/32917027

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档