2012-06-03 11 views
8

L'obiettivo è di avviare in modo programmatico un Windows Form, ottenere il relativo handle e inviare informazioni alla sua funzione wndProc() utilizzando la funzione SendMessage() di Win Api.Come si ottiene un handle della finestra principale di Process in C#?

Ho ricevuto la parte SendMessage(), ma il problema ora è ottenere l'handle del modulo dopo l'avvio del processo.

La mia prima ipotesi era che la proprietà MainWindowHandle di Process mi avrebbe ottenuto l'handle che sto cercando, ma dopo aver avviato il processo MainWindowHandle rimane uguale a 0 e il codice seguente non mostra l'handle del processo che ho appena avviato :

Qualcuno può dirmi come fare questo e se può effettivamente essere fatto?

+2

Provare a fare 'Thread.Sleep (3000);' dopo aver avviato il processo, verificare se il risultato è diverso. Inoltre, che processo stai iniziando? Ha persino una finestra? – SimpleVar

+0

sembra che mettere il filo addormentato abbia funzionato. grazie –

+0

@YoryeNathan puoi inserire il tuo commento come risposta? –

risposta

9

A volte il processo richiede un secondo per impostare tutto, ma l'oggetto viene restituito immediatamente.

Per questo motivo, è necessario attendere un po ', in modo da consentire al processo di avviarsi realmente, e quindi MainWindowHandle verrà impostato in modo appropriato, pronto per essere consumato.

var proc = Process.Start("notepad"); 

Thread.Sleep(1000); // This will wait 1 second 

var handle = proc.MainWindowHandle; 

Un altro modo per farlo in un modo più intelligente sarebbe:

var proc = Process.Start("notepad"); 

try 
{ 
    while (proc.MainWindowHandle == IntPtr.Zero) 
    { 
     // Discard cached information about the process 
     // because MainWindowHandle might be cached. 
     proc.Refresh(); 

     Thread.Sleep(10); 
    } 

    var handle = proc.MainWindowHandle; 
} 
catch 
{ 
    // The process has probably exited, 
    // so accessing MainWindowHandle threw an exception 
} 

che farà sì che il processo per iniziare, e attendere che il MainWindowHandle non è vuoto.

+0

effettivamente Yorye, penso che sarei negligente se non menzionassi quello basato sulle mie osservazioni, il tuo secondo approccio non funzionerà, perché, per qualche ragione, se accedi a MainWindowHandle prima che sia inizializzato, non lo fa ottenere inizializzato a tutti, il che significa che il tuo ciclo di tempo verrà eseguito per sempre. Perché è così? Non lo so, ma provalo se non mi credi. –

+3

@JohnSmith Hai ragione, le informazioni vengono memorizzate nella cache dell'oggetto. Chiamando il metodo 'Refresh' scarta le informazioni memorizzate nella cache, quindi la prossima volta che accedi alla proprietà' MainWindowHandle', la recupererà dalla finestra attuale, se necessario. Vedi l'aggiornamento del mio post. – SimpleVar

+0

A volte sto imparando cose nuove dalle mie stesse risposte 3 anni fa. – SimpleVar

Problemi correlati