Перейти к основному содержанию

Продвинутый рабочий процесс

Цель и область применения

Этот документ охватывает нестандартные сценарии, когда 15 составных UI-компонентов из src/components/ui/ недостаточны для вашей задачи. Вы узнаете, как компоновать пять базовых примитивов (Block, Box, Grid, Flex, Stack) из src/core/ui/ для создания пользовательских интерфейсов. Для типичного использования компонентов с готовыми композитами см. Базовый рабочий процесс. Для общих рекомендаций по использованию и паттернов см. Лучшие практики. Источники: .devin/wiki.json191-198 src/components/GUIDE_CREATE_FORM.md1-10

Когда использовать продвинутый рабочий процесс

Библиотека предоставляет 15 составных компонентов, которые покрывают ~80% обычных сценариев UI. Однако некоторые элементы намеренно отсутствуют в библиотеке:
Отсутствующий тип компонентаПричина отсутствияПродвинутое решение
Элементы форм (Form, Label, Input)HTML-семантика сильно варьируетсяКомпоновать Block + Box с пропом component
Выпадающие списки SelectТребуется сложное управление состояниемИспользовать Box component="select" с вариантами
Пользовательские интерактивные виджетыСпецифическая для приложения логикаСтроить с помощью примитивов + вариантов
Нестандартные макетыУникальные структурные требованияКомпоновать Grid, Flex, Stack напрямую
Дерево решений: Базовый vs Продвинутый рабочий процесс
Да

Нет

Да

Нет

Да

Нет

Нужен UI-элемент

Компонент существует в
src/components/ui/?

Использовать составной компонент
(Button, Card, Badge)

Стандартный HTML-элемент
со стилизацией?

Использовать Block/Box
с пропом component

Сложная структура
макета?

Компоновать Grid/Flex/Stack
с примитивами

Создать пользовательский компонент
из примитивов

Базовый рабочий процесс (5.1)

Продвинутый рабочий процесс (5.2)
Источники: src/components/README.md1-8 src/components/GUIDE_CREATE_FORM.md5-10

Построение форм с помощью Block и Box

Библиотека не включает специализированные компоненты Form, Label или Input. Вместо этого используйте полиморфный проп component на Block и Box для рендеринга семантических HTML-элементов с полной системой вариантов.

Паттерн пропа component

Проп component преобразует примитивы в любой HTML-элемент, сохраняя типобезопасные пропы вариантов:
Пропы вариантов

Отрендеренные элементы

проп component

Примитивные компоненты

применяется к

применяется к

применяется к

применяется к

Block
(семантический контейнер)

Box
(гибкий примитив)

component='form'

component='label'

component='input'

component='textarea'

component='select'

<form>

<label>

<input>

<textarea>

<select>

p, m, px, py, и т.д.

w, h, maxW, minH

rounded, border, shadow

bg, c, borderColor
Источники: src/components/GUIDE_CREATE_FORM.md7-9

Паттерн структуры формы

Используйте Block с component="form" как обёртку формы, применяя варианты макета и стилизации: Структура контейнера формы:
ЭлементКомпонентПропыНазначение
Обёртка формы<Block component="form">w, maxW, p, rounded, shadow, bgСемантический контейнер формы с макетом
Группы полей<Block>w="full", className="space-y-2"Вертикальное расстояние между полями
Метки<Box component="label">c, className="text-sm font-medium"Доступные метки полей
Поля ввода<Box component="input">w="full", p, rounded, border, borderColorПоля ввода формы
Текстовые области<Box component="textarea">w="full", p, rounded, border, minHМногострочный ввод текста
Кнопка отправки<Button>w="full", size, variantОтправка формы
Пример структуры формы (см. src/components/GUIDE_CREATE_FORM.md14-32):
<Block 
  component="form"
  w="full"
  maxW="md"
  p="lg"
  rounded="lg"
  shadow="md"
  bg="white"
>
  {/* Поля формы */}
</Block>
Источники: src/components/GUIDE_CREATE_FORM.md11-33

Паттерны полей ввода

Все типы ввода используют Box с component="input" и стандартными HTML-атрибутами: Текстовое поле (src/components/GUIDE_CREATE_FORM.md37-50):
<Box 
  component="input"
  type="text"
  placeholder="Enter your name"
  w="full"
  p="md"
  rounded="md"
  border="default"
  borderColor="gray-300"
