/* The Actions tool — /actions.
   Ported from the 3.0 kit's Tools.dc.html, whose Actions screen begins at line 106.

   Loaded via yield :page_stylesheets, not on every page — a ranked action list has
   nothing to say to any other surface.

   Everything here resolves through --zw-* tokens. Green appears in exactly two places,
   both of them measurement: the impact/effort dots and the done checkmark. Every CTA is
   the action blue. That split is 3.0's colour law and green_is_never_a_button_test.rb
   enforces the button half of it. */

/* Matches the site header rather than the kit's 1440px tool measure, for the reason
   calendar_tool.css records: a tool surface wider than the menu above it reads as a
   broken page rather than a wide one. Mirrored as values so the two can be compared. */
.zw-act-page {
  width: 100%;
  max-width: 80rem; /* Tailwind max-w-7xl, the site header's measure */
  margin: 0 auto;
  padding: 28px 1rem 56px; /* px-4 */
}

@media (min-width: 640px) {
  .zw-act-page { padding-inline: 1.5rem; } /* sm:px-6 */
}

@media (min-width: 1024px) {
  .zw-act-page { padding-block: 44px 72px; padding-inline: 2rem; } /* lg:px-8 */
}

/* --- masthead -------------------------------------------------------------- */

.zw-act-title {
  font-family: var(--zw-font-serif);
  font-size: 32px;
  font-weight: 600;
  letter-spacing: -0.015em;
  line-height: 1.15;
  color: var(--zw-ink);
  margin: 0 0 6px;
}

.zw-act-dek {
  margin: 0 0 26px;
  font-size: 15px;
  line-height: 1.6;
  color: var(--zw-muted);
  max-width: 620px;
}

/* --- shell ----------------------------------------------------------------- */

.zw-act-shell {
  display: grid;
  grid-template-columns: minmax(0, 1fr);
  gap: 28px;
  align-items: start;
}

@media (min-width: 1024px) {
  .zw-act-shell { grid-template-columns: minmax(0, 1fr) 320px; gap: 44px; }
}

/* A grid child defaults to min-width:auto, so one long unbroken word — a pasted URL in an
   action's summary — can push the column wider than its track and shove the sidebar off. */
.zw-act-main { min-width: 0; }

/* --- band headers ---------------------------------------------------------- */

.zw-act-band {
  display: flex;
  align-items: center;
  gap: 12px;
  margin: 0 0 8px 2px;
}

/* The kit separates bands with a 34px gap below the LIST, not above the header, so a
   band's label sits tight to its own items rather than floating between two groups. */
.zw-act-list { margin-bottom: 34px; }

/* "Yours" is the one label that sits INSIDE a list rather than above one, so nothing below
   it supplies the gap other band labels inherit — it needs its own, or it collides with the
   shared action directly above. Less than a band gap, because it subdivides a band rather
   than starting one. */
.zw-act-list > .zw-act-band { margin-top: 18px; }

/* Except for a list nested in a list: the Yours list renders inside the Single Actions one,
   which already carries the band gap. Its own would push the cap toggle away from the rows
   the toggle belongs to. */
.zw-act-list--tight { margin-bottom: 0; }

.zw-act-band__label {
  font-size: 16px;
  font-weight: 600;
  letter-spacing: -0.01em;
  color: var(--zw-pin-slate);
  white-space: nowrap;
}

.zw-act-band__rule {
  flex: 1;
  height: 1px;
  background: var(--zw-border-warm);
}

.zw-act-band__meta {
  font-size: 13px;
  color: var(--zw-muted);
  white-space: nowrap;
}

/* --- single actions -------------------------------------------------------- */

.zw-act-list { display: grid; gap: 1px; }

/* A Single Action is a ROW, not a card, until you open it.
   Kit values (Tools.dc.html:2246-2250, computed per item):
     closed  background transparent · border transparent · no shadow · padding 11px 18px
     open    background #faf8f4     · border #ece9e3     · lift shadow · padding 16px 18px · margin 6px 0
     hover   background #faf8f4
   Shipping these as permanently white bordered cards was the "doesn't look like the mock
   up" defect: four boxed cards where the kit has a flush chromeless list that lifts only
   the item under discussion.

   `#faf8f4` resolves to --zw-surface-warm (#fbfaf7), whose declared role is exactly "row
   hover, quiet fills" — one point per channel apart and imperceptible, which is preferable
   to a second near-identical token. The open shadow uses --zw-shadow-float (10px 28px)
   against the kit's 8px 26px, for the same reason. */
