// Chat experience — the "Start a brief" flow.
//
// Multi-step conversation in Dossier's visual vocabulary. Five states:
//   1. greeting    — empty, large centered prompt + textarea + examples
//   2. refining    — user msg shown, assistant "thinking" indicator
//   3. approval    — query approval card with stats, approve/adjust actions
//   4. payment     — Stripe-style card form (mocked)
//   5. confirmed   — brief queued; email + ETA
//
// Query refinement calls window.claude.complete so the moment feels real;
// falls back to a deterministic mock if the call fails or returns
// unparseable JSON. Volume/voices/confidence are then displayed verbatim.

const EXAMPLES = [
  'How are people talking about tokenized gold custody this month?',
  'What developers actually think about vibe coding tools like Cursor and Windsurf.',
  'Endurance athletes on continuous glucose monitors — what protocols are emerging?',
];

function ChatHeader({ briefNo, step, onClose }) {
  const t = window.dossierTokens;
  const steps = ['Describe', 'Approve', 'Pay', 'Confirmed'];
  const stepIdx = { greeting: 0, refining: 0, approval: 1, payment: 2, confirmed: 3 }[step] ?? 0;

  return (
    <header style={{ display: 'flex', alignItems: 'center', justifyContent: 'space-between', padding: '20px 40px', borderBottom: `1px solid ${t.rule}`, background: t.bg, position: 'sticky', top: 0, zIndex: 5 }}>
      <div style={{ display: 'flex', alignItems: 'center', gap: 16 }}>
        <window.SBMark size={26} mark />
        <span style={{ width: 1, height: 22, background: t.rule }} />
        <span style={{ fontFamily: t.mono, fontSize: 12, color: t.ink3, letterSpacing: 0.6 }}>BRIEF · Nº {briefNo}</span>
      </div>
      <div style={{ display: 'flex', alignItems: 'center', gap: 14, fontSize: 13, color: t.ink3 }}>
        {steps.map((s, i) => (
          <React.Fragment key={s}>
            <span style={{ display: 'inline-flex', alignItems: 'center', gap: 8 }}>
              <span style={{
                width: 18, height: 18, borderRadius: '50%',
                border: `1px solid ${i <= stepIdx ? t.ink : t.rule}`,
                background: i < stepIdx ? t.ink : 'transparent',
                color: i < stepIdx ? t.bg : (i === stepIdx ? t.ink : t.ink3),
                fontSize: 10, fontWeight: 600, display: 'grid', placeItems: 'center',
              }}>{i < stepIdx ? '✓' : i + 1}</span>
              <span style={{ color: i <= stepIdx ? t.ink : t.ink3, fontWeight: i === stepIdx ? 600 : 400 }}>{s}</span>
            </span>
            {i < steps.length - 1 && <span style={{ width: 18, height: 1, background: t.rule }} />}
          </React.Fragment>
        ))}
      </div>
      <button onClick={onClose} className="sb-btn sb-btn-ghost" style={{ background: 'transparent', border: 'none', color: t.ink2, fontSize: 22, lineHeight: 1, width: 32, height: 32, borderRadius: 16, cursor: 'pointer', fontFamily: 'inherit' }}>×</button>
    </header>
  );
}

function ThinkingDots() {
  const t = window.dossierTokens;
  return (
    <span style={{ display: 'inline-flex', gap: 4, alignItems: 'center' }}>
      {[0, 1, 2].map((i) => (
        <span key={i} style={{
          width: 6, height: 6, borderRadius: '50%', background: t.ink3,
          animation: `sbDot 1.2s ${i * 0.15}s infinite ease-in-out`,
        }} />
      ))}
    </span>
  );
}

// One-time keyframe injection for the thinking dots animation.
if (typeof document !== 'undefined' && !document.getElementById('sb-chat-styles')) {
  const s = document.createElement('style');
  s.id = 'sb-chat-styles';
  s.textContent = `
    @keyframes sbDot { 0%, 80%, 100% { opacity: .3; transform: scale(.85); } 40% { opacity: 1; transform: scale(1); } }
    @keyframes sbFade { from { opacity: 0; transform: translateY(8px); } to { opacity: 1; transform: translateY(0); } }
    .sb-msg { animation: sbFade .35s ease both; }
    .sb-input:focus { outline: none; border-color: #1a1d23; box-shadow: 0 0 0 4px rgba(26,29,35,.06); }
  `;
  document.head.appendChild(s);
}

