实现 

模拟场景:页面上"帮助"按钮的点击触发帮助文档的弹出框,且每个页面的帮助文档不一样

因此弹出框里的帮助文档是一个动态模板而不是动态组件

以下comp均代表Type类型的动态组件,即 comp:Type<any>

//xx.component.ts

export class xxComponent implements Oninit{
constructor(private helpingService:HelpingService){ }
fireClick($event:any){//按钮的点击事件
this.helpingService.changeHelpContent(comp);
}
}
//helping.service.ts
@Injectable()
export class HelpingService{
helpChangeEvent:EventEmitter<comp>;
constractor(){
this.helpChangeEvent=new EventEmitter<comp>()
}
public changeHelpContent(comp){
this.helpChangeEvent.emit(comp)//发射helpChangeEvent事件
}
}
//helping.component.ts

@component({
selector: 'helping',
templateUrl: './helping.component.html',
styleUrls: ['./helping.component.scss']
}) @ViewChild('con',{read:ViewContainerRef})
conRef:ViewContainerRef; export class HelpingComponent implements OnInit{
constractor(private helpingService:HelpingService,
private factoryResolver: ComponentFactoryResolver,){
this.helpingService.helpchangeEvent.subscribe((comp)=>{//接收helpChangeEvent事件
this.loadComponent(comp)
})
}
private loadComponent(comp){
this.conRef.clear();//删除之前的视图
let factory=this.factoryResolver.resolveComponentFactory(comp);//factory创建组件的实例
this.conRef.createComponent(factory)
}
}

动态创建组件的相关知识点

1.TemplateRef

通过TemplateRef实例,可以创建内嵌视图Embedded Views

涉及对象和相关方法:

1.crateEbeddedView创建内嵌视图

@Component({
selector:'helping',
template:`//创建组件,那组件内容就是固定的
<template #tpl>
<span>i am a span in Template {{name}}</span>
</template>
`
})
export class helpingComponent{
@ViewChild('tpl')
tpl:TemplateRef<any>; name:string='Artimis'; ngAfterViewInit(){
let view=this.tpl.createEmbeddedView(null);
let commentEle=this.tpl.elementRef.nativeElement;
view.rootNodes.forEach((node)=>{//没有ViewContainerRef,只能手动把元素塞到视图里
commentEle.parentNode.insertBefore(node,commentEle.nextSibling)
})
}
}

2.VIiewContainerRef

视图容器,是管理创建好的内嵌视图或组件视图

通过ViewContainerRef实例,基于TemplateRef + createEmbeddedView创建内嵌视图

@Component({
selector:'helping',
template:`
<template #tpl>
<span>i am a span in Template {{name}}</span>
</template>
`
})
export class helpingComponent{
@ViewChild('tpl')
tpl:TemplateRef<any>; @ViewChild('tpl',{read:ViewContainerRef})
tplVcRef:ViewContainerRef; name:string='Artimis'; ngAfterViewInit(){
//有ViewContainerRef,直接通过createEmbeddedView方法塞进视图
this.tplVcRef.createEmbeddedView(this.tplRef)
}

 动态创建模板的相关知识点

1.ComponentFactoryResolver

通过ViewContainerRef实例,基于ComponentFactoryResolver + createComponent 创建模板视图

涉及对象和相关方法:

1. ComponentFactoryResolver:一个服务对象(需要注入)

2. resolveComponentFactory:ComponentFactoryResolver的方法,接收一个组件类作为参数,返回一个ComponentFactory实例

3.createComponent:ViewContainerRef的方法,内部会调用ComponentFactory实例的create方法创建对应组件,并将组件添加到容器内

export abstract class ComponentFactoryResolver{
static NULL:ComponentFactoryResolver=new _NullComponentFactoryResolver();
abstract resolverComponentFactory<T>(component:Type<T>):ComponentFactory<T>
}
@Component({
selector:'helping',
template:`//创建模板,那模板的内容就不是固定的
<ng-container #con></ng-container>
`
})
export class helpingComponent{ @ViewChild('con',{read:ViewContainerRef})
conRef:ViewContainerRef; constractor(private factoryResolver: ComponentFactoryResolver,
private helpingService: HelpingService){
this.helpingService.manualChange.subscribe((comp)=>{
this.loadComp(comp);
}) private loadComp(comp){
this.conRef.clear();//删除之前的视图
let factory=this.factoryResolver.resolveComponentFactory(comp);//factory是一个如何创建组件的实例
this.conRef.createComponent(factory)
}
}

  

angular4 动态创建组件 vs 动态创建模板的更多相关文章

  1. Java 动态编译组件 & 类动态加载

