颜色混合2种以上的颜色



我正在尝试找到一种基于%量的算法,该算法将混合颜色。我正在研究选举项目,并希望能够在种族中分配不同颜色的每个候选人,然后根据候选人获得的投票来创建"结果"颜色。

这个问题:

是否有一种用于颜色混合的算法,例如混合真实颜色?

是我要问的问题 - 但可能需要能够将3或4或5种颜色混合在一起。我了解这最终是一个非常复杂的问题 - 但是我很好奇建议在两种颜色上做什么建议。所以,我可能有:

红色(40%),绿色(10%),蓝色(50%)

红色(40%),黄色(5%),蓝色(10%),橙色(45%)

再次,我知道最后一个例子可能会产生某种灰色,棕色或黑色 - 这很好。我的问题是我什至没有试图解决此问题的算法。


编辑:因此 - 发布此消息后,我意识到我真正要完成的工作基本上是颜色混合。换句话说,我不希望浅色混合,我想模拟油漆混合会发生的事情 - 因为那是我一直'期望'的"可预测"结果 - 并且在获得难度。

我找到了此链接:http://painting.about.com/library/blpaint/blcolormixingpalette1.htm

的表现与我要完成的工作非常紧密 - 并在我的最初想法中暴露了一个小的"缺陷"。证明的是,即使我可以使用此算法混合多达6种颜色,但实际的"数据"总是分解为3种原色。

即使如此 - 这很近。

感谢所有为此主题做出贡献的人 - 所有这些建议对探索这个令人惊讶的复杂问题/领域都非常有帮助。

您是否尝试过简单地进行加权总和?

d.R = a.R*0.25 + b.R*0.25 + c.R*0.5
d.G = a.G*0.25 + b.G*0.25 + c.G*0.5
...
where a, b, c are the colors you're mixing

从我的研究中,似乎没有任何正确的答案,但是似乎会产生最合适的效果。此外,我认为简单地将颜色融合在一起会真正指示信息图上的任何内容。您最好尝试一些真正颗粒状的抖动http://en.wikipedia.org/wiki/wiki/dither#digital_photography_and_image_image_processing

RGB颜色系统对这种计算不利,因为它不像人类感知颜色那样工作。例如,我们只是不将黄色视为绿色和红色的混合物。第一步是在颜色空间中转换您的颜色,在该颜色空间中,您的颜色坐标均匀,并为颜色提供两个坐标。这可以是HLS或Cielab。HLS转换更为简单,但是Cielab中的坐标代表了更好的人类颜色体验。在这个颜色空间中,相等的距离至少在人类感知中大致相等。

在此颜色空间中,您的所有颜色都具有坐标,A和B。L应该相同。您的基本颜色应该在灰点周围圆上,因此它们具有相同的距离,并且没有比其他颜色更强的颜色。因此,您基本上在飞机上有几个点,需要计算它们的加权中间点。您将此观点转换回RGB。

这一切都取决于颜色模型中的原色。看起来您正在使用RGB颜色型号,这意味着所有颜色都可以用红色,绿色和蓝色的混合表示。

也就是说,任何不是红色,绿色或蓝色的颜色,您都会将它们分解为红色,绿色和蓝色的对应物,然后将这些重量总体上乘以重量。

在您的第二个示例中:

红色(40%),黄色(5%),蓝色(10%),橙色(45%)

黄色和橙色需要分解。假设您有橙色的Color实例,则可以这样做:

orangeRed = o.R * .05;
orangeBlue = o.B * .05;
orangeGreen = o.G * .05;

实际上可以跨越所有 Color实例(对于原色,RGB中只有一个具有值),然后可以采用总和和加权平均值来获得混合颜色。

这样做的简单扩展方法将是:

static Color Mix(this IEnumerable<Tuple<Color, double>> colors)
{
    // The red, green, and blue values.
    double red = 0.0, green = 0.0, blue = 0.0;
    // The denominator for the weighted average for a color.
    double denominator = byte.MaxValue * 3.0;
    // Cycle through the colors.
    foreach (Tuple<Color, double> color in colors)
    {
        // Get the weighted average value for each component, and then
        // multiply that by the weight for the color.
        red   += ((color.Item1.R / denominator) * color.Item2);
        green += ((color.Item1.G / denominator) * color.Item2);
        blue  += ((color.Item1.B / denominator) * color.Item2);
    }
    // Create the color and return.
    return Color.FromArgb((int) red, (int) green, (int) blue);
}

最新更新