// ─────────────────────────────────────────────────────────────
// Übergabe- / Rückgabe-Workflows
// Guided step-by-step process for handing equipment over to a tenant
// (Übergabe) and taking it back (Rückgabe), with checklists, deposit /
// fee / ID confirmation, and a damage/missing report that writes straight
// into the Lager (equipment.repairQty / accessory.defectQty).
//
// Data model — rf-workflows: { [rentalId]: {
//   handover: { checks:{[key]:bool}, deposit:bool, fee:bool, id:bool, done:bool, doneAt:iso },
//   ret:      { checks:{[key]:bool}, depositBack:bool, done:bool, doneAt:iso },
//   reports:  [{ id, itemType:'equipment'|'accessory', itemId, name, issue:'defect'|'missing', qty, note, at }]
// }}
// ─────────────────────────────────────────────────────────────
const { useState: useStateWF, useEffect: useEffectWF } = React;

// Blank workflow record
function wfBlank() {
  return { handover: { checks: {}, deposit: false, fee: false, id: false, done: false, doneAt: null },
           ret: { checks: {}, depositBack: false, done: false, doneAt: null },
           reports: [] };
}
function wfGet(workflows, rentalId) {
  const w = workflows && workflows[rentalId];
  if (!w) return wfBlank();
  return { ...wfBlank(), ...w, handover: { ...wfBlank().handover, ...(w.handover || {}) }, ret: { ...wfBlank().ret, ...(w.ret || {}) }, reports: w.reports || [] };
}

// Which action is due for a rental? 'handover' | 'return' | null
// handover: not yet handed over and pickup within ±2 days (or already past-due).
// return:   handed over, not yet returned, and end within ±2 days (or past-due).
function wfDue(rental, workflows, today) {
  if (!rental || rental.status === 'abgeschlossen') return null;
  const w = wfGet(workflows, rental.id);
  const near = (iso, back = 2, fwd = 2) => {
    if (!iso) return false;
    const d = Math.round((fromISO(iso) - fromISO(today)) / 86400000);
    return d >= -60 && d <= fwd; // due once within window, stays due if overdue
  };
  if (!w.handover.done && near(rental.start)) return 'handover';
  if (w.handover.done && !w.ret.done && near(rental.end)) return 'return';
  return null;
}

// Build the equipment + accessory line items a workflow checklist covers.
function wfLines(rental, accessories = []) {
  const eq = (window.getRentalItems ? window.getRentalItems(rental) : []).map(it => ({
    key: 'e:' + it.equipmentId, type: 'equipment', id: it.equipmentId,
    name: it.equipmentName || it.name, qty: Math.max(1, Number(it.quantity) || 1),
  }));
  const acc = (rental.accessoryItems || []).map(a => ({
    key: 'a:' + a.accessoryId, type: 'accessory', id: a.accessoryId,
    name: a.name, qty: Math.max(1, Number(a.quantity) || 1),
    cat: (accessories.find(x => x.id === a.accessoryId) || {}).cat,
  }));
  return { eq, acc, all: [...eq, ...acc] };
}

// Overall workflow progress label
function wfStatusMeta(w, t) {
  if (w.ret.done) return { label: 'Abgeschlossen', color: t.textSec, tint: t.chip };
  if (w.handover.done) return { label: 'Läuft · Rückgabe offen', color: t.accent, tint: t.accentSoft };
  return { label: 'Übergabe offen', color: t.green, tint: t.greenSoft };
}

