Click here to Skip to main content
Click here to Skip to main content

Image Bit depth conversion from 32 Bit to 8 Bit

By , 20 May 2004
 

Introduction

This article describes about image bit depth conversion from 32 bit to 8 bit. There are several methods for conversion. In this article, Indexed color and palette are used.

32 Bit to 8 Bit Conversion

There are several methods to convert to indexed color. Some methods are Dithering, Nearest Color, Adaptive or Optimized or Perceptual Palette, Standard Web Browser Palette etc. Here I am describing about Standard Web Browser Palette.

The Standard Palette (often called Web palette) always contains the same colors for any image. It is sometimes called 6-6-6, because it contains six standard evenly spaced colors for each of Red, Green, and Blue. Those 6x6x6 color combinations create 6x6x6 = 216 standard color combinations, which are used for any image.

The Standard Palette always contains combinations of the following 6 tones for each of the Red, Green, Blue primaries:

The 216 combinations of these 18 colors above (six shades of the three RGB colors, 6x6x6 = 216) produce the Standard web-safe palette. This Standard web-safe palette color shades are shown below:

Sample screenshot

First, we define a standard color table using those 6 colors.

const DWORD STANDARD_PALETTE[] = {00,51,102,153,204,255}
const INT STANDARD_COLOR_SIZE = 6;
const INT STANDARD_PALETTE_VAL_DIF = 51; 
// difference between two consecutive standard color Palette.

For 8 bit conversion, we must create a color table which is called as Palette color map. All possible combinations of Standard palette colors are entries in this table. Palette color map creation is shown below:

DWORD dwColorMapTable[216] = {0};
int  nColorMapIdx = 0;
for (int nBlueIdx = 0; nBlueIdx < STANDARD_COLOR_SIZE; ++nBlueIdx)
{
    for(int nGreenIdx = 0; nGreenIdx < STANDARD_COLOR_SIZE; ++nGreenIdx)
    {
        for(int nRedIdx = 0; nRedIdx < STANDARD_COLOR_SIZE; ++nRedIdx)
        {
            RGBQUAD objColor;
            objColor.rgbRed    = STANDARD_PALETTE[nRedIdx];
            objColor.rgbGreen = STANDARD_PALETTE[nGreenIdx];
            objColor.rgbBlue = STANDARD_PALETTE[nBlueIdx];
            objColor.rgbReserved = 0;
            memcpy(&dwColorMapTable[nColorMapIdx],&objColor,sizeof(RGBQUAD));
            ++nColorMapIdx;
        }
    }
}

After that, we can convert a 32 bit image file to 8 bit image file. For conversion, read each pixel data from input image data. Get Red, Green and Blue values from pixel. With these RGB values, calculate suitable color from STANDARD_PALETTE. Find suitable color from the Palette color map table. Set table map entry index to the output pixel value.

Cstring csInputFileName = "c:\\32BitImage.bmp";
Bitmap InputImage(csInputFileName,FALSE);
INT nImageHeight = InputImage .GetHeight();
INT nImageWidth = InputImage .GetWidth();
INT nPixelSize = nImageHeight * nImageWidth;
BYTE byBitsPerPixel = 32; // Input image Bits per pixel.
BYTE pixels = new BYTE[nPixelSize];
for(UINT nRow = 0; nRow < nImageHeight; ++nRow)
{
    for(UINT nCol = 0; nCol < nImageWidth; ++nCol)
    {
        Color objColorData;
        UINT i8bppPixel = nRow * nImageWidth + nCol;
        // Get pixel data from Input image.
        if(Ok != InputImage GetPixel(nCol,nRow,&objColorData))
        {
            printf("Get Image Pixel Failed.\n")
        }
        // Get RGB value from color data.
        int nRed = objColorData.GetRed();
        int nGreen = objColorData.GetGreen();
        int nBlue = objColorData.GetBlue();
        // Get Index of suitable color data in the palette table.
        UINT uRedValue = GetPixelValue(objColorData.GetRed());
        UINT uGreenValue = GetPixelValue(objColorData.GetGreen());
        UINT uBlueValue = GetPixelValue(objColorData.GetBlue());

        // Calculate Pixel color position
        // in the color map table using RGB values. 
        // Finally set this index in to the pixel data.
        UINT uPalettePos = uBlueValue*36+uGreenValue*6+uRedValue;
        pixels[i8bppPixel] =(BYTE)uPalettePos;
    }
}

