Angular RxJS: получить последнее значение из anyControl.valueChanges- аналогично BehaviorSubject

#angular #rxjs #angular-reactive-forms

#angular #rxjs #angular-reactive-forms

Вопрос:

Я использую valueChanges для просмотра изменений конкретного элемента управления. Проблема начинается, когда я получаю управляющее значение as @Input и инициализирую его ngOnChanges . Если я смотрю его с помощью async канала, он не работает.

Я полагаю, что это происходит потому ngOnChanges , что происходит раньше ngOnInit , тогда «подписка» на observable выполняется после начальной загрузки. Вопрос в том, как это решить. Могут ли valueChanges действовать как BehaviorSubject? Или у кого-нибудь есть другая идея?

Это мой код:

component.ts:

 @Input() customerId;
customerState$: observable<number>;
myForm:FormGroup;

constructor(){
 this.customerState$= this.myForm.controls.customerId.valueChanges;
}

ngOnChanges(){
     if (changes.customerId) {
        this.myForm.controls.customerId.setValue(changes.customerId.currentValue);
      }
}
  

component.html:

 {{customerState$|async}}
  

В первый раз он ничего не показывает.
Значение отображается только при другом изменении customeId.

Я отмечу, что мой код на самом деле выглядит не так, и мое требование немного сложнее, просто чтобы проиллюстрировать проблему, я создал нечто концептуально похожее.

Поэтому я хотел бы получить ответ на вопрос, который я задал, а не конкретный трюк, который решил бы проблему здесь.

Ответ №1:

Кажется, я нашел! Решение заключается в операторе rxjs . Я не до конца понял, но это работает! Если кто-нибудь хотел бы прокомментировать это, я хотел бы услышать.

 constructor(){
 this.customerState$= this.myForm.controls.customerId.valueChanges.pipe(
  shareReplay(1)
);
}
  

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

1. Вы правы. Как раз в тот момент, когда я готовлю для вас свой ответ: stackblitz.com/edit/angular-ivy-qkhigq?file=src/app /… shareReplay(1) будет кэшировать последнее переданное значение. Поскольку изменение значения выполняется ДО настройки подписки на асинхронный канал (изменения ввода могут произойти до инициализации шаблона), вам необходимо кэшировать это значение, чтобы отобразить его в вашей подписке на асинхронный канал.

2. @enno.void Спасибо за добрую волю! По-видимому, иногда вам просто нужно знать, о чем вы спрашиваете, чтобы найти ответ самостоятельно…