/* =========================================================
   Rubber Ducky Floats - rubberduckyfloats.com
   Plain CSS, no build step. Mobile-first.

   Colors are sampled directly from the brand artwork in brand/, so the
   site and the logo cannot drift apart. Everything below keys off these
   variables; retuning :root is most of a reskin.
   ========================================================= */

:root {
  --ink:        #012050;   /* navy wordmark - headings, dark bands */
  --ink-2:      #26364f;
  --steel:      #55617a;
  --muted:      #7b869c;
  --line:       #dae1ec;
  --line-soft:  #edf1f7;
  --bg:         #ffffff;
  --bg-2:       #f4f7fc;
  --bg-3:       #e8eef7;
  --accent:     #0342AC;   /* primary blue - wave field, logo ring */
  --accent-lt:  #0562CC;
  --accent-wash:#eef4fe;
  --cyan:       #01ABF0;   /* "for level sensors" */
  --duck:       #FEC003;   /* duck yellow - used sparingly, never as body text */
  --duck-deep:  #FA7403;

  --wrap: 1140px;
  --gut: 1.25rem;
  --radius: 4px;

  --sans: "Helvetica Neue", Helvetica, Arial, system-ui, -apple-system,
          "Segoe UI", Roboto, sans-serif;
  --mono: ui-monospace, SFMono-Regular, "SF Mono", Menlo, Consolas, monospace;

  --shadow-sm: 0 1px 2px rgba(1, 32, 80, .07), 0 1px 3px rgba(1, 32, 80, .09);
  --shadow-md: 0 4px 12px rgba(1, 32, 80, .09), 0 2px 4px rgba(1, 32, 80, .06);
  --shadow-lg: 0 12px 32px rgba(1, 32, 80, .13), 0 4px 8px rgba(1, 32, 80, .07);
}

*, *::before, *::after { box-sizing: border-box; }

html { -webkit-text-size-adjust: 100%; scroll-behavior: smooth; }
@media (prefers-reduced-motion: reduce) {
  html { scroll-behavior: auto; }
  *, *::before, *::after { animation-duration: .01ms !important; transition-duration: .01ms !important; }
}

body {
  margin: 0;
  font-family: var(--sans);
  font-size: 1.0625rem;
  line-height: 1.65;
  color: var(--ink-2);
  background: var(--bg);
  -webkit-font-smoothing: antialiased;
}

img, svg, video { max-width: 100%; height: auto; display: block; }

a { color: var(--ink); text-decoration-color: var(--accent); text-underline-offset: 3px; }
a:hover { color: var(--accent); }

h1, h2, h3, h4 {
  color: var(--ink);
  line-height: 1.15;
  letter-spacing: -.02em;
  margin: 0 0 .6em;
  font-weight: 700;
}
h1 { font-size: clamp(2rem, 5vw, 3.1rem); }
h2 { font-size: clamp(1.55rem, 3.4vw, 2.25rem); }
h3 { font-size: clamp(1.15rem, 2.2vw, 1.4rem); }
h4 { font-size: 1.0625rem; }
p  { margin: 0 0 1.15em; }
p:last-child, ul:last-child, ol:last-child { margin-bottom: 0; }

:focus-visible {
  outline: 3px solid var(--accent);
  outline-offset: 2px;
  border-radius: 2px;
}

.skip-link {
  position: absolute; left: -9999px; top: 0; z-index: 200;
  background: var(--ink); color: #fff; padding: .75rem 1.25rem;
}
.skip-link:focus { left: 0; }

.wrap { width: 100%; max-width: var(--wrap); margin-inline: auto; padding-inline: var(--gut); }
.wrap-narrow { max-width: 760px; }

.eyebrow {
  font-size: .75rem; font-weight: 700; letter-spacing: .14em;
  text-transform: uppercase; color: var(--accent);
  margin: 0 0 .85rem;
}
.eyebrow-light { color: var(--cyan); }

.lede { font-size: clamp(1.1rem, 1.9vw, 1.3rem); line-height: 1.55; color: var(--steel); }

