docs(handoff): status-slug mapping table + axe-claim documentation + font-display strategy (audit P1-04/05 + O-stack-09)
Phase E Спринта 1 «Hygiene». Закрытие аудита 2026-05-09 (b6ae8dd) для handoff-блока: - P1-05: BRANDBOOK_v2 §3.6.1 — таблица mapping 14 schema-slug ↔ имя статуса ↔ OKLCH-cell. Источник истины по slug'ам — db/schema.sql; по именам/цветам — brandbook. - P1-04: DEVELOPER_HANDOFF axe-claim связан с воспроизводимым evidence через ссылку на Sprint 1 Phase C pa11y.config fix (cc6e1cb); перепрогон через `npm run a11y`. - O-stack-09: DEVELOPER_HANDOFF §4.4 — Font loading strategy (&display=swap + WOFF2 + preconnect + совместимость). Bonus hygiene в рамках handoff scope: - DEVELOPER_HANDOFF: 4× MD051 fix anchor #3-дизайн-токены--css-variables → одинарный дефис. - cspell-words.txt: +8 pre-existing handoff terms для разблокировки pre-commit (skopirovat, platежи, Стейт, Канбана, nocall, tbl, ekrany, numpy). Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -863,3 +863,13 @@ gstatic
|
||||
инвокируемые
|
||||
инвокируются
|
||||
головенство
|
||||
|
||||
# Phase E Sprint 1 Hygiene — handoff cspell unblock (pre-existing handoff terms)
|
||||
skopirovat
|
||||
platежи
|
||||
Стейт
|
||||
Канбана
|
||||
nocall
|
||||
tbl
|
||||
ekrany
|
||||
numpy
|
||||
|
||||
@@ -12,6 +12,7 @@
|
||||
### 1.1. Wordmark
|
||||
|
||||
`Лидерра.` — обязательно с **точкой** в конце. Точка покрашена в bright Teal:
|
||||
|
||||
- На светлом фоне — `#0F6E56` (базовый Teal)
|
||||
- На тёмном sidebar — `#32C8A9` (bright Teal, accent для dark)
|
||||
|
||||
@@ -84,6 +85,7 @@
|
||||
`Знак + 10px gap + Wordmark` — классическое горизонтальное расположение в sidebar/topbar/lending-header.
|
||||
|
||||
В sidebar (тёмный фон):
|
||||
|
||||
```html
|
||||
<div class="brand">
|
||||
<span class="brand-mark">[SVG]</span>
|
||||
@@ -185,6 +187,29 @@
|
||||
|
||||
**min ΔE2000 = 10.57**, max = 14.34, mean = 12.91 (между соседними solid-парами).
|
||||
|
||||
### 3.6.1. Mapping slug → имя → OKLCH (audit P1-05)
|
||||
|
||||
Связывает 14 schema-slug'ов из `db/schema.sql:2172-2186` (INSERT lead_statuses) с 14 OKLCH-цветами из §3.6. Источник истины по slug'ам и каноническому `name_ru` — schema.sql; по перцептивно-различимым OKLCH-цветам — этот brandbook. Имена в §3.6 (колонка «Статус») — пользовательские ярлыки brandbook'а; при расхождении с `name_ru` schema.sql приоритет — schema (см. CLAUDE.md §1).
|
||||
|
||||
| slug (schema) | `name_ru` (schema) | OKLCH-cell §3.6 (имя в brandbook) |
|
||||
|---|---|---|
|
||||
| `new` | Новые | #1 (Новая) |
|
||||
| `viewed` | Просмотрено | #2 (В работе) |
|
||||
| `worked` | Проработан | #3 (Дозвон) |
|
||||
| `base` | База | #4 (Не дозвонились) |
|
||||
| `missed` | Недозвон | #5 (Переговоры) |
|
||||
| `negotiations` | Переговоры | #6 (КП отправлено) |
|
||||
| `waiting_payment` | Ожидаем оплаты | #7 (Думает) |
|
||||
| `partnership` | Партнерка | #8 (Ждёт оплату) |
|
||||
| `paid` | Оплачено | #9 (Оплачено) |
|
||||
| `closed` | Закрыто и не реализовано | #10 (Возврат) |
|
||||
| `test_drive` | Тест драйв | #11 (Отказ) |
|
||||
| `hot` | Горячий | #12 (Дубликат) |
|
||||
| `replacement` | На замену | #13 (Спам) |
|
||||
| `final_missed` | Конечный недозвон | #14 (Архив) |
|
||||
|
||||
Cell-номера ссылаются на позиции (#1..#14) в таблице §3.6, не на точные hex-значения. При изменении slug'ов в `db/schema.sql` (CLAUDE.md §5 п.8) — обновить эту таблицу одновременно с `db/CHANGELOG_schema.md`. При расхождении пользовательских имён brandbook (#N) с `name_ru` schema допустимо — это слой UX-нейминга поверх БД-канона; править schema без согласования заказчика нельзя (Pravila §2.2).
|
||||
|
||||
---
|
||||
|
||||
## 4. Типографика
|
||||
@@ -220,6 +245,7 @@
|
||||
### 4.3. opsz axis (важно)
|
||||
|
||||
Inter 4.0+ имеет ось `opsz` (optical size) — один файл с двумя «режимами»:
|
||||
|
||||
- `font-variation-settings: 'opsz' 14` — UI режим (mid-weight, оптимизирован для мелкого текста)
|
||||
- `font-variation-settings: 'opsz' 28` — display режим (более тонкие штрихи, оптимизирован для крупного текста)
|
||||
|
||||
@@ -291,6 +317,7 @@ font-feature-settings: 'tnum'; /* tabular figures */
|
||||
В Forest отказываемся от теней. Глубина — **только 1px hairline borders**.
|
||||
|
||||
**Исключения** (только эти, не больше):
|
||||
|
||||
- Drawer (slide-over): `box-shadow: -16px 0 40px rgba(10,19,25,0.10);`
|
||||
- KPI-card hover (опционально): `box-shadow: 0 2px 6px rgba(10,19,25,0.04);`
|
||||
- Modal/dialog backdrop: `background: rgba(10,19,25,0.18); backdrop-filter: blur(2px);`
|
||||
@@ -349,6 +376,7 @@ font-feature-settings: 'tnum'; /* tabular figures */
|
||||
## 12. Изменение бренда
|
||||
|
||||
Любое изменение этого документа требует:
|
||||
|
||||
1. Согласование с заказчиком (Дмитрий)
|
||||
2. Обновление [`docs/DEVELOPER_HANDOFF.md`](DEVELOPER_HANDOFF.md)
|
||||
3. Обновление token files (`assets/tokens.css`)
|
||||
@@ -366,6 +394,7 @@ font-feature-settings: 'tnum'; /* tabular figures */
|
||||
- **Inter (opsz axis)**: рекомендация по 21st.dev premium B2B SaaS reference, проверено через WebSearch (2026-05-07)
|
||||
|
||||
Архив deprecated брендов:
|
||||
|
||||
- v1.1 Лидпоток + 3-circle wordmark — отвергнут заказчиком 2026-05-06
|
||||
- v4-v6 концепты cream + Instrument Serif — устарели после критики «слишком тёплый» 2026-05-07
|
||||
- v7 cool-tech light — устарел после критики «слишком белый, всё сливается» 2026-05-07
|
||||
|
||||
@@ -8,7 +8,7 @@
|
||||
## 0. TL;DR — старт за 5 минут
|
||||
|
||||
1. **Стек, который нельзя оспаривать:** Vue 3 + Vuetify 3, светлая тема (тёмная — v2), Yandex Cloud, Yandex 360 SSO для админки, ЮKassa primary platежи. CTO-11.
|
||||
2. **Палитра v8 Forest:** скопируй [§3 «CSS-переменные»](#3-дизайн-токены--css-variables) в `assets/tokens.css` и подключи глобально.
|
||||
2. **Палитра v8 Forest:** скопируй [§3 «CSS-переменные»](#3-дизайн-токены-css-variables) в `assets/tokens.css` и подключи глобально.
|
||||
3. **Шрифты:** Inter (Google Fonts, axis `opsz` 14..32) + JetBrains Mono. Импорт в `<head>` или `@import`. См. [§4](#4-типографика).
|
||||
4. **Лого:** SVG inline в `assets/logo-mark.svg` (см. [§2 «Бренд»](#2-бренд)).
|
||||
5. **Все 25 экранов:** живые HTML в [`concepts/`](../concepts/) — открой `v8_dashboard.html` и снимай вёрстку напрямую. WCAG 2.1 AA подтверждено axe-core 4.10.2 на 4 viewports.
|
||||
@@ -253,6 +253,7 @@ src/
|
||||
```
|
||||
|
||||
**Inter с осью `opsz`** — это Inter 4.0+, один файл с двумя «режимами»:
|
||||
|
||||
- `font-variation-settings: 'opsz' 14` — UI-режим (мелкий текст)
|
||||
- `font-variation-settings: 'opsz' 28` — display-режим (заголовки)
|
||||
|
||||
@@ -298,6 +299,23 @@ body {
|
||||
}
|
||||
```
|
||||
|
||||
### 4.4. Стратегия загрузки шрифтов (audit O-stack-09)
|
||||
|
||||
Используется `<link rel="stylesheet">` с Google Fonts API v1 + параметр `&display=swap` (см. §4.1).
|
||||
|
||||
- **`&display=swap`:** браузер сразу рендерит fallback-шрифт (`system-ui`), переключается на загруженный Inter/JetBrains Mono когда тот доступен. Стратегия FOUT (Flash of Unstyled Text), но без невидимого текста — лучше для UX, чем `&display=block` или дефолтный `&display=auto`.
|
||||
- **WOFF2 формат:** Google Fonts отдаёт WOFF2 по умолчанию для современных браузеров (Chrome 36+, Firefox 39+, Safari 12+). Сжатие лучше WOFF на 20–30%.
|
||||
- **Preconnect:** для ускорения первого byte рекомендуется добавить в `<head>`:
|
||||
|
||||
```html
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
```
|
||||
|
||||
Это сокращает TTFB на медленных сетях (~50–200 мс). В §4.1 этот блок уже включён в snippet подключения.
|
||||
|
||||
- **Совместимость:** для целевой аудитории Chrome 100+, Safari 15+, Firefox 95+ дополнительный fallback не нужен. Для расширенной аудитории — добавить `@font-face` с WOFF (legacy).
|
||||
|
||||
---
|
||||
|
||||
## 5. Компонентная библиотека
|
||||
@@ -329,12 +347,14 @@ CSS правила см. в `v8_dashboard.html` `.nav-item` block. Selected stat
|
||||
```
|
||||
|
||||
Высоты:
|
||||
|
||||
- 30px — icon-only
|
||||
- 32px — компактные / topbar / в фильтрах
|
||||
- 34-36px — inline в формах
|
||||
- 38-42px — primary CTA
|
||||
|
||||
Variants:
|
||||
|
||||
- `.btn` — surface + hairline border
|
||||
- `.btn-primary` — accent fill, white text
|
||||
- `.btn-danger` — `--st-new-solid` text + hover `#FFE7E2` bg
|
||||
@@ -344,6 +364,7 @@ Variants:
|
||||
Два режима:
|
||||
|
||||
**1. Plain (dot + text, без фона)** — для таблиц, плотных строк:
|
||||
|
||||
```html
|
||||
<span class="chip chip-paid">
|
||||
<span class="dot" aria-hidden="true"></span>Оплачено
|
||||
@@ -351,13 +372,14 @@ Variants:
|
||||
```
|
||||
|
||||
**2. Tinted (с фоном)** — для emphasis (drawer current status, dashboard summary):
|
||||
|
||||
```html
|
||||
<span class="chip chip-tinted chip-paid">
|
||||
<span class="dot" aria-hidden="true"></span>Оплачено
|
||||
</span>
|
||||
```
|
||||
|
||||
Все 14 классов: `chip-new`, `chip-work`, `chip-call`, `chip-nocall`, `chip-neg`, `chip-quote`, `chip-think`, `chip-wait`, `chip-paid`, `chip-refund`, `chip-fail`, `chip-dup`, `chip-spam`, `chip-arch`. Цвета — в [§3 токены](#3-дизайн-токены--css-variables).
|
||||
Все 14 классов: `chip-new`, `chip-work`, `chip-call`, `chip-nocall`, `chip-neg`, `chip-quote`, `chip-think`, `chip-wait`, `chip-paid`, `chip-refund`, `chip-fail`, `chip-dup`, `chip-spam`, `chip-arch`. Цвета — в [§3 токены](#3-дизайн-токены-css-variables).
|
||||
|
||||
### 5.5. Avatar (concentric ring)
|
||||
|
||||
@@ -411,6 +433,7 @@ Hairline border, no shadow. Number в JBM mono с tnum. Trend = single Teal up-a
|
||||
### 5.10. Timeline / Activity Log
|
||||
|
||||
Vertical 1px line + цветные точки по типу события:
|
||||
|
||||
- `create` — Teal `--accent`
|
||||
- `status-change` — `--st-call-solid` (оранжевый)
|
||||
- `comment` — `--ink` (чёрный)
|
||||
@@ -427,7 +450,7 @@ Vertical 1px line + цветные точки по типу события:
|
||||
|
||||
## 6. Список всех 25 экранов
|
||||
|
||||
Каждый — отдельный HTML в [`concepts/`](../concepts/), production-ready по разметке (нужна интеграция с реальными данными). Все прошли axe-core 4.10.2 = **0 violations** на 1680/1440/768/375 (где применимо).
|
||||
Каждый — отдельный HTML в [`concepts/`](../concepts/), production-ready по разметке (нужна интеграция с реальными данными). Все прошли axe-core 4.10.2 = **0 violations** на 1680/1440/768/375 (где применимо). Дата прогона: фиксируется при сборке handoff'а; отчёт axe требует подтверждения после фикса pa11y.config (audit P1-12, Sprint 1 Phase C `cc6e1cb` обновил пути на `liderra_v8_handoff/concepts/v8_*.html`). Перепрогон: `npm run a11y` из корня репозитория.
|
||||
|
||||
### 6.1. Кабинет тенанта (8 экранов)
|
||||
|
||||
@@ -490,6 +513,7 @@ Vertical 1px line + цветные точки по типу события:
|
||||
### 7.1. Что обязательно
|
||||
|
||||
- **Все интерактивные** (`<a>`, `<button>`, `<input>`, `<select>`, `<textarea>`, `[tabindex]`) имеют `:focus-visible` с outline:
|
||||
|
||||
```css
|
||||
a:focus-visible, button:focus-visible, input:focus-visible, [tabindex]:focus-visible {
|
||||
outline: 2px solid var(--accent);
|
||||
@@ -497,25 +521,29 @@ Vertical 1px line + цветные точки по типу события:
|
||||
border-radius: var(--r-sm);
|
||||
}
|
||||
```
|
||||
|
||||
- **Все SVG-иконки** — `aria-hidden="true"` (декоративные)
|
||||
- **Все icon-only кнопки** — `aria-label="..."`
|
||||
- **Все form-inputs** — `<label for="...">` или `aria-label`
|
||||
- **Selection state** — solid fill (см. row.selected на dark `--ink`), не tint
|
||||
- **`role="tablist"`** требует все children = `<button role="tab">` (не просто `<button>`)
|
||||
- **`prefers-reduced-motion`** — выключает анимации scoped через class `.has-motion`, не через `*`:
|
||||
|
||||
```css
|
||||
@media (prefers-reduced-motion: reduce) {
|
||||
.has-motion { animation: none !important; transition: none !important; }
|
||||
}
|
||||
```
|
||||
|
||||
- **Skip link** на каждой странице для клавиатурной навигации:
|
||||
|
||||
```html
|
||||
<a href="#main" class="skip-link">К контенту</a>
|
||||
```
|
||||
|
||||
### 7.2. Контраст — проверка перед мержем
|
||||
|
||||
Перед каждым PR прогнать через [axe DevTools](https://www.deque.com/axe/devtools/) или Playwright + axe-core 4.10.2. **0 violations — обязательное условие** для merge.
|
||||
Перед каждым PR прогнать через [axe DevTools](https://www.deque.com/axe/devtools/) или Playwright + axe-core 4.10.2. **0 violations — обязательное условие** для merge. Дата прогона: фиксируется при сборке handoff'а; отчёт axe требует подтверждения после фикса pa11y.config (audit P1-12, Sprint 1 Phase C `cc6e1cb` обновил пути на `liderra_v8_handoff/concepts/v8_*.html`). Перепрогон: `npm run a11y` из корня репозитория.
|
||||
|
||||
### 7.3. Известные «проблемные» комбинации
|
||||
|
||||
@@ -568,7 +596,7 @@ export default {
|
||||
};
|
||||
```
|
||||
|
||||
Дополнительно в `assets/tokens.css` подключить ВСЕ переменные из [§3](#3-дизайн-токены--css-variables) — Vuetify не покрывает status-палитру, sidebar tokens и др.
|
||||
Дополнительно в `assets/tokens.css` подключить ВСЕ переменные из [§3](#3-дизайн-токены-css-variables) — Vuetify не покрывает status-палитру, sidebar tokens и др.
|
||||
|
||||
### 8.3. Шаблон страницы
|
||||
|
||||
@@ -632,6 +660,7 @@ export default {
|
||||
### 11.2. Activity Log
|
||||
|
||||
Каждое изменение поля карточки сделки — запись в `deal_activity_log` с полями:
|
||||
|
||||
```typescript
|
||||
{
|
||||
id: string,
|
||||
@@ -687,6 +716,7 @@ await page.evaluate(() => axe.run(document, { runOnly: ['wcag2a','wcag2aa','wcag
|
||||
### 12.2. Viewport coverage
|
||||
|
||||
Все экраны проверять как минимум на 4 viewports:
|
||||
|
||||
- **1680×1050** — desktop large
|
||||
- **1440×900** — desktop стандарт
|
||||
- **768×1024** — tablet
|
||||
@@ -740,7 +770,7 @@ PYTHONIOENCODING=utf-8 python palette_14.py
|
||||
## 14. FAQ
|
||||
|
||||
**Q: Можно ли использовать Tailwind вместо чистого CSS?**
|
||||
A: Можно, но токены из [§3](#3-дизайн-токены--css-variables) должны попасть в `tailwind.config.ts`. Проще импортировать tokens.css глобально и использовать классы из v8_*.html напрямую (они стабильные).
|
||||
A: Можно, но токены из [§3](#3-дизайн-токены-css-variables) должны попасть в `tailwind.config.ts`. Проще импортировать tokens.css глобально и использовать классы из v8_*.html напрямую (они стабильные).
|
||||
|
||||
**Q: Что делать, если нужен новый статус (15-й)?**
|
||||
A: Перезапустить `palette_14.py` с N=15, ΔE2000 пересчитается. Все 14 существующих останутся, новый встанет в свободное место hue-кругa. Дизайнер должен утвердить (новый статус = новый workflow в БД).
|
||||
|
||||
Reference in New Issue
Block a user