如何获取Windows资源管理器显示的文件类型图标?

时间:2008-09-20 12:11:31

标签: c# winforms

这里的第一个问题。我正在开发一个用C#(.NET 3.5)编写的程序,它在listview中显示文件。我想让“大图标”视图显示Windows资源管理器用于该文件类型的图标,否则我将不得不使用这样的现有代码:

        private int getFileTypeIconIndex(string fileName)
    {
        string fileLocation = Application.StartupPath + "\\Quarantine\\" + fileName;
        FileInfo fi = new FileInfo(fileLocation);
        switch (fi.Extension)
        {
            case ".pdf":
                return 1;
            case ".doc": case ".docx": case ".docm": case ".dotx":case ".dotm": case ".dot":case ".wpd": case ".wps":
                return 2;
            default:
                return 0;
        }

    }

上面的代码返回一个整数,用于从我填充了一些常用图标的图像列表中选择一个图标。它工作正常,但我需要在阳光下添加每个扩展!有没有更好的办法?谢谢!

4 个答案:

答案 0 :(得分:11)

您可能会发现使用Icon.ExtractAssociatedIcon比使用SHGetFileInfo更简单(一种托管)方法。但请注意:具有相同扩展名的两个文件可能具有不同的图标。

答案 1 :(得分:8)

文件图标保存在注册表中。这有点令人费解,但它有点像

  • 获取文件扩展名和查找 它的注册表项,用于 示例.DOC获取默认值 对于该注册表设置, “Word.Document.8”
  • 现在查找 注册表中的值。
  • 看看 “默认图标”的默认值 注册表项,在这种情况下, C:\的Windows \ {安装91120000-002E-0000-0000-0000000FF1CE} \ wordicon.exe,1
  • 打开文件并获取图标, 使用逗号后的任何数字作为 索引器。

CodeProject

上有一些示例代码

答案 2 :(得分:7)

我在最近的一个项目中使用了codeproject中的以下解决方案

Obtaining (and managing) file and folder icons using SHGetFileInfo in C#

演示项目非常自我解释,但基本上你只需要这样做:

private System.Windows.Forms.ListView FileView;

private ImageList _SmallImageList = new ImageList();
private ImageList _LargeImageList = new ImageList();
private IconListManager _IconListManager;

在构造函数中:

_SmallImageList.ColorDepth = ColorDepth.Depth32Bit;
_LargeImageList.ColorDepth = ColorDepth.Depth32Bit;

_SmallImageList.ImageSize = new System.Drawing.Size(16, 16);
_LargeImageList.ImageSize = new System.Drawing.Size(32, 32);

_IconListManager = new IconListManager(_SmallImageList, _LargeImageList);

FileView.SmallImageList = _SmallImageList;
FileView.LargeImageList = _LargeImageList;

然后在创建ListViewItem时最终:

ListViewItem item = new ListViewItem(file.Name, _IconListManager.AddFileIcon(file.FullName));

对我来说很棒。

答案 3 :(得分:4)

编辑:Here是没有PInvoke的版本。

[StructLayout(LayoutKind.Sequential)]
public struct SHFILEINFO
{
    public IntPtr hIcon;
    public IntPtr iIcon;
    public uint dwAttributes;
    [MarshalAs(UnmanagedType.ByValTStr, SizeConst = 260)]
    public string szDisplayName;
    [MarshalAs(UnmanagedType.ByValTStr, SizeConst = 80)]
    public string szTypeName;
};

public const uint SHGFI_ICON = 0x100;
public const uint SHGFI_LARGEICON = 0x0; // 'Large icon
public const uint SHGFI_SMALLICON = 0x1; // 'Small icon

[DllImport("shell32.dll")]
public static extern IntPtr SHGetFileInfo(string pszPath, uint dwFileAttributes, ref SHFILEINFO psfi, uint cbSizeFileInfo, uint uFlags);

[DllImport("User32.dll")]
public static extern int DestroyIcon(IntPtr hIcon);

public static System.Drawing.Icon GetSystemIcon(string sFilename)
{
    //Use this to get the small Icon
    IntPtr hImgSmall; //the handle to the system image list
    //IntPtr hImgLarge; //the handle to the system image list
    APIFuncs.SHFILEINFO shinfo = new APIFuncs.SHFILEINFO();
    hImgSmall = APIFuncs.SHGetFileInfo(sFilename, 0, ref shinfo,
        (uint)Marshal.SizeOf(shinfo), APIFuncs.SHGFI_ICON | APIFuncs.SHGFI_SMALLICON);

    //Use this to get the large Icon
    //hImgLarge = SHGetFileInfo(fName, 0, 
    //  ref shinfo, (uint)Marshal.SizeOf(shinfo), 
    //  Win32.SHGFI_ICON | Win32.SHGFI_LARGEICON);

    //The icon is returned in the hIcon member of the shinfo struct
    System.Drawing.Icon myIcon = (System.Drawing.Icon)System.Drawing.Icon.FromHandle(shinfo.hIcon).Clone();
    DestroyIcon(shinfo.hIcon); // Cleanup
    return myIcon;
}