使用 formControlName 和 ngModel 的 Angular 6 警告

问题描述 投票:0回答:7

我最近将 Angular 版本升级到 6-rc。我收到以下警告

看起来您正在与以下相同的表单字段上使用 ngModel 表单控件名称。支持使用 ngModel 输入属性和 具有反应式表单指令的 ngModelChange 事件已被弃用 在 Angular v6 中,并将在 Angular v7 中删除

有关此内容的更多信息,请参阅此处的 API 文档: https://angular.io/api/forms/FormControlName#use-with-ngmodel

它到底说了什么?该链接没有任何

#use-with-ngmodel

的片段

我想我需要删除

ngModel
并使用 formGroup 作为我的数据绑定对象。

angular angular-ngmodel angular-reactive-forms
7个回答
56
投票

现在您可以在这里找到文档:

https://angular.io/api/forms/FormControlName#use-with-ngmodel-is-deprecated

所以你有3个选择:

  1. 使用反应式表单

  2. 使用模板驱动表单

  3. 静音警告(不推荐)

<!-- language: lang-ts -->

    imports: [
      ReactiveFormsModule.withConfig({warnOnNgModelWithFormControl: 'never'});
    ]

32
投票

从 formGroup 中包含

[(ngModel)]
的每个字段中删除
formControlName
并在控制器类中设置值,如下所示
this.form.get('first').setValue('some value');
不要显式关闭或静音警告。 并获得价值

this.form.get('first').value

另一种实现功能的方法更简单。

this.form.controls.first.setValue('some Value');

并使用表单组作为获取值

this.holidaysForm.value.first;

5
投票

添加

[ngModelOptions]="{standalone: true}" 

您可以从 Angular 网站阅读更多内容https://angular.io/api/forms/NgModel


0
投票

所以我在尝试在

mat-select
中显示用户头像时偶然发现了这一点:

<mat-form-field [formGroup]="assignedToFormGroup">
<mat-select placeholder="Assign to" [(ngModel)]="assignedTo" formControlName="assignTo">
  <mat-select-trigger>
    <img style="vertical-align:middle;" aria-hidden
      src="{{assignedToFormGroup.controls['assignTo'].value.photoUrl}}" height="20" />
    <span>@{{assignedToFormGroup.controls['assignTo'].value.userName}}</span>
  </mat-select-trigger>
  <!-- {{user.userName}} -->
  <mat-option *ngFor="let user of members" [value]="user">
    <img style="vertical-align:middle;" aria-hidden src="{{user.photoUrl}}" height="20" />
    <span>@{{user.userName}}</span>
  </mat-option>
</mat-select>

在控制器中,formGroup是这样定义的:

public assignedToFormGroup: FormGroup;

我听从了 Sohail 的建议,从我的 HTML 代码中删除了

[(ngModel)]

<mat-form-field [formGroup]="assignedToFormGroup">
<mat-select placeholder="Assign to" formControlName="assignTo">
  <mat-select-trigger>
    <img style="vertical-align:middle;" aria-hidden
      src="{{assignedToFormGroup.controls['assignTo'].value.photoUrl}}" height="20" />
    <span>@{{assignedToFormGroup.controls['assignTo'].value.userName}}</span>
  </mat-select-trigger>
  <!-- {{user.userName}} -->
  <mat-option *ngFor="let user of members" [value]="user">
    <img style="vertical-align:middle;" aria-hidden src="{{user.photoUrl}}" height="20" />
    <span>@{{user.userName}}</span>
  </mat-option>
</mat-select>

这在打开页面时给了我错误 - 我尝试从 null 加载 photoUrl 和 userName,因为通过删除 [(ngModel)] 我还删除了

mat-select
中的默认选择。

因此我修改了控制器以执行以下操作: 1.构造函数:

this.assignedToFormGroup.controls['assignTo'].setValue({photoUrl: '', userName: ''});
  1. 我保存表单的按钮操作 - 添加了以下行:

    let assignedTo = this.assignedToFormGroup.controls['assignTo'].value;

这确实有效。现在,我在页面加载时设置默认选择,并在提交表单时读取所选值。 我知道这不是最好、最漂亮的解决方案,但我想我会分享它 - 可能是更好解决方案的一个很好的起点。


0
投票

当我在嵌入式自定义控件中将 [(ngMode)] 与 [formControlName] 一起使用时,我遇到了相同的警告。我的表单是使用 formBuilder.array([]) 动态构建的,我必须保留 [formControlName]:

this.searchForm = this.formBuilder.group({
      dynamicFormArray: this.formBuilder.array([])
});

但是在我删除了双向边界 [(ngMode)] 后,我无法再使用 form.value 从嵌入式自定义控件中获取用户输入值(尽管我可以看到嵌入式控件内的值)!

经过一段时间的痛苦挣扎,我终于找到了一个解决方案,使嵌入式控件中的用户输入值可用于form.value。关键是对dyanmicFormArray使用patchValue(不是表单本身或formBuilder.group!):

this.dynamicFormArray.patchValue([{name: this.value}]);

希望可以帮助到有类似问题的朋友。


0
投票

(ngModelChange)
更改为
(input)
解决了我的弃用警告。这适用于
<input>
<select>
<textarea>
来源:Angular 6 使用 formControlName 和 ngModel 的警告


-2
投票

使用 formControl(反应式表单)与 Rxjs 结合起来更直接,因此 Angular 团队改变了它的使用方式。

更改 html 文件

<!-- [ngModel]='model' (ngModelChange)='changed($event)' -->

[formControl]="myControl"

更改 ts 文件

model: string;
  modelChanged: Subject<string> = new Subject<string>();

  changed(text: string) {
      this.modelChanged.next(text);
  }
  this.modelChanged.pipe(
      .subscribe(model => this.postErrorMessage = model);

this.myControl.valueChanges.pipe(
      .subscribe(model => this.postErrorMessage = model);
© www.soinside.com 2019 - 2024. All rights reserved.