// ─── The step-by-step runner sheet ───────────────────────────
function WorkflowSheet({ open, mode, rental, workflows, setWorkflows, equipment, setEquipment, accessories, setAccessories, setRentals, onClose, toast }) {
  const t = useTheme();
  const [step, setStep] = useStateWF(0);
  const [reportFor, setReportFor] = useStateWF(null); // line being reported
  useEffectWF(() => { if (open) { setStep(0); setReportFor(null); } }, [open, rental && rental.id, mode]);

  if (!rental) return null;
  const w = wfGet(workflows, rental.id);
  const lines = wfLines(rental, accessories);
  const patch = (fn) => setWorkflows(prev => {
    const cur = wfGet(prev, rental.id);
    const next = fn(JSON.parse(JSON.stringify(cur)));
    return { ...prev, [rental.id]: next };
  });

  const isReturn = mode === 'return';
  const branch = isReturn ? w.ret : w.handover;
  const setCheck = (key, val) => patch(c => { const b = isReturn ? c.ret : c.handover; b.checks[key] = val; return c; });
  const allChecked = lines.all.length > 0 && lines.all.every(l => branch.checks[l.key]);
  const toggleAll = (val) => patch(c => { const b = isReturn ? c.ret : c.handover; lines.all.forEach(l => { b.checks[l.key] = val; }); return c; });

  // Damage / missing report — writes into Lager
  const submitReport = (rep) => {
    patch(c => { c.reports = [...(c.reports || []), { ...rep, id: 'rep-' + Date.now().toString(36), at: todayISO() }]; return c; });
    if (rep.itemType === 'equipment' && setEquipment) {
      setEquipment(prev => prev.map(e => e.id === rep.itemId
        ? { ...e, repairQty: Math.max(0, (Number(e.repairQty) || 0) + (Number(rep.qty) || 1)),
            maint: [...(e.maint || []), { id: 'm-' + Date.now().toString(36), type: rep.issue === 'missing' ? 'defect' : 'repair', title: (rep.issue === 'missing' ? 'Fehlt nach Rückgabe' : 'Schaden nach Rückgabe') + ' · ' + rental.tenantName, date: todayISO(), done: false, note: rep.note || '' }] }
        : e));
    }
    if (rep.itemType === 'accessory' && setAccessories) {
      setAccessories(prev => prev.map(a => a.id === rep.itemId
        ? { ...a, defectQty: Math.max(0, (Number(a.defectQty) || 0) + (Number(rep.qty) || 1)), note: [a.note, (rep.issue === 'missing' ? 'Fehlt' : 'Schaden') + ' (' + rental.tenantName + '): ' + (rep.note || '')].filter(Boolean).join(' · ') }
        : a));
    }
    if (toast) toast(rep.issue === 'missing' ? 'Als fehlend im Lager vermerkt' : 'Schaden im Lager vermerkt');
    setReportFor(null);
  };

  // Steps definition
  const HANDOVER_STEPS = ['Equipment einpacken', 'Zubehör einpacken', 'Kaution & Gebühr', 'Ausweis', 'Abschluss'];
  const RETURN_STEPS = ['Equipment zurück', 'Zubehör zurück', 'Kaution zurück', 'Abschluss'];
  const steps = isReturn ? RETURN_STEPS : HANDOVER_STEPS;

  const finish = () => {
    patch(c => {
      const b = isReturn ? c.ret : c.handover;
      b.done = true; b.doneAt = todayISO();
      return c;
    });
    if (setRentals) {
      setRentals(prev => prev.map(r => r.id === rental.id
        ? { ...r, status: isReturn ? 'abgeschlossen' : 'aktiv',
            depositStatus: isReturn ? 'zurueckgezahlt' : 'erhalten',
            paymentStatus: isReturn ? r.paymentStatus : 'bezahlt' }
        : r));
    }
    if (toast) toast(isReturn ? 'Rückgabe abgeschlossen' : 'Übergabe abgeschlossen');
    onClose();
  };

  // ── Checklist renderer ──
  const Checklist = ({ items, emptyLabel, withReport }) => (
    <div>
      {items.length === 0 && <div style={{ padding: '24px 16px', textAlign: 'center', color: t.textSec, fontSize: 13 }}>{emptyLabel}</div>}
      {items.length > 0 &&
      <Pressable onClick={() => toggleAll(!items.every(l => branch.checks[l.key]))} scale={0.98}>
        <div style={{ display: 'flex', alignItems: 'center', justifyContent: 'space-between', padding: '4px 4px 10px' }}>
          <span style={{ fontSize: 12, color: t.textSec, fontWeight: 600 }}>{items.filter(l => branch.checks[l.key]).length}/{items.length} erledigt</span>
          <span style={{ fontSize: 12.5, color: t.accent, fontWeight: 600 }}>{items.every(l => branch.checks[l.key]) ? 'Alle abwählen' : 'Alle abhaken'}</span>
        </div>
      </Pressable>}
      <div style={{ display: 'flex', flexDirection: 'column', gap: 8 }}>
        {items.map(l => {
          const on = !!branch.checks[l.key];
          const rep = (w.reports || []).find(r => r.itemType === l.type && r.itemId === l.id);
          return (
            <div key={l.key} style={{ background: t.card, borderRadius: 12, boxShadow: t.shadowCard, overflow: 'hidden' }}>
              <div style={{ display: 'flex', alignItems: 'center', gap: 12, padding: '12px 14px' }}>
                <Pressable onClick={() => setCheck(l.key, !on)} scale={0.85}>
                  <div style={{ width: 26, height: 26, borderRadius: 8, flexShrink: 0, background: on ? t.green : 'transparent', border: on ? 'none' : `1.6px solid ${t.textTer}`, display: 'flex', alignItems: 'center', justifyContent: 'center' }}>
                    {on && <svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="#fff" strokeWidth="3.4" strokeLinecap="round" strokeLinejoin="round"><path d="M5 12l5 5L20 7"/></svg>}
                  </div>
                </Pressable>
                <div style={{ flex: 1, minWidth: 0 }} onClick={() => setCheck(l.key, !on)}>
                  <div style={{ fontSize: 14, fontWeight: 600, color: t.text, whiteSpace: 'nowrap', overflow: 'hidden', textOverflow: 'ellipsis' }}>{l.name}</div>
                  <div style={{ fontSize: 11.5, color: t.textSec, marginTop: 1 }}>{l.qty}× {l.type === 'accessory' ? (l.cat || 'Zubehör') : 'Gerät'}</div>
                </div>
                {withReport &&
                <Pressable onClick={() => setReportFor(l)} scale={0.9}>
                  <div style={{ padding: '6px 10px', borderRadius: 8, background: rep ? t.orangeSoft : t.chip, color: rep ? t.orange : t.textSec, fontSize: 11.5, fontWeight: 600, display: 'flex', alignItems: 'center', gap: 4 }}>
                    <Icon d="M12 9v4M12 17h.01M10.3 3.9L1.8 18a2 2 0 001.7 3h17a2 2 0 001.7-3L13.7 3.9a2 2 0 00-3.4 0z" color={rep ? t.orange : t.textSec} size={13} sw={1.9}/>
                    {rep ? 'Gemeldet' : 'Melden'}
                  </div>
                </Pressable>}
              </div>
              {rep &&
              <div style={{ padding: '0 14px 10px 52px', fontSize: 11.5, color: t.orange }}>
                {rep.issue === 'missing' ? 'Fehlt' : 'Schaden'}{rep.qty > 1 ? ` (${rep.qty}×)` : ''}{rep.note ? ' · ' + rep.note : ''}
              </div>}
            </div>
          );
        })}
      </div>
    </div>
  );

  // ── Confirm row (Kaution / Gebühr / Ausweis) ──
  const ConfirmRow = ({ label, sub, field, icon }) => {
    const on = !!branch[field];
    return (
      <Pressable onClick={() => patch(c => { const b = isReturn ? c.ret : c.handover; b[field] = !b[field]; return c; })} scale={0.98}>
        <div style={{ background: t.card, borderRadius: 12, boxShadow: t.shadowCard, padding: '14px', display: 'flex', alignItems: 'center', gap: 12 }}>
          <div style={{ width: 26, height: 26, borderRadius: 8, flexShrink: 0, background: on ? t.green : 'transparent', border: on ? 'none' : `1.6px solid ${t.textTer}`, display: 'flex', alignItems: 'center', justifyContent: 'center' }}>
            {on && <svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="#fff" strokeWidth="3.4" strokeLinecap="round" strokeLinejoin="round"><path d="M5 12l5 5L20 7"/></svg>}
          </div>
          <div style={{ flex: 1 }}>
            <div style={{ fontSize: 14.5, fontWeight: 600, color: t.text }}>{label}</div>
            {sub && <div style={{ fontSize: 12, color: t.textSec, marginTop: 1 }}>{sub}</div>}
          </div>
        </div>
      </Pressable>
    );
  };

  // ── Step body ──
  const deposit = Number(rental.deposit) || 0;
  const total = window.rentalTotal ? window.rentalTotal(rental) : 0;
  let body;
  if (!isReturn) {
    if (step === 0) body = <Checklist items={lines.eq} emptyLabel="Kein Equipment in dieser Miete." />;
    else if (step === 1) body = <Checklist items={lines.acc} emptyLabel="Kein Zubehör in dieser Miete." />;
    else if (step === 2) body = (
      <div style={{ display: 'flex', flexDirection: 'column', gap: 10 }}>
        <ConfirmRow label="Kaution erhalten" sub={deposit ? deposit + ' €' : 'Keine Kaution hinterlegt'} field="deposit" />
        <ConfirmRow label="Mietgebühr bezahlt" sub={total ? total + ' € gesamt' : ''} field="fee" />
      </div>);
    else if (step === 3) body = (
      <div style={{ display: 'flex', flexDirection: 'column', gap: 10 }}>
        <ConfirmRow label="Personalausweis geprüft" sub="Identität kontrolliert / Foto vorhanden" field="id" />
        {(rental.photos || []).some(p => /ausweis/i.test(p.label || '')) &&
          <div style={{ fontSize: 12, color: t.green, padding: '0 4px' }}>✓ Ausweis-Fotos liegen dieser Miete bei.</div>}
      </div>);
    else body = <WorkflowSummary mode={mode} lines={lines} branch={branch} w={w} t={t} deposit={deposit} />;
  } else {
    if (step === 0) body = <Checklist items={lines.eq} emptyLabel="Kein Equipment." withReport />;
    else if (step === 1) body = <Checklist items={lines.acc} emptyLabel="Kein Zubehör." withReport />;
    else if (step === 2) body = <ConfirmRow label="Kaution zurückgegeben" sub={deposit ? deposit + ' €' : 'Keine Kaution'} field="depositBack" />;
    else body = <WorkflowSummary mode={mode} lines={lines} branch={branch} w={w} t={t} deposit={deposit} />;
  }

  const lastStep = step === steps.length - 1;
  // Gate advancing on the current step being satisfied
  const canNext = (() => {
    if (isReturn) {
      if (step === 0) return lines.eq.every(l => branch.checks[l.key]) || lines.eq.length === 0;
      if (step === 1) return lines.acc.every(l => branch.checks[l.key]) || lines.acc.length === 0;
      return true;
    }
    if (step === 0) return lines.eq.every(l => branch.checks[l.key]) || lines.eq.length === 0;
    if (step === 1) return lines.acc.every(l => branch.checks[l.key]) || lines.acc.length === 0;
    return true;
  })();

  return (
    <Sheet open={open} onClose={onClose} maxHeight="92%">
      <div style={{ padding: '4px 20px 28px' }}>
        {/* Header */}
        <div style={{ display: 'flex', alignItems: 'center', justifyContent: 'space-between', marginBottom: 4 }}>
          <div style={{ fontSize: 11, fontWeight: 700, letterSpacing: 1, textTransform: 'uppercase', color: isReturn ? t.accent : t.green }}>
            {isReturn ? 'Rückgabe' : (rental.delivery && rental.delivery.enabled ? 'Auslieferung' : 'Übergabe')}
          </div>
          <Pressable onClick={onClose} scale={0.9}><div style={{ fontSize: 13, color: t.textSec, fontWeight: 600 }}>Schließen</div></Pressable>
        </div>
        <div style={{ fontSize: 23, fontWeight: 700, color: t.text, letterSpacing: -0.5 }}>{rental.tenantName}</div>
        <div style={{ fontSize: 12.5, color: t.textSec, marginTop: 2 }}>{fmtRange(rental.start, rental.end)}</div>

        {/* Progress dots */}
        <div style={{ display: 'flex', gap: 6, margin: '16px 0 18px' }}>
          {steps.map((s, i) => (
            <div key={i} style={{ flex: 1, height: 4, borderRadius: 2, background: i <= step ? (isReturn ? t.accent : t.green) : t.chip }} />
          ))}
        </div>
        <div style={{ fontSize: 15, fontWeight: 700, color: t.text, marginBottom: 12 }}>{steps[step]}</div>

        {body}

        {/* Nav */}
        <div style={{ display: 'flex', gap: 10, marginTop: 20 }}>
          {step > 0 &&
          <Pressable onClick={() => setStep(s => s - 1)} scale={0.97} style={{ flex: 1 }}>
            <div style={{ padding: '14px 0', textAlign: 'center', borderRadius: 12, background: t.chip, color: t.text, fontSize: 14.5, fontWeight: 600 }}>Zurück</div>
          </Pressable>}
          {!lastStep &&
          <Pressable onClick={() => canNext && setStep(s => s + 1)} scale={canNext ? 0.97 : 1} style={{ flex: 2 }}>
            <div style={{ padding: '14px 0', textAlign: 'center', borderRadius: 12, background: canNext ? t.solidBg : t.chip, color: canNext ? t.solidFg : t.textTer, fontSize: 14.5, fontWeight: 700 }}>Weiter</div>
          </Pressable>}
          {lastStep &&
          <Pressable onClick={finish} scale={0.97} style={{ flex: 2 }}>
            <div style={{ padding: '14px 0', textAlign: 'center', borderRadius: 12, background: isReturn ? t.accent : t.green, color: '#fff', fontSize: 14.5, fontWeight: 700 }}>
              {isReturn ? 'Rückgabe abschließen' : 'Übergabe abschließen'}
            </div>
          </Pressable>}
        </div>
      </div>

      {/* Report sub-sheet */}
      <ReportSheet open={!!reportFor} line={reportFor} onClose={() => setReportFor(null)} onSubmit={submitReport} t={t} />
    </Sheet>
  );
}

