Сжатие изображений для веб-разработчиков
- Введение
- Что может быть хуже, чем заставлять пользователей платить за загрузку вашего сайта
- Большие изображения – большие проблемы
- Форматы изображений
- Компромисс между качеством и размером
- Качество изображений, размер и различные разрешения экранов.
- Размеры изображений, восприятие пользователя и время загрузки
- Нестандартные изображения
- Улучшения сжатия PNG за счёт лучшей обработки.
- Заключение
Введение
На данный момент изображения остаются самой большой по объёму трафика частью контента веб-страницы. Поэтому для того, чтобы сайт быстро загружался и быстро реагировал на действия пользователя, веб-разработчикам чрезвычайно важно жёстко контролировать размер изображений и их качество. В этом смысле «попасть в яблочко» не так просто.
Вы можете автоматизировать создание изображений и получать «неплохое» качество в большинстве случаев, но для получения наилучших результатов, вам придётся следить за уровнем качества с помощью ваших, человеческих, глаз. В этой статье представлена небольшая историческая справка, причины и методы сжатия изображений, чтобы понимать и правильно адресовать проблемы сжатия изображений при работе с вашим сайтом.

Памятка: Контрольный список по сжатию изображений
- Сжимайте изображения в подходящем формате в наименьшем приемлемом качестве:
- Настройте уровень сжатия всех изображений вручную, где это возможно.
- Автоматизируйте сжатие остальных, чтобы достичь наивысшей производительности.
- Рассмотрите возможность использования формата WebP для ваших изображений;
- Сохраняйте ваши изображения с прогрессивными настройками. Это благоприятно скажется на восприятии пользователями вашего сайта;
- Исследуйте другие интересные способы достичь лучшего сжатия или прозрачности. Мыслите нестандартно.
Почему важно быть маленьким
Если говорить очень упрощённо, чем больше страница, тем дольше она загружается. Проведено множество исследований, которые показывают, что пользователи медленных сайтов проводят меньше времени на сайте, меньше нажимают на ссылки и рекламные блоки, и тратят меньше денег. Маленькие сайты, такие как AutoAnything, которые вдвое сократили время загрузки сайта, отметили увеличение выручки на 13 процентов. А исследования на крупных сайтах, таких как Amazon, показали, что их выручка снижается на 1 процент на каждые 100 миллисекунд задержки загрузки.
Что может быть хуже, чем заставлять пользователей платить за загрузку вашего сайта
Вдобавок к тому, что большие страницы отрицательно влияют на производительность стационарных компьютеров, больше всего раздутые страницы заставляют страдать мобильных пользователей. Страница размером в 1Мб не только бесконечно долго загружается, она также может неприятно отразиться на счёте за услуги связи.
Даже так называемые «безлимитные» тарифные планы для мобильных телефонов, на самом деле таковыми не являются. Большинство из них предоставляют около 2Гб за фиксированную плату, а превышение этого лимита может тарифицироваться дополнительно. Не говоря уже о том, что есть множество мест в мире, где отсутствуют безлимитные тарифные планы и где стоимость загрузки информации является серьёзной проблемой для пользователей.
Большие изображения – большие проблемы
Мы можем видеть, что наибольшую долю в объёме страницы занимают изображения. Это плохие новости для мобильных устройств, где картинка буквально стоит тысячи слов.
Неправильная обработка изображений часто становится причиной плохой производительности. Слишком большие, недостаточно сжатые изображения или изображения очень высокого качества могут оказаться слишком тяжёлыми, что оказывает прямое влияние на скорость загрузки вашего сайта. Выбрать правильный метод сжатия и достичь при этом наилучших результатов несложно, зная об особенностях этого процесса.
Виды алгоритмов сжатия
В общем случае, существует две стадии сжатия изображения: с потерей данных и без потери данных. Алгоритмы сжатия с потерей данных обработают исходный поток данных так, что потерянные данные не могут быть восстановлены при декомпрессии.
Большинство алгоритмов сжатия изображений с потерей данных основаны на особенностях человеческого зрения и часто избавляются от информации, которую мы на самом деле не можем видеть, за счёт этого уменьшая объём. Например, ограничивая количество цветов, использованных в изображении. Меньше цветов – меньше объём данных для передачи. Как правило, когда вы сохраняете изображение в формате, поддерживающем потерю данных, вы выбираете некоторое значение, представляющее собой соотношение качества изображения к его размеру.
Опытные веб-разработчики понимают, что существует золотая середина, когда качество достаточно высокое, а размер файла сокращён, насколько это возможно.
До | После |
0.123, 1.2345, 21.2165, 21.999, 12.123 | 0,0,20,20,10 |
Рис. 1 – Пример сжатия с потерей данных. Значения округляются до ближайшего числа, кратного 10. Это преобразование необратимо.
После сжатия с потерей данных применяется сжатие без потерь, когда данные при декомпрессии восстанавливаются в исходное состояние. Следующие алгоритмы сжатия позволяют восстановить исходные данные напрямую без какой-либо потери точности или иной информации. Для изображений популярными кодеками являются LZ77, RLE и Арифметическое кодирование. Алгоритмы сжатия без потерь являются основой сжатия, часто выжимая последние проценты экономии из вашего контента.
До | После |
aaaaabbbbbcccddddeeeeffffaaaaabb | a5b4c2d4e4f4a5bb0 |
Рис. 2 – Пример сжатия без потерь. Количество символов, идущих подряд, определяется числом, после символа. Мы можем точно восстановить исходные данные. Заметьте, что если подряд идут не больше двух символов, имеет смысл просто оставить их как есть. Вы видите такой пример в конце потока в виде ‘bb’.
Форматы изображений
Формат изображений для обеспечения экономии размера при сжатии, как правило, соединяет вместе различные алгоритмы сжатия с потерями и без. Существует несколько форматов, поддерживаемых веб браузерами, с различными характеристиками. Точнее, не существует (пока) одного формата «на все случаи жизни». Разные виды изображений должны быть закодированы в разные форматы, в зависимости от того, что это за изображение, от того, какие форматы поддерживает браузер и от потребностей конкретной веб-страницы.
В общем случае веб-разработчику при выборе формата изображения нужно ответить на следующие вопросы:
- Нужна ли прозрачность?
- Нужна ли анимация?
- Нужно ли высокое качество изображения?
'Lena' – распространённое изображение для оценки и сравнения алгоритмов сжатия изображений.
PNG – простой формат, поддерживающий прозрачность и сжатие без потерь. Он позволяет вам выбрать альфа-канал для вашего изображения, чтобы замаскировать прозрачные области, а также, по желанию, активировать компрессор данных Deflate.
(Deflate – это комбинация двух компрессоров: LZ77 и Кода Хаффмана). Поскольку сжатие происходит без потерь, качество изображения остаётся идентичным исходному. Однако это порождает проблемы: размеры файлов обычно получаются раздутыми, не такими маленькими, какими они могут быть.
GIF – ещё один формат, поддерживающий прозрачность наряду с анимацией. Формат GIF содержит две стадии сжатия: этап сжатия с потерей данных или определение палитры (ограничение цветовой гаммы изображения до 256 цветов), за которым следует сжатие без потерь по алгоритму LZW. Процесс квантования цветов изображения до всего лишь 256 производит агрессивное снижение качества в пользу меньшего размера, что также хорошо влияет на сжатие на этапе LZW.
Большинство современных передовых компрессоров больше всего выигрывают от совмещения нескольких этапов кодирования. Один этап может изменить поток данных так, что последующие смогут сжать его лучше, чем сам исходный поток. Популярные архиваторы, такие как 7zipсоединяют в себе кодирование словаря по алгоритму LZ, производящее уменьшенное подмножество символов, которое может быть более эффективно использовано в алгоритме Цепь Маркова.
Или, например, вы можете применить алгоритм сжатия без потерь поверх существующего формата с потерей данных, полученного от графического процессора, чтобы ещё больше сжать данные. Наибольший выигрыш можно получить от правильной комбинации алгоритмов.
Если вам не нужна прозрачность или анимация, JPG – лучший формат для вас.
Изначально он был разработан, чтобы обеспечивать сжатие высококачественных фотографий, однако он предоставляет набор настроек сжатия с потерей данных, позволяя вам найти компромисс между качеством сжатия и размером изображения, подходящий для вашего приложения.

