10+ years of app development
Everything from a single source
50+ successful app projects

Blog

Animations in Jetpack Compose

Modern applications are becoming more design-centric and therefore end-user-centric. For the user, the technical side of the program is not at all interesting, but rather taken for granted. Attractive design, animation and ease of use, on the contrary, all other things being equal, can make the application more popular among competitors.

Artikelbild für Animations in Jetpack Compose

The animation in Android Compose has been completely redesigned. Jetpack Compose's declarative approach makes creation of animation easier and clearer. Let's look at different types of animations using the SenseBox app as an example:

Appearance and Disappearance Animation

The appearance/disappearance animation is carried out by the composite function AnimatedVisibility, which has the following signature:

@Composable
@ComposableInferredTarget
public fun ColumnScope.AnimatedVisibility(
    visible: Boolean,
    modifier: Modifier,
    enter: EnterTransition,
    exit: ExitTransition,
    label: String,
    content: @Composable() (AnimatedVisibilityScope.() -> Unit)
): Unit

It is enough to specify the content for animation in the AnimatedVisibility() function via a lambda expression, and also specify the condition under which the animation will be performed and the function itself will apply the default animation to the content.

Image with code that shows how to implement a box animation  

The animation can also be flexibly customized to suit your needs. For example, we need to create a message that will appear from TopUpBar when you click on the “add/remove” favorites icon. To do this, we will create a сomposable function ShowMessage() that will contain the appearing panel and accept the favoriteMessageShown and isFavorite state. So we need favoriteMessageShown to be reset to false again after some certain time, we will create:

suspend fun showFavoriteStatusMessage() {
    if (!favoriteMessageShown) {
        favoriteMessageShown = true
        delay(2000L)
        favoriteMessageShown = false
    }
}

AnimatedVisibility() has also two arguments to customize the animation - EnterTransition and ExitTransition. There are many functions with which you can configure the appearance and disappearance, the full list can be found on the Jetpack Compose Animation documentation. We will use slideInVertically() and slideOutVertically(), and in the parameters we will set the starting point of the offset, as well as the type and duration of the animation. We can also combine the EnterTransition or ExitTransition functions by simply adding them together, in this example adding fadeIn() and fadeOut() respectively.

Image with code that shows how to implement a box animation  

You like how we approach things?

This blog is supposed to give you a little insight into our everyday business when we build an app in a full-service-environment or just provide our expertise via EaaS.

Have a look at our development services

Animation modifiers

There are animation modifiers (animateContentSize(), animateItemPlacement(), animateEnterExit()) that are convenient to apply to list items. Let's look at each of them.

AnimateContentSize

When you press the button, the contents of the card are revealed/hidden with a slight bouncing effect.

Image with code that shows how to implement the AnimateContentSize modifier  

AnimateItemPlacement

Сreates animation when the position of an item changes. For example, it can be used when deleting a list item.

Image with code that shows how to implement the AnimateItemPlacement modifier  

AnimateEnterExit

Responsible for the animation of an element entering/exiting the screen.

Image with code that shows how to implement the AnimateEnterExit modifier.  

Animating a simple value change

In addition to using ready-made functions for animation, we can animate specific values, for example animateColorAsState(), animateDpAsState(), animateFloatAsState(), etc.

AnimateColorAsState

Let's say that when you click a button that reveals the description of a box, we need to show not only an animation of changing the container, but also an animation of changing the color. Without animation, the background color would be triggered like this:

val backgroundColor = if (detailEnabled) 
    MaterialTheme.colorScheme.tertiaryContainer 
    else MaterialTheme.colorScheme.primaryContainer

In order to apply animation when the detailEnabled state changes, we must wrap this condition in a function animateColorAsState(), and also set animation parameters if necessary.

Image with code that shows how to implement a color animation for state changes  

AnimateDpAsState

Using the dp value, the size, padding, etc. are usually set. If we want to animate the dp's state change, we must wrap this value in a function animateDpAsState()

Image with code that shows how to implement a grow or shrink animation  

AnimateFloatAsState

Using a float value, you can set the rotation angle of the box icon. If we wrap this conditional expression in a animateFloatAsState() function, we get a nice animation of the box flipping over when viewing the box details.

Image with code that shows how to implement a rotation animation of an icon in Jetpack Compose  

Now you have made it this far, so we assume you gained some interest into our work. That is totally fine. Be our guest and give us some feedback or discuss a project of yours. We will be happy to hear from you.

Let's talk

Conlusion

We've covered here the basic animation tools that Jetpack Compose offers. As we see, the use of animation has become much easier, and there are more possibilities. By combining different animation tools and creativity, you can get amazing results.

In conclusion, it is worth noting that user events accompanied by reasonable animation help to better navigate the application interface, in other words, it is able to report certain states of the UI and direct attention. Animation helps the user see the results of their actions and can influence their behavior.

You can find the source code in our public Github repository: Cayas Github.

Igor Gridin

Igor Gridin

With over 15 years of experience in software development with Java and Kotlin, I support our customers in the banking and logistics sector with exciting native Android projects. Here I write about all the new technologies and trends that are emerging in the field of Android application development.

Related articles

Voice input facilitates documentation - A hackathon topic
Voice input facilitates documentation - A hackathon topic

Voice input makes it possible to intuitively record food eaten and drunk without having to look at a device or tap. Instead of laboriously entering everything by hand, users can simply record their meals and snacks by voice command. This approach can lower the inhibition threshold and encourage users to continuously document their eating habits. This saves time and encourages regular documentation.

Jetpack Compose: Google's modern UI toolkit
Jetpack Compose: Google's modern UI toolkit

It's been almost two years since the release of the stable version of Jetpack Compose, but still many developers are skeptical about using this framework in their projects. To answer the question, is it worth using Compose in your projects, let's make a small comparison between Android Views and Jetpack Compose based on typical tasks when developing native Android projects.

How to workaround Xamarin Androids VersionCode limitation

Learn why your Xamarin Android build fails with "Error executing task Aapt: VersionCode is outside 0, 65535 interval" and how to workaround that issue.