jetc.dev Newsletter Issue #124
Published: 2022-07-19
I’m back! 👋
This week, we spend a bunch of time on next-generation animations and transitions,
powered by AnimatedContent()
and LookaheadLayout()
. We touch on semantics, spans,
and, well, touches. We apply Paging3 to lazy lists and zoom some images. And I
hope that someday we get more official advice on packaging composables in libraries
and library modules.
One Off the Stack, One Off the Slack
You’ve got questions. That’s understandable!
How Can I Give a Shadow To an ImageVector?
Vector drawables are great, but we lack any built-in ability to give one a shadow
that corresponds to the vector itself. If you can get your vector drawable
converted to a Path
, though, you can add a shadow, as we see in this week’s
highlighted Stack Overflow question.
The Cost of inline
Some core composables, like Layout()
, are marked as inline
. On the whole, this is
a good thing. However, it does mean that they behave a bit different than expected
when it comes to recompositions and remeasuring. Learn more about this phenomenon
in this week’s highlighted Kotlinlang #compose
Slack thread!
Composable Commentary
Posts, videos, and other new information related to Jetpack Compose!
Video: Animations with Rebecca Franks
Google’s Rebecca Franks joins the Code With the Italians team to talk
about AnimatedContent()
, an experimental API for animations that
Rebecca also covered in an Android Developers Medium post.
Introducing LookaheadLayout
Jorge Castillo examines LookaheadLayout()
, a new API in Compose UI 1.3.0-alpha01
.
LookaheadLayout()
gives you two measure/placement passes, where the second
one can leverage the results of the first, for transition-style effects.
Jorge compares and contrasts LookaheadLayout()
with alternatives like
SubcomposeLayout
and intrinsics, shows how it can be applied, and also
examines how it is implemented.
Medium: Introducing Jetpack Compose’s New Layout: “LookaheadLayout”
Medium user jisungbin also explored LookaheadLayout()
, using an example
of an expanding FAB to illustrate how LookaheadLayout()
can be used to animate
transitions between two composable states.
Jetpack Compose Accessibility: Semantics
Joe Birch is starting a new series of posts on accessibility in Compose UI. In this first post, Joe focuses on defining “semantics”, a key concept in Compose UI’s accessibility support. Joe explores how trees of semantic information relate to, but are distinct from, the UI nodes that we define using our composables.
Drawing custom text spans in Compose UI
In the classic View
system, SpannedString
supports custom spans, albeit with limitations
Saket Narayan wanted the same sort of thing for AnnotatedString
, applying visual
effects (like animated undersquiggles) to sections of text in a Text()
composable. This is not officially supported yet, but Saket was able to accomplish
the objective using onTextLayout
and some trickery. The results are available
in a library on GitHub.
Medium: Android Touch System — Part 5: How Gestures Work in Jetpack Compose
Sherry Yuan has been writing extensively about touch events, both for the classic
View
system and for Compose UI. Sherry’s
Part 4 post
covered modifiers for gesture detection, such as swipeable()
and draggable()
.
Here, in Part 5, Sherry examines how to create your own custom modifiers for
gesture detection, including ones that do not consume the touch events, but rather
let them fall through to other detectors as needed.
Other Interesting Links
- Medium: Touch Interactions in Jetpack Compose
- Medium: Nested Auto Scroll For Section Based Lists With Jetpack Compose
- Navigation parameters, and dynamic startDestination with Jetpack Compose
- Medium: Jetpack Compose Navigation in a multi-module project
- Medium: Jetpack Compose Navigation with ViewModel
- Creating User Authentication UI with Compose for Desktop
- Medium: Side Effects in Jetpack Compose
- Medium: Do you know the ways to represent states in Jetpack Compose?
- Medium: Jetpack compose: Custom animations
- Medium: Lazy components in Jetpack Compose
- Medium: Implement Horizontal and Vertical ViewPager in Jetpack Compose
Resource Roundup
100% pure code!
Gist: riggaroo / BouncyRopes.kt
Google’s Rebecca Franks put together a “bouncy ropes” animation, with a curve behaving like a weighted elastic band bounces as you move an endpoint. See Rebecca’s tweet for a video of the effect in action.
GitHub: SmartToolFactory / Compose-Image
The Smart Tool Factory team gives us another composable library, focused on images.
For example, ImageWithConstraints()
works like BoxWithConstraints()
but using an image
as the foundation. The library also includes a zoom()
modifier, MorphLayout()
and TransformLayout()
, and more!
GitHub: KevinnZou / compose-pagingList
GitHub user KevinnZou brings us a library that simplifies the use of Paging3
in Compose UI, including a PagingLazyColumn()
and PagingListContainer()
set of composables for easily implementing a scrolling list backed by paged data.
Other Interesting Links
- GitHub: commandiron / BubbleNavigationBarCompose (bottom nav with animated bubbles)
- Gist: EthanStandel / LegacyColorConversion.kt (
Color
to colorInt
converter) - GitHub: nanihadesuka / LazyColumnScrollbar (scrollbar for
Column()
/LazyColumn()
) - GitHub: fengdai / compose-pulltorefresh (pull to refresh implementation)
…And One More Thing
Overall, the Compose documentation is very well done. Compose is a complex topic, so the breadth and depth of the official documentation is welcome.
However, there are always more things that could be covered. One would be recommendations for packaging composables in libraries.
For library modules in an app project, we would have one layer of advice, such as:
-
Rules for what does (and does not) need to be synchronized with other modules with respect to Compose versions, particularly in light of the version independence movement
-
Details of how immutability inference works across module boundaries, compared with how it works within a single module
-
Notes about how having composables split across multiple modules might affect Android Studio features, especially the upcoming Electric Eel ones like Live Edit
-
Recommendations on code organization as it pertains to Compose, such as the use of
internal
on composables -
And so on
A second layer would be advice on creating libraries designed to be packaged as AAR artifacts and used across projects, perhaps even across organizations. For example, there are many open source libraries of composables, but it is unclear if the organic approaches that their developers are taking represent best practices for libraries of composables.
No doubt we can reverse-engineer the guidance by examining those public libraries, especially Google-maintained ones. Up-to-date documentation generally is simpler for the mass of developers to use, though.
Or, you can subscribe to the Atom feed or follow Mark Murphy in the Fediverse.
Recent Issues:
- 2024-10-01: Lazy grids! Focus! @colinmarsch@androiddev.social on CMP accessibility! @skydoves@androiddev.social on Landscapist! @sinasamaki@androiddev.social on Slider()! And... what is it?!?
- 2024-09-24: A Compose security fix and a new alpha! clipToBounds()! Localization! offset()! @skydoves@androiddev.social on server-defined UI! Bottom sheets! And... someone set us up *3* BOMs?!?
- 2024-09-17: Compose 1.7.1 and Compose Multiplatform 1.7.0-beta02! Flow layouts! TV Compose! SharedBounds! Image cropping! And... why does remember() not seem always to remember?!?