C# 关于图片转ICO的代码整理(无损,不需要第三方类库)

概述(Overview)

感觉网上文章整理的不全,我这边做个专栏,专门做这个事情吧,节省大家搜索、筛选、整理的时间精力。有用可以点个赞。引用本文章请注明出处,谢谢。

(I feel that the online articles are not complete, so I will make a column here to do this thing, so as to save everyone's time and energy in searching, screening, and sorting. If it's useful, you can like it.Please indicate the source for citing this article, thank you.)

代码(Code)

using System;
using System.Diagnostics;
using System.Drawing;
using System.Drawing.Imaging;
using System.IO;
using System.Windows.Forms;   

public class ICON
{
		/// <summary>
		/// 保存为ICO文件
		/// </summary>
		/// <param name="filePath">文件路径</param>
		/// <param name="width">宽度</param>
		/// <param name="height">高度</param>
		/// <returns>true:成功 false:失败</returns>
		public static bool SaveAsICON(string filePath, int width = 0, int height = 0)
		{
			try
			{
                //基于源文件路径,仅修改后缀名为ico
                string fileDirectory = Path.GetDirectoryName(filePath);
				string fileSavePath = Path.Combine(fileDirectory, Path.GetFileNameWithoutExtension(filePath)) + ".ico";

				using (Bitmap bm = new Bitmap(filePath))
				{
                    //尺寸范围:【1-255,1-255】
                    width = width == 0 ? bm.Width : width;
					width = width > 255 ? 255 : width;

					height = height == 0 ? bm.Height : height;
					height = height > 255 ? 255 : height;

					//转换结果
					bool isSuccess = ConvertImageToIcon(filePath, fileSavePath, new Size(width, height));
					if (!isSuccess)
					{
						return isSuccess;
					}
					//转换成功,打开文本保存所在目录
					Process.Start("explorer.exe", fileDirectory);
					return isSuccess;
				}
			}
			catch (Exception ex)
			{
				MessageBox.Show("转化失败。错误信息:" + ex.Message);
				return false;
			}
		}

		/// <summary>
		/// 图片转换为ico文件
		/// </summary>
		/// <param name="origin">原图片路径</param>
		/// <param name="destination">输出ico文件路径</param>
		/// <param name="iconSize">输出ico图标尺寸,不可大于255x255</param>
		/// <returns>是否转换成功</returns>
		private static bool ConvertImageToIcon(string origin, string destination, Size iconSize)
		{
            if (iconSize.Width > 255 || iconSize.Height > 255)
            {
                return false;
            }

			Bitmap originBMP = new Bitmap(origin);
            Image image = new Bitmap(originBMP, iconSize); //先读取已有的图片为bitmap,并缩放至设定大小
			MemoryStream bitMapStream = new MemoryStream(); //存原图的内存流
			MemoryStream iconStream = new MemoryStream(); //存图标的内存流
			image.Save(bitMapStream, ImageFormat.Png); //将原图读取为png格式并存入原图内存流,保证原图透明度、清晰度
			BinaryWriter iconWriter = new BinaryWriter(iconStream); 

			//下面是根据原图信息,进行文件头写入
			iconWriter.Write((short)0);//0-1保留
            iconWriter.Write((short)1);//2-3文件类型。1=图标, 2=光标
            iconWriter.Write((short)1);//4-5图像数量(图标可以包含多个图像)
            iconWriter.Write((byte)image.Width);//6图标宽度
            iconWriter.Write((byte)image.Height);//7图标高度
            iconWriter.Write((short)0);//8颜色数(若像素位深>=8,填0。这是显然的,达到8bpp的颜色数最少是256,byte不够表示) ;9保留。必须为0
            iconWriter.Write((short)0);//10-11调色板
            iconWriter.Write((short)32);//12-13位深
            iconWriter.Write((int)bitMapStream.Length);//14-17位图数据大小
            iconWriter.Write(22); //18 - 21位图数据起始字节

            //写入图像体至目标图标内存流
            iconWriter.Write(bitMapStream.ToArray());
			//保存流,并将流指针定位至头部以Icon对象进行读取输出为文件
			iconWriter.Flush();
			iconWriter.Seek(0, SeekOrigin.Begin);
			Stream iconFileStream = new FileStream(destination, FileMode.Create);
			Icon icon = new Icon(iconStream);
			icon.Save(iconFileStream); //储存图像

			 //下面开始释放资源
            iconFileStream.Close();
			iconWriter.Close();
			iconStream.Close();
			bitMapStream.Close();
            originBMP.Dispose();
            icon.Dispose();
			image.Dispose();
			iconFileStream.Dispose();

            return File.Exists(destination);
		}

}

引用

图标(ico,cur)文件的结构解析_ico文件格式解析-CSDN博客

【C#】无损转换Image为Icon - ahdung - 博客园 (cnblogs.com)

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值