:root { --background: #0b0d0f; --foreground: #16191b; --text: #f4f6f7; --accent: #65e5b7; --accent-contrast: #07130e; --muted-text: #929b9e; --company: "TimeTracker"; --border: color-mix(in srgb, var(--text) 14%, var(--foreground)); --panel: color-mix(in srgb, var(--foreground) 55%, var(--background)); --panel-raised: color-mix(in srgb, var(--text) 6%, var(--foreground)); --text-soft: color-mix(in srgb, var(--text) 65%, var(--muted-text)); --text-faint: color-mix(in srgb, var(--muted-text) 65%, var(--foreground));
  /* Semantic hues that aren't one of the five theme colours. Defaults suit a dark ground;
     the [data-theme="light"] block below swaps in accessible equivalents for a light ground.
     data-theme is set on <html> by public/theme.js / theme-init.js from the resolved palette. */
  --danger-text: #ff8172; --warning-text: #ffb74d; --warn-strong: #d95926;
  color-scheme: dark; font-family: Inter, ui-sans-serif, system-ui, sans-serif; background: var(--background); color: var(--text); }
:root[data-theme="light"] {
  --border: color-mix(in srgb, var(--text) 22%, var(--foreground));
  --panel: color-mix(in srgb, var(--text) 5%, var(--foreground));
  --panel-raised: color-mix(in srgb, var(--text) 9%, var(--foreground));
  --text-faint: color-mix(in srgb, var(--muted-text) 78%, var(--foreground));
  --danger-text: #c62828; --warning-text: #a15c00; --warn-strong: #b8430f;
}
/* Without this, iOS Safari can silently boost some text's rendered size beyond what any
   CSS here specifies (its own "text inflation" heuristic for readability on narrow
   viewports) - looks like a layout bug (oversized icons/spacing not matching the rest of
   the design) but is really iOS overriding sizes the page never asked it to. */