.zw-act-item {
  padding: 11px 18px;
  background: transparent;
  border: 1px solid transparent;
  border-radius: var(--zw-radius-md);
  transition: background var(--dur-3) var(--zw-ease-out),
              box-shadow var(--dur-3) var(--zw-ease-out),
              border-color var(--dur-3) var(--zw-ease-out);
}

.zw-act-item:hover { background: var(--zw-surface-warm); }

/* :has() rather than a class toggled in JS — the <details> already holds the open state,
   and duplicating it into a class gives two sources of truth that can disagree. */
.zw-act-item:has(details[open]) {
  margin: 6px 0;
  padding: 16px 18px;
  background: var(--zw-surface-warm);
  border-color: var(--zw-border-warm);
  box-shadow: var(--zw-shadow-float);
}

.zw-act-item__row { display: flex; align-items: flex-start; gap: 13px; }

.zw-act-check__form { margin: 0; flex: none; }

/* Green, and correctly so: a completed action is a measurement, not an invitation. */
.zw-act-check {
  display: flex;
  align-items: center;
  justify-content: center;
  width: 20px;
  height: 20px;
  flex: none;
  margin-top: 1px;
  padding: 0;
  font-size: 11px;
  line-height: 1;
  color: transparent;
  background: transparent;
  /* The kit's #d5d0c7, not one of the structural hairlines. An unchecked box outlined in
     --zw-border-warm (#ece9e3, 1.21:1 on white) is nearly invisible — reported as "way
     lower contrast than in the spec", and correctly. */
  border: 1.5px solid var(--zw-border-warm-strong);
  /* 5px, from the kit. A tick box is square; rounding it to a circle turns a checkbox
     into a radio button, which says "pick one of these" rather than "tick what you did". */
  border-radius: 5px;
  cursor: pointer;
  transition: background var(--dur-2) var(--zw-ease-out), border-color var(--dur-2) var(--zw-ease-out);
}

.zw-act-check:hover { border-color: var(--zw-ladder-1); }

.zw-act-check--on {
  background: var(--zw-ladder-1);
  border-color: var(--zw-ladder-1);
  color: var(--zw-ladder-1-ink);
}

.zw-act-item__body { flex: 1; min-width: 0; }

.zw-act-item__summary {
  display: flex;
  align-items: center;
  gap: 8px;
  cursor: pointer;
  list-style: none;
}

.zw-act-item__summary::-webkit-details-marker { display: none; }

.zw-act-item__title {
  font-size: 15px;
  font-weight: 500;
  color: var(--zw-ink);
}

/* Done is lighter text, NOT a strikethrough.
   The kit strikes it through (`strike: isDone ? "line-through" : "none"`), and the owner
   overruled that: a struck line reads as cancelled or withdrawn, where a finished action is
   something you did. --zw-quiet is the kit's own done-text colour (#9a978f) — the recession
   carries the meaning on its own.
   The swap card's "from" keeps its strikethrough: there it means "stop buying this", which
   is a different statement from "you have done this". */
.zw-act-item__title--done { color: var(--zw-quiet); text-decoration: none; }

/* A personal row SWAPS for its editor rather than sitting above it, which is what the kit
   does (an edited row is filtered out of the list and the composer takes its place). Left
   stacked, the title appeared twice — once as the summary and once as the input's own
   placeholder. The shared list's rows keep their summary, because there the title is the
   heading for a description rather than a field you are editing. */
.zw-act-item--personal details[open] > .zw-act-item__summary { display: none; }

/* An unnamed to-do reads as a blank waiting to be filled, not as a thing called "New
   action": lighter weight and a recessive colour, as the kit has it (titleWeight 400,
   titleFg #b9b5ac). */
.zw-act-item__title--untitled { font-weight: 400; color: var(--zw-whisper); }

