该函数在可以直接在显示器或打印机上显示DIB,在显示时不进行缩放处理。此函数主要难理解地方在于StartScan参数指定图像坐标系的原点位置。
在BITMAPINFOHEADER结构中biHeight字段的正负号指定DIB图像的绘制方向。
文章主要从biHeight > 0、biHeight < 0进行描述。
1. 函数原型:
2. int SetDIBitsToDevice(
3. [in]HDC hdc, // 目标设备上下文句柄
4. [in]int xDest, // 指定目标设备上绘制区域的左上角x坐标
5. [in]int yDest, // 指定目标设备上绘制区域的左上角y坐标
6. [in]DWORD w, // 指定要显示的图像区域(不一定是整个图像)的宽度
7. [in]DWORD h, // 指定要显示的图像区域(不一定是整个图像)的高度
8. [in]int xSrc, // 指定要显示的图像区域(不一定是整个图像)的x坐标
9. [in]int ySrc, // 指定要显示的图像区域(不一定是整个图像)的y坐标
10. [in]UINT StartScan, // 指定lpvBits指向的数据在图像的y坐标
11. [in]UINT cLines, // 指定lpvBits包含的行数
12. [in]CONST VOID *lpvBits, // 指向图像像素数据
13. [in]CONST BITMAPINFO *lpbmi, // 指向BITMAPINFO结构的指针
14. [in]UINT ColorUse // 指定BITMAPINFO结构中的bmiColors(只在非真彩色图像用到时此参数才有效)包含真实的RGB值还
15. // 还是调色板中的索引值,取值包括两种:
16. // DIB_PAL_COLORS: 调色板中包含的是当前逻辑调色板的索引值
17. // DIB_RGB_COLORS: 调色板中包含的是真正的RGB数值
18. );
BITMAPINFOHEADER中的biHeight为正值,以下图为例详细说明各参数意义:
(图1为原始图像尺寸,其余图片为排版方便已适当缩小)
图1 示例图片(来自百度搜索)400(宽度) X 600(高度)
将图1图像数据读入内存,数组元素为自下而上顺序,第一行位于图像最下方,最后一行位于图像最上方,如图2所示 。
图2 图像数组元素顺序
【1】xDest/yDest:指定目标设备上绘制区域的左上角坐标,如下图所示,表示目标设备(如显示器)的坐标系表示。
图3 目标设备(如显示器)的坐标系
.【2】StartScan:指定lpvBits指向的数据位于图像坐标系的y坐标,以lpvBits指向图像最下方即第一行数据,如图4。
StartScan > 0、StartScan < 0、StartScan = 0时的图像坐标系分别如图5所示。
图4 lpvBits指向图像数据的位置
StartScan > 0 StartScan < 0 StartScan = 0
图5 图像坐标系的描述
【3】cLines:指定lpvBits指向的图像数组中的像素行数
当cLines大于能达到的最大值时,此函数自动调整cLines为能达到的最大值,如6所示,图像尺寸:400(宽度) X 600(高度)。
lpvBits指向图像数据的第一行, lpvBits不是指向图像数据的第一行,
cLines大于完整图像的高度,函数自动调整cLines为600; 此时cLines大于能达到的最大值,函数自动调整cLines为400。
图6 cLines参数的调整
【4】xSrc、ySrc、w、h:在StartScan确定的坐标系下指定要显示的图像区域。
最终显示图像大小为w x h,有像素数据部分为红框部分,超出红框部分为空白。