Десять причин нашего перехода с иконочного шрифта на SVG

У нас на lonelyplanet.com используется много иконок, и недавно перед нами встала задача перенести их из иконочного шрифта в SVG-файлы. В рамках этой статьи я хотел бы поделиться причинами, которые нас привели к этому решению, обозначить некоторые ограничения со стороны SVG, с которыми мы лично столкнулись, а также поделиться историей о том, как нам удалось с ними справиться.

1. Разделение функций

До недавнего времени на lonelyplanet.com использовался подключённый шрифт, в котором все иконки были упакованы в один файл вместе с ним, причём глифы хранились в области частного использования Unicode. Такое решение нас полностью устраивало, поскольку для загрузки всех иконок требовался всего один HTTP-запрос, но, в то же время, данное решение ограничивало возможность управления приоритетом загрузки ресурсов.

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

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

Контраргумент

Объединять подключённый шрифт и иконочный шрифт вовсе необязательно, их можно хранить отдельно. Наверное, мы бы так и сделали, если бы решили остановиться на использовании иконочного шрифта.

2. Некоторые устройства не поддерживают области частного использования Unicode

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

Я уже и не помню, на каком устройстве проводил тестирование, когда обнаружил, что одна из наших иконок с «птичкой» была заменена иконкой цветной печати. Страница казалась мне дилетантской и «сломанной», что, без сомнения, послужило дополнительным стимулом для перехода на SVG.

3. Чёрные квадратики и крестики в Opera Mini

Добиться правильной поддержки и распознавания начертания шрифта никогда не было просто. Уверен, что вы все видели эту иллюстрацию отрисовки шрифта Awesome в Opera Mini:

пример

Я не буду вдаваться в подробности, так как проблемы поддержки Opera Mini и многих других платформ уже хорошо описаны в этой статье от @kaelig.

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

На данный момент, мы получаем не очень большую долю трафика с Opera Mini. Однако, важно помнить, что мы — компания, связанная с сферой туризма, и мы обязаны предоставляет свои услуги в любых условиях, при любом качестве подключения к сети. Так что нам всегда следует стремится делать наш сервис более доступным. Наибольшую уверенность в том, что пользователь увидит адекватное отображение страницы, нам предоставляют форматы SVG и PNG.

4. В последнее время поддержка иконочных шрифтов в Chrome отвратительна

В Chrome Canary и Beta недавно появилась отвратительная ошибка при отображении шрифтов. Если вы её пока не встречали, вкратце — после определённого периода неактивности страницы шрифт сбрасывается и заменяется на системный.

Когда происходит сброс шрифта, ваш текст отображается в Georgia, и, хоть это и не критически важный момент, он все же действует на нервы. А вот когда тот самый шрифт отвечает и за отображение иконок, страница внезапно заполняется мусором из чёрных квадратиков, и пользоваться нормально ей становится невозможно.

Эта ошибка проявилась как раз когда мы осуществляли переход на SVG. В результате, когда нам начали поступать первые отчёты об обнаружении этой ошибки на нашем сайте, мы уже перешли на новую систему и вздохнули с облегчением.

Контраргумент

Эта ошибка так и не добралась до официальной сборки Chrome.

5. Чётче иконки в Firefox

Мы обнаружили, что в Firefox наш шрифт отображается чуть жирнее, чем в других браузерах. Когда дело касается текста, в этом нет ничего страшного (хотя, и хорошего тоже мало), а вот из-за жирных иконок вся страница выглядит неухоженной и аляповатой. Используя SVG нам удалось добиться нормального отображения иконок во всех браузерах.

6. Не всегда есть возможность использовать генерируемый контент

Если вы хотите использовать шрифтовые иконки в CSS, вам придётся прописывать их, используя свойство content для генерируемого контента. Иногда это может быть затруднительным, потому что вы уже используете псевдоэлементы :before и :after, да и не все элементы поддерживают генерируемое содержимое.

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

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

7. Проще позиционирование

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

