/* ==========================================================================
   stop&loss — 공지사항 페이지(notice.html) 전용 스타일

   notice.html 이 이 파일을 싣고, 관리자 콘솔(admin/index.html)도 함께 싣는다 —
   콘솔의 '미리보기'가 홈페이지와 똑같은 본문 조판(.notice-body · .notice-detail-*)을
   쓰기 위해서다. 그래서 이 파일을 고칠 때는 두 화면을 함께 생각해야 한다.
   목록 · 필터 · 카드 규칙은 콘솔에 대상이 없어 아무 영향도 주지 않는다.

   ── 이름을 바꾸면 안 되는 것들 (가장 중요) ──
   아래 선택자는 static/notice.js 가 만들거나 찾는 요소와 일대일로 짝이다.
   이름을 바꾸면 오류 없이 조용히 스타일만 빠져 화면이 무너진다.
     .notice-shell / .notice-chip / .notice-cat-* / .notice-pin / .notice-new
     .notice-card(.is-pinned) / -head / -title / -summary / -foot
     .notice-date / .notice-more / .notice-more-arrow / .notice-truncated
     .notice-state(-title/-text) / .notice-skeleton(-row) / .notice-link
     .notice-detail / .notice-back / .notice-detail-tags / -title / -meta
     .notice-body / .notice-pager(-link.is-next / -label / -title)

   ── 왜 다시 만들었나 ──
   예전 화면은 다른 페이지와 똑같은 회색 머리띠(.page-hero) 아래 900px 한 칸에
   칩 줄과 카드를 세로로 늘어놓은 것이 전부였다. 목록이 길어지면 분류 칩이 화면
   밖으로 사라져 다른 분류로 옮기려면 매번 맨 위까지 올라가야 했고, 넓은 모니터
   에서는 양옆이 통째로 비었다.

   지금 구조
     .nt-hero        두 줄짜리 띠(약 120px) — 윗줄 이동 경로 · 라벨, 아랫줄 제목 / 설명
                     로그인과 같은 유체 엔진(static/fluid.js)이 물감을 그린다
     .notice-rail    분류 + 검색이 한 줄. 720px 이상에서 헤더 아래에 붙어 따라온다
     .notice-list    한 칸 피드. 카드 왼쪽에 타임라인 레일과 분류 색 점이 선다
     .notice-detail  상세. notice.js 가 목록과 자리를 바꾼다

   ── 폭은 .container 하나가 정한다 (2026-08 수정) ──
   헤더 · 히어로 · 하단 CTA 는 전부 style.css 의 .container(1140px)를 쓴다. 예전에는
   목록 셸만 880px, 상세만 820px 로 가운데 정렬해서 히어로 아래에서 한 번 좁아졌다가
   CTA 에서 다시 넓어지는 계단이 생겼다. 지금은 이 파일 어디에도 판의 max-width 가
   없고, 줄 길이는 글이 있는 두 곳(.notice-card-summary · .notice-detail .notice-body)
   에서만 ch 단위로 잡는다. 판의 폭과 글의 폭을 갈라 두는 것이 규칙이다 —
   여기에 max-width 를 되살리면 그 계단이 그대로 돌아온다.

   ── FAQ 와 무엇을 맞추고 무엇을 가르나 (2026-08-30 재정리) ──
   히어로는 맞춘다. 골격(윗줄 이동 경로 · 라벨 / 아랫줄 제목 | 설명) · 접히는 폭 ·
   칼럼 배분 · 라벨 모양이 저쪽과 같은 값이다. 예전에는 그 넷을 일부러 갈라
   두었는데, 그 때문에 제목이 시작하는 세로선이 페이지마다 밀려 두 화면을 오갈 때
   글이 좌우로 흔들렸다. 히어로에서 갈라야 할 것은 형태가 아니라 색이다.

   본문은 가른다. 저쪽은 찾아 들어가는 '인덱스'라 왼쪽에 고정 목차를 두고 2열로
   펴는 것이 맞고, 이쪽은 시간 순으로 훑어 내려가는 '피드'라 한 칸으로 흘리고
   위에 조작 줄 하나만 붙이는 것이 맞다.
     이쪽 — 가로 스캔라인 · 적색 · 세그먼트 분류 · 타임라인 · 고정폭 날짜
     저쪽 — 도트 매트릭스 · 청록 · 낱개 알약 목차 · 아코디언 · 고정폭 번호

   마우스 효과는 이제 히어로에서 같은 엔진을 쓴다 (2026-08-30)
     둘 다 로그인의 물감(static/fluid.js)이고 팔레트만 다르다 — 이쪽은 적이 앞에,
     저쪽은 청록이 앞에 선다. 예전의 '선과 눈금'(신호 트레이스)과 '원'(커서 렌즈)은
     지웠다. 목록 아래로는 여전히 다르다 — 이쪽은 레일 위의 마디와 카드의 1px
     세로 하이라인, 저쪽은 카드 위의 원형 스포트라이트다.
   본문 쪽 값을 서로 복사해 오지 말 것. 그렇게 해서 똑같아졌던 화면이다.

   색은 새로 만들지 않았다. 전부 style.css 토큰과 히어로 색분산 계열이다.
   분류 색은 '뜻'을 나른다 — 중요(적) · 점검(호박) · 업데이트(청록) · 일반(흰 계조).
   관리자 콘솔의 상태 배지와 같은 계열이라 두 화면에서 규칙이 하나다.
   ========================================================================== */

/* ---------- 1. 히어로 (가로 2열) ---------- */

/*
 * 눌러 놓은 히어로. 골격은 FAQ 와 같고 재질만 다르다.
 *   빛     오른쪽 위 적색이 주(主)  ← 저쪽은 왼쪽 위 청록
 *   질감   가로 스캔라인            ← 저쪽은 도트 매트릭스
 *   물감   적이 앞에 선 팔레트      ← 저쪽은 청록이 앞에 선다 (엔진은 같다)
 *   이음매 오른쪽에서 밝다          ← 저쪽은 왼쪽에서 밝다
 *
 * 세 번 줄였다. ① 가운데 축에 세로로 쌓아 480px, ② 눕히면서 오른쪽에 분류
 * 상태판을 세워 190px, ③ 그 판을 들어내고 두 줄짜리 띠로 눌러 약 120px
 * (데스크톱 실측 — 처음의 4분의 1).
 *
 * 지금 구조 — 900px 이상에서 격자 두 줄.
 *   'meta  meta'    이동 경로 · NOTICE 라벨 (한 줄을 통째로)
 *   'title lead'    제목  |  한 줄 설명
 *
 * 라벨을 제목 옆이 아니라 윗줄에 두는 이유는 1-c절에 적었다.
 */
.nt-hero {
  position: relative;
  isolation: isolate;
  overflow: hidden;
  padding: 22px 0 20px;
  background: var(--bg);
}

/*
 * 아래 경계선. 오른쪽(상태판 쪽)에서 가장 밝다 — FAQ 는 왼쪽에서 밝다.
 * 두 페이지를 연달아 보면 이 한 줄의 방향만으로도 화면이 바뀐 것을 알아챈다.
 */
.nt-hero::after {
  content: '';
  position: absolute;
  left: 0;
  right: 0;
  bottom: 0;
  z-index: 3;
  height: 1px;
  background: linear-gradient(90deg,
    transparent,
    rgba(255, 255, 255, .06) 38%,
    rgba(255, 255, 255, .12) 66%,
    rgba(255, 45, 92, .5));
}

.nt-hero-bg {
  position: absolute;
  inset: 0;
  z-index: 0;
  pointer-events: none;
}

