Icon.FromHandle: should I Dispose it, or call DestroyIcon?

后端 未结 3 1269
执念已碎
执念已碎 2020-12-20 17:06

I use Win32 SHGetFileInfo to get a handle to the icon belonging to a certain file. There are a lot of descriptions how to do this, also on stackoverflow, for instance: Get i

3条回答
  •  既然无缘
    2020-12-20 17:52

    Addition by OP. There is an error in this answer. Because of all the comments it became harsh to see the forest through the trees. Hence I decided to edit this answer. (Sorry if I offended someone)

    The .net source code is online: http://referencesource.microsoft.com/#System.Drawing/commonui/System/Drawing/Icon.cs,81a28d20524554ae

    Take a look at Icon.FromHandle:

    public static Icon FromHandle(IntPtr handle)
    {
        IntSecurity.ObjectFromWin32Handle.Demand();
        return new Icon(handle);
    }
    internal Icon(IntPtr handle) : this(handle, false)
    {
    }
    internal Icon(IntPtr handle, bool takeOwnership)
    {
        if (handle == IntPtr.Zero)
        {
            throw new ArgumentException(SR.GetString(SR.InvalidGDIHandle,
                  (typeof(Icon)).Name));
        }
        this.handle = handle;
        this.ownHandle = takeOwnership;
    }
    

    Note that after Icon.FromHandle ownHandle is false.

    Let's look at Dispose:

    void Dispose(bool disposing)
    {
        if (handle != IntPtr.Zero)
        {
            DestroyHandle();
        }
    }
    
    internal void DestroyHandle()
    {
        if (ownHandle)
        {
            SafeNativeMethods.DestroyIcon(new HandleRef(this, handle));
            handle = IntPtr.Zero;
        }
    }
    

    Conclusion: After Icon.FromHandle, the field ownHandle is false, and thus Dispose / FromHandle won't call DestroyIcon

    Therefore: if you create an Icon using Icon.FromHandle you'll have to Dispose() the Icon as well as call DestroyIcon, just as the remarks section says

提交回复
热议问题