我的目标是将所有验证消息放在组件而不是html文件中
public buildRegisterForm() { this.userForm = this.fb.group({ firstName: ['',[Validators.required,Validators.minLength(3)]],lastName: ['',Validators.maxLength(50)]],emailGroup: this.fb.group({ email: ['',Validators.pattern(this.emailPattern)]],retypeEmail: ['',Validators.required],},{ validator: formMatcherValidator('email','retypeEmail') }),passwordGroup: this.fb.group({ password: ['',strongPasswordValidator()]],retypePassword: ['',{ validator: formMatcherValidator('password','retypePassword')}),}); }
我正在按照本教程link来实现我想要的东西
将所有验证消息放在组件文件中而不是html文件中.
export const validationMessages = { 'firstName': { 'required': 'Your first name is required.','minlength': 'Your first name must be at least 3 characters long.' },'lastName': { 'required': 'Your last name is required.','minlength': 'Your last name must be less than 50 characters long.' },'emailGroup': { 'email': { 'required': 'Your email is required','pattern': 'Your login email does not seem to be a valid email address.' },'retypeEmail': { 'required': 'Your retype email is required','match': 'The email provided do not match.' },'passwordGroup':{ 'password': { 'required': 'Your password is required','strongPassword': 'Your password must be between 8 - 15 characters and must contain at least three of the following: upper case letter,lower case letter,number,symbol.' },'retypePassword': { 'required': 'Your retype password is required','match': 'The password provided do not match.' } }
onValueChanged方法
private onValueChanged(data?: any) { if (!this.userForm) { return; } const form = this.userForm; // tslint:disable-next-line:forin for (const field in this.formErrors) { // clear prevIoUs error message (if any) this.formErrors[field] = ''; let control = form.get(field); // console.log("control",control.dirty); console.log("controlEmail",control); if (control && (control.dirty || control.touched) && control.invalid) { let messages = validationMessages[field]; // tslint:disable-next-line:forin for (const key in control.errors) { this.formErrors[field] += messages[key] + ' '; } } } }
当我有多个formBuider组或嵌套对象时,此方法不起作用.这1的任何提示?
类似于这个How to validate reactive forms with nested form groups?
我看到它的方式,你需要在onValueChanged(data)-method中创建一个嵌套循环.由于你有很多嵌套组,我不打算复制它.但嵌套循环是通用的,因此它适用于所有组.但这是一个只有一个嵌套组而不是几个嵌套组的例子.我正在使用英雄的例子.
嵌套组名称是group,其中的formcontrol称为child.
因此,代码中使用的formErrors应该具有内部组中的子项:
formErrors = { 'name': '','power': '','group':{ 'child': '' } };
因此,您必须记住在模板中添加验证时,您需要使用:
<div *ngIf="formErrors.group.child"> {{ formErrors.group.child }} </div>
验证消息不在组内,但与其他验证消息一样:
validationMessages = { 'name': { 'required': 'Name is required.','power': { 'required': 'Power is required.' },'child': { 'required': 'Child is required.',} };
最后,修改后的onValueChanges:
onValueChanged(data?: any) { if (!this.heroForm) { return; } const form = this.heroForm; // iterate toplevel of formErrors for (const field in this.formErrors) { // check if the field corresponds a formgroup (controls is present) if(form.get(field).controls ) { // if yes,iterate the inner formfields for(const subfield in form.get(field).controls) { // in this example corresponds = "child",reset the error messages this.formErrors[field][subfield] = ''; // now access the actual formfield const control = form.get(field).controls[subfield]; // validate and show appropriate error message if (control && control.dirty && !control.valid) { const messages = this.validationMessages[subfield]; for (const key in control.errors) { this.formErrors[field][subfield] += messages[key] + ' '; } } } } // does not contain a nested formgroup,so just iterate like before making changes to this method else { const control = form.get(field); this.formErrors[field] = ''; if (control && control.dirty && !control.valid) { const messages = this.validationMessages[field]; for (const key in control.errors) { this.formErrors[field] += messages[key] + ' '; } } } } }
最后,一个DEMO