/* ============================================================
   UR E27 — App styles (Stratos)
   Maritime cybersecurity ops console — light only
   ============================================================ */

* { box-sizing: border-box; }

html, body {
  margin: 0; padding: 0; height: 100%;
  background: var(--bg-app);
  color: var(--fg-1);
  font-family: var(--font-sans);
  /* 지시서 §3.1 — 본문 12.5px 기준. 옛 14px 는 정보 밀도를 떨어뜨렸다 */
  font-size: 12.5px;
  letter-spacing: var(--tracking);
  -webkit-font-smoothing: antialiased;
  -moz-osx-font-smoothing: grayscale;
}

a { color: var(--brand-500); text-decoration: none; }
a:hover { color: var(--brand-700); text-decoration: underline; }

button { font-family: inherit; letter-spacing: inherit; }
input, select, textarea { font-family: inherit; letter-spacing: inherit; }

/* Scrollbars */
::-webkit-scrollbar { width: 10px; height: 10px; }
::-webkit-scrollbar-track { background: transparent; }
::-webkit-scrollbar-thumb {
  background: #c9cfd6;
  border-radius: 6px;
  border: 3px solid transparent;
  background-clip: content-box;
}
::-webkit-scrollbar-thumb:hover { background: var(--gray-400); }

::selection { background: var(--brand-100); color: var(--fg-1); }
*:focus-visible { outline: 2px solid var(--brand-500); outline-offset: 2px; border-radius: var(--r-sm); }

/* ============================================================
   전역 셸 — 좌측 내비 246px + 헤더 56px (REDESIGN-SPEC §2)
   상단 탭 9개는 없앴다. 내비게이션이 두 겹이면 "지금 어디인가"가 흐려진다.
   ============================================================ */
.app-shell {
  display: grid;
  grid-template-columns: var(--nav-w) minmax(0, 1fr);
  height: 100vh;
}

