Angular TIPS

Angular TIPS

フォームへの入力値をイベントハンドラーで受け取るには?(テンプレート参照変数)

2017年8月16日

フォーム要素への入力値をイベントとして受け取る方法として、テンプレート参照変数を利用する方法を説明する。

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

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

 フォーム要素(<input><select>など)への入力値をイベントハンドラーで受け取るには、いくつかの方法があります。

 まず、双方向バインディングを利用することです。別稿「TIPS:フォームの入力値をコンポーネントと同期するには?」でも触れたように、双方向バインディングを利用することで、フォーム要素とコンポーネントのプロパティとを同期できます。この場合、イベントハンドラーからはthis.プロパティでプロパティ(=ひも付いたフォーム要素)にアクセスできます。

 また、イベントオブジェクト$eventtargetプロパティを利用することもできます。targetプロパティはイベント発生元の要素を表すので、そのvalueプロパティなどで入力値を取得できます。具体的な例は、前掲の別稿から「補足:双方向バインディングの仕組み」も参照してください。

テンプレート参照変数の基本

 そして本稿で解説するのは3番目の方法、テンプレート参照変数を利用することです。一般的に、入力値にアクセスするために、イベントハンドラーに対してイベントオブジェクトをそのまま渡すのは大ざっぱにすぎます。そもそもイベントの発生元と取得したい要素とが異なる場合、ハンドラー側で文書ツリーを意識したコードを書かなければならないのも望ましい状態ではありません。

 また、イベントハンドラーでの参照だけを目的に、双方向バインディングを利用するのも避けるべきです。双方向バインディングは、常にビュー/コンポーネントの状態を監視しなければならないので、相応にオーバーヘッドの大きな仕組みであるからです。

 そのような場合には、テンプレート参照変数を利用することで、イベントハンドラーに対して、入力値だけを渡せるようになります。

 まずは、具体的なサンプルを見てみましょう。以下は、テキストボックスに入力した値に基づいて、「Hello, ●○!!」というメッセージを表示する例です。

テキストボックスの値に応じて、挨拶メッセージを表示
テキストボックスの値に応じて、挨拶メッセージを表示

1FormsModuleモジュールをインポートする

 Angularのフォーム機能を利用するコードは別稿で示したものと全く同じです。

TypeScript
import { NgModule }      from '@angular/core';
import { BrowserModule } from '@angular/platform-browser';
import { FormsModule }   from '@angular/forms';

import { AppComponent }  from './app.component';

@NgModule({
  imports:      [ BrowserModule, FormsModule ],
  declarations: [ AppComponent ],
  bootstrap:    [ AppComponent ]
})
export class AppModule { }
FormsModuleモジュールをインポートするコード(app.module.ts)

2コンポーネントを準備する

 あとは、テキストボックスを備えたコンポーネントを作成するだけです。太字部分が別稿から変更した箇所です。

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

@Component({
  selector: 'my-app',
  template: `
    <form>
      <label for="name">名前:</label>
      <!--1テキストボックスtxtNameを変数nameでアクセスできるように-->
      <input id="txtName" name="txtName" type="text" #name />
      <!--2イベントハンドラーにテキストボックスへの入力値を引き渡す-->
      <input type="button" value="送信" (click)="onclick(name.value)" />
      <div>{{msg}}</div>
    </form>
  `,
})
export class AppComponent  {
  msg= '';
  
  onclick(value: string) {
    this.msg = `Hello, ${value}!!`;
  }
}
双方向バインディングの基本的な例(app.component.ts)

 テンプレート参照変数とは、名前の通り、テンプレート上の要素を参照するための変数です。1のように、目的の要素に対して#名前の形式で属性を付与することで、その名前で要素オブジェクトを参照できるようになります(この例であれば、テキストボックスtxtNameを変数nameでアクセスできます)。

 あとは、2のように、name.valueでテキストボックスの値をイベントハンドラーに引き渡します*1

  • *1 name(要素オブジェクト)をそのまま渡すこともできますが、大きなオブジェクトをざっくり渡すのではなく、まずは、目的の値だけに絞って渡すことを優先すべきです。
処理対象:テンプレート構文(Template Syntax) カテゴリ:基本
処理対象:テンプレート参照変数(Template Reference Variable) カテゴリ:テンプレート構文(Template Syntax)
処理対象:#変数名 カテゴリ:テンプレート構文(Template Syntax) > テンプレート参照変数(Template Reference Variable)

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

18. フォームの入力値をコンポーネントと同期するには?(双方向バインディング)

テンプレート上のフォーム入力値とコンポーネントのプロパティ値を双方向にバインドするTwo-way Bindingのバインディング構文を説明し、その仕組みを紹介する。

19. イベントハンドラーでイベント情報を参照するには?($event)

要素にイベントハンドラーをバインドするEvent Bindingで、その引数で得られるイベントオブジェクト「$event」から、イベントに関する詳細情報を取得する方法を説明する。

20. 【現在、表示中】≫ フォームへの入力値をイベントハンドラーで受け取るには?(テンプレート参照変数)

フォーム要素への入力値をイベントとして受け取る方法として、テンプレート参照変数を利用する方法を説明する。

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

Angularで数値によってテキスト表示内容を切り替えるための、i18nPluralパイプの基本的な使い方を説明する。

22. 数値をパーセント形式に整形するには?(percent)

Angularで数値を%(パーセント)形式のテキスト表示に整形するための、percentパイプの基本的な使い方を説明する。

サイトからのお知らせ

Twitterでつぶやこう!