/* ============================================================================
   The standalone public pages: /tjanster, /kunder, /referensprojekt, /om-oss,
   /certifieringar, /garantier, /kvalitet-miljo-ansvar and /fragor-och-svar,
   plus the landing page's services grid, which renders the same cards.

   One sheet rather than one per page: they share the card language, the
   heading rhythm and the prose column, and several of them render the same
   components (the FAQ list, the three-step inspection). Splitting per page
   would mean either duplicating those or adding a second <link> to every
   page that needs one.

   The card language deliberately mirrors blog.css: same surface, same radius,
   same hover lift, same condensed uppercase titles. The two grids sit on the
   same site and often on the same screen (the landing page carries both), so
   inventing a second card idiom here would read as a mistake, not a choice.
   ========================================================================== */

.svc-grid {
  list-style: none;
  margin: 0;
  padding: 0;
  display: grid;
  grid-template-columns: repeat(3, minmax(0, 1fr));
  gap: var(--sp-5);
}

.svc-card {
  min-width: 0;
}

.svc-card > a {
  display: flex;
  flex-direction: column;
  height: 100%;
  background: var(--surface-card);
  border: 1px solid var(--line-1);
  border-radius: var(--radius-md);
  overflow: hidden;
  color: inherit;
  text-decoration: none;
  box-shadow: var(--shadow-card);
  transition:
    transform var(--speed) var(--ease),
    box-shadow var(--speed) var(--ease),
    border-color var(--speed) var(--ease);
}

.svc-card > a:hover {
  transform: translateY(-1px);
  border-color: var(--blue-200);
  box-shadow: var(--shadow-raised);
}

.svc-card > a:active {
  transform: translateY(1px);
}

.svc-card > a:focus-visible {
  outline: none;
  box-shadow: var(--focus-ring);
  border-color: var(--blue-500);
}

/* 16:9, matching the service page's own hero crop, so the picture an admin
   frames on the card is the picture the page opens with. */
.svc-card-media {
  aspect-ratio: 16 / 9;
  overflow: hidden;
  background: var(--paper-2);
}

.svc-card-media img {
  width: 100%;
  height: 100%;
  object-fit: cover;
  display: block;
  transition: transform 320ms var(--ease);
}

.svc-card > a:hover .svc-card-media img {
  transform: scale(1.03);
}

/* A service without a photograph yet. Brand tint and the service's icon slot
   rather than a broken <img> or a gray void — several seeded services ship
   without a plausible photo, and an empty state that looks designed is what
   keeps them publishable until real photos exist. */
.svc-card-media--icon {
  display: flex;
  align-items: center;
  justify-content: center;
  background: linear-gradient(135deg, var(--paper-2), var(--blue-100));
  color: var(--blue-500);
}

.svc-card-body {
  padding: var(--sp-5);
  display: flex;
  flex-direction: column;
  gap: var(--sp-2);
  flex: 1;
}

.svc-card-title {
  font: var(--display-sm);
  line-height: 1.25;
  letter-spacing: var(--display-tracking);
  text-transform: uppercase;
  color: var(--ink-900);
  padding-block: 0.05em;
}

.svc-card-excerpt {
  font: var(--body-sm);
  color: var(--text-body);
  text-wrap: pretty;
}

/* The affordance line. margin-top:auto keeps every card's arrow on one
   baseline regardless of excerpt length, same trick as .blog-card-meta. */
.svc-card-more {
  margin-top: auto;
  display: inline-flex;
  align-items: center;
  gap: var(--sp-1);
  font: var(--body-sm);
  font-weight: 600;
  color: var(--blue-600);
}

/* The landing page's #tjanster grid: same cards, no photographs, tighter
   padding. Twelve full-height cards on the landing page would out-shout the
   sections around them; the compact form keeps the section a menu, not a
   gallery. */
.svc-grid--compact .svc-card-body {
  padding: var(--sp-4);
}

/* The brief's "Vi arbetar med alla takmaterial" block, above the grid on
   /tjanster. Set on a tinted plate rather than as plain prose: it is the page's
   answer to "can you do my roof", and it has to survive being scrolled past by
   someone who came looking for one specific card. */
