Binding Texts With Charm

Easier binding of texts for data binding library

Miroslav Kacera
The Startup
4 min readJan 19, 2021

--

Successfully bound user facing texts. Tobias Keller

I’m sure everyone using data binding in her/his application has already bound some texts into TextView or Button or any other View responsible for displaying textual information to the user.

I’m also quite sure most of you have already encountered situation when the final text was a result of some conditional flow or even result of some remote response (otherwise you wouldn’t really require binding, would you? 😃). In situation like that you can be confronted with a reality that you sometimes have String data and sometimes you have Int data (resource id) to display in that one and only View.

The Problem

Translations and internationalization asides, the example easy to imagine can be a situation where you are receiving some text from a remote API. This text is of course not part of your APK’s resources so you’ll end up with some String or some CharSequence in general. This is fine for happy path but there are situations when not everything works as you would imagine. There could be error situations or the user is just simply offline.

Then you would most likely want to display an error message, the one which is (hopefully) in your string.xml file(s). This would be referenced as an Int of course, not a String. You can use Context to load the content of that resource to String representation but if you are using some modern architecture (and with binding enabled you probably are 😉) you would argue that you don’t have any Context around, for example, in a standard ViewModel.

And that is actually a good thing as we all know that Context, the all-mighty god object of Android is rather tedious to keep around…

Artistic representation of Context, colorized. Coco Van Oppens

… no thank you! The good thing is that TextView and its many child classes can work with both String and resource Int id. But if you try to somehow bind that to your view it won’t work out of the box even though the methods have same names.

The compiler just can’t magically call the one with Int parameter and other times the one with String.

The problem is not difficult to solve but most of the solutions are ugly and verbose. Raging from defining multiple variables in view models to having custom binding adapters or even having multiple views in your layout 😱. But there are some good news… There is (at least one) library for that!🎉

The Library

DynamicText library which is part of Dynamic Components project can easily solve this problem with next to none verbosity or code changes to your already existing binding code.

The usual code in layout’s xml can often look similar to this

Like this but more complicated, right? 😵

As you can see viewmodel’s property title is bound to TextView. You would expect that if viewmodel.title is returning String (or some observable type of String) everything would just work fine as this code would call TextView‘s setText method under the hood displaying your title to the user. It would also fail spectacularly if that method or variable was actually Int.

Let’s see how it can look in case of the use of DynamicText library

The main point here is the val property title. It is not String nor Int but a DynamicText type coming from the library. Later in the code you can easily assign a value to this (in-this-case-LiveData-but-that-is-not-requirement) property with factory functions conveniently provided for you by the library.

Only defining your variable as DynamicText and assigning the right value and you are good to go. The code will compile without any further change needed. Binding code is not required to change at all. You are free to use Int or String, it doesn’t matter. You can even use formatted String like

or

How is that possible? The library takes care of binding logic and processing of the string exactly the way how would you expect it to do and in the standard manner fully compatible with data binding library. No need to write your own binding adapters or helpers.

It’s only a cherry on top that plurals are also supported out of the box if you need them.

This will produce “1 month” or “5 months” and can be bound to your view in no time! 🙌

That’s about it

If you would like more info visit project’s GitHub to see how to include it in your project and use it. There is even more dynamic components coming in the near future.

Happy coding!

--

--