VB6 雖無內建熱鍵元件,但可透過 Windows API GetAsyncKeyState 搭配 Timer 控制項輪詢鍵盤狀態,實現全域熱鍵(即使表單無焦點也能觸發)。本文提供極簡實作範例。
Private Declare Function GetAsyncKeyState Lib "User32" (ByVal Vkey As Long) As Integer
Private Function MyHotKey(vKeyCode) As Boolean
MyHotKey = GetAsyncKeyState(vKeyCode) < 0 ' 高位元為 1 表示鍵盤按下
End Function
Private Sub Form_Load()
Timer1.Interval = 50 ' 20 次/秒輪詢
Label1.Caption = "熱鍵是 F1"
End Sub
Private Sub Timer1_Timer()
If MyHotKey(vbKeyF1) Then
MsgBox "你按下了熱鍵!", , "熱鍵提示"
End If
End Sub
GetAsyncKeyState 回傳有號短整數:高位元 (bit 15) 為 1 表示鍵盤「當下」被按住;低位元 (bit 0) 為 1 表示「自上次呼叫後」曾被按下。判斷 < 0 即檢查高位元。vbKeyF1 為 VB 內建虛擬鍵碼常數(值 112),完整列表見 MSDN KeyCode Constants。Timer.Interval = 50 平衡回應速度與 CPU 佔用;若需更低延遲可改 10~20ms,但會增加系統負擔。輪詢法缺點:持續佔用 CPU、無法攔截按鍵(其他程式仍收到按鍵)。專業做法呼叫 RegisterHotKey / UnregisterHotKey 向系統註冊熱鍵,透過 WM_HOTKEY 訊息通知:
Private Declare Function RegisterHotKey Lib "User32" (ByVal hWnd As Long, ByVal id As Long, ByVal fsModifiers As Long, ByVal vk As Long) As Long
Private Declare Function UnregisterHotKey Lib "User32" (ByVal hWnd As Long, ByVal id As Long) As Long
Const MOD_ALT = &H1, MOD_CONTROL = &H2, MOD_SHIFT = &H4, MOD_WIN = &H8
Private Sub Form_Load()
RegisterHotKey Me.hWnd, 1, MOD_CONTROL + MOD_ALT, vbKeyF1 ' Ctrl+Alt+F1
End Sub
Private Sub Form_Unload(Cancel As Integer)
UnregisterHotKey Me.hWnd, 1
End Sub
Protected Overrides Sub WndProc(ByRef m As System.Windows.Forms.Message)
If m.Msg = &H312 Then ' WM_HOTKEY
If m.WParam.ToInt32() = 1 Then MsgBox "系統熱鍵觸發!"
End If
MyBase.WndProc(m)
End Sub
注意:VB6 需子類別化 才能攔截 WM_HOTKEY,或升級至 VB.NET 直接覆寫 WndProc。
| 方案 | 優點 | 缺點 |
|---|---|---|
| GetAsyncKeyState 輪詢 | 程式碼極簡、無需子類別化、相容 VB6 純 IDE | CPU 輪詢開銷、非即時、無法獨佔熱鍵 |
| RegisterHotKey 系統註冊 | 零 CPU 輪詢、系統級攔截、可組合修飾鍵 | 需子類別化/訊息迴路、VB6 實作複雜 |