UI 自动化和 Microsoft Active Accessibility

注释

本文档适用于想要使用 System.Windows.Automation 命名空间中定义的托管 UI 自动化类的 .NET Framework 开发人员。 有关 UI 自动化的最新信息,请参阅 Windows 自动化 API:UI 自动化

Microsoft活动辅助功能是使应用程序易于访问的早期解决方案。 Microsoft UI 自动化是适用于 Microsoft Windows 的新辅助功能模型,旨在满足辅助技术产品和自动化测试工具的需求。 UI 自动化相较于 Active Accessibility 带来了许多改进。

本主题包括 UI 自动化的主要功能,并介绍了这些功能与活动辅助功能有何不同。

编程语言

主动辅助功能基于支持双接口的组件对象模型(COM),因此在 C/C++、Microsoft Visual Basic 6.0 和脚本语言中是可编程的。 UI 自动化(包括标准控件的客户端提供程序库)是用托管代码编写的,UI 自动化客户端应用程序使用 C# 或 Visual Basic .NET 轻松编程。 UI 自动化提供程序(即接口实现)可以用托管代码或 C/C++编写。

Windows Presentation Foundation 中的支持

Windows Presentation Foundation(WPF)是用于创建用户界面的新模型。 WPF 元素不包含对 Active Accessibility 的本机支持;但是,它们支持 UI 自动化,这包括对 Active Accessibility 客户端的桥接支持。 只有专为 UI 自动化编写的客户端才能充分利用 WPF 的辅助功能,例如对文本的丰富支持。

服务器和客户端

在 Active Accessibility 中,服务器和客户端主要通过服务器的 IAccessible 实现进行直接通信。

在 UI 自动化中,核心服务位于服务器(称为提供程序)和客户端之间。 核心服务对提供程序实现的接口进行调用,并提供其他服务,例如为元素生成唯一的运行时标识符。 客户端应用程序使用库函数调用 UI 自动化服务。

UI 自动化提供程序可以向活动辅助功能客户端提供信息,活动辅助功能服务器可以向 UI 自动化客户端应用程序提供信息。 但是,由于 Active Accessibility 不公开与 UI 自动化一样多的信息,因此这两个模型不完全兼容。

UI 元素

Active Accessibility 以 IAccessible 接口或子标识符的形式呈现 UI 元素。 很难比较两个 IAccessible 指针以确定它们是否引用同一元素。

在 UI 自动化中,每个元素都表示为一个 AutomationElement 对象。 比较是使用相等运算符或 Equals 方法完成的,这两者都比较元素的唯一运行时标识符。

树视图和导航

屏幕上的用户界面(UI)元素可以作为树结构,桌面作为根、应用程序窗口作为直接子级,以及应用程序中的元素作为进一步后代。

在 Active Accessibility 中,许多与最终用户不相关的自动化元素都公开在树中。 客户端应用程序必须查看所有元素,以确定哪些元素有意义。

UI 自动化客户端应用程序通过筛选视图查看 UI。 该视图仅包含感兴趣的元素:向用户提供信息或启用交互的元素。 仅控件元素和内容元素的预定义视图可用;此外,应用程序还可以定义自定义视图。 UI 自动化简化了向用户描述 UI 以及帮助用户与应用程序交互的任务。

在活动辅助功能中,元素之间的导航可以是空间性的(例如,移动到屏幕上左侧的元素)、逻辑性的(例如,移动到下一个菜单项或对话框中选项卡顺序的下一项),或者是层次性的(例如,移动到容器中的第一个子元素,或从子元素移动到父元素)。 分层导航很复杂,因为子元素并不总是实现 IAccessible的对象。

在 UI 自动化中,所有 UI 元素都是 AutomationElement 支持相同基本功能的对象。 (从提供程序的角度来看,它们是实现从 IRawElementProviderSimple.继承的接口的对象)导航主要是分层的:从父级到子级,从一个同级到下一个。 (同级之间的导航具有一个逻辑元素,因为它可能遵照的是 Tab 键顺序。)通过使用 TreeWalker 类,你可以使用树的任何筛选视图从任何起点进行导航。 您还可以使用 FindFirstFindAll 导航到特定的子级或后代;例如,检索对话框中支持指定控件模式的所有元素非常简单。

用户界面自动化中的导航比 Active Accessibility 更一致。 某些元素(如下拉列表和弹出窗口)在活动辅助功能树中出现两次,并且从它们进行导航可能会产生意外的结果。 其实就是无法对 rebar 控件正确实现 Active Accessibility。 UI 自动化能够重排根目录并进行重新布置,因此可以在树的任何位置放置元素,不必考虑窗口所有者构建的层次结构。

角色和控件类型

