/* Timesheet Module Styles
   Scoped to [data-module="timesheet"]. CSS custom properties only.
   Prefix: ts-
   Both themes supported via existing platform tokens. */

/* Calm canvas: the platform caps every module at
   .strata-module-container { max-width: 1200px; margin: 0 auto }
   and pads .strata-content with 24px. The weekly grid wants room to
   breathe -- a fluid outer gutter keeps it off the sidebar, and a
   1600px cap stops day columns from ballooning on ultra-wide screens.
   The platform sets data-module on the module-container element itself
   (not a descendant), so use a direct attribute selector on the
   container and :has() only for the outer wrapper. See modules.md
   lesson: `:has()` selects ancestors, not the node itself. */
.strata-content:has([data-module="timesheet"]) {
  padding: 12px 0 0;
}
.strata-module-container[data-module="timesheet"] {
  max-width: 1600px;
  margin: 0 auto;
  padding: 0;
  height: 100%;
}

[data-module="timesheet"] {
  display: flex;
  flex-direction: column;
  height: calc(100vh - 56px);
  overflow: hidden;
  background: var(--bg);
  color: var(--text-primary);

  /* On-accent foreground: text/icons that sit on top of var(--accent)
     fills (commit button, FAB). Both themes use white because --accent
     is a saturated blue in both themes. Mirrors fixture-list's
     --fl-on-accent so each module owns its own token. */
  --ts-on-accent: #ffffff;

  /* Phase-code palette. Each phase gets a stable hue that renders identically
     in both themes (they're accent variations, not surface tokens). */
  --ts-phase-10: #a78bfa;
  --ts-phase-20: #a78bfa;
  --ts-phase-30: #60a5fa;
  --ts-phase-40: #60a5fa;
  --ts-phase-50: #818cf8;
  --ts-phase-60: #667eea;
  --ts-phase-70: #667eea;
  --ts-phase-80: #34d399;
  --ts-phase-90: #fbbf24;
  --ts-phase-pm: #fbbf24;
  --ts-phase-offgen: #9ca3af;

  /* Auto-fill source palette. Saturated accent hues that read on both
     dark and light surfaces (same rationale as the phase palette), so a
     single value serves both themes. Drives the banner source chips and
     the rail card source pips. */
  --ts-source-outlook: #60a5fa;
  --ts-source-planner: #a78bfa;
  --ts-source-recent:  var(--success);
  --ts-source-sent-email: #34d399;
}

/* Near-full-bleed surface: the grid + toolbar sit on a single panel that
   spans the width with no side borders, separated from the topbar by a
   thin top rule. The daily-total bar pins to the bottom; the dock floats
   above it. */
[data-module="timesheet"] .ts-root {
  display: flex;
  flex-direction: column;
  flex: 1;
  min-height: 0;
  overflow: hidden;
  background: var(--panel);
  border: 0;
  border-top: 1px solid var(--border);
}

/* ── Toolbar ──────────────────────────────────────────── */
[data-module="timesheet"] .ts-toolbar {
  display: flex;
  align-items: center;
  gap: 14px;
  padding: 8px 16px;
  border-bottom: 1px solid var(--border);
  background: transparent;
  flex-shrink: 0;
  flex-wrap: wrap;
}

[data-module="timesheet"] .ts-week-nav {
  display: flex;
  align-items: center;
  gap: 6px;
}

[data-module="timesheet"] .ts-nav-btn {
  width: 26px;
  height: 26px;
  border: 1px solid var(--border);
  background: transparent;
  color: var(--text-secondary);
  border-radius: 6px;
  cursor: pointer;
  font-size: 14px;
  display: flex;
  align-items: center;
  justify-content: center;
  font-family: inherit;
}

[data-module="timesheet"] .ts-nav-btn:hover {
  background: var(--row-hover);
  color: var(--text-primary);
}

[data-module="timesheet"] .ts-nav-btn-today {
  width: auto;
  padding: 0 10px;
  font-size: 12px;
}

[data-module="timesheet"] .ts-week-label {
  min-width: 160px;
  text-align: center;
}

[data-module="timesheet"] .ts-week-range {
  font-size: 13px;
  font-weight: 700;
  color: var(--text-primary);
  white-space: nowrap;
}

[data-module="timesheet"] .ts-week-sub {
  font-size: 10px;
  color: var(--text-tertiary);
  letter-spacing: 0.3px;
  text-transform: uppercase;
}

[data-module="timesheet"] .ts-total {
  display: flex;
  align-items: baseline;
  gap: 5px;
  padding-left: 14px;
  border-left: 1px solid var(--border);
}

[data-module="timesheet"] .ts-total-val {
  font-size: 26px;
  font-weight: 700;
  color: var(--text-primary);
  letter-spacing: -0.6px;
  line-height: 1;
}

[data-module="timesheet"] .ts-total-lbl {
  font-size: 12px;
  color: var(--text-secondary);
}

[data-module="timesheet"] .ts-toolbar-right {
  margin-left: auto;
  display: flex;
  gap: 6px;
  align-items: center;
}

[data-module="timesheet"] .ts-btn-ghost {
  padding: 5px 10px;
  background: transparent;
  border: 1px solid var(--border);
  border-radius: 6px;
  color: var(--text-secondary);
  font-size: 11px;
  cursor: pointer;
  white-space: nowrap;
  font-family: inherit;
}

[data-module="timesheet"] .ts-btn-ghost:hover {
  background: var(--row-hover);
  color: var(--text-primary);
}

[data-module="timesheet"] .ts-vp-indicator {
  width: 8px;
  height: 8px;
  border-radius: 50%;
  display: inline-block;
}

[data-module="timesheet"] .ts-vp-indicator.is-on {
  background: var(--success);
  box-shadow: 0 0 6px var(--success);
}

[data-module="timesheet"] .ts-vp-indicator.is-off {
  background: var(--text-tertiary);
}

[data-module="timesheet"] .ts-status {
  display: inline-flex;
  align-items: center;
  gap: 5px;
  padding: 4px 10px;
  border-radius: 16px;
  font-size: 11px;
  font-weight: 600;
  white-space: nowrap;
  border: 1px solid var(--border);
}

[data-module="timesheet"] .ts-status-dot {
  width: 5px;
  height: 5px;
  border-radius: 50%;
  background: currentColor;
}

[data-module="timesheet"] .ts-status-draft      { color: var(--text-secondary); }
[data-module="timesheet"] .ts-status-submitting { color: var(--accent); }
[data-module="timesheet"] .ts-status-submitted  { color: var(--success); border-color: rgba(52,211,153,0.3); }
[data-module="timesheet"] .ts-status-error      { color: var(--error);   border-color: rgba(248,113,113,0.3); }

[data-module="timesheet"] .ts-submit {
  padding: 6px 14px;
  font-size: 12px;
  font-weight: 700;
  white-space: nowrap;
}

/* ── Grid view ────────────────────────────────────────── */
[data-module="timesheet"] .ts-grid-wrap {
  flex: 1;
  overflow: auto;
  min-height: 0;
}

[data-module="timesheet"] .ts-grid {
  width: 100%;
  border-collapse: collapse;
  table-layout: fixed;
}

/* Stable column widths. Day cols share the flexible remainder so on wider
   viewports each day column has room for both the hour input and a
   comment input beneath it. Project/Phase/Task/Total/Del are fixed. */
/* Project + Codes are sticky (frozen pane) so the day grid can scroll
   horizontally without losing context. Day cols share the flex remainder.
   Weekend cols collapse to a tiny width when their week-totals are zero. */
[data-module="timesheet"] .ts-grid .ts-col-project { width: 200px; }
[data-module="timesheet"] .ts-grid .ts-col-codes   { width: 240px; }
[data-module="timesheet"] .ts-grid .ts-col-day     { width: auto; min-width: 108px; }
[data-module="timesheet"] .ts-grid .ts-col-day.is-collapsed { width: 30px; min-width: 30px; }
[data-module="timesheet"] .ts-grid .ts-col-total   { width: 76px; }

[data-module="timesheet"] .ts-grid thead tr {
  background: var(--panel);
}

[data-module="timesheet"] .ts-grid thead th {
  /* Sticky header survives vertical scroll inside .ts-grid-wrap */
  position: sticky;
  top: 0;
  z-index: 5;
  background: var(--panel);
}

/* Project + Codes columns are sticky-left so they stay visible while
   day columns scroll horizontally. Two layers: ts-sticky pins the
   first column, ts-sticky-2 pins the second after the first's width.
   z-index above day cells so content scrolls under, not over. */
[data-module="timesheet"] .ts-grid .ts-sticky {
  position: sticky;
  left: 0;
  z-index: 3;
  background: var(--bg);
  /* subtle separator so the frozen pane reads visually distinct */
  box-shadow: inset -1px 0 0 var(--border);
}

[data-module="timesheet"] .ts-grid .ts-sticky-2 {
  left: 200px; /* matches .ts-col-project width */
  box-shadow: inset -1px 0 0 var(--border);
}

[data-module="timesheet"] .ts-grid thead .ts-sticky {
  z-index: 6; /* above body sticky */
  background: var(--panel);
}

[data-module="timesheet"] .ts-grid thead .ts-sticky-2 {
  z-index: 6;
  background: var(--panel);
}

[data-module="timesheet"] .ts-grid tbody .ts-row .ts-sticky,
[data-module="timesheet"] .ts-grid tbody .ts-sub-row .ts-sticky {
  background: var(--bg);
}

[data-module="timesheet"] .ts-grid tbody .ts-row:hover .ts-sticky,
[data-module="timesheet"] .ts-grid tbody .ts-sub-row:hover .ts-sticky {
  background: var(--row-hover);
}

/* Group/banner rows that use colspan also need to participate in
   horizontal scroll honestly. A colspan row in a sticky context renders
   fine -- its first cell carries ts-sticky-row to keep its background
   solid as you scroll horizontally. */
[data-module="timesheet"] .ts-grid .ts-sticky-row {
  position: sticky;
  left: 0;
  /* span the visible viewport via background; cell width is colspan-driven */
  background: var(--panel);
  z-index: 4;
}

[data-module="timesheet"] .ts-th {
  padding: 8px 8px;
  font-size: 9px;
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.6px;
  color: var(--text-tertiary);
  border-bottom: 2px solid var(--border-strong);
  border-right: 1px solid var(--border);
  text-align: left;
  background: var(--panel);
}

[data-module="timesheet"] .ts-th-day {
  text-align: center;
  min-width: 64px;
  padding: 5px 4px 6px;
  vertical-align: top;
}

/* Weekend column dimmer; collapsed state renders narrow with mini text. */
[data-module="timesheet"] .ts-th-day.is-weekend {
  background: color-mix(in srgb, var(--panel) 92%, var(--bg));
  opacity: 0.7;
}

/* Today: accent bg + 2px accent underline + accent text. */
[data-module="timesheet"] .ts-th-day.is-today {
  background: color-mix(in srgb, var(--accent) 9%, var(--panel));
  border-bottom-color: var(--accent);
}

[data-module="timesheet"] .ts-th-day.is-today .ts-th-day-lbl,
[data-module="timesheet"] .ts-th-day.is-today .ts-th-day-num {
  color: var(--accent);
}

[data-module="timesheet"] .ts-th-day.is-collapsed {
  padding: 6px 2px;
  min-width: 30px;
}

[data-module="timesheet"] .ts-th-day.is-collapsed .ts-th-day-lbl {
  font-size: 8px;
}

[data-module="timesheet"] .ts-th-day.is-collapsed .ts-th-day-num,
[data-module="timesheet"] .ts-th-day.is-collapsed .ts-th-day-total,
[data-module="timesheet"] .ts-th-day.is-collapsed .ts-th-bar {
  display: none;
}

/* Collapsed weekend cells stay clickable + editable -- they just shrink.
   Some folks DO log weekend hours; opening the editor on a collapsed
   cell auto-expands the column on the next render once a value is saved. */
[data-module="timesheet"] .ts-td-hour.is-collapsed,
[data-module="timesheet"] .ts-foot-day.is-collapsed,
[data-module="timesheet"] .ts-sub-day.is-collapsed {
  padding: 0 1px;
  min-width: 30px;
}

[data-module="timesheet"] .ts-td-hour.is-collapsed .ts-hour {
  font-size: 11px;
}

[data-module="timesheet"] .ts-td-hour.is-collapsed .ts-hour-preview,
[data-module="timesheet"] .ts-td-hour.is-collapsed .ts-fill-handle {
  display: none;
}

[data-module="timesheet"] .ts-td-hour.is-collapsed .ts-hour-wrap {
  height: 26px;
  border-radius: 4px;
}

[data-module="timesheet"] .ts-foot-day.is-collapsed .ts-foot-day-val,
[data-module="timesheet"] .ts-sub-day.is-collapsed .ts-sub-val {
  font-size: 10px;
}

[data-module="timesheet"] .ts-foot-day.is-collapsed .ts-th-bar {
  display: none;
}

[data-module="timesheet"] .ts-th-day-lbl {
  font-size: 9px;
  font-weight: 700;
  color: var(--text-tertiary);
  letter-spacing: 0.6px;
  line-height: 1;
}

[data-module="timesheet"] .ts-th-day-num {
  font-size: 18px;
  font-weight: 700;
  color: var(--text-primary);
  line-height: 1.15;
  letter-spacing: -0.4px;
  margin-top: 1px;
  text-transform: none;
}

[data-module="timesheet"] .ts-th-day-total {
  font-size: 11px;
  font-weight: 700;
  margin-top: 1px;
  text-transform: none;
  letter-spacing: 0;
}

[data-module="timesheet"] .ts-th-day-total.is-empty { color: var(--text-tertiary); }
[data-module="timesheet"] .ts-th-day-total.is-under { color: var(--warning); }
[data-module="timesheet"] .ts-th-day-total.is-ok    { color: var(--success); }

/* Mini progress bar to MIN_WORK_HOURS (9h). Used in both day header and
   sticky footer. The .is-spacer variant reserves the same vertical space
   so weekend / non-workday columns don't collapse to a different height. */
[data-module="timesheet"] .ts-th-bar {
  height: 3px;
  border-radius: 2px;
  background: var(--border);
  width: 32px;
  margin: 4px auto 0;
  overflow: hidden;
}

[data-module="timesheet"] .ts-th-bar.is-spacer {
  background: transparent;
}

[data-module="timesheet"] .ts-th-bar-fill {
  height: 100%;
  border-radius: 2px;
  transition: width 0.35s ease, background 0.2s;
}

[data-module="timesheet"] .ts-th-bar-fill.is-empty { background: transparent; }
[data-module="timesheet"] .ts-th-bar-fill.is-under { background: var(--warning); }
[data-module="timesheet"] .ts-th-bar-fill.is-ok    { background: var(--success); }

[data-module="timesheet"] .ts-row {
  border-bottom: 1px solid var(--border);
  /* Compact rows. Per-day comments live in the DayEditor popover.
     When a day has a comment, a tiny preview line renders inside the
     cell without shifting row height (height is reserved via padding). */
  height: 48px;
}

[data-module="timesheet"] .ts-row:hover {
  background: var(--row-hover);
}

/* Leading column of the project cell: selection checkbox + project
   button laid out as a tight flex row. The checkbox stays invisible
   at rest so empty/unfocused grids look the same as before; it
   appears on row hover and stays visible while the row is selected.
   Pinned rows skip the checkbox entirely (no .ts-row-select rendered). */
[data-module="timesheet"] .ts-row-lead {
  display: flex;
  align-items: center;
  gap: 4px;
  width: 100%;
}

[data-module="timesheet"] .ts-row-select {
  width: 16px;
  height: 16px;
  min-width: 16px;
  border-radius: 3px;
  border: 1.5px solid var(--text-tertiary);
  background: var(--bg);
  color: var(--bg);
  cursor: pointer;
  padding: 0;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  opacity: 0;
  transition: opacity 0.1s, background 0.1s, border-color 0.1s;
}
[data-module="timesheet"] .ts-row:hover .ts-row-select,
[data-module="timesheet"] .ts-row.is-selected .ts-row-select,
[data-module="timesheet"] .ts-row-select:focus-visible,
[data-module="timesheet"] .ts-row-select.is-on {
  opacity: 1;
}
[data-module="timesheet"] .ts-row-select.is-on {
  background: var(--accent);
  border-color: var(--accent);
  color: var(--bg);
}
[data-module="timesheet"] .ts-row-select:hover {
  border-color: var(--accent);
}
[data-module="timesheet"] .ts-row-select:focus-visible {
  outline: 2px solid var(--accent);
  outline-offset: 1px;
}

/* Selected-row tint. Sits above the autop / hover treatments so the
   selection state is unambiguous. */
[data-module="timesheet"] .ts-row.is-selected {
  background: color-mix(in srgb, var(--accent) 8%, transparent);
}
[data-module="timesheet"] .ts-row.is-selected:hover {
  background: color-mix(in srgb, var(--accent) 12%, transparent);
}

/* Selection bar between the toolbar and grid. Sticky so the user can
   keep acting on the selection while scrolling. Mirrors --accent so
   it visually anchors to the highlighted rows. */
[data-module="timesheet"] .ts-selection-bar {
  position: sticky;
  top: 0;
  z-index: 10;
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 12px;
  padding: 8px 16px;
  background: color-mix(in srgb, var(--accent) 10%, var(--panel));
  border-bottom: 1px solid color-mix(in srgb, var(--accent) 30%, var(--border));
  font-size: 12px;
}
[data-module="timesheet"] .ts-selection-count {
  font-weight: 600;
  color: var(--text-primary);
}
[data-module="timesheet"] .ts-selection-actions {
  display: inline-flex;
  gap: 8px;
}
[data-module="timesheet"] .ts-selection-action {
  display: inline-flex;
  align-items: center;
  height: 26px;
  padding: 0 12px;
  border: 1px solid var(--border);
  background: var(--bg);
  border-radius: 6px;
  color: var(--text-primary);
  font-size: 12px;
  font-weight: 500;
  font-family: inherit;
  cursor: pointer;
}
[data-module="timesheet"] .ts-selection-action:hover {
  background: var(--row-hover);
  border-color: var(--border-strong);
}
[data-module="timesheet"] .ts-selection-action.is-delete {
  border-color: color-mix(in srgb, var(--error) 50%, var(--border));
  color: var(--error);
}
[data-module="timesheet"] .ts-selection-action.is-delete:hover {
  background: color-mix(in srgb, var(--error) 12%, var(--bg));
}

/* "default: <comment>" chip on pinned rows. Lives in the codes cell
   alongside the source pill; replaces the per-day comment preview
   repetition that pinned rows used to show in every empty cell. */
[data-module="timesheet"] .ts-default-chip {
  display: inline-flex;
  align-items: center;
  gap: 4px;
  padding: 2px 6px;
  margin-left: 4px;
  font-size: 11px;
  color: var(--text-secondary);
  background: var(--row-alt, var(--panel-2));
  border-radius: 10px;
  max-width: 220px;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}
[data-module="timesheet"] .ts-default-chip-label {
  font-family: var(--font-mono, monospace);
  font-size: 10px;
  color: var(--text-tertiary);
  text-transform: uppercase;
  letter-spacing: 0.04em;
}

[data-module="timesheet"] .ts-td {
  padding: 2px 6px;
  border-right: 1px solid var(--border);
  font-size: 12px;
}

[data-module="timesheet"] .ts-td-total {
  text-align: center;
  font-weight: 700;
  color: var(--text-primary);
}

/* Total cell anchors the row total value AND the overlaid × button.
   The × is invisible until row hover, then floats over the right edge
   without claiming a dedicated column. */
[data-module="timesheet"] .ts-td-total {
  position: relative;
}

[data-module="timesheet"] .ts-row-total-val {
  display: inline-block;
}

[data-module="timesheet"] .ts-del {
  position: absolute;
  top: 50%;
  right: 4px;
  transform: translateY(-50%);
  width: 20px;
  height: 20px;
  border: none;
  background: var(--bg);
  color: var(--text-tertiary);
  cursor: pointer;
  opacity: 0;
  border-radius: 4px;
  transition: opacity 0.1s;
  font-size: 14px;
  line-height: 1;
  font-family: inherit;
}

[data-module="timesheet"] .ts-row:hover .ts-del {
  opacity: 1;
}

[data-module="timesheet"] .ts-del:hover {
  background: var(--row-hover);
  color: var(--error);
}

/* Per-project subtotal row -- subdued background, italic value, sits
   between the project group's last row and the next group header. */
[data-module="timesheet"] .ts-sub-row {
  background: color-mix(in srgb, var(--panel) 50%, var(--bg));
  border-bottom: 1px solid var(--border);
}

[data-module="timesheet"] .ts-sub-row .ts-td {
  padding: 4px 8px;
  border-right: 1px solid var(--border);
}

[data-module="timesheet"] .ts-sub-lbl {
  font-size: 10px;
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.5px;
  padding-left: 16px;
}

[data-module="timesheet"] .ts-sub-day {
  text-align: center;
  font-size: 11px;
}

[data-module="timesheet"] .ts-sub-val {
  font-weight: 700;
  color: var(--text-primary);
}

[data-module="timesheet"] .ts-sub-val.is-empty {
  color: var(--text-tertiary);
  font-weight: 400;
}

[data-module="timesheet"] .ts-sub-total {
  text-align: center;
  font-size: 12px;
}

/* Auto-save pulse -- silent fade-in/out near the toolbar status. */
[data-module="timesheet"] .ts-saved-pulse {
  font-size: 11px;
  color: var(--success);
  opacity: 0;
  transition: opacity 0.2s ease-out;
  pointer-events: none;
  white-space: nowrap;
  padding: 0 6px;
}

[data-module="timesheet"] .ts-saved-pulse.is-on {
  opacity: 1;
  transition: opacity 0.1s ease-in;
}

/* Phase 51 inline coach inside the DayEditor. */
[data-module="timesheet"] .ts-de-coach {
  font-size: 11px;
  line-height: 1.5;
  padding: 8px 10px;
  background: rgba(251, 191, 36, 0.08);
  border: 1px solid rgba(251, 191, 36, 0.3);
  border-radius: 6px;
  color: var(--warning);
}

/* ── Density toggle: Compact mode overrides ─────────────────────────
   Shrinks rows, hides preview by default, smaller fonts. Used by
   designers who want maximum info density on small screens. */
[data-module="timesheet"] .ts-root.is-compact .ts-row {
  height: 32px;
}

[data-module="timesheet"] .ts-root.is-compact .ts-hour-wrap {
  height: 28px;
}

[data-module="timesheet"] .ts-root.is-compact .ts-hour {
  font-size: 12px;
}

[data-module="timesheet"] .ts-root.is-compact .ts-hour-preview {
  display: none;
}

[data-module="timesheet"] .ts-root.is-compact .ts-row:hover .ts-hour-preview {
  display: block;
  position: absolute;
  top: 100%;
  left: 0;
  right: 0;
  background: var(--panel);
  border: 1px solid var(--border);
  border-radius: 4px;
  padding: 2px 6px;
  z-index: 4;
  box-shadow: 0 4px 12px rgba(0, 0, 0, 0.2);
}

[data-module="timesheet"] .ts-root.is-compact .ts-codes .ts-chip {
  height: 22px;
  font-size: 10px;
  padding: 2px 6px;
}

[data-module="timesheet"] .ts-root.is-compact .ts-cell {
  height: 26px;
  font-size: 11px;
}

[data-module="timesheet"] .ts-root.is-compact .ts-th {
  padding: 6px 6px;
}

/* Group headers -- tinted band per project. The cell carries an inline
   --grp-color via JS (project color routed through safeColor); we re-use
   the same color for border-top, soft bg, and the trailing total. */
[data-module="timesheet"] .ts-grp-row {
  background: var(--panel-2, color-mix(in srgb, var(--bg) 90%, var(--panel)));
}

[data-module="timesheet"] .ts-grp-cell {
  padding: 7px 16px 6px;
  border-top: 2px solid var(--border);
  border-bottom: 1px solid var(--border);
  font-size: 11px;
}
/* Flex layout lives on an inner wrapper, NOT the <td>. display:flex on a
   table cell overrides display:table-cell, which drops colspan width --
   under sticky positioning the band collapses and a long project name
   (e.g. "Palazzo VIP Check In") wraps instead of spanning the full row. */
[data-module="timesheet"] .ts-grp-inner {
  display: flex;
  align-items: center;
  gap: 8px;
}

/* Pinned row -- subdued grey band, no project tint. */
[data-module="timesheet"] .ts-grp-row.is-pinned .ts-grp-cell {
  border-top-color: var(--border);
  background: color-mix(in srgb, var(--text-tertiary) 7%, var(--bg));
  padding-top: 6px;
  padding-bottom: 5px;
}

[data-module="timesheet"] .ts-grp-pin-icon {
  color: var(--text-tertiary);
  flex-shrink: 0;
}

[data-module="timesheet"] .ts-grp-pin-label {
  font-size: 10px;
  font-weight: 700;
  letter-spacing: 0.8px;
  text-transform: uppercase;
  color: var(--text-secondary);
}

/* Pinned group is a collapse toggle (button reset; reuses .ts-grp-inner flex). */
[data-module="timesheet"] .ts-grp-toggle {
  width: 100%;
  padding: 0;
  border: 0;
  background: none;
  font: inherit;
  color: inherit;
  text-align: left;
  cursor: pointer;
}

[data-module="timesheet"] .ts-grp-caret {
  display: inline-block;
  width: 10px;
  font-size: 12px;
  font-weight: 700;
  line-height: 1;
  text-align: center;
  color: var(--text-tertiary);
  flex-shrink: 0;
}

[data-module="timesheet"] .ts-grp-count {
  font-size: 10px;
  font-weight: 600;
  color: var(--text-tertiary);
  background: color-mix(in srgb, var(--text-tertiary) 14%, transparent);
  border-radius: 8px;
  padding: 1px 6px;
}

[data-module="timesheet"] .ts-grp-hint {
  font-size: 10px;
  font-style: italic;
  color: var(--text-tertiary);
}

[data-module="timesheet"] .ts-grp-dot {
  display: inline-block;
  width: 7px;
  height: 7px;
  border-radius: 50%;
  flex-shrink: 0;
}

[data-module="timesheet"] .ts-grp-name {
  font-weight: 700;
  font-size: 11px;
}

[data-module="timesheet"] .ts-grp-code {
  font-family: var(--font-mono, monospace);
  font-size: 10px;
  opacity: 0.65;
}

/* Running project total -- right-aligned in the band, color-matched to the
   project tint. */
[data-module="timesheet"] .ts-grp-total {
  margin-left: auto;
  font-size: 12px;
  font-weight: 700;
  letter-spacing: -0.2px;
}

/* Cells (buttons for dropdowns) */
[data-module="timesheet"] .ts-cell {
  width: 100%;
  height: 32px;
  padding: 0 8px;
  background: transparent;
  border: 1px solid transparent;
  border-radius: 6px;
  color: var(--text-primary);
  font-size: 12px;
  font-family: inherit;
  text-align: left;
  cursor: pointer;
  display: flex;
  align-items: center;
  gap: 6px;
}

[data-module="timesheet"] .ts-cell:hover,
[data-module="timesheet"] .ts-cell:focus-visible {
  background: var(--row-hover);
  border-color: var(--border);
  outline: none;
}

[data-module="timesheet"] .ts-dot {
  width: 7px;
  height: 7px;
  border-radius: 50%;
  flex-shrink: 0;
}

[data-module="timesheet"] .ts-cell-text {
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
  flex: 1;
  min-width: 0; /* allow the label to shrink + ellipsize instead of clipping the job code */
}

[data-module="timesheet"] .ts-cell-hint {
  font-size: 10px;
  color: var(--text-tertiary);
  font-family: var(--font-mono, monospace);
  margin-left: auto;
}

/* Combined Phase + Task chip cell. Two chips side-by-side: phase code
   in its phase color, task code/name in neutral. Each is independently
   clickable -- editing one doesn't disturb the other. */
[data-module="timesheet"] .ts-codes {
  display: flex;
  align-items: center;
  gap: 4px;
  width: 100%;
  padding: 0 6px;
  min-width: 0;
}

[data-module="timesheet"] .ts-codes .ts-chip {
  background: transparent;
  border: 1px solid var(--border);
  border-radius: 4px;
  padding: 3px 8px;
  font-size: 11px;
  font-family: inherit;
  cursor: pointer;
  white-space: nowrap;
  text-overflow: ellipsis;
  overflow: hidden;
  height: 26px;
  display: inline-flex;
  align-items: center;
}

[data-module="timesheet"] .ts-codes .ts-chip-phase {
  font-weight: 700;
  flex-shrink: 0;
  background: color-mix(in srgb, currentColor 8%, transparent);
}

[data-module="timesheet"] .ts-codes .ts-chip-task {
  flex: 1;
  min-width: 0;
  color: var(--text-secondary);
}

[data-module="timesheet"] .ts-codes .ts-chip-task.is-warn {
  color: var(--warning);
  border-color: rgba(251, 191, 36, 0.4);
  background: rgba(251, 191, 36, 0.06);
}

[data-module="timesheet"] .ts-codes .ts-chip:hover {
  background: var(--row-hover);
}

/* Source pill (Phase 1.2): shows where an entry came from when not
   manually entered. Visual weight is intentionally low -- it sits
   next to phase + task chips and must not steal the eye from them.
   The leading dot picks up the project color so the row's source +
   project read together at a glance. */
[data-module="timesheet"] .ts-source-pill {
  display: inline-flex;
  align-items: center;
  gap: 4px;
  height: 18px;
  padding: 0 6px;
  margin-left: 4px;
  border: 1px solid var(--border);
  border-radius: 9px;
  font-size: 10px;
  line-height: 1;
  color: var(--text-tertiary);
  background: color-mix(in srgb, var(--accent) 4%, transparent);
  white-space: nowrap;
  flex-shrink: 0;
}

[data-module="timesheet"] .ts-source-pill .ts-source-dot {
  display: inline-block;
  width: 6px;
  height: 6px;
  border-radius: 50%;
}

[data-module="timesheet"] .ts-source-pill .ts-source-label {
  text-transform: lowercase;
  letter-spacing: 0.02em;
}

[data-module="timesheet"] .ts-source-pill .ts-source-edited {
  color: var(--text-secondary);
  font-style: italic;
}

[data-module="timesheet"] .ts-source-pill.is-edited {
  background: transparent;
}

/* Auto-populated, unedited rows render at reduced strength so the user
   knows "review me" before committing. The user-edit path bumps
   updated_at, which drops is-auto on the next render and the row
   restores to full strength. */
[data-module="timesheet"] .ts-row.is-auto {
  opacity: 0.72;
}

