/*
 * Fire Stopping — Survey SHOW page styles.
 *
 * Loaded only on ?page=fire-stopping-survey-show. Holds the full-bleed header,
 * the sync/offline strip, the dark-active tab bar (fit-content), the tab panels
 * and the show-page cards. Shared chips + table language live in
 * fire-stopping.css. Built against the GLOBAL :root tokens.
 */

/* Full-bleed: zero the .content horizontal padding for this page so the header,
   sync strip and tabs span edge-to-edge (mirrors the inspection-show rule). */
.content:has(.page-section--fs-survey-show) {
  padding-left: 0;
  padding-right: 0;
}

.page-section--fs-survey-show {
  padding: 0 0 28px;
  background: var(--canvas);
  color: var(--ink);

  /* Canonical --ipi-* token scope — forked 1:1 from inspection_show.css's
     `.page-section--inspection-show` block. This page is NOT `.fire-stopping-page`,
     so it must define these itself or the canonical `.ipi-filter-rail`/
     `.ipi-filter-railbtn` primitives + the forked `fss-pen` filter strip render
     against undefined variables (transparent fills, currentcolor borders). */
  --ipi-bg: var(--canvas, #f7f5f0);
  --ipi-bg-inset: var(--surface-inset, #edeae3);
  --ipi-bg-card: var(--surface-card, #ffffff);
  --ipi-bg-hover: rgba(26, 24, 21, 0.04);
  --ipi-rule: var(--rule, rgba(26, 24, 21, 0.08));
  --ipi-rule-h: rgba(26, 24, 21, 0.11);
  --ipi-ink: var(--ink, #1a1815);
  --ipi-ink-2: #3d3a34;
  --ipi-ink-3: var(--ink-3, #6b6458);
  --ipi-ink-4: var(--ink-4, #9a9188);
  --ipi-accent: var(--accent, #c49510);
  --ipi-accent-bg: rgba(196, 149, 16, 0.08);
  --ipi-accent-border: rgba(196, 149, 16, 0.34);
  --ipi-shadow-sm: 0 1px 3px rgba(26, 24, 21, 0.06), 0 1px 2px rgba(26, 24, 21, 0.04);
  --ipi-shadow-card: 0 1px 4px rgba(26, 24, 21, 0.06), 0 0 0 1px rgba(26, 24, 21, 0.05);
}

html[data-theme="dark"] .page-section--fs-survey-show {
  --ipi-bg: rgba(15, 23, 42, 0.55);
  --ipi-bg-inset: rgba(15, 23, 42, 0.62);
  --ipi-bg-card: rgba(15, 23, 42, 0.7);
  --ipi-bg-hover: rgba(148, 163, 184, 0.08);
  --ipi-rule: rgba(71, 85, 105, 0.58);
  --ipi-rule-h: rgba(148, 163, 184, 0.22);
  --ipi-ink: var(--ink, #e2e8f0);
  --ipi-ink-2: #cbd5e1;
  --ipi-ink-3: #94a3b8;
  --ipi-ink-4: #64748b;
  --ipi-shadow-sm: none;
  --ipi-shadow-card: none;
}

/* (Sync / offline strip rules live in fire-stopping-offline.css — a literal
   fork of the inspection_show.css offline rules. Single ownership there.) */

/* ---- Header (forked from .insp-header) ----------------------------------- */
.fss-header {
  width: 100%;
  padding: 18px 32px;
  background: var(--surface-card);
  border-bottom: 1px solid var(--rule);
  box-shadow: var(--shadow-sm);
  box-sizing: border-box;
}

.fss-h-back {
  display: inline-flex;
  align-items: center;
  gap: 5px;
  margin-bottom: 14px;
  color: var(--ink-4);
  font-size: 12px;
  text-decoration: none;
  transition: color 0.15s ease;
}

.fss-h-back svg,
.fss-h-meta-item svg {
  width: 12px;
  height: 12px;
  flex-shrink: 0;
}

.fss-h-back:hover {
  color: var(--accent);
}

.fss-h-main {
  display: flex;
  align-items: flex-start;
  justify-content: space-between;
  gap: 16px;
}

.fss-h-left {
  min-width: 0;
}

.fss-h-title-row {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 10px;
  margin-bottom: 5px;
}

.fss-h-title {
  font-family: var(--font-display);
  font-size: 20px;
  font-weight: 700;
  line-height: 1.1;
  letter-spacing: -0.025em;
  color: var(--ink);
}

.fss-h-meta {
  display: flex;
  flex-wrap: wrap;
  gap: 14px;
}

.fss-h-meta-item {
  display: inline-flex;
  align-items: center;
  gap: 5px;
  color: var(--ink-4);
  font-size: 12.5px;
}

.fss-h-meta-item strong {
  color: var(--ink-3);
  font-weight: 500;
}

.fss-h-right {
  display: flex;
  align-items: center;
  gap: 8px;
  flex-shrink: 0;
  flex-wrap: wrap;
  justify-content: flex-end;
}

.fss-h-right .btn.is-disabled {
  opacity: 0.5;
  pointer-events: none;
  cursor: default;
}

/* Status-chip parity with the fire-door inspection-show chip (.insp-chip):
   tighter padding, 5px dot and a faint 1px ring. Scoped to the survey-show
   page so the global .fss-chip used on list pages is unaffected. The ring
   tracks the chip's own colour via currentColor, so dark mode adapts. */
.page-section--fs-survey-show .fss-chip {
  gap: 5px;
  padding: 3px 10px;
  border: 1px solid color-mix(in srgb, currentColor 18%, transparent);
}

.page-section--fs-survey-show .fss-chip-dot {
  width: 5px;
  height: 5px;
}

/* ---- Header "More actions" dropdown ------------------------------------
   A 1:1 fork of the fire-door .show-more-actions menu
   (inspection_show.css). Uses design tokens (identical to fire-door's
   hardcoded light values) so dark mode adapts for free. The mobile "More"
   variant lives inside .fss-h-mobile-actions (see the ≤900px block). */
.fss-h-mobile-actions {
  display: none;
}

.fss-show-more-actions {
  position: relative;
}

.fss-show-more-actions > summary {
  list-style: none;
  cursor: pointer;
}

.fss-show-more-actions > summary::-webkit-details-marker {
  display: none;
}

/* Caret size — fire-door sizes its summary SVG via `.ph-btn svg`; FS buttons
   don't carry that class, so size the caret here to match (13px). */
.fss-show-more-actions > summary svg {
  width: 13px;
  height: 13px;
  flex-shrink: 0;
}

.fss-show-more-actions__panel {
  position: absolute;
  top: calc(100% + 8px);
  right: 0;
  min-width: 220px;
  padding: 8px;
  border: 1px solid var(--rule);
  border-radius: 10px;
  background: var(--surface-card);
  box-shadow: var(--shadow-md);
  z-index: 12;
}

.fss-show-more-actions:not([open]) .fss-show-more-actions__panel {
  display: none;
}

/* The Send-to-defects POST form sits inside the panel as a single item —
   display:contents removes the global `form` card chrome (style.css) so the
   button renders as a flush menu row. */
.fss-show-more-actions__form {
  display: contents;
}

.fss-show-more-actions__item {
  width: 100%;
  display: flex;
  align-items: center;
  padding: 9px 10px;
  border: 0;
  border-radius: 8px;
  background: transparent;
  color: var(--ink-2);
  font: 500 12.5px/1.4 "Inter", sans-serif;
  text-decoration: none;
  cursor: pointer;
  text-align: left;
}

.fss-show-more-actions__item:hover,
.fss-show-more-actions__item:focus {
  background: var(--surface-subtle);
  color: var(--ink);
}

.fss-show-more-actions__item.is-disabled {
  color: var(--ink-4);
  cursor: default;
}

.fss-show-more-actions__hint {
  opacity: 0.6;
  margin-left: 4px;
}

.fss-show-more-actions__divider {
  height: 1px;
  margin: 6px 0;
  background: var(--rule);
}

/* Edit-details modal — two-column field grid (fork of the fire-door
   .inspection-modal__form-grid; collapses to one column on mobile). */
.page-section--fs-survey-show .fss-edit-grid {
  display: grid;
  gap: 14px;
  grid-template-columns: repeat(2, minmax(0, 1fr));
  align-items: start;
  margin-bottom: 14px;
}
.page-section--fs-survey-show .fss-edit-grid .fss-assign-field {
  margin: 0;
}
@media (max-width: 900px) {
  .page-section--fs-survey-show .fss-edit-grid {
    grid-template-columns: 1fr;
  }
}

/* ---- Tabs (forked from .inspection-tabs — dark-active, fit-content) ------ */
.fss-vtabs {
  display: flex;
  width: fit-content;
  max-width: 100%;
  gap: 0;
  margin: 16px 16px 0;
  padding: 4px;
  border-radius: 12px;
  border: 1px solid var(--rule);
  background: var(--surface-card);
  box-shadow: var(--shadow-card);
  overflow-x: auto;
  -webkit-overflow-scrolling: touch;
  scrollbar-width: none;
}

.fss-vtabs::-webkit-scrollbar {
  display: none;
}

.fss-vtab {
  flex: 0 0 auto;
  white-space: nowrap;
  padding: 10px 16px;
  border: 0;
  border-radius: 8px;
  background: transparent;
  color: var(--ink-4);
  font: 500 13px/1 var(--font-sans);
  cursor: pointer;
}

.fss-vtab:hover {
  color: var(--ink-2);
}

.fss-vtab.is-active {
  background: var(--ink);
  color: var(--surface-card);
  box-shadow: var(--shadow-sm);
}

.fss-vtab-panels {
  margin-top: 0;
}

.fss-vtab-panel[hidden] {
  display: none;
}

.fss-vtab-content {
  display: flex;
  flex-direction: column;
  gap: 16px;
  padding: 20px 28px 0;
}

/* ---- Cards on the show page ---------------------------------------------- */
.fss-card {
  background: var(--surface-card);
  border-radius: 12px;
  box-shadow: var(--shadow-card);
  overflow: hidden;
}

.fss-card-head {
  padding: 16px 20px 0;
}

.fss-card-eyebrow {
  display: block;
  color: var(--accent);
  font-size: 9.5px;
  font-weight: 600;
  letter-spacing: 0.1em;
  text-transform: uppercase;
}

.fss-card-title {
  margin: 4px 0 0;
  color: var(--ink);
  font-size: 15px;
  font-weight: 600;
}

.fss-card-body {
  padding: 14px 20px 18px;
}

.fss-placeholder {
  color: var(--ink-3);
  font-size: 13px;
  line-height: 1.6;
}

.page-section--fs-survey-show .fss-table-wrap {
  margin-top: 12px;
}

/* ==========================================================================
   Summary surface — KPI stat strip + Property / Client / Summary info cards.
   Forked 1:1 from the inspection-show _summary.php block (sc-strip / show-info-
   row), on fss-* classes and global :root tokens (so dark mode comes for free).
   Desktop: always shown. Mobile (≤900px): collapsed behind the header
   "Details" toggle (.is-open reveals it).
   ========================================================================== */
.fss-sc-strip {
  display: grid;
  grid-template-columns: repeat(5, minmax(0, 1fr));
  gap: 14px;
  padding: 20px 28px 0;
}

.fss-sc {
  display: flex;
  flex-direction: column;
  gap: 6px;
  min-width: 0;
  padding: 14px 16px;
  border-radius: 10px;
  background: var(--surface-card);
  box-shadow: var(--shadow-card);
}

.fss-sc-label {
  font-size: 10px;
  font-weight: 600;
  letter-spacing: 0.08em;
  text-transform: uppercase;
  color: var(--ink-4);
}

.fss-sc-value {
  font-family: var(--font-display, "Space Grotesk", "Inter", sans-serif);
  font-size: 24px;
  font-weight: 700;
  line-height: 1;
  letter-spacing: -0.03em;
  color: var(--ink);
}

.fss-sc-value.warn {
  color: var(--danger);
}

.fss-sc-value.ok {
  color: var(--success);
}

.fss-sc-foot,
.fss-sc-sig,
.fss-sc-sig-link {
  font-size: 11px;
  color: var(--ink-4);
}

.fss-sig-img {
  display: block;
  max-width: 100%;
  max-height: 34px;
  border-radius: 6px;
  border: 1px solid var(--rule);
  background: var(--surface-inset);
  padding: 4px 8px;
}

.fss-info-row {
  display: grid;
  grid-template-columns: repeat(3, minmax(0, 1fr));
  gap: 14px;
  padding: 14px 28px 0;
}

.fss-ir-card {
  min-width: 0;
  background: var(--surface-card);
  border-radius: 10px;
  padding: 16px 18px;
  box-shadow: var(--shadow-card);
}

.fss-ir-label {
  display: flex;
  align-items: center;
  gap: 5px;
  margin-bottom: 6px;
  color: var(--ink-4);
  font-size: 9.5px;
  font-weight: 600;
  letter-spacing: 0.1em;
  text-transform: uppercase;
}

.fss-ir-label-dot {
  width: 6px;
  height: 6px;
  border-radius: 50%;
  background: var(--surface-inset);
  border: 1px solid var(--rule-strong);
}

.fss-ir-label-dot.connected {
  background: var(--success);
}

.fss-ir-label-dot.warn {
  background: var(--accent);
}

.fss-ir-title {
  margin-bottom: 2px;
  font-size: 15px;
  font-weight: 600;
  color: var(--ink);
}

.fss-ir-sub,
.fss-ir-summary-label {
  color: var(--ink-4);
  font-size: 12px;
}

.fss-ir-sub--empty {
  margin-bottom: 10px;
}

.fss-ir-logo-wrap {
  margin-bottom: 8px;
}

.fss-ir-logo {
  max-height: 28px;
  width: auto;
}

.fss-ir-actions {
  display: flex;
  align-items: center;
  gap: 6px;
  flex-wrap: wrap;
}

/* The inline Unlink <form> must not pick up the global form{} card chrome
   (background/padding/radius) — display:contents drops its box so the button
   sits directly in the flex row. */
.fss-ir-actions form {
  display: contents;
}

.fss-ir-action {
  display: inline-flex;
  align-items: center;
  gap: 5px;
  padding: 5px 10px;
  border-radius: 6px;
  border: 1px solid var(--rule-strong);
  background: var(--surface-card);
  color: var(--ink-3);
  font: 500 11.5px/1 var(--font-sans);
  text-decoration: none;
  cursor: pointer;
}

.fss-ir-action:hover {
  background: var(--surface-subtle);
  color: var(--ink);
}

.fss-ir-summary-stack {
  margin-top: 8px;
}

.fss-ir-summary-row {
  display: flex;
  align-items: baseline;
  justify-content: space-between;
  gap: 10px;
  padding: 3px 0;
}

.fss-ir-summary-value {
  font-size: 14px;
  font-weight: 600;
  color: var(--ink);
}

.fss-ir-summary-value.warn {
  color: var(--danger);
}

.fss-ir-note-preview {
  margin-top: 8px;
  font-size: 12px;
  color: var(--ink-4);
  font-style: italic;
}

/* Mobile "Details" toggle lives in the header — hidden on desktop, the summary
   is always visible there. */
.fss-h-details-btn {
  display: none;
}

/* ==========================================================================
   Responsive (≤900px)
   ========================================================================== */
@media (max-width: 900px) {
  /* Summary collapses behind the header Details toggle. */
  .fss-h-details-btn {
    display: inline-flex;
  }

  .page-section--fs-survey-show .fss-summary {
    display: none;
  }

  .page-section--fs-survey-show .fss-summary.is-open {
    display: block;
  }

  .fss-sc-strip {
    grid-template-columns: repeat(2, minmax(0, 1fr));
    gap: 12px;
    padding: 14px 16px 0;
  }

  .fss-sc-value {
    font-size: 26px;
  }

  .fss-info-row {
    grid-template-columns: minmax(0, 1fr);
    gap: 12px;
    padding: 12px 16px 0;
  }

  .fss-ir-card {
    border-radius: 12px;
    padding: 16px;
  }

  .fss-header {
    padding: 16px;
  }

  .fss-h-main {
    flex-direction: column;
  }

  /* Title eases down on phones (fire-door .ih-title does the same: 24 -> 20). */
  .fss-h-title {
    font-size: 20px;
    letter-spacing: -0.025em;
  }

  .fss-h-right {
    width: 100%;
    justify-content: flex-start;
  }

  /* Desktop action cluster hides; the mobile Details + More cluster shows
     (mirrors fire-door .ih-right--desktop / .ih-mobile-actions). */
  .fss-h-right--desktop {
    display: none;
  }

  .fss-h-mobile-actions {
    display: flex;
    align-items: center;
    gap: 8px;
    width: 100%;
  }

  .fss-h-mobile-actions .fss-show-more-actions__panel {
    left: 0;
    right: auto;
    width: min(260px, calc(100vw - 32px));
    min-width: 0;
    max-width: calc(100vw - 32px);
    z-index: 20;
  }

  /* (Mobile sync-strip rules live in fire-stopping-offline.css.) */

  .fss-vtabs {
    width: auto;
    margin: 16px 16px 0;
  }

  .fss-vtab-content {
    padding: 16px 16px 0;
  }
}

/* ==========================================================================
   Penetrations tab — toolbar + table forked to the fire-door Doors-tab
   treatment. The rail/railbtn/drawer chrome are the shared canonical
   primitives; the filter STRIP (fss-pen-filtergrid/search/select) is forked
   1:1 from the Doors tab's isd-doors-* strip so it matches byte-for-byte
   (the canonical ipi-filter-bar grid did NOT). Table + chips are fss-pen-*.
   ========================================================================== */

/* Refresh sits on its own row beneath Filters/Compact/Clear, gold-tinted —
   mirrors the Doors rail (only visible ≤900 where the rail renders). */
.page-section--fs-survey-show .fss-pen-shell { overflow: hidden; }

.page-section--fs-survey-show .fss-pen-shell .ipi-filter-rail__actions {
  flex-direction: column;
  align-items: stretch;
  gap: 8px;
}

.page-section--fs-survey-show .fss-pen-actionrow {
  display: flex;
  gap: 8px;
  justify-content: flex-end;
}

.page-section--fs-survey-show .ipi-filter-rail__actions .ipi-filter-railbtn[data-fss-pen-refresh] {
  justify-content: center;
  background: rgba(196, 149, 16, 0.16);
  border-color: rgba(196, 149, 16, 0.55);
  color: #8f6a06;
}

html[data-theme="dark"] .page-section--fs-survey-show .ipi-filter-rail__actions .ipi-filter-railbtn[data-fss-pen-refresh] {
  background: rgba(227, 176, 8, 0.18);
  border-color: rgba(227, 176, 8, 0.45);
  color: #f4d98b;
}

.page-section--fs-survey-show .ipi-filter-railbtn span[data-fss-pen-filters-count] {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  min-width: 18px;
  height: 18px;
  padding: 0 5px;
  border-radius: 999px;
  background: var(--ipi-accent-bg);
  color: var(--ipi-accent);
  font-size: 10px;
  font-weight: 700;
}

/* Desktop: the canonical .tnt-filter-drawer unwraps inline (display:contents),
   so the strip renders as a horizontal filter bar of pills. */
.page-section--fs-survey-show .fss-pen-filtergrid {
  display: flex;
  flex-wrap: nowrap;
  align-items: center;
  gap: 8px;
  padding: 12px 20px;
}

.page-section--fs-survey-show .fss-pen-search {
  display: flex;
  align-items: center;
  gap: 8px;
  flex: 1 1 auto;
  min-width: 0;
  height: 32px;
  padding: 0 11px;
  border: 1px solid var(--ipi-rule-h);
  border-radius: 7px;
  background: var(--ipi-bg);
}

.page-section--fs-survey-show .fss-pen-search svg {
  width: 13px;
  height: 13px;
  color: var(--ipi-ink-4);
  flex-shrink: 0;
}

.page-section--fs-survey-show .fss-pen-search input {
  flex: 1 1 auto;
  width: 100%;
  min-height: auto;
  margin: 0;
  padding: 0;
  border: 0;
  border-radius: 0;
  background: transparent;
  box-shadow: none;
  color: var(--ipi-ink);
  font-size: 12.5px;
  outline: none;
}

.page-section--fs-survey-show .fss-pen-search input::placeholder { color: var(--ipi-ink-4); }

.page-section--fs-survey-show .fss-pen-select {
  flex: 0 0 130px;
  width: 130px;
  min-width: 130px;
  min-height: 32px;
  height: 32px;
  padding: 0 28px 0 11px;
  border: 1px solid var(--ipi-rule-h);
  border-radius: 7px;
  background-color: var(--ipi-bg);
  color: var(--ipi-ink);
  font: 500 12.5px/1 "Inter", sans-serif;
  appearance: none;
  cursor: pointer;
  outline: none;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
  background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 10 6' fill='none' stroke='%239A9188' stroke-width='1.5' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpath d='M1 1l4 4 4-4'/%3E%3C/svg%3E");
  background-repeat: no-repeat;
  background-position: right 10px center;
  background-size: 10px;
}

.page-section--fs-survey-show .fss-pen-select--sort {
  flex-basis: 150px;
  width: 150px;
  min-width: 150px;
}

/* 901–1024 (tablet): above 900 the drawer unwraps inline, but the desktop rule
   above keeps it a nowrap row of fixed-width selects — on iPad-width tablets that
   overflows/crams. Mirror the Doors isd-doors tablet rule: let the inline bar
   wrap and the controls size to content so they breathe. */
@media (min-width: 901px) and (max-width: 1024px) {
  .page-section--fs-survey-show .fss-pen-filtergrid {
    flex-wrap: wrap;
  }

  .page-section--fs-survey-show .fss-pen-search {
    flex: 1 1 220px;
    min-width: 180px;
  }

  .page-section--fs-survey-show .fss-pen-select,
  .page-section--fs-survey-show .fss-pen-select--sort {
    flex: 0 1 auto;
    width: auto;
    min-width: 150px;
  }
}

/* ≤900: the drawer is a bottom-sheet; stack the filters as 44px touch targets
   (mirrors the Doors isd-doors-* drawer styling). */
@media (max-width: 900px) {
  .page-section--fs-survey-show .fss-pen-filtergrid {
    display: grid;
    grid-template-columns: 1fr;
    flex-wrap: initial;
    gap: 12px;
    padding: 0;
  }

  .page-section--fs-survey-show .fss-pen-search {
    height: 44px;
    padding: 0 14px;
    border: 0;
    border-radius: 12px;
    background: var(--ipi-bg-card);
    box-shadow: var(--ipi-shadow-card);
  }

  .page-section--fs-survey-show .fss-pen-search input { font-size: 13px; }

  .page-section--fs-survey-show .fss-pen-select,
  .page-section--fs-survey-show .fss-pen-select--sort {
    flex: initial;
    width: 100%;
    min-width: 0;
    height: 44px;
    min-height: 44px;
    padding: 0 28px 0 14px;
    border: 1px solid var(--ipi-rule-h);
    border-radius: 12px;
    background-color: var(--ipi-bg-card);
    box-shadow: var(--ipi-shadow-card);
    font-size: 13px;
  }
}

/* Column widths (mirror door-overview-table's proportions). DESKTOP ONLY —
   at ≤900 the table card-ifies and each cell must be full-width; leaving these
   percentages unscoped shrank the mobile card cells to 9–24% (cramming the
   values left + helping the per-char label wrap). */
@media (min-width: 901px) {
  .fss-pen-table td[data-label="Penetration"],
  .fss-pen-table th:nth-child(1) { width: 24%; }
  .fss-pen-table td[data-label="Status"],
  .fss-pen-table th:nth-child(2) { width: 9%; }
  .fss-pen-table td[data-label="Severity"],
  .fss-pen-table th:nth-child(3) { width: 9%; }
  .fss-pen-table td[data-label="System"],
  .fss-pen-table th:nth-child(4) { width: 16%; }
  .fss-pen-table td[data-label="Specs"],
  .fss-pen-table th:nth-child(5) { width: 19%; }
  .fss-pen-table td[data-label="Construction"],
  .fss-pen-table th:nth-child(6) { width: 16%; }
  .fss-pen-table .fss-td-actions { width: 44px; text-align: right; white-space: nowrap; }
}

/* Clickable name (the whole row opens Edit, like a door row opens its detail). */
.fss-pen-row:hover .fss-td-name { color: var(--accent-strong); }
.fss-td-sub--defect { color: var(--danger); }

/* Status + severity chips — fork of .pass-chip / .sev-chip (rounded-rect, 5px). */
.fss-pen-chip {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  min-height: 20px;
  padding: 2px 8px;
  border-radius: 5px;
  border: 1px solid var(--rule-strong);
  font-size: 11px;
  font-weight: 600;
  letter-spacing: 0.01em;
  white-space: nowrap;
}
.fss-pen-chip--pass { background: var(--success-soft); color: var(--success); border-color: rgba(30, 122, 69, 0.2); }
.fss-pen-chip--fail { background: var(--danger-soft); color: var(--danger); border-color: rgba(176, 48, 48, 0.18); }
.fss-pen-chip--defective { background: var(--accent-soft); color: var(--accent); border-color: rgba(196, 149, 16, 0.22); }
.fss-pen-chip--na { background: var(--surface-inset); color: var(--ink-3); border-color: var(--rule-strong); }
.fss-pen-chip--sev-low { background: var(--surface-inset); color: var(--ink-4); border-color: var(--rule-strong); }
.fss-pen-chip--sev-medium { background: var(--accent-soft); color: var(--accent); border-color: rgba(196, 149, 16, 0.22); }
.fss-pen-chip--sev-high { background: var(--danger-soft); color: var(--danger); border-color: rgba(176, 48, 48, 0.18); }

/* Subtle row delete — revealed on hover so the row reads like the doors list. */
.fss-pen-table .table-delete-btn { opacity: 0; transition: opacity 0.12s ease; }
.fss-pen-row:hover .table-delete-btn,
.fss-pen-table .table-delete-btn:focus-visible { opacity: 1; }

/* Compact density toggle (mirrors door-overview-table--compact). */
.fss-pen-table--compact thead th,
.fss-pen-table--compact tbody td { padding-top: 7px; padding-bottom: 7px; }

/* ---- Mobile (≤900px): a proper card per penetration --------------------------
   The shared `.fss-table` card-ification (fire-stopping.css) stacks every cell as
   a label/value row, which crams the rich "Penetration" identity cell to the
   right. Override it for `.fss-pen-table` so the card reads like the fire-door
   `.isd-doorcard`: the location is the heading (left, no label), a visible delete
   pinned top-right, then Status/Severity/System/Specs/Construction as a clean
   spec list. Also reveal the delete (no :hover on touch) and surface the filter
   rail at ≤900 — the canonical `.ipi-filter-rail` only shows ≤768, so 769–900px
   had no inline filters AND no Filters button (a dead zone). */
@media (max-width: 900px) {
  /* Full rail layout at ≤900 (mirrors the Doors isd-doors ≤900 rail block).
     The canonical rail layout is gated at ≤768, but we surface the rail up to
     ≤900 — without the container layout here, tablet portrait (769–900) showed
     the rail unstyled and the Filters/Compact/Clear/Refresh cluster collapsed
     out of its stacked card. The __actions column + actionrow already apply at
     all widths above. */
  .page-section--fs-survey-show .fss-pen-shell .ipi-filter-rail {
    display: flex;
    align-items: flex-start;
    justify-content: space-between;
    gap: 12px;
    padding: 14px 16px;
    background: var(--ipi-bg-card);
    border-radius: 12px;
    box-shadow: var(--ipi-shadow-card);
  }

  .page-section--fs-survey-show .fss-pen-table tbody tr {
    position: relative;
    padding: 14px 16px;
    gap: 0;
  }

  /* "Penetration" cell becomes the card heading: full width, left, no label. */
  .page-section--fs-survey-show .fss-pen-table td[data-label="Penetration"] {
    display: block;
    text-align: left;
    padding: 0 42px 10px 0;
  }
  .page-section--fs-survey-show .fss-pen-table td[data-label="Penetration"]::before { display: none; }
  .page-section--fs-survey-show .fss-pen-table td[data-label="Penetration"] .fss-td-name {
    font: 700 15px/1.25 var(--font-display, "Space Grotesk", "Inter", sans-serif);
    letter-spacing: -0.01em;
  }
  .page-section--fs-survey-show .fss-pen-table td[data-label="Penetration"] .fss-td-sub { display: block; margin-top: 2px; }

  /* Status / Severity / System / Specs / Construction = clean label/value rows. */
  .page-section--fs-survey-show .fss-pen-table td[data-label="Status"],
  .page-section--fs-survey-show .fss-pen-table td[data-label="Severity"],
  .page-section--fs-survey-show .fss-pen-table td[data-label="System"],
  .page-section--fs-survey-show .fss-pen-table td[data-label="Specs"],
  .page-section--fs-survey-show .fss-pen-table td[data-label="Construction"] {
    padding: 8px 0;
    border-top: 1px solid var(--rule);
  }
  /* The label sits left and must stay on one line. `mobile.css` sets
     `.content { overflow-wrap: anywhere }` (inherited), which — with the
     flex squeeze — otherwise breaks the `::before` label one char per line
     (the "S T A T U S" bug). nowrap + no-shrink pins it; the value wraps. */
  .page-section--fs-survey-show .fss-pen-table td[data-label="Status"]::before,
  .page-section--fs-survey-show .fss-pen-table td[data-label="Severity"]::before,
  .page-section--fs-survey-show .fss-pen-table td[data-label="System"]::before,
  .page-section--fs-survey-show .fss-pen-table td[data-label="Specs"]::before,
  .page-section--fs-survey-show .fss-pen-table td[data-label="Construction"]::before {
    flex: 0 0 auto;
    white-space: nowrap;
  }
  .page-section--fs-survey-show .fss-pen-table td[data-label] > * { min-width: 0; }

  /* Delete: pinned top-right, always visible, a real 34px tap target. */
  .page-section--fs-survey-show .fss-pen-table .fss-td-actions {
    position: absolute;
    top: 8px;
    right: 8px;
    width: auto;
    padding: 0;
    border-top: 0;
  }
  .page-section--fs-survey-show .fss-pen-table .fss-td-actions::before { display: none; }
  .page-section--fs-survey-show .fss-pen-table .table-delete-btn {
    opacity: 1;
    width: 34px;
    height: 34px;
    display: inline-flex;
    align-items: center;
    justify-content: center;
  }
}

/* "No matches" note under the table (mirrors .doors-empty-note). */
.fss-pen-empty-filter {
  margin: 0;
  padding: 22px 20px;
  text-align: center;
  font-size: 13px;
  color: var(--ink-4);
}

.fss-pen-emptycard .fss-card-body { text-align: left; }

/* ==========================================================================
   Penetration detail modal — forked 1:1 from the fire-door door-detail modal
   (`.inspection-door-modal__*`), adapted for a penetration. Lives inside the
   `.fss-modal` shell; token-based so dark mode comes for free. Evidence images
   are auto-loaded inline (grouped Before/During/After) and zoom via the shared
   lightbox. Roughly half the door modal's sections (no component checklist).
   ========================================================================== */

.fss-pen-detail {
  display: flex;
  flex-direction: column;
  gap: 16px;
}

/* The view + edit form are the article's direct children (gapped above); the
   view's own sections (summary, gallery, status bar, actions) need their own
   column gap or they sit flush. */
.fss-pen-detail__view {
  display: flex;
  flex-direction: column;
  gap: 16px;
}

.fss-pen-detail__loading {
  padding: 28px 8px;
  text-align: center;
  color: var(--ink-4);
  font-size: 13px;
}

/* ---- Summary card (inset, sectioned with separators — mirrors the door) --- */
.fss-pen-detail__summary {
  background: var(--surface-inset);
  border: 1px solid var(--rule-strong);
  border-radius: 12px;
  overflow: hidden;
}

.fss-pen-detail__summary-head {
  display: flex;
  align-items: center;
  justify-content: space-between;
  flex-wrap: wrap;
  gap: 10px;
  padding: 14px 16px 10px;
  border-bottom: 1px solid var(--rule);
}

.fss-pen-detail__name {
  color: var(--ink);
  font-family: var(--font-display, "Space Grotesk", "Inter", sans-serif);
  font-size: 15px;
  font-weight: 700;
  letter-spacing: -0.015em;
  min-width: 0;
}

.fss-pen-detail__chips {
  display: flex;
  align-items: center;
  gap: 6px;
  flex-wrap: wrap;
}

.fss-pen-detail__alert {
  padding: 10px 16px;
  color: var(--ink-3);
  font-size: 12.5px;
  line-height: 1.55;
  border-bottom: 1px solid var(--rule);
}

.fss-pen-detail__alert code {
  background: var(--surface-card);
  border-radius: 5px;
  padding: 1px 5px;
  color: var(--ink);
}

.fss-pen-detail__alert--defect {
  color: var(--danger);
  background: var(--danger-soft);
}

.fss-pen-detail__spec-row {
  display: flex;
  align-items: center;
  gap: 6px;
  flex-wrap: wrap;
  padding: 10px 16px;
  border-bottom: 1px solid var(--rule);
}

.fss-pen-detail__spec-pill {
  display: inline-flex;
  align-items: center;
  padding: 3px 10px;
  border-radius: 999px;
  background: var(--surface-card);
  border: 1px solid var(--rule-strong);
  color: var(--ink-3);
  font-size: 12px;
  font-weight: 400;
}

.fss-pen-detail__spec-pill--muted { color: var(--ink-4); }

.fss-pen-detail__meta-row {
  padding: 10px 16px 12px;
}

.fss-pen-detail__notes {
  color: var(--ink-4);
  font-size: 12.5px;
  font-weight: 300;
  line-height: 1.55;
}

/* ---- Auto-loaded evidence gallery (the penetration-specific addition) ----- */
.fss-pen-detail__gallery-wrap {
  display: flex;
  flex-direction: column;
  gap: 14px;
}

.fss-pen-detail__gallery-label {
  margin: 0 0 8px;
  color: var(--ink-4);
  font-size: 9.5px;
  font-weight: 700;
  letter-spacing: 0.09em;
  text-transform: uppercase;
}

.fss-pen-detail__gallery {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(118px, 1fr));
  gap: 8px;
}

.fss-pen-detail__photo {
  display: block;
  aspect-ratio: 4 / 3;
  border-radius: 10px;
  overflow: hidden;
  border: 1px solid var(--rule-strong);
  background: var(--surface-inset);
  cursor: zoom-in;
}

.fss-pen-detail__photo img {
  width: 100%;
  height: 100%;
  object-fit: cover;
  display: block;
}

.fss-pen-detail__empty {
  margin: 0;
  padding: 18px;
  border: 1px dashed var(--rule-strong);
  border-radius: 10px;
  text-align: center;
  color: var(--ink-4);
  font-size: 12.5px;
}

/* ---- Status bar (mirrors the door status bar) ----------------------------- */
.fss-pen-detail__status-bar {
  display: flex;
  align-items: center;
  gap: 20px;
  padding: 12px 16px;
  border-radius: 10px;
  border: 1px solid var(--success);
  background: var(--success-soft);
}

.fss-pen-detail__status-bar--fail {
  border-color: var(--danger);
  background: var(--danger-soft);
}

.fss-pen-detail__status-metric p {
  margin: 0 0 2px;
  color: var(--ink-4);
  font-size: 9px;
  font-weight: 700;
  letter-spacing: 0.1em;
  text-transform: uppercase;
}

.fss-pen-detail__status-metric strong {
  color: var(--success);
  font-size: 15px;
  font-weight: 700;
  letter-spacing: -0.01em;
}

.fss-pen-detail__status-bar--fail .fss-pen-detail__status-metric strong { color: var(--danger); }
.fss-pen-detail__severity-value--low { color: var(--ink-4); }
.fss-pen-detail__severity-value--medium { color: var(--accent); }
.fss-pen-detail__severity-value--high { color: var(--danger); }

.fss-pen-detail__status-sep {
  width: 1px;
  height: 28px;
  background: var(--success);
  opacity: 0.4;
  flex-shrink: 0;
}

.fss-pen-detail__status-bar--fail .fss-pen-detail__status-sep { background: var(--danger); }

.fss-pen-detail__status-note {
  margin: 0 0 0 auto;
  color: var(--success);
  font-size: 12.5px;
  font-weight: 500;
  letter-spacing: 0.04em;
  text-transform: uppercase;
}

.fss-pen-detail__status-bar--fail .fss-pen-detail__status-note { color: var(--danger); }

/* ---- Actions ------------------------------------------------------------- */
.fss-pen-detail__actions {
  display: flex;
  align-items: center;
  justify-content: space-between;
  gap: 10px;
  flex-wrap: wrap;
}

.fss-pen-detail__danger-btn {
  color: var(--danger);
  font-weight: 600;
  font-size: 13px;
  padding: 0;
  background: transparent;
  border: 0;
  cursor: pointer;
  text-decoration: underline;
  text-underline-offset: 2px;
}

.fss-pen-detail__danger-btn:hover,
.fss-pen-detail__danger-btn:focus-visible {
  color: #851d1d;
  outline: none;
}

/* ---- In-modal edit form (everything editable in place — no redirect) ------
   Fields inherit the `.fss-modal` form-field styling (label + input); the rules
   below are layout-only helpers + the evidence photo manager. */
.fss-pen-edit {
  gap: 16px;
}

/* Tabbed sections (Identity / Construction / System / Result / Evidence) — only
   one short panel shows at a time, so the form never reads as a wall of fields.
   Same `.fss-tabs`/`.fss-tab` pattern as the Tested Systems add/edit modal. */
.fss-pen-edit__tabs {
  display: flex;
  max-width: 100%;
  overflow-x: auto;
  scrollbar-width: none;
}

.fss-pen-edit__tabs::-webkit-scrollbar { display: none; }

.fss-pen-edit__tabs .fss-tab {
  flex: 0 0 auto;
  white-space: nowrap;
}

.fss-pen-edit__panel {
  display: flex;
  flex-direction: column;
  gap: 14px;
}

.fss-pen-edit__hint {
  margin: 0;
  font-size: 12px;
  line-height: 1.5;
  color: var(--ink-4);
}

.fss-pen-edit__row {
  display: grid;
  grid-template-columns: 1fr 1fr;
  gap: 12px;
}

.fss-pen-edit__row--3 { grid-template-columns: 1fr 1fr 1fr; }

.fss-pen-edit__defect {
  display: flex;
  flex-direction: column;
  gap: 14px;
  padding: 12px;
  border: 1px solid var(--rule);
  border-radius: 10px;
  background: var(--surface-inset);
}

.fss-pen-edit__stagelabel {
  position: relative;
  padding-left: 14px;
  font-size: 12px;
  font-weight: 600;
  color: var(--ink);
}

.fss-pen-edit__stagelabel::before {
  content: "";
  position: absolute;
  left: 0;
  top: 50%;
  width: 8px;
  height: 8px;
  margin-top: -4px;
  border-radius: 999px;
  background: var(--accent);
}

.fss-pen-edit__stage[data-stage="during"] .fss-pen-edit__stagelabel::before { background: var(--info, #2563a8); }
.fss-pen-edit__stage[data-stage="after"] .fss-pen-edit__stagelabel::before { background: var(--success); }

/* Before / During / After as three columns: add button in the top row, the
   stage's images stack beneath it (under the correct column, only when any). */
.fss-pen-edit__photos {
  display: grid;
  grid-template-columns: repeat(3, minmax(0, 1fr));
  gap: 12px;
  align-items: start;
}

.fss-pen-edit__stage {
  display: flex;
  flex-direction: column;
  gap: 8px;
  min-width: 0;
}

.fss-pen-edit__thumbs {
  display: grid;
  grid-template-columns: repeat(2, minmax(0, 1fr));
  gap: 6px;
}

.fss-pen-edit__thumb {
  position: relative;
  aspect-ratio: 1 / 1;
  border-radius: 8px;
  overflow: hidden;
  border: 1px solid var(--rule-strong);
}

.fss-pen-edit__thumb img {
  width: 100%;
  height: 100%;
  object-fit: cover;
  display: block;
}

.fss-pen-edit__thumb-del {
  position: absolute;
  top: 4px;
  right: 4px;
  width: 22px;
  height: 22px;
  display: inline-flex;
  align-items: center;
  justify-content: center;
  border: 0;
  border-radius: 999px;
  background: rgba(26, 24, 21, 0.66);
  color: #fff;
  font-size: 16px;
  line-height: 1;
  cursor: pointer;
}

.fss-pen-edit__thumb-del:hover { background: var(--danger); }

/* `.fss-modal`'s input styling omits type="number"; match it here so the gap /
   depth fields render like the other inputs. */
.fss-pen-edit input[type="number"] {
  min-height: 40px;
  padding: 10px 13px;
  border-radius: 9px;
  border: 1px solid var(--rule-strong);
  background: var(--surface-card);
  font-family: var(--font-sans);
  font-size: 13.5px;
  color: var(--ink);
  width: 100%;
  box-sizing: border-box;
  transition: border-color 0.15s ease, box-shadow 0.15s ease;
}

.fss-pen-edit input[type="number"]:focus {
  border-color: var(--accent-strong);
  box-shadow: 0 0 0 3px var(--accent-soft);
  outline: none;
}

/* Add-photo tile — a compact dashed square at the end of the stage's thumbnail
   row (the native file input is hidden; the tile is the click target). */
.fss-pen-edit__fileinput {
  position: absolute;
  width: 1px;
  height: 1px;
  opacity: 0;
  overflow: hidden;
}

.fss-pen-edit__addtile {
  min-height: 72px;
  display: flex;
  align-items: center;
  justify-content: center;
  border-radius: 8px;
  border: 1px dashed var(--rule-strong);
  background: var(--surface-inset);
  color: var(--ink-4);
  cursor: pointer;
  transition: border-color 0.15s ease, color 0.15s ease, background 0.15s ease;
}

.fss-pen-edit__addtile:hover {
  border-color: var(--accent);
  color: var(--accent);
  background: var(--accent-soft);
}

.fss-pen-edit__fileinput:focus-visible + .fss-pen-edit__addtile {
  border-color: var(--accent-strong);
  box-shadow: 0 0 0 3px var(--accent-soft);
}

.fss-pen-edit__actions {
  display: flex;
  align-items: center;
  justify-content: flex-end;
  gap: 10px;
  padding-top: 18px;
  border-top: 1px solid var(--rule);
}

@media (max-width: 900px) {
  .fss-pen-edit__row,
  .fss-pen-edit__row--3 { grid-template-columns: 1fr; }
}

/* ==========================================================================
   FLOORPLANS — Layout & tags tab + pin modal.
   A verbatim fork of the fire-door floorplan CSS (inspection_show.css), which
   is NOT loaded on FS pages. Class names are kept identical for a pixel 1:1;
   only the modal z-index is raised (2130 -> 2500) so the pin modal stacks above
   the mobile capture stepper (z-index 2200-2400), and the gallery click hook is
   the forked data-fss-floorplan-plan-id. Driven by features/fire-stopping-floorplan.js.
   ========================================================================== */
.floorplan-modal {
    position: fixed;
    inset: 0;
    background: rgba(26, 24, 21, 0.42);
    display: flex;
    align-items: center;
    justify-content: center;
    z-index: 2500;
    padding: 40px;
}
.floorplan-modal[hidden] {
    display: none;
}
.floorplan-modal__backdrop {
    position: absolute;
    inset: 0;
}
.floorplan-modal__dialog {
    position: relative;
    background: #ffffff;
    border-radius: 18px;
    border: 1px solid rgba(35, 31, 24, 0.08);
    padding: 0;
    width: 100%;
    max-width: calc(100vw - 80px);
    height: calc(100vh - 80px);
    overflow: hidden;
    display: flex;
    flex-direction: column;
    gap: 0;
    box-shadow: 0 28px 80px rgba(25, 19, 9, 0.22);
}
.floorplan-modal__header {
    display: flex;
    justify-content: space-between;
    align-items: flex-start;
    gap: 16px;
    padding: 18px 22px;
    flex-shrink: 0;
    border-bottom: 1px solid rgba(35, 31, 24, 0.08);
}
.floorplan-modal__tabs {
    display: flex;
    flex-wrap: wrap;
    gap: 8px;
    padding: 10px 22px;
    flex-shrink: 0;
    border-bottom: 1px solid rgba(35, 31, 24, 0.08);
    background: #f7f5f0;
}
.floorplan-modal__tabs button {
    border: 1px solid rgba(35, 31, 24, 0.12);
    border-radius: 999px;
    padding: 6px 14px;
    background: #ffffff;
    font-size: 0.82rem;
    font-weight: 500;
    color: #1a1815;
    cursor: pointer;
    transition: background 0.15s, border-color 0.15s;
}
.floorplan-modal__tabs button:hover {
    background: #edeae3;
}
.floorplan-modal__tabs button.is-active {
    background: #1a1815;
    color: #fff;
    border-color: #1a1815;
}
.floorplan-modal__stage {
    position: relative;
    background: #0f172a;
    border-radius: 0;
    flex: 1 1 auto;
    min-height: 0;
    overflow: hidden;
    touch-action: none;
}
.floorplan-stage__loading {
    position: absolute;
    inset: 0;
    display: flex;
    flex-direction: column;
    align-items: center;
    justify-content: center;
    gap: 12px;
    z-index: 5;
    pointer-events: none;
    opacity: 0;
    transition: opacity 0.2s ease;
}
.floorplan-modal__stage.is-loading .floorplan-stage__loading {
    opacity: 1;
}
.floorplan-modal__stage.is-loading .floorplan-stage__inner {
    opacity: 0;
}
.floorplan-stage__spinner {
    width: 28px;
    height: 28px;
    border-radius: 50%;
    border: 2.5px solid rgba(255, 255, 255, 0.18);
    border-top-color: rgba(255, 255, 255, 0.85);
    animation: fdBtnSpin 0.8s linear infinite;
}
.floorplan-stage__loading-text {
    font-size: 12px;
    font-weight: 500;
    color: rgba(255, 255, 255, 0.55);
    letter-spacing: 0.02em;
}
.floorplan-stage__inner {
    position: absolute;
    left: 50%;
    top: 50%;
    transform-origin: center center;
    transition: opacity 0.2s ease;
}
.floorplan-stage__inner img {
    display: block;
    max-width: none;
    pointer-events: none;
    width: 100%;
    height: 100%;
    object-fit: contain;
}
.floorplan-pin {
    position: absolute;
    width: 22px;
    height: 22px;
    border-radius: 50%;
    border: none;
    background: var(--brand, #c49510);
    transform: translate(-50%, -50%);
    box-shadow: 0 6px 12px rgba(0, 82, 204, 0.5);
    cursor: grab;
    z-index: 2;
}
.floorplan-pin[data-label]:not([data-label=""])::after {
    content: attr(data-label);
    position: absolute;
    top: -10px;
    left: 50%;
    transform: translate(-50%, -120%);
    background: rgba(234, 88, 12, 0.92);
    color: #fff;
    padding: 2px 8px;
    border-radius: 999px;
    font-size: 0.7rem;
    white-space: nowrap;
    pointer-events: none;
    box-shadow: 0 4px 10px rgba(15, 23, 42, 0.25);
}
.floorplan-pin[hidden]::after {
    content: '';
    display: none;
}

.floorplan-upload {
    margin-top: 12px;
    display: flex;
    flex-direction: column;
    gap: 12px;
}
.floorplan-header-actions {
    display: inline-flex;
    align-items: center;
    justify-content: flex-end;
    gap: 10px;
    flex-wrap: wrap;
}
.floorplan-upload--collapsed {
    margin-top: 8px;
}
.floorplan-upload summary::marker,
.floorplan-upload summary::-webkit-details-marker {
    content: '';
    display: none;
}
.floorplan-upload summary::-webkit-details-marker {
    content: '';
    display: none;
}
.floorplan-upload form {
    display: flex;
    flex-direction: column;
    gap: 12px;
}
.floorplan-upload__footer {
    display: flex;
    flex-wrap: wrap;
    align-items: center;
    gap: 12px;
}
.floorplan-markers {
    position: absolute;
    inset: 0;
    pointer-events: auto;
    z-index: 1;
}
.floorplan-marker {
    position: absolute;
    transform: translate(-50%, -100%);
    display: flex;
    flex-direction: column;
    align-items: center;
    gap: 4px;
    pointer-events: auto;
    text-align: center;
}
.floorplan-marker__dot {
    width: 12px;
    height: 12px;
    border-radius: 50%;
    background: rgba(234, 88, 12, 0.9);
    box-shadow: 0 4px 10px rgba(15, 23, 42, 0.3);
}
.floorplan-marker--tagged .floorplan-marker__dot {
    background: #16a34a;
}
.floorplan-marker--pending .floorplan-marker__dot {
    background: #f97316;
}
.floorplan-marker--faulty .floorplan-marker__dot {
    background: #dc2626;
}
.floorplan-marker__label {
    padding: 2px 6px;
    border-radius: 999px;
    background: rgba(15, 23, 42, 0.85);
    color: #fff;
    font-size: 0.68rem;
    max-width: 130px;
    white-space: nowrap;
    overflow: hidden;
    text-overflow: ellipsis;
}
.floorplan-gallery {
    margin-top: 16px;
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(260px, 1fr));
    gap: 20px;
}
.floorplan-gallery__item {
    display: flex;
    flex-direction: column;
    gap: 10px;
}
.floorplan-gallery__canvas {
    position: relative;
    border-radius: 16px;
    overflow: hidden;
    background: #0f172a;
    min-height: 220px;
}
.floorplan-gallery__canvas--empty {
    display: flex;
    align-items: center;
    justify-content: center;
    color: color-mix(in srgb, var(--text-muted, #475569) 55%, transparent);
    font-size: 0.9rem;
    text-transform: uppercase;
    letter-spacing: 0.08em;
}
.floorplan-gallery__canvas img {
    width: 100%;
    height: 100%;
    object-fit: contain;
    display: block;
    background: #0f172a;
}
.floorplan-gallery__meta {
    display: flex;
    flex-direction: column;
    gap: 4px;
}
.floorplan-gallery__title {
    margin: 0;
    font-size: 1rem;
}
.floorplan-gallery__pill {
    align-self: flex-start;
    padding: 2px 10px;
    border-radius: 999px;
    background: color-mix(in srgb, var(--brand, #c49510) 12%, var(--card, #ffffff));
    color: color-mix(in srgb, var(--brand-dark, #a97807) 78%, var(--text, #0f172a));
    font-size: 0.8rem;
}
.floorplan-gallery__empty {
    padding: 20px;
    border: 1px dashed color-mix(in srgb, var(--border, #e2e8f0) 75%, transparent);
    border-radius: 18px;
    background: var(--surface-muted, #f8fafc);
    text-align: center;
    color: var(--text-muted, #475569);
}
.floorplan-gallery__hint {
    margin: 0;
    font-size: 0.85rem;
    color: var(--text-muted, #475569);
}
/* Floorplan card management actions (Rename / Delete) — forked 1:1 of the
   fire-door .floorplan-gallery__action so FS renders identically without
   loading fire-door module CSS. */
.floorplan-gallery__actions {
    display: flex;
    flex-wrap: wrap;
    gap: 8px;
    margin-top: 8px;
}
.floorplan-gallery__action {
    border: 1px solid var(--rule, rgba(26, 24, 21, 0.12));
    background: var(--surface-card, #fff);
    color: var(--ink-2, #3d3a34);
    border-radius: 7px;
    padding: 4px 10px;
    font: 500 12px/1.3 "Inter", sans-serif;
    cursor: pointer;
    transition: background 0.15s ease, border-color 0.15s ease, color 0.15s ease;
}
.floorplan-gallery__action:hover,
.floorplan-gallery__action:focus {
    background: var(--surface-subtle, #f2efe9);
    color: var(--ink, #1a1815);
}
.floorplan-gallery__action--danger {
    color: var(--danger, #b03030);
}
.floorplan-gallery__action--danger:hover,
.floorplan-gallery__action--danger:focus {
    background: rgba(176, 48, 48, 0.08);
    border-color: rgba(176, 48, 48, 0.32);
    color: var(--danger, #b03030);
}
html[data-theme="dark"] .floorplan-gallery__action {
    background: rgba(15, 23, 42, 0.55);
    border-color: rgba(148, 163, 184, 0.22);
    color: #e2e8f0;
}
html[data-theme="dark"] .floorplan-gallery__action:hover,
html[data-theme="dark"] .floorplan-gallery__action:focus {
    background: rgba(15, 23, 42, 0.78);
    color: #f8fafc;
}
html[data-theme="dark"] .floorplan-gallery__action--danger {
    color: #f87171;
}
.floorplan-modal__hint {
    margin: 0;
    padding: 8px 22px;
    font-size: 12px;
    color: #8f8476;
    flex-shrink: 0;
    background: #f7f5f0;
    border-top: 1px solid rgba(35, 31, 24, 0.08);
}
.floorplan-modal__status {
    margin: 0;
    padding: 8px 22px;
    font-size: 12px;
    color: #6b6458;
    flex-shrink: 0;
    background: #edeae3;
    border-top: 1px solid rgba(35, 31, 24, 0.08);
}
.floorplan-modal__actions {
    display: flex;
    justify-content: space-between;
    align-items: center;
    gap: 10px;
    flex-wrap: wrap;
    flex-shrink: 0;
    padding: 16px 22px;
    border-top: 1px solid rgba(35, 31, 24, 0.08);
    background: #ffffff;
}
.floorplan-modal__actions-primary {
    display: flex;
    gap: 10px;
}

/* Narrow viewports: fullscreen floorplan — surfaces match ICM / door stepper (warm neutrals, not slate) */
.floorplan-modal.floorplan-modal--fullscreen {
    align-items: stretch;
    justify-content: stretch;
    padding: 0;
    background: #f7f5f0;
}

.floorplan-modal.floorplan-modal--fullscreen .floorplan-modal__backdrop {
    display: none;
}

.floorplan-modal.floorplan-modal--fullscreen .floorplan-modal__dialog {
    width: 100%;
    max-width: none;
    height: 100dvh;
    max-height: none;
    min-height: 100dvh;
    border-radius: 0;
    padding: 0;
    gap: 0;
    box-shadow: none;
    border: 0;
    background: #f7f5f0;
}

.floorplan-modal.floorplan-modal--fullscreen .floorplan-modal__header {
    flex-shrink: 0;
    align-items: flex-start;
    flex-wrap: wrap;
    gap: 10px 14px;
    padding: calc(env(safe-area-inset-top, 0px) + 10px) 20px 12px;
    background: #ffffff;
    border-bottom: 1px solid rgba(0, 0, 0, 0.07);
    box-shadow: 0 1px 3px rgba(0, 0, 0, 0.06), 0 1px 2px rgba(0, 0, 0, 0.04);
}

.floorplan-modal.floorplan-modal--fullscreen .floorplan-modal__header .inspection-modal__header-copy {
    flex: 1 1 auto;
    min-width: 0;
}

.floorplan-modal.floorplan-modal--fullscreen .floorplan-modal__header .inspection-modal__eyebrow {
    margin: 0 0 2px;
    color: #c49510;
    font-size: 9px;
    font-weight: 600;
    letter-spacing: 0.12em;
    text-transform: uppercase;
}

.floorplan-modal.floorplan-modal--fullscreen .floorplan-modal__header .inspection-modal__title {
    margin: 0;
    color: #1a1815;
    font-family: "Sora", sans-serif;
    font-size: 16px;
    font-weight: 700;
    letter-spacing: -0.02em;
    line-height: 1.2;
}

.floorplan-modal.floorplan-modal--fullscreen .floorplan-modal__header .inspection-modal__subcopy {
    display: none;
}

/* Specificity bumped 2026-04-12: must win over canonical
   .page-section--inspection-show .inspection-modal .modal__close (0,3,0)
   so the narrow-viewport close button keeps its 44px touch target. */
.page-section--inspection-show .inspection-modal.floorplan-modal.floorplan-modal--fullscreen .floorplan-modal__header .btn-link,
.page-section--inspection-show .inspection-modal.floorplan-modal.floorplan-modal--fullscreen .floorplan-modal__header .modal__close {
    color: #3d3a34;
    background: #ffffff;
    border: 1px solid rgba(0, 0, 0, 0.12);
    border-radius: 999px;
    min-width: 44px;
    min-height: 44px;
    width: 44px;
    height: 44px;
    font-size: 1.35rem;
    line-height: 1;
    display: inline-flex;
    align-items: center;
    justify-content: center;
}

.floorplan-modal.floorplan-modal--fullscreen .floorplan-modal__tabs {
    flex-shrink: 0;
    flex-wrap: nowrap;
    overflow-x: auto;
    overflow-y: hidden;
    -webkit-overflow-scrolling: touch;
    gap: 8px;
    padding: 10px 16px;
    background: #ffffff;
    border-bottom: 1px solid rgba(0, 0, 0, 0.07);
    scrollbar-width: thin;
}

.floorplan-modal.floorplan-modal--fullscreen .floorplan-modal__tabs button {
    flex-shrink: 0;
    border-color: rgba(35, 31, 24, 0.12);
    background: #f7f5f0;
    color: #1a1815;
}

.floorplan-modal.floorplan-modal--fullscreen .floorplan-modal__tabs button.is-active {
    background: #1a1815;
    color: #fff;
    border-color: #1a1815;
}

.floorplan-modal.floorplan-modal--fullscreen .floorplan-modal__stage {
    flex: 1 1 auto;
    min-height: 0;
    border-radius: 0;
    border: 0;
    background: #1f1b16;
}

.floorplan-modal.floorplan-modal--fullscreen .floorplan-modal__hint {
    display: none;
}

.floorplan-modal.floorplan-modal--fullscreen .floorplan-modal__status {
    flex-shrink: 0;
    margin: 0;
    padding: 10px 16px;
    font-size: 12px;
    line-height: 1.45;
    font-weight: 400;
    border: 0;
    border-top: 1px solid rgba(0, 0, 0, 0.08);
    border-bottom: 1px solid rgba(0, 0, 0, 0.08);
    background: #edeae3;
    color: #6b6458;
}

.floorplan-modal.floorplan-modal--fullscreen .floorplan-modal__actions {
    flex-shrink: 0;
    margin: 0;
    padding: 12px 24px calc(12px + env(safe-area-inset-bottom, 0px));
    background: #ffffff;
    border-top: 1px solid rgba(0, 0, 0, 0.07);
    box-shadow: 0 -4px 20px rgba(0, 0, 0, 0.06);
    flex-wrap: nowrap;
    gap: 10px;
}

.floorplan-modal.floorplan-modal--fullscreen .floorplan-modal__actions .btn {
    min-height: 44px;
}
.floorplan-gallery__item[data-fss-floorplan-plan-id] {
    cursor: zoom-in;
}

/* FS-specific Layout/capture extras (not in the fire-door floorplan block). */
.fss-lt-sub {
    margin: 0 0 14px;
    font-size: 0.9rem;
    color: var(--text-muted, #6b6458);
}
.floorplan-empty-state { margin-top: 8px; }
.fss-cap-floorplan { display: flex; flex-direction: column; gap: 6px; }
.fss-cap-floorplan-row { display: flex; align-items: center; gap: 10px; flex-wrap: wrap; }
.fss-cap-floorplan-preview { font-size: 0.85rem; color: var(--text-muted, #6b6458); display: inline-flex; align-items: center; gap: 8px; }
.fss-cap-fhint { margin: 0; font-size: 0.82rem; color: var(--text-muted, #6b6458); }
.fss-td-sub--floor { color: var(--text-muted, #6b6458); }

/* --------------------------------------------------------------------------
   Floorplan dark mode — ported 1:1 from the fire-door source
   (inspection_show.css). The floorplan modal markup is a verbatim fork using
   identical bare `.floorplan-*` class names, but the FS fork copied only the
   light rules; without these overrides the modal, tabs, gallery and fullscreen
   stage rendered light-on-light in dark mode. Selectors are intentionally bare
   (the modal is appended to <body>, outside .page-section--fs-survey-show) to
   match the source so behaviour is identical to the fire-door floorplan.
   -------------------------------------------------------------------------- */
html[data-theme="dark"] .floorplan-modal__dialog {
    background: rgba(2, 6, 23, 0.92);
    border: 1px solid rgba(148, 163, 184, 0.22);
    box-shadow: 0 20px 60px rgba(0, 0, 0, 0.65);
}

html[data-theme="dark"] .floorplan-modal__header {
    background: rgba(15, 23, 42, 0.96);
    border-bottom-color: rgba(148, 163, 184, 0.18);
}

html[data-theme="dark"] .floorplan-modal__tabs {
    background: rgba(15, 23, 42, 0.72);
    border-bottom-color: rgba(148, 163, 184, 0.18);
}

html[data-theme="dark"] .floorplan-modal__tabs button {
    background: rgba(15, 23, 42, 0.65);
    border-color: rgba(148, 163, 184, 0.22);
    color: rgba(226, 232, 240, 0.86);
}

html[data-theme="dark"] .floorplan-modal__tabs button.is-active {
    background: var(--button-primary, #1a1815);
    color: #fff;
    border-color: var(--button-primary, #1a1815);
}

html[data-theme="dark"] .floorplan-modal__hint {
    background: rgba(15, 23, 42, 0.55);
    border-top-color: rgba(148, 163, 184, 0.18);
}

html[data-theme="dark"] .floorplan-modal__status {
    background: rgba(15, 23, 42, 0.72);
    border-top-color: rgba(148, 163, 184, 0.18);
}

html[data-theme="dark"] .floorplan-modal__actions {
    background: rgba(2, 6, 23, 0.94);
    border-top-color: rgba(148, 163, 184, 0.18);
}

html[data-theme="dark"] .floorplan-gallery__pill {
    background: rgba(59, 130, 246, 0.16);
    color: #bfdbfe;
}

html[data-theme="dark"] .floorplan-gallery__empty {
    background: rgba(15, 23, 42, 0.6);
    border-color: rgba(148, 163, 184, 0.28);
    color: rgba(148, 163, 184, 0.92);
}

html[data-theme="dark"] .floorplan-gallery__hint,
html[data-theme="dark"] .floorplan-modal__hint,
html[data-theme="dark"] .floorplan-modal__status {
    color: rgba(148, 163, 184, 0.92);
}

/* Fullscreen variant — the FS floorplan modal opens fullscreen. */
html[data-theme="dark"] .floorplan-modal.floorplan-modal--fullscreen,
html[data-theme="dark"] .floorplan-modal.floorplan-modal--fullscreen .floorplan-modal__dialog {
    background: rgba(2, 6, 23, 0.98);
}

html[data-theme="dark"] .floorplan-modal.floorplan-modal--fullscreen .floorplan-modal__header {
    background: rgba(15, 23, 42, 0.96);
    border-bottom-color: rgba(148, 163, 184, 0.18);
    box-shadow: none;
}

html[data-theme="dark"] .floorplan-modal.floorplan-modal--fullscreen .floorplan-modal__header .inspection-modal__eyebrow {
    color: #e8c252;
}

html[data-theme="dark"] .floorplan-modal.floorplan-modal--fullscreen .floorplan-modal__header .inspection-modal__title {
    color: rgba(241, 245, 249, 0.96);
}

html[data-theme="dark"] .floorplan-modal.floorplan-modal--fullscreen .floorplan-modal__header .btn-link {
    color: rgba(226, 232, 240, 0.9);
    background: rgba(15, 23, 42, 0.72);
    border-color: rgba(148, 163, 184, 0.22);
}

html[data-theme="dark"] .floorplan-modal.floorplan-modal--fullscreen .floorplan-modal__tabs {
    background: rgba(15, 23, 42, 0.96);
    border-bottom-color: rgba(148, 163, 184, 0.18);
}

html[data-theme="dark"] .floorplan-modal.floorplan-modal--fullscreen .floorplan-modal__tabs button {
    background: rgba(2, 6, 23, 0.65);
    border-color: rgba(148, 163, 184, 0.22);
    color: rgba(226, 232, 240, 0.88);
}

html[data-theme="dark"] .floorplan-modal.floorplan-modal--fullscreen .floorplan-modal__tabs button.is-active {
    background: var(--button-primary, #1a1815);
    color: #fff;
    border-color: var(--button-primary, #1a1815);
}

html[data-theme="dark"] .floorplan-modal.floorplan-modal--fullscreen .floorplan-modal__stage {
    background: #0f0c09;
}

html[data-theme="dark"] .floorplan-modal.floorplan-modal--fullscreen .floorplan-modal__status {
    background: rgba(15, 23, 42, 0.88);
    color: rgba(203, 213, 225, 0.92);
    border-top-color: rgba(148, 163, 184, 0.16);
    border-bottom-color: rgba(148, 163, 184, 0.16);
}

html[data-theme="dark"] .floorplan-modal.floorplan-modal--fullscreen .floorplan-modal__actions {
    background: rgba(2, 6, 23, 0.96);
    border-top-color: rgba(148, 163, 184, 0.2);
    box-shadow: 0 -4px 24px rgba(0, 0, 0, 0.35);
}

/* ==========================================================================
   QR TAGS — Layout & tags two-column grid + "Tags" column + in-app scanner +
   capture label step. The fire-door tag-card / qr-* CSS is scattered and mostly
   scoped under .page-section--inspection-show (so it doesn't load on FS pages);
   this is a cohesive fork with values matched to the fire-door tag cards.
   ========================================================================== */

/* Two-column grid + mobile Floorplans/Tags subview toggle */
.fss-lt-toggle { display: none; }
.fss-lt-grid {
    display: grid;
    grid-template-columns: minmax(0, 1fr) minmax(0, 1fr);
    gap: 20px;
    align-items: start;
}
@media (max-width: 900px) {
    .fss-lt-toggle {
        display: inline-flex;
        gap: 4px;
        padding: 4px;
        margin-bottom: 14px;
        border-radius: 12px;
        background: var(--surface-muted, #f1ede4);
        border: 1px solid var(--rule, #e6ded0);
    }
    .fss-lt-toggle__btn {
        border: 0;
        background: transparent;
        border-radius: 9px;
        padding: 7px 16px;
        font-size: 0.85rem;
        font-weight: 600;
        color: var(--text-muted, #6b6458);
        cursor: pointer;
    }
    .fss-lt-toggle__btn.is-active {
        background: var(--card, #ffffff);
        color: var(--text, #1a1815);
        box-shadow: 0 1px 3px rgba(15, 23, 42, 0.08);
    }
    .fss-lt-grid { grid-template-columns: 1fr; gap: 0; }
    .fss-lt-grid[data-fss-lt-active="floorplans"] .fss-lt-col--tags { display: none; }
    .fss-lt-grid[data-fss-lt-active="tags"] .fss-lt-col--floorplans { display: none; }
}

/* QR tags toolbar */
.qr-selects { display: flex; flex-wrap: wrap; align-items: center; gap: 10px; margin: 4px 0 14px; }
.qr-select {
    appearance: none;
    border: 1px solid var(--rule, #e6ded0);
    border-radius: 9px;
    padding: 7px 12px;
    background: var(--card, #ffffff);
    color: var(--text, #1a1815);
    font-size: 0.85rem;
    cursor: pointer;
}
.qr-select:focus { outline: 2px solid var(--brand, #c49510); outline-offset: 1px; }

.qr-section-label {
    display: flex;
    justify-content: space-between;
    align-items: baseline;
    gap: 8px;
    margin: 16px 0 8px;
    font-weight: 600;
    font-size: 0.9rem;
    color: var(--text, #1a1815);
}
.qr-count { font-weight: 500; font-size: 0.8rem; color: var(--text-muted, #6b6458); }

/* Tag card (1:1 of the fire-door tag-card) */
.tag-card, .qr-door-card {
    border-radius: 12px;
    padding: 10px 12px;
    background: var(--surface-muted, #f8f6f1);
    border: 1px solid var(--rule, #e6ded0);
    margin-bottom: 8px;
}
.tag-card__row, .qr-dc-top {
    display: flex;
    justify-content: space-between;
    align-items: baseline;
    gap: 8px;
    margin-bottom: 4px;
}
.qr-dc-name { font-weight: 600; color: var(--text, #1a1815); }
.tag-card__status, .qr-dc-tagged {
    font-size: 0.72rem;
    text-transform: uppercase;
    letter-spacing: 0.08em;
    color: var(--text-muted, #6b6458);
}
.tag-card__status--tagged { color: #15803d; }
.tag-card__meta, .qr-dc-meta {
    display: flex;
    flex-wrap: wrap;
    gap: 8px;
    font-size: 0.8rem;
    color: var(--text-muted, #6b6458);
    margin: 0 0 4px;
}
.tag-card__meta code, .qr-dc-meta code {
    font-size: 0.78rem;
    background: rgba(0, 0, 0, 0.05);
    padding: 1px 5px;
    border-radius: 5px;
}
.table-subtext { font-size: 0.78rem; color: var(--text-muted, #6b6458); margin: 0 0 4px; }
.tag-card__actions, .qr-dc-actions {
    margin-top: 6px;
    display: flex;
    flex-wrap: wrap;
    gap: 6px;
    align-items: center;
}
.tag-card__actions form, .qr-dc-actions form { margin: 0; padding: 0; border: 0; background: transparent; box-shadow: none; }
.tag-card__more { position: relative; }
.tag-card__more summary { list-style: none; cursor: pointer; }
.tag-card__more summary::-webkit-details-marker { display: none; }
.tag-card__more-actions { display: flex; flex-wrap: wrap; gap: 6px; margin-top: 6px; }
.tag-card__more-actions form { margin: 0; }

/* Grouped-by-floorplan section */
.tagging-advanced { margin-top: 14px; }
.tagging-advanced > summary {
    cursor: pointer;
    font-weight: 600;
    font-size: 0.9rem;
    color: var(--text, #1a1815);
    list-style: none;
    padding: 6px 0;
}
.tagging-advanced > summary::-webkit-details-marker { display: none; }
.tagging-layout-groups { display: flex; flex-direction: column; gap: 16px; }
.tagging-group__header { margin-bottom: 8px; }
.tagging-group__header h4 { margin: 0; font-size: 0.95rem; }
.tagging-grid { display: flex; flex-direction: column; gap: 8px; }

/* In-app QR scanner modal (stacks above the capture stepper, like the pin modal) */
.fss-scan-modal { position: fixed; inset: 0; z-index: 2500; display: flex; align-items: center; justify-content: center; padding: 24px; }
.fss-scan-modal[hidden] { display: none; }
.fss-scan-modal__overlay { position: absolute; inset: 0; background: rgba(15, 23, 42, 0.6); }
.fss-scan-modal__dialog {
    position: relative;
    width: 100%;
    max-width: 420px;
    background: var(--card, #ffffff);
    border-radius: 18px;
    overflow: hidden;
    box-shadow: 0 28px 80px rgba(25, 19, 9, 0.3);
}
.fss-scan-modal__head { display: flex; justify-content: space-between; align-items: center; padding: 14px 18px; border-bottom: 1px solid var(--rule, #e6ded0); }
.fss-scan-modal__title { margin: 0; font-size: 1rem; }
.fss-scan-modal__stage { background: #0f172a; aspect-ratio: 1 / 1; display: flex; align-items: center; justify-content: center; }
.fss-scan-modal__video { width: 100%; height: 100%; object-fit: cover; }
.fss-scan-modal__status { margin: 0; padding: 12px 18px; font-size: 0.85rem; color: var(--text-muted, #6b6458); }

/* Capture post-save label step */
.fss-cap-labelgen { display: flex; flex-direction: column; align-items: center; gap: 8px; text-align: center; }
.fss-cap-labelgen__hint { margin: 0; font-size: 0.85rem; color: var(--text-muted, #6b6458); }
.fss-cap-labelpreview { display: flex; flex-direction: column; align-items: center; gap: 12px; }
.fss-cap-labelpreview__imgwrap { background: #ffffff; border: 1px solid var(--rule, #e6ded0); border-radius: 12px; padding: 10px; max-width: 280px; }
.fss-cap-labelpreview__imgwrap img { display: block; width: 100%; height: auto; }
.fss-cap-labelpreview__format { display: inline-flex; gap: 6px; }
.fss-cap-labelpreview__format .is-active { background: var(--text, #1a1815); color: #ffffff; }

/* ==========================================================================
   TIMELINE tab — a 1:1 copy of the fire-door inspection _timeline.php. The filter
   strip is the fire-door `.tl-controls` block (NOT the Doors/Penetrations rail):
   an inline `.tl-desktop-controls` bar on desktop (Show + Penetration selects +
   Export CSV) and the `.tl-mobile-rail` + `.tl-controls-panel` drawer on mobile.
   Values mirror inspection_show.css; rules are restated here because the fire-door
   ones are `.page-section--inspection-show`-scoped and never reach this page.
   ========================================================================== */

/* The strip card (white, rounded, soft ring) — matches .tl-controls/.tl-event. */
.page-section--fs-survey-show .tl-controls {
  box-sizing: border-box;
  width: 100%;
  min-width: 0;
  max-width: 100%;
  display: flex;
  align-items: center;
  gap: 8px;
  padding: 12px 20px;
  margin-bottom: 16px;
  background: #ffffff;
  border-radius: 12px;
  border: 0;
  box-shadow: 0 1px 4px rgba(0, 0, 0, 0.06), 0 0 0 1px rgba(0, 0, 0, 0.05);
}
.page-section--fs-survey-show .tl-desktop-controls {
  display: flex;
  align-items: center;
  gap: 8px;
  flex: 1 1 auto;
  min-width: 0;
}
.page-section--fs-survey-show .tl-filter-title { display: none; }
.page-section--fs-survey-show .timeline-filter-form {
  display: flex;
  align-items: center;
  gap: 8px;
  flex-wrap: nowrap;
  margin: 0;
  padding: 0;
  background: transparent;
  border-radius: 0;
}
.page-section--fs-survey-show .tl-filter-label {
  display: flex;
  align-items: center;
  min-width: 0;
  margin: 0;
}
.page-section--fs-survey-show .tl-filter-copy { display: none; }
.page-section--fs-survey-show .tl-filter-select {
  min-width: 138px;
  height: 32px;
  min-height: 32px;
  padding: 0 28px 0 10px;
  border-radius: 7px;
  border: 1px solid rgba(0, 0, 0, 0.11);
  font-size: 12.5px;
  line-height: 1;
  background: #f7f5f0;
  color: #1a1815;
  box-shadow: none;
  cursor: pointer;
}
.page-section--fs-survey-show .tl-controls-right {
  margin-left: auto;
  display: flex;
  align-items: center;
  gap: 8px;
}
.page-section--fs-survey-show .tl-export-btn {
  display: inline-flex;
  align-items: center;
  gap: 6px;
  text-decoration: none;
}
.page-section--fs-survey-show .tl-mobile-rail { display: none; }

/* Desktop keeps the canonical .tnt-filter-drawer (display:contents) from
   unwrapping inline next to the desktop strip — the strip owns the filters. */
@media (min-width: 901px) {
  .page-section--fs-survey-show .tl-controls-panel { display: none !important; }
}

/* ≤900: desktop strip hides, rail shows, drawer becomes the canonical sheet. */
@media (max-width: 900px) {
  .page-section--fs-survey-show .tl-controls {
    display: grid;
    gap: 10px;
    padding: 0;
    margin-bottom: 12px;
    background: transparent;
    border-radius: 0;
    box-shadow: none;
  }
  .page-section--fs-survey-show .tl-desktop-controls { display: none; }
  .page-section--fs-survey-show .tl-mobile-rail { display: flex; }
  .page-section--fs-survey-show .tl-controls-panel .timeline-filter-form {
    display: grid;
    grid-template-columns: minmax(0, 1fr);
    gap: 12px;
  }
  .page-section--fs-survey-show .tl-controls-panel .tl-filter-select {
    width: 100%;
    min-width: 0;
    min-height: 44px;
    height: auto;
    padding: 0 14px;
    border-radius: 12px;
    background: #ffffff;
    box-shadow: 0 1px 4px rgba(0, 0, 0, 0.06), 0 0 0 1px rgba(0, 0, 0, 0.05);
    font-size: 13px;
  }
}

.tl-timeline-wrap { padding: 4px 2px; }
.timeline-empty { margin: 18px 0; text-align: center; font-size: 0.9rem; color: var(--text-muted, #6b6458); }

.tl-date-group { margin-bottom: 16px; }
.tl-date-label {
    display: flex;
    align-items: center;
    gap: 8px;
    padding: 0 0 10px;
    color: var(--text-muted, #9a9188);
    font-size: 10px;
    font-weight: 600;
    letter-spacing: 0.1em;
    text-transform: uppercase;
}
.tl-date-label::after { content: ""; flex: 1; height: 1px; background: rgba(0, 0, 0, 0.07); }
.tl-events { display: flex; flex-direction: column; gap: 8px; }

.tl-event { display: flex; align-items: flex-start; gap: 14px; padding: 14px 18px; border: 0; border-radius: 12px; background: var(--card, #ffffff); box-shadow: 0 1px 4px rgba(0, 0, 0, 0.06), 0 0 0 1px rgba(0, 0, 0, 0.05); }
.tl-icon {
    width: 30px;
    height: 30px;
    border-radius: 50%;
    border: 1px solid rgba(0, 0, 0, 0.11);
    background: #edeae3;
    display: flex;
    align-items: center;
    justify-content: center;
    flex-shrink: 0;
}
.tl-icon.added { background: rgba(30, 122, 69, 0.08); border-color: rgba(30, 122, 69, 0.2); }
.tl-icon.update { background: rgba(37, 99, 168, 0.08); border-color: rgba(37, 99, 168, 0.15); }
.tl-icon svg { width: 13px; height: 13px; color: var(--text-muted, #9a9188); }

.tl-body { min-width: 0; flex: 1 1 auto; }
.tl-top { display: flex; align-items: center; gap: 8px; margin-bottom: 4px; flex-wrap: wrap; }
.tl-time { color: var(--text-muted, #9a9188); font-size: 11.5px; }
.tl-type-chip {
    display: inline-flex;
    align-items: center;
    min-height: 20px;
    padding: 2px 8px;
    border-radius: 5px;
    border: 1px solid rgba(0, 0, 0, 0.11);
    font-size: 10px;
    font-weight: 700;
    letter-spacing: 0.08em;
    text-transform: uppercase;
    white-space: nowrap;
}
.tl-chip-update { background: rgba(37, 99, 168, 0.08); color: #2563a8; border-color: rgba(37, 99, 168, 0.16); }
.tl-chip-added { background: rgba(30, 122, 69, 0.08); color: #1e7a45; border-color: rgba(30, 122, 69, 0.2); }
.tl-desc { margin-bottom: 5px; color: var(--text, #1a1815); font-size: 13px; line-height: 1.5; }
.tl-actor-byline { color: var(--text-muted, #9a9188); }

.tl-attrs { display: flex; gap: 6px; flex-wrap: wrap; margin-top: 8px; }
.tl-attr {
    display: inline-flex;
    align-items: center;
    gap: 4px;
    padding: 2px 8px;
    border-radius: 4px;
    border: 1px solid rgba(0, 0, 0, 0.11);
    background: #edeae3;
    color: #6b6458;
    font-size: 11.5px;
}
.tl-attr__label { font-weight: 400; }
.tl-attr__value { font-weight: 500; }
.tl-attr--status-pass { background: rgba(30, 122, 69, 0.08); color: #1e7a45; border-color: rgba(30, 122, 69, 0.2); }
.tl-attr--status-na { background: #f1f5f9; color: #475569; border-color: rgba(0, 0, 0, 0.11); }
.tl-attr--status-fail,
.tl-attr--status-defective { background: rgba(176, 48, 48, 0.07); color: #b03030; border-color: rgba(176, 48, 48, 0.18); }
.tl-attr--severity-low { background: #edeae3; color: #8f8578; border-color: rgba(0, 0, 0, 0.11); }
.tl-attr--severity-medium { background: rgba(196, 149, 16, 0.08); color: #c49510; border-color: rgba(196, 149, 16, 0.22); }
.tl-attr--severity-high { background: rgba(176, 48, 48, 0.07); color: #b03030; border-color: rgba(176, 48, 48, 0.18); }
.tl-attr--rating { background: #f2efe9; color: #6b6458; border-color: rgba(0, 0, 0, 0.11); }

/* ==========================================================================
   FOLLOW-UP tab — reminder schedule + public PIN. Forked from the fire-door
   fu-* / rem-sched-* / qr-pin-* (inspection-scoped in inspection_show.css), so
   written fresh here with matching values.
   ========================================================================== */

.fu-card { margin-bottom: 16px; }
/* Note colours mirror the fire-door followup: body/footer notes are the faint
   --ink-4 (#9a9188), the role-gate inline note is the darker --ink-2 (#3d3a34),
   the schedule hint stays --ink-3 (#6b6458). */
.fu-body-note { margin: 0 0 12px; font-size: 0.9rem; color: var(--ink-4, #9a9188); }
.fu-footer-note { margin: 12px 0 0; font-size: 0.82rem; color: var(--ink-4, #9a9188); }
.fu-inline-note { font-size: 0.85rem; color: var(--ink-2, #3d3a34); margin-bottom: 10px; }
.fu-sched-note { font-size: 0.82rem; color: var(--ink-3, #6b6458); }

.rem-sched-grid { display: grid; grid-template-columns: repeat(4, minmax(0, 1fr)); gap: 10px; margin: 4px 0 14px; }
.rem-sched-card {
    display: block;
    padding: 13px 15px;
    border-radius: 10px;
    background: var(--surface-muted, #f8f6f1);
    border: 1px solid var(--rule, #e6ded0);
    cursor: pointer;
    position: relative;
}
.rem-sched-card.is-active { border-color: var(--brand, #c49510); box-shadow: 0 0 0 1px var(--brand, #c49510) inset; }
.rem-sched-check { position: absolute; opacity: 0; pointer-events: none; }
.rsc-period { font-weight: 600; font-size: 0.9rem; color: var(--text, #1a1815); }
.rsc-status { margin-top: 4px; font-size: 0.78rem; color: var(--text-muted, #6b6458); }
.rem-sched-footer { display: flex; flex-wrap: wrap; align-items: center; gap: 12px; }
@media (max-width: 900px) { .rem-sched-grid { grid-template-columns: repeat(2, 1fr); } }

.qr-pin-row { display: grid; grid-template-columns: 1fr 1fr; gap: 14px; margin-bottom: 12px; }
.qr-pin-field { display: flex; flex-direction: column; gap: 6px; }
.qr-pin-field--toggle { padding: 12px 14px; border-radius: 10px; background: var(--surface-muted, #f8f6f1); border: 1px solid var(--rule, #e6ded0); }
.qr-pin-toggle { display: inline-flex; align-items: center; gap: 8px; font-size: 13px; color: var(--ink-2, #3d3a34); }
.qr-pin-input { letter-spacing: 0.12em; font-size: 1.1rem; font-weight: 600; }
.reminder-actions { display: flex; flex-wrap: wrap; align-items: center; gap: 12px; }
.fu-pin-reveal-form, .fu-pin-reset-form { margin-top: 12px; padding-top: 12px; border-top: 1px solid var(--rule, #e6ded0); }
.fu-pin-reveal-row { display: flex; flex-wrap: wrap; align-items: center; gap: 8px; margin-top: 6px; }
.qr-pin-reveal-input { min-width: 220px; padding: 7px 10px; border-radius: 8px; border: 1px solid var(--rule, #e6ded0); }
@media (max-width: 900px) { .qr-pin-row { grid-template-columns: 1fr; } }

/* The Follow-up tab was forked 1:1 from the fire-door _followup.php, so its markup
   carries the fire-door card chrome (header divider) + form primitives
   (.f-label / .f-input / .f-hint). Those rules live in inspection_show.css
   (`.page-section--inspection-show`-scoped) so they DON'T reach this page — the
   labels were rendering as plain dark body text and the PIN input as a bare white
   box. Restate them here, scoped to the followup panel (values mirror
   inspection_show.css desktop), so the tab renders 1:1. */
.page-section--fs-survey-show [data-fss-vpanel="followup"] .fss-card-head {
  padding: 14px 20px;
  border-bottom: 1px solid var(--rule, #e6ded0);
}
.page-section--fs-survey-show [data-fss-vpanel="followup"] .fss-card-body {
  padding: 18px 20px;
}
.page-section--fs-survey-show [data-fss-vpanel="followup"] .f-label {
  display: block;
  color: var(--ink-4);
  font-size: 10px;
  font-weight: 600;
  letter-spacing: 0.08em;
  text-transform: uppercase;
}
.page-section--fs-survey-show [data-fss-vpanel="followup"] .f-input {
  width: 100%;
  min-width: 0;
  min-height: 40px;
  padding: 10px 13px;
  border: 1px solid var(--rule-strong);
  border-radius: 9px;
  background: var(--canvas);
  color: var(--ink);
  font-family: var(--font-sans);
  box-sizing: border-box;
  transition: border-color 0.15s ease, box-shadow 0.15s ease;
}
.page-section--fs-survey-show [data-fss-vpanel="followup"] .f-input::placeholder { color: var(--ink-4); }
.page-section--fs-survey-show [data-fss-vpanel="followup"] .f-input:focus {
  outline: none;
  border-color: var(--accent);
  box-shadow: 0 0 0 3px rgba(196, 149, 16, 0.12);
}
.page-section--fs-survey-show [data-fss-vpanel="followup"] .f-hint {
  display: block;
  color: var(--ink-4);
  font-size: 0.78rem;
  line-height: 1.45;
}

/* On mobile the Follow-up card titles switch to the display face, 1:1 with the
   fire-door followup tab (inspection_show.css `[data-tab-panel="followup"]
   .cs-title` → Space Grotesk). Scoped to the followup panel so the other tabs'
   .fss-card-title stays on the body face, exactly as the fire-door does. The
   header divider is dropped on mobile too, matching the fire-door followup. */
@media (max-width: 900px) {
  .page-section--fs-survey-show [data-fss-vpanel="followup"] .fss-card-title {
    font: 700 16px/1.15 var(--font-display, "Space Grotesk", "Inter", sans-serif);
    letter-spacing: -0.02em;
  }
  .page-section--fs-survey-show [data-fss-vpanel="followup"] .fss-card-head {
    padding: 16px 16px 0;
    border-bottom: 0;
  }
  .page-section--fs-survey-show [data-fss-vpanel="followup"] .fss-card-body {
    padding: 16px;
  }
}

/* ==========================================================================
   PDF-job progress UI (Download report)
   Copied verbatim from inspection_show.css so the shared inspection-pdf-job.js
   progress overlay is styled on the FS survey-show page too (this page loads
   its own stylesheet, not inspection_show.css). All tokens are global :root,
   so dark mode + reduced-motion come for free. Keep in sync if the inspection
   job UI markup changes.
   ========================================================================== */
.inspection-pdf-job-host {
    position: fixed;
    right: 22px;
    bottom: 22px;
    z-index: 10000;
    max-width: min(400px, calc(100vw - 44px));
    pointer-events: auto;
    animation: inspection-pdf-job-enter 280ms ease-out;
}

@keyframes inspection-pdf-job-enter {
    from {
        opacity: 0;
        transform: translateY(10px);
    }

    to {
        opacity: 1;
        transform: translateY(0);
    }
}

.inspection-pdf-job {
    padding: 18px 20px 16px;
    border-radius: var(--radius-md);
    background: var(--surface-card);
    border: 1px solid var(--rule-strong);
    box-shadow: var(--shadow-md);
    color: var(--ink);
}

.inspection-pdf-job__eyebrow {
    font-size: 0.65rem;
    font-weight: 700;
    letter-spacing: 0.16em;
    text-transform: uppercase;
    color: var(--ink-4);
    margin: 0 0 6px;
}

.inspection-pdf-job__title {
    margin: 0 0 8px;
    font: 600 1.05rem/1.25 "Space Grotesk", "Inter", sans-serif;
    letter-spacing: -0.02em;
    color: var(--ink);
}

.inspection-pdf-job__sub {
    margin: 0 0 14px;
    font-size: 0.8125rem;
    line-height: 1.45;
    color: var(--ink-3);
    font-weight: 500;
}

.inspection-pdf-job__sub--hint {
    margin-top: -8px;
    color: var(--ink-4);
    font-size: 0.78rem;
}

.inspection-pdf-job__track {
    position: relative;
    height: 6px;
    border-radius: 999px;
    background: var(--surface-inset);
    overflow: hidden;
    margin-bottom: 10px;
}

.inspection-pdf-job__bar-fill {
    height: 100%;
    border-radius: 999px;
    background: linear-gradient(90deg, var(--info), color-mix(in srgb, var(--info) 70%, #ffffff));
    transition: width 160ms ease-out;
}

.inspection-pdf-job__track--success .inspection-pdf-job__bar-fill {
    background: linear-gradient(90deg, var(--success), color-mix(in srgb, var(--success) 70%, #ffffff));
}

.inspection-pdf-job__bar-indet {
    position: absolute;
    inset: 0;
    width: 40%;
    border-radius: 999px;
    background: linear-gradient(90deg, transparent, color-mix(in srgb, var(--info) 55%, transparent), var(--info));
    animation: inspection-pdf-job-indet 1.1s ease-in-out infinite;
}

.inspection-pdf-job__track--success .inspection-pdf-job__bar-indet {
    display: none !important;
}

@keyframes inspection-pdf-job-indet {
    0% {
        transform: translateX(-100%);
    }

    100% {
        transform: translateX(350%);
    }
}

.inspection-pdf-job__meta {
    margin: 0;
    font-size: 0.75rem;
    font-weight: 600;
    color: var(--ink-4);
    font-variant-numeric: tabular-nums;
}

.inspection-pdf-job__footer--error {
    margin-top: 4px;
}

.inspection-pdf-job__errmsg {
    margin: 0 0 12px;
    font-size: 0.8125rem;
    line-height: 1.45;
    color: var(--danger);
    font-weight: 500;
}

html[data-theme="dark"] .inspection-pdf-job {
    background: #0f172a;
    border-color: rgba(148, 163, 184, 0.24);
    color: #f1f5f9;
    box-shadow: 0 18px 48px rgba(0, 0, 0, 0.45);
}

html[data-theme="dark"] .inspection-pdf-job__eyebrow,
html[data-theme="dark"] .inspection-pdf-job__sub--hint,
html[data-theme="dark"] .inspection-pdf-job__meta {
    color: rgba(148, 163, 184, 0.85);
}

html[data-theme="dark"] .inspection-pdf-job__title {
    color: #f1f5f9;
}

html[data-theme="dark"] .inspection-pdf-job__sub {
    color: rgba(226, 232, 240, 0.82);
}

html[data-theme="dark"] .inspection-pdf-job__track {
    background: rgba(148, 163, 184, 0.18);
}

html[data-theme="dark"] .inspection-pdf-job__errmsg {
    color: #fca5a5;
}

@media (prefers-reduced-motion: reduce) {
    .inspection-pdf-job-host {
        animation: none;
    }

    .inspection-pdf-job__bar-indet {
        animation: none;
        width: 100%;
        opacity: 0.35;
        transform: none;
    }

    .inspection-pdf-job__bar-fill {
        transition: none;
    }
}

@media (max-width: 1024px) {
    .inspection-pdf-job-host {
        right: 16px;
        left: 16px;
        bottom: calc(env(safe-area-inset-bottom, 0px) + 108px);
        max-width: none;
    }
}

/* ============================================================================
   Per-penetration reports modal (fss-irm-*) — penetration picker + output mode.
   A forked 1:1 of the fire-door irm-* set (inspection_show.css), with the FS
   status palette (pass / fail / defective / na). Paired with
   show/_reports_modal.php + initFsReportsModal() in fire-stopping-surveys.js.
   ========================================================================== */
.fss-reports-modal .fss-modal__dialog { max-width: min(560px, calc(100vw - 32px)); }

.fss-irm-toolbar { display: flex; align-items: center; justify-content: space-between; gap: 10px; flex-wrap: wrap; margin-bottom: 12px; }
.fss-irm-toolbar__quick { display: flex; gap: 6px; flex-wrap: wrap; }
.fss-irm-count { font-size: 12px; font-weight: 600; color: var(--ink-3); white-space: nowrap; }

.fss-irm-list { list-style: none; margin: 0 0 16px; padding: 6px; display: flex; flex-direction: column; gap: 4px; max-height: 320px; overflow-y: auto; background: var(--surface-inset); border: 1px solid var(--rule); border-radius: var(--radius-sm); }
.fss-irm-item { margin: 0; }
.fss-irm-row { display: flex; align-items: center; gap: 10px; padding: 9px 10px; border-radius: 7px; background: var(--surface-card); border: 1px solid var(--rule); cursor: pointer; }
.fss-irm-row:hover { border-color: var(--accent); }
.fss-irm-row__label { flex: 1 1 auto; min-width: 0; font-size: 13.5px; font-weight: 500; color: var(--ink); overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.fss-irm-row input[type="checkbox"] { width: 17px; height: 17px; flex: 0 0 auto; accent-color: var(--accent); }
.fss-irm-chip { flex: 0 0 auto; font-size: 10px; font-weight: 700; letter-spacing: 0.04em; padding: 2px 7px; border-radius: 5px; }
.fss-irm-chip--pass { background: rgba(30, 122, 69, 0.1); color: var(--success); }
.fss-irm-chip--fail,
.fss-irm-chip--defective { background: rgba(176, 48, 48, 0.1); color: var(--danger); }
.fss-irm-chip--na { background: var(--surface-inset); color: var(--ink-4); }

.fss-irm-mode { border: 0; margin: 0; padding: 0; display: flex; flex-direction: column; gap: 8px; }
.fss-irm-mode > legend { padding: 0; margin-bottom: 8px; }
.fss-irm-mode__opt { display: flex; gap: 10px; align-items: flex-start; padding: 11px 12px; border: 1px solid var(--rule); border-radius: 9px; background: var(--surface-card); cursor: pointer; }
.fss-irm-mode__opt:hover { border-color: var(--accent); }
.fss-irm-mode__opt input { margin-top: 2px; flex: 0 0 auto; accent-color: var(--accent); }
.fss-irm-mode__copy { display: flex; flex-direction: column; gap: 2px; }
.fss-irm-mode__copy strong { font-size: 13.5px; color: var(--ink); }
.fss-irm-mode__copy small { font-size: 11.5px; color: var(--ink-3); line-height: 1.4; }

.fss-irm-submit-spinner { display: none; width: 14px; height: 14px; margin-left: 8px; border: 2px solid currentColor; border-right-color: transparent; border-radius: 50%; animation: fss-irm-spin 0.6s linear infinite; vertical-align: -2px; }
[data-fss-irm-submit].is-loading .fss-irm-submit-spinner { display: inline-block; }
[data-fss-irm-submit].is-loading { opacity: 0.85; pointer-events: none; }
@keyframes fss-irm-spin { to { transform: rotate(360deg); } }

.fss-pen-detail__report-link { font-size: 12px; font-weight: 600; color: var(--accent-strong); text-decoration: none; }
.fss-pen-detail__report-link:hover { text-decoration: underline; }

html[data-theme="dark"] .fss-irm-list { background: rgba(2, 6, 23, 0.42); border-color: rgba(148, 163, 184, 0.22); }
html[data-theme="dark"] .fss-irm-row,
html[data-theme="dark"] .fss-irm-mode__opt { background: rgba(15, 23, 42, 0.55); border-color: rgba(148, 163, 184, 0.22); }
html[data-theme="dark"] .fss-irm-chip--na { background: rgba(148, 163, 184, 0.14); }
