Форматы изображений: GIF

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

GIF можно рассматривать как обертку для данных изображения. У него есть своего рода окно просмотра, называемое «логическим экраном», на котором рисуются отдельные кадры данных изображения — что-то вроде слоев в документе Photoshop. Именно так GIF поддерживает свою анимацию, подобную флипбуку: один кадр рисуется на логическом экране, затем заменяется другим, а затем еще одним. Конечно, это различие не важно, когда мы имеем дело со статическим GIF-файлом, состоящим из одного кадра, нарисованного на логическом экране.

GIF использует метод сжатия данных без потерь — вариант алгоритма Лемпеля-Зива-Уэлча , если вам интересно. Более мелкие детали того, как работает этот алгоритм, — это больше, чем нам нужно здесь вдаваться, но на высоком уровне: он работает немного как «уродливый» JavaScript, где повторяющиеся строки символов по всему файлу сохраняются в своего рода внутреннем словаре. , чтобы на них можно было ссылаться, а не повторять каждый раз, когда они появляются.

Визуализация ссылки gif с использованием сетки четыре на четыре.

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

Хотя GIF технически использует сжатие без потерь, у него есть серьезное ограничение, которое серьезно влияет на качество изображений: сохранение изображения в формате GIF всегда приводит к снижению точности, если только изображение уже не использует 256 цветов или меньше.

Каждый кадр, отображаемый на логическом экране GIF, может содержать не более 256 цветов. GIF также поддерживает «индексную прозрачность», где прозрачный пиксель будет ссылаться на индекс прозрачного «цвета» в таблице цветов.

Практика сокращения диапазона значений до меньшего, аппроксимированного набора выходных значений называется квантованием . Этот термин вы часто будете встречать, изучая кодирование изображений. Результаты такого квантования палитры обычно очевидны:

Пример статической гифки

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

Три горизонтальных синих прямоугольника, за которыми следует один красный прямоугольник.

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

Горизонтальные прямоугольники от синего до красного цвета в конфигурации два на четыре, причем один синий прямоугольник затенен темнее остальных.

При отсутствии какого-либо сжатия, так сказать, вы можете описать эту сетку так:

Первая строка, первый столбец — #0000FF. Первая строка, второй столбец — #0000FF. Первая строка, третий столбец — #0000FF. Первая строка, четвертый столбец — #FF0000. Вторая строка, первый столбец — #0000FF. Вторая строка, второй столбец — #000085. Вторая строка, третий столбец — #0000FF. Вторая строка, четвертый столбец — #FF0000.

Используя что-то вроде сжатия данных без потерь и индексации цвета в формате GIF, вы можете описать это так:

А: #0000FF, Б: #FF0000, С: #000085. Первая строка, столбцы с первого по третий — A. Первая строка, четвертый столбец — B. Вторая строка, первый столбец — A. Вторая строка, второй столбец — C. Вторая строка, третий столбец — A. Вторая строка, четвертый столбец — B.

Это позволяет сжать попиксельное описание в нескольких местах («столбцы с первого по третий…») и сэкономить несколько символов за счет определения повторяющихся цветов в своего рода словаре заранее. В визуальной точности изменений нет. Информация сжата без потерь.

Горизонтальные прямоугольники синего и красного цвета с одним темным пикселем размером 2x2.

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

А: #0000FF, Б: #FF0000. Первая строка, столбцы с первого по третий — A. Первая строка, четвертый столбец — B. Вторая строка, столбцы с первого по третий — A. Вторая строка, четвертый столбец — B.

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

Равномерно синие и красные горизонтальные прямоугольники.

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

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

При кодировании в формате GIF тонкие градиенты, такие как тени, становятся пестрыми, а отдельные пиксели выделяются из окружения:

Розовые цветы на зеленом фоне.

На практике сочетание сжатия без потерь и квантования палитры означает, что GIF не очень полезен в современной веб-разработке. Сжатие без потерь недостаточно для уменьшения размера файлов, а уменьшение палитры означает очевидное снижение качества.

В конечном счете, GIF — это всего лишь эффективный формат для кодирования простых изображений, которые уже используют ограниченные цветовые палитры, резкие края вместо сглаживания и сплошные цвета вместо градиентов — все эти варианты использования гораздо лучше подходят для других форматов. Меньший по размеру и более функциональный PNG часто является лучшим выбором для растровых изображений, хотя оба они намного уступают SVG с точки зрения размера файла и визуальной точности для таких случаев использования, как значки или штриховая графика, где вектор сияет. Наиболее распространенным вариантом использования GIF в современном мире является анимация, но существуют гораздо более эффективные и доступные современные видеоформаты, способные служить этой цели.