function MessageUser({ children }) {
  const t = window.dossierTokens;
  return (
    <div className="sb-msg" style={{ display: 'flex', justifyContent: 'flex-end', marginBottom: 24 }}>
      <div style={{ maxWidth: '78%' }}>
        <div style={{ fontFamily: t.mono, fontSize: 10.5, color: t.ink3, letterSpacing: 0.6, textAlign: 'right', marginBottom: 6, textTransform: 'uppercase' }}>You</div>
        <div style={{ background: t.ink, color: t.bg, padding: '14px 18px', borderRadius: '14px 14px 4px 14px', fontSize: 15.5, lineHeight: 1.5 }}>{children}</div>
      </div>
    </div>
  );
}

function MessageAssistant({ children, label = 'Brief assistant' }) {
  const t = window.dossierTokens;
  return (
    <div className="sb-msg" style={{ marginBottom: 24, maxWidth: '88%' }}>
      <div style={{ display: 'flex', alignItems: 'center', gap: 10, marginBottom: 6 }}>
        <window.SBMark size={20} label={false} />
        <span style={{ fontFamily: t.mono, fontSize: 10.5, color: t.ink3, letterSpacing: 0.6, textTransform: 'uppercase' }}>{label}</span>
      </div>
      <div style={{ paddingLeft: 30 }}>{children}</div>
    </div>
  );
}

// Query approval card — the centerpiece of the chat flow. The transparency
// checkpoint moment: user sees the exact query and a volume estimate before
// any payment.
function QueryCard({ result, onApprove, onAdjust, price = 9 }) {
  const t = window.dossierTokens;
  const conf = (result.confidence || 'HIGH').toUpperCase();
  const confColor = conf === 'HIGH' ? '#1f7a3d' : conf === 'MEDIUM' ? t.amber : '#a04646';
  return (
    <div style={{ background: t.paper, border: `1px solid ${t.rule}`, borderLeft: `3px solid ${t.blue}`, padding: '24px 26px 22px', borderRadius: 4 }}>
      <div style={{ display: 'flex', justifyContent: 'space-between', alignItems: 'baseline', marginBottom: 4 }}>
        <div style={{ fontSize: 11.5, letterSpacing: 1.6, textTransform: 'uppercase', color: t.blue, fontWeight: 600 }}>Proposed query</div>
        <div style={{ fontFamily: t.mono, fontSize: 11, color: t.ink3, letterSpacing: 0.4 }}>30-DAY WINDOW</div>
      </div>
      <div style={{ background: t.ink, color: t.bg, fontFamily: t.mono, fontSize: 13, lineHeight: 1.55, padding: '14px 16px', borderRadius: 4, marginTop: 14, whiteSpace: 'pre-wrap', wordBreak: 'break-word' }}>
        {result.query}
      </div>
      {result.note && (
        <div style={{ marginTop: 12, fontSize: 13, color: t.ink2, lineHeight: 1.5, fontStyle: 'italic', fontFamily: t.serif }}>
          {result.note}
        </div>
      )}
      <div style={{ display: 'grid', gridTemplateColumns: 'repeat(3, 1fr)', gap: 14, marginTop: 18 }}>
        {[
          ['Estimated posts', result.estimated_posts?.toLocaleString?.() || result.estimated_posts, t.ink],
          ['Distinct voices', result.distinct_voices?.toLocaleString?.() || result.distinct_voices, t.ink],
          ['Signal confidence', conf, confColor],
        ].map(([k, v, col]) => (
          <div key={k} style={{ background: t.bg, borderRadius: 4, padding: '14px 16px', border: `1px solid ${t.ruleSoft}` }}>
            <div style={{ fontFamily: t.mono, fontSize: 10.5, color: t.ink3, letterSpacing: 0.6, textTransform: 'uppercase' }}>{k}</div>
            <div style={{ fontFamily: t.serif, fontSize: 24, fontWeight: 500, letterSpacing: -0.4, marginTop: 6, color: col, lineHeight: 1 }}>{v}</div>
          </div>
        ))}
      </div>
      <div style={{ display: 'flex', gap: 10, marginTop: 22, alignItems: 'center' }}>
        <button onClick={onApprove} className="sb-btn sb-btn-primary" style={{ background: t.ink, color: t.bg, border: 'none', borderRadius: 999, padding: '13px 22px', fontFamily: 'inherit', fontSize: 14.5, fontWeight: 500, cursor: 'pointer' }}>
          Approve &amp; pay ${price} →
        </button>
        <button onClick={onAdjust} className="sb-btn sb-btn-ghost" style={{ background: 'transparent', color: t.ink, border: `1px solid ${t.ink}`, borderRadius: 999, padding: '13px 22px', fontFamily: 'inherit', fontSize: 14.5, fontWeight: 500, cursor: 'pointer' }}>
          Adjust the query
        </button>
        <div style={{ flex: 1 }} />
        <span style={{ fontSize: 12.5, color: t.ink3 }}>Refund if data is thin</span>
      </div>
    </div>
  );
}

