GSS 技術部落格
在這個園地裡我們將從技術、專案管理、客戶對談面和大家分享我們多年的經驗,希望大家不管是喜歡或是有意見,都可以回饋給我們,讓我們有機會和大家對話並一起成長!
若有任何問題請來信:gss_crm@gss.com.tw
字體大小: +
4 分鐘閱讀時間 (864 個字)

Angular # 19 - 深入 Components [2]

shutterstock_198004562
  • Component 間的溝通

    • Input
      • 先前的篇章中已經深入探討過,不再多作說明
      • 更精確來說是透過 @Input 所裝飾的屬性
      • 方向上是由 ParentChild
    • Output
      • 除了由上至下之外,元件也可以透過發出事件來通知 Parent,或是任何關注此事件的 Component,接下來的就由它們自行處理
        • 舉例來說,TabsComponent 可以發出事件告知目前使用中的 TabComponent 為何
        • 承上,這樣做可以使得關注此事件的元件(e.g. ToolTipComponent 也許需要作內容的異動,好針對目前的 tab 顯示不同的提示)
    • 直接使用其他 Component 的方式
      • View Child, 可以取得 Child 的 controller 參考並在自己的 controller 中使用
      • Local variables, 可以取得 Child 的 controller 參考,並在自己的 template 中使用
  • 假設我們想在 nav bar 上加一個 重新整理 的按鈕, 在按下按鈕時重新載入資料,要該怎麼做,才能正確的觸發資料更新,並進一步顯示在頁面上?

    • 首先,要調整一下 NavBarComponent 如下:

        import { Component, Output, EventEmitter } from '@angular/core';
      
        @Component({
          selector: 'app-navbar',
          templateUrl: './navbar.component.html',
          styleUrls: ['./navbar.component.css']
        })
        export class NavbarComponent  {
          constructor() { }
          @Output() onRefresh: EventEmitter<null> = new EventEmitter<null>();
      
          refresh() {
            this.onRefresh.emit();
          }
        }
      • 多 import 了 OutputEventEmitter
      • 宣告一個變數 onRefresh 並以 @Output() 裝飾之(特別留意它的型別為 EventEmitter<null>)
        • 這麼做會使得 Angular 留意有 onRefresh 這個事件
        • 如果我們打算關注此事件,就會寫 (onRefresh)="...expression..."
        • angle brackets(角括號) 中的型別為 null 代表的意義是這個事件中不會帶有任何資料(沒錯,事件發出的時候也是可以傳遞資的)
      • EventEmitter 是一個特殊的物件,有了它我們可以和 Angular 的 change detection 一起使用
      • 光是設定一個事件是沒用的,所以還定義了一個 refresh 方法,裡面會呼叫 EventEmitter 的 emit() 這個方法
        • 呼叫了這個方法, 事件就會被觸發,那些監聽此事件的 parent component
        • 下一步就是在修改 template 如下:
          <button class="btn btn-success" type="button" (click)="refresh()">Reload</button>
        • 如上設定,在按鈕按下時會呼叫 refresh
        • refresh 這個方法便會進一步發出 onRefresh 事件
        • AppComponent 會被通知有一個 onRefresh 事件, 但因為我們還沒作任何調整,所以不會有任何事情發生
      • 事不宜遲,來在 AppComponent 中加入處理吧!
        • 在那之前,請先看一下程式碼,或回憶一下,AppComponent 有兩個 ViewChild,分別為 NavBar 與 Dashboard(不要忘記怎麼區分 ViewChild 與 Content Child 啊!)
        • 當 AppComponent 被通知有 onRefresh 事件時, 它應該要告訴 DashboardComponent:「喂,該更新資料了」
          • 所以要來調整一下 AppComponent 的 Template
            <app-navbar (onRefresh)="dashboard.generateData()"></app-navbar>
            <app-dashboard #dashboard></app-dashboard>
          • 如此便能在 onRefresh 事件發生時更新資料
      • 為何 AppComponent 能用 DashboardComponent 中的方法呢?
        • 在上面的 HTML 片段中,第二列的 #dashboard 是一個特殊的語法,稱作 local template variable
        • 顧名思義,AppComponent 就可以在自己的 template 上透過 dashboard 這個變數操作 DashboardComponent 的 controller 中 public 方法
        • 承上,private 的方法像是 randomInteger 就無法被呼叫
        • 特別留意如果沒有任何 Component 監聽此事件(onRefresh),事件就不會向上拋出。換言之,@Output 的事件只會到有監聽的 Parent Component(跟 DOM event 不一樣,一律都會往上拋)
  • 小結

    • Component 間是可以溝通的
      • 由上至下可以透過 @Input
      • 由下至上,進而達到橫向溝通可以使用 @Output 搭配 EventEmitter
      • ViewChild 可以提供 local template variable,讓 parent 得以在 template 上操作 ViewChild 本身的方法(非 private)
×
Stay Informed

When you subscribe to the blog, we will send you an e-mail when there are new updates on the site so you wouldn't miss them.

Angular #20 - 深入 Components [3]
Angular #18 - 深入 Components [1]

相關文章

 

評論

尚無評論
已經注冊了? 這裡登入
2026年4月08日, 星期三

Captcha 圖像