.nt-hero-bg > span {
  position: absolute;
  inset: 0;
  display: block;
}

/*
 * 빛은 오른쪽 위 적색이 주(主)다. 공지는 '알림'이라 신호 색이 앞에 서는 편이
 * 성격에 맞고, 무엇보다 청록이 앞에 선 FAQ 와 첫인상이 갈린다.
 * blur() 대신 그라데이션의 투명 정지점만 쓰는 것은 저사양 PC 에서 프레임이
 * 떨어질 이유를 만들지 않기 위해서다(사이트 공통 규칙).
 */
.nt-hero-glow {
  background:
    radial-gradient(640px 360px at 88% -22%, rgba(255, 45, 92, .14), transparent 62%),
    radial-gradient(520px 300px at 6% 118%, rgba(61, 233, 255, .07), transparent 66%);
}

/*
 * 가로 스캔라인 — 이 페이지의 질감이다.
 *
 * 가로선인 이유: 이 화면의 모든 것이 가로로 쌓인다(조작 줄 · 카드 · 타임라인).
 * 배경이 같은 방향을 가리키면 목록이 아래로 이어진다는 인상이 강해진다.
 * FAQ 는 점을 뿌린다 — 두 페이지가 같은 배경을 깔지 않는다.
 *
 * 마스크를 오른쪽 위 모서리에 앉혀 아래 · 왼쪽으로 잦아들게 한다. 글자 뒤에서
 * 선이 진하게 남으면 읽는 데 방해가 된다.
 */
