/* =============================================================================
   LAYOUT PRIMITIVES — composable, intrinsic layouts (after Every Layout).
   These solve 90% of page structure WITHOUT bespoke CSS, so feature work
   rarely needs new layout rules. Prefer these over ad-hoc fl/grid in views.

   Usage in ERB:
     <div class="stack" style="--stack-gap: var(--space-lg)"> … </div>
     <div class="cluster"> … </div>
     <div class="container"> … </div>
   ========================================================================== */

@layer layout {
  /* Container: centers content with a readable max width + side padding. */
  .container {
    inline-size: min(100% - (var(--container-pad) * 2), var(--container-max));
    margin-inline: auto;
  }
  .container--narrow { --container-max: 38rem; }
  .container--wide   { --container-max: 90rem; }

  /* Stack: vertical rhythm. Owns the space BETWEEN children only. */
  .stack { display: flex; flex-direction: column; }
  .stack > * + * { margin-block-start: var(--stack-gap, var(--space-md)); }

  /* Page + page-section: vertical rhythm between major blocks vs. inside a section.
     Use .page on the outer wrapper; .page-section on each labelled <section>.
     Child margins (not gap) so each block shows the intended margin-block-start in
     devtools and spacing survives component margin resets inside sections. */
  .page {
    display: flex;
    flex-direction: column;
  }
  .page > * + * { margin-block-start: var(--page-block-gap); }
  .page-section {
    display: flex;
    flex-direction: column;
    gap: var(--space-md);
  }

  /* Section heading row — always wrap .menu-section-title in this, even when
     there is no trailing meta, so title-to-content spacing matches everywhere. */
  .page-section-heading {
    display: flex;
    flex-wrap: wrap;
    align-items: baseline;
    justify-content: space-between;
    gap: var(--inline-space);
  }

  .page-section-heading > .menu-section-title,
  .page-section-meta {
    line-height: 1;
  }

  .page-section-meta {
    font-size: var(--text-xs);
    color: var(--color-text-muted);
    flex: none;
  }

  /* link-action's 44px tap target is for standalone links, not heading meta. */
  .page-section-heading > .link-action { min-block-size: 0; }

  /* Cluster: horizontal group that wraps gracefully (toolbars, tag rows). */
  .cluster {
    display: flex;
    flex-wrap: wrap;
    gap: var(--cluster-gap, var(--inline-space));
    align-items: var(--cluster-align, center);
    justify-content: var(--cluster-justify, flex-start);
  }

  /* Center: horizontally center a block with optional intrinsic centering. */
  .center { margin-inline: auto; max-inline-size: var(--center-max, var(--measure)); }

  /* Switcher: row that collapses to a column below a threshold. */
  .switcher { display: flex; flex-wrap: wrap; gap: var(--switcher-gap, var(--space-md)); }
  .switcher > * { flex: 1 1 var(--switcher-min, 18rem); }

  /* Grid: auto-fit responsive grid (card lists, the Care Plan grid). */
  .grid-auto {
    display: grid;
    gap: var(--grid-gap, var(--space-md));
    grid-template-columns: repeat(auto-fill, minmax(var(--grid-min, 16rem), 1fr));
  }

  /* Sidebar: content + side panel that wraps on small screens. */
  .with-sidebar { display: flex; flex-wrap: wrap; gap: var(--space-lg); }
  .with-sidebar > .sidebar { flex-basis: var(--sidebar-width, 18rem); flex-grow: 1; }
  .with-sidebar > .not-sidebar { flex-basis: 0; flex-grow: 999; min-inline-size: var(--sidebar-content-min, 60%); }

  /* Cover: full-height area with centered content (auth screens, empties). */
  .cover { display: flex; flex-direction: column; min-block-size: var(--cover-min, 100svh); padding: var(--space-lg); }
  .cover > * { margin-block: var(--space-xs); }
  .cover > .cover-centered { margin-block: auto; }

  /* App shell (FEA-0000): persistent app-bar + scrollable main + primary nav.
     MOBILE posture: app-bar on top, bottom-nav in the thumb zone. Content swaps
     inside <main> via a Turbo Frame so the bars never reload. */
  .app-shell {
    display: grid;
    grid-template-rows: auto 1fr auto;
    /* Definite, dynamic height so the `1fr` row resolves and the inner <main>
       scroller actually clamps + scrolls. `min-block-size` (a floor) + `svh`
       left the height indefinite, which Blink-on-Android failed to resolve in
       portrait → <main> grew instead of scrolling (landscape happened to work).
       `dvh` also tracks the retracting URL bar correctly. */
    block-size: 100dvh;
    padding-block-start: var(--safe-top);
  }
  .app-shell > main {
    padding-block: var(--space-lg);
    padding-inline: max(var(--container-pad), var(--safe-left));
    /* min-block-size:0 lets this grid item shrink below its content so
       overflow:auto creates a real scroll container (default is min-content). */
    min-block-size: 0;
    overflow: auto;
  }

  /* DESKTOP posture (>=48rem): sidebar + content; no bottom-nav. */
  @media (min-width: 48rem) {
    .app-shell {
      grid-template-columns: var(--side-nav-w, 16rem) 1fr;
      grid-template-rows: auto 1fr;
    }
    .app-shell > .app-bar     { grid-column: 1 / -1; }
    .app-shell > .side-nav    { grid-row: 2; }
    .app-shell > main         { grid-row: 2; }
    .app-shell > .bottom-nav  { display: none; }
  }
}