.zw-act-flag {
  display: inline-flex;
  align-items: center;
  align-self: center;
  gap: 5px;
  padding: 2px 8px 2px 6px;
  font-size: 11px;
  font-weight: 600;
  color: var(--zw-ladder-1);
  background: var(--zw-green-50);
  border-radius: var(--zw-radius-pill);
  white-space: nowrap;
}

.zw-act-flag__star { display: flex; }

.zw-act-item__detail { display: grid; gap: 8px; margin-top: 10px; }

.zw-act-item__dek,
.zw-act-item__fit,
.zw-act-item__scores {
  margin: 0;
  font-size: 14px;
  line-height: 1.55;
  color: var(--zw-muted);
}

.zw-act-item__fit { color: var(--zw-pin-slate); font-weight: 500; }

.zw-act-item__scores { display: flex; flex-wrap: wrap; gap: 18px; }

.zw-act-score {
  display: inline-flex;
  align-items: center;
  gap: 7px;
  font-size: 12px;
  color: var(--zw-faint);
}

/* --- rating dots ----------------------------------------------------------- */

.zw-act-dots { display: inline-flex; gap: 3px; }

.zw-act-dot {
  width: 6px;
  height: 6px;
  border-radius: 999px;
  background: var(--zw-border-warm);
}

.zw-act-dot--on { background: var(--zw-ladder-1); }

/* --- ghost button ---------------------------------------------------------- */

.zw-act-ghost__form { margin: 0; }

/* button_to wraps the button in a form, so the auto-margin has to live on the wrapper —
   on the button it would only push within a form that is already only as wide as it is. */
.zw-act-ghost__form--skip { margin-left: auto; }

/* The kit's row of secondary actions: filled warm pills with NO border, not outlined
   rectangles. Bordered rects read as a form; these read as a row of quiet offers. */
.zw-act-ghost {
  padding: 6px 12px;
  font-size: 13px;
  font-weight: 600;
  color: var(--zw-ink-2, var(--zw-muted));
  background: var(--zw-panel);
  border: none;
  border-radius: var(--zw-radius-pill);
  cursor: pointer;
  white-space: nowrap;
  transition: background var(--dur-2) var(--zw-ease-out), color var(--dur-2) var(--zw-ease-out);
}

.zw-act-ghost:hover { background: var(--zw-border-warm-grid); color: var(--zw-ink); }

.zw-act-item__actions { display: flex; align-items: center; gap: 8px; }

/* "Not for me" sits at the far right of the row and is quieter than the offers beside it:
   the kit gives it margin-left:auto and no fill (Tools.dc.html:171). Turning something down
   should not compete with the two buttons inviting you to do it. */
.zw-act-ghost--skip {
  margin-left: auto;
  padding: 6px 10px;
  background: none;
}

.zw-act-ghost--skip:hover { background: var(--zw-border-warm-grid); color: var(--zw-ink); }

/* --- the one CTA style: blue, because it acts ------------------------------ */

.zw-act-cta {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  padding: 7px 14px;
  font-size: 13px;
  font-weight: 600;
  color: var(--zw-surface);
  background: var(--zw-blue-700);
  border: none;
  border-radius: var(--zw-radius-sm);
  cursor: pointer;
  white-space: nowrap;
  transition: background var(--dur-2) var(--zw-ease-out);
}

.zw-act-cta:hover { background: var(--zw-blue-800); color: var(--zw-surface); }

/* The overflow link under a capped band. Quiet, aligned with the row titles above it rather
   than the card edge, so it reads as the end of the list instead of a control beside it. */
.zw-act-more {
  display: inline-block;
  margin-top: 10px;
  font-size: 13px;
  font-weight: 600;
  color: var(--zw-blue-700);
}

.zw-act-more:hover { color: var(--zw-blue-800); }

/* --- swaps ----------------------------------------------------------------- */

.zw-act-swap {
  display: block;
  padding: 16px 18px;
  border: 1px solid var(--zw-border-warm-2);
  border-radius: var(--zw-radius-md);
  background: var(--zw-surface);
  box-shadow: var(--zw-shadow-sm);
  transition: box-shadow var(--dur-2) var(--zw-ease-out), border-color var(--dur-2) var(--zw-ease-out);
}

