/* Compliance & safety page: rules specific to compliance.html.
   Shared components live in ../styles.css. Selectors stay flat so they
   override by source order only. */


/* --- A credential value stays whole --------------------------------------
   A hyphen is a line-break opportunity in its own right, so once the column
   narrows - and browser text size narrows every column in font-relative terms -
   "Z21-869-00S" breaks after one of its own hyphens and reads as two numbers.
   A licence number split across two lines is not a credential any more. The
   span holds the value on one line while the row it sits in still wraps
   normally around it. Only ever put this on a value short enough to fit its
   own column; the sizes beside it (.cred__data, the credential strip's mono)
   are tied to their container so that stays true at 200% text size. */
.nowrap {
  white-space: nowrap;
}


/* --- Licences and insurance: data cards ---------------------------------- */

.licences__lead {
  margin-top: var(--s-6);
}

/* `container-type` makes the card the query container its data line measures
   against (see `.cred__data`). It changes nothing about the layout. */
.cred {
  gap: 0;
  container-type: inline-size;
}

/* mono label: the element also carries class="mono" */
.cred__title {
  color: var(--ink-soft);
  margin-bottom: var(--s-4);
}

/* not the shared .mono label: a data readout at display size, set sentence-case
   with tighter tracking so a licence number reads as a figure, not a caption */
/* The value is held on one line by the `.nowrap` span in the markup, so a
   licence number never breaks at its own hyphens. That makes the value an
   unbreakable word, and the card is `overflow: hidden`, so the size has to be
   tied to the card rather than to the root font: at 200% text size the 1.375rem
   readout set "Z21-869-00S" 290px wide inside a 180px card and the card ate the
   end of it. The value runs about 6.6x its font size, so 14cqw always fits; at
   the default text size the cqw term is well above the rem at every width, so
   the 100% rendering is unchanged. The plain rem is declared first as the
   fallback where container query units are missing. */
.cred__data {
  font-family: var(--font-mono);
  font-size: 1.375rem;
  font-size: min(1.375rem, 14cqw);
  font-weight: 500;
  letter-spacing: 0.02em;
  line-height: 1.25;
  color: var(--navy-700);
  /* a licence number or an ABN must never cross its card's border: at large text
     the container query unit alone still left the ABN overhanging at 1024px */
  max-width: 100%;
  overflow-wrap: anywhere;
}

.cred__text {
  margin-top: var(--s-3);
  color: var(--ink-soft);
  font-size: var(--text-small);
}

.cred-note {
  margin-top: var(--s-8);
  color: var(--ink-soft);
}


/* --- Officer standards: one fixed frame for the photograph -----------------
   The figure used to stretch to whatever height the opener and the hairline list
   set beside it, which sized the frame by the length of the copy: in the 5fr track
   that rendered a 0.48 to 1 portrait slot at 1440 and 0.53 at 1230, and the file is
   1.5 to 1, so all but a narrow vertical slice of the photograph was cut away - the
   door frame, the doorway and the house number all gone.

   3:2 instead, the same frame the seven service photographs use and the exact ratio
   compliance-ppe.jpg is cropped to, so the frame shows the whole file with no trim at
   all and no object-position steering is needed. The column balance is handled by the
   sticky rule below rather than by stretching the picture. */

.standards__media {
  position: relative;
  align-self: start;
  margin: 0;
  aspect-ratio: 3 / 2;
  overflow: hidden;
  border: 1px solid var(--line);
  border-radius: var(--radius);
  background: var(--navy-900);
}

.standards__media img {
  position: absolute;
  inset: 0;
  width: 100%;
  height: 100%;
  object-fit: cover;
}

/* Two columns, and the copy is much the taller of the two: a 5fr 3:2 frame is about
   290px and the body runs to 900. The frame therefore top-aligns with the heading and
   then sticks while the rest of the section scrolls past, so the photograph stays beside
   the standards it illustrates and the unused part of the track is never on screen as a
   void under the picture. It is bounded by its grid area, so it releases at the end of
   the section. The offset clears the fixed header, matching .split__sticky. */
@media (min-width: 1025px) {
  .standards__media {
    position: sticky;
    top: calc(var(--header-h-scrolled) + var(--s-8));
  }
}

