2010-07-16 19 views
7

Cette "simple" question semble être lourde de problèmes secondaires.
par ex. Le nouveau processus ouvre-t-il plusieurs fenêtres? A-t-il un écran de démarrage?
Existe-t-il un moyen simple? (Je commence une nouvelle instance de Notepad ++)Comment obtenir hWnd de fenêtre ouverte par ShellExecuteEx .. hProcess?

... 
std::tstring tstrNotepad_exe = tstrProgramFiles + _T("\\Notepad++\\notepad++.exe"); 

SHELLEXECUTEINFO SEI={0}; 
sei.cbSize  = sizeof(SHELLEXECUTEINFO); 
sei.fMask  = SEE_MASK_NOCLOSEPROCESS; 
sei.hwnd   = hWndMe; // This app's window handle 
sei.lpVerb  = _T("open"); 
sei.lpFile  = tstrNotepad_exe.c_str();  
sei.lpParameters = _T(" -multiInst -noPlugins -nosession -notabbar "; 
sei.lpDirectory = NULL; 
sei.nShow  = SW_SHOW; 
sei.hInstApp  = NULL;  
if(ShellExecuteEx(&sei)) 
{ // I have sei.hProcess, but how best to utilize it from here? 
} 
... 

Répondre

12

Première utilisation WaitForInputIdle pour mettre en pause votre programme jusqu'à ce que l'application a commencé et est en attente d'entrée utilisateur (la fenêtre principale aurait dû être créé alors), puis utilisez EnumWindows et GetWindowThreadProcessId pour déterminer quelles fenêtres du système appartiennent au processus créé.

Par exemple:

struct ProcessWindowsInfo 
{ 
    DWORD ProcessID; 
    std::vector<HWND> Windows; 

    ProcessWindowsInfo(DWORD const AProcessID) 
     : ProcessID(AProcessID) 
    { 
    } 
}; 

BOOL __stdcall EnumProcessWindowsProc(HWND hwnd, LPARAM lParam) 
{ 
    ProcessWindowsInfo *Info = reinterpret_cast<ProcessWindowsInfo*>(lParam); 
    DWORD WindowProcessID; 

    GetWindowThreadProcessId(hwnd, &WindowProcessID); 

    if(WindowProcessID == Info->ProcessID) 
     Info->Windows.push_back(hwnd); 

    return true; 
} 

.... 

if(ShellExecuteEx(&sei)) 
{ 
    WaitForInputIdle(sei.hProcess, INFINITE); 

    ProcessWindowsInfo Info(GetProcessId(sei.hProcess)); 

    EnumWindows((WNDENUMPROC)EnumProcessWindowsProc, 
     reinterpret_cast<LPARAM>(&Info)); 

    // Use Info.Windows..... 
} 
+0

Merci Jon ... le chemin si court intervalle d'interrogation est d'aller ... qui a du sens :) –

+0

Je travaille dans votre exemple maintenant ... et PS à mon commentaire précédent: Je viens de remarquer dans MSDN: WaitForInputIdle peut être utilisé à tout moment, pas seulement au démarrage de l'application. Toutefois, WaitForInputIdle n'attend qu'une seule fois qu'un processus devienne inactif. les appels WaitForInputIdle suivants sont renvoyés immédiatement, que le processus soit inactif ou occupé. * Il semble que l'interrogation n'est pas une bonne idée ... Je vais faire quelques tests. –

+0

Vous devez uniquement utiliser WaitForInputIdle lorsque le processus est créé. À partir de là, interrogez simplement l'appel EnumWindows pour obtenir la liste des fenêtres mise à jour. –

Questions connexes