今天有人在QQ群里问GDI能不能支持带alpha通道的线条绘制?
大家的答案当然是否定的,很多人推荐用GDI+。

一个基本的图形引擎要包括几个方面的支持:位图绘制,文字绘制,矢量绘制(如矩形,线条)。

可惜GDI这个20多年前发明的老古董,对这几项的绘制, 除了位图绘制可以通过AlphaBlend支持alpha通道,其他绘制都不支持alpha通道。
那有没有方法让能通过纯GDI让文字和矢量的绘制也支持alpha通道呢?

讨论这个问题之前,我们先看一下用GDI函数在支持alpha通道的DC上绘制会发生什么? 这里 有人讨论过这个问题。
当然我们也可以自己测试,测试结果是GDI函数会把绘制覆盖目标像素的alpha通道改都改成0, 也 就是说如果画一条线条, 线条通过的位置的alpha通道都回被改成0。

实际上我们可以利用系统的这个特性,结合AlphaBlend函数实现alpha通道的文字和矢量图形绘制。

具体做法大概如下:
1. 创建内存DC和一幅32bit的DIB Section, 将位图选入DC
2. 将位图的所有字节全都改成0xFF
3. 在内存DC上用文字和矢量 GDI函数 (如DrawText, Rectangle)绘制东西
4. 遍历所有像素,发现alpha通道为0 (表示该区域被绘制过),则将 alpha通道改成我们需要的alpha值;否则,则将像素的alpha通道改成0 (表示没有内容绘制上去)
5. 最后通过AlphaBlend将生成好的DIB Section合成绘制到目标区域

通过上面这种方法, 我们可以实现带alpha通道的矢量和文字绘制,我猜测GDI+应该也是通过类似这种修改像素的方法实现的。

当然,这种方法因为效率问题, 建议一些简单的绘制可以考虑 (如果不想引入GDI+), 如果大规模应用就要仔细斟酌了。

微软当初引入GDI+,部分原因就是因为GDI不支持alpha通道,可惜GDI+的效率是如此臭名昭著, 大家大部分时候都是尽量避免引入,很多时候我们引入GDI+只是为了使用它的图像编解码功能。

还好技术总是不断进步,如果你的程序不用考虑XP(现在看来还要过几年), Vista之后系统为我们提供了高效的图形支持:
图像编解码可以用WIC,文字操作可以用DirectWrite,图形渲染可以用Direct2D  (既支持alpha通道,又支持GPU加速), 实际上IE9之后的浏览器都已采用Direct2D开发

如何基于纯GDI实现alpha通道的矢量和文字绘制的更多相关文章

  1. 使用GDI+保存带Alpha通道的图像

    带Alpha通道的图像(ARBG)在通过GDIPlus::Bitmap::FromHBITMAP等转为GDI+位图,再存储时,透明区域会变成纯黑(也有可能是纯白?).   网上找了两段保持透明的实现代 ...

  2. 使用GDI+保存带Alpha通道的图像(续)

    之前结合网上的一些代码及ATL::CImage的实现,自己写了一个将HBITMAP以PNG格式保存到文件到函数.见上一篇日记. 不过,后来换了个环境又发现了问题,昨天和今天上午把<Windows ...

  3. 窗体的Alpha通道透明色支持(一旦 Form 被定义为利用 LayeredWindow ,窗口的绘图不再响应沿用多年的 WM_Paint 消息)

    参考: http://www.delphibbs.com/delphibbs/dispq.asp?lid=2190768 Windows 2000后,为了支持类似MAC界面的Alpha通道混合效果,提 ...

  4. 窗体的Alpha通道透明色支持

    参考: http://www.delphibbs.com/delphibbs/dispq.asp?lid=2190768 Windows 2000后,为了支持类似MAC界面的Alpha通道混合效果,提 ...

  5. 什么是Alpha通道?

    图像处理(Alpha通道,RGB,...)祁连山(Adobe 系列教程)****的UI课程 一个也许很傻的问题,在图像处理中alpha到底是什么?  Alpha通道是计算机图形学中的术语,指的是特别的 ...

  6. 基于纯 CSS3 技术实现美观的标签云效果

    标签云是博客的标配功能,能够清晰的呈现博客的各个关键词和主题.在这个效果中,您将学习如何使用 CSS3 技术创建一个效果精美的标签云效果. 作为实验项目,使用了 CSS3 渐变,阴影和最重要的的 CS ...

  7. [ActionScript 3.0] AS3.0 将图像的Alpha通道转换为黑白图像(分离ARGB方式)

    import flash.display.BitmapData; import flash.display.Bitmap; /** * 将图像的Alpha通道转换为黑白图像(分离ARGB方式) */ ...

  8. [ActionScript 3.0] AS3.0将图像的Alpha通道转换为黑白图像(复制通道方式)

    import flash.display.BitmapData; /** * 将图像的Alpha通道转换为黑白图像 */ var p:Point = new Point(0,0); var bmpd: ...

  9. ImagXpress中如何修改Alpha通道方法汇总

    ImagXpress支持处理Alpha通道信息来管理图像的透明度,Alpha通道支持PNG ,TARGA和TIFF文件,同时还支持BMP和ICO文件.如果说保存的图像样式不支持Alpha通道,就将会丢 ...

随机推荐

  1. Mac下U盘安装系统“未验证的错误”

    bash下 输入下面命令: date 1220141012015.30

  2. Android学习 之 ColorStateList按钮文字变色

    首先添加一个ColorStateList资源XML文件,XML文件保存在res/color/button_text.xml: <?xml version="1.0" enco ...

  3. Echarts给柱状图每一条顶部都添加数值

    在 series中添加 itemStyle : { normal: {label : {show: true}}}, 不过目测要把markPoint等去掉,不然最大值和最小值会和label冲突,应该有 ...

  4. 关于UltraEdit的两个小问题

    问题一:如何让Java在编写过程中的关键字着色? 首先,需要把编辑的文件名字后缀更改为.java; 然后,找到UltraEdit的安装目录下的wordfile文件夹(以前是一个wordfile.txt ...

  5. hdu 1015(DFS)

    Safecracker Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others)Total ...

  6. CM+CDH安装遇到的问题

    1.实在是在安装CDH的时候无法安装成功的话,只有重新启动了,下面给大家分享一个神器,按照这个脚本应该差不多就能卸载干净,然后重新安装,写一个脚本,内容如下,救命的神器呀: #!/bin/bash s ...

  7. JavaScript-navigator_userAgent-编写一段代码能够区分浏览器的主流和区分

    1 userAgent:包含浏览器名称和版本号的字符串 <!DOCTYPE html> <html> <head lang="en"> < ...

  8. 黑马程序员_Java基础:多线程总结

    ------- android培训.java培训.期待与您交流! ---------- 一.多线程的概念 进程和线程经常会被人混淆,那是因为对它们的概念不明确.就拿我们平时使用的操作系统来说,它是多任 ...

  9. shell选择语句

    if语句 1) if ... else 语句 if ... else 语句的语法: if [ expression ] then Statement(s) to be executed if expr ...

  10. 【Android UI】Android ListView详解

    在android开发中ListView是比较常用的组件,它以列表的形式展示具体内容,并且能够根据数据的长度自适应显示.抽空把对ListView的使用做了整理,并写了个小例子,如下图. 列表的显示需要三 ...