Angular 2个表单 + OnPush

Angular 2 forms + OnPush

我正在编写一个 angular 2 应用程序,出于性能原因,我尝试在所有地方使用 ChangeDetectionStrategy.OnPush。我有一个复杂的组件需要 OnPush 才能顺利工作,其中包含另一个显示表单的组件(使用 FormBuilder 创建)。我现在注意到,当我点击滑块时,它的内部值会更新(即 form.value),但滑块组件不会显示这个新值,即它停留在旧位置。

我解决这个问题的第一个想法是将叶组件的变化检测策略设置为默认值,但这没有效果,因为显然这也需要更改其父组件的变化检测策略(这在我的环境中是不可能的申请)。

然后我想出了这个主意:

@Component({
   ...
})
class MyComponent implements OnInit {
  constructor(private zone: NgZone) {}

ngOnInit() {
  INIT_FORM();

  this.form.valueChanges
    .subscribe(() => {
      this.zone.run(() => {});
    });
  }
}

但是没有效果

是否有可能使 angular 2 个表单在使用 OnPush 的组件中工作?

我自己没有测试过,但手动调用更改检测可能会做你想做的事:

@Component({
   ...
})
class MyComponent implements OnInit {
  constructor(private cdRef: ChangeDetectorRef) {}

ngOnInit() {
  INIT_FORM();

  this.form.valueChanges
    .subscribe(() => {
      this.cdRef.detectChanges();
    });
  }
}

让我用我在其他帖子上回答过的东西来回应,你可以做得更好!,让我知道这是否有效:

当你使用响应式表单时,你可以使用一个非常酷的方法,叫做 updateValueAndValidity();触发变化检测。

private changeControlValue(control, value: number) {
    control.setValue(value);
    control.updateValueAndValidity();
  }

您也可以在更新添加到表单的验证器时使用此方法,示例:

this.control.setValidators([Validators.required, Validators.minLength(5)]);
control.updateValueAndValidity();

这应该可以解决问题!我认为这是针对 ng-model 使用反应式表单或表单控件的最佳冒险之一。

我不建议在您的表单中使用 valueChanges,因为您很容易忘记取消订阅并造成内存泄漏,即使您记得创建此流程可能很乏味。

请记住,当使用 onPush 变化检测时,只有三件事会被 Angular 检测为变化:

1- 输入和输出。 2- Html 用户可以执行的事件,例如(单击)。 3- 订阅等异步事件。

希望对你有所帮助!