/>
Поле с состояниями фокуса (src/components/GUIDE_CREATE_FORM.md54-67):
<Box 
  component="input"
  type="text"
  w="full"
  p="md"
  rounded="lg"
  border="default"
  bg="white"
  c="gray-900"
  className="focus:ring-2 focus:ring-blue-500 focus:border-blue-500"
/>
Поле пароля (src/components/GUIDE_CREATE_FORM.md70-82):
<Box 
  component="input"
  type="password"
  placeholder="Password"
  w="full"
  p="md"
  rounded="md"
  border="default"
  borderColor="gray-300"
/>
Числовое поле с ограничениями (src/components/GUIDE_CREATE_FORM.md84-97):
<Box 
  component="input"
  type="number"
  placeholder="Age"
  w="full"
  p="md"
  rounded="md"
  border="default"
  min={0}
  max={120}
/>
Источники: src/components/GUIDE_CREATE_FORM.md35-97

Поля Textarea

Используйте Box с component="textarea" для многострочного ввода текста: Базовая текстовая область (src/components/GUIDE_CREATE_FORM.md99-115):
<Box 
  component="textarea"
  rows={4}
  placeholder="Enter your message"
  w="full"
  p="md"
  rounded="md"
  border="default"
  borderColor="gray-300"
  className="resize-none"
/>
Текстовая область с минимальной высотой (src/components/GUIDE_CREATE_FORM.md117-129):
<Box 
  component="textarea"
  placeholder="Description"
  w="full"
  p="md"
  rounded="lg"
  border="default"
  minH="32"
  className="resize-y"
/>
Источники: src/components/GUIDE_CREATE_FORM.md99-129

Полный пример формы

Архитектура контактной формы:
Block component='form'
обработчик onSubmit
Макет: w='full' maxW='lg' p='lg'
Стиль: rounded='lg' shadow='lg' bg='white'

Block (группа поля имени)
w='full' space-y-2

Box component='label'
c='gray-700' text-sm font-medium

Box component='input'
type='text' name='name' required
w='full' p='md' rounded='md'
border='default' borderColor='gray-300'

Block (группа поля email)
w='full' space-y-2

Box component='label'
c='gray-700' text-sm font-medium

Box component='input'
type='email' name='email' required
w='full' p='md' rounded='md'

Block (группа поля сообщения)
w='full' space-y-2

Box component='label'
c='gray-700' text-sm font-medium

Box component='textarea'
rows=5 name='message' required
w='full' p='md' minH='32'
resize-none focus:ring-2

Button type='submit'
w='full' size='lg' variant='default'
Полная реализация в src/components/GUIDE_CREATE_FORM.md134-226 Ключевые паттерны:
  1. Обработка событий формы: проп onSubmit на форме Block
  2. Структура полей: обёртка Block → метка → поле ввода в каждой группе
  3. Расстояния: className="space-y-6" на форме, className="space-y-2" на группах полей
  4. Валидация: атрибут required на полях ввода
  5. Состояния фокуса: комбинация вариантов с className для колец фокуса
Источники: src/components/GUIDE_CREATE_FORM.md131-226

Многоколоночный макет формы

Для сложных форм используйте Box с grid-отображением (src/components/GUIDE_CREATE_FORM.md228-277):
<Block 
  component="form"
  w="full"
  maxW="2xl"
  p="lg"
  rounded="lg"
  shadow="md"
  bg="white"
>
  <Box 
    display="grid" 
    className="grid-cols-1 md:grid-cols-2 gap-6"
  >
    {/* Поле имени */}
    <Block className="space-y-2">
      <Box component="label" className="text-sm font-medium">
        First Name
      </Box>
      <Box 
        component="input"
        type="text"
        w="full"
        p="md"
        rounded="md"
        border="default"
      />
    </Block>

    {/* Поле фамилии */}
    <Block className="space-y-2">
      <Box component="label" className="text-sm font-medium">
        Last Name
      </Box>
      <Box 
        component="input"
        type="text"
        w="full"
        p="md"
        rounded="md"
        border="default"
      />
    </Block>
  </Box>
</Block>
Источники: src/components/GUIDE_CREATE_FORM.md228-277

Паттерн валидации формы