[data-module="timesheet"] .ts-row.is-auto:hover,
[data-module="timesheet"] .ts-row.is-auto:focus-within {
  opacity: 1;
}

[data-module="timesheet"] .ts-card.is-auto {
  opacity: 0.78;
}

[data-module="timesheet"] .ts-card.is-auto:focus-within {
  opacity: 1;
}

/* Hour cell tile: a clickable, rounded card showing hours + optional
   1-line comment preview. Click opens the DayEditor popover which owns
   editing. Empty / filled / active states follow the design's visual
   contract (empty: transparent + dash; filled: accent-tinted + value;
   active: solid accent border). */
[data-module="timesheet"] .ts-hour-wrap {
  position: relative;
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  gap: 1px;
  width: 100%;
  height: 40px;
  cursor: pointer;
  border-radius: 6px;
  border: 1px solid transparent;
  background: transparent;
  transition: background 0.12s, border-color 0.12s, box-shadow 0.12s;
}

/* Filled-state tints. Prefilled = from planner/outlook (accent); user =
   typed by the user (success). Empty stays transparent so the column
   reads light by default. */
[data-module="timesheet"] .ts-hour-wrap.is-prefilled {
  background: color-mix(in srgb, var(--accent) 7%, transparent);
  border-color: color-mix(in srgb, var(--accent) 22%, transparent);
}

[data-module="timesheet"] .ts-hour-wrap.is-user {
  background: color-mix(in srgb, var(--success) 6%, transparent);
  border-color: color-mix(in srgb, var(--success) 22%, transparent);
}

[data-module="timesheet"] .ts-hour-wrap:hover {
  background: color-mix(in srgb, var(--accent) 6%, var(--row-hover));
  border-color: color-mix(in srgb, var(--accent) 18%, var(--border));
}

[data-module="timesheet"] .ts-hour-wrap:focus-visible,
[data-module="timesheet"] .ts-hour-wrap:focus {
  outline: none;
  border-color: var(--accent);
  background: color-mix(in srgb, var(--accent) 12%, transparent);
  box-shadow: 0 0 0 2px color-mix(in srgb, var(--accent) 22%, transparent);
}

[data-module="timesheet"] .ts-hour-wrap.is-warn {
  background: rgba(251, 191, 36, 0.07);
  border-color: rgba(251, 191, 36, 0.4);
}

/* Hour text inside the tile -- replaces the previous readonly <input>. */
[data-module="timesheet"] .ts-hour {
  display: block;
  text-align: center;
  background: transparent;
  border: none;
  color: var(--text-primary);
  font-size: 13px;
  font-weight: 600;
  font-family: inherit;
  line-height: 1;
  padding: 0;
}

[data-module="timesheet"] .ts-hour.is-empty {
  color: var(--text-tertiary);
  font-weight: 400;
  /* Empty body cells no longer render an em-dash (the JS emits an empty
     span). The cell stays a visible hit-target via the wrap's hover
     background; a tiny center dot replaces the dash as the affordance
     so the column doesn't look broken when the grid is mostly empty. */
  min-height: 12px;
  position: relative;
}
[data-module="timesheet"] .ts-hour.is-empty::before {
  content: '';
  position: absolute;
  left: 50%;
  top: 50%;
  width: 3px;
  height: 3px;
  border-radius: 50%;
  background: var(--text-tertiary);
  opacity: 0.32;
  transform: translate(-50%, -50%);
}
/* Hover/focus lifts the dot out, since the hour wrap's hover treatment
   itself communicates "this is clickable" -- the dot would compete. */
[data-module="timesheet"] .ts-hour-wrap:hover .ts-hour.is-empty::before,
[data-module="timesheet"] .ts-hour-wrap:focus .ts-hour.is-empty::before,
[data-module="timesheet"] .ts-hour-wrap:focus-visible .ts-hour.is-empty::before {
  opacity: 0;
}

/* Today column: tinted background on the TD, slightly lifted tile inside. */
[data-module="timesheet"] .ts-td-hour.is-today {
  background: color-mix(in srgb, var(--accent) 4%, transparent);
}

/* Inline one-line preview beneath the hour number. Truncates with
   ellipsis; tooltip (title attr) shows the full comment on hover.
   Non-italic + slightly larger than the previous treatment so the
   text reads as integral cell content (this hour was for X) rather
   than a footnote. */
[data-module="timesheet"] .ts-hour-preview {
  display: block;
  font-size: 10px;
  line-height: 1.2;
  color: var(--text-secondary);
  text-align: center;
  white-space: nowrap;
  overflow: hidden;
  text-overflow: ellipsis;
  max-width: 95%;
  padding: 0 3px;
  font-style: normal;
}

/* Empty cells with a seeded/leftover comment dim the preview so the
   eye reads "0h with a label" rather than "an entry." Once the user
   logs hours the cell flips back to the standard preview color via
   the parent .is-prefilled / .is-user rules. */
[data-module="timesheet"] .ts-hour-wrap.is-empty .ts-hour-preview {
  color: var(--text-tertiary);
}

[data-module="timesheet"] .ts-hour-preview.is-ghost {
  color: var(--text-tertiary);
  opacity: 0.75;
  font-style: italic;
}

/* ── DayEditor popover: Deltek's pulldown, reimagined ─────────────
   Opens on click/focus of an hour cell. Contains hour + comment
   inputs in a single focused panel with autocomplete, "apply to
   week" action, and keyboard chaining between day cells. */
[data-module="timesheet"] .ts-day-editor {
  position: absolute;
  z-index: 200;
  background: var(--panel);
  border: 1px solid var(--border-strong);
  border-radius: 10px;
  box-shadow: 0 12px 32px rgba(0, 0, 0, 0.35);
  padding: 12px 14px;
  display: flex;
  flex-direction: column;
  gap: 8px;
}

[data-module="timesheet"] .ts-de-head {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 10px;
  padding-bottom: 6px;
  border-bottom: 1px solid var(--border);
}

[data-module="timesheet"] .ts-de-date {
  font-size: 11px;
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.5px;
  color: var(--text-secondary);
}

[data-module="timesheet"] .ts-de-warn {
  font-size: 10px;
  padding: 2px 6px;
  background: rgba(251, 191, 36, 0.12);
  border: 1px solid rgba(251, 191, 36, 0.35);
  color: var(--warning);
  border-radius: 4px;
  font-weight: 700;
}

[data-module="timesheet"] .ts-de-row {
  display: flex;
  align-items: center;
  gap: 10px;
}

[data-module="timesheet"] .ts-de-label {
  font-size: 10px;
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.5px;
  color: var(--text-tertiary);
  width: 60px;
  flex-shrink: 0;
}

[data-module="timesheet"] .ts-de-hour {
  width: 84px;
  height: 32px;
  text-align: center;
  background: var(--input-bg, var(--bg));
  border: 1px solid var(--border);
  border-radius: 6px;
  color: var(--text-primary);
  font-size: 15px;
  font-weight: 700;
  font-family: inherit;
  outline: none;
}

[data-module="timesheet"] .ts-de-hour:focus {
  border-color: var(--accent);
}

[data-module="timesheet"] .ts-de-cmt-wrap {
  position: relative;
  flex: 1;
}

[data-module="timesheet"] .ts-de-comment {
  width: 100%;
  height: 32px;
  padding: 0 10px;
  background: var(--input-bg, var(--bg));
  border: 1px solid var(--border);
  border-radius: 6px;
  color: var(--text-primary);
  font-size: 13px;
  font-family: inherit;
  outline: none;
}

[data-module="timesheet"] .ts-de-comment:focus {
  border-color: var(--accent);
}

[data-module="timesheet"] .ts-de-suggest {
  display: none;
  position: absolute;
  top: calc(100% + 4px);
  left: 0;
  right: 0;
  background: var(--panel);
  border: 1px solid var(--border-strong);
  border-radius: 8px;
  box-shadow: 0 6px 20px rgba(0, 0, 0, 0.25);
  max-height: 220px;
  overflow-y: auto;
  z-index: 1;
}

[data-module="timesheet"] .ts-de-suggest.is-open { display: block; }

[data-module="timesheet"] .ts-de-sg-item {
  padding: 6px 10px;
  font-size: 12px;
  color: var(--text-primary);
  cursor: pointer;
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 10px;
}

[data-module="timesheet"] .ts-de-sg-item:hover,
[data-module="timesheet"] .ts-de-sg-item.is-active {
  background: var(--row-hover);
}

[data-module="timesheet"] .ts-de-sg-badge {
  font-size: 9px;
  padding: 1px 6px;
  background: var(--row-hover);
  color: var(--text-tertiary);
  border-radius: 3px;
  text-transform: uppercase;
  letter-spacing: 0.5px;
  font-weight: 700;
  flex-shrink: 0;
}

[data-module="timesheet"] .ts-de-foot {
  display: flex;
  flex-direction: column;
  align-items: stretch;
  gap: 6px;
  margin-top: 2px;
  padding-top: 8px;
  border-top: 1px solid var(--border);
}

/* Action row: compact buttons, right-aligned. Collapses to zero height
   when both buttons are contextually hidden so the footer is just the hint. */
[data-module="timesheet"] .ts-de-actions {
  display: flex;
  justify-content: flex-end;
  gap: 6px;
}
/* Collapse the row entirely when both buttons are contextually hidden, so the
   footer is just the keyboard hint (no empty gap). */
[data-module="timesheet"] .ts-de-actions:not(:has(button:not([hidden]))) {
  display: none;
}

[data-module="timesheet"] .ts-de-apply,
[data-module="timesheet"] .ts-de-clear {
  padding: 3px 9px;
  background: transparent;
  border: 1px solid var(--border);
  border-radius: 5px;
  font-size: 11px;
  font-weight: 600;
  font-family: inherit;
  line-height: 1.4;
  cursor: pointer;
  white-space: nowrap;
}
[data-module="timesheet"] .ts-de-apply[hidden],
[data-module="timesheet"] .ts-de-clear[hidden] {
  display: none;
}

[data-module="timesheet"] .ts-de-apply { color: var(--accent); }
[data-module="timesheet"] .ts-de-apply:hover {
  background: var(--row-hover);
  border-color: var(--accent);
}

[data-module="timesheet"] .ts-de-clear { color: var(--error); }
[data-module="timesheet"] .ts-de-clear:hover {
  background: var(--error-soft);
  border-color: var(--error);
}

[data-module="timesheet"] .ts-de-hint {
  font-size: 10px;
  color: var(--text-tertiary);
  text-align: right;
  white-space: nowrap;
}

/* Add line */
[data-module="timesheet"] .ts-addrow td {
  padding: 6px 16px;
  border-top: 1px dashed var(--border);
}

[data-module="timesheet"] .ts-addrow-btn {
  background: transparent;
  border: none;
  color: var(--text-tertiary);
  font-size: 11px;
  cursor: pointer;
  padding: 2px 0;
  font-family: inherit;
}

[data-module="timesheet"] .ts-addrow-btn:hover {
  color: var(--text-primary);
}

/* Footer totals */
/* Sticky daily-total band. Now that the grid lives inside a --panel card,
   the footer needs its own surface (--panel-2) plus an upward shadow so it
   reads as a pinned band lifting above the rows that scroll under it,
   rather than blending into the card body. */
[data-module="timesheet"] .ts-foot-row {
  background: var(--panel-2);
  position: sticky;
  bottom: 0;
  z-index: 4;
  border-top: 2px solid var(--border-strong);
  box-shadow: 0 -6px 16px -8px var(--overlay-bg);
}

[data-module="timesheet"] .ts-foot-lbl {
  padding: 8px 16px;
  font-size: 10px;
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.5px;
  color: var(--text-secondary);
  border-right: 1px solid var(--border);
}
/* Match the sticky label cell to the footer band -- .ts-sticky otherwise
   paints it --bg (correct for body rows, wrong for the footer band). */
[data-module="timesheet"] .ts-foot-row .ts-foot-lbl.ts-sticky {
  background: var(--panel-2);
}

[data-module="timesheet"] .ts-foot-day {
  text-align: center;
  padding: 6px 4px;
  border-right: 1px solid var(--border);
  vertical-align: middle;
}

/* Today column gets the same accent tint in the footer as in the header. */
[data-module="timesheet"] .ts-foot-day.is-today,
[data-module="timesheet"] .ts-sub-day.is-today {
  background: color-mix(in srgb, var(--accent) 4%, transparent);
}

[data-module="timesheet"] .ts-foot-weekend {
  opacity: 0.6;
}

[data-module="timesheet"] .ts-foot-day-val {
  font-size: 12px;
  font-weight: 700;
}

[data-module="timesheet"] .ts-foot-day-val.is-empty { color: var(--text-tertiary); }
[data-module="timesheet"] .ts-foot-day-val.is-under { color: var(--warning); }
[data-module="timesheet"] .ts-foot-day-val.is-ok    { color: var(--success); }

[data-module="timesheet"] .ts-foot-total {
  text-align: center;
  font-weight: 700;
  color: var(--accent);
  font-size: 14px;
  padding: 6px 4px;
}

/* ── Combobox ────────────────────────────────────────── */
/* Combobox styles are dual-scoped: the picker is opened both from
   inside the module container (grid + dock cells) AND from inside
   a body-mounted ctx.ui.modal overlay (the bulk-paste preview
   inline pickers). Without the .strata-overlay selector pair, the
   modal-context combobox renders unstyled raw HTML -- audit caught
   this on the 1.5.4 polish pass. */
[data-module="timesheet"] .ts-combobox,
.strata-overlay .ts-combobox {
  position: absolute;
  z-index: 9100;
  background: var(--panel);
  border: 1px solid var(--border-strong);
  border-radius: 8px;
  box-shadow: 0 8px 24px rgba(0, 0, 0, 0.25);
  min-width: 220px;
  max-width: 360px;
  display: flex;
  flex-direction: column;
  overflow: hidden;
}

[data-module="timesheet"] .ts-combobox-input,
.strata-overlay .ts-combobox-input {
  padding: 8px 10px;
  background: transparent;
  border: none;
  border-bottom: 1px solid var(--border);
  color: var(--text-primary);
  font-size: 13px;
  font-family: inherit;
  outline: none;
}

[data-module="timesheet"] .ts-combobox-list,
.strata-overlay .ts-combobox-list {
  max-height: 280px;
  overflow-y: auto;
  padding: 4px 0;
}

[data-module="timesheet"] .ts-combobox-empty,
.strata-overlay .ts-combobox-empty {
  padding: 10px 12px;
  color: var(--text-tertiary);
  font-size: 12px;
  font-style: italic;
}

[data-module="timesheet"] .ts-combobox-item,
.strata-overlay .ts-combobox-item {
  padding: 6px 10px;
  display: flex;
  align-items: center;
  gap: 8px;
  font-size: 12px;
  cursor: pointer;
  color: var(--text-primary);
}

/* 3.4 -- section divider between ranked "recent" tasks and the full
   catalog. Non-interactive label row. */
[data-module="timesheet"] .ts-combobox-divider,
.strata-overlay .ts-combobox-divider {
  padding: 6px 10px 3px;
  margin-top: 3px;
  border-top: 1px solid var(--border);
  font-size: 9px;
  font-weight: 700;
  letter-spacing: 0.06em;
  text-transform: uppercase;
  color: var(--text-tertiary);
  cursor: default;
}

