Thread: bitmap images

  1. #1
    Registered User
    Join Date
    Apr 2008
    Posts
    204

    bitmap images

    Hi guys. So I am making progess understanding file manipulation in c++. My ultimate plan is to make a program that can find one image within another in 24 bit color bitmaps.
    I have been reading BMP file format - Wikipedia, the free encyclopedia for info on bitmaps.
    My first question is about the output of my pixel array.
    This is my current method of saving it and printint it out:
    Code:
    void change2Negative(fstream &dFile, Image &dInfo)
    {
        int pixel[dInfo.imageWidth][dInfo.imageHeight];
        for(int i = 0; i < dInfo.imageWidth; i++)
        {
             for(int j = 0; j < dInfo.imageHeight; j++)
             {
                 dFile.seekg(dInfo.offSet + i);
                 dFile.read(reinterpret_cast<char *>(&pixel[i][j]), sizeof(pixel));
                 cout << pixel[i][j] << ",";
             }
             cout <<","<< endl;
        }
    }
    This outputs large numbers, positive or negative. TBH I didnt expect them to be negative, but I suppose the values are signed?
    Anyway. I am wanting to compare to images, so I suppose I dont need to break that into the RGB values (which for bitmaps appear to be BGR)?
    So for an algorithm that find one image (image A) inside another(image B), is the best way to go along each pixel in B, until I find the value of the first pixel in A, then check what the value of pixel 2 is in A, and see if the next pixel in B is that number - keep doing that until the end of the line in A, and then jump to next line and continue checking. If a pixel doesnt match, reset back to the first pixel in A and continue checking in B?
    What does anyone think?

  2. #2
    Algorithm Dissector iMalc's Avatar
    Join Date
    Dec 2005
    Location
    New Zealand
    Posts
    6,318
    Whether the values appear signed or not is not to do with what is in the file, it is to do with what you are printing them from. In this instance you have read them into an array of int. When cout is given an int, it knows that means a signed value, and outputs the value accordingly. If you want to show undigned values, then make your array of unsigned ints.

    Having said that, to be honest, your images probably aren't stored as 32-bits per pixel. At best they are probably 24-bits per pixel, so an array of ints is the wrong size to begin with. That and reading sizeof(pixel) inside nested loops is outrageously wrong. At most you want sizeof(pixel[0][0]), but I strongly advise doing just one single read up front of the whole image, or at least only one read per scanline.
    My homepage
    Advice: Take only as directed - If symptoms persist, please see your debugger

    Linus Torvalds: "But it clearly is the only right way. The fact that everybody else does it some other way only means that they are wrong"

  3. #3
    Registered User
    Join Date
    Apr 2008
    Posts
    204
    Thanks iMalc, everything you write makes sense.
    So just to clarify, if I have the number 127 and I put it in a signed integer, if will come out as zero? Regardless of the fact that in the original file it was 127?
    Over the 24 bit thing, yeah I was wondering whether I needed to unsign it, and then break it into three bytes, rather than what currently seems like one large number - but actually to compare two images that isnt going to make the difference...Yeah you are right BTW it is 24 bit bitmaps.
    Reading around, I should be making an array like:
    Code:
    std::vector<std::bitset<24> > pixel;
    or
    Code:
    struct ThreeBytes {
        uint32_t value:24;
    };
    Then declaring a new one like:
    Code:
    ThreeBytes *pixel= new ThreeBytes[dInfo.imageWidth][dInfo.imageHeight];
    However that gives me this error:
    error: 'dInfo' cannot appear in a constant-expression
    Yeah, I can see why reading sizeof(pixel) is so wrong. Have made a variable at the start that is the size now...

    EDIT:
    I think from rechecking the bitmpa format, each pixel maybe 32 bit because the last byte is padding...
    So in other words I need to break it down to bytes (4 of them) and display only the first three?

    So I have changed my method to this:
    Code:
    void displayPixelData(fstream &dFile, Image &dInfo)
    {
    
        unsigned int pixel[dInfo.imageWidth][dInfo.imageHeight];
        unsigned char bytes[4];
        int imageSize = sizeof(pixel[0][0]);
        for(int i = 0; i < dInfo.imageWidth; i++)
        {
            for(int j = 0; j < dInfo.imageHeight; j++)
            {
                dFile.seekg(dInfo.offSet + i);
                dFile.read(reinterpret_cast<char *>(&pixel[i][j]), imageSize);
                bytes[0] = (pixel[i][j] >> 24) & 0xFF;
                bytes[1] = (pixel[i][j] >> 16) & 0xFF;
                bytes[2] = (pixel[i][j] >> 8) & 0xFF;
                bytes[3] = pixel[i][j] & 0xFF;
                printf("%x %x %x %x", bytes[0], bytes[1], bytes[2], bytes[3]);
                //cout << pixel[i][j] << ",";
            }
            cout <<","<< endl;
        }
    Does that improve things?
    Last edited by a.mlw.walker; 09-23-2012 at 04:20 AM. Reason: Made some changes...

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. Replies: 0
    Last Post: 03-16-2012, 09:59 AM
  2. Something \a images
    By C++Child in forum C++ Programming
    Replies: 9
    Last Post: 07-23-2004, 10:32 PM
  3. Images
    By krappykoder in forum Game Programming
    Replies: 2
    Last Post: 08-01-2002, 03:28 PM
  4. Mearging two bitmap images
    By Jeff in forum Game Programming
    Replies: 2
    Last Post: 06-18-2002, 09:28 PM
  5. MFC Bitmap Images
    By westie in forum C Programming
    Replies: 0
    Last Post: 12-13-2001, 10:07 AM