// vvj-screens.jsx — Verdens Viktigste Jobb (VVJ): hoved-workspace
// Tabs: Oversikt, Ansatte, Kontrakter, Timer, NyBy, Lønn & forskudd, Ansattportal

// ── helpers ──────────────────────────────────────────────────────────────
const vvjFmtKr = (n) => (n || 0).toLocaleString('nb-NO');
const vvjFmtKrShort = (n) => {
  if (!n) return '0';
  if (n >= 1000) return `${(n / 1000).toFixed(1).replace('.', ',')}k`;
  return n.toLocaleString('nb-NO');
};
const vvjFmtDate = (iso) => {
  if (!iso) return '—';
  const d = new Date(iso);
  return d.toLocaleDateString('nb-NO', { day: 'numeric', month: 'short' });
};
const vvjFmtDateLong = (iso) => {
  if (!iso) return '—';
  const d = new Date(iso);
  return d.toLocaleDateString('nb-NO', { day: 'numeric', month: 'long', year: 'numeric' });
};
const vvjDays = (iso) => {
  const today = new Date(VVJ_TODAY);
  const d = new Date(iso);
  return Math.ceil((d - today) / 86400000);
};
const vvjUtestaende = (a) => Math.max(0, (a.accruedKr || 0) - (a.paidAdvanceKr || 0));
const vvjAccessPct = (a) => {
  // Tilgjengelig forskudd: 60% av opptjent − allerede tatt forskudd
  const cap = Math.round((a.accruedKr || 0) * (VVJ_LONNSPERIODE.forskudd_takPct / 100));
  return Math.max(0, cap - (a.paidAdvanceKr || 0));
};
const vvjStatusPill = (status) => {
  const map = {
    aktiv:      { cls: 'track',  label: 'Aktiv' },
    onboarding: { cls: 'risk',   label: 'Onboarding' },
    utkast:     { cls: 'draft',  label: 'Utkast' },
    pause:      { cls: 'risk',   label: 'I pause' },
    sluttet:    { cls: 'done',   label: 'Sluttet' },
  };
  return map[status] || { cls: 'draft', label: status };
};
const vvjOnbScore = (o) => {
  const steps = Object.values(o);
  const done = steps.filter(s => s === 'done').length;
  return { done, total: steps.length, pct: Math.round((done / steps.length) * 100) };
};

// VVJ-spesifikke ikoner
const VI = {
  kr:    <svg width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="2" strokeLinecap="round" strokeLinejoin="round"><path d="M7 4v16"/><path d="M7 12h2"/><path d="M16 4l-7 8 7 8"/></svg>,
  clock: <svg width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="2" strokeLinecap="round" strokeLinejoin="round"><circle cx="12" cy="12" r="9"/><polyline points="12 7 12 12 15.5 14"/></svg>,
  nyby:  <svg width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="2" strokeLinecap="round" strokeLinejoin="round"><path d="M3 9l9-7 9 7v11a2 2 0 0 1-2 2h-4v-7H10v7H6a2 2 0 0 1-2-2z"/><circle cx="17" cy="6" r="2.6" fill="currentColor" stroke="none"/></svg>,
  briefcase: <svg width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="2" strokeLinecap="round" strokeLinejoin="round"><rect width="20" height="14" x="2" y="7" rx="2"/><path d="M16 21V5a2 2 0 0 0-2-2h-4a2 2 0 0 0-2 2v16"/></svg>,
  signature: <svg width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="2" strokeLinecap="round" strokeLinejoin="round"><path d="M20 19H4"/><path d="M3 15c5-1 7-4 9-7s4-3 7-2"/><path d="M14 6a3 3 0 0 1 2 3v0a3 3 0 0 1-3 3"/></svg>,
  export: <svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="2" strokeLinecap="round" strokeLinejoin="round"><path d="M14 3h7v7"/><path d="M21 3l-9 9"/><path d="M21 14v5a2 2 0 0 1-2 2H5a2 2 0 0 1-2-2V5a2 2 0 0 1 2-2h5"/></svg>,
  link: <svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="2" strokeLinecap="round" strokeLinejoin="round"><path d="M10 13a5 5 0 0 0 7.54.54l3-3a5 5 0 0 0-7.07-7.07l-1.72 1.71"/><path d="M14 11a5 5 0 0 0-7.54-.54l-3 3a5 5 0 0 0 7.07 7.07l1.71-1.71"/></svg>,
  arrow: <svg width="12" height="12" viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="2.5" strokeLinecap="round" strokeLinejoin="round"><path d="M5 12h14"/><path d="m12 5 7 7-7 7"/></svg>,
  filter: <svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="2" strokeLinecap="round" strokeLinejoin="round"><polygon points="22 3 2 3 10 12.5 10 19 14 21 14 12.5 22 3"/></svg>,
  pin: <svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="2" strokeLinecap="round" strokeLinejoin="round"><path d="M12 22s-7-7-7-12a7 7 0 0 1 14 0c0 5-7 12-7 12z"/><circle cx="12" cy="10" r="2.5"/></svg>,
  smile: <svg width="16" height="16" viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="2" strokeLinecap="round" strokeLinejoin="round"><circle cx="12" cy="12" r="9"/><path d="M8 14s1.5 2 4 2 4-2 4-2"/><line x1="9" x2="9.01" y1="9" y2="9"/><line x1="15" x2="15.01" y1="9" y2="9"/></svg>,
};

