/* =========================================================
   LETSRUN PLAY · HOME (데스크탑 1440 기준 · 반응형)
   정본: Figma 「05 · 최종 기본 2」 Home-데스크탑 / Home-모바일
   치트시트 규격: 컨테이너 1280 / 마진 80 / 섹션 72 / 카드 갭 32
   카드 문법: 미디어(r18) → 하단 텍스트 → 태그 (딤·오버레이 없음)
   ========================================================= */

*{box-sizing:border-box;margin:0;padding:0}
html{scroll-behavior:smooth}
/* scrollbar-gutter:stable — 모달이 body overflow:hidden으로 스크롤을 잠글 때 스크롤바가 사라지며
   페이지 전체가 옆으로 밀리던 현상(공유·코스·캘린더·검색 모달 공통) 방지: 스크롤바 자리를 항상 예약.
   260812 버그 수정: 이 규칙이 @media (min-width:998px) 안에만 있어서, 클래식 스크롤바를 쓰는
   데스크톱 브라우저 창을 998px 아래로 줄이면 방어가 빠져 그대로 밀렸다 — 실제로 900px에서 공유 모달을
   열면 상세 Hero가 406.5→414px(+7.5px)로 순간 커졌다("이미지가 확대되는" 증상의 정체).
   미디어쿼리를 걷어내 전 구간에 적용한다. 모바일 우려(우측 빈 줄)는 발생하지 않는다 — 오버레이
   스크롤바 환경에서는 scrollbar-gutter가 사양상 무효이며, 375px에서 clientWidth 변화 0으로 실측 확인했다.
   반대로 클래식 스크롤바를 쓰는 환경이라면 폭과 무관하게 예약하는 것이 맞다. */
html{scrollbar-gutter:stable}
body{font-family:var(--font-sans);color:var(--ink);background:var(--white);line-height:var(--lh-base)}
a{color:inherit;text-decoration:none}
button{font-family:inherit;border:0;background:none;cursor:pointer;color:inherit}
img{max-width:100%;display:block}
[hidden]{display:none!important} /* 필터로 숨긴 카드가 .card{display:flex}에 덮이지 않도록 */
.container{max-width:calc(var(--container) + var(--pad-page)*2);margin-inline:auto;padding-inline:var(--pad-page)}
/* 시각적으로는 숨기되 스크린리더에는 읽히는 접근성 전용 텍스트 — HOME처럼 히어로가 이미지 완성형이라
   화면에 노출할 첫 제목 텍스트가 없는 페이지에 h1 하나를 반드시 두기 위해 사용한다. */
.sr-only{position:absolute;width:1px;height:1px;padding:0;margin:-1px;overflow:hidden;clip:rect(0,0,0,0);white-space:nowrap;border:0}

/* =========================================================
   상호작용 상태 — Focus · Pressed (260806 신설)
   ---------------------------------------------------------
   이전에는 저자 CSS에 :focus-visible이 detail.css 1건뿐이고 :active(Pressed)는 전 파일 0건이었다.
   포커스 링은 브라우저 기본값이 살아 있어 "안 보이는" 상태는 아니었지만, 브랜드 기준이 없어
   요소마다 링 모양이 제각각이었고 눌림 피드백은 아예 없었다.

   ⚠ :where()로 감싸 특이도를 0으로 만든다 — 컴포넌트별 규칙이 항상 이겨서, 이 블록 때문에
   기존 스타일이 덮이는 일이 없다. detail.css의 .detail-gallery__item:focus-visible과 값이 같아
   화면 결과도 동일하다(그 규칙은 개별 선언으로 남겨 둔다).

   포커스 링 색은 --focus-ring 변수로 받는다. 기본은 ink이고, 아래 "어두운 표면" 블록에서만
   흰색으로 바꾼다 — 어두운 배경 위에서 ink 링은 보이지 않기 때문이다.
   outline-offset:2px 덕분에 .btn--dark처럼 배경이 진한 버튼도 링이 요소 바깥(밝은 지면)에 그려져
   대비가 확보된다.
   ========================================================= */
:root{--focus-ring:var(--ink)}
:where(a[href],button,input,select,textarea,[tabindex]):focus-visible{
  outline:2px solid var(--focus-ring);
  outline-offset:2px;
}
/* 어두운 표면 위의 컨트롤 — 히어로 배너(재생·정지), 라이트박스(닫기·이전·다음), 영상 재생 아이콘 */
.hero__banner,.lightbox-modal,.card__play{--focus-ring:var(--white)}

/* Pressed — 배경이 있는 컨트롤은 밝기를, 배경이 없는 아이콘 버튼은 불투명도를 낮춘다.
   (배경이 투명한 버튼에 brightness를 걸면 아이콘 색만 미세하게 변해 눌림이 잘 안 보인다.) */
:where(.btn,.chip,.chip-dd__opt,.rail__arrow,.nav-hero__arrow,.courses__pause,.modal__close,.cal-day,.share-options__item):not([disabled]):active{
  filter:brightness(.93);
}
:where(.gnb__icon,.hero__pause,.section__more,.playnow__more,.gnb-dd__trigger):active{opacity:.55}

/* Hover — 이미 hover가 있는 컴포넌트(칩·카드·목록 등)는 건드리지 않고, 없던 조작 요소에만 더한다. */
:where(.rail__arrow,.nav-hero__arrow,.courses__pause,.modal__close):hover{filter:brightness(.95)}
:where(.gnb__icon,.section__more,.playnow__more):hover{opacity:.7}
@media (hover:none){ /* 터치 기기에서는 hover 잔상이 남지 않도록 */
  :where(.rail__arrow,.nav-hero__arrow,.courses__pause,.modal__close):hover{filter:none}
  :where(.gnb__icon,.section__more,.playnow__more):hover{opacity:1}
}

/* 반응형 표시 토글 */
.only-mob,.only-mob-block,.only-mob-flex{display:none}
.only-desk{display:inline}
.only-desk-block{display:block}
.only-desk-flex{display:flex}

/* ---------- GNB ---------- */
/* GNB 전용 디스플레이 폰트 (260819 클라이언트 요청 — 현대카드 DIVE 레퍼런스 → 같은 날
   에이투지체로 교체 확정, freesentation.blog/a2z). A2Z ExtraBold(SIL OFL, 무료 상용,
   라틴 베이스 Outfit) 단일 웨이트만 셀프호스팅(assets/fonts, 146KB) — 사이트가 안내하는
   임베딩 대신 셀프호스팅을 쓴다: 외부 CDN 요청 없음(오프라인 데모·납품 환경 유지).
   적용 범위는 GNB 텍스트(메뉴·방문정보 트리거·로그인)뿐이며 본문 타이포는 기존 --font-sans
   그대로다. 로드 실패 시 폴백도 --font-sans. 웨이트는 8 ExtraBold → 7 Bold를 거쳐
   "너무 두껍다"는 클라이언트 피드백 2회로 6 SemiBold(600)로 확정. */
@font-face{
  font-family:"A2Z";
  font-weight:600;
  font-style:normal;
  /* 260820: swap → block. swap은 "폴백으로 먼저 그리고 나중에 교체"라 페이지를 넘길 때마다
     GNB 메뉴가 시스템 폰트로 한 번 그려졌다가 A2Z(라틴 베이스 Outfit, 폭이 더 넓다)로 바뀌며
     글자 크기가 튀어 보였다(클라이언트 리포트 — preload만으로는 첫 페인트 타이밍을 못 막는다).
     block은 폰트가 준비될 때까지 그 글자만 그리지 않고 기다렸다가 A2Z로 한 번에 그린다 —
     적용 범위가 GNB 텍스트 3곳뿐이고 폰트는 preload + 캐시라 실제 대기 시간은 사실상 0이며,
     최악의 경우(첫 방문·느린 네트워크)에도 3초 후 폴백으로 자동 표시된다(스펙 기본 동작). */
  font-display:block;
  src:url("../assets/fonts/A2Z-SemiBold.woff2") format("woff2");
}
.gnb{position:sticky;top:0;z-index:50;background:var(--gnb-bg,var(--white));border-bottom:1px solid var(--gnb-line,var(--line));transition:background .4s ease,border-color .4s ease}
.gnb__inner{max-width:1440px;margin-inline:auto;height:80px;padding-inline:var(--pad-page);display:flex;align-items:center;justify-content:space-between;gap:28px}
/* display는 지정하지 않는다 — .only-mob-block/.only-desk-block(0,1,0) 토글을 이기지 않도록(기본 display:block은 위 img 규칙에서 이미 적용) */
.gnb__logo img{height:38px;width:auto} /* 260819: 32→38 — 로고 애니메이션 도입과 함께 소폭 확대(클라이언트 요청) */
/* 로고 자산 2종 — 지오메트리(264x96)가 완전히 동일해 형태·비율·위치가 항상 같고 색만 다르다.
   height:32px(모바일 24px) + width:auto로 표시하므로 원본 비율이 그대로 유지된다.
   · logo_color.svg : 컬러. 흰/밝은 헤더(전 페이지 + HOME 데스크톱)
   · logo_white.svg : 화이트 단색 녹아웃. HOME 모바일 다크 헤더 전용
     (CSS 반전 필터는 쓰지 않는다 — 별도 파일을 직접 사용). */

/* HOME 모바일 전용: 화이트/컬러 로고를 같은 자리에 겹쳐두고 opacity만 크로스페이드(레이아웃 이동 없음).
   html.is-header-dark는 home.js의 syncHeaderTheme가 이미 계산해 두는 스크롤 상태 클래스를 그대로 재사용한다
   (새 스크롤 판정 로직 추가 안 함). 기본값(클래스 없음)은 화이트가 보이는 상태 — 최초 페인트 전에도
   히어로 최상단(다크 배경)과 시각적으로 어긋나지 않도록 하기 위함. */
/* display는 지정하지 않는다 — .only-mob-block의 (0,1,0) 토글을 이기지 않도록(위 .gnb__logo img 규칙과 동일한 이유) */
.gnb__logo-mob{position:relative}
.gnb__logo-mob .gnb__logo-img--white{position:relative;transition:opacity .15s linear} /* 정상 flow — span 크기를 이 이미지가 정함 */
.gnb__logo-mob .gnb__logo-img--color{position:absolute;top:0;left:0;width:100%;height:100%;opacity:0;transition:opacity .15s linear}
html:not(.is-header-dark) .gnb__logo-mob .gnb__logo-img--white{opacity:0}
html:not(.is-header-dark) .gnb__logo-mob .gnb__logo-img--color{opacity:1}
/* ---------- GNB 로고 애니메이션 (260819) ----------
   PLAY 4글자(P·L·A·Y)가 순서대로 한 바퀴 돌아가는 3D 플립. 디자이너 원본
   (`렛츠런파크 로고/animation/index.html`)의 기하·타이밍·컬러를 그대로 옮긴 것이며,
   깊이감을 만드는 슬랩(단면) 156장은 home.js가 공식으로 생성한다(마크업 하드코딩 없음).

   ⚠ 정지 상태(0%)는 기존 logo_color.svg와 같은 그림이다 — 애니메이션이 꺼져도(reduced-motion)
   로고가 평소와 다르게 보이지 않는다.
   ⚠ HOME 모바일 다크 헤더의 화이트 로고(logo_white.svg)도 같은 애니메이션의 화이트 변형으로
   교체된다(260819 클라이언트 요청). 화이트 변형은 컬러 변형과 구조가 완전히 동일하고 카드 색만
   흰색(글자는 동일한 불투명 검정)이다 — 녹아웃(mask 구멍) 방식은 회전 중 글자가 사라지고 카드가
   깨져 보여 폐기(home.js IIFE 주석 참고). 타이밍·크기·위치가 동일해 크로스페이드가 그대로 통한다.
   ⚠ 클래스는 전부 `logo-anim` 접두사를 쓴다 — 원본의 .face/.core/.slab/.card-slot은
   이름이 너무 일반적이라 프로젝트 CSS와 충돌할 수 있다. */
.logo-anim{
  --logo-anim-cycle:4000ms;   /* 한 바퀴(캐스케이드 + 쉬는 구간) */
  --logo-anim-stagger:200ms;  /* 글자 간 시작 간격 */
  --logo-anim-persp:1600px;   /* 클수록 납작 — 슬랩 scale 값과 짝이라 임의 변경 금지 */
  --logo-anim-scale:calc(38 / 125); /* 위 .gnb__logo img height(38px, 모바일 28px)와 동일 크기 */
  width:calc(345px * var(--logo-anim-scale));
  height:calc(125px * var(--logo-anim-scale));
  overflow:visible}
/* display는 특이도 0(:where)으로 준다 — 교체 전 <img>가 갖고 있던 .only-mob-block/.only-desk-block
   토글(0,1,0)을 절대 이기지 않아야 한다(위 .gnb__logo img 규칙과 같은 이유). */
:where(.logo-anim){display:block}
.logo-anim__canvas{position:relative;display:block;width:345px;height:125px;
  transform:scale(var(--logo-anim-scale));transform-origin:0 0}
.logo-anim__wordmark{position:absolute;left:0;top:0;width:172.2px;height:26.84px;display:block} /* LETSRUN — 항상 정지 */
.logo-anim__slot{position:absolute;top:38.4912px;width:86.0069px;height:86.0069px}
.logo-anim__scene{display:block;width:100%;height:100%;
  perspective:var(--logo-anim-persp);perspective-origin:50% 50%}
/* 구(L·A)는 원으로 클리핑한다 — 구가 돌아도 실루엣은 항상 완전한 원이어야 한다 */
.logo-anim__scene--round{clip-path:circle(49.85% at 50% 50%);-webkit-clip-path:circle(49.85% at 50% 50%)}
.logo-anim__card{position:relative;display:block;width:100%;height:100%;
  transform-style:preserve-3d;animation:logo-anim-spin var(--logo-anim-cycle) infinite}
.logo-anim__card--p{animation-delay:0ms}
.logo-anim__card--l{animation-delay:calc(var(--logo-anim-stagger) * 1)}
.logo-anim__card--a{animation-delay:calc(var(--logo-anim-stagger) * 2)}
.logo-anim__card--y{animation-delay:calc(var(--logo-anim-stagger) * 3)}
.logo-anim__face,.logo-anim__slab,.logo-anim__core{position:absolute;inset:0;width:100%;height:100%;display:block}
.logo-anim__face{backface-visibility:hidden;-webkit-backface-visibility:hidden}
/* 글자면은 각 입체의 바깥 표면에 놓인다. scale은 (perspective − depth/2) / perspective로
   원근 확대를 상쇄해 정지 프레임이 원본 로고와 픽셀 단위로 같아지게 한다. */
.logo-anim__card--p .logo-anim__face--front,.logo-anim__card--y .logo-anim__face--front{transform:translateZ(35px) scale(0.978125)}
.logo-anim__card--p .logo-anim__face--back, .logo-anim__card--y .logo-anim__face--back {transform:rotateY(180deg) translateZ(35px) scale(0.978125)}
.logo-anim__card--l .logo-anim__face--front,.logo-anim__card--a .logo-anim__face--front{transform:translateZ(43.0035px) scale(0.973123)}
.logo-anim__card--l .logo-anim__face--back, .logo-anim__card--a .logo-anim__face--back {transform:rotateY(180deg) translateZ(43.0035px) scale(0.973123)}
/* 코어면 = 입체의 측면 실루엣. 옆으로 완전히 돌아간 순간의 빈틈을 메우고,
   쉬는 동안에는 사라져 정지 로고에 실선으로 비치지 않게 한다.
   슬랩(단면)도 같은 페이드를 탄다(260819 경계 찌글거림 수정) — 슬랩 70~86장은 원근 보정 때문에
   정지 상태에서 앞면과 픽셀 단위로 같은 크기가 되는데, 같은 자리에 안티앨리어싱된 가장자리가
   수십 장 겹쳐 쌓이면 벡터의 깔끔한 테두리가 지저분한 픽셀 프린지로 보인다. 슬랩은 회전 중
   옆면 깊이를 보여줄 때만 필요하므로 코어와 동일한 구간(플립 동안)에만 나타나게 한다 —
   정지 로고는 앞면 SVG 한 장의 가장자리만 그려져 원본 벡터와 동일하게 선명하다. */
.logo-anim__core{transform:rotateY(90deg)}
.logo-anim__core,.logo-anim__slab{opacity:0;
  animation:logo-anim-core var(--logo-anim-cycle) linear infinite}
.logo-anim__card--p :is(.logo-anim__core,.logo-anim__slab){animation-delay:0ms}
.logo-anim__card--l :is(.logo-anim__core,.logo-anim__slab){animation-delay:calc(var(--logo-anim-stagger) * 1)}
.logo-anim__card--a :is(.logo-anim__core,.logo-anim__slab){animation-delay:calc(var(--logo-anim-stagger) * 2)}
.logo-anim__card--y :is(.logo-anim__core,.logo-anim__slab){animation-delay:calc(var(--logo-anim-stagger) * 3)}
@keyframes logo-anim-spin{
  0%{transform:rotateY(0deg);animation-timing-function:cubic-bezier(0.6,0,0.3,1)}
  45%{transform:rotateY(180deg)}
  100%{transform:rotateY(180deg)}
}
@keyframes logo-anim-core{
  0%{opacity:0} 2.5%{opacity:1} 40%{opacity:1} 44.5%{opacity:0} 100%{opacity:0}
}
@media (prefers-reduced-motion:reduce){
  .logo-anim__card{animation:none}
  .logo-anim__core,.logo-anim__slab{animation:none;opacity:0}
}

.gnb__menu{display:flex;gap:28px;flex:1;justify-content:flex-start;min-width:0;overflow-x:auto;scrollbar-width:none}
.gnb__menu::-webkit-scrollbar{display:none}
.gnb__inner{position:relative}
/* 메뉴 타이포 (260819 확대 — DIVE 레퍼런스): --fs-body-sm(14px)/400 → --fs-card(17px, 모바일 14px)/A2Z 600(18px/800→700→600·17px로 클라이언트 피드백 따라 단계 조정).
   기존 hover(굵기 400→700 전환)는 base가 이미 최고 굵기가 되어 무의미해졌으므로
   사이트 공통 hover 언어(opacity .7 — .gnb__icon 등과 동일)로 교체. is-active는 노란 밑줄 유지. */
.gnb__menu a{font-family:"A2Z",var(--font-sans);font-size:var(--fs-card);font-weight:600;padding:4px 0 8px;position:relative;color:var(--gnb-fg,var(--ink));white-space:nowrap;flex:none}
.gnb__menu a.is-active::after{content:"";position:absolute;left:0;right:0;bottom:0;height:3px;border-radius:2px;background:var(--yellow-500)}
.gnb__menu a:hover{opacity:.7}
.gnb__right{display:flex;align-items:center;gap:12px}
/* 260819: 메뉴·유틸을 로고의 PLAY 블록 행 중심에 광학 정렬 — 로고는 상단에 LETSRUN 워드마크가
   얹혀 있어 그래픽의 무게중심(PLAY 행)이 박스 중심보다 아래에 있다(38px 기준 약 +5.8px).
   flex 중앙정렬을 그대로 두고 transform으로만 내려 레이아웃·히트영역 계산에 영향을 주지 않는다.
   드롭다운 패널은 JS가 트리거 실측 좌표(getBoundingClientRect)로 띄우므로 함께 따라온다.
   모바일(≤997)은 로고가 작고 1행 구조라 대상 아님. */