.svc-lead {
  margin: var(--sp-6) 0 var(--sp-7);
  padding: var(--sp-6) var(--sp-7);
  background: var(--surface-section);
  border-radius: var(--radius-md);
  max-width: 76ch;
}

.svc-lead-title {
  font: var(--display-md);
  letter-spacing: var(--display-tracking);
  text-transform: uppercase;
  color: var(--ink-900);
  margin: 0 0 var(--sp-4);
}

.svc-group {
  margin-top: var(--sp-7);
  /* The navigation panel's headings link to these sections by id; without the
     margin an anchor jump parks the group title under the sticky header. */
  scroll-margin-top: calc(var(--nav-total, 65px) + var(--sp-4));
}

.svc-group-title {
  font: var(--display-sm);
  letter-spacing: var(--display-tracking);
  text-transform: uppercase;
  color: var(--text-heading);
  margin: 0 0 var(--sp-5);
  padding-bottom: var(--sp-3);
  border-bottom: 1px solid var(--line-1);
}

/* ── One service page ─────────────────────────────────────────────────────── */

/* The claim list above the body on the pages that carry one.
   Both this and .svc-marks below are scoped to .article-body ON PURPOSE, and
   the scope is load-bearing rather than tidiness: blog.css styles every
   `.article-body ul` as a column flex box with its own padding, which at one
   class plus one element outranks a bare `.svc-highlights`. Written unscoped,
   the two-column plate rendered as a single column and the mark row stacked
   vertically — CSS that looked correct in isolation and lost every time it was
   actually used. */
.article-body .svc-highlights {
  list-style: none;
  margin: 0 0 var(--sp-6);
  padding: var(--sp-5) var(--sp-6);
  background: var(--surface-section);
  border-radius: var(--radius-md);
  display: grid;
  grid-template-columns: repeat(2, minmax(0, 1fr));
  gap: var(--sp-3) var(--sp-5);
}

.article-body .svc-highlights li {
  display: flex;
  align-items: flex-start;
  gap: var(--sp-2);
  font: var(--body-sm);
  color: var(--text-body);
}

/* The certification marks, at the end of the body. A mark with no artwork yet
   renders as a named chip: the claim is true either way, and an empty frame
   would say the file is broken rather than that it has not arrived. */
.article-body .svc-marks {
  list-style: none;
  margin: var(--sp-6) 0 0;
  padding: var(--sp-5) 0 0;
  border-top: 1px solid var(--line-1);
  display: flex;
  flex-direction: row;
  flex-wrap: wrap;
  align-items: center;
  gap: var(--sp-5);
}

.article-body .svc-mark img {
  display: block;
  max-height: 72px;
  width: auto;
  object-fit: contain;
}

.article-body .svc-mark--text {
  padding: var(--sp-2) var(--sp-4);
  border: 1px dashed var(--line-1);
  border-radius: var(--radius-sm);
  font: var(--kicker);
  letter-spacing: var(--kicker-tracking);
  text-transform: uppercase;
  color: var(--ink-300);
}

.svc-faq-more {
  margin: var(--sp-5) 0 0;
  font: var(--body-sm);
  color: var(--text-muted);
}

@media (max-width: 700px) {
  .svc-lead {
    padding: var(--sp-5);
  }

  .article-body .svc-highlights {
    grid-template-columns: minmax(0, 1fr);
  }

  /* Stacked rather than wrapped on a phone. Wrapping a row of centre-aligned
     items of very different heights — a 72px mark next to a one-line text chip
     — staggers them across two lines and reads as a broken row rather than as
     a list that ran out of width. */
  .article-body .svc-marks {
    flex-direction: column;
    align-items: flex-start;
    gap: var(--sp-4);
  }
}

/* ── /kunder ──────────────────────────────────────────────────────────────
   Four prose segments, not cards: each carries two full paragraphs, and prose
   that long set inside a card grid reads cramped at every width. */

.kund-flow {
  display: grid;
  gap: var(--sp-7);
  max-width: 76ch;
}

.kund-segment h2 {
  font: var(--display-md);
  letter-spacing: var(--display-tracking);
  text-transform: uppercase;
  color: var(--ink-900);
  margin: 0 0 var(--sp-3);
}

.kund-segment .prose-body p {
  font: var(--body-lg);
}

