// ─── Slips Module ─────────────────────────────────────────
var SIGNOFFS = [
  "you knew.",
  "if you know, you know.",
  "culturally sound.",
  "receipts don't lie.",
  "the group chat needs therapy.",
];

var SLIP_MEDIUMS = ['film', 'tv', 'music', 'internet', 'slang'];

var SLIP_DEFAULTS = {
  acronym: '', answer: '', source: '', medium: 'film', setup: '', signoff: 0,
  scheduled_date: null, status: 'draft', performance: null, rated_at: null
};

// ─── Dynamic Font Sizing (binary search) ──────────────────
function fitSingleLine(text, fontFamily, maxWidth, minSize, maxSize) {
  var el = document.createElement('div');
  el.style.cssText = 'position:absolute;left:-9999px;top:-9999px;white-space:nowrap;font-family:' + fontFamily + ';font-weight:900;line-height:100%;visibility:hidden';
  document.body.appendChild(el);
  var lo = minSize || 24, hi = maxSize || 300, best = lo;
  while (lo <= hi) {
    var mid = Math.floor((lo + hi) / 2);
    el.style.fontSize = mid + 'px';
    el.style.letterSpacing = (mid * -0.0125) + 'px';
    el.textContent = text;
    if (el.offsetWidth <= maxWidth) { best = mid; lo = mid + 1; }
    else { hi = mid - 1; }
  }
  document.body.removeChild(el);
  return best;
}

function fitMultiLine(text, fontFamily, maxWidth, maxLines, minSize, maxSize) {
  var el = document.createElement('div');
  el.style.cssText = 'position:absolute;left:-9999px;top:-9999px;font-family:' + fontFamily + ';font-weight:700;line-height:150%;visibility:hidden;text-align:center;word-wrap:break-word';
  el.style.width = maxWidth + 'px';
  document.body.appendChild(el);
  var lo = minSize || 16, hi = maxSize || 48, best = lo;
  while (lo <= hi) {
    var mid = Math.floor((lo + hi) / 2);
    el.style.fontSize = mid + 'px';
    el.textContent = text;
    var lineH = mid * 1.5;
    var lines = Math.ceil(el.offsetHeight / lineH);
    if (lines <= maxLines) { best = mid; lo = mid + 1; }
    else { hi = mid - 1; }
  }
  document.body.removeChild(el);
  return best;
}

// ─── Slide Components ─────────────────────────────────────
function SlipSlide1(props) {
  var data = props.data, sizes = props.sizes;
  var acronymSize = sizes.acronym || 100;
  var ls = acronymSize * -0.0125;
  return (
    <div className="SL-slide">
      <div className="content">
        <div className="acronym" style={{fontSize: acronymSize, letterSpacing: ls, color: '#FFF'}}>{data.acronym}</div>
        <div className="source-line">{(data.source || '').toLowerCase() + ' \u00b7 ' + (data.medium || '')}</div>
      </div>
    </div>
  );
}

function SlipSlide2(props) {
  var data = props.data, sizes = props.sizes;
  var setupSize = sizes.setup || 32;
  return (
    <div className="SL-slide">
      <div className="content">
        <div className="setup-text" style={{fontSize: setupSize, letterSpacing: (setupSize * -0.0125)}}>{data.setup}</div>
      </div>
    </div>
  );
}

function SlipSlide3(props) {
  var data = props.data, sizes = props.sizes;
  var answerSize = sizes.answer || 100;
  var ls = answerSize * -0.0125;
  return (
    <div className="SL-slide">
      <div className="content">
        <div className="answer" style={{fontSize: answerSize, letterSpacing: ls, color: '#FF007F'}}>{data.answer}</div>
        <div className="source-line">{(data.source || '').toLowerCase() + ' \u00b7 ' + (data.medium || '')}</div>
      </div>
    </div>
  );
}

function SlipSlide4(props) {
  var data = props.data, sizes = props.sizes;
  var logoSize = sizes.logo || 120;
  var ls = logoSize * -0.0125;
  var signoffText = SIGNOFFS[data.signoff] || SIGNOFFS[0];
  return (
    <div className="SL-slide">
      <div className="content">
        <div className="logo" style={{fontSize: logoSize, letterSpacing: ls, color: '#FF007F'}}>LINECONIC</div>
        <div className="signoff-text">{signoffText}</div>
      </div>
    </div>
  );
}

