Crunching RxAndroid — Part 1

Learning Reactive Programming the easy way


During the last episode, we have been through the very beginning of RxJava and now we are ready to dive into it a little bit more!

First of all, the main goal for today is to shorten the code we wrote during the first article so that it gets more understandable when we look at it after a while… let’s start then with creating something that will just set an input String as the text in a TextView we already linked few lines before:

Action1<String> textViewOnNextAction = new Action1<String>() {
@Override
public void call(String s) {
txtPart1.setText(s);
}
};

Analyzing these lines here, we can notice right away that we did not create a fully qualified subscriber, but we just instanced something that will happen if and only if we succeed, avoiding the boilerplate associated with the other events we don’t really need this time.

We don’t really want to just set a label in a View, what we truly need is to make it uppercase, because we want to shout to the world and we can make it using a function, more or less like this one:

Func1<String, String> toUpperCaseMap = new Func1<String, String>(){
@Override
public String call(String s) {
return s.toUpperCase();
}
};

At this point we just need to create a new Observable and wire all the logic: since we just need to emit a single String once and we are done, we can use a shortcut and create it right away from the Observable static method

Observable<String> singleObservable = Observable.just(“Hello, World!”);

Now, if we wire up the Observable, the Function and the Subscriber, we would see something like this:

singleObservable.observeOn(AndroidSchedulers.mainThread())
.map(toUpperCaseMap)
.subscribe(textViewOnNextAction);

Can you spot the news here? I’m talking about the map operator!

Operators

In this example, we introduced our first operator that, in this specific case, is a Function from String to String that will allow us to manipulate the emission of an Observable before passing it to the ultimate Subscriber. RxJava comes with a ton of different operators that we can use to transform the flow of data in everything we might need!

Working with arrays and lists

We saw how we can emit a single item but what if we actually wanted to work with a set of entries, emitting them one by one? Starting from the easiest situation possible, we want to take an array of String and show them in a Toast, one at a time, as we were cycling through them.

Let’s define a Subscriber that will just show a message out of any input String, so we have at least the end of the queue up and running:

Action1<String> toastOnNextAction = new Action1<String>() {
@Override
public void call(String s) {
Toast.makeText(context, s, Toast.LENGTH_SHORT).show();
}
};

As we can see, there is nothing really new here, so we can skip directly to the creation of the Observable, that is really similar to what we did in our previous case, but here we can use something that will emit each and every entry of the array, one by one:

Observable<String> oneByOneObservable = Observable.from(manyWords);

Using from() we are able to send out all the items in our array in the order they appear, without caring too much about looping through them! Great!

Let’s face instead a more difficult case, in which we need to emit a full list on a single shot and then process each and everyone of the elements on its own. First of all, we need to emit the full list, and we know how to do it by the first example, creating a single Observable from the factory method:

Observable.just(manyWordList);

Then, we need something that takes an Observable and gives back another Observable… maybe we have an operator for that!

Introducing the flatMap

We saw the map operator that can transform something in something else, but it’s not the only thing that comes in handy! We can make use, in this case, of an item that can transform the emission of an Observable into the emission of another. The implementation is fairly easy and we can see it in action in the blink of an eye:

Func1<List<String>, Observable<String>> getUrls = new   Func1<List<String>, Observable<String>>() {
@Override
public Observable<String> call (List<String> strings) {
return Observable.from(strings);
}
};

Now, we would like instead to merge all the strings in a single item divided by a space to show a nicely formatted message: we can then use the reduce operator, that will take as input a function and will emit the merged string once the Observable which it is attached finishes emitting.

Func2<String, String, String> mergeRoutine = new Func2<String, String, String>() {
@Override
public String call (String s, String s1) {
return String.format(“%s %s”,s, s1);
}
};

Finally, we can wire everything together and see the magic happen!

Observable.just(manyWordList)
.observeOn(AndroidSchedulers.mainThread())
.flatMap(getUrls)
.reduce(mergeRoutine)
.subscribe(toastOnNextAction);

If you want to try this example right away, head over to GitHub, where you can find the latest source code related to this article.