| page.title=Building Accessibility Services |
| parent.title=Accessibility |
| parent.link=index.html |
| @jd:body |
| |
| <div id="qv-wrapper"> |
| <div id="qv"> |
| |
| <h2>Topics</h2> |
| <ol> |
| <li><a href="#manifest">Manifest Declarations and Permissions</a> |
| <ol> |
| <li><a href="#service-declaration">Accessibility service declaration</a></li> |
| <li><a href="#service-config">Accessibility service configuration</a></li> |
| </ol> |
| </li> |
| <li><a href="#register">Registering for Accessibility Events</a></li> |
| <li><a href="#methods">AccessibilityService Methods</a></li> |
| <li><a href="#event-details">Getting Event Details</a></li> |
| <li><a href="#act-for-users">Taking Action for Users</a> |
| <ol> |
| <li><a href="#detect-gestures">Listening for gestures</a></li> |
| <li><a href="#using-actions">Using accessibility actions</a></li> |
| <li><a href="#focus-types">Using focus types</a></li> |
| </ol> |
| </li> |
| <li><a href="#examples">Example Code</a></li> |
| </ol> |
| |
| <h2>Key classes</h2> |
| <ol> |
| <li>{@link android.accessibilityservice.AccessibilityService}</li> |
| <li>{@link android.accessibilityservice.AccessibilityServiceInfo}</li> |
| <li>{@link android.view.accessibility.AccessibilityEvent}</li> |
| <li>{@link android.view.accessibility.AccessibilityRecord}</li> |
| <li>{@link android.view.accessibility.AccessibilityNodeInfo}</li> |
| </ol> |
| |
| <h2>See also</h2> |
| <ol> |
| <li><a href="{@docRoot}training/accessibility/index.html">Training: Implementing Accessibility</a></li> |
| </ol> |
| |
| </div> |
| </div> |
| |
| <p>An accessibility service is an application that provides user interface enhancements to |
| assist users with disabilities, or who may temporarily be unable to fully interact with a device. |
| For example, users who are driving, taking care of a young child or attending a very loud party |
| might need additional or alternative interface feedback.</p> |
| |
| <p>Android provides standard accessibility services, including TalkBack, and developers can |
| create and distribute their own services. This document explains the basics of building an |
| accessibility service.</p> |
| |
| <p>The ability for you to build and deploy accessibility services was introduced with Android 1.6 |
| (API Level 4) and received significant improvements with Android 4.0 (API Level 14). The Android |
| <a href="{@docRoot}tools/support-library/index.html">Support Library</a> was also updated with |
| the release of Android 4.0 to provide support for these enhanced accessibility features back to |
| Android 1.6. Developers aiming for widely compatible accessibility services are encouraged to use |
| the Support Library and develop for the more advanced accessibility features introduced in |
| Android 4.0.</p> |
| |
| |
| <h2 id="manifest">Manifest Declarations and Permissions</h2> |
| |
| <p>Applications that provide accessibility services must include specific declarations in their |
| application manifests to be treated as an accessibility service by the Android system. This |
| section explains the required and optional settings for accessibility services.</p> |
| |
| |
| <h3 id="service-declaration">Accessibility service declaration</h3> |
| |
| <p>In order to be treated as an accessibility service, your application must include the |
| {@code service} element (rather than the {@code activity} element) within the {@code application} |
| element in its manifest. In addition, within the {@code service} element, you must also include an |
| accessibility service intent filter. For compatiblity with Android 4.1 and higher, the manifest |
| must also request the {@link android.Manifest.permission#BIND_ACCESSIBILITY_SERVICE} permission |
| as shown in the following sample:</p> |
| |
| <pre> |
| <application> |
| <service android:name=".MyAccessibilityService" |
| android:label="@string/accessibility_service_label"> |
| <intent-filter> |
| <action android:name="android.accessibilityservice.AccessibilityService" /> |
| </intent-filter> |
| </service> |
| <uses-permission android:name="android.permission.BIND_ACCESSIBILITY_SERVICE" /> |
| </application> |
| </pre> |
| |
| <p>These declarations are required for all accessibility services deployed on Android 1.6 (API Level |
| 4) or higher.</p> |
| |
| |
| <h3 id="service-config">Accessibility service configuration</h3> |
| |
| <p>Accessibility services must also provide a configuration which specifies the types of |
| accessibility events that the service handles and additional information about the service. The |
| configuration of an accessibility service is contained in the {@link |
| android.accessibilityservice.AccessibilityServiceInfo} class. Your service can build and set a |
| configuration using an instance of this class and {@link |
| android.accessibilityservice.AccessibilityService#setServiceInfo setServiceInfo()} at runtime. |
| However, not all configuration options are available using this method.</p> |
| |
| <p>Beginning with Android 4.0, you can include a {@code <meta-data>} element in your manifest |
| with a reference to a configuration file, which allows you to set the full range of options for |
| your accessibility service, as shown in the following example:</p> |
| |
| <pre> |
| <service android:name=".MyAccessibilityService"> |
| ... |
| <meta-data |
| android:name="android.accessibilityservice" |
| android:resource="@xml/accessibility_service_config" /> |
| </service> |
| </pre> |
| |
| <p>This meta-data element refers to an XML file that you create in your application’s resource |
| directory ({@code <project_dir>/res/xml/accessibility_service_config.xml}). The following code |
| shows example contents for the service configuration file:</p> |
| |
| <pre> |
| <accessibility-service xmlns:android="http://schemas.android.com/apk/res/android" |
| android:description="@string/accessibility_service_description" |
| android:packageNames="com.example.android.apis" |
| android:accessibilityEventTypes="typeAllMask" |
| android:accessibilityFlags="flagDefault" |
| android:accessibilityFeedbackType="feedbackSpoken" |
| android:notificationTimeout="100" |
| android:canRetrieveWindowContent="true" |
| android:settingsActivity="com.example.android.accessibility.ServiceSettingsActivity" |
| /> |
| </pre> |
| |
| <p>For more information about the XML attributes which can be used in the accessibility service |
| configuration file, follow these links to the reference documentation:</p> |
| |
| <ul> |
| <li><a href="{@docRoot}reference/android/R.styleable.html#AccessibilityService_description">{@code android:description}</a></li> |
| <li><a href="{@docRoot}reference/android/R.styleable.html#AccessibilityService_packageNames">{@code android:packageNames}</a></li> |
| <li><a href="{@docRoot}reference/android/R.styleable.html#AccessibilityService_accessibilityEventTypes">{@code android:accessibilityEventTypes}</a></li> |
| <li><a href="{@docRoot}reference/android/R.styleable.html#AccessibilityService_accessibilityFlags">{@code android:accessibilityFlags}</a></li> |
| <li><a href="{@docRoot}reference/android/R.styleable.html#AccessibilityService_accessibilityFeedbackType">{@code android:accessibilityFeedbackType}</a></li> |
| <li><a href="{@docRoot}reference/android/R.styleable.html#AccessibilityService_notificationTimeout">{@code android:notificationTimeout}</a></li> |
| <li><a href="{@docRoot}reference/android/R.styleable.html#AccessibilityService_canRetrieveWindowContent">{@code android:canRetrieveWindowContent}</a></li> |
| <li><a href="{@docRoot}reference/android/R.styleable.html#AccessibilityService_settingsActivity">{@code android:settingsActivity}</a></li> |
| </ul> |
| |
| <p>For more information about which configuration settings can be dynamically set at runtime, see |
| the {@link android.accessibilityservice.AccessibilityServiceInfo} reference documentation.</p> |
| |
| |
| <h2 id="register">Registering for Accessibility Events</h2> |
| |
| <p>One of the most important functions of the accessibility service configuration parameters is to |
| allow you to specify what types of accessibility events your service can handle. Being able to |
| specify this information enables accessibility services to cooperate with each other, and allows you |
| as a developer the flexibility to handle only specific events types from specific applications. The |
| event filtering can include the following criteria:</p> |
| |
| <ul> |
| <li><strong>Package Names</strong> - Specify the package names of applications whose accessibility |
| events you want your service to handle. If this parameter is omitted, your accessibility service is |
| considered available to service accessibility events for any application. This parameter can be set |
| in the accessibility service configuration files with the {@code android:packageNames} attribute as |
| a comma-separated list, or set using the {@link |
| android.accessibilityservice.AccessibilityServiceInfo#packageNames |
| AccessibilityServiceInfo.packageNames} member.</li> |
| <li><strong>Event Types</strong> - Specify the types of accessibility events you want your service |
| to handle. This parameter can be set in the accessibility service configuration files with the |
| {@code android:accessibilityEventTypes} attribute as a list separated by the {@code |} character |
| (for example {@code accessibilityEventTypes="typeViewClicked|typeViewFocused"}), or set using the |
| {@link android.accessibilityservice.AccessibilityServiceInfo#eventTypes |
| AccessibilityServiceInfo.eventTypes} member. </li> |
| </ul> |
| |
| <p>When setting up your accessibility service, carefully consider what events your service is able |
| to handle and only register for those events. Since users can activate more than one accessibility |
| services at a time, your service must not consume events that it is not able to handle. Remember |
| that other services may handle those events in order to improve a user's experience.</p> |
| |
| <p class="note"><strong>Note:</strong> The Android framework dispatches accessibility events to |
| more than one accessibility service if the services provide different |
| <a href="{@docRoot}reference/android/R.styleable.html#AccessibilityService_accessibilityFeedbackType"> |
| feedback types</a>. However, if two or more services provide the same feedback type, then only the |
| first registered service receives the event.</p> |
| |
| |
| <h2 id="methods">AccessibilityService Methods</h2> |
| |
| <p>An accessibility service must extend the {@link |
| android.accessibilityservice.AccessibilityService} class and override the following methods from |
| that class. These methods are presented in the order in which they are called by the Android system, |
| from when the service is started |
| ({@link android.accessibilityservice.AccessibilityService#onServiceConnected onServiceConnected()}), |
| while it is running ({@link android.accessibilityservice.AccessibilityService#onAccessibilityEvent |
| onAccessibilityEvent()}, |
| {@link android.accessibilityservice.AccessibilityService#onInterrupt onInterrupt()}) to when it is |
| shut down ({@link android.accessibilityservice.AccessibilityService#onUnbind onUnbind()}).</p> |
| |
| <ul> |
| <li>{@link android.accessibilityservice.AccessibilityService#onServiceConnected |
| onServiceConnected()} - (optional) This system calls this method when it successfully connects to |
| your accessibility service. Use this method to do any one-time setup steps for your service, |
| including connecting to user feedback system services, such as the audio manager or device vibrator. |
| If you want to set the configuration of your service at runtime or make one-time adjustments, this |
| is a convenient location from which to call {@link |
| android.accessibilityservice.AccessibilityService#setServiceInfo setServiceInfo()}.</li> |
| |
| <li>{@link android.accessibilityservice.AccessibilityService#onAccessibilityEvent |
| onAccessibilityEvent()} - (required) This method is called back by the system when it detects an |
| {@link android.view.accessibility.AccessibilityEvent} that matches the event filtering parameters |
| specified by your accessibility service. For example, when the user clicks a button or focuses on a |
| user interface control in an application for which your accessibility service is providing feedback. |
| When this happens, the system calls this method, passing the associated {@link |
| android.view.accessibility.AccessibilityEvent}, which the service can then interpret and use to |
| provide feedback to the user. This method may be called many times over the lifecycle of your |
| service.</li> |
| |
| <li>{@link android.accessibilityservice.AccessibilityService#onInterrupt onInterrupt()} - |
| (required) This method is called when the system wants to interrupt the feedback your service is |
| providing, usually in response to a user action such as moving focus to a different control. This |
| method may be called many times over the lifecycle of your service.</li> |
| |
| <li>{@link android.accessibilityservice.AccessibilityService#onUnbind onUnbind()} - (optional) |
| This method is called when the system is about to shutdown the accessibility service. Use this |
| method to do any one-time shutdown procedures, including de-allocating user feedback system |
| services, such as the audio manager or device vibrator.</li> |
| </ul> |
| |
| <p>These callback methods provide the basic structure for your accessibility service. It is up to |
| you to decide on how to process data provided by the Android system in the form of {@link |
| android.view.accessibility.AccessibilityEvent} objects and provide feedback to the user. For more |
| information about getting information from an accessibility event, see the |
| <a href="{@docRoot}training/accessibility/service.html">Implementing Accessibility</a> training.</p> |
| |
| |
| <h2 id="event-details">Getting Event Details</h2> |
| |
| <p>The Android system provides information to accessibility services about the user interface |
| interaction through {@link android.view.accessibility.AccessibilityEvent} objects. Prior to Android |
| 4.0, the information available in an accessibility event, while providing a significant amount of |
| detail about a user interface control selected by the user, offered limited contextual |
| information. In many cases, this missing context information might be critical to understanding the |
| meaning of the selected control.</p> |
| |
| <p>An example of an interface where context is critical is a calendar or day planner. If the |
| user selects a 4:00 PM time slot in a Monday to Friday day list and the accessibility service |
| announces “4 PM”, but does not announce the weekday name, the day of the month, or the month name, |
| the resulting feedback is confusing. In this case, the context of a user interface control is |
| critical to a user who wants to schedule a meeting.</p> |
| |
| <p>Android 4.0 significantly extends the amount of information that an accessibility service can |
| obtain about an user interface interaction by composing accessibility events based on the view |
| hierarchy. A view hierarchy is the set of user interface components that contain the component (its |
| parents) and the user interface elements that may be contained by that component (its children). In |
| this way, the Android system can provide much richer detail about accessibility events, allowing |
| accessibility services to provide more useful feedback to users.</p> |
| |
| <p>An accessibility service gets information about an user interface event through an {@link |
| android.view.accessibility.AccessibilityEvent} passed by the system to the service’s |
| {@link android.accessibilityservice.AccessibilityService#onAccessibilityEvent |
| onAccessibilityEvent()} callback method. This object provides details about the event, including the |
| type of object being acted upon, its descriptive text and other details. Starting in Android 4.0 |
| (and supported in previous releases through the {@link |
| android.support.v4.view.accessibility.AccessibilityEventCompat} object in the Support Library), you |
| can obtain additional information about the event using these calls:</p> |
| |
| <ul> |
| <li>{@link android.view.accessibility.AccessibilityEvent#getRecordCount |
| AccessibilityEvent.getRecordCount()} and {@link |
| android.view.accessibility.AccessibilityEvent#getRecord getRecord(int)} - These methods allow you to |
| retrieve the set of {@link android.view.accessibility.AccessibilityRecord} objects which contributed |
| to the {@link android.view.accessibility.AccessibilityEvent} passed to you by the system. This level |
| of detail provides more context for the event that triggered your accessibility service.</li> |
| |
| <li>{@link android.view.accessibility.AccessibilityEvent#getSource |
| AccessibilityEvent.getSource()} - This method returns an {@link |
| android.view.accessibility.AccessibilityNodeInfo} object. This object allows you to request view |
| layout hierarchy (parents and children) of the component that originated the accessibility event. |
| This feature allows an accessibility service to investigate the full context of an event, including |
| the content and state of any enclosing views or child views. |
| |
| <p class="caution"><strong>Important:</strong> The ability to investigate the view |
| hierarchy from an {@link android.view.accessibility.AccessibilityEvent} potentially exposes private |
| user information to your accessibility service. For this reason, your service must request this |
| level of access through the accessibility <a href="#service-config">service configuration XML</a> |
| file, by including the {@code canRetrieveWindowContent} attribute and setting it to {@code true}. If |
| you do not include this setting in your service configuration xml file, calls to {@link |
| android.view.accessibility.AccessibilityEvent#getSource getSource()} fail.</p> |
| |
| <p class="note"><strong>Note:</strong> In Android 4.1 (API Level 16) and higher, the |
| {@link android.view.accessibility.AccessibilityEvent#getSource getSource()} method, |
| as well as {@link android.view.accessibility.AccessibilityNodeInfo#getChild |
| AccessibilityNodeInfo.getChild()} and |
| {@link android.view.accessibility.AccessibilityNodeInfo#getParent getParent()}, return only |
| view objects that are considered important for accessibility (views that draw content or respond to |
| user actions). If your service requires all views, it can request them by setting the |
| {@link android.accessibilityservice.AccessibilityServiceInfo#flags flags} member of the service's |
| {@link android.accessibilityservice.AccessibilityServiceInfo} instance to |
| {@link android.accessibilityservice.AccessibilityServiceInfo#FLAG_INCLUDE_NOT_IMPORTANT_VIEWS}.</p> |
| </li> |
| </ul> |
| |
| |
| <h2 id="act-for-users">Taking Action for Users</h2> |
| |
| <p>Starting with Android 4.0 (API Level 14), accessibility services can act on behalf |
| of users, including changing the input focus and selecting (activating) user interface elements. |
| In Android 4.1 (API Level 16) the range of actions has been expanded to include scrolling lists |
| and interacting with text fields. Accessibility services can |
| also take global actions, such as navigating to the Home screen, pressing the Back button, opening |
| the notifications screen and recent applications list. Android 4.1 also includes a new type of |
| focus, <em>Accessibilty Focus</em>, which makes all visible elements selectable by an |
| accessibility service.</p> |
| |
| <p>These new capabilities make it possible for developers of accessibility services to create |
| alternative navigation modes such as |
| <a href="{@docRoot}tools/testing/testing_accessibility.html#test-gestures">gesture navigation</a>, |
| and give users with disabilities improved control of their Android devices.</p> |
| |
| |
| <h3 id="detect-gestures">Listening for gestures</h3> |
| |
| <p>Accessibility services can listen for specific gestures and respond by taking action on behalf |
| of a user. This feature, added in Android 4.1 (API Level 16), and requires that your |
| accessibility service request activation of the Explore by Touch feature. Your service can |
| request this activation by setting the |
| {@link android.accessibilityservice.AccessibilityServiceInfo#flags flags} member of the service’s |
| {@link android.accessibilityservice.AccessibilityServiceInfo} instance to |
| {@link android.accessibilityservice.AccessibilityServiceInfo#FLAG_REQUEST_TOUCH_EXPLORATION_MODE}, |
| as shown in the following example. |
| </p> |
| |
| <pre> |
| public class MyAccessibilityService extends AccessibilityService { |
| @Override |
| public void onCreate() { |
| getServiceInfo().flags = AccessibilityServiceInfo.FLAG_REQUEST_TOUCH_EXPLORATION_MODE; |
| } |
| ... |
| } |
| </pre> |
| |
| <p>Once your service has requested activation of Explore by Touch, the user must allow the |
| feature to be turned on, if it is not already active. When this feature is active, your service |
| receives notification of accessibility gestures through your service's |
| {@link android.accessibilityservice.AccessibilityService#onGesture onGesture()} callback method |
| and can respond by taking actions for the user.</p> |
| |
| |
| <h3 id="using-actions">Using accessibility actions</h3> |
| |
| <p>Accessibility services can take action on behalf of users to make interacting with applications |
| simpler and more productive. The ability of accessibility services to perform actions was added |
| in Android 4.0 (API Level 14) and significantly expanded with Android 4.1 (API Level 16).</p> |
| |
| <p>In order to take actions on behalf of users, your accessibility service must |
| <a href="#register">register</a> to receive events from a few or many applications and request |
| permission to view the content of applications by setting the |
| <a href="{@docRoot}reference/android/R.styleable.html#AccessibilityService_canRetrieveWindowContent"> |
| {@code android:canRetrieveWindowContent}</a> to {@code true} in the |
| <a href="#service-config">service configuration file</a>. When events are received by your |
| service, it can then retrieve the |
| {@link android.view.accessibility.AccessibilityNodeInfo} object from the event using |
| {@link android.view.accessibility.AccessibilityEvent#getSource getSource()}. |
| With the {@link android.view.accessibility.AccessibilityNodeInfo} object, your service can then |
| explore the view hierarchy to determine what action to take and then act for the user using |
| {@link android.view.accessibility.AccessibilityNodeInfo#performAction performAction()}.</p> |
| |
| <pre> |
| public class MyAccessibilityService extends AccessibilityService { |
| |
| @Override |
| public void onAccessibilityEvent(AccessibilityEvent event) { |
| // get the source node of the event |
| AccessibilityNodeInfo nodeInfo = event.getSource(); |
| |
| // Use the event and node information to determine |
| // what action to take |
| |
| // take action on behalf of the user |
| nodeInfo.performAction(AccessibilityNodeInfo.ACTION_SCROLL_FORWARD); |
| |
| // recycle the nodeInfo object |
| nodeInfo.recycle(); |
| } |
| ... |
| } |
| </pre> |
| |
| <p>The {@link android.view.accessibility.AccessibilityNodeInfo#performAction performAction()} method |
| allows your service to take action within an application. If your service needs to perform a |
| global action such as navigating to the Home screen, pressing the Back button, opening the |
| notifications screen or recent applications list, then use the |
| {@link android.accessibilityservice.AccessibilityService#performGlobalAction performGlobalAction()} |
| method.</p> |
| |
| |
| <h3 id="focus-types">Using focus types</h3> |
| |
| <p>Android 4.1 (API Level 16) introduces a new type of user interface focus called <em>Accessibility |
| Focus</em>. This type of focus can be used by accessibility services to select any visible user |
| interface element and act on it. This focus type is different from the more well known <em>Input |
| Focus</em>, which determines what on-screen user interface element receives input when a user |
| types characters, presses <strong>Enter</strong> on a keyboard or pushes the center button of a |
| D-pad control.</p> |
| |
| <p>Accessibility Focus is completely separate and independent from Input Focus. In fact, it is |
| possible for one element in a user interface to have Input Focus while another element has |
| Accessibility Focus. The purpose of Accessibility Focus is to provide accessibility services with |
| a method of interacting with any visible element on a screen, regardless of whether or not the |
| element is input-focusable from a system perspective. You can see accessibility focus in action by |
| testing accessibility gestures. For more information about testing this feature, see |
| <a href="{@docRoot}tools/testing/testing_accessibility.html#test-gestures">Testing gesture |
| navigation</a>.</p> |
| |
| <p class="note"> |
| <strong>Note:</strong> Accessibility services that use Accessibility Focus are responsible for |
| synchronizing the current Input Focus when an element is capable of this type of focus. Services |
| that do not synchronize Input Focus with Accessibility Focus run the risk of causing problems in |
| applications that expect input focus to be in a specific location when certain actions are taken. |
| </p> |
| |
| <p>An accessibility service can determine what user interface element has Input Focus or |
| Accessibility Focus using the {@link android.view.accessibility.AccessibilityNodeInfo#findFocus |
| AccessibilityNodeInfo.findFocus()} method. You can also search for elements that can be selected |
| with Input Focus using the |
| {@link android.view.accessibility.AccessibilityNodeInfo#focusSearch focusSearch()} method. |
| Finally, your accessibility service can set Accessibility Focus using the |
| {@link android.view.accessibility.AccessibilityNodeInfo#performAction |
| performAction(AccessibilityNodeInfo.ACTION_SET_ACCESSIBILITY_FOCUS)} method.</p> |
| |
| |
| <h2 id="examples">Example Code</h2> |
| |
| <p>The API Demo project contains two samples which can be used as a starting point for generating |
| accessibility services |
| ({@code <sdk>/samples/<platform>/ApiDemos/src/com/example/android/apis/accessibility}): |
| </p> |
| |
| <ul> |
| <li><a href="{@docRoot}resources/samples/ApiDemos/src/com/example/android/apis/accessibility/ClockBackService.html">ClockBackService</a> |
| - This service is based on the original implementation of {@link |
| android.accessibilityservice.AccessibilityService} and can be used as a base for developing basic |
| accessibility services that are compatible with Android 1.6 (API Level 4) and higher.</li> |
| <li><a href="{@docRoot}resources/samples/ApiDemos/src/com/example/android/apis/accessibility/TaskBackService.html">TaskBackService</a> |
| - This service is based on the enhanced accessibility APIs introduced in Android 4.0 (API Level |
| 14). However, you can use the Android <a href="{@docRoot}tools/support-library/index.html">Support |
| Libary</a> to substitute classes introduced in later API levels (e.g., |
| {@link android.view.accessibility.AccessibilityRecord}, |
| {@link android.view.accessibility.AccessibilityNodeInfo} |
| ) with equivalent support package classes (e.g., |
| {@link android.support.v4.view.accessibility.AccessibilityRecordCompat}, |
| {@link android.support.v4.view.accessibility.AccessibilityNodeInfoCompat} |
| ) to make this example work with API versions back to Android 1.6 (API Level 4).</li> |
| </ul> |