* {
  box-sizing: border-box;
}

html, body {
  margin: 0;
  padding: 0;
  width: 100%;
  height: 100%;
  overflow: hidden;
  background: #242428;
  font-family: -apple-system, BlinkMacSystemFont, "Segoe UI", sans-serif;
  color: #e8e8ee;
}

#canvas {
  position: fixed;
  inset: 0;
  display: block;
  cursor: default;
  /* Tells the browser not to intercept touch gestures on the canvas for its own scrolling/
     pinch-zoom — pan and pinch-zoom are handled by the app itself (see main.js's pointer
     handling), and without this the browser fights it for every touch. */
  touch-action: none;
}

#toolbar {
  position: fixed;
  top: 16px;
  left: 16px;
  display: flex;
  gap: 8px;
  z-index: 10;
}

#toolbar button {
  background: #34343c;
  color: #e8e8ee;
  border: 1px solid #4a4a54;
  border-radius: 6px;
  padding: 8px 14px;
  font-size: 14px;
  cursor: pointer;
}

#toolbar button:hover {
  background: #3d3d47;
}

/* Transient flash for a Hookline error (see main.js's Sync.onError) — same danger palette as
   .settings-danger-btn, just applied to whichever toolbar button needs it for a few seconds
   rather than permanently. */
#toolbar button.sync-error {
  border-color: #7a3535;
  color: #f0b4b4;
}

#toolbar button.sync-error:hover {
  background: #3d2626;
}

/* Anchors the dropdown below its own toggle button — the ONLY thing .toolbar-menu does; the
   button and dropdown otherwise style themselves independently. */
.toolbar-menu {
  position: relative;
}

/* A small anchored popup rather than a modal overlay (see .overlay elsewhere) — dismissed by
   picking an option or clicking anywhere else (see main.js), not its own close button. */
#toolbar .toolbar-dropdown {
  position: absolute;
  top: calc(100% + 6px);
  left: 0;
  display: flex;
  flex-direction: column;
  gap: 2px;
  min-width: 140px;
  background: #28282e;
  border: 1px solid #4a4a54;
  border-radius: 8px;
  padding: 6px;
  z-index: 11;
}

#toolbar .toolbar-dropdown button {
  display: block;
  width: 100%;
  background: transparent;
  border: none;
  border-radius: 5px;
  padding: 8px 10px;
  text-align: left;
}

#toolbar .toolbar-dropdown button:hover {
  background: #3d3d47;
}

#side-panel {
  position: fixed;
  top: 16px;
  right: 16px;
  width: 280px;
  max-height: calc(100vh - 32px);
  overflow-y: auto;
  background: rgba(40, 40, 46, 0.92);
  border: 1px solid #4a4a54;
  border-radius: 10px;
  padding: 16px;
  z-index: 10;
}

/* A dedicated full-page view, not a floating panel — Tasks replaces the graph entirely while
   open (opaque, inset:0, above the canvas/toolbar/side-panel's z-index:10) rather than sharing
   the screen with it. Toggled by #task-list-btn; #task-list-close-btn (or Escape) returns to the
   graph. A centered, readable column rather than edge-to-edge, same idea as any list/reading app. */
#task-list-panel {
  position: fixed;
  inset: 0;
  overflow-y: auto;
  background: #1c1c20;
  padding: 0 40px 44px;
  z-index: 15;
}

/* Sticky within the panel's own scroll, so "Back to graph", the heading, and the assignee filter
   chips below it all stay reachable without scrolling back up first. Carries its own top padding
   (rather than #task-list-panel above) so the spacing above it is identical whether it's sitting
   at the top of an unscrolled panel or pinned there after scrolling — and its own opaque
   background plus a bottom border, since content now scrolls up underneath it instead of past it. */
#task-list-sticky {
  position: sticky;
  top: 0;
  padding-top: 24px;
  background: #1c1c20;
  border-bottom: 1px solid #303036;
  z-index: 1;
}

#task-list-header {
  display: flex;
  align-items: flex-start;
  justify-content: space-between;
  gap: 16px;
  max-width: 640px;
  margin: 0 auto;
  padding: 0 0 18px;
}

