Carpe Diem

備忘録

angular-cliで手軽にAngular2を始める

概要

Angular2のチュートリアルを終えた後で「いざ作ってみよう」となると

  • 「package.jsonやtsconfigとかどうしよう」
  • 「system.jsよりwebpackがいいって聞くけどどうなんだろ」
  • 「テストフレームワークは何がいいんだろう」

みたいなことで悩んでなかなか進まないことがあると思います。
そんなときにそういった開発の下準備的なことをまとめてやってくれるのがangular-cliです。
angular-cliに下準備を任せ、Material Designをあてたページを作成します。

環境

  • angular-cli 1.0.0-beta.21

成果物

今回実装してできるものは以下です。

デモページ

Angular2Sample

ソース

github.com

angular-cliのインストール

$ npm install -g angular-cli

初期化

新規に作る場合は

$ ng new プロジェクト名

とします。githubリポジトリを先に作っていて、そのフォルダ内で作りたい場合は

$ ng init

を実行します。後者の場合はREADME.mdなどのファイルが存在すると対話的に残すか上書きするかを訊いてくれます。

作成すると同時にライブラリもインストールしてくれるのですぐに初期画面を起動できます。

$ ng serve

とすると起動するので

http://localhost:4200/

にアクセスしてください。すると以下の画面が表示されます。

f:id:quoll00:20161130004635p:plain

Material Designを適用

次にMaterial Designをあてます。angular-cliは途中からSystemJSでなくwebpackを採用したので設定の仕方が変わってます。検索するときはその点に注意してください。

また今回は様々なディレクティブを使用するのでimportするライブラリがたくさんありますが、実際に開発する際は必要なもののみを入れてください。

material designのライブラリをインストール

--- a/package.json
+++ b/package.json
@@ -20,6 +20,13 @@
     "@angular/platform-browser": "2.2.1",
     "@angular/platform-browser-dynamic": "2.2.1",
     "@angular/router": "3.2.1",
+    "@angular2-material/button": "^2.0.0-alpha.8-2",
+    "@angular2-material/card": "^2.0.0-alpha.8-2",
+    "@angular2-material/checkbox": "^2.0.0-alpha.8-2",
+    "@angular2-material/core": "^2.0.0-alpha.8-2",
+    "@angular2-material/radio": "^2.0.0-alpha.8-2",
+    "@angular2-material/slider": "^2.0.0-alpha.8-2",
+    "@angular2-material/tooltip": "^2.0.0-alpha.8-2",
     "core-js": "^2.4.1",
+    "hammerjs": "^2.0.8",
     "rxjs": "5.0.0-beta.12",
     "ts-helpers": "^1.1.1",

app.module.tsでインポート

--- a/src/app/app.module.ts
+++ b/src/app/app.module.ts
@@ -3,6 +3,17 @@ import { NgModule } from '@angular/core';
 import { FormsModule } from '@angular/forms';
 import { HttpModule } from '@angular/http';
 
+import 'hammerjs' 
+
+// Material 2 
+import { MdCoreModule, MdUniqueSelectionDispatcher, OVERLAY_PROVIDERS } from '@angular2-material/core'
+import { MdButtonModule } from '@angular2-material/button';
+import { MdCardModule } from '@angular2-material/card';
+import { MdRadioModule } from '@angular2-material/radio';
+import { MdCheckboxModule } from '@angular2-material/checkbox'
+import { MdTooltipModule } from '@angular2-material/tooltip';
+import { MdSliderModule } from '@angular2-material/slider';
+
 import { AppComponent } from './app.component';
 
 @NgModule({
@@ -12,9 +23,11 @@ import { AppComponent } from './app.component';
   imports: [
     BrowserModule,
     FormsModule,
-    HttpModule
+    HttpModule,
+    MdCoreModule, MdCardModule, MdButtonModule, MdRadioModule,
+    MdCheckboxModule, MdTooltipModule, MdSliderModule
   ],
-  providers: [],
+  providers: [MdUniqueSelectionDispatcher, OVERLAY_PROVIDERS],
   bootstrap: [AppComponent]
 })

app.component.htmlでMaterial Designのディレクティブを使用

--- a/src/app/app.component.html
+++ b/src/app/app.component.html
@@ -1,3 +1,32 @@
-<h1>
-  {{title}}
-</h1>
+<div class="app-content">
+  <h1>{{title}}</h1>
+
+  <!-- Buttons -->
+  <md-card>
+    <button md-button>FLAT</button>
+    <button md-raised-button md-tooltip="This is a tooltip!">RAISED</button>
+    <button md-raised-button color="primary">PRIMARY RAISED</button>
+    <button md-raised-button color="accent">ACCENT RAISED</button>
+  </md-card>
+
+  <!-- Checkboxes -->
+  <md-card>
+    <md-checkbox>Unchecked</md-checkbox>
+    <md-checkbox [checked]="true">Checked</md-checkbox>
+    <md-checkbox [indeterminate]="true">Indeterminate</md-checkbox>
+    <md-checkbox [disabled]="true">Disabled</md-checkbox>
+  </md-card>
+
+  <!-- Radio Buttons -->
+  <md-card>
+    <md-radio-button name="symbol">Alpha</md-radio-button>
+    <md-radio-button name="symbol">Beta</md-radio-button>
+    <md-radio-button name="symbol" disabled>Gamma</md-radio-button>
+  </md-card>
+
+  <!-- Slider -->
+  <md-card>
+    <md-slider min="1" max="5"></md-slider>
+  </md-card>
+</div>

デフォルトだとtooltipがきちんと表示されないのでoverlay.cssをあてる

--- a/angular-cli.json
+++ b/angular-cli.json
@@ -18,7 +18,8 @@
       "prefix": "app",
       "mobile": false,
       "styles": [
-        "styles.css"
+        "styles.css",
+        "../node_modules/@angular2-material/core/overlay/overlay.css"
       ],
       "scripts": [],
       "environments": {

動作確認

$ ng serve

以下のようになればOKです。

f:id:quoll00:20161130012706p:plain

その他起きたエラー

hammerjsがない

[default] Checking started in a separate process...
[default] /Users/jun06t/prog/github/angular2-sample/node_modules/@angular2-material/core/gestures/MdGestureConfig.d.ts:4:40 
    Cannot find name 'HammerManager'.
[default] /Users/jun06t/prog/github/angular2-sample/node_modules/@angular2-material/slider/slider.d.ts:61:20 
    Cannot find name 'HammerInput'.
[default] /Users/jun06t/prog/github/angular2-sample/node_modules/@angular2-material/slider/slider.d.ts:63:25 
    Cannot find name 'HammerInput'.
[default] Checking finished with 3 errors

上記のようなエラーが出るときはhammerjsがないです。
coreやsliderで必要となりますが自動ではインストールされないみたいです。

$ npm install hammerjs --save-dev
$ npm install @types/hammerjs --save-dev

をしてimportしてください。

EXCEPTION: No provider for Overlay!

Error: No provider for Overlay!
    at NoProviderError.BaseError [as constructor] (main.bundle.js:3418)
    at NoProviderError.AbstractProviderError [as constructor] (main.bundle.js:36788)
    at new NoProviderError (main.bundle.js:36819)
    at ReflectiveInjector_._throwOrNull (main.bundle.js:52480)
    at ReflectiveInjector_._getByKeyDefault (main.bundle.js:52508)
    at ReflectiveInjector_._getByKey (main.bundle.js:52471)
    at ReflectiveInjector_.get (main.bundle.js:52280)
    at AppModuleInjector.NgModuleInjector.get (main.bundle.js:37490)
    at CompiledTemplate.proxyViewClass.AppView.injectorGet (main.bundle.js:53022)
    at CompiledTemplate.proxyViewClass.DebugAppView.injectorGet (main.bundle.js:53264)

OVERLAY_PROVIDERSをprovidersに設定していないと起きます。

EXCEPTION: No provider for MdUniqueSelectionDispatcher!

Error: No provider for MdUniqueSelectionDispatcher!
    at NoProviderError.BaseError [as constructor] (errors.js:24)
    at NoProviderError.AbstractProviderError [as constructor] (reflective_errors.js:41)
    at new NoProviderError (reflective_errors.js:72)
    at ReflectiveInjector_._throwOrNull (reflective_injector.js:758)
    at ReflectiveInjector_._getByKeyDefault (reflective_injector.js:786)
    at ReflectiveInjector_._getByKey (reflective_injector.js:749)
    at ReflectiveInjector_.get (reflective_injector.js:558)
    at AppModuleInjector.NgModuleInjector.get (ng_module_factory.js:95)
    at CompiledTemplate.proxyViewClass.AppView.injectorGet (view.js:109)
    at CompiledTemplate.proxyViewClass.DebugAppView.injectorGet (view.js:351)

MdUniqueSelectionDispatcherをprovidersに設定していないと起きます。

ソース