首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> 更多程式語言 >> 程式設計綜合問答

C++ SendInput 模擬按鍵失效:memset 初始化缺失導致 dwFlags 臨時值干擾

     編輯:程式設計綜合問答

SendInput 失效根因:未初始化的 INPUT 結構體攜帶垃圾標誌位

調用 SendInput 模擬 ESC 鍵時,若省略 memset 初始化,或改用非數組變量 INPUT iput 而未清零,會導致 ki.dwFlags 字段包含隨機垃圾值,從而觸發非預期行為(如被誤判為 KEYUP、SCANCODE 或 UNICODE 模式),導致按鍵模擬失效。

關鍵字段分析:KEYBDINPUT.dwFlags

標誌位常量含義若意外為 1 的後果
KEYEVENTF_KEYUP (0x0002)按鍵釋放系統認為是「鬆開 ESC」,而非按下
KEYEVENTF_SCANCODE (0x0008)使用掃描碼而非虛擬鍵碼wVk 被忽略,需填寫 wScan
KEYEVENTF_UNICODE (0x0004)發送 Unicode 字符wVk 被忽略,wScan 視為 Unicode 碼點

正確初始化模式

INPUT input = {0};           // C++11 聚合初始化全零(推薦)
// 或
INPUT input;
ZeroMemory(&input, sizeof(INPUT)); // 兼容舊標準
// 或
memset(&input, 0, sizeof(INPUT));  // C 風格

input.type = INPUT_KEYBOARD;
input.ki.wVk = VK_ESCAPE;   // 虛擬鍵碼
input.ki.dwFlags = 0;       // 明確設置為按下事件(可省略,因已清零)
SendInput(1, &input, sizeof(INPUT));

為什麼數組版本 INPUT iput[1] 配合 memset 就正常?

memset(iput, 0, sizeof(INPUT)) 將整個數組(即單個 INPUT)內存清零,確保 dwFlags=0,即標準「按下虛擬鍵」語義。去掉 memset 或改用未初始化的單變量,dwFlags 含隨機值,極大概率觸發上述非預期標誌位。

最佳實踐

  • **永遠**在填充前對 INPUT 結構體進行全零初始化(INPUT input = {0}; 最簡潔安全)。
  • 僅設置必要字段(type、ki.wVk),其餘依賴零值默認語義。
  • 發送「按下+釋放」完整點擊需構造兩個 INPUT,第二個設置 dwFlags = KEYEVENTF_KEYUP。
  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved