Reputation: 73
I'm trying to create a custom Input component using Reative Form in Angular 7
but i'm having trouble passing events to the input field.
My component
has a label and an input field and a specific layout. My component html
looks like this:
<div id="customInputGroup" [formGroup]="parentFormGroup" [ngClass]="{'input-value': hasValue()}">
<label [for]="inputId">{{label}}</label>
<input [id]="inputId" [name]="inputName" class="form-control" [placeholder]="placeholder" [formControlName]="inputName" [mask]="mask">
</div>
And in my Component
:
@Component({
selector: 'app-input-field',
templateUrl: './input-field.component.html',
styleUrls: ['./input-field.component.css']
})
export class InputFieldComponent implements OnInit {
@Input('placeholder') placeholder = '' ;
@Input('label') label = '';
@Input('inputId') inputId = '';
@Input('inputName') inputName = '';
@Input('parentFormGroup') parentFormGroup:FormGroup;
@Input('mask') mask;
constructor() { }
ngOnInit() {
}
hasValue(){
return (this.parentFormGroup.get(this.inputName).value != undefined
&& this.parentFormGroup.get(this.inputName).value != null
&& this.parentFormGroup.get(this.inputName).value != '')
}
Everything was working fine till i had to handle an input onBlur
event(or it could be any other input event).
The result i want is to call my component
passing any event like this:
<app-input-field (blur)="functionName()"></app-input-field>
or
<app-input-field (keyup)="functionName()"></app-input-field>
And my component
will be able to pass these events to my input field 'dynamically'. Is it possible to do it?
Upvotes: 5
Views: 11235
Reputation: 22213
Events like blur
works on input field
, not selectors like <app-input-field>
You can emit event for all events like blur, keyup, mouseover etc..
InputFieldComponent:
HTML:
<input (blur)="functionName('blur')" (keyup)="functionName('keyUp')" [id]="inputId" [name]="inputName" class="form-control" [placeholder]="placeholder" [formControlName]="inputName" [mask]="mask">
TS:
@Output() OnInputEvent= new EventEmitter();
functionName(eventName) {
this.OnInputEvent.emit(eventName);
}
In your component:
<app-input-field (OnInputEvent)="functionName($event)"></app-input-field>
TS:
functionName(event) {
switch (event) {
case "blur":
...
break;
case "keyUp":
...
break;
}
}
Upvotes: 5
Reputation: 24424
for blur event you need to create a eventemitter with the same name and emit this event on input elemnt blur emit
export class InputFieldComponent implements OnInit {
@Output() blur:EventEmitter<any> = new EventEmitter(); // 👈
constructor() { }
ngOnInit() {
}
}
template
<input type="text" (blur)="blur.emit($event)" >
app.template
<app-input-field (blur)="onBlur($event)" (keyup)="onKeyup($event)"></app-input-field>
we did this for the blur event because the event is not bubble where the keyup will work without create any custom event because it bubble.
you can implement two way data binding like this
@Input() value:EventEmitter<any> = new EventEmitter();
@Output() valueChange:EventEmitter<any> = new EventEmitter();
template
<app-input-field [(value)]="name" ></app-input-field>
any bubble event like input,keypress,keyup,keydown you can capture on the element itself or you can work around it like what we did on blur event.
Upvotes: 5