Saltearse al contenido

Frontend Componente Library

Frontend Componente Library

Version: 1.0 Date: 2025-11-19 Project: Algesta Dashboard React

Tabla de Contenidos

  1. Descripción General del Sistema de Diseño
  2. Tokens de Diseño
  3. Catálogo de Componentes
  4. Patrones de Uso de Componentes
  5. Enfoque de Estilos
  6. Accesibilidad
  7. Personalización
  8. Agregar Nuevos Componentes
  9. Guía de Desarrollo de Componentes

Descripción General del Sistema de Diseño

El Dashboard de Algesta implementa un sistema de diseño integral basado en el patrón shadcn/ui. Este enfoque proporciona:

  • Componentes Componibles: Componentes pequeños y enfocados que trabajan juntos
  • Accesible por Defecto: Construido sobre primitivos Radix UI (compatible con WAI-ARIA)
  • Personalizable: Los componentes se copian al proyecto y pueden modificarse
  • Type-Safe: Soporte completo de TypeScript con tipos de props explícitos

Filosofía

A diferencia de las bibliotecas de componentes tradicionales (paquetes npm), los componentes shadcn/ui se copian directamente en tu proyecto. Esto te da:

  • Propiedad y control total sobre el código del componente
  • Sin dependencias de caja negra
  • Personalización fácil sin luchar contra la biblioteca
  • Capacidad de ver y modificar el código fuente del componente

Tokens de Diseño

Paleta de Colores

Todos los colores se definen como variables CSS en src/index.css usando formato HSL:

Colores Primarios

TokenValorUso
--primaryhsla(32, 100%, 50%, 1)Naranja - Color principal de marca para botones, enlaces, acciones primarias
--primary-foregroundhsla(0, 0%, 100%, 1)Blanco - Texto sobre fondo primario

Neutral Colors (Gray Scale)

TokenValueUsage
--neutral-50hsla(0, 0%, 98%, 1)Lightest gray - Background
--neutral-100hsla(240, 5%, 96%, 1)Very light gray
--neutral-200hsla(240, 6%, 90%, 1)Light gray - Borders
--neutral-300hsla(240, 5%, 84%, 1)Medium-light gray
--neutral-400hsla(240, 5%, 65%, 1)Medium gray
--neutral-500hsla(240, 4%, 46%, 1)Medium-dark gray - Secondary text
--neutral-600hsla(240, 5%, 34%, 1)Dark gray
--neutral-700hsla(240, 5%, 26%, 1)Darker gray - Body text
--neutral-800hsla(240, 4%, 16%, 1)Very dark gray
--neutral-900hsla(240, 6%, 10%, 1)Almost black - Headings

Blue (Accent)

TokenValueUsage
--blue-50 to --blue-900Various blue shadesInformational elements, links, accents

Success (Green)

TokenValueUsage
--success-50 to --success-900Various green shadesSuccess states, positive actions, Completod Estado

Warning (Yellow/Orange)

TokenValueUsage
--warning-50 to --warning-900Various yellow/orange shadesWarning states, Pendiente actions

Destructive (Red)

TokenValueUsage
--destructiveRedError states, dangerous actions, delete buttons
--destructive-foregroundWhiteText on destructive background

Chart Colors

TokenValueUsage
--chart-1hsla(12, 76%, 61%, 1)Chart data series 1
--chart-2hsla(173, 58%, 39%, 1)Chart data series 2
--chart-3hsla(197, 37%, 24%, 1)Chart data series 3
--chart-4hsla(43, 74%, 66%, 1)Chart data series 4
--chart-5hsla(27, 87%, 67%, 1)Chart data series 5

Typography

  • Font Family: Inter Variable (--font-inter)
  • Font Sizes: Tailwind defaults (text-xs, text-sm, text-base, text-lg, text-xl, etc.)
  • Font Weights: 400 (normal), 500 (medium), 600 (semibold), 700 (bold)

Spacing

Tailwind spacing scale (0.25rem increments):

  • p-1 = 0.25rem (4px)
  • p-2 = 0.5rem (8px)
  • p-4 = 1rem (16px)
  • p-6 = 1.5rem (24px)
  • p-8 = 2rem (32px)

