标签: angular-reactive-forms

如何在 Angular 模板中获取表单控件验证错误

我有一个表单,它根据下拉列表中的某些值更改其验证。如果选择 A 大学,那么最低百分比要求为 60,如果选择 B 大学,则最低百分比会下降到 55。尽管我已经找到了一种方法来获取模板中的最小错误,这样我就不必费力了在我的模板中编写百分比值。虽然我不确定这是否是正确的方法。

<div formGroupName="marks">
  <div class="form-group">
    <label for="email" class="col-lg-3 control-label">Semester 1</label>
    <div class="col-lg-3">
      <input autocomplete="off"
             #sem1
             type="text"
             min="0"
             max="99"
             maxlength="1"
             maxlength="2"
             class="form-control"
             id="email"
             placeholder="Sem 1 (%)"
             (keypress)="onlyNumberKey($event)"
             formControlName="sem1">
      <span *ngIf="registrationForm.controls['marks'].controls['sem1'].hasError('required') &&
                   registrationForm.controls['marks'].controls['sem1'].touched"
                   class="text-danger">
        Sem 1 percentage required
      </span>
      <span *ngIf="registrationForm.controls['marks'].controls['sem1'].hasError('min') ||
                   registrationForm.controls['marks'].controls['sem1'].hasError('max') ||
                   registrationForm.controls['marks'].controls['sem1'].hasError('minlength')||
                   registrationForm.controls['marks'].controls['sem1'].hasError('maxlength') &&
                   registrationForm.controls['marks'].controls['sem1'].touched"
                   class="text-danger">
        Percenatge must be {{ registrationForm.get('marks.sem1')._errors.min.min }}  and above.
      </span>
    </div>
  </div>
</div>
Run Code Online (Sandbox Code Playgroud)

成分

