This codelab is part of the Advanced Android Development training course, developed by the Google Developers Training team. You will get the most value out of this course if you work through the codelabs in sequence.

For complete details about the course, see the Advanced Android Development overview.

Introduction

Accessibility is a set of design, implementation, and testing techniques that enable your app to be usable by everyone, including people with disabilities.

Common disabilities that can affect a person's use of an Android device include blindness, low vision, color blindness, deafness or hearing loss, and restricted motor skills. When you develop your apps with accessibility in mind, you make the user experience better not only for users with these disabilities, but also for all of your other users.

Accessibility usually does not require a full overhaul of your app's design or code. Accessibility does require you to pay attention to details and test your app under the same conditions your users may encounter.

Android includes several accessibility-related features, to help you optimize your app's user interface (UI) for accessibility. In this lesson, you learn how to test your app and add features that enhance its accessibility.

What you should already know

You should be familiar with:

What you'll learn

What you'll do

The SimpleAccessibility app demonstrates how to add accessible features to your app's UI. The app, when complete, looks like this:

None of the views have click handlers, so the app does not have any actual functionality. The focus for this app (and this codelab) is in the layout XML code and in the attributes that enable accessibility.

In this task, you run the starter app for SimpleAccessibility and explore it in TalkBack.

1.1 Download and open the sample app

  1. Download the SimpleAccessibility-start app and unzip the file.
  2. Open the app in Android Studio.
  3. Open res/layout/activity_main.xml.

The SimpleAccessibility app contains a number of views in a layout, including buttons (Button and ImageButton views), checkboxes, and an image. All the accessibility functions you learn about in this practical are implemented in the layout.

1.2 Test the app with TalkBack

TalkBack is Android's built-in screen reader. When TalkBack is on, the user can interact with their Android device without seeing the screen. Users with visual impairments may rely on TalkBack to use your app. In this task, you manually explore the app with TalkBack enabled, to expose possible accessibility problems.

Enable TalkBack:

  1. On a device, navigate to Settings > Accessibility > TalkBack.
  2. Tap the On/Off toggle button to turn on TalkBack.
  3. Tap OK to confirm permissions.

After TalkBack is on, you can navigate the Android UI in one of these ways:

Now test your app with TalkBack enabled:

  1. Build and run your app in Android Studio.

When your app starts with TalkBack enabled, no item is initially focused. TalkBack reads the title of the app.

  1. Tap each element or swipe to hear the descriptions for the elements in sequence. Note the following:
  1. Swipe from left to right to navigate between focusable elements on the screen. Note that the focus moves from top to bottom. The partly cloudy image is not focusable.

Experimenting with TalkBack and the starter app in the previous task exposed problems in how the app's views are identified for vision-impaired users. In this task, you fix some of these problems.

2.1 Inspect and fix the code in Android Studio

Android Studio highlights places in your XML layout code that have potential accessibility problems, and makes suggestions for fixing those problems. For accessibility, Android Studio checks two things:

To inspect and fix your code for accessibility, use these steps:

  1. In Android Studio, open the res/layout/activity_main.xml file, if it's not already open. Switch to the Text tab.
  2. Note that the ImageButton and ImageView elements have yellow highlights on them. When you hover over the elements, the message reads, "Missing contentDescription attribute on image."
  3. Add an android:contentDescription attribute to the ImageButton view, with the value "Discard." Extract this string into a resource.
  4. Add an android:contentDescription attribute to the ImageView, with the value "Partly Cloudy." Extract this string into a resource.
  5. Build and run your app.
  6. Navigate your app with TalkBack turned on. The trash-can button now has a reasonable description, but you still can't focus on the partly cloudy image.

2.2 Add focus to views

In addition to readable descriptions, make sure that users can navigate your screen layouts using hardware or software-based directional controls such as D-pads, trackballs, keyboards, or on-screen gestures.

Most views are focusable by default, and the focus moves from view to view in your layout. The Android platform tries to figure out the most logical focus order based on each view's closest neighbor. Generally, views are focussed from left to right and top to bottom. In some cases, you want to make your views explicitly focusable or change the focus order to reflect how the user uses your app.