GetPixelValue() returns appropriate pixel index value in the Standard Palette table. Implementation is shown below:

UINT GetPixelValue(UINT uPixelValue_i)
{
    UINT uRetValue = 0;
    UINT uPos = uPixelValue_i / PALETTE_VAL_DIF;
    if(0 == uPixelValue_i % PALETTE_VAL_DIF)
    {
        uRetValue = uPixelValue_i/PALETTE_VAL_DIF;
    }
    else
    {
        if(abs(uPixelValue_i - STANDARD_PALETTE [uPos]) > 
           abs(uPixelValue_i - STANDARD_PALETTE [uPos+1]))
        {
            uRetValue = uPos+1;
        }
        else
        {
            uRetValue = uPos;
        }
    }
    return uRetValue;
}

For viewing converted image:

  1. Create an output file.
  2. Write Bitmap header to the output file.
  3. Write pixel data to the output file.
  4. Close output file.

Good luck!

License

This article, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)

About the Author

Shanu K S
Software Developer NeST
India India
No Biography provided

Sign Up to vote   Poor Excellent
Add a reason or comment to your vote: x
Votes of 3 or less require a comment

Comments and Discussions

 
Hint: For improved responsiveness ensure Javascript is enabled and choose 'Normal' from the Layout dropdown and hit 'Update'.
You must Sign In to use this message board.
Search this forum  
    Spacing  Noise  Layout  Per page   
Generalpixel datamembersandeeprattu1-Jul-09 21:18 
Questionconvert 16 bit to 8 bit?memberharshi_mm214-Feb-08 0:34 
GeneralConversion of 16 bit to 8 bit or 24 bitmemberharshi_mm211-Feb-08 22:25 
GeneralConversion from 8-bit to 32-bitmemberNilesh Kontamwar17-Jul-07 1:30 
GeneralRe: Conversion from 8-bit to 32-bitmemberNilesh Kontamwar22-Jul-07 18:08 
Generalexception:-array index out of boundsmemberPlatinumhimani27-Nov-06 20:37 
GeneralRe: exception:-array index out of boundsmemberShanu K S29-Nov-06 17:18 
GeneralMissing parts of the code...memberdesi_nerd19-Aug-06 3:07 
GeneralRe: Missing parts of the code... [modified]membernpkinh19-Feb-08 15:11 
GeneralHelp plz.........very urgentmemberAshwini Iyengar25-Mar-05 22:07 
GeneralErm...memberChristian Graus3-Mar-05 13:41 
GeneralRe: Erm...memberTeashirt219-Oct-07 9:50 
GeneralCreating Imagememberseasons1593-Mar-05 12:35 
Generalnon-aligned DWORD image widthmemberTHollande28-Jul-04 23:15 
GeneralRe: non-aligned DWORD image widthmembernpkinh19-Feb-08 15:25 
Generalsample screen shotmemberRabidCow21-May-04 12:18 
GeneralRe: sample screen shotmemberShanuKS23-May-04 18:43 
GeneralCQuantizermemberKochise21-May-04 4:05 

General General    News News    Suggestion Suggestion    Question Question    Bug Bug    Answer Answer    Joke Joke    Rant Rant    Admin Admin   

Permalink | Advertise | Privacy | Mobile
Web02 | 2.6.130617.1 | Last Updated 21 May 2004
Article Copyright 2004 by Shanu K S
Everything else Copyright © CodeProject, 1999-2013
Terms of Use
Layout: fixed | fluid