Skip to content

Instantly share code, notes, and snippets.

@alecmce
Last active October 11, 2017 19:00
Show Gist options
  • Save alecmce/791a7a1f2b8e365b7bb453abd244a392 to your computer and use it in GitHub Desktop.
Save alecmce/791a7a1f2b8e365b7bb453abd244a392 to your computer and use it in GitHub Desktop.
import { Observable } from 'rxjs/Observable';
import 'rxjs/add/observable/fromEvent';
import 'rxjs/add/operator/filter';
import 'rxjs/add/operator/map';
import 'rxjs/add/operator/combineLatest';
import 'rxjs/add/operator/distinctUntilChanged';
import 'rxjs/add/operator/takeUntil';
/**
* I am learning rxjs. The most complicated part is understanding the
* most elegant way to combine two upstream observables when they play
* different roles to the downstream behavior. Almost all examples of
* combining upstream observables imagine that the two observables are
* merged.
*
* In this example I imagine three actors: an active stream; a mousemove
* stream; and an update subscriber function. I want the update to be
* called with the mousemove event, only when active is true.
*
* There are two strategies offered, based on my very 2 day experience
* of rxjs. Neither seems quite right to me. I currently prefer the
* strategyUsingNestedSubscribers. Is there a 'best' way in rxjs? What is
* it?
*/
const active = makeActive();
const mousemove = makeMouseMove();
type Update = (event: MouseEvent) => void;
function strategyUsingNestedSubscribers(update: Update) {
active
.filter((flag: boolean) => flag)
.subscribe(() => {
mousemove
.takeUntil(active)
.subscribe(update);
})
}
function strategyUsingCombineLatest(update: Update) {
mousemove
.combineLatest(active)
.filter(([e, flag]: [MouseEvent, boolean]) => flag)
.map(([e, flag]: [MouseEvent, boolean]) => e)
.subscribe(update);
}
/** A reference example for how an active stream may be generated. */
function makeActive(): Observable<boolean> {
return Observable.fromEvent(checkbox, 'change')
.map((e: Event) => checkbox.checked)
.distinctUntilChanged();
}
/** A reference example for how a mousemove stream may be generated. */
function makeMouseMove(): Observable<MouseEvent> {
return Observable.fromEvent(document, 'mousemove');
}
@alecmce
Copy link
Author

alecmce commented Jul 29, 2017

@trxcllnt, thanks for pointing it out. Yeah, another thing to keep in mind!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment