SendInput vs. keybd_event

MSDN states that keybd_event has been replaced by SendInput. During the dubbing, I switched to using SendInput ..., which was good except for trying to send the Alt key combination. On a Win7 64-bit system (not yet tried elsewhere) sending an Alt key causes a long delay until the keystroke is visible in the target application.

Any ideas why? Or what did I do wrong? At the moment, I'm back to keybd_event - the second version below.

//Keyboard input from this version appears only after a ~4-5 second //time lag... procedure SendAltM; var KeyInputs: array of TInput; KeyInputCount: Integer; //-------------------------------------------- procedure KeybdInput(VKey: Byte; Flags: DWORD); begin Inc(KeyInputCount); SetLength(KeyInputs, KeyInputCount); KeyInputs[KeyInputCount - 1].Itype := INPUT_KEYBOARD; with KeyInputs[KeyInputCount - 1].ki do begin wVk := VKey; wScan := MapVirtualKey(wVk, 0); dwFlags := KEYEVENTF_EXTENDEDKEY; dwFlags := Flags or dwFlags; time := 0; dwExtraInfo := 0; end; end; begin KeybdInput(VK_MENU, 0); // Alt KeybdInput(Ord('M'), 0); KeybdInput(Ord('M'), KEYEVENTF_KEYUP); KeybdInput(VK_MENU, KEYEVENTF_KEYUP); // Alt SendInput(KeyInputCount, KeyInputs[0], SizeOf(KeyInputs[0])); end; //Keyboard input from this version appears immediately... procedure SendAltM; begin keybd_event( VK_MENU, MapVirtualkey( VK_MENU, 0 ), 0, 0); keybd_event( Ord('M'), MapVirtualKey( Ord('M'),0), 0, 0); keybd_event( Ord('M'), MapVirtualKey( Ord('M'),0), KEYEVENTF_KEYUP, 0); keybd_event( VK_MENU, MapVirtualkey( VK_MENU, 0 ), KEYEVENTF_KEYUP, 0); end; 
+4
source share
2 answers

Problem 1

You have not initialized KeyInputCount . Therefore, its value is undefined. Before the first call to KeybdInput set it to zero. Or just get rid of it and use Length(KeyInputs) .

Problem 2

Incorrect dwFlags setting. Do not include KEYEVENTF_EXTENDEDKEY . You did not include it in the code that calls keybd_event , and you should not include it for SendInput .

Fixed code

This version works.

 procedure SendAltM; var KeyInputs: array of TInput; //-------------------------------------------- procedure KeybdInput(VKey: Byte; Flags: DWORD); begin SetLength(KeyInputs, Length(KeyInputs)+1); KeyInputs[high(KeyInputs)].Itype := INPUT_KEYBOARD; with KeyInputs[high(KeyInputs)].ki do begin wVk := VKey; wScan := MapVirtualKey(wVk, 0); dwFlags := Flags; end; end; begin KeybdInput(VK_MENU, 0); // Alt KeybdInput(Ord('M'), 0); KeybdInput(Ord('M'), KEYEVENTF_KEYUP); KeybdInput(VK_MENU, KEYEVENTF_KEYUP); // Alt SendInput(Length(KeyInputs), KeyInputs[0], SizeOf(KeyInputs[0])); end; 
+7
source

this way you can use keybd_event :

 keybd_event( VK_MENU, MapVirtualkey( VK_MENU, 0 ), KEYEVENTF_EXTENDEDKEY or 0, 0); keybd_event( Ord('M'), MapVirtualKey( Ord('M'),0), KEYEVENTF_EXTENDEDKEY or 0, 0); keybd_event( Ord('M'), MapVirtualKey( Ord('M'),0), KEYEVENTF_EXTENDEDKEY or KEYEVENTF_KEYUP, 0); keybd_event( VK_MENU, MapVirtualkey( VK_MENU, 0 ), KEYEVENTF_EXTENDEDKEY or KEYEVENTF_KEYUP, 0); 
+3
source

Source: https://habr.com/ru/post/1500976/


All Articles