// Goodie Hunter — 共用元件
// SymAvatar / StratChip / PriceBadge / Sparkline
// 相依：tokens.jsx（顏色）、data.jsx（SYMBOL_BY / STRATEGY_BY_ID）

// ── Symbol avatar ────────────────────────────────────────────────
function SymAvatar({ sym, size = 44 }) {
  const meta = window.SYMBOL_BY[sym] || { color: '#888', logo: sym[0] };
  const fontSize = size <= 28 ? 11 : size <= 36 ? 13 : 15;
  return (
    <div style={{
      width: size, height: size, borderRadius: size * 0.32,
      background: meta.color,
      color: 'white',
      display: 'flex', alignItems: 'center', justifyContent: 'center',
      fontFamily: '"Plus Jakarta Sans", sans-serif',
      fontWeight: 700, fontSize,
      letterSpacing: -0.3,
      boxShadow: '0 1px 0 rgba(0,0,0,0.04), inset 0 -1px 0 rgba(0,0,0,0.08)',
      flexShrink: 0,
    }}>{sym.slice(0, sym.length <= 4 ? sym.length : 4)}</div>
  );
}
window.SymAvatar = SymAvatar;

// ── Strategy chip ────────────────────────────────────────────────
function StratChip({ strategyId, size = 'sm', neutral = false }) {
  const s = window.STRATEGY_BY_ID[strategyId];
  if (!s) return null;
  const t = window.flutterTokens;
  const c = { bg: t.surfaceAlt, ink: t.ink2 };
  const padY = size === 'lg' ? 6 : 3;
  const padX = size === 'lg' ? 12 : 8;
  const fz   = size === 'lg' ? 13 : 11.5;
  return (
    <span style={{
      display: 'inline-flex', alignItems: 'center', gap: 4,
      background: c.bg, color: c.ink,
      padding: `${padY}px ${padX}px`,
      borderRadius: 999,
      fontSize: fz, fontWeight: 600,
      whiteSpace: 'nowrap',
    }}>
      {s.name}
    </span>
  );
}
window.StratChip = StratChip;

// ── Price/change badge ───────────────────────────────────────────
function PriceBadge({ price, chg, size = 'md' }) {
  const t = flutterTokens;
  const up = chg >= 0;
  const color = up ? t.up : t.down;
  const bg    = up ? t.upBg : t.downBg;
  const fzPrice = size === 'lg' ? 18 : 14;
  const fzPct   = size === 'lg' ? 13 : 11;
  return (
    <div style={{ display: 'flex', flexDirection: 'column', alignItems: 'flex-end', gap: 2 }}>
      <div style={{
        fontFamily: '"Plus Jakarta Sans", monospace',
        fontVariantNumeric: 'tabular-nums',
        fontWeight: 600, fontSize: fzPrice,
        color: t.ink,
      }}>
        ${price.toLocaleString('en-US', { minimumFractionDigits: 2, maximumFractionDigits: 2 })}
      </div>
      <div style={{
        fontFamily: '"Plus Jakarta Sans", monospace',
        fontVariantNumeric: 'tabular-nums',
        fontWeight: 600, fontSize: fzPct,
        color, background: bg,
        padding: '1px 6px', borderRadius: 6,
      }}>
        {up ? '+' : ''}{chg.toFixed(2)}%
      </div>
    </div>
  );
}
window.PriceBadge = PriceBadge;

// ── Sparkline (decorative, pseudo-random per seed) ───────────────
function Sparkline({ seed = 'x', up = true, width = 56, height = 22, color }) {
  // seeded PRNG
  let h = 0; for (const c of seed) h = (h*31 + c.charCodeAt(0)) | 0;
  const rand = () => { h = (h * 1664525 + 1013904223) | 0; return ((h>>>0) % 1000) / 1000; };
  const N = 24;
  const pts = [];
  let v = 0.5;
  for (let i = 0; i < N; i++) {
    v += (rand() - 0.5) * 0.18;
    v = Math.max(0.05, Math.min(0.95, v));
    pts.push(v);
  }
  // bias end toward up/down
  pts[N-1] = up ? Math.max(...pts) - 0.05 : Math.min(...pts) + 0.05;
  const t = flutterTokens;
  const stroke = color || (up ? t.up : t.down);
  const path = pts.map((p, i) => {
    const x = (i / (N-1)) * width;
    const y = height - p * height;
    return `${i === 0 ? 'M' : 'L'}${x.toFixed(1)} ${y.toFixed(1)}`;
  }).join(' ');
  const last = pts[N-1];
  const lx = width;
  const ly = height - last * height;
  return (
    <svg width={width} height={height} viewBox={`0 0 ${width} ${height}`} style={{ overflow: 'visible' }}>
      <path d={path} fill="none" stroke={stroke} strokeWidth={1.6} strokeLinecap="round" strokeLinejoin="round" opacity={0.85}/>
      <circle cx={lx} cy={ly} r={2.2} fill={stroke}/>
    </svg>
  );
}
window.Sparkline = Sparkline;