Если вы ищете что-то более универсальное среди форматов изображений, стоит обратить внимание на WebP. Этот формат может похвастать не только лучшим соотношением качества сжатия и размера, но также и поддержкой прозрачности, и анимации. Он использует сжатие, как с потерей, так и без потери данных, и во многом так же, как формат JPG, позволит вам определить подходящий уровень качества и размера файла.
Конечно, новый формат пока не поддерживается всеми браузерами, поэтому веб-разработчики, которые уже внедрили его, сейчас сталкиваются с проблемами юзабилити. Несмотря на это, 30% экономия, по сравнению с JPG наряду с возможностью адаптации формата на уровне сервера доказывают, что WebP – доминирующий формат для любых сайтов, где размер изображений представляет проблему.
Сжатие | Без потерь | С потерями | Прозрачность | Анимация | |
PNG | Хорошее | Да | Нет | Полная | Нет |
GIF | OK | Да | Да | Бинарная | Да |
JPG | Хорошее | Да | Да | Нет | Нет |
WebP | Отличное | Да | Да | Полная | Да |
Рис. 3 – Особенности некоторых форматов, поддерживаемых браузерами.
Компромисс между качеством и размером
Для тех изображений, качество которых вы не можете изменить, очевидно, что наибольший выигрыш вы можете получить, только вручную оптимизировав качество, чтобы получить наименьший файл. На сайте Помощи Вебмастерам Google есть замечательное видео, которое покажет вам несколько путей тестирования качества вашего изображения и как правильно проверить его восприятие.
Кроме того, как показывает проект imgmin, как правило, при сжатии JPG на уровне от 75 до 100 восприятие качества изменяется незначительно:
Это значит, что многие изображения выглядят хорошо для обычного пользователя на уровне качества 75, но вдвое меньше размером, чем, если бы они были на уровне качества 95. По мере того, как качество опускается ниже 75, появляются более различимые визуальные изменения, а экономия в размере уменьшается.
Следующая таблица показывает, что на большинстве крупных веб-сайтов уровень качества колеблется около 75 практически для всех их изображений JPG:
Сайт | Качество JPG |
Эскизы картинок Google | 74-76 |
Полноразмерные изображения на Facebook | 85 |
Изображения JPEG на главной странице Yahoo | 69-91 |
Изображения JPEG на главной странице Youtube | 70-82 |
Изображения в Википедии | 80 |
Фоновое изображение на Windows live | 82 |
Изображения JPEG пользователей Twitter | 30-100 |
Рис. 4 – Средний уровень качества JPG, используемый на крупнейших сайтах.
Настройка параметров каждого изображения на вашей странице, проводимая с целью сбалансировать качество и размер, позволит вам добиться наилучшей экономии при наилучших уровнях качества. Однако на крупных сайтах размещено множество изображений, и они обычно не могут вручную оптимизировать каждое, поэтому индивидуальная для каждого изображения настройка уровня качества практически невозможна.
Некоторые разработчики выбрали более автоматизированный подход к этому типу кодирования, часто применяя к изображениям собственные эвристические процессы и процессы кодирования во время разработки. Этот способ обработки подходит в качестве золотой середины между настройкой и автоматизацией, которая поможет большинству веб-разработчиков. Вы можете также использовать различные приложения, например JPEGmini, которое также автоматически настроит ваш уровень сжатия JPG, чтобы получить наилучшее качество.
Немного радикальным подходом, который используют разработчики, чтобы уменьшить размер изображения, является преобразование всех простых значков и изображений в файлы SVG, и их растеризация на стороне клиента перед отображением.
Этот процесс – компромисс между размером файла и быстродействием клиента: он экономит трафик, но провоцирует большую нагрузку на стороне клиента, чтобы реконструировать изображение при рендеринге.
Как таковой, формат изображений SVG сильно отличается от других типов файлов тем, что это векторный формат, то есть окончательное изображение генерируется процедурно, используя информацию об описанных в файле формах, до получения определённого окончательного изображения. Когда изображение SVG загружается, оно конвертируется в растровый формат (двумерный массив пикселей, вроде битовой карты) перед тем, как будет отображено.

