61 lines
19 KiB
Markdown
61 lines
19 KiB
Markdown
# Принципы UX/UI KT AI – применять при создании любого дизайна
|
||
|
||
Рабочий контракт принципов: «почему так». DESIGN.md – «чем строить», ELEVENLABS_DESIGN.md – «как выглядит». **Проверка («прошло или нет») вынесена в единый гейт `CHECKLIST.md`** — прогоняй его при любом изменении UI (новый продукт / фича / правка). Этот файл объясняет, ПОЧЕМУ пункты гейта именно такие.
|
||
|
||
## 10 эвристик Нильсена → как они реализованы у нас
|
||
|
||
1. **Видимость статуса системы.** Каждое действие даёт отклик ≤100мс: loading-кнопка на сабмитах, toast на завершениях, progress на долгих операциях, статус-pill на объектах, стриминг ответов в AI-продуктах. Молчащий интерфейс = баг.
|
||
2. **Соответствие системе и реальному миру.** Язык пользователя, не наш: «Отправить в Реестр», а не «Синхронизировать сущность». Термины из глоссария КТ (Лотус, СЗ, паспорт агента). Иконки – буквальные (Lucide), не метафоры.
|
||
3. **Контроль и свобода.** Из любого состояния есть выход: modal закрывается по Esc и клику мимо, drawer – стрелкой назад, деструктив – с подтверждением, многошаговые процессы (stepper) позволяют вернуться на шаг. Автосохранение черновиков, где возможно.
|
||
4. **Согласованность и стандарты (закон Якоба).** Пользователь приходит из других продуктов – не изобретать: поиск сверху, детали справа в drawer, primary справа в паре кнопок, крестик закрытия справа сверху. Внутри KT AI – единый API компонентов (enum-таблица в DESIGN.md), один компонент = одно поведение во всех продуктах.
|
||
5. **Предотвращение ошибок.** Валидация до сабмита (data-invalid + .error в field), недоступные действия – disabled с объяснением в tooltip, деструктив – глаголом действия и подтверждением, необратимое – вводом имени объекта. Маски и подсказки формата (телефон, даты) до того, как человек ошибся.
|
||
6. **Узнавание вместо вспоминания.** Видимые подписи у иконок в навигации (icon-only только в rail-режиме), placeholder с примером формата, недавние значения в combobox первыми, breadcrumbs показывают где я.
|
||
7. **Гибкость и эффективность.** Два слоя скорости: новичку – видимые кнопки и подсказки, опытному – ⌘K командная палитра, kbd-шорткаты, плотность таблиц (data-density), bulk-операции.
|
||
8. **Эстетика и минимализм.** Каждый элемент экрана зарабатывает своё место: один primary, KPI тихой полосой, метаданные muted, пустое пространство – инструмент, а не потеря. Правило: убери элемент – если экран не сломался, элемент был лишним.
|
||
9. **Помощь в распознавании и восстановлении после ошибок.** Текст ошибки говорит: что случилось, почему, что делать. «Не удалось сохранить: нет связи с сервером – повторите через минуту», а не «Ошибка 500». Тон risk-banner, рядом действие повтора.
|
||
10. **Справка и документация.** Подсказки в месте использования: hint под полем, tooltip на icon-only, onboarding-экран перед сложным flow (как в AI Interviewer), empty-state объясняет «что здесь будет и как начать».
|
||
|
||
## Правила по референсу ElevenLabs (Mobbin) — сверять при любом экране
|
||
|
||
ElevenLabs (мониторинг через Mobbin) — главный живой референс системы. Правила ниже выведены из их продакшн-экранов и обязательны:
|
||
|
||
- **KPI-карточка: три уровня сверху вниз — подпись, значение, уточнение.** Маленькая muted-подпись, сразу под ней значение (sans, tabular-nums, semibold), при необходимости третьим уровнем `.hint` — знаменатель, доля или период («из 2 954 · 58 % плана»). Значение — число или короткая величина (≤12 символов); слова-квалификаторы («при норме 7 дней», «за неделю») живут в подписи, не в значении. Длинное значение автоматически мельче (`data-long`), но это страховка, а не норма. **Значение не прижимается к низу карточки:** в полосе из карточек с уточнением и без числа встанут на разной высоте, и глаз прочитает их как разные по важности. Полоса выравнивает карточки по верху.
|
||
- **KPI как табы (dashboard).** Клик по метрике переключает большой чарт периода. Выбранная — рамка-акцент; никаких стрелок/иконок-подсказок на невыбранных, доступность через hover и `role=tab`.
|
||
- **Одна цифра — один раз на экране.** Значение метрики живёт на KPI-карточке; шапка чарта её НЕ повторяет (только название ряда и период). Дубли одной цифры в трёх местах — баг.
|
||
- **Главная страница — обзор, не свалка.** Дашборд: KPI → чарт → разборы → «Требует внимания» топ-5 со ссылкой «Все →». Полный реестр — отдельный раздел nav (`view:"registry"`: та же таблица с поиском/фильтрами/пагинацией). Как Home vs Voices/History у ElevenLabs.
|
||
- **Разборы под чартом — три формы:** top-N с бар-треком за подписью («Top called paths»), доли с процент-барами («Language»), мини-карточки статистики («Most called agents»). Каждый чарт/ряд несёт note — чтение одной фразой.
|
||
- **Многошаговое — вертикальный степпер слева** с номером/галкой, названием и 1-строчным описанием шага (референс их publishing-flow); контент справа, «‹ Назад» ghost слева, primary справа.
|
||
- **Список+чтение (inbox):** узкий список слева (заголовок + muted-подпись + время + pill), панель чтения справа: label:value строки со значениями по правому краю, разбор агента отдельной секцией.
|
||
- **Документ (Studio):** абзацы/фрагменты с тонкой левой чертой; помеченные агентом — с тёплой чертой и плашкой причины. Текст дышит, никакой рамки вокруг каждого абзаца.
|
||
- **Чарты:** один акцентный цвет на ряд, лёгкая пунктирная сетка, area-заливка ≤10% непрозрачности, подписи оси только по краям и шагом, крайние — text-anchor start/end (не режутся).
|
||
|
||
## Гештальт-принципы → правила вёрстки
|
||
|
||
- **Близость (proximity).** Расстояние кодирует связь и берётся из шкалы ритма, а не подбирается: внутри группы `stack-tight` (12), между элементами блока `stack-block` (16), **между блоками экрана `stack-group` (24)**, поля области и отрыв от топбара `stack-region` (32), смена секции — `space-10+` (40+). Label ближе к своему полю, чем к чужому. Если элемент визуально «прилип» не к своей группе – это баг вёрстки. **Пять разных значений для одного отношения — баг**: разница в 4px не читается как иерархия, она читается как небрежность. **Один и тот же зазор на всё — баг ровно такой же**: экран становится плоским, панель фильтров и её вкладки расходятся так же далеко, как список от шапки, и ни одна группа не читается. Ритм — это разные расстояния для разных отношений, а не одно расстояние везде.
|
||
- **Сходство (similarity).** Одинаковая роль = одинаковый вид: все ссылки одного цвета, все статусы – pill, все метаданные – meta. Обратное тоже: разная роль обязана выглядеть по-разному (secondary ≠ primary).
|
||
- **Общая область (common region).** Граница/фон группирует сильнее отступа: карточка объединяет, divider разделяет. Не вкладывать карточку в карточку – две рамки спорят за группировку.
|
||
- **Непрерывность и выравнивание.** Всё сидит на 4px-сетке и общих осях: левый край контента – одна линия, числа в таблицах – по правому краю, baseline текста в ряду – общий.
|
||
- **Фигура и фон.** Слои тона (bg → bg-soft → bg-elevated) и overlay создают глубину без теней; модальные поверхности всегда elevated + затемнение фона.
|
||
- **Замыкание.** Усечённые списки с «показать ещё N» – мозг достроит; не выводить 200 строк сразу.
|
||
|
||
## Законы взаимодействия
|
||
|
||
- **Фиттс.** Чем важнее и чаще действие, тем больше и ближе цель: primary крупнее визуально, touch-цели ≥44px (pointer: coarse автоматом), зоны клика рядов – весь ряд, а не только текст.
|
||
- **Хик.** Меньше выборов – быстрее решение: меню ≤7 пунктов на уровень, формы шагами (stepper), один вопрос за раз (паттерн AI Interviewer), фильтры по умолчанию свёрнуты до самых ходовых.
|
||
- **Операционная краткость.** Заголовок экрана, фильтры, статусы и кнопки не описывают весь процесс. Они называют рабочий объект или действие: `Очередь рисков`, `Нет документов`, `Подтвердить риск`. Длинные объяснения живут в subtitle, drawer или help.
|
||
- **Метрики по задаче пользователя.** Верхняя карточка, счётчик или виджет отвечает не на вопрос «какую ценность продукт хочет доказать», а на вопрос «зачем пользователь открыл этот экран прямо сейчас». Для рабочего экрана это очередь, просрочка, блокер, риск, задача на подтверждение, новый входящий объект или состояние процесса. ROI, FTE, экономия часов и тенге не выводятся на рабочий экран по умолчанию. Они живут только там, где пользователь принимает управленческое решение по эффекту: management/reporting view, паспорт, расчёт эффекта или экран проекта.
|
||
- **Неприкосновенный shell.** Sidebar, topbar, theme toggle и AI-кнопка Төре – системный контракт, а не творческая зона. Новый продукт меняет рабочую область, таблицу, drawer, формы и сценарии, но не изобретает заново базовую оболочку.
|
||
- **Продуктовый язык вместо debug-языка.** В интерфейсе нельзя показывать внутренние объяснения генерации: `модель вернула`, `fallback`, `не проходит дизайн-систему`, `shell`, `JSON`, `prompt`. Если прототип собран автоматически, пользователь всё равно видит нормальные продуктовые подписи, действия и статусы.
|
||
- **Миллер (7±2).** Чанкование: телефоны с пробелами, длинные таблицы с группировкой, навигация секциями по 3-5 пунктов.
|
||
- **Эффект эстетики-юзабилити.** Аккуратный интерфейс прощает мелкие огрехи и вызывает доверие – поэтому паритет тем, ровные отступы и выравнивание не «полировка», а функциональное требование.
|
||
- **Постепенное раскрытие.** Сложность по запросу: детали в drawer, advanced-настройки за «ещё», JSON/код за переключателем. Первый экран – только то, что нужно для главного действия.
|
||
- **Ориентация (wayfinding).** Каждый экран отвечает на 4 вопроса: где я? куда могу пойти? что здесь? как выйти? Если хоть один без ответа — экран дезориентирует (топбар-крошка, активный пункт nav, заголовок, Esc/назад).
|
||
- **Маппинг и лейблы.** Близость и расположение контрола отражают то, на что он влияет; **если контролу нужен поясняющий лейбл — маппинг слабый**, переделай контрол. Лейблы конкретны: nav называется по содержимому, не общим «зонтиком» — конкретность даёт предсказуемость (не «Управление», а «Лоты»).
|
||
- **Обратная связь: причинность и польза.** Отклик привязан к вызвавшему его событию (fire on cause) и добавляется только там, где нужен (успех/ошибка/коммит/снап), а не на каждый чих. Валидация — по ходу ввода, не на сабмите.
|
||
- **Текст не заменяет устройство экрана.** Объяснение на экране — признак того, что интерфейс не объясняет себя сам. Прежде чем добавить поясняющую строку, оговорку или подзаголовок, проверь: нельзя ли это сказать самим элементом (подпись пилюли, название колонки, подсказка у метки, состояние кнопки). Оговорка живёт РЯДОМ с тем, к чему относится, а не отдельной строкой над списком: у элемента её прочитают в момент решения, над списком — пролистают. Что убирать в первую очередь: подзаголовок, повторяющий заголовок; инструкцию «проверьте и примите решение» там, где это и так единственное действие; пояснение источника данных, которому место в подсказке; текст, одинаковый для всех строк списка. Правило проверяемое: **любая строка текста, которая не меняется от данных, — кандидат на удаление**; если она нужна для честности (оговорка про непроверенное, про тестовые данные, про пробел в данных), она остаётся, но переезжает к элементу.
|
||
- **Ремесло (craft).** Каждый отступ, тайминг и выравнивание — намеренны; внимание к деталям строит доверие. Кривой пиксель читается как «недоделано» независимо от контента.
|
||
|
||
## Чек-лист
|
||
|
||
Перенесён в единый гейт → **`CHECKLIST.md`** (Definition of Done). Там же — что машинно ловит `validate_product.py` (`[auto]`), а что требует глаз (`[review]`), и какие гейты прогонять для нового продукта / фичи / правки. Не дублируй чек-лист здесь — правь его в одном месте.
|