调色板数据
如果位图的描述还需要调色板数据,则应该在BMP文件头之后定义一个颜色表,它包含若干个表项。其中,每一个表项定义了一种颜色,Windows将其定义为如下的 RGBQUAD结构:
typedef struct tagRGBQUAD
{
BYTE rgbBlue;BYTE rgbGreen;BYTE rgbRed; BYTE rgbReserved;
}RGBQUAD;
注意:RGBQUAD数据结构中,增加了一个保留字段rgbReserved,它不代表任何意 义,必须取固定值00。同时,RGBQUAD结构定义的颜色值中,红色、绿色与蓝色的排 列顺序与一般图像文件的颜色数据排列顺序恰好相反,即:蓝色的亮度由rgbBlue字段定义、绿色的亮度由rgbGreen字段定义,红色的亮度由rgbRed字段定义。若位图中某个像素点的颜色描述为"00,00,FF,00",则表示该点的颜色为纯红色,而不是纯蓝色。
综上,在DIB位图文件组成中,位图信息头和颜色表组成位图信息,两者共同构成完整的位图文件BITMAPINFO。Windows将BITMAPINFO结构定义为:
typedef struct tagBITMAPINFO
{
BITMAPINFOHEADER bmiHeader:
RGBQUAD bmiColors[1];
}BITMAPINFO;
其中,bmiHeader字段指向位图颜色格式以及大小定义的 BITMAPINFOHEADER结构。bmiCo1our[1]字段指向RGBQUAD结构数组或者定义位图颜色值的双字数据结构,它定义了BMP图像文件的颜色表,它包含多少个表项是由 BITMAPINFOHEADER数据结构中的biBitCount字段定义的:若该字段的取值为1,则颜色表包含两个表项;若该字段的取值为4,则颜色表包含16个表项;若该字段的取值为8,则颜色表包含256个表项;若该字段的取值为16,而且 BITMAPINFO结构定义中指定bmiColors字段的取值为BI_RGB,则颜色表中的表项为空,位图阵列中每个字代表一个像素,字中每5位上的值代表该像素点一种基色的亮度,其中最低5位代表蓝色亮度,依次为绿色与红色,字的最高位没有任何意义。若该字段的取值为24,则颜色表中的表项为空,而位图阵列的每三个字节代表一个像素,这3个字节直接定义了像素颜色中蓝、绿、红三种基色的相对亮度。 若该字段的取值为32,而且BITMAPINFO结构定义中bmiColors字段的取值为BI—RGB,则颜色表中的表项为空,且位图阵列中的每个双字代表一个像素的三原色亮度构成。 注意:颜色表中的数据应该按照重要性的帧序进行排列。另外,如果应用程序中需要使用DIB位图,则bmiColors字段可以为16位的无符号整数数组,这些整数指定当前逻辑调色板的颜色索引,而不是显式的RGB值。当然,如果位图存储在文件中或者需要传送到其它应用程序,则该字段中不能包含调色板索引值。
位图数据记录了位图的每一个像素值,记录顺序是在扫描行内是从左到右,扫描行之间是从下到上。位图的一个像素值所占的字节数:
当biBitCount=1时,8个像素占1个字节;
当biBitCount=4时,2个像素占1个字节;
当biBitCount=8时,1个像素占1个字节;
当biBitCount=24时,1个像素占3个字节;
Windows规定一个扫描行所占的字节数必须是 4的倍数(即以long为单位),不足的以0填充, biSizeImage = ((((bi.biWidth * bi.biBitCount) + 31) & ~31) / 8) * bi.biHeight。
下面是一个BMP文件:
424D 4690 0000 0000 0000 4600 0000 2800 0000 8000 0000 9000 0000 0100*1000 0300 0000 0090 0000 A00F 0000 A00F 0000 0000 0000 0000 0000*00F8 E007 1F00 0000*02F1 84F1 04F1 84F1 84F1 06F2 84F1 06F2 04F2 86F2 06F2 86F2 86F2 .... ....
BMP文件可分为四个部分:位图文件头、位图信息头、彩色板、位图数据阵列,例子中每个部分都用*隔开了。
图像文件头
(1) 1:(这里的数字代表的是"字",即两个字节,下同)图像文件头。0x4D42=’BM’,表示是Windows支持的BMP格式。 彩色图像的边缘检测处理程序设计(9):http://www.751com.cn/jisuanji/lunwen_6655.html