public static BitmapSource GetFileIcon(string FileName, IImageListSize size, bool checkDisk) { var shinfo = new SHFILEINFO(); const uint SHGFI_USEFILEATTRIBUTES = 0x000000010; const uint SHGFI_SYSICONINDEX = 0x4000; const int FILE_ATTRIBUTE_NORMAL = 0x80; var flags = SHGFI_SYSICONINDEX; if (!checkDisk) // This does not seem to work. If I try it, a folder icon is always returned. { flags |= SHGFI_USEFILEATTRIBUTES; } var res = SHGetFileInfo(FileName, FILE_ATTRIBUTE_NORMAL, ref shinfo, Marshal.SizeOf(shinfo), flags); if (res == 0) { throw (new FileNotFoundException()); } var iconIndex = shinfo.iIcon; // Get the System IImageList object from the Shell: var iidImageList = new Guid("46EB5926-582E-4017-9FDF-E8998DAA0950"); IImageList iml; SHGetImageList(size, ref iidImageList, out iml); var hIcon = IntPtr.Zero; const int ILD_TRANSPARENT = 1; iml.GetIcon(iconIndex, ILD_TRANSPARENT, ref hIcon); var myIcon = Icon.FromHandle(hIcon); var bs = IconSource(myIcon); myIcon.Dispose(); bs.Freeze(); // very important to avoid memory leak DestroyIcon(hIcon); SendMessage(hIcon, WM_CLOSE, IntPtr.Zero, IntPtr.Zero); return(bs); }
private static extern int SHGetImageList( IImageListSize iImageList, ref Guid riid, out IImageList ppv );