Verify Android Bitmap is GrayScale

淺唱寂寞╮ 提交于 2019-12-13 12:37:24

问题


I got a doubt. When I obtain the pixels from a Bitmap in Android. I've got an image loaded inside it, this image is a grayscale image. If I make a getPixels() and check the values I can see values with R != G != B.

I think I can check if it's grayscale if the values of the three slides (R, G and B) got the same value, but I couldn't be possible. There is a way to verify it?

Lots of thanks!


回答1:


Let first off say that there are a couple of ways of accomplishing this.

I would say get the size of the image using (something like)

int myHeight = myImage.getHeight();
int myWidth  = myImage.getWidth();

I would say in this case you may also want to verify the Bitmap' config as it could be one of 3 different formats

ALPHA_8, ARGB_8888, or RGB_565

You get the configuration using the

myImage.getConfig()

routine. We will get back to how this should be used later.

Now that you know the size of the image you should run a dual loop structure as follows:

boolean isGrayscaleImage = true;  // assume it is grayscale until proven otherwise

for(int i = 0; i < myWidth; i++){
    for(int j = 0; j < myHeight; j++){
        int currPixel = myImage.getPixel(i, j);

        if( false == isGrayScalePixel(currPixel) ){
            isGrayscaleImage = false;
            break;
        }
    }
}

Back to HOW TO TEST IF THE PIXEL IS GRAYSCALE: If the image is stored as ALPHA_8 it really isn't a grayscale image, but it could technically be converted to one by turning the image into an ARGB_8888 image and setting the Alpha value to 0xFF and each of the R, G, and B components to the alpha value provided within the original 8 bit ALPHA_8 based image.

If the image is RGB_565 formatted, this is a bit trickier as you will have to pull apart the R, G, and B values into their own bytes by yourself using shift and MASKING operators. Once you have done this, it is essentially like processing the ARGB_8888 image (talked about below).

For the ARGB_8888 image: the alpha channel SHOULD always be 0xFF.

As you stated in your question a pixel is considered grayscale if R == G == B SO (Sample Code Might Look As Follows)

boolean isGrayScalePixel(int pixel){
    int alpha = (pixel && 0xFF000000) >> 24;
    int red   = (pixel && 0x00FF0000) >> 16;
    int green = (pixel && 0x0000FF00) >> 8;
    int blue  = (pixel && 0x000000FF);

    if( 0 == alpha && red == green && green == blue ) return true;
    else return false;

}

There are optimizations that could be made, but I am trying to document the main algorithm for you.

Hope this helps you out :-)




回答2:


Note the use of && (boolean AND) when masking should be a single & (bitwise AND) as below:

int alpha = (pixel & 0xFF000000) >> 24;
int red   = (pixel & 0x00FF0000) >> 16;
int green = (pixel & 0x0000FF00) >> 8;
int blue  = (pixel & 0x000000FF);



回答3:


If all you have to do is check whether the R,G and B values are the same then just do it using Colors.red(), Colors.green() or Colors.blue().

Here is a small portion of the actual code.

for(int x=0;x< bmp.getWidth();x++) {
    for(int y=0;y< bmp.getHeight();y++) {    

        int pixel=bmp.getPixel(x,y);
        int alpha=Color.alpha(pixel);            
        int gray_color=Color.red(pixel);         
        int gray_color1=Color.green(pixel);

        //int gray_color=pixel&0x000000ff;
        //int gray_color1=(pixel&0x0000ff00)>>8;
        //int gray_color2=(pixel&0x00ff0000)>>16;
        //int gray_color3=Math.abs((pixel&0xff000000))>>24;

        int pixels= (int)Math.pow(gray_color,gamma);
        k.add(""+alpha+" "+gray_color+" "+gray_color1);
        bmp.setPixel(x,y,Color.argb(alpha,pixels,pixels,pixels));
    }
}

You can see I have commented the shifting and masking part.



来源:https://stackoverflow.com/questions/10957348/verify-android-bitmap-is-grayscale

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