在bufferedimage中找到具有容差的颜色

时间:2014-07-13 01:34:03

标签: java colors awt rgb awtrobot

我正在编写一个尝试在bufferedImage中查找颜色的方法。目前,该方法通过采用屏幕截图,然后扫描图像以获得特定颜色来工作。现在我想添加一些RGB容忍度,所以如果用户试图找到容差为1的颜色(1,3,5),任何颜色+ -1 R,B或G都将返回true。

我可以通过首先生成一个有效的RGB值的arrayList来解决这个问题,然后对于每个像素,我可以通过数组并检查每个值。问题是,对于大图像的高容差,可能会非常慢。

是否有更高效或可能的内置方式我可以做到这一点?这是我现在的方法。谢谢!

public static Point findColor(Box searchArea, int color){
    System.out.println("Test");
    BufferedImage image = generateScreenCap(searchArea);
    for (int i = 0; i < image.getWidth(); i++) {
        for (int j = 0; j < image.getHeight(); j++) {
            if((image.getRGB(i, j)*-1)==color){
                return new Point(i + searchArea.x1, j + searchArea.y1);
            }
        }
    }
    return new Point(-1, -1);
}

编辑:我正在使用int RGB值进行所有比较,因此我使用Color.getRGB()而不是Color [1,1,1],它返回一个负数int,我转换为正数以便最终用户简单

1 个答案:

答案 0 :(得分:2)

您需要比较RGB值而不是&#34;整体&#34;颜色,如果你想有一个自定义公差。这是代码,它没有经过测试,但你明白了:

public static Point findColor(Box searchArea, int r, int g, int b, int tolerance){
    System.out.println("Test");

    // Pre-calc RGB "tolerance" values out of the loop (min is 0 and max is 255)
    int minR = Math.max(r - tolerance, 0);
    int minG = Math.max(g - tolerance, 0);
    int minB = Math.max(b - tolerance, 0);
    int maxR = Math.min(r + tolerance, 255);
    int maxG = Math.min(g + tolerance, 255);
    int maxB = Math.min(b + tolerance, 255);

    BufferedImage image = generateScreenCap(searchArea);
    for (int i = 0; i < image.getWidth(); i++) {
        for (int j = 0; j < image.getHeight(); j++) {
            // get single RGB pixel
            int color = image.getRGB(i, j);

            // get individual RGB values of that pixel
            // (could use Java's Color class but this is probably a little faster)
            int red = (color >> 16) & 0x000000FF;
            int green = (color >>8 ) & 0x000000FF;
            int blue = (color) & 0x000000FF;  

            if ( (red >= minR && red <= maxR) &&
                 (green >= minG && green <= maxG) &&
                 (blue >= minB && blue <= maxB) ) 
                return new Point(i + searchArea.x1, j + searchArea.y1);
        }
    }
    return new Point(-1, -1);
}