// ── Final summary step ──
function WorkflowSummary({ mode, lines, branch, w, t, deposit }) {
  const isReturn = mode === 'return';
  const done = lines.all.filter(l => branch.checks[l.key]).length;
  const Row = ({ label, ok }) => (
    <div style={{ display: 'flex', alignItems: 'center', gap: 10, padding: '9px 0', borderBottom: `0.5px solid ${t.sep}` }}>
      <div style={{ width: 20, height: 20, borderRadius: 10, background: ok ? t.green : t.chip, display: 'flex', alignItems: 'center', justifyContent: 'center', flexShrink: 0 }}>
        {ok && <svg width="11" height="11" viewBox="0 0 24 24" fill="none" stroke="#fff" strokeWidth="3.6" strokeLinecap="round" strokeLinejoin="round"><path d="M5 12l5 5L20 7"/></svg>}
      </div>
      <span style={{ fontSize: 13.5, color: t.text, fontWeight: 500 }}>{label}</span>
    </div>
  );
  return (
    <div style={{ background: t.card, borderRadius: 14, boxShadow: t.shadowCard, padding: '6px 16px 12px' }}>
      <Row label={`Equipment & Zubehör (${done}/${lines.all.length})`} ok={lines.all.length > 0 && done === lines.all.length} />
      {!isReturn && <Row label={`Kaution erhalten${deposit ? ' · ' + deposit + ' €' : ''}`} ok={branch.deposit} />}
      {!isReturn && <Row label="Mietgebühr bezahlt" ok={branch.fee} />}
      {!isReturn && <Row label="Personalausweis geprüft" ok={branch.id} />}
      {isReturn && <Row label={`Kaution zurückgegeben${deposit ? ' · ' + deposit + ' €' : ''}`} ok={branch.depositBack} />}
      {isReturn && (w.reports || []).length > 0 &&
        <div style={{ marginTop: 10, padding: '10px 12px', borderRadius: 10, background: t.orangeSoft }}>
          <div style={{ fontSize: 12, fontWeight: 700, color: t.orange, marginBottom: 4 }}>{w.reports.length} Meldung(en) ans Lager</div>
          {w.reports.map(r => <div key={r.id} style={{ fontSize: 11.5, color: t.orange }}>· {r.name}: {r.issue === 'missing' ? 'fehlt' : 'Schaden'}{r.note ? ' – ' + r.note : ''}</div>)}
        </div>}
      <div style={{ fontSize: 12, color: t.textSec, marginTop: 12, lineHeight: 1.5 }}>
        {isReturn ? 'Mit „Rückgabe abschließen" wird die Miete beendet und Meldungen im Lager verbucht.' : 'Mit „Übergabe abschließen" wird die Miete aktiv gesetzt.'}
      </div>
    </div>
  );
}