.zw-act-swap:hover { box-shadow: var(--zw-shadow-md); border-color: var(--zw-border-warm); }
.zw-act-swap:hover .zw-act-swap__to,
.zw-act-swap:hover .zw-act-swap__title { color: var(--zw-blue-700); }

.zw-act-swap__head { display: flex; align-items: center; justify-content: space-between; gap: 10px; }

/* The children are spans inside an anchor now, so the ones that were <p> need their own
   block behaviour back. */
.zw-act-swap__dek,
.zw-act-swap__meta { display: block; }

.zw-act-swap__title { font-size: 15px; font-weight: 600; color: var(--zw-ink); }

/* The pair is the heading when we have one, so it carries the heading's weight rather
   than sitting under a title that repeated it. */
.zw-act-swap__pair {
  display: flex;
  align-items: center;
  flex-wrap: wrap;
  gap: 8px;
  margin: 0;
  font-size: 15px;
}

.zw-act-swap__from { color: var(--zw-faint); text-decoration: line-through; }
.zw-act-swap__arrow { color: var(--zw-quiet); }
.zw-act-swap__to { color: var(--zw-ink); font-weight: 600; }

.zw-act-swap__dek { margin: 8px 0 0; font-size: 14px; line-height: 1.55; color: var(--zw-muted); }

.zw-act-swap__meta {
  display: inline-block;
  margin-top: 8px;
  font-size: 12px;
  color: var(--zw-faint);
}

/* --- petitions ------------------------------------------------------------- */

.zw-act-petition {
  padding: 18px 20px;
  border: 1px solid var(--zw-border-warm-2);
  border-radius: var(--zw-radius-md);
  background: var(--zw-surface);
  box-shadow: var(--zw-shadow-sm);
}

.zw-act-petition__head {
  display: flex;
  align-items: flex-start;
  justify-content: space-between;
  gap: 12px;
  margin-bottom: 12px;
}

.zw-act-petition__title { font-size: 15px; font-weight: 600; color: var(--zw-ink); }
.zw-act-petition__title:hover { color: var(--zw-blue-700); }

.zw-act-petition__scope {
  display: block;
  margin-top: 3px;
  font-size: 12px;
  color: var(--zw-faint);
}

.zw-act-petition__bar { margin-bottom: 8px; }

.zw-act-petition__count { margin: 0; font-size: 13px; color: var(--zw-muted); }
.zw-act-petition__count strong { color: var(--zw-ink); }

.zw-act-petition__dek { margin: 8px 0 0; font-size: 14px; line-height: 1.55; color: var(--zw-muted); }

/* --- masthead: title + the setup as a sentence ------------------------------ */

.zw-act-masthead { margin-bottom: 26px; }

.zw-act-sentence {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  gap: 6px;
  margin: 8px 0 0;
  font-size: 16px;
  color: var(--zw-muted);
}

/* The two editable words. Dashed underline so they read as answerable, not as fields —
   the sentence should look like prose that happens to be adjustable. */
.zw-act-sentence__word {
  appearance: none;
  -webkit-appearance: none;
  /* A select sizes to its WIDEST option, which ran the underline 200px past "student" and
     broke the sentence into two halves. field-sizing shrinks it to the chosen value; where it
     is unsupported the max-width keeps the overrun to something a sentence survives. */
  field-sizing: content;
  max-width: 13ch;
  padding: 0;
  font-size: 16px;
  font-weight: 600;
  color: var(--zw-ink);
  background: none;
  border: none;
  border-bottom: 1px dashed var(--zw-border-warm-strong);
  border-radius: 0;
  cursor: pointer;
}

.zw-act-sentence__word:hover { border-bottom-color: var(--zw-ink); }
.zw-act-sentence__word:focus { outline: none; border-bottom-style: solid; border-bottom-color: var(--zw-blue-700); }

/* One editable word: the native select, with a styled menu layered over it on wide screens.
   The select is always the field — it just becomes invisible once the menu is doing the
   showing, so there is still exactly one control and one value. */
.zw-act-choice { position: relative; display: inline-flex; }

.zw-act-choice__menu-wrap { display: none; }

