161 lines
5.6 KiB
TypeScript
161 lines
5.6 KiB
TypeScript
import React, { useState, useEffect } from 'react';
|
|
import { Menu, X, Scale, Search } from 'lucide-react';
|
|
import { Link, useLocation, useNavigate } from 'react-router-dom';
|
|
import { cn } from '../../lib/utils';
|
|
|
|
export function Navbar() {
|
|
const [isScrolled, setIsScrolled] = useState(false);
|
|
const [isMobileMenuOpen, setIsMobileMenuOpen] = useState(false);
|
|
const location = useLocation();
|
|
const navigate = useNavigate();
|
|
|
|
useEffect(() => {
|
|
const handleScroll = () => {
|
|
setIsScrolled(window.scrollY > 10);
|
|
};
|
|
window.addEventListener('scroll', handleScroll);
|
|
return () => window.removeEventListener('scroll', handleScroll);
|
|
}, []);
|
|
|
|
// Handle hash scrolling when navigating across pages
|
|
useEffect(() => {
|
|
if (location.hash) {
|
|
const element = document.querySelector(location.hash);
|
|
if (element) {
|
|
setTimeout(() => {
|
|
element.scrollIntoView({ behavior: 'smooth' });
|
|
}, 100);
|
|
}
|
|
} else {
|
|
window.scrollTo(0,0);
|
|
}
|
|
}, [location]);
|
|
|
|
const handleNavClick = (e: React.MouseEvent<HTMLAnchorElement>, href: string) => {
|
|
setIsMobileMenuOpen(false);
|
|
if (href.startsWith('/#')) {
|
|
const hash = href.substring(1);
|
|
if (location.pathname === '/') {
|
|
e.preventDefault();
|
|
const element = document.querySelector(hash);
|
|
if (element) {
|
|
element.scrollIntoView({ behavior: 'smooth' });
|
|
// Update URL hash without jumping
|
|
window.history.pushState(null, '', hash);
|
|
}
|
|
} else {
|
|
// Let it navigate to /#hash normally
|
|
}
|
|
}
|
|
};
|
|
|
|
const navLinks = [
|
|
{ name: 'Sobre', href: '/sobre' },
|
|
{ name: 'Áreas de Atuação', href: '/areas' },
|
|
{ name: 'Como Funciona', href: '/funcionamento' },
|
|
{ name: 'Blog', href: '/blog' },
|
|
{ name: 'Contato', href: '/contato' },
|
|
];
|
|
|
|
return (
|
|
<nav
|
|
className={cn(
|
|
'fixed left-0 right-0 top-0 z-50 transition-all duration-300',
|
|
isScrolled
|
|
? 'bg-white shadow-md py-3'
|
|
: 'bg-brand-blue py-5 text-white'
|
|
)}
|
|
>
|
|
<div className="mx-auto flex max-w-7xl items-center justify-between px-6 lg:px-8">
|
|
<Link to="/" className="flex items-center gap-2">
|
|
<Scale className={cn("h-8 w-8", isScrolled ? "text-brand-gold" : "text-brand-gold")} />
|
|
<div className="flex flex-col">
|
|
<span className={cn("font-serif text-xl font-bold leading-none tracking-tight", isScrolled ? "text-brand-blue" : "text-white")}>
|
|
João Silva
|
|
</span>
|
|
<span className={cn("text-xs font-medium tracking-widest", isScrolled ? "text-gray-500" : "text-gray-300")}>
|
|
ADVOGADO
|
|
</span>
|
|
</div>
|
|
</Link>
|
|
|
|
{/* Desktop Nav */}
|
|
<div className="hidden items-center gap-8 md:flex">
|
|
{navLinks.map((link) => (
|
|
<Link
|
|
key={link.name}
|
|
to={link.href}
|
|
onClick={(e) => handleNavClick(e, link.href)}
|
|
className={cn(
|
|
'text-sm font-medium transition-colors hover:text-brand-gold',
|
|
isScrolled ? 'text-gray-700' : 'text-gray-200'
|
|
)}
|
|
>
|
|
{link.name}
|
|
</Link>
|
|
))}
|
|
<div className="flex items-center gap-6 border-l border-white/20 pl-6">
|
|
<Link
|
|
to="/blog?focus=true"
|
|
title="Buscar Artigos"
|
|
className={cn(
|
|
'transition-colors hover:text-brand-gold',
|
|
isScrolled ? 'text-brand-blue' : 'text-white'
|
|
)}
|
|
>
|
|
<Search className="h-5 w-5" />
|
|
</Link>
|
|
<Link
|
|
to="/contato"
|
|
className="rounded-none border-2 border-brand-gold bg-brand-gold px-6 py-2 text-sm font-semibold text-white transition-colors hover:bg-transparent hover:text-brand-gold"
|
|
>
|
|
Consulta Online
|
|
</Link>
|
|
</div>
|
|
</div>
|
|
|
|
{/* Mobile Nav Toggle */}
|
|
<button
|
|
className="md:hidden"
|
|
onClick={() => setIsMobileMenuOpen(!isMobileMenuOpen)}
|
|
>
|
|
{isMobileMenuOpen ? (
|
|
<X className={cn("h-6 w-6", isScrolled ? "text-brand-blue" : "text-white")} />
|
|
) : (
|
|
<Menu className={cn("h-6 w-6", isScrolled ? "text-brand-blue" : "text-white")} />
|
|
)}
|
|
</button>
|
|
</div>
|
|
|
|
{/* Mobile Menu */}
|
|
{isMobileMenuOpen && (
|
|
<div className="absolute left-0 right-0 top-full flex flex-col items-center gap-6 bg-white py-8 shadow-xl md:hidden">
|
|
{navLinks.map((link) => (
|
|
<Link
|
|
key={link.name}
|
|
to={link.href}
|
|
onClick={(e) => handleNavClick(e, link.href)}
|
|
className="text-base font-medium text-gray-800 transition-colors hover:text-brand-gold"
|
|
>
|
|
{link.name}
|
|
</Link>
|
|
))}
|
|
<Link
|
|
to="/blog?focus=true"
|
|
onClick={() => setIsMobileMenuOpen(false)}
|
|
className="flex items-center gap-2 text-base font-medium text-gray-800 transition-colors hover:text-brand-gold"
|
|
>
|
|
<Search className="h-5 w-5" /> Buscar Artigo
|
|
</Link>
|
|
<Link
|
|
to="/contato"
|
|
onClick={() => setIsMobileMenuOpen(false)}
|
|
className="mt-4 rounded-none border-2 border-brand-gold bg-brand-gold px-8 py-3 text-base font-semibold text-white transition-colors hover:bg-white hover:text-brand-gold"
|
|
>
|
|
Consulta Online
|
|
</Link>
|
|
</div>
|
|
)}
|
|
</nav>
|
|
);
|
|
}
|