@media (max-width: 900px) {
  .svc-grid {
    grid-template-columns: repeat(2, minmax(0, 1fr));
  }
}

@media (max-width: 620px) {
  .svc-grid {
    grid-template-columns: minmax(0, 1fr);
  }
}

/* The hover lift and the image zoom are decoration, not information. */
@media (prefers-reduced-motion: reduce) {
  .svc-card > a,
  .svc-card-media img {
    transition: none;
  }

  .svc-card > a:hover {
    transform: none;
  }

  .svc-card > a:hover .svc-card-media img {
    transform: none;
  }
}

/* ============================================================================
   The expansion pages. Everything below is shared vocabulary first, then one
   block per page, in the order the navigation lists them.
   ========================================================================== */

/* ── Shared ───────────────────────────────────────────────────────────────── */

/* A prose column narrower than the 1140px container. Long-form text at full
   container width runs to ~140 characters a line, which is roughly twice what
   is comfortable to read. */
.container--narrow {
  max-width: 760px;
}

.prose-body--narrow {
  max-width: 68ch;
}

/* Rendered markdown, everywhere outside an article: service bodies, customer
   segments, the company presentation, quality blocks, project descriptions and
   FAQ answers all render through render.RenderBody into a .prose-body.
   .article-body in blog.css is the same job for an article; the two are kept
   apart because an article is a document with headings and tables while these
   are short passages inside a page that already has its own heading level.

   The `> * + *` rule is what gives paragraphs their rhythm, and it is the one
   that was missing: without it every multi-paragraph body — which is most of
   them, since the CMS hint tells editors a blank line starts a new paragraph —
   collapsed into an unbroken wall of text on the page while looking perfectly
   correct in the editor. */
/* Both rules are one class plus a universal selector, so the second wins on
   source order. Setting `margin: 0` on the typography rule below instead would
   NOT work: `.prose-body p` outranks `.prose-body > * + *`, so the shorthand
   would silently reset the very margin-top this exists to set — which is
   exactly how the rhythm went missing the first time. Nothing below this may
   set `margin` on a child of .prose-body without also restoring it. */
.prose-body > * {
  margin: 0;
}

.prose-body > * + * {
  margin-top: var(--sp-4);
}

.prose-body p,
.prose-body ul,
.prose-body ol {
  font: var(--body-md);
  color: var(--text-body);
}

.prose-body ul,
.prose-body ol {
  padding-left: 1.2em;
  display: flex;
  flex-direction: column;
  gap: var(--sp-2);
}

.prose-body li::marker {
  color: var(--blue-400);
}

.prose-body h2,
.prose-body h3 {
  font-family: var(--font-display);
  font-weight: 600;
  line-height: 1.25;
  letter-spacing: var(--display-tracking);
  text-transform: uppercase;
  color: var(--ink-900);
  margin: var(--sp-6) 0 0;
  padding-block: 0.05em;
}

.prose-body h2 {
  font-size: 1.5rem;
}

.prose-body h3 {
  font-size: 1.15rem;
}

.prose-body strong {
  font-weight: 600;
  color: var(--ink-900);
}

.prose-body a {
  /* blue-700 rather than blue-600: prose renders on --paper-1 as often as on
     white, and blue-600 measures 4.48 there against the 4.5 this text needs.
     Failing by two hundredths is still failing, and it is the same surface
     dependency that moved .section-label and .article-cta-phone. */
  color: var(--blue-700);
  text-decoration: underline;
  text-underline-offset: 0.15em;
}

/* Off-screen but still in the accessibility tree. The clip-path recipe rather
   than display:none for the same reason the installations street list uses it:
   a hidden element LEAVES the tree, which would turn "label this column" into
   "remove this column". */
.sr-only {
  position: absolute;
  width: 1px;
  height: 1px;
  margin: -1px;
  padding: 0;
  overflow: hidden;
  clip-path: inset(50%);
  white-space: nowrap;
  border: 0;
}

/* What a section shows before its content has been written. Deliberately
   styled rather than blank: an empty container reads as a broken page, and the
   owner opening a section they have not filled in should see that it works. */
.empty-notice {
  margin: var(--sp-6) 0 0;
  padding: var(--sp-5) var(--sp-6);
  border: 1px dashed var(--line-1);
  border-radius: var(--radius-md);
  background: var(--surface-section);
  color: var(--text-muted);
  font: var(--body-md);
  text-align: center;
}

