It's been a couple of months since I'm using Ionic Framework (ionic-angular 3.9.2 latest) to build Progressive Web Apps. In the meantime, I've always wondered the difference between ngOnInit
and ionViewWillLoad
.
If I'm not wrong, I believe that ngOnInit
is an Angular lifecycle hook and it initializes the directive and component. (Sets the directive/component's input properties.)
ionViewWillLoad
is an Ionic navigation lifecycle event, and it seems to get executed before ionViewDidLoad
(Everything has been already loaded) event gets fired. It looks like ionViewWillLoad
event has not added to NavController, and the documentation also has not updated yet.
As far as I know, the constructor gets called by the JavaScript engine, and it should be avoided using it for complex initializations. (details: why you should avoid complex constructor logic)
For this reason, I've used ionViewWillLoad
to set up the component after Ionic sets the input properties.
I'm not sure why, but ionViewWillLoad
was the only event that worked without getting any errors.
export class UsernamePage {
usernameControl: FormControl;
constructor(private userService: UserServiceProvider){ }
// No errors
ionViewWillLoad() { this.createUsernameForm(); }
// Errors
ionViewWillEnter() { this.createUsernameForm(); }
ionViewDidEnter() { this.createUsernameForm(); }
ionViewDidLoad() { this.createUsernameForm(); }
createUsernameForm() {
this.usernameControl = new FormControl('',
{
validators: [Validators.required, Validators.minLength(4)],
asyncValidators: CustomValidator.username(this.userService)
});
}
}
Should I stick with using ionViewWillLoad
? Or is it better to implement OnInit interface? What's the difference?
In other words, The ngOnInit () lifecycle hook Initialize the component after Angular first displays the data-bound properties and sets the component’s input properties It is a guarantee that our bindings are readily available. It is called only once.
ngOnInit - Initialize your component and load data from services that don't need refreshing on each subsequent visit. ionViewWillEnter - Since ionViewWillEnter is called every time the view is navigated to (regardless if initialized or not), it's a good method to load data from services.
The ngOnInit or OnInit hook is called when the component is created for the first time. This hook is called after the constructor and first ngOnChanges hook is fired. This is a perfect place where you want to add any initialization logic for your component. Note that ngOnChanges hook is fired before ngOnInit.
The ngOnInit is Angular specific and is called when the Angular has initialized the component with all its input properties The @Input properties are available under the ngOnInit lifecycle hook.
Note: For V3, I use the terms "hooks" and "events" interchangeably when referring to the lifecycle methods.
From what I can tell, ionViewWillLoad
is not one of the lifecycle hooks in the latest version of Ionic V3. I'd be curious to know specifically what errors you're seeing for the other life cycle events. But for now, I'm aiming this answer at a few underlying questions:
1) What is the difference between Angular's ngOnInit
and Ionic's ionViewDidLoad
? Is one better than the other?
Interestingly enough, there seems to be overlapping purpose between Angular's ngOnInit
and ngOnDestroy
lifecycle hooks and Ionic's ionViewDidLoad
and ionViewWillUnload
lifecycle events (respectively). They are only called when a page is created or deleted (respectively), which may not happen as often as you think because of how Ionic tends to cache pages for a better mobile experience.
In child/sub components for V3, your only choice is to use the Angular lifecycle hooks. In page-level components for V3 (AKA components that are pushed/popped from a NavController
) you can use them interchangeably, but I would just choose one or the other, not both, and be consistent. In Ionic V4, they made this choice for you by removing ionViewDidLoad
and ionViewWillUnload
.
2) What is the difference between Angular's ngOnInit
and Ionic's ionViewWillEnter
? Is one better than the other?
Firstly, these questions only apply to page-level components because Ionic Lifecycle events can only be used in page-level components (V3 documentation). Child/sub components do not know anything about Ionic Lifecycle Events because they aren't being pushed/popped by the NavController
(this might be the reason why you were seeing errors?).
The major difference between these two particular events is the sequence in which they fire and how often they fire. When a page-level component is created, ngOnInit
will fire before before ionViewWillEnter
. However pages are not necessarily destroyed (and therefore will not be recreated later) unless they are popped off the navigation stack (V3 documentation).
By default, pages are cached and left in the DOM if they are navigated away from but still in the navigation stack (the exiting page on a
push()
for example). They are destroyed when removed from the navigation stack (onpop()
orsetRoot()
).
I wouldn't say that one is better than the other. You can implement both. Just be aware that ngOnInit
may not fire as often/consistently as you'd expect. ionViewWillEnter
fires whenever the page is about to enter and become the active page.
For Ionic V4 (Angular)
Lifecycle events are much more straightforward in V4. There are half as many Ionic lifecycle events and they don't overlap in functionality with Angular lifecycle events like I mentioned for v3. There are good explanations for each and actual guidance around the usage of Angular and Ionic lifecycle events
The main takeaways are similar (and I believe applicable to V3).
Pages are only removed from the DOM when they are "popped", for instance, by pressing the back button in the UI or the browsers back button.
Because of this special handling, the
ngOnInit
andngOnDestroy
methods might not fire when you would usually think they should.
ngOnInit
will only fire each time the page is freshly created, but not when navigated back to the page. For instance, navigating between each page in a tabs interface will only call each page'sngOnInit
method once, but not on subsequent visits.ngOnDestroy
will only fire when a page "popped".
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