/*
 * B-17 Goat Farm — theme and layout on top of Bootstrap 5.3.
 *
 * Two jobs:
 *   1. Colour. The palette is lifted from the tag badge, so the app, the
 *      printed tag and the scan page look like one thing.
 *   2. Phones. This gets used one-handed at the pen, so every wide table
 *      folds into a stack of labelled rows below the md breakpoint, and
 *      nothing needs a horizontal swipe to read.
 */

:root {
  /*
   * Monochrome. Black, white and grey everywhere, with two exceptions that are
   * not decoration: the withdrawal red and the amber used for a dose or a date
   * that needs attention. Those carry meaning and keep their hue.
   */
  --farm-ink:       #000000;   /* navbar, headings */
  --farm-green:     #000000;   /* accent: buttons, links, tag numbers */
  --farm-green-600: #262626;   /* accent, hovered */
  --farm-green-400: #8a8a8a;   /* accent, disabled or faint */
  --farm-moss:      #111111;
  --farm-cream:     #f5f5f5;   /* card headers, table headings */
  --farm-sand:      #ffffff;   /* page background */
  --farm-line:      #e5e5e5;
  --farm-muted:     #6b6b6b;

  --farm-red:       #b81c1c;   /* the withdrawal banner */
  --farm-amber:     #d98a1f;
  --farm-amber-ink: #8a5a10;
  --farm-blue:      #4a4a4a;   /* was a blue; now simply a lighter grey */

  /*
   * Bootstrap's utilities follow. Success and primary become greys so a badge
   * still separates from its neighbours by tone; danger and warning stay as
   * they are, because a red badge on this app means do not eat the animal.
   */
  --bs-success-rgb: 0, 0, 0;
  --bs-danger-rgb:  184, 28, 28;
  --bs-warning-rgb: 217, 138, 31;
  --bs-primary-rgb: 74, 74, 74;

  --bs-body-bg:        var(--farm-sand);
  --bs-body-color:     #171717;
  --bs-border-color:   var(--farm-line);
  --bs-secondary-color: var(--farm-muted);

  --bs-link-color:       var(--farm-green);
  --bs-link-hover-color: var(--farm-ink);
  --bs-link-color-rgb:   0, 0, 0;

  --bs-border-radius:    .5rem;
  --bs-border-radius-sm: .375rem;

  /*
   * One scale for spacing, corners and depth, so cards, sheets and toasts
   * added later match what is here. Shadows are soft and neutral: depth in
   * grey, never a colour.
   */
  --farm-space-1: .25rem;
  --farm-space-2: .5rem;
  --farm-space-3: .75rem;
  --farm-space-4: 1rem;
  --farm-space-5: 1.5rem;
  --farm-space-6: 2rem;

  --farm-radius-sm: .375rem;
  --farm-radius:    .5rem;
  --farm-radius-lg: .75rem;
  --farm-radius-xl: 1rem;

  --farm-shadow-sm: 0 1px 2px rgba(0, 0, 0, .06), 0 1px 1px rgba(0, 0, 0, .03);
  --farm-shadow:    0 2px 8px rgba(0, 0, 0, .06), 0 1px 2px rgba(0, 0, 0, .05);
  --farm-shadow-lg: 0 12px 32px rgba(0, 0, 0, .12), 0 2px 6px rgba(0, 0, 0, .06);

  /* Type: a clear page title and big headline numbers. */
  --farm-title-size: clamp(1.4rem, 1.15rem + 1vw, 1.75rem);
  --farm-stat-size:  clamp(2rem, 1.6rem + 1.4vw, 2.6rem);

  --farm-focus: var(--farm-ink);
}

body {
  background-color: var(--farm-sand);
  -webkit-text-size-adjust: 100%;
}

/* Numbers that get compared down a column need to line up. */
.display-6, .fs-4, .fw-bold, th, td, .badge { font-variant-numeric: tabular-nums; }

h1, h2, h3, .h3, .h4, .h5 { color: var(--farm-ink); }

/* Never make someone aim at something smaller than a fingertip. */
.btn, .form-control, .form-select, .nav-link, .list-group-item-action {
  min-height: 2.75rem;
}
.btn-sm { min-height: 2.25rem; }
.form-control, .form-select { font-size: 1rem; }   /* 16px: stops iOS zooming on focus */

