Extending Material theme in Jetpack Compose | Xmartlabs Blog

Building Android UIs with a consistent look and feel is easier than ever by using the new Jetpack Compose framework and setting up themes. Compose offers a Material theme implementation that makes it easy to use Material style throughout the whole app.

As you may already know, Material allows us to have a uniform UI that follows Android UI best practices and guidelines, but at the same time, it’s super rigid and limited when the app needs a more complex UI customization level.

In this post, we’ll learn how to adapt, customize and extend Compose Material Theme in order to fulfill your app UI requirements and get rid of material limitations.

What's an application theme?

Most Android apps already follow Material Design Guidelines, that’s the reason Jetpack Compose provides the MaterialTheme implementation, which is a systematic way to customize Material Design to better reflect your app style and branding. Material Theme comprises color, typography, and shape attributes that can be tweaked to get custom style variations of the components.

Sounds good, but is it perfect?

Secondly, Material comprises only color, typography, and shape attributes, but what if your app needs more resources, such as dimensions or icons?

Extending Material colors

According to our experience, most apps need way more than 9 colors. For example, a text link color or a subheader background color are common cases that signal the need for more colors.

An important comment here is that all of these colors should be defined in your color palette because they could change depending on the system’s configuration (light or dark mode) or your app’s state.

Let’s suppose we want to define a subtitleTextColor, in this case, Google recommends a way to do that:

If you look closely at this code, you can see that the subtitleTextColor is only based on Material color's light property. However, what if we wanted to handle multiple color palettes in the same app, how could we possibly achieve that?

The approach we will use is to define a brand new color class named AppColor, which will keep Material standard colors and add our own custom ones.

AppColors then holds all of the app's colors. Each application can also define multiple color palettes, often selecting one or another depending on the app's state. Suppose that we now want to define two color palettes, one based on blue colors and the other based on pink ones:

Note that, by using this approach, we could also define a colorblind-friendly palette, improving the app’s accessibility.

Given a color palette and the UI mode, the appColors method returns an AppColors instance. The complete implementation of these classes can be found in Xmartlabs Gong template project code.

Right now we have a method that provides an AppColors palette, but then how can we get the current app color palette? Material provides a way of obtaining the current Material color palette, by invoking a composable method named MaterialTheme.colors. To get our custom color palette, we will use the same idea: we will invoke AppTheme.colors and get it. For that we will have to create our app theme, a custom theme that is the result of composing the MaterialTheme:

These lines define two things, a Composable app theme to handle our custom colors and a static class that provides them. The full implementation of these classes can be found here.

Extending shape and typography

I will not explain the code because it’s almost identical, you can also find it on Gong repo and if you have any questions, don’t forget to comment!

Adding custom resources to your theme

Defining dimensions in our theme

We can use a similar approach here and define a dimension class:

That’s all fine, but you may be asking yourself a question which is: what are the actual advantages?

First, your theme will be consistent. You can reuse the dimensions in multiple places throughout your app and thus make sure the correct values are enforced.

Second, you gain flexibility as you can define custom dimensions based on the device’s state or specs. A practical example, considering devices with small screens, is to define a separate set of dimensions for them to improve the user experience.

Last but not least, you avoid magic numbers making your codebase more maintainable and readable.

Then, you have to add the AppDims to your AppTheme just like we did with the AppColors example. Check out the complete code in Gong repo.

Conclusion

Compose is coming to transform the way we build Android apps, it’s a whole new approach that drastically simplifies and accelerates UI development.

Theming the application using Material Theme helps when it comes to encapsulating and reutilizing styles and assets. There is nothing worse than having a huge app that is a mess regarding the theme, assets management, and configuration.

This blog post presents concepts and ideas to leverage compose, app theming, and Material. If your app still needs more customization, you’ll be able to extend Material capabilities to derive full benefit from them. The benefits are clear, we end up having a clean code base, drastically reducing redundant style configuration code, and having full control over the whole app style from a single source of truth, the application-wide theming.

Technical expertise for great products.

Know more about our services and how we can help you at xmartlabs.com.

Originally published at https://blog.xmartlabs.com.

We provide exceptional strategy, design and technology to create innovative and high-value software. Follow us on IG, IN, FB @xmartlabs

We provide exceptional strategy, design and technology to create innovative and high-value software. Follow us on IG, IN, FB @xmartlabs