arbritage/layouts/Sidebar.tsx

110 lines
6.1 KiB
TypeScript
Raw Normal View History

2026-01-26 14:20:25 +00:00
import React from 'react';
import { NavLink } from 'react-router-dom';
import { LayoutDashboard, Search, History, Boxes, Store, Users, TrendingUp, LogOut, Wallet, ShoppingCart, Package, BarChart3, Settings } from 'lucide-react';
import { useCRM } from '../context/CRMContext';
import clsx from 'clsx';
interface SidebarProps {
isOpen?: boolean;
onClose?: () => void;
}
const Sidebar: React.FC<SidebarProps> = ({ isOpen = false, onClose }) => {
const { user, isAdmin, signOut } = useCRM();
const currentUser = user;
const navItems = [
{ to: '/', icon: LayoutDashboard, label: 'Dashboard' },
{ to: '/sales', icon: ShoppingCart, label: 'Vendas' },
{ to: '/sourcing', icon: Search, label: 'Sourcing' },
{ to: '/products', icon: Package, label: 'Produtos' },
{ to: '/orders', icon: History, label: 'Pedidos' },
{ to: '/financial', icon: Wallet, label: 'Financeiro' },
{ to: '/customers', icon: Users, label: 'Clientes' },
{ to: '/inventory', icon: Boxes, label: 'Estoque' },
{ to: '/suppliers', icon: Store, label: 'Fornecedores' },
{ to: '/reports', icon: BarChart3, label: 'Relatórios' },
{ to: '/users', icon: Users, label: 'Usuários' },
{ to: '/settings', icon: Settings, label: 'Configurações' }
];
return (
<>
{/* Mobile Overlay */}
{isOpen && (
<div
className="fixed inset-0 bg-black/60 backdrop-blur-sm z-40 md:hidden"
onClick={onClose}
/>
)}
<aside className={clsx(
"fixed inset-y-0 left-0 z-50 w-64 bg-card/95 backdrop-blur-xl border-r border-border flex flex-col justify-between transition-transform duration-300 md:translate-x-0 md:relative md:bg-card/80",
isOpen ? "translate-x-0" : "-translate-x-full"
)}>
<div>
{/* Logo Area */}
<div className="h-20 flex items-center justify-between px-6 md:justify-start md:px-8 border-b border-border">
<div className="flex items-center">
<div className="w-10 h-10 bg-gradient-to-br from-indigo-500 to-purple-600 rounded-xl flex items-center justify-center shadow-lg shadow-indigo-500/20">
<span className="text-white font-bold text-xl">P</span>
</div>
<span className="block ml-3 font-bold text-lg bg-clip-text text-transparent bg-gradient-to-r from-white to-slate-400">
Paraguai
</span>
</div>
{/* Close button for mobile only */}
<button onClick={onClose} className="md:hidden text-muted-foreground hover:text-foreground">
<span className="sr-only">Fechar</span>
{/* Using a simple X approach manually or just relying on overlay */}
<svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="2" strokeLinecap="round" strokeLinejoin="round"><path d="M18 6 6 18" /><path d="m6 6 18 18" /></svg>
</button>
</div>
</div>
{/* NAV */}
<nav className="flex-grow px-4 space-y-1 overflow-y-auto pt-4">
<div className="text-[10px] font-bold text-muted-foreground uppercase tracking-widest px-4 mb-3 opacity-50">Menu</div>
{navItems.filter(item => item.label !== 'Usuários' || isAdmin).map((item) => (
<NavLink
key={item.to}
to={item.to}
onClick={onClose} // Auto close on mobile nav click
className={({ isActive }) => clsx(
"group flex items-center gap-3 px-4 py-3 rounded-xl text-sm font-medium transition-all duration-200 outline-none",
isActive
? 'bg-secondary text-foreground shadow-sm'
: 'text-muted-foreground hover:text-foreground hover:bg-secondary/50'
)}
>
{({ isActive }) => (
<>
<item.icon size={18} className={clsx("transition-transform group-hover:scale-110", isActive ? "text-foreground" : "text-muted-foreground")} />
<span>{item.label}</span>
{isActive && <div className="ml-auto w-1.5 h-1.5 rounded-full bg-foreground shadow-[0_0_8px_rgba(255,255,255,0.5)]"></div>}
</>
)}
</NavLink>
))}
</nav>
{/* USER FOOTER */}
<div className="p-6 border-t border-border mt-auto bg-card/50">
<div onClick={signOut} className="flex items-center gap-3 p-3 rounded-2xl bg-secondary/30 border border-border/50 hover:bg-secondary/50 transition-colors cursor-pointer group">
<div className="w-9 h-9 rounded-full overflow-hidden border border-border ring-2 ring-transparent group-hover:ring-border/50 transition-all">
<img src={currentUser?.avatar || "https://api.dicebear.com/7.x/avataaars/svg?seed=Admin"} alt="User" />
</div>
<div className="flex-1 min-w-0">
<p className="text-sm font-bold text-foreground truncate">{currentUser?.name || "Admin"}</p>
<p className="text-[10px] text-muted-foreground truncate">Administrador</p>
</div>
<LogOut size={14} className="text-muted-foreground group-hover:text-destructive transition-colors" />
</div>
</div>
</aside>
</>
);
};
export default Sidebar;