Введение
В течение последних нескольких месяцев мы реализовали корпоративную дизайн-систему VUI (Vizend UI). VUI является общим языком и соглашением, которое связывает дизайнеров и разработчиков, чтобы создавать продукты одинаковым образом. Это дизайн-система, которая объединяет дизайн-токены, компоненты, паттерны и принципы, а также автоматизацию, связывающую это с кодом. В качестве базового движка мы используем MUI (Material UI). Я кратко расскажу о том, как мы создаем дизайн-систему.
Вот порядок.① Почему была нужна дизайн-система, ② Причины использования MUI в качестве базы, ③ Дизайн-токены, используемые в дизайн-системе, ④ Принцип работы тем MUI, как дизайн-токены потребляются темами MUI и каким образом они интегрируются в реальные компоненты, ⑤ Как мы разделили конфигурацию тем по режимам, таким как мобильный/настольный и светлая/темная тема, и наконец, ⑥ Проблемы, которые еще не были решены.
1. Почему нужна дизайн-система
Дизайн-систему часто рассматривают как «набор повторно используемых UI-компонентов». Однако суть дизайн-системы, как я ее понял, заключается в общем языке и договоренности о том, как создавать продукты. Если упрощенно, то UI Kit это «корзина с LEGO-блоками», а дизайн-система включает в себя не только завод по производству блоков, но и инструкцию по сборке и сами блоки.
Отправной точкой стал ИИ. Пытаясь создать автоматическую генерацию фронтенд-кода с помощью ИИ, мы поняли, что нужна хорошо организованная и реализованная система, которую ИИ сможет понять. Кроме того, когда система будет построена, это будет второй причиной, почему можно будет проводить дизайн/публикацию с меньшим количеством людей. Опора на человеческую память и добросовестность перестает работать, особенно при небольшом количестве сотрудников, что также снижает эффективность использования ИИ. Мы установили как основную цель создание дизайнерских активов с учетом принципов VUI, таких как «обязательность и автоматизация системы».
Стоимость отсутствия дизайн-системы была конкретной.
-
Фрагментированный опыт: Хотя «кнопка» одна и та же, радиус закругления, цвет и высота могут незначительно различаться от экрана к экрану. Если не контролировать это, то каждый продукт будет выглядеть по-разному.
-
Коммуникационные затраты: Неясный запрос, вроде «синим цветом сделай немного темнее», передается между дизайнерами и разработчиками как пинг-понг.
-
Повторяющаяся работа (Toil): Простое повторение ручного применения стилей для каждого экрана отнимает время, которое могло бы быть потрачено на бизнес-логику.
Поэтому VUI стремится не просто к последовательности, а к инженерной последовательности (Engineered Consistency). Мы хотим создать общий язык, чтобы говорить «не просто «сделай фон серым», а «изменить токен Background-Default на Background-Dark», что делает дизайнерское решение данными и позволяет отслеживать и откатывать изменения.
2. Выбор MUI
Когда речь заходит о создании дизайн-системы, первым делом возникает вопрос: строить или покупать? Создавать ли все компоненты самостоятельно или использовать проверенную библиотеку и адаптировать ее под себя. Я выбрал второй вариант и основой стал MUI (Material UI).
2.1 Построение самостоятельно
Создать одну кнопку не так сложно. Проблема в том, что эта кнопкаКлавиатурный фокус, экранный читалка (ARIA), неактивное состояние, RTL, кроссбраузерностьв том, что «качество продукта» включает в себя все это. Кроме того,DataGrid, DatePicker, Autocompleteесли создавать и поддерживать даже такие высококомплексные компоненты, то ресурсы маленькой команды будут расходоваться не на бизнес-логики, а на «переизобретение колеса». Качество доступности и совместимости также будет варьироваться в зависимости от способностей команды.
2.2 Сравнение кандидатов — почему MUI победил по нашим критериям
Три основополагающих критерия, которые я установил при выборе библиотеки, были следующими: ① насколько глубокой и безопасной является настройка тем для бренда, ② достаточно ли экосистемы сложных компонентов для корпоративного интерфейса (таблицы, даты, автозавершение), ③ возможно ли согласование с Figma (синхронизация дизайна и разработки).
|
Кандидат |
Сильные стороны |
Слабые стороны |
|---|---|---|
|
Построено самостоятельно (headless комбинация) |
Полная свобода |
Наибольшие затраты на постройку, доступность и обслуживание — нереалистично для маленькой команды |
|
Ant Design |
Высококачественные корпоративные компоненты |
Дизайнерский язык сильно фиксирован — трудно переопределить бренд и глубинные темы |
|
Chakra UI |
Легкий и ориентированный на токены |
Экосистема сложных компонентов, таких как таблицы и даты, относительно незначительна |
|
MUI (по выбору) |
Глубина переопределения createTheme + экосистема x-data-grid·x-date-pickers + соответствие Material Figma Kit + огромное сообщество |
Цвета Material Design остаются → необходимо закрыть токенами и обертками |
Ключевым моментом было то, что MUIофициальный API для переопределения тем (createTheme)был. Возможность вводить стиль бренда только на уровне 'настройки (Configuration)' открыла путь для следующего принципа.
2.3 Естественное обновление — принцип “Без форков”
Наибольший риск при использовании открытого исходного кода возникает в момент форка (редактирования) оригинала для настройки. В момент форка вы навсегда отдаляетесь от обновлений upstream. Поэтому VUIне изменяет исходники MUI или папку node_modulesсоблюдает это правило. Все настройки выполняются только с помощью официального API для переопределения тем MUI. Результат — “свобода в обслуживании” — npm updateодин раз приводит к тому, что патчи безопасности и новые функции естественным образом приходят, а наше переопределение бренда остается неизменным.
Кнопка VUI просто оборачивает Button от MUI, при этом все визуальные параметры, такие как цвет, радиус, промежуток, заполняются по пути.Токен → ТемаВместо того чтобы форкать оригинал и вносить изменения, обернув его так тонко, можно не бояться, что обёртка сломается при обновлении версии MUI.
3. Figma как SSOT — кодирование дизайнерских токенов
Самое нижнее (Уровень 1) в архитектуре VUI 6-уровней этодизайнерский токенТокены абстрагируют все визуальные решения, такие как цвет (#Hex), промежуток (px), типографика, радиусв платформенно-независимые данные.Разница между хардкодингом и токенами заключается в «значении».
// Bad — 이 색이 무슨 의미인지 코드만 봐선 모른다
background-color: #2196F3;
// Good — '브랜드의 메인 컬러'임이 이름에 드러난다
background-color: tokens.color.brand.primary.main;
Ключевой принцип заключается в том, чтоFigma является единым источником правды (SSOT)Если вы хотите изменить цвет, делайте это не в коде, а в Figma, и код просто «переписывает» это решение. Для этого мы устранили необходимость вручную переписывать токены и автоматизировали это в пайплайне.
3.1 Пайплайн кодирования токенов (Figma → JSON → TS)
Пайплайн состоит из трёх этапов. Сначала дизайнер определяет значения цвета, промежутка и типографики в Figma Variables с помощью нестандартного плагина Figma,Стандарт JSON W3C DTCG Мы извлекаем в формате. Затем мы используем библиотеку под названием Style Dictionary, чтобы развернуть цепочку ссылок между токенами (component → semantic → primitive) в реальные значения. Наконец, результат сохраняется в файле TypeScript, и MUI использует эти дизайнерские токены. Визуальные решения Figma протекают в кодовые токены без вмешательства человека. Даже если есть разрывы ссылок, это не приводит к сбоям сборки, и записывается в журналчто нужно было сделать, чтобы CI не останавливался во время изменения дизайна. Если один раз получить в стандартном формате (W3C DTCG), то в дальнейшем любой инструмент может прочитать, что позволяет автоматизировать процесс.
3.2 Иерархия токенов, отношения ссылок (Семантические имена — primitive → semantic → component)
Токены создаются в трех уровнях, чтобы их назначение можно было понять только по имени. primitive(сам пигмент: blue-500), semantic(значение и роль: primary-main), component(применение конкретной детали: button-contained-bg). Разрешены только односторонние зависимости (primitive ← semantic ← component), даже если менять только нижний цвет.
// primitive — 물감 자체 (실제 색 값)
color/blue/500 = #2196F3
// semantic — 의미·역할 (primitive 를 가리킴)
color/primary/main = {color.blue.500}
// component — 특정 부품의 쓰임 (semantic 을 가리킴)
button/contained/bg = {color.primary.main}
// → blue-500 한 곳만 바꾸면 primary, button 까지 연쇄 반영된다
4. Как MUI Theme потребляет токены
Если токены — это данные (Layer 1), то движок, который преобразует эти данные в «одежду» для реальных компонентов,это MUI Theme (Layer 2).Ключевым моментом является понимание того, как работает тема MUI.
4.1 Принципы работы конфигурации MUI Theme — 3 канала
Компоненты MUI читают объект theme, полученный из контекста ThemeProvider, для расчета стилей. Основные каналы в основном три.
-
Глобальные значения дизайна: palette / typography / spacing / shape и другие глобальные значения, которыми делятся все компоненты
-
Основные props: components.MuiX.defaultProps — базовое поведение и форма компонента
-
Переопределение стилей: components.MuiX.styleOverrides — стили по комбинациям variant·color·state
VUI заполняет все три канала токенами. Поэтому, изменив только одно место(ThemeOptions) все компоненты изменяются одновременно. Создание темы обернуто в вспомогательную функцию, принимающую бренд·режим в качестве аргументов.
4.2 token-adapter — “значения автоматические, структура ручная”
Если записать путь к автоматически сгенерированным токенам (например: component.button['md-radius']) непосредственно в стили компонента, код будет ломаться каждый раз, когда дизайнер изменяет структуру токена. Так что token-adapter.tsипуть автоматически сгенерированного токена сопоставляется с надежным именем слота один разсделано. После этого токен значениеменяется, путь остается прежним и автоматически обновляется, а токен структура (путь)изменяется только тогда, когда нужно исправить одну строку адаптера. components.tsэто адаптер, который экспонирует buttonTokens / chipTokens / alertTokensи так далее, для написания MUI styleOverrides.
// components.ts — token-adapter 의 슬롯을 MUI styleOverrides 로 연결
import { buttonTokens, chipTokens, alertTokens } from './token-adapter';
// MUI Theme 객체에 선언된 MUI Button 스타일 선언코드
MuiButton: {
styleOverrides: {
contained: ({ theme, ownerState }) => ({
backgroundColor: buttonTokens.variant.contained.bg[ownerState.color],
borderRadius: theme.shape.radiusControlSm,
}),
},
}
Необычные слоты VUI, отсутствующие в стандартной палитре MUI (например, surface / field / border / icon / overlay)расширение модулярасширив тип на, theme.vui или я получил доступ к слотам расширенной палитры(mui-augmentation.ts). IDE может извлекать множество токенов, не путая их только с помощью автозаполнения — Система типов это документ, на который можно ссылатьсятак получается.
4.3 Проверка совместимости токенов дизайна с Figma MCP
Одним из важных аспектов при создании дизайн-системы является «сопряжение спецификаций компонентов, определенных в Figma, с реальными токенами и темами», и проверка их согласованности.Проверка соответствия дизайнаэто была работа. В последнее время этот процесс сопоставления Искусственный интеллектиспользуется.
Суть в двух этапах. Сначала С помощью Figma MCP AI Agent фактически читает информацию о дизайнерских токенах, примененных к определенным компонентам внутри рамки Figma(цвет, типография, интервалы, радиус и т. д., какие переменные где связаны) и анализирует её самостоятельно. Затем эта информация о токенах Figma сравнивается с компонентомреально реализованным в Storybookи сравнивается.
<Storybook>
<Figma>
AI Agent сравнивает два результата и проверяет, где в реализованном коде отсутствуютдизайнерские токеныили где значения не совпадают с FigmaЭто позволяет AI Agent делать первичный фильтр того, что человек раньше проверял вручную. Причина, по которой такая проверка возможна, заключается в том, что общий язык токеновпозволяет это — Figma и код описываются по одному и тому же критерию (токенам), что и позволяет автоматическое сравнение.
5. Составление тем по режимам — компоненты остаются прежними, изменяется только тема
Фактический продукт не ограничивается лишь одним экраном. Он должен хорошо выглядеть как на больших мониторах, так и на маленьких телефонах, на светлых экранах и темных экранах, а также на продуктах разных брендов. VUI обрабатывает все эти изменения одновременно, но ключевым моментом является Компонентный код остается прежним, только меняется ‘тематика’это точка. В данный момент основа этого перехода состоит из трех частей.
-
Размер экрана (настольный / мобильный) — даже если это один и тот же компонент, при уменьшении экрана размер шрифта и промежутки автоматически становятся более плотными. Тематика самостоятельно меняет значения на настольные и мобильные в зависимости от ширины экрана.
-
Светлый / темный режим — цвет фона и текста полностью меняются в зависимости от режима. Когда пользователь включает темный режим, компонент остается прежним, но набор цветов просто заменяется на темный.
-
Бренд (например, vizend / devlime) — для каждого продукта можно по-разному выполнить цвет и атмосферу бренда. Если нужен новый бренд, просто определите новые цвета в дизайне и добавьте их.
Важно, как бы вы ни комбинировали эти три оси, разработчик не изменяет ни строчки кода компонентаэто. Как только вы вверху экрана определили ‘какой бренд, какой режим’, все компоненты ниже автоматически подстраиваются к соответствующей тематике. Вместо того чтобы добавлять сложную ветвление в каждый компонент, эта сложность была поднята на уровень тематики, упрощая нижний уровень.
// 맨 위에서 '브랜드 / 모드'만 정하면 끝 — 컴포넌트 코드는 그대로
<VuiThemeProvider brand="vizend" mode="dark">
<App />
</VuiThemeProvider>
6. Проблемы, которые еще необходимо решить
это задачи, которые стали очевидными в процессе проектирования и реализации, и которые все еще не решены.
6.1 Проблема сопоставления дизайнерских токенов — нельзя управлять всеми стилями с помощью MUI Theme.
Цвета, основанные на значениях VUI, стандарты MUI theme.paletteслот структуры не полностью сопоставляется. Палитра MUIprimary/secondary/text/backgroundпредполагая степень, наши семантические токены имеют больше оттенков. В результате vuiColors.bg.surfaceкак вспомогательные функции или CSS-переменныеобходной доступстало больше. “В Figma мы определилиtext.mutedзначение, но проблема в том, что в палитре MUI нет места, чтобы отразить это значение в слоте textхотя эта проблема частично смягчена с помощью модуля дополнения, странность сосуществования стандарта и расширения продолжается.
6.2 Неассиметрия обнаружения изменений структуры и незавершенная проводка компонентов
благодаря token-adapter токен значения Изменения автоматические и бесконечные, токен структура (путь) изменения осуществляются человеком build.logнеобходимо читать напрямую и исправлять адаптер — асимметрия автоматического/ручного способа вызывает неудобства. Также у токен-адаптера есть слоты, но components.tsосталось множество компонентов, к которым еще не применены styleOverrides, так что пользователю нужно sxпользоваться токенами напрямую. Данные все есть, но проводка неполная — если один раз поработать, будущие затраты на обслуживание почти отсутствуют, но сейчас это незавершенно.
6.3 Необходимость установления и документирования принципов дизайна
Пока что мы сосредоточились на "кодировании токенов", но на самом деле на этом уровне человек должен следовать принципам дизайнаи Руководство по использованию компонентовеще не достаточно организовано. Система готова, но не хватает документации, которая бы объясняла, “как и когда это использовать”.
Нужны два типа документации. Один - это документ принципов дизайна— почему были разделены семантический и компонентный слои, какие запросы принимаются как токены, а какие отклоняются, такие как критерии принятия решений— чтобы даже человек, присоединяющийся через 6 месяцев, мог принимать такие же решения. Другой - это Руководство по использованию компонентов— нужно уточнить, когда и с какой комбинацией пропов использовать каждый компонент VUI, а также какие распространенные ошибки есть, чтобы сохранить согласованность на всех этапах использования.
Мы дошли до кодирования токенов, теперь пришло время документировать принципы и методы использования в коде— это определяет скорость адаптации новых членов команды и устойчивость системы.
В заключение
одно из предложений, полученных в процессе создания VUI, звучит так — “Ответственность за согласованность нужно возложить не на добросовестность человека, а на систему.”Выбор на основе MUI, использование Figma в качестве SSOT, кодирование токенов и применение их в темах, а также поглощение модификаций в качестве настроек указывают на одно направление.
Я считаю, что смысл этой работы состоит из двух слоев. Ближе всего, это использование рычага, позволяющего небольшой команде добиваться стандартного качества дизайна и публикации даже с небольшим количеством людей.Далее, это основа автоматической генерации фронтенд-кода, к которой стремится платформа Bizend.Поскольку для этого необходима хорошо организованная и стандартизированная дизайн-система с токенами, чтобы AI мог создавать последовательный экранный код на ее основе.
Brown