// ─── AI Helpers ──────────────────────────────────────────
function selectReferencesForSlips(library, crowdScores) {
  if (!library || !library.length) return [];
  var scored = library.map(function(r) {
    var score = r.lineconic_score || r.scores && r.scores.lineconic_score || 5;
    // Bonus for short answers (≤6 words) — better acronym puzzles
    var answer = r.content && r.content.answer || r.line || '';
    if (answer.split(/\s+/).length <= 6) score += 2;
    // Penalize recently played
    var cs = crowdScores && crowdScores[r.id];
    if (cs && cs.lastPlayed) {
      var daysSince = (Date.now() - new Date(cs.lastPlayed).getTime()) / 86400000;
      if (daysSince < 30) score -= 4;
    }
    score += Math.random() * 1.5;
    return { ref: r, score: score };
  });
  scored.sort(function(a, b) { return b.score - a.score; });
  return scored.slice(0, 150).map(function(s) { return s.ref; });
}

function buildSlipDigest(refs) {
  return refs.map(function(r) {
    var id = r.id || '';
    var answer = r.content && r.content.answer || r.line || '';
    var source = r.source || '';
    var mediaType = r.media_type || '';
    // Map movie → film for slip medium
    if (mediaType === 'movie') mediaType = 'film';
    var ls = r.lineconic_score || r.scores && r.scores.lineconic_score || '';
    var scoreTag = ls ? ' LS:' + ls : '';
    return '[' + id + '] "' + answer + '" — ' + source + ' (' + mediaType + ')' + scoreTag;
  }).join('\n');
}

function fixAcronym(answer) {
  if (!answer) return '';
  return answer.trim().split(/\s+/).map(function(w) { return w.charAt(0).toUpperCase(); }).join('.') + '.';
}

