是否有可能创建一个触摸应用程序来与另一个应用程序进行交互,“共享”两者之间的焦点?

时间:2013-11-07 04:06:55

标签: c# wpf winforms windows-8 touch

我要做的是有一个帮助应用程序,用户可以使用触摸输入来影响第二个应用程序。我已经能够向第二个应用程序发送击键,但我遇到的问题是当我想按住一个按钮时。

例如,在我的应用程序中,我希望能够按住一个按钮来模拟按下ctrl键。触摸此按钮时,我希望能够与第二个应用程序进行交互。如果用户放开按钮,则按下ctrl键。我可以解决这个问题,除非用户在第二个应用程序上执行任何操作,按下的按钮是未按下的(因为其他应用程序获得了焦点)。

我不在乎是否必须使用WPF或Windows窗体,只要我可以使用它。 Windows 8或8.1也是可以接受的(所有客户端都是8.1)。

任何帮助将不胜感激!

注意我已添加到下面的评论中。

第二个应用程序是我没有创建的应用程序,它可能是真的。一个场景是我的应用程序有一个ctrl按钮,你可以按住按住,例如,在outlook中单击一个链接。或者在我的应用程序中按住一个移动按钮,同时用笔在Photoshop中绘图画一条直线。我能够发送击键,但是无法处理“保持”触摸命令。

2 个答案:

答案 0 :(得分:0)

我真的很想知道为什么你需要在两个不同的应用程序中,但这是我能想到的最好的。

在应用程序中,您应该能够订阅KeyDown,KeyUp,Focus和Blur(失去焦点)。我不清楚这是一个实际按钮还是它的触摸输入,但无论情况如何,假设KeyDown是当用户“模拟”按下的ctrl键时触发的任何事件,而KeyUp是任何事件触发当用户停止“模拟”ctrl键关闭时。

设置App1,这样当它获得焦点时,它会与App2通信状态:郁闷或不抑郁。每次KeyDown或KeyUp触发时,都会向App2发送一条消息。

当App1的Blur事件触发时,停止向App2发送消息。即使App1不再按下按钮,App2也不会知道它,并且可以继续按下按钮,直到App2重新获得焦点,然后可以再次发送消息。

如果是我,我会让App2拥有与App1完全相同的逻辑,所以当App2进入Focus时,它开始处理上/下状态本身。当发生模糊/焦点事件时,您可能希望让两个应用程序执行某种“握手”以确保在切换时保持状态。当App2获得Blur事件时,它将状态转移到App1并再次握手,因此App1知道它现在负责管理状态。

这基本上是让应用程序通过“tag-team”进行合作。它们保持一些状态在彼此之间同步,当模糊/焦点事件触发时“切换”责任。由于你无法知道Blur会在Focus激发另一个应用程序之前触发一个应用程序,你需要使用相同的机制来传达这个“模拟按钮”的状态来协调应用程序,这样它们就不会相互干扰。

有些东西告诉我,这并没有完全解决你的问题,但是听到为什么它不会让每个人都更接近于思考剩下的方式。让我知道扭曲的结局,嗯?

答案 1 :(得分:0)

由于时间太长,我正在创造一个新的答案。我做了研究,我很确定我知道发生了什么。但是在得出结论之前,我会提到我检查过的所有官方资源。

可能的打包解决方案

首先,新的Windows Input Simulator可能会立即解决您的所有麻烦。如果您需要我将在下面讨论的Windows API,请先检查PInvoke.net,看看他们是否有您正在尝试拨打的电话的文档。

Windows API方式

最好的起点是MSDN上的User Interaction文章。那里有一堆新的Winu8 Touch API,但您可能对遗留的Keyboard input文章感兴趣。

应用程序的每个窗口都必须有Windows Procedure(又名WindowsProc),负责对其关注的消息做出反应(例如,单击按钮,指示Window需要绘制GUI的消息,或WM_QUIT事件提醒它以优雅地处理Window持有的资源。此过程还负责处理来自输入设备的消息,如鼠标点击和键盘上的键。

在你的情况下,你更感兴趣的是让Window认为当没有时,键盘会显示一条消息。这就是SendInput API调用的用途;它允许您将键盘,鼠标或其他输入设备直接插入队列中的INPUT消息数组,从而避免了用户进行物理操作的需要。这个简单的API调用专门接受MOUSEINPUTKEYBDINPUTHARDWAREINPUT消息。

对于键盘,当按下某个键( WM_KEYDOWN )以及发布时( WM_KEYUP ),您会收到一条消息),要确定 CTRL+C 等热键,您必须注意 WM_KEYDOWN 消息中的字母 C < / strong>在 WM_KEYDOWN CTRL 之后但 WM_KEYUP 之前收到的消息。

管理输入设备消息

要模拟输入设备,请使用 SendInput 传递 WM_KEYDOWN 和/或 WM_KEYUP 消息到目标窗口。但是不要忘记应用程序可以有多个窗口。有一些API调用来获取不同的Windows,但是在你可以使用 SendInput 之前编写代码来找到它。

要了解窗口对输入设备的看法,请使用GetAsyncKeyState。如果你干涉了与输入设备相关的API,你可能无法信任它。

窗口上有一个BlockInput调用,拒绝除阻止它的线程中的 SendInput 调用之外的所有邮件。在大多数情况下,尽快重新启用输入是正确的。文档说如果阻塞线程死亡,则 BlockInput 被禁用。类似但不那么苛刻的调用是EnableWindow,它会阻止窗口接收输入焦点。

适用于Windows的API包含to register hooks功能,可让您specify kinds of messages and/or certain windows to be reviewed通过用户指定的功能。