Winscale
Подробный разбор функций
Рис. 3.
На рис. 3 показана функциональная блок-схема алгоритма winscale. Она состоит из пяти блоков: блока предварительного масштабирования (используется только для уменьшения изображения с коэффициентом больше 2), блока буфера строк (используется для
вертикального потокового буфера), блока winfilter (выполняет фильтрацию
взвешенного суммирования), блока интерполятора фильтра (увеличивает или уменьшает коэффициенты фильтра), и блока расчета весовых коэффициентов.
Блок предварительного деления представляет собой значения шагов и слагаемые для масштабирования на степень двойки по горизонтали или по вертикали, а Winfilter – четыре множителя и три слагаемых для взвешенных сумм четырех пикселей.
SF рассчитывается только один раз, исходя из коэффициента масштабирования. Коэффициенты фильтра – шесть переменных. Это координаты центра (winX, winY) и граничные координаты (winLX, winRX, winTY, winBY) фильтр. Этим коэффициентам на этапе инициализации присваиваются постоянные значения для
первого пикселя приемника, согласно коэффициенту масштабирования, и увеличивается в ходе работы алгоритма для следующих пикселей приёмника шестью сложениями в блоке интерполятора фильтра. Приращения по горизонтали и вертикали – winW и winH соответственно. Их получаем по формуле (2).
Весовые коэффициенты W0…W3 рассчитываются путем умножения А0…А3 на SF. А0…А3 в свою очередь рассчитываются, исходя из dL, dR, dT и dB, являющихся дробными частями координат границ фильтра.
Масштабирование выполняется построчно: вертикальное движение происходит после окончания движения по горизонтали. Если направление перемещения фильтра горизонтально, то новые значения координат фильтра получают сложением предыдущего значения х-координаты фильтра с шириной фильтра. Аналогичным образом, при движении по вертикали складываются у-координата и высота фильтра. Сравнивая координаты границ и центра фильтра, мы можем проверить охват пикселя границами фильтра. Результаты сравнений обрабатывает интерполятор, генерируя четыре однобитных флага (XL, XR, YT, YB), значения которых зависят от принадлежности покрытого пикселя областям, получаемым перемещением центрального пикселя (winX, winY). То есть, если установлен флаг XL, то левый пиксель покрыт фильтром. На рис. 4 левый и верхний пиксели покрыты фильтром: флаги XL и YT установлены, а флаги XR и YB сброшены. Обращаясь к этим флагам, нетрудно вычислить параметры dL и dT, чтобы затем получить значения фильтра А0…А3. Следующий шаг – вычисление произведения SF на А0…А3. В результате получаем весовые коэффициенты W0…W3. Пользуясь этими значениями и значениями пикселей С0…С3, вычисляем окончательное значение выходного пикселя Р.
Рис. 4.
На рис. 2 показан пример уменьшения размера изображения (с разрешения 5*5 пикселей до 4*4 пикселей).
Основной принцип уменьшения изображения почти такой же, за исключением предварительного масштабирования и размера фильтра. Если коэффициент уменьшения больше 2, блок предварительного масштабирования выполняет уменьшение путём равномерно взвешенного суммирования с коэффициентом, являющимся степенью двойки для того, чтобы подобрать значение коэффициента масштабирования от 1 до ½ перед основным процессом уменьшения. Тем самым гарантируется, что каждый пиксель использовался хотя бы один раз, то есть все пиксели источника повлияли на результат независимо от значения коэффициента масштабирования. Размеры ширины и высоты фильтра сжались до 1, чтобы гарантировать покрытие максимум четырьмя пикселями приемника. Таким образом, в случае уменьшения размера изображения значение шага смещения фильтра для получения следующего пикселя будет больше 1, а значение коэффициента SF независимо от коэффициента масштабирования будет равно 1.
Как избавиться от зубчатых краёв.
В случае, когда коэффициент увеличения масштаба является целым числом, алгоритм имеет недостаток. Область фильтра перекрывается всего одним пикселем источника. Таким образом, весовой коэффициент равен 0 или 1, а алгоритм работает так же, как алгоритм ближайшего соседа. В этом случае будет наблюдаться эффект зубчатости краёв. Чтобы устранить этот недостаток, воспользуемся следующим приёмом.
Рис. 5.
Увеличим размеры фильтра так, чтобы он перекрывался несколькими пикселями источника (см. рис. 5). Будем увеличивать картинку размером N*N до размеров M*M (M>N). Увеличиваем площадь фильтра до 1, а значение шага полагаем равным (N–1)/(M–1). Таким образом изображение сглаживается, избавляемся от зубчатых краёв.