介紹 ngOnChanges 基礎用法
ngOnChanges:
觸發的時機點:component如果,
當父類別透過透過Property Binding (屬性繫結)將資料傳到子元件,
子元件透過宣告 @Input() 的變數來接收父類別傳來的資料,
子元件的ngOnChange就會被觸發,
當父類別的來源資料有異動的時候,也會重新觸發 ngOnChanges()
執行的先後順序
constructor() => ngOnChanges() => ngOnInit()
範例說明:
建立兩個component :
ng g c demo-parent
ng g c demo-child
在父元件裡面設定一個要給子元件的參數:counter ,預設是0 過兩秒鐘之後累加一次
export class DemoParentComponent implements OnInit {
constructor() {}
counter = 0;
ngOnInit() {
setTimeout(() => {
this.counter++;
}, 3000);
}
}
接著在template內透過Property Binding (屬性繫結)將資料傳到子元件
<p>
demo-parent works!
</p>
<app-demo-child [iCounter]="counter"></app-demo-child>
然後開始改子元件的component.ts
寫 ngOnChanges() 的時候建議可以加入interface OnChanges,這樣打錯字或是 ngOnChanges() 打錯字的錯誤就可避免
新增一個 @Input() iCounter;
然後依序在三個事件內加入console.log ,可以觀察三個事件的執行先後順序
export class DemoChildComponent implements OnInit, OnChanges {
@Input() iCounter;
constructor() {
console.log('Child component constructor');
}
ngOnInit() {
console.log('Child component ngOnInit');
}
ngOnChanges() {
console.log('Child component ngOnChanges');
}
}
執行結果如下:
可看到執行先後順序
constructor() => ngOnChanges() => ngOnInit()
因為在父元件那邊有寫了一個 setTimeout 過了三秒鐘累加counter的值
累加之後,子元件的 @Input() iCounter 資料也改變了,所以會在觸發一次 ngOnChanges()事件
ngOnChanges() 參數
ngOnChanges() 的參數型態是一個物件,
假設父元件傳遞了兩個以上的 @Input() 到子元件
子元件的 ngOnChanges() 接收到的物件就會有兩個屬性,一個是inItem、一個是inContent
也就是在子元件宣告的 @Input() 名稱
inItem、inContent 這個兩屬性名稱對應的又是另外的物件
物件內的currentValue 才是真正傳進來的值
以下圖為例:inItem 接收的是一個物件、inContent 接收的是一個字串
除了 currentValue 之外還有 firstChange、previousValue 讓開發人員去判斷是否為第一次變更、上一次的值是什麼
在ngChanges 裡面,可以用判斷 @Input() 變數名稱 的方式來設計要獨立的後續作業
@Input() inItem;
@Input() inContent;
ngOnChanges(changeItems) {
if (changeItems.inItem) {
// inItem 要做的事情
this.OriItem = changeItems.inItem.currentValue;
this.inItem = Object.assign({}, changeItems.inItem.currentValue);
}
if (changeItems.inContent) {
// inContent 要做的事情
}
}