// Fallback when claude.complete is unavailable or returns junk.
function mockQueryFor(topic) {
  const lower = topic.toLowerCase();
  const guess = (re) => re.test(lower);
  let query = '"' + topic.split(/\s+/).slice(0, 4).join(' ') + '"';
  let est = 4200 + Math.floor(Math.random() * 8000);
  if (guess(/gold|paxg|xaut|tokeniz/)) {
    query = '("tokenized gold" OR "PAXG" OR "XAUT")\nAND (custody OR "proof of reserve" OR regulation OR audit)\n-pump -giveaway lang:en';
    est = 14200;
  } else if (guess(/cursor|windsurf|vibe|copilot|claude code/)) {
    query = '("Cursor" OR "Windsurf" OR "Claude Code" OR "Copilot")\nAND (workflow OR migration OR "switched to" OR review)\n-job -hiring lang:en';
    est = 21400;
  } else if (guess(/cgm|glucose|athlete|endurance/)) {
    query = '("CGM" OR "continuous glucose" OR Levels OR Stelo)\nAND (endurance OR training OR athlete OR coach)\n-affiliate lang:en';
    est = 7800;
  } else if (guess(/web3|no.code|builder/)) {
    query = '("no-code" OR "low-code") AND (web3 OR dApp OR onchain)\nAND (Thirdweb OR Bubble OR Builderbot OR "switched from")\nlang:en';
    est = 9600;
  }
  return {
    ack: 'Framing this around the public conversation, filtered for substantive posts.',
    query,
    estimated_posts: est,
    distinct_voices: Math.round(est * 0.27),
    confidence: est > 10000 ? 'HIGH' : est > 4000 ? 'MEDIUM' : 'LOW',
    note: 'Excluding promotional posts, giveaways, and obvious bot replies. English language only.',
  };
}

async function refineQuery(topic) {
  if (!window.claude || !window.claude.complete) return mockQueryFor(topic);
  const prompt = `You are Intellegio's query design assistant. The user describes a topic they want to understand from public X (Twitter) conversation over the past 30 days. Design an X search query that captures their intent, and estimate volume.

Return ONLY valid JSON. No prose outside JSON, no markdown code fences:

{
  "ack": "One short sentence (max 20 words) acknowledging what they want and how you are framing the search. Conversational, not robotic.",
  "query": "X search query as a single string. Use OR groups in parens, AND, exclusions with leading -. Include 'lang:en' if relevant. Aim for under 140 chars. Newlines OK.",
  "estimated_posts": <integer between 300 and 25000, realistic for a 30-day window>,
  "distinct_voices": <integer, roughly 25-35% of estimated_posts>,
  "confidence": "HIGH" or "MEDIUM" or "LOW",
  "note": "One short sentence (max 20 words) noting caveats, exclusions, or what is filtered out."
}

User topic: """${topic}"""`;

  try {
    const raw = await window.claude.complete(prompt);
    const m = raw.match(/\{[\s\S]*\}/);
    if (!m) throw new Error('no JSON found');
    const parsed = JSON.parse(m[0]);
    if (!parsed.query) throw new Error('missing query');
    return parsed;
  } catch (e) {
    console.warn('[chat] refine fallback:', e.message);
    return mockQueryFor(topic);
  }
}