Используя SVG, нам стало гораздо легче их позиционировать. А для единого кроссбраузерного отображения мы используем background-size: cover, и просто делаем размеры элемента резиновыми.

8. Многоцветные иконки

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

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

Контраргумент

Многоцветный иконочный шрифт можно получить посредством наложения иконок.

Тем не менее, сделать это качественно та еще задачка: если правильное кросс-браузерное позиционирование одного глифа — это довольно непростой фокус, то с двумя всё становится ещё сложнее.

9. SVG позволяет использовать иконки с анимацией

Мы пока не воспользовались этим свойством, но, вполне возможно, что мы ещё рассмотрим такую возможность, раз уж она у нас теперь есть.

10. Нам не давала покоя мысль, что мы используем хак

Применение шрифта для отображения иконок нам всегда казалось хаком. Бесспорно, он великолепен, однако суть всё же состоит в маскировании объекта одного типа под какой-то другой.

Как насчёт преимуществ использования шрифта?

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

Стоит признать что нам было бы намного сложнее справиться с этими проблемами без огромной работы, проделанной командой Filament Group на Grunticon.

Вариативность цвета

Огромным преимуществом иконочного шрифта является его гибкость. У него нет ограничений в количестве вариаций цвета, его можно легко менять в зависимости от текущего состояния (:hover, :focus, .is-active и др.). Это редкая роскошь, которая очень способствует ускорению разработки. И это одна из причин того, почему мы так долго откладывали переход на SVG.

Наше решение

Для обеспечения схожей функциональности есть несколько решений, хотя все они пока имеют свои определенные ограничения. Мы наконец нашли собственную технику, которая нас вполне устраивает, и которая, в тоже время, находится на границе гибкости и ресурсоемкости.

В Grunticon каждая иконка объявляется отдельно, таким образом избегается использование спрайтов. Мы последовали их примеру, но, хотя мы и использовали для каждой иконки один CSS-селектор, все они были представлены в шести цветах, как показано здесь.

иконки

Так как мы всего лишь несколько раз дублировали одну и ту же иконку в одном и том же файле, его размер сжался до размера одной иконки (плюс около 50 байтов на GZIP-указатели). Это значит, что мы можем создать практически любое количество вариаций цвета почти без дополнительных затрат со стороны ресурсов. Вот пример работы этого приёма на jsFiddle.

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

С помощью этого приёма можно также без усилий применять к иконкам изменения, привязанные к состоянию, изменяя позиционирование фона.

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

Поддержка браузеров

Иконочный шрифт работает во всех браузерах вплоть до IE8, в отличие от SVG. Для нашего варианта реализации нам также нужна поддержка background-size, которая является почти такой же, как и для SVG.

Наше решение

У Grunticon реализован креативный подход к старым версиям браузеров. Он создаёт PNG-версии SVG-файлов, и передаёт их старым браузерам в зависимости от того, поддерживают они SVG, или нет.

В связи с отсутствием поддержки background-size, мы решили для старых версий браузеров использовать только часть иконок (только очень важные, такие как логотип). Мы могли бы обойтись без этого CSS-свойства, с помощью изменения размеров всех исходных SVG-файлов, однако, поскольку многие иконки используются с разными вариантами размера, мы решили использовать только иконки первостепенной важности с одинаковым размером в спрайте.

Мы также пробовали использовать этот полифил background-size, однако вскоре отказались от него. Я бы крайне не советовал его использовать, если вам нужно изменить размер больше, чем для одного-двух изображений. Обнаружилось, что его применение для более чем двух изображений приводит к постоянным сбоям в IE8.

Стоило ли оно того?

Результаты использования обоих приёмов независимы от разрешения, масштабируемы и довольно легки по объёму, так что с точки зрения пользователя оба являются хорошими. Взвесив все за и против мы решили, что SVG дает нам больше уверенности в том, как наше приложение будет выглядеть для каждого пользователя, и этот дополнительный элемент контроля сыграл решающую роль.

Мы используем SVG на Lonely Planet с ноября 2013 года, и пока никаких проблем по разработке в этой части не возникало.