/* SolucionPage — shared component rendering one solution-category page from data. */ const { useEffect: useEffectSP, useRef: useRefSP, useState: useStateSP } = React; /* ---------- Logo (same as home) ---------- */ const LogoSP = ({ size = 32 }) => ( ); /* ---------- Navbar (mega-menu, sub-page) ---------- */ const NavbarSol = ({ currentKey }) => { const ctx = window.useMegaMenuMM(); return ( ); }; /* ---------- FadeUp (local copy — BlurText.jsx defines it but we want to be explicit) ---------- */ const FadeUpSP = window.FadeUp || (({ children, delay = 0, className = '' }) => { const ref = useRefSP(null); const [visible, setVisible] = useStateSP(false); useEffectSP(() => { const el = ref.current; if (!el) return; const io = new IntersectionObserver(([e]) => { if (e.isIntersecting) { setVisible(true); io.disconnect(); } }, { threshold: 0.1 }); io.observe(el); return () => io.disconnect(); }, []); return (
{children}
); }); /* ---------- Breadcrumb ---------- */ const Breadcrumb = ({ label }) => ( ); /* ---------- Hero ---------- */ const SolHero = ({ d }) => (
{d.eyebrow}

{d.h1}

{d.sub}

{d.stats}
); /* ---------- Problem ---------- */ const SolProblem = ({ d }) => (
El problema hoy

¿Te suena alguno de estos?

{d.problems.map((it, i) => { const I = iconFromName(it.icon); return (

{it.title}

{it.body}

); })}
); /* ---------- Workflows ---------- */ const SolWorkflows = ({ d }) => (
Workflows de esta categoría

Tres automatizaciones que resuelven el 80% del trabajo repetitivo.

{d.workflows.map((w, i) => ( ))}
); const WorkflowDetailCard = ({ w }) => (
#{w.id}

{w.title}

{w.desc}

{w.stack.map((s, i) => ( {s} ))}
); /* ---------- Stack técnico ---------- */ const SolStack = ({ d }) => (
Stack técnico

Las herramientas que operamos en esta categoría.

{d.stack.map((s, i) => { const Icon = iconFromName(s.icon); return (

{s.title}

{s.desc}

); })}
); /* ---------- Timeline (4 weeks) ---------- */ const SolTimeline = ({ d }) => (
Proceso

De diagnóstico a producción en 4 semanas.

{d.timeline.map((s, i) => (
{s.w}

{s.title}

{s.body}

))}
); /* ---------- Case study ---------- */ const SolCaseStudy = ({ d }) => (
Caso típico

{d.caseStudy.profile}

{d.caseStudy.disclaimer}

{d.caseStudy.cols.map((c, i) => { const cls = c.label.toLowerCase() .normalize('NFD').replace(/[\u0300-\u036f]/g, ''); return (
{c.label}

{c.body}

); })}
); /* ---------- Related solutions ---------- */ const SolRelated = ({ d, currentKey }) => { const all = window.SOLUCIONES_DATA; const others = (d.related || []).filter(k => k !== currentKey).map(k => all[k]).filter(Boolean); return (
Otras soluciones

Otras categorías que resolvemos.

{others.map((o, i) => { const Icon = iconFromName(o.icon); return (

{o.label}

{o.sub.split('.')[0] + '.'}

); })}
); }; /* ---------- Final CTA ---------- */ const SolCTA = ({ d }) => (
¿Empezamos?

Diagnóstico gratis sobre tu proceso de {d.category}.

30 minutos. Mapeamos lo automatizable, priorizamos por ROI y te decimos qué workflow construir primero.

); /* ---------- Footer ---------- */ const SolFooter = () => { const [emailValue, setEmailValue] = useStateSP(''); const [newsletterStatus, setNewsletterStatus] = useStateSP('idle'); const currentYear = new Date().getFullYear(); const prefix = '../'; return ( ); }; /* ---------- WhatsApp Floating Button ---------- */ const WhatsAppFloatSP = () => ( ); /* ---------- Page composition ---------- */ const SolucionPage = ({ data }) => ( <> ); /* ---------- Global parallax (same as home App.jsx) ---------- */ function useGlobalParallaxSP() { useEffectSP(() => { const reduced = window.matchMedia('(prefers-reduced-motion: reduce)').matches; if (reduced) return; let raf = 0; function onScroll() { if (raf) return; raf = requestAnimationFrame(() => { const items = document.querySelectorAll('[data-parallax]'); const y = window.scrollY; items.forEach(el => { const speed = parseFloat(el.dataset.parallax) || 0.3; const base = el.dataset.parallaxBase || ''; el.style.transform = `${base} translate3d(0, ${y * speed}px, 0)`; }); raf = 0; }); } window.addEventListener('scroll', onScroll, { passive: true }); onScroll(); return () => window.removeEventListener('scroll', onScroll); }, []); } window.SolucionPage = SolucionPage; window.useGlobalParallaxSP = useGlobalParallaxSP;