VendeeDocs
Frontend

Componentes

shadcn/ui, shared components e Lucide icons

O frontend trabalha com três camadas de componentes:

  • src/components/ui/ — primitivos do shadcn/ui (código próprio, editável)
  • src/components/shared/ — componentes compartilhados de alto nível, obrigatórios para padronização
  • src/components/layout/ — shell do app (AppLayout, AppSidebar, AppHeader)

Shared Components

Localizados em src/components/shared/. Obrigatórios para qualquer nova página. Nunca construa esses padrões manualmente inline — use os componentes.

ComponenteUso
PageHeaderCabeçalho de página (title, description, children = ação principal)
KpiCardCartão de métrica (label, value, tooltip, delta)
ChartCardWrapper de gráficos (title, description, action, legend, narrative)
EmptyStateEstado vazio de página (icon, title, description, action)
SectionOverlineTexto de rótulo de seção
HubLayoutLayout de hub (sidebar + área principal)
HubSidebarSectionSeção colapsável na sidebar do hub
HubTimelineTimeline de eventos do hub
InlineEditFieldCampo editável inline (click-to-edit)
SearchableSelectCombobox com busca accent-insensitive e opção "Criar X"
LoadingStateSkeleton de carregamento de página
RouteErrorBoundaryError boundary global da rota raiz
SuspenseWrapperWrapper para lazy loading com Suspense

Nunca use <h1>, <h2> ou <h3> soltos como título de página — sempre PageHeader. Nunca envolva um gráfico em Card + CardHeader + CardTitle direto — use ChartCard. Nunca construa um cartão de KPI manualmente — use KpiCard.

Exemplo: PageHeader

import { PageHeader } from "@/components/shared/PageHeader";

<PageHeader title="Negócios" description="Gerencie seu pipeline de vendas.">
  <Button>Novo negócio</Button>
</PageHeader>

Exemplo: KpiCard

import { KpiCard } from "@/components/shared/KpiCard";

<KpiCard
  label="Negócios ganhos"
  value="R$ 42.000"
  tooltip="Total de negócios marcados como ganhos no período"
  delta={{ value: "+12%", direction: "up" }}
/>

Exemplo: ChartCard

import { ChartCard } from "@/components/shared/ChartCard";

<ChartCard title="Negócios por semana" description="Criados vs ganhos">
  {/* loading skeleton, error state, empty state ou o chart */}
</ChartCard>

shadcn/ui

Style radix-nova. Configuração em apps/app/components.json, tokens (oklch) em src/index.css.

A lista atual de componentes instalados está em apps/app/src/components/ui/. Antes de adicionar, verifique se já existe.

Adicionar componentes

cd apps/app && bunx shadcn@latest add <component>

Componentes recomendados

Antes de hand-buildar UI, veja se shadcn já tem:

  • Tabelas com sorting/filtering → table + TanStack Table
  • Charts → chart
  • Command palette → command
  • Paginação → pagination
  • Date picking → calendar / date-picker
  • Drawers → drawer
  • Toasts → sonner (use toast() de sonner)

Imports

Importe diretamente — sem wrappers:

import { Button } from "@/components/ui/button";
import { Card, CardContent, CardHeader, CardTitle } from "@/components/ui/card";

Customização

Os componentes em src/components/ui/ são código próprio. Edite o arquivo diretamente quando precisar customizar.

cn()

Utilitário para merge condicional de classes (clsx + tailwind-merge):

import { cn } from "@/lib/utils";

<div className={cn("px-4 py-2", isActive && "bg-primary text-white")} />

Ícones

Apenas Lucide React:

import { Settings, Users, Kanban } from "lucide-react";

<Settings className="size-4" />

On this page