SendKeys возится с моим ключом NumLock через код VBA в форме доступа

У меня есть следующий код для формы доступа. Кажется, что SendKeys возится с моим ключом NumLock, переключая его, когда я открываю и закрываю форму.

По вполне обоснованным причинам, которые я не хочу вдаваться, я действительно не хочу полностью скрывать ленту (я хочу, чтобы выпадающие меню все еще были доступны), поэтому команда DoCmd.ShowToolbar не является моим предпочтительным способом делать Это.

Есть ли у кого-нибудь какие-либо предложения относительно того, как я могу изменить код ниже, чтобы выполнить то, что я хочу, используя команду SendKeys?

Используя Access 2007, команда

CommandBars.ExecuteMso "MinimizeRibbon"

недоступен для меня.

Кстати, база данных будет распространена, поэтому решение должно содержаться в базе данных.

Private Sub Form_Close()

' Unhide navigation pane
    DoCmd.NavigateTo "acNavigationCategoryObjectType"
    DoCmd.Maximize

' Maximize the ribbon
RibbonState = (CommandBars("Ribbon").Controls(1).Height < 75)

Select Case RibbonState
    Case True
        SendKeys "^{F1}", True
    Case False
        'Do nothing, already maximized
End Select
End Sub

Private Sub Form_Load()
' Hide navigation pane
    DoCmd.NavigateTo "acNavigationCategoryObjectType"
    DoCmd.Minimize
Debug.Print Application.CommandBars.Item("Ribbon").Height
' Minimize ribbon
RibbonState = (CommandBars("Ribbon").Controls(1).Height < 100)

Select Case RibbonState
    Case True
        'Do nothing, already minimized
    Case False
            SendKeys "^{F1}", False
End Select
End Sub

Ответ 1

Это ошибка в Microsoft VBA. Но есть обходное решение.

Используйте F8 для запуска макроса и найдите, где он отключается. Это обычно после SendKeys.

Затем добавьте    Sendkeys "{NUMLOCK}", True после строки, чтобы отменить эффект.

Если вы не можете найти его, просто добавьте его в конце и, когда он закончится, он вернется. Надеюсь, если вы добавите его во время процесса show/hide, он будет работать.

Ответ 2

У меня была аналогичная проблема, и я нашел решение на каком-то форуме vba. Вместо перехваченных Sendkeys вы можете имитировать kyes, как это.

    Option Explicit
'//WIN32API Declare
Private Declare Sub keybd_event Lib "user32" (ByVal bVk As Byte, ByVal bScan As Byte, ByVal dwFlags As Long, ByVal dwExtraInfo As Long)

'//WIN32API Constant

Public Const KEYEVENTF_EXTENDEDKEY = &H1
Public Const KEYEVENTF_KEYUP = &H2
Public Const VK_CONTROL = &H11
Public Const VK_SHIFT = &H10
Public Const VK_F6 = &H75

Public Function PreviousTab()
    keybd_event VK_CONTROL, 0, 0, 0
    keybd_event VK_SHIFT, 0, 0, 0
    keybd_event VK_F6, 0, 0, 0
    keybd_event VK_F6, 0, KEYEVENTF_KEYUP, 0
    keybd_event VK_SHIFT, 0, KEYEVENTF_KEYUP, 0
    keybd_event VK_CONTROL, 0, KEYEVENTF_KEYUP, 0
End Function

Другие ключи можно найти здесь форум vba Эта функция "previousTab" просто отправляет клавишу Control + Shift + F6.

Ответ 3

Эта строка вызвала мою проблему:

Application.SendKeys "%s"

SOLVED, изменив на это:

Application.SendKeys "{NUMLOCK}%s"

Нет никакой разницы между добавлением {NUMLOCK} в начале или в конце строки.

Ответ 4

Это вызвано:

Sendkeys "any key", False

Вместо False в качестве второго параметра используйте True.

Ответ 5

Сразу после вашего оператора SendKeys добавьте эти две строки:

DoEvents
SendKeys "{NUMLOCK}{NUMLOCK}"

Ответ 6

Когда вы выполняете окончательную команду sendKeys в своем коде, добавление в {NUMLOCK} к заявлению может сделать трюк, как отмечают RodB и iceBird76. Но это не хорошая практика кодирования, и вот почему: если что-то отличается от одного момента времени, когда вы запускаете макрос, он может работать или не работать. Я знаю это, потому что сам испытываю подобную проблему. Когда я буду делать команду sendKeys в конце моей программы, иногда Num Lock будет продолжать работать, но в других случаях она будет оставаться без изменений, только в зависимости от определенных переменных в моей таблице (независимо от того, включен ли я /NUMLOCK в мой последний оператор SendKeys).
Я не буду вдаваться в подробности моих собственных переменных, но дело в том, что для создания программы/макроса, который будет постоянно поддерживать ваш Num Lock, вам нужно ПЕРВЫЙ ТЕСТ, ЧТОБЫ УВИДЕТЬ, ЕСЛИ НУМНЫЙ БЛОК ВКЛЮЧЕН ИЛИ ВЫКЛ, тогда выполнить код, основанный на текущем состоянии.

Private Declare Function GetKeyState Lib "user32" (ByVal nVirtKey As Long) As Integer
Private Const kNumlock = 144

Public Function NumLock() As Boolean
    NumLock = KeyState(kNumlock)
    If (NumLock = True) Then
        MsgBox ("Num lock was off. Will turn back on now...")
        SendKeys "{NUMLOCK}", True
    Else: MsgBox ("Num Lock stayed on")
    End If
End Function

Private Function KeyState(lKey As Long) As Boolean
    KeyState = CBool(GetKeyState(lKey))
End Function


Sub myMainMethod()
    'do a function here that includes .SendKeys
    Call NumLock
End Sub

Эта примерная программа даст вам сообщение с подтверждением о включении или выключении Num Lock и включении его, если оно выключено.

Ответ 7

Функция SendKeys(), встроенная в VBA, действительно имеет побочный эффект, который приводит к деактивации NumLock. Но вы можете использовать обходной путь и вызвать другую реализацию той же функции, которая является частью компонента WSCRIPT (часть операционной системы Windows). В следующем примере кода показано, как можно создать ссылку на этот компонент, а затем вызвать его метод:

Set WshShell = CreateObject("WScript.Shell")
WshShell.SendKeys "^g", True

Таким образом, вы получаете ту же функциональность (в этом случае вызываете комбинацию клавиш Ctrl-G), но в этом случае с NumLock проблем нет.

Ответ 8

SendKeys "^{HOME}", True отключил блокировку num, поэтому я просто повторил команду и снова включил ее:

SendKeys "^{HOME}", True
SendKeys "^{HOME}", True

Ответ 9

Попробовав много решений. Наиболее солидный, кажется, по ссылке ниже. Вставьте его в модуль.

http://access.mvps.org/access/api/api0046.htm