Reputation: 4604
My child component as following:
'use strict';
import {Component, Input, OnInit, OnChanges, ChangeDetectionStrategy, ElementRef} from 'angular2/core';
@Component({
changeDetection: ChangeDetectionStrategy.OnPush,
selector: 'my-app',
template: ''
})
export class MyApp implements OnInit {
@Input() options: any;
constructor(private el: ElementRef) {
}
ngOnInit() {
}
ngOnChanges(...args: any[]) {
console.log('changing', args);
}
}
And Parent component as following:
'use strict';
import {Component, Input} from 'angular2/core';
import {MyApp} from './MyApp';
@Component({
selector: 'map-presentation',
template: `<my-app [options]="opts"></my-app>
<button (click)="updates($event)">UPDATES</button>
`,
directives: [MyApp]
})
export class MainApp {
opts: any;
constructor() {
this.opts = {
width: 500,
height: 600
};
}
updates() {
console.log('before changes');
this.opts = {
name: 'nanfeng'
};
}
}
Each time while i clicked the "UPDATES" button, the ngOnChanges
method never be called, but why?
I angular version i am using is "2.0.0-beta.8"
Upvotes: 15
Views: 74249
Reputation: 1295
Looks like you haven't implemented interface OnChanges ..if you implement OnChanges interface then only ngOnChanges will be consider as lifecycle hook function and it will get call on input changes otherwise it will be consider as normal function
Upvotes: 1
Reputation: 339
Well it works with "input properties", this means with those passed in this format: @Input() myVariable: string;
I made it work normally when this input value is a string, number or boolean, but with objects I still do not now what's going on.
So, in the "AppComponent" template (the .html) can go something like this:
<input type="text" [(ngModel)]="name"> // name is a string property of the AppComponent
<app-test [myVal]="name"></app-test>
And the "test component" can look like this:
import {Component, Input } from '@angular/core';
@Component({
selector: 'app-test',
template: `
<div> TEST COMPONENT {{myVal}}</div>
`,
styles: []
})
export class TestComponent {
constructor() { }
ngOnChanges(changeRecord: SimpleChanges) {
console.log('It works!');
/* changeRecord will have a property for each INPUT named the same
as the input. These are added to changeRecord when the input
gets a value */
if(typeof changeRecord.myVal !== 'undefined){
console.log('myVal = ', changeRecord.myVal.currentValue);
}
}
@Input() myVal: string;
}
Cheers.
Upvotes: 3
Reputation: 55443
It's working
app.ts
import {Component} from 'angular2/core';
import {child} from 'src/child';
@Component({
selector: 'my-app',
providers: [],
template: `
<child-cmp [options]="opts"></child-cmp>
<button (click)="updates($event)">UPDATES</button>
`,
directives: [child]
})
export class App {
opts: any;
constructor() {
this.opts = {
width: 500,
height: 600
};
}
updates() {
console.log('after changes');
this.opts = {
name: 'micronyks'
};
}
};
child.ts
import {Input,Component,Output,EventEmitter} from 'angular2/core';
import {Component, Input, OnInit, OnChanges, ChangeDetectionStrategy, ElementRef} from 'angular2/core';
@Component({
selector: 'child-cmp',
changeDetection: ChangeDetectionStrategy.OnPush,
template: `
`
})
export class child {
@Input() options: any;
ngOnChanges(...args: any[]) {
console.log('onChange fired');
console.log('changing', args);
}
}
Upvotes: 17