// Aksentfarger for activity-feed
const VVJ_ACCENT = {
  coral:   '#f2545c',
  green:   '#08605f',
  success: '#08654f',
  warn:    '#f2b950',
  info:    '#28589f',
};

// ═══════════════════════════════════════════════════════════════════════════
// VVJ WORKSPACE — hovedkomponent
// ═══════════════════════════════════════════════════════════════════════════
function VVJWorkspaceMock({ go, deeplink }) {
  const [tab, setTab] = React.useState(deeplink || 'oversikt');
  const [selectedAnsattId, setSelectedAnsattId] = React.useState(null);

  // KPIs som vises i header
  const aktive = VVJ_ANSATTE.filter(a => a.status === 'aktiv').length;
  const onboarding = VVJ_ANSATTE.filter(a => a.status === 'onboarding' || a.status === 'utkast').length;
  const utlopendeKontrakter = VVJ_KONTRAKTER.filter(k => k.status === 'utløper').length;
  const ventendeTimer = VVJ_TIMER.filter(t => t.status === 'ventende').length;
  const ventendeForskudd = VVJ_FORSKUDD.filter(f => f.status === 'ventende').length;
  const totalAccrued = VVJ_ANSATTE.reduce((s, a) => s + (a.accruedKr || 0), 0);
  const totalAdvanced = VVJ_ANSATTE.reduce((s, a) => s + (a.paidAdvanceKr || 0), 0);

  const tabs = [
    { id: 'oversikt',    label: 'Oversikt' },
    { id: 'ansatte',     label: `Ansatte (${VVJ_ANSATTE.length})` },
    { id: 'kontrakter',  label: 'Kontrakter', badge: utlopendeKontrakter },
    { id: 'timer',       label: 'Timer', badge: ventendeTimer },
    { id: 'nyby',        label: 'NyBy-oppdrag' },
    { id: 'lonn',        label: 'Lønn & forskudd', badge: ventendeForskudd },
    { id: 'portal',      label: 'Ansattportal' },
  ];

  return (
    <div className="ok-content__inner" style={{ maxWidth: 1280 }}>
      {/* Header */}
      <div style={{ display: 'flex', alignItems: 'flex-start', justifyContent: 'space-between', marginBottom: 18, gap: 24 }}>
        <div style={{ flex: 1, minWidth: 0 }}>
          <div style={{ display: 'flex', alignItems: 'center', gap: 8, marginBottom: 8 }}>
            <Pill status="track">Aktivt prosjekt</Pill>
            <span style={{ fontSize: 11.5, color: SK.soft, fontWeight: 500 }}>Gjennomføring</span>
            <span style={{ fontSize: 11.5, color: SK.soft }}>·</span>
            <span style={{ fontSize: 11.5, color: SK.soft, fontWeight: 500 }}>Alle avdelinger</span>
            <span style={{ fontSize: 11.5, color: SK.soft }}>·</span>
            <span style={{ fontSize: 11.5, color: SK.soft, fontWeight: 500 }}>Eier: Hanne Myhre</span>
          </div>
          <h1 style={{ margin: 0, fontSize: 28, fontWeight: 600, letterSpacing: -0.02, display: 'flex', alignItems: 'baseline', gap: 12 }}>
            Verdens Viktigste Jobb
            <span style={{ fontSize: 13.5, color: SK.soft, fontWeight: 500 }}>VVJ-26</span>
          </h1>
          <div style={{ marginTop: 6, color: SK.soft, fontSize: 13, maxWidth: 720 }}>
            Helhetlig oppfølging av midlertidige ansatte — fra kontraktsgenerering og onboarding
            til timeføring, NyBy-oppdrag og daglig forskudd på opptjent lønn.
          </div>
        </div>
        <div style={{ display: 'flex', gap: 8, flexShrink: 0 }}>
          <Button size="sm" icon={I.download}>Statusrapport</Button>
          <Button variant="primary" icon={I.plus}>Ny ansatt</Button>
        </div>
      </div>

      {/* Tabs */}
      <VVJTabs tabs={tabs} value={tab} onChange={setTab} />

      {tab === 'oversikt'   && <VVJOversikt go={go} setTab={setTab} setSelectedAnsattId={setSelectedAnsattId} kpis={{ aktive, onboarding, utlopendeKontrakter, ventendeTimer, ventendeForskudd, totalAccrued, totalAdvanced }} />}
      {tab === 'ansatte'    && <VVJAnsatte go={go} setTab={setTab} selectedAnsattId={selectedAnsattId} setSelectedAnsattId={setSelectedAnsattId} />}
      {tab === 'kontrakter' && <VVJKontrakter setTab={setTab} setSelectedAnsattId={setSelectedAnsattId} />}
      {tab === 'timer'      && <VVJTimer />}
      {tab === 'nyby'       && <VVJNyBy />}
      {tab === 'lonn'       && <VVJLonn />}
      {tab === 'portal'     && <VVJPortal />}
    </div>
  );
}

