How to use Material Transitions in Fragment Transactions

Android UI design patterns have changed quite a bit since the arrival of Material Design. It used to be that Android apps were plain ugly, lagging behind the trail of iOS design decisions. Things changed with Lollipop and Material Design, Android became its own thing, no longer looking at the competition. Material Transitions play a big role in this change but paradoxically they were first introduced in KitKat, a little before Material Design fully fleshed out in Lollipop.

The intent of this article is to show how to use Transitions in the scope of Fragment Transactions and by doing so creating meaningful transitions that improve the UX of our application.

Scope

We have these 2 Fragments:

Fragment 1
Fragment 2

Fragment1 will be on screen when the application starts and Fragment2 will be loaded shortly after with no user action needed. This Fragment Transaction -by default- will simply replace one Fragment with the other, by applying a Transition to this FragmentTransaction we can make our application gracefully animate this change like this:

Fragment transition

Basics

  • Shared Element Transitions require Android SDK 21+, therefore we won’t look at solutions for implementing Material Transitions pre Android 5.0.
  • Transitions will have the scope of a single Android Activity.
  • Such Android Activity will solely have a FrameLayout which will act as our Fragment container.
  • We’re using a few libraries in our project to make our life easier and our code simpler, Butterknife for our layout widgets and retrolambda to use some Java8 features. We highly recommend them and we use them in all our Android projects.

Our Activity & Our Two Fragments

Both our Activity and our 2 Fragments are very simple. This is our hosting Activity:

These will be our 2 Fragments, both pretty bare:

We will see the code for the use of Transitions later on.

Understanding Transitions

The following concepts are key in understanding Transitions:
· Fragment Transactions: we will load our Fragments using Transactions, as is common for Fragment use, these are not the scope of this article, they are used but not thoroughly explained.
· Enter/Exit Transitions.
· Shared Element Transitions.

When executing our Fragment Transaction we will define an Enter Transition for our new Fragment and an Exit Transition for our old Fragment. Any new element added to our Activity will follow the Enter Transition and elements that disappear will use the Exit Transition.

It is important to understand that Enter/Exit Transitions are applied to the Fragments themselves.

Shared Elements are elements that exist in both Fragments involved in the Transaction. Shared Element Transitions are applied to the Fragment Transaction.

Timing

If we look at our preview of the Transition (beginning of the article) we will see that 3 different animations are chained.

· First, the text fades out.
· Next, the logo moves (and automatically resizes).
· Last, our button fades in.

In order for this to work we will have to time our animations correctly. The text will fade out for the duration time we set to the Exit Transition we apply to the previously loaded Fragment.

The move applied to the logo has a delay of the duration of the previous text fade out. On top of that we specify a duration for this move and take that duration into account for the delay for the final button fade in.

Shared Elements in XML layouts

One more thing is needed for the whole process to function properly. Our shared elements need to have the same transitionName in the layouts of the Fragments involved in the Transition. These are the fragments:

Notice that the ImageView that contains the logo (the only shared element in the Transition) has the same transitionName in both layouts.

The Code

This is where the Transition is actually implemented:

performTransition() from MainActivity.java

It’s all pretty straight forward except for the duration/delays for each specific animation. Let’s repeat that part again:

  1. Old elements disappear with a fade out that lasts 300ms.
  2. Shared Elements start moving after 300ms and the whole movement takes 1000ms.
  3. New elements fade in after 1300ms and fade in lasts 300ms.

What Did We Accomplish?

If you download the example project and run the app you will see some animations on your smartphone’s screen but we did so much more here, we’re not animating stuff, we are loading new Fragments on screen in a seamless way. We are creating meaningful transitions between Fragments and improving the UX of our application.

Project repository: https://github.com/Bynder/FragmentTransitionExample

PS: Activity Transitions are a different beast, if you want to achieve a Transition between Fragments belonging to different Activities you need to look into Activity Transitions.