.check-list--sm {
  margin-top: var(--sp-4);
  gap: var(--sp-2);
}

.check-list--sm li {
  font: var(--body-sm);
  color: var(--text-muted);
}

/* ── FAQ ──────────────────────────────────────────────────────────────────── */

.faq-list {
  display: flex;
  flex-direction: column;
  gap: var(--sp-2);
  margin-top: var(--sp-6);
}

.faq-item {
  background: var(--surface-card);
  border: 1px solid var(--line-1);
  border-radius: var(--radius-md);
  transition: border-color var(--speed) var(--ease);
}

.faq-item[open],
.faq-item:hover {
  border-color: var(--blue-300);
}

.faq-item > summary {
  display: flex;
  align-items: center;
  gap: var(--sp-4);
  padding: var(--sp-4) var(--sp-5);
  cursor: pointer;
  font: 600 17px/1.35 var(--font-body);
  color: var(--text-heading);
  /* Both are needed: the first kills the triangle in Safari, the second
     everywhere else. Without them the marker sits beside our own chevron. */
  list-style: none;
}

.faq-item > summary::-webkit-details-marker {
  display: none;
}

.faq-item > summary:focus-visible {
  outline: none;
  box-shadow: var(--focus-ring);
  border-radius: var(--radius-md);
}

.faq-item-chevron {
  margin-left: auto;
  flex: 0 0 auto;
  color: var(--accent-strong);
  transition: transform var(--speed) var(--ease);
}

.faq-item[open] .faq-item-chevron {
  transform: rotate(180deg);
}

.faq-item-answer {
  padding: 0 var(--sp-5) var(--sp-5);
  color: var(--text-body);
}

.faq-item-answer > :first-child {
  margin-top: 0;
}

/* ── Trestegsbesiktningen ─────────────────────────────────────────────────── */

.insp-steps {
  list-style: none;
  margin: var(--sp-6) 0 0;
  padding: 0;
  display: grid;
  grid-template-columns: repeat(3, minmax(0, 1fr));
  gap: var(--sp-5);
}

.insp-step {
  background: var(--surface-card);
  border: 1px solid var(--line-1);
  border-radius: var(--radius-md);
  padding: var(--sp-5);
  box-shadow: var(--shadow-card);
}

.insp-step-n {
  font: var(--kicker);
  letter-spacing: var(--kicker-tracking);
  text-transform: uppercase;
  color: var(--accent-strong);
  margin: 0 0 var(--sp-2);
}

.insp-step-title {
  font: var(--display-sm);
  letter-spacing: var(--display-tracking);
  text-transform: uppercase;
  color: var(--text-heading);
  margin: 0 0 var(--sp-3);
}

.insp-step-intro {
  font: var(--body-sm);
  color: var(--text-muted);
  margin: 0 0 var(--sp-4);
}

.insp-step-points {
  list-style: none;
  margin: 0;
  padding: 0;
  display: flex;
  flex-direction: column;
  gap: var(--sp-1);
}

.insp-step-points li {
  position: relative;
  padding-left: var(--sp-5);
  font: var(--body-sm);
  color: var(--text-body);
}

.insp-step-points li::before {
  content: "✓";
  position: absolute;
  left: 0;
  color: var(--blue-500);
  font-weight: 700;
}

/* ── /referensprojekt ─────────────────────────────────────────────────────── */

.proj-list {
  display: flex;
  flex-direction: column;
  gap: var(--sp-5);
  margin-top: var(--sp-6);
}

.proj-card {
  display: grid;
  grid-template-columns: minmax(0, 1.6fr) minmax(0, 1fr);
  gap: var(--sp-6);
  background: var(--surface-card);
  border: 1px solid var(--line-1);
  border-radius: var(--radius-md);
  padding: var(--sp-6);
  box-shadow: var(--shadow-card);
}

.proj-card-title {
  font: var(--display-md);
  letter-spacing: var(--display-tracking);
  text-transform: uppercase;
  color: var(--text-heading);
  margin: 0 0 var(--sp-4);
}

