我试图编写一个简单的函数,将一些图像数据保存为位图。我生成的数据是3601 x 3601.我在调试器中验证了传递给函数的所有数据都是正确的。我还验证了焊盘尺寸与我期望的24位BMP宽度3601(padSize = 1)一样。
这个创建的位图要比我用相同尺寸的绘制创建的位图大得多,这意味着这里写的东西太多了。我把这个文件比作一个类似大小的位图,标题是相同的,所以我不认为我的问题就在那里。我认为我在charbuffer上的写命令必须写得比预期更多,但我无法弄清楚原因。任何帮助表示赞赏。
void SaveBMPData(string fname, unsigned char *data, int imgWid, int imgHei)
{
ofstream file;
file.open(fname.c_str(), std::ios::out);
if (file.is_open())
{
//string fname = "APnormal.bmp";
cout << "INFO >> Saving BMP data: " << fname << "." << endl;
//write header
unsigned char fileinfo[14] = {
'B', 'M', // magic
0, 0, 0, 0, // size in bytes
0, 0, // app data
0, 0, // app data
40 + 14, 0, 0, 0 // start of data offset
};
unsigned char info[40] = {
40, 0, 0, 0, // info hd size
0, 0, 0, 0, // width
0, 0, 0, 0, // heigth
1, 0, // number color planes
24, 0, // bits per pixel
0, 0, 0, 0, // compression is none
0, 0, 0, 0, // image bits size
0x13, 0x0B, 0, 0, // horz resoluition in pixel / m
0x13, 0x0B, 0, 0, // vert resolutions (0x03C3 = 96 dpi, 0x0B13 = 72 dpi)
0, 0, 0, 0, // #colors in pallete
0, 0, 0, 0, // #important colors
};
int w = imgWid;
int h = imgHei;
int padSize = (4 - ((w * 3) % 4)) % 4;
int sizeData = w*h * 3 +h*padSize;
int sizeAll = sizeData + sizeof(fileinfo) + sizeof(info);
fileinfo[2] = (unsigned char)(sizeAll);
fileinfo[3] = (unsigned char)(sizeAll >> 8);
fileinfo[4] = (unsigned char)(sizeAll >> 16);
fileinfo[5] = (unsigned char)(sizeAll >> 24);
info[4] = (unsigned char)(w);
info[5] = (unsigned char)(w >> 8);
info[6] = (unsigned char)(w >> 16);
info[7] = (unsigned char)(w >> 24);
info[8] = (unsigned char) (h);
info[9] = (unsigned char) (h >> 8);
info[10] = (unsigned char)(h >> 16);
info[11] = (unsigned char)(h >> 24);
info[20] = (unsigned char)(sizeData);
info[21] = (unsigned char)(sizeData >> 8);
info[22] = (unsigned char)(sizeData >> 16);
info[23] = (unsigned char)(sizeData >> 24);
file.write((char*)fileinfo, sizeof(fileinfo));
file.write((char*)info, sizeof(info));
unsigned char *charbuffer = new unsigned char[w * 3 + padSize];
for (int y = 0; y<h; y++)
{
for (int x = 0; x<w; x++)
{
unsigned char red = data[(x + y*imgWid) * 3];
unsigned char green = data[(x + y*imgWid) * 3 + 1];
unsigned char blue = data[(x + y*imgWid) * 3 + 2];
charbuffer[x * 3 ] = blue;
charbuffer[x * 3 + 1] = green;
charbuffer[x * 3 + 2] = red;
}
file.write((char *)(void*)charbuffer, w*3+padSize);
}
file.close();
delete [] charbuffer;
}
else
{
cout << "can't read file.\n";
}
}
答案 0 :(得分:1)
您需要以二进制模式打开文件,否则任何值为0x0a的像素组件都将导致写入0x0d 0x0a文件。
file.open(fname.c_str(), std::ios::out | std::ios::binary);
答案 1 :(得分:0)
你是否将绘图中的位图保存为24位bmp?
我强烈建议在互联网上获取一些代码,例如:http://tipsandtricks.runicsoft.com/Cpp/BitmapTutorial.html并查看/使用该代码。
我会避免使用带有值和注释(info,fileinfo)的数组,并使用真实的具体结构来定义属性。
您的问题应该很容易理解,但IMO最好使用已编写的代码,因为这已经多次完成所以。