Bit-Block Transfer
相比图元文件,位图有两个大缺点,一是易受设备依赖性问题影响。比如在一个单色设备上显示位图经常不会令人满意;还有位图的缩放,经常涉及到行或列的重复或丢弃,这样会造成缩放位图的混乱。第二个缺点是位图占用存储空间大。然而,位图最大的优点是速度,显示位图要比图元文件快得多。
GetDeviceCaps的BITSPIXEL和PLANES参数获取显卡的颜色参数。
BitBlt(hdcDst,xDst,yDst,cx,cy,hdcSrc,xSrc,ySrc,dwROP):把hdcSrc(xSrc,ySrc,xSrc+cx,ySrc+cy)显示到hdcDst(xDst,yDst,xDst+cx,yDst+cy)。要用这个函数,两个DC必须兼容。
StretchBlt(hdcDst,xDst,yDst,cxDst,cyDst,hdcSrc,xSrc,ySrc,cxSrc,cySrc,dwROP):BitBlt只能按原始大小显示,StretchBlt可以拉伸位图。这个函数可以解决两个DC物理显示不同的问题。StretchBlt还可以翻转位图,把xDst改为xSrc+cxSrc,cxDst改为-cxSrc试试。
SetStretchBltMode(hdc,iMode):设置StretchBlt模式。当目标位图比原来位图小时,StretchBlt需要减少一些行或列,它有四种模式,由iMode指定。BLACKONWHITE或STRETCH_ANDSCANS(默认):把需要合并的像素按位与,用在白背景主要为黑色为主的位图较好。WHITEONBLACK或STRETCH_ORSCANS:按位或,用在黑底白图的位图。COLORONCOLOR或STRETCH_DELETESCANS:简单删除不要的像素,是彩色位图最好的模式。HALFTONE或STRETCH_HALFTONE:取平均值(以后介绍)。
GetStretchBltMode
ROP(Raster Operation,Bitblt的最后一个参数)
BitBlt和StretchBlt并不是简单的复制,而是对三个图片做位操作:
1.Source 拉伸或压缩为目标位图大小
2.Destination 调用BitBlt或StretchBlt前的目标区域位图
3.Pattern 目标设备DC的画刷在水平或垂直重复绘制与目标区域大小相同的位图。
对这三个位图的变换有:
定义 操作
BLACKNESS 0
NOTSRCERASE ~(S|D)
NOTSRCCOPY ~S
SRCERASE S&~D
DSINVERT ~D
PATINVERT P^D
SRCINVERT S^D
SRCAND S&D
MERGEPAINT ~S&D
MERGECOPY P&S
SRCCOPY S
SRCPAINT S|D
PATCOPY P
PATPAINT P|~S|D
WHITENESS 1
PatBlt(hdc,x,y,cx,cy,dwROP):没有源位图,FillRect和InvertRect就用这个函数实现。
BitBlt、PatBlt和StretchBlt是GDI中仅有的以一个点、长和宽参数绘制矩形,其他函数都要以左上角和右下角坐标为参数。这三个函数中点可以是任意一个点的坐标,长和宽可以为负。如果Y坐标正方向向上,简单的方法是(x,y)为左上角,cy用负数。
创建位图
位图分两种DDB(Device-Dependent Bitmap)和DIB(Device-Independent Bitmap)。
CreateBitmap(cx,cy,cPlanes,cBitsPixel,bits):返回HBITMAP。cx,cy是长和高,cPlanes是调色板数,cBitsPixel是像素深度,bits是位图指针,如果不想初始化DDB设为NULL。分配空间每行以两字节为单位,计算公式iWidthBytes=((cx*cBitsPixel+15)&~15)>>3。CreateBitmap为DDB分配的空间iBitmapBytes=cy*cPlanes*iWidthBytes。
CreateBitmap在实际中只用以下两类参数:
1.cPlanes和cBitsPixel都为1,显示单色
2.cPlanes和cBitsPixel与设为某个DC的值,用GetDeviceCaps的PLANES和BITSPIXEL获取。
第二种用法完成可以用CreateCompatibleBitmap替代。
CreateCompatibleBitmap(hdc,cx,cy)
CreateDiscardableBitmap(hdc,cx,cy):与上一个相同,在以前的Windows版本中,用它创建的DDB在内存低时会被Windows回收。
CreateBitmapIndirect(&bitmap):bitmap是BITMAP结构体,不用初始化bmWidthBytes字段,Windows会自动计算。所有创建的DDB都要用DeleteObject销毁。
GetObject(hBitmap,sizeof(BITMAP),&bitmap):得到hBitmap的位图信息。
LoadBitmap(hInstance,szBitmapName):hInstance为NULL,加载系统位图(以OBM开头宏)。如果位图资源与一个ID关联而不是名字,则用MAKEINTRESOURCE宏转化。返回的bitmap句柄总与DC兼容。
CreatePatternBrush(hBitmap):返回HBRUSH,把hBitmap加载到画刷中,Bitmap至少为8*8。也可用CreateBrushIndirect创建,LOGBRUSH的lpStyle字段设为BS_PATTERN。Bitmap和Brush都是GDI对象,都要在程序结束前调用DeleteObject。当基于Bitmap创建Brush时,Brush中会有一个Bitmap拷贝,这时就可以删除Bitmap了。
位图像素