Создавайте переиспользуемые компоненты полей с валидацией (src/components/GUIDE_CREATE_FORM.md311-339):
function ValidatedInput({ error, label, ...props }) {
  return (
    <Block w="full" className="space-y-2">
      <Box component="label" c="gray-700" className="text-sm font-medium">
        {label}
      </Box>
      <Box 
        component="input"
        w="full"
        p="md"
        rounded="md"
        border="default"
        borderColor={error ? "red-500" : "gray-300"}
        bg={error ? "red-50" : "white"}
        className={error ? "focus:ring-red-500" : "focus:ring-blue-500"}
        {...props}
      />
      {error && (
        <Box c="red-600" className="text-sm">
          {error}
        </Box>
      )}
    </Block>
  );
}
Разбор паттерна:
  • Условные borderColor и bg на основе состояния ошибки
  • Динамические цвета кольца фокуса через className
  • Отображение сообщения об ошибке с Box для цвета текста
  • Распространение пропов с {...props} для HTML-атрибутов
Источники: src/components/GUIDE_CREATE_FORM.md311-339

Доступные пропы вариантов для примитивов

Все примитивы поддерживают 12 категорий вариантов CVA. Ключевые варианты для построения форм:

Варианты расстояний

ПропЗначенияНазначение
p, px, py, pt, pb, pl, prnone, xs, sm, md, lg, xl, 2xlУправление padding
m, mx, my, mt, mb, ml, mrnone, xs, sm, md, lg, xl, 2xl, autoУправление margin

Варианты макета

ПропЗначенияНазначение
wauto, full, screen, fit, min, max, 1/2, 1/3, и т.д.Управление шириной
hauto, full, screen, fit, min, maxУправление высотой
minHЧисловые значения типа "32", "64"Минимальная высота (полезно для textarea)
maxWxs, sm, md, lg, xl, 2xl, 3xl, и т.д.Максимальная ширина (полезно для центрированных форм)
displayblock, flex, grid, inline, noneТип отображения

Варианты границ и стиля

ПропЗначенияНазначение
bordernone, default, 2, 4, 8Ширина границы
borderColorВсе цвета дизайн-системыЦвет границы
roundednone, sm, md, lg, xl, 2xl, 3xl, fullРадиус скругления
shadownone, sm, md, lg, xl, 2xlТень блока

Варианты цвета

ПропЗначенияНазначение
bgВсе цвета дизайн-системы (напр., white, card, gray-50)Цвет фона
cВсе цвета дизайн-системы (напр., gray-700, red-600)Цвет текста
Источники: src/components/GUIDE_CREATE_FORM.md279-301 src/components/README.md205-222

Лучшие практики для продвинутой компоновки

Рекомендации для полей формы

  1. Всегда устанавливайте w="full" на полях ввода для согласованной ширины (src/components/GUIDE_CREATE_FORM.md304)
  2. Используйте Block для структуры формы (элемент формы, группы полей) (src/components/GUIDE_CREATE_FORM.md305)
  3. Используйте Box для фактических полей ввода (input, textarea, select) (src/components/GUIDE_CREATE_FORM.md306)
  4. Комбинируйте пропы вариантов с Tailwind-классами для состояний фокуса (src/components/GUIDE_CREATE_FORM.md307)
  5. Используйте minH для textarea вместо фиксированной высоты (src/components/GUIDE_CREATE_FORM.md308)
  6. Применяйте className="resize-none" для предотвращения изменения размера textarea при необходимости (src/components/GUIDE_CREATE_FORM.md309)

Гибридный паттерн Вариант + className

Система вариантов покрывает ~80% потребностей в стилизации. Для оставшихся 20% комбинируйте варианты с className:
<Box 
  component="input"
  // Варианты покрывают структуру
  w="full"
  p="md"
  rounded="md"
  border="default"
  bg="white"
  // className покрывает интерактивные состояния
  className="focus:ring-2 focus:ring-blue-500 focus:border-blue-500"
/>
Когда использовать className:
  • Интерактивные состояния (:hover, :focus, :active)
  • Псевдоэлементы (:before, :after)
  • Сложные анимации
  • Grid/flex утилиты, не покрытые вариантами
  • Точки останова адаптивности за пределами системы вариантов
