【问题标题】:Get used color names from image从图像中获取使用的颜色名称
【发布时间】:2010-04-05 11:10:20
【问题描述】:

我想检查图像中存在哪些颜色。这将存储在数据库中并用于搜索表单。 (红色=1,绿色=1,蓝色=0,黄色=1,黑色=1,白色=1等)

img = Magick::Image.read('phosto-file.jpg').first
img = img.quantize(10
h = img.color_histogram
pp h
{red=12815, green=18494, blue=15439, opacity=0=>13007,
 red=44662, green=47670, blue=51967, opacity=0=>18254,
 red=17608, green=43331, blue=48321, opacity=0=>11597,
 red=21105, green=25865, blue=39467, opacity=0=>10604,
 red=15125, green=36629, blue=22824, opacity=0=>10223,
 red=52102, green=42405, blue=10063, opacity=0=>12928,
 red=39043, green=28726, blue=40855, opacity=0=>7728,
 red=10410, green=8880, blue=7826, opacity=0=>13795,
 red=25484, green=25337, blue=24235, opacity=0=>7351,
 red=44485, green=12617, blue=11169, opacity=0=>14513}

如何将这 10 个值转换为颜色名称? red、green、NOMATCH、yellow、black、white 等。只需要粗略的颜色名称 - 不是 LimeGreen 而是 Green 等。

最好的问候。 阿斯比约恩·莫雷尔

【问题讨论】:

  • 示例中的 ruby​​ 代码无效:opacity=0=>13007 无效。

标签: ruby-on-rails ruby imagemagick


【解决方案1】:

如果您可以用 ImageMagick 返回的相同数字格式表示您正在寻找的所有颜色。然后您可以比较 RGB 值以找出最接近的值。

例如,如果您的直方图值为(假设每种颜色有 255 个值,YMMV)

{ red => 10, green => 255, blue => 10 }

然后你可以将它与每个比较

{
  red   => {red => 255, green => 0, blue => 0},
  green => {red => 0, green => 255, blue => 0},
  blue  => {red => 0, green => 0, blue => 255}
}

因此,如果您将所有元素之间的差异相加,您将得到

{
  red   => 510,
  green =>  20,
  blue  => 510,
}

所以你可以清楚地看到颜色最接近绿色

更新:在 Ruby 中添加了一个解决方案


def compare_color(color_val)
  colors = {
    :red    => [255,0,0],
    :green  => [0,255,0],
    :blue   => [0,0,255]
  }

  difference = {}

  def compare_array(a1,a2)
    total = 0
    a1.each_index do |x|
      total += (a1[x]-a2[x]).abs
    end
    total
  end

  colors.each do |color,hex|
    difference[color] = compare_array(color_val,hex)
  end

  closest = difference.sort{|a,b| a[1]  b[1]}.first                                                                       [closest,difference]
end

p compare_color([10,255,10])
# [[:green, 20], {:red=>510, :green=>20, :blue=>510}]

【讨论】:

  • 如果这些代码是数组而不是散列,可能更容易(从数学角度)编写,但这更能说明问题
  • 非常好。谢谢你的例子。 :)
【解决方案2】:

简单的方法是列出 RGB 值和相应的名称,然后选择最接近的匹配颜色(在一些可接受的误差范围内)。对于基本颜色,即使是每个 RGB 通道中非常简单的差异总和也可以给出可行的结果,尽管我怀疑如果数据看起来像这样,你会用完颜色名称。你可以在网上找到list of colour names,也许去掉一个这样的列表可能会有所帮助。 (请注意,这些通常期望颜色范围为 0..255,因此您需要从数据中更广泛的范围向下转换。)

一种更高级的方法是将 RGB 值转换为色调、饱和度和亮度,并使用它们来生成名称,例如“深红色”当色调为红色、饱和度足够高而不会变成灰色、亮度低(但不足以低到黑色)时。

【讨论】:

    【解决方案3】:

    您可能会在我的博客上发现 this post 很有趣。它准确地解释了如何解决您的问题。我还发布了ColorNamer gem,它为您提供了与 RGB 值或 HTML 哈希值最接近的命名颜色。您也可以使用任何Color 对象

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2011-11-27
      • 2013-07-21
      • 2019-07-27
      • 2015-05-09
      • 1970-01-01
      • 2016-09-06
      • 1970-01-01
      相关资源
      最近更新 更多