Итак, я решил свою проблему с помощью щедрого благотворителя по Discord.
Проблема заключалась в том, что я передавал Lamda
для ap / invoke в качестве делегата:
[DllImport("user32.dll")]
[return: MarshalAs(UnmanagedType.Bool)]
private static extern bool EnumChildWindows(IntPtr hwndParent, EnumWindowsProc lpEnumFunc, IntPtr lParam);
Таким образом, каждый раз, когда unmanaged
WinAPI
перезванивал моему делегату, у GC
была возможность запустить, если он это сделал, он собирал мою лямду, вызвавшую этот сбой.Это не обязательно должно происходить, поэтому мой метод работал большую часть времени и зависал непоследовательно.
Решением было добавить ссылку на лямду, которая помешала бы сборщику мусора (хотя я и пошел полностьюи сделал это локальной функцией, потому что ремень и скобки):
public static int GetMdiTitledChildWindows(IntPtr parentWindow)
{
IntPtr mdiClient = FindWindowEx(parentWindow, IntPtr.Zero, MdiClient, "");
List<IntPtr> handles = new List<IntPtr>();
bool addToList(IntPtr hwnd, IntPtr param)
{
handles.Add(hwnd);
return true;
}
EnumWindowsProc gcHolder = addToList;
EnumChildWindows(mdiClient, gcHolder, IntPtr.Zero);
int counter = 0;
foreach (IntPtr handle in handles)
{
int textLength = GetWindowTextLength(handle) + 1;
StringBuilder builder = new StringBuilder(textLength);
GetWindowText(handle, builder, textLength);
if (builder.Length > 0)
{
counter++;
}
}
return counter;
}
Приложение теперь работает как положено.