// ─── Input area ──────────────────────────────────────────────────
function ChatInput({ value, onChange, onSubmit, placeholder, disabled, autoFocus }) {
  const t = window.dossierTokens;
  const ref = React.useRef(null);
  React.useEffect(() => { if (autoFocus && ref.current) ref.current.focus(); }, [autoFocus]);
  const submit = (e) => { e && e.preventDefault(); if (!value.trim() || disabled) return; onSubmit(); };
  return (
    <form onSubmit={submit} style={{ position: 'relative', background: t.paper, border: `1px solid ${t.rule}`, borderRadius: 10, padding: '14px 14px 12px', display: 'flex', flexDirection: 'column', gap: 12, transition: 'border-color .15s, box-shadow .15s' }}>
      <textarea
        ref={ref}
        value={value}
        onChange={(e) => onChange(e.target.value)}
        onKeyDown={(e) => { if (e.key === 'Enter' && (e.metaKey || e.ctrlKey || !e.shiftKey)) submit(e); }}
        placeholder={placeholder}
        disabled={disabled}
        rows={2}
        className="sb-input"
        style={{ background: 'transparent', border: 'none', resize: 'none', fontFamily: t.sans, fontSize: 16, lineHeight: 1.5, color: t.ink, width: '100%', minHeight: 48 }}
      />
      <div style={{ display: 'flex', justifyContent: 'space-between', alignItems: 'center' }}>
        <span style={{ fontSize: 12, color: t.ink3 }}>Enter to send · Shift+Enter for newline</span>
        <button type="submit" disabled={!value.trim() || disabled} className="sb-btn sb-btn-primary" style={{ background: value.trim() && !disabled ? t.ink : t.rule, color: t.bg, border: 'none', borderRadius: 999, padding: '9px 18px', fontFamily: 'inherit', fontSize: 14, fontWeight: 500, cursor: value.trim() && !disabled ? 'pointer' : 'default' }}>
          Send →
        </button>
      </div>
    </form>
  );
}

// ─── Payment ─────────────────────────────────────────────────────
function PaymentCard({ price, tier, onPay }) {
  const t = window.dossierTokens;
  const [card, setCard] = React.useState({ name: '', number: '', exp: '', cvc: '', email: '' });
  const [paying, setPaying] = React.useState(false);
  const upd = (k) => (e) => setCard((c) => ({ ...c, [k]: e.target.value }));
  const ready = card.name && card.number.length >= 12 && card.exp && card.cvc && /@/.test(card.email);

  const pay = (e) => {
    e.preventDefault();
    if (!ready || paying) return;
    setPaying(true);
    setTimeout(() => onPay(card.email), 1400); // fake processing
  };

  const Field = ({ label, k, type = 'text', placeholder, span = 12 }) => (
    <label style={{ display: 'flex', flexDirection: 'column', gap: 6, gridColumn: `span ${span}` }}>
      <span style={{ fontFamily: t.mono, fontSize: 10.5, color: t.ink3, letterSpacing: 0.6, textTransform: 'uppercase' }}>{label}</span>
      <input
        type={type} value={card[k]} onChange={upd(k)} placeholder={placeholder}
        className="sb-input"
        style={{ background: t.bg, border: `1px solid ${t.rule}`, borderRadius: 6, padding: '11px 14px', fontFamily: type === 'text' && (k === 'number' || k === 'exp' || k === 'cvc') ? t.mono : t.sans, fontSize: 15, color: t.ink, transition: 'border-color .15s, box-shadow .15s' }}
      />
    </label>
  );

  return (
    <div style={{ background: t.paper, border: `1px solid ${t.rule}`, borderRadius: 6, padding: '28px 30px' }}>
      <div style={{ display: 'flex', justifyContent: 'space-between', alignItems: 'baseline', marginBottom: 22 }}>
        <div>
          <div style={{ fontSize: 11.5, letterSpacing: 1.6, textTransform: 'uppercase', color: t.blue, fontWeight: 600 }}>Order summary</div>
          <div style={{ fontFamily: t.serif, fontSize: 26, fontWeight: 500, letterSpacing: -0.4, marginTop: 6 }}>Intellegio · {tier}</div>
          <div style={{ fontSize: 13.5, color: t.ink2, marginTop: 4 }}>One brief · 30-day window · ~24h delivery</div>
        </div>
        <div style={{ textAlign: 'right' }}>
          <div style={{ fontFamily: t.serif, fontSize: 38, fontWeight: 500, letterSpacing: -1, lineHeight: 1 }}>${price}</div>
          <div style={{ fontSize: 12, color: t.ink3, marginTop: 4 }}>one-time</div>
        </div>
      </div>
      <div style={{ height: 1, background: t.ruleSoft, margin: '0 0 22px' }} />
      <form onSubmit={pay} style={{ display: 'grid', gridTemplateColumns: 'repeat(12, 1fr)', gap: 14 }}>
        <Field label="Email for delivery" k="email" type="email" placeholder="you@firm.com" />
        <Field label="Name on card" k="name" placeholder="Full name" />
        <Field label="Card number" k="number" placeholder="4242 4242 4242 4242" span={6} />
        <Field label="Expiry" k="exp" placeholder="MM / YY" span={3} />
        <Field label="CVC" k="cvc" placeholder="123" span={3} />
        <div style={{ gridColumn: 'span 12', display: 'flex', alignItems: 'center', justifyContent: 'space-between', marginTop: 10 }}>
          <div style={{ fontSize: 12.5, color: t.ink3, display: 'flex', alignItems: 'center', gap: 8 }}>
            <svg width="14" height="14" viewBox="0 0 14 14" fill="none"><path d="M3 6V4.5a4 4 0 1 1 8 0V6m-9 0h10v6.5H2V6z" stroke={t.ink3} strokeWidth="1.2" strokeLinecap="round" strokeLinejoin="round"/></svg>
            Test mode — no card will be charged in this prototype.
          </div>
          <button type="submit" disabled={!ready || paying} className="sb-btn sb-btn-primary" style={{ background: ready && !paying ? t.ink : t.rule, color: t.bg, border: 'none', borderRadius: 999, padding: '14px 24px', fontFamily: 'inherit', fontSize: 15, fontWeight: 500, cursor: ready && !paying ? 'pointer' : 'default' }}>
            {paying ? <ThinkingDots /> : <>Pay ${price} →</>}
          </button>
        </div>
      </form>
    </div>
  );
}

