TimeRange — RxJS custom function that emits a set of values in specified timeouts
Tags: webdev, javascript, rxjs
Published: 2019-09-23 11:41:56

---
title: TimeRange — RxJS custom function that emits a set of values in specified timeouts
published: true
tags: webdev,javascript,rxjs
canonical_url: https://medium.com/@alexanderposhtaruk/timerange-rxjs-custom-function-that-emits-a-set-of-values-in-specified-timeouts-bd6dd07974ce
---

### TimeRange — RxJS custom function that emits a set of values in specified timeouts

_Why, how and where for those who like RxJS :-)_

![](https://cdn-images-1.medium.com/max/1024/1*7hyHYXeUNMhJBjV2Q1N6yA.jpeg)<figcaption>Customizing RxJS (Photo by <a href="https://unsplash.com/@sneakyelbow?utm_source=unsplash&amp;utm_medium=referral&amp;utm_content=creditCopyText">Sneaky Elbow</a>)</figcaption>


**Prerequisites: I assume you knwo RxJS and have some practice with it. If you are new to it or want to learn some advanced topics - watch my video-course "** [**Hands-on RxJS for Web development**](https://www.udemy.com/course/hands-on-rxjs-for-web-development/) **" on Udemy.**


### Why

Periodically in my development practice, I meet situations when you have to emit a few values in specified timeouts.

For example:

1. To show and then hide some splash-message:

![](https://cdn-images-1.medium.com/max/400/1*2jn_yYTMGcpyLqeDxAG3CA.gif)<figcaption>Managing splash-message show/hide timeouts</figcaption>

2. To do some nice animations

![](https://cdn-images-1.medium.com/max/605/1*2klU0Bnmad1gZWWD3U20Wg.gif)<figcaption>Managing appearance timeouts</figcaption>

3. Or even just emit values for unit tests (yeah, I know about [marbles](https://github.com/ReactiveX/rxjs/blob/master/docs_app/content/guide/testing/marble-testing.md), but sometimes I just want to check final value, period:)

![](https://cdn-images-1.medium.com/max/1024/1*fJ1bCfDzLkr74GNhIt1bcQ.png)<figcaption>Simple code for auto-complete with debounce — demands providing values with specific timings to be tested</figcaption>

So how it can be implemented? Ok, let's review some scenarios:

### How to implement?

#### Ugly way

Ok, the simplest way — to run many _setTimeout's_, like this:

![](https://cdn-images-1.medium.com/max/1024/1*FVkmaCdDDeU9eMhNtd_pCA.png)

OK, not so bad, but what if I want to show more elements in different delays?

![](https://cdn-images-1.medium.com/max/1024/1*_aM-J9WdnCjrJbP3VAQ0pg.png)

Looks oldschool and ugly. Can we do better?

#### Ugly way, part 2

Lets use RxJS now and try to implement it:

![](https://cdn-images-1.medium.com/max/1024/1*tib9DxYqHvMl2FXCK_WPEw.png)

This code doesn't allow absolute delay (when the next emission is delayed against start/subscription moment).

To implement absolute delays approach (all delays are specified against subscription/start moment) we can use [**_mergeMap_**](https://rxjs.dev/api/operators/mergeMap) instead of [**_concatMap_**](https://rxjs.dev/api/operators/concatMap):

![](https://cdn-images-1.medium.com/max/1024/1*Rz_4cWxC16LU7EqrEN1kGg.png)

Looks like a lot of code, and also delays are hardcoded. We can do better. So let's go further!

#### Editor choice method

Ok, we already know that hardcoding values/delays is not reusable, and we also want to be able to schedule in _relative_ (delayed against previous emissions) and _non-relative/absolute_ (delayed against subscription moment) way. Taking all the above into account, I implemented a custom **timeRange** function.

![](https://cdn-images-1.medium.com/max/1024/1*PUxyK_cCYZO50x2ZIy1wUA.png)<figcaption>Custom <strong>timeRange</strong> function.</figcaption>

**Benefits:**

1. Looks nice and compact.
2. Allows both absolute and relative delays to be specified.

OK, now let's show three use-cases I mentioned previously.

### _Where to use it_

**#1 Splash-message control example**

Here it implementation code:

![](https://cdn-images-1.medium.com/max/1024/1*LgFQcOH27DNM1x4UTYIxqw.png)

What do we do here?

1. Emit two values with 1000 and 2000 delay (values don't play any role here, actually only timings matter)
2. The first value will show splash element with a message.
3. Second will hide it (using _.classList.toggle('show')_)

Here is how it works:

![](https://cdn-images-1.medium.com/max/400/1*2jn_yYTMGcpyLqeDxAG3CA.gif)

You can play with it in a codepen [here](https://codepen.io/kievsash/pen/ZEzVWKa?editors=0010).

**#2 Animating a few elements subsequent appearance**

Here is the code:

![](https://cdn-images-1.medium.com/max/1024/1*JIRhdrg4jCWsR7G_r6BQkQ.png)

We just grab a set of elements and then show them one by one with specified timeouts on each range$ Observable emission.

Here is the result:

![](https://cdn-images-1.medium.com/max/605/1*2klU0Bnmad1gZWWD3U20Wg.gif)

You can check the code [here](https://codepen.io/kievsash/pen/YzKdqzd?editors=0110).

**#3 Mocking input params for unit tests code with timeRange.**

![](https://cdn-images-1.medium.com/max/1024/1*zE7VK8Cvu3HBxxUJmfETiQ.png)

How it works:

1. We mock ajax.get with a function that will return value '42' asynchronously (emulation of network request)
2. Then se debounce time = 15ms.
3. After that call _getSearchResult_ with mocked _input$_ as a param and subscribe (to start the process).
4. _input$_ will emit three values with delays 1ms, 5ms, 30ms. Since debounceTime is set to 15ms, only second and third values will cause network request to be called (ajax.get in our case);

And result:

![](https://cdn-images-1.medium.com/max/1024/1*6cEnFwnKvIVv7tm9jiqGPw.png)

The code and the test can be found [here](https://codepen.io/kievsash/pen/ePoRxg?editors=0010).

#### Conclusion

I've added **_timeRange_** function to my [**_rxjs-toolbox_**](https://github.com/kievsash/rxjs-toolbox)lib. It is not big for now. You can read more about it here: [_‘forkJoin’ with the progress of completion_](https://dev.to/oleksandr/rxjs-recipes-forkjoin-with-the-progress-of-completion-for-bulk-network-requests-in-angular-4964-temp-slug-231854)

Have your own interesting RxJS solutions? Mention them in comments!

Like this article? Let's keep in touch on [Twitter](https://twitter.com/El_Extremal).

Want to learn more about RxJS? Give a try to my video-course "[Hands-on RxJS](https://www.udemy.com/course/hands-on-rxjs-for-web-development/)". It contains both total beginners content and more advanced topics as well.

Cheers.