Reputation: 1077
Please refer the project in a stackblitz here.
As can be seen, I have reactive form with controls as firstNumber
, secondNumber
and thirdNumber
. I need to have validation for form control thirdNumber
such that its value should not be greater than the value of the form control which is having minimum value among firstNumber
and secondNumber
.
The custom validator validateThirdNumber
which is there in the component works fine whenever form control thirdNumber
changes, but I need
fire its validation on changes of form controls firstNumber
and secondNumber
too as the validation logic can change on changes of form controls
firstNumber
and secondNumber
.
For that purpose, I have added an event on change of form controls firstNumber
and secondNumber
where I am marking the form control thirdNumber
as touched
but its validation did not seem to be triggered.
So, how to fire the validation for form control thirdNumber
on changes of form controls firstNumber
and secondNumber
?
Also, why is this.myFormGroup
is undefined some times in custom validator (refer logs in app.componen.ts
at line:22
) even after binding this
to its form control declaration and this.myFormGroup
is defined in the constructor
?
Upvotes: 5
Views: 18451
Reputation: 484
I have created a simpler option if you want to use it. No form control validation used.
<div>
<form [formGroup]="myFormGroup" #formRef="ngForm">
First number:<input #firstNum type="number" formControlName="firstNumber"><br/>
Second number:<input #secondNum type="number" formControlName="secondNumber"><br/>
Third number:<input #thirdNum type="number" formControlName="thirdNumber"><br/>
<span *ngIf="firstNum && thirdNum && (thirdNum.value > firstNum.value)">
Third number cannot be greater than First Number
</span>
<hr>
<span *ngIf="secondNum && thirdNum && (thirdNum.value > secondNum.value)">
Third number cannot be greater than Second Number
</span>
</form>
</div>
And delete all validation in your .ts
file.
If you start creating larger components then the form validation option would be best.
Upvotes: 0
Reputation: 546
the best choice for you is to create your own custom global validator.
class ValidateThirdNumber {
static validate(control: AbstractControl) {
console.log(control);
if(control) {
const firstNumber = control.get('firstNumber').value;
const secondNumber = control.get('secondNumber').value;
const thirdnumber = control.get('thirdNumber').value;
if (firstNumber > secondNumber) {
if (thirdnumber > secondNumber) {
control.get('thirdNumber').setErrors( {greaterThanSecondNumber: true} );
}
} else if (firstNumber < secondNumber) {
if (thirdnumber > firstNumber) {
control.get('thirdNumber').setErrors( {greaterThanFirstNumber: true} );
}
}
}
return null;
}
}
the initialization of form group should be:
this.myFormGroup = this.fb.group({
firstNumber: [0],
secondNumber: [0],
thirdNumber: [0]
}, {validator: [ValidateThirdNumber.validate] });
you don't need the touched attribute any more
<span *ngIf="myFormGroup.get('thirdNumber').errors?.greaterThanFirstNumber">
Third number cannot be greater than First Number
</span>
<span *ngIf=" myFormGroup.get('thirdNumber').errors?.greaterThanSecondNumber">
Third number cannot be greater than Second Number
</span>
also you don't need the (change)
events remove them
Upvotes: 1