После публикации прошлой статьи, я полностью забил на попытку выполнить алгоритм при помощи HSV или Lab координат. Забил на использовании библиотек цветов и вообще на сам скрипт забил.
Но что-то стало скучно и опять зачесались руки поработать с изображениями и одновременно захотелось исправить уже имеющийся алгоритм.
Скрипт: link
![](https://habrastorage.org/r/w780q1/storage2/d9f/ec4/516/d9fec45165ed968b211b1bce5ad9ed69.jpg)
Больным местом алгоритма было определение похожих тонов. Больным оно являлось из-за не учета яркости похожих цветов. На момент написания я прекрасно представлял проблему, с которой мне бы предстояло столкнуться при определении яркости и я решил не учитывать ее. Это обернулось тем, что черно-белые изображения не обрабатывались. Также довольно насыщенные цветами и контрастные изображения выдавали странные тона, которых как бы и не было на картинке.
Возникало это все вот почему. Уникальный идентификатор цвета определялся как (r-g)*1000000+(r-b)*1000+(g-b). Соответственно цвета имеющие одинаковые идентификаторы являлись подобными. При обработке постоянно вносилась все большая погрешность в r, g и b составляющие цвета. Вносилось простейшим округлением: round(round( (r-g)/$error ) * $error) итд.
Собственно решение оказалось крайне простым, но не без нюанса. Я для начала определил яркость цвета. Это простейшее среднее арифметическое, только приведенное к целочисленной шкале от 0 до n, где n в данном случае — количество интервалов яркости. Собственно тут и возникает большая проблема, на границе интервалов будут находится на самом деле похожие цвета, но они будут обрабатываться уже отдельно и каждый отдельно будет выведен. Но это будет заметно только на изображениях, где как раз попадутся цвета располагающиеся по разные стороны от границы. В идеале, такие границы должны быть разбиты не строго, т.е. в зависимости от текущей палитры смещены в одну или другую сторону.
Также из-за разбиения тонов на интервалы яркости, пришлось увеличить количество обрабатываемых цветов. Теперь вместо 60000, алгоритм обрабатывает 500000 цветов и шаг проверки уменьшился с 20px до 10px. Так что возможно замедление работы.
В результате, картина очень сильно изменилась в лучшую сторону! Скрипт выдает более менее адекватные цвета на большинство изображений. Также работают и ч/б изображения, хотя с ними возможны баги.
Ниже несколько примеров работы:
![](https://habrastorage.org/r/w780q1/storage2/6b1/f83/8cb/6b1f838cb40ac99ce62ab57191ad0434.jpg)
![](https://habrastorage.org/r/w780q1/storage2/65e/91e/6f8/65e91e6f8daa6ac9d9a2ef547d424b37.jpg)
![](https://habrastorage.org/r/w780q1/storage2/bc6/f80/37c/bc6f8037cddee62a88ec3c3f81ed8be1.jpg)
![](https://habrastorage.org/r/w780q1/storage2/e04/6f9/0ec/e046f90ec0dbdeaa8dcf3677b296c289.jpg)
![](https://habrastorage.org/r/w780q1/storage2/304/7a3/fea/3047a3feabbd75488eb37105192da6bb.jpg)
Не стал публиковать в блог «Алгоритмы», т.к. это всего лишь небольшое изменение в работу предыдущей версии.
Многие спрашивали скрипт для определения цветов на изображении. Собственно вот. Внутри есть описание.
UPD_1 По просьбе некоторых пользователей, добавил вывод цветов в hex формате после обработки изображения. RGB нужен?
UPD_2 Добавил поддержку PNG.
UPD_3 Автор фотографии рыжей девушки: Елена Серебрякова.
UPD_4 Пересчет яркости по формуле 0.299*R + 0.587*G + 0.114*B. Изменена погрешность. Добавлена возможность перевода цвета из HEX в RGB формат.
UPD_5 Уменьшил пороговую погрешность. Добавил возможность определения цветов на загруженной фотографии. Просто кликните в нужном месте на изображении.
Но что-то стало скучно и опять зачесались руки поработать с изображениями и одновременно захотелось исправить уже имеющийся алгоритм.
Скрипт: link
![](https://habrastorage.org/storage2/d9f/ec4/516/d9fec45165ed968b211b1bce5ad9ed69.jpg)
Решение
Больным местом алгоритма было определение похожих тонов. Больным оно являлось из-за не учета яркости похожих цветов. На момент написания я прекрасно представлял проблему, с которой мне бы предстояло столкнуться при определении яркости и я решил не учитывать ее. Это обернулось тем, что черно-белые изображения не обрабатывались. Также довольно насыщенные цветами и контрастные изображения выдавали странные тона, которых как бы и не было на картинке.
Возникало это все вот почему. Уникальный идентификатор цвета определялся как (r-g)*1000000+(r-b)*1000+(g-b). Соответственно цвета имеющие одинаковые идентификаторы являлись подобными. При обработке постоянно вносилась все большая погрешность в r, g и b составляющие цвета. Вносилось простейшим округлением: round(round( (r-g)/$error ) * $error) итд.
Собственно решение оказалось крайне простым, но не без нюанса. Я для начала определил яркость цвета. Это простейшее среднее арифметическое, только приведенное к целочисленной шкале от 0 до n, где n в данном случае — количество интервалов яркости. Собственно тут и возникает большая проблема, на границе интервалов будут находится на самом деле похожие цвета, но они будут обрабатываться уже отдельно и каждый отдельно будет выведен. Но это будет заметно только на изображениях, где как раз попадутся цвета располагающиеся по разные стороны от границы. В идеале, такие границы должны быть разбиты не строго, т.е. в зависимости от текущей палитры смещены в одну или другую сторону.
Также из-за разбиения тонов на интервалы яркости, пришлось увеличить количество обрабатываемых цветов. Теперь вместо 60000, алгоритм обрабатывает 500000 цветов и шаг проверки уменьшился с 20px до 10px. Так что возможно замедление работы.
Результат
В результате, картина очень сильно изменилась в лучшую сторону! Скрипт выдает более менее адекватные цвета на большинство изображений. Также работают и ч/б изображения, хотя с ними возможны баги.
Ниже несколько примеров работы:
![](https://habrastorage.org/storage2/6b1/f83/8cb/6b1f838cb40ac99ce62ab57191ad0434.jpg)
![](https://habrastorage.org/storage2/65e/91e/6f8/65e91e6f8daa6ac9d9a2ef547d424b37.jpg)
![](https://habrastorage.org/storage2/bc6/f80/37c/bc6f8037cddee62a88ec3c3f81ed8be1.jpg)
![](https://habrastorage.org/storage2/e04/6f9/0ec/e046f90ec0dbdeaa8dcf3677b296c289.jpg)
![](https://habrastorage.org/storage2/304/7a3/fea/3047a3feabbd75488eb37105192da6bb.jpg)
Дополнительно
Не стал публиковать в блог «Алгоритмы», т.к. это всего лишь небольшое изменение в работу предыдущей версии.
Многие спрашивали скрипт для определения цветов на изображении. Собственно вот. Внутри есть описание.
UPD_1 По просьбе некоторых пользователей, добавил вывод цветов в hex формате после обработки изображения. RGB нужен?
UPD_2 Добавил поддержку PNG.
UPD_3 Автор фотографии рыжей девушки: Елена Серебрякова.
UPD_4 Пересчет яркости по формуле 0.299*R + 0.587*G + 0.114*B. Изменена погрешность. Добавлена возможность перевода цвета из HEX в RGB формат.
UPD_5 Уменьшил пороговую погрешность. Добавил возможность определения цветов на загруженной фотографии. Просто кликните в нужном месте на изображении.