【问题标题】:How to check if component has a child node of <template></template>?如何检查组件是否有 <template></template> 的子节点?
【发布时间】:2017-10-03 01:38:28
【问题描述】:

以我的组件为例:

<div [my-component]="'text'"></div>

在代码中我有this.viewContainerRef,它是节点本身(&lt;div&gt;)。

但用户可能想将其模板添加到myComponent,所以他会这样做:

<div [my-component]="'text'">
   <template>
   ...
   </template>
</div>

我的问题是如何在代码中检查是否存在 &lt;template&gt; 节点并使用/读取其内部 HTML?

【问题讨论】:

  • 你在使用 Angular 4 吗?
  • 在 Angular 2 中,DOM 中永远不会有 &lt;template&gt; 元素。在 Angular 4 中,&lt;template&gt; 被重命名为 &lt;ng-template&gt; 以释放 &lt;template&gt; 以添加到 DOM。我不确定 Angular4,因为使用 &lt;template&gt; 会导致弃用警告。不确定&lt;template&gt; 是否只会在 Angular5 中被释放,或者它是否已经被释放(我自己还没有尝试过) - 如果元素确实存在,只需检查 DOM。
  • &lt;template&gt; 只是在你构建应用程序时被翻译成 JavaScript,实际上从来没有变成 DOM 元素,只在 Angular 内部处理。这就是他们将其更改为 &lt;ng-template&gt; 的原因,因为 &lt;template&gt; 是一个普通的 HTML 元素,例如,当您想将 Polymer 与 Angular 一起使用时有时需要(我遇到的只是一个示例)。
  • 这是意料之中的。没有 &lt;template&gt; 元素,并且在 Angular2 中没有办法让 Angular 添加一个。您可以使用直接 DOM 操作添加一个,例如 &lt;div [innerHTML]="someHtml | safeHtml"&gt;&lt;/div&gt;someHtml = '&lt;template&gt;...&lt;/template&gt;。这样你就可以围绕 Angular 工作了。 (safeHtml 是我在一个答案中展示的消毒管)
  • 您可以使用&lt;template&gt;或(Angular4中的&lt;ng-template&gt;)然后使用ngTemplateOutletngForTemplate(或createInnerView不确定这是正确的名称)`来标记模板.这仅适用于您的弹出窗口、工具提示......组件是 Angular 组件并希望通过模板。 &lt;template&gt; 标记仍然不会添加到 DOM,您仍然可以通过在 MyComponent 中使用 @ViewChild(TemplateRef) template:TemplateRef; 来访问它,因为 Angular 会在内部处理这个问题。

标签: angular typescript angular2-directives angular2-components


【解决方案1】:

您可以使用 ContentChild(TemplateRef) 并在定义模板时以及它只是 html 时进行渲染。这是一个例子。这适用于 Angular 2。对于 Angular 4,可以使用“*ngIf;else Block”。

  @Component({
    selector: '[my-component]',
    template: `
      my-component with input {{v}}
      <ng-container *ngIf="tpl">
        Template block:
        <ng-container [ngTemplateOutlet]="tpl"></ng-container>
      </ng-container>

      <ng-container *ngIf="!tpl">
        No Template block: <ng-content></ng-content>
      </ng-container>
    `
  })
  export class MyComponent {
    @Input('my-component') v : string;
    @ContentChild(TemplateRef) public tpl: TemplateRef;
  }
  @Component({
    selector: 'my-app',
    template: `
      <div>
        <div [my-component]="'text'">
          <template><pre>hi there</pre></template>
        </div>
        <hr>
        <div [my-component]="'text1'">
          aaa
        </div>
      </div>
    `,
  })
  export class App {
    constructor() {
    }
  }

【讨论】:

  • 从将要使用该组件的用户的角度来看,它工作且易于理解和使用。谢谢!
猜你喜欢
  • 2015-07-07
  • 1970-01-01
  • 1970-01-01
  • 2017-04-30
  • 2020-02-06
  • 2015-04-18
  • 1970-01-01
  • 1970-01-01
  • 2011-04-16
相关资源
最近更新 更多