:root {
  --nav-height: 60px;
}

body {
  font-family: 'Segoe UI', Arial, sans-serif;
  background-color: #F8F9FA;
  margin: 0; padding: 0;
  color: #1A1A2E;
  min-height: 100vh;
  width: 100%;
  display: flex;
  flex-direction: column;
}
.page { display: none; padding: 40px; flex: 1; }
.page.active { display: block; }

nav {
  background-color: #1A1A2E;
  box-shadow: 0 2px 8px rgba(0,0,0,0.25);
  position: sticky;
  top: 0;
  z-index: 100;
}
.nav-inner {
  padding: 10px 40px;
  display: flex; gap: 24px; align-items: center;
}

.nav-logo {
  display: flex;
  align-items: center;
  gap: 10px;
  text-decoration: none;
  cursor: pointer;
  outline: none;
  transition: opacity 0.15s;
}
.nav-logo:hover { opacity: 0.85; }

.nav-logo-text {
  font-size: 13px;
  font-weight: 600;
  color: white;
  line-height: 1.3;
}

.nav-logo-text span {
  color: #D95F02;
  display: block;
}

/* Placeholder square shown until a nav logo is uploaded. */
.nav-logo-ph {
  width: 38px; height: 38px; flex: 0 0 auto;
  border: 1.5px dashed rgba(255,255,255,0.35); border-radius: 9px;
  color: rgba(255,255,255,0.55); font-size: 10px; font-weight: 600;
  display: flex; align-items: center; justify-content: center;
  text-transform: uppercase; letter-spacing: 0.5px;
}

/* App-name variant of the nav text ("dsiTOOL"): one line, larger, with the
   TOOL part orange inline (overrides the two-line org-name layout above). */
.nav-logo-text.nav-app-name {
  font-size: 19px;
  font-weight: 700;
  letter-spacing: 0.5px;
}
.nav-logo-text.nav-app-name span { display: inline; }

.nav-divider {
  width: 1px;
  height: 24px;
  background: rgba(255,255,255,0.2);
  margin-right: 8px;
}

/* The page links + user area. On desktop this is just an inline flex row
   that fills the bar (nav-user keeps its margin-left:auto, so it pins right).
   On mobile (see the MOBILE block) it becomes a drop-down panel. */
.nav-menu {
  display: flex;
  align-items: center;
  gap: 24px;
  flex: 1;
}

/* ── FOOTER ── */
footer {
  background: #1A1A2E;
  color: rgba(255,255,255,0.5);
  font-size: 12px;
  margin-top: 60px;
  position: relative;
  z-index: 51;
}
.footer-inner {
  padding: 20px 40px;
  display: flex;
  justify-content: space-between;
  align-items: center;
  flex-wrap: wrap;
  gap: 8px;
}

footer a {
  color: #D95F02;
  text-decoration: none;
}

footer a:hover { text-decoration: underline; }

nav button {
  color: rgba(255,255,255,0.8); font-weight: 600;
  background: none; border: none;
  font-size: 14px; font-family: inherit;
  cursor: pointer; padding: 0;
}

