/* Shared primitives & helpers for the design system page */

const { useState, useEffect, useRef, useMemo, createContext, useContext } = React;

/* ============================================================
 * Variant system — lets the whole page swap between
 * "origin", "refine", and "horizon" design systems.
 * Provider lives in app.jsx; consumers read via useVariant().
 * ============================================================ */
const VariantContext = createContext({ variant: 'origin', setVariant: () => {} });
function useVariant() { return useContext(VariantContext); }

function cx(...xs) { return xs.filter(Boolean).join(' '); }

function copy(text) {
  try { navigator.clipboard.writeText(text); } catch (e) {}
}

/* Section wrapper — every section is a stacked block with a sticky header */
function Section({ id, eyebrow, title, intro, children }) {
  return (
    <section data-section={id} data-screen-label={id} id={id} style={S.section}>
      <div style={S.sectionHead}>
        {eyebrow && <div style={S.eyebrow}>{eyebrow}</div>}
        <h2 style={S.h2}>{title}</h2>
        {intro && <p style={S.intro}>{intro}</p>}
      </div>
      <div style={{ display: 'flex', flexDirection: 'column', gap: 32 }}>
        {children}
      </div>
    </section>
  );
}

/* Sub-block inside a section */
function Block({ title, note, children, style }) {
  return (
    <div style={{ ...style }}>
      {(title || note) && (
        <div style={{ display: 'flex', alignItems: 'baseline', justifyContent: 'space-between', marginBottom: 16, gap: 24, flexWrap: 'wrap' }}>
          {title && <h3 style={S.h3}>{title}</h3>}
          {note && <div style={S.blockNote}>{note}</div>}
        </div>
      )}
      {children}
    </div>
  );
}

/* Card — the canonical container used across the page */
function Card({ children, style, pad = 24, variant = 'default' }) {
  const base = {
    background: 'var(--bg-primary)',
    border: '1px solid var(--border-secondary)',
    borderRadius: 16,
    padding: pad,
    ...style,
  };
  if (variant === 'inset') {
    base.background = 'var(--bg-secondary)';
    base.border = '1px solid var(--border-tertiary)';
  }
  if (variant === 'brand') {
    base.background = 'var(--brand-600)';
    base.color = '#fff';
    base.border = 'none';
  }
  return <div style={base}>{children}</div>;
}

/* Token row — used across color / spacing / shadow displays */
function TokenRow({ swatch, name, value, note }) {
  return (
    <div
      onClick={() => copy(value)}
      style={{
        display: 'grid',
        gridTemplateColumns: '56px 1fr auto',
        alignItems: 'center',
        gap: 16,
        padding: '12px 16px',
        borderRadius: 12,
        cursor: 'pointer',
        transition: 'background .15s',
      }}
      onMouseEnter={e => e.currentTarget.style.background = 'var(--bg-secondary)'}
      onMouseLeave={e => e.currentTarget.style.background = 'transparent'}
    >
      {swatch}
      <div style={{ minWidth: 0 }}>
        <div style={{ fontSize: 14, fontWeight: 600, color: 'var(--text-primary)' }}>{name}</div>
        {note && <div style={{ fontSize: 12, color: 'var(--text-quaternary)', marginTop: 2 }}>{note}</div>}
      </div>
      <code style={{ fontSize: 12, color: 'var(--text-tertiary)', whiteSpace: 'nowrap' }}>{value}</code>
    </div>
  );
}

/* Simple copy-to-clipboard chip */
function Code({ children, block }) {
  const [copied, setCopied] = useState(false);
  const onClick = () => {
    copy(String(children));
    setCopied(true);
    setTimeout(() => setCopied(false), 1200);
  };
  if (block) {
    return (
      <pre
        onClick={onClick}
        style={{
          background: 'var(--brand-950)', color: '#E8EAFB',
          padding: 16, borderRadius: 12, fontSize: 13, lineHeight: 1.6,
          overflowX: 'auto', margin: 0, cursor: 'pointer',
          fontFamily: 'var(--font-mono)',
        }}
      >{children}</pre>
    );
  }
  return (
    <code
      onClick={onClick}
      title={copied ? 'Copied' : 'Click to copy'}
      style={{
        fontFamily: 'var(--font-mono)', fontSize: 12, fontWeight: 500,
        background: 'var(--bg-tertiary)', color: 'var(--text-secondary)',
        padding: '2px 8px', borderRadius: 6,
        border: '1px solid var(--border-secondary)', cursor: 'pointer',
      }}>{copied ? '✓ copied' : children}</code>
  );
}

