6.2 GIF

GIF的全称是图像交换格式Graphics Interchange Format,是CompuServe公司在1987年创建并使用的。这种格式使用8位索引值来表达一个像素,也就是说1个像素1个byte,最多可以表示256种颜色。它使用LZW无损压缩算法来对图像进行压缩,之后这家公司又和几家其他的公司发明了PNG文件格式,并被更广泛地应用在Web以及其他领域。GIF支持动画,可以保存数个帧并不断地播放。关于动画的部分我们将会放到非常后面来讲,现在只谈谈GIF的透明。

在GIF文件的头部有一个调色板Palette,里面保存了颜色的信息。一般而言,如果对GIF进行LockBits的操作,只能把它lock成Format*bppIndexed,这样才不会导致前面调色板信息的丢失,在处理上也更方便一些。在调色板里面定义了透明的颜色,也就是说当实际数据为这个颜色时,那个位置的颜色为透明。让我们来看看Palette是怎么使用的。 顺便再说一句,GIF没有半透明,只支持完全透明或者不透明。此外,在一个调色板中,只有一种颜色可以设置为透明,这是GIF标准所决定的。

 1         public static unsafe void ConvertTransparancyGif(int colorIndex, string baseFile, string outputFile)
 2         {
 3             using (FileStream fs = new FileStream(baseFile, FileMode.Open, FileAccess.Read))
 4             {
 5                 Bitmap img = (Bitmap)Image.FromStream(fs, false, false);
 6                 int width = img.Width;
 7                 int height = img.Height;
 8 
 9                 Bitmap resultbmp = new Bitmap(width, height, PixelFormat.Format8bppIndexed);
10                 ColorPalette palette = resultbmp.Palette;
11                 int n = 0;
12                 foreach (Color tc in img.Palette.Entries)
13                 {
14                     palette.Entries[n] = Color.FromArgb(255, tc);
15                     n++;
16                 }
17 
18                 palette.Entries[colorIndex] = Color.FromArgb(0, palette.Entries[colorIndex]);
19                 resultbmp.Palette = palette;
20 
21                 //now to copy the actual bitmap data 
22                 BitmapData src = img.LockBits(
23                     new Rectangle(0, 0, width, height),
24                     ImageLockMode.ReadOnly,
25                     img.PixelFormat);
26 
27                 BitmapData dst = resultbmp.LockBits(
28                     new Rectangle(0, 0, width, height),
29                     ImageLockMode.WriteOnly,
30                     resultbmp.PixelFormat);
31 
32                 byte* pSrc = (byte*)src.Scan0.ToPointer();
33                 byte* pDst = (byte*)dst.Scan0.ToPointer();
34                 int offset = src.Stride - width;
35 
36                 //steps through each pixel 
37                 for (int y = 0; y < height; y++)
38                 {
39                     for (int x = 0; x < width; x++)
40                     {
41                         pDst[0] = pSrc[0];
42                         pDst++;
43                         pSrc++;
44                     }
45                     pDst += offset;
46                     pSrc += offset;
47                 }
48 
49                 //unlock the bitmaps 
50                 img.UnlockBits(src);
51                 resultbmp.UnlockBits(dst);
52 
53                 resultbmp.Save(outputFile, ImageFormat.Gif);
54 
55                 img.Dispose();
56                 resultbmp.Dispose();
57             } 
59         }

请注意,在这里,我读图的时候和我之前推荐的方法不同。 我没有创建一个新的Bitmap,这是因为在创建新的Bitmap的时候,调色板信息会完全丢失,所以Indexed的格式不可以随意进行复制,否则将造成信息的丢失。这也就是为什么当时我说这是一个土办法的原因。真正的好办法是复制那个流,而不是直接去复制Bitmap。不过那是看需求的。在创建一个带透明颜色的GIF的时候,只要创建一个调色板,就一切OK了。这比Alpha通道修正要简单。还可以参考KB 319061 http://support.microsoft.com/kb/319061/en-us

最后提一句,Bitmap类还提供了一个MakeTransparent方法用于设置透明颜色,不过只对PNG有效。

