Newsletter Issue #102

Published: 2022-02-01

1.1.0 is… not yet stable! But, we now have an rc03, in addition to 1.2.0-alpha02.

Beyond those, we look at keys, both in terms of user input and in terms of triggering recomposition. We examine the next phase of Glance, navigation, and scoped viewmodels. We see a media picker library and a collapsible tab bar. Plus, I talk a bit about everybody’s favorite subject: documentation!

(what? that’s not your favorite subject?!?)

Alpha Analysis

Reviewing the release notes for the latest Jetpack Compose update!

This past week, we got 1.1.0-rc03. There were no obvious significant changes, though Google reiterates that Compose Material widgets have minimium touch target sizes.

We also got 1.2.0-alpha02. Among other changes, this alpha includes:

  • Mouse wheel scrolling support for scrollable() containers

  • excludeFromSystemGesture() modifiers

  • onRotaryScrollEvent() and onPreRotaryScrollEvent() modifiers (for watches with crowns that rotate)

We also got an update to Glance, which includes a new androidx.glance:glance-wear-tiles artifact. More on this below!

One Off the Stack, One Off the Slack

You’ve got questions. That’s understandable!

How Do We React to Global Key Events?

Sometimes, you want to react to key events outside of having something like a TextField() with the focus. For example, you might be interested in responding to D-pad input from a remote control in a TV app. How to do that in a Compose-friendly way is the subject of this week’s highlighted Stack Overflow question.

Are Constant Keys OK?

We often have the opportunity to provide “key” objects to composables. When the key changes, the composable will get recomposed. But, we see some samples where the key is a constant. We explore whether or not that’s a good idea in this week’s highlighted Kotlinlang #compose Slack thread.

Composable Commentary

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

Announcing Glance: Tiles for Wear OS made simple

We have had alpha releases of Glance for a while, but only with support for app widgets. Now, the second half of Glance is out, with support for creating tiles in Wear OS apps. Tiles on Wear OS fill a similar role as do app widgets on phones and tablets, and now our code can be similar as well (and composable as a bonus)!

Video: Compose Snapshots

The Code with the Italians team brought in Google’s Chuck Jazdzewski to talk about Compose’s snapshot system, which is what makes State work and drives a lot of the Compose foundation.

Medium: Android Jetpack Compose: Create a Replacement Material Theme

Medium user Pedro wanted to use Compose Material but with a theme that was based only partially on MaterialTheme(). This requires a bit of reverse-engineering, to determine how Compose Material composables use MaterialTheme(), so alternative typography, shapes, etc. can be applied.

Medium: Animations in Jetpack Compose with examples

Jimmy Sanghani looks at four different animation effects and explores how to implement them, using state animation and infinite animation APIs.

Bite-size Jetpack Compose: Navigation

Myric September walks us through the setup and usage of Navigation for Compose, including using sealed class for navigation routes, passing navigation arguments, and more!

Medium: Navigation in Jetpack Compose using ViewModel state

Medium user Frank continues our tour of Navigation for Compose. In this case, Frank examines how state — not events — can handle navigation from composable to composable, to better align with how Compose operates.

Every Composable deserves a ViewModel

Sebastian Lobato Genco created the Resaca library that I mentioned two weeks ago. In this post, Sebastian explains the rationale behind creating Resaca and its rememberScoped() function, to try to have narrower viewmodel-style objects for use by specific reusable composables.

Getting Started with ConstraintLayout in Jetpack Compose

ConstraintLayout is very popular in the classic View system, but not everybody realizes that there is a ConstraintLayout for Compose UI as well. Shrey Sindher walks us through why you might want ConstraintLayout in a composable and how standard ConstraintLayout capabilities — such as guidelines and chains — translate to a Kotlin DSL.

Medium: Creating Custom Jetpack Compose Chips

Chips are popular UI elements. Kamaldeep Kumar reviews how to create various styles of chips from scratch using basic composables.

Resource Roundup

100% pure code!

GitHub: rektplorer64 / picker-kt

Tanawin Wichit created a set of libraries that combine to provide a Material3-based, responsive media selection UI. The library handles rendering the previews of the media, and you get a list of Uri objects back representing the selections.

GitHub: nesyou01 / LazyStaggeredGrid

Younes Lagmah created a LazyStaggeredGrid() composable, offering a controllable set of columns and cells of arbitrary height within those columns.

GitHub: getStream / butterfly

The Stream team brings us a library to help with dealing with tablets and foldables, with State objects for window size classes, fold posture (open, half-open), hinge size, and more!

Gist: c5inco / CollapsingTabBar.kt

Google’s Chris Sinco offers the source for a CollapsingTabBar() composable: an icon bar that expands outward from a central FAB-style button.

…And One More Thing

We have @Preview in the IDE. Showkase also lets us use @Preview-annotated composables for screenshot testing.

For me, the next step is: use @Preview as part of generating documentation.

Principally, my concern is for library documentation. Having screenshots (or GIF animations) of composables is really quite useful for developers hunting for a library that might solve particular UI concerns. Having up-to-date screenshots be generated automatically as part of publishing the documentation can be a big win. Manually generating screenshots is a pain, which means that either:

  • We don’t get many screenshots, or

  • Those screenshots may not be maintained and could be out of sync with the actual code base

However, the value of documentation is also valid for in-house use by development teams. While Showkase works nicely in-app, browsing composables in the app may or may not be the most efficient course of action for bulk knowledge transfer (think: onboarding new team members).

In principle, the @Preview-rendering logic from the IDE could be made available for documentation Gradle tasks. After all, the IDE is not running Android. Or, perhaps we could get something out of Compose for Desktop that serves the same role.

This idea is in the “Coming Soon!” list for Showkase. Between them and other independent developers, with luck, we can get something in this area in the not-too-distant future.