Figma to Frontend: как мы автоматически синхронизируем дизайн и код

4c58bbee08877ca52df903d67cfb7f3a.jpg

Меня зовут Анастасия Кабалкина, я Head of design в VK Tech. В этой статье я расскажу, как мы синхронизировали треть нашей дизайн-системы за счет автоматической генерации дизайн-токенов и компонентов.

Продукты и особенности разработки

Наше направление занимается разработкой финансовых и аналитических b2b-продуктов — VK Tax Compliance, VK GRC, VK Data Symphony, VK Process Mining и т.д. Помимо сопровождения решений, уже выпущенных на рынок, мы ежегодно реализуем порядка 10 продуктовых инициатив, и наш продуктовый портфель постоянно (и очень быстро) растет и развивается.

У такого быстрого роста есть обратная сторона — контролировать качество интерфейсов и обеспечивать единство UX/UI-паттернов становится сложно и одновременно очень важно. 

«Рассинхрон» дизайна и фронта

Несколько лет назад мы, как и большинство команд продуктовой разработки, столкнулись с проблемой «рассинхрона» дизайна и фронта.

В нашей дизайн‑системе периодически появляются новые компоненты, уже существующие дорабатываются и развиваются, некоторые устаревают — и далеко не все эти изменения со 100%‑ной точностью переносятся на frontend (по очень разным причинам).

В какой‑то момент «рассинхрон» стал критическим — почти каждый компонент на frontend‑е хоть и немного, но расходился с дизайном.

Очевидно, что даже самые мелкие несоответствия в своей совокупности очень сильно искажают общую картинку.

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

Наши попытки синхронизировать дизайн и frontend «традиционными» методами не увенчались успехом.

Нам не удалось ни встроить в процесс разработки отдельный этап дизайн‑ревью, ни вручную сверить все компоненты, ни выделить специальное время в спринтах под эту активность — у нас всегда находились задачи приоритетнее.

Но и смириться с «рассинхроном» тоже нельзя, потому что от него в конечном итоге страдают все — и дизайнеры, и разработчики, и аналитики, и presale‑менеджеры, и тестировщики, и, что важнее всего, пользователи и бизнес.

Идея автогенерации стилей и компонентов из Figma-файла 

Что делать, если работу выполнять надо, а времени на неё нет? Единственный вариант — автоматизировать.

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

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

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

Общая схема процесса выглядит так:

  1. Мы забираем данные напрямую из Figma‑файла через API.

  2. Пропускаем их через самописный генератор кода (далее — Figma‑генератор).

  3. На выходе получаем дизайн‑токены стилей в форматах css, json, ts (но можно и в любом другом), иконки в svg и код для компонентов на react (javascript).

  4. Сгенерированные компоненты автоматически помещаются в storybook.

Схема генерации.

Схема генерации.

Источником кодогенерации является Figma‑файл, поэтому в нем обязательно должны быть отражены все параметры стилей и компонентов.

Для этого мы придумали специальный формат организации стилей и параметризации компонентов в Figma, который подходит для генерации и при этом не конфликтует с общепринятыми подходами к оформлению дизайн‑систем.

Оформление Figma-файла для автогенерации стилей

Текстовые стили, цвета и эффекты оформляются стандартным способом через Local styles (Text styles, Color styles, Effect styles) и генерируются как есть без дополнительных настроек.

Для генерации стилей, которые нельзя оформить через Local styles (в нашем случае это border, borderRadius, spacing и iconSize*), создаются специальные компоненты. Каждому компоненту присваивается название стиля и те параметры, за которые этот стиль отвечает.

Например, для генерации стиля обводки создается компонент с названием стиля (допустим, default, fieldBorder, imageBorder или любым другим на усмотрение дизайнера и frontend‑разработчика) и присвоенными параметрами Stroke color и Stroke width. Если стилей обводки несколько, то для каждого стиля создается отдельный компонент.

Пример оформления стилей обводки.

Пример оформления стилей обводки.

*Код для генерации стилей был написан до появления Variables. Сейчас у нас в планах доработать в этой части Figma‑генератор, чтобы генерировать стили и из Local styles, и из Variables.

Оформление Figma-файла для автогенерации компонентов

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

Вот несколько примеров таких характеристик:

  • наличие вариантов, отличающихся друг от друга комбинациями параметров,

  • наличие псевдосостояний (псевдоклассов), определяющих стили компонента в зависимости от состояния, в котором компонент находится (hover, focus, active, checked),

  • компоненты могут содержать в себе другие компоненты (например, компонент icon внутри кнопки),

  • компоненты могут конфигурироваться (например, icon внутри кнопки может отображаться или нет, а также может располагаться справа и/или слева),

  • компоненты могут содержать текст (например, label кнопки, чекбокса или радиобаттона), а также фигуру или кривую (например, галочка внутри чекбокса или круг внутри радиобаттона).

