@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.
- package/dist-lib/ai/blocos/chart/budget-breakdown.tsx +174 -0
- package/dist-lib/ai/blocos/indice.md +43 -0
- package/dist-lib/ai/blocos/paneldetail/detalhe-com-tabela.tsx +450 -0
- package/dist-lib/ai/blocos/paneldetail/detalhe-de-tarefa-com-abas.tsx +570 -0
- package/dist-lib/ai/blocos/paneldetail/detalhe-do-registro.tsx +555 -0
- package/dist-lib/ai/componentes/AlertModal.md +47 -0
- package/dist-lib/ai/componentes/AppShell.md +117 -0
- package/dist-lib/ai/componentes/Breadcrumb.md +187 -0
- package/dist-lib/ai/componentes/Button.md +116 -0
- package/dist-lib/ai/componentes/ButtonGroup.md +162 -0
- package/dist-lib/ai/componentes/CardCheckbox.md +99 -0
- package/dist-lib/ai/componentes/CardOption.md +133 -0
- package/dist-lib/ai/componentes/Chart.md +93 -0
- package/dist-lib/ai/componentes/Chip.md +68 -0
- package/dist-lib/ai/componentes/ChoroplethMap.md +118 -0
- package/dist-lib/ai/componentes/ColorPicker.md +70 -0
- package/dist-lib/ai/componentes/Combobox.md +51 -0
- package/dist-lib/ai/componentes/ConversationListItem.md +90 -0
- package/dist-lib/ai/componentes/DataList.md +111 -0
- package/dist-lib/ai/componentes/DataTable.md +867 -0
- package/dist-lib/ai/componentes/DatePicker.md +84 -0
- package/dist-lib/ai/componentes/DateSeparatorChip.md +59 -0
- package/dist-lib/ai/componentes/EmptyState.md +72 -0
- package/dist-lib/ai/componentes/FileUploadField.md +95 -0
- package/dist-lib/ai/componentes/FloatingPanel.md +118 -0
- package/dist-lib/ai/componentes/FooterTable.md +62 -0
- package/dist-lib/ai/componentes/FormField.md +110 -0
- package/dist-lib/ai/componentes/Gantt.md +552 -0
- package/dist-lib/ai/componentes/Header.md +98 -0
- package/dist-lib/ai/componentes/Icon.md +65 -0
- package/dist-lib/ai/componentes/Kanban.md +343 -0
- package/dist-lib/ai/componentes/Kpi.md +103 -0
- package/dist-lib/ai/componentes/List.md +61 -0
- package/dist-lib/ai/componentes/MarkdownText.md +59 -0
- package/dist-lib/ai/componentes/MenuSidebar.md +128 -0
- package/dist-lib/ai/componentes/MessageAck.md +53 -0
- package/dist-lib/ai/componentes/MessageBubble.md +115 -0
- package/dist-lib/ai/componentes/MessageComposer.md +80 -0
- package/dist-lib/ai/componentes/MessageVariablesPicker.md +104 -0
- package/dist-lib/ai/componentes/Modal.md +88 -0
- package/dist-lib/ai/componentes/MonthYearPicker.md +49 -0
- package/dist-lib/ai/componentes/PageHeader.md +129 -0
- package/dist-lib/ai/componentes/Panel.md +84 -0
- package/dist-lib/ai/componentes/Scheduler.md +421 -0
- package/dist-lib/ai/componentes/ScreenLoader.md +60 -0
- package/dist-lib/ai/componentes/SingleMenuSidebar.md +171 -0
- package/dist-lib/ai/componentes/Spinner.md +52 -0
- package/dist-lib/ai/componentes/Table.md +192 -0
- package/dist-lib/ai/componentes/TableToolbar.md +87 -0
- package/dist-lib/ai/componentes/TabsNavigation.md +152 -0
- package/dist-lib/ai/componentes/Toast.md +49 -0
- package/dist-lib/ai/componentes/_primitivos.md +74 -0
- package/dist-lib/ai/componentes/avatar-ig.md +181 -0
- package/dist-lib/ai/componentes/indice.json +49 -0
- package/dist-lib/ai/exemplos/app-shell/app-shell-example.tsx +140 -0
- package/dist-lib/ai/exemplos/app-shell/index.ts +3 -0
- package/dist-lib/ai/exemplos/app-shell/nav-data.ts +97 -0
- package/dist-lib/ai/exemplos/app-shell/routes.tsx +75 -0
- package/dist-lib/ai/exemplos/chat/chat-screen.tsx +152 -0
- package/dist-lib/ai/exemplos/chat/chat-v2-mocks.ts +171 -0
- package/dist-lib/ai/exemplos/chat/chat-v2.styles.ts +23 -0
- package/dist-lib/ai/exemplos/chat/chat-v2.types.ts +81 -0
- package/dist-lib/ai/exemplos/chat/components/ChannelDot/channel-dot.tsx +28 -0
- package/dist-lib/ai/exemplos/chat/components/ConversationActionsMenu/conversation-actions-menu.tsx +83 -0
- package/dist-lib/ai/exemplos/chat/components/ConversationActionsMenu/index.ts +4 -0
- package/dist-lib/ai/exemplos/chat/components/ConversationColumn/conversation-column.styles.ts +22 -0
- package/dist-lib/ai/exemplos/chat/components/ConversationColumn/conversation-column.tsx +203 -0
- package/dist-lib/ai/exemplos/chat/components/ConversationColumn/conversation-column.types.ts +10 -0
- package/dist-lib/ai/exemplos/chat/components/ConversationColumn/index.ts +2 -0
- package/dist-lib/ai/exemplos/chat/components/ConversationListItem/conversation-list-item.styles.ts +55 -0
- package/dist-lib/ai/exemplos/chat/components/ConversationListItem/conversation-list-item.tsx +52 -0
- package/dist-lib/ai/exemplos/chat/components/ConversationListItem/conversation-list-item.types.ts +7 -0
- package/dist-lib/ai/exemplos/chat/components/ConversationListItem/index.ts +2 -0
- package/dist-lib/ai/exemplos/chat/components/DateSeparator/date-separator.tsx +18 -0
- package/dist-lib/ai/exemplos/chat/components/DetailField/detail-field.tsx +23 -0
- package/dist-lib/ai/exemplos/chat/components/DetailSection/detail-section.tsx +41 -0
- package/dist-lib/ai/exemplos/chat/components/DetailSection/index.ts +1 -0
- package/dist-lib/ai/exemplos/chat/components/DetailsColumn/details-column.styles.ts +30 -0
- package/dist-lib/ai/exemplos/chat/components/DetailsColumn/details-column.tsx +142 -0
- package/dist-lib/ai/exemplos/chat/components/DetailsColumn/details-column.types.ts +16 -0
- package/dist-lib/ai/exemplos/chat/components/DetailsColumn/index.ts +5 -0
- package/dist-lib/ai/exemplos/chat/components/FilterRow/filter-row.styles.ts +37 -0
- package/dist-lib/ai/exemplos/chat/components/FilterRow/filter-row.tsx +45 -0
- package/dist-lib/ai/exemplos/chat/components/FilterRow/index.ts +1 -0
- package/dist-lib/ai/exemplos/chat/components/FiltersColumn/filters-column.styles.ts +27 -0
- package/dist-lib/ai/exemplos/chat/components/FiltersColumn/filters-column.tsx +66 -0
- package/dist-lib/ai/exemplos/chat/components/FiltersColumn/filters-column.types.ts +13 -0
- package/dist-lib/ai/exemplos/chat/components/FiltersColumn/filters-rail.tsx +38 -0
- package/dist-lib/ai/exemplos/chat/components/FiltersColumn/index.ts +6 -0
- package/dist-lib/ai/exemplos/chat/components/MessageBubble/index.ts +2 -0
- package/dist-lib/ai/exemplos/chat/components/MessageBubble/message-bubble.styles.ts +37 -0
- package/dist-lib/ai/exemplos/chat/components/MessageBubble/message-bubble.tsx +29 -0
- package/dist-lib/ai/exemplos/chat/components/MessageBubble/message-bubble.types.ts +5 -0
- package/dist-lib/ai/exemplos/chat/components/PersonAvatar/index.ts +5 -0
- package/dist-lib/ai/exemplos/chat/components/PersonAvatar/person-avatar.tsx +31 -0
- package/dist-lib/ai/exemplos/chat/components/QueueColumn/index.ts +2 -0
- package/dist-lib/ai/exemplos/chat/components/QueueColumn/queue-column.styles.ts +19 -0
- package/dist-lib/ai/exemplos/chat/components/QueueColumn/queue-column.tsx +140 -0
- package/dist-lib/ai/exemplos/chat/components/QueueColumn/queue-column.types.ts +13 -0
- package/dist-lib/ai/exemplos/chat/components/RailItem/index.ts +1 -0
- package/dist-lib/ai/exemplos/chat/components/RailItem/rail-item.styles.ts +30 -0
- package/dist-lib/ai/exemplos/chat/components/RailItem/rail-item.tsx +42 -0
- package/dist-lib/ai/exemplos/chat/hooks/use-resizable.ts +98 -0
- package/dist-lib/ai/exemplos/chat/index.ts +1 -0
- package/dist-lib/ai/exemplos/clientes/_table-data.ts +59 -0
- package/dist-lib/ai/exemplos/clientes/clientes-screen.tsx +505 -0
- package/dist-lib/ai/exemplos/clientes/clientes-showcase-mocks.ts +117 -0
- package/dist-lib/ai/exemplos/clientes/clientes-showcase.styles.ts +13 -0
- package/dist-lib/ai/exemplos/clientes/clientes-showcase.types.ts +16 -0
- package/dist-lib/ai/exemplos/clientes/components/DetailDrawer/detail-drawer.styles.ts +28 -0
- package/dist-lib/ai/exemplos/clientes/components/DetailDrawer/detail-drawer.tsx +303 -0
- package/dist-lib/ai/exemplos/clientes/components/DetailDrawer/detail-drawer.types.ts +14 -0
- package/dist-lib/ai/exemplos/clientes/components/DetailDrawer/index.ts +2 -0
- package/dist-lib/ai/exemplos/clientes/components/NovoClienteDrawer/index.ts +2 -0
- package/dist-lib/ai/exemplos/clientes/components/NovoClienteDrawer/novo-cliente-drawer.tsx +207 -0
- package/dist-lib/ai/exemplos/clientes/index.ts +1 -0
- package/dist-lib/ai/exemplos/dashboard/dashboard-brazil-map.ts +33 -0
- package/dist-lib/ai/exemplos/dashboard/dashboard-screen.tsx +1110 -0
- package/dist-lib/ai/exemplos/dashboard/index.ts +1 -0
- package/dist-lib/ai/exemplos/edit-page/components/StepNav.tsx +81 -0
- package/dist-lib/ai/exemplos/edit-page/components/section-card.tsx +85 -0
- package/dist-lib/ai/exemplos/edit-page/edit-page-screen.tsx +234 -0
- package/dist-lib/ai/exemplos/edit-page/index.ts +1 -0
- package/dist-lib/ai/exemplos/finance/_table-data.ts +57 -0
- package/dist-lib/ai/exemplos/finance/clientes-financeiro-mocks.ts +227 -0
- package/dist-lib/ai/exemplos/finance/clientes-financeiro.types.ts +75 -0
- package/dist-lib/ai/exemplos/finance/clientes-showcase-mocks.ts +117 -0
- package/dist-lib/ai/exemplos/finance/clientes-showcase.styles.ts +13 -0
- package/dist-lib/ai/exemplos/finance/clientes-showcase.types.ts +16 -0
- package/dist-lib/ai/exemplos/finance/components/EditarFinanceDrawer/editar-finance-drawer.tsx +241 -0
- package/dist-lib/ai/exemplos/finance/components/EditarFinanceDrawer/index.ts +5 -0
- package/dist-lib/ai/exemplos/finance/components/ExtratoExpansion/extrato-expansion.tsx +172 -0
- package/dist-lib/ai/exemplos/finance/components/ExtratoExpansion/index.ts +1 -0
- package/dist-lib/ai/exemplos/finance/components/FinanceDetailPanel/finance-detail-panel.tsx +241 -0
- package/dist-lib/ai/exemplos/finance/components/FinanceDetailPanel/index.ts +2 -0
- package/dist-lib/ai/exemplos/finance/components/NovoClienteDrawer/index.ts +2 -0
- package/dist-lib/ai/exemplos/finance/components/NovoClienteDrawer/novo-cliente-drawer.tsx +207 -0
- package/dist-lib/ai/exemplos/finance/components/SacarDialog/index.ts +2 -0
- package/dist-lib/ai/exemplos/finance/components/SacarDialog/sacar-dialog.tsx +346 -0
- package/dist-lib/ai/exemplos/finance/finance-screen.tsx +821 -0
- package/dist-lib/ai/exemplos/finance/index.ts +1 -0
- package/dist-lib/ai/exemplos/gantt/_gantt-data.tsx +402 -0
- package/dist-lib/ai/exemplos/gantt/gantt-screen.tsx +512 -0
- package/dist-lib/ai/exemplos/gantt/index.ts +1 -0
- package/dist-lib/ai/exemplos/login/index.ts +1 -0
- package/dist-lib/ai/exemplos/login/login-screen.tsx +246 -0
- package/dist-lib/ai/exemplos/mapa-rede/components/ConsultorDetailPanel/consultor-detail-panel.tsx +158 -0
- package/dist-lib/ai/exemplos/mapa-rede/components/ConsultorDetailPanel/index.ts +2 -0
- package/dist-lib/ai/exemplos/mapa-rede/index.ts +1 -0
- package/dist-lib/ai/exemplos/mapa-rede/mapa-de-rede-mocks.ts +655 -0
- package/dist-lib/ai/exemplos/mapa-rede/mapa-de-rede.types.ts +53 -0
- package/dist-lib/ai/exemplos/mapa-rede/mapa-rede-screen.tsx +227 -0
- package/dist-lib/ai/exemplos/order-detail/components/ActivityTab.tsx +77 -0
- package/dist-lib/ai/exemplos/order-detail/components/AttachmentsTab.tsx +45 -0
- package/dist-lib/ai/exemplos/order-detail/components/CommentsTab.tsx +111 -0
- package/dist-lib/ai/exemplos/order-detail/components/DetailsTab.tsx +189 -0
- package/dist-lib/ai/exemplos/order-detail/components/OverviewTab.tsx +200 -0
- package/dist-lib/ai/exemplos/order-detail/components/section-card.tsx +85 -0
- package/dist-lib/ai/exemplos/order-detail/index.ts +1 -0
- package/dist-lib/ai/exemplos/order-detail/order-detail-screen.tsx +119 -0
- package/dist-lib/ai/exemplos/order-detail/order-mocks.ts +186 -0
- package/dist-lib/ai/exemplos/order-detail/order.types.ts +118 -0
- package/dist-lib/ai/global/componentes.md +217 -0
- package/dist-lib/ai/global/composicao.md +182 -0
- package/dist-lib/ai/indice.json +192 -0
- package/dist-lib/ai/lint/ds-lint-patterns.mjs +115 -0
- package/dist-lib/ai/manifest.json +42 -0
- package/dist-lib/ai/regras/design.md +88 -0
- package/dist-lib/ai/regras/temas.md +192 -0
- package/dist-lib/ai/regras-por-componente.json +103 -0
- package/dist-lib/ai/roteiros/app-builder/roteiro.md +155 -0
- package/dist-lib/ai/roteiros/auth-builder/roteiro.md +42 -0
- package/dist-lib/ai/roteiros/cards/roteiro.md +34 -0
- package/dist-lib/ai/roteiros/charts/roteiro.md +32 -0
- package/dist-lib/ai/roteiros/chat/roteiro.md +31 -0
- package/dist-lib/ai/roteiros/crud-builder/blueprint.md +63 -0
- package/dist-lib/ai/roteiros/crud-builder/entrevista.md +139 -0
- package/dist-lib/ai/roteiros/crud-builder/geracao.md +113 -0
- package/dist-lib/ai/roteiros/crud-builder/roteiro.md +89 -0
- package/dist-lib/ai/roteiros/dashboard-builder/blueprint.md +47 -0
- package/dist-lib/ai/roteiros/dashboard-builder/entrevista.md +62 -0
- package/dist-lib/ai/roteiros/dashboard-builder/geracao.md +88 -0
- package/dist-lib/ai/roteiros/dashboard-builder/roteiro.md +88 -0
- package/dist-lib/ai/roteiros/drawers/roteiro.md +41 -0
- package/dist-lib/ai/roteiros/list-builder/blueprint.md +94 -0
- package/dist-lib/ai/roteiros/list-builder/entrevista.md +188 -0
- package/dist-lib/ai/roteiros/list-builder/geracao.md +63 -0
- package/dist-lib/ai/roteiros/list-builder/roteiro.md +91 -0
- package/dist-lib/ai/roteiros/module-replicator/roteiro.md +56 -0
- package/dist-lib/ai/roteiros/page-detail/roteiro.md +32 -0
- package/dist-lib/ai/roteiros/page-edit/roteiro.md +31 -0
- package/dist-lib/ai/roteiros/screen-composer/roteiro.md +95 -0
- package/package.json +4 -1
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export { DashboardScreen, default } from "./dashboard-screen";
|
|
@@ -0,0 +1,81 @@
|
|
|
1
|
+
import type { LucideIcon } from "@/lib/lucide-types";
|
|
2
|
+
import { cn } from "@/lib/utils";
|
|
3
|
+
|
|
4
|
+
export type Step = {
|
|
5
|
+
id: string;
|
|
6
|
+
icon: LucideIcon;
|
|
7
|
+
title: string;
|
|
8
|
+
description: string;
|
|
9
|
+
};
|
|
10
|
+
|
|
11
|
+
/**
|
|
12
|
+
* Nav lateral (stepper) da tela de edição — itens com ícone + título +
|
|
13
|
+
* descrição; o ativo ganha destaque de marca. Clicar seleciona + rola até a
|
|
14
|
+
* seção. Composição local do showcase usando tokens DS.
|
|
15
|
+
*/
|
|
16
|
+
export function StepNav({
|
|
17
|
+
steps,
|
|
18
|
+
activeId,
|
|
19
|
+
onSelect,
|
|
20
|
+
className,
|
|
21
|
+
}: {
|
|
22
|
+
steps: Step[];
|
|
23
|
+
activeId: string;
|
|
24
|
+
onSelect: (id: string) => void;
|
|
25
|
+
className?: string;
|
|
26
|
+
}) {
|
|
27
|
+
return (
|
|
28
|
+
<nav
|
|
29
|
+
className={cn(
|
|
30
|
+
"flex flex-col gap-gp-xs rounded-radius-lg border border-border-subtle bg-bg-surface p-pad-md shadow-sh-sm",
|
|
31
|
+
className,
|
|
32
|
+
)}
|
|
33
|
+
aria-label="Etapas do pedido"
|
|
34
|
+
>
|
|
35
|
+
{steps.map((s) => {
|
|
36
|
+
const Icon = s.icon;
|
|
37
|
+
const active = s.id === activeId;
|
|
38
|
+
return (
|
|
39
|
+
<button
|
|
40
|
+
key={s.id}
|
|
41
|
+
type="button"
|
|
42
|
+
onClick={() => onSelect(s.id)}
|
|
43
|
+
aria-current={active ? "step" : undefined}
|
|
44
|
+
className={cn(
|
|
45
|
+
"flex items-start gap-gp-md rounded-radius-md border p-pad-lg text-left transition-colors",
|
|
46
|
+
active
|
|
47
|
+
? "border-border-brand bg-bg-brand-subtle"
|
|
48
|
+
: "border-transparent hover:bg-bg-muted",
|
|
49
|
+
)}
|
|
50
|
+
>
|
|
51
|
+
<span
|
|
52
|
+
className={cn(
|
|
53
|
+
"grid size-8 shrink-0 place-items-center rounded-radius-md border",
|
|
54
|
+
active
|
|
55
|
+
? "border-transparent bg-bg-brand text-fg-on-brand"
|
|
56
|
+
// bg-surface (branco no light) + borda: contrasta tanto no card
|
|
57
|
+
// quanto no hover cinza (senão o ícone funde com o hover).
|
|
58
|
+
: "border-border-subtle bg-bg-surface text-fg-muted",
|
|
59
|
+
)}
|
|
60
|
+
>
|
|
61
|
+
<Icon className="size-icon-sm" />
|
|
62
|
+
</span>
|
|
63
|
+
<span className="min-w-0 flex-1">
|
|
64
|
+
<span
|
|
65
|
+
className={cn(
|
|
66
|
+
"block text-body-sm font-semibold",
|
|
67
|
+
active ? "text-fg-brand" : "text-fg-default",
|
|
68
|
+
)}
|
|
69
|
+
>
|
|
70
|
+
{s.title}
|
|
71
|
+
</span>
|
|
72
|
+
<span className="mt-gp-2xs block text-caption-sm leading-snug text-fg-muted">
|
|
73
|
+
{s.description}
|
|
74
|
+
</span>
|
|
75
|
+
</span>
|
|
76
|
+
</button>
|
|
77
|
+
);
|
|
78
|
+
})}
|
|
79
|
+
</nav>
|
|
80
|
+
);
|
|
81
|
+
}
|
|
@@ -0,0 +1,85 @@
|
|
|
1
|
+
import type { ReactNode } from "react";
|
|
2
|
+
import { cn } from "@/lib/utils";
|
|
3
|
+
|
|
4
|
+
/**
|
|
5
|
+
* Card de seção flat — bg-surface + borda sutil, sem elevação pesada.
|
|
6
|
+
* Espelha o visual dos blocos da referência (Products ordered, Customer, etc).
|
|
7
|
+
* Composição local do showcase consumindo tokens DS via classes.
|
|
8
|
+
*/
|
|
9
|
+
export function SectionCard({
|
|
10
|
+
title,
|
|
11
|
+
icon,
|
|
12
|
+
action,
|
|
13
|
+
children,
|
|
14
|
+
className,
|
|
15
|
+
bodyClassName,
|
|
16
|
+
}: {
|
|
17
|
+
title?: ReactNode;
|
|
18
|
+
icon?: ReactNode;
|
|
19
|
+
action?: ReactNode;
|
|
20
|
+
children: ReactNode;
|
|
21
|
+
className?: string;
|
|
22
|
+
bodyClassName?: string;
|
|
23
|
+
}) {
|
|
24
|
+
const hasHeader = !!(title || action);
|
|
25
|
+
const header = hasHeader && (
|
|
26
|
+
// Header: padding 16px (pad-2xl) + divider full-bleed embaixo.
|
|
27
|
+
<header className="flex items-center justify-between gap-gp-md border-b border-border-subtle bg-bg-subtle p-pad-2xl">
|
|
28
|
+
{/* gap ícone↔título = 12px (gap-gp-md) */}
|
|
29
|
+
<div className="flex items-center gap-gp-md">
|
|
30
|
+
{icon && (
|
|
31
|
+
<span className="grid size-8 shrink-0 place-items-center rounded-radius-md bg-bg-muted text-fg-muted">
|
|
32
|
+
{icon}
|
|
33
|
+
</span>
|
|
34
|
+
)}
|
|
35
|
+
{title && (
|
|
36
|
+
<h2 className="text-title-md font-semibold text-fg-default">
|
|
37
|
+
{title}
|
|
38
|
+
</h2>
|
|
39
|
+
)}
|
|
40
|
+
</div>
|
|
41
|
+
{action}
|
|
42
|
+
</header>
|
|
43
|
+
);
|
|
44
|
+
|
|
45
|
+
return (
|
|
46
|
+
<section className={cn("overflow-hidden rounded-radius-lg border border-border-subtle bg-bg-surface shadow-sh-sm", className)}>
|
|
47
|
+
{header}
|
|
48
|
+
{/* body: padding 16px (pad-2xl) — uniforme; abaixo do divider quando há header */}
|
|
49
|
+
<div className={cn("p-pad-2xl", bodyClassName)}>{children}</div>
|
|
50
|
+
</section>
|
|
51
|
+
);
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
/** Divisória sutil de seção. `my` controla o respiro vertical (default md). */
|
|
55
|
+
export function SectionDivider({ className }: { className?: string }) {
|
|
56
|
+
return <div className={cn("h-px bg-border-subtle", className)} />;
|
|
57
|
+
}
|
|
58
|
+
|
|
59
|
+
/** Par label-uppercase + valor (grid de Customer/Shipping/Billing Information). */
|
|
60
|
+
export function Field({
|
|
61
|
+
label,
|
|
62
|
+
value,
|
|
63
|
+
accent,
|
|
64
|
+
}: {
|
|
65
|
+
label: string;
|
|
66
|
+
value: ReactNode;
|
|
67
|
+
/** Destaca o valor com a cor de marca (links, ids de transação, etc). */
|
|
68
|
+
accent?: boolean;
|
|
69
|
+
}) {
|
|
70
|
+
return (
|
|
71
|
+
<div className="flex flex-col gap-gp-2xs">
|
|
72
|
+
<span className="text-caption-sm font-medium uppercase tracking-wider text-fg-muted">
|
|
73
|
+
{label}
|
|
74
|
+
</span>
|
|
75
|
+
<span
|
|
76
|
+
className={cn(
|
|
77
|
+
"text-body-md",
|
|
78
|
+
accent ? "text-fg-brand" : "text-fg-default",
|
|
79
|
+
)}
|
|
80
|
+
>
|
|
81
|
+
{value}
|
|
82
|
+
</span>
|
|
83
|
+
</div>
|
|
84
|
+
);
|
|
85
|
+
}
|
|
@@ -0,0 +1,234 @@
|
|
|
1
|
+
import { useRef, useState } from "react";
|
|
2
|
+
import { CreditCard, MapPin, Package, User } from "lucide-react";
|
|
3
|
+
import { Button } from "@/components/ui/Button/button";
|
|
4
|
+
import { ChipGroup, ChipGroupItem } from "@/components/ui/Chip";
|
|
5
|
+
import { PageHeader } from "@/components/ui/PageHeader";
|
|
6
|
+
import {
|
|
7
|
+
FormField,
|
|
8
|
+
FormFieldInput,
|
|
9
|
+
FormFieldSelect,
|
|
10
|
+
} from "@/components/ui/FormField";
|
|
11
|
+
import {
|
|
12
|
+
Select,
|
|
13
|
+
SelectContent,
|
|
14
|
+
SelectItem,
|
|
15
|
+
SelectTrigger,
|
|
16
|
+
SelectValue,
|
|
17
|
+
} from "@/components/shadcn/select";
|
|
18
|
+
import { Input } from "@/components/shadcn/input";
|
|
19
|
+
import { SectionCard } from "./components/section-card";
|
|
20
|
+
import { StepNav, type Step } from "./components/StepNav";
|
|
21
|
+
|
|
22
|
+
const STEPS: Step[] = [
|
|
23
|
+
{
|
|
24
|
+
id: "produtos",
|
|
25
|
+
icon: Package,
|
|
26
|
+
title: "Selecionar produtos",
|
|
27
|
+
description: "Adicione produtos à lista de compra.",
|
|
28
|
+
},
|
|
29
|
+
{
|
|
30
|
+
id: "cliente",
|
|
31
|
+
icon: User,
|
|
32
|
+
title: "Dados do cliente",
|
|
33
|
+
description: "Nome, e-mail e telefone do cliente.",
|
|
34
|
+
},
|
|
35
|
+
{
|
|
36
|
+
id: "endereco",
|
|
37
|
+
icon: MapPin,
|
|
38
|
+
title: "Endereço",
|
|
39
|
+
description: "Informe o endereço de entrega.",
|
|
40
|
+
},
|
|
41
|
+
{
|
|
42
|
+
id: "pagamento",
|
|
43
|
+
icon: CreditCard,
|
|
44
|
+
title: "Pagamento",
|
|
45
|
+
description: "Método e dados do pagamento.",
|
|
46
|
+
},
|
|
47
|
+
];
|
|
48
|
+
|
|
49
|
+
const COUNTRY_OPTIONS = [
|
|
50
|
+
{ value: "br", label: "Brasil" },
|
|
51
|
+
{ value: "pt", label: "Portugal" },
|
|
52
|
+
{ value: "us", label: "Estados Unidos" },
|
|
53
|
+
];
|
|
54
|
+
|
|
55
|
+
const PAYMENT_OPTIONS = [
|
|
56
|
+
{ value: "card", label: "Cartão de crédito/débito" },
|
|
57
|
+
{ value: "pix", label: "PIX" },
|
|
58
|
+
{ value: "boleto", label: "Boleto" },
|
|
59
|
+
];
|
|
60
|
+
|
|
61
|
+
const DDI_OPTIONS = ["+55", "+1", "+351"];
|
|
62
|
+
|
|
63
|
+
/**
|
|
64
|
+
* EditPageScreen — tela de edição de pedido (formulário em etapas). Mesmo
|
|
65
|
+
* modelo de design da OrderDetail (SectionCard) + nav lateral (stepper).
|
|
66
|
+
* Toggle de layout: 1 coluna (igual à referência) ou 2 colunas. Domínio
|
|
67
|
+
* iGreen (energia solar).
|
|
68
|
+
*/
|
|
69
|
+
export function EditPageScreen() {
|
|
70
|
+
const [cols, setCols] = useState<"one" | "two">("one");
|
|
71
|
+
const [activeStep, setActiveStep] = useState("produtos");
|
|
72
|
+
|
|
73
|
+
const sectionRefs = useRef<Record<string, HTMLDivElement | null>>({});
|
|
74
|
+
|
|
75
|
+
const goTo = (id: string) => {
|
|
76
|
+
setActiveStep(id);
|
|
77
|
+
sectionRefs.current[id]?.scrollIntoView({ behavior: "smooth", block: "start" });
|
|
78
|
+
};
|
|
79
|
+
|
|
80
|
+
const setRef = (id: string) => (el: HTMLDivElement | null) => {
|
|
81
|
+
sectionRefs.current[id] = el;
|
|
82
|
+
};
|
|
83
|
+
|
|
84
|
+
return (
|
|
85
|
+
// Conteúdo da página (sem shell). Embrulhe no seu AppShell/layout — o
|
|
86
|
+
// parent precisa dar altura (h-full/flex) pra página preencher.
|
|
87
|
+
<div className="flex flex-col h-full min-h-0 gap-gp-2xl">
|
|
88
|
+
<PageHeader
|
|
89
|
+
title="Editar pedido"
|
|
90
|
+
description="Pedido #84021 · atualize produtos, cliente, entrega e pagamento."
|
|
91
|
+
hideTextOnMobile={false}
|
|
92
|
+
actions={
|
|
93
|
+
<ChipGroup
|
|
94
|
+
type="single"
|
|
95
|
+
value={cols}
|
|
96
|
+
onValueChange={(v) => v && setCols(v as "one" | "two")}
|
|
97
|
+
size="sm"
|
|
98
|
+
ariaLabel="Layout das colunas"
|
|
99
|
+
>
|
|
100
|
+
<ChipGroupItem value="one">1 coluna</ChipGroupItem>
|
|
101
|
+
<ChipGroupItem value="two">2 colunas</ChipGroupItem>
|
|
102
|
+
</ChipGroup>
|
|
103
|
+
}
|
|
104
|
+
/>
|
|
105
|
+
|
|
106
|
+
<div className="grid grid-cols-1 items-start gap-gp-4xl pb-pad-6xl lg:grid-cols-[260px_1fr]">
|
|
107
|
+
{/* Nav lateral */}
|
|
108
|
+
<StepNav
|
|
109
|
+
steps={STEPS}
|
|
110
|
+
activeId={activeStep}
|
|
111
|
+
onSelect={goTo}
|
|
112
|
+
className="lg:sticky lg:top-gp-2xl"
|
|
113
|
+
/>
|
|
114
|
+
|
|
115
|
+
{/* Seções do formulário */}
|
|
116
|
+
<div
|
|
117
|
+
className={
|
|
118
|
+
cols === "two"
|
|
119
|
+
? "grid grid-cols-1 items-start gap-gp-4xl xl:grid-cols-2"
|
|
120
|
+
: "flex flex-col gap-gp-4xl"
|
|
121
|
+
}
|
|
122
|
+
>
|
|
123
|
+
<div ref={setRef("produtos")} className="scroll-mt-gp-2xl">
|
|
124
|
+
<SectionCard title="Selecionar produtos">
|
|
125
|
+
<FormFieldInput
|
|
126
|
+
label="Buscar produto"
|
|
127
|
+
placeholder="Busque por nome ou SKU..."
|
|
128
|
+
/>
|
|
129
|
+
</SectionCard>
|
|
130
|
+
</div>
|
|
131
|
+
|
|
132
|
+
<div ref={setRef("cliente")} className="scroll-mt-gp-2xl">
|
|
133
|
+
<SectionCard title="Dados do cliente">
|
|
134
|
+
<div className="flex flex-col gap-form-gap">
|
|
135
|
+
<div className="grid grid-cols-1 gap-form-gap sm:grid-cols-2">
|
|
136
|
+
<FormFieldInput label="Nome" placeholder="Nome" />
|
|
137
|
+
<FormFieldInput label="Usuário" placeholder="Nome de usuário" />
|
|
138
|
+
</div>
|
|
139
|
+
<FormFieldInput
|
|
140
|
+
label="Email"
|
|
141
|
+
type="email"
|
|
142
|
+
placeholder="email@exemplo.com"
|
|
143
|
+
/>
|
|
144
|
+
<FormField label="Telefone">
|
|
145
|
+
{({ id }) => (
|
|
146
|
+
<div className="flex gap-gp-sm">
|
|
147
|
+
<Select defaultValue="+55">
|
|
148
|
+
<SelectTrigger className="w-24 shrink-0">
|
|
149
|
+
<SelectValue />
|
|
150
|
+
</SelectTrigger>
|
|
151
|
+
<SelectContent>
|
|
152
|
+
{DDI_OPTIONS.map((d) => (
|
|
153
|
+
<SelectItem key={d} value={d}>
|
|
154
|
+
{d}
|
|
155
|
+
</SelectItem>
|
|
156
|
+
))}
|
|
157
|
+
</SelectContent>
|
|
158
|
+
</Select>
|
|
159
|
+
<Input
|
|
160
|
+
id={id}
|
|
161
|
+
type="tel"
|
|
162
|
+
placeholder="Número de telefone"
|
|
163
|
+
className="flex-1"
|
|
164
|
+
/>
|
|
165
|
+
</div>
|
|
166
|
+
)}
|
|
167
|
+
</FormField>
|
|
168
|
+
</div>
|
|
169
|
+
</SectionCard>
|
|
170
|
+
</div>
|
|
171
|
+
|
|
172
|
+
<div ref={setRef("endereco")} className="scroll-mt-gp-2xl">
|
|
173
|
+
<SectionCard title="Endereço">
|
|
174
|
+
<div className="flex flex-col gap-form-gap">
|
|
175
|
+
<FormFieldSelect
|
|
176
|
+
label="País"
|
|
177
|
+
placeholder="Selecione o país"
|
|
178
|
+
options={COUNTRY_OPTIONS}
|
|
179
|
+
/>
|
|
180
|
+
<FormFieldInput label="Endereço" placeholder="Rua, número" />
|
|
181
|
+
<div className="grid grid-cols-1 gap-form-gap sm:grid-cols-2">
|
|
182
|
+
<FormFieldInput label="Cidade" placeholder="Cidade" />
|
|
183
|
+
<FormFieldInput label="CEP" placeholder="00000-000" />
|
|
184
|
+
</div>
|
|
185
|
+
</div>
|
|
186
|
+
</SectionCard>
|
|
187
|
+
</div>
|
|
188
|
+
|
|
189
|
+
<div ref={setRef("pagamento")} className="scroll-mt-gp-2xl">
|
|
190
|
+
<SectionCard title="Pagamento">
|
|
191
|
+
<div className="flex flex-col gap-form-gap">
|
|
192
|
+
<FormFieldSelect
|
|
193
|
+
label="Método de pagamento"
|
|
194
|
+
defaultValue="card"
|
|
195
|
+
options={PAYMENT_OPTIONS}
|
|
196
|
+
/>
|
|
197
|
+
<FormFieldInput
|
|
198
|
+
label="Nome no cartão"
|
|
199
|
+
placeholder="Nome impresso no cartão"
|
|
200
|
+
/>
|
|
201
|
+
<FormFieldInput
|
|
202
|
+
label="Número do cartão"
|
|
203
|
+
placeholder="0000 0000 0000 0000"
|
|
204
|
+
inputMode="numeric"
|
|
205
|
+
/>
|
|
206
|
+
<div className="grid grid-cols-1 gap-form-gap sm:grid-cols-2">
|
|
207
|
+
<FormFieldInput label="Validade" placeholder="MM/AA" />
|
|
208
|
+
<FormFieldInput label="CVV" placeholder="123" />
|
|
209
|
+
</div>
|
|
210
|
+
</div>
|
|
211
|
+
</SectionCard>
|
|
212
|
+
</div>
|
|
213
|
+
|
|
214
|
+
{/* Footer de ações */}
|
|
215
|
+
<div
|
|
216
|
+
className={
|
|
217
|
+
"flex items-center justify-end gap-gp-md" +
|
|
218
|
+
(cols === "two" ? " xl:col-span-2" : "")
|
|
219
|
+
}
|
|
220
|
+
>
|
|
221
|
+
<Button variant="outline" color="secondary" size="md">
|
|
222
|
+
Cancelar
|
|
223
|
+
</Button>
|
|
224
|
+
<Button variant="filled" color="primary" size="md">
|
|
225
|
+
Salvar pedido
|
|
226
|
+
</Button>
|
|
227
|
+
</div>
|
|
228
|
+
</div>
|
|
229
|
+
</div>
|
|
230
|
+
</div>
|
|
231
|
+
);
|
|
232
|
+
}
|
|
233
|
+
|
|
234
|
+
export default EditPageScreen;
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export { EditPageScreen, default } from "./edit-page-screen";
|
|
@@ -0,0 +1,57 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Dados base compartilhados (extraídos do showcase TableDoc do DS).
|
|
3
|
+
* Mantém o exemplo autossuficiente — sem dependência da infra de preview.
|
|
4
|
+
*/
|
|
5
|
+
|
|
6
|
+
export const STATUSES: Record<string, { label: string; color: string }> = {
|
|
7
|
+
active: { label: "Ativo", color: "var(--color-fg-success)" },
|
|
8
|
+
pending: { label: "Pendente", color: "var(--color-fg-warning)" },
|
|
9
|
+
paused: { label: "Pausado", color: "var(--color-fg-info)" },
|
|
10
|
+
inactive: { label: "Inativo", color: "var(--color-fg-muted)" },
|
|
11
|
+
};
|
|
12
|
+
|
|
13
|
+
export type CategoryKind = "warning" | "info" | "success" | "neutral";
|
|
14
|
+
export const CATEGORIES: Record<string, { label: string; kind: CategoryKind }> = {
|
|
15
|
+
royal: { label: "Royal", kind: "warning" },
|
|
16
|
+
licenciado: { label: "Licenciado", kind: "info" },
|
|
17
|
+
lead: { label: "Lead", kind: "success" },
|
|
18
|
+
};
|
|
19
|
+
|
|
20
|
+
export const AGENTS: Record<string, { name: string; initials: string; color: string }> = {
|
|
21
|
+
you: { name: "Voce", initials: "VC", color: "#0a3a2e" },
|
|
22
|
+
aline: { name: "Aline Castro", initials: "AC", color: "#f59e0b" },
|
|
23
|
+
carlos: { name: "Carlos Souza", initials: "CS", color: "#8754ec" },
|
|
24
|
+
maria: { name: "Maria Lima", initials: "ML", color: "#ef4444" },
|
|
25
|
+
};
|
|
26
|
+
|
|
27
|
+
export type ClientRow = {
|
|
28
|
+
id: string;
|
|
29
|
+
name: string;
|
|
30
|
+
initials: string;
|
|
31
|
+
avatarColor: string;
|
|
32
|
+
email: string;
|
|
33
|
+
phone: string;
|
|
34
|
+
statusId: keyof typeof STATUSES;
|
|
35
|
+
categoryId: keyof typeof CATEGORIES;
|
|
36
|
+
location: string;
|
|
37
|
+
value: number;
|
|
38
|
+
agentId: keyof typeof AGENTS;
|
|
39
|
+
createdAt: number;
|
|
40
|
+
lastContact: number;
|
|
41
|
+
};
|
|
42
|
+
|
|
43
|
+
const BASE_DATE = new Date("2026-04-15T12:00:00Z").getTime();
|
|
44
|
+
const DAY_MS = 86400000;
|
|
45
|
+
|
|
46
|
+
export const CLIENTS_MOCK: ClientRow[] = [
|
|
47
|
+
{ id: "CLI-2401", name: "Maria Silva", initials: "MS", avatarColor: "#f59e0b", email: "maria.silva@example.com", phone: "+55 11 91234-5678", statusId: "active", categoryId: "royal", location: "São Paulo, SP", value: 4800, agentId: "you", createdAt: BASE_DATE - 65 * DAY_MS, lastContact: BASE_DATE - 2 * DAY_MS },
|
|
48
|
+
{ id: "CLI-2402", name: "João Santos", initials: "JS", avatarColor: "#0a3a2e", email: "joao.santos@example.com", phone: "+55 11 92345-6789", statusId: "pending", categoryId: "licenciado", location: "Rio de Janeiro, RJ", value: 12300, agentId: "aline", createdAt: BASE_DATE - 58 * DAY_MS, lastContact: BASE_DATE - 5 * DAY_MS },
|
|
49
|
+
{ id: "CLI-2403", name: "Carlos Oliveira", initials: "CO", avatarColor: "#8754ec", email: "carlos.oliveira@example.com", phone: "+55 11 93456-7890", statusId: "active", categoryId: "lead", location: "Belo Horizonte, MG", value: 2150, agentId: "carlos", createdAt: BASE_DATE - 51 * DAY_MS, lastContact: BASE_DATE - 1 * DAY_MS },
|
|
50
|
+
{ id: "CLI-2404", name: "Ana Costa", initials: "AC", avatarColor: "#1cb280", email: "ana.costa@example.com", phone: "+55 11 94567-8901", statusId: "paused", categoryId: "royal", location: "Porto Alegre, RS", value: 8900, agentId: "maria", createdAt: BASE_DATE - 44 * DAY_MS, lastContact: BASE_DATE - 12 * DAY_MS },
|
|
51
|
+
{ id: "CLI-2405", name: "Pedro Pereira", initials: "PP", avatarColor: "#ef4444", email: "pedro.pereira@example.com", phone: "+55 11 95678-9012", statusId: "inactive", categoryId: "lead", location: "Curitiba, PR", value: 1100, agentId: "you", createdAt: BASE_DATE - 37 * DAY_MS, lastContact: BASE_DATE - 30 * DAY_MS },
|
|
52
|
+
{ id: "CLI-2406", name: "Lúcia Almeida", initials: "LA", avatarColor: "#f9a47a", email: "lucia.almeida@example.com", phone: "+55 11 96789-0123", statusId: "active", categoryId: "licenciado", location: "Recife, PE", value: 6750, agentId: "aline", createdAt: BASE_DATE - 30 * DAY_MS, lastContact: BASE_DATE - 3 * DAY_MS },
|
|
53
|
+
{ id: "CLI-2407", name: "Roberto Souza", initials: "RS", avatarColor: "#0088cc", email: "roberto.souza@example.com", phone: "+55 11 97890-1234", statusId: "pending", categoryId: "royal", location: "São Paulo, SP", value: 15200, agentId: "carlos", createdAt: BASE_DATE - 23 * DAY_MS, lastContact: BASE_DATE - 7 * DAY_MS },
|
|
54
|
+
{ id: "CLI-2408", name: "Fernanda Lima", initials: "FL", avatarColor: "#e1306c", email: "fernanda.lima@example.com", phone: "+55 11 98901-2345", statusId: "active", categoryId: "lead", location: "Rio de Janeiro, RJ", value: 3400, agentId: "maria", createdAt: BASE_DATE - 16 * DAY_MS, lastContact: BASE_DATE - 1 * DAY_MS },
|
|
55
|
+
{ id: "CLI-2409", name: "Bruno Rodrigues", initials: "BR", avatarColor: "#70c748", email: "bruno.rodrigues@example.com", phone: "+55 11 99012-3456", statusId: "paused", categoryId: "licenciado", location: "Belo Horizonte, MG", value: 5600, agentId: "you", createdAt: BASE_DATE - 9 * DAY_MS, lastContact: BASE_DATE - 6 * DAY_MS },
|
|
56
|
+
{ id: "CLI-2410", name: "Camila Ribeiro", initials: "CR", avatarColor: "#8754ec", email: "camila.ribeiro@example.com", phone: "+55 11 90123-4567", statusId: "active", categoryId: "royal", location: "Porto Alegre, RS", value: 9800, agentId: "aline", createdAt: BASE_DATE - 2 * DAY_MS, lastContact: BASE_DATE },
|
|
57
|
+
];
|