支持文本编辑器中插入符号移动的IAccesible界面的正确解决方案是什么? [英] What is the correct solution to support IAccesible interface for caret movement in text editors?

查看:121
本文介绍了支持文本编辑器中插入符号移动的IAccesible界面的正确解决方案是什么?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我想从头开始实现一个支持IAccessible接口的文本编辑器.我正在使用MFC和Win32 API.

当标准文本编辑器(如记事本)中的插入符号位置发生更改时,插入符号移动所对应的字母,单词或行由诸如Narrator,JAWS等客户端工具发出发音.我不知道如何实现此功能.我在互联网上搜索并阅读了MSDN文档.

我阅读了 http://msdn.microsoft.com/en-us/library/dd317978. aspx http://msdn.microsoft.com/en-us/library/dd373892.客户端通过操作系统中的AccessibleObjectFromWindow方法请求插入符号的aspx ,操作系统将WM_GETOBJECT发送到应用程序. WM_GETOBJECT消息在相应的窗口回调函数中接收,但插入符号移动事件的hWnd为NULL.我检查了线程消息队列,但在线程消息队列中根本没有收到WM_GETOBJECT.

一种可行的方法,但不是正确的解决方案是调用

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()函数跟踪插入符号的以下事件:

  • EVENT_OBJECT_CREATE
  • EVENT_OBJECT_DESTROY
  • EVENT_OBJECT_SHOW
  • EVENT_OBJECT_HIDE
  • EVENT_OBJECT_LOCATIONCHANGE
  • EVENT_OBJECT_FOCUS

如果使用自定义控件,则需要使用 NotifyWinEvent()自行触发这些事件,尤其是应触发旁白的EVENT_OBJECT_LOCATIONCHANGE.

当客户端处理这些事件时,客户端应使用 AccessibleObjectFromEvent()访问其跟踪的对象的 IAccessible 接口.

正如您所说,Microsoft Active Accessibility将处理此调用并将WM_GETOBJECT消息发送到相应的窗口,具体取决于赋予 AccessibleObjectFromEvent()的处理程序(应该是事件中包含的处理程序)

当收到插入符号的WM_GETOBJECT时,应返回相应的 IAccessible 接口,该接口将报告正确的 accRole accLocation .

如果您没有收到正确的WM_GETOBJECT消息,则可能是因为您没有触发正确的事件.

您可以使用 Accessible Event Watcher 检查是否发送了正确的事件: http://msdn.microsoft.com/zh-我们/library/windows/desktop/dd317979%28v=vs.85%29.aspx

请参阅MSDN上的Active Accessibility服务器开发人员指南: http://msdn.microsoft.com/zh-我们/library/windows/desktop/dd318053%28v=vs.85%29.aspx

修改

此外,如果您使用Riched20.dll提供的标准插入符号(以Rich Edit为例),则文档规定与其他UI元素不同,它没有关联的窗口句柄.

I want to implement a text editor from scratch which supports IAccessible interface. I am using MFC and Win32 API.

When the caret position change in the standard text editors like Notepad, the corresponding letter, word or line to the caret movement is pronounced by client tools like Narrator, JAWS or etc. I don't know how to implement this feature. I search the internet and read the MSDN documentation.

I read in http://msdn.microsoft.com/en-us/library/dd317978.aspx and http://msdn.microsoft.com/en-us/library/dd373892.aspx that client asks for caret by AccessibleObjectFromWindow method from OS, and OS send WM_GETOBJECT to the application. WM_GETOBJECT messages received in the corresponding window callback function, but hWnd for caret movement event is NULL. I checked the thread message queue, but WM_GETOBJECT didn't receive at all in the thread message queue.

One method that has worked somewhat, but not the correct solution is to call

NotifyWinEvent( EVENT_OBJECT_NAMECHANGE, hwnd, OBJID_CLIENT, CHILDID_SELF )

when the caret move by user. And when client ask for the changed name, I return the corresponding text related to the caret movement.

HRESULT  CMyEditor::get_accName(VARIANT varChild, BSTR *pszName)
{
   *pszName = SysAllocString( L"CORESPONDING TEXT TO THE CARET MOVEMENT" );
   return S_OK;
}

解决方案

The client would use the SetWinEventHook() function to track the following events of the caret :

  • EVENT_OBJECT_CREATE
  • EVENT_OBJECT_DESTROY
  • EVENT_OBJECT_SHOW
  • EVENT_OBJECT_HIDE
  • EVENT_OBJECT_LOCATIONCHANGE
  • EVENT_OBJECT_FOCUS

If you use a custom control, you need to use NotifyWinEvent() to fire those events yourself, especially EVENT_OBJECT_LOCATIONCHANGE which should trigger the narration.

When the client handle thoses events, it should access the IAccessible interface of the object he's tracking using AccessibleObjectFromEvent().

As you say, Microsoft Active Accessibility would handle this call and send an WM_GETOBJECT message to the corresponding window depending on the handler given to AccessibleObjectFromEvent() (which should be the handler contained in the event).

When you receive the WM_GETOBJECT for the caret you should return the corresponding IAccessible interface which would report the proper accRole and accLocation.

If you're not receiving the right WM_GETOBJECT message it may be because you're not triggering the right events.

You can use the Accessible Event Watcher to check if the right events are sent : http://msdn.microsoft.com/en-us/library/windows/desktop/dd317979%28v=vs.85%29.aspx

See the Developer's Guide for Active Accessibility Servers on MSDN : http://msdn.microsoft.com/en-us/library/windows/desktop/dd318053%28v=vs.85%29.aspx

Edit

Also, if you're using the standard caret provided by Riched20.dll (in a Rich Edit as instance), the documentation stipulate that unlike other UI elements, it does not have an associated window handle.

这篇关于支持文本编辑器中插入符号移动的IAccesible界面的正确解决方案是什么?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