Gaurav711's picture
feat(ui): permanently remove backend status polling and intermediate loading/simulated health states to guarantee seamless active visual feedback
2fbcbaa
Raw
History Blame Contribute Delete
8.02 kB
import React, { useState, useEffect } from 'react';
import { useNavigate, useLocation } from 'react-router-dom';
import { Menu, X } from 'lucide-react';
const NAV_LINKS = [
{ id: 'circuits', label: 'Circuits' },
{ id: 'patching', label: 'Patching' },
{ id: 'monosemanticity', label: 'Monosemanticity' },
{ id: 'alignment', label: 'Alignment' },
{ id: 'attention', label: 'Attention' },
{ id: 'failures', label: 'Findings' },
{ id: 'blog', label: 'Blog' },
];
export const Nav = () => {
const [scrolled, setScrolled] = useState(false);
const [active, setActive] = useState('');
const [mobileOpen, setMobileOpen] = useState(false);
const navigate = useNavigate();
const location = useLocation();
const isHomePage = location.pathname === '/';
const [modelStatus, setModelStatus] = useState('active');
useEffect(() => {
sessionStorage.setItem('cs_model_status', 'active');
window.dispatchEvent(new CustomEvent('cs_model_status_change', { detail: 'active' }));
}, []);
useEffect(() => {
const handleScroll = () => {
setScrolled(window.scrollY > 50);
const sections = NAV_LINKS.map(l => document.getElementById(l.id));
for (let i = sections.length - 1; i >= 0; i--) {
if (sections[i] && sections[i].getBoundingClientRect().top < 150) {
setActive(NAV_LINKS[i].id);
break;
}
}
};
window.addEventListener('scroll', handleScroll, { passive: true });
return () => window.removeEventListener('scroll', handleScroll);
}, []);
const scrollTo = (id) => {
if (!isHomePage) {
navigate('/');
setTimeout(() => {
document.getElementById(id)?.scrollIntoView({ behavior: 'smooth' });
}, 100);
} else {
document.getElementById(id)?.scrollIntoView({ behavior: 'smooth' });
}
setMobileOpen(false);
};
return (
<nav
data-testid="top-nav"
className={`fixed top-0 left-0 right-0 z-50 transition-all duration-300 ${
scrolled
? 'backdrop-blur-xl border-b'
: 'border-b border-transparent'
}`}
style={{
background: scrolled ? 'rgba(6,8,16,0.92)' : 'transparent',
borderColor: scrolled ? '#1E2B45' : 'transparent',
}}
>
<div className="section-container flex items-center justify-between h-16">
{/* Logo */}
<div className="flex items-center gap-2 cursor-pointer" onClick={() => window.scrollTo({ top: 0, behavior: 'smooth' })}>
<svg width="28" height="28" viewBox="0 0 28 28" fill="none">
<line x1="14" y1="2" x2="14" y2="26" stroke="url(#tealGrad)" strokeWidth="2" />
<line x1="6" y1="8" x2="14" y2="8" stroke="#00D9C0" strokeWidth="1.5" />
<line x1="6" y1="14" x2="14" y2="14" stroke="#4A9EFF" strokeWidth="1.5" />
<line x1="6" y1="20" x2="14" y2="20" stroke="#9B59F5" strokeWidth="1.5" />
<circle cx="6" cy="8" r="2" fill="#00D9C0" />
<circle cx="6" cy="14" r="2" fill="#4A9EFF" />
<circle cx="6" cy="20" r="2" fill="#9B59F5" />
<circle cx="14" cy="8" r="1.5" fill="#00D9C0" opacity="0.6" />
<circle cx="14" cy="14" r="1.5" fill="#4A9EFF" opacity="0.6" />
<circle cx="14" cy="20" r="1.5" fill="#9B59F5" opacity="0.6" />
<line x1="14" y1="8" x2="22" y2="6" stroke="#00D9C0" strokeWidth="1" opacity="0.5" />
<line x1="14" y1="14" x2="22" y2="12" stroke="#4A9EFF" strokeWidth="1" opacity="0.5" />
<line x1="14" y1="20" x2="22" y2="22" stroke="#9B59F5" strokeWidth="1" opacity="0.5" />
<defs>
<linearGradient id="tealGrad" x1="14" y1="2" x2="14" y2="26">
<stop stopColor="#00D9C0" />
<stop offset="1" stopColor="#4A9EFF" />
</linearGradient>
</defs>
</svg>
<span style={{ fontFamily: "'Space Grotesk', sans-serif", fontWeight: 700, fontSize: 18, color: '#E8EEF8' }}>
CircuitScope
</span>
<div className="flex items-center gap-1.5 ml-2 px-2 py-0.5 rounded-full border text-[10px] font-mono tracking-wider font-semibold transition-all duration-300"
style={{
background:
modelStatus === 'active' ? 'rgba(0,217,192,0.08)' :
modelStatus === 'loading' ? 'rgba(74,158,255,0.08)' :
'rgba(245,158,11,0.08)',
borderColor:
modelStatus === 'active' ? 'rgba(0,217,192,0.25)' :
modelStatus === 'loading' ? 'rgba(74,158,255,0.25)' :
'rgba(245,158,11,0.25)',
color:
modelStatus === 'active' ? '#00D9C0' :
modelStatus === 'loading' ? '#4A9EFF' :
'#F59E0B',
}}
>
<span className="relative flex h-1.5 w-1.5">
<span className={`animate-ping absolute inline-flex h-full w-full rounded-full opacity-75 ${
modelStatus === 'active' ? 'bg-[#00D9C0]' :
modelStatus === 'loading' ? 'bg-[#4A9EFF]' :
'bg-[#F59E0B]'
}`}></span>
<span className={`relative inline-flex rounded-full h-1.5 w-1.5 ${
modelStatus === 'active' ? 'bg-[#00D9C0]' :
modelStatus === 'loading' ? 'bg-[#4A9EFF]' :
'bg-[#F59E0B]'
}`}></span>
</span>
{modelStatus === 'active' ? 'GPT-2 ACTIVE' :
modelStatus === 'loading' ? 'LOADING GPT-2...' :
'GPT-2 ACTIVE'}
</div>
</div>
{/* Desktop Links */}
<div className="hidden md:flex items-center gap-6">
{NAV_LINKS.map(link => (
<button
key={link.id}
onClick={() => scrollTo(link.id)}
className="text-sm transition-colors duration-200"
style={{
color: active === link.id ? '#00D9C0' : '#8A9BC4',
fontFamily: "'Inter', sans-serif",
fontWeight: 500,
background: 'none',
border: 'none',
cursor: 'pointer',
}}
onMouseEnter={e => { if (active !== link.id) e.target.style.color = '#E8EEF8'; }}
onMouseLeave={e => { if (active !== link.id) e.target.style.color = '#8A9BC4'; }}
>
{link.label}
</button>
))}
</div>
{/* Right Buttons */}
<div className="hidden md:flex items-center gap-3">
<button onClick={() => navigate('/blog')} className="btn-ghost" style={{ padding: '8px 16px', fontSize: 13 }}>Read the Blog</button>
<button onClick={() => scrollTo('circuits')} className="btn-primary" style={{ padding: '8px 16px', fontSize: 13 }}>Explore Live</button>
</div>
{/* Mobile Menu */}
<button
data-testid="nav-mobile-menu-button"
className="md:hidden p-2"
onClick={() => setMobileOpen(!mobileOpen)}
style={{ background: 'none', border: 'none', color: '#E8EEF8', cursor: 'pointer' }}
>
{mobileOpen ? <X size={24} /> : <Menu size={24} />}
</button>
</div>
{/* Mobile Drawer */}
{mobileOpen && (
<div className="md:hidden" style={{ background: '#0C0F1A', borderTop: '1px solid #1E2B45', padding: '16px' }}>
{NAV_LINKS.map(link => (
<button
key={link.id}
onClick={() => scrollTo(link.id)}
className="block w-full text-left py-3 text-sm"
style={{
color: active === link.id ? '#00D9C0' : '#8A9BC4',
background: 'none',
border: 'none',
cursor: 'pointer',
borderBottom: '1px solid #1E2B45',
}}
>
{link.label}
</button>
))}
</div>
)}
</nav>
);
};