// ── Damage / missing report sub-sheet ──
function ReportSheet({ open, line, onClose, onSubmit, t }) {
  const [issue, setIssue] = useStateWF('defect');
  const [qty, setQty] = useStateWF(1);
  const [note, setNote] = useStateWF('');
  useEffectWF(() => { if (open) { setIssue('defect'); setQty(1); setNote(''); } }, [open]);
  if (!line) return null;
  return (
    <Sheet open={open} onClose={onClose} maxHeight="70%">
      <div style={{ padding: '4px 20px 28px' }}>
        <div style={{ display: 'flex', alignItems: 'center', justifyContent: 'space-between', marginBottom: 4 }}>
          <div style={{ fontSize: 20, fontWeight: 700, color: t.text, letterSpacing: -0.4 }}>Problem melden</div>
          <Pressable onClick={onClose} scale={0.9}><div style={{ fontSize: 13, color: t.textSec, fontWeight: 600 }}>Abbrechen</div></Pressable>
        </div>
        <div style={{ fontSize: 13, color: t.textSec, marginTop: 2, marginBottom: 18 }}>{line.name}</div>

        <div style={{ display: 'flex', gap: 8, marginBottom: 16 }}>
          {[['defect', 'Beschädigt'], ['missing', 'Fehlt']].map(([id, label]) => {
            const on = issue === id;
            return (
              <Pressable key={id} onClick={() => setIssue(id)} scale={0.97} style={{ flex: 1 }}>
                <div style={{ padding: '12px 0', textAlign: 'center', borderRadius: 12, background: on ? t.solidBg : t.chip, color: on ? t.solidFg : t.text, fontSize: 14, fontWeight: 600 }}>{label}</div>
              </Pressable>
            );
          })}
        </div>

        <div style={{ display: 'flex', alignItems: 'center', justifyContent: 'space-between', marginBottom: 16 }}>
          <span style={{ fontSize: 14, color: t.text, fontWeight: 500 }}>Anzahl betroffen</span>
          <div style={{ display: 'flex', alignItems: 'center', gap: 12 }}>
            <Pressable onClick={() => setQty(q => Math.max(1, q - 1))} scale={0.85}>
              <div style={{ width: 32, height: 32, borderRadius: 16, background: t.chip, display: 'flex', alignItems: 'center', justifyContent: 'center' }}><Icon d="M5 12h14" color={t.text} size={14} sw={2.4}/></div>
            </Pressable>
            <span style={{ minWidth: 24, textAlign: 'center', fontSize: 17, fontWeight: 700, color: t.text }}>{qty}</span>
            <Pressable onClick={() => setQty(q => Math.min(line.qty, q + 1))} scale={0.85}>
              <div style={{ width: 32, height: 32, borderRadius: 16, background: t.solidBg, display: 'flex', alignItems: 'center', justifyContent: 'center' }}><Icon d="M12 5v14M5 12h14" color={t.solidFg} size={14} sw={2.4}/></div>
            </Pressable>
          </div>
        </div>

        <textarea value={note} onChange={e => setNote(e.target.value)} rows={3} placeholder="Was ist passiert? (optional)"
          style={{ width: '100%', boxSizing: 'border-box', padding: '11px 13px', borderRadius: 11, border: `0.5px solid ${t.inputBorder}`, background: t.inputBg, fontSize: 14, color: t.text, outline: 'none', resize: 'none', fontFamily: 'inherit', marginBottom: 18 }} />

        <Pressable onClick={() => onSubmit({ itemType: line.type, itemId: line.id, name: line.name, issue, qty, note: note.trim() })} scale={0.97}>
          <div style={{ padding: '15px', textAlign: 'center', borderRadius: 14, background: t.orange, color: '#fff', fontSize: 15, fontWeight: 700 }}>Im Lager vermerken</div>
        </Pressable>
        <Pressable onClick={onClose} scale={0.97}>
          <div style={{ padding: '13px', textAlign: 'center', borderRadius: 14, background: t.chip, color: t.text, fontSize: 14.5, fontWeight: 600, marginTop: 8 }}>Zurück zur Checkliste</div>
        </Pressable>
        <div style={{ fontSize: 11.5, color: t.textSec, textAlign: 'center', marginTop: 10, lineHeight: 1.5 }}>
          Wird bei {line.type === 'equipment' ? 'diesem Gerät' : 'diesem Zubehör'} als {issue === 'missing' ? 'fehlend' : 'in Reparatur'} vermerkt und reduziert die Verfügbarkeit.
        </div>
      </div>
    </Sheet>
  );
}