/* Enhanced (desktop): the menu shows and the select goes transparent ON TOP of it, so a click
   still lands on the real control for anything relying on it, while the menu is what you see.
   Not `display: none` on the select — a hidden field is skipped by some autofill and by
   Capybara's default visibility, and it is still the thing that submits. */
.zw-act-choice--enhanced .zw-act-choice__menu-wrap { display: inline-flex; }

.zw-act-choice--enhanced .zw-act-choice__native {
  position: absolute;
  inset: 0;
  width: 100%;
  opacity: 0;
  pointer-events: none;
}

.zw-act-choice__label {
  padding: 0;
  font-size: 16px;
  font-weight: 600;
  color: var(--zw-ink);
  background: none;
  border: none;
  border-bottom: 1px dashed var(--zw-border-warm-strong);
  cursor: pointer;
  white-space: nowrap;
}

.zw-act-choice__label:hover { border-bottom-color: var(--zw-ink); }

/* The part a native select cannot give us. */
.zw-act-choice__menu {
  position: absolute;
  top: calc(100% + 6px);
  left: 0;
  z-index: 20;
  display: grid;
  min-width: 190px;
  padding: 6px;
  background: var(--zw-surface);
  border: 1px solid var(--zw-border-warm-2);
  border-radius: var(--zw-radius-md);
  box-shadow: var(--zw-shadow-float);
}

.zw-act-choice__option {
  padding: 7px 10px;
  font-size: 14px;
  text-align: left;
  white-space: nowrap;
  color: var(--zw-ink);
  background: none;
  border: none;
  border-radius: var(--zw-radius-sm);
  cursor: pointer;
}

.zw-act-choice__option:hover { background: var(--zw-surface-warm); }

.zw-act-choice__option--on { font-weight: 600; color: var(--zw-blue-700); }

/* --- the two-column shell -------------------------------------------------- */

.zw-act-grid {
  display: grid;
  grid-template-columns: minmax(0, 1fr);
  gap: 28px;
  align-items: start;
}

@media (min-width: 1024px) {
  .zw-act-grid { grid-template-columns: minmax(0, 1fr) 360px; gap: 44px; }
  /* Clear of the sticky site header, not tucked under it. --zw-header-h is that header's
     height; the extra 24px is the breathing room the owner asked for. */
  .zw-act-detail { position: sticky; top: calc(var(--zw-header-h) + 24px); }
}

/* --- a row, whatever its kind ---------------------------------------------- */

.zw-act-row {
  display: flex;
  align-items: center;
  gap: 13px;
  padding: 11px 18px;
  border: 1px solid transparent;
  border-radius: var(--zw-radius-md);
  transition: background var(--dur-2) var(--zw-ease-out), border-color var(--dur-2) var(--zw-ease-out);
}

.zw-act-row:hover { background: var(--zw-surface-warm); }

/* Selected reads as the row the panel is describing — a quiet tie between the two columns,
   not a second emphasis competing with the panel itself. */
.zw-act-row--selected { background: var(--zw-surface-warm); border-color: var(--zw-border-warm); }

/* Rows past a band's cap: rendered, hidden, revealed by the toggle without a request. */
.zw-act-row--hidden { display: none; }
.zw-act-row--revealed { display: flex; }

.zw-act-row__form { margin: 0; flex: none; }

.zw-act-row__body {
  display: flex;
  align-items: center;
  gap: 8px;
  flex: 1;
  min-width: 0;
  padding: 0;
  background: none;
  border: none;
  text-align: left;
  cursor: pointer;
}

.zw-act-row__title { font-size: 15px; font-weight: 500; color: var(--zw-ink); }

.zw-act-row--done .zw-act-row__title { color: var(--zw-quiet); }

.zw-act-row__status { font-size: 13px; color: var(--zw-faint); white-space: nowrap; }

/* A commitment, not a checkmark: starting a run or adding your name is a different gesture
   from ticking something off, so it gets a different control. */
.zw-act-commit {
  display: flex;
  align-items: center;
  justify-content: center;
  width: 20px;
  height: 20px;
  flex: none;
  color: var(--zw-faint);
  background: transparent;
  border: 1.5px solid var(--zw-border-warm-strong);
  border-radius: 999px;
  cursor: pointer;
  transition: background var(--dur-2) var(--zw-ease-out), color var(--dur-2) var(--zw-ease-out);
}