html { -webkit-text-size-adjust: 100%; text-size-adjust: 100%; }
* { box-sizing: border-box; }
body { margin: 0; background: radial-gradient(circle at 80% 0%, color-mix(in srgb, var(--accent) 22%, var(--background)) 0, transparent 34rem), var(--background); min-height: 100vh; }
main { width: min(980px, calc(100% - 32px)); margin: 0 auto; padding: 40px 0 80px; }
.app-recovery { grid-column: 1 / -1; width: min(620px, 100%); margin: 48px auto; padding: 28px; border: 1px solid var(--border); border-radius: 14px; background: var(--foreground); box-shadow: 0 18px 55px rgb(0 0 0 / 22%); }
.app-recovery h1 { font-size: clamp(1.7rem, 5vw, 2.25rem); }
.app-recovery p { margin-top: 12px; color: var(--muted-text); line-height: 1.6; }
.app-recovery-button { margin-top: 22px; padding: 12px 17px; border: 0; border-radius: 9px; color: var(--accent-contrast); background: var(--accent); font: inherit; font-weight: 800; cursor: pointer; }
.app-recovery-button:hover { filter: brightness(1.06); }
header, .section-title, .timer { display: flex; align-items: center; justify-content: space-between; gap: 24px; }
.account { display: flex; align-items: center; gap: 14px; color: var(--muted-text); }
h1, h2, p { margin: 0; } h1 { font-size: 2.5rem; letter-spacing: -.06em; } h2 { font-size: 1.35rem; }
.eyebrow, .label { color: var(--accent); font-size: .7rem; letter-spacing: .16em; font-weight: 800; }
.eyebrow { text-transform: uppercase; }
.eyebrow::before { content: var(--company); }
.card { background: color-mix(in srgb, var(--foreground) 93%, transparent); border: 1px solid color-mix(in srgb, var(--text) 14%, var(--foreground)); border-radius: 16px; padding: 24px; margin-top: 20px; box-shadow: 0 18px 60px #0005; }
.timer { min-height: 150px; border-color: color-mix(in srgb, var(--accent) 45%, var(--foreground)); } #elapsed { font: 700 2.5rem/1.2 ui-monospace, monospace; color: var(--accent); margin-top: 12px; }
.timer-info { min-width: 0; }
.timer-title-row { display: flex; align-items: center; gap: 14px; }
#timer-title { min-width: 0; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.timer-note { flex: 1; min-width: 180px; width: auto; padding: 6px 10px; }
.timer-note[hidden] { display: none; }
.conversion-prompt { padding: 16px 20px; border-color: color-mix(in srgb, var(--accent) 30%, var(--foreground)); }
.conversion-prompt-row { display: flex; align-items: center; justify-content: space-between; gap: 16px; }
.conversion-prompt-actions { display: flex; align-items: center; gap: 9px; }
.conversion-dismiss { border: 0; background: transparent; color: var(--muted-text); font-size: 1.2rem; line-height: 1; padding: 4px 8px; }
.conversion-dismiss:hover { color: var(--text); }
.conversion-prompt-form { display: grid; gap: 8px; }
.conversion-prompt-form label { color: var(--muted-text); font-size: .78rem; font-weight: 700; }
.conversion-prompt-form input, .conversion-prompt-form textarea, .conversion-prompt-form select { width: 100%; font: inherit; }
.conversion-prompt-form textarea { resize: vertical; }
.conversion-prompt-form select { padding: 13px 15px; color: inherit; background: var(--panel); border: 1px solid var(--border); border-radius: 9px; }
.jira-user-picker { position: relative; display: grid; gap: 8px; }
.jira-user-picker-input-row { display: flex; gap: 8px; }
.jira-user-picker-input-row input { min-width: 0; flex: 1; }
.jira-unassigned { flex: 0 0 auto; }
.jira-user-results { position: absolute; z-index: 30; top: calc(100% + 4px); left: 0; right: 0; max-height: 240px; overflow-y: auto; padding: 6px; border: 1px solid var(--border); border-radius: 9px; background: var(--panel-raised); box-shadow: 0 14px 35px #000a; }
.jira-user-results button { display: grid; width: 100%; gap: 2px; padding: 9px 10px; border: 0; border-radius: 7px; color: var(--text); background: transparent; text-align: left; }
.jira-user-results button:hover, .jira-user-results button:focus-visible { background: color-mix(in srgb, var(--accent) 14%, var(--panel-raised)); outline: none; }
.jira-user-results small, .jira-user-results p { color: var(--muted-text); }
.jira-user-results p { padding: 8px 10px; }
input { width: min(360px, 50%); padding: 13px 15px; color: inherit; background: var(--panel); border: 1px solid var(--border); border-radius: 9px; }
button { cursor: pointer; font: inherit; } button:disabled { cursor: not-allowed; opacity: .45; }
.danger { border: 0; border-radius: 9px; padding: 13px 18px; background: #ed6a5a; color: #170302; font-weight: 800; }
.quiet { border: 1px solid var(--border); border-radius: 8px; padding: 8px 11px; color: var(--text-soft); background: transparent; }
.quiet:hover { border-color: var(--accent); }
.link-button { display: inline-block; text-decoration: none; }
.link-button[hidden] { display: none; }
.settings-link { position: relative; display: grid; place-items: center; width: 38px; height: 38px; border: 1px solid var(--border); border-radius: 9px; color: var(--text-soft); }
.settings-link[hidden] { display: none; }.settings-link:hover { color: var(--accent); border-color: var(--accent); }
.settings-link:focus-visible { color: var(--accent); border-color: var(--accent); outline: 2px solid var(--accent); outline-offset: 2px; }
.settings-link::after { content: attr(data-tooltip); position: absolute; z-index: 20; top: calc(100% + 8px); left: 50%; padding: 6px 8px; border: 1px solid var(--border); border-radius: 6px; color: var(--text); background: var(--panel-raised); box-shadow: 0 8px 24px #0009; font-size: .72rem; font-weight: 700; line-height: 1; white-space: nowrap; pointer-events: none; opacity: 0; visibility: hidden; transform: translate(-50%, -2px); transition: opacity 100ms ease, transform 100ms ease, visibility 0s linear 100ms; }
.settings-link:focus-visible::after { opacity: 1; visibility: visible; transform: translate(-50%, 0); transition-delay: 0s; }
@media (hover: hover) and (pointer: fine) { .settings-link:hover::after { opacity: 1; visibility: visible; transform: translate(-50%, 0); transition-delay: 0s; } }
.settings-link svg { width: 20px; height: 20px; fill: none; stroke: currentColor; stroke-width: 1.7; stroke-linecap: round; stroke-linejoin: round; }
.codes { display: grid; grid-template-columns: repeat(2, 1fr); gap: 10px; }
.codes-row { display: flex; align-items: center; justify-content: space-between; gap: 16px; margin-top: 20px; }
.codes-row .codes { flex: 1; margin-top: 0; }
.projects { display: grid; grid-template-columns: repeat(4, 1fr); gap: 10px; margin-top: 24px; }
.quick-query-action { flex: 0 0 auto; width: max-content; }
.quick-query-action[hidden] { display: none; }
.project-filter { display: flex; align-items: center; justify-content: space-between; gap: 16px; min-height: 86px; text-align: left; border: 1px solid var(--border); border-radius: 12px; background: var(--panel); color: inherit; padding: 16px; }
.project-filter:hover { border-color: var(--accent); transform: translateY(-1px); }
.project-filter.active { border-color: var(--accent); background: color-mix(in srgb, var(--accent) 12%, var(--foreground)); box-shadow: inset 0 0 0 1px color-mix(in srgb, var(--accent) 20%, transparent); }
.project-filter span, .project-filter small { display: block; }
.project-filter small { margin-top: 7px; color: var(--accent); font: 700 .74rem ui-monospace, monospace; }
.project-filter em { display: grid; place-items: center; min-width: 32px; height: 32px; padding: 0 8px; border-radius: 99px; color: var(--muted-text); background: var(--panel-raised); font-style: normal; font-size: .78rem; font-weight: 800; }
.project-filter.active em { color: var(--accent-contrast); background: var(--accent); }
.selection-meta { display: flex; align-items: center; justify-content: space-between; gap: 14px; margin-top: 25px; }.selection-meta[hidden] { display: none; }.selection-heading { color: var(--muted-text); font-size: .8rem; font-weight: 750; }
.search-project-filters { display: flex; align-items: center; justify-content: flex-end; gap: 7px; flex-wrap: wrap; }.search-project-filters[hidden] { display: none; }.search-project-filter { display: inline-flex; align-items: center; gap: 7px; padding: 6px 9px; border: 1px solid var(--border); border-radius: 99px; color: var(--muted-text); background: var(--panel); font-size: .72rem; font-weight: 750; }.search-project-filter:hover { color: var(--accent); border-color: var(--accent); }.search-project-filter.active { color: var(--accent-contrast); border-color: var(--accent); background: var(--accent); }.search-project-filter em { min-width: 20px; padding: 2px 5px; border-radius: 99px; color: inherit; background: color-mix(in srgb, currentColor 13%, transparent); font-style: normal; font-size: .65rem; text-align: center; }
.timesheet-title { display: grid; grid-template-columns: 1fr auto 1fr; align-items: end; gap: 12px; }
#week-range { display: block; margin-top: 5px; color: var(--muted-text); font-size: .76rem; }
.week-controls { grid-column: 3; justify-self: end; display: flex; align-items: center; gap: 7px; }
.week-controls #current-week { white-space: nowrap; }
.week-controls #total { min-width: 92px; margin-left: 8px; text-align: right; }
.week-arrow, .page-arrow { display: grid; place-items: center; padding: 0; line-height: 1; }
.week-arrow { width: 35px; height: 35px; font-size: 1.2rem; }
.week-approval { position: relative; grid-column: 2; justify-self: center; display: flex; align-items: center; gap: 10px; }
.week-approval-stacked { flex-direction: column; gap: 6px; }
.week-approval-status { color: var(--muted-text); font-size: .82rem; font-weight: 700; }
.week-approval-status.rejected { color: var(--danger-text); }
.week-approval-note { max-width: 360px; color: var(--text-soft); font-size: .78rem; line-height: 1.35; text-align: center; }
.approval-history { color: var(--text-soft); font-size: .76rem; text-align: left; }
.approval-history summary { width: max-content; margin: 0 auto; cursor: pointer; font-weight: 750; }
.approval-history summary:hover, .approval-history summary:focus-visible { color: var(--accent); }
.approval-history ol { position: absolute; z-index: 20; top: calc(100% + 8px); left: 50%; display: grid; width: min(380px, 70vw); max-height: min(430px, 65vh); gap: 7px; margin: 0; padding: 18px 22px 18px 40px; overflow-y: auto; border: 1px solid var(--border); border-radius: 8px; background: var(--panel); box-shadow: 0 14px 34px rgb(0 0 0 / 38%); transform: translateX(-50%); }
.approval-history li { padding-left: 2px; }
.approval-history li strong, .approval-history li span, .approval-history li small { display: block; }
.approval-history li span { margin-top: 2px; color: var(--muted-text); }
.approval-history li small { margin-top: 3px; color: var(--text-soft); font-size: .72rem; }
.day-group { margin-top: 18px; border: 1px solid var(--border); border-radius: 10px; overflow: visible; }
.day-header { display: flex; align-items: center; justify-content: space-between; gap: 20px; min-height: 42px; padding: 10px 14px; border-radius: 9px 9px 0 0; color: var(--text-soft); background: var(--panel-raised); }
.day-header > strong { font-size: .82rem; }.day-header > span { color: var(--muted-text); font-size: .72rem; }.day-header b { margin-left: 5px; color: var(--text); font-size: .9rem; }
.day-group .entry { padding-left: 13px; padding-right: 13px; }.day-group .entry:last-child { border-radius: 0 0 9px 9px; }
.week-empty { padding: 28px 2px 8px; }
.timesheet-footer { display: grid; grid-template-columns: 1fr auto 1fr; align-items: center; gap: 20px; margin-top: 20px; }
.week-export { grid-column: 2; justify-self: center; white-space: nowrap; }
.timesheet-pagination { grid-column: 3; justify-self: end; display: flex; align-items: center; justify-content: flex-end; gap: 9px; color: var(--muted-text); font-size: .78rem; }
.timesheet-pagination[hidden] { display: none; }
.page-arrow { width: 35px; height: 35px; }
.timesheet-pagination select { width: 68px; padding: 8px 9px; border: 1px solid var(--border); border-radius: 8px; color: var(--text-soft); background: var(--panel); }
.staff-picker { border-color: color-mix(in srgb, var(--accent) 45%, var(--foreground)); }
#staff-select { min-width: 240px; padding: 11px 12px; border: 1px solid var(--border); border-radius: 8px; color: var(--text); background: var(--panel); font: inherit; }
.staff-empty { margin-top: 24px; text-align: center; }
.poll-stale-banner { margin: 0 0 14px; padding: 9px 13px; border: 1px solid color-mix(in srgb, var(--warning-text) 45%, var(--border)); border-radius: 8px; background: color-mix(in srgb, var(--warning-text) 12%, var(--foreground)); color: var(--text); font-size: .82rem; }
@media (max-width: 650px) { .staff-picker .section-title { align-items: stretch; } #staff-select { width: 100%; } }
.groups { display: grid; grid-template-columns: repeat(3, 1fr); gap: 8px; margin-top: 12px; }
.group-filter { display: flex; align-items: center; justify-content: space-between; gap: 14px; min-height: 54px; text-align: left; border: 1px solid var(--border); border-radius: 9px; padding: 11px 13px; color: var(--text-soft); background: var(--panel); }
.group-filter:hover { border-color: var(--accent); }
.group-filter.active { color: var(--text); border-color: var(--accent); background: color-mix(in srgb, var(--accent) 12%, var(--foreground)); }
.group-filter em { flex: 0 0 auto; min-width: 27px; padding: 4px 7px; border-radius: 99px; color: var(--muted-text); background: var(--panel-raised); font-style: normal; text-align: center; font-size: .72rem; font-weight: 800; }
.group-filter.active em { color: var(--accent-contrast); background: var(--accent); }
.assigned-group-copy { min-width: 0; }
.assigned-group-copy b, .assigned-group-copy small { display: block; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.assigned-group-copy small { margin-top: 4px; color: var(--muted-text); font-size: .72rem; font-weight: 500; }
.assigned-groups-back { flex: 0 0 auto; border: 0; padding: 0; background: transparent; color: var(--accent); font-size: .8rem; font-weight: 750; }
.assigned-groups-back:hover { text-decoration: underline; }
.picker-empty { grid-column: 1 / -1; padding: 24px 2px 4px; }
.code { text-align: left; border: 1px solid var(--border); border-radius: 10px; background: var(--panel); color: inherit; padding: 14px; }
.code-organisation { background: var(--panel-raised); }
.code:hover { border-color: var(--accent); transform: translateY(-1px); }.code.active { border-color: var(--accent); background: color-mix(in srgb, var(--accent) 12%, var(--foreground)); box-shadow: inset 0 0 0 1px color-mix(in srgb, var(--accent) 20%, transparent); }.code span, .code small, .entry small { display: block; }.code small, .entry small, .empty { color: var(--muted-text); margin-top: 5px; }
.work-actions { display: flex; align-items: flex-start; justify-content: space-between; gap: 22px; margin-top: 16px; padding: 16px; border: 1px solid color-mix(in srgb, var(--accent) 40%, var(--foreground)); border-radius: 11px; background: color-mix(in srgb, var(--accent) 8%, var(--foreground)); }
.work-actions[hidden] { display: none; }.selected-work { min-width: 0; }.selected-work strong, .selected-work small { display: block; }.selected-work strong { margin-top: 5px; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }.selected-work small { margin-top: 4px; color: var(--muted-text); }
/* The three columns top-align (.work-actions align-items: flex-start). The "Description" label
   is a plain inline child of .quick-note-field, so it sits in the panel's 16px line-box - the
   same box the SELECTED WORK ITEM eyebrow sits in on the left - and the two line up. The input
   drops onto its own line below (display: block) with the 6px label gap. */
.quick-note-field { display: block; flex: 1 1 220px; min-width: 0; color: var(--muted-text); font-weight: 700; }.quick-note-field[hidden] { display: none; }.quick-note-field > span { font-size: .78rem; }.quick-note-field input { display: block; width: 100%; margin-top: 6px; }
.work-action-buttons, .dialog-actions { display: flex; align-items: center; gap: 9px; }.primary-action, .secondary-action { border-radius: 9px; padding: 11px 16px; font-weight: 800; }.primary-action { border: 0; color: var(--accent-contrast); background: var(--accent); }.secondary-action { border: 1px solid var(--accent); color: var(--accent); background: transparent; }.secondary-action:hover { color: var(--accent-contrast); background: var(--accent); }.work-action-buttons .primary-action { border: 1px solid transparent; }
/* Pin both action buttons to the Description input's rendered height (~43px: its default
   form-control font line-box + 13px vertical padding + 1px border, box-sizing: border-box).
   The buttons' own 16px/800 label is a taller line-box than the input's, so their natural
   11px-padding height overshoots by a pixel or two - min-height + no vertical padding clamps
   both to the input's box, and the button's native content-centring keeps the label centred. */
.work-action-buttons .primary-action, .work-action-buttons .secondary-action { min-height: 43px; padding-top: 0; padding-bottom: 0; }
/* The button group top-aligns with the other columns too, then drops by one line-height
   (the label's line) plus its 6px gap, so the buttons sit level with the Description input
   rather than the label above it. */
.work-action-buttons { margin-top: calc(1lh + 6px); }
.entry-dialog { width: min(520px, calc(100% - 32px)); padding: 0; border: 1px solid var(--border); border-radius: 15px; color: var(--text); background: var(--foreground); box-shadow: 0 26px 90px #000c; }.entry-dialog::backdrop { background: #000b; backdrop-filter: blur(3px); }.entry-dialog form { padding: 23px; }.dialog-heading { display: flex; align-items: flex-start; justify-content: space-between; gap: 20px; }.dialog-close { width: 34px; height: 34px; border: 1px solid var(--border); border-radius: 8px; color: var(--muted-text); background: transparent; font-size: 1.35rem; line-height: 1; }.dialog-close:hover { color: var(--accent); border-color: var(--accent); }.manual-work-title { margin-top: 18px; padding: 12px 13px; border-radius: 8px; color: var(--text-soft); background: var(--panel); font-weight: 750; }.manual-fields { display: grid; grid-template-columns: 1.2fr 1fr 1fr; gap: 10px; margin-top: 18px; }.entry-dialog label { display: grid; gap: 7px; color: var(--muted-text); font-size: .78rem; font-weight: 700; }.entry-dialog input { width: 100%; }.manual-note { margin-top: 12px; }.dialog-actions { justify-content: flex-end; margin-top: 20px; }.form-error { margin-top: 12px; color: var(--danger-text); font-size: .8rem; }
.entry { display: grid; grid-template-columns: minmax(225px, 1fr) 48px 38px 210px 44px 98px 80px; align-items: center; gap: 10px; border-top: 1px solid var(--border); padding: 13px 0; }.entry:first-child { margin-top: 14px; }
/* The DOM order groups icons/date/actions together (for the mobile layout below) rather than
   matching desktop's visual left-to-right order, so desktop needs explicit column numbers
   instead of relying on grid auto-flow to place children in DOM order. .icon-row and
   .time-duration-row are just grouping wrappers for mobile - invisible to desktop's grid via
   display: contents, so their children act as direct grid items in their assigned columns,
   same as if the wrappers didn't exist. grid-row: 1 is explicit on every one of them too, not
   just grid-column - leaving the row on auto let some browsers' auto-placement cursor treat
   entering/exiting a display:contents wrapper as a reason to advance to a new row, splitting
   .time-range/.duration-input (inside .time-duration-row, later in DOM order) onto a second
   row below everything else even though nothing here overlaps in the specified columns. */
.entry-description { grid-column: 1; grid-row: 1; }
.icon-row, .time-duration-row { display: contents; }
.label-cell { grid-column: 2; grid-row: 1; }
.billable-cell { grid-column: 3; grid-row: 1; }
.time-range { grid-column: 4; grid-row: 1; }
.date-control { grid-column: 5; grid-row: 1; }
.duration-input { grid-column: 6; grid-row: 1; }
.entry-actions { grid-column: 7; grid-row: 1; }
.entry-description { min-width: 0; }.entry-description b { display: block; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }.entry-description small { overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }.entry-description small .entry-place { color: var(--text-soft); font-weight: 500; }.description-input { width: 100%; padding: 6px 10px; }
.entry input { min-width: 0; }
.time-range { display: flex; align-items: center; justify-content: center; gap: 3px; color: var(--text-faint); }
/* 76px clipped the last character of the HH:MM text against Chrome desktop's own clock-icon
   affordance inside the native time input - same class of issue the mobile breakpoint's own
   width bump fixed a few sessions back, just never carried over to desktop since it hadn't
   been reported there yet. Keeping the native control (Tom explicitly wants Chrome's own
   clock icon and picker, not a custom one) just means giving it enough width instead. */
.entry-time { width: 92px; padding: 7px 5px; border-color: transparent; background: transparent; color: var(--text-soft); text-align: center; }
.date-control { position: relative; display: grid; place-items: center; width: 40px; height: 36px; }
/* Purely the visible icon - pointer-events: none so real taps/clicks pass straight through to
   .entry-date underneath instead of stopping on this button. iOS Safari won't reliably open a
   native date picker from a JS-triggered showPicker()/click() call (which is what this button
   used to rely on exclusively); it needs a genuine user tap landing on the actual input.
   Keyboard activation still works - pointer-events: none only affects pointer/touch hit-
   testing, not Enter/Space-triggered clicks on a focused button - so the JS handler below
   remains the keyboard/screen-reader path. */
/* Shared by every password input (PasswordField.jsx) - the toggle button sits inside the
   input's own box via absolute positioning, so callers style the <input> exactly as before
   (this div is a transparent wrapper, not a new layout box with its own width/padding rules
   to keep in sync) and only need to reserve room on the right for the icon. flex+align-items
   keeps the input itself vertically centred if this wrapper ever gets stretched taller than
   its content by a parent grid/flex row (e.g. .password-reset-form's own grid row, which
   sizes to its tallest child and defaults to stretch, not center) - without this, the input
   sat at the top of that taller box instead of centred like a plain <input> would. Doesn't
   affect the toggle button below, which is position: absolute and ignores flex placement. */
.password-field { position: relative; display: flex; align-items: center; width: 100%; }
/* !important is deliberate here: every page that embeds a password field also declares its
   own shorthand `padding` on `input` (login.css, settings.css, backup.css, jira.css), each at
   equal-or-higher selector specificity and loaded after this shared stylesheet - without it,
   whichever page-specific rule wins would silently swallow the padding-right this reserves for
   the icon, letting typed text run underneath it. */
.password-field input { padding-right: 42px !important; }
.password-toggle { position: absolute; top: 0; right: 0; bottom: 0; display: grid; place-items: center; width: 40px; border: 0; border-radius: 0 8px 8px 0; color: var(--muted-text); background: transparent; cursor: pointer; }
.password-toggle:hover, .password-toggle:focus-visible { color: var(--accent); outline: none; }
.password-toggle svg { width: 19px; height: 19px; fill: none; stroke: currentColor; stroke-width: 1.6; stroke-linecap: round; stroke-linejoin: round; }

.date-picker { display: grid; place-items: center; width: 40px; height: 36px; padding: 0; border: 1px solid transparent; border-radius: 8px; color: var(--muted-text); background: transparent; cursor: pointer; pointer-events: none; }
.date-picker:hover, .date-picker:focus { border-color: var(--accent); color: var(--accent); background: color-mix(in srgb, var(--accent) 12%, var(--foreground)); outline: none; }
.date-picker svg { width: 20px; height: 20px; fill: none; stroke: currentColor; stroke-width: 1.6; stroke-linecap: round; }
/* Sized and stacked to exactly cover the icon above, rather than a 1x1px dot - this is now
   the real tap target real users hit, not just a value holder driven entirely by JS. */
.entry-date { position: absolute; inset: 0; width: 100%; height: 100%; margin: 0; padding: 0; border: 0; opacity: 0; cursor: pointer; }
.duration-input { width: 88px; justify-self: center; padding: 7px 8px; border-color: transparent; background: transparent; color: var(--text); text-align: center; font-weight: 800; }
.entry-time:hover, .entry-time:focus, .entry-date:hover, .entry-date:focus, .duration-input:hover, .duration-input:focus { border-color: var(--accent); background: var(--panel); outline: none; }
/* Excludes .entry-date - it must stay fully invisible in every state, disabled included
   (a still-running entry disables all its inputs, .entry-date among them). Without this
   exclusion, `.entry input:disabled` (a class + type + pseudo-class selector) beats
   `.entry-date`'s own `opacity: 0` (a single class selector) in specificity, so a running
   entry's real date input showed its actual native text ("16/08" etc.) faintly through at
   65% opacity instead of staying invisible behind the decorative calendar icon. */
.entry input:disabled:not(.entry-date) { opacity: .65; }
.label-cell { display: grid; place-items: center; position: relative; }
.label-menu { position: relative; }
.label-menu summary { display: inline-flex; align-items: center; justify-content: center; gap: 3px; width: 38px; height: 34px; color: var(--accent); border: 1px solid transparent; border-radius: 8px; list-style: none; cursor: pointer; }
.label-menu summary::-webkit-details-marker { display: none; }
.label-menu summary:hover, .label-menu[open] summary { border-color: var(--accent); background: color-mix(in srgb, var(--accent) 12%, var(--foreground)); }
.label-menu svg { width: 19px; fill: none; stroke: currentColor; stroke-width: 1.6; }
.label-menu summary span { font-size: .65rem; font-weight: 800; }
.label-menu-empty summary { color: var(--text-faint); }
.label-menu-empty summary:hover, .label-menu-empty[open] summary { color: var(--accent); }
.billable-cell { display: grid; place-items: center; }
.billable-toggle { display: inline-flex; align-items: center; justify-content: center; width: 30px; height: 30px; border: 1px solid transparent; border-radius: 8px; color: var(--text-faint); background: transparent; font-size: .95rem; font-weight: 800; cursor: pointer; }
.billable-toggle:hover { border-color: var(--accent); }
.billable-toggle.active { color: var(--accent); background: color-mix(in srgb, var(--accent) 12%, var(--foreground)); }
.billable-toggle:disabled { opacity: .6; cursor: default; }
.label-editor { position: absolute; z-index: 5; top: 39px; left: 50%; width: 260px; padding: 9px; transform: translateX(-50%); border: 1px solid var(--border); border-radius: 9px; background: var(--panel); box-shadow: 0 12px 30px #0009; }
.label-search { width: 100%; padding: 8px 9px; border: 1px solid var(--border); border-radius: 7px; color: var(--text-soft); background: var(--foreground); font: inherit; }
.label-options { max-height: 220px; margin: 8px 0; overflow-y: auto; }
.label-option { display: flex; align-items: center; gap: 8px; padding: 7px 6px; border-radius: 6px; color: var(--text-soft); cursor: pointer; }
.label-option:hover { background: color-mix(in srgb, var(--accent) 12%, transparent); }
.label-option[hidden] { display: none; }
.label-option span { overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.label-add-new { color: var(--accent); }
.label-save { width: 100%; padding: 9px; border: 0; border-radius: 7px; color: var(--accent-contrast); background: var(--accent); font-weight: 850; }
.entry-actions { display: flex; align-items: center; gap: 4px; justify-self: end; }
.resume-entry { display: grid; place-items: center; width: 36px; height: 36px; border: 1px solid transparent; border-radius: 50%; color: var(--accent); background: transparent; font-size: 1.05rem; }
.resume-entry:hover { border-color: var(--accent); background: color-mix(in srgb, var(--accent) 12%, var(--foreground)); }
.entry-menu { position: relative; }
.entry-menu summary { display: inline-flex; align-items: center; justify-content: center; width: 36px; height: 36px; color: var(--muted-text); border: 1px solid transparent; border-radius: 50%; list-style: none; cursor: pointer; }
.entry-menu summary::-webkit-details-marker { display: none; }
.entry-menu summary:hover, .entry-menu[open] summary { color: var(--accent); border-color: var(--accent); background: color-mix(in srgb, var(--accent) 12%, var(--foreground)); }
.entry-menu svg { width: 19px; fill: currentColor; stroke: none; }
.entry-menu-links { position: absolute; z-index: 5; top: 39px; right: 0; min-width: 140px; padding: 7px; border: 1px solid var(--border); border-radius: 9px; background: var(--panel); box-shadow: 0 12px 30px #0009; display: grid; gap: 2px; }
.entry-menu-links button { display: block; width: 100%; padding: 8px 9px; border: 0; border-radius: 6px; color: var(--text-soft); background: transparent; text-align: left; font: inherit; }
.entry-menu-links button:hover:not(:disabled) { color: var(--accent-contrast); background: var(--accent); }
.entry-menu-links button:disabled { color: var(--text-faint); cursor: not-allowed; }
.entry-menu-links .delete-entry:hover:not(:disabled) { color: #170302; background: #ed6a5a; }
.sync-badge { margin-left: 6px; color: var(--danger-text); cursor: default; }
.correction-badge { display: inline-block; margin-left: 6px; padding: 1px 5px; border-radius: 4px; background: #8a4b08; color: #fff; font-size: 0.68rem; font-weight: 700; cursor: default; vertical-align: middle; }
.lock-badge { display: inline-flex; margin-left: 6px; color: var(--muted-text); cursor: default; vertical-align: middle; }
.lock-badge svg { width: 14px; height: 14px; fill: none; stroke: currentColor; stroke-width: 2; stroke-linecap: round; stroke-linejoin: round; }
@media (max-width: 760px) { .projects, .groups { grid-template-columns: 1fr; } }
@media (max-width: 650px) {
  header { align-items: stretch; flex-direction: column; gap: 16px; }
  .account { width: 100%; flex-wrap: wrap; gap: 10px; }
  .account #identity { flex: 1 1 90px; min-width: 0; line-height: 1.3; }
  .account #logout { margin-left: auto; white-space: nowrap; }
  .codes { grid-template-columns: 1fr; }
  .section-title { align-items: flex-start; flex-direction: column; }
  input { width: 100%; }
}
@media (max-width: 1040px) { .entry { grid-template-columns: minmax(220px, 1fr) 42px 34px 202px 40px 94px 76px; gap: 6px; } }
@media (max-width: 820px) {
  /* A genuinely separate mobile layout, not a squeezed-down version of the desktop grid -
     two rows of purpose-built groups instead of reusing desktop's column-sharing (that
     sharing is exactly what caused the last two overflow bugs). Row 1: title. Row 2: label,
     billable, date and actions icons, spread evenly. Row 3: time range + duration together.
     Each row is its own grid track, so nothing here competes for width with anything in
     another row the way desktop's auto-sized columns did. */
  .entry { grid-template-columns: 1fr; gap: 10px; }
  /* Reclaims width for the fixed-size time/duration row below - at this breakpoint the two
     time inputs plus the duration field need more of the available width than the desktop
     13px card inset leaves spare, so mobile gets a tighter inset instead. */
  .day-group .entry { padding-left: 3px; padding-right: 3px; }
  .entry-description { grid-column: 1; }
  /* A real flex row (not grid columns sharing width) so the four icon groups can be spaced
     evenly across the full row with plain justify-content, instead of the previous grid
     layout that packed three items to the left and left a single large gap before the
     actions pushed to the far right. min-width: 0 stops this flex box (a grid item here)
     from claiming more than its track's width - without it, a grid item's default
     `min-width: auto` lets it request its content's min-content size regardless of the
     track, which is exactly what caused the row below to silently overflow its card. */
  .icon-row { display: flex; align-items: center; justify-content: space-between; min-width: 0; }
  /* Both must stay on one line - splitting the time range and duration onto two lines is
     exactly the "spilling over two rows" bug this is fixing, not the intended design. Sizes
     are fixed (not flex-grow/shrink) at the widths already proven safe on a real device
     earlier this session, rather than letting the row's natural content size balloon past
     its container - min-width: 0 for the same grid-item reason as .icon-row above. */
  .time-duration-row { display: flex; align-items: center; gap: 2px; min-width: 0; }
  .time-range { flex: 0 1 auto; }
  .entry-time { flex: 0 0 auto; width: 92px; }
  .duration-input { flex: 0 0 auto; width: 88px; padding: 7px 6px; }
}
/* Below this, even the fixed single-row sizing above doesn't fit (iPhone SE and similarly
   narrow older devices) - let the time range and duration wrap onto their own lines rather
   than overflow the card. Tom's own device is well above this width; this is a floor for
   hardware neither of us is testing on, not the primary target. */
@media (max-width: 360px) {
  .time-duration-row { flex-wrap: wrap; justify-content: space-between; }
}
@media (max-width: 650px) { .timesheet-title { grid-template-columns: 1fr; align-items: stretch; } .week-approval, .week-controls { grid-column: 1; justify-self: stretch; } .week-controls { width: 100%; flex-wrap: wrap; } .week-controls #total { margin-left: auto; } .timesheet-footer { grid-template-columns: 1fr; gap: 12px; } .week-export, .timesheet-pagination { grid-column: 1; justify-self: start; } .timesheet-pagination { justify-content: flex-start; flex-wrap: wrap; } }
@media (max-width: 650px) { .selection-meta { align-items: flex-start; flex-direction: column; }.search-project-filters { justify-content: flex-start; } }
@media (max-width: 650px) { .work-actions { align-items: stretch; flex-direction: column; }.work-action-buttons { width: 100%; margin-top: 0; }.work-action-buttons button { flex: 1; }.manual-fields { grid-template-columns: 1fr 1fr; }.manual-fields label:first-child { grid-column: 1 / -1; } }
.app-footer { width: min(980px, calc(100% - 32px)); margin: -56px auto 24px; padding-top: 20px; border-top: 1px solid var(--border); color: var(--muted-text); font-size: .72rem; text-align: center; }
.app-footer a { color: var(--muted-text); text-decoration: underline; text-underline-offset: 3px; }
.app-footer a:hover { color: var(--accent); }
