// waiv-factory.jsx — pinned, scroll-scrubbed "making of a waiv" scene.
// Blank → UV print → chip embed → finish → activate → a dimensional tunnel of
// cards flowing toward the viewer → the finished card resolves. Lusion-flavoured.

(function () {
  const { useRef, useEffect } = React;
  const clamp = (v, a, b) => Math.min(b, Math.max(a, v));
  const ease = t => t * t * (3 - 2 * t);
  const es = (p, a, b) => ease(clamp((p - a) / (b - a), 0, 1));
  const ss = (x, a, b) => { const t = clamp((x - a) / (b - a), 0, 1); return t * t * (3 - 2 * t); };
  const mix = (a, b, t) => a + (b - a) * t;
  const frac = x => x - Math.floor(x);

  const FINISHES = [
    'radial-gradient(135% 110% at 18% -5%,rgba(255,231,170,.26),transparent 52%),linear-gradient(125deg,#11203f,#26406a 46%,#02060f)',
    'radial-gradient(135% 110% at 18% -5%,rgba(180,205,255,.4),transparent 52%),linear-gradient(125deg,#0a2a8a,#2f6ff0 46%,#040d2b)',
    'radial-gradient(135% 110% at 18% -5%,rgba(255,180,180,.3),transparent 52%),linear-gradient(125deg,#3a0a10,#b3202a 46%,#1a0305)',
    'radial-gradient(135% 110% at 18% -5%,rgba(255,255,255,.6),transparent 55%),linear-gradient(125deg,#9fc4cd,#eef6f8 46%,#86acb6)',
    'radial-gradient(135% 110% at 18% -5%,rgba(255,255,255,.3),transparent 52%),linear-gradient(125deg,#16171a,#5d5f64 46%,#070708)',
    'radial-gradient(135% 110% at 18% -5%,rgba(180,255,210,.3),transparent 52%),linear-gradient(125deg,#06251a,#1f8a5b 46%,#04130d)',
  ];

  function FactoryScene() {
    const trackRef = useRef(null), stickyRef = useRef(null), rigRef = useRef(null);
    const printedRef = useRef(null), headRef = useRef(null), xrayRef = useRef(null);
    const coilRef = useRef(null), chipRef = useRef(null), glossRef = useRef(null), stampRef = useRef(null);
    const bedRef = useRef(null), gridRef = useRef(null), vglowRef = useRef(null);
    const tunnelRef = useRef(null), portalRef = useRef(null), finalRef = useRef(null), ctaRef = useRef(null), fogRef = useRef(null);
    const flyRefs = useRef([]), starRefs = useRef([]), ringRefs = useRef([]), capRefs = useRef([]), railRefs = useRef([]), stepRef = useRef(null);

    // stable descriptors for the wormhole
    const fly = useRef(null);
    if (!fly.current) {
      fly.current = Array.from({ length: 12 }, (_, i) => ({
        off: i / 12 + Math.random() * 0.02,
        x: (Math.random() * 2 - 1) * 230, y: (Math.random() * 2 - 1) * 145,
        rxs: (Math.random() * 1.3 + 0.4) * (Math.random() < .5 ? -1 : 1),
        rys: (Math.random() * 1.3 + 0.4) * (Math.random() < .5 ? -1 : 1),
        rzs: (Math.random() * 1.1 + 0.3) * (Math.random() < .5 ? -1 : 1),
        s: 0.82 + Math.random() * 0.5, g: FINISHES[i % FINISHES.length],
      }));
    }
    const stars = useRef(null);
    if (!stars.current) {
      stars.current = Array.from({ length: 110 }, () => {
        const a = Math.random() * Math.PI * 2, rad = 18 + Math.random() * 360;
        return { off: Math.random(), x: Math.cos(a) * rad, y: Math.sin(a) * rad, deg: a * 180 / Math.PI + 90 };
      });
    }
    const rings = useRef(null);
    if (!rings.current) rings.current = Array.from({ length: 14 }, (_, i) => ({ off: i / 14 }));

    useEffect(() => {
      let raf;
      const tick = () => {
        const track = trackRef.current, sticky = stickyRef.current;
        if (track && sticky && !window.matchMedia('(max-width:860px)').matches) {
          const r = track.getBoundingClientRect();
          const vh = window.innerHeight;
          const p = clamp(-r.top / (r.height - vh), 0, 1);

          // ambient
          if (gridRef.current) gridRef.current.style.transform = `translate3d(0,${(p * -60).toFixed(1)}px,0)`;
          if (vglowRef.current) vglowRef.current.style.opacity = (0.5 + Math.sin(p * Math.PI) * 0.5).toFixed(2);

          // rig rotation + fade as tunnel takes over
          const rigOp = 1 - es(p, 0.82, 0.90);
          const ry = mix(-16, 12, es(p, 0.05, 0.70)) + Math.sin(p * 6) * 2;
          const rx = mix(10, 4, es(p, 0.05, 0.55));
          if (rigRef.current) {
            rigRef.current.style.transform = `rotateX(${rx.toFixed(2)}deg) rotateY(${ry.toFixed(2)}deg) rotateZ(2deg)`;
            rigRef.current.style.opacity = rigOp.toFixed(3);
          }
          if (bedRef.current) bedRef.current.style.opacity = (1 - es(p, 0.50, 0.66)).toFixed(2);

          // UV print sweep
          const printSeg = es(p, 0.14, 0.35);
          if (printedRef.current) printedRef.current.style.clipPath = `inset(0 ${((1 - printSeg) * 100).toFixed(2)}% 0 0)`;
          if (headRef.current) {
            headRef.current.style.left = mix(-4, 104, printSeg) + '%';
            headRef.current.style.opacity = (es(p, 0.12, 0.16) * (1 - es(p, 0.33, 0.37))).toFixed(3);
          }

          // chip embed x-ray
          const xrayOp = es(p, 0.36, 0.45) * (1 - es(p, 0.53, 0.60));
          if (xrayRef.current) xrayRef.current.style.opacity = xrayOp.toFixed(3);
          if (coilRef.current) {
            const rings = coilRef.current.children;
            for (let i = 0; i < rings.length; i++) rings[i].style.opacity = (es(p, 0.37 + i * 0.012, 0.45 + i * 0.012)).toFixed(3);
          }
          if (chipRef.current) {
            const c = es(p, 0.46, 0.54);
            chipRef.current.style.opacity = c.toFixed(3);
            chipRef.current.style.transform = `translateY(${((1 - c) * -34).toFixed(1)}px) scale(${(0.7 + 0.3 * c).toFixed(3)})`;
          }

          // finish gloss sweep
          if (glossRef.current) {
            glossRef.current.style.opacity = (es(p, 0.57, 0.62) * (1 - es(p, 0.68, 0.72))).toFixed(3);
            glossRef.current.style.transform = `translateX(${mix(-70, 70, es(p, 0.56, 0.71)).toFixed(1)}%)`;
          }

          // activation stamp + pulse
          if (stampRef.current) {
            const sp = es(p, 0.70, 0.785);
            stampRef.current.style.opacity = (sp * (1 - es(p, 0.83, 0.89))).toFixed(3);
            stampRef.current.style.transform = `translate(-50%,-50%) scale(${mix(0.4, 1, sp).toFixed(3)}) rotate(-11deg)`;
          }
          sticky.classList.toggle('is-live', p > 0.70 && p < 0.92);

          // final resolved card rises straight out of the activated card
          const fp = es(p, 0.82, 0.97);
          if (finalRef.current) {
            finalRef.current.style.opacity = fp.toFixed(3);
            finalRef.current.style.transform = `translate(-50%,-50%) scale(${mix(0.6, 1, fp).toFixed(3)}) rotateY(${mix(26, 0, fp).toFixed(1)}deg)`;
          }
          if (ctaRef.current) ctaRef.current.style.opacity = es(p, 0.92, 1).toFixed(3);

          // captions + rail (5 stages)
          const idx = p >= 0.82 ? 4 : p >= 0.56 ? 3 : p >= 0.36 ? 2 : p >= 0.13 ? 1 : 0;
          capRefs.current.forEach((el, i) => el && el.classList.toggle('is-on', i === idx));
          railRefs.current.forEach((el, i) => el && el.classList.toggle('is-on', i <= idx));
          if (stepRef.current) stepRef.current.innerHTML = `STAGE <b>0${idx + 1}</b> / 05`;
        }
        raf = requestAnimationFrame(tick);
      };
      raf = requestAnimationFrame(tick);
      return () => cancelAnimationFrame(raf);
    }, []);

    const caps = [
      <>It begins as a <em>blank.</em></>,
      <>UV-printed in <em>high-build layers.</em></>,
      <>A secure NFC chip, <em>sealed inside.</em></>,
      <>Cured, bevelled, <em>finished.</em></>,
      <>Tested live — <em>ready to tap.</em></>,
    ];

    return (
      <section className="fz-track" id="made" ref={trackRef}>
        <div className="fz-sticky" ref={stickyRef}>
          <div className="fz-field" aria-hidden="true">
            <div className="fz-grid" ref={gridRef} />
            <div className="fz-vglow" ref={vglowRef} />
            <div className="fz-grain" />
          </div>

          <div className="fz-head">
            <div className="wv-kicker"><span className="wv-kicker-mark" />MADE TO BE TAPPED</div>
            <div className="fz-step-no" ref={stepRef}>STAGE <b>01</b> / 05</div>
          </div>

          <div className="fz-stage">
            <div className="fz-rig" ref={rigRef}>
              <div className="fz-bed" ref={bedRef}>
                <div className="fz-rail t" /><div className="fz-rail b" />
                <div className="fz-bed-tag">waiv · fabrication bed</div>
              </div>

              <div className="fz-card fz-blank" />
              <div className="fz-card fz-printed" ref={printedRef} style={{ clipPath: 'inset(0 100% 0 0)' }}>
                <img className="fz-printed-logo" src={(window.__resources&&window.__resources.logoYellow)||"assets/waiv-yellow.png"} alt="" />
                <div className="fz-printed-nfc" />
                <div className="fz-printed-meta">MIDNIGHT GOLD · NFC ∞</div>
              </div>

              <div className="fz-head-bar" ref={headRef} style={{ left: '-4%' }}>
                <div className="fz-nozzle" />
              </div>

              <div className="fz-xray" ref={xrayRef}>
                <div className="fz-xray-dim" />
                <div className="fz-coil" ref={coilRef}><span /><span /><span /><span /><span /><span /><span /></div>
                <div className="fz-chip" ref={chipRef} />
              </div>

              <div className="fz-gloss" ref={glossRef} />
              <div className="fz-stamp" ref={stampRef}>
                <svg viewBox="0 0 24 24"><path d="M5 13l4 4L19 7" /></svg>ACTIVATED
              </div>
            </div>

            <div className="fz-pulse" aria-hidden="true"><span /><span /><span /></div>

            {/* finished card */}
            <div className="fz-final" ref={finalRef}>
              <img className="fz-printed-logo" src={(window.__resources&&window.__resources.logoYellow)||"assets/waiv-yellow.png"} alt="" />
              <div className="fz-printed-nfc" />
              <div className="fz-printed-meta">MIDNIGHT GOLD · NFC ∞</div>
            </div>
            <div className="fz-final-cta" ref={ctaRef}>
              <b>Ready to tap.</b>
              <span>yours in 3 days</span>
            </div>
          </div>

          <div className="fz-caps">
            <div className="fz-cap">
              {caps.map((c, i) => <p key={i} ref={el => capRefs.current[i] = el} className={i === 0 ? 'is-on' : ''}>{c}</p>)}
            </div>
            <div className="fz-rail">
              {[0, 1, 2, 3, 4].map(i => <i key={i} ref={el => railRefs.current[i] = el} className={i === 0 ? 'is-on' : ''} />)}
            </div>
          </div>
        </div>
      </section>
    );
  }

  window.FactoryScene = FactoryScene;
})();