GDI+中常见的几个问题(6)相关推荐

  1. 使用×××版软件中常见的一些错误代码

    1.错误代码(691):由于域上的用户名或密码无效而拒绝访问. 如果是使用的易游提供的×××服务器,请在帐务系统确认使用的帐号是否状态正常,刚设置好的帐号需要等5分钟才能使用.如果是外部×××服务器请 ...

  2. Python 中常见的配置文件写法

    相信学习Python或者正在进行Python工作的小伙伴都会有一个疑问,为什么要写配置文件呢?在开发过程中,我们常常会用到一些固定参数或者是常量.对于这些较为固定且常用到的部分,往往会将其写到一个固定 ...

  3. 操作系统中进程并发运行的过程_三种电磁流量计运行过程中常见故障解决详情!...

    原标题:三种电磁流量计运行过程中常见故障解决详情! 昨天给大家介绍了电磁流量计的一些典型故障,今天我们继续来谈电磁流量计的故障问题!电磁流量计在正常的保养与维护之后,在正常使用的过程中依旧是会因为当时 ...

  4. php中常见的错误类型有,JavaScript中常见的错误类型有哪些?(详细介绍)

    在JavaScript中,当发生错误时会生成描述错误类型的错误对象,此错误对象包含错误类型和编号等信息,这些信息可用于后续处理等,在本篇文章中将给大家介绍常见的错误类型以及如何处理这些错误. Java ...

  5. GDI+ 中发生一般性错误(生成验证码时出现的错误)

    我在生成验证码时,出现这样的错误:GDI+ 中发生一般性错误. 怎么解决? 转载于:https://www.cnblogs.com/happyangle/archive/2008/06/11/1217 ...

  6. iOS开发OC基础:Xcode中常见英文总结,OC常见英文错误

    在开发的过程中难免会遇到很多的错误,可是当看到系统给出的英文时,又不知道是什么意思.所以这篇文章总结了Xcode中常见的一些英文单词及词组,可以帮助初学的人快速了解给出的提示.多练习,就肯定能基本掌握 ...

  7. GDI+中发生一般性错误

    在PictureBox中有一副图,希望保存成图片,用 pictureBox1.Image("c:\\aa.jpg",System.Drawing.Imaging.ImageForm ...

  8. Java中常见的异常

    作为一名游戏开发者,程序员,很自然必须熟悉对程序的调试方法.而要调试程序,自然需要对程序中的常见的异常有一定的了解,这些日子很多朋友都提出了很多问题,都是关于游戏中的报错,因此在这里我将一些常见的程序 ...

  9. PHP开发中常见的安全问题详解和解决方法

    PHP开发中常见的安全问题详解和解决方法 参考文章: (1)PHP开发中常见的安全问题详解和解决方法 (2)https://www.cnblogs.com/walblog/articles/83313 ...

最新文章

  1. R语言ggplot2可视化绘制分组水平并行条形图(bar plot)并为条形图内添加标签
  2. 单分子实时测序技术的原理与应用
  3. C语言什么时候必须用到二级指针?(需要调用函数为一维空指针确定值的情况下,需要传入二维指针,也就是那个一维指针的指针)
  4. 用 JavaScript 验证只能输入数字,并做数字加总
  5. 把 Console 部署成 Windows 服务,四种方式总有一款适合你!
  6. 第五十四期:MongoDB与MySQL:如何选择
  7. python 数字转化excel行列_Python实现excel的列名称转数字、26进制(A-Z)与10进制互相转换...
  8. 好色之旅-画图三字经
  9. vue 鼠标点击事件_点击鼠标,利用VBA代码实现精准控制触发事件的第二方案
  10. 教你如何在Linux中通过expect工具实现脚本的自动交互
  11. ubuntu下有没有类似于imagewatch的软件_大家有没有什么好的app推荐下,学习的类似timing小众点的?...
  12. python词云图生成
  13. 早间简评:黄金亚盘快速下跌   1300关口岌岌可危?
  14. 人生这么短,哪有空嫌晚
  15. 十六、 Interpreter 解释器(行为型模式)
  16. 计算机系女学霸男生追,杨紫李现解锁恋爱新姿势:吃最甜的糖,追最燃的梦
  17. Python有嘻哈:Crossin教你用代码写出押韵的verse
  18. kafka学习(六)
  19. 使用Python简单实现马赛克拼图
  20. 序列化和反序列化——字节码

热门文章

  1. 什么是JAVA内容仓库(Java Content Repository)
  2. 怎样在Excel里第一格设计斜线表头
  3. 为什么都说猫有九条命呢
  4. IOS线程学习(一)
  5. sqlite3-查看数据库
  6. Jquery 提示插件
  7. 推荐六款帮助你实现惊艳视差滚动效果的 jQuery 插件
  8. DOS下从硬盘安装XP系统方法与要点
  9. 倾斜摄影技术在城市规划行业中扮演着什么样的角色?
  10. C++学习基础七——深复制与浅复制