我想从零开始实现一个支持IAccessible接口的文本编辑器。 我正在使用MFC和Win32 API。
当标记文字编辑器(如记事本)中的插入符号位置发生变化时,插入符号移动的相应字母,单词或行将由Narrator,JAWS等客户端工具发出。我不知道如何实现此function。 我search互联网并阅读MSDN文档。
我在http://msdn.microsoft.com/en-us/library/dd317978.aspx和http://msdn.microsoft.com/en-us/library/dd373892.aspx阅读客户端请求通过AccessibleObjectFromWindow方法从操作系统,和操作系统发送WM_GETOBJECT到应用程序。 WM_GETOBJECT消息在相应的窗口callback函数中收到,但hWnd用于脱字符号移动事件是NULL。 我检查了线程消息队列,但是WM_GETOBJECT在线程消息队列中根本没有收到。
一种有效的方法,但不是正确的解决scheme是打电话
NotifyWinEvent( EVENT_OBJECT_NAMECHANGE, hwnd, OBJID_CLIENT, CHILDID_SELF )
当用户移动插入符时。 当客户要求更改的名称时,我会返回与相关的脱字符号相关的文字。
HRESULT CMyEditor::get_accName(VARIANT varChild, BSTR *pszName) { *pszName = SysAllocString( L"CORESPONDING TEXT TO THE CARET MOVEMENT" ); return S_OK; }
客户端将使用SetWinEventHook()函数跟踪以下事件的脱字符:
如果使用自定义控件,则需要使用NotifyWinEvent()来自己触发这些事件,特别是EVENT_OBJECT_LOCATIONCHANGE,这会触发叙述。
当客户端处理事件时,它应该访问使用AccessibleObjectFromEvent()跟踪的对象的IAccessible接口。
正如您所说,Microsoft Active Accessibility将处理此调用,并根据给予AccessibleObjectFromEvent() (应该是事件中包含的处理程序)的处理程序将WM_GETOBJECT消息发送到相应的窗口。
当您收到WM_GETOBJECT的脱字符时,您应该返回相应的IAccessible接口,它将报告正确的accRole和accLocation 。
如果你没有收到正确的WM_GETOBJECT消息,可能是因为你没有触发正确的事件。
您可以使用Accessible Event Watcher来检查是否发送了正确的事件: http : //msdn.microsoft.com/en-us/library/windows/desktop/dd317979%28v=vs.85%29.aspx
请参阅MSDN上的Active Accessibility server开发人员指南: http : //msdn.microsoft.com/en-us/library/windows/desktop/dd318053%28v=vs.85%29.aspx
编辑
此外,如果您使用Riched20.dll提供的标准插入符(Rich Edit作为实例),则文档规定与其他UI元素不同,它没有关联的窗口句柄。