/* ===== Brand marks — paths lifted directly from the official
   "Nexus Logo Split Master" SVG so geometry is canonical. =====

   The Split Master file expresses the emblem in the native 136×140
   bounding region (x: 7.9 → 128.1, y: 9.9 → 130.1). Everything below
   uses that native viewBox so paths aren't scaled or redrawn — we just
   wrap / color them. */

const ARROW_PATH = "M128.055 9.93506H87.925H7.92499V50.0651H59.555L7.92499 101.685L22.115 115.875L36.305 130.065L87.935 78.4351V130.065H127.905L128.055 9.93506ZM124.625 126.635V50.0651L124.615 50.0551V13.3651H11.355V46.6351H67.845L61.985 52.4951L12.785 101.695L24.545 113.455L36.305 125.215L85.505 76.0151L91.365 70.1551V126.635H124.625Z";

/* NR monogram path, translated so its left edge sits at x=136
   (directly after the arrow's 128px footprint + 8px inter-mark space
   to match the Split Master composition). */
const NR_PATH = "M300.785 89.2251C315.375 82.1851 324.475 70.1751 324.475 52.4951V52.1551C324.475 39.7951 320.865 31.0451 313.495 23.6651C305.075 15.2551 291.685 9.93506 270.235 9.93506H211.545V62.8051L168.945 9.93506H127.935L127.925 50.0551L127.935 50.0651L127.925 130.065H171.185V74.6351L215.805 130.065H251.705V95.7451H260.285L282.935 130.065H328.755L300.775 89.2251H300.785ZM269.035 67.0851C278.635 67.0851 284.475 62.7951 284.475 55.4151L284.485 55.4251V55.0751C284.485 47.3451 278.655 43.5751 269.215 43.5751H251.705V67.0851H269.035Z";

/* =============================================================
 * Brand mark family — three variants
 *
 * OriginArrow / OriginNRMark     — current system (Penn Blue + Aureolin)
 * RefineArrow / RefineNRMark     — evolved geometry, rounded joins
 * HorizonGlyph / HorizonNRMark   — exploratory trefoil glyph
 *
 * `ArrowMark` and `NRMark` are the public dispatchers that read
 * the active variant from VariantContext. Keeping the dispatchers
 * signature-compatible with the previous API means the 60+ usages
 * across sections never need to change — they just swap visually.
 * ============================================================= */

/* ---------- Origin (current) ---------- */
function OriginArrow({ size = 48, fill = 'var(--accent-400)', boxed = false, boxFill = 'var(--brand-600)', radius = 0, padding = 20 }) {
  if (boxed) {
    const vb = 136 + padding * 2;
    return (
      <svg width={size} height={size} viewBox={`0 0 ${vb} ${vb}`} fill="none" xmlns="http://www.w3.org/2000/svg" style={{ display: 'block' }}>
        <rect width={vb} height={vb} rx={radius} fill={boxFill} />
        <g transform={`translate(${padding - 7.925} ${padding - 9.935})`}>
          <path d={ARROW_PATH} fill={fill} fillRule="evenodd" clipRule="evenodd" />
        </g>
      </svg>
    );
  }
  return (
    <svg width={size} height={size} viewBox="7.925 9.935 120.13 120.13" fill="none" xmlns="http://www.w3.org/2000/svg" style={{ display: 'block' }}>
      <path d={ARROW_PATH} fill={fill} fillRule="evenodd" clipRule="evenodd" />
    </svg>
  );
}

