// ====================================================================
// BENCHMARKS PAGE, three-rail compare + Playbook adherence
// You vs Goal vs System vs Playbook
// ====================================================================

(function () {

// Inline icons for playbook concepts not in the main Icon library
const PB = {
  search:  <svg viewBox="0 0 24 24" width="16" height="16" fill="none" stroke="currentColor" strokeWidth="1.8" strokeLinecap="round" strokeLinejoin="round"><circle cx="11" cy="11" r="7"/><path d="M21 21l-4.3-4.3"/></svg>,
  dollar:  <svg viewBox="0 0 24 24" width="16" height="16" fill="none" stroke="currentColor" strokeWidth="1.8" strokeLinecap="round" strokeLinejoin="round"><path d="M12 2v20M17 5H9.5a3.5 3.5 0 000 7h5a3.5 3.5 0 010 7H6"/></svg>,
  layers:  <svg viewBox="0 0 24 24" width="16" height="16" fill="none" stroke="currentColor" strokeWidth="1.8" strokeLinecap="round" strokeLinejoin="round"><path d="M12 2l9 5-9 5-9-5zM3 12l9 5 9-5M3 17l9 5 9-5"/></svg>,
  share:   <svg viewBox="0 0 24 24" width="16" height="16" fill="none" stroke="currentColor" strokeWidth="1.8" strokeLinecap="round" strokeLinejoin="round"><circle cx="18" cy="5" r="3"/><circle cx="6" cy="12" r="3"/><circle cx="18" cy="19" r="3"/><path d="M8.6 13.5l6.8 4M15.4 6.5l-6.8 4"/></svg>,
  globe:   <svg viewBox="0 0 24 24" width="16" height="16" fill="none" stroke="currentColor" strokeWidth="1.8" strokeLinecap="round" strokeLinejoin="round"><circle cx="12" cy="12" r="9"/><path d="M3 12h18M12 3a14 14 0 010 18M12 3a14 14 0 000 18"/></svg>,
  trend:   <svg viewBox="0 0 24 24" width="16" height="16" fill="none" stroke="currentColor" strokeWidth="1.8" strokeLinecap="round" strokeLinejoin="round"><path d="M3 17l6-6 4 4 8-8M14 7h7v7"/></svg>,
  trendDn: <svg viewBox="0 0 24 24" width="16" height="16" fill="none" stroke="currentColor" strokeWidth="1.8" strokeLinecap="round" strokeLinejoin="round"><path d="M3 7l6 6 4-4 8 8M14 17h7v-7"/></svg>,
  stack:   <svg viewBox="0 0 24 24" width="16" height="16" fill="none" stroke="currentColor" strokeWidth="1.8" strokeLinecap="round" strokeLinejoin="round"><path d="M12 2l9 5-9 5-9-5zM3 12l9 5 9-5M3 17l9 5 9-5"/></svg>,
  grid:    <svg viewBox="0 0 24 24" width="16" height="16" fill="none" stroke="currentColor" strokeWidth="1.8" strokeLinecap="round" strokeLinejoin="round"><rect x="3" y="3" width="7" height="7"/><rect x="14" y="3" width="7" height="7"/><rect x="3" y="14" width="7" height="7"/><rect x="14" y="14" width="7" height="7"/></svg>,
  target:  <svg viewBox="0 0 24 24" width="16" height="16" fill="none" stroke="currentColor" strokeWidth="1.8" strokeLinecap="round" strokeLinejoin="round"><circle cx="12" cy="12" r="9"/><circle cx="12" cy="12" r="5"/><circle cx="12" cy="12" r="1.2" fill="currentColor"/></svg>,
  eye:     <svg viewBox="0 0 24 24" width="16" height="16" fill="none" stroke="currentColor" strokeWidth="1.8" strokeLinecap="round" strokeLinejoin="round"><path d="M2 12s3.5-7 10-7 10 7 10 7-3.5 7-10 7S2 12 2 12z"/><circle cx="12" cy="12" r="3"/></svg>,
  tag:     <svg viewBox="0 0 24 24" width="16" height="16" fill="none" stroke="currentColor" strokeWidth="1.8" strokeLinecap="round" strokeLinejoin="round"><path d="M20.6 13.4L13 21a2 2 0 01-2.8 0l-7.2-7.2a2 2 0 010-2.8L10.6 3.4a2 2 0 011.4-.6h7.2a2 2 0 012 2v7.2a2 2 0 01-.6 1.4z"/><circle cx="16" cy="8" r="1.2" fill="currentColor"/></svg>,
  refresh: <svg viewBox="0 0 24 24" width="16" height="16" fill="none" stroke="currentColor" strokeWidth="1.8" strokeLinecap="round" strokeLinejoin="round"><path d="M3 12a9 9 0 0115-6.7L21 8M21 4v4h-4M21 12a9 9 0 01-15 6.7L3 16M3 20v-4h4"/></svg>,
  doc:     <svg viewBox="0 0 24 24" width="16" height="16" fill="none" stroke="currentColor" strokeWidth="1.8" strokeLinecap="round" strokeLinejoin="round"><path d="M14 2H6a2 2 0 00-2 2v16a2 2 0 002 2h12a2 2 0 002-2V8zM14 2v6h6M9 13h6M9 17h6"/></svg>,
  bulb:    <svg viewBox="0 0 24 24" width="16" height="16" fill="none" stroke="currentColor" strokeWidth="1.8" strokeLinecap="round" strokeLinejoin="round"><path d="M9 18h6M10 22h4M12 2a7 7 0 00-4 12.7c1 .8 1.5 2 1.5 3.3h5c0-1.3.5-2.5 1.5-3.3A7 7 0 0012 2z"/></svg>,
  rocket:  <svg viewBox="0 0 24 24" width="16" height="16" fill="none" stroke="currentColor" strokeWidth="1.8" strokeLinecap="round" strokeLinejoin="round"><path d="M14 4l6 6-9 9-6 1 1-6zM14 4a7 7 0 016 6M5 19l-2 2"/></svg>,
  chart:   <svg viewBox="0 0 24 24" width="16" height="16" fill="none" stroke="currentColor" strokeWidth="1.8" strokeLinecap="round" strokeLinejoin="round"><path d="M4 20V10M10 20V4M16 20v-8M22 20H2"/></svg>,
  warn:    <svg viewBox="0 0 16 16" width="14" height="14" fill="none" stroke="currentColor" strokeWidth="1.8" strokeLinecap="round" strokeLinejoin="round"><path d="M8 1.5L1 14h14zM8 6.5v3M8 12h.01"/></svg>,
  check:   <svg viewBox="0 0 16 16" width="14" height="14" fill="none" stroke="currentColor" strokeWidth="2" strokeLinecap="round" strokeLinejoin="round"><path d="M13 4L6 11.5 3 8.5"/></svg>,
};

const T = window.toast || (() => {});

// Routes config / recommendation actions to Settings → Network Playbook
// (the decision system). Works whether or not Settings is already mounted.
function goPlaybookSettings(note) {
  window.__settingsTab = 'playbook';
  window.dispatchEvent(new CustomEvent('set-settings-tab', { detail: 'playbook' }));
  window.dispatchEvent(new CustomEvent('go-page', { detail: 'settings' }));
  T('Opening playbook settings', note || 'Network Playbook · configure the decision system', 'info');
}

// ----- Channel scale-signal chips (business outcome + when to invest) -----
// Reads window.CHANNEL_PLAYBOOK so outcome + scale signals stay consistent
// everywhere a channel is called out (local rows, HQ table, Settings).
function SignalChip({ children }) {
  return (
    <span style={{ display: 'inline-flex', alignItems: 'center', fontSize: 10, fontFamily: 'var(--ff-mono)', color: 'var(--ink-3)', background: 'var(--cream)', border: '1px solid var(--cream-3)', borderRadius: 999, padding: '2px 8px', whiteSpace: 'nowrap' }}>{children}</span>
  );
}
function ScaleWhenLabel() {
  return (
    <span style={{ display: 'inline-flex', alignItems: 'center', gap: 4, fontSize: 9.5, fontWeight: 700, color: 'var(--sage)', textTransform: 'uppercase', letterSpacing: '0.05em' }}>
      <svg viewBox="0 0 24 24" width="11" height="11" fill="none" stroke="currentColor" strokeWidth="2.2" strokeLinecap="round" strokeLinejoin="round"><path d="M3 17l6-6 4 4 8-8M14 7h7v7"/></svg>
      Scale when
    </span>
  );
}
// Inline meta for a channel row: one-line outcome + scale-signal chips.
function ChannelMeta({ ck }) {
  const cp = window.channelPlay && window.channelPlay(ck);
  if (!cp) return null;
  return (
    <div style={{ marginTop: 10, paddingTop: 10, borderTop: '1px dashed var(--cream-3)' }}>
      <div style={{ fontSize: 11.5, color: 'var(--ink-2)', lineHeight: 1.5, marginBottom: 7 }}>{cp.outcome}</div>
      <div style={{ display: 'flex', alignItems: 'center', gap: 6, flexWrap: 'wrap' }}>
        <ScaleWhenLabel/>
        {cp.signals.map((s, i) => <SignalChip key={i}>{s}</SignalChip>)}
      </div>
    </div>
  );
}
// Reference grid of channels, each a card with outcome + scale signals.
function ChannelPlaybookGrid({ keys, cols }) {
  const cp = window.CHANNEL_PLAYBOOK;
  if (!cp) return null;
  const list = (keys || cp.order).map(k => ({ k, ...cp.channels[k] })).filter(x => x.label);
  return (
    <div style={{ display: 'grid', gridTemplateColumns: `repeat(${cols || 3}, 1fr)`, gap: 12 }}>
      {list.map(c => (
        <div key={c.k} className="card card-pad" style={{ padding: 14 }}>
          <div style={{ fontFamily: 'var(--ff-display)', fontSize: 13.5, fontWeight: 600, color: 'var(--ink)', marginBottom: 5, letterSpacing: '-0.01em' }}>{c.label}</div>
          <div style={{ fontSize: 11.5, color: 'var(--ink-2)', lineHeight: 1.5, marginBottom: 10 }}>{c.outcome}</div>
          <div style={{ display: 'flex', alignItems: 'center', gap: 6, flexWrap: 'wrap' }}>
            <ScaleWhenLabel/>
            {c.signals.map((s, i) => <SignalChip key={i}>{s}</SignalChip>)}
          </div>
        </div>
      ))}
    </div>
  );
}
window.ChannelMeta = ChannelMeta;
window.ChannelPlaybookGrid = ChannelPlaybookGrid;

// ----- mini SVG sparkline-ish "rail", 4 markers along a track -----
function CompareRail({ row }) {
  const vals = [row.you, row.goal, row.play, row.peer].filter(v => typeof v === 'number');
  const min = Math.min(...vals), max = Math.max(...vals);
  const pad = (max - min) * 0.15 || max * 0.1 || 1;
  const lo = min - pad, hi = max + pad;
  const span = hi - lo;
  const pos = v => ((v - lo) / span) * 100;
  const better = row.better === 'higher'
    ? (row.you >= row.play && row.you >= row.peer)
    : (row.you <= row.play && row.you <= row.peer);
  const fmt = (v) => {
    if (row.unit === '$') return '$' + v;
    if (row.unit === '%') return v + '%';
    if (row.unit === '★') return v.toFixed(1) + '★';
    if (row.unit === 'h') return v + 'h';
    return v;
  };
  return (
    <div style={{ position: 'relative' }}>
      <div style={{ position: 'relative', height: 8, background: 'var(--cream-2)', borderRadius: 4 }}>
        {/* peer median tick */}
        <div title={`System median: ${fmt(row.peer)}`} style={{ position: 'absolute', left: pos(row.peer) + '%', top: -2, width: 2, height: 12, background: 'var(--ink-5)', transform: 'translateX(-1px)' }}/>
        {/* playbook target tick */}
        <div title={`Playbook target: ${fmt(row.play)}`} style={{ position: 'absolute', left: pos(row.play) + '%', top: -4, width: 0, height: 0,
          borderLeft: '5px solid transparent', borderRight: '5px solid transparent', borderBottom: '8px solid var(--violet)',
          transform: 'translateX(-5px)' }}/>
        <div title={`Playbook target: ${fmt(row.play)}`} style={{ position: 'absolute', left: pos(row.play) + '%', top: 8, width: 0, height: 0,
          borderLeft: '5px solid transparent', borderRight: '5px solid transparent', borderTop: '8px solid var(--violet)',
          transform: 'translateX(-5px)' }}/>
        {/* goal tick */}
        <div title={`Your goal: ${fmt(row.goal)}`} style={{ position: 'absolute', left: pos(row.goal) + '%', top: -3, width: 2, height: 14, background: 'var(--marigold)', transform: 'translateX(-1px)' }}/>
        {/* you marker */}
        <div title={`You: ${fmt(row.you)}`} style={{ position: 'absolute', left: pos(row.you) + '%', top: -4, width: 16, height: 16, borderRadius: '50%', background: better ? 'var(--sage)' : 'var(--terra)', border: '3px solid var(--paper)', boxShadow: '0 1px 3px rgba(0,0,0,.15)', transform: 'translateX(-8px)' }}/>
      </div>
      <div style={{ display: 'flex', justifyContent: 'space-between', fontSize: 9.5, color: 'var(--ink-4)', marginTop: 6, fontFamily: 'var(--ff-mono)' }}>
        <span>{row.better === 'higher' ? 'lower' : 'higher'}</span>
        <span>{row.better === 'higher' ? 'higher' : 'lower'}</span>
      </div>
    </div>
  );
}

// ----- Legend chip -----
function LegendChip({ swatch, label, sub }) {
  return (
    <div style={{ display: 'inline-flex', alignItems: 'center', gap: 8, padding: '6px 10px', background: 'var(--paper)', border: '1px solid var(--cream-3)', borderRadius: 8 }}>
      {swatch}
      <div style={{ fontSize: 11.5 }}>
        <div style={{ fontWeight: 600, color: 'var(--ink)' }}>{label}</div>
        {sub && <div style={{ fontSize: 10, color: 'var(--ink-4)' }}>{sub}</div>}
      </div>
    </div>
  );
}

// ----- Stage gauge: Learning → Stabilization → Scaling -----
function StageGauge({ stages, currentKey, monthsLive }) {
  return (
    <div style={{ display: 'grid', gridTemplateColumns: 'repeat(3, 1fr)', gap: 10, position: 'relative' }}>
      {stages.map((s, i) => {
        const active = s.key === currentKey;
        const passed = stages.findIndex(x => x.key === currentKey) > i;
        const ic = PB[s.icon] || PB.bulb;
        const accent = s.key === 'learning' ? 'var(--marigold)' : s.key === 'stabilization' ? 'var(--terra-3)' : 'var(--sage)';
        return (
          <div key={s.key} style={{
            border: active ? `2px solid ${accent}` : '1px solid var(--cream-3)',
            background: active ? 'var(--paper)' : passed ? 'var(--cream)' : 'var(--paper)',
            borderRadius: 12, padding: '14px 14px 12px', position: 'relative',
            opacity: passed ? 0.7 : 1
          }}>
            {active && <div style={{ position: 'absolute', top: -10, left: 14, background: accent, color: 'var(--ink)', fontSize: 10, fontWeight: 700, padding: '2px 8px', borderRadius: 6, letterSpacing: '0.04em' }}>YOU ARE HERE</div>}
            <div style={{ display: 'flex', alignItems: 'center', gap: 8, marginBottom: 6 }}>
              <div style={{ width: 26, height: 26, borderRadius: 6, background: passed ? 'var(--sage-soft)' : active ? `${accent}33` : 'var(--cream-2)', color: passed ? 'var(--sage)' : 'var(--ink-2)', display: 'flex', alignItems: 'center', justifyContent: 'center' }}>
                {passed ? PB.check : ic}
              </div>
              <div style={{ fontWeight: 600, fontFamily: 'var(--ff-display)', fontSize: 14 }}>{s.title}</div>
            </div>
            <div style={{ fontFamily: 'var(--ff-mono)', fontSize: 10.5, color: 'var(--ink-4)', textTransform: 'uppercase', letterSpacing: '0.06em', marginBottom: 8 }}>{s.window}</div>
            <div style={{ fontSize: 11.5, color: 'var(--ink-3)', lineHeight: 1.5 }}>{s.copy}</div>
            {active && (
              <div style={{ marginTop: 10, paddingTop: 8, borderTop: '1px dashed var(--cream-3)', fontSize: 11, color: 'var(--ink-2)' }}>
                <strong>Month {monthsLive}</strong> · You've been past Stabilization for {Math.max(0, monthsLive - 4)} months, performance compounds from here.
              </div>
            )}
          </div>
        );
      })}
    </div>
  );
}

// ----- Growth Framework progress -----
function GrowthFrameworkRail({ steps, status }) {
  const byKey = Object.fromEntries(status.map(s => [s.key, s]));
  return (
    <div>
      {steps.map((s, i) => {
        const st = byKey[s.key] || { status: 'not-started', detail: '' };
        const ic = PB[s.icon] || PB.bulb;
        const dotBg = st.status === 'complete' ? 'var(--sage)' : st.status === 'in-progress' ? 'var(--marigold)' : 'var(--ink-5)';
        const dotFg = st.status === 'complete' ? 'var(--paper)' : st.status === 'in-progress' ? 'var(--ink)' : 'var(--paper)';
        const labelChip =
          st.status === 'complete' ? <span className="badge badge-ok" style={{ fontSize: 10 }}>Complete</span> :
          st.status === 'in-progress' ? <span className="badge badge-warn" style={{ fontSize: 10 }}>In progress</span> :
          <span className="badge badge-neutral" style={{ fontSize: 10 }}>Not started</span>;
        return (
          <div key={s.key} style={{ display: 'grid', gridTemplateColumns: '36px 1fr auto', gap: 14, alignItems: 'flex-start', padding: '14px 0', borderBottom: i === steps.length - 1 ? 'none' : '1px solid var(--cream-2)' }}>
            <div style={{ position: 'relative' }}>
              <div style={{ width: 32, height: 32, borderRadius: '50%', background: dotBg, color: dotFg, display: 'flex', alignItems: 'center', justifyContent: 'center', fontWeight: 700, fontSize: 13 }}>
                {st.status === 'complete' ? PB.check : s.n}
              </div>
              {i < steps.length - 1 && (
                <div style={{ position: 'absolute', top: 36, left: 15, width: 2, height: 'calc(100% + 14px)', background: st.status === 'complete' ? 'var(--sage)' : 'var(--cream-3)' }}/>
              )}
            </div>
            <div>
              <div style={{ display: 'flex', alignItems: 'center', gap: 10, marginBottom: 4 }}>
                <span style={{ color: 'var(--ink-2)' }}>{ic}</span>
                <div style={{ fontFamily: 'var(--ff-display)', fontSize: 15, fontWeight: 600 }}>{s.title}</div>
                {labelChip}
              </div>
              <div style={{ fontSize: 12.5, color: 'var(--ink-3)', lineHeight: 1.5 }}>{s.copy}</div>
              {st.detail && (
                <div style={{ fontSize: 11.5, color: st.status === 'complete' ? 'var(--sage)' : st.status === 'in-progress' ? '#917200' : 'var(--ink-4)', marginTop: 6, fontFamily: 'var(--ff-mono)' }}>
                  → {st.detail}
                </div>
              )}
            </div>
            <div>
              {st.status !== 'complete' && (
                <button className="btn btn-quiet btn-xs" onClick={() => T('Plan opened', `Lenny is drafting steps for "${s.title}".`, 'info')}>
                  {st.status === 'in-progress' ? 'Continue →' : 'Start →'}
                </button>
              )}
            </div>
          </div>
        );
      })}
    </div>
  );
}

// ----- Foundation checklist -----
function FoundationGroup({ group, status, onToggle }) {
  const tasks = group.tasks || [];
  const done = tasks.filter(t => status[t.id]).length;
  const tier = group.tier;
  return (
    <div className="card card-pad" style={{ marginBottom: 14 }}>
      <div style={{ display: 'flex', alignItems: 'center', gap: 10, marginBottom: 10 }}>
        <span className={tier === 'Required' ? 'badge badge-bad' : 'badge badge-info'} style={{ fontSize: 10 }}>{tier}</span>
        <div style={{ fontFamily: 'var(--ff-display)', fontSize: 15, fontWeight: 600 }}>{group.title}</div>
        <div style={{ marginLeft: 'auto', fontSize: 11.5, color: 'var(--ink-3)', fontFamily: 'var(--ff-mono)' }}>{done} / {tasks.length} complete</div>
      </div>
      {group.why && (
        <div style={{ background: 'var(--cream)', padding: '8px 12px', borderRadius: 8, marginBottom: 12 }}>
          <div style={{ fontSize: 10.5, fontWeight: 700, color: 'var(--ink-3)', textTransform: 'uppercase', letterSpacing: '0.06em', marginBottom: 4 }}>Why it matters</div>
          <ul style={{ margin: 0, paddingLeft: 18, fontSize: 12, color: 'var(--ink-2)', lineHeight: 1.6 }}>
            {group.why.map((w, i) => <li key={i}>{w}</li>)}
          </ul>
        </div>
      )}
      <div>
        {tasks.map(t => {
          const checked = !!status[t.id];
          return (
            <div key={t.id} style={{ display: 'flex', alignItems: 'center', gap: 12, padding: '10px 0', borderBottom: '1px solid var(--cream-2)' }}>
              <button onClick={() => onToggle(t.id)} style={{ width: 20, height: 20, borderRadius: 5, border: checked ? '0' : '1.5px solid var(--ink-5)', background: checked ? 'var(--sage)' : 'var(--paper)', color: 'var(--paper)', display: 'flex', alignItems: 'center', justifyContent: 'center', cursor: 'pointer', flexShrink: 0 }}>
                {checked && PB.check}
              </button>
              <div style={{ flex: 1, fontSize: 13, color: checked ? 'var(--ink-3)' : 'var(--ink)', textDecoration: checked ? 'line-through' : 'none' }}>{t.label}</div>
              {!checked && <button className="btn btn-quiet btn-xs" onClick={() => T('Set up', t.label, 'info')}>Set up</button>}
            </div>
          );
        })}
      </div>
    </div>
  );
}

// ----- Channel adherence row -----
function ChannelAdherenceRow({ row, idx, last, onEnroll, onIncrease }) {
  const tone =
    row.status === 'on-target' ? { bg: 'var(--sage-soft)', col: 'var(--sage)', label: 'On playbook' } :
    row.status === 'above'     ? { bg: 'var(--sky-soft)',  col: 'var(--sky)',  label: 'Above target' } :
    row.status === 'below'     ? { bg: 'var(--marigold-soft)', col: '#917200', label: 'Below target' } :
                                 { bg: 'var(--berry-soft)', col: '#a12118', label: 'Off playbook' };
  const pct = row.recommended ? Math.min(150, Math.round((row.spend / row.recommended) * 100)) : null;
  return (
    <div style={{ padding: '14px 0', borderBottom: last ? 'none' : '1px solid var(--cream-2)' }}>
      <div style={{ display: 'grid', gridTemplateColumns: '1.2fr 1fr 1.4fr auto', gap: 14, alignItems: 'center' }}>
      <div>
        <div style={{ fontWeight: 600, fontSize: 13 }}>{row.name}</div>
        <div style={{ fontSize: 11, color: 'var(--ink-4)', marginTop: 2 }}>{row.enrolled ? 'Enrolled' : 'Not enrolled'}</div>
      </div>
      <div style={{ fontFamily: 'var(--ff-mono)', fontSize: 12 }}>
        {row.recommended > 0 ? (
          <>
            <div style={{ color: 'var(--ink)' }}>${row.spend} <span style={{ color: 'var(--ink-4)' }}>/ ${row.recommended} target</span></div>
            <div style={{ marginTop: 4, height: 4, background: 'var(--cream-2)', borderRadius: 2, overflow: 'hidden' }}>
              <div style={{ width: Math.min(100, pct) + '%', height: '100%', background: tone.col }}/>
            </div>
          </>
        ) : (
          <div style={{ color: 'var(--ink-4)', fontStyle: 'italic' }}>No spend target</div>
        )}
      </div>
      <div>
        <span style={{ display: 'inline-flex', alignItems: 'center', gap: 6, fontSize: 11.5, fontWeight: 600, color: tone.col, background: tone.bg, padding: '4px 10px', borderRadius: 12 }}>
          <span style={{ width: 6, height: 6, borderRadius: '50%', background: tone.col }}/>
          {tone.label}
        </span>
      </div>
      <div>
        {row.status === 'off-playbook' && <button className="btn btn-terra btn-xs" onClick={() => onEnroll(row)}>Enroll →</button>}
        {row.status === 'below' && <button className="btn btn-ghost btn-xs" onClick={() => onIncrease(row)}>Increase →</button>}
      </div>
      </div>
      <ChannelMeta ck={row.key}/>
    </div>
  );
}

// ====================================================================
// SERVICE RECOMMENDATION TILES
// Every service recommendation must justify itself: a performance-tied
// reason (Why) and the business outcome it drives (Outcome). Tiles are
// secondary by default and live below the performance content. The one
// exception: a service whose non-adoption is directly dragging results
// gets promoted with an "Affecting results" treatment, and it leads.
// ====================================================================
function ServiceReasoning({ svc, compact }) {
  const rows = [
    { label: 'Why', color: 'var(--ink-4)', text: svc.why },
    { label: 'Outcome', color: 'var(--sage)', text: svc.outcome },
  ];
  return (
    <div style={{ display: 'grid', gap: compact ? 6 : 8, margin: compact ? '8px 0 12px' : '12px 0 16px' }}>
      {rows.map(r => (
        <div key={r.label} style={{ display: 'flex', gap: 10 }}>
          <span style={{ fontSize: 9.5, fontWeight: 700, color: r.color, textTransform: 'uppercase', letterSpacing: '0.05em', flexShrink: 0, width: 58, paddingTop: 2 }}>{r.label}</span>
          <span style={{ fontSize: 11.5, color: 'var(--ink-2)', lineHeight: 1.5 }}>{r.text}</span>
        </div>
      ))}
    </div>
  );
}

// Secondary tile, muted. Used for the low-priority "in the playbook" list.
function SubtleServiceTile({ svc, onDismiss, onDetail, onAdd }) {
  return (
    <div style={{ position: 'relative', background: 'var(--paper)', border: '1px solid var(--cream-3)', borderRadius: 12, padding: '14px 16px' }}>
      <div style={{ display: 'flex', alignItems: 'center', gap: 8, marginBottom: 6 }}>
        <span style={{ width: 8, height: 8, borderRadius: '50%', background: svc.accent, flexShrink: 0 }}/>
        <span style={{ fontFamily: 'var(--ff-display)', fontSize: 14, fontWeight: 600, color: 'var(--ink)' }}>{svc.name}</span>
        <span style={{ flex: 1 }}/>
        <span style={{ fontSize: 10, color: 'var(--ink-4)', fontFamily: 'var(--ff-mono)' }}>{svc.category}</span>
        <button onClick={onDismiss} style={{ background: 'transparent', border: 'none', cursor: 'pointer', color: 'var(--ink-4)', fontSize: 14, lineHeight: 1, padding: 0 }} aria-label="Dismiss">×</button>
      </div>
      <ServiceReasoning svc={svc} compact/>
      <div style={{ display: 'flex', alignItems: 'center', gap: 12, fontSize: 10.5, color: 'var(--ink-4)', fontFamily: 'var(--ff-mono)' }}>
        <span>{svc.recommendedSpend > 0 ? '$' + svc.recommendedSpend + '/mo' : 'No added cost'}</span>
        <span>·</span>
        <span>Unlocks at {svc.unlocks}</span>
        <span style={{ flex: 1 }}/>
        <button className="btn btn-quiet btn-xs" onClick={onDetail}>{svc.ctaSecondary}</button>
        <button className="btn btn-quiet btn-xs" onClick={onAdd}>{svc.ctaPrimary} →</button>
      </div>
    </div>
  );
}

// Promoted tile, the exception. Non-adoption is directly hurting results.
function AffectingServiceTile({ svc, onDetail, onAdd }) {
  return (
    <div className="card" style={{ marginBottom: 16, background: 'var(--berry-soft)', border: '1px solid var(--berry)', borderRadius: 14, padding: '18px 20px' }}>
      <div style={{ display: 'flex', alignItems: 'center', gap: 10, marginBottom: 10, flexWrap: 'wrap' }}>
        <span style={{ display: 'inline-flex', alignItems: 'center', gap: 6, fontSize: 10.5, fontWeight: 700, color: '#a12118', background: 'var(--paper)', padding: '4px 10px', borderRadius: 999, textTransform: 'uppercase', letterSpacing: '0.05em' }}>{PB.warn} Affecting results</span>
        <span style={{ fontSize: 11.5, color: 'var(--ink-3)' }}>A recommended service isn't running, and it's holding performance back.</span>
      </div>
      <div style={{ fontFamily: 'var(--ff-display)', fontSize: 19, fontWeight: 600, color: 'var(--ink)', letterSpacing: '-0.01em', marginBottom: 6 }}>{svc.name}</div>
      <div style={{ fontSize: 13, color: 'var(--ink-2)', lineHeight: 1.55, marginBottom: 4, maxWidth: 780 }}>{svc.resultsNote}</div>
      <ServiceReasoning svc={svc}/>
      <div style={{ display: 'flex', gap: 8 }}>
        <button className="btn btn-primary btn-sm" style={{ background: 'var(--terra)', borderColor: 'var(--terra)' }} onClick={onAdd}>{svc.ctaPrimary} →</button>
        <button className="btn btn-ghost btn-sm" onClick={onDetail}>{svc.ctaSecondary}</button>
      </div>
    </div>
  );
}

// ====================================================================
// STRATEGIC SUMMARY, top-of-playbook. Frames WHY (problem + business
// impact) before the WHAT (growth strategy + channel pillars). Shows
// identically for corporate and local, it's the first thing they see.
// ====================================================================
function StrategicSummary({ persona }) {
  const phases = [
    { t: 'Maximize search first', c: 'var(--terra)' },
    { t: 'scale until efficiency declines', c: 'var(--sky)' },
    { t: 'layer in social', c: 'var(--marigold)' },
    { t: 'strengthen local foundation', c: 'var(--sage)' },
  ];
  const pillars = [
    { head: 'Prioritize intent-driven channels',
      body: 'Run search and local-intent channels at smaller budgets. They capture people already looking, so conversion is higher and waste is lower, every dollar works harder.' },
    { head: 'Keep awareness efficient',
      body: 'Maintain visibility, but lean toward efficient channels like Google Business Profile and Performance Max rather than broad, expensive reach.' },
    { head: 'Retarget warm audiences',
      body: 'Re-engage people who already know you (Meta retargeting, Meta in-app lead gen) for lower cost and higher conversion likelihood.' },
  ];
  return (
    <div className="card" style={{ marginBottom: 16, overflow: 'hidden', border: '1px solid var(--violet-soft)' }}>
      {/* Framing strip: the problem + the business impact */}
      <div style={{ display: 'grid', gridTemplateColumns: '1fr 1fr', background: 'var(--cream)', borderBottom: '1px solid var(--cream-3)' }}>
        <div style={{ padding: '15px 22px' }}>
          <div style={{ fontSize: 10.5, color: 'var(--terra)', textTransform: 'uppercase', letterSpacing: '0.08em', fontWeight: 700, marginBottom: 6 }}>The problem</div>
          <div style={{ fontSize: 12.5, color: 'var(--ink-2)', lineHeight: 1.55 }}>Budget gets spread thin across channels that don't convert, and spend keeps scaling past the point where it still earns.</div>
        </div>
        <div style={{ padding: '15px 22px', borderLeft: '1px solid var(--cream-3)' }}>
          <div style={{ fontSize: 10.5, color: '#917200', textTransform: 'uppercase', letterSpacing: '0.08em', fontWeight: 700, marginBottom: 6 }}>Business impact</div>
          <div style={{ fontSize: 12.5, color: 'var(--ink-2)', lineHeight: 1.55 }}>Higher cost per lead, wasted spend, and slower growth, dollars land where they don't return.</div>
        </div>
      </div>

      {/* Recommendation: growth strategy (top) + channel pillars (underneath) */}
      <div style={{ padding: '20px 22px 22px', background: 'linear-gradient(135deg, var(--violet-soft) 0%, var(--paper) 58%)' }}>
        <div style={{ fontSize: 10.5, color: 'var(--violet)', textTransform: 'uppercase', letterSpacing: '0.08em', fontWeight: 700, marginBottom: 14 }}>Our recommendation · growth strategy</div>
        <div style={{ display: 'grid', gridTemplateColumns: 'repeat(3, 1fr)', gap: 14 }}>
          {pillars.map((p) => (
            <div key={p.head} style={{
              background: 'var(--paper)',
              border: '1px solid var(--cream-3)',
              borderRadius: 12,
              padding: '14px 16px',
              boxShadow: '0 1px 2px rgba(16,24,40,0.04)',
            }}>
              <div style={{ fontFamily: 'var(--ff-display)', fontSize: 14.5, fontWeight: 600, color: 'var(--ink)', marginBottom: 6 }}>{p.head}</div>
              <div style={{ fontSize: 12, color: 'var(--ink-3)', lineHeight: 1.55 }}>{p.body}</div>
            </div>
          ))}
        </div>
      </div>
    </div>
  );
}

// ====================================================================
// MAIN
// ====================================================================
function BenchmarksPage({ data, persona }) {
  const { benchmarks, playbook, playbookAdherence } = data;
  const [tab, setTab] = React.useState('playbook');          // playbook | compare | foundation
  const isHq = persona === 'hq';
  const isBare = data.variant === 'bare';
  const [brandVoice, setBrandVoice] = React.useState(playbook.brandVoice || '');
  const [brandVoiceSaved, setBrandVoiceSaved] = React.useState(playbook.brandVoice || '');
  const [reqOpen, setReqOpen] = React.useState(null);   // null | 'cpl' | 'mix' | 'min'
  const [reqText, setReqText] = React.useState('');
  const [peerSet, setPeerSet] = React.useState('system');    // system | top | dma | cohort
  const [foundation, setFoundation] = React.useState(playbookAdherence.foundationStatus);
  const [showPlaybook, setShowPlaybook] = React.useState(false);
  const [enrollChannel, setEnrollChannel] = React.useState(null);   // channel row or null
  const [budgetChannel, setBudgetChannel] = React.useState(null);   // channel row or null
  const [dismissedServices, setDismissedServices] = React.useState({});   // keyed by service.key
  const [serviceDetail, setServiceDetail] = React.useState(null);   // service object or null

  const stages = playbook.priorities.find(p => p.key === 'expectations').stages;
  const foundationDef = playbook.priorities.find(p => p.key === 'foundation').groups;
  const totalFoundation = foundationDef.reduce((s, g) => s + g.tasks.length, 0);
  const doneFoundation = Object.values(foundation).filter(Boolean).length;
  const foundationPct = Math.round((doneFoundation / totalFoundation) * 100);

  // Channel-layering adherence derives from channelAdherence rows that
  // have a non-zero recommended budget (i.e. the playbook expects them on)
  const layeringRows = playbookAdherence.channelAdherence.filter(c => c.recommended > 0);
  const layeringLive = layeringRows.filter(c => c.enrolled).length;
  const layeringPct = layeringRows.length ? Math.round((layeringLive / layeringRows.length) * 100) : 0;
  // Search-budget adherence, % of recommended Search spend
  const searchRow = playbookAdherence.channelAdherence.find(c => c.key === 'search') || { spend: 0, recommended: 1500 };
  const searchPct = Math.min(100, Math.round((searchRow.spend / Math.max(1, searchRow.recommended)) * 100));
  const adherenceByPillar = isBare ? {
    'Search Budget':    { val: searchPct, label: `${searchPct}% of target ($${searchRow.spend} vs $${searchRow.recommended})` },
    'Channel Layering': { val: layeringPct, label: `${layeringLive} of ${layeringRows.length} channels live` },
    'Local Foundation': { val: foundationPct, label: `${doneFoundation} of ${totalFoundation} tasks complete` },
    'Reviews Cadence':  { val: 0,   label: 'Reviews program not enrolled' },
  } : {
    'Search Budget':    { val: 100, label: 'Above target ($1,800 vs $1,500)' },
    'Channel Layering': { val: 75,  label: '3 of 4 channels live' },
    'Local Foundation': { val: foundationPct, label: `${doneFoundation} of ${totalFoundation} tasks complete` },
    'Reviews Cadence':  { val: 85,  label: 'Responding within 2.4h' },
  };

  const peerLabel = {
    system: 'All FreshNest locations',
    top: 'Top quartile (top 25%)',
    dma: 'Same DMA (Texas)',
    cohort: 'Same tenure (18-24 mo)',
  }[peerSet];

  const beats = benchmarks.filter(b => b.better === 'higher' ? b.you >= b.play : b.you <= b.play).length;

  // -------- HQ portfolio rollup (only used when isHq) --------
  const portfolio = data.playbookPortfolio || null;
  const portfolioPct = portfolio ? Math.round((portfolio.enrolledLocations / portfolio.totalLocations) * 100) : 0;
  const totalEnrolled = portfolio ? portfolio.enrolledLocations : 0;
  const portfolioFoundationComplete = portfolio
    ? Math.round((portfolio.foundationCompletion.reduce((s, t) => s + t.complete, 0) / portfolio.foundationCompletion.length))
    : 0;
  const foundationPctHq = portfolio ? Math.round((portfolioFoundationComplete / portfolio.totalLocations) * 100) : 0;
  // Locations missing 2+ Local Foundation tasks, derived from the SoT total (denominator 700).
  const missingTwoPlus = portfolio ? Math.round(portfolio.totalLocations * 0.29) : 0;

  return (
    <div className="page active">
      <div className="page-header">
        <div>
          <div className="page-title">{isHq ? "The FreshNest service standard." : 'Your playbook.'}</div>
          <div className="page-sub">{isHq
            ? 'Network-wide service standards, adoption rates, and what to improve.'
            : <>Plan progress against the <strong style={{ color: 'var(--violet)' }}>{playbook.brand} playbook {playbook.version}</strong>, plus how you compare to your goal and the system.</>}
          </div>
        </div>
        <div className="page-actions" style={{ display: 'flex', gap: 8 }}>
          <window.DropMenu value={peerSet} onPick={setPeerSet} options={[
            { v: 'system', l: 'All FreshNest locations' },
            { v: 'top', l: 'Top quartile' },
            { v: 'dma', l: 'Same DMA (Texas)' },
            { v: 'cohort', l: 'Same tenure cohort' },
          ]}/>
          <button className="btn btn-ghost btn-sm" onClick={() => setShowPlaybook(true)}>
            View playbook
          </button>
        </div>
      </div>

      {/* Strategic Summary, top of the playbook for corp and local */}
      <StrategicSummary persona={persona}/>

      {/* Headline strip, three questions. Franchisee: How am I doing / Following plan / What next.
          HQ: How is the brand doing / Are locations following / What should you do next. */}
      {!isHq && (
      <div className="card card-pad" style={{ marginBottom: 16, background: isBare
          ? 'linear-gradient(135deg, var(--terra-softer), var(--paper) 60%, var(--marigold-soft))'
          : 'linear-gradient(135deg, var(--terra-softer), var(--paper) 60%, var(--sage-soft))' }}>
        <div style={{ display: 'grid', gridTemplateColumns: '1fr 1fr 1.4fr', gap: 0 }}>
          {/* 1. How am I doing? */}
          <div style={{ paddingRight: 22 }}>
            <div style={{ fontSize: 10.5, color: 'var(--ink-3)', textTransform: 'uppercase', letterSpacing: '0.08em', fontWeight: 700, marginBottom: 8 }}>How am I doing?</div>
            <div style={{ display: 'flex', gap: 12, alignItems: 'center' }}>
              <div style={{ width: 48, height: 48, borderRadius: '50%', background: 'var(--paper)', border: '2px solid var(--cream-3)', overflow: 'hidden', flexShrink: 0 }}>
                <window.LennyLlama size={48} mood={isBare ? 'alert' : 'happy'} bg="circle"/>
              </div>
              <div>
                <div style={{ fontFamily: 'var(--ff-display)', fontSize: 17, fontWeight: 600, lineHeight: 1.25, marginBottom: 2 }}>
                  {isBare ? (
                    <>You're behind the playbook on <strong style={{ color: 'var(--terra)' }}>{benchmarks.length - beats} of {benchmarks.length}</strong> metrics.</>
                  ) : (
                    <>You're outperforming the playbook on <strong style={{ color: 'var(--sage)' }}>{beats} of {benchmarks.length}</strong> metrics.</>
                  )}
                </div>
                <div style={{ fontSize: 11.5, color: 'var(--ink-4)', fontFamily: 'var(--ff-mono)' }}>Rank #{playbookAdherence.rank.position.toLocaleString()} of {playbookAdherence.rank.total.toLocaleString()} FreshNest locations</div>
              </div>
            </div>
          </div>

          {/* 2. Am I following the plan? */}
          <div style={{ borderLeft: '1px solid var(--cream-3)', paddingLeft: 22, paddingRight: 22 }}>
            <div style={{ fontSize: 10.5, color: 'var(--ink-3)', textTransform: 'uppercase', letterSpacing: '0.08em', fontWeight: 700, marginBottom: 8 }}>Am I following the plan?</div>
            <div style={{ display: 'flex', alignItems: 'baseline', gap: 6, marginBottom: 4 }}>
              <div style={{ fontFamily: 'var(--ff-display)', fontSize: 32, fontWeight: 500, letterSpacing: '-0.02em', lineHeight: 1, color: isBare ? 'var(--terra)' : 'var(--ink)' }}>{playbookAdherence.overallScore}</div>
              <div style={{ fontSize: 14, color: 'var(--ink-4)' }}>/100 Playbook Score</div>
            </div>
            <div style={{ fontSize: 12.5, color: 'var(--ink-2)' }}>
              Stage: <strong style={{ color: 'var(--ink)' }}>{playbookAdherence.stage.charAt(0).toUpperCase() + playbookAdherence.stage.slice(1)}</strong> · Month <strong style={{ color: 'var(--ink)' }}>{playbookAdherence.monthsLive}</strong>
            </div>
            <div style={{ fontSize: 11, color: isBare ? 'var(--terra)' : 'var(--sage)', fontWeight: 600, marginTop: 4 }}>
              {isBare
                ? `↓ Bottom ${100 - playbookAdherence.rank.percentile}% of FreshNest`
                : `↑ Top ${100 - playbookAdherence.rank.percentile}% of FreshNest`}
            </div>
          </div>

          {/* 3. What should I do next? */}
          <div style={{ borderLeft: '1px solid var(--cream-3)', paddingLeft: 22 }}>
            <div style={{ fontSize: 10.5, color: 'var(--violet)', textTransform: 'uppercase', letterSpacing: '0.08em', fontWeight: 700, marginBottom: 8 }}>What should I do next?</div>
            {isBare ? (
              <>
                <div style={{ fontFamily: 'var(--ff-display)', fontSize: 16, fontWeight: 500, lineHeight: 1.3, color: 'var(--ink)', marginBottom: 10 }}>
                  Get <strong style={{ color: 'var(--violet)' }}>Google Search</strong> to the playbook floor first. You're at <strong style={{ color: 'var(--terra)' }}>$300/mo</strong>; playbook recommends <strong style={{ color: 'var(--ink)' }}>$1,500/mo</strong>, below that, ads show too rarely to learn.
                </div>
                <button className="btn btn-primary btn-sm" onClick={() => setBudgetChannel(searchRow)}>
                  Raise Search to $1,500 →
                </button>
              </>
            ) : (
              <>
                <div style={{ fontFamily: 'var(--ff-display)', fontSize: 16, fontWeight: 500, lineHeight: 1.3, color: 'var(--ink)', marginBottom: 10 }}>
                  Enroll in <strong style={{ color: 'var(--violet)' }}>Demand Gen</strong>, it's the biggest off-playbook gap. Playbook recommends <strong style={{ color: 'var(--ink)' }}>$750/mo</strong>; you're at $0.
                </div>
                <button className="btn btn-primary btn-sm" onClick={() => setEnrollChannel({ key: 'demandgen', name: 'Demand Gen', enrolled: false, spend: 0, recommended: 750, status: 'off-playbook' })}>
                  Enroll Demand Gen →
                </button>
              </>
            )}
          </div>
        </div>
      </div>
      )}

      {/* HQ summary, three questions, brand version */}
      {isHq && portfolio && (() => {
        const affecting = (portfolio.newServices || []).filter(s => !dismissedServices[s.key] && s.affectingResults);
        return (
          <>
          <div className="card card-pad" style={{ marginBottom: 16, background: 'linear-gradient(135deg, var(--terra-softer), var(--paper) 60%, var(--sage-soft))' }}>
          <div style={{ display: 'grid', gridTemplateColumns: '1fr 1fr 1.4fr', gap: 0 }}>
            {/* 1. How is the brand doing? */}
            <div style={{ paddingRight: 22 }}>
              <div style={{ fontSize: 10.5, color: 'var(--ink-3)', textTransform: 'uppercase', letterSpacing: '0.08em', fontWeight: 700, marginBottom: 8 }}>How is the brand doing?</div>
              <div style={{ display: 'flex', alignItems: 'baseline', gap: 6, marginBottom: 6 }}>
                <div style={{ fontFamily: 'var(--ff-display)', fontSize: 26, fontWeight: 500, letterSpacing: '-0.018em', lineHeight: 1, color: 'var(--ink)' }}>{portfolio.enrolledLocations.toLocaleString()}</div>
                <div style={{ fontSize: 12.5, color: 'var(--ink-4)' }}>of {portfolio.totalLocations.toLocaleString()} on the playbook</div>
              </div>
              <div style={{ fontSize: 11.5, color: 'var(--sage)', fontWeight: 600, marginBottom: 10 }}>↑ {portfolioPct}% adoption · +{portfolio.adoptionTrend[5] - portfolio.adoptionTrend[0]}pts last 6 mo</div>
              {/* 6-month adoption sparkbar */}
              <div style={{ display: 'flex', alignItems: 'flex-end', gap: 3, height: 36 }}>
                {portfolio.adoptionTrend.map((v, i) => {
                  // Scale: map 70–100% range to 6–36px so bars never overflow the 36px track
                  const h = Math.max(6, Math.min(36, ((v - 70) / 30) * 36));
                  return (
                    <div key={i} style={{ flex: 1, height: h + 'px', background: i === 5 ? 'var(--sage)' : 'var(--sage-soft)', borderRadius: 2 }} title={`${v}% adoption`}/>
                  );
                })}
              </div>
              <div style={{ display: 'flex', justifyContent: 'space-between', fontSize: 9.5, color: 'var(--ink-4)', marginTop: 4, fontFamily: 'var(--ff-mono)' }}>
                <span>Nov</span><span>Apr</span>
              </div>
            </div>

            {/* 2. Are locations following the plan? */}
            <div style={{ borderLeft: '1px solid var(--cream-3)', paddingLeft: 22, paddingRight: 22 }}>
              <div style={{ fontSize: 10.5, color: 'var(--ink-3)', textTransform: 'uppercase', letterSpacing: '0.08em', fontWeight: 700, marginBottom: 8 }}>Are locations following the plan?</div>
              <div style={{ display: 'flex', alignItems: 'baseline', gap: 6, marginBottom: 8 }}>
                <div style={{ fontFamily: 'var(--ff-display)', fontSize: 32, fontWeight: 500, letterSpacing: '-0.02em', lineHeight: 1 }}>76</div>
                <div style={{ fontSize: 14, color: 'var(--ink-4)' }}>/100 avg Playbook Score</div>
              </div>
              {/* Stage distribution mini-bars */}
              <div style={{ display: 'flex', flexDirection: 'column', gap: 4, fontSize: 11 }}>
                {[
                  { l: 'Foundation',  v: portfolio.stageDistribution.foundation, c: 'var(--marigold)' },
                  { l: 'Scaling',     v: portfolio.stageDistribution.scaling,    c: 'var(--sky)' },
                  { l: 'Optimizing',  v: portfolio.stageDistribution.optimizing, c: 'var(--sage)' },
                  { l: 'At-risk',     v: portfolio.stageDistribution.atRisk,     c: 'var(--terra)' },
                ].map((s, i) => (
                  <div key={i} style={{ display: 'flex', alignItems: 'center', gap: 8 }}>
                    <span style={{ width: 8, height: 8, borderRadius: '50%', background: s.c, flexShrink: 0 }}/>
                    <span style={{ color: 'var(--ink-2)', flex: 1 }}>{s.l}</span>
                    <span style={{ fontFamily: 'var(--ff-mono)', fontSize: 11, color: 'var(--ink-3)', fontVariantNumeric: 'tabular-nums' }}>{s.v.toLocaleString()}</span>
                  </div>
                ))}
              </div>
            </div>

            {/* 3. What should you do next? */}
            <div style={{ borderLeft: '1px solid var(--cream-3)', paddingLeft: 22 }}>
              <div style={{ fontSize: 10.5, color: 'var(--violet)', textTransform: 'uppercase', letterSpacing: '0.08em', fontWeight: 700, marginBottom: 8 }}>What should you do next?</div>
              <div style={{ fontFamily: 'var(--ff-display)', fontSize: 16, fontWeight: 500, lineHeight: 1.3, color: 'var(--ink)', marginBottom: 10 }}>
                <strong style={{ color: 'var(--terra)' }}>{portfolio.atRiskCount} at-risk locations</strong> are ≥30 days behind on Foundation tasks. Schedule a strategist sweep before they slip further.
              </div>
              <div style={{ display: 'flex', gap: 8, flexWrap: 'wrap' }}>
                <button className="btn btn-primary btn-sm"
                        onClick={() => goPlaybookSettings('Optimization Rules · at-risk recovery')}>
                  Review in playbook →
                </button>
                <button className="btn btn-ghost btn-sm"
                        onClick={() => T('Sweep scheduled', `Strategist will reach out to all ${portfolio.atRiskCount} owners this week.`, 'ok')}>
                  Schedule sweep
                </button>
              </div>
            </div>
          </div>
        </div>
        {affecting.map(svc => (
          <AffectingServiceTile key={svc.key} svc={svc}
            onDetail={() => setServiceDetail(svc)}
            onAdd={() => goPlaybookSettings('Service Strategy · add ' + svc.name)}/>
        ))}
        </>
        );
      })()}
      {isHq && (
        <div className="card card-pad" style={{ marginBottom: 18, display: 'flex', alignItems: 'center', gap: 16, flexWrap: 'wrap', background: 'linear-gradient(120deg, var(--violet-soft) 0%, transparent 62%)', border: '1px solid var(--violet-soft)' }}>
          <span style={{ width: 40, height: 40, borderRadius: 10, background: 'var(--paper)', border: '1px solid var(--violet-soft)', display: 'flex', alignItems: 'center', justifyContent: 'center', color: 'var(--violet)', flexShrink: 0 }}>{PB.doc}</span>
          <div style={{ flex: 1, minWidth: 260 }}>
            <div style={{ fontFamily: 'var(--ff-display)', fontSize: 16, fontWeight: 600, color: 'var(--ink)' }}>This is the performance view of the playbook.</div>
            <div style={{ fontSize: 12.5, color: 'var(--ink-2)', lineHeight: 1.5, marginTop: 2 }}>Service strategy, budget rules, optimization tiers, KPI goals, brand voice and approvals are configured in <strong>Settings → Network Playbook</strong>. Recommendations here route there.</div>
          </div>
          <button className="btn btn-primary btn-sm" style={{ background: 'var(--violet)', borderColor: 'var(--violet)' }} onClick={() => goPlaybookSettings()}>Open playbook settings →</button>
        </div>
      )}

      {/* Tabs */}
      <div className="tabs" style={{ marginBottom: 18 }}>
        {[
          ['playbook', 'Plan Progress'],
          ['compare', 'Compare Performance'],
          ['foundation', 'Local Setup'],
        ].map(([k, l]) => (
          <button key={k} className={'tab ' + (tab === k ? 'active' : '')} onClick={() => setTab(k)}>{l}</button>
        ))}
      </div>

      {/* ============= TAB: COMPARE ============= */}
      {tab === 'compare' && !isHq && (
        <>
          {/* Legend */}
          <div style={{ display: 'flex', gap: 8, flexWrap: 'wrap', marginBottom: 14 }}>
            <LegendChip swatch={<span style={{ width: 14, height: 14, borderRadius: '50%', background: 'var(--sage)', border: '3px solid var(--paper)', boxShadow: '0 0 0 1px var(--cream-3)' }}/>} label="You" sub="this location"/>
            <LegendChip swatch={<span style={{ width: 2, height: 14, background: 'var(--marigold)' }}/>} label="Goal" sub="your target"/>
            <LegendChip swatch={<span style={{ width: 0, height: 0, borderLeft: '5px solid transparent', borderRight: '5px solid transparent', borderTop: '6px solid var(--violet)' }}/>} label="Playbook" sub={`${playbook.brand} ${playbook.version}`}/>
            <LegendChip swatch={<span style={{ width: 2, height: 14, background: 'var(--ink-5)' }}/>} label="System median" sub={peerLabel}/>
          </div>

          <div className="card" style={{ overflow: 'hidden' }}>
            <table className="tbl">
              <thead>
                <tr>
                  <th>Metric</th>
                  <th style={{ width: 90 }}>You</th>
                  <th style={{ width: 90 }}>Goal</th>
                  <th style={{ width: 110 }}>Playbook</th>
                  <th style={{ width: 110 }}>System</th>
                  <th style={{ width: 320 }}>Position</th>
                  <th style={{ width: 130 }}>Status</th>
                </tr>
              </thead>
              <tbody>
                {benchmarks.map((b, i) => {
                  const fmt = (v) => {
                    if (v == null) return '–';
                    if (b.unit === '$') return '$' + v;
                    if (b.unit === '%') return v + '%';
                    if (b.unit === '★') return v.toFixed(1) + '★';
                    if (b.unit === 'h') return v + 'h';
                    return v;
                  };
                  const beatsPlay = b.better === 'higher' ? b.you >= b.play : b.you <= b.play;
                  const beatsGoal = b.better === 'higher' ? b.you >= b.goal : b.you <= b.goal;
                  const beatsPeer = b.better === 'higher' ? b.you >= b.peer : b.you <= b.peer;
                  const status = beatsGoal ? { l: 'Goal beat', cls: 'badge-ok' } : beatsPlay ? { l: 'On playbook', cls: 'badge-info' } : beatsPeer ? { l: 'Above system', cls: 'badge-warn' } : { l: 'Below system', cls: 'badge-bad' };
                  return (
                    <tr key={i}>
                      <td className="strong">{b.metric}</td>
                      <td><span style={{ fontFamily: 'var(--ff-display)', fontSize: 17, fontWeight: 500, color: beatsPlay ? 'var(--sage)' : 'var(--terra)' }}>{fmt(b.you)}</span></td>
                      <td className="muted" style={{ fontFamily: 'var(--ff-mono)', fontSize: 12.5 }}>{fmt(b.goal)}</td>
                      <td style={{ fontFamily: 'var(--ff-mono)', fontSize: 12.5, color: 'var(--violet)' }}>{fmt(b.play)}</td>
                      <td className="muted" style={{ fontFamily: 'var(--ff-mono)', fontSize: 12.5 }}>{fmt(b.peer)}</td>
                      <td><CompareRail row={b}/></td>
                      <td><span className={'badge ' + status.cls} style={{ fontSize: 10.5 }}>{status.l}</span></td>
                    </tr>
                  );
                })}
              </tbody>
            </table>
          </div>

          <div style={{ display: 'grid', gridTemplateColumns: '1fr 1fr', gap: 14, marginTop: 18 }}>
            <div className="card card-pad">
              <div style={{ display: 'flex', alignItems: 'center', gap: 8, marginBottom: 10 }}>
                <span style={{ color: 'var(--sage)' }}>{PB.trend}</span>
                <div style={{ fontFamily: 'var(--ff-display)', fontSize: 15, fontWeight: 600 }}>Where you're winning</div>
              </div>
              <ul style={{ margin: 0, paddingLeft: 18, fontSize: 12.5, color: 'var(--ink-2)', lineHeight: 1.7 }}>
                <li><strong>Review response time</strong>, 2.4h, 70% faster than playbook target.</li>
                <li><strong>Lead → Booked conversion</strong>, 41% vs 35% playbook target.</li>
                <li><strong>NAP accuracy</strong>, 98%, near top quartile.</li>
              </ul>
            </div>
            <div className="card card-pad" style={{ background: 'var(--marigold-soft)', borderColor: 'var(--marigold)' }}>
              <div style={{ display: 'flex', alignItems: 'center', gap: 8, marginBottom: 10 }}>
                <span style={{ color: '#917200' }}>{PB.warn}</span>
                <div style={{ fontFamily: 'var(--ff-display)', fontSize: 15, fontWeight: 600 }}>Gaps to close</div>
              </div>
              <ul style={{ margin: 0, paddingLeft: 18, fontSize: 12.5, color: 'var(--ink-2)', lineHeight: 1.7 }}>
                <li><strong>Impression Share 74%</strong>, playbook says 75%+. You're losing ~3 leads/wk to budget. <button className="btn btn-quiet btn-xs" style={{ padding: 0 }} onClick={() => T('Budget', 'Opening Search budget…', 'info')}>Increase →</button></li>
                <li><strong>AI Visibility 72</strong>, your goal is 80. Lenny can pitch a content sprint. <button className="btn btn-quiet btn-xs" style={{ padding: 0 }} onClick={window.openLenny}>Ask Lenny →</button></li>
              </ul>
            </div>
          </div>
        </>
      )}

      {/* ============= TAB: COMPARE, HQ ============= */}
      {tab === 'compare' && isHq && (
        <>
          {/* Legend */}
          <div style={{ display: 'flex', gap: 8, flexWrap: 'wrap', marginBottom: 14 }}>
            <LegendChip swatch={<span style={{ width: 12, height: 12, background: 'var(--sage)', transform: 'rotate(45deg)', display: 'inline-block' }}/>} label="Brand average" sub="across 700 locations"/>
            <LegendChip swatch={<span style={{ width: 8, height: 8, borderRadius: '50%', background: 'var(--sage-soft)', border: '1.5px solid var(--sage)' }}/>} label="Top performer" sub="brand best"/>
            <LegendChip swatch={<span style={{ width: 8, height: 8, borderRadius: '50%', background: 'var(--terra-softer)', border: '1.5px solid var(--terra)' }}/>} label="Bottom performer" sub="brand worst"/>
            <LegendChip swatch={<span style={{ width: 0, height: 0, borderLeft: '5px solid transparent', borderRight: '5px solid transparent', borderTop: '6px solid var(--violet)' }}/>} label="Playbook" sub={`${playbook.brand} ${playbook.version}`}/>
            <LegendChip swatch={<span style={{ width: 2, height: 14, background: 'var(--ink-5)' }}/>} label="System median" sub="all Location3 brands"/>
          </div>

          <div className="card" style={{ overflow: 'hidden' }}>
            <table className="tbl">
              <thead>
                <tr>
                  <th>Metric</th>
                  <th style={{ width: 100 }}>Brand avg</th>
                  <th style={{ width: 100 }}>Brand best</th>
                  <th style={{ width: 100 }}>Brand worst</th>
                  <th style={{ width: 100 }}>System</th>
                  <th style={{ width: 100 }}>Playbook</th>
                  <th style={{ width: 240 }}>Position</th>
                </tr>
              </thead>
              <tbody>
                {benchmarks.map((b, i) => {
                  const fmt = (v) => {
                    if (v == null) return '–';
                    if (b.unit === '$') return '$' + v;
                    if (b.unit === '%') return v + '%';
                    if (b.unit === '★') return v.toFixed(1) + '★';
                    if (b.unit === 'h') return v + 'h';
                    return v;
                  };
                  // Synthesize brand-portfolio shape from existing per-location data:
                  // brandAvg ≈ peer (system here is 'all FreshNest' from this location's POV),
                  // best/worst ≈ ±18% spread that respects the 'better' direction.
                  const base = b.peer != null ? b.peer : b.you;
                  const spread = base * 0.18;
                  const best  = b.better === 'higher' ? +(base + spread).toFixed(b.unit === '★' ? 1 : 0) : +(base - spread).toFixed(b.unit === '★' ? 1 : 0);
                  const worst = b.better === 'higher' ? +(base - spread).toFixed(b.unit === '★' ? 1 : 0) : +(base + spread).toFixed(b.unit === '★' ? 1 : 0);
                  const brandAvg = base;
                  const beatsPlay = b.better === 'higher' ? brandAvg >= b.play : brandAvg <= b.play;
                  // mini diamond rail
                  const allVals = [brandAvg, b.play, b.peer, best, worst].filter(v => typeof v === 'number');
                  const min = Math.min(...allVals), max = Math.max(...allVals);
                  const range = max - min || 1;
                  const pos = (v) => ((v - min) / range) * 100;
                  return (
                    <tr key={i}>
                      <td className="strong">{b.metric}</td>
                      <td><span style={{ fontFamily: 'var(--ff-display)', fontSize: 17, fontWeight: 500, color: beatsPlay ? 'var(--sage)' : 'var(--terra)' }}>{fmt(brandAvg)}</span></td>
                      <td style={{ fontFamily: 'var(--ff-mono)', fontSize: 12.5, color: 'var(--sage)' }}>{fmt(best)}</td>
                      <td style={{ fontFamily: 'var(--ff-mono)', fontSize: 12.5, color: 'var(--terra)' }}>{fmt(worst)}</td>
                      <td className="muted" style={{ fontFamily: 'var(--ff-mono)', fontSize: 12.5 }}>{fmt(b.peer)}</td>
                      <td style={{ fontFamily: 'var(--ff-mono)', fontSize: 12.5, color: 'var(--violet)' }}>{fmt(b.play)}</td>
                      <td>
                        <div style={{ position: 'relative', height: 22, background: 'var(--cream-2)', borderRadius: 11 }}>
                          {/* worst dot */}
                          <div title={`Worst: ${fmt(worst)}`} style={{ position: 'absolute', left: pos(worst) + '%', top: 7, width: 8, height: 8, borderRadius: '50%', background: 'var(--terra-softer)', border: '1.5px solid var(--terra)', transform: 'translateX(-50%)' }}/>
                          {/* best dot */}
                          <div title={`Best: ${fmt(best)}`} style={{ position: 'absolute', left: pos(best) + '%', top: 7, width: 8, height: 8, borderRadius: '50%', background: 'var(--sage-soft)', border: '1.5px solid var(--sage)', transform: 'translateX(-50%)' }}/>
                          {/* system tick */}
                          <div title={`System: ${fmt(b.peer)}`} style={{ position: 'absolute', left: pos(b.peer) + '%', top: 5, width: 2, height: 12, background: 'var(--ink-5)', transform: 'translateX(-1px)' }}/>
                          {/* playbook arrow */}
                          <div title={`Playbook: ${fmt(b.play)}`} style={{ position: 'absolute', left: pos(b.play) + '%', top: 3, width: 0, height: 0, borderLeft: '5px solid transparent', borderRight: '5px solid transparent', borderBottom: '8px solid var(--violet)', transform: 'translateX(-5px)' }}/>
                          {/* brand avg diamond */}
                          <div title={`Brand avg: ${fmt(brandAvg)}`} style={{ position: 'absolute', left: pos(brandAvg) + '%', top: 6, width: 10, height: 10, background: 'var(--sage)', transform: 'translateX(-50%) rotate(45deg)', boxShadow: '0 0 0 2px var(--paper)' }}/>
                        </div>
                      </td>
                    </tr>
                  );
                })}
              </tbody>
            </table>
          </div>

          <div style={{ display: 'grid', gridTemplateColumns: '1fr 1fr', gap: 14, marginTop: 18 }}>
            <div className="card card-pad">
              <div style={{ display: 'flex', alignItems: 'center', gap: 8, marginBottom: 10 }}>
                <span style={{ color: 'var(--sage)' }}>{PB.trend}</span>
                <div style={{ fontFamily: 'var(--ff-display)', fontSize: 15, fontWeight: 600 }}>Where the brand is winning</div>
              </div>
              <ul style={{ margin: 0, paddingLeft: 18, fontSize: 12.5, color: 'var(--ink-2)', lineHeight: 1.7 }}>
                <li><strong>Review response time</strong>, brand averages 3.1h vs 8h playbook target. Top performer at 1.2h.</li>
                <li><strong>Lead → Booked</strong>, 38% brand avg, 6 pts above system median.</li>
                <li><strong>NAP accuracy</strong>, 95% of locations clear the 95% threshold.</li>
              </ul>
            </div>
            <div className="card card-pad" style={{ background: 'var(--marigold-soft)', borderColor: 'var(--marigold)' }}>
              <div style={{ display: 'flex', alignItems: 'center', gap: 8, marginBottom: 10 }}>
                <span style={{ color: '#917200' }}>{PB.warn}</span>
                <div style={{ fontFamily: 'var(--ff-display)', fontSize: 15, fontWeight: 600 }}>Brand-wide gaps</div>
              </div>
              <ul style={{ margin: 0, paddingLeft: 18, fontSize: 12.5, color: 'var(--ink-2)', lineHeight: 1.7 }}>
                <li><strong>Demand Gen adoption 26%</strong>, playbook recommends 80%+. Push enrollment to scaling locations. <button className="btn btn-quiet btn-xs" style={{ padding: 0 }} onClick={() => T('Push queued', 'Demand Gen recommendation will be sent to 892 locations.', 'info')}>Push →</button></li>
                <li><strong>Bottom-decile CPL</strong> sits 2.3× above brand average. Strategist sweep on 120 locations. <button className="btn btn-quiet btn-xs" style={{ padding: 0 }} onClick={() => T('Sweep scheduled', 'Strategy Director will reach out to bottom-decile owners.', 'ok')}>Schedule →</button></li>
              </ul>
            </div>
          </div>
        </>
      )}

      {/* ============= TAB: PLAN PROGRESS ============= */}
      {tab === 'playbook' && !isHq && (
        <>
          {/* Stage gauge */}
          <div className="section-label" style={{ marginTop: 0 }}>Where you are in the playbook</div>
          <StageGauge stages={stages} currentKey={playbookAdherence.stage} monthsLive={playbookAdherence.monthsLive}/>

          <SourceNote>Calculated by LOCALACT</SourceNote>

          {/* Plan progress pillars */}
          <div className="section-label">Plan progress by pillar</div>
          <div style={{ display: 'grid', gridTemplateColumns: 'repeat(4, 1fr)', gap: 12 }}>
            {Object.entries(adherenceByPillar).map(([k, v]) => (
              <div key={k} className="card card-pad">
                <div style={{ fontSize: 11, color: 'var(--ink-3)', fontWeight: 600, marginBottom: 6 }}>{k}</div>
                <div style={{ display: 'flex', alignItems: 'baseline', gap: 4, marginBottom: 8 }}>
                  <div style={{ fontFamily: 'var(--ff-display)', fontSize: 26, fontWeight: 500, color: v.val >= 80 ? 'var(--sage)' : v.val >= 50 ? '#917200' : 'var(--terra)' }}>{v.val}</div>
                  <div style={{ fontSize: 12, color: 'var(--ink-4)' }}>%</div>
                </div>
                <div style={{ height: 5, background: 'var(--cream-2)', borderRadius: 3, overflow: 'hidden', marginBottom: 8 }}>
                  <div style={{ width: v.val + '%', height: '100%', background: v.val >= 80 ? 'var(--sage)' : v.val >= 50 ? 'var(--marigold)' : 'var(--terra)' }}/>
                </div>
                <div style={{ fontSize: 11, color: 'var(--ink-3)', lineHeight: 1.4 }}>{v.label}</div>
              </div>
            ))}
          </div>

          {/* Two-column: Growth Framework + Channel adherence */}
          <div style={{ display: 'grid', gridTemplateColumns: '1.1fr 1fr', gap: 18, marginTop: 24 }}>
            <div className="card card-pad">
              <div style={{ display: 'flex', alignItems: 'center', gap: 8, marginBottom: 4 }}>
                <span style={{ color: 'var(--violet)' }}>{PB.stack}</span>
                <div style={{ fontFamily: 'var(--ff-display)', fontSize: 16, fontWeight: 600 }}>Growth Framework</div>
                {(() => {
                  const c = playbookAdherence.growthFrameworkStatus.filter(s => s.status === 'complete').length;
                  const ip = playbookAdherence.growthFrameworkStatus.filter(s => s.status === 'in-progress').length;
                  return <div style={{ marginLeft: 'auto', fontSize: 11, color: 'var(--ink-3)' }}>{c} of 5 complete · {ip} in progress</div>;
                })()}
              </div>
              <div style={{ fontSize: 12.5, color: 'var(--ink-3)', marginBottom: 14 }}>The 5-step sequence every FreshNest location works through.</div>
              <GrowthFrameworkRail steps={playbook.growthFramework} status={playbookAdherence.growthFrameworkStatus}/>
            </div>

            <div>
              <div className="card card-pad" style={{ marginBottom: 14 }}>
                <div style={{ display: 'flex', alignItems: 'center', gap: 8, marginBottom: 4 }}>
                  <span style={{ color: 'var(--terra)' }}>{PB.layers}</span>
                  <div style={{ fontFamily: 'var(--ff-display)', fontSize: 16, fontWeight: 600 }}>Channel plan progress</div>
                </div>
                <div style={{ fontSize: 12.5, color: 'var(--ink-3)', marginBottom: 8 }}>Are you running every play the playbook prescribes?</div>
                <div>
                  {playbookAdherence.channelAdherence.map((c, i) => (
                    <ChannelAdherenceRow key={c.key} row={c} idx={i} last={i === playbookAdherence.channelAdherence.length - 1} onEnroll={setEnrollChannel} onIncrease={setBudgetChannel}/>
                  ))}
                </div>
              </div>

              {/* Watch outs */}
              <div className="card card-pad" style={{ background: 'var(--berry-soft)', borderColor: 'var(--berry)' }}>
                <div style={{ display: 'flex', alignItems: 'center', gap: 8, marginBottom: 8 }}>
                  <span style={{ color: '#a12118' }}>{PB.warn}</span>
                  <div style={{ fontFamily: 'var(--ff-display)', fontSize: 14, fontWeight: 600 }}>Playbook watch-outs for your stage</div>
                </div>
                <ul style={{ margin: 0, paddingLeft: 18, fontSize: 12, color: 'var(--ink-2)', lineHeight: 1.6 }}>
                  {isBare ? (
                    <>
                      <li>Treating $300/mo as "running Search", below the $1,500 floor, ads show too rarely to learn what works.</li>
                      <li>Skipping the Local Foundation, paid ads can't compensate for missing GBP photos, posts, or review responses.</li>
                      <li>Layering Social or LSA before Search is funded, playbook is sequential. Get to the floor first, then add channels.</li>
                    </>
                  ) : (
                    <>
                      <li>Drawing conclusions from one slow week, you've been past Stabilization for 19 months.</li>
                      <li>Major budget changes before enough data exists, 14-day moving avg is your friend.</li>
                      <li>Comparing month-1 to month-23 locations, different stages, different rules.</li>
                    </>
                  )}
                </ul>
              </div>
            </div>
          </div>
        </>
      )}

      {/* ============= TAB: PLAN PROGRESS, HQ ============= */}
      {tab === 'playbook' && isHq && portfolio && (
        <>
          {/* ===== Mirrored framework, performance view of the decision system ===== */}
          {/* Plan progress */}
          <div className="section-label" style={{ marginTop: 0 }}>Plan progress <span style={{ fontSize: 11, color: 'var(--ink-4)', fontWeight: 500 }}>· live across {portfolio.totalLocations.toLocaleString()} locations</span></div>
          {(() => {
            const pp = portfolio.planProgress;
            const perf = [
              { l: 'On track', v: pp.healthy, c: 'var(--sage)' },
              { l: 'Recommended increase', v: pp.recommendedIncrease, c: 'var(--sky)' },
              { l: 'Struggling', v: pp.struggling, c: 'var(--marigold)' },
              { l: 'Aggressive recovery', v: pp.aggressiveRecovery, c: 'var(--terra)' },
            ];
            const ptotal = perf.reduce((s, x) => s + x.v, 0);
            return (
              <div className="card card-pad" style={{ marginBottom: 18 }}>
                <div style={{ display: 'flex', gap: 28, alignItems: 'flex-start', flexWrap: 'wrap', marginBottom: 16 }}>
                  <div style={{ minWidth: 180 }}>
                    <div style={{ fontSize: 10.5, color: 'var(--ink-3)', textTransform: 'uppercase', letterSpacing: '0.07em', fontWeight: 700, marginBottom: 6 }}>Following the plan</div>
                    <div style={{ display: 'flex', alignItems: 'baseline', gap: 8 }}>
                      <div style={{ fontFamily: 'var(--ff-display)', fontSize: 36, fontWeight: 500, letterSpacing: '-0.02em', lineHeight: 1, color: 'var(--sage)' }}>{pp.following.toLocaleString()}</div>
                      <div style={{ fontSize: 13, color: 'var(--ink-4)' }}>/ {portfolio.totalLocations.toLocaleString()}</div>
                    </div>
                    <div style={{ fontSize: 11.5, color: 'var(--sage)', fontWeight: 600, marginTop: 4 }}>{Math.round((pp.following / portfolio.totalLocations) * 100)}% adoption</div>
                  </div>
                  <div style={{ flex: 1, minWidth: 280 }}>
                    <div style={{ fontSize: 10.5, color: 'var(--ink-3)', textTransform: 'uppercase', letterSpacing: '0.07em', fontWeight: 700, marginBottom: 8 }}>Performance distribution</div>
                    <div style={{ display: 'flex', height: 30, borderRadius: 6, overflow: 'hidden', border: '1px solid var(--cream-3)' }}>
                      {perf.map(p => {
                        const pct = (p.v / ptotal) * 100;
                        return <div key={p.l} title={`${p.l}: ${p.v}`} style={{ width: pct + '%', background: p.c, display: 'flex', alignItems: 'center', justifyContent: 'center', color: '#fff', fontSize: 11, fontWeight: 700, fontFamily: 'var(--ff-mono)', minWidth: 30 }}>{pct >= 6 ? p.v : ''}</div>;
                      })}
                    </div>
                    <div style={{ display: 'flex', gap: 16, flexWrap: 'wrap', marginTop: 10 }}>
                      {perf.map(p => (
                        <div key={p.l} style={{ display: 'flex', alignItems: 'center', gap: 6, fontSize: 11.5 }}>
                          <span style={{ width: 9, height: 9, borderRadius: 2, background: p.c }} />
                          <span style={{ color: 'var(--ink-2)', fontWeight: 600 }}>{p.l}</span>
                          <span style={{ fontFamily: 'var(--ff-mono)', color: 'var(--ink-4)' }}>{p.v}</span>
                        </div>
                      ))}
                    </div>
                  </div>
                </div>
              </div>
            );
          })()}

          {/* Optimization ladder */}
          {portfolio.optimizationLadder && (
            <>
              <div className="section-label">Optimization ladder <span style={{ fontSize: 11, color: 'var(--ink-4)', fontWeight: 500 }}>· how hard we push, by performance tier</span></div>
              <div className="card card-pad" style={{ marginBottom: 18 }}>
                {(() => {
                  const max = Math.max(...portfolio.optimizationLadder.map(t => t.count));
                  return portfolio.optimizationLadder.map((t, i) => (
                    <div key={i} style={{ display: 'grid', gridTemplateColumns: '210px 1fr', gap: 16, alignItems: 'center', padding: '12px 0', borderBottom: i < portfolio.optimizationLadder.length - 1 ? '1px solid var(--cream-2)' : 'none' }}>
                      <div>
                        <div style={{ display: 'flex', alignItems: 'center', gap: 8 }}>
                          <span style={{ width: 22, height: 22, borderRadius: 6, background: t.c, color: '#fff', display: 'inline-flex', alignItems: 'center', justifyContent: 'center', fontWeight: 700, fontSize: 11, flexShrink: 0 }}>{i + 1}</span>
                          <span style={{ fontFamily: 'var(--ff-display)', fontSize: 14, fontWeight: 600, color: 'var(--ink)' }}>{t.tier}</span>
                        </div>
                        <div style={{ fontSize: 10.5, color: 'var(--ink-4)', marginTop: 3, marginLeft: 30 }}>{t.who}</div>
                      </div>
                      <div>
                        <div style={{ display: 'flex', alignItems: 'center', gap: 10, marginBottom: 4 }}>
                          <div style={{ flex: 1, height: 18, background: 'var(--cream-2)', borderRadius: 4, overflow: 'hidden' }}>
                            <div style={{ width: Math.max(4, (t.count / max) * 100) + '%', height: '100%', background: t.c, borderRadius: 4 }} />
                          </div>
                          <span style={{ fontFamily: 'var(--ff-mono)', fontSize: 13, fontWeight: 700, color: t.c, minWidth: 56, textAlign: 'right' }}>{t.count} locs</span>
                        </div>
                        <div style={{ fontSize: 11.5, color: 'var(--ink-3)', lineHeight: 1.4 }}>{t.does}</div>
                      </div>
                    </div>
                  ));
                })()}
                <div style={{ marginTop: 12, paddingTop: 12, borderTop: '1px dashed var(--cream-3)', display: 'flex', alignItems: 'center', gap: 10 }}>
                  <span style={{ fontSize: 11.5, color: 'var(--ink-3)' }}>Optimization rules are set in the playbook.</span>
                  <span style={{ flex: 1 }} />
                  <button className="btn btn-quiet btn-xs" onClick={() => goPlaybookSettings('Optimization Rules')}>Edit optimization rules →</button>
                </div>
              </div>
            </>
          )}

          {/* KPI goal attainment */}
          {portfolio.kpiGoals && (
            <>
              <div className="section-label">KPI goal attainment <span style={{ fontSize: 11, color: 'var(--ink-4)', fontWeight: 500 }}>· share of locations hitting each goal vs. target</span></div>
              <div style={{ display: 'grid', gridTemplateColumns: 'repeat(5, 1fr)', gap: 12, marginBottom: 18 }}>
                {portfolio.kpiGoals.map((k, i) => {
                  const hit = k.currentPct >= k.targetPct;
                  return (
                    <div key={i} className="card card-pad" style={{ padding: 14 }}>
                      <div style={{ fontSize: 11.5, fontWeight: 600, color: 'var(--ink)', marginBottom: 2 }}>{k.metric}</div>
                      <div style={{ fontSize: 10.5, color: 'var(--ink-4)', fontFamily: 'var(--ff-mono)', marginBottom: 10 }}>Goal {k.goal}</div>
                      <div style={{ display: 'flex', alignItems: 'baseline', gap: 4 }}>
                        <div style={{ fontFamily: 'var(--ff-display)', fontSize: 24, fontWeight: 500, color: hit ? 'var(--sage)' : 'var(--marigold)' }}>{k.currentPct}%</div>
                        <div style={{ fontSize: 10.5, color: 'var(--ink-4)' }}>of locs</div>
                      </div>
                      <div style={{ position: 'relative', height: 6, background: 'var(--cream-2)', borderRadius: 3, overflow: 'visible', margin: '8px 0 6px' }}>
                        <div style={{ width: k.currentPct + '%', height: '100%', background: hit ? 'var(--sage)' : 'var(--marigold)', borderRadius: 3 }} />
                        <div title={`Target ${k.targetPct}%`} style={{ position: 'absolute', left: k.targetPct + '%', top: -3, width: 2, height: 12, background: 'var(--ink)', transform: 'translateX(-1px)' }} />
                      </div>
                      <div style={{ fontSize: 10, color: 'var(--ink-4)', fontFamily: 'var(--ff-mono)' }}>Target {k.targetPct}% · {hit ? 'on target' : 'below'}</div>
                    </div>
                  );
                })}
              </div>
            </>
          )}

          {/* Service strategy by market */}
          {portfolio.marketStrategy && (
            <>
              <div className="section-label">Service strategy by market type <span style={{ fontSize: 11, color: 'var(--ink-4)', fontWeight: 500 }}>· emphasis adapts to reach &amp; competition</span></div>
              <div style={{ display: 'grid', gridTemplateColumns: 'repeat(3, 1fr)', gap: 12, marginBottom: 22 }}>
                {portfolio.marketStrategy.map((m, i) => (
                  <div key={i} className="card card-pad" style={{ borderTop: '3px solid ' + m.c }}>
                    <div style={{ display: 'flex', alignItems: 'baseline', justifyContent: 'space-between', marginBottom: 8 }}>
                      <div style={{ fontFamily: 'var(--ff-display)', fontSize: 17, fontWeight: 600, color: 'var(--ink)' }}>{m.type}</div>
                      <div style={{ fontFamily: 'var(--ff-mono)', fontSize: 13, fontWeight: 700, color: m.c }}>{m.count} locs</div>
                    </div>
                    <div style={{ display: 'flex', flexDirection: 'column', gap: 4, marginBottom: 10 }}>
                      <div style={{ fontSize: 11, color: 'var(--ink-3)' }}><span style={{ color: 'var(--ink-4)', fontWeight: 600 }}>Reach:</span> {m.reach}</div>
                      <div style={{ fontSize: 11, color: 'var(--ink-3)' }}><span style={{ color: 'var(--ink-4)', fontWeight: 600 }}>Competition:</span> {m.competition}</div>
                    </div>
                    <div style={{ fontSize: 11.5, color: 'var(--ink-2)', lineHeight: 1.5 }}>{m.emphasis}</div>
                  </div>
                ))}
              </div>
            </>
          )}

          <SourceNote>Calculated by LOCALACT</SourceNote>

          {/* Adoption funnel */}
          <div className="section-label" style={{ marginTop: 0 }}>Brand adoption funnel</div>
          <div className="card card-pad" style={{ marginBottom: 18 }}>
            <div style={{ display: 'grid', gridTemplateColumns: 'repeat(4, 1fr)', gap: 0, position: 'relative' }}>
              {[
                { l: 'Total locations',   v: portfolio.totalLocations,        sub: 'In the brand',          c: 'var(--ink-3)' },
                { l: 'Enrolled',          v: portfolio.enrolledLocations,     sub: `${portfolioPct}% of total`, c: 'var(--sky)' },
                { l: 'Active this month', v: portfolio.activeLocations,       sub: 'Spend > $0',            c: 'var(--marigold)' },
                { l: 'Fully on plan',     v: portfolio.fullyOnPlanLocations,  sub: 'All channels live',     c: 'var(--sage)' },
              ].map((s, i, arr) => {
                const pct = Math.round((s.v / portfolio.totalLocations) * 100);
                return (
                  <div key={i} style={{ paddingRight: i < arr.length - 1 ? 18 : 0, borderRight: i < arr.length - 1 ? '1px solid var(--cream-3)' : 'none', paddingLeft: i > 0 ? 18 : 0, position: 'relative' }}>
                    <div style={{ fontSize: 10.5, color: 'var(--ink-3)', textTransform: 'uppercase', letterSpacing: '0.06em', fontWeight: 700, marginBottom: 6 }}>{s.l}</div>
                    <div style={{ fontFamily: 'var(--ff-display)', fontSize: 30, fontWeight: 500, letterSpacing: '-0.018em', color: s.c, lineHeight: 1, marginBottom: 4 }}>{s.v.toLocaleString()}</div>
                    <div style={{ fontSize: 11, color: 'var(--ink-4)', marginBottom: 10 }}>{s.sub}</div>
                    <div style={{ height: 4, background: 'var(--cream-2)', borderRadius: 2, overflow: 'hidden' }}>
                      <div style={{ width: pct + '%', height: '100%', background: s.c }}/>
                    </div>
                    <div style={{ fontFamily: 'var(--ff-mono)', fontSize: 10, color: 'var(--ink-4)', marginTop: 4 }}>{pct}%</div>
                  </div>
                );
              })}
            </div>
          </div>

          <SourceNote>Calculated by LOCALACT</SourceNote>

          {/* Stage distribution */}
          <div className="section-label">Where locations are in the playbook</div>
          <div className="card card-pad" style={{ marginBottom: 18 }}>
            {(() => {
              const sd = portfolio.stageDistribution;
              const stages = [
                { k: 'foundation', l: 'Foundation', v: sd.foundation, c: 'var(--marigold)', d: 'First 90 days · setup + Local Foundation' },
                { k: 'scaling',    l: 'Scaling',    v: sd.scaling,    c: 'var(--sky)',      d: 'Search live · layering channels' },
                { k: 'optimizing', l: 'Optimizing', v: sd.optimizing, c: 'var(--sage)',     d: 'Full plan running · refining' },
                { k: 'atRisk',     l: 'At-risk',    v: sd.atRisk,     c: 'var(--terra)',    d: '≥30 days behind on Foundation' },
              ];
              const total = stages.reduce((s, x) => s + x.v, 0);
              return (
                <>
                  <div style={{ display: 'flex', height: 36, borderRadius: 6, overflow: 'hidden', marginBottom: 14, border: '1px solid var(--cream-3)' }}>
                    {stages.map(s => {
                      const pct = (s.v / total) * 100;
                      return (
                        <div key={s.k} style={{ width: pct + '%', background: s.c, display: 'flex', alignItems: 'center', justifyContent: 'center', color: '#fff', fontSize: 11.5, fontWeight: 600, fontFamily: 'var(--ff-mono)', minWidth: 40 }} title={`${s.l}: ${s.v} (${pct.toFixed(1)}%)`}>
                          {pct >= 5 ? `${s.v.toLocaleString()}` : ''}
                        </div>
                      );
                    })}
                  </div>
                  <div style={{ display: 'grid', gridTemplateColumns: 'repeat(4, 1fr)', gap: 12 }}>
                    {stages.map(s => (
                      <div key={s.k} style={{ display: 'flex', gap: 10, alignItems: 'flex-start' }}>
                        <span style={{ width: 10, height: 10, background: s.c, borderRadius: 2, marginTop: 4, flexShrink: 0 }}/>
                        <div>
                          <div style={{ fontSize: 12.5, fontWeight: 600, color: 'var(--ink)' }}>{s.l} <span style={{ fontFamily: 'var(--ff-mono)', fontSize: 11, color: 'var(--ink-3)', fontWeight: 500, marginLeft: 4 }}>{s.v.toLocaleString()} · {((s.v / total) * 100).toFixed(1)}%</span></div>
                          <div style={{ fontSize: 11, color: 'var(--ink-4)', lineHeight: 1.4 }}>{s.d}</div>
                        </div>
                      </div>
                    ))}
                  </div>
                </>
              );
            })()}
          </div>

          <SourceNote>Calculated by LOCALACT</SourceNote>

          {/* Channel adoption table */}
          <div className="section-label">Channel adoption</div>
          <div className="card" style={{ overflow: 'hidden', marginBottom: 14 }}>
            <table className="tbl">
              <thead>
                <tr>
                  <th>Channel</th>
                  <th style={{ width: 100, textAlign: 'right' }}>Enrolled</th>
                  <th style={{ width: 110, textAlign: 'right' }}>On target</th>
                  <th style={{ width: 110, textAlign: 'right' }}>Below target</th>
                  <th style={{ width: 110, textAlign: 'right' }}>Not enrolled</th>
                  <th style={{ width: 240 }}>Distribution</th>
                  <th style={{ width: 220 }}>Action</th>
                </tr>
              </thead>
              <tbody>
                {portfolio.channelAdoption.map((c, i) => {
                  const total = portfolio.totalLocations;
                  const onPct = (c.onTarget / total) * 100;
                  const belowPct = (c.belowTarget / total) * 100;
                  const noPct = (c.notEnrolled / total) * 100;
                  return (
                    <tr key={i}>
                      <td className="strong">
                        <div>{c.channel}</div>
                        {(() => { const cp = window.channelPlay && window.channelPlay(c.channel); return cp ? <div style={{ fontWeight: 400, fontSize: 11, color: 'var(--ink-3)', lineHeight: 1.4, marginTop: 3, maxWidth: 280 }}>{cp.outcome}</div> : null; })()}
                      </td>
                      <td style={{ textAlign: 'right', fontFamily: 'var(--ff-mono)', fontSize: 12.5 }}>{c.enrolled.toLocaleString()}</td>
                      <td style={{ textAlign: 'right', fontFamily: 'var(--ff-mono)', fontSize: 12.5, color: 'var(--sage)' }}>{c.onTarget.toLocaleString()}</td>
                      <td style={{ textAlign: 'right', fontFamily: 'var(--ff-mono)', fontSize: 12.5, color: 'var(--marigold)' }}>{c.belowTarget.toLocaleString()}</td>
                      <td style={{ textAlign: 'right', fontFamily: 'var(--ff-mono)', fontSize: 12.5, color: 'var(--terra)' }}>{c.notEnrolled.toLocaleString()}</td>
                      <td>
                        <div style={{ display: 'flex', height: 14, borderRadius: 4, overflow: 'hidden', border: '1px solid var(--cream-3)' }}>
                          <div style={{ width: onPct + '%', background: 'var(--sage)' }} title={`On target: ${c.onTarget}`}/>
                          <div style={{ width: belowPct + '%', background: 'var(--marigold)' }} title={`Below: ${c.belowTarget}`}/>
                          <div style={{ width: noPct + '%', background: 'var(--cream-3)' }} title={`Not enrolled: ${c.notEnrolled}`}/>
                        </div>
                      </td>
                      <td>
                        <button className="btn btn-quiet btn-xs"
                                onClick={() => goPlaybookSettings('Service Strategy · ' + c.channel + ' enrollment')}>
                          Push enrollment to {c.notEnrolled.toLocaleString()} →
                        </button>
                      </td>
                    </tr>
                  );
                })}
              </tbody>
            </table>
          </div>

          <SourceNote>Calculated by LOCALACT · from Google Ads, GBP &amp; FreshNest CRM</SourceNote>

          {/* Scale signals, when to invest more in each channel */}
          <div className="section-label">When to scale each channel <span style={{ fontSize: 11, color: 'var(--ink-4)', fontWeight: 500 }}>· business outcome + the signal that says invest more</span></div>
          <window.ChannelPlaybookGrid/>

          {/* Bottom callout */}
          <div className="card card-pad" style={{ background: 'var(--berry-soft)', borderColor: 'var(--berry)', display: 'flex', alignItems: 'center', gap: 14, marginTop: 18 }}>
            <span style={{ color: '#a12118', fontSize: 18 }}>{PB.warn}</span>
            <div style={{ flex: 1 }}>
              <div style={{ fontFamily: 'var(--ff-display)', fontSize: 14, fontWeight: 600, color: 'var(--ink)', marginBottom: 2 }}>{portfolio.atRiskCount} locations below the playbook minimum on 3+ channels</div>
              <div style={{ fontSize: 12, color: 'var(--ink-2)' }}>Open the at-risk list to triage, most need a single channel turned back on.</div>
            </div>
            <button className="btn btn-primary btn-sm" onClick={() => goPlaybookSettings('Optimization Rules · at-risk recovery')}>Review in playbook →</button>
          </div>
        </>
      )}

      {/* ============= TAB: FOUNDATION ============= */}
      {tab === 'foundation' && !isHq && (
        <>
          <div className="card card-pad" style={{ marginBottom: 18, display: 'flex', gap: 18, alignItems: 'center' }}>
            <div style={{ flex: 1 }}>
              <div style={{ fontFamily: 'var(--ff-display)', fontSize: 17, fontWeight: 600, marginBottom: 4 }}>Local Foundation: {doneFoundation} of {totalFoundation} tasks complete</div>
              <div style={{ fontSize: 12.5, color: 'var(--ink-3)', marginBottom: 10, maxWidth: 620 }}>Your paid ads perform best when local presence is solid. The playbook says <strong>required tasks first</strong>, then layer in recommended.</div>
              <div style={{ height: 8, background: 'var(--cream-2)', borderRadius: 4, overflow: 'hidden', maxWidth: 620 }}>
                <div style={{ width: foundationPct + '%', height: '100%', background: foundationPct >= 80 ? 'var(--sage)' : 'var(--marigold)', transition: 'width 0.4s' }}/>
              </div>
            </div>
            <div style={{ textAlign: 'right' }}>
              <div style={{ fontFamily: 'var(--ff-display)', fontSize: 32, fontWeight: 500, color: foundationPct >= 80 ? 'var(--sage)' : 'var(--marigold)' }}>{foundationPct}%</div>
              <div style={{ fontSize: 11, color: 'var(--ink-3)' }}>Playbook target: 100%</div>
            </div>
          </div>

          {foundationDef.map((g, i) => (
            <FoundationGroup key={i} group={g} status={foundation} onToggle={(id) => {
              setFoundation(prev => ({ ...prev, [id]: !prev[id] }));
              T(foundation[id] ? 'Marked incomplete' : 'Task complete', g.tasks.find(t => t.id === id).label, 'ok');
            }}/>
          ))}

          <div className="card card-pad" style={{ background: 'var(--berry-soft)', borderColor: 'var(--berry)' }}>
            <div style={{ display: 'flex', alignItems: 'center', gap: 8, marginBottom: 8 }}>
              <span style={{ color: '#a12118' }}>{PB.warn}</span>
              <div style={{ fontFamily: 'var(--ff-display)', fontSize: 14, fontWeight: 600 }}>Watch out for</div>
            </div>
            <ul style={{ margin: 0, paddingLeft: 18, fontSize: 12, color: 'var(--ink-2)', lineHeight: 1.6 }}>
              {playbook.priorities.find(p => p.key === 'foundation').watchOut.map((w, i) => <li key={i}>{w}</li>)}
            </ul>
          </div>
        </>
      )}

      {/* ============= TAB: FOUNDATION, HQ ============= */}
      {tab === 'foundation' && isHq && portfolio && (
        <>
          {/* Hero summary */}
          <div className="card card-pad" style={{ marginBottom: 18, display: 'flex', gap: 18, alignItems: 'center' }}>
            <div style={{ flex: 1 }}>
              <div style={{ fontFamily: 'var(--ff-display)', fontSize: 17, fontWeight: 600, marginBottom: 4 }}>
                {foundationPctHq}% of locations have Local Foundation complete <span style={{ fontFamily: 'var(--ff-mono)', fontSize: 13, color: 'var(--ink-3)', fontWeight: 500, marginLeft: 6 }}>({portfolioFoundationComplete.toLocaleString()} of {portfolio.totalLocations.toLocaleString()})</span>
              </div>
              <div style={{ fontSize: 12.5, color: 'var(--ink-3)', marginBottom: 10, maxWidth: 720 }}>Paid ads under-perform when local presence isn't solid. The playbook says <strong>required tasks first</strong>, then layer in recommended. Push reminders to the locations falling behind.</div>
              <div style={{ height: 8, background: 'var(--cream-2)', borderRadius: 4, overflow: 'hidden', maxWidth: 720 }}>
                <div style={{ width: foundationPctHq + '%', height: '100%', background: foundationPctHq >= 80 ? 'var(--sage)' : 'var(--marigold)', transition: 'width 0.4s' }}/>
              </div>
            </div>
            <div style={{ textAlign: 'right' }}>
              <div style={{ fontFamily: 'var(--ff-display)', fontSize: 32, fontWeight: 500, color: foundationPctHq >= 80 ? 'var(--sage)' : 'var(--marigold)' }}>{foundationPctHq}%</div>
              <div style={{ fontSize: 11, color: 'var(--ink-3)' }}>Playbook target: 100%</div>
            </div>
          </div>

          <SourceNote>Calculated by LOCALACT · from Google Ads, GBP &amp; FreshNest CRM</SourceNote>

          {/* Foundation task table */}
          <div className="section-label">Foundation tasks · brand-wide completion</div>
          <div className="card" style={{ overflow: 'hidden', marginBottom: 18 }}>
            <table className="tbl">
              <thead>
                <tr>
                  <th>Task</th>
                  <th style={{ width: 110, textAlign: 'right' }}>Complete</th>
                  <th style={{ width: 110, textAlign: 'right' }}>Missing</th>
                  <th style={{ width: 90, textAlign: 'right' }}>%</th>
                  <th style={{ width: 200 }}>Coverage</th>
                  <th style={{ width: 220 }}>Action</th>
                </tr>
              </thead>
              <tbody>
                {portfolio.foundationCompletion.map((t, i) => {
                  const pct = Math.round((t.complete / portfolio.totalLocations) * 100);
                  const tone = pct >= 90 ? 'var(--sage)' : pct >= 75 ? 'var(--marigold)' : 'var(--terra)';
                  return (
                    <tr key={i}>
                      <td className="strong">{t.task}</td>
                      <td style={{ textAlign: 'right', fontFamily: 'var(--ff-mono)', fontSize: 12.5, color: 'var(--sage)' }}>{t.complete.toLocaleString()}</td>
                      <td style={{ textAlign: 'right', fontFamily: 'var(--ff-mono)', fontSize: 12.5, color: 'var(--terra)' }}>{t.missing.toLocaleString()}</td>
                      <td style={{ textAlign: 'right', fontFamily: 'var(--ff-mono)', fontSize: 13, fontWeight: 600, color: tone }}>{pct}%</td>
                      <td>
                        <div style={{ height: 6, background: 'var(--cream-2)', borderRadius: 3, overflow: 'hidden' }}>
                          <div style={{ width: pct + '%', height: '100%', background: tone }}/>
                        </div>
                      </td>
                      <td>
                        <button className="btn btn-quiet btn-xs"
                                onClick={() => goPlaybookSettings('Content & Reviews · ' + t.task)}>
                          Push compliance reminder →
                        </button>
                      </td>
                    </tr>
                  );
                })}
              </tbody>
            </table>
          </div>

          {/* Bottom callout */}
          <div className="card card-pad" style={{ background: 'var(--berry-soft)', borderColor: 'var(--berry)', display: 'flex', alignItems: 'center', gap: 14 }}>
            <span style={{ color: '#a12118', fontSize: 18 }}>{PB.warn}</span>
            <div style={{ flex: 1 }}>
              <div style={{ fontFamily: 'var(--ff-display)', fontSize: 14, fontWeight: 600, color: 'var(--ink)', marginBottom: 2 }}>{missingTwoPlus} locations are missing 2+ foundation tasks</div>
              <div style={{ fontSize: 12, color: 'var(--ink-2)' }}>They're costing the brand an estimated <strong style={{ color: 'var(--terra)' }}>${(portfolio.atRiskRevenueImpact / 1000).toFixed(0)}K/mo</strong> in unrealized leads, paid spend on these locations runs ~22% less efficient.</div>
            </div>
            <button className="btn btn-primary btn-sm" onClick={() => T('Triage list opened', `${missingTwoPlus} locations queued · sorted by revenue impact.`, 'info')}>Open triage list →</button>
          </div>
        </>
      )}

      {/* New-in-playbook services, secondary. Below all performance content.
          The affecting-results exception is promoted higher, near the top. */}
      {isHq && portfolio && (() => {
        const subtle = (portfolio.newServices || []).filter(s => !dismissedServices[s.key] && !s.affectingResults);
        if (!subtle.length) return null;
        return (
          <div style={{ marginTop: 28 }}>
            <div style={{ display: 'flex', alignItems: 'baseline', gap: 10, marginBottom: 4 }}>
              <div className="section-label" style={{ margin: 0 }}>New in the playbook</div>
              <span style={{ fontSize: 11.5, color: 'var(--ink-4)' }}>Optional additions · review when the fundamentals are on track</span>
              <span style={{ flex: 1 }}/>
              <button className="btn btn-quiet btn-xs" onClick={() => window.T && window.T('Notification settings', 'You\'ll get an email digest when new services are released.', 'info')}>Notification settings</button>
            </div>
            <div style={{ display: 'grid', gridTemplateColumns: `repeat(${Math.min(3, subtle.length)}, 1fr)`, gap: 12, marginTop: 12 }}>
              {subtle.map(svc => (
                <SubtleServiceTile key={svc.key} svc={svc}
                  onDismiss={() => setDismissedServices(d => ({ ...d, [svc.key]: true }))}
                  onDetail={() => setServiceDetail(svc)}
                  onAdd={() => goPlaybookSettings('Service Strategy · add ' + svc.name)}/>
              ))}
            </div>
          </div>
        );
      })()}

      {/* Footer, playbook attribution */}
      <div style={{ display: 'flex', alignItems: 'center', gap: 12, padding: '20px 0 0', marginTop: 28, borderTop: '1px dashed var(--cream-3)', fontSize: 11.5, color: 'var(--ink-4)' }}>
        <span style={{ width: 8, height: 8, borderRadius: '50%', background: 'var(--violet)' }}/>
        <span>Playbook: <strong style={{ color: 'var(--ink-3)' }}>{playbook.brand} {playbook.version}</strong> · published {playbook.publishedOn} by {playbook.publishedBy} · covers {playbook.coverage}</span>
        <span style={{ marginLeft: 'auto' }}>
          <button className="btn btn-quiet btn-xs" onClick={() => T('Coaching booked', 'Strategist will reach out within 1 business day.', 'ok')}>Book a strategist call →</button>
        </span>
      </div>

      {/* ===== Playbook drawer ===== */}
      <window.Modal open={showPlaybook} onClose={() => setShowPlaybook(false)} width={780}
        title={`${playbook.brand} Playbook ${playbook.version}`}
        sub={`Published ${playbook.publishedOn} by ${playbook.publishedBy} · ${playbook.coverage}`}
        footer={<>
          <button className="btn btn-ghost btn-sm" onClick={() => setShowPlaybook(false)}>Close</button>
          <button className="btn btn-terra btn-sm" onClick={() => { setShowPlaybook(false); T('Strategist call booked', 'Walks you through the playbook 1:1.', 'ok'); }}>Book a strategist walk-through</button>
        </>}>
        <div style={{ fontSize: 13, color: 'var(--ink-2)', lineHeight: 1.55, padding: 14, background: 'var(--cream)', borderRadius: 10, marginBottom: 18 }}>
          <div style={{ fontSize: 10.5, color: 'var(--violet)', textTransform: 'uppercase', letterSpacing: '0.08em', fontWeight: 700, marginBottom: 4 }}>Purpose</div>
          {playbook.purpose}
        </div>

        <div className="section-label" style={{ marginBottom: 10 }}>The 8 pillars</div>
        <div style={{ display: 'grid', gridTemplateColumns: 'repeat(2, 1fr)', gap: 8, marginBottom: 22 }}>
          {playbook.pillars.map(p => (
            <div key={p.key} style={{ padding: '10px 12px', background: 'var(--cream)', borderRadius: 8, border: '1px solid var(--cream-2)' }}>
              <div style={{ fontWeight: 600, fontSize: 12.5 }}>{p.title}</div>
              <div style={{ fontSize: 11.5, color: 'var(--ink-3)', marginTop: 2, lineHeight: 1.5 }}>{p.desc}</div>
            </div>
          ))}
        </div>

        <div className="section-label" style={{ marginBottom: 10 }}>Priorities · in order</div>
        <div>
          {playbook.priorities.map(pr => (
            <div key={pr.key} style={{ display: 'flex', gap: 14, padding: '14px 0', borderBottom: '1px solid var(--cream-2)' }}>
              <div style={{ width: 28, height: 28, flexShrink: 0, borderRadius: '50%', background: 'var(--violet-soft)', color: 'var(--violet)', display: 'flex', alignItems: 'center', justifyContent: 'center', fontWeight: 700, fontSize: 12, fontFamily: 'var(--ff-mono)' }}>{pr.n}</div>
              <div style={{ flex: 1 }}>
                <div style={{ fontWeight: 600, fontSize: 13.5 }}>{pr.title}</div>
                <div style={{ fontSize: 12, color: 'var(--ink-3)', marginTop: 3, lineHeight: 1.55 }}>{pr.lead}</div>
              </div>
            </div>
          ))}
        </div>

        <div className="section-label" style={{ marginTop: 24, marginBottom: 10 }}>Growth framework · 5 sequenced plays</div>
        <div style={{ display: 'grid', gap: 6 }}>
          {playbook.growthFramework.map(g => (
            <div key={g.key} style={{ display: 'flex', alignItems: 'center', gap: 12, padding: '8px 12px', background: 'var(--cream)', borderRadius: 8 }}>
              <div style={{ width: 22, height: 22, borderRadius: '50%', background: 'var(--paper)', border: '1px solid var(--cream-3)', display: 'flex', alignItems: 'center', justifyContent: 'center', fontSize: 11, fontWeight: 700, color: 'var(--ink-3)', fontFamily: 'var(--ff-mono)' }}>{g.n}</div>
              <div style={{ flex: 1 }}>
                <div style={{ fontSize: 12.5, fontWeight: 600 }}>{g.title}</div>
                <div style={{ fontSize: 11.5, color: 'var(--ink-3)', marginTop: 1 }}>{g.copy}</div>
              </div>
            </div>
          ))}
        </div>
      </window.Modal>

      {/* ===== Enroll channel — single confirmation panel (rule-driven) ===== */}
      {enrollChannel && (
        <window.EnrollConfirmModal
          open={true}
          onClose={() => setEnrollChannel(null)}
          channel={{
            name: enrollChannel.name,
            recommended: enrollChannel.recommended,
            reason: `You're at the ${playbookAdherence.stage} stage${playbookAdherence.stage === 'scaling' ? ' and Search is saturated' : ''}. ${enrollChannel.name} is the next layer — it captures demand Search alone can't reach.`,
          }}
          locations={persona === 'hq' ? ['All enrolled locations'] : [(data.location && data.location.name) || 'this location']}
          owner={(data.location && data.location.operator) || 'your LOCALACT strategist'}
        />
      )}

      {/* ===== Increase budget modal ===== */}
      {budgetChannel && (
        <window.Modal open={true} onClose={() => setBudgetChannel(null)} width={520}
          title={`Increase ${budgetChannel.name} budget`}
          sub={`Currently $${budgetChannel.spend}/mo · target $${budgetChannel.recommended}/mo`}
          footer={<>
            <button className="btn btn-ghost btn-sm" onClick={() => setBudgetChannel(null)}>Not now</button>
            <button className="btn btn-terra btn-sm" onClick={() => { const n = budgetChannel.name; setBudgetChannel(null); T('Budget updated', `${n} bumped to playbook target, applies next billing cycle.`, 'ok'); }}>Bump to ${budgetChannel.recommended}/mo</button>
          </>}>
          <div style={{ padding: 14, background: 'var(--marigold-soft)', borderRadius: 10, marginBottom: 16, fontSize: 12.5, color: 'var(--ink-2)', lineHeight: 1.55 }}>
            <div style={{ fontSize: 10.5, color: '#917200', textTransform: 'uppercase', letterSpacing: '0.08em', fontWeight: 700, marginBottom: 4 }}>What you're missing</div>
            At ${budgetChannel.spend}, you're <strong>${budgetChannel.recommended - budgetChannel.spend} below</strong> the playbook target. Estimated <strong>2–3 additional bookings/wk</strong> being left on the table.
          </div>
          <div style={{ fontSize: 12, color: 'var(--ink-3)', marginBottom: 4 }}>Change applies next billing cycle. You can roll back anytime in <strong>Budget</strong>.</div>
        </window.Modal>
      )}

      {/* ===== New-service detail modal ===== */}
      {serviceDetail && (
        <window.Modal open={true} onClose={() => setServiceDetail(null)} width={560}
          title={serviceDetail.name}
          sub={`${serviceDetail.category} · published ${serviceDetail.published}`}
          footer={<>
            <button className="btn btn-ghost btn-sm" onClick={() => setServiceDetail(null)}>Close</button>
            <button className="btn btn-primary btn-sm"
                    style={{ background: serviceDetail.accent, borderColor: serviceDetail.accent }}
                    onClick={() => { const s = serviceDetail; setServiceDetail(null); goPlaybookSettings('Service Strategy · add ' + s.name); }}>
              {serviceDetail.ctaPrimary}
            </button>
          </>}>
          <div style={{ padding: 14, background: serviceDetail.accent + '14', border: '1px solid ' + serviceDetail.accent + '44', borderRadius: 10, marginBottom: 16, fontSize: 13, color: 'var(--ink-2)', lineHeight: 1.6 }}>
            {serviceDetail.summary}
          </div>
          <div style={{ display: 'grid', gridTemplateColumns: 'repeat(3, 1fr)', gap: 12, marginBottom: 16 }}>
            {[
              { l: 'Recommended spend', v: serviceDetail.recommendedSpend > 0 ? '$' + serviceDetail.recommendedSpend + '/mo' : 'Included' },
              { l: 'Unlocks at',         v: serviceDetail.unlocks },
              { l: 'In beta',            v: serviceDetail.addedToBeta + ' locations' },
            ].map((s, i) => (
              <div key={i} style={{ padding: 12, background: 'var(--cream)', borderRadius: 8 }}>
                <div style={{ fontSize: 9.5, color: 'var(--ink-4)', textTransform: 'uppercase', letterSpacing: '0.08em', fontWeight: 700, marginBottom: 4 }}>{s.l}</div>
                <div style={{ fontFamily: 'var(--ff-display)', fontSize: 16, fontWeight: 600, color: 'var(--ink)' }}>{s.v}</div>
              </div>
            ))}
          </div>
          <div style={{ fontSize: 11, color: 'var(--ink-3)', lineHeight: 1.55 }}>
            Adding to the playbook makes this service available to all enrolled locations. Franchisees will see a notification in their dashboard within 24 hours and can enroll on demand.
          </div>
        </window.Modal>
      )}
    </div>
  );
}

window.BenchmarksPage = BenchmarksPage;
})();
