Как я могу подписаться на изменения группы форм и рассчитать одно из свойств из двух других?

#angular #typescript #observable

Вопрос:

У меня есть функция, создающая группу форм, и мне нужно вычислить одно поле из двух других: сумма = цена * количество. Как я могу это сделать?

 public createService = (): FormGroup => {
    const group = this.fb.group({
      name: [''],
      measure: [''],
      count: [''],
      price: [''],
      sum: ['']
    });

    group.valueChanges.subscribe(res => {
      // group.patchValue({...res, sum:  res.price *  res.count});
      // res.sum =  res.price *  res.count;
      console.log(res);
    });

    return group;
  }
 

Ответ №1:

Если вы подпишетесь на всю форму и обновите значение sum внутри изменений значений, будет бесконечный цикл вызовов для изменения значений. Вместо этого вы должны подписаться на отдельные элементы управления формами.

 import { merge } from 'rxjs/observable/merge';

public createService = (): FormGroup => {
   const group = this.fb.group({
     name: [''],
     measure: [''],
     count: [''],
     price: [''],
     sum: ['']
   }); 

   merge(
     group.get('count').valueChanges,
     group.get('price').valueChanges
   ).subscribe(res => {
     this.calculateSum(group);
   });
}

calculateSum(group) {
  const count =  group.get('count').value;
  const price =  group.get('price').value;
  group.get('sum').setValue(count   price);
}
 

Ответ №2:

Вам не нужно подписываться на всю группу форм. Просто поищите изменения в полях цена и количество. Что-то вроде ниже;

  this.group.get('price').valueChanges.subscribe(value => {
      this.price = value;
      this.calculateSum();
  });

this.group.get('count').valueChanges.subscribe(value => {
      this.count = value;
      this.calculateSum();
  });

calculateSum() {
   sum = this.price*this.count;
   this.group.get('sum').setValue(sum);
}
 

Комментарии:

1. Мне нужно рассчитать и установить значение для третьего ввода формы.

Ответ №3:

 import { combineLatest } from 'rxjs';

   combineLatest(
     this.group.get('count').valueChanges,
     this.group.get('price').valueChanges
   ).subscribe(([count, price]) => {
       this.testForm.get('sum').setValue( count    price);
   });
 

Ответ №4:

Вы можете задать значение атрибута для поля сумма, например {{form.count form.price}} . Сейчас я не могу это проверить, но это что-то в этом роде.