// Artifact panel — Claude-style split view. Opens on the right when the user
// generates a report; the app shell collapses the sidebar to icons while open.
// The panel renders a REAL PDF (built in-browser with jsPDF) inside an iframe,
// so it's the actual document, not an HTML mock.

// Build the report as a real jsPDF document (vector text, selectable, A4).
const buildReportDoc = (a) => {
  const jsPDFCtor = window.jspdf && window.jspdf.jsPDF;
  if (!jsPDFCtor) return null;
  const doc = new jsPDFCtor({ unit: 'pt', format: 'a4', compress: true });
  doc.setProperties({ title: a.title || 'Report' });

  const M = 54;
  const W = doc.internal.pageSize.getWidth();
  const H = doc.internal.pageSize.getHeight();
  const CW = W - M * 2;
  let y = M + 8;
  const ensure = (need) => { if (y + need > H - M) { doc.addPage(); y = M + 8; } };

  // Title
  doc.setFont('helvetica', 'bold'); doc.setFontSize(22); doc.setTextColor(26, 26, 23);
  doc.text(a.title || 'Report', M, y);
  // Meta
  if (a.meta || a.date) {
    y += 16; doc.setFont('helvetica', 'normal'); doc.setFontSize(10); doc.setTextColor(107, 106, 100);
    doc.text((a.meta || '') + (a.date ? ' · ' + a.date : ''), M, y);
  }
  // Divider
  y += 14; doc.setDrawColor(216, 214, 209); doc.setLineWidth(0.6); doc.line(M, y, W - M, y);

  (a.sections || []).forEach((s) => {
    if (s.type === 'h') {
      ensure(30); y += 26;
      doc.setFont('helvetica', 'bold'); doc.setFontSize(13); doc.setTextColor(26, 26, 23);
      doc.text(s.text, M, y); y += 4;
    } else if (s.type === 'p') {
      doc.setFont('helvetica', 'normal'); doc.setFontSize(11); doc.setTextColor(58, 58, 53);
      const lines = doc.splitTextToSize(s.text, CW);
      ensure(lines.length * 15 + 12); y += 14;
      doc.text(lines, M, y); y += lines.length * 15 - 2;
    } else if (s.type === 'ul') {
      doc.setFont('helvetica', 'normal'); doc.setFontSize(11); doc.setTextColor(58, 58, 53);
      y += 10;
      s.items.forEach((it) => {
        const lines = doc.splitTextToSize(it, CW - 16);
        ensure(lines.length * 15 + 4);
        doc.setFillColor(120, 118, 111); doc.circle(M + 3, y - 3.5, 1.4, 'F');
        doc.text(lines, M + 14, y); y += lines.length * 15 + 3;
      });
    } else if (s.type === 'table') {
      y += 12; ensure(50);
      doc.autoTable({
        head: [s.cols], body: s.rows, startY: y,
        margin: { left: M, right: M }, theme: 'grid',
        styles: { fontSize: 10, cellPadding: 6, textColor: [40, 40, 36], lineColor: [232, 231, 227], lineWidth: 0.5 },
        headStyles: { fillColor: [250, 250, 249], textColor: [107, 106, 100], fontStyle: 'bold', fontSize: 9 },
      });
      y = doc.lastAutoTable.finalY + 8;
    }
  });
  return doc;
};

const _sleep = (ms) => new Promise((r) => setTimeout(r, ms));