#task-list-header h2 {
  margin: 0 0 6px;
  font-size: 22px;
  font-weight: 700;
  color: #e8e8ee;
}

#task-list-close-btn {
  flex-shrink: 0;
  background: #34343c;
  color: #e8e8ee;
  border: 1px solid #4a4a54;
  border-radius: 6px;
  padding: 9px 14px;
  font-size: 13px;
  cursor: pointer;
  white-space: nowrap;
}

#task-list-close-btn:hover {
  background: #3d3d47;
}

/* Hidden entirely (display:none, set in JS) rather than empty whenever nobody has an assignee
   set — see main.js's renderTaskFilters. */
#task-list-filters {
  display: none;
  flex-wrap: wrap;
  gap: 6px;
  max-width: 640px;
  margin: 0 auto 14px;
}

.task-filter-chip {
  background: #26262c;
  color: #b9b9c4;
  border: 1px solid #4a4a54;
  border-radius: 999px;
  padding: 5px 12px;
  font-size: 12px;
  cursor: pointer;
}

.task-filter-chip:hover {
  background: #303038;
}

.task-filter-chip-active {
  background: #34343c;
  color: #e8e8ee;
  border-color: #5cc8ff;
}

#task-list-items {
  max-width: 640px;
  margin: 0 auto;
}

.panel-hint {
  margin: 0;
  font-size: 12px;
  color: #8a8a94;
  line-height: 1.4;
}

.task-list-toggle {
  display: flex;
  align-items: center;
  gap: 6px;
  margin-top: 8px;
  font-size: 12px;
  color: #b9b9c4;
  cursor: pointer;
  user-select: none;
}

.task-list-toggle input {
  cursor: pointer;
}

.task-list-empty {
  margin: 0;
  font-size: 14px;
  color: #8a8a94;
}

/* The outcome as a heading, its flat item list underneath (see graph.js's taskListForOutcome /
   main.js's renderTaskList). */
.task-list-root {
  margin-bottom: 14px;
}

.task-list-root:last-child {
  margin-bottom: 0;
}

/* Deliberately close to plain text — no per-row box, no separator line. Always tinted by the same
   MULTISTATE_COLORS the row's underlying node is shown in on the canvas (see view.js) — set
   inline per-row in main.js, so the two can never drift apart. */
.task-list-row {
  display: flex;
  align-items: flex-start;
  gap: 9px;
  padding: 4px 4px 4px 9px;
  border-left: 2px solid transparent;
  cursor: pointer;
}

/* The outcome's own row (and its own "needs discussion"/"needs scoping" entry, if any) — a real
   heading, not just another item, so the list underneath reads as belonging to it. */
.task-list-heading .task-list-row-title {
  font-size: 16px;
  font-weight: 700;
}

/* Every other item, indented the one level under its outcome's heading — never nested further
   among themselves (see taskListForOutcome's own comment on why this is flat, not a tree). */
.task-list-items {
  margin-left: 8px;
  padding-left: 11px;
  border-left: 1px solid #303036;
}

/* Not actionable right now (blocked, or still waiting on its own requirements), OR filtered out
   by the assignee chips — shown dimmed by default rather than omitted, since it's still real,
   useful context for the rest of the list (see graph.js's taskListForOutcome). The "Hide
   non-ready tasks" toggle (off by default — see #task-list-panel.hide-non-ready below) hides
   these same rows outright instead: once you're filtered to one person, a row that isn't
   actionable OR isn't theirs is equally not something to act on right now. */
.task-list-row-dimmed .task-list-row-title,
.task-list-row-dimmed .task-list-row-meta {
  opacity: 0.5;
}

#task-list-panel.hide-non-ready .task-list-row-dimmed {
  display: none;
}

/* Dark, custom-drawn tickbox — the browser default renders as a plain white square, which reads
   as foreign dropped into this theme. Shared with the "Hide non-ready tasks" toggle above (see
   .task-list-toggle) so every checkbox on this page reads as the same control. */