Рис. 5 – Пример растрового изображения (слева) в сравнении с векторным изображением (справа). Заметьте, что векторное изображение намного проще и менее детализировано. Это из-за того, что данный формат не предназначен для создания высококачественных изображений.
Думайте об SVG как о формате, который позволяет вам хранить «описание» изображения в очень небольшом объёме памяти и генерировать высококачественное, независимое от разрешения изображение на клиенте, вне зависимости от размера исходных данных. Одно из ограничений формата SVG заключается в том, что он может быть использован для представления только определённого вида изображений, иначе говоря, векторные изображения должны быть упрощёнными и использовать набор примитивных типов, чтобы определить, как отобразить цвета на экране.
Луг в прериях, например, потребовал бы слишком много сложных форм, чтобы добиться экономии при сжатии. Растровые изображения лучше всего использовать для фотографий и других информационно-плотных изображений, тогда как векторные изображения прекрасно подходят для логотипов и других простых шаблонов изображений.
Качество изображений, размер и различные разрешения экранов.
Одна из больших проблем, с которой сталкиваются разработчики – это количество пикселей монитора относительно размера создаваемых изображений. То есть, если автор создаёт изображения для настольного веб-сайта, скорее всего, размеры изображений были выбраны им для просмотра на больших настольных мониторах. Однако мобильные устройства создают проблему, так как размеры их экранов гораздо меньше и их трафик гораздо дороже. Как следствие пользователи будут загружать изображения размером больше, чем им требуется или чем они могут отобразить.
Есть несколько способов решить эту проблему.
Одно из решений заключается в предварительном, автономном, расчёте размеров изображений для каждого возможного разрешения. Большинство статичных веб-сайтов могут легко добиться этого на этапе создания, возможно изменяя размеры изображений с помощью наборов инструментов, типа Grunt.
Преимущества этой техники в том, что изображения должным образом кэшируются в том разрешении, которое необходимо каждому устройству, и вы не теряете время или трафик, чтобы доставить информацию клиенту. Однако с другой (отрицательной) стороны, это сумасшествие – управлять экспоненциально возрастающим объёмом данных и дополнительной логикой, чтобы отправлять информацию, предназначенную для конкретных пользователей.
Если вы заинтересованы в использовании Grunt для генерации этого контента, я бы порекомендовал попробовать наш способ создания адаптивных изображений с помощью Grunt совместно с ImageMagic для автоматической генерации изображений с предварительно рассчитанными размерами.
Для тех, кто использует Node/Express, в качестве альтернативы подойдёт express-processimage, или вы можете создать скрипт, вызывающий для вас ImageMagick.
Однако, одна из пока-не-разрешённых проблем с этим подходом – найти хорошее решение для управления ростом объёма ваших данных. Что касается логики, есть надежда, что атрибут srcset решит эту проблему (движок WebKit, как вы знаете, поддерживает его, Blink намерен реализовать поддержку, FF будет его поддерживать в iOS).
А пока, можно использовать polyfill для srcset в качестве промежуточного шага.

