6.0 KiB
Button Component Standardization - Complete
Overview
Fixed Button component and all Sites pages to match IGNY8 global design standard:
- Secondary button color now uses
text-dim(#64748b) - Removed ALL
Linkcomponent usage from buttons - All buttons now use
onClicknavigation withuseNavigate()
Changes Made
1. Button Component (/frontend/src/components/ui/button/Button.tsx)
Removed Link/Anchor Support
- Removed imports:
Linkfrom react-router-dom - Removed props:
as,href,to,target,rel - Simplified component: Always renders
<button>element (no conditional rendering) - Result: Button component ONLY supports
onClicknavigation
Fixed Secondary Color
Changed ALL secondary variants to use text-dim color (#64748b):
Before (WRONG):
brand: {
secondary: "bg-brand-50 text-brand-600 hover:bg-brand-100"
}
success: {
secondary: "bg-success-50 text-success-600 hover:bg-success-100"
}
// etc...
After (CORRECT):
brand: {
secondary: "bg-transparent text-[#64748b] hover:bg-gray-100 dark:hover:bg-white/[0.08]"
}
success: {
secondary: "bg-transparent text-[#64748b] hover:bg-gray-100 dark:hover:bg-white/[0.08]"
}
// etc...
Affected tones:
- ✅ brand
- ✅ success
- ✅ warning
- ✅ danger
- ✅ neutral (already correct)
2. Sites Pages - Removed All Link Usage
Dashboard.tsx (/frontend/src/pages/Sites/Dashboard.tsx)
- Removed import:
Linkfrom react-router-dom - Changed: 5 Quick Action cards from
<Link to={...}>to<button onClick={() => navigate(...)}>> - Actions updated:
- Manage Pages
- Manage Content
- Integrations
- Sync Dashboard
- Deploy Site
Before:
<Link to={`/sites/${siteId}/pages`} className="...">
{/* card content */}
</Link>
After:
<button onClick={() => navigate(`/sites/${siteId}/pages`)} className="...">
{/* card content */}
</button>
List.tsx (/frontend/src/pages/Sites/List.tsx)
- Removed import:
Linkfrom react-router-dom - Changed: Site card buttons from
Button as={Link} to={...}toButton onClick={() => navigate(...)} - Buttons updated:
- Dashboard (primary variant)
- Content (secondary variant)
- Pages (secondary variant)
- Settings (secondary variant)
Before:
<Button
as={Link}
to={`/sites/${site.id}`}
variant="primary"
size="sm"
startIcon={<EyeIcon className="w-4 h-4" />}
>
Dashboard
</Button>
After:
<Button
onClick={() => navigate(`/sites/${site.id}`)}
variant="primary"
size="sm"
startIcon={<EyeIcon className="w-4 h-4" />}
>
Dashboard
</Button>
Content.tsx (/frontend/src/pages/Sites/Content.tsx)
- Removed import:
Linkfrom react-router-dom - Changed: 2 buttons from
Button as={Link}toButton onClick - Buttons updated:
- "New Post" button (top of page)
- "Create Your First Post" button (empty state)
Editor.tsx (/frontend/src/pages/Sites/Editor.tsx)
- Removed import:
Linkfrom react-router-dom (was imported but not yet used)
Verification
TypeScript Compilation
✅ No errors found in:
/frontend/src/components/ui/button/Button.tsx/frontend/src/pages/Sites/Dashboard.tsx/frontend/src/pages/Sites/List.tsx/frontend/src/pages/Sites/Content.tsx/frontend/src/pages/Sites/Editor.tsx
Code Search
✅ No remaining instances of:
<Button as={Link}in Sites pagesButton.*as={Link}anywhere in frontend
Button Standard Summary
Correct Usage (ONLY allowed format)
import { Button } from '@/components/ui/button/Button';
import { useNavigate } from 'react-router-dom';
const navigate = useNavigate();
// Simple button
<Button onClick={() => navigate('/path')} variant="primary">
Click Me
</Button>
// Button with icon
<Button
onClick={() => navigate('/path')}
variant="secondary"
startIcon={<IconComponent className="w-4 h-4" />}
>
Action
</Button>
// Multiple buttons (primary + secondary)
<div className="flex gap-2">
<Button onClick={handlePrimary} variant="primary">
Primary Action
</Button>
<Button onClick={handleSecondary} variant="secondary">
Secondary Action
</Button>
</div>
Variants
- primary: Brand color background (#0693e3), white text
- secondary: Text-dim color (#64748b), transparent background, gray hover
- outline: Colored text with ring border
- ghost: Colored text with subtle hover
- gradient: Gradient background with shadow
Tones
- brand: Primary blue (#0693e3)
- success: Teal-green (#0bbf87)
- warning: Vivid orange (#ff7a00)
- danger: Red (#ef4444)
- neutral: Gray
Sizes
- xs: h-7 px-2.5 text-xs
- sm: h-9 px-3 text-sm (most common)
- md: h-10 px-4 text-sm
- lg: h-12 px-5 text-base
Color Reference
Text-Dim Color
/* tokens.css */
--color-text-dim: #64748b; /* Light mode */
.dark {
--color-text-dim: #9ca3af; /* Dark mode */
}
This is Tailwind's slate-500 equivalent, used for:
- Secondary button text
- Subdued/helper text
- Less prominent UI elements
What Was Wrong Before
- Secondary color mismatch: Used tone-specific colors (brand-600, success-600, etc.) instead of universal text-dim
- Link component usage: Button component had
as={Link}prop support (accessibility anti-pattern for navigation buttons) - Mixed patterns: Some pages used
<Link>, others usedButton as={Link}, creating inconsistency - Wrong variants: Some buttons still used old "solid"/"soft" names
Result
✅ Consistent design: All secondary buttons now have same text-dim color across all tones
✅ Single pattern: ALL buttons use onClick with useNavigate() - no Link components
✅ Proper semantics: Navigation uses button elements with click handlers (matches HTML standard)
✅ Type safe: Removed unnecessary props from Button component
✅ Maintainable: Single source of truth for button styles in Button.tsx
Date: 2024 Status: ✅ Complete - All Sites pages standardized