How do I create a 24-bpp DDB from a DIB?

I want to create a 24-bpp DDB from a DIB (the DIB is of an unknown pixel depth - it could be anywhere from monochrome to true-color). My intention is to have a quick n' dirty way to extract the data from a BMP file in RGB format without having to parse the RGB data myself.

So, a simple way to do this is:
* Load the BMP data into memory
* Use CreateDIBitmap() to create a display-compatible DDB that contains the data from the BMP file.
* Use GetDIBits() to grab a scanline's worth of data in 24bpp format.

Now the only problem is that if the display is not true-color (say, you are running a 256-color display), you may lose color information when you call CreateDIBitmap() - it will map the DIB data to the closest entry in the display palette.

So, what I'd really like to do is create a 24-bpp DDB directly from the DIB I read in from the BMP file. I can't figure out how to do this - the closest I've come is like so:

    // Create an uninitialized bitmap, with the specified size and 24-bpp
    // color depth.
    HBITMAP hbm = CreateBitmap(infoHeader->biWidth, abs(infoHeader->biHeight),
                        1, 24,  // # planes, # bits per pixel
                        NULL);

    // Create a DC that is compatible with the display DC
    HDC hdc = GetDC(hwin);
    HDC hdcMem = CreateCompatibleDC(hdc);
    ReleaseDC(hwin, hdc);

    // Select our 24-bit bitmap into the memory DC, which I'm hoping will make
    // it into a 24-bpp DC.
    SelectObject(hdcMem, hbm);

    // Now create our DDB - hopefully it will be 24-bpp
    bitmap = CreateDIBitmap(hdcMem, infoHeader, CBM_INIT, bits, (BITMAPINFO *) infoHeader, DIB_RGB_COLORS);

This *almost* works, but the bitmap created by CreateDIBitmap in this case is *monochrome*. If I use GetDIBits() to fill in a BitmapInfoHeader for it, it shows that it has only 1 bpp. It has all the data that the original BMP file has, but it's been converted to B&W.

So, please help! What am I doing wrong? I do *not* want to have to parse through the BMP file myself to extract RGB values, as supporting all the different bit depths and compression algorithms is more of a pain than I require.

Thanks in advance!

Drew
bigdrewAsked:
Who is Participating?
I wear a lot of hats...

"The solutions and answers provided on Experts Exchange have been extremely helpful to me over the last few years. I wear a lot of hats - Developer, Database Administrator, Help Desk, etc., so I know a lot of things but not a lot about one thing. Experts Exchange gives me answers from people who do know a lot about one thing, in a easy to use platform." -Todd S.

bigdrewAuthor Commented:
One possible avenue I've come across is to use LoadImage(), passing LR_LOADFROMFILE and LR_CREATEDIBSECTION to load the file into a DIBSection. Possibly this would return a DDB that I can use GetDIBits() with?
0
chensuCommented:
It doesn't make sense to create such a DDB. Since it is a DDB, it is device dependent, meaning that its format follows the current display device. What you really want seems to create a 24-bit DIB.

Please give more details about what you are doing so that we can find a solution for you.
0
bigdrewAuthor Commented:
Yes, that's another way to look at it - I want to create a 24-bit DIB from a BMP file that is of an arbitrary color depth. My goal is to extract the data from a BMP file one scanline at a time in 24-bit RGB format, without having to parse the BMP file format, deal with compression, etc.

Or, if I can create a DDB that is of the same color depth as the BMP file, then I can use GetDIBits() to extract the data in 24-bit format -- I don't care what the actual format of the DDB is, since GetDIBits() will give me the data in RGB format.
0
Introduction to Web Design

Develop a strong foundation and understanding of web design by learning HTML, CSS, and additional tools to help you develop your own website.

bigdrewAuthor Commented:
Yes, that's another way to look at it - I want to create a 24-bit DIB from a BMP file that is of an arbitrary color depth. My goal is to extract the data from a BMP file one scanline at a time in 24-bit RGB format, without having to parse the BMP file format, deal with compression, etc.

Or, if I can create a DDB that is of the same color depth as the BMP file, then I can use GetDIBits() to extract the data in 24-bit format -- I don't care what the actual format of the DDB is, since GetDIBits() will give me the data in RGB format.
0
chensuCommented:
Download the following sample, which contains dib.h and dib.c. There is a function named ChangeDIBFormat you can use to change a DIB to your desired format.

SeedIB.exe Shows 16 and 32 Bits-Per-Pel Bitmap Formats
http://support.microsoft.com/support/kb/articles/Q94/3/26.ASP
0

Experts Exchange Solution brought to you by

Your issues matter to us.

Facing a tech roadblock? Get the help and guidance you need from experienced professionals who care. Ask your question anytime, anywhere, with no hassle.

Start your 7-day free trial
bigdrewAuthor Commented:
Thanks for the pointer. This gave me the info I needed.

What I ended up doing was calling CreateDIBSection() to create a DIB of the same format as the BMP file, then reading the BMP file data into the buffer that CreateDIBSection() returned to hold the color data. I can then use the HBITMAP returned by CreateDIBSection() with GetDIBits() to get 24-bit data.

0
It's more than this solution.Get answers and train to solve all your tech problems - anytime, anywhere.Try it for free Edge Out The Competitionfor your dream job with proven skills and certifications.Get started today Stand Outas the employee with proven skills.Start learning today for free Move Your Career Forwardwith certification training in the latest technologies.Start your trial today
Microsoft Development

From novice to tech pro — start learning today.