我正在尝试构建呈现 JSON 对象集合的通用 Web 组件,例如树视图和多列表视图(在两个列表之间移动项目)。我想复制 iron-list 使用的模式,其中包含单个项目表示的模板被传递到组件中以供重用。
例如,给定这个 Web 组件模板:
<dom-module id="intworkspace-tree">
<template>
<style include="iron-flex iron-flex-alignment">
paper-icon-item {
--paper-item-min-height: var(--intworkspace-tree-margin,30px);
--paper-item-icon-width : var(--intworkspace-tree-margin,30px);
}
paper-icon-item:focus::before,
paper-icon-item:focus::after {
color: inherit;
opacity: 0;
}
.node {
margin-left: var(--intworkspace-tree-margin,30px);;
}
</style>
<slot id="labelView"></slot>
<template id="nodeView">
<div class="layout vertical">
<paper-icon-item on-tap="nodeSelected">
<iron-icon icon="expand-less" slot="item-icon" hidden$="[[!hasNodes(node)]]"></iron-icon>
<!-- label goes here-->
</paper-icon-item>
<iron-collapse class="node" opened hidden$="[[!hasNodes(node)]]">
<intworkspace-tree tree="[[node.nodes]]" embedded></intworkspace-tree>
</iron-collapse>
</div>
</template>
</template>
...
</dom-module>
和这种用法:
<intworkspace-tree tree="{{testTree}}">
<template><paper-item-body>[[node.name]]</paper-item-body> </template>
</intworkspace-tree>
利用 Polymer.Templatize.templatize API 加载模板,创建/标记新实例,并使用 DOM API 将它们附加在一起并将它们添加到 Web 组件的影子 DOM。
访问模板内容,将它们组合在一起,创建并导入新模板,然后根据需要克隆它。
在经历了很多逆境之后,我能够成功地实施#1 但不是#2,这就是我提出问题的动机。#2 对我更有吸引力,因为我更容易合并模板一次,而不是合并它们生成的标记实例,而且这种方法似乎是我可以重用嵌套模板(如 dom-repeat)的唯一方法。
我的主要障碍是,一旦加载了 Polymer 或者它的 polyfill,模板就会变得不透明,并且只能由 Polymer 模板化功能使用。例如,此代码在没有任何 Polymer 导入的情况下工作正常:
<template>
<div>Template Contents</div>
</template>
<div>
Template Test
</div>
<script>
let template = document.querySelector("template");
let clone = document.importNode(template.content,true);
document.querySelector("div").appendChild(clone);
</script>
在 Polymer 之外,template.content DOMFragment 有子元素并设置了 innerHTML。然而,一旦使用了 Polymer,template.content 就没有子元素,并且 innerHTML 是空的。这使我无法使用 DOM API 创建一个将可用模板混合在一起的新模板,即
let newTemplate = document.createElement("template");
newTemplate.content = ... // combine #labelView > template.content with #nodeView.content
let nodeView = document.importNode(newTemplate.content,true);
nodeView.tree=...
也许通过设计使用标准 HTML 机制导入模板对我不起作用。是否有另一种方法可以在运行时使用 Polymer 动态创建/合并模板?同样,我的主要动机是我想重用嵌套在模板中的 dom-if 和 dom-repeat Web 组件,而无需重新实现它们的所有功能。