/* ---------- 좌측 내비 ---------- */
.nav {
  display: flex; flex-direction: column;
  background: var(--nav-bg);
  color: #cfd8e0;
  min-height: 0;
}
.nav-brand {
  display: flex; align-items: center; gap: 10px;
  padding: 18px 18px 16px;
  border-bottom: 1px solid rgba(255,255,255,.08);
}
.nav-brand-badge {
  flex: 0 0 auto;
  display: inline-flex; align-items: center; justify-content: center;
  width: 30px; height: 30px; border-radius: 7px;
  background: rgba(255,255,255,.10);
  color: #f2f6fa; font-size: 11px; font-weight: 600; letter-spacing: 0;
}
.nav-brand-text { display: flex; flex-direction: column; gap: 1px; min-width: 0; }
.nav-brand-name {
  font-size: 13px; font-weight: 600; color: #f2f6fa; letter-spacing: -0.01em;
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.nav-brand-sub { font-size: 10.5px; color: #8698a8; }

/* 그룹 라벨 — 모노 대문자 (지시서 §3.1) */
.nav-group-label {
  font-size: 9.5px; letter-spacing: .14em; text-transform: uppercase;
  color: #61717f; padding: 14px 8px 6px;
}

/* ACTIVE PROJECT 스위처 */
.nav-switch-wrap { padding: 0 10px; }
.nav-switch-wrap .nav-group-label { padding: 12px 4px 6px; color: #6f8090; }
.nav-switch { position: relative; }
.nav-switch-card {
  display: flex; align-items: center; gap: 9px;
  padding: 9px 10px; border-radius: 8px; cursor: pointer;
  background: rgba(255,255,255,.06);
  border: 1px solid rgba(255,255,255,.08);
  list-style: none;
}
.nav-switch-card::-webkit-details-marker { display: none; }
.nav-switch-card:hover { background: rgba(255,255,255,.10); }
.nav-switch-dot {
  flex: 0 0 8px; width: 8px; height: 8px; border-radius: 50%;
  background: #5c6874;
}
.nav-switch-dot.is-active { background: var(--warn-500); }
.nav-switch-text { display: flex; flex-direction: column; gap: 2px; min-width: 0; flex: 1; }
.nav-switch-code { font-size: 10px; color: #93a5b5; }
.nav-switch-name {
  font-size: 12.5px; font-weight: 600; color: #e8eef4;
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.nav-switch-chev { color: #7a8b9b; display: flex; }
.nav-switch[open] .nav-switch-chev { transform: rotate(180deg); }
.nav-switch-menu {
  position: absolute; left: 0; right: 0; top: calc(100% + 4px); z-index: 30;
  background: #14232f;
  border: 1px solid rgba(255,255,255,.12);
  border-radius: 8px;
  box-shadow: 0 12px 40px rgba(0,0,0,.45);
  padding: 4px; display: flex; flex-direction: column; gap: 2px;
  max-height: 300px; overflow-y: auto;
}
.nav-switch-item {
  display: flex; align-items: center; gap: 8px;
  padding: 7px 9px; border-radius: 6px;
  color: #cfd8e0; font-size: 12px; text-decoration: none;
}
.nav-switch-item:hover { background: rgba(255,255,255,.10); color: #fff; text-decoration: none; }
.nav-switch-item.is-current { background: rgba(255,255,255,.14); color: #fff; font-weight: 600; }
.nav-switch-item .mono { font-size: 10px; color: #93a5b5; flex: 0 0 auto; }
.nav-switch-item-name { min-width: 0; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.nav-switch-item-st { font-size: 9.5px; color: #7a8b9b; margin-left: auto; }
.nav-switch-item.is-manage { border-top: 1px solid rgba(255,255,255,.08); margin-top: 2px; padding-top: 9px; color: #93a5b5; }

/* 메뉴 항목 — 2자 모노 키 / 라벨 / 카운트 */
.nav-menu {
  flex: 1; min-height: 0; overflow-y: auto;
  padding: 4px 10px 10px;
  display: flex; flex-direction: column; gap: 2px;
}
.nav-item {
  display: flex; align-items: center; gap: 9px;
  padding: 7px 9px; border-radius: 7px;
  color: #b9c5d0; font-size: 12.5px; font-weight: 500;
  text-decoration: none;
}
.nav-item:hover { background: rgba(255,255,255,.07); color: #eaf0f6; text-decoration: none; }
.nav-item.is-active { background: rgba(255,255,255,.12); color: #ffffff; font-weight: 600; }
.nav-item-key {
  flex: 0 0 auto; width: 20px;
  font-size: 9.5px; letter-spacing: .06em; color: #6f8090;
}
.nav-item.is-active .nav-item-key { color: #a8bccd; }
.nav-item-label { min-width: 0; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.nav-item-count {
  margin-left: auto; flex: 0 0 auto;
  font-size: 10px; color: #8698a8;
  background: rgba(255,255,255,.07);
  border-radius: 999px; padding: 1px 6px;
}
.nav-item-count.is-warn { color: #f0cd85; background: rgba(224,165,48,.16); }
.nav-item.is-active .nav-item-count { color: #dbe6ef; background: rgba(255,255,255,.14); }

/* 하단 사용자 */
.nav-user {
  border-top: 1px solid rgba(255,255,255,.08);
  padding: 12px 14px;
  display: flex; align-items: center; gap: 10px;
}
.nav-user-avatar {
  flex: 0 0 auto;
  display: inline-flex; align-items: center; justify-content: center;
  width: 28px; height: 28px; border-radius: 50%;
  background: rgba(255,255,255,.12);
  color: #eaf0f6; font-size: 12px; font-weight: 600;
}
.nav-user-text { display: flex; flex-direction: column; min-width: 0; flex: 1; }
.nav-user-name {
  font-size: 12px; font-weight: 500; color: #eaf0f6;
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.nav-user-role { font-size: 9.5px; letter-spacing: .1em; color: #7a8b9b; text-transform: uppercase; }
.nav-user-out {
  border: 1px solid rgba(255,255,255,.14); background: transparent;
  color: #b9c5d0; font-size: 10.5px; border-radius: 6px;
  padding: 4px 8px; cursor: pointer;
}
.nav-user-out:hover { background: rgba(255,255,255,.10); color: #fff; }

/* ---------- 본문 ---------- */
.main {
  display: flex; flex-direction: column;
  min-width: 0; min-height: 0;
  background: var(--bg-app);
}

/* ---------- 헤더 56px ---------- */
.hdr {
  height: var(--topbar-h); flex: 0 0 var(--topbar-h);
  display: flex; align-items: center; gap: 16px;
  padding: 0 22px;
  background: var(--bg-card);
  border-bottom: 1px solid var(--border-1);
}
.hdr-crumb {
  display: flex; align-items: center; gap: 8px;
  font-size: 12.5px; color: var(--fg-3); min-width: 0;
}
.hdr-crumb-code {
  font-size: 10.5px; font-weight: 600; color: var(--fg-2);
  background: var(--bg-subtle); border: 1px solid var(--border-1);
  border-radius: 5px; padding: 2px 6px;
}
.hdr-crumb-proj { white-space: nowrap; overflow: hidden; text-overflow: ellipsis; max-width: 240px; }
.hdr-crumb-sep { color: var(--fg-5); }
.hdr-crumb-cur { color: var(--fg-1); font-weight: 600; white-space: nowrap; }
.hdr-right { margin-left: auto; display: flex; align-items: center; gap: 10px; }
.hdr-chip {
  display: inline-flex; align-items: center; gap: 6px;
  height: 30px; padding: 0 10px;
  background: var(--warn-50); border: 1px solid var(--warn-100);
  border-radius: 7px; color: var(--warn-700);
  font-size: 11.5px; font-weight: 500; text-decoration: none;
}
.hdr-chip:hover { text-decoration: none; }
.hdr-chip .mono { color: var(--warn-700); font-size: 10.5px; }
.hdr-chip-d { font-weight: 600; }
.hdr-search {
  display: flex; align-items: center; gap: 8px;
  width: 320px; padding: 7px 11px;
  border-radius: 8px; background: var(--bg-chrome);
  border: 1px solid var(--border-1);
  color: var(--fg-4);
}
.hdr-search:focus-within { border-color: var(--brand-500); background: var(--bg-card); }
.hdr-search input {
  flex: 1; min-width: 0; border: 0; outline: 0; background: transparent;
  font-size: 12px; color: var(--fg-1);
}
.hdr-search input::placeholder { color: var(--fg-4); }
.hdr-search-kbd {
  font-size: 10px; color: var(--fg-4);
  border: 1px solid var(--border-2); border-radius: 4px; padding: 1px 4px;
}

/* ---------- 페이지 캔버스 ---------- */
.page-canvas {
  flex: 1; min-height: 0; overflow-y: auto;
  padding: 26px 26px 40px;
  display: flex; flex-direction: column; gap: 18px;
}

/* 페이지 머리 (화면 제목 행) */
.page-head { display: flex; align-items: flex-start; gap: 24px; }
.page-head-main { display: flex; flex-direction: column; gap: 7px; min-width: 0; }
.page-head-actions { margin-left: auto; display: flex; gap: 8px; flex: 0 0 auto; }
.page-title-row { display: flex; align-items: center; gap: 10px; }
.page-title { margin: 0; font-size: 21px; font-weight: 600; color: var(--fg-1); letter-spacing: -0.012em; line-height: 1.25; }
.page-subtitle { font-size: 12.5px; color: var(--fg-3); }
.page-meta { display: flex; align-items: center; gap: 14px; font-size: 12.5px; color: var(--fg-3); flex-wrap: wrap; }

/* 인쇄 문서 (리포트) — 셸 없이 종이처럼 */
.print-page { max-width: 1140px; margin: 0 auto; padding: 30px 26px 60px; background: var(--bg-card); min-height: 100vh; }

/* ============================================================
   Cards
   ============================================================ */
.card {
  background: var(--bg-card);
  border: 1px solid var(--border-1);
  border-radius: var(--r-xl);
  padding: 15px 18px;
  display: flex; flex-direction: column; gap: 12px;
  min-width: 0;
}
.card-tight { padding: 12px 14px; }
.card-flush { padding: 0; overflow: hidden; gap: 0; }
/* 카드 머리 — 제목 13.5px/600 (지시서 §3.1) */
.card-head, .card-header {
  display: flex; align-items: center; justify-content: space-between;
  gap: var(--sp-4); margin: 0;
}
.card-title { margin: 0; font-size: 13.5px; font-weight: 600; color: var(--fg-1); letter-spacing: -0.005em; }
.card-sub, .card-subtitle { margin: 0; font-size: 11.5px; color: var(--fg-3); font-weight: 400; }

.stripe-accent {
  background: var(--bg-card);
  border: 1px solid var(--border-1);
  border-left: 3px solid var(--accent-500);
  border-radius: var(--r-md);
  padding: var(--sp-4) var(--sp-5);
}
.info-card {
  background: var(--brand-50);
  border: 1px solid var(--brand-100);
  border-radius: var(--r-md);
  padding: var(--sp-4) var(--sp-5);
}

/* ============================================================
   Table
   ============================================================ */
.tbl {
  width: 100%;
  border-collapse: collapse;
  font-size: 13px;
  letter-spacing: var(--tracking);
  background: var(--bg-card);
  border: 1px solid var(--border-1);
  border-radius: var(--r-xl);
  overflow: hidden;
}
.tbl thead th {
  background: var(--bg-app);
  font-family: var(--font-mono);
  font-size: 9.5px; font-weight: 500;
  letter-spacing: .1em; text-transform: uppercase;
  color: var(--fg-3);
  text-align: left;
  padding: 8px 12px;
  border-bottom: 1px solid var(--border-1);
  white-space: nowrap;
}
.tbl thead th:first-child { padding-left: 20px; }
.tbl thead th:last-child  { padding-right: 20px; }
.tbl tbody td {
  padding: 9px 12px;
  border-bottom: 1px solid var(--gray-100);
  font-size: 12px;
  color: var(--fg-1);
  vertical-align: middle;
}
.tbl tbody td:first-child { padding-left: 20px; }
.tbl tbody td:last-child  { padding-right: 20px; }
.tbl tbody tr:last-child td { border-bottom: 0; }
/* bg-hover(gray-50)는 흰 배경에서 사실상 보이지 않았다 → gray-100 */
.tbl tbody tr:hover td { background: var(--bg-app); }
.tbl tbody tr.is-selected td { background: var(--accent-50); }
/* 스트라이프는 행 왼쪽에 한 번만. td 전체에 inset 을 걸면 모든 열 사이에 줄이 생긴다(기존 버그) */
.tbl tbody tr.is-selected td:first-child { box-shadow: inset 3px 0 0 var(--accent-500); }

/* 주의가 필요한 행 강조 — 근거 미비/기한 초과처럼 "이 행을 처리해야 한다"는 신호.
   상태 배지(행 안의 값)와 다른 축이다. 행 배경은 아주 옅게, 신호는 좌측 스트라이프로. */
.tbl tbody tr.row-flag td { background: var(--danger-50); }
.tbl tbody tr.row-flag td:first-child { box-shadow: inset 3px 0 0 var(--danger-500); }
.tbl tbody tr.row-flag:hover td { background: var(--danger-100); }
.tbl tbody tr.row-warn td { background: var(--warn-50); }
.tbl tbody tr.row-warn td:first-child { box-shadow: inset 3px 0 0 var(--warn-500); }

.tbl .cell-meta { color: var(--fg-3); font-weight: 500; font-size: 12px; }
.tbl .cell-mono { font-family: var(--font-mono); font-variant-numeric: tabular-nums; font-size: 12px; letter-spacing: 0; }
.tbl .cell-bold { font-weight: 700; }
.tbl .cell-ref  { font-family: var(--font-mono); font-size: 12px; font-weight: 600; color: var(--brand-500); letter-spacing: 0; }

/* ============================================================
   Layout helpers
   ============================================================ */
.row { display: flex; align-items: center; }
.row-gap-1 { gap: 4px; } .row-gap-2 { gap: 8px; } .row-gap-3 { gap: 12px; } .row-gap-4 { gap: 16px; }
.col { display: flex; flex-direction: column; }
.col-gap-1 { gap: 4px; } .col-gap-2 { gap: 8px; } .col-gap-3 { gap: 12px; } .col-gap-4 { gap: 16px; } .col-gap-6 { gap: 24px; }
.spacer { flex: 1; }
.grid { display: grid; gap: 16px; }
/* 그리드 — `1fr` 은 minmax(auto,1fr) 이라 콘텐츠가 트랙을 부풀린다(캔버스·표에서 실제로 겪었다).
   전부 minmax(0,1fr) 로 잡아 트랙이 줄어들 수 있게 한다. */
.grid-2  { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: 14px; }
.grid-3  { display: grid; grid-template-columns: repeat(3, minmax(0, 1fr)); gap: 14px; }
.grid-4  { display: grid; grid-template-columns: repeat(4, minmax(0, 1fr)); gap: 14px; }
.grid-23 { display: grid; grid-template-columns: minmax(0, 2fr) minmax(0, 1fr); gap: 14px; }
.grid-115 { display: grid; grid-template-columns: minmax(0, 1.15fr) minmax(0, 1fr); gap: 14px; }
.mt-1 { margin-top: 4px; } .mt-2 { margin-top: 8px; } .mt-3 { margin-top: 12px; } .mt-4 { margin-top: 16px; } .mt-6 { margin-top: 24px; }
.mb-1 { margin-bottom: 4px; } .mb-2 { margin-bottom: 8px; } .mb-3 { margin-bottom: 12px; } .mb-4 { margin-bottom: 16px; }
.wrap { flex-wrap: wrap; }

/* ============================================================
   Button
   ============================================================ */
.btn {
  display: inline-flex; align-items: center; justify-content: center;
  gap: 6px; height: 32px; padding: 0 13px;
  border-radius: var(--r-md);
  font-size: 12px; font-weight: 600;
  letter-spacing: var(--tracking);
  cursor: pointer;
  white-space: nowrap;
  border: 1px solid var(--border-2);
  background: var(--bg-card);
  color: var(--fg-1);
  transition: background 100ms ease, border-color 100ms ease;
  text-decoration: none;
}
.btn:hover { background: var(--bg-subtle); border-color: var(--brand-500); color: var(--brand-500); text-decoration: none; }
.btn:disabled { opacity: 0.5; cursor: not-allowed; }
.btn.primary       { background: var(--brand-500); color: #fff; border-color: var(--brand-500); }
.btn.primary:hover { background: var(--brand-700); border-color: var(--brand-700); color: #fff; }
/* accent = primary 와 같은 잉크다. 별도 액센트색을 쓰지 않는다(지시서 §3.2) */
.btn.accent        { background: var(--brand-500); color: #fff; border-color: var(--brand-500); }
.btn.accent:hover  { background: var(--brand-700); border-color: var(--brand-700); color: #fff; }
.btn.ghost         { background: transparent; border-color: transparent; color: var(--fg-2); }
.btn.ghost:hover   { background: var(--bg-subtle); color: var(--fg-1); }
.btn.danger        { background: var(--bg-card); color: var(--danger-500); border-color: var(--danger-100); }
.btn.danger:hover  { background: var(--danger-50); border-color: var(--danger-100); color: var(--danger-500); }
.btn.primary-soft  { background: var(--brand-50); color: var(--brand-500); border-color: var(--brand-100); }
.btn.primary-soft:hover { background: var(--brand-100); }
.btn.sm  { height: 26px; padding: 0 9px; font-size: 11.5px; }
.btn.lg  { height: 40px; padding: 0 18px; font-size: 14px; }
.btn.icon-only { width: 32px; padding: 0; }

/* ============================================================
   Inputs
   ============================================================ */
.input, .select, .textarea, input[type=text], input[type=number], input[type=password],
input[type=email], input[type=search], select, textarea {
  width: 100%;
  background: var(--bg-card);
  border: 1px solid var(--border-2);
  border-radius: var(--r-md);
  padding: 0 12px; height: 34px;
  color: var(--fg-1);
  font-size: 13px; font-weight: 500;
  letter-spacing: var(--tracking);
  transition: border-color 120ms ease, box-shadow 120ms ease;
  outline: none;
}
.input:focus, input[type=text]:focus, input[type=number]:focus, input[type=search]:focus,
select:focus, textarea:focus {
  border-color: var(--accent-500);
  box-shadow: 0 0 0 3px rgba(14,165,233,.12);
}
textarea {
  height: auto; min-height: 80px; padding: 10px 12px;
  resize: vertical; line-height: 1.5;
}
.field { display: block; margin-bottom: 12px; }
.field > span {
  display: block;
  font-family: var(--font-mono);
  font-size: 9.5px; font-weight: 500;
  color: var(--fg-3);
  text-transform: uppercase;
  letter-spacing: 0.1em;
  margin-bottom: 5px;
}

/* ============================================================
   Badges / pills
   ============================================================ */
.badge {
  display: inline-flex; align-items: center; gap: 6px;
  padding: 3px 10px;
  border-radius: var(--r-sm);
  font-size: 12px; font-weight: 700;
  background: var(--bg-subtle); color: var(--fg-2);
  border: 1px solid var(--border-1);
  white-space: nowrap;
}
.badge-sm { padding: 2px 8px; font-size: 11px; }
.badge .dot { width: 7px; height: 7px; border-radius: 50%; flex-shrink: 0; }

/* Status — 4 tier */
.status-badge { display: inline-flex; align-items: center; gap: 5px;
  padding: 2px 9px; border-radius: var(--r-pill);
  font-size: 10.5px; font-weight: 600;
  background: var(--neutral-50); color: var(--neutral-700);
  border: 1px solid transparent; white-space: nowrap;
}
.status-badge .dot { width: 7px; height: 7px; border-radius: 50%; flex-shrink: 0; }
.status-ok          { background: var(--ok-50);     color: var(--ok-700); border: 1px solid var(--ok-100); }
.status-ok .dot     { background: var(--ok-500); }
.status-prog        { background: var(--warn-50);   color: var(--warn-700); border: 1px solid var(--warn-200); }
.status-prog .dot   { background: var(--warn-500); }
.status-gap         { background: var(--danger-50); color: var(--danger-700); border: 1px solid var(--danger-100); }
.status-gap .dot    { background: var(--danger-500); }
.status-na          { background: var(--bg-subtle); color: var(--fg-3); border: 1px solid var(--border-1); }
.status-na .dot     { background: var(--fg-4); }

/* Map our internal statuses to those tiers */
.status-compliant    { background: var(--ok-50);     color: var(--ok-700); border-color: var(--ok-100); }
.status-compliant .dot { background: var(--ok-500); }
.status-partial      { background: var(--warn-50);   color: var(--warn-700); border-color: var(--warn-200); }
.status-partial .dot { background: var(--warn-500); }
.status-non_compliant { background: var(--danger-50); color: var(--danger-700); border-color: var(--danger-100); }
.status-non_compliant .dot { background: var(--danger-500); }
.status-pending      { background: var(--bg-subtle); color: var(--fg-3); border-color: var(--border-1); }
.status-pending .dot { background: var(--fg-4); }
.status-badge.status-na .dot { background: var(--fg-4); }

/* ADR-0025: pending(미평가)과 na(해당 없음)이 완전히 같은 회색 배지로 렌더돼 구분이 안 됐다.
   둘은 반대되는 정보다 — pending 은 "아직 안 한 일", na 는 "할 일이 아님".
   새 색을 만들지 않고 형태로 가른다: pending = 점선 테두리 + 빈 원(미결),  na = 실선 + 대시(해당 없음). */
.status-badge.status-pending {
  background: var(--bg-card); color: var(--fg-2);
  border: 1px dashed var(--border-2);
}
.status-badge.status-pending .dot {
  background: transparent;
  box-shadow: inset 0 0 0 1.5px var(--fg-4);
}
.status-badge.status-na .dot {
  width: 9px; height: 3px; border-radius: 1px;
  background: var(--fg-4);
}

/* Risk */
.risk-badge { display: inline-flex; align-items: center; gap: 6px;
  padding: 3px 10px; border-radius: var(--r-sm);
  font-size: 11px; font-weight: 700; letter-spacing: 0.04em;
  text-transform: uppercase;
  border: 1px solid var(--border-1);
}
.risk-low    { background: var(--ok-50);     color: var(--ok-700); border-color: var(--ok-100); }
.risk-medium { background: var(--warn-50);   color: var(--warn-700); border-color: var(--warn-200); }
.risk-high   { background: var(--danger-50); color: var(--danger-700); border-color: var(--danger-100); }

/* Security Profile (SP0~SP4) */
.sp-badge {
  display: inline-flex; align-items: center;
  padding: 0 7px; height: 20px;
  border-radius: var(--r-xs);
  font-family: var(--font-mono);
  font-size: 11px; font-weight: 700; letter-spacing: 0.02em;
  white-space: nowrap;
  border: 1px solid;
}
.sp-badge.sp-0 { background: var(--gray-100); color: var(--gray-500); border-color: var(--gray-300); }
.sp-badge.sp-1 { background: var(--accent-50); color: var(--accent-700); border-color: var(--accent-200); }
.sp-badge.sp-2 { background: var(--accent-500); color: #fff; border-color: var(--accent-500); }
.sp-badge.sp-3 { background: var(--accent-600); color: #fff; border-color: var(--accent-600); }
.sp-badge.sp-4 { background: var(--brand-500); color: #fff; border-color: var(--brand-500); }

/* Generic pill */
/* 상태 pill — radius 999px, 10–11px (지시서 §3.3) */
.pill {
  display: inline-flex; align-items: center; gap: 5px;
  padding: 2px 9px;
  border-radius: var(--r-pill);
  font-size: 10.5px; font-weight: 600;
  background: var(--neutral-50); color: var(--neutral-700);
  border: 1px solid transparent;
  white-space: nowrap;
}
.pill.pill-brand   { background: var(--brand-50);   color: var(--brand-500); border-color: var(--brand-100); }
.pill.pill-accent  { background: var(--accent-50);  color: var(--accent-700); border-color: var(--accent-100); }
.pill.pill-ok      { background: var(--ok-50);      color: var(--ok-700); border-color: var(--ok-100); }
.pill.pill-warn    { background: var(--warn-50);    color: var(--warn-700); border-color: var(--warn-200); }
.pill.pill-danger  { background: var(--danger-50);  color: var(--danger-700); border-color: var(--danger-100); }
.pill.pill-outline { background: var(--bg-card);    color: var(--fg-2); border-color: var(--border-2); }
.pill.mono { font-family: var(--font-mono); letter-spacing: 0; }

/* FR tag */
.fr-tag {
  display: inline-block; font-family: var(--font-mono);
  font-size: 10px; font-weight: 500; color: var(--fg-3);
  background: var(--bg-subtle); border: 1px solid var(--border-1);
  border-radius: 4px; padding: 1px 5px; white-space: nowrap;
}

/* CSF tags */
.csf-tag {
  display: inline-flex; padding: 2px 8px; border-radius: var(--r-sm);
  font-size: 11px; font-weight: 700; margin-right: 4px;
  font-family: var(--font-mono); letter-spacing: 0;
  border: 1px solid;
}
.csf-tag.csf-Identify { background: var(--csf-identify-bg); color: var(--csf-identify); border-color: var(--csf-identify-br); }
.csf-tag.csf-Protect  { background: var(--accent-50); color: var(--accent-700); border-color: var(--accent-100); }
.csf-tag.csf-Detect   { background: var(--csf-detect-bg); color: var(--csf-detect); border-color: var(--csf-detect-br); }
.csf-tag.csf-Respond  { background: var(--warn-50); color: var(--warn-700); border-color: var(--warn-200); }
.csf-tag.csf-Recover  { background: var(--ok-50); color: var(--ok-700); border-color: var(--ok-100); }

/* ============================================================
   KPI tile
   ============================================================ */
/* ADR-0024: .kpi 가 두 번 정의돼 있었다(여기 + Work queue 블록). 정의는 여기 하나로 두고,
   구형 API(.label/.value/.sub — report·certifications·gap_analysis)와
   신형 API(.kpi-label/.kpi-value/.kpi-sub — dashboard)를 같은 규격으로 묶는다. */
.kpi {
  background: var(--bg-card);
  border: 1px solid var(--border-1);
  border-radius: var(--r-xl);
  padding: 14px 16px 16px;
  display: flex; flex-direction: column;
  /* bar 가 없는 타일과 있는 타일의 높이를 맞춘다 */
  min-height: 108px;
  position: relative; overflow: hidden;
}
.kpi-accent::before {
  content: ''; position: absolute; top: 0; left: 0; right: 0; height: 2px;
  background: var(--accent-500);
}
.kpi .label, .kpi-label {
  font-size: 11px; font-weight: 700;
  text-transform: uppercase; letter-spacing: 0.05em;
  color: var(--fg-3);
  display: flex; align-items: center; gap: 6px;
}
.kpi .value, .kpi-value {
  font-family: var(--font-mono);
  font-size: 30px; font-weight: 700;
  line-height: 1.05; letter-spacing: -0.02em;
  color: var(--fg-1);
  font-variant-numeric: tabular-nums;
  margin-top: 8px;
}
.kpi .unit, .kpi-value .unit { font-size: 14px; font-weight: 600; color: var(--fg-3); margin-left: 2px; }
.kpi .sub, .kpi-sub { font-size: 12px; color: var(--fg-3); margin-top: 5px; }
/* 숫자와 보조설명 사이를 밀어내서 타일들의 기준선이 맞는다 */
.kpi .sub, .kpi-sub { margin-top: auto; padding-top: 6px; }

/* Progress bar */
.progress { width: 100%; height: 4px; background: #eef1f4;
  border-radius: 3px; overflow: hidden;
}
.progress > span { display: block; height: 100%;
  background: var(--accent-500);
  border-radius: var(--r-pill);
  transition: width 400ms ease-out; }
.progress.ok    > span { background: var(--ok-500); }
.progress.warn  > span { background: var(--warn-500); }
.progress.brand > span { background: var(--brand-500); }

/* ============================================================
   Compliance Matrix (cell dots)
   ============================================================ */
.matrix-wrap { overflow-x: auto;
  border-radius: var(--r-xl);
  border: 1px solid var(--border-1);
  background: var(--bg-card);
}
table.matrix { border-collapse: collapse; width: 100%; }
table.matrix th, table.matrix td {
  padding: 11px 12px;
  border-bottom: 1px solid var(--border-1);
  white-space: nowrap;
  font-size: 12px;
  line-height: 1.5;
}
table.matrix thead th {
  background: var(--bg-subtle);
  font-size: 11px; font-weight: 700;
  letter-spacing: 0.05em;
  text-transform: uppercase;
  color: var(--fg-2);
  border-bottom: 1px solid var(--border-2);
  /* th 기본값이 center 라서 헤더는 가운데, 셀은 왼쪽으로 어긋나 있었다.
     열 정렬은 헤더와 셀이 같아야 한다 → 기본 left, 가운데 정렬 열만 .col-center/.doc 로 지정. */
  text-align: left;
  /* 2줄 헤더(S001 §절 / DNV-RU-SHIP)와 1줄 헤더의 밑선을 맞춘다 */
  vertical-align: bottom;
  /* 41행을 스크롤하는 동안 열 머리(S001~S006)가 보여야 셀을 읽을 수 있다.
     오프셋은 topbar + tabbar. .matrix-wrap 이 스크롤 컨테이너가 아니라 페이지가 스크롤될 때 대비. */
  position: sticky; top: 0; z-index: 2;
}
table.matrix td.req { white-space: normal; min-width: 300px; }
table.matrix th.doc, table.matrix td.doc,
table.matrix th.col-center, table.matrix td.col-center { text-align: center; }
/* 긴 텍스트 열: nowrap 이면 내용이 열 폭을 강제로 벌려 앞 열들이 눌린다 → 줄바꿈 허용 */
table.matrix th.col-wrap, table.matrix td.col-wrap { white-space: normal; line-height: 1.4; }
table.matrix tr:hover td { background: var(--gray-100); cursor: pointer; }
/* 산출물 열 경계 — 6개 doc 열이 어디서 시작하는지 보이게 (커버리지 점만 있으면 정렬이 안 읽힌다) */
table.matrix th.doc-first, table.matrix td.doc-first { border-left: 1px solid var(--border-2); }
/* 미매핑(빈칸)은 이 제품에서 가장 중요한 정보다 — 조용하지만 "없음"으로 읽혀야 한다 (H2).
   .cell-dot 과 같은 14px 자리를 차지해서 열 정렬이 유지되고, 빈칸처럼 사라지지 않는다.
   범례에서도 같은 클래스를 쓰므로 테이블 밖에서도 유효해야 한다. */
.cov-none {
  display: inline-block; width: 14px; text-align: center;
  font-family: var(--font-mono); font-weight: 700;
  color: var(--fg-3);
  cursor: help;
}
table.matrix tr.fr-divider td {
  background: var(--brand-50) !important;
  font-weight: 700; padding: 8px 14px;
  border-top: 1px solid var(--brand-100);
  border-bottom: 1px solid var(--brand-100);
}
/* ADR-0026: 커버리지 3단계는 상태(4단계)와 다른 축이다. 기존에는 셋 다 "꽉 찬 원"이고
   색만 달라서(green/amber/gray) 상태 배지의 색과 구별되지 않았다.
   → 채움 정도(form)로 서열을 인코딩한다: full=꽉 참 / partial=아래 절반 / referenced=테두리만.
   색은 보조 신호로 남고, 흑백 인쇄와 색약 환경에서도 서열이 읽힌다. */
.cell-dot { display: inline-block; width: 14px; height: 14px;
  border-radius: 50%; border: 1.5px solid var(--border-2);
  background: transparent; vertical-align: middle; }
.cell-dot.full       { background: var(--ok-500);   border-color: var(--ok-500); }
.cell-dot.partial    { background: var(--warn-50);  border-color: var(--warn-500);
                       box-shadow: inset 0 -5px 0 var(--warn-500); }
.cell-dot.referenced { background: transparent;     border-color: var(--fg-4); }

.dot-cs { color: var(--ok-500); font-size: 18px; line-height: 1; }

/* ============================================================
   Filters bar
   ============================================================ */
.filters { display: flex; gap: 10px; flex-wrap: wrap; align-items: center; margin-bottom: 16px; }
.filters input[type=text], .filters select { max-width: 240px; }

/* ============================================================
   Requirement detail layout
   ============================================================ */
.detail-layout {
  display: grid;
  grid-template-columns: minmax(0, 1.4fr) minmax(280px, 0.9fr);
  gap: 16px;
  align-items: flex-start;
}
@media (max-width: 1100px) {
  .detail-layout { grid-template-columns: 1fr; }
}
.req-section-title { font-size: 17px; font-weight: 700; color: var(--fg-1); margin-top: 6px; }
.req-standards-line {
  font-family: var(--font-mono);
  color: var(--brand-500); font-size: 12px; font-weight: 700;
  margin: 4px 0 14px;
  letter-spacing: 0;
}
.req-shall {
  margin: 0 0 16px;
  padding: 14px 16px;
  background: var(--brand-50);
  border-left: 3px solid var(--brand-500);
  border-radius: 0 var(--r-md) var(--r-md) 0;
  color: var(--fg-1);
  line-height: 1.6;
  font-size: 14px;
  font-weight: 500;
  white-space: pre-wrap;
}
.std-ref { width: 100%; font-size: 13px; }
.std-ref td { padding: 7px 10px; border-bottom: 1px solid var(--border-1); }
.std-ref td:first-child { color: var(--fg-3); width: 220px; font-weight: 600; }
.std-ref tr:last-child td { border-bottom: 0; }
.desc-block {
  background: var(--bg-subtle);
  border: 1px solid var(--border-1);
  border-radius: var(--r-md);
  padding: 14px 16px;
  white-space: pre-wrap; font-family: inherit;
  color: var(--fg-1); font-size: 13px; line-height: 1.6;
}
.impl-textarea { min-height: 220px; font-family: inherit; line-height: 1.6; }

/* ============================================================
   Attachments
   ============================================================ */
.upload-drop {
  display: flex; flex-direction: column; align-items: center; justify-content: center;
  gap: 6px; padding: 22px;
  border: 1.5px dashed var(--border-2);
  border-radius: var(--r-md);
  background: var(--bg-subtle);
  cursor: pointer;
  transition: border-color .15s, background .15s;
}
.upload-drop:hover, .upload-drop.drag { border-color: var(--accent-500); background: var(--accent-50); }
.upload-drop .upload-ico { font-size: 22px; color: var(--accent-500); line-height: 1; font-weight: 700; }
.att-grid { display: grid; gap: 14px;
  grid-template-columns: repeat(auto-fill, minmax(220px, 1fr)); margin-top: 8px; }
.att-card { margin: 0; background: var(--bg-card);
  border: 1px solid var(--border-1); border-radius: var(--r-md);
  overflow: hidden; display: flex; flex-direction: column; }
.att-card a { display: block; background: var(--gray-100); }
.att-card img { display: block; width: 100%; height: 180px; object-fit: contain;
  background: var(--gray-100); transition: transform .2s; }
.att-card:hover img { transform: scale(1.02); }
.att-card figcaption { padding: 8px 10px 10px; display: flex; flex-direction: column; gap: 4px; }
.att-card figcaption input { font-size: 12px; padding: 5px 8px; height: 30px; }
.att-meta { font-size: 11px; color: var(--fg-3); display: flex; gap: 4px; flex-wrap: wrap; }

/* ============================================================
   Network topology canvas (Cytoscape)
   ============================================================ */
.cy-canvas {
  height: 680px;
  background: var(--bg-card);
  border: 1px solid var(--border-1);
  border-radius: var(--r-xl);
  position: relative; overflow: hidden;
  background-image:
    linear-gradient(var(--gray-100) 1px, transparent 1px),
    linear-gradient(90deg, var(--gray-100) 1px, transparent 1px);
  background-size: 32px 32px;
  background-position: -1px -1px;
}
.cy-tip {
  position: absolute; pointer-events: none; display: none;
  background: var(--bg-card);
  border: 1px solid var(--border-2); color: var(--fg-1);
  padding: 8px 10px; border-radius: var(--r-md);
  font-size: 12px; line-height: 1.4;
  box-shadow: var(--shadow-pop);
  z-index: 1000; max-width: 280px;
}
.legend-line { display: inline-block; width: 26px; height: 3px; border-radius: 2px; vertical-align: middle; }
.legend-line.legend-dashed { background-image: repeating-linear-gradient(90deg, currentColor 0 6px, transparent 6px 12px) !important; background-color: transparent !important; }
.legend-box { display: inline-block; width: 12px; height: 8px; border-radius: 2px; vertical-align: middle; }
.link-pill { display: inline-block; padding: 2px 8px; border-radius: var(--r-sm); font-size: 11px;
  font-weight: 700; border: 1px solid; font-family: var(--font-mono); letter-spacing: 0; }

/* ============================================================
   Status dot indicator
   ============================================================ */
.status-dot {
  display: inline-block; width: 8px; height: 8px; border-radius: 50%; flex-shrink: 0;
}
.status-dot.s-ok    { background: var(--ok-500);    box-shadow: 0 0 0 3px rgba(16, 185, 129, 0.12); }
.status-dot.s-prog  { background: var(--warn-500);  box-shadow: 0 0 0 3px rgba(245, 158, 11, 0.12); }
.status-dot.s-gap   { background: var(--danger-500);box-shadow: 0 0 0 3px rgba(225, 29, 72, 0.12); }
.status-dot.s-na    { background: var(--fg-4); }

/* ============================================================
   Certification status (선급별 진행현황)
   ============================================================ */
.cert-grid {
  display: grid;
  grid-template-columns: repeat(auto-fill, minmax(340px, 1fr));
  gap: 16px;
}
.cert-card {
  background: var(--bg-card);
  border: 1px solid var(--border-1);
  border-radius: var(--r-xl);
  overflow: hidden;
  text-decoration: none;
  color: var(--fg-1);
  display: flex;
  flex-direction: column;
  transition: border-color 120ms ease, transform 120ms ease, box-shadow 120ms ease;
}
.cert-card:hover {
  border-color: var(--border-strong);
  text-decoration: none;
  box-shadow: var(--shadow-md);
  transform: translateY(-1px);
}
.cert-stripe { height: 4px; }
.cert-card-body { padding: 18px 18px 20px; }
.cert-code {
  font-family: var(--font-mono);
  font-size: 22px; font-weight: 700; line-height: 1;
  letter-spacing: 0.02em;
}

/* Stage strip (6 dots) */
.stage-strip {
  display: flex; align-items: center; gap: 0;
  padding: 4px 0;
}
.stage-dot {
  width: 26px; height: 26px;
  border-radius: 50%;
  border: 1.5px solid var(--border-2);
  background: var(--bg-card);
  color: var(--fg-3);
  font-family: var(--font-mono);
  font-size: 11px; font-weight: 700;
  display: inline-flex; align-items: center; justify-content: center;
  flex-shrink: 0;
}
.stage-dot.stage-completed   { background: var(--ok-500);     border-color: var(--ok-500);     color: #fff; }
.stage-dot.stage-in_progress { background: var(--warn-500);   border-color: var(--warn-500);   color: #fff;
  box-shadow: 0 0 0 3px rgba(245,158,11,.18); }
.stage-dot.stage-skipped     { background: var(--bg-subtle);  border-color: var(--border-1);   color: var(--fg-4); }
.stage-dot.stage-pending     {}

.stage-link {
  flex: 1; height: 2px;
  background: var(--border-1);
}
.stage-link.stage-link-on { background: var(--ok-500); }

/* Mini "current stage" indicator inside cards */
.cert-meta {
  display: grid; grid-template-columns: minmax(0, 1fr) minmax(0, 1.4fr);
  gap: 14px;
  padding-top: 14px;
  border-top: 1px solid var(--border-1);
}

/* Big society mark on detail page */
.cert-mark {
  display: inline-flex; align-items: center; justify-content: center;
  height: 26px; padding: 0 9px; border-radius: 6px;
  font-family: var(--font-mono); font-size: 12px; font-weight: 600; color: #fff;
}

/* Timeline */
.timeline { display: flex; flex-direction: column; }
.timeline-item {
  border-bottom: 1px solid var(--border-1);
}
.timeline-item:last-child { border-bottom: 0; }
.timeline-item > summary { list-style: none; cursor: pointer; }
.timeline-item > summary::-webkit-details-marker { display: none; }
.timeline-summary {
  display: flex; align-items: center; gap: 14px;
  padding: 12px 4px;
  transition: background 100ms ease;
}
.timeline-item:hover .timeline-summary { background: var(--bg-hover); }
.timeline-marker {
  width: 34px; height: 34px;
  border-radius: 50%;
  border: 2px solid var(--border-2);
  background: var(--bg-card);
  color: var(--fg-3);
  font-family: var(--font-mono);
  font-size: 13px; font-weight: 700;
  display: inline-flex; align-items: center; justify-content: center;
  flex-shrink: 0;
}
.timeline-marker.stage-completed   { background: var(--ok-500);   border-color: var(--ok-500);   color: #fff; }
.timeline-marker.stage-in_progress { background: var(--warn-500); border-color: var(--warn-500); color: #fff;
  box-shadow: 0 0 0 4px rgba(245,158,11,.18); }
.timeline-marker.stage-skipped     { background: var(--bg-subtle);                                color: var(--fg-4); }
.timeline-chev {
  transition: transform 120ms ease;
}
.timeline-item[open] .timeline-chev { transform: rotate(180deg); }
.timeline-body {
  padding: 8px 4px 22px 52px;
}

/* Stage status badges — internal pending/in_progress/completed/skipped */
.stage-status-pending     { background: var(--bg-subtle); color: var(--fg-3); border: 1px solid var(--border-1); }
.stage-status-pending .dot{ background: var(--fg-4); }
.stage-status-in_progress { background: var(--warn-50); color: var(--warn-700); border: 1px solid var(--warn-200); }
.stage-status-in_progress .dot{ background: var(--warn-500); }
.stage-status-completed   { background: var(--ok-50); color: var(--ok-700); border: 1px solid var(--ok-100); }
.stage-status-completed .dot{ background: var(--ok-500); }
.stage-status-skipped     { background: var(--bg-subtle); color: var(--fg-4); border: 1px solid var(--border-1); }
.stage-status-skipped .dot{ background: var(--fg-4); }

/* Cert evidence drop — slightly tighter than the requirement one */
.cert-drop { padding: 18px; }

/* ============================================================
   Animations
   ============================================================ */
@keyframes fade-in {
  from { opacity: 0; transform: translateY(2px); }
  to   { opacity: 1; transform: translateY(0); }
}
.page-fade { animation: fade-in 200ms ease-out; }

/* ============================================================
   Project switcher (ADR-0005) · Export actions · Work queue (ADR-0006)
   ============================================================ */
.proj-switch { margin-top: 14px; }
.proj-switch > summary { margin-top: 0; cursor: pointer; list-style: none; }
.proj-switch > summary::-webkit-details-marker { display: none; }
.proj-switch > summary:hover { border-color: var(--accent-400); }
.proj-switch[open] .proj-caret { transform: rotate(180deg); }
.proj-caret { transition: transform 120ms ease-out; flex-shrink: 0; }

.proj-menu {
  margin-top: 4px; padding: 4px;
  background: var(--bg-card);
  border: 1px solid var(--border-1);
  border-radius: var(--r-md);
  box-shadow: var(--shadow-md);
  display: flex; flex-direction: column; gap: 1px;
}
.proj-menu form { margin: 0; }
.proj-item {
  width: 100%; display: flex; align-items: center; gap: 8px;
  padding: 7px 8px; border: 0; border-radius: var(--r-sm);
  background: transparent; cursor: pointer; text-align: left;
  font-family: var(--font-sans); font-size: 12px; color: var(--fg-2);
}
.proj-item:hover { background: var(--bg-subtle); color: var(--fg-1); }
.proj-item.is-current { background: var(--brand-50); color: var(--brand-500); font-weight: 700; }
.proj-item-code { font-size: 10px; font-weight: 700; color: var(--accent-600); flex-shrink: 0; }
.proj-item-name { flex: 1; min-width: 0; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.proj-item-status {
  font-size: 9px; font-weight: 700; text-transform: uppercase; letter-spacing: 0.04em;
  color: var(--fg-4); background: var(--bg-subtle);
  padding: 1px 5px; border-radius: var(--r-xs); flex-shrink: 0;
}
.proj-manage {
  display: block; padding: 7px 8px; margin-top: 2px;
  border-top: 1px solid var(--border-1);
  font-size: 11px; font-weight: 600; color: var(--accent-600);
}
.proj-manage:hover { text-decoration: none; background: var(--bg-subtle); }

.audit-chip.is-empty {
  background: var(--bg-subtle); border-color: var(--border-1); color: var(--fg-3);
}
.audit-chip:hover { text-decoration: none; filter: brightness(0.98); }

.export-actions { display: inline-flex; gap: 6px; }
.btn-export {
  display: inline-flex; align-items: center; gap: 6px;
  height: 32px; padding: 0 12px;
  border: 1px solid var(--border-2); border-radius: var(--r-md);
  background: var(--bg-card); color: var(--fg-2);
  font-size: 12px; font-weight: 600;
}
.btn-export:hover { text-decoration: none; background: var(--bg-hover); color: var(--brand-500); border-color: var(--accent-400); }
.btn-export .icon { color: var(--fg-4); }

/* ---- KPI pair: claimed vs evidenced (ADR-0006 ⑤) ----
   .kpi 본체 정의는 위 "KPI tile" 섹션 하나로 통합했다 (ADR-0024). 여기는 변형만 둔다. */
.kpi-row { display: grid; grid-template-columns: repeat(auto-fit, minmax(190px, 1fr)); gap: var(--sp-4); }
.kpi-bar { margin-top: 10px; height: 6px; border-radius: var(--r-pill); background: var(--gray-200); overflow: hidden; }
.kpi-bar > span { display: block; height: 100%; border-radius: var(--r-pill); transition: width 400ms ease-out; }
/* bar 가 있으면 sub 를 bar 바로 아래로 (auto margin 해제) */
.kpi-bar + .kpi-sub { margin-top: 6px; padding-top: 0; }

/* 주장 ↔ 근거확보는 "한 쌍"으로 읽혀야 한다 (ADR-0006 ⑤). 상단 2px 마크로 짝을 표시하고
   색은 claimed=시안(주장) / evidenced=녹색(확보)으로 갈라 차이를 눈에 보이게 한다. */
.kpi--claimed, .kpi--evidenced { position: relative; }
.kpi--claimed::before, .kpi--evidenced::before {
  content: ''; position: absolute; top: 0; left: 0; right: 0; height: 2px;
}
.kpi--claimed::before   { background: var(--accent-400); }
.kpi--evidenced::before { background: var(--ok-500); }
.kpi--claimed .kpi-bar > span   { background: var(--accent-400); }
.kpi--evidenced .kpi-bar > span { background: var(--ok-500); }
.kpi--risk { border-color: var(--danger-100); background: var(--danger-50); }
.kpi--risk .kpi-value { color: var(--danger-500); }
.kpi--risk .kpi-label { color: var(--danger-700); }
.kpi--risk .kpi-bar { background: var(--danger-100); }
.kpi--risk .kpi-bar > span { background: var(--danger-500); }

/* ---- Deadline rail ---- */
.rail { display: flex; flex-direction: column; }
.rail-row {
  display: grid; grid-template-columns: 60px minmax(0,1fr) auto auto; align-items: center; gap: 12px;
  padding: 10px var(--sp-5); border-top: 1px solid var(--border-1);
}
.rail-row:hover { background: var(--gray-100); }
/* D-day 는 식별자가 아니라 "긴급도"다 → 보더를 줘서 배지처럼 읽히게 하고 폭을 고정한다 */
.dday {
  display: inline-flex; align-items: center; justify-content: center;
  font-family: var(--font-mono); font-size: 10.5px; font-weight: 600;
  padding: 2px 7px; border-radius: 999px;
  background: var(--neutral-50); color: var(--neutral-700);
  border: 1px solid transparent; white-space: nowrap;
}
.dday.is-soon { background: var(--warn-50); color: var(--warn-700); border-color: var(--warn-200); }
.dday.is-over { background: var(--danger-50); color: var(--danger-700); border-color: var(--danger-100); }

/* ---- Work queue (근거 미비) ---- */
.wq { display: flex; flex-direction: column; }
.wq-row {
  display: grid; grid-template-columns: minmax(0,1fr) auto; align-items: start; gap: 12px;
  padding: 11px var(--sp-5); border-top: 1px solid var(--border-1);
}
/* "정상 상태는 조용해야 한다" — 처리 끝난 큐는 실제로 물러나야 한다.
   기존에는 .wq-title 이 color:fg-1 을 직접 걸어 .is-clean 이 무력화됐다 (버그) */
.wq-row.is-clean .wq-title { color: var(--fg-3); font-weight: 500; }
.wq-row.is-clean .wq-why   { color: var(--fg-4); }
.wq-row.is-clean .wq-count { background: var(--bg-subtle); color: var(--fg-4); border-color: var(--border-1); }
.wq-title { font-size: 13px; font-weight: 600; color: var(--fg-1); }
.wq-why { font-size: 11px; color: var(--fg-3); margin-top: 2px; line-height: 1.45; }
.wq-count {
  font-family: var(--font-mono); font-size: 15px; font-weight: 700;
  padding: 2px 10px; border-radius: var(--r-sm);
  border: 1px solid transparent;
  min-width: 44px; text-align: center;
  font-variant-numeric: tabular-nums;
}
.wq-count.is-bad  { background: var(--danger-50); color: var(--danger-700); border-color: var(--danger-100); }
.wq-count.is-warn { background: var(--warn-50); color: var(--warn-700); border-color: var(--warn-200); }
.wq-count.is-ok   { background: var(--bg-subtle); color: var(--fg-4); border-color: var(--border-1); }
.wq-chips { display: flex; flex-wrap: wrap; gap: 4px; margin-top: 6px; }
.wq-chip {
  font-family: var(--font-mono); font-size: 10px; font-weight: 600;
  padding: 2px 6px; border-radius: var(--r-xs);
  background: var(--bg-subtle); border: 1px solid var(--border-1); color: var(--fg-2);
}
.wq-chip:hover { text-decoration: none; border-color: var(--accent-400); color: var(--accent-600); }

/* ---- Project cards ---- */
.proj-grid { display: grid; grid-template-columns: repeat(auto-fill, minmax(330px, 1fr)); gap: 14px; }
.proj-card { position: relative; display: flex; flex-direction: column; gap: 10px; }
.proj-card.is-current { border-color: var(--brand-400); box-shadow: inset 3px 0 0 var(--brand-500); }
.proj-card-head { display: flex; align-items: flex-start; gap: 10px; }
.proj-card-code {
  font-family: var(--font-mono); font-size: 10.5px; font-weight: 600;
  color: #fff; background: var(--brand-500);
  padding: 3px 8px; border-radius: var(--r-sm); flex-shrink: 0;
}
.proj-card-name { font-size: 13.5px; font-weight: 600; color: var(--fg-1); line-height: 1.35; }
.proj-card-meta { font-size: 11px; color: var(--fg-3); margin-top: 2px; }
.proj-card-kpis { display: grid; grid-template-columns: repeat(3, 1fr); gap: 8px; }
.proj-mini { background: var(--bg-subtle); border: 1px solid var(--border-1); border-radius: 7px; padding: 8px 10px; }
.proj-mini-label { font-family: var(--font-mono); font-size: 9px; font-weight: 500; text-transform: uppercase; letter-spacing: 0.1em; color: var(--fg-3); }
.proj-mini-value { font-family: var(--font-mono); font-size: 17px; font-weight: 600; color: var(--brand-500); margin-top: 2px; }
.proj-mini-value.is-bad { color: var(--danger-500); }

/* ============================================================
   Auth pages (login / setup) — B-026
   ============================================================ */
.auth-shell {
  min-height: 100vh; display: flex; align-items: center; justify-content: center;
  padding: var(--sp-6); background: var(--bg-app);
}
.auth-card {
  width: 100%; max-width: 420px;
  background: var(--bg-card); border: 1px solid var(--border-1);
  border-radius: var(--r-xl); padding: var(--sp-8);
  box-shadow: var(--shadow-lg);
}
.auth-brand { display: flex; align-items: center; gap: 10px; }
.auth-error {
  background: var(--danger-50); border: 1px solid var(--danger-100); color: var(--danger-700);
  border-radius: var(--r-md); padding: 10px 12px; font-size: 13px; font-weight: 600;
  margin-bottom: var(--sp-4);
}

/* ------------------------------------------------------------
   로그인 분할 레이아웃 — commission-platform 의 SplitAuthLayout 이식
   좌: 브랜드 패널(사진 + 그라디언트 3겹) / 우: 흰 카드 430px
   ------------------------------------------------------------ */
.auth-body { background: var(--bg-app); }
.auth-split {
  display: flex; min-height: 100vh; padding: 24px; gap: 24px;
  background: var(--bg-app);
}

/* ---- 좌: 브랜드 패널 ---- */
.auth-brandpanel {
  position: relative; flex: 1 1 0; min-width: 0; overflow: hidden;
  border-radius: 22px;
  /* 이미지 여백과 같은 톤 — cover 로 잘려도 경계가 보이지 않게 */
  background: #0a1017;
  display: flex; flex-direction: column; justify-content: space-between;
  padding: 40px 0 60px; color: #fafaff; isolation: isolate;
}
/* 금색 실드가 이 이미지의 주제다 — **채도를 죽이지 않는다.**
   이전 이미지에 걸었던 luminosity 블렌드 + 브랜드 색 wash 를 빼고 원본 색으로 둔다.
   세로 이미지라 Y 를 22% 로 올려 주제를 위로 보내고 좌하단(텍스트 자리)을 비운다. */
.auth-bg {
  position: absolute; inset: 0; width: 100%; height: 100%;
  object-fit: cover; object-position: 62% 22%;
  z-index: -2;
}
/* 가독성 — 텍스트가 앉는 좌하단만 덮는다. 그림 전체를 어둡게 하지 않는다. */
.auth-bg-grad {
  position: absolute; inset: 0; z-index: -1;
  background:
    /* 하단 띠는 세게 덮는다 — 원본 아래쪽의 단계 아이콘·대시보드 조각이
       불릿 3줄 뒤에서 잡티처럼 보였다 */
    linear-gradient(to top,
      rgba(5, 10, 16, .96) 0%, rgba(5, 10, 16, .93) 20%,
      rgba(5, 10, 16, .58) 38%, rgba(5, 10, 16, .12) 58%, rgba(5, 10, 16, 0) 70%),
    linear-gradient(to right,
      rgba(5, 10, 16, .60) 0%, rgba(5, 10, 16, .16) 42%, rgba(5, 10, 16, 0) 70%);
}
.auth-panel-top { padding: 0 40px; }
.auth-panel-body { padding: 0 40px; display: flex; flex-direction: column; gap: 34px; }
.auth-headline {
  margin: 0; font-size: 38px; line-height: 1.22; font-weight: 600;
  letter-spacing: -0.025em; color: #fafaff;
  text-shadow: 0 1px 18px rgba(8, 20, 34, .35);
}
.auth-bullets { list-style: none; margin: 0; padding: 0; display: flex; flex-direction: column; gap: 16px; }
.auth-bullets li { display: flex; align-items: center; gap: 14px; }
/* 아이콘 타일 — 이미지의 금색 실드와 같은 재질을 노린다.
   평평한 반투명 사각형은 싸구려로 보인다. 세 겹을 쓴다:
     1) 대각 금색 그라디언트 채움  2) `::before` 로 그린 그라디언트 **테두리**
        (단색 border 는 아래쪽이 뜬다 — 위는 밝고 아래는 사라져야 금속처럼 보인다)
     3) 위쪽 하이라이트 + 아래 그림자 로 두께를 준다 */
.auth-bullet-ico {
  position: relative; flex: 0 0 auto; width: 48px; height: 48px; border-radius: 13px;
  display: inline-flex; align-items: center; justify-content: center;
  background:
    linear-gradient(152deg, rgba(233, 191, 128, .22) 0%, rgba(233, 191, 128, .07) 52%,
                            rgba(255, 255, 255, .02) 100%);
  color: #eec793;
  box-shadow: inset 0 1px 0 rgba(255, 255, 255, .12), 0 8px 20px rgba(0, 0, 0, .38);
  backdrop-filter: blur(3px);
}
.auth-bullet-ico::before {
  content: ""; position: absolute; inset: 0; border-radius: inherit; padding: 1px;
  background: linear-gradient(152deg, rgba(244, 209, 154, .62) 0%, rgba(244, 209, 154, .16) 48%,
                                      rgba(244, 209, 154, .04) 100%);
  -webkit-mask: linear-gradient(#000 0 0) content-box, linear-gradient(#000 0 0);
          mask: linear-gradient(#000 0 0) content-box, linear-gradient(#000 0 0);
  -webkit-mask-composite: xor; mask-composite: exclude;
  pointer-events: none;
}
.auth-bullet-ico svg { position: relative; filter: drop-shadow(0 0 7px rgba(233, 180, 105, .30)); }
.auth-bullet-text {
  font-size: 14.5px; font-weight: 500; color: rgba(250, 250, 255, .92);
  letter-spacing: -0.005em;
}

/* ---- enious 워드마크 ---- */
.enious-logo { display: inline-flex; align-items: center; gap: 9px; color: inherit; }
.enious-logo svg { flex: none; }
.enious-word {
  font-size: 26px; font-weight: 700; letter-spacing: -0.04em; line-height: 1;
  color: currentColor;
}

/* ---- 우: 인증 카드 ---- */
.auth-pane {
  flex: 0 0 46%; max-width: 640px; min-width: 0;
  display: flex; align-items: center; justify-content: center;
}
.auth-pane-inner {
  width: 100%; max-width: 430px;
  display: flex; flex-direction: column; align-items: center; gap: 22px;
}
.auth-pane-logo { color: var(--brand-500); }
.auth-pane-logo .enious-word { font-size: 28px; }
.auth-pane .auth-card {
  width: 100%; max-width: 430px;
  border-radius: 18px; padding: 32px 40px 40px;
  box-shadow: 0 18px 44px rgba(16, 26, 36, .10);
}
.auth-card-title {
  margin: 0 0 24px; font-size: 21px; font-weight: 600; letter-spacing: -0.015em; color: var(--fg-1);
}
/* 문구를 걷어내 제목·입력·버튼만 남았다 → 제목은 가운데(사용자 지시).
   **입력 라벨과 값은 왼쪽 그대로다** — 폼 필드를 가운데 정렬하면 읽는 눈이 줄마다 흔들린다. */
.auth-card.is-centered .auth-card-title { text-align: center; }
.auth-form { display: flex; flex-direction: column; gap: 14px; }
.auth-form .field { margin: 0; }
.auth-submit { width: 100%; justify-content: center; height: 42px; margin-top: 6px; }
.auth-foot {
  margin: 0; font-size: 11px; font-weight: 500; letter-spacing: .02em; color: var(--fg-4);
}

@media (max-width: 1080px) {
  /* 좁은 화면에서는 브랜드 패널을 접는다 — 로그인은 입력이 우선이다 */
  .auth-split { padding: 16px; gap: 0; }
  .auth-brandpanel { display: none; }
  .auth-pane { flex: 1 1 auto; max-width: none; }
}


/* ============================================================
   IA 재편 v2 — Projects 목록 + 프로젝트 워크스페이스 탭
   ADR-0020: chrome 3층 구조 (흰 topbar → 톤 밴드 → 회색 캔버스)
   ============================================================ */

/* ---- 사이드바: 프로젝트 목록 ---- */
/* 프로젝트가 많아도 사이드바가 뷰포트를 넘지 않게 이 영역만 스크롤한다 (1366×768) */
.sidebar-top { display: flex; flex-direction: column; min-height: 0; flex: 1; }
.side-projects {
  gap: 2px;
  overflow-y: auto;
  min-height: 0;
  /* 스크롤바가 항목 위에 겹치지 않도록 */
  margin-right: -4px; padding-right: 4px;
  scrollbar-width: thin;
}
.side-proj {
  display: grid;
  grid-template-columns: auto 1fr auto;
  align-items: center;
  gap: 8px;
  padding: 7px 9px;
  border-radius: var(--r-sm);
  color: var(--fg-2);
  font-size: 13px;
  transition: background 100ms ease, color 100ms ease;
}
.side-proj:hover { background: var(--bg-subtle); color: var(--fg-1); text-decoration: none; }
/* 현재 프로젝트 = 네이비 채움 + 시안 좌측 스트라이프(= 선택 축). 탭의 "현재 위치"와 구분된다. */
.side-proj.is-active {
  background: var(--brand-500);
  color: #fff;
  font-weight: 700;
  box-shadow: inset 2px 0 0 var(--accent-400);
}
/* 코드는 식별자다 → 네이비. 시안은 "선택·액션" 축에만 남긴다 (3축 분리) */
.side-proj-code {
  font-size: 10px; font-weight: 700; letter-spacing: 0.02em;
  color: var(--brand-500);
  background: var(--brand-50);
  border: 1px solid var(--brand-100);
  padding: 1px 5px; border-radius: var(--r-xs);
  flex-shrink: 0;
}
.side-proj.is-active .side-proj-code {
  color: #fff; background: rgba(255,255,255,0.16); border-color: rgba(255,255,255,0.28);
}
.side-proj-name { overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.side-proj-status {
  font-size: 9px; font-weight: 700; text-transform: uppercase; letter-spacing: 0.04em;
  color: var(--fg-4); background: var(--bg-subtle);
  padding: 1px 5px; border-radius: var(--r-xs);
}
.side-proj.is-active .side-proj-status {
  color: #fff; background: rgba(255,255,255,0.16);
}
.side-proj-dot { width: 6px; height: 6px; border-radius: 50%; background: var(--accent-400); }
.side-empty { padding: 6px 9px; font-size: 11px; color: var(--fg-4); line-height: 1.6; }
.side-user.is-active { background: var(--bg-subtle); border-radius: var(--r-md); }

/* 그룹 구분선을 읽히게: 라벨 한 단계 진하게 + 위쪽 여백 확대 */
.side-section-divider { color: var(--fg-3); margin: 18px 0 7px; }
.side-section-divider:first-of-type { margin-top: 16px; }

/* ============================================================
   프로젝트 워크스페이스 chrome (ADR-0020)

   층위:
     .topbar       흰색(bg-card)  — 전역 액션 (검색·마감칩·제출물)
     .proj-header  bg-chrome 톤   — 프로젝트 정체성 (코드·이름·상태·목표)
     .proj-tabbar  bg-chrome 톤   — 탭. 하단 rail(border-2)이 콘텐츠 경계다. sticky.
     .page-canvas  bg-app 회색    — 콘텐츠

   활성 탭은 톤 밴드 위로 "흰색으로 떠오르고" + 네이비 700 + 시안 2px 밑줄.
   3중 신호이므로 색약·저휘도 모니터에서도 구분된다.
   ============================================================ */
.proj-header {
  background: var(--bg-chrome);
  padding: 12px var(--sp-6) 11px;
  /* 아래에 .proj-tabbar 가 같은 톤으로 이어지므로 보더를 두지 않는다 (경계선 중복 제거) */
}
.proj-header-row { display: flex; align-items: center; gap: 10px; flex-wrap: wrap; }
.proj-header-code {
  font-size: 11px; font-weight: 700;
  color: #fff; background: var(--brand-500);
  padding: 3px 8px; border-radius: var(--r-sm);
}
.proj-header-name {
  margin: 0;
  font-size: 20px; font-weight: 700;
  letter-spacing: -0.018em;
  color: var(--fg-1);
}
.proj-header-meta {
  margin-top: 3px;
  font-size: 12px; color: var(--fg-2);
}

/* ---- 탭 바 ---- */
.proj-tabbar {
  background: var(--bg-chrome);
  padding: 0 var(--sp-6);
  /* rail = 탭 바가 끝나는 선. inset 이므로 배경 레이어에 그려지고,
     활성 탭(자손)이 그 위에 덮어써서 "연결된 탭" 형태가 된다. */
  box-shadow: inset 0 -1px 0 var(--border-2);
  /* topbar 바로 아래에 고정 — 41행/103행 표를 스크롤해도 탭이 사라지지 않는다.
     오프셋은 --topbar-h (tokens.css). 1px 겹치게 해서 틈이 생기지 않도록 한다. */
  position: sticky;
  top: calc(var(--topbar-h) - 1px);
  z-index: 4;
  min-height: var(--tabbar-h);
}
.proj-tabs {
  display: flex;
  gap: 2px;
  overflow-x: auto;
  overflow-y: hidden;
  scrollbar-width: thin;
}
.proj-tab {
  display: inline-flex; align-items: center; justify-content: center;
  /* 라벨 길이가 KO/EN 혼용으로 불규칙하다 → min-width 로 리듬을 맞춘다 */
  min-width: 74px;
  padding: 9px 14px;
  font-size: 13px; font-weight: 600;
  /* 비활성도 읽혀야 한다: fg-3(slate-500) → fg-2(slate-700). 톤 밴드 위에서 8:1 이상 */
  color: var(--fg-2);
  background: transparent;
  border-bottom: 2px solid transparent;
  border-radius: var(--r-md) var(--r-md) 0 0;
  white-space: nowrap;
  transition: background 100ms ease, color 100ms ease;
}
.proj-tab:hover {
  color: var(--fg-1);
  background: var(--bg-chrome-hover);
  text-decoration: none;
}
.proj-tab.is-active {
  color: var(--brand-500);
  font-weight: 700;
  background: var(--bg-card);
  border-bottom-color: var(--accent-500);
}
.proj-tab.is-active:hover { background: var(--bg-card); color: var(--brand-500); }

/* ============================================================
   1366×768 (조선소 노트북) 보정
   사이드바 232 + 캔버스 좌우 48 → 실사용 폭 1086px
   ============================================================ */
@media (max-width: 1439px) {
  /* 세로 768px에서 chrome(63+~75+38)이 이미 176px이다 — 캔버스 여백을 줄인다 */
  .page-canvas { padding: var(--sp-5) var(--sp-6); }
  /* 토폴로지 캔버스가 뷰포트보다 크면 탐색이 불가능해진다 */
  .cy-canvas { height: clamp(420px, calc(100vh - 250px), 680px); }
}
@media (max-height: 820px) {
  .cy-canvas { height: clamp(400px, calc(100vh - 240px), 680px); }
}

/* ============================================================
   인쇄 — /export/report.html 이 선급 제출물이다 (H4)
   ADR-0022. 화면 chrome 을 걷어내고, 색으로 전달되는 데이터 마크는 남긴다.
   ============================================================ */
@media print {
  @page { margin: 12mm; }

  html, body { background: #fff; }
  .app-shell { display: block; min-height: 0; }

  /* 네비게이션·액션·입력은 제출물에 없어야 한다 */
  .sidebar, .topbar, .proj-tabbar, .proj-tabs,
  .export-actions, .audit-chip, .lang-toggle,
  .filters, .upload-drop, .btn, .btn-export, .cy-tip,
  .side-footer, .search {
    display: none !important;
  }

  .page-canvas { padding: 0; max-width: none; margin: 0; }
  .page-fade { animation: none; }

  /* 프로젝트 식별 정보는 표지 정보로서 남긴다 — 단 탭 없이, 흰 배경으로 */
  .proj-header {
    position: static;
    background: #fff;
    padding: 0 0 10px;
    border-bottom: 1px solid var(--border-2);
    margin-bottom: 14px;
    box-shadow: none;
  }

  /* 페이지 넘김 */
  thead { display: table-header-group; }   /* 41행 matrix 가 여러 장으로 넘어가도 헤더 반복 */
  tfoot { display: table-footer-group; }
  tr, .rail-row, .wq-row, .att-card, .timeline-item { break-inside: avoid; }
  .card, .kpi, .stripe-accent, .info-card, .cert-card { break-inside: avoid; box-shadow: none; }
  h1, h2, h3, .card-title, .req-section-title { break-after: avoid; }

  /* 표를 가로 스크롤이 아니라 전개해서 인쇄한다 */
  .matrix-wrap { overflow: visible !important; border: 0; border-radius: 0; }
  table.matrix thead th { position: static; }
  table.matrix th, table.matrix td { padding: 5px 7px; font-size: 9.5px; }
  .tbl { font-size: 10.5px; }
  .tbl thead th { padding: 6px 8px; font-size: 9px; }
  .tbl tbody td { padding: 5px 8px; font-size: 10.5px; }
  .tbl tbody tr:hover td { background: transparent; }

  /* ★ 상태·커버리지·SP는 색이 곧 데이터다. 브라우저의 배경 제거를 강제로 무효화한다.
     이게 없으면 인쇄된 matrix 의 커버리지 점이 전부 사라진다. */
  .cell-dot, .status-badge, .status-badge .dot, .badge, .badge .dot,
  .sp-badge, .fr-tag, .csf-tag, .pill, .risk-badge,
  .stage-dot, .stage-link, .dday, .wq-count, .wq-chip,
  .progress, .progress > span, .kpi-bar, .kpi-bar > span,
  .status-dot, .proj-card-code, .proj-header-code,
  .cert-stripe, .cert-mark, .timeline-marker, .req-shall {
    -webkit-print-color-adjust: exact;
    print-color-adjust: exact;
  }

  /* 링크는 종이에서 파랗게 뜨면 노이즈다. 단 식별자는 네이비를 유지한다 (Stratos 서명) */
  a { color: var(--fg-1) !important; text-decoration: none !important; }
  .cell-ref, .req-standards-line, .t-brand { color: var(--brand-500) !important; }

  /* 화면용 hover/포커스 잔여물 제거 (단 inset 스트라이프는 정보이므로 남긴다) */
  .stage-dot, .timeline-marker, .status-dot, .lang-toggle button { box-shadow: none !important; }
  *:focus-visible { outline: none; }
}

/* ---- 딩뱃 → Lucide SVG 마무리 (ADR-0027) ----
   `↑`/`▾` 문자는 폰트에 따라 모양·크기가 달라지고 인쇄에서 흐려진다.
   `●`(CYBER SECURE SP1)는 S001 원문의 `•` 표기를 재현하는 **데이터 표기**이므로 문자로 남긴다. */
.upload-drop .upload-ico {
  color: var(--accent-500);
  line-height: 0;
  display: inline-flex;
}
.disclosure-chev { display: inline-flex; vertical-align: -2px; line-height: 0; }
details[open] > summary .disclosure-chev { transform: rotate(180deg); }
.timeline-chev { display: inline-flex; line-height: 0; color: var(--fg-3); }

/* --topbar-h 결합을 아래에서 고정한다 — 콘텐츠가 줄어도 탭 sticky 오프셋이 어긋나지 않게.
   (topbar_meta 블록을 쓰기 시작하면 높이가 늘어나므로 토큰도 함께 고쳐야 한다) */
.topbar { min-height: var(--topbar-h); }

/* ============================================================
   Requirements 워크스페이스 — 좌 레일 + 우 패널 (ADR-0028)
   Compliance Matrix 탭을 없애고 Requirements 한 화면으로 통합했다.
   같은 41행을 두 화면이 각각 그리던 중복을 제거한 것이다(PM ADR-0006 · B-017 잔여).
   ============================================================ */
.req-ws {
  display: grid;
  grid-template-columns: 316px minmax(0, 1fr);
  gap: 14px;
  align-items: start;
}
@media (max-width: 1180px) {
  /* 레일이 위로 올라가고 높이를 제한한다 — 좁은 화면에서 우측 패널을 살린다 */
  .req-ws { grid-template-columns: 1fr; }
  .req-rail { position: static !important; max-height: 260px; }
}
.req-pane { min-width: 0; }

/* ---- 레일 ---- */
.req-rail {
  position: sticky;
  /* topbar + 탭바 아래에 붙는다. 매직넘버 대신 토큰을 쓴다 */
  top: calc(var(--topbar-h) + var(--tabbar-h) + 14px);
  max-height: calc(100vh - var(--topbar-h) - var(--tabbar-h) - 28px);
  display: flex;
  flex-direction: column;
  background: var(--bg-card);
  border: 1px solid var(--border-1);
  border-radius: var(--r-xl);
  overflow: hidden;
}
.req-rail-head {
  padding: 10px 12px 8px;
  border-bottom: 1px solid var(--border-1);
  background: var(--bg-subtle);
}
.eyebrow-label {
  font-size: 10px; font-weight: 700; letter-spacing: 0.06em;
  text-transform: uppercase; color: var(--fg-2);
}

.req-rail-list { overflow-y: auto; }
.req-rail-item {
  display: block;
  padding: 8px 12px;
  border-bottom: 1px solid var(--border-1);
  color: var(--fg-2);
}
.req-rail-item:hover { background: var(--gray-100); text-decoration: none; }
.req-rail-item.is-current {
  background: var(--brand-50);
  box-shadow: inset 3px 0 0 var(--accent-500);
}
.req-rail-item.is-flagged { box-shadow: inset 3px 0 0 var(--danger-500); }
.req-rail-item.is-current.is-flagged {
  background: var(--brand-50);
  box-shadow: inset 3px 0 0 var(--danger-500);
}
.req-rail-item-top { display: flex; align-items: center; gap: 6px; }
.req-rail-code { font-size: 11px; font-weight: 700; color: var(--brand-500); }
.req-rail-item.is-current .req-rail-code { color: var(--brand-700); }
.req-rail-fr { font-size: 9px; padding: 0 4px; }
.status-dot-only {
  width: 8px; height: 8px; border-radius: 50%;
  margin-left: auto; flex-shrink: 0;
  border: 1px solid var(--border-2);
}
.status-dot-only.status-compliant     { background: var(--ok-500);     border-color: var(--ok-500); }
.status-dot-only.status-partial       { background: var(--warn-500);   border-color: var(--warn-500); }
.status-dot-only.status-non_compliant { background: var(--danger-500); border-color: var(--danger-500); }
.status-dot-only.status-pending       { background: var(--bg-card);    border-style: dashed; }
.status-dot-only.status-na            { background: var(--fg-4);       border-color: var(--fg-4); }

.req-rail-title {
  display: block;
  font-size: 12px;
  line-height: 1.4;
  color: var(--fg-1);
  margin: 3px 0 5px;
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}
.req-rail-bottom { display: flex; align-items: center; gap: 6px; }
.req-rail-cov { display: flex; justify-content: flex-end; }
.req-rail-flags { display: flex; gap: 3px; margin-left: auto; }
.rail-flag {
  font-family: var(--font-mono);
  font-size: 9px; font-weight: 700;
  padding: 0 3px; border-radius: var(--r-xs);
  background: var(--bg-subtle); color: var(--fg-3);
  border: 1px solid var(--border-1);
}
.rail-flag.is-warn { background: var(--warn-50); color: var(--warn-700); border-color: var(--warn-100); }
.rail-flag.is-bad  { background: var(--danger-50); color: var(--danger-700); border-color: var(--danger-100); }

/* ---- 커버리지 범례 (격자 위) ---- */
.cov-legend {
  display: flex; flex-wrap: wrap; gap: 14px;
  padding: 0 var(--sp-5) 12px;
  font-size: 11px; color: var(--fg-3);
}
.cov-legend span { display: inline-flex; align-items: center; gap: 5px; }
.cov-legend i { font-style: normal; }

/* 2패널 안에서는 상세 레이아웃을 더 이른 시점에 1열로 접는다 */
@media (max-width: 1520px) {
  .req-pane .detail-layout { grid-template-columns: 1fr; }
}

/* ---- 탭은 라벨 1줄이다 (2026-07-31, ADR-0028 부제 노출을 철회) ----
   부제("오늘 할 일" 등)를 2줄로 노출했더니 탭바가 무거워지고 라벨이 묻혔다.
   부제는 title 속성(툴팁)으로만 남긴다. 세로 리듬은 .proj-tab 기본 패딩이 잡는다. */
.proj-tab-label { display: block; line-height: 1.25; }

/* 레일: Item 1차 / SR 2차 (ADR-0029 — UR E27 Item 이 기준축) */
.req-rail-sr { font-size: 9.5px; font-weight: 600; color: var(--fg-4); }
.req-rail-item.is-current .req-rail-sr { color: var(--fg-3); }

/* DNV 열: 앞 배지(§절 R행)의 글자 수가 §4.2.2 R1 ~ §4.2.10 R12 로 들쭉날쭉해서
   뒤따르는 SP 배지의 x 위치가 행마다 흔들렸다. 앞 배지 폭을 고정해 SP 열을 세로로 맞춘다. */
.dnv-ref { display: inline-flex; align-items: center; gap: 6px; }
.dnv-ref .dnv-sec {
  width: 100px;            /* 최장 '§4.2.10 R12' 기준 */
  justify-content: flex-start;
  flex: 0 0 auto;
}
.dnv-ref .sp-badge { flex: 0 0 auto; }

/* ── S001 기재 위치 (§절) — Requirements 격자·레일의 1차 정보 (ADR-0031) ───────
   "매핑됐나"(항상 예)를 점으로 그리는 대신, 선급 검토자가 찾아가는 좌표를 직접 쓴다. */
.sec-ref {
  font-family: var(--font-mono);
  font-size: 12px;
  letter-spacing: -0.01em;
  color: var(--ink-700);
  background: var(--bg-chrome);
  border: 1px solid var(--line-200);
  border-radius: var(--radius-sm);
  padding: 2px 7px;
  white-space: nowrap;
}
.sec-ref.is-verified {
  color: var(--ok-700);
  background: var(--ok-100);
  border-color: var(--ok-700);
  font-weight: 600;
}
.sec-ref.is-blank { color: var(--ink-400); border-style: dashed; }


/* 레일 안의 §절은 한 줄 오른쪽 끝에 붙는다 */
.req-rail-cov .sec-ref { font-size: 11px; padding: 0 5px; }


/* 레일 항목: 제목과 절 번호를 한 줄에 (플래그가 없으면 항목은 2줄이다) */
.req-rail-mid {
  display: flex; align-items: baseline; justify-content: space-between;
  gap: 8px; min-width: 0;
}
.req-rail-mid .req-rail-title { min-width: 0; }
.req-rail-mid .req-rail-cov { flex: none; }

/* ── 매핑된 산출물 — 근거: 좁은 우측 단에서 6열 표가 삐져나왔다 → 블록 리스트 ── */
.map-list { display: flex; flex-direction: column; gap: 2px; }
.map-row {
  display: flex; flex-direction: column; gap: 6px;
  padding: 10px 10px;
  border-radius: var(--r-md);
  border: 1px solid transparent;
}
.map-row + .map-row { border-top: 1px solid var(--border-1); border-radius: 0; }
.map-row.is-mapped { background: var(--bg-subtle); }
.map-row.is-unmapped .map-row-title,
.map-row.is-unmapped .cell-ref { color: var(--fg-3); }
.map-row-doc { display: flex; align-items: baseline; gap: 7px; flex-wrap: wrap; }
.map-row-title { font-size: 12px; color: var(--fg-2); min-width: 0; }
.map-row-tag {
  font-size: 10px; font-weight: 700; letter-spacing: 0.04em;
  color: var(--fg-4); border: 1px dashed var(--border-2);
  border-radius: var(--r-sm); padding: 0 4px;
}
.map-row-pdf {
  margin-left: auto; font-size: 11px; font-weight: 700;
  color: var(--accent-700); text-decoration: none; white-space: nowrap;
}
.map-row-pdf:hover { text-decoration: underline; }
.map-row-ctl { display: flex; align-items: center; gap: 6px; flex-wrap: wrap; }
.map-row-ctl .map-sec { width: 88px; }
.map-row-ctl .map-cov { width: 104px; }
.map-ver {
  display: inline-flex; align-items: center; gap: 4px;
  font-size: 11px; color: var(--fg-2); white-space: nowrap; cursor: pointer;
}

/* 매핑 줄에서 coverage 를 뺀 뒤 남은 컨트롤 — 라벨로 무엇을 넣는 칸인지 말한다 */
.map-lbl { font-size: 11px; color: var(--fg-3); white-space: nowrap; }
.map-add {
  display: flex; align-items: center; gap: 6px; flex-wrap: wrap;
  margin-top: 10px; padding-top: 10px;
  border-top: 1px dashed var(--border-2);
}
.map-add select { max-width: 210px; }

/* 모달 규칙은 REDESIGN-SPEC §5 로 다시 씀 — 아래 dialog.modal 블록 참조 */

/* 온보딩 폼처럼 항목이 많은 모달 — 기본(760px)보다 넓게 */
/* modal-wide 는 §5 블록에서 정의한다 */

/* ── 네트워크 다이어그램 노드 카드 (commission-platform 이식, ADR-0039) ─────────
   Cytoscape 는 노드에 HTML 을 못 그린다 → 카드는 HTML 오버레이, 간선·존은 캔버스.
   원본은 다크(#111A2E)였다. Stratos 라이트 토큰으로 옮겼고 구조·치수는 그대로다:
   210px 폭 · 아이콘 26px 박스 · 이름 12px/700 · IP 10.5px 모노. */
.cy-wrap { position: relative; }
.cy-cards {
  position: absolute; inset: 0;
  pointer-events: none;      /* 드래그·선택은 Cytoscape 캔버스가 받는다 */
  overflow: hidden;
}
.net-card {
  position: absolute; top: 0; left: 0;
  transform-origin: 0 0;
  box-sizing: border-box;
  display: flex; align-items: center; gap: 10px;
  padding: 8px 12px;
  border-radius: 8px;
  background: var(--bg-card);
  border: 1px solid var(--border-2);
  box-shadow: 0 1px 2px rgba(15, 23, 42, .06);
}
.net-card.is-external { border-color: var(--danger-500); }
.net-card.is-selected { outline: 2px solid var(--accent-500); outline-offset: 2px; }
.net-card-icon {
  flex: none;
  display: flex; align-items: center; justify-content: center;
  width: 26px; height: 26px;
  border-radius: 6px;
  background: var(--bg-subtle);
}
.net-card-text { display: flex; flex-direction: column; gap: 1px; min-width: 0; }
.net-card-name {
  font-size: 12px; font-weight: 700; line-height: 1.25;
  letter-spacing: -0.01em; color: var(--fg-1);
  display: -webkit-box; -webkit-line-clamp: 2; -webkit-box-orient: vertical;
  overflow: hidden; overflow-wrap: anywhere;
}
.net-card-ip {
  font-family: var(--font-mono);
  font-size: 10.5px; font-weight: 500; line-height: 1.3;
  color: var(--fg-3);
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}

/* 존 라벨 — 원본의 [색 점] + 이름. Cytoscape 라벨에는 점을 넣을 수 없어 HTML 로 그린다. */
.net-zone {
  position: absolute; top: 0; left: 0;
  transform-origin: 0 0;
  display: flex; align-items: center; gap: 7px;
  white-space: nowrap;
}
.net-zone-dot { width: 7px; height: 7px; border-radius: 999px; flex: none; }
.net-zone-label { font-size: 11px; font-weight: 700; letter-spacing: -0.01em; }
/* 편집 모드에서 존 라벨은 **손잡이**다 — 이 칩을 끌면 존 전체가 움직인다.
   존 박스 안쪽을 끌 수 있게 하면 캔버스 대부분이 존이라 어디를 끌어도 존이 움직인다. */
.cy-wrap.is-editing .net-zone {
  pointer-events: auto; cursor: grab;
  padding: 3px 8px 3px 7px; margin: -3px 0 0 -7px;
  border-radius: 999px;
  border: 1px solid transparent;
}
.cy-wrap.is-editing .net-zone:hover {
  background: color-mix(in srgb, var(--bg-card) 82%, transparent);
  border-color: var(--border-2);
}
.cy-wrap.is-editing .net-zone.is-dragging {
  cursor: grabbing;
  background: var(--bg-card); border-color: var(--brand-500);
}

/* ── 네트워크 편집 모드 (ADR-0040, commission-platform 이식) ─────────────── */
.net-toolbar {
  display: flex; align-items: center; justify-content: space-between;
  gap: var(--sp-4); flex-wrap: wrap; margin-bottom: 14px;
}
.net-sep { border-left: 1px solid var(--border-1); height: 18px; }
.net-select {
  /* 폼 요소 기본 규칙이 width:100% 라 툴바에서 한 줄을 다 먹었다 → 폭을 고정한다 */
  width: auto; max-width: 210px; flex: none;
  height: 30px; font-size: 12px; padding: 0 8px;
  border: 1px solid var(--border-2); border-radius: var(--r-md);
  background: var(--bg-card); color: var(--fg-2);
}
.net-select:disabled { opacity: .5; }

/* 케이블 종류 선택 — 선택한 종류의 색으로 채워 어느 선을 그리는지 보이게 한다 */
.btn-group { display: inline-flex; border: 1px solid var(--border-2); border-radius: var(--r-md); overflow: hidden; }
.btn-group > .btn { border: 0; border-radius: 0; }
.btn-group > .btn + .btn { border-left: 1px solid var(--border-2); }
.cable-picker { align-items: stretch; }
.cable-picker-label {
  display: flex; align-items: center; padding: 0 8px;
  font-size: 11px; color: var(--fg-4); background: var(--bg-subtle);
  border-right: 1px solid var(--border-2);
}
.cable-btn {
  border: 0; border-left: 1px solid var(--border-2);
  padding: 0 9px; height: 30px;
  font-family: inherit; font-size: 11px; font-weight: 600;
  background: var(--bg-card); color: var(--fg-3); cursor: pointer;
}
.cable-btn:first-of-type { border-left: 0; }
.cable-btn:hover { background: var(--bg-subtle); }

/* 편집 모드에서만 핸들이 보인다 — 보기 모드에서 점이 떠 있으면 클릭 대상처럼 읽힌다 */
.net-handle {
  position: absolute; width: 8px; height: 8px; border-radius: 999px;
  background: var(--accent-500); border: 1.5px solid var(--bg-card);
  opacity: 0; pointer-events: none; transition: opacity 100ms ease;
}
.cy-wrap.is-editing .net-card { pointer-events: none; }        /* 카드 본체는 캔버스가 받는다 */
.cy-wrap.is-editing .net-handle { opacity: 1; pointer-events: auto; cursor: crosshair; }
.cy-wrap.is-editing .net-handle:hover { transform: scale(1.35); }
.net-handle-top    { top: -5px;  left: 50%; margin-left: -4px; }
.net-handle-bottom { bottom: -5px; left: 50%; margin-left: -4px; }
.net-handle-left   { left: -5px;  top: 50%; margin-top: -4px; }
.net-handle-right  { right: -5px; top: 50%; margin-top: -4px; }
.net-card.is-drop { outline: 2px solid var(--accent-500); outline-offset: 2px; }

/* 연결 미리보기 선 */
.net-guide { position: absolute; inset: 0; pointer-events: none; z-index: 5; }

/* 존 관리 모달 */
.zone-list { display: flex; flex-direction: column; gap: 6px; }
.zone-row {
  display: flex; align-items: center; gap: 8px;
  padding: 7px 8px; border-radius: var(--r-md); background: var(--bg-subtle);
}
.zone-row .zone-name {
  flex: 1; min-width: 0; height: 28px; font-size: 12px;
  border: 1px solid var(--border-2); border-radius: var(--r-sm);
  padding: 0 7px; background: var(--bg-card);
}
.zone-ext {
  font-size: 10px; font-weight: 700; color: var(--danger-500);
  border: 1px solid var(--danger-500); border-radius: var(--r-sm); padding: 0 4px;
}
.zone-pal { display: inline-flex; gap: 3px; }
.zone-sw {
  width: 16px; height: 16px; border-radius: 4px; cursor: pointer;
  border: 1.5px solid transparent; padding: 0;
}
.zone-sw.is-on { border-color: var(--fg-1); }

/* 툴바 두 세트 — `.row`의 display:flex 가 [hidden] 의 display:none 을 덮어
   보기 도구와 편집 도구가 같이 보였다. 전용 클래스로 분리하고 hidden 을 우선시한다. */
.net-view-tools, .net-edit-tools {
  display: flex; align-items: center; flex-wrap: wrap; gap: 8px;
}
.net-view-tools[hidden], .net-edit-tools[hidden] { display: none; }

/* 케이블 선택기 — v1 은 종류가 7개다(원본은 4개). 잘리지 않게 줄바꿈을 허용한다. */
.cable-picker { flex-wrap: wrap; }
.cable-picker-label { white-space: nowrap; }
.cable-btn { white-space: nowrap; }

/* ── AS-IS / TO-BE (ADR-0042) ─────────────────────────────────────────
   컨설팅 관점 화면. 왼쪽이 현재(이전 담당자가 쓴 S001 Description), 오른쪽이 목표.
   초안과 확정을 눈으로 구분해야 한다 — 검토 안 된 문장이 확정처럼 보이면 H1 위반이다. */
.pill.pill-danger { background: var(--danger-50); color: var(--danger-700); border-color: var(--danger-100); }

.at-list { display: flex; flex-direction: column; gap: 10px; }
.at-row { padding: 0; overflow: hidden; }
/* 확정된 것은 왼쪽에 초록 띠, 초안은 주황 띠 — 목록을 훑으며 남은 일을 센다 */
.at-row.is-confirmed { box-shadow: inset 3px 0 0 var(--ok-500); }
.at-row.is-draft { box-shadow: inset 3px 0 0 var(--warn-500); }
.at-head {
  display: flex; align-items: center; gap: 8px; flex-wrap: wrap;
  padding: 12px var(--sp-5);
  border-bottom: 1px solid var(--border-1);
  background: var(--bg-subtle);
}
.at-title { font-size: 13px; font-weight: 600; color: var(--fg-1); }
.at-cols {
  display: grid; grid-template-columns: 1fr 1fr;
  gap: 0;
}
.at-col { padding: 14px var(--sp-5); min-width: 0; }
.at-col + .at-col { border-left: 1px solid var(--border-1); }
.at-label {
  font-size: 10px; font-weight: 700; letter-spacing: 0.06em; text-transform: uppercase;
  color: var(--fg-3); margin-bottom: 8px;
  display: flex; align-items: center; gap: 6px;
}
.at-body {
  font-size: 12px; line-height: 1.55; color: var(--fg-1);
  white-space: pre-wrap; overflow-wrap: anywhere;
  max-height: 150px; overflow-y: auto;
}
.at-empty { font-size: 12px; color: var(--fg-3); font-style: normal; }
.at-meta { margin-top: 10px; font-size: 11px; color: var(--fg-3); }
.at-meta .sec-ref { margin-right: 4px; }
.at-input {
  width: 100%; font-family: inherit; font-size: 12px; line-height: 1.5;
  padding: 7px 9px; border: 1px solid var(--border-2); border-radius: var(--r-md);
  background: var(--bg-card); color: var(--fg-1); resize: vertical;
}
.at-pri { height: 26px; font-size: 11px; padding: 0 6px; width: auto; }
.at-draft-tag {
  font-size: 10px; font-weight: 700; letter-spacing: 0;
  color: var(--warn-700); background: var(--warn-50);
  border: 1px solid var(--warn-100); border-radius: var(--r-sm);
  padding: 1px 5px; text-transform: none;
}

/* 보고서 표 */
.at-report td { vertical-align: top; }
/* 리포트 안의 소제목 — 한 칸에 두 성격(요구사항 답변 / 시험 절차)이 들어가므로 구분이 필요하다 */
.at-rep-sub {
  font-size: 8.5px; font-weight: 600; letter-spacing: .1em; color: var(--fg-4);
  margin-top: 7px; padding-top: 5px; border-top: 1px dotted var(--border-2);
}
/* 시험 절차는 번호 목록이라 줄바꿈이 의미다 */
.at-rep-pre {
  font-family: var(--font-mono); font-size: 9.5px; line-height: 1.5; color: var(--fg-2);
  white-space: pre-wrap; overflow-wrap: anywhere; margin-top: 3px;
}
/* 요구사항 원문 — 우리가 쓴 글이 아니라 규정 인용이다. 세로선으로 구분한다. */
.at-rep-req {
  font-size: 10.5px; line-height: 1.5; color: var(--fg-1);
  white-space: pre-line; margin-top: 5px;
  padding-left: 7px; border-left: 2px solid var(--brand-400);
}
.at-rep-body { font-size: 11px; line-height: 1.5; color: var(--fg-2); white-space: pre-wrap; margin-top: 4px; }
.at-rep-action { font-size: 11px; line-height: 1.5; color: var(--fg-1); white-space: pre-wrap; margin-top: 5px; font-weight: 600; }
.at-rep-meta { font-size: 10.5px; color: var(--fg-3); margin-top: 5px; }

@media (max-width: 1100px) {
  .at-cols { grid-template-columns: 1fr; }
  .at-col + .at-col { border-left: 0; border-top: 1px solid var(--border-1); }
}
@media print {
  .at-report { font-size: 10px; }
  .at-body { max-height: none; overflow: visible; }
}

/* ── AS-IS / TO-BE 구성도 두 장 (B-050) ───────────────────────────────
   PNG 첨부 대신 기준선 좌표로 다시 그린다 — 두 장이 같은 렌더러를 써야 비교가 성립한다. */
.topo-pair {
  display: grid; grid-template-columns: 1fr 1fr; gap: var(--sp-4);
  margin-bottom: var(--sp-4);
}
.topo-fig { margin: 0; }
.topo-cap {
  font-size: 11px; font-weight: 700; letter-spacing: 0.04em; text-transform: uppercase;
  color: var(--fg-2); margin-bottom: 6px;
  display: flex; align-items: baseline; gap: 8px;
}
.topo-fig .cy-wrap {
  height: 340px;
  border: 1px solid var(--border-1); border-radius: var(--r-lg);
  background: var(--bg-card); overflow: hidden;
}
.topo-fig .cy-canvas { width: 100%; height: 100%; }
.topo-empty {
  display: flex; align-items: center; justify-content: center; height: 100%;
  font-size: 12px; color: var(--fg-3);
}
@media (max-width: 1100px) { .topo-pair { grid-template-columns: 1fr; } }
@media print {
  /* 인쇄에서는 두 장을 위아래로 — 좌우로 나누면 카드 글자가 읽히지 않는다 */
  .topo-pair { grid-template-columns: 1fr; gap: 10px; }
  .topo-fig { break-inside: avoid; }
  .topo-fig .cy-wrap { height: 300px; }
}

/* ── 네트워크 AS-IS / TO-BE 보기 전환 ─────────────────────────────────
   편집은 TO-BE(현재)에서만 한다. AS-IS 는 얼린 기준선이라 읽기 전용이다. */
/* `1fr` 은 minmax(auto, 1fr) 이라 트랙이 콘텐츠 min-content 보다 작아지지 못한다.
   Cytoscape 가 캔버스에 픽셀 폭을 직접 넣으므로 TO-BE 트랙이 1368px 로 부풀고
   AS-IS 트랙이 2px 로 찌그러졌다 → minmax(0, 1fr) 로 줄어들 수 있게 한다. */
.net-stage { display: grid; grid-template-columns: minmax(0, 1fr); gap: 12px; }
.net-stage[data-scope="both"] { grid-template-columns: minmax(0, 1fr) minmax(0, 1fr); }
/* AS-IS 만 보기: 현재 캔버스를 접는다 */
.net-stage[data-scope="asis"] .net-pane-tobe { display: none; }
.net-stage .cy-wrap { position: relative; }
.net-pane-cap {
  position: absolute; top: 10px; left: 14px; z-index: 3;
  display: flex; align-items: baseline; gap: 7px;
  font-size: 10px; font-weight: 700; letter-spacing: 0.06em; text-transform: uppercase;
  color: var(--fg-3);
  background: color-mix(in srgb, var(--bg-card) 88%, transparent);
  border: 1px solid var(--border-1); border-radius: var(--r-sm);
  padding: 2px 7px;
}
.net-pane-cap .mono { text-transform: none; letter-spacing: 0; font-weight: 500; }
/* 나란히 볼 때는 각 캔버스가 좁아진다 — 높이를 맞춰 비교가 되게 한다 */
.net-stage[data-scope="both"] .cy-wrap,
.net-stage[data-scope="asis"] .cy-wrap { height: 520px; }
.net-stage[data-scope="both"] .cy-canvas,
.net-stage[data-scope="asis"] .cy-canvas { height: 100%; }
.net-pane-asis { border: 1px solid var(--border-1); border-radius: var(--r-lg); overflow: hidden; }
.net-scope .btn.is-on { background: var(--ink-900, var(--fg-1)); color: #fff; }
.net-scope .btn:disabled { opacity: .45; cursor: not-allowed; }
@media (max-width: 1100px) { .net-stage[data-scope="both"] { grid-template-columns: 1fr; } }


/* ============================================================
   개요 화면 블록 (REDESIGN-SPEC §4.1)
   ============================================================ */
.kpi-row { display: grid; grid-template-columns: repeat(4, minmax(0, 1fr)); gap: 14px; }
.kpi {
  background: var(--bg-card);
  border: 1px solid var(--border-1);
  border-radius: var(--r-xl);
  padding: 16px 17px;
  display: flex; flex-direction: column; gap: 9px;
  min-width: 0;
}
.kpi.is-danger { border-color: var(--danger-100); background: var(--danger-50); }
.kpi-label { font-size: 9.5px; letter-spacing: .12em; text-transform: uppercase; color: var(--fg-3); }
.kpi-value-row { display: flex; align-items: baseline; gap: 6px; }
.kpi-value {
  font-size: 30px; font-weight: 600; line-height: 1;
  letter-spacing: -0.02em; color: var(--brand-500);
}
.kpi-unit { font-size: 12px; color: var(--fg-4); }
.kpi-bar { height: 4px; border-radius: 3px; background: #eef1f4; overflow: hidden; }
.kpi-bar > span { display: block; height: 100%; }
.kpi-sub { font-size: 11.5px; color: var(--fg-3); }

/* 갭 배너 */
.gap-banner {
  display: flex; align-items: center; gap: 18px; flex-wrap: wrap;
  background: var(--danger-50);
  border: 1px solid var(--danger-100);
  border-radius: var(--r-xl);
  padding: 14px 17px;
}
.gap-banner-msg { min-width: 220px; flex: 1; }
.gap-banner-title { font-size: 13px; font-weight: 600; color: var(--danger-700); }
.gap-banner-sub { font-size: 11.5px; color: var(--fg-2); margin-top: 3px; }
.gap-cells { display: grid; grid-template-columns: repeat(4, minmax(0, 1fr)); gap: 8px; flex: 0 0 auto; }
.gap-cell {
  display: flex; align-items: center; gap: 7px;
  background: var(--bg-card); border: 1px solid var(--border-1);
  border-radius: 7px; padding: 7px 10px; min-width: 132px;
}
.gap-cell-code { font-size: 10px; font-weight: 600; color: var(--fg-4); }
.gap-cell-label { font-size: 11.5px; color: var(--fg-2); }
.gap-cell-n { margin-left: auto; font-size: 14px; font-weight: 600; }
.gap-cell.is-bad { border-color: var(--danger-100); }
.gap-cell.is-bad .gap-cell-n { color: var(--danger-500); }
.gap-cell.is-ok .gap-cell-n { color: var(--ok-500); }
.gap-banner-cta { flex: 0 0 auto; }

/* FR별 진행 */
.fr-list { display: flex; flex-direction: column; gap: 7px; }
.fr-row { display: grid; grid-template-columns: 44px minmax(0, 1fr) 150px 62px; align-items: center; gap: 10px; }
.fr-code { font-size: 10.5px; font-weight: 600; color: var(--fg-2); }
.fr-name { font-size: 12px; color: var(--fg-2); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.fr-bar { display: flex; height: 6px; border-radius: 3px; background: var(--border-2); overflow: hidden; }
.fr-seg { display: block; height: 100%; }
.fr-n { font-size: 11px; color: var(--fg-3); text-align: right; }
.fr-legend {
  display: flex; gap: 14px; flex-wrap: wrap;
  border-top: 1px solid var(--border-1); padding-top: 10px;
  font-size: 11px; color: var(--fg-3);
}
.fr-legend span { display: inline-flex; align-items: center; gap: 5px; }
.fr-legend i { width: 9px; height: 9px; border-radius: 2px; }

/* 다음 할 일 */
.todo-list { display: flex; flex-direction: column; }
.todo-row {
  display: grid; grid-template-columns: 62px 70px minmax(0, 1fr) auto;
  align-items: center; gap: 10px;
  padding: 8px 4px; border-bottom: 1px solid var(--gray-100);
  color: var(--fg-1); text-decoration: none;
}
.todo-row:last-child { border-bottom: 0; }
.todo-row:hover { background: var(--bg-app); text-decoration: none; }
.todo-item { font-size: 10.5px; font-weight: 600; color: var(--brand-500); }
.todo-sr { font-size: 10.5px; color: var(--fg-3); }
.todo-title { font-size: 12px; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.todo-tags { display: inline-flex; gap: 4px; }
.gap-tag {
  font-size: 9.5px; font-weight: 600;
  color: var(--danger-700); background: var(--danger-50);
  border: 1px solid var(--danger-100); border-radius: 4px; padding: 1px 4px;
}

/* 선급 요약 7칸 */
.soc-grid { display: grid; grid-template-columns: repeat(7, minmax(0, 1fr)); gap: 10px; }
.soc-card {
  display: flex; flex-direction: column; gap: 6px;
  background: var(--bg-card);
  border: 1px solid var(--border-1);
  border-top: 2px solid var(--soc-OTHER);
  border-radius: 8px; padding: 11px 12px;
  text-decoration: none; color: var(--fg-1);
}
.soc-card:hover { box-shadow: var(--shadow-md); text-decoration: none; }
.soc-card-code { font-size: 14px; font-weight: 600; }
.soc-card-name {
  font-size: 10.5px; color: var(--fg-3); line-height: 1.35;
  display: -webkit-box; -webkit-line-clamp: 2; -webkit-box-orient: vertical; overflow: hidden;
}
.soc-card-bar { height: 4px; border-radius: 3px; background: #eef1f4; overflow: hidden; margin-top: auto; }
.soc-card-bar > span { display: block; height: 100%; }
.soc-card-meta { font-size: 10px; color: var(--fg-3); }

@media (max-width: 1500px) {
  .soc-grid { grid-template-columns: repeat(4, minmax(0, 1fr)); }
  .kpi-row { grid-template-columns: repeat(2, minmax(0, 1fr)); }
}
@media (max-width: 1200px) {
  .grid-115, .grid-2, .grid-23 { grid-template-columns: minmax(0, 1fr); }
}

/* ============================================================
   2-pane 워크벤치 (REDESIGN-SPEC §4.3)
   좌측 392px 목록 + 우측 상세. 41개 세로 스택을 폐기한 자리다.
   ============================================================ */
.wb {
  display: grid; grid-template-columns: 392px minmax(0, 1fr);
  gap: 14px; align-items: start;
  min-height: 0;
}
.wb-list {
  display: flex; flex-direction: column;
  background: var(--bg-card);
  border: 1px solid var(--border-1);
  border-radius: var(--r-xl);
  overflow: hidden;
  position: sticky; top: 0;
  max-height: calc(100vh - var(--topbar-h) - 66px);
}
.wb-list-head { padding: 14px 15px 12px; border-bottom: 1px solid var(--border-1); }
.wb-list-title { font-size: 13.5px; font-weight: 600; color: var(--fg-1); }
.wb-list-sub { font-size: 11px; color: var(--fg-3); margin-top: 2px; }
.wb-chips { display: flex; gap: 6px; margin-top: 10px; flex-wrap: wrap; }
.wb-chip {
  font-size: 11px; font-weight: 500;
  padding: 4px 9px; border-radius: 999px;
  border: 1px solid var(--border-2); background: var(--bg-card);
  color: var(--fg-2); text-decoration: none;
}
.wb-chip:hover { border-color: var(--brand-500); color: var(--brand-500); text-decoration: none; }
.wb-chip.is-on { background: var(--brand-500); border-color: var(--brand-500); color: #fff; }

.wb-list-scroll { flex: 1; min-height: 0; overflow-y: auto; }
.wb-row {
  display: flex; gap: 9px; align-items: flex-start;
  padding: 10px 15px;
  border-bottom: 1px solid var(--gray-100);
  color: var(--fg-1); text-decoration: none;
  border-left: 3px solid transparent;
}
.wb-row:hover { background: var(--bg-app); text-decoration: none; }
.wb-row.is-sel { background: var(--brand-50); border-left-color: var(--brand-500); }
.wb-row-dot { flex: 0 0 7px; width: 7px; height: 7px; border-radius: 50%; margin-top: 5px; }
.wb-row-dot.is-ok { background: var(--ok-500); }
.wb-row-dot.is-draft { background: var(--warn-500); }
.wb-row-body { display: flex; flex-direction: column; gap: 2px; min-width: 0; }
.wb-row-meta { font-size: 10px; color: var(--fg-3); }
.wb-row-title {
  font-size: 12px; line-height: 1.35; color: var(--fg-1);
  display: -webkit-box; -webkit-line-clamp: 2; -webkit-box-orient: vertical; overflow: hidden;
}
.wb-list-foot {
  display: flex; gap: 6px; flex-wrap: wrap;
  padding: 10px 15px; border-top: 1px solid var(--border-1); background: var(--bg-app);
}

/* ---------- 우측 상세 ---------- */
.wb-detail { display: flex; flex-direction: column; gap: 14px; max-width: 1080px; min-width: 0; }
.wb-head { display: flex; align-items: flex-start; gap: 18px; }
.wb-head-main { display: flex; flex-direction: column; gap: 7px; min-width: 0; }
.wb-head-ids { display: flex; align-items: center; gap: 7px; flex-wrap: wrap; }
.wb-item-chip {
  font-size: 10.5px; font-weight: 600; color: #fff;
  background: var(--brand-500); border-radius: 5px; padding: 2px 7px;
}
.wb-head-sr { font-size: 11px; color: var(--fg-2); font-weight: 600; }
.wb-head-fr {
  font-size: 10px; color: var(--fg-3);
  background: var(--bg-subtle); border: 1px solid var(--border-1);
  border-radius: 4px; padding: 1px 5px;
}
.wb-head-title { margin: 0; font-size: 18px; font-weight: 600; color: var(--fg-1); letter-spacing: -0.012em; line-height: 1.3; }
.wb-head-actions { margin-left: auto; display: flex; gap: 8px; flex: 0 0 auto; }

/* E1–E4 체크 카드 */
.wb-checks { display: grid; grid-template-columns: repeat(4, minmax(0, 1fr)); gap: 10px; }
.wb-check {
  display: flex; align-items: center; gap: 7px;
  background: var(--bg-card); border: 1px solid var(--border-1);
  border-radius: 8px; padding: 10px 12px;
}
.wb-check-code { font-size: 10px; font-weight: 600; border-radius: 4px; padding: 1px 5px; }
.wb-check.is-ok .wb-check-code { color: var(--ok-700); background: var(--ok-50); }
.wb-check.is-bad .wb-check-code { color: var(--danger-700); background: var(--danger-50); }
.wb-check.is-bad { border-color: var(--danger-100); }
.wb-check-label { font-size: 12px; color: var(--fg-2); }
.wb-check-note { margin-left: auto; font-size: 10.5px; color: var(--fg-3); }
.wb-check.is-ok .wb-check-note { color: var(--ok-700); }
.wb-check.is-bad .wb-check-note { color: var(--danger-500); }

/* 요구사항 원문 — AS-IS/TO-BE 가 답해야 하는 기준.
   왼쪽 굵은 세로선으로 "인용문"임을 표시한다. 이건 우리가 쓴 글이 아니라 규정 원문이다. */
.wb-req {
  background: var(--bg-card); border: 1px solid var(--border-1);
  border-left: 3px solid var(--brand-500);
  border-radius: 8px; padding: 13px 16px 14px;
}
.wb-req-head {
  display: flex; align-items: baseline; justify-content: space-between;
  gap: 12px; flex-wrap: wrap; margin-bottom: 8px;
}
.wb-req-label {
  font-size: 9.5px; font-weight: 600; letter-spacing: .08em; text-transform: uppercase;
  color: var(--brand-500);
}
.wb-req-src { font-size: 10px; color: var(--fg-4); }
/* 원문은 영어다 — 본문 폰트로 두고 줄간만 넉넉히 (읽는 문장이지 코드가 아니다) */
.wb-req-text {
  margin: 0; font-size: 13px; line-height: 1.62; color: var(--fg-1);
  white-space: pre-line;
}
.wb-req-tp { margin-top: 11px; border-top: 1px solid var(--border-1); padding-top: 9px; }
.wb-req-tp > summary {
  cursor: pointer; font-size: 11px; font-weight: 500; color: var(--fg-3);
  list-style: none;
}
.wb-req-tp > summary::-webkit-details-marker { display: none; }
/* 삼각형은 **CSS 로 그린다.** ▸(U+25B8)·▾(U+25BE)는 Pretendard 에 글리프가 없어
   OS 폰트(Cambria Math 등)로 떨어졌다 — 크기·색이 제멋대로가 된다. */
.wb-req-tp > summary::before {
  content: ""; display: inline-block; vertical-align: 1px; margin-right: 6px;
  border-left: 5px solid var(--fg-4);
  border-top: 3.5px solid transparent; border-bottom: 3.5px solid transparent;
  transition: transform .12s ease;
}
.wb-req-tp[open] > summary::before { transform: rotate(90deg) translateX(1px); }
.wb-req-tp > summary:hover { color: var(--brand-500); }
/* 절차는 번호 목록이라 줄바꿈이 의미다 → pre 로 두되 폰트는 모노 */
.wb-req-pre {
  margin: 9px 0 0; padding: 11px 13px;
  background: var(--bg-app); border: 1px solid var(--border-1); border-radius: 6px;
  font-family: var(--font-mono); font-size: 11px; line-height: 1.62; color: var(--fg-2);
  white-space: pre-wrap; word-break: break-word;
  max-height: 340px; overflow-y: auto;
}

/* AS-IS / TO-BE 2단 */
.wb-cols { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: 14px; align-items: start; }
.wb-pane {
  background: var(--bg-card); border: 1px solid var(--border-1);
  border-top: 3px solid var(--border-2);
  border-radius: var(--r-xl); padding: 14px 16px;
  display: flex; flex-direction: column; gap: 10px; min-width: 0;
}
.wb-pane-tobe { border-top-color: var(--warn-500); }
.wb-pane-head { display: flex; align-items: center; gap: 8px; flex-wrap: wrap; }
.wb-pane-label { font-size: 9.5px; letter-spacing: .12em; text-transform: uppercase; color: var(--fg-3); }
.wb-pane-src { margin-left: auto; font-size: 10.5px; color: var(--fg-3); }
.wb-pane-body {
  font-size: 12px; line-height: 1.65; color: var(--fg-1);
  white-space: pre-wrap; overflow-wrap: anywhere;
  max-height: 260px; overflow-y: auto;
  text-wrap: pretty;
}
.wb-pane-foot { font-size: 10.5px; color: var(--fg-3); border-top: 1px solid var(--gray-100); padding-top: 8px; }
/* 시험 절차는 번호 목록이라 **줄바꿈이 의미다** → pre 로 두고 모노로 읽는다.
   Description(산문)은 `.wb-pane-body` 쪽이다 — 두 성격을 한 스타일로 묶지 않는다. */
.wb-pane-pre {
  margin: 0; padding: 11px 12px;
  background: var(--bg-app); border: 1px solid var(--border-1); border-radius: 8px;
  font-family: var(--font-mono); font-size: 11px; line-height: 1.65; color: var(--fg-2);
  white-space: pre-wrap; overflow-wrap: anywhere;
  max-height: 330px; overflow-y: auto;
}
.wb-ta-tall { min-height: 240px; font-family: var(--font-mono); font-size: 11px; }
.wb-pri { height: 24px; font-size: 11px; padding: 0 6px; width: auto; margin-left: auto; }
.wb-ta {
  width: 100%; font-family: inherit; font-size: 12px; line-height: 1.6;
  padding: 9px 11px; border: 1px solid var(--border-2); border-radius: var(--r-md);
  background: var(--bg-card); color: var(--fg-1); resize: vertical;
}
.wb-ta:focus { outline: none; border-color: var(--brand-500); }
.wb-cond {
  background: var(--warn-50); border: 1px solid var(--warn-100);
  border-radius: 8px; padding: 10px 12px;
  display: flex; flex-direction: column; gap: 6px;
}
.wb-cond-title { font-size: 9.5px; letter-spacing: .1em; text-transform: uppercase; color: var(--warn-700); }
.wb-cond-row { display: flex; align-items: center; gap: 7px; font-size: 11.5px; color: var(--fg-2); }
.wb-cond-box {
  width: 12px; height: 12px; border-radius: 3px;
  border: 1.5px solid var(--warn-200); background: var(--bg-card); flex: 0 0 auto;
}
.wb-cond-box.is-ok { background: var(--ok-500); border-color: var(--ok-500); }

/* 하단 메타 3칸 */
.wb-meta {
  display: grid; grid-template-columns: repeat(3, minmax(0, 1fr)); gap: 0;
  background: var(--bg-card); border: 1px solid var(--border-1); border-radius: var(--r-xl);
}
.wb-meta-cell { padding: 12px 15px; min-width: 0; }
.wb-meta-cell + .wb-meta-cell { border-left: 1px solid var(--border-1); }
.wb-meta-label { font-size: 9.5px; letter-spacing: .1em; text-transform: uppercase; color: var(--fg-3); margin-bottom: 6px; }
.wb-meta-body { font-size: 11.5px; color: var(--fg-1); display: flex; gap: 6px; flex-wrap: wrap; }
.wb-meta-link {
  font-size: 11px; color: var(--fg-2);
  background: var(--bg-subtle); border: 1px solid var(--border-1);
  border-radius: 5px; padding: 2px 6px; text-decoration: none;
}
.wb-meta-link:hover { border-color: var(--brand-500); color: var(--brand-500); text-decoration: none; }

@media (max-width: 1400px) {
  .wb { grid-template-columns: 330px minmax(0, 1fr); }
  .wb-cols { grid-template-columns: minmax(0, 1fr); }
  .wb-checks { grid-template-columns: repeat(2, minmax(0, 1fr)); }
}

/* ============================================================
   요구사항 격자 / 규정 대조표 표 (REDESIGN-SPEC §4.2)
   ============================================================ */
.mx-wrap { overflow-x: auto; }
.mx { border-collapse: collapse; width: 100%; }
.mx thead th {
  position: sticky; top: 0; z-index: 2;
  background: var(--bg-app);
  font-family: var(--font-mono);
  font-size: 9.5px; font-weight: 500;
  letter-spacing: .1em; text-transform: uppercase;
  color: var(--fg-3);
  text-align: left; padding: 9px 10px;
  border-bottom: 1px solid var(--border-1);
  white-space: nowrap;
}
.mx tbody td {
  padding: 0 10px; height: 36px;
  border-bottom: 1px solid var(--gray-100);
  font-size: 12px; color: var(--fg-1);
  white-space: nowrap;
}
.mx tbody tr:hover td { background: var(--bg-app); }
.mx .mx-c { text-align: center; padding: 0; }
.mx-item { font-weight: 600; color: var(--brand-500); }
.mx-sr { font-size: 11px; color: var(--fg-2); }
.mx-fr { font-size: 10px; color: var(--fg-3); }
.mx-title { white-space: normal; line-height: 1.4; min-width: 220px; }
.mx-ev { display: flex; align-items: center; gap: 7px; min-width: 0; }
.mx-ev-text { font-size: 10px; color: var(--fg-3); overflow: hidden; text-overflow: ellipsis; }

/* 문서 셀 기호 3단계 — 색 단독이 아니라 채움 정도로도 구분된다 */
.mx-dot { display: inline-block; width: 9px; height: 9px; border-radius: 50%; }
.mx-dot.is-full { background: var(--ok-500); }
.mx-dot.is-part { background: var(--warn-500); box-shadow: inset -3px 0 0 rgba(255,255,255,.75); }
.mx-dot.is-none { width: 4px; height: 4px; background: var(--fg-5); }
.mx-legend { display: flex; gap: 12px; align-items: center; font-size: 11px; color: var(--fg-3); }
.mx-legend span { display: inline-flex; align-items: center; gap: 5px; }

/* 필터 바 */
.filters { display: flex; align-items: center; gap: 8px; flex-wrap: wrap; }
.filters input[type="text"], .filters select {
  height: 32px; font-size: 12px; padding: 0 10px; width: auto;
  border: 1px solid var(--border-2); border-radius: var(--r-md);
  background: var(--bg-card); color: var(--fg-1);
}
.filters input[type="text"] { min-width: 260px; }
.filters input:focus, .filters select:focus { outline: none; border-color: var(--brand-500); }

/* ============================================================
   산출물 카드 그리드 (§4.6)
   ============================================================ */
.doc-grid { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: 14px; }
.doc-card {
  background: var(--bg-card); border: 1px solid var(--border-1);
  border-radius: var(--r-xl); padding: 15px 18px;
  display: flex; flex-direction: column; gap: 10px; min-width: 0;
}
.doc-card-top { display: flex; align-items: flex-start; gap: 10px; }
.doc-code {
  flex: 0 0 auto; font-size: 11px; font-weight: 600; color: var(--brand-500);
  background: var(--brand-50); border: 1px solid var(--brand-100);
  border-radius: 5px; padding: 3px 7px;
}
.doc-title {
  font-size: 13px; font-weight: 600; color: var(--fg-1); line-height: 1.4;
  display: -webkit-box; -webkit-line-clamp: 2; -webkit-box-orient: vertical; overflow: hidden;
  text-decoration: none; min-width: 0;
}
.doc-title:hover { color: var(--brand-500); text-decoration: none; }
.doc-pdf { margin-left: auto; flex: 0 0 auto; }
.doc-purpose { font-size: 11.5px; color: var(--fg-3); line-height: 1.5; text-wrap: pretty; }
.doc-meta {
  display: grid; grid-template-columns: repeat(4, minmax(0, 1fr));
  border-top: 1px solid var(--border-1); padding-top: 10px; gap: 8px;
}
.doc-meta-cell { display: flex; flex-direction: column; gap: 3px; min-width: 0; }
.doc-meta-label { font-size: 9px; letter-spacing: .1em; text-transform: uppercase; color: var(--fg-4); }
.doc-meta-val { font-size: 11.5px; color: var(--fg-1); }
.doc-meta-sub { color: var(--fg-3); font-size: 10px; }

/* ============================================================
   선급 카드 + 스텝퍼 (§4.7)
   ============================================================ */
.cert-grid { display: grid; grid-template-columns: repeat(3, minmax(0, 1fr)); gap: 14px; }
.cert-card {
  background: var(--bg-card); border: 1px solid var(--border-1);
  border-top: 3px solid var(--soc-OTHER);
  border-radius: var(--r-xl); padding: 14px 16px;
  display: flex; flex-direction: column; gap: 11px;
  text-decoration: none; color: var(--fg-1); min-width: 0;
}
.cert-card:hover { box-shadow: var(--shadow-md); text-decoration: none; }
.cert-card-top { display: flex; align-items: center; gap: 9px; }
.cert-code { font-size: 19px; font-weight: 700; letter-spacing: -0.01em; }
.cert-name {
  font-size: 11.5px; color: var(--fg-3); min-width: 0;
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.cert-card-top .pill { margin-left: auto; flex: 0 0 auto; }
.cert-stepper { display: flex; gap: 5px; align-items: center; flex-wrap: wrap; }
.cert-step {
  width: 12px; height: 12px; border-radius: 50%;
  border: 1.5px solid var(--border-2); background: var(--bg-card);
}
.cert-step.is-done { background: var(--ok-500); border-color: var(--ok-500); }
.cert-step.is-now  { background: var(--warn-500); border-color: var(--warn-500); }
.cert-card-foot {
  display: flex; align-items: center; gap: 9px; flex-wrap: wrap;
  border-top: 1px solid var(--border-1); padding-top: 9px;
  font-size: 11px; color: var(--fg-3);
}
.cert-card-cur { color: var(--fg-2); min-width: 0; overflow: hidden; text-overflow: ellipsis; white-space: nowrap; }
.cert-card-contact { margin-left: auto; font-size: 10px; color: var(--fg-4); }
.cert-card-contact.is-set { color: var(--ok-700); }

/* ============================================================
   자산 2-pane 보조 (§4.4)
   ============================================================ */
.wb.wb-330 { grid-template-columns: 330px minmax(0, 1fr); }
.wb-group {
  padding: 10px 15px 6px;
  font-size: 9.5px; letter-spacing: .12em; text-transform: uppercase;
  color: var(--fg-4); background: var(--bg-app);
  border-bottom: 1px solid var(--border-1);
  display: flex; gap: 6px;
}
.wb-row-n { margin-left: auto; font-size: 10.5px; color: var(--fg-3); flex: 0 0 auto; }
.form-grid-2 { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: 10px 12px; }
.form-grid-2 .field { margin: 0; }
.form-grid-2 .field-full { grid-column: 1 / -1; }
.form-col { display: flex; flex-direction: column; gap: 10px; }
.form-col .field { margin: 0; }
.form-foot { display: flex; align-items: center; gap: 12px; flex-wrap: wrap; }
.form-foot-meta { font-size: 10.5px; color: var(--fg-4); }
.link-summary { display: flex; align-items: center; gap: 12px; }
.link-summary-n { font-size: 26px; font-weight: 600; color: var(--brand-500); line-height: 1; }
.link-summary-note { font-size: 11.5px; color: var(--fg-3); line-height: 1.5; }

/* 알림 박스 */
.notice {
  font-size: 11.5px; color: var(--fg-3);
  background: var(--bg-subtle); border: 1px solid var(--border-1);
  border-radius: 7px; padding: 8px 11px;
}
.notice.is-bad { background: var(--danger-50); border-color: var(--danger-100); color: var(--danger-700); }
.notice.is-ok  { background: var(--ok-50); border-color: var(--ok-100); color: var(--ok-700); }

/* 입력 공통 (지시서 §3.3) */
input[type="text"], input[type="password"], input[type="email"], input[type="number"],
input[type="date"], input[type="search"], select, textarea {
  width: 100%;
  border: 1px solid var(--border-2); border-radius: var(--r-md);
  background: var(--bg-card); color: var(--fg-1);
  font-size: 12px; padding: 7px 10px;
}
input:focus, select:focus, textarea:focus { outline: none; border-color: var(--brand-500); }
select { height: 32px; padding: 0 8px; }
textarea { line-height: 1.6; resize: vertical; }

@media (max-width: 1500px) {
  .cert-grid { grid-template-columns: repeat(2, minmax(0, 1fr)); }
}
@media (max-width: 1200px) {
  .doc-grid, .cert-grid { grid-template-columns: minmax(0, 1fr); }
  .wb, .wb.wb-330 { grid-template-columns: minmax(0, 1fr); }
  .form-grid-2 { grid-template-columns: minmax(0, 1fr); }
}

/* ============================================================
   리포트 문서형 (REDESIGN-SPEC §4.9)
   base.html 이 /export/* 를 `.print-page`(1140px) 로 감싼다.
   ============================================================ */
.rp-head { display: flex; flex-direction: column; gap: 8px; margin-bottom: 22px; }
.rp-rule { height: 2px; background: var(--fg-1); }
.rp-std { font-size: 9.5px; letter-spacing: .1em; text-transform: uppercase; color: var(--fg-3); }
.rp-title-row { display: flex; align-items: center; gap: 16px; }
.rp-title { margin: 0; font-size: 24px; font-weight: 600; letter-spacing: -0.015em; color: var(--fg-1); }
.rp-print { margin-left: auto; }
.rp-meta { display: flex; gap: 14px; flex-wrap: wrap; font-size: 12px; color: var(--fg-3); }

.rp-kpis {
  display: grid; grid-template-columns: repeat(4, minmax(0, 1fr));
  gap: 0; border: 1px solid var(--border-1); border-radius: var(--r-lg);
  margin-bottom: 20px;
}
.rp-kpi { padding: 13px 15px; display: flex; flex-direction: column; gap: 5px; min-width: 0; }
.rp-kpi + .rp-kpi { border-left: 1px solid var(--border-1); }
.rp-kpi-label { font-size: 9px; letter-spacing: .1em; text-transform: uppercase; color: var(--fg-3); }
.rp-kpi-val { font-size: 26px; font-weight: 600; line-height: 1; color: var(--brand-500); letter-spacing: -0.02em; }
.rp-kpi-val span { font-size: 12px; color: var(--fg-4); font-weight: 500; }
.rp-kpi-sub { font-size: 10.5px; color: var(--fg-3); }

.rp-warn {
  background: var(--danger-50); border: 1px solid var(--danger-100);
  border-radius: var(--r-lg); padding: 12px 15px; margin-bottom: 20px;
  display: flex; flex-direction: column; gap: 5px;
}
.rp-warn-title { font-size: 13px; font-weight: 600; color: var(--danger-700); }
.rp-warn-body { font-size: 11.5px; color: var(--fg-2); }
.rp-warn-note { font-size: 11px; color: var(--fg-3); }

.rp-h2 {
  margin: 26px 0 10px; font-size: 15px; font-weight: 600; color: var(--fg-1);
  padding-bottom: 7px; border-bottom: 1px solid var(--border-1);
}
.rp-mx tbody td { height: 30px; }
.print-page .mx-title { min-width: 180px; }

/* ============================================================
   모달 6종 (REDESIGN-SPEC §5)
   폭 520–680px · radius 12px · 오버레이 rgba(13,26,39,.45)
   ============================================================ */
dialog.modal {
  position: relative;
  width: min(680px, calc(100vw - 32px));
  max-height: calc(100vh - 64px);
  overflow-y: auto;
  padding: 0;
  border: 0;
  border-radius: var(--r-2xl);
  background: var(--bg-card);
  color: var(--fg-1);
  box-shadow: 0 12px 40px rgba(16, 26, 36, .22);
}
dialog.modal::backdrop { background: rgba(13, 26, 39, .45); }
dialog.modal.modal-wide { width: min(880px, calc(100vw - 32px)); }
dialog.modal .modal-head {
  display: flex; align-items: flex-start; justify-content: space-between;
  gap: var(--sp-4);
  padding: 16px 20px 14px;
  border-bottom: 1px solid var(--border-1);
  margin: 0;
}
dialog.modal .modal-title { margin: 0; font-size: 15px; font-weight: 600; padding-right: 0; }
dialog.modal .modal-sub { margin: 4px 0 0; font-size: 11.5px; color: var(--fg-3); line-height: 1.5; }
dialog.modal .modal-head > form { margin: 0; flex: none; }
dialog.modal .modal-x { padding: 4px 8px; line-height: 1; }
dialog.modal .modal-body {
  display: grid; grid-template-columns: repeat(2, minmax(0, 1fr));
  gap: 12px 14px;
  padding: 18px 20px;
}
dialog.modal .modal-body > .field { margin: 0; }
/* 긴 텍스트·체크박스 묶음은 1열 전체 폭 (지시서 §5) */
dialog.modal .modal-body > .field:has(textarea),
dialog.modal .modal-body > .row,
dialog.modal .modal-body > .card,
dialog.modal .modal-body > .modal-foot,
dialog.modal .modal-body > .zone-list,
dialog.modal .modal-body > label.row { grid-column: 1 / -1; }
dialog.modal .modal-foot {
  display: flex; justify-content: flex-end; gap: 8px; align-items: center;
  margin: 4px 0 0; padding-top: 14px;
  border-top: 1px solid var(--border-1);
}
dialog.modal .modal-body > form { grid-column: 1 / -1; }


/* ============================================================
   선급 상세 §4.8 — 단계 행 · 배지 · 좌우 1.35fr/1fr
   ============================================================ */
.grid-135 { display: grid; grid-template-columns: minmax(0, 1.35fr) minmax(0, 1fr); gap: 14px; align-items: start; }
.back-link { font-size: 11.5px; color: var(--fg-3); text-decoration: none; }
.back-link:hover { color: var(--brand-500); }
.cert-badge {
  display: inline-flex; align-items: center; justify-content: center;
  height: 26px; padding: 0 9px; border-radius: 6px;
  color: #fff; font-size: 12px; font-weight: 600;
}
.stage-list { display: flex; flex-direction: column; }
.stage-row {
  display: flex; align-items: center; gap: 11px;
  padding: 10px 16px;
  border-bottom: 1px solid var(--gray-100);
}
.stage-row:hover { background: var(--bg-app); }
.stage-body { display: flex; flex-direction: column; gap: 2px; min-width: 0; flex: 1; }
.stage-label { font-size: 12.5px; font-weight: 500; color: var(--fg-1); }
.stage-meta { font-size: 10px; color: var(--fg-3); }
.stage-note {
  padding: 11px 16px; border-top: 1px solid var(--border-1);
  background: var(--bg-app); font-size: 11px; color: var(--fg-3); line-height: 1.5;
}
.stage-form { display: grid; grid-template-columns: repeat(3, minmax(0, 1fr)); gap: 10px 12px; }
.stage-form .field { margin: 0; }
.stage-form .field-full, .stage-form .modal-foot { grid-column: 1 / -1; }
.stage-ev {
  grid-column: 1 / -1;
  border-top: 1px solid var(--border-1); padding-top: 14px;
  display: flex; flex-direction: column; gap: 10px;
}
.upload-drop {
  display: flex; flex-direction: column; align-items: center; gap: 4px;
  padding: 18px; border: 1.5px dashed var(--border-2); border-radius: 8px;
  background: var(--bg-app); cursor: pointer; text-align: center;
}
.upload-drop:hover { border-color: var(--brand-500); }
.upload-drop strong { font-size: 12.5px; color: var(--fg-1); }
.upload-ico { color: var(--fg-4); }

/* 리포트 보조 */
.rp-h2-sub { font-size: 10px; font-weight: 500; color: var(--fg-4); letter-spacing: .08em; }
.rp-note { font-size: 11px; color: var(--fg-3); line-height: 1.55; margin: 0 0 10px; }

@media (max-width: 1200px) {
  .grid-135 { grid-template-columns: minmax(0, 1fr); }
  .stage-form { grid-template-columns: minmax(0, 1fr); }
}
