@snksergio/design-system 0.61.0 → 0.63.0

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 (193) hide show
  1. package/dist-lib/ai/blocos/chart/budget-breakdown.tsx +174 -0
  2. package/dist-lib/ai/blocos/indice.md +43 -0
  3. package/dist-lib/ai/blocos/paneldetail/detalhe-com-tabela.tsx +450 -0
  4. package/dist-lib/ai/blocos/paneldetail/detalhe-de-tarefa-com-abas.tsx +570 -0
  5. package/dist-lib/ai/blocos/paneldetail/detalhe-do-registro.tsx +555 -0
  6. package/dist-lib/ai/componentes/AlertModal.md +47 -0
  7. package/dist-lib/ai/componentes/AppShell.md +117 -0
  8. package/dist-lib/ai/componentes/Breadcrumb.md +187 -0
  9. package/dist-lib/ai/componentes/Button.md +116 -0
  10. package/dist-lib/ai/componentes/ButtonGroup.md +162 -0
  11. package/dist-lib/ai/componentes/CardCheckbox.md +99 -0
  12. package/dist-lib/ai/componentes/CardOption.md +133 -0
  13. package/dist-lib/ai/componentes/Chart.md +93 -0
  14. package/dist-lib/ai/componentes/Chip.md +68 -0
  15. package/dist-lib/ai/componentes/ChoroplethMap.md +118 -0
  16. package/dist-lib/ai/componentes/ColorPicker.md +70 -0
  17. package/dist-lib/ai/componentes/Combobox.md +51 -0
  18. package/dist-lib/ai/componentes/ConversationListItem.md +90 -0
  19. package/dist-lib/ai/componentes/DataList.md +111 -0
  20. package/dist-lib/ai/componentes/DataTable.md +867 -0
  21. package/dist-lib/ai/componentes/DatePicker.md +84 -0
  22. package/dist-lib/ai/componentes/DateSeparatorChip.md +59 -0
  23. package/dist-lib/ai/componentes/EmptyState.md +72 -0
  24. package/dist-lib/ai/componentes/FileUploadField.md +95 -0
  25. package/dist-lib/ai/componentes/FloatingPanel.md +118 -0
  26. package/dist-lib/ai/componentes/FooterTable.md +62 -0
  27. package/dist-lib/ai/componentes/FormField.md +110 -0
  28. package/dist-lib/ai/componentes/Gantt.md +552 -0
  29. package/dist-lib/ai/componentes/Header.md +98 -0
  30. package/dist-lib/ai/componentes/Icon.md +65 -0
  31. package/dist-lib/ai/componentes/Kanban.md +343 -0
  32. package/dist-lib/ai/componentes/Kpi.md +103 -0
  33. package/dist-lib/ai/componentes/List.md +61 -0
  34. package/dist-lib/ai/componentes/MarkdownText.md +59 -0
  35. package/dist-lib/ai/componentes/MenuSidebar.md +128 -0
  36. package/dist-lib/ai/componentes/MessageAck.md +53 -0
  37. package/dist-lib/ai/componentes/MessageBubble.md +115 -0
  38. package/dist-lib/ai/componentes/MessageComposer.md +80 -0
  39. package/dist-lib/ai/componentes/MessageVariablesPicker.md +104 -0
  40. package/dist-lib/ai/componentes/Modal.md +88 -0
  41. package/dist-lib/ai/componentes/MonthYearPicker.md +49 -0
  42. package/dist-lib/ai/componentes/PageHeader.md +129 -0
  43. package/dist-lib/ai/componentes/Panel.md +84 -0
  44. package/dist-lib/ai/componentes/Scheduler.md +421 -0
  45. package/dist-lib/ai/componentes/ScreenLoader.md +60 -0
  46. package/dist-lib/ai/componentes/SingleMenuSidebar.md +171 -0
  47. package/dist-lib/ai/componentes/Spinner.md +52 -0
  48. package/dist-lib/ai/componentes/Table.md +192 -0
  49. package/dist-lib/ai/componentes/TableToolbar.md +87 -0
  50. package/dist-lib/ai/componentes/TabsNavigation.md +152 -0
  51. package/dist-lib/ai/componentes/Toast.md +49 -0
  52. package/dist-lib/ai/componentes/_primitivos.md +74 -0
  53. package/dist-lib/ai/componentes/avatar-ig.md +181 -0
  54. package/dist-lib/ai/componentes/indice.json +49 -0
  55. package/dist-lib/ai/exemplos/app-shell/app-shell-example.tsx +140 -0
  56. package/dist-lib/ai/exemplos/app-shell/index.ts +3 -0
  57. package/dist-lib/ai/exemplos/app-shell/nav-data.ts +97 -0
  58. package/dist-lib/ai/exemplos/app-shell/routes.tsx +75 -0
  59. package/dist-lib/ai/exemplos/chat/chat-screen.tsx +152 -0
  60. package/dist-lib/ai/exemplos/chat/chat-v2-mocks.ts +171 -0
  61. package/dist-lib/ai/exemplos/chat/chat-v2.styles.ts +23 -0
  62. package/dist-lib/ai/exemplos/chat/chat-v2.types.ts +81 -0
  63. package/dist-lib/ai/exemplos/chat/components/ChannelDot/channel-dot.tsx +28 -0
  64. package/dist-lib/ai/exemplos/chat/components/ConversationActionsMenu/conversation-actions-menu.tsx +83 -0
  65. package/dist-lib/ai/exemplos/chat/components/ConversationActionsMenu/index.ts +4 -0
  66. package/dist-lib/ai/exemplos/chat/components/ConversationColumn/conversation-column.styles.ts +22 -0
  67. package/dist-lib/ai/exemplos/chat/components/ConversationColumn/conversation-column.tsx +203 -0
  68. package/dist-lib/ai/exemplos/chat/components/ConversationColumn/conversation-column.types.ts +10 -0
  69. package/dist-lib/ai/exemplos/chat/components/ConversationColumn/index.ts +2 -0
  70. package/dist-lib/ai/exemplos/chat/components/ConversationListItem/conversation-list-item.styles.ts +55 -0
  71. package/dist-lib/ai/exemplos/chat/components/ConversationListItem/conversation-list-item.tsx +52 -0
  72. package/dist-lib/ai/exemplos/chat/components/ConversationListItem/conversation-list-item.types.ts +7 -0
  73. package/dist-lib/ai/exemplos/chat/components/ConversationListItem/index.ts +2 -0
  74. package/dist-lib/ai/exemplos/chat/components/DateSeparator/date-separator.tsx +18 -0
  75. package/dist-lib/ai/exemplos/chat/components/DetailField/detail-field.tsx +23 -0
  76. package/dist-lib/ai/exemplos/chat/components/DetailSection/detail-section.tsx +41 -0
  77. package/dist-lib/ai/exemplos/chat/components/DetailSection/index.ts +1 -0
  78. package/dist-lib/ai/exemplos/chat/components/DetailsColumn/details-column.styles.ts +30 -0
  79. package/dist-lib/ai/exemplos/chat/components/DetailsColumn/details-column.tsx +142 -0
  80. package/dist-lib/ai/exemplos/chat/components/DetailsColumn/details-column.types.ts +16 -0
  81. package/dist-lib/ai/exemplos/chat/components/DetailsColumn/index.ts +5 -0
  82. package/dist-lib/ai/exemplos/chat/components/FilterRow/filter-row.styles.ts +37 -0
  83. package/dist-lib/ai/exemplos/chat/components/FilterRow/filter-row.tsx +45 -0
  84. package/dist-lib/ai/exemplos/chat/components/FilterRow/index.ts +1 -0
  85. package/dist-lib/ai/exemplos/chat/components/FiltersColumn/filters-column.styles.ts +27 -0
  86. package/dist-lib/ai/exemplos/chat/components/FiltersColumn/filters-column.tsx +66 -0
  87. package/dist-lib/ai/exemplos/chat/components/FiltersColumn/filters-column.types.ts +13 -0
  88. package/dist-lib/ai/exemplos/chat/components/FiltersColumn/filters-rail.tsx +38 -0
  89. package/dist-lib/ai/exemplos/chat/components/FiltersColumn/index.ts +6 -0
  90. package/dist-lib/ai/exemplos/chat/components/MessageBubble/index.ts +2 -0
  91. package/dist-lib/ai/exemplos/chat/components/MessageBubble/message-bubble.styles.ts +37 -0
  92. package/dist-lib/ai/exemplos/chat/components/MessageBubble/message-bubble.tsx +29 -0
  93. package/dist-lib/ai/exemplos/chat/components/MessageBubble/message-bubble.types.ts +5 -0
  94. package/dist-lib/ai/exemplos/chat/components/PersonAvatar/index.ts +5 -0
  95. package/dist-lib/ai/exemplos/chat/components/PersonAvatar/person-avatar.tsx +31 -0
  96. package/dist-lib/ai/exemplos/chat/components/QueueColumn/index.ts +2 -0
  97. package/dist-lib/ai/exemplos/chat/components/QueueColumn/queue-column.styles.ts +19 -0
  98. package/dist-lib/ai/exemplos/chat/components/QueueColumn/queue-column.tsx +140 -0
  99. package/dist-lib/ai/exemplos/chat/components/QueueColumn/queue-column.types.ts +13 -0
  100. package/dist-lib/ai/exemplos/chat/components/RailItem/index.ts +1 -0
  101. package/dist-lib/ai/exemplos/chat/components/RailItem/rail-item.styles.ts +30 -0
  102. package/dist-lib/ai/exemplos/chat/components/RailItem/rail-item.tsx +42 -0
  103. package/dist-lib/ai/exemplos/chat/hooks/use-resizable.ts +98 -0
  104. package/dist-lib/ai/exemplos/chat/index.ts +1 -0
  105. package/dist-lib/ai/exemplos/clientes/_table-data.ts +59 -0
  106. package/dist-lib/ai/exemplos/clientes/clientes-screen.tsx +505 -0
  107. package/dist-lib/ai/exemplos/clientes/clientes-showcase-mocks.ts +117 -0
  108. package/dist-lib/ai/exemplos/clientes/clientes-showcase.styles.ts +13 -0
  109. package/dist-lib/ai/exemplos/clientes/clientes-showcase.types.ts +16 -0
  110. package/dist-lib/ai/exemplos/clientes/components/DetailDrawer/detail-drawer.styles.ts +28 -0
  111. package/dist-lib/ai/exemplos/clientes/components/DetailDrawer/detail-drawer.tsx +303 -0
  112. package/dist-lib/ai/exemplos/clientes/components/DetailDrawer/detail-drawer.types.ts +14 -0
  113. package/dist-lib/ai/exemplos/clientes/components/DetailDrawer/index.ts +2 -0
  114. package/dist-lib/ai/exemplos/clientes/components/NovoClienteDrawer/index.ts +2 -0
  115. package/dist-lib/ai/exemplos/clientes/components/NovoClienteDrawer/novo-cliente-drawer.tsx +207 -0
  116. package/dist-lib/ai/exemplos/clientes/index.ts +1 -0
  117. package/dist-lib/ai/exemplos/dashboard/dashboard-brazil-map.ts +33 -0
  118. package/dist-lib/ai/exemplos/dashboard/dashboard-screen.tsx +1110 -0
  119. package/dist-lib/ai/exemplos/dashboard/index.ts +1 -0
  120. package/dist-lib/ai/exemplos/edit-page/components/StepNav.tsx +81 -0
  121. package/dist-lib/ai/exemplos/edit-page/components/section-card.tsx +85 -0
  122. package/dist-lib/ai/exemplos/edit-page/edit-page-screen.tsx +234 -0
  123. package/dist-lib/ai/exemplos/edit-page/index.ts +1 -0
  124. package/dist-lib/ai/exemplos/finance/_table-data.ts +57 -0
  125. package/dist-lib/ai/exemplos/finance/clientes-financeiro-mocks.ts +227 -0
  126. package/dist-lib/ai/exemplos/finance/clientes-financeiro.types.ts +75 -0
  127. package/dist-lib/ai/exemplos/finance/clientes-showcase-mocks.ts +117 -0
  128. package/dist-lib/ai/exemplos/finance/clientes-showcase.styles.ts +13 -0
  129. package/dist-lib/ai/exemplos/finance/clientes-showcase.types.ts +16 -0
  130. package/dist-lib/ai/exemplos/finance/components/EditarFinanceDrawer/editar-finance-drawer.tsx +241 -0
  131. package/dist-lib/ai/exemplos/finance/components/EditarFinanceDrawer/index.ts +5 -0
  132. package/dist-lib/ai/exemplos/finance/components/ExtratoExpansion/extrato-expansion.tsx +172 -0
  133. package/dist-lib/ai/exemplos/finance/components/ExtratoExpansion/index.ts +1 -0
  134. package/dist-lib/ai/exemplos/finance/components/FinanceDetailPanel/finance-detail-panel.tsx +241 -0
  135. package/dist-lib/ai/exemplos/finance/components/FinanceDetailPanel/index.ts +2 -0
  136. package/dist-lib/ai/exemplos/finance/components/NovoClienteDrawer/index.ts +2 -0
  137. package/dist-lib/ai/exemplos/finance/components/NovoClienteDrawer/novo-cliente-drawer.tsx +207 -0
  138. package/dist-lib/ai/exemplos/finance/components/SacarDialog/index.ts +2 -0
  139. package/dist-lib/ai/exemplos/finance/components/SacarDialog/sacar-dialog.tsx +346 -0
  140. package/dist-lib/ai/exemplos/finance/finance-screen.tsx +821 -0
  141. package/dist-lib/ai/exemplos/finance/index.ts +1 -0
  142. package/dist-lib/ai/exemplos/gantt/_gantt-data.tsx +402 -0
  143. package/dist-lib/ai/exemplos/gantt/gantt-screen.tsx +512 -0
  144. package/dist-lib/ai/exemplos/gantt/index.ts +1 -0
  145. package/dist-lib/ai/exemplos/login/index.ts +1 -0
  146. package/dist-lib/ai/exemplos/login/login-screen.tsx +246 -0
  147. package/dist-lib/ai/exemplos/mapa-rede/components/ConsultorDetailPanel/consultor-detail-panel.tsx +158 -0
  148. package/dist-lib/ai/exemplos/mapa-rede/components/ConsultorDetailPanel/index.ts +2 -0
  149. package/dist-lib/ai/exemplos/mapa-rede/index.ts +1 -0
  150. package/dist-lib/ai/exemplos/mapa-rede/mapa-de-rede-mocks.ts +655 -0
  151. package/dist-lib/ai/exemplos/mapa-rede/mapa-de-rede.types.ts +53 -0
  152. package/dist-lib/ai/exemplos/mapa-rede/mapa-rede-screen.tsx +227 -0
  153. package/dist-lib/ai/exemplos/order-detail/components/ActivityTab.tsx +77 -0
  154. package/dist-lib/ai/exemplos/order-detail/components/AttachmentsTab.tsx +45 -0
  155. package/dist-lib/ai/exemplos/order-detail/components/CommentsTab.tsx +111 -0
  156. package/dist-lib/ai/exemplos/order-detail/components/DetailsTab.tsx +189 -0
  157. package/dist-lib/ai/exemplos/order-detail/components/OverviewTab.tsx +200 -0
  158. package/dist-lib/ai/exemplos/order-detail/components/section-card.tsx +85 -0
  159. package/dist-lib/ai/exemplos/order-detail/index.ts +1 -0
  160. package/dist-lib/ai/exemplos/order-detail/order-detail-screen.tsx +119 -0
  161. package/dist-lib/ai/exemplos/order-detail/order-mocks.ts +186 -0
  162. package/dist-lib/ai/exemplos/order-detail/order.types.ts +118 -0
  163. package/dist-lib/ai/global/componentes.md +217 -0
  164. package/dist-lib/ai/global/composicao.md +182 -0
  165. package/dist-lib/ai/indice.json +192 -0
  166. package/dist-lib/ai/lint/ds-lint-patterns.mjs +115 -0
  167. package/dist-lib/ai/manifest.json +42 -0
  168. package/dist-lib/ai/regras/design.md +88 -0
  169. package/dist-lib/ai/regras/temas.md +192 -0
  170. package/dist-lib/ai/regras-por-componente.json +103 -0
  171. package/dist-lib/ai/roteiros/app-builder/roteiro.md +155 -0
  172. package/dist-lib/ai/roteiros/auth-builder/roteiro.md +42 -0
  173. package/dist-lib/ai/roteiros/cards/roteiro.md +34 -0
  174. package/dist-lib/ai/roteiros/charts/roteiro.md +32 -0
  175. package/dist-lib/ai/roteiros/chat/roteiro.md +31 -0
  176. package/dist-lib/ai/roteiros/crud-builder/blueprint.md +63 -0
  177. package/dist-lib/ai/roteiros/crud-builder/entrevista.md +139 -0
  178. package/dist-lib/ai/roteiros/crud-builder/geracao.md +113 -0
  179. package/dist-lib/ai/roteiros/crud-builder/roteiro.md +89 -0
  180. package/dist-lib/ai/roteiros/dashboard-builder/blueprint.md +47 -0
  181. package/dist-lib/ai/roteiros/dashboard-builder/entrevista.md +62 -0
  182. package/dist-lib/ai/roteiros/dashboard-builder/geracao.md +88 -0
  183. package/dist-lib/ai/roteiros/dashboard-builder/roteiro.md +88 -0
  184. package/dist-lib/ai/roteiros/drawers/roteiro.md +41 -0
  185. package/dist-lib/ai/roteiros/list-builder/blueprint.md +94 -0
  186. package/dist-lib/ai/roteiros/list-builder/entrevista.md +188 -0
  187. package/dist-lib/ai/roteiros/list-builder/geracao.md +63 -0
  188. package/dist-lib/ai/roteiros/list-builder/roteiro.md +91 -0
  189. package/dist-lib/ai/roteiros/module-replicator/roteiro.md +56 -0
  190. package/dist-lib/ai/roteiros/page-detail/roteiro.md +32 -0
  191. package/dist-lib/ai/roteiros/page-edit/roteiro.md +31 -0
  192. package/dist-lib/ai/roteiros/screen-composer/roteiro.md +95 -0
  193. package/package.json +4 -1
