Я разрабатываю рутину для автоматического улучшения сканированных 35-мм слайдов. Я ищу хороший алгоритм для увеличения контраста и удаления цветового оттенка. Алгоритм должен быть полностью автоматическим, так как тысячи изображений будут обрабатываться. Это несколько образцов изображений прямо со сканера, только обрезанные и уменьшенные для веб-страниц:
Я использую библиотеку AForge.NET и пробовал фильтры HistogramEqualization
и ContrastStretch
. HistogramEqualization
хорош для максимизации локального контраста, но не дает приятных результатов в целом. ContrastStretch
лучше, но поскольку он растягивает гистограмму каждой цветовой полосы по отдельности, она иногда производит сильный цвет:
Чтобы уменьшить смещение цвета, я сам создал фильтр UniformContrastStretch
, используя классы ImageStatistics
и LevelsLinear
. Это использует тот же диапазон для всех цветовых диапазонов, сохраняя цвета за счет меньшего контраста.
ImageStatistics stats = new ImageStatistics(image);
int min = Math.Min(Math.Min(stats.Red.Min, stats.Green.Min), stats.Blue.Min);
int max = Math.Max(Math.Max(stats.Red.Max, stats.Green.Max), stats.Blue.Max);
LevelsLinear levelsLinear = new LevelsLinear();
levelsLinear.Input = new IntRange(min, max);
Bitmap stretched = levelsLinear.Apply(image);
Изображение все еще довольно голубое, поэтому я создал фильтр ColorCorrection
, который сначала вычисляет среднюю яркость изображения. Затем вычисляется значение гамма-коррекции для каждого цветового канала, так что среднее значение каждого цветового канала будет равно средней яркости. Равномерное растянутое изображение с контрастностью имеет средние значения R=70 G=64 B=93
, средняя яркость (70 + 64 + 93) / 3 = 76
. Значения гамма вычисляются до R=1.09 G=1.18 B=0.80
, и получившееся очень нейтральное изображение имеет средние значения R=76 G=76 B=76
, как ожидалось:
Теперь, дойдя до настоящей проблемы... Я полагаю, что исправление среднего цвета изображения до серого немного чересчур и сделает некоторые изображения довольно скучными по внешнему виду, например, второй образец (первое изображение равномерно растянуто, следующий - тот же самый цвет изображения):
Одним из способов ручной коррекции цвета в программе редактирования фотографий является выбор цвета известного нейтрального цвета (белый/серый/черный) и настройка остальной части изображения на него. Но поскольку эта процедура должна быть полностью автоматической, это не вариант.
Я думаю, я мог бы добавить настройку силы в мой фильтр ColorCorrection
, так что сила 0,5 будет перемещать средние значения на половину расстояния до средней яркости. Но, с другой стороны, некоторые изображения могут делать лучше всего без какой-либо коррекции цвета.
Любые идеи для лучшего алгоритма? Или какой-либо метод для определения того, имеет ли изображение цветное изображение или просто имеет много цвета, например, второй образец?