Источники: src/components/GUIDE_CREATE_FORM.md302-310 src/components/README.md237-244

Пользовательская компоновка компонентов

Создание переиспользуемых композитов

Когда вам нужен один и тот же паттерн многократно, извлеките его в пользовательский компонент: Паттерн: Поле ввода с меткой
управляет

отображает

рендерит

Пользовательский компонент ValidatedInput

Обёртка Block
w='full' space-y-2

Box component='label'
c='gray-700'
text-sm font-medium

Box component='input'
w='full' p='md'
rounded='md' border='default'
Условно: borderColor, bg

Box (условный рендер)
c='red-600' text-sm
Отображает сообщение об ошибке

Пропы:
- error (string | undefined)
- label (string)
- ...props (HTML-атрибуты)
Подход к реализации:
  1. Принимать пропы вариантов и HTML-атрибуты через распространение пропов
  2. Обрабатывать условную логику (состояния ошибок, валидация)
  3. Поддерживать доступность (ассоциации меток, ARIA-атрибуты)
  4. Возвращать компоновку примитивов (Block + Box)
Источники: src/components/GUIDE_CREATE_FORM.md311-339

Нестандартные пользовательские сценарии, не связанные с формами

Пользовательские интерактивные виджеты: При создании специфичных для приложения виджетов (слайдеры, пикеры, пользовательские элементы управления):
  1. Начинайте с Box или Block как контейнера
  2. Применяйте семантический проп component (<Box component="button"> для кликабельных элементов)
  3. Используйте пропы вариантов для макета и стилизации
  4. Добавляйте обработчики событий (onClick, onChange, и т.д.)
  5. Комбинируйте с className для сложных взаимодействий
Пользовательские структуры макета: Для уникальных требований к макету, не покрытых DashLayout, LayoutBlock или SplitBlock:
  1. Компонуйте Grid, Flex или Stack из src/core/ui/
  2. Применяйте варианты макета (cols, gap, align, justify)
  3. Вкладывайте примитивы для иерархической структуры
  4. Используйте Block с component="section"/component="aside" для семантической разметки
Источники: src/components/README.md237-244 .devin/wiki.json191-198

Сравнение: Базовый vs Продвинутый рабочий процесс

Когда использовать каждый подход:
Продвинутый рабочий процесс (5.2)

Базовый рабочий процесс (5.1)

Да

Нет

Готовые компоненты существуют

Card, Button, Badge,
Title, Text, Image, Icon

Использовать составные компоненты
из src/components/ui/

Пример:
<Card p='lg' rounded='xl'>

Пользовательские требования

Элементы форм, пользовательские виджеты,
уникальные макеты

Компоновать примитивы
из src/core/ui/

Пример:
<Block component='form'>
<Box component='input'/>

Компонент существует
в библиотеке?
Матрица возможностей:
ОсобенностьБазовый рабочий процессПродвинутый рабочий процесс
Скорость разработкиБыстрая (готовые компоненты)Умеренная (ручная компоновка)
ГибкостьОграничена пропами компонентовПолный контроль через примитивы
Поддержка кодаПроще (меньше компонентов)Более сложная (больше кода)
ТипобезопасностьПолная (типы составных компонентов)Полная (типы примитивных компонентов)
Поддержка вариантовЧерез пробрасывание проповПрямое применение
Семантический HTMLПредопределённая структураПолный контроль через проп component
Лучше всего дляСтандартных UI-паттерновПользовательских/уникальных требований
Источники: src/components/README.md1-19 src/components/GUIDE_CREATE_FORM.md1-10

Резюме

Продвинутый рабочий процесс позволяет создавать пользовательские интерфейсы, когда 15 составных компонентов недостаточны:
  1. Формы: Компонуйте Block + Box с пропом component для элементов форм, меток и полей ввода
  2. Пользовательские виджеты: Используйте примитивы с семантическими пропами component и системой вариантов
  3. Уникальные макеты: Компонуйте Grid, Flex, Stack для структурных требований
  4. Гибридный подход: Комбинируйте пропы вариантов (~80% покрытие) с className для граничных случаев
Для стандартных сценариев с существующими компонентами используйте Базовый рабочий процесс. Для общих рекомендаций см. Лучшие практики. Источники: src/components/GUIDE_CREATE_FORM.md341-347 .devin/wiki.json191-198