主动辅助功能使用 accRole 属性(IAccessible::get_actRole)来获取有关 UI 中元素角色的描述,例如 ROLE_SYSTEM_SLIDER 或 ROLE_SYSTEM_MENUITEM。 元素的角色是确定其可用功能的主要线索。 使用固定方法(如 IAccessible::accSelectIAccessible::accDoDefaultAction)实现与控件的交互。 客户端应用程序和用户界面之间的交互仅限于可以通过IAccessible实现的功能。

相比之下,UI 自动化在很大程度上将元素(由 ControlType 属性描述)的控件类型与其预期功能分离。 功能由通过实现其特殊化接口的提供程序支持的控件模式来确定。 可以组合控件模式来描述特定 UI 元素支持的完整功能集。 某些提供程序需要支持特定控件模式;例如,复选框的提供程序必须支持切换控件模式。 其他提供程序需要支持一组控件模式中的一项或多项;例如,按钮必须支持切换或调用功能。 还有一些人根本不支持控制模式;例如,无法移动、调整大小或停靠的窗格没有任何控件模式。

UI 自动化支持自定义控件,这些控件由 Custom 属性标识,并且可以通过 LocalizedControlTypeProperty 属性描述。

下表显示了 Active Accessibility 角色到用户界面自动化控件类型的映射。

Active Accessibility 角色 UI 自动化控件类型
ROLE_SYSTEM_PUSHBUTTON 按钮
ROLE_SYSTEM_CLIENT 日历
ROLE_SYSTEM_CHECKBUTTON 复选框
ROLE_SYSTEM_COMBOBOX 组合框
ROLE_SYSTEM_CLIENT 习惯
ROLE_SYSTEM_LIST 数据网格
ROLE_SYSTEM_LISTITEM 数据项
ROLE_SYSTEM_DOCUMENT 文档
ROLE_SYSTEM_TEXT 编辑
ROLE_SYSTEM_GROUPING
ROLE_SYSTEM_LIST 标题
ROLE_SYSTEM_COLUMNHEADER 标头项
ROLE_SYSTEM_LINK 超链接
ROLE_SYSTEM_GRAPHIC 图片
ROLE_SYSTEM_LIST 列表
ROLE_SYSTEM_LISTITEM 列表项
ROLE_SYSTEM_MENUPOPUP 菜单
ROLE_SYSTEM_MENUBAR 菜单栏
ROLE_SYSTEM_MENUITEM 菜单项
ROLE_SYSTEM_PANE 面板
ROLE_SYSTEM_PROGRESSBAR 进度栏
ROLE_SYSTEM_RADIOBUTTON 单选按钮
ROLE_SYSTEM_SCROLLBAR 滚动条
ROLE_SYSTEM_SEPARATOR 分隔符
ROLE_SYSTEM_SLIDER 滑 块
ROLE_SYSTEM_SPINBUTTON 旋转图标
ROLE_SYSTEM_SPLITBUTTON “拆分”按钮
ROLE_SYSTEM_STATUSBAR 状态栏
ROLE_SYSTEM_PAGETABLIST 选项卡
ROLE_SYSTEM_PAGETAB 选项卡项
ROLE_SYSTEM_TABLE
ROLE_SYSTEM_STATICTEXT 文本
ROLE_SYSTEM_INDICATOR 拇指
ROLE_SYSTEM_TITLEBAR 标题栏
ROLE_SYSTEM_TOOLBAR 工具栏
ROLE_SYSTEM_TOOLTIP 工具提示
ROLE_SYSTEM_OUTLINE
ROLE_SYSTEM_OUTLINEITEM 树形项目
ROLE_SYSTEM_WINDOW 窗口

有关不同控件类型的详细信息,请参阅 UI 自动化控件类型

状态和属性

在 Active Accessibility 中,元素支持一组常见的属性,某些属性(例如 accState)必须根据元素的角色描述非常不同的内容。 服务器必须实现IAccessible中所有返回属性的方法,包括那些与元素无关的方法。

UI 自动化定义更多属性,其中一些属性对应于 Active Accessibility 中的状态。 有些元素很常见,但其他元素特定于控件类型和控件模式。 属性通过唯一标识符进行区分,大多数属性都可以使用单个方法进行检索, GetCurrentPropertyValue 或者 GetCachedPropertyValue。 许多属性也可以从 CurrentCached 属性访问器中轻松检索。

UI 自动化提供程序不必实现不相关的属性,但只需为它不支持的任何属性返回一个 null 值。 此外,UI 自动化核心服务可以从默认窗口提供程序获取某些属性,这些属性与提供程序显式实现的属性合并。

除了支持更多属性外,UI 自动化还允许通过单个跨进程调用检索多个属性来提供更好的性能。

下表显示了两个模型中的属性之间的对应关系。

