Multiple transclusion using ngFor in Angular2

爷,独闯天下 提交于 2019-12-04 05:57:35

You can use ngTemplateOutlet to achieve this but there is another approach that uses low-level API:

parent.component.html

<grid>
  <div *ngFor="let item of items">
    <span>{{item}}</span>
  </div>
</grid>

Additional directive that will help us to recognize destination index.

@Directive({
  selector: '[grid-item-index]'
})
export class GridItemIndexDirective {
  @Input('grid-item-index') index: any;

  constructor(public vcRef: ViewContainerRef) {}
}

grid.component.html

<div class="grid">
  <div class="row">
    <div class="col-xs-4">
      <ng-template grid-item-index="1"></ng-template>
    </div>
    <div class="col-xs-4">
      <ng-template grid-item-index="2"></ng-template>
    </div>
    <div class="col-xs-4">
      <ng-template grid-item-index="3"></ng-template>
    </div>
  </div>
  <div class="row">
    <div class="col-xs-4">
      <ng-template grid-item-index="4"></ng-template>
    </div>
    <div class="col-xs-4">
      <ng-template grid-item-index="5"></ng-template>
    </div>
    <div class="col-xs-4">
      <ng-template grid-item-index="6"></ng-template>
    </div>
  </div>
</div>

grid.component.ts

@ContentChild(TemplateRef, { read: ViewContainerRef }) vcRef: ViewContainerRef;
@ViewChildren(GridItemIndexDirective) containers: QueryList<GridItemIndexDirective>;

ngAfterViewInit() {
  const len = this.vcRef.length;
  for( var i = 1; i <= len; i++) {
    const destinationContainer = this.containers.find(x => x.index == i);
    if(destinationContainer) {
      const view = this.vcRef.detach(0);
      destinationContainer.vcRef.insert(view);
    }
  }
}

Plunker Example

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!