registrationForm = new FormGroup({
  college: new FormControl('', [
    Validators.required, dropDrownValidator
  ]),
  marks: new FormGroup({ …
Run Code Online (Sandbox Code Playgroud)

angular2-forms angular angular-reactive-forms

6
推荐指数
1
解决办法
2万
查看次数

响应式表单 setValidator 和 updateOn

我试图在 formControl 上动态设置验证器,但似乎无法让 updateOn: "blur" 正常工作。它似乎不是在检查模糊,而是在检查变化。我需要做一些特别的事情才能让它在模糊而不是变化上工作吗?

this.form.get("deviceInfo").controls.deviceNumber.setValidators({validators: [Validators.required, this.checkDeviceExists()], updateOn: 'blur'});
Run Code Online (Sandbox Code Playgroud)

添加了 updateValueAndValidity() 但仍然会在更改时触发而不是模糊

var deviceInfo = this.form.get("deviceInfo");

deviceInfo.controls.deviceNumber.setValidators({validators: [Validators.required, this.checkDeviceExists()], updateOn: 'blur'});
deviceInfo.controls.deviceNumber.updateValueAndValidity();
Run Code Online (Sandbox Code Playgroud)

angular angular-reactive-forms

6
推荐指数
1
解决办法
9430
查看次数

为什么 FormControl#valueChanges 的订阅没有被垃圾收集?

我已经浏览过很多线程,说需要取消订阅FormControl#valueChanges以防止内存泄漏。我了解“何时”和“如何”取消订阅Observables。据我了解,产生无限数量值的 Observables 需要取消订阅,这FormControl#valueChanges就是其中之一Observable。

Observables但我的问题是,为什么这些垃圾没有被收集?我的意思是,当 Angular 组件被破坏时,引用就消失了,对吧?模板中的表单控件不再存在。实例FormControl也消失了。Observable因此,如果、 、的“源”FormControl消失了,那么它的成员为何valueChanges仍然存在并保留其订阅呢?

memory-leaks observable rxjs angular angular-reactive-forms

6
推荐指数
1
解决办法
331
查看次数

使用动态/更新参数的 Angular 7 自定义验证

我正在使用 Angular 7 和材料设计组件

我需要将 requireMatch 验证添加到 mat-autocomplete 中。

我已经使用参数创建了自定义验证,但参数值确实会动态变化。

下面是我的组件代码。

this.stepFormGroup = this.formBuilder.group({
    AccessCode: ["", [Validators.required, this.requireMatch(this.accessCodeList)]]
});

////require-match validation for access-code
requireMatch = (accessCodes: string[]) => {
    return (control: FormControl) => {
        const selection: any = control.value;
        console.log("accessCodes", accessCodes, "selection", selection);
        if (accessCodes.indexOf(selection)===-1) {
            return { requireMatch: true };
        }
        return null;
    }
}
Run Code Online (Sandbox Code Playgroud)

accessCodes我面临的问题是我的内部总是空的(init)requireMatch。

的更改this.accessCodeList不会反映到验证器。

意味着更改后this.accessCodeList它不会在requireMatch验证器中获得更新的数组。

那么有人知道如何在自定义验证器中传递动态参数吗?

angular-validation angular angular-reactive-forms angular-validator

6
推荐指数
1
解决办法
7405
查看次数

是否可以在响应式表单控件上触发 statusChanges 而无需触发 valueChanges?

我有一个FormGroup具有多个嵌套组和控件的。其中大多数包含验证器,例如Validators.required. 每当用户单击提交按钮时,我都会递归地循环遍历表单,以确保触发每个验证器并且每个控件都有效。这是通过将每个控件标记为 Touched 并调用 来完成的control.updateValueAndValidity()。

然而,这会触发valueChanged和statusChanged事件。我已向该事件添加了订阅者statusChanged,该事件应该处理任何错误,但我不希望触发,valueChanged因为该值没有更改。

是否可以在statusChanged不开火的情况下手动开火valueChanged?传递{ emitEvent: false }到updateValueAndValidity将阻止这两个事件被触发。

public ngOnInit(): void {
    const form = this.formBuilder.group({
        'name': ['', Validators.required],
        'address': this.formBuilder.group({
            'street': ['', Validators.required],
            'number': ['', Validators.required]
        })
    });

    form.valueChanges.subscribe(() => console.log('Should not fire'));
    form.statusChanges.subscribe(() => console.log('Should fire'));

    this.validateForm(form);

    console.log(form.valid);
}

private validateForm(control: AbstractControl): void {
    if (control instanceof FormControl) {
        control.markAsTouched();
        control.markAsDirty();
        control.updateValueAndValidity();
    } else …
Run Code Online (Sandbox Code Playgroud)

angular angular-reactive-forms

6
推荐指数
1
解决办法
6416
查看次数

Angular Reactive Forms - 实现输入组件包装器的最佳方式?

我试图解决的任务:

创建可重复使用的输入组件包装器,以节省编写表单模板时的时间。

我的意思的例子:

而不必编写以下模板:

<form [formGroup]="myForm">
  <mat-form-field>
    <input matInput placeholder="Email" [formControl]="email" required>
    <mat-error *ngIf="email.invalid">{{getErrorMessage()}}</mat-error>
  </mat-form-field> 
<form>
Run Code Online (Sandbox Code Playgroud)

我想写:

<form [formGroup]="myForm">
    <my-input-component [form]="myForm" [myFormControl]="email" [myFormControlName]="'email'" [label]="'Email'"></my-input-component>
</form>
Run Code Online (Sandbox Code Playgroud)

我的输入组件看起来像:

<mat-form-field [formGroup]="form">
    <input
        matInput
        type="text"
        [attr.inputmode]="inputMode"
        [placeholder]="label"
        [formControlName]="myFormControlName"
    />
    <mat-error class="errors" *ngIf="myFormControl.invalid">
        <div>{{ getError() }}</div>
    </mat-error>
</mat-form-field>
Run Code Online (Sandbox Code Playgroud)

这是按原样工作的,但我不知道这是否是将 FormGroup 和 FormControls 作为绑定传递的好方法。

在网上搜索后,我不断遇到NG_CONTROL_VALUE_ACCESSOR,并且有点困惑是否可以或应该在我的场景中使用它。

我不打算让这些组件成为“自定义”,即使用滑块作为表单控件或类似性质的东西,而只是希望“包装器”来节省一些时间。

任何有关该主题的建议或建议将不胜感激!

angular-material angular angular-reactive-forms

6
推荐指数
1
解决办法
4819
查看次数

为什么表单错误的 getter 在我的 Angular Reactive Form 组件模板中不起作用,但直接引用却可以?

快速提问。这是那些令人烦恼的小错误之一。我在延迟加载的注册模块中有一个 Angular 反应形式。代码结构如下:

TS

get email() {
  return this.myForm.get('email');
}
// This code works from within the component, but not when referenced from within the template.
Run Code Online (Sandbox Code Playgroud)

超文本标记语言

<div class="errors" *ngIf="email.errors?.required && email.touched">Must enter email</div>
Run Code Online (Sandbox Code Playgroud)

在模板中,div 永远不会显示,因为即使存在错误,表达式也永远不会计算为 true。我已经检查过控制台。

更令人困惑的是,我在 中使用 getter 没有问题component.ts,事实上,我的方式console.log是通过编写console.log(this.email.errors). 这很好用。但模板中没有。

我的混乱解决方案是直接访问错误,这确实有效:

<div class="errors" *ngIf="myForm.controls.email.errors.required && myForm.controls.email.touched">
  Must enter email
</div>
// This works! As you can see the expression is very long and messy.
Run Code Online (Sandbox Code Playgroud)

任何帮助表示赞赏!

typescript angular angular-reactive-forms angular-template-form

6
推荐指数
1
解决办法
5424
查看次数

如何将 FormControl 从模板传递给函数?

假设我有这个:

<input formControlName="someName" (click)="onClick()">
Run Code Online (Sandbox Code Playgroud)

我希望我的onClick函数是通用的,并设置相应的值FormControl(我单击的函数)。

我如何将相关内容FormControl作为 的参数传递onClick?

我以为我可以从FormControlDirective或FormControlNamecontrol的属性中检索它,但它们都没有属性。exportAs

javascript angular angular-reactive-forms

6
推荐指数
1
解决办法
2万
查看次数

类型“AbstractControl | null' 不可分配给类型'FormGroup'

我[formGroup]在 Angular 中传递给子组件时遇到问题。它说Type 'AbstractControl | null' is not assignable to type 'FormGroup'。我想我已经设置了所有安全条件并且我已经很好地初始化了它。我不明白为什么这种情况仍然发生。错误是在[formGroup]="linkAccounts?.get('bank')"这个link-accounts.component.html

注册.组件.ts

linkAccountsForm = this.formBuilder.group({
  bank: this.formBuilder.group({
    bank_name: [null, Validators.required],
    account_name: [null, Validators.required],
    account_number: [null, Validators.required],
    swift_code: [null, Validators.required],
  }),
  credit_card: this.formBuilder.group({
    name: [null, Validators.required],
    card_number: [null, Validators.required],
    cvc: [null, Validators.required],
    exp_date: [null, Validators.required],
  }),
});
Run Code Online (Sandbox Code Playgroud)

注册.component.html

<form
  [formGroup]="linkAccountsForm"
  (ngSubmit)="onLinkAccount(linkAccountsForm)"
>
  <app-link-accounts
    [linkAccounts]="linkAccountsForm"
    [step]="step"
    [submitted]="submitted"
  ></app-link-accounts>
</form>
Run Code Online (Sandbox Code Playgroud)

链接账户.component.ts

 @Input() linkAccounts!: FormGroup;
 @Input() step!: number;
 @Input() submitted!: boolean;
Run Code Online (Sandbox Code Playgroud)

链接-accounts.component.html

<div [formGroup]="linkAccounts" *ngIf="step === …
Run Code Online (Sandbox Code Playgroud)

typescript angular angular-reactive-forms angular-forms

6
推荐指数
1
解决办法
1万
查看次数

Angular 14 中的类型化表单显示“&lt;any&gt;”而不是类型

在使用最新版本的 Angular(版本 14)时,我似乎没有做得很好,因此严格类型化的反应式表单无法按预期工作。

表单是ngOnInit使用injected在内部初始化的FormBuilder。

 public form!: FormGroup;

 constructor(private formBuilder: FormBuilder) {}

 ngOnInit(): void {
    this.initializeForm();
  }

  private initializeForm(): void {
    this.form = this.formBuilder.group({
      title: ['', [Validators.required, Validators.minLength(3)]],
      content: ['', Validators.required],
    });
  }
Run Code Online (Sandbox Code Playgroud)

现在,当我尝试访问表单的控件时,没有自动完成功能,类型为FormGroup<any>。此外,当尝试访问对象上不存在的控件时,它不会引发错误FormGroup。

  • 例子:

在此输入图像描述

  • package.json

在此输入图像描述

  • 角度官方文档:

https://angular.io/guide/typed-forms

forms typescript angular angular-reactive-forms angular14

6
推荐指数
1
解决办法
4320
查看次数