.zw-act-commit:hover { border-color: var(--zw-ladder-1); color: var(--zw-ladder-1); }

.zw-act-commit--on {
  color: var(--zw-ladder-1-ink);
  background: var(--zw-ladder-1);
  border-color: var(--zw-ladder-1);
}

/* --- the detail panel ------------------------------------------------------ */

.zw-act-detail {
  padding: 18px 20px;
  background: var(--zw-surface);
  border: 1px solid var(--zw-border-warm-2);
  border-radius: var(--zw-radius-md);
  box-shadow: var(--zw-shadow-hairline);
}

.zw-act-detail__head { display: flex; align-items: center; gap: 10px; margin-bottom: 14px; }

.zw-act-detail__meta { font-size: 12px; color: var(--zw-faint); }

.zw-act-detail__close {
  display: flex;
  align-items: center;
  justify-content: center;
  width: 22px;
  height: 22px;
  margin-left: auto;
  padding: 0;
  font-size: 13px;
  color: var(--zw-faint);
  background: none;
  border: none;
  border-radius: var(--zw-radius-pill);
  cursor: pointer;
}

.zw-act-detail__close:hover { background: var(--zw-border-warm-grid); color: var(--zw-ink); }

.zw-act-detail__body { display: grid; gap: 12px; }

.zw-act-detail__title {
  margin: 0;
  font-family: var(--zw-font-serif);
  font-size: 22px;
  font-weight: 600;
  letter-spacing: -0.015em;
  line-height: 1.2;
  color: var(--zw-ink);
}

.zw-act-detail__dek,
.zw-act-detail__why,
.zw-act-detail__prompt,
.zw-act-detail__count { margin: 0; font-size: 14px; line-height: 1.55; color: var(--zw-muted); }

.zw-act-detail__count strong { color: var(--zw-ink); }
.zw-act-detail__fit { margin: 0; font-size: 14px; font-weight: 500; color: var(--zw-pin-slate); }

/* Stacked, so the replacement reads as the answer to the thing above it. */
.zw-act-detail__swap { display: grid; gap: 2px; margin: 0; font-size: 14px; }
.zw-act-detail__from { color: var(--zw-faint); text-decoration: line-through; }
.zw-act-detail__to { color: var(--zw-ink); font-weight: 600; }

.zw-act-detail__scores { display: flex; flex-wrap: wrap; gap: 18px; margin: 0; }
.zw-act-detail__links { display: flex; flex-wrap: wrap; gap: 8px; }

/* "Not for me" carries no pill. It sits beside the primary action and declining should not
   look like a second thing to do — the same call as the old --skip modifier. */
.zw-act-detail__foot .zw-act-ghost {
  padding: 6px 4px;
  background: none;
  color: var(--zw-faint);
}

.zw-act-detail__foot .zw-act-ghost:hover { background: none; color: var(--zw-ink); }

.zw-act-detail__foot {
  display: flex;
  align-items: center;
  gap: 8px;
  margin-top: 16px;
  padding-top: 14px;
  border-top: 1px solid var(--zw-border-warm-inner);
}

.zw-act-detail__primary-form { margin: 0; flex: 1; }

.zw-act-detail__primary {
  width: 100%;
  padding: 9px 16px;
  font-size: 14px;
  font-weight: 600;
  color: var(--zw-surface);
  background: var(--zw-blue-700);
  border: none;
  border-radius: var(--zw-radius-sm);
  cursor: pointer;
  transition: background var(--dur-2) var(--zw-ease-out);
}

.zw-act-detail__primary:hover { background: var(--zw-blue-800); }

.zw-act-detail__empty { padding: 22px 4px; text-align: center; }
.zw-act-detail__empty-icon { display: inline-flex; color: var(--zw-whisper); }
.zw-act-detail__empty-title { margin-top: 10px; font-size: 15px; font-weight: 600; color: var(--zw-ink); }
.zw-act-detail__empty-dek { margin: 6px 0 0; font-size: 14px; line-height: 1.55; color: var(--zw-faint); }

