Window Insets and Keyboard Animations Tutorial for Android 11

In this tutorial, you’ll learn about Window Insets and Keyboard Animations in Android 11 and how to add these features to your android app. By Carlos Mota.

Leave a rating/review
Download materials
Save for later
Share

Until Android 11, keyboards and Androids seemed to go in opposite directions. There was no API you could query to learn if the keyboard was open or to know its size. When the keyboard popped up, the screen and views would automatically rearrange themselves without a smooth transition.

Developers used to handle everything manually with complex logic. It was time consuming and difficult. To overcome these issues, Android 11 introduces new features focused on window insets and keyboard animations.

In this tutorial, you’ll learn:

  • About window insets and the keyboard.
  • What’s new in Android 11 and what’s available in older APIs for handling keyboards.
  • Keyboard animations
  • Interacting with the keyboard in Android 11.
Note: This tutorial assumes you’re familiar with Android Studio and the basics of Android development. If you’re new to either, read through Beginning Android Development and Kotlin for Android: An Introduction before continuing.

Getting Started

Download the starter project by clicking the Download Materials button at the top or bottom of the tutorial. You’ll find two projects inside the ZIP file. Starter has the skeleton of the app you’ll build, and Final gives you something to compare your code to when you’re done.

Adding notes to Brain Dump app

It’s easy to feel overwhelmed with everything you need to do in a day: Get the kids to school, stop at the grocery store, update a section on this tutorial. If you don’t want to forget any of these items you need to write them down.

To solve this problem, you’ll build BrainDump, a note-taking app that helps you keep track of everything you need to do.

First, take some time to understand the project structure.

Understanding the Project Structure

Open the Starter project in Android Studio and wait for it to synchronize.

The directory structure of the project.

You’ll see a set of subfolders and other important files:

  • model: This is the data object used to represent a note. A note is made up of its content and the date it was created.
  • compat: Keyboard animations are only available for devices running Android 11. Therefore, you need different implementations for specific calls. RWCompat.kt is a factory responsible for loading RWCompat10.kt or RWCompat11.kt, depending on the device’s Android version.
  • ui: In this folder, you’ll find the activity, fragments and adapters you’ll use to let your users view and interact with the app’s data.
  • Utils.kt: This file contains a set of utility methods you’ll use throughout the project. Namely, you’ll use these to save and load your notes into and from shared preferences and format a note timestamp to an easily readable date.

Before diving in, spend some time learning about WindowInsets.

Understanding Window Insets

On Android, the window view could be categorised into two: the section for your application and the section for the Android OS. Window insets are the different portions of the screen that intersect with the system UI, such as the status and navigation bars and the lateral navigation sections on the new system gestures.

To avoid having user actions defined on areas already defined by the system for navigation, which would make them unusable, you can use a set of insets to locate these areas and control them according to your application’s specifications. Below are some of the available insets:

  • System window insets
  • Tappable element insets
  • Gesture insets
  • Stable insets

In this tutorial, you’ll use the system window insets. To learn more about window insets check out this Gesture Navigation Tutorial for Android.

Note: Android introduced WindowInsets in API 20. If you’re targeting a lower version you should use the AndroidX backported class WindowInsetsCompat. This is the class you’ll use throughout the tutorial.

Next, you’ll get familiar with the keyboard.

Getting to Know the Keyboard

Until now, there was no direct API you could use to access the keyboard and retrieve information about its state. Gathering this information was a job for complex calculus and inference, if not guessing.

Gone are the days when you had to manually implement everything to get any information about the keyboard’s current state. With the launch of Android 11, developers have new set of functionalities that let you animate the keyboard’s appearance or disappearance and how users interact with it.

Even better, Android backported most of these features to previous Android versions. After reading this tutorial, you can go back to your projects and remove hundreds of lines of keyboard-specifc code. :]

What’s Available on Older APIs

The following functionalities are available on all the Android versions supported by the AndroidX’s appcompat libraries.

Launching the Keyboard

You can launch the keyboard using two different APIs:

Or the correspondent hide method, if you want to close it:

On both calls, you use WindowInsetsController with the corresponding WindowInsetsCompat you want to access. In this case, the keyboard, or IME, so you can open or close it.

  • requestFocus: Launch the keyboard by calling this method on EditText or other components that lets users enter text.
  • windowInsetsController: With this API you manually force the keyboard to show:
    view.windowInsetsController.show(WindowInsetsCompat.Type.ime())
    
    view.windowInsetsController.hide(WindowInsetsCompat.Type.ime())
    
view.windowInsetsController.show(WindowInsetsCompat.Type.ime())
view.windowInsetsController.hide(WindowInsetsCompat.Type.ime())
Note:You can sufficiently use these APIs to control your keyboard in place of the InputMethodManager API.

Checking if the Keyboard is Visible

To see if the keyboard is open, you can call:

view.rootWindowInsets.isVisible(WindowInsetsCompat.Type.ime())

WindowInsetsCompat.Type.ime() defines the type of insets you need to access to see if the keyboard is open.

Getting the Keyboard Height

You guessed it! Once again you can rely on WindowInsetsCompat to get the keyboard height. Simply call:

view.rootWindowInsets.getInsets(WindowInsetsCompat.Type.ime()).bottom

This bottom value is directly related to keyboard visibility. If the keyboard is visible, it returns its height. If not, the value is 0.

Now that you’ve reviewed what the old APIs can do, it’s time to see what’s new in Android 11.

What’s New in Android 11

Along with these new methods, Android 11 also introduced a set of functionalities focused on keyboard animations and how your views interact with them.

Before diving in, add some notes to the list. Notice how unsynchronized opening the keyboard is:

Opening and closing the keyboard without animations

Preparing Your App for Keyboard Animations

To animate your keyboard, or IME, and the surrounding UI, you need to set your app as fullscreen because the IME is part of the system UI. Prior to Android 11, you could do this via:

window.decorView.systemUiVisibility = View.SYSTEM_UI_FLAG_LAYOUT_STABLE or
  View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN or
  View.SYSTEM_UI_FLAG_FULLSCREEN

However, this API is now deprecated. That’s a good thing, since it was always tricky to find the right combination of flags. In it’s place, Android backported a single method to the previous Android versions via WindowCompat that lets you achieve the same behavior.

Go to MainActivity.kt, and before calling super.onCreate(savedInstanceState), add:

WindowCompat.setDecorFitsSystemWindows(window, !isAtLeastAndroid11())

Android studio prompts you for two imports. So, import androidx.core.view.WindowCompat and com.raywenderlich.android.braindump.isAtLeastAndroid11.

Here, the second parameter, !isAtLeastAndroid11(), defines whether the app will handle the system windows. If the device runs Android 11 or newer, this value will be false so the app can define the keyboard animations. On lower versions, since these functionalities aren’t available, the value will be true so the system controls them.

To understand these differences, compile and run the on a device with a version lower than Android 11.

Brain dump app running on Android 10 where the app doesn't handle the system bars

Everything seems perfect! What if you run it on a device with Android 11?

Brain dump app running on Android 11 where the app handles the system bars

As you can see, the UI now overlaps the system bars. This overlap happens because your app asked to occupy the entire screen. At the same time, it said it would take care of the system windows, which it didn’t.

So, time to do that. :]