// ── Custom Tabs med badges ───────────────────────────────────────────────
function VVJTabs({ tabs, value, onChange }) {
  return (
    <div className="ok-tabs" style={{ marginBottom: 20 }}>
      {tabs.map(t => (
        <button
          key={t.id}
          className={`ok-tab ${value === t.id ? 'ok-tab--active' : ''}`}
          onClick={() => onChange(t.id)}
        >
          {t.label}
          {t.badge ? (
            <span style={{
              marginLeft: 7, background: value === t.id ? SK.coral : 'rgba(17,24,61,.1)',
              color: value === t.id ? '#fff' : SK.soft,
              fontSize: 10, fontWeight: 600, padding: '1px 7px', borderRadius: 99,
            }}>{t.badge}</span>
          ) : null}
        </button>
      ))}
    </div>
  );
}

// ═══════════════════════════════════════════════════════════════════════════
// OVERSIKT
// ═══════════════════════════════════════════════════════════════════════════
function VVJOversikt({ go, setTab, setSelectedAnsattId, kpis }) {
  const aktiveAnsatte = VVJ_ANSATTE.filter(a => a.status === 'aktiv');
  const ukentligeTimer = VVJ_TIMER.filter(t => t.date >= '2026-05-18' && t.date <= '2026-05-21').reduce((s, t) => s + t.hours, 0);
  const nybyDenneUka = VVJ_NYBY_OPPDRAG.filter(o => o.status === 'fullført' || o.status === 'påtatt').length;
  const top5OutstandingAnsatte = [...VVJ_ANSATTE]
    .filter(a => a.status === 'aktiv')
    .sort((b, a) => vvjUtestaende(a) - vvjUtestaende(b))
    .slice(0, 5);

  return (
    <div>
      {/* KPI strip */}
      <div style={{ display: 'grid', gridTemplateColumns: 'repeat(5, 1fr)', gap: 14, marginBottom: 14 }}>
        <Card padded>
          <KPI label="Ansatte aktive" value={kpis.aktive}
            sub={`${kpis.onboarding} i onboarding/utkast`} />
        </Card>
        <Card padded>
          <KPI label="Timer denne uka" value={`${ukentligeTimer.toLocaleString('nb-NO')}`}
            sub={`${kpis.ventendeTimer} venter godkjenning`} accent={kpis.ventendeTimer > 6} />
        </Card>
        <Card padded>
          <KPI label="Opptjent (mai)" value={`${vvjFmtKrShort(kpis.totalAccrued)} kr`}
            sub={`${vvjFmtKrShort(kpis.totalAdvanced)} kr forskudd utbetalt`} />
        </Card>
        <Card padded>
          <KPI label="Kontrakter utløper" value={kpis.utlopendeKontrakter}
            sub="innen 30 dager" accent={kpis.utlopendeKontrakter > 0} />
        </Card>
        <Card padded>
          <KPI label="NyBy-oppdrag" value={nybyDenneUka}
            sub={`${VVJ_NYBY_OPPDRAG.filter(o=>o.status==='tilgjengelig').length} tilgjengelige nå`} />
        </Card>
      </div>

      <div style={{ display: 'grid', gridTemplateColumns: '1.5fr 1fr', gap: 14, marginBottom: 14 }}>
        {/* Aktive ansatte — utestående */}
        <Card title="Aktive ansatte — opptjent vs. utbetalt forskudd"
          padded={false}
          action={<Button size="sm" variant="ghost" onClick={() => setTab('ansatte')}>
            Alle ansatte <span style={{ marginLeft: 4 }}>{I.chevron}</span>
          </Button>}
        >
          <table className="ok-table">
            <thead>
              <tr>
                <th style={{ paddingLeft: 18 }}>Ansatt</th>
                <th style={{ textAlign: 'right' }}>Opptjent</th>
                <th style={{ textAlign: 'right' }}>Forskudd</th>
                <th style={{ width: 200 }}>Utestående</th>
              </tr>
            </thead>
            <tbody>
              {top5OutstandingAnsatte.map(a => {
                const ut = vvjUtestaende(a);
                const pct = a.accruedKr > 0 ? Math.round((a.paidAdvanceKr / a.accruedKr) * 100) : 0;
                return (
                  <TR key={a.id} onClick={() => { setSelectedAnsattId(a.id); setTab('ansatte'); }}>
                    <td style={{ paddingLeft: 18 }}>
                      <div style={{ display: 'flex', alignItems: 'center', gap: 10 }}>
                        <Avatar initials={a.initials} color={a.color} />
                        <div>
                          <div style={{ fontWeight: 600, fontSize: 12.5 }}>{a.name}</div>
                          <div style={{ fontSize: 11, color: SK.soft, marginTop: 1 }}>{a.role} · {a.avd}</div>
                        </div>
                      </div>
                    </td>
                    <td style={{ textAlign: 'right', fontWeight: 600, fontSize: 13 }}>{vvjFmtKr(a.accruedKr)} kr</td>
                    <td style={{ textAlign: 'right', color: SK.soft, fontSize: 12.5 }}>{vvjFmtKr(a.paidAdvanceKr)} kr</td>
                    <td>
                      <div style={{ display: 'flex', alignItems: 'center', gap: 8 }}>
                        <div style={{ flex: 1 }}>
                          <Progress value={pct} status={pct > 70 ? 'risk' : 'track'} />
                        </div>
                        <div style={{ fontSize: 12.5, fontWeight: 600, minWidth: 64, textAlign: 'right' }}>
                          {vvjFmtKr(ut)} kr
                        </div>
                      </div>
                    </td>
                  </TR>
                );
              })}
            </tbody>
          </table>
        </Card>

        {/* Aktivitetsfeed */}
        <Card title="Aktivitet" action={<span style={{ fontSize: 11, color: SK.soft }}>siste 48 t</span>}>
          <div style={{ display: 'flex', flexDirection: 'column' }}>
            {VVJ_ACTIVITY.slice(0, 8).map((l, i) => (
              <div key={l.id} style={{
                padding: '10px 0', borderTop: i ? '1px solid rgba(17,24,61,.06)' : 'none',
                display: 'flex', gap: 10, alignItems: 'flex-start',
              }}>
                <span style={{
                  width: 28, height: 28, borderRadius: 8, flexShrink: 0,
                  background: `${VVJ_ACCENT[l.accent]}22`, color: VVJ_ACCENT[l.accent],
                  display: 'flex', alignItems: 'center', justifyContent: 'center',
                }}>
                  {l.ikon === 'kr' ? VI.kr : l.ikon === 'nyby' ? VI.nyby : l.ikon === 'clock' ? VI.clock : l.ikon === 'doc' ? I.doc : l.ikon === 'check' ? I.check : VI.export}
                </span>
                <div style={{ flex: 1, minWidth: 0 }}>
                  <div style={{ fontSize: 12.5, lineHeight: 1.35 }}>{l.tekst}</div>
                  <div style={{ fontSize: 10.5, color: SK.soft, marginTop: 2 }}>
                    {l.tid} · {l.avsender}
                  </div>
                </div>
              </div>
            ))}
          </div>
        </Card>
      </div>

      {/* Integrasjoner */}
      <Card title="Integrasjoner" padded={false}>
        <div style={{ display: 'grid', gridTemplateColumns: 'repeat(3, 1fr)' }}>
          {[
            { name: 'NyBy', desc: 'Ekstrajobber for ansatte', status: 'tilkoblet', last: 'Sist sync: i dag 09:14', count: '6 nye oppdrag', dot: SK.success },
            { name: 'Visma Lønn', desc: 'Lønnseksport · forskuddsregistrering', status: 'tilkoblet', last: 'Sist eksport: 8. mai (april-kjøring)', count: 'Klar for mai-eksport 1/6', dot: SK.success },
            { name: 'BankID-signering', desc: 'Digital kontraktssignering', status: 'tilkoblet', last: 'Sist signert: i går 16:45', count: '2 venter på signering', dot: SK.warn },
            { name: 'Skatteetaten', desc: 'Skattekort-oppslag', status: 'tilkoblet', last: 'Sist sync: i morges 06:00', count: 'Alle aktive ansatte verifisert', dot: SK.success },
            { name: 'Altinn A-melding', desc: 'Månedlig rapportering', status: 'tilkoblet', last: 'Sist sendt: 5. mai', count: 'Neste: 5. juni', dot: SK.success },
            { name: 'OK:bistro/sykkel/data', desc: 'Vaktplan & oppdragsregister', status: 'tilkoblet', last: 'Live-kobling', count: '4 avdelinger', dot: SK.success },
          ].map((x, i) => (
            <div key={i} style={{
              padding: '16px 18px',
              borderRight: (i + 1) % 3 !== 0 ? '1px solid rgba(17,24,61,.06)' : 'none',
              borderTop: i >= 3 ? '1px solid rgba(17,24,61,.06)' : 'none',
            }}>
              <div style={{ display: 'flex', alignItems: 'center', gap: 8, marginBottom: 6 }}>
                <span style={{ width: 8, height: 8, borderRadius: '50%', background: x.dot }} />
                <span style={{ fontWeight: 600, fontSize: 13 }}>{x.name}</span>
              </div>
              <div style={{ fontSize: 11.5, color: SK.soft, marginBottom: 4 }}>{x.desc}</div>
              <div style={{ fontSize: 11.5, color: SK.ink, fontWeight: 500 }}>{x.count}</div>
              <div style={{ fontSize: 10.5, color: SK.soft, marginTop: 2 }}>{x.last}</div>
            </div>
          ))}
        </div>
      </Card>
    </div>
  );
}