// ─── Confirmation ────────────────────────────────────────────────
function Confirmation({ briefNo, email, topic, onClose }) {
  const t = window.dossierTokens;
  return (
    <div style={{ maxWidth: 720, margin: '64px auto 80px', padding: '0 32px' }}>
      <div style={{ fontSize: 12.5, letterSpacing: 2.4, textTransform: 'uppercase', color: t.blue, fontWeight: 600, marginBottom: 18 }}>● Queued · Brief Nº {briefNo}</div>
      <h2 style={{ fontFamily: t.serif, fontSize: 64, lineHeight: 1.02, letterSpacing: -1.6, margin: 0, fontWeight: 500, textWrap: 'balance' }}>
        You're queued. We'll be in touch.
      </h2>
      <p style={{ fontFamily: t.serif, fontSize: 20, color: t.ink2, marginTop: 24, lineHeight: 1.45 }}>
        Your brief on <em style={{ fontStyle: 'italic', color: t.ink }}>"{topic.length > 80 ? topic.slice(0, 80) + '…' : topic}"</em> is in the queue. You'll get a download link at <strong style={{ color: t.ink }}>{email}</strong> within 24 hours.
      </p>

      <div style={{ marginTop: 48, display: 'grid', gridTemplateColumns: 'repeat(3, 1fr)', gap: 16, padding: '28px 0', borderTop: `1px solid ${t.rule}`, borderBottom: `1px solid ${t.rule}` }}>
        {[
          ['Brief Nº', briefNo, 'Reference this if you write in.'],
          ['ETA', 'Within 24h', 'Usually 8–14h. We email you.'],
          ['Format', 'PDF + web', 'Download once it lands.'],
        ].map(([k, v, sub]) => (
          <div key={k}>
            <div style={{ fontFamily: t.mono, fontSize: 11, color: t.ink3, letterSpacing: 0.8, textTransform: 'uppercase' }}>{k}</div>
            <div style={{ fontFamily: t.serif, fontSize: 26, fontWeight: 500, letterSpacing: -0.4, marginTop: 4 }}>{v}</div>
            <div style={{ fontSize: 13, color: t.ink3, marginTop: 4, lineHeight: 1.45 }}>{sub}</div>
          </div>
        ))}
      </div>

      <div style={{ marginTop: 32 }}>
        <div style={{ fontFamily: t.serif, fontSize: 22, fontWeight: 500, letterSpacing: -0.3, marginBottom: 12 }}>While you wait</div>
        <div style={{ display: 'flex', gap: 14 }}>
          <button onClick={onClose} className="sb-btn sb-btn-primary" style={{ background: t.ink, color: t.bg, border: 'none', borderRadius: 999, padding: '14px 22px', fontFamily: 'inherit', fontSize: 14.5, fontWeight: 500, cursor: 'pointer' }}>
            Back to landing
          </button>
          <button className="sb-btn sb-btn-ghost" style={{ background: 'transparent', color: t.ink, border: `1px solid ${t.ink}`, borderRadius: 999, padding: '14px 22px', fontFamily: 'inherit', fontSize: 14.5, fontWeight: 500, cursor: 'pointer' }}>
            Read a sample brief
          </button>
        </div>
      </div>
    </div>
  );
}

