Reading BMP file C++ (trouble with reading BMP header)

ぐ巨炮叔叔 提交于 2021-02-07 10:30:04

问题


I am trying to write BMP image class with reading method. I saw msdn specification of BMP files, so I try to read the headers and after, using the biHeight and biWidth information, read RGB info of every pixel. So, it don't read header information, the value of every header parameter is -1.

Here's code:

#ifndef BMP_IMAGE_H
#define BMP_IMAGE_H

#include <fstream>

using namespace std;


typedef struct
{
    unsigned int    bfType;
    unsigned long   bfSize;
    unsigned int    bfReserved1;
    unsigned int    bfReserved2;
    unsigned long   bfOffBits;
} BitMapFileHeader;

typedef struct
{
    unsigned int    biSize;
    int             biWidth;
    int             biHeight;
    unsigned short  biPlanes;
    unsigned short  biBitCount;
    unsigned int    biCompression;
    unsigned int    biSizeImage;
    int             biXPelsPerMeter;
    int             biYPelsPerMeter;
    unsigned int    biClrUsed;
    unsigned int    biClrImportant;
} BitMapInfoHeader;

typedef struct
{
    int   rgbBlue;
    int   rgbGreen;
    int   rgbRed;
    int   rgbReserved;
} RGBColor;


class BMPImage
{
private:
    unsigned short read_u16();
    unsigned int   read_u32();
    int            read_s32();
public:
    ifstream pFile;
    int imageWidth;
    int imageHeight;
    RGBColor **rgb;
    BMPImage(char* fileName);
    void pixelsInfo();
};

#endif // BMP_IMAGE_H

#include "bmp_image.h"
#include <iostream>
using namespace std;
BMPImage::BMPImage(char* fileName)
{
     ifstream pFile(fileName, ios::in | ios::binary);


     // read the header of file
     BitMapFileHeader header __attribute__((unused));

     header.bfType      = read_u16();
     header.bfSize      = read_u32();
     header.bfReserved1 = read_u16();
     header.bfReserved2 = read_u16();
     header.bfOffBits   = read_u32();

     // read the header of image
     BitMapInfoHeader bmiHeader;

     bmiHeader.biSize          = read_u32();
     bmiHeader.biWidth         = read_s32();
     bmiHeader.biHeight        = read_s32();
     bmiHeader.biPlanes        = read_u16();
     bmiHeader.biBitCount      = read_u16();
     bmiHeader.biCompression   = read_u32();
     bmiHeader.biSizeImage     = read_u32();
     bmiHeader.biXPelsPerMeter = read_s32();
     bmiHeader.biYPelsPerMeter = read_s32();
     bmiHeader.biClrUsed       = read_u32();
     bmiHeader.biClrImportant  = read_u32();

     cout << (int)bmiHeader.biHeight <<"\n";
     RGBColor **rgb = new RGBColor*[bmiHeader.biHeight];
     for (int i = 0; i < bmiHeader.biWidth; i++)
            rgb[i] = new RGBColor[bmiHeader.biHeight];

     for (int i = 0; i < bmiHeader.biWidth; i++) {
         for (int j = 0; j < bmiHeader.biHeight; j++) {
            rgb[i][j].rgbBlue = pFile.get();
            rgb[i][j].rgbGreen = pFile.get();
            rgb[i][j].rgbRed = pFile.get();


         }


         char temp;
         pFile.get(temp);
      }

     imageWidth = bmiHeader.biWidth;
     imageHeight = bmiHeader.biHeight;

     pFile.close();
}

unsigned short BMPImage::read_u16(){
    unsigned char b0, b1;
    b0 = pFile.get();
    b1 = pFile.get();

    return ((b1 << 8) | b0);
}

unsigned int BMPImage::read_u32(){
    unsigned char b0, b1, b2, b3;
    b0 = pFile.get();
    b1 = pFile.get();
    b2 = pFile.get();
    b3 = pFile.get();

    return ((((((b3 << 8) | b2) << 8) | b1) << 8) | b0);
}

int BMPImage::read_s32(){
        unsigned char b0, b1, b2, b3;
        b0 = pFile.get();
        b1 = pFile.get();
        b2 = pFile.get();
        b3 = pFile.get();
        return ((int)(((((b3 << 8) | b2) << 8) | b1) << 8) | b0);

}

void BMPImage::pixelsInfo(){
    for (int i = 0; i < imageWidth; i++) {
            for (int j = 0; j < imageHeight; j++) {
                std::cout << rgb[i][j].rgbRed <<" " << rgb[i][j].rgbGreen << " " << rgb[i][j].rgbBlue << std::endl;
            }
            std::cout << std::endl;
        }
}

P.S. Thank you everybody for help


回答1:


The member

ifstream pFile;

of class BMPImage is not being initialized, so when you use it in member functions it isn't valid. Instead you are locally defining a different pFile instance in the constructor. These should probably be the same instance.




回答2:


I think you should change this:

typedef struct
{
    int   rgbBlue;
    int   rgbGreen;
    int   rgbRed;
    int   rgbReserved;
} RGBColor;

For this:

typedef struct
{
    unsigned char rgbBlue;
    unsigned char rgbGreen;
    unsigned char rgbRed;
    unsigned char rgbReserved;
} RGBColor;

Reference: https://msdn.microsoft.com/en-us/library/windows/desktop/dd162938(v=vs.85).aspx



来源:https://stackoverflow.com/questions/22112412/reading-bmp-file-c-trouble-with-reading-bmp-header

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!