Android 调色板未选择主色

Android Palette not chosing predominant colors

我有以下图片:

而且我有以下方法returns我从这个图像的位图中选择调色板颜色:

 public static int getPredominantColorFromPokemon(String pokemonId, Context context) {
    int pokemonImage = PokemonUtils.getPokemonSugimoriImageById(pokemonId, context);
    if (pokemonImage == 0) {
        return Color.WHITE;
    }
    Bitmap bitmap = BitmapFactory.decodeResource(context.getResources(), pokemonImage);
    Palette palette = Palette.from(bitmap).generate();
    int colorPalette1 = palette.getLightVibrantColor(Color.WHITE);
    int colorPalette2 = colorPalette1 == -1 ? palette.getVibrantColor(Color.WHITE) : colorPalette1;//Fallback
    int colorPalette3 = colorPalette2 == -1 ? palette.getLightMutedColor(Color.WHITE) : colorPalette2; //Fallback
    int colorPalette4 = colorPalette3 == -1 ? palette.getDominantColor(Color.WHITE) : colorPalette3;//Fallback
    return colorPalette4;
}

这3张图片的结果颜色如下:

但是,这不是我要找的,我想要的输出是这样的:

第一张和第二张图片结果还可以,背景是一种绿色,因为主要颜色是绿色,但第三张图片(Venusaur)不是,因为结果是一种pink/purple 颜色,我希望调色板改为检测绿色。如何修改我的方法以检测主要颜色?

颜色是非常主观的,并不总是能清楚地决定哪种颜色占主导地位。关键因素是 lumincane 和直方图。显然 google 的实现认为粉红色比蓝色更重要。这甚至是可以理解的,因为 red/orange/yellow 是人眼认为更重要的信号颜色(与图像中它们的数量无关)。

想象一个灰色的大矩形,里面有一个霓虹粉色的小圆圈。您可能会将霓虹粉色视为主色,而不是灰色。即便如此灰度还是比较大的。

简而言之:如果您想使用调色板 API,您必须处理它给您的结果。

但由于调色板 API 提供了几种提取的颜色,您可以将它们的色调与图像的直方图进行比较,然后相应地选择您最喜欢的调色板颜色。

这里是一个关于如何将颜色从 RGB 转换为 HSV 并返回的示例。

  • H = 色调 = 您要处理的基本颜色类型(红色、绿色、橙色等)
  • S = 饱和度(色调的强度。深红色或浅红色)
  • V = 值(色调有多亮。从完全暗到完全亮)
int color = Color.rgb(206, 43, 55);

int red = Color.red(color);
int green = Color.green(color);
int blue = Color.blue(color);
System.out.println(red + ", " + green + ", " + blue);
//prints: 206, 43, 55 (as expected)

float[] hsv = new float[3];
Color.RGBToHSV(red, green, blue, hsv);

float hue = hsv[0];
float sat = hsv[1];
float val = hsv[2];

int outputColor = Color.HSVToColor(hsv);
red = Color.red(outputColor);
green = Color.green(outputColor);
blue = Color.blue(outputColor);
System.out.println(red + ", " + green + ", " + blue);

对于初学者,我会尝试只使用 HSV,因为创建直方图非常慢,因为您基本上必须遍历图像的每个像素并将其颜色累积到列表中。 3次。对于红色、绿色和蓝色。

这是您找不到“第一个完美解决方案”的地方。相反,您可能必须在可维护代码、速度和应用程序要求之间权衡取舍。

祝你好运!