2011-08-10 19 views
10

Tengo un comportamiento extraño cuando se trata de usar el método de la API de Windows EnumChildWindows. Parece que no está recogiendo una sección de ventanas para niños. Cuando profundizo usando Spy ++ puedo ver a los niños, pero cuando ejecuto mi código, no devuelve los que veo en Spy ++.¿Por qué EnumChildWindows omite niños?

Lo que veo en Spy ++ What I see in Spy++ http://img24.imageshack.us/img24/9264/spyhandles.png

Aquí está mi código:

public delegate bool EnumWindowProc(IntPtr hWnd, IntPtr parameter); 

    [DllImport("user32")] 
    [return: MarshalAs(UnmanagedType.Bool)] 
    public static extern bool EnumChildWindows(IntPtr window, EnumWindowProc callback, IntPtr i); 

    public static List<IntPtr> GetChildWindows(IntPtr parent) 
    { 
     List<IntPtr> result = new List<IntPtr>(); 
     GCHandle listHandle = GCHandle.Alloc(result); 
     try 
     { 
      EnumWindowProc childProc = new EnumWindowProc(EnumWindow); 
      EnumChildWindows(parent, childProc, GCHandle.ToIntPtr(listHandle)); 
     } 
     finally 
     { 
      if (listHandle.IsAllocated) 
       listHandle.Free(); 
     } 
     return result; 
    } 

    private static bool EnumWindow(IntPtr handle, IntPtr pointer) 
    { 
     GCHandle gch = GCHandle.FromIntPtr(pointer); 
     List<IntPtr> list = gch.Target as List<IntPtr>; 
     if (list == null) 
      throw new InvalidCastException("GCHandle Target could not be cast as List<IntPtr>"); 

     list.Add(handle);    
     return true; 
    } 

¿Hay una razón de por qué la sección roja resaltado en la pantalla de arriba no conseguiría poblada en mi colección (List<IntPtr>) al llamar a EnumChildWindows?

+0

Implementé este código en mi función FindWindowsByClassAndTitle() y encuentra las ventanas aproximadamente 30 millones de veces más rápido que el código que estaba usando previamente. – Anders

Respuesta

8

Doh! Descubrí los errores de mis formas. La razón por la que solo conseguía la mitad de los hijos era porque no esperaba el tiempo suficiente para que la ventana cargase inicialmente y creara TODOS los niños dentro de ella, por lo tanto solo obtenía la primera mitad que creaba en el vez que llamé a mi función para obtener todas las ventanas secundarias. Así que agregué una línea de código para dormir antes de llamar a EnumChildWindows().

"Windows no llama a la función de devolución de llamada para las ventanas secundarias creadas después de llamar a EnumChildWindows, pero antes de que regrese." - Source

La información citada es la que enciende la bombilla en mi cabeza.

Cuestiones relacionadas