.proj-quote {
  margin: var(--sp-5) 0 0;
  padding-left: var(--sp-5);
  border-left: 3px solid var(--blue-300);
  color: var(--text-body);
}

.proj-quote p {
  font: var(--body-lg);
  font-style: italic;
  margin: 0;
}

.proj-quote cite {
  display: block;
  margin-top: var(--sp-2);
  font: var(--label);
  font-style: normal;
  color: var(--text-muted);
}

/* Project photographs. auto-fit rather than a fixed column count so one photo
   fills the width and four tile — a project has as many pictures as it has,
   and a lone shot stranded in a quarter-width cell looks like a loading
   failure. */
.proj-shots {
  list-style: none;
  margin: var(--sp-5) 0 0;
  padding: 0;
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(220px, 1fr));
  gap: var(--sp-3);
}

.proj-shots img {
  display: block;
  width: 100%;
  aspect-ratio: 4 / 3;
  object-fit: cover;
  border-radius: var(--radius-sm);
}

.proj-facts {
  margin: 0;
  padding: var(--sp-5);
  background: var(--surface-section);
  border-radius: var(--radius-md);
  align-self: start;
}

.proj-fact {
  display: flex;
  justify-content: space-between;
  gap: var(--sp-4);
  padding: var(--sp-2) 0;
  border-bottom: 1px solid var(--line-1);
}

.proj-fact:last-child {
  border-bottom: 0;
}

.proj-fact dt {
  font: var(--body-sm);
  color: var(--text-muted);
  flex: 0 0 auto;
}

.proj-fact dd {
  margin: 0;
  font: 500 14px/1.5 var(--font-body);
  color: var(--text-heading);
  text-align: right;
  min-width: 0;
}

/* ── /om-oss ──────────────────────────────────────────────────────────────── */

.about-lead,
.about-staff {
  display: grid;
  grid-template-columns: minmax(0, 1.3fr) minmax(0, 1fr);
  gap: var(--sp-7);
  align-items: start;
  margin-top: var(--sp-6);
}

.about-figure {
  margin: 0;
  border-radius: var(--radius-md);
  overflow: hidden;
}

.about-figure img {
  display: block;
  width: 100%;
  height: 100%;
  aspect-ratio: 4 / 5;
  object-fit: cover;
}

.team-grid,
.group-grid,
.cert-grid,
.gar-systems,
.kval-grid {
  list-style: none;
  margin: var(--sp-6) 0 0;
  padding: 0;
  display: grid;
  gap: var(--sp-5);
}

.team-grid {
  grid-template-columns: repeat(4, minmax(0, 1fr));
}

.team-card {
  background: var(--surface-card);
  border: 1px solid var(--line-1);
  border-radius: var(--radius-md);
  overflow: hidden;
  box-shadow: var(--shadow-card);
}

.team-card-photo {
  display: block;
  width: 100%;
  aspect-ratio: 4 / 5;
  object-fit: cover;
}

.team-card-photo--empty {
  display: grid;
  place-items: center;
  background: var(--paper-2);
  color: var(--ink-300);
}

.team-card-body {
  padding: var(--sp-4) var(--sp-5) var(--sp-5);
}

.team-card-name {
  font: 600 18px/1.25 var(--font-body);
  color: var(--text-heading);
  margin: 0;
}

.team-card-role {
  font: var(--kicker);
  letter-spacing: var(--kicker-tracking);
  text-transform: uppercase;
  color: var(--accent-strong);
  margin: var(--sp-2) 0 0;
}

.team-card-expertise,
.team-card-bio {
  font: var(--body-sm);
  color: var(--text-muted);
  margin: var(--sp-3) 0 0;
}

.team-card-creds {
  list-style: none;
  display: flex;
  flex-wrap: wrap;
  gap: var(--sp-1);
  margin: var(--sp-4) 0 0;
  padding: 0;
}

.team-card-creds li {
  font: var(--body-sm);
  font-size: 12.5px;
  padding: 2px var(--sp-3);
  border: 1px solid var(--line-1);
  border-radius: var(--radius-pill);
  background: var(--surface-section);
  color: var(--text-muted);
}

.group-grid {
  grid-template-columns: repeat(3, minmax(0, 1fr));
}

.group-card {
  background: var(--surface-card);
  border: 1px solid var(--line-1);
  border-radius: var(--radius-md);
  padding: var(--sp-5);
}

