Angular指令ngIf用法详解

时间:2021-08-07 17:08:19

HTML是没有条件控制的语言,如果要根据某变量的值显示或隐藏某个DOM元素,往往需要结合JavaScript的if-else表达式来控制。

Angular ngIf就可以增强Html这方面的能力。ngIf接受一个表达式作为值,并且强制把表达式计算出的值转换为Boolean类型,如果值为true,则在DOM中渲染模板,如果值为false则不渲染ngIf所在的模板。

Angular指令ngIf用法详解

示例:

<div class="container" *ngIf="userLoggedIn">
    <h2>欢迎登录</2>
    <p>使用说明。。。。。</p>
</div>

示例中如果用户登录了,则显示出欢迎语。是否登录有userLoggedIn的值确定,userLoggeIn的值为true,则表示登录,false表示未登录。

应用ngIf的位置

应用ngIf的位置分为两种:

  • 模板存在容器父元素,即一个父元素,包含了所有是否要显示或隐藏的其他元素,这种情况ngIf放置在父元素上。
  • 模板没有容器元素,可以使用<ng-container>把其他元素包含在内,然后ngIf应用在<ng-container>上。

上面示例div就是一个容器元素。所以ng应用在它上面就可以了。

但模板没有容器元素,把ngIf应用在<ng-container>上,这样就可以控制显示或隐藏<ng-container>里的元素。而不需要额外添加其他类似div的父元素。

<ng-container *ngIf="userLoggedIn">
    <h2>欢迎登录</2>
    <p>使用说明。。。。。</p>
</ng-container>

ngIf 接受表达式的类型

ngIf不仅仅接受布尔表达式,还可以接受任意有效的TypeScript表达式,只要表达式能够转化为Boolean值就可以。它会根据表达式转换的Boolean值来决定是否渲染模板元素。

ngIf可以接受表达式的类型:布尔表达式,字符串,数组,对象以及数字等等。这个和JavaScript里if检测表达式是否为真是相同的。。

数字和字符串示例:

<div class="container" *ngIf="10">
   10表示为True,结果显示
</div>

<div class="container" *ngIf="0">
   0表示为False,结果隐藏
</div>

<div class="container" *ngIf="'hello world'">
   非空字符串为True,结果显示
</div>

<div class="container" *ngIf="''">
   空字符串为False,结果隐藏
</div>

数组和对象示例:

<div class="container" *ngIf="{hello: 'world'}">
     非null或undefined对象为True,结果显示
</div>

<div class="container" *ngIf="{}">
     空对象为True,结果显示
</div>

<div class="container" *ngIf="[1, 2 ,3]">
     数组对象为True,结果显示
</div>

<div class="container" *ngIf="[]">
     空数组为True,结果显示
</div>

数组和对象是否为true,是依据它的值是否为null或者undefined。

ngIf else语法

除了使用ngIf用于控制显示/隐藏外,有些情况需要使用else语句来控制显示的内容。

语法如下:

<div *ngIf="condition; else elseBlockId">
    condition条件为True,显示此内容
</div>
<ng-template #elseBlockId>
    condition条件为False,则显示此由elseBlock标记的模板内容。
</ng-template>

ngIf用于判断的表达式condition使用分号(;)与else关键词隔开,else后为标记模板id,示例为elseBlockId。<ng-template>使用elseBlockId标记,定义了条件为false,else要显示的内容。

ngIf then else语法

除了直接在ngIf容器元素内定义条件为true显示的内容外,可以使用then关键词,定义条件为true时显示的内容。是ngIf else的变种写法:

<div *ngIf="condition; then thenBlock else elseBlock"></div> 
<ng-template #thenBlock>
     condition条件为True,显示thenBlock内容
</ng-template> 
<ng-template #elseBlock>
      condition条件为False,显示elseBlock内容
</ng-template>

在ngIf表达式种使用Observable数据

如果是基于RxJs写的应用吗,在模板种使用的数据通常是使用Observable提供。

ngIf 指令可以结合async pipe来使用 Observable,如以下示例:

<ng-container *ngIf="(user$ | async) as user">    
   <span>用户名:</span>
   <span class="profile">{{user.name}}</span>
</ng-container>

示例中user$是一个Observable数据。不同于原始数据,Observable数据需要通过async管道来订阅,当Observable有数据发出,就会触发async的订阅。as user是把Observable发出的数据赋值给模板的本地变量user。

在模板中使用Observable有以下好处:

  • 当组件被销毁时,async管道会自动取消订阅 Observable。
  • 如果使用 OnPush 更改检测策略,组件视图将使用最新的 Observable 数据自动更新。

ngIf指令的语法糖

ngIf实际是ngIf指令的语法糖。其中前缀星号*,表示ngIf指令是一种结构性指令。

Angular在编译时,会把*表示的结构性执行编译为初始的形式,如*ngIf示例:

<div class="container" *ngIf="condition; else elseBlock">
       ... Angular会解糖(de-sugar)*ngIf语法
</div>

<ng-template #elseBlock>
     condition为false,显示此内容
</ng-template>

解糖为<ng-template>为:

<ng-template [ngIf]="condition" [ngIfElse]="elseBlock">
    <div class="container">
       ... Angular会解糖(de-sugar)*ngIf语法
     </div>
</ng-template>

<ng-template #elseBlock>
  condition为false,显示此内容
</ng-template>