/* The band toggle is a button now, not a link — it expands in place. */
.zw-act-showall {
  justify-self: start;
  /* Flush with the band label above it, not indented to the row text — it belongs to the band,
     not to the list of rows. */
  margin: 10px 0 0;
  padding: 6px 0;
  font-size: 14px;
  /* A button centres its text and, as a grid item, stretches the full column — which put the
     label in the middle of the list. Both have to be undone, not just one. */
  text-align: left;
  color: var(--zw-faint);
  background: none;
  border: none;
  cursor: pointer;
}

/* Text, not a pill. A filled rounded hover on a flush chromeless list read as a stray
   button floating under the rows — the label is a quiet control, so it darkens and
   underlines rather than growing a shape. */
.zw-act-showall:hover { color: var(--zw-ink); text-decoration: underline; }

/* --- Yours: the reader's own to-dos ---------------------------------------- */

/* Add-row and composer SWAP rather than stack, as the kit has it. The summary is hidden
   while the details is open so only one of the two is ever on screen. */
.zw-act-add__form { margin: 0; }

/* A button that creates the row, not a disclosure that reveals a form. */
.zw-act-add__row {
  width: 100%;
  background: none;
  border: none;
  text-align: left;
  display: flex;
  align-items: center;
  gap: 13px;
  padding: 11px 18px;
  cursor: pointer;
  list-style: none;
  border-radius: var(--zw-radius-md);
  transition: background var(--dur-2) var(--zw-ease-out);
}

.zw-act-add__row::-webkit-details-marker { display: none; }
.zw-act-add__row:hover { background: var(--zw-surface-warm); }

/* A dashed tick box, so the row reads as a blank waiting to be filled. Kit line 222. */
.zw-act-add__plus {
  display: flex;
  align-items: center;
  justify-content: center;
  width: 20px;
  height: 20px;
  flex: none;
  font-size: 14px;
  line-height: 1;
  color: var(--zw-faint);
  border: 1.5px dashed var(--zw-border-warm-strong);
  border-radius: 5px;
}

.zw-act-add__label { font-size: 16px; color: var(--zw-faint); }

/* The editor is the row's own content: the row itself is already the lifted card once open,
   so a second card floating inside it would be a card in a card. */
.zw-act-composer,
.zw-act-composer--edit {
  margin: 10px 0 0;
  padding: 0;
  background: none;
  border: none;
  box-shadow: none;
}

.zw-act-composer__body {
  display: grid;
  grid-template-columns: auto minmax(0, 1fr);
  gap: 13px;
  align-items: start;
}

/* Lines the inputs up with the rows above. Solid, not dashed: it stands in for a real tick
   box rather than for an empty one. */
.zw-act-composer__mark {
  width: 20px;
  height: 20px;
  flex: none;
  margin-top: 1px;
  border: 1.5px solid var(--zw-border-warm-strong);
  border-radius: 5px;
}

.zw-act-composer__fields { display: grid; gap: 7px; min-width: 0; }

/* Borderless and transparent — the kit gives these no underline at all. An input that looks
   like a field turns a quick note into filling in a form. */
.zw-act-composer__title,
.zw-act-composer__note {
  min-width: 0;
  width: 100%;
  padding: 0;
  background: transparent;
  border: none;
  outline: none;
}

.zw-act-composer__title {
  font-size: 16px;
  font-weight: 500;
  letter-spacing: -0.01em;
  color: var(--zw-ink);
}

.zw-act-composer__note { font-size: 14px; color: var(--zw-muted); }

.zw-act-composer__foot {
  display: flex;
  align-items: center;
  gap: 12px;
  margin-top: 14px;
  padding-top: 12px;
  border-top: 1px solid var(--zw-border-warm-inner);
}

.zw-act-composer__hint { font-size: 13px; color: var(--zw-faint); }

/* The kit has no save button — it commits on Enter. We keep one because a form that only
   submits on a keystroke is unusable on a phone, but it stays quiet. */
.zw-act-composer__save {
  margin-left: auto;
  padding: 6px 12px;
  font-size: 13px;
  font-weight: 600;
  color: var(--zw-blue-700);
  background: none;
  border: none;
  border-radius: var(--zw-radius-pill);
  cursor: pointer;
  transition: background var(--dur-2) var(--zw-ease-out);
}