Border Radius

TokenValueUsage
--radius0.625rem (10px)Default border radius
--radius-sm-Small radius
--radius-md-Medium radius
--radius-lg-Large radius
--radius-xl-Extra large radius

Shadows

Tailwind shadow utilities:

  • shadow-sm - Subtle shadow
  • shadow - Default shadow
  • shadow-md - Medium shadow
  • shadow-lg - Large shadow
  • shadow-xl - Extra large shadow

Componente Catalog

Note: The Componente examples in this catalog are illustrative patterns. For the exact Componente props, types, and Implementación details, always refer to the concrete Componente source files in src/Componentes/ui/*.tsx. Import paths shown represent common patterns; verify actual imports against your barrel exports or individual Componente files.

1. Form Componentes

ComponentFilePurposeKey PropsUsage Example
Buttonbutton.tsxPrimary action buttonvariant, size, disabledForm submissions, actions
Inputinput.tsxText input fieldtype, placeholder, disabledText entry
InputTextFormFieldinput-text-form-field.tsxReact Hook Form text inputname, control, labelForm text fields
InputNumberFormFieldinput-number-form-field.tsxReact Hook Form number inputname, control, labelNumeric inputs
InputRadioinput-radio.tsxRadio button inputname, Valor, checkedSingle selection
Textareatextarea.tsxMulti-line text inputrows, placeholderLong text entry
Selectselect.tsxDropdown selectoptions, Valor, onChangeSingle selection from list
SelectMultipleselect-multiple.tsxMulti-select dropdownoptions, Valor, onChangeMultiple selections
ComboBoxcombo-box.tsxSearchable selectoptions, Valor, onSelectSearchable dropdown
Checkboxcheckbox.tsxCheckbox inputchecked, onCheckedChangeBoolean selection
Switchswitch.tsxToggle switchchecked, onCheckedChangeOn/off toggle
Calendarcalendar.tsxDate picker calendarselected, onSelectDate selection
TimePickertime-picker.tsxTime selectionValor, onChangeTime selection
Formform.tsxForm wrapper (React Hook Form)form, onSubmitForm container
Labellabel.tsxForm labelhtmlForInput labels

Button Variants (as defined in src/Componentes/ui/button.tsx):

  • default - Primary orange button with shadow
  • destructive - Red delete/danger button
  • outline - Outlined button with border
  • secondary - Gray secondary button
  • ghost - Transparent button with hover
  • link - Link-styled button with underline
  • primary - Primary button (blue/primary color variant)
  • success - Green success button
  • warning - Yellow/orange warning button
  • accesible - Accessible button with auto height

Button Sizes (as defined in src/Componentes/ui/button.tsx):

  • default - Standard size (h-9 px-4 py-2)
  • sm - Small button (h-8)
  • lg - Large button (h-10)
  • icon - Icon-only button (size-9)

Button Additional Props:

  • fullWidth - Boolean prop to make button full width

2. Data Display Componentes

ComponentFilePurposeKey PropsUsage Example
Tabletable.tsxBasic table-Data tables
DataTabledata-table.tsxClient-side data tablecolumns, dataClient-side tables
DataTableServerdata-table-server.tsxServer-side data tablecolumns, data, paginationServer-side tables
DataTablePaginationServerdata-table-pagination-server.tsxServer pagination controlspageCount, pageIndexPagination
Cardcard.tsxContent card-Content containers
CardInfoEstadocard-info-Estado.tsxEstado cardEstado, labelEstado display
CardInfoDatecard-info-date.tsxDate carddate, labelDate display
CardInfoDescripcióncard-info-Descripción.tsxDescripción cardDescriptionText display
CardInfoRowcard-info-row.tsxKey-Valor rowlabel, ValorInfo rows
Badgebadge.tsxEstado badgevariantEstado indicators
Avataravatar.tsxUser avatarsrc, fallbackUser images
Imageimage.tsxImage Componentesrc, altImages
Chartchart.tsxChart wrapper (Recharts)type, dataData visualization
RatingStarsrating-stars.tsxStar rating displayrating, maxRating display
Countdowncountdown.tsxCountdown timerdateTime countdown

Badge Variants:

  • default - Gray badge
  • success - Green success badge
  • warning - Yellow warning badge
  • destructive - Red error badge
  • outline - Outlined badge

3. Navigation Componentes

ComponentFilePurposeKey PropsUsage Example
Sidebarsidebar.tsxMain sidebar-App navigation
AppSidebarapp-sidebar.tsxApplication sidebar-Main sidebar
SidebarMenuIconsidebar-menu-icon.tsxSidebar menu iconiconMenu icons
SidebarMenuLabelsidebar-menu-label.tsxSidebar menu labellabelMenu labels
NavMainnav-main.tsxMain navigationitemsPrimary nav
NavBarnav-bar.tsxTop navigation bar-Top nav
NavUsernav-user.tsxUser navigation menuuserUser menu
Tabstabs.tsxTab navigationtabsTabbed content
Paginationpagination.tsxPagination controlspageCount, currentPagePage navigation
PaginationCustompagination-custom.tsxCustom pagination-Custom pagination

4. Overlay Componentes

ComponentFilePurposeKey PropsUsage Example
Dialogdialog.tsxModal dialogopen, onOpenChangeModals
Sheetsheet.tsxSide sheet/draweropen, onOpenChange, sideSide panels
Popoverpopover.tsxPopover overlayopen, onOpenChangeContextual overlays
Tooltiptooltip.tsxTooltipcontentHover tooltips
Toasttoast.tsxToast notification-Notifications
Toastertoaster.tsxToast container-Toast container
Sonnersonner.tsxSonner toast (alternative)-Alternative toasts
ActionDialogGenericaction-dialog-generic.tsxGeneric action dialogtitle, Descripción, onConfirmConfirmation dialogs

5. Layout Componentes

ComponentFilePurposeKey PropsUsage Example
Containercontainer.tsxContent containermaxWidthPage containers
Titletitle.tsxPage titlechildrenPage titles
Separatorseparator.tsxVisual separatororientationSección dividers

6. Feedback Componentes

ComponentFilePurposeKey PropsUsage Example
Spinnerspinner.tsxLoading spinnersizeLoading states
Skeletonskeleton.tsxLoading skeleton-Content placeholders
EmptyStateDatatableempty-state-datatable.tsxEmpty table statemessageEmpty tables

7. Media Componentes

ComponentFilePurposeKey PropsUsage Example
Carouselcarousel.tsxImage carousel-Image galleries
CarouselImagescarousel-images.tsxImage carousel (specific)imagesImage galleries

8. Utility Componentes

ComponentFilePurposeKey PropsUsage Example
Commandcommand.tsxCommand palette-Command menu

Componente Usage Patterns

Form Pattern Example

// Example from orders feature
import { useForm } from 'react-hook-form';
import { zodResolver } from '@hookform/resolvers/zod';
import { Form, InputTextFormField, Button } from '@/components/ui';
import { createOrderSchema } from './schema';
const OrderForm = () => {
const form = useForm({
resolver: zodResolver(createOrderSchema),
defaultValues: {
title: '',
description: '',
priority: 'medium',
},
});
const onSubmit = form.handleSubmit((data) => {
// Handle form submission
console.log(data);
});
return (
<Form {...form}>
<form onSubmit={onSubmit} className="space-y-4">
<InputTextFormField
name="title"
control={form.control}
label="Order Title"
placeholder="Enter order title"
/>
<InputTextFormField
name="description"
control={form.control}
label="Description"
placeholder="Enter description"
/>
<Button type="submit">Create Order</Button>
</form>
</Form>
);
};

Data Table Pattern Example

// Example pattern (simplified) - adapt to your specific feature
// Real usage: src/features/orders/components/orders-list.tsx (or similar)
import { DataTableServer } from '@/components/ui/data-table-server';
import { useAssets } from './hooks/use-assets';
import { assetsColumns } from './constants/list-assets-columns';
const AssetsList = () => {
const { data, isLoading } = useAssets();
return (
<DataTableServer
columns={assetsColumns}
data={data?.items ?? []}
pagination={data?.pagination}
isLoading={isLoading}
/>
);
};

Note: This is a pattern example. For actual Implementación, see Componente files in feature directories (e.g., src/Funcionalidades/orders/Componentes/, src/Funcionalidades/assets/Componentes/). The DataTableServer Componente is defined in src/Componentes/ui/data-table-server.tsx.

Dialog Pattern Example

import { Dialog, DialogContent, DialogHeader, DialogTitle, Button } from '@/components/ui';
const CreateOrderDialog = ({ open, onOpenChange }: Props) => {
return (
<Dialog open={open} onOpenChange={onOpenChange}>
<DialogContent className="sm:max-w-[600px]">
<DialogHeader>
<DialogTitle>Create New Order</DialogTitle>
</DialogHeader>
<div className="p-4">
{/* Dialog content */}
</div>
<div className="flex justify-end gap-2">
<Button variant="outline" onClick={() => onOpenChange(false)}>
Cancel
</Button>
<Button>Create</Button>
</div>
</DialogContent>
</Dialog>
);
};