[data-module="timesheet"] .ts-combobox-item.is-active,
[data-module="timesheet"] .ts-combobox-item:hover,
.strata-overlay .ts-combobox-item.is-active,
.strata-overlay .ts-combobox-item:hover {
  background: var(--row-hover);
}

[data-module="timesheet"] .ts-combobox-item.is-warn,
.strata-overlay .ts-combobox-item.is-warn {
  color: var(--warning);
}

[data-module="timesheet"] .ts-combobox-item.is-warn::before,
.strata-overlay .ts-combobox-item.is-warn::before {
  content: '!';
  margin-right: 2px;
}

[data-module="timesheet"] .ts-combobox-dot,
.strata-overlay .ts-combobox-dot {
  width: 7px;
  height: 7px;
  border-radius: 50%;
  flex-shrink: 0;
}

[data-module="timesheet"] .ts-combobox-label,
.strata-overlay .ts-combobox-label {
  flex: 1;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}

[data-module="timesheet"] .ts-combobox-hint,
.strata-overlay .ts-combobox-hint {
  font-size: 10px;
  color: var(--text-tertiary);
  font-family: var(--font-mono, monospace);
}

/* ── Day view (mobile / focus) ───────────────────────── */
[data-module="timesheet"] .ts-day-view {
  flex: 1;
  overflow: hidden;
  display: flex;
  flex-direction: column;
  min-height: 0;
}

/* Day tabs: rich label + date + total. Active tab gets a 2px accent
   underline; today gets accent-tinted text even when not active. */
[data-module="timesheet"] .ts-day-tabs {
  display: flex;
  border-bottom: 1px solid var(--border);
  background: var(--panel);
  flex-shrink: 0;
  overflow-x: auto;
}

[data-module="timesheet"] .ts-day-tab {
  flex: 1;
  min-width: 56px;
  padding: 8px 4px 7px;
  background: transparent;
  border: none;
  border-bottom: 2px solid transparent;
  cursor: pointer;
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: 1px;
  font-family: inherit;
  color: var(--text-secondary);
}

[data-module="timesheet"] .ts-day-tab.is-active {
  border-bottom-color: var(--accent);
}

[data-module="timesheet"] .ts-day-tab.is-active .ts-day-tab-lbl,
[data-module="timesheet"] .ts-day-tab.is-active .ts-day-tab-num {
  color: var(--text-primary);
}

[data-module="timesheet"] .ts-day-tab.is-today .ts-day-tab-lbl {
  color: var(--accent);
}

[data-module="timesheet"] .ts-day-tab.is-active.is-today .ts-day-tab-lbl,
[data-module="timesheet"] .ts-day-tab.is-active.is-today .ts-day-tab-num {
  color: var(--accent);
}

[data-module="timesheet"] .ts-day-tab-lbl {
  font-size: 9px;
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.5px;
  line-height: 1;
  color: var(--text-tertiary);
}

[data-module="timesheet"] .ts-day-tab-num {
  font-size: 17px;
  font-weight: 700;
  line-height: 1.15;
  letter-spacing: -0.3px;
  color: var(--text-secondary);
}

[data-module="timesheet"] .ts-day-tab-val {
  font-size: 10px;
  font-weight: 600;
  line-height: 1.4;
  color: var(--text-tertiary);
}

[data-module="timesheet"] .ts-day-tab-val.is-empty { color: var(--text-tertiary); }
[data-module="timesheet"] .ts-day-tab-val.is-under { color: var(--warning); }
[data-module="timesheet"] .ts-day-tab-val.is-ok    { color: var(--success); }

/* Day status bar: full date + today badge + day status (e.g. "1.5h to
   go"). One-line layout, sits under the tab strip. */
[data-module="timesheet"] .ts-day-status {
  padding: 9px 16px 8px;
  border-bottom: 1px solid var(--border);
  flex-shrink: 0;
  display: flex;
  align-items: center;
  gap: 8px;
}

[data-module="timesheet"] .ts-day-status-left {
  display: flex;
  align-items: center;
  gap: 8px;
}

[data-module="timesheet"] .ts-day-status-date {
  font-size: 13px;
  font-weight: 700;
  color: var(--text-primary);
}

[data-module="timesheet"] .ts-day-status-today {
  font-size: 10px;
  font-weight: 700;
  padding: 2px 7px;
  background: color-mix(in srgb, var(--accent) 12%, transparent);
  border: 1px solid color-mix(in srgb, var(--accent) 35%, transparent);
  color: var(--accent);
  border-radius: 5px;
  text-transform: uppercase;
  letter-spacing: 0.5px;
}

[data-module="timesheet"] .ts-day-status-right {
  margin-left: auto;
  font-size: 11px;
  font-weight: 600;
}

[data-module="timesheet"] .ts-day-status-empty   { color: var(--text-tertiary); }
[data-module="timesheet"] .ts-day-status-under   { color: var(--warning); }
[data-module="timesheet"] .ts-day-status-ok      { color: var(--success); }
[data-module="timesheet"] .ts-day-status-neutral { color: var(--text-secondary); }

[data-module="timesheet"] .ts-day-cards {
  flex: 1;
  overflow: auto;
  padding: 10px 12px 16px;
  display: flex;
  flex-direction: column;
  gap: 8px;
}

[data-module="timesheet"] .ts-day-empty {
  padding: 40px 20px;
  text-align: center;
  color: var(--text-tertiary);
  font-size: 13px;
}

/* Entry card: project-color border-left, gentle shadow, larger padding
   to feel touch-friendly. Border-radius is right-side only so the color
   bar runs flush from corner to corner. */
[data-module="timesheet"] .ts-card {
  background: var(--panel);
  border: 1px solid var(--border);
  border-left: 4px solid var(--accent);
  border-radius: 0 12px 12px 0;
  padding: 12px 14px;
  display: flex;
  flex-direction: column;
  gap: 10px;
}

[data-module="timesheet"] .ts-card-head {
  display: flex;
  align-items: center;
  gap: 8px;
  flex-wrap: wrap;
}

[data-module="timesheet"] .ts-card-proj {
  display: inline-flex;
  align-items: center;
  gap: 7px;
  background: transparent;
  border: 0;
  padding: 0;
  color: var(--text-primary);
  font-family: inherit;
  font-size: 13px;
  font-weight: 700;
  cursor: pointer;
  text-align: left;
}

[data-module="timesheet"] .ts-card-proj-dot {
  width: 8px;
  height: 8px;
  border-radius: 50%;
  flex-shrink: 0;
}

[data-module="timesheet"] .ts-card-pinned {
  margin-left: auto;
  font-size: 9px;
  font-weight: 700;
  letter-spacing: 0.6px;
  text-transform: uppercase;
  color: var(--text-tertiary);
}

[data-module="timesheet"] .ts-card-codes {
  display: flex;
  gap: 6px;
  flex-wrap: wrap;
}

[data-module="timesheet"] .ts-chip {
  background: transparent;
  border: 1px solid var(--border);
  border-radius: 5px;
  padding: 3px 8px;
  font-size: 11px;
  font-weight: 700;
  font-family: inherit;
  cursor: pointer;
  color: var(--text-secondary);
  white-space: nowrap;
}

[data-module="timesheet"] .ts-chip-task {
  font-weight: 500;
  color: var(--text-secondary);
}

[data-module="timesheet"] .ts-chip:hover {
  background: var(--row-hover);
}

[data-module="timesheet"] .ts-card-comment {
  width: 100%;
  height: 38px;
  background: var(--input-bg, var(--bg));
  border: 1px solid var(--border);
  border-radius: 8px;
  padding: 0 12px;
  color: var(--text-primary);
  font-size: 13px;
  font-family: inherit;
  outline: none;
}

[data-module="timesheet"] .ts-card-comment:focus {
  border-color: var(--accent);
}

[data-module="timesheet"] .ts-card-comment.is-warn {
  border-color: rgba(251, 191, 36, 0.5);
  background: rgba(251, 191, 36, 0.06);
  color: var(--warning);
}

/* Hour stepper: 44px tall touch row -- minus | value | plus | delete.
   Replaces the previous number input so iOS thumbs can adjust without
   summoning the keyboard. Always 0.25h increments. */
[data-module="timesheet"] .ts-card-stepper {
  display: flex;
  align-items: stretch;
  background: var(--input-bg, var(--bg));
  border: 1px solid var(--border);
  border-radius: 10px;
  height: 44px;
  overflow: hidden;
}

[data-module="timesheet"] .ts-stepper-btn {
  width: 52px;
  flex-shrink: 0;
  display: flex;
  align-items: center;
  justify-content: center;
  background: transparent;
  border: none;
  color: var(--text-secondary);
  font-size: 22px;
  font-weight: 300;
  line-height: 1;
  cursor: pointer;
  font-family: inherit;
  transition: background 0.12s, color 0.12s;
}

[data-module="timesheet"] .ts-stepper-btn:hover:not(:disabled) {
  background: var(--row-hover);
  color: var(--text-primary);
}

[data-module="timesheet"] .ts-stepper-btn:disabled {
  color: var(--text-tertiary);
  cursor: not-allowed;
  opacity: 0.5;
}

[data-module="timesheet"] .ts-stepper-minus {
  border-right: 1px solid var(--border);
}

[data-module="timesheet"] .ts-stepper-plus {
  border-left: 1px solid var(--border);
  color: var(--accent);
}

[data-module="timesheet"] .ts-stepper-plus:hover:not(:disabled) {
  color: var(--accent);
  background: color-mix(in srgb, var(--accent) 8%, transparent);
}

[data-module="timesheet"] .ts-stepper-value {
  flex: 1;
  display: flex;
  align-items: center;
  justify-content: center;
  gap: 4px;
}

[data-module="timesheet"] .ts-stepper-hours {
  font-size: 18px;
  font-weight: 700;
  color: var(--text-primary);
  letter-spacing: -0.3px;
}

[data-module="timesheet"] .ts-stepper-hours:has(+ :empty) {
  color: var(--text-tertiary);
}

[data-module="timesheet"] .ts-stepper-unit {
  font-size: 12px;
  color: var(--text-secondary);
}

[data-module="timesheet"] .ts-card-del {
  width: 44px;
  flex-shrink: 0;
  background: transparent;
  border: none;
  border-left: 1px solid var(--border);
  color: var(--text-tertiary);
  font-size: 18px;
  cursor: pointer;
  font-family: inherit;
  display: flex;
  align-items: center;
  justify-content: center;
}

[data-module="timesheet"] .ts-card-del:hover {
  background: var(--row-hover);
  color: var(--error);
}

/* Add-entry button: dashed CTA at the bottom of the cards list. */
[data-module="timesheet"] .ts-day-add {
  padding: 14px;
  background: transparent;
  border: 1.5px dashed var(--border);
  border-radius: 12px;
  color: var(--text-secondary);
  font-size: 13px;
  font-weight: 600;
  font-family: inherit;
  cursor: pointer;
  display: flex;
  align-items: center;
  justify-content: center;
  gap: 7px;
  width: 100%;
  margin-top: 4px;
  transition: border-color 0.15s, color 0.15s, background 0.15s;
}

[data-module="timesheet"] .ts-day-add:hover {
  border-color: var(--accent);
  color: var(--text-primary);
  background: color-mix(in srgb, var(--accent) 4%, transparent);
}

/* Day-cards scroll region leaves room for the floating dock so the
   last card isn't hidden behind it. Matches .ts-grid-wrap's bottom
   padding. */
[data-module="timesheet"] .ts-day-cards {
  padding-bottom: 96px;
}

/* ── Mobile responsive ───────────────────────────────── */
@media (max-width: 768px) {
  [data-module="timesheet"] .ts-btn-ghost {
    display: none;
  }

  [data-module="timesheet"] .ts-toolbar {
    padding: 8px 12px;
    gap: 8px;
  }
}

@media (max-width: 640px) {
  [data-module="timesheet"] {
    height: calc(100vh - 56px);
  }

  /* Override the outer gutter on phone -- full-bleed is fine at 375px
     and the gutter would just steal grid width. Drop the card chrome too
     so the grid runs edge to edge. */
  .strata-content:has([data-module="timesheet"]) { padding: 0; }
  [data-module="timesheet"] .ts-root { border: 0; border-radius: 0; }

  /* Project col is hidden in day-view, but keep the identity columns
     modest if the grid is shown (e.g. landscape phone). */
  [data-module="timesheet"] .ts-grid .ts-col-project { width: 140px; }
  [data-module="timesheet"] .ts-grid .ts-col-codes   { width: 180px; }
  [data-module="timesheet"] .ts-grid .ts-sticky-2     { left: 140px; }

  [data-module="timesheet"] .ts-total {
    padding-left: 0;
    border-left: none;
  }

  [data-module="timesheet"] .ts-total-val {
    font-size: 20px;
  }

  /* Keep the status pill hidden on phone -- it's a middle-of-toolbar
     chip that competes with the week nav and submit button for space.
     The dock + grand total carry the same information. */
  [data-module="timesheet"] .ts-status {
    display: none;
  }

  [data-module="timesheet"] .ts-submit {
    padding: 8px 12px;
    font-size: 12px;
  }

  /* Make phone-sized inputs avoid iOS zoom (16px) */
  [data-module="timesheet"] .ts-card-comment,
  [data-module="timesheet"] .ts-dock-input,
  [data-module="timesheet"] .ts-dock-comment-input {
    font-size: 16px;
  }
}

/* ── Phase 3 ─────────────────────────────────────────── */

/* H — Empty state: shown above the grid when no hours have been logged
   yet on the current week. Three big CTAs guide the user to the
   fastest path. The grid still renders below (with pinned rows) so
   the empty card never hides the live data structure. */
[data-module="timesheet"] .ts-empty {
  padding: 24px 32px 8px;
  display: flex;
  justify-content: center;
}

[data-module="timesheet"] .ts-empty-card {
  width: 100%;
  max-width: 720px;
  text-align: center;
}

[data-module="timesheet"] .ts-empty-title {
  font-size: 16px;
  font-weight: 700;
  color: var(--text-primary);
  margin-bottom: 4px;
}

[data-module="timesheet"] .ts-empty-sub {
  font-size: 13px;
  color: var(--text-secondary);
  margin-bottom: 16px;
}

[data-module="timesheet"] .ts-empty-actions {
  display: grid;
  grid-template-columns: repeat(3, 1fr);
  gap: 12px;
}

[data-module="timesheet"] .ts-empty-action {
  display: flex;
  flex-direction: column;
  gap: 6px;
  align-items: center;
  padding: 18px 14px;
  background: var(--panel);
  border: 1px solid var(--border);
  border-radius: 10px;
  cursor: pointer;
  font-family: inherit;
  color: var(--text-primary);
  transition: border-color 0.15s, background 0.15s, transform 0.1s;
}

[data-module="timesheet"] .ts-empty-action:hover {
  border-color: var(--accent);
  background: color-mix(in srgb, var(--accent) 6%, transparent);
}

[data-module="timesheet"] .ts-empty-action:active {
  transform: scale(0.98);
}

[data-module="timesheet"] .ts-empty-action-icon {
  font-size: 22px;
  font-weight: 700;
  color: var(--accent);
}

[data-module="timesheet"] .ts-empty-action-title {
  font-size: 14px;
  font-weight: 700;
}

[data-module="timesheet"] .ts-empty-action-sub {
  font-size: 11px;
  color: var(--text-tertiary);
}

@media (max-width: 640px) {
  [data-module="timesheet"] .ts-empty-actions {
    grid-template-columns: 1fr;
  }
}

