简体   繁体   中英

How to get color from specific area in an Image in C#

I am trying to get color from specific area in an Image. 在此处输入图片说明

Assume that , this is image , and I want to get color inside image.(the result should be red of the above image) This color may be different position in image. Because I don't know exact position of color where it starting, so I can't get exact result.

Until now, I cropped image giving manually position of x and y, and then cropped image and I got average color of cropped image. But I know , this is not exact color.

What I tried :

private RgbDto GetRGBvalueCroppedImage(Image croppedImage)
        {
        var avgRgb = new RgbDto();
        var bm = new Bitmap(croppedImage);


        BitmapData srcData = bm.LockBits(
            new Rectangle(0, 0, bm.Width, bm.Height),
            ImageLockMode.ReadOnly,
            PixelFormat.Format32bppArgb);

        int stride = srcData.Stride;

        IntPtr Scan0 = srcData.Scan0;

        long[] totals = new long[] { 0, 0, 0 };

        int width = bm.Width;
        int height = bm.Height;

        unsafe
        {
            byte* p = (byte*)(void*)Scan0;

            for (int y = 0; y < height; y++)
            {
                for (int x = 0; x < width; x++)
                {
                    for (int color = 0; color < 3; color++)
                    {
                        int idx = (y * stride) + x * 4 + color;

                        totals[color] += p[idx];
                    }
                }
            }
        }

        avgRgb.avgB = (int)totals[0] / (width * height);
        avgRgb.avgG = (int)totals[1] / (width * height);
        avgRgb.avgR = (int)totals[2] / (width * height);

        return avgRgb;
    }

How can I get exact position to crop? May be I can convert image to byte array, then I can find different color and take position of it and then crop. But I have no clue how do this.

You can use something this extension method to get dominant color in a region of an image in case they are not all the same

public static Color GetDominantColor(this Bitmap bitmap, int startX, int startY, int width, int height) {

    var maxWidth = bitmap.Width;
    var maxHeight = bitmap.Height;

    //TODO: validate the region being requested

    //Used for tally
    int r = 0;
    int g = 0;
    int b = 0;
    int totalPixels = 0;

    for (int x = startX; x < (startX + width); x++) {
        for (int y = startY; y < (startY + height); y++) {
            Color c = bitmap.GetPixel(x, y);

            r += Convert.ToInt32(c.R);
            g += Convert.ToInt32(c.G);
            b += Convert.ToInt32(c.B);

            totalPixels++;
        }
    }

    r /= totalPixels;
    g /= totalPixels;
    b /= totalPixels;

    Color color = Color.FromArgb(255, (byte)r, (byte)g, (byte)b);

    return color;
}

You can then use it like

Color pixelColor = myBitmap.GetDominantColor(xPixel, yPixel, 5, 5); 

there is room for improvement, like using a Point and Size, or even a Rectangle

public static Color GetDominantColor(this Bitmap bitmap, Rectangle area) {
    return bitmap.GetDominantColor(area.X, area.Y, area.Width, area.Height);
}

and following this link: https://www.c-sharpcorner.com/UploadFile/0f68f2/color-detecting-in-an-image-in-C-Sharp/

If you want to get the image colors, you don't need to do any cropping at all. Just loop on image pixels and find the two different colors. (Assuming that you already know the image will have exactly 2 colors, as you said in comments). I've written a small function that will do that. However, I didn't test it in an IDE, so expect some small mistakes:

private static Color[] GetColors(Image image)
{
    var bmp = new Bitmap(image);
    var colors = new Color[2];
    colors[0] = bmp.GetPixel(0, 0);
    for (int i = 0; i < bmp.Width; i++)
    {
        for (int j = 0; j < bmp.Height; j++)
        {
            Color c = bmp.GetPixel(i, j);
            if (c == colors[0]) continue;
            colors[1] = c;
            return colors;
        }   
    }
    return colors;
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM