『windows』WM_HOTKEY 热键

1. WM_HOTKEY

This message is posted when the user presses a hot key registered by the RegisterHotKey function. The message is placed at the top of the message queue associated with the thread that registered the hot key.

WM_HOTKEY idHotKey = (int) wParam; 
  fuModifiers = (UINT) LOWORD(lParam); 
  uVirtKey = (UINT) HIWORD(lParam);
Parameters
idHotKey
Hot key identifier that generated the message. If the message was generated by a system-defined hot key, the idHotKey parameter is one of the following values.
ValueDescription
IDHOT_SNAPDESKTOPThe snap desktop hot key was pressed.
IDHOT_SNAPWINDOWThe snap window hot key was pressed.
fuModifiers
Specifies the keys that were to be pressed in combination with the key specified by the nVirtKey parameter to generate the WM_HOTKEY message. The fuModifiers parameter can be a combination of the following values.
ValueDescription
MOD_ALTEither ALT key was held down.
MOD_CONTROLEither CTRL key was held down.
MOD_KEYUPBoth key up events and key down events generate a WM_HOTKEY message
MOD_SHIFTEither SHIFT key was held down.
MOD_WINEither WINDOWS key was held down. These keys are labeled with the Microsoft Windows logo.
uVirtKey
Specifies the virtual key code of the hot key. 
2. Keyboard Messages

Programming elementDescription
WM_ACTIVATEThis message is sent when a window is being activated or deactivated.
WM_CHARThis message is posted to the window with the keyboard focus when a WM_KEYDOWN message is translated by the TranslateMessage function.
WM_HOTKEYThis message is posted when the user presses a hot key registered by the RegisterHotKey function.
WM_INITMENUPOPUPThis message is sent when a pop-up menu is about to become active.
WM_KEYDOWNThis message is posted to the window with the keyboard focus when a nonsystem key is pressed.
WM_KEYUPThis message is posted to the window with the keyboard focus when a nonsystem key is released.
WM_KILLFOCUSThis message is sent to a window immediately before it loses the keyboard focus.
WM_MENUCHARThis message is sent when a menu is active and the user presses a key that does not correspond to any mnemonic or accelerator key.
WM_SETFOCUSThis message is sent to a window after it has gained the keyboard focus.
WM_SYSCHARThis message is posted to the window with the keyboard focus when a WM_SYSKEYDOWN message is translated by the TranslateMessage function.
WM_SYSCOMMANDThis message is sent to a window when the user chooses a command from the window menu, formerly known as the system or control menu, or when the user chooses the maximize button or the minimize button.
WM_SYSDEADCHARThis message is posted to the window with the keyboard focus when a WM_SYSKEYDOWN message is translated by the TranslateMessage function.
WM_SYSKEYDOWNThis message is posted to the window with the keyboard focus when the user holds down the ALT key and then presses another key.
WM_SYSKEYUPThis message is posted to the window with the keyboard focus when the user releases a key that was pressed while the ALT key was held down. 

3. RegisterHotKey

This function defines a system-wide hot key.

BOOL RegisterHotKey( 
  HWND hWnd, 
  int id, 
  UINT fsModifiers, 
  UINT vk 
);
Parameters
hWnd
[in] Handle to the window that will receive WM_HOTKEY messages generated by the hot key. The value of this parameter should not be NULL.
id
[in] Identifier of the hot key. No other hot key in the calling thread should have the same identifier. An application must specify a value in the range 0x0000 through 0xBFFF. A shared dynamic-link library (DLL) must specify a value in the range 0xC000 through 0xFFFF.
fsModifiers
[in] Specifies keys that must be pressed in combination with the key specified by the nVirtKey parameter in order to generate a WM_HOTKEY message. The fsModifiers parameter can be a combination of the following values.
ValueDescription
MOD_ALTEither ALT key must be held down.
MOD_CONTROLEither CTRL key must be held down.
MOD_KEYUPBoth key up events and key down events generate a WM_HOTKEY message.
MOD_SHIFTEither SHIFT key must be held down.
MOD_WINEither WINDOWS key was held down. These keys are labeled with the Microsoft Windows logo.
vk
[in] Specifies the virtual-key code of the hot key.
Return Values

Nonzero indicates success. Zero indicates failure. 

Remarks

