简体   繁体   中英

Conditional observable interaction RxJS

I have the following observables:

this.searchValue$ = this.searchValue.valueChanges.pipe(
  startWith(''),
  debounceTime(500)
);

this.cardAmount$ = fromEvent(this.button.nativeElement, 'click').pipe(
  startWith(0),
  scan(count => count + 20, 0)
);

To add a bit more context to the code: searchValue$ is related to input field changes and emits the value that is changed. cardAmount$ is related to button presses. Each time you press a button it emits a new value 20, 40, 60 and so on.

I would like "set" the value of cardAmount$ back to 0 once searchValue$ is emited. What is a correct RxJS way of doing this?

You can't with this code (as far as I know).

For that, you will need a proxy that acts both as an observable and an observer. Otherwise, you can't emit a value in your stream.

Try with BehaviorSubject :

this.searchValue$ = this.searchValue.valueChanges.pipe(
  startWith(''),
  debounceTime(500),
  tap(() => this.cardAmount.next(0)),
);

this.cardAmount$ = new BehaviorSubject(0);

fromEvent(this.button.nativeElement, 'click').pipe(
  startWith(0),
  switchMap(() => this.cardAmount$),
).subscribe(curr => this.cardAmount$.next(curr + 20));

I slightly changed the last observer because if you don't and keep your previous one, the count value won't care about the reset of the value changes. To be sure it does care, you'll have to use the current value of the observer.

Sounds like the perfect case for the switchMap operator :

this.cardAmount$ = this.searchValue$
.pipe(switchMap( search =>
  fromEvent(this.button.nativeElement, 'click')
   .pipe(
    startWith(0),
    scan(count => count + 20, 0)
)));

A new Observable starting from 0 will be generated on each searchValue emission.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM