@sberbusiness/triplex-next-mcp-server 1.44.0-beta → 1.45.0-beta

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (76) hide show
  1. package/README.md +7 -6
  2. package/bundle/components/AlertContext.md +11 -8
  3. package/bundle/components/AlertProcess.md +13 -10
  4. package/bundle/components/Badge.md +6 -3
  5. package/bundle/components/Button.md +46 -43
  6. package/bundle/components/ButtonDropdownExtended.md +3 -2
  7. package/bundle/components/ButtonIcon.md +7 -4
  8. package/bundle/components/Calendar.md +62 -59
  9. package/bundle/components/Caption.md +26 -23
  10. package/bundle/components/Checkbox.md +32 -29
  11. package/bundle/components/CheckboxTreeExtended.md +9 -5
  12. package/bundle/components/Chip.md +44 -41
  13. package/bundle/components/CodeText.md +26 -23
  14. package/bundle/components/Col.md +1 -2
  15. package/bundle/components/CollapsibleTree.md +8 -5
  16. package/bundle/components/Dropdown.md +33 -28
  17. package/bundle/components/EmptyView.md +12 -5
  18. package/bundle/components/FooterPage.md +6 -2
  19. package/bundle/components/FormField.md +44 -41
  20. package/bundle/components/FormGroup.md +192 -52
  21. package/bundle/components/Header.md +491 -211
  22. package/bundle/components/HeaderPage.md +6 -2
  23. package/bundle/components/ImageGallery.md +33 -34
  24. package/bundle/components/ImageGalleryExtended.md +33 -34
  25. package/bundle/components/Island.md +16 -13
  26. package/bundle/components/LightBox.md +14 -12
  27. package/bundle/components/Link.md +211 -96
  28. package/bundle/components/ListActionItem.md +7 -4
  29. package/bundle/components/ListItem.md +11 -8
  30. package/bundle/components/ListItemControlsButton.md +16 -13
  31. package/bundle/components/ListItemControlsButtonDropdown.md +9 -6
  32. package/bundle/components/ListItemSelectable.md +7 -4
  33. package/bundle/components/ListMasterFooter.md +8 -5
  34. package/bundle/components/ListMasterHeader.md +8 -5
  35. package/bundle/components/ListSortableItem.md +11 -8
  36. package/bundle/components/ListTableItem.md +7 -4
  37. package/bundle/components/LoaderMiddle.md +7 -4
  38. package/bundle/components/LoaderScreen.md +11 -8
  39. package/bundle/components/LoaderSmall.md +7 -4
  40. package/bundle/components/Marker.md +184 -69
  41. package/bundle/components/MarkerStatus.md +206 -88
  42. package/bundle/components/MaskedField.md +2 -4
  43. package/bundle/components/MasterTable.md +602 -0
  44. package/bundle/components/ModalWindow.md +7 -4
  45. package/bundle/components/MultiselectField.md +2183 -132
  46. package/bundle/components/Notification.md +12 -9
  47. package/bundle/components/Overlay.md +9 -4
  48. package/bundle/components/Page.md +2 -2
  49. package/bundle/components/Pagination.md +15 -8
  50. package/bundle/components/Row.md +1 -1
  51. package/bundle/components/SelectExtendedField.md +3 -3
  52. package/bundle/components/SelectField.md +466 -148
  53. package/bundle/components/SliderExtended.md +39 -36
  54. package/bundle/components/SmallInput.md +194 -51
  55. package/bundle/components/Suggest.md +535 -99
  56. package/bundle/components/SwipeableArea.md +428 -79
  57. package/bundle/components/TableBasic.md +19 -11
  58. package/bundle/components/TabsExtended.md +24 -21
  59. package/bundle/components/Tag.md +6 -2
  60. package/bundle/components/Text.md +28 -25
  61. package/bundle/components/TextField.md +3 -4
  62. package/bundle/components/ThemeProvider.md +50 -1
  63. package/bundle/components/Title.md +26 -23
  64. package/bundle/components/Tooltip.md +24 -21
  65. package/bundle/components/TopOverlay.md +7 -4
  66. package/bundle/guides/codestyle.md +3 -0
  67. package/bundle/guides/context.md +84 -12
  68. package/bundle/guides/guidelines.md +321 -0
  69. package/bundle/guides/template.md +22 -12
  70. package/bundle/manifest.json +31 -14
  71. package/bundle/release-notes/1.45.0.mdx +117 -0
  72. package/bundle/release-notes/1.46.0.mdx +7 -0
  73. package/bundle/tokens.json +6362 -0
  74. package/dist/index.js +177 -28
  75. package/dist/index.js.map +1 -1
  76. package/package.json +1 -1