function OriginNRMark({ height = 48, fill = 'var(--accent-400)', style }) {
  const aspect = 320.83 / 120.13;
  return (
    <svg height={height} width={height * aspect} viewBox="7.925 9.935 320.83 120.13" fill="none" xmlns="http://www.w3.org/2000/svg" style={{ display: 'block', ...style }}>
      <path d={ARROW_PATH} fill={fill} fillRule="evenodd" clipRule="evenodd" />
      <path d={NR_PATH} fill={fill} fillRule="evenodd" clipRule="evenodd" />
    </svg>
  );
}

/* ---------- Refine (subtle evolution) ----------
   Same silhouette DNA as the current arrow, but with the outer contour
   softened — `stroke-linejoin="round"` on the existing path rounds every
   corner without redrawing. It reads as the mature, considered
   cousin of the angular original. */
function RefineArrow({ size = 48, fill = 'var(--accent-400)', boxed = false, boxFill = 'var(--brand-600)', radius = 0, padding = 20 }) {
  const stroke = 9;
  const render = (
    <path
      d={ARROW_PATH}
      fill={fill}
      stroke={fill}
      strokeWidth={stroke}
      strokeLinejoin="round"
      strokeLinecap="round"
      fillRule="evenodd"
      clipRule="evenodd"
    />
  );
  if (boxed) {
    const vb = 136 + padding * 2;
    return (
      <svg width={size} height={size} viewBox={`0 0 ${vb} ${vb}`} fill="none" xmlns="http://www.w3.org/2000/svg" style={{ display: 'block' }}>
        <rect width={vb} height={vb} rx={radius} fill={boxFill} />
        <g transform={`translate(${padding - 7.925} ${padding - 9.935})`}>{render}</g>
      </svg>
    );
  }
  /* widen the viewBox slightly so the outward-grown stroke isn't clipped */
  return (
    <svg width={size} height={size} viewBox="3 5 130 130" fill="none" xmlns="http://www.w3.org/2000/svg" style={{ display: 'block' }}>
      {render}
    </svg>
  );
}

function RefineNRMark({ height = 48, fill = 'var(--accent-400)', style }) {
  const aspect = 320.83 / 120.13;
  const stroke = 9;
  return (
    <svg height={height} width={height * aspect} viewBox="3 5 330 130" fill="none" xmlns="http://www.w3.org/2000/svg" style={{ display: 'block', ...style }}>
      <path d={ARROW_PATH} fill={fill} stroke={fill} strokeWidth={stroke}
        strokeLinejoin="round" strokeLinecap="round" fillRule="evenodd" clipRule="evenodd" />
      <path d={NR_PATH} fill={fill} stroke={fill} strokeWidth={stroke}
        strokeLinejoin="round" strokeLinecap="round" fillRule="evenodd" clipRule="evenodd" />
    </svg>
  );
}

/* ---------- Horizon (exploratory) ----------
   A trefoil/gyre: three arrow petals radiating 120° from a central hub.
   Preserves "arrow" DNA but speaks flow, circularity, regeneration.
   Drawn inside a centred viewBox for easy rotation math. */
const HORIZON_PETAL = "M -14 -18 L 0 -48 L 14 -18 L 6 -18 L 6 -4 L -6 -4 L -6 -18 Z";

function HorizonGlyph({ size = 48, fill = 'var(--accent-400)', boxed = false, boxFill = 'var(--brand-600)', radius = 0, padding = 16 }) {
  const glyph = (
    <g>
      {[0, 120, 240].map(deg => (
        <g key={deg} transform={`rotate(${deg})`}>
          <path d={HORIZON_PETAL} fill={fill} />
        </g>
      ))}
      <circle r="4.5" fill={fill} />
    </g>
  );
  if (boxed) {
    const vb = 120 + padding * 2;
    return (
      <svg width={size} height={size} viewBox={`0 0 ${vb} ${vb}`} fill="none" xmlns="http://www.w3.org/2000/svg" style={{ display: 'block' }}>
        <rect width={vb} height={vb} rx={radius} fill={boxFill} />
        <g transform={`translate(${vb / 2} ${vb / 2})`}>{glyph}</g>
      </svg>
    );
  }
  return (
    <svg width={size} height={size} viewBox="-60 -60 120 120" fill="none" xmlns="http://www.w3.org/2000/svg" style={{ display: 'block' }}>
      {glyph}
    </svg>
  );
}

