gpt4 book ai didi

c# - WPF C# 提取并显示默认文件图标

转载 作者:行者123 更新时间:2023-12-02 11:24:38 25 4
gpt4 key购买 nike

我正在为某些扩展(例如 XLS、XLSX、PDF 等)提取系统默认图标(仅限 16 * 16),并尝试在图像控制中显示该图标。我注意到,如果我将这些图标转储到磁盘上,它们看起来很清晰,但列表框中的图标看起来有些模糊。

你知道这里会发生什么吗?我从我读到的帖子中尝试了很多建议,但无法解决问题

代码片段:

案例1 - 我通过Win32 Pinvoke提取文件的图标 - 结果 -> 图标模糊

private const uint SHGFI_ICON = 0x100;
private const uint SHGFI_LARGEICON = 0x0;
private const uint SHGFI_SMALLICON = 0x1;
private const int FILE_ATTRIBUTE_NORMAL = 0x80;
private const uint SHGFI_USEFILEATTRIBUTES = 0x000000010;
[StructLayout(LayoutKind.Sequential)]
private 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;
};
[DllImport("shell32.dll")]
private static extern IntPtr SHGetFileInfo(string pszPath, uint dwFileAttributes,
ref SHFILEINFO psfi, uint cbSizeFileInfo, uint uFlags);

private static Icon Extract(string fileName)
{
var shinfo = new SHFILEINFO();

IntPtr hIcon = SHGetFileInfo(fileName, 0, ref shinfo, (uint)Marshal.SizeOf(shinfo), SHGFI_ICON | SHGFI_SMALLICON);
//The icon is returned in the hIcon member of the shinfo struct
var icon = (Icon)Icon.FromHandle(shinfo.hIcon).Clone();
DestroyIcon(shinfo.hIcon);
return icon;
}
[DllImport("User32.dll")]
public static extern int DestroyIcon(IntPtr hIcon);

案例2 - 将上面创建的图标对象转储到磁盘并在资源管理器中查看它们 -> 图标质量非常好

string filePath = string.Format("C:\\temp\\Icons\\{0}.ico", iconName.Substring(1));
var stream = new FileStream(filePath, FileMode.OpenOrCreate);
iconObject.ExtensionSource.ToBitmap().Save(stream, ImageFormat.Bmp);
stream.Close();

列表框 xaml -

<Grid>
<Grid.RowDefinitions>
<RowDefinition Height="Auto"/>
<RowDefinition Height="*"/>
</Grid.RowDefinitions>

<StackPanel Orientation="Horizontal"
Grid.Row="0"
Margin="10">
<TextBox Text="{Binding ExtensionNames, Mode=TwoWay}"
ToolTip="Comma Separated List of Extensions, Tab out to persist changes.."
Margin="5"/>
<Button Content="Dump All Icons"
Click="Button_DumpAllIconsClick"
Width="100"
ToolTip="Dump Path: C:\temp\Icons"
Margin="5"/>

</StackPanel>
<ListBox ItemsSource="{Binding Icons}"
Grid.Row="1"
Margin="2">
<ListBox.ItemTemplate>
<DataTemplate>
<StackPanel Orientation="Horizontal"
HorizontalAlignment="Stretch"
Margin="5">
<TextBlock Text="{Binding ExtensionName}"
FontWeight="Bold"
FontSize="20"/>
<Image Source="{Binding Path=ExtensionSource,
Converter={ExtractIconWPF:IconToImageSourceConverter}}"
Margin="5"/>
</StackPanel>
</DataTemplate>
</ListBox.ItemTemplate>
<ListBox.ItemContainerStyle>
<Style TargetType="ListBoxItem">
<Setter Property="HorizontalContentAlignment" Value="Stretch"/>
</Style>
</ListBox.ItemContainerStyle>
</ListBox>
</Grid>

我如何将 Icon 转换为 ImageSource 对象:

var stream = GetIconStream(iconObject);
ImageSource source = GetBitMapImage(stream);

public static Stream GetIconStream(Icon icon)
{
var iconStream = new MemoryStream();

var bitmap = icon.ToBitmap();
bitmap.Save(iconStream, ImageFormat.Png);

return iconStream;
}

public static ImageSource GetBitMapImage(Stream iconStream)
{
var bi = new BitmapImage();

bi.BeginInit();
bi.StreamSource = iconStream;
bi.EndInit();

return bi;
}

任何指点都将受到高度赞赏!

谢谢

最佳答案

我知道这个问题已经有一段时间得到解决了,但我看到了一个很酷的 win32 调用快捷方式:

var sysicon = System.Drawing.Icon.ExtractAssociatedIcon(filePath);
var bmpSrc = System.Windows.Interop.Imaging.CreateBitmapSourceFromHIcon(
sysicon.Handle,
System.Windows.Int32Rect.Empty,
System.Windows.Media.Imaging.BitmapSizeOptions.FromEmptyOptions());
sysicon.Dispose();

我认为这可能比你所做的一切更好。

来源:Here

关于c# - WPF C# 提取并显示默认文件图标,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/13428580/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com