Come enumerare tutte le windows appartenenti a un particolare processo utilizzando .NET?

Come posso trovare tutte le windows create da un particolare processo usando c #?

AGGIORNARE

ho bisogno di enumerare tutte le windows appartenenti a un particolare processo usando il PID (ID di processo) di un’applicazione.

Utilizzare l’ EnumWindows dell’API Win32 (se si desidera Windows figlio EnumChildWindows )) o in alternativa è ansible utilizzare EnumThreadWindows .

[DllImport("user32.dll", CharSet=CharSet.Auto, SetLastError=true)] public static extern bool EnumWindows(EnumThreadWindowsCallback callback, IntPtr extraData); 

Quindi verificare a quale processo appartiene ciascuna finestra utilizzando l’API Win32 GetWindowThreadProcessId

 [DllImport("user32.dll", CharSet=CharSet.Auto, SetLastError=true)] public static extern int GetWindowThreadProcessId(HandleRef handle, out int processId); 
 delegate bool EnumThreadDelegate(IntPtr hWnd, IntPtr lParam); [DllImport("user32.dll")] static extern bool EnumThreadWindows(int dwThreadId, EnumThreadDelegate lpfn, IntPtr lParam); static IEnumerable EnumerateProcessWindowHandles(int processId) { var handles = new List(); foreach (ProcessThread thread in Process.GetProcessById(processId).Threads) EnumThreadWindows(thread.Id, (hWnd, lParam) => { handles.Add(hWnd); return true; }, IntPtr.Zero); return handles; } 

e l’utilizzo del campione:

 private const uint WM_GETTEXT = 0x000D; [DllImport("user32.dll", CharSet = CharSet.Auto)] static extern IntPtr SendMessage(IntPtr hWnd, uint Msg, int wParam, StringBuilder lParam); [STAThread] static void Main(string[] args) { foreach (var handle in EnumerateProcessWindowHandles( Process.GetProcessesByName("explorer").First().Id)) { StringBuilder message = new StringBuilder(1000); SendMessage(handle, WM_GETTEXT, message.Capacity, message); Console.WriteLine(message); } } 

Filo antico, ma mi ha fatto iniziare così ecco una piccola funzione di utilità che troverà una finestra figlio che corrisponde a una lambda (Predicato). Essere facile da cambiare per restituire una lista. Più criteri sono gestiti nel predicato.

  public delegate bool Win32Callback(IntPtr hwnd, IntPtr lParam); [DllImport("user32.Dll")] [return: MarshalAs(UnmanagedType.Bool)] public static extern bool EnumChildWindows(IntPtr parentHandle, Win32Callback callback, IntPtr lParam); ///  /// Find a child window that matches a set of conditions specified as a Predicate that receives hWnd. Returns IntPtr.Zero /// if the target window not found. Typical search criteria would be some combination of window attributes such as /// ClassName, Title, etc., all of which can be obtained using API functions you will find on pinvoke.net ///  ///  /// Example: Find a window with specific title (use Regex.IsMatch for more sophisticated search) ///  Win32.GetWindowText(ptr) == "Dashboard");]]> ///  /// Handle to window at the start of the chain. Passing IntPtr.Zero gives you the top level /// window for the current process. To get windows for other processes, do something similar for the FindWindow /// API. /// Predicate that takes an hWnd as an IntPtr parameter, and returns True if the window matches. The /// first match is returned, and no further windows are scanned. ///  hWnd of the first found window, or IntPtr.Zero on failure  public static IntPtr FindWindow(IntPtr parentHandle, Predicate target) { var result = IntPtr.Zero; if (parentHandle == IntPtr.Zero) parentHandle = Process.GetCurrentProcess().MainWindowHandle; EnumChildWindows(parentHandle, (hwnd, param) => { if (target(hwnd)) { result = hwnd; return false; } return true; }, IntPtr.Zero); return result; } 

Esempio

 var foundHandle = Win32.FindWindow(IntPtr.Zero, ptr => Win32.GetWindowText(ptr) == "Dashboard"); 

Dopo un po ‘ho trovato un modo semplice e più breve:

Avrai bisogno di: ” using System.Diagnostics;

  [DllImport("kernel32.dll", SetLastError = true)] // Optional [return: MarshalAs(UnmanagedType.Bool)] // Optional private void button1_Click(object sender, EventArgs e) { AllocConsole(); // Easy to read // Optional Process[] processlist = Process.GetProcesses(); foreach (Process process in processlist) { if (!string.IsNullOrEmpty(process.MainWindowTitle)) { Console.WriteLine("Process: {0} ID: {1} Window title: {2}", process.ProcessName, process.Id, process.MainWindowTitle); } } }