対象読者
- jQueryなどを使っている開発者
- JavaScriptを使った複数人でのプロジェクトに参加している方
- JavaScriptを使ってサーバ等と連携したフロントエンドの開発をしている方
必要な環境
この記事では、AngularJSを使用し、Chrome(39.0)、IE11、Firefox(35.0)、Safari(8.0.2)の環境にて確認を行っています。
入力フォームを扱うためのディレクティブ
FormやInputタグなどフォームを扱うディレクティブでは、ユーザから入力される値を管理するために表示するだけのディレクティブとは異なり、便利な機能が沢山あります。それらの機能をうまく使うことで手間なく、また、問題がおきにくいシステムを構築できるようになっています。まずは、このフォームを扱うための機能を紹介します。
フォームの管理を扱うためのディレクティブ ngForm/ngSubmit
ngFormディレクティブは、フォームコントロール要素(input要素等)を管理するためのディレクティブです。ngFormは<form>タグがそのまま利用できるために属性などで指定する必要はありません。フォームを送信する際には、ngSubmitもしくはngClickが使用されます。ngSubmitディレクティブは、フォームがサブミットされた時のイベント処理でonsubmitと同様のことができ、ngFormと共に利用されます。ngSubmitの代わりにngClickもよく利用されます。ただし、どちらも実際にサーバにサブミット(データ送信)が行われるわけではないので、ngSubmit/ngClickで指定したメソッド内で実装する必要があります。また、このディレクティブにはFormControllerというフォームの状態を管理するためのオブジェクトが同時に生成されます。このオブジェクトはフォーム全体のステータスを管理していて、表1(プロパティ一覧)に示すような状態の把握が可能です。
変数名 | 意味 |
---|---|
$pristine | いずれのフォームコントール要素で入力、もしく変更がまだされていない状態 |
$dirty | いずれかのフォームコントロール要素で値の入力、もしくは変更がされた状態 |
$valid | すべてのフォームコントロール要素(入力)のバリデーションにエラーがない状態 |
$invalid | いずれかのフォームコントール要素(入力)のバリデーションエラーがある状態 |
$submitted | フォームがサブミットされたことがある状態 |
$error | バリデーションエラーがある場合に。そのエラーの理由を保持するオブジェクト。(エラー理由の詳細は後述) |
実際のフォームの状態を表示するコードのサンプルがリスト1です。FormControllerのインスタンスは、form要素のname属性の変数名でアクセス可能です。また、後述しますが、input要素のなどの各フォームコントロールの状態もFormControllerのインスタンスを利用してアクセス可能です。
<form name="frm" ng-submit="submit()"> <input name="name" placeholder="値を入力してください" ng-model="item" ng-pattern="/^[0-9A-Za-z]+$/" ng-maxlength="4" ng-minlength="2" ng-required="true" > <input type="submit" value="送信"> <table> : 省略 <tr> <td>{{frm.$valid}}/{{frm.$invalid}} </td> <td>{{frm.$dirty}}</td> <td>{{frm.$pristine}}</td> <td>{{frm.$submitted}}</td> </tr> : 省略 <tr> <td>{{!!frm.$error.required}}</td> <td>{{!!frm.$error.minlength}}</td> <td>{{!!frm.$error.maxlength}}</td> <td>{{!!frm.$error.pattern}}</td> </tr> </table> </form>
FormControllerにコントローラからアクセスする場合には、リスト2のようにテンプレートで使用した変数名と同様に利用できます。
変数名なども同様ですので、同じように扱うことが可能です。
$scope.submit = function(){ console.log($scope.frm.$valid,$scope.frm.$invalid); // $scope.frmでアクセス可能です };