Существует ли алгоритм смешивания цветов, который работает как смешивание реальных цветов? - PullRequest
57 голосов
/ 29 августа 2009

Общее смешение цветов RGB сильно отличается от смешения цветов для картин, это смешивание света вместо смешивания пигментов.

Например:

Blue (0,0,255) + Yellow (255,255,0) = Grey (128,128,128)

(должен быть синий + желтый = зеленый)

Есть ли какой-нибудь известный алгоритм смешивания цветов, который работает как смешивание реальных цветов?


Мой подход

Я уже пробовал следующее:

Преобразование обоих цветов в HSV и оттенков смешения (умноженное на коэффициент, рассчитанный по насыщенности), и простое среднее для каналов насыщенности и значения. Затем я вычислил среднюю яркость из обоих цвета и скорректировать полученный цвет, чтобы соответствовать этой яркости. Это работало довольно хорошо, но смешивание оттенков иногда было неправильным, т.е. g.:

Red (Hue 0°) + Blue (Hue 240°) = Green (Hue 120°)

Я понял, что иногда мне нужно сместить значение оттенка на 360 ° (когда разница между оттенки больше 180 °).

Red (Hue 360°) + Blue (Hue 240°) = Magenta/fuchsia (Hue 300°)

Но это смещение тоже было не очень хорошим, например ::1010 *

Cyan (Hue 179°) + Red (Hue 0°) = Hue 89.5°
Cyan (Hue 181°) + Red (Hue 0°) --> shifting is performed (the difference is greater than 180°)
Cyan (Hue 181°) + Red (Hue 360°) = Hue 270.5°

(оттенок 179 + красный) и (оттенок 181 + красный) дают два совершенно разных цвета.


Затем Я попробовал цветовое пространство CIE Lab (как в Photoshop), которое разработано так, чтобы быть ближе к восприятию цветов людьми.

Я использовал простое среднее значение для каждого соответствующего двух каналов, но результаты не были удовлетворительными, например, я получил розовый (64, 26, -9,5) из синего (98, -16, 93) и желтого (30, 68, -112). Эти коэффициенты были взяты из фотошопа.

Может быть, если бы я использовал какую-то операцию, отличную от средней, она могла бы работать, но Я не знаю что.


CMYK тоже не работал , результаты такие же, как в RGB или LAB.


Кажется, что ни тривиальная добавка, ни вычитающее смешение цветов в любом из этих цветовых пространств не дают естественных результатов.


Рабочие реализации

Krita & ndash; Малярный миксер

Редактор растровой графики Krita в какой-то момент работал с более реалистичным смешиванием цветов: http://commit -digest.org / Issues / 2007-08-12 / (Плагин микшера Painterly)

Говорят, что это первое общедоступное приложение, в котором реализована специальная технология с использованием уравнений Кубелки и Мунка, описывающих поведение пигментов.

Вот видео смешивания цветов Krita: https://www.youtube.com/watch?v=lyLPZDVdQiQ

Бумага от FiftyThree

Также есть статья о смешивании цветов в приложении Paper для iOS , разработанном FiftyThree . Они описывают, как они вводят новшества и экспериментируют в этой области, а также предлагают образцы смешивания синего и желтого, что приводит к зеленому. Тем не менее, фактический процесс или алгоритм на самом деле не описаны там.

Цитирование:

«В поисках хорошего алгоритма наложения мы сначала попытались интерполировать различные цветовые пространства: RGB, HSV и HSL, затем CieLAB и CieLUV. Результаты оказались неутешительными», - говорит Чен. «Мы знаем, что красный и желтый должны давать оранжевый, или что красный и синий должен становиться фиолетовым, но нет никакого способа получить эти цвета, независимо от того, какое цветовое пространство вы используете. Есть инженерная аксиома: сделайте самую простую вещь, которая может сработать. Ну, теперь мы попробовали самые простые подходы, и они не чувствовали себя даже отдаленно правыми. "

Кажется, что так же, как Krita, Paper реализует модель Kubelka-Munk:

[...] модель Кубелки-Мунка имела как минимум шесть значений для каждого цвета, включая значения отражения и поглощения для каждого из цветов RGB. «В то время как появление цвета на экране можно описать в трех измерениях, на самом деле смешивание цвета происходит в шестимерном пространстве», - объясняет Георг Петшниг, соучредитель и генеральный директор FiftyThree. Газета «Кубелка-Мунк» позволила команде перевести эстетическую задачу в математическую структуру. [...]

Из всей этой информации кажется, что реализация на основе модели Кубелки-Мунка могла бы стать шагом вперед и предложить результаты, которые намного ближе к реальности.

Несмотря на то, что это выглядит как сложный процесс, я еще не видел много хорошей информации о том, как реализовать что-то подобное.


Смежные вопросы

Эти вопросы были опубликованы после этого, все они касаются одного и того же.

Ни у кого из них нет ответа.


Другие ссылки и ресурсы

Ответы [ 7 ]

24 голосов
/ 29 августа 2009

Правильный ответ НЕТ, потому что правильная рабочая модель того, как на самом деле работает "смешение цветов в реальном мире", отсутствует. Это FAR слишком сложный и условный и совсем не похожий на простой красно-сине-желтый материал, который мы выучили в школе (на самом деле для решения требуется вся химия, а также много физики и биологии).

