介紹如何通過代碼實現類比按鍵的函數

來源:互聯網
上載者:User
作者: 陸島工作室

Windows API 的 keybd_event 函數,它可以產生鍵盤訊息。實現向其他視窗類比真實的按鍵動作。
例如:  {按下A鍵} 
  Edit1.SetFocus; 
  keybd_event(VK_SHIFT, 0, 0, 0); 
  keybd_event(ord('A'), 0, 0, 0); 
  keybd_event(VK_SHIFT, 0, KEYEVENTF_KEYUP, 0); 
  
  {按下左Window鍵然後選擇“運行”} 
  keybd_event(VK_LWIN, 0, 0, 0); 
  keybd_event(ord('R'), 0, 0, 0); 
  keybd_event(VK_LWIN, 0, KEYEVENTF_KEYUP, 0); 

KEYBD_EVENT 的函數說明:
函數功能:該函數合成一次擊鍵事件。系統可使用這種合成的擊鍵事件來產生WM_KEYUP或WM_KEYDOWN訊息,鍵盤驅動程式的中斷處理常式調用keybd_event函數。在Windows NT中該函數己被使用Sendlhput來替代它。

函數原型;VOID keybd_event(BYTE bVk,BYTE bScan,DWORD dwFlags,DWORD dwExtralnfo);

參數:

    bVk:定義一個虛據擬鍵碼。鍵碼值必須在1~254之間。

    bScan:定義該鍵的硬體掃描碼。

    dwFlags:定義函數操作的名個方面的一個標誌位集。應用程式可使用如下一些預定義常數的組合設定標誌位。

    KEYEVENTF_EXETENDEDKEY:若指定該值,則掃描碼前一個值為OXEO(224)的首碼位元組。DEYEVENTF_KEYUP:若指定該值,該鍵將被釋放;若未指定該值,該鍵交被接下。dwExtralnfo:定義與擊鍵相關的附加的32位值。

根據這個API函數,整理一個完整的函數,方便操作:

procedure PostKey(const mKey: Word; mShiftState: TShiftState; mCount: Integer = 1);  
const   
  cExtended: set of Byte = [VK_UP, VK_DOWN, VK_LEFT, VK_RIGHT, VK_HOME, VK_END, VK_PRIOR, VK_NEXT, VK_INSERT, VK_DELETE];   
    
  procedure pKeyboardEvent(mKey,   mScanCode:   Byte;   mFlags:   Longint);   
  var   
    vKeyboardMsg: TMsg;   
  begin   
    keybd_event(mKey, mScanCode, mFlags, 0);   
    while PeekMessage(vKeyboardMsg, 0, WM_KEYFIRST, WM_KEYLAST, PM_REMOVE) do 
    begin   
      TranslateMessage(vKeyboardMsg);   
      DispatchMessage(vKeyboardMsg);   
    end;   
  end;
    
  procedure pSendKeyDown(mKey: Word; mGenUpMsg: Boolean);   
  var   
    vScanCode: Byte;   
    vNumState: Boolean;   
    vKeyBoardState: TKeyboardState;   
  begin   
    if (mKey = VK_NUMLOCK) then
    begin   
      vNumState := ByteBool(GetKeyState(VK_NUMLOCK) and 1);   
      GetKeyBoardState(vKeyBoardState);   
      if vNumState then   
        vKeyBoardState[VK_NUMLOCK] := (vKeyBoardState[VK_NUMLOCK] and not 1)   
      else 
        vKeyBoardState[VK_NUMLOCK] := (vKeyBoardState[VK_NUMLOCK] or 1);   
        
      SetKeyBoardState(vKeyBoardState);   
      Exit;   
    end;   
  
    vScanCode := Lo(MapVirtualKey(mKey, 0));   
    if (mKey in cExtended) then 
    begin   
      pKeyboardEvent(mKey, vScanCode, KEYEVENTF_EXTENDEDKEY);   
      if mGenUpMsg then   
        pKeyboardEvent(mKey, vScanCode, KEYEVENTF_EXTENDEDKEY or KEYEVENTF_KEYUP)   
    end else
    begin   
      pKeyboardEvent(mKey, vScanCode, 0);   
      if mGenUpMsg then pKeyboardEvent(mKey, vScanCode, KEYEVENTF_KEYUP);   
    end;   
  end;   {   pSendKeyDown   }   
    
   procedure pSendKeyUp(mKey: Word);   
   var   
     vScanCode: Byte;   
   begin   
     vScanCode := Lo(MapVirtualKey(mKey, 0));   
     if mKey in cExtended then   
       pKeyboardEvent(mKey, vScanCode, KEYEVENTF_EXTENDEDKEY and KEYEVENTF_KEYUP)   
     else 
       pKeyboardEvent(mKey, vScanCode, KEYEVENTF_KEYUP);   
   end; 
    
var   
  I: Integer;   
begin   
  for I := 1 to mCount do
  begin   
    if ssShift in mShiftState then pSendKeyDown(VK_SHIFT, False);   
    if ssCtrl in mShiftState then pSendKeyDown(VK_CONTROL, False);   
    if ssAlt in mShiftState then pSendKeyDown(VK_MENU, False);   
    pSendKeyDown(mKey,   True);   
    if ssShift in mShiftState then pSendKeyUp(VK_SHIFT);   
    if ssCtrl in mShiftState then pSendKeyUp(VK_CONTROL);   
    if ssAlt in mShiftState then pSendKeyUp(VK_MENU);   
  end;   
end; 

另外一處函數也可以實作類別似功能。

Procedure PostKeyEx32( key: Word; Const shift: TShiftState; specialkey: Boolean ); 
Type 
  TShiftKeyInfo = Record 
    shift: Byte; 
    vkey : Byte; 
  End; 
  
  byteset = Set of 0..7; 
Const 
  shiftkeys: Array [1..3] of TShiftKeyInfo = 
    ((shift: Ord(ssCtrl); vkey: VK_CONTROL ), 
     (shift: Ord(ssShift); vkey: VK_SHIFT ), 
     (shift: Ord(ssAlt); vkey: VK_MENU )); 
Var 
  flag: DWORD; 
  bShift: ByteSet absolute shift; 
  i: Integer; 
Begin 
  for i := 1 to 3 Do 
  begin 
   if shiftkeys[i].shift in bShift Then 
     keybd_event( shiftkeys[i].vkey, MapVirtualKey(shiftkeys[i].vkey, 0), 0, 0); 
  end;  
  
  if specialkey then 
    flag := KEYEVENTF_EXTENDEDKEY 
  else 
    flag := 0; 
 
  keybd_event( key, MapvirtualKey( key, 0 ), flag, 0 ); 
  flag := flag or KEYEVENTF_KEYUP; 
  keybd_event( key, MapvirtualKey( key, 0 ), flag, 0 ); 
 
  for i := 3 downto 1 do 
  begin 
   If shiftkeys[i].shift In bShift Then 
   keybd_event( shiftkeys[i].vkey, MapVirtualKey(shiftkeys[i].vkey, 0), KEYEVENTF_KEYUP, 0); 
  end; { For } 
End; 

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.