Load BMP data (for heightmaps etc)
From Sidvind
Contents |
[edit] Overview
BMP is a simple image format developed by Microsoft. The colordepth wary between 2 (1-bit), 16 (4-bit), 256 (8-bit), 16-bit and 24-bit. The image is usually not compressed, but it might be compressed with the RLE algorothm. This tutorial will cover how to read pixels from a BMP image into an 2-dimensional array.
[edit] File format
[edit] File header
| Offset | Bytes | Description | C/C++ datatype |
|---|---|---|---|
| 0x00 - 0x01 | 2 | This bytes must contain the ASCII character 'B' and 'M' | Char |
| 0x02 - 0x05 | 4 | Size of the file in bytes | Integer |
| 0x06 - 0x07 | 4 | Reserved, must be zero | |
| 0x08 - 0x09 | 4 | Reserved, must be zero | |
| 0x0A - 0x0D | 4 | Offset to pixeldata | Integer |
[edit] Image header
| Offset | Bytes | Description | C/C++ datatype |
|---|---|---|---|
| 0x0E - 0x11 | 4 | Size of the image header, must be 40 (0x28) | Integer |
| 0x12 - 0x15 | 4 | Image width in pixels | Integer |
| 0x16 - 0x19 | 4 | Image height in pixels | Integer |
| 0x1A - 0x1B | 4 | Nr of planes, must be one | Integer |
| 0x1C - 0x1D | 4 | Bits per pixel, must be 1,2,4,8,16,24 or 32 | Integer |
| 0x1E - 0x21 | 4 | Compression
0 = No compression 1 = RLE compression for 8bit bitmaps 2 = RLE compression for 4bit bitmaps Integer Following fields may be ignored most of the time. They is used to describe and store the palette. || | |
| 0x22 - 0x25 | 4 | Size of image data, may be zero if no compression is used | Integer |
| 0x26 - 0x29 | 4 | Horizontal resolution of the image | Integer |
| 0x2A - 0x2D | 4 | Vertical resolution of the image | Integer |
| 0x2E - 0x31 | 4 | Number of color indexes actually used, if set to zero all colors is used | Integer |
| 0x32 - 0x35 | 4 | Nr of colors indexes required to render the image, if set to zero all color is used | Integer |
| 0x36 - | 4 | Optional: This part may contain the palette used by the image.
The format is RGBx (x is 1 byte reserved, must be set to zero) || |
[edit] Reading the header
The first step to read our image is to read its header to find out its size,bits-per-pixel and encoding. We will begin by making a simple struct to hold our data and a couple of enumerations for eventual errors. Lets start with struct.
typedef struct Bitmap {
int offset;
int width;
int height;
int bpp;
int encoding;
int size;
bool loaded;
unsigned char* pData;
};
For now this is all we need to store, but we will add more later. I don't think any of these need any further explanation.
enum BITMAP_RESULTS {
BMP_OK,
BMP_NO_FILE,
BMP_INVALID_HEADER,
BMP_OUT_OF_MEMORY,
BMP_UNSUPPORTED,
BMP_LOADED,
};
The first enum simply indicates everythings good soo far. BMP_NO_FILE means the file could not be opened, most likely the file doesn't exist but it might be permission error. BMP_INVALID_HEADER tells us the file isn't a valid BMP file, either it doesn't start with BM or the length is wrong. BMP_OUT_OF_MEMORY is self explanary. BMP_UNSUPPORTED is going to be used when the bpp has weired modes and/or encodings. The last one, BMP_LOADED, is used when there is already a bitmap loaded.
In order to read the header we first need to load the file into memory:
#include <fstream>
using namespace std;
int loadBMP(Bitmap* img,char* filename){
ifstream::pos_type size
ifstream file(filename, ios::in|ios::binary|ios::ate);
if(file.is_open()){
size = file.tellg();
memblock = new char [size];
file.seekg (0, ios::beg);
file.read (memblock, size);
file.close();
}
}
[edit] Loading 8-bit monocrome image
TBD
[edit] Loading 24-bit truecolor image
TBD
[edit] Summary
TBD

