  :root{
    --panel:#2c2140; --panel2:#3a2c55; --edge:#1a1228;
    --ink:#f6f0ff; --muted:#b7a6d6; --gold:#ffd23f; --xp:#5ad1ff;
    --font:"Trebuchet MS","Segoe UI",system-ui,sans-serif;
  }
  *{box-sizing:border-box;-webkit-tap-highlight-color:transparent;user-select:none}
  /* ⚠ iOS 설치 앱(홈 화면 추가)에서 **가로로 돌리면 빈 여백이 생긴다.**
       `height:100%` 는 회전 순간의 문서 높이를 따라가지 못해
       문서가 화면보다 작은 채로 남고, 그 밖은 브라우저 기본색(흰색)으로 보인다.
       (사파리는 `orientation:landscape` 를 무시하므로 회전에 기대질 수도 없다)
     → `position:fixed; inset:0` 으로 **뷰포트에 직접 못 박는다.**
       회전하든 주소창이 숨든 항상 꿉 차다. */
  html{background:#191024}
  html,body{margin:0;position:fixed;inset:0;width:100%;height:100%;
    background:#191024;color:var(--ink);font-family:var(--font);overflow:hidden}
  #app{max-width:none;margin:0;padding:8px;display:flex;flex-direction:column;gap:8px;height:100%}
  .topbar{display:flex;align-items:center;gap:8px;background:var(--panel);border:2px solid var(--edge);border-radius:14px;padding:8px 10px}
  .who{position:absolute;left:10px;top:10px;display:flex;align-items:center;gap:8px;width:228px;max-width:46%;
    background:rgba(25,16,36,.62);border:2px solid var(--edge);border-radius:12px;padding:6px 8px;pointer-events:none;z-index:6}
  .av{width:38px;height:38px;border-radius:50%;position:relative;flex:0 0 auto;box-shadow:inset 0 -3px 0 rgba(0,0,0,.25)}
  .av svg{position:absolute;inset:0;margin:auto}
  .meta{min-width:0;flex:1}
  .meta .l1{font-weight:800;font-size:14px;display:flex;align-items:center;gap:6px}
  .lvpill{background:var(--gold);color:#4a3600;font-size:10px;font-weight:900;border-radius:999px;padding:1px 6px}
  .xpwrap{margin-top:4px;height:7px;background:#160e22;border-radius:999px;overflow:hidden}
  .xpbar{height:100%;width:0;background:linear-gradient(90deg,#2aa8ff,var(--xp));transition:width .2s}
  .hpwrap{margin-top:5px;height:8px;background:#160e22;border-radius:999px;overflow:hidden}
  .hpbar{height:100%;width:100%;background:linear-gradient(90deg,#e0533c,#ff8a5b);transition:width .12s}
  .hptext{font-size:10px;font-weight:800;color:#ff9c86;margin-left:auto}
  .res{position:absolute;left:50%;top:10px;transform:translateX(-50%);display:flex;gap:9px;align-items:center;
    background:rgba(25,16,36,.62);border:2px solid var(--edge);border-radius:12px;padding:5px 10px;pointer-events:auto;z-index:6}
  .res .item{display:flex;align-items:center;gap:3px;font-weight:800;font-size:13px;white-space:nowrap}
  .res .item svg{width:16px;height:16px}
  .stage{position:relative;flex:1;border-radius:16px;overflow:hidden;border:2px solid var(--edge);background:#6cbf4f;min-height:0}
  canvas{display:block;width:100%;height:100%;touch-action:none}
  .float-ui{position:absolute;inset:0;pointer-events:none}
  .btn{pointer-events:auto;background:var(--panel);color:var(--ink);border:2px solid var(--edge);border-radius:999px;
    padding:8px 13px;font-weight:800;font-size:13px;font-family:var(--font);cursor:pointer;display:flex;align-items:center;gap:7px}
  .btn.on{background:#3ea06b;border-color:#276e49}
  .dot{width:9px;height:9px;border-radius:50%;background:#7d6ba0}
  .btn.on .dot{background:#d6ffe6;box-shadow:0 0 8px #8effb9}
  /* ⚠ 모달(20~25) 위에 떠야 한다. 가방·설비 창을 연 채로 강화하면
     안내가 창 뒤에 가려져 **아무 반응이 없는 것처럼 보인다.** */
  #hint{position:absolute;left:50%;bottom:58px;transform:translateX(-50%);text-align:center;font-size:12px;color:#fff;background:rgba(25,16,36,.6);
    padding:5px 10px;border-radius:8px;max-width:70%;line-height:1.35;z-index:40}
  .classes{display:grid;grid-template-columns:repeat(6,1fr);gap:6px}
  .cbtn{background:var(--panel);border:2px solid var(--edge);border-radius:11px;padding:7px 2px 5px;cursor:pointer;
    display:flex;flex-direction:column;align-items:center;gap:3px;color:var(--muted);transition:.12s}
  .cbtn .chip{width:30px;height:30px;border-radius:8px;display:flex;align-items:center;justify-content:center}
  .cbtn .chip svg{width:20px;height:20px}
  .cbtn .lbl{font-size:10.5px;font-weight:800}
  .cbtn.sel{border-color:var(--gold);color:var(--ink);background:var(--panel2);transform:translateY(-2px)}
  .foot{font-size:10px;color:var(--muted);text-align:center;line-height:1.4}
  .res{cursor:pointer;transition:.12s}
  .res:hover{border-color:var(--gold)}
  .res:hover{background:var(--panel2)}
  .bag-hint{font-size:9px;color:var(--muted);font-weight:700;margin-left:2px}
  #saveflash{position:absolute;left:50%;bottom:64px;transform:translateX(-50%);
    background:rgba(62,160,107,.92);color:#fff;font-weight:800;font-size:12px;padding:5px 12px;border-radius:999px;
    opacity:0;transition:opacity .3s;pointer-events:none;z-index:6}
  #invModal{position:absolute;inset:0;background:rgba(10,7,16,.72);display:none;align-items:center;justify-content:center;z-index:20;padding:14px}
  #invModal.open{display:flex}
  .topbtns{position:absolute;top:10px;right:10px;display:flex;gap:6px;flex-direction:column;align-items:flex-end;z-index:5}
  .btn.small{padding:6px 10px;font-size:11px}
  .quickbar{display:flex;gap:6px;pointer-events:auto}
  .zoombtns{position:absolute;left:10px;bottom:30px;display:flex;flex-direction:column;align-items:center;gap:6px;pointer-events:auto;z-index:5}
  #zoomSlider{writing-mode:vertical-lr;direction:rtl;width:22px;height:96px;accent-color:var(--gold,#ffd23f);cursor:pointer}
  .zbtn{width:34px;height:34px;border-radius:9px;border:2px solid var(--edge);background:rgba(20,14,30,.72);
    color:var(--ink);font-size:18px;font-weight:800;cursor:pointer;font-family:var(--font);line-height:1;padding:0}
  #modeBtn{background:#3a2836;border-color:#e0563c}
  #modeBtn.gather{background:#26362a;border-color:#54b06a}
  .qslot{width:44px;height:44px;border-radius:11px;background:rgba(20,14,30,.72);border:2px solid var(--edge);
    display:flex;align-items:center;justify-content:center;position:relative;cursor:pointer}
  .qslot svg{width:26px;height:26px}
  .qslot .num{position:absolute;top:1px;left:4px;font-size:9px;font-weight:900;color:var(--muted)}
  .qslot .q{position:absolute;bottom:0px;right:4px;font-size:10px;font-weight:900;color:#fff;text-shadow:0 1px 2px #000}
  .qslot.empty{opacity:.5}
  .tabs{display:flex;gap:5px;margin-bottom:9px}
  .tab{flex:1;padding:7px 2px;border-radius:9px;border:2px solid var(--edge);background:var(--panel2);
    color:var(--muted);font-weight:800;font-size:12px;font-family:var(--font);cursor:pointer}
  .tab.on{background:var(--gold);color:#3a2a00;border-color:var(--gold)}
  .sortrow{display:flex;align-items:center;gap:6px;margin-bottom:10px}
  .sortrow .slabel{font-size:11px;color:var(--muted);font-weight:800}
  .sbtn{padding:5px 9px;border-radius:8px;border:2px solid var(--edge);background:var(--panel2);color:var(--muted);
    font-weight:800;font-size:11px;font-family:var(--font);cursor:pointer}
  .sbtn.on{background:var(--panel);color:var(--ink);border-color:#4a5a7a}
  .sbtn.ord{margin-left:auto}
  #statsModal{position:absolute;inset:0;background:rgba(10,7,16,.72);display:none;align-items:center;justify-content:center;z-index:21;padding:14px}
  #statsModal.open{display:flex}
  .statrow{display:flex;justify-content:space-between;padding:7px 2px;border-bottom:1px solid var(--edge);font-size:13px}
  .statrow .k{color:var(--muted);font-weight:700}
  .statrow .v{font-weight:800}
  .statrow .v small{color:var(--muted);font-weight:700}
  .statgrid{display:grid;grid-template-columns:1fr 1fr;gap:6px;margin:10px 0}
  .statcell{display:flex;align-items:center;gap:6px;background:var(--panel2);border-radius:9px;padding:6px 8px}
  .statcell .sname{flex:1;font-size:11px;font-weight:800}
  .statcell .sname small{color:var(--muted);font-weight:700;font-size:9px}
  .statcell .sval{font-size:15px;font-weight:900;min-width:20px;text-align:right}
  .splus{width:24px;height:24px;border-radius:7px;border:2px solid var(--edge);background:var(--gold);color:#3a2a00;
    font-weight:900;font-size:14px;cursor:pointer;font-family:var(--font);padding:0}
  .splus:disabled{background:var(--panel);color:#5a5060;cursor:default;opacity:.5}
  .proflist{margin-top:8px;display:flex;flex-direction:column;gap:6px}
  .profrow{display:grid;grid-template-columns:auto auto 1fr;align-items:center;gap:8px;font-size:11px;font-weight:800}
  .profrow .pst{color:var(--muted);font-size:9px}
  .pbar{height:7px;background:#160e22;border-radius:999px;overflow:hidden}
  .pfill{height:100%;width:0}
  .stawrap{margin-top:4px;height:6px;background:#160e22;border-radius:999px;overflow:hidden}
  .stabar{height:100%;width:100%;background:linear-gradient(90deg,#2aa86a,#7ce0a0);transition:width .1s}
  .invcard{width:100%;max-width:360px;background:var(--panel);border:2px solid var(--edge);border-radius:16px;padding:16px}
  .invcard-lg{max-width:400px}
  .equip{display:flex;gap:8px;justify-content:center;margin-bottom:12px}
  .eslot{flex:1;max-width:88px;background:var(--panel2);border:2px solid var(--edge);border-radius:12px;padding:7px 4px;text-align:center;cursor:pointer;position:relative}
  .eslot .cap{font-size:9px;color:var(--muted);font-weight:800}
  .eslot .box{width:100%;height:46px;display:flex;align-items:center;justify-content:center}
  .eslot .box svg{width:36px;height:36px}
  /* 양손무기 사용 중 방패 슬롯: 지금 적용되지 않음을 표시 */
  .eslot.inactive{opacity:.42;filter:grayscale(.7)}
  .eslot.inactive .inact{position:absolute;left:50%;bottom:3px;transform:translateX(-50%);
    background:rgba(60,30,10,.9);border:1px solid #8a5a2a;border-radius:6px;
    padding:0 5px;font-size:9px;font-weight:800;color:#ffcf7a;white-space:nowrap;opacity:1}
  .eslot.has{border-color:var(--gold)}
  .eslot .plus{position:absolute;top:2px;right:5px;font-size:10px;font-weight:900;color:var(--gold)}
  .grid{display:grid;grid-template-columns:repeat(6,1fr);gap:5px;margin-bottom:10px}
  .cell{aspect-ratio:1;background:#160e22;border:2px solid #241a34;border-radius:9px;display:flex;align-items:center;justify-content:center;cursor:pointer;position:relative}
  .cell.sel{border-color:#fff}
  .cell svg{width:28px;height:28px}
  .cell .qty{position:absolute;bottom:1px;right:3px;font-size:10px;font-weight:900;color:#fff;text-shadow:0 1px 2px #000}
  .cell .pl{position:absolute;top:1px;right:3px;font-size:9px;font-weight:900;color:var(--gold)}
  .detail{background:var(--panel2);border-radius:10px;padding:9px 11px;min-height:52px;margin-bottom:10px;font-size:12px}
  .detail .dim{color:var(--muted)}
  .detail .dname{font-weight:800;font-size:13px}
  .detail .ddesc{color:var(--muted);margin-top:2px}
  .detail .act{margin-top:7px;display:flex;gap:6px}
  .detail .act button{padding:6px 12px;border-radius:8px;border:2px solid var(--edge);background:var(--gold);color:#3a2a00;font-weight:800;cursor:pointer;font-family:var(--font);font-size:12px}
  .detail .act button.ghost{background:var(--panel);color:var(--ink)}
  .resmini{display:flex;gap:12px;justify-content:center;margin-bottom:12px;font-size:12px;font-weight:800}
  .resmini .m{display:flex;align-items:center;gap:3px}
  .resmini .m svg{width:15px;height:15px}
  .invcard h3{margin:0 0 12px;font-size:16px;display:flex;align-items:center;justify-content:space-between}
  .invrow{display:flex;align-items:center;gap:10px;margin-bottom:11px}
  .invrow .ic{width:30px;height:30px;border-radius:8px;background:var(--panel2);display:flex;align-items:center;justify-content:center;flex:0 0 auto}
  .invrow .ic svg{width:20px;height:20px}
  .invrow .info{flex:1;min-width:0}
  .invrow .nm{font-size:12px;font-weight:800;display:flex;justify-content:space-between}
  .invrow .cnt{color:var(--muted)}
  .invrow .bar{margin-top:4px;height:7px;background:#160e22;border-radius:999px;overflow:hidden}
  .invrow .fill{height:100%;border-radius:999px;transition:width .2s}
  .invrow.full .cnt{color:#ff8a6b}
  .invbtns{display:flex;gap:8px;margin-top:6px}
  .invbtns button{flex:1;padding:9px;border-radius:10px;border:2px solid var(--edge);font-weight:800;font-family:var(--font);cursor:pointer;font-size:13px}
  .b-close{background:var(--panel2);color:var(--ink)}
  .b-reset{background:#5a2130;color:#ffd6d6;border-color:#3a1420}
  .xbtn{background:none;border:none;color:var(--muted);font-size:20px;cursor:pointer;line-height:1;padding:0 2px}
  @media(max-width:540px){
    .classes{grid-template-columns:repeat(3,1fr)}
    #hint{max-width:50%}
    .topbtns{top:10px}
    .qslot{width:40px;height:40px}
    .qslot svg{width:23px;height:23px}
  }

/* 모바일 세로 → 가로 안내 */
.rotate-hint{display:none}
@media (orientation:portrait) and (max-width:900px){
  .rotate-hint{display:flex;position:fixed;inset:0;z-index:9999;
    background:#150e22;align-items:center;justify-content:center;text-align:center}
  .rot-inner{color:#f7f3e8;font-family:var(--font,'Trebuchet MS');font-weight:800;
    font-size:22px;line-height:1.7;letter-spacing:.5px}
}

/* ---------- 홈 화면에 추가 ---------- */
/* ⚠ 버튼은 **세로 안내 화면 안에만** 산다 — 게임 HUD 를 안 건드려야
     지금까지 맞춰둔 배치가 안 흔들린다. (12j-install.js 가 .rot-inner 에 넣는다) */
.a2hs-btn{display:block;margin:26px auto 0;padding:13px 22px;
  font-family:var(--font,'Trebuchet MS');font-weight:800;font-size:15px;letter-spacing:.3px;
  color:#150e22;background:var(--gold,#ffd23f);border:none;border-radius:12px;
  box-shadow:0 6px 18px rgba(0,0,0,.4);cursor:pointer;-webkit-tap-highlight-color:transparent}
.a2hs-btn:active{transform:translateY(1px)}

#a2hsSheet{display:none;position:fixed;inset:0;z-index:10000;
  background:rgba(10,7,16,.78);align-items:center;justify-content:center;padding:20px}
#a2hsSheet.open{display:flex}
#a2hsSheet .a2hs-card{width:100%;max-width:340px;background:var(--panel,#2c2140);
  border:2px solid var(--edge,#1a1228);border-radius:16px;padding:18px;
  font-family:var(--font,'Trebuchet MS');color:var(--ink,#f6f0ff)}
#a2hsSheet .a2hs-tt{font-weight:800;font-size:16px;margin-bottom:14px}
#a2hsSheet .a2hs-step{display:flex;align-items:center;gap:9px;font-size:13px;
  font-weight:700;line-height:1.5;margin:10px 0}
#a2hsSheet .a2hs-n{flex:none;width:22px;height:22px;border-radius:50%;
  background:var(--gold,#ffd23f);color:#150e22;font-weight:900;font-size:12px;
  display:flex;align-items:center;justify-content:center}
#a2hsSheet .a2hs-ic{flex:none;display:flex;color:var(--gold,#ffd23f)}
#a2hsSheet .a2hs-x{display:block;width:100%;margin-top:16px;padding:11px;
  font-family:inherit;font-weight:800;font-size:14px;color:var(--ink,#f6f0ff);
  background:var(--panel2,#3a2c55);border:2px solid var(--edge,#1a1228);
  border-radius:11px;cursor:pointer}

/* 건설/제작 UI */
#modeBtn.build{background:#3a3226;border-color:#c9a24a}
.buildbar{position:absolute;left:50%;bottom:96px;transform:translateX(-50%);display:flex;gap:5px;flex-wrap:wrap;justify-content:center;max-width:92vw;
  background:rgba(25,16,36,.72);border:2px solid var(--edge);border-radius:12px;padding:6px;pointer-events:auto;z-index:6}
.bsel{background:var(--panel2);border:2px solid var(--edge);color:var(--ink);border-radius:9px;
  padding:6px 10px;font-weight:800;font-size:12px;cursor:pointer;font-family:var(--font)}
/* ⚠ 12b-aegis.js 가 건설 목록을 `.bscroll` 상자에 담는다.
   PC 에선 `display:contents` 로 **상자를 없는 셈 치기** 때문에 기존 배치가 그대로다. */
.bscroll{display:contents}
.bsel.on{border-color:var(--gold);background:#3a3226}
.binstall{background:var(--gold);color:#3a2a00;border:2px solid var(--edge);border-radius:9px;
  padding:6px 14px;font-weight:900;font-size:13px;cursor:pointer;font-family:var(--font)}
.build-act{pointer-events:auto}
.actbar{position:absolute;left:50%;bottom:58px;transform:translateX(-50%);display:flex;gap:6px;pointer-events:none;z-index:6}
#craftModal{position:absolute;inset:0;background:rgba(10,7,16,.72);display:none;align-items:center;justify-content:center;z-index:20;padding:14px}
#craftModal.open{display:flex}
.recipe{display:flex;align-items:center;gap:10px;background:var(--panel2);border:2px solid var(--edge);
  border-radius:12px;padding:10px;margin-bottom:8px}
.recipe .rc-name{font-weight:800;flex:1}
.recipe .rc-cost{font-size:11px;color:var(--muted)}
.recipe .rc-make{background:var(--gold);color:#3a2a00;border:none;border-radius:8px;padding:6px 12px;font-weight:900;cursor:pointer;font-family:var(--font)}
.recipe .rc-make:disabled{background:var(--panel);color:#5a5060;cursor:default}
.cq-row{font-size:12px;color:var(--ink);margin-top:4px}
.cq-bar{height:7px;background:#160e22;border-radius:999px;overflow:hidden;margin-top:2px}
.cq-fill{height:100%;background:linear-gradient(90deg,#2aa86a,#7ce0a0)}

/* 배치 확정 버튼(모바일, 고스트 옆) */
.placebtns{position:absolute;display:none;gap:4px;flex-direction:column;pointer-events:auto;z-index:8}
.placebtns .pOK{background:#2aa86a;color:#fff;border:2px solid #1c7a4c;border-radius:8px;padding:5px 10px;font-weight:900;font-size:12px;font-family:var(--font);cursor:pointer}
.placebtns .pOK.bad{background:#8a3a34;border-color:#5a221e}
.placebtns .pNo{background:#3a2836;color:#fff;border:2px solid var(--edge);border-radius:8px;padding:5px 10px;font-weight:800;font-size:12px;font-family:var(--font);cursor:pointer}

/* 습격 HUD / 경고 / 디버그 */
.raid-hud{position:absolute;left:50%;top:52px;transform:translateX(-50%);z-index:6;pointer-events:none;
  background:rgba(25,16,36,.7);border:2px solid var(--edge);border-radius:10px;padding:4px 12px;
  font-family:var(--font);font-weight:800;font-size:13px;color:#cfe3ff;white-space:nowrap}
.raid-hud.warn{border-color:#e8a23c;color:#ffcf7a;background:rgba(60,30,10,.7)}
.raid-hud.active{border-color:#e0563c;color:#ffb3a6;background:rgba(60,14,10,.75)}
/* 필드 보스 HP바 (교전 중에만 표시) */
.boss-hud{position:absolute;left:50%;top:92px;transform:translateX(-50%);z-index:7;pointer-events:none;
  width:min(420px,72vw);background:rgba(30,10,14,.72);border:2px solid #b8432f;border-radius:11px;padding:5px 11px 7px;
  font-family:var(--font);box-shadow:0 3px 14px rgba(0,0,0,.4)}
.boss-top{display:flex;align-items:baseline;justify-content:space-between;gap:8px;margin-bottom:4px}
.boss-name{font-weight:900;font-size:13px;color:#ffd23f;letter-spacing:.02em;white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
.boss-hp{font-weight:800;font-size:11px;color:#ffb3a6;font-variant-numeric:tabular-nums;white-space:nowrap}
.boss-wrap{height:9px;background:#2a1016;border-radius:6px;overflow:hidden;border:1px solid #6a2418}
.boss-bar{height:100%;width:100%;border-radius:5px;background:linear-gradient(90deg,#e0563c,#ffb03c);transition:width .15s}
.raid-flash{position:absolute;inset:0;z-index:4;pointer-events:none;opacity:0;
  background:radial-gradient(ellipse at center, rgba(200,20,20,0) 45%, rgba(200,20,20,.55) 100%);
  box-shadow:inset 0 0 120px 30px rgba(210,30,30,.6);transition:opacity .1s linear}
.dbgbtn{position:absolute;left:10px;top:100px;z-index:7;pointer-events:auto;width:30px;height:30px;
  border-radius:8px;border:2px solid var(--edge);background:rgba(20,14,30,.72);color:#fff;font-size:15px;cursor:pointer;padding:0}
.dbgmenu{position:absolute;left:10px;top:136px;z-index:8;pointer-events:auto;display:flex;flex-direction:column;gap:5px;
  background:rgba(20,14,30,.92);border:2px solid var(--edge);border-radius:10px;padding:8px}
.dbg-title{font-family:var(--font);font-weight:800;font-size:11px;color:var(--muted);padding:0 2px}
.dbg-item{background:var(--panel2);border:1px solid var(--edge);color:var(--ink);border-radius:7px;
  padding:6px 10px;font-family:var(--font);font-weight:700;font-size:12px;cursor:pointer;text-align:left;white-space:nowrap}
.dbg-item:hover{border-color:var(--gold)}
.blindslot{min-width:34px;font-size:15px;padding:5px 8px}
.blindslot:hover{border-color:var(--gold)}
.bbreak{flex-basis:100%;height:0}
.bsel.tgl{background:#241a33;border-color:#4a3a5e}
.bsel.tgl.on{background:#3a2a1a;border-color:var(--gold);color:#ffd98a}
#marketModal{position:absolute;inset:0;background:rgba(10,7,16,.72);display:none;align-items:center;justify-content:center;z-index:20;padding:14px}
#marketModal.open{display:flex}
#lootToast{position:absolute;left:50%;top:82px;transform:translateX(-50%);z-index:40;display:none;pointer-events:none;
  background:rgba(60,14,10,.88);border:2px solid #e0563c;border-radius:10px;padding:5px 12px;
  font-family:var(--font);font-weight:800;font-size:12px;color:#ffd7cf;white-space:nowrap}
.shield-tag{position:absolute;left:50%;top:76px;transform:translateX(-50%);z-index:6;pointer-events:none;
  background:rgba(20,40,60,.8);border:2px solid #6fa8dc;border-radius:10px;padding:3px 10px;
  font-family:var(--font);font-weight:800;font-size:11px;color:#bfe0ff}
#pvpBtn.on{background:#3a1a1a;border-color:#e0563c;color:#ffb3a6}
.qcancel{background:#3a2836;border:1px solid var(--edge);color:#ffb3a6;border-radius:6px;padding:2px 8px;font-size:11px;font-weight:700;font-family:var(--font);cursor:pointer;float:right}
.qcancel:hover{border-color:#e0563c}
.who{pointer-events:auto;cursor:pointer;position:relative}
.who:hover{border-color:var(--gold)}
#freeDot{position:absolute;top:-5px;right:-5px;background:#ffd23f;color:#3a2a00;border-radius:999px;
  font-size:10px;font-weight:900;padding:1px 5px;border:1px solid #8a6a00}
.coords{position:absolute;right:10px;left:auto;top:165px;z-index:6;pointer-events:none;
  display:flex;align-items:center;gap:7px;justify-content:flex-end;
  background:rgba(25,16,36,.55);border-radius:7px;padding:2px 8px;
  font-family:var(--font);font-weight:700;font-size:11px;color:#9fb2c8}
.coords .biome-tag{font-weight:900;letter-spacing:.02em;
  text-shadow:0 1px 2px rgba(0,0,0,.7);white-space:nowrap}
.coords .biome-tag:empty{display:none}
.coords #coordsXY{font-variant-numeric:tabular-nums}

.qcancel{background:transparent;border:none;color:#e08a7a;font-size:14px;font-weight:900;line-height:1;
  padding:0 2px;cursor:pointer;font-family:var(--font);float:none;margin-left:6px}
.qcancel:hover{color:#ff6b5e}
.cq-row{display:flex;align-items:center;gap:6px;flex-wrap:wrap}
.cq-row .cq-lbl{flex:1;min-width:0}
.cq-row .cq-bar{flex-basis:100%}
/* 설비/거래소 모달: 높이 고정 + 내부 스크롤 (버튼 위치 고정) */
#craftModal .invcard, #marketModal .invcard{max-height:78vh;display:flex;flex-direction:column}
#craftList{flex:1;min-height:0;overflow-y:auto}
#craftQ{flex:1;min-height:0;overflow-y:auto;display:flex;flex-direction:column}
#mkSell,#mkBuy{max-height:26vh;overflow-y:auto}
.mkbar{display:flex;gap:6px;margin:6px 0}
.mkinput{background:var(--panel2);border:2px solid var(--edge);color:var(--ink);border-radius:8px;
  padding:5px 8px;font-family:var(--font);font-size:12px;font-weight:700;flex:1;min-width:0}
.mkinput:focus{outline:none;border-color:var(--gold)}
.mkprice{flex:none}
#mkList{max-height:44vh;overflow-y:auto}

/* ===== 와이드 2단 모달 (거래소/설비/인벤) ===== */
.mdl{width:min(980px,95vw);max-width:none;height:min(700px,86vh);display:flex;flex-direction:column;
  background:var(--panel);border:2px solid var(--edge);border-radius:16px;padding:14px 16px}
.mdl h3{margin:0 0 8px;display:flex;align-items:center;justify-content:space-between;gap:16px}
/* ⚠ `flex:1; min-height:0` 만으로는 **격자가 부모를 뚫고 나간다.**
     행을 안 정하면 암묵적 행이 `auto` 로 생기고, `auto` 행은 **내용만큼 늘어나서**
     `.mdl-body` 자신을 밀어올려 `flex:1` 을 무력화시킨다.
     (실측: .mdl 은 700px 인데 .mdl-body 가 789px 로 불어나 장착 비교칸이 모달 밖으로 샐졌다)
   → `minmax(0,1fr)` 이어야 한다. `1fr` 은 최소가 내용 크기지만
     `minmax(0,1fr)` 은 0 까지 줄어들 수 있어 부모를 안 뚫는다.
     격자 오버플로우를 고칠 때와 **정확히 같은 함정**이다 — 그때는 가로, 이번은 세로. */
.mdl-body{flex:1;min-height:0;display:grid;
  grid-template-columns:1fr 320px;grid-template-rows:minmax(0,1fr);gap:12px}
.pane{min-height:0;display:flex;flex-direction:column}
.pane-scroll{flex:1;min-height:0;overflow-y:auto;padding-right:4px}
.side{background:var(--panel2);border:2px solid var(--edge);border-radius:12px;padding:12px;overflow-y:auto}
.tiles{display:grid;grid-template-columns:repeat(auto-fill,minmax(96px,1fr));gap:8px}
.tile{background:#160e22;border:2px solid #241a34;border-radius:11px;padding:8px 6px;cursor:pointer;
  display:flex;flex-direction:column;align-items:center;gap:4px;position:relative;transition:.1s}
.tile:hover{transform:translateY(-2px)}
.tile.sel{border-color:var(--gold);background:#241a33}
.tile .tname{font-size:11px;font-weight:800;text-align:center;line-height:1.25;color:var(--ink)}
.tile .tsub{font-size:10px;color:var(--muted)}
.tile .tbadge{position:absolute;top:3px;right:4px;font-size:10px}
.tile.dim{opacity:.45}
.side .sTitle{font-weight:900;font-size:15px;margin-bottom:4px}
.side .sRow{display:flex;justify-content:space-between;font-size:12px;padding:3px 0;border-bottom:1px solid #2a1f3a}
.side .sRow b{font-weight:800}
.cmp-up{color:#7ce0a0}.cmp-dn{color:#ff8a7a}.cmp-eq{color:var(--muted)}
/* ⚠ 예전엔 `.side .bigbtn` 이라 **옆 패널 안에서만** 스타일이 먹었다 →
   우편함·주사위 창의 버튼이 브라우저 기본 모양(흰 상자)으로 나왔다.
   어디서 쓰든 같은 모습이어야 한다. */
.bigbtn{width:100%;margin-top:10px;background:var(--gold);color:#3a2a00;border:none;border-radius:10px;
  padding:9px;font-weight:900;font-size:13px;cursor:pointer;font-family:var(--font)}
.bigbtn:hover{filter:brightness(1.08)}
.bigbtn.alt{background:var(--panel);color:var(--ink);border:2px solid var(--edge)}
.bigbtn.alt:hover{border-color:var(--gold)}
.bigbtn:disabled{background:#2a2233;color:#5a5060;cursor:default}
/* 좋은 창(820px 이하) — 좌우 2단을 위아래로 쌓는다.
   ⚠ 쌓기만 하면 **행 높이가 내용만큼 늘어난다.**
     그러면 `.cmpcol` 이 높이 제한을 못 받아 `.cmpcol .side{flex:1}` 도 줄어들 이유가 사라지고,
     장착 비교칸이 모달 밖으로 샐져나간다.
   → 칸마다 자르는 대신(`max-height:38vh` 은 카드가 두 장일 때 소용없었다)
     **본문 전체를 한 번에 스크롤**한다. 스크롤바가 하나라 휠도 예측대로 움직인다. */
@media(max-width:820px){
  .mdl{ height:92vh }
  .mdl-body{ grid-template-columns:1fr; overflow-y:auto }
  .side{ max-height:none }
  .cmpcol{ min-height:auto }
  .cmpcol .side{ flex:none; overflow-y:visible }
}
/* 인벤 2단: 그리드는 폭에 맞춰 자동 열 수 */
#invModal .grid{grid-template-columns:repeat(auto-fill,minmax(58px,1fr));gap:6px}
#invModal .equip{margin-bottom:8px}
#invModal .sortrow{align-items:center}
#invDetail .ddesc{font-size:12px;color:var(--muted);line-height:1.45}
/* ⚠ 격자 칸 안에서도 `min-height:0` 이 있어야 자식이 줄어든다.
     없으면 두 카드가 각자 내용만큼 버티며 칸을 밀어낸다. */
.cmpcol{display:flex;flex-direction:column;gap:8px;min-height:0;overflow:hidden}
.cmpcol .side{flex:1 1 0;min-height:0;overflow-y:auto}
.tipHead{font-size:10px;font-weight:900;letter-spacing:.5px;color:var(--muted);text-transform:uppercase;margin-bottom:4px}
.qslot.worn{border-color:var(--gold);box-shadow:0 0 0 2px rgba(255,210,63,.25) inset}
.dragghost{position:fixed;z-index:9999;pointer-events:none;transform:translate(-50%,-50%);opacity:.9;
  filter:drop-shadow(0 4px 6px rgba(0,0,0,.6))}
#invModal .cell,#invModal .eslot{touch-action:none}
body.dragging{user-select:none}
.gearbar{display:flex;gap:5px;pointer-events:auto}
.gslot{width:52px;height:52px;border-radius:10px;border:2px solid var(--edge);background:rgba(20,14,30,.72);
  display:flex;flex-direction:column;align-items:center;justify-content:center;gap:1px;cursor:pointer;position:relative}
.gslot .glab{font-family:var(--font);font-size:9px;font-weight:800;color:var(--muted);line-height:1}
.gslot.empty .gempty{font-size:16px;color:#4a3f5e;font-weight:900}
.gslot.worn{border-color:var(--gold);box-shadow:0 0 0 2px rgba(255,210,63,.25) inset}
.gslot:hover{border-color:#7a6a9e}

/* 하단 바: 소모품(좌) + 장비(우) 한 줄 */
.barrow{position:absolute;left:50%;bottom:12px;transform:translateX(-50%);display:flex;gap:14px;
  align-items:flex-end;z-index:6;pointer-events:none;transition:transform .25s ease, opacity .2s}
.barrow>*{pointer-events:auto}
.barrow.hidden{transform:translate(-50%,120%);opacity:0}
/* 상호작용 버튼 크게 */
.actbar{bottom:96px;gap:8px}
.build-act{font-size:15px;padding:11px 18px;border-radius:12px;font-weight:900}
.buildinfo{position:absolute;left:50%;bottom:14px;transform:translateX(-50%);display:flex;align-items:center;gap:12px;
  background:rgba(25,16,36,.86);border:2px solid var(--edge);border-radius:14px;padding:9px 16px;z-index:6;pointer-events:none;max-width:92vw}
.bi-icon{display:flex}
.bi-name{font-family:var(--font);font-weight:900;font-size:15px;color:var(--ink)}
.bi-lock{font-size:11px;color:#ff9a8a;font-weight:800}
.bi-sub{font-family:var(--font);font-size:11px;color:var(--muted);margin-top:2px}
.bi-lv{font-family:var(--font);font-size:11px;font-weight:800;color:#ffd98a;text-align:center;min-width:74px}
.bi-bar{height:5px;background:#160e22;border-radius:999px;overflow:hidden;margin-top:3px}
.bi-fill{height:100%;background:linear-gradient(90deg,#c9a24a,#ffd23f)}
.bsel.locked{opacity:.45}
/* 토스트 스택 (습격 타이머 아래) */
/* ⚠ 모달(z-index 20~25) **위**에 떠야 한다. 9 로 두면 가방을 연 채로 강화했을 때
   토스트가 모달 뒤에 가려져 **아무 반응이 없는 것처럼 보인다.** */
#toastStack{position:absolute;left:50%;top:84px;transform:translateX(-50%);z-index:40;pointer-events:none;
  display:flex;flex-direction:column;gap:5px;align-items:center;max-width:92vw}
.toast{background:rgba(25,16,36,.92);border:2px solid var(--edge);border-radius:10px;padding:6px 14px;
  font-family:var(--font);font-weight:800;font-size:13px;color:var(--ink);white-space:nowrap;
  box-shadow:0 3px 10px rgba(0,0,0,.45);animation:tin .18s ease}
.toast.warn{border-color:#e0563c;background:rgba(60,14,10,.92);color:#ffd7cf}
.toast.good{border-color:#5ce07a;background:rgba(14,45,25,.92);color:#c8ffd8}
@keyframes tin{from{opacity:0;transform:translateY(-6px)}to{opacity:1;transform:none}}
/* 저장됨: 좌하단 줌 옆에 작게 */
#saveflash{position:absolute;left:52px;bottom:16px;top:auto;right:auto;transform:none;z-index:6;
  font-size:10px;padding:2px 7px;background:rgba(20,14,30,.7);border:1px solid var(--edge);border-radius:6px;color:#9fd8a8}
/* 장비 슬롯을 아이템 슬롯과 동일 크기 */
.gslot{width:44px;height:44px;border-radius:11px}
.gslot .glab{font-size:8px}
/* HP바 오른쪽 컨트롤(자동사냥/우선순위) */
.whoctl{display:flex;flex-direction:row;gap:5px;pointer-events:auto;align-items:flex-end}
.ictl{width:26px;height:26px;border-radius:8px;border:2px solid var(--edge);background:rgba(20,14,30,.6);
  font-size:13px;line-height:1;padding:0;cursor:pointer;opacity:.45;transition:.12s}
.ictl.on{opacity:1;border-color:var(--gold);background:#3a2a1a;box-shadow:0 0 0 2px rgba(255,210,63,.18) inset}
.ictl:hover{opacity:.85}
/* PvP 태그: 자원 HUD 옆 */
.pvptag{display:flex;align-items:center;gap:3px;margin-left:6px;
  background:rgba(20,14,30,.5);border:2px solid var(--edge);border-radius:9px;padding:3px 8px;
  pointer-events:auto;cursor:pointer;font-family:var(--font);font-weight:900;font-size:10px;color:var(--muted)}
.pvptag .pv-ic{font-size:13px;filter:grayscale(1) opacity(.6)}
.pvptag.on{border-color:#e0563c;background:rgba(60,14,10,.75);color:#ffb3a6}
.pvptag.on .pv-ic{filter:none}
/* 미니맵이 우상단으로 이동 → 겹침 방지 */
.raid-hud{top:62px}
#toastStack{top:108px;gap:8px}
.shield-tag{top:96px}

.ictl{width:32px;height:32px;font-size:15px}
.res{align-items:center}

.mdl h3 .xbtn{flex:none;margin-left:auto}
.modetag{color:var(--ink);border-color:#e0563c;background:rgba(60,20,20,.5)}
.modetag.gather{border-color:#54b06a;background:rgba(20,50,30,.5)}
.modetag.build{border-color:#c9a24a;background:rgba(58,50,38,.5)}
.bag-hint.first{margin-right:4px;font-size:15px}
/* 획득 로그 (좌하단) */
.gainlog{position:absolute;left:10px;top:50%;transform:translateY(-50%);z-index:6;pointer-events:none;
  display:flex;flex-direction:column;justify-content:flex-end;gap:3px;max-width:44vw;max-height:46vh;overflow:hidden}
.gline{font-family:var(--font);font-weight:800;font-size:11px;line-height:1.35;
  background:rgba(20,14,30,.5);border-radius:6px;padding:2px 8px;white-space:nowrap;align-self:flex-start;
  text-shadow:0 1px 2px rgba(0,0,0,.7);animation:gin .18s ease;transition:opacity .25s ease, transform .25s ease}
.gline.out{opacity:0 !important;transform:translateY(-10px)}
@keyframes gin{from{opacity:0;transform:translateY(8px)}to{opacity:1;transform:none}}
/* 커서는 항상 표시 (조준/커서 모드 구분 없음) */
/* F 상호작용 프롬프트 */
/* ⚠ 건설바(bottom:96px)가 두 줄이 되면 150px 까지 올라와 겹친다.
   건설 모드일 때는 더 위로 올린다 (.buildon 은 건설 중에 body 에 붙는다). */
.interprompt{position:absolute;left:50%;bottom:150px;transform:translateX(-50%);z-index:7;pointer-events:none;
  display:flex;align-items:center;gap:7px;background:rgba(25,16,36,.86);border:2px solid var(--edge);border-radius:12px;
  padding:6px 14px;font-family:var(--font);font-weight:800;font-size:14px;color:var(--ink);white-space:nowrap}
.ip-key{background:var(--gold);color:#3a2a00;border-radius:6px;padding:1px 8px;font-size:12px;font-weight:900}
.ip-more{color:var(--muted);font-size:11px;margin-left:4px}
/* 상호작용 목록 */
#interList{position:absolute;inset:0;display:none;align-items:center;justify-content:center;z-index:21;background:rgba(10,7,16,.5)}
#interList.open{display:flex}
.il-card{background:var(--panel);border:2px solid var(--edge);border-radius:14px;padding:14px;min-width:240px;display:flex;flex-direction:column;gap:6px}
.il-head{font-family:var(--font);font-weight:900;font-size:13px;color:var(--muted);margin-bottom:2px}
.il-item{background:var(--panel2);border:2px solid var(--edge);color:var(--ink);border-radius:10px;padding:9px 12px;
  font-family:var(--font);font-weight:800;font-size:13px;cursor:pointer;text-align:left}
.il-item:hover{border-color:var(--gold)}
.il-d{float:right;color:var(--muted);font-size:11px}
.il-close{background:var(--panel);border:2px solid var(--edge);color:var(--muted);border-radius:10px;padding:7px;
  font-family:var(--font);font-weight:800;font-size:12px;cursor:pointer;margin-top:2px}
/* 단축키 설정 */
#keyModal{position:absolute;inset:0;background:rgba(10,7,16,.72);display:none;align-items:center;justify-content:center;z-index:22;padding:14px}
#keyModal.open{display:flex}
.keybtn{background:var(--panel2);border:2px solid var(--edge);color:var(--ink);border-radius:8px;padding:3px 12px;
  font-family:var(--font);font-weight:900;font-size:12px;cursor:pointer;min-width:64px}
.keybtn.wait{border-color:var(--gold);color:var(--gold)}
/* PC: 상호작용은 F 프롬프트로 통일 → 버튼 숨김 / 모바일: 버튼 사용 */
body:not(.touch) .actbar{display:none}
/* 화면 위 UI는 항상 클릭 가능 (커서가 늘 보이므로 모드별 차단 없음) */

/* 설비 창: 오른쪽 대기열/보관함 패널을 세로로 길게 */
#craftModal .mdl-body{grid-template-columns:1fr 330px}
#craftQ{height:100%}
#craftQ .cq-row{flex:none}
#craftQ .blindwrap{flex:1;min-height:0;overflow-y:auto;align-content:flex-start}
/* 월드맵 */
#mapModal{position:absolute;inset:0;background:rgba(10,7,16,.78);display:none;align-items:center;justify-content:center;z-index:23;padding:14px}
#mapModal.open{display:flex}
.mapbox{flex:1;min-height:0;background:#0f0a18;border:2px solid var(--edge);border-radius:12px;overflow:hidden;margin:6px 0}
#mapCanvas{display:block;width:100%;height:100%;cursor:crosshair}
#slotPick{position:absolute;inset:0;display:none;align-items:center;justify-content:center;z-index:24;background:rgba(10,7,16,.55)}
#slotPick.open{display:flex}
.res .item span.warn{color:#ffd23f}
.res .item span.full{color:#ff8a7a}
/* 설정 창 정리 */
/* ⚠ 항목이 20개가 넘어 **세로로 길어지면 화면을 벗어난다.**
   넓게 잡고 2열로 깔아 높이를 줄인다. */
/* ⚠ `.invcard` 에 `max-width:360px` 이 있어서 width 만 키우면 **360 에서 잘린다.**
   max-width 도 같이 풀어야 실제로 넓어진다. */
#keyModal .invcard{width:min(820px,94vw);max-width:none}
#keyList{display:grid;grid-template-columns:1fr 1fr;gap:0 22px;align-content:start}
/* 구분선·탭·안내는 폭 전체를 쓴다 */
#keyList .setSec,#keyList .setTabs{grid-column:1/-1}
/* ⚠ 2열에서는 `+ .setRow` 구분선이 열 경계에서 어긋난다 → 각 줄에 아래선을 준다 */
#keyList .setRow{border-top:none;border-bottom:1px solid rgba(255,255,255,.05)}
#keyList .setRow+.setRow{border-top:none}
/* 좁은 화면에서는 다시 한 줄로 (2열이면 글자가 뭉개진다) */
@media(max-width:620px){
  #keyModal .invcard{width:min(420px,92vw);max-width:none}
  #keyList{grid-template-columns:1fr}
}
.setSec{font-size:11px;font-weight:900;color:var(--gold);letter-spacing:.5px;margin:14px 0 6px;
  border-bottom:1px solid var(--edge);padding-bottom:5px}
.setSec:first-child{margin-top:4px}
.setHint{font-weight:700;color:var(--muted);font-size:10px;margin-left:6px}
.setRow{display:flex;align-items:center;justify-content:space-between;gap:12px;padding:7px 2px;min-height:34px}
.setRow+.setRow{border-top:1px solid rgba(255,255,255,.05)}
.setLabel{font-size:13px;font-weight:700;color:var(--ink)}
.setFix{font-size:12px;color:var(--muted);font-weight:800}
.setBtns{display:flex;gap:6px}
.langbtn{background:var(--panel2);border:2px solid var(--edge);color:var(--ink);border-radius:8px;
  padding:5px 12px;font-family:var(--font);font-weight:800;font-size:12px;cursor:pointer}
.langbtn.on{border-color:var(--gold);background:#3a2a1a;color:var(--gold)}
.langbtn:hover{border-color:#7a6a9e}


/* ==================== 닉네임 시작 화면 ==================== */
/* 배경에 실제 게임 화면(데모)이 흐르므로 오버레이는 반투명 */
#nickGate{position:fixed;inset:0;z-index:9000;display:none;
  background:linear-gradient(180deg,rgba(8,13,19,.62),rgba(8,13,19,.86));
  backdrop-filter:blur(2px);-webkit-backdrop-filter:blur(2px);}
#nickGate.open{display:block;}
#nickGate .ng-scroll, #helpModal .ng-scroll{position:absolute;inset:0;overflow-y:auto;overflow-x:hidden;
  display:flex;align-items:flex-start;justify-content:center;padding:22px 14px 34px;
  -webkit-overflow-scrolling:touch;}
/* 왼쪽 시작 카드 · 오른쪽 안내(넓으면 2단으로 펼침) */
/* ⚠ 고정 폭(400px + 760px)이면 화면이 좁을 때 **오른쪽이 잘린다.**
   `minmax(0, ...)` 로 줄어들 수 있게 하고, 폭이 모자라면 아래 미디어쿼리가 1열로 바꾼다. */
#nickGate .ng-wrap, #helpModal .ng-wrap{display:grid;
  grid-template-columns:minmax(300px,400px) minmax(0,760px);
  gap:34px;align-items:start;justify-content:center;width:100%;max-width:1240px;}
#nickGate .ng-guide, #helpModal .ng-guide{display:grid;grid-template-columns:repeat(2,minmax(0,1fr));
  gap:26px;align-content:start;}
#nickGate .ng-wrap > *, #helpModal .ng-wrap > *{min-width:0;}
#nickGate .ng-box, #helpModal .ng-box, #nickGate .ng-sec, #helpModal .ng-sec, #nickGate .ng-ad, #helpModal .ng-ad{max-width:100%;box-sizing:border-box;}
#nickGate .ng-col, #helpModal .ng-col{display:flex;flex-direction:column;gap:26px;}
/* 광고 슬롯 — 내용이 채워지지 않으면 공간을 차지하지 않는다 */
#nickGate .ng-ad:empty, #helpModal .ng-ad:empty{display:none;}
#nickGate .ng-ad, #helpModal .ng-ad{min-height:0;border-radius:14px;overflow:hidden;
  background:rgba(255,255,255,.03);border:1px solid rgba(255,255,255,.06);}
#nickGate .ng-guide .ng-sec, #helpModal .ng-guide .ng-sec{margin-top:0;
  background:linear-gradient(180deg,rgba(26,37,50,.92),rgba(15,22,31,.94));
  border:1px solid rgba(255,255,255,.09);box-shadow:0 14px 40px rgba(0,0,0,.4);
  padding:14px 15px 12px;border-radius:14px;}
#nickGate .ng-box, #helpModal .ng-box{width:auto;box-sizing:border-box;padding:24px 22px 18px;border-radius:18px;text-align:center;
  background:linear-gradient(180deg,rgba(26,37,50,.94),rgba(15,22,31,.96));
  border:1px solid rgba(255,255,255,.10);box-shadow:0 26px 70px rgba(0,0,0,.6);}
#nickGate .ng-logo, #helpModal .ng-logo{font:800 32px/1.1 Trebuchet MS,sans-serif;color:#eaf2ff;letter-spacing:.5px;
  text-shadow:0 2px 12px rgba(0,0,0,.5);}
#nickGate .ng-logo span, #helpModal .ng-logo span{color:#7fe0ff;}
#nickGate .ng-sub, #helpModal .ng-sub{margin:8px 0 16px;font:500 13px/1.5 Trebuchet MS,sans-serif;color:#9db0c6;}
#nickGate .ng-input, #helpModal .ng-input{width:100%;box-sizing:border-box;padding:13px 14px;border-radius:11px;
  background:rgba(6,10,15,.9);border:1px solid rgba(255,255,255,.14);color:#eaf2ff;
  font:600 15px Trebuchet MS,sans-serif;text-align:center;outline:none;}
#nickGate .ng-input:focus, #helpModal .ng-input:focus{border-color:#7fe0ff;box-shadow:0 0 0 3px rgba(127,224,255,.16);}
#nickGate .ng-msg, #helpModal .ng-msg{min-height:17px;margin:7px 0 3px;font:500 12px Trebuchet MS,sans-serif;color:#9db0c6;}
#nickGate .ng-msg.bad, #helpModal .ng-msg.bad{color:#ff9a8f;}
#nickGate .ng-btn, #helpModal .ng-btn{width:100%;margin-top:4px;padding:14px 0;border:0;border-radius:11px;cursor:pointer;
  background:linear-gradient(180deg,#4aa3ff,#2b7fe0);color:#fff;font:800 16px Trebuchet MS,sans-serif;
  box-shadow:0 8px 22px rgba(42,120,220,.38);}
#nickGate .ng-btn:hover, #helpModal .ng-btn:hover{filter:brightness(1.09);}
#nickGate .ng-btn:disabled, #helpModal .ng-btn:disabled{opacity:.6;cursor:default;}
#nickGate .ng-state, #helpModal .ng-state{margin-top:11px;font:600 11px Trebuchet MS,sans-serif;}
#nickGate .ng-state.ok, #helpModal .ng-state.ok{color:#7ce0a0;}
#nickGate .ng-state.off, #helpModal .ng-state.off{color:#ffcf7f;}

/* 구분선 '또는' */
#nickGate .ng-or{display:flex;align-items:center;gap:10px;margin:12px 0 10px;
  font:700 11px Trebuchet MS,sans-serif;color:#6e7f94;}
#nickGate .ng-or::before, #nickGate .ng-or::after{content:'';flex:1;height:1px;background:rgba(255,255,255,.1);}

/* Google 버튼 */
#nickGate .ng-btn-g{display:flex;align-items:center;justify-content:center;gap:9px;margin-top:0;
  background:#fff;color:#1f2937;font:700 14px Trebuchet MS,sans-serif;
  box-shadow:0 4px 14px rgba(0,0,0,.28);}
#nickGate .ng-btn-g:hover{filter:brightness(.96);}
#nickGate .ng-btn-g svg{display:block;flex:0 0 18px;}

/* 게스트 경고 (게스트일 때만 보임) */
#nickGate .ng-guest{margin-top:12px;padding:10px 12px;border-radius:11px;text-align:left;
  background:rgba(255,190,110,.1);border:1px solid rgba(255,190,110,.3);}
#nickGate .ng-guest b{display:block;margin-bottom:4px;font:800 12px Trebuchet MS,sans-serif;color:#ffd8a0;}
#nickGate .ng-guest span{font:500 11.5px/1.6 Trebuchet MS,sans-serif;color:#d9c7ab;}
#nickGate .ng-guest span b{display:inline;margin:0;color:#ffe2b8;}

/* 인게임 계정 배지 — 좌표(150px)와 채널(202px) 사이 */
.acc-badge{position:absolute;right:10px;top:191px;z-index:7;
  display:inline-flex;align-items:center;pointer-events:auto;user-select:none;
  padding:4px 9px;border-radius:9px;white-space:nowrap;
  font-family:var(--font);font-weight:700;font-size:11px;color:#9db0c6;
  background:rgba(25,16,36,.62);border:1px solid rgba(255,255,255,.09);}
.acc-badge.guest{cursor:pointer;color:#ffd8a0;
  background:rgba(255,190,110,.14);border-color:rgba(255,190,110,.34);}
.acc-badge.guest:hover{background:rgba(255,190,110,.22);}
.acc-badge.off{color:#8a93a0;}

/* 안내 섹션 */
#nickGate .ng-sec, #helpModal .ng-sec{margin-top:16px;padding:13px 13px 11px;border-radius:12px;text-align:left;
  background:rgba(255,255,255,.035);border:1px solid rgba(255,255,255,.07);}
#nickGate .ng-sec.ng-warn, #helpModal .ng-sec.ng-warn{background:rgba(255,190,110,.07);border-color:rgba(255,190,110,.22);}
#nickGate .ng-sec-t, #helpModal .ng-sec-t{margin-bottom:8px;font:800 12px Trebuchet MS,sans-serif;color:#cfe0f5;
  letter-spacing:.3px;text-transform:none;}
#nickGate .ng-warn .ng-sec-t, #helpModal .ng-warn .ng-sec-t{color:#ffd8a0;}
#nickGate .ng-row, #helpModal .ng-row{display:flex;gap:8px;margin:5px 0;font:500 12px/1.65 Trebuchet MS,sans-serif;color:#a8b8cc;}
#nickGate .ng-row b:first-child, #helpModal .ng-row b:first-child{flex:0 0 14px;color:#7fe0ff;font-weight:800;}
#nickGate .ng-row span b, #helpModal .ng-row span b{color:#e6f0fb;font-weight:700;}
#nickGate .ng-warn .ng-row b:first-child, #helpModal .ng-warn .ng-row b:first-child{color:#ffcf7f;}

/* 조작 키 */
#nickGate .ng-keys, #helpModal .ng-keys{display:grid;grid-template-columns:1fr;gap:6px;}
#nickGate .ng-key, #helpModal .ng-key{display:flex;align-items:center;gap:6px;flex-wrap:wrap;
  font:500 12px Trebuchet MS,sans-serif;color:#a8b8cc;}
#nickGate .ng-key kbd, #helpModal .ng-key kbd{display:inline-block;min-width:20px;padding:3px 7px;border-radius:6px;text-align:center;
  background:rgba(255,255,255,.09);border:1px solid rgba(255,255,255,.16);border-bottom-width:2px;
  color:#e6f0fb;font:700 11px Trebuchet MS,sans-serif;}
#nickGate .ng-key span, #helpModal .ng-key span{margin-left:4px;color:#93a5ba;}
#nickGate .ng-tip, #helpModal .ng-tip{margin-top:8px;font:500 11px/1.6 Trebuchet MS,sans-serif;color:#8496aa;}
#nickGate .ng-note, #helpModal .ng-note{margin-top:14px;padding-top:12px;border-top:1px solid rgba(255,255,255,.08);
  font:500 11px/1.6 Trebuchet MS,sans-serif;color:#7c8b9e;}

/* 데모 배경 중에는 캔버스만 남기고 UI를 모두 숨긴다 */
body.demo-bg #stage > *:not(canvas){ display:none !important; }

/* 화면이 좁아지면 단계적으로 접힌다 */
/* ⚠ `#helpModal` 도 같은 구조다 — 여기 빠지면 **도움말 창만 안 접혀 잘린다.** */
@media (max-width:1240px){
  #nickGate .ng-guide, #helpModal .ng-guide{grid-template-columns:1fr;gap:22px;}
  #nickGate .ng-wrap, #helpModal .ng-wrap{
    grid-template-columns:minmax(280px,400px) minmax(0,430px);gap:28px;}
}
@media (max-width:840px){
  #nickGate .ng-wrap, #helpModal .ng-wrap{grid-template-columns:min(94vw,430px);gap:20px;}
  #nickGate .ng-col, #helpModal .ng-col{gap:20px;}
}
@media (max-width:420px){
  #nickGate .ng-box{padding:20px 16px 16px;}
  #nickGate .ng-logo{font-size:27px;}
}

/* ==================== 인게임 도움말 ==================== */
#helpModal{position:fixed;inset:0;z-index:8500;display:none;align-items:center;justify-content:center;
  background:rgba(6,10,15,.72);backdrop-filter:blur(2px);-webkit-backdrop-filter:blur(2px);padding:18px;}
#helpModal.open{display:flex;}
#helpModal .hm-box{width:min(96vw,780px);max-height:88vh;display:flex;flex-direction:column;
  border-radius:16px;overflow:hidden;
  background:linear-gradient(180deg,rgba(26,37,50,.98),rgba(15,22,31,.99));
  border:1px solid rgba(255,255,255,.11);box-shadow:0 26px 70px rgba(0,0,0,.6);}
#helpModal .hm-head{display:flex;align-items:center;justify-content:space-between;
  padding:14px 16px;border-bottom:1px solid rgba(255,255,255,.08);}
#helpModal .hm-title{font:800 16px Trebuchet MS,sans-serif;color:#eaf2ff;}
#helpModal .hm-x{width:30px;height:30px;border:0;border-radius:8px;cursor:pointer;
  background:rgba(255,255,255,.08);color:#cfe0f5;font:700 18px/1 Trebuchet MS,sans-serif;}
#helpModal .hm-x:hover{background:rgba(255,255,255,.15);}
#helpModal .hm-body{padding:14px 16px;overflow-y:auto;
  display:grid;grid-template-columns:1fr 1fr;gap:12px;align-content:start;}
#helpModal .hm-body .ng-sec{margin-top:0;
  background:rgba(255,255,255,.035);border:1px solid rgba(255,255,255,.07);
  padding:13px 14px 11px;border-radius:12px;}
#helpModal .hm-body .ng-sec.ng-warn{background:rgba(255,190,110,.07);border-color:rgba(255,190,110,.22);}
#helpModal .hm-foot{display:flex;align-items:center;justify-content:space-between;gap:10px;
  padding:12px 16px;border-top:1px solid rgba(255,255,255,.08);}
#helpModal .hm-foot span{font:600 11px Trebuchet MS,sans-serif;color:#8496aa;}
#helpModal .hm-btns{display:flex;gap:8px;align-items:center;}
#helpModal .hm-ok{padding:9px 20px;border:0;border-radius:9px;cursor:pointer;
  background:linear-gradient(180deg,#4aa3ff,#2b7fe0);color:#fff;font:800 13px Trebuchet MS,sans-serif;}
#helpModal .hm-ok:hover{filter:brightness(1.08);}
#helpModal .hm-reset{padding:9px 14px;border:1px solid rgba(255,120,110,.35);border-radius:9px;cursor:pointer;
  background:rgba(255,90,80,.10);color:#ff9a8f;font:700 12px Trebuchet MS,sans-serif;}
#helpModal .hm-reset:hover{background:rgba(255,90,80,.20);}
#helpModal .hm-reset:disabled{opacity:.6;cursor:default;}
@media (max-width:700px){
  #helpModal .hm-body{grid-template-columns:1fr;}
}

/* ==================== 채팅 ==================== */
#chatBox{position:fixed;right:12px;left:auto;bottom:12px;z-index:600;width:min(92vw,340px);
  display:flex;flex-direction:column;border-radius:12px;overflow:hidden;
  background:linear-gradient(180deg,rgba(18,26,36,.82),rgba(12,18,26,.90));
  border:1px solid rgba(255,255,255,.09);box-shadow:0 10px 30px rgba(0,0,0,.45);
  font-family:Trebuchet MS,sans-serif;}
#chatBox .ch-head{display:flex;align-items:center;justify-content:space-between;gap:6px;
  padding:6px 8px;border-bottom:1px solid rgba(255,255,255,.07);}
#chatBox .ch-tabs{display:flex;gap:4px;}
#chatBox .ch-tab{padding:4px 10px;border:0;border-radius:7px;cursor:pointer;
  background:rgba(255,255,255,.06);color:#93a5ba;font:700 11px Trebuchet MS,sans-serif;}
#chatBox .ch-tab.on{background:rgba(74,163,255,.22);color:#cfe6ff;}
#chatBox .ch-tab:hover{background:rgba(255,255,255,.12);}
#chatBox .ch-fold{min-width:26px;height:22px;padding:0 6px;border:0;border-radius:7px;cursor:pointer;
  background:rgba(255,255,255,.06);color:#cfe0f5;font:700 11px Trebuchet MS,sans-serif;}
#chatBox .ch-log{height:168px;overflow-y:auto;padding:7px 9px;display:flex;flex-direction:column;gap:3px;}
#chatBox .ch-msg{font:500 12px/1.45 Trebuchet MS,sans-serif;color:#c4d3e4;word-break:break-word;}
#chatBox .ch-msg .ch-t{color:#5f7086;font-size:10px;margin-right:5px;}
#chatBox .ch-msg .ch-n{color:#7fe0ff;font-weight:700;margin-right:5px;}
#chatBox .ch-msg.mine .ch-n{color:#ffd77f;}
#chatBox .ch-msg.sys{color:#ffcf7f;font-style:italic;font-size:11px;}
#chatBox .ch-input{display:flex;gap:6px;padding:7px 8px;border-top:1px solid rgba(255,255,255,.07);}
#chatBox .ch-input input{flex:1;min-width:0;padding:8px 10px;border-radius:8px;
  background:rgba(6,10,15,.8);border:1px solid rgba(255,255,255,.12);color:#eaf2ff;
  font:500 12px Trebuchet MS,sans-serif;outline:none;}
#chatBox .ch-input input:focus{border-color:#4aa3ff;}
#chatBox .ch-input button{padding:8px 12px;border:0;border-radius:8px;cursor:pointer;
  background:linear-gradient(180deg,#4aa3ff,#2b7fe0);color:#fff;font:700 12px Trebuchet MS,sans-serif;}
#chatBox .ch-locked{padding:11px 12px;text-align:center;border-top:1px solid rgba(255,255,255,.07);}
#chatBox .ch-locked-t{font:600 11px Trebuchet MS,sans-serif;color:#ffcf7f;margin-bottom:7px;}
#chatBox .ch-locked button{width:100%;padding:9px 0;border:0;border-radius:8px;cursor:pointer;
  background:linear-gradient(180deg,#f5f7fa,#dfe6ee);color:#2b3a4a;font:800 12px Trebuchet MS,sans-serif;}
#chatBox .ch-locked button:hover{filter:brightness(1.05);}
#chatBox .ch-locked button:disabled{opacity:.6;cursor:default;}
#chatBox .ch-locked-s{margin-top:6px;font:500 10px Trebuchet MS,sans-serif;color:#7c8b9e;}
#chatBox.folded .ch-log, #chatBox.folded .ch-input, #chatBox.folded .ch-locked{display:none !important;}
/* 데모 배경 중에는 숨김 */
body.demo-bg #chatBox{display:none;}
@media (max-width:520px){
  #chatBox{width:calc(100vw - 24px);}
  #chatBox .ch-log{height:132px;}
}

/* ==================== 채널 표시 (미니맵 아래 좌표 바로 밑) ==================== */
.room-tag{position:absolute;right:10px;top:217px;z-index:7;pointer-events:auto;user-select:none;
  display:flex;align-items:center;gap:6px;padding:3px 5px 3px 9px;border-radius:7px;
  background:rgba(25,16,36,.55);border:1px solid rgba(255,255,255,.09);
  color:#9fd8ff;font-family:var(--font);font-weight:700;font-size:11px;}
.room-tag.full{color:#ffcf7f;}
.room-tag .room-sw{width:20px;height:18px;padding:0;border:0;border-radius:5px;cursor:pointer;
  background:rgba(255,255,255,.10);color:#cfe0f5;font-size:11px;line-height:1;}
.room-tag .room-sw:hover{background:rgba(255,255,255,.22);}
/* 채널 선택 팝업 */
.room-pick{position:absolute;right:10px;top:243px;z-index:9;display:none;width:184px;
  border-radius:10px;overflow:hidden;background:rgba(16,22,32,.96);
  border:1px solid rgba(255,255,255,.12);box-shadow:0 12px 32px rgba(0,0,0,.5);
  font-family:var(--font);pointer-events:auto;}
.room-pick.open{display:block;}
.room-pick .rp-t{padding:7px 10px;font-size:11px;font-weight:800;color:#cfe0f5;
  border-bottom:1px solid rgba(255,255,255,.08);}
.room-pick .rp-list{max-height:200px;overflow-y:auto;padding:5px;}
.room-pick .rp-item{width:100%;display:flex;justify-content:space-between;align-items:center;
  padding:6px 8px;margin-bottom:3px;border:0;border-radius:7px;cursor:pointer;
  background:rgba(255,255,255,.05);color:#c4d3e4;font:600 11px var(--font);}
.room-pick .rp-item:hover{background:rgba(255,255,255,.13);}
.room-pick .rp-item.on{background:rgba(74,163,255,.24);color:#cfe6ff;}
.room-pick .rp-item.full{opacity:.45;cursor:default;}
.room-pick .rp-c{color:#8fa0b4;font-size:10px;}
.room-pick .rp-n{padding:6px 10px;border-top:1px solid rgba(255,255,255,.08);
  font-size:10px;line-height:1.5;color:#7c8b9e;}

/* ==================== 단축키 패널 ==================== */
.keyhud{width:100%;border-radius:10px;overflow:hidden;
  background:rgba(12,18,26,.60);border:1px solid rgba(255,255,255,.08);
  font-family:Trebuchet MS,sans-serif;pointer-events:auto;user-select:none;}
.keyhud .kh-head{display:flex;align-items:center;justify-content:space-between;
  padding:5px 8px;cursor:pointer;background:rgba(255,255,255,.04);}
.keyhud .kh-head:hover{background:rgba(255,255,255,.09);}
.keyhud .kh-title{font:700 10px Trebuchet MS,sans-serif;color:#9db0c6;letter-spacing:.4px;}
.keyhud .kh-fold{font:700 10px Trebuchet MS,sans-serif;color:#7c8b9e;}
.keyhud .kh-body{padding:6px 8px;display:flex;flex-direction:column;gap:3px;}
.keyhud.folded .kh-body{display:none;}
.keyhud .kh-row{display:flex;align-items:center;gap:6px;font:500 10px Trebuchet MS,sans-serif;color:#93a5ba;}
.keyhud .kh-row kbd{min-width:30px;padding:2px 5px;border-radius:5px;text-align:center;
  background:rgba(255,255,255,.09);border:1px solid rgba(255,255,255,.14);border-bottom-width:2px;
  color:#dceaf8;font:700 9px Trebuchet MS,sans-serif;}
body.demo-bg .lefthud, body.demo-bg .room-tag, body.demo-bg .acc-badge{display:none;}
@media (max-width:520px){ .lefthud{width:132px;} }

/* 습격·보스 카운트다운 */
.raid-count{position:fixed;left:50%;top:34%;transform:translate(-50%,-50%);z-index:400;
  font:900 92px/1 Trebuchet MS,sans-serif;color:#ff9a8f;pointer-events:none;
  text-shadow:0 0 24px rgba(255,90,80,.55),0 4px 14px rgba(0,0,0,.7);opacity:0;}
.raid-count.boss{color:#ffd77f;text-shadow:0 0 26px rgba(255,200,90,.6),0 4px 14px rgba(0,0,0,.7);}
.raid-count.pop{animation:raidPop .9s ease-out forwards;}
@keyframes raidPop{
  0%{opacity:0;transform:translate(-50%,-50%) scale(1.5);}
  18%{opacity:1;transform:translate(-50%,-50%) scale(1);}
  70%{opacity:1;}
  100%{opacity:0;transform:translate(-50%,-50%) scale(.92);}
}
body.demo-bg .raid-count{display:none;}

/* ==================== 서버 접속 관문 ==================== */
.net-gate{position:fixed;inset:0;z-index:9500;display:none;
  background:radial-gradient(120% 90% at 50% 0%,#1a2436 0%,#0c1018 70%);}
.net-gate.open{display:flex;align-items:center;justify-content:center;}
.net-gate .net-box{width:min(360px,86vw);padding:28px 24px 20px;border-radius:18px;text-align:center;
  background:rgba(18,24,36,.9);border:1px solid rgba(255,255,255,.09);
  box-shadow:0 18px 50px rgba(0,0,0,.55);}
.net-gate .net-logo{font:800 28px/1.1 Trebuchet MS,sans-serif;color:#eaf2ff;letter-spacing:.5px;}
.net-gate .net-logo span{color:#7fe0ff;}
.net-gate .net-spin{width:26px;height:26px;margin:18px auto 14px;border-radius:50%;
  border:3px solid rgba(127,224,255,.22);border-top-color:#7fe0ff;animation:netspin .8s linear infinite;}
@keyframes netspin{to{transform:rotate(360deg)}}
.net-gate .net-msg{margin-top:14px;font:700 14px/1.6 Trebuchet MS,sans-serif;color:#e6f0fb;}
.net-gate .net-code{margin-top:6px;min-height:15px;font:600 11px Trebuchet MS,sans-serif;color:#ff9a8f;}
.net-gate .net-retry{margin-top:14px;padding:11px 22px;border:0;border-radius:10px;cursor:pointer;
  background:linear-gradient(180deg,#4aa3ff,#2b7fe0);color:#fff;font:800 14px Trebuchet MS,sans-serif;
  box-shadow:0 8px 22px rgba(42,120,220,.35);}
.net-gate .net-retry:hover{filter:brightness(1.09);}
.net-gate .net-note{margin-top:16px;font:500 11px/1.7 Trebuchet MS,sans-serif;color:#8595a8;}


/* ==================== 좌측 세로 스택 (단축키 → 접속자) ==================== */
/* 절대배치는 컨테이너에만 준다. 안쪽은 일반 흐름이라 단축키를 접으면 명단이 따라 올라온다. */
.lefthud{position:absolute;left:10px;top:138px;z-index:6;width:146px;
  display:flex;flex-direction:column;gap:6px;pointer-events:none;}
.lefthud > *{pointer-events:auto;}

/* 접속자 명단 */
.plist{width:100%;border-radius:10px;overflow:hidden;
  background:rgba(12,18,26,.60);border:1px solid rgba(255,255,255,.08);
  font-family:Trebuchet MS,sans-serif;user-select:none;}
.plist .pl-head{display:flex;align-items:center;justify-content:space-between;
  padding:5px 8px;cursor:pointer;background:rgba(255,255,255,.04);}
.plist .pl-head:hover{background:rgba(255,255,255,.09);}
.plist .pl-title{font:700 10px Trebuchet MS,sans-serif;color:#9db0c6;letter-spacing:.4px;}
.plist .pl-n{color:#7fe0ff;font-weight:800;}
.plist .pl-fold{font:700 10px Trebuchet MS,sans-serif;color:#7c8b9e;}
.plist .pl-body{padding:5px 6px;display:flex;flex-direction:column;gap:2px;
  max-height:168px;overflow-y:auto;}
.plist.folded .pl-body{display:none;}
.plist .pl-row{display:flex;align-items:center;gap:6px;padding:2px 3px;border-radius:5px;
  font:500 10px Trebuchet MS,sans-serif;color:#93a5ba;}
.plist .pl-row.me{background:rgba(127,224,255,.10);color:#cfe6f5;}
.plist .pl-dot{flex:0 0 8px;width:8px;height:8px;border-radius:50%;
  box-shadow:0 0 0 1px rgba(0,0,0,.45);}
.plist .pl-nick{flex:1;min-width:0;overflow:hidden;text-overflow:ellipsis;white-space:nowrap;}
.plist .pl-me{flex:0 0 auto;font-size:9px;font-weight:800;color:#7fe0ff;}
.plist .pl-empty{padding:4px 3px;font:500 10px Trebuchet MS,sans-serif;color:#6e7f94;}

/* ==================== 캐릭터 색 고르기 ==================== */
.sk-dot{width:22px;height:22px;padding:0;border-radius:50%;cursor:pointer;
  border:2px solid rgba(255,255,255,.18);box-shadow:0 2px 6px rgba(0,0,0,.35);}
.sk-dot:hover{transform:scale(1.12);}
.sk-dot.on{border-color:#fff;box-shadow:0 0 0 2px rgba(127,224,255,.7),0 2px 8px rgba(0,0,0,.45);}

#nickGate .ng-skin{margin-top:12px;}
#nickGate .ng-skin-t{margin-bottom:7px;font:800 11px Trebuchet MS,sans-serif;color:#9db0c6;
  letter-spacing:.3px;text-align:left;}
#nickGate .ng-skin-row{display:flex;flex-wrap:wrap;gap:7px;justify-content:center;}

/* 인게임 팝업 (HUD 아바타 클릭) */
.skin-pop{position:absolute;left:10px;top:96px;z-index:30;display:none;width:184px;
  padding:9px 10px;border-radius:11px;
  background:rgba(16,22,32,.96);border:1px solid rgba(255,255,255,.12);
  box-shadow:0 12px 32px rgba(0,0,0,.5);font-family:Trebuchet MS,sans-serif;pointer-events:auto;}
.skin-pop.open{display:block;}
.skin-pop .sp-t{margin-bottom:8px;font:800 10px Trebuchet MS,sans-serif;color:#cfe0f5;letter-spacing:.3px;}
.skin-pop .sp-row{display:flex;flex-wrap:wrap;gap:7px;}

/* 설정 창의 슬라이더 (장식물 진하기) */
#keyList input[type=range]{width:120px;height:4px;cursor:pointer;accent-color:#7fe0ff;
  vertical-align:middle;}
#keyList .setBtns{display:flex;align-items:center;gap:9px;}

/* 채널 선택 — 새 채널 / 빈 목록 */
.room-pick .rp-new{color:#7fe0ff;}
.room-pick .rp-new .rp-no{font-weight:800;}
.room-pick .rp-empty{padding:10px;text-align:center;
  font:500 11px Trebuchet MS,sans-serif;color:#6e7f94;}

/* ==================== 파티 ==================== */
/* 접속자 명단 안의 파티 표시·버튼 */
.plist .pl-row.party{background:rgba(120,200,255,.10);color:#cfe6f5;}
.plist .pl-p{flex:0 0 auto;font-size:9px;font-weight:800;color:#7fe0ff;}
.plist .pl-btn{flex:0 0 auto;width:15px;height:15px;padding:0;border-radius:4px;cursor:pointer;
  border:1px solid rgba(255,255,255,.16);background:rgba(255,255,255,.06);
  font:800 10px/1 Trebuchet MS,sans-serif;color:#9db0c6;}
.plist .pl-btn:hover{background:rgba(255,255,255,.16);color:#fff;}
.plist .pl-btn.kick:hover{background:rgba(255,110,95,.28);border-color:rgba(255,110,95,.5);color:#ffd8d2;}

/* 파티 — 좌측 스택(단축키 → 접속자 → 파티)의 마지막 칸 */
.party-hud{width:100%;border-radius:10px;overflow:hidden;display:none;
  background:rgba(12,18,26,.60);border:1px solid rgba(255,255,255,.08);
  font-family:Trebuchet MS,sans-serif;user-select:none;}
.party-hud.open{display:block;}
.party-hud .ph-head{display:flex;align-items:center;justify-content:space-between;
  padding:5px 8px;cursor:pointer;background:rgba(255,255,255,.04);}
.party-hud .ph-head:hover{background:rgba(255,255,255,.09);}
.party-hud .ph-title{font:700 10px Trebuchet MS,sans-serif;color:#9db0c6;letter-spacing:.4px;}
.party-hud .ph-n{color:#7fe0ff;font-weight:800;}
.party-hud .ph-fold{font:700 10px Trebuchet MS,sans-serif;color:#7c8b9e;}
.party-hud .ph-body{padding:5px 6px;display:flex;flex-direction:column;gap:3px;}
.party-hud.folded .ph-body{display:none;}
.party-hud .ph-xp{font:700 9px Trebuchet MS,sans-serif;color:#7fe0ff;padding:0 3px 2px;}
.party-hud .pt-row{display:flex;align-items:center;gap:5px;padding:2px 3px;border-radius:5px;
  font:500 10px Trebuchet MS,sans-serif;color:#93a5ba;}
.party-hud .pt-row.me{background:rgba(127,224,255,.10);color:#cfe6f5;}
.party-hud .pt-nick{flex:1;min-width:0;overflow:hidden;text-overflow:ellipsis;white-space:nowrap;}
.party-hud .pt-kick{flex:0 0 auto;width:15px;height:15px;padding:0;border-radius:4px;cursor:pointer;
  border:1px solid rgba(255,255,255,.16);background:rgba(255,255,255,.06);
  font:800 10px/1 Trebuchet MS,sans-serif;color:#9db0c6;}
.party-hud .pt-kick:hover{background:rgba(255,110,95,.28);border-color:rgba(255,110,95,.5);color:#ffd8d2;}
.party-hud .pt-out{margin-top:3px;padding:4px 6px;border:0;border-radius:6px;cursor:pointer;
  font:700 10px Trebuchet MS,sans-serif;background:rgba(255,255,255,.10);color:#c8d4e2;}
.party-hud .pt-out:hover{background:rgba(255,255,255,.2);}

/* 초대 — 놓치면 안 되므로 눈에 띄게 */
.party-hud.invite{border-color:rgba(127,224,255,.55);background:rgba(18,30,44,.94);
  box-shadow:0 0 0 1px rgba(127,224,255,.22);}
.party-hud.invite .ph-head{cursor:default;background:rgba(127,224,255,.12);}
.party-hud.invite .ph-title{color:#cfe6f5;}
.party-hud .ph-from{font:800 11px Trebuchet MS,sans-serif;color:#eaf2ff;padding:1px 3px 4px;}
.party-hud .ph-btns{display:flex;gap:5px;}
.party-hud .ph-btns button{flex:1;padding:5px 6px;border:0;border-radius:6px;cursor:pointer;
  font:800 10px Trebuchet MS,sans-serif;background:rgba(255,255,255,.12);color:#dfe8f5;}
.party-hud .ph-btns button:hover{background:rgba(255,255,255,.22);}
.party-hud #phYes{background:linear-gradient(180deg,#4aa3ff,#2b7fe0);color:#fff;}

/* ==================== 도움 요청 ==================== */
.help-panel{position:absolute;left:10px;bottom:150px;z-index:8;display:none;
  min-width:150px;max-width:190px;padding:8px 9px;border-radius:11px;pointer-events:auto;
  background:rgba(16,22,32,.94);border:1px solid rgba(255,255,255,.12);
  box-shadow:0 10px 26px rgba(0,0,0,.45);font-family:Trebuchet MS,sans-serif;}
.help-panel.open{display:flex;flex-direction:column;gap:5px;}
.help-panel .hp-t{margin-top:2px;font:800 10px Trebuchet MS,sans-serif;color:#ffcf7f;letter-spacing:.3px;}
.help-panel button{width:100%;padding:6px 8px;border:0;border-radius:8px;cursor:pointer;
  font:800 11px Trebuchet MS,sans-serif;text-align:left;
  background:rgba(255,255,255,.12);color:#dfe8f5;}
.help-panel button:hover{background:rgba(255,255,255,.22);}
.help-panel .hp-call{background:linear-gradient(180deg,#ff8a5c,#e05a2b);color:#fff;text-align:center;}
.help-panel .hp-call.on{background:rgba(255,255,255,.14);color:#ffcf7f;}
.help-panel .hp-go{background:rgba(127,224,255,.16);color:#cfe6f5;}
.help-panel .hp-go:hover{background:rgba(127,224,255,.3);}

/* 거래소 우편함 배지 — 안 받은 우편이 있으면 개수를 보여준다 */
.mk-badge{display:inline-block;min-width:15px;padding:0 4px;margin-left:3px;border-radius:8px;
  background:#e05b5b;color:#fff;font-size:10px;line-height:15px;text-align:center;font-weight:700}
.mail-row{display:flex;gap:9px;align-items:center;padding:8px 9px;margin:5px 0;border-radius:9px;
  background:rgba(255,255,255,.045);border:1px solid rgba(255,255,255,.08)}
.mail-row .ml-ic{font-size:17px;width:22px;text-align:center}
.mail-row .ml-txt{flex:1;min-width:0}
.mail-row .ml-t{font-size:12.5px;color:#e9e4f5}
.mail-row .ml-s{font-size:10.5px;color:#8b8299;margin-top:1px}
.mail-row .ml-btn{padding:5px 11px;border-radius:8px;border:0;cursor:pointer;
  background:linear-gradient(180deg,#6d8fd6,#4f6db0);color:#fff;font-size:11.5px;font-weight:700}

/* 거래 가능 표시 — 슬롯에서 바로 보이게 (예전엔 눌러봐야 알 수 있었다) */
.cell{position:relative}
.cell .tr, .eslot .box .tr{position:absolute;left:2px;top:1px;font-size:9px;line-height:1;
  text-shadow:0 1px 2px rgba(0,0,0,.8);pointer-events:none}
.eslot .box{position:relative}

/* 약탈 안내 — F 안내 바로 위 (겹치지 않게) */
/* bottom 은 uxHudTick 이 건설바 높이에 맞춰 직접 정한다 */
.lootprompt{border-color:#c0554a}
.lootprompt .ip-key{background:#e05b5b;color:#fff}
/* 게임 내 확인창 (시스템 confirm 대신) */
#askModal{position:absolute;inset:0;background:rgba(10,7,16,.72);display:none;
  align-items:center;justify-content:center;z-index:24;padding:14px}
#askModal.open{display:flex}
#askModal .invcard{max-width:340px}

/* 보스 목록 (B) */
#bossModal{position:absolute;inset:0;background:rgba(10,7,16,.72);display:none;
  align-items:center;justify-content:center;z-index:23;padding:14px}
#bossModal.open{display:flex}
#bossModal .invcard{max-width:420px;width:100%}
.bl-sec{font-size:11px;font-weight:800;color:var(--muted);margin:8px 2px 4px;letter-spacing:.5px}
.bl-sec.high{color:#ff9a3c}
.bl-sec span{font-weight:600;opacity:.75}
.bl-row{background:rgba(255,255,255,.045);border:1px solid rgba(255,255,255,.08);
  border-radius:9px;padding:7px 9px;margin:4px 0}
.bl-l{display:flex;align-items:center;gap:6px;font-size:13px;color:#e9e4f5}
.bl-dot{width:9px;height:9px;border-radius:50%;flex:none}
.bl-lv{font-size:10.5px;margin-left:auto;font-weight:700}
.bl-m{font-size:10.5px;color:#8b8299;margin-top:2px}
.bl-d{margin-top:5px;display:flex;flex-wrap:wrap;gap:4px}
.bl-mat{font-size:10.5px;background:rgba(255,255,255,.07);border-radius:5px;padding:1px 6px;color:#cfd8ff}
.bl-mat.key{background:rgba(255,154,60,.18);color:#ffd0a0;font-weight:700}
.bl-note{font-size:10.5px;color:var(--muted);margin-top:8px;text-align:center}

/* 보스 목록 버튼 — 미니맵 아래, 좌표 표시 위 */
/* ⚠ 미니맵(우상단)·좌표·계정배지·채널을 모두 피해야 한다.
   → **미니맵 왼쪽** 빈 자리에 둔다 (오른쪽 여백 = 미니맵 폭 + 여유). */
.bosstag{position:absolute;right:250px;top:14px;z-index:7;pointer-events:auto;
  background:rgba(25,16,36,.86);border:2px solid var(--edge);border-radius:9px;
  padding:3px 9px;font-family:var(--font);font-weight:800;font-size:11px;
  color:var(--ink);cursor:pointer;white-space:nowrap}
.bosstag:hover{border-color:var(--gold)}

/* 아이템 스킬 표시 */
.sk-v{background:rgba(255,154,60,.2);color:#ffc98a;border-radius:4px;
  padding:0 4px;font-size:10px;font-weight:900;margin-left:3px}
.sk-how{color:var(--muted);font-size:10px;margin-top:1px}

/* 스킬 주사위 */
#diceModal{position:absolute;inset:0;background:rgba(10,7,16,.72);display:none;
  align-items:center;justify-content:center;z-index:24;padding:14px}
#diceModal.open{display:flex}
#diceModal .invcard{max-width:340px;width:100%}
.dice-row{background:rgba(255,255,255,.05);border:1px solid rgba(255,255,255,.09);
  border-radius:9px;padding:8px 10px;margin:5px 0;cursor:pointer}
.dice-row:hover{border-color:var(--gold);background:rgba(255,210,63,.09)}
.dice-n{font-size:13px;font-weight:800;color:#e9e4f5}
.dice-t{font-size:11px;color:#cfd8ff;margin-top:2px}

/* 가방 사용량 */
.bag-cap{font-size:11px;color:var(--muted);text-align:right;margin:2px 2px 0}
.bag-cap.full{color:#ff8a6b;font-weight:800}

/* 개발 메뉴 (어드민 전용) */
.dbgtag{top:46px;border-color:#5a7f5a}
#dbgModal{position:absolute;inset:0;background:rgba(10,7,16,.72);display:none;
  align-items:center;justify-content:center;z-index:25;padding:14px}
#dbgModal.open{display:flex}
/* 개발 메뉴도 항목이 많아 좁으면 답답하다 */
#dbgModal .invcard{max-width:560px;width:100%}
.dbg-sec{font-size:11px;font-weight:800;color:var(--muted);margin:9px 2px 4px}
.dbg-row{display:flex;gap:6px;align-items:center;margin:4px 0}
.dbg-in{flex:1;background:var(--panel2);border:2px solid var(--edge);border-radius:8px;
  color:var(--ink);padding:5px 8px;font-family:var(--font);font-size:12px;min-width:0}
.dbg-in.n{flex:0 0 66px}
.dbg-chk{font-size:11px;color:var(--muted);display:flex;align-items:center;gap:4px;white-space:nowrap}
.dbg-quick{display:flex;flex-wrap:wrap;gap:4px;max-height:130px;overflow-y:auto}
.dbg-q{background:var(--panel2);border:1px solid var(--edge);border-radius:6px;
  color:var(--ink);padding:3px 7px;font-size:11px;cursor:pointer}
.dbg-q:hover{border-color:var(--gold)}

/* 거래소 여러 개 고르기 */
.mkmulti{cursor:pointer;white-space:nowrap;flex:0 0 auto}
.mkmulti.on{border-color:var(--gold);color:var(--gold)}
.tile.picked{border-color:var(--gold);background:rgba(255,210,63,.12)}
.tile{position:relative}
.tpick{position:absolute;left:4px;top:3px;font-size:11px;font-weight:900;color:var(--gold)}

/* 거래소 다중 선택 안내 */
.mk-tip{font-size:11px;color:var(--muted);background:rgba(255,255,255,.04);
  border:1px solid rgba(255,255,255,.08);border-radius:7px;padding:4px 9px;margin:4px 0 2px}
.mk-tip b{color:var(--gold)}

/* 우편함은 격자가 아니라 목록 (칸에 갇히면 글자가 세로로 눌린다) */
.tiles.as-list{display:block}
.tiles.as-list .bigbtn{width:100%;margin-top:8px}

/* 개수 지정 */
.qbtn{background:var(--panel2);border:2px solid var(--edge);border-radius:8px;
  color:var(--ink);padding:4px 9px;font-family:var(--font);font-size:11px;
  font-weight:800;cursor:pointer;white-space:nowrap}
.qbtn:hover{border-color:var(--gold)}

/* 변경 주사위 — 고르는 게 아니라 보여주기만 */
.dice-row.plain{cursor:default}
.dice-row.plain:hover{border-color:rgba(255,255,255,.09);background:rgba(255,255,255,.05)}

/* 주사위 남은 장수 */
.dl{opacity:.7;font-weight:800;font-size:11px}

/* 장비칸의 슬롯 강화·증폭 표시 */
.eslot .slotb{position:absolute;left:3px;bottom:2px;font-size:9px;font-weight:900;
  color:#ffc98a;background:rgba(255,154,60,.18);border-radius:5px;padding:0 4px;line-height:14px}
.eslot .slotb.max{color:#ffe9a8;background:rgba(255,210,63,.24)}
.eslot .slotb i{font-style:normal;opacity:.85;margin-left:1px}

/* 퀵슬롯 번호 지정 */
#qpModal{position:absolute;inset:0;background:rgba(10,7,16,.72);display:none;
  align-items:center;justify-content:center;z-index:26;padding:14px}
#qpModal.open{display:flex}
#qpModal .invcard{max-width:320px;width:100%}
.qp-row{display:flex;align-items:center;gap:9px;background:rgba(255,255,255,.05);
  border:1px solid rgba(255,255,255,.09);border-radius:9px;padding:7px 10px;margin:5px 0;cursor:pointer}
.qp-row:hover{border-color:var(--gold);background:rgba(255,210,63,.09)}
.qp-n{background:var(--panel2);border-radius:6px;padding:1px 8px;font-size:12px;color:var(--gold)}
.qp-t{font-size:12px;color:#cfd8ff}

/* 바꿀 수 없는 조작 안내 */
.setRow.fixed .setFix{color:var(--muted);font-weight:800;font-size:12px}

/* 설정 창 탭 */
.setTabs{margin:0 0 6px}
.setTabs .tab{flex:1}

/* 능력치 설명이 길어져 줄바꿈 허용 */
.statcell .sname small{display:block;opacity:.65;font-size:10px;margin-top:1px;white-space:nowrap}

/* 로그인 화면 언어 선택 */
.ng-lang{display:flex;gap:6px;justify-content:center;margin-bottom:10px}
.ng-langbtn{background:rgba(255,255,255,.06);border:1px solid rgba(255,255,255,.14);
  border-radius:999px;color:#cfd8ff;padding:3px 12px;font-family:var(--font);
  font-size:11px;font-weight:800;cursor:pointer}
.ng-langbtn:hover{border-color:var(--gold)}
.ng-langbtn.on{background:var(--gold);border-color:var(--gold);color:#3a2a00}

/* ==================== 영어 표기 대응 ==================== */
/* ⚠ 영어는 한글보다 **글자 수가 늘어난다** → 고정 크기 버튼·배지가 터진다.
   넘치면 줄이거나 줄바꿈하도록 공통 규칙을 둔다. */
.btn,.bigbtn,.tab,.keybtn,.langbtn,.splus,.rc-make,.slotb,.xbtn{
  min-width:0;                       /* 내용이 밀어내지 못하게 */
  overflow-wrap:anywhere;            /* 긴 단어도 잘라 넣는다 */
}
/* 한 줄로 보여야 하는 작은 배지는 줄이는 쪽으로 */
.qslot .num,.qslot .q,.setFix,.ng-langbtn{
  white-space:nowrap; overflow:hidden; text-overflow:ellipsis;
}
/* 안내 줄·설명은 줄바꿈을 허용한다 (잘리는 것보다 낫다) */
.setRow,.ng-sec li,.hm-row,.il-card{ overflow-wrap:anywhere; }
.setRow .setLabel{ min-width:0; }
/* 하단 조작 안내는 화면을 넘으면 접는다 */
#hintLine,.hintline{ max-width:96vw; overflow-wrap:anywhere; }

/* ==================== 모바일 전용 버튼 ==================== */
/* ⚠ 터치 기기에서만 보인다 (PC 는 우클릭·F11 이 있다) */
/* ⚠ `absolute` 로 두면 부모(#stage) 기준이라 **화면 밖으로 밀려난다** → `fixed`.
   ⚠ 채팅창(z-index 600)보다 위에 있어야 가려지지 않는다.
   ⚠ 오른쪽 아래는 채팅이 쓰므로 **왼쪽 아래**에 둔다. */
/* ⚠ 이 버튼은 `.float-ui`(pointer-events:none) 안에 있다 →
   **auto 를 주지 않으면 클릭이 그대로 통과해** 눌리지 않는다. */
.mobtn{pointer-events:auto;position:fixed;left:12px;display:none;width:54px;height:54px;border-radius:50%;
  background:rgba(20,14,30,.9);border:2px solid var(--edge);color:#e8e2f5;
  font-size:24px;line-height:1;cursor:pointer;z-index:700;
  align-items:center;justify-content:center;padding:0;
  -webkit-tap-highlight-color:transparent;touch-action:manipulation}
/* ⚠ 여기에도 `hover:none` 이 **또** 있었다 — S펜 기기에선 매칭이 안 돼
   달리기·전체화면 버튼이 아예 안 그려졌다 (안드로이드 크롬 증상).
   → 모바일 판정은 12e-ux.js **한 곳에서만** 하고, CSS 는 그 결과(body.mobile)를 따른다.
     같은 판정을 두 군데 두면 한쪽만 고치게 된다. */
body.mobile .mobtn{display:flex}
/* ⚠ 왼쪽 아래는 **줌 슬라이더**(.zoombtns — left:10px, bottom:30px)가 쓴다 →
   그 위로 올린다. 오른쪽은 미니맵·좌표·계정·채널이 쌓여 있어 자리가 없다. */
#runBtn{bottom:200px}
#fsBtn{bottom:262px}
/* 화면이 낮으면 겹치므로 더 붙인다 */
@media (max-height:460px){
  .mobtn{width:44px;height:44px;font-size:20px}
  #runBtn{bottom:150px}
  #fsBtn{bottom:198px}
}
/* 달리는 중 — 눌린 상태가 보여야 한다 */
#runBtn.on{background:var(--gold);border-color:var(--gold);color:#3a2a00}
/* 기력이 없으면 못 뛴다는 것을 보여준다 */
#runBtn.lock{opacity:.4}

/* ==================== 좁은 화면 (모바일 가로) ==================== */
/* ⚠ 세로 공간이 부족해 **요소들이 서로 겹친다.** 스케치 기준으로 자리를 나눈다:
     좌상 = 체력카드 / 좌중 = 목록(접힘) / 좌하 = 줌(좌측 묶음)
     우상 = 미니맵 + 보스아이콘 / 우중 = 좌표·계정·채널(접힘) / 우하 = 조작 버튼
     하단중앙 = 채팅(접힘) + 퀵슬롯
   ⚠ 폰트·아이콘도 **함께 줄여야** 한다 — 자리만 옮기면 여전히 넘친다. */
/* ⚠ 옛 미디어쿼리 절은 지웠다 — `body.mobile` 격자와 **충돌**했다 (v281).
   특히 `.bosstag{font-size:0}` 이 아이콘을 지우고 있었다.
   모바일 규칙은 `body.mobile` 아래 **한 곳에서만** 정한다. */


/* ⚠ `viewport-fit=cover` 를 쓰면 화면 끝까지 그려지지만 **노치·홈바에 가린다.**
   ⚠ `margin` 으로 밀면 `left/right` 를 쓰는 요소에는 **안 먹는다** →
     안전 영역을 **패딩으로 한 번에** 잡아준다 (지원 안 하면 0 이라 그대로다). */
.float-ui{
  padding-left:env(safe-area-inset-left,0px);
  padding-right:env(safe-area-inset-right,0px);
  padding-bottom:env(safe-area-inset-bottom,0px);
  padding-top:env(safe-area-inset-top,0px);
}
/* fixed 요소는 부모 패딩을 못 받으므로 각자 계산한다 */
.mobtn{ right:calc(10px + env(safe-area-inset-right,0px)) !important }
#chatBox{ bottom:calc(56px + env(safe-area-inset-bottom,0px)) }
.sidetab.left{ left:env(safe-area-inset-left,0px) }
.sidetab.right{ right:env(safe-area-inset-right,0px) }

/* ==================== 좌우 패널 접기 ==================== */
/* ⚠ 좁은 화면에서는 목록이 화면을 크게 먹는다 → 통째로 접는다.
   ⚠ `.float-ui` 안이라 pointer-events:auto 가 없으면 안 눌린다. */
/* ⚠ 접기 탭은 **PC 에서도 필요하다** — 접속자·파티·튜토리얼이 여기 딸려 있다.
   (v282 에서 잘못 숨겼다) */
.sidetab{pointer-events:auto;position:absolute;z-index:8;width:22px;height:44px;
  background:rgba(20,14,30,.86);border:2px solid var(--edge);color:#cfd8ff;
  font-size:12px;line-height:1;cursor:pointer;padding:0;
  display:flex;align-items:center;justify-content:center;
  -webkit-tap-highlight-color:transparent;touch-action:manipulation}
.sidetab.left{left:0;top:50%;transform:translateY(-50%);border-left:none;
  border-radius:0 10px 10px 0}
.sidetab.right{right:0;top:50%;transform:translateY(-50%);border-right:none;
  border-radius:10px 0 0 10px}
/* 접히면 자리를 완전히 비운다
   ⚠ `transform` 만으로는 격자 칸을 계속 차지한다 → `display:none` */
.lefthud.folded{display:none}
.lefthud{transition:transform .18s ease, opacity .18s ease}
/* 줌 슬라이더도 좌측 묶음이다 → 같이 접힌다 */
.zoombtns{transition:transform .18s ease, opacity .18s ease}
.zoombtns.folded{display:none}
/* 우측 스택 — 각각 떠 있으므로 개별로 숨긴다 */
/* ⚠ `transform` 만으로는 **완전히 안 사라진다** (요소 폭이 좁으면 화면 안에 남는다)
     → `display:none` 으로 확실히 감춘다. */
.rs-folded{display:none !important}
#coords,#accBadge,#roomTag{transition:transform .18s ease, opacity .18s ease}

/* ==================================================================
   모바일 전용 레이아웃 — **격자로 자리를 못 박는다**
   ⚠ CSS 로 하나씩 밀면 하나 고칠 때 다른 게 밀린다 (v264~v278 에서 겪음).
     `.float-ui` 를 3×3 격자로 만들고 **각 요소에 칸을 지정**한다 → 겹칠 수가 없다.

     ┌──────────┬────────────┬──────────┐
     │ 캐릭터    │ 화폐·알리미 │ 버튼·미니맵│  ← top
     ├──────────┼────────────┼──────────┤
     │ 목록(접힘)│  (게임 화면) │ 좌표(접힘) │  ← mid
     ├──────────┼────────────┼──────────┤
     │ 줌       │ 채팅·퀵슬롯 │ 조작 버튼  │  ← bot
     └──────────┴────────────┴──────────┘
   ================================================================== */
body.mobile{
  --sl:env(safe-area-inset-left,0px);
  --sr:env(safe-area-inset-right,0px);
  --sb:env(safe-area-inset-bottom,0px);
  --st:env(safe-area-inset-top,0px);
}
body.mobile .float-ui{
  display:grid;
  /* ⚠ `1fr` 은 **최소폭 바닥(min-content)** 이 있어 줄어들지 않는다.
       가운데 칸이 안 줄어들면 그만큼 **3열이 화면 밖으로 밀려난다.** */
  grid-template-columns:auto minmax(0,1fr) auto;
  grid-template-rows:auto minmax(0,1fr) auto;
  grid-template-areas:
    "tl tc tr"
    "ml mc mr"
    "bl bc br";
  align-items:start; justify-items:start;
  /* ⚠ 좌우 가장자는 접기 탭(◀▶)이 쓴다 → 그 폭만큼 비워둔다 */
  padding:calc(6px + var(--st)) calc(var(--tabw) + var(--sr)) calc(6px + var(--sb)) calc(var(--tabw) + var(--sl));
  gap:6px; font-size:11px;
}
/* ⚠ 격자 안에서는 **절대 위치를 쓰면 안 된다** — 칸을 벗어난다.
     원래 absolute/fixed 였던 것들을 static 으로 되돌린다. */
/* ⚠ 아래 네(who·coords·lefthud·gainlog·zoombtns)만 격자를 태다.
     나머지(자원·습격알림·버튼줄·퀵슬롯·우측스택)는 **스테이지 기준 absolute** 로 둔다 —
     미니맵이 캔버스 좌표로 그려지므로 **기준을 맞춰야** 숫자가 맞아떨어진다.
     (퀵슬롯 12칸이 격자 가운데 칸을 413px 로 부풀려
      오른쪽 열을 화면 밖으로 밀어낸 것도 이 때문이었다) */
body.mobile .float-ui>.who,
body.mobile .float-ui>.coords,
body.mobile .float-ui>.lefthud,
body.mobile .float-ui>.gainlog,
body.mobile .float-ui>.zoombtns{
  position:static; left:auto; right:auto; top:auto; bottom:auto;
  transform:none; margin:0; max-width:none;
}

/* ---------- 각 칸 배정 ---------- */
/* ⚠ `scale(.72)` 는 **그려지는 크기만** 줄인다 — 격자는 210px 를 그대로 잡는다.
     → 줄어든 만큼 음수 마진으로 되돌려줘야 왼쪽에 빈칸이 안 생긴다. */
body.mobile .float-ui>.who      { grid-area:tl; --wsc:.72; --ww:210px;
                                  transform:scale(var(--wsc));transform-origin:top left;
                                  width:var(--ww);
                                  margin-right:calc(var(--ww) * (var(--wsc) - 1));
                                  margin-bottom:calc(56px * (var(--wsc) - 1)) }
/* ⚠ 화폐창과 타이머는 **같은 칸(tc)에 세로로 쌓고 가운데 정렬**한다.
     정렬이 다르면(한쪽은 margin, 한쪽은 justify-self) 세로줄이 어긋난다. */
body.mobile .float-ui>.topline  { flex-wrap:nowrap }
body.mobile .float-ui>.raid-hud { font-size:10px;padding:3px 9px;
                                  white-space:nowrap;overflow:hidden;text-overflow:ellipsis }

body.mobile .float-ui>.lefthud  { grid-area:ml; width:104px;font-size:9.5px }
body.mobile .float-ui>.gainlog  { grid-area:ml; align-self:end;font-size:10px;max-width:min(30vw,140px) }
body.mobile .float-ui>.zoombtns { grid-area:bl; transform:scale(.72);transform-origin:left bottom }
/* 퀵슬롯·제작·건설 바는 원래 `left:50%` 으로 **스테이지 가운데** 에 있다 —
   격자를 안 타게 해서 그 자리를 그대로 쓴다 (더 정확하고 칸을 부풀리지도 않는다) */

/* ---------- 우상: 버튼 줄 + 미니맵 자리 비우기 ---------- */
/* ⚠ 미니맵은 **캔버스에 직접 그린다** → 격자를 안 탄다.
     그 폭(좁은 화면 130 + 여백)만큼 우상 칸을 비워 둔다. */
/* ⚠ 미니맵(캔버스)이 우상단을 덮으므로 **tc 칸 전체**를 그만큼 왼쪽으로 민다
     (개별 요소에 margin 을 주면 서로 어긋난다). */
/* ⚠ 패딩을 주면 **하단 칸(채팅·퀵슬롯)까지 왼쪽으로 밀린다** →
     상단 줄(tc·tr)에만 자리를 비운다. */
/* ⚠ 미니맵 폭을 **코드가 알려준다** (09-draw.js 가 --mm 을 넣는다) →
     미니맵 크기가 바뀌어도 여기를 안 고쳐도 된다. */
/* ⚠ `margin-right` 로 밀면 **격자 칸 안에서** 밀는 거라 자리를 두 번 세는 셈이 된다.
   ⚠ 그렇다고 `fixed`(브라우저 창 기준)를 쓰면 **안 된다** —
     `#app{padding:8px}` + 스테이지 테두리 2px 만큼 스테이지가 창보다 안쪽이라
     원소가 스테이지 **바깥 배경 위로 띄어버린다.**
   → 미니맵과 **같은 기준**, 즉 `.float-ui`(=캔버스 영역) 기준 absolute 로 잡는다. */
/* --rzone = 여백 + 미니맵(--mm) + 버튼 4개. --tabw = 접기 탭 폭.
   ⚠ 숫자는 여기 한 곳에서만 정한다 — 버튼이나 미니맵이 바뀌면 전부 따라온다. */
body.mobile{
  --tbw:26px; --tbg:4px; --tabw:20px;
  /* 하단 바 치수 — 채팅이 이걸 보고 바로 위에 선다 (숫자를 따로 박지 않는다) */
  --qsz:29px; --qbot:12px;
  --whow:158px;                              /* 캐릭터 패널이 실제로 보이는 폭(210×.72)+여백 */
  /* ⚠ 노치(--sl)를 빼먹으면 캐릭터 패널이 띠 안으로 침범해 서로 겹친다 */
  --bandL:calc(var(--tabw) + var(--sl) + var(--whow));
  /* 상단 우측 버튼: PVP · ? · 가방 · 보스안내 = 4개
     (모드 버튼은 오른쪽 아래로 내려보냈다) */
  --rzone:calc(6px + var(--mm, 146px) + 4 * (var(--tbw) + var(--tbg)));
}
/* 캐릭터 패널과 버튼줄 사이 **빈 띠에 가운데 정렬**.
   `left`+`right`+`width:max-content`+`margin:0 auto` 면 그 띠 안에서 알아서 가운데로 간다. */
/* ⚠ `.topline` 을 짧게 잡으면 **그게 자식 `.ctlbtns` 의 기준이 된다** —
     positioned 요소는 자식 absolute 의 컨테이너가 되기 때문에
     버튼줄이 자원창 오른쪽 끝 기준으로 계산돼 캐릭터 패널 위로 날아갔다 (v2.97 증상).
   → `.topline` 을 **스테이지 전폭**으로 깔고, 좌우 패딩으로 가운데 띠를 만든다.
     그러면 자원창은 띠 안에서 가운데 정렬되고,
     `.ctlbtns` 의 `right` 는 결국 **스테이지 오른쪽 끝** 기준이 된다. */
body.mobile .float-ui>.topline{
  position:absolute; z-index:7; top:6px; left:0; right:0;
  width:auto; max-width:none; margin:0; transform:none; box-sizing:border-box;
  display:flex; justify-content:center; align-items:flex-start;
  padding-left:var(--bandL); padding-right:var(--rzone) }
body.mobile .float-ui>.raid-hud{
  position:absolute; z-index:7; top:38px;
  left:var(--bandL); right:var(--rzone);
  margin:0 auto; width:max-content; max-width:100%; transform:none }

/* ---------- 우상: 버튼 4개를 미니맵 왼쪽에 한 줄로 ---------- */
/* ⚠ `.topbtns` 는 `.topline`(tc 칸) 안이고 `.bosstag` 는 tr 칸이라 **따로 놀았다.**
     → 둘 다 tr 칸으로 모아 **한 줄**로 세운다.
     순서(왼→오): 전투 · PVP · ❓ · 👑, 그다음이 미니맵. */
/* ⚠ 보스안내도 **같은 줄**에 세운다 (따로 두면 크기·자리가 어긋난다) */
/* ⚠ 예전엔 `.ctlbtns` 를 `.topline` 기준, `.bosstag` 를 tr 칸에 두어
     **기준이 서로 달라** 한 줄로 설 수가 없었다 (보스안내가 미니맵 뒤로 들어갔다).
     → 둘 다 스테이지 기준 absolute. 순서(왼→오): 전투 · PVP · ? · 보스안내 · 미니맵 */
body.mobile .float-ui>.bosstag,
body.mobile .topline .ctlbtns{
  position:absolute; top:6px; z-index:8;
  display:flex; gap:var(--tbg); align-items:center;
  margin:0; left:auto; bottom:auto; transform:none }
body.mobile .float-ui>.bosstag{ right:calc(var(--mm, 146px) + 8px) }
/* ⚠ 부모가 `static` 이면 자식의 `absolute` 가 엉뚱한 곳을 기준 삼는다 */
/* ⚠ 보스안내(tr 칸)와 **나란히** 서야 한다 → 미니맵 폭 + 보스 버튼(26) + 여백만큼 민다.
     숫자를 박지 않고 `--mm` 을 쓴다 (미니맵이 바뀌어도 따라간다). */
body.mobile .topline .ctlbtns{
  right:calc(var(--mm, 146px) + 8px + var(--tbw) + var(--tbg)) }
/* ⚠ `font-size:0` + `::first-letter` 로는 **이모지가 안 보인다** —
     🗡️ 같은 이모지는 여러 글자로 이뤄져 첫 글자만 키우면 깨진다.
     → 글자는 `.btx` 로 감싸 숨기고 아이콘은 그대로 둔다 (12e-ux.js 가 감싼다). */
/* ⚠ 넷 다 **같은 크기**여야 줄이 깔끔하다 (보스안내만 커 보였다) */
/* ⚠ 좌하 띠가 좁은 폰에서도 들어가게 자원창을 살짝 줄인다 */
body.mobile .res{ font-size:12px; gap:7px; padding:4px 9px }
body.mobile .res .item svg{ width:14px;height:14px }
/* 가방 버튼도 같은 크기로 — 12e-ux.js 가 글자를 `.btx` 로 감싸서 아이콘만 남는다 */
body.mobile .ctlbtns .pvptag,body.mobile .bosstag{
  margin:0;padding:0;font-size:13px;line-height:1;border-radius:8px;
  width:var(--tbw);height:var(--tbw);min-width:0;flex:0 0 auto;
  display:flex;align-items:center;justify-content:center;gap:0 }
body.mobile .btx,body.mobile #pvpBtn .pv-tx{ display:none }
body.mobile #pvpBtn .pv-ic{ font-size:15px }
/* ---------- 우중: 좌표·계정·채널 ---------- */
/* ⚠ **한 상자(.rightstack)에 담아 세로로 쌓는다** (12i-keyhud.js 가 담는다).
     따로 두면 자리를 숫자로 밀어야 하고, 하나 바뀔 때마다 나머지가 어긋난다.
     담아두면 flex 가 **알아서** 간격을 맞춘다 — 숫자를 안 쓴다. */
/* ⚠ 이것도 미니맵 바로 아래에 붙어야 하므로 **캔버스 기준 absolute**.
     격자에 두면 첫줄 높이만큼 더 내려가 미니맵과 사이가 벌어졌다.
     오른쪽은 접기 탭 폭(--tabw)만큼 비운다 — 안 그러면 ▶ 이 글자를 덮는다. */
/* ⚠ 미니맵은 캔버스에 그려져 **안전영역을 안 피한다** — 오른쪽 끝이 `스테이지 - 10px`.
     여기서 --sr 을 더하면 스택만 안쪽으로 밀려 미니맵과 줄이 안 맞는다.
     → 미니맵과 **오른쪽 끝을 맞춘다**. */
body.mobile .float-ui>.rightstack{
  position:absolute; top:calc(var(--mmh, 104px) + 20px);
  right:10px; left:auto; bottom:auto;
  display:flex; flex-direction:column; align-items:flex-end; gap:3px;
  max-width:min(40vw, 200px) }
body.mobile .rightstack>*{
  position:static; left:auto; right:auto; top:auto; bottom:auto; transform:none;
  margin:0; font-size:10px; padding:2px 7px; width:max-content;
  max-width:100%; white-space:nowrap; overflow:hidden; text-overflow:ellipsis }

/* ---------- 화폐창 ---------- */
body.mobile .res{ gap:5px;padding:4px 8px;font-size:11px;min-width:0 }
body.mobile .res svg{ width:14px;height:14px }
body.mobile .bag-hint{ display:none }

/* ---------- 하단: 채팅 + 퀵슬롯 ---------- */
/* ⚠ 채팅은 `fixed` 라 격자를 안 탄다 → 하단 중앙에 직접 놓는다 */
/* ⚠ 채팅은 **퀵슬롯 바로 위**에 붙인다 (퀵슬롯 높이 29 + 여백) */
/* ⚠ 가로 화면은 세로가 350px 남짧뿐이다 → 채팅이 넓으면 시야를 크게 먹는다.
     (기본 접힘은 14-chat.js 가 이미 처리한다 — 여기선 폭만 줄인다) */
/* ⚠ 예전엔 `fixed`(창 기준) + `bottom:56px` 이었는데,
     퀵슬롯은 스테이지 기준이라 **기준이 달라** 서로 따로 놀았다.
     그 차이를 iOS 의 홈 인디케이터 여백(--sb≈21px)이 우연히 메워줘서 사파리에선 멀정해 보였고,
     --sb 가 0 인 안드로이드에선 3px 겹쳤다.
   → 12e-ux.js 가 채팅을 `.float-ui` 안으로 옮긴다. 여기서는 퀵슬롯 **바로 위**를 잡으면 된다.
     `--qbot`·`--qsz` 를 써서 퀵슬롯 크기가 바뀌면 채팅도 따라즌다. */
body.mobile .float-ui>#chatBox{
  position:absolute; left:50%; right:auto; top:auto; transform:translateX(-50%);
  bottom:calc(var(--qbot) + var(--qsz) + 8px);
  width:min(46vw,230px); pointer-events:auto; z-index:600 }
body.mobile #chatBox .ch-log{ max-height:13vh;font-size:10.5px }
body.mobile #chatBox .ch-in,body.mobile #chatBox .ch-head{ font-size:10.5px;padding:4px 6px }
/* 퀵슬롯 12칸 한 줄 */
/* ⚠ 화면 **가운데**에 오게 한다 (왼쪽으로 쏠려 있었다) */
body.mobile .barrow{ flex-wrap:nowrap;gap:3px;max-width:none;
  justify-content:center;width:max-content;margin:0 auto }
body.mobile .quickbar,body.mobile .gearbar{ display:flex;gap:2px }
body.mobile .barrow{ bottom:var(--qbot) }
body.mobile .qslot{ width:var(--qsz);height:var(--qsz);border-radius:7px }
body.mobile .qslot svg{ width:17px;height:17px }
body.mobile .qslot .num{ font-size:7px;top:0;left:2px }
body.mobile .qslot .q{ font-size:8px;bottom:0;right:2px }
body.mobile .gslot{ width:var(--qsz);height:var(--qsz);border-radius:7px;padding:0;
  display:flex;align-items:center;justify-content:center }
body.mobile .gslot .glab{ display:none }
body.mobile .gslot svg{ width:19px;height:19px }
body.mobile .gslot .gempty{ font-size:12px }
/* ⚠ 배경이 엷으면 **캔버스 위 오브젝트와 섞여** 버튼인지 안 보인다 */
body.mobile .whoctl{ gap:4px;margin-left:4px }
body.mobile .ictl{ width:26px;height:26px;font-size:12px;
  background:rgba(20,14,30,.82);border-width:1.5px }

/* ---------- 조작 버튼 (우하단) ---------- */
/* ⚠ 이것도 `fixed` 면 스테이지 밖으로 나간다 → absolute 로 맞춘다.
     우측 스택이 미니맵 아래로 내려오므로 버튼은 더 아래에 붙인다. */
/* 미니맵·우측 스택과 **같은 세로줄**에 세운다 (right:10px) */
body.mobile .mobtn{ position:absolute;width:44px;height:44px;font-size:19px;
  left:auto;right:10px !important;z-index:700 }
body.mobile #runBtn{ bottom:calc(62px + var(--sb)) }
body.mobile #fsBtn { bottom:calc(16px + var(--sb)) }
/* ---------- 건설바: 한 줄 + 좀우 스크롤 ---------- */
/* ⚠ `flex-wrap:wrap` 이라 모바일에선 목록이 여러 줄로 접혀 **화면을 다 가렸다.**
     설치할 땅이 안 보이면 건설 자체가 불가능하다.
   → 목록은 한 줄로 두고 좌우로 밀어서 보게 하고,
     **재배치·연속배치는 오른쪽에 고정**해 언제든 누를 수 있게 한다. */
body.mobile .buildbar{
  flex-wrap:nowrap; gap:4px; padding:5px;
  max-width:calc(100% - 2 * (var(--tabw) + 4px));
  bottom:calc(58px + var(--sb)) }
body.mobile .bscroll{
  display:flex; gap:4px; flex:1 1 auto; min-width:0;
  overflow-x:auto; overflow-y:hidden;
  -webkit-overflow-scrolling:touch; scrollbar-width:none }
body.mobile .bscroll::-webkit-scrollbar{ display:none }
/* ⚠ `flex:0 0 auto` 가 없으면 버튼이 눈치보며 짜불어든다 */
body.mobile .buildbar .bsel{ flex:0 0 auto; font-size:10.5px; padding:5px 8px; white-space:nowrap }
body.mobile .buildbar .binstall{ flex:0 0 auto; font-size:11px; padding:5px 10px; white-space:nowrap }
/* 줄바꿈은 한 줄에선 방해만 된다 */
body.mobile .buildbar .bbreak{ display:none }
/* 연속배치는 **항상 보인다** — 스크롤 밖에 있어 밀려나지 않는다 */
body.mobile .buildbar #contToggle{ flex:0 0 auto; font-size:10.5px; padding:5px 8px; white-space:nowrap }

/* ---------- 모드 버튼: 달리기·전체화면과 같은 줄에, 글자로 ---------- */
/* ⚠ 12e-ux.js 가 모바일에선 이 버튼을 `.float-ui` 직속으로 **옮긴다.**
     `#topBtns` 안에 두면 그게 positioned 이라 기준이 되어버리기 때문이다. */
/* ⚠ 세로로 3개를 쌓으면 **가장 좁은 화면(SE 가로, 스테이지 315px)에서 우측 스택과 6px 겹친다.**
     → 달리기 버튼 **왼쪽 옆자리**에 둔다. 퀵슬롯은 더 아래 줄(bottom:12)이라 안 부딪힌다. */
body.mobile .float-ui>#modeBtn{
  position:absolute; left:auto; top:auto;
  right:calc(10px + 44px + 6px);          /* 달리기 버튼 폭 + 여백만큼 왼쪽 */
  bottom:calc(62px + var(--sb));          /* 달리기 버튼과 같은 줄 */
  margin:0; z-index:700;
  height:32px; min-width:44px; padding:0 10px;
  display:flex; align-items:center; justify-content:center;
  font-size:12px; font-weight:800; white-space:nowrap; border-radius:10px }
/* 이모지 대신 **글자**를 보여준다 (전투/채집/건설 · Combat/Gather/Build).
   라벨은 00-i18n.js 의 `mode_*` 에서 오므로 언어를 따라간다. */
body.mobile .float-ui>#modeBtn .bic{ display:none }
body.mobile .float-ui>#modeBtn .btx{ display:inline }
/* 접기 탭 */
/* ⚠ 접기 탭은 **화면 끝(베젤)에 붙어야** 잡기 쉽다.
     노치가 없는 기기는 안전영역이 0 이므로 그대로 0 이 된다. */
/* ⚠ 안전영역을 **패딩으로 주면 안 된다** — 18px 버튼에 노치 폭이 더해져
     **탭이 통째로 검은 덩어리**가 되고 화살표가 한쪽으로 밀린다.
     → 패딩이 아니라 **위치(left/right)** 로 밀어야 크기가 그대로다. */
body.mobile .sidetab{ width:18px;height:44px;font-size:11px;border-radius:0;padding:0;box-sizing:border-box }
/* 좌측 탭은 노치 안깊이만큼 들어오되, 15px 정도는 바깥쪽으로 내준다 */
body.mobile .sidetab.left { left:max(4px, calc(var(--sl) - 15px)); padding:0; border-radius:0 9px 9px 0 }
/* ⚠ 우측 탭은 안 쓴다 — 좌표·계정·채널은 항상 보여준다 (12i-keyhud.js 가 접힘을 푸다) */
body.mobile .sidetab.right{ display:none }
/* 하단 조작 안내는 모바일에선 필요 없다 */
body.mobile .foot,body.mobile #ctrlhint{ display:none }


/* ==================================================================
   모바일 모달 — 전체화면 + 와이어프레임 배치
   ⚠ 세로가 390px 뿐이라 **위아래로 쌓으면 아무것도 안 보인다** → 가로로 나눈다.
   ================================================================== */
body.mobile #invModal,body.mobile #keyModal,body.mobile #statsModal,
body.mobile #bossModal,body.mobile #diceModal,body.mobile #dbgModal,
body.mobile #qpModal,body.mobile #askModal{ padding:0 }

/* ⚠ `height:100vh` 는 **틀렸다.** `#statsModal`·`#invModal` 은 `.stage` 안에 있고
     스테이지는 `#app{padding:8px}` + 테두리 2px 만큼 화면보다 20px 낮다.
     `.stage{overflow:hidden}` 이라 카드가 그만큼 삐져나가 **아래쪽(닫기 버튼)이 잘렸다.**
     → 덮개(inset:0)를 꽉 채우는 `100%` 로 잡으면 스테이지 안이든 body 든 항상 맞는다. */
body.mobile .mdl,body.mobile .invcard{
  width:100% !important; max-width:none !important;
  height:100% !important; max-height:100% !important;
  box-sizing:border-box;
  border-radius:0; border-left:none; border-right:none;
  padding:calc(8px + var(--st)) calc(10px + var(--sr)) calc(8px + var(--sb)) calc(10px + var(--sl));
}
body.mobile .mdl h3,body.mobile .invcard h3{ font-size:15px;margin-bottom:6px }
body.mobile .xbtn{ width:34px;height:34px;font-size:18px }

/* ---------- 가방: 좌(장비 세로) + 중(격자 | 상세) ---------- */
body.mobile #invModal .mdl{
  display:grid;
  grid-template-columns:52px 1fr;
  grid-template-rows:auto 1fr;
  grid-template-areas:"head head" "eq grid";
  gap:6px;
}
body.mobile #invModal h3{ grid-area:head;margin:0 }
body.mobile #invModal .equip{
  grid-area:eq;flex-direction:column;gap:4px;margin:0;overflow-y:auto }
body.mobile #invModal .eslot{ width:46px;height:46px }
body.mobile #invModal .bagmid{
  grid-area:grid;display:flex;flex-direction:column;gap:4px;min-height:0 }
body.mobile #invModal .tabs,body.mobile #invModal .sortrow{
  margin:0;flex-wrap:nowrap;overflow-x:auto }
body.mobile #invModal .tabs button,body.mobile #invModal .sbtn{
  font-size:10px;padding:3px 7px;white-space:nowrap }
body.mobile #invModal .bag-cap{ font-size:10px;margin:0 }
/* ⚠ `cmpcol` 은 `mdl-body` 안이라 grid-area 로 못 빼낸다 → 여기서 가로로 나눈다 */
body.mobile #invModal .mdl-body{
  display:grid;grid-template-columns:1fr minmax(140px,34%);gap:6px;min-height:0;overflow:hidden }
body.mobile #invModal .grid{ grid-template-columns:repeat(auto-fill,minmax(40px,1fr));gap:4px }
body.mobile #invModal .cell{ width:auto;aspect-ratio:1 }
body.mobile #invModal .cmpcol{ display:flex;flex-direction:column;gap:6px;min-height:0 }
body.mobile #invModal .side{ font-size:10.5px;padding:6px;flex:1;overflow-y:auto }
body.mobile #invModal .invbtns{ display:none }

/* ---------- 단순 목록형 창(능력치·보스안내·주사위·퀵슬롯·디버그) ---------- */
/* ⚠ `.invcard` 를 `height:100vh` 로만 만들고 **안쪽에 스크롤 영역을 안 둔 것**이 문제였다.
     제목·본문·닫기가 그냥 넘쳐서 잘리고, 스크롤도 안 돼 보스안내가 통째로 안 보였다.
     가방·제작대는 각자 격자 규칙이 있어 멀족했다.
   → 카드를 **세로 flex** 로 바꾸고 가운데 본문만 늘어나며 스크롤하게 한다.
     제목과 닫기는 `flex:none` 이라 항상 화면에 남는다. */
body.mobile #statsModal .invcard,
body.mobile #bossModal .invcard,
body.mobile #diceModal .invcard,
body.mobile #dbgModal  .invcard,
body.mobile #qpModal   .invcard,
body.mobile #askModal  .invcard{
  display:flex; flex-direction:column; overflow:hidden }
body.mobile #statsModal .invcard>h3,   body.mobile #statsModal .invbtns,
body.mobile #bossModal  .invcard>h3,   body.mobile #bossModal  .invbtns,
body.mobile #diceModal  .invcard>h3,   body.mobile #diceModal  .invbtns,
body.mobile #dbgModal   .invcard>h3,   body.mobile #dbgModal   .invbtns,
body.mobile #qpModal    .invcard>h3,   body.mobile #qpModal    .invbtns,
body.mobile #askModal   .invcard>h3,   body.mobile #askModal   .invbtns{ flex:none }
/* 본문만 늘어난다. ⚠ `min-height:0` 이 없으면 flex 자식은 **줄어들지 않아** 스크롤이 안 생긴다 */
body.mobile #statsBody,
body.mobile #bossListBody,
body.mobile #qpList,
body.mobile #dbgBody{
  flex:1 1 auto; min-height:0; overflow-y:auto; -webkit-overflow-scrolling:touch }

/* ---------- 능력치: 세로가 모자라니 **두 단**으로 ---------- */
body.mobile #statsBody{
  display:grid; grid-template-columns:1fr 1fr; gap:0 14px; align-content:start }
/* 항목은 두 칸에 번갈아 채우고, 폭을 다 쓰는 블록은 한 줄 전체를 차지한다 */
body.mobile #statsBody>.statgrid,
body.mobile #statsBody>.proflist{ grid-column:1 / -1 }
body.mobile .statrow{ font-size:11px;padding:5px 2px }
body.mobile .statcell{ padding:5px 7px }
body.mobile .statcell .sname{ font-size:10px }
body.mobile .statcell .sval{ font-size:13px }
body.mobile .statgrid{ margin:8px 0;gap:5px }
body.mobile .profrow{ font-size:10px }

/* ---------- 보스 안내: 목록도 두 단 ---------- */
/* 가로로 널찍한 화면에 한 줄씩 쌓으면 스크롤이 지나치게 길어진다 */
body.mobile #bossListBody{
  display:grid; grid-template-columns:1fr 1fr; gap:0 10px; align-content:start }
body.mobile #bossListBody>.bl-sec,
body.mobile #bossListBody>.bl-note{ grid-column:1 / -1 }
body.mobile .bl-row{ margin:3px 0;padding:6px 8px }
body.mobile .bl-l{ font-size:11.5px }
body.mobile .bl-m,body.mobile .bl-mat,body.mobile .bl-lv{ font-size:9.5px }

/* ---------- 제작대·강화·거래소: 상단 탭 + 목록 | 상세 ---------- */
body.mobile .mdl .tabs{ flex-wrap:nowrap;overflow-x:auto;gap:4px }
body.mobile .mdl .tabs button{ font-size:10.5px;padding:4px 8px;white-space:nowrap }
body.mobile .mdl-body{ grid-template-columns:1fr minmax(140px,32%);gap:6px;overflow:hidden }
body.mobile .mdl-body>.pane{ min-height:0;overflow-y:auto }
body.mobile .side{ max-height:none;padding:8px;font-size:10.5px }
body.mobile .recipe-row,body.mobile .rc-row{ font-size:10.5px;padding:5px 7px }

/* 화폐창 + 상단 버튼을 한 줄로 (PC)
   ⚠ 안 묶으면 `.float-ui` 가 흐름 배치라 버튼이 아랫줄로 떨어진다. */
/* ⚠ `.res` 가 `position:absolute; left:50%` 로 **화면 가운데에 못 박혀** 있다 →
     감싸기만 하면 화폐창만 가운데로 가고 **버튼은 흐름대로 왼쪽에 남는다.**
     → 묶음을 가운데로 옮기고 `.res` 는 흐름으로 되돌린다. */
.topline{position:absolute;left:50%;top:10px;transform:translateX(-50%);
  display:flex;align-items:center;gap:6px;pointer-events:auto;z-index:6}
.topline>.res{position:static;left:auto;top:auto;transform:none}
.ctlbtns{display:flex;align-items:center;gap:6px;pointer-events:auto}