@@ -3,10 +3,10 @@ component: ListSortableItem
3
3
  category: List
4
4
  related: [ListSortable, ListSortableItemTarget, ListSortableItemControls, ListItem]
5
5
  tokens:
6
- - --triplex-next-ListItem-Background
7
- - --triplex-next-ListItem-Background_Selected
8
- - --triplex-next-ListItem-Background_Dragging
9
- - --triplex-next-ListItem-Shadow_Dragging
6
+ - ListItem.Background
7
+ - ListItem.Background_Hover
8
+ - ListItem.Background_Dragging
9
+ - ListItem.Shadow_Dragging
10
10
  stories: stories/List/List.stories.tsx
11
11
  version: "1.0"
12
12
  ---
@@ -54,14 +54,17 @@ drag-handle нужно вынести в отдельный элемент.
54
54
 
55
55
  ## Дизайн-токены
56
56
 
57
+ Переопределяются через `ThemeProvider` (prop `tokens`) — см. `ThemeProvider-ai.md` →
58
+ «Как переопределять токены». Значения по умолчанию — `src/components/DesignTokens/components/ListItem.ts`.
59
+
57
60
  Сам `ListSortableItem` не использует токены (только z-index при `dragging`).
58
61
  Токены применяются в `ListSortableItem.Target`:
59
62
 
60
63
  ```text
61
- --triplex-next-ListItem-Background // фон по умолчанию
62
- --triplex-next-ListItem-Background_Selected // фон при hover
63
- --triplex-next-ListItem-Background_Dragging // фон во время drag
64
- --triplex-next-ListItem-Shadow_Dragging // тень во время drag
64
+ ListItem.Background // фон по умолчанию
65
+ ListItem.Background_Hover // фон при hover
66
+ ListItem.Background_Dragging // фон во время drag
67
+ ListItem.Shadow_Dragging // тень во время drag
65
68
  ```
66
69
 
67
70
  ---
@@ -3,8 +3,8 @@ component: ListTableItem
3
3
  category: List
4
4
  related: [ListItem, ListItemSelectable, ListItemControls, ListItemControlsButton, SwipeableArea]
5
5
  tokens:
6
- - --triplex-next-ListItem-Background
7
- - --triplex-next-ListItem-Background_Selected
6
+ - ListItem.Background
7
+ - ListItem.Background_Selected
8
8
  stories: stories/List/ListTableItem.stories.tsx
9
9
  version: "1.0"
10
10
  ---
@@ -50,9 +50,12 @@ version: "1.0"
50
50
 
51
51
  ## Дизайн-токены
52
52
 
53
+ Переопределяются через `ThemeProvider` (prop `tokens`) — см. `ThemeProvider-ai.md` →
54
+ «Как переопределять токены». Значения по умолчанию — `src/components/DesignTokens/components/ListItem.ts`.
55
+
53
56
  ```text
54
- --triplex-next-ListItem-Background // фон строки
55
- --triplex-next-ListItem-Background_Selected // фон выбранной строки (через ListItemSelectable + ListItemContent)
57
+ ListItem.Background // фон строки
58
+ ListItem.Background_Selected // фон выбранной строки (через ListItemSelectable + ListItemContent)
56
59
  ```
57
60
 
58
61
  Применяются в подкомпонентах `ListItemContent`/`ListItemSelectable`. Сам
@@ -3,8 +3,8 @@ component: LoaderMiddle
3
3
  category: Loaders
4
4
  related: [LoaderSmall, LoaderScreen, TableBasic]
5
5
  tokens:
