天天看點

C++ 周遊程序視窗标題、視窗類名

目的:周遊每個程序,一次查找程序下的視窗,找到視窗标題為 “” ,視窗類名為 “RunDll” 的視窗。如果找到傳回 true ,沒找到傳回 false。

上代碼,奏戰歌 ——

#pragma region 依賴

typedef struct EnumHWndsArg{
  std::vector<HWND> *vecHWnds;
  DWORD dwProcessId;
}EnumHWndsArg, *LPEnumHWndsArg;

// 判斷視窗是否屬于目标程序
BOOL CALLBACK lpEnumFunc(HWND hwnd, LPARAM lParam){
  EnumHWndsArg *pArg = (LPEnumHWndsArg)lParam;
  DWORD  processId;

  // 檢索視窗線程辨別符
  GetWindowThreadProcessId(
    hwnd,     // 視窗句柄
    &processId    // 接收 PID 的指針
    );

  // 如果這個 HWND 屬于這個 PID ,則加入到 vecHWnds 數組末尾
  if (processId == pArg->dwProcessId){pArg->vecHWnds->push_back(hwnd);}

  return TRUE;
}

// 根據 PID 擷取 HWND
void GetHWndsByProcessID(DWORD processID, std::vector<HWND> &vecHWnds){
  EnumHWndsArg wi;
  wi.dwProcessId = processID;
  wi.vecHWnds = &vecHWnds;

  // 枚舉所有頂級視窗
  EnumWindows(
    lpEnumFunc,   // 回調函數指針
    (LPARAM)&wi   // 傳遞給回調函數的值
    );
}

#pragma endregion

bool CSOL_dh()
{
  HANDLE hProcessSnap = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS,0);
  PROCESSENTRY32 process = {sizeof(PROCESSENTRY32)};
  
  // 周遊程序
  while (Process32Next(hProcessSnap,&process)){
    string processName = process.szExeFile;   // 程序名
    std::vector<HWND> vecHWnds;         // 程序下的窗體句柄數組
    GetHWndsByProcessID(process.th32ProcessID,vecHWnds);
    
    // 擷取 HWND 視窗标題、視窗類名
    TCHAR szBuf_title[MAX_PATH];
    TCHAR szBuf_class[MAX_PATH];
    for (const HWND &h : vecHWnds){
      GetWindowText(
      h,          // 視窗句柄
      szBuf_title,    // 接收視窗标題的緩沖區指針
      MAX_PATH      // 緩沖區位元組大小
      );
      GetClassName(
      h,          // 視窗句柄
      szBuf_class,    // 接收視窗類名的緩沖區指針
      MAX_PATH      // 緩沖區位元組大小
      );

      // 判斷是否有符合要求的窗體
      if(strcmp(szBuf_title,"") == 0 && strcmp(szBuf_class,"RunDLL") == 0){
        return true;
      }
      
      // 輸出結果 
      //cout << "szBuf_title = " << szBuf_title << endl;
      //cout << "szBuf_class = " << szBuf_class << endl;
      //cout << "--------------------------------------------" << endl;
    }

  }
  
  return false;
}