(Angular 2+)在*ngFor中使用ng-content,无法访问循环变量

riy*_*uyu 9 javascript ng-template ngfor angular

如何将/ transllude/project转换为循环内的插槽,并使投影内容能够访问循环变量?

假设我有一个带有以下内容的基本组件

<tr *ngFor="let data of items">
    <td>{{data.title}}</td>
    <ng-content select="[slot]"></ng-content>
</tr>
Run Code Online (Sandbox Code Playgroud)

一个使用翻译槽"slot"的子组件

<parent [items]="items"> 
    <ng-container slot>
        <td>{{data.category}}</td>
        <td>{{data.number}}</td>
    </ng-container>
</parent>
Run Code Online (Sandbox Code Playgroud)

我想生成的HTML是

<tr>
    <td>{{data.title}}</td>
    <td>{{data.category}}</td>
    <td>{{data.number}}</td>
</tr>
Run Code Online (Sandbox Code Playgroud)

但实际发生的是"数据"未在子组件中定义,这是有道理的.有什么方法可以让它像这样工作吗?

dhi*_*ilt 3

使用TemplateRef它可以在模板级别以声明方式声明在两个组件之间起作用的模板变量。以下解决方案并不完全匹配您的“插槽”基础设施,但可能有助于进一步调查。

列表组件.ts

import { Component, Input, ContentChild, TemplateRef } from '@angular/core';

@Component({
  selector: 'list',
  template: `
    <tr class="box" *ngFor="let data of items">
      <td>{{data.title}}</td>
      <ng-template
        [ngTemplateOutlet]="template"
        [ngTemplateOutletContext]="{ $implicit: data }">
      </ng-template>
    </tr>`
})
export class ListComponent {
  @Input() items;
  @ContentChild(TemplateRef) template: TemplateRef;
  constructor() { }
}
Run Code Online (Sandbox Code Playgroud)

包装器组件.ts

import { Component, ContentChild, TemplateRef } from '@angular/core';

@Component({
  selector: 'wrapper',
  template: `
    <table>
      <list [items]="items">
        <ng-template let-data>
          <td>{{data.category}}</td>
          <td>{{data.number}}</td>
        </ng-template>
      </list>
    </table>`
})
export class WrapperComponent {
  items = [
    { title: 'T1', category: 'C1', number: 'N1' },
    { title: 'T2', category: 'C2', number: 'N2' },
    { title: 'T3', category: 'C3', number: 'N3' }
  ];
  @ContentChild(TemplateRef) template: TemplateRef;
  constructor() { }
}
Run Code Online (Sandbox Code Playgroud)

我还创建了一个Plunker 演示...