// ═══════════════════════════════════════════════════════════════════════════
// ANSATTE — liste + detalj (onboarding-checklist)
// ═══════════════════════════════════════════════════════════════════════════
function VVJAnsatte({ go, setTab, selectedAnsattId, setSelectedAnsattId }) {
  const [statusFilter, setStatusFilter] = React.useState('all');
  const [avdFilter, setAvdFilter] = React.useState('all');
  const [search, setSearch] = React.useState('');

  const avds = ['all', ...new Set(VVJ_ANSATTE.map(a => a.avd))];

  const liste = VVJ_ANSATTE.filter(a => {
    if (statusFilter !== 'all' && a.status !== statusFilter) return false;
    if (avdFilter !== 'all' && a.avd !== avdFilter) return false;
    if (search && !a.name.toLowerCase().includes(search.toLowerCase()) && !a.role.toLowerCase().includes(search.toLowerCase())) return false;
    return true;
  });

  // Hvis valgt ansatt — vis detalj
  const selected = VVJ_ANSATTE.find(a => a.id === selectedAnsattId);

  if (selected) {
    return <VVJAnsattDetalj ansatt={selected} onBack={() => setSelectedAnsattId(null)} setTab={setTab} />;
  }

  return (
    <Card padded={false}>
      <div style={{ padding: '12px 16px', display: 'flex', gap: 10, alignItems: 'center', borderBottom: '1px solid rgba(17,24,61,.08)', flexWrap: 'wrap' }}>
        <input
          className="ok-input ok-input--search"
          placeholder="Søk i ansatte…"
          value={search}
          onChange={e => setSearch(e.target.value)}
          style={{ maxWidth: 240 }}
        />
        <div style={{ display: 'flex', gap: 4 }}>
          {[
            ['all', 'Alle'], ['aktiv', 'Aktive'], ['onboarding', 'Onboarding'], ['utkast', 'Utkast'], ['pause', 'I pause'], ['sluttet', 'Sluttet'],
          ].map(([k, l]) => (
            <button key={k} onClick={() => setStatusFilter(k)} className="ok-btn ok-btn--sm" style={{
              background: statusFilter === k ? SK.ink : 'transparent',
              color: statusFilter === k ? '#fff' : SK.ink,
              borderColor: statusFilter === k ? SK.ink : 'rgba(17,24,61,.15)',
            }}>{l}</button>
          ))}
        </div>
        <div style={{ width: 1, height: 24, background: 'rgba(17,24,61,.1)' }} />
        <select value={avdFilter} onChange={e => setAvdFilter(e.target.value)}
          className="ok-input" style={{ maxWidth: 220, padding: '6px 10px' }}>
          {avds.map(a => <option key={a} value={a}>{a === 'all' ? 'Alle avdelinger' : a}</option>)}
        </select>
        <div style={{ marginLeft: 'auto', display: 'flex', gap: 6 }}>
          <Button size="sm" icon={I.download}>CSV</Button>
          <Button size="sm" variant="primary" icon={I.plus}>Ny ansatt</Button>
        </div>
      </div>

      <table className="ok-table">
        <thead>
          <tr>
            <th style={{ paddingLeft: 18 }}>Ansatt</th>
            <th>Avdeling</th>
            <th>Kontrakt</th>
            <th>Onboarding</th>
            <th>Status</th>
            <th style={{ textAlign: 'right' }}>Uke 21</th>
            <th style={{ textAlign: 'right' }}>Utestående</th>
            <th></th>
          </tr>
        </thead>
        <tbody>
          {liste.map(a => {
            const onb = vvjOnbScore(a.onboarding);
            const pill = vvjStatusPill(a.status);
            const days = vvjDays(a.contractEnd);
            const utest = vvjUtestaende(a);
            return (
              <TR key={a.id} onClick={() => setSelectedAnsattId(a.id)}>
                <td style={{ paddingLeft: 18 }}>
                  <div style={{ display: 'flex', alignItems: 'center', gap: 10 }}>
                    <Avatar initials={a.initials} color={a.color} />
                    <div>
                      <div style={{ fontWeight: 600, fontSize: 13 }}>{a.name}</div>
                      <div style={{ fontSize: 11, color: SK.soft, marginTop: 1 }}>{a.role}</div>
                    </div>
                  </div>
                </td>
                <td style={{ fontSize: 12 }}>{a.avd}</td>
                <td>
                  <div style={{ fontSize: 12, fontWeight: 500 }}>{a.contractType.split('·')[0].trim()}</div>
                  <div style={{ fontSize: 10.5, color: days < 30 && days >= 0 ? SK.coral : SK.soft, marginTop: 1 }}>
                    til {vvjFmtDate(a.contractEnd)} {days >= 0 && days < 60 ? `· ${days}d igjen` : ''}
                  </div>
                </td>
                <td style={{ width: 130 }}>
                  <div style={{ display: 'flex', alignItems: 'center', gap: 8 }}>
                    <Progress value={onb.pct} status={onb.pct === 100 ? 'track' : 'risk'} style={{ flex: 1 }} />
                    <span style={{ fontSize: 11, color: SK.soft, whiteSpace: 'nowrap' }}>{onb.done}/{onb.total}</span>
                  </div>
                </td>
                <td><Pill status={pill.cls}>{pill.label}</Pill></td>
                <td style={{ textAlign: 'right', fontSize: 12.5 }}>
                  <div style={{ fontWeight: 600 }}>{a.weekHours}t</div>
                  <div style={{ fontSize: 10.5, color: SK.soft }}>av {a.weeklyHours}t</div>
                </td>
                <td style={{ textAlign: 'right', fontSize: 12.5, fontWeight: 600, color: utest > 0 ? SK.ink : SK.soft }}>
                  {utest > 0 ? `${vvjFmtKr(utest)} kr` : '—'}
                </td>
                <td style={{ paddingRight: 18, textAlign: 'right' }}>
                  <span style={{ color: SK.soft }}>{I.chevron}</span>
                </td>
              </TR>
            );
          })}
        </tbody>
      </table>
    </Card>
  );
}

