角反应形式订阅

时间:2018-06-27 19:54:45

标签: angular typescript angular-forms

我订阅了Angular反应形式的valueChanges事件。我需要对用户输入做出反应以防止或纠正他的输入,我尝试了几种方法,但没有人能按预期工作。订阅时出现Maximum call stack size exceeded错误。

const controlArray = <FormArray> this.formArray.get('items');
    this.formArray.get('items').valueChanges.subscribe(val => {
      val.forEach(s => {
        controlArray.controls.forEach(control => {
          const con = control.get('symbol');
          if (con.value === s.symbol) {
            con.setValue(s.symbol.toUpperCase());
          }
        });
      });
    }); 

在这种情况下,我只想将每个字母输入更改为大写。我怎样才能做到这一点?还是有比每次键盘事件重复更少的方法更简单的方法?

我也尝试放置(change)="function(value)",但是只有在键盘:/

上使用enter时才会调用

2 个答案:

答案 0 :(得分:1)

有一种更简单的方法可以实现此目的。使用input指令。假设您有一个对象book,并且您想在用户输入文本时将其字段title设置为大写。

HTML模板

<input id="book-title" name="book-title" (input)="book.title = book.title.toUpperCase();"/>

答案 1 :(得分:1)

超出了最大调用堆栈大小,这是因为您发现自己陷入了无限循环,而观看时您更改的值要比观察者再次调用,它会更改该值,并再次调用观察者,一次又一次地更改值。

由于原生的patchValue方法,您可以做的是不发出观察者内部的事件:

    this.myCustomForm.patchValue({
      fieldSimbol: this.myCustomForm.value.fieldSimbol.toUpperCase()
    }, { emitEvent: false })

然后您可以将其包含在通用的buildForm函数中

buildForm() {

//...FormControls
this.myForm= new FormGroup({
  fieldSimbol: new FormControl('', Validators.required)
});

//..ValidationMessages
this.validationMessages = {
'fieldSimbol': [
    { type: 'required', message: 'Please fill this field' }
  ]
}

//..observe value change
this.myForm.valueChanges.subscribe((data) => {
  //..other stuff
  //..some controls

  //..what you probably need
  this.myCustomForm.patchValue({
   fieldSimbol: this.myCustomForm.value.fieldSimbol.toUpperCase()
  }, { emitEvent: false })
});

}