.task-list-row input[type='checkbox'],
.task-list-toggle input[type='checkbox'] {
  appearance: none;
  -webkit-appearance: none;
  width: 16px;
  height: 16px;
  margin-top: 1px;
  border: 1.5px solid #4a4a54;
  border-radius: 4px;
  background: #1c1c20;
  cursor: pointer;
  flex-shrink: 0;
  position: relative;
}

.task-list-row input[type='checkbox']:hover,
.task-list-toggle input[type='checkbox']:hover {
  border-color: #6e6e78;
}

.task-list-row input[type='checkbox']:checked,
.task-list-toggle input[type='checkbox']:checked {
  background: #4ade80;
  border-color: #4ade80;
}

.task-list-row input[type='checkbox']:checked::after,
.task-list-toggle input[type='checkbox']:checked::after {
  content: '';
  position: absolute;
  left: 4px;
  top: 1px;
  width: 4px;
  height: 8px;
  border: solid #14251a;
  border-width: 0 2px 2px 0;
  transform: rotate(45deg);
}

.task-list-row-title {
  font-size: 14px;
  color: #e8e8ee;
  line-height: 1.3;
}

.task-list-row-meta {
  font-size: 11.5px;
  color: #8a8a94;
  margin-top: 1px;
}

/* Inline assignee editor on an action row — sits where the assignee used to render as plain meta
   text, and stays that quiet until hovered/focused, when it picks up a visible field affordance. */
.task-list-row-assignee {
  display: block;
  margin-top: 2px;
  padding: 1px 4px;
  border: 1px solid transparent;
  border-radius: 4px;
  background: transparent;
  font: inherit;
  font-size: 11.5px;
  color: #b9b9c2;
  max-width: 220px;
  cursor: text;
}

.task-list-row-assignee::placeholder {
  color: #6a6a74;
  font-style: italic;
}

.task-list-row-assignee:hover {
  border-color: #3a3a42;
}

.task-list-row-assignee:focus {
  outline: none;
  border-color: #5c8cff;
  background: #1c1c20;
  color: #e8e8ee;
}

.task-list-row-dimmed .task-list-row-assignee {
  opacity: 0.5;
}

#side-panel h2 {
  margin: 0 0 12px;
  font-size: 15px;
  font-weight: 600;
  color: #b9b9c4;
}

#panel-empty {
  color: #8a8a94;
  font-size: 14px;
}

#panel-empty-text {
  margin: 0 0 12px;
}

#add-backdrop-btn {
  width: 100%;
  background: #34343c;
  color: #e8e8ee;
  border: 1px solid #4a4a54;
  border-radius: 6px;
  padding: 8px;
  font-size: 13px;
  cursor: pointer;
}

#add-backdrop-btn:hover {
  background: #3d3d47;
}

#panel-content {
  display: none;
}

#panel-dot-info {
  display: none;
  color: #b9b9c4;
  font-size: 13px;
  line-height: 1.5;
  margin: 0 0 14px;
}

#panel-action-fields,
#panel-resource-fields,
#panel-multistate-field {
  display: none;
}

.field {
  display: flex;
  flex-direction: column;
  gap: 4px;
  font-size: 13px;
  color: #b9b9c4;
  margin-bottom: 14px;
}

/* A checkbox field reads left-to-right (box, then label) rather than stacked like every other
   field above it — the same reasoning the Tasks view's own checkbox rows already follow. */
.field-checkbox {
  flex-direction: row;
  align-items: center;
  gap: 8px;
}

.field-checkbox input[type='checkbox'] {
  width: auto;
  padding: 0;
  background: none;
  border: none;
  cursor: pointer;
}

.field input,
.field select,
.field textarea {
  background: #1c1c20;
  border: 1px solid #4a4a54;
  border-radius: 6px;
  color: #e8e8ee;
  padding: 8px;
  font-size: 14px;
  font-family: inherit;
  resize: vertical;
}

.field input:focus,
.field select:focus,
.field textarea:focus {
  outline: none;
  border-color: #5cc8ff;
}

.stat {
  display: flex;
  justify-content: space-between;
  align-items: baseline;
  font-size: 13px;
  color: #b9b9c4;
  margin-bottom: 16px;
  padding: 10px;
  background: #1c1c20;
  border-radius: 6px;
}