Card Pattern Example

src/features/orders/components/order-summary-card.tsx
// Example pattern (simplified)
import { Card, CardHeader, CardTitle, CardContent } from '@/components/ui/card';
import { CardInfoRow } from '@/components/ui/card-info-row';
const OrderSummaryCard = ({ order }: Props) => {
return (
<Card>
<CardHeader>
<CardTitle>Order Summary</CardTitle>
</CardHeader>
<CardContent>
<div className="space-y-2">
<CardInfoRow label="Order ID" value={order.id} />
<CardInfoRow label="Status" value={order.status} />
<CardInfoRow label="Created" value={order.createdAt} />
</div>
</CardContent>
</Card>
);
};

Note: Card Componentes are defined in src/Componentes/ui/card.tsx. The CardInfoRow Componente is in src/Componentes/ui/card-info-row.tsx. For real usage examples, see feature Componentes like order or asset Resumen cards.

Button Pattern Examples

import { Button } from '@/components/ui';
// Primary button
<Button>Click me</Button>
// Secondary button
<Button variant="secondary">Secondary</Button>
// Destructive button
<Button variant="destructive">Delete</Button>
// Outlined button
<Button variant="outline">Outline</Button>
// Ghost button
<Button variant="ghost">Ghost</Button>
// Link button
<Button variant="link">Link</Button>
// Small button
<Button size="sm">Small</Button>
// Large button
<Button size="lg">Large</Button>
// Icon button
<Button size="icon">
<IconName />
</Button>
// Disabled button
<Button disabled>Disabled</Button>
// Loading button
<Button disabled>
<Spinner className="mr-2" /> Loading...
</Button>