@@ -0,0 +1,113 @@
1
+ > **Nota de portabilidade.** Este roteiro foi extraído do pipeline do iGreen DS
2
+ > para Claude Code. Menções a slash command (`/ds-create-…`), a `.claude/` e a
3
+ > ferramentas daquele ambiente descrevem **como ele é acionado lá** — aqui o
4
+ > equivalente é carregar este roteiro pelo `indice.json`. O conteúdo de decisão
5
+ > (entrevista, blueprint, regras de composição) vale igual.
6
+
7
+ > **Modo submódulo (`ds-link`).** Existe `.claude/ds-config.json` com `"mode": "submodule"`?
8
+ > Então **NÃO rode `igreen:add`** — esse script não existe no seu projeto. Os componentes e
9
+ > exemplos já estão no disco em `<dsPath>/src`: importe pelo `importBase` do config
10
+ > (compostos) e pelo `primitivesBase` (primitivos shadcn), e **leia** o exemplo direto de
11
+ > `<dsPath>/src/examples/`.
12
+
13
+ # CRUD Builder — Geração
14
+
15
+ Só entre aqui após o gate aprovado. Ordem obrigatória:
16
+
17
+ ## 1. Puxar do registry (componentes + exemplo canônico)
18
+
19
+ ```bash
20
+ npm run igreen:add -- data-table example-clientes
21
+ # + example-finance (se houver drawers de criar/editar/detalhe)
22
+ # + outros componentes citados no blueprint (chip, avatar-ig, etc — o registry resolve deps)
23
+ ```
24
+
25
+ ## 2. LER antes de escrever (precedência de fontes)
26
+
27
+ 1. `src/examples/clientes/clientes-screen.tsx` — o molde real (colunas via `textColumn/currencyColumn/dateColumn/statusColumn/actionColumn`, `useMemo`, toolbar, paginação, seleção).
28
+ 2. `src/components/ui/DataTable/USAGE.md` + types ao lado — API exata.
29
+ 3. Pra drawers: `src/examples/finance/components/NovoClienteDrawer` e `.../FinanceDetailPanel`.
30
+
31
+ Nunca gere props de memória — copie a forma do exemplo.
32
+
33
+ ## 3. Criar a página
34
+
35
+ - Caminho/rota conforme o blueprint (`PAGES_DIR`/`REGISTRO`).
36
+ - Wrapper: `<div className="flex flex-col h-full min-h-0 gap-gp-2xl">` → `<PageHeader .../>` → `<DataTable className="flex-1 min-h-0" .../>`.
37
+ - `columns` em `useMemo`; server mode ⇒ `fetchData` em `useCallback`.
38
+
39
+ ### Regras de coluna (OBRIGATÓRIO — pega bugs comuns)
40
+
41
+ 1. **Filtro em TODAS as colunas de dados**: cada coluna ganha `enableColumnFilter: true` + `filterType` (text→`"text"`, number/currency/percentage→`"number"`, date→`"date"`, badge/status/select→`"select"`, multiSelect/tags→`"multiSelect"`). Só ficam de fora `actions` e render-custom sem valor. ⚠️ O funil/drawer de filtros só lista colunas com `enableColumnFilter` — marcar só 2 = bug "filtra só 2 colunas".
42
+ 2. **Coluna `actions` por ÚLTIMO**, `type: "actions"` (via `actionColumn`/`getActions`). É o **`type`** que dá as 3 garantias — vai pro fim (mesmo declarada no meio), **ancora à direita** (`pinned: "right"` é redundante) e **não entra no rateio** do autoFit. Coluna de botões montada na unha (`render` sem `type`) não recebe nenhuma das três: fica no meio da tabela e cresce no rateio. ⚠️ **NÃO passe `width`** (lib 0.42.0+): a largura é **derivada do nº de ações** — 1→44px, 2→74px, 3→104px, **4+ colapsam no "…"** (44px). Até a 0.41.x esta linha mandava espelhar `width: 64`; era inútil, porque o cálculo **ignorava `col.width`** nesta coluna. Agora vale, e 64px cabe **1** ícone. Split manual: `showInMenu: true` nos itens que devem ir pro menu (desliga o automático, sem limite de inline).
43
+ 3. **Prefira NÃO setar `width`** nas colunas de dados — `autoFit` (default ON) distribui pra preencher o container (sem 1ª coluna esticada, sem scroll). Nunca `autoFit: false` sem motivo. **(v0.22.0+)** `col.width` virou **base/piso** (não trava fixa): o autoFit usa como mínimo e ainda distribui a sobra proporcionalmente — setar `width` em várias colunas **não** deixa mais sobra à direita. Travar de fato = `width`+`maxWidth` iguais (ou `type` fixo). Título do header **nunca trunca** (a largura mínima já inclui o `headerName`).
44
+ 4. **Copiar valor** (`copyable`) — **infira, não espere que peçam**; ícone de copiar no **hover/foco** da célula + feedback "Copiado!" (~2s, `navigator.clipboard`). Critério: **o valor é um identificador que a pessoa cola em outro lugar**. ✅ documento (CPF/CNPJ/RG/IE), e-mail, telefone/WhatsApp, conta/agência/chave PIX, código de rastreio/protocolo/contrato/NF/pedido, token/hash, ID **externo**. ❌ nome de pessoa/empresa, status, data, valor monetário, quantidade, percentual, endereço em prosa. ⚠️ `id` sequencial curto (1, 2, 3) **não**; UUID/protocolo/NF **sim** — decide servir fora da tela, não a coluna se chamar "id". **Limites (verificados no código):** inerte em `actions`, na coluna de árvore e na célula em edição — marcar lá não dá erro, só não aparece; **`readMore` vence `copyable`** na mesma coluna (escolha um); copia o texto **formatado**, então numa coluna `currency` sai `R$ 1.234,56` e não `1234.56` — pro valor cru use `copyable: { value: (row) => String(row.x) }`. Texto/rótulo diferentes: `copyable: { value: (row) => "...", label: "Copiar conta" }`. **Declare no gate** as colunas em que você inferiu, pra o usuário recusar em lote — inferência silenciosa de recurso que ele não sabe que existe é surpresa, não conveniência.
45
+ 5. **Grab-to-scroll é NATIVO** (`grabToScroll` default `true`, v0.26.0+): toda tabela já rola lateral ao arrastar o corpo (mouse/pen, threshold ~6px, clique/seleção preservados). Não configure — só `grabToScroll={false}` pra desligar.
46
+ 6. **Filtro visível na tabela** (`showEmptyFilterChips`, v0.6.0+): pros filtros que o usuário mais usa (status, categoria, tipo, graduação…), passe `showEmptyFilterChips={["status", "categoria"]}` no `<DataTable>` → os chips nascem **vazios e clicáveis** já no load, sem abrir o menu de filtros. É o que faz o filtro **aparecer** na tela — sem isso o usuário não vê a afordância e acaba pedindo select na unha (⛔ **proibido** montar form/select acima da tabela — ver `.claude/rules/ds-components.md`). Status/segmento como eixo de navegação (poucos valores) → alternativa: **uma visão por valor** em `defaultViews` (ver item de visões abaixo). Regra de ouro: se a informação está numa coluna, **chip nativo primeiro**.
47
+
48
+ **Formato de data.** `type: "date"` renderiza `14/03/2023` e `type: "datetime"` renderiza `14/03/2023 09:30` — **com ano** (lib 0.43.0+). Precisa de outro formato (mês escrito, relativo, ISO)? Passe **`valueFormatter`** na coluna: ele vence o formato do tipo e vale na célula, no export e no clipboard. **NÃO** escreva `render` próprio só pra formatar data. ⚠️ Até a 0.42.1 esses tipos mostravam a data **sem ano** e o `valueFormatter` não chegava na célula — se você viu `render` de data em código antigo, era contorno disso.
49
+
50
+
51
+ ### Padrões de CÉLULA (consistência finance — OBRIGATÓRIO)
52
+
53
+ Espelhar `finance-screen.tsx` (puxe `example-finance`). **Componente do DS sempre antes de markup manual**:
54
+
55
+ - **Coluna primária (nome)**: `isPrimary` + `render` com `<Avatar size="md">` + nome `text-body-sm font-medium` + secundária `text-caption-md text-fg-muted` (email/ID/doc) + ícone "abrir detalhe" (`<SquareArrowOutUpRight>` num `size-[24px] rounded-radius-sm border bg-bg-canvas shadow-sh-sm`) quando o row click abre painel.
56
+ - **Status / badge**: `type: "badge"` + `render` com `<Chip variant="soft" size="sm" shape="pill">` (cor semântica). Nunca pill na unha com `<span>` estilizado.
57
+ - **Avatar**: use **`avatar-ig`** (`@/components/ui/avatar-ig`), não o `avatar` (Radix puro, sem `colorHex`/`size`). `size="md"` na tabela (não `sm`). **Números/moeda/%**: `tabular-nums` + `type` (`currency`/`percentage`) + `align: "right"`. **Tags**: `type: "tags"` + `<Chip soft sm rounded>`. **Código/identificador/valor técnico** (chave de env, ID, hash, slug, path): preset **`text-code-sm`** — nunca `font-mono text-body-sm` + `tracking-*` na unha.
58
+
59
+ ### Detail panel (row click → painel)
60
+
61
+ **Cite o bloco `dsgreen-paneldetail-1`** — a estrutura inteira já está resolvida e
62
+ referenciável por ID (`npm run igreen:add -- dsgreen-paneldetail-1`, ou peça
63
+ *"use a referência dsgreen-paneldetail-1"*).
64
+
65
+ A referência anterior era "espelhe o `FinanceDetailPanel`", e ela funciona — o
66
+ `example-finance` distribui esse arquivo. O bloco é melhor por dois motivos, não porque o
67
+ outro esteja quebrado: **não exige puxar uma tela inteira** só pra ver um painel, e o arquivo
68
+ dele traz **o porquê de cada decisão** (com as medições) em vez de só o resultado.
69
+
70
+ **Sempre** `<FloatingPanel>`, nunca markup solto. O que o bloco carrega:
71
+
72
+ - `titleSlot`: `<Avatar size="lg">` + nome (`text-body-md font-semibold`) + linha
73
+ `código · <Chip status>`. ⚠️ Se você usar `Panel` em vez de `FloatingPanel`, esse header é
74
+ impossível: lá `title`/`description` são **string**.
75
+ - `headerActions`: 1–2 ações de ícone, **todas `variant="soft"`** (`secondary` neutro,
76
+ `success` contato, `critical` destrutivo). `ghost` no meio da fileira fica sem container e lê
77
+ como desabilitada ao lado do maximize/close, que o componente renderiza como `soft`.
78
+ `aria-label` obrigatório — botão de ícone não tem texto.
79
+ - `bodyPadded={false}` + **agrupar por assunto** em `<FloatingPanelSection title>`.
80
+ - 1ª seção = **métricas do registro**, em cards compactos (ícone + valor 18px + rótulo), 2 por
81
+ linha. ⛔ **Não use `Kpi`**: ele é card de dashboard (144px de altura por célula) e come a
82
+ primeira dobra do painel antes de qualquer campo.
83
+ - Cada dado simples = **uma linha** `<FloatingPanelField label value/>`.
84
+ - Dado que **não é** `label: valor` sai do Field: entidade com marca (banco, gestor) vira linha
85
+ de largura cheia com `Avatar`; vários valores viram `<Chip>`; e-mail/telefone viram
86
+ `mailto:`/`tel:` com cor de link.
87
+ - `footer`: Fechar + ação primária.
88
+ - ⛔ **Sem aba.** Se o corpo já é pilha de seções colapsáveis, o colapso **é** o mecanismo de
89
+ esconder — ter os dois faz o usuário procurar o dado em dois lugares.
90
+
91
+ - **Tabela + Lista (toggle)**: se o usuário quer alternar entre tabela e uma **lista de cards** (não kanban), use `viewMode` + `listConfig={{ renderItem(row), paginated?, hierarchical?, getPath?, getMenuItems? }}` no próprio `<DataTable>` — mesma toolbar, toggle Tabela/Lista automático. NÃO monte um `<DataList>` paralelo + toggle na mão.
92
+ - **Lista flat paginada**: `listConfig.paginated: true` — a lista usa a MESMA paginação da tabela + mostra o footer. Default `false` (mostra todas, sem footer); ignorado em `hierarchical`. Use quando a lista flat puder ter muitas linhas.
93
+ - ⛔ **No MÁXIMO 2 presets, e NUNCA um preset "Todos"/"Todas"**: `maxTabs` default é 3 e a aba **Default** (nativa, que já É a visão sem filtro) consome 1 slot — sobram 2. O excedente é cortado por `.slice(0, maxTabs - 1)` — em DEV o componente avisa no console qual visão foi engolida (v0.43.1), em produção não. Precisa de mais? `maxViewTabs={N + 1}` no `<DataTable>` (o `+1` é a Default) — mas 2 é o default por um motivo: barra de visões não é menu. Um preset "Todos" duplica a Default e gasta um slot com nada.
94
+ - **Visões pré-definidas read-only (`allowCreateView={false}`, v0.23.0+)**: passe `defaultViews={[presetView({ id, name, filters?, sort?, viewMode? })]}` + `persistId` pras abas nativas da tela. `allowCreateView={false}` esconde o botão "+" (o usuário não salva visões próprias — só usa as suas). Default `true`. **viewMode "sticky"**: trocar de visão só muda Tabela↔Lista↔Kanban se o preset declarar `viewMode` explícito; sem isso, mantém a view que o usuário está vendo (só declare `viewMode` no preset que DEVE forçar uma view).
95
+ - Lista árvore **+ tabela árvore**: `hierarchical` + `getTreeDataPath` (tabela não pagina).
96
+ - **Tabela FLAT paginada + lista em ÁRVORE**: `hierarchical` + **`listConfig.getPath`** e NÃO passe `getTreeDataPath` (senão a tabela vira tree-data e perde paginação).
97
+ - Drawers de criar/editar: espelhe `NovoClienteDrawer` (Panel + FormField + `gap-form-gap`), ligados via estado da página (igual ao `finance-screen.tsx`).
98
+ - Tokens/spacing/typography conforme `.claude/rules/ds-design.md` + `DESIGN.md`.
99
+
100
+ ## 4. Registrar a rota
101
+
102
+ No ponto que o usuário indicou (router / App). Página órfã = incompleto.
103
+
104
+ ## 5. Validar
105
+
106
+ ```bash
107
+ npx tsc --noEmit # abort se falhar — corrija antes do handoff
108
+ ```
109
+
110
+ ## 6. Handoff
111
+
112
+ `CRUD_PRONTO: <Entidade>` + onde foi registrada + como rodar (`npm run dev`).
113
+ Sugira ao usuário abrir a tela e conferir; ofereça ajustes finos (larguras de coluna, filtros).
@@ -0,0 +1,89 @@
1
+ > **Nota de portabilidade.** Este roteiro foi extraído do pipeline do iGreen DS
2
+ > para Claude Code. Menções a slash command (`/ds-create-…`), a `.claude/` e a
3
+ > ferramentas daquele ambiente descrevem **como ele é acionado lá** — aqui o
4
+ > equivalente é carregar este roteiro pelo `indice.json`. O conteúdo de decisão
5
+ > (entrevista, blueprint, regras de composição) vale igual.
6
+
7
+
8
+ # CRUD Builder (consumidor) — Router
9
+
10
+ Você guia a criação de uma tela de tabela que consome `<DataTable>` **sem fugir
11
+ do exemplo e da documentação do projeto**. NÃO inventa API de props, NÃO gera
12
+ código de memória, NÃO toca em arquivo antes do gate aprovado.
13
+
14
+ > **Kanban / board / funil / pipeline de vendas** caem AQUI: kanban é uma `viewMode`
15
+ > do DataTable (mesmos dados/colunas/filtros, só muda a exibição). "Quero um kanban/
16
+ > funil" → esta skill; a Fase 6 do interview configura as lanes pela coluna de
17
+ > status/etapa. Funil = board agrupado por etapa. Ref. visual: `example-finance`.
18
+
19
+ ## Ambiente (este é um projeto CONSUMIDOR, copy-in)
20
+
21
+ | Variável | Valor |
22
+ | ------------------------ | --------------------------------------------------------------------------------------------------------------- |
23
+ | `IMPORT_PATH` | `@/components/ui/DataTable`, `@/components/ui/Button`, etc (copy-in via alias) |
24
+ | `EXEMPLO_CANÔNICO` | `example-clientes` → `npm run igreen:add -- example-clientes` → ler `src/examples/clientes/clientes-screen.tsx` |
25
+ | `DOC` | `src/components/ui/DataTable/USAGE.md` (após `igreen:add data-table`) + types ao lado |
26
+ | `PAGES_DIR` / `REGISTRO` | perguntar ao usuário (onde mora a página + como registra rota) |
27
+
28
+ Se o componente/exemplo ainda não está no disco, **puxe via `igreen:add`** antes de ler — nunca gere de memória.
29
+
30
+ > **Modo submódulo (ds-link).** Se existe `.claude/ds-config.json` com `"mode": "submodule"`,
31
+ > o DS é consumido como **submódulo** (não copy-in): os componentes/exemplos JÁ estão no disco
32
+ > em `<dsPath>/src` e **não** há registry. Use `importBase` do config (ex.: `@ds/components/ui/<Nome>`)
33
+ > e leia o exemplo canônico direto em `<dsPath>/src/examples/clientes/clientes-screen.tsx` —
34
+ > **NÃO** rode `igreen:add`. `PAGES_DIR`/`REGISTRO` continuam do projeto pai.
35
+
36
+ ## Fluxo — 3 estágios
37
+
38
+ ```
39
+ /ds-create-crud
40
+ ▼ interview.md
41
+ 1. ENTREVISTA (fases 0-6) — acumula escolhas, ZERO edição em disco
42
+ ▼ blueprint.md
43
+ 2. BLUEPRINT [GATE] — preview consolidado + pré-validações → aguarda "aprovar"
44
+ ▼ generate.md
45
+ 3. GERAÇÃO — igreen:add → ler exemplo → criar página → registrar → tsc → handoff
46
+ ```
47
+
48
+ Carregue cada sub-arquivo só no estágio correspondente: `interview.md` agora, `blueprint.md` ao fim da entrevista, `generate.md` só após o gate.
49
+
50
+ ## ⚠️ Precedência de fontes (anti-drift)
51
+
52
+ ```
53
+ 1. src/examples/clientes/clientes-screen.tsx (exemplo real, vence tudo)
54
+ 2. src/components/ui/DataTable/USAGE.md + types ao lado
55
+ 3. Snippets desta skill
56
+ 4. Memória da IA ← NUNCA confiar sozinha
57
+ ```
58
+
59
+ Se USAGE.md divergir do exemplo/types, o exemplo + types vencem.
60
+
61
+ ## Guardrails (não-negociáveis)
62
+
63
+ 1. `columns` SEMPRE em `useMemo`; `fetchData` (server mode) SEMPRE em `useCallback` (senão loop de refetch).
64
+ 2. Operador de filtro válido pro filterType (multiSelect⇒`isAnyOf`, text⇒`contains`, date⇒`between`...).
65
+ 3. `virtualize: true` ⇒ paginação desligada + container com altura (`flex-1 min-h-0` num pai `h-full`).
66
+ 4. `groupBy`/kanban ativo ⇒ paginação desligada (avisar).
67
+ 5. Forms em drawers/modais usam `<FormField>` (nunca `<label>` cru) + `gap-form-gap`.
68
+ 6. Classes DS antes de Tailwind literal; zero hardcode de cor/tamanho (ver `.claude/rules/ds-design.md`).
69
+ 7. Wrapper da tela: `flex flex-col h-full min-h-0 gap-gp-2xl` (PageHeader → 16px → tabela). Ver `DESIGN.md`.
70
+ 8. Página registrada no roteador do usuário — página órfã = tarefa incompleta.
71
+ 9. `npx tsc --noEmit` limpo antes do handoff (abort-on-error).
72
+ 10. LER o exemplo canônico ANTES de gerar — nunca de memória.
73
+ 11. Ação destrutiva (excluir) ⇒ **confirmação via `AlertModal`** — nunca deletar direto.
74
+ 12. Sempre wire os 3 estados: `loading`/`renderLoading` (skeleton), `renderEmpty` (sem
75
+ registros + CTA _Adicionar_), `renderNoResults` (filtro sem match). **O default
76
+ embutido conta como wirado — desde que declarado no blueprint** (linha `Estados:`).
77
+ Faltou = incompleto: o que não vale é o estado nunca ter sido decidido.
78
+
79
+ ## Drawers (criar/editar/detalhe) — ligado ao CRUD
80
+
81
+ Se o CRUD precisa de criar/editar/ver-detalhe, espelhe o padrão do `example-finance`:
82
+ `NovoClienteDrawer` (criar/editar via `Panel` + `FormField`) e `FinanceDetailPanel`
83
+ (detalhe via `FloatingPanel`). Puxe `example-finance`, leia esses componentes e
84
+ reuse a estrutura — mesmo design de drawer do DS.
85
+
86
+ ## Handoff
87
+
88
+ - Entrevista pronta → `BLUEPRINT_PRONTO: <Entidade> — aguardando gate`
89
+ - Pós-geração → `CRUD_PRONTO: <Entidade>` (+ onde foi registrada)
@@ -0,0 +1,47 @@
1
+ > **Nota de portabilidade.** Este roteiro foi extraído do pipeline do iGreen DS
2
+ > para Claude Code. Menções a slash command (`/ds-create-…`), a `.claude/` e a
3
+ > ferramentas daquele ambiente descrevem **como ele é acionado lá** — aqui o
4
+ > equivalente é carregar este roteiro pelo `indice.json`. O conteúdo de decisão
5
+ > (entrevista, blueprint, regras de composição) vale igual.
6
+
7
+ > **Modo submódulo (`ds-link`).** Existe `.claude/ds-config.json` com `"mode": "submodule"`?
8
+ > Então **NÃO rode `igreen:add`** — esse script não existe no seu projeto. Os componentes e
9
+ > exemplos já estão no disco em `<dsPath>/src`: importe pelo `importBase` do config
10
+ > (compostos) e pelo `primitivesBase` (primitivos shadcn), e **leia** o exemplo direto de
11
+ > `<dsPath>/src/examples/`.
12
+
13
+ # Dashboard Builder (consumidor) — Blueprint + GATE
14
+
15
+ Consolide a entrevista num preview de uma tela só e **pare** — ⛔ zero edição antes do "aprovar".
16
+
17
+ ## Preview a apresentar
18
+
19
+ ```
20
+ PAINEL: <nome> · rota <definir com o usuário> · fonte: mock | API(<shape>)
21
+ Wrapper: AppShell + PageHeader | puro (chrome do print entregue? sim/não)
22
+
23
+ ⚠️ Inferido (não perguntei) — vete se discordar:
24
+ • <decisão> → <o que muda se vetar> [ou: nenhuma]
25
+
26
+ MAPA DE ROWS (top → bottom):
27
+ Row 1 — [hero/insight?] (opcional)
28
+ Row 2 — KPI-group "Painel do Líder" · N cols (§1) KPIs: <label · tom · delta(signed?)> …
29
+ Row 3 — <gráfico principal> (2/3) + <donut/resumo> (1/3) (§2)
30
+ Row 4 — <ranking / fusão KPI+evolução?> (§3)
31
+ Row 5 — <card dividido / mapa?> (§4)
32
+ Row 6 — <tabela | lista embutida?> (§5/§6 → delega crud/list-builder)
33
+
34
+ Primitivos (igreen:add): kpi · chart · panel · <data-table|data-list?> · example-dashboard (base)
35
+ ```
36
+
37
+ ## Pré-validações
38
+ - [ ] É mesmo dashboard (2+ tipos de seção)? Senão → rotear pro builder certo.
39
+ - [ ] Cada gráfico com tipo + séries; cabe no padrão (skill `charts`).
40
+ - [ ] KPI delta: `signed` só onde sinal = bom/ruim; senão tom explícito.
41
+ - [ ] Ícone: KPI-group = círculo; mini-stat/legenda = quadrado.
42
+ - [ ] Tabela/lista embutida delega a crud/list-builder; distribuição correta.
43
+ - [ ] Layout estreito não coloca cards lado-a-lado apertados; zero hardcode.
44
+
45
+ ## Gate
46
+ Apresentar mapa de rows + pré-validações numa tela só. Aguardar `aprovar` → `generate.md`;
47
+ `ajustar X` → re-montar; `cancelar` → abortar (zero edits). **Não tocar em arquivo antes do aprovar.**
@@ -0,0 +1,62 @@
1
+ > **Nota de portabilidade.** Este roteiro foi extraído do pipeline do iGreen DS
2
+ > para Claude Code. Menções a slash command (`/ds-create-…`), a `.claude/` e a
3
+ > ferramentas daquele ambiente descrevem **como ele é acionado lá** — aqui o
4
+ > equivalente é carregar este roteiro pelo `indice.json`. O conteúdo de decisão
5
+ > (entrevista, blueprint, regras de composição) vale igual.
6
+
7
+ > **Modo submódulo (`ds-link`).** Existe `.claude/ds-config.json` com `"mode": "submodule"`?
8
+ > Então **NÃO rode `igreen:add`** — esse script não existe no seu projeto. Os componentes e
9
+ > exemplos já estão no disco em `<dsPath>/src`: importe pelo `importBase` do config
10
+ > (compostos) e pelo `primitivesBase` (primitivos shadcn), e **leia** o exemplo direto de
11
+ > `<dsPath>/src/examples/`.
12
+
13
+ # Dashboard Builder (consumidor) — Entrevista (fases 0–6)
14
+
15
+ Uma pergunta (ou grupo curto) por vez. Acumule as escolhas — **ZERO edição em disco**
16
+ até o gate. Use `AskUserQuestion` pra escolhas fechadas; proponha um default sensato.
17
+ As receitas de cada seção estão no `generate.md` (§1–§6) + no `example-dashboard`.
18
+
19
+ ## Fase 0 — Intent + fonte
20
+ - Do que é o painel? (visão geral de quê, pra quem — ex.: painel do líder, resumo de
21
+ categoria, financeiro consolidado).
22
+ - Dados: mock ou API? Se API, anote o shape → a geração cria mock tipado espelhando.
23
+ - Período/segmentação no topo? (quase sempre → PeriodSelector no `actions` do PageHeader).
24
+
25
+ - **Envelope (wrapper)** — verifique antes de perguntar: existe `AppShell`? A referência
26
+ mostra rail/menu/header? Chrome sem shell → ofereça `/ds-create-app` junto; recusado →
27
+ registre no blueprint o que do print fica de fora.
28
+
29
+ ## Fase 1 — KPIs rápidos ("Painel do Líder", §1)
30
+ - Quais métricas rápidas? (label + valor + tom do ícone).
31
+ - Delta? O sinal é literalmente bom/ruim → `signed`. Senão, tom explícito (tempo ↓ = success).
32
+ - Quantas colunas (4–6)? → `<KpiGroup columns={N} divided>`.
33
+
34
+ ## Fase 2 — Gráficos (chart-cards, §2)
35
+ - Quais gráficos? Tipo (barras/linha/área/pizza-donut), séries, o que comparam (ver skill `charts`).
36
+ - Cada um num SectionCard (head título+subtítulo discreto). Big-number liderando? Legenda/metric-rows?
37
+ - Donut com total no centro? 2 séries → verde+âmbar; pizza → rampa da marca.
38
+
39
+ ## Fase 3 — Ranking / fusão KPI+evolução (§3)
40
+ - Ranking (reconhecimento, top do mês) ou linha de lista rica que funde identidade +
41
+ mini-KPIs em colunas + métrica headline com delta (ex.: cidades/licenciados por status)?
42
+ - Se sim: mini-KPIs (label+ícone+tom), métrica headline à direita (delta Chip), identificador (rank/nome/sub).
43
+
44
+ ## Fase 4 — Card dividido em 2 / mapa (§4)
45
+ - Seção que junta dados + visual lado a lado (ex.: barras por UF | mapa)? → card dividido (divisor no 2º painel).
46
+ - Precisa de mapa? (SVG por região/UF + legenda). Anote regiões/UFs.
47
+
48
+ ## Fase 5 — Tabela / lista embutida (delega)
49
+ - Termina com tabela (grade) ou lista (cards) de detalhe?
50
+ - Tabela → geração delega a distribuição de colunas ao `crud-builder` (identidade → status →
51
+ categóricos → muted → moeda/data à direita; filtros nativos pré-aplicados).
52
+ - Lista/kanban → delega ao `list-builder` (linha1 título+secundário, linha2 meta, status chip,
53
+ valor à direita; sem botão de ação).
54
+ - Nenhuma → pula.
55
+
56
+ ## Fase 6 — Layout das rows
57
+ - Ordem/agrupamento. Padrão: (1) hero/insight opcional · (2) KPI-group "Painel do Líder" faixa larga ·
58
+ (3) gráfico principal (2/3) + donut/resumo (1/3) · (4) qualidade/ranking/fusão · (5) listas/tabela.
59
+ - Estreito → 1 card/row + coluna única. Rows 2–3 col via `grid grid-cols-1 lg:grid-cols-{2,3} gap-gp-2xl items-stretch`.
60
+
61
+ ## Fim
62
+ Resumir em 1 frase + `BLUEPRINT_PRONTO: <Painel> (dashboard) — aguardando gate` → carregar `blueprint.md`.
@@ -0,0 +1,88 @@
1
+ > **Nota de portabilidade.** Este roteiro foi extraído do pipeline do iGreen DS
2
+ > para Claude Code. Menções a slash command (`/ds-create-…`), a `.claude/` e a
3
+ > ferramentas daquele ambiente descrevem **como ele é acionado lá** — aqui o
4
+ > equivalente é carregar este roteiro pelo `indice.json`. O conteúdo de decisão
5
+ > (entrevista, blueprint, regras de composição) vale igual.
6
+
7
+ > **Modo submódulo (`ds-link`).** Existe `.claude/ds-config.json` com `"mode": "submodule"`?
8
+ > Então **NÃO rode `igreen:add`** — esse script não existe no seu projeto. Os componentes e
9
+ > exemplos já estão no disco em `<dsPath>/src`: importe pelo `importBase` do config
10
+ > (compostos) e pelo `primitivesBase` (primitivos shadcn), e **leia** o exemplo direto de
11
+ > `<dsPath>/src/examples/`.
12
+
13
+ # Dashboard Builder (consumidor) — Geração
14
+
15
+ Só após o gate aprovado. Abort-on-error.
16
+
17
+ ## 1. Puxar + ler ANTES de montar (nunca de memória)
18
+
19
+ ```bash
20
+ npm run igreen:add -- example-dashboard kpi chart panel
21
+ # + data-table (se tabela embutida) / data-list (se lista embutida)
22
+ ```
23
+ Ler `src/examples/dashboard/dashboard-screen.tsx` (referência runnable) + `Kpi/USAGE.md`
24
+ + `Chart/USAGE.md`. Catálogo visual: **https://igreen-desingsystem-admin.vercel.app** (`#/dashboard-showcase`).
25
+ **Prefira adaptar o example-dashboard** a montar do zero.
26
+
27
+ ## 2. Receitas canônicas (as 6 — resumo; o example-dashboard tem o código completo)
28
+
29
+ **Shell**: `<div className="flex flex-col h-full min-h-0 gap-gp-2xl">` + `PageHeader`
30
+ (actions = PeriodSelector) + rows.
31
+
32
+ **§1 KPI-group "Painel do Líder"** (faixa de KPIs rápidos):
33
+ ```tsx
34
+ <KpiGroup columns={N} divided>
35
+ <Kpi label="..." value="..." icon={<Icon />} tone="success|brand|info|warning|danger|neutral"
36
+ hint="..." delta={<KpiDelta value="+34" signed />} />
37
+ </KpiGroup>
38
+ ```
39
+ Tone colore SÓ o ícone (círculo `size-form-lg rounded-radius-full`); valor default (só KPI de
40
+ alerta ganha cor). `signed` deriva verde/vermelho + seta do sinal; use tom explícito quando
41
+ "subir" não é bom (tempo ↓ = success).
42
+
43
+ **§2 Chart-card**: SectionCard (`flex flex-col gap-gp-2xl p-pad-3xl bg-bg-surface border
44
+ border-border-subtle rounded-radius-xl shadow-sh-sm`) com head discreto (título `text-body-md
45
+ font-medium`, subtítulo `text-body-xs text-fg-muted`, gap `gap-gp-2xs` (2px)) + `<ChartContainer
46
+ className="h-[160px]">`. Cor só por token. Big-number liderando: `text-stat-lg
47
+ leading-none tabular-nums` (30px/bold — o preset existe; NÃO hardcode `text-[30px]`). Legenda/metric-row: ícone-**quadrado** `size-comp-xl rounded-radius-base`
48
+ + label/sub + valor à direita, sob `border-t border-border-subtle`.
49
+
50
+ **§3 Fusão KPI+evolução / ranking** (linha rica): identidade (rank badge `size-comp-sm
51
+ rounded-radius-full` + nome) · mini-KPIs em colunas (`hidden sm:flex gap-gp-6xl`, cada = quadrado
52
+ `size-comp-lg rounded-radius-base` tonal + valor `text-body-md font-semibold tabular-nums` +
53
+ label `text-caption-sm text-fg-muted`) · bloco headline à direita `ml-auto shrink-0 border-l
54
+ border-border-subtle pl-gp-3xl` (valor `text-title-lg font-bold` + delta Chip `shape="rounded"`,
55
+ seta 180° se negativo + micro-label `uppercase tracking-[0.04em]`).
56
+
57
+ **§4 Card dividido em 2**: 1 surface SEM padding + `grid lg:grid-cols-2`; cada painel `p-pad-3xl`
58
+ com ColHead; divisor no **2º painel**: `border-t border-border-subtle ... lg:border-l lg:border-t-0`.
59
+
60
+ **§5 Tabela embutida** → delega ao `crud-builder`: ordem identidade → status → categóricos →
61
+ muted → moeda/data à direita (`align:"right" tabular-nums`); primário `isPrimary`+`minWidth`+
62
+ `font-medium`; status `Chip variant="soft" size="sm" shape="rounded"`; filtros nativos
63
+ pré-aplicados (`defaultViews`/`presetView`), sem form solto acima.
64
+
65
+ **§6 Lista/kanban embutida** → delega ao `list-builder`: linha1 título bold `body-md` + `·`
66
+ secundário muted · linha2 meta muted `caption-md` (lugar · pessoa · data) · status Chip soft pill ·
67
+ valor à direita fixo `font-semibold tabular-nums`. **Sem botão de ação na linha.**
68
+
69
+ ## 3. Registro
70
+ Registrar a página no roteador do app (perguntar ao usuário onde/como). Página órfã = incompleto.
71
+
72
+ ## 4. Sequência (abort-on-error)
73
+ 1. `igreen:add` dos itens + ler o example-dashboard.
74
+ 2. Montar seção por seção (as § acima; adaptar o exemplo).
75
+ 3. Registrar rota.
76
+ 4. `npx tsc --noEmit` → erro: corrigir e repetir.
77
+ 5. (recomendado) rodar o app e conferir: KPI-group divided, gráficos com token, ranking com
78
+ `border-l`, card dividido, tabela/lista embutida, responsivo + dark.
79
+
80
+ ## 5. Checklist final
81
+ - [ ] Compõe 2+ tipos de seção espelhando o example-dashboard
82
+ - [ ] KPI-group divided + KpiDelta (signed só onde cabe); ícone círculo vs quadrado certo
83
+ - [ ] Gráficos só com token; tabela/lista via crud/list-builder
84
+ - [ ] Zero Tailwind literal com equivalente DS · zero hardcode
85
+ - [ ] Registro completo · `npx tsc --noEmit` limpo
86
+
87
+ ## Handoff
88
+ `DASHBOARD_PRONTO: <Painel>` (+ onde foi registrada)
@@ -0,0 +1,88 @@
1
+ > **Nota de portabilidade.** Este roteiro foi extraído do pipeline do iGreen DS
2
+ > para Claude Code. Menções a slash command (`/ds-create-…`), a `.claude/` e a
3
+ > ferramentas daquele ambiente descrevem **como ele é acionado lá** — aqui o
4
+ > equivalente é carregar este roteiro pelo `indice.json`. O conteúdo de decisão
5
+ > (entrevista, blueprint, regras de composição) vale igual.
6
+
7
+
8
+ # Dashboard Builder (consumidor) — Router
9
+
10
+ Você guia a criação de uma tela de **dashboard/painel** que **compõe** os primitivos
11
+ do DS (`Kpi`/`KpiGroup`/`KpiDelta`, `Chart`, `Panel`, `DataTable`, `DataList`) nos
12
+ **padrões canônicos**. NÃO inventa API, NÃO gera de memória, NÃO toca em arquivo
13
+ antes do gate.
14
+
15
+ > Irmão do `crud-builder` (tabela) e do `list-builder` (lista). Dashboard não é um
16
+ > componente — é **composição** de seções. Uma tabela/lista DENTRO do dashboard é
17
+ > delegada ao crud/list-builder.
18
+
19
+ ## ⚠️ Desambiguação ANTES de tudo
20
+
21
+ | Dashboard (ESTA skill) | Não é dashboard |
22
+ |---|---|
23
+ | **compõe** 2+ tipos de seção: KPIs + gráfico(s) + ranking/resumo numa "visão geral" | 1 tabela densa → `crud-builder` |
24
+ | foco em métrica/tendência/comparação, pouca edição | 1 lista de cards standalone → `list-builder` |
25
+ | ex: painel do líder, resumo de categoria, visão da rede | 1 gráfico isolado → skill `charts` |
26
+
27
+ Só 1 grade/lista/gráfico → **PARAR** e rotear pro builder certo.
28
+
29
+ ## Ambiente (projeto CONSUMIDOR, copy-in)
30
+
31
+ | Variável | Valor |
32
+ | --- | --- |
33
+ | `IMPORT_PATH` | `@/components/ui/Kpi`, `@/components/ui/Chart`, `@/components/ui/Panel`, etc (copy-in via alias) |
34
+ | `EXEMPLO_CANÔNICO` | `example-dashboard` → `npm run igreen:add -- example-dashboard` → ler `src/examples/dashboard/dashboard-screen.tsx` |
35
+ | `DOC` | `src/components/ui/Kpi/USAGE.md` + `Chart/USAGE.md` (após `igreen:add`) + types ao lado; catálogo visual hospedado `#/dashboard-showcase` |
36
+ | `PAGES_DIR` / `REGISTRO` | perguntar ao usuário (onde mora a página + como registra rota) |
37
+
38
+ Se o componente/exemplo não está no disco, **puxe via `igreen:add`** antes de ler.
39
+
40
+ > **Modo submódulo (ds-link).** Se existe `.claude/ds-config.json` com `"mode": "submodule"`,
41
+ > o DS é consumido como **submódulo** (não copy-in): os componentes/exemplos JÁ estão no disco
42
+ > em `<dsPath>/src` e **não** há registry. Use `importBase` do config (ex.: `@ds/components/ui/<Nome>`)
43
+ > e leia o exemplo canônico direto em `<dsPath>/src/examples/dashboard/dashboard-screen.tsx` —
44
+ > **NÃO** rode `igreen:add`. `PAGES_DIR`/`REGISTRO` continuam do projeto pai.
45
+
46
+ ## Fluxo — 3 estágios
47
+
48
+ ```
49
+ /ds-create-dashboard
50
+ ▼ interview.md
51
+ 1. ENTREVISTA (fases 0-6) — KPIs → gráficos → ranking/fusão → dividido/mapa → tabela/lista → layout; ZERO edição
52
+ ▼ blueprint.md
53
+ 2. BLUEPRINT [GATE] — mapa de rows + pré-validações → aguarda "aprovar"
54
+ ▼ generate.md
55
+ 3. GERAÇÃO — igreen:add example-dashboard → ler → montar → registrar → tsc → handoff
56
+ ```
57
+
58
+ Carregue cada sub-arquivo só no estágio: `interview.md` agora, `blueprint.md` ao fim
59
+ da entrevista, `generate.md` só após o gate.
60
+
61
+ ## ⚠️ Precedência de fontes (anti-drift)
62
+
63
+ ```
64
+ 1. src/examples/dashboard/dashboard-screen.tsx (exemplo real — vence tudo)
65
+ 2. src/components/ui/Kpi/USAGE.md + Chart/USAGE.md + types ao lado
66
+ 3. Snippets/receitas desta skill (generate.md)
67
+ 4. Memória da IA ← NUNCA confiar sozinha
68
+ ```
69
+
70
+ ## Guardrails (não-negociáveis)
71
+
72
+ 1. LER `example-dashboard` ANTES de montar — nunca de memória.
73
+ 2. **KPI rápido = "Painel do Líder"**: `<KpiGroup divided>` + `<Kpi>` + `<KpiDelta>`.
74
+ Tone colore SÓ o ícone (círculo); valor default (só KPI de alerta ganha cor).
75
+ Delta: `signed` só quando sinal = bom/ruim; senão `tone` explícito ("-12s" é melhora → success).
76
+ 3. Gráfico = SEMPRE `<ChartContainer>`, cor só por token (`--color-chart-1..5`); ver skill `charts`.
77
+ 4. Ranking/fusão + card dividido: divisor via `border-l`/`border-t` (nunca só gap);
78
+ ícone mini-stat = **quadrado** `size-comp-lg rounded-radius-base`, KPI-group = **círculo** `size-form-lg rounded-radius-full`.
79
+ 5. Tabela/lista embutida → delegar a `crud-builder`/`list-builder`; filtros nativos pré-aplicados, sem form solto acima.
80
+ 6. Classes DS antes de Tailwind literal; zero hardcode (ver `.claude/rules/ds-design.md`, `DESIGN.md`). Números grandes literais só onde não há preset.
81
+ 7. Shell: `flex flex-col h-full min-h-0 gap-gp-2xl` (PageHeader → 16px → rows). Estreito → 1 card/row.
82
+ 8. Página registrada no roteador do usuário — órfã = incompleto.
83
+ 9. `npx tsc --noEmit` limpo antes do handoff.
84
+
85
+ ## Handoff
86
+
87
+ - Entrevista pronta → `BLUEPRINT_PRONTO: <Painel> (dashboard) — aguardando gate`
88
+ - Pós-geração → `DASHBOARD_PRONTO: <Painel>` (+ onde foi registrada)
@@ -0,0 +1,41 @@
1
+ > **Nota de portabilidade.** Este roteiro foi extraído do pipeline do iGreen DS
2
+ > para Claude Code. Menções a slash command (`/ds-create-…`), a `.claude/` e a
3
+ > ferramentas daquele ambiente descrevem **como ele é acionado lá** — aqui o
4
+ > equivalente é carregar este roteiro pelo `indice.json`. O conteúdo de decisão
5
+ > (entrevista, blueprint, regras de composição) vale igual.
6
+
7
+
8
+ # drawers — Criar / Editar / Detalhe
9
+
10
+ Padrão de drawer do DS, ligado ao CRUD/detalhe. Três variantes, mesma família visual.
11
+
12
+ ## Fluxo
13
+ 1. `npm run igreen:add -- example-finance` (traz os drawers + `Panel`, `FloatingPanel`, `FormField`).
14
+ 2. **Leia** os componentes-modelo:
15
+ - Criar/editar → `src/examples/finance/components/NovoClienteDrawer` e `.../EditarFinanceDrawer` (base: `Panel` + `FormField`).
16
+ - Ver detalhe → `src/examples/finance/components/FinanceDetailPanel` (base: `FloatingPanel`, não-modal).
17
+ 3. Adapte os campos/conteúdo ao caso. Ligue ao estado da página (igual `finance-screen.tsx`: `open`/`onOpenChange` + registro selecionado).
18
+
19
+ > **Modo submódulo (ds-link).** Se existe `.claude/ds-config.json` com `"mode": "submodule"`,
20
+ > o DS é consumido como **submódulo** (não copy-in): os componentes/exemplos JÁ estão no disco
21
+ > em `<dsPath>/src` e **não** há registry. Use `importBase` do config (ex.: `@ds/components/ui/Panel`)
22
+ > e leia os drawers-modelo direto em `<dsPath>/src/examples/finance/components/` —
23
+ > **NÃO** rode `igreen:add`.
24
+
25
+ ## Gotchas do tipo
26
+ - **Criar/Editar** = `Panel` (drawer modal lateral) com form em `<FormField>` + `gap-form-gap`. Footer sticky com Cancelar/Salvar.
27
+ - **Detalhe** = `FloatingPanel` (não-modal, não bloqueia a página; pode coexistir com a tabela). `shadow-sh-aside`.
28
+ - Largura: `Panel` default é `size="md"` = **560px**. O token `max-w-drawer-md` (480px) é outra coisa — não confunda. Mobile (<1024px): vira Sheet full.
29
+ - Nunca `<label>` cru; nunca `<button onClick>` como "card de seleção" (use label/FormField nativo).
30
+ - Abrir detalhe no click da linha (`onRowClick`); abrir editar via ação da linha.
31
+
32
+ Aplique `DESIGN.md` + regras. Handoff: `DRAWER_PRONTO: <criar|editar|detalhe> de <Entidade>`.
33
+
34
+ ## Aba dentro do drawer/painel
35
+
36
+ `<Tabs fullWidth>` com a variante **default** (`segmented`) — nunca `line`. Estas superfícies
37
+ são estreitas por construção (`Panel` 560px, `FloatingPanel` 320–720 e **redimensionável**),
38
+ e ali o `line` vira um trilho curto que lê como fragmento. Sem `fullWidth` as abas ficam num
39
+ canto. ⛔ Não escreva `w-full` no `TabsList` nem `flex-1` nos triggers: a prop faz as três
40
+ camadas (root + list + triggers), e `w-full` só no list estica o container e agrupa as abas
41
+ na esquerda.
@@ -0,0 +1,94 @@
1
+ > **Nota de portabilidade.** Este roteiro foi extraído do pipeline do iGreen DS
2
+ > para Claude Code. Menções a slash command (`/ds-create-…`), a `.claude/` e a
3
+ > ferramentas daquele ambiente descrevem **como ele é acionado lá** — aqui o
4
+ > equivalente é carregar este roteiro pelo `indice.json`. O conteúdo de decisão
5
+ > (entrevista, blueprint, regras de composição) vale igual.
6
+
7
+
8
+ > **Modo submódulo (`ds-link`).** Existe `.claude/ds-config.json` com `"mode": "submodule"`?
9
+ > Então **NÃO rode `igreen:add`** — esse script não existe no seu projeto. Os componentes e
10
+ > exemplos já estão no disco em `<dsPath>/src`: importe pelo `importBase` do config
11
+ > (compostos) e pelo `primitivesBase` (primitivos shadcn), e **leia** o exemplo direto de
12
+ > `<dsPath>/src/examples/`.
13
+
14
+ # List Builder — Blueprint [GATE]
15
+
16
+ ## Pré-validações automáticas (ANTES de exibir)
17
+
18
+ Corrigir silenciosamente (ou reportar se exigir decisão):
19
+
20
+ 1. **Excludências de escala** — `virtualized` + `enableDnD` → desligar DnD;
21
+ `virtualized` + `onLoadMore` → escolher um; `fillHeight` + `virtualized` →
22
+ `fillHeight` off. Anotar `← corrigido`.
23
+ 2. **branchHighlight** só com `layout="hierarchical"` — em outro layout, ignorar
24
+ e avisar.
25
+ 3. **Coerência de layout** — `grouped` tem `groups`; `hierarchical` tem itens com
26
+ `children` (ou `onLoadChildren`).
27
+ 4. **filterFields** — cada um tem `accessor`; `select` tem `options`. Operador de
28
+ view/filtro pré-aplicado válido pro `type` (multiSelect⇒`isAnyOf`,
29
+ select⇒`equals`, text⇒`contains`, number⇒`equals`, date⇒`between`,
30
+ boolean⇒`equals`).
31
+ 5. **Colisão de rota** — o id/rota proposto não pode já existir no router **deste
32
+ projeto**. Colisão → propor sufixo. (Onde ficam as rotas varia: React Router,
33
+ TanStack Router, file-based do Next… **pergunte** se não for óbvio pelo repo.)
34
+ 6. **Card** — `title` presente (slots) OU `renderItem` definido. Excluir
35
+ (destructive) tem `AlertModal` no plano (se houver form).
36
+
37
+ ## Formato do blueprint (apresentar TUDO de uma vez)
38
+
39
+ ```markdown
40
+ ## Blueprint — Lista <Entidade>
41
+
42
+ **Página**: <Título> · id `<page-id>` · wrapper <ExamplePageLayout|AppShell|puro> · nav "List Components"
43
+ **Dados**: <client|server> mode · fonte: <sample|interface|endpoint|manual> · ~<N> itens · id: `<campo>`
44
+
45
+ ### ⚠️ Decisões inferidas — vete se discordar
46
+
47
+ Só o que o usuário NÃO disse e você decidiu sozinho (wrapper, tema, tipo de campo com
48
+ confiança baixa…) — uma linha cada, com o que muda se ele vetar. Sem inferência →
49
+ `nenhuma`; não apague a seção: é a ausência dela que faz a decisão passar aprovada
50
+ em pacote junto com o resto.
51
+
52
+ ### Card (<slots|renderItem>)
53
+ - leading: <avatar/ícone|—> · title: `<campo>` · subtitle: `<campo|—>`
54
+ - meta: [<label:campo(align)>, ...] · trailing: <badge|—> · description: <campo|—>
55
+ - (ou renderItem custom: <descrição do card rico>)
56
+ - densidade <comfortable|compact> · menu por card [<Editar·Excluir>|—]
57
+
58
+ ### Layout
59
+ <standard | grouped (groups: <id(cor)>...; DnD <on|off>; surface <on|off>)
60
+ | hierarchical (branchHighlight <none|block|active>; expand inicial <...>; lazy <on|off>)>
61
+
62
+ ### Toolbar
63
+ título OU views[<abas>] · busca <on|off> · refresh <on|off> · moreActions [<...>]
64
+ filterFields: [<id:label:type>, ...]
65
+
66
+ ### Seleção / escala
67
+ selectable <on|off> + bulk [<actions>] · onItemClick <nada|detalhe|nav>
68
+ escala: <nenhuma | virtualized (estimate <N>) | infinite (onLoadMore/hasMore/loadingMore)>
69
+ fillHeight <on|off>
70
+
71
+ ### Estados
72
+ loading <skeletonCount> · vazio <emptyState msg/CTA>
73
+
74
+ ### Arquivos
75
+ - CRIAR <PAGES_DIR><Nome>.tsx (~<N> linhas)
76
+ - EDITAR <REGISTRO> (rota + entrada de navegação do SEU projeto — ver Fase 0)
77
+
78
+ ### Referências canônicas que serão lidas antes de gerar
79
+ <lista da matriz do generate.md, só os cenários presentes>
80
+
81
+ ⛔ Nenhum arquivo será tocado antes da aprovação.
82
+ Responda **aprovar** · **ajustar <o quê>** · **cancelar**.
83
+ ```
84
+
85
+ ## Protocolo do gate
86
+
87
+ - Enunciar a **Assumption** central junto do blueprint (ex.: "o sample é
88
+ representativo; `status` tem exatamente os N valores mapeados") — é o que torna a
89
+ decisão reversível depois. **Não** há audit log a preencher neste projeto.
90
+ - `aprovar` → carregar `generate.md` e executar.
91
+ - `ajustar X` → re-montar → re-apresentar (novo gate).
92
+ - `cancelar` → abortar; nota de cancelamento. Zero disco.
93
+
94
+ Sinal junto com o preview: `BLUEPRINT_PRONTO: <Entidade> (lista) — aguardando gate`