Angular-内容投影

1、单插槽内容投影(映射内容)

答:在组件模版中需要投影内容的位置添加<ng-content></ng-content>指令,作为投影内容的占位符

在使用该组件时,在组件标签元素之间放置需要投影到组件模版中的内容,如:

// 组件模版

<div><ng-content></ng-content></div>

// 使用组件时

<customer-component><p>这个p标签是需要投影到组件模版中的内容</p></customer-component>

2、多插槽内容投影(映射内容)

答:在组件模版中拥有多个插槽,通过在<ng-content>占位符上添加select属性来指定那些内容需要投影到该位置,可用的值有元素的属性、标签名、css类名、:not伪类的任意组合

注意当投影内容没有匹配到任何一个具名插槽时,会使用默认的插槽填充

如:

// 组件模版

<div>

<ng-content select=“[custAttr]"></ng-content>

<ng-content select=“b”></ng-content>

<ng-content select=“.content”></ng-content>

<—默认插槽-->

<ng-content></ng-content>

</div>

// 使用时

<div>

<customer-com>

<p custAttr>找到匹配属性为custAttr的插槽</p>

<b>找到匹配标签名为b的插槽</b>

<p class=“content”>找到匹配class类名为content的插槽</p>

<p>使用默认插槽</p>

</customer-com>

</div>

3、有条件的内容投影(容器+模版组合)

答:使用<ng-container>和<ng-template>组合实现由条件的内容投影,在<ng-container>标签上使用属性型指令ngTemplateOutlet来指定使用的模版内容,同时在组件类中使用@ContentChild或者@ContentChildren装饰器来获取对此模版内容的引用(即TemplateRef),如:

// 组件模版

<div>

<ng-container [ngTemplateOutlet]=“content"></ng-container>

</div>

// 组件类

@ContentChild(TemplateRef) content!: TemplateRef<unknown>

要使用非空断言!,否则会报错

// 使用时

<customer-com>

<ng-template>模版内容</ng-template>

</customer-com>

4、将一块内容作为一个元素投影到指定位置(重命名内容块为某个位置的映射内容)

答:使用ngProjectAs属性将一块代码包装为一个完整的投影内容,打包投影到组件的指定位置

如:

// 组件模版

<div>

<ng-content select=“[customerAttr]"></ng-content>

</div>

// 使用时

<div>

<customer-com>

<ng-container ngProjectAs=“[customerAttr]”>

<p></p>

<b></b>

</ng-container>

</customer-com>

</div>

注意:无论<ng-content>是否定义或者是否显示,只要在使用该组件时提供了需要投影的内容,则都会初始化该内容

https://angular.cn/guide/content-projection