// Hero section with dashboard mockup const { useState: useStateHero, useEffect: useEffectHero, useRef: useRefHero } = React; function AnimatedNumber({ to, duration = 1200, prefix = '', suffix = '', decimals = 0, trigger }) { const [val, setVal] = useStateHero(0); const startedRef = useRefHero(false); useEffectHero(() => { if (!trigger || startedRef.current) return; startedRef.current = true; const start = performance.now(); const from = 0; const tick = (now) => { const t = Math.min(1, (now - start) / duration); const eased = 1 - Math.pow(1 - t, 3); setVal(from + (to - from) * eased); if (t < 1) requestAnimationFrame(tick); }; requestAnimationFrame(tick); }, [trigger, to, duration]); const formatted = val.toLocaleString('es-ES', { minimumFractionDigits: decimals, maximumFractionDigits: decimals, }); return {prefix}{formatted}{suffix}; } function DashboardMockup() { const [play, setPlay] = useStateHero(false); const ref = useRefHero(null); useEffectHero(() => { const obs = new IntersectionObserver((entries) => { entries.forEach((e) => { if (e.isIntersecting) setPlay(true); }); }, { threshold: 0.3 }); if (ref.current) obs.observe(ref.current); return () => obs.disconnect(); }, []); // Growth chart data (monthly net worth) const data = [42, 45, 48, 47, 52, 55, 58, 62, 66, 71, 75, 82]; const max = Math.max(...data); const min = Math.min(...data); const w = 520; const h = 180; const pts = data.map((v, i) => { const x = (i / (data.length - 1)) * w; const y = h - ((v - min) / (max - min)) * (h - 20) - 10; return [x, y]; }); const path = pts.map((p, i) => (i === 0 ? `M${p[0]},${p[1]}` : `L${p[0]},${p[1]}`)).join(' '); const areaPath = `${path} L${w},${h} L0,${h} Z`; return (
Te ayudamos a organizar tu dinero, ahorrar en comisiones y construir patrimonio. Sin conflictos de interés, porque no vendemos productos.
{/* CTAs */} {/* Trust row */}