nav button:hover { color: white; text-decoration: underline; }
nav button.active { color: white; border-bottom: 2px solid #D95F02; padding-bottom: 2px; }

.page.active { display: block; }

h1 { color: #D95F02; margin-bottom: 4px; }
h2 { color: #555; }

/* ── Dashboard redesign ─────────────────────────── */
.dash-page-header { margin-bottom: 28px; }
.dash-title   { font-size: 22px; font-weight: 700; color: #1A1A2E; margin: 0; }

.dash-section-label {
  display: flex; align-items: center; gap: 12px;
  font-size: 11px; font-weight: 700; color: #bbb;
  text-transform: uppercase; letter-spacing: 1.2px;
  margin-bottom: 14px;
}
.dash-section-label::after {
  content: ''; flex: 1; height: 1px; background: #efefef;
}

.dash-kpi-grid {
  display: grid;
  grid-template-columns: repeat(3, 1fr);
  gap: 14px;
  margin-bottom: 14px;
}

.dash-kpi-card {
  background: white; border-radius: 12px;
  padding: 18px 20px;
  display: flex; align-items: center; gap: 14px;
  box-shadow: 0 1px 3px rgba(0,0,0,0.07), 0 1px 2px rgba(0,0,0,0.04);
}

/* ── Member trend chart (Mitgliederentwicklung) ── */
/* order:2 puts the toggle AFTER the section label's ::after divider line. */
.trend-toggle { display: inline-flex; background: #f0f0f3; border-radius: 9px; padding: 3px; order: 2; }
.trend-toggle button {
  border: none; background: none; padding: 5px 12px; border-radius: 7px;
  font-family: inherit; font-size: 12px; font-weight: 600; color: #555; cursor: pointer;
  text-transform: none; letter-spacing: normal;
}
.trend-toggle button.active { background: #1A1A2E; color: #fff; }

.trend-card {
  background: #fff; border-radius: 12px; padding: 16px 16px 8px;
  box-shadow: 0 1px 3px rgba(0,0,0,0.07), 0 1px 2px rgba(0,0,0,0.04);
}
.trend-legend { display: flex; gap: 16px; flex-wrap: wrap; font-size: 13px; color: #444; margin-bottom: 4px; }
.trend-legend span { display: inline-flex; align-items: center; gap: 6px; }
.trend-legend i {
  width: 14px; height: 0; border-top-width: 3px; border-top-style: solid;
  display: inline-block; border-radius: 2px;
}
.trend-legend .lg-net    i { border-top-color: #1A1A2E; }
.trend-legend .lg-joins  i { border-top-color: #D95F02; }
.trend-legend .lg-leaves i { border-top-color: #9aa0a6; border-top-style: dashed; }

.trend-svg-wrap { position: relative; }
.trend-svg-wrap svg { display: block; width: 100%; height: auto; }
/* axis font-size comes from an SVG attribute (it re-scales per viewport) — no font-size here */
.trend-axis-label { fill: #999; }
.trend-grid-line  { stroke: #ececf0; stroke-width: 1; }

.trend-tip {
  position: absolute; pointer-events: none; display: none;
  background: #1A1A2E; color: #fff; border-radius: 8px;
  padding: 8px 11px; font-size: 12.5px; line-height: 1.5;
  box-shadow: 0 4px 14px rgba(0,0,0,0.25); white-space: nowrap; z-index: 5;
}
.trend-tip b { font-size: 13px; }
.trend-tip .t-net    { color: #ffd9b8; }
.trend-tip .t-joins  { color: #ff9d4d; }
.trend-tip .t-leaves { color: #b9bec6; }

.trend-hint { font-size: 12px; color: #999; padding: 6px 2px 8px; }

/* Quick-action strip — navigate-and-open buttons under the dashboard header */
.dash-quick-actions {
  display: flex; flex-wrap: wrap; gap: 10px; margin: 4px 0 24px;
}
.dash-quick-btn {
  display: inline-flex; align-items: center; gap: 8px;
  background: #fff; border: 1px solid #e6e6ec; border-radius: 9px;
  padding: 9px 15px; font-size: 13px; font-weight: 600; color: #1A1A2E;
  cursor: pointer; transition: all 0.13s ease;
  box-shadow: 0 1px 2px rgba(0,0,0,0.04);
}
.dash-quick-btn svg { color: #D95F02; }
.dash-quick-btn:hover {
  border-color: #D95F02; transform: translateY(-1px);
  box-shadow: 0 4px 12px rgba(217, 95, 2, 0.12);
}
.dash-quick-btn:focus-visible { outline: 2px solid #D95F02; outline-offset: 2px; }

/* Clickable dashboard cards (KPIs + charts) — navigate to their page on click.
   Lift slightly on hover; show a clear focus ring for keyboard users. */
.dash-clickable { cursor: pointer; transition: transform 0.12s ease, box-shadow 0.12s ease; }
.dash-clickable:hover {
  transform: translateY(-2px);
  box-shadow: 0 6px 18px rgba(26, 26, 46, 0.12), 0 2px 4px rgba(0,0,0,0.05);
}
.dash-clickable:focus-visible { outline: 2px solid #D95F02; outline-offset: 2px; }

.dash-kpi-icon {
  width: 44px; height: 44px; border-radius: 10px; flex-shrink: 0;
  display: flex; align-items: center; justify-content: center;
}
.dash-kpi-icon--orange { background: #FEF0E6; color: #D95F02; }
.dash-kpi-icon--navy   { background: #ECEDF5; color: #1A1A2E; }
.dash-kpi-icon--amber  { background: #FEF6E6; color: #B45309; }
.dash-kpi-icon--green  { background: #EAF4EB; color: #2E7D32; }

.dash-kpi-number {
  font-size: 26px; font-weight: 700; color: #1A1A2E; line-height: 1;
}
.dash-kpi-number--amber { color: #B45309; }
.dash-kpi-number--navy  { color: #1A1A2E; }
.dash-kpi-number--green { color: #2E7D32; }
.dash-kpi-label { font-size: 12px; color: #999; margin-top: 5px; }

.dash-chart-grid {
  display: grid; grid-template-columns: 1fr 1fr; gap: 14px;
}
.dash-card {
  background: white; border-radius: 12px; padding: 20px 24px;
  box-shadow: 0 1px 3px rgba(0,0,0,0.07), 0 1px 2px rgba(0,0,0,0.04);
}
.dash-card-title {
  font-size: 11px; font-weight: 700; color: #bbb;
  text-transform: uppercase; letter-spacing: 1px; margin-bottom: 16px;
}
/* Recent-members widget — square cards (KPI-card style) in a wrapping grid */
.dash-recent-grid {
  display: grid; grid-template-columns: repeat(auto-fill, minmax(150px, 1fr));
  gap: 14px;
}
.dash-member-tile {
  display: flex; flex-direction: column; align-items: center; justify-content: center;
  gap: 9px; text-align: center; min-height: 132px;
  background: white; border: 1px solid #ececf0; border-radius: 12px;
  padding: 18px 14px; cursor: pointer; font-family: inherit;
  box-shadow: 0 1px 3px rgba(0,0,0,0.07), 0 1px 2px rgba(0,0,0,0.04);
  transition: transform 0.12s ease, box-shadow 0.12s ease, border-color 0.12s ease;
}
.dash-member-tile:hover {
  transform: translateY(-2px); border-color: #D95F02;
  box-shadow: 0 6px 18px rgba(217, 95, 2, 0.12);
}
.dash-member-tile:focus-visible { outline: 2px solid #D95F02; outline-offset: 2px; }
.dash-member-avatar {
  width: 42px; height: 42px; border-radius: 50%; flex-shrink: 0;
  display: flex; align-items: center; justify-content: center;
  background: #FEF0E6; color: #D95F02; font-weight: 700; font-size: 15px;
}
.dash-member-name {
  font-size: 13px; font-weight: 600; color: #1A1A2E; line-height: 1.3;
  max-width: 100%; overflow-wrap: anywhere;
}
.dash-member-joined { font-size: 11px; color: #999; }
.dash-recent-empty { color: #aaa; font-size: 13px; padding: 8px 2px; }

.dash-chart-body {
  display: flex; align-items: center; gap: 20px;
}
.dash-chart-legend {
  display: flex; flex-direction: column; gap: 6px; flex: 1;
}
.legend-item {
  display: flex; align-items: center; gap: 6px; font-size: 12px; color: #444;
}
.legend-dot {
  width: 8px; height: 8px; border-radius: 50%; flex-shrink: 0;
}

/* Backup status widget on the dashboard (admin-only).
   Colour states driven by data-status: ok / stale / not_configured / missing / error / loading.
   not_configured shares the amber warning look with stale: no backup target is set up,
   which is a gap to close, not a failure that just happened. */
.dash-backup-card {
  background: white; border-radius: 12px;
  padding: 16px 20px;
  display: flex; align-items: center; gap: 14px;
  box-shadow: 0 1px 3px rgba(0,0,0,0.07), 0 1px 2px rgba(0,0,0,0.04);
  border-left: 4px solid #ccc;
}
.dash-backup-dot {
  width: 12px; height: 12px; border-radius: 50%;
  background: #ccc; flex-shrink: 0;
}
.dash-backup-body { flex: 1; min-width: 0; }
.dash-backup-title { font-size: 14px; font-weight: 600; color: #1A1A2E; }
.dash-backup-sub   { font-size: 12px; color: #777; margin-top: 3px; }

.dash-backup-card[data-status="ok"]      { border-left-color: #2E7D32; }
.dash-backup-card[data-status="ok"]      .dash-backup-dot { background: #2E7D32; }
.dash-backup-card[data-status="stale"],
.dash-backup-card[data-status="not_configured"] { border-left-color: #F9A825; }
.dash-backup-card[data-status="stale"]          .dash-backup-dot { background: #F9A825; }
.dash-backup-card[data-status="not_configured"] .dash-backup-dot { background: #F9A825; }
.dash-backup-card[data-status="missing"],
.dash-backup-card[data-status="error"]   { border-left-color: #C62828; background: #fff5f5; }
.dash-backup-card[data-status="missing"] .dash-backup-dot,
.dash-backup-card[data-status="error"]   .dash-backup-dot { background: #C62828; }
.dash-backup-card[data-status="missing"] .dash-backup-title,
.dash-backup-card[data-status="error"]   .dash-backup-title { color: #C62828; }

/* kept for any non-dashboard usage */
.dashboard { display: flex; gap: 16px; margin-top: 16px; flex-wrap: wrap; }
.stat-card {
  background: white; border-radius: 10px; padding: 16px 24px; text-align: center;
  border-top: 4px solid #D95F02; box-shadow: 0 2px 8px rgba(0,0,0,0.07);
  flex: 1; min-width: 150px;
}
.stat-card .number { font-size: 32px; font-weight: bold; color: #D95F02; }
.stat-card .label  { font-size: 13px; color: #888; margin-top: 4px; }

/* .filter-btn is the small pill button — now used ONLY by the Events
   "Show N more" toggle (Members/Finance/Tickets all moved to .ctrl-bar).
   The old .filter-bar / .filter-label container classes were removed with
   the Tickets migration. */
.filter-btn {
  background: white; border: 1px solid #e0e0e0;
  color: #888; font-size: 13px; padding: 5px 14px;
  border-radius: 20px; cursor: pointer;
  font-family: 'Segoe UI', Arial, sans-serif;
  transition: all 0.15s;
}
.filter-btn:hover { border-color: #D95F02; color: #D95F02; }
.filter-btn.active { background: #D95F02; color: white; border-color: #D95F02; }

table {
  width: 100%; border-collapse: collapse; margin-top: 24px;
  background: white; border-radius: 10px;
  overflow: hidden; box-shadow: 0 2px 8px rgba(0,0,0,0.07);
  table-layout: fixed;
}

/* ── ONE data-table typography for the whole app (2026-08-02) ───────────────
   These values ARE the Mandate table's, promoted from `.mand-table` to the base
   rule after measuring every table in the app: seven data grids carried five
   header sizes (10.5 / 11 / 11.5 / 14 / 16px), four body sizes, seven padding
   pairs and three header colours. They already shared the chrome (navy bar,
   white sheet, shadow, 10px radius) — only the type differed, so one rule here
   replaces the per-table blocks that merely restated it differently.

   Small uppercase rather than a 16px sentence, because a header is a label for
   a column, not a line of prose, and a compact one leaves the row itself the
   loudest thing in the table.

   Reference surfaces are NOT data grids and switch this off on purpose:
   `.help-table`, `.perm-matrix`, `.notif-matrix`, the import-mapping tables.
   Adding a fourth exception is a sign the new thing is not a data grid either. */
th {
  background-color: #1A1A2E; color: white;
  text-align: left; padding: 10px 12px;
  font-size: 11.5px; font-weight: 700;
  text-transform: uppercase; letter-spacing: .05em;
}
/* `white-space: nowrap` deliberately did NOT come along from `.mand-table`. The
   reference tables override background, size, weight, transform, spacing and
   padding but none of them overrides white-space, so a global nowrap would have
   reached inside the matrices and pushed a long header (a role name in a 132px
   column) out of its cell instead of letting it wrap. It stays where it was. */
table.mand-table th { white-space: nowrap; }

td { padding: 10px 12px; font-size: 13.5px; border-bottom: 1px solid #F0F0F0; color: #2D2D2D; }
tr:last-child td { border-bottom: none; }
tr:hover td { background-color: #FFF5F0; }

td select {
  border: none; background: transparent;
  font-size: 14px; font-family: 'Segoe UI', Arial, sans-serif;
  cursor: pointer; outline: none; width: 100%;
}

/* Member status is no longer colored (the status cell/badge dropped its status
   class). `.active` stays because it is a SHARED toggle class (.page.active,
   nav button.active, .notes-content.active, …) — not status-only. */
.active   { color: #2E7D32; }

.notes-row td { padding: 0; background: #FFFAF7; }
.notes-content { display: none; padding: 12px 16px; border-top: 1px solid #F0F0F0; }
.notes-content.active { display: block; }

.notes-content textarea {
  width: 100%; border: 1px solid #e0e0e0; border-radius: 6px;
  padding: 10px; font-size: 13px;
  font-family: 'Segoe UI', Arial, sans-serif;
  color: #444; resize: vertical; box-sizing: border-box;
  outline: none; min-height: 80px;
}

.notes-content textarea:focus { border-color: #D95F02; }

/* ── Handlungsbedarf (needs-action) ──────────────────────────────────────────
   Orange left-edge marker on a flagged row + the reasons panel (a second
   collapsible section inside the shared notes-row). */
#membersTable tr.flagged td:first-child { box-shadow: inset 3px 0 0 #E8662A; }

.hb-content { display: none; padding: 12px 16px 14px; border-top: 1px solid #F0E6DD; }
.hb-content.active { display: block; }
.hb-head { font-size: 11px; font-weight: 700; color: #9a9aa6; text-transform: uppercase; letter-spacing: .4px; margin-bottom: 9px; }
.hb-reason { display: flex; align-items: center; gap: 10px; background: #fff; border: 1px solid #ececf1; border-radius: 9px; padding: 8px 11px; margin-bottom: 8px; }
.hb-reason .hb-ri { width: 15px; height: 15px; flex: none; color: #E8662A; }
.hb-rt { font-size: 13.5px; color: #333; flex: 1; }
.hb-tag { font-size: 10px; font-weight: 700; padding: 2px 7px; border-radius: 5px; }
.hb-tag-s { background: #eef2fb; color: #3a5ba0; }
.hb-tag-m { background: #f0eef9; color: #6b4ea0; }
.hb-clear { border: 1px solid #cfe0cf; background: #fff; color: #2e7d32; border-radius: 7px; padding: 5px 10px; font-size: 12px; font-weight: 700; cursor: pointer; font-family: inherit; display: inline-flex; align-items: center; gap: 5px; }
.hb-clear svg { width: 12px; height: 12px; }
.hb-clear.hb-rm { border-color: #e6cccc; color: #b13b3b; }
.hb-none { font-size: 13px; color: #b4b4be; font-style: italic; margin-bottom: 9px; }
.hb-add { display: flex; gap: 8px; margin-top: 4px; }
.hb-add input { flex: 1; border: 1px solid #dcdce3; border-radius: 7px; padding: 7px 11px; font-size: 13px; font-family: inherit; outline: none; }
.hb-add input:focus { border-color: #D95F02; }
.hb-add button { background: #1A1A2E; color: #fff; border: none; border-radius: 7px; padding: 7px 13px; font-size: 13px; font-weight: 700; cursor: pointer; font-family: inherit; }

/* Inline fee-edit row — the record-payment form is moved into this row, right
   below the fee being edited. Inside the table "card" (white, rounded, clipped)
   the form drops its own panel chrome (grey box, rounded corners, margin) and
   renders as a clean edge-to-edge inset, matching the comment/notes row. */
#feesTable tr.fee-edit-row > td { padding: 0; border: none; }
#feesTable tr.fee-edit-row .pp-fee-form {
  margin: 0; border: none; border-radius: 0;
  border-top: 1px solid #F0F0F0; background: #FFFAF7;
}

/* .btn-add lives with the other text buttons further down, so every variant
   shares one geometry. */

.btn-edit, .btn-notes, .btn-delete, .btn-fee, .btn-hb, .btn-info {
  width: 30px; height: 30px; padding: 0;
  display: inline-flex; align-items: center; justify-content: center;
  border-radius: 6px; cursor: pointer; border: 1px solid #e0e0e0;
  background: transparent; margin-right: 2px; transition: all 0.15s;
  /* Force border-box so <a class='btn-edit'> renders at the exact same
     30x30 outer size as <button class='btn-edit'>. Without this, <a>
     defaults to content-box and ends up 32x32, while buttons default to
     border-box and stay at 30x30. */
  box-sizing: border-box;
}
.btn-edit   { color: #D95F02; border-color: #D95F02; }
.btn-fee    { color: #2E7D32; border-color: #2E7D32; }
.btn-notes  { color: #888;    border-color: #e0e0e0; }
.btn-hb     { color: #888;    border-color: #e0e0e0; }
/* The (i) disclosure button. It joins the family above rather than carrying its
   own padding/font-size/min-height/display, which is what CLAUDE.md forbids on a
   button, and that is also why it lands at exactly the same 30x30 as the pencil
   it sits beside in a card head.
   The border is transparent rather than removed: an (i) is a passive hint, not an
   action, so a visible frame around it only adds chrome to every card head. Keeping
   the 1px transparent border (instead of `border: none`) leaves the family's box
   model untouched, so the icon stays optically centred in the same 30x30 as the
   bordered siblings it sits beside. */
.btn-info   { color: #888;    border-color: transparent; }
.btn-delete { color: #B34D00; border-color: #B34D00; margin-right: 0; }
.btn-edit:hover   { background: #D95F02; color: white; }
.btn-fee:hover    { background: #2E7D32; color: white; }
.btn-notes:hover  { border-color: #D95F02; color: #D95F02; }
.btn-hb:hover     { border-color: #E8662A; color: #E8662A; }
/* Colour alone carries the hover, since there is no border left to light up. */
.btn-info:hover   { color: #D95F02; }
/* Filled while its popover is open, so it is obvious which (i) is talking. The
   background paints under the transparent border too, so the square stays solid. */
.btn-info[aria-expanded="true"] { background: #1A1A2E; color: #fff; }
/* Flagged: a member with ≥1 Handlungsbedarf reason → solid orange "!" icon. */
.btn-hb.flagged          { color: #fff; background: #E8662A; border-color: #E8662A; }
.btn-hb.flagged:hover    { background: #d2551f; border-color: #d2551f; }
.btn-delete:hover { background: #B34D00; color: white; }
.btn-edit svg, .btn-notes svg, .btn-delete svg, .btn-fee svg, .btn-hb svg { width: 14px; height: 14px; }
.btn-info svg { width: 15px; height: 15px; }

/* ── The (i) disclosure popover ───────────────────────────────────────────────
   One singleton on <body>, driven by any [data-info] trigger (js/info-pop.js).
   The text lives in js/help-content.js keyed by card id, NOT inline in markup:
   half the cards are rendered from JS, and the Hilfe search plus the
   Dokumenten-Assistent need the same strings.

   Deliberately NOT .note-tooltip (further down this file). That one is
   hover-driven, which does not exist on touch, and position:absolute at
   z-index 250, so any ancestor with overflow:hidden clips it. This is
   position:fixed at 1100: above the 1000 .modal-overlay tier so an (i) works
   inside a dialog, below the 9998+ toast/spinner tier, and unclippable by
   construction. */
.info-pop {
  position: fixed; z-index: 1100; display: none;
  width: 340px; max-width: calc(100vw - 32px);
  background: #fff; border: 1px solid #d5d7e0; border-radius: 10px;
  box-shadow: 0 10px 30px rgba(26,26,46,.16);
  padding: 14px 16px; color: #3A4150;
  font-size: 13px; line-height: 1.62;
  user-select: text;                 /* the text is meant to be copyable */
}
.info-pop.active { display: block; }
.info-pop h4 { margin: 0 0 7px; font-size: 12.5px; font-weight: 700; color: #1A1A2E; }
.info-pop p { margin: 0 0 9px; }
.info-pop p:last-child { margin-bottom: 0; }
.info-pop ul { margin: 0 0 9px; padding-left: 17px; }
.info-pop ul:last-child { margin-bottom: 0; }
.info-pop li { margin-bottom: 5px; }
.info-pop li:last-child { margin-bottom: 0; }
.info-pop strong { color: #1A1A2E; }
.info-pop em { font-style: normal; color: #1A1A2E; font-weight: 600; }
.info-pop code {
  background: #EEF0F5; border-radius: 4px; padding: 1px 5px;
  font-family: monospace; font-size: 12px; color: #1A1A2E;
}
/* An outbound link inside a popover (Google Cloud Console, AI Studio). It keeps
   the underline a plain <a> has, so it never reads as the section pointer below,
   which is deliberately underline-free until hover. */
.info-pop a { color: #D95F02; font-weight: 600; }
/* A pointer to the section that OWNS a setting, reusing the existing
   data-goto-section convention instead of growing a second copy of the control. */
.info-pop .info-pop-goto {
  display: inline-block; margin-top: 2px; color: #D95F02;
  text-decoration: none; font-weight: 600; font-size: 12.5px; cursor: pointer;
}
.info-pop .info-pop-goto:hover { text-decoration: underline; }
.info-pop-close { display: none; }          /* mobile only, see mobile.css */
.info-pop-backdrop {
  position: fixed; inset: 0; z-index: 1099; display: none;
  background: rgba(26,26,46,.34);
}
.info-pop-backdrop.active { display: block; }

/* An (i) beside a heading, a field label or a modal title, where there is no
   icon-button row to join. */
.info-row { display: flex; align-items: center; gap: 9px; }
.info-row > h1, .info-row > h2, .info-row > h3, .info-row > h4, .info-row > label { margin: 0; }
/* A centred container (.modal-box) turns the flex row into a left-aligned block,
   so the modifier restores what text-align used to do for the bare heading. */
.info-row--center { justify-content: center; }
/* On an 11px uppercase field label a full 30x30 square shouts. The BOX is
   scaled rather than the button, so the button keeps its family geometry and no
   local padding/font-size override is introduced. */
.info-row--label .btn-info { transform: scale(.73); transform-origin: left center; margin: 0 -4px; }

.form-section {
  margin-top: 32px; background: white;
  padding: 24px; border-radius: 10px;
  box-shadow: 0 2px 8px rgba(0,0,0,0.07);
}
.form-section h3 { margin-top: 0; color: #D95F02; }

.form-row { display: flex; gap: 12px; flex-wrap: wrap; margin-bottom: 12px; align-items: flex-start; }

.form-row input, .form-row select {
  flex: 1; padding: 10px 12px; border: 1px solid #ccc;
  border-radius: 6px; font-size: 14px; outline: none; box-sizing: border-box;
}

.form-field {
  display: flex; flex-direction: column; gap: 4px; flex: 1;
}
.form-field input, .form-field select, .form-field textarea {
  flex: none; width: 100%; box-sizing: border-box;
}
.form-label {
  font-size: 11px; color: #aaa; text-transform: uppercase; letter-spacing: 0.5px;
}

.modal-overlay {
  display: none; position: fixed;
  top: 0; left: 0; width: 100%; height: 100%;
  background: rgba(0,0,0,0.4); z-index: 1000;
  justify-content: center; align-items: center;
}
.modal-overlay.active { display: flex; }

.modal-box {
  background: white; border-radius: 12px; padding: 32px;
  max-width: 380px; width: 90%;
  box-shadow: 0 8px 32px rgba(0,0,0,0.2); text-align: center;
}
.modal-box h3 { color: #1A1A2E; margin-bottom: 8px; }
.modal-box p  { color: #888; font-size: 14px; margin-bottom: 24px; }
/* A modal title that carries an (i) shares its line with the button, so its own
   bottom margin has to move up to the row. Both rules that set that margin
   (.modal-box h3 above, .bulk-fee-box h3 further down) come AFTER the generic
   .info-row reset and would otherwise win and push the button off the baseline. */
.modal-box .info-row { margin-bottom: 8px; }
.modal-box .info-row > h3 { margin: 0; }

.modal-actions { display: flex; gap: 12px; justify-content: center; }

/* ── Text buttons: one geometry, colour carries the emphasis ────────────────
   Every text button in the app shares height, radius, font and transition, so
   any two placed side by side line up. Two things used to break that and BOTH
   have to stay fixed:

     1. The classes carried different metrics. `.btn-cancel`/`.btn-confirm`/
        `.btn-add` were `10px 24px` at `14px`, `.btn-primary`/`.btn-secondary`/
        `.btn-danger` were `8px 20px` at `13px`. An Abbrechen next to a
        Speichern came out 41px vs 35px tall.
     2. The filled variants had `border: none` while the outlined ones had
        `border: 1px solid`. That alone is 2px of height, so equalising the
        padding is not enough. Hence `border: 1px solid transparent` below:
        every variant reserves the same 1px, filled or not.

   Consequence worth knowing before editing: a per-variant `padding` or
   `font-size` override reintroduces the bug. Use .btn-sm/.btn-lg instead, and
   never an inline style. */
.btn-primary,
.btn-secondary,
.btn-cancel,
.btn-quiet,
.btn-confirm,
.btn-add,
.btn-danger,
.btn-danger-outline,
.btn-inset {
  display: inline-flex; align-items: center; justify-content: center; gap: 7px;
  box-sizing: border-box;
  min-height: 36px;
  padding: 8px 18px;
  font-family: inherit; font-size: 13px; font-weight: 600; line-height: 1.4;
  border-radius: 7px;
  border: 1px solid transparent;
  cursor: pointer; white-space: nowrap; text-decoration: none;
  transition: background 0.15s, border-color 0.15s, color 0.15s;
}

/* The one main action of a card or dialog. */
.btn-primary         { background: #1A1A2E; color: #fff; }
.btn-primary:hover:not(:disabled)   { background: #2d2d4e; }

/* A real secondary action: Bearbeiten, Aktualisieren, Testen, Verbinden. */
.btn-secondary       { background: #fff; color: #1A1A2E; border-color: #1A1A2E; }
.btn-secondary:hover:not(:disabled) { background: #f0f0f5; }

/* The low-emphasis neutral look, under two names because the JOB differs even
   though the appearance must not:
     .btn-cancel — the Abbrechen partner in an edit footer or a dialog. Quieter
       than .btn-secondary on purpose, so Speichern stays the obvious target.
     .btn-quiet  — a small side action in a dense row that should not compete
       for attention: Entfernen next to an uploaded logo, the × on a rate row,
       the ▲▼ reorder chevrons. These DO something, so calling them "cancel"
       would misdescribe them to the next reader; a red or navy button would
       overstate them.
   #6B7280 rather than a lighter grey because at 13px this is normal-size text
   and needs 4.5:1 against white to stay legible. */
.btn-cancel, .btn-quiet             { background: #fff; color: #6B7280; border-color: #d5d7e0; }
.btn-cancel:hover:not(:disabled),
.btn-quiet:hover:not(:disabled)      { background: #f4f5f8; border-color: #b9bcc8; color: #4b5261; }
/* A destructive .btn-quiet (a row delete) turns red only on hover, so the row
   stays calm until the pointer is actually on the button. */
.btn-quiet--danger:hover:not(:disabled) { background: #fdf0ee; border-color: #e0a9a2; color: #c0392b; }

/* Brand accent: creating something new. */
.btn-add             { background: #D95F02; color: #fff; }
.btn-add:hover:not(:disabled)       { background: #B34D00; }

/* Confirming inside a modal. Deliberately the darker burnt orange, so a
   confirmation reads heavier than an everyday "add". */
.btn-confirm         { background: #B34D00; color: #fff; }
.btn-confirm:hover:not(:disabled)   { background: #8c3c00; }

/* Filled red only where there is no undo, and only inside a confirmation. */
.btn-danger          { background: #c0392b; color: #fff; }
.btn-danger:hover:not(:disabled)    { background: #a93226; }

/* Outline variant for low-emphasis destructive actions (e.g. Löschen in the
   Email Vorlagen/Automatisierungen lists) — reddish border, not a filled red. */
.btn-danger-outline       { background: #fff; color: #c0392b; border-color: #e0a9a2; }
.btn-danger-outline:hover:not(:disabled) { background: #fdf0ee; border-color: #c0392b; }

/* Disabled reads identically on every variant, so a blocked action never looks
   like a different kind of button.
   Deliberately NO pointer-events:none here. The `disabled` attribute already
   blocks activation, while pointer-events:none also stops the element being a
   hit-test target, which suppresses its `title` tooltip. Several blocked buttons
   carry their reason ONLY in that title ("Wird noch verwendet. Zuerst Mitglieder
   umtragen."), so hiding it removes the explanation exactly when it is needed. */
.btn-primary:disabled, .btn-secondary:disabled, .btn-cancel:disabled,
.btn-confirm:disabled, .btn-add:disabled, .btn-danger:disabled,
.btn-danger-outline:disabled, .btn-add-small:disabled, .btn-quiet:disabled {
  opacity: 0.45; cursor: not-allowed;
}
/* Looks unavailable but stays CLICKABLE on purpose, so the click can explain
   itself. Used where the reason is a sentence the handler already renders beside
   the row: a membership type still in use, the last remaining Beitragssatz. A
   real `disabled` attribute swallows that click and leaves only the `title`,
   which does not exist on a touch device, and mobile.css deliberately sizes
   these icon buttons up for tapping. */
.btn-blocked { opacity: 0.45; cursor: not-allowed; }

/* .is-disabled is for an <a>, where there is no `disabled` attribute to honour,
   so here the pointer-events block is what actually prevents navigation. It
   covers the whole family, not just two variants, so a future
   .btn-add.is-disabled cannot silently stay clickable. */
.btn-primary.is-disabled, .btn-secondary.is-disabled, .btn-cancel.is-disabled,
.btn-confirm.is-disabled, .btn-add.is-disabled, .btn-danger.is-disabled,
.btn-danger-outline.is-disabled, .btn-add-small.is-disabled, .btn-quiet.is-disabled {
  opacity: 0.45; cursor: not-allowed; pointer-events: none;
}

/* Two size steps. These exist so no caller ever needs an inline padding or
   font-size, which is what fragmented the sizes in the first place.
   .btn-sm — dense rows: list-card action rows, table cells, inline pickers.
   .btn-lg — a single standalone main action with room around it. */
.btn-sm { min-height: 30px; padding: 5px 12px; font-size: 12px; border-radius: 6px; gap: 6px; }
.btn-lg { min-height: 42px; padding: 11px 24px; font-size: 14px; border-radius: 8px; }

/* Square, label-less member of the same family (a × or a ▲ in a row). */
.btn-icon { width: 36px; padding: 0; }
.btn-icon.btn-sm { width: 30px; }

/* An affordance that lives INSIDE a field rather than beside it: the calendar in a
   date field. Square, borderless and transparent on purpose, so it reads as part of
   the control instead of as a second button competing with it.
   It is a STEP IN THE FAMILY and not a local exception, because the alternative was
   a date-specific rule putting `padding` and `display` on a `<button>` (which the
   geometry rule above forbids) repeated at every date field in the app. Position is
   the field wrapper's job, never the button's. */
.btn-inset { width: 28px; min-height: 28px; padding: 0; border: 0; background: none; color: #888; border-radius: 6px; }
.btn-inset:hover:not(:disabled) { background: #f0f0f5; color: #D95F02; }
.btn-inset > svg { width: 15px; height: 15px; flex: 0 0 auto; }

/* Leading/trailing icons scale with the button, never with the SVG's own attrs. */
.btn-primary > svg, .btn-secondary > svg, .btn-cancel > svg, .btn-quiet > svg,
.btn-confirm > svg, .btn-add > svg,
.btn-danger > svg, .btn-danger-outline > svg { width: 15px; height: 15px; flex: 0 0 auto; }
.btn-sm > svg { width: 13px; height: 13px; }

/* An action row. One gap value app-wide; --end right-aligns (edit footers),
   --split pushes everything after .btn-row-spacer to the right. */
.btn-row { display: flex; align-items: center; gap: 8px; flex-wrap: wrap; }
.btn-row--end { justify-content: flex-end; }
.btn-row--split > .btn-row-spacer { margin-right: auto; }

/* File pickers are <label>s, not <button>s, but must read as the same control.
   One class, because the same affordance rendered from four inline recipes
   drifts into different looks. */
.btn-file {
  display: inline-flex; align-items: center; justify-content: center; gap: 7px;
  box-sizing: border-box; min-height: 36px; padding: 8px 18px;
  font-family: inherit; font-size: 13px; font-weight: 600; line-height: 1.4;
  border-radius: 7px; border: 1px dashed #ccc; background: #F5F7FA; color: #4b5261;
  cursor: pointer; white-space: nowrap;
  transition: background 0.15s, border-color 0.15s, color 0.15s;
}
.btn-file:hover { background: #eef1f6; border-color: #D95F02; color: #D95F02; }
.btn-file input[type="file"] { display: none; }

/* ── Datumsfeld (.dfield) ─────────────────────────────
   A German-format text input with the system calendar one click behind it. Lives
   here rather than in a screen's section because every date field in the app uses
   it. The markup and the wiring are in frontend/js/date-field.js.

   The wrapper positions both the button and the picker, so neither carries a
   position of its own. */
.dfield { position: relative; display: inline-block; }

/* Room for the inset button. Matched on the CLASS, not on `input[type="text"]`:
   the predecessor matched the type, so the 36px gutter would have vanished the
   moment a field was rendered as anything else and the icon would paint over the
   text.
   ⚠ And matched with the element type too, for specificity (0,2,1) rather than
   (0,2,0). This gutter is STRUCTURAL, not decoration: any container rule that sets
   the `padding` SHORTHAND silently resets padding-right and the calendar icon then
   paints on top of the typed date. `.pf-interrupt-add .dfield-text` does exactly
   that at equal specificity and later in this file, and it did break it. */
.dfield > input.dfield-text { padding-right: 34px; }
.dfield > .dfield-btn { position: absolute; top: 50%; right: 4px; transform: translateY(-50%); }
/* A locked field shows no calendar. The admin cards add and remove `readonly` at
   runtime, so this follows the attribute rather than being decided when the field is
   built. The click handler refuses the same case, so this is the appearance half. */
.dfield:has(> input.dfield-text[readonly]) > .dfield-btn { display: none; }

/* The native picker: present only for its popup, never seen, never focusable.
   Its absolute right/bottom is what anchors Chrome's calendar under the button.

   ⚠ SPECIFICITY IS LOAD-BEARING HERE, and the predecessor got it wrong. A single
   class (0,1,0) loses to every container rule that styles bare inputs, and there
   are many: `.bl-field input`, `.form-field input`, `.pp-fee-form input`,
   `.fq-field input`, `.ctrl-pop-dates input`, and `.pf-input` plus friends in
   mobile.css. So `padding: 0`, `border: 0` and `min-width: 0` were all being
   overridden, and the supposedly 1×1 element was really 190px wide on the desktop
   and a full-width 44px-tall box on a phone, hanging out of its own wrapper. Two
   classes plus the element type (0,2,1) win against all of them regardless of
   source order, which matters because mobile.css loads last. */
.dfield > input.dfield-picker {
  position: absolute; right: 26px; bottom: 0;
  width: 1px; height: 1px; min-width: 0; min-height: 0;
  padding: 0; margin: 0; border: 0;
  opacity: 0; pointer-events: none;
}

/* ── Audit log table ── */
/* Audit log — card list. The accent colour comes from --cat-color, set per
   card in admin.js (CATEGORY_META). Both the left edge and the badge tint
   derive from that single value, so the palette can't drift out of sync. */
.audit-list { display: flex; flex-direction: column; gap: 8px; }
.audit-card {
  display: flex; align-items: center; gap: 12px;
  background: #fff; border: 1px solid #ececf0;
  border-left: 4px solid var(--cat-color, #6b7280);
  border-radius: 10px; padding: 10px 14px; font-size: 13px;
}
.audit-card-action {
  flex: 0 0 auto; font-weight: 600; font-size: 12px;
  padding: 3px 11px; border-radius: 20px; white-space: nowrap;
  color: var(--cat-color, #6b7280);
  background: color-mix(in srgb, var(--cat-color, #6b7280) 13%, #fff);
}
.audit-card-entity {
  flex: 1 1 auto; min-width: 0; color: #333;
  overflow: hidden; text-overflow: ellipsis; white-space: nowrap;
}
.audit-card-meta {
  flex: 0 0 auto; display: flex; flex-direction: column;
  align-items: flex-end; gap: 1px; text-align: right;
}
.audit-card-user { color: #555; font-weight: 500; }
.audit-card-time { color: #aaa; font-size: 12px; white-space: nowrap; }

/* ── GDPR dropdown ── */
.gdpr-dropdown { position: relative; display: inline-block; }

.gdpr-dropdown-toggle {
  display: inline-flex; align-items: center; gap: 6px;
}

.gdpr-dropdown-menu {
  display: none;
  position: absolute; top: calc(100% + 6px); right: 0;
  background: white; border: 1px solid #ddd; border-radius: 8px;
  box-shadow: 0 4px 18px rgba(0,0,0,0.13);
  min-width: 230px; z-index: 300; overflow: hidden;
  padding: 4px 0;
}
.gdpr-dropdown-menu.open { display: block; }

.gdpr-dropdown-item {
  display: flex; align-items: center; gap: 10px;
  width: 100%; padding: 10px 16px;
  font-size: 13px; color: #1A1A2E;
  text-decoration: none; border: none; background: transparent;
  cursor: pointer; text-align: left; box-sizing: border-box;
  transition: background 0.1s;
}
.gdpr-dropdown-item:hover { background: #f5f7fa; }
.gdpr-dropdown-item--danger { color: #c0392b; }
.gdpr-dropdown-item--danger:hover { background: #fdf0ee; color: #a93226; }

.gdpr-dropdown-divider { height: 1px; background: #eee; margin: 4px 0; }

/* ── Back button ── */
.btn-back {
  display: inline-flex; align-items: center; gap: 6px;
  background: #fff; color: #1A1A2E; border: 1px solid #e2e2e8;
  border-radius: 8px; font-size: 13px; font-weight: 600;
  cursor: pointer; padding: 7px 14px; transition: all 0.13s ease;
}
.btn-back:hover { border-color: #D95F02; color: #D95F02; }

/* ── Profile Page ── */
.pp-header {
  display: flex; align-items: center; gap: 20px;
  margin-bottom: 32px; flex-wrap: wrap;
}
.pp-identity { flex: 1; }
.pp-identity h1 { margin: 0 0 10px 0; color: #1A1A2E; }
.pp-badges { display: flex; gap: 8px; align-items: center; flex-wrap: wrap; }

/* Name + status on same line */
.pp-name-row {
  display: flex; align-items: center; gap: 12px; margin-bottom: 6px;
}
.pp-name-row h1 { margin: 0; }

.pp-membership-label {
  font-size: 15px; font-weight: 600; color: #555;
}

/* Sortable table headers */
th.sortable { cursor: pointer; user-select: none; }
th.sortable:hover { background: #bf5300; }
.sort-arrow { font-size: 11px; margin-left: 4px; opacity: 0.45; }
th.sort-asc  .sort-arrow,
th.sort-desc .sort-arrow { opacity: 1; }
.pp-status-badge {
  display: inline-block; padding: 3px 11px; border-radius: 20px;
  font-size: 11px; font-weight: 700; text-transform: uppercase; letter-spacing: 0.5px;
  background: #F5F5F5; color: #555;
}
.pp-actions { display: flex; gap: 8px; align-items: center; }
/* Unified Actions dropdown toggle (kebab + label), used on the profile header. */
.pp-actions-toggle { display: inline-flex; align-items: center; gap: 7px; }
.pp-actions-toggle svg { flex-shrink: 0; }
.pp-actions-menu { min-width: 232px; }
.pp-actions-menu .gdpr-dropdown-item svg { width: 15px; height: 15px; flex-shrink: 0; }
/* GDPR group visibility (admin/manager only) — toggled by class. */
#ppGdprGroup.pp-gdpr-hidden { display: none; }
/* The "DSGVO" sub-dropdown toggle is desktop-only; on mobile the three GDPR
   items sit flat in the ⋮ Actions kebab (see the ≥641px block in mobile.css). */
.pp-gdpr-toggle { display: none; }

.pp-grid {
  display: grid; grid-template-columns: 1fr 1fr; gap: 20px;
}
.pp-card {
  background: #fff; border: 1px solid #e0e0e0;
  border-radius: 12px; padding: 24px 28px;
}
.pp-card-full { grid-column: 1 / -1; }
.pp-card-title {
  font-size: 11px; font-weight: 700; text-transform: uppercase;
  letter-spacing: 1px; color: #888; margin-bottom: 16px;
  display: flex; align-items: center; gap: 8px;
}
.pp-card-title > svg { width: 15px; height: 15px; flex: none; color: #E8662A; }
.pp-card-title + .pp-card-title { margin-top: 24px; }

/* Each label+value row inside a card */
.pf-row {
  display: flex; align-items: baseline; gap: 12px;
  padding: 10px 0; border-bottom: 1px solid #f5f5f5;
}
.pf-row:last-child { border-bottom: none; }
.pf-label {
  font-size: 13px; color: #888; min-width: 130px; flex-shrink: 0;
}
.pf-value {
  font-size: 14px; color: #1A1A2E; font-weight: 500; flex: 1;
}
.pf-value.empty { color: #ccc; font-style: italic; font-weight: 400; }

/* Inputs hidden in read mode, shown in edit mode */
.pf-input {
  display: none; flex: 1; font-size: 14px; padding: 6px 10px;
  border: 1px solid #ddd; border-radius: 6px;
  font-family: inherit; color: #1A1A2E; background: #fff;
  box-sizing: border-box; width: 100%;
}
.pf-input:focus { outline: none; border-color: #D95F02; }

/* A date field standing in a .pf-row.
   ⚠ .pf-input is TWO things at once: the show/hide switch for edit mode AND the box
   styling of the control. A wrapper carrying it would therefore paint a second border
   around the field it contains, so the two jobs are split here: the WRAPPER takes the
   row's slot and the visibility, the text input inside keeps .pf-input for the box and
   for mobile.css's 44px touch target. */
.dfield.pf-input-wrap { display: none; flex: 1; }
#page-profile.edit-mode .dfield.pf-input-wrap,
#addMemberForm .dfield.pf-input-wrap { display: block; }

#page-profile.edit-mode .pf-value { display: none; }
#page-profile.edit-mode .pf-input { display: block; }
/* Required-field stars sit in the (shared) row label; show them only while editing,
   not in the read-only profile view. */
#page-profile:not(.edit-mode) .pf-label .req-star { display: none; }
/* Add-member form reuses the profile's pf-row layout but is always in "edit" state. */
#addMemberForm .pf-input { display: block; }

/* Mitgliedsnotizen: read-only text block in read mode, textarea in edit mode. */
.pp-notes-read { font-size: 14px; color: #1A1A2E; white-space: pre-wrap; line-height: 1.5; min-height: 1.2em; }
.pp-notes-read.empty { color: #ccc; font-style: italic; }
.pp-edit-only { display: none; }
#page-profile.edit-mode .pp-edit-only { display: block; }
#page-profile.edit-mode .pp-notes-read { display: none; }

/* Auszeiten (interruptions) editor — shown only in edit mode, like .pf-input. */
.pf-interrupt-editor { display: none; flex: 1; }
#page-profile.edit-mode .pf-interrupt-editor { display: block; }
.pf-interrupt-item {
  display: flex; align-items: center; gap: 8px;
  font-size: 14px; color: #1A1A2E; padding: 3px 0;
}
.pf-interrupt-item button {
  border: none; background: none; color: #c0392b;
  cursor: pointer; font-size: 18px; line-height: 1; padding: 0 4px;
}
.pf-interrupt-add { display: flex; align-items: center; gap: 8px; margin-top: 8px; flex-wrap: wrap; }
/* ⚠ Matched on the CLASS since the Auszeit fields became text inputs with a calendar
   behind them. This was the ONLY styling those two ever had, and it was keyed on
   `input[type="date"]`, so the conversion would have dropped all six properties and
   left two unstyled boxes in the middle of the profile. */
.pf-interrupt-add .dfield-text {
  font-size: 14px; padding: 5px 8px; border: 1px solid #ddd; border-radius: 6px;
  font-family: inherit; color: #1A1A2E; background: #fff;
}

/* .pf-always-input lived here until 2026-08-02: an "always editable in both modes"
   input for skills, languages and notes. Nothing emits the class any more:
   Fähigkeiten and Sprachen are plain .pf-input in both the add-member form and the
   profile, and the notes field has .pp-notes-textarea just below. So the rule, its
   :hover, its :focus and its touch-target entry in mobile.css all matched nothing. */

.pp-notes-textarea {
  width: 100%; min-height: 120px; font-size: 14px;
  padding: 12px; border: 1px solid #eee; border-radius: 8px;
  font-family: inherit; color: #1A1A2E; resize: vertical;
  box-sizing: border-box; background: #fafafa;
}
.pp-notes-textarea:hover  { border-color: #ddd; }
.pp-notes-textarea:focus  { outline: none; border-color: #D95F02; background: #fff; }

.event-card {
  background: white; border-radius: 10px;
  padding: 16px 20px; margin-bottom: 12px;
  box-shadow: 0 2px 8px rgba(0,0,0,0.07);
  display: flex; align-items: center; gap: 16px;
}

/* Date-box colour is the event type's colour (--ev-color, set per card) */
.event-date-box {
  background: var(--ev-color, #64748b); color: white;
  border-radius: 8px; padding: 8px 12px;
  text-align: center; min-width: 52px; flex-shrink: 0;
}

.event-date-box .day   { font-size: 22px; font-weight: bold; line-height: 1; }
.event-date-box .month { font-size: 11px; text-transform: uppercase; letter-spacing: 0.5px; }

.event-info  { flex: 1; }
.event-title { font-weight: 600; color: #1A1A2E; font-size: 15px; }
.event-meta  { font-size: 12px; color: #aaa; margin-top: 2px; }
.event-link  { display: inline-block; margin-top: 5px; font-size: 12px; font-weight: 600; color: #2563eb; text-decoration: none; }
.event-link:hover { text-decoration: underline; }
/* Small (G) marker before Google-synced event titles */
.event-g {
  display: inline-flex; align-items: center; justify-content: center;
  width: 16px; height: 16px; border-radius: 50%;
  background: #4285F4; color: #fff; font-size: 10px; font-weight: 700;
  vertical-align: middle; position: relative; top: -1px; margin-right: 3px;
}

.event-card.past .event-date-box { background: #aaa; }
.event-card.past { opacity: 0.6; }

/* Note → tap-to-reveal panel (hidden until the card is tapped), mirroring the
   transaction cards. Only cards with a note get the pointer cursor. */
.event-card.has-note { cursor: pointer; }
.event-note { display: none; margin-top: 6px; font-size: 13px; color: #555; line-height: 1.5; white-space: pre-wrap; }
.event-card.note-open .event-note { display: block; }

/* In-card edit: the card hosts the relocated shared form. Stack vertically,
   keep just the title visible, and strip the form-section's own card chrome
   (it's already sitting inside a card). */
.event-card.editing { flex-direction: column; align-items: stretch; gap: 12px; cursor: default; }
.event-card.editing > .event-date-box,
.event-card.editing > span,                 /* the edit/delete action wrapper */
.event-card.editing .event-meta,
.event-card.editing .event-link,
.event-card.editing .event-note { display: none; }
.event-card.editing .form-section {
  margin: 0; padding: 0; background: transparent; box-shadow: none;
}

.help-section {
  background: white; border-radius: 10px; padding: 24px;
  box-shadow: 0 2px 8px rgba(0,0,0,0.07); margin-bottom: 20px;
}
.help-section h3 { color: #D95F02; margin-top: 0; }
.help-section p, .help-section li { color: #555; font-size: 14px; line-height: 1.7; }
.help-section ul { padding-left: 20px; }
/* Sub-headings inside a Hilfe section. They exist so a section reads as groups
   ("Was automatisch passiert", "Regeln", "Wenn es nicht klappt") instead of one
   long essay. Added as a RULE rather than left to inline styles: the three <h4>s
   that predated the rewrite each carried their own, which is exactly the local
   override the button rule warns about, only in prose. */
.help-section h4 {
  font-size: 12px; font-weight: 700; text-transform: uppercase; letter-spacing: .5px;
  color: #1A1A2E; margin: 26px 0 8px;
}
.help-section h4:first-of-type { margin-top: 18px; }
/* A table inside a Hilfe section. Reason/effect pairs (Handlungsbedarf, Lauf-Status,
   Kategorie-Reihenfolge) read as a grid and turn into an unreadable comma chain as
   prose. Deliberately NOT the app's .data-table: that one is a dark-header data grid
   with row hover, and this is quiet reference text.

   Everything up to `table-layout` exists to UNDO the bare-element rules at the top of
   this file (`table`, `th`, `td`, `tr:hover td`). Those are element selectors, so a
   property this block does not name keeps the data-grid value: leaving the th
   background out once was enough to render the whole Hilfe page with navy header rows,
   and `table-layout: fixed` gives a 4-column reference table four equal columns
   regardless of how much text each holds. */
.help-table {
  width: 100%; border-collapse: collapse; margin: 4px 0 14px; font-size: 13.5px;
  background: transparent; box-shadow: none; border-radius: 0;
  table-layout: auto; overflow: visible;
  /* Wide rows must scroll inside their own container, never the page. */
  display: table;
}
.help-table th {
  background: transparent;
  text-align: left; font-size: 11px; font-weight: 700; text-transform: uppercase;
  letter-spacing: .04em; color: #9a9aa4; padding: 0 12px 7px 0;
  border-bottom: 1px solid #e6e6ec; white-space: nowrap;
}
.help-table td {
  color: #555; font-size: 13.5px; line-height: 1.6; padding: 8px 12px 8px 0;
  border-bottom: 1px solid #f2f2f5; vertical-align: top;
}
.help-table tr:hover td { background: transparent; }
.help-table tr:last-child td { border-bottom: none; }
.help-table td:first-child { color: #1A1A2E; font-weight: 600; }
.help-table strong { color: #1A1A2E; }
/* ── Hilfe-Suche ────────────────────────────────────────────────────────────
   The row lives in .admin-content, never in the sidebar strip: mobile.css
   hardcodes #page-help { --subtab-h: 47px } and positions the askDSI messenger
   off it, so a row in the strip breaks that offset invisibly and only on
   phones. Inside .admin-content it just flows above the sections. */
.help-search { position: relative; margin-bottom: 18px; }
/* The Dokumenten-Assistent owns the screen while it is the active section, so
   the row steps aside at EVERY width. One rule, two reasons: on a phone the
   messenger is position:fixed over the whole content area and the row would sit
   underneath it, invisible but still focusable; on the desktop the row is 58px
   of the height that made the PAGE scroll instead of the chat feed. It comes
   back on the other sixteen sections, where it is in normal flow. `.help-ai-open`
   is set by initSidebarNav's activate() in utils.js, the same call that toggles
   `.active` on the panel, so it cannot be out of sync with the panel it dodges. */
#page-help.help-ai-open .help-search { display: none; }
.help-search-field { position: relative; display: block; }
.help-search-field > svg {
  position: absolute; left: 12px; top: 50%; transform: translateY(-50%);
  width: 15px; height: 15px; color: #9AA1AE; pointer-events: none;
}
.help-search-input {
  width: 100%; box-sizing: border-box; padding: 10px 78px 10px 36px;
  border: 1px solid #d5d7e0; border-radius: 9px;
  font: inherit; font-size: 13.5px; color: #1A1A2E; background: #fff;
}
.help-search-input:focus { outline: none; border-color: #D95F02; box-shadow: 0 0 0 3px rgba(217,96,2,.12); }
.help-search-input::placeholder { color: #9AA1AE; }
.help-search-kbd {
  position: absolute; right: 10px; top: 50%; transform: translateY(-50%);
  font-size: 10.5px; color: #9AA1AE; border: 1px solid #E6E7EF;
  background: #F7F8FA; border-radius: 5px; padding: 2px 6px; pointer-events: none;
}
.help-search-input:not(:placeholder-shown) ~ .help-search-kbd { display: none; }

.help-results {
  display: none; margin-top: 8px; background: #fff;
  border: 1px solid #E6E7EF; border-radius: 10px; overflow: hidden;
  box-shadow: 0 6px 20px rgba(26,26,46,.08);
}
.help-results.active { display: block; }
.help-result {
  display: block; width: 100%; text-align: left; border: 0; background: none;
  font: inherit; cursor: pointer; padding: 11px 15px; border-bottom: 1px solid #F0F1F5;
}
.help-result:last-child { border-bottom: 0; }
.help-result:hover, .help-result.sel { background: #F7F8FA; }
/* display:block matters: these are <span>s inside the result <button>, so
   without it the section label runs straight into the snippet
   ("EUER . REGELNDie EUER rechnet …"). */
.help-result-sec {
  display: block;
  font-size: 10.5px; text-transform: uppercase; letter-spacing: .07em;
  color: #9AA1AE; font-weight: 700; margin-bottom: 3px;
}
.help-result-txt { display: block; font-size: 13px; color: #3A4150; line-height: 1.5; }
.help-result-txt mark { background: #FFE9C7; color: #1A1A2E; border-radius: 2px; padding: 0 1px; }
.help-result-src {
  display: inline-block; margin-left: 7px; font-size: 9.5px; font-weight: 700;
  color: #6B7280; background: #EEF0F5; border-radius: 8px; padding: 1px 6px;
  letter-spacing: .03em; text-transform: uppercase;
}
.help-noresult { padding: 15px; font-size: 13px; color: #6B7280; line-height: 1.65; }
.help-noresult b { color: #1A1A2E; }

/* Activating the section is not the same as showing WHERE in it the hit was. */
@keyframes help-flash {
  0%, 100% { background: transparent; box-shadow: none; }
  14%      { background: #FFF6E6; box-shadow: 0 0 0 6px #FFF6E6; }
}
.help-hit { animation: help-flash 1.4s ease-out 1; border-radius: 3px; }
/* A hit can be a whole table row. A <tr> in table layout does not reliably
   paint a box-shadow, and its background sits behind the cells, so flash the
   cells instead, without the halo that would overlap between them. */
@keyframes help-flash-cell {
  0%, 100% { background: transparent; }
  14%      { background: #FFF6E6; }
}
.help-table tr.help-hit { animation: none; }
.help-table tr.help-hit td { animation: help-flash-cell 1.4s ease-out 1; }

.help-badge {
  display: inline-block; background: #FFF5F0; color: #D95F02;
  border: 1px solid #D95F02; border-radius: 4px;
  font-size: 11px; font-weight: 700; padding: 2px 7px;
  font-family: monospace; margin: 0 2px;
}
.fee-paid    { color: #2E7D32; font-weight: bold; }
.fee-pending { color: #B45309; font-style: italic; }

/* Fee History (in profile) */
.pp-fee-form {
  background: #fafafa; border: 1px solid #eee; border-radius: 8px;
  padding: 16px; margin-bottom: 16px; display: flex;
  gap: 12px; flex-wrap: wrap; align-items: flex-end;
}
.pp-fee-form .form-field { flex: 1; min-width: 120px; margin: 0; }
.pp-fee-form label { font-size: 12px; font-weight: 600; color: #555;
  display: block; margin-bottom: 4px; }
.pp-fee-form input, .pp-fee-form select {
  width: 100%; padding: 7px 10px; border: 1px solid #ddd;
  border-radius: 6px; font-size: 14px; box-sizing: border-box; outline: none;
}
.pp-fee-form input:focus, .pp-fee-form select:focus { border-color: #D95F02; }
/* Recording a fee uses .btn-add. No separate accent class for it: one lived
   here and drifted out of the family geometry, ending up shorter than the
   Abbrechen beside it. */
/* Small accent-outline "add" button. Same geometry as .btn-sm so it lines up
   with the rest of the family; only the colour differs. */
.btn-add-small {
  display: inline-flex; align-items: center; justify-content: center; gap: 6px;
  box-sizing: border-box; min-height: 30px; padding: 5px 12px;
  font-family: inherit; font-size: 12px; font-weight: 600; line-height: 1.4;
  border-radius: 6px; border: 1px solid #D95F02;
  background: none; color: #D95F02;
  cursor: pointer; white-space: nowrap;
  transition: background 0.15s, color 0.15s;
}
.btn-add-small:hover:not(:disabled) { background: #D95F02; color: white; }
/* Fee quick-row (inline form below a member row) */
.fee-quick-row td { padding: 0; background: #F1FBF3; }
.fee-quick-content { display: none; padding: 10px 16px; border-top: 1px solid #C8E6C9; }
.fee-quick-content.active { display: block; }
/* Donation row (inline donor-info panel below a transaction row).
   Used in two modes: fill-mode (tagging fresh) and edit-mode (already tagged). */
/* Donation row uses two TDs (fields colspan=7, actions colspan=1) so the
   action buttons sit in the SAME column as the action column above.
   vertical-align: top keeps both TDs flush with the row's top edge so the
   border-top is one continuous line across both cells (otherwise the
   shorter actions cell would be middle-aligned and the border would land
   in the middle of the row). */
.donation-row td { padding: 0; background: #F1F8E9; vertical-align: top; }
.donation-content { display: none; padding: 10px 16px; border-top: 2px solid #A5D6A7; }
.donation-content.active { display: block; }
.donation-content .fq-field input:focus { border-color: #2E7D32; }
.donation-content.donation-actions { white-space: nowrap; }

/* Mobile-only meta lines on the finance cards (transactions: method · date ·
   tag; fees: period · date · method). Hidden on desktop, where those live in
   their own table columns. */
.tx-mmeta, .fee-mmeta { display: none; }

.fq-form { display: flex; flex-wrap: wrap; gap: 10px; align-items: flex-end; }
.fq-field { display: flex; flex-direction: column; min-width: 110px; }
.fq-field label { font-size: 11px; font-weight: 600; color: #555; margin-bottom: 3px; }
.fq-field input, .fq-field select {
  padding: 6px 9px; border: 1px solid #c8e6c9; border-radius: 5px;
  font-size: 13px; outline: none; background: white;
}
.fq-field input:focus, .fq-field select:focus { border-color: #2E7D32; }
.fq-actions { display: flex; gap: 6px; align-items: flex-end; padding-bottom: 1px; }

.fees-table { width: 100%; border-collapse: collapse; margin-top: 12px; }
/* Typography from the base rule; the darker body ink is this table's own. */
.fees-table td { border-bottom: 1px solid #f0f0f0; color: #1A1A2E; }
.fees-table tr:last-child td { border-bottom: none; }
/* Action column: fixed table layout splits unwidthed columns evenly, which is
   too narrow for five 30px icon buttons — the last one (Löschen) got clipped
   on Lastschrift rows. Reserve the real width; the text columns share the rest. */
#feesLogTable .col-action, #feesTable .col-action { width: 186px; }
.fee-period-badge {
  display: inline-block; background: #FFF3E0; color: #D95F02;
  border-radius: 4px; padding: 2px 8px; font-size: 12px; font-weight: 700;
}
/* A storniert fee row (Rücklastschrift) stays visible as history but stops
   competing with the rows that are still true. Dimmed rather than struck through:
   the amount was real, it just came back. The actions keep full contrast, since
   deleting such a row is a normal thing to want. */
.fee-card-row.fee-row-cancelled > td { opacity: .55; }
.fee-card-row.fee-row-cancelled > td.tbl-cell-act,
.fee-card-row.fee-row-cancelled > td.mcard-actions { opacity: 1; }
/* Overdue members section — a card grid (all viewports): one card per member
   with direct actions; the quick-pay form expands inside its card, which then
   stretches across the whole grid row. */
.overdue-section {
  background: #FFFBF5; border: 1px solid #F5C07A;
  border-radius: 10px; padding: 20px 24px; margin-bottom: 32px;
}
.overdue-section h2 { color: #B45309; margin: 0 0 4px 0; font-size: 17px; }
.overdue-head { display: flex; align-items: center; gap: 8px; }
.overdue-head svg { width: 17px; height: 17px; flex: none; }

.overdue-grid { display: grid; grid-template-columns: repeat(auto-fill, minmax(250px, 1fr)); gap: 12px; }
.ocard { background: #fff; border: 1px solid #F3E0BE; border-radius: 9px; padding: 12px 14px; display: flex; flex-direction: column; }
.ocard-name { font-weight: 600; font-size: 14px; }
.ocard-meta { color: #888; font-size: 12px; margin-top: 2px; }
.ocard-actions { display: flex; flex-wrap: wrap; gap: 4px; align-items: center; margin-top: 12px; }
.ocard-sp { flex: 1; }

/* Inline comment (member comment, shared with the members list). */
.ocard-note { display: none; margin-top: 10px; }
.ocard-note.active { display: block; }
.ocard-note textarea {
  width: 100%; border: 1px solid #F3E0BE; border-radius: 6px;
  padding: 8px 10px; font-size: 12.5px;
  font-family: 'Segoe UI', Arial, sans-serif;
  color: #444; resize: vertical; box-sizing: border-box;
  outline: none; min-height: 52px; background: #FFFAF2;
}
.ocard-note textarea:focus { border-color: #B45309; }
/* Open quick-pay form: card takes the full grid row, amber-bordered fields. */
.ocard.form-open { grid-column: 1 / -1; border-color: #F5C07A; }
.ocard-form { display: none; margin-top: 12px; background: #FFF8EC; border-radius: 8px; padding: 12px 14px; }
.ocard.form-open .ocard-form { display: block; }
.ocard-form .fq-field input,
.ocard-form .fq-field select { border-color: #F5C07A; }
.ocard-form .fq-field input:focus,
.ocard-form .fq-field select:focus { border-color: #B45309; }
/* Cards beyond the preview stay hidden until "Mehr anzeigen". */
.ocard.overdue-extra { display: none; }
.overdue-grid.overdue-show-all .ocard.overdue-extra { display: flex; }

/* A comment already exists behind this button — mark it orange. */
.btn-notes.has-note, .mand-icon-btn.has-note { color: #D95F02; border-color: #D95F02; }

/* Finance page — summary cards */
.fin-summary-grid {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(200px, 1fr));
  gap: 16px;
  margin-bottom: 36px;
}
.fin-stat-card {
  background: white;
  border-radius: 10px;
  padding: 20px 22px 16px;
  box-shadow: 0 1px 3px rgba(0,0,0,0.07), 0 0 0 1px rgba(0,0,0,0.04);
  border-left: 4px solid #D95F02;
  display: flex;
  flex-direction: column;
}
.fin-stat-card.accent-navy  { border-left-color: #1A1A2E; }
.fin-stat-card.accent-blue  { border-left-color: #1565C0; }
.fin-stat-card.accent-green { border-left-color: #2E7D32; }
.fin-stat-card.accent-amber { border-left-color: #B45309; }
.fin-stat-label {
  font-size: 11px; font-weight: 700; text-transform: uppercase;
  letter-spacing: 0.6px; color: #999; margin-bottom: 10px;
}
.fin-stat-value {
  font-size: 30px; font-weight: 700; color: #1A1A2E;
  line-height: 1; margin-bottom: 5px;
}
.fin-stat-sub  { font-size: 12px; color: #aaa; flex: 1; margin-bottom: 14px; }
.fin-stat-actions { display: flex; gap: 8px; flex-wrap: wrap; margin-top: auto; }
.fin-set-btn {
  background: none; border: 1px solid #e0e0e0; color: #888;
  font-size: 11px; padding: 4px 10px; border-radius: 4px; cursor: pointer;
}
.fin-set-btn:hover { border-color: #D95F02; color: #D95F02; }

/* ── Admin section read/edit mode ─────────────────── */
.admin-section-subtitle { color: #888; font-size: 13px; margin: 0; }

/* ── Admin card head: icon, title, one sentence, then state + pencil ────────
   Every card in the console opens with this same shape. Before, some cards had
   a header wrapper and some were a bare <h3> + <p>, which is why the pencil
   sat at a different height from card to card. The icon is what makes a
   section scannable without reading each title. */
/* align-items:center, NOT flex-start. flex-start only ever LOOKED right while a
   grey subtitle made the text block as tall as the 38px icon; a head whose text is
   one 20px line put the title's centre 9px above its own icon and 4px above the
   (i) and the pencil, on every card in all nine sections. Measured, not eyeballed.
   Centring is also correct for the two cards that still carry a live status line
   under the title: the icon then centres on the whole block. */
.admin-card-head {
  display: flex; align-items: center; gap: 14px; margin-bottom: 18px;
}
.admin-card-icon {
  flex: 0 0 auto; width: 38px; height: 38px; border-radius: 10px;
  display: inline-flex; align-items: center; justify-content: center;
  background: #F4F5F8; border: 1px solid #E6E7EF; color: #5A6472;
}
.admin-card-icon svg { width: 19px; height: 19px; }
/* Smaller inline variant, e.g. the service logo inside a connection row. */
.admin-card-icon--sm { width: 34px; height: 34px; border-radius: 9px; }
.admin-card-icon--sm svg { width: 17px; height: 17px; }
.admin-card-head-text { flex: 1 1 auto; min-width: 0; }
/* No margin: the 1px top plus 4px bottom was the nudge that half-corrected the
   flex-start offset above, and with centring it would tip the title back off the
   icon's centre line. The gap to a following status line moves onto that line. */
.admin-card-head-text .admin-card-title { margin: 0; }
.admin-card-head-text .admin-card-title + .admin-section-subtitle { margin-top: 4px; }
.admin-card-head-actions {
  flex: 0 0 auto; display: flex; align-items: center; gap: 10px;
}

/* Section head: title plus one orienting sentence. All nine sections open the
   same way, instead of three having a subtitle and six not. */
.admin-section-head { margin-bottom: 22px; }
.admin-section-head .admin-section-subtitle { max-width: 82ch; line-height: 1.6; }

/* ── Groups inside one card, and their sub-heading ──────────────────────────
   A card that holds two distinct groups (Mitgliedschaft: Beitrag, then
   Mitgliedschaftsarten) needs a heading per group. Both used to carry the SAME
   four hardcoded inline styles, which is the local-override pattern the button
   rule warns about, only in a heading: the third one added would have differed
   from the first two. */
.admin-card-subhead { margin: 0; font-size: 14px; font-weight: 700; color: #1A1A2E; }
.admin-card-group { margin-top: 26px; }
.admin-card-group:first-of-type { margin-top: 0; }

/* ── A locked row in an editable list ───────────────────────────────────────
   Lifted out of the EÜR rule editor (`.rgl-sysrow`) on 2026-08-02, the same
   move that produced `.seg`: a value the code owns, shown so the list is
   complete, locked because renaming or removing it is not the user's to do.

   Three things are deliberate. It sits IN the list rather than in a section of
   its own, so the list reads as "these are the types" with one of them locked.
   The lock sits at the RIGHT end of the name box, never before the text, or it
   indents that one name and breaks the left edge every other row shares. And
   `box-sizing` plus the transparent border are load-bearing, not decoration: a
   span is content-box, so the flex basis would otherwise render 20px wider than
   the inputs above it and push its trailing text out of the shared column, and
   `.card-field-input` carries a 1px transparent border that the name has to
   match or it starts 1px to the left of every name below it. */
.locked-row { display: flex; align-items: center; gap: 10px; }
.locked-name {
  box-sizing: border-box; border: 1px solid transparent;
  display: flex; align-items: center; justify-content: space-between; gap: 8px;
  padding: 7px 10px; font-size: 14px; font-weight: 500; color: #6a6a76;
}
.locked-name svg { width: 13px; height: 13px; color: #b0b0ba; flex: none; }

/* The Mitgliedschaftsarten list this locked row lives in. The row layout used to
   be an inline style written from JS on every render; as a rule it is stated
   once, and the name can carry a width. That width is the whole fix for the
   emptiness in the middle of the row: `flex: 1` stretched the name to the card
   edge and left the count a hand-span away from what it counts. Both kinds of
   row share the basis so every count lands in one column. */
.mt-row { display: flex; align-items: center; gap: 10px; margin-bottom: 8px; }
.mt-row > .mt-label,
.mt-row > .locked-name { flex: 0 1 300px; }
.mt-count { font-size: 12px; color: #888; }
/* In edit mode every EDITABLE row grows two chevrons in front of its name
   (30px + 10px gap each), so without this the locked row's name and count sit
   80px to the left of all the others exactly when the list is being worked in.
   The gutter it leaves empty is also honest: this row has no actions. The live
   check asserts one left edge in BOTH modes, so a change to the icon size fails
   loudly instead of drifting. */
.admin-editing #membershipTypesList .locked-row { padding-left: 80px; }

/* ── One status pill for the whole console ──────────────────────────────────
   Every connection or job state in the console renders through this, so the
   padding, background and radius cannot differ per card. --on/--off/--warn/--err are the only states
   a connection or a job can be in here. */
.admin-status {
  display: inline-flex; align-items: center; gap: 7px; flex: 0 0 auto;
  font-size: 12.5px; font-weight: 700; padding: 5px 12px; border-radius: 20px;
  white-space: nowrap;
}
.admin-status svg { width: 14px; height: 14px; }
.admin-status--on   { background: #EAF7EE; color: #1B7A32; }
.admin-status--off  { background: #F1F2F6; color: #6B7280; }
.admin-status--warn { background: #FFF6E5; color: #92620A; }
.admin-status--err  { background: #FDF1EE; color: #B4443A; }

/* ── Connection row ────────────────────────────────────────────────────────
   The uniform way to show "this external service is/isn't hooked up", plus the
   one button that changes it. Used by the Google connection, the Sparkasse
   FinTS access and the calendar state line. */
.admin-conn {
  display: flex; align-items: center; gap: 14px; flex-wrap: wrap;
  padding: 14px 16px; border: 1px solid #E6E7EF; border-radius: 10px;
  background: #FBFBFD;
}
.admin-conn + .admin-conn { margin-top: 10px; }
.admin-conn-main { flex: 1 1 240px; min-width: 0; }
.admin-conn-title {
  font-size: 13.5px; font-weight: 700; color: #1A1A2E;
  display: flex; align-items: center; gap: 9px; flex-wrap: wrap;
}
.admin-conn-sub { font-size: 12.5px; color: #8B92A2; margin: 3px 0 0; line-height: 1.5; }
.admin-conn-actions { flex: 0 0 auto; display: flex; align-items: center; gap: 8px; }
/* Warning/attention variant, e.g. a pending TAN confirmation. */
.admin-conn--warn { background: #FFF8E1; border-color: #FFD54F; }
.admin-conn--warn .admin-conn-sub { color: #7d6209; }

/* E-Mail-Konten (Admin → E-Mail-Konten): account list rows + inline add/edit form */
.ea-row { display: flex; align-items: center; gap: 12px; padding: 12px 0; border-bottom: 1px solid #eee; }
.ea-row:last-child { border-bottom: none; }
.ea-row__main { flex: 1; min-width: 0; }
.ea-row__title { font-weight: 600; color: #1A1A2E; display: flex; align-items: center; gap: 8px; flex-wrap: wrap; }
.ea-row__sub { font-size: 13px; color: #888; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.ea-badge {
  display: inline-block; font-size: 11px; font-weight: 600; padding: 2px 8px; border-radius: 10px;
  background: #eef0f3; color: #5a6472; letter-spacing: .01em;
}
.ea-badge--default { background: #1A1A2E; color: #fff; }
.ea-form { border: 1px solid #e0e0e0; border-radius: 10px; padding: 18px; background: #fafafb; }
.ea-form__title { margin: 0 0 14px; font-size: 14px; font-weight: 700; color: #1A1A2E; }
.ea-form__sub { margin: 18px 0 10px; font-size: 12px; font-weight: 700; color: #888; text-transform: uppercase; letter-spacing: .04em; }
.ea-grid { display: grid; grid-template-columns: 1fr 1fr; gap: 12px 16px; }
.ea-grid-wide { display: grid; grid-template-columns: 2fr 1fr; gap: 12px 16px; }
.ea-field { display: flex; flex-direction: column; gap: 5px; min-width: 0; }
.ea-field > span { font-size: 11px; font-weight: 600; text-transform: uppercase; letter-spacing: .03em; color: #aaa; }
.ea-field input[type="text"], .ea-field input[type="email"], .ea-field input[type="number"], .ea-field input[type="password"] {
  width: 100%; padding: 9px 11px; border: 1px solid #ddd; border-radius: 7px; font-size: 14px; background: #fff; box-sizing: border-box;
}
.ea-field input:focus { outline: none; border-color: #D95F02; }
.ea-field--check { flex-direction: row; align-items: center; gap: 8px; align-self: end; }
.ea-field--check input { width: auto; }
.ea-field--check > span { text-transform: none; letter-spacing: 0; font-size: 13px; font-weight: 500; color: #444; }
.ea-form__hint { margin: 10px 0 0; font-size: 12px; color: #888; line-height: 1.5; }
.ea-adv-toggle { margin-top: 16px; }
#eaAdvancedBox { margin-top: 4px; }
.ea-test-result { margin-top: 14px; font-size: 13px; line-height: 1.6; }
/* Uses .btn-row.btn-row--split; the normalising padding patch that used to live
   here is gone, because the button classes now ship one geometry themselves. */
.ea-form__actions { margin-top: 16px; }
/* Push the "test" button to the left; cancel/save group to the right. On a narrow
   screen the auto-margin lets the row wrap cleanly instead of forcing overflow. */
.ea-test-btn { margin-right: auto; }

.admin-field-grid {
  display: grid; grid-template-columns: 1fr 1fr 1fr; gap: 0 20px;
}
.admin-field-grid.two-col { grid-template-columns: 1fr 1fr; }
.admin-field-grid .full { grid-column: 1 / -1; }
.admin-field-wrap { margin-bottom: 16px; }
.admin-field-label {
  font-size: 11px; font-weight: 700; text-transform: uppercase;
  letter-spacing: 0.05em; color: #aaa; margin-bottom: 4px; display: block;
}
.admin-field-input {
  width: 100%; padding: 7px 10px;
  border: 1px solid transparent; border-radius: 6px;
  font-size: 14px; color: #1A1A2E; font-weight: 500;
  font-family: 'Segoe UI', Arial, sans-serif;
  background: transparent; box-sizing: border-box; outline: none;
  transition: border-color 0.15s, background 0.15s;
}
.admin-field-input[readonly], .admin-field-input:disabled {
  cursor: default; pointer-events: none;
}
.admin-editing .admin-field-input {
  border-color: #ddd; background: white; cursor: text; pointer-events: auto;
}
.admin-editing .admin-field-input:focus { border-color: #D95F02; }
.card-field-input {
  width: 100%; padding: 7px 10px;
  border: 1px solid transparent; border-radius: 6px;
  font-size: 14px; color: #1A1A2E; font-weight: 500;
  font-family: 'Segoe UI', Arial, sans-serif;
  background: transparent; box-sizing: border-box; outline: none;
  transition: border-color 0.15s, background 0.15s;
}
.card-field-input[readonly], .card-field-input:disabled {
  cursor: default; pointer-events: none;
}
.admin-editing .card-field-input {
  border-color: #ddd; background: white; cursor: text; pointer-events: auto;
}
.admin-editing .card-field-input:focus { border-color: #D95F02; }
/* Edit affordance on admin cards is an icon-only pencil (30×30 .btn-edit),
   same on desktop and mobile — no text label. */
.admin-section-edit-btn { flex-shrink: 0; }
.admin-section-edit-btn svg { width: 15px; height: 15px; }
/* Abbrechen/Speichern sit in a card FOOTER under the fields being edited (the
   app-wide standard since 2026-07-31; they used to live in the card header).
   Hidden in read mode; the pencil stays top-right as the entry point. */
.admin-section-save-actions {
  display: none; align-items: center; justify-content: flex-end; gap: 8px;
  margin-top: 18px; padding-top: 14px; border-top: 1px solid #f0f0f3;
}
.admin-editing .admin-section-edit-btn { display: none !important; }
.admin-editing .admin-section-save-actions { display: flex !important; }
.admin-logo-upload { display: none; margin-top: 8px; }

/* Bank capability pills (Sparkasse-Verbindung card): one pill per FinTS
   operation the bank advertises for this access; the segment ID (HKDME, …)
   sits in the tooltip. Green = granted; the grey "+N weitere" collects the
   protocol segments nobody needs to read. */
.bank-cap-head { display: block; font-size: 11px; font-weight: 700; text-transform: uppercase; letter-spacing: .05em; color: #aaa; margin-bottom: 6px; }
.bank-cap-row  { display: flex; flex-wrap: wrap; gap: 6px; }
.bank-cap      { display: inline-flex; align-items: center; font-size: 11.5px; font-weight: 600; padding: 3px 10px; border-radius: 20px; background: #EAF4EB; color: #2E7D32; white-space: nowrap; }
.bank-cap.more { background: #f1f1f4; color: #6b7280; }
.bank-cap-when { display: block; font-size: 12px; color: #888; margin-top: 8px; }
.bank-cap-note { display: block; font-size: 12px; color: #8a5a1f; margin-top: 8px; }
.admin-editing .admin-logo-upload { display: flex; align-items: center; gap: 16px; flex-wrap: wrap; }

/* scroll-margin so the sticky top nav (60px) doesn't cover a section when
   something scrolls to it (e.g. a dashboard quick-action → "Add Member"). */
.subtab-anchor { scroll-margin-top: 72px; }

.fin-fee-overview {
  display: flex; flex-wrap: wrap; gap: 10px; margin-top: 20px;
}
.fin-member-chip {
  background: white; border-radius: 8px; padding: 10px 16px;
  box-shadow: 0 1px 4px rgba(0,0,0,0.08); font-size: 13px;
  display: flex; flex-direction: column; gap: 2px; min-width: 160px;
}
.fin-member-chip .chip-name  { font-weight: 600; color: #1A1A2E; margin-bottom: 6px; }
.chip-quarter {
  font-size: 12px; padding: 5px 8px; border-radius: 6px;
  margin-bottom: 4px; display: flex; align-items: center; gap: 6px; flex-wrap: wrap;
}
.chip-q-paid { background: #F1F8F1; color: #2E7D32; }
.chip-q-due  { background: #FFF8F0; color: #B45309; }
.chip-pay-btn {
  margin-left: auto; background: #2E7D32; color: white;
  border: none; border-radius: 4px; font-size: 11px;
  padding: 3px 8px; cursor: pointer; font-weight: 600;
  white-space: nowrap;
}
.chip-pay-btn:hover { background: #1B5E20; }

.tx-income  { color: #2E7D32; }
.tx-outcome { color: #B34D00; }
.tx-tag {
  display: inline-block; font-size: 11px; padding: 2px 8px;
  border-radius: 10px; background: #F0F0F0; color: #555;
}
.tx-tag.membership_fee      { background: #E8F5E9; color: #2E7D32; }
.tx-tag.recurring_donation  { background: #E3F2FD; color: #1565C0; }
.tx-tag.onetime_donation    { background: #EDE7F6; color: #512DA8; }
.tx-tag.expense             { background: #FBE9E7; color: #BF360C; }

  /* ── Login page ── */
/* Login-Hintergrund „Abendverlauf": Navy kippt diagonal in einen dunklen
   Warmton, mit warmem Glühen unten rechts — Karte bleibt der Blickfang. */
#page-login,
#page-force-password,
#page-forgot-password,
#page-reset-password,
#page-terms-gate {
  min-height: 100vh;  /* Fallback für ältere Browser */
  min-height: 100dvh; /* mobil misst 100vh inkl. eingeklappter Adressleiste — dvh nimmt die echte sichtbare Höhe */
  box-sizing: border-box; /* padding zählt zur Höhe — sonst scrollt die Seite um 40px */
  align-items: center;
  justify-content: center;
  padding: 20px;
  background:
    radial-gradient(120% 90% at 96% 110%, rgba(217, 95, 2, 0.20) 0%, rgba(217, 95, 2, 0) 55%),
    radial-gradient(90% 70% at -5% -10%, rgba(255, 246, 239, 0.05) 0%, rgba(255, 246, 239, 0) 55%),
    linear-gradient(135deg, #1A1A2E 0%, #20203A 35%, #31222F 65%, #43261B 100%);
}

#page-login.active {
  display: flex;
}

#page-force-password.active {
  display: flex;
}

#page-forgot-password.active,
#page-reset-password.active {
  display: flex;
}

#page-terms-gate.active {
  display: flex;
}

/* The reset-password screen is the one logged-out page reachable by deep link
   (the emailed /reset-password?token= URL). Like the others it must stay visible
   while body.logged-out is set — covered by the :not() list on the hide rule below. */
.login-back {
  display: inline-block;
  margin-top: 18px;
  font-size: 13px;
  color: #888;
  text-decoration: none;
}
.login-back:hover { color: #D95F02; text-decoration: underline; }

/* Generic success note inside a login card (reuses the muted login palette). */
.login-note {
  margin-top: 16px;
  padding: 10px 12px;
  background: #E8F5E9;
  color: #2E7D32;
  font-size: 13px;
  border-radius: 6px;
  line-height: 1.5;
}

/* ── Terms-of-use acceptance gate ───────────────── */
.terms-card {
  background: white;
  border-radius: 12px;
  max-width: 720px;
  width: 100%;
  max-height: 88dvh;             /* card never exceeds the viewport — the body scrolls inside */
  display: flex;
  flex-direction: column;
  box-shadow: 0 8px 32px rgba(0,0,0,0.1);
  border-top: 4px solid #D95F02;
  overflow: hidden;
}
.terms-head { padding: 32px 32px 12px; }
.terms-head h2 { margin: 0 0 8px; color: #D95F02; }
/* Scroll container for the stack of document blocks (scrolls between docs). */
.terms-docs {
  flex: 1;
  overflow-y: auto;
  padding: 12px 32px;
  border-top: 1px solid #eee;
  border-bottom: 1px solid #eee;
}
.terms-doc { padding: 16px 0; }
.terms-doc + .terms-doc { border-top: 1px solid #eee; }
.terms-doc-title { margin: 0 0 10px; font-size: 15px; color: #1A1A2E; }
/* Each document's own scrollable text box (fixed height → scroll-to-read works). */
.terms-doc-body {
  height: 220px;
  overflow-y: auto;
  padding: 12px 14px;
  border: 1px solid #e6e6e6;
  border-radius: 6px;
  background: #fcfcfc;
  white-space: pre-wrap;         /* preserve the line breaks stored in the text */
  overflow-wrap: anywhere;
  line-height: 1.6;
  font-size: 14px;
  color: #333;
}
.terms-doc-hint { margin: 8px 0 10px; font-size: 12px; color: #B45309; }
.terms-doc-hint.done { display: none; }
.terms-foot { padding: 18px 32px 24px; }
.terms-check {
  display: flex; align-items: flex-start; gap: 10px;
  font-size: 14px; color: #1A1A2E; cursor: pointer;
}
.terms-check input { margin-top: 2px; width: 16px; height: 16px; flex: none; cursor: pointer; }
.terms-check input:disabled { cursor: not-allowed; }
.terms-actions { display: flex; gap: 12px; margin-top: 4px; }
.terms-actions button {
  flex: 1; padding: 12px; border-radius: 6px;
  font-size: 14px; font-weight: 600; cursor: pointer; border: none;
}
.terms-decline { background: #f0f0f0; color: #555; }
.terms-decline:hover { background: #e4e4e4; }
.terms-accept { background: #D95F02; color: white; }
.terms-accept:hover { background: #B34D00; }
.terms-accept:disabled { background: #e7c3a8; cursor: not-allowed; }

/* Admin terms editor: the "current version / acceptances" status line. */
.terms-status {
  background: #F8F9FA;
  border: 1px solid #e0e0e0;
  border-radius: 8px;
  padding: 12px 16px;
  font-size: 13px;
  color: #555;
  margin-bottom: 18px;
}
/* Admin terms editor: the "wesentliche Änderung" checkbox row. */
.terms-material-row { margin-bottom: 18px; }
.terms-material-label {
  display: flex; align-items: flex-start; gap: 10px;
  font-size: 14px; color: #1A1A2E; cursor: pointer; line-height: 1.4;
}
.terms-material-label input {
  margin-top: 1px; width: 16px; height: 16px; flex: none;
  accent-color: #D95F02; cursor: pointer;
}

.login-card {
  background: white;
  border-radius: 12px;
  padding: 40px;
  max-width: 400px;
  width: 100%;
  box-shadow: 0 8px 32px rgba(0,0,0,0.1);
  border-top: 4px solid #D95F02;
}

.login-card h2 {
  margin: 0 0 8px;
  color: #D95F02;
}

/* dsiTOOL-Wortmarke auf der Login-Karte: "dsi" navy, "TOOL" orange.
   Ohne Vereinskürzel bleibt das h2 die orange Willkommen-Überschrift. */
.login-card h2.login-wordmark { color: #1A1A2E; letter-spacing: -0.5px; }
.login-card h2.login-wordmark span { color: #D95F02; }

.login-orgline {
  color: #888;
  font-size: 13px;
  margin: 0 0 2px;
}

.login-subtitle {
  color: #888;
  font-size: 13px;
  margin-bottom: 24px;
}

/* Unter der Wortmarke + Vereinszeile wird der Anmelde-Hinweis zur leisen
   dritten Zeile (auf der Force-Password-Seite bleibt er gut lesbar). */
#page-login .login-subtitle { color: #aaa; font-size: 12px; }

.login-card label {
  display: block;
  font-size: 11px;
  color: #aaa;
  text-transform: uppercase;
  letter-spacing: 0.6px;
  margin-bottom: 4px;
  margin-top: 16px;
}

.login-card input {
  width: 100%;
  padding: 10px 12px;
  font-size: 14px;
  border: 1px solid #e0e0e0;
  border-radius: 6px;
  box-sizing: border-box;
  outline: none;
}

.login-card input:focus { border-color: #D95F02; }

.login-card button {
  width: 100%;
  padding: 12px;
  margin-top: 24px;
  background: #D95F02;
  color: white;
  border: none;
  border-radius: 6px;
  font-size: 14px;
  font-weight: 600;
  cursor: pointer;
}

.login-card button:hover { background: #B34D00; }

.login-error {
  margin-top: 16px;
  padding: 10px;
  background: #FBE9E7;
  color: #BF360C;
  border-radius: 6px;
  font-size: 13px;
  display: none;
}

.login-error.active { display: block; }

.login-divider {
  display: flex;
  align-items: center;
  gap: 10px;
  margin: 16px 0;
  color: #aaa;
  font-size: 13px;
}
.login-divider::before,
.login-divider::after {
  content: '';
  flex: 1;
  height: 1px;
  background: #e0e0e0;
}

.btn-google {
  display: flex;
  align-items: center;
  justify-content: center;
  gap: 10px;
  width: 100%;
  padding: 10px 16px;
  border: 1px solid #dadce0;
  border-radius: 6px;
  background: white;
  color: #3c4043;
  font-size: 14px;
  font-weight: 500;
  cursor: pointer;
  text-decoration: none;
  box-sizing: border-box;
  transition: background 0.15s, box-shadow 0.15s;
}
.btn-google:hover {
  background: #f8f9fa;
  box-shadow: 0 1px 3px rgba(0,0,0,0.12);
}

/* ── User indicator in nav ── */
.nav-user {
  margin-left: auto;
  display: flex;
  align-items: center;
  gap: 12px;
  color: rgba(255,255,255,0.7);
  font-size: 13px;
}

/* ── Account menu (gear dropdown) — used on ALL viewports ──────────────
   One dropdown replaced the old desktop inline buttons (Admin / Name /
   Logout). The gear icon is the trigger; the menu carries the signed-in
   identity + admin / Konto / Logout. Mobile-only extras (the version line
   + pinned-doc links) are hidden here and shown again in mobile.css. */
.nav-gear-wrap { display: block; position: relative; }
.nav-gear-btn {
  background: transparent;
  border: 1px solid rgba(255,255,255,0.25);
  color: rgba(255,255,255,0.7);
  border-radius: 50%;
  width: 30px; height: 30px;
  cursor: pointer;
  display: flex; align-items: center; justify-content: center;
  flex-shrink: 0;
  transition: background 0.15s, border-color 0.15s, color 0.15s;
}
.nav-gear-btn svg { width: 17px; height: 17px; }
.nav-gear-btn:hover { color: #fff; border-color: rgba(255,255,255,0.6); background: rgba(255,255,255,0.1); }

.nav-gear-menu {
  display: none;
  position: absolute;
  top: calc(100% + 10px); right: 0;
  min-width: 210px;
  background: #fff;
  border-radius: 12px;
  box-shadow: 0 12px 30px rgba(0,0,0,0.28);
  padding: 8px;
  z-index: 300;
}
.nav-gear-menu.open { display: block; }

/* Signed-in identity header — was the desktop account button's name + role. */
.gear-head {
  padding: 8px 12px 10px;
  margin-bottom: 4px;
  border-bottom: 1px solid #eee;
  line-height: 1.3;
}
.gear-head-name { display: block; font-size: 14px; font-weight: 700; color: #1A1A2E; }
.gear-head-role { display: block; font-size: 11px; color: #9a9aa2; }

.gear-row {
  display: flex; align-items: center; gap: 12px;
  width: 100%;
  background: none; border: none; cursor: pointer;
  font-family: inherit; font-size: 15px; font-weight: 600;
  color: #1A1A2E; text-align: left; text-decoration: none;
  padding: 12px; border-radius: 9px; min-height: 46px;
}
.gear-row svg { width: 20px; height: 20px; color: #555; flex-shrink: 0; }
/* Hover/active: fill with the navy brand + flip text & icon to white, so the
   row clearly reads as selected. text-decoration:none overrides the generic
   `nav button:hover` underline (these rows are <button>s inside <nav>). */
.gear-row:active,
.gear-row:hover { background: #1A1A2E; color: #fff; text-decoration: none; }
.gear-row:hover svg, .gear-row:active svg { color: #fff; }
.gear-row--danger { color: #c0392b; }
.gear-row--danger svg { color: #c0392b; }
/* Danger row (Logout) → red fill on hover, also white text/icon. */
.gear-row--danger:active,
.gear-row--danger:hover { background: #c0392b; color: #fff; }
.gear-row--danger:hover svg, .gear-row--danger:active svg { color: #fff; }

/* Version line — MOBILE-ONLY (desktop shows it in the footer); mobile.css
   flips it back to visible. */
.gear-meta {
  display: none;
  padding: 10px 12px 4px;
  margin-top: 4px;
  border-top: 1px solid #eee;
  color: #9a9aa2; font-size: 12px;
}

.nav-user .nav-help-btn {
  background: transparent;
  border: 1px solid rgba(255,255,255,0.25);
  color: rgba(255,255,255,0.65);
  border-radius: 50%;
  width: 26px; height: 26px;
  font-size: 13px; font-weight: 700;
  cursor: pointer;
  display: flex; align-items: center; justify-content: center;
  flex-shrink: 0;
  transition: background 0.15s, border-color 0.15s, color 0.15s;
}
.nav-user .nav-help-btn:hover {
  color: white;
  border-color: rgba(255,255,255,0.6);
  background: rgba(255,255,255,0.1);
}
.nav-user .nav-help-btn.active {
  color: white;
  border-color: white;
  background: rgba(255,255,255,0.15);
  /* override the underline active state from generic nav button rule */
  border-bottom-width: 1px;
  padding-bottom: 0;
}

/* Hide the whole app shell when not logged in */
body.logged-out nav,
body.logged-out footer,
body.logged-out .page:not(#page-login):not(#page-force-password):not(#page-forgot-password):not(#page-reset-password):not(#page-terms-gate) {
  display: none !important;
}

/* Spinner */
#spinner {
  display: none;
  position: fixed;
  inset: 0;
  background: rgba(255,255,255,0.6);
  z-index: 10000;
  align-items: center;
  justify-content: center;
}
#spinner.show { display: flex; }
.spinner-circle {
  width: 40px;
  height: 40px;
  border: 4px solid #eee;
  border-top-color: #D95F02;
  border-radius: 50%;
  animation: spin 0.7s linear infinite;
}
@keyframes spin { to { transform: rotate(360deg); } }

/* Required field asterisk */
.req-star { color: #c0392b; font-weight: bold; }

/* Form validation error */
.form-error {
  color: #c0392b;
  font-size: 13px;
  margin-top: 8px;
  display: none;
}
.form-error.show { display: block; }

/* Toast notification */
#toast {
  position: fixed;
  bottom: 32px;
  right: 32px;
  background: #1A1A2E;
  color: #fff;
  padding: 12px 20px;
  border-radius: 8px;
  font-size: 14px;
  opacity: 0;
  pointer-events: none;
  transition: opacity 0.3s ease;
  z-index: 9999;
}
#toast.show { opacity: 1; }

/* Scroll-to-top button */
#scrollTopBtn {
  position: fixed;
  bottom: 90px;
  right: 32px;
  width: 40px;
  height: 40px;
  border-radius: 50%;
  background: #D95F02;
  color: white;
  border: none;
  font-size: 22px;
  line-height: 1;
  cursor: pointer;
  opacity: 0;
  pointer-events: none;
  transition: opacity 0.25s ease;
  z-index: 9998;
  box-shadow: 0 2px 8px rgba(0,0,0,0.2);
}
#scrollTopBtn.visible { opacity: 1; pointer-events: auto; }
#scrollTopBtn:hover { background: #bf5300; }

/* ── Admin Console ── */
.admin-section {
  background: #fff;
  border: 1px solid #e0e0e0;
  border-radius: 12px;
  padding: 28px 32px;
  margin-bottom: 28px;
}
.admin-section.admin-section-cards {
  background: none;
  border: none;
  border-radius: 0;
  padding: 0;
}
.admin-card {
  background: #fff;
  border: 1px solid #e0e0e0;
  border-radius: 12px;
  padding: 28px 32px;
  margin-bottom: 24px;
}
.admin-card-title {
  font-size: 15px;
  font-weight: 700;
  color: #1A1A2E;
  margin: 0 0 4px;
}
/* Lighter card for list items nested inside a section .admin-card (the Email
   "Vorlagen" tab: template + automation items). Avoids the heavy double border
   of nesting .admin-card inside .admin-card. */
.email-card {
  background: #fff;
  border: 1px solid #e3e3e8;
  border-radius: 10px;
  padding: 18px 20px;
  margin-bottom: 12px;
  box-shadow: 0 1px 4px rgba(26,26,46,0.07);
}
.email-card:last-child { margin-bottom: 0; }
.admin-section h2 {
  font-size: 16px;
  font-weight: 700;
  color: #1A1A2E;
  margin: 0 0 20px 0;
}

/* ── Inline automation editor (rendered inside an .admin-card in edit mode) ──
   Soft-filled fields + brand focus ring — modern, matches the composer look,
   not the old gray-box inputs. */
.auto-edit-title { font-size: 15px; font-weight: 700; color: #1A1A2E; margin: 0 0 16px; }
.auto-field { margin-bottom: 14px; }
.auto-field > label { display: block; font-size: 12px; font-weight: 600; color: #777; margin-bottom: 6px; }
.auto-input, .auto-select, .auto-textarea {
  width: 100%; box-sizing: border-box;
  font-family: inherit; font-size: 14px; color: #1A1A2E;
  background: #f7f7f9; border: 1px solid transparent; border-radius: 8px;
  padding: 10px 12px; outline: none;
  transition: background-color .12s, border-color .12s, box-shadow .12s;
}
.auto-input:focus, .auto-select:focus, .auto-textarea:focus {
  background: #fff; border-color: #D95F02; box-shadow: 0 0 0 3px rgba(217,95,2,0.12);
}
.auto-textarea { resize: vertical; min-height: 56px; line-height: 1.5; }
.auto-row { display: flex; gap: 14px; flex-wrap: wrap; }
.auto-row > .auto-field { flex: 1; min-width: 180px; margin-bottom: 14px; }
.auto-edit-actions { display: flex; gap: 10px; align-items: center; margin-top: 4px; flex-wrap: wrap; }

/* ── Admin Console sidebar layout ── */
/* Sections inside any sidebar-layout page are show-one-at-a-time
   (Admin Console, Finance, Help, E-Mail). */
#page-admin .admin-section,
#page-finance .admin-section,
#page-help .admin-section,
#page-email .admin-section { display: none; }
#page-admin .admin-section.active,
#page-finance .admin-section.active,
#page-help .admin-section.active,
#page-email .admin-section.active { display: block; }

/* Flatten the section "card box" on the sidebar pages — content now
   sits directly on the page background like the main pages (the sidebar
   already separates sections, so the boxes are redundant). Grouping cards
   INSIDE a section (.admin-card, .fin-stat-card) stay. Scoped to these
   pages so the My Account page (also .admin-section) keeps its boxes. */
#page-admin .admin-section,
#page-finance .admin-section,
#page-help .admin-section,
#page-email .admin-section {
  background: none;
  border: none;
  border-radius: 0;
  box-shadow: none;   /* help-section adds a shadow — flatten that too */
  padding: 0;
  margin-bottom: 0;
}

/* Section title — matches the main pages' big orange <h1>. Used on every
   section across the sidebar pages (the help sections title via their <h3>).
   Id-scoped so it beats the `.admin-section h2 { font-size:16px }` rule. */
#page-help .admin-section > h3:first-child,
#page-finance .section-title,
#page-email .section-title,
#page-admin .section-title {
  font-size: 1.9rem;
  font-weight: 700;
  color: #D95F02;
  line-height: 1.15;
  margin: 0 0 16px;
}
/* Inside an .admin-section-head the title sits tight to whatever follows, so the
   16px above would double a gap the head already owns: its subtitle on the
   E-Mail page, and in the console the head's own 22px straight to the first card
   (the nine console subtitles were dropped on 2026-08-01). Id-scoped to match
   the rule it has to beat: a plain .admin-section-head .section-title loses to
   one id. */
#page-finance .admin-section-head .section-title,
#page-email .admin-section-head .section-title,
#page-admin .admin-section-head .section-title { margin: 0 0 5px; }
/* A title that shares its line with an (i) hands its bottom margin to the row:
   align-items:center centres the MARGIN box, so any margin left on the title
   offsets the button by half of it. Id-scoped to outrank the rules above, which
   a plain .info-row > h1 cannot. The row then owns the spacing: inside an
   .admin-section-head the head's own 22px already provides it, elsewhere
   .info-row--title restores the 16px the bare title had. */
#page-finance .info-row > .section-title,
#page-email .info-row > .section-title,
#page-admin .info-row > .section-title { margin: 0; }
/* … including a head that keeps its own 5px, which the reset above must outrank. */
#page-email .admin-section-head .info-row > .section-title { margin: 0; }
.info-row--title { margin-bottom: 16px; }

#page-admin {
  padding-left: 0;
}
.admin-layout {
  padding-left: 244px; /* 220px sidebar + 24px gap */
}
.admin-sidebar {
  position: fixed;
  left: 0;
  top: var(--nav-height);
  bottom: 0;
  width: 220px;
  overflow-y: auto;
  background: #20203a;
  border-radius: 0;
  padding: 16px 0 10px;
  z-index: 50;
}
.admin-sidebar-title {
  font-size: 10px;
  font-weight: 700;
  color: rgba(255,255,255,0.3);
  text-transform: uppercase;
  letter-spacing: 0.7px;
  padding: 10px 16px 10px;
  margin: 0;
}
/* Flex + gap so an item can carry a leading icon. Text-only items (the E-Mail,
   Finanzen and Hilfe sidebars) render identically to the old display:block. */
.admin-nav-item {
  display: flex;
  align-items: center;
  gap: 11px;
  padding: 10px 16px;
  font-size: 14px;
  color: rgba(255,255,255,0.55);
  cursor: pointer;
  text-decoration: none;
  border-left: 3px solid transparent;
  transition: background 0.12s, color 0.12s;
  user-select: none;
}
/* Icons inherit the item's colour, so they brighten with it on hover/active
   rather than needing their own palette on the dark sidebar. */
.admin-nav-item > svg {
  width: 17px; height: 17px; flex: 0 0 auto; opacity: 0.75;
}
.admin-nav-item:hover {
  background: rgba(255,255,255,0.07);
  color: rgba(255,255,255,0.9);
}
.admin-nav-item.active {
  color: #fff;
  font-weight: 600;
  border-left-color: #D95F02;
  background: rgba(255,255,255,0.1);
}
.admin-nav-item.active > svg { opacity: 1; }
.admin-content {
  min-width: 0;
}

/* Only the column widths are this table's own now. Everything the old block set
   (14px type, its own paddings, a grey #fafafa hover that was the single
   one-off hover in the app) is the base rule's job. */
#usersTable td { vertical-align: middle; }
.usr-col-name    { width: 26%; }
.usr-col-mail    { width: 44%; }
.usr-col-role    { width: 20%; }
.usr-col-actions { width: 10%; }


.role-badge {
  display: inline-block;
  padding: 3px 10px;
  border-radius: 20px;
  font-size: 11px;
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.5px;
}
/* One class per stored role value, so the badge styles itself from the DB value
   (admin-users.js writes `role-badge <role>`). Navy is the technical owner, orange
   the Kassenwart; the two in between step down in weight, so the four read as a
   ladder rather than four unrelated colours. Values from the reviewed prototype. */
.role-badge.super_admin    { background: #1A1A2E; color: #fff; }
.role-badge.org_admin      { background: #38405A; color: #fff; }
.role-badge.treasurer      { background: #D95F02; color: #fff; }
.role-badge.member_manager { background: #EEF0F4; color: #4B5261; }

/* ── Rollen und Rechte: the permission matrix ──────────────────────────────────
   `styles.css` styles bare `table`, `th`, `td` and `tr:hover td` as the dark data
   grid, so this table has to UNDO all of that before adding anything. Every row
   rule carries the `table.perm-matrix` prefix on purpose: the reset below is
   (0,1,2) and would otherwise out-specify a bare `.pm-row td`, which silently
   flattens the padding to 0 and eats the row separators. Same shape as the
   existing table.notif-matrix. */
.perm-wrap { overflow-x: auto; }
table.perm-matrix {
  width: 100%; min-width: 660px; border-collapse: collapse;
  background: none; box-shadow: none; border-radius: 0; overflow: visible; margin-top: 0;
  table-layout: auto;
}
table.perm-matrix th, table.perm-matrix td { text-align: left; padding: 0; border: none; }
table.perm-matrix tr:hover td { background: transparent; }
table.perm-matrix thead th {
  background: none; font-size: 10.5px; font-weight: 700; color: #b2b2ba;
  text-transform: uppercase; letter-spacing: .3px;
  padding: 0 0 12px; border-bottom: 1px solid #f0f0f3; vertical-align: bottom;
}
table.perm-matrix thead th.pm-role {
  text-align: center; width: 132px; padding-left: 6px; padding-right: 6px;
  color: #38405A; font-size: 12.5px; letter-spacing: 0; text-transform: none;
}
table.perm-matrix .pm-group td {
  font-size: 10.5px; font-weight: 800; text-transform: uppercase; letter-spacing: .09em;
  color: #D95F02; padding: 26px 0 8px;
}
table.perm-matrix .pm-group.is-first td { padding-top: 16px; }
table.perm-matrix .pm-row td {
  padding: 12px 0; border-bottom: 1px solid #f4f4f7; vertical-align: middle;
}

.pm-name { font-size: 13.5px; font-weight: 600; color: #1A1A2E; display: flex; align-items: center; gap: 9px; flex-wrap: wrap; }
.pm-desc { font-size: 12px; color: #8B92A2; margin-top: 3px; line-height: 1.5; max-width: 64ch; }

/* "Diese Zeile weicht von der Voreinstellung ab." A dot, not a word: the (i) on
   the card explains it once, and eighteen rows do not need eighteen labels. The
   gap keeps the reset button off the dot, which otherwise reads as one two-part
   control rather than a state plus an action. */
.pm-marks { display: inline-flex; align-items: center; gap: 13px; }
.pm-dot {
  width: 7px; height: 7px; border-radius: 50%; background: #E0A020;
  flex: 0 0 auto; display: inline-block;
}
.pm-reset { display: none; }
.admin-editing .pm-reset { display: inline-flex; }

/* One cell. Read mode = an icon, edit mode = a checkbox, so a read-only matrix
   never renders as a grid of greyed-out inputs. */
table.perm-matrix td.pm-cell { text-align: center; padding-left: 6px; padding-right: 6px; }
table.perm-matrix td.pm-cell svg { width: 17px; height: 17px; }
.pm-yes  { color: #1B7A32; }
.pm-no   { color: #D2D4DC; }
.pm-lock { color: #9AA0AE; }
/* Both live on one class each, so the .admin-editing swap below can out-specify
   them. A `td.pm-cell .pm-read` selector here would win instead and the read
   icons would never hide in edit mode. */
.pm-read { display: inline-flex; align-items: center; }
.pm-edit { display: none; align-items: center; }
.admin-editing .pm-read { display: none; }
.admin-editing .pm-edit { display: inline-flex; }
.pm-edit input[type=checkbox] { width: 17px; height: 17px; cursor: pointer; accent-color: #D95F02; margin: 0; }

/* A reserved permission stays locked for every role but Super Admin, so this
   screen can never become a self-service route to full access. */
.pm-cell.is-reserved .pm-edit { display: none !important; }
.pm-cell.is-reserved .pm-read { display: inline-flex !important; }

.user-role-select {
  font-size: 13px;
  padding: 4px 8px;
  border: 1px solid #ddd;
  border-radius: 6px;
  background: #fff;
  cursor: pointer;
}

.finance-toggle {
  display: flex;
  align-items: center;
  gap: 8px;
  font-size: 13px;
  color: #555;
}
.finance-toggle input[type=checkbox] {
  width: 16px;
  height: 16px;
  cursor: pointer;
  accent-color: #D95F02;
}
.finance-toggle.disabled {
  opacity: 0.4;
  pointer-events: none;
}

.you-badge {
  display: inline-block;
  margin-left: 6px;
  padding: 1px 7px;
  border-radius: 20px;
  font-size: 10px;
  font-weight: 700;
  background: #D95F02;
  color: #fff;
  vertical-align: middle;
}

/* Inline-editable inputs inside the users table */
.editable-cell {
  border: 1px solid transparent;
  background: transparent;
  font-family: inherit;
  font-size: 14px;
  color: inherit;
  padding: 4px 6px;
  border-radius: 6px;
  width: 100%;
  box-sizing: border-box;
}
.editable-cell:hover  { border-color: #ddd; background: #fafafa; }
.editable-cell:focus  { outline: none; border-color: #D95F02; background: #fff; }

.admin-form-footer {
  grid-column: 1 / -1;
  display: flex;
  align-items: center;
  gap: 12px;
  margin-top: 4px;
}

/* ── Documents (Admin card + footer/gear quick links) ── */
.docs-admin-list { display: flex; flex-direction: column; gap: 8px; margin-bottom: 18px; }
.docs-admin-row {
  display: flex; align-items: center; justify-content: space-between; gap: 12px;
  padding: 10px 14px; border: 1px solid #e8e8ec; border-radius: 9px; background: #fafafb;
}
.docs-admin-main { display: flex; flex-direction: column; gap: 2px; min-width: 0; }
.docs-admin-label {
  display: inline-flex; align-items: center; gap: 7px;
  font-weight: 600; color: #1A1A2E; text-decoration: none; font-size: 14px;
}
.docs-admin-label:hover { color: #D95F02; }
.docs-admin-label svg { width: 16px; height: 16px; color: #888; flex-shrink: 0; }
.docs-admin-meta { font-size: 12px; color: #999; }
.docs-admin-actions { display: flex; align-items: center; gap: 12px; flex-shrink: 0; }
.docs-replace-btn { cursor: pointer; display: inline-flex; }
.docs-replace-btn svg { width: 16px; height: 16px; }

.docs-pin-toggle {
  display: inline-flex; align-items: center; gap: 6px;
  font-size: 12px; color: #666; cursor: pointer; white-space: nowrap;
}

.docs-upload { border-top: 1px solid #eee; padding-top: 18px; }
.docs-upload-title { font-size: 13px; font-weight: 700; color: #1A1A2E; margin: 0 0 12px; }
.docs-upload-row { display: flex; align-items: center; gap: 16px; flex-wrap: wrap; margin-top: 12px; }
/* Footer quick links (desktop) — class beats the element-level `footer a` colour */
.footer-docs { display: inline-flex; align-items: center; gap: 14px; }
.footer-doc-link {
  display: inline-flex; align-items: center; gap: 5px;
  color: rgba(255,255,255,0.7); text-decoration: none;
}
.footer-doc-link:hover { color: #D95F02; }
.footer-doc-link svg { width: 13px; height: 13px; }

/* Gear-menu quick links — MOBILE-ONLY (desktop shows pinned docs in the
   footer); mobile.css flips .gear-docs back to visible. Small, like the
   version line; box-sizing keeps the hover fill inside the rounded menu
   (the .gear-row base overflowed). */
.gear-docs { display: none; margin-top: 2px; }
.gear-doc-link {
  display: flex; align-items: center; gap: 8px;
  box-sizing: border-box; width: 100%;
  padding: 6px 12px; border-radius: 8px;
  font-size: 12px; color: #9a9aa2; text-decoration: none;
}
.gear-doc-link svg { width: 14px; height: 14px; color: #b5b5bd; flex-shrink: 0; }
.gear-doc-link:hover { background: #f3f4f6; color: #1A1A2E; }
.gear-doc-link:hover svg { color: #555; }

/* ── askDSI document chat (Help page) ── */
/* Theme: DSI orange accent + the AI "sparkle" icon in DSI navy on an orange
   avatar — on-brand (orange/navy) and unmistakably AI (the sparkle). */
.askchat {
  --ai-accent: #D95F02;       /* DSI orange */
  --ai-ink: #1A1A2E;          /* DSI navy   */
  --ai-tint: #fff6ef;         /* light orange wash for bot bubbles/chips */
  display: flex; flex-direction: column;
  border: 1px solid #f0e0d2; border-radius: 14px; overflow: hidden;
  background: #fff; margin: 14px 0 6px;
}
.askchat-header {
  display: flex; align-items: center; gap: 10px;
  padding: 12px 16px; border-bottom: 1px solid #f3e7dc;
  background: linear-gradient(135deg, #fff6ef 0%, #fffaf6 100%);
}
.askchat-ava {
  width: 30px; height: 30px; border-radius: 50%; flex-shrink: 0;
  background: var(--ai-accent); color: var(--ai-ink);
  display: flex; align-items: center; justify-content: center;
}
.askchat-ava svg { width: 18px; height: 18px; }
.askchat-id { display: flex; flex-direction: column; line-height: 1.25; flex: 1; min-width: 0; }
.askchat-name { font-weight: 700; color: #1A1A2E; font-size: 14px; }
.askchat-sub { font-size: 11px; color: #999; }
.askchat-reset {
  background: none; border: 1px solid #d8d8de; border-radius: 7px;
  padding: 5px 12px; font-size: 12px; color: #666; cursor: pointer; flex-shrink: 0;
}
.askchat-reset:hover { background: #f0f0f3; color: #1A1A2E; }

.askchat-messages {
  display: flex; flex-direction: column;
  padding: 16px; min-height: 340px; max-height: min(60vh, 520px);
  overflow-y: auto; background: #fff;
}
/* Bottom-orient: the feed sticks to the bottom (margin-top:auto), so short
   chats sit near the input. When it overflows, the auto-margin collapses and
   scrolling reaches the top normally. */
.askchat-feed { margin-top: auto; display: flex; flex-direction: column; gap: 12px; }
.askchat-row { display: flex; gap: 8px; max-width: 85%; }
.askchat-row.user { align-self: flex-end; flex-direction: row-reverse; }
.askchat-row.bot, .askchat-row.error { align-self: flex-start; }
.askchat-bubble {
  padding: 10px 14px; border-radius: 14px; font-size: 14px; line-height: 1.55;
  white-space: pre-wrap; word-break: break-word;
}
.askchat-row.user  .askchat-bubble { background: #1A1A2E; color: #fff; border-bottom-right-radius: 4px; }
.askchat-row.bot   .askchat-bubble { background: var(--ai-tint); color: #1A1A2E; border-left: 3px solid var(--ai-accent); border-bottom-left-radius: 4px; }
.askchat-row.error .askchat-bubble { background: #FFF5F5; color: #a13030; border-left: 3px solid #c0392b; border-bottom-left-radius: 4px; }
.askchat-bava {
  width: 24px; height: 24px; border-radius: 50%; flex-shrink: 0; align-self: flex-end;
  background: var(--ai-accent); color: var(--ai-ink);
  display: flex; align-items: center; justify-content: center;
}
.askchat-bava svg { width: 14px; height: 14px; }

/* empty state */
.askchat-empty { display: flex; flex-direction: column; gap: 12px; width: 100%; }
.askchat-chips { display: flex; flex-wrap: wrap; gap: 8px; padding-left: 32px; }
.askchat-chip {
  border: 1px solid #f5d9c2; background: var(--ai-tint); color: #b4521a;
  border-radius: 16px; padding: 7px 14px; font-size: 13px; cursor: pointer; text-align: left;
}
.askchat-chip:hover { background: #fdebdd; }

/* typing indicator */
.askchat-typing { display: inline-flex; gap: 4px; align-items: center; padding: 2px 0; }
.askchat-typing span { width: 6px; height: 6px; border-radius: 50%; background: var(--ai-accent); animation: askblink 1.2s infinite; }
.askchat-typing span:nth-child(2) { animation-delay: .2s; }
.askchat-typing span:nth-child(3) { animation-delay: .4s; }
@keyframes askblink { 0%, 60%, 100% { opacity: .25; } 30% { opacity: 1; } }

.askchat-inputbar {
  display: flex; align-items: flex-end; gap: 8px;
  padding: 10px 12px; border-top: 1px solid #eee; background: #fafafb;
}
.askchat-input {
  flex: 1; box-sizing: border-box; resize: none; overflow-y: auto;
  border: 1px solid #d8d8de; border-radius: 12px; padding: 10px 14px;
  font-family: inherit; font-size: 14px; line-height: 1.4; max-height: 120px; color: #1A1A2E;
}
.askchat-input:focus { outline: none; border-color: var(--ai-accent); }
.askchat-send {
  flex-shrink: 0; width: 40px; height: 40px; border-radius: 50%; border: none;
  background: var(--ai-accent); color: #fff; cursor: pointer;
  display: flex; align-items: center; justify-content: center;
}
.askchat-send:hover { filter: brightness(1.12); }
.askchat-send:disabled { background: #cdd3d8; filter: none; cursor: not-allowed; }
.askchat-send svg { width: 18px; height: 18px; }

.doc-ask-hint { display: block; font-size: 12px; color: #999; margin-top: 8px; }
.doc-ask-hint.warn { color: #B45309; }
/* id selector — beats `.help-section p` (class+element) which was forcing 14px. */
#askPrivacy { font-size: 10px; font-weight: 600; color: #b6b6b6; line-height: 1.5; margin-top: 6px; }

/* ── askDSI as a messenger, and the shape is the same at every width ─────────
   While #help-ai is the active section the chat stops being a card parked on a
   page and becomes a pane: the header pins to the top, the feed scrolls, and
   the input plus the two disclaimer lines dock at the bottom. Only the SIZING
   differs per breakpoint and lives in mobile.css, because only that part has to
   know where the pane's edges are: position:fixed against the viewport on a
   phone, a calc() height inside the content column on the desktop. The shape
   itself is here, once, since the two used to be separate rule sets aiming at
   the same result and the desktop half kept drifting off it.

   Gated on the plain `#help-ai.active` class and never on an ancestor: that is
   the same mechanism that shows and hides these sections, so nothing can fall
   out of sync with it, and it needs no :has() and no JS. */
#page-help #help-ai.active { display: flex; flex-direction: column; background: #fff; }
/* the box drops its card chrome and fills the pane */
#page-help #help-ai.active .askchat {
  flex: 1; min-height: 0; margin: 0;
  border: none; border-radius: 0;
}
#page-help #help-ai.active .askchat-messages { flex: 1; min-height: 0; max-height: none; }
#page-help #help-ai.active .askchat-header,
#page-help #help-ai.active .askchat-inputbar,
#page-help #help-ai.active .doc-ask-hint,
#page-help #help-ai.active .doc-ask-privacy { flex-shrink: 0; }
/* A pane is as wide as the window and a line of text must not be: at 1920 the
   85% bubble would run about 1360px. Bubbles, input field and disclaimer sit in
   one centred 860px column, while the header, the input bar's background and
   its top border stay full width so the pane still reads as one surface. Done
   with padding rather than a max-width on the bar itself, which would cut that
   border short. No effect on a phone, where the pane is the narrower of the two. */
/* width:100% is NOT redundant next to max-width. The feed is a flex item of a
   column container, so it would normally stretch to full width, but an auto
   margin in the cross axis turns stretching off and sizes it to its CONTENT
   instead. Without the explicit width the column came out as wide as the
   longest bubble (644px) and drifted with the conversation. */
#page-help #help-ai.active .askchat-feed { width: 100%; max-width: 860px; margin-inline: auto; }
#page-help #help-ai.active .askchat-inputbar,
#page-help #help-ai.active .doc-ask-hint,
#page-help #help-ai.active .doc-ask-privacy {
  padding-inline: max(14px, calc((100% - 860px) / 2));
}
#page-help #help-ai.active .doc-ask-hint,
#page-help #help-ai.active .doc-ask-privacy {
  margin: 0; padding-top: 4px; background: #fff;
}
#page-help #help-ai.active .doc-ask-privacy { padding-bottom: 8px; }

/* ── Shared table cell utilities ────────────────── */
.tbl-cell     { padding: 9px 10px; border-bottom: 1px solid #f0f0f0; }
.tbl-cell-amt { padding: 9px 10px; border-bottom: 1px solid #f0f0f0; font-weight: 600; color: #2E7D32; }
.tbl-cell-act { padding: 9px 10px; border-bottom: 1px solid #f0f0f0; white-space: nowrap; }

/* ── Shared text utilities ──────────────────────── */
.amt-positive { font-weight: 600; color: #2E7D32; }
.amt-blue     { font-weight: 600; color: #1565C0; }
.fw-bold      { font-weight: 600; }

/* ── Email variable chips ───────────────────────── */
.var-chip {
  background: #f0f0f0;
  border: 1px solid #ddd;
  border-radius: 4px;
  padding: 2px 7px;
  font-size: 11px;
  cursor: pointer;
  font-family: monospace;
  color: #555;
  user-select: none;
  transition: background 0.12s, color 0.12s;
}
.var-chip:hover { background: #e2e2e2; color: #1A1A2E; }

/* ── Finance table polish (Type column removed, no emojis, dot status) ── */

/* ── Transaction table column widths ─────────────────────────────
   The global table rule sets table-layout: fixed, so percentage
   widths on the first row's <th> cells are strict and they all sum
   to 100% — the table always fits its container exactly. Order:
   Date, Amount, Method, From/To, Note, Status, Action. */
#txTable             { font-size: 13px; }
#txTable .col-date    { width: 10%; white-space: nowrap; }
#txTable .col-amount  { width: 10%; white-space: nowrap; }
#txTable .col-method  { width: 10%; white-space: nowrap; }
#txTable .col-fromto  { width: 18%; }
#txTable .col-note    { width: 34%; }    /* widest */
#txTable .col-status  { width: 5%;  text-align: center; padding: 12px 6px; }
#txTable .col-action  { width: 13%; white-space: nowrap; }

/* Section header bar — sits above an .admin-card and outside its border.
   Used when .admin-section-cards is on the parent. */
.section-header-bar {
  display: flex;
  align-items: center;
  justify-content: space-between;
  margin-bottom: 14px;
}

/* Status dot — title attribute gives the word ("Paid" / "Pending") on hover */
.status-dot {
  display: inline-block; width: 10px; height: 10px; border-radius: 50%;
  vertical-align: middle;
}
.status-dot.status-paid    { background: #2E7D32; }
.status-dot.status-pending { background: #F59E0B; }

/* Long text cells (Note + From/To) truncate to one line with ellipsis;
   full text shown in a hover-tooltip (.note-tooltip, below). */
.col-note   .note-cell,
.col-fromto .fromto-cell {
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
  cursor: default;
}

/* Hover tooltip for note cells — text-selectable so users can copy. */
.note-tooltip {
  position: absolute;
  display: none;
  background: white;
  border: 1px solid #ddd;
  border-radius: 6px;
  box-shadow: 0 4px 16px rgba(0,0,0,0.15);
  padding: 10px 14px;
  font-size: 13px;
  color: #1A1A2E;
  max-width: 480px;
  z-index: 250;
  user-select: text;
  word-break: break-word;
  line-height: 1.4;
}
.note-tooltip.active { display: block; }

/* ── Tickets / Feedback ──────────────────────────── */

/* Nav lightbulb button + "new" count badge */
.nav-tickets-btn { position: relative; }
.nav-tickets-btn svg { width: 15px; height: 15px; }
.nav-tickets-badge {
  position: absolute; top: -5px; right: -5px;
  min-width: 15px; height: 15px; padding: 0 4px;
  border-radius: 8px; background: #D95F02; color: #fff;
  font-size: 9px; font-weight: 700; line-height: 15px; text-align: center;
  box-shadow: 0 0 0 2px #1A1A2E;
}

/* ── Notification bell + dropdown feed (matches prototypes/notifications.html) ── */
.nav-bell-wrap { position: relative; display: inline-flex; }
.nav-bell-btn { position: relative; }
.nav-bell-btn svg { width: 16px; height: 16px; }

.nav-bell-feed {
  position: absolute; top: calc(100% + 12px); right: 0;
  width: 360px; max-width: 92vw;
  background: #fff; color: #1A1A2E;
  border-radius: 12px; box-shadow: 0 12px 40px rgba(0,0,0,.22);
  overflow: hidden; display: none; z-index: 300; /* same tier as the gear/GDPR dropdowns */
}
.nav-bell-feed.open { display: block; }
.bell-feed-head {
  display: flex; align-items: center; justify-content: space-between;
  padding: 14px 16px; border-bottom: 1px solid #eee;
}
.bell-feed-head h3 { margin: 0; font-size: 15px; font-weight: 700; }
.bell-feed-head button {
  background: none; border: none; color: #D95F02; font-size: 12px; font-weight: 600;
  cursor: pointer; font-family: inherit; padding: 2px 4px; border-radius: 5px;
}
.bell-feed-head button:hover { background: #fff6ef; }
.bell-feed-head button:disabled { color: #bbb; cursor: default; background: none; }
.bell-feed-list { max-height: 380px; overflow-y: auto; }
.bell-feed-item {
  padding: 13px 16px 13px 18px; border-bottom: 1px solid #f2f2f2;
  position: relative;
}
.bell-feed-item { cursor: pointer; }
.bell-feed-item:hover { background: #fafafa; }
.bell-feed-item:focus-visible { outline: 2px solid #D95F02; outline-offset: -2px; }
.bell-feed-item.unread { background: #fff6ef; }
.bell-feed-item.unread::before {
  content: ''; position: absolute; left: 0; top: 0; bottom: 0; width: 3px; background: #E8662A;
}
.bell-feed-item:last-child { border-bottom: none; }
.bell-fi-title { font-size: 13.5px; line-height: 1.35; word-break: break-word; }
.bell-feed-item.unread .bell-fi-title { font-weight: 700; }
.bell-fi-body { font-size: 12.5px; color: #666; line-height: 1.4; margin-top: 2px;
  white-space: pre-wrap; word-break: break-word;
  display: -webkit-box; -webkit-line-clamp: 2; -webkit-box-orient: vertical; overflow: hidden; }
.bell-fi-time { font-size: 11.5px; color: #999; margin-top: 3px; }
.bell-feed-empty { padding: 34px 16px; text-align: center; color: #999; font-size: 13px; }

/* ── Notification preferences matrix (My Account → Benachrichtigungen) ── */
/* ── My Account page — desktop layout ─────────────────────────────────
   Was a narrow centered max-width:480 column (read like the phone layout
   on desktop). Now a wider, centered 2-column card grid: left = account /
   sign-in / security, right = preferences. Cards reuse .admin-card; titles
   use .admin-card-title (the app's card type scale). Collapses to one
   column on narrow screens (mobile.css). */
#page-account .acct-page { max-width: 1060px; margin: 0 auto; }
/* This page deliberately carries NO title-margin override any more (2026-08-02).
   It used to need three: `#page-account .admin-card-title { margin: 0 0 18px }` for
   room before the card content, plus two more to undo that again for the titles that
   shared their line with an (i). All six cards now open with a real .admin-card-head,
   which brings its own 18px below itself, so the shared
   `.admin-card-head-text .admin-card-title { margin: 0 }` is correct here and the
   spacing under the title is unchanged.
   Do not reinstate the 18px. Because it was written with an id it outranked the shared
   rule, so the h3 kept an 18px bottom margin inside the head; `align-items: center`
   then centred a 38px MARGIN box against a 20px line of text and every title on this
   page rendered exactly 9px high. That is the same failure the old comment here warned
   about for the (i) row, reintroduced from the other side. */
.acct-grid { display: grid; grid-template-columns: 1fr 1fr; gap: 24px; align-items: start; }
/* min-width:0 = grid hygiene: lets a column shrink below its content's
   intrinsic min so the matrix's overflow-x:auto wrap scrolls instead of
   widening the whole layout on a narrow viewport. */
.acct-col { display: flex; flex-direction: column; gap: 24px; min-width: 0; }
.acct-name-row { display: flex; gap: 10px; align-items: flex-end; }
.acct-name-row .fq-field { flex: 1; margin: 0; }
.acct-pw-fields { display: flex; flex-direction: column; gap: 12px; }
.acct-prefs { font-size: 14px; color: #555; line-height: 1.8; }
/* „PIN speichern" on the Bankzugang card: label and box on one baseline, so the
   sentence reads as a sentence rather than as a form field. */
.acct-bank-check { display: flex; align-items: center; gap: 8px; font-size: 13px; color: #555; }
.acct-bank-check input { margin: 0; }
/* One person's Zugang in the admin overview: state on the left, the remove action on
   the right, calm rows rather than a table for what is usually one or two entries. */
.user-access-row { display: flex; align-items: center; justify-content: space-between; gap: 12px;
                   padding: 10px 0; border-bottom: 1px solid #f0f0f0; }
.user-access-row:last-child { border-bottom: none; }
.user-access-who { font-size: 14px; color: #1A1A2E; font-weight: 600; }
.user-access-sub { font-size: 12px; color: #888; margin: 2px 0 0; }
.user-access-empty { font-size: 13px; color: #888; margin: 0; }
/* Inputs fill their field exactly (border-box) so they never overflow the
   card on a narrow phone — .fq-field input has no box-sizing of its own. */
#page-account .fq-field input { width: 100%; box-sizing: border-box; }

/* ── Notification settings matrix (My Account) ──
   A calm, borderless settings list on the account card: labels left, three
   right-aligned checkbox columns flush to the card's right border. It's an HTML
   <table>, so it explicitly opts out of the global data-table chrome (shadow/
   rounded box, navy headers, row borders + hover) meant for Members/Finance. */
.notif-matrix-wrap { min-width: 0; }
table.notif-matrix {
  width: 100%; min-width: 360px; border-collapse: collapse;
  background: none; box-shadow: none; border-radius: 0; overflow: visible; margin-top: 0;
}
table.notif-matrix th, table.notif-matrix td { text-align: left; padding: 0; border: none; }
table.notif-matrix tr:hover td { background: transparent; }

/* Muted hairline header; channel columns right-aligned (the "symmetry"). */
table.notif-matrix thead th {
  background: none; font-size: 10.5px; font-weight: 600; color: #b2b2ba;
  text-transform: uppercase; letter-spacing: .3px;
  padding: 0 0 16px; border-bottom: 1px solid #f0f0f3;
}
table.notif-matrix thead th.ch { width: 56px; }
table.notif-matrix th.ch, table.notif-matrix td.ch { text-align: right; }

/* Rows + labels. */
.notif-ev-row td { padding: 15px 0; vertical-align: middle; }
.notif-ev-label { font-size: 13.5px; font-weight: 500; color: #3c3c4a; }

/* Flat custom checkbox — native controls render with shadows + grey disabled
   fills in mobile browsers; appearance:none gives one crisp look everywhere. */
table.notif-matrix td.ch input[type=checkbox] {
  appearance: none; -webkit-appearance: none;
  width: 18px; height: 18px; margin: 0; padding: 0;
  border: 1.5px solid #ccccd4; border-radius: 5px; background: #fff;
  cursor: pointer; position: relative; vertical-align: middle;
  transition: background .12s ease, border-color .12s ease;
}
table.notif-matrix td.ch input[type=checkbox]:hover:not(:disabled) { border-color: #D95F02; }
table.notif-matrix td.ch input[type=checkbox]:checked { background: #D95F02; border-color: #D95F02; }
table.notif-matrix td.ch input[type=checkbox]:checked::after {
  content: ""; position: absolute; left: 5.5px; top: 1.5px;
  width: 4px; height: 9px; border: solid #fff; border-width: 0 2px 2px 0;
  transform: rotate(45deg);
}
table.notif-matrix td.ch input[type=checkbox]:focus-visible {
  outline: 2px solid rgba(217,95,2,.45); outline-offset: 1px;
}
/* Locked cells (In-App forced on, or push off on this device): muted. */
.notif-ch-locked { opacity: .4; }
.notif-ch-locked input[type=checkbox] { cursor: not-allowed; }

/* Push device opt-in control (under the matrix, My Account). Empty until rendered,
   so only reserve space when it actually holds a button/hint. */
.push-ctrl:not(:empty) { margin-top: 18px; }
.push-ctrl-hint { color: #9a9aa2; font-size: 12px; line-height: 1.5; margin: 0; }

/* Small hint under the composer — left-aligned to the composer's edge */
.tk-hint { color: #9a9aa2; font-size: 11px; margin: 10px auto 64px; max-width: 680px; text-align: left; }

/* Composer-first hero: fills the first screenful so the table reveals on scroll.
   100px ≈ page top padding (40) + the h1 above. Vertically centres the composer. */
.tk-hero {
  min-height: calc(100vh - var(--nav-height) - 100px);
  display: flex; flex-direction: column; justify-content: center;
}

/* Composer column — owns the width so the card and the action bar align */
.tk-composer { max-width: 680px; margin: 0 auto; width: 100%; }

/* Compose card — holds the text only; lifted off the page with a soft shadow */
.tk-compose {
  background: #fff; border: 1px solid #f0f0f4; border-radius: 10px;
  padding: 14px 16px; margin: 0 0 10px;
  box-shadow: 0 6px 24px rgba(26, 26, 46, 0.09);
}
.tk-compose-title {
  width: 100%; border: none; outline: none;
  font-size: 15px; font-weight: 600; color: #1A1A2E;
  padding: 2px 0; box-sizing: border-box;
}
.tk-compose-title::placeholder { color: #b8b8c0; font-weight: 500; }
.tk-compose-body {
  width: 100%; border: none; outline: none; resize: vertical;
  min-height: 96px; margin-top: 4px; padding: 8px 0 4px;
  font-family: 'Segoe UI', Arial, sans-serif; font-size: 14px;
  color: #333; line-height: 1.6; box-sizing: border-box;
  border-top: 1px solid #f1f1f4;
}
.tk-compose-body::placeholder { color: #b8b8c0; }
.tk-compose-bar {
  display: flex; align-items: center; justify-content: space-between;
  gap: 10px; margin: 0; flex-wrap: wrap;
}
.tk-compose-left { display: flex; align-items: center; gap: 8px; flex-wrap: wrap; }
.tk-type-select {
  border: 1px solid #e2e2e8; border-radius: 7px; padding: 6px 9px;
  font-size: 13px; color: #444; background: #fff; cursor: pointer; outline: none;
}
.tk-type-select:focus { border-color: #D95F02; }
/* Icon-only attachment button (paperclip), squared to match the type select height */
.tk-shot-btn {
  display: inline-flex; align-items: center; justify-content: center;
  border: 1px solid #e2e2e8; border-radius: 7px; padding: 7px;
  color: #666; cursor: pointer; transition: all 0.15s;
}
.tk-shot-btn svg { width: 16px; height: 16px; }
.tk-shot-btn:hover { border-color: #D95F02; color: #D95F02; }
/* Smaller, flatter submit button inside the composer */
.tk-compose .btn-add { padding: 7px 18px; font-size: 13px; border-radius: 7px; }

.tk-shot-preview {
  display: flex; align-items: center; gap: 10px;
  margin-top: 10px; padding: 7px; border: 1px solid #f1f1f4;
  border-radius: 7px; background: #fafafb;
}
.tk-shot-thumb { height: 36px; width: 36px; object-fit: cover; border-radius: 5px; }
.tk-shot-name  { font-size: 12px; color: #666; flex: 1; word-break: break-all; }
.tk-shot-remove {
  border: none; background: transparent; color: #b34d00;
  font-size: 14px; cursor: pointer; line-height: 1; padding: 4px;
}

/* Table — inherits the app's standard table styling (dark-navy header,
   white card, shadow) for consistency with Members/Finance. `.tk-table-wrap`
   is a plain no-op container (no rule needed); only per-cell refinements live here. */
/* Column widths — the table is table-layout:fixed, so without these the 8
   columns split evenly and Title gets cramped. Title (col 2) takes the rest. */
#ticketsTable th:nth-child(1) { width: 84px; }   /* Type */
#ticketsTable th:nth-child(3) { width: 124px; }  /* Status */
#ticketsTable th:nth-child(4) { width: 108px; }  /* Priority */
#ticketsTable th:nth-child(5) { width: 150px; }  /* From */
#ticketsTable th:nth-child(6) { width: 118px; }  /* Created */
#ticketsTable th:nth-child(7) { width: 118px; }  /* Updated */
#ticketsTable th:nth-child(8) { width: 132px; }  /* Actions */
.tk-title-cell { font-weight: 400; }
/* Action buttons sit at the right of their column, padded off the border. */
.tk-action-cell { text-align: right; }
.tk-date-cell { color: #9a9aa2; font-size: 13px; white-space: nowrap; }
.tk-muted { color: #c4c4cc; }
/* Attachment link reuses .btn-notes (bordered icon) for app consistency;
   only needs the underline removed since it's an <a>. */
.tk-attach-link { text-decoration: none; }
.tk-desc-text { font-size: 13px; color: #555; line-height: 1.6; white-space: pre-wrap; }

/* Inline admin triage selects (status / priority) */
.tk-inline-select {
  width: 100%; border: 1px solid #e2e2e8; border-radius: 6px;
  padding: 5px 7px; font-size: 13px; color: #444;
  background: #fff; cursor: pointer; outline: none;
  font-family: 'Segoe UI', Arial, sans-serif;
}
.tk-inline-select:focus { border-color: #D95F02; }

/* Inline edit panel (creator / admin) inside the expanded description row */
.tk-edit { display: flex; flex-direction: column; gap: 10px; }
.tk-edit-title {
  width: 100%; border: 1px solid #e2e2e8; border-radius: 7px;
  padding: 8px 10px; font-size: 14px; font-weight: 600; color: #1A1A2E;
  box-sizing: border-box; outline: none; font-family: 'Segoe UI', Arial, sans-serif;
}
.tk-edit-title:focus { border-color: #D95F02; }
.tk-edit-desc {
  width: 100%; border: 1px solid #e2e2e8; border-radius: 7px;
  padding: 8px 10px; font-size: 13px; color: #444; line-height: 1.6;
  min-height: 90px; resize: vertical; box-sizing: border-box; outline: none;
  font-family: 'Segoe UI', Arial, sans-serif;
}
.tk-edit-desc:focus { border-color: #D95F02; }
.tk-edit-actions { display: flex; justify-content: flex-end; }
.tk-edit .btn-add { padding: 7px 18px; font-size: 13px; border-radius: 7px; }

/* Quiet, flat pills */
.tk-badge {
  display: inline-block; padding: 2px 8px; border-radius: 5px;
  font-size: 11px; font-weight: 600; white-space: nowrap; letter-spacing: 0.2px;
}
.tk-type-bug      { background: #fdecea; color: #c0392b; }
.tk-type-feature  { background: #eaf5ec; color: #2e7d32; }
.tk-type-other    { background: #eef1f8; color: #3949ab; }
.tk-status-new         { background: #fff3e0; color: #b45309; }
.tk-status-in_progress { background: #e7f1fb; color: #1565c0; }
.tk-status-done        { background: #eaf5ec; color: #2e7d32; }
.tk-pri-low    { background: #f2f2f4; color: #777; }
.tk-pri-normal { background: #fff3e0; color: #b45309; }
.tk-pri-high   { background: #fdecea; color: #c0392b; }


/* Mobile compact-card views for the tables live in mobile.css. */

/* ════════════════════════════════════════════════════════════════
   Unified table control bar (.ctrl-bar) — ONE component for both
   desktop and mobile, above the Members and Transactions tables.
   Layout: search (left) · Filter/Sort tools · spacer · actions (right).
   Desktop shows button labels; phones collapse to compact icons.
   ════════════════════════════════════════════════════════════════ */
.ctrl-bar {
  display: flex; align-items: center; flex-wrap: wrap;
  gap: 8px; margin: 16px 0 14px;
}
.ctrl-search {
  flex: 0 1 280px; min-width: 0;
  padding: 9px 12px; border: 1px solid #ddd; border-radius: 9px;
  font-size: 14px; font-family: inherit; box-sizing: border-box;
}
.ctrl-search:focus { outline: none; border-color: #D95F02; }
.ctrl-spacer { flex: 1 1 auto; }                 /* pushes actions to the right */
.ctrl-pop-wrap { position: relative; flex: 0 0 auto; }

/* Filter / Sort trigger buttons */
.ctrl-btn {
  display: flex; align-items: center; gap: 6px;
  height: 38px; padding: 0 12px;
  background: #fff; border: 1px solid #ddd; border-radius: 9px;
  font-family: inherit; font-size: 13px; font-weight: 600; color: #444;
  cursor: pointer; white-space: nowrap;
}
.ctrl-btn:hover { border-color: #D95F02; color: #D95F02; }
.ctrl-btn svg { width: 16px; height: 16px; }
.ctrl-badge {
  min-width: 16px; height: 16px; padding: 0 4px;
  border-radius: 8px; background: #D95F02; color: #fff;
  font-size: 10px; font-weight: 700; line-height: 16px; text-align: center;
}
.ctrl-arrow {
  flex: 0 0 auto; width: 38px; height: 38px;
  border: 1px solid #ddd; border-radius: 9px; background: #fff;
  cursor: pointer; font-size: 15px; color: #555;
}
.ctrl-arrow:hover { border-color: #D95F02; color: #D95F02; }

/* Action buttons */
.ctrl-add {
  display: flex; align-items: center; gap: 6px;
  height: 38px; padding: 0 16px;
  background: #D95F02; color: #fff; border: none; border-radius: 9px;
  font-family: inherit; font-size: 13px; font-weight: 600; cursor: pointer;
  white-space: nowrap;
}
.ctrl-add:hover { background: #B34D00; }
.ctrl-add .ctrl-add-icon { display: none; }      /* desktop shows the label */
/* Popovers (Filter checkboxes + Sort options) */
.ctrl-pop {
  display: none;
  position: absolute; top: calc(100% + 6px); left: 0;
  min-width: 200px; max-height: 72vh; overflow-y: auto;
  background: #fff; border-radius: 10px;
  box-shadow: 0 8px 24px rgba(0,0,0,0.22);
  padding: 8px; z-index: 60;
}
.ctrl-pop.open { display: block; }
/* A popover on the ACTION side of the bar (anything after .ctrl-spacer) opens
   LEFTWARD. Left-anchored it would hang off a button that already sits at the right
   edge, overflow the content area, and — being absolutely positioned with nothing
   clipping it — add horizontal scroll to the whole page. Written as a general
   sibling rule rather than a per-popover class so every future action-side popover
   inherits it. Phones right-anchor every popover already (mobile.css). */
.ctrl-spacer ~ .ctrl-pop-wrap .ctrl-pop { left: auto; right: 0; }
/* Escape hatch, set by JS when right-anchoring would instead overflow the LEFT edge
   (a wrapped control bar). Needs this specificity to beat the rule above. */
.ctrl-spacer ~ .ctrl-pop-wrap .ctrl-pop.ctrl-pop--left { left: 0; right: auto; }
.ctrl-pop-title {
  font-size: 11px; font-weight: 700; text-transform: uppercase;
  letter-spacing: 0.4px; color: #999; padding: 8px 8px 4px;
}
.ctrl-check {
  display: flex; align-items: center; gap: 10px;
  padding: 9px 8px; border-radius: 7px;
  font-size: 14px; color: #1A1A2E; cursor: pointer;
}
.ctrl-check input { width: 17px; height: 17px; accent-color: #D95F02; }
.ctrl-check:hover { background: #f4f4f6; }

/* ── Segment switch: one of a few, all of them visible ──────────────────────
   Lifted out of the EÜR rule editor's Art toggle on 2026-08-02, when a second
   caller wanted the same control. Living here rather than beside its first
   caller is the point: a shared component inside a feature's own block is how
   the next screen ends up with a copy of it.

   Use it instead of a `<select>` when there are two or three options and seeing
   them all is worth the width. Beyond that a select is still right.

   The segments are `<button>`s WITHOUT a `.btn-*` class, so the one-geometry
   rule for the text-button family does not reach them and the padding and font
   size here are the control's own, not a local override of that family.

   `.on` is the app's established chosen-state: the orange wash and orange ink
   that a selected Mandate status card already uses. A caller whose options
   carry their own meaning overrides it, the way `.rgl-seg` keeps green for
   Einnahme and red for Ausgabe. */
.seg {
  display: inline-flex; background: #fafafb;
  border: 1px solid #e6e6ec; border-radius: 9px; overflow: hidden;
}
.seg button {
  flex: 1; border: none; background: transparent; padding: 8px 14px;
  font-family: inherit; font-size: 12.5px; font-weight: 600;
  color: #9a9aa4; cursor: pointer; white-space: nowrap;
}
.seg button:hover { color: #1A1A2E; }
.seg button.on { background: #FFF8F2; color: #D95F02; }

/* ════════════════════════════════════════════════════════════════
   E-Mail-Composer (Verfassen-Tab) — Chip-Empfänger + Rich-Text.
   Adaptiert aus dem Claude-Design-Entwurf, auf die DSI-Marke gemappt
   (Orange #D95F02 / Navy #1A1A2E statt des Platzhalter-Blaus).
   ════════════════════════════════════════════════════════════════ */
.composer-card {
  background: #fff;
  border: 1px solid #e0e0e0;
  border-radius: 12px;
  box-shadow: 0 6px 24px rgba(26,26,46,0.08);
  /* Fill the full content column (like every other page) — no narrow cap. */
  width: 100%;
  display: flex;
  flex-direction: column;
}

/* Zeilen (Vorlage / An / Betreff) */
.composer-row {
  display: flex;
  align-items: flex-start;
  gap: 12px;
  padding: 12px 20px;
  border-bottom: 1px solid #f0f0f0;
}
.composer-row--center { align-items: center; }
.composer-row-label {
  font-size: 13px;
  color: #888;
  line-height: 32px;
  min-width: 64px;
  flex-shrink: 0;
}
.composer-inline-select {
  border: none;
  background: transparent;
  font-family: inherit;
  font-size: 14px;
  color: #1A1A2E;
  padding: 6px 0;
  cursor: pointer;
  outline: none;
  flex: 1;
}

/* Vorlagen-Chips (anklickbar; aktive = gefüllt orange) */
.composer-tmpl-chips {
  flex: 1;
  display: flex;
  flex-wrap: wrap;
  gap: 6px;
  align-items: center;
  min-height: 32px;
  min-width: 0;
}
.composer-tmpl-empty { font-size: 13px; color: #b8b8b8; line-height: 32px; }
.composer-tmpl-chip {
  height: 28px;
  padding: 0 12px;
  border-radius: 999px;
  border: 1px solid #ddd;
  background: #fff;
  color: #555;
  font-family: inherit;
  font-size: 13px;
  font-weight: 500;
  cursor: pointer;
  transition: background-color 0.12s, border-color 0.12s, color 0.12s;
}
.composer-tmpl-chip:hover { background: #fff6ef; border-color: #F2C9A3; }
.composer-tmpl-chip--active { background: #D95F02; border-color: #D95F02; color: #fff; }
.composer-subject-input {
  flex: 1;
  border: none;
  outline: none;
  background: transparent;
  font-family: inherit;
  font-size: 15px;
  font-weight: 500;
  color: #1A1A2E;
  padding: 6px 0;
}
.composer-subject-input::placeholder { color: #b8b8b8; font-weight: 400; }

/* An-Zeile: Empfänger-Button links + Auswahl-Zusammenfassung daneben */
.composer-recipient-row { position: relative; }
.composer-recipient-main {
  flex: 1;
  display: flex;
  align-items: center;
  gap: 12px;
  min-width: 0;
  position: relative;   /* Anker für das Dropdown + die Auswahl-Liste */
}
.composer-recipient-summary {
  font-size: 14px;
  color: #1A1A2E;
  min-width: 0;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}
.composer-recipient-empty { color: #b8b8b8; }
.composer-recipient-name { font-weight: 500; }

/* Rundmail-Badge (Navy, ab 2 Empfängern) */
.rundmail-badge {
  display: inline-flex;
  align-items: center;
  gap: 5px;
  height: 26px;
  padding: 0 10px;
  border: none;
  border-radius: 999px;
  background: #1A1A2E;
  color: #fff;
  font-family: inherit;
  font-size: 12px;
  font-weight: 600;
  white-space: nowrap;
  cursor: pointer;
  transition: background-color 0.12s;
}
.rundmail-badge:hover { background: #2a2a44; }

/* Empfänger-Button */
.empf-btn {
  display: inline-flex;
  align-items: center;
  gap: 7px;
  height: 32px;
  padding: 0 12px;
  font-family: inherit;
  font-size: 13px;
  font-weight: 600;
  color: #D95F02;
  background: #fff;
  border: 1px solid #ddd;
  border-radius: 8px;
  cursor: pointer;
  transition: background-color 0.12s, border-color 0.12s;
}
.empf-btn:hover,
.empf-btn[aria-expanded="true"] { background: #fff6ef; border-color: #F2C9A3; }
.empf-chev { transition: transform 0.16s ease; }
.empf-btn[aria-expanded="true"] .empf-chev { transform: rotate(180deg); }

/* Empfänger-Dropdown-Panel — öffnet links unter dem Empfänger-Button */
.empf-panel {
  position: absolute;
  top: calc(100% + 4px);
  left: 0;
  right: auto;
  /* Relative to the recipient area (positioned ancestor), so the right edge
     stays inside the card/viewport no matter how far right the button sits.
     Using 100vw here was the bug — it ignored the panel's left offset. */
  width: min(460px, 100%);
  background: #fff;
  border: 1px solid #e0e0e0;
  border-radius: 12px;
  box-shadow: 0 8px 28px rgba(26,26,46,0.16);
  z-index: 40;
  overflow: hidden;
}
/* Suche + Typ-Filter auf einer Zeile (minimalistisch). */
.empf-panel-filters {
  display: flex;
  gap: 8px;
  padding: 14px 16px;
  border-bottom: 1px solid #f0f0f0;
}
.empf-search { flex: 1; position: relative; min-width: 0; }
.empf-type-select { flex: 0 0 150px; }
.empf-search svg {
  position: absolute; left: 10px; top: 50%; transform: translateY(-50%);
  color: #b8b8b8; pointer-events: none;
}
.empf-input {
  width: 100%;
  height: 38px;
  padding: 0 10px;
  border: 1px solid #ddd;
  border-radius: 6px;
  font-family: inherit;
  font-size: 14px;
  color: #1A1A2E;
  background: #fff;
  outline: none;
  box-sizing: border-box;
}
.empf-input:focus { border-color: #D95F02; }
.empf-search .empf-input { padding-left: 34px; }
select.empf-input { cursor: pointer; }

.empf-panel-list { max-height: 110px; overflow-y: auto; padding: 8px 0; }
.empf-member {
  display: flex;
  align-items: center;
  gap: 12px;
  padding: 7px 16px;
  cursor: pointer;
  transition: background-color 0.1s;
}
.empf-member:hover { background: #faf7f4; }
.empf-member input[type="checkbox"] {
  width: 16px; height: 16px; accent-color: #D95F02; cursor: pointer; flex-shrink: 0; margin: 0;
}
.empf-member__name {
  flex: 1; font-size: 14px; color: #1A1A2E;
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.empf-member__name--noemail { color: #b8b8b8; }
.empf-member__meta { font-size: 12px; color: #aaa; flex-shrink: 0; }
.empf-panel-empty { padding: 24px 16px; text-align: center; font-size: 14px; color: #888; }
/* One tidy line: [N badge] … Alle wählen/abwählen  [✓] */
.empf-panel-footer {
  display: flex;
  align-items: center;
  gap: 10px;
  padding: 10px 16px;
  border-top: 1px solid #f0f0f0;
  background: #faf7f4;
}
.empf-count-badge {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  min-width: 22px;
  height: 22px;
  padding: 0 7px;
  border-radius: 999px;
  background: #1A1A2E;
  color: #fff;
  font-size: 12px;
  font-weight: 600;
}
#emailEmpfSelectAll { margin-left: auto; }   /* push the action + apply to the right */
.empf-link-btn {
  border: none; background: transparent;
  font-family: inherit; font-size: 13px; font-weight: 600;
  color: #D95F02; cursor: pointer; padding: 6px 8px; border-radius: 4px; white-space: nowrap;
}
.empf-link-btn:hover { background: #fff6ef; }
/* Icon-only apply button (check = übernehmen) */
.empf-apply-btn {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 36px;
  height: 32px;
  padding: 0;
  flex-shrink: 0;
}

/* Auswahl-Liste (Popover beim Klick auf das Rundmail-Badge) */
.selected-pop {
  position: absolute;
  top: calc(100% + 4px);
  left: 0;
  width: min(320px, 100%);
  background: #fff;
  border: 1px solid #e0e0e0;
  border-radius: 12px;
  box-shadow: 0 8px 28px rgba(26,26,46,0.16);
  z-index: 40;
  overflow: hidden;
}
/* The popover's own aria-label names it, so the visible heading was dropped
   (2026-08-01) and .selected-pop-head with it. The list keeps the top padding the
   heading used to provide. */
.selected-pop-list { max-height: 200px; overflow-y: auto; padding: 12px 8px 8px; }
.selected-pop-item {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 10px;
  padding: 7px 8px;
  font-size: 14px;
  color: #1A1A2E;
  border-radius: 6px;
}
.selected-pop-item:hover { background: #faf7f4; }
.selected-pop-item__remove {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 22px; height: 22px;
  border: none;
  background: transparent;
  border-radius: 50%;
  color: #888;
  cursor: pointer;
  flex-shrink: 0;
}
.selected-pop-item__remove:hover { background: #F2C9A3; color: #9A4D11; }

/* Formatierungs-Toolbar */
.composer-toolbar {
  display: flex;
  align-items: center;
  gap: 2px;
  padding: 6px 14px;
  border-bottom: 1px solid #f0f0f0;
}
.composer-tool {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 34px; height: 34px;
  border: none;
  background: transparent;
  border-radius: 6px;
  color: #666;
  cursor: pointer;
  transition: background-color 0.1s, color 0.1s;
}
.composer-tool:hover { background: #f0f0f0; color: #1A1A2E; }
.composer-tool--active { background: #fff6ef; color: #D95F02; }
.composer-tool-sep { width: 1px; height: 18px; background: #e0e0e0; margin: 0 8px; }
.composer-var-at { font-size: 14px; font-weight: 700; }

/* Variable-einfügen-Menü */
.composer-var-wrap { position: relative; }
.composer-var-menu {
  position: absolute;
  top: calc(100% + 4px);
  left: 0;
  min-width: 240px;
  background: #fff;
  border: 1px solid #e0e0e0;
  border-radius: 8px;
  box-shadow: 0 8px 28px rgba(26,26,46,0.16);
  z-index: 40;
  padding: 6px 0;
  max-height: 260px;
  overflow-y: auto;
}
.composer-var-item {
  display: block;
  width: 100%;
  text-align: left;
  border: none;
  background: transparent;
  padding: 8px 14px;
  font-family: inherit;
  font-size: 13px;
  color: #1A1A2E;
  cursor: pointer;
}
.composer-var-item:hover { background: #fff6ef; color: #D95F02; }

/* Nachricht (contentEditable) — modest empty floor so the empty composer
   fits a standard laptop viewport without page scroll; grows as you type up
   to max-height (then scrolls inside the body, not the page). */
.composer-body {
  min-height: 140px;
  max-height: 48vh;
  overflow-y: auto;
  padding: 16px 20px;
  font-size: 14px;
  line-height: 1.6;
  color: #1A1A2E;
  outline: none;
  cursor: text;
}
.composer-body:empty::before {
  content: attr(data-placeholder);
  color: #b8b8b8;
  pointer-events: none;
}
.composer-body ul, .composer-body ol { margin: 0.4em 0; padding-left: 1.6em; }
.composer-body a { color: #D95F02; }

/* Framed standalone rich-text editor — the reusable composer (richtext.js) used
   in the template editor, the signature field and the profile composer. The
   Verfassen composer lives in its own card and needs no frame, so it gets no
   .rte wrapper. No overflow:hidden here — the @-variable menu must escape the
   box. Modest body floor (smaller than the full Verfassen composer). */
.rte { border: 1px solid #e0e0e0; border-radius: 10px; background: #fff; }
.rte .composer-toolbar { border-top-left-radius: 10px; border-top-right-radius: 10px; }
.rte .composer-body { min-height: 110px; max-height: 320px; }

/* PDF-Anhang */
.composer-attach { padding: 14px 20px; border-top: 1px solid #f0f0f0; }
.composer-attach-label { display: block; font-size: 13px; color: #888; margin-bottom: 6px; }
/* The pick-several list for Beitragsrechnungen. Scrolls rather than growing, because a
   long-standing member has dozens of Beiträge and the composer must not push the send
   button off the screen. */
.composer-attach-list { max-height: 168px; overflow-y: auto; border: 1px solid #e0e0e0; border-radius: 8px; padding: 4px; }
.composer-attach-list:empty { display: none; }
.composer-attach-opt { display: flex; align-items: center; gap: 9px; padding: 6px 8px; border-radius: 6px; font-size: 13.5px; color: #1A1A2E; cursor: pointer; }
.composer-attach-opt:hover { background: #f6f7f9; }
.composer-attach-opt input { width: 16px; height: 16px; accent-color: #D95F02; cursor: pointer; flex: none; margin: 0; }
.composer-attach-opt .composer-attach-sub { color: #8a8a93; font-size: 12.5px; }
.composer-attach-empty { padding: 8px; font-size: 13px; color: #9a9aa2; }
.composer-attach .composer-inline-select {
  border: 1px solid #ddd; border-radius: 6px; padding: 8px 10px; width: 100%; box-sizing: border-box;
}

/* Footer */
.composer-footer {
  display: flex;
  align-items: center;
  gap: 12px;
  padding: 14px 20px;
  border-top: 1px solid #f0f0f0;
}
.composer-footer-spacer { flex: 1; }
.composer-footer-hint { font-size: 13px; color: #888; }
.ctrl-pop-clear {
  width: 100%; margin-top: 6px; padding: 9px;
  border: none; border-top: 1px solid #eee; background: none;
  color: #D95F02; font-weight: 600; font-size: 13px; cursor: pointer; font-family: inherit;
}
.ctrl-sort-opt {
  display: block; width: 100%; text-align: left;
  padding: 10px 12px; border: none; background: none; border-radius: 7px;
  font-family: inherit; font-size: 14px; font-weight: 600; color: #1A1A2E; cursor: pointer;
}
.ctrl-sort-opt:hover { background: #f4f4f6; }
.ctrl-sort-opt.active { color: #D95F02; background: rgba(217,95,2,0.08); }
.ctrl-pop-dates { display: flex; align-items: center; gap: 6px; padding: 6px 8px; }
/* ⚠ The flex item is the .dfield WRAPPER now, not the input: the input is one level
   deeper, so `flex: 1 1 auto` on it would size nothing. The two have to be split or
   the two date boxes collapse to their content width. */
/* ⚠ min-width, not 0: the popover's own min-width is 200px, which left each box 82px
   once the gap, the dash and the padding were taken out. That fits a native date
   control but not „01.06.2026" PLUS the 34px calendar gutter, so the date was cut off.
   The popover has no max-width, so letting the two boxes ask for a real width simply
   makes it wider. */
.ctrl-pop-dates .dfield { flex: 1 1 auto; min-width: 116px; }
.ctrl-pop-dates input {
  flex: 1 1 auto; min-width: 0;
  padding: 7px 8px; border: 1px solid #ddd; border-radius: 7px;
  font-family: inherit; font-size: 13px;
}
.ctrl-pop-dates .dfield-text { width: 100%; box-sizing: border-box; }

/* CSV export column-picker modal (opens from the bulk bar's "CSV exportieren").
   Wider + left-aligned than the default centered modal. The box is a capped flex
   column so the column list scrolls INSIDE it and the actions stay pinned + on
   screen at any viewport height. Group titles + checkboxes reuse
   .ctrl-pop-title / .ctrl-check. */
.export-cols-box  { text-align: left; max-width: 460px; display: flex; flex-direction: column; max-height: 88vh; }
.export-cols-list { flex: 1 1 auto; min-height: 0; overflow-y: auto; margin-bottom: 4px; }

/* Desktop: the per-row card pieces are hidden (cards are a mobile-only view). */
.mcard-mship  { display: none; }   /* membership shown via its own column on desktop */
.mcard-kebab  { display: none; }   /* desktop shows the action icons inline */
.mcard-mlabel { display: none; }   /* desktop action buttons are icon-only */
.mcard-menu   { display: inline-flex; gap: 6px; align-items: center; }

/* ══════════════════════════════════════════════════════════════════════════
   Members bulk actions (desktop) — checkbox column, the contextual action bar,
   and the shared result modal. The checkbox cells carry .mcard-hide so the
   mobile card view (td.mcard-hide { display:none }) drops them; the header
   checkbox lives in the header row, which mobile hides outright.
   ══════════════════════════════════════════════════════════════════════════ */
.col-select { width: 40px; text-align: center; padding-left: 10px; padding-right: 6px; }
.bulk-select, #selectAllMembers {
  width: 16px; height: 16px; accent-color: #D95F02; cursor: pointer; vertical-align: middle; margin: 0;
}
#membersTable tr.row-selected td { background: #FEF5EC; }

.bulk-bar {
  display: flex; align-items: center; gap: 10px;
  margin: 0 0 12px; padding: 10px 14px;
  background: #FEF5EC; border: 1px solid #F3D8BE; border-radius: 10px;
}
.bulk-bar[hidden] { display: none; }
.bulk-bar-count  { font-size: 14px; font-weight: 700; color: #1A1A2E; }
.bulk-bar-spacer { flex: 1 1 auto; }
.bulk-btn {
  padding: 8px 16px; border-radius: 6px; font-family: inherit;
  font-size: 13px; font-weight: 600; cursor: pointer;
  background: #fff; color: #1A1A2E; border: 1px solid #d8d8e0;
}
.bulk-btn:hover { background: #f4f4f6; }
.bulk-btn--danger { background: #B34D00; color: #fff; border-color: #B34D00; }
.bulk-btn--danger:hover { background: #934000; }
.bulk-btn--ghost  { background: transparent; color: #888; border-color: transparent; }
.bulk-btn--ghost:hover { background: #f0e7de; color: #555; }

/* Bulk-bar layout wrappers. On desktop the wrappers are transparent
   (display:contents), so the bar stays the exact flat flex row it always was;
   the Alle-auswählen / Fertig buttons are mobile-only. mobile.css reshapes all
   of this into a pinned bottom panel for the phone select-mode (Stage 5). */
.bulk-toprow, .bulk-actions { display: contents; }
.bulk-selall, .bulk-done { display: none; }
/* The "Auswählen" entry lives only on mobile — desktop has the checkbox column. */
.ctrl-bar .ctrl-select { display: none; }

/* Bulk-edit modal select (status / membership). */
.bulk-edit-select {
  width: 100%; padding: 10px 12px; margin: 4px 0 24px; box-sizing: border-box;
  border: 1px solid #ccc; border-radius: 6px; font-size: 14px;
  font-family: inherit; color: #1A1A2E; background: #fff;
}

/* Bulk record-fee modal. */
.bulk-fee-box { max-width: 460px; text-align: left; }
.bulk-fee-box h3 { text-align: left; margin-bottom: 4px; }
.bulk-fee-grid { display: grid; grid-template-columns: 1fr 1fr; gap: 12px; margin: 12px 0 16px; }
.bulk-fee-field { display: flex; flex-direction: column; gap: 4px; font-size: 12px; font-weight: 600; color: #888; }
.bulk-fee-field select, .bulk-fee-field input {
  padding: 9px 10px; border: 1px solid #ccc; border-radius: 6px; font-size: 14px;
  font-family: inherit; font-weight: 400; color: #1A1A2E; background: #fff; box-sizing: border-box;
}
.bulk-fee-hint { font-size: 12px; color: #888; line-height: 1.5; margin: 0 0 22px; }
@media (max-width: 520px) { .bulk-fee-grid { grid-template-columns: 1fr; } }

/* Result modal — left-aligned list (overrides the centered .modal-box). */
.bulk-result-box { max-width: 440px; text-align: left; }
.bulk-result-box h3 { text-align: left; margin-bottom: 4px; }
.bulk-result-body { margin: 4px 0 24px; max-height: 50vh; overflow-y: auto; }
.bulk-result-line {
  display: flex; align-items: center; gap: 8px;
  font-size: 14px; font-weight: 600; color: #1A1A2E; margin-top: 12px;
}
.bulk-result-line:first-child { margin-top: 0; }
.bulk-result-badge {
  min-width: 24px; text-align: center; padding: 2px 8px;
  border-radius: 20px; font-size: 12px; font-weight: 700;
}
.bulk-result-badge--ok   { background: #eaf5ec; color: #2e7d32; }
.bulk-result-badge--skip { background: #fff4e5; color: #B34D00; }
.bulk-result-badge--fail { background: #fdecea; color: #c0392b; }
.bulk-result-names { font-size: 12px; color: #888; font-weight: 400; margin: 3px 0 0 32px; line-height: 1.5; }
.bulk-result-note {
  margin-top: 16px; padding-top: 12px; border-top: 1px solid #eee;
  font-size: 12.5px; color: #777; line-height: 1.5;
}

/* ══════════════════════════════════════════════════════════════════════════
   Configurable member import — the mapping UI (member-import.js, Phase B Stage 4)
   ──────────────────────────────────────────────────────────────────────────
   Everything is scoped under .mi-wrap. The mapping/visibility tables are built
   from <table>/<th>/<td>/<select>, which would otherwise inherit the global
   data-table chrome (shadow halo, dark header, row dividers, hover tint,
   borderless full-width selects). Each of those global rules is explicitly
   reset below so the component renders as the calm card it is — the same lesson
   that boxed/shadowed the notification matrix (CHANGELOG 2026-06-27).
   ══════════════════════════════════════════════════════════════════════════ */
.mi-wrap { color: #1A1A2E; }
.mi-wrap .admin-card { padding: 0; overflow: hidden; }
.mi-source-card { margin-bottom: 18px; }

/* ── Card head + step badge ── */
.mi-card-head {
  padding: 17px 24px; font-size: 15px; font-weight: 700; color: #1A1A2E;
  border-bottom: 1px solid #eee; display: flex; align-items: center; gap: 10px;
}

/* ── Source picker ── */
.mi-source-grid { display: flex; gap: 14px; padding: 20px 24px; flex-wrap: wrap; }
.mi-src-opt {
  flex: 1; min-width: 210px; text-align: left; background: #fff;
  border: 1.5px solid #e0e0e0; border-radius: 10px; padding: 15px 16px;
  cursor: pointer; font-family: inherit; display: flex; flex-direction: column;
  gap: 6px; transition: border-color .12s, box-shadow .12s;
}
.mi-src-title { font-size: 14px; font-weight: 700; color: #1A1A2E; display: flex; align-items: center; gap: 8px; }
.mi-src-title svg { color: #2e7d32; flex: none; }
.mi-src-opt.selected { border-color: #E8662A; box-shadow: 0 0 0 3px rgba(232,102,42,.12); }
.mi-src-opt.disabled { cursor: not-allowed; opacity: .55; background: #fafafa; }
.mi-src-soon {
  font-size: 10px; font-weight: 700; text-transform: uppercase; letter-spacing: .4px;
  color: #999; background: #f0f0f0; padding: 2px 7px; border-radius: 10px;
}
.mi-src-config { padding: 0 24px 22px; display: flex; align-items: flex-end; gap: 12px; flex-wrap: wrap; }
.mi-src-id label { font-size: 12px; font-weight: 600; color: #666; display: block; margin-bottom: 6px; }
.mi-id-input {
  font-family: 'Segoe UI', Arial, sans-serif; font-size: 13px; padding: 9px 11px;
  border: 1px solid #cfcfd6; border-radius: 7px; min-width: 320px;
}
.mi-id-input:focus { outline: none; border-color: #D95F02; }
.mi-analyze-status { font-size: 12.5px; }
.mi-analyze-status .warn { color: #d64545; font-weight: 600; }

/* ── Source bar (shown atop the mapping card) ── */
.mi-source-bar {
  display: flex; align-items: center; justify-content: space-between; gap: 14px;
  padding: 16px 24px; background: #fbfbfd; border-bottom: 1px solid #ececf1; flex-wrap: wrap;
}
.mi-sb-main { font-size: 13.5px; color: #1A1A2E; display: flex; align-items: center; gap: 9px; }
.mi-sb-main svg { color: #2e7d32; flex: none; }
/* A text link that is really a button (it runs JS, it does not navigate). Used
   wherever a card points at the section that owns a setting. A real <button>
   rather than a bare <a>, so it is keyboard-focusable without inventing a
   tabindex, and so no dead href="#" can jump the page before the handler runs.
   .mi-link-btn is the older member-import-scoped name for the same thing. */
.link-btn, .mi-link-btn {
  background: none; border: none; color: #D95F02; font-size: 12.5px; font-weight: 600;
  cursor: pointer; font-family: inherit; padding: 4px 6px; border-radius: 5px; white-space: nowrap;
}
.link-btn:hover, .mi-link-btn:hover { background: #fff6ef; }
.link-btn:focus-visible, .mi-link-btn:focus-visible {
  outline: 2px solid rgba(217,95,2,.45); outline-offset: 1px;
}

/* ── Tabs ── */
.mi-tabs { display: flex; gap: 4px; padding: 0 24px; border-bottom: 1px solid #eee; }
.mi-tab {
  background: none; border: none; font-family: inherit; cursor: pointer;
  font-size: 13.5px; font-weight: 600; color: #888; padding: 15px 8px 13px;
  border-bottom: 2.5px solid transparent; margin-bottom: -1px;
}
.mi-tab:hover { color: #1A1A2E; }
.mi-tab.active { color: #1A1A2E; border-bottom-color: #E8662A; }
.mi-pane { padding: 22px 24px; display: none; }
.mi-pane.active { display: block; }

/* ── Tables: neutralise the global table/th/td/hover/select chrome ── */
.mi-wrap table.mi-map,
.mi-wrap table.mi-vis {
  width: 100%; margin-top: 0; background: transparent; border-radius: 0;
  box-shadow: none; table-layout: auto; border-collapse: collapse; overflow: visible;
}
.mi-wrap table.mi-map th,
.mi-wrap table.mi-vis th {
  background: transparent; color: #aaa; font-size: 10.5px; font-weight: 700;
  text-transform: uppercase; letter-spacing: .5px; text-align: left;
  padding: 0 12px 10px 0; border-bottom: 2px solid #eee;
}
.mi-wrap table.mi-vis th.r { text-align: right; width: 90px; }
.mi-wrap table.mi-map td,
.mi-wrap table.mi-vis td {
  padding: 11px 12px 11px 0; color: #1A1A2E; vertical-align: middle;
  background: transparent; border-bottom: none;
}
.mi-wrap table.mi-vis td { padding-top: 12px; padding-bottom: 12px; }
.mi-wrap tr.mi-row > td { border-bottom: 1px solid #f4f4f4; }
.mi-wrap table.mi-vis tbody td { border-bottom: 1px solid #f4f4f4; }
.mi-wrap table.mi-vis tbody tr:last-child td { border-bottom: none; }
.mi-wrap table.mi-map tr:hover td,
.mi-wrap table.mi-vis tr:hover td { background: transparent; }

.mi-col-name { font-size: 13.5px; font-weight: 600; color: #1A1A2E; }
.mi-col-sample { font-size: 12px; color: #999; margin-top: 2px; font-style: italic; }
.mi-arrow { color: #ccc; width: 26px; text-align: center; }
td.mi-target { width: 300px; }
.mi-target-pick { display: flex; align-items: center; gap: 8px; flex-wrap: wrap; }

/* restore real <select> chrome (global `td select` is borderless/transparent/100%) */
.mi-wrap td select.mi-fieldsel,
.mi-wrap td select.mi-valsel {
  font-family: 'Segoe UI', Arial, sans-serif; border: 1px solid #cfcfd6;
  border-radius: 7px; background: #fff; color: #1A1A2E; cursor: pointer;
}
.mi-wrap td select.mi-fieldsel { font-size: 13px; padding: 7px 9px; width: auto; min-width: 180px; }
.mi-wrap td select.mi-valsel { font-size: 12.5px; padding: 5px 8px; width: auto; }
.mi-wrap td select.mi-fieldsel:focus,
.mi-wrap td select.mi-valsel:focus { outline: none; border-color: #D95F02; }
.mi-fieldsel.is-notes { color: #6a5acd; border-color: #d9d4f5 !important; background: #f7f6fe !important; }
.mi-fieldsel.is-ignore { color: #aaa; background: #fafafa !important; }
.mi-fieldsel.dup { border-color: #d64545 !important; background: #fdf3f3 !important; }

.mi-badge {
  font-size: 10px; font-weight: 700; text-transform: uppercase; letter-spacing: .4px;
  padding: 2px 7px; border-radius: 10px; background: #eef6ee; color: #2e7d32; white-space: nowrap;
}
.mi-badge.hidden { display: none; }
.mi-values-link {
  background: none; border: none; color: #D95F02; font-size: 12px; font-weight: 600;
  cursor: pointer; font-family: inherit; padding: 3px 6px; border-radius: 5px; white-space: nowrap;
}
.mi-values-link:hover { background: #fff6ef; }
.mi-dup-msg { display: none; font-size: 11.5px; color: #d64545; margin-top: 4px; }
.mi-dup-msg.show { display: block; }

/* ── Value-map sub panel ── */
.mi-wrap tr.mi-values-row > td { padding: 0 12px 0 0; border-bottom: none; }
.mi-values-box {
  display: none; background: #fbfbfd; border: 1px solid #ececf1; border-radius: 9px;
  margin: 0 0 12px; padding: 14px 16px;
}
.mi-values-box.open { display: block; }
.mi-values-box h4 { margin: 0 0 4px; font-size: 12.5px; font-weight: 700; color: #1A1A2E; }
.mi-values-box p { margin: 0 0 12px; font-size: 11.5px; color: #888; }
.mi-vm-row { display: grid; grid-template-columns: 1fr 26px 1fr; align-items: center; gap: 8px; padding: 6px 0; max-width: 460px; }
.mi-vm-their { font-size: 13px; font-weight: 600; word-break: break-word; }
.mi-vm-arrow { color: #ccc; text-align: center; }
.mi-vm-add { margin-top: 12px; padding-top: 12px; border-top: 1px dashed #e3e3ea; }
.mi-vm-add-form { display: inline-flex; align-items: center; gap: 6px; margin-left: 8px; }
.mi-vm-add-input {
  font-family: inherit; font-size: 12.5px; padding: 6px 9px; border: 1px solid #cfcfd6;
  border-radius: 6px; margin-right: 6px; min-width: 170px;
}
.mi-vm-add-input:focus { outline: none; border-color: #D95F02; }
.mi-vm-add-err { font-size: 11.5px; color: #d64545; margin-top: 8px; }

/* ── Notes preview ── */
.mi-notes-preview { margin-top: 22px; background: #f7f6fe; border: 1px solid #e3def7; border-radius: 9px; padding: 14px 16px; }
.mi-notes-preview h4 { margin: 0 0 9px; font-size: 11px; font-weight: 700; color: #6a5acd; text-transform: uppercase; letter-spacing: .4px; }
.mi-notes-preview .np-line { font-size: 13px; color: #1A1A2E; padding: 3px 0; line-height: 1.4; }
.mi-notes-preview .np-line b { font-weight: 700; }

/* ── Visibility pane ── */
.mi-wrap .vis-field { font-size: 13.5px; font-weight: 600; }
.mi-wrap .vis-req { color: #D95F02; font-weight: 700; margin-left: 2px; }
.mi-wrap .vis-src { font-size: 12.5px; color: #777; }
.mi-wrap .vis-src.none { color: #b3b3b3; font-style: italic; }
.mi-wrap .vis-src.manual { color: #6a5acd; font-style: italic; }
.mi-wrap td.vis-toggle { text-align: right; }
.mi-switch { position: relative; display: inline-block; width: 40px; height: 22px; }
.mi-switch input { opacity: 0; width: 0; height: 0; }
.mi-slider { position: absolute; inset: 0; background: #ccc; border-radius: 22px; transition: .2s; cursor: pointer; }
.mi-slider::before { content: ''; position: absolute; height: 16px; width: 16px; left: 3px; top: 3px; background: #fff; border-radius: 50%; transition: .2s; }
.mi-switch input:checked + .mi-slider { background: #D95F02; }
.mi-switch input:checked + .mi-slider::before { transform: translateX(18px); }
.mi-switch.locked .mi-slider { opacity: .4; cursor: not-allowed; }

/* ── Footer / summary ── */
.mi-foot {
  display: flex; align-items: center; justify-content: space-between; gap: 16px;
  padding: 16px 24px; background: #fbfbfd; border-top: 1px solid #ececf1; flex-wrap: wrap;
}
.mi-foot-left { display: flex; flex-direction: column; gap: 8px; }
.mi-summary { font-size: 12.5px; color: #666; display: flex; align-items: center; gap: 16px; flex-wrap: wrap; }
.mi-summary .ok { color: #2e7d32; font-weight: 600; }
.mi-summary .warn { color: #d64545; font-weight: 600; }
.mi-foot-hint { display: flex; align-items: center; gap: 6px; font-size: 12px; color: #999; }
.mi-foot-hint svg { color: #bbb; flex: none; }

/* Import-status picker (one-time roster import). Sits in the footer while editing. */
.mi-import-status { display: flex; align-items: center; gap: 8px; font-size: 12.5px; color: #666; flex-wrap: wrap; }
.mi-import-status select {
  padding: 5px 8px; font-size: 12.5px; border: 1px solid #ccc; border-radius: 6px;
  background: #fff; color: #1A1A2E; font-family: inherit;
}

/* ── Member-import: per-source connection prerequisite (Google Sheets) ── */
.mi-conn { padding: 0 24px; }
.mi-conn:empty { display: none; }
.mi-conn-line { display: flex; align-items: center; gap: 11px; flex-wrap: wrap; padding: 12px 14px; border-radius: 9px; font-size: 13px; margin-bottom: 14px; }
.mi-conn-line.on  { background: #eef6ee; border: 1px solid #dcecdc; color: #2e7d32; }
.mi-conn-line.off { background: #fffaf6; border: 1px solid #f3d9c2; color: #b4530a; }
.mi-conn-line svg { flex: none; }
.mi-conn-line b { font-weight: 700; }
.mi-conn-txt { flex: 1; min-width: 220px; }
.mi-wrap .mi-id-input:disabled { background: #f5f5f7; color: #aaa; cursor: not-allowed; }

/* ── Member-import polish: Datenquelle action row, ghost btn, sync result, read-only ── */
.mi-source-card .mi-src-config { padding-bottom: 12px; }
.mi-src-foot { display: flex; align-items: center; gap: 16px; flex-wrap: wrap; padding: 0 24px 20px; }
/* Layout comes from .btn-row on the element; a local gap here would silently
   win on source order and reintroduce a second spacing value. */
.mi-src-status { font-size: 12.5px; color: #888; }
/* No padding/font-size patch here any more: the button classes carry one
   geometry, and :disabled is handled once with the rest of the family. */
.mi-analyze-status { padding: 0 24px 8px; }
.mi-analyze-status:empty { display: none; }
.mi-sync-result { margin: 0 24px 20px; padding: 12px 16px; border-radius: 8px; font-size: 13px; }
.mi-sync-result.ok  { background: #E8F5E9; border: 1px solid #A5D6A7; color: #2E7D32; }
.mi-sync-result.err { background: #FFEBEE; border: 1px solid #EF9A9A; color: #C62828; }


/* Read-only (view) mode: locked source grid + non-editable mapping controls. */
.mi-source-grid.mi-locked .mi-src-opt:not(.disabled) { cursor: default; }
.mi-source-grid.mi-locked .mi-src-opt:not(.selected):not(.disabled) { opacity: .55; }
.mi-wrap td select.mi-fieldsel:disabled { background: #f7f7f9; color: #555; -webkit-text-fill-color: #555; opacity: 1; cursor: default; }

/* ── SEPA-Lastschriftmandate ─────────────────────────
   Shared by the profile mandate card (#ppMandate) and the Finanzen tab
   (#fin-mandates). Status colours mirror the app's semantic palette. */

/* Status badge */
.mand-badge { display: inline-flex; align-items: center; gap: 6px; font-size: 11.5px; font-weight: 600; padding: 3px 10px; border-radius: 20px; white-space: nowrap; }
.mand-badge .d { width: 6px; height: 6px; border-radius: 50%; }
.mand-aktiv       { background: #EAF4EB; color: #2E7D32; } .mand-aktiv .d       { background: #2E7D32; }
.mand-angefordert { background: #FEF6E6; color: #B45309; } .mand-angefordert .d { background: #B45309; }
.mand-entwurf     { background: #eef0f2; color: #5b6472; } .mand-entwurf .d     { background: #9aa0a6; }
.mand-abgelaufen  { background: #FDECEA; color: #C0392B; } .mand-abgelaufen .d  { background: #C0392B; }
.mand-widerrufen  { background: #f4f4f6; color: #9aa0a6; } .mand-widerrufen .d  { background: #c2c2cc; }

/* Profile card body */
.mand-head { margin-bottom: 14px; }
.mand-muted { color: #aaa; font-size: 14px; margin: 6px 0 0; }
.mand-seal { border: 1px solid #cfe3d0; background: #f3f9f3; border-radius: 8px; padding: 12px 15px; font-size: 12.5px; color: #3a5a3c; margin-top: 16px; line-height: 1.5; }
.mand-seal b { color: #223; }
.mand-actions { display: flex; gap: 10px; flex-wrap: wrap; margin-top: 18px; }
.mand-actions .btn-primary svg { vertical-align: -2px; margin-right: 6px; }
.mand-empty { text-align: center; padding: 26px 20px 10px; color: #999; }
.mand-empty svg { color: #cfcfd8; margin-bottom: 10px; }
.mand-empty p { margin: 0 0 16px; font-size: 14px; }

/* Finanzen tab — KPI chips */
/* Status cards double as the list filter: click filters the table, clicking the
   active card (or its ✕) clears the filter again. */
.mand-kpi-row { display: flex; gap: 12px; flex-wrap: wrap; margin-bottom: 20px; }
.mand-kpi { background: #fff; border: 1px solid #ececf0; border-radius: 10px; padding: 12px 18px; display: flex; align-items: center; gap: 12px; box-shadow: 0 1px 2px rgba(0,0,0,.04); font-family: inherit; text-align: left; cursor: pointer; transition: border-color .12s, box-shadow .12s, background .12s; }
.mand-kpi:hover { border-color: #D95F02; }
.mand-kpi.active { border-color: #D95F02; box-shadow: 0 0 0 1px #D95F02, 0 1px 2px rgba(0,0,0,.04); background: #FFF8F2; }
.mand-kpi-txt { display: block; }
.mand-kpi-n { display: block; font-size: 22px; font-weight: 700; line-height: 1.1; }
.mand-kpi-l { display: block; font-size: 12px; color: #888; line-height: 1.3; }
.mand-kpi-dot { width: 9px; height: 9px; border-radius: 50%; flex: none; }
.mand-kpi-clr { display: none; margin-left: 4px; color: #D95F02; }
.mand-kpi.active .mand-kpi-clr { display: inline-flex; }
.mand-kpi.green .mand-kpi-n { color: #2E7D32; } .mand-kpi.green .mand-kpi-dot { background: #2E7D32; }
.mand-kpi.amber .mand-kpi-n { color: #B45309; } .mand-kpi.amber .mand-kpi-dot { background: #B45309; }
.mand-kpi.red   .mand-kpi-n { color: #C0392B; } .mand-kpi.red   .mand-kpi-dot { background: #C0392B; }
.mand-kpi.grey  .mand-kpi-n { color: #5b6472; } .mand-kpi.grey  .mand-kpi-dot { background: #98a; }

/* Finanzen tab — toolbar + table */
.mand-toolbar { display: flex; align-items: center; gap: 12px; margin-bottom: 14px; flex-wrap: wrap; }
.mand-toolbar .ctrl-search { flex: 1; min-width: 180px; max-width: 320px; }
/* The table inherits the app's general table style (navy header, card look,
   row hover) from the base `table`/`th`/`td` rules. It KEEPS the app-wide
   fixed layout with explicit column widths: under auto layout every filter
   click re-derived the widths from the visible rows — with only unsigned rows
   the all-"—" date columns collapsed until the two-word "Gültig bis" header
   wrapped onto two lines. Fixed widths keep every filter view identical; on
   narrow desktops the wrapper scrolls horizontally. */
.mand-table-wrap { overflow-x: auto; }
table.mand-table { table-layout: fixed; min-width: 980px; margin-top: 4px; }
/* The header/body typography that used to live here IS the base rule now: these
   were the values every other table was measured against and then given. */
.mand-col-name    { width: 13%;   }
.mand-col-mship   { width: 10%;   }
.mand-col-ref     { width: 11%;   }
.mand-col-iban    { width: 13%;   }
.mand-col-status  { width: 17%;   }   /* the widest badge, "Warten auf Unterschrift", is nowrap */
.mand-col-signed  { width: 10%;   }
.mand-col-valid   { width: 8%;    }
.mand-col-actions { width: 14.5%; }   /* up to 4 icon buttons (WhatsApp/Profil/Kommentar/PDF) */
.mand-m-name { font-weight: 600; }
.mand-mono { font-variant-numeric: tabular-nums; letter-spacing: .2px; }
.mand-valid-exp { color: #C0392B; font-weight: 600; }
.mand-row-actions { display: flex; gap: 6px; justify-content: flex-end; }
.mand-icon-btn { width: 30px; height: 30px; border: 1px solid #e0e0e0; background: #fff; border-radius: 7px; display: inline-flex; align-items: center; justify-content: center; cursor: pointer; color: #555; }
.mand-icon-btn:hover { border-color: #D95F02; color: #D95F02; }
/* Every row carries a notes-row (the member-comment editor); kill its own
   bottom border so a collapsed (0-height) notes-row doesn't double the divider. */
table.mand-table tr.notes-row td { border-bottom: none; }
.mand-empty-row { text-align: center; color: #aaa; padding: 26px 16px; font-size: 14px; }

/* Mandate tab — multi-select + bulk bar */
.mand-check-cell { width: 40px; text-align: center; padding-right: 0; }
.mand-check-cell input { width: 16px; height: 16px; accent-color: #D95F02; cursor: pointer; }
.mand-bulk { display: flex; align-items: center; gap: 16px; background: #fff6ef; border: 1px solid #f0d8c0; border-radius: 9px; padding: 10px 16px; margin-bottom: 12px; font-size: 13.5px; color: #8a5a1f; }
.mand-bulk.hidden { display: none; }
.mand-bulk b { color: #1A1A2E; }
.mand-bulk .btn-primary { padding: 8px 16px; font-size: 13px; }

/* "Kein Mandat" badge — hollow/neutral to read as an absence, not a state. */
.mand-kein { background: #f6f6f8; color: #8a8a96; border: 1px dashed #d3d3db; }
.mand-kein .d { background: #bcbcc6; }

.mand-empty-actions { display: flex; gap: 10px; justify-content: center; flex-wrap: wrap; }

/* ── Beitragsläufe / Einzüge tab (SEPA collection runs) ─────────────────── */
.bl-toolbar { display: flex; align-items: center; gap: 12px; margin-bottom: 16px; flex-wrap: wrap; }
.bl-muted { color: #9a9aa2; font-size: 14px; }
.bl-mono { font-variant-numeric: tabular-nums; letter-spacing: .2px; }
.bl-amt { font-variant-numeric: tabular-nums; font-weight: 600; }
/* Per-period amounts behind a total, shown only when the periods were billed at
   DIFFERENT fee rates (a catch-up debit spanning a Beitragssatz change). */
.bl-rate-split { display: block; font-size: 11px; font-weight: 400; color: #888; margin-top: 2px; }
.bl-dash { color: #c7c7d0; }
.bl-sec { font-size: 13px; font-weight: 700; text-transform: uppercase; letter-spacing: .4px; color: #1A1A2E; margin: 24px 0 12px; }
.bl-back { display: inline-flex; align-items: center; gap: 6px; font-size: 13px; font-weight: 600; color: #888; cursor: pointer; margin-bottom: 14px; }
.bl-back:hover { color: #D95F02; }

/* Info strip (deadline etc.) */
.bl-strip { display: flex; gap: 9px; align-items: center; font-size: 13px; color: #5b6472; background: #f7f8fa; border: 1px solid #ececf0; border-radius: 9px; padding: 10px 14px; margin-bottom: 18px; }
.bl-strip svg { flex: none; }
.bl-strip b { color: #1A1A2E; font-weight: 700; }
.bl-strip.ok { background: #f2f9f3; border-color: #cfe3d0; color: #2c5c30; }
.bl-strip.ok b { color: #2c5c30; }
.bl-strip.warn { background: #fff8f0; border-color: #f0dcc4; color: #8a5a1f; }
.bl-strip.warn b { color: #8a5a1f; }
/* A BLOCKED state, not a warning: the Einreichfrist-Wächter's third zone is the
   only place in this view where an action is refused rather than merely risky,
   and next to four amber strips an amber fifth would not read as a stop. */
.bl-strip.stop { background: #fdf3f2; border-color: #f0cdc9; color: #a33227; }
.bl-strip.stop b { color: #a33227; }

/* Table */
.bl-table-wrap { overflow-x: auto; }
.bl-table { width: 100%; border-collapse: collapse; }
/* Size, weight, transform and padding come from the base rule. What stays is the
   bottom hairline; the grey #a9a9b4 header text went with the unification, since
   it was grey on the same navy bar every other table has and made a third header
   colour out of nothing. */
.bl-table th { border-bottom: 1px solid #f0f0f3; }
.bl-table th.r, .bl-table td.r { text-align: right; }
.bl-table th.bl-check, .bl-table td.bl-check { width: 34px; text-align: center; padding-left: 8px; padding-right: 8px; }
.bl-table .bl-check input { cursor: pointer; margin: 0; }
.bl-table td { border-bottom: 1px solid #f4f4f7; vertical-align: middle; }
.bl-table tbody tr:last-child td { border-bottom: none; }
.bl-table tbody tr.clickable { cursor: pointer; }
.bl-table tbody tr.clickable:hover { background: #fcfbfa; }
.bl-m-name { font-weight: 600; }
.bl-m-sub { color: #aaa; font-size: 11.5px; }
.bl-empty-row { text-align: center; color: #9a9aa2; padding: 26px; }
.bl-muted-row td { color: #9a9aa2; font-style: italic; }

/* Status badge */
.bl-badge { display: inline-flex; align-items: center; gap: 5px; font-size: 11.5px; font-weight: 600; padding: 3px 9px; border-radius: 20px; white-space: nowrap; }
.bl-badge .d { width: 6px; height: 6px; border-radius: 50%; }
.bl-badge.entwurf     { background: #eef0f2; color: #5b6472; } .bl-badge.entwurf .d { background: #9aa0a6; }
.bl-badge.exportiert  { background: #E8F0FE; color: #1A56DB; } .bl-badge.exportiert .d { background: #1A56DB; }
.bl-badge.eingereicht { background: #EDE9FE; color: #6D28D9; } .bl-badge.eingereicht .d { background: #6D28D9; }
.bl-badge.abgeglichen { background: #EAF4EB; color: #2E7D32; } .bl-badge.abgeglichen .d { background: #2E7D32; }
.bl-badge.ruecklast   { background: #FDECEA; color: #C0392B; } .bl-badge.ruecklast .d { background: #C0392B; }
/* Der WEG einer Zeile in der Abrechnung. Bewusst kräftig und nicht als stilles graues
   Zeichen: die eine Sorte holt Geld von den Konten der Mitglieder, die andere verschickt
   Papier, und in einer gemeinsamen Liste ist dieses Abzeichen das Einzige, was die
   beiden auf den ersten Blick trennt. Die Wörter sind die der ZAHLUNGSART am Profil,
   denn genau das Feld entscheidet, wer in welchem Lauf landet. */
.bl-badge.abr-weg-ls  { background: #FFF1E6; color: #B44A05; } .bl-badge.abr-weg-ls .d { background: #D95F02; }
.bl-badge.abr-weg-ue  { background: #E8F0FE; color: #1A56DB; } .bl-badge.abr-weg-ue .d { background: #1A56DB; }
.abr-col-weg { width: 130px; }
.bl-table td.abr-weg { white-space: nowrap; }

/* Sequence chip */
.bl-seq { font-size: 10.5px; font-weight: 700; letter-spacing: .3px; padding: 2px 7px; border-radius: 5px; }
.bl-seq.frst { background: #E8F0FE; color: #1A56DB; }
.bl-seq.rcur { background: #f1f1f4; color: #6b7280; }

/* Reconciliation (Abgleich) status of a run position. */
.bl-recon { font-size: 10.5px; font-weight: 700; padding: 2px 8px; border-radius: 20px; white-space: nowrap; background: #eef0f2; color: #5b6472; }
.bl-recon.ok  { background: #EAF4EB; color: #2E7D32; }
.bl-recon.bad { background: #FDECEA; color: #C0392B; }

/* Status-cell flags in the runs list (Rückläufer count, Vorabankündigung
   state) — same compact pill shape as .bl-recon, next to the status badge. */
.bl-flag { display: inline-flex; align-items: center; font-size: 10.5px; font-weight: 700; padding: 2px 8px; border-radius: 20px; white-space: nowrap; margin-left: 6px; vertical-align: middle; }
.bl-flag.ret     { background: #FDECEA; color: #C0392B; }
.bl-flag.pn-ok   { background: #EAF4EB; color: #2c5c30; }
.bl-flag.pn-open { background: #fff8f0; color: #B45309; }

/* Internal run id shown next to the period in the Beitragsläufe list/detail. */
.bl-runid { font-size: 11px; font-weight: 600; color: #9aa0a6; margin-left: 6px; }

/* Block summary cards (FRST / RCUR / total) */
.bl-blocks { display: flex; gap: 14px; flex-wrap: wrap; margin: 6px 0; }
.bl-block { flex: 1; min-width: 190px; border: 1px solid #e6e6ec; border-radius: 10px; padding: 14px 16px; background: #fcfcfd; }
.bl-block.total { background: #fff; }
.bl-block-t { font-size: 11px; font-weight: 700; text-transform: uppercase; letter-spacing: .4px; color: #8a8a94; margin-bottom: 8px; display: flex; align-items: center; gap: 7px; }
.bl-block-n { font-size: 20px; font-weight: 700; font-variant-numeric: tabular-nums; }
.bl-block-s { font-size: 12.5px; color: #888; margin-top: 2px; }

/* Detail meta row */
.bl-detail-head { display: flex; align-items: center; gap: 14px; flex-wrap: wrap; margin-bottom: 14px; }
.bl-detail-head .h { font-size: 20px; font-weight: 700; }
.bl-detail-meta { display: flex; gap: 30px; flex-wrap: wrap; margin-bottom: 20px; }
/* ── The opened run, grouped ─────────────────────────────────────────────────
   Up to eight equal-weight pairs used to sit in one flat row, so finding the
   one you wanted meant reading all of them. Three captions (Termine,
   Beteiligte, Weg) give the eye somewhere to land. Positionen and Summe are NOT
   among them any more: the tiles directly below state both, and a number worth
   showing twice on a screen about money is a number worth showing once.

   The pair row stays `.bl-detail-meta`, so the small-caps label and its value
   keep the styling they already have. Only the value steps down to the table
   body size, which is what makes the block read as quiet reference instead of a
   headline row. */
.bl-meta-groups { display: flex; flex-wrap: wrap; gap: 18px 46px; margin-bottom: 22px; }
.bl-meta-group { display: flex; flex-direction: column; gap: 5px; }
.bl-meta-cap {
  font-size: 10px; font-weight: 700; text-transform: uppercase; letter-spacing: .07em;
  color: #b4b4bd; margin-bottom: 2px;
}
.bl-meta-group .bl-detail-meta { margin-bottom: 0; gap: 28px; }
.bl-meta-group .bl-detail-meta .v { font-size: 13.5px; }

/* Every state strip in ONE place, between what the run IS and what can be done
   with it. They used to sit in two places, one above the button row and the
   rest below, so the reading order broke in the middle. `:empty` matters: the
   wrapper is always emitted and most runs have nothing to say. */
.bl-strips { display: flex; flex-direction: column; gap: 8px; margin: 4px 0 16px; }
.bl-strips:empty { display: none; }
.bl-strips .bl-strip { margin-bottom: 0; }

/* The file and its XSD stamp are a STATEMENT about the run, not an action, so
   they leave the button row. The bar itself appears only when the file is the
   route to the bank; where the bank takes direct debits the stamp stands alone
   (see fileLine in sepa-runs.js). */
.bl-filebar {
  display: flex; align-items: center; gap: 10px; flex-wrap: wrap;
  padding: 9px 12px; margin-bottom: 12px;
  background: #fafafb; border: 1px solid #ececf0; border-radius: 9px;
}
.bl-checkline { display: block; margin-bottom: 12px; }
.bl-detail-meta .k { font-size: 11px; color: #9a9aa2; text-transform: uppercase; letter-spacing: .4px; }
.bl-detail-meta .v { font-size: 15px; font-weight: 600; font-variant-numeric: tabular-nums; margin-top: 2px; }
.bl-actions { display: flex; gap: 10px; flex-wrap: wrap; align-items: center; margin: 4px 0 8px; }
/* A locked action (e.g. „Vorabankündigung vorbereiten" before the date clears the
   5-day window, or „anlegen" with nothing selected) must LOOK locked. */
/* Opacity + cursor come from the central :disabled rule now. This stays only
   because the hover guard is what keeps a locked button from lighting up. */
.bl-actions .btn-primary:disabled:hover { background: #1A1A2E; }

/* File chip + verified chip */
.bl-file { display: inline-flex; align-items: center; gap: 8px; background: #f6f8fc; border: 1px solid #dde5f2; border-radius: 8px; padding: 7px 11px; font-size: 13px; }
.bl-file .bl-mono { color: #1A1A2E; font-weight: 600; }
.bl-chk { display: inline-flex; align-items: center; gap: 5px; background: #EAF4EB; color: #2E7D32; font-size: 11.5px; font-weight: 700; padding: 4px 9px; border-radius: 20px; }

/* Create form */
.bl-field-row { display: flex; gap: 20px; flex-wrap: wrap; align-items: flex-start; margin-bottom: 6px; }
.bl-field { display: flex; flex-direction: column; gap: 6px; }
.bl-field label { font-size: 12px; font-weight: 600; color: #6b7280; }
.bl-field select, .bl-field input { padding: 9px 11px; border: 1px solid #ccc; border-radius: 7px; font-family: inherit; font-size: 14px; color: #1A1A2E; outline: none; min-width: 190px; }
.bl-field select:focus, .bl-field input:focus { border-color: #D95F02; }
.bl-editlink { font-size: 12.5px; color: #888; cursor: pointer; font-weight: 600; text-decoration: underline; }
.bl-editlink:hover { color: #D95F02; }

/* Scope toggle in the create preview ("Offene Rückstände einbeziehen") */
.bl-toggle { display: inline-flex; align-items: center; gap: 9px; font-size: 13.5px; color: #1A1A2E; cursor: pointer; }
.bl-toggle input { width: 17px; height: 17px; accent-color: #D95F02; cursor: pointer; flex: none; }
.bl-toggle.off { color: #6b7280; }
.bl-toggle-hint { font-size: 12.5px; color: #6b7280; margin: 7px 0 0; }

/* Einzugsdatum ändern: the inline editor inside a run's detail panel. Set apart
   from the action row above it, because it is a form and not one more button. */
.bl-datechange { background: #f7f8fa; border: 1px solid #ececf0; border-radius: 9px; padding: 14px 16px; margin: 4px 0 12px; }
/* The field is not inside a .bl-field-row here, so the column flex would stretch
   the .dfield wrapper across the whole card and park its calendar button at the far
   right, a hand's width from the input it belongs to. */
.bl-datechange .bl-field { align-items: flex-start; }
.bl-datechange .bl-toggle-hint { max-width: 62ch; }
.bl-datechange .bl-actions { margin: 12px 0 0; }

/* Create card (opens above the table, like the add-member form) */
.bl-card { background: #fff; border: 1px solid #e6e6ec; border-radius: 12px; padding: 20px 22px; box-shadow: 0 1px 3px rgba(0,0,0,.05); margin-bottom: 22px; }
.bl-card-head { font-size: 16px; font-weight: 700; color: #1A1A2E; margin-bottom: 16px; display: flex; align-items: center; gap: 8px; }

/* Inline detail row (expands under a clicked run, like the tx comment row) */
.bl-detail-row { display: none; }
.bl-detail-row.open { display: table-row; }
.bl-detail-row > td { background: #f6f7fb; padding: 0; border-bottom: 1px solid #e9e9f0; }
.bl-detail-panel { padding: 18px 22px; }

/* Dismissable, copyable error box (SEPA generate validation errors) */
.bl-error { position: relative; background: #fdf0ef; border: 1px solid #f3c9c4; border-radius: 9px; padding: 14px 16px 14px; margin: 14px 0; }
.bl-error-title { font-weight: 700; color: #b3372c; margin-bottom: 8px; font-size: 13.5px; padding-right: 24px; }
.bl-error-text { white-space: pre-wrap; word-break: break-word; font-family: ui-monospace, Menlo, Consolas, monospace; font-size: 12px; line-height: 1.5; color: #7a2a22; background: #fff; border: 1px solid #f0d4d0; border-radius: 6px; padding: 10px 12px; margin: 0 0 10px; max-height: 200px; overflow: auto; }
.bl-error-x { position: absolute; top: 8px; right: 11px; background: none; border: none; font-size: 22px; line-height: 1; color: #b3372c; cursor: pointer; padding: 0; }
.bl-error-x:hover { color: #8f2a20; }

/* Visually hidden but still clickable from script. NOT date-specific despite the
   name: the camt upload reuses it for its `<input type="file">`, which is why the
   name stays. It only really collapses to 1×1 outside a container that styles bare
   inputs, so the date field below brings its own rule instead of this one. */
.bl-date-hidden { position: absolute; right: 30px; bottom: 0; opacity: 0; width: 1px; height: 1px; min-width: 0; padding: 0; border: 0; pointer-events: none; }

/* ── EÜR view ─────────────────────────────────────── */
.euer-config { display: flex; gap: 22px; flex-wrap: wrap; align-items: flex-end; margin: 16px 0 18px; }
.euer-cfg-field { display: flex; flex-direction: column; gap: 6px; }
.euer-chips { display: flex; gap: 6px; flex-wrap: wrap; }
.euer-chip { border: 1px solid #e6e6ec; background: #fff; color: #555; border-radius: 8px; padding: 7px 13px; font-size: 13px; font-weight: 600; cursor: pointer; font-family: inherit; }
.euer-chip:hover { border-color: #D95F02; }
.euer-chip.active { background: #1A1A2E; color: #fff; border-color: #1A1A2E; }
.euer-input { padding: 8px 10px; border: 1px solid #e6e6ec; border-radius: 8px; font-size: 14px; width: 150px; box-sizing: border-box; font-family: inherit; }
.euer-input:focus { outline: none; border-color: #D95F02; }
.euer-sumgrid { display: grid; grid-template-columns: 1fr 1fr; gap: 26px; margin: 8px 0 4px; }
@media (max-width: 720px) { .euer-sumgrid { grid-template-columns: 1fr; } }
.euer-sumcol h3 { font-size: 12px; font-weight: 700; color: #555; margin: 0 0 8px; padding-bottom: 6px; border-bottom: 1px solid #e6e6ec; }
.euer-row { display: flex; justify-content: space-between; padding: 5px 0; font-size: 13.5px; }
.euer-row .v { font-variant-numeric: tabular-nums; font-weight: 600; }
.euer-row.un .k { color: #C62828; }
.euer-row.tot { border-top: 1.5px solid #e6e6ec; margin-top: 6px; padding-top: 9px; font-weight: 700; }
.euer-net { display: flex; justify-content: space-between; align-items: center; margin-top: 14px; padding: 12px 16px; background: #ECEDF5; border-radius: 10px; font-weight: 700; font-size: 15px; }
.euer-net .v { font-variant-numeric: tabular-nums; }
.euer-banner { display: flex; align-items: center; gap: 10px; padding: 12px 16px; border-radius: 10px; font-size: 14px; font-weight: 600; }
.euer-banner.ok { background: #EAF4EB; color: #2E7D32; }
.euer-banner.bad { background: #FDECEC; color: #C62828; }
.euer-banner.warn { background: #FEF6E6; color: #B45309; }
.euer-banner small { font-weight: 500; opacity: .85; margin-left: auto; font-size: 12px; }
/* Sideways scroll for the wide desktop table. A CLASS rather than the inline style
   this used to be: the phone card layout has to switch the scroll container off, and
   an inline style cannot be overridden from a stylesheet. Mirrors .mand-table-wrap
   and .bl-table-wrap, which already work that way. */
.euer-table-wrap { overflow-x: auto; }
#euerTable { width: 100%; border-collapse: collapse; }
/* Typography from the base rule; the hairlines and the #bbb-to-white header are
   the only things that changed here. */
#euerTable th { border-bottom: 1px solid #e6e6ec; }
#euerTable td { border-bottom: 1px solid #f2f2f5; vertical-align: middle; }
#euerTable td.num { text-align: right; font-variant-numeric: tabular-nums; font-weight: 600; white-space: nowrap; }
#euerTable select.cat { font-size: 12.5px; padding: 4px 6px; border: 1px solid #e6e6ec; border-radius: 6px; max-width: 210px; }
#euerTable select.cat.empty { border-color: #D95F02; color: #D95F02; font-weight: 600; }
.euer-badge { font-size: 10px; border-radius: 4px; padding: 2px 6px; margin-left: 6px; }
/* EÜR Kategorien & Regeln editor (mobile layer in mobile.css) */
.rgl-title { margin-top: 0; }
.rgl-title-row { margin-bottom: 16px; }
.rgl-head,
.rgl-row { display: grid; grid-template-columns: 176px 1.1fr 1.5fr 40px; gap: 10px; align-items: center; }
.rgl-head { padding: 0 2px 7px; font-size: 11px; font-weight: 700; letter-spacing: .04em; text-transform: uppercase; color: #b3b3bd; }
.rgl-row { padding: 7px 0; border-bottom: 1px solid #f4f4f7; }
.rgl-flabel { display: none; }
/* The Art toggle is the shared `.seg` plus what is specific to it: it fills its
   grid cell, its segments are tighter because three sit in one narrow column,
   and its chosen state carries the Einnahme/Ausgabe colours instead of the
   component's neutral orange. */
.rgl-seg { width: 100%; }
.rgl-seg button { padding: 8px 6px; }
.rgl-seg button.on[data-art="einnahme"] { background: #e9f5ec; color: #2e7d32; }
.rgl-seg button.on[data-art="ausgabe"] { background: #fdecec; color: #c62828; }
.rgl-inp { width: 100%; box-sizing: border-box; border: 1px solid #e0e0e8; border-radius: 9px; padding: 9px 11px; font-family: inherit; font-size: 13px; color: #1A1A2E; background: #fff; outline: none; }
.rgl-inp::placeholder { color: #b8b8c2; }
.rgl-inp:focus { border-color: #D95F02; box-shadow: 0 0 0 3px rgba(217,95,2,.12); }
.rgl-inp.rgl-kw { background: #fcfcfd; }
.rgl-del { width: 34px; height: 34px; display: inline-flex; align-items: center; justify-content: center; border: 1px solid #ececef; background: #fff; border-radius: 9px; color: #b0b0ba; cursor: pointer; }
.rgl-del:hover { border-color: #f0c9c9; background: #fdeeee; color: #c62828; }
.rgl-del svg { width: 15px; height: 15px; }
.rgl-divider { display: flex; align-items: center; gap: 10px; margin: 18px 0 10px; }
.rgl-divider span { font-size: 11px; font-weight: 700; letter-spacing: .04em; text-transform: uppercase; color: #b3b3bd; white-space: nowrap; }
.rgl-divider::after { content: ""; flex: 1; height: 1px; background: #f0f0f4; }
/* One column since the per-row hint moved into the (i); the second column would
   otherwise sit empty at 1fr and stretch the row. */
.rgl-sysrow { display: grid; grid-template-columns: 1fr; padding: 8px 0; }
.rgl-sysname { display: flex; align-items: center; gap: 7px; font-size: 13.5px; font-weight: 600; color: #6a6a76; }
.rgl-lock { display: inline-flex; }
.rgl-lock svg { width: 13px; height: 13px; color: #b0b0ba; }
.rgl-systag { font-size: 11px; font-weight: 600; color: #9a9aa4; background: #f3f3f6; border-radius: 6px; padding: 2px 8px; }
.rgl-footer { display: flex; gap: 10px; margin-top: 18px; }

/* ── CSV import modal ─────────────────────────────── */
.csv-import-box { max-width: 460px; text-align: left; max-height: 88vh; overflow-y: auto; }
/* The h3 sits in an .info-row with the (i); the row carries the spacing the
   dropped intro paragraph used to provide. */
.csv-import-box .info-row { margin-bottom: 18px; }
.csv-field { margin: 14px 0; display: flex; flex-direction: column; gap: 6px; }
.csv-select {
  width: 100%; padding: 9px 11px; border: 1px solid #e6e6ec; border-radius: 8px;
  font-size: 14px; font-family: inherit; background: #fff; color: #1A1A2E; box-sizing: border-box; cursor: pointer;
}
.csv-select:focus { outline: none; border-color: #D95F02; }
.csv-file { font-size: 13.5px; color: #555; max-width: 100%; }
.csv-file::file-selector-button {
  font-family: inherit; font-size: 13px; font-weight: 600; color: #1A1A2E;
  background: #fff; border: 1px solid #e6e6ec; border-radius: 8px;
  padding: 8px 14px; margin-right: 10px; cursor: pointer; transition: border-color .15s, color .15s;
}
.csv-file::file-selector-button:hover { border-color: #D95F02; color: #D95F02; }
.csv-preview { display: none; margin: 12px 0; padding: 12px 14px; background: #f6f7f9; border-radius: 8px; font-size: 14px; line-height: 1.5; }
.csv-import-commit { background: #1A1A2E; }
.csv-import-commit:hover { background: #2d2d4e; }
.csv-import-commit:disabled { opacity: .5; cursor: not-allowed; }
.euer-pdf-opt { display: flex; align-items: center; gap: 8px; font-size: 14px; color: #333; cursor: pointer; padding: 3px 0; font-weight: normal; text-transform: none; letter-spacing: 0; }
.euer-pdf-opt input { margin: 0; width: auto; }