/* D — Week navigator chip strip in the toolbar. */
[data-module="timesheet"] .ts-week-chips {
  display: flex;
  gap: 4px;
  margin-left: 6px;
  padding-left: 8px;
  border-left: 1px solid var(--border);
}

[data-module="timesheet"] .ts-week-chip {
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: 2px;
  padding: 4px 7px;
  background: transparent;
  border: 1px solid transparent;
  border-radius: 6px;
  cursor: pointer;
  font-family: inherit;
  color: var(--text-secondary);
  font-size: 10px;
  min-width: 40px;
}

[data-module="timesheet"] .ts-week-chip:hover {
  background: var(--row-hover);
  color: var(--text-primary);
}

[data-module="timesheet"] .ts-week-chip.is-current {
  background: color-mix(in srgb, var(--accent) 14%, transparent);
  border-color: var(--accent);
  color: var(--text-primary);
}

[data-module="timesheet"] .ts-week-chip-dot {
  width: 6px;
  height: 6px;
  border-radius: 50%;
  background: var(--text-tertiary);
}

[data-module="timesheet"] .ts-week-chip.is-submitted .ts-week-chip-dot { background: var(--success); }
[data-module="timesheet"] .ts-week-chip.is-submitting .ts-week-chip-dot { background: var(--accent); }
[data-module="timesheet"] .ts-week-chip.is-draft .ts-week-chip-dot { background: var(--warning); }
[data-module="timesheet"] .ts-week-chip.is-error .ts-week-chip-dot { background: var(--error); }
[data-module="timesheet"] .ts-week-chip.is-empty .ts-week-chip-dot { background: var(--border-strong); }

[data-module="timesheet"] .ts-week-chip-date {
  font-weight: 600;
  white-space: nowrap;
}

@media (max-width: 1024px) {
  [data-module="timesheet"] .ts-week-chips { display: none; }
}

/* E — Hover-pin button (overlays the Total cell next to the × delete). */
[data-module="timesheet"] .ts-pin {
  position: absolute;
  top: 50%;
  right: 28px; /* sits to the LEFT of the × delete button */
  transform: translateY(-50%);
  width: 20px;
  height: 20px;
  border: none;
  background: var(--bg);
  color: var(--text-tertiary);
  cursor: pointer;
  opacity: 0;
  border-radius: 4px;
  transition: opacity 0.1s, color 0.1s;
  display: flex;
  align-items: center;
  justify-content: center;
  font-family: inherit;
  padding: 0;
}

[data-module="timesheet"] .ts-row:hover .ts-pin {
  opacity: 1;
}

[data-module="timesheet"] .ts-pin:hover {
  color: var(--accent);
  background: var(--row-hover);
}

[data-module="timesheet"] .ts-pin.is-already {
  color: var(--accent);
  opacity: 0.5;
  cursor: not-allowed;
}

[data-module="timesheet"] .ts-pin.is-already:hover {
  background: transparent;
  color: var(--accent);
}

/* F — Drag-to-fill: tiny corner handle on populated hour cells, plus
   target highlight while dragging. */
[data-module="timesheet"] .ts-fill-handle {
  position: absolute;
  bottom: 1px;
  right: 1px;
  width: 8px;
  height: 8px;
  border: none;
  background: var(--accent);
  cursor: crosshair;
  opacity: 0;
  border-radius: 1px;
  padding: 0;
  z-index: 2;
  transition: opacity 0.1s, transform 0.1s;
}

[data-module="timesheet"] .ts-row:hover .ts-fill-handle {
  opacity: 0.7;
}

[data-module="timesheet"] .ts-fill-handle:hover {
  opacity: 1;
  transform: scale(1.3);
}

[data-module="timesheet"] .ts-hour-wrap.is-fill-target {
  background: color-mix(in srgb, var(--accent) 18%, transparent);
  outline: 2px solid var(--accent);
  outline-offset: -2px;
  border-radius: 5px;
}

/* Suppress fill handle in compact mode (less hover real estate) */
[data-module="timesheet"] .ts-root.is-compact .ts-fill-handle {
  width: 6px;
  height: 6px;
}

/* ── Quick-add dock (floating bottom bar) ─────────────────────────
   Mirrors the fixture-list dock: a position:fixed surface anchored
   to the viewport bottom that swaps between collapsed (FAB) and
   expanded (facet pickers) modes. Idle = single input row with
   placeholder grammar hint. Backdrop blur requires no transform on
   ancestors -- .strata-module-container has none.

   Reserves bottom space on the grid wrap so the last row is never
   hidden behind the dock. */
/* No bottom padding here: a sticky bottom:0 row sticks ABOVE the
   container's bottom padding, so any padding-bottom would float the
   daily-total bar off the true bottom. Dock clearance for the last rows
   comes from the .ts-foot-spacer row instead. */
[data-module="timesheet"] .ts-grid-wrap {
  padding-bottom: 0;
}

/* Spacer row before the daily-total bar -- gives the last grid rows room
   to scroll clear of the floating dock without padding the scroll
   container (which would unpin the sticky total bar). */
[data-module="timesheet"] .ts-foot-spacer td {
  height: 104px;
  border: 0;
  padding: 0;
  background: transparent;
}

/* Day view has no total bar; keep its own bottom clearance for the dock. */
[data-module="timesheet"] .ts-day-cards {
  padding-bottom: 116px;
}

[data-module="timesheet"] .ts-dock {
  position: fixed;
  left: 50%;
  bottom: 52px; /* float above the pinned daily-total bar */
  transform: translateX(-50%);
  width: calc(100% - 48px);
  max-width: 880px;
  background: color-mix(in srgb, var(--panel-2, var(--panel)) 92%, transparent);
  backdrop-filter: saturate(1.2) blur(18px);
  -webkit-backdrop-filter: saturate(1.2) blur(18px);
  border: 1px solid color-mix(in srgb, var(--border-strong) 80%, transparent);
  border-radius: 16px;
  box-shadow:
    0 20px 60px -16px rgba(0, 0, 0, 0.55),
    0 4px 12px -2px rgba(0, 0, 0, 0.35),
    inset 0 1px 0 rgba(255, 255, 255, 0.04);
  z-index: 80;
  overflow: hidden;
  display: flex;
  flex-direction: column;
  transition: box-shadow 180ms ease, transform 180ms ease, opacity 180ms ease;
}

[data-module="timesheet"] .ts-dock-expanded {
  box-shadow:
    0 32px 80px -20px rgba(0, 0, 0, 0.65),
    0 8px 20px -4px rgba(0, 0, 0, 0.40),
    inset 0 1px 0 rgba(255, 255, 255, 0.05);
}

/* Collapsed FAB anchors to bottom-right. */
[data-module="timesheet"] .ts-dock-fab {
  position: fixed;
  left: auto;
  right: 24px;
  bottom: 24px;
  transform: none;
  width: 48px;
  height: 48px;
  padding: 0;
  border-radius: 50%;
  background: var(--accent);
  color: var(--ts-on-accent);
  border: 0;
  box-shadow:
    0 10px 28px -6px rgba(0, 0, 0, 0.55),
    0 3px 8px -2px rgba(0, 0, 0, 0.30);
  cursor: pointer;
  display: inline-flex;
  align-items: center;
  justify-content: center;
}

[data-module="timesheet"] .ts-dock-fab:hover {
  filter: brightness(1.08);
  transform: scale(1.05);
  transition: transform 120ms ease;
}

[data-module="timesheet"] .ts-dock-row {
  display: flex;
  align-items: center;
  gap: 10px;
  padding: 8px 12px;
  min-height: 48px;
}

[data-module="timesheet"] .ts-dock-input-row {
  background: var(--input-bg, var(--bg));
  border-top: 1px solid var(--border);
}

[data-module="timesheet"] .ts-dock:not(.ts-dock-expanded) .ts-dock-input-row {
  border-top: 0;
}

[data-module="timesheet"] .ts-dock-icon {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  color: var(--accent);
  width: 20px;
  height: 20px;
  flex: 0 0 20px;
}

[data-module="timesheet"] .ts-dock-input {
  flex: 1;
  min-width: 0;
  padding: 6px 4px;
  border: 0;
  background: transparent;
  color: var(--text-primary);
  font-size: 14px;
  font-family: inherit;
  outline: none;
}

[data-module="timesheet"] .ts-dock-input::placeholder {
  color: var(--text-tertiary);
}

[data-module="timesheet"] .ts-dock-icon-btn {
  position: relative;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  width: 32px;
  height: 32px;
  padding: 0;
  border: 1px solid transparent;
  background: transparent;
  color: var(--text-secondary);
  border-radius: 8px;
  cursor: pointer;
  font-family: inherit;
}

[data-module="timesheet"] .ts-dock-icon-btn:hover {
  background: var(--row-hover);
  color: var(--text-primary);
}

/* Expansion panel sits above the input row. */
[data-module="timesheet"] .ts-dock-panel {
  padding: 12px 14px;
  border-bottom: 1px solid var(--border);
}

[data-module="timesheet"] .ts-dock-panel-hint {
  font-size: 12px;
  color: var(--text-secondary);
  line-height: 1.6;
}

[data-module="timesheet"] .ts-dock-panel-hint code {
  padding: 1px 5px;
  background: var(--panel);
  border: 1px solid var(--border);
  border-radius: 3px;
  font-family: ui-monospace, monospace;
  font-size: 11px;
  color: var(--text-secondary);
}

[data-module="timesheet"] .ts-dock-panel-hint kbd {
  padding: 1px 5px;
  background: var(--panel);
  border: 1px solid var(--border);
  border-radius: 3px;
  font-family: ui-monospace, monospace;
  font-size: 11px;
  color: var(--text-secondary);
}

@keyframes ts-dock-fade-in {
  from { opacity: 0; transform: translateY(2px); }
  to { opacity: 1; transform: translateY(0); }
}

[data-module="timesheet"] .ts-dock-grid {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 10px 18px;
  animation: ts-dock-fade-in 140ms ease-out;
}

[data-module="timesheet"] .ts-dock-facet {
  display: flex;
  flex-direction: column;
  gap: 5px;
  min-width: 0;
}

/* Comment + Days facets span the full width since chip count varies. */
[data-module="timesheet"] .ts-dock-facet-comment,
[data-module="timesheet"] .ts-dock-facet-days {
  grid-column: 1 / -1;
}

[data-module="timesheet"] .ts-dock-facet-label {
  font-size: 9px;
  font-weight: 700;
  text-transform: uppercase;
  letter-spacing: 0.6px;
  color: var(--text-tertiary);
}

[data-module="timesheet"] .ts-dock-facet-chips {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 5px;
}

/* Facet chip: small toggle-able pill. Active = solid accent fill. */
[data-module="timesheet"] .ts-dock-chip {
  display: inline-flex;
  align-items: center;
  gap: 5px;
  padding: 4px 9px;
  height: 26px;
  background: transparent;
  border: 1px solid var(--border);
  border-radius: 6px;
  color: var(--text-secondary);
  font-size: 11px;
  font-weight: 500;
  font-family: inherit;
  cursor: pointer;
  white-space: nowrap;
  transition: background 0.12s, color 0.12s, border-color 0.12s;
}

[data-module="timesheet"] .ts-dock-chip:hover {
  background: var(--row-hover);
  color: var(--text-primary);
  border-color: var(--border-strong);
}

[data-module="timesheet"] .ts-dock-chip:disabled {
  opacity: 0.45;
  cursor: not-allowed;
}

[data-module="timesheet"] .ts-dock-chip.is-on {
  background: color-mix(in srgb, var(--accent) 18%, transparent);
  color: var(--accent);
  border-color: color-mix(in srgb, var(--accent) 50%, transparent);
}

/* Project chip: dot + name. Inherits chip layout. */
[data-module="timesheet"] .ts-dock-chip-dot {
  width: 7px;
  height: 7px;
  border-radius: 50%;
  flex-shrink: 0;
}

[data-module="timesheet"] .ts-dock-chip-text {
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
  max-width: 140px;
}

/* Picker chips ("Pick project…", "Change…") look more button-like.
   Phase chip pulls its color from the inline --ts-chip-color var
   when set, so the user sees the phase palette at a glance. */
[data-module="timesheet"] .ts-dock-chip-picker {
  border-style: dashed;
  color: var(--text-tertiary);
}

[data-module="timesheet"] .ts-dock-chip-picker.is-on {
  border-style: solid;
}

/* Inferred chips (Phase 1.3): rendered with a softer outline + an inline
   "auto" badge so the user sees what the dock prefilled vs what they
   typed. Mirrors FL dock.js's is-rule treatment. The badge disappears
   as soon as the user clicks the picker (handlers strip the inference
   entry from parsed.inferences). */
[data-module="timesheet"] .ts-dock-chip-picker.is-auto {
  border-style: dashed;
  border-color: color-mix(in srgb, var(--accent) 30%, var(--border));
  background: color-mix(in srgb, var(--accent) 5%, transparent);
}

[data-module="timesheet"] .ts-dock-auto-mark {
  display: inline-block;
  margin-left: 6px;
  padding: 1px 5px;
  font-size: 9px;
  line-height: 1.2;
  letter-spacing: 0.04em;
  text-transform: uppercase;
  color: var(--accent);
  background: color-mix(in srgb, var(--accent) 12%, transparent);
  border-radius: 8px;
  vertical-align: middle;
}

[data-module="timesheet"] .ts-dock-chip-phase {
  font-weight: 700;
}

[data-module="timesheet"] .ts-dock-chip-phase.is-on {
  color: var(--ts-chip-color, var(--accent));
  border-color: color-mix(in srgb, var(--ts-chip-color, var(--accent)) 45%, transparent);
  background: color-mix(in srgb, var(--ts-chip-color, var(--accent)) 14%, transparent);
}

/* Day chips: stacked label (Mon) over date number (22). Today gets
   a subtle accent ring even when not selected. */
[data-module="timesheet"] .ts-dock-chip-day {
  flex-direction: column;
  gap: 0;
  height: auto;
  padding: 4px 9px 5px;
  min-width: 44px;
}

[data-module="timesheet"] .ts-dock-chip-day-lbl {
  font-size: 9px;
  font-weight: 700;
  letter-spacing: 0.5px;
  text-transform: uppercase;
  line-height: 1;
  color: var(--text-tertiary);
}

[data-module="timesheet"] .ts-dock-chip-day-num {
  font-size: 14px;
  font-weight: 700;
  line-height: 1.1;
  color: var(--text-secondary);
  letter-spacing: -0.3px;
}

[data-module="timesheet"] .ts-dock-chip-day:hover .ts-dock-chip-day-lbl,
[data-module="timesheet"] .ts-dock-chip-day:hover .ts-dock-chip-day-num {
  color: var(--text-primary);
}

[data-module="timesheet"] .ts-dock-chip-day.is-on .ts-dock-chip-day-lbl,
[data-module="timesheet"] .ts-dock-chip-day.is-on .ts-dock-chip-day-num {
  color: var(--accent);
}

[data-module="timesheet"] .ts-dock-chip-day.is-today:not(.is-on) {
  border-color: color-mix(in srgb, var(--accent) 30%, var(--border));
}

[data-module="timesheet"] .ts-dock-chip-day.is-today:not(.is-on) .ts-dock-chip-day-lbl {
  color: var(--accent);
}

/* 3.1 -- Recent-row chip strip. Full-width facet above the grid; each
   chip preloads a whole billing row. Tinted to read as a shortcut row,
   distinct from the toggle chips below it. */