const ArtifactPanel = ({ artifact, onClose }) => {
  const [status, setStatus] = React.useState('loading'); // loading | ready | failed
  const containerRef = React.useRef(null);
  const docRef = React.useRef(null);

  React.useEffect(() => {
    if (!artifact) return;
    let cancelled = false;
    setStatus('loading');

    const run = async () => {
      // Wait for jsPDF + pdf.js to finish loading from CDN.
      let tries = 0;
      while ((!(window.jspdf && window.jspdf.jsPDF) || !window.pdfjsLib) && tries < 40) { await _sleep(150); tries++; }
      if (cancelled) return;
      if (!(window.jspdf && window.jspdf.jsPDF) || !window.pdfjsLib) { setStatus('failed'); return; }

      const pdfjs = window.pdfjsLib;
      if (!pdfjs.GlobalWorkerOptions.workerSrc) {
        pdfjs.GlobalWorkerOptions.workerSrc = 'https://cdn.jsdelivr.net/npm/pdfjs-dist@3.11.174/build/pdf.worker.min.js';
      }

      try {
        const doc = buildReportDoc(artifact);
        docRef.current = doc;
        const data = new Uint8Array(doc.output('arraybuffer'));
        const pdf = await pdfjs.getDocument({ data }).promise;
        if (cancelled) return;
        const container = containerRef.current;
        if (!container) return;
        container.innerHTML = '';
        const scale = 2; // render at 2x for crisp text, displayed responsively
        for (let p = 1; p <= pdf.numPages; p++) {
          const page = await pdf.getPage(p);
          if (cancelled) return;
          const viewport = page.getViewport({ scale });
          const canvas = document.createElement('canvas');
          canvas.width = viewport.width;
          canvas.height = viewport.height;
          canvas.style.cssText = 'width:100%;height:auto;display:block;background:#fff;';
          await page.render({ canvasContext: canvas.getContext('2d'), viewport }).promise;
          if (cancelled) return;
          container.appendChild(canvas);
        }
        setStatus('ready');
      } catch (e) {
        console.error('PDF render failed', e);
        if (!cancelled) setStatus('failed');
      }
    };
    run();
    return () => { cancelled = true; };
  }, [artifact]);

  if (!artifact) return null;
  const a = artifact;
  const download = () => { if (docRef.current) docRef.current.save((a.title || 'report') + '.pdf'); };

  return (
    <aside style={{
      flex: '1.15 1 0', minWidth: 0,
      display: 'flex', flexDirection: 'column',
      borderLeft: '0.5px solid var(--line)',
      background: 'var(--bg)',
      animation: 'nx-fade-up .2s ease-out',
    }}>
      {/* Header */}
      <header style={{
        height: 48, flex: '0 0 48px', display: 'flex', alignItems: 'center', gap: 10,
        padding: '0 14px 0 16px', borderBottom: '0.5px solid var(--line)',
      }}>
        <div style={{ width: 26, height: 26, borderRadius: 7, flexShrink: 0, background: 'var(--accent-soft)', color: 'var(--accent-ink)', display: 'flex', alignItems: 'center', justifyContent: 'center' }}>
          <Icon name="doc" size={15} />
        </div>
        <div style={{ flex: 1, minWidth: 0 }}>
          <div style={{ fontSize: 13, fontWeight: 600, color: 'var(--ink)', overflow: 'hidden', textOverflow: 'ellipsis', whiteSpace: 'nowrap' }}>{a.title}</div>
        </div>
        <span className="nx-chip" style={{ height: 20, fontSize: 10, flexShrink: 0 }}>{a.kind || 'PDF'}</span>
        <button className="nx-btn sm accent" onClick={download} style={{ flexShrink: 0 }}>
          <Icon name="arrow-up-right" size={12} /> Download PDF
        </button>
        <button onClick={onClose} title="Close" className="nx-btn sm ghost" style={{ width: 28, padding: 0, justifyContent: 'center', flexShrink: 0 }}>
          <Icon name="x" size={14} />
        </button>
      </header>

      {/* PDF pages rendered to <canvas> via pdf.js (Claude-style document view) */}
      <div style={{ flex: 1, minHeight: 0, overflowY: 'auto', background: '#ffffff', position: 'relative' }}>
        <div ref={containerRef} />
        {status !== 'ready' && (
          <div style={{ position: 'absolute', inset: 0, display: 'flex', alignItems: 'center', justifyContent: 'center', gap: 8, color: 'var(--ink-3)', fontSize: 13, pointerEvents: 'none' }}>
            {status === 'failed'
              ? <span>Couldn’t render the PDF (library failed to load).</span>
              : <><Icon name="refresh" size={14} className="nx-spin" /> <span>Rendering PDF…</span></>}
          </div>
        )}
      </div>
    </aside>
  );
};

window.ArtifactPanel = ArtifactPanel;