/* ---------- Buttons ---------- */
.btn {
  display: inline-flex; align-items: center; justify-content: center; gap: .5rem;
  font: inherit; font-weight: 700; font-size: .95rem;
  letter-spacing: .01em;
  padding: .85rem 1.6rem;
  border: 2px solid transparent; border-radius: var(--radius);
  cursor: pointer; text-decoration: none;
  transition: background-color .15s ease, color .15s ease, border-color .15s ease, transform .15s ease;
}
.btn:hover { transform: translateY(-1px); }
.btn-primary { background: var(--accent); border-color: var(--accent); color: #fff; }
.btn-primary:hover { background: #012F80; border-color: #012F80; color: #fff; }
.btn-dark { background: var(--ink); border-color: var(--ink); color: #fff; }
.btn-dark:hover { background: var(--ink-2); border-color: var(--ink-2); color: #fff; }
.btn-ghost { border-color: var(--line); color: var(--ink); background: #fff; }
.btn-ghost:hover { border-color: var(--ink); color: var(--ink); }
.btn-ghost-light { border-color: rgba(255,255,255,.35); color: #fff; background: transparent; }
.btn-ghost-light:hover { border-color: #fff; color: #fff; background: rgba(255,255,255,.08); }
.btn-row { display: flex; flex-wrap: wrap; gap: .75rem; }

/* ---------- Header ---------- */
.site-header {
  position: sticky; top: 0; z-index: 100;
  background: rgba(255,255,255,.97);
  backdrop-filter: saturate(180%) blur(8px);
  border-bottom: 1px solid var(--line);
}
.header-bar { display: flex; align-items: center; justify-content: space-between; gap: 1rem; min-height: 74px; }

/* The brand must be allowed to shrink. With flex-shrink:0 the long tagline
   ("Quality Plastic Parts for Level Sensors") held the header bar at ~480px
   and every page scrolled sideways on a 320px phone. */
.brand { display: flex; align-items: center; gap: .7rem; text-decoration: none; min-width: 0; }
.brand-text { min-width: 0; }
/* The duck is a shaded illustration, not a flat mark, so it needs a little
   more room than a glyph logo would to stay readable. 44px is the floor at
   which the beak and the float ring still separate. */
.brand .mark { width: 44px; height: 44px; flex-shrink: 0; }
.brand-text { display: flex; flex-direction: column; line-height: 1.05; }
.brand-name { font-size: 1.16rem; font-weight: 800; color: var(--ink); letter-spacing: -.025em; }
/* "Floats" is set in the lighter blue exactly as the logo does it. */
.brand-name em { font-style: normal; font-weight: 800; color: var(--accent); }
.brand-tag { font-size: .66rem; font-weight: 600; letter-spacing: .13em; text-transform: uppercase; color: var(--muted); }
/* Below 560px the mark plus the name is enough; the tagline cannot fit beside
   a Menu button without either truncating or forcing a horizontal scroll.
   It stays in the footer, where there is room for it. */
@media (max-width: 559px) {
  .site-header .brand-tag { display: none; }
  .site-header .brand .mark { width: 38px; height: 38px; }
}

.nav-toggle {
  display: inline-flex; align-items: center; gap: .5rem;
  background: none; border: 1px solid var(--line); border-radius: var(--radius);
  padding: .55rem .8rem; font: inherit; font-size: .85rem; font-weight: 700;
  color: var(--ink); cursor: pointer;
}
.nav-toggle-bars { display: block; width: 18px; height: 2px; background: var(--ink); position: relative; }
.nav-toggle-bars::before, .nav-toggle-bars::after {
  content: ""; position: absolute; left: 0; width: 18px; height: 2px; background: var(--ink);
}
.nav-toggle-bars::before { top: -6px; }
.nav-toggle-bars::after  { top: 6px; }

.main-nav ul { list-style: none; margin: 0; padding: 0; }
.main-nav a {
  display: block; text-decoration: none; font-size: .95rem; font-weight: 600;
  color: var(--ink-2); padding: .55rem 0;
}
.main-nav a:hover, .main-nav a[aria-current="page"] { color: var(--accent); }
.header-cta { display: none; }

@media (max-width: 900px) {
  .main-nav {
    display: none;
    position: absolute; left: 0; right: 0; top: 100%;
    background: #fff; border-bottom: 1px solid var(--line);
    box-shadow: var(--shadow-md);
    padding: .5rem var(--gut) 1.25rem;
  }
  .main-nav.is-open { display: block; }
  .main-nav li + li { border-top: 1px solid var(--line-soft); }
  .main-nav a { padding: .85rem 0; }
  .main-nav .nav-phone { color: var(--accent); font-weight: 700; }
}
@media (min-width: 901px) {
  .nav-toggle { display: none; }
  .main-nav ul { display: flex; align-items: center; gap: 1.6rem; }
  .main-nav .nav-phone { display: none; }
  .header-cta { display: inline-flex; }
}

/* ---------- Hero ---------- */
.hero {
  background: var(--ink);
  color: #fff;
  position: relative;
  overflow: hidden;
  padding: clamp(3.5rem, 8vw, 6.5rem) 0;
}
.hero::after {
  content: ""; position: absolute; inset: 0; pointer-events: none;
  background:
    repeating-linear-gradient(115deg, rgba(255,255,255,.028) 0 2px, transparent 2px 9px),
    radial-gradient(120% 90% at 82% 12%, rgba(1,171,240,.20), transparent 62%);
}
.hero .wrap { position: relative; z-index: 1; }
.hero h1 { color: #fff; max-width: 17ch; }
.hero h1 em { font-style: normal; color: var(--cyan); }
.hero .lede { color: rgba(255,255,255,.76); max-width: 56ch; margin-bottom: 2rem; }
.hero .btn-row { margin-bottom: 2.75rem; }

.hero-split { display: grid; gap: 2.5rem; align-items: center; }
@media (min-width: 960px) {
  .hero-split { grid-template-columns: 1.15fr .85fr; gap: 4rem; }
}

/* Technical data plate - stands in for a hero photo and reinforces precision. */
.spec-plate {
  border: 1px solid rgba(255,255,255,.16);
  border-radius: var(--radius);
  background: linear-gradient(160deg, rgba(255,255,255,.055), rgba(255,255,255,.015));
  padding: 1.5rem 1.6rem 1.75rem;
}
.spec-plate h2 {
  font-size: .72rem; font-weight: 700; letter-spacing: .14em; text-transform: uppercase;
  color: var(--cyan); margin: 0 0 1.25rem;
  padding-bottom: .9rem; border-bottom: 1px solid rgba(255,255,255,.14);
}
.spec-plate dl { margin: 0; }
.spec-plate .plate-row {
  display: flex; justify-content: space-between; align-items: baseline; gap: 1rem;
  padding: .7rem 0; border-bottom: 1px solid rgba(255,255,255,.09);
}
.spec-plate .plate-row:last-child { border-bottom: 0; padding-bottom: 0; }
.spec-plate dt {
  font-size: .82rem; color: rgba(255,255,255,.6); letter-spacing: .02em;
}
.spec-plate dd {
  margin: 0; font-size: .92rem; font-weight: 700; color: #fff;
  font-variant-numeric: tabular-nums; text-align: right;
}

.hero-stats {
  display: grid; grid-template-columns: repeat(2, 1fr); gap: 1.5rem 1rem;
  border-top: 1px solid rgba(255,255,255,.16); padding-top: 1.75rem;
  margin-top: 2.75rem;
}
.hero-stats dt {
  font-size: clamp(1.6rem, 3.4vw, 2.1rem); font-weight: 800; color: #fff;
  letter-spacing: -.03em; font-variant-numeric: tabular-nums; line-height: 1;
}
.hero-stats dd {
  margin: .45rem 0 0; font-size: .78rem; font-weight: 600;
  letter-spacing: .08em; text-transform: uppercase; color: rgba(255,255,255,.58);
}
@media (min-width: 700px) { .hero-stats { grid-template-columns: repeat(4, 1fr); } }

/* Interior page header */
.page-head {
  background: var(--ink); color: #fff; position: relative; overflow: hidden;
  padding: clamp(2.75rem, 6vw, 4.5rem) 0;
}
.page-head::after {
  content: ""; position: absolute; inset: 0; pointer-events: none;
  background:
    repeating-linear-gradient(115deg, rgba(255,255,255,.026) 0 2px, transparent 2px 9px),
    radial-gradient(110% 100% at 88% 0%, rgba(1,171,240,.18), transparent 60%);
}
.page-head .wrap { position: relative; z-index: 1; }
.page-head h1 { color: #fff; margin-bottom: .35rem; }
.page-head .lede { color: rgba(255,255,255,.72); max-width: 62ch; margin-top: 1rem; }

.crumbs { font-size: .82rem; color: rgba(255,255,255,.6); margin: 0 0 1rem; }
.crumbs a { color: rgba(255,255,255,.82); text-decoration: none; }
.crumbs a:hover { color: #fff; text-decoration: underline; }
.crumbs span { padding: 0 .4rem; opacity: .5; }

/* ---------- Sections ---------- */
.section { padding: clamp(3rem, 7vw, 5.25rem) 0; }
.section-tight { padding: clamp(2.25rem, 5vw, 3.5rem) 0; }
.section-alt { background: var(--bg-2); }
.section-dark { background: var(--ink); color: rgba(255,255,255,.78); }
.section-dark h2, .section-dark h3 { color: #fff; }

.section-head { max-width: 62ch; margin-bottom: clamp(2rem, 4vw, 3rem); }
.section-head.center { margin-inline: auto; text-align: center; }

/* ---------- Grids & cards ---------- */
.grid { display: grid; gap: 1.25rem; }
.grid-2 { grid-template-columns: 1fr; }
.grid-3 { grid-template-columns: 1fr; }
.grid-4 { grid-template-columns: repeat(2, 1fr); }
@media (min-width: 640px) { .grid-2 { grid-template-columns: repeat(2, 1fr); } }
@media (min-width: 860px) {
  .grid-3 { grid-template-columns: repeat(3, 1fr); }
  .grid-4 { grid-template-columns: repeat(4, 1fr); }
  .grid { gap: 1.5rem; }
}

.card {
  background: #fff; border: 1px solid var(--line); border-radius: var(--radius);
  padding: 1.6rem 1.5rem;
  display: flex; flex-direction: column;
  transition: border-color .15s ease, box-shadow .15s ease, transform .15s ease;
}
.card h3 { margin-bottom: .5rem; }
.card p { color: var(--steel); font-size: .98rem; }
a.card { text-decoration: none; color: inherit; }
a.card:hover { border-color: var(--ink); box-shadow: var(--shadow-md); transform: translateY(-2px); color: inherit; }
.card-num {
  font: 700 .72rem/1 var(--mono); letter-spacing: .1em; color: var(--accent);
  margin-bottom: .9rem;
}
.card-more { margin-top: auto; padding-top: 1rem; font-size: .88rem; font-weight: 700; color: var(--accent); }
.card-more::after { content: " \2192"; }

.card-flat { background: var(--bg-2); border-color: transparent; }
.section-alt .card { background: #fff; }

/* ---------- Spec / capability list ---------- */
.spec-list { list-style: none; margin: 0; padding: 0; }
.spec-list li {
  display: flex; justify-content: space-between; gap: 1.25rem;
  padding: .85rem 0; border-bottom: 1px solid var(--line);
  font-size: .97rem;
}
.spec-list li:first-child { border-top: 1px solid var(--line); }
.spec-list dt, .spec-list .spec-k { color: var(--steel); }
.spec-list .spec-v { font-weight: 700; color: var(--ink); text-align: right; font-variant-numeric: tabular-nums; }

.check-list { list-style: none; margin: 0; padding: 0; }
.check-list li { position: relative; padding: 0 0 .7rem 1.7rem; color: var(--steel); }
.check-list li::before {
  content: ""; position: absolute; left: 0; top: .58em;
  width: 9px; height: 9px; border-radius: 1px;
  background: var(--accent);
}
.section-dark .check-list li { color: rgba(255,255,255,.78); }

/* ---------- Prose ---------- */
.prose { max-width: 72ch; }
.prose h2 { margin-top: 2.5rem; }
.prose h3 { margin-top: 2rem; }
.prose h2:first-child, .prose h3:first-child { margin-top: 0; }
.prose ul, .prose ol { padding-left: 1.15rem; margin: 0 0 1.15em; }
.prose li { margin-bottom: .45em; color: var(--steel); }
.prose strong { color: var(--ink); }

.pull {
  border-left: 3px solid var(--accent);
  padding: .3rem 0 .3rem 1.35rem;
  margin: 2rem 0;
  font-size: 1.2rem; line-height: 1.5; color: var(--ink); font-weight: 600;
}

/* ---------- Split (text + panel) ---------- */
.split { display: grid; gap: 2rem; align-items: start; }
/* Grid items default to min-width:auto, so a wide child (a spec table, a long
   part number) makes the track wider than its share and shoves the page past
   the viewport. This is what lets .table-scroll actually scroll. */
.split > *, .contact-grid > *, .hero-split > * { min-width: 0; }
@media (min-width: 900px) {
  .split { grid-template-columns: 1.15fr .85fr; gap: 3.5rem; }
  .split-even { grid-template-columns: 1fr 1fr; }
}

.panel {
  background: var(--bg-2); border: 1px solid var(--line);
  border-radius: var(--radius); padding: 1.75rem 1.6rem;
}
.panel h3 { font-size: 1.05rem; margin-bottom: 1rem; }
.section-alt .panel { background: #fff; }

/* ---------- Industries pills ---------- */
.pill-grid { display: flex; flex-wrap: wrap; gap: .55rem; list-style: none; margin: 0; padding: 0; }
.pill-grid li {
  border: 1px solid var(--line); border-radius: 999px;
  padding: .45rem 1rem; font-size: .9rem; font-weight: 600; color: var(--ink-2);
  background: #fff;
}
.section-dark .pill-grid li { border-color: rgba(255,255,255,.2); background: transparent; color: rgba(255,255,255,.85); }

/* ---------- Client logos / names ---------- */
.client-list {
  columns: 2; column-gap: 2rem;
  list-style: none; margin: 0; padding: 0;
  font-size: .92rem; color: var(--steel);
}
.client-list li { break-inside: avoid; padding: .3rem 0; }
@media (min-width: 700px) { .client-list { columns: 3; } }
@media (min-width: 1000px) { .client-list { columns: 4; } }

/* ---------- Case study ---------- */
.case-meta {
  display: flex; flex-wrap: wrap; gap: .5rem 1.5rem;
  font-size: .82rem; font-weight: 600; letter-spacing: .06em; text-transform: uppercase;
  color: var(--muted); margin-bottom: 1.5rem;
  padding-bottom: 1.25rem; border-bottom: 1px solid var(--line);
}
.case-meta strong { color: var(--ink); font-weight: 700; }

.result-grid { display: grid; gap: 1rem; grid-template-columns: repeat(2, 1fr); margin: 2rem 0; }
@media (min-width: 760px) { .result-grid { grid-template-columns: repeat(3, 1fr); } }
.result {
  background: var(--accent-wash); border: 1px solid #cfe0fb;
  border-radius: var(--radius); padding: 1.25rem;
}
.result dt { font-size: 1.6rem; font-weight: 800; color: var(--ink); letter-spacing: -.03em; font-variant-numeric: tabular-nums; }
.result dd { margin: .35rem 0 0; font-size: .85rem; color: var(--steel); line-height: 1.4; }

/* ---------- Photo placeholder (until client photos arrive) ---------- */
.photo-slot {
  position: relative;
  background:
    repeating-linear-gradient(135deg, var(--bg-3) 0 10px, var(--bg-2) 10px 20px);
  border: 1px dashed var(--line);
  border-radius: var(--radius);
  aspect-ratio: 4 / 3;
  display: flex; align-items: center; justify-content: center;
  color: var(--muted); font-size: .82rem; font-weight: 600;
  letter-spacing: .06em; text-transform: uppercase; text-align: center;
  padding: 1rem;
}
.photo-slot-wide { aspect-ratio: 16 / 9; }

/* ---------- CTA band ---------- */
.cta-band {
  background: var(--ink); color: #fff;
  padding: clamp(2.75rem, 6vw, 4.25rem) 0;
  position: relative; overflow: hidden;
}
.cta-band::after {
  content: ""; position: absolute; inset: 0; pointer-events: none;
  background: radial-gradient(90% 120% at 15% 50%, rgba(1,171,240,.20), transparent 60%);
}
.cta-band .wrap { position: relative; z-index: 1; }
.cta-band h2 { color: #fff; max-width: 22ch; }
.cta-band p { color: rgba(255,255,255,.72); max-width: 56ch; }

/* ---------- Contact ---------- */
.contact-grid { display: grid; gap: 2.5rem; }
@media (min-width: 900px) { .contact-grid { grid-template-columns: 1fr 1fr; gap: 4rem; } }

.contact-lines { list-style: none; margin: 0; padding: 0; }
.contact-lines li { padding: 1rem 0; border-bottom: 1px solid var(--line); }
.contact-lines li:first-child { border-top: 1px solid var(--line); }
.contact-k {
  display: block; font-size: .72rem; font-weight: 700; letter-spacing: .12em;
  text-transform: uppercase; color: var(--muted); margin-bottom: .2rem;
}
.contact-v { font-size: 1.12rem; font-weight: 700; color: var(--ink); text-decoration: none; }
a.contact-v:hover { color: var(--accent); }
.contact-v address { font-style: normal; font-weight: 700; line-height: 1.4; }

/* ---------- Footer ---------- */
.site-footer {
  background: var(--ink); color: rgba(255,255,255,.66);
  padding: clamp(2.75rem, 6vw, 4rem) 0 0;
  font-size: .93rem;
}
.footer-grid { display: grid; gap: 2rem; }
@media (min-width: 760px) { .footer-grid { grid-template-columns: 1.4fr 1fr 1fr; gap: 3rem; } }

.site-footer .brand-name { color: #fff; }
.site-footer .brand-tag { color: rgba(255,255,255,.5); }
.site-footer .brand-name em { color: var(--cyan); }
.footer-blurb { margin: 1.1rem 0 0; max-width: 40ch; color: rgba(255,255,255,.6); }

/* Catch-all for links in the footer, including prose links inside
   .footer-blurb. Without this a plain <a> falls back to the base rule
   (color: var(--ink), navy) and disappears against the navy footer - it
   rendered as a bare underline with no visible text. The more specific
   .footer-links / tel / mailto rules below still win. */
.site-footer a { color: #fff; }
.site-footer a:hover { color: var(--cyan); }

.footer-h {
  font-size: .74rem; font-weight: 700; letter-spacing: .13em; text-transform: uppercase;
  color: #fff; margin: 0 0 1rem;
}
.footer-links { list-style: none; margin: 0; padding: 0; }
.footer-links li { margin-bottom: .6rem; }
.footer-links a { color: rgba(255,255,255,.66); text-decoration: none; }
.footer-links a:hover { color: var(--cyan); }
.site-footer address { font-style: normal; line-height: 1.6; }
.site-footer a[href^="tel"], .site-footer a[href^="mailto"] { color: #fff; text-decoration: none; font-weight: 600; }
.site-footer a[href^="tel"]:hover, .site-footer a[href^="mailto"]:hover { color: var(--cyan); }

.footer-bottom {
  margin-top: 2.75rem; border-top: 1px solid rgba(255,255,255,.13);
  padding: 1.35rem 0 1.5rem;
  display: flex; flex-wrap: wrap; gap: .5rem 1.5rem; justify-content: space-between;
  font-size: .84rem; color: rgba(255,255,255,.5);
}
.footer-bottom a { color: rgba(255,255,255,.62); text-decoration: none; }
.footer-bottom a:hover { color: var(--cyan); }
/* Direct children only - a nested <span id="yr"> must stay inline. */
.footer-bottom > span { display: block; }

/* ---------- Archive photography ----------
   Every photo on this site is a 2005-era scan. The six that survived the cull
   run 378px to 600px wide; the other 22 were ~100px thumbnails and were
   dropped rather than upscaled.

   The rule throughout: NEVER render one above its native pixel width, so the
   browser only ever downsamples. Each rule below therefore caps max-width at
   the real intrinsic width of the images it serves. Raising any of these
   numbers, or dropping the width/height attributes in the markup, is what
   would make them look bad. Replace the files before relaxing the caps.

   Do NOT AI-upscale these. They are precision molded parts a buyer may compare
   against a physical sample, and invented geometry on a threaded core is a
   worse failure than a small photo. */

/* Figure floated beside prose. Falls back to full-width, centered, on narrow
   screens - a 180px float in a 320px column reads as a mistake. */
.figure-inline,
.figure-block {
  margin: 0 0 1.5rem;
  padding: .6rem .6rem 0;
  background: #fff;
  border: 1px solid var(--line);
  border-radius: var(--radius);
  /* fit-content, not a fixed width: the figure shrinks to whatever the photo
     actually is (69px to 302px tall/wide here) so nothing is ever stretched. */
  width: fit-content;
  max-width: 100%;
}
.figure-inline img,
.figure-block img {
  width: auto;        /* intrinsic size - never upscaled */
  max-width: 100%;    /* but still shrinks on a narrow phone */
  height: auto;
  border-radius: 2px;
}
.figure-inline figcaption,
.figure-block figcaption {
  font-size: .8rem;
  line-height: 1.4;
  color: var(--steel);
  padding: .6rem .15rem .75rem;
  /* width:0 keeps the caption out of the figure's max-content calculation, so
     the box sizes to the photo instead of stretching to fit the caption on one
     line; min-width then makes it fill and wrap. Without this a 165px photo
     ends up in a 590px box. */
  width: 0;
  min-width: 100%;
}
.figure-block { margin-inline: auto; }

.archive-note {
  margin: 1.5rem 0 0;
  font-size: .85rem;
  color: var(--muted);
}

/* Small print under a block. Was .form-hint until the contact form was
   removed; the two remaining uses were never about a form. */
.note { font-size: .82rem; color: var(--muted); margin-top: .4rem; }

@media (min-width: 700px) {
  .figure-inline {
    float: right;
    margin: .35rem 0 1.25rem 1.75rem;
  }
  /* Clear the float at the next heading so it cannot collide. Because of this,
     a .figure-inline must be placed immediately AFTER the heading it belongs
     with - put it before, and the heading clears it and nothing wraps. */
  .prose h2, .prose h3 { clear: both; }
}

/* ---------- Wave ----------
   The motif from the logo, rebuilt as vector (see WAVE_SVG in build.mjs) so it
   spans any width without a raster seam. It sits at the BOTTOM of a dark band
   and is filled in the color of whatever comes next, so it reads as the light
   section washing over the dark one. */
.wave {
  position: absolute;
  left: 0; right: 0; bottom: -1px;   /* -1px kills the sub-pixel hairline */
  width: 100%;
  height: clamp(28px, 4vw, 56px);
  display: block;
  pointer-events: none;
  z-index: 2;
}
/* Two solid fills, never one path at reduced opacity: translucent white over
   navy renders grey and reads as muddy. The back crest is the logo's lighter
   blue; only the front path carries the color of the section below. */
.wave .wave-back  { fill: var(--accent-lt); }
.wave .wave-front { fill: var(--bg); }
/* A dark band followed by a tinted section needs the front path tinted to
   match, otherwise a white stripe appears between them. */
.wave-alt .wave-front { fill: var(--bg-2); }

.site-footer { position: relative; }
/* The footer's wave points the other way: it is the light page washing INTO
   the navy footer, so it flips, the front path takes the footer color, and
   the back crest stays the lighter blue so the layering still reads. */
.site-footer .wave {
  top: -1px; bottom: auto;
  transform: scaleY(-1);
}
.site-footer .wave .wave-front { fill: var(--ink); }
.site-footer .wave .wave-back  { fill: var(--accent); }
.page-head, .hero, .cta-band { padding-bottom: clamp(3.75rem, 8vw, 6rem); }

/* ---------- Self-sizing grids ----------
   One formula, each grid declares only its ideal column width. This replaces
   a hand-maintained list of breakpoints where adding a grid and forgetting to
   register it silently ships a broken mobile layout.

   Three things here are load-bearing:
   1. min(IDEAL, 100%) - a bare minmax(290px, 1fr) sets a 290px FLOOR, so in a
      280px container the single column still measures 290px and overflows the
      viewport. min() clamps the floor to the space actually available.
   2. auto-fit, never auto-fill - auto-fit collapses empty tracks, so 2 items
      in a 3-track grid become 2 equal halves instead of sitting at 2/3 width.
   3. min-width: 0 on the items - grid items default to min-width:auto, so one
      unbreakable token (RDF-4501-R, an email address) forces its track wider
      than its share and shoves the page past the viewport.

   Pick IDEAL by arithmetic, not roundness: n columns fit when
   n*IDEAL + (n-1)*gap <= inner width (1140px wrap - 2*20px gutter = 1100px). */
.g {
  display: grid;
  gap: 1.375rem;
  grid-template-columns: repeat(auto-fit, minmax(min(var(--col, 280px), 100%), 1fr));
}
.g > * { min-width: 0; overflow-wrap: break-word; }

/* Two sizes, picked so each page's card count divides evenly and no row is
   left with a single orphan. Inner width is 1100px (1140 wrap - 2x20 gutter)
   and the gap is 22px:
     --col 255: 4*255 + 3*22 = 1086  fits 4    (5 would need 1341)
     --col 290: 3*290 + 2*22 =  914  fits 3    (4 would need 1226)
   Use .g-tiles for 4 and 7 card pages (4, and 4+3), .g-parts for 3 and 6
   (3, and 3+3). Changing a card count means re-checking which class applies. */
.g-tiles { --col: 255px; }
.g-parts { --col: 290px; }

/* ---------- Part cards ---------- */
.part {
  background: #fff;
  border: 1px solid var(--line);
  border-top: 3px solid var(--accent);
  border-radius: var(--radius);
  padding: 1.4rem 1.4rem 1.5rem;
  display: flex; flex-direction: column;
}
.section-alt .part { background: #fff; }
.part-sku {
  font: 800 .95rem/1 var(--mono);
  letter-spacing: .04em;
  color: var(--accent);
  margin: 0 0 .5rem;
}
.part h3 { font-size: 1.05rem; margin-bottom: .7rem; }
.part p  { color: var(--steel); font-size: .95rem; }
/* margin-top:auto bottom-aligns the spec lists across a row so cards with
   shorter descriptions do not leave their data floating mid-card. */
.part-specs { list-style: none; margin: auto 0 0; padding: 0; font-size: .9rem; padding-top: .5rem; }
.part-specs li {
  display: flex; justify-content: space-between; gap: 1rem;
  padding: .5rem 0; border-bottom: 1px solid var(--line-soft);
}
.part-specs li:last-child { border-bottom: 0; }
.part-specs .k { color: var(--muted); flex-shrink: 0; }
.part-specs .v { font-weight: 700; color: var(--ink); text-align: right; font-variant-numeric: tabular-nums; }
/* Flags a claim carried over from 2005 that has not been re-confirmed.
   align-self keeps the pill hugging its text - as a flex child it would
   otherwise stretch the full width of the card. */
.part-flag {
  display: inline-block; align-self: flex-start; margin-top: .9rem;
  font-size: .72rem; font-weight: 700; letter-spacing: .07em; text-transform: uppercase;
  color: var(--duck-deep); background: #fff5e8;
  border: 1px solid #ffd9ac; border-radius: 999px; padding: .25rem .7rem;
}

/* ---------- Spec tables ----------
   These carry the data that used to be locked inside 100px JPEGs. They must
   stay real tables: indexable, screen-readable, and quotable by an answer
   engine. Wide ones scroll inside their own box so the page never does. */
/* max-width:100% is load-bearing, not decorative. overflow-x:auto only clips
   if the wrapper itself is constrained; inside a grid item (which defaults to
   min-width:auto) the wrapper otherwise grows to the table's min-width and
   pushes the whole PAGE sideways instead of scrolling inside its own box.
   Pairs with the `min-width: 0` on .split > * and .contact-grid > * below. */
.table-scroll {
  overflow-x: auto;
  max-width: 100%;
  margin: 1.5rem 0;
  -webkit-overflow-scrolling: touch;
}
table.spec {
  width: 100%;
  min-width: 34rem;
  border-collapse: collapse;
  font-size: .94rem;
  background: #fff;
}
table.spec caption {
  text-align: left; font-weight: 700; color: var(--ink);
  padding: 0 0 .75rem; font-size: 1.05rem;
}
table.spec th, table.spec td {
  text-align: left; padding: .7rem .85rem;
  border-bottom: 1px solid var(--line);
  vertical-align: top;
}
table.spec thead th {
  background: var(--ink); color: #fff;
  font-size: .74rem; font-weight: 700; letter-spacing: .1em; text-transform: uppercase;
  border-bottom: 0;
}
table.spec tbody tr:nth-child(even) { background: var(--bg-2); }
table.spec td:first-child { font-weight: 700; color: var(--ink); white-space: nowrap; }
table.spec .num { font-variant-numeric: tabular-nums; }

/* ---------- Callout ---------- */
.callout {
  background: var(--accent-wash);
  border: 1px solid #cfe0fb;
  border-left: 4px solid var(--accent);
  border-radius: var(--radius);
  padding: 1.4rem 1.5rem;
  margin: 2rem 0;
}
.callout h3 { font-size: 1.05rem; margin-bottom: .5rem; }
.callout p  { color: var(--ink-2); margin-bottom: 0; }
.callout p + p { margin-top: .8rem; }

/* A single yellow accent, used once per page at most. The duck is the brand's
   humor; leaning on it turns a parts catalog into a toy store. */
.rule-duck { border: 0; height: 3px; width: 64px; background: var(--duck); margin: 0 0 1.5rem; }

/* ---------- Utilities ---------- */
.center { text-align: center; }
.mt-0 { margin-top: 0; }
.mb-0 { margin-bottom: 0; }
.stack > * + * { margin-top: 1rem; }
.visually-hidden {
  position: absolute; width: 1px; height: 1px; padding: 0; margin: -1px;
  overflow: hidden; clip: rect(0 0 0 0); white-space: nowrap; border: 0;
}
