У меня проблема с настраиваемыми курсорами в приложении WPF. Я использую следующий код для создания объектов Cursor
:
[DllImport("user32.dll")]
private static extern IntPtr CreateIconIndirect(ref IconInfo icon);
[DllImport("user32.dll")]
[return: MarshalAs(UnmanagedType.Bool)]
private static extern bool GetIconInfo(IntPtr hIcon, ref IconInfo pIconInfo);
private static Cursor CreateCursor(string cursorName, System.Drawing.Bitmap bmp,
int xHotspot, int yHotspot, out SafeFileHandle handle)
{
IconInfo tmp = new IconInfo();
GetIconInfo(bmp.GetHicon(), ref tmp);
tmp.xHotspot = xHotspot;
tmp.yHotspot = yHotspot;
tmp.fIcon = false;
IntPtr ptr = CreateIconIndirect(ref tmp);
handle = new SafeFileHandle(ptr, true);
if (handle.IsClosed)
{
return null;
}
Cursor cur = CursorInteropHelper.Create(handle);
return cur;
}
Когда я закрываю мое приложение и сборщик мусора начинают собирать мусор, выдает исключение:
System.Runtime.InteropServices.SEHException was unhandled
Message=External component has thrown an exception.
Source=mscorlib
ErrorCode=-2147467259
StackTrace:
at Microsoft.Win32.Win32Native.CloseHandle(IntPtr handle)
at Microsoft.Win32.SafeHandles.SafeFileHandle.ReleaseHandle()
at System.Runtime.InteropServices.SafeHandle.InternalDispose()
at System.Runtime.InteropServices.SafeHandle.Dispose(Boolean disposing)
at System.Runtime.InteropServices.SafeHandle.Dispose()
at System.Windows.Input.Cursor.Finalize()
InnerException:
Я провел дополнительное расследование, установив точку останова на if (handle.IsClosed)
и используя окно немедленного вызова для вызова handle.Close ()
. Некоторые из SafeFileHandle
закрываются нормально, другие выдают такое же исключение - сразу после создания дескриптора.
И, чтобы развлечься, дескрипторы сами работают нормально. IsInvalid
- ложь, IsClosed
- ложь, и появляются курсоры. Просто некоторые дескрипторы никогда не могут быть закрыты.
Поскольку я никогда не собираюсь этого делать. закройте ручки вручную, и они будут закрыты только во время завершения объектов Cursor
, когда приложение закрывается ses, я мог бы просто игнорировать их. Я не пробовал сборку Release за пределами VS2010, и я не знаю, приведет ли это к появлению диалогового окна сбоя. Но даже если я могу их игнорировать, это все равно грязно.
В общем, я ищу любую информацию о том, что здесь может быть не так, где искать, чтобы отладить это ...кажется, что все написано в собственном коде или в сборщике мусора, и я не могу ничего отладить.