.nt-hero-lines {
  background-image: repeating-linear-gradient(to bottom,
    rgba(255, 255, 255, .05) 0 1px,
    transparent 1px 6px);
  -webkit-mask-image: radial-gradient(90% 130% at 100% 0%, #000 0%, rgba(0, 0, 0, .3) 44%, transparent 72%);
  mask-image: radial-gradient(90% 130% at 100% 0%, #000 0%, rgba(0, 0, 0, .3) 44%, transparent 72%);
}

/* ---------- 1-b. 물감 배경 (이 페이지의 마우스 효과) ---------- */

/*
 * 로그인 화면과 같은 유체 엔진(static/fluid.js)이 이 무대 안 캔버스에 물감을 그린다.
 * 커서를 따라 잉크가 번지고, 손을 멈추면 몇 초에 한 방울씩 스스로 피어난다.
 *
 * 여기에 있던 것 (2026-08-30 에 통째로 지웠다 — 되살리기 전에 읽을 것)
 *   눈금자 · 잔광 · 잔상 · 색분산 · 코어 · 접점, 여섯 겹짜리 '신호 트레이스'였다.
 *   커서 높이를 따라 가로 빔이 지나가고 이음매의 눈금이 그 둘레에서 드러났다.
 *   자주 묻는 질문의 '커서 렌즈'와 축을 갈라 두 화면을 구분하려던 장치인데,
 *   두 히어로를 모두 물감으로 바꾸면서 그 구분이 뜻을 잃었다. 물감 위에 다시
 *   얹으면 커서 둘레가 이중으로 밝아져 어느 쪽이 반응인지 읽히지 않는다.
 *
 * 자주 묻는 질문과 무엇이 다른가
 *   엔진은 같고 색만 다르다. 이쪽은 적(#ff2d5c)이 앞에 서고 저쪽은 청록(#3de9ff)이
 *   앞에 선다. 그 아래 깔린 질감도 다르다 — 이쪽은 가로 스캔라인, 저쪽은 도트
 *   매트릭스다. 두 값을 서로 복사해 오면 그 순간 두 페이지가 같은 화면이 된다.
 *
 * 캔버스가 배경을 덮지 않는다
 *   셰이더가 밝기에서 알파를 뽑아 내보내므로 물감이 없는 자리는 투명하게 남고,
 *   위 1절의 잔광 · 스캔라인이 그대로 비친다. WebGL 이 없거나 셰이더가 실패하면
 *   캔버스는 통째로 투명하게 남는다 — 효과만 사라지고 화면은 지금 모습 그대로다.
 */
.nt-hero-stage {
  position: absolute;
  inset: 0;
  z-index: 1;
  /* 커서는 히어로 <section> 이 받는다(notice-scan.js). 이 겹이 이벤트를 먹으면
     그 아래 이동 경로를 누를 수 없게 된다. */
  pointer-events: none;
}

.nt-hero-canvas {
  position: absolute;
  inset: 0;
  width: 100%;
  height: 100%;
  /*
   * 위아래 끝을 흘려보낸다.
   *
   * 히어로가 120px 짜리 띠라 마스크가 없으면 물감이 헤더 밑선과 아래 이음매에
   * 칼로 자른 듯 끊긴다 — 배경이 아니라 '띠 하나가 얹힌' 것으로 보인다.
   * 좌우는 셰이더의 가장자리 감쇠가 이미 맡고 있어 여기서 건드리지 않는다.
   */
  -webkit-mask-image: linear-gradient(to bottom, transparent, #000 20%, #000 80%, transparent);
  mask-image: linear-gradient(to bottom, transparent, #000 20%, #000 80%, transparent);
  opacity: 0;
  transition: opacity .9s ease;
}

/* 첫 프레임이 실제로 나온 뒤에만 드러낸다(fluid.js 가 무대에 is-live 를 단다).
   미리 켜면 빈 사각형이 한 번 번쩍인다 — 로그인 화면과 같은 규칙이다. */
.nt-hero-stage.is-live .nt-hero-canvas { opacity: 1; }

/*
 * 가독성 베일. 이 한 겹이 없으면 물감이 가장 진해지는 순간 그 자리의 글자가
 * 읽히지 않는다 — 로그인은 카드가 어두운 유리라 그 일을 대신하지만, 여기서는
 * 제목과 설명이 배경 위에 바로 앉는다.
 *
 * 물감의 세기(fluid 옵션의 gain · 감쇠)와 한 묶음이다. 이 값을 낮추려면
 * static/notice-scan.js 의 gainMax 도 함께 낮춰야 대비가 유지된다.
 */
.nt-hero-veil {
  position: absolute;
  inset: 0;
  background: rgba(4, 4, 7, .38);
}

/* ---------- 1-c. 히어로 배치 ---------- */

/*
 * 자주 묻는 질문(.fq-hero-inner)과 같은 골격이다 — 2026-08-30에 맞췄다.
 *   'meta'   이동 경로 · NOTICE 라벨
 *   'title'  제목
 *   'lead'   한 줄 설명
 * 900px 부터 아래 두 줄이 좌우로 접힌다(13절).
 *
 * 예전에는 라벨을 제목과 같은 줄에 세우고(.nt-hero-head) 이동 경로가 윗줄을
 * 통째로 썼다. 저쪽과 첫 줄부터 갈라 보이게 하려던 배치인데, 그 때문에 제목이
 * 시작하는 세로선이 라벨 폭만큼 밀려 두 페이지를 오갈 때 글이 좌우로 흔들렸다.
 * 라벨을 윗줄로 올리면 제목 · 설명 · 아래 본문이 모두 같은 세로선에서 시작한다.
 * .nt-hero-head 와 .nt-badge 는 그래서 지웠다 — 되살리면 그 흔들림도 돌아온다.
 */
.nt-hero-inner {
  position: relative;
  z-index: 2;
  display: grid;
  grid-template-columns: minmax(0, 1fr);
  grid-template-areas:
    'meta'
    'title'
    'lead';
  gap: 10px 44px;
  /*
   * 검정 배경에서는 보이지 않는다. 물감이 글자 뒤를 지날 때만 일한다 —
   * 베일(1-b절)만으로는 잉크가 가장 진해지는 순간의 대비가 모자란다.
   * 상속되므로 이동 경로 · 라벨 · 제목 · 설명이 한 줄로 함께 받는다
   * (요금제 히어로가 셰이더 위에서 쓰는 것과 같은 수법이다).
   */
  text-shadow: 0 1px 14px rgba(4, 4, 7, .85);
}

/* 이동 경로와 라벨이 한 줄에 선다. 글자 열한 자 때문에 22px 을 더 쓰는 것은
   두 줄짜리 띠에서 가장 아까운 높이다. */
.nt-hero-meta {
  grid-area: meta;
  display: flex;
  align-items: center;
  flex-wrap: wrap;
  gap: 6px 12px;
  min-width: 0;
}

/* 왼쪽 정렬로 되돌린다. 가운데 정렬은 축이 하나였던 시절의 값이다. */
.nt-crumb { justify-content: flex-start; }

/*
 * 영문 라벨 — 고정폭 글자에 왼쪽 머리카락 선.
 *
 * 예전에는 채워진 알약(.nt-badge)이었다. 라벨이 제목 옆에 설 때는 그 무게가
 * 맞았지만, 이동 경로 옆으로 올라오면 알약 하나만 배경이 채워져 그 줄에서
 * 혼자 튄다. 자주 묻는 질문(.fq-eyebrow)과 같은 틀을 쓰되 점 색만 이 페이지의
 * 적색이다 — 두 화면을 가르는 것은 이제 형태가 아니라 색이다.
 */
.nt-eyebrow {
  display: inline-flex;
  align-items: center;
  gap: 8px;
  padding-left: 12px;
  border-left: 1px solid var(--border);
  color: var(--muted);
  font-family: var(--font-mono);
  font-size: 10.5px;
  font-weight: 600;
  letter-spacing: .22em;
}

.nt-eyebrow i {
  flex: 0 0 auto;
  width: 5px;
  height: 5px;
  border-radius: 50%;
  background: var(--danger);
  box-shadow: 0 0 0 3px rgba(255, 92, 122, .16);
}

/*
 * 흰색이 아래로 잦아드는 결. style.css 의 .text-gradient 와 같은 문법이다.
 *
 * 기본값은 흰 글자이고 그라데이션은 @supports 안에서만 켠다. 순서를 뒤집으면
 * background-clip: text 를 모르는 브라우저에서 color: transparent 만 적용되어
 * 제목이 통째로 사라진다.
 */
.nt-title {
  grid-area: title;
  min-width: 0;
  /* 자주 묻는 질문과 같은 값이다. 제목이 한 줄로 서야 띠가 두 줄로 끝난다 —
     상한을 44 로 되돌리면 900~1100px 구간에서 두 줄로 꺾인다(실측). */
  font-size: clamp(26px, 5.2vw, 38px);
  font-weight: 700;
  line-height: 1.14;
  letter-spacing: -.04em;
  color: #fff;
}

@supports ((-webkit-background-clip: text) or (background-clip: text)) {
  .nt-title {
    background: linear-gradient(180deg, #fff 30%, rgba(255, 255, 255, .62));
    -webkit-background-clip: text;
    background-clip: text;
    color: transparent;
  }
}

.nt-lead {
  grid-area: lead;
  /* 46ch 는 오른쪽 칸이 900px 에서 갖는 폭과 거의 같다. 더 넓게 두면 설명이
     제목 쪽으로 흘러가 두 칸의 경계가 흐려진다(자주 묻는 질문과 같은 값). */
  max-width: 46ch;
  color: var(--muted);
  font-size: 14px;
  line-height: 1.7;
}

.nt-lead b { color: var(--text-soft); font-weight: 600; }

/*
 * 여기에 있던 분류 상태판(.nt-board · .nt-legend · .nt-dot-*)은 통째로 지웠다.
 *
 * 그 판이 설명하던 네 분류는 바로 아래 조작 줄의 칩(.notice-chip)에도 그대로 있고,
 * 색이 무엇을 뜻하는지는 카드의 배지(.notice-cat-*)와 타임라인 점이 이미 말한다.
 * 같은 것을 세 곳에서 말하면서 히어로만 190px 이 됐고, 정작 이 페이지에서 할 일
 * (공지를 찾아 읽는 것)이 그만큼 아래로 밀렸다.
 *
 * 되살리려거든 먼저 그 높이부터 재 볼 것. 색 설명이 정말 필요하다면 히어로가 아니라
 * 조작 줄 옆이 제자리다 — 분류를 고르는 순간에 읽히는 자리여야 뜻이 있다.
 */

/* ---------- 2. 셸 (한 칸 피드) ---------- */

.nt-main { padding: 26px 0 72px; }

/*
 * 왼쪽 고정 목차를 두지 않는다.
 *
 * 자주 묻는 질문은 '찾아 들어가는' 화면이라 목차가 늘 떠 있어야 하지만, 공지는
 * 시간 순으로 훑어 내려가며 읽는 화면이다. 목차에 244px 을 내주면 정작 읽을 카드가
 * 그만큼 좁아지고, 분류가 다섯 개뿐이라 그 폭을 세로로 쓸 이유도 없다.
 * 대신 분류와 검색을 한 줄(.notice-rail)로 묶어 위에 붙인다.
 *
 * ── 폭 상한을 두지 않는다 (2026-08 수정) ──
 * 예전에는 여기에 max-width: 880px + margin: 0 auto 가 있었다. 그런데 이 문서에서
 * 폭을 정하는 요소가 셋(헤더 · 히어로 · 하단 CTA)이고 그 셋은 전부 style.css 의
 * .container(1140px)를 쓴다. 목록만 880px 로 좁혀 가운데 정렬하면 좌우가 113px 씩
 * 안으로 들어가, 히어로 아래에서 한 번 좁아졌다가 CTA 에서 다시 넓어지는 계단이
 * 생긴다(사용자 지적 · 스크린샷). 한 페이지에 세로선이 두 벌 있으면 어느 쪽이
 * 기준인지 알 수 없고, 화면은 '디자인'이 아니라 '고장'으로 읽힌다.
 *
 * 그래서 폭은 .container 하나가 정하고, 여기서는 상한을 두지 않는다. 대신 줄 길이는
 * '글이 있는 곳'에서만 잡는다 — 카드 미리보기(.notice-card-summary)와 상세 본문
 * (.notice-detail .notice-body)에 각각 ch 단위 상한이 있다. 판의 폭과 글의 폭을
 * 갈라 두면, 판은 헤더와 같은 선에 서면서도 한 줄이 90자를 넘지 않는다.
 *
 * 다시 max-width 를 걸고 싶어지면 헤더 · 히어로 · CTA 에도 같은 값을 함께 걸 것.
 * 한 곳만 좁히면 그때 그 계단이 그대로 돌아온다.
 *
 * scroll-margin-top 은 notice.js 의 scrollToShell 을 위한 값이다. 없으면
 * 목록 ↔ 상세를 오갈 때마다 셸 윗부분이 고정 헤더 뒤로 들어가 잘린다.
 */
.notice-shell {
  scroll-margin-top: calc(var(--header-h) + 16px);
}

/* notice.js 가 hidden 속성으로 목록과 상세의 자리를 바꾼다.
   여기에 display 를 주면 그 전환이 죽으므로 절대 주지 말 것. */
.notice-list-view[hidden] { display: none; }

/* ---------- 3. 조작 줄 (분류 + 검색) ---------- */

/*
 * 분류와 검색이 한 줄에 산다.
 *
 * 720px 부터 헤더 아래에 붙어 따라온다. 그보다 좁으면 붙이지 않는다 —
 * 헤더 64px + 이 줄(두 단으로 접힌다)이면 세로가 짧은 휴대폰에서 화면의
 * 3분의 1이 늘 조작 막대로 차 버린다.
 */
.notice-rail {
  position: relative;
  z-index: 10;
  display: grid;
  gap: 10px;
  padding: 14px 0 12px;
  background: var(--bg);
}

/* 카드가 밑으로 지나갈 때 경계가 딱 잘리지 않게 하는 12px 짜리 페이드. */
.notice-rail::after {
  content: '';
  position: absolute;
  left: 0;
  right: 0;
  bottom: -12px;
  height: 12px;
  pointer-events: none;
  background: linear-gradient(to bottom, var(--bg), transparent);
}

/*
 * 분류 — 낱개 알약이 아니라 한 덩어리(세그먼트) 컨트롤이다.
 *
 * FAQ 의 목차와 다른 물건이다. 저쪽은 넓은 화면에서 세로로 서는 '목차'이고
 * 이쪽은 폭과 상관없이 한 줄에 붙어 서는 '탭'이다 — 다섯 개가 전부이고 늘어날
 * 일이 없으므로 한 틀 안에 가두는 편이 무엇을 고를 수 있는지 한눈에 보인다.
 *
 * notice.js 는 .notice-chip 과 data-category 만 알고 있으면 된다. 이 파일이
 * 바꾼 것은 겉모습뿐이라 그쪽 코드는 한 줄도 손대지 않았다.
 */
.notice-filters {
  display: flex;
  gap: 2px;
  min-width: 0;
  padding: 3px;
  background: rgba(255, 255, 255, .03);
  border: 1px solid var(--border);
  border-radius: 9999px;
  overflow-x: auto;
  scrollbar-width: none;
  -webkit-overflow-scrolling: touch;
}

.notice-filters::-webkit-scrollbar { display: none; }

/* flex: 1 0 auto — 넓으면 남는 폭을 고르게 나눠 갖고, 좁으면 내용 폭을 지키며
   가로로 흐른다. 0 으로 두면 넓은 화면에서 다섯 개가 왼쪽에만 뭉친다. */
.notice-chip {
  display: inline-flex;
  align-items: center;
  justify-content: center;
  flex: 1 0 auto;
  min-height: 36px;
  padding: 6px 16px;
  background: transparent;
  border: 0;
  border-radius: 9999px;
  color: var(--muted);
  font-size: 13.5px;
  font-weight: 600;
  white-space: nowrap;
  transition: color var(--ease), background var(--ease);
}

.notice-chip:hover { color: #fff; background: rgba(255, 255, 255, .05); }

/* 고른 쪽은 밝은 유리다. 흰 알약(FAQ 의 칩)은 이 줄에서 너무 크게 소리친다 —
   세그먼트 안이라 '지금 여기'가 위치로 이미 드러난다. */
.notice-chip.is-active {
  background: rgba(255, 255, 255, .12);
  color: #fff;
  box-shadow: inset 0 0 0 1px rgba(255, 255, 255, .07);
}

/* ---------- 4. 검색 ---------- */

/* 조작 줄 안에 들어가므로 FAQ 의 검색창(48px 전폭 알약)보다 한 단계 작다.
   같은 크기로 두면 이 줄만 두 배로 두꺼워져 목록이 그만큼 밀린다. */
.notice-search {
  position: relative;
  display: block;
}

.notice-search .input {
  width: 100%;
  min-height: 44px;
  padding: 10px 16px 10px 40px;
  border-radius: 9999px;
  font-size: 14.5px;
}

.notice-search .input:focus {
  border-color: rgba(61, 233, 255, .55);
  box-shadow: 0 0 0 3px rgba(61, 233, 255, .12);
}

.notice-search-icon {
  position: absolute;
  top: 50%;
  left: 14px;
  transform: translateY(-50%);
  width: 15px;
  height: 15px;
  pointer-events: none;
  background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 16 16'%3E%3Ccircle cx='7' cy='7' r='4.6' fill='none' stroke='%23ffffff' stroke-opacity='.45' stroke-width='1.6'/%3E%3Cpath d='M10.6 10.6 14 14' fill='none' stroke='%23ffffff' stroke-opacity='.45' stroke-width='1.6' stroke-linecap='round'/%3E%3C/svg%3E");
  background-repeat: no-repeat;
  background-position: center;
  background-size: 15px 15px;
}

/* ---------- 5. 개수 · 안내 줄 ---------- */

.notice-meta {
  margin-bottom: 14px;
  color: var(--muted);
  font-size: 13px;
  line-height: 1.65;
}

.notice-meta b { color: var(--text-soft); font-weight: 600; }

/* 목록이 상한에 걸려 잘렸을 때만 나타난다.
   개수 줄과 같은 회색으로 두면 그냥 안내문으로 읽혀 지나친다 — 이 줄만 색이
   달라야 '이 목록이 전부가 아니다'가 눈에 걸린다. */
.notice-truncated {
  display: block;
  margin-top: 8px;
  padding: 8px 12px;
  background: rgba(255, 196, 77, .07);
  border: 1px solid rgba(255, 196, 77, .28);
  border-radius: var(--radius-sm);
  color: #ffd98a;
  font-size: 12.5px;
  line-height: 1.6;
}

/* ---------- 6. 목록 (타임라인) ---------- */

/*
 * 카드를 그냥 늘어놓는 대신 왼쪽에 레일을 세우고 카드마다 점을 찍는다.
 *
 * 공지는 시간 순으로 쌓이는 기록이라 그 순서가 형태로 보여야 한다 — 자주 묻는
 * 질문의 아코디언 목록과 이 화면이 갈리는 지점이 여기다. 점은 분류 색을 그대로
 * 받으므로, 배지 글자를 읽지 않고 훑기만 해도 중요 · 점검이 어디 있는지 보인다.
 *
 * :has() 로 감싸는 이유
 *   #noticeList 안에는 카드 말고도 뼈대(.notice-skeleton)와 안내(.notice-state)가
 *   들어온다. 레일을 무조건 그리면 '공지가 없습니다' 판 옆에 선이 혼자 서 있게 된다.
 *   :has() 를 모르는 브라우저에서는 레일과 점이 통째로 빠지고 카드만 남는다 —
 *   기능은 그대로이므로 그 정도 물러섬이면 충분하다.
 */
.notice-list {
  display: grid;
  gap: 12px;
  /* 레일 위 빛의 높이. static/notice-scan.js 가 CSSOM 으로 갱신한다.
     기본값이 0 이라 스크립트가 없으면 빛은 맨 위에 놓인 채 투명하게 남는다. */
  --nt-rail-y: 0px;
}

.notice-list:has(.notice-card) {
  position: relative;
  padding-left: 28px;
}

/* 위아래 끝을 투명으로 흘린다. 선이 첫 카드 위와 마지막 카드 아래에서 뚝 끊기면
   목록이 거기서 끝났다는 뜻으로 읽힌다. */
.notice-list:has(.notice-card)::before {
  content: '';
  position: absolute;
  left: 5px;
  top: 18px;
  bottom: 18px;
  width: 1px;
  background: linear-gradient(to bottom,
    transparent, var(--border) 6%, var(--border) 94%, transparent);
}

/*
 * 레일 위의 점. 좌표는 위 padding-left(28) · 레일 left(5)와 한 묶음이다 —
 * 셋 중 하나만 바꾸면 점이 선에서 벗어난다. 지금 값은 점 중심 5.5px 로
 * 레일 중심(5.5px)과 정확히 겹친다.
 *
 * box-shadow 로 배경색 테를 두르는 이유: 선이 점 뒤로 지나가면 점이 아니라
 * 매듭처럼 보인다. 배경색으로 그 자리만 지운다.
 */
.notice-list:has(.notice-card) .notice-card::before {
  content: '';
  position: absolute;
  left: -27px;
  top: 24px;
  width: 9px;
  height: 9px;
  border-radius: 50%;
  background: var(--surface-2);
  box-shadow: 0 0 0 3px var(--bg);
  transition: background var(--ease);
}

/* 분류 색을 점으로 옮긴다. 배지는 카드 안에 있어서 색이 카드 안에 갇히는데,
   점은 레일 위에 있어 목록 전체를 세로로 훑을 때 한 줄로 읽힌다. */
.notice-list:has(.notice-card) .notice-card:has(.notice-cat-important)::before   { background: var(--danger); }
.notice-list:has(.notice-card) .notice-card:has(.notice-cat-maintenance)::before { background: var(--warn); }
.notice-list:has(.notice-card) .notice-card:has(.notice-cat-update)::before      { background: var(--primary); }
.notice-list:has(.notice-card) .notice-card:has(.notice-cat-general)::before     { background: rgba(255, 255, 255, .45); }

/*
 * 레일 위를 흐르는 빛 — 히어로의 빔이 목록으로 이어지는 자리다.
 *
 * 히어로에서는 가로 빔이 '세로로' 움직였고, 여기서는 세로 레일 위의 빛이 커서를
 * 따라 '세로로' 흐른다. 축이 같으므로 히어로에서 목록으로 시선을 옮겨도 같은
 * 신호가 계속 흐르는 것처럼 읽힌다 — FAQ 는 이 자리에서 원형 스포트라이트를 쓴다.
 *
 * 위치가 위 레일(::before)과 한 묶음이다. left 값이 어긋나면 빛만 선 옆으로
 * 비껴 흐른다 — 좁은 화면 규칙(13절)에서도 둘을 함께 옮겨야 한다.
 *
 * 절대 배치라 격자 항목이 되지 않는다. 목록 칸을 하나 더 만들지 않는다는 뜻이다.
 */
.notice-list:has(.notice-card)::after {
  content: '';
  position: absolute;
  left: 5px;
  top: 0;
  width: 1px;
  height: 148px;
  margin-top: -74px;
  pointer-events: none;
  /* top 을 매 프레임 바꾸면 레이아웃부터 다시 계산된다. 히어로의 트레이스와 같은
     이유로 transform 만 쓴다(1-b절 주석). */
  transform: translate3d(0, var(--nt-rail-y), 0);
  /* 가운데의 흰 점이 이 빛을 '띠'가 아니라 '지나가는 마디'로 읽히게 한다.
     히어로가 물감으로 바뀐 지금, 커서를 '점'으로 따라가는 표현은 이 목록에만 남았다. */
  background: linear-gradient(to bottom,
    transparent,
    rgba(61, 233, 255, .28) 22%,
    rgba(61, 233, 255, .85) 44%,
    #fff 50%,
    rgba(61, 233, 255, .85) 56%,
    rgba(61, 233, 255, .28) 78%,
    transparent);
  box-shadow: 0 0 10px rgba(61, 233, 255, .45);
  opacity: 0;
  transition: opacity .3s ease;
}

/* 마우스가 목록 안에 있을 때만 켜진다. 터치 기기에서는 notice-scan.js 가 아예
   붙지 않으므로 이 클래스가 달리는 일이 없다. */
.notice-list.is-tracing:has(.notice-card)::after { opacity: .9; }

/*
 * 카드 전체가 링크다(<a href="?id=N">).
 *
 * 제목만 링크로 두면 손가락으로 누를 표적이 한 줄뿐이라 모바일에서 계속 빗나간다.
 * <a> 를 쓰는 덕에 키보드 이동 · 가운데 클릭(새 탭) · 링크 복사가 전부 공짜로 된다 —
 * div + onclick 이었다면 셋 다 직접 만들어야 하고, 대개 하나를 빠뜨린다.
 */
.notice-card {
  display: block;
  position: relative;
  /* 카드 안 커서 좌표. static/notice-scan.js 가 CSSOM 으로 넣는다.
     기본값이 가운데라, 스크립트가 없으면 호버 시 카드 한가운데가 은은히 밝아진다 —
     효과가 사라질 뿐 화면이 깨지지 않는다. */
  --nt-cx: 50%;
  --nt-cy: 50%;
  padding: 18px 20px;
  background: var(--surface);
  border: 1px solid var(--border);
  border-radius: var(--radius-md);
  transition: border-color var(--ease), background var(--ease);
}

/*
 * 커서를 따라가는 카드 안의 계측 커서.
 *
 * 겹이 둘이다 — 커서 자리에 서는 1px 세로 하이라인, 그리고 그 뒤에 고이는 납작한
 * 빛. 하이라인이 히어로의 눈금자와 같은 말을 하고(계측기), 빛이 카드를 띄운다.
 * 예전에는 빛 하나뿐이라 '어딘가 밝아졌다'로만 읽혔다.
 *
 * FAQ 의 카드는 원형 스포트라이트에 테두리 빛이다 — 두 페이지가 히어로에서 갈린
 * 원 · 선의 축을 본문까지 끝까지 지킨다. 한쪽 값을 다른 쪽에 복사해 오지 말 것.
 *
 * 세로 마스크가 하이라인의 위아래 끝을 흘려 보낸다. 이게 없으면 1px 선이 카드
 * 테두리에 딱 닿아, 커서가 아니라 카드가 두 쪽으로 갈린 것처럼 보인다.
 * mask 를 모르는 브라우저에서는 선이 끝까지 닿을 뿐 다른 문제가 없다.
 *
 * 카드에 overflow: hidden 이 없으므로 모서리를 직접 깎는다. inherit 를 쓰지 않는
 * 이유는 좁은 화면에서 padding 만 바뀌고 반지름은 그대로이기 때문이다.
 */
.notice-card::after {
  content: '';
  position: absolute;
  inset: 0;
  z-index: 0;
  border-radius: var(--radius-md);
  pointer-events: none;
  background:
    linear-gradient(90deg,
      transparent calc(var(--nt-cx) - 1px),
      rgba(61, 233, 255, .45) calc(var(--nt-cx) - .5px),
      rgba(61, 233, 255, .45) calc(var(--nt-cx) + .5px),
      transparent calc(var(--nt-cx) + 1px)),
    radial-gradient(300px 150px at var(--nt-cx) var(--nt-cy),
      rgba(255, 255, 255, .075), transparent 72%);
  -webkit-mask-image: linear-gradient(to bottom, transparent, #000 16%, #000 84%, transparent);
  mask-image: linear-gradient(to bottom, transparent, #000 16%, #000 84%, transparent);
  opacity: 0;
  transition: opacity .25s ease;
}

.notice-card:hover::after,
.notice-card:focus-visible::after { opacity: 1; }

/* 빛은 배치된 겹이라 정적인 카드 내용보다 위에 그려진다. 내용에도 자리를 줘서
   위로 올린다 — 이 세 줄이 없으면 제목과 미리보기가 빛 아래로 깔려 흐려 보인다. */
.notice-card-head,
.notice-card-summary,
.notice-card-foot { position: relative; z-index: 1; }

/*
 * 호버에 떠오르지 않는다(translateY 없음).
 *
 * 점이 카드의 자식이라 카드가 뜨면 점도 함께 떠서 레일에서 벗어난다 — 선 위의
 * 매듭이 하나만 어긋난 것처럼 보인다. 테두리와 배경만 밝히는 편이 이 화면에 맞고,
 * 시간 순으로 훑어 내려가는 목록에서는 그 정도가 조용해서 좋다.
 */
.notice-card:hover {
  border-color: rgba(255, 255, 255, .26);
  background: rgba(255, 255, 255, .03);
}

/*
 * 고정 공지.
 *
 * 예전에는 왼쪽에 2px 선을 세웠는데, 그 자리에 타임라인 레일이 생기면서 선이
 * 두 줄로 겹쳐 보인다. 판을 아주 옅게 물들이고 점에 테를 둘러 대신한다 —
 * 검색으로 걸러 순서가 흐트러져도 이 글이 상단 고정이라는 사실이 남는다.
 *
 * 이 두 규칙은 반드시 위 분류 색 규칙보다 뒤에 있어야 한다. 선택자 무게가 같아
 * 순서로 이긴다 — 앞으로 옮기면 고정 공지의 점이 분류 색으로 덮인다.
 */
.notice-card.is-pinned {
  background: rgba(61, 233, 255, .045);
  border-color: rgba(61, 233, 255, .22);
}

.notice-card.is-pinned:hover {
  background: rgba(61, 233, 255, .08);
  border-color: rgba(61, 233, 255, .4);
}

.notice-list:has(.notice-card) .notice-card.is-pinned::before {
  background: var(--primary);
  box-shadow: 0 0 0 3px var(--bg), 0 0 0 4.5px rgba(61, 233, 255, .38);
}

.notice-card-head {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 8px;
  margin-bottom: 9px;
}

.notice-card-title {
  color: var(--text);
  font-size: 16.5px;
  font-weight: 700;
  letter-spacing: -.01em;
  line-height: 1.5;
  transition: color var(--ease);
}

.notice-card:hover .notice-card-title { color: #fff; }

/* 미리보기는 두 줄까지. 세 줄을 넘어가면 카드가 아니라 본문이 되어,
   목록을 훑는 동안 어느 글이 어디서 끝나는지 알 수 없게 된다.

   줄 길이 상한은 판(.notice-shell)이 아니라 여기에 둔다. 판은 헤더 · 히어로 · CTA 와
   같은 선에 서야 하고(2절 주석), 글은 90자를 넘으면 눈이 다음 줄 첫 글자를 못 찾는다.
   76ch 는 14px 기준 약 700px 로, 예전 880px 판에서 이 글이 갖던 폭과 거의 같다 —
   판만 넓어지고 읽는 느낌은 그대로다. */
.notice-card-summary {
  max-width: 76ch;
  margin-top: 6px;
  color: var(--muted);
  font-size: 14px;
  line-height: 1.7;
  display: -webkit-box;
  -webkit-line-clamp: 2;
  -webkit-box-orient: vertical;
  overflow: hidden;
}

.notice-card-foot {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 8px 14px;
  margin-top: 12px;
  padding-top: 11px;
  border-top: 1px solid var(--border);
}

/* 고정폭 날짜 스탬프. 자릿수가 같은 글꼴이라야 카드를 세로로 훑을 때 날짜가
   같은 자리에 서고, 기록물이라는 인상도 그 글꼴이 만든다 —
   FAQ 의 같은 자리에는 고정폭 '번호'가 선다. 두 페이지가 갈리는 작은 축이다. */
.notice-date {
  color: rgba(255, 255, 255, .45);
  font-family: var(--font-mono);
  font-size: 12px;
  letter-spacing: -.01em;
  font-variant-numeric: tabular-nums;
}

/* '자세히 보기'는 오른쪽 끝에 붙는다. 화살표만 호버에 움직여, 카드 전체가
   눌리는 것이라는 사실을 글자를 읽지 않고도 알 수 있게 한다. */
.notice-more {
  display: inline-flex;
  align-items: center;
  gap: 5px;
  margin-left: auto;
  color: var(--primary);
  font-size: 12.5px;
  font-weight: 700;
}

.notice-more-arrow {
  width: 12px;
  height: 12px;
  background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 14 14'%3E%3Cpath d='M2 7h9.5M7.5 3 11.5 7l-4 4' fill='none' stroke='%233de9ff' stroke-width='1.7' stroke-linecap='round' stroke-linejoin='round'/%3E%3C/svg%3E");
  background-repeat: no-repeat;
  background-position: center;
  background-size: 12px 12px;
  transition: transform var(--ease);
}

.notice-card:hover .notice-more-arrow { transform: translateX(3px); }

/* ---------- 7. 배지 ---------- */

/* style.css 의 .tag 와 값이 비슷하지만 이름을 따로 둔다. 저쪽은 사이트 공용이라
   여기서 크기나 색을 바꾸면 전략 카드 · 관리자 화면까지 함께 움직인다. */
.notice-cat {
  padding: 3px 10px;
  border-radius: 9999px;
  font-size: 11.5px;
  font-weight: 800;
  letter-spacing: .01em;
  white-space: nowrap;
}

.notice-cat-important   { background: rgba(255, 92, 122, .14); color: var(--danger); }
.notice-cat-maintenance { background: rgba(255, 196, 77, .14); color: var(--warn); }
.notice-cat-update      { background: rgba(61, 233, 255, .13); color: var(--primary); }
.notice-cat-general     { background: rgba(255, 255, 255, .08); color: var(--text-soft); }

/* 상단 고정 표시. 분류와 나란히 서지만 성격이 달라(분류는 '무엇' · 고정은 '어디')
   테두리만 있는 빈 알약으로 둔다 — 색 배지가 둘 나란히 있으면 어느 쪽이
   분류인지 매번 다시 읽어야 한다. */
.notice-pin {
  display: inline-flex;
  align-items: center;
  gap: 4px;
  padding: 2px 9px;
  border: 1px solid rgba(255, 255, 255, .22);
  border-radius: 9999px;
  color: var(--text-soft);
  font-size: 11px;
  font-weight: 700;
  white-space: nowrap;
}

/* 최근 글 표시. 날짜를 읽어 계산하지 않아도 새 글이 눈에 걸리게 한다.
   글자 없이 점만 쓰는 이유는 배지가 셋 이상 늘어서면 제목이 밀려나기 때문이다.
   (뜻은 title 속성과 안쪽의 .sr-only 글자가 나른다 — notice.js 가 함께 넣는다.) */
.notice-new {
  display: inline-block;
  width: 6px;
  height: 6px;
  border-radius: 50%;
  background: var(--primary);
  box-shadow: 0 0 0 3px rgba(61, 233, 255, .16);
}

/* ---------- 8. 상태 표시 (로딩 · 없음 · 오류) ---------- */

.notice-state {
  display: grid;
  gap: 10px;
  place-items: center;
  padding: 52px 24px;
  background: var(--surface);
  border: 1px solid var(--border);
  border-radius: var(--radius-lg);
  text-align: center;
}

.notice-state-title {
  color: var(--text);
  font-size: 15.5px;
  font-weight: 700;
}

.notice-state-text {
  max-width: 460px;
  color: var(--muted);
  font-size: 14px;
  line-height: 1.7;
}

.notice-state-text a {
  color: var(--primary);
  text-decoration: underline;
  text-underline-offset: 3px;
}

.notice-state-text a:hover { color: #fff; }

.notice-state .btn { margin-top: 6px; }

/* 뼈대 화면. 빈 화면을 보여주는 대신 카드가 들어올 자리를 미리 잡아,
   목록이 도착할 때 페이지가 아래로 튀지 않는다. */
.notice-skeleton { display: grid; gap: 10px; }

.notice-skeleton-row {
  height: 118px;
  border-radius: var(--radius-md);
  background: linear-gradient(90deg, var(--surface) 25%, var(--surface-2) 50%, var(--surface) 75%);
  background-size: 200% 100%;
  animation: notice-shimmer 1.4s ease-in-out infinite;
}

@keyframes notice-shimmer {
  0%   { background-position: 200% 0; }
  100% { background-position: -200% 0; }
}

/* ---------- 9. 상세 ---------- */

/*
 * notice.js 가 hidden 속성으로 목록과 자리를 바꾼다. [hidden] 규칙이
 * display 선언보다 구체적이어야 하므로 이 줄을 지우지 말 것.
 */
.notice-detail[hidden] { display: none; }

/*
 * 여기에도 폭 상한을 두지 않는다 (2026-08 수정).
 *
 * 예전에는 max-width: 820px + margin: 0 auto 였다. 목록에서 상한을 걷어낸 뒤
 * 이것만 남겨 두면 상세를 열 때마다 '목록으로' 버튼과 제목이 안쪽으로 들어갔다가
 * 아래 CTA 에서 다시 넓어져, 고친 계단이 상세 화면에서 그대로 되살아난다.
 *
 * 대신 줄 길이는 본문(.notice-body)에서만 잡는다 — 제목 · 배지 · 제목 아래 선 ·
 * 이전/다음 링크는 판의 폭을 그대로 쓰고, 글만 74ch 에서 접힌다. 제목 아래 선이
 * 화면을 가로지르는 편이 편집물의 결에도 맞는다.
 */

/* 유리 알약 — 히어로의 보조 CTA(.btn-ghost)와 같은 문법이다. */
.notice-back {
  display: inline-flex;
  align-items: center;
  gap: 8px;
  min-height: 42px;
  margin-bottom: 22px;
  padding: 9px 18px;
  background: rgba(255, 255, 255, .05);
  border: 1px solid rgba(255, 255, 255, .2);
  border-radius: 9999px;
  color: rgba(255, 255, 255, .8);
  font-size: 13.5px;
  font-weight: 600;
  transition: border-color var(--ease), background var(--ease), color var(--ease);
}

.notice-back:hover {
  border-color: rgba(255, 255, 255, .5);
  background: rgba(255, 255, 255, .1);
  color: #fff;
}

.notice-back-icon {
  width: 13px;
  height: 13px;
  background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 14 14'%3E%3Cpath d='M12 7H2.5M6.5 3 2.5 7l4 4' fill='none' stroke='%23ffffff' stroke-opacity='.75' stroke-width='1.6' stroke-linecap='round' stroke-linejoin='round'/%3E%3C/svg%3E");
  background-repeat: no-repeat;
  background-position: center;
  background-size: 13px 13px;
  transition: transform var(--ease);
}

.notice-back:hover .notice-back-icon { transform: translateX(-2px); }

.notice-detail-head {
  padding-bottom: 20px;
  margin-bottom: 24px;
  border-bottom: 1px solid var(--border);
}

.notice-detail-tags {
  display: flex;
  flex-wrap: wrap;
  align-items: center;
  gap: 8px;
  margin-bottom: 12px;
}

.notice-detail-tags:empty { display: none; }

.notice-detail-title {
  color: #fff;
  font-size: 24px;
  font-weight: 700;
  line-height: 1.38;
  letter-spacing: -.025em;
  overflow-wrap: anywhere;
}

/* 게시일 · 수정일. 값이 둘일 수도 하나일 수도 있어 flex 로 둔다. */
.notice-detail-meta {
  display: flex;
  flex-wrap: wrap;
  gap: 4px 16px;
  margin-top: 12px;
  color: var(--muted);
  font-size: 12.5px;
  font-variant-numeric: tabular-nums;
}

/* ---------- 10. 본문 조판 ---------- */

/*
 * 여기 있는 선택자는 notice.js 의 renderBody 가 만드는 요소와 일대일로 짝이다.
 * 본문은 평문으로 저장되고, 스크립트가 줄머리 기호를 보고 아래 셋 중 하나로 그린다.
 *   '#' ~ '###' 로 시작하는 줄 → h3
 *   '- ' / '• ' / '* '        → ul > li
 *   그 밖의 줄                 → p (문단 안 줄바꿈은 br)
 *
 * 관리자 콘솔의 미리보기도 이 규칙을 그대로 쓴다. 여기를 고치면 두 화면이
 * 함께 바뀐다 — 그게 의도다.
 */
.notice-body {
  color: var(--text-soft);
  font-size: 15.5px;
  line-height: 1.9;
  overflow-wrap: anywhere;
}

/*
 * 읽는 글의 줄 길이 상한. 판이 아니라 글에 건다(9절 주석).
 *
 * .notice-detail 로 한정하는 이유가 중요하다 — 관리자 콘솔의 미리보기도 같은
 * .notice-body 를 쓰는데, 그쪽은 이미 좁은 패널 안이라 상한이 필요 없고
 * 무엇보다 '홈페이지에 이렇게 나갑니다'라는 화면이 홈페이지와 다른 규칙을
 * 갖게 되면 미리보기의 뜻이 사라진다. 상한이 걸리는 폭까지 넓어질 일이 없으므로
 * 두 화면의 조판은 지금도 같다.
 *
 * 74ch 는 15.5px 기준 약 740px 로, 예전 820px 판에서 이 글이 갖던 폭과 거의 같다.
 */
.notice-detail .notice-body { max-width: 74ch; }

/*
 * HTML 본문일 때의 컨테이너.
 *
 * 하는 일은 읽는 줄 길이를 잡는 것 하나뿐이다. 조판(문단 간격 · 소제목 · 목록 ·
 * 표 · 이미지)은 static/prose.css 가 통째로 맡는다.
 *
 * 왜 .notice-body 를 그대로 쓰지 않는가
 *   그 클래스에는 이 파일의 조판 규칙이 잔뜩 붙어 있다(위 10절). 거기에 .prose 를
 *   함께 달면 같은 요소를 두 파일이 칠하게 되고, 어느 쪽이 이길지가 파일을 싣는
 *   순서와 선택자 무게에 달린다 — 둘 다 나중에 바뀐다. 이름을 갈라 두면 겹치는
 *   자리가 아예 없어서 그 다툼이 생기지 않는다.
 *   (평문으로 저장된 옛 공지는 여전히 .notice-body 로 그린다 — static/notice.js
 *    의 renderNoticeBody 가 둘 중 하나만 단다.)
 */
.notice-detail .notice-prose { max-width: 74ch; }

.notice-body p + p,
.notice-body ul + p,
.notice-body p + ul,
.notice-body ul + ul { margin-top: 16px; }

.notice-body h3 {
  margin: 32px 0 12px;
  padding-top: 4px;
  color: #fff;
  font-size: 17.5px;
  font-weight: 700;
  letter-spacing: -.01em;
  line-height: 1.5;
}

/* 첫 줄이 소제목이면 위 여백이 제목 아래 선과 겹쳐 빈 띠가 생긴다. */
.notice-body > h3:first-child { margin-top: 0; }

/* 본문 안의 http(s) 주소. notice.js 가 URL 로 파싱해 프로토콜을 확인한 뒤에만 만든다.
   주변 글자와 색이 같으면 링크인 줄 모르므로 색 + 밑줄로 구분한다. */
.notice-link {
  color: var(--primary);
  text-decoration: underline;
  text-underline-offset: 3px;
  overflow-wrap: anywhere;
}

.notice-link:hover { color: #fff; }

.notice-body ul { display: grid; gap: 9px; }

.notice-body li {
  position: relative;
  padding-left: 19px;
}

/* 목록 점은 렌즈 색분산의 청록. 이 페이지에서 색을 쓰는 곳은 분류 배지 ·
   고정 선 · 이 점 셋뿐이다. */
.notice-body li::before {
  content: '';
  position: absolute;
  left: 3px;
  top: .82em;
  width: 5px;
  height: 5px;
  border-radius: 50%;
  background: var(--primary);
}

/* ---------- 11. 이전 · 다음 공지 ---------- */

.notice-pager {
  display: grid;
  gap: 10px;
  margin-top: 36px;
  padding-top: 22px;
  border-top: 1px solid var(--border);
}

/* 첫 글 · 마지막 글에서는 링크가 하나뿐이거나 아예 없다. */
.notice-pager:empty { display: none; }

.notice-pager-link {
  display: grid;
  gap: 3px;
  padding: 14px 16px;
  background: var(--surface);
  border: 1px solid var(--border);
  border-radius: var(--radius-md);
  transition: border-color var(--ease), background var(--ease), transform var(--ease-spring);
}

.notice-pager-link:hover {
  border-color: rgba(255, 255, 255, .3);
  background: rgba(255, 255, 255, .025);
  transform: translateY(-2px);
}

.notice-pager-label {
  color: var(--muted);
  font-size: 11.5px;
  font-weight: 700;
  letter-spacing: .1em;
}

/* 제목이 길면 한 줄로 자른다. 두 줄이 되면 이전/다음 두 칸의 키가 어긋난다. */
.notice-pager-title {
  overflow: hidden;
  color: var(--text-soft);
  font-size: 14.5px;
  font-weight: 600;
  text-overflow: ellipsis;
  white-space: nowrap;
}

.notice-pager-link:hover .notice-pager-title { color: #fff; }
.notice-pager-link.is-next { text-align: right; }

/* ---------- 12. 하단 CTA ---------- */

/* 판은 style.css 의 .cta-band 를 그대로 쓴다. 여기서는 위 여백만 정한다. */
.nt-cta { margin-top: 44px; }

/* ---------- 13. 반응형 ---------- */

@media (max-width: 639px) {
  .notice-card { padding: 16px 17px; }
  /* 좁은 폭에서는 오른쪽 끝으로 밀지 않는다. 날짜 바로 옆이 자연스럽다. */
  .notice-more { margin-left: 0; }

  /* 레일 폭을 줄인다. 28px 을 그대로 두면 카드가 그만큼 좁아진다.
     아래 네 값은 한 묶음이다 — 점 중심(4.5px) · 흐르는 빛이 레일 중심과 맞아야 한다.
     하나만 고치면 점이나 빛이 선에서 벗어난다. */
  .notice-list:has(.notice-card) { padding-left: 20px; }
  .notice-list:has(.notice-card)::before { left: 4px; }
  .notice-list:has(.notice-card)::after { left: 4px; }
  .notice-list:has(.notice-card) .notice-card::before { left: -20px; top: 21px; }
}

@media (min-width: 640px) {
  .nt-hero { padding: 24px 0 22px; }
  .nt-main { padding: 32px 0 88px; }
  .nt-lead { font-size: 14.5px; }

  .notice-card { padding: 20px 22px; }
  .notice-detail-title { font-size: 28px; }
  .notice-pager { grid-template-columns: 1fr 1fr; }
}

/*
 * 분류와 검색이 한 줄에 서고, 그 줄이 헤더 아래에 붙는다.
 *
 * 720px 부터인 이유: 분류 세그먼트 다섯 칸이 최소 420px 안팎을 쓴다. 검색창
 * 244px 을 옆에 세우려면 그만큼은 있어야 하고, 더 일찍 나누면 분류가 가로로
 * 스크롤되기 시작해 '다섯 개가 한눈에 보인다'는 이 컨트롤의 뜻이 사라진다.
 */
@media (min-width: 720px) {
  .notice-rail {
    position: sticky;
    top: var(--header-h);
    grid-template-columns: minmax(0, 1fr) 244px;
    align-items: center;
    gap: 12px;
  }

  /*
   * 세그먼트는 왼쪽 칸을 다 쓰지 않는다.
   *
   * 판에서 폭 상한을 걷어내면서 왼쪽 칸이 840px 까지 늘어난다(2절 주석). 칩은
   * flex: 1 0 auto 라 남는 폭을 나눠 갖는데, 그러면 알약 다섯 개가 각각 168px 이
   * 되어 컨트롤이 아니라 배너처럼 보인다. 620px 은 예전 880px 판에서 이 컨트롤이
   * 갖던 폭이라, 판만 넓어지고 조작 줄의 인상은 그대로 남는다.
   *
   * 상한에 걸리면 세그먼트는 왼쪽 칸의 시작(= 컨테이너 왼쪽 끝)에 서고 검색창은
   * 오른쪽 끝에 남는다 — 줄의 양 끝이 헤더 · 히어로 · CTA 와 같은 선에 선다.
   */
  .notice-filters { max-width: 620px; }
}

/*
 * 히어로가 두 줄 격자로 접히는 지점. FAQ 와 같은 900px · 같은 배분이다 —
 * 두 페이지가 서로 다른 폭에서 접히면 창을 줄여 가며 볼 때 한쪽이 고장 난 것처럼
 * 보이고, 배분이 다르면 제목이 시작하는 세로선이 페이지마다 어긋난다.
 *
 * align-items: end 로 두 줄의 아랫선을 맞춘다. 그래야 큰 제목과 작은 설명이
 * 같은 바닥에 서서, 글자 크기가 달라도 한 줄로 읽힌다.
 */
@media (min-width: 900px) {
  .nt-hero { padding: 26px 0 24px; }

  .nt-hero-inner {
    grid-template-columns: minmax(0, 1.08fr) minmax(0, .92fr);
    grid-template-areas:
      'meta  meta'
      'title lead';
    gap: 12px 48px;
    align-items: end;
  }

  /*
   * 제목의 마지막 줄과 설명의 마지막 줄이 같은 바닥에 서도록 미세 보정.
   *
   * 예전에는 여기에 세로 머리카락 선(border-left)이 있었다. 라벨이 제목 옆에
   * 서던 시절, 두 칸의 경계를 드러내려고 넣은 것이다. 지금은 골격이 FAQ 와
   * 같아 그 선만 남으면 이 페이지에만 있는 군더더기로 보인다 — 되살리지 말 것.
   */
  .nt-lead { padding-bottom: 3px; }

  .notice-card-title { font-size: 17px; }
  .notice-detail-title { font-size: 31px; }
  .notice-body { font-size: 16px; }
}

/* ---------- 14. 접근성: 모션 최소화 ---------- */

/*
 * 물감 배경과 레일 위의 빛은 여기서 끄지 않는다.
 *
 * 성능을 위해 창 애니메이션을 꺼 둔 Windows PC 는 브라우저가 모든 사이트에
 * reduce 를 보고한다. 그 신호로 마우스 효과를 지우면 정작 주 사용자만 밋밋한
 * 화면을 보게 된다 — 메인 히어로 셰이더 · 로그인 유체 · 요금제 프리즘과 같은
 * 규칙이다. 물감은 CSS 전환이 아니라 캔버스에 그려지는 것이라, 아래에서
 * 전환 시간을 지워도 그대로 흐른다(첫 프레임에 드러나는 순간만 즉시 바뀐다).
 *
 * style.css 가 전역 transition 을 이미 줄인다. 여기서는 무한 반복하는
 * 뼈대 애니메이션만 끈다 — 그것만은 duration 을 줄여도 계속 깜빡인다.
 */
@media (prefers-reduced-motion: reduce) {
  .notice-skeleton-row { animation: none; }
  .notice-card,
  .notice-chip,
  .nt-hero-canvas,
  .notice-pager-link { transition: none; }
}