When a key is pressed, the system looks for a match against all hot keys. Upon finding a match, the system posts the WM_HOTKEY message to the message queue of the thread that registered the hot key. This message is posted to the beginning of the queue so it is removed by the next iteration of the message loop.

RegisterHotKey can be used to register hot keys across threads.

RegisterHotKey fails if the keystrokes specified for the hot key have already been registered by another hot key.

If the window identified by the hWnd parameter already registered a hot key with the same identifier as that specified by the id parameter, the new values for the fsModifiers and vk parameters replace the previously specified values for these parameters. 


4. Virtual-Key Codes

Symbolic constantHexadecimal valueMouse or keyboard equivalent
VK_LBUTTON01Left mouse button
VK_RBUTTON02Right mouse button
VK_CANCEL03Control-break processing
VK_MBUTTON04Middle mouse button on a three-button mouse
 0507Undefined
VK_BACK08BACKSPACE key
VK_TAB09TAB key
 0A0BUndefined
VK_CLEAR0CCLEAR key
VK_RETURN0DENTER key
 0E0FUndefined
VK_SHIFT10SHIFT key
VK_CONTROL11CTRL key
VK_MENU12ALT key
VK_PAUSE13PAUSE key
VK_CAPITAL14CAPS LOCK key
 1519Reserved for Kanji systems
 1AUndefined
VK_ESCAPE1BESC key
 1C1FReserved for Kanji systems
VK_SPACE20SPACEBAR
VK_PRIOR21PAGE UP key
VK_NEXT22PAGE DOWN key
VK_END23END key
VK_HOME24HOME key
VK_LEFT25LEFT ARROW key
VK_UP26UP ARROW key
VK_RIGHT27RIGHT ARROW key
VK_DOWN28DOWN ARROW key
VK_SELECT29SELECT key
 2ASpecific to original equipment manufacturer
VK_EXECUTE2BEXECUTE key
VK_SNAPSHOT2CPRINT SCREEN key
VK_INSERT2DINS key
VK_DELETE2EDEL key
VK_HELP2FHELP key
 3A40Undefined
VK_LWIN5BLeft Windows key on a Microsoft Natural Keyboard
VK_RWIN5CRight Windows key on a Microsoft Natural Keyboard
VK_APPS5DApplications key on a Microsoft Natural Keyboard
 5E5FUndefined
VK_NUMPAD060Numeric keypad 0 key
VK_NUMPAD161Numeric keypad 1 key
VK_NUMPAD262Numeric keypad 2 key
VK_NUMPAD363Numeric keypad 3 key
VK_NUMPAD464Numeric keypad 4 key
VK_NUMPAD565Numeric keypad 5 key
VK_NUMPAD666Numeric keypad 6 key
VK_NUMPAD767Numeric keypad 7 key
VK_NUMPAD868Numeric keypad 8 key
VK_NUMPAD969Numeric keypad 9 key
VK_MULTIPLY6AMultiply key
VK_ADD6BAdd key
VK_SEPARATOR6CSeparator key
VK_SUBTRACT6DSubtract key
VK_DECIMAL6EDecimal key
VK_DIVIDE6FDivide key
VK_F170F1 key
VK_F271F2 key
VK_F372F3 key
VK_F473F4 key
VK_F574F5 key
VK_F675F6 key
VK_F776F7 key
VK_F877F8 key
VK_F978F9 key
VK_F1079F10 key
VK_F117AF11 key
VK_F127BF12 key
VK_F137CF13 key
VK_F147DF14 key
VK_F157EF15 key
VK_F167FF16 key
VK_F1780HF17 key
VK_F1881HF18 key
VK_F1982HF19 key
VK_F2083HF20 key
VK_F2184HF21 key
VK_F2285HF22 key

(PPC only) Key used to lock device.

VK_F2386HF23 key
VK_F2487HF24 key
 888FUnassigned
VK_NUMLOCK90NUM LOCK key
VK_SCROLL91SCROLL LOCK key
VK_LSHIFT0xA0Left SHIFT
VK_RSHIFT0xA1Right SHIFT
VK_LCONTROL0xA2Left CTRL
VK_RCONTROL0xA3Right CTRL
VK_LMENU0xA4Left ALT
VK_RMENU0xA5Right ALT
 BA-C0Specific to original equipment manufacturer; reserved. See following tables.
 C1-DAUnassigned
 DB-E2Specific to original equipment manufacturer; reserved. See following tables.
 E3 – E4Specific to original equipment manufacturer
 E5Unassigned
 E6Specific to original equipment manufacturer
