Newsletter Issue #98

Published: 2022-01-04

It was a quiet week in the world of Compose. Still, we try to remember when we need to use rememberSaveable(), deal with composables per product flavor, and implement an animated loading button. We also look at adding action menus and preference screens, mimicking what we are used to in the pre-Compose world. And Kirill Grouchnikov takes a deep dive into why some Compose-defined gradients turn out ugly.

One Off the Stack, One Off the Slack

You’ve got questions. That’s understandable!

Why Does rememberLauncherForActivityResult() Lose State?

Whenever your app’s UI moves to the background, your process is at risk of being terminated to free up system RAM. We think of this a lot with system HOME navigation, and occasionally for other things like launching a camera app. However, it could happen for other launch-an-app scenarios as well. To handle those, we need to rely on rememberSaveable(), not just remember(), as we see in this week’s highlighted Stack Overflow question.

Is It Safe to Nest Coroutines?

LaunchedEffect() runs your supplied lambda in a coroutine. The question is: is it safe to then launch() another coroutine from inside of that coroutine? In short, the answer appears to be “yes”, as we see in this week’s highlighted Kotlinlang #compose Slack thread.

Composable Commentary

Posts, videos, and other new information related to Jetpack Compose!

Medium: Jetpack Compose in Multi Flavor Apps

Sebastian Rieger works on a “white label” app, one that uses product flavors to customize the app for different targets. In a View-based system, you can easily override resources for that. Porting that to Compose UI requires different approaches, and Sebastian demonstrates how they handled per-flavor colors in this Medium post.

Medium: Creating a Loading Button in Jetpack Compose

Francesc Vilarino Guell returns, this time looking at a button that changes its content from a typical text label to an animated loading state and back again. This is a bit tricky, particularly if you want the button to stay the same size, rather than resizing as the content changes. Francesc demonstrates a LoadingIndicator() composable for the animated loading state and a LoadingButton() composable that handles the full UI.

Medium: Screen templates — using Compose, SwiftUI & KMM

Ian Alexander wrote about how to minimize code duplication in a Kotlin/Multiplatform project by use of screen templates, to try to isolate only the differences in UI rendering and keep the rest of the presentation logic common between platforms.

Polish your Jetpack Compose dev experience

Thomas Künneth is back, looking at how we can use file templates and live templates in Android Studio to simplify some aspects of our Compose development process.

Compose Desktop gradients and Skia shaders

Kirill Grouchnikov continues an exploration of Compose for Desktop. Gradient fills are popular, but the way that the Skia-backed Brush.horizontalGradient() actually interpolates between start and end colors sometimes gives poor results. Kirill experiments with a few other gradient implementations to try to improve on those results.

Jetpack Compose - Configuring Slider with Label

You have probably seen volume sliders and the like that have a floating bubble over the slider thumb, showing the current value of the slider. That bubble moves along with the thumb and updates to reflect changes in the value. Since the Slider() composable in Compose Material does not currently support this, MK decided to create one, and in this post shows how it is accomplished.

Medium: Interacting with Composable Canvas

Piotr Prus needed to build an interactive bar chart, supporting both bar selections and horizontal swipe gestures to show more of the chart. After an initial Box()-based implementation failed for performance reasons, Piotr created one using a raw Canvas() with some custom gesture management to handle the selections and scrolling.

Resource Roundup

100% pure code!

GitHub: jacobras / ComposeActionMenu

TopAppBar() does not handle all of the functionality that we associate with an action bar/toolbar/app bar. To help fill the gap, Jacob Ras released an implementation of an action menu for TopAppBar(), with support for toolbar icons, an overflow menu, checkable items, and more!

GitHub: JamalMulla / ComposePrefs

PreferenceScreen and its related Preference types handle both the UI for displaying/collecting preference values and the logic to persist those. Jamal Mulla took the same approach here, where you use PrefsScreen() and related composables to build up an equivalent UI with built-in DataStore support.

…And One More Thing

This section took a vacation the week between Christmas and New Year’s, but it should return next week!