c# - Icon.FromHandle : should I Dispose it, 或调用 DestroyIcon?

标签 c# .net winapi icons idisposable

我使用 Win32 SHGetFileInfo 获取属于某个文件的图标的句柄。有很多关于如何做到这一点的描述,也在 stackoverflow 上,例如:Get icons used by shell

调用该函数后,您将获得一个带有图标句柄的结构。使用静态方法 Icon.FromHandle 我可以将它转换为类 System.Drawing.Icon 的对象。此类实现 System.IDisposable。正确的用法是这样的:

using (Icon icon = Icon.FromHandle(shFileInfo.hIcon))
{
    // do what you need to do with the icon
}

在离开 using 语句后,图标对象被释放。

MSDN 在 Icon.FromHandle (click to view) 的描述中警告:

When using this method, you must dispose of the original icon by using the DestroyIcon method in the Win32 API to ensure that the resources are released.

并且在 Icon.Dispose (click to view)

Releases all resources used by this Icon.

问题:

Dispose() 对象是否足够,或者我应该同时调用 Dispose() 和 DestroyIcon,还是调用 DestroyIcon 而不是 Disposing 对象?

最佳答案

.NET Icon 类非常笨拙,需要您自己处理。 SHFILEICON 的 MSDN 文章对此毫不掩饰,您必须调用 DestroyIcon()。 Icon.FromHandle() 的 MSDN 文章也是如此。您调用 DestroyIcon 的确切时间也很重要,它必须延迟到一些代码已经复制了该图标,或者直到您不再需要该图标并且通常会调用它Dispose() 方法。

注意 MSDN 文章中的代码片段,它显示了提前调用 DestroyIcon() 的场景。好的,在特定 情况下,因为它已分配给 Form.Icon 属性。一个角落案例,肯定不是你想做的。

处理此问题的唯一真正合适的方法是重写 Icon.FromHandle() 的行为并强制对象获取 native 图标句柄的所有权。这样当你处理它时它会自动调用 DestroyIcon() 。这需要 hack,允许您执行此操作的 Icon 构造函数是内部。救援反射,您可以使用代码 from this post ,请注意 GetConstructor() 调用。通过编写一个执行此操作一百万次的小单元测试开始感觉良好。如果您不喜欢它,请编写您自己的 IDisposable 包装器,这样您就可以处理图标 pinvoke DestroyIcon()。

关于c# - Icon.FromHandle : should I Dispose it, 或调用 DestroyIcon?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/30979653/

相关文章:

c# - Identityserver 隐式流 unauthorized_client

c# - 使用表达式树生成排序列表

winapi - Windows 中的进程间共享内存是否一致?

c# - C# 中的谷歌分析 API

java - Azure 脱机同步来自 1 :n relationship in Android mobile app 的数据

.net - 如何抑制或忽略 SQL SELECT 语句中的错误

c++ - 集成 Windows 身份验证 Wininet

C++ Windows API - 如何检索字体缩放百分比

c# - 扩展用户主体; FindByIdentity() 失败

.net - 使用 WiX 中的在线设置安装 .NET Framework