[data-module="timesheet"] .ts-dock-facet-recent {
  grid-column: 1 / -1;
}

[data-module="timesheet"] .ts-dock-recent-chip {
  border-style: dashed;
  border-color: color-mix(in srgb, var(--accent) 22%, var(--border));
}

[data-module="timesheet"] .ts-dock-recent-chip:hover {
  background: var(--row-hover);
  border-color: color-mix(in srgb, var(--accent) 45%, var(--border));
  color: var(--text-primary);
}

/* 3.2 -- Chain-add lock. After a Shift+Enter commit the billing facets
   (Project, Phase . Task) stay filled and are ringed so the user sees
   what carries forward. Esc breaks the chain. */
[data-module="timesheet"] .ts-dock-facet.is-chain-locked {
  position: relative;
  padding: 6px;
  margin: -6px;
  border-radius: 8px;
  outline: 1px dashed color-mix(in srgb, var(--accent) 55%, transparent);
  outline-offset: 0;
  background: color-mix(in srgb, var(--accent) 6%, transparent);
}

[data-module="timesheet"] .ts-dock-chain-note {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  font-size: 10px;
  font-weight: 600;
  letter-spacing: 0.03em;
  text-transform: uppercase;
  color: var(--accent);
}

/* Custom-hour input + comment input: full-width inside their facet. */
[data-module="timesheet"] .ts-dock-hour-input {
  width: 80px;
  height: 26px;
  padding: 0 8px;
  background: var(--input-bg, var(--bg));
  border: 1px solid var(--border);
  border-radius: 6px;
  color: var(--text-primary);
  font-size: 12px;
  font-family: inherit;
  outline: none;
}

[data-module="timesheet"] .ts-dock-hour-input:focus {
  border-color: var(--accent);
}

[data-module="timesheet"] .ts-dock-comment-input {
  flex: 1;
  min-width: 0;
  height: 30px;
  padding: 0 10px;
  background: var(--input-bg, var(--bg));
  border: 1px solid var(--border);
  border-radius: 6px;
  color: var(--text-primary);
  font-size: 13px;
  font-family: inherit;
  outline: none;
}

[data-module="timesheet"] .ts-dock-comment-input:focus {
  border-color: var(--accent);
}

[data-module="timesheet"] .ts-dock-warn {
  font-size: 10px;
  color: var(--warning);
  background: rgba(251, 191, 36, 0.1);
  border: 1px solid rgba(251, 191, 36, 0.3);
  border-radius: 5px;
  padding: 2px 7px;
  white-space: nowrap;
}

[data-module="timesheet"] .ts-dock-notes {
  margin-top: 10px;
  display: flex;
  flex-direction: column;
  gap: 4px;
}

[data-module="timesheet"] .ts-dock-note {
  font-size: 11px;
  color: var(--text-secondary);
  padding: 5px 8px;
  background: var(--row-hover);
  border-left: 2px solid var(--accent);
  border-radius: 0 4px 4px 0;
}

/* Footer commit button: spans the whole dock. Disabled until hours set. */
[data-module="timesheet"] .ts-dock-footer {
  padding: 10px 14px;
  border-bottom: 1px solid var(--border);
}

[data-module="timesheet"] .ts-dock-commit {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 12px;
  width: 100%;
  height: 40px;
  padding: 0 14px;
  background: var(--accent);
  color: var(--ts-on-accent);
  border: 0;
  border-radius: 8px;
  font-family: inherit;
  font-size: 13px;
  font-weight: 600;
  cursor: pointer;
  transition: filter 120ms ease, background 120ms ease;
}

[data-module="timesheet"] .ts-dock-commit:hover:not(:disabled) {
  filter: brightness(1.08);
}

[data-module="timesheet"] .ts-dock-commit:disabled {
  background: var(--row-hover);
  color: var(--text-tertiary);
  cursor: not-allowed;
}

[data-module="timesheet"] .ts-dock-commit-label {
  text-align: left;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}

/* Phase 1.4 -- full-row preview inside the commit button. Each segment
   is independently classed so inferred facets render in italics while
   user-typed ones stay roman. The arrow leads the row; separators are
   subtle bullet dots between project / phase / task. */
[data-module="timesheet"] .ts-dock-preview-arrow {
  font-weight: 600;
  margin-right: 6px;
  opacity: 0.9;
}

[data-module="timesheet"] .ts-dock-preview-seg {
  font-weight: 600;
}

[data-module="timesheet"] .ts-dock-preview-seg.is-inferred {
  font-style: italic;
  opacity: 0.92;
}

[data-module="timesheet"] .ts-dock-preview-sep {
  display: inline-block;
  margin: 0 4px;
  opacity: 0.5;
}

/* 3.3 -- multi-day footer mini-cards. One pill per (day, hours) pair. */
[data-module="timesheet"] .ts-dock-minidays {
  display: inline-flex;
  flex-wrap: wrap;
  gap: 4px;
  margin-left: 6px;
  vertical-align: middle;
}

[data-module="timesheet"] .ts-dock-miniday {
  display: inline-flex;
  align-items: baseline;
  gap: 4px;
  padding: 2px 7px;
  border-radius: 6px;
  background: color-mix(in srgb, var(--accent) 16%, transparent);
  border: 1px solid color-mix(in srgb, var(--accent) 40%, transparent);
}

[data-module="timesheet"] .ts-dock-miniday-day {
  font-size: 9px;
  font-weight: 700;
  letter-spacing: 0.5px;
  text-transform: uppercase;
  color: var(--accent);
}

[data-module="timesheet"] .ts-dock-miniday-hrs {
  font-size: 11px;
  font-weight: 700;
  color: var(--text-primary);
}

[data-module="timesheet"] .ts-dock-commit-hint {
  font-weight: 500;
  opacity: 0.85;
}

[data-module="timesheet"] .ts-dock-commit-right {
  font-size: 11px;
  font-weight: 500;
  opacity: 0.85;
  flex-shrink: 0;
}

[data-module="timesheet"] .ts-dock-commit-right kbd {
  padding: 1px 5px;
  background: rgba(255, 255, 255, 0.15);
  border-radius: 3px;
  font-family: ui-monospace, monospace;
  font-size: 10px;
  margin-right: 2px;
}

/* Mobile: collapse the two-column grid + offer chevron toggle to keep
   the input row reachable without scrolling away from the keyboard. */
@media (max-width: 720px) {
  [data-module="timesheet"] .ts-dock-grid {
    grid-template-columns: 1fr;
  }
  [data-module="timesheet"] .ts-dock-quickadd:not([data-panel="open"]) .ts-dock-panel,
  [data-module="timesheet"] .ts-dock-quickadd:not([data-panel="open"]) .ts-dock-footer {
    display: none;
  }
}

[data-module="timesheet"] .ts-dock-quickadd[data-panel="closed"] .ts-dock-panel,
[data-module="timesheet"] .ts-dock-quickadd[data-panel="closed"] .ts-dock-footer {
  display: none;
}

/* --- Bulk paste preview modal: width override ------------------------- */
/* The platform .strata-modal caps at 560px; the bulk preview needs more
   horizontal room for date + project + phase/task + hours + comment in a
   single row. :has() targets only the overlay that holds our preview
   tree, leaving every other modal in the app at its default width.
   Tested in Chromium/Edge/Safari/Firefox 121+ (where :has shipped). */
.strata-overlay:has(.ts-bulk-preview-root) .strata-modal {
  max-width: min(1200px, 95vw);
  width: 1200px;
}

/* --- Bulk paste modal -------------------------------------------------- */
/* Mounted on document.body via ctx.ui.modal, so these rules cannot scope
   under [data-module="timesheet"]. Prefix everything with .ts-bulk- so
   nothing leaks into other modules' content. Tokens are platform-wide
   so both themes inherit without per-theme blocks here. */

.ts-bulk-help {
  margin: 0 0 12px 0;
  color: var(--text-secondary);
  font-size: 13px;
  line-height: 1.5;
}
.ts-bulk-help p {
  margin: 6px 0;
}
.ts-bulk-help .ts-bulk-format {
  margin: 8px 0;
  padding: 8px 10px;
  background: var(--panel-2);
  border: 1px solid var(--border);
  border-radius: 6px;
  font-family: ui-monospace, monospace;
  font-size: 11px;
  white-space: pre;
  overflow-x: auto;
  color: var(--text-primary);
}
.ts-bulk-help .ts-bulk-copy-prompt {
  color: var(--accent);
  text-decoration: none;
  font-weight: 500;
}
.ts-bulk-help .ts-bulk-copy-prompt:hover {
  text-decoration: underline;
}

.ts-bulk-textarea {
  width: 100%;
  min-height: 220px;
  resize: vertical;
  padding: 10px 12px;
  background: var(--panel-2);
  color: var(--text-primary);
  border: 1px solid var(--border);
  border-radius: 6px;
  font-family: ui-monospace, monospace;
  font-size: 12px;
  line-height: 1.45;
  box-sizing: border-box;
  white-space: pre;
}
.ts-bulk-textarea:focus {
  outline: none;
  border-color: var(--accent);
  box-shadow: 0 0 0 3px var(--accent-soft);
}

.ts-bulk-summary {
  display: flex;
  align-items: baseline;
  gap: 12px;
  margin-bottom: 10px;
  color: var(--text-secondary);
  font-size: 12px;
}
.ts-bulk-summary-fmt {
  padding: 2px 8px;
  background: var(--accent-soft);
  color: var(--accent);
  border-radius: 999px;
  font-weight: 500;
  font-size: 11px;
}

.ts-bulk-empty {
  padding: 24px;
  text-align: center;
  color: var(--text-secondary);
  font-style: italic;
}

.ts-bulk-table-wrap {
  max-height: 60vh;
  overflow-y: auto;
  border: 1px solid var(--border);
  border-radius: 6px;
}
.ts-bulk-table {
  width: 100%;
  border-collapse: collapse;
  font-size: 12px;
  color: var(--text-primary);
}
.ts-bulk-table thead th {
  position: sticky;
  top: 0;
  background: var(--panel-2);
  border-bottom: 1px solid var(--border-strong);
  text-align: left;
  font-weight: 500;
  color: var(--text-secondary);
  padding: 8px 10px;
  font-size: 11px;
  text-transform: uppercase;
  letter-spacing: 0.04em;
  z-index: 1;
}
.ts-bulk-table .ts-bulk-th-num {
  text-align: right;
}
.ts-bulk-table tbody td {
  padding: 8px 10px;
  border-bottom: 1px solid var(--border);
  vertical-align: top;
}
.ts-bulk-table tbody tr:last-child td {
  border-bottom: none;
}
.ts-bulk-table tbody tr:hover {
  background: var(--row-hover);
}
.ts-bulk-row.is-blocked {
  opacity: 0.55;
}
.ts-bulk-cell-check {
  width: 28px;
  text-align: center;
}
.ts-bulk-cell-day,
.ts-bulk-cell-hours {
  white-space: nowrap;
}
.ts-bulk-cell-hours {
  text-align: right;
  font-variant-numeric: tabular-nums;
}
.ts-bulk-cell-comment {
  max-width: 320px;
  word-wrap: break-word;
}
.ts-bulk-errors {
  margin-top: 4px;
  color: var(--error);
  font-size: 11px;
}

.ts-bulk-status-pill {
  display: inline-flex;
  align-items: center;
  padding: 2px 8px;
  border-radius: 999px;
  font-size: 11px;
  font-weight: 500;
  white-space: nowrap;
  border: 1px solid transparent;
}
.ts-bulk-status-pill.is-ok {
  background: var(--success-soft);
  color: var(--success);
  border-color: color-mix(in srgb, var(--success) 32%, transparent);
}
.ts-bulk-status-pill.is-inferred {
  background: var(--accent-soft);
  color: var(--accent);
  border-color: var(--accent-line);
}
.ts-bulk-status-pill.is-dup {
  background: var(--warning-soft);
  color: var(--warning);
  border-color: color-mix(in srgb, var(--warning) 32%, transparent);
}
.ts-bulk-status-pill.is-warn {
  background: var(--error-soft);
  color: var(--error);
  border-color: color-mix(in srgb, var(--error) 32%, transparent);
}
/* Multi-week paste destination indicator -- distinct from is-warn so
   the user reads it as "different week" rather than "error". Uses the
   accent tint, dashed border for the "this is going somewhere else"
   cue. */
.ts-bulk-status-pill.is-other-week {
  background: color-mix(in srgb, var(--accent) 12%, transparent);
  color: var(--accent);
  border: 1px dashed color-mix(in srgb, var(--accent) 50%, transparent);
}

.ts-bulk-summary-hint {
  margin-top: 4px;
  margin-bottom: 10px;
  font-size: 11px;
  font-style: italic;
  color: var(--text-tertiary);
}

/* Count pills row in the summary header. Each pill mirrors the section
   stripe colors so the user can connect "47 ready" up top with the
   green-edged "Ready" section row below. */
.ts-bulk-counts {
  display: inline-flex;
  gap: 6px;
  flex-wrap: wrap;
  margin-left: 8px;
}
.ts-bulk-count-pill {
  display: inline-flex;
  align-items: center;
  padding: 2px 9px;
  border-radius: 999px;
  font-size: 11px;
  font-weight: 600;
  white-space: nowrap;
  border: 1px solid transparent;
}
.ts-bulk-count-pill.is-warn {
  background: var(--error-soft);
  color: var(--error);
  border-color: color-mix(in srgb, var(--error) 32%, transparent);
}
.ts-bulk-count-pill.is-inferred {
  background: var(--accent-soft);
  color: var(--accent);
}
.ts-bulk-count-pill.is-dup {
  background: var(--warning-soft);
  color: var(--warning);
}
.ts-bulk-count-pill.is-ok {
  background: var(--success-soft);
  color: var(--success);
}
.ts-bulk-count-pill.is-other-week {
  background: color-mix(in srgb, var(--accent) 12%, transparent);
  color: var(--accent);
}

/* Filter toggle (shown only when there are needs-attention rows). */
.ts-bulk-filter {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  margin-left: auto;
  font-size: 12px;
  color: var(--text-secondary);
  cursor: pointer;
  user-select: none;
}
.ts-bulk-filter input[type="checkbox"] {
  margin: 0;
  cursor: pointer;
}

/* Section header row spans the full table width. Visually distinct
   from data rows (slightly larger, no left stripe, subtle bg tint).
   The toggle button covers the label/count/chev so a click anywhere
   on the header expands/collapses the bucket. */
.ts-bulk-section {
  background: var(--panel-2);
}
.ts-bulk-section-cell {
  padding: 6px 10px !important;
  border-bottom: 1px solid var(--border-strong) !important;
}
.ts-bulk-section-toggle {
  display: inline-flex;
  align-items: center;
  gap: 8px;
  background: none;
  border: none;
  padding: 4px 6px;
  margin: 0;
  font-family: inherit;
  font-size: 12px;
  font-weight: 600;
  color: var(--text-primary);
  cursor: pointer;
  border-radius: 4px;
}
.ts-bulk-section-toggle:hover {
  background: var(--row-hover, var(--panel));
}
.ts-bulk-section-chev {
  display: inline-flex;
  width: 12px;
  font-size: 10px;
  color: var(--text-tertiary);
}
.ts-bulk-section-label {
  text-transform: uppercase;
  letter-spacing: 0.04em;
}
.ts-bulk-section-count {
  padding: 1px 6px;
  background: var(--bg);
  border-radius: 999px;
  font-size: 10px;
  font-weight: 600;
  color: var(--text-secondary);
}
.ts-bulk-section-selcount {
  font-size: 11px;
  font-weight: 500;
  font-style: italic;
  color: var(--accent);
  margin-left: 4px;
}
.ts-bulk-section.is-needs .ts-bulk-section-label { color: var(--error); }
.ts-bulk-section.is-inf .ts-bulk-section-label   { color: color-mix(in srgb, var(--accent) 70%, var(--text-tertiary)); }
.ts-bulk-section.is-other .ts-bulk-section-label { color: var(--accent); }
.ts-bulk-section.is-dup .ts-bulk-section-label   { color: var(--warning); }
.ts-bulk-section.is-ok .ts-bulk-section-label    { color: var(--success); }