// ─── Main chat shell ─────────────────────────────────────────────
function Chat({ onClose, initialTier = 'Self-serve', initialPrice = 9 }) {
  const t = window.dossierTokens;
  const [step, setStep] = React.useState('greeting');
  const [topic, setTopic] = React.useState('');
  const [topicSubmitted, setTopicSubmitted] = React.useState('');
  const [draftInput, setDraftInput] = React.useState('');
  const [refined, setRefined] = React.useState(null);
  const [briefNo] = React.useState(() => String(2615 + Math.floor(Math.random() * 40)).padStart(4, '0'));
  const [email, setEmail] = React.useState('');

  // Esc closes (only from greeting; from later steps it'd be too easy to lose progress)
  React.useEffect(() => {
    const k = (e) => { if (e.key === 'Escape' && step === 'greeting') onClose(); };
    document.addEventListener('keydown', k);
    return () => document.removeEventListener('keydown', k);
  }, [step, onClose]);

  // Lock body scroll while overlay is open
  React.useEffect(() => {
    const prev = document.body.style.overflow;
    document.body.style.overflow = 'hidden';
    return () => { document.body.style.overflow = prev; };
  }, []);

  // Auto-scroll the chat body when new messages arrive
  const bodyRef = React.useRef(null);
  React.useEffect(() => {
    if (bodyRef.current) bodyRef.current.scrollTop = bodyRef.current.scrollHeight;
  }, [step, refined]);

  const submitTopic = async (text) => {
    const t0 = Date.now();
    setTopicSubmitted(text);
    setTopic(text);
    setDraftInput('');
    setStep('refining');
    const result = await refineQuery(text);
    // Minimum 1.4s on refining state so it doesn't snap, feels deliberate
    const elapsed = Date.now() - t0;
    if (elapsed < 1400) await new Promise((r) => setTimeout(r, 1400 - elapsed));
    setRefined(result);
    setStep('approval');
  };

  const adjust = () => {
    setDraftInput(topicSubmitted);
    setStep('greeting');
    setRefined(null);
  };

  const useExample = (ex) => {
    setDraftInput(ex);
  };

  // ── Greeting view (initial, before any topic submitted) ────────
  if (step === 'greeting' && !topicSubmitted) {
    return (
      <div style={{ position: 'fixed', inset: 0, background: t.bg, color: t.ink, fontFamily: t.sans, zIndex: 100, display: 'flex', flexDirection: 'column', overflow: 'auto' }}>
        <ChatHeader briefNo={briefNo} step={step} onClose={onClose} />
        <div style={{ flex: 1, display: 'flex', flexDirection: 'column', alignItems: 'center', justifyContent: 'center', padding: '40px 24px 80px' }}>
          <div style={{ maxWidth: 720, width: '100%' }}>
            <div style={{ fontSize: 12.5, letterSpacing: 2.4, textTransform: 'uppercase', color: t.blue, fontWeight: 600, marginBottom: 22, textAlign: 'center' }}>Start a brief</div>
            <h1 style={{ fontFamily: t.serif, fontSize: 64, lineHeight: 1.02, letterSpacing: -1.6, margin: 0, fontWeight: 500, textAlign: 'center', textWrap: 'balance' }}>
              What do you want to <em style={{ fontStyle: 'italic', color: t.blue }}>understand</em>?
            </h1>
            <p style={{ fontFamily: t.serif, fontSize: 19, color: t.ink2, marginTop: 22, lineHeight: 1.5, textAlign: 'center', maxWidth: 580, margin: '22px auto 0' }}>
              Tell us in plain language. Mention the topic, who you are, and what decision you're making.
            </p>

            <div style={{ marginTop: 44 }}>
              <ChatInput
                value={draftInput}
                onChange={setDraftInput}
                onSubmit={() => submitTopic(draftInput.trim())}
                placeholder="e.g. I'm evaluating tokenized gold custody for a family office. What are operators actually doing about proof-of-reserve, and where is regulatory sentiment heading?"
                autoFocus
              />
            </div>

            <div style={{ marginTop: 26 }}>
              <div style={{ fontFamily: t.mono, fontSize: 10.5, color: t.ink3, letterSpacing: 0.8, textTransform: 'uppercase', marginBottom: 10 }}>Or try one of these</div>
              <div style={{ display: 'flex', flexDirection: 'column', gap: 8 }}>
                {EXAMPLES.map((ex) => (
                  <button key={ex} onClick={() => useExample(ex)} className="sb-btn sb-btn-ghost" style={{ textAlign: 'left', background: 'transparent', border: `1px solid ${t.rule}`, borderRadius: 8, padding: '12px 14px', fontFamily: t.serif, fontStyle: 'italic', fontSize: 15, color: t.ink2, cursor: 'pointer', lineHeight: 1.4 }}>
                    "{ex}"
                  </button>
                ))}
              </div>
            </div>
          </div>
        </div>
      </div>
    );
  }

  // ── Chat-mode view (after a topic submitted; conversation history) ──
  return (
    <div style={{ position: 'fixed', inset: 0, background: t.bg, color: t.ink, fontFamily: t.sans, zIndex: 100, display: 'flex', flexDirection: 'column' }}>
      <ChatHeader briefNo={briefNo} step={step} onClose={onClose} />
      <div ref={bodyRef} style={{ flex: 1, overflow: 'auto' }}>
        {step === 'confirmed' ? (
          <Confirmation briefNo={briefNo} email={email} topic={topic} onClose={onClose} />
        ) : (
          <div style={{ maxWidth: 760, margin: '40px auto 24px', padding: '0 32px' }}>
            <MessageUser>{topicSubmitted}</MessageUser>

            {step === 'refining' && (
              <MessageAssistant>
                <div style={{ display: 'inline-flex', alignItems: 'center', gap: 12, background: t.paper, border: `1px solid ${t.rule}`, padding: '12px 18px', borderRadius: '4px 14px 14px 14px', color: t.ink2, fontSize: 15 }}>
                  Reading your intent <ThinkingDots />
                </div>
              </MessageAssistant>
            )}

            {(step === 'approval' || step === 'payment' || step === 'confirmed') && refined && (
              <>
                <MessageAssistant>
                  <div style={{ fontSize: 15.5, color: t.ink, lineHeight: 1.55, marginBottom: 16 }}>{refined.ack}</div>
                  <QueryCard
                    result={refined}
                    price={initialPrice}
                    onApprove={() => setStep('payment')}
                    onAdjust={adjust}
                  />
                </MessageAssistant>
              </>
            )}

            {step === 'payment' && (
              <MessageAssistant label="Checkout">
                <PaymentCard
                  price={initialPrice}
                  tier={initialTier}
                  onPay={(em) => { setEmail(em); setStep('confirmed'); }}
                />
              </MessageAssistant>
            )}
          </div>
        )}
      </div>

      {/* Footer hint, shown only in chat history mode where the input bar is gone */}
      {step !== 'greeting' && step !== 'confirmed' && (
        <div style={{ padding: '12px 32px 18px', borderTop: `1px solid ${t.rule}`, fontSize: 12, color: t.ink3, textAlign: 'center', background: t.bg }}>
          {step === 'refining' && 'Designing your query · this usually takes a few seconds.'}
          {step === 'approval' && 'Nothing happens until you approve. Adjusting is free.'}
          {step === 'payment' && 'Card details are not transmitted in this prototype.'}
        </div>
      )}
    </div>
  );
}

window.Chat = Chat;