VK_PACKETE7Used to pass Unicode characters as if they were keystrokes. If VK_PACKET is used with SendInput, then the Unicode character to be delivered should be placed into the lower 16 bits of the scan code. If a keyboard message is removed from the message queue and the virtual key is VK_PACKET, then the Unicode character will be the upper 16 bits of the lparam.
 E8Unassigned
 E9-F5Specific to original equipment manufacturer
VK_ATTNF6ATTN key
VK_CRSELF7CRSEL key
VK_EXSELF8EXSEL key
VK_EREOFF9Erase EOF key
VK_PLAYFAPLAY key
VK_ZOOMFBZOOM key
VK_NONAMEFCReserved for future use
VK_PA1FDPA1 key
VK_OEM_CLEARFECLEAR key
VK_KEYLOCKF22Key used to lock device

Original equipment manufacturers should make special note of the VK key ranges reserved for specific original equipment manufacturer use: 2A, DBE4, E6, and E9F5.

In addition to the VK key assignments in the previous table, Microsoft has assigned the following specific original equipment manufacturer VK keys.

Symbolic constantHexadecimal valueMouse or keyboard equivalent
VK_OEM_SCROLL0x91None
VK_OEM_10xBA";:" for US
VK_OEM_PLUS0xBB"+" any country/region
VK_OEM_COMMA0xBC"," any country/region
VK_OEM_MINUS0xBD"-" any country/region
VK_OEM_PERIOD0xBE"." any country/region
VK_OEM_20xBF"/?" for US
VK_OEM_30xC0"`~" for US
VK_OEM_40xDB"[{" for US
VK_OEM_50xDC"\|" for US
VK_OEM_60xDD"]}" for US
VK_OEM_70xDE"'"" for US
VK_OEM_80xDFNone
VK_OEM_AX0xE1AX key on Japanese AX keyboard
VK_OEM_1020xE2"<>" or "\|" on RT 102-key keyboard


5. 如何POST一个WM_HOTKEY消息?

首先从上面MSDN中关于WM_HOTKEY的内容可以看到,如何填入wParam、lParam参数.

转来一段)运用PostMessage(HWND_BROADCAST, WM_HOTKEY, 0, MAKELONG(MOD_ALT | MOD_CONTROL, VK_DELETE));来发送虚拟键盘,但是在winNT以后的系统里我们还有很多事情要做,比如:OpenDesktop()、OpenInputDesktop()、GetThreadDesktop()、SetThreadDesktop()、CloseDesktop()、GetUserObjectInformation()

代码如下:(直接PostMessage是没有起作用,下面这个做法,VK_DELETE换成其他键值也同样效果,为啥?)

#include "windows.h"
BOOL simulateAltControlDel();
void main()
{
    simulateAltControlDel();
}
BOOL simulateAltControlDel()
{
    HDESK   hdeskCurrent;
    HDESK   hdesk;
    HWINSTA hwinstaCurrent;
    HWINSTA hwinsta;
    // 
    // Save the current Window station
    // 
    hwinstaCurrent = GetProcessWindowStation();
    if (hwinstaCurrent == NULL)
        return FALSE;
    // 
    // Save the current desktop
    // 
    hdeskCurrent = GetThreadDesktop(GetCurrentThreadId());
    if (hdeskCurrent == NULL)
        return FALSE;
    // 
    // Obtain a handle to WinSta0 - service must be running
    // in the LocalSystem account
    // 
    hwinsta = OpenWindowStation("winsta0", FALSE,
                              WINSTA_ACCESSCLIPBOARD   |
                              WINSTA_ACCESSGLOBALATOMS |
                              WINSTA_CREATEDESKTOP     |
                              WINSTA_ENUMDESKTOPS      |
                              WINSTA_ENUMERATE         |
                              WINSTA_EXITWINDOWS       |
                              WINSTA_READATTRIBUTES    |
                              WINSTA_READSCREEN        |
                              WINSTA_WRITEATTRIBUTES);
    if (hwinsta == NULL)
        return FALSE;
    // 
    // Set the windowstation to be winsta0
    // 
    if (!SetProcessWindowStation(hwinsta))
     return FALSE;

    // 
    // Get the default desktop on winsta0
    // 
    hdesk = OpenDesktop("Winlogon", 0, FALSE,
                        DESKTOP_CREATEMENU |
              DESKTOP_CREATEWINDOW |
                        DESKTOP_ENUMERATE    |
                        DESKTOP_HOOKCONTROL  |
                        DESKTOP_JOURNALPLAYBACK |
                        DESKTOP_JOURNALRECORD |
                        DESKTOP_READOBJECTS |
                        DESKTOP_SWITCHDESKTOP |
                        DESKTOP_WRITEOBJECTS);
    if (hdesk == NULL)
       return FALSE;

    // 
    // Set the desktop to be "default"
    // 
    if (!SetThreadDesktop(hdesk))
       return FALSE;
    PostMessage(HWND_BROADCAST,WM_HOTKEY,0,MAKELPARAM(MOD_ALT|MOD_CONTROL,VK_DELETE));


    // 
    // Reset the Window station and desktop
    // 
    if (!SetProcessWindowStation(hwinstaCurrent))
       return FALSE;

    if (!SetThreadDesktop(hdeskCurrent))
    return FALSE;

    // 
    // Close the windowstation and desktop handles
    // 
    if (!CloseWindowStation(hwinsta))
        return FALSE;
    if (!CloseDesktop(hdesk))
        return FALSE;
    return TRUE;
}
偶一开始试验了发现不成功,后来冰河大哥告诉我说OpenDesktop("Winlogon", ......)本身需要LocalSystem权限,
果然如此,把它注册成服务,然后效果实现。相信如何注册成服务不用我说了吧。ok,我们想要的功能实现了。