/* NR wordmark for horizon — glyph + "NR" rendered in Space Grotesk.
   SVG <text> picks up the imported display font from the document. */
function HorizonNRMark({ height = 48, fill = 'var(--accent-400)', style }) {
  /* viewBox planned for aspect ~ 3.2:1 to match Origin NR proportions */
  const aspect = 3.2;
  return (
    <svg height={height} width={height * aspect} viewBox="0 0 320 100" fill="none" xmlns="http://www.w3.org/2000/svg" style={{ display: 'block', ...style }}>
      <g transform="translate(50 50) scale(0.85)">
        {[0, 120, 240].map(deg => (
          <g key={deg} transform={`rotate(${deg})`}>
            <path d={HORIZON_PETAL} fill={fill} />
          </g>
        ))}
        <circle r="4.5" fill={fill} />
      </g>
      <text
        x="115"
        y="78"
        fill={fill}
        fontFamily="'Space Grotesk', -apple-system, sans-serif"
        fontSize="92"
        fontWeight="700"
        letterSpacing="-4"
      >NR</text>
    </svg>
  );
}

/* ---------- Public dispatchers ---------- */
function ArrowMark(props) {
  const { variant } = useVariant();
  if (variant === 'refine') return <RefineArrow {...props} />;
  if (variant === 'horizon') return <HorizonGlyph {...props} />;
  return <OriginArrow {...props} />;
}

function NRMark(props) {
  const { variant } = useVariant();
  if (variant === 'refine') return <RefineNRMark {...props} />;
  if (variant === 'horizon') return <HorizonNRMark {...props} />;
  return <OriginNRMark {...props} />;
}

/* Accent chip label */
function Eyebrow({ children, color = 'var(--brand-600)' }) {
  return (
    <span style={{
      display: 'inline-flex', alignItems: 'center', gap: 6,
      fontSize: 11, fontWeight: 700, letterSpacing: '.12em', textTransform: 'uppercase',
      color,
    }}>
      <span style={{ width: 6, height: 6, background: color, borderRadius: 2 }} />
      {children}
    </span>
  );
}

/* ------- Base form components (Nexus-styled, Untitled UI alike) ------- */
function Btn({ children, variant = 'primary', size = 'md', iconLeft, iconRight, style, onClick, disabled }) {
  const sizes = {
    sm: { padding: '8px 12px', fontSize: 14, borderRadius: 8, gap: 6 },
    md: { padding: '10px 16px', fontSize: 14, borderRadius: 8, gap: 6 },
    lg: { padding: '12px 20px', fontSize: 16, borderRadius: 10, gap: 8 },
    xl: { padding: '14px 22px', fontSize: 16, borderRadius: 10, gap: 8 },
  }[size];
  const variants = {
    primary: { background: 'var(--brand-600)', color: '#fff', border: '1px solid var(--brand-700)',
      boxShadow: '0 1px 2px rgba(16,24,40,.05), inset 0 -2px 0 rgba(0,0,0,.12), inset 0 1px 0 rgba(255,255,255,.12)' },
    accent:  { background: 'var(--accent-400)', color: 'var(--brand-700)', border: '1px solid var(--accent-500)', fontWeight: 700,
      boxShadow: '0 1px 2px rgba(16,24,40,.05), inset 0 -2px 0 rgba(0,0,0,.08), inset 0 1px 0 rgba(255,255,255,.4)' },
    secondary: { background: 'var(--bg-primary)', color: 'var(--text-secondary)', border: '1px solid var(--border-primary)',
      boxShadow: '0 1px 2px rgba(16,24,40,.05)' },
    tertiary: { background: 'transparent', color: 'var(--text-secondary)', border: '1px solid transparent' },
    destructive: { background: 'var(--error-500)', color: '#fff', border: '1px solid #B42318',
      boxShadow: '0 1px 2px rgba(16,24,40,.05), inset 0 -2px 0 rgba(0,0,0,.12)' },
    link: { background: 'transparent', color: 'var(--brand-600)', border: '1px solid transparent', padding: 0, textDecoration: 'underline', textUnderlineOffset: 3 },
  }[variant];

  return (
    <button
      onClick={onClick}
      disabled={disabled}
      style={{
        display: 'inline-flex', alignItems: 'center', justifyContent: 'center',
        fontWeight: 600, lineHeight: 1, whiteSpace: 'nowrap',
        transition: 'transform .08s, box-shadow .15s, background .15s',
        opacity: disabled ? 0.5 : 1,
        cursor: disabled ? 'not-allowed' : 'pointer',
        ...sizes, ...variants, ...style,
      }}
      onMouseDown={e => !disabled && (e.currentTarget.style.transform = 'translateY(1px)')}
      onMouseUp={e => (e.currentTarget.style.transform = 'translateY(0)')}
      onMouseLeave={e => (e.currentTarget.style.transform = 'translateY(0)')}
    >
      {iconLeft}{children}{iconRight}
    </button>
  );
}

