透明位图显示//TransparentBlt //DrawTransparentBitmap函数

来源:互联网 发布:方正字体软件 编辑:程序博客网 时间:2024/05/16 14:31

 画透明位图通常的方法是使用遮罩。所谓遮罩就是一张黑白双色的位图,他和要透明的位图是对应的,遮罩描述了位图中需要透明的部分,透明的部分是黑色的,而不透明的是白色的,白色的部分就是透明的部分。 

    假设图A是要画的透明位图,图B是遮罩,图A上是一个大写字母A,字母是红色的,背景是黑色的,图B背景是白色的,上面有一个黑色的字母A和图A的形状是一样的。 

       比如我们要在一张蓝天白云的背景上透明地画图A,就是只把红色的字母A画上去。我们可以先将图B和背景进行与操作,再把图B和背景进行或操作就可以了。 

用VC MFC实现的代码如下: 
void CDemoDlg::OnPaint() 

CPaintDC dc(this); 
CBitmap BmPBack,BmpA,BmpB,*pOldBack,*pOldA,*pOldB; 

BmpBack.LoadBitmap(IDB_BACKGROUND); // 载入背景图 
BmpA.LoadBitmap(IDB_BITMAPA); //载入图A 
BmpB.LoadBitmap(IDB_BITMAPB); //载入图B 

CDC dcBack,dcA,dcB; //声明三个内存DC用于画图 
dcBack.CreateCompatibleDC(&dc); 
dcA.CreateCompatibleDC(&dc); 
dcB.CreateCompatibleDC(&dc); //把这三个内存DC创建成和PaintDC兼容的DC 

pOldBack=dcBack.SelectObject(&BmpBack); 
pOldA=dcA.SelectObject(&BmpA); 
pOldB=dcB.SelectObject(&BmpB); //把三个位图选入相应的DC 

dc.BitBlt(0,0,100,100,&dcBack,0,0,SRCCOPY); //画背景 
dc.BitBlt(0,0,48,48,&dcB,0,0,SRCAND); //用与的方式画遮罩图B 
dc.BitBlt(0,0,48,48,&dcA,0,0,SRCPAINT); //用或的方式画遮图A 

dcBack.SelectObject(pOldBack); 
dcBack.SelectObject(pOldA); 
dcBack.SelectObject(pOldB); //从内存DC中删除位图 


你会看到红色的字母A透明地画在背景上了。 

用遮罩的方法必须事先做好遮罩,遮罩和位图大小一样等于多消耗一倍的资源,比较浪费。

方法二:

还有一种画透明位图的方法,基本原理是一样的,只是不用事先做好遮罩,根据需要动态生成遮罩,但是要求需要透明的位图必须指定一种透明色,凡是这个透明色的地方则画成透明的。 

用VC MFC实现的代码如下: 
/* 
这是一个用来画透明位图的函数 
CDC *pDC 需要画位图的CDC指针 
UINT IDImage 位图资源ID 
CRect &rect 指定位图在pDC中的位置 
COLORREF rgbMask 位图的透明色 
*/ 
void DrawTransparentBitmap(CDC *pDC, UINT IDImage,CRect &rect, COLORREF rgbMask) 

CDC ImageDC,MaskDC; 

CBitmap Image,*pOldImage; 
CBitmap maskBitmap,*pOldMaskDCBitmap ; 

Image.LoadBitmap(IDImage); 
ImageDC.CreateCompatibleDC(pDC); 
pOldImage=ImageDC.SelectObject(&Image); 

MaskDC.CreateCompatibleDC(pDC); 
maskBitmap.CreateBitmap( rect.Width(), rect.Height(), 1, 1, NULL ); 
pOldMaskDCBitmap = MaskDC.SelectObject( &maskBitmap ); 

ImageDC.SetBkColor(rgbMask); 
MaskDC.BitBlt( 0, 0, rect.Width(), rect.Height(), &ImageDC, 0, 0, SRCCOPY ); 

ImageDC.SetBkColor(RGB(0,0,0)); 
ImageDC.SetTextColor(RGB(255,255,255)); 
ImageDC.BitBlt(0, 0, rect.Width(), rect.Height(), &MaskDC, 0, 0, SRCAND); 

pDC->BitBlt(rect.left,rect.top,rect.Width(), rect.Height(), &MaskDC, 0, 0, SRCAND); 
pDC->BitBlt(rect.left,rect.top,rect.Width(), rect.Height(), &ImageDC, 0, 0,SRCPAINT); 

MaskDC.SelectObject(pOldMaskDCBitmap); 
ImageDC.SelectObject(pOldImage); 


void CDemoDlg::OnPaint() 

CPaintDC dc(this); 

CBitmap BmpBack,*pOldBack,; 
BmpBack.LoadBitmap(IDB_BACKGROUND); 

CDC dcBack; 
dcBack.CreateCompatibleDC(&dc); 
pOldBack=dcBack.SelectObject(&BmpBack); 

dc.BitBlt(0,0,100,100,&dcBack,0,0,SRCCOPY); 
DrawTransparentBitmap(&dc,IDB_BITMAPA,CRect(0,0,48,48),RGB(192,192,0)); 

dcBack.SelectObject(pOldBack); 
}

 

//////////////////////////////////////////////////////////////////////////////////

TransparentBlt 函数在Windows98/Windows2000以上版本运行,系统中需要包含 Msimg32.dll,使用时可以链接 Msimg32.lib。
Windows98下的TransparentBlt会产生资源泄漏,所以不建议在WIN98下使用该函数。
TransparentBlt函数原型如下:

BOOL TransparentBlt( HDC hdcDest, // 目标DC int nXOriginDest, // 目标X偏移 int nYOriginDest, // 目标Y偏移 int nWidthDest, // 目标宽度 int hHeightDest, // 目标高度 HDC hdcSrc, // 源DC int nXOriginSrc, // 源X起点 int nYOriginSrc, // 源Y起点 int nWidthSrc, // 源宽度 int nHeightSrc, // 源高度 UINT crTransparent // 透明色,COLORREF类型 );

使用示例:

CBitmap FootballBMP; FootballBMP.LoadBitmap(IDB_FOOTBALLBMP); CDC ImageDC; ImageDC.CreateCompatibleDC(pDC); CBitmap *pOldImageBMP = ImageDC.SelectObject(&FootballBMP); TransparentBlt(pDC->m_hDC, 0, 0, 218, 199, ImageDC.m_hDC, 0, 0, 218, 199, RGB(0,0,0xff)); ImageDC.SelectObject(pOldImageBMP);
原文连接 http://blog.csdn.net/zhoubl668/article/details/4338317