In the case of the SimpleAccessibility app, the partly cloudy image is not focusable, even with a content description added. Assuming that the partly cloudy image is there to show the current weather, you must add a focusable attribute to that image so that TalkBack can read the content description.

To make the partly cloudy image focusable, use these steps:

  1. Find the partly cloudy ImageView element in the XML layout.
  2. Add the android:focusable attribute to the ImageView:
android:focusable="true"
  1. Build and run the app. With TalkBack enabled, navigate to the partly cloudy image. TalkBack reads the image's content description.

In this task, you add an EditText view and an associated label (a TextView). EditText views and TextView labels are a special case for handling accessibility in your app.

3.1 Add views and test the app in TalkBack

  1. Add a TextView to the app's layout below the ImageView. Give it the android:text attribute of "Message." Extract that string into a resource.
  2. Add an EditText just below the TextView. Give it an ID of @+id/edittext_message, and the android:hint attribute "Enter your message." Extract that string into a resource.
  3. Build and run the app and navigate to the new views. Experiment with entering text in TalkBack.

Note these things:

In EditText views, it's better to use android:hint rather than android:text for the default text.

3.2 Add explicit labels for EditText views (API 17 and higher)

If you target your app to Android 4.2 (API level 17) or higher, use the android:labelFor attribute when labeling views that serve as content labels for other views. For readable descriptions, TalkBack prefers explicit labels (using android:labelFor) over attributes such as android:text or android:hint.

Explicit labels are only available in API 17 or higher, and Android Studio can highlight missing labels for EditText views as part of code inspection. The SimpleAccessibility app uses the default minimum SDK of 15. In this task, you change the API level to enable explicit labels. Then you add the appropriate label attribute.

  1. Open the build.gradle (Module: app) file and change minSdkVersion from 15 to 17.
  2. Click Sync Now to rebuild the project.
  3. In the activity_main.xml layout file, delete the android:hint attribute from the EditText.

The EditText element is now highlighted in yellow. When you hover over the element, the message reads, "No label views point to this text field with an android:labelFor="@+id/edittext_message" attribute."

  1. Add the android:labelFor attribute to the TextView that serves as a label for this EditText:
android:labelFor="@+id/edittext_message"

The highlight on the EditText disappears.

  1. Build and run the app. TalkBack now reads the contents of the label to identify the EditText.

Android Studio project: SimpleAccessibility

Challenge: If the content of a view changes programmatically as the app runs, you need to update the content descriptions to reflect the new state.

Hints:

Get an image drawable from the resources:

Drawable img = ContextCompat.getDrawable(this, R.drawable.my_drawable);

Get a string from the resources:

String str = getResources().getString(R.string.my_string);

Compare two drawables:

if (drawable1.getConstantState() == drawable2.getConstantState()) {
   ... 
}

The related concept documentation is in 6.1 Accessibility.

Android support documentation:

Android developer documentation:

Material Design: Usability - Accessibility

Videos:

Other:

This section lists possible homework assignments for students who are working through this codelab as part of a course led by an instructor. It's up to the instructor to do the following:

Instructors can use these suggestions as little or as much as they want, and should feel free to assign any other homework they feel is appropriate.

If you're working through this codelab on your own, feel free to use these homework assignments to test your knowledge.

Build and run an app

In the SimpleAccessibility app, add three new images:

  1. Add a description for the first image that describes the image. Ensure that the image is focusable.
  2. Add a decorative image with no description. Ensure that the image is not focusable.
  3. For the third image, add a text label that describes the image.

Answer these questions

Question 1

Which of the following attributes should you add to ImageView and ImageButton elements to enable screen readers to describe the image?

Question 2

When should you add a content description to an ImageView or ImageButton?

Question 3

When do you NOT need to add a content description to a view element?

Submit your findings for grading

Guidance for graders

Check that the app has the following features:

The layout for the first new image should include the following:

The layout for the second new image should include the following:

The layout for the third new image should include the following:

To see all the codelabs in the Advanced Android Development training course, visit the Advanced Android Development codelabs landing page.