Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Rxjs, fromEvent to handle multiple events

What is the best way to handle multiple events on the same DOM node in rxjs 5.1?

fromEvent($element, 'event_name') but I can specify only one event at a time.

I want handle scroll wheel touchmove touchend events.

like image 305
Reddy Avatar asked Aug 03 '17 21:08

Reddy


People also ask

How does observable emit multiple values?

Observables can emit multiple valuesAn Observable will emit events where a defined callback executes for each event. If you want to handle a single event, use a Promise. If you want to stream multiple events from the same API, use Observables.

What is FromEvent in RxJs?

FromEvent: FromEvent is a method provided by RxJs to create Observable. The best thing is that we can create Observable from DOM events directly. By DOM events, it means click event, key up events, scroll events, etc.

Which of the following will create an observable from an event using RxJs in angular?

Angular provides FromEvent method to create an observable from DOM events directly.


1 Answers

Note: This is for RxJS v5. See bottom of this answer for the v6 and v7 equivalent.


You can use the Rx.Observable.merge function to merge multiple observable streams into a single stream:

// First, create a separate observable for each event:
const scrollEvents$    = Observable.fromEvent($element, 'scroll');
const wheelEvents$     = Observable.fromEvent($element, 'wheel');
const touchMoveEvents$ = Observable.fromEvent($element, 'touchmove');
const touchEndEvents$  = Observable.fromEvent($element, 'touchend');

// Then, merge all observables into one single stream:
const allEvents$ = Observable.merge(
    scrollEvents$,
    wheelEvents$,
    touchMoveEvents$,
    touchEndEvents$
);

If that seems a little bloated, we might clean up a little by creating an array for the events, and then map that array to Observable objects. This works best if you do not need to reference the events their associated observables separately at some point:

const events = [
    'scroll',
    'wheel',
    'touchmove',
    'touchend',
];

const eventStreams = events.map((ev) => Observable.fromEvent($element, ev));
const allEvents$ = Observable.merge(...eventStreams);

You are now able to handle all events with one single subscription:

const subscription = allEvents$.subscribe((event) => {
    // do something with event...
    // event may be of any type present in the events array.
});

Update for RxJS v6 and v7

Starting from RxJS 6 you can import the standalone merge and fromEvent functions equivalent to the static methods in v5, and use them the same way:

import { fromEvent, merge } from 'rxjs';

const scrollEvents = fromEvent($element, 'scroll');
// creating other input observables...

const allEvents$ = merge(
    scrollEvents$,
    wheelEvents$,
    touchMoveEvents$,
    touchEndEvents$
);
like image 186
JJWesterkamp Avatar answered Sep 21 '22 13:09

JJWesterkamp