Angular 

Sean Chou

What is Angular ?

Angular 是一款開源 JavaScript 函式庫

用來協助單一頁面應用程式運行。

目標是透過MVC模式

增強基於瀏覽器的應用,使開發和測試變得更加容易。

What's more ?

ALL-IN-ONE

TypeScript

Component Thinking

Component Thinking

Component A

Component A

Component B

Component B

Component B

Component B

Component C

Component D

Component E

Component B

Environment

  • node 6.9.x  
  • npm 3.x.x
  • Angular Cli
npm install -g @angular/cli

Run your project

ng new my-app

Create a new project

cd my-app
ng serve --o
Architecture

Modules

  • Every Angular app has at least one NgModule class, the root module, conventionally named AppModule
  • 可以將多個 component 打包近一個 modules,提供其他的 app 使用
  • Attribute:
    • declarations
    • providers
    • imports
    • exports
    • ​bootstrap

Root module

/* app.modules.ts */

// import 這隻 webapp 會用到的 package,最基本的 BrowserModule 和 NgModule
import {BrowserModule} from '@angular/platform-browser';
import {NgModule} from '@angular/core';

// 入口點的 component 也要 import 進來
import {AppComponent} from './app.component';

// 定義這個 module 的 metadata
@NgModule({
  declarations: [AppComponent],  // 宣告這個 app 的 component
  imports: [BrowserModule],      // 要使用到的 package
  bootstrap: [AppComponent]      // 表示這個 webapp 的入口點
})

export class AppModule {}

Components

  • Components
    • Control view,需要與 Templates & Metadata 搭配
  • Templates
    • 這個 component 的長相
    • 使用許多 directives 組合而成
  • Metadata
    • @Component 宣告在 component 裡面
    • Metadata 用來綁定 HTML template 、CSS 和 Component

Root Component

/* app.component.ts */

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

@Component({
  selector: 'my-app',
  template: `<h1>{{title}}</h1>`,
  styles: [`h1 { font-weight: normal; }`]
})

export class AppComponent {
  title = 'Hello World';
}
  • selector: 目標的 tag
  • template: component 的長相
  • styles: component 的 style

Refactor your code

/* app.component.ts */

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

@Component({
  selector: 'my-app',
  templateUrl: './app.component.html',
  styleUrls: [ './app.component.css' ],
})

export class AppComponent {
  title = 'Hello World';
}
<!-- app.component.html -->
<h1>{{title}}</h1>
/* app.component.css */ 
h1 { font-weight: normal; }

Define a data model

/* masterData.ts */

export class MasterData {
  key: string;
  value: string;
}
import { Component } from '@angular/core';

// 從同層目錄結構底下 import MasterData
import { MasterData } from './masterData';

// 用這個 model 來宣告一個新的資料陣列
const MASTERS: MasterData[] = [
  { key: 'Hello1', value: 'World1' },
  { key: 'Hello2', value: 'World2' },
  { key: 'Hello3', value: 'World3' },
];

@Component({
  selector: 'my-app',
  templateUrl: './app.component.html',
  styleUrls: [ './app.component.css' ],
})
export class AppComponent {
  title = 'Hello World';

  // 就可以在這裡使用
  datas = MASTERS;
}

use in component

Multiple Component

/* ui.select.component.ts */
import { Component, Input } from '@angular/core';
import { MasterData } from './masterData';

@Component({
  selector: 'ui-select',
  templateUrl: './ui.select.component.html',
})
export class UiSelectComponent {
  // 這裡有一個 input 接口,讓外界可以傳資料進來這個 component
  @Input() data: MasterData[];
}
<!-- ui.select.component.html -->
<select>
  <option *ngFor="let d of data"
    id="{{d.key}}">
    {{d.value}}
  </option>
</select>
/* app.component.ts */
import { Component } from '@angular/core';
import { MasterData } from './masterData';

@Component({
  selector: 'app-root',
  templateUrl: './app.component.html',
  styleUrls: ['./app.component.css']
})

export class AppComponent {
    // 利用我們定義好的 MasterData model 來宣告變數
    bindingData: MasterData[];
    constructor() {
      // 先假造資料
      this.bindingData = [
        {key: 'A1', value: 'valueA'},
        {key: 'B1', value: 'valueB'}
      ]
    }
}
<!-- app.component.html-->
<ui-select [data]="bindingData">

ui-select component

Create a Service

ng g s DataService
/* data-service.service.ts 部分內容 */
import { Injectable } from '@angular/core';

@Injectable()
export class DataServiceService {
  constructor() { }
}
/* app.module.ts 部分內容 */
...
import { DataServiceService } from './data-service/data-service.service';
...
@NgModule({
  ...
  providers: [DataServiceService],
  ...
})
export class AppModule { }

Service

decorator: @Injectable

Http Module

The app will depend on the Angular http service, which itself depends on other supporting services.

The HttpModule from the @angular/http library holds providers for a complete set of HTTP services.

/* app.module.ts */

import {BrowserModule} from '@angular/platform-browser';
import {NgModule} from '@angular/core';
import {AppComponent} from './app.component';
import {HttpModule} from '@angular/http';

@NgModule({
  declarations: [
    AppComponent
  ],
  imports: [
    BrowserModule,
    HttpModule // 要在這裡 import HttpModule
  ],
  bootstrap: [AppComponent]
})

export class AppModule { }

http + promise

/* post.servcie.ts */

import {Injectable} from '@angular/core';
import {Http} from '@angular/http';

@Injectable()
export class PostService {
    private getPostsURI = 'http://xxx/api/get';
    constructor(private http: Http) { }
    getData = () => {
        return this.http.get(this.getPostsURI)
             .toPromise()
             .then(response => response.json())
             .catch(this.handleError);
    }
    private handleError(error: any): Promise<any> {
        console.error('An error occurred', error); // for demo purposes only
        return Promise.reject(error.message || error);
    }
}
this.postService.getData();

Use it in component!

Routing

/* app.module.ts 部分內容 */
...
import { AppRoutingModule } from './app-routing.module';
...
  imports: [
    ...
    AppRoutingModule
  ],
...

The Angular Router enables navigation from one view to the next as users perform application tasks.

/* app-routing.module.ts */

import { NgModule } from '@angular/core';

// import RouterModule and Routers
import { RouterModule, Routes } from '@angular/router';

// import 兩個不同長相的 component
import {ContentComponent} from './content/content.component';
import {PictureComponent} from './picture/picture.component';

// 這是 routing 的規則
const routes: Routes = [
  // 當 root path 的時候自動導到 /content
  { path: '', redirectTo: '/content', pathMatch: 'full' },
  // 當 host:port/picture 時,使用 PictureComponent 渲染頁面
  { path: 'picture', component: PictureComponent },
  // 當 host:port/content 時,使用 ContentComponent 渲染頁面
  { path: 'content', component: ContentComponent }
];

// 在這裡定義 import & export
@NgModule({
  imports: [ RouterModule.forRoot(routes) ],
  exports: [ RouterModule ]
})
export class AppRoutingModule {}

Routing

Build your project

ng build

Build production

ng build --prod
ng build --prod --base-href "project"

Build with parameters

Angular 4 Introduction

By Sean Chou

Angular 4 Introduction

A basic concept of Angular

  • 198