// ─── Main Module ──────────────────────────────────────────
function SlipsModule(props) {
  var db = props.db, showToast = props.showToast;
  var slips = props.slips || {};
  var library = props.library || [];
  var crowdScores = props.crowdScores || {};
  var tasteProfile = props.tasteProfile;

  var [search, setSearch] = useState('');
  var [selectedId, setSelectedId] = useState(null);
  var [editData, setEditData] = useState(null);
  var [saving, setSaving] = useState(false);
  var [deleteConfirm, setDeleteConfirm] = useState(false);
  var [showImport, setShowImport] = useState(false);
  var [importText, setImportText] = useState('');
  var [exporting, setExporting] = useState(false);
  var [sizes, setSizes] = useState({});

  // AI state
  var [aiMode, setAiMode] = useState(false);
  var [aiBrief, setAiBrief] = useState('');
  var [aiCount, setAiCount] = useState(10);
  var [aiMedium, setAiMedium] = useState(null);
  var [aiUseLibrary, setAiUseLibrary] = useState(true);
  var [aiLoading, setAiLoading] = useState(false);
  var [aiPlan, setAiPlan] = useState(null);
  var [aiError, setAiError] = useState(null);
  var [aiRefineText, setAiRefineText] = useState('');
  var [aiRefining, setAiRefining] = useState(false);

  var [isMobile, setIsMobile] = useState(window.innerWidth < 768);
  useEffect(function(){
    function onResize(){setIsMobile(window.innerWidth < 768)}
    window.addEventListener('resize', onResize);
    return function(){window.removeEventListener('resize', onResize)};
  },[]);

  // Derive sorted list
  var slipList = useMemo(function() {
    var arr = Object.values(slips);
    arr.sort(function(a, b) { return (b.created_at || 0) - (a.created_at || 0); });
    if (search) {
      var q = search.toLowerCase();
      arr = arr.filter(function(s) {
        return (s.acronym || '').toLowerCase().indexOf(q) > -1 ||
               (s.answer || '').toLowerCase().indexOf(q) > -1 ||
               (s.source || '').toLowerCase().indexOf(q) > -1;
      });
    }
    return arr;
  }, [slips, search]);

  // Recompute font sizes when editData changes
  useEffect(function() {
    if (!editData) { setSizes({}); return; }
    var contentW = 840;
    var newSizes = {};
    if (editData.acronym) {
      newSizes.acronym = fitSingleLine(editData.acronym, "'Neue Haas Grotesk Display Pro','Impact',sans-serif", contentW, 24, 300);
    }
    if (editData.answer) {
      newSizes.answer = fitSingleLine(editData.answer, "'Neue Haas Grotesk Display Pro','Impact',sans-serif", contentW, 24, 300);
    }
    if (editData.setup) {
      newSizes.setup = fitMultiLine(editData.setup, "'Space Mono',monospace", contentW, 5, 16, 48);
    }
    newSizes.logo = fitSingleLine('LINECONIC', "'Neue Haas Grotesk Display Pro','Impact',sans-serif", contentW, 60, 120);
    setSizes(newSizes);
  }, [editData && editData.acronym, editData && editData.answer, editData && editData.setup]);

  // Select a slip
  function selectSlip(slip) {
    setSelectedId(slip.id);
    setEditData(Object.assign({}, slip));
    setDeleteConfirm(false);
  }

  // New slip
  function newSlip() {
    var id = 'slip-' + Date.now() + '-' + Math.random().toString(36).substr(2, 6);
    var data = Object.assign({}, SLIP_DEFAULTS, { id: id, created_at: Date.now() });
    setSelectedId(id);
    setEditData(data);
    setDeleteConfirm(false);
  }

  // Update field
  function updateField(field, value) {
    setEditData(function(prev) {
      var next = Object.assign({}, prev);
      next[field] = value;
      return next;
    });
  }

  // Save
  function saveSlip() {
    if (!editData || !editData.acronym) { showToast('ACRONYM REQUIRED'); return; }
    setSaving(true);
    var data = Object.assign({}, editData);
    if (!data.created_at) data.created_at = Date.now();
    if (data.scheduled_date && data.status === 'draft') data.status = 'scheduled';
    if (!data.scheduled_date && data.status === 'scheduled') data.status = 'draft';
    db.ref('slips/' + data.id).set(data).then(function() {
      setSaving(false);
      showToast('SAVED');
    }).catch(function(err) {
      setSaving(false);
      showToast('SAVE FAILED: ' + err.message);
    });
  }

  // Delete
  function deleteSlip() {
    if (!selectedId) return;
    db.ref('slips/' + selectedId).remove().then(function() {
      setSelectedId(null);
      setEditData(null);
      setDeleteConfirm(false);
      showToast('DELETED');
    });
  }

  // Bulk import
  function handleImport() {
    try {
      var arr = JSON.parse(importText);
      if (!Array.isArray(arr)) { showToast('MUST BE AN ARRAY'); return; }
      var updates = {};
      arr.forEach(function(item) {
        var id = 'slip-' + Date.now() + '-' + Math.random().toString(36).substr(2, 6);
        updates['slips/' + id] = {
          id: id,
          acronym: (item.acronym || '').toUpperCase(),
          answer: (item.answer || '').toUpperCase(),
          source: item.source || '',
          medium: item.medium || 'film',
          setup: item.setup || '',
          signoff: typeof item.signoff === 'number' ? item.signoff : 0,
          created_at: Date.now()
        };
      });
      db.ref().update(updates).then(function() {
        showToast('IMPORTED ' + arr.length + ' SLIPS');
        setShowImport(false);
        setImportText('');
      });
    } catch(e) {
      showToast('INVALID JSON');
    }
  }

  // ─── AI Generation ───────────────────────────────────────
  function getToken() { return firebase.auth().currentUser.getIdToken(); }

  function generateSlips() {
    if (!aiBrief.trim()) { showToast('BRIEF REQUIRED'); return; }
    setAiLoading(true); setAiError(null); setAiPlan(null); setAiRefineText('');

    var digest = null;
    var totalSize = 0;
    if (aiUseLibrary && library.length) {
      var refs = selectReferencesForSlips(library, crowdScores);
      digest = buildSlipDigest(refs);
      totalSize = library.length;
    }

    var tp = tasteProfile && tasteProfile.content ? tasteProfile.content : null;

    getToken().then(function(token) {
      return aiFetch('/api/ai/generate-slips', {
        method: 'POST',
        headers: { 'Content-Type': 'application/json', 'Authorization': 'Bearer ' + token },
        body: JSON.stringify({ brief: aiBrief, count: aiCount, medium: aiMedium, libraryDigest: digest, totalLibrarySize: totalSize, tasteProfile: tp })
      });
    }).then(function(res) {
      return res.json();
    }).then(function(data) {
      if (!data.ok || !data.plan) throw new Error('Invalid response');
      // Auto-fix acronyms
      var plan = data.plan.map(function(item) {
        var computed = fixAcronym(item.answer);
        if (computed && item.acronym !== computed) item.acronym = computed;
        return item;
      });
      setAiPlan(plan);
      setAiLoading(false);
    }).catch(function(err) {
      setAiError(formatAiError(err));
      setAiLoading(false);
    });
  }

  function refineSlips() {
    if (!aiRefineText.trim() || !aiPlan) return;
    setAiRefining(true); setAiError(null);

    var digest = null;
    var totalSize = 0;
    if (aiUseLibrary && library.length) {
      var refs = selectReferencesForSlips(library, crowdScores);
      digest = buildSlipDigest(refs);
      totalSize = library.length;
    }

    var tp = tasteProfile && tasteProfile.content ? tasteProfile.content : null;

    getToken().then(function(token) {
      return aiFetch('/api/ai/generate-slips', {
        method: 'POST',
        headers: { 'Content-Type': 'application/json', 'Authorization': 'Bearer ' + token },
        body: JSON.stringify({ brief: aiBrief, count: aiCount, medium: aiMedium, libraryDigest: digest, totalLibrarySize: totalSize, tasteProfile: tp, currentPlan: aiPlan, instruction: aiRefineText })
      });
    }).then(function(res) {
      return res.json();
    }).then(function(data) {
      if (!data.ok || !data.plan) throw new Error('Invalid response');
      var plan = data.plan.map(function(item) {
        var computed = fixAcronym(item.answer);
        if (computed && item.acronym !== computed) item.acronym = computed;
        return item;
      });
      setAiPlan(plan);
      setAiRefining(false);
      setAiRefineText('');
    }).catch(function(err) {
      setAiError(formatAiError(err));
      setAiRefining(false);
    });
  }

  function acceptSlip(item) {
    var id = 'slip-' + Date.now() + '-' + Math.random().toString(36).substr(2, 6);
    var data = {
      id: id,
      acronym: (item.acronym || '').toUpperCase(),
      answer: (item.answer || '').toUpperCase(),
      source: item.source || '',
      medium: item.medium || 'film',
      setup: item.setup || '',
      signoff: typeof item.signoff === 'number' ? item.signoff : 0,
      created_at: Date.now(),
      status: 'draft',
      scheduled_date: null,
      performance: null,
      rated_at: null
    };
    db.ref('slips/' + id).set(data).then(function() {
      showToast('ACCEPTED: ' + data.acronym);
    }).catch(function(err) {
      showToast('SAVE FAILED: ' + err.message);
    });
  }

  function acceptAllSlips() {
    if (!aiPlan || !aiPlan.length) return;
    var updates = {};
    aiPlan.forEach(function(item) {
      var id = 'slip-' + Date.now() + '-' + Math.random().toString(36).substr(2, 6);
      updates['slips/' + id] = {
        id: id,
        acronym: (item.acronym || '').toUpperCase(),
        answer: (item.answer || '').toUpperCase(),
        source: item.source || '',
        medium: item.medium || 'film',
        setup: item.setup || '',
        signoff: typeof item.signoff === 'number' ? item.signoff : 0,
        created_at: Date.now(),
        status: 'draft',
        scheduled_date: null,
        performance: null,
        rated_at: null
      };
    });
    db.ref().update(updates).then(function() {
      showToast('ACCEPTED ' + aiPlan.length + ' SLIPS');
    }).catch(function(err) {
      showToast('BATCH SAVE FAILED: ' + err.message);
    });
  }

  function editAiSlip(item) {
    var id = 'slip-' + Date.now() + '-' + Math.random().toString(36).substr(2, 6);
    var data = {
      id: id,
      acronym: (item.acronym || '').toUpperCase(),
      answer: (item.answer || '').toUpperCase(),
      source: item.source || '',
      medium: item.medium || 'film',
      setup: item.setup || '',
      signoff: typeof item.signoff === 'number' ? item.signoff : 0,
      created_at: Date.now()
    };
    setSelectedId(id);
    setEditData(data);
    setAiMode(false);
    setDeleteConfirm(false);
  }

  // PNG export — single slide
  function exportSlide(slideIndex) {
    if (!editData || typeof html2canvas === 'undefined') { showToast('html2canvas NOT LOADED'); return; }
    setExporting(true);

    // Create off-screen full-size container
    var container = document.createElement('div');
    container.style.cssText = 'position:fixed;left:-9999px;top:-9999px;width:1080px;height:1350px';
    document.body.appendChild(container);

    var SlideComponent = [SlipSlide1, SlipSlide2, SlipSlide3, SlipSlide4][slideIndex];
    ReactDOM.render(React.createElement(SlideComponent, { data: editData, sizes: sizes }), container, function() {
      // Remove the scale transform for capture
      var slideEl = container.querySelector('.SL-slide');
      if (slideEl) {
        slideEl.style.transform = 'none';
      }
      setTimeout(function() {
        html2canvas(slideEl || container, {
          width: 1080, height: 1350, scale: 1, backgroundColor: '#000000',
          useCORS: true, logging: false
        }).then(function(canvas) {
          var link = document.createElement('a');
          link.download = 'slip_' + (editData.acronym || 'export') + '_slide' + (slideIndex + 1) + '.png';
          link.href = canvas.toDataURL('image/png');
          link.click();
          document.body.removeChild(container);
          setExporting(false);
          showToast('EXPORTED SLIDE ' + (slideIndex + 1));
        }).catch(function(err) {
          document.body.removeChild(container);
          setExporting(false);
          showToast('EXPORT FAILED');
          console.error(err);
        });
      }, 100);
    });
  }

  // Export all 4 slides
  function exportAll() {
    if (!editData) return;
    setExporting(true);
    var i = 0;
    function next() {
      if (i >= 4) { setExporting(false); return; }
      var idx = i++;
      // Small delay between exports
      setTimeout(function() {
        exportSlideAsync(idx).then(next);
      }, idx === 0 ? 0 : 400);
    }
    next();
  }

  function exportSlideAsync(slideIndex) {
    return new Promise(function(resolve) {
      var container = document.createElement('div');
      container.style.cssText = 'position:fixed;left:-9999px;top:-9999px;width:1080px;height:1350px';
      document.body.appendChild(container);
      var SlideComponent = [SlipSlide1, SlipSlide2, SlipSlide3, SlipSlide4][slideIndex];
      ReactDOM.render(React.createElement(SlideComponent, { data: editData, sizes: sizes }), container, function() {
        var slideEl = container.querySelector('.SL-slide');
        if (slideEl) slideEl.style.transform = 'none';
        setTimeout(function() {
          html2canvas(slideEl || container, {
            width: 1080, height: 1350, scale: 1, backgroundColor: '#000000',
            useCORS: true, logging: false
          }).then(function(canvas) {
            var link = document.createElement('a');
            link.download = 'slip_' + (editData.acronym || 'export') + '_slide' + (slideIndex + 1) + '.png';
            link.href = canvas.toDataURL('image/png');
            link.click();
            document.body.removeChild(container);
            resolve();
          }).catch(function() {
            document.body.removeChild(container);
            resolve();
          });
        }, 100);
      });
    });
  }

  // ─── Render ───────────────────────────────────────────────
  return (
    <div className="SL">
      {/* Left panel — list */}
      <div className="SL-list" style={isMobile ? (editData || aiMode ? {display:'none'} : {maxHeight:'none',borderBottom:'none'}) : undefined}>
        <div className="SL-list-head">
          <input className="A-input" placeholder="SEARCH SLIPS..." value={search} onChange={function(e){setSearch(e.target.value)}} style={{fontSize:11,textTransform:'uppercase',letterSpacing:1}} />
          <div style={{fontSize:10,color:'var(--text-dim)',letterSpacing:1}}>{slipList.length} SLIP{slipList.length !== 1 ? 'S' : ''}</div>
          <div className="SL-list-actions">
            <button className="A-btn signal" style={{flex:1,fontSize:10,padding:'5px 8px'}} onClick={newSlip}>+ NEW</button>
            <button className="A-btn" style={{flex:1,fontSize:10,padding:'5px 8px',background:'var(--gold)',color:'#000',fontWeight:700}} onClick={function(){setAiMode(!aiMode);setEditData(aiMode ? editData : null)}}>{aiMode ? 'CLOSE AI' : 'AI GENERATE'}</button>
            <button className="A-btn cyan" style={{flex:1,fontSize:10,padding:'5px 8px'}} onClick={function(){setShowImport(!showImport)}}>{showImport ? 'CANCEL' : 'IMPORT'}</button>
          </div>
          {showImport && (
            <div>
              <textarea className="A-textarea" rows={6} placeholder='Paste JSON array: [{"acronym":"...","answer":"...","source":"...","medium":"film","setup":"...","signoff":0}]' value={importText} onChange={function(e){setImportText(e.target.value)}} style={{fontSize:10,marginBottom:6}} />
              <button className="A-btn signal" style={{width:'100%',fontSize:10,padding:'5px 8px'}} onClick={handleImport}>IMPORT ALL</button>
            </div>
          )}
        </div>
        <div className="SL-list-items">
          {slipList.map(function(slip) {
            return (
              <div key={slip.id} className={'SL-list-item' + (selectedId === slip.id ? ' on' : '')} onClick={function(){selectSlip(slip)}}>
                <div style={{display:'flex',alignItems:'center',gap:6}}>
                  <span className="acro">{slip.acronym || '—'}</span>
                  {slip.status && slip.status !== 'draft' && (
                    <span style={{fontSize:8,letterSpacing:'.06em',padding:'1px 5px',border:'1px solid',borderColor:slip.status==='published'?'#4ade80':slip.status==='scheduled'?'var(--gold)':'var(--border)',color:slip.status==='published'?'#4ade80':slip.status==='scheduled'?'var(--gold)':'var(--text-dim)'}}>{slip.status.toUpperCase()}</span>
                  )}
                </div>
                <div className="ans">{slip.answer || 'Untitled'}</div>
              </div>
            );
          })}
          {slipList.length === 0 && (
            <div style={{padding:20,textAlign:'center',color:'var(--text-dim)',fontSize:10,letterSpacing:1}}>NO SLIPS YET</div>
          )}
        </div>
      </div>

      {/* Right panel — editor + preview OR AI panel */}
      <div className="SL-right" style={isMobile ? ((editData || aiMode) ? {position:'fixed',inset:0,zIndex:200,background:'#000',overflow:'auto',padding:16} : {display:'none'}) : undefined}>
        {aiMode ? (
          <div className="SL-ai-panel">
            {isMobile && <button className="A-btn" style={{marginBottom:12}} onClick={function(){setAiMode(false);setEditData(null);setSelectedId(null)}}>← BACK</button>}
            <div className="A-section">
              <div className="A-section-head">AI GENERATE</div>

              <div style={{marginBottom:12}}>
                <label className="A-label">BRIEF</label>
                <textarea className="A-textarea" rows={3} value={aiBrief} onChange={function(e){setAiBrief(e.target.value)}} placeholder="creative direction — e.g. 'nostalgia hits for millennials, mix of 90s film and early internet'" style={{fontSize:11}} />
              </div>

              <div style={{display:'flex',flexDirection:isMobile?'column':'row',gap:12,marginBottom:12,alignItems:isMobile?'stretch':'flex-end'}}>
                <div style={{flex:1}}>
                  <label className="A-label">COUNT</label>
                  <input className="A-input" type="number" min={5} max={30} value={aiCount} onChange={function(e){setAiCount(Math.max(5, Math.min(30, parseInt(e.target.value) || 10)))}} style={{fontSize:11}} />
                </div>
                <div style={isMobile ? undefined : {flex:2}}>
                  <label className="A-label">MEDIUM FILTER</label>
                  <div className="SL-chips">
                    <div className={'A-chip' + (!aiMedium ? ' on' : '')} onClick={function(){setAiMedium(null)}}>ALL</div>
                    {SLIP_MEDIUMS.map(function(m) {
                      return <div key={m} className={'A-chip' + (aiMedium === m ? ' on' : '')} onClick={function(){setAiMedium(m)}}>{m.toUpperCase()}</div>;
                    })}
                  </div>
                </div>
              </div>

              <div style={{display:'flex',gap:8,alignItems:'center',marginBottom:12}}>
                <label className="A-label" style={{margin:0}}>USE LIBRARY</label>
                <div className={'A-chip' + (aiUseLibrary ? ' signal' : '')} onClick={function(){setAiUseLibrary(!aiUseLibrary)}} style={{cursor:'pointer'}}>{aiUseLibrary ? 'ON' : 'OFF'}</div>
                {aiUseLibrary && library.length > 0 && <span style={{fontSize:10,color:'var(--text-dim)'}}>{library.length} cards available</span>}
              </div>

              <div className="SL-ai-presets" style={{flexWrap:'wrap'}}>
                <button className="A-btn" style={{fontSize:10,padding:'5px 12px'}} onClick={function(){setAiCount(5);setAiBrief(aiBrief || 'weekly content — mix of iconic film, tv, and music references')}}>WEEK (5)</button>
                <button className="A-btn" style={{fontSize:10,padding:'5px 12px'}} onClick={function(){setAiCount(20);setAiBrief(aiBrief || 'monthly content batch — wide variety across all mediums, balance iconic with deep cuts')}}>MONTH (20)</button>
                <button className="A-btn" style={{fontSize:10,padding:'5px 12px'}} onClick={function(){setAiCount(30);setAiBrief(aiBrief || 'quarterly content pipeline — comprehensive coverage of film, tv, music, internet, and slang')}}>QUARTER (30)</button>
              </div>

              <button className="A-btn signal" style={{width:'100%',fontSize:11,padding:'8px',fontWeight:700}} onClick={generateSlips} disabled={aiLoading}>{aiLoading ? 'GENERATING...' : 'GENERATE'}</button>

              {aiError && <div style={{color:'var(--signal)',fontSize:11,marginTop:8}}>ERROR: {aiError}</div>}
            </div>

            {aiPlan && aiPlan.length > 0 && (
              <div className="A-section">
                <div className="A-section-head" style={{display:'flex',justifyContent:'space-between',alignItems:'center'}}>
                  <span>RESULTS ({aiPlan.length})</span>
                  <button className="A-btn signal" style={{fontSize:10,padding:'4px 12px'}} onClick={acceptAllSlips}>ACCEPT ALL</button>
                </div>

                {aiPlan.map(function(item, i) {
                  return (
                    <div key={i} className="SL-ai-result">
                      <div><span className="acro">{item.acronym}</span><span className="ans">{item.answer}</span></div>
                      <div className="meta">{item.source} · {item.medium} · signoff: {SIGNOFFS[item.signoff] || SIGNOFFS[0]}</div>
                      <div className="setup-preview">{item.setup}</div>
                      <div style={{display:'flex',gap:6,marginTop:8}}>
                        <button className="A-btn signal" style={{fontSize:9,padding:'3px 10px'}} onClick={function(){acceptSlip(item)}}>ACCEPT</button>
                        <button className="A-btn" style={{fontSize:9,padding:'3px 10px'}} onClick={function(){editAiSlip(item)}}>EDIT</button>
                      </div>
                    </div>
                  );
                })}

                <div style={{marginTop:16}}>
                  <label className="A-label">REFINE</label>
                  <div style={{display:'flex',gap:8}}>
                    <textarea className="A-textarea" rows={2} value={aiRefineText} onChange={function(e){setAiRefineText(e.target.value)}} placeholder="e.g. 'replace the music ones with tv references' or 'make the setups more specific'" style={{flex:1,fontSize:11}} />
                    <button className="A-btn cyan" style={{fontSize:10,padding:'6px 16px',alignSelf:'flex-end'}} onClick={refineSlips} disabled={aiRefining}>{aiRefining ? 'REFINING...' : 'REFINE'}</button>
                  </div>
                </div>
              </div>
            )}
          </div>
        ) : !editData ? (
          <div className="A-empty">
            <div className="icon">S</div>
            <div className="msg">SELECT OR CREATE A SLIP</div>
          </div>
        ) : (
          <div>
            {isMobile && <button className="A-btn" style={{marginBottom:12}} onClick={function(){setAiMode(false);setEditData(null);setSelectedId(null)}}>← BACK</button>}
            {/* Editor */}
            <div className="A-section">
              <div className="A-section-head">EDITOR</div>
              <div className="SL-editor">
                <div>
                  <label className="A-label">ACRONYM</label>
                  <input className="A-input" value={editData.acronym || ''} onChange={function(e){updateField('acronym', e.target.value.toUpperCase())}} placeholder="I.A.Y.F." style={{textTransform:'uppercase',fontFamily:'var(--display)',fontSize:16,letterSpacing:2}} />
                </div>
                <div>
                  <label className="A-label">ANSWER</label>
                  <input className="A-input" value={editData.answer || ''} onChange={function(e){updateField('answer', e.target.value.toUpperCase())}} placeholder="I AM YOUR FATHER" style={{textTransform:'uppercase'}} />
                </div>
                <div>
                  <label className="A-label">SOURCE</label>
                  <input className="A-input" value={editData.source || ''} onChange={function(e){updateField('source', e.target.value)}} placeholder="Star Wars" />
                </div>
                <div>
                  <label className="A-label">MEDIUM</label>
                  <div className="SL-chips">
                    {SLIP_MEDIUMS.map(function(m) {
                      return <div key={m} className={'A-chip' + (editData.medium === m ? ' on' : '')} onClick={function(){updateField('medium', m)}}>{m.toUpperCase()}</div>;
                    })}
                  </div>
                </div>
                <div className="SL-editor-full">
                  <label className="A-label">SETUP</label>
                  <textarea className="A-textarea" rows={3} value={editData.setup || ''} onChange={function(e){updateField('setup', e.target.value)}} placeholder="the relatable scenario text..." />
                </div>
                <div className="SL-editor-full">
                  <label className="A-label">SIGNOFF</label>
                  <div className="SL-chips">
                    {SIGNOFFS.map(function(s, i) {
                      return <div key={i} className={'A-chip' + (editData.signoff === i ? ' signal' : '')} onClick={function(){updateField('signoff', i)}}>{s}</div>;
                    })}
                  </div>
                </div>
                <div>
                  <label className="A-label">SCHEDULED DATE</label>
                  <input className="A-input" type="date" value={editData.scheduled_date || ''} onChange={function(e){updateField('scheduled_date', e.target.value || null)}} style={{fontSize:11}} />
                </div>
                <div>
                  <label className="A-label">STATUS</label>
                  <div className="SL-chips">
                    {['draft','scheduled','published'].map(function(s) {
                      return <div key={s} className={'A-chip' + (editData.status === s ? ' signal' : '')} onClick={function(){updateField('status', s)}}>{s.toUpperCase()}</div>;
                    })}
                  </div>
                </div>
                <div className="SL-editor-full" style={{display:'flex',gap:8,marginTop:4}}>
                  <button className="A-btn signal" onClick={saveSlip} disabled={saving}>{saving ? 'SAVING...' : 'SAVE'}</button>
                  {!deleteConfirm ? (
                    <button className="A-btn danger" onClick={function(){setDeleteConfirm(true)}}>DELETE</button>
                  ) : (
                    <button className="A-btn danger" onClick={deleteSlip} style={{fontWeight:700}}>CONFIRM DELETE</button>
                  )}
                </div>
              </div>
            </div>

            {/* Preview */}
            <div className="A-section">
              <div className="A-section-head">PREVIEW</div>
              <div className="SL-preview-row">
                <div className="SL-slide-wrap"><SlipSlide1 data={editData} sizes={sizes} /></div>
                <div className="SL-slide-wrap"><SlipSlide2 data={editData} sizes={sizes} /></div>
                <div className="SL-slide-wrap"><SlipSlide3 data={editData} sizes={sizes} /></div>
                <div className="SL-slide-wrap"><SlipSlide4 data={editData} sizes={sizes} /></div>
              </div>
            </div>

            {/* Export */}
            <div className="A-section">
              <div className="A-section-head">EXPORT</div>
              <div className="SL-export-row">
                <button className="A-btn" onClick={function(){exportSlide(0)}} disabled={exporting}>SLIDE 1</button>
                <button className="A-btn" onClick={function(){exportSlide(1)}} disabled={exporting}>SLIDE 2</button>
                <button className="A-btn" onClick={function(){exportSlide(2)}} disabled={exporting}>SLIDE 3</button>
                <button className="A-btn" onClick={function(){exportSlide(3)}} disabled={exporting}>SLIDE 4</button>
                <button className="A-btn signal" onClick={exportAll} disabled={exporting}>{exporting ? 'EXPORTING...' : 'EXPORT ALL'}</button>
              </div>
            </div>
          </div>
        )}
      </div>
    </div>
  );
}
