How do you get the RGB values from a Bitmap on Android?

57,159

Solution 1

This may be slightly late, but to clear up the confusion with the use of &0xff:

In Java ints are 32 bits, so the (A)RGB values for each pixel are packed in 4 bytes. In other words, a pixel with the values R(123), G(93), B(49) = FF7B 5D31 in the ARGB_8888 model. Where Alpha = FF, R = 7B, G = 5D, B = 31. But this is stored as an int as -8692431.

So, to extract the Green value from -8692431, we need to shift the 5D by 8 bits to the right, as you know. This gives 00FF 7B5D. So, if we were just to take that value we would be left with 16743261 as our Green value. Therefore, we bitwise-and that value with the mask of 0xFF (which is equivalent to 0000 00FF) and will result in 00FF 7B5D being 'masked' to 0000 005D. So we have extracted our Green value of 5D (or 93 decimal).

We can use the same mask of 0xFF for each extraction because the values have all been shifted to expose the desired two bytes as the least significant. Hence the previously suggested code of:

int p = pixel[index];

int R = (p >> 16) & 0xff;
int G = (p >> 8) & 0xff;
int B = p & 0xff;

If it makes it clearer, you can perform the equivalent operation of:

int R = (p & 0xff0000) >> 16;
int G = (p & 0x00ff00) >> 8;
int B = (p & 0x0000ff) >> 0;

For brevity, the extra 0s can be dropped, and it can be written as

int R = (p & 0xff0000) >> 16;
int G = (p & 0xff00) >> 8;
int B = p & 0xff;

Note however, that alternative colour models may be used, such as RGB_555 which stores each pixel as just 2 bytes, with varying precision for the RGB channels. So you should check the model that your bitmap is using before you perform the extraction, because the colours may be stored differently.

Solution 2

Bitmap#getPixel(x, y) returns an int with the colour values and alpha value embedded into it.

int colour = bitmap.getPixel(x, y);

int red = Color.red(colour);
int green = Color.green(colour);
int blue = Color.blue(colour);
int alpha = Color.alpha(colour);

Solution 3

This is how I am trying to get that value. Use bitmap.getPixel() to get the corresponding bitmap in integer array. By using bitwise rotation operation, we will get RGB values.

             int[] pix = new int[picw * pich];
             bitmap.getPixels(pix, 0, picw, 0, 0, picw, pich);

             int R, G, B,Y;

             for (int y = 0; y < pich; y++){
             for (int x = 0; x < picw; x++)
                 {
                 int index = y * picw + x;
                 int R = (pix[index] >> 16) & 0xff;     //bitwise shifting
                 int G = (pix[index] >> 8) & 0xff;
                 int B = pix[index] & 0xff;

                 //R,G.B - Red, Green, Blue
                  //to restore the values after RGB modification, use 
 //next statement
                 pix[index] = 0xff000000 | (R << 16) | (G << 8) | B;
                 }}

Solution 4

Arbitrary Bitmap Color Handling

You can read about the various Color methods here that will extract the components of color from a pixel int.

You might want to apply a filter to the bitmap, and return a byte array. Otherwise, you can cut this example down to the for-loop and roll through the pixels generating your array of bytes.

private byte[] rgbValuesFromBitmap(Bitmap bitmap)
{
    ColorMatrix colorMatrix = new ColorMatrix();
    ColorFilter colorFilter = new ColorMatrixColorFilter(
            colorMatrix);
    Bitmap argbBitmap = Bitmap.createBitmap(bitmap.getWidth(), bitmap.getHeight(),
            Bitmap.Config.ARGB_8888);
    Canvas canvas = new Canvas(argbBitmap);

    Paint paint = new Paint();

    paint.setColorFilter(colorFilter);
    canvas.drawBitmap(bitmap, 0, 0, paint);

    int width = bitmap.getWidth();
    int height = bitmap.getHeight();
    int componentsPerPixel = 3;
    int totalPixels = width * height;
    int totalBytes = totalPixels * componentsPerPixel;

    byte[] rgbValues = new byte[totalBytes];
    @ColorInt int[] argbPixels = new int[totalPixels];
    argbBitmap.getPixels(argbPixels, 0, width, 0, 0, width, height);
    for (int i = 0; i < totalPixels; i++) {
        @ColorInt int argbPixel = argbPixels[i];
        int red = Color.red(argbPixel);
        int green = Color.green(argbPixel);
        int blue = Color.blue(argbPixel);
        rgbValues[i * componentsPerPixel + 0] = (byte) red;
        rgbValues[i * componentsPerPixel + 1] = (byte) green;
        rgbValues[i * componentsPerPixel + 2] = (byte) blue;
    }

    return rgbValues;
}

Solution 5

One for statement less :D

imagen.getPixels(pix, 0, picw, 0, 0, picw, pich);

    for (i = 0; i < pix.length; i++) {
        r = (pix[i]) >> 16 & 0xff;
        g = (pix[i]) >> 8 & 0xff;
        b = (pix[i]) & 0xff;
    }
Share:
57,159
barzos
Author by

barzos

Updated on January 20, 2022

Comments

  • barzos
    barzos over 2 years

    I want to get RGB values of a Bitmap on Android but I can't do this so far. My aim is to obtain RGB values for each pixel of a Bitmap. Is there any specific function for Android or anything else?

    Also I wonder that do I need colorMatrix() function?

    It is very important for my project.

  • barzos
    barzos about 13 years
    thanks but whats the meaning of &0xff because ff=11111111. &(and operation) get the same number with 11111 because 0&1=1 1&1=1 all the time. int R = (pix[index] >> 16) Is enough to obtain R ?
  • barzos
    barzos about 13 years
    thanks but whats the meaning of &0xff because ff=11111111. &(and operation) get the same number with 11111 because 0&1=1 1&1=1 all the time. int R = (pix[index] >> 16) Is enough to obtain R ?
  • Rizwan Ahmed
    Rizwan Ahmed almost 9 years
    A very easy way to calculate the pixel color values. Thanks a lot man !
  • fWd82
    fWd82 almost 6 years
    Hello @Cameron Lowell Palmer can you please answer this question. I think I am not defining boundries to click event. As when I click on top left corner it works, but when I click on other corners the app crashes. Please help.
  • topher217
    topher217 about 3 years
    Is there any reason R, G, and B cannot be bytes rather than ints?
  • typedecker
    typedecker about 3 years
    Thanks this works like a charm and explains both on how to extract the rgb vals and then process them accordingly.