他说的注册为服务应该是这个:Running CMD.EXE as Local System

原理清楚了,不过我还是到Google了搜了下,找到了两篇相关文章。
一篇就叫《利用服务创建SYSTEM权限CMD》,说不定就和这个小工具有关系。

另外一篇是一个国外的一个大牛在MSDN的Blog上的,就叫《Running CMD.EXE as Local System 》。

这个人说了一种直接用sc命令创建服务来运行SYSTEM权限的CMD的方法,测试了下,果然很好用。
我把它写成如下一个简单的批处理,同样可以得到SYSTEM权限的CMD:

sc Create SuperCMD binPath= "cmd /K start" type= own type= interact
sc start SuperCMD


  • 0
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
在VB.NET中注册多个热键,可以使用Windows API函数来实现。以下是一个示例代码,说明如何在VB.NET中注册多个热键: 首先,导入系统的用户界面库: Imports System.Runtime.InteropServices 然后,定义一些常量和API函数: Public Class Form1 ' 定义常量 Private Const MOD_CONTROL As Integer = &H2 Private Const WM_HOTKEY As Integer = &H312 ' 导入Windows API函数 <DllImport("user32.dll")> _ Private Shared Function RegisterHotKey(ByVal hWnd As IntPtr, ByVal id As Integer, ByVal fsModifiers As Integer, ByVal vk As Integer) As Boolean End Function <DllImport("user32.dll")> _ Private Shared Function UnregisterHotKey(ByVal hWnd As IntPtr, ByVal id As Integer) As Boolean End Function 接下来,在窗体加载事件中注册热键: Private Sub Form1_Load(sender As Object, e As EventArgs) Handles MyBase.Load ' 注册热键 RegisterHotKey(Me.Handle, 1, MOD_CONTROL, Keys.A) RegisterHotKey(Me.Handle, 2, MOD_CONTROL, Keys.B) End Sub 接着,在窗体消息处理事件中处理热键消息: Protected Overrides Sub WndProc(ByRef m As Message) If m.Msg = WM_HOTKEY Then Dim hotkeyId As Integer = m.WParam.ToInt32() Select Case hotkeyId Case 1 ' 处理热键1的逻辑 MessageBox.Show("热键1被触发") Case 2 ' 处理热键2的逻辑 MessageBox.Show("热键2被触发") End Select End If MyBase.WndProc(m) End Sub 最后,在窗体关闭事件中取消注册热键: Private Sub Form1_FormClosing(sender As Object, e As FormClosingEventArgs) Handles MyBase.FormClosing ' 取消注册热键 UnregisterHotKey(Me.Handle, 1) UnregisterHotKey(Me.Handle, 2) End Sub 以上代码演示了如何在VB.NET中注册多个热键,并在热键被触发时处理相应的逻辑。你可以根据需要修改和扩展这个示例代码。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值