// ── Ansatt-detalj (drawer-stil, ekspandert kort) ─────────────────────────
function VVJAnsattDetalj({ ansatt, onBack, setTab }) {
  const a = ansatt;
  const onb = vvjOnbScore(a.onboarding);
  const pill = vvjStatusPill(a.status);
  const days = vvjDays(a.contractEnd);
  const utest = vvjUtestaende(a);
  const tilgjengelig = vvjAccessPct(a);

  const onbSteg = [
    { key: 'kontrakt', label: 'Kontrakt opprettet og signert (BankID)' },
    { key: 'skattekort', label: 'Skattekort hentet fra Skatteetaten' },
    { key: 'bankkonto', label: 'Bankkonto registrert og verifisert' },
    { key: 'it', label: 'IT-konto opprettet (AD + M365)' },
    { key: 'hms', label: 'HMS-gjennomgang og signert egenerklæring' },
    { key: 'opplaring', label: 'Opplæringsplan gjennomført' },
    { key: 'oppfolging', label: 'Første oppfølgingsmøte med veileder' },
  ];

  const ansatteTimer = VVJ_TIMER.filter(t => t.ansattId === a.id).slice(-5);
  const ansatteForskudd = VVJ_FORSKUDD.filter(f => f.ansattId === a.id);
  const ansatteNyBy = VVJ_NYBY_OPPDRAG.filter(o => o.ansattId === a.id);

  return (
    <div>
      <div style={{ marginBottom: 14 }}>
        <button onClick={onBack} className="ok-btn ok-btn--ghost ok-btn--sm">
          <span style={{ transform: 'rotate(180deg)', display: 'inline-flex' }}>{I.chevron}</span> Tilbake til liste
        </button>
      </div>

      {/* Ansatt-header */}
      <Card padded style={{ marginBottom: 14 }}>
        <div style={{ display: 'flex', alignItems: 'center', gap: 16, padding: '4px 0' }}>
          <Avatar initials={a.initials} color={a.color} size={56} />
          <div style={{ flex: 1, minWidth: 0 }}>
            <div style={{ display: 'flex', alignItems: 'center', gap: 8, marginBottom: 4 }}>
              <Pill status={pill.cls}>{pill.label}</Pill>
              <span style={{ fontSize: 11.5, color: SK.soft }}>{a.contractType}</span>
            </div>
            <h2 style={{ margin: 0, fontSize: 22, fontWeight: 600 }}>{a.name}</h2>
            <div style={{ marginTop: 4, fontSize: 13, color: SK.soft }}>
              {a.role} · {a.avd} · Veileder: {TEAM[a.veileder]?.n || a.veileder}
            </div>
          </div>
          <div style={{ display: 'flex', gap: 8, flexShrink: 0 }}>
            <Button size="sm" icon={VI.briefcase}>Endre kontrakt</Button>
            <Button size="sm" variant="primary">Send melding</Button>
          </div>
        </div>
      </Card>

      <div style={{ display: 'grid', gridTemplateColumns: '1.4fr 1fr', gap: 14 }}>
        {/* Venstre */}
        <div style={{ display: 'flex', flexDirection: 'column', gap: 14 }}>
          {/* Onboarding checklist */}
          <Card title={`Onboarding · ${onb.done} av ${onb.total} fullført`}
            action={<span style={{ fontSize: 11, fontWeight: 600, color: onb.pct === 100 ? SK.success : SK.coral }}>{onb.pct}%</span>}
          >
            <div style={{ marginBottom: 12 }}>
              <Progress value={onb.pct} status={onb.pct === 100 ? 'track' : 'risk'} />
            </div>
            <div style={{ display: 'flex', flexDirection: 'column', gap: 0 }}>
              {onbSteg.map((s, i) => {
                const stegStatus = a.onboarding[s.key];
                return (
                  <div key={s.key} style={{
                    padding: '10px 0', borderTop: i ? '1px solid rgba(17,24,61,.06)' : 'none',
                    display: 'flex', alignItems: 'center', gap: 12,
                  }}>
                    <span style={{
                      width: 20, height: 20, borderRadius: '50%',
                      background: stegStatus === 'done' ? SK.success : stegStatus === 'in_progress' ? SK.warn : 'transparent',
                      border: stegStatus === 'open' ? `2px solid rgba(17,24,61,.18)` : 'none',
                      display: 'flex', alignItems: 'center', justifyContent: 'center',
                      color: '#fff', flexShrink: 0,
                    }}>
                      {stegStatus === 'done' ? <svg width="12" height="12" viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="3" strokeLinecap="round" strokeLinejoin="round"><polyline points="20 6 9 17 4 12"/></svg> : null}
                      {stegStatus === 'in_progress' ? <span style={{ width: 8, height: 8, background: '#fff', borderRadius: '50%' }} /> : null}
                    </span>
                    <span style={{ flex: 1, fontSize: 13, color: stegStatus === 'done' ? SK.soft : SK.ink, textDecoration: stegStatus === 'done' ? 'line-through' : 'none' }}>{s.label}</span>
                    <span style={{ fontSize: 11, color: SK.soft }}>
                      {stegStatus === 'done' ? 'Fullført' : stegStatus === 'in_progress' ? 'Pågår' : 'Åpen'}
                    </span>
                  </div>
                );
              })}
            </div>
          </Card>

          {/* Siste timer */}
          <Card title="Siste timeføringer" padded={false}
            action={<Button size="sm" variant="ghost" onClick={() => setTab('timer')}>Se alle <span style={{ marginLeft: 4 }}>{I.chevron}</span></Button>}
          >
            <table className="ok-table">
              <tbody>
                {ansatteTimer.length === 0 ? (
                  <tr><td colSpan="4" style={{ padding: '20px', textAlign: 'center', color: SK.soft }}>Ingen timer registrert ennå</td></tr>
                ) : ansatteTimer.map(t => (
                  <tr key={t.id} style={{ cursor: 'default' }}>
                    <td style={{ paddingLeft: 18, fontSize: 12.5, fontWeight: 500 }}>{vvjFmtDate(t.date)}</td>
                    <td style={{ fontSize: 12.5 }}>{t.kontext}
                      {t.kilde === 'NyBy-API' ? <span style={{ marginLeft: 6, fontSize: 10, color: SK.purple, fontWeight: 600 }}>NYBY</span> : null}
                    </td>
                    <td style={{ textAlign: 'right', fontWeight: 600, fontSize: 12.5 }}>{t.hours} t</td>
                    <td style={{ paddingRight: 18, textAlign: 'right' }}>
                      <Pill status={t.status === 'godkjent' ? 'track' : t.status === 'ventende' ? 'draft' : 'delay'}>
                        {t.status === 'godkjent' ? 'Godkjent' : t.status === 'ventende' ? 'Venter' : 'Avvist'}
                      </Pill>
                    </td>
                  </tr>
                ))}
              </tbody>
            </table>
          </Card>
        </div>

        {/* Høyre — utestående + kontrakt + NyBy */}
        <div style={{ display: 'flex', flexDirection: 'column', gap: 14 }}>
          {/* Utestående lønn */}
          <Card title="Opptjent og forskudd">
            <div style={{ padding: '6px 0' }}>
              <div style={{ display: 'flex', justifyContent: 'space-between', alignItems: 'baseline', marginBottom: 4 }}>
                <span style={{ fontSize: 11, fontWeight: 600, color: SK.soft, letterSpacing: 0.04, textTransform: 'uppercase' }}>Utestående</span>
                <span style={{ fontSize: 11, color: SK.soft }}>siden 1. mai</span>
              </div>
              <div style={{ fontSize: 32, fontWeight: 600, letterSpacing: -0.02 }}>
                {vvjFmtKr(utest)} <span style={{ fontSize: 16, color: SK.soft, fontWeight: 500 }}>kr</span>
              </div>
              <div style={{ marginTop: 12, marginBottom: 10 }}>
                <Progress value={a.accruedKr > 0 ? Math.round((a.paidAdvanceKr / a.accruedKr) * 100) : 0} status={a.paidAdvanceKr / Math.max(1, a.accruedKr) > 0.7 ? 'risk' : 'track'} />
              </div>
              <div style={{ display: 'flex', justifyContent: 'space-between', fontSize: 12 }}>
                <span style={{ color: SK.soft }}>Opptjent: <b style={{ color: SK.ink }}>{vvjFmtKr(a.accruedKr)} kr</b></span>
                <span style={{ color: SK.soft }}>Forskudd: <b style={{ color: SK.ink }}>{vvjFmtKr(a.paidAdvanceKr)} kr</b></span>
              </div>
              <div style={{ marginTop: 14, padding: 12, background: SK.iceBlueLight, borderRadius: 8, fontSize: 11.5, color: SK.soft }}>
                <b style={{ color: SK.ink }}>Tilgjengelig for forskudd nå:</b> {vvjFmtKr(tilgjengelig)} kr
                <div style={{ marginTop: 2 }}>(60% av opptjent − allerede tatt)</div>
              </div>
            </div>
          </Card>

          {/* Kontrakt */}
          <Card title="Kontrakt">
            <div style={{ display: 'flex', flexDirection: 'column', gap: 8, fontSize: 12.5 }}>
              <RowLabel l="Type">{a.contractType}</RowLabel>
              <RowLabel l="Periode">{vvjFmtDate(a.contractStart)} – {vvjFmtDate(a.contractEnd)}</RowLabel>
              <RowLabel l="Timelønn">{vvjFmtKr(a.hourRate)} kr/t</RowLabel>
              <RowLabel l="Avtalt arbeidstid">inntil {a.weeklyHours} t/uke</RowLabel>
              <RowLabel l="Utløper">
                <span style={{ color: days < 30 && days >= 0 ? SK.coral : SK.ink, fontWeight: 600 }}>
                  {days < 0 ? `${Math.abs(days)}d forsinket` : `om ${days} dgr`}
                </span>
              </RowLabel>
            </div>
            <div style={{ marginTop: 10, display: 'flex', gap: 6 }}>
              <Button size="sm" icon={I.doc}>Åpne PDF</Button>
              <Button size="sm" variant="ghost">Forleng kontrakt</Button>
            </div>
          </Card>

          {/* NyBy */}
          <Card title="NyBy-oppdrag"
            action={<span style={{ fontSize: 11, color: SK.soft }}>{ansatteNyBy.length} totalt</span>}
          >
            {ansatteNyBy.length === 0 ? (
              <div style={{ fontSize: 12, color: SK.soft, padding: '6px 0' }}>
                Ingen NyBy-oppdrag registrert ennå.
              </div>
            ) : (
              <div style={{ display: 'flex', flexDirection: 'column', gap: 0 }}>
                {ansatteNyBy.slice(0, 3).map((o, i) => (
                  <div key={o.id} style={{ padding: '8px 0', borderTop: i ? '1px solid rgba(17,24,61,.06)' : 'none', display: 'flex', gap: 10, alignItems: 'flex-start' }}>
                    <span style={{ width: 24, height: 24, borderRadius: 6, background: 'rgba(88,107,164,.15)', color: SK.purple, display: 'flex', alignItems: 'center', justifyContent: 'center', flexShrink: 0 }}>{VI.nyby}</span>
                    <div style={{ flex: 1, minWidth: 0 }}>
                      <div style={{ fontSize: 12.5, fontWeight: 500, lineHeight: 1.3 }}>{o.tittel}</div>
                      <div style={{ fontSize: 11, color: SK.soft, marginTop: 2 }}>
                        {vvjFmtDate(o.dato)} · {o.timer}t · {vvjFmtKr(o.sats)} kr/t
                      </div>
                    </div>
                    <Pill status={o.status === 'fullført' ? 'done' : o.status === 'påtatt' ? 'draft' : 'track'}>
                      {o.status === 'fullført' ? 'Fullført' : o.status === 'påtatt' ? 'Påtatt' : 'Tilgj.'}
                    </Pill>
                  </div>
                ))}
              </div>
            )}
          </Card>
        </div>
      </div>
    </div>
  );
}

// Liten label-row helper
function RowLabel({ l, children }) {
  return (
    <div style={{ display: 'flex', justifyContent: 'space-between', gap: 12 }}>
      <span style={{ color: SK.soft }}>{l}</span>
      <span style={{ fontWeight: 500, textAlign: 'right' }}>{children}</span>
    </div>
  );
}

Object.assign(window, { VVJWorkspaceMock, VVJOversikt, VVJAnsatte, VVJAnsattDetalj, vvjFmtKr, vvjFmtKrShort, vvjFmtDate, vvjFmtDateLong, vvjDays, vvjUtestaende, vvjAccessPct, vvjStatusPill, vvjOnbScore, VI, VVJ_ACCENT });
