遍历聚合物内容插入点

4

What I'd like is for the following html:

<father name = "John">
  <son name = "Bob">likes lollipops</son>
  <son name = "David">likes computers</son>
</father>

生成:
John has two sons, Bob and David:

Bob: likes lollipops
David: likes computers

现在,假设我已经正确地编写了“son”聚合标签,它会渲染一个块级div,内容为“Bob:喜欢棒棒糖”。这个很容易让我正常工作,所以我得到了这样的东西:
John

Bob: likes lolipops
David: likes computers

然而,为了获得那个顶部线条,我真的不确定正确的方法是什么,基本上我想要类似于这样的东西:

<polymer-element name = "father" attributes = "name">
    <template>
        <style>...
        </style>
        <div layout vertical>
            {{name}} has ???{count}??? sons, ???{{ iterate son nodes, print out name attribute for each }}???<br/>
            <!-- I dont know how ot access JS here, so not sure how to turn all child nodes into a children array -->
            <content select = "son"></content>
        </div> 
    </template>
    <script>
        Polymer({});
    </script>
</polymer-element>
2个回答

3

这个问题可能有几种解决方法,但以下是其中一种途径。 (完整版本在 JSBin 上)。

<polymer-element name="son-element" attributes="name" noscript>
  <template>
    <p>{{name}}: <content></content></p>
  </template>
</polymer-element>

<polymer-element name="father-element" attributes="name">
  <template>
    <p>{{name}} has {{count}} sons, {{sons}}:</p>
    <p><content id="content"></content></p>
  </template>
  <script>
    Polymer({
      count: 0,
      sons: '',
      domReady: function() {
        var names = [].map.call(this.children, function(sonElement) {
          return sonElement.name;
        });
        this.count = names.length;
        this.sons = names.join(' and ');
      }
    });
  </script>
</polymer-element>

<father-element name="John">
  <son-element name="Bob">likes lollipops</son-element>
  <son-element name="David">likes computers</son-element>
</father-element>

关键的一步是连接到<father-element>domReady 生命周期方法,并检查它的子级。因为我们知道它们都是<son-element>,所以我们只需盲目地查找它们的name属性并将它们映射到一个数组中,但如果你愿意,你可以采取一些步骤,仅查询<son-element>
(哦,Polymer元素的名称都需要有-,因此您需要使用<father-element>(或类似的名称)而不是<father>。)

3
专业提示:这是一个不错的解决方案,但检查this.children有两个限制性:(1)如果元素通过<content>进行投射,它们将不会出现在children中; (2)子元素可能会出现和消失。尽可能明确地握手关系。例如,当<son-element>attached()时触发son-added事件,当detached()时触发son-removed事件。father-element可以监听这些事件并直接管理这些关系。 - Scott Miles

0

这是我的解决方案,它基于Jeff Posnick的解决方案,但采用了Scott Miles的建议来监听添加和删除事件。

<polymer-element name="baby-element" attributes="name">
  <template>
    <p>{{name}}: <content></content> <input type="button" value="Kill Baby" on-click="{{killBaby}}"/></p>
  </template>
  <script>
    Polymer("baby-element", {
      attached: function(){
        this.fire('baby-added');
      },
      killBaby: function(){
        this.fire('baby-removed');
  //    this.remove();
      },
      detached: function() {
        this.fire('baby-removed');
      }
    });
  </script>
</polymer-element>

<polymer-element name="parent-element" attributes="name">
  <template>
    <p>{{name}} has {{count}} babys, {{babys}}:</p>
    <p><content id="content"></content></p>
  </template>
  <script>
    Polymer({
      count: 0,
      babys: '',
      domReady: function() {
        this.recalcBabys();
        this.addEventListener('baby-added', this.babyAdded);
        this.addEventListener('baby-removed', this.babyRemoved);
      },
      babyRemoved: function(e) {
        e.target.remove();
        this.recalcBabys();
      },
      babyAdded: function(e) {
        this.recalcBabys();
      },
      recalcBabys: function(){
        var names = [].map.call(this.children, function(babyElement) {
          return babyElement.name;
        });
        this.count = names.length;
        this.babys = names.join(' and ');
      }
    });
  </script>

</polymer-element>

<h1>It's aparent baby thing:</h1>
<input type=button value="make baby" id="makeBaby"></input>
<input type=input placeholder="baby name" id="babyName"></input>
<input type=input placeholder="baby info" id="babyInfo"></input>

<parent-element id="parent" name="Slim Sim">
  <baby-element name="Curie">has X</baby-element>
  <baby-element name="Korbut">volts like no other!</baby-element>
  <baby-element name="Pavlov">has dogs!</baby-element>
  <baby-element name="Schrodinger">... maybe has a cat?</baby-element>
</parent-element>


<script>
  document.getElementById('makeBaby').addEventListener('click', function(){
    var name = document.getElementById('babyName');
    var info = document.getElementById('babyInfo');
    var parent = document.getElementById('parent');
    var baby = document.createElement("baby-element");
    var inner = document.createTextNode(info.value);
    baby.appendChild(inner);
    baby.setAttribute("name",name.value);
    parent.appendChild(baby);
  });
</script>

我无法通过例如document.getElementsByTagName('baby-element')[0].remove()从外部删除婴儿时,使父元素重新计算Babys。

我希望(在baby-element上)仅触发附加和分离方法的baby-added和baby-removed事件,并且killBaby函数仅执行'this.remove()'。但是我无法让父级听到所有这些事件...

请随意审查此代码并告诉我任何错误,我有点新于Polymer,但我仍然希望能够做出贡献!


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接