Angular TIPS

Angular TIPS

数値(単数/複数)によって表示を切り替えるには?(ngPlural)

2017年12月5日

Angularで数値によってテキスト表示内容を切り替えるための、ngPluralディレクティブの基本的な使い方を説明する。

  • このエントリーをはてなブックマークに追加

【対応バージョン】 Angular 5以降。v5時点で執筆しました。

【注意】Angular 4以前からの本TIPS読者へ

 今回からAngular 5ベースで執筆していきます。

 2017年11月1日以降、QuickStartが非推奨となりました。このため、2017年11月27日以前のAngular TIPSはQuickStartベースとなっていましたが、2017年12月5日以降、全てのAngular TIPSをAngular CLI前提に変更しました。

 QuickStartベースではmy-appという名前のセレクターが使われていましたが、CLIではapp-rootという名前のセレクターが自動生成されるため、全てのAngular TIPSのサンプルコードの「my-app」を「app-root」に書き換えました。

 読者がこれまで作成したきたQuickStartベースのアプリについても、推奨されているAngular CLIで実行する際には、全てのソースファイルにおける<my-app>要素は<app-root>要素に、selector: 'my-app'selector: 'app-root'という記載に変更してください。これを行わない場合、TIPSのサンプルコードのセレクター名と手元のソースコードのセレクター名に食い違いが生じてエラーとなる可能性があるので注意が必要です。

 逆に、QuickStartベースで実行する必要がある際には、全てのソースファイルにおける<app-root>要素は<my-app>要素に、selector: 'app-root'selector: 'my-app'に変更してください。繰り返しになりますが、QuickStartは非推奨となっており、本TIPSとしても、今後はAngular CLIに切り替えることを推奨します。

 ngPluralディレクティブは、i18nPluralパイプのディレクティブ版。与えられた式の値が単数/複数(またはいくつか)によって、出力を切り替えるためのディレクティブです。

 例えば以下は、メールボックスなどのアプリを想定したものです。新着メールの件数に応じて、以下のようなメッセージを表示させるものとします。

件数 メッセージ
0 新着メールはありません。
1 新着メールがあります。
2以上 ●○件の新着メールがあります。
新着メールの件数によってメッセージを変化

 このようなメッセージの差し替えを、ngPluralディレクティブで実装しているのが、以下のコードです。

TypeScript
import { Component } from '@angular/core';

@Component({
  selector: 'app-root',
  template: `
  <div [ngPlural]="mails.length">
    <ng-template ngPluralCase="=0">新着メールはありません。
    </ng-template>
    <ng-template ngPluralCase="=1">新着メールがあります。
    </ng-template>
    <ng-template ngPluralCase="other">
      {{mails.length}}件の新着メールがあります。
    </ng-template>
  </div>
  `
})
export class AppComponent {
  // 新着メール情報
  mails = [
    { name: '山田太郎', body: 'こんにちは。今年は暑いねー。' },
    { name: '鈴木久美子', body: 'お久しぶりです。元気にしてますか?' },
    { name: '佐藤雄二', body: '今度の日曜日、ランチしに行きませんか。' },
    { name: '山口夕夏', body: 'お誕生日おめでとう!' },
    { name: '田中仁', body: 'いつもお世話になっております。明日はよろしくお願い致します。' }
  ];
}
変数の値によってメッセージを切り替えるためのコード(app.component.ts)
新着メールの件数(mails.length)によってメッセージが変化(1)
新着メールの件数(mails.length)によってメッセージが変化(2)
新着メールの件数(mails.length)によってメッセージが変化(3)
新着メールの件数(mails.length)によってメッセージが変化*1
  • *1 メッセージの変化を確認するには、mailsプロパティ(配列)に含まれる要素の個数を変えてください。

 ngPluralディレクティブの構文は、以下の通りです。

[構文]ngPluralディレクティブ

<element [ngPlural]="value">
&nbsp: <ng-template ngPluralCase="num">message</ng-template>
&nbsp: ...
</element>

  • element: 任意の要素
  • value: 任意の式
  • num: 引数valueに対応する値
  • message: 件数に応じたメッセージ

 式(引数value)の値が、引数numに一致する場合に、<ng-template>要素配下のメッセージを表示します。引数numの「=0」「=1」は、「0、1に等しい場合」を意味します。ここでは利用していませんが、「=2」「=3」……で2以上の値を表すことも可能です。また、「いずれの値にも合致しない場合」を表すには、「other」としてください。

 i18nPluralパイプと異なり、メッセージはテンプレートの一部なので、{{...}}構文を使えば、メッセージには任意の値を埋め込むことも可能です(パイプでは、基本的に#で元の値を埋め込めるだけです)。

 その性質上、動的にメッセージを組み立てる用途、そもそものメッセージ量が多いような状況では、i18nPluralパイプよりもngPluralディレクティブを利用すべきです。一方、メッセージをテンプレートから切り離したい(=コンポーネント側で管理したい)という場合には、メッセージ定義を連想配列で表現できるi18nPluralパイプの方が便利でしょう。

処理対象:ディレクティブ(Directive) カテゴリ:基本
API:NgPlural(*ngFor) カテゴリ:@angular > common > DIRECTIVE(ディレクティブ)

※以下では、本稿の前後を合わせて5回分(第29回~第33回)のみ表示しています。
 連載の全タイトルを参照するには、[この記事の連載 INDEX]を参照してください。

29. 複数の要素を繰り返し出力するには?(ngFor)

配列の内容を順に出力できるngForディレクティブ(=ngForOfディレクティブ)と、ダミーのコンテナー要素(<ng-container>)を使うことで、複数の要素群をまとめて繰り返し出力する方法を説明する。

30. 条件式に応じて要素を表示/非表示にするには?(ngIf)

与えられた条件式に基づき要素の表示/非表示を切り替えるngIfディレクティブの基本的な使い方を説明。また、ngIfディレクティブによる表示/非表示の挙動の特性と注意点も示す。

31. 条件式の真偽に応じて出力を切り替えるには?(ngIf/else)

与えられた条件式に基づき要素の表示/非表示を切り替えるngIfディレクティブで用いる、「さもなければ」を意味するelse句と、テンプレートとして別出しするためのthen句の、基本的な使い方を説明する。

32. 【現在、表示中】≫ 数値(単数/複数)によって表示を切り替えるには?(ngPlural)

Angularで数値によってテキスト表示内容を切り替えるための、ngPluralディレクティブの基本的な使い方を説明する。

33. 複数のスタイルクラスをまとめて操作するには?(ngClass)

スタイルシートとして定義した複数の対象クラスのスタイルを、任意の要素のclass属性にまとめて着脱できるngClassディレクティブの基本的な使い方を説明する。

サイトからのお知らせ

Twitterでつぶやこう!