jetc.dev Newsletter Issue #134
We got a new beta for Compose 1.3.0, and stuff keeps changing!
In addition, we look at animations and dual-pane UIs, plus steppers and lock patterns. However, a growing concern is performance, so we look at upcoming Flamingo composition tracing, and I worry about how weird our composables are going to get as we deal with this and other limitations.
Ooooo… What Did We Get?
Reviewing the release notes for the latest Jetpack Compose update!
Compose is out with a
The big thing is that the lambdas that you pass to
are now considered to be
crossinline. You cannot perform an early return from
crossinline lambda expression. That was never supported anyway, apparently,
but now you get a clearer compiler error.
In addition, we got more stuff that seems like it should not be in a beta, such as:
Line-breaking options for
pullRefresh()modifier for the popular pull-to-refresh pattern
(these are all great, but they feel more like changes that belong in an alpha, not a beta)
Wear Compose has a new
1.1.0-alpha06 release. In addition to fixing a
bug, they added a
scrollAway() modifier for
ScalingLazyColumn(). The primary use case is to allow you to have the
scroll with the content.
One Off the Stack, One Off the Slack
You’ve got questions. That’s understandable!
It’s a common requirement: you need something to immediately follow some text,
remain close to the text (i.e., no extra whitespace), but also force the text
to wrap or ellipsize to control maximum width. Learn about the
weight() modifier, and how it can help with this case, in this week’s
highlighted Stack Overflow question.
android:autoLink, backed by
Linkify. This was handy but prone
to problems. There is no direct analogue for
Text() in Compose UI, but learn
how to set it up yourself (and problems in doing so), in this week’s highlighted
#compose Slack thread.
Posts, videos, and other new information related to Jetpack Compose!
Google’s Ben Trengrove walks us through some new performance analysis options in the upcoming Flamingo version of Android Studio. Compose Composition Tracing marries the composable call stack with system traces, to help you identify what composables are contributing to hot spots in your app execution.
Google’s Chris Arriola continues a series of posts on Compose basics, this time looking at what it means for a function to be “composable”, what “recomposition” means, and assumptions that you should avoid when creating your composables.
Katie Barnett delivered a presentation for GDG Melbourne focusing on animations. There is a dizzying array of animation options for Compose; Katie looks at several options for animating cards (e.g., flipping cards from front to back).
Kristen Halper returns, this time looking at the Accompanist
as a counterpart to Microsoft’s own take on that UI. While both are aware of foldables
and can help you better work with that form factor,
TwoPane() always shows both
panes, whereas the Microsoft
TwoPaneLayout() shows one or two panes based on
device posture and other considerations.
Manshi Shah continues an exploration of Compose animation APIs started in this earlier Medium post. Here in Part 2, Manshi examines animated transitions with Navigation for Compose, using Accompanist for those navigation animations.
Júlia Jakubcová and Tadeas Kriz experimented with using Compose to drive an iOS set of Swift UI widgets for the droidcon 2022 app. Their takeaway: if you are looking to implement a Kotlin/Multiplatform app, Compose for iOS is worth considering.
Ferdinand Bada was running into problems with Paging-backed columns, where navigating away from and back to a column would reset the scroll position to the top. The underlying issue appears to be a classic “fixed, but not really” one, and Ferdinand walks us through a workaround.
Other Interesting Links
- Rounded Corners
- Medium: Exploring LaunchedEffect and InfiniteTransition in Jetpack Compose
- Medium: Jetpack compose ViewModel decoupling mechanism: Wireless ViewModel
100% pure code!
maryam memarzadeh created a stepper: a UI for showing the user a series of steps,
with options for going forwards and backwards through those steps. The
handles rendering a row of step circles, with the caller supplying the names of
the steps, optional colors, plus state information for where the user is within
the step sequence. Learn more about it in this Medium post!
Long-time Android users may remember using a pattern lock for their device, where
a path among a grid of dots is used to represent the equivalent of a PIN. GitHub user
mrhwsn created a
ComposeLock() function that implements the same UI, with customizable
grid size, dot and line rendering, and more.
…And One More Thing
Compose is starting to show some cracks in its foundation.
The idea behind Compose was supposed to be simplicity: you “simply” declare what you want the UI to be based on the present state. Compose would arrange to:
Detect relevant state changes
Call your code to re-declare what the UI should be now
Figure out what changed between the previous UI and the new UI and make the necessary on-screen adjustments
You would just write nearly-ordinary functions to implement the code behind that second bullet. Using reactive data sources would “just work”, and Compose would be efficient when doing all of this.
And, at a high level, that is all still true. But, we are starting to see where the simplicity is not holding up:
Over-composing — doing unnecessary recompositions due to state changes — is a significant problem, dragging down performance. The good news is that the tooling is getting better for this, particularly in the Electric Eel and Flamingo editions of Android Studio. The bad news is that we have to start introducing artificial workarounds, like converting parameters into lambdas to reduce composition counts, as seen here and here.
Part of the theory behind composables, particularly the stock widgets, is that they are stateless. That is not always possible in practice. Last week’s warnings about
TextField()stem from state management inside of
TextField(), necessary because it needs to interact with external-to-Compose elements, such as the soft keyboard. As a result of this hidden state, we have to take steps to ensure that our composables are not wrecking that internal
Neither of these things are show-stoppers. However, they do throw sand in the gears of Compose development. Worse, for teams who are currently considering whether or not to make the move to Compose, these sorts of problems cause more 🤔 or 🙃 than 😀.
In other words, some may feel that they are headed towards the trough of disillusionment.
If many more of these sorts of problems show up in the short term, Compose may be in for a rough go of it for a while. In the long run, it seems likely that Compose can be augmented to handle these two problems more naturally.
And, in the meantime… be sure to check your composition counts.
- 2023-09-12: Compose 1.5.1! Glance 1.0.0! Compose Multiplatform! Themes! Photos! Coachmarks! A bit of CommonsWare history! And @firstname.lastname@example.org tells us what not to do!
- 2023-09-05: Compose Compiler 1.5.3! Compose Multiplatform 1.5.0! @email@example.com on greyscaling composables! @firstname.lastname@example.org on Espresso testing with Compose interop! Scrollbars! AnnotatedString!
- 2023-08-29: Compose Compiler 1.5.2! Compose and Wear Compose alphas! Capture composables to bitmaps! Testing! Recomposition! Compose Multiplatform! And... Accompanist is downsizing?!?