.standards__lead {
  margin-top: var(--s-6);
}


/* --- Policies: two policy cards beside one sticky opener ---------------- */

.policies__lead {
  margin-top: var(--s-6);
}

/* the box, the border and the split rule come from the shared .card component;
   only the head/body rhythm below is page-specific */
.policy__head {
  display: flex;
  flex-wrap: wrap;
  justify-content: space-between;
  gap: var(--s-2) var(--s-6);
  padding: calc(var(--s-5) + var(--rule-h)) var(--s-8) var(--s-4);
  border-bottom: 1px solid var(--line);
}

/* mono labels: both elements also carry class="mono" */
.policy__title {
  line-height: 1.5;
  color: var(--navy-700);
}

.policy__meta {
  line-height: 1.5;
  color: var(--ink-soft);
}

/* minmax(0, 1fr), never the implicit `auto` track: an implicit column is floored
   at the min-content width of the longest line in the policy, and the card that
   holds it is `overflow: hidden`, so at 200% text size the card silently clipped
   49px off the right of every paragraph in the OH&S policy (8px in the risk
   policy) with no scrollbar and no change to document.scrollWidth. */
.policy__body {
  display: grid;
  grid-template-columns: minmax(0, 1fr);
  gap: var(--s-5);
  padding: var(--s-8);
}

.policy__intro {
  color: var(--ink-soft);
}

.policy__lead {
  font-weight: 600;
  color: var(--navy-700);
}

/* same reason as .policy__body: the commitments are the longest lines on the
   page and a bare implicit track carries their min-content width into the card */
.policy__list {
  display: grid;
  grid-template-columns: minmax(0, 1fr);
  gap: var(--s-3);
  margin: 0;
  padding: 0;
  list-style: none;
}

.policy__list li {
  position: relative;
  padding-left: 1.5rem;
}

.policy__list li::before {
  content: "";
  position: absolute;
  top: 0.7em;
  left: 0;
  width: 6px;
  height: 6px;
  background: var(--navy-700);
}


/* --- Technology and reporting: two spec sheets --------------------------- */

.ops {
  display: grid;
  grid-template-columns: repeat(2, minmax(0, 1fr));
  gap: var(--s-6);
}

/* the panels are shared .card boxes; only the head and spec rhythm is page-specific */
.ops__head {
  display: flex;
  flex-wrap: wrap;
  align-items: baseline;
  justify-content: space-between;
  gap: var(--s-2) var(--s-6);
  padding: calc(var(--s-6) + var(--rule-h)) var(--s-8) var(--s-5);
  border-bottom: 1px solid var(--line);
}

.ops__title {
  font-family: var(--font-display);
  font-size: 2rem;
  font-weight: 600;
  letter-spacing: var(--track-display);
  text-transform: uppercase;
  line-height: 1;
  color: var(--navy-700);
}

/* mono label: the element also carries class="mono" */
.ops__tag {
  color: var(--blue-700);
}

/* the shared .spec sheet (styles.css) inside the panel; short terms, so a narrow term column */
.ops__spec {
  --spec-term: 7.5rem;
  padding: var(--s-2) var(--s-8) var(--s-6);
}


/* --- Service transition ------------------------------------------------- */

.transition__led {
  margin-top: var(--s-8);
  color: var(--ink-soft);
}


/* --- Responsive --------------------------------------------------------- */

@media (max-width: 768px) {
  /* minmax(0, 1fr), never a bare 1fr: the stacked track would otherwise be
     floored at the min-content width of the panel inside it. */
  .ops {
    grid-template-columns: minmax(0, 1fr);
  }

  .policy__head,
  .policy__body,
  .ops__head {
    padding-inline: var(--s-6);
  }

  .ops__spec {
    padding-inline: var(--s-6);
  }
}

/* While the cards sit in rows, they share a floor, so both rows are the same
   height and the set reads as one block rather than one row inflated by its
   longest card. Below 480 the grid is a single column and the floor would only
   add dead space, so it applies from 481 up. */
@media (min-width: 481px) {
  .cred {
    min-height: 13.5rem;
  }
}

@media (max-width: 480px) {
  .cred__data {
    font-size: 1.25rem;
    font-size: min(1.25rem, 14cqw);
  }
}
