JavaScript 製オープンソース Web フレームワークである AngularJS は、リッチなフロントエンドを簡単に作ることができて便利です。実は業務でも使っています(個人的にはまあ色々言いたいこともあるけどw)。 一方で、AngularJS やマテリアルデザインである Angular Material は特に日本語での情報があまり多くなく、標準以外の機能を使おうとすると色々苦労することがあります。その辺りを補足する目的もあって、調べたことのメモを公開します。


AngularJS を使うことで普通に作っても見栄えがよくなりますが、サブモジュールである Datepicker を使うと、日付データの入力に便利な UI を簡単に配置できます(↓こんなやつです):
2018040301


この Datepicker を使う方法も簡単で、JavaScript コード側で @angular/material/datepicker をインポートしておいて、
import {MatDatepickerModule} from '@angular/material/datepicker';

その上で以下のような HTML を記述するだけです:
  :
  :

<mat-form-field>
  <input matInput [matDatepicker]="picker" placeholder="Choose a date">
  <mat-datepicker-toggle matSuffix [for]="picker"></mat-datepicker-toggle>
  <mat-datepicker #picker></mat-datepicker>
</mat-form-field>

  :
  :

すると上記画像のように <input> フィールドそのものに CSS が適用され、カレンダーアイコンをクリックして日付選択ができるようになる、というスグレモノです。モバイルブラウザのタッチイベントにも対応していたりするなど、機能的にも優秀です。日付選択は HTML5 の type="date" を使う方法もありますが、まだ主要ブラウザの実装もまちまちで、対応されていてもちと使いにくさを感じることもあるため、現時点での代用品としてはかなりの需要があると思っています。


一方で、この Datepicker にも問題点はあります。標準機能をそのまま使うと、選択した日付は日本ではあまり馴染みのない M/d/yyyy フォーマットで画面に表示されることです:
2018040302


この表示部分だけでもなんとか日本式の yyyy/M/d フォーマットにできないだろうか・・と調べた結果が以下の方法です。いくつかの対応手段がありそうですが、簡単なのは「日本ロケール(ja-JP)を指定する」以下のやり方でした。

HTML はそのままで、JavaScript を以下のように書き換えます:
//. 赤の2行を追加インポート
import {MatDatepickerModule} from '@angular/material/datepicker';
import {MAT_MOMENT_DATE_FORMATS, MomentDateAdapter} from '@angular/material-moment-adapter';
import {DateAdapter, MAT_DATE_FORMATS, MAT_DATE_LOCALE} from '@angular/material/core';

  :
  :

@Component({
  selector: 'datepicker-locale-example',
  templateUrl: 'datepicker-locale-example.html',
  styleUrls: ['datepicker-locale-example.css'],
  providers: [
    //. 'ja-JP' ロケールを指定
    {provide: MAT_DATE_LOCALE, useValue: 'ja-JP'},

    //. MomentDateAdapter と MAT_MOMENT_DATE_FORMATS をインポート
    {provide: DateAdapter, useClass: MomentDateAdapter, deps: [MAT_DATE_LOCALE]},
    {provide: MAT_DATE_FORMATS, useValue: MAT_MOMENT_DATE_FORMATS},
  ],
})

  :
  :

export class DatepickerLocaleExample {
  //. クラスのコンストラクタに DateAdapter を渡す
  constructor(private adapter: DateAdapter) {}
}

この変更を加えて上で同じ HTML を参照すると、日付は日本ロケールで表示されるようになります:
2018040303



めでたしめでたし。


(参考)
https://material.angular.io/components/datepicker/overview