像 GlovePIE 一样伪造输入

Posted

技术标签:

【中文标题】像 GlovePIE 一样伪造输入【英文标题】:Faking Input Like GlovePIE 【发布时间】:2011-11-21 18:24:53 【问题描述】:

我一直在针对 Kinect 进行编程,现在我想让游戏对我在 Kinect 上所做的事情做出反应。将数据发送到记事本以进行按键操作确实很容易,但将其发送到游戏则要困难得多。

首先,我一直在使用 Kinect 中的 WPF Skeleton 示例,并在此基础上进行构建。我可以使用 C++ 版本,但我的 C++ 非常生锈,我不想这样做。

这就是我到目前为止所做的,我尝试过SendKeysSendInputkeybd_eventPost_Message。这些都没有进入像Burnout Paradise这样的游戏。

我知道 GlovePIE 输入可以用于游戏,但如何?目前我的工作/破解是使用 PPJoy,它有 C++ 中的示例代码来模拟按钮按下。我通过我的 WPF 应用程序中的 [DllImport] 调用它。然后我拿起 GlovePIE 中按下的操纵杆按钮并将其转换为键盘键。所以我绕了一圈,它可以工作,但 PPJoys 驱动程序没有签名,所以我不能真正分享这段代码,因为人们必须允许测试签名的驱动程序。

有人知道 GlovePIE 是如何实现他们的按键操作的吗?我已在 GlovePIE 论坛上发帖,但没有回复。 GlovePIE 对旧的 openNI kinect 驱动程序有一点破解,但我使用的是几周前最近发布的标准微软版本。

【问题讨论】:

【参考方案1】:

好的,不知道在回答你自己的问题时有什么独家新闻,但我想出了整个正确的解决方案,并想分享为已勾选的答案。

首先包含这个 using 语句

using System.Runtime.InteropServices;

然后把这个放到你的班级这个在你的班级

[DllImport("user32.dll", EntryPoint = "keybd_event", CharSet = CharSet.Auto, ExactSpelling = true)]
public static extern void Keybd_event(byte vk, byte scan, int flags, int extrainfo);

这将导入 C 方法以在 C# 中使用。 现在一些游戏/应用程序使用虚拟键 VKey,而一些(Direct X aka DIKey)使用扫描码。我的问题是我不正确地使用了扫描码,因此它不适用于某些游戏。我建议如果你不知道什么应用程序想要使用这些,你调用它两次,一次使用虚拟键,一次用于直接输入键

以下是使用虚拟键然后使用直接输入键两次调用字母“A”的示例。

KEYDOWN = 0
KEYUP = 2
//Virtual Key
Keybd_event(65, 0, KEYDOWN, 0);

//Direct Input Key
Keybd_event(0, 30, KEYDOWN, 0);

如您所见,A 的值与 VK 和 DIK 不同 这两个链接都与 HEX 值有关,而我上面的示例显示 Base 10(整数)

VKeys 链接http://delphi.about.com/od/objectpascalide/l/blvkc.htm

DIKeys 链接http://community.bistudio.com/wiki/DIK_KeyCodes

这也应该适用于 SendInput,但我还没有完全验证。

【讨论】:

【参考方案2】:

我不知道 GlovePIE,抱歉,但也许这些可能会有所帮助。

PostMessage 和 SendMessage 在处理模拟击键时得到不同的行为。 还有助于了解您实际发送的消息,keydown/up,keypress 等。

您可能需要更改焦点 - 可能选择了错误的元素,或者您发送到错误的(子)窗口。

类似地,如果您模拟鼠标点击,也可以检查鼠标的位置,以确保它仍在可点击区域上。

考虑同时按住一个键触发重复机制发送多个键消息,通常在游戏中你按住键不只是点击一次。

【讨论】:

我已经通过使用睡眠“按住”键,然后发送 keyup 命令。一切都在记事本中运行良好,我也不想指定我发送击键的窗口/子窗口。所以我不能让它与游戏/应用程序无关。不过感谢您的一些想法。 取决于各种事情,应用程序可能期望的不仅仅是 keyup 需要一些时间 - 或者忽略它并使用其他东西,例如看到多个 'wm_char' 消息。 ` ::SendMessage(hWND, WM_KEYDOWN, VK_RETURN, 0); ::SendMessage(hWND, WM_CHAR,VK_RETURN,0); ::SendMessage(hWND, WM_CHAR,VK_RETURN,0); ::SendMessage(hWND, WM_KEYUP, VK_RETURN, 0); `【参考方案3】:

虽然我不会说这是最好的答案,但我想用我正在使用的解决方案来回过头来。我发现我可以使用已签名的 vJoy http://headsoft.com.au/index.php?category=vjoy,因此它可以在 Windows 7 64 位中使用。我可以调用这个 extern keybd_event

[DllImport("user32.dll", EntryPoint = "keybd_event", CharSet = CharSet.Auto, ExactSpelling = true)]
public static extern void Keybd_event(byte vk, byte scan, int flags, int extrainfo);

从那里我可以 Keybd_event(CKEY, SCANCODE, KEYDOWN, 0); 然后 X 帧稍后调用 Keybd_event(CKEY, SCANCODE, KEYUP, 0);

我将 vJoy 设置为读取“c”或我通过 keybd_event 发送的其他键。 vJoy 正确读取此内容,然后“按下”GlovePIE 拾取的相关按钮。所以在 GlovePIE 中我的脚本看起来像

A = joystick1.Button1
Z = joystick1.Button2

这在我尝试过的游戏中有效。 这绝对不是主意,但它可以工作并允许最终用户通过 vJoy 和 GlovePIE 自定义输入。

【讨论】:

以上是关于像 GlovePIE 一样伪造输入的主要内容,如果未能解决你的问题,请参考以下文章

如何在 C++03 中伪造构造函数继承?

BugKu——Web——社工-伪造

是否可以生成一个伪类型,以便我可以伪造 gdb 漂亮的打印系统?

跨站请求伪造(csrf)

跨站请求伪造

CSRF跨站请求伪造的安全防护