#panel-backdrop-fields {
  display: none;
}

.flag-pill {
  display: inline-block;
  font-size: 0.72rem;
  font-weight: 600;
  padding: 2px 9px;
  border-radius: 999px;
  border: 1px solid #4a4a54;
  background: #34343c;
  color: #b9b9c4;
}

#delete-btn {
  width: 100%;
  background: #4a2a2a;
  color: #f0c0c0;
  border: 1px solid #6a3a3a;
  border-radius: 6px;
  padding: 8px;
  font-size: 13px;
  cursor: pointer;
}

#delete-btn:hover {
  background: #5a3232;
}

#help-btn,
#settings-btn {
  border-radius: 999px;
  padding: 8px 14px;
  font-weight: 600;
}

/* Shared by #help-overlay and #settings-overlay — a centered modal panel over a dimmed backdrop. */
.overlay {
  position: fixed;
  inset: 0;
  background: rgba(10, 10, 12, 0.55);
  z-index: 20;
  display: flex;
  align-items: center;
  justify-content: center;
}

.overlay-panel {
  width: 480px;
  max-width: calc(100vw - 48px);
  max-height: calc(100vh - 96px);
  overflow-y: auto;
  background: #28282e;
  border: 1px solid #4a4a54;
  border-radius: 10px;
  padding: 20px 24px;
}

.overlay-panel-header {
  display: flex;
  align-items: center;
  justify-content: space-between;
  margin-bottom: 10px;
}

.overlay-panel-header h2 {
  margin: 0;
  font-size: 16px;
  font-weight: 600;
  color: #e8e8ee;
}

.overlay-close-btn {
  background: transparent;
  border: none;
  color: #b9b9c4;
  font-size: 20px;
  line-height: 1;
  cursor: pointer;
  padding: 4px;
}

.overlay-close-btn:hover {
  color: #e8e8ee;
}

#help-panel ul {
  margin: 0;
  padding-left: 20px;
  color: #c7c7d0;
  font-size: 13px;
  line-height: 1.7;
}

#help-panel li {
  margin-bottom: 6px;
}

#help-panel strong {
  color: #e8e8ee;
}

#settings-panel p {
  margin: 0 0 14px;
  color: #c7c7d0;
  font-size: 13px;
  line-height: 1.6;
}

.settings-row {
  display: flex;
  gap: 10px;
  margin-bottom: 14px;
}

.settings-row:last-child {
  margin-bottom: 0;
}

.settings-row button {
  flex: 1;
  background: #34343c;
  color: #e8e8ee;
  border: 1px solid #4a4a54;
  border-radius: 6px;
  padding: 10px;
  font-size: 13px;
  cursor: pointer;
}

.settings-row button:hover {
  background: #3d3d47;
}

.settings-divider {
  border: none;
  border-top: 1px solid #3a3a42;
  margin: 16px 0;
}

/* Same shape as any other settings button, just tinted to read as destructive/irreversible —
   matches the confirm() prompt main.js still shows before this actually does anything. Selector
   specificity matches .settings-row button above so this doesn't need !important to win. */
.settings-row button.settings-danger-btn {
  border-color: #7a3535;
  color: #f0b4b4;
}

.settings-row button.settings-danger-btn:hover {
  background: #3d2626;
}

/* A lightweight command-palette-style quick switcher (? key, or the Jump button) — reuses
   .overlay/.overlay-panel's dimmed backdrop + centered card, but skips the header/close-button
   furniture those use: this is meant to feel instant (type, arrow, Enter), not like a settings
   dialog, and Escape/click-outside already close it. */
#jump-panel {
  --jump-max-height: 70vh; /* a custom property, not a plain value, so #jump-results below can
    size itself off the SAME number rather than a second hardcoded one that could quietly drift
    out of sync with it (see the mobile override, which only ever needs to change this one) */
  width: 480px;
  max-width: calc(100vw - 48px);
  max-height: var(--jump-max-height);
  padding: 10px;
  display: flex;
  flex-direction: column;
}

