C# 如何在不丢失透明度的情况下将图像转换为图标?
我有PNG图像,我需要转换成一个图标,然后再显示它 我就是这样做的:C# 如何在不丢失透明度的情况下将图像转换为图标?,c#,winforms,alpha-transparency,C#,Winforms,Alpha Transparency,我有PNG图像,我需要转换成一个图标,然后再显示它 我就是这样做的: public Icon ImageToIcon(Image imgTest) { Bitmap bitmap = new Bitmap(imgTest); Icon icoTest; IntPtr iPtr = bitmap.GetHicon(); icoTest = (Icon) Icon.FromHandle(iPtr).Clone(); return icoTest; } 执
public Icon ImageToIcon(Image imgTest)
{
Bitmap bitmap = new Bitmap(imgTest);
Icon icoTest;
IntPtr iPtr = bitmap.GetHicon();
icoTest = (Icon) Icon.FromHandle(iPtr).Clone();
return icoTest;
}
执行此操作后,我失去了透明度,alpha透明图像没有按预期渲染……这可以解决吗?不,还有很多问题。图标有一个非常复杂的内部结构,经过优化,可以在80年代的硬件上合理工作。图标图像有三个位图,一个用于图标,一个单色位图指示图像的哪些部分是透明的,另一个单色位图指示哪些部分是反转的。生成那些单色位图非常痛苦,.NET不支持它们。Bitmap.GetHicon()也没有对此进行尝试。你需要一个图书馆来为你做这项工作 Vista让人松了一口气,它开始支持包含PNG图像的图标。您将有机会使用自己的代码生成它。像这样:
public static Icon IconFromImage(Image img) {
var ms = new System.IO.MemoryStream();
var bw = new System.IO.BinaryWriter(ms);
// Header
bw.Write((short)0); // 0 : reserved
bw.Write((short)1); // 2 : 1=ico, 2=cur
bw.Write((short)1); // 4 : number of images
// Image directory
var w = img.Width;
if (w >= 256) w = 0;
bw.Write((byte)w); // 0 : width of image
var h = img.Height;
if (h >= 256) h = 0;
bw.Write((byte)h); // 1 : height of image
bw.Write((byte)0); // 2 : number of colors in palette
bw.Write((byte)0); // 3 : reserved
bw.Write((short)0); // 4 : number of color planes
bw.Write((short)0); // 6 : bits per pixel
var sizeHere = ms.Position;
bw.Write((int)0); // 8 : image size
var start = (int)ms.Position + 4;
bw.Write(start); // 12: offset of image data
// Image data
img.Save(ms, System.Drawing.Imaging.ImageFormat.Png);
var imageSize = (int)ms.Position - start;
ms.Seek(sizeHere, System.IO.SeekOrigin.Begin);
bw.Write(imageSize);
ms.Seek(0, System.IO.SeekOrigin.Begin);
// And load it
return new Icon(ms);
}
在.NET4.5和Windows8.1上测试。当心你在PNG图像上看到的边缘透明的“条纹”的可能性。只有当图像以众所周知的背景色显示时,该选项才能正常工作。从设计上来说,图标永远不能依赖于此。专用图标编辑器始终是获得好看图标的唯一真正好方法。我最近开发了一个开源软件,它有一个扩展方法。或创建多图像图标的方法。对于
光标
,将类型设置为2,并写入热点X和Y坐标,而不是颜色平面计数和BPP。