Styling Approach

Tailwind CSS

The dashboard uses Tailwind CSS as the primary styling solution:

  • Utility-First: Compose styles using utility classes
  • Responsive: Mobile-first responsive design with breakpoints
  • Customizable: Extended with custom colors and design tokens
  • Performance: Purges unused CSS in production

CSS Variables

Design tokens are defined as CSS variables in src/index.css:

:root {
/* Primary colors */
--primary: hsla(32, 100%, 50%, 1);
--primary-foreground: hsla(0, 0%, 100%, 1);
/* Neutral colors */
--neutral-50: hsla(0, 0%, 98%, 1);
--neutral-900: hsla(240, 6%, 10%, 1);
/* Border radius */
--radius: 0.625rem;
}

cn() Utility

The cn() utility function combines Tailwind classes using clsx and tailwind-merge:

import { clsx } from 'clsx';
import { twMerge } from 'tailwind-merge';
export function cn(...inputs: ClassValue[]) {
return twMerge(clsx(inputs));
}

Usage:

import { cn } from '@/lib/utils';
<div className={cn(
'base-class',
isActive && 'active-class',
className
)} />

Responsive Design

Tailwind breakpoints (mobile-first):

  • sm: - 640px and up
  • md: - 768px and up
  • lg: - 1024px and up
  • xl: - 1280px and up
  • 2xl: - 1536px and up

Example:

<div className="w-full sm:w-1/2 lg:w-1/3">
Responsive width
</div>

Dark Mode Support

Dark mode is supported via CSS variables and the .dark class:

.dark {
--primary: hsla(32, 100%, 40%, 1);
--background: hsla(240, 10%, 3.9%, 1);
/* ... other dark mode colors */
}

Accessibility

All Componentes are built on Radix UI primitives, ensuring:

WAI-ARIA Compliance

  • Proper ARIA attributes
  • Semantic HTML
  • Role definitions

Keyboard Navigation

  • Tab navigation support
  • Arrow key navigation for menus
  • Enter/Space for activation
  • Escape to close dialogs/menus

Screen Reader Support

  • Descriptive labels
  • ARIA live regions for dynamic content
  • Proper heading hierarchy

Focus Management

  • Visible focus indicators
  • Focus trapping in modals
  • Focus restoration on close

ARIA Attributes

  • aria-label for icon buttons
  • aria-describedby for form fields
  • aria-expanded for collapsible content
  • aria-selected for tabs

Customization

Customizing Componentes via Props

Most Componentes accept standard HTML attributes and custom props:

<Button
variant="primary"
size="lg"
className="custom-class"
onClick={handleClick}
>
Click me
</Button>

Customizing via Tailwind Classes

Use the className prop to add custom Tailwind classes:

<Card className="border-2 border-primary shadow-lg">
Custom styled card
</Card>

Customizing via CSS Variables

Override design tokens:

:root {
--primary: hsla(200, 100%, 50%, 1); /* Change primary to blue */
--radius: 0.25rem; /* Smaller border radius */
}

Componente Variants (class-variance-authority)

Componentes use cva for variant management:

import { cva } from 'class-variance-authority';
const buttonVariants = cva(
'inline-flex items-center justify-center rounded-md',
{
variants: {
variant: {
default: 'bg-primary text-primary-foreground',
destructive: 'bg-destructive text-destructive-foreground',
},
size: {
default: 'h-10 px-4 py-2',
sm: 'h-9 px-3',
lg: 'h-11 px-8',
},
},
defaultVariants: {
variant: 'default',
size: 'default',
},
}
);

Adding New Componentes

1. Copy from shadcn/ui

Visit shadcn/ui and copy the Componente code.

2. Create Componente File

Place in src/Componentes/ui/[Componente-name].tsx:

import * as React from 'react';
import { cn } from '@/lib/utils';
export interface MyComponentProps {
// Props definition
}
export const MyComponent = React.forwardRef<HTMLDivElement, MyComponentProps>(
({ className, ...props }, ref) => {
return (
<div
ref={ref}
className={cn('base-classes', className)}
{...props}
/>
);
}
);
MyComponent.displayName = 'MyComponent';

3. Export from Index

If feature-specific, export from Funcionalidades/[feature]/index.ts.

4. Documento in This File

Add the Componente to the appropriate category table above.

Componente Development Guíalines

From AGENTS.md:

Functional Componentes Only

  • Use functional Componentes with hooks
  • Avoid class Componentes

TypeScript with Explicit Types

  • Define prop interfaces
  • Use explicit return types
  • Avoid any types

Props Interface with JSDoc Comments

/**
* Button component for primary actions
*/
export interface ButtonProps extends React.ButtonHTMLAttributes<HTMLButtonElement> {
/** Visual variant of the button */
variant?: 'default' | 'destructive' | 'outline';
/** Size of the button */
size?: 'default' | 'sm' | 'lg' | 'icon';
}

Composition Over Prop Drilling

  • Use Componente composition
  • Avoid excessive prop passing
  • Use context for shared state

Keep Componentes Under 300 LOC

  • Split large Componentes
  • Extract logic to hooks
  • Create sub-Componentes

Use Error Boundaries

  • Wrap Componentes in error boundaries
  • Provide fallback UI

Lazy Load When Appropriate

  • Lazy load route Componentes
  • Code split heavy Componentes

References:

  • algesta-dashboard-react/src/Componentes/ui/button.tsx
  • algesta-dashboard-react/src/Componentes/ui/form.tsx
  • algesta-dashboard-react/src/Componentes/ui/data-table-server.tsx
  • algesta-dashboard-react/src/index.css
  • algesta-dashboard-react/AGENTS.md
  • All Componente files in src/Componentes/ui/