详解Angular 4.x NgTemplateOutlet


Posted in Javascript onMay 24, 2017

该指令用于基于已有的 TemplateRef 对象,插入对应的内嵌视图。在应用 NgTemplateOutlet 指令时,我们可以通过 [ngTemplateOutletContext] 属性来设置 EmbeddedViewRef 的上下文对象。绑定的上下文应该是一个对象,此外可通过 let 语法来声明绑定上下文对象属性名。

友情提示:若 let 语法未绑定任何属性名,则上下文对象中 $implicit 属性,对应的值将作为默认值。

NgTemplateOutlet 指令语法

<ng-container *ngTemplateOutlet="templateRefExp; context: contextExp"></ng-container>

NgTemplateOutlet 使用示例

@Component({
 selector: 'ng-template-outlet-example',
 template: `
 <ng-container *ngTemplateOutlet="greet"></ng-container>
 <hr>
 <ng-container *ngTemplateOutlet="eng; context: myContext"></ng-container>
 <hr>
 <ng-container *ngTemplateOutlet="svk; context: myContext"></ng-container>
 <hr>
 <ng-template #greet><span>Hello</span></ng-template>
 <ng-template #eng let-name><span>Hello {{name}}!</span></ng-template>
 <ng-template #svk let-person="localSk"><span>Ahoj {{person}}!</span></ng-template>
`
})
class NgTemplateOutletExample {
 myContext = {$implicit: 'World', localSk: 'Svet'};
}

基础知识

TemplateRef

TemplateRef 实例用于表示模板对象。

ViewContainerRef

ViewContainerRef 实例提供了 createEmbeddedView() 方法,该方法接收 TemplateRef 对象作为参数,并将模板中的内容作为容器 (comment 元素) 的兄弟元素,插入到页面中。

<ng-template>

<ng-template> 用于定义模板,使用 * 语法糖的结构指令,最终都会转换为 <ng-template> 模板指令,模板内的内容如果不进行处理,是不会在页面中显示。

<ng-container>

<ng-container> 是一个逻辑容器,可用于对节点进行分组,但不作为 DOM 树中的节点,它将被渲染为 HTML中的 comment 元素,它可用于避免添加额外的元素来使用结构指令。

若想进一步了解 <ng-template> <ng-container> 的区别,请参考Angular 4.x 动态创建组件 文章中我有话说版块。

NgTemplateOutlet 源码分析

NgTemplateOutlet 指令定义

@Directive({
 selector: '[ngTemplateOutlet]'
})

NgTemplateOutlet 类私有属性及构造函数

export class NgTemplateOutlet implements OnChanges {
 // 表示创建的内嵌视图
 private _viewRef: EmbeddedViewRef<any>; 
 // 注入ViewContainerRef实例
 constructor(private _viewContainerRef: ViewContainerRef) {}
}

NgTemplateOutlet 类输入属性

@Input() public ngTemplateOutletContext: Object; // 用于设定EmbeddedViewRef上下文
@Input() public ngTemplateOutlet: TemplateRef<any>; // 用于设定TemplateRef对象

NgTemplateOutlet 指令声明周期

export class NgTemplateOutlet implements OnChanges {
 ngOnChanges(changes: SimpleChanges) {
 // 若this._viewRef已存在,则先从视图容器中对应的位置移除该视图。
 if (this._viewRef) {
  this._viewContainerRef.remove(this._viewContainerRef.indexOf(this._viewRef));
 }
 // 若this.ngTemplateOutlet输入属性有绑定TemplateRef对象,则基于设定的上下文对象创建内嵌视图
 if (this.ngTemplateOutlet) {
  this._viewRef = this._viewContainerRef.createEmbeddedView(
   this.ngTemplateOutlet, this.ngTemplateOutletContext);
 }
 }
}

ngTemplateOutlet 指令的源码相对比较简单,如果读者有兴趣了解 createEmbeddedView() 方法的内部实现,可以参考 Angular 4.x NgIf 文章中的相关内容。

