/* Calendari (task H). Continuous months like the iOS Calendar, riso marks:
   logged period = full pink ink, predicted = dashed pink outline, fertile = a soft blue band,
   ovulation = blue ring, today = ink halo, dots = what was logged (body / mind / life). */

.cal,
.cal-sheet {
  /* filter inks: one per slot (the legend and the bars use the same order) */
  --cal-k1: var(--c-peach);
  --cal-k2: var(--c-mint);
  --cal-k3: var(--luteal);
  /* day geometry grows with Dynamic Type (rem), the 44 px target is the cell itself */
  --mark: 2.125rem;
  --cell-h: calc(var(--mark) + 16px);
  --ink-blend: multiply;
  --ink-alpha: .16;
}
@media (prefers-color-scheme: dark) {
  .cal, .cal-sheet { --ink-blend: screen; --ink-alpha: .10; }
}

.cal {
  display: grid; gap: var(--s-4);
  /* no scroll anchoring: when the header changes height the days keep their place under it (keepPlace in JS) */
  overflow-anchor: none;
}
/* the sticky header covers the top of the page: focus, VoiceOver and scrollIntoView stop a day below it.
   Only on what scrolls under it (a scroll-padding on <html> would also scroll for the header's own controls) */
.cal-months .cal-day,
.cal-empty .btn {
  scroll-margin-top: calc(var(--cal-head-h, 8rem) + var(--s-2));
  scroll-margin-bottom: calc(env(safe-area-inset-bottom) + var(--tabbar-h) + var(--s-2));
}