// ─── Akten: Workflows list (per customer) ────────────────────
function WorkflowsList({ rentals = [], workflows = {}, accessories = [], onOpen }) {
  const t = useTheme();
  // Show non-completed rentals first, then completed workflows.
  const rows = rentals
    .filter(r => r.status !== 'abgeschlossen' || wfGet(workflows, r.id).handover.done || wfGet(workflows, r.id).ret.done)
    .map(r => ({ r, w: wfGet(workflows, r.id), due: wfDue(r, workflows, todayISO()) }))
    .sort((a, b) => (a.r.start || '').localeCompare(b.r.start || ''));

  if (rows.length === 0) {
    return <div style={{ padding: '48px 24px', textAlign: 'center', color: t.textSec, fontSize: 13.5 }}>Noch keine Workflows.<br/>Sobald eine Übergabe oder Rückgabe ansteht, erscheint sie hier.</div>;
  }

  return (
    <div style={{ padding: '14px 16px 0', display: 'flex', flexDirection: 'column', gap: 10 }}>
      {rows.map(({ r, w, due }) => {
        const meta = wfStatusMeta(w, t);
        const reps = (w.reports || []).length;
        return (
          <Pressable key={r.id} onClick={() => onOpen(r, due || (w.handover.done && !w.ret.done ? 'return' : 'handover'))} scale={0.99}>
            <div style={{ background: t.card, borderRadius: 14, boxShadow: t.shadowCard, padding: '13px 15px' }}>
              <div style={{ display: 'flex', alignItems: 'center', gap: 12 }}>
                <div style={{ flex: 1, minWidth: 0 }}>
                  <div style={{ fontSize: 15, fontWeight: 600, color: t.text, whiteSpace: 'nowrap', overflow: 'hidden', textOverflow: 'ellipsis' }}>{r.tenantName}</div>
                  <div style={{ fontSize: 12, color: t.textSec, marginTop: 2, whiteSpace: 'nowrap', overflow: 'hidden', textOverflow: 'ellipsis' }}>{(window.rentalEquipmentLabel ? window.rentalEquipmentLabel(r) : r.equipmentName) || ''} · {fmtRange(r.start, r.end)}</div>
                </div>
                <div style={{ textAlign: 'right', flexShrink: 0 }}>
                  <span style={{ display: 'inline-block', padding: '4px 10px', borderRadius: 100, fontSize: 11, fontWeight: 700, color: meta.color, background: meta.tint }}>{meta.label}</span>
                  {reps > 0 && <div style={{ fontSize: 10.5, color: t.orange, fontWeight: 600, marginTop: 4 }}>{reps} Meldung(en)</div>}
                </div>
              </div>
              {due &&
              <div style={{ marginTop: 10, padding: '9px 12px', borderRadius: 10, background: due === 'return' ? t.accentSoft : t.greenSoft, display: 'flex', alignItems: 'center', justifyContent: 'space-between' }}>
                <span style={{ fontSize: 12.5, fontWeight: 700, color: due === 'return' ? t.accent : t.green }}>{due === 'return' ? 'Rückgabe starten' : 'Übergabe starten'}</span>
                <Icon d="M9 18l6-6-6-6" color={due === 'return' ? t.accent : t.green} size={14} sw={2.2}/>
              </div>}
            </div>
          </Pressable>
        );
      })}
    </div>
  );
}

Object.assign(window, { wfBlank, wfGet, wfDue, wfLines, wfStatusMeta, WorkflowSheet, WorkflowsList });
