BMP
BMP格式是以重图片格式。文件由三个部分组成:文件头,信息头,rgb数据。
文件头(14字节) + 信息头(40字节) = 54 字节
文件头(14字节)
| 名称 | 占用空间 | 内容 | 示例数据 |
|---|---|---|---|
| bfType | 2字节 | 标识,就是“BM” | BM |
| bfSize | 4字节 | 整个 BMP 文件的大小 | 0x000C0036(786486) |
| bfReserved1 | 2字节 | 保留字 | 0 |
| bfReserved2 | 2字节 | 保留字 | 0 |
| bfOffBits | 4字节 | 偏移数,即位图文件头 位图信息头 调色板的大小 | 0x36(54) |
信息头(40字节)
| 名称 | 占用空间 | 内容 | 示例数据 | |
|---|---|---|---|---|
| biSize | 4字节 | 位图信息头的大小,为40 | 40 | |
| biWidth | 4字节 | 位图的宽度,单位是像素 | 1920 | |
| biHeight | 4字节 | 位图的高度,单位是像素 | 1080 | |
| biPlanes | 2字节 | 固定值1 | 1 | |
| biClrUsed | 4字节 | 位图使用的颜色数 | 如果为0,则颜色数为2的biBitCount次方 | 0 |
| biBitCount | 2字节 | 每个像素的位数 1-黑白图,4-16色,8-256色,24-真彩色,32-带alpha通道 | 32 | |
| biSizeImage | 4字节 | 位图全部像素占用的字节数,BI_RGB时可设为0 | 1920 x 1080 x 4 | |
| biCompression | 4字节 | 压缩方式,BI_RGB(0)为不压缩 | 0 | |
| biClrImportant | 4字节 | 重要的颜色数,0代表所有颜色都重要 | 0 | |
| biXPelsPerMeter | 4字节 | 水平分辨率(像素/米) | 2835 | |
| biYPelsPerMeter | 4字节 | 垂直分辨率(像素/米) | 2835 |
//参数:pdata是rgb32数据,width,height是图片的宽与高
void SaveRgb2Bmp(const uint8_t * pdata, int width, int height)
{
int size = width * height * 4 * sizeof(char); //这里乘以4,是因为rgb32数据是rgba的数据,一共有四个分量。
BITMAPFILEHEADER bfh;
bfh.bfType = (WORD)0x4d42;
bfh.bfSize = size + sizeof(BITMAPFILEHEADER) + sizeof(BITMAPINFOHEADER);
bfh.bfReserved1 = 0;
bfh.bfReserved2 = 0;
bfh.bfOffBits = sizeof(BITMAPFILEHEADER) + sizeof(BITMAPINFOHEADER);
BITMAPINFOHEADER bih;
bih.biSize = sizeof(BITMAPINFOHEADER);
bih.biWidth = width;
bih.biHeight = -height;//!!!
bih.biPlanes = 1;
bih.biClrUsed = 0;
bih.biBitCount = 32;
bih.biSizeImage = size;
bih.biCompression = 0;
bih.biClrImportant = 0;
bih.biXPelsPerMeter = 2835;
bih.biYPelsPerMeter = 2835;
FILE * fp = nullptr;
fopen_s(&fp, "Screen.bmp", "wb");
if (!fp) return;
fwrite(&bfh, 8, 1, fp);
fwrite(&bfh.bfReserved2, sizeof(bfh.bfReserved2), 1, fp);
fwrite(&bfh.bfOffBits, sizeof(bfh.bfOffBits), 1, fp);
fwrite(&bih, sizeof(BITMAPINFOHEADER), 1, fp);
fwrite(pdata, size, 1, fp);
fclose(fp);
}
上面代码有个细节:bih.biHeight = -height;
为什么是负的?原因如下:
- RGB24 文件中存储的顺序是 RGB, RGB, RGB ...... RGB
- BMP 文件中 RGB 数据存储的顺序是 BGR, BGR, BGR ... BGR
- 发现RGB文件与BMP存储RGB数据的时候是相反的,所以我们的biHeight需要为负数。biHeight 为正,位图自底向顶扫描,biHeight 为负,位图自顶向底扫描。