另外需要注意的是使用 let 语法创建模板局部变量,若未设置绑定的值,则默认是上下文对象中 $implicit 属性对应的值。为什么属性名是 $implicit 呢?因为 Angular 不知道用户会如何命名,所以定义了一个默认的属性名。 即 let-name="$implicit" let-name 是等价的。

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
判断客户端浏览器是否安装了Flash插件的多种方法
Aug 11 Javascript
javascript图像处理—仿射变换深度理解
Jan 16 Javascript
jquery 插件实现多行文本框[textarea]自动高度
Mar 04 Javascript
Javascript实现获取及设置光标位置的方法
Jul 21 Javascript
XML文件转化成NSData对象的方法
Aug 12 Javascript
浅谈jquery的map()和each()方法
Jun 12 Javascript
Vue代码分割懒加载的实现方法
Nov 23 Javascript
解决vue页面DOM操作不生效的问题
Mar 17 Javascript
React全家桶环境搭建过程详解
May 18 Javascript
Jquery异步上传文件代码实例
Nov 13 jQuery
Vue点击切换Class变化,实现Active当前样式操作
Jul 17 Javascript
如何让vue长列表快速加载
Mar 29 Vue.js
javascript简单写的判断电话号码实例
May 24 #Javascript
Angular2搜索和重置按钮过场动画
May 24 #Javascript
深入理解react-router@4.0 使用和源码解析
May 23 #Javascript
angularjs中ng-bind-html的用法总结
May 23 #Javascript
vue.js实现价格格式化的方法
May 23 #Javascript
js编写选项卡效果
May 23 #Javascript
jQuery日期范围选择器附源码下载
May 23 #jQuery
You might like
自定义php类(查找/修改)xml文档
2013/03/26 PHP
关于js和php对url编码的处理方法
2014/03/04 PHP
PHP5.4起内置web服务器使用方法
2016/08/09 PHP
原来Jquery.load的方法可以一直load下去
2011/03/28 Javascript
javascript删除option选项的多种方法总结
2013/11/22 Javascript
javascript拖拽上传类库DropzoneJS使用方法
2013/12/05 Javascript
jquery删除指定的html标签并保留标签内文本内容的方法
2014/04/02 Javascript
JavaScript中各种引用类型的常用操作方法小结
2016/05/05 Javascript
jQuery原理系列-css选择器的简单实现
2016/06/07 Javascript
vue.js中$watch的用法示例
2016/10/04 Javascript
js自制图片放大镜功能
2017/01/24 Javascript
Bootstrap 响应式实用工具实例详解
2017/03/29 Javascript
基于代数方程库Algebra.js解二元一次方程功能示例
2017/06/09 Javascript
JS 使用 window对象的print方法实现分页打印功能
2018/05/16 Javascript
菊花转动的jquery加载动画效果
2018/08/19 jQuery
Vue项目部署的实现(阿里云+Nginx代理+PM2)
2019/03/26 Javascript
使用flow来规范javascript的变量类型
2019/09/12 Javascript
vue实现表格过滤功能
2019/09/27 Javascript
JS箭头函数和常规函数之间的区别实例分析【 5 个区别】
2020/05/27 Javascript
[04:44]DOTA2 2017全国高校联赛视频回顾
2017/08/21 DOTA
详细解读Python中解析XML数据的方法
2015/10/15 Python
Python使用Matplotlib实现Logos设计代码
2017/12/25 Python
Django使用Mysql数据库已经存在的数据表方法
2018/05/27 Python
在Mac下使用python实现简单的目录树展示方法
2018/11/01 Python
PyTorch中Tensor的维度变换实现
2019/08/18 Python
利用python实现冒泡排序算法实例代码
2019/12/01 Python
Python 使用threading+Queue实现线程池示例
2019/12/21 Python
如何使用python切换hosts文件
2020/04/29 Python
通过cmd进入python的步骤
2020/06/16 Python
如何用Python和JS实现的Web SSH工具
2021/02/23 Python
公关关系专员的自我评价分享
2013/11/20 职场文书
学习方法演讲稿
2014/05/10 职场文书
2014年教师政治学习材料
2014/06/02 职场文书
安全目标责任书
2014/07/22 职场文书
夫妻分居协议书范文
2014/11/26 职场文书
公司财务管理制度
2015/08/04 职场文书