Active Accessibility 属性访问器 UI 自动化属性 ID 注解
get_accKeyboardShortcut AccessKeyPropertyAcceleratorKeyProperty AccessKeyProperty 如果两者都存在,则优先。
get_accName NameProperty
get_accRole ControlTypeProperty 请参阅上表,了解如何将角色映射到控制类型。
get_accValue ValuePattern.ValueProperty

RangeValuePattern.ValueProperty
仅适用于支持 ValuePattern 或 RangeValuePattern 的控件类型。 RangeValue 值规范化为 0-100,与 MSAA 行为保持一致。 值项使用字符串。
get_accHelp HelpTextProperty
accLocation BoundingRectangleProperty
get_accDescription 在 UI 自动化中不支持 accDescription MSAA 中没有明确的规范,这导致提供程序在此属性中放置不同的信息片段。
get_accHelpTopic 在 UI 自动化中不支持

下表显示了哪些 UI 自动化属性对应于活动辅助功能状态常量。

Active Accessibility 状态 UI 自动化属性 是否触发状态更改?
STATE_SYSTEM_CHECKED 对于复选框, ToggleStateProperty

对于单选按钮, IsSelectedProperty
Y
STATE_SYSTEM_COLLAPSED ExpandCollapseState = Collapsed Y
STATE_SYSTEM_EXPANDED ExpandCollapseState = ExpandedPartiallyExpanded Y
STATE_SYSTEM_FOCUSABLE IsKeyboardFocusableProperty N
STATE_SYSTEM_FOCUSED HasKeyboardFocusProperty N
STATE_SYSTEM_HASPOPUP 针对菜单项的 ExpandCollapsePattern N
STATE_SYSTEM_INVISIBLE IsOffscreenProperty = True 且 GetClickablePoint 导致 NoClickablePointException N
STATE_SYSTEM_LINKED ControlTypeProperty =

Hyperlink
N
STATE_SYSTEM_MIXED ToggleState = Indeterminate N
STATE_SYSTEM_MOVEABLE CanMoveProperty N
STATE_SYSTEM_MUTLISELECTABLE CanSelectMultipleProperty N
STATE_SYSTEM_OFFSCREEN IsOffscreenProperty = 真 N
STATE_SYSTEM_PROTECTED IsPasswordProperty N
STATE_SYSTEM_READONLY RangeValuePattern.IsReadOnlyPropertyValuePattern.IsReadOnlyProperty N
STATE_SYSTEM_SELECTABLE SelectionItemPattern 已被支持 N
STATE_SYSTEM_SELECTED IsSelectedProperty N
STATE_SYSTEM_SIZEABLE CanResize N
STATE_SYSTEM_UNAVAILABLE IsEnabledProperty Y

以下状态要么没有被大多数 Active Accessibility 控制服务器实现,要么在 UI 自动化中没有等效项。

Active Accessibility 状态 注解
STATE_SYSTEM_BUSY 在 UI 自动化中不可用
STATE_SYSTEM_DEFAULT 在 UI 自动化中不可用
STATE_SYSTEM_ANIMATED 在 UI 自动化中不可用
STATE_SYSTEM_EXTSELECTABLE 未通过 Active Accessibility 服务器广泛实现
STATE_SYSTEM_MARQUEED 未通过 Active Accessibility 服务器广泛实现
STATE_SYSTEM_SELFVOICING 未通过 Active Accessibility 服务器广泛实现
STATE_SYSTEM_TRAVERSED 在 UI 自动化中不可用
STATE_SYSTEM_ALERT_HIGH 未通过 Active Accessibility 服务器广泛实现
STATE_SYSTEM_ALERT_MEDIUM 未通过 Active Accessibility 服务器广泛实现
STATE_SYSTEM_ALERT_LOW 未通过 Active Accessibility 服务器广泛实现
STATE_SYSTEM_FLOATING 未通过 Active Accessibility 服务器广泛实现
STATE_SYSTEM_HOTTRACKED 在 UI 自动化中不可用
STATE_SYSTEM_PRESSED 在 UI 自动化中不可用

有关 UI 自动化属性标识符的完整列表,请参阅 UI 自动化属性概述

事件

UI 自动化中的事件机制与 Active Accessibility 中的事件机制不同,它不依赖于 Windows 事件路由(与窗口句柄紧密绑定),并且不需要客户端应用程序设置挂钩。 可以对事件订阅进行微调,不仅能订阅特定事件,甚至还能订阅树的特定部分。 通过跟踪所侦听的事件,提供程序也可微调其事件的引发。

客户端还可以更轻松地检索引发事件的元素,因为这些元素直接传递给事件回调。 如果客户端订阅事件时缓存请求处于活动状态,则会自动预提取元素的属性。

下表显示了 Active Accessibility WinEvents 和 UI 自动化事件的对应关系。