Однако, упрощенный ответ таков: ДА, используйте вычитающее смешивание вместо Аддитивное смешивание.

Смешивание цветов, которое мы изучали в начальной школе, основано на комбинациях пигментов, которые являются формой субтрактивного смешения цветов (очень упрощенно). То есть, чем больше цветов мы добавляем вместе, тем темнее становится, потому что каждый пигмент вычитает немного больше света.

С другой стороны, почти все компьютерные цветовые схемы аддитивные в том смысле, что они основаны на сочетании световых волн (очень упрощенно), поэтому они становятся ярче, потому что каждый цвет добавляет немного больше света .

Схема RGB + является своего рода дополнительным дополнением к схеме вычитания, которую мы изучали в большинстве начальных школ США (которая называется RBY-). Тем не менее, они не совпадают точно, и может быть трудно конвертировать между ними (исследуя сейчас ...)


ОК, если вы просто хотите переключиться с аддитивных комбинаций в RGB на вычитающие, вы можете использовать следующую формулу обратного байесовского типа, чтобы объединить два цвета:

NewColor.R = (Color1.R * Color2.R)/255
NewColor.G = (Color1.G * Color2.G)/255
NewColor.B = (Color1.B * Color2.B)/255

Корректировка разницы в хроматических полюсах (от G к Y, затем к G) намного сложнее ...


Было отмечено, что это приводит к появлению черного для примера задачи, и технически это правильно для истинной субтрактивной системы, однако, если вам нужна более разбавляющая / вычитающая система, вы можете попробовать это вместо этого:

NewColor.R = 255 - SQRT(((255-Color1.R)^2 + (255-Color2.R)^2)/2)
NewColor.G = 255 - SQRT(((255-Color1.G)^2 + (255-Color2.G)^2)/2)
NewColor.B = 255 - SQRT(((255-Color1.B)^2 + (255-Color2.B)^2)/2)

Это дает темно-серый цвет вместо черного. Но чтобы получить желтый или что-то похожее, вам все равно нужно решить проблему с выравниванием полюсов цветовой схемы.

5 голосов
/ 29 августа 2009

есть две разные возможности сочетания цветов:

  1. аддитивное смешивание (например, RGB)

  2. вычитающее смешивание (как у CMYK)

Таким образом, при вычитающем смешивании цветов результат будет таким, как вы ожидали, но синего нет, вместо этого есть голубой:

Желтый + голубой = зеленый

В общем, субтрактивное смешение цветов - это просто «удаление» (фильтрация) от белого, в то время как аддитивное смешение цветов складывается из черного. (основные цвета субтрактива обратны от аддитивных: красный -> голубой; зеленый -> пурпурный; синий -> желтый)

Итак, если вы начнете с белого экрана, применяя фильтры:

мин (белый (255,255,255), желтый (255,255,0), голубой (0,255,255)) = зеленый (0,255,0)

2 голосов
/ 21 апреля 2012

Существует код для реалистичного смешивания цветов в крите: https://projects.kde.org/projects/calligra/repository/revisions/master/show/krita/plugins/extensions/painterlyframework.

Обратите внимание, что код, включающий файл осветительных приборов, - GPLv2 +. Он может конвертировать из RGB в длины волн, создавать композиции и конвертировать обратно.

1 голос
/ 13 октября 2016

Интересно, работает ли расчет инверсии значения RGB. Так как речь идет о вычитании огней, технически часть вычитания может быть вычислена простой математикой.

Например, голубой + желтый

голубой = 0x00ffff желтый = 0xffff00

Их инверсии 0xff0000 и 0x0000ff, что означает, что они полностью поглощают красный и синий свет. Их смесь 1: 1 должна поглощать половину красного и синего света (поскольку другая половина смеси все еще может отражать некоторое количество красного и синего света), что согласуется с (0xff0000 + 0x00ffff) / 2 = 0x7f007f. Теперь мы вычитаем значение из 0xffffff, у нас есть 0x80ff80, который зеленый!

1 голос
/ 30 апреля 2015

Один из способов вычитать смесь цветов RGB - это сначала преобразовать цвета RGB в кривые спектральной отражательной способности. Преобразование довольно простое, и после того, как вы это сделаете, вы можете сделать истинную вычитающую смесь кривых отражения, а затем преобразовать результат обратно в RGB. Есть еще один похожий вопрос: stackoverflow.com / questions / 10254022 / , где этот процесс обсуждается более подробно.

1 голос
/ 21 декабря 2011

Я думаю, что ваша проблема с сочетанием оттенков состоит в том, что вы делаете это, складывая вместе два угла и деля их на два. Как вы заметили, результат часто не имеет смысла. Я думаю, что вам лучше преобразовать углы в декартовы координаты на единичной окружности, усреднить их и найти угол полученной точки (игнорируя величину).

0 голосов
/ 30 января 2013

Проверьте это внедрение для аддитивных, субстративных и других алгоритмов смешивания.

Полностью функциональный (написан на Java), так что вы можете протестировать любые цвета, которые вам нужно смешать, и посмотреть, соответствует ли он вашим потребностям.

Как указывалось в других ответах, Синий + Желтый (в точности Голубой + Желтый ) - Зеленый вкл субстративный CMYK alghoritm. Смотри сам

...