.zw-act-composer__save:hover { background: var(--zw-border-warm-grid); }

.zw-act-composer__form { margin: 0; }
.zw-act-composer__delete-form { margin: 0; }

/* An icon button, not a "Delete" label: it sits beside a save action and should not read as
   the equal-weight second option. Kit line 212. */
.zw-act-composer__delete {
  display: flex;
  align-items: center;
  justify-content: center;
  width: 28px;
  height: 28px;
  padding: 0;
  color: var(--zw-whisper);
  background: none;
  border: none;
  border-radius: 8px;
  cursor: pointer;
  transition: background var(--dur-2) var(--zw-ease-out), color var(--dur-2) var(--zw-ease-out);
}

.zw-act-composer__delete:hover { background: var(--zw-advocacy-track); color: var(--zw-advocacy); }

/* The note, shown on a collapsed row. */
.zw-act-item__note { display: block; margin-top: 2px; font-size: 14px; color: var(--zw-muted); }

/* --- Habits ---------------------------------------------------------------- */

/* Boxed, unlike a Single Action row: a 21-day run with a progress track is something you
   commit to rather than a line you tick. Kit values, Tools.dc.html:278. */
.zw-act-habit {
  padding: 18px 20px;
  background: var(--zw-surface);
  border: 1px solid var(--zw-border-warm-2);
  border-radius: var(--zw-radius-md);
  box-shadow: var(--zw-shadow-hairline);
  transition: box-shadow var(--dur-3) var(--zw-ease-out), border-color var(--dur-3) var(--zw-ease-out);
}

.zw-act-habit:hover { box-shadow: var(--zw-shadow-dock); }

.zw-act-habit__head {
  display: flex;
  align-items: flex-start;
  justify-content: space-between;
  gap: 16px;
}

.zw-act-habit__lead { display: grid; gap: 4px; min-width: 0; }

.zw-act-habit__title { font-size: 16px; font-weight: 600; letter-spacing: -0.01em; color: var(--zw-ink); }
.zw-act-habit__dek { font-size: 14px; line-height: 1.5; color: var(--zw-muted); }

/* Blue, not the kit's green. Starting a habit is an action, and 3.0's own law says green
   measures — the track below this is where the green belongs. */
.zw-act-habit__join {
  flex: none;
  padding: 8px 16px;
  font-size: 14px;
  font-weight: 600;
  color: var(--zw-surface);
  background: var(--zw-blue-700);
  border: 1px solid var(--zw-blue-700);
  border-radius: var(--zw-radius-sm);
  cursor: pointer;
  white-space: nowrap;
  transition: background var(--dur-2) var(--zw-ease-out);
}

.zw-act-habit__join:hover { background: var(--zw-blue-800); color: var(--zw-surface); }

/* Enrolled is a state, not an invitation, so it stops looking like a button to press. */
.zw-act-habit__join--on {
  color: var(--zw-ladder-1);
  background: var(--zw-green-50);
  border-color: var(--zw-green-50);
}

.zw-act-habit__join--on:hover { background: var(--zw-green-50); color: var(--zw-ladder-1); }

.zw-act-habit__track { margin-top: 14px; }

.zw-act-habit__foot { margin-top: 10px; }

.zw-act-habit__cadence { font-size: 13px; color: var(--zw-faint); }

.zw-act-habit__whylink {
  margin-top: 10px;
  font-size: 13px;
  font-weight: 600;
  color: var(--zw-blue-700);
  cursor: pointer;
  list-style: none;
}

.zw-act-habit__whylink::-webkit-details-marker { display: none; }
.zw-act-habit__whylink:hover { color: var(--zw-blue-800); }

.zw-act-habit__whybody {
  margin-top: 12px;
  padding: 12px 14px;
  background: var(--zw-surface-warm);
  border-radius: var(--zw-radius-sm);
}

.zw-act-habit__whybody p { margin: 0 0 8px; font-size: 14px; line-height: 1.55; color: var(--zw-muted); }
.zw-act-habit__whybody p:last-child { margin-bottom: 0; }