/* ---------- sticky header: works as the navigation bar ---------- */
.cal-head {
  position: sticky; top: 0; z-index: 10;
  margin:
    calc(-1 * (env(safe-area-inset-top) + var(--s-5)))
    calc(-1 * (env(safe-area-inset-right) + var(--s-5)))
    0
    calc(-1 * (env(safe-area-inset-left) + var(--s-5)));
  padding:
    calc(env(safe-area-inset-top) + var(--s-2))
    calc(env(safe-area-inset-right) + var(--s-5))
    var(--s-2)
    calc(env(safe-area-inset-left) + var(--s-5));
  background: var(--bg);   /* opaque: days and inks scrolling under it must not show through */
  box-shadow: 0 1px 0 var(--line);
  display: grid; gap: var(--s-1);
}
.cal-bar { display: flex; align-items: center; justify-content: space-between; gap: var(--s-2); min-height: 44px; }
/* one line, like a navigation bar: the large title grows with Dynamic Type only up to what fits next to ‹ › */
.cal-title {
  font-size: min(var(--fs-xl), 8vw); font-weight: 780; min-width: 0;
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.cal-title-year { color: var(--text-3); font-weight: 600; }
.cal-nav { display: flex; flex: none; margin-right: calc(-1 * var(--s-2)); }
.cal-icon-btn {
  appearance: none; border: 0; background: transparent; color: var(--ink); cursor: pointer;
  width: 44px; height: 44px; display: grid; place-items: center; border-radius: var(--r-pill);
  transition: transform var(--t-fast) var(--ease), opacity var(--t-fast);
}
.cal-icon-btn:active { transform: scale(.92); opacity: .7; }
.cal-icon-btn:disabled { opacity: .3; cursor: default; }
.cal-tools { display: flex; align-items: center; gap: var(--s-2); min-width: 0; }
.cal-tools > :not(.grow):not(.cal-clear) { flex: none; }
.cal-tools > [hidden] { display: none; }
/* with a filter on, the button keeps only its glyph and the pills take the room */
.cal.is-filtering .cal-filter-btn { min-width: 44px; padding: 0 var(--s-3); }
.cal.is-filtering .cal-filter-label { display: none; }
.cal-tools .cal-icon-btn { margin-right: calc(-1 * var(--s-2)); }
.cal-filter-btn[aria-pressed="true"] { box-shadow: inset 0 0 0 1.5px var(--ink); }

/* three overlapping inks: the filter's own glyph */
.cal-inks { display: inline-flex; }
.cal-inks i { width: 11px; height: 11px; border-radius: 50%; mix-blend-mode: var(--ink-blend); }
.cal-inks i + i { margin-left: -4px; }
.cal-inks i:nth-child(1) { background: var(--cal-k1); }
.cal-inks i:nth-child(2) { background: var(--cal-k2); transform: translateY(-2px); }
.cal-inks i:nth-child(3) { background: var(--cal-k3); }

/* active filter: its own row under the tools, one pill per symptom in its ink. The pills are the legend,
   so all of them stay in sight: long names shorten (…) instead of scrolling away. The whole row is one
   button (one VoiceOver stop that reads every symptom) that opens the filter to change it.
   Grid with minmax(0, max-content): short pills keep their whole name, the free room goes to the long ones. */
.cal-filterbar {
  appearance: none; border: 0; background: none; color: inherit; font: inherit; cursor: pointer;
  width: 100%; min-width: 0; min-height: 44px; padding: 0; border-radius: var(--r-pill);
  display: grid; grid-auto-flow: column; grid-auto-columns: minmax(0, max-content);
  justify-content: start; align-items: center; gap: var(--s-2);
  -webkit-tap-highlight-color: transparent;
}
.cal-filterbar[hidden] { display: none; }
.cal-filterbar:active .cal-pill { opacity: .7; }
.cal-pill {
  min-width: 0; max-width: 100%;
  display: inline-flex; align-items: center; gap: 5px;
  min-height: 34px; padding: 0 var(--s-3);
  border-radius: var(--r-pill);
  /* the pill itself is the ink sample: tint + ring in the symptom's colour */
  background: color-mix(in oklab, var(--k) 26%, var(--bg));
  box-shadow: inset 0 0 0 2px var(--k);
  color: var(--ink); font-size: var(--fs-xs); font-weight: 650; line-height: 1.1;
  transition: opacity var(--t-fast);
}
.cal-pill-name { min-width: 0; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.cal-pill svg { flex: none; }
.cal-swatch { flex: none; width: 10px; height: 10px; border-radius: 50%; background: var(--k); }
.cal-hits { font-variant-numeric: tabular-nums; white-space: nowrap; overflow: hidden; padding-left: var(--s-1); }
.cal-clear {
  appearance: none; border: 0; background: none; cursor: pointer;
  min-height: 44px; padding: 0 var(--s-2);
  color: var(--menstrual-ink); font-weight: 650; font-size: var(--fs-sm);
}
/* in the tools row it may shorten as a last resort (German at the biggest text sizes on the small iPhone) */
.cal-tools .cal-clear { flex: 0 1 auto; min-width: 0; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }

.cal-weekdays {
  display: grid; grid-template-columns: repeat(7, minmax(0, 1fr));
  padding-top: var(--s-1);
  text-align: center; font-size: var(--fs-xs); font-weight: 600; color: var(--text-2);
}

/* ---------- empty state ---------- */
.cal-empty {
  display: grid; grid-template-columns: auto 1fr; align-items: center; gap: var(--s-3) var(--s-4);
  padding: var(--s-5); border-radius: var(--r-lg); background: var(--surface-2);
}
.cal-empty .cal-empty-text { display: grid; gap: var(--s-1); }
.cal-empty h2 { font-size: var(--fs-lg); }
.cal-empty .btn { grid-column: 1 / -1; }
.cal-empty-wrap:empty { display: none; }

/* ---------- months ---------- */
.cal-months { display: grid; gap: var(--s-6); }
.cal-month { display: grid; gap: var(--s-2); }
.cal-month-title { font-size: var(--fs-xl); font-weight: 780; }
.cal-month.is-current .cal-month-title { color: var(--menstrual-ink); }
.cal-year { color: var(--text-3); font-weight: 600; }
.cal-grid { display: grid; grid-auto-rows: var(--cell-h); min-height: calc(var(--rows) * var(--cell-h)); }
.cal-row { display: grid; grid-template-columns: repeat(7, minmax(0, 1fr)); }
.cal-cell { position: relative; min-width: 0; }

/* fertile window: a band of soft blue joining the days, rounded where it starts and ends */
.cal-cell.is-fertile::before {
  content: ""; position: absolute; top: 2px; left: 0; right: 0; height: min(var(--mark), calc(100% - 4px));
  background: var(--ovulation-soft);
}
.cal-cell.f-start::before { left: calc(50% - var(--mark) / 2); border-radius: var(--r-pill) 0 0 var(--r-pill); }
.cal-cell.f-end::before { right: calc(50% - var(--mark) / 2); border-radius: 0 var(--r-pill) var(--r-pill) 0; }
.cal-cell.f-start.f-end::before { border-radius: var(--r-pill); }

.cal-day {
  appearance: none; border: 0; background: none; cursor: pointer; color: var(--ink);
  position: relative; width: 100%; height: 100%; min-height: 44px;
  display: flex; flex-direction: column; align-items: center; gap: 3px;
  padding: 2px 0 0; border-radius: var(--r-sm);
  font: inherit;
}
.cal-day:focus-visible { outline-offset: -2px; }
.cal-day:active .cal-mark { transform: scale(.9); }

.cal-mark {
  position: relative; z-index: 1;
  display: grid; place-items: center;
  width: min(var(--mark), calc(100% - 4px)); aspect-ratio: 1; flex: none;
  border-radius: 50%; border: 2px solid transparent;
  font-family: var(--font-display); font-size: var(--fs-md); font-weight: 600; line-height: 1;
  font-variant-numeric: tabular-nums; letter-spacing: -.02em;
  transition: transform var(--t-fast) var(--ease);
}
.cal-day.is-future .cal-mark { color: var(--text-2); }
.cal-mark.logged { background: var(--menstrual); border-color: var(--menstrual); color: var(--menstrual-on); font-weight: 760; }
.cal-mark.predicted { border: 2px dashed var(--predicted); color: var(--menstrual-ink); font-weight: 700; }
.cal-mark.ovulation { border-color: var(--ovulation); color: var(--ovulation-ink); font-weight: 760; }
.cal-day.is-today .cal-mark,
.cal-mark.today-sample { outline: 2px solid var(--ink); outline-offset: 2px; font-weight: 800; color: var(--ink); }
.cal-day.is-today .cal-mark.logged { color: var(--menstrual-on); }

/* what was logged: one dot per group, always in the same place */
.cal-dots { display: grid; grid-template-columns: repeat(3, 5px); gap: 3px; height: 5px; }
.cal-dots i { width: 5px; height: 5px; border-radius: 50%; }
.cal-dots .g-body { grid-column: 1; background: var(--c-peach); }
.cal-dots .g-mind { grid-column: 2; background: var(--luteal); }
.cal-dots .g-life { grid-column: 3; background: var(--c-mint); }

/* filter: inks printed over the day (2 px out of register, like riso) + one bar per symptom */
.cal-ink {
  position: absolute; inset: 0 3px 1px; z-index: 0; pointer-events: none;
  border-radius: var(--r-sm);
  background: var(--k);
  opacity: calc(var(--ink-alpha) + .32 * var(--lv));
  mix-blend-mode: var(--ink-blend);
  transform: translate(calc(var(--off) * 2px), calc(var(--off) * -2px));
}
.cal-bars { position: relative; z-index: 1; display: grid; grid-template-columns: repeat(3, 6px); gap: 2px; align-items: end; height: 10px; }
.cal-bars i { width: 6px; height: 3px; border-radius: 2px; visibility: hidden; }
.cal-bars i.on { visibility: visible; height: calc(3px + 7px * var(--lv)); background: var(--k); box-shadow: 0 0 0 1px color-mix(in oklab, var(--ink) 25%, transparent); }
.cal.is-filtering .cal-day:not(.is-hit) .cal-mark:not(.logged):not(.predicted) { color: var(--text-3); }
.cal.is-filtering .cal-day.is-hit .cal-mark:not(.logged) { font-weight: 780; color: var(--ink); }

/* ---------- sheets ---------- */
.cal-sheet { display: grid; gap: var(--s-4); }

/* filter */
.cal-search {
  appearance: none; -webkit-appearance: none; width: 100%;
  min-height: 44px; padding: 0 var(--s-4);
  border: 0; border-radius: var(--r-sm);
  background: var(--surface-3); color: var(--ink);
  font: inherit; font-size: var(--fs-md);   /* ≥ 16 px: iOS does not zoom in */
}
.cal-search::placeholder { color: var(--text-2); }
.cal-filter-status { display: flex; align-items: center; gap: var(--s-2); margin-top: calc(-1 * var(--s-2)); }
.cal-filter-status .cal-filter-hint { flex: 1; }
.cal-filter-status .cal-clear { flex: none; margin-right: calc(-1 * var(--s-2)); }
.cal-clear[hidden] { display: none; }
.cal-filter-list { display: grid; gap: var(--s-5); }
.cal-filter-group { display: grid; gap: var(--s-2); }
.cal-filter-cat { display: flex; align-items: center; gap: var(--s-2); font-size: var(--fs-md); font-weight: 720; }
.cal-filter .chip.is-off { opacity: .45; }
.cal-filter .chip .cal-swatch { order: -1; }
.cal-count { font-size: var(--fs-xs); font-weight: 600; color: var(--text-2); font-variant-numeric: tabular-nums; }

/* forecast */
.cal-forecast-day { font-weight: 650; }
.cal-prob { display: flex; flex-wrap: wrap; align-items: baseline; gap: 0 var(--s-2); }
.cal-prob-num { font-family: var(--font-display); font-size: var(--fs-2xl); font-weight: 800; letter-spacing: -.03em; line-height: 1; color: var(--menstrual-ink); }
.cal-prob-text { color: var(--text-2); }
.cal-forecast-facts { display: grid; gap: var(--s-2); }
.cal-forecast-facts:empty { display: none; }
.cal-fact { padding-left: var(--s-3); box-shadow: inset 3px 0 0 var(--line); }
.cal-fact.is-fertile { box-shadow: inset 3px 0 0 var(--ovulation); }

/* legend */
.cal-legend-list { list-style: none; margin: 0; padding: 0; display: grid; gap: var(--s-1); }
.cal-legend-row { display: flex; align-items: center; gap: var(--s-3); min-height: 44px; }
/* wide enough for the biggest sample: today's halo (outline 2 px + offset 2 px) at large text sizes */
.cal-legend-sample { position: relative; flex: none; width: max(48px, calc(var(--mark) + 14px)); display: grid; place-items: center; }
.cal-legend-sample .cal-mark { width: var(--mark); }
.cal-band-sample { position: absolute; top: 50%; left: 0; right: 0; height: var(--mark); transform: translateY(-50%); background: var(--ovulation-soft); border-radius: var(--r-pill); }
.cal-legend-sample .cal-dots { grid-template-columns: 10px; }
.cal-legend-sample .cal-dots i { grid-column: 1; width: 10px; height: 10px; }
.cal-legend-sample .cal-dots { height: 10px; }
.cal-legend-h { font-size: var(--fs-md); font-weight: 720; margin-top: var(--s-2); }