.group-card--current {
  border-color: var(--blue-300);
  box-shadow: 0 0 0 3px var(--blue-100);
}

.group-card-logo {
  display: block;
  max-height: 40px;
  width: auto;
  margin-bottom: var(--sp-4);
}

.group-card h3 {
  font: var(--display-sm);
  letter-spacing: var(--display-tracking);
  text-transform: uppercase;
  color: var(--text-heading);
  margin: 0 0 var(--sp-2);
}

.group-card p {
  font: var(--body-sm);
  color: var(--text-muted);
  margin: 0;
}

.group-card-tag {
  margin-top: var(--sp-3) !important;
  font: var(--label);
  color: var(--accent-strong) !important;
}

.group-card a {
  display: inline-flex;
  align-items: center;
  gap: var(--sp-1);
  margin-top: var(--sp-3);
  font: var(--label);
  color: var(--link);
  text-decoration: none;
}

.group-card a:hover {
  color: var(--link-hover);
  text-decoration: underline;
}

/* ── /certifieringar ──────────────────────────────────────────────────────── */

.cert-group {
  margin-top: var(--sp-7);
}

.cert-group-title {
  font: var(--display-sm);
  letter-spacing: var(--display-tracking);
  text-transform: uppercase;
  color: var(--text-heading);
  margin: 0;
  padding-bottom: var(--sp-3);
  border-bottom: 1px solid var(--line-1);
}

.cert-grid {
  grid-template-columns: repeat(4, minmax(0, 1fr));
}

.cert-card {
  background: var(--surface-card);
  border: 1px solid var(--line-1);
  border-radius: var(--radius-md);
  padding: var(--sp-5);
  text-align: center;
}

.cert-card-logo {
  display: grid;
  place-items: center;
  height: 72px;
  margin-bottom: var(--sp-4);
  padding: var(--sp-2);
  border-radius: var(--radius-sm);
}

/* The cap is a pixel value, not 100%, on purpose: the img is a grid item and
   the frame's single row is auto-sized by its content, so a percentage
   max-height has nothing definite to resolve against and is ignored. Wide
   logos hide that (max-width catches them first); a square one grows to the
   card's full width and paints over the name and description below. 56px is
   the frame's 72px minus its --sp-2 padding on each side. */
.cert-card-logo img {
  max-height: 56px;
  max-width: 100%;
  width: auto;
  object-fit: contain;
}

/* The no-artwork state. A dashed frame reads as "not filled in yet" rather
   than as a broken image, and the name inside it still carries the claim. */
.cert-card-logo--text {
  border: 1px dashed var(--line-1);
  background: var(--surface-section);
}

.cert-card-logo--text span {
  font: var(--kicker);
  letter-spacing: var(--kicker-tracking);
  text-transform: uppercase;
  color: var(--ink-300);
}

.cert-card-name {
  font: 600 16px/1.3 var(--font-body);
  color: var(--text-heading);
  margin: 0 0 var(--sp-2);
}

.cert-card-desc {
  font: var(--body-sm);
  color: var(--text-muted);
  margin: 0;
}

/* ── /garantier ───────────────────────────────────────────────────────────── */

.gar-systems {
  grid-template-columns: repeat(3, minmax(0, 1fr));
}

.gar-system {
  background: var(--surface-card);
  border: 1px solid var(--line-1);
  border-radius: var(--radius-md);
  padding: var(--sp-5);
}

.gar-system-logo {
  display: block;
  max-height: 40px;
  width: auto;
  margin-bottom: var(--sp-4);
}

.gar-system-name {
  font: var(--display-sm);
  letter-spacing: var(--display-tracking);
  text-transform: uppercase;
  color: var(--text-heading);
  margin: 0;
}

.gar-system-term {
  font: var(--label);
  color: var(--accent-strong);
  margin: var(--sp-2) 0 var(--sp-3);
}

.gar-system-desc {
  font: var(--body-sm);
  color: var(--text-muted);
  margin: 0;
}

/* The wrapper scrolls, never the document. Four columns of Swedish labels do
   not fit a phone, and a table that widens the page breaks every section
   above it. */