WinEvent UI 自动化事件标识符
EVENT_OBJECT_ACCELERATORCHANGE AcceleratorKeyProperty 属性更改
EVENT_OBJECT_CONTENTSCROLLED 相关联的滚动条上的 VerticalScrollPercentPropertyHorizontalScrollPercentProperty 属性更改
EVENT_OBJECT_CREATE StructureChangedEvent
EVENT_OBJECT_DEFACTIONCHANGE 无等效项
EVENT_OBJECT_DESCRIPTIONCHANGE 没有确切的等效项;也许 HelpTextPropertyLocalizedControlTypeProperty 属性更改
EVENT_OBJECT_DESTROY StructureChangedEvent
EVENT_OBJECT_FOCUS AutomationFocusChangedEvent
EVENT_OBJECT_HELPCHANGE HelpTextProperty 更改
EVENT_OBJECT_HIDE StructureChangedEvent
EVENT_OBJECT_LOCATIONCHANGE BoundingRectangleProperty 属性更改
EVENT_OBJECT_NAMECHANGE NameProperty 属性更改
EVENT_OBJECT_PARENTCHANGE StructureChangedEvent
EVENT_OBJECT_REORDER 在 Active Accessibility 中使用不一致。 在 UI 自动化中没有定义直接对应的事件。
事件对象选择 ElementSelectedEvent
EVENT_OBJECT_SELECTIONADD ElementAddedToSelectionEvent
EVENT_OBJECT_SELECTIONREMOVE ElementRemovedFromSelectionEvent
EVENT_OBJECT_SELECTIONWITHIN 无等效项
EVENT_OBJECT_SHOW StructureChangedEvent
EVENT_OBJECT_STATECHANGE 各种属性更改事件
EVENT_OBJECT_VALUECHANGE RangeValuePattern.ValuePropertyValuePattern.ValueProperty 已更改
EVENT_SYSTEM_ALERT 无等效项
EVENT_SYSTEM_CAPTUREEND 无等效项
EVENT_SYSTEM_CAPTURESTART 无等效项
EVENT_SYSTEM_CONTEXTHELPEND 无等效项
EVENT_SYSTEM_CONTEXTHELPSTART 无等效项
EVENT_SYSTEM_DIALOGEND WindowClosedEvent
EVENT_SYSTEM_DIALOGSTART WindowOpenedEvent
EVENT_SYSTEM_DRAGDROPEND 无等效项
EVENT_SYSTEM_DRAGDROPSTART 无等效项
EVENT_SYSTEM_FOREGROUND AutomationFocusChangedEvent
EVENT_SYSTEM_MENUEND MenuClosedEvent
EVENT_SYSTEM_MENUPOPUPEND MenuClosedEvent
EVENT_SYSTEM_MENUPOPUPSTART MenuOpenedEvent
EVENT_SYSTEM_MENUSTART MenuOpenedEvent
EVENT_SYSTEM_MINIMIZEEND WindowVisualStateProperty 属性更改
EVENT_SYSTEM_MINIMIZESTART WindowVisualStateProperty 属性更改
EVENT_SYSTEM_MOVESIZEEND BoundingRectangleProperty 属性更改
EVENT_SYSTEM_MOVESIZESTART BoundingRectangleProperty 属性更改
EVENT_SYSTEM_SCROLLINGEND VerticalScrollPercentPropertyHorizontalScrollPercentProperty 属性更改
EVENT_SYSTEM_SCROLLINGSTART VerticalScrollPercentPropertyHorizontalScrollPercentProperty 属性更改
EVENT_SYSTEM_SOUND 无等效项
EVENT_SYSTEM_SWITCHEND 没有等效项,但事件 AutomationFocusChangedEvent 指示新应用程序获得了焦点
EVENT_SYSTEM_SWITCHSTART 无等效项
无等效项 CurrentViewProperty 属性更改
无等效项 HorizontallyScrollableProperty 属性更改
无等效项 VerticallyScrollableProperty 属性更改
无等效项 HorizontalScrollPercentProperty 属性更改
无等效项 VerticalScrollPercentProperty 属性更改
无等效项 HorizontalViewSizeProperty 属性更改
无等效项 VerticalViewSizeProperty 属性更改
无等效项 ToggleStateProperty 属性更改
无等效项 WindowVisualStateProperty 属性更改
无等效项 AsyncContentLoadedEvent 事件
无等效项 ToolTipOpenedEvent

安全

某些 IAccessible 自定义场景需要将基础 IAccessible 封装起来并进行调用。 这会产生安全影响,因为部分受信任的组件不应是代码路径上的中介。

UI 自动化模型消除了提供者需要调用其他提供者代码的需求。 UI 自动化核心服务执行所有必要的聚合。

另请参阅