Following this good article on angular's change detection, I wanted to debug the checkAndUpdateView function. However, it is never triggered.
What am I missing? I tried with the latest Chrome and Firefox.
By default, angular will run the change detector every time @Input() data is changed or modified. But with OnPush strategy, the change detector is only triggered if the data passed on @Input() has a new reference.
To run the change detector manually: Inject ChangeDetectorRef service in the component. Use markForCheck in the subscription method to instruct Angular to check the component the next time change detectors run. On the ngOnDestroy() life cycle hook, unsubscribe from the observable.
An OnPush change detector gets triggered in a couple of other situations other than changes in component Input() references, it also gets triggered for example: if a component event handler gets triggered. if an observable linked to the template via the async pipe emits a new value.
By default, Angular 2+ performs change detection on all components (from top to bottom) every time something changes in your app. A change can occur from a user event or data received from a network request.
That article is old, from 2018, and since then Angular has introduced the Ivy compiler, which completely overhauled the internals of Angular. If you are using Angular 9 or later this breakpoint won't be hit. I tested an Angular 7, 8 and 9 app. Versions 7 & 8 hit the breakpoint, and the Angular 9 app didn't.
I would suggest using this component to debug change detection. Add it to your app and it will count change detection cycles.
debug-change-detection.component.ts:
import { Component, NgZone } from '@angular/core';
@Component({
selector: 'app-debug-change-detection',
template: '<p class="number">{{check()}} zone checks</p>',
styles: [`
:host {
position: absolute;
left: 10px;
bottom: 0;
display: block;
}
.number {
display: block;
}
`]
})
export class DebugChangeDetectionComponent {
count = 0;
constructor(private zone: NgZone) { }
check() {
this.zone.runOutsideAngular(() => {
setTimeout(() => this.count = this.count + 1);
});
return this.count;
}
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With