.ts-bulk-section-actions {
  display: inline-flex;
  gap: 6px;
  margin-left: 12px;
}
.ts-bulk-section-action {
  display: inline-flex;
  align-items: center;
  height: 22px;
  padding: 0 8px;
  border: 1px solid var(--border);
  background: var(--bg);
  border-radius: 4px;
  color: var(--text-secondary);
  font-size: 11px;
  font-weight: 500;
  font-family: inherit;
  cursor: pointer;
}
.ts-bulk-section-action:hover {
  background: var(--row-hover, var(--panel));
  border-color: var(--border-strong);
  color: var(--text-primary);
}

/* Per-row left stripe encodes status without a dedicated column. */
.ts-bulk-row.is-stripe-warn        td:first-child { box-shadow: inset 3px 0 0 var(--error); }
.ts-bulk-row.is-stripe-other-week  td:first-child { box-shadow: inset 3px 0 0 var(--accent); }
.ts-bulk-row.is-stripe-inferred    td:first-child { box-shadow: inset 3px 0 0 color-mix(in srgb, var(--accent) 70%, var(--text-tertiary)); }
.ts-bulk-row.is-stripe-dup         td:first-child { box-shadow: inset 3px 0 0 var(--warning); }
.ts-bulk-row.is-stripe-ok          td:first-child { box-shadow: inset 3px 0 0 var(--success); }

/* Single-line comment row holds the optional warn-pill on the left and
   the comment text on the right. Used only for needs-attention rows;
   inferred/duplicate/ok render the comment alone. */
.ts-bulk-comment-row {
  display: flex;
  align-items: center;
  gap: 8px;
}
.ts-bulk-comment-text {
  flex: 1;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}

/* Codes cell: phase + task chips inline, no wrap. Long task names get
   truncated by .ts-bulk-chip's max-width + ellipsis. */
.ts-bulk-codes {
  display: inline-flex;
  gap: 4px;
  flex-wrap: nowrap;
  align-items: center;
  max-width: 240px;
}
.ts-bulk-table .ts-bulk-chip {
  max-width: 200px;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}

/* Detailed-prompt link styled differently from the generic one so the
   user can tell the two options apart at a glance. */
.ts-bulk-help .ts-bulk-copy-prompt.is-detailed {
  color: var(--accent);
  border-bottom: 1px dashed currentColor;
}

.ts-bulk-codes {
  display: inline-flex;
  gap: 4px;
  flex-wrap: wrap;
}

.ts-bulk-chip {
  display: inline-flex;
  align-items: center;
  padding: 3px 8px;
  background: var(--panel-2);
  border: 1px solid var(--border-strong);
  border-radius: 4px;
  font-size: 11px;
  font-weight: 500;
  color: var(--text-primary);
  cursor: pointer;
  font-family: inherit;
  white-space: nowrap;
  transition: border-color 120ms ease, background 120ms ease;
}
.ts-bulk-chip:hover:not(:disabled) {
  border-color: var(--accent);
  background: var(--accent-soft);
}
.ts-bulk-chip:focus {
  outline: none;
  border-color: var(--accent);
  box-shadow: 0 0 0 2px var(--accent-soft);
}
.ts-bulk-chip.is-empty {
  color: var(--text-tertiary);
  font-style: italic;
}
.ts-bulk-chip.is-warn {
  border-color: color-mix(in srgb, var(--error) 40%, transparent);
  background: var(--error-soft);
  color: var(--error);
}
.ts-bulk-chip.is-disabled,
.ts-bulk-chip:disabled {
  opacity: 0.55;
  cursor: not-allowed;
}

/* Toolbar + dock entry-point buttons (these DO scope under the
   timesheet module since they live inside the module container). */
[data-module="timesheet"] .ts-bulk-paste-btn {
  /* Inherits .ts-btn-ghost styling already; no overrides needed. */
}
[data-module="timesheet"] .ts-dock-icon-btn[data-action="ts-dock-bulk-paste"] svg {
  width: 14px;
  height: 14px;
}

/* ── Auto-fill review banner ──────────────────────────────────────
   Slim strip between the toolbar and the grid. Announces the unreviewed
   auto-fill count by source; the whole strip is tappable to open the
   review rail. Both themes resolve from accent tokens. */
[data-module="timesheet"] .ts-review-banner {
  display: flex;
  align-items: center;
  gap: 10px;
  padding: 8px 16px;
  background: var(--accent-soft);
  border-bottom: 1px solid var(--accent-line);
  flex-shrink: 0;
  flex-wrap: wrap;
  cursor: pointer;
}
[data-module="timesheet"] .ts-review-banner:hover {
  background: color-mix(in srgb, var(--accent) 10%, transparent);
}
[data-module="timesheet"] .ts-review-banner-count {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  min-width: 20px;
  height: 20px;
  padding: 0 6px;
  border-radius: 10px;
  background: var(--accent);
  color: var(--ts-on-accent);
  font-size: 11px;
  font-weight: 700;
  flex-shrink: 0;
}
[data-module="timesheet"] .ts-review-banner-label {
  font-size: 12px;
  font-weight: 600;
  color: var(--accent);
}
[data-module="timesheet"] .ts-review-banner-sources {
  flex: 1;
  display: flex;
  gap: 6px;
  flex-wrap: wrap;
  min-width: 0;
}
[data-module="timesheet"] .ts-review-banner-source {
  display: inline-flex;
  align-items: center;
  gap: 4px;
  padding: 2px 8px;
  border-radius: 10px;
  background: var(--panel);
  border: 1px solid var(--accent-line);
  font-size: 11px;
  color: var(--text-primary);
  white-space: nowrap;
}
[data-module="timesheet"] .ts-review-banner-source-dot {
  width: 6px;
  height: 6px;
  border-radius: 50%;
}
[data-module="timesheet"] .ts-review-banner-source strong {
  font-weight: 700;
}
[data-module="timesheet"] .ts-review-banner-actions {
  display: flex;
  gap: 6px;
  margin-left: auto;
  flex-shrink: 0;
}
[data-module="timesheet"] .ts-review-banner-btn {
  padding: 5px 12px;
  border-radius: 6px;
  font-size: 11px;
  font-weight: 600;
  font-family: inherit;
  cursor: pointer;
  white-space: nowrap;
  touch-action: manipulation;
}
[data-module="timesheet"] .ts-review-banner-btn.is-primary {
  background: var(--accent);
  color: var(--ts-on-accent);
  border: 0;
}
[data-module="timesheet"] .ts-review-banner-btn.is-primary:hover {
  filter: brightness(1.08);
}
[data-module="timesheet"] .ts-review-banner-btn.is-secondary {
  background: transparent;
  border: 1px solid var(--accent-line);
  color: var(--accent);
}
[data-module="timesheet"] .ts-review-banner-btn.is-secondary:hover {
  background: var(--accent-soft);
}

/* Collapse the banner on phone -- the day view is too narrow for the
   source chips and both buttons. Keep the count + label + single
   Review button. */
@media (max-width: 640px) {
  [data-module="timesheet"] .ts-review-banner-sources { display: none; }
  [data-module="timesheet"] .ts-review-banner-actions .is-secondary { display: none; }
  [data-module="timesheet"] .ts-review-banner-actions { margin-left: 0; }
}

/* ── Auto-fill review rail (slide-over) ───────────────────────────
   A module-internal slide-over: the wrapper renders inside the module
   container (no transformed ancestor, so position:fixed is viewport-
   relative). Sits above the floating dock (z 80) and below the day-
   editor combobox (z 9100). Below 640px it becomes a bottom sheet. */
[data-module="timesheet"] .ts-review-rail-backdrop {
  display: none;
  position: fixed;
  inset: 0;
  background: var(--overlay-bg);
  z-index: 90;
}
[data-module="timesheet"] .ts-review-rail[data-open="true"] .ts-review-rail-backdrop {
  display: block;
}

[data-module="timesheet"] .ts-review-rail-panel {
  position: fixed;
  top: 56px; /* below the platform topbar (matches the module's 100vh - 56px) */
  right: 0;
  bottom: 0;
  width: 360px;
  background: var(--panel);
  border-left: 1px solid var(--border);
  display: flex;
  flex-direction: column;
  z-index: 91;
  transform: translateX(100%);
  transition: transform 220ms cubic-bezier(0.4, 0, 0.2, 1);
  box-shadow: var(--shadow-lg);
  overflow: hidden;
}
[data-module="timesheet"] .ts-review-rail[data-open="true"] .ts-review-rail-panel {
  transform: translateX(0);
}

[data-module="timesheet"] .ts-review-rail-head {
  padding: 14px 16px 0;
  border-bottom: 1px solid var(--border);
  flex-shrink: 0;
  position: relative;
}
[data-module="timesheet"] .ts-review-rail-title {
  font-size: 14px;
  font-weight: 700;
  letter-spacing: -0.01em;
  display: flex;
  align-items: center;
  gap: 8px;
  padding-right: 32px;
  color: var(--text-primary);
}
[data-module="timesheet"] .ts-review-rail-pip {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  min-width: 20px;
  height: 18px;
  padding: 0 6px;
  border-radius: 9px;
  background: var(--accent-soft);
  color: var(--accent);
  font-size: 11px;
  font-weight: 700;
}
[data-module="timesheet"] .ts-review-rail-sub {
  font-size: 11px;
  color: var(--text-secondary);
  margin-top: 4px;
  line-height: 1.45;
  padding-bottom: 10px;
}
[data-module="timesheet"] .ts-review-rail-close {
  position: absolute;
  top: 12px;
  right: 14px;
  width: 28px;
  height: 28px;
  border-radius: 6px;
  background: transparent;
  border: 1px solid var(--border);
  color: var(--text-secondary);
  display: inline-flex;
  align-items: center;
  justify-content: center;
  cursor: pointer;
  font-family: inherit;
}
[data-module="timesheet"] .ts-review-rail-close:hover {
  background: var(--row-hover);
  color: var(--text-primary);
}

[data-module="timesheet"] .ts-review-rail-tabs {
  display: flex;
  margin: 8px -16px 0;
  padding: 0 16px;
  border-top: 1px solid var(--border);
}
[data-module="timesheet"] .ts-review-rail-tab {
  font-size: 11.5px;
  color: var(--text-secondary);
  padding: 8px 0;
  margin-right: 18px;
  border: 0;
  background: transparent;
  border-bottom: 2px solid transparent;
  cursor: pointer;
  font-family: inherit;
  white-space: nowrap;
}
[data-module="timesheet"] .ts-review-rail-tab.is-on {
  color: var(--text-primary);
  border-bottom-color: var(--accent);
  font-weight: 600;
}
[data-module="timesheet"] .ts-review-rail-tab:hover:not(.is-on) {
  color: var(--text-primary);
}

[data-module="timesheet"] .ts-review-rail-body {
  flex: 1;
  overflow-y: auto;
  padding: 10px 12px 24px;
  display: flex;
  flex-direction: column;
  gap: 10px;
}
[data-module="timesheet"] .ts-review-rail-empty {
  font-size: 12px;
  color: var(--text-tertiary);
  text-align: center;
  padding: 28px 12px;
}

[data-module="timesheet"] .ts-review-card {
  border: 1px solid var(--border);
  border-radius: 10px;
  background: var(--panel-2);
  padding: 10px 12px 12px;
  position: relative;
}
[data-module="timesheet"] .ts-review-card::before {
  content: '';
  position: absolute;
  left: 0;
  top: 10px;
  bottom: 10px;
  width: 3px;
  background: var(--rc-color, var(--accent));
  border-radius: 0 3px 3px 0;
}
[data-module="timesheet"] .ts-review-card-head {
  display: flex;
  align-items: baseline;
  gap: 8px;
  margin-bottom: 4px;
}
[data-module="timesheet"] .ts-review-card-project {
  font-size: 12.5px;
  font-weight: 600;
  color: var(--text-primary);
  flex: 1;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}
[data-module="timesheet"] .ts-review-card-day {
  font-size: 10px;
  color: var(--text-tertiary);
  text-transform: uppercase;
  letter-spacing: 0.06em;
  font-variant-numeric: tabular-nums;
  flex-shrink: 0;
}
[data-module="timesheet"] .ts-review-card-codes {
  font-size: 11.5px;
  color: var(--text-secondary);
  display: flex;
  align-items: center;
  gap: 6px;
  flex-wrap: wrap;
  margin-bottom: 8px;
}
[data-module="timesheet"] .ts-review-card-phase {
  display: inline-flex;
  align-items: center;
  padding: 2px 6px;
  border-radius: 4px;
  border: 1px solid color-mix(in srgb, var(--ts-chip-color, var(--text-secondary)) 35%, var(--border));
  font-weight: 700;
  font-size: 10.5px;
  color: var(--ts-chip-color, var(--text-secondary));
}
[data-module="timesheet"] .ts-review-card-source-pip {
  display: inline-flex;
  align-items: center;
  gap: 4px;
  padding: 2px 7px;
  border-radius: 10px;
  background: var(--bg);
  border: 1px solid var(--border);
  font-size: 10.5px;
  color: var(--text-secondary);
  margin-left: auto;
}
[data-module="timesheet"] .ts-review-card-source-dot {
  width: 5px;
  height: 5px;
  border-radius: 50%;
}
[data-module="timesheet"] .ts-review-card-hours {
  display: inline-flex;
  align-items: baseline;
  gap: 4px;
  margin-bottom: 4px;
}
[data-module="timesheet"] .ts-review-card-h-val {
  font-size: 20px;
  font-weight: 700;
  letter-spacing: -0.01em;
  color: var(--text-primary);
  font-variant-numeric: tabular-nums;
}
[data-module="timesheet"] .ts-review-card-h-unit {
  font-size: 11px;
  color: var(--text-tertiary);
}
[data-module="timesheet"] .ts-review-card-evidence {
  background: var(--bg);
  border: 1px solid var(--border);
  border-radius: 6px;
  padding: 6px 8px;
  font-size: 11.5px;
  color: var(--text-secondary);
  line-height: 1.4;
  margin-top: 6px;
}
[data-module="timesheet"] .ts-review-card-evidence strong {
  color: var(--text-primary);
  font-weight: 600;
  display: block;
}
[data-module="timesheet"] .ts-review-card-evidence em {
  color: var(--text-tertiary);
  font-style: normal;
  font-size: 10.5px;
  margin-top: 2px;
  display: block;
}
[data-module="timesheet"] .ts-review-card-actions {
  display: flex;
  gap: 6px;
  margin-top: 10px;
  align-items: center;
}
[data-module="timesheet"] .ts-review-card-btn {
  padding: 5px 12px;
  border-radius: 6px;
  font-size: 11px;
  font-weight: 600;
  font-family: inherit;
  cursor: pointer;
  white-space: nowrap;
  touch-action: manipulation;
  min-height: 30px;
}
[data-module="timesheet"] .ts-review-card-btn.is-approve {
  background: var(--accent);
  color: var(--ts-on-accent);
  border: 0;
}
[data-module="timesheet"] .ts-review-card-btn.is-approve:hover { filter: brightness(1.08); }
[data-module="timesheet"] .ts-review-card-btn.is-edit {
  background: transparent;
  border: 1px solid var(--border);
  color: var(--text-secondary);
}
[data-module="timesheet"] .ts-review-card-btn.is-edit:hover {
  border-color: var(--accent-line);
  color: var(--accent);
}
[data-module="timesheet"] .ts-review-card-btn.is-dismiss {
  background: transparent;
  border: 0;
  color: var(--text-tertiary);
  margin-left: auto;
  font-weight: 400;
  text-decoration: underline dotted;
  text-underline-offset: 3px;
  padding: 5px 4px;
}
[data-module="timesheet"] .ts-review-card-btn.is-dismiss:hover {
  color: var(--error);
}