6
- - --triplex-next-Loader-Middle_Background_Default
7
- - --triplex-next-Loader-Element_Background_Brand
6
+ - Loader.Middle_Background_Default
7
+ - Loader.Element_Background_Brand
8
8
  stories: stories/Loaders/LoaderMiddle/LoaderMiddle.stories.tsx
9
9
  version: "1.0"
10
10
  ---
@@ -48,9 +48,12 @@ version: "1.0"
48
48
 
49
49
  ## Дизайн-токены
50
50
 
51
+ Переопределяются через `ThemeProvider` (prop `tokens`) — см. `ThemeProvider-ai.md` →
52
+ «Как переопределять токены». Значения по умолчанию — `src/components/DesignTokens/components/Loader.ts`.
53
+
51
54
  ```text
52
- --triplex-next-Loader-Middle_Background_Default
53
- --triplex-next-Loader-Element_Background_Brand
55
+ Loader.Middle_Background_Default
56
+ Loader.Element_Background_Brand
54
57
  ```
55
58
 
56
59
  - `Middle_Background_Default` — фон квадратной подложки (`ColorNeutral.80` в светлой теме,
@@ -3,8 +3,8 @@ component: LoaderScreen
3
3
  category: Loaders
4
4
  related: [LoaderSmall, LoaderMiddle, Gap, Text, ModalWindowContent, LightBoxContent, LightBoxSideOverlay, List, TableBasic, MultiselectField]
5
5
  tokens:
6
- - --triplex-next-LoaderScreen-Small_Backdrop_Default
7
- - --triplex-next-LoaderScreen-Middle_Backdrop_Default
6
+ - LoaderScreen.Small_Backdrop_Default
7
+ - LoaderScreen.Middle_Backdrop_Default
8
8
  stories: stories/Loaders/LoaderScreen/LoaderScreen.stories.tsx
9
9
  version: "1.0"
10
10
  ---
@@ -85,19 +85,22 @@ LoaderScreen и сами фиксируют `type="middle"`. Потребите
85
85
 
86
86
  ## Дизайн-токены
87
87
 
88
- ```
89
- --triplex-next-LoaderScreen-Small_Backdrop_Default (подложка при type="small")
90
- --triplex-next-LoaderScreen-Middle_Backdrop_Default (подложка при type="middle")
88
+ Переопределяются через `ThemeProvider` (prop `tokens`) — см. `ThemeProvider-ai.md` →
89
+ «Как переопределять токены». Значения по умолчанию — `src/components/DesignTokens/components/LoaderScreen.ts`.
90
+
91
+ ```text
92
+ LoaderScreen.Small_Backdrop_Default (подложка при type="small")
93
+ LoaderScreen.Middle_Backdrop_Default (подложка при type="middle")
91
94
  ```
92
95
 
93
96
  Определены в `src/components/DesignTokens/components/LoaderScreen.ts`. Оба ссылаются на
94
97
  `ColorNeutralAlpha.30` (в тёмной теме — `ColorDarkNeutralAlpha.30`), то есть визуально совпадают, но
95
98
  разведены по типам намеренно — чтобы дизайн мог развести их независимо.
96
99
 
97
- Там же объявлен третий токен `--triplex-next-LoaderScreen-Middle_Background_Default`, который стилями
100
+ Там же объявлен третий токен `LoaderScreen.Middle_Background_Default`, который стилями
98
101
  LoaderScreen **не используется**: фон плашки `LoaderMiddle` берётся из
99
- `--triplex-next-Loader-Middle_Background_Default`, а точки — из
100
- `--triplex-next-Loader-Element_Background_Brand`. Токен остаётся в публичном наборе (его удаление —
102
+ `Loader.Middle_Background_Default`, а точки — из
103
+ `Loader.Element_Background_Brand`. Токен остаётся в публичном наборе (его удаление —
101
104
  breaking change для темизации), но опираться на него не нужно.
102
105
 
103
106
  Собственных цветов текста у компонента нет — они приходят из `Text` (`Typography`).
@@ -3,8 +3,8 @@ component: LoaderSmall
3
3
  category: Loaders
4
4
  related: [LoaderMiddle, LoaderScreen, Button, Dropdown, ListItemLoading, SuggestField, SelectExtendedField]
5
5
  tokens:
6
- - --triplex-next-Loader-Element_Background_Brand
7
- - --triplex-next-Loader-Element_Background_Neutral
6
+ - Loader.Element_Background_Brand
7
+ - Loader.Element_Background_Neutral
8
8
  stories: stories/Loaders/LoaderSmall/LoaderSmall.stories.tsx
9
9
  version: "1.0"
10
10
  ---
@@ -62,9 +62,12 @@ version: "1.0"
62
62
 
63
63
  ## Дизайн-токены
64
64
 
65
+ Переопределяются через `ThemeProvider` (prop `tokens`) — см. `ThemeProvider-ai.md` →
66
+ «Как переопределять токены». Значения по умолчанию — `src/components/DesignTokens/components/Loader.ts`.
67
+
65
68
  ```text
66
- --triplex-next-Loader-Element_Background_Brand
67
- --triplex-next-Loader-Element_Background_Neutral
69
+ Loader.Element_Background_Brand
70
+ Loader.Element_Background_Neutral
68
71
  ```
69
72
 
70
73
  - `Element_Background_Brand` — цвет точек темы `BRAND` (`ColorBrand.50` в обеих темах).
@@ -1,11 +1,13 @@
1
1
  ---
2
2
  component: Marker
3
- category: Feedback
4
- figma-node: ""
5
- figma-file: ""
6
- related: [MarkerStatus, Badge, TagColor]
7
- tokens: []
8
- stories: ""
3
+ category: Marker
4
+ related: [Badge, MarkerStatus]
5
+ tokens:
6
+ - Marker.Background_Error
7
+ - Marker.Background_Success
8
+ - Marker.Background_Waiting
9
+ - Marker.Background_Warning
10
+ stories: stories/Marker/Marker.stories.tsx
9
11
  version: "1.0"
10
12
  ---
11
13
 
@@ -13,110 +15,150 @@ version: "1.0"
13
15
 
14
16
  ## Назначение
15
17
 
16
- Тонкая обёртка над `Badge.Dot` — цветной кружок-статус (success/error/
17
- warning/waiting). Содержательно это **именованный preset цвета** для точки,
18
- чтобы не передавать `palette`-атрибут каждый раз.
18
+ Цветная точка-индикатор статуса. Тонкая обёртка над `Badge.Dot`: единственное, что
19
+ `Marker` добавляет к точке, — цвет фона по статусу. Ни содержимого, ни состояния, ни
20
+ логики у компонента нет; размер, разметка и проброс `ref` целиком приходят из `Badge.Dot`.
19
21
 
20
- Используй когда: нужен компактный индикатор статуса (в строке таблицы,
21
- заголовке, рядом с меткой) и выбор из фиксированной 4-статусной палитры
22
- семантики. Для статуса с подписью — `MarkerStatus`. Для кастомного цвета —
23
- `Badge.Dot` напрямую.
22
+ Используй когда: нужно отметить статус объекта компактной цветной точкой — в строке
23
+ таблицы, в списке, рядом с заголовком.
24
24
 
25
- ---
26
-
27
- ## Файловая структура
25
+ Не используй когда:
28
26
 
29
- ```text
30
- src/components/Marker/
31
- ├── Marker.tsx # FC, обёртка над Badge.Dot
32
- ├── enums.ts # EMarkerStatus (SUCCESS/ERROR/WARNING/WAITING)
33
- ├── utils.ts # statusToClassNameMap — публичная, используется MarkerStatus
34
- ├── styles/Marker.module.less # Цвета статусов
35
- └── index.ts # Barrel
36
- ```
27
+ - Нужна точка с подписью статуса и описанием под ней — возьми `MarkerStatus`, это
28
+ готовая композиция `Marker` + типографика.
29
+ - Нужен нейтральный индикатор без статусной семантики (счётчик уведомлений,
30
+ «есть непрочитанное») — возьми `Badge.Dot` напрямую: у него один общий токен фона.
31
+ - Нужен интерактивный элемент — `Marker` рендерит неинтерактивный `<span>` без роли,
32
+ фокуса и обработки клавиатуры.
37
33
 
38
34
  ---
39
35
 
40
36
  ## Варианты и props
41
37
 
42
- ### `IMarkerProps extends IBadgeDotProps`
38
+ `IMarkerProps extends IBadgeDotProps`, то есть публичный API `Marker` наследует форму
39
+ props точки: любой стандартный атрибут `<span>` (`id`, `data-*`, `style`, `role`,
40
+ `aria-*`, обработчики) уходит на корневой элемент через `...restProps`. `className`
41
+ объединяется с базовыми классами через `clsx`, а не заменяет их.
43
42
 
44
- | Prop | Тип | Обязателен | Описание |
45
- |---|---|---|---|
46
- | `status` | `EMarkerStatus` | Да | Семантический статус (цвет). |
47
- | `...IBadgeDotProps` | — | — | Все props `Badge.Dot` (size, className, прочие). |
43
+ ### Обязательные props
48
44
 
49
- ### EMarkerStatus
45
+ | Prop | Тип | Описание |
46
+ |---|---|---|
47
+ | `status` | `EMarkerStatus` | Цвет точки: `SUCCESS` / `ERROR` / `WARNING` / `WAITING`. Значения по умолчанию нет |
48
+ | `size` | `EComponentSize` | Диаметр точки: `SM` — 6px, `MD` — 8px, `LG` — 10px. Приходит из `IBadgeDotProps`, значения по умолчанию нет |
50
49
 
51
- ```ts
52
- enum EMarkerStatus {
53
- SUCCESS = "success",
54
- ERROR = "error",
55
- WARNING = "warning",
56
- WAITING = "waiting",
57
- }
58
- ```
50
+ Опциональных props сверх стандартных атрибутов `<span>` у компонента нет.
51
+ `children` унаследован из `IBadgeDotProps` как `never` — точка не имеет содержимого,
52
+ передать детей не даст типизация.
59
53
 
60
- Четыре фиксированных статуса. Расширение — breaking change.
54
+ ### Статусы и цвета
61
55
 
62
- ---
56
+ Каждому значению `EMarkerStatus` соответствует один css-класс и один токен фона —
57
+ соответствие задано таблицей `STATUS_TO_CLASS_NAME_MAP` в `src/components/Marker/utils.ts`.
58
+ Другой палитры и других вариантов оформления у компонента нет: чтобы добавить статус,
59
+ нужно добавить и значение enum (breaking change), и класс, и токен.
63
60
 
64
- ## Ключевые особенности реализации
65
-
66
- ### Реализация — одна строка
67
-
68
- ```tsx
69
- <Badge.Dot className={clsx(styles.marker, statusToClassNameMap[status], className)} {...rest} />
70
- ```
61
+ ---
71
62
 
72
- - Поверх `Badge.Dot` накладывается класс `.marker` + один из `.success/.error/.warning/.waiting` из `Marker.module.less`, которые переопределяют цвета у точки.
73
- - Все остальные props `Badge.Dot` (включая `size`, `style`) прокидываются как есть.
63
+ ## Дизайн-токены
74
64
 
75
- ### `statusToClassNameMap` — экспортируемая утилита
65
+ Переопределяются через `ThemeProvider` (prop `tokens`) — см. `ThemeProvider-ai.md` →
66
+ «Как переопределять токены». Значения по умолчанию — `src/components/DesignTokens/components/Marker.ts`.
76
67
 
77
- ```ts
78
- export const statusToClassNameMap = { [EMarkerStatus.SUCCESS]: styles.success, ... };
68
+ ```text
69
+ Marker.Background_Success
70
+ Marker.Background_Error
71
+ Marker.Background_Warning
72
+ Marker.Background_Waiting
79
73
  ```
80
74
 
81
- - **Экспортируется для переиспользования в `MarkerStatus`** (который применяет те же классы к своему контейнеру для окраски текста/описания).
82
- - Если добавляешь статус — обязательно обнови `utils.ts` и LESS-стили, и проверь, что `MarkerStatus` тоже подтягивает новый класс.
75
+ Значения одинаковы в светлой и тёмной темах: `ColorBrand.50`, `ColorError.50`,
76
+ `ColorWarning.50`, `ColorSystem.50` соответственно. Геометрия точки (диаметр,
77
+ скругление) токенами не задаётся — она приходит из `Badge.Dot` литералами в LESS.
83
78
 
84
79
  ---
85
80
 
86
81
  ## Инварианты
87
82
 
88
- - **`EMarkerStatus`** (4 значения) — публичный API. Расширение — breaking.
89
- - **`Marker = Badge.Dot + className`** — тонкая обёртка; избегать добавления своих props, которые размажут семантику со `Badge`.
90
- - **`statusToClassNameMap`** экспортируется из `utils.ts` — `MarkerStatus` зависит от неё. Не менять shape.
91
- - **`size` приходит от `Badge.Dot`** (через `IBadgeDotProps`), а не кастомизируется Marker'ом.
92
- - **FC, не forwardRef** — ref прокидывается `Badge.Dot` внутри? Проверь перед изменением.
83
+ - **`forwardRef` — не убирать.** `ref` уходит на корневой `<span>`, отрендеренный
84
+ `Badge.Dot` (тип — `HTMLSpanElement`).
85
+ - **Корневой элемент — `<span>` из `Badge.Dot`.** Собственной разметки `Marker` не
86
+ создаёт; смена тега или добавление обёртки ломает инлайновое размещение и вертикальное
87
+ выравнивание у потребителей (в том числе у `MarkerStatus`).
88
+ - **Значения `EMarkerStatus`** (`"success"`, `"error"`, `"warning"`, `"waiting"`) —
89
+ часть публичного API. Совпадают с именами css-классов в `Marker.module.less`, но это
90
+ совпадение, а не контракт: связь между статусом и классом идёт только через
91
+ `STATUS_TO_CLASS_NAME_MAP`.
92
+ - **`STATUS_TO_CLASS_NAME_MAP` — внутренняя утилита, но с внешним потребителем.**
93
+ Через barrel не экспортируется, однако `MarkerStatus` импортирует её напрямую
94
+ (`src/components/MarkerStatus/MarkerStatus.tsx`) и вешает те же классы на свой
95
+ корневой `<div>`; на них опирается `MarkerStatus.test.tsx`. Переименование карты
96
+ или её ключей ломает соседний компонент и его тест.
97
+ - **Классы `.success` / `.error` / `.warning` / `.waiting` работают только вложенными
98
+ в `.marker`** (в LESS они записаны как `&.success` и т.д.). На корневом элементе
99
+ `MarkerStatus` те же классы фона не дают — там они висят как маркер статуса для тестов.
100
+ - **`IMarkerProps extends IBadgeDotProps`** — любое изменение формы `IBadgeDotProps`
101
+ автоматически меняет публичный API `Marker`.
102
+ - **`displayName`** — `Marker`, виден в React DevTools.
103
+ - **Имена токенов `Marker.Background_Success` / `_Error` / `_Warning` / `_Waiting`** —
104
+ не переименовывать: путь токена потребитель передаёт в `ThemeProvider`, а на
105
+ соответствующий ему внутренний css-слой ссылается `Marker.module.less`.
93
106
 
94
107
  ---
95
108
 
96
109
  ## Accessibility
97
110
 
98
- - `Badge.Dot` по умолчанию — декоративный элемент без ARIA. Для анонсирования статуса скринридером потребитель должен добавить `aria-label` через `...rest` или сопроводить текстом рядом.
99
- - `MarkerStatus` уже выводит текстовый статус — там a11y закрыт.
111
+ Компонент неинтерактивен: не получает фокус, не обрабатывает клавиатуру, ARIA-ролей и
112
+ атрибутов сам не выставляет. Строк на конкретном языке не хардкодит — весь текст
113
+ приходит от потребителя.
100
114
 
101
- ---
115
+ **Своего доступного имени у точки нет** — это ограничение унаследовано от `Badge.Dot`:
116
+ корневой `<span>` без роли попадает в `generic`, а для него доступное имя запрещено,
117
+ поэтому одного `aria-label` недостаточно. Обязанность потребителя:
102
118
 
103
- ## Дизайн-токены
119
+ - если статус продублирован видимым текстом рядом (типичный случай — `MarkerStatus`),
120
+ точка декоративна: передай `aria-hidden`;
121
+ - если точка — единственный носитель смысла, передай роль, поддерживающую имя, вместе
122
+ с текстом: `role="img"` и `aria-label` (оба уходят в `...restProps`).
104
123
 
105
- Цвета статусов заданы в `styles/Marker.module.less` (не через CSS-переменные). Для новой темы статусов — переопределяй в LESS.
124
+ **Пример внутри библиотеки:** `MarkerStatus` рендерит `<Marker status={status} size={size} />`
125
+ без `aria-hidden` — осознанно: смысл статуса там несёт текст рядом, а точка без роли
126
+ попадает в `generic` и своего имени в дерево доступности не добавляет
127
+ (см. `MarkerStatus-ai.md` → «Accessibility»). Для отдельно стоящего `Marker` это
128
+ не образец: там носитель смысла один, и роль с именем нужны.
106
129
 
107
130
  ---
108
131
 
109
132
  ## Связанные компоненты
110
133
 
111
- - `Badge` / `Badge.Dot` — основа.
112
- - `MarkerStatus` — Marker + текст + описание, использует тот же `statusToClassNameMap`.
113
- - `TagColor` — альтернатива для статуса с подписью внутри "пилюли".
134
+ - `Badge` (`src/components/Badge/Badge.tsx`) — семейство, из которого `Marker` берёт
135
+ точку: рендерит `Badge.Dot` и наследует `IBadgeDotProps`. Всё, кроме цвета фона
136
+ (размеры, разметка, `ref`, ограничение `children: never`), задаётся там.
137
+ - `MarkerStatus` (`src/components/MarkerStatus/MarkerStatus.tsx`) — готовая композиция
138
+ «точка + заголовок статуса + описание». Единственный внутренний потребитель `Marker`,
139
+ и при этом он опирается на внутреннюю карту `STATUS_TO_CLASS_NAME_MAP` — см. «Инварианты».
114
140
 
115
141
  ---
116
142
 
117
143
  ## Stories
118
144
 
119
- Нет отдельных — только через `MarkerStatus.stories.tsx` (там показаны все 4 статуса).
145
+ Основные истории: `stories/Marker/Marker.stories.tsx`
146
+ Файлы примеров: `stories/Marker/examples/`
147
+
148
+ | Story | Example file | Что демонстрирует |
149
+ |---|---|---|
150
+ | `Playground` | `Playground.tsx` | Интерактивный подбор `status` и `size` |
151
+ | `Default` | `Default.tsx` | Минимальный вызов: оба props обязательны |
152
+ | `Statuses` | `Statuses.tsx` | Все четыре статуса с подписями |
153
+ | `Sizes` | `Sizes.tsx` | Размеры `SM` / `MD` / `LG` |
154
+ | `WithAccessibleName` | `WithAccessibleName.tsx` | Точка как единственный носитель смысла: `role="img"` + `aria-label` |
155
+
156
+ Скриншот-регрессия снимается со стори `Statuses` и `Sizes`
157
+ (`__screenshots__/marker--{statuses,sizes}--xs|xl.png`). `Playground` исключён как
158
+ интерактивная песочница, `Default` и `WithAccessibleName` — через `testRunner: { skip: true }`:
159
+ обе рендерят ровно ту же точку, что уже есть в `Statuses`. Отдельная стори `VisualTests`
160
+ не нужна — у компонента нет состояний, требующих взаимодействия (ни hover, ни focus,
161
+ ни раскрытия).
120
162
 
121
163
  ---
122
164
 
@@ -124,4 +166,77 @@ export const statusToClassNameMap = { [EMarkerStatus.SUCCESS]: styles.success, .
124
166
 
125
167
  | Дата | Изменение |
126
168
  |---|---|
127
- | 2026-04-18 | Создан документ |
169
+ | 2026-09-01 | Создан документ. AI-рефакторинг: `Marker` переведён с `React.FC` на `React.forwardRef` — `ref` теперь уходит на корневой `<span>` от `Badge.Dot`; добавлены JSDoc на компонент, `IMarkerProps.status`, значения `EMarkerStatus` и `STATUS_TO_CLASS_NAME_MAP`, карта закреплена через `satisfies Record<EMarkerStatus, string>`, поправлен порядок импортов. Карта переименована `statusToClassNameMap` → `STATUS_TO_CLASS_NAME_MAP` по `codestyle.md` (константа модульного уровня — UPPER_SNAKE_CASE); переименование внутреннее, `utils.ts` не входит ни в один barrel, синхронно обновлён импорт в `MarkerStatus.tsx`. Добавлены unit-тесты: `__tests__/Marker.test.tsx` (все статусы, проброс `size` в `Badge.Dot`, мердж `className`, `ref`, спред `...restProps`, `displayName`) и `__tests__/utils.test.tsx` (различимость и непустота классов карты статусов). Разметку точки и полную матрицу размеров не дублируем — их покрывает `Badge/__tests__/BadgeDot.test.tsx`; полноту карты статусов гарантирует `satisfies`. Заведены stories `stories/Marker/` в modern pattern. Публичный API (имена и типы props, значения `EMarkerStatus`, barrel-экспорты), разметка и визуальное поведение не изменены. |
170
+
171
+ ---
172
+
173
+ ## Примеры использования
174
+
175
+ ### Default
176
+
177
+ `stories/Marker/examples/Default.tsx`
178
+
179
+ ```tsx
180
+ import React from "react";
181
+ import { Marker, EMarkerStatus, EComponentSize } from "@sberbusiness/triplex-next";
182
+
183
+ export const Default = () => <Marker status={EMarkerStatus.SUCCESS} size={EComponentSize.MD} />;
184
+ ```
185
+
186
+ ### Statuses
187
+
188
+ `stories/Marker/examples/Statuses.tsx`
189
+
190
+ ```tsx
191
+ import React from "react";
192
+ import { Marker, EMarkerStatus, EComponentSize } from "@sberbusiness/triplex-next";
193
+
194
+ const STATUSES = Object.values(EMarkerStatus);
195
+
196
+ export const Statuses = () => (
197
+ <div style={{ display: "flex", alignItems: "flex-start", gap: 32, flexWrap: "wrap" }}>
198
+ {STATUSES.map((status) => (
199
+ <div key={status}>
200
+ <div style={{ marginBottom: 8, fontSize: 16, fontWeight: 700 }}>{status.toUpperCase()}</div>
201
+ <Marker status={status} size={EComponentSize.MD} aria-hidden />
202
+ </div>
203
+ ))}
204
+ </div>
205
+ );
206
+ ```
207
+
208
+ ### Sizes
209
+
210
+ `stories/Marker/examples/Sizes.tsx`
211
+
212
+ ```tsx
213
+ import React from "react";
214
+ import { Marker, EMarkerStatus, EComponentSize } from "@sberbusiness/triplex-next";
215
+
216
+ const SIZES = Object.values(EComponentSize);
217
+
218
+ export const Sizes = () => (
219
+ <div style={{ display: "flex", alignItems: "flex-start", gap: 32, flexWrap: "wrap" }}>
220
+ {SIZES.map((size) => (
221
+ <div key={size}>
222
+ <div style={{ marginBottom: 8, fontSize: 16, fontWeight: 700 }}>{size.toUpperCase()}</div>
223
+ <Marker status={EMarkerStatus.SUCCESS} size={size} aria-hidden />
224
+ </div>
225
+ ))}
226
+ </div>
227
+ );
228
+ ```
229
+
230
+ ### WithAccessibleName
231
+
232
+ `stories/Marker/examples/WithAccessibleName.tsx`
233
+
234
+ ```tsx
235
+ import React from "react";
236
+ import { Marker, EMarkerStatus, EComponentSize } from "@sberbusiness/triplex-next";
237
+
238
+ export const WithAccessibleName = () => (
239
+ <Marker status={EMarkerStatus.ERROR} size={EComponentSize.MD} role="img" aria-label="Ошибка" />
240
+ );
241
+ ```
242
+