function Badge({ children, color = 'gray', variant = 'subtle', icon, dot }) {
  const palettes = {
    gray:    { bg: 'var(--neutral-100)', fg: 'var(--neutral-700)', border: 'var(--neutral-200)', dot: 'var(--neutral-500)' },
    brand:   { bg: 'var(--brand-50)', fg: 'var(--brand-700)', border: 'var(--brand-200)', dot: 'var(--brand-500)' },
    accent:  { bg: 'var(--accent-50)', fg: 'var(--accent-800)', border: 'var(--accent-300)', dot: 'var(--accent-500)' },
    success: { bg: '#ECFDF3', fg: '#067647', border: '#ABEFC6', dot: 'var(--success-500)' },
    warning: { bg: '#FFFAEB', fg: '#B54708', border: '#FEDF89', dot: 'var(--warning-500)' },
    error:   { bg: '#FEF3F2', fg: '#B42318', border: '#FECDCA', dot: 'var(--error-500)' },
  }[color];
  const style = variant === 'solid'
    ? { background: palettes.dot, color: '#fff', border: '1px solid transparent' }
    : variant === 'outline'
      ? { background: 'transparent', color: palettes.fg, border: `1px solid ${palettes.border}` }
      : { background: palettes.bg, color: palettes.fg, border: `1px solid ${palettes.border}` };
  return (
    <span style={{
      display: 'inline-flex', alignItems: 'center', gap: 4,
      padding: '2px 8px', borderRadius: 999,
      fontSize: 12, fontWeight: 500, lineHeight: 1.5,
      ...style,
    }}>
      {dot && <span style={{ width: 6, height: 6, borderRadius: 999, background: palettes.dot }} />}
      {icon}
      {children}
    </span>
  );
}

/* Make primitives available to other <script type="text/babel"> files */
Object.assign(window, {
  cx, copy,
  Section, Block, Card, TokenRow, Code, ArrowMark, NRMark, Eyebrow, Btn, Badge,
  /* Variant system */
  VariantContext, useVariant,
  /* Explicit marks — for the switcher preview tiles */
  OriginArrow, OriginNRMark,
  RefineArrow, RefineNRMark,
  HorizonGlyph, HorizonNRMark,
});

/* Shared stylesheet — scoped via React inline styles where practical */
const S = {
  section: {
    padding: '56px 40px 24px',
    borderBottom: '1px solid var(--border-tertiary)',
  },
  sectionHead: {
    maxWidth: 780,
    marginBottom: 40,
  },
  eyebrow: {
    display: 'inline-flex', alignItems: 'center', gap: 8,
    fontSize: 11, fontWeight: 700, letterSpacing: '.12em', textTransform: 'uppercase',
    color: 'var(--brand-500)', marginBottom: 12,
  },
  h2: {
    fontSize: 40, lineHeight: 1.1, fontWeight: 600, letterSpacing: '-0.02em',
    color: 'var(--text-primary)', margin: 0,
  },
  h3: {
    fontSize: 18, fontWeight: 600, margin: 0, color: 'var(--text-primary)',
  },
  intro: {
    fontSize: 16, lineHeight: 1.6, color: 'var(--text-tertiary)',
    marginTop: 12, marginBottom: 0,
  },
  blockNote: {
    fontSize: 13, color: 'var(--text-quaternary)',
  },
};
window.S = S;
