如何以编程方式按键与键盘上按键完全相同?

时间:2014-11-03 11:13:26

标签: delphi vbscript

有没有人知道如何以编程方式按键与键盘上按键完全相同? PostMessage失败,SendInput失败,keybd_event失败,SendMessage失败,我甚至尝试使用Vcl.Touch.Keyboard模仿按键的不寻常方式。我甚至写了一个快速的vb脚本文件调用sendkeys也失败了。 我在一个名为Sellerdeck http://www.sellerdeck.com/

的程序中尝试这样做时遇到了麻烦

我已经尝试了以下所有内容,它们都与记事本配合使用但在此程序中失败。 通过

成功地将窗口带到了forground
procedure bringToForegroung;
Var
findhandle1 : cardinal;
begin
findhandle1 := FindWindow(NIL, 'Business Plus - Test site: Online Catalogue');
ShowWindow(findhandle1,SW_SHOW);
SetForegroundWindow(findhandle1);
end;

1

procedure SendF10;
Var
findhandle1 : cardinal;
begin
findhandle1 := FindWindow(NIL, 'Business Plus - Test site: Online Catalogue');
ShowWindow(findhandle1,SW_SHOW);
SetForegroundWindow(findhandle1);
PostMessage(findhandle1, WM_KEYDOWN, VK_F10, 0);
PostMessage(findhandle1, WM_KEYUP, VK_F10, 0);
end;

2

 procedure SendAltF;
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('F'), 0);
  KeybdInput(Ord('F'), KEYEVENTF_KEYUP);
  KeybdInput(VK_MENU, KEYEVENTF_KEYUP);   // Alt
  SendInput(Length(KeyInputs), KeyInputs[0], SizeOf(KeyInputs[0]));
end;

3

procedure SendKey2(Wnd,VK : Cardinal; Ctrl,Alt,Shift : Boolean);
var
  MC,MA,MS : Boolean;
begin
  // Try to bring target window to foreground
  ShowWindow(Wnd,SW_SHOW);
  SetForegroundWindow(Wnd);

  // Get current state of modifier keys
  MC:=Hi(GetAsyncKeyState(VK_CONTROL))>127;
  MA:=Hi(GetAsyncKeyState(VK_MENU))>127;
  MS:=Hi(GetAsyncKeyState(VK_SHIFT))>127;

  // Press modifier keys if necessary (unless already pressed by real user)
  if Ctrl<>MC then keybd_event(VK_CONTROL,0,Byte(MC)*KEYEVENTF_KEYUP,0);
  if Alt<>MA then keybd_event(VK_MENU,0,Byte(MA)*KEYEVENTF_KEYUP,0);
  if Shift<>MS then keybd_event(VK_SHIFT,0,Byte(MS)*KEYEVENTF_KEYUP,0);

  // Press key
  keybd_event(VK,0,0,0);
  keybd_event(VK,0,KEYEVENTF_KEYUP,0);

  // Release modifier keys if necessary
  if Ctrl<>MC then keybd_event(VK_CONTROL,0,Byte(Ctrl)*KEYEVENTF_KEYUP,0);
  if Alt<>MA then keybd_event(VK_MENU,0,Byte(Alt)*KEYEVENTF_KEYUP,0);
  if Shift<>MS then keybd_event(VK_SHIFT,0,Byte(Shift)*KEYEVENTF_KEYUP,0);
end;

4

procedure SendF10v2;
Var
findhandle1 : cardinal;
begin
findhandle1 := FindWindow(NIL, 'Business Plus - Test site: Online Catalogue');
ShowWindow(findhandle1,SW_SHOW);
SetForegroundWindow(findhandle1);
SendMessage(findhandle1, WM_KEYDOWN, VK_F10, 0);
SendMessage(findhandle1, WM_KEYUP, VK_F10, 0);
end;

5

uses
  Vcl.Touch.Keyboard, Vcl.Touch.KeyboardTypes;
type
    procedure FormCreate(Sender: TObject);
protected        {i.e. dont make form active}
    procedure CreateParams(var Params: TCreateParams); override; {i.e. dont make keyboard form active}


procedure TForm1.CreateParams(var Params: TCreateParams);
 begin
  inherited CreateParams(Params);
  with Params do
  begin
    ExStyle   := ExStyle or WS_EX_NOACTIVATE;
    WndParent := GetDesktopwindow;
  end;
end;

procedure TForm1.SpeedButton1Click(Sender: TObject);
var
  KeyData: TKeyData;
begin
KeyData := VKey(VK_F10, -1);
SendKey(KeyData, ksDown);
SendKey(KeyData, ksUp);
end;

6。 (VBS)

Option Explicit
Dim objShell
Set objShell = CreateObject("WScript.Shell")
objShell.Run """C:\Program Files (x86)\SellerDeck 2013\Catalog.exe"" /s ""Test site"" /n Administrator /w Administrator", 0, True
Wscript.Sleep 10000
objShell.SendKeys "%F"
Wscript.Sleep 1000
objShell.SendKeys "%F"
Wscript.Sleep 1000
objShell.SendKeys "%F"
Wscript.Sleep 1000
objShell.SendKeys "%F"
Wscript.Sleep 1000
objShell.SendKeys "%F"
Wscript.Sleep 1000
objShell.SendKeys "%F"
WScript.Quit 

正如我所说的那样,这些工作都在记事本中,否则我会认为这是我的PC问题。 我正在尝试自动执行此Sellerdeck程序的一些基本任务。无论如何要完全模仿按键吗?我希望只是因为我遗漏了一些非常基本的东西。

2 个答案:

答案 0 :(得分:1)

以下代码适用于我:

procedure TForm1.Button1Click(Sender: TObject);
begin
  keybd_event(VK_MENU, $b8, 0, 0);
  keybd_event(VK_F4, $8f, 0, 0);
  keybd_event(VK_F4, $8f, KEYEVENTF_KEYUP, 0);
  keybd_event(VK_MENU, $b8, KEYEVENTF_KEYUP, 0);
end;

所需功能如下:

  

void keybd_event(BYTE bVirtualKey ,BYTE bScanCode ,DWORD dwFlags ,   DWORD dwExtraInfo );

必须使用此语法:

  • bVirtualKey :密钥的虚拟密钥代码。例如,VK_RETURN,VK_TAB ......
  • bScanCode :扫描密钥的代码值。例如,“Left Alt”键的0xb8。
  • dwFlags :为密钥状态设置的标志。例如,KEYEVENTF_KEYUP。
  • dwExtraInfo :有关击键的32位额外信息。

以下链接详细总结了有关该功能的所有信息: http://www.codeproject.com/Articles/7305/Keyboard-Events-Simulation-using-keybd-event-funct

答案 1 :(得分:1)

我的猜测是你将命令发送到错误的Window句柄。也许FindWindow()返回的主应用程序窗口不是一个句柄键盘。

尝试使用调试工具,如WinSight(ws32.exe - 旧版本的Delphi中提供),猜测正确的句柄......