我可以在Excel VBA中捕获并模仿关键事件吗?



Arun Singh对类似问题给出了很好的答案(在编辑单元格时按键时会发射任何事件?)。如果用户使用箭头键滚动。

,我想设置一个标志以防止执行selection_change事件。

实际上很容易。我正在将其用于 up down 箭头键。您可以在其中添加更多内容,例如右/左/tab/enter 等...我已经评论了可以添加键的部分。

将其粘贴到工作表代码区域

Option Explicit
Private Sub Worksheet_SelectionChange(ByVal Target As Range)
    If CancSelEvnt = False Then
        '
        '~~> Rest of the code for the Selection Change
        '
    Else
        '~~> Only for demostration purpose. Remove Msgbox later
        MsgBox "User pressed one of the navigation keys"
        CancSelEvnt = False
    End If
End Sub

将其粘贴到模块中

Option Explicit
'~~> We need this as this will help us in cancelling the
'~~> Selection chnage event
Public CancSelEvnt As Boolean
Private Type POINTAPI
    x As Long
    y As Long
End Type
Private Type MSG
    hwnd As Long
    Message As Long
    wParam As Long
    lParam As Long
    time As Long
    pt As POINTAPI
End Type
Private Declare Function WaitMessage Lib "user32" () As Long
Private Declare Function PeekMessage Lib "user32" Alias "PeekMessageA" _
    (ByRef lpMsg As MSG, ByVal hwnd As Long, _
     ByVal wMsgFilterMin As Long, _
     ByVal wMsgFilterMax As Long, _
     ByVal wRemoveMsg As Long) As Long
Private Declare Function TranslateMessage Lib "user32" _
    (ByRef lpMsg As MSG) As Long
Private Declare Function PostMessage Lib "user32" Alias "PostMessageA" _
    (ByVal hwnd As Long, _
     ByVal wMsg As Long, _
     ByVal wParam As Long, _
     lParam As Any) As Long
Private Declare Function FindWindow Lib "user32" Alias "FindWindowA" _
    (ByVal lpClassName As String, _
     ByVal lpWindowName As String) As Long
Private Const WM_KEYDOWN As Long = &H100
Private Const PM_REMOVE  As Long = &H1
Private Const WM_CHAR    As Long = &H102
Private bExitLoop As Boolean
Sub StartKeyWatch()
    Dim msgMessage As MSG
    Dim bCancel As Boolean
    Dim iKeyCode As Integer
    Dim lXLhwnd As Long
    On Error GoTo errHandler:
    Application.EnableCancelKey = xlErrorHandler
    bExitLoop = False
    lXLhwnd = FindWindow("XLMAIN", Application.Caption)
    Do
        WaitMessage
        If PeekMessage _
            (msgMessage, lXLhwnd, WM_KEYDOWN, WM_KEYDOWN, PM_REMOVE) Then
            iKeyCode = msgMessage.wParam
            TranslateMessage msgMessage
            PeekMessage msgMessage, lXLhwnd, WM_CHAR, _
            WM_CHAR, PM_REMOVE
            If iKeyCode = vbKeyBack Then SendKeys "{BS}"
            If iKeyCode = vbKeyReturn Then SendKeys "{ENTER}"
            bCancel = False
            '
            '~~> This is the main part where we check what key is pressed
            '
            If iKeyCode = vbKeyDown Then   '<~~ Down
                SendKeys "{DOWN}"
                CancSelEvnt = True
            ElseIf iKeyCode = vbKeyUp Then '<~~ UP
                SendKeys "{UP}"
                CancSelEvnt = True
            '
            '~~> And so on for the rest of the navigation keys
            '
            Else
                CancSelEvnt = False
            End If
            If bCancel = False Then
                PostMessage _
                lXLhwnd, msgMessage.Message, msgMessage.wParam, 0
            End If
        End If
errHandler:
        DoEvents
    Loop Until bExitLoop
End Sub
Sub StopKeyWatch()
    bExitLoop = True
End Sub

这是您可能需要的东西;)

vbkey代码列表

vbKeyLButton    Left Mouse Button
vbKeyRButton    Right Mouse Button
vnKeyCancel     Cancel Key
vbKeyMButton    Middle Mouse button
vbKeyBack       Back Space Key
vbKeyTab        Tab Key
vbKeyClear      Clear Key
vbKeyReturn     Enter Key
vbKeyShift      Shift Key
vbKeyControl    Ctrl Key
vbKeyMenu       Menu Key
vbKeyPause      Pause Key
vbKeyCapital    Caps Lock Key
vbKeyEscape     Escape Key
vbKeySpace      Spacebar Key
vbKeyPageUp     Page Up Key
vbKeyPageDown   Page Down Key
vbKeyEnd        End Key
vbKeyHome       Home Key
vbKeyLeft       Left Arrow Key
vbKeyUp         Up Arrow Key
vbKeyRight      Right Arrow Key
vbKeyDown       Down Arrow Key
vbKeySelect     Select Key
vbKeyPrint      Print Screen Key
vbKeyExecute    Execute Key
vbKeySnapshot   Snapshot Key
vbKeyInsert     Insert Key
vbKeyDelete     Delete Key
vbKeyHelp       Help Key
vbKeyNumlock    Delete Key
vbKeyA through vbKeyZ are the key code constants for the alphabet
vbKey0 through vbKey9 are the key code constants for numbers
vbKeyF1 through vbKeyF16 are the key code constants for the function keys
vbKeyNumpad0 through vbKeyNumpad9 are the key code constants for the numeric key pad
Math signs are:
vbKeyMultiply      -  Multiplication Sign (*)
vbKeyAdd             - Addition Sign (+)
vbKeySubtract     - Minus Sign (-)
vbKeyDecimal    - Decimal Point (.)
vbKeyDivide        - Division sign (/)
vbKeySeparator  - Enter (keypad) sign

当然,此密钥代码的MSDN链接。

我需要调整以上以与Worksheet_change和TAB键一起工作,因为基本上按下选项卡键,然后更改目标(在编辑A2并按下A2键并按下TAB键,更改事件显示小区B2)我想避免。

我将关键部分更改为:

        If iKeyCode = vbKeyTab Then   '<~~ Tab
            SendKeys "{TAB}"
            CancSelEvnt = True
        Else
            CancSelEvnt = False
        End If<code>

但是正在努力为此取得任何结果吗?

当我按下选项卡键时,我的更改事件根本不调用Sub StartKeyWatch()。也直接从Worksheet_change调用sub StartKeyWatch()似乎没有做任何事情...

我在这里缺少什么?

谢谢mkvarious

相关内容

  • 没有找到相关文章

最新更新