// Effects — Reveal-on-scroll wrapper + Marquee brand strip

/**
 * Reveal — wraps children in a div that fades + translates in when
 * it enters the viewport. Uses IntersectionObserver. No-op for
 * users with prefers-reduced-motion.
 */
function Reveal({ children, delay = 0, y = 24, once = true, threshold = 0.12, as: Tag = 'div', style = {} }) {
  const ref = React.useRef(null);
  const [visible, setVisible] = React.useState(false);

  React.useEffect(() => {
    const node = ref.current;
    if (!node) return;
    const reduce = window.matchMedia && window.matchMedia('(prefers-reduced-motion: reduce)').matches;
    if (reduce) { setVisible(true); return; }
    const io = new IntersectionObserver((entries) => {
      entries.forEach((e) => {
        if (e.isIntersecting) {
          setVisible(true);
          if (once) io.unobserve(node);
        } else if (!once) {
          setVisible(false);
        }
      });
    }, { threshold, rootMargin: '0px 0px -8% 0px' });
    io.observe(node);
    return () => io.disconnect();
  }, [once, threshold]);

  return (
    <Tag
      ref={ref}
      style={{
        opacity: visible ? 1 : 0,
        transform: visible ? 'translateY(0)' : `translateY(${y}px)`,
        transition: `opacity 900ms cubic-bezier(0.22, 0.61, 0.36, 1) ${delay}ms, transform 900ms cubic-bezier(0.22, 0.61, 0.36, 1) ${delay}ms`,
        willChange: 'opacity, transform',
        ...style,
      }}
    >
      {children}
    </Tag>
  );
}

/**
 * BrandMarquee — slow, infinite horizontal scroll of brand names.
 * Pure CSS animation; pauses on hover.
 */
function BrandMarquee({ items, speed = 60 }) {
  const isMobile = window.__dch_isMobile;
  // Repeat the list twice so the loop is seamless
  const row = (key) => (
    <div key={key} style={marquee.row} aria-hidden={key === 'b'}>
      {items.map((it, i) => (
        <React.Fragment key={key + i}>
          <span style={marquee.item}>{it}</span>
          <span style={marquee.dot} aria-hidden="true">✦</span>
        </React.Fragment>
      ))}
    </div>
  );

  return (
    <div style={{ ...marquee.wrap, padding: isMobile ? '16px 0' : '20px 0' }}
         className="dch-marquee">
      <div style={{ ...marquee.track, animationDuration: `${speed}s` }}>
        {row('a')}
        {row('b')}
      </div>
      {/* fade edges so the loop blends into the background */}
      <span style={{ ...marquee.fade, left: 0, background: 'linear-gradient(to right, #0A0A0A, rgba(10,10,10,0))' }} />
      <span style={{ ...marquee.fade, right: 0, background: 'linear-gradient(to left, #0A0A0A, rgba(10,10,10,0))' }} />
    </div>
  );
}

const marquee = {
  wrap: {
    position: 'relative',
    overflow: 'hidden',
    background: '#0A0A0A',
    borderTop: '1px solid #1A1A1A',
    borderBottom: '1px solid #1A1A1A',
  },
  track: {
    display: 'flex',
    width: 'max-content',
    animation: 'dchMarquee linear infinite',
    willChange: 'transform',
  },
  row: {
    display: 'flex',
    alignItems: 'center',
    flexShrink: 0,
    gap: 0,
    paddingRight: 0,
  },
  item: {
    fontFamily: "'Cormorant Garamond', serif",
    fontStyle: 'italic',
    fontWeight: 300,
    fontSize: 32,
    color: '#C8BFA8',
    letterSpacing: '0.04em',
    padding: '0 40px',
    whiteSpace: 'nowrap',
  },
  dot: {
    color: '#C4A45A',
    fontSize: 10,
    opacity: 0.7,
  },
  fade: {
    position: 'absolute',
    top: 0,
    bottom: 0,
    width: 120,
    pointerEvents: 'none',
    zIndex: 2,
  },
};

window.Reveal = Reveal;
window.BrandMarquee = BrandMarquee;
