Angular-如何验证Angular Material步进器中的每个步骤



在Angular-12中,我正在实现Material Stepper。它有两(2(个步骤:

组件:

export class SignupCompanyComponent implements OnInit {
isLinear = true;
isLoading = false;
companySetupForm!: FormGroup;
companyForm!: FormGroup;
idForm!: FormGroup;
ngOnInit() {
this.companyForm = this.fb.group({
companyName: ['', [Validators.required, Validators.minLength(3), Validators.maxLength(100)]]
});
this.idForm = this.fb.group({
registrationNumber: ['', [Validators.required, Validators.maxLength(100)]],
});
}
get fc() {
return this.companyForm.controls;
};
get fi() {
return this.idForm.controls;
};
onSubmit() {}
}

HTML:

<mat-horizontal-stepper [linear]="isLinear" #stepper labelPosition="bottom">
<mat-step [stepControl]="companyForm">
<form [formGroup]="companyForm">
<ng-template matStepLabel matStepperIcon="phone">Company Info</ng-template>
<div class="col-12 col-md-12">
<div class="form-group">
<label for="name">Company Name:<span style="color:red;">*</span></label>}
<input type="text" formControlName="companyName" placeholder="Company Name" class="form-control" required/>
</div>
<div *ngIf="fc.companyName.touched && fc.companyName.invalid">
<div *ngIf="fc.companyName.hasError('required')">
<div class="text-danger">
Company Name is required!
</div>
</div>
<div *ngIf="fc.companyName.hasError('minlength')">
<div class="text-danger">
Company Name cannot be less than 3 characters!
</div>
</div>
<div *ngIf="fc.companyName.hasError('maxlength')">
<div class="text-danger">
Company Name cannot be more than 100 characters!
</div>
</div>
</div>
</div>
<div class="card-footer">
<button mat-raised-button color="primary" matStepperNext>Next</button>
</div>
</form>
</mat-step>
<mat-step [stepControl]="idForm">
<form [formGroup]="idForm">
<ng-template matStepLabel>Company ID</ng-template>
<div class="col-12 col-md-4">
<div class="form-group">
<label for="registration_number">Registration Number:<span style="color:red;">*</span></label>
<input type="text" formControlName="registrationNumber" placeholder="Registration Number" class="form-control" required/>
</div>
<div *ngIf="fi.registrationNumber.touched && fi.registrationNumber.invalid">
<div *ngIf="fi.registrationNumber.hasError('required')">
<div class="text-danger">
Company Reg. No. is required!
</div>
</div>
<div *ngIf="fi.registrationNumber.hasError('maxlength')">
<div class="text-danger">
Company Reg. No. cannot be more than 100 characters!
</div>
</div>
</div>
</div>
<div class="card-footer">
<button mat-raised-button color="black" matStepperPrevious>Back</button> &nbsp;
<button mat-raised-button color="success" [disabled]="isLoading" type="submit" (click)="onSubmit()">
<span *ngIf="isLoading" class="spinner-border spinner-border-sm mr-1"></span>
Submit
</button> &nbsp;
<button mat-raised-button color="warn" (click)="stepper.reset()">Reset</button>
</div>
</mat-step>
</mat-horizontal-stepper>

当触摸每个formControl时,"材质步进器"工作正常。它会立即显示错误。但是,当点击下一步按钮时,步骤1(companyForm(中没有填写任何数据,尽管它没有移动到下一步或表单,但没有显示错误。

我希望它能验证每个步骤,并在触摸每个表单控件时显示出来。

我该如何做到这一点?

感谢

材料似乎没有将表单标记为已触摸,所以我会重新绑定按钮:

<button mat-raised-button color="primary" (click)="onFirstStepDone()">Next</button>

在组件中,您需要一个对步进器的引用:

@ViewChild('stepper') stepper: MatHorizontalStepper;
onFirstStepDone() {
if(!this.companyForm .valid) {
// this should make all invalid fields light up in red
this.companyForm.markAllAsTouched();
return;
}
this.stepper.next();
}

我做的两件事是将字段验证设置为类似onBlur

this.companyForm = this.fb.group({
companyName: ['',
[Validators.required,
Validators.minLength(3),
Validators.maxLength(100)]]
},
{ updateOn: "blur" });

就我个人而言,我不喜欢允许继续,直到所需的字段有效,所以我将步进器按钮设置为禁用,直到它像这样;

<button mat-raised-button
color="primary"
matStepperNext
[disabled]="companyForm.status != 'VALID'">
Next
</button>

或者一定要看到下面Manhattan先生的评论来验证最后的表单,您可以通过将上面的{ updateOn: "blur" }blur更改为submit来完成同样的事情

最新更新