    1.JDK6 动态编译组件 Java SE 6 之后自身集成了运行时编译的组件:javax.tools,存放在 tools.jar 包里,可以实现 Java 源代码编译,帮助扩展静态应用程序.该包中提 ...

  2. Delphi 动态创建组件,单个创建、单个销毁

    效果图如下: 实现部分代码如下: var rec: Integer = 0; //记录增行按钮点击次数 implementation {$R *.dfm} //动态释放单个组件内存,即销毁组件 pro ...

  3. vue 动态创建组件(运行时创建组件)

    function mountCmp (cmp, props, parent) { if (cmp.default) { cmp = cmp.default } cmp = Vue.extend(cmp ...

  4. Angular 创建组件

    创建组件 0 命令创建 1 创建组件 定义hello.component.ts组件 在app.module.ts中引用并添加到declarations声明中 在app.component.html中使 ...

  5. ionic小白的学习路之目录结构分析、创建组件、创建页面、页面跳转

    一. 目录结构分析 hooks:编译cordova 时自定义的脚本命令,方便整合到我们的编译系统和版本控制系统中. node_modules :node 各类依赖包. resources :andro ...

  6. Angular动态创建组件之Portals

    这篇文章主要介绍使用Angular api 和 CDK Portals两种方式实现动态创建组件,另外还会讲一些跟它相关的知识点,如:Angular多级依赖注入.ViewContainerRef,Por ...

  7. 动态创建组件TEdit

    //动态创建组件TEdit procedure TForm1.FormMouseDown(Sender: TObject; Button: TMouseButton;  Shift: TShiftSt ...

  8. Delphi动态创建组件,并释放内存

    开发所用delphi版本是xe2,效果图如下: 代码如下: ---------------------------------------------------------------------- ...

  9. Qt Quick 组件和动态创建的对象具体的解释

    在<Qt Quick 事件处理之信号与槽>一文中介绍自己定义信号时,举了一个简单的样例.定义了一个颜色选择组件,当用户在组建内点击鼠标时,该组件会发出一个携带颜色值的信号,当时我使用 Co ...

随机推荐

  1. mysql 多表join

    两个表可以简单地写为 select a.,b. from a left join b on a.id =b.id; 三个以上 select a.,b. from a left join b on a. ...

  2. thinkphp 虚拟模型

    虚拟模型是指虽然是模型类,但并不会真正的操作数据库的模型.有些时候,我们建立模型类但又不需要进行数据库操作,仅仅是借助模型类来封装一些业务逻辑,那么可以借助虚拟模型来完成.虚拟模型不会自动连接数据库, ...

  3. 报javax.servlet.ServletException: Servlet.init() for servlet [springmvc] threw exception的解决记录

    1.异常详情: 2.异常分析: 从异常的详情中看出:companyService未找到,出现这种情况的愿意可能是companyServiceImpl类没有交给IOC容器管理,但是经过我已经在该类上打了 ...

  4. poj 3660 Cow Contest (bitset+floyd传递闭包)

    传送门 解题思路 考试题,想到传递闭包了,写了个O(n^3)的,T了7个点...后来看题解是tm的bitset优化???以前好像没听过诶(我太菜了),其实也不难,时间复杂度O(n^3/32) #inc ...

  5. javaweb的几种开发模式

    1.MVC模式基础 1.1.MVC模式简介 MVC是一种架构型模式,它本身并不引入新的功能,只是用来指导我们改善应用程序的架构,使得应用的模型和视图相分离,从而达到更好的开发和维护效率.在MVC模式中 ...

  6. T2988 删除数字【状压Dp+前缀和优化】

    Online Judge:从Topcoder搬过来,具体哪一题不清楚 Label:状压Dp+前缀和优化 题目描述 给定两个数A和N,形成一个长度为N+1的序列,(A,A+1,A+2,...,A+N-1 ...

  7. Luogu P3835 【模板】可持久化平衡树(fhq Treap)

    P3835 [模板]可持久化平衡树 题意 题目背景 本题为题目普通平衡树的可持久化加强版. 题目描述 您需要写一种数据结构(可参考题目标题),来维护一些数,其中需要提供以下操作(对于各个以往的历史版本 ...

  8. Gym-102141E

    https://vjudge.net/problem/Gym-102141E 用set乱搞 #include<iostream> #include<cstdio> #inclu ...

  9. parameter– tRPRE and tRPST

    DDR读数据有效之前,有一段时间DQS(DQS#)需为低(高),此段时间即为read preamble,tRPRE. 同理,读数据结束之前,某段时间为read postamble,tRPST.

  10. Django项目:CRM(客户关系管理系统)--73--63PerfectCRM实现CRM讲师下载作业

    # teacher_urls.py # ————————62PerfectCRM实现CRM讲师讲课记录———————— from django.conf.urls import url from bp ...