Custom event types in Ionic
In Ionic 6, component events have well-documented, strongly typed arguments. This should allow them to be used in such event handlers:
onInputChange(inputEvent: InputCustomEvent) {
console.log(inputEvent.detail.value);
}
Provided, of course, you have the following markup in the template:
<ion-input (ionChange)="onInputChange($event)"></ion-input>
Unfortunately, the outputs in Angular are still typed as Event
so ionic build --prod
for the above code fails with the following error message:
Type 'Event' is missing the following properties from type 'InputCustomEvent': detail, initCustomEvent
Even ionic serve
would fail with the same error if it were not for the aot: false
setting for the default build in the generated angular.json
.
The issue has already been reported and there is even a fix for it, but it did not make it into Ionic 6 as it would involve a breaking change. So until the fix is released, you'll have to settle for one of the workarounds below:
The simplest solution would be to abandon strong typing altogether and just use
any
for the argument type in the event handler:onInputChange(inputEvent: any) { console.log(inputEvent.detail.value); }
The obvious drawback is that the compiler cannot now detect type errors when accessing
InputCustomEvent
.A better solution is to cast the input argument to the correct type before using it. This also allows you to use
Event
for the type argument:onInputChange(event: Event) { const inputEvent = event as InputCustomEvent; console.log(inputEvent.detail.value); }
This provides more type safety than the first alternative, but you can still accidentally call the method with the wrong argument type, either from the template or from code.
The best solution, in my opinion, is to keep the correct argument type in the code and do the casting in the template. Since type casts are not supported in Angular templates, this requires another helper method:
asInputCustomEvent(event: Event) { return event as InputCustomEvent; } onInputChange(inputEvent: InputCustomEvent) { console.log(inputEvent.detail.value); }
This is how you could call the method from the markup:
<ion-input (ionChange)="onInputChange(asInputCustomEvent($event))" ></ion-input>
It's still not completely type-safe, but it makes it harder to make a mistake. And I think this is the most type safety that can be achieved before the problem is fixed in Ionic. The code is perfectly type safe as long as you do not call
asInputCustomEvent
. You should only call this method from the markup for outputs that have this argument type documented.
You can find a working example project showing all 4 approaches in my GitHub repository.
In Ionic 6, custom component events have strongly typed arguments. Unfortunately, they cannot yet be used in this way in Angular. Until a solution to this problem is released, there are several workarounds. In this post I present all of them that I can think of, each with their advantages and disadvantages.