Обсуждение статьи "Изучаем класс CCanvas. Реализация прозрачности графических объектов" - страница 6

 
Nikolai Semko:

Это, Петр, слишком просто.

Вот тебе задачка для освоения и закреплении сути вопроса:

 - как смешать два цвета ARGB(a1,r1,g1,b1) и ARGB(a2,r2,g2,b2) в рамках одного слоя, каждый из которых имеет свою прозрачность  a1 и a2?

Без такого смешивания невозможно правильно накладывать друг на друга сглаженные объекты.

На вскидку: На исходный цвет слоя накладываем первый ARGB(a1,r1,g1,b1) методом изложенным в статье. Далее, поверх первого положенного цвета, накладываем второй, делая рассчеты АRGB по той же формуле. Просто на этот раз, нижнем цветом будет первый, который мы положили над исходным цветом слоя.

Возможно ошибаюсь, Николай, но почему это не должно сработать?

ЗЫ. Еще не экспериментировал, но первый вариант может не сработать, потому что неправильно рассчитывается конечная прозрачность двух верхних слоев. В этом случае, нужно смешать средний слой с верхним, и получив их общий цвет, наложить его на исходный слой.

 
Реter Konow:

На вскидку: На исходный цвет слоя накладываем первый ARGB(a1,r1,g1,b1) методом изложенным в статье. Далее, поверх первого положенного цвета, накладываем второй, делая рассчеты АRGB по той же формуле. Просто на этот раз, нижнем цветом будет первый, который мы положили над исходным цветом слоя.

Возможно ошибаюсь, Николай, но почему это не должно сработать?

ЗЫ. Еще не экспериментировал, но первый вариант может не сработать, потому что неправильно рассчитывается конечная прозрачность двух верхних слоев. В этом случае, нужно смешать средний слой с верхним, и получив их общий цвет, наложить его на исходный слой.

на самом деле задачка не из простых.
Но кто сможет решить ее самостоятельно, тот по праву может считаться гуру цвета.
Данная статья далека от академичности именно из-за отсутствия данной формулы.
 
Nikolai Semko:
на самом деле задачка. не из простых.
Но кто сможет решить ее самостоятельно, тот по праву может считаться гуру цвета.

А как? Сам-то экспериментировал? Наверно верхний цвет как фильтр использовать, просчитать каждый компонент (rgb) нижнего слоя пропорционально уровню соответствующего компонента верхнего слоя и прозрачности (определяется сколько чего пройдет с нижнего через верхний).  Потом пересчитать уровни компонентов верхнего в соответствии с непрозрачностью (определяется сколько остается верхнего). В конце посчитать среднее по каждому компоненту нижнего и верхнего слоев (не исходного нижнего и верхнего, а пересчитанных, как написано). Не пробовал.

Ну или просто сложить компоненты пропорционально прозрачности.

Надо поэкспериментировать... интересная задачка.

 
Dmitry Fedoseev:

А как? Сам-то экспериментировал?

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

Уфффф... все намного проще оказалось, фильтровать не надо перед сложением. Компоненты просто складываются пропорционально прозрачности и непрозрачности:

r=lr*(255-Alpha)/255+ur*Alpha/255;
g=lg*(255-Alpha)/255+ug*Alpha/255;
b=lb*(255-Alpha)/255+ub*Alpha/255;

Alpha: 255 - верхний слой непрозрачен, 0 - полностью прозрачен. 

lr, lg, lb - компоненты нижнего слоя. 

ur, ug, ub - компоненты верхнего слоя. 

Вот в терминале, черный фон, красный квадрат непрозрачный, на нем синий с прозрачностью 50% и потом желтый с прозрачностью 50%

Вот тоже самое в фотошопе:


 
Dmitry Fedoseev:

Уфффф... все намного проще оказалось, фильтровать не надо перед сложением. Компоненты просто складываются пропорционально прозрачности и непрозрачности:

Alpha: 255 - верхний слой непрозрачен, 0 - полностью прозрачен. 

lr, lg, lb - компоненты нижнего слоя. 

ur, ug, ub - компоненты верхнего слоя. 

доберусь до компа, попробую смешать две прозрачные картинки по этой флрмуле и посмотрим что получится. :))
 
Nikolai Semko:
доберусь до компа, попробую смешать две прозрачные картинки по этой флрмуле и посмотрим что получится. :))

А как можно две прозрачные смешивать? Сначала одна накладывается на фон, потом вторая накладывается на получившееся.

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

***

Вот что было бы особо интересно - разораться со всеми методами наложения слоев как в фотошопе.

 
Dmitry Fedoseev:

Уфффф... все намного проще оказалось, фильтровать не надо перед сложением. Компоненты просто складываются пропорционально прозрачности и непрозрачности:

r=lr*(255-Alpha)/255+ur*Alpha/255;
g=lg*(255-Alpha)/255+ug*Alpha/255;
b=lb*(255-Alpha)/255+ub*Alpha/255;

Alpha: 255 - верхний слой непрозрачен, 0 - полностью прозрачен. 

lr, lg, lb - компоненты нижнего слоя. 

ur, ug, ub - компоненты верхнего слоя. 

Вот в терминале, черный фон, красный квадрат непрозрачный, на нем синий с прозрачностью 50% и потом желтый с прозрачностью 50%

Вот тоже самое в фотошопе:

не то ...

речь о том, что существует Alpha1 и Alpha2

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

Вы по сути повторили формулу автора статьи смешения прозрачного цвета с фоном:

result=backgraund*(1-alpha)+foreground

а у Вас:

result=backgraund*(1-alpha)+foreground*alpha

Ваш вариант правильный, а вот автор статьи накосячил в простой формуле, и прикольно, что Петр его благодарит за эту формулу :))

Ведь невооруженным глазом видно, что в формуле автора легко наступает переполнение uchar. Странно что за 4 года никто не увидел эту грубую ошибку.

 

вот здесь применяется алгоритм смешения друх прозрачных цветов:


 
А зачем смешивать два прозрачных слоя, что бы потом их накладывать? Сначала один слой наложить, подом другой.