Чтобы компонент сгенерировался корректно, Figma‑генератор должен получить из Figma‑файла всю вышеперечисленную информацию и на её основании сгенерировать код компонента на React (JavaScript). Для этого мы разработали несложную методику верстки и параметризации компонентов в Figma на основе функций Auto layout и Properties.

Все наши компоненты верстаются с помощью функции Auto layout:

  • параметрами Horizontal gap between items, Horizontal и Vertical padding мы устанавливаем падинги и внутренние отступы,

  • параметрами Min width, Max width, Min height и Max height определяем пределы ширины и высоты компонента,

  • устанавливаем возможность «обрезать» не помещающийся текст параметром Truncate text,

  • устанавливаем допустимое количество строк в текстовом контейнере параметром Max lines.

Кроме того, мы также передаем на frontend тип поведения компонента с помощью параметров Horizontal и Vertical resizing (будет ли размер компонента зависеть от его контента (hug) или компонент будет занимать всё отведенное для него место (fill)).

Пример настройки компонента status.

Пример настройки компонента status.

Примеры оформления свойств

Для оформления свойств с множественными значениями (например, свойство size со значениями xs, s, m, l) мы используем функцию Variant property. Таким же способом задаются свойства, принимающие значения true/false, например, disabled, isNegative, isLoading и т. п.

Псевдосостояния (псевдоклассы) тоже задаются через Variant property, принимают значения true/false и дополнительно в названии этих состояний ставится двоеточие, чтобы Figma‑генератор смог отличить эти свойства от других (например,: hover,: focus,: active).

Булевы свойства мы оформляем стандартно с помощью функции Boolean (например, свойства showIconLeft, showFirstButton и т. п.), а для того, чтобы вставить компонент в другой компонент, областям вставки задаём параметр Instance swap property.

Пример настройки компонента button.

Пример настройки компонента button.

Если в компоненте присутствует контейнер с текстом, то такому контейнеру присваивается параметр Text с названием Children, чтобы на стороне frontend‑а была возможность «прокидывать» в компонент любой текст.

Пример настройки параметра Text.

Пример настройки параметра Text.

Достижения и ограничения автогенерации компонентов

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

Тем не менее нам удалось:

  • передать на frontend все основные параметры компонентов,

  • сгенерировать полноценные компоненты с оптимальным кодом, написанным так же грамотно, как если бы его писал квалифицированный разработчик,

  • сгенерировать компоненты с возможностью подключения к ним сторонних библиотек (например, мы самостоятельно генерируем компонент title, но компонент tooltip, появляющийся при наведении курсора на иконку «i», — это компонент AntDesign, который подключается автоматически).

Пример настройки компонента title со встраиваемым внешним компонентом.

Пример настройки компонента title со встраиваемым внешним компонентом.

У генерации есть и ограничения. Например, не все компоненты могут быть сгенерированы, главным образом потому, что это просто нецелесообразно — затраты на написание кода для генератора будут слишком большими и никогда себя не окупят (взять протестированный компонент select с уже продуманной логикой из открытой библиотеки несравнимо проще, чем с нуля написать генератор для этого компонента).

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

И, наверное, самое важное ограничение — Figma‑генератор получает данные через API, на который мы не можем влиять, соответственно, изменения в API или ограничение доступа к нему могут привести к необходимости доработки генератора или полному отказу от генерации компонентов таким способом. Да и кто знает, что будет в следующем обновлении Figma в Dev Mode?)

Что мы в итоге получили

Несмотря на то, что сгенерировать всю дизайн‑систему нам не удалось, мы получили полностью генерируемую библиотеку стилей и набор автоматически генерируемых компонентов, которые составляют около 30% от всех компонентов нашей дизайн‑системы.

Что это значит для нас?

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

Генерируемые компоненты мы можем дорабатывать и дообогащать вариантами, а затем за считанные минуты доставлять их на frontend.

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

У нас есть основа для дальнейших экспериментов, потому что Figma‑генератор можно совершенствовать и дальше.

Но самое важное, у нас (и теперь, надеюсь, и у вас) есть уверенность в том, что дизайнеры и frontend‑разработчики, работая и развиваясь вместе, способны решать самые оригинальные задачи!

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

Контакты и благодарности

Спасибо команде за интересный внутренний проект, за смелость и поддержку, за неповторимый опыт и за помощь в подготовке этой статьи!

Если у вас есть идеи и предложения, то пишите их в комментариях :)

© Habrahabr.ru