从任何过程中获取密钥

我在网上看过很多解决方案,但没有一个完全符合我的要求。 我的应用程序在后台运行时,在给定进程(而不是我的控制台应用程序)中按下任何键的最佳/最简单方法是什么? 我不需要修改器或任何东西。

如果您不特别关心在最简单的方法中按下哪个键,则调用GetAsyncKeyState 。 它相当有限,因为它没有挂钩键盘,需要你连续调用它。 在我看来,最好的方法是挂钩键盘。

使用SetWindowsHookEx,您实际上可以显式指定与挂钩过程关联的线程的标识符,以便您可以挂钩特定进程的键(请参阅dwThreadId )。

这是一个你可以使用的课程(最初在Micrsoft博客上找到,但我现在似乎无法找到作者的名字!)

public delegate IntPtr KeyboardProcess(int nCode, IntPtr wParam, IntPtr lParam); public sealed class KeyboardHook { public static event EventHandler KeyPressed; private const int WH_KEYBOARD = 13; private const int WM_KEYDOWN = 0x0100; private static KeyboardProcess keyboardProc = HookCallback; private static IntPtr hookID = IntPtr.Zero; public static void CreateHook() { hookID = SetHook(keyboardProc); } public static void DisposeHook() { UnhookWindowsHookEx(hookID); } private static IntPtr SetHook(KeyboardProcess keyboardProc) { using (Process currentProcess = Process.GetCurrentProcess()) using (ProcessModule currentProcessModule = currentProcess.MainModule) { return SetWindowsHookEx(WH_KEYBOARD, keyboardProc, GetModuleHandle(currentProcessModule.ModuleName), 0); } } private static IntPtr HookCallback(int nCode, IntPtr wParam, IntPtr lParam) { if (nCode >= 0 && wParam == (IntPtr)WM_KEYDOWN) { int vkCode = Marshal.ReadInt32(lParam); if (KeyPressed != null) KeyPressed(null, new KeyPressedEventArgs((Keys)vkCode)); } return CallNextHookEx(hookID, nCode, wParam, lParam); } [DllImport("user32.dll", CharSet = CharSet.Auto, SetLastError = true)] private static extern IntPtr SetWindowsHookEx(int idHook, KeyboardProcess lpfn, IntPtr hMod, uint dwThreadId); [DllImport("user32.dll", CharSet = CharSet.Auto, SetLastError = true)] private static extern IntPtr CallNextHookEx(IntPtr hhk, int nCode, IntPtr wParam, IntPtr lParam); [DllImport("kernel32.dll", CharSet = CharSet.Auto, SetLastError = true)] private static extern IntPtr GetModuleHandle(string lpModuleName); [DllImport("user32.dll", CharSet = CharSet.Auto, SetLastError = true)] [return: MarshalAs(UnmanagedType.Bool)] private static extern bool UnhookWindowsHookEx(IntPtr hhk); } public class KeyPressedEventArgs : EventArgs { public Keys KeyCode { get; set; } public KeyPressedEventArgs(Keys Key) { KeyCode = Key; } } 

通过控制台应用实现:

 class Program { static void Main(string[] args) { KeyboardHook.CreateHook(); KeyboardHook.KeyPressed += KeyboardHook_KeyPressed; Application.Run(); KeyboardHook.DisposeHook(); } static void KeyboardHook_KeyPressed(object sender, KeyPressedEventArgs e) { Console.WriteLine(e.KeyCode.ToString()); } } 

您正在寻找的是全局键盘钩子。 您可以在MSDN上找到更多信息和示例。

哦,所以你在老式游戏术语中寻找“Autofire”?

而不是编写自己的键盘钩子应用程序(除非你是为了娱乐/它的快感/练习)你可能想要看看AutoIt或AutoHotkey,它们都非常适合键盘/鼠标自动化。

例如,请参阅此主题… http://www.autohotkey.com/board/topic/40598-autofire-keyboard/