/* Phone: the panel becomes a bottom sheet. */
@media (max-width: 640px) {
  [data-module="timesheet"] .ts-review-rail-panel {
    top: auto;
    left: 0;
    right: 0;
    bottom: 0;
    width: 100%;
    max-height: 70vh;
    border-left: 0;
    border-top: 1px solid var(--border);
    border-radius: 16px 16px 0 0;
    transform: translateY(100%);
  }
  [data-module="timesheet"] .ts-review-rail[data-open="true"] .ts-review-rail-panel {
    transform: translateY(0);
  }
}

/* Learned-shortcuts (Phase 4.4) -- toolbar button + count badge live
   inside the module container; the panel below is rendered into the
   platform modal (mounted on document.body), so its selectors are NOT
   scoped to [data-module]. All colors use theme tokens, so both themes
   resolve without a separate light block. */
[data-module="timesheet"] .ts-learned-badge {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  min-width: 16px;
  height: 16px;
  padding: 0 5px;
  margin-left: 4px;
  border-radius: 8px;
  background: var(--accent);
  color: var(--ts-on-accent);
  font-size: 11px;
  font-weight: 600;
  line-height: 1;
}

.ts-learned-panel .ts-ls-section {
  margin-bottom: 18px;
}
.ts-learned-panel .ts-ls-section:last-child {
  margin-bottom: 0;
}
.ts-learned-panel .ts-ls-head {
  margin: 0 0 8px;
  font-size: 12px;
  font-weight: 600;
  text-transform: uppercase;
  letter-spacing: 0.04em;
  color: var(--text-tertiary);
}
.ts-learned-panel .ts-ls-empty {
  margin: 0;
  font-size: 13px;
  color: var(--text-tertiary);
}
.ts-learned-panel .ts-ls-list {
  list-style: none;
  margin: 0;
  padding: 0;
  display: flex;
  flex-direction: column;
  gap: 6px;
}
.ts-learned-panel .ts-ls-item {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 12px;
  padding: 8px 10px;
  border: 1px solid var(--border);
  border-radius: 8px;
  background: var(--panel-2);
}
.ts-learned-panel .ts-ls-info {
  display: flex;
  flex-direction: column;
  gap: 2px;
  min-width: 0;
}
.ts-learned-panel .ts-ls-phrase {
  font-size: 14px;
  font-weight: 600;
  color: var(--text-primary);
}
.ts-learned-panel .ts-ls-map {
  font-size: 12px;
  color: var(--text-secondary);
}
.ts-learned-panel .ts-ls-count {
  font-size: 11px;
  color: var(--text-tertiary);
}
.ts-learned-panel .ts-ls-actions {
  display: flex;
  gap: 6px;
  flex-shrink: 0;
}
.ts-learned-panel .ts-ls-actions .ts-btn-ghost {
  padding: 4px 10px;
  font-size: 13px;
  border: 1px solid var(--border);
  border-radius: 6px;
  background: var(--panel);
  color: var(--text-secondary);
  cursor: pointer;
}
.ts-learned-panel .ts-ls-actions .ts-btn-ghost:hover {
  background: var(--row-hover);
  color: var(--text-primary);
  border-color: var(--border-strong);
}

/* ── Persistent "Review (N)" toolbar button (R13) ──────────────────── */
[data-module="timesheet"] .ts-review-btn {
  display: inline-flex;
  align-items: center;
  gap: 6px;
}
[data-module="timesheet"] .ts-review-btn-badge {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  min-width: 18px;
  height: 18px;
  padding: 0 5px;
  border-radius: 9px;
  background: var(--accent);
  color: var(--ts-on-accent);
  font-size: 11px;
  font-weight: 700;
}
[data-module="timesheet"] .ts-review-btn.is-clear {
  color: var(--success);
}

/* ── Deltek manual-entry walkthrough (R13) ─────────────────────────────
   Centered modal rendered inside the module container (no transformed
   ancestor, so position:fixed is viewport-relative). Backdrop z 90 / panel
   z 91 -- same band as the review rail. Becomes a bottom sheet under 640px. */
[data-module="timesheet"] .ts-deltek-backdrop {
  position: fixed;
  inset: 0;
  background: var(--overlay-bg);
  z-index: 90;
}
[data-module="timesheet"] .ts-deltek-panel {
  position: fixed;
  top: 50%;
  left: 50%;
  transform: translate(-50%, -50%);
  width: min(540px, calc(100vw - 32px));
  max-height: calc(100vh - 96px);
  background: var(--panel);
  border: 1px solid var(--border);
  border-radius: var(--panel-radius);
  box-shadow: var(--shadow-lg);
  z-index: 91;
  display: flex;
  flex-direction: column;
  overflow: hidden;
}
[data-module="timesheet"] .ts-dw-head {
  padding: 16px 18px 12px;
  border-bottom: 1px solid var(--border);
  position: relative;
  flex-shrink: 0;
}
[data-module="timesheet"] .ts-dw-title {
  font-size: 15px;
  font-weight: 700;
  letter-spacing: -0.01em;
  color: var(--text-primary);
  padding-right: 32px;
}
[data-module="timesheet"] .ts-dw-sub {
  font-size: 11.5px;
  color: var(--text-secondary);
  margin-top: 4px;
  line-height: 1.45;
  padding-right: 32px;
}
[data-module="timesheet"] .ts-dw-close {
  position: absolute;
  top: 14px;
  right: 16px;
  width: 28px;
  height: 28px;
  border-radius: 6px;
  background: transparent;
  border: 1px solid var(--border);
  color: var(--text-secondary);
  display: inline-flex;
  align-items: center;
  justify-content: center;
  cursor: pointer;
  font-family: inherit;
}
[data-module="timesheet"] .ts-dw-close:hover {
  background: var(--row-hover);
  color: var(--text-primary);
}
[data-module="timesheet"] .ts-dw-progress {
  height: 4px;
  background: var(--row-alt);
  flex-shrink: 0;
}
[data-module="timesheet"] .ts-dw-progress-fill {
  height: 100%;
  background: var(--accent);
  transition: width 200ms ease;
}
[data-module="timesheet"] .ts-dw-progress-lbl {
  font-size: 11px;
  color: var(--text-tertiary);
  padding: 6px 18px 0;
  flex-shrink: 0;
}
[data-module="timesheet"] .ts-dw-body {
  padding: 14px 18px;
  overflow-y: auto;
  flex: 1;
}
[data-module="timesheet"] .ts-dw-step {
  font-size: 11px;
  font-weight: 600;
  color: var(--text-tertiary);
  text-transform: uppercase;
  letter-spacing: 0.04em;
  margin-bottom: 8px;
}
[data-module="timesheet"] .ts-dw-card {
  border: 1px solid var(--border);
  border-radius: var(--button-radius);
  background: var(--panel-2);
  padding: 14px;
}
[data-module="timesheet"] .ts-dw-codes {
  display: flex;
  flex-direction: column;
  gap: 8px;
}
[data-module="timesheet"] .ts-dw-code {
  display: flex;
  align-items: baseline;
  gap: 8px;
}
[data-module="timesheet"] .ts-dw-code-k {
  font-size: 10.5px;
  text-transform: uppercase;
  letter-spacing: 0.04em;
  color: var(--text-tertiary);
  width: 44px;
  flex-shrink: 0;
}
[data-module="timesheet"] .ts-dw-code-v {
  font-size: 16px;
  font-weight: 700;
  color: var(--text-primary);
  font-variant-numeric: tabular-nums;
}
[data-module="timesheet"] .ts-dw-code-n {
  font-size: 12px;
  color: var(--text-secondary);
}
[data-module="timesheet"] .ts-dw-days {
  display: grid;
  grid-template-columns: repeat(7, 1fr);
  gap: 4px;
  margin-top: 14px;
}
[data-module="timesheet"] .ts-dw-day {
  text-align: center;
  padding: 6px 2px;
  border-radius: 6px;
  background: var(--row-alt);
  opacity: 0.5;
}
[data-module="timesheet"] .ts-dw-day.has-hours {
  opacity: 1;
  background: var(--accent-soft);
}
[data-module="timesheet"] .ts-dw-day-lbl {
  display: block;
  font-size: 9.5px;
  text-transform: uppercase;
  color: var(--text-tertiary);
}
[data-module="timesheet"] .ts-dw-day-val {
  display: block;
  font-size: 12.5px;
  font-weight: 700;
  color: var(--text-primary);
  font-variant-numeric: tabular-nums;
  margin-top: 2px;
}
[data-module="timesheet"] .ts-dw-day.has-hours .ts-dw-day-val {
  color: var(--accent);
}
[data-module="timesheet"] .ts-dw-comments {
  margin-top: 12px;
  display: flex;
  flex-direction: column;
  gap: 6px;
}
[data-module="timesheet"] .ts-dw-comment {
  font-size: 12px;
  color: var(--text-secondary);
  line-height: 1.4;
}
[data-module="timesheet"] .ts-dw-comment-day {
  font-weight: 700;
  color: var(--text-tertiary);
  margin-right: 6px;
}
[data-module="timesheet"] .ts-dw-total {
  margin-top: 14px;
  padding-top: 10px;
  border-top: 1px solid var(--border);
  font-size: 12px;
  color: var(--text-secondary);
}
[data-module="timesheet"] .ts-dw-total strong {
  color: var(--text-primary);
  font-variant-numeric: tabular-nums;
}
[data-module="timesheet"] .ts-dw-empty,
[data-module="timesheet"] .ts-dw-done {
  text-align: center;
  padding: 24px 8px;
  color: var(--text-secondary);
}
[data-module="timesheet"] .ts-dw-done-check {
  font-size: 32px;
  color: var(--success);
  line-height: 1;
}
[data-module="timesheet"] .ts-dw-done-msg {
  font-size: 14px;
  font-weight: 700;
  color: var(--text-primary);
  margin-top: 10px;
}
[data-module="timesheet"] .ts-dw-done-sub {
  font-size: 12px;
  margin-top: 6px;
}
[data-module="timesheet"] .ts-dw-foot {
  padding: 12px 18px;
  border-top: 1px solid var(--border);
  flex-shrink: 0;
  display: flex;
  flex-direction: column;
  gap: 10px;
}
[data-module="timesheet"] .ts-dw-nav {
  display: flex;
  align-items: center;
  gap: 8px;
}
[data-module="timesheet"] .ts-dw-nav-spacer {
  flex: 1;
}
[data-module="timesheet"] .ts-dw-btn {
  font-size: 12px;
  padding: 7px 12px;
  border-radius: var(--button-radius);
  border: 1px solid var(--border);
  background: var(--panel);
  color: var(--text-secondary);
  cursor: pointer;
  font-family: inherit;
}
[data-module="timesheet"] .ts-dw-btn:hover {
  background: var(--row-hover);
  color: var(--text-primary);
}
[data-module="timesheet"] .ts-dw-btn.is-step {
  background: var(--accent-soft);
  color: var(--accent);
  border-color: transparent;
  font-weight: 600;
}
[data-module="timesheet"] .ts-dw-confirm {
  width: 100%;
}
[data-module="timesheet"] .ts-dw-confirm-hint {
  font-size: 11px;
  color: var(--text-tertiary);
  text-align: center;
}
@media (max-width: 640px) {
  [data-module="timesheet"] .ts-deltek-panel {
    top: auto;
    bottom: 0;
    left: 0;
    transform: none;
    width: 100%;
    max-height: 88vh;
    border-radius: var(--panel-radius) var(--panel-radius) 0 0;
  }
  [data-module="timesheet"] .ts-dw-days {
    grid-template-columns: repeat(4, 1fr);
  }
}

/* ============================================================
   Sent-mail time suggestions (fb_1781039359) -- consent card +
   preview-and-select modal. Body-mounted modal content is NOT under
   [data-module="timesheet"]; scope on .ts-se-* classes instead. Tokens
   only, so both themes are covered by the platform's token switch.
   ============================================================ */
.ts-se-consent .ts-se-lead { margin: 0 0 0.75rem; color: var(--text-primary); }
.ts-se-privacy {
  margin: 0 0 0.75rem;
  padding-left: 1.1rem;
  color: var(--text-secondary);
  line-height: 1.5;
}
.ts-se-privacy li { margin: 0.35rem 0; }
.ts-se-note {
  margin: 0;
  font-size: 0.85rem;
  color: var(--text-tertiary);
}

.ts-se-hint { margin: 0 0 0.6rem; color: var(--text-secondary); font-size: 0.9rem; }
.ts-se-empty { padding: 1rem 0; color: var(--text-tertiary); }

.ts-se-table { width: 100%; border-collapse: collapse; font-size: 0.9rem; }
.ts-se-table thead th {
  text-align: left;
  padding: 0.35rem 0.5rem;
  color: var(--text-tertiary);
  font-weight: 600;
  border-bottom: 1px solid var(--border);
}
.ts-se-table td { padding: 0.4rem 0.5rem; border-bottom: 1px solid var(--border); color: var(--text-primary); }
.ts-se-row.is-covered { opacity: 0.5; }
.ts-se-row.is-dismissed { opacity: 0.4; text-decoration: line-through; }
.ts-se-c-check { width: 1.5rem; }
.ts-se-c-hrs { white-space: nowrap; color: var(--text-secondary); }
.ts-se-c-ev { color: var(--text-secondary); }

.ts-se-covered-badge {
  margin-left: 0.4rem;
  padding: 0.05rem 0.35rem;
  border-radius: 4px;
  border: 1px solid var(--border);
  color: var(--text-tertiary);
  font-size: 0.72rem;
}

/* Confidence pip: a small dot before the evidence label. */
.ts-se-tier {
  display: inline-block;
  width: 0.5rem;
  height: 0.5rem;
  border-radius: 50%;
  margin-right: 0.4rem;
  vertical-align: middle;
  background: var(--text-tertiary);
}
.ts-se-tier-high { background: var(--ts-source-sent-email); }
.ts-se-tier-med  { background: var(--warning); }
.ts-se-tier-low  { background: var(--text-tertiary); }

.ts-se-dismiss, .ts-se-undismiss {
  background: none;
  border: none;
  padding: 0;
  color: var(--text-tertiary);
  cursor: pointer;
  font-size: 0.82rem;
  text-decoration: underline;
}
.ts-se-dismiss:hover, .ts-se-undismiss:hover { color: var(--text-secondary); }