#jump-input {
  background: #1c1c20;
  border: 1px solid #4a4a54;
  border-radius: 6px;
  color: #e8e8ee;
  padding: 10px 12px;
  font-size: 15px;
  font-family: inherit;
  outline: none;
}

#jump-input:focus {
  border-color: #5cc8ff;
}

/* A fixed height (not just a max-height that shrinks to fit) — .overlay centers #jump-panel as a
   whole, so if this instead only grew/shrank with the result count, the INPUT's own position
   would drift up and down every keystroke along with it. Reserving the same space always keeps
   the input's position rock-stable; with few results that just means empty space below them
   (normal for a command palette), and with many, this is what scrolls. Reads --jump-max-height
   off #jump-panel (60px is the input's own height plus this margin) rather than its own
   independent vh guess, so the two can never mismatch and clip the input off the panel's bottom. */
#jump-results {
  margin-top: 8px;
  height: calc(var(--jump-max-height) - 60px);
  overflow-y: auto;
}

.jump-result-row {
  display: flex;
  align-items: baseline;
  gap: 9px;
  padding: 8px 10px;
  border-radius: 6px;
  cursor: pointer;
  font-size: 14px;
  color: #e8e8ee;
}

.jump-result-row:hover,
.jump-result-row-active {
  background: #34343c;
}

.jump-result-kind {
  flex-shrink: 0;
  font-size: 10.5px;
  font-weight: 600;
  color: #8a8a94;
  text-transform: uppercase;
  letter-spacing: 0.03em;
}

/* Pushed to the far right (margin-left:auto) rather than sitting right after the label — reads
   as a trailing "assigned to" tag, not a second title. */
.jump-result-assignee {
  flex-shrink: 0;
  margin-left: auto;
  font-size: 12px;
  color: #8a8a94;
}

.jump-result-empty {
  padding: 8px 10px;
  color: #8a8a94;
  font-size: 13px;
}

/* Narrow/touch screens: the toolbar and side-panel are sized and positioned for a wide desktop
   window above this — both assume plenty of spare horizontal room, which a phone doesn't have
   (the two would otherwise sit on top of each other; see the toolbar's fixed top-left and the
   side-panel's fixed top-right, both anchored independently with no shared layout). This
   reflows both to fit, and enlarges tap targets generally. */
@media (max-width: 680px) {
  #toolbar {
    right: 16px; /* forces a width, so flex-wrap actually has something to wrap against */
    flex-wrap: wrap;
    gap: 6px;
  }

  #toolbar button,
  #help-btn,
  #settings-btn {
    padding: 9px 11px;
    font-size: 13px;
  }

  /* A bottom sheet instead of a floating top-right card — the side panel is shown whenever
     anything is selected (including the "no selection" empty state), so on a phone it needs a
     spot that never collides with the toolbar rather than one more fixed corner. */
  #side-panel {
    top: auto;
    right: 0;
    bottom: 0;
    left: 0;
    width: 100%;
    max-height: 45vh;
    border-radius: 14px 14px 0 0;
    border-width: 1px 0 0 0;
    padding: 14px 16px calc(14px + env(safe-area-inset-bottom));
  }

  /* Fullscreen already fits any width on its own (see #task-list-panel above) — just trim the
     generous desktop side padding, which would otherwise eat a big chunk of a phone screen. No
     top padding here either, same as the desktop rule — #task-list-sticky carries its own (see
     its own comment): a leftover top padding on THIS element left a visible gap above the
     header once scrolled, since the sticky header pins below it rather than absorbing it. */
  #task-list-panel {
    padding: 0 16px 40px;
  }

  #task-list-header {
    gap: 10px;
  }

  #task-list-header h2 {
    font-size: 19px;
  }

  .overlay-panel {
    padding: 16px 18px;
  }

  /* Roomier on a phone rather than a modest centered box — more of the screen is touch target,
     and there's less horizontal room to spare for anything else to share it with anyway.
     #jump-results reads this same variable (see its own comment), so it grows to match with
     nothing further to keep in sync here. */
  #jump-panel {
    --jump-max-height: 88vh;
  }
}