:focus-visible {
  outline: 2px solid var(--farm-focus);
  outline-offset: 2px;
}
/* On the black navbar, menu and toasts the ring has to be white to be seen. */
.navbar, .farm-offcanvas, .ui-toast { --farm-focus: #fff; }

/* --- brand ---------------------------------------------------------------- */

.brand-mark { width: 34px; height: 34px; object-fit: contain; flex: 0 0 auto; }
.brand-logo { width: 190px; max-width: 60%; height: auto; }

/* --- navbar --------------------------------------------------------------- */

.navbar.bg-dark {
  background-color: var(--farm-ink) !important;
  box-shadow: 0 1px 0 rgba(0, 0, 0, .25);
}
.navbar-brand { font-weight: 700; letter-spacing: -.01em; }
.navbar .btn-link { text-decoration: none; }

.navbar .nav-link {
  display: flex;
  align-items: center;
  gap: .35rem;              /* flex eats the whitespace between text and span */
  border-radius: .4rem;
  padding-inline: .75rem;
}
/* Where you are now, said plainly. */
.navbar .nav-link.active {
  background: rgba(255, 255, 255, .14);
  color: #fff;
  font-weight: 600;
}

/* Your own links (farms, plan, account) under your name on a wide screen. */
.navbar .dropdown-menu { --bs-dropdown-link-active-bg: var(--farm-green); }

/* The mobile menu is an offcanvas panel: full-height rows, easy to hit. */
.farm-offcanvas { background: var(--farm-ink); color: #fff; }
.farm-offcanvas .offcanvas-header { border-bottom: 1px solid rgba(255, 255, 255, .15); }
.farm-offcanvas .nav-link {
  color: rgba(255, 255, 255, .82);
  min-height: 3.25rem;
  font-size: 1.05rem;
  border-radius: .5rem;
  margin-bottom: .15rem;
}
.farm-offcanvas .nav-link.active { background: var(--farm-green); color: #fff; }
.farm-offcanvas .btn-close { filter: invert(1) grayscale(1) brightness(2); }

/* --- cards ---------------------------------------------------------------- */

.card {
  --bs-card-border-color: var(--farm-line);
  --bs-card-cap-bg: var(--farm-cream);
  --bs-card-bg: #fff;
  --bs-card-border-radius: var(--farm-radius-lg);
  --bs-card-inner-border-radius: calc(var(--farm-radius-lg) - 1px);
  box-shadow: var(--farm-shadow-sm);
}
.card-header {
  font-weight: 600;
  color: var(--farm-ink);
  border-bottom-color: var(--farm-line);
}

/* Headline counts on the dashboard and reports. */
.stat .display-6, .stat .h3, .stat .h4 { color: var(--farm-ink); line-height: 1.1; }
.stat .display-6 { font-size: var(--farm-stat-size); font-weight: 700; letter-spacing: -.02em; }
.stat { border-inline-start: 4px solid var(--farm-green); }
/* Money figures have to fit a half-width tile on a phone. */
@media (max-width: 575.98px) {
  .stat .display-6 { font-size: 2rem; }
  .stat .h3 { font-size: 1.4rem; }
  .stat .h4 { font-size: 1.1rem; }
}
.stat-danger  { border-inline-start-color: var(--farm-red); }
.stat-warning { border-inline-start-color: var(--farm-amber); }
.stat-info    { border-inline-start-color: var(--farm-blue); }

/* --- buttons -------------------------------------------------------------- */

.btn-success {
  --bs-btn-bg: var(--farm-green);
  --bs-btn-border-color: var(--farm-green);
  --bs-btn-hover-bg: var(--farm-green-600);
  --bs-btn-hover-border-color: var(--farm-green-600);
  --bs-btn-active-bg: var(--farm-ink);
  --bs-btn-active-border-color: var(--farm-ink);
  --bs-btn-disabled-bg: var(--farm-green-400);
  --bs-btn-disabled-border-color: var(--farm-green-400);
}
.btn-outline-success {
  --bs-btn-color: var(--farm-green);
  --bs-btn-border-color: var(--farm-green);
  --bs-btn-hover-bg: var(--farm-green);
  --bs-btn-hover-border-color: var(--farm-green);
  --bs-btn-active-bg: var(--farm-ink);
  --bs-btn-active-border-color: var(--farm-ink);
}
.btn-outline-dark {
  --bs-btn-color: var(--farm-ink);
  --bs-btn-border-color: #cfcfcf;
  --bs-btn-hover-bg: var(--farm-ink);
  --bs-btn-hover-border-color: var(--farm-ink);
}
.btn-secondary {
  --bs-btn-bg: #4a4a4a;
  --bs-btn-border-color: #4a4a4a;
  --bs-btn-hover-bg: var(--farm-ink);
  --bs-btn-hover-border-color: var(--farm-ink);
}
.btn-outline-secondary { --bs-btn-color: #4a4a4a; --bs-btn-border-color: #cfcfcf; }

/*
 * Danger and warning buttons were still Bootstrap's own red and amber rather
 * than ours — and #dc3545 as text on white is 4.15:1, under the readable
 * threshold. Use the farm colours, darkened where they carry text.
 */
.btn-danger {
  --bs-btn-bg: var(--farm-red);
  --bs-btn-border-color: var(--farm-red);
  --bs-btn-hover-bg: #9d1717;
  --bs-btn-hover-border-color: #9d1717;
  --bs-btn-active-bg: #7d1010;
  --bs-btn-active-border-color: #7d1010;
}
.btn-outline-danger {
  --bs-btn-color: #9d1717;
  --bs-btn-border-color: #d9a9a9;
  --bs-btn-hover-bg: var(--farm-red);
  --bs-btn-hover-border-color: var(--farm-red);
  --bs-btn-active-bg: #7d1010;
  --bs-btn-active-border-color: #7d1010;
}
.btn-warning {
  --bs-btn-bg: var(--farm-amber);
  --bs-btn-border-color: var(--farm-amber);
  --bs-btn-color: #241a06;
  --bs-btn-hover-bg: #c47b16;
  --bs-btn-hover-border-color: #c47b16;
  --bs-btn-hover-color: #241a06;
}
/* Bootstrap's yellow outline is 1.6:1 on white; a dark amber reads (6.9:1),
   and the border is 4:1, enough for a control's edge. */
.btn-outline-warning {
  --bs-btn-color: #7a4f00;
  --bs-btn-border-color: #a8761a;
  --bs-btn-hover-bg: var(--farm-amber);
  --bs-btn-hover-border-color: var(--farm-amber);
  --bs-btn-hover-color: #241a06;
  --bs-btn-active-bg: var(--farm-amber);
  --bs-btn-active-border-color: var(--farm-amber);
  --bs-btn-active-color: #241a06;
}

/* --- badges and status ---------------------------------------------------- */

.badge { font-weight: 600; letter-spacing: .01em; padding: .35em .6em; }
.badge.bg-light { border: 1px solid var(--farm-line); }
.text-caution { color: var(--farm-amber-ink) !important; }

/* --- alerts --------------------------------------------------------------- */

.alert { border: 0; border-inline-start: 4px solid transparent; }
.alert-danger  { background: #fbeaea; color: #7d1010; border-inline-start-color: var(--farm-red); }
.alert-warning { background: #fdf4e3; color: #6d4708; border-inline-start-color: var(--farm-amber); }
.alert-success { background: #f2f2f2; color: #1a1a1a; border-inline-start-color: var(--farm-green); }

/* The withdrawal banner is the one thing on the page that must not be missed. */
.alert-withdrawal {
  background: var(--farm-red);
  color: #fff;
  border-inline-start-color: #7d1010;
}
.alert-withdrawal strong { color: #fff; }

/* --- tables --------------------------------------------------------------- */

.table {
  /* Bootstrap defaults --bs-table-bg to --bs-body-bg; ours is sand, and these
     tables sit on white cards, so say white explicitly. */
  --bs-table-bg: #fff;
  --bs-table-border-color: var(--farm-line);
  --bs-table-hover-bg: #f3f3f3;
  margin-bottom: 0;
}
.table > thead th {
  background-color: var(--farm-cream);
  font-size: .78rem;
  text-transform: uppercase;
  letter-spacing: .04em;
  font-weight: 700;
  color: var(--farm-muted);
  white-space: nowrap;
}
.table-light { --bs-table-bg: var(--farm-cream); }

/* Long lists keep their headings in view while you scroll. */
@media (min-width: 768px) {
  .table-sticky > thead th { position: sticky; top: 0; z-index: 2; background: var(--farm-cream); }
}

.tag-code {
  font-weight: 700;
  letter-spacing: .01em;
  color: var(--farm-green);
  text-decoration: none;
}
.tag-code:hover { color: var(--farm-ink); text-decoration: underline; }

/*
 * Phones: a table with six columns is unreadable, and swiping sideways to find
 * a column is worse. Each row becomes its own block, every cell captioned with
 * the heading it lost. Mark up cells with data-label and the caption appears.
 */
@media (max-width: 767.98px) {
  .table-stack > thead { display: none; }

  .table-stack > tbody > tr {
    display: block;
    padding: .85rem 1rem;
    border-bottom: 1px solid var(--farm-line);
  }
  .table-stack > tbody > tr:last-child { border-bottom: 0; }

  .table-stack > tbody > td,
  .table-stack > tbody > tr > td {
    display: flex;
    flex-wrap: wrap;
    align-items: baseline;
    justify-content: space-between;
    gap: .15rem 1rem;
    width: auto;
    padding: .2rem 0;
    border: 0;
    background: none;
    overflow-wrap: anywhere;
  }
  .table-stack > tbody > tr > td::before {
    content: attr(data-label);
    flex: 0 0 auto;
    color: var(--farm-muted);
    font-size: .8rem;
    font-weight: 600;
    text-transform: uppercase;
    letter-spacing: .03em;
  }
  /* Cells with nothing to caption, and the row's own headline. */
  .table-stack > tbody > tr > td:not([data-label])::before { content: none; }
  .table-stack > tbody > tr > td.stack-title {
    display: block;
    font-size: 1.05rem;
    padding-bottom: .35rem;
  }
  .table-stack > tbody > tr > td.stack-title::before { content: none; }
  .table-stack > tbody > tr > td.stack-hide { display: none; }
  .table-stack > tbody > tr > td.text-end { text-align: start !important; }

  /* An empty list still needs to say so. */
  .table-stack > tbody > tr > td[colspan] { display: block; text-align: center; }

  /* Detail tables (label in a th, value in a td) stack the same way. */
  .table-detail > tbody > tr { display: block; padding: .6rem 1rem; border-bottom: 1px solid var(--farm-line); }
  .table-detail > tbody > tr > th,
  .table-detail > tbody > tr > td { display: block; width: auto !important; border: 0; padding: 0; }
  .table-detail > tbody > tr > th {
    font-size: .78rem;
    text-transform: uppercase;
    letter-spacing: .04em;
    color: var(--farm-muted);
  }
}

/* --- lists ---------------------------------------------------------------- */

.list-group-item { border-color: var(--farm-line); }
.list-group-item-action:hover { background: #f3f3f3; }

/* Empty states should offer the next step, not just report nothing. */
.empty {
  padding: 1.5rem 1rem;
  text-align: center;
  color: var(--farm-muted);
}
.empty a { font-weight: 600; }

/* --- forms ---------------------------------------------------------------- */

.form-label { font-weight: 600; font-size: .9rem; color: var(--farm-ink); }
.form-text { color: var(--farm-muted); }
.form-control:focus, .form-select:focus {
  border-color: var(--farm-green-400);
  box-shadow: 0 0 0 .2rem rgba(0, 0, 0, .14);
}
.card-footer { background: var(--farm-cream); border-top-color: var(--farm-line); }

/* On a phone the Save button should never be somewhere you have to hunt for. */
@media (max-width: 575.98px) {
  .form-actions .btn { width: 100%; }
  .form-actions { gap: .5rem; flex-direction: column-reverse; }
}

/* --- page header ---------------------------------------------------------- */

.page-head {
  display: flex;
  flex-wrap: wrap;
  gap: .5rem 1rem;
  align-items: center;
  justify-content: space-between;
  margin-bottom: 1rem;
}
.page-head h1 { margin: 0; }
.page-head h1.h4 { font-size: var(--farm-title-size); font-weight: 700; letter-spacing: -.01em; }
[dir="rtl"] .page-head h1.h4 { letter-spacing: normal; }   /* spacing breaks Nastaliq's joins */
@media (max-width: 575.98px) {
  .page-head .page-actions { width: 100%; display: flex; gap: .5rem; }
  .page-head .page-actions > * { flex: 1 1 0; }
}

/* --- goat switcher ---------------------------------------------------------
 * Prev / find / next above a goat's page, so walking the herd one animal at a
 * time does not mean bouncing back to the list. On a phone the three buttons
 * share the width; from sm up they sit on the right, "All goats" on the left.
 */
.goat-nav {
  display: grid;
  grid-template-columns: 1fr auto 1fr;   /* switcher dead centre, "All goats" on the left */
  align-items: center;
  gap: .5rem 1rem;
  margin-bottom: 1rem;
}
.goat-nav-back { justify-self: start; }
.goat-nav-step { grid-column: 2; }
.goat-nav-back {
  color: var(--farm-muted);
  text-decoration: none;
  font-size: .9rem;
  white-space: nowrap;
}
.goat-nav-back:hover { color: var(--farm-ink); }

.goat-nav-step {
  display: flex;
  align-items: stretch;
  border: 1px solid var(--farm-line);
  border-radius: 999px;
  background: #fff;
  overflow: hidden;
}
.goat-nav-step .btn {
  --bs-btn-border-width: 0;
  --bs-btn-border-radius: 0;
  --bs-btn-hover-bg: var(--farm-cream);
  --bs-btn-active-bg: var(--farm-line);
  min-height: 2.5rem;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  gap: .4rem;
  line-height: 1.2;
  padding: .25rem .9rem;
  font-size: .9rem;
  white-space: nowrap;
}
.goat-nav-btn { min-width: 2.75rem; color: var(--farm-ink); }
.goat-nav-chev { display: block; flex: 0 0 auto; }
.goat-nav-btn.disabled { color: var(--farm-green-400); opacity: 1; }
.goat-nav-tag { font-weight: 700; font-variant-numeric: tabular-nums; }
.goat-nav-find {
  font-weight: 600;
  border-left: 1px solid var(--farm-line) !important;
  border-right: 1px solid var(--farm-line) !important;
}
.goat-nav-count {
  color: var(--farm-muted);
  font-weight: 400;
  font-size: .8rem;
  font-variant-numeric: tabular-nums;
}

@media (max-width: 575.98px) {
  .goat-nav-back { display: none; }
  .goat-nav { grid-template-columns: 1fr; }
  .goat-nav-step { grid-column: 1; }
  .goat-nav-step .btn { padding-inline: .6rem; }
  .goat-nav-find { flex: 1 1 auto; }
  .goat-nav-count { display: none; }
}

/* The picker: a searchable list of the herd, sliding in from the side. */
.goat-picker { --bs-offcanvas-width: 380px; }
.goat-picker .offcanvas-header { border-bottom: 1px solid var(--farm-line); }
.goat-picker-search { padding: .75rem 1rem; border-bottom: 1px solid var(--farm-line); }
.goat-picker .list-group-item { padding: .6rem 1rem; }
.goat-picker .list-group-item.is-current {
  background: var(--farm-cream);
  box-shadow: inset 3px 0 0 var(--farm-ink);
}
.goat-picker .min-w-0 { min-width: 0; }
.goat-picker .list-group-item[hidden] { display: none !important; }
@media (max-width: 575.98px) { .goat-picker { --bs-offcanvas-width: 100%; } }

@media print { .goat-nav, .goat-picker { display: none !important; } }

/* --- filters -------------------------------------------------------------- */

.filters {
  background: #fff;
  border: 1px solid var(--farm-line);
  border-radius: var(--bs-border-radius);
  padding: .85rem;
}

/* --- due page ------------------------------------------------------------- */

.due-panel .card-header { display: flex; align-items: center; justify-content: space-between; }
.due-row { display: flex; flex-wrap: wrap; align-items: center; gap: .35rem .75rem; }
.due-row .due-meta { color: var(--farm-muted); font-size: .875rem; }
.due-row .due-when { margin-inline-start: auto; }
@media (max-width: 575.98px) {
  .due-row .due-when { margin-inline-start: 0; width: 100%; }
}

/* --- weekly checks -------------------------------------------------------- */

/* One line of the walk-round: what to look at, and the three answers. The
   buttons drop to their own full-width row on a phone so they stay thumb-sized. */
.check-item { display: flex; flex-wrap: wrap; align-items: center; gap: .5rem .75rem; }
.check-item .check-label { flex: 1 1 14rem; }
.check-item .check-states { flex: 0 0 auto; margin-left: auto; }
.check-states .btn { min-width: 5rem; }
@media (max-width: 575.98px) {
  .check-item .check-states { margin-left: 0; width: 100%; }
  .check-states .btn { flex: 1 1 0; min-width: 0; }
}

.check-row { display: flex; flex-wrap: wrap; align-items: center; gap: .35rem .75rem; }
.check-row .check-row-meta { display: flex; flex-wrap: wrap; align-items: center; gap: .25rem .5rem; }
.check-row .check-row-go { margin-left: auto; }
@media (max-width: 575.98px) {
  .check-row .check-row-go { margin-left: 0; width: 100%; }
}

/* --- milking round -------------------------------------------------------- */

/* The litres box stays on the tag's line, even on a phone: the round is a
   column of numbers, and a box on its own line doubles the scrolling. */
.milk-row .check-row-goat { flex: 1 1 0; min-width: 0; }
.milk-row .check-row-meta { order: 3; flex-basis: 100%; }
.milk-row .check-row-go,
.check-row.milk-row .check-row-go { margin: 0; margin-inline-start: auto; width: auto; }
.milk-input { width: 8.5rem; flex-wrap: nowrap; }
details.card > summary { cursor: pointer; list-style: none; }
details.card > summary::-webkit-details-marker { display: none; }
details.card > summary > :last-child::after { content: '▾'; margin-inline-start: .5rem; }
details.card[open] > summary > :last-child::after { content: '▴'; }

/* --- weight chart --------------------------------------------------------- */

.chart-wrap { overflow-x: auto; }
.chart-wrap svg { min-width: 320px; }

/* --- print ---------------------------------------------------------------- */

@media print {
  .navbar, .page-actions, .filters, .card-footer { display: none !important; }
  .card { box-shadow: none; border-color: #ccc; }
}

@media (prefers-reduced-motion: reduce) {
  *, *::before, *::after { animation-duration: .001ms !important; transition-duration: .001ms !important; }
}

/* --- farm full: the page that sells the next animal or seat ---------------- */

.limit-card {
  max-width: 34rem;
  background: #fff;
  border: 1px solid var(--farm-line);
  border-radius: 1rem;
  overflow: hidden;
  box-shadow: 0 10px 30px rgba(0, 0, 0, .08), 0 1px 2px rgba(0, 0, 0, .06);
}
/* Amber, because amber on this app means "needs you" — never decoration. */
.limit-hero {
  display: flex;
  gap: 1rem;
  align-items: flex-start;
  padding: 1.5rem 1.5rem 1.25rem;
  background: linear-gradient(135deg, #fff8ec 0%, #fbe3b8 100%);
  border-bottom: 1px solid #f1d29b;
}
.limit-icon {
  flex: 0 0 auto;
  display: grid;
  place-items: center;
  width: 3.25rem;
  height: 3.25rem;
  border-radius: 50%;
  background: var(--farm-amber);
  color: #fff;
  box-shadow: 0 4px 12px rgba(217, 138, 31, .35);
}
.limit-eyebrow {
  font-size: .75rem;
  font-weight: 700;
  letter-spacing: .06em;
  text-transform: uppercase;
  color: var(--farm-amber-ink);
  margin-bottom: .15rem;
}
.limit-hero p { color: #3d2d10; }
.limit-body { padding: 1.25rem 1.5rem 1.5rem; }

.limit-meter .progress { height: .65rem; background: var(--farm-cream); }
.limit-meter .progress-bar { background: var(--farm-amber); }

.limit-tile {
  height: 100%;
  padding: .85rem 1rem;
  border: 1px solid var(--farm-line);
  border-radius: .75rem;
  background: var(--farm-cream);
}
.limit-tile-next { background: #fff; border: 2px solid var(--farm-ink); }
.limit-price {
  font-size: 1.85rem;
  font-weight: 800;
  line-height: 1.15;
  color: var(--farm-ink);
  font-variant-numeric: tabular-nums;
  white-space: nowrap;
}

.limit-points li {
  display: flex;
  align-items: center;
  gap: .6rem;
  padding: .3rem 0;
}
.limit-points svg {
  flex: 0 0 auto;
  padding: .2rem;
  width: 1.4rem;
  height: 1.4rem;
  border-radius: 50%;
  background: var(--farm-ink);
  color: #fff;
}

.limit-cta { font-weight: 700; padding-block: .85rem; border-radius: .75rem; }

@media (max-width: 575.98px) {
  .limit-hero { padding: 1.25rem 1rem 1rem; gap: .75rem; }
  .limit-body { padding: 1rem; }
  .limit-price { font-size: 1.5rem; }
}

/* --- plan page: buy only what you need --------------------------------- */

.buy-section {
  font-size: .75rem;
  font-weight: 700;
  letter-spacing: .06em;
  text-transform: uppercase;
  color: var(--farm-muted);
  margin-bottom: .6rem;
}
.buy-rows {
  border: 1px solid var(--farm-line);
  border-radius: .75rem;
  overflow: hidden;
}
.buy-row {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  justify-content: space-between;
  gap: .75rem 1rem;
  padding: .9rem 1rem;
  background: #fff;
}
.buy-row + .buy-row { border-top: 1px solid var(--farm-line); }
.buy-row.is-invalid { background: #fdf2f2; }
.buy-row-text { flex: 1 1 12rem; min-width: 0; }
.buy-row-error { flex-basis: 100%; }
.buy-step {
  display: flex;
  align-items: stretch;
  flex: 0 0 auto;
}
.buy-step .btn {
  width: 2.75rem;
  font-size: 1.25rem;
  font-weight: 700;
  line-height: 1;
}
.buy-step .btn:first-child { border-radius: .6rem 0 0 .6rem; }
.buy-step .btn:last-child  { border-radius: 0 .6rem .6rem 0; }
.buy-step input {
  width: 4.5rem;
  border-radius: 0;
  border-left: 0;
  border-right: 0;
  border-color: var(--farm-ink);
  font-size: 1.15rem;
  font-weight: 700;
  font-variant-numeric: tabular-nums;
  -moz-appearance: textfield;
}
.buy-step input::-webkit-outer-spin-button,
.buy-step input::-webkit-inner-spin-button { -webkit-appearance: none; margin: 0; }

.buy-months {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(7rem, 1fr));
  gap: .5rem;
}
.buy-month {
  display: flex;
  flex-direction: column;
  gap: .1rem;
  padding: .7rem .9rem;
  border: 1px solid var(--farm-line);
  border-radius: .75rem;
  background: #fff;
  cursor: pointer;
  font-variant-numeric: tabular-nums;
}
.buy-month:hover { border-color: var(--farm-green-400); }
.btn-check:checked + .buy-month {
  border: 2px solid var(--farm-ink);
  padding: calc(.7rem - 1px) calc(.9rem - 1px);
  background: var(--farm-cream);
}
.btn-check:focus-visible + .buy-month { outline: 2px solid var(--farm-ink); outline-offset: 2px; }

.buy-summary {
  padding: 1rem;
  border-radius: .75rem;
  background: var(--farm-cream);
}
.buy-line {
  display: flex;
  justify-content: space-between;
  gap: 1rem;
  padding: .2rem 0;
  font-variant-numeric: tabular-nums;
}
.buy-total {
  margin-top: .4rem;
  padding-top: .6rem;
  border-top: 1px solid #d4d4d4;
  font-size: 1.25rem;
  font-weight: 800;
}

.buy-footer {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: .5rem 1rem;
  padding: 1rem;
}
.buy-cta { font-weight: 700; border-radius: .75rem; }

@media (max-width: 575.98px) {
  .buy-step { width: 100%; }
  .buy-step input { flex: 1 1 auto; }
  .buy-cta { width: 100%; }
}

/* --- after paying: thank you, bills, receipt ------------------------------ */

.thanks-hero {
  background: linear-gradient(135deg, #f3faf3 0%, #dcefdc 100%);
  border-bottom-color: #bcdcbc;
}
.thanks-hero p { color: #1f3a1f; }
.thanks-hero .limit-eyebrow { color: #2f6b2f; }
.thanks-icon { background: #2f7d32; box-shadow: 0 4px 12px rgba(47, 125, 50, .35); }

.bills-fresh > td { background: #f3faf3 !important; }

.receipt {
  max-width: 40rem;
  padding: 1.5rem;
  background: #fff;
  border: 1px solid var(--farm-line);
  border-radius: 1rem;
  box-shadow: 0 10px 30px rgba(0, 0, 0, .06);
}
.receipt-head {
  display: flex;
  align-items: flex-start;
  justify-content: space-between;
  gap: 1rem;
  padding-bottom: 1rem;
  margin-bottom: 1rem;
  border-bottom: 2px solid var(--farm-ink);
}
.receipt-brand {
  font-size: .75rem;
  font-weight: 700;
  letter-spacing: .06em;
  text-transform: uppercase;
  color: var(--farm-muted);
}
.receipt-meta {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(14rem, 1fr));
  gap: .75rem 1.5rem;
  margin-bottom: 1.25rem;
}
.receipt-meta dt { font-size: .8rem; font-weight: 600; color: var(--farm-muted); }
.receipt-meta dd { margin: 0; }
.receipt-items th { background: var(--farm-cream); }
.receipt-total th { font-size: 1.15rem; border-bottom: 0; }

@media (max-width: 575.98px) {
  .receipt { padding: 1rem; }
}
@media print {
  .receipt { box-shadow: none; border: 0; padding: 0; max-width: none; }
}

/* --- dashboard: count tiles you can tap, and the plan panel ---------------- */

.stat-link {
  color: inherit;
  text-decoration: none;
  transition: transform .12s ease, box-shadow .12s ease;
}
.stat-link:hover, .stat-link:focus-visible {
  color: inherit;
  transform: translateY(-2px);
  box-shadow: 0 6px 16px rgba(0, 0, 0, .08);
}

.plan-meter {
  height: 100%;
  padding: .85rem 1rem;
  border: 1px solid var(--farm-line);
  border-radius: .75rem;
  background: var(--farm-cream);
}
.plan-count {
  font-size: 1.85rem;
  font-weight: 800;
  line-height: 1.1;
  font-variant-numeric: tabular-nums;
}
.plan-cap { font-size: 1.1rem; font-weight: 600; color: var(--farm-muted); }
.plan-meter .progress { height: .6rem; background: #e2e2e2; }
.plan-meter .progress-bar { background: var(--farm-ink); transition: width .6s ease; }
/* Amber and red mean "needs you" here, as everywhere else in the app. */
.plan-near .progress-bar { background: var(--farm-amber); }
.plan-near .plan-room    { color: var(--farm-amber-ink); }
.plan-full               { border-color: #f1c4c4; background: #fdf2f2; }
.plan-full .progress-bar { background: var(--farm-red); }
.plan-full .plan-room    { color: var(--farm-red); }

.plan-calc {
  padding-top: 1rem;
  border-top: 1px dashed var(--farm-line);
}
.buy-step-sm .btn { width: 2.25rem; font-size: 1rem; padding-inline: 0; }
.buy-step-sm input { width: 3.25rem; font-size: 1rem; padding-inline: .25rem; }
.plan-calc-price {
  font-size: 1.35rem;
  font-weight: 800;
  line-height: 1.1;
  font-variant-numeric: tabular-nums;
}

@media (max-width: 575.98px) {
  .plan-calc-buy { width: 100%; justify-content: space-between; }
}

/* --- plan page: add to this plan, or renew -------------------------------- */

.buy-switch {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: .5rem;
}
.buy-way {
  display: flex;
  flex-direction: column;
  gap: .1rem;
  padding: .8rem 1rem;
  border: 1px solid var(--farm-line);
  border-radius: .75rem;
  background: #fff;
  cursor: pointer;
}
.buy-way:hover { border-color: var(--farm-green-400); }
.btn-check:checked + .buy-way {
  border: 2px solid var(--farm-ink);
  padding: calc(.8rem - 1px) calc(1rem - 1px);
  background: var(--farm-cream);
}
.btn-check:focus-visible + .buy-way { outline: 2px solid var(--farm-ink); outline-offset: 2px; }

/* Star rating input: radio buttons drawn as stars. They stay focusable (arrow
   keys move between them) and work without JavaScript; the stars up to the
   chosen one are filled where :has() is supported, else just the chosen one. */
.star-input { display: inline-flex; gap: .1rem; }
.star-input input { position: absolute; opacity: 0; width: 1px; height: 1px; margin: 0; }
.star-input label { display: inline-flex; align-items: center; justify-content: center; min-width: 2.75rem; min-height: 2.75rem;
                     font-size: 2rem; line-height: 1; color: #c8c8c8; cursor: pointer; padding: 0; border-radius: .25rem; }
.star-input:has(input:checked) label { color: #f0a500; }
.star-input input:checked + label ~ label { color: #c8c8c8; }
.star-input input:checked + label { color: #f0a500; }
.star-input input:focus-visible + label { outline: 2px solid #198754; outline-offset: 1px; }

/* --- dashboard: today's tasks as cards, trend against last month ---------- */

/* Each kind of work due is one card you tap to get to it. The edge colour is
   the meaning the badges had: red withdrawal, amber to settle, grey the rest. */
.task-grid {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(8.75rem, 1fr));
  gap: .5rem;
}
.task-card {
  --task-tone: var(--farm-ink);
  display: flex;
  flex-direction: column;
  justify-content: space-between;
  gap: .35rem;
  min-height: 5.25rem;
  padding: .75rem .85rem;
  border: 1px solid var(--farm-line);
  border-inline-start: 4px solid var(--task-tone);
  border-radius: var(--farm-radius);
  background: #fff;
  color: inherit;
  text-decoration: none;
}
.task-card:hover, .task-card:focus-visible { color: inherit; border-color: var(--farm-green-400); border-inline-start-color: var(--task-tone); }
.task-n { font-size: 1.85rem; font-weight: 800; line-height: 1; font-variant-numeric: tabular-nums; color: var(--farm-ink); }
.task-label { font-size: .85rem; line-height: 1.3; color: var(--farm-muted); }
.task-card.is-zero { --task-tone: var(--farm-line); background: var(--farm-cream); }
.task-card.is-zero .task-n { color: var(--farm-green-400); }
.task-danger  { --task-tone: var(--farm-red); }
.task-warning { --task-tone: var(--farm-amber); }
.task-info    { --task-tone: var(--farm-blue); }

.trend {
  display: inline-flex;
  align-items: center;
  gap: .2rem;
  margin-inline-start: .35rem;
  font-size: .75rem;
  font-weight: 600;
  color: var(--farm-muted);
  white-space: nowrap;
  vertical-align: middle;
}
.trend-arrow { font-size: .65rem; }

/* --- animal page: photo header, section bar ------------------------------- */

.animal-title { display: flex; align-items: center; gap: .75rem; }
.animal-title-text { min-width: 0; }
.animal-hero {
  flex: 0 0 auto;
  display: grid;
  place-items: center;
  width: 3.75rem;
  height: 3.75rem;
  border-radius: 50%;
  overflow: hidden;
  background: var(--farm-cream);
  box-shadow: inset 0 0 0 1px var(--farm-line);
  font-size: 1.9rem;
  line-height: 1;
}
.animal-hero img { width: 100%; height: 100%; object-fit: cover; display: block; }
.photo-zoom { overflow: hidden; border-start-start-radius: inherit; border-start-end-radius: inherit; }
.photo-zoom img { display: block; width: 100%; }

/* Tab-like links to the sections below, in the page's own order. On a phone
   the bar sticks to the top while you scroll; it scrolls sideways itself, the
   page never does. */
.section-bar {
  display: flex;
  gap: .25rem;
  margin: 0 0 1rem;
  padding: .35rem 0;
  overflow-x: auto;
  overscroll-behavior-x: contain;
  scrollbar-width: none;
  background: var(--farm-sand);
}
.section-bar::-webkit-scrollbar { display: none; }
.section-bar a {
  flex: 0 0 auto;
  display: inline-flex;
  align-items: center;
  min-height: 2.75rem;
  padding: 0 .9rem;
  border-radius: 999px;
  color: var(--farm-muted);
  font-size: .9rem;
  font-weight: 600;
  text-decoration: none;
  white-space: nowrap;
}
.section-bar a:hover { color: var(--farm-ink); background: #f0f0f0; }
.section-bar a[aria-current] { color: #fff; background: var(--farm-ink); }
@media (max-width: 767.98px) {
  .section-bar { position: sticky; top: 0; z-index: 1020; box-shadow: 0 1px 0 var(--farm-line); }
  [data-section] { scroll-margin-top: 4rem; }
}
@media print { .section-bar { display: none !important; } }

/* --- vet request: step tracker, countdown ring ----------------------------- */

/* Four steps on a line. The grey line is the whole way; the black one runs to
   the last step reached (--steps-fill, 0–100% of the way from first to last). */
.vet-steps {
  position: relative;
  display: grid;
  grid-template-columns: repeat(4, 1fr);
  padding: 0;
  text-align: center;
}
.vet-steps::before,
.vet-steps::after {
  content: "";
  position: absolute;
  top: 1rem;
  inset-inline-start: 12.5%;
  height: 3px;
  margin-top: -1.5px;
  border-radius: 3px;
}
.vet-steps::before { width: 75%; background: var(--farm-line); }
.vet-steps::after { width: calc(var(--steps-fill, 0%) * .75); background: var(--farm-ink); }
.vet-step-item {
  position: relative;
  z-index: 1;
  display: flex;
  flex-direction: column;
  align-items: center;
  gap: .35rem;
  color: var(--farm-muted);
}
.vet-step-dot {
  display: grid;
  place-items: center;
  width: 2rem;
  height: 2rem;
  border-radius: 50%;
  background: #fff;
  border: 2px solid var(--farm-line);
}
.vet-step-item.is-on { color: var(--farm-ink); font-weight: 600; }
.vet-step-item.is-on .vet-step-dot { background: var(--farm-ink); border-color: var(--farm-ink); }
.vet-step-item.is-on .vet-step-dot::after {
  content: "";
  width: .6rem;
  height: .32rem;
  border: solid #fff;
  border-width: 0 0 2px 2px;
  transform: translateY(-1px) rotate(-45deg);
}

.countdown { display: inline-flex; align-items: center; gap: .5rem; }
.countdown-ring { flex: 0 0 auto; transform: rotate(-90deg); }
[dir="rtl"] .countdown-ring { transform: rotate(-90deg) scaleY(-1); }   /* runs the other way round */
.countdown-track { fill: none; stroke: var(--farm-line); stroke-width: 3.5; }
.countdown-left { fill: none; stroke: var(--farm-ink); stroke-width: 3.5; stroke-linecap: round; }
.countdown.is-low .countdown-left { stroke: var(--farm-amber); }

/* Rating saved: the check mark (and, with motion, a burst around it). */
.rate-burst {
  position: relative;
  display: grid;
  place-items: center;
  width: 4rem;
  height: 4rem;
  margin: .25rem auto 1rem;
}
.rate-burst-check {
  position: relative;
  z-index: 1;
  display: grid;
  place-items: center;
  width: 3.5rem;
  height: 3.5rem;
  border-radius: 50%;
  background: var(--farm-ink);
  color: #fff;
}
.rate-burst-check svg { width: 1.75rem; height: 1.75rem; }
.rate-burst-ring {
  position: absolute;
  inset: 0;
  border-radius: 50%;
  border: 2px solid var(--farm-ink);
  opacity: 0;
}
.rate-burst-dots { position: absolute; inset: 0; }
.rate-burst-dots i {
  position: absolute;
  top: 50%;
  left: 50%;
  width: .45rem;
  height: .45rem;
  margin: -.225rem;
  border-radius: 50%;
  background: var(--farm-ink);
  opacity: 0;
}
.rate-burst-dots i:nth-child(even) { background: var(--farm-amber); }
.rate-burst-dots i:nth-child(1) { --a: 0deg; }
.rate-burst-dots i:nth-child(2) { --a: 45deg; }
.rate-burst-dots i:nth-child(3) { --a: 90deg; }
.rate-burst-dots i:nth-child(4) { --a: 135deg; }
.rate-burst-dots i:nth-child(5) { --a: 180deg; }
.rate-burst-dots i:nth-child(6) { --a: 225deg; }
.rate-burst-dots i:nth-child(7) { --a: 270deg; }
.rate-burst-dots i:nth-child(8) { --a: 315deg; }

/* --- public vets pages: the landing page's look ---------------------------- */

/* Same voice as the front page: a small spaced eyebrow over a heavy, tight
   title, a muted lede, cards with soft depth that lift under the pointer. */
.pub-vets .eyebrow {
  display: inline-block;
  margin-bottom: .5rem;
  font-size: .78rem;
  font-weight: 700;
  letter-spacing: .18em;
  text-transform: uppercase;
  color: var(--farm-ink);
  text-decoration: none;
}
.pub-vets h2 { font-weight: 800; letter-spacing: -.025em; }
.pub-vets .pub-title { margin: 0 0 .5rem; font-size: clamp(1.9rem, 7vw, 2.6rem); line-height: 1.08; }
.pub-vets .lede { max-width: 60ch; font-size: 1.05rem; color: var(--farm-muted); }
.pub-vets .vet-card { border: 1px solid var(--farm-line); border-radius: var(--farm-radius-lg); box-shadow: var(--farm-shadow-sm); }
[dir="rtl"] .pub-vets .eyebrow { letter-spacing: normal; font-size: .9rem; }
[dir="rtl"] .pub-vets h2 { letter-spacing: normal; line-height: 1.6; }
/* Nastaliq at weight 800 and 2.6rem is heavy: a calmer size and weight, with room under the eyebrow. */
[dir="rtl"] .pub-vets .pub-title { font-size: clamp(1.6rem, 5.5vw, 2.1rem); font-weight: 700; line-height: 1.75; margin-top: .25rem; }

/* Previous / next under a long list (views/_pager.php). */
.list-pager { display: flex; flex-wrap: wrap; align-items: center; justify-content: space-between; gap: .5rem; padding: .6rem .75rem; }
.list-pager-count { color: var(--bs-secondary-color, #6c757d); font-size: .875rem; }
.list-pager-step { display: flex; align-items: center; gap: .5rem; margin-inline-start: auto; }
.list-pager-of { font-size: .875rem; white-space: nowrap; }
