/* dashboard.css — page + widget styles. */

:root {
  --dash-bg: #f0f2f5;
  --dash-surface: #ffffff;
  --dash-surface2: #f8f9fb;
  --dash-border: #e2e5ea;
  --dash-text: #1a1d23;
  --dash-text-dim: #6b7280;
  --dash-blue: #2563eb;
  --dash-blue-bg: rgba(37,99,235,.08);
  --dash-purple: #7c3aed;
  --dash-amber: #d97706;
  --dash-green: #16a34a;
  --dash-red: #dc2626;
  --dash-radius: 10px;
  --dash-shadow: 0 1px 3px rgba(0,0,0,.06);
}

* { box-sizing: border-box; }
body {
  margin: 0;
  font-family: 'Inter', -apple-system, sans-serif;
  background: var(--dash-bg);
  color: var(--dash-text);
}

/* ── Page header ─────────────────────────────────────── */
.dash-header {
  background: linear-gradient(135deg, #1e293b 0%, #334155 100%);
  color: #fff;
  padding: 14px 18px;
  display: flex; align-items: center; justify-content: space-between;
  flex-wrap: wrap; gap: 12px;
}
.dash-header-left {
  display: flex; align-items: baseline; gap: 14px;
  flex-wrap: wrap;
}
.dash-header h1 {
  font-size: 19px; font-weight: 700; margin: 0;
}
.dash-header h1 .badge {
  font-size: 10px; font-weight: 600; padding: 3px 9px;
  border-radius: 20px; background: rgba(255,255,255,.15);
  color: rgba(255,255,255,.85); letter-spacing: .5px;
  text-transform: uppercase; margin-left: 10px;
}
.dash-today {
  font-size: 13px; font-weight: 500; color: rgba(255,255,255,.7);
  padding: 4px 10px; border-radius: 14px;
  background: rgba(255,255,255,.08);
  border: 1px solid rgba(255,255,255,.1);
}
.dash-header a.back {
  color: rgba(255,255,255,.7); text-decoration: none;
  font-size: 13px; padding: 6px 12px; border-radius: 6px;
}
.dash-header a.back:hover { background: rgba(255,255,255,.1); color: #fff; }

.dash-header-actions { display: flex; gap: 10px; align-items: center; flex-wrap: wrap; }
.dash-updated {
  font-size: 12px; color: rgba(255,255,255,.65);
  font-family: 'SF Mono', monospace;
  padding: 3px 8px; border-radius: 10px;
  background: rgba(255,255,255,.06);
}
.dash-btn {
  background: rgba(255,255,255,.1); color: #fff; border: 1px solid rgba(255,255,255,.2);
  padding: 7px 14px; border-radius: 7px; font-size: 13px; font-weight: 500;
  cursor: pointer; transition: background .15s;
}
.dash-btn:hover { background: rgba(255,255,255,.18); }
.dash-btn-small {
  background: rgba(255,255,255,.08); color: #fff; border: 1px solid rgba(255,255,255,.15);
  padding: 5px 12px; border-radius: 5px; font-size: 11px; font-weight: 500;
  cursor: pointer; transition: background .15s;
}
.dash-btn-small:hover { background: rgba(255,255,255,.14); }
.dash-btn.primary { background: var(--dash-blue); border-color: var(--dash-blue); }
.dash-btn.primary:hover { background: #1d4fd4; }
.dash-btn.danger { background: rgba(220,38,38,.85); border-color: rgba(220,38,38,1); }

/* ── Toolbar (period + actions) ─────────────────────── */
.dash-toolbar {
  background: var(--dash-surface);
  border-bottom: 1px solid var(--dash-border);
  padding: 12px 28px;
  display: flex; gap: 16px; align-items: center; flex-wrap: wrap;
  position: relative; z-index: 60; /* keep toolbar above GridStack edit handles */
}
.dash-toolbar .dash-btn {
  background: var(--dash-blue-bg); color: var(--dash-blue);
  border: 1px solid rgba(37,99,235,.2);
  padding: 7px 14px; border-radius: 7px; font-size: 13px; font-weight: 500;
  cursor: pointer; transition: background .15s;
  position: relative; z-index: 61;
}
.dash-toolbar .dash-btn:hover { background: rgba(37,99,235,.15); }
.dash-toolbar .dash-btn.primary { background: var(--dash-blue); color: #fff; border-color: var(--dash-blue); }
.dash-toolbar .dash-btn.primary:hover { background: #1d4fd4; }
.dash-toast {
  font-size: 12px; padding: 4px 10px; border-radius: 12px;
  background: var(--dash-surface2); color: var(--dash-text-dim);
  opacity: 0; transition: opacity .2s;
}
.dash-toast.visible { opacity: 1; }
.dash-toast[data-kind="error"] {
  background: rgba(220,38,38,.1); color: var(--dash-red);
}

/* Sparkline hover hint — the invisible per-point rects carry <title> tooltips
   so the cursor change tells users the chart is interactive. */
.dash-spark-pt rect { cursor: help; }
/* Sparkline value-label overlay. Value labels are HTML <span>s positioned on
   top of the SVG (via percentage X + pixel Y) instead of inline <text>, so
   they don't get distorted when the SVG stretches to fill its container. */
.dash-spark-wrap { position: relative; }
.dash-spark-wrap > svg { position: absolute; inset: 0; }
.dash-spark-label {
  position: absolute;
  font-weight: 700;
  line-height: 1;
  white-space: nowrap;
  pointer-events: none;
  letter-spacing: -0.01em;
  /* Soft white halo so labels stay readable when they overlap the line */
  text-shadow: 0 0 3px #fff, 0 0 3px #fff, 0 1px 2px rgba(255,255,255,0.9);
}
.dash-period-group {
  display: inline-flex; background: var(--dash-surface2);
  border: 1px solid var(--dash-border); border-radius: 8px;
  padding: 3px;
}
.dash-period-btn {
  background: transparent; border: 0; padding: 5px 12px;
  border-radius: 6px; font-size: 12px; font-weight: 500;
  color: var(--dash-text-dim); cursor: pointer; transition: all .15s;
}
.dash-period-btn:hover { color: var(--dash-text); }
.dash-period-btn.active { background: var(--dash-blue); color: #fff; }

.dash-toolbar-info {
  font-size: 12px; color: var(--dash-text-dim);
  margin-left: auto;
}

/* ── Grid container ─────────────────────────────────── */
/* Wider max-width + tighter padding so widgets get more horizontal room
   on ultra-wide displays. User complaint: "виджеты ограничены по бокам". */
.dash-grid-wrap {
  padding: 12px 16px 32px;
  max-width: 1920px; margin: 0 auto;
}

.grid-stack { background: transparent; }
.grid-stack-item-content {
  background: var(--dash-surface);
  border-radius: var(--dash-radius);
  box-shadow: var(--dash-shadow);
  overflow: hidden;
  display: flex; flex-direction: column;
  border: 1px solid var(--dash-border);
}

.dash-widget-header {
  display: flex; align-items: center; justify-content: space-between;
  padding: 10px 14px; border-bottom: 1px solid var(--dash-border);
  background: var(--dash-surface2);
  flex-shrink: 0;
}
.dash-widget-header .title {
  font-size: 14px; font-weight: 600;
  display: flex; align-items: center; gap: 8px;
}
.dash-widget-header .title .icon { font-size: 16px; }
.dash-widget-actions { display: flex; gap: 4px; align-items: center; }
.dash-widget-period {
  font-size: 11px; padding: 3px 8px; border-radius: 12px;
  background: var(--dash-blue-bg); color: var(--dash-blue);
  font-weight: 600;
}
.dash-widget-period.overridden { background: rgba(124,58,237,.1); color: var(--dash-purple); }

.dash-icon-btn {
  background: transparent; border: 0; cursor: pointer; padding: 4px 6px;
  border-radius: 5px; color: var(--dash-text-dim); font-size: 14px;
}
.dash-icon-btn:hover { background: rgba(0,0,0,.05); color: var(--dash-text); }
.dash-icon-btn.remove { color: var(--dash-red); display: none; }

.dash-widget-body {
  flex: 1; overflow: auto;
  padding: 12px 14px;
  /* min-* 0 is the canonical fix for flex/grid children that otherwise
     refuse to shrink below their content size and cause clipping when the
     GridStack cell is resized smaller than the natural content width. */
  min-height: 0; min-width: 0;
}
/* Any direct grid child of the body that's a grid container itself
   inherits the same shrink-friendly semantics. */
.dash-widget-body > * { min-width: 0; }

.dash-widget-empty {
  display: flex; align-items: center; justify-content: center;
  height: 100%; color: var(--dash-text-dim); font-size: 13px;
  text-align: center;
}

/* Edit mode visuals */
body.dash-edit .grid-stack-item-content {
  outline: 2px dashed transparent;
  transition: outline-color .15s;
}
body.dash-edit .grid-stack-item-content:hover {
  outline-color: var(--dash-blue);
}
body.dash-edit .dash-icon-btn.remove { display: inline-block; }
body.dash-edit .dash-widget-header { cursor: move; }

/* Compact widget (Motivation banner) — header is completely hidden,
   including in edit mode. User feedback: "в редакторе тоже можно
   оставить без внешнего контора и подписи, т.к. занимает место".
   In edit mode, only the ✕ remove button surfaces as a tiny floating
   overlay at the top-right of the widget content. Drag still works
   via the corner resize handle (GridStack's resize is independent of
   the drag handle); to move the widget, remove + re-add. */
/* PR-FFF: simplified compact behavior.
   - Non-edit mode: header hidden completely (saves chrome).
   - Edit mode:     full header restored so user can drag widget by it.
   Previous implementation used a tiny floating ✕ overlay with
   `pointer-events: none` on the wrapper, which silently disabled
   GridStack drag (it binds to `.dash-widget-header`). Restoring the
   normal header is the simpler + more honest fix. */
.dash-widget-header.is-compact { display: none; }
body.dash-edit .dash-widget-header.is-compact {
  /* Use the default header layout — flex row with title + actions.
     Drag handle (the whole header) gets default pointer events back. */
  display: flex;
}

/* ── Scout Activity widget ───────────────────────────── */
.dash-scout-summary {
  display: flex; align-items: baseline; gap: 8px;
  flex-wrap: wrap;
  margin-bottom: 10px;
}
.dash-scout-summary-val {
  font-size: 22px; font-weight: 700; color: var(--dash-blue);
  font-family: 'SF Mono', monospace;
}
.dash-scout-summary-lbl {
  font-size: 12px; color: var(--dash-text-dim);
}
.dash-scout-grid {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(min(180px, 100%), 1fr));
  gap: 10px;
}
.dash-scout-card {
  background: var(--dash-surface2);
  border: 1px solid var(--dash-border);
  border-radius: 8px;
  padding: 8px 10px;
  display: flex; flex-direction: column; gap: 4px;
  min-width: 0;
}
.dash-scout-head {
  display: flex; align-items: center; justify-content: space-between;
  gap: 6px;
}
/* Name + region pill share the same row — pill sits right after the name.
   `min-width:0` lets the name truncate when space is tight. */
.dash-scout-name-wrap {
  display: flex; align-items: center; gap: 6px; min-width: 0; flex: 1;
}
.dash-scout-name {
  font-size: 12px; font-weight: 600;
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
  min-width: 0; flex: 1 1 auto;
}
.dash-scout-region {
  font-size: 10px; padding: 1px 7px; border-radius: 10px;
  background: rgba(37,99,235,.08); color: var(--dash-blue);
  text-transform: capitalize; font-weight: 500;
  flex-shrink: 0;
}
.dash-scout-card { cursor: pointer; }
.dash-scout-card:hover { background: #eef2f7; }
/* Zero-activity scouts (no leads in the selected period) get dimmed so the
   eye can quickly skim past them while still seeing who didn't work. */
.dash-scout-card.inactive { opacity: 0.55; }
.dash-scout-card.inactive:hover { opacity: 0.85; }
/* Region-name chip used by Region Activity cards — same geometry as the
   scout-region pill but the color comes from REGION_COLORS inline. */
.dash-region-chip {
  display: inline-block;
  font-size: 12px; font-weight: 600;
  padding: 2px 8px; border-radius: 10px;
  background: rgba(37,99,235,.08); color: #1f2937;
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
  min-width: 0; flex: 1 1 auto; max-width: 100%;
}
.dash-scout-total {
  font-family: 'SF Mono', monospace; font-size: 15px; font-weight: 700;
  color: var(--dash-blue); flex-shrink: 0;
}
.dash-scout-spark { width: 100%; }
.dash-scout-meta {
  display: flex; justify-content: space-between;
  font-size: 10px; color: var(--dash-text-dim);
}

/* ── Location Stages widget ─────────────────────────── */
/* `minmax(min(96px,100%),1fr)` is the standard CSS-Grid trick that lets the
   cells shrink below their content size when the widget is resized down —
   without it the cards would overflow and clip when the grid can't fit. */
.dash-stage-grid {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(min(96px, 100%), 1fr));
  gap: 8px;
}
.dash-stage-card {
  text-decoration: none; color: inherit;
  background: var(--dash-surface2);
  border: 1px solid var(--dash-border);
  border-left: 4px solid var(--accent, #ccc);
  border-radius: 8px;
  padding: 8px 12px;
  display: flex; flex-direction: column; gap: 2px;
  min-width: 0;
  transition: transform .15s, box-shadow .15s;
}
.dash-stage-card:hover {
  transform: translateY(-1px); box-shadow: 0 4px 12px rgba(0,0,0,.06);
}
.dash-stage-icon { font-size: 14px; }
.dash-stage-count {
  font-family: 'SF Mono', monospace; font-size: 22px; font-weight: 700;
  color: var(--accent, var(--dash-text));
  line-height: 1.1;
}
.dash-stage-label {
  font-size: 11px; color: var(--dash-text-dim); font-weight: 500;
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}

/* ── Pending IC widget ──────────────────────────────── */
.dash-pending-wrap { overflow-x: auto; }
.dash-pending-table {
  width: 100%; border-collapse: collapse; font-size: 13px;
}
.dash-pending-table thead th {
  text-align: left; padding: 8px 10px;
  font-size: 11px; font-weight: 600; text-transform: uppercase;
  letter-spacing: .5px; color: var(--dash-text-dim);
  border-bottom: 1px solid var(--dash-border); background: var(--dash-surface);
  position: sticky; top: 0; z-index: 1;
}
.dash-pending-table tbody td {
  padding: 7px 10px; border-bottom: 1px solid #f0f1f3;
}
.dash-pending-row { cursor: pointer; transition: background .15s; }
.dash-pending-row:hover { background: var(--dash-surface2); }
.dash-pending-name { font-weight: 500; }
.dash-pending-num { font-family: 'SF Mono', monospace; text-align: right; }
.dash-pending-days { text-align: center; }
.dash-days {
  font-family: 'SF Mono', monospace; font-weight: 600;
  padding: 2px 8px; border-radius: 12px;
  background: var(--dash-blue-bg); color: var(--dash-blue);
  font-size: 12px;
}
.dash-days-warn {
  background: rgba(217,119,6,.12); color: var(--dash-amber);
}
.dash-days-na {
  background: var(--dash-surface2); color: var(--dash-text-dim);
}
/* Format chip — single letter, brand-colored per format. */
.dash-fmt-chip {
  display: inline-block; min-width: 24px;
  font-family: 'SF Mono', monospace; font-weight: 700; font-size: 11px;
  padding: 2px 0; border-radius: 6px; text-align: center;
}
.dash-fmt-B  { background: rgba(37,99,235,.12);  color: var(--dash-blue); }
.dash-fmt-M  { background: rgba(124,58,237,.12); color: var(--dash-purple); }
.dash-fmt-S  { background: rgba(22,163,74,.12);  color: var(--dash-green); }
.dash-fmt-G  { background: rgba(217,119,6,.12);  color: var(--dash-amber); }
.dash-fmt-na { background: var(--dash-surface2); color: var(--dash-text-dim); }

/* ── Add-widget modal ───────────────────────────────── */
.dash-modal {
  position: fixed; inset: 0;
  background: rgba(15,23,42,.55); z-index: 100;
  display: none; align-items: center; justify-content: center;
}
.dash-modal.open { display: flex; }
.dash-modal-box {
  background: var(--dash-surface);
  border-radius: 12px;
  max-width: 560px; width: calc(100% - 40px);
  max-height: 80vh; overflow: auto;
  box-shadow: 0 20px 60px rgba(0,0,0,.3);
}
.dash-modal-head {
  display: flex; align-items: center; justify-content: space-between;
  padding: 14px 18px; border-bottom: 1px solid var(--dash-border);
}
.dash-modal-head h3 { margin: 0; font-size: 16px; font-weight: 700; }
.dash-modal-body { padding: 12px 18px 18px; }
.dash-catalog-item {
  display: flex; align-items: flex-start; gap: 12px;
  padding: 12px; border: 1px solid var(--dash-border); border-radius: 8px;
  margin-bottom: 8px; cursor: pointer; transition: background .15s, border-color .15s;
}
.dash-catalog-item:hover {
  background: var(--dash-surface2);
  border-color: var(--dash-blue);
}
.dash-catalog-item.disabled {
  opacity: .5; cursor: not-allowed;
}
.dash-catalog-item.disabled:hover { background: transparent; border-color: var(--dash-border); }
.dash-catalog-icon { font-size: 22px; line-height: 1; flex-shrink: 0; }
.dash-catalog-title { font-size: 14px; font-weight: 600; margin-bottom: 2px; }
.dash-catalog-desc { font-size: 12px; color: var(--dash-text-dim); }
.dash-catalog-on {
  font-size: 10px; padding: 2px 8px; border-radius: 10px;
  background: var(--dash-blue-bg); color: var(--dash-blue);
  font-weight: 600; margin-left: auto; flex-shrink: 0;
}
.dash-catalog-soon {
  font-size: 10px; padding: 2px 8px; border-radius: 10px;
  background: rgba(217,119,6,.12); color: var(--dash-amber);
  font-weight: 600; margin-left: auto; flex-shrink: 0;
  letter-spacing: .5px; text-transform: uppercase;
}

/* ── Loading ────────────────────────────────────────── */
.dash-loading {
  text-align: center; padding: 60px 20px; color: var(--dash-text-dim);
}
.dash-spinner {
  width: 36px; height: 36px;
  border: 3px solid var(--dash-border);
  border-top-color: var(--dash-blue);
  border-radius: 50%;
  animation: dash-spin 1s linear infinite;
  margin: 0 auto 14px;
}
@keyframes dash-spin { to { transform: rotate(360deg); } }

/* ── Tasks widgets (my_tasks / watch_user_tasks) ────── */
.dash-tasks-head {
  display: flex; align-items: center; gap: 12px;
  margin-bottom: 10px;
}
.dash-task-donut-wrap { flex-shrink: 0; }
.dash-task-donut { display: block; }
.dash-tasks-head-text { display: flex; flex-direction: column; gap: 2px; min-width: 0; flex: 1; }
.dash-tasks-head-lbl {
  font-size: 12px; color: var(--dash-text-dim);
  text-transform: uppercase; letter-spacing: .5px; font-weight: 600;
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.dash-tasks-head-sub { font-size: 12px; color: var(--dash-text-dim); }
.dash-tasks-head-cnt {
  font-family: 'SF Mono', monospace; font-size: 16px; font-weight: 700;
  color: var(--dash-blue);
}
/* Diagnostic line at top of My Tasks (own queue only) — shows the
   currently-signed-in email + 8-char uid prefix so the user can verify
   identity without DevTools. */
.dash-task-diag {
  font-size: 10px; color: var(--dash-text-dim);
  margin-bottom: 6px;
  padding: 4px 8px;
  background: var(--dash-surface2);
  border-radius: 4px;
  font-family: 'SF Mono', monospace;
}
.dash-task-diag b { font-weight: 600; color: var(--dash-text); }

/* Inspect (🔍) button per task row — only rendered when showDiag=true.
   Opens a modal with raw JSON of the task document so the user can
   identify the source of unfamiliar tasks. Visible on hover. */
.dash-task-inspect {
  background: transparent; border: 0; cursor: pointer;
  font-size: 12px; padding: 2px 6px;
  color: var(--dash-text-dim);
  opacity: 0; transition: opacity .15s, color .15s;
  flex-shrink: 0;
}
.dash-task-row:hover .dash-task-inspect { opacity: 1; }
.dash-task-inspect:hover { color: var(--dash-blue); }

/* Inspect modal — uses .dash-modal frame but JSON pre is a code block.
   Sits above everything so user can read raw data without leaving page. */
.dash-task-inspect-hint {
  font-size: 11px; color: var(--dash-text-dim);
  margin-bottom: 8px;
}
.dash-task-inspect-hint code {
  background: var(--dash-surface2);
  padding: 1px 4px; border-radius: 3px;
  font-family: 'SF Mono', monospace;
}
.dash-task-inspect-json {
  font-family: 'SF Mono', Menlo, monospace;
  font-size: 11px;
  background: #0f172a; color: #e2e8f0;
  padding: 12px;
  border-radius: 6px;
  overflow: auto;
  max-height: 60vh;
  margin: 0;
  white-space: pre;
  user-select: text;
}

.dash-task-list {
  display: flex; flex-direction: column; gap: 4px;
}
.dash-task-row {
  display: flex; align-items: center; gap: 8px;
  padding: 7px 10px; border-radius: 6px;
  text-decoration: none; color: inherit;
  background: var(--dash-surface2);
  transition: background .15s, transform .1s;
  font-size: 13px; min-width: 0;
  cursor: pointer; user-select: none;
}
.dash-task-row:hover { background: #eef2f7; }
.dash-task-row:active { transform: translateY(1px); }
.dash-task-row:focus { outline: 2px solid var(--dash-blue); outline-offset: 1px; }
/* Task row now has a 2-line stack: title on top, subtitle (creator · time)
   below. `.dash-task-main` is the flex column holding both. */
.dash-task-main {
  flex: 1; min-width: 0;
  display: flex; flex-direction: column; gap: 1px;
}
.dash-task-title {
  flex: 1; min-width: 0;
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.dash-task-sub {
  font-size: 10px; color: var(--dash-text-dim);
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.dash-task-status {
  font-size: 10px; padding: 2px 8px; border-radius: 10px;
  font-weight: 600; flex-shrink: 0;
  text-transform: lowercase;
}
.dash-task-status.st-todo     { background: rgba(37,99,235,.1); color: var(--dash-blue); }
.dash-task-status.st-progress { background: rgba(217,119,6,.12); color: var(--dash-amber); }
.dash-task-status.st-pending  { background: rgba(124,58,237,.12); color: var(--dash-purple); }
.dash-task-status.st-review   { background: rgba(22,163,74,.12); color: var(--dash-green); }

/* ── Task groups (My Tasks grouped by project) ────────── */
.dash-task-groups { display: flex; flex-direction: column; gap: 6px; }
.dash-task-group {
  border-radius: 8px; background: var(--dash-surface);
  border: 1px solid var(--dash-border);
  overflow: hidden;
}
.dash-task-group-head {
  display: flex; align-items: center; gap: 8px;
  padding: 7px 10px;
  cursor: pointer; user-select: none;
  background: var(--dash-surface2);
  font-size: 12px; font-weight: 600;
  transition: background .15s;
}
.dash-task-group-head:hover { background: #eef2f7; }
.dash-task-group-name { flex: 1; min-width: 0; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.dash-task-group-cnt {
  font-family: 'SF Mono', monospace; font-size: 11px;
  padding: 1px 7px; border-radius: 10px;
  background: var(--dash-blue-bg); color: var(--dash-blue);
  flex-shrink: 0;
}
.dash-task-group-chev {
  font-size: 10px; color: var(--dash-text-dim);
  transition: transform .2s;
  flex-shrink: 0;
}
.dash-task-group.collapsed .dash-task-group-chev { transform: rotate(-90deg); }
.dash-task-group-body {
  display: flex; flex-direction: column; gap: 3px;
  padding: 6px;
  max-height: 600px;
  transition: max-height .2s ease, padding .2s ease, opacity .15s ease;
  overflow: hidden;
}
.dash-task-group.collapsed .dash-task-group-body {
  max-height: 0; padding-top: 0; padding-bottom: 0; opacity: 0;
}
.dash-task-group .dash-task-row { background: var(--dash-surface2); }
.dash-task-group .dash-task-row:hover { background: #eef2f7; }
.dash-pri-dot {
  width: 8px; height: 8px; border-radius: 50%;
  flex-shrink: 0; display: inline-block;
}
.dash-pri-1 { background: #dc2626; }
.dash-pri-2 { background: #f97316; }
.dash-pri-3 { background: #facc15; }
.dash-pri-none { background: #cbd5e1; }
.dash-tasks-foot {
  margin-top: 8px; text-align: center;
  font-size: 11px; color: var(--dash-text-dim);
}

/* ── Counter widget (tasks_done_week) ────────────────── */
.dash-counter-card {
  height: 100%;
  display: flex; flex-direction: column; gap: 4px;
  justify-content: center;
}
.dash-counter-label {
  font-size: 11px; color: var(--dash-text-dim);
  text-transform: uppercase; letter-spacing: .5px; font-weight: 600;
}
.dash-counter-value {
  font-family: 'SF Mono', monospace; font-size: 42px; font-weight: 700;
  color: var(--dash-green); line-height: 1;
}
.dash-counter-spark { width: 100%; }
.dash-counter-foot {
  font-size: 11px; color: var(--dash-text-dim);
}

/* ── Period override popover ────────────────────────── */
.dash-popover {
  position: absolute; z-index: 50;
  background: var(--dash-surface);
  border: 1px solid var(--dash-border);
  border-radius: 8px;
  box-shadow: 0 8px 24px rgba(0,0,0,.12);
  min-width: 160px; padding: 4px;
}
.dash-popover-item {
  padding: 6px 12px; font-size: 13px; cursor: pointer;
  border-radius: 5px; display: flex; justify-content: space-between;
  align-items: center;
}
.dash-popover-item:hover { background: var(--dash-surface2); }
.dash-popover-item.active { background: var(--dash-blue-bg); color: var(--dash-blue); font-weight: 600; }
.dash-popover-divider {
  height: 1px; background: var(--dash-border); margin: 4px 0;
}
.dash-popover-label {
  font-size: 10px; color: var(--dash-text-dim);
  text-transform: uppercase; letter-spacing: .5px;
  padding: 4px 12px 2px;
}

/* ── Pending-IC saved-by tag ─────────────────────────── */
.dash-pending-by {
  font-size: 11px; color: var(--dash-text-dim);
}

/* ── Region Activity drill-down: traffic indicators ──── */
.dash-traffic-yes { color: var(--dash-green); font-weight: 600; }
.dash-traffic-no  { color: var(--dash-text-dim); }
/* PR-ZZZ: when traffic chip carries a link, decorate it like a link
   on hover without losing the green colour. */
a.dash-traffic-yes {
  text-decoration: none;
  cursor: pointer;
}
a.dash-traffic-yes:hover {
  text-decoration: underline;
}

/* PR-ZZZ: clickable lead-name cell (scout-activity + region-activity
   overlay tables). Inherits color so the row visual stays consistent
   with non-link cells, but underlines on hover for affordance. */
.dash-pending-link {
  color: inherit;
  text-decoration: none;
  cursor: pointer;
}
.dash-pending-link:hover {
  color: var(--dash-blue);
  text-decoration: underline;
}

/* ── Stage pill (PR-RR) ────────────────────────────────────
   Used in the Region Activity overlay detail table to show each
   lead's current funnel position. Three flavours:
     .dash-stage-active  — neutral purple, normal in-flight stages
     .dash-stage-lost    — red, status_id 143 (Unsuccessful Deal)
     .dash-stage-won     — green, status_id 142 (Won)
     .dash-stage-unknown — gray, status_id not in funnel map
   The .dash-stage-reason chip appears below a lost pill and shows
   the rejection reason from amoCRM custom field 749419. */
.dash-stage-wrap {
  display: flex; flex-direction: column; align-items: flex-start; gap: 3px;
}
.dash-stage-pill {
  display: inline-block;
  padding: 2px 8px;
  border-radius: 10px;
  font-size: 10px; font-weight: 600;
  letter-spacing: .2px;
  white-space: nowrap;
}
.dash-stage-active {
  background: rgba(124, 58, 237, .12);
  color: #6d28d9;
}
.dash-stage-lost {
  background: rgba(220, 38, 38, .14);
  color: #b91c1c;
}
.dash-stage-won {
  background: rgba(34, 197, 94, .16);
  color: #15803d;
}
.dash-stage-signed {
  background: rgba(59, 130, 246, .14);
  color: #1e40af;
}
.dash-stage-unknown {
  background: var(--dash-surface2);
  color: var(--dash-text-dim);
  font-style: italic;
}
.dash-stage-reason {
  font-size: 10px;
  color: var(--dash-text-dim);
  font-style: italic;
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
  max-width: 220px;
}

/* ── Waterfall Live ─────────────────────────────────── */
.dash-wf-cards {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(min(120px, 100%), 1fr));
  gap: 8px;
  margin-bottom: 12px;
}
.dash-wf-card {
  background: var(--dash-surface2);
  border: 1px solid var(--dash-border);
  border-left: 4px solid var(--accent, #ccc);
  border-radius: 8px;
  padding: 8px 12px;
  display: flex; flex-direction: column; gap: 2px;
}
.dash-wf-cnt {
  font-family: 'SF Mono', monospace; font-size: 22px; font-weight: 700;
  color: var(--accent, var(--dash-text)); line-height: 1.1;
}
.dash-wf-lbl {
  font-size: 11px; color: var(--dash-text-dim); font-weight: 500;
}
.dash-wf-pill {
  font-size: 10px; padding: 2px 8px; border-radius: 10px; font-weight: 600;
}
.dash-wf-pill.st-opened    { background: rgba(22,163,74,.12);  color: var(--dash-green); }
.dash-wf-pill.st-signed    { background: rgba(37,99,235,.12);  color: var(--dash-blue); }
.dash-wf-pill.st-signing   { background: rgba(217,119,6,.12);  color: var(--dash-amber); }
.dash-wf-pill.st-searching { background: rgba(107,114,128,.12);color: var(--dash-text-dim); }

/* ── Waterfall mini-grid (wide mode, w >= 6) ──────────── */
/* Scroll wrap so the table can be wider than the widget without clipping —
   the user can horizontal-scroll to see all months at narrow widget sizes. */
.dash-wf-scroll {
  overflow-x: auto;
  max-width: 100%;
}
.dash-wf-grid {
  width: 100%;
  min-width: 480px; /* below this columns crush; scroll the wrap instead */
  border-collapse: collapse;
  font-size: 12px;
}
.dash-wf-grid thead th {
  text-align: left; padding: 6px 8px;
  font-size: 10px; font-weight: 600; text-transform: uppercase;
  letter-spacing: .5px; color: var(--dash-text-dim);
  border-bottom: 1px solid var(--dash-border);
  background: var(--dash-surface);
  position: sticky; top: 0; z-index: 1;
}
.dash-wf-grid tbody td {
  padding: 5px 8px; border-bottom: 1px solid #f0f1f3;
  vertical-align: middle;
}
.dash-wf-grid tbody tr:hover { background: var(--dash-surface2); }
.dash-wf-idx {
  font-family: 'SF Mono', monospace; font-size: 10px;
  color: var(--dash-text-dim); text-align: right;
  width: 28px;
}
.dash-wf-name { font-weight: 500; min-width: 0; }
.dash-wf-region {
  font-size: 11px; white-space: nowrap;
  border-radius: 4px;
}
.dash-wf-month-h {
  text-align: center !important;
  width: 32px; padding: 4px 2px !important;
}
.dash-wf-month-h.is-current {
  background: var(--dash-blue-bg);
  color: var(--dash-blue);
}
.dash-wf-month-cell {
  text-align: center; padding: 2px !important;
  width: 32px;
}
.dash-wf-month-cell.is-opening {
  background: rgba(37,99,235,.04);
}
.dash-wf-month-cell.is-current {
  background: rgba(37,99,235,.06);
}
.dash-wf-month-cell.is-opening.is-current {
  background: rgba(37,99,235,.12);
}

/* ── Planned Payments ───────────────────────────────── */
.dash-pp-head {
  display: flex; align-items: baseline; gap: 12px;
  margin-bottom: 10px;
}
.dash-pp-total {
  font-family: 'SF Mono', monospace; font-size: 26px; font-weight: 700;
  color: var(--dash-green);
}
.dash-pp-meta {
  font-size: 11px; color: var(--dash-text-dim);
}
.dash-pp-more {
  display: inline-block;
  font-size: 10px; padding: 1px 6px; border-radius: 8px;
  background: var(--dash-blue-bg); color: var(--dash-blue);
  margin-left: 4px;
}
.dash-pp-toolbar {
  display: flex; gap: 8px; margin-bottom: 10px;
  flex-wrap: wrap;
}
.dash-pp-sel {
  font-size: 12px;
  padding: 4px 8px;
  border-radius: 6px;
  border: 1px solid var(--dash-border);
  background: var(--dash-surface);
  color: var(--dash-text);
  cursor: pointer;
}
.dash-pp-row:hover { background: var(--dash-surface2); }

/* ── Google Calendar widget (Google-like card design) ─── */
/* ── Google Calendar widget (PR-M redesign) ─────────────
   Filled-color event cards that mirror the look of Google Calendar's
   week view: each event is a solid rectangle in its colorId palette,
   title bold on top, time+duration on a second line, optional green
   Meet chip top-right inside the card, no attendee icons. Single-
   column layout — multi-day views stack sections vertically. */
.dash-gcal-wrap {
  display: flex; flex-direction: column; gap: 14px;
  min-width: 0;
}
/* PR-DDD: when gcal widget hides the default widget-header (compact:true),
   strip the widget-body top padding too so the sticky day-head sits flush
   against the top of the widget box instead of leaving a 12px white gap
   above. Only affects widget bodies that DIRECTLY host a .dash-gcal-wrap
   so this rule won't bleed into other widgets that might share padding. */
.dash-widget-body:has(> .dash-gcal-wrap) {
  padding-top: 0;
}
/* PR-ZZ: calendar-picker toolbar at top of widget body. Click the
   pill → checkbox dropdown of all accessible calendars.
   PR-AAA: now also hosts a view-switcher button on the LEFT (Today /
   Tomorrow / Both). Layout: space-between so each anchors its own side. */
/* PR-CCC: legacy standalone toolbar element kept for backward compat
   if any old layout references it. New header embeds the same buttons
   inside `.dash-gcal-day-tools` (right side of the day-head row). */
.dash-gcal-toolbar {
  display: flex; align-items: center; justify-content: space-between;
  position: relative;
  min-height: 26px;
  gap: 8px;
}
/* PR-CCC: day-tools — wrapper for the view-switcher + calendar-picker
   buttons. Lives inside the first day-head row, pushed to the far right
   via `margin-left: auto`. `position: relative` so the dropdowns anchor
   to it (not the wider day-head, which would put the picker popover
   over the SAT-23 badge). */
.dash-gcal-day-tools {
  display: flex; align-items: center; gap: 6px;
  margin-left: auto;
  position: relative;
  flex-shrink: 0;
}
/* Empty-state variant — when user unchecks all calendars, day-head has
   no badge / meta / stats, just the tools row. Right-align so the
   buttons still appear in the same visual spot. */
.dash-gcal-day-head-empty {
  border-bottom: 0;
  /* Small padding parity with the normal day-head so tools don't sit
     flush against the widget body edge in the empty-state. */
  padding: 4px 2px;
  justify-content: flex-end;
}
/* View switcher button (left side of toolbar). Shares the same pill
   styling as the calendar picker on the right. */
.dash-gcal-view-btn {
  display: inline-flex; align-items: center; gap: 4px;
  padding: 3px 8px;
  border: 1px solid var(--dash-border);
  background: var(--dash-surface);
  border-radius: 12px;
  font-size: 11px; font-weight: 500;
  color: var(--dash-text-dim);
  cursor: pointer;
  transition: background .15s, color .15s;
}
.dash-gcal-view-btn:hover {
  background: var(--dash-surface2);
  color: var(--dash-text);
}
.dash-gcal-view-label { line-height: 1; }
.dash-gcal-view-popover {
  position: absolute;
  top: calc(100% + 4px);
  /* PR-CCC review HIGH: anchor right (vs left) so dropdown extends INTO
     the widget body rather than past its right edge on narrow widgets.
     Picker popover already uses right:0 — same anchoring keeps both
     dropdowns predictably within the widget. */
  right: 0;
  z-index: 50;
  min-width: 180px;
  background: var(--dash-surface);
  border: 1px solid var(--dash-border);
  border-radius: 8px;
  box-shadow: 0 6px 20px rgba(0,0,0,.12);
  padding: 4px 0;
}
.dash-gcal-view-item {
  display: block; width: 100%;
  padding: 8px 14px;
  text-align: left;
  background: transparent;
  border: 0;
  font-size: 12px;
  color: var(--dash-text);
  cursor: pointer;
}
.dash-gcal-view-item:hover { background: var(--dash-surface2); }
.dash-gcal-view-item.active {
  background: var(--dash-blue-bg);
  color: var(--dash-blue);
  font-weight: 600;
}
.dash-gcal-picker-btn {
  display: inline-flex; align-items: center; gap: 4px;
  padding: 3px 8px;
  border: 1px solid var(--dash-border);
  background: var(--dash-surface);
  border-radius: 12px;
  font-size: 11px; font-weight: 500;
  color: var(--dash-text-dim);
  cursor: pointer;
  transition: background .15s, color .15s;
}
.dash-gcal-picker-btn:hover {
  background: var(--dash-surface2);
  color: var(--dash-text);
}
.dash-gcal-picker-icon { font-size: 12px; line-height: 1; }
.dash-gcal-picker-chevron { font-size: 9px; opacity: .6; }
.dash-gcal-picker-popover {
  position: absolute;
  top: calc(100% + 4px);
  right: 0;
  z-index: 50;
  min-width: 240px;
  max-width: 320px;
  background: var(--dash-surface);
  border: 1px solid var(--dash-border);
  border-radius: 8px;
  box-shadow: 0 6px 20px rgba(0,0,0,.12);
  padding: 4px 0;
}
.dash-gcal-picker-head {
  display: flex; align-items: center; gap: 6px;
  padding: 6px 12px;
  font-size: 11px; font-weight: 600; color: var(--dash-text-dim);
  text-transform: uppercase; letter-spacing: .5px;
  border-bottom: 1px solid var(--dash-border);
}
.dash-gcal-picker-action {
  background: var(--dash-blue-bg);
  color: var(--dash-blue);
  border: 0; padding: 2px 8px; border-radius: 4px;
  font-size: 10px; font-weight: 600;
  cursor: pointer;
  text-transform: uppercase; letter-spacing: .3px;
}
.dash-gcal-picker-action:hover { background: rgba(37,99,235,.15); }
.dash-gcal-picker-head span:first-child { flex: 1; }
.dash-gcal-picker-list {
  max-height: 320px; overflow-y: auto;
  padding: 4px 0;
}
.dash-gcal-picker-item {
  display: flex; align-items: center; gap: 8px;
  padding: 6px 8px 6px 4px;
  cursor: pointer;
  font-size: 12px;
  border-radius: 4px;
  /* PR-GGG: smooth visual feedback when row gets reordered via drag-drop. */
  transition: background .12s, opacity .12s, transform .12s;
}
.dash-gcal-picker-item:hover { background: var(--dash-surface2); }
.dash-gcal-picker-item input[type="checkbox"] {
  margin: 0; flex-shrink: 0;
  cursor: pointer;
}
/* PR-GGG: drag handle (≡-ish ⋮⋮ glyph). Cursor changes to grab affordance.
   Stays muted by default; the parent row gets a brighter background on
   hover which gives the handle enough contrast. Touching the handle
   doesn't toggle the checkbox because <label> + cursor + native
   HTML5 drag-drop initiation is the primary interaction here. */
.dash-gcal-drag-handle {
  flex-shrink: 0;
  width: 14px;
  text-align: center;
  color: var(--dash-text-dim);
  font-size: 12px;
  letter-spacing: -2px;
  cursor: grab;
  user-select: none;
  opacity: .5;
}
.dash-gcal-picker-item:hover .dash-gcal-drag-handle { opacity: 1; }
.dash-gcal-picker-item.is-dragging {
  opacity: .35;
  background: var(--dash-blue-bg);
}
.dash-gcal-picker-item.is-dragging .dash-gcal-drag-handle { cursor: grabbing; }
/* Visual indicator for drop target — subtle accent so the user knows
   where the dragged row will land. */
.dash-gcal-picker-item.is-drop-target {
  background: var(--dash-blue-bg);
  box-shadow: inset 0 0 0 1px var(--dash-blue);
}
.dash-gcal-cal-swatch {
  display: inline-block; width: 12px; height: 12px;
  border-radius: 3px;
  flex-shrink: 0;
}
.dash-gcal-cal-name {
  flex: 1; min-width: 0;
  color: var(--dash-text);
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.dash-gcal-cal-tag {
  font-size: 9px; font-weight: 600;
  color: var(--dash-text-dim);
  background: var(--dash-surface2);
  border-radius: 8px; padding: 1px 6px;
  text-transform: uppercase; letter-spacing: .3px;
}
.dash-gcal-picker-empty {
  padding: 10px 12px;
  font-size: 11px; color: var(--dash-text-dim);
  font-style: italic;
}
.dash-gcal-picker-foot {
  padding: 6px 12px;
  font-size: 10px; color: var(--dash-text-dim);
  border-top: 1px solid var(--dash-border);
  font-style: italic;
}
.dash-gcal-partial-warn {
  padding: 4px 10px;
  font-size: 10px;
  background: rgba(217,119,6,.1);
  color: var(--dash-amber);
  border-radius: 4px;
  text-align: center;
  cursor: help;
}
.dash-gcal-section {
  display: flex; flex-direction: column; gap: 6px;
  min-width: 0;
}
/* Day header: SAT 23 badge on the left + label/count + stats + tools
   (view switcher + calendar picker, only on first section) on the right.
   PR-CCC made this the SINGLE compact header line.
   PR-DDD: now STICKY to the top of the widget body. The widget body
   has overflow:auto so sticky pins the row to the visible viewport
   while events scroll under it. Solid white background + small shadow
   prevents events from bleeding through. Each section has its own
   day-head — sticky behavior means today's header pins until user
   scrolls past today's events into tomorrow's section, where
   tomorrow's day-head takes over (natural sticky-table-header UX).
   The default "🗓 Google Calendar" widget header (registry compact:true)
   is hidden in non-edit mode, so day-head IS the visible top chrome. */
.dash-gcal-day-head {
  display: flex; align-items: center; gap: 8px;
  padding: 6px 4px;
  border-bottom: 1px solid var(--dash-border);
  /* No wrap — keep everything in one line. On very narrow widgets
     individual children clip via their own overflow rules rather than
     wrapping (which would defeat the "compact one line" purpose). */
  flex-wrap: nowrap;
  min-width: 0;
  /* Sticky pin to top of widget body. */
  position: sticky;
  top: 0;
  z-index: 30;
  background: var(--dash-surface);
  /* Subtle drop-shadow only when content is scrolled under — avoids the
     "always visible separator" look that fixed:top can produce. */
  box-shadow: 0 1px 0 var(--dash-border);
}
.dash-gcal-day-badge {
  display: flex; flex-direction: column; align-items: center; justify-content: center;
  /* PR-CCC: shrunk 40x40 → 32x32 to reclaim ~8px of vertical chrome and
     leave more horizontal room for the tools pills on narrow widgets. */
  width: 32px; height: 32px;
  border-radius: 8px;
  background: var(--dash-blue-bg);
  color: var(--dash-blue);
  line-height: 1;
  flex-shrink: 0;
}
.dash-gcal-day-wd {
  font-size: 8px; font-weight: 700; letter-spacing: .5px;
  text-transform: uppercase;
  margin-bottom: 2px;
}
.dash-gcal-day-num {
  font-family: 'SF Mono', monospace;
  font-size: 14px; font-weight: 700;
}
.dash-gcal-day-meta {
  display: flex; flex-direction: column; gap: 1px; min-width: 0;
  /* No margin-right:auto anymore — flex gap + tools margin-left:auto
     handles spacing. meta can shrink/clip if the row gets crowded. */
  flex-shrink: 1; overflow: hidden;
}
/* day-label and day-cnt — their own rules already exist later in the
   file (~line 1114); CSS last-rule-wins means those take effect. Keeping
   them slim (font-size 12px / 10px) matches the original look. */
/* Mini-dashboard stats — right side of day-head row. Compact pills with
   count + label (meet / blocks / all-day / total time).
   PR-CCC review MED: allow stats to shrink (and individual pills to hide
   via overflow) so badge + tools don't push stats off-screen on narrow
   widgets. With flex-shrink:1 + min-width:0, the row degrades gracefully:
   meta clips first, then stats, then tools (which are kept at the right
   via margin-left:auto). */
.dash-gcal-day-stats {
  display: flex; align-items: center; gap: 4px;
  flex-shrink: 1;
  min-width: 0;
  overflow: hidden;
}
.dash-gcal-stat {
  font-size: 10px; padding: 3px 7px;
  border-radius: 10px;
  background: var(--dash-surface2);
  color: var(--dash-text-dim);
  font-weight: 500;
  white-space: nowrap;
}
.dash-gcal-stat .dash-gcal-stat-n {
  font-family: 'SF Mono', monospace; font-weight: 700;
  color: var(--dash-text);
  margin-right: 3px;
}
.dash-gcal-stat-time {
  background: var(--dash-blue-bg);
  color: var(--dash-blue);
  font-family: 'SF Mono', monospace; font-weight: 700;
}
.dash-gcal-day-label {
  font-size: 12px; font-weight: 600; color: var(--dash-text);
}
.dash-gcal-day-cnt {
  font-size: 10px; color: var(--dash-text-dim);
}
.dash-gcal-empty {
  padding: 14px 4px;
  font-size: 12px; color: var(--dash-text-dim);
  font-style: italic;
}
/* ── Timeline (PR-Y rewrite) ──────────────────────────
   Google-Calendar-style time-proportional layout: 1h event = 48px tall,
   30min = 24px, 15min = 12px. Hour gridlines + labels on the left.
   Events render absolute-positioned inside .dash-gcal-grid based on
   their start time + duration. Overlapping events stagger right with
   z-index increasing so the latest-laned card sits on top. */
.dash-gcal-timeline {
  position: relative;
  display: flex;
  width: 100%;
  border-top: 1px solid var(--dash-border);
}
.dash-gcal-gutter {
  position: relative;
  width: 44px;
  flex-shrink: 0;
  border-right: 1px solid var(--dash-border);
  background: var(--dash-surface);
}
.dash-gcal-hour-label {
  position: absolute;
  right: 6px;
  font-family: 'SF Mono', monospace;
  font-size: 10px;
  color: var(--dash-text-dim);
  /* Pull up by half line-height so the label sits ON the hour line */
  transform: translateY(-50%);
  white-space: nowrap;
}
.dash-gcal-grid {
  position: relative;
  flex: 1;
  min-width: 0;
  /* Clip any positioned event card that would extend outside the grid
     bounds — defends against malformed timestamps that compute weird
     top/left/width values from showing up as floating chips beyond the
     timeline area. */
  overflow: hidden;
}
.dash-gcal-hour-line {
  position: absolute;
  left: 0; right: 0;
  height: 1px;
  background: rgba(0,0,0,.05);
  pointer-events: none;
}
/* Current-time indicator — thin red horizontal line + dot on the left edge.
   Renders only on today's section. */
.dash-gcal-now-line {
  position: absolute;
  left: 0; right: 0;
  height: 2px;
  background: #ea4335;
  z-index: 100;
  pointer-events: none;
  box-shadow: 0 0 6px rgba(234,67,53,0.4);
}
.dash-gcal-now-line::before {
  content: '';
  position: absolute;
  left: -5px; top: -4px;
  width: 10px; height: 10px;
  border-radius: 50%;
  background: #ea4335;
}

/* All-day events render in a strip above the timeline (no time-of-day to
   position against). */
.dash-gcal-allday-strip {
  display: flex; flex-direction: column; gap: 3px;
  padding-bottom: 4px;
}
.dash-gcal-allday-card {
  display: flex; align-items: center; gap: 6px;
  padding: 4px 10px;
  border-radius: 6px;
  text-decoration: none;
  cursor: pointer; /* now a <div>, needs explicit cursor (PR-MM) */
  font-size: 12px;
  min-width: 0;
  box-shadow: inset 0 0 0 1px rgba(0,0,0,.04);
}
.dash-gcal-allday-card:hover { filter: brightness(1.05); }
.dash-gcal-allday-label {
  font-family: 'SF Mono', monospace;
  font-size: 9px;
  opacity: 0.8;
  font-weight: 600;
  letter-spacing: 0.5px;
  text-transform: uppercase;
  flex-shrink: 0;
}
.dash-gcal-allday-title {
  font-weight: 600;
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
  min-width: 0; flex: 1;
}

/* Filled card — bg/fg colors come from inline `style="background:...;color:..."`
   set by the renderer based on the event's Google colorId. Position is
   absolute (inside .dash-gcal-grid) with top/height/left/width inline.
   Right padding reserves space for the Meet chip.
   - border-radius bumped from 4 → 7 (softer Google-like corners)
   - inset shadow strengthened on lanes >= 1 so overlapping same-color
     events still visually separate (rendered inline by JS via z-index +
     lane meta — see .dash-gcal-card[data-lane="1"] etc below) */
.dash-gcal-card {
  position: absolute;
  display: flex; flex-direction: column;
  padding: 3px 28px 3px 8px;
  /* Tight gap between adjacent cards — the inline top/left/width values
     already pixel-pack, so a 1px inset border (via box-shadow) creates
     the visual separation Google has. */
  border-radius: 7px;
  text-decoration: none;
  cursor: pointer; /* card is now a <div>, needs explicit cursor (PR-MM) */
  transition: filter .12s, transform .1s, opacity .12s;
  overflow: hidden;
  box-shadow: inset 0 0 0 1px rgba(0,0,0,.04);
}
/* Compact card (event height 22-38px) — tight padding so title + time
   row both fit. Math: card 22px - padding 2px (1+1) - title 11px - time
   9px = 0px slack. Card 30px = comfortable. PR-NN: was padding 2px y +
   line-height 1.2/1.1 which overflowed 22px cards by ~5px → time row
   clipped. Now line-height 1 + padding 1px = exact fit. */
.dash-gcal-card-compact { padding: 1px 24px 1px 6px; gap: 0; }
/* Tiny card (height < 22px, e.g. 15-min slots) — single line, no time row,
   minimal padding. The title row fills the whole 12-18px height. */
.dash-gcal-card-tiny { padding: 1px 18px 1px 5px; gap: 0; }
.dash-gcal-card:hover  { filter: brightness(1.05); }
.dash-gcal-card:active { transform: translateY(1px); }
/* Overlap differentiation — second-and-later lanes get a stronger inset
   shadow (left edge) so two same-color cards stacking are visually
   separable. lane=0 has the default light shadow. User feedback: "если
   идет наслаивание одинакого цвета прошу тебя второю встречу затемнять". */
.dash-gcal-card[data-lane="1"] {
  box-shadow: inset 2px 0 0 rgba(0,0,0,.22), inset 0 0 0 1px rgba(0,0,0,.06);
  filter: brightness(0.92);
}
.dash-gcal-card[data-lane="2"] {
  box-shadow: inset 2px 0 0 rgba(0,0,0,.28), inset 0 0 0 1px rgba(0,0,0,.08);
  filter: brightness(0.85);
}
.dash-gcal-card[data-lane="3"] {
  box-shadow: inset 2px 0 0 rgba(0,0,0,.34), inset 0 0 0 1px rgba(0,0,0,.1);
  filter: brightness(0.78);
}
/* Past events fade to grayscale-ish so the eye skims to upcoming items
   — mirrors Google Calendar's week-view convention. */
.dash-gcal-card.is-past {
  filter: grayscale(0.65) brightness(0.92);
  opacity: 0.78;
}
.dash-gcal-card.is-past:hover {
  filter: grayscale(0.4) brightness(0.95);
  opacity: 0.95;
}
/* Title row — title fills left. Meet chip is NO LONGER inline here —
   it's absolute-positioned on the right edge of the card so it always
   looks like a "join" button anchored to the card. */
.dash-gcal-card-head {
  display: flex; align-items: center; gap: 6px;
  min-width: 0;
}
/* PR-NN: per-density font sizes tuned to physically FIT inside event-height.
   30-min event = 22px tall. Padding 1px y = 20px content. Title 11px + time
   9px at line-height 1 = 20px → fits exactly. Earlier 1.2/1.1 line-heights
   overflowed → time row got clipped by overflow:hidden. */
.dash-gcal-card-title {
  flex: 1; min-width: 0;
  font-weight: 600;
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.dash-gcal-card-tiny    .dash-gcal-card-title { font-size: 10px; line-height: 1; }
.dash-gcal-card-compact .dash-gcal-card-title { font-size: 11px; line-height: 1; }
.dash-gcal-card-full    .dash-gcal-card-title { font-size: 12px; line-height: 1.15; }
.dash-gcal-card-time {
  font-family: 'SF Mono', monospace;
  opacity: .85;
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.dash-gcal-card-compact .dash-gcal-card-time { font-size: 9px; line-height: 1; }
.dash-gcal-card-full    .dash-gcal-card-time { font-size: 10px; line-height: 1.2; }

/* PR-AAA: narrow-card wrap mode. When ≥3 events overlap (or 2 events
   on a small widget), each card is <50% wide → title gets cut to "M…" .
   For cards tall enough (full density, height ≥ ~40px) allow the title
   AND time to break onto a second line so the user can actually read
   what's there. Tiny/compact cards stay single-line — they don't have
   vertical room for wrap regardless. */
.dash-gcal-card-full[data-narrow="1"] .dash-gcal-card-title {
  white-space: normal;
  word-break: break-word;
  line-height: 1.1;
  /* Cap to 3 lines so a long title doesn't push beyond the card height
     and clip via overflow:hidden on the outer card. */
  display: -webkit-box;
  -webkit-line-clamp: 3;
  -webkit-box-orient: vertical;
}
.dash-gcal-card-full[data-narrow="1"] .dash-gcal-card-time {
  white-space: normal;
  word-break: break-word;
  line-height: 1.15;
}
/* Narrow cards have the Meet chip to the right of the title. With wrap
   enabled the title can grow over multiple lines, so shrink the right
   padding so the chip doesn't crowd the title text. */
.dash-gcal-card-full[data-narrow="1"] {
  padding-right: 22px;
}
.dash-gcal-loc {
  display: flex; align-items: center; gap: 4px;
  font-size: 10px; opacity: .85;
  margin-top: 2px;
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.dash-gcal-loc .dash-gcal-icon { font-size: 10px; }
/* Green Meet chip — always green regardless of card bg color per user spec.
   Pinned to the right edge of the card, vertically centered (was inline
   on the title row in PR-N; user fed back that should sit on the card
   itself, on the right side). */
/* Meet chip — anchored top-right of the card, always green, scales down
   on compact/tiny cards so a 12px-tall 15-min event still has a visible
   chip without overflowing. */
.dash-gcal-meet-chip {
  position: absolute;
  top: 3px;
  right: 3px;
  width: 18px; height: 18px;
  display: flex; align-items: center; justify-content: center;
  border-radius: 50%;
  background: #34a853;
  color: #fff;
  font-size: 9px;
  text-decoration: none;
  box-shadow: 0 1px 2px rgba(0,0,0,.18);
  transition: transform .1s, background .12s;
  z-index: 2;
}
.dash-gcal-meet-chip.is-compact { width: 14px; height: 14px; font-size: 8px; top: 2px; right: 2px; }
.dash-gcal-meet-chip.is-tiny    { width: 12px; height: 12px; font-size: 7px; top: 1px; right: 1px; }
.dash-gcal-meet-chip:hover  { background: #2c8f46; transform: scale(1.08); }
.dash-gcal-meet-chip:active { transform: scale(0.95); }

/* ── Task-edit popup (iframe of tasks.html) ──────────── */
.dash-task-modal {
  position: fixed; inset: 0;
  background: rgba(15,23,42,.55);
  z-index: 200;
  display: none; align-items: center; justify-content: center;
}
.dash-task-modal.open { display: flex; }
.dash-task-modal-box {
  background: var(--dash-surface);
  width: 90vw; height: 90vh;
  max-width: 1280px;
  border-radius: 12px;
  position: relative;
  overflow: hidden;
  box-shadow: 0 20px 60px rgba(0,0,0,.3);
}
.dash-task-modal-close {
  position: absolute; top: 12px; right: 12px;
  z-index: 2;
  background: var(--dash-surface); color: var(--dash-text);
  border: 1px solid var(--dash-border);
  width: 32px; height: 32px;
  border-radius: 50%;
  font-size: 14px; cursor: pointer;
  box-shadow: 0 2px 8px rgba(0,0,0,.08);
}
.dash-task-modal-close:hover { background: var(--dash-surface2); }
#dash-task-iframe {
  width: 100%; height: 100%;
  border: 0; background: transparent;
  display: block;
}

/* ── Scout expanded overlay ──────────────────────────── */
.dash-overlay {
  position: fixed; inset: 0;
  background: rgba(15,23,42,.55);
  z-index: 200;
  display: none; align-items: center; justify-content: center;
}
.dash-overlay.open { display: flex; }
.dash-overlay-box {
  background: var(--dash-surface);
  border-radius: 12px;
  padding: 22px 26px;
  width: min(880px, 92vw);
  max-height: 86vh;
  overflow: auto;
  position: relative;
  box-shadow: 0 20px 60px rgba(0,0,0,.3);
}
.dash-overlay-close {
  position: absolute; top: 10px; right: 12px;
  background: transparent; border: 0; cursor: pointer;
  font-size: 16px; color: var(--dash-text-dim);
  padding: 4px 8px; border-radius: 6px;
}
.dash-overlay-close:hover { background: var(--dash-surface2); color: var(--dash-text); }
.dash-overlay-head {
  display: flex; align-items: center; justify-content: space-between;
  margin-bottom: 16px;
}
.dash-overlay-title { font-size: 18px; font-weight: 700; }
.dash-overlay-sub {
  font-size: 12px; color: var(--dash-text-dim);
  margin-top: 4px; text-transform: capitalize;
}
.dash-overlay-stats {
  font-size: 11px; color: var(--dash-text-dim);
  margin-top: 6px; letter-spacing: .3px;
}
.dash-overlay-big {
  font-family: 'SF Mono', monospace; font-size: 34px; font-weight: 700;
  color: var(--dash-blue);
}
.dash-overlay-spark {
  background: var(--dash-surface2);
  border-radius: 8px; padding: 14px 16px;
  margin-bottom: 8px;
  overflow-x: auto; /* if native-width SVG is wider than the overlay, allow horizontal scroll */
}
.dash-overlay-axis {
  display: flex; gap: 4px; padding: 0 16px 14px;
  font-size: 10px; color: var(--dash-text-dim);
  border-bottom: 1px solid var(--dash-border);
  margin-bottom: 14px;
}
.dash-overlay-stat {
  display: grid; grid-template-columns: repeat(3, 1fr); gap: 10px;
}
.dash-overlay-stat > div {
  background: var(--dash-surface2);
  border-radius: 8px; padding: 10px 12px;
}
.dash-overlay-stat .lbl {
  font-size: 10px; color: var(--dash-text-dim);
  text-transform: uppercase; letter-spacing: .5px;
}
.dash-overlay-stat .val {
  font-family: 'SF Mono', monospace; font-size: 22px; font-weight: 700;
  color: var(--dash-text);
}

/* ── Reminders widget ─────────────────────────────────── */
.dash-rem { display: flex; flex-direction: column; gap: 8px; height: 100%; min-width: 0; }

/* PR-NNN: quick-filter chip row — sits between the head counter and
   the quick-capture input. Counts inside each chip read at a glance. */
.dash-rem-filters {
  display: flex; gap: 4px; flex-wrap: wrap;
  margin-top: 2px;
}
.dash-rem-filter-chip {
  display: inline-flex; align-items: center; gap: 5px;
  font: 600 11px var(--font, 'Inter');
  border: 1px solid var(--dash-border);
  background: var(--dash-surface);
  color: var(--dash-text-dim);
  padding: 4px 10px;
  border-radius: 12px;
  cursor: pointer;
  transition: background .12s, color .12s, border-color .12s;
}
.dash-rem-filter-chip:hover {
  border-color: var(--dash-blue);
  color: var(--dash-blue);
}
.dash-rem-filter-chip.active {
  background: var(--dash-blue);
  border-color: var(--dash-blue);
  color: #fff;
}
.dash-rem-filter-cnt {
  font: 700 10px 'SF Mono', monospace;
  background: rgba(0,0,0,.1);
  color: inherit;
  padding: 1px 6px;
  border-radius: 8px;
  min-width: 16px;
  text-align: center;
}
.dash-rem-filter-chip.active .dash-rem-filter-cnt {
  background: rgba(255,255,255,.25);
}

/* PR-RRR: second filter row — priority chips. Same chip shape as the
   bucket chips above but tinted by the urgency palette so the picker
   visually previews what the user will see in the list. */
.dash-rem-pri-filters { gap: 3px; }
.dash-rem-pri-filter-chip {
  display: inline-flex; align-items: center; gap: 4px;
  font: 600 10px var(--font, 'Inter');
  border: 1px solid var(--dash-border);
  background: var(--dash-surface);
  color: var(--dash-text-dim);
  padding: 3px 8px;
  border-radius: 10px;
  cursor: pointer;
  transition: background .12s, color .12s, border-color .12s;
}
.dash-rem-pri-filter-chip:hover { border-color: var(--dash-text-dim); color: var(--dash-text); }
.dash-rem-pri-filter-chip.active.pri-1 { background: rgba(239,68,68,.18);  border-color: rgba(239,68,68,.5);  color: #991b1b; }
.dash-rem-pri-filter-chip.active.pri-2 { background: rgba(234,179,8,.18);  border-color: rgba(234,179,8,.5);  color: #854d0e; }
.dash-rem-pri-filter-chip.active.pri-3 { background: rgba(148,163,184,.2); border-color: rgba(148,163,184,.5); color: #475569; }
.dash-rem-pri-filter-chip.active.pri-none { background: var(--dash-surface2); border-color: var(--dash-text-dim); color: var(--dash-text); }
.dash-rem-pri-filter-chip.active:not([class*=" pri-"]) {
  background: var(--dash-blue); color: #fff; border-color: var(--dash-blue);
}

/* PR-RRR: shared priority filter chips — used by Person Projects and
   My Tasks. Same shape as Reminders pri-filter for visual consistency. */
.dash-pp-pri-filters {
  display: flex; gap: 4px; flex-wrap: wrap;
  margin-bottom: 6px;
}
.dash-pp-pri-filter-chip {
  display: inline-flex; align-items: center; gap: 4px;
  font: 600 10px var(--font, 'Inter');
  border: 1px solid var(--dash-border);
  background: var(--dash-surface);
  color: var(--dash-text-dim);
  padding: 3px 8px;
  border-radius: 10px;
  cursor: pointer;
  transition: background .12s, color .12s, border-color .12s;
}
.dash-pp-pri-filter-chip:hover { border-color: var(--dash-text-dim); color: var(--dash-text); }
.dash-pp-pri-filter-chip.active.pri-1    { background: rgba(239,68,68,.18);  border-color: rgba(239,68,68,.5);  color: #991b1b; }
.dash-pp-pri-filter-chip.active.pri-2    { background: rgba(234,179,8,.18);  border-color: rgba(234,179,8,.5);  color: #854d0e; }
.dash-pp-pri-filter-chip.active.pri-3    { background: rgba(148,163,184,.2); border-color: rgba(148,163,184,.5); color: #475569; }
.dash-pp-pri-filter-chip.active.pri-none { background: var(--dash-surface2); border-color: var(--dash-text-dim); color: var(--dash-text); }
.dash-pp-pri-filter-chip.active:not([class*=" pri-"]) {
  background: var(--dash-blue); color: #fff; border-color: var(--dash-blue);
}
.dash-pp-pri-filter-cnt {
  font: 700 9px 'SF Mono', monospace;
  background: rgba(0,0,0,.1);
  color: inherit;
  padding: 1px 5px;
  border-radius: 8px;
  min-width: 14px;
  text-align: center;
}
.dash-pp-pri-filter-chip.active .dash-pp-pri-filter-cnt {
  background: rgba(255,255,255,.25);
}

/* PR-NNN: per-row snooze buttons (+1d / +1w). Compact, only visible
   on hover so the row stays uncluttered. Owner-only on active items. */
.dash-rem-snooze {
  background: transparent; border: 0; cursor: pointer;
  font: 600 10px 'SF Mono', monospace;
  color: var(--dash-text-dim);
  padding: 2px 6px;
  border-radius: 4px;
  opacity: 0;
  transition: opacity .15s, background .12s, color .12s;
  flex-shrink: 0;
}
.dash-rem-row:hover .dash-rem-snooze { opacity: 0.75; }
.dash-rem-snooze:hover {
  opacity: 1;
  background: var(--dash-blue-bg);
  color: var(--dash-blue);
}

.dash-rem-head {
  display: flex; align-items: baseline; gap: 6px;
  font-size: 12px; color: var(--dash-text-dim);
  text-transform: uppercase; letter-spacing: .5px; font-weight: 600;
}
.dash-rem-cnt {
  font-family: 'SF Mono', monospace; font-size: 18px; font-weight: 700;
  color: var(--dash-blue); text-transform: none;
}
.dash-rem-input-wrap {
  display: flex; gap: 6px; align-items: center;
  background: var(--dash-surface2);
  border: 1px solid var(--dash-border); border-radius: 8px;
  padding: 2px 4px 2px 12px;
}
.dash-rem-input {
  flex: 1; min-width: 0;
  border: 0; background: transparent; outline: none;
  font: 14px var(--font, 'Inter');
  padding: 8px 0;
  color: var(--dash-text);
}
.dash-rem-input::placeholder { color: var(--dash-text-dim); }
.dash-rem-input:focus { outline: none; }
.dash-rem-more {
  background: transparent; border: 0; cursor: pointer;
  padding: 6px 10px; border-radius: 6px;
  color: var(--dash-text-dim); font-size: 14px;
}
.dash-rem-more:hover { background: rgba(0,0,0,.04); color: var(--dash-text); }

.dash-rem-more-row {
  display: flex; gap: 6px; flex-wrap: wrap;
  padding: 2px 0;
}
.dash-rem-more-row[hidden] { display: none; }
.dash-rem-more-row input[type="date"],
.dash-rem-more-row select {
  font: 12px var(--font, 'Inter');
  padding: 5px 8px; border-radius: 6px;
  border: 1px solid var(--dash-border);
  background: var(--dash-surface);
  color: var(--dash-text);
  cursor: pointer;
}

.dash-rem-list { display: flex; flex-direction: column; gap: 3px; min-height: 0; }
.dash-rem-row {
  display: flex; align-items: center; gap: 8px;
  padding: 6px 8px; border-radius: 6px;
  background: var(--dash-surface2);
  font-size: 13px; min-width: 0;
  transition: background .15s, opacity .2s;
}
.dash-rem-row:hover { background: #eef2f7; }
.dash-rem-row.done { opacity: .55; }
.dash-rem-row.done .dash-rem-text { text-decoration: line-through; color: var(--dash-text-dim); }

.dash-rem-check {
  background: transparent; border: 0; cursor: pointer;
  font-size: 16px; padding: 0 2px;
  color: var(--dash-text-dim);
  flex-shrink: 0; line-height: 1;
}
.dash-rem-check:hover { color: var(--dash-blue); }
.dash-rem-row.done .dash-rem-check { color: var(--dash-green); }

.dash-rem-text {
  flex: 1; min-width: 0;
  /* PR-MMM: allow long reminders to wrap onto multiple lines — was
     `white-space: nowrap` + ellipsis, hid most of the text. */
  white-space: normal;
  word-wrap: break-word;
  overflow-wrap: anywhere;
  line-height: 1.35;
  cursor: text;
}
.dash-rem-edit-input {
  width: 100%; box-sizing: border-box;
  font: 13px var(--font, 'Inter');
  border: 0; outline: 2px solid var(--dash-blue);
  outline-offset: -2px;
  background: var(--dash-surface);
  padding: 4px 6px; border-radius: 4px;
}

.dash-rem-tags { display: flex; gap: 4px; flex-shrink: 0; flex-wrap: wrap; }
.dash-rem-due-tag,
.dash-rem-rec-tag,
.dash-rem-assignee-tag {
  font-size: 10px; padding: 2px 7px; border-radius: 10px;
  background: var(--dash-surface); color: var(--dash-text-dim);
  font-weight: 500; white-space: nowrap;
}
.dash-rem-due-tag.soon { background: rgba(37,99,235,.1); color: var(--dash-blue); }
.dash-rem-due-tag.overdue { background: rgba(220,38,38,.12); color: var(--dash-red); font-weight: 600; }
.dash-rem-rec-tag { background: rgba(124,58,237,.1); color: var(--dash-purple); }
.dash-rem-assignee-tag { background: rgba(217,119,6,.1); color: var(--dash-amber); }

.dash-rem-del,
.dash-rem-settings {
  background: transparent; border: 0; cursor: pointer;
  color: var(--dash-text-dim); font-size: 12px;
  padding: 4px 8px; border-radius: 4px;
  opacity: 0; transition: opacity .15s;
  flex-shrink: 0;
}
.dash-rem-row:hover .dash-rem-del,
.dash-rem-row:hover .dash-rem-settings { opacity: 1; }
.dash-rem-del:hover { background: rgba(220,38,38,.1); color: var(--dash-red); }
.dash-rem-settings:hover { background: rgba(0,0,0,.05); color: var(--dash-text); }

/* Inline settings panel — slides out under a reminder row when ⚙ is clicked.
   Wide rows stay one line; narrow widgets wrap each control onto its own
   line via flex-wrap. */
.dash-rem-settings-panel {
  display: flex; flex-direction: column; gap: 8px;
  margin: 2px 0 8px 28px;  /* indent to align with text column */
  padding: 10px 12px;
  background: var(--dash-surface);
  border: 1px solid var(--dash-border);
  border-radius: 8px;
}
.dash-rem-settings-row {
  display: flex; align-items: center; gap: 8px;
  flex-wrap: wrap;
}
.dash-rem-settings-lbl {
  font-size: 11px; font-weight: 600; color: var(--dash-text-dim);
  text-transform: uppercase; letter-spacing: .5px;
  min-width: 60px;
}
.dash-rem-settings-row input[type="date"],
.dash-rem-settings-row select {
  font: 12px var(--font, 'Inter');
  padding: 5px 8px; border-radius: 6px;
  border: 1px solid var(--dash-border);
  background: var(--dash-surface2);
  color: var(--dash-text);
}
.dash-rem-set-due-clear {
  background: transparent; border: 0; cursor: pointer;
  color: var(--dash-text-dim); font-size: 12px;
  padding: 4px 8px; border-radius: 4px;
}
.dash-rem-set-due-clear:hover { background: rgba(0,0,0,.05); }
.dash-rem-pri-chip.pri-none.active {
  background: var(--dash-surface2); border-color: var(--dash-border);
  color: var(--dash-text-dim);
}
.dash-rem-settings-actions {
  display: flex; gap: 6px; justify-content: flex-end;
  border-top: 1px solid var(--dash-border);
  padding-top: 8px;
}
.dash-rem-settings-cancel,
.dash-rem-settings-save {
  font: 12px var(--font, 'Inter'); font-weight: 600;
  padding: 6px 14px; border-radius: 6px;
  cursor: pointer;
  border: 1px solid var(--dash-border);
  background: var(--dash-surface2); color: var(--dash-text);
}
.dash-rem-settings-cancel:hover { background: rgba(0,0,0,.05); }
.dash-rem-settings-save {
  background: var(--dash-blue); border-color: var(--dash-blue); color: #fff;
}
.dash-rem-settings-save:hover { background: #1d4fd4; }

.dash-rem-done-head {
  display: flex; align-items: center; gap: 6px;
  margin-top: 8px; padding: 4px 8px;
  font-size: 11px; color: var(--dash-text-dim);
  text-transform: uppercase; letter-spacing: .5px; font-weight: 600;
  cursor: pointer; user-select: none;
}
.dash-rem-done-head:hover { color: var(--dash-text); }
.dash-rem-done-chev { font-size: 10px; transition: transform .2s; }
.dash-rem-done-body {
  display: flex; flex-direction: column; gap: 3px;
  max-height: 600px; overflow: hidden;
  transition: max-height .2s ease;
}
.dash-rem-done-body.collapsed { max-height: 0; }

/* Priority chip group inside the More-row. Click cycles selection: a chip
   becomes `.active` on first click, deselects on second. Color matches the
   row tint of the same priority for visual continuity. */
.dash-rem-pri-group { display: inline-flex; gap: 4px; }
.dash-rem-pri-chip {
  font: 11px var(--font, 'Inter'); font-weight: 600;
  padding: 5px 9px; border-radius: 6px;
  border: 1px solid var(--dash-border);
  background: var(--dash-surface); color: var(--dash-text-dim);
  cursor: pointer; transition: background .15s, color .15s;
}
.dash-rem-pri-chip:hover { color: var(--dash-text); }
.dash-rem-pri-chip.pri-1.active { background: rgba(34,197,94,.18); border-color: rgba(34,197,94,.4); color: #166534; }
.dash-rem-pri-chip.pri-2.active { background: rgba(234,179,8,.18); border-color: rgba(234,179,8,.4); color: #854d0e; }
.dash-rem-pri-chip.pri-3.active { background: rgba(148,163,184,.18); border-color: rgba(148,163,184,.4); color: #475569; }

/* PR-MMM: priority indicator — clearer "is this urgent?" signal.
   Left stripe (4px) + tinted bg using a more intuitive palette:
     P1 = red    (urgent — drop everything)
     P2 = orange (important — get to it today)
     P3 = gray   (someday / low)
   Tint is moderate (~14%) so the row stays readable. Hover deepens. */
.dash-rem-row.pri-1 { background: rgba(239,68,68,.14);  border-left: 4px solid #ef4444; }
.dash-rem-row.pri-1:hover { background: rgba(239,68,68,.22); }
.dash-rem-row.pri-2 { background: rgba(234,179,8,.14);  border-left: 4px solid #eab308; }
.dash-rem-row.pri-2:hover { background: rgba(234,179,8,.22); }
.dash-rem-row.pri-3 { background: rgba(148,163,184,.10); border-left: 4px solid #94a3b8; }
.dash-rem-row.pri-3:hover { background: rgba(148,163,184,.18); }
/* Counterpart for the P1/P2 chip "active" state — mirror the urgency
   palette so the picker matches what lands in the list. */
.dash-rem-pri-chip.pri-1.active { background: rgba(239,68,68,.18);  border-color: rgba(239,68,68,.4);  color: #991b1b; }
.dash-rem-pri-chip.pri-2.active { background: rgba(234,179,8,.18);  border-color: rgba(234,179,8,.4);  color: #854d0e; }

/* Drag handle — visible on hover only so the row stays uncluttered when
   the user is just reading. `grab` cursor signals draggability. */
.dash-rem-handle {
  flex-shrink: 0; width: 14px;
  font-size: 12px; color: var(--dash-text-dim);
  cursor: grab; opacity: 0; transition: opacity .15s;
  line-height: 1; letter-spacing: -2px;
  user-select: none;
}
.dash-rem-row:hover .dash-rem-handle { opacity: 0.7; }
.dash-rem-handle:hover { opacity: 1; cursor: grab; }
.dash-rem-handle-empty { cursor: default; }
.dash-rem-row.dragging {
  opacity: 0.4; cursor: grabbing;
}
/* Drop indicator — a small accent line above / below the target row. */
.dash-rem-row.drop-before { box-shadow: inset 0 2px 0 0 var(--dash-blue); }
.dash-rem-row.drop-after  { box-shadow: inset 0 -2px 0 0 var(--dash-blue); }

/* Toast color for the "warning" kind used by the reminders summary banner.
   Existing toast styles cover info/error; warning is new. */
.dash-toast[data-kind="warning"] {
  background: rgba(234,179,8,.18); color: #854d0e; font-weight: 600;
}

/* ── Motivation widget ────────────────────────────────────
   Horizontal banner with a rotating motivational quote. Designed for a
   1-row-tall widget (defaultSize.h=1) — keeps the dashboard light. */
.dash-motiv {
  display: flex; align-items: center; gap: 12px;
  height: 100%;
  /* PR-PP: ripped the card chrome (border + gradient bg + border-radius
     + extra inner padding). User feedback: "не было белого контура, он
     съедает место, просто фраза и фон который сразу за ней хватит".
     Widget now sits flush on the dashboard surface — quote reads as a
     free-floating phrase, not a card. min-height tightened from 36 to
     28 since the rim is gone. */
  min-height: 28px;
  min-width: 0;
  padding: 0 4px;
  background: transparent;
  border: 0;
}
.dash-motiv-quote {
  flex: 1; min-width: 0;
  display: flex; align-items: center; gap: 10px;
  /* nowrap keeps the banner one-line; if the phrase is too long the
     text-overflow ellipsis kicks in (single-line banner is more readable
     than a 2-line wrap). */
  flex-wrap: nowrap;
  transition: opacity 0.3s ease;
}
.dash-motiv-quote.fading { opacity: 0; }
.dash-motiv-text {
  /* Bigger font + medium weight (not italic) — italic at 14px was hard to
     read per user feedback "сделай крупнее шрифтом". */
  font-size: 15px; font-weight: 500;
  color: var(--dash-text);
  line-height: 1.3;
  min-width: 0;
  /* Truncate long quotes with ellipsis instead of wrapping to a second
     line — keeps the banner consistently thin. */
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.dash-motiv-author {
  font-size: 12px; font-weight: 600;
  color: var(--dash-text-dim);
  white-space: nowrap;
  flex-shrink: 0;
}
.dash-motiv-next {
  background: transparent; border: 0; cursor: pointer;
  padding: 4px 8px; border-radius: 4px;
  color: var(--dash-text-dim); font-size: 12px;
  flex-shrink: 0;
  transition: background .15s, color .15s;
}
.dash-motiv-next:hover {
  background: rgba(0,0,0,.06); color: var(--dash-text);
}

/* ── Waterfall Pro widget ────────────────────────────────
   Dense full-data table mirroring bizdev/waterfall.html columns. Sticky
   header + scrollable body so all rows are reachable inside a widget's
   limited height. */
.dash-wfpro-summary {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(min(110px, 100%), 1fr));
  gap: 6px;
  margin-bottom: 10px;
}
.dash-wfpro-tile {
  display: flex; flex-direction: column; align-items: center;
  padding: 6px 8px; border-radius: 8px;
  background: var(--dash-surface2);
  border: 1px solid var(--dash-border);
}
.dash-wfpro-tile .cnt {
  font-family: 'SF Mono', monospace;
  font-size: 18px; font-weight: 700;
  color: var(--dash-text);
}
.dash-wfpro-tile .lbl {
  font-size: 9px; font-weight: 600;
  color: var(--dash-text-dim);
  text-transform: uppercase; letter-spacing: .5px;
}
/* Per-status accent on the left edge of each tile — matches the
   .dash-wf-pill colors used elsewhere in the dashboard. */
.dash-wfpro-tile.st-opened    { border-left: 3px solid #16a34a; }
.dash-wfpro-tile.st-signed    { border-left: 3px solid var(--dash-blue); }
.dash-wfpro-tile.st-signing   { border-left: 3px solid var(--dash-amber); }
.dash-wfpro-tile.st-searching { border-left: 3px solid var(--dash-text-dim); }
.dash-wfpro-tile.total        { border-left: 3px solid var(--dash-purple); }
.dash-wfpro-tile.total.losses { border-left: 3px solid var(--dash-red); }
/* Losses tile cnt color follows sign of the value — set via inline class
   on the .cnt span. Falls back to neutral if zero/missing. */
.dash-wfpro-tile.losses .cnt.dash-wfpro-loss-bad  { color: var(--dash-red); }
.dash-wfpro-tile.losses .cnt.dash-wfpro-loss-good { color: var(--dash-green); }
.dash-wfpro-tile.losses .cnt.dash-wfpro-loss-zero { color: var(--dash-text-dim); }

.dash-wfpro-scroll {
  /* Constrain vertical height so the sticky header makes sense; if the
     widget is short the user just scrolls inside the wrap. */
  max-height: calc(100% - 80px);
  overflow: auto;
  border: 1px solid var(--dash-border);
  border-radius: 6px;
}
.dash-wfpro-table {
  width: 100%;
  border-collapse: collapse;
  font-size: 12px;
  min-width: 680px; /* below this columns crush; horizontal-scroll instead */
}
.dash-wfpro-table thead th {
  position: sticky; top: 0; z-index: 2;
  background: var(--dash-surface);
  text-align: left;
  padding: 7px 8px;
  font-size: 10px; font-weight: 600;
  color: var(--dash-text-dim);
  text-transform: uppercase; letter-spacing: .5px;
  border-bottom: 1px solid var(--dash-border);
  white-space: nowrap;
}
.dash-wfpro-table tbody td {
  padding: 5px 8px;
  border-bottom: 1px solid #f0f1f3;
  vertical-align: middle;
  white-space: nowrap;
}
.dash-wfpro-row {
  cursor: pointer;
  transition: background .12s;
}
.dash-wfpro-row:hover { background: var(--dash-surface2); }
.dash-wfpro-idx {
  font-family: 'SF Mono', monospace; font-size: 10px;
  color: var(--dash-text-dim); text-align: right;
  width: 28px;
}
/* Pill-shape region label (was a full-cell colored background — user
   feedback: "сделай нормальные закругленные регионы а не прямоугольники
   закрашенные"). The td (.dash-wfpro-region-cell) is now neutral; the
   color tint lives on a pill <span> inside it. */
.dash-wfpro-region-cell {
  padding: 4px 8px !important;
}
.dash-wfpro-region-pill {
  display: inline-block;
  font-size: 11px; font-weight: 600;
  color: #1f2937;
  padding: 2px 10px;
  border-radius: 12px;
  white-space: nowrap;
  /* tint set inline per-row from REGION_COLORS */
}
/* Legacy class kept so any stale cache version still has fallback colors. */
.dash-wfpro-region {
  font-size: 11px; font-weight: 500;
  color: #1f2937;
}
.dash-wfpro-name {
  font-weight: 500;
  max-width: 180px;
  overflow: hidden; text-overflow: ellipsis;
}
.dash-wfpro-mo {
  font-family: 'SF Mono', monospace;
  font-size: 11px; font-weight: 600;
  text-align: center; width: 36px;
}
.dash-wfpro-km {
  font-family: 'SF Mono', monospace;
  font-size: 11px; font-weight: 600;
  text-align: right;
  color: var(--dash-blue);
}
.dash-wfpro-diff-early {
  font-family: 'SF Mono', monospace; font-size: 11px; font-weight: 700;
  color: var(--dash-green);
}
.dash-wfpro-diff-late {
  font-family: 'SF Mono', monospace; font-size: 11px; font-weight: 700;
  color: var(--dash-red);
}
.dash-wfpro-diff-ontime {
  font-family: 'SF Mono', monospace; font-size: 11px; font-weight: 600;
  color: var(--dash-text-dim);
}
.dash-wfpro-diff-na { color: var(--dash-text-dim); }

/* Losses column — financial losses from main waterfall computation.
   Positive = actual loss (red), negative absolute value = gain (green). */
.dash-wfpro-loss-bad {
  font-family: 'SF Mono', monospace; font-size: 11px; font-weight: 700;
  color: var(--dash-red);
}
.dash-wfpro-loss-good {
  font-family: 'SF Mono', monospace; font-size: 11px; font-weight: 700;
  color: var(--dash-green);
}
.dash-wfpro-loss-zero {
  font-family: 'SF Mono', monospace; font-size: 11px;
  color: var(--dash-text-dim);
}
.dash-wfpro-loss-na { color: var(--dash-text-dim); }

/* ── Funnel Stages widget ────────────────────────────────
   Horizontal-bar chart with per-stage rows + filter pills. Click on a row
   opens the drill-down overlay (shared scout-overlay box). */
.dash-fs { display: flex; flex-direction: column; gap: 10px; height: 100%; min-width: 0; }
.dash-fs-toolbar {
  display: flex; align-items: center; flex-wrap: wrap; gap: 6px;
  font-size: 12px;
}
.dash-fs-toolbar select {
  font: 12px var(--font, 'Inter');
  padding: 4px 8px; border-radius: 6px;
  border: 1px solid var(--dash-border);
  background: var(--dash-surface);
  color: var(--dash-text);
  cursor: pointer;
}
.dash-fs-pills {
  display: flex; gap: 4px; flex-wrap: wrap;
}
.dash-fs-pill {
  display: inline-flex; align-items: center; gap: 4px;
  font-size: 11px; font-weight: 500;
  padding: 3px 8px; border-radius: 12px;
  background: var(--dash-blue-bg); color: var(--dash-blue);
  cursor: pointer;
}
.dash-fs-pill:hover { background: rgba(37,99,235,.18); }
.dash-fs-summary {
  margin-left: auto;
  font-size: 11px; color: var(--dash-text-dim);
}
.dash-fs-summary strong { color: var(--dash-text); }
.dash-fs-bars {
  display: flex; flex-direction: column; gap: 6px;
  flex: 1; min-height: 0;
}
.dash-fs-row {
  display: grid; grid-template-columns: minmax(100px, 160px) 1fr;
  gap: 10px; align-items: center;
  cursor: pointer;
  padding: 4px 6px; border-radius: 5px;
  transition: background .12s;
}
.dash-fs-row:hover { background: var(--dash-surface2); }
.dash-fs-row-label {
  display: flex; align-items: center; gap: 6px;
  font-size: 11px; min-width: 0;
}
.dash-fs-stage-num {
  font-family: 'SF Mono', monospace;
  font-size: 10px; font-weight: 600;
  background: var(--dash-surface2);
  color: var(--dash-text-dim);
  padding: 1px 6px; border-radius: 8px;
  flex-shrink: 0;
}
.dash-fs-stage-name {
  font-weight: 500; color: var(--dash-text);
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.dash-fs-bar-track {
  position: relative;
  height: 22px;
  background: var(--dash-surface2);
  border-radius: 4px;
  overflow: hidden;
}
.dash-fs-bar {
  position: absolute; left: 0; top: 0; bottom: 0;
  background: linear-gradient(90deg, var(--dash-blue) 0%, #60a5fa 100%);
  border-radius: 4px;
  transition: width .25s ease;
  /* Minimum stub so every funnel stage stays visible as a tiny accent
     even when count=0 — user sees the whole funnel instead of a row of
     empty labels. */
  min-width: 4px;
}
.dash-fs-bar.is-empty {
  background: linear-gradient(90deg, rgba(107,114,128,.4) 0%, rgba(107,114,128,.25) 100%);
}
.dash-fs-bar-val {
  position: absolute; right: 8px; top: 50%; transform: translateY(-50%);
  font-family: 'SF Mono', monospace;
  font-size: 11px; font-weight: 600;
  color: var(--dash-text);
  text-shadow: 0 0 4px var(--dash-surface);
  z-index: 1;
}
.dash-fs-bar-pct {
  color: var(--dash-text-dim); font-weight: 500;
  font-size: 10px;
}

/* ── Loss Reasons widget ─────────────────────────────────
   Horizontal-bar chart sorted by count desc. Same pattern as funnel-stages
   but reasons aren't numbered and bars use a warm red palette. */
.dash-lr { display: flex; flex-direction: column; gap: 8px; height: 100%; min-width: 0; }
.dash-lr-title {
  font-size: 14px; font-weight: 700;
  color: var(--dash-text);
  letter-spacing: -0.01em;
}
/* Headline counter — total leads in period → rejected (red) + ratio %. */
.dash-lr-counter {
  display: flex; align-items: center; gap: 10px;
  padding: 8px 12px;
  background: var(--dash-surface2);
  border-radius: 8px;
  border: 1px solid var(--dash-border);
}
.dash-lr-counter-cell {
  display: flex; flex-direction: column; gap: 1px;
  line-height: 1.1;
}
.dash-lr-counter-n {
  font-family: 'SF Mono', monospace; font-size: 18px; font-weight: 700;
  color: var(--dash-text);
}
.dash-lr-counter-bad { color: var(--dash-red); }
.dash-lr-counter-lbl {
  font-size: 10px; color: var(--dash-text-dim);
  text-transform: uppercase; letter-spacing: 0.5px;
  font-weight: 600;
}
.dash-lr-counter-sep {
  font-size: 16px; color: var(--dash-text-dim); padding: 0 4px;
}
.dash-lr-counter-pct {
  margin-left: auto;
  font-family: 'SF Mono', monospace;
  font-size: 16px; font-weight: 700;
  color: var(--dash-red);
  padding: 4px 10px;
  border-radius: 12px;
  background: rgba(220,38,38,0.10);
}
.dash-lr-summary {
  font-size: 12px; color: var(--dash-text-dim);
  padding: 2px 0;
}
.dash-lr-summary strong { color: var(--dash-text); font-weight: 700; }
.dash-lr-period { float: right; font-size: 11px; opacity: 0.8; text-transform: capitalize; }
.dash-lr-bars {
  display: flex; flex-direction: column; gap: 8px;
  flex: 1; min-height: 0;
}
.dash-lr-row {
  cursor: pointer;
  padding: 4px 6px; border-radius: 5px;
  transition: background .12s;
}
.dash-lr-row:hover { background: var(--dash-surface2); }
.dash-lr-row-label {
  display: flex; align-items: baseline; justify-content: space-between; gap: 8px;
  margin-bottom: 4px;
}
.dash-lr-reason {
  font-size: 12px; font-weight: 600; color: var(--dash-text);
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
  min-width: 0; flex: 1;
}
.dash-lr-reason-meta {
  font-size: 10px; color: var(--dash-text-dim);
  font-family: 'SF Mono', monospace;
  flex-shrink: 0;
}
.dash-lr-bar-track {
  height: 8px;
  background: var(--dash-surface2);
  border-radius: 4px;
  overflow: hidden;
}
.dash-lr-bar {
  height: 100%;
  background: linear-gradient(90deg, var(--dash-red) 0%, #f87171 100%);
  border-radius: 4px;
  transition: width .25s ease;
}

/* ── Pipeline Conversion widget ──────────────────────────
   Per-stage rows: stage label + funnel bar (share of entry stage) +
   conversion-rate chip to the next stage (green/amber/red). */
.dash-conv { display: flex; flex-direction: column; gap: 8px; height: 100%; min-width: 0; }
.dash-conv-summary {
  display: flex; flex-wrap: wrap; gap: 10px; align-items: baseline;
  font-size: 12px; color: var(--dash-text-dim);
  padding: 2px 0 6px;
  border-bottom: 1px solid var(--dash-border);
}
.dash-conv-summary strong { color: var(--dash-text); font-weight: 700; font-size: 14px; }
.dash-conv-overall {
  margin-left: auto;
  font-weight: 700; color: var(--dash-blue);
}
.dash-conv-lost { color: var(--dash-red); font-weight: 600; }
.dash-conv-rows {
  display: flex; flex-direction: column; gap: 4px;
  flex: 1; overflow-y: auto; min-height: 0;
}
.dash-conv-row {
  display: flex; align-items: center; gap: 8px;
}
.dash-conv-label {
  display: flex; align-items: center; gap: 6px;
  width: 150px; flex-shrink: 0;
}
.dash-conv-name {
  font-size: 12px; color: var(--dash-text);
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.dash-conv-bar-track {
  flex: 1; position: relative;
  height: 20px;
  background: var(--dash-surface2);
  border-radius: 4px;
  overflow: hidden;
  min-width: 40px;
}
.dash-conv-bar {
  height: 100%;
  background: linear-gradient(90deg, var(--dash-blue) 0%, #60a5fa 100%);
  border-radius: 4px;
  transition: width .25s ease;
}
.dash-conv-cnt {
  position: absolute; right: 6px; top: 50%; transform: translateY(-50%);
  font: 700 11px 'SF Mono', monospace;
  color: var(--dash-text);
}
.dash-conv-rate {
  width: 54px; flex-shrink: 0; text-align: right;
  font: 700 12px 'SF Mono', monospace;
}
.dash-conv-rate.good { color: #166534; }
.dash-conv-rate.mid  { color: #854d0e; }
.dash-conv-rate.low  { color: #991b1b; }
.dash-conv-rate.end  { color: var(--dash-text-dim); }

/* ── Signings & Openings Trend widget ────────────────────
   Grouped vertical bars per month: signed (blue) + opened (green).
   Bars grow from the baseline; value labels float above. */
.dash-trend { display: flex; flex-direction: column; gap: 8px; height: 100%; min-width: 0; }
.dash-trend-toolbar {
  display: flex; align-items: center; justify-content: space-between;
  gap: 10px; flex-wrap: wrap;
}
.dash-trend-legend { display: flex; gap: 12px; font-size: 12px; color: var(--dash-text-dim); }
.dash-trend-leg { display: inline-flex; align-items: center; gap: 5px; }
.dash-trend-leg strong { color: var(--dash-text); font-weight: 700; }
.dash-trend-leg i {
  width: 10px; height: 10px; border-radius: 2px; display: inline-block;
}
.dash-trend-leg i.signed { background: var(--dash-blue); }
.dash-trend-leg i.opened { background: #22c55e; }
.dash-trend-range { display: inline-flex; border: 1px solid var(--dash-border); border-radius: 6px; overflow: hidden; }
.dash-trend-rbtn {
  background: transparent; border: 0;
  font: 600 11px var(--font, 'Inter');
  padding: 3px 9px; cursor: pointer; color: var(--dash-text-dim);
  transition: background .12s, color .12s;
}
.dash-trend-rbtn + .dash-trend-rbtn { border-left: 1px solid var(--dash-border); }
.dash-trend-rbtn.active { background: var(--dash-blue-bg); color: var(--dash-blue); }
.dash-trend-chart {
  display: flex; align-items: flex-end; gap: 6px;
  flex: 1; min-height: 0;
  padding-top: 14px; /* room for value labels above bars */
}
.dash-trend-col {
  flex: 1; min-width: 0;
  display: flex; flex-direction: column; align-items: center;
  height: 100%;
  cursor: pointer;
  border-radius: 6px;
  transition: background .12s;
}
.dash-trend-col:hover { background: var(--dash-surface2); }
.dash-trend-bars {
  flex: 1; min-height: 0;
  display: flex; align-items: flex-end; justify-content: center; gap: 3px;
  width: 100%;
}
.dash-trend-barwrap {
  position: relative;
  flex: 1; max-width: 16px;
  height: 100%;
  display: flex; align-items: flex-end; justify-content: center;
}
.dash-trend-val {
  position: absolute; top: -13px; left: 50%; transform: translateX(-50%);
  font: 700 9px 'SF Mono', monospace;
  color: var(--dash-text-dim);
  white-space: nowrap;
}
.dash-trend-bar {
  width: 100%;
  border-radius: 3px 3px 0 0;
  transition: height .25s ease;
  min-height: 0;
}
.dash-trend-bar.signed { background: linear-gradient(180deg, #60a5fa 0%, var(--dash-blue) 100%); }
.dash-trend-bar.opened { background: linear-gradient(180deg, #4ade80 0%, #22c55e 100%); }
.dash-trend-month {
  font-size: 10px; color: var(--dash-text-dim);
  margin-top: 4px; white-space: nowrap;
}
.dash-trend-tag {
  font: 700 9px var(--font, 'Inter'); padding: 1px 6px; border-radius: 8px;
  text-transform: uppercase; letter-spacing: .3px;
}
.dash-trend-tag.signed { background: var(--dash-blue-bg); color: var(--dash-blue); }
.dash-trend-tag.opened { background: rgba(34,197,94,.15); color: #166534; }

/* ── Stalled Leads widget ────────────────────────────────
   Actionable list of leads stuck in a stage too long. Rows sorted
   worst-first; days chip colour-ramps by severity. */
.dash-stale { display: flex; flex-direction: column; gap: 8px; height: 100%; min-width: 0; }
.dash-stale-toolbar {
  display: flex; align-items: center; justify-content: space-between;
  gap: 10px; flex-wrap: wrap;
}
.dash-stale-summary { font-size: 12px; color: var(--dash-text-dim); }
.dash-stale-summary strong { color: var(--dash-text); font-weight: 700; font-size: 14px; }
.dash-stale-thresh { display: inline-flex; border: 1px solid var(--dash-border); border-radius: 6px; overflow: hidden; }
.dash-stale-thbtn {
  background: transparent; border: 0;
  font: 600 11px var(--font, 'Inter');
  padding: 3px 9px; cursor: pointer; color: var(--dash-text-dim);
  transition: background .12s, color .12s;
}
.dash-stale-thbtn + .dash-stale-thbtn { border-left: 1px solid var(--dash-border); }
.dash-stale-thbtn.active { background: var(--dash-blue-bg); color: var(--dash-blue); }
.dash-stale-list { display: flex; flex-direction: column; gap: 4px; flex: 1; overflow-y: auto; min-height: 0; }
.dash-stale-row {
  display: flex; align-items: center; gap: 8px;
  padding: 6px 8px;
  background: var(--dash-surface);
  border: 1px solid var(--dash-border);
  border-radius: 6px;
}
.dash-stale-main { flex: 1; min-width: 0; }
.dash-stale-name {
  font-size: 12px; font-weight: 500; color: var(--dash-text);
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.dash-stale-sub {
  display: flex; gap: 8px; flex-wrap: wrap;
  font-size: 10px; color: var(--dash-text-dim); margin-top: 1px;
}
.dash-stale-stage { font-weight: 600; }
.dash-stale-days {
  flex-shrink: 0;
  font: 700 12px 'SF Mono', monospace;
  padding: 3px 8px; border-radius: 10px;
}
.dash-stale-days.sev-low  { background: var(--dash-surface2); color: var(--dash-text-dim); }
.dash-stale-days.sev-mid  { background: rgba(234,179,8,.18); color: #854d0e; }
.dash-stale-days.sev-high { background: rgba(220,38,38,.14); color: #991b1b; }

/* ── Upcoming Signings widget ────────────────────────────
   Locations in confirmation stages, biggest Key Money first. */
.dash-upc { display: flex; flex-direction: column; gap: 8px; height: 100%; min-width: 0; }
.dash-upc-summary {
  display: flex; align-items: baseline; justify-content: space-between;
  gap: 10px; font-size: 12px; color: var(--dash-text-dim);
  padding-bottom: 6px; border-bottom: 1px solid var(--dash-border);
}
.dash-upc-summary strong { color: var(--dash-text); font-weight: 700; font-size: 14px; }
.dash-upc-total { font-weight: 700; color: var(--dash-blue); }
.dash-upc-list { display: flex; flex-direction: column; gap: 4px; flex: 1; overflow-y: auto; min-height: 0; }
.dash-upc-row {
  display: flex; align-items: center; gap: 8px;
  padding: 6px 8px;
  background: var(--dash-surface);
  border: 1px solid var(--dash-border);
  border-radius: 6px;
}
.dash-upc-main { flex: 1; min-width: 0; }
.dash-upc-name {
  font-size: 12px; font-weight: 500; color: var(--dash-text);
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.dash-upc-sub { display: flex; gap: 6px; flex-wrap: wrap; align-items: center; margin-top: 2px; }
.dash-upc-stage { font-size: 10px; color: var(--dash-text-dim); font-weight: 600; }
.dash-upc-region {
  font-size: 10px; padding: 1px 7px; border-radius: 8px;
  background: var(--dash-surface2); color: var(--dash-text-dim);
  white-space: nowrap;
}
.dash-upc-km {
  flex-shrink: 0;
  font: 700 12px 'SF Mono', monospace;
  color: #166534;
  padding: 3px 8px; border-radius: 10px;
  background: rgba(34,197,94,.12);
}

/* ── Top Traffic Locations widget ────────────────────────
   Ranked list of locations by measured pedestrian count. Each row:
   rank + name (+ file link) + proportional bar + region/date + count. */
.dash-tt { display: flex; flex-direction: column; gap: 8px; height: 100%; min-width: 0; }
.dash-tt-summary {
  display: flex; align-items: baseline; gap: 10px;
  font-size: 12px; color: var(--dash-text-dim);
  padding-bottom: 6px; border-bottom: 1px solid var(--dash-border);
}
.dash-tt-summary strong { color: var(--dash-text); font-weight: 700; font-size: 14px; }
.dash-tt-more { margin-left: auto; opacity: .8; }
.dash-tt-list { display: flex; flex-direction: column; gap: 6px; flex: 1; overflow-y: auto; min-height: 0; }
.dash-tt-row { display: flex; align-items: center; gap: 8px; }
.dash-tt-rank {
  flex-shrink: 0; width: 20px; text-align: center;
  font: 700 12px 'SF Mono', monospace; color: var(--dash-text-dim);
}
.dash-tt-main { flex: 1; min-width: 0; display: flex; flex-direction: column; gap: 2px; }
.dash-tt-name {
  font-size: 12px; font-weight: 500; color: var(--dash-text);
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
  display: flex; align-items: center; gap: 5px;
}
.dash-tt-file { text-decoration: none; font-size: 11px; flex-shrink: 0; }
.dash-tt-file:hover { opacity: .7; }
.dash-tt-bar-track {
  height: 5px; background: var(--dash-surface2);
  border-radius: 3px; overflow: hidden;
}
.dash-tt-bar {
  height: 100%;
  background: linear-gradient(90deg, #f59e0b 0%, #fbbf24 100%);
  border-radius: 3px; transition: width .25s ease;
}
.dash-tt-sub { display: flex; gap: 6px; align-items: center; flex-wrap: wrap; }
.dash-tt-region {
  font-size: 10px; padding: 1px 7px; border-radius: 8px;
  background: var(--dash-surface2); color: var(--dash-text-dim); white-space: nowrap;
}
.dash-tt-date { font-size: 10px; color: var(--dash-text-dim); }
.dash-tt-count {
  flex-shrink: 0;
  font: 700 13px 'SF Mono', monospace;
  color: #b45309;
  min-width: 48px; text-align: right;
}

/* ── Notes widget (personal scratchpad) ──────────────────
   Full-height textarea + footer hint/counter. Content persists in the
   widget config (no Firestore collection). */
.dash-notes { display: flex; flex-direction: column; gap: 6px; height: 100%; min-width: 0; }
.dash-notes-area {
  flex: 1; min-height: 0; width: 100%; box-sizing: border-box;
  resize: none;
  border: 1px solid var(--dash-border);
  border-radius: 8px;
  background: #fffdf5; /* faint legal-pad tint so it reads as a note */
  padding: 10px 12px;
  font: 13px/1.5 var(--font, 'Inter');
  color: var(--dash-text);
}
.dash-notes-area:focus {
  outline: 2px solid var(--dash-blue);
  outline-offset: -1px;
  border-color: transparent;
}
.dash-notes-foot {
  display: flex; align-items: center; justify-content: space-between;
  font-size: 10px; color: var(--dash-text-dim);
}
.dash-notes-count { font-family: 'SF Mono', monospace; }

/* ── Quick Links widget (personal bookmarks) ─────────────
   Scrollable link list + add form. Content persists in widget config. */
.dash-ql { display: flex; flex-direction: column; gap: 8px; height: 100%; min-width: 0; }
.dash-ql-list { display: flex; flex-direction: column; gap: 4px; flex: 1; overflow-y: auto; min-height: 0; }
.dash-ql-row { display: flex; align-items: center; gap: 6px; }
.dash-ql-link {
  flex: 1; min-width: 0;
  display: flex; align-items: center; gap: 8px;
  padding: 6px 8px;
  border: 1px solid var(--dash-border);
  border-radius: 6px;
  background: var(--dash-surface);
  text-decoration: none;
  transition: background .12s, border-color .12s;
}
.dash-ql-link:hover { background: var(--dash-surface2); border-color: var(--dash-text-dim); }
.dash-ql-glyph { flex-shrink: 0; font-size: 13px; }
.dash-ql-meta { min-width: 0; display: flex; flex-direction: column; gap: 1px; }
.dash-ql-label {
  font-size: 12px; font-weight: 500; color: var(--dash-text);
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.dash-ql-host {
  font-size: 10px; color: var(--dash-text-dim);
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.dash-ql-del {
  flex-shrink: 0;
  background: transparent; border: 0; cursor: pointer;
  color: var(--dash-text-dim); font-size: 11px;
  padding: 4px 6px; border-radius: 4px;
  opacity: 0; transition: opacity .15s, color .12s, background .12s;
}
.dash-ql-row:hover .dash-ql-del { opacity: 0.7; }
.dash-ql-del:hover { opacity: 1; color: var(--dash-red); background: rgba(220,38,38,.08); }
.dash-ql-form { display: flex; gap: 4px; flex-wrap: wrap; }
.dash-ql-in-label { flex: 1 1 90px; min-width: 0; }
.dash-ql-in-url { flex: 2 1 120px; min-width: 0; }
.dash-ql-form input {
  font: 12px var(--font, 'Inter');
  padding: 5px 8px;
  border: 1px solid var(--dash-border);
  border-radius: 6px;
  background: var(--dash-surface);
  box-sizing: border-box;
}
.dash-ql-form input:focus { outline: 2px solid var(--dash-blue); outline-offset: -1px; border-color: transparent; }
.dash-ql-in-url.dash-ql-invalid { border-color: var(--dash-red); background: rgba(220,38,38,.05); }
.dash-ql-add {
  flex-shrink: 0;
  background: var(--dash-blue-bg); color: var(--dash-blue);
  border: 1px solid rgba(37,99,235,.2);
  font: 600 12px var(--font, 'Inter');
  padding: 5px 12px; border-radius: 6px; cursor: pointer;
  transition: background .12s;
}
.dash-ql-add:hover:not(:disabled) { background: rgba(37,99,235,.15); }
.dash-ql-add:disabled { opacity: .5; cursor: default; }

/* ── Scout Leaderboard widget ────────────────────────────
   Ranked scouts: rank + avatar + name + found-bar + stat cluster
   (found / signed / conv% / active). */
.dash-sl { display: flex; flex-direction: column; gap: 8px; height: 100%; min-width: 0; }
.dash-sl-head {
  display: flex; align-items: center; justify-content: space-between; gap: 10px;
  flex-wrap: wrap; padding-bottom: 6px; border-bottom: 1px solid var(--dash-border);
}
.dash-sl-summary { font-size: 12px; color: var(--dash-text-dim); }
.dash-sl-summary strong { color: var(--dash-text); font-weight: 700; font-size: 14px; }
.dash-sl-legend { display: flex; gap: 8px; font-size: 10px; color: var(--dash-text-dim); flex-wrap: wrap; }
.dash-sl-list { display: flex; flex-direction: column; gap: 5px; flex: 1; overflow-y: auto; min-height: 0; }
.dash-sl-row { display: flex; align-items: center; gap: 8px; }
.dash-sl-rank { flex-shrink: 0; width: 18px; text-align: center; font: 700 12px 'SF Mono', monospace; color: var(--dash-text-dim); }
.dash-sl-avatar {
  flex-shrink: 0; width: 26px; height: 26px; border-radius: 50%;
  background: linear-gradient(135deg, #818cf8 0%, #6366f1 100%);
  color: #fff; font: 700 10px var(--font, 'Inter');
  display: flex; align-items: center; justify-content: center;
}
.dash-sl-main { flex: 1; min-width: 0; display: flex; flex-direction: column; gap: 3px; }
.dash-sl-name {
  font-size: 12px; font-weight: 500; color: var(--dash-text);
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.dash-sl-bar-track { height: 4px; background: var(--dash-surface2); border-radius: 2px; overflow: hidden; }
.dash-sl-bar { height: 100%; background: linear-gradient(90deg, var(--dash-blue) 0%, #818cf8 100%); border-radius: 2px; transition: width .25s ease; }
.dash-sl-stats { flex-shrink: 0; display: flex; gap: 6px; align-items: center; }
.dash-sl-stat {
  font: 700 12px 'SF Mono', monospace; color: var(--dash-text);
  min-width: 20px; text-align: right;
}
.dash-sl-stat.signed { color: #166534; }
.dash-sl-stat.active { color: var(--dash-blue); }
.dash-sl-conv {
  font: 700 11px 'SF Mono', monospace; min-width: 30px; text-align: right;
  color: var(--dash-text-dim);
}
.dash-sl-conv.good { color: #166534; }
.dash-sl-conv.mid  { color: #854d0e; }
.dash-sl-conv.low  { color: #991b1b; }

/* ── Sales Velocity widget ───────────────────────────────
   3 KPI tiles (avg / median / count) + range line + distribution bars. */
.dash-vel { display: flex; flex-direction: column; gap: 8px; height: 100%; min-width: 0; }
.dash-vel-kpis { display: flex; gap: 8px; }
.dash-vel-kpi {
  flex: 1; text-align: center;
  background: var(--dash-surface2); border-radius: 8px; padding: 8px 4px;
}
.dash-vel-num { font: 700 22px 'SF Mono', monospace; color: var(--dash-blue); line-height: 1; }
.dash-vel-lbl { font-size: 10px; color: var(--dash-text-dim); margin-top: 3px; text-transform: uppercase; letter-spacing: .3px; }
.dash-vel-range { font-size: 11px; color: var(--dash-text-dim); text-align: center; }
.dash-vel-chart {
  display: flex; align-items: flex-end; gap: 6px;
  flex: 1; min-height: 40px; padding-top: 12px;
}
.dash-vel-col { flex: 1; min-width: 0; display: flex; flex-direction: column; align-items: center; height: 100%; }
.dash-vel-barwrap { position: relative; flex: 1; min-height: 0; width: 100%; display: flex; align-items: flex-end; justify-content: center; }
.dash-vel-val {
  position: absolute; top: -12px; left: 50%; transform: translateX(-50%);
  font: 700 9px 'SF Mono', monospace; color: var(--dash-text-dim);
}
.dash-vel-bar {
  width: 70%; max-width: 28px; border-radius: 3px 3px 0 0;
  background: linear-gradient(180deg, #818cf8 0%, var(--dash-blue) 100%);
  transition: height .25s ease;
}
.dash-vel-blabel { font-size: 9px; color: var(--dash-text-dim); margin-top: 4px; white-space: nowrap; }

/* ── Region × Stage Matrix widget ────────────────────────
   Heatmap table: region rows × stage columns, blue-tint cells. */
.dash-rsm { display: flex; flex-direction: column; gap: 8px; height: 100%; min-width: 0; }
.dash-rsm-legend { font-size: 12px; color: var(--dash-text-dim); }
.dash-rsm-legend strong { color: var(--dash-text); font-weight: 700; }
.dash-rsm-hint { display: block; font-size: 10px; opacity: .7; margin-top: 1px; }
.dash-rsm-wrap { flex: 1; overflow: auto; min-height: 0; }
.dash-rsm-table { border-collapse: collapse; width: 100%; font-size: 11px; }
.dash-rsm-table th, .dash-rsm-table td { text-align: center; padding: 3px 4px; }
.dash-rsm-corner { text-align: left; color: var(--dash-text-dim); font-weight: 600; position: sticky; left: 0; background: var(--dash-surface); }
.dash-rsm-stage {
  font: 700 11px 'SF Mono', monospace; color: var(--dash-text-dim);
  cursor: help; width: 30px;
}
.dash-rsm-region { text-align: left; position: sticky; left: 0; background: var(--dash-surface); }
.dash-rsm-pill {
  font-size: 11px; padding: 1px 7px; border-radius: 8px; white-space: nowrap;
  background: var(--dash-surface2); color: var(--dash-text-dim);
}
.dash-rsm-cell {
  font: 600 11px 'SF Mono', monospace;
  border-radius: 3px; min-width: 26px;
  color: var(--dash-text);
}
.dash-rsm-total { font: 700 11px 'SF Mono', monospace; color: var(--dash-text); background: var(--dash-surface2); }
.dash-rsm-table tfoot th, .dash-rsm-table tfoot td { border-top: 2px solid var(--dash-border); }

/* ── Format Mix widget ───────────────────────────────────
   Two stacked horizontal bars (pipeline / signed) + legend + table. */
.dash-fmix { display: flex; flex-direction: column; gap: 10px; height: 100%; min-width: 0; }
.dash-fmix-block { display: flex; flex-direction: column; gap: 4px; }
.dash-fmix-blabel { font-size: 12px; color: var(--dash-text-dim); }
.dash-fmix-blabel strong { color: var(--dash-text); font-weight: 700; font-size: 14px; margin-left: 4px; }
.dash-fmix-bar {
  display: flex; height: 26px; border-radius: 6px; overflow: hidden;
  background: var(--dash-surface2);
}
.dash-fmix-seg {
  display: flex; align-items: center; justify-content: center;
  font: 700 10px var(--font, 'Inter'); color: #fff;
  white-space: nowrap; overflow: hidden; transition: width .25s ease;
  min-width: 0;
}
.dash-fmix-empty { font-size: 11px; color: var(--dash-text-dim); padding: 4px 8px; font-style: italic; }
.dash-fmix-legend { display: flex; gap: 12px; flex-wrap: wrap; font-size: 11px; color: var(--dash-text-dim); }
.dash-fmix-leg { display: inline-flex; align-items: center; gap: 4px; }
.dash-fmix-leg i { width: 10px; height: 10px; border-radius: 2px; display: inline-block; }
.dash-fmix-table { width: 100%; border-collapse: collapse; font-size: 11px; margin-top: auto; }
.dash-fmix-table th { text-align: right; color: var(--dash-text-dim); font-weight: 600; padding: 2px 6px; }
.dash-fmix-table th:first-child { text-align: left; }
.dash-fmix-table td { padding: 2px 6px; }
.dash-fmix-num { text-align: right; font: 700 11px 'SF Mono', monospace; color: var(--dash-text); }
.dash-fmix-dot { display: inline-block; width: 8px; height: 8px; border-radius: 2px; margin-right: 5px; }

/* ── My Day widget (today agenda) ────────────────────────
   Merged reminders+tasks, Overdue + Today sections. */
.dash-myday { display: flex; flex-direction: column; gap: 8px; height: 100%; min-width: 0; }
.dash-myday-head {
  display: flex; align-items: baseline; justify-content: space-between; gap: 8px;
  padding-bottom: 6px; border-bottom: 1px solid var(--dash-border);
}
.dash-myday-date { font-size: 13px; font-weight: 600; color: var(--dash-text); }
.dash-myday-total { font-size: 11px; color: var(--dash-text-dim); font-family: 'SF Mono', monospace; }
.dash-myday-body { flex: 1; overflow-y: auto; min-height: 0; display: flex; flex-direction: column; gap: 10px; }
.dash-myday-section { display: flex; flex-direction: column; gap: 3px; }
.dash-myday-shead {
  font-size: 10px; font-weight: 700; text-transform: uppercase; letter-spacing: .4px;
  color: var(--dash-text-dim);
  display: flex; align-items: center; gap: 6px;
}
.dash-myday-shead.overdue { color: var(--dash-red); }
.dash-myday-shead.today { color: var(--dash-blue); }
.dash-myday-scount {
  font-family: 'SF Mono', monospace; font-weight: 700;
  background: var(--dash-surface2); border-radius: 8px; padding: 0 6px;
}
.dash-myday-row {
  display: flex; align-items: center; gap: 8px;
  padding: 6px 8px;
  background: var(--dash-surface);
  border: 1px solid var(--dash-border);
  border-radius: 6px;
}
.dash-myday-glyph { flex-shrink: 0; font-size: 13px; }
.dash-myday-title {
  flex: 1; min-width: 0;
  font-size: 12px; color: var(--dash-text);
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.dash-myday-due {
  flex-shrink: 0;
  font: 600 10px 'SF Mono', monospace;
  padding: 2px 7px; border-radius: 8px;
  background: var(--dash-surface2); color: var(--dash-text-dim);
}
.dash-myday-due.overdue { background: rgba(220,38,38,.12); color: var(--dash-red); font-weight: 700; }
.dash-myday-due.today { background: rgba(37,99,235,.1); color: var(--dash-blue); }

/* ── Pending Tenders widget ──────────────────────────────
   Open tenders awaiting award, oldest first. Row = project name +
   deadline/invited + days-open chip (severity-ramped). */
.dash-pt { display: flex; flex-direction: column; gap: 8px; height: 100%; min-width: 0; }
.dash-pt-summary { font-size: 12px; color: var(--dash-text-dim); padding-bottom: 6px; border-bottom: 1px solid var(--dash-border); }
.dash-pt-summary strong { color: var(--dash-text); font-weight: 700; font-size: 14px; }
.dash-pt-list { display: flex; flex-direction: column; gap: 4px; flex: 1; overflow-y: auto; min-height: 0; }
.dash-pt-row { display: flex; align-items: center; gap: 8px; }
.dash-pt-main {
  flex: 1; min-width: 0;
  display: flex; flex-direction: column; gap: 2px;
  padding: 6px 8px; border: 1px solid var(--dash-border); border-radius: 6px;
  background: var(--dash-surface); text-decoration: none;
  transition: background .12s, border-color .12s;
}
.dash-pt-main:hover { background: var(--dash-surface2); border-color: var(--dash-text-dim); }
.dash-pt-name {
  font-size: 12px; font-weight: 500; color: var(--dash-text);
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.dash-pt-sub { display: flex; gap: 8px; align-items: center; flex-wrap: wrap; }
.dash-pt-deadline { font-size: 10px; color: var(--dash-text-dim); }
.dash-pt-deadline.overdue { color: var(--dash-red); font-weight: 700; }
.dash-pt-invited { font-size: 10px; color: var(--dash-text-dim); }
.dash-pt-age {
  flex-shrink: 0;
  font: 700 12px 'SF Mono', monospace;
  padding: 3px 8px; border-radius: 10px;
  background: var(--dash-surface2); color: var(--dash-text-dim);
}
.dash-pt-age.sev-low  { background: var(--dash-surface2); color: var(--dash-text-dim); }
.dash-pt-age.sev-mid  { background: rgba(234,179,8,.18); color: #854d0e; }
.dash-pt-age.sev-high { background: rgba(220,38,38,.14); color: #991b1b; }

/* ── Construction Projects widget ────────────────────────
   Projects by stage — coloured dot + label + bar + count. */
.dash-cp { display: flex; flex-direction: column; gap: 8px; height: 100%; min-width: 0; }
.dash-cp-summary {
  display: flex; align-items: baseline; justify-content: space-between; gap: 10px;
  font-size: 12px; color: var(--dash-text-dim);
  padding-bottom: 6px; border-bottom: 1px solid var(--dash-border);
}
.dash-cp-summary strong { color: var(--dash-text); font-weight: 700; font-size: 14px; }
.dash-cp-active { color: var(--dash-blue); font-weight: 600; }
.dash-cp-list { display: flex; flex-direction: column; gap: 8px; flex: 1; overflow-y: auto; min-height: 0; justify-content: center; }
.dash-cp-row { display: flex; align-items: center; gap: 8px; }
.dash-cp-dot { flex-shrink: 0; width: 10px; height: 10px; border-radius: 3px; }
.dash-cp-label { flex-shrink: 0; width: 92px; font-size: 12px; color: var(--dash-text); }
.dash-cp-bar-track { flex: 1; height: 8px; background: var(--dash-surface2); border-radius: 4px; overflow: hidden; }
.dash-cp-bar { height: 100%; border-radius: 4px; transition: width .25s ease; }
.dash-cp-count { flex-shrink: 0; min-width: 24px; text-align: right; font: 700 13px 'SF Mono', monospace; color: var(--dash-text); }

/* ── Thai Words widget ───────────────────────────────────
   Daily phrase cards: Thai script + romanisation + meaning. */
.dash-tw { display: flex; flex-direction: column; gap: 8px; height: 100%; min-width: 0; }
.dash-tw-head { display: flex; align-items: center; justify-content: space-between; }
.dash-tw-title { font-size: 12px; font-weight: 600; color: var(--dash-text-dim); }
.dash-tw-shuffle {
  background: transparent; border: 1px solid var(--dash-border); border-radius: 6px;
  cursor: pointer; font-size: 13px; padding: 2px 8px; transition: background .12s;
}
.dash-tw-shuffle:hover { background: var(--dash-surface2); }
.dash-tw-grid {
  flex: 1; min-height: 0; overflow-y: auto;
  display: grid; grid-template-columns: repeat(auto-fill, minmax(120px, 1fr)); gap: 8px;
}
.dash-tw-card {
  background: var(--dash-surface2); border: 1px solid var(--dash-border);
  border-radius: 8px; padding: 8px 10px; text-align: center;
}
.dash-tw-th { font-size: 18px; font-weight: 700; color: var(--dash-text); line-height: 1.2; }
.dash-tw-tr { font-size: 11px; color: var(--dash-blue); font-style: italic; margin-top: 2px; }
.dash-tw-en { font-size: 11px; color: var(--dash-text-dim); margin-top: 3px; }

/* ── Shop Revenue (projected scaffold) widget ────────────
   Projection banner + KPI tiles + top-shops bars. */
.dash-sr { display: flex; flex-direction: column; gap: 8px; height: 100%; min-width: 0; }
.dash-sr-banner {
  font-size: 10px; color: #854d0e;
  background: rgba(234,179,8,.14); border: 1px solid rgba(234,179,8,.3);
  border-radius: 6px; padding: 4px 8px; text-align: center;
}
.dash-sr-kpis { display: flex; gap: 8px; }
.dash-sr-kpi { flex: 1; text-align: center; background: var(--dash-surface2); border-radius: 8px; padding: 8px 4px; }
.dash-sr-num { font: 700 17px 'SF Mono', monospace; color: #166534; line-height: 1; }
.dash-sr-lbl { font-size: 9px; color: var(--dash-text-dim); margin-top: 3px; text-transform: uppercase; letter-spacing: .3px; }
.dash-sr-top-label { font-size: 10px; color: var(--dash-text-dim); text-transform: uppercase; letter-spacing: .3px; }
.dash-sr-list { display: flex; flex-direction: column; gap: 4px; flex: 1; overflow-y: auto; min-height: 0; }
.dash-sr-row { display: flex; align-items: center; gap: 8px; }
.dash-sr-name {
  flex: 0 0 38%; min-width: 0; font-size: 11px; color: var(--dash-text);
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.dash-sr-bar-track { flex: 1; height: 7px; background: var(--dash-surface2); border-radius: 4px; overflow: hidden; }
.dash-sr-bar { height: 100%; background: linear-gradient(90deg, #22c55e 0%, #4ade80 100%); border-radius: 4px; transition: width .25s ease; }
.dash-sr-val { flex-shrink: 0; font: 700 11px 'SF Mono', monospace; color: #166534; min-width: 44px; text-align: right; }
.dash-sr-foot { font-size: 10px; color: var(--dash-text-dim); font-style: italic; }

/* ── Competitor Proximity widget ─────────────────────────
   Our committed shops ranked by # competitors within the chosen radius. */
.dash-cmp { display: flex; flex-direction: column; gap: 8px; height: 100%; min-width: 0; }
.dash-cmp-toolbar { display: flex; align-items: center; justify-content: space-between; gap: 10px; flex-wrap: wrap; padding-bottom: 6px; border-bottom: 1px solid var(--dash-border); }
.dash-cmp-summary { font-size: 12px; color: var(--dash-text-dim); }
.dash-cmp-summary strong { color: var(--dash-text); font-weight: 700; }
.dash-cmp-radius { display: inline-flex; border: 1px solid var(--dash-border); border-radius: 6px; overflow: hidden; }
.dash-cmp-rbtn {
  background: transparent; border: 0; font: 600 11px var(--font, 'Inter');
  padding: 3px 9px; cursor: pointer; color: var(--dash-text-dim); transition: background .12s, color .12s;
}
.dash-cmp-rbtn + .dash-cmp-rbtn { border-left: 1px solid var(--dash-border); }
.dash-cmp-rbtn.active { background: var(--dash-blue-bg); color: var(--dash-blue); }
.dash-cmp-list { display: flex; flex-direction: column; gap: 5px; flex: 1; overflow-y: auto; min-height: 0; }
.dash-cmp-row { display: flex; align-items: center; gap: 8px; }
.dash-cmp-main { flex: 1; min-width: 0; display: flex; flex-direction: column; gap: 2px; }
.dash-cmp-name {
  font-size: 12px; font-weight: 500; color: var(--dash-text);
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.dash-cmp-region { font-size: 10px; color: var(--dash-text-dim); }
.dash-cmp-bar-track { height: 5px; background: var(--dash-surface2); border-radius: 3px; overflow: hidden; }
.dash-cmp-bar { height: 100%; border-radius: 3px; transition: width .25s ease; }
.dash-cmp-bar.sev-low  { background: #22c55e; }
.dash-cmp-bar.sev-mid  { background: #f59e0b; }
.dash-cmp-bar.sev-high { background: var(--dash-red); }
.dash-cmp-count {
  flex-shrink: 0; min-width: 28px; text-align: center;
  font: 700 13px 'SF Mono', monospace;
  padding: 3px 8px; border-radius: 10px;
}
.dash-cmp-count.sev-low  { background: rgba(34,197,94,.14); color: #166534; }
.dash-cmp-count.sev-mid  { background: rgba(234,179,8,.18); color: #854d0e; }
.dash-cmp-count.sev-high { background: rgba(220,38,38,.14); color: #991b1b; }

/* ── Days per Stage widget ───────────────────────────────
   Per-stage horizontal bars with average days + region-colored sub-chips
   below each bar. Footer surfaces slowest stage as bottleneck callout. */
.dash-dps { display: flex; flex-direction: column; gap: 10px; height: 100%; min-width: 0; }
.dash-dps-summary {
  font-size: 12px; color: var(--dash-text-dim);
  padding: 6px 0;
  border-bottom: 1px solid var(--dash-border);
}
.dash-dps-summary strong { color: var(--dash-text); font-weight: 700; }
.dash-dps-period { float: right; font-size: 11px; opacity: 0.8; text-transform: capitalize; }
.dash-dps-bars {
  display: flex; flex-direction: column; gap: 10px;
  flex: 1; min-height: 0;
}
.dash-dps-row {
  display: flex; flex-direction: column; gap: 4px;
}
.dash-dps-row-empty { opacity: 0.55; }
.dash-dps-row-label {
  display: flex; align-items: center; gap: 6px;
  font-size: 11px;
}
.dash-dps-bar-track {
  position: relative;
  height: 18px;
  background: var(--dash-surface2);
  border-radius: 3px;
  overflow: hidden;
}
.dash-dps-bar {
  position: absolute; left: 0; top: 0; bottom: 0;
  background: linear-gradient(90deg, var(--dash-amber) 0%, #fb923c 100%);
  border-radius: 3px;
  transition: width .25s ease;
}
.dash-dps-bar-val {
  position: absolute; right: 8px; top: 50%; transform: translateY(-50%);
  font-family: 'SF Mono', monospace;
  font-size: 11px; font-weight: 700;
  color: var(--dash-text);
  text-shadow: 0 0 4px var(--dash-surface);
  z-index: 1;
}
.dash-dps-bar-unit { font-weight: 500; opacity: 0.7; }
.dash-dps-empty-msg {
  display: flex; align-items: center; justify-content: center; height: 100%;
  font-size: 10px; color: var(--dash-text-dim); font-style: italic;
}
.dash-dps-region-row {
  display: flex; gap: 4px; flex-wrap: wrap;
  padding-left: 32px;
}
.dash-dps-region-chip {
  font-size: 10px; font-weight: 600;
  padding: 2px 7px; border-radius: 10px;
  white-space: nowrap;
}
.dash-dps-footer {
  font-size: 12px; color: var(--dash-text);
  padding: 8px 10px;
  background: rgba(217,119,6,.08);
  border-radius: 6px;
  border-left: 3px solid var(--dash-amber);
}
.dash-dps-footer b { font-weight: 700; }

/* Orphan reminders badge — appears in the Reminders header for admins
   when one or more reminders are assigned to a user that no longer exists
   in the `users` collection. Click → opens a drill-down overlay where
   the admin can reassign-to-self or delete each orphan. */
.dash-rem-orphan-badge {
  margin-left: auto;
  background: rgba(220,38,38,.12); color: var(--dash-red);
  border: 1px solid rgba(220,38,38,.3);
  font-size: 10px; font-weight: 600;
  padding: 2px 8px; border-radius: 12px;
  cursor: pointer;
  transition: background .12s;
}
.dash-rem-orphan-badge:hover { background: rgba(220,38,38,.2); }

.dash-rem-orphan-reassign,
.dash-rem-orphan-del {
  font: 11px var(--font, 'Inter');
  padding: 4px 10px; border-radius: 4px;
  border: 1px solid var(--dash-border);
  background: var(--dash-surface); cursor: pointer;
  margin-right: 4px;
}
.dash-rem-orphan-reassign { color: var(--dash-blue); border-color: rgba(37,99,235,.3); }
.dash-rem-orphan-reassign:hover { background: var(--dash-blue-bg); }
.dash-rem-orphan-del { color: var(--dash-red); border-color: rgba(220,38,38,.3); }
.dash-rem-orphan-del:hover { background: rgba(220,38,38,.08); }

/* ── Projects by People widget (PR-GG) ─────────────────────
   Personal mini-CRM tracker — each card represents one person, nested
   projects inside. Drag-drop reorder, accordion expand, inline status
   pill cycle. Reuses Reminders styles (drag handle pattern, due chips). */
/* ── Person Projects widget (PR-WWW rebuild) ─────────────────
   Masonry layout, always-expanded stickers, drag-drop on projects
   (within + across people), inline comments, reminder integration.
   See dashboard/widgets/person-projects.js for behaviour notes. */
.dash-pp {
  display: flex; flex-direction: column; gap: 8px;
  height: 100%; min-width: 0; position: relative;
}
.dash-pp-head {
  display: flex; align-items: baseline; gap: 6px;
  flex-wrap: wrap; row-gap: 6px;
  font-size: 12px; color: var(--dash-text-dim);
  text-transform: uppercase; letter-spacing: .5px; font-weight: 600;
}
.dash-pp-cnt {
  font-family: 'SF Mono', monospace; font-size: 18px; font-weight: 700;
  color: var(--dash-blue); text-transform: none;
}
.dash-pp-add-person {
  margin-left: auto;
  background: var(--dash-blue-bg); color: var(--dash-blue);
  border: 1px solid rgba(37,99,235,.2);
  font: 600 11px var(--font, 'Inter');
  padding: 4px 10px; border-radius: 6px;
  cursor: pointer; transition: background .12s;
  text-transform: none;
}
.dash-pp-add-person:hover { background: rgba(37,99,235,.15); }

/* PR-redesign: view-mode toggle (📋 Kanban / 📑 Detail).
   Segmented button pair sitting in the head row. Active button gets
   a filled background; inactive is borderless transparent. */
.dash-pp-view-toggle {
  display: inline-flex;
  gap: 0;
  margin-left: 8px;
  border: 1px solid var(--dash-border);
  border-radius: 6px;
  overflow: hidden;
  background: var(--dash-surface);
}
.dash-pp-view-btn {
  background: transparent;
  border: 0;
  font: 600 11px var(--font, 'Inter');
  padding: 4px 9px;
  color: var(--dash-text-dim);
  cursor: pointer;
  text-transform: none;
  transition: background .12s, color .12s;
}
.dash-pp-view-btn:hover { background: rgba(0,0,0,.04); color: var(--dash-text); }
.dash-pp-view-btn.active {
  background: var(--dash-blue-bg);
  color: var(--dash-blue);
}
.dash-pp-view-btn + .dash-pp-view-btn {
  border-left: 1px solid var(--dash-border);
}

/* PR-redesign: Detail mode — split-pane layout. Left = compact list of
   all persons (clickable rows). Right = the full Kanban column for the
   currently selected person (uses the same .dash-pp-person markup,
   sized to fill the pane). One person on screen at a time. Designed
   for narrow widget tiles where horizontal Kanban scroll feels cramped. */
.dash-pp-detail-shell {
  display: flex;
  gap: 10px;
  flex: 1;
  min-height: 0;
}
.dash-pp-detail-list {
  flex: 0 0 220px;
  display: flex; flex-direction: column;
  gap: 4px;
  overflow-y: auto;
  padding-right: 4px;
  border-right: 1px solid var(--dash-border);
}
.dash-pp-detail-list-item {
  display: flex; align-items: center; gap: 8px;
  padding: 6px 8px;
  border-radius: 6px;
  cursor: pointer;
  border: 1px solid transparent;
  background: var(--dash-surface);
  transition: background .12s, border-color .12s;
}
.dash-pp-detail-list-item:hover { background: var(--dash-surface2); }
.dash-pp-detail-list-item.active {
  background: var(--dash-blue-bg);
  border-color: rgba(37,99,235,.3);
}
.dash-pp-detail-list-avatar {
  width: 24px; height: 24px;
  border-radius: 50%;
  background: linear-gradient(135deg, #818cf8 0%, #6366f1 100%);
  color: #fff;
  font: 700 10px var(--font, 'Inter');
  display: flex; align-items: center; justify-content: center;
  flex-shrink: 0;
}
.dash-pp-detail-list-name {
  flex: 1; min-width: 0;
  font-size: 12px; font-weight: 600;
  color: var(--dash-text);
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.dash-pp-detail-list-cnt {
  font-family: 'SF Mono', monospace; font-size: 10px;
  padding: 1px 6px; border-radius: 8px;
  background: rgba(37,99,235,.1); color: var(--dash-blue);
  font-weight: 600; flex-shrink: 0;
}
.dash-pp-detail-list-item.active .dash-pp-detail-list-cnt {
  background: rgba(255,255,255,.6);
}
.dash-pp-detail-list-color {
  width: 4px;
  align-self: stretch;
  border-radius: 2px;
  flex-shrink: 0;
}
.dash-pp-detail-pane {
  flex: 1; min-width: 0;
  display: flex; flex-direction: column;
  min-height: 0;
}
.dash-pp-detail-pane .dash-pp-person {
  /* In Detail mode the single visible person takes the full pane width
     (override the fixed 300px Kanban column width). */
  width: 100%; min-width: 0; max-width: 100%;
  max-height: 100%;
  flex-shrink: 0;
}
/* In Detail mode person-reorder DnD is intentionally disabled (only one
   person visible at a time — no other column to drop into), so the
   ⋮⋮ drag handle would be misleading. Hide it. */
.dash-pp-detail-pane .dash-pp-handle { display: none; }
.dash-pp-detail-empty {
  flex: 1;
  display: flex; align-items: center; justify-content: center;
  color: var(--dash-text-dim);
  font-size: 13px;
  background: var(--dash-surface);
  border: 1px dashed var(--dash-border);
  border-radius: 8px;
}

/* PR-redesign: Kanban-style layout. Each person becomes a column with
   horizontal scroll across the widget. Wider columns (280-320px) so
   project titles + multi-line notes are fully readable. Drag-drop
   handled by SortableJS (set up in person-projects.js); the CSS just
   provides the visual structure. */
.dash-pp-grid {
  display: flex;
  gap: 10px;
  overflow-x: auto;
  overflow-y: hidden;
  align-items: flex-start;
  flex: 1;
  min-height: 0;
  padding-bottom: 4px; /* breathing room for scrollbar */
  scroll-behavior: smooth;
}
.dash-pp-grid.single {
  /* single-person mode (PP widget configured for one specific person) */
  justify-content: flex-start;
}

/* Person sticker = Kanban column. Fixed minimum width so chips +
   multi-line text never get squeezed. Internal vertical scroll if a
   person has many projects. */
.dash-pp-person {
  display: flex; flex-direction: column;
  background: var(--dash-surface2);
  border: 1px solid var(--dash-border);
  border-radius: 10px;
  width: 300px;
  min-width: 300px;
  max-width: 300px;
  flex-shrink: 0;
  max-height: 100%;
  transition: box-shadow .15s, background .15s;
}
.dash-pp-grid.single .dash-pp-person {
  width: 100%; min-width: 0; max-width: 100%;
}
/* PR-redesign: SortableJS ghost (the placeholder card shown while
   dragging) — a faint dashed outline so the user sees the drop slot
   without visual noise. Applied automatically by Sortable.create. */
.dash-pp-person.sortable-ghost {
  opacity: 0.35;
  background: rgba(37,99,235,.06);
  border: 2px dashed var(--dash-blue) !important;
}
.dash-pp-person.sortable-drag {
  box-shadow: 0 8px 24px rgba(0,0,0,.18);
  cursor: grabbing;
}
.dash-pp-projects.sortable-drag-over {
  background: rgba(37,99,235,.05);
}
.dash-pp-person-head {
  display: flex; align-items: center; gap: 8px;
  padding: 8px 10px 6px;
  border-bottom: 1px solid var(--dash-border);
}
.dash-pp-avatar {
  flex-shrink: 0;
  width: 28px; height: 28px;
  border-radius: 50%;
  background: linear-gradient(135deg, #818cf8 0%, #6366f1 100%);
  color: #fff;
  font-size: 11px; font-weight: 700;
  display: flex; align-items: center; justify-content: center;
}
.dash-pp-person-meta {
  flex: 1; min-width: 0;
  display: flex; flex-direction: column; gap: 1px;
}
.dash-pp-person-name {
  font-size: 13px; font-weight: 600; color: var(--dash-text);
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.dash-pp-person-sub {
  font-size: 10px; color: var(--dash-text-dim);
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.dash-pp-person-cnt {
  font-family: 'SF Mono', monospace; font-size: 11px;
  padding: 2px 7px; border-radius: 10px;
  background: rgba(37,99,235,.1); color: var(--dash-blue);
  font-weight: 600; flex-shrink: 0;
}
.dash-pp-person-del {
  background: transparent; border: 0; cursor: pointer;
  color: var(--dash-text-dim); font-size: 12px;
  padding: 4px 8px; border-radius: 4px;
  opacity: 0; transition: opacity .15s, color .12s;
  flex-shrink: 0;
}
.dash-pp-person:hover .dash-pp-person-del { opacity: 0.7; }
.dash-pp-person-del:hover { color: var(--dash-red); opacity: 1; background: rgba(220,38,38,.08); }

/* PR-YYY: edit button beside delete + drag handle on the far left of
   the header (initiates person reorder). */
.dash-pp-person-edit {
  background: transparent; border: 0; cursor: pointer;
  font-size: 11px;
  padding: 4px 6px; border-radius: 4px;
  opacity: 0; transition: opacity .15s, background .12s;
  flex-shrink: 0;
}
.dash-pp-person:hover .dash-pp-person-edit { opacity: 0.7; }
.dash-pp-person-edit:hover { opacity: 1; background: rgba(0,0,0,.05); }

.dash-pp-handle {
  flex-shrink: 0;
  font-size: 12px; color: var(--dash-text-dim);
  cursor: grab;
  opacity: 0; transition: opacity .15s;
  line-height: 1; letter-spacing: -2px;
  user-select: none;
  padding: 2px 0;
}
.dash-pp-person:hover .dash-pp-handle { opacity: 0.6; }
.dash-pp-handle:active { cursor: grabbing; }

/* (Legacy HTML5 drag-drop CSS removed — SortableJS uses .sortable-ghost /
   .sortable-chosen / .sortable-drag now; see PR-redesign.) */

.dash-pp-person.has-color .dash-pp-person-head {
  border-bottom: 1px solid rgba(0,0,0,.08);
}

/* PR-AAA: footer color band — 5px strip below projects body, same hex
   as the header so the sticker is visually wrapped by colour. Rounded
   to match the sticker bottom corners (.dash-pp-person uses 8px radius). */
.dash-pp-person-footer {
  height: 5px;
  border-radius: 0 0 7px 7px;
  border-top: 1px solid rgba(0,0,0,.06);
}

/* PR-AAA: collapse toggle button + collapsed state. */
.dash-pp-person-toggle {
  background: transparent; border: 0; cursor: pointer;
  color: var(--dash-text-dim); font-size: 11px;
  padding: 2px 6px; border-radius: 4px;
  opacity: 0; transition: opacity .15s, background .12s;
  flex-shrink: 0;
  line-height: 1;
}
.dash-pp-person:hover .dash-pp-person-toggle { opacity: 0.7; }
.dash-pp-person-toggle:hover { opacity: 1; background: rgba(0,0,0,.05); }
/* When collapsed keep the toggle always visible — it's the only way back. */
.dash-pp-person.collapsed .dash-pp-person-toggle { opacity: 0.85; }

.dash-pp-person.collapsed .dash-pp-projects { display: none; }
/* In collapsed state the head loses its bottom border (projects body
   that used to anchor it is hidden), so the footer slides up against
   the head directly. Hairline border removed for cleaner edge. */
.dash-pp-person.collapsed.has-color .dash-pp-person-footer {
  border-top: 0;
}

/* Color picker — palette of selectable swatches */
.dash-pp-color-section {
  border-top: 1px solid var(--dash-border);
  margin-top: 10px;
  padding-top: 10px;
}
.dash-pp-color-label {
  font-size: 11px; font-weight: 600;
  color: var(--dash-text-dim);
  text-transform: uppercase; letter-spacing: 0.3px;
  margin-bottom: 6px;
}
.dash-pp-swatches {
  display: flex; flex-wrap: wrap; gap: 6px;
}
.dash-pp-swatch {
  width: 28px; height: 28px;
  border-radius: 50%;
  border: 2px solid var(--dash-border);
  cursor: pointer;
  transition: transform .12s, border-color .12s, box-shadow .12s;
  background: var(--dash-surface);
  padding: 0;
}
.dash-pp-swatch:hover {
  transform: scale(1.1);
  border-color: var(--dash-text-dim);
}
.dash-pp-swatch[data-selected="1"] {
  border-color: var(--dash-blue);
  box-shadow: 0 0 0 2px rgba(37,99,235,.2);
}
.dash-pp-swatch.is-none {
  position: relative;
  background: var(--dash-surface);
}
.dash-pp-swatch.is-none::after {
  content: '';
  position: absolute;
  top: 50%; left: 10%; right: 10%;
  height: 2px; background: var(--dash-red);
  transform: translateY(-50%) rotate(-45deg);
}

/* Person editor modal — rename + email + color */
.dash-pp-editor {
  display: flex; flex-direction: column; gap: 10px;
  padding: 4px 0;
}
.dash-pp-editor-field {
  display: flex; flex-direction: column; gap: 3px;
}
.dash-pp-editor-field > span {
  font-size: 11px; font-weight: 600;
  color: var(--dash-text-dim);
  text-transform: uppercase; letter-spacing: 0.3px;
}
.dash-pp-editor-field input {
  font: 13px var(--font, 'Inter');
  padding: 7px 10px;
  border: 1px solid var(--dash-border);
  border-radius: 5px;
  background: var(--dash-surface);
}
.dash-pp-editor-field input:focus {
  outline: 2px solid var(--dash-blue);
  outline-offset: -1px;
  border-color: transparent;
}
.dash-pp-editor-actions {
  display: flex; justify-content: flex-end; gap: 6px;
  padding-top: 6px;
  border-top: 1px solid var(--dash-border);
}
.dash-pp-editor-save {
  background: var(--dash-blue); color: #fff;
  border: 0; border-radius: 6px;
  font: 600 12px var(--font, 'Inter');
  padding: 8px 16px;
  cursor: pointer;
}
.dash-pp-editor-save:hover { background: #1d4fd4; }
.dash-pp-editor-cancel {
  background: var(--dash-surface2); color: var(--dash-text-dim);
  border: 0; border-radius: 6px;
  font: 600 12px var(--font, 'Inter');
  padding: 8px 16px;
  cursor: pointer;
}
.dash-pp-editor-cancel:hover { background: #e2e5ea; }

/* Projects body — vertical flex column with internal scroll so a
   person with many projects gets a scrollable list inside the Kanban
   column instead of forcing the whole widget taller. */
.dash-pp-projects {
  display: flex; flex-direction: column; gap: 4px;
  padding: 6px 8px 8px;
  min-height: 60px; /* drop zone visible even when empty */
  flex: 1;
  overflow-y: auto;
  overflow-x: hidden;
}
.dash-pp-project {
  border-radius: 6px;
  background: var(--dash-surface);
  font-size: 12px;
  border: 1px solid var(--dash-border);
  cursor: grab;
  transition: background .15s, opacity .15s, box-shadow .15s;
}
.dash-pp-project:hover { background: #f0f3f8; }
/* PR-redesign: SortableJS ghost/drag styles for project cards. */
.dash-pp-project.sortable-ghost {
  opacity: 0.35;
  background: rgba(37,99,235,.08);
  border: 1px dashed var(--dash-blue);
}
.dash-pp-project.sortable-drag {
  cursor: grabbing;
  box-shadow: 0 4px 12px rgba(0,0,0,.15);
}
.dash-pp-project.has-comments-open { background: rgba(37,99,235,.04); }

.dash-pp-project-row {
  display: flex; align-items: center; gap: 4px;
  padding: 5px 7px;
}
.dash-pp-status {
  font-size: 9px; padding: 2px 5px; border-radius: 8px;
  font-weight: 700; flex-shrink: 0;
  cursor: pointer; user-select: none;
  text-transform: uppercase; letter-spacing: 0.3px;
}
.dash-pp-status-active  { background: rgba(34,197,94,.18); color: #166534; }
.dash-pp-status-pending { background: rgba(234,179,8,.18); color: #854d0e; }
.dash-pp-status-done    { background: rgba(148,163,184,.18); color: #475569; }
.dash-pp-project-main { flex: 1; min-width: 0; display: flex; flex-direction: column; gap: 1px; }
.dash-pp-title {
  font-weight: 500;
  font-size: 12.5px;
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
  cursor: text;
}
.dash-pp-title-input {
  width: 100%; box-sizing: border-box;
  font: 12px var(--font, 'Inter');
  border: 0; outline: 2px solid var(--dash-blue);
  outline-offset: -2px;
  background: var(--dash-surface);
  padding: 2px 4px; border-radius: 3px;
}
.dash-pp-note {
  font-size: 10px; color: var(--dash-text-dim);
  /* PR-OOO: 2-line clamp so the inline preview reads as a teaser
     without crowding the row. Full text in the 📝 editor panel. */
  display: -webkit-box;
  -webkit-line-clamp: 2;
  -webkit-box-orient: vertical;
  overflow: hidden;
  word-wrap: break-word;
  line-height: 1.3;
}
.dash-pp-due {
  font-size: 10px; padding: 2px 7px; border-radius: 10px;
  background: var(--dash-surface2); color: var(--dash-text-dim);
  font-weight: 500; white-space: nowrap; flex-shrink: 0;
}
.dash-pp-due.soon     { background: rgba(37,99,235,.1); color: var(--dash-blue); }
.dash-pp-due.overdue  { background: rgba(220,38,38,.12); color: var(--dash-red); font-weight: 700; }

/* Compact icon buttons: 💬 / ⏰ / 📝 / ✕
   PR-readability: in idle state ONLY count-bearing buttons (📝 with note,
   💬 with comments) are visible — the rest (⏰, ✕, empty 📝/💬) collapse
   to display:none so the title gets ~150px of breathing room instead of
   ~50px. On row hover all buttons appear (layout shift on the right side
   is acceptable because the cursor is already there targeting the action). */
.dash-pp-btn {
  background: transparent; border: 0; cursor: pointer;
  color: var(--dash-text-dim); font-size: 10px;
  padding: 1px 4px; border-radius: 4px;
  transition: background .15s, color .12s;
  flex-shrink: 0;
  font-family: var(--font, 'Inter');
  line-height: 1.2;
  /* Default: hidden until hover. has-count buttons override below. */
  display: none;
}
.dash-pp-project:hover .dash-pp-btn { display: inline-block; }
.dash-pp-btn:hover { background: rgba(0,0,0,.05); }
.dash-pp-btn.has-count {
  display: inline-block;
  color: var(--dash-blue); font-weight: 600;
}
.dash-pp-btn-del:hover { background: rgba(220,38,38,.1); color: var(--dash-red); }
.dash-pp-btn-remind:hover { background: rgba(234,179,8,.12); color: #854d0e; }
.dash-pp-btn-note:hover { background: rgba(34,197,94,.12); color: #166534; }
.dash-pp-btn-note.has-count { color: #166534; }

/* PR-PPP: priority on projects — same palette as Reminders so the
   urgency cue is consistent across the dashboard.
     P1 = red    (urgent)
     P2 = orange (important)
     P3 = gray   (someday)
   Visual: left stripe + tinted background on the row, coloured chip
   button (P1/P2/P3) that cycles on click. */
.dash-pp-pri-btn {
  background: transparent;
  border: 1px solid var(--dash-border);
  color: var(--dash-text-dim);
  font: 700 9px 'SF Mono', monospace;
  padding: 1px 4px;
  border-radius: 4px;
  cursor: pointer;
  transition: background .12s, color .12s, border-color .12s;
  flex-shrink: 0;
  line-height: 1.2;
  /* PR-readability: empty-priority chip (P–) hidden until hover.
     Priority chips with pri-1/2/3 override below to stay visible. */
  display: none;
}
.dash-pp-project:hover .dash-pp-pri-btn { display: inline-block; }
.dash-pp-pri-btn:hover { background: rgba(0,0,0,.05); }
.dash-pp-pri-btn.pri-1 { display: inline-block; background: rgba(239,68,68,.18);  border-color: rgba(239,68,68,.5);  color: #991b1b; }
.dash-pp-pri-btn.pri-2 { display: inline-block; background: rgba(234,179,8,.18);  border-color: rgba(234,179,8,.5);  color: #854d0e; }
.dash-pp-pri-btn.pri-3 { display: inline-block; background: rgba(148,163,184,.2); border-color: rgba(148,163,184,.5); color: #475569; }

/* Row tint + left stripe by priority — only when priority is set so
   un-prioritized projects keep the existing neutral look. */
.dash-pp-project.pri-1 { background: rgba(239,68,68,.10);  border-left: 4px solid #ef4444; }
.dash-pp-project.pri-1:hover { background: rgba(239,68,68,.18); }
.dash-pp-project.pri-2 { background: rgba(234,179,8,.10);  border-left: 4px solid #eab308; }
.dash-pp-project.pri-2:hover { background: rgba(234,179,8,.18); }
.dash-pp-project.pri-3 { background: rgba(148,163,184,.08); border-left: 4px solid #94a3b8; }
.dash-pp-project.pri-3:hover { background: rgba(148,163,184,.16); }

/* PR-popover: floating detail panel shown on hover (with 350ms delay) over
   a project row. Trello-style preview — full title (no clamp), full note
   (preserve newlines), all chips (status / priority / due), comments count.
   Attached to <body> with position:fixed so it can escape the Kanban
   column's overflow-hidden + scroll, and z-index above gridstack chrome.
   Mouseenter the popover itself keeps it open. */
.dash-pp-detail-popover {
  position: fixed;
  background: #fff;
  border: 1px solid var(--dash-border);
  border-radius: 8px;
  box-shadow: 0 8px 24px rgba(0,0,0,.18), 0 2px 6px rgba(0,0,0,.08);
  padding: 12px 14px;
  width: 340px;
  max-width: calc(100vw - 24px);
  z-index: 9999;
  font-family: var(--font, 'Inter');
  color: var(--dash-text);
  /* Soft fade-in so the popover doesn't snap on hover. */
  animation: dash-pp-pop-fade .12s ease-out;
}
@keyframes dash-pp-pop-fade {
  from { opacity: 0; transform: translateY(-2px); }
  to   { opacity: 1; transform: translateY(0); }
}
.dash-pp-detail-popover-title {
  font-size: 14px; font-weight: 600;
  color: var(--dash-text);
  line-height: 1.35;
  margin: 0 0 8px;
  /* Allow wrapping — the whole point is to show the full title that the
     row had to truncate. */
  word-wrap: break-word; overflow-wrap: anywhere;
}
.dash-pp-detail-popover-meta {
  display: flex; flex-wrap: wrap; gap: 6px;
  margin-bottom: 8px;
}
.dash-pp-detail-popover-meta:empty { display: none; }
.dash-pp-detail-popover-note {
  font-size: 12px;
  line-height: 1.5;
  color: var(--dash-text);
  background: var(--dash-surface2);
  border-radius: 6px;
  padding: 8px 10px;
  margin-bottom: 8px;
  /* preserve newlines from the source text (engine renders with \n→<br>) */
  white-space: pre-wrap;
  word-wrap: break-word;
  /* Cap height so a 2000-char note doesn't blow up the screen — scroll
     inside the popover instead. */
  max-height: 240px;
  overflow-y: auto;
}
.dash-pp-detail-popover-empty {
  font-size: 12px;
  color: var(--dash-text-dim);
  font-style: italic;
  margin-bottom: 8px;
}
.dash-pp-detail-popover-stats {
  display: flex; flex-wrap: wrap; gap: 10px;
  font-size: 11px;
  color: var(--dash-text-dim);
  padding-top: 8px;
  border-top: 1px solid var(--dash-border);
}
.dash-pp-detail-popover-stats span { white-space: nowrap; }
.dash-pp-detail-popover-hint {
  font-size: 10px;
  color: var(--dash-text-dim);
  margin-top: 6px;
  font-style: italic;
}

/* Priority chips in the "Add project" inline form. Mirror the row-stripe
   palette so the picker matches what lands in the list. */
.dash-pp-form-pri-group {
  display: inline-flex;
  gap: 4px;
  align-items: center;
}
.dash-pp-form-pri-chip {
  background: transparent;
  border: 1px solid var(--dash-border);
  color: var(--dash-text-dim);
  font: 600 10px var(--font, 'Inter');
  padding: 4px 8px;
  border-radius: 4px;
  cursor: pointer;
  transition: background .12s, color .12s, border-color .12s;
}
.dash-pp-form-pri-chip:hover { color: var(--dash-text); }
.dash-pp-form-pri-chip.pri-1.active { background: rgba(239,68,68,.18); border-color: rgba(239,68,68,.5); color: #991b1b; }
.dash-pp-form-pri-chip.pri-2.active { background: rgba(234,179,8,.18); border-color: rgba(234,179,8,.5); color: #854d0e; }
.dash-pp-form-pri-chip.pri-3.active { background: rgba(148,163,184,.2); border-color: rgba(148,163,184,.5); color: #475569; }

/* PR-OOO: full-note editor panel — multi-line textarea inline under
   the project row. Same dashed-border treatment as comments + reminder
   popover so it visually reads as "expanded inline content". */
.dash-pp-note-editor {
  border-top: 1px dashed var(--dash-border);
  padding: 6px 8px 8px;
  background: rgba(34,197,94,.03);
  display: flex; flex-direction: column; gap: 6px;
}
.dash-pp-note-input {
  width: 100%; box-sizing: border-box;
  font: 12px var(--font, 'Inter');
  padding: 6px 8px;
  border: 1px solid var(--dash-border);
  border-radius: 5px;
  background: var(--dash-surface);
  resize: vertical;
  min-height: 60px;
  max-height: 280px;
  line-height: 1.4;
  white-space: pre-wrap;
  word-wrap: break-word;
}
.dash-pp-note-input:focus {
  outline: 2px solid #22c55e;
  outline-offset: -1px;
  border-color: transparent;
}
.dash-pp-note-actions {
  display: flex; gap: 4px; justify-content: flex-end;
}
.dash-pp-note-save {
  background: #22c55e; color: #fff;
  border: 0; border-radius: 4px;
  font: 600 11px var(--font, 'Inter');
  padding: 5px 12px; cursor: pointer;
}
.dash-pp-note-save:hover { background: #16a34a; }
.dash-pp-note-cancel {
  background: var(--dash-surface2); color: var(--dash-text-dim);
  border: 0; border-radius: 4px;
  font: 600 11px var(--font, 'Inter');
  padding: 5px 12px; cursor: pointer;
}
.dash-pp-note-cancel:hover { background: #e2e5ea; }
.dash-pp-project.has-note-open { background: rgba(34,197,94,.04); }
/* When the editor is open, the inline preview line becomes redundant —
   hide it so the textarea is the single source of truth visually. */
.dash-pp-project.has-note-open .dash-pp-note { display: none; }

/* PR-pri-picker: floating priority selector popover. Opens on click of
   the row's priority chip — 4 buttons in a row (P1 / P2 / P3 / None)
   so user can pick directly instead of cycling through values. Attached
   to <body> with position:fixed (escape Kanban column overflow). */
.dash-pp-pri-picker {
  position: fixed;
  background: #fff;
  border: 1px solid var(--dash-border);
  border-radius: 6px;
  box-shadow: 0 6px 20px rgba(0,0,0,.16), 0 2px 4px rgba(0,0,0,.06);
  padding: 4px;
  display: inline-flex;
  gap: 3px;
  z-index: 9999;
  animation: dash-pp-pop-fade .1s ease-out;
}
.dash-pp-pri-pick {
  background: transparent;
  border: 1px solid var(--dash-border);
  font: 700 11px 'SF Mono', monospace;
  padding: 4px 9px;
  border-radius: 4px;
  cursor: pointer;
  transition: background .12s, color .12s, border-color .12s, transform .08s;
  line-height: 1;
  color: var(--dash-text-dim);
}
.dash-pp-pri-pick:hover { transform: translateY(-1px); }
.dash-pp-pri-pick.pri-1 { background: rgba(239,68,68,.18);  border-color: rgba(239,68,68,.5);  color: #991b1b; }
.dash-pp-pri-pick.pri-2 { background: rgba(234,179,8,.18);  border-color: rgba(234,179,8,.5);  color: #854d0e; }
.dash-pp-pri-pick.pri-3 { background: rgba(148,163,184,.2); border-color: rgba(148,163,184,.5); color: #475569; }
.dash-pp-pri-pick.is-none {
  font-family: var(--font, 'Inter');
  font-weight: 600;
  font-size: 10px;
  letter-spacing: 0.3px;
}
.dash-pp-pri-pick.is-current {
  box-shadow: inset 0 0 0 2px var(--dash-blue);
}

/* Reminder popover — appears below project row */
.dash-pp-reminder-pop {
  position: absolute;
  background: var(--dash-surface);
  border: 1px solid var(--dash-border);
  border-radius: 8px;
  box-shadow: 0 6px 24px rgba(0,0,0,.15);
  padding: 10px;
  z-index: 50;
  margin-top: 4px;
  min-width: 220px;
  right: 8px;
}
.dash-pp-reminder-pop-head {
  font: 600 11px var(--font, 'Inter');
  color: var(--dash-text);
  margin-bottom: 6px;
}
.dash-pp-reminder-when {
  width: 100%; box-sizing: border-box;
  font: 12px var(--font, 'Inter');
  padding: 5px 7px;
  border: 1px solid var(--dash-border);
  border-radius: 4px;
  background: var(--dash-surface);
  margin-bottom: 8px;
}
.dash-pp-reminder-actions {
  display: flex; gap: 4px; justify-content: flex-end;
}
.dash-pp-reminder-save,
.dash-pp-reminder-cancel {
  font: 600 11px var(--font, 'Inter');
  border: 0; border-radius: 4px;
  padding: 5px 12px;
  cursor: pointer;
}
.dash-pp-reminder-save { background: var(--dash-blue); color: #fff; }
.dash-pp-reminder-save:hover { background: #1d4fd4; }
.dash-pp-reminder-cancel { background: var(--dash-surface2); color: var(--dash-text-dim); }
.dash-pp-reminder-cancel:hover { background: #e2e5ea; }

/* "+ Add project" button */
.dash-pp-add-project {
  font: 600 11px var(--font, 'Inter');
  background: transparent; color: var(--dash-blue);
  border: 1px dashed rgba(37,99,235,.4);
  padding: 4px 10px; border-radius: 6px;
  cursor: pointer; transition: background .12s;
  margin-top: 2px;
  align-self: flex-start;
}
.dash-pp-add-project:hover { background: var(--dash-blue-bg); }

/* Inline "add project" form — stacks now since stickers can be narrow */
.dash-pp-form {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 5px;
  padding: 6px 8px;
  border-radius: 6px;
  background: rgba(37,99,235,.05);
  border: 1px solid rgba(37,99,235,.2);
  margin-top: 2px;
}
.dash-pp-form-title { grid-column: 1 / -1; }
.dash-pp-form-note  { grid-column: 1 / -1; }
/* PR-PPP: priority chips span both columns inside the grid form. */
.dash-pp-form-pri-group { grid-column: 1 / -1; }
.dash-pp-form input,
.dash-pp-form select {
  font: 12px var(--font, 'Inter');
  border: 1px solid var(--dash-border);
  background: var(--dash-surface);
  border-radius: 4px;
  padding: 4px 6px;
  min-width: 0;
}
.dash-pp-form-save,
.dash-pp-form-cancel {
  font: 600 11px var(--font, 'Inter');
  border: 0; border-radius: 4px;
  padding: 4px 10px;
  cursor: pointer;
}
.dash-pp-form-save { background: var(--dash-blue); color: #fff; }
.dash-pp-form-save:hover { background: #1d4fd4; }
.dash-pp-form-cancel { background: var(--dash-surface2); color: var(--dash-text-dim); }
.dash-pp-form-cancel:hover { background: #e2e5ea; }

/* Toast (limit warnings, errors) */
.dash-pp-toast {
  position: absolute;
  bottom: 8px; left: 50%;
  transform: translateX(-50%);
  background: var(--dash-text);
  color: #fff;
  font: 500 11px var(--font, 'Inter');
  padding: 6px 12px;
  border-radius: 6px;
  box-shadow: 0 4px 12px rgba(0,0,0,.2);
  z-index: 60;
  white-space: nowrap;
  max-width: 90%;
  text-overflow: ellipsis;
  overflow: hidden;
  animation: dash-pp-toast-in .2s ease-out;
}
.dash-pp-toast.warn { background: #b45309; }
.dash-pp-toast.info { background: var(--dash-blue); }
@keyframes dash-pp-toast-in {
  from { opacity: 0; transform: translate(-50%, 8px); }
  to   { opacity: 1; transform: translate(-50%, 0); }
}

/* Person picker overlay (Teammate tab + Custom tab) */
.dash-pp-picker-tabs {
  display: flex; gap: 4px;
  border-bottom: 1px solid var(--dash-border);
  margin: 8px 0;
}
.dash-pp-picker-tab {
  background: transparent; border: 0; cursor: pointer;
  font: 600 12px var(--font, 'Inter');
  color: var(--dash-text-dim);
  padding: 6px 12px;
  border-bottom: 2px solid transparent;
  margin-bottom: -1px;
}
.dash-pp-picker-tab.active {
  color: var(--dash-blue);
  border-bottom-color: var(--dash-blue);
}
.dash-pp-picker-search,
.dash-pp-picker-name,
.dash-pp-picker-email {
  width: 100%; box-sizing: border-box;
  font: 13px var(--font, 'Inter');
  padding: 7px 10px; border-radius: 6px;
  border: 1px solid var(--dash-border);
  background: var(--dash-surface);
  margin-bottom: 6px;
}
.dash-pp-picker-list {
  max-height: 320px;
  overflow-y: auto;
  display: flex; flex-direction: column; gap: 3px;
}
.dash-pp-picker-item {
  display: flex; align-items: center; gap: 10px;
  padding: 6px 10px;
  border-radius: 6px;
  cursor: pointer;
  border: 1px solid transparent;
}
.dash-pp-picker-item:hover { background: var(--dash-blue-bg); border-color: rgba(37,99,235,.2); }
.dash-pp-picker-avatar {
  width: 28px; height: 28px;
  border-radius: 50%;
  background: linear-gradient(135deg, #818cf8 0%, #6366f1 100%);
  color: #fff;
  font-size: 11px; font-weight: 700;
  display: flex; align-items: center; justify-content: center;
  flex-shrink: 0;
}
.dash-pp-picker-meta { min-width: 0; flex: 1; }
.dash-pp-picker-name-row {
  font-size: 13px; font-weight: 600;
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.dash-pp-picker-email-row {
  font-size: 11px; color: var(--dash-text-dim);
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.dash-pp-picker-save {
  background: var(--dash-blue); color: #fff;
  border: 0; border-radius: 6px;
  padding: 8px 16px;
  font: 600 13px var(--font, 'Inter');
  cursor: pointer;
}
.dash-pp-picker-save:hover { background: #1d4fd4; }

/* ── ClickUp Tasks widget (PR-JJJ rewrite) ─────────────────
   Designed to mirror ClickUp's own visual style. List + Kanban views,
   add/delete tasks, inline status, lightbox with checklists + comments,
   colored assignee avatars. */
/* PR-UUU: widget body becomes a non-scrolling flex column. Sticky bar
   is the FIRST flex child (fixed height, flex-shrink:0). The task list
   is the SECOND child with overflow:auto — scrolls independently.
   Result: scrollbar appears ONLY along the task list edge, not next to
   the sticky head/filters (user reported scroll visually extending
   through the header in PR-TTT). */
.dash-widget-body:has(> .dash-clickup-sticky) {
  padding: 0;
  overflow: hidden;
  display: flex;
  flex-direction: column;
}
.dash-clickup-sticky {
  flex-shrink: 0;
  background: var(--dash-surface);
  padding: 6px 12px 0;
  border-bottom: 1px solid var(--dash-border);
  z-index: 2;
}
.dash-clickup-body {
  flex: 1;
  min-height: 0; /* allow shrinking inside flex parent so overflow works */
  overflow: auto;
  padding: 4px 12px 12px;
}
.dash-clickup-head {
  display: flex; align-items: center; gap: 6px;
  padding: 0 0 5px;
  border-bottom: 1px solid var(--dash-border);
  margin-bottom: 5px;
}
/* PR-VVV: brand pill sits at the far left of the head so the widget
   identifies itself even with `compact: true` hiding the dashboard's
   default widget header. ClickUp purple (#7B68EE) used for the label
   to match the gradient in the SVG glyph. */
.dash-clickup-brand {
  display: inline-flex; align-items: center; gap: 4px;
  padding: 0 2px 0 0;
  font-weight: 700; font-size: 12px;
  color: #7B68EE; letter-spacing: -0.1px;
  user-select: none;
}
.dash-clickup-brand-icon { flex: none; }
.dash-clickup-brand-label { line-height: 1; }
.dash-clickup-cnt {
  font-weight: 600; font-size: 12px; color: var(--dash-text);
}
.dash-clickup-team {
  font-size: 11px; color: var(--dash-text-dim);
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
  max-width: 180px;
}
.dash-clickup-view-toggle {
  display: inline-flex; margin-left: auto;
  background: var(--dash-surface2);
  border-radius: 6px;
  padding: 2px;
  gap: 2px;
}
.dash-clickup-view-btn {
  background: transparent; border: 0;
  padding: 3px 8px; border-radius: 4px;
  font-size: 13px; cursor: pointer;
  color: var(--dash-text-dim);
}
.dash-clickup-view-btn.active {
  background: var(--dash-surface);
  color: var(--dash-blue);
  box-shadow: 0 1px 2px rgba(0,0,0,.08);
}
/* PR-QQQ: Me ↔ All mode toggle. Same pill shape as the view toggle.
   Margin-left auto moved here so this pair pushes everything else right
   (view + add + refresh + disconnect) when both toggles exist. */
.dash-clickup-mode-toggle {
  display: inline-flex; margin-left: auto;
  background: var(--dash-surface2);
  border-radius: 6px;
  padding: 2px;
  gap: 2px;
}
.dash-clickup-view-toggle {
  margin-left: 0; /* the mode toggle now owns the right-push */
}
.dash-clickup-mode-btn {
  background: transparent; border: 0;
  padding: 3px 9px; border-radius: 4px;
  font-size: 11px; font-weight: 600; cursor: pointer;
  color: var(--dash-text-dim);
  white-space: nowrap;
}
.dash-clickup-mode-btn.active {
  background: var(--dash-surface);
  color: var(--dash-blue);
  box-shadow: 0 1px 2px rgba(0,0,0,.08);
}
.dash-clickup-refresh, .dash-clickup-disconnect, .dash-clickup-add {
  flex-shrink: 0;
}
.dash-clickup-add {
  color: var(--dash-blue);
  font-weight: 700;
}
.dash-clickup-truncated {
  background: rgba(234, 179, 8, .14);
  color: #854d0e;
  font-size: 11px; font-weight: 600;
  padding: 4px 8px;
  border-radius: 6px;
  margin-bottom: 6px;
  text-align: center;
}

/* PR-UUU: compact filter bar. Smaller controls, tighter spacing, single
   row at default widget size (8 cols ≈ 640px). Status-type uses a
   segmented control instead of a 3-option dropdown — saves height +
   makes the active state visible at a glance. */
.dash-clickup-filters {
  display: flex; flex-wrap: wrap; gap: 5px;
  padding: 0 0 6px;
  border-bottom: 1px solid var(--dash-border);
  margin-bottom: 5px;
  align-items: center;
}
.dash-clickup-search {
  flex: 1; min-width: 110px;
  padding: 4px 8px;
  border: 1px solid var(--dash-border);
  border-radius: 5px;
  font-size: 11px; height: 24px;
  background: var(--dash-surface);
  color: var(--dash-text);
}
.dash-clickup-search:focus { outline: none; border-color: var(--dash-blue); }
.dash-clickup-select {
  padding: 3px 4px;
  border: 1px solid var(--dash-border);
  border-radius: 5px;
  font-size: 11px; height: 24px;
  background: var(--dash-surface);
  color: var(--dash-text);
  cursor: pointer;
  max-width: 130px;
}
.dash-clickup-select:focus { outline: none; border-color: var(--dash-blue); }

/* Status-type segmented control (replaces the 3-option <select>).
   3 small inline pills with active state highlighted. */
.dash-clickup-statustype {
  display: inline-flex;
  background: var(--dash-surface2);
  border-radius: 5px;
  padding: 2px;
  gap: 1px;
  height: 24px;
  flex-shrink: 0;
}
.dash-clickup-statustype-btn {
  background: transparent; border: 0;
  padding: 0 8px; border-radius: 3px;
  font-size: 10px; font-weight: 600; cursor: pointer;
  color: var(--dash-text-dim);
  text-transform: uppercase; letter-spacing: .3px;
}
.dash-clickup-statustype-btn.active {
  background: var(--dash-surface);
  color: var(--dash-blue);
  box-shadow: 0 1px 2px rgba(0,0,0,.08);
}

/* ─ List view ─ */
.dash-clickup-list {
  display: flex; flex-direction: column; gap: 4px;
}
/* PR-TTT: task rows + column header use the SAME CSS grid template so
   columns line up across all rows like a table. Cell widths sized to
   fit typical content: status ~110px, priority icon ~28px, due chip
   ~90px, 3-avatar stack ~80px, action icons ~28-30px.
   Title column is `minmax(0, 1fr)` so it grows but can also shrink
   below content-width (truncation kicks in instead of overflow). */
.dash-clickup-col-header,
.dash-clickup-task {
  display: grid;
  grid-template-columns: minmax(0, 1fr) 110px 28px 88px 80px 30px 28px;
  gap: 8px;
  align-items: center;
}
.dash-clickup-col-header {
  padding: 6px 10px;
  font-size: 9px; font-weight: 700;
  color: var(--dash-text-dim);
  text-transform: uppercase; letter-spacing: .4px;
  border-bottom: 1px solid var(--dash-border);
}
.dash-clickup-col-header > div {
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.dash-clickup-cell {
  display: flex; align-items: center;
  min-width: 0;
}
.dash-clickup-cell-center {
  justify-content: center;
}
/* Task row — left-aligned content, generous hover area, subtle hover
   background, action buttons on the right. */
.dash-clickup-task {
  padding: 8px 10px;
  border-radius: 6px;
  background: var(--dash-surface);
  border: 1px solid var(--dash-border);
  cursor: pointer;
  text-align: left;
  text-decoration: none;
  color: var(--dash-text);
  transition: background .12s, border-color .12s, box-shadow .12s;
}
.dash-clickup-task:hover {
  background: var(--dash-surface2);
  border-color: var(--dash-blue);
  box-shadow: 0 1px 4px rgba(0,0,0,.05);
}
.dash-clickup-task:focus {
  outline: none;
  border-color: var(--dash-blue);
  box-shadow: 0 0 0 2px rgba(37,99,235,.15);
}
.dash-clickup-task-main {
  flex: 1; min-width: 0;
  display: flex; flex-direction: column; gap: 2px;
  text-align: left;
}
.dash-clickup-task-title {
  font-size: 13px; font-weight: 500;
  color: var(--dash-text);
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.dash-clickup-task-sub {
  display: flex; align-items: center; gap: 6px; flex-wrap: wrap;
  min-width: 0;
}
.dash-clickup-path {
  font-size: 10px;
  color: var(--dash-text-dim);
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
  max-width: 220px;
}
.dash-clickup-tag {
  font-size: 9px; font-weight: 600;
  padding: 1px 6px;
  border-radius: 8px;
  white-space: nowrap;
}
/* Priority flag — ClickUp uses a flag icon (▲) colored by priority. */
.dash-clickup-prio-flag {
  flex-shrink: 0;
  font-size: 11px;
  line-height: 1;
  font-weight: 700;
}
.dash-clickup-prio-flag.is-p1 { color: #e74c3c; }
.dash-clickup-prio-flag.is-p2 { color: #f1c40f; }
.dash-clickup-prio-flag.is-p3 { color: #3498db; }
.dash-clickup-prio-flag.is-p4 { color: #95a5a6; }

/* Status badge — ClickUp style: colored dot + uppercase text. */
.dash-clickup-status-badge {
  display: inline-flex; align-items: center; gap: 4px;
  flex-shrink: 0;
  padding: 3px 8px;
  border-radius: 12px;
  background: var(--dash-surface2);
  font-size: 9px; font-weight: 700;
  letter-spacing: .4px;
}
.dash-clickup-status-dot {
  display: inline-block;
  width: 8px; height: 8px;
  border-radius: 50%;
  flex-shrink: 0;
}
.dash-clickup-status-text {
  color: var(--dash-text);
  white-space: nowrap;
}

/* Due chip */
.dash-clickup-due {
  flex-shrink: 0;
  font-size: 10px;
  padding: 3px 7px;
  border-radius: 8px;
  background: var(--dash-surface2);
  color: var(--dash-text-dim);
  font-weight: 600;
  white-space: nowrap;
}
.dash-clickup-due.is-overdue { background: rgba(220, 38, 38, .14); color: #dc2626; }
.dash-clickup-due.is-today   { background: rgba(217, 119, 6, .14); color: #d97706; }
.dash-clickup-due.is-week    { background: rgba(37, 99, 235, .12); color: var(--dash-blue); }
.dash-clickup-due.is-none    { display: none; }

/* Avatar */
.dash-clickup-avatars { display: inline-flex; flex-shrink: 0; }
.dash-clickup-avatars .dash-clickup-avatar:not(:first-child) { margin-left: -6px; }
.dash-clickup-avatar {
  display: inline-flex; align-items: center; justify-content: center;
  border-radius: 50%;
  color: #fff; font-weight: 700;
  border: 2px solid var(--dash-surface);
  flex-shrink: 0;
  text-transform: uppercase;
  line-height: 1;
}

/* External + delete */
.dash-clickup-ext-link {
  flex-shrink: 0;
  color: var(--dash-text-dim);
  text-decoration: none;
  font-size: 13px;
  padding: 2px 4px;
  border-radius: 4px;
}
.dash-clickup-ext-link:hover {
  background: var(--dash-blue-bg);
  color: var(--dash-blue);
}
.dash-clickup-row-del {
  flex-shrink: 0;
  background: transparent;
  border: 0;
  color: var(--dash-text-dim);
  font-size: 12px;
  width: 22px; height: 22px;
  border-radius: 4px;
  cursor: pointer;
  opacity: 0;
  transition: opacity .12s, background .12s, color .12s;
}
.dash-clickup-task:hover .dash-clickup-row-del { opacity: 1; }
.dash-clickup-row-del:hover {
  background: rgba(220, 38, 38, .12);
  color: var(--dash-red);
}

.dash-clickup-empty {
  display: flex; flex-direction: column; align-items: center; gap: 8px;
  padding: 30px 12px;
  text-align: center;
  font-size: 13px; color: var(--dash-text-dim);
}
.dash-clickup-empty > div:first-child { font-size: 26px; }

/* ─ Kanban view ─ */
.dash-clickup-kanban {
  display: flex; gap: 10px;
  overflow-x: auto;
  padding-bottom: 8px;
}
.dash-clickup-kanban-col {
  flex: 0 0 220px;
  display: flex; flex-direction: column; gap: 6px;
  background: var(--dash-surface2);
  border-radius: 8px;
  padding: 8px;
  max-height: 100%;
}
.dash-clickup-kanban-head {
  display: flex; align-items: center; gap: 6px;
  font-size: 11px; font-weight: 700;
  text-transform: uppercase; letter-spacing: .3px;
  color: var(--dash-text);
  padding: 0 2px 4px;
  border-bottom: 1px solid var(--dash-border);
}
.dash-clickup-kanban-name { flex: 1; min-width: 0; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.dash-clickup-kanban-cnt {
  background: var(--dash-surface);
  color: var(--dash-text-dim);
  padding: 1px 6px;
  border-radius: 8px;
  font-size: 10px;
  font-family: 'SF Mono', monospace;
}
.dash-clickup-kanban-cards {
  display: flex; flex-direction: column; gap: 6px;
  overflow-y: auto;
}
.dash-clickup-kcard {
  background: var(--dash-surface);
  border: 1px solid var(--dash-border);
  border-radius: 6px;
  padding: 8px;
  cursor: pointer;
  transition: border-color .12s, box-shadow .12s;
  display: flex; flex-direction: column; gap: 4px;
  text-align: left;
}
.dash-clickup-kcard:hover {
  border-color: var(--dash-blue);
  box-shadow: 0 1px 4px rgba(0,0,0,.05);
}
.dash-clickup-kcard-top {
  display: flex; align-items: center; gap: 6px; flex-wrap: wrap;
}
.dash-clickup-kcard-title {
  font-size: 12px; font-weight: 500;
  color: var(--dash-text);
  word-break: break-word;
}
.dash-clickup-kcard-path {
  font-size: 10px; color: var(--dash-text-dim);
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.dash-clickup-kcard-tags {
  display: flex; gap: 3px; flex-wrap: wrap;
}

/* Connect UI */
.dash-clickup-connect {
  display: flex; flex-direction: column; align-items: center; gap: 10px;
  padding: 24px 16px;
  text-align: center;
}
.dash-clickup-icon { font-size: 28px; }
.dash-clickup-msg { font-size: 13px; color: var(--dash-text); max-width: 260px; }
.dash-clickup-err {
  background: rgba(220, 38, 38, .12);
  color: #dc2626;
  padding: 6px 10px;
  border-radius: 6px;
  font-weight: 600;
  font-size: 12px;
}
.dash-clickup-form {
  display: flex; gap: 6px; width: 100%; max-width: 280px;
}
.dash-clickup-form input {
  flex: 1; min-width: 0;
  padding: 6px 10px;
  border: 1px solid var(--dash-border);
  border-radius: 6px;
  font: 500 12px 'SF Mono', monospace;
  background: var(--dash-surface);
  color: var(--dash-text);
}
.dash-clickup-form input:focus { outline: none; border-color: var(--dash-blue); }
.dash-clickup-help {
  font-size: 11px;
  color: var(--dash-blue);
  text-decoration: none;
}
.dash-clickup-help:hover { text-decoration: underline; }

/* Lightbox overlay */
.dash-clickup-overlay {
  position: fixed; inset: 0;
  background: rgba(0,0,0,.45);
  z-index: 1000;
  display: none;
  align-items: flex-start; justify-content: center;
  padding: 5vh 4vw;
  overflow-y: auto;
}
.dash-clickup-overlay.open { display: flex; }
.dash-clickup-modal {
  background: var(--dash-surface);
  border-radius: 12px;
  width: 100%;
  max-width: 680px;
  max-height: 90vh;
  display: flex; flex-direction: column;
  overflow: hidden;
  box-shadow: 0 20px 60px rgba(0,0,0,.3);
}
.dash-clickup-modal-add { max-width: 520px; }
.dash-clickup-modal-head {
  display: flex; align-items: flex-start; gap: 8px;
  padding: 12px 14px;
  border-bottom: 1px solid var(--dash-border);
  background: var(--dash-surface2);
}
.dash-clickup-modal-title-wrap {
  display: flex; flex-wrap: wrap; align-items: center; gap: 8px;
  flex: 1; min-width: 0;
}
.dash-clickup-modal-title {
  font-size: 15px; font-weight: 600;
  min-width: 0;
  word-wrap: break-word;
}
.dash-clickup-modal-close { flex-shrink: 0; }
.dash-clickup-modal-body {
  padding: 12px 14px;
  overflow-y: auto;
  display: flex; flex-direction: column; gap: 10px;
}
.dash-clickup-modal-meta {
  display: flex; flex-direction: column; gap: 8px;
  font-size: 12px; color: var(--dash-text);
}
.dash-clickup-modal-meta b { color: var(--dash-text-dim); font-weight: 600; }
.dash-clickup-modal-row { font-size: 12px; }
.dash-clickup-assignees-row {
  display: flex; gap: 6px; flex-wrap: wrap;
}
.dash-clickup-assignee-wrap {
  display: inline-flex; align-items: center; gap: 4px;
  background: var(--dash-surface2);
  padding: 3px 8px 3px 4px;
  border-radius: 12px;
  font-size: 11px;
}
.dash-clickup-assignee-name {
  color: var(--dash-text);
}
.dash-clickup-modal-controls {
  display: flex; flex-wrap: wrap; gap: 10px;
  padding: 10px 0;
  border-top: 1px solid var(--dash-border);
  border-bottom: 1px solid var(--dash-border);
  align-items: center;
}
.dash-clickup-modal-controls label {
  display: flex; align-items: center; gap: 5px;
  font-size: 11px;
}
.dash-clickup-modal-controls select,
.dash-clickup-modal-controls input[type="date"] {
  padding: 4px 6px;
  border: 1px solid var(--dash-border);
  border-radius: 4px;
  font-size: 11px;
  background: var(--dash-surface);
  color: var(--dash-text);
}
.dash-clickup-danger {
  background: rgba(220, 38, 38, .10);
  color: var(--dash-red);
  border-color: rgba(220, 38, 38, .25);
  margin-left: auto;
}
.dash-clickup-danger:hover { background: rgba(220, 38, 38, .18); }
.dash-clickup-section-label {
  font-size: 10px; font-weight: 700;
  color: var(--dash-text-dim);
  text-transform: uppercase; letter-spacing: .4px;
  margin-top: 4px;
}
.dash-clickup-desc {
  font-size: 12px; color: var(--dash-text);
  background: var(--dash-surface2);
  padding: 10px 12px;
  border-radius: 6px;
  white-space: pre-wrap; word-break: break-word;
  max-height: 240px; overflow-y: auto;
  line-height: 1.45;
}
.dash-clickup-subtasks {
  display: flex; flex-direction: column; gap: 4px;
}
.dash-clickup-subtask {
  display: flex; align-items: center; gap: 8px;
  font-size: 11px;
  padding: 4px 6px;
  border-radius: 4px;
}
.dash-clickup-subtask:hover { background: var(--dash-surface2); }
.dash-clickup-checklist {
  display: flex; flex-direction: column; gap: 4px;
  background: var(--dash-surface2);
  padding: 8px;
  border-radius: 6px;
}
.dash-clickup-checkitem {
  display: flex; align-items: center; gap: 8px;
  font-size: 12px;
  padding: 4px 6px;
  cursor: pointer;
  border-radius: 4px;
}
.dash-clickup-checkitem:hover { background: var(--dash-surface); }
.dash-clickup-checkitem input[type="checkbox"] {
  margin: 0; cursor: pointer; flex-shrink: 0;
}
.dash-clickup-checkitem span.is-resolved {
  text-decoration: line-through;
  color: var(--dash-text-dim);
}
.dash-clickup-comments {
  display: flex; flex-direction: column; gap: 8px;
  max-height: 280px; overflow-y: auto;
  background: var(--dash-surface2);
  padding: 10px;
  border-radius: 6px;
}
.dash-clickup-comment {
  background: var(--dash-surface);
  padding: 8px 10px;
  border-radius: 6px;
  border: 1px solid var(--dash-border);
}
.dash-clickup-comment-meta {
  display: flex; gap: 6px; align-items: center;
  font-size: 11px;
}
.dash-clickup-comment-author { font-weight: 600; color: var(--dash-text); }
.dash-clickup-comment-when { color: var(--dash-text-dim); font-size: 10px; }
.dash-clickup-comment-text {
  font-size: 12px;
  margin-top: 4px;
  white-space: pre-wrap; word-break: break-word;
  color: var(--dash-text);
  line-height: 1.45;
}
.dash-clickup-empty-line {
  font-size: 11px; color: var(--dash-text-dim);
  font-style: italic;
  text-align: center;
  padding: 6px;
}
.dash-clickup-reply {
  display: flex; gap: 6px; align-items: stretch;
}
.dash-clickup-reply textarea {
  flex: 1; min-width: 0;
  padding: 8px 10px;
  border: 1px solid var(--dash-border);
  border-radius: 6px;
  font-size: 12px;
  font-family: inherit;
  resize: vertical;
  min-height: 38px;
  background: var(--dash-surface);
  color: var(--dash-text);
}
.dash-clickup-reply textarea:focus { outline: none; border-color: var(--dash-blue); }
.dash-clickup-modal-foot {
  padding: 8px 0 0;
  border-top: 1px solid var(--dash-border);
  text-align: right;
}

/* Add-task modal */
.dash-clickup-add-row {
  display: flex; flex-direction: column; gap: 4px;
  font-size: 12px;
}
.dash-clickup-add-row span { color: var(--dash-text); }
.dash-clickup-add-row b { color: var(--dash-text); font-weight: 600; }
.dash-clickup-add-row input,
.dash-clickup-add-row select,
.dash-clickup-add-row textarea {
  padding: 7px 9px;
  border: 1px solid var(--dash-border);
  border-radius: 6px;
  font-size: 12px;
  font-family: inherit;
  background: var(--dash-surface);
  color: var(--dash-text);
}
.dash-clickup-add-row input:focus,
.dash-clickup-add-row select:focus,
.dash-clickup-add-row textarea:focus {
  outline: none; border-color: var(--dash-blue);
}
.dash-clickup-add-row textarea { resize: vertical; min-height: 60px; }
.dash-clickup-add-foot {
  display: flex; justify-content: flex-end; gap: 6px;
  padding-top: 8px;
  border-top: 1px solid var(--dash-border);
}

/* ── Strategic Tasks widget (PR-XXX) ─────────────────
   Company-wide goals — admin writes, employee reads + comments.
   Visual idea: cards with a coloured left stripe by status, progress
   bar derived from milestone done-count, expandable milestone + comment
   panels. */
.dash-st {
  display: flex; flex-direction: column; gap: 8px;
  height: 100%; min-width: 0; position: relative;
}
.dash-st-head {
  display: flex; align-items: center; gap: 6px;
  font-size: 12px; color: var(--dash-text-dim);
  letter-spacing: .3px; font-weight: 600;
}
.dash-st-brand {
  font-size: 13px; font-weight: 700; color: var(--dash-text);
  display: inline-flex; align-items: center; gap: 4px;
  margin-right: 4px;
}
.dash-st-brand-lbl { font-size: 12px; }
.dash-st-cnt {
  font-family: 'SF Mono', monospace; font-size: 16px; font-weight: 700;
  color: var(--dash-blue); text-transform: none;
}
.dash-st-lbl { font-size: 11px; text-transform: uppercase; }
.dash-st-add {
  margin-left: auto;
  background: var(--dash-blue); color: #fff;
  border: 0;
  font: 600 11px var(--font, 'Inter');
  padding: 5px 12px; border-radius: 6px;
  cursor: pointer; transition: background .12s;
  text-transform: none;
}
.dash-st-add:hover { background: #1d4fd4; }

.dash-st-list {
  display: flex; flex-direction: column; gap: 8px;
  overflow-y: auto;
  flex: 1; min-height: 0;
}

/* Task card */
.dash-st-task {
  display: flex; align-items: stretch;
  background: var(--dash-surface);
  border: 1px solid var(--dash-border);
  border-radius: 8px;
  overflow: hidden;
  transition: box-shadow .15s, border-color .15s;
}
.dash-st-task:hover {
  box-shadow: 0 2px 8px rgba(0,0,0,.06);
  border-color: var(--dash-text-dim);
}

/* Coloured left stripe — visual status anchor */
.dash-st-stripe {
  flex-shrink: 0;
  width: 5px;
  background: #6b7280;
}
.dash-st-stripe-on_track { background: #22c55e; }
.dash-st-stripe-at_risk  { background: #eab308; }
.dash-st-stripe-blocked  { background: #ef4444; }
.dash-st-stripe-done     { background: #94a3b8; }

.dash-st-body {
  flex: 1; min-width: 0;
  padding: 10px 12px;
  display: flex; flex-direction: column; gap: 6px;
}

.dash-st-row1 {
  display: flex; align-items: center; gap: 8px;
}
.dash-st-title-block {
  flex: 1; min-width: 0;
  display: flex; align-items: center; gap: 6px;
}
.dash-st-pin { font-size: 11px; flex-shrink: 0; }
.dash-st-title {
  font-size: 14px; font-weight: 700; color: var(--dash-text);
  overflow: hidden; text-overflow: ellipsis;
  white-space: nowrap;
}
.dash-st-status {
  font-size: 10px; padding: 3px 9px; border-radius: 10px;
  font-weight: 700; flex-shrink: 0;
  text-transform: uppercase; letter-spacing: 0.3px;
}
.dash-st-status-on_track { background: rgba(34,197,94,.18);  color: #166534; }
.dash-st-status-at_risk  { background: rgba(234,179,8,.18);  color: #854d0e; }
.dash-st-status-blocked  { background: rgba(239,68,68,.18);  color: #991b1b; }
.dash-st-status-done     { background: rgba(148,163,184,.18); color: #475569; }

.dash-st-iconbtn {
  background: transparent; border: 0; cursor: pointer;
  color: var(--dash-text-dim); font-size: 12px;
  padding: 4px 6px; border-radius: 4px;
  opacity: 0.5; transition: opacity .15s, background .12s;
  flex-shrink: 0;
}
.dash-st-task:hover .dash-st-iconbtn { opacity: 1; }
.dash-st-iconbtn:hover { background: rgba(0,0,0,.05); }
.dash-st-iconbtn-del:hover { background: rgba(220,38,38,.1); color: var(--dash-red); }

.dash-st-meta {
  display: flex; align-items: center; gap: 6px;
  font-size: 11px; flex-wrap: wrap;
}
.dash-st-quarter {
  background: var(--dash-blue-bg); color: var(--dash-blue);
  font-weight: 600;
  padding: 2px 7px; border-radius: 10px;
}
.dash-st-due {
  background: var(--dash-surface2); color: var(--dash-text-dim);
  font-weight: 500;
  padding: 2px 7px; border-radius: 10px;
}
.dash-st-due.overdue { background: rgba(220,38,38,.12); color: var(--dash-red); font-weight: 700; }
.dash-st-owner {
  color: var(--dash-text-dim);
  padding: 2px 0;
}

.dash-st-desc {
  font-size: 12px; color: var(--dash-text);
  line-height: 1.4;
  background: var(--dash-surface2);
  padding: 6px 8px; border-radius: 5px;
  word-wrap: break-word;
}

/* Progress bar — coloured by status */
.dash-st-progress {
  height: 6px; border-radius: 3px;
  background: var(--dash-surface2);
  overflow: hidden;
}
.dash-st-progress-bar {
  height: 100%;
  transition: width .25s ease;
}
.dash-st-progress-on_track { background: #22c55e; }
.dash-st-progress-at_risk  { background: #eab308; }
.dash-st-progress-blocked  { background: #ef4444; }
.dash-st-progress-done     { background: #94a3b8; }
.dash-st-progress-lbl {
  font-size: 10px; color: var(--dash-text-dim);
  font-weight: 500;
}
.dash-st-progress-lbl.muted { font-style: italic; }

.dash-st-actions {
  display: flex; gap: 6px; align-items: center;
  margin-top: 2px;
}
.dash-st-toggle {
  background: transparent; border: 1px solid var(--dash-border);
  color: var(--dash-text-dim); cursor: pointer;
  font: 600 10px var(--font, 'Inter');
  padding: 3px 8px; border-radius: 4px;
  transition: background .12s, color .12s, border-color .12s;
}
.dash-st-toggle:hover {
  background: var(--dash-blue-bg);
  color: var(--dash-blue);
  border-color: rgba(37,99,235,.3);
}
.dash-st-toggle.open {
  background: var(--dash-blue-bg);
  color: var(--dash-blue);
  border-color: rgba(37,99,235,.4);
}

/* Milestones panel */
.dash-st-milestones {
  display: flex; flex-direction: column; gap: 3px;
  padding: 6px 8px;
  background: rgba(37,99,235,.03);
  border: 1px dashed var(--dash-border);
  border-radius: 5px;
}
.dash-st-milestone {
  display: flex; align-items: center; gap: 8px;
  font-size: 12px;
  padding: 2px 0;
}
.dash-st-milestone-cb { margin: 0; cursor: pointer; }
.dash-st-milestone-cb:disabled { cursor: not-allowed; }
.dash-st-milestone-text {
  flex: 1; min-width: 0;
  cursor: text;
  word-wrap: break-word;
}
.dash-st-milestone-text.done {
  text-decoration: line-through;
  color: var(--dash-text-dim);
}
.dash-st-milestone-edit {
  width: 100%; box-sizing: border-box;
  font: 12px var(--font, 'Inter');
  border: 0; outline: 2px solid var(--dash-blue);
  outline-offset: -2px;
  background: var(--dash-surface);
  padding: 2px 4px; border-radius: 3px;
}
.dash-st-milestone-del {
  background: transparent; border: 0; cursor: pointer;
  color: var(--dash-text-dim); font-size: 10px;
  padding: 0 4px; opacity: 0; transition: opacity .15s;
  flex-shrink: 0;
}
.dash-st-milestone:hover .dash-st-milestone-del { opacity: 0.6; }
.dash-st-milestone-del:hover { opacity: 1; color: var(--dash-red); }

.dash-st-add-milestone {
  font: 600 10px var(--font, 'Inter');
  background: transparent; color: var(--dash-blue);
  border: 1px dashed rgba(37,99,235,.4);
  padding: 3px 8px; border-radius: 4px;
  cursor: pointer; align-self: flex-start;
  margin-top: 2px;
}
.dash-st-add-milestone:hover { background: var(--dash-blue-bg); }

.dash-st-milestone-form {
  display: flex; gap: 4px; padding: 4px 0;
}
.dash-st-milestone-input {
  flex: 1;
  font: 12px var(--font, 'Inter');
  border: 1px solid var(--dash-border);
  background: var(--dash-surface);
  border-radius: 4px;
  padding: 3px 6px;
}
.dash-st-milestone-save,
.dash-st-milestone-cancel {
  font: 600 10px var(--font, 'Inter');
  border: 0; border-radius: 4px;
  padding: 4px 8px;
  cursor: pointer;
}
.dash-st-milestone-save { background: var(--dash-blue); color: #fff; }
.dash-st-milestone-save:hover { background: #1d4fd4; }
.dash-st-milestone-cancel { background: var(--dash-surface2); color: var(--dash-text-dim); }
.dash-st-milestone-cancel:hover { background: #e2e5ea; }

/* Comments panel */
.dash-st-comments {
  padding: 8px;
  background: rgba(37,99,235,.04);
  border: 1px dashed var(--dash-border);
  border-radius: 5px;
  display: flex; flex-direction: column; gap: 6px;
}
.dash-st-comments-list {
  display: flex; flex-direction: column; gap: 4px;
  max-height: 240px; overflow-y: auto;
}
.dash-st-empty-line {
  font-size: 11px; color: var(--dash-text-dim);
  padding: 4px 0; font-style: italic;
}
.dash-st-comment {
  background: var(--dash-surface);
  border: 1px solid var(--dash-border);
  border-radius: 5px;
  padding: 5px 8px;
  font-size: 11px;
}
.dash-st-comment-head {
  display: flex; align-items: center; gap: 6px;
  margin-bottom: 2px;
}
.dash-st-comment-author {
  font-weight: 600; color: var(--dash-text);
  font-size: 10px;
}
.dash-st-comment-time {
  font-size: 9px; color: var(--dash-text-dim);
}
.dash-st-comment-del {
  margin-left: auto;
  background: transparent; border: 0; cursor: pointer;
  color: var(--dash-text-dim); font-size: 10px;
  padding: 0 4px; opacity: 0; transition: opacity .15s;
}
.dash-st-comment:hover .dash-st-comment-del { opacity: 0.6; }
.dash-st-comment-del:hover { opacity: 1; color: var(--dash-red); }
.dash-st-comment-text {
  color: var(--dash-text); line-height: 1.4;
  font-size: 11px;
  word-wrap: break-word;
  white-space: pre-wrap;
}
.dash-st-comment-form {
  display: flex; gap: 4px; align-items: flex-end;
}
.dash-st-comment-input {
  flex: 1;
  font: 11px var(--font, 'Inter');
  padding: 5px 7px;
  border: 1px solid var(--dash-border);
  border-radius: 4px;
  background: var(--dash-surface);
  resize: vertical;
  min-height: 32px;
  max-height: 160px;
  box-sizing: border-box;
}
.dash-st-comment-input:focus {
  outline: 2px solid var(--dash-blue);
  outline-offset: -1px;
  border-color: transparent;
}
.dash-st-comment-save {
  background: var(--dash-blue); color: #fff;
  border: 0; border-radius: 4px;
  font: 600 10px var(--font, 'Inter');
  padding: 6px 12px;
  cursor: pointer;
}
.dash-st-comment-save:hover { background: #1d4fd4; }

/* Toast */
.dash-st-toast {
  position: absolute;
  bottom: 12px; left: 50%;
  transform: translateX(-50%);
  background: var(--dash-text);
  color: #fff;
  font: 500 11px var(--font, 'Inter');
  padding: 6px 12px;
  border-radius: 6px;
  box-shadow: 0 4px 12px rgba(0,0,0,.2);
  z-index: 60;
  max-width: 90%;
  text-overflow: ellipsis;
  overflow: hidden;
  animation: dash-st-toast-in .2s ease-out;
}
.dash-st-toast.warn { background: #b45309; }
.dash-st-toast.info { background: var(--dash-blue); }
@keyframes dash-st-toast-in {
  from { opacity: 0; transform: translate(-50%, 8px); }
  to   { opacity: 1; transform: translate(-50%, 0); }
}

/* Task editor overlay */
.dash-st-editor {
  display: flex; flex-direction: column; gap: 10px;
  padding: 4px 0;
}
.dash-st-editor-field {
  display: flex; flex-direction: column; gap: 3px;
}
.dash-st-editor-field > span {
  font-size: 11px; font-weight: 600;
  color: var(--dash-text-dim);
  text-transform: uppercase; letter-spacing: 0.3px;
}
.dash-st-editor-field input,
.dash-st-editor-field select,
.dash-st-editor-field textarea {
  font: 13px var(--font, 'Inter');
  padding: 7px 10px;
  border: 1px solid var(--dash-border);
  border-radius: 5px;
  background: var(--dash-surface);
  box-sizing: border-box;
  width: 100%;
}
.dash-st-editor-field textarea { resize: vertical; min-height: 56px; }
.dash-st-editor-row {
  display: grid;
  grid-template-columns: 1fr 1fr 1fr;
  gap: 8px;
}
.dash-st-editor-check {
  display: flex; align-items: center; gap: 6px;
  font-size: 12px; color: var(--dash-text);
  cursor: pointer; user-select: none;
}
.dash-st-editor-actions {
  display: flex; justify-content: flex-end; gap: 6px;
  padding-top: 6px;
  border-top: 1px solid var(--dash-border);
}
.dash-st-ed-save {
  background: var(--dash-blue); color: #fff;
  border: 0; border-radius: 6px;
  font: 600 12px var(--font, 'Inter');
  padding: 8px 16px;
  cursor: pointer;
}
.dash-st-ed-save:hover { background: #1d4fd4; }
.dash-st-ed-cancel {
  background: var(--dash-surface2); color: var(--dash-text-dim);
  border: 0; border-radius: 6px;
  font: 600 12px var(--font, 'Inter');
  padding: 8px 16px;
  cursor: pointer;
}
.dash-st-ed-cancel:hover { background: #e2e5ea; }

/* ── Widget Access modal (PR-perm-B) ──────────────────────
   Admin-only UI for granting/revoking widget visibility. Opens from
   the 🔑 button on each widget header in non-edit mode. Two sections:
   global "available to everyone" toggle, then per-employee tri-state
   (Default / Show / Hide). */
.dash-access-modal {
  max-width: 560px;
}
.dash-access-badge {
  display: inline-block;
  font: 600 10px var(--font, 'Inter');
  padding: 2px 8px;
  border-radius: 10px;
  margin-left: 6px;
  text-transform: uppercase; letter-spacing: 0.3px;
  vertical-align: middle;
}
.dash-access-badge-sensitive { background: rgba(239,68,68,.15); color: #991b1b; }
.dash-access-badge-admin     { background: rgba(148,163,184,.18); color: #475569; }
.dash-access-section {
  border-top: 1px solid var(--dash-border);
  padding-top: 12px;
  margin-top: 12px;
}
.dash-access-section-title {
  font: 700 11px var(--font, 'Inter');
  text-transform: uppercase; letter-spacing: 0.5px;
  color: var(--dash-text-dim);
  margin-bottom: 6px;
}
.dash-access-hint {
  font-size: 11px; color: var(--dash-text-dim);
  line-height: 1.4;
  margin-bottom: 8px;
}
.dash-access-global-toggle {
  display: flex; gap: 10px; align-items: flex-start;
  padding: 10px 12px;
  background: rgba(37,99,235,.06);
  border: 1px solid rgba(37,99,235,.2);
  border-radius: 6px;
  cursor: pointer;
}
.dash-access-global-toggle input { margin-top: 3px; flex-shrink: 0; }
.dash-access-global-label {
  font: 600 13px var(--font, 'Inter');
  color: var(--dash-text);
}
.dash-access-global-hint {
  font-size: 11px; color: var(--dash-text-dim);
  margin-top: 2px;
}
.dash-access-list {
  display: flex; flex-direction: column; gap: 4px;
  max-height: 360px; overflow-y: auto;
}
.dash-access-row {
  display: flex; align-items: center; gap: 10px;
  padding: 6px 10px;
  border-radius: 5px;
  background: var(--dash-surface);
  border: 1px solid var(--dash-border);
}
.dash-access-row:hover { background: var(--dash-surface2); }
.dash-access-user { flex: 1; min-width: 0; }
.dash-access-name {
  font: 600 12px var(--font, 'Inter');
  color: var(--dash-text);
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.dash-access-email {
  font-size: 10px; color: var(--dash-text-dim);
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.dash-access-toggle {
  display: inline-flex; gap: 2px;
  background: var(--dash-surface2);
  border-radius: 5px;
  padding: 2px;
}
.dash-access-opt {
  background: transparent; border: 0;
  font: 600 10px var(--font, 'Inter');
  color: var(--dash-text-dim);
  padding: 4px 10px;
  border-radius: 4px;
  cursor: pointer;
  transition: background .12s, color .12s;
}
.dash-access-opt:hover { color: var(--dash-text); }
.dash-access-opt.active {
  background: var(--dash-surface);
  color: var(--dash-blue);
  box-shadow: 0 1px 2px rgba(0,0,0,.08);
}
.dash-access-opt[data-state="show"].active { color: #166534; }
.dash-access-opt[data-state="hide"].active { color: #991b1b; }
.dash-access-actions {
  display: flex; align-items: center; gap: 8px;
  padding-top: 12px;
  border-top: 1px solid var(--dash-border);
  margin-top: 12px;
}
.dash-access-changed-cnt {
  flex: 1;
  font: 600 11px var(--font, 'Inter');
  color: var(--dash-text-dim);
}
.dash-access-save {
  background: var(--dash-blue); color: #fff;
  border: 0; border-radius: 6px;
  font: 600 12px var(--font, 'Inter');
  padding: 8px 18px;
  cursor: pointer;
}
.dash-access-save:hover:not(:disabled) { background: #1d4fd4; }
.dash-access-save:disabled { background: var(--dash-border); cursor: not-allowed; }
.dash-access-cancel {
  background: var(--dash-surface2); color: var(--dash-text-dim);
  border: 0; border-radius: 6px;
  font: 600 12px var(--font, 'Inter');
  padding: 8px 14px;
  cursor: pointer;
}
.dash-access-cancel:hover { background: #e2e5ea; }

/* ── Weekly Trend widget ──────────────────────────────────────────── */
.dash-wt { display: flex; flex-direction: column; height: 100%; padding: 2px; }
.dash-wt-toolbar {
  display: flex; align-items: center; justify-content: space-between;
  gap: 8px; flex-wrap: wrap; margin-bottom: 6px;
}
.dash-wt-summary { font-size: 12px; color: var(--dash-text-dim); }
.dash-wt-summary strong { color: var(--dash-text); font-weight: 700; }
.dash-wt-range { display: inline-flex; gap: 2px; background: var(--dash-surface2); border: 1px solid var(--dash-border); border-radius: 7px; padding: 2px; }
.dash-wt-rbtn {
  border: 0; background: transparent; cursor: pointer;
  font: 600 11px var(--font, 'Inter'); color: var(--dash-text-dim);
  padding: 3px 8px; border-radius: 5px;
}
.dash-wt-rbtn.active { background: var(--dash-surface); color: var(--dash-text); box-shadow: 0 1px 2px rgba(0,0,0,.08); }
.dash-wt-chart {
  flex: 1; min-height: 0;
  display: flex; align-items: stretch; gap: 1px;
}
.dash-wt-col {
  flex: 1; min-width: 0;
  display: flex; flex-direction: column;
  cursor: pointer;
}
.dash-wt-col.month-start { border-left: 1px dashed var(--dash-border); }
.dash-wt-barwrap {
  flex: 1; min-height: 0;
  display: flex; flex-direction: column; justify-content: flex-end;
  padding: 15px 15% 0; /* headroom ≥ label height so the tallest bar's label fits */
}
.dash-wt-bar {
  background: #2563eb; border-radius: 2px 2px 0 0;
  min-height: 0; opacity: .85;
}
.dash-wt-bar.current {
  background: repeating-linear-gradient(45deg, #2563eb, #2563eb 3px, #93c5fd 3px, #93c5fd 6px);
}
.dash-wt-col:hover .dash-wt-bar { opacity: 1; }
/* In-flow label DIRECTLY above its own bar (flex column, justify-end) —
   not pinned to the chart top. Sits on the bar it belongs to at any height. */
.dash-wt-val {
  text-align: center; font: 700 10px var(--font, 'Inter'); color: #2563eb;
  white-space: nowrap; overflow: visible; line-height: 1.2;
  margin-bottom: 1px; flex-shrink: 0;
}
.dash-wt-month {
  height: 14px; font: 600 9px var(--font, 'Inter');
  color: var(--dash-text-dim); text-align: left;
  white-space: nowrap; overflow: visible; padding-top: 3px;
}
.dash-wt-month b { color: var(--dash-text); font-weight: 700; }

/* Week drill-down overlay table */
.dash-wt-dd-wrap { max-height: 55vh; overflow-y: auto; margin-top: 10px; }
.dash-wt-dd-table { width: 100%; border-collapse: collapse; font-size: 12px; }
.dash-wt-dd-table th {
  position: sticky; top: 0; background: var(--dash-surface);
  text-align: left; font: 700 10px var(--font, 'Inter');
  text-transform: uppercase; letter-spacing: .04em;
  color: var(--dash-text-dim); padding: 6px 8px;
  border-bottom: 1px solid var(--dash-border);
}
.dash-wt-dd-table td { padding: 6px 8px; border-bottom: 1px solid var(--dash-surface2); }
.dash-wt-dd-name { color: #2563eb; text-decoration: none; font-weight: 600; }
.dash-wt-dd-name:hover { text-decoration: underline; }
.dash-wt-dd-pill {
  display: inline-block; padding: 1px 8px; border-radius: 999px;
  font-size: 11px; background: #f3f4f6; color: #1f2937; white-space: nowrap;
}
.dash-wt-dd-scout { color: var(--dash-text-dim); }
.dash-wt-dd-day { color: var(--dash-text-dim); white-space: nowrap; }

/* ── Custom calendar period picker (PR-cal) ───────────────────────── */
.dash-cal-month-row {
  display: flex; gap: 6px; align-items: center;
  padding: 4px 10px 8px;
}
.dash-cal-month {
  flex: 1; min-width: 0;
  border: 1px solid var(--dash-border); border-radius: 6px;
  background: var(--dash-surface); color: var(--dash-text);
  font: 500 12px var(--font, 'Inter');
  padding: 5px 6px;
}
.dash-cal-apply {
  border: 0; border-radius: 6px; cursor: pointer;
  background: #2563eb; color: #fff;
  font: 600 12px var(--font, 'Inter');
  padding: 6px 10px;
}
.dash-cal-apply:hover { background: #1d4ed8; }
.dash-cal-weeks { max-height: 190px; overflow-y: auto; }
.dash-popover-item.disabled { opacity: .4; cursor: default; }

/* ── CBDO View preset preview banner ──────────────────────────────── */
.dash-preset-banner {
  margin: 0 16px 10px; padding: 9px 14px;
  background: #eff6ff; border: 1px solid #bfdbfe; border-radius: 8px;
  color: #1e3a8a; font-size: 13px; line-height: 1.4;
}
.dash-preset-banner strong { font-weight: 700; }

/* ── Company Pulse (executive scorecard) ──────────────────────────── */
.dash-pulse { height: 100%; padding: 2px; }
.dash-pulse-tiles {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(150px, 1fr));
  gap: 10px;
  height: 100%;
}
.dash-pulse-tile {
  background: var(--dash-surface2);
  border: 1px solid var(--dash-border);
  border-radius: 10px;
  padding: 10px 12px;
  display: flex; flex-direction: column; justify-content: center;
  min-width: 0;
}
.dash-pulse-tile.stock { background: var(--dash-surface); }
.dash-pulse-top {
  display: flex; align-items: center; justify-content: space-between; gap: 6px;
}
.dash-pulse-ic { font-size: 16px; line-height: 1; }
.dash-pulse-val {
  font: 800 26px var(--font, 'Inter');
  color: var(--dash-text);
  margin: 5px 0 2px; line-height: 1.1;
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.dash-pulse-lbl { font-size: 11px; color: var(--dash-text-dim); }
.dash-pulse-per { opacity: .8; }
.dash-pulse-delta {
  font: 700 11px var(--font, 'Inter');
  padding: 2px 7px; border-radius: 999px; white-space: nowrap;
}
.dash-pulse-delta.up   { color: #15803d; background: #dcfce7; }
.dash-pulse-delta.down { color: #b91c1c; background: #fee2e2; }
.dash-pulse-delta.flat { color: var(--dash-text-dim); background: var(--dash-surface); }
.dash-pulse-tag {
  font: 700 10px var(--font, 'Inter');
  text-transform: uppercase; letter-spacing: .04em;
  color: var(--dash-text-dim); background: var(--dash-bg);
  border: 1px solid var(--dash-border);
  padding: 1px 6px; border-radius: 999px;
}

/* ── Team in Regions widget ───────────────────────────────────────── */
.dash-team-list { display: flex; flex-direction: column; gap: 6px; }
.dash-team-row {
  display: flex; align-items: center; gap: 10px;
  padding: 8px 10px; border: 1px solid var(--dash-border);
  border-radius: 8px; background: var(--dash-surface);
}
/* the chip is flex:1 in scout cards; here it sizes to its label */
.dash-team-row .dash-region-chip { flex: 0 0 auto; }
.dash-team-names {
  flex: 1 1 auto; min-width: 0; font-size: 12px; color: var(--dash-text-dim);
  overflow: hidden; text-overflow: ellipsis; white-space: nowrap;
}
.dash-scout-divider {
  grid-column: 1 / -1;
  font-size: 10px; font-weight: 700; letter-spacing: .5px; text-transform: uppercase;
  color: var(--dash-text-dim);
  padding: 6px 2px 0; margin-top: 4px; border-top: 1px dashed var(--dash-border);
}
.dash-team-avg {
  margin-left: auto; font-size: 11px; color: var(--dash-text-dim);
  white-space: nowrap;
}
.dash-team-avg b { color: var(--dash-text); font-weight: 700; }
