Angular中,控件创建后如何给FormControl添加Validator?
In Angular, how to add Validator to FormControl after control is created?
我们有一个具有动态构建表单的组件。添加带有验证器的控件的代码可能如下所示:
var c = new FormControl('', Validators.required);
但是假设我想在以后 添加第二个验证器。我们怎样才能做到这一点?我们在网上找不到任何文档。我确实发现在表单控件中有 setValidators
this.form.controls["firstName"].setValidators
但不清楚如何添加新的或自定义的验证器。
您只需传递 FormControl
验证器数组。
下面的示例展示了如何向现有的 FormControl 添加验证器:
this.form.controls["firstName"].setValidators([Validators.minLength(1), Validators.maxLength(30)]);
请注意,这将重置您在创建 FormControl
时添加的任何现有验证器。
Angular 12更新
从Angular 12开始,如果你想在不删除现有验证器的情况下向表单添加新的验证器,你可以使用addValidator
:
this.form.controls["firstName"].addValidators([Validators.minLength(1), Validators.maxLength(30)]);
添加@Delosdos 发布的内容。
为FormGroup
中的控件设置验证器:
this.myForm.controls['controlName'].setValidators([Validators.required])
从 FormGroup 中的控件中删除 验证器:
this.myForm.controls['controlName'].clearValidators()
更新 FormGroup 一旦你有 运行 以上任何一行。
this.myForm.controls['controlName'].updateValueAndValidity()
这是一种以编程方式设置表单验证的绝妙方法。
如果您使用的是 reactiveFormModule 并且 formGroup 定义如下:
public exampleForm = new FormGroup({
name: new FormControl('Test name', [Validators.required, Validators.minLength(3)]),
email: new FormControl('test@example.com', [Validators.required, Validators.maxLength(50)]),
age: new FormControl(45, [Validators.min(18), Validators.max(65)])
});
比您能够使用这种方法向 FormControl 添加新的验证器(并保留旧的验证器):
this.exampleForm.get('age').setValidators([
Validators.pattern('^[0-9]*$'),
this.exampleForm.get('age').validator
]);
this.exampleForm.get('email').setValidators([
Validators.email,
this.exampleForm.get('email').validator
]);
FormControl.validator returns 包含所有先前定义的验证器的组合验证器。
我认为选择的答案不正确,因为原问题是 "how to add a new validator after create the formControl"。
据我所知,这是不可能的。您唯一能做的就是动态创建验证器数组。
但是我们想念的是函数 addValidator() 不会覆盖已经添加到 formControl 的验证器。如果有人对此要求有答案,很高兴张贴在这里。
除了 Eduard Void 的答案之外,还有 addValidators
方法:
declare module '@angular/forms' {
interface FormControl {
addValidators(validators: ValidatorFn[]): void;
}
}
FormControl.prototype.addValidators = function(this: FormControl, validators: ValidatorFn[]) {
if (!validators || !validators.length) {
return;
}
this.clearValidators();
this.setValidators( this.validator ? [ this.validator, ...validators ] : validators );
};
使用它您可以动态设置验证器:
some_form_control.addValidators([ first_validator, second_validator ]);
some_form_control.addValidators([ third_validator ]);
一个简单的解决方案是首先获取表单控件中的所有验证器,并在需要时为其分配一个新的 validatorFn 代码将像这样。
//get existing validators and assign a new validator
const formControl = this.form.controls["firstName"];
const validators: ValidatorFn[] = !!formControl.validator ?
[formControl.validator, Validators.required] :
[Validators.required];
formControl.setValidators(validators);
formControl.validtor 持有现有的验证器(不是 asyncValidators)
我们使用三元检查它是否不为空并添加到它(这里我们向它添加所需的验证器),否则,我们只分配我们的新验证器
如果您需要删除添加的表单控件上的某些现有验证,请在控件上调用以下函数
this.form.controls["name"].clearValidators();
之后你需要调用下面的函数来更新表单控件,它会立即在表单控件上生效。
this.form.controls['name'].updateValueAndValidity();
如果您需要在已添加的表单控件上添加一些验证,请在控件上调用以下函数
this.signupForm.controls['name'].setValidators([Validators.required]);
之后立即调用updateValueAndValidity()
函数,所以它会立即反映出来。
我们有一个具有动态构建表单的组件。添加带有验证器的控件的代码可能如下所示:
var c = new FormControl('', Validators.required);
但是假设我想在以后 添加第二个验证器。我们怎样才能做到这一点?我们在网上找不到任何文档。我确实发现在表单控件中有 setValidators
this.form.controls["firstName"].setValidators
但不清楚如何添加新的或自定义的验证器。
您只需传递 FormControl
验证器数组。
下面的示例展示了如何向现有的 FormControl 添加验证器:
this.form.controls["firstName"].setValidators([Validators.minLength(1), Validators.maxLength(30)]);
请注意,这将重置您在创建 FormControl
时添加的任何现有验证器。
Angular 12更新
从Angular 12开始,如果你想在不删除现有验证器的情况下向表单添加新的验证器,你可以使用addValidator
:
this.form.controls["firstName"].addValidators([Validators.minLength(1), Validators.maxLength(30)]);
添加@Delosdos 发布的内容。
为FormGroup
中的控件设置验证器:
this.myForm.controls['controlName'].setValidators([Validators.required])
从 FormGroup 中的控件中删除 验证器:
this.myForm.controls['controlName'].clearValidators()
更新 FormGroup 一旦你有 运行 以上任何一行。
this.myForm.controls['controlName'].updateValueAndValidity()
这是一种以编程方式设置表单验证的绝妙方法。
如果您使用的是 reactiveFormModule 并且 formGroup 定义如下:
public exampleForm = new FormGroup({
name: new FormControl('Test name', [Validators.required, Validators.minLength(3)]),
email: new FormControl('test@example.com', [Validators.required, Validators.maxLength(50)]),
age: new FormControl(45, [Validators.min(18), Validators.max(65)])
});
比您能够使用这种方法向 FormControl 添加新的验证器(并保留旧的验证器):
this.exampleForm.get('age').setValidators([
Validators.pattern('^[0-9]*$'),
this.exampleForm.get('age').validator
]);
this.exampleForm.get('email').setValidators([
Validators.email,
this.exampleForm.get('email').validator
]);
FormControl.validator returns 包含所有先前定义的验证器的组合验证器。
我认为选择的答案不正确,因为原问题是 "how to add a new validator after create the formControl"。
据我所知,这是不可能的。您唯一能做的就是动态创建验证器数组。
但是我们想念的是函数 addValidator() 不会覆盖已经添加到 formControl 的验证器。如果有人对此要求有答案,很高兴张贴在这里。
除了 Eduard Void 的答案之外,还有 addValidators
方法:
declare module '@angular/forms' {
interface FormControl {
addValidators(validators: ValidatorFn[]): void;
}
}
FormControl.prototype.addValidators = function(this: FormControl, validators: ValidatorFn[]) {
if (!validators || !validators.length) {
return;
}
this.clearValidators();
this.setValidators( this.validator ? [ this.validator, ...validators ] : validators );
};
使用它您可以动态设置验证器:
some_form_control.addValidators([ first_validator, second_validator ]);
some_form_control.addValidators([ third_validator ]);
一个简单的解决方案是首先获取表单控件中的所有验证器,并在需要时为其分配一个新的 validatorFn 代码将像这样。
//get existing validators and assign a new validator
const formControl = this.form.controls["firstName"];
const validators: ValidatorFn[] = !!formControl.validator ?
[formControl.validator, Validators.required] :
[Validators.required];
formControl.setValidators(validators);
formControl.validtor 持有现有的验证器(不是 asyncValidators) 我们使用三元检查它是否不为空并添加到它(这里我们向它添加所需的验证器),否则,我们只分配我们的新验证器
如果您需要删除添加的表单控件上的某些现有验证,请在控件上调用以下函数
this.form.controls["name"].clearValidators();
之后你需要调用下面的函数来更新表单控件,它会立即在表单控件上生效。
this.form.controls['name'].updateValueAndValidity();
如果您需要在已添加的表单控件上添加一些验证,请在控件上调用以下函数
this.signupForm.controls['name'].setValidators([Validators.required]);
之后立即调用updateValueAndValidity()
函数,所以它会立即反映出来。