When using a function to show/hide with *ngIf
the block is not updated in the html.
when rendering the block to check the value ({{contactInfoValid(contact)}}
) it is updated correctly, the *ngIf
is not being triggered
HTML
<mat-form-field>
<input matInput type="text"
[(ngModel)]="contact.info" required>
<mat-error *ngIf="contactInfoValid(contact) == false">
email not correct
</mat-error>
</mat-form-field>
Component
contactInfoValid(contact) {
if (contact.hasValidInfo) {
return true;
}
return false;
}
The mat-error
is never shown.
A FormControl cannot be used in this specific case since it is used in a dynamic grid
The <mat-error>
component need an ErrorStateMatcher
in order to display anything. There's a good article about this here; https://itnext.io/materror-cross-field-validators-in-angular-material-7-97053b2ed0cf
In short you need to specify [errorStateMatcher]="myErrorStateMatcher"
on the form field that you're validating.
<mat-form-field>
<input matInput type="text" [(ngModel)]="contact.info" required
[errorStateMatcher]="myErrorStateMatcher">
<mat-error *ngIf="contactInfoValid(contact) == false">
email not correct
</mat-error>
</mat-form-field>
Normally ErrorStateMatcher works with FormControls, but if you want to use ngModel you can provide custom ErrorStateMatcher that have access to the data you need in order to display error messages. Below is a simplified example of this;
export class RuleErrorStateMatcher<T> implements ErrorStateMatcher {
constructor(private editControl: IValidatableEditControl<T>) { }
isErrorState(control: FormControl | null, form: FormGroupDirective | NgForm | null): boolean {
return this.editControl && this.editControl.model && !this.editControl.model.isValid;
}
}
export interface IValidatableEditControl<T> {
model: ValidationGeneric<T>;
}
export class ValidationGeneric<T> {
public value: T;
public isValid: boolean;
}
If you try another html tag than mat-error you will see that your ngIf is probably working;
<span *ngIf="contactInfoValid(contact) == false">
email not correct
</span>