透过前面的图象看到背景图象,称前面的图象为透明图象,我们见过很多程序和电视节目中都有使用透明图象,而且大家一定会为图象的透明而称奇。究竟透明图象是如何做出来的呢?下面我们将来探讨这种透明图象的制作方法。
创建透明图象的五个必须的步骤:
准备两个位图文件,一个作背景,一个是将要成为透明图象的源位图。
1、 取得源位图的长、宽数据,依此数据保存一块和源位图一样大小的背景位图,源位图将要在这块背景位图上绘制。通过用白色像素显示位图的透明区域,黑色像素显示位图的不透明区域,创建决定位图透明的单色掩码。
2、单色掩码像素与所用的背景位图进行二进制“与”(and)位操作,不透明的区域,背景显示黑色。
3、用第一步所做的单色掩码建立一个反向拷贝,再用这个反向拷贝与所用的源位图进行二进制“与”(and)位操作,源位图透明的区域将显示黑色
4、用第二步修改过的背景和第三步修改的源位图进行二进制“异或”(xor)位操作,这时可以透过透明位图看到背景。
5、把结果位图复制给背景
应用实例:
创建包含一个 commandbutton 控件和两个picturebox控件的 窗体form1。创建一个模块(在 “工程”菜单中单击“添加模块”)。
给窗体增加下列控件,设置相关的属性值:
控件 name property settings
—————————————————————–
picturebox pictsource picture =”c:flower_vine.bmp”
picturebox pictdest picture =”c:stones_blue.bmp”
command button command1 caption =”透明图象”
—- 将下面的代码粘贴到窗体的声明部分中,
—- option explicit 这段代码调用过程transparent()复制源位图到目标(背景)picturebox控件, 并将其变成透明,使人们可以看到后面的背景图象。
sub command1_click()
call transparent(pictsource.picture.handle, pictdest,
10, 10, qbcolor(15))
end sub
—- 将下面的代码粘贴到模块的声明部分中,
option explicit
—- 由于要读取位图的基本信息,所以首先要定义一个bitmap结构的变量,然后
—- 利用这一变量来接受位图的基本信息。
type bitmap
type as long 位图类型
width as long 宽度
height as long 高度
widthbytes as long 多少二进制位构成一个存储单位
planes as integer 调色板数
bitspixel as integer 每一个pixel所占用的二进制位数
bits as long 二进制位数据的起始位置
end type
api 函数说明
declare function getobject lib “gdi32”
alias “getobjecta” (byval hobject as _
long, byval ncount as long, lpobject as any) as long
经由对象的handle取得对象数据结构的api函数
declare function createcompatibledc lib “gdi32”
(byval hdc as long) as long
此函数将图象绘制到存储器中可避免直
接将图象绘制到屏幕上而造成图象闪烁
declare function createbitmap lib “gdi32”
(byval nwidth as long, _
byval nheight as long, byval nplanes
as long, _
byval nbitcount as long, lpbits as any)
as long 建立位图对象
declare function createcompatiblebitmap lib
“gdi32” (byval hdc as long, _
byval nwidth as long, byval nheight as long)
as long 建立兼容性的位图
declare function bitblt lib “gdi32”
(byval hdestdc as long, _
byval x as long, byval y as long, byval
nwidth as long, _
byval nheight as long, byval hsourcedc as long,
byval xsrc as long, _
byval ysrc as long, byval dwrop as long) as long 图象转移
declare function setbkcolor lib “gdi32” (byval hdc as long,
byval crcolor as long) as long
declare function deletedc lib “gdi32” (byval hdc as long)
as long 删除存储器dc
declare function selectobject lib “gdi32” (byval hdc as long,
byval hobject as long) as long 为dc选用对象
declare function deleteobject lib “gdi32” (byval hobject as
long) as long 删除位图对象
—- 过程transparent() 复制源位图到背景的任意 x,y 位置,使这一区域变成透明。transparent()接受五个参数:一个将要变成透明的源位图,一个目标 picturebox控件 (pictdest), 一个rgb颜色值,另两个是你想放置原位图的目的地坐标(destx 和 desty,以像素为单位)。
sub transparent(byval sourcebmp as long, dest as control, byval _
destx as integer, byval desty as integer, byval transcolor as long)
const pixel = 3
dim sourcedc as long 源位图
dim destscale as long
dim maskdc as long mask位图 (monochrome)
dim savedc as long 源位图的备份
dim resultdc as long 源位图与背景的合并
dim invdc as long mask位图的反向图
dim origcolor as long 背景色
dim success as long 调用 windows api的结果
dim bmp as bitmap 原位图的数据结构说明
dim hresultbmp as long 源与背景的位图合并
dim hsavebmp as long 原位图的拷贝
dim hsrcprevbmp as long
dim hdestprevbmp as long
dim hinvbmp as long 反转掩码位图 (monochrome)
dim hprevbmp as long
dim hinvprevbmp as long
dim hsaveprevbmp as long
dim hmaskbmp as long
dim hmaskprevbmp as long
destscale = dest.scalemode 保存 scalemode以便后面恢复
dest.scalemode = pixel 设置 scalemode
sourcedc = createcompatibledc(dest.hdc) 建立存储器dc
savedc = createcompatibledc(dest.hdc) 建立存储器dc
invdc = createcompatibledc(dest.hdc) 建立存储器dc
maskdc = createcompatibledc(dest.hdc) 建立存储器dc
resultdc = createcompatibledc(dest.hdc) 建立存储器dc
接受源位图得到它的的宽度和长度 (bmp.width , bmp.height)
success = getobject(sourcebmp, len(bmp), bmp)
创建单色掩码位图
hmaskbmp = createbitmap(bmp.width, bmp.height, 1, 1, byval 0&)
hinvbmp = createbitmap(bmp.width, bmp.height, 1, 1, byval 0&)
hresultbmp = createcompatiblebitmap(dest.hdc, bmp.width, _
bmp.height)
hsavebmp = createcompatiblebitmap(dest.hdc, bmp.width, _
bmp.height)
hsrcprevbmp = selectobject(sourcedc, sourcebmp)
hsaveprevbmp = selectobject(savedc, hsavebmp)
hmaskprevbmp = selectobject(maskdc, hmaskbmp)
hinvprevbmp = selectobject(invdc, hinvbmp)
hdestprevbmp = selectobject(resultdc, hresultbmp) 选择位图
success = bitblt(savedc, 0, 0, bmp.width, bmp.height, sourcedc, _
0, 0, vbsrccopy) 制作源位图的拷贝以便后面恢复
origcolor = setbkcolor(sourcedc, transcolor)
success = bitblt(maskdc, 0, 0, bmp.width, bmp.height, sourcedc, _
0, 0, vbsrccopy)
transcolor = setbkcolor(sourcedc, origcolor)
success = bitblt(invdc, 0, 0, bmp.width, bmp.height, maskdc, _
0, 0, vbnotsrccopy)
拷贝背景图并创建最终的透明位图
success = bitblt(resultdc, 0, 0, bmp.width, bmp.height, _
dest.hdc, destx, desty, vbsrccopy)
success = bitblt(resultdc, 0, 0, bmp.width, bmp.height, _
maskdc, 0, 0, vbsrcand)
success = bitblt(sourcedc, 0, 0, bmp.width, bmp.height, invdc, _
0, 0, vbsrcand)
success = bitblt(resultdc, 0, 0, bmp.width, bmp.height, _
sourcedc, 0, 0, vbsrcinvert)
success = bitblt(dest.hdc, destx, desty, bmp.width, bmp.height, _
resultdc, 0, 0, vbsrccopy) 在背景上显示透明位图
success = bitblt(sourcedc, 0, 0, bmp.width, bmp.height, savedc, _
0, 0, vbsrccopy) 恢复位图
选择对象以便释放
hprevbmp = selectobject(resultdc, hdestprevbmp)
hprevbmp = selectobject(sourcedc, hsrcprevbmp)
hprevbmp = selectobject(savedc, hsaveprevbmp)
hprevbmp = selectobject(invdc, hinvprevbmp)
hprevbmp = selectobject(maskdc, hmaskprevbmp)
释放资源
success = deletedc(savedc)
success = deletedc(invdc)
success = deletedc(resultdc)
success = deleteobject(hsavebmp)
success = deleteobject(hmaskbmp)
success = deleteobject(hinvbmp)
success = deletedc(sourcedc)
success = deletedc(maskdc)