.gar-tablewrap {
  margin-top: var(--sp-6);
  overflow-x: auto;
  border: 1px solid var(--line-1);
  border-radius: var(--radius-md);
  background: var(--surface-card);
}

.gar-table {
  width: 100%;
  border-collapse: collapse;
  font: var(--body-md);
}

.gar-table th,
.gar-table td {
  padding: var(--sp-3) var(--sp-4);
  border-bottom: 1px solid var(--line-2);
  text-align: left;
  vertical-align: top;
}

.gar-table thead th {
  font: var(--display-sm);
  font-size: 17px;
  letter-spacing: var(--display-tracking);
  text-transform: uppercase;
  color: var(--text-heading);
  background: var(--surface-section);
  white-space: nowrap;
}

.gar-table tbody th {
  font: 500 15px/1.5 var(--font-body);
  color: var(--text-body);
}

.gar-table tbody tr:last-child th,
.gar-table tbody tr:last-child td {
  border-bottom: 0;
}

.gar-unknown {
  color: var(--ink-300);
}

.gar-note {
  margin-top: var(--sp-5);
  font: var(--body-sm);
  color: var(--text-muted);
  max-width: 68ch;
}

/* ── /kvalitet-miljo-ansvar ───────────────────────────────────────────────── */

.kval-chain {
  margin-top: var(--sp-6);
  padding: var(--sp-6);
  border-radius: var(--radius-md);
  background: var(--brand-gradient);
  color: var(--text-on-brand);
}

.kval-chain-name {
  font: var(--display-md);
  letter-spacing: var(--display-tracking);
  text-transform: uppercase;
  margin: 0;
}

.kval-chain-intro {
  font: var(--body-lg);
  margin: var(--sp-3) 0 0;
  max-width: 68ch;
  opacity: 0.92;
}

.kval-grid {
  grid-template-columns: repeat(3, minmax(0, 1fr));
}

.kval-card {
  background: var(--surface-card);
  border: 1px solid var(--line-1);
  border-radius: var(--radius-md);
  padding: var(--sp-5);
  box-shadow: var(--shadow-card);
}

.kval-card-icon {
  display: block;
  color: var(--accent-strong);
  margin-bottom: var(--sp-3);
}

.kval-card-title {
  font: var(--display-sm);
  letter-spacing: var(--display-tracking);
  text-transform: uppercase;
  color: var(--text-heading);
  margin: 0 0 var(--sp-3);
}

.kval-card .prose-body p,
.kval-card .prose-body ul {
  font: var(--body-sm);
  color: var(--text-muted);
}

/* ── Responsive ───────────────────────────────────────────────────────────── */

@media (max-width: 1000px) {
  .team-grid,
  .cert-grid {
    grid-template-columns: repeat(3, minmax(0, 1fr));
  }

  .insp-steps,
  .group-grid,
  .gar-systems,
  .kval-grid {
    grid-template-columns: repeat(2, minmax(0, 1fr));
  }

  .proj-card,
  .about-lead,
  .about-staff {
    grid-template-columns: minmax(0, 1fr);
    gap: var(--sp-5);
  }
}

@media (max-width: 700px) {
  .team-grid,
  .cert-grid,
  .insp-steps,
  .group-grid,
  .gar-systems,
  .kval-grid {
    grid-template-columns: repeat(2, minmax(0, 1fr));
  }

  .kval-chain {
    padding: var(--sp-5);
  }
}

@media (max-width: 520px) {
  .team-grid,
  .cert-grid,
  .insp-steps,
  .group-grid,
  .gar-systems,
  .kval-grid {
    grid-template-columns: minmax(0, 1fr);
  }

  .proj-card {
    padding: var(--sp-5);
  }

  /* Label above value once the row is too narrow to hold both. Justified
     space-between at 320px puts a two-word label against a five-word value
     and leaves a ragged gutter between them. */
  .proj-fact {
    flex-direction: column;
    gap: 2px;
  }

  .proj-fact dd {
    text-align: left;
  }
}

/* A project's comparison, inside the card's prose column. Single column: the
   card is already two columns wide-over-narrow, and a comparison split further
   would be too small to see a roofline in. */
.proj-ba {
  list-style: none;
  margin: var(--sp-5) 0 0;
  padding: 0;
  display: grid;
  gap: var(--sp-4);
}
