本指南提供了 Android TV 上无障碍功能的最佳实践,并针对原生应用和非原生应用提供了建议。
为什么无障碍功能对我的 TV 应用很重要?
在观看电视的人群中,视力障碍并不罕见。根据世界卫生组织 (WHO) 提供的数据,全球有 22 亿人有视力障碍。根据 2018 年国民健康访谈调查,在美国,有 3200 万名年满 18 周岁的美国人出现了明显的视力丧失。根据欧洲盲人联盟 (EBU) 的数据,在欧洲,预计有 3,000 万失明和半视力人士。
最重要的是,有视觉障碍的用户对媒体内容的喜爱程度和视力正常的用户一样。Comcast 在 2017 年的一项调查表明,96% 的盲人或低视力用户经常观看电视,其中 81% 的用户每天的观看时间超过 1 小时。然而,65% 的玩家也表示在查找电视上的内容时遇到了问题。2020 年英国的一项调查显示,80% 的残障人士表示,他们在使用视频点播在线媒体服务时遇到了无障碍功能方面的问题。
虽然辅助技术可以并且确实可以帮助低视力用户,但在 TV 应用的内容发现历程中支持无障碍功能非常重要。例如,要格外注意提供导航指导和适当标记元素,并确保 TV 应用能够很好地与 TalkBack 等无障碍功能搭配使用。这些步骤可以显著改善视障用户的体验。
改进无障碍功能的第一步是提升认知度。本指南可帮助您和您的团队发现 TV 应用的无障碍功能问题。
Android 无障碍功能资源
如需详细了解 Android 上的无障碍功能,请参阅我们的无障碍功能开发资源。
文字缩放
Android TV 应用应通过支持不同的像素密度,尊重用户对文本缩放的偏好。
请特别注意:
- 对界面组件中的维度使用
wrap_content
。 - 确保布局会在组件尺寸随文本缩放比例而变化时重新排列组件。
- 确保组件在较大的文本比例下仍可适应屏幕。
- 不要为不灵活的组件使用 sp 文本大小单位。
检查
FONT_SCALE
的值以在自定义视图中进行调整:// Checking font scale with Context val scale = resources.configuration.fontScale Log.d(TAG, "Text scale is: " + scale)
可以使用以下命令更改文本缩放比例:
adb shell settings put system font_scale 1.2f
在 Android 12 及更高版本中,用户可以在设备设置中更改文本缩放比例。
键盘布局
在 Android 13(API 级别 33)及更高版本中,您可以使用 getKeyCodeForKeyLocation()
查找键码,以确定预期的密钥位置。如果用户已重新映射某些按键位置,或者使用的键盘具有典型布局,则可能需要执行此操作。
语音描述
在 Android 13(API 级别 33)及更高版本中,新的系统级无障碍功能偏好设置可让用户在所有应用中启用语音描述。Android TV 应用可以使用 isAudioDescriptionRequested()
进行查询,以此来检查用户的偏好设置。
Kotlin
private lateinit var accessibilityManager: AccessibilityManager // In onCreate(): accessibilityManager = getSystemService(AccessibilityManager::class.java) // Where your media player is initialized if (am.isAudioDescriptionRequested) { // User has requested to enable audio descriptions }
Java
private AccessibilityManager accessibilityManager; // In onCreate(): accessibilityManager = getSystemService(AccessibilityManager.class); // Where your media player is initialized if(accessibilityManager.isAudioDescriptionRequested()) { // User has requested to enable audio descriptions }
Android TV 应用可以通过向 AccessibilityManager
添加监听器来监控用户偏好设置何时发生变化:
Kotlin
private val listener = AccessibilityManager.AudioDescriptionRequestedChangeListener { enabled -> // Preference changed; reflect its state in your media player } override fun onStart() { super.onStart() accessibilityManager.addAudioDescriptionRequestedChangeListener(mainExecutor, listener) } override fun onStop() { super.onStop() accessibilityManager.removeAudioDescriptionRequestedChangeListener(listener) }
Java
private AccessibilityManager.AudioDescriptionRequestedChangeListener listener = enabled -> { // Preference changed; reflect its state in your media player }; @Override protected void onStart() { super.onStart(); accessibilityManager.addAudioDescriptionRequestedChangeListener(getMainExecutor(), listener); } @Override protected void onStop() { super.onStop(); accessibilityManager.removeAudioDescriptionRequestedChangeListener(listener); }