@media (min-width:998px){
  .gnb__menu,.gnb__right{transform:translateY(6px)}
}
.gnb__icon{position:relative;display:flex;align-items:center;justify-content:center;color:var(--gnb-fg,#212121)}
.gnb__icon svg{height:20px;width:auto} /* viewBox 비율 유지(calendar 20:22 · search 20:20) — width 동시 고정 금지 */
/* 히트 영역 확장(260806) — 버튼 자체가 아이콘 크기(데스크톱 20 / 모바일 22)라 누를 수 있는 면적이
   그만큼밖에 되지 않았다. 레이아웃 박스를 키우면 GNB 우측 정렬과 아이콘 간격이 함께 움직이므로
   가상 요소로만 넓힌다 — 화면에 보이는 결과는 이전과 완전히 동일하다.
   32px: 두 아이콘의 중심 간격(데스크톱 32 / 모바일 34)과 같아 서로 겹치지 않는 최대값.
   40px: 위로 GNB 상단, 아래로 모바일 메뉴 줄(17px)과 겹치지 않는 최대값.
   ⚠ Apple HIG 권장치 44×44까지 키우려면 .gnb__right의 gap(12px)을 22px 이상으로 넓혀야 하는데
   그건 GNB의 실제 시각 변경이라 별도 승인 대상이다(§36). 현재 값으로 WCAG 2.5.8 AA(24×24)는 충족한다. */
.gnb__icon::after{content:"";position:absolute;top:50%;left:50%;transform:translate(-50%,-50%);width:32px;height:40px}
/* 로그인 — GNB 우측 유틸(260819). 실제 로그인 URL·세션 판정은 서버 영역이라 여기서는
   [data-login-trigger] 훅만 두고 href를 만들지 않는다(§9 — 가짜 URL·disabled 잔존 금지).
   서버가 <a href="…" class="gnb__login" data-login-trigger>로 교체해도 스타일은 그대로 적용된다.
   색은 .gnb__icon과 같은 --gnb-fg를 참조 — HOME 모바일 다크 히어로 위에서 함께 흰색이 된다. */
.gnb__login{font-family:"A2Z",var(--font-sans);font-size:var(--fs-body);font-weight:600;color:var(--gnb-fg,var(--ink));background:none;border:0;padding:4px 2px;line-height:1;white-space:nowrap;cursor:pointer} /* 260819: 메뉴와 같은 GNB 폰트, 크기만 한 단계 작게(15px) — 유틸리티 위계 유지 */
.gnb__login:hover{text-decoration:underline;text-underline-offset:3px}
.gnb__login:active{opacity:.55}
/* 기업 홈페이지 복귀 링크(260830) — 로그인과 같은 유틸 슬롯이지만 한 단계 낮은 위계(grey + 한 단계 작은 글자).
   ⚠ 모바일은 GNB 가로 여유가 0이라 라벨을 숨기고 아이콘만 남긴다(아래 모바일 블록) — 접근성 이름은 aria-label. */
.gnb__corp{display:inline-flex;align-items:center;gap:5px;font-family:"A2Z",var(--font-sans);
  font-size:var(--fs-body-sm);font-weight:600;color:var(--gnb-fg,var(--grey));padding:4px 2px;line-height:1;white-space:nowrap;opacity:.8}
.gnb__corp .ico-svg{width:15px;height:15px;flex:none}
/* 마사회 파비콘(assets/logo/kra-favicon.png — kra.co.kr 공식 파비콘 16px 반입, 260830 총괄 지정)
   — 좁은 폰(≤423px)에서 텍스트 라벨 대신 이것 하나만 남는다(아래 분기). 그 외 폭에서는 숨김. */
.gnb__corp__favicon{display:none;width:16px;height:16px;flex:none;border-radius:3px}
.gnb__corp:hover{opacity:1;text-decoration:underline;text-underline-offset:3px}
.gnb__corp:active{opacity:.55}

/* ---------- 긴급 공지 ---------- */
/* position+z-index 필요 — 모바일 히어로 블러 배경(.hero__bg)이 GNB 뒤로 200px 확장되며 공지 바 영역까지
   덮는데, .hero가 이후 DOM 순서라 기본 스택에서는 공지 위로 그려진다. 공지를 명시적으로 위 레이어에 둔다. */
.notice{position:relative;z-index:2;display:flex;align-items:center;gap:10px;background:var(--coral-100);border-left:4px solid var(--coral-500);padding:14px var(--pad-page);min-height:52px}
.notice__badge{font-size:var(--fs-badge);font-weight:700;background:var(--coral-500);color:var(--white);border-radius:4px;padding:3px 8px;flex:none;line-height:16px}
.notice__text{font-size:var(--fs-label);font-weight:600;flex:1;min-width:0;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.notice__close{font-size:var(--fs-body-sm);color:var(--grey);padding:4px;flex:none}

/* ---------- 히어로 ---------- */
/* Hero Group 높이 정렬(데스크톱 전용, 997px 이하는 별도 .hero 규칙이 완전히 덮어써서 영향 없음):
   .hero는 stretch로 두되, 히어로 배너 자신은 align-self:start로 stretch에서 빠져
   항상 자기 aspect-ratio 그대로의 높이를 유지한다(예전에 stretch를 금지했던 이유 — 아래 참고).
   그 결과 grid row 높이 = 히어로의 자연 높이가 되고, PLAY NOW(.playnow)만 기본 stretch로
   그 행 높이를 그대로 따라간다 — "히어로가 기준, PLAY NOW가 따라간다"는 방향을 명확히 한 것.
   (과거엔 사이드바가 히어로보다 커지는 998~1200px 구간에서 반대로 히어로가 사이드바 높이까지
   늘어나 버리는 문제가 있었다 — 히어로에 align-self:start를 줘서 그 경로 자체를 막는다.) */
/* 260802: 히어로 그룹에 별도의 좁은 max-width를 주는 방식은 폐기 — .container(다른 섹션과 동일)
   기준을 벗어나 독립적으로 가운데 정렬되면서 "취향대로 둘러보기" 등 아래 섹션과 좌우 정렬선이
   어긋나 보였다(피드백). 대신 사이드바(PLAY NOW) 컬럼 자체를 넓혀 히어로 비율은 그대로 유지하되
   폭을 좁은 만큼만 확보 — 정렬은 다른 섹션과 100% 동일한 .container를 그대로 쓰고, 사이드바가
   넓어진 만큼 히어로(1fr)가 자연히 조금 작아진다(1280 기준 907px → 856px, 높이 704 → 664px).
   사이드바를 280px→360px(26%→30%)로 넓힌 건 "코리아컵 국제대회"처럼 긴 제목이 잘리던 문제(피드백)도
   같이 해결하기 위함 — 아래 clamp() 값은 원래(개별 max-width 적용 전) 수치로 되돌렸다. */
/* 260821: 배너↔사이드바 간격 40 → 24px. 항목 자체의 좌측 패딩(16)이 더해져 배너에서 썸네일까지
   56px이 비어 "허전해 보인다"는 클라이언트 피드백 — 시각 간격 40px로 맞춘다(모바일은 gap:0 별도). */
.hero{display:grid;grid-template-columns:minmax(0,1fr) minmax(320px,30%);gap:24px;padding-top:32px;align-items:stretch}
.hero__bg{display:none} /* 모바일 전용 블러 배경 — 데스크톱은 흰 배경 유지(아래 ≤997 블록에서 활성) */
.hero__banner{position:relative;border-radius:var(--r-hero);overflow:hidden;align-self:start}
/* 실제 가로 스크롤 트랙(무한 순환 클론 포함) — 데스크톱은 피크 없이 1장씩, 모바일은 --hero-peek로 양옆 노출 */
.hero__track{position:relative;display:flex;overflow-x:auto;overflow-y:hidden;scroll-snap-type:x mandatory;scrollbar-width:none}
.hero__track::-webkit-scrollbar{display:none}
/* 히어로 카드 — 높이는 항상 '비율'에서 도출한다(고정 height 금지: 폭이 변하면 프레임 모양이 달라져 사진이 크게 잘림).
   데스크톱 ≥998 → --hero-ratio-desk(876:680) · 모바일 ≤997 → --hero-ratio(7/8) */
.hero__slide{--hero-ratio:var(--hero-ratio-desk);position:relative;display:block;flex:0 0 100%;aspect-ratio:var(--hero-ratio);scroll-snap-align:center;overflow:hidden;border-radius:inherit}
/* 배너는 제목·날짜·설명·가독성 그라데이션이 전부 포함된 완성형 이미지(운영 가이드 참고) —
   PC/모바일 전환은 <picture>의 <source>가 담당하고, CSS는 비율에 맞춰 꽉 채우기만 한다.
   딤·그라디언트·텍스트를 여기서 다시 얹지 않는다(이미지에 이미 포함되어 있어 중복 노출 금지). */
.hero__media{position:absolute;inset:0;display:block}
.hero__media img{width:100%;height:100%;object-fit:cover;display:block}
.hero__counter{position:absolute;right:20px;bottom:20px;background:rgba(0,0,0,.45);color:var(--white);font-size:var(--fs-body-sm);font-weight:700;border-radius:var(--r-full);padding:4px 14px;display:flex;align-items:center;gap:8px;z-index:1}
.hero__pause{position:relative;width:18px;height:18px;flex:none;display:flex;align-items:center;justify-content:center;font-size:var(--fs-badge);line-height:1;color:var(--white)}
/* 히트 영역 확장(260806) — .gnb__icon과 같은 방식·같은 값. 자동재생 정지는 접근성상 반드시 누를 수
   있어야 하는 컨트롤인데 버튼이 18×18뿐이었다. 카운터 알약(93×29)의 레이아웃을 건드리지 않도록
   가상 요소로만 넓힌다 — 화면에 보이는 결과는 이전과 동일하다.
   32px: 오른쪽 카운터 텍스트가 +17px 지점에서 시작하므로 겹치지 않는 최대값.
   40px: 알약 밖 배너 영역으로 넘어가지만 그 자리에 다른 조작 요소가 없어 안전하다. */
.hero__pause::after{content:"";position:absolute;top:50%;left:50%;transform:translate(-50%,-50%);width:32px;height:40px}

/* PLAY NOW 리스트 — 데스크톱에서 위 .hero의 stretch를 그대로 받아 히어로와 같은 높이를 채운다.
   min-height:0은 grid/flex 중첩 시 내부 콘텐츠가 stretch된 높이를 무시하고 넘치는 걸 방지. */
.playnow{display:flex;flex-direction:column;gap:30px;min-height:0}
.playnow__head{display:flex;align-items:baseline;justify-content:space-between}
.playnow__title{font-size:var(--fs-h2);font-weight:700}
/* .section__more와 같은 역할("더 보기")이므로 히트 영역 규칙도 같은 값을 쓴다(260811 정정 —
   이전에는 .section__more만 44px로 넓히고 이쪽은 21px 텍스트 높이 그대로였다).
   가상 요소로만 확장해 글자 크기·위치는 그대로다. */
.playnow__more{position:relative;font-size:var(--fs-body-sm);font-weight:700;color:var(--ink)}
.playnow__more::after{content:"";position:absolute;top:50%;left:0;right:0;transform:translateY(-50%);height:44px}
.playnow__list{position:relative;list-style:none;display:flex;flex-direction:column;gap:10px}
/* 260820: 선택 테두리 3px → 1px. 두꺼운 라인이 투박해 보인다는 피드백 — 선택 표시는 연한
   옐로우 필이 맡고 라인은 윤곽만 잡는다. 모든 항목이 같은 1px 투명 테두리를 가져 선택 시
   높이·정렬이 흔들리지 않는다. */
.playnow__item{display:flex;align-items:center;gap:14px;height:79px;padding:16px;border-radius:var(--r-md);border:1px solid transparent;cursor:pointer;transition:background .2s,border-color .2s}
.playnow__item:hover{background:var(--bg)}
/* 260821: 선택 상태 = 키컬러 옐로우(500) 완전 채움 — 데스크톱·모바일 공통(클라이언트: "모바일 노란색
   셀렉 컬러를 웹에도 동일하게"). 이전 데스크톱은 연한 200이라 두 화면의 선택 표현이 달랐다. */
/* 260829: 항목 클릭 = 상세 이동 — 앵커는 display:contents라 기존 flex 레이아웃 무변경 */
.playnow__link{display:contents;color:inherit;text-decoration:none}
.playnow__item.is-active{background:var(--yellow-500);border-color:var(--yellow-500)}
.playnow__item.is-active .playnow__meta{color:var(--ink);opacity:.75}

/* 목록 아래 "+ 더보기" — 데스크톱 전용(상단 헤드를 대체). 폭을 꽉 채우는 아웃라인 버튼. */
.playnow__more-btn{align-items:center;justify-content:center;height:48px;border:1px solid var(--line);
  border-radius:var(--r-md);background:var(--white);font-size:var(--fs-body-sm);font-weight:700;
  color:var(--ink);transition:background .2s,border-color .2s}
.playnow__more-btn:hover{background:var(--bg);border-color:var(--grey-line,var(--line))}
/* 썸네일 비율 고정(84:47) — 데스크톱/모바일 모두 동일 비율, width만 다르고 height는 자동 도출 */
/* 260821: 썸네일 가로형(84:47) → 정방형. 식별용 보조 이미지일 뿐이라 가로로 넓게 자리를 차지할
   이유가 없다(클라이언트). 폭 = 항목 안쪽 높이에 맞춘 값 — 가로 여백이 제목·날짜 쪽으로 돌아간다. */
.playnow__thumb{width:52px;aspect-ratio:1/1;border-radius:6px;flex:none;background:var(--img, var(--neut-thumb));background-size:cover;background-position:center}
/* min-width:0이 없으면 플렉스 자식(제목)이 줄어들지 못해 썸네일·배지를 밀어내거나 억지로 줄바꿈된다 */
.playnow__info{flex:1;min-width:0}
.playnow__name{font-size:var(--fs-body-sm);font-weight:700;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.playnow__meta{font-size:var(--fs-caption);color:var(--grey);white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.playnow__item .badge{margin-left:auto}

/* 처음방문 CTA (말마 배너) — 260803: 데스크톱·모바일 두 변형 모두 완성형 이미지 배너로 통일했다.
   문구·마스코트는 이미지 안에 포함되고 HTML 텍스트는 두지 않는다(히어로 배너와 동일 원칙, 접근성은 aria-label).
   고정 padding+텍스트 조합은 폭이 좁아져도 높이가 거의 줄지 않아 히어로와의 하단 라인 정렬을 방해했는데,
   aspect-ratio 기반 이미지는 폭에 비례해 함께 낮아진다.
   배경 폴백은 --neut-thumb(중립 회색)이 아니라 브랜드 CTA 그린 — 이미지 로드 전/실패 시에도 CTA로 읽히게. */
/* 260819 재구성: 완성형 이미지(playnow-firstvisit-banner.png) → HTML/CSS + 말마 캐릭터 PNG.
   클라이언트가 말마프렌즈 디자인 소스(Drive)를 제공하며 캐릭터 그래픽으로 개편 요청 —
   텍스트가 라이브 텍스트로 돌아와 수정·번역·접근성이 쉬워지고, 캐릭터는 투명 PNG
   (assets/img/malma/, 스티커 원본에서 추출)를 우하단에 얹는다. 기존 이미지 자산은 삭제하지
   않고 남겨 둔다(문서 데모·백업). */
/* 260821 8차 — ⭐ 문구와 말마 사이 간격을 "우연"이 아니라 구조로 보장한다.
   그동안은 말마 크기와 문구 폭이 서로 모르는 채 각자 정해져, 폭이 조금만 달라져도 다시 붙었다
   (클라이언트 리포트 3회). 이제 배너 높이(--fv-h) 하나에서 말마 크기가 파생되고, 그 말마가
   차지할 폭(--fv-mascot-w)에 최소 간격(--fv-gap)을 더한 만큼을 배너의 padding-right로
   **미리 예약**한다 → 문구는 그 안쪽에만 그려지므로 어떤 화면 폭에서도 --fv-gap이 지켜진다.
   ⚠ 값을 바꿀 때 손대는 것은 --fv-* 변수뿐이다. height·padding-right·말마 위치는 전부 파생값. */
.firstvisit{
  /* 배너 높이 — 모든 파생값의 기준. 데스크톱 사이드바는 998px에서 320px까지 좁아지므로
     고정값(92px)이면 그 구간에서 말마 예약 폭이 문구 자리를 먹어 문구가 2줄로 접힌다.
     폭에 비례해 흐르게 두고 1440에서 92px가 되도록 잡았다(998에서 78px). */
  /* 260831(총괄): 데스크톱 사이드바 배너를 낮춘다 — 위 PLAY NOW 미니 리스트가 더 잘 보이게.
     92 → 72px(1440), 78 → 60px(998). 말마도 함께 한 단계 작게(scale 1.8→1.6). */
  --fv-h:clamp(60px, 5vw, 72px);
  --fv-scale:1.6;       /* 말마 요소 높이 = --fv-h × 이 값 */
  --fv-crop:0.27;       /* 아래에서 잘라내는 비율(상체 구도 유지) */
  --fv-aspect:0.778;    /* 말마 PNG 가로÷세로(1256÷1615) — 폭 계산용 */
  --fv-gap:24px;        /* ⭐ 문구↔말마 최소 간격(보장값) */
  --fv-right:8px;       /* 말마 오른쪽 오프셋(음수면 배너 밖으로 걸친다) */
  --fv-mascot-w:calc(var(--fv-h) * var(--fv-scale) * var(--fv-aspect));
  position:relative;margin-top:auto;display:flex;align-items:center;border-radius:var(--r-card);
  height:var(--fv-h);padding-left:28px;
  padding-right:calc(var(--fv-right) + var(--fv-mascot-w) + var(--fv-gap));
  background:var(--cta-green);color:var(--ink)}
/* 260821: 998~1200 구간에서는 사이드바가 320px대로 좁아 22px 고정이면 문구가 2줄로 접힌다
   (말마 예약 폭을 뺀 나머지가 그만큼 줄기 때문) — 폭에 따라 18~22px로 흐르게 한다. */
/* 260831: 문구↔화살표 중앙 정렬(총괄 리포트). 화살표가 18px **고정**이라 제목이 커질수록
   크기 차가 벌어지고, 인라인 베이스라인 정렬이라 한글 글자 중심과 화살표 중심이 어긋나 있었다.
   → inline-flex + align-items:center로 두 글자 상자의 세로 중심을 맞추고, 화살표 크기는
   em(제목 비례)으로 바꾼다. 간격은 margin 대신 gap. */
.firstvisit__title{display:inline-flex;align-items:center;gap:8px;line-height:1;
  font-size:clamp(18px, 1.5vw, 22px);font-weight:700}
.firstvisit__arrow{font-size:.86em;font-weight:700;line-height:1;margin-left:0}
/* 말마 — 배너 우측. 위 --fv-* 변수에서 크기·위치가 전부 파생된다(직접 px를 쓰지 않는다).
   · 위로는 배너를 넘어가고(모자·머리 노출), 아래는 상체 하단에서 잘린다(허리 아래 다리 미노출).
   · overflow:hidden으로 자르면 위쪽 돌출까지 함께 잘리므로 요소 자체를 clip-path로 자른다.
   · bottom의 음수값이 clip으로 잘려나간 높이와 정확히 상쇄돼 "보이는 아래끝 = 배너 바닥선"이 된다.
   ⚠ 260826: 이 "위 돌출 + 하단 크롭" 구조를 클라이언트가 마음에 들어해 Collection 더보기 밴드
   마스코트(collection.css)에도 같은 구조를 이식했다 — 이 블록은 그 원본이니 되돌리지 말 것. */
.firstvisit__mascot{position:absolute;right:var(--fv-right);
  height:calc(var(--fv-h) * var(--fv-scale));
  bottom:calc(-1 * var(--fv-h) * var(--fv-scale) * var(--fv-crop));
  width:auto;object-fit:contain;object-position:bottom;pointer-events:none;
  clip-path:inset(0 0 calc(var(--fv-crop) * 100%) 0)}
/* ---------- 공통 섹션 ---------- */
.section{padding-top:var(--gap-section)}
/* 260811: GNB 바로 아래 "첫" 섹션만 HOME 히어로와 같은 리듬(.hero{padding-top:32px})으로 맞춘다.
   허브 4종(PLAY NOW·체험·공원 탐색·PARK LIVE)이 첫 섹션에도 --gap-section(72px)을 그대로 써서
   HOME보다 40px 더 벌어져 있었다 — 섹션 사이 간격(72px)은 그대로 두고 첫 섹션 진입부만 조정한다.
   HOME은 첫 자식이 .hero(+sr-only h1)라 이 선택자에 걸리지 않는다(영향 없음). */
main > .section:first-child{padding-top:32px}
.section__head{display:flex;flex-direction:column;gap:10px;margin-bottom:20px}
/* h1/h2 시각 스타일은 항상 동일 — Page Intro 제거 이후 각 허브 페이지의 첫 Featured 3 섹션 제목만
   h1(문서 구조상 그 페이지의 진짜 첫 제목)이고 그 아래 "전체 일정" 등은 h2이지만, 같은 Section
   Level(대표 영역 ↔ 전체 목록)의 제목이므로 크기·굵기·행간이 달라 보이면 안 된다. HTML Heading
   레벨(h1/h2)은 문서 구조용으로만 쓰고, 시각적 크기는 이 규칙 하나로 통일한다. */
.section__head h1,.section__head h2{font-size:var(--fs-h1);font-weight:700;line-height:1.18}
.section__head p{font-size:var(--fs-body-sm);color:var(--grey)}
/* 섹션 제목 오른쪽 끝 "전체 보기" — PLAY NOW(.playnow__more)와 같은 자리 규칙을 모든 HOME 섹션에 공용 적용 */
.section__head__top{display:flex;align-items:center;justify-content:space-between;gap:12px}
.section__more{position:relative;font-size:var(--fs-body-sm);font-weight:700;color:var(--ink);white-space:nowrap;flex:none}
/* 히트 영역 확장(260806) — 글자 높이(21px)가 곧 누를 수 있는 높이였다. 줄 높이를 키우면 섹션 제목과의
   정렬이 틀어지므로 가상 요소로만 세로 44px를 확보한다(가로는 글자 폭 그대로 — 좌우에 다른 조작 요소가 없다). */
.section__more::after{content:"";position:absolute;top:50%;left:0;right:0;transform:translateY(-50%);height:44px}

/* ---------- 태그 · 배지 · 칩 ---------- */
.tag{display:inline-flex;align-items:center;font-size:var(--fs-label);font-weight:700;border-radius:var(--r-sm);padding:5px 10px}
.tag--pill{border-radius:var(--r-full);background:var(--ink);color:var(--white);font-size:var(--fs-body-lg);padding:7px 16px}
/* 지역 배지 — 미디어 좌상단에 딱 붙는 형태라 '바깥쪽(좌상단) 라운드는 담기는 컨테이너와 같은 값'이어야 모서리가 맞는다.
   260819 재설계(클라이언트 요청): 좌상단 모서리에 융합되는 큰 박스(17px·비대칭 radius)가
   "무식하게 크고 못생겼다"는 피드백 — 커머스 앱 배지처럼 모서리에서 띄운 작은 필로 교체.
   반투명 다크 + 블러(유리 효과)라 어떤 사진 위에서도 읽히고, 모서리 곡률과 무관해져
   컨테이너별 --region-badge-r 주입 훅도 필요 없어졌다(관련 setter 제거). */
.card-region-badge{position:absolute;top:10px;left:10px;margin:0;background:rgba(0,0,0,.55);color:var(--white);font-weight:600;font-size:var(--fs-caption);line-height:1;padding:6px 10px;white-space:nowrap;width:max-content;border-radius:var(--r-full);pointer-events:none;z-index:1;backdrop-filter:blur(4px);-webkit-backdrop-filter:blur(4px)}
/* 큰 히어로 배너 위에서는 살짝만 키우고 여백도 비례해 띄운다 */
/* 260821: 히어로 배너는 이미지가 워낙 커서 캡션(12px) 다음 단계(13px)로는 여전히 눈에 잘 안
   띈다는 피드백 — 배너 전용으로 올렸다가(14px) "더 커야 한다"는 재피드백으로 16px까지 올린다.
   패딩·오프셋도 같이 키워 배지가 커진 만큼 배너 모서리에서 더 떨어지게 한다.
   카드 위 배지(기본 12px)는 그대로 — 히어로에서만 커진다. */
.hero__slide .card-region-badge,.nav-hero__slide .card-region-badge{font-size:var(--fs-body-lg);font-weight:700;padding:10px 18px;top:20px;left:20px}
/* 카테고리 태그 · 상태 배지 — 브랜드 문서 Badge 규격(M: height26 · fs13)에 맞춰 두 컴포넌트를 동일한 박스 모델로 통일.
   height+inline-flex로 높이를 고정해서, 한 줄에 나란히 놓여도(캘린더 일정 카드·상세 히어로·검색 결과) 자동으로 정렬·크기가 맞는다.
   margin-top:10px는 태그/배지 자체가 아니라 '.card 맨 아래 요소일 때만' 필요한 간격이므로 .card > 로 범위를 좁혔다
   (그 전엔 .tag--cat에 무조건 붙어 있어서, 가로 줄에서 배지 옆에 놓일 때 배지보다 아래로 처지는 정렬 버그가 있었다). */
.tag--cat{border-radius:var(--r-full);font-size:var(--fs-label);padding:0 12px;height:26px;display:inline-flex;align-items:center;width:fit-content}
.card > .tag--cat{margin-top:10px}
.tag--fac{background:var(--green-500);color:var(--ink)}
.tag--exp{background:var(--ground-500);color:var(--ink)}
.tag--event{background:var(--yellow-500);color:var(--ink)}
.tag--season{background:var(--coral-500);color:var(--ink)}
/* Type Badge(시설 유형: 공간/F&B/전시/액티비티) — 카테고리가 "시설"인 콘텐츠에만 붙는
   조건부 값이다(행사·시즌·체험은 이 필드 자체가 없음 — 운영 가이드 "카테고리 vs 유형 구분" 참고).
   그래서 같은 카드에 다른 Category Badge(행사/시즌/체험)와 나란히 놓일 일이 없고, 항상 "시설"
   Category와만 짝을 이룬다 — 이미 사람들이 "시설=초록"으로 인지하고 있는 .tag--fac과 똑같은
   색을 그대로 쓴다(새 배지 디자인을 따로 만들지 않음, 텍스트만 "시설"에서 실제 유형값으로 바뀜). */
.tag--type{border-radius:var(--r-full);font-size:var(--fs-label);padding:0 12px;height:26px;display:inline-flex;align-items:center;width:fit-content;background:var(--c-fac);color:var(--ink)}
.card > .tag--type{margin-top:10px}
.card__badges .tag--type{margin-top:0}
.badge{font-size:var(--fs-label);font-weight:500;border-radius:var(--r-full);padding:0 12px;height:26px;display:inline-flex;align-items:center;flex:none;width:fit-content;align-self:flex-start}
.card > .badge{margin-top:10px}
/* Status Chip(일정 상태) — Category Badge와 같은 컬러 계열을 쓰면 안 된다(예: 진행중이 행사 배지와 같은
   노란색이면 같은 카드에 나란히 놓였을 때 구분이 안 된다). 카테고리 컬러를 상속하지 않는 별도 톤 사용. */
.badge--on{background:var(--ink);color:var(--white)}
.badge--muted{background:#EDEDEF;color:var(--ink)}
.badge--ended{background:transparent;border:1px solid var(--line);color:var(--soft)}
/* Category Badge + Status Chip을 같은 카드에 나란히 표시할 때(예: PLAY NOW)의 공용 가로 래퍼 —
   .card는 flex-column이라 두 요소를 그냥 나열하면 세로로 쌓인다. */
/* 260821: 이미지 위 배지 묶음 — 지역 배지 + 유형/카테고리 배지를 좌상단 한 줄에 나란히 둔다
   ("언제 와도" 카드: 유형 배지를 카드 하단에서 여기로 이동). 래퍼가 위치를 잡으므로 안의
   지역 배지는 static으로 풀고, 유형 배지는 지역 배지와 같은 박스 치수(글자 12px·패딩 6×10)로
   맞춰 두 알약의 높이가 정확히 같게 한다 — 색만 다르다(지역=반투명 검정, 유형=브랜드 그린). */
.card__media-badges{position:absolute;top:10px;left:10px;z-index:1;display:flex;align-items:center;gap:6px;pointer-events:none}
.card__media-badges .card-region-badge{position:static}
.card__media-badges .tag--type,.card__media-badges .tag--cat{height:auto;font-size:var(--fs-caption);font-weight:600;line-height:1;padding:6px 10px;margin:0;white-space:nowrap}
.card__badges{display:flex;align-items:center;gap:6px}
.card > .card__badges{margin-top:10px}
.card__badges .tag--cat,.card__badges .badge{margin-top:0}
/* 더 작은 버전(브랜드 문서 Badge S: height19 · fs11) — 목록형 밀집 UI(캘린더·검색 결과)에 사용 */
.badge--sm{height:19px;padding:0 10px;font-size:var(--fs-badge)}

/* ---------- 요일 표시(Day Pills) — 요일 반복 운영 콘텐츠 공용 (260829 신설) ----------
   월~일 7칸 중 운영 요일만 옐로우 키컬러로 켜진다(표시 전용 — 누를 수 없다, Badge 계열).
   PLAY NOW "상설 프로그램" 그룹 헤더가 사용. 켜짐/꺼짐은 .is-on 클래스 하나로만 제어.
   260829 후속(총괄): 데스크톱 26px는 큰 그룹 제목 옆에서 너무 작았다 — 데스크톱 38px로
   확대(레퍼런스 주간 스트립 스케일), 모바일은 원래 보기 좋았던 26px 유지. */
.day-pills{display:inline-flex;gap:6px}
.day-pill{width:38px;height:38px;border-radius:50%;display:inline-flex;align-items:center;justify-content:center;
  font-size:var(--fs-body-sm);font-weight:700;color:var(--grey);background:var(--bg)}
.day-pill.is-on{background:var(--yellow-500);color:var(--ink)}
@media (max-width:997px){
  .day-pills{gap:4px}
  .day-pill{width:26px;height:26px;font-size:var(--fs-badge)}
}
/* touch-action:pan-x — 넘치는 칩 행을 손가락으로 끌 때 브라우저가 텍스트 선택 제스처로 오인하지
   않고(iOS Safari에서 실제로 재현되는 문제) 가로 스크롤로만 해석하게 한다. user-select:none은
   칩 라벨이 애초에 선택할 필요가 없는 조작 UI라 드래그 시작점이 텍스트여도 선택이 걸리지 않는다.
   .rail__track 등 카드 레일이 이미 드래그 중에만 쓰는 것(.is-dragging{user-select:none})과 같은
   목적이지만, 칩은 라벨이 항상 텍스트라 상시 적용이 맞다. */
.chips{display:flex;gap:8px;flex-wrap:wrap;margin-bottom:20px;touch-action:pan-x;-webkit-user-select:none;user-select:none}
/* 260813 2차 Visual Pass: Chip은 전부 "사용자가 누르는 조작 UI"(지역·카테고리·진행상태·채널
   선택, 드롭다운 트리거, 모바일 통합 필터 버튼)다 — 표시 전용 Badge(.badge/.tag--cat 등, 계속 pill)와
   시각적으로 구분하기 위해 pill(--r-full)에서 rounded rectangle(--r-md)로 바꾼다.
   .chip--slots(드롭다운 트리거)·.chip.is-selected 전부 이 한 규칙만 상속하므로 여기 하나만 고치면
   HOME 취향대로·PLAY NOW 지역/카테고리/진행상태·PLAY NOW B·공원탐색·PARK LIVE 채널 필터가 함께 바뀐다. */
.chip{height:36px;min-width:48px;padding-inline:14px;border-radius:var(--r-md);background:var(--white);border:1px solid var(--line);color:var(--grey);font-size:var(--fs-label);font-weight:500;display:inline-flex;align-items:center;gap:8px;white-space:nowrap;flex:none}
.chip:hover{background:var(--bg)}
/* 260819: 클릭/탭 직후 일부 브라우저가 그리는 기본 포커스 링(선택 칩 위의 검정 라인)을 모든
   칩·드롭다운 옵션에서 차단한다 — plain :focus에만 적용하며, 키보드 :focus-visible 링(전역
   규칙)은 그대로 살아 있어 a11y를 해치지 않는다. */
.chip,.chip-dd__opt{-webkit-tap-highlight-color:transparent}
.chip:focus:not(:focus-visible),.chip-dd__opt:focus:not(:focus-visible){outline:none}
/* 260820: 일부 브라우저는 마우스로 칩을 누른 뒤에도 :focus-visible을 적용해 선택된 칩에 검정
   포커스 링(--focus-ring = ink 2px)이 남는다(클라이언트 리포트). 링 자체를 없애면 키보드
   접근성이 깨지므로, home.js가 "마지막 입력이 포인터였는지"만 html[data-input]에 표시하고
   그때만 링을 감춘다 — Tab·화살표로 이동하면 data-input이 key로 바뀌어 링이 정상 노출된다. */
html[data-input="pointer"] :where(.chip,.chip-dd__opt,.chip-dd__trigger):focus-visible{outline:none}
/* 260819: 선택 상태를 검정 Filled → 브랜드 키컬러 옐로우 Filled로 교체(클라이언트 요청).
   텍스트는 밝은 옐로우 위에서 대비가 나오는 --ink로 바꾼다(흰색은 거의 안 보임).
   PLAY NOW 카테고리/지역/진행상태·공원탐색·PARK LIVE 채널 필터 등 .chip.is-selected를 쓰는
   모든 화면이 이 한 규칙으로 함께 바뀐다(위 260813 주석 참고) — 페이지별 재정의 없음.
   .chip--slots(드롭다운 트리거)는 원래도 이 규칙을 상속하지 않고 항상 Outline이라 무관. */
.chip.is-selected{background:var(--yellow-500);border-color:var(--yellow-500);color:var(--ink)}
/* 취향 칩 등에 붙는 이모지 아이콘(THEME_ICONS, common/theme-data.js) — 기존 .ico-svg(18px)와
   시각 크기를 맞추되 emoji 글리프 자체 여백 때문에 폰트 크기는 살짝 낮춘다. color emoji는
   currentColor를 따르지 않으므로(항상 고유 색) 선택 상태에서도 텍스트 색과 무관하게 원래 색 유지 —
   의도된 동작(옐로우 배경 위에서도 이모지 컬러가 그대로 보여야 더 "귀엽고 재미있는" 인상). */
.chip__emoji{font-size:16px;line-height:1;flex:none}
/* 드롭다운 트리거(.chip--slots)는 카테고리 탭(.chip)과 조작 방식이 달라 선택 Filled(옐로우)를
   쓰지 않는다 — 선택값은 배경색이 아니라 버튼 텍스트로만 표시한다. 260819 재조정(클라이언트
   피드백): ink 테두리가 "선택된 박스"처럼 보인다는 지적으로, 옆의 일반 필터 칩과 같은 연회색
   라인(--line) + 연회색 필(--bg)로 톤을 낮췄다. 텍스트·아이콘은 ink 유지(현재 값 가독성).
   is-selected 클래스 유무와 무관하게 항상 이 톤이다.
   탭/클릭 시 일부 브라우저가 그리는 기본 포커스 링·하이라이트는 끄되(:focus-visible이 아닌
   plain :focus만), 키보드 포커스 링(:focus-visible, 전역 규칙)은 그대로 살아 있다 — a11y 유지. */
.chip--slots,.chip--slots.is-selected{background:var(--white);border-color:var(--line);color:var(--ink)} /* 260819 3차: 필 색도 옆 칩과 완전히 동일(흰색)로 — 연회색 필은 혼자 눌린 상태처럼 보인다는 피드백 */
.chip--slots:hover{background:var(--bg)}
.chip__pre,.chip__suf{font-size:var(--fs-caption);opacity:.85}
/* 드롭다운 칩 캐럿 — 인라인 <svg>(arrow_down.svg와 동일한 path)로 직접 그린다.
   이전에는 mask+currentColor(배경색을 아이콘 모양으로 잘라내는 방식)를 썼는데, 이 방식이
   일부 브라우저 환경에서 아이콘 자체를 그리지 못하는 사례가 있어 인라인 svg로 옮겼다 —
   stroke="currentColor"가 SVG 안에 직접 있어 부모 글자색을 그대로 따르는 점은 동일하다.
   크기는 칩 높이 36px 대비 일반적인 버튼 내 아이콘 비율인 16px. 열리면 180° 회전(.is-up). */
.chip__caret{width:16px;height:16px;flex:none;opacity:.85;transition:transform .2s ease}
.chip__caret.is-up{transform:rotate(180deg)}
/* 공용 아이콘 — 인라인 <svg>에 stroke="currentColor"가 직접 있어
   버튼·링크의 글자색을 그대로 따른다. 크기만 여기서 통일 관리(.ico-svg 기본 18px). */
.ico-svg{display:inline-block;width:18px;height:18px;flex:none}
/* mask 축약형(mask:var(--ico) center/contain no-repeat)은 Safari에서 값+position/size가
   섞인 축약 구문을 제대로 파싱하지 못해 아이콘 전체가 렌더링되지 않는 경우가 있다 —
   모든 브라우저에서 동일하게 동작하도록 항상 개별(longhand) 속성으로 나눠 쓴다. */
/* url()을 --ico 커스텀 프로퍼티에 담아 var()로 물려주는 방식은 일부 브라우저에서
   상대경로 해석이 어긋나 아이콘이 통째로 사라지는 사례가 있었다 — 각 .ico--* 클래스가
   mask-image를 직접 선언하도록 바꿔 커스텀 프로퍼티 간접 참조 자체를 없앴다(가장 안전한 방식). */
/* 크기 modifier — .ico-svg(기본 18px)와 함께 써서 필요한 곳만 다른 크기로(예: <svg class="ico-svg icon--sm">) */
.icon--sm{width:16px;height:16px}
.icon--md{width:20px;height:20px}
.icon--lg{width:24px;height:24px}

/* 지역 드롭다운 (단일 선택 · 칩 라벨 갱신) */
.chip-dd{position:relative;flex:none}
.chips__divider{width:1px;align-self:stretch;background:var(--line);margin-inline:2px;flex:none}
/* 구분선 왼쪽(드롭다운류)과 오른쪽(카테고리 칩)을 한 줄 안에서 좌/우로 벌려 배치할 때 사용 */
.chips__divider--push{margin-left:auto}
/* 260813: 떠 있는 패널을 그림자 대신 얇은 border로 구분한다(Shadow 최소화 방향).
   border는 원래도 있었으므로 그림자만 걷어냈다 — 면이 깨끗해지고 경계는 그대로 읽힌다. */
/* position:fixed(절대 좌표는 버튼 기준 JS 계산, wireChipDropdown open()) — .gnb-dd__panel과 같은
   이유(아래 주석 참고)로 position:absolute를 쓰지 않는다: 이 트리거가 모바일에서 overflow-x:auto인
   .chips 행 안에 있으면(취향대로·공간시설 결합 필터 등) 브라우저가 overflow-y도 auto로 취급해
   패널이 그 행 높이로 세로 클리핑되어 옵션이 한 줄만 보이고 잘려 보인다(260819 3차에서 실측 재현). */
/* z-index:110 — .modal(100)보다 위. 이 드롭다운이 모바일 필터 Bottom Sheet(.modal) 안에서
   열릴 수 있게 되면서(wireFilterSheet, 아래 필터 그룹 참고) 시트 자체보다 낮으면 옵션 목록이
   시트 뒤에 깔려 보이지 않는다. */
.chip-dd__panel{position:fixed;z-index:110;min-width:200px;background:var(--white);border:1px solid var(--line);border-radius:var(--r-lg);padding:8px;list-style:none;display:flex;flex-direction:column}
.chip-dd__panel[hidden]{display:none}
.chip-dd__opt{display:flex;align-items:center;gap:10px;width:100%;padding:11px 12px;border-radius:var(--r-md);font-size:var(--fs-body);color:var(--ink);text-align:left}
.chip-dd__opt:hover{background:var(--bg)}
/* 260813: 체크박스 테두리를 1.5px 하드코딩 회색 → 1px 공용 --line으로, radius도 6→4로 낮췄다.
   드롭다운 패널·시트·검색 필터가 전부 이 한 클래스를 쓰므로 체크박스 생김새가 한 번에 통일된다. */
.chip-dd__box{width:22px;height:22px;border-radius:4px;border:1px solid var(--line);background:var(--white);flex:none;display:flex;align-items:center;justify-content:center;color:transparent;font-size:var(--fs-label);font-weight:700;line-height:1}
.chip-dd__opt.is-checked{font-weight:700}
.chip-dd__opt.is-checked .chip-dd__box{background:var(--yellow-500);border-color:var(--yellow-500);color:var(--ink)} /* 260819: 위 .chip.is-selected와 같은 옐로우 선택 언어로 통일(지역·유형 드롭다운 옵션 체크) */

/* ---------- 필터 그룹 + 모바일 Bottom Sheet (260819 4차) ----------
   Collection의 결합 필터 행(지역 드롭다운 + 테마/유형)은 데스크톱에서 그대로 노출하되,
   모바일(≤997px)에서는 같은 DOM을 그대로 옮겨 기존 공용 .modal/.sheet-modal 셸 안에 담는다
   (collection.js buildFilters의 window.wireFilterSheet). 그룹 래퍼(.filter-sheet__group)는
   평소 display:contents라 데스크톱 레이아웃(.chips 한 줄)에 전혀 영향이 없고, .modal 안으로
   들어갔을 때만 라벨 있는 블록 섹션으로 펼쳐진다 — 마크업을 두 벌 만들지 않는다. */
.filter-sheet__group{display:contents}
.filter-sheet__label{display:none}
/* renderFilterChips가 대상 컨테이너의 innerHTML을 통째로 새로 쓰기 때문에, 라벨과 같은 요소에
   바로 칩을 그리면 라벨이 지워진다 — 칩 전용 하위 컨테이너에 붙이는 클래스. 이 컨테이너도 항상
   display:contents라 데스크톱/모바일 어느 쪽에서도 레이아웃에 자기 자신의 흔적을 남기지 않는다
   (모바일에서 블록으로 펼쳐지는 것은 바깥 .filter-sheet__group의 역할). */
.filter-sheet__group-body{display:contents}
/* .filter-sheet-panel(항상 붙는 식별 클래스, wireFilterSheet) — 검색 모달 등 다른 .chips가
   같은 .modal 안에 있어도 영향받지 않도록, 그룹을 세로로 쌓는 대상은 이 패널로만 한정한다. */
.modal .filter-sheet-panel{display:block}
.modal .filter-sheet__group{display:block;margin-bottom:24px}
.modal .filter-sheet__group:last-child{margin-bottom:0}
.modal .filter-sheet__label{display:block;font-size:var(--fs-body-sm);font-weight:700;color:var(--ink);margin:0 0 8px}
/* 구분선은 데스크톱 한 줄 배치에서만 의미가 있다 — 시트 안 블록 섹션에는 필요 없다 */
.modal .chips__divider{display:none}

.modal__foot.filter-sheet__foot{display:flex;gap:10px}

/* 필터 시트는 캘린더·검색 모달과 달리 내용이 짧다 — common/calendar.css의
   .sheet-modal .modal__box{height:min(640px,86vh)} 고정 높이(콘텐츠량이 늘 많은 캘린더·검색
   전용 설계)를 그대로 받으면 푸터 위에 빈 공간이 크게 남는다. .sheet-modal.sheet-modal--auto로
   내용 높이에 맞게 되돌린다(특이도를 올리기 위해 두 클래스를 함께 건다 — calendar.css가
   home.css보다 나중에 로드되어 같은 특이도면 그쪽이 이긴다). */
.sheet-modal.sheet-modal--auto .modal__box{height:auto}
@media (max-width:997px){
  .sheet-modal.sheet-modal--auto .modal__box{height:auto;max-height:88vh;max-height:88svh}
}

/* 필터 Bottom Sheet 트리거 — ⚠ 260819 2차 확정: 비활성(전 폭 항상 노출).
   한때 모바일(≤997)에서 결합 필터 행을 "필터" 트리거 하나로 접어 Bottom Sheet에 담았으나
   (Phase 9), 클라이언트가 "모든 폭에서 필터를 항상 노출"로 재확정해 그 분기를 걷어냈다 —
   이제 결합 필터 행이 해상도와 무관하게 그대로 보이고(좁은 폭에서는 .chips의 기본 wrap으로
   여러 줄), 이 트리거는 어디서도 나타나지 않는다.
   wireFilterSheet(home.js)·시트용 CSS·collection.js의 호출은 지우지 않고 보존한다 — 다시
   시트로 되돌리려면 아래 media 블록(주석)만 복원하면 된다. 트리거 자체는 새 컴포넌트가
   아니라 기존 .chip.chip--slots 그대로였다(검색 모달 드롭다운 트리거와 동일 스타일).
@media (max-width:997px){
  [data-filter-sheet-panel]{display:none}
  .filter-sheet-trigger{display:inline-flex}
}
*/
.filter-sheet-trigger{display:none}

/* ---------- GNB "방문정보" 드롭다운 ----------
   위 .chip-dd와 같은 시각 언어(흰 배경·라운드·그림자)를 쓰되, 항목이 실제 외부 링크라 체크 표시
   대신 오른쪽에 외부 링크 아이콘을 둔다. 패널은 .gnb__menu(모바일 가로 스크롤 컨테이너) 밖에
   마크업되어 있고 JS(wireGnbDropdown)가 열 때마다 버튼 위치 기준으로 position:fixed 좌표를
   계산해 붙인다 — overflow-x:auto 컨테이너 안에 두면 세로로 잘려 보이는 문제를 피하기 위함. */
.gnb-dd{position:relative;display:flex}
.gnb-dd__trigger{display:inline-flex;align-items:center;gap:4px;font:inherit;font-family:"A2Z",var(--font-sans);font-size:var(--fs-card);font-weight:600;padding:4px 0 8px;background:none;border:0;color:var(--gnb-fg,var(--ink));cursor:pointer;white-space:nowrap} /* 260819: 메뉴 링크와 동일 타이포(위 .gnb__menu a 주석 참고) */
.gnb-dd__trigger:hover{opacity:.7}
.gnb-dd__trigger .chip__caret{opacity:.7}
.gnb-dd__panel{position:fixed;z-index:60;min-width:180px;background:var(--white);border:1px solid var(--line);border-radius:var(--r-lg);padding:8px;list-style:none}
.gnb-dd__panel[hidden]{display:none}
.gnb-dd__panel li a{display:flex;align-items:center;justify-content:space-between;gap:16px;width:100%;padding:11px 12px;border-radius:var(--r-md);font-size:var(--fs-body);font-weight:400;color:var(--ink)}
.gnb-dd__panel li a:hover{background:var(--bg)}
.gnb-dd__panel li a svg{width:16px;height:16px;flex:none;color:var(--soft)}

/* ---------- 카드 레일 (캐러셀) ---------- */
.rail{position:relative}
/* 스크롤 여지가 있을 때만(다음 화살표가 보일 때) 우측 카드가 갑자기 잘리지 않고
   배경으로 자연스럽게 흐려지도록 페이드 오버레이 표시 — 모든 캐러셀 공통 */
.rail:has(.rail__arrow--next:not(.is-hidden))::after{content:"";position:absolute;top:0;right:0;bottom:0;width:88px;background:linear-gradient(to right, rgba(255,255,255,0), var(--white) 82%);pointer-events:none;z-index:1}
@media (max-width:997px){
  .rail::after{display:none} /* 모바일은 화살표 없이 스와이프 전용 — 페이드도 함께 숨김 */
  .chips__divider--push{margin-left:0} /* 좁은 화면은 줄바꿈되므로 강제로 밀어붙이지 않는다 */
}
/* snap: proximity — 오버플로가 카드 1장보다 작은 섹션에서도 끝까지 도달 가능
   (드래그 후 카드 정렬은 home.js snapNearest가 보장) */
.rail__track{position:relative;display:flex;gap:var(--gap-card,32px);overflow-x:auto;scroll-snap-type:x proximity;scrollbar-width:none;padding-bottom:4px}
.rail__track::-webkit-scrollbar{display:none}
.rail__track>*{scroll-snap-align:start;flex:none}
/* 우측 블리드: 콘텐츠 폭 밖(뷰포트 끝)까지 카드 피크 */
.rail--bleed{margin-right:calc(var(--pad-page)*-1)}
.rail--bleed .rail__track{padding-right:var(--pad-page)}
/* 260813: 캐러셀 화살표도 그림자 대신 얇은 border로 — 이미지 위에 떠 있어도 면이 탁해지지 않는다 */
.rail__arrow{position:absolute;top:calc(var(--media-h,280px)/2 - 26px);width:52px;height:52px;border-radius:50%;background:var(--white);border:1px solid var(--line);display:flex;align-items:center;justify-content:center;z-index:2}
.rail__arrow--prev{left:8px}
.rail__arrow--next{right:8px}
/* 260828: 블리드 레일은 박스가 --pad-page만큼 뷰포트 쪽으로 넓어 화살표가 다른 섹션보다
   오른쪽에 뜬다 — 화살표는 항상 컨테이너 우측선(다른 레일과 같은 세로 라인)에 정렬한다.
   (같은 날 후속으로 취향대로의 블리드 자체를 제거해 현재 사용처는 0이지만, 블리드 레일을
   다시 쓰게 되면 이 규칙이 정렬을 보장하므로 유틸리티로 유지) */
.rail--bleed .rail__arrow--next{right:calc(8px + var(--pad-page))}
.rail__arrow.is-hidden{display:none}
.rail__arrow svg{width:18px;height:18px;fill:none;stroke:var(--ink);stroke-width:1.8;stroke-linecap:round;stroke-linejoin:round}
.rail__empty{padding:40px 0;font-size:var(--fs-body-sm);color:var(--grey)}
/* [data-dim]은 "이 카드 미디어는 딤 처리 대상"이라는 의미 표시다. 260806 이전에는 home.js가 Canvas로
   이미지 색을 추출해 --dim을 주입했으나, 이 CSS를 포함해 --dim을 읽는 곳이 한 곳도 없어 삭제했다
   (home.js 3번 주석 참고). 실제 딤은 .card__media의 그라디언트가 담당한다 — 빈 규칙을 남기지 않는다. */

/* ---------- Hub Featured / Rail (허브 대표 콘텐츠 — 레일형) ----------
   컴포넌트 패밀리 Hub Featured의 두 번째 Variant. 열기/닫기·드래그·화살표·스냅은 전부 기존
   .rail/.rail__track/.rail__arrow/wireRailArrows/dragScroll을 그대로 재사용(home.js의
   setupFeaturedGroup) — 여기서는 이 Variant일 때만 카드 폭을 NOL 참고형(Active 카드를 크게,
   다음 카드는 일부만 보이는 Preview)으로 재정의한다. 이 스코프(.hub-featured--rail) 밖의 다른
   .rail.rail--arrows(최신 현장 소식, 지역별 공간 등)는 기존 고정폭 카드 그대로 영향받지 않는다. */
.hub-featured--rail{margin-bottom:32px}
.hub-featured--rail .rail__track{scroll-snap-type:x mandatory}
.hub-featured--rail .rail__track>.card{flex:0 0 auto;width:min(58%, 460px);min-width:280px}
.hub-featured__indicator{position:absolute;left:50%;bottom:-28px;transform:translateX(-50%);font-size:var(--fs-caption);font-weight:700;color:var(--soft);margin:0}
@media (max-width:997px){
  .hub-featured--rail .rail__track>.card{width:86%;max-width:400px;min-width:240px}
  .hub-featured__indicator{bottom:-24px}
}
@media (prefers-reduced-motion: reduce){
  .hub-featured--rail .rail__track{scroll-behavior:auto}
}

/* ---------- Hub Featured / Rail — Wide Banner Card (신규 Variant) ----------
   NOL 참고형: 이미지가 카드 전체를 채우는 가로로 긴 배너 + 이미지 위 텍스트(제목·메타)를 하단
   그라데이션과 함께 얹는다 — 기존 Content Card 문법("미디어→하단 텍스트, 오버레이 없음")과는
   의도적으로 다른 별도 카드 타입이다(기존 .card--wide는 변경 없이 그대로 유지·재사용
   가능 — PARK LIVE 추천 클립은 계속 이 타입을 쓴다). 이미지는 현재 자산을 재사용하거나(비율이
   맞지 않으면 완료 보고에 교체 검토로 기록) 그라데이션 placeholder를 쓴다. */
.hub-featured-card--banner{position:relative;display:block;border-radius:var(--r-media);overflow:hidden;aspect-ratio:21/9;background:var(--img,var(--neut-thumb));background-size:cover;background-position:center;flex:0 0 auto;width:min(76%, 720px);min-width:260px}
.hub-featured-card--banner::after{content:"";position:absolute;inset:0;background:linear-gradient(to top, rgba(0,0,0,.6), rgba(0,0,0,0) 60%);pointer-events:none}
.hub-featured-card--banner__body{position:absolute;left:24px;right:24px;bottom:18px;z-index:1;color:var(--white)}
.hub-featured-card--banner__title{font-size:var(--fs-h2);font-weight:800;margin:0 0 6px;line-height:1.25}
.hub-featured-card--banner__meta{font-size:var(--fs-label);font-weight:500;margin:0;opacity:.92}
.hub-featured-card--banner>.tag,.hub-featured-card--banner>.card__badges{position:absolute;top:16px;left:16px;z-index:1;margin:0}
@media (max-width:997px){
  .hub-featured-card--banner{width:88%;max-width:420px;min-width:220px;aspect-ratio:16/9}
  .hub-featured-card--banner__title{font-size:18px}
  .hub-featured-card--banner__body{left:16px;right:16px;bottom:14px}
}

/* ---------- Hub Featured / Rail (허브 페이지 첫 섹션 전용) ----------
   PLAY NOW·PARK LIVE·체험·공원 탐색 4개 페이지가 전부 이 하나의 구조를 공유한다 — 페이지마다
   별도 캐러셀 CSS/JS를 두지 않는다(재생/정지·카운터·드래그·루프는 home.js의 setupNavHero()가
   HOME 히어로와 동일한 알고리즘으로 4개 페이지 공통 담당). HOME 메인 히어로(.hero)와는 별도
   컴포넌트다 — HOME은 폭 전체 1장(비율 고정·높이 무제한)이지만 이 Variant는 처음부터 "중앙 카드
   강조 + 좌우 카드 프리뷰"가 목적이라 카드 폭 자체를 vw와 px 상한(min())으로 동시에 제한한다.
   비율은 고정, 폭은 min()으로 상한 → 화면이 아무리 넓어져도 카드의 실제 픽셀 높이가 더 이상
   커지지 않는다("너비 반응형 + 높이 상한").
   Full-bleed: .nav-hero 자체를 100vw로 뷰포트 끝까지 확장한다(Section Heading은 그대로
   .container 정렬 유지 — 이 규칙 하나만 컨테이너 밖으로 나간다). 예전 버전은 .nav-hero가
   .section.container 안쪽 padding-inline(--pad-page) 폭 그대로만 썼고, 그 안에서 cqw로 좌우
   프리뷰 폭을 계산해서 프리뷰가 화면 끝까지 못 가고 컨테이너 padding 선에서 한 번 더 잘려
   보였다 — 이제는 트랙 자체가 화면 끝까지 나가고, 프리뷰 여백(--nh-peek)만큼만 트랙 padding으로
   가운데 정렬한다. */
.nav-hero{position:relative;width:100vw;margin-inline:calc(50% - 50vw)}
.nav-hero__banner{position:relative}
/* 좌우 흰색 Fade Mask는 없앴다 — 카드가 슬라이드 이동 중에 마스크 경계를 통과하면서 밝기가
   순간적으로 바뀌어 보여 모션이 끊기는 느낌을 줬다. 프리뷰 카드는 마스킹 없이 그대로 노출한다. */
/* 슬라이드 폭 — vw 기준(배너가 100vw이므로 cqw와 동일 효과) + px 상한. 페이지별 높이 override를
   추가하지 않고 네 페이지가 이 한 줄만 공유한다. */
.nav-hero__track{position:relative;display:flex;gap:var(--gap-card);overflow-x:auto;overflow-y:hidden;scroll-snap-type:x mandatory;scrollbar-width:none;padding-inline:calc((100vw - min(60vw,760px))/2);cursor:grab}
.nav-hero__track::-webkit-scrollbar{display:none}
.nav-hero__track.is-dragging{cursor:grabbing;scroll-snap-type:none;user-select:none}
.nav-hero__track.is-dragging *{pointer-events:none}
.nav-hero__slide{position:relative;display:block;flex:0 0 min(60vw,760px);width:min(60vw,760px);aspect-ratio:16/9;scroll-snap-align:center;overflow:hidden;border-radius:var(--r-hero)}
.nav-hero__slide picture{position:absolute;inset:0;display:block}
.nav-hero__slide img{width:100%;height:100%;object-fit:cover;display:block}
/* PLAY NOW도 데스크톱에서 공통 16:9를 그대로 쓴다(과거엔 완성형 배너의 원본 비율(--hero-ratio-desk)을
   따로 썼으나, 실제 배너 3종 모두 16:9로 크롭해도 제목·날짜 텍스트가 잘리지 않는 것을 확인해 예외를
   없앴다 — 네 페이지의 중앙 배너 높이가 완전히 같아진다). */
.nav-hero__arrow{position:absolute;top:50%;transform:translateY(-50%);width:52px;height:52px;border-radius:50%;background:var(--white);border:1px solid var(--line);display:flex;align-items:center;justify-content:center;z-index:3}
.nav-hero__arrow--prev{left:8px}
.nav-hero__arrow--next{right:8px}
.nav-hero__arrow svg{width:18px;height:18px;fill:none;stroke:var(--ink);stroke-width:1.8;stroke-linecap:round;stroke-linejoin:round}
/* 슬라이드 내부 콘텐츠 — 이미지 위 텍스트 오버레이(지역·제목·일정). 완성형 배너 이미지를 그대로
   쓰는 PLAY NOW는 이 오버레이를 쓰지 않는다(텍스트가 이미지에 이미 포함되어 있음). */
/* 260811: 텍스트 가독성 보강 — 기존 단일 stop(62%→0% at 55%) 대신 하단을 더 어둡게(.62→.78),
   중간 지점을 하나 추가해 위로 갈수록 더 빠르게 투명해지도록(48%면 완전 투명) 조정했다.
   새 레이어를 얹지 않고 기존 ::after의 background 값만 바꾼 것 — 이미지 상단 절반 이상은
   그대로 원본 색감을 유지한다. */
.nav-hero:not(.nav-hero--banner-ratio) .nav-hero__slide::after{content:"";position:absolute;inset:0;background:linear-gradient(to top, rgba(0,0,0,.78) 0%, rgba(0,0,0,.4) 24%, rgba(0,0,0,0) 48%);pointer-events:none}
.nav-hero__slide>.tag,.nav-hero__slide>.card__badges{position:absolute;top:16px;left:16px;z-index:1;margin:0}
/* PLAY NOW 전용: 지역 배지(card-region-badge)가 이미 좌상단을 차지하므로 Category/Status Badge는
   우상단으로 옮겨 겹치지 않게 한다(다른 3개 페이지는 지역 배지를 쓰지 않아 영향 없음). */
.nav-hero--banner-ratio .nav-hero__slide>.card__badges{left:auto;right:16px}
.nav-hero__body{position:absolute;left:24px;right:24px;bottom:20px;z-index:1;color:var(--white)}
/* 260811: title 한 단계 확대 — --fs-hero-meta(24px/13.5px, 모바일 값이 본문보다 작아 헤딩 부적합)
   대신 이미 있는 --fs-card-lg(26px/20px)로 교체. 새 font-size 토큰은 만들지 않았다. */
.nav-hero__title{font-size:var(--fs-card-lg);font-weight:var(--fw-bold);margin:0 0 6px;line-height:1.25}
/* 260811: meta 가독성 — 크기는 유지, 기존 스케일 안에서 weight만 500→600(semibold), 인위적
   opacity 감쇠(.92)도 제거해 하단 dim 보강분과 함께 대비를 높였다. */
.nav-hero__meta{font-size:var(--fs-body-sm);font-weight:600;margin:0;opacity:1}
@media (max-width:997px){
  .nav-hero__body{left:16px;right:16px;bottom:14px}
  /* 모바일 크기는 새 수치를 만들지 않고 HOME 모바일 히어로가 쓰는 토큰(--hero-peek/--hero-card)을
     그대로 재사용한다 — 네 페이지가 HOME과 같은 폭·높이·라운딩·여백·갭으로 보이게 하기 위함
     (HOME 히어로 컴포넌트 자체는 건드리지 않음, 값만 참조). */
  /* HOME 히어로와 같은 토큰을 쓰므로 위 롤백 버그도 동일하게 발생한다 — 같은 방식으로 고친다. */
  .nav-hero__track{gap:var(--gap-card);
    --hero-side:max(var(--hero-peek), calc((100% - var(--hero-card)) / 2));
    padding-inline:var(--hero-side);scroll-padding-inline:var(--hero-side)}
  .nav-hero__slide{flex-basis:var(--hero-card);width:var(--hero-card);aspect-ratio:7/8}
  .nav-hero__arrow{display:none}
  /* 모바일 전용 Full-bleed 대체 기법 — 데스크톱(≥998px)의 100vw 트릭은 vw가 스크롤바 폭까지
     포함해 계산되는 성질 때문에, 클래식 스크롤바 환경의 좁은 폭에서 정확히 스크롤바 폭(약 15px)만큼
     페이지 가로 스크롤을 만들었다(실기기 오버레이 스크롤바에서는 안 드러날 수 있는 값이라도
     안전하게 vw에 의존하지 않는 방식으로 바꾼다).
     ※ 260812 정정: 이 주석은 원래 "scrollbar-gutter:stable이 998px 이상에서만 걸려 있어서"라고
     설명했으나, 그 미디어쿼리 제한 자체가 모달 열 때 레이아웃이 밀리는 버그의 원인이라 제거됐다
     (파일 상단 html{scrollbar-gutter:stable} 참고). 아래 대체 기법은 gutter와 무관하게 유효하다. */
     모바일은 --pad-page(고정 px, 현재 16px)만큼만 컨테이너 밖으로 나가면 이미 화면 끝이므로
     vw 대신 알고 있는 padding 값만큼 %+px로 계산한다 — 스크롤바 유무와 무관하게 항상 정확하다. */
  .nav-hero{width:calc(100% + var(--pad-page) * 2);margin-inline:calc(var(--pad-page) * -1)}
}
@media (prefers-reduced-motion: reduce){
  .nav-hero__track{scroll-behavior:auto}
  .nav-hero__slide{transition:none}
}

/* 마우스 드래그 스크롤 (home.js dragScroll) */
.rail__track,.courses,.hero__track,.playnow__list{cursor:grab}
.rail__track.is-dragging,.courses.is-dragging,.hero__track.is-dragging,.playnow__list.is-dragging{cursor:grabbing;scroll-snap-type:none;user-select:none}
.rail__track.is-dragging *,.hero__track.is-dragging *,.playnow__list.is-dragging *{pointer-events:none}

/* ---------- 카드 (NOL 문법: 미디어 + 하단 텍스트) ---------- */
.card{display:flex;flex-direction:column}
/* overflow:hidden — 좌상단 지역 배지가 미디어의 둥근 모서리 밖으로 삐져나오지 않도록 잘라낸다(히어로 배너와 동일 처리) */
.card__media{position:relative;border-radius:var(--r-media);overflow:hidden;background:var(--img,var(--neut-thumb));background-size:cover;background-position:center;margin-bottom:16px}
.card__title{font-size:var(--fs-h3);font-weight:700;padding-inline:2px;display:-webkit-box;-webkit-line-clamp:2;-webkit-box-orient:vertical;overflow:hidden}
/* 260821 카드 텍스트 위계 정돈(클라이언트: "제목·설명·방문정보 구분이 약하다", DIVE 카드 참고 —
   단, 우리 spacing 안에서). 세 줄을 역할별로 다르게 읽히게 한다:
   · 제목   — 굵게(700), ink                      · 설명   — 회색·가벼운 400, 제목에 6px 붙음
   · 방문정보 — 회색 → **ink 600**(한 단계 올림), 설명과 8px 띄움. 날짜·운영시간은 "읽고 넘기는
     설명"이 아니라 "방문 계획에 쓰는 값"이라 설명보다 또렷해야 한다.
   간격은 5/5 → 6/8 — 레퍼런스(10~14)보다 좁게, 기존 토큰 리듬 유지. */
.card__sub{font-size:var(--fs-body-sm);font-weight:400;color:var(--grey);margin-top:6px;padding-inline:2px} /* 260828 저녁 메일: 1줄 말줄임 해제 — 설명 끝까지 노출(카드 높이는 내용에 따름) */
.card__meta{font-size:var(--fs-label);font-weight:600;color:var(--ink);margin-top:8px;padding-inline:2px;display:-webkit-box;-webkit-line-clamp:1;-webkit-box-orient:vertical;overflow:hidden}
.card--pick{width:240px}                 /* 데스크탑 5장 노출 · 미디어 비율 고정(1:1) */
.card--pick .card__media{aspect-ratio:1/1;height:auto}
.card--pick .card__title{font-size:20px}
.card--pick .card__meta{margin-top:8px}
.card--wide{width:420px}
.card--wide .card__media{aspect-ratio:var(--content-card-media-ratio)}
/* 260828 2차: 세로 카드(280×411:731) → **정방형 340px**(클라이언트 확정 — "정방형으로 크게").
   비율이 제각각인 실제 SNS/유튜브 썸네일을 한 프레임에 담기 위해 미디어는 card__media--sq(1:1) +
   card__media--fit(contain+blur 배경) 조합만 쓴다. 구 세로 비율 클래스(--tall)는 사용처가 없어져 제거. */
.card--sns{width:340px}
.card__media--sq{aspect-ratio:1/1;background:var(--neut-thumb)}
.card__title--sns{font-size:20px}
/* 260811: IG/YT/BL 약어 원형 배지 → 한글 풀네임(인스타그램/유튜브/블로그) 노출로 바뀌면서
   고정 원형(30x30)에 텍스트가 들어가지 않아 auto-width 알약형으로 바꿨다 — 배경·글자색·굵기 등
   기존 배지 톤은 그대로 두고 모양(고정폭 원 → 콘텐츠 길이에 맞는 pill)과 padding만 대응한다. */
/* 260829: 채널 한글 텍스트 알약 → 모노톤 아이콘 원형(고객 4차 메일 ③-2 — Figma "Simple SNS ICON"
   세트 3종, ink 원 + 흰 아이콘). 채널명 텍스트는 카드 aria-label이 계속 전달한다. */
.sns-ch{position:absolute;top:14px;left:14px;width:30px;height:30px;border-radius:50%;background:var(--ink);color:var(--white);display:flex;align-items:center;justify-content:center}
.sns-ch svg{width:16px;height:16px;display:block}
.card:hover .card__media{filter:brightness(.96)}
.sns-note{font-size:var(--fs-badge);color:var(--soft);margin-top:20px}

/* 공통 Video Card 확장 — 기존 .card--wide 비율/radius 그대로, 재생 아이콘만 추가(LIVE 현장 등 재사용) */
.card__play{position:absolute;inset:0;margin:auto;width:52px;height:52px;border-radius:50%;background:rgba(0,0,0,.55);display:flex;align-items:center;justify-content:center;pointer-events:none}
.card__play svg{width:18px;height:18px;fill:var(--white);margin-left:2px}

/* 공통 랭킹 표시 확장 — 기존 카드에 순위 숫자만 추가(체험하기 인기 콘텐츠 등 재사용) */
.card__rank{position:absolute;left:16px;bottom:14px;font-size:64px;font-weight:800;color:var(--white);text-shadow:0 2px 14px rgba(0,0,0,.45);line-height:1}

/* ---------- 코스 캐러셀(Course Carousel) — HOME "코스로 즐기기" · 공원 탐색 "코스로 즐기기" 공용 ----------
   두 페이지가 원래부터 같은 마크업(.courses)과 같은 데이터(course-data.js), 같은 렌더링 로직
   (course.js)을 공유하고 있어 새 컴포넌트를 만들지 않고 이 블록 하나만 고쳐 두 페이지에 동시
   반영한다(JS는 home.js "코스 캐러셀" 섹션, createLoopCarousel을 align:"center"로 재사용).
   NOL 프로모션 배너 캐러셀처럼 이전·현재·다음 카드가 한 화면에 전부 완전히 보이고 현재 카드가
   정확히 중앙에 오며, 화면을 아무리 넓혀도 잘리거나 4번째 카드가 살짝 보이는 일 없이 정확히
   3장만 깔끔하게 떨어지는 구조(NOL 프로모션 배너 참고 요청 반영).
   ⚠ 260803 두 차례 재수정 — 두 단계 래퍼로 정리했다:
   1) .courses-viewport(바깥, Full-bleed) — .container 밖으로 자체 padding(--pad-page)만큼만
      escape한다(모바일과 동일한 %기반 공식 — 998px 미만에서만 문제되는 100vw 스크롤바 이슈와
      무관). 998~1439px처럼 .container가 아직 max-width(1440px)에 닿지 않은 구간에서 카드 3장이
      들어갈 여유 공간을 벌어주는 역할만 한다.
   2) .courses-viewport__inner(안�, 실제 카드 3장+gap 합과 정확히 같은 max-width로 고정) — 바깥
      래퍼가 벌어준 공간 안에서 margin-inline:auto로 항상 정중앙에 놓인다. 처음엔 카드를 고정
      폭(410px)으로 두고 "3장+gap 합(1278px)이 .container 콘텐츠 폭(1280px)과 거의 같다"는 점만
      믿고 안쪽 래퍼 없이 바깥 래퍼만 썼는데, 1440px 이상에서 바깥 래퍼가 계속 .container 콘텐츠
      폭(최대 1280px)만큼 넓게 남아 있어 카드 3장(1278px) 대비 살짝 넓은 만큼 네 번째 카드가
      미세하게 다시 보이는 문제가 있었다(실사용 화면에서 재확인). max-width를 정확히 3장+gap 합인
      1278px로 고정해 두 번째 카드가 그 이상 넓어지지 않게 못박았다 — 화면을 아무리 키워도 정확히
      3장, 여백까지 깔끔하게 떨어진다.
   카드 폭 자체는 고정 410px 대신 min(410px, calc((100vw - 48px)/3))로 반응형 처리했다 — "카드
   3장 + gap(24px)×2 = 뷰포트 폭"이 되는 지점까지는 화면에 맞춰 줄어들고, 그 지점(약 1278px)을
   넘어서면 410px에서 더 커지지 않는다(nav-hero의 min(60vw,760px)과 같은 패턴). 998~1279px
   구간(예: 1025px)에서 카드가 화면 오른쪽 끝에 잘려 보이던 문제를 이 반응형 폭이 해결한다. 카드
   자체의 색상·라운딩·패딩·타이포는 전혀 건드리지 않았다("카드 디자인 자체 변경 금지" 범위 밖 —
   캐러셀 Slide 사이징만 조정). 이전/다음 버튼은 nav-hero__arrow의 기본 위치(카드 안쪽 8px 겹침)를
   그대로 쓴다(Hub Featured/Rail에서 이미 검증된 허용 패턴). 무한 루프(클론 앞뒤 삽입 후
   transitionend에 조용히 되감기)는 히어로와 동일한 createLoopCarousel을 그대로 재사용하므로
   별도 구현이 없다. */
.courses-viewport{width:calc(100% + var(--pad-page) * 2);margin-inline:calc(var(--pad-page) * -1)}
.courses-viewport__inner{position:relative;max-width:1278px;margin-inline:auto} /* 1278px = 카드(min(410px,…)) 3장 + gap(24px) 2개 */
.courses{position:relative;display:flex;gap:24px;overflow-x:auto;scroll-snap-type:x mandatory;scrollbar-width:none;padding-inline:calc((100% - min(410px, calc((100vw - 48px)/3)))/2)}
.courses::-webkit-scrollbar{display:none}
/* 활성(중앙) 카드는 scale(1)/opacity 1, 좌우 프리뷰 카드는 살짝 축소·페이드 — 과한 확대·블러·Dim 없이
   중앙 카드만 은은하게 강조한다. 전환 시간(.4s)·이징은 courseLoop의 스크롤 애니메이션(400ms,
   ease-out-cubic)과 맞춰 이동과 강조 모션이 하나로 이어져 보이게 했다. */
.course{position:relative;flex:0 0 min(410px, calc((100vw - 48px)/3));width:min(410px, calc((100vw - 48px)/3));scroll-snap-align:center;border-radius:18px;padding:24px 28px;height:150px;text-align:left;color:var(--white);background:linear-gradient(135deg,var(--c1),var(--c2));display:flex;flex-direction:column;justify-content:center;gap:4px;opacity:.86;transform:scale(.97);transition:transform .4s cubic-bezier(.33,1,.68,1),opacity .4s cubic-bezier(.33,1,.68,1)}
.course.is-active{opacity:1;transform:scale(1)}
.course__sub{font-size:var(--fs-body-sm);opacity:.85}
.course__title{font-size:22px;font-weight:700}
.course__meta{font-size:var(--fs-caption);opacity:.7;margin-top:4px}
.courses__ctrl{display:flex;align-items:center;gap:16px;margin-top:20px;justify-content:center}
.courses__pause{position:relative;width:28px;height:28px;border-radius:50%;border:1px solid var(--line);font-size:var(--fs-caption);font-weight:700;display:flex;align-items:center;justify-content:center}
/* 히트 영역 확장(260806) — .gnb__icon과 같은 방식. 원 지름 28px은 그대로 두고 누를 면적만 넓힌다.
   40px: 옆 진행바와의 간격(.courses__ctrl gap 16px)을 넘지 않는 값이라 서로 겹치지 않는다. */
.courses__pause::after{content:"";position:absolute;top:50%;left:50%;transform:translate(-50%,-50%);width:40px;height:40px;border-radius:50%}
.courses__bar{flex:0 1 360px;height:4px;border-radius:var(--r-full);background:var(--line);overflow:hidden}
.courses__bar i{display:block;height:100%;width:50%;background:var(--ink);border-radius:var(--r-full);transition:width .3s}
.courses__count{font-size:var(--fs-caption);color:var(--grey);font-weight:700}
@media (prefers-reduced-motion: reduce){
  .course{transition:none;transform:none}
  .course.is-active{transform:none}
}

/* ---------- 방문 정보 ---------- */
.visit__title{font-size:var(--fs-hero-meta);font-weight:700;line-height:32px;margin-bottom:16px}
.visit__list{list-style:none;display:flex;flex-direction:column;gap:12px}
/* 260813: border가 이미 경계를 만들고 있어 이중으로 얹혀 있던 그림자를 제거(Shadow 최소화) */
.visit__item{display:flex;align-items:center;gap:12px;background:var(--white);border:1px solid var(--line);border-radius:var(--r-lg);padding:16px}
.visit__icon{width:32px;height:32px;border-radius:var(--r-lg);background:var(--icon-bg);display:flex;align-items:center;justify-content:center;flex:none}
.visit__icon svg{width:18px;height:18px;color:var(--ink)}
.visit__label{font-size:var(--fs-caption);font-weight:700;color:var(--grey);line-height:17px;margin-bottom:4px}
.visit__value{font-size:var(--fs-body-sm);font-weight:700;line-height:20px}
/* 260821: "오시는 길" 값만 지도 링크가 된다(네이버 지도 · 경마공원역). 전역 a{color:inherit}라 색은
   본문 그대로 두고 밑줄로만 링크임을 알린다 — 방문정보 카드 안에서 유일한 클릭 요소다.
   ⚠ 무료입장권 값의 링크는 제거했다(260821 클라이언트) — 이 규칙은 링크가 있는 값에만 적용된다. */
.visit__value a{text-decoration:underline;text-underline-offset:3px;text-decoration-thickness:1px;
  text-decoration-color:var(--line)}
.visit__value a:hover{text-decoration-color:currentColor}

/* ---------- Footer (라이트) ---------- */
.footer{margin-top:var(--gap-section);background:var(--bg);color:var(--ink)}
.footer__inner{padding-top:56px;padding-bottom:48px}
.footer__top{display:flex;align-items:flex-start;justify-content:space-between}
.footer__brand{display:flex;flex-direction:column;align-items:flex-start;gap:12px}
.footer__logo{height:35px;width:auto}
.footer__slogan{font-size:var(--fs-caption);color:var(--grey)}
.footer__cols{gap:72px}
.footer__cols h4{font-size:var(--fs-caption);font-weight:700;color:var(--grey);margin-bottom:12px}
.footer__cols a{display:block;font-size:var(--fs-caption);font-weight:400;padding:6px 0;color:var(--ink)}
.footer__cols a:hover{text-decoration:underline}
/* 방문정보 — Footer는 드롭다운을 복제하지 않고 그룹 안에 라벨 + 지역 3개를 그대로 나열한다.
   라벨(.footer__cols__label)은 클릭 요소가 아니라서 h4(그룹 제목)와 구분되도록 살짝 진하게만 준다. */
.footer__cols__label{font-size:var(--fs-caption);font-weight:700;color:var(--ink);padding:6px 0 2px}
.footer__cols a.footer__cols__region{padding-left:8px}
.footer__links{gap:16px;flex-wrap:wrap}
.footer__links a{font-size:var(--fs-caption);color:var(--ink)}
.footer__line{border:0;height:1px;background:var(--line);margin-block:36px}
/* 법인·사업장 정보 그리드 — park.kra.co.kr 하단 표기 구조(서울/부경/제주 + 고객센터) 그대로 */
.footer__legal-grid{display:grid;grid-template-columns:repeat(4,1fr);gap:24px;margin-bottom:28px}
.footer__legal-col p{font-size:var(--fs-caption);color:var(--grey);line-height:1.6}
.footer__legal-title{font-weight:700;color:var(--ink)!important}
.footer__phone{font-size:var(--fs-body)!important;font-weight:700;color:var(--ink)!important}
.footer__bottom{display:flex;align-items:flex-start;justify-content:space-between;gap:16px;flex-wrap:wrap}
.footer__policy{display:flex;gap:16px;flex-wrap:wrap}
.footer__policy a{font-size:var(--fs-caption);color:var(--grey)}
.footer__policy--strong{font-weight:700;color:var(--ink)!important}
.footer__legal{display:flex;flex-direction:column;gap:6px}
.footer__legal p{font-size:var(--fs-caption);color:var(--grey)}
.footer__copy{font-size:var(--fs-caption);color:var(--grey)}

/* ---------- 좋아요 하트 — 퍼블리싱 Hook (260819) ----------
   ⚠ 좋아요는 **콘텐츠 상세 전용**이다(260819 확정). 카드·목록·일정 행에는 두지 않는다 —
   탐색 단계에서 바로 누르는 기능이 아니라, 상세에서 내용을 확인한 뒤 저장하는 기능이기 때문이다.
   (카드용으로 잠시 있던 .card-slot / .wson-slot 오버레이 규칙은 같은 날 제거했다.)

   ⚠ 이 프로젝트는 마크업·상태 CSS까지만 갖는다. 로그인 판정·좋아요 저장/조회·마이페이지는
   전부 서버 개발 영역이며, 여기에 그 동작을 흉내 내는 JS를 두지 않는다(localStorage 금지).

   서버가 붙이는 지점은 두 곳뿐이다:
     1) <body data-auth="guest|member"> — 이 한 곳만 출력하면 상세의 하트가 켜지고 꺼진다.
        정적 납품본의 기본값은 guest라서 화면에 하트가 보이지 않는 것이 정상이다.
     2) 각 버튼의 aria-pressed="true|false" — 사용자별 좋아요 여부. class 추가가 필요 없도록
        상태를 이 속성 하나로만 표현한다(서버·JSP에서 속성 값만 바꾸면 시각 상태가 따라온다).

   콘텐츠 식별은 [data-content-id] — 값은 common/content-data.js의 contentId와 동일하다.
   아이콘은 취향 칩 "데이트"(home.js PICK_ICONS.date)와 같은 하트 path를 그대로 재사용한다
   (신규 SVG 제작 없음 — §2). */
body[data-auth="guest"] [data-like]{display:none}

.btn-like{display:inline-flex;align-items:center;justify-content:center;gap:6px;background:none;border:0;padding:0;cursor:pointer;font-family:inherit;color:var(--ink)}
.btn-like svg{width:22px;height:22px;fill:none;stroke:currentColor;flex:none}
.btn-like[aria-pressed="true"] svg{fill:var(--coral-500);stroke:var(--coral-500)}

/* 상세 상단 — 기존 공유 버튼과 같은 .btn .btn--pill .btn--outline .btn--lg 규격을 그대로 쓴다.
   면·테두리·padding은 .btn/.btn--outline이 그대로 결정하고(둘 다 이 블록보다 뒤에 오거나
   detail.css라 우선한다), 여기서는 아이콘 크기와 눌림 상태 색만 얹는다.
   svg 18px = 옆 공유 버튼의 .ico-svg와 같은 크기(한 줄에서 두 아이콘이 어긋나지 않게). */
.btn-like--detail svg{width:18px;height:18px}
.btn-like--detail[aria-pressed="true"]{border-color:var(--coral-500);color:var(--coral-500)}

/* ---------- 플로팅 (CFB Brand) ---------- */
/* 260813 2차 Visual Pass: FAB도 상시 노출 CTA라 pill→rounded rectangle */
/* 260819: 화면 고정 위치는 .fab-stack이 갖고, .fab은 스택 안에서 흐름 배치만 한다.
   .fab 자체의 시각 규격(높이·radius·컬러·그림자)은 260813 값 그대로 — 디자인 변경 없음.
   기존처럼 .fab 하나만 있는 페이지도 스택으로 감싸므로 우하단 좌표는 이전과 동일하다. */
.fab-stack{position:fixed;right:40px;bottom:40px;z-index:60;display:flex;flex-direction:column;align-items:flex-end;gap:12px}
.fab{height:48px;display:inline-flex;align-items:center;gap:6px;padding-inline:16px;border-radius:var(--r-md);background:var(--yellow-500);color:var(--ink);font-size:var(--fs-body-sm);font-weight:600;box-shadow:var(--shadow-fab)}
.fab svg{width:20px;height:20px;fill:none;stroke:currentColor;stroke-width:1.8;stroke-linecap:round}
/* 무료티켓 FAB — 데스크톱은 아이콘+"무료티켓" 한 줄 필. 모바일에서는 아래 ≤997 블록이
   원형 2줄("무료 / 티켓")로 바꾼다. .fab__label-br이 모바일에서만 줄바꿈 역할을 한다. */
.fab--ticket .fab__label-br{display:inline}
/* 260828 클라이언트: FAB 문구 "무료티켓" → "무료입장권(원데이패스)". 데스크톱 필은 전체 문구,
   모바일 64px 원형은 "무료/입장권" 2줄만(괄호 보조어는 공간상 숨김 — aria-label에는 전체 유지). */
.fab--ticket .fab__label-sub{display:inline}
/* 미니게임 — 260830 전면 교체(고객 제공 완성 아이콘 + 총괄: "모바일·데스크톱 동일 원형").
   ⭐ 원(다크)·"미니게임" 글자·말마가 **한 장의 이미지에 이미 다 들어 있다**
   (assets/img/malma/malma-game.png — 고객 전달 malma_game.svg를 표시 3배로 렌더한 것.
   원본 SVG는 제작자산/말마캐릭터_원본/에 보관). 그래서 버튼 자체는 배경·문구·padding이 없는
   투명한 히트 영역이고, 보이는 것은 전부 이 이미지다 — 버튼에 배경색이나 텍스트를 다시 넣지 말 것.
   · 버튼 = 원의 크기(--fab-game-d) 그대로. 이미지는 원보다 1.5배 높아 그만큼 위로 넘치고
     (말마 머리), 아래끝이 원 아래끝 = 버튼 아래끝에 정확히 맞는다(자산 실측 비율 288/193).
   · 그림자는 box-shadow(사각형)가 아니라 drop-shadow로 — 원+말마 실루엣을 따라간다.
   · 데스크톱·모바일 동일 규격(총괄 확정) — 폭만 --fab-game-d로 조절한다. */
.fab--game{--fab-game-d:64px;
  width:var(--fab-game-d);height:var(--fab-game-d);padding:0;background:none;border:0;
  border-radius:var(--r-full);box-shadow:none;cursor:pointer;position:relative;font-size:0}
.fab__game-img{position:absolute;left:0;bottom:0;width:100%;height:auto;pointer-events:none;
  filter:drop-shadow(0 4px 12px rgba(0,0,0,.14))}

/* 260819 겹침 수정 — 데스크톱 짧은 뷰포트(높이 ≤950px)에서만 가로 배치.
   문제: HOME 우측 열은 위로 "처음 방문한다면?" 배너, 아래로 "공간 더 보기" 링크가 있고,
   home.js의 충돌 회피가 링크를 피해 스택을 밀어 올리면 세로 스택(48+12+48=108px)이
   배너 하단을 약 56px 덮는다. 두 요소 사이에 실제로 남는 세로 공간은 약 52px뿐이라
   버튼 높이·gap을 줄이는 정도로는 해결되지 않는다(40+8+40=88px도 부족).
   해결: 이 구간에서만 스택을 가로로 눕힌다 — 높이가 48px가 되어 배너와 링크 사이에 정확히 들어간다.
   위로 밀어 PLAY NOW 목록을 가리는 방식은 쓰지 않는다(더 나쁜 가림이 생긴다).
   ⚠ 세로 스택("게임하기"가 위) 자체는 기본값이며, 높이가 넉넉한 화면과 모바일에서는 그대로다. */
/* ⚠ 260830 총괄 지시로 **가로 눕히기는 폐지**(미니게임은 항상 무료입장권 위). 대신 이 구간에서는
   스택 자체를 압축해 겹침을 줄인다 — 아래 ≤860px 블록의 축소(원 52px·티켓 40px)와 이어진다. */
@media (min-width:998px) and (max-height:950px){
  .fab-stack{gap:8px}
}

/* 260819 2차 보정 — 높이 ≤860px에서 스택 자체를 한 단계 줄인다.
   1440×800 실측: "처음 방문한다면?" 배너가 683~770에 있고 그 아래로 남는 세로 여백은 30px,
   오른쪽으로 남는 가로 여백은 94px뿐이다. 스택은 가로 배치로도 236×48이라
   ① 아래로 완전히 내려가기엔 30px가 모자라고 ② 오른쪽으로 비켜서기엔 94px가 모자라며
   ③ 위로 올리면 PLAY NOW 목록(~659까지)을 덮는다 — 세 방향 모두 막혀 있다.
   따라서 "완전 회피"는 CSS로 불가능하고, 여기서는 겹치는 면적을 최소화한다:
   높이 48 → 40(§31 버튼 M 규격 — 새 수치를 만들지 않는다), bottom 40 → 12, gap 10 → 8,
   right 40 → 20, padding 16 → 14. 배너를 덮는 세로 폭이 58px → 22px로 줄어든다.
   ⚠ 이 구간에서도 배너 우측 하단 일부는 계속 가려진다 — 완전 해결은 배너 위치나 FAB 문구를
   바꿔야 가능하며 그건 HOME/배너 구조 변경이라 이번 범위 밖이다(보고서에 기록). */
@media (min-width:998px) and (max-height:860px){
  .fab-stack{right:20px;bottom:12px;gap:8px}
  /* ⚠ :not(.fab--game) — 미니게임은 원형 이미지 버튼이라 높이를 눌러 찌그러뜨리면 안 된다
     (이 블록이 .fab--game 정의보다 뒤라 제외하지 않으면 40px로 덮인다, 260830). 대신 원 지름만 줄인다. */
  .fab:not(.fab--game){height:40px;padding-inline:14px}
  /* ⚠ 미니게임 원은 여기서도 줄이지 않는다 — "데스크톱·모바일 동일 규격"이 총괄 확정 사항(260830).
     :not()으로 위 높이 축소에서 제외하는 것까지만 하고 지름(--fab-game-d:64px)은 그대로 둔다. */
}
/* 충돌 회피(260811) — .fab은 우하단 고정이고 "더 보기" 링크(.section__more/.playnow__more)도 우측
   정렬이라 x범위가 항상 100% 겹친다(1440·1024·768·375 실측). 스크롤 위치에 따라 FAB이 링크를 덮어
   클릭이 차단되던 문제를 막기 위해, 겹치는 구간에서만 home.js가 bottom 값을 키워 위로 비켜 세운다.
   숨기지 않는 이유: FAB이 사라지면 주 CTA가 순간적으로 없어져(1440×900 HOME은 로드 직후가 그 구간)
   오히려 기능이 약해진다. 위치만 잠깐 올리므로 FAB은 항상 보이고 항상 눌린다.
   transform이 아니라 bottom을 쓰는 이유: 아래 모바일 미디어쿼리(bottom:16px)를 그대로 이어받아
   기준 위치가 화면 폭에 따라 자동으로 맞고, 되돌릴 때 인라인 값만 지우면 되기 때문이다.
   transition을 걸지 않는 이유: 이 위치 변화는 스크롤을 따라가는 값이라 전환을 걸면 스크롤보다
   늦게 따라와 오히려 겹치는 순간이 생긴다. 즉시 반영이 맞다. */

/* ---------- 모달 (코스 · 종결형) ---------- */
/* ---------- Toast (260821 신설) ----------
   액션 결과를 짧게 알리는 검정 알약 — 좋아요 누름/취소, 링크 복사 등. 일반적인 모바일 UX 관례:
   화면 하단 중앙, 2.2초 뒤 스스로 사라짐, 누를 수 없음(pointer-events:none), 한 번에 1개만
   (새 메시지가 오면 문구만 교체). 마크업은 home.js의 window.showToast()가 최초 호출 때 1개 만든다.
   role="status"+aria-live="polite"라 스크린리더에도 같은 문구가 읽힌다. */
.toast{position:fixed;left:50%;bottom:calc(28px + env(safe-area-inset-bottom));z-index:120;
  transform:translate(-50%, 12px);opacity:0;pointer-events:none;
  max-width:min(92vw, 420px);padding:12px 18px;border-radius:var(--r-full);
  background:rgba(29,29,31,.92);color:var(--white);font-size:var(--fs-body-sm);font-weight:600;
  line-height:1.4;text-align:center;white-space:nowrap;overflow:hidden;text-overflow:ellipsis;
  box-shadow:0 6px 20px rgba(0,0,0,.18);
  transition:opacity .2s ease,transform .2s ease}
.toast.is-on{opacity:1;transform:translate(-50%, 0)}
/* 모바일 상세: 하단 고정 CTA 바(72px)에 가리지 않게 바 위로 */
@media (max-width:997px){
  .detail-page:has(.detail-hero__cta) .toast{bottom:calc(88px + env(safe-area-inset-bottom))}
}
@media (prefers-reduced-motion:reduce){ .toast{transition:none;transform:translate(-50%, 0)} }

.modal{position:fixed;inset:0;z-index:100;display:flex;align-items:center;justify-content:center}
.modal[hidden]{display:none}
.modal__dim{position:absolute;inset:0;background:rgba(0,0,0,.55)}
/* 260827: max-height에 svh 2차 선언 — iOS 사파리에서 vh는 툴바가 접힌 "큰 뷰포트" 기준이라
   툴바가 보이는 동안 모달 아래가 잘렸다(실기기 리포트). svh(작은 뷰포트 단위)는 툴바가 있어도
   항상 보이는 높이 기준. 미지원 브라우저는 앞 선언(86vh)으로 폴백된다 — min()으로 합치면
   미지원 시 선언 전체가 무효가 되므로 반드시 두 줄로 쓴다. */
.modal__box{position:relative;width:min(560px,calc(100vw - 40px));background:var(--white);border-radius:var(--r-media);overflow:hidden;max-height:86vh;max-height:86svh;display:flex;flex-direction:column}
/* 260813: 기본 모달 헤더를 노란 그라디언트 → 깨끗한 흰 면 + 얇은 구분선으로.
   실사용 모달은 전부 .sheet-modal(캘린더·검색·필터시트·코스) 또는 .share-modal이고 둘 다 이미
   흰 헤더를 자체 지정하고 있어 화면상 변화는 없다 — 기본값만 현재 시각 언어에 맞춘 정리다.
   (코스 미리보기 모달의 코스 그라디언트 헤더는 course.js가 인라인으로 주입하므로 영향 없음) */
.modal__head{background:var(--white);border-bottom:1px solid var(--line);padding:28px 28px 22px}
/* 모달 제목 기본값 = Utility Modal Title(검색·캘린더·공유). 공용 셸(.modal)을 소유한 이 파일이
   기본 타이포를 갖는다(260811 정리 — 이전에는 여기 22px/800이 있었으나 실제 모달 4종 전부가
   각자 파일에서 덮어써 어디에도 적용되지 않는 死규칙이었고, 그 결과 같은 역할의 제목이
   16/18/18/26px 네 값으로 갈라져 있었다).
   콘텐츠 강조형(코스 미리보기)만 .course-modal__title로 Large를 명시한다 — course.css 참고. */
.modal__head h3{font-size:18px;font-weight:700;color:var(--ink)}
.modal__head p{font-size:var(--fs-caption);color:rgba(0,0,0,.55);margin-top:4px}
/* 260813: 닫기 버튼을 반투명 흰 원 → 중립 회색 면으로 통일(흰 헤더 위에서 반투명은 형태가 흐려진다).
   .sheet-modal이 이미 같은 값(--bg/--ink)을 쓰고 있어, 기본값을 거기에 맞춰 모달 종류가 달라도
   닫기 버튼 생김새가 같아진다. 크기·위치·터치 영역(::after 44px, 260806)은 그대로. */
.modal__close{position:absolute;top:16px;right:16px;width:34px;height:34px;border-radius:50%;background:var(--bg);color:var(--ink);font-size:var(--fs-label)}
.modal__body{padding:24px 28px;overflow-y:auto}
.modal__intro{font-size:var(--fs-label);color:var(--grey);margin-bottom:16px}
.modal__spots{list-style:none;display:flex;flex-direction:column;gap:10px}
.modal__spots li{display:flex;align-items:center;gap:14px;background:var(--bg);border-radius:var(--r-card);padding:14px 16px}
.modal__spots em{font-style:normal;font-size:var(--fs-label);font-weight:800;color:var(--yellow-700)}
.modal__spots strong{font-size:var(--fs-body-lg);display:block}
.modal__spots span:not(.tag){font-size:var(--fs-caption);color:var(--grey)}
.modal__spots .tag{margin:0 0 0 auto}
.modal__foot{padding:4px 24px 24px}
/* 기본 크기 = 브랜드 문서 버튼 M(40 · fs14). 크기 변형(--lg 52 · --full 48)은 height만 덮어쓴다.
   기존엔 기본 .btn에 크기가 없어서 --lg/--full 없이 쓰면(예약 안내 등) 텍스트에 딱 붙은 맨몸 버튼이 됐다. */
.btn{display:inline-flex;align-items:center;justify-content:center;gap:6px;font-weight:700;border-radius:var(--r-md);height:40px;padding-inline:20px;font-size:var(--fs-body-sm)}
.btn--dark{background:var(--ink);color:var(--white)}
.btn--full{width:100%;height:48px;font-size:var(--fs-body-lg)}
.btn[disabled]{opacity:.4;cursor:not-allowed}

/* =========================================================
   998px 이상 공통
   ========================================================= */
@media (min-width:998px){
  /* #pickRail gap 20px 축소 오버라이드는 260828 제거 — 같은 .card--pick 레일인 체험
     둘러보기(32px)와 간격이 달라 보인다는 클라이언트 지적. 레일 간격은 공용 --gap-card 하나만 쓴다. */

  /* 데스크톱 히어로는 '비율'을 고정한다(높이 고정 ✗).
     높이를 고정하면 폭이 변할 때 프레임 비율이 1.60(1440) ~ 0.90(998)으로 널뛰어
     배너 모양 자체가 달라지고, 넓은 화면에서 사진이 50% 넘게 잘린다.
     비율을 고정하면 어느 폭에서도 모양·라운딩이 동일하게 유지된다(Figma 876:680 정본). */
  /* 데스크톱 메인 히어로는 좌우 프리뷰 없이 슬라이드 1장 전체가 꽉 차게 유지한다(예전 방식으로 복귀).
     좌우 미리보기는 우측 PLAY NOW 미니 리스트가 이미 담당하므로, 메인 배너에서 이전/다음 조각이
     함께 보이지 않게 한다 — 미니 리스트만 활성 index가 바뀔 때 한 장씩 전환되면 된다. */
  .hero__slide{aspect-ratio:var(--hero-ratio-desk)}

  /* PLAY NOW 사이드바 — 히어로가 좁아지는 만큼 카드도 같이 비율적으로 줄어들게(clamp).
     998px(카드 5장 최소 높이)~1440px(카드 5장 여유 높이) 사이에서 리스트 전체 높이가
     항상 히어로 이미지 높이 근처에 맞춰지도록 폭에 비례해 축소한다. (260802: 사이드바 컬럼 폭
     자체는 위 .hero의 minmax(360px,30%)로 넓혔지만, 이 clamp() 수치들은 최초 설계값 그대로다 —
     컬럼이 넓어져도 항목 1개의 세로 높이·폰트 크기까지 커질 필요는 없어서 손대지 않았다.) */
  /* 260803: 헤드↔리스트↔CTA 사이 간격을 좁혀(30→24) 리스트에 줄 세로 공간을 확보한다 —
     "6개가 스크롤 없이 다 보이게" 목표에서 상단 여백보다 항목 노출이 우선. */
  /* 260820: 데스크톱은 헤드(타이틀 "PLAY NOW!" + 상단 더 보기)를 노출하지 않는다 —
     GNB 최상단의 PLAY NOW와 겹쳐 보이고, 걷어낸 만큼 목록이 세로로 넉넉해진다.
     타이틀은 마크업에 그대로 남아 스크린리더용 섹션 제목 역할을 계속한다. */
  .playnow__head{display:none}
  .playnow{gap:clamp(14px, 1.7vw, 20px)}
  .playnow__title{font-size:clamp(18px, 2vw, 22px)}
  /* 260802: home.js의 syncPlaynowHeight()가 .playnow 높이를 히어로 배너 실측 높이로 고정한다.
     리스트는 flex:1;min-height:0으로 그 안에서 남는 공간만 차지하고, 항목이 다 안 들어가면
     overflow-y:auto로 세로 스크롤(Netflix 리스트 방식) — 잘리거나 아래로 넘치지 않는다.
     스크롤바는 이 프로젝트의 다른 스크롤 영역(GNB 메뉴·히어로 트랙·카드 레일·코스·모바일 미니 리스트)과
     동일하게 숨긴다 — 데스크톱 리스트만 네이티브 스크롤바가 보이던 일관성 오류를 맞춘 것. */
  .playnow__list{gap:clamp(8px, 1.1vw, 12px);flex:1;min-height:0;overflow-y:auto;overscroll-behavior:contain;scrollbar-width:none}
  .playnow__list::-webkit-scrollbar{display:none}
  /* 스크롤바를 숨긴 대신 "아래에 더 있다"는 신호를 하단 페이드로 준다(모바일 히어로 블러 배경과 동일 기법).
     .has-more는 home.js의 syncPlaynowFade()가 "스크롤 가능 + 아직 끝이 아님"일 때만 붙이므로,
     맨 아래까지 내리면 페이드가 사라져 마지막 항목이 영구적으로 흐려 보이지 않는다. */
  .playnow__list.has-more{
    -webkit-mask-image:linear-gradient(180deg,#000 calc(100% - 28px),transparent);
    mask-image:linear-gradient(180deg,#000 calc(100% - 28px),transparent)}
  /* 260803: 고정 높이(clamp) → 남는 공간을 6개가 균등하게 나눠 채우는 방식으로 변경.
     고정 높이일 때는 넓은 화면에서 6×79+간격 = 519px가 필요한데 실제 가용 높이는 약 476px라
     항상 스크롤이 생겼다(사용자 피드백: 스크롤인지 인지도 안 됨). flex로 채우면 화면 폭에 따라
     항목 높이가 자동으로 맞춰져 스크롤 없이 6개가 모두 보인다.
     · min-height 60px = 썸네일(84:47)+2줄 텍스트가 읽히는 하한선 — 이보다 좁히지 않는다.
     · max-height 79px = 기존 디자인 상한 그대로(공간이 남아도 과도하게 커지지 않게).
     · 998~1200px대는 히어로 자체가 낮아(예: 998px에서 359px) 6개×60px가 물리적으로 안 들어간다 —
       이 구간에서만 위 overflow-y:auto가 실제로 동작하고(스크롤바는 숨김+하단 페이드), 그 위 폭에서는
       스크롤이 발생하지 않는다. */
  /* 260820: 헤드를 걷어내 생긴 여유를 항목에 돌린다(상한 79 → 96, 하한 60 → 68). */
  /* min-height는 폭에 따라 60~68 — 998~1200대는 히어로 자체가 낮아 하한을 68로 고정하면
     3~4개만 보이고 나머지가 스크롤로 숨는다(1024 실측). 넓은 화면에서만 항목을 키운다. */
  .playnow__item{flex:1 1 auto;min-height:clamp(60px, 5vw, 68px);max-height:96px;padding:clamp(12px, 1.5vw, 16px);gap:clamp(10px, 1.2vw, 16px)}
  /* 데스크톱 리스트 썸네일 — 정방형(260821). 항목 안쪽 높이(min-height − 패딩)에 맞춰
     40~52px: 1024에서 40, 1440에서 52. 원본은 cover로 중앙 크롭된다(자르지 않는 옵션은 없음). */
  .playnow__thumb{width:clamp(44px, 3.9vw, 56px)} /* 260821 한 단계 확대: 1024→44 · 1440→56 */
  .playnow__name{font-size:clamp(14px, 1.15vw, 15px)}
  .playnow__meta{font-size:clamp(12px, 1vw, 13px)}
}

/* =========================================================
   태블릿 998~1199 (취향 카드 약 3장 노출)
   ========================================================= */
@media (min-width:998px) and (max-width:1199px){
  .card--pick{width:calc((100vw - var(--pad-page)*2 - var(--gap-card)*2)/3)}
  /* #pickRail --media-h 오버라이드는 제거(260828) — HTML 인라인 스타일에 항상 져서 적용된 적이
     없던 죽은 규칙. 화살표 기준은 home.js updateArrows()가 카드 이미지 높이를 실측해 넣는다. */
}

/* =========================================================
   반응형 ≤997 (마진 20 · 스와이프+피크 · 화살표 숨김)
   ========================================================= */
@media (max-width:997px){
  .only-mob{display:inline}
  .only-mob-block{display:block}
  .only-mob-flex{display:flex}
  .only-desk,.only-desk-block,.only-desk-flex{display:none}

  .container{padding-inline:var(--pad-page)}
  /* 260819 · 1단 GNB: 메뉴가 PLAY NOW·방문정보 2개로 줄어 전체 폭 2행 구조가 필요 없어졌다.
     로고 · 메뉴 · 유틸(로그인+검색)을 한 줄에 둔다 — 햄버거·새 모바일 메뉴 시스템은 만들지 않고
     기존 요소·클래스를 순서만 바꿔 재사용한다. breakpoint(997px)는 그대로. */
  .gnb__inner{height:56px;min-height:0;flex-wrap:nowrap;align-items:center;row-gap:0;padding-inline:clamp(6px, calc((100vw - 363px) / 2), var(--pad-page));padding-block:0;gap:6px}
  /* 바 좌우 패딩 — 6px은 375px에서 메뉴가 안 잘리는 최솟값일 뿐이다(260821 실측: 가로 여유 0).
     내용 폭(≈363px)을 뺀 나머지를 양쪽에 나눠 준다: 375→6 · 390→13.5 · 395+→16(--pad-page).
     "모바일 네비 양옆 여유를 더 달라"(태블릿 폭 캡처) 요청 반영 — 375px 무잘림은 그대로 유지. */
  .gnb__logo,.gnb__right{padding-inline:0}
  .gnb__logo{order:1;flex:none}
  /* 260820: 데스크톱(≥998)과 같은 광학 정렬을 모바일에도 적용 — 로고는 위쪽에 LETSRUN 워드마크가
     얹혀 있어 그래픽 무게중심(PLAY 블록 행)이 박스 중심보다 아래다. 메뉴·유틸을 바 중심에 그대로
     두면 로고보다 위로 떠 보인다(클라이언트 리포트). 데스크톱 38px→6px과 같은 비율로 32px→5px.
     transform이라 레이아웃·히트영역에는 영향이 없다. */
  /* 260821: 로그인 텍스트와 검색 아이콘이 붙어 보인다는 피드백 — 6→12px.
     늘린 6px은 아래 메뉴 gap(20px)이 아니라 바 좌우 패딩에서 회수한다(문구 잘림 방지). */
  .gnb__right{order:3;margin-left:0;gap:12px;flex:none;transform:translateY(5px)}
  /* 260820: 28→32(클라이언트 "모바일 로고를 좀 더 크게"). 로고 폭이 77→88px로 11px 늘어나는데
     375px 1행에는 여유가 0이었다(실측) — 바 패딩 12→10(4) · inner gap 8→6(2) · 유틸 gap 8→6(2) ·
     메뉴 내부 여유(3)에서 정확히 11px를 회수했다. 로고↔메뉴 20px는 menu margin-left 12→14로 보전.
     ⚠ 여기서 더 키우려면 메뉴 폰트나 항목 간격(터치 구분 20px)을 건드려야 한다 — 그건 별도 승인. */
  .gnb__logo img{height:32px}
  .logo-anim{--logo-anim-scale:calc(32 / 125)} /* 위 img height:32px와 같은 크기 */
  .gnb__icon svg{height:22px;width:auto}

  .gnb{border-bottom:0} /* 2단 메뉴 아래 흰 구분선 제거(다크 테마와 겹쳐 지저분해 보임) */
  .gnb__menu{order:2;position:static;left:auto;transform:translateY(5px);display:flex;flex:1 1 auto;min-width:0;justify-content:flex-start;align-items:center;gap:20px;overflow-x:auto;scrollbar-width:none;padding:0;margin-left:14px} /* 260819: 항목 간 터치 구분 여백 확보(10→20) — 인접 터치 타깃을 손가락으로 구분해 누를 수 있는 간격. 375px 무잘림은 .gnb__inner gap을 8로 줄여 확보(실측) */
  .gnb__menu::-webkit-scrollbar{display:none}
  /* 260819: 모바일 메뉴 타이포 — A2Z 600은 유지하되 크기는 14px(--fs-body-sm)로 되돌린다.
     A2Z(라틴 베이스 Outfit)가 기존 시스템 폰트보다 폭이 넓어 15px 이상이면 375px 1행에서
     "방문정보"가 첫 화면에 잘린다(실측 부족분 42px). 트리거(button)는 a 선택자에 안 걸려
     데스크톱 18px이 새던 것도 함께 수정. 로그인도 모바일에선 메뉴와 같은 14px.
     간격 배분(260819 재조정, 클라이언트 before/after 이미지 기준): 로고↔메뉴 20px(inner gap 8
     + menu margin-left 12) · 메뉴 항목 사이 20px(터치 구분) · 메뉴↔로그인 8px. 늘어난 폭은
     바 패딩 16→12, 방문정보 캐럿 gap 4→2, 로그인 좌우 패딩 2→0에서 회수해 375px 1행
     무잘림(deficit 0 실측)을 유지한다 — 메뉴 항목·간격을 더할 때는 375px 실측 필수. */
  .gnb__menu a,.gnb-dd__trigger,.gnb__login{font-size:var(--fs-body-sm)}
  /* 260830 재정정(총괄: "모바일 GNB에도 한국마사회 보여야") — 유틸 슬롯은 하나뿐이다:
     이 바는 375px에서 가로 여유 0이라 로그인+한국마사회를 병기하면 방문정보가 94px 가려진다(실측).
     → 모바일에서는 **로그인을 내리고 한국마사회를 올린다** — 고객 배포본(kra.co.kr/letsrunPlay)이
     이미 로그인 자리를 기업홈 링크로 바꿔 운영 중인 것과 같은 우선순위이며, 로그인·좋아요는
     jsp 전환 시 서버 GNB에서 복귀한다(handoff §12-1-1). 데스크톱(≥998)은 둘 다 노출(변경 없음).
     ⚠ 418px 미만(SE급)에서는 "한국마사회" 5자도 방문정보를 33px 가린다(실측) — 그 구간만
     라벨을 숨기고 외부링크 아이콘만 남긴다(아래 424px 분기, 접근성 이름은 aria-label). */
  /* 로그인 앵커 자체가 260830부터 HTML 주석 상태(고객 배포본과 동일) — 아래 규칙은 jsp 전환으로
     로그인이 복귀했을 때를 위한 안전망이다(모바일에선 여전히 자리가 없어 숨겨야 한다). */
  .gnb__login{display:none}
  .gnb__corp{display:inline-flex;color:var(--gnb-fg,var(--ink));opacity:1;gap:4px;padding-inline:0}
  .gnb__corp__label{font-size:var(--fs-body-sm)}
  /* 바로가기(외부링크) 아이콘은 모바일에서도 유지(260830 총괄 — "바로가기 아이콘은 있어야").
     14px로 한 단계 줄이고 corp 좌우 패딩·유틸 gap을 회수해 430px에서 가려짐 3px 이내(실측). */
  .gnb__corp .ico-svg{width:14px;height:14px}
  .gnb__right{gap:8px}
  .gnb__menu a{flex:none;white-space:nowrap;padding:16px 0 14px}
  .gnb__menu a.is-active::after{bottom:10px}
  .gnb-dd{align-items:center}
  .gnb-dd__trigger{gap:2px} /* 260819: 375px 무잘림용 2px 회수(기본 4) */
  .gnb__login{padding-inline:0} /* 260819: 375px 무잘림용 4px 회수(기본 2+2) */
  .gnb-dd__trigger{padding:16px 0 14px;min-height:44px}
  .gnb-dd__panel li a{min-height:44px}

  .notice{padding:12px var(--pad-page);min-height:0} /* 높이는 내용에 맞게(1줄=낮게, 2줄=자연 확장 — 260828: 고정 64px 제거). 정렬은 기본 center 상속 — 1줄에서 배지·닫기가 위로 붙어 보이던 flex-start 폐기 */
  .notice__text{white-space:normal;overflow:visible;line-height:20px;display:-webkit-box;-webkit-line-clamp:2;-webkit-box-orient:vertical;overflow:hidden}

  /* 히어로: Play Now(가로 스크롤) → 배너 · 상단 배경은 단색이 아니라 '활성 배너 이미지의 블러 복제본' */
  /* align-items:stretch 필수 — 데스크톱 grid용 align-items:start가 그대로 상속되면
     flex column에서 자식(배너·Play Now)이 콘텐츠 폭으로 부풀어 트랙 overflow가 사라지고
     배너 스와이프·자동재생·카운터 위치가 전부 깨진다 */
  .hero{display:flex;flex-direction:column;align-items:stretch;gap:0;padding-top:0;padding-inline:0;
        position:relative;isolation:isolate}

  /* ---------- 이미지 기반 블러 배경 ----------
     활성 슬라이드 이미지(--hero-bg-img, home.js 주입)를 GNB 뒤(-200px)부터 카드 중간(--hero-tint-end)까지 깔고
     하단 90px은 마스크로 흰 배경에 자연스럽게 페이드아웃. 카드가 그 위에 떠 있는 구조.
     이미지 레이어는 넉넉히 키워(inset -12% + scale 1.25) 블러 가장자리가 절대 보이지 않게 하고,
     흰색 GNB 텍스트 대비를 위해 brightness로 어둡게 보정한다. */
  .hero__bg{display:block;position:absolute;z-index:-1;left:0;right:0;
    top:calc(-1 * var(--hero-bg-extend));
    height:calc(var(--hero-bg-extend) + var(--hero-tint-end));
    overflow:hidden;background:#221b10; /* 이미지 로드 전/미지정 폴백 */
    -webkit-mask-image:linear-gradient(180deg,#000 calc(100% - 90px),transparent);
    mask-image:linear-gradient(180deg,#000 calc(100% - 90px),transparent)}
  .hero__bg-img{position:absolute;inset:-12%;
    background:var(--hero-bg-img) center/cover no-repeat;
    filter:blur(28px) brightness(.5) saturate(1.15);
    transform:scale(1.25);
    transition:background .45s ease}
  .playnow{order:1;gap:6px;padding:12px var(--pad-page) 14px}
  .playnow__head{padding-bottom:0;justify-content:flex-end} /* 타이틀이 숨어 more만 남으므로 우측 정렬 유지 */
  /* 260819: 모바일에서는 "PLAY NOW!" 타이틀을 시각적으로만 숨긴다(클라이언트 요청 — 다크 헤더
     위 레일만으로 충분). display:none 대신 sr-only 패턴을 써서 스크린리더 섹션 제목은 유지. */
  .playnow__title{position:absolute;width:1px;height:1px;padding:0;margin:-1px;overflow:hidden;clip:rect(0 0 0 0);white-space:nowrap;border:0}
  .playnow__more{color:var(--white)}
  .playnow__list{flex-direction:row;gap:10px;overflow-x:auto;scrollbar-width:none;margin-inline:calc(var(--pad-page) * -1);padding-inline:var(--pad-page)}
  .playnow__list::-webkit-scrollbar{display:none}
  .playnow__item{flex:none;height:58px;padding:8px 12px 8px 8px;border-radius:var(--r-card);border:1px solid var(--line);background:var(--white);gap:8px}
  /* 선택 상태(옐로우 500)는 260821부터 기본 규칙이 담당 — 모바일 전용 재정의 없음. */
  .playnow__thumb{width:42px;border-radius:var(--r-sm)} /* 항목 58 − 패딩 16 = 42 정방형 */
  .playnow__item .badge{display:none}
  .playnow .firstvisit{display:none}

  /* 히어로 피크 캐러셀: 활성 카드 중앙 + 양옆 카드 일부 노출(--hero-peek) · 스와이프+스냅(기본 트랙 동작은 상단 base 규칙 공용) */
  /* 피크는 화면폭에 비례(7vw)해 넓어지고, 카드폭은 560px에서 멈춘다 —
     폰(≤430)에서는 지금까지처럼 거의 꽉 찬 카드, 태블릿(~997)에서는 양옆 카드가 확실히 보이는 캐러셀. */
  :root{
    /* 모바일 첫 화면 세로 점유율을 소폭 줄이기 위해 카드 폭(→7:8 비율로 높이도 비례 축소)만 살짝 줄임 —
       피크(좌우 미리보기)·중앙 정렬 구조는 그대로, peek을 약간 늘리고 최대폭 상한만 낮췄다. */
    --hero-peek:clamp(28px, 8vw, 84px);
    --hero-card:min(calc(100vw - var(--hero-peek) * 2), 520px);
    /* 블러 배경이 끝나는 지점 = Play Now 블록 높이(142px) + 카드 높이(카드폭*8/7)의 절반 */
    --hero-tint-end:calc(142px + var(--hero-card) * 4 / 7);
    /* 블러 배경을 .hero 위쪽(GNB·공지 뒤)으로 얼마나 끌어올릴지 — GNB(2단 ~118px)+공지(최대 ~80px) 커버 */
    --hero-bg-extend:200px;
  }
  /* align-self:start는 데스크톱 grid 전용 지정이다 — 모바일은 flex-column이라 align-self가
     가로축(폭)에 적용되므로, 되돌리지 않으면 배너가 폭 전체로 안 늘어나는 회귀가 생긴다. */
  .hero__banner{order:2;border-radius:0;overflow:visible;align-self:stretch}
  /* ⚠ 260820 롤백 버그 수정 — 좌우 여백은 peek이 아니라 "카드를 중앙에 놓는 데 필요한 값"이어야 한다.
     --hero-card가 520px 상한에 걸리는 폭(대략 태블릿 이상)에서는 필요한 여백이 peek보다 커지는데,
     여백이 모자라면 트랙 양 끝의 **클론 슬라이드를 중앙까지 스크롤할 수 없다**(872px 실측 100px 부족).
     그러면 createLoopCarousel의 targetOf()가 clamp된 값을 돌려주고, 루프가 감길 때마다 화면이
     중앙에서 어긋난 채 멈췄다가 되감겨 "자꾸 롤백"으로 보인다. max()로 필요한 만큼 확보한다
     — 카드가 상한에 안 걸리는 폰 폭에서는 두 값이 같아 기존과 완전히 동일하다(375 실측 30px). */
  .hero__track{gap:var(--gap-card);
    --hero-side:max(var(--hero-peek), calc((100% - var(--hero-card)) / 2));
    scroll-padding-inline:var(--hero-side);padding-inline:var(--hero-side)}
  .hero__slide{--hero-ratio:7/8;flex-basis:var(--hero-card);border-radius:var(--r-hero)}
  /* 카드가 최대폭에서 멈추면 실제 여백이 --hero-peek보다 커지므로, 카운터는 카드 우측 기준으로 계산 */
  .hero__counter{right:calc((100vw - var(--hero-card)) / 2 + 16px);bottom:16px}
  .tag--pill{font-size:var(--fs-body-lg);padding:7px 16px}

  .section{padding-top:var(--gap-section)}
  /* 260811: 모바일도 데스크톱과 같은 원칙 — GNB 아래 첫 섹션만 진입 여백을 줄인다.
     HOME 모바일은 히어로가 GNB에 붙고(.hero{padding-top:0}, 블러 배경이 GNB 뒤까지 올라가는 구조)
     첫 텍스트("PLAY NOW!")가 .playnow{padding-top:12px}로 12px에서 시작한다 — 허브 4종은 40px이라
     리듬이 어긋나 있었다. 기준값을 HOME과 정확히 같은 12px로 맞춘다. */
  main > .section:first-child{padding-top:12px}
  /* 히어로 바로 다음 섹션(취향대로 둘러보기)만 여백을 소폭 줄여 첫 화면에 제목이 더 보이게 —
     다른 섹션 간 간격(공용 --gap-section)은 건드리지 않는다 */
  .hero + .section{padding-top:28px}
  .section__head{gap:4px;margin-bottom:16px}
  .section__head h1,.section__head h2{font-size:var(--fs-h1)}
  .section__head p{display:none;font-size:var(--fs-caption)}
  .section__head p.only-mob{display:block}

  /* 칩: 한 줄 가로 스크롤 (드롭다운 열림 시 클립 해제) */
  .chips{flex-wrap:nowrap;overflow-x:auto;scrollbar-width:none;margin-inline:calc(var(--pad-page) * -1);padding-inline:var(--pad-page);margin-bottom:16px}
  .chips::-webkit-scrollbar{display:none}
  .chips.is-open{overflow:visible}
  .chip{flex:none}

  /* 레일: 피크 + 진행바, 화살표 제거 */
  .rail__arrow{display:none}
  /* scroll-padding-inline: 자동 스냅이 padding을 무시하고 첫 카드를 뷰포트 끝에 붙이는 현상 방지 */
  .rail__track{gap:12px;margin-inline:calc(var(--pad-page) * -1);padding-inline:var(--pad-page);scroll-padding-inline:var(--pad-page)}
  .rail--bleed{margin-right:0}
  .rail--bleed .rail__track{padding-right:var(--pad-page)}
  .card--pick{width:260px} /* 1장 + 다음 카드 피크 */
  .card--wide{width:300px}
  .card--sns{width:260px} /* 정방형 미디어 — .card--pick과 동일 폭(Phase 84) */
  .card__title{font-size:20px}
  .card__title--sns{font-size:var(--fs-card)}

  /* 처음방문 CTA — 인라인 배너 */
  /* 260803: 모바일 인라인 CTA도 데스크톱 사이드바와 동일한 완성형 이미지 배너를 그대로 쓴다
     (같은 이미지 1장 재사용 — 모바일 전용 자산을 별도로 요구하지 않는다). 비율·배경은 .firstvisit
     베이스 규칙이 담당하므로 여기서는 배치(노출·상단 여백)만 지정한다. */
  /* 260819: 넓은 모바일/태블릿(~997px)에서 aspect 13/3이 배너를 세로로 부풀려
     텍스트 위·말마 아래만 남고 가운데가 텅 비어 보였다 — 인라인 변형은 비율 대신
     높이 클램프(96~136px)로 고정해 어떤 폭에서도 낮은 띠 배너를 유지한다. */
  /* 260820: 태블릿 폭(~997px)에서 96~136px는 폭 대비 너무 납작해(7:1 이상) 띠처럼 보였다 —
     높이를 폭에 더 따라가게 키운다(375에서 112 · 768에서 146 · 997에서 180). */
  /* 260821: 모바일 배너가 "애매하게 작다"는 피드백 — 높이·텍스트·말마를 함께 키운다.
     ⚠ 343px 폭에서는 셋이 서로 경쟁한다(말마는 보이는 부분이 가로로 더 넓은 1.07:1이라
     높이를 키우면 폭도 같이 커져 문구를 침범한다). 실측으로 잡은 균형점:
     배너 134 · 문구 21px · 좌패딩 12 · 말마 158%(폭 165px) → 문구와 13px 여유, 위로 21px 돌출. */
  /* 모바일·태블릿 — 위 --fv-* 변수만 덮어쓰면 높이·말마 크기·예약 폭이 함께 따라온다.
     ⚠ 343px 폭에서는 문구·간격·말마가 서로 자리를 다툰다: 말마는 보이는 부분이 가로로 더 넓어
     (약 1.07:1) 키울수록 폭을 많이 먹는다. --fv-right를 음수로 둬 배너 모서리 밖(페이지 여백)까지
     걸치게 하는 것이 문구 자리를 뺏지 않고 캐릭터만 키우는 유일한 여지다.
     간격(--fv-gap)은 padding-right로 예약돼 있어 어떤 폭에서도 지켜진다. */
  /* 260821: 왼쪽 여백이 데스크톱(28/380 = 7.4%)에 비해 모바일만 3.5%라 문구가 모서리에
     붙어 보였다(클라이언트 리포트) → 26px(7.6%)로 맞춘다. 늘린 여백만큼 말마가 쓸 폭이
     줄지만, 배너 높이를 조금 낮추고(134→124) --fv-scale을 올리면(1.55→1.62) **같은 폭에서
     오히려 돌출이 커진다** — 돌출 = 폭 × (0.938 − 1.285/scale)이라 scale이 클수록 유리하다.
     결과: 여백 7.6% · 돌출 23px(배너 높이의 18%, 참고 이미지 비율과 동일). */
  /* 260830 축소(고객: "영역 차지가 부담스럽고 크다") — 260821에 키웠던 값(124~180px·말마 162%)을
     한 단계 내린다: 높이 96~120px(태블릿 상한 180→120이 체감 축소의 핵심), 말마 150%(폭 156→112px대),
     문구 18~22px. 말마 크기·예약 폭·돌출은 전부 --fv-h에서 파생이라 세 변수만 내리면 함께 줄어든다
     (돌출 23px대 → 10px대). 좌패딩 26은 유지(여백 비율 7%대 — 260821 확정값). */
  /* 260831(총괄, 예시 이미지): 모바일 배너를 **알약(pill) 형태 + 큰 문구**로 바꾼다.
     · border-radius를 --r-full로 → 양 끝이 완전히 둥근 알약. 둥근 끝이 문구를 파고들지 않도록
       왼쪽 패딩을 26 → 32px로 넓힌다.
     · 문구를 키우고(18~22 → 20~26px) 굵기도 700 → 800으로.
     · **높이·문구·말마 전부 고정값**(260831 총괄: "저 폭에서 배너가 너무 커진다 · 캐릭터도
       글자도 커지면 안 되고 높이는 고정이면 좋겠다"). 구 clamp(88~112px)는 997px에서 112px까지
       부풀어 태블릿 폭에서 배너가 화면을 크게 먹었다 → **72px 고정**(같은 요청의 "더 얇게" 반영),
       문구도 19px 고정. 폭이 넓어져도 배너는 가로로만 길어진다.
     · right는 **양수(2px)** — 말마를 배너 **안쪽**에 완전히 넣는다.
     ⚠ 260831 리포트("우측 잘린다"): --fv-right를 음수로 두면 말마가 배너 밖으로 나가는데,
       배너 오른쪽 = 페이지 여백(16px) 안쪽이라 화면 가장자리까지 남는 여유가 2px뿐이었다
       (-18px일 땐 아예 2px 밖으로 나가 잘렸다). **말마를 배너 밖으로 내밀지 말 것** —
       가로 여유를 여백에 기대면 기기·스크롤바 변수에 바로 잘린다.
     ⚠ 이 네 값(scale·gap·right·padding-left)은 문구 한 줄 유지와 직결된다 — 바꾸면 375px에서
       줄바꿈 여부를 반드시 실측할 것. */
  .firstvisit--inline{--fv-h:72px;--fv-scale:1.8;--fv-gap:12px;--fv-right:2px;
    border-radius:var(--r-full);
    /* 260830: 배너 위 64px / 아래 40px(다음 섹션 padding-top)로 비대칭이라 이 자리만 유독
       벌어져 보였다(총괄: "취향대로↔언제와도 간격만 넓다"). 섹션 리듬과 같은 --gap-section으로
       맞춰 위·아래 40px 대칭. 말마 돌출은 이 간격 안에서 처리돼 위 카드를 침범하지 않는다. */
    display:flex;margin-top:var(--gap-section);padding-left:26px}
  .firstvisit--inline .firstvisit__title{font-size:19px;font-weight:800}

  /* 코스: 데스크톱과 같은 원리(중앙 정렬 + 카드 폭 기준 padding-inline) — .courses-viewport의
     Full-bleed는 위 공용 규칙이 --pad-page(모바일 16px) 기준으로 이미 처리해 여기서 다시 정의하지
     않는다. 카드 폭만 데스크톱의 반응형 공식 대신 기존 310px 고정값으로 되돌린다(모바일 규격 유지). */
  .courses{gap:12px;padding-inline:calc((100% - 310px)/2);scroll-padding-inline:calc((100% - 310px)/2)}
  .course{flex:0 0 310px;width:310px}
  .courses__ctrl{justify-content:flex-end;gap:8px;margin-top:12px}
  .courses__bar{display:none}
  .courses__pause{width:30px;height:30px;border:0;background:rgba(0,0,0,.55);color:var(--white);font-size:var(--fs-caption);font-weight:400}
  .courses__count{background:rgba(0,0,0,.55);color:var(--white);border-radius:var(--r-full);height:30px;display:inline-flex;align-items:center;padding-inline:12px}

  /* 방문 정보 */
  .visit__title{font-size:20px;line-height:29px}

  /* Footer */
  .footer__inner{padding-top:40px;padding-bottom:32px}
  .footer__logo{height:30px}
  .footer__line{margin-block:24px}
  .footer__links{margin-top:24px}
  .footer__bottom{flex-direction:column;gap:8px}
  .footer__legal-grid{grid-template-columns:1fr;gap:20px}

  /* 260821: 모바일 플로팅은 세로로 쌓으면 콘텐츠를 길게 덮는다 — 가로 정렬로 바꾼다
     (클라이언트가 보여준 플로팅 배너 예시와 같은 형태).
     260827: bottom에 env(safe-area-inset-bottom) 보정 — 전 페이지가 viewport-fit=cover라
     아이폰(홈 인디케이터 기종)에서 화면이 인디케이터 밑까지 확장되는데, 고정 16px만 주면
     FAB이 인디케이터에 걸려 잘려 보였다(실기기 리포트). 토스트·상세 하단 CTA 바는 이미
     같은 보정을 쓰고 있었고 fab-stack 기본값만 누락돼 있던 것. */
  /* 260830(총괄): 미니게임이 무료입장권 **위**에 오도록 세로 스택으로 되돌린다(가로 정렬은
     260821 클라이언트 요청이었으나 이번 지시로 대체). 미니게임 말마는 자기 원 위로만 넘치므로
     아래의 무료입장권과 겹치지 않는다. */
  .fab-stack{right:16px;bottom:calc(16px + env(safe-area-inset-bottom, 0px));gap:10px;flex-direction:column;align-items:flex-end}
  /* 무료티켓은 원형 안에 "무료 / 티켓" 2줄로 — 아이콘만 있으면 뭔지 모르겠다는 피드백 이후
     문구를 되살리되, 가로 정렬에서 필이 길어지지 않도록 원형에 2줄로 넣는다.
     원이 커지더라도 텍스트가 들어가는 쪽이 낫다는 클라이언트 판단(64px). */
  .fab--ticket{width:64px;height:64px;padding:0;flex-direction:column;justify-content:center;
    gap:1px;border-radius:var(--r-full);font-size:11px;font-weight:700;line-height:1.15;text-align:center}
  .fab--ticket svg{width:16px;height:16px}
  .fab--ticket .fab__label{display:block}
  .fab--ticket .fab__label-br{display:block}
  .fab--ticket .fab__label-sub{display:none}
  /* 260830 고객 요청: 미니게임도 무료입장권과 똑같은 64px 원형 + 말마는 좌우 겹침이 아니라
     **버튼 바로 위에서 빼꼼**. 빼꼼(몸통은 원 뒤에 숨고 머리만 위로)은 char에 z-index:-1을
     주고 버튼에 isolation:isolate를 걸어 만든다 — 격리 없이는 음수 z-index가 조상 배경 뒤로
     빠져 통째로 안 보인다(캘린더 선택 원 ::before와 같은 기법, Phase 19 교훈). */
  /* 260830: 미니게임은 데스크톱과 완전히 동일한 원형 이미지 버튼이라 모바일 전용 재정의가 없다
     (예전의 원형 전환·문구 2줄·말마 빼꼼 z-index 규칙은 이미지 한 장으로 대체돼 전부 삭제). */
}

/* 좁은 폰(iPhone SE~플러스급)에서는 GNB 기업홈 라벨 → 마사회 파비콘 축약(997 블록의 .gnb__corp
   주석 참고 — "한국마사회" 5자는 418px 미만에서 방문정보를 가린다 · 실측 경계 418 + 여유 6px).
   아이콘은 일반 외부링크 아이콘이 아니라 kra.co.kr 공식 파비콘(총괄 지정) — 어느 기관으로 가는
   링크인지 심볼로 읽힌다. 424~997은 "한국마사회" 텍스트. */
@media (max-width:423px){
  .gnb__corp__label{display:none}
  .gnb__corp{padding:2px;gap:3px}
  .gnb__corp__favicon{display:block;width:18px;height:18px}
  /* 파비콘 옆에도 작은 바로가기 아이콘 유지(260830 총괄) — 합계 38px, 가려짐 0 실측 */
  .gnb__corp .ico-svg{width:13px;height:13px}
}

/* =========================================================
   말마 미니게임 선택 모달 (260827 — home.js 게임 모달 IIFE 전용)
   공용 .modal 셸 위에 카드 2장만 얹는다. 캐릭터는 기존 말마 PNG 재사용.
   ========================================================= */
.game-modal .modal__box{width:min(520px,calc(100vw - 40px))}
.game-modal__body{padding:20px}
.game-modal__grid{display:grid;grid-template-columns:1fr 1fr;gap:12px}
.game-card{position:relative;display:flex;flex-direction:column;align-items:center;text-align:center;
  gap:4px;padding:22px 14px 18px;border-radius:var(--r-card);text-decoration:none;color:var(--ink);
  overflow:hidden;transition:transform .16s ease}
.game-card:hover{transform:translateY(-3px)}
.game-card__char{height:96px;width:auto;margin-bottom:8px;transition:transform .16s ease}
.game-card:hover .game-card__char{transform:rotate(-5deg) scale(1.07)}
.game-card__name{font-size:var(--fs-h3);font-weight:800}
.game-card__desc{font-size:var(--fs-caption);color:var(--grey);line-height:1.5;word-break:keep-all}
/* PLAY 필 = 선택 칩과 같은 브랜드 옐로우(§ Phase 15의 선택 색 언어 재사용) */
.game-card__play{margin-top:12px;font-size:var(--fs-label);font-weight:800;letter-spacing:.02em;
  padding:8px 22px;border-radius:var(--r-full);background:var(--yellow-500);color:var(--ink)}
/* 러너 = 초원 그린 (기존 -200 파스텔 스케일만 사용 — Collection 밴드와 같은 원칙) */
.game-card--run{background:var(--green-200)}
/* 우주 = ink 다크 + CSS 별(이미지 자산 없이 radial-gradient 점 2겹) */
.game-card--space{background:var(--ink);color:var(--white)}
.game-card--space .game-card__desc{color:rgba(255,255,255,.72)}
.game-card--space::before{content:"";position:absolute;inset:0;pointer-events:none;opacity:.7;
  background-image:radial-gradient(circle, rgba(255,255,255,.95) 1px, transparent 1.6px),
    radial-gradient(circle, rgba(255,255,255,.6) 1px, transparent 1.4px);
  background-size:74px 74px, 52px 52px;background-position:8px 12px, 34px 40px}
@media (max-width:430px){
  .game-modal__grid{gap:10px}
  .game-card{padding:18px 10px 14px}
  .game-card__char{height:72px}
  .game-card__desc{font-size:11px}
}

/* =========================================================
   가로형 썸네일 카드 미디어 (260828 — 지금 현장/현장 더보기 유튜브 썸네일)
   세로/정방형 카드 프레임에 16:9 썸네일을 크롭 없이: 실제 썸네일 contain 중앙 +
   같은 이미지를 확대·강블러 배경으로 깔아 위아래 여백이 비지 않게(클라이언트 지정 처리,
   상세 갤러리 유튜브 카드와 동일 기법). 프레임 비율·radius·배지는 기존 카드 규칙 그대로.
   ========================================================= */
.card__media--fit{position:relative;overflow:hidden}
.card__media--fit .card__media-bg{position:absolute;inset:0;width:100%;height:100%;object-fit:cover;
  filter:blur(28px) brightness(.82);transform:scale(1.35)}
.card__media--fit .card__media-fg{position:absolute;inset:0;width:100%;height:100%;object-fit:contain}
.card__media--fit .sns-ch,.card__media--fit .card-region-badge{z-index:1}