Другой подход, рассчитанный на взрывное распространение мобильных устройств с большим разрешением экрана, состоит в том, что вы можете поиграть с качеством изображения, его размерами и ценой преобразования размера на стороне клиента.
Фактически, вы можете хранить изображение с удвоенным разрешением (масштабированное), однако, когда вы экспортируете его в формат с потерей данных, вы выбираете очень низкое качество (что приводит к лучшему сжатию). Идея в том, чтобы выбрать такой уровень качества, при котором сжатое большее изображение будет меньше по размеру, чем сжатое меньшее изображение.
На стороне клиента вы можете указать желаемые размеры изображения (которые должны быть меньше текущих, поскольку изображение было масштабировано). Веб-браузер уменьшит изображение до желаемого разрешения, в процессе чего сгладятся шумы, возникшие при низкокачественном сжатии; в некоторых случаях – полностью. Окончательный результат – меньший файл, который легко масштабируется в несколько разрешений экрана и не демонстрирует заметного снижения качества.
Размеры изображений, восприятие пользователя и время загрузки
По сути, единственное, что важно, это чтобы пользователю казалось, что сайт загружается быстро. Быстро появляется, значит быстро загружается, поэтому видимая производительность гораздо важнее, чем настоящая скорость.
Существует два основных способа отображать изображения в сети.
- Подождать полной загрузки изображения и отобразить его после загрузки;
- Отобразить часть изображения, загруженную на данный момент.
Браузеры не используют первый вариант, так как это приводит к наиболее медленной загрузке страницы.
Большинство сайтов в сети построено на втором варианте. Я уверен, мы все знакомы с постепенным «разворачиванием» изображения сверху вниз. Это происходит потому, что обычно изображения хранятся в растровом порядке, иначе говоря, первые байты изображения, которые получает браузер, находятся в левом верхнем углу изображения и дальше идут по порядку горизонтально. Очевидно, что если мы храним изображение по-другому, мы можем изменить порядок передачи битов по сети, что изменит то, как изображение отображается на экране.
Этот «прогрессивный» метод кодирования может оказать благоприятное воздействие на пользователя, заставив его думать, что страница загружается «быстро» (заметьте, что это утверждение спорно и зависит от пользователя). Это достигается кодированием нескольких дополнительных версий изображения меньшего разрешения, которые могут быть быстрее доставлены пользователю, что позволяет ему увидеть очертания изображения, которые постепенно, по мере загрузки, становятся всё чётче.
На Coddinghorror.com есть прекрасный пример визуальной разницы этих двух технологий. Вы можете видеть, как стандартный метод разворачивает изображение сверху вниз, тогда как прогрессивный делает его всё чётче по мере получения новых данных.
Линейная | Прогрессивная |
![]() | ![]() |
Рис. 6 – Пример линейной и прогрессивной загрузки изображений.
Если вы не любите единорогов, можете также посмотреть более подробный пример в блоге Патрика Минана или даже протестировать ваши изображения, используя интерактивный тестер Патрика.
Использовать это свойство для ваших изображений чрезвычайно просто: Просто сохраните ваши GIF или PNG изображения с опцией «interlaced», или JPEG изображения с опцией «progressive» - и вашим пользователям начнёт нравиться время загрузки вашего веб-сайта. Хотя, стоит уточнить, что прогрессивные изображения пока не поддерживаются всеми браузерами, и загрузка прогрессивного изображения на таких платформах может на самом деле ухудшить производительность.
Нестандартные изображения
Интернет полон гениальных веб-разработчиков, поэтому никакая статья по сжатию изображений не будет полной без упоминания некоторых прекрасных взломов, обходных путей и вообще впечатляющих вещей, сделанных этими разработчиками, которые позволили им создать впечатляющие маленькие, но качественные, изображения.
Разделение вашего прозрачного слоя для улучшения сжатия.
Разработчики игр под HTML5 обычно пересылают больше изображений, чем ваш обычный веб-сайт, большинство из которых – прозрачные рамки для анимации. К сожалению это вынуждает делать PNG изображения, чтобы добиться прозрачности. Однако несколько разработчиков изобрели обходные пути, чтобы получить лучшее сжатие и прозрачность изображений. Например, вы можете разделить данные по цветам и прозрачности в два разных файла изображений (например, два файла JPG), и восстановить их на клиенте, используя элемент CANVAS. Хотя это и увеличивает количество запросов в сети, экономия в размере изображения может быть существенной для разработчиков, у которых на сайте множество прозрачных изображений.
Стоит отметить, что может быть быстрее просто использовать -webkit-mask там, где это поддерживается вместо всего этого сумасшествия с canvas. К счастью я создал библиотеку, чтобы помочь вам в этом.
Улучшения сжатия PNG за счёт лучшей обработки.
Опция Deflate в PNG – это кодер без потерь, но это не должно останавливать вас от использования предобработки с потерей качества, если вы хотите. Инструменты обработки изображений, такие как ImageAlpha и ImageOptim, могут сжать ваше PNG изображение, используя метод с потерей данных в качестве предварительной обработки перед кодированием изображения в PNG формат. Это создаёт двухступенчатый процесс, где сжатие с потерями и без потерь осуществляются двумя разными приложениями. Результаты впечатляющие: уменьшение пространства цветов позволяет сжатию без потерь найти и обработать больше совпадений в файле, что выливается в лучшее сжатие.
После того, как вы сохранили изображение в формате PNG, можно переупаковать ваши данные PNG, используя более совершенные компрессоры, чтобы сгенерировать меньший файл PNG. Такие инструменты, как advPNG, возьмут ваш файл PNG и прогонят его через улучшенный Deflate компрессор, чтобы получить меньший файл. Или вы можете совместить PNGOUT с инструментами, вроде OptiPNG или Zopfli, чтобы добиться того же эффекта. Конечно, каждая из этих систем выдаёт немного разные результаты, в зависимости от входных данных, поэтому мудрой мыслью будет использовать систему, которая произведёт сжатие несколькими компрессорами и выберет наименьший файл. Если вам лень её создавать, ScriptPNG возьмёт на себя всю тяжёлую работу.
Не все анимации созданы равными.
Команда SublimeText запустила вебсайт, где они хотели широко использовать анимацию для показа особенностей их редактора. Вместо использования видео или стандартного GIF, они создали собственную систему анимации и сжатия, чтобы получать прекрасную анимацию при гораздо меньших размерах файлов. Этот метод позволяет им отображать высококачественную анимацию на разных платформах без необходимости использовать сложное видео или flash плагин.
Существует больше одного пути к отзывчивым изображениям.
Поскольку восприятие пользователя – это самый важный элемент сайта, стоит сказать, что существуют другие способы создать сайты, которые «воспринимаются» как быстрые. Недавно BBC изменили подход к обработке отзывчивых изображений. Их метод позволяет клиенту загрузить сначала маленькое изображение (чтобы создать видимость картинки), а затем получать изображения в высоком разрешении с помощью ленивой загрузки при необходимости. Вы можете найти более детальное описание этого способа, а также версию с открытым кодом, чтобы попробовать её на вашем сайте.
Заключение
Изображения – это хитрый тип контента, который может улучшить качество и восприятие пользователями вашего сайта, но также может подорвать ваши усилия по его быстрой загрузке и отзывчивости. Перед тем, как вы выложите ваш сайт в сеть, убедитесь, что он соответствует контрольному списку по сжатию изображений
- Сжимайте изображения в подходящем формате в наименьшем приемлемом качестве:
- Настройте уровень сжатия всех изображений вручную, где это возможно
- Автоматизируйте сжатие остальных, чтобы достичь наивысшей производительности
- Рассмотрите возможность использования формата WebP для ваших изображений;
- Сохраняйте ваши изображения с прогрессивными настройками. Это благоприятно скажется на восприятии пользователями вашего сайта;
- Исследуйте другие интересные способы достичь лучшего сжатия или прозрачности. Мыслите нестандартно.
Полезные инструменты
- ImageAlpha
- ImageOptim
- advPNG
- ImageAlpha w/ Canvas Helper Library
- Interactive tool for testing progressive images