91 lines
2.1 KiB
C#
91 lines
2.1 KiB
C#
using System;
|
|||
|
|
using System.Drawing;
|
||
|
|
using System.Drawing.Imaging;
|
||
|
|
using System.IO;
|
||
|
|
using System.Runtime.InteropServices;
|
||
|
|
|
||
|
|
namespace Crysome.Client.Util;
|
||
|
|
|
||
|
|
internal static class ShellSmallIconPng
|
||
|
|
{
|
||
|
|
private struct SHFILEINFO
|
||
|
|
{
|
||
|
|
public IntPtr hIcon;
|
||
|
|
|
||
|
|
public int iIcon;
|
||
|
|
|
||
|
|
public uint dwAttributes;
|
||
|
|
|
||
|
|
[MarshalAs(UnmanagedType.ByValTStr, SizeConst = 260)]
|
||
|
|
public string szDisplayName;
|
||
|
|
|
||
|
|
[MarshalAs(UnmanagedType.ByValTStr, SizeConst = 80)]
|
||
|
|
public string szTypeName;
|
||
|
|
}
|
||
|
|
|
||
|
|
private const uint SHGFI_ICON = 256u;
|
||
|
|
|
||
|
|
private const uint SHGFI_SMALLICON = 1u;
|
||
|
|
|
||
|
|
private const uint SHGFI_USEFILEATTRIBUTES = 16u;
|
||
|
|
|
||
|
|
private const uint FILE_ATTRIBUTE_DIRECTORY = 16u;
|
||
|
|
|
||
|
|
[DllImport("shell32.dll", CharSet = CharSet.Auto)]
|
||
|
|
private static extern IntPtr SHGetFileInfo(string pszPath, uint dwFileAttributes, ref SHFILEINFO psfi, uint cbFileInfo, uint uFlags);
|
||
|
|
|
||
|
|
[DllImport("user32.dll", CharSet = CharSet.Auto)]
|
||
|
|
private static extern bool DestroyIcon(IntPtr hIcon);
|
||
|
|
|
||
|
|
public static byte[] TryGetPng(string fullPath, bool isDirectory)
|
||
|
|
{
|
||
|
|
if (string.IsNullOrEmpty(fullPath))
|
||
|
|
{
|
||
|
|
return null;
|
||
|
|
}
|
||
|
|
try
|
||
|
|
{
|
||
|
|
if (!isDirectory && File.Exists(fullPath))
|
||
|
|
{
|
||
|
|
using (Icon icon = Icon.ExtractAssociatedIcon(fullPath))
|
||
|
|
{
|
||
|
|
if (icon == null)
|
||
|
|
{
|
||
|
|
return null;
|
||
|
|
}
|
||
|
|
return IconToPng(icon);
|
||
|
|
}
|
||
|
|
}
|
||
|
|
SHFILEINFO psfi = default(SHFILEINFO);
|
||
|
|
uint dwFileAttributes = (isDirectory ? 16u : 0u);
|
||
|
|
if (SHGetFileInfo(fullPath, dwFileAttributes, ref psfi, (uint)Marshal.SizeOf<SHFILEINFO>(), 273u) == IntPtr.Zero || psfi.hIcon == IntPtr.Zero)
|
||
|
|
{
|
||
|
|
return null;
|
||
|
|
}
|
||
|
|
IntPtr hIcon = psfi.hIcon;
|
||
|
|
try
|
||
|
|
{
|
||
|
|
using Icon icon2 = Icon.FromHandle(hIcon);
|
||
|
|
using Icon ico = (Icon)icon2.Clone();
|
||
|
|
return IconToPng(ico);
|
||
|
|
}
|
||
|
|
finally
|
||
|
|
{
|
||
|
|
DestroyIcon(hIcon);
|
||
|
|
}
|
||
|
|
}
|
||
|
|
catch
|
||
|
|
{
|
||
|
|
return null;
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
private static byte[] IconToPng(Icon ico)
|
||
|
|
{
|
||
|
|
using Bitmap bitmap = ico.ToBitmap();
|
||
|
|
using MemoryStream memoryStream = new MemoryStream();
|
||
|
|
bitmap.Save(memoryStream, ImageFormat.Png);
|
||
|
|
return memoryStream.ToArray();
|
||
|
|
}
|
||
|
|
}
|