说起Android无障碍,也许很多同学没听说过,那这里我就来扫盲一下。许多Android用户有不同的能力(限制),这要求他们以不同的方式使用他们的Android设备。这些限制包括视力,肢体或与年龄有关,这些限制阻碍了他们看到或充分使用触摸屏,而用户的听力丧失,让他们可能无法感知声音信息和警报。Android提供了辅助功能的特性和服务帮助这些用户更容易的使用他们的设备,这些功能包括语音合成、触觉反馈、手势导航、轨迹球和方向键导航。Android应用程序开发人员可以利用这些服务,使他们的应用程序更贴近用户。
当然,我们这里无障碍化的实现主要是针对盲人用户,以语音的方式提示操作。许多用户界面控件依赖视觉线索来表示他们的意义和用法。例如,一个记笔记的应用程序可能会使用一个带加号图片的ImageButton表示用户可以添加一条新的笔记。在一个EditText组件旁边可能会有一个标签来说明需要输入的内容。视力较弱的用户看不到我们给出这些提示,这使得这些提示毫无用处。你可以使用在XML布局中的android:contentDescription 属性使这些控件更容易理解。 添加了这个属性的文本并不出现在屏幕上,但如果用户打开了提供声音提示的辅助功能服务,那么当用户进行访问控制时,文本会被讲出来。出于这个原因,将android:contentDescription属性应用在你应用程序用户界面的每个ImageButton ImageView,CheckBox上,并且在其他输入控件中添加该属性,对于无法看到输入控件的用户,这些额外的信息是很有必要的。
要想测试下无障碍的体验,我们需要以下几步:1.下载TalkBack辅助工具。2.下载讯飞语音软件。3到设置里面打开高级工具--->辅助功能--->打开TalkBack。完成上面这三步你就可以听到系统读出来的操作提示语音了。此时你是不是觉得有点麻烦,咋这么多步骤呢,盲人操作起来不是更费力吗?其实偷偷跟你说,盲人的手机里这些设置是一直打开的,所以你不用担心盲人使用这些功能会不方便。
上面废话了这么多,下面就直接进主题了。那我们的代码中要怎么实现呢?有两条线索:第一,如果你使用的控件是系统提供的,那么我们只需要在布局文件里面给每个控件添加android:contentDescription 属性,可以类似下面这样:
<ImageButton
android:id="@+id/icon"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_centerVertical="true"
android:layout_marginLeft="8dp"
android:layout_marginRight="8dp"
android:background="@drawable/trans"
android:contentDescription="添加图片按钮"
android:src="@drawable/photo_pack" />
很简单,只要这样设置就可以了。由于添加了android:contentDescription 这个属性,当用户移动焦点到这个按钮或将鼠标悬停在它上面时,提供口头反馈的辅助功能服务就会发出“添加图片按钮”提示用户进行添加图片操作。注意:对于EditText控件,提供了一个android:hint属性代替了contentDescription属性,这个属性可以在内容为空时,提示用户应该输入的内容。当输入完成后,TalkBack 读出输入内容给用户,不再是提示的文本内容。对于系统控件还有一种方式可以实现无障碍,类似于下面这种:
ImageView rightMoreButton = getRightMoreButton();
if (rightMoreButton != null) {
getRightMoreButton().setContentDescription("更多");
}
对于系统控件,总结起来就是要么在布局文件中设置android:contentDescription 属性,要么就在动态代码里面setContentDescription()。第二,如果我们使用的是自定义控件或者自绘控件,采用上面的方法实现无障碍是行不通的,但方法还是有的,那就是今天的重头戏:虚拟节点。
对于采用虚拟节点实现无障碍,我们需要在自定义控件的内部写一个类继承自ExporedByTouchHelper这个类,并且实现其中的5个关键方法。
//首先声明一个无障碍辅助类的变量
protected XXXTouchHelper touchHelper;
//然后初始化无障碍辅助类,初始化的时机可以在构造方法中,也可以在onMeasure方法中
if (isAccessibilityEnable()) {//当开启无障碍设置时才执行
if(touchHelper==null) {
touchHelper = new XXXTouchHelper(this);
//无障碍委托
ViewCompat.setAccessibilityDelegate(this, touchHelper);
//