/* ── tokens.css（构建时并入，2026-10-30）── */
/* tokens.css — 设计令牌（视觉基准：W12 周复盘风格）
 * 温和浅底 + 大圆角 + 轻阴影 + 语义化彩色 Tag / 进度条 / 卡片层次。
 * 变量统一在此，业务色分区清晰、可整体换肤。
 */
:root {
  /* ── 背景层次（页面 → 卡片 → 嵌套区块，三层灰度递进） ── */
  --bg-page: #F5F6FA;          /* 页面底色，比周复盘略偏冷灰，衬托白卡 */
  --bg-card: #FFFFFF;
  --bg-sunken: #F8F9FB;        /* 卡片内凹陷区块 / 输入框 */
  --bg-hover: #F1F3F8;

  /* ── 文字层次 ── */
  --text-title: #1A1A2E;       /* 标题：深墨蓝黑 */
  --text-body: #3D3D5C;        /* 正文 */
  --text-sub: #8E8EA0;         /* 次要 / 副标题 */
  --text-placeholder: #B8B8C8;
  --text-inverse: #FFFFFF;

  /* ── 主品牌色（保留原型 Ant #4263EB，用于导航高亮/主按钮/主数据） ── */
  --brand: #4263EB;
  --brand-strong: #3B5BDB;
  --brand-soft: #EEF2FF;       /* 主色浅底 */
  --brand-press: #3347C0;

  /* ── 语义化状态色 ── */
  --ok: #2F9E44;   --ok-soft: #E7F8EE;   /* 完成达标 / 上涨 */
  --warn: #B85C00; --warn-soft: #FFF4E0; /* 预警 */
  --danger: #C4314B; --danger-soft: #FDE8EB; /* 异常 / 删除 */
  --info: #4263EB; --info-soft: #EEF2FF;
  --gold: #A87300;             /* 喜报奖项文字用「深金」：白底上纯金黄(#FFD700)几乎看不清，压暗到 4:1 才立得住 */

  /* ── 类别语义色（积分构成 / 分类 Tag，对应周复盘多色系统） ── */
  --cat-course: #4A90D9;   --cat-course-soft: #EAF3FC;   /* 课程：明亮蓝 */
  --cat-comp: #9B59B6;     --cat-comp-soft: #F3ECF8;     /* 竞赛：优雅紫 */
  --cat-activity: #F39C12; --cat-activity-soft: #FEF4E4; /* 活动：琥珀橙 */
  --cat-other: #7F8C8D;    --cat-other-soft: #EEF1F1;    /* 其他：中性灰 */

  /* 趋势/图表辅助色（降序渐变，视觉统一） */
  --chart-1: #4263EB; --chart-2: #36CFC9; --chart-3: #F5A623;
  --chart-4: #9B59B6; --chart-5: #E91E8C; --chart-6: #2F9E44;

  /* 背景层次别名（geo/pk 等页面早期引用的短名，统一指回上面三层灰度） */
  --bg-2: #F8F9FB;

  /* ── 圆角（大圆角风格） ── */
  --radius-card: 14px;
  --radius-md: 10px;
  --radius-sm: 8px;
  --radius-pill: 999px;
  /* 短名别名（早期 geo/pk 样式引用 --radius，指回 10px 档） */
  --radius: 10px;

  /* ── 边框与阴影（轻柔和缓） ── */
  --line: #ECEFF4;             /* 边框色（短名，配 border: 1px solid 用） */
  --border: 1px solid #ECEFF4;
  --shadow-card: 0 1px 2px rgba(26,26,46,.04), 0 4px 16px rgba(26,26,46,.06);
  --shadow-lift: 0 4px 12px rgba(26,26,46,.10), 0 10px 32px rgba(26,26,46,.12);
  --shadow-focus: 0 0 0 3px rgba(66,99,235,.15);
  /* 短名别名（早期 geo/pk 样式引用 --shadow / --accent） */
  --shadow: 0 1px 2px rgba(26,26,46,.04), 0 4px 16px rgba(26,26,46,.06);
  --accent: #4263EB;

  /* ── 图表统一高度（各页面图表卡等高对齐的基础） ── */
  --chart-h: 240px;
  --chart-h-sm: 200px;

  /* ── 间距（8px 栅格） ── */
  --sp-1: 4px; --sp-2: 8px; --sp-3: 12px; --sp-4: 16px;
  --sp-5: 20px; --sp-6: 24px; --sp-7: 32px; --sp-8: 40px;

  /* ── 字体 ── */
  --font: "PingFang SC", "Microsoft YaHei", "思源黑体", -apple-system,
          "Segoe UI", Roboto, "Helvetica Neue", Arial, sans-serif;
  /* 字号缩放系数：系统设置「界面字号」写入，ui.js 在首屏渲染前挂到 <html> 的
   * --fs-scale 上（settings.json 的 font_scale，1 / 1.15 / 1.3）。
   * 全站字号一律 `calc(基准px * var(--fs-scale))`——含原来写死的 11.5px 这类
   * 非令牌值，保证放大时不会有一半文字不动。
   * ⚠️ 只放大字号、不放大间距（--sp-* 保持定值），排布密度由布局自适应兜住。 */
  --fs-scale: 1;
  --fs-xs: calc(12px * var(--fs-scale)); --fs-sm: calc(13px * var(--fs-scale));
  --fs-md: calc(14px * var(--fs-scale)); --fs-lg: calc(16px * var(--fs-scale));
  --fs-xl: calc(20px * var(--fs-scale)); --fs-2xl: calc(24px * var(--fs-scale));
  --fs-3xl: calc(30px * var(--fs-scale));
  --fw-regular: 400; --fw-medium: 500; --fw-semibold: 600; --fw-bold: 700;

  /* ── 布局尺寸 ── */
  /* 侧边栏收窄 220px → 132px（−40%）。最宽项「工作室列表」5 字 ×13px ≈ 65px，
   * 加上 nav 12+8 与 item 12+8 的内边距共 40px → 105px，仍有 ~27px 余量不折行。
   * 2026-10：新看板项「上进双创工作室看板」9 字 = 117px，132px 会被省略号截断，
   * 领导要求的改名要在导航里看全 → 放宽到 158px（文字可用宽 118px）。
   * 2026-10-23：随字号缩放，否则「特大」档导航项全部被省略号吃掉。 */
  --sidebar-w: calc(158px * var(--fs-scale));
  --topbar-h: calc(50px * var(--fs-scale));   /* 2026-10-19：标题+副文案并为一行后从 60px 收窄 */
  --content-max: 1480px;

  /* ── 动效 ── */
  --ease: cubic-bezier(.4,0,.2,1);
  --dur: .16s;
}
/* ── app.css ── */
/* app.css — 全局布局 + 组件样式（tokens.css 之上）

 * 设计原则（对齐优化方向）：
 *   - 极简：去除冗余品牌元素，仅保留必要层级
 *   - 自适应：Flex/Grid + clamp，容器不足时横向滚动而非挤压溢出
 *   - 大数据量友好：深色表格头、sticky、行 hover、密度适中
 */
* { box-sizing: border-box; margin: 0; padding: 0; }

html, body { height: 100%; }

body {
  font-family: var(--font);
  font-size: var(--fs-md);
  color: var(--text-body);
  background: var(--bg-page);
  -webkit-font-smoothing: antialiased;
}

button, input, select, textarea { font-family: inherit; font-size: inherit; color: inherit; }

a { color: var(--brand); text-decoration: none; }
a:hover { color: var(--brand-strong); }

::-webkit-scrollbar { width: 10px; height: 10px; }
::-webkit-scrollbar-thumb { background: #CBD0DC; border-radius: 6px; border: 2px solid transparent; background-clip: content-box; }
::-webkit-scrollbar-thumb:hover { background-color: #Aab0c0; }
::-webkit-scrollbar-track { background: transparent; }

/* ════════════ 应用外壳 ════════════ */
.app {
  display: flex;
  height: 100vh;
  min-width: 0;
  overflow: hidden;
}

/* ── 侧边导航 ── */
.sidebar {
  width: var(--sidebar-w);
  flex: 0 0 var(--sidebar-w);
  background: #1A1A2E;
  color: #C9C9DE;
  display: flex;
  flex-direction: column;
  box-shadow: 2px 0 12px rgba(26,26,46,.08);
  z-index: 10;
}
.sidebar__brand {
  display: flex; flex-direction: column; align-items: center; justify-content: center;
  padding: var(--sp-5) var(--sp-3) var(--sp-4);
  color: #fff; font-size: var(--fs-md); font-weight: var(--fw-semibold);
  border-bottom: 1px solid rgba(255,255,255,.08);
  text-align: center; line-height: 1.3;
}
.sidebar__brand > * + * { margin-top: var(--sp-2); }
/* logo 尺寸：44px → 66px（+50%）→ 86px（客户 2026-10-15 再 +30%）。
   侧栏 158px 减去左右各 12px 内边距还剩 134px，86px 不贴边。 */
.sidebar__brand .brand-logo {
  width: 86px; height: 86px; object-fit: contain;
}
/* 侧栏收窄到 132px 后的防折行兜底：文字一律单行，溢出用省略号而非换行（换行会把 nav 撑高、行距不齐）。 */
.sidebar__brand .txt, .nav__item .txt { white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.nav { flex: 1; overflow-y: auto; padding: var(--sp-3) var(--sp-2); }
.nav__group { margin-bottom: var(--sp-3); }
.nav__group-label {
  padding: var(--sp-2) var(--sp-3); font-size: var(--fs-xs);
  /* 一级目录：#6E6E8B 在 #1A1A2E 深底上对比不足（≈3:1），提亮到 #A7ADC9（≈6:1）
     并加粗一档；仍比二级项文字（#C9C9DE）暗，层级不反转 */
  color: #A7ADC9; font-weight: var(--fw-semibold);
  text-transform: uppercase; letter-spacing: .5px;
}
/* 一级目录彩色圆点（方案A 2026-10-16）：颜色区分序列域，二级项不放图标防挤压 */
.nav__dot { display: inline-block; width: 6px; height: 6px; border-radius: 50%;
  margin-right: 6px; vertical-align: 1px; }
.nav__item {
  display: flex; align-items: center;
  padding: var(--sp-2) var(--sp-3);
  border-radius: var(--radius-sm);
  color: #C9C9DE; cursor: pointer;
  font-size: var(--fs-sm); font-weight: var(--fw-medium);
  transition: background var(--dur) var(--ease), color var(--dur) var(--ease);
  user-select: none;
}
.nav__item > * + * { margin-left: var(--sp-2); }
.nav__item .ico { width: 18px; text-align: center; opacity: .85; }
.nav__item:hover { background: rgba(255,255,255,.06); color: #fff; }
.nav__item.is-active { background: var(--brand); color: #fff; }
.nav__item.is-active .ico { opacity: 1; }

/* ── 主区 ── */
.main { flex: 1; min-width: 0; display: flex; flex-direction: column; }
.topbar {
  height: var(--topbar-h); flex: 0 0 var(--topbar-h);
  background: #fff;
  display: flex; align-items: center;
  padding: 0 var(--sp-6);
  border-bottom: var(--border);
  box-shadow: 0 1px 2px rgba(26,26,46,.04);
  position: sticky; top: 0; z-index: 9;
}
.topbar > * + * { margin-left: var(--sp-4); }
/* 标题 + 副文案同排（2026-10-19 客户：两行太占地方）；
 * 副文案排在「?」图标之后，可自由伸缩，过长时省略号截断（全文见 title 悬停）。 */
.topbar__head { display: flex; align-items: baseline; min-width: 0; flex: 1; }
.topbar__title { font-size: var(--fs-lg); font-weight: var(--fw-semibold); color: var(--text-title); flex: 0 0 auto; }
.topbar__sub { font-size: var(--fs-xs); color: var(--text-sub); min-width: 0; margin-left: var(--sp-3);
  display: flex; align-items: center; white-space: nowrap; overflow: hidden; }
/* 文字节点单独收缩：放不下时省略号只截文字 */
.topbar__sub > .sub-text { flex: 0 1 auto; min-width: 0; overflow: hidden; text-overflow: ellipsis; }
.topbar__spacer { flex: 1; }
.topbar__action { display: flex; align-items: center; }
.topbar__action > * + * { margin-left: var(--sp-2); }

.content {
  flex: 1; overflow: auto; padding: var(--sp-6);
}
.content__inner { max-width: var(--content-max); margin: 0 auto; }

/* ⚠️ 不要写成全局 `.card + .card { margin-top }`：.col-2 / .col-3 栅格里的第二个
 * 卡片会被顶下 16px，整行栏位错位（历史实锤问题）。间距一律交给容器 gap。 */
.stack > .card + .card { margin-top: 0; }
.card {
  background: var(--bg-card);
  border: var(--border);
  border-radius: var(--radius-card);
  box-shadow: var(--shadow-card);
  padding: var(--sp-5) var(--sp-6);
  min-width: 0;
}
.card__head { display: flex; align-items: flex-start; margin-bottom: var(--sp-4); min-height: 34px; }
.card__head > * + * { margin-left: var(--sp-3); }
/* 固定剔除用户卡：收起态只有一行标题，标题/计数/按钮垂直居中一条线（2026-10-19） */
.card--ex > .card__head { align-items: center; }
.card__head h3 { font-size: var(--fs-lg); font-weight: var(--fw-semibold); color: var(--text-title); line-height: 1.4; }
.card__head p { font-size: var(--fs-xs); color: var(--text-sub); margin-top: 2px; }
.card__head .spacer { flex: 1; }
/* 卡片脚注（统一底部对齐区） */
.card__foot { margin-top: auto; padding-top: var(--sp-3); }

/* 页面根容器：所有页面统一用同一套栅格与间距，避免各页各写一套导致参差 */
.page { display: grid; grid-template-columns: minmax(0, 1fr); gap: var(--sp-5); align-content: start; }
/* 工作室配置两页（上进双创/智能）：模块多且高，主块间距放宽一档（2026-10-16 布局优化，data-page 作用域） */
.page[data-page="studios"], .page[data-page="studios_ai"] { gap: var(--sp-6); }

/* 布局工具 */
.row { display: flex; }
.grow { flex: 1; min-width: 0; }
.row > .grow { flex: 1; min-width: 0; }
.row > * + * { margin-left: var(--sp-4); }
/* minmax(0,1fr)：允许列收缩到内容最小宽度之下，避免图表/卡内容撑破容器产生横向溢出 */
.col-3 { display: grid; grid-template-columns: repeat(3, minmax(0, 1fr)); gap: var(--sp-4); align-items: stretch; }
.col-2 { display: grid; grid-template-columns: repeat(2, minmax(0, 1fr)); gap: var(--sp-4); align-items: stretch; }
/* .stack 用 grid 而非 flex：QtWebEngine(Chromium83) 不支持 flex gap，grid 的 gap 才生效 */
.stack { display: grid; grid-template-columns: minmax(0, 1fr); gap: var(--sp-5); align-content: start; }
/* 工具条：flex 容器（Chromium83 不支持 flex gap，用 margin 兜底） */
.toolbar { display: flex; align-items: center; flex-wrap: wrap; min-height: 42px; }
.toolbar > * + * { margin-left: var(--sp-3); }
.scroll-y { overflow-y: auto; min-height: 0; }

/* ════════════ KPI 卡 ════════════ */
/* 固定 5 列栅格（容不下才折行）—— auto-fit 会因卡片文字长度差异导致每行列数抖动、左右边缘参差 */
.kpi-grid { display: grid; grid-template-columns: repeat(5, minmax(0, 1fr)); gap: var(--sp-4); }
.kpi {
  background: #fff; border: var(--border); border-radius: var(--radius-card);
  box-shadow: var(--shadow-card); padding: var(--sp-4) var(--sp-5);
  position: relative; overflow: hidden;
  display: flex; flex-direction: column; min-width: 0; min-height: 96px;
}
.kpi::before {
  content: ""; position: absolute; top: 0; left: 0; right: 0; height: 3px;
  background: linear-gradient(90deg, var(--brand), #7048E8);
}
.kpi--ok::before { background: linear-gradient(90deg, var(--ok), #40C057); }
.kpi--warn::before { background: linear-gradient(90deg, var(--warn), #F59F00); }
.kpi--danger::before { background: linear-gradient(90deg, var(--danger), #E03131); }
.kpi__label { font-size: var(--fs-xs); color: var(--text-sub); margin-bottom: var(--sp-2); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
/* 只把「整体工作室看板」那 5 张卡的标题提亮到近黑（客户 2026-10-15：灰色小字标题看不清；
   第二轮明确只改这一页，看板/课程资源库/配置/详情页维持灰色层级）。 */
.page[data-page="network"] .kpi__label { color: var(--text-title); }
.kpi__value {
  font-size: var(--fs-2xl); font-weight: var(--fw-bold); color: var(--text-title);
  font-variant-numeric: tabular-nums; line-height: 1.25; margin-top: auto;
}
.kpi__extra { font-size: var(--fs-xs); color: var(--text-sub); margin-top: var(--sp-1); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }

/* ════════════ Tag / Pill ════════════ */
.pill {
  display: inline-flex; align-items: center;
  padding: 2px 9px; border-radius: var(--radius-pill);
  font-size: var(--fs-xs); font-weight: var(--fw-medium); line-height: 1.5;
  white-space: nowrap;
}
.pill > * + * { margin-left: 3px; }
.pill--ok   { background: var(--ok-soft);   color: var(--ok); }
.pill--warn { background: var(--warn-soft); color: var(--warn); }
.pill--danger{background: var(--danger-soft); color: var(--danger); }
.pill--grey { background: #EFF1F5; color: #5B5B78; }
.pill--brand{ background: var(--brand-soft); color: var(--brand); }
.pill--cat-course   { background: var(--cat-course-soft);   color: var(--cat-course); }
.pill--cat-comp     { background: var(--cat-comp-soft);     color: var(--cat-comp); }
.pill--cat-activity { background: var(--cat-activity-soft); color: var(--cat-activity); }

/* 语义 Tag（彩色底白字，对应周复盘顶栏标签） */
.tag {
  display: inline-flex; align-items: center;
  padding: 3px 12px; border-radius: var(--radius-pill);
  font-size: var(--fs-xs); font-weight: var(--fw-medium); color: #fff;
}
.tag--course { background: var(--cat-course); }
.tag--comp   { background: var(--cat-comp); }
.tag--activity{background: var(--cat-activity); }
.tag--other  { background: var(--cat-other); }

/* ════════════ 按钮 ════════════ */
.btn {
  display: inline-flex; align-items: center; justify-content: center;
  height: calc(34px * var(--fs-scale)); padding: 0 16px; border-radius: var(--radius-sm);
  border: 1px solid transparent; cursor: pointer;
  font-size: var(--fs-md); font-weight: var(--fw-medium);
  transition: background var(--dur) var(--ease), box-shadow var(--dur) var(--ease), transform var(--dur) var(--ease);
  user-select: none; white-space: nowrap;
}
.btn > * + * { margin-left: 6px; }
.btn:active { transform: translateY(1px); }
.btn:disabled { opacity: .45; cursor: not-allowed; }
.btn--primary { background: var(--brand); color: #fff; }
.btn--primary:hover:not(:disabled) { background: var(--brand-strong); box-shadow: var(--shadow-focus); }
.btn--secondary { background: #fff; border-color: #D9DEE9; color: var(--text-body); }
.btn--secondary:hover:not(:disabled) { background: var(--bg-hover); }
.btn--danger { background: var(--danger); color: #fff; }
.btn--danger:hover:not(:disabled) { background: #B0273E; }
.btn--sm { height: calc(28px * var(--fs-scale)); padding: 0 10px; font-size: var(--fs-sm); }
.btn--text { background: transparent; color: var(--brand); border: none; }
.btn--text:hover { background: var(--brand-soft); }

/* ════════════ 图标按钮 ════════════ */
.icon-btn {
  width: calc(30px * var(--fs-scale)); height: calc(30px * var(--fs-scale)); display: inline-flex; align-items: center; justify-content: center;
  border-radius: var(--radius-sm); border: none; background: transparent; cursor: pointer;
  font-size: var(--fs-md); color: var(--text-sub); transition: all var(--dur) var(--ease);
}
.icon-btn:hover { background: var(--bg-hover); color: var(--text-title); }
.icon-btn--danger:hover { background: var(--danger-soft); color: var(--danger); }
.icon-btn--primary:hover { background: var(--brand-soft); color: var(--brand); }
[data-tip] { position: relative; }
[data-tip]::after {
  content: attr(data-tip); position: absolute; top: calc(100% + 6px); left: 50%;
  transform: translateX(-50%); background: rgba(26,26,46,.92); color: #fff;
  padding: 3px 8px; border-radius: 6px; font-size: var(--fs-xs); white-space: nowrap;
  /* 淡出后必须连 visibility 一起收掉：只留 opacity:0 的话盒子仍在渲染树里，
   * WebView2 会把它算进聚焦元素的范围、画出一圈系统焦点线框（2026-10-28 客户反馈
   * 「提示消失后还留有黄色线框」根因）。visibility 延到淡出结束再切，收尾不闪。*/
  opacity: 0; visibility: hidden; pointer-events: none;
  transition: opacity var(--dur) var(--ease), visibility 0s linear var(--dur); z-index: 50;
}
[data-tip]:hover::after { opacity: 1; visibility: visible; transition-delay: 0s; }

/* ════════════ 说明收纳（标题「?」悬停 / 可折叠） ════════════
 * 成段解释文字用户看过一次就够，不该常驻页面撑乱版面：
 *   · 一句话口径 → 标题右侧 .hint-ico，悬停或键盘聚焦出气泡；
 *   · 多条件长说明 → .hint-fold 收成一行「说明」，点开才展开。
 * ⚠️ 不复用上面的 [data-tip]：那是图标按钮的单行提示（white-space:nowrap），装不下长句。
 * ⚠️ 用 :focus 不用 :focus-visible（分享版要兼容老 Chromium）。 */
.hint-ico {
  display: inline-flex; align-items: center; justify-content: center;
  width: 16px; height: 16px; margin-left: 6px; border-radius: 50%;
  border: 1px solid #C3CAD9; background: #F7F8FC;
  color: var(--text-sub); font-size: calc(11px * var(--fs-scale)); font-weight: var(--fw-bold);
  line-height: 1; cursor: help; position: relative; vertical-align: 1px;
  transition: background var(--dur) var(--ease), color var(--dur) var(--ease);
}
.hint-ico:hover, .hint-ico:focus { border-color: var(--brand); background: var(--brand); color: #fff; outline: none; }
.hint-ico::after {
  content: attr(data-hint);
  position: absolute; top: calc(100% + 8px); left: 0;
  width: max-content; max-width: min(340px, 46vw);
  white-space: pre-line; text-align: left; font-weight: 400;
  background: rgba(26,26,46,.94); color: #fff;
  padding: 8px 10px; border-radius: 8px;
  font-size: var(--fs-xs); line-height: 1.65;
  /* 同 [data-tip]：淡出后收掉 visibility，只留 opacity:0 会被 WebView2 画成残留线框 */
  opacity: 0; visibility: hidden; pointer-events: none;
  transition: opacity var(--dur) var(--ease), visibility 0s linear var(--dur); z-index: 70;
}
.hint-ico:hover::after, .hint-ico:focus::after { opacity: 1; visibility: visible; transition-delay: 0s; }
.hint-fold { margin-top: 2px; }
.hint-fold > summary {
  cursor: pointer; list-style: none; user-select: none;
  font-size: var(--fs-xs); color: var(--text-sub); line-height: 1.7;
}
.hint-fold > summary::-webkit-details-marker { display: none; }
.hint-fold > summary::before { content: '▸ '; }
.hint-fold[open] > summary::before { content: '▾ '; }
.hint-fold > summary:hover { color: var(--brand); }
.hint-fold__body { font-size: var(--fs-xs); color: var(--text-sub); line-height: 1.75; margin-top: 2px; }

/* ════════════ 输入 ════════════ */
.input, .select {
  height: calc(34px * var(--fs-scale)); padding: 0 12px; border-radius: var(--radius-sm);
  border: 1px solid #D9DEE9; background: var(--bg-card);
  outline: none; transition: border-color var(--dur) var(--ease), box-shadow var(--dur) var(--ease);
}
.input:hover, .select:hover { border-color: #B9C0CF; }
.input:focus, .select:focus { border-color: var(--brand); box-shadow: var(--shadow-focus); }
.textarea { resize: vertical; min-height: 90px; padding: 10px 12px; border-radius: var(--radius-sm); border: 1px solid #D9DEE9; outline: none; }
textarea:focus { border-color: var(--brand); box-shadow: var(--shadow-focus); }

/* ════════════ 表格 ════════════ */
/* 统一 max-height（滚动在自己身上），不再由各页写 calc(100vh - Npx) 硬编码 */
.table-wrap { overflow: auto; border-radius: var(--radius-md); border: var(--border); background: #fff; max-height: 58vh; }
.table-wrap--sm { max-height: 42vh; }
.table-wrap--none { max-height: none; }

/* ── 「整页一张表」型页面：表格撑满窗口剩余高度（工作室列表 / 报告历史） ──
 * 58vh 在 900px 高的窗口上只剩 ~520px，一屏看不了几行。这里把上下链路都变成有界
 * flex 列，由 .table-wrap 自己 flex 撑开 —— 窗口多高就用多高（实测 708px @900）。
 * 页面模块导出 `fill = true` 时由 ui.js 挂上这三个类：
 *   .content--fill / .content__inner--fill / .page--fill
 *
 * 🔴 契约：**任何情况下都不比旧的 58vh 更矮**。报告历史页会冒出一张「任务进度」卡
 *    （生成期间才显示），若只做「吃掉剩余高度」，那时表格反而只剩 459px < 522px。
 *    所以表格留 min-height:58vh 保底，空间不够时让**页面**滚动，而不是把表格压扁。
 *    → 因此 .content--fill 用 overflow:auto（不能用 hidden，否则保底那一段会被裁掉）。
 *
 * ⚠️ Chromium83 不支持 flex gap：本段一律不写 gap，间距挂到非撑满卡的 margin-bottom。
 * ⚠️ 靠 .card--fill 显式标注**哪张卡该长**（报告历史页还有进度卡 / 空态卡），
 *    不用 :has()（Chromium83 不支持）。
 * ⚠️ .page--fill 用 minmax(min-content, 1fr)：min-content 让「保底高度」能被行承认，
 *    否则行只有 1fr，保底内容会溢出卡片边框。 */
.content--fill { display: flex; flex-direction: column; overflow: auto; }
.content__inner--fill { flex: 1; min-height: 0; display: flex; flex-direction: column; }
.page--fill { flex: 1; min-height: 0; grid-template-rows: minmax(min-content, 1fr); align-content: stretch; }
.page--fill > .card--fill { display: flex; flex-direction: column; }
/* 报告历史页在 .page 与 .card 之间多一层 .stack。这里**必须用 flex 而不是 grid**：
 * grid 的「auto + minmax(0,1fr)」依赖行序号，而「任务进度」卡是 display:none
 * （不生成网格项）→ 历史卡会落到 auto 行、高度反而比原来的 58vh 更矮（实测 479px < 522px）。
 * flex 只看 flex-grow，与兄弟是否可见无关。 */
.page--fill > .stack { display: flex; flex-direction: column; }
.page--fill > .stack > .card { flex: 0 0 auto; }
.page--fill > .stack > .card:not(.card--fill) { margin-bottom: var(--sp-5); }
.page--fill > .stack > .card--fill { flex: 1 1 auto; display: flex; flex-direction: column; }
/* 卡内：工具条/卡头是固定高度，表格吃掉剩下的，滚动条落在表格自己身上 */
.page--fill .card--fill > .table-wrap { flex: 1 1 auto; min-height: 58vh; max-height: none; }
.table {
  width: 100%; border-collapse: separate; border-spacing: 0;
  font-size: var(--fs-sm); min-width: 100%;
}
.table thead th {
  position: sticky; top: 0; z-index: 2;
  background: var(--bg-sunken); color: var(--text-sub);
  font-weight: var(--fw-semibold); font-size: var(--fs-xs);
  text-align: left; padding: 10px 12px; white-space: nowrap;
  border-bottom: var(--border);
}
.table tbody td { padding: 9px 12px; border-bottom: 1px solid #F2F4F8; color: var(--text-body); vertical-align: middle; }
.table tbody tr:last-child td { border-bottom: none; }
.table tbody tr { transition: background var(--dur) var(--ease); }
.table tbody tr:hover { background: var(--bg-hover); }
.table .num { font-variant-numeric: tabular-nums; text-align: right; }
.table .strong { font-weight: var(--fw-semibold); color: var(--text-title); }
.table .muted { color: var(--text-sub); }
.table .cell-wrap { display: inline-flex; align-items: center; }
.table .cell-wrap > * + * { margin-left: 6px; }
.table .ops { display: flex; justify-content: flex-start; }
.table .ops > * + * { margin-left: 2px; }
.table .row-actions { visibility: hidden; }
.table tbody tr:hover .row-actions { visibility: visible; }
.table [data-sort] { cursor: pointer; user-select: none; }
.table [data-sort]:hover { color: var(--text-title); }

/* 勾选框 */
.checkbox { width: 16px; height: 16px; accent-color: var(--brand); cursor: pointer; }

/* ════════════ 进度条（周复盘风格：细横条 + 圆角端点） ════════════ */
.progress { height: 6px; border-radius: var(--radius-pill); background: #EDEFF5; overflow: hidden; }
.progress__fill { height: 100%; border-radius: inherit; background: var(--brand); transition: width .4s var(--ease); }
.progress__fill--ok { background: var(--ok); }
.progress__fill--warn { background: var(--warn); }
.progress__fill--danger { background: var(--danger); }

/* ════════════ 预警 chip 流（可横向滚动，杜绝整条挤压溢出） ════════════ */
.chip-flow { display: flex; overflow-x: auto; padding-bottom: 2px; }
.chip-flow > * + * { margin-left: var(--sp-2); }
.chip {
  display: inline-flex; align-items: center;
  padding: 5px 12px; border-radius: var(--radius-pill);
  background: var(--warn-soft); color: var(--warn);
  font-size: var(--fs-sm); font-weight: var(--fw-medium); white-space: nowrap; cursor: pointer;
  border: 1px solid rgba(184,92,0,.18); transition: all var(--dur) var(--ease);
}
.chip > * + * { margin-left: 6px; }
.chip:hover { background: #FFE9C4; box-shadow: var(--shadow-lift); }

/* ════════════ 进度条行（ID+名称+进度） ════════════ */
.rate-row { display: flex; align-items: center; }
.rate-row > * + * { margin-left: var(--sp-3); }
.rate-row__name { width: calc(120px * var(--fs-scale)); font-size: var(--fs-sm); color: var(--text-body); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; flex: 0 0 calc(120px * var(--fs-scale)); }
.rate-row__bar { flex: 1; min-width: 0; }
.rate-row__val { width: calc(52px * var(--fs-scale)); text-align: right; font-size: var(--fs-sm); font-weight: var(--fw-medium); color: var(--text-title); font-variant-numeric: tabular-nums; flex: 0 0 calc(52px * var(--fs-scale)); }

/* ════════════ Toast ════════════ */
.toast-region { position: fixed; top: 16px; right: 16px; z-index: 1000; display: flex; flex-direction: column; }
.toast-region .toast + .toast { margin-top: 8px; }
.toast {
  min-width: 240px; max-width: 380px; padding: 11px 16px; border-radius: var(--radius-md);
  background: #fff; box-shadow: var(--shadow-lift); font-size: var(--fs-sm);
  display: flex; align-items: flex-start;
  animation: toast-in .22s var(--ease);
  border-left: 4px solid var(--brand);
}
.toast > * + * { margin-left: 8px; }
.toast--ok { border-left-color: var(--ok); }
.toast--info { border-left-color: var(--brand); }
.toast--warn { border-left-color: var(--warn); }
.toast--danger { border-left-color: var(--danger); }
.toast.out { opacity: 0; transform: translateX(20px); transition: all .25s var(--ease); }
@keyframes toast-in { from { opacity: 0; transform: translateX(20px); } to { opacity: 1; transform: none; } }

/* ════════════ 空状态 / 骨架 ════════════ */
.empty { text-align: center; padding: 40px 20px; color: var(--text-sub); }
.empty .ico { font-size: calc(34px * var(--fs-scale)); margin-bottom: 10px; }
.empty .hint { font-size: var(--fs-xs); margin-top: 4px; color: var(--text-placeholder); }

.loading { display: flex; align-items: center; justify-content: center; padding: 50px; color: var(--text-sub); }
.loading > * + * { margin-left: 10px; }
.spinner {
  width: 20px; height: 20px; border-radius: 50%;
  border: 3px solid var(--brand-soft); border-top-color: var(--brand);
  animation: spin .7s linear infinite;
}
@keyframes spin { to { transform: rotate(360deg); } }

/* ════════════ Modal ════════════ */
/* ⚠️ Chromium 83（QtWebEngine）不支持 inset 简写（87+ 才有），必须写四边展开。
 * 历史实锤：.modal-mask 曾用 inset:0，Qt 内核下遮罩无坐标 → 「生成工作室报告」弹窗
 * 打开了但完全不可见，用户看起来就是按钮点了没反应。 */
.modal-mask {
  position: fixed; top: 0; left: 0; right: 0; bottom: 0; background: rgba(26,26,46,.42); z-index: 900;
  display: flex; align-items: center; justify-content: center; padding: var(--sp-6);
}
.modal {
  background: #fff; border-radius: var(--radius-card); box-shadow: var(--shadow-lift);
  width: 100%; max-width: 640px; max-height: 88vh; display: flex; flex-direction: column;
  animation: modal-in .2s var(--ease); overflow: hidden;
}
.modal__head { padding: var(--sp-5) var(--sp-6); border-bottom: var(--border); display: flex; align-items: center; }
.modal__head h3 { font-size: var(--fs-lg); font-weight: var(--fw-semibold); color: var(--text-title); }
.modal__head .close { margin-left: auto; }
.modal__body { padding: var(--sp-6); overflow-y: auto; }
.modal__foot { padding: var(--sp-4) var(--sp-6); border-top: var(--border); display: flex; justify-content: flex-end; }
.modal__foot > * + * { margin-left: var(--sp-2); }
@keyframes modal-in { from { opacity: 0; transform: scale(.96); } to { opacity: 1; transform: none; } }

/* ════════════ 图表容器 ════════════ */
/* 图表卡统一：SVG 走 viewBox 等比缩放，高度由 CSS 锁死 → 同排卡片等高、不参差 */
.chart-box { width: 100%; min-width: 0; overflow: hidden; height: var(--chart-h); }
.chart-box--sm { height: var(--chart-h-sm); }
.chart-box--tall { height: 300px; }
.chart-box > svg, .chart svg { display: block; width: 100%; height: 100%; }
.chart .axis-label { font-size: calc(12px * var(--fs-scale)); fill: var(--text-sub); font-family: var(--font); }
.chart .val-label { font-size: calc(12px * var(--fs-scale)); fill: var(--text-title); font-family: var(--font); font-weight: var(--fw-semibold); font-variant-numeric: tabular-nums; }
.chart-foot { font-size: calc(12px * var(--fs-scale)); color: var(--text-sub); margin-top: var(--sp-2); line-height: 1.55; }
/* 横向滚动容器（工作室多时图表不被压扁） */
.chart-scroll { overflow-x: auto; overflow-y: hidden; padding-bottom: 2px; }
.chart-scroll > svg { display: block; height: var(--chart-h); }

/* ════════════ 积分期次工具条（上进双创工作室看板顶部） ════════════
 * 弱化成一行浅灰小字 + 小号下拉：它只是口径开关，不该和 KPI/地图抢版面。
 * flex 不用 gap（QtWebEngine Chromium83 不支持），用 margin 兜底。 */
.period-bar { display: flex; align-items: center; flex-wrap: wrap; font-size: var(--fs-sm); color: var(--text-sub); }
.period-bar__label { display: inline-flex; align-items: center; }
.period-bar__label > * + * { margin-left: var(--sp-1); }
.period-bar .select { margin-left: var(--sp-3); width: 176px; }
.period-bar__note { margin-left: var(--sp-3); font-size: var(--fs-xs); color: var(--text-sub); }

/* ════════════ 看板分区标题（合并后的看板用来隔开「工作室维度 / 学生维度」） ════════════
 * 只有一行字 + 一条延伸细线，不再用整块卡片装分区名（合并页已经很长，标题卡会更碎）。 */
.sec-title { display: flex; align-items: center; margin-top: var(--sp-2); }
.sec-title h2 { font-size: var(--fs-md); font-weight: var(--fw-semibold); color: var(--text-title); }
.sec-title::after { content: ''; flex: 1; height: 1px; background: var(--line); margin-left: var(--sp-3); }

/* ════════════ 横向条（在学方向分布 / 阶段完成率 / 各方向可选门数 共用一套） ════════════ */
.hbar-list { display: grid; gap: 9px; }
.hbar { display: flex; align-items: center; font-size: var(--fs-xs); color: var(--text-sub); }
.hbar__name { flex: none; width: calc(112px * var(--fs-scale)); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
.hbar__track { flex: 1; min-width: 0; height: 12px; border-radius: 3px; background: #F1F3F9; }
.hbar__track i { display: block; height: 100%; border-radius: 3px; background: var(--brand); }
.hbar__val { flex: none; width: calc(44px * var(--fs-scale)); text-align: right; color: var(--text-title);
  font-weight: var(--fw-semibold); font-variant-numeric: tabular-nums; }
/* 可点的条（课程方向 / 关键技术 → 右栏只列在学该课程的室） */
.hbar--btn { cursor: pointer; }
.hbar--btn:hover .hbar__name { color: var(--brand); }
.hbar--btn.is-on .hbar__name { color: var(--brand); font-weight: var(--fw-semibold); }
.hbar--btn.is-on .hbar__track i { background: var(--brand-strong); }

/* 「在学课程构成」的两列左栏（.cs-grid/.cs-col/.cs-h）随 2026-10-26 的拆图下线：
 * 看板页现在是两张独立条形图卡，直接复用上面的 .hbar-list / .hbar。 */
.stars { color: #F5A623; letter-spacing: 1px; white-space: nowrap; }
/* 卡内容吃满剩余高度（学习进度总览与右栏列表卡等高时用；右栏靠 .geo-listcard 自带） */
.card--fill { display: flex; flex-direction: column; }
.card--fill > .card-fill { flex: 1; min-height: 0; }
/* 学习进度总览：环图带自己的图例，阶段条纵向铺满右半，两栏一起把卡片撑实 */
.prog-donut { flex: 0 0 auto; display: flex; flex-direction: column; justify-content: center; }
.prog-donut .legend-row { margin-top: var(--sp-3); justify-content: center; }
.prog-stages { display: flex; flex-direction: column; }
.prog-stages > .hbar-list { flex: 1; align-content: space-between; }

/* ════════════ 筛选条（课程资源库） ════════════ */
/* flex 不支持 gap（Chromium83），一行放不下换行时用 margin-bottom 留出第二行的间距 */
.filter-bar { display: flex; align-items: center; flex-wrap: wrap; }
.filter-bar > * { margin-bottom: var(--sp-2); }
.filter-bar > * + * { margin-left: var(--sp-3); }
.filter-bar .select { width: 148px; }
/* pill 里的「✕」（取消筛选）：做成无边框同字号的按钮，点得到又不抢视觉 */
.pill-x { border: 0; background: transparent; color: inherit; font: inherit; cursor: pointer;
  padding: 0 2px; margin-left: 6px; }

/* ════════════ 省份分布（工作室总览用；上进双创看板第 2 行也复用这套列表卡） ════════════ */
/* align-items: stretch → 地图卡与右侧工作室列表卡等高（领导要求两模块对齐；
 * 列表卡靠下面 .geo-listcard 的 flex 撑满，多出的条目在自己内部滚动） */
/* ════════════ 联动合并卡：主栏 + 明细栏同属一张卡（工作室总览地图行 / 看板在学课程行） ════════════
 * 关系靠「同一张卡 + 一条分隔线」表达，不再靠两卡之间的空隙；卡头放主标题与计数，
 * 两栏各有一个二级小标题，右栏小标题随左栏点选更新（明细从哪来一目了然）。 */
.card--link { padding: 0; overflow: hidden; }
.card--link > .card__head { padding: var(--sp-5) var(--sp-6) var(--sp-3); margin-bottom: 0; align-items: center; }
.link-body { display: grid; grid-template-columns: minmax(0, 1.55fr) minmax(0, 1fr); border-top: var(--border); align-items: stretch; }
.link-pane { display: flex; flex-direction: column; min-width: 0; padding: var(--sp-4) var(--sp-5) var(--sp-5) var(--sp-6); }
.link-pane--l { border-right: var(--border); }
.link-pane--r { background: var(--bg-sunken); padding-right: var(--sp-6); }
.link-pane__h { display: flex; align-items: center; min-height: 20px; margin-bottom: var(--sp-3);
  font-size: var(--fs-sm); font-weight: var(--fw-semibold); color: var(--text-title); }
.link-pane__h > * + * { margin-left: var(--sp-2); }
.link-pane__h .spacer { flex: 1; }
.link-pane__h em { font-style: normal; font-weight: var(--fw-regular); font-size: var(--fs-xs); color: var(--text-sub); }
.link-clear { border: 0; background: none; padding: 0; color: var(--brand); font: inherit; font-size: var(--fs-xs);
  cursor: pointer; white-space: nowrap; }
.link-clear:hover { color: var(--brand-strong); text-decoration: underline; }
/* 右栏是浅底：列表条目回到白底才看得出可点 */
.link-pane--r .geo-list__item { background: var(--bg-card); }
.link-pane .geo-map { flex: 1; }
/* 明细区高度上限沿用 .geo-listcard 的硬上限口径（Chromium83 自动最小尺寸不可靠，见上面注释）。
 * 地图右侧那栏 2026-10-15 起整表渲染 + 内部滚动（不再翻页），这条 470px 上限就是唯一的兜底。 */
.link-pane .geo-listwrap { flex: 1; min-height: 0; max-height: calc(470px * var(--fs-scale)); overflow-y: auto; padding-right: 2px; }
.link-pane .chart-foot { margin-top: auto; padding-top: var(--sp-2); }
.geo-layout { display: grid; grid-template-columns: minmax(0, 1.55fr) minmax(0, 1fr); gap: var(--sp-5); align-items: stretch; }
.geo-map { width: 100%; }
.geo-map svg { width: 100%; height: auto; display: block; }
.geo-echart { width: 100%; height: 470px; }
.kpi-row { display: grid; grid-template-columns: repeat(4, minmax(0, 1fr)); gap: var(--sp-4); }
.legend-row { display: flex; align-items: center; flex-wrap: wrap; }
.legend-row > .lg-label { font-size: var(--fs-xs); color: var(--text-sub); margin: 0 var(--sp-1); }
.legend-row .lg-cell { width: 22px; height: 12px; border-radius: 3px; margin-right: 2px; }
.legend-row .lg-note { font-size: var(--fs-xs); color: var(--text-sub); margin-left: var(--sp-3); }
/* 列表卡：整卡做成 flex 列，卡头固定、列表区吃剩余空间、翻页器钉在底部 */
.geo-listcard { display: flex; flex-direction: column; }
/* max-height 是硬上限，不能只靠 grid stretch：QtWebEngine(Chromium83) 算「flex 子项 min-height:0
 * + 父项被 stretch」的自动最小尺寸不准，几百条会把整块撑到无限长（用户实测）。
 * 写死上限 + 列表翻页器兜底，两个引擎表现一致。 */
.geo-listcard > .geo-listwrap { flex: 1; min-height: 0; max-height: calc(470px * var(--fs-scale)); overflow-y: auto; padding-right: 2px; }
.geo-list { display: grid; align-content: start; gap: var(--sp-2); }
.geo-pager { display: flex; align-items: center; margin-top: auto; padding-top: var(--sp-3); }
.geo-pager > * + * { margin-left: var(--sp-3); }
.geo-pager__info { margin-left: auto; font-size: var(--fs-xs); }
.geo-list__item {
  display: block; width: 100%; text-align: left; padding: var(--sp-3);
  border: 1px solid var(--line); border-radius: var(--radius-sm);
  background: var(--bg-card); cursor: pointer; transition: all var(--dur) var(--ease);
}
.geo-list__item:hover { border-color: var(--accent); background: var(--brand-soft); }
.geo-list__name { font-size: var(--fs-sm); font-weight: var(--fw-semibold); color: var(--text-title); }
.geo-list__meta { font-size: var(--fs-xs); color: var(--text-sub); margin-top: var(--sp-1); }
.geo-list__meta .sep { margin: 0 var(--sp-2); }
/* 工作室分类标签（总览地图右列表）：标准=蓝（主色系），上进双创=紫 */
.geo-kind {
  display: inline-block; margin-right: 6px; padding: 0 7px; border-radius: 8px;
  font-size: var(--fs-xs); font-weight: var(--fw-semibold); line-height: calc(18px * var(--fs-scale));
  vertical-align: 2px; white-space: nowrap;
}
.geo-kind--zn { background: var(--brand-soft); color: #2E5BD8; }
.geo-kind--sx { background: #F5EEF9; color: #8F4DA8; }
.geo-filter { display: flex; align-items: center; margin-left: auto; }
.geo-filter__label { font-size: var(--fs-xs); color: var(--text-sub); margin-right: var(--sp-2); }
.geo-seg {
  padding: 5px 12px; font-size: var(--fs-xs); border: 1px solid var(--line);
  background: #fff; color: var(--text-body); cursor: pointer; white-space: nowrap;
  border-radius: 0; transition: all var(--dur) var(--ease);
}
.geo-seg:first-of-type { border-radius: var(--radius-sm) 0 0 var(--radius-sm); }
.geo-seg:last-of-type { border-radius: 0 var(--radius-sm) var(--radius-sm) 0; }
.geo-seg + .geo-seg { border-left-width: 0; }
.geo-seg:hover { background: var(--brand-soft); }
.geo-seg.is-on { background: var(--brand); border-color: var(--brand); color: #fff; }

/* ── 地图联动卡的全屏态 ──
 * 这张卡脱离 .page 栅格铺满窗口（盖住侧栏与顶栏），左地图 / 右列表结构不变；
 * z-index 800 压过侧栏(10)/顶栏(9)，但让开弹窗(900)与 toast(1000)。
 * 470px 那套高度上限在这里全部解除，两栏一起吃到视口底；地图容器改成撑满，
 * ECharts 由 geo.js 里那个 ResizeObserver 自动 resize()，不需要手动干预。 */
.card--link.is-fs {
  position: fixed; top: 0; left: 0; right: 0; bottom: 0; z-index: 800;
  padding: 0; border: 0; border-radius: 0; box-shadow: none;
  display: flex; flex-direction: column;
}
.card--link.is-fs > .card__head { padding: var(--sp-4) var(--sp-6); }
.card--link.is-fs > .link-body { flex: 1; min-height: 0; grid-template-columns: minmax(0, 1.85fr) minmax(0, 1fr); }
.card--link.is-fs .link-pane { min-height: 0; padding: var(--sp-4) var(--sp-5) var(--sp-4) var(--sp-6); }
.card--link.is-fs .link-pane .geo-map { flex: 1 1 auto; min-height: 0; display: flex; }
.card--link.is-fs .geo-echart { flex: 1; min-height: 0; height: auto; }
.card--link.is-fs .link-pane .geo-listwrap { max-height: none; }
body.fs-lock { overflow: hidden; }
/* 窗口/手机屏太窄时全屏也不硬撑两栏，右栏落到下方 */
@media (max-width: 760px) {
  .card--link.is-fs > .link-body { grid-template-columns: minmax(0, 1fr); }
  .card--link.is-fs .link-pane--l { border-right: 0; border-bottom: var(--border); }
}

/* ════════════ 竞赛成果：喜报卡片墙（工作室总览）+ 成果列表（上进双创看板）════════════ */
.aw-mq { overflow: hidden; padding: 2px 0 6px; }
/* flex 无 gap（Chromium83）→ 卡片自带 margin-right；track 位移一半宽度后接回，形成无缝滚动 */
.aw-mq__track { display: flex; align-items: stretch; width: max-content; will-change: transform; }
.aw-card { flex: 0 0 auto; width: 296px; margin-right: var(--sp-4); padding: var(--sp-4);
  border: var(--border); border-radius: var(--radius-md); background: var(--bg-card);
  display: flex; flex-direction: column; }
/* 看板「全部工作室」轮播卡：可点跳详情，悬停给选中反馈 */
.aw-card--studio { cursor: pointer; transition: border-color .15s ease, box-shadow .15s ease; }
.aw-card--studio:hover { border-color: var(--brand); box-shadow: var(--shadow-lift); }
.aw-card__top { display: flex; align-items: center; }
.aw-card__year { background: var(--bg-sunken); color: var(--text-sub); }
.aw-card__who { margin-top: var(--sp-3); font-size: var(--fs-sm); font-weight: var(--fw-semibold);
  color: var(--text-title); line-height: 1.5; }
.aw-card__people { margin-top: var(--sp-2); font-size: var(--fs-sm); color: var(--text-body); line-height: 1.6; }
.aw-card__people b { font-weight: var(--fw-medium); color: var(--brand); }
/* 竞赛名（2026-10-16 客户：「字略小、字色太浅」）：14px 正文灰 → 16px 近黑半粗；
 * 奖项行仍靠深金 + 奖杯压在它下面一档；超过两行截断，完整名称挂 title 悬停可见。 */
.aw-card__comp { margin-top: var(--sp-2); font-size: var(--fs-lg); font-weight: var(--fw-semibold);
  color: var(--text-title); line-height: 1.5;
  display: -webkit-box; -webkit-line-clamp: 2; -webkit-box-orient: vertical; overflow: hidden; }
/* 奖项唯一形态：奖杯 + 「级别+奖项」（国家级说「全国」）。卡片墙的 .aw-card__award 与看板成果表的
 * .aw-prize 共用；源表只登记「一等奖 1 队」这类计数的也播进同一行，不再另做橙色小片。 */
.aw-card__award, .aw-prize { font-weight: var(--fw-bold); color: var(--gold); }
.aw-card__award::before, .aw-prize::before { content: '🏆'; margin-right: var(--sp-2); }
.aw-card__award { margin-top: auto; padding-top: var(--sp-3); font-size: var(--fs-lg); }
/* 奖项行不换行：整条口径（含「××1项、××2项」的计数串）读作一行。表格里降到 13px，
 * 否则这一列的 min-content 宽度会把「竞赛项目」列挤到折行，8 行就顶出 .table-wrap。 */
.aw-prize { font-size: var(--fs-sm); white-space: nowrap; }
/* 级别小片：越大的赛越重的色（国际=竞赛紫 · 国家级=琥珀 · 省级=品牌蓝 · 市/校=中性灰阶） */
.aw-lv--int  { background: var(--cat-comp); color: #fff; }
.aw-lv--nat  { background: var(--cat-activity); color: #fff; }
.aw-lv--prov { background: var(--brand-soft); color: var(--brand); }
.aw-lv--city { background: #EFF1F5; color: #5B5B78; }
.aw-lv--sch  { background: #F4F5F9; color: var(--text-sub); }
.aw-lv--none { background: var(--bg-sunken); color: var(--text-placeholder); border: var(--border); }

/* ════════════ 积分构成横向分段条（chart.js 的 segBar；原「工作室对比」模块已删） ════════════ */
.pk-bar { display: flex; height: 18px; border-radius: var(--radius-pill); overflow: hidden; background: #EDEFF5; }
.pk-bar > span { display: block; height: 100%; }
.pk-bar-legend { display: flex; flex-wrap: wrap; margin-top: var(--sp-2); }
.pk-bar-legend > * + * { margin-left: var(--sp-4); }
.pk-bar-legend .lg { display: inline-flex; align-items: center; font-size: var(--fs-xs); color: var(--text-sub); }
.pk-bar-legend .lg i { width: 10px; height: 10px; border-radius: 3px; margin-right: 6px; display: inline-block; }
@media (max-width: 1100px) {
  .geo-layout { grid-template-columns: minmax(0, 1fr); }
  /* 合并卡竖排后：主/明细之间的分隔线从竖变横，浅底栏改到下方 */
  .link-body { grid-template-columns: minmax(0, 1fr); }
  .link-pane--l { border-right: 0; border-bottom: var(--border); }
}

/* ════════════ 页内 Tab（详情页） ════════════ */
.tabs { display: flex; align-items: center; border-bottom: 1px solid var(--line); margin-bottom: var(--sp-4); }
.tab {
  padding: var(--sp-3) var(--sp-4); font-size: var(--fs-md); font-weight: var(--fw-medium);
  color: var(--text-sub); background: none; border: none; cursor: pointer;
  border-bottom: 2px solid transparent; margin-bottom: -1px; transition: all var(--dur) var(--ease);
}
.tab:hover { color: var(--text-title); }
.tab.is-on { color: var(--brand); border-bottom-color: var(--brand); font-weight: var(--fw-semibold); }

/* ════════════ 详情页头部 ════════════ */
.detail-hero { display: flex; align-items: flex-start; flex-wrap: wrap; }
.detail-hero > * + * { margin-left: var(--sp-4); }
.detail-hero__name { font-size: var(--fs-xl); font-weight: var(--fw-bold); color: var(--text-title); }
.detail-hero__meta { font-size: var(--fs-sm); color: var(--text-sub); margin-top: var(--sp-1); }
.back-btn { display: inline-flex; align-items: center; height: calc(30px * var(--fs-scale)); padding: 0 10px; border-radius: var(--radius-sm); border: 1px solid var(--line); background: #fff; cursor: pointer; font-size: var(--fs-sm); color: var(--text-body); }
.back-btn:hover { background: var(--bg-hover); }

/* ════════════ 迷你条形（榜单内联占比） ════════════ */
.mbar { display: flex; align-items: center; }
.mbar__track { width: 90px; height: 6px; border-radius: var(--radius-pill); background: #EDEFF5; overflow: hidden; margin-right: var(--sp-2); }
.mbar__fill { height: 100%; border-radius: inherit; background: var(--brand); }

/* ════════════ 表单行（设置页） ════════════ */
/* 标签列要容得下最长的设置项名（「报告流水线完成后自动导出」= 12 个汉字 ≈156px @13px），
 * 132px 会让它在列内突然折行。控件列一律撑满，否则目录/网址这类长值被
 * 浏览器默认宽度（~177px）截断，看不出配的是什么。 */
.field { display: grid; grid-template-columns: calc(178px * var(--fs-scale)) minmax(0, 1fr); align-items: center; gap: var(--sp-3); }
.field__label { font-size: var(--fs-sm); color: var(--text-sub); }
.field .input, .field .select, .field .textarea { width: 100%; min-width: 0; }
.field + .field { margin-top: var(--sp-3); }
.form-foot { display: flex; align-items: center; }
.form-foot > * + * { margin-left: var(--sp-3); }

/* ════════════ 提示块（需登录 / 跳过说明） ════════════ */
.notice {
  border-radius: var(--radius-card);
  padding: var(--sp-3) var(--sp-4);
  border: 1px solid transparent;
  font-size: var(--fs-sm); line-height: 1.7;
}
.notice--warn { background: var(--warn-soft); border-color: rgba(184,92,0,.22); color: var(--warn); }
.notice--info { background: var(--brand-soft); border-color: rgba(66,99,235,.2); color: var(--brand); }
.notice__title { font-weight: var(--fw-bold); margin-bottom: 2px; }
.notice__body { opacity: .92; }

/* ════════════ 响应式 ════════════ */
/* ⚠️ KPI 固定 5 张，桌面端（≥960px）一律排一行。
 * 历史实锤：曾在 1440px 降级为 4 列 → 第 5 张「平均完成率」独自掉到第二行，
 * 左边空出 3 个卡位，是「模块对不齐」的头号观感问题。窄屏降级时必须凑满行。 */
@media (max-width: 1280px) {
  .col-3 { grid-template-columns: repeat(2, minmax(0, 1fr)); }
  .geo-layout { grid-template-columns: minmax(0, 1fr); }
  .kpi-row { grid-template-columns: repeat(2, minmax(0, 1fr)); }
}
@media (max-width: 960px) {
  /* 5 张分 3 列 → 第 4 张跨 2 列，排成 3 + 2，不留空位 */
  .kpi-grid { grid-template-columns: repeat(3, minmax(0, 1fr)); }
  .kpi-grid > :nth-child(4) { grid-column: span 2; }
  .kpi-row { grid-template-columns: repeat(2, minmax(0, 1fr)); }
  .col-3, .col-2 { grid-template-columns: minmax(0, 1fr); }
  .sidebar { width: 64px; flex-basis: 64px; }
  .sidebar__brand .txt, .nav__item .txt { display: none; }
  .field { grid-template-columns: minmax(0, 1fr); }
}
@media (max-width: 760px) {
  .content { padding: var(--sp-3); }
}
/* ════════════ 分享版（share.html 专用）════════════
 * 无侧边栏，顶部栏切换视图。注意 Chromium 83 兼容：
 * flex 容器禁 gap（用 margin 间距）、禁 inset 简写。 */
.share-brand {
  display: flex; align-items: center;
  /* 站名要压得住顶栏：14px 正文色时像说明文字，抬到 17px + 近黑标题色才像网站名 */
  font-weight: var(--fw-bold); font-size: calc(17px * var(--fs-scale));
  line-height: 1.2; letter-spacing: .3px; color: var(--text-title);
}
.share-brand img {
  /* logo.png 原图 2398×1147（比例 ≈2.09:1 的横版字标）：写死 26×26 会被横向压扁，
     只锁高度、宽度走 auto，并禁掉 flex 压缩。 */
  height: 26px; width: auto; flex: none; margin-right: var(--sp-2);
  /* logo.png 是白色图形+透明底（为深色侧边栏设计），白底顶栏上会隐形。
     CSS 滤镜染成品牌蓝（≈#4263EB），原图不动。 */
  filter: brightness(0) saturate(100%) invert(30%) sepia(85%) saturate(4500%) hue-rotate(224deg) brightness(99%) contrast(95%);
}
.share-tabs { display: flex; align-items: center; margin-left: var(--sp-6); }
/* 共同体徽标：顶栏最左，与「上进」字标以竖线分隔、同一品牌蓝（已重着色，见 web/logo-community.png）。
 * 圆形徽标视觉上比同高字标「小一圈」，取 34px 才和 26px 的字标齐眉。 */
.share-brand__sep {
  margin: 0 var(--sp-3); color: #C3CAD9; font-weight: 400;
  font-size: calc(14px * var(--fs-scale)); line-height: 1;
}
.share-brand .share-brand__seal { height: calc(34px * var(--fs-scale)); margin-right: 0; filter: none; }
/* 顶栏是白底：不能用侧边栏的浅灰字/悬停白字（白底上会隐形）。
 * 正常态深字；悬停浅蓝底 + 品牌色字；选中态品牌底白字。 */
.share-tabs .nav__item {
  padding: var(--sp-2) var(--sp-4);
  border-radius: var(--radius-sm);
  color: var(--ink);
  font-weight: var(--fw-medium);
}
.share-tabs .nav__item:not(.is-active):hover {
  background: var(--brand-soft);
  color: var(--brand);
}
.share-tabs .nav__item + .nav__item { margin-left: var(--sp-2); }
.share-tabs .nav__item.is-active { background: var(--brand); color: #fff; }

/* 报告选择页（share_reports.js）：工作室卡片栅格 */
.share-grid {
  display: grid; grid-template-columns: repeat(3, minmax(0, 1fr));
  gap: var(--sp-4); margin-top: var(--sp-4);
}
.share-card { cursor: pointer; transition: box-shadow var(--dur) var(--ease), transform var(--dur) var(--ease); }
.share-card:hover { box-shadow: 0 6px 18px rgba(26,26,46,.12); transform: translateY(-2px); }
.share-card__name { font-weight: var(--fw-bold); font-size: var(--fs-md); margin-bottom: var(--sp-2); }
.share-card__row { display: flex; flex-wrap: wrap; font-size: var(--fs-sm); }
.share-card__row > * + * { margin-left: var(--sp-3); }
.share-card__go {
  margin-top: var(--sp-3); color: var(--brand);
  font-size: var(--fs-sm); font-weight: var(--fw-medium);
}
@media (max-width: 1280px) { .share-grid { grid-template-columns: repeat(2, minmax(0, 1fr)); } }
@media (max-width: 960px) {
  .share-grid { grid-template-columns: minmax(0, 1fr); }
  .share-tabs { margin-left: var(--sp-3); }
  /* 窄屏只收掉品牌名，分隔符要留着——它左边的字没了，两个徽标仍靠它分开 */
  .share-brand > span:not(.share-brand__sep) { display: none; }
}

/* ════════════ 上进双创工作室看板 · B 版视觉（2026-10-23） ════════════
 * 参考已评审的 B 版整页原型：深色总数卡 + 白色三格轨道、细线分栏、
 * 6px 圆角进度条、轻边框卡片、表格去彩色胶囊。
 * 🔴 全部规则都挂在 .page[data-page="studio"] 下：其他看板/课程/配置页不受影响。
 * ⚠️ Chromium83：不用 flex gap（间距走 grid gap / margin），不用 :has()。 */
.page[data-page="studio"] {
  --text-sub: #6F7488;
  --radius-card: 12px;
  --shadow-card: 0 1px 2px rgba(26,26,46,.04);
  --bg-sunken: #FAFBFD;
  --stu-line: #E3E7F0;
  --stu-faint: #98A0B3;
  --num: "Bahnschrift", "DIN Alternate", "Segoe UI", "Microsoft YaHei", sans-serif;
  gap: 18px;
}
.page[data-page="studio"] .stack { gap: 18px; }

/* ── 首屏 KPI：总数压舱 + 三项指标轨道 ── */
.page[data-page="studio"] .studio-kpi { display: grid; grid-template-columns: 1.33fr 4fr; gap: 12px; min-height: 132px; }
.page[data-page="studio"] .studio-kpi__hero {
  background: #1A1A2E; border-radius: var(--radius-card); padding: 17px 22px 15px;
  display: flex; flex-direction: column; min-width: 0;
}
.page[data-page="studio"] .studio-kpi__label {
  font-size: calc(12.5px * var(--fs-scale)); font-weight: 500; color: #4A4F63; line-height: 1.3;
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.page[data-page="studio"] .studio-kpi__hero .studio-kpi__label { color: #A7ADC9; }
.page[data-page="studio"] .studio-kpi__value {
  margin-top: 8px; font-family: var(--num); font-size: calc(31px * var(--fs-scale)); font-weight: 600;
  line-height: 1.05; color: var(--text-title); letter-spacing: -.015em;
  font-variant-numeric: tabular-nums; white-space: nowrap;
}
.page[data-page="studio"] .studio-kpi__hero .studio-kpi__value { margin-top: 9px; font-size: calc(42px * var(--fs-scale)); letter-spacing: -.02em; color: #fff; }
.page[data-page="studio"] .studio-kpi__unit {
  font-family: var(--font); font-size: calc(12.5px * var(--fs-scale)); font-weight: 500; color: var(--text-sub);
  margin-left: 4px; letter-spacing: 0; vertical-align: 1px;
}
.page[data-page="studio"] .studio-kpi__hero .studio-kpi__unit { font-size: calc(13.5px * var(--fs-scale)); color: #B9BFD6; vertical-align: 2px; }
.page[data-page="studio"] .studio-kpi__rule { height: 1px; background: rgba(255,255,255,.1); margin-top: auto; }
.page[data-page="studio"] .studio-kpi__extra { margin-top: 8px; font-size: calc(11.5px * var(--fs-scale)); line-height: 1.4; color: var(--text-sub); }
.page[data-page="studio"] .studio-kpi__hero .studio-kpi__extra { margin-top: 10px; font-size: calc(11px * var(--fs-scale)); color: #A7ADC9; }
.page[data-page="studio"] .studio-kpi__rail {
  display: grid; grid-template-columns: repeat(3, minmax(0, 1fr));
  background: var(--bg-card); border: 1px solid var(--stu-line);
  border-radius: var(--radius-card); box-shadow: var(--shadow-card); overflow: hidden;
}
.page[data-page="studio"] .studio-kpi__metric { display: flex; flex-direction: column; min-width: 0; padding: 16px 18px 14px; }
.page[data-page="studio"] .studio-kpi__metric + .studio-kpi__metric { border-left: 1px solid var(--line); }
.page[data-page="studio"] .studio-kpi__metric .studio-kpi__label { color: #4A4F63; }
.page[data-page="studio"] .studio-kpi__metric .studio-kpi__extra { margin-top: auto; padding-top: 9px; line-height: 1.35; }

/* ── 工具条与卡片：比原版更薄一档，去掉重阴影 ── */
.page[data-page="studio"] .period-bar .select { height: calc(30px * var(--fs-scale)); font-size: calc(11.5px * var(--fs-scale)); }
.page[data-page="studio"] .period-bar__note { font-size: calc(10.5px * var(--fs-scale)); color: var(--stu-faint); }
.page[data-page="studio"] .card {
  padding: 18px 20px; border-color: var(--stu-line);
  border-radius: var(--radius-card); box-shadow: var(--shadow-card);
}
.page[data-page="studio"] .card__head { min-height: 24px; margin-bottom: 14px; }
.page[data-page="studio"] .card__head h3 { font-size: calc(14.5px * var(--fs-scale)); letter-spacing: .005em; }

/* 卡头右侧的口径计数（「41 个工作室 · 30 间有在学项目」这类）压淡一档 */
.page[data-page="studio"] .card__head .muted { font-size: calc(12px * var(--fs-scale)); color: var(--stu-faint); }

/* ── 工作室积分 TOP20 + 竞赛成果：并排一行（2026-10-30 客户要求，榜单在成果左侧）──
 * 左栏固定窄栏（4 列：排名 / 工作室 / 学员数 / 人均积分，室名单行省略、全名靠 title），
 * 右栏吃满剩余宽度；两卡等高，卡内不留白。
 * 窄于 1281 退回单列：成果表本身要 760px 保底，硬并会把两栏都挤成横向滚动。 */
@media (min-width: 1281px) {
  .page[data-page="studio"] .studio-duo {
    display: grid; grid-template-columns: minmax(0, calc(440px * var(--fs-scale))) minmax(0, 1fr);
    gap: var(--sp-5); align-items: stretch;
  }
  /* 成果表被并排挤窄后行高变两行，58vh 上限会把 8 行截断成「卡内滚动 + 下方翻页器」双滚动；
   * 并排时整张卡的高度由 TOP20 决定，直接放开让 8 行都露出来。 */
  .page[data-page="studio"] .studio-duo .table-wrap { max-height: none; }
}
.page[data-page="studio"] .card--top20 { display: flex; flex-direction: column; min-height: 0; }
.page[data-page="studio"] .card--top20 .table { table-layout: fixed; }
.page[data-page="studio"] .card--top20 th:nth-child(1),
.page[data-page="studio"] .card--top20 td:nth-child(1) { width: calc(64px * var(--fs-scale)); white-space: nowrap; }
.page[data-page="studio"] .card--top20 th:nth-child(3),
.page[data-page="studio"] .card--top20 td:nth-child(3) { width: calc(56px * var(--fs-scale)); }
.page[data-page="studio"] .card--top20 th:nth-child(4),
.page[data-page="studio"] .card--top20 td:nth-child(4) { width: calc(66px * var(--fs-scale)); }
/* 成果卡被并排拉高时，列表盒吃掉多出来的高度，翻页器贴卡底（不在卡底攒一条空白） */
.page[data-page="studio"] .studio-duo [data-role="awards-list"] { display: flex; flex-direction: column; }
/* ⚠️ 光给 .table-wrap 设 flex 不够：它的父级 .awards-host 若是普通 block，
 *    高度只等于内容高度，多出来的空间就攒在 host 外面（实测 832px 卡里空 181px）。
 *    host 必须自己也是 flex 项 + flex 容器，表格才真正撑到卡底。 */
.page[data-page="studio"] .studio-duo [data-role="awards-list"] .awards-host {
  flex: 1 1 auto; min-height: 0; display: flex; flex-direction: column;
}
.page[data-page="studio"] .studio-duo [data-role="awards-list"] .awards-host > .table-wrap {
  flex: 1 1 auto; min-height: 0; max-height: none;
}
/* ⚠️ 别给这张表加 min-height:100%「把零头吃掉」：表格一拉伸，平均行高被算大，
 *    行数就会退回 8 行（实测 1920×1200 从 10 行掉到 8 行），等于把自适应取消掉。
 *    宁可留「不到一行」的零头（实测 ≤44px）。 */
/* 翻页器固定在卡底，不参与收缩（否则行数一多它先被压扁） */
.page[data-page="studio"] .studio-duo [data-role="awards-list"] > .geo-pager { flex: 0 0 auto; }
.page[data-page="studio"] .studio-duo [data-role="awards-list"] .table-wrap { flex: 1 1 auto; }
.page[data-page="studio"] .card--top20 td:nth-child(2) > span {
  display: block; overflow: hidden; text-overflow: ellipsis; white-space: nowrap;
}
.page[data-page="studio"] .card--top20 .table-wrap { flex: 1 1 auto; min-height: 0; max-height: none; }

/* ── 学生维度：分数段分布 + 排行榜并排一行（2026-10-26）──
 * 榜单要装 4 列 + 搜索框，给它宽侧；两卡各自高度自然，不做等高拉伸。
 * 只在宽屏生效：窄屏交回底部 .col-2 的单列响应式，不然两张卡都挤。 */
@media (min-width: 961px) {
  .page[data-page="studio"] .col-2--stu { grid-template-columns: minmax(0, 1fr) minmax(0, 1.5fr); }
  /* 左列（两张窄卡 + 分数段分布）整体拉到与右侧排行榜等高：
   * 剩余高度全给图表盒，卡底不攒空白；窄卡保持自然高度。 */
  .page[data-page="studio"] .col-2--stu > .stack { grid-template-rows: auto minmax(0, 1fr); }
  .page[data-page="studio"] [data-role="dist-card"] { display: flex; flex-direction: column; min-height: 0; }
  .page[data-page="studio"] [data-role="dist-card"] .chart-box { flex: 1 1 auto; height: auto; min-height: 260px; }
  .page[data-page="studio"] [data-role="dist-card"] .chart-foot { margin-top: 10px; }
}

/* 学生维度的两个总数（上榜学员 / 积分总和）提成窄卡，压在分数段分布上方。
 * 沿用本页指标带的语言：一个容器 + 一根分割线，不是两张等权浮卡；
 * 数字比首屏轨道卡小一档，避免和顶部 KPI 抢视线。 */
.page[data-page="studio"] .stu-stats {
  display: grid; grid-template-columns: repeat(2, minmax(0, 1fr));
  background: var(--bg-card); border: 1px solid var(--stu-line);
  border-radius: var(--radius-card); box-shadow: var(--shadow-card); overflow: hidden;
}
.page[data-page="studio"] .stu-stat { min-width: 0; padding: 17px 18px 15px; }
.page[data-page="studio"] .stu-stat + .stu-stat { border-left: 1px solid var(--line); }
.page[data-page="studio"] .stu-stat__label {
  font-size: calc(12.5px * var(--fs-scale)); font-weight: 500; color: #4A4F63; line-height: 1.3;
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.page[data-page="studio"] .stu-stat__value {
  margin-top: 6px; font-family: var(--num); font-size: calc(29px * var(--fs-scale)); font-weight: 600;
  line-height: 1.05; color: var(--text-title); letter-spacing: -.015em;
  font-variant-numeric: tabular-nums; white-space: nowrap;
}
.page[data-page="studio"] .stu-stat__unit {
  font-family: var(--font); font-size: calc(12px * var(--fs-scale)); font-weight: 500;
  color: var(--text-sub); margin-left: 4px; vertical-align: 1px;
}
.page[data-page="studio"] .stu-stat__note {
  margin-top: 6px; font-size: calc(11px * var(--fs-scale)); line-height: 1.35; color: var(--text-sub);
}

/* ── 表格：浅灰表头 + 中性数字，完成率用细进度条 ── */
.page[data-page="studio"] .table-wrap { border-color: var(--stu-line); border-radius: 10px; }
.page[data-page="studio"] .table thead th {
  background: #FAFBFD; color: var(--stu-faint); font-weight: 500; font-size: calc(11px * var(--fs-scale)); padding: 9px 12px;
}
.page[data-page="studio"] .table tbody td { font-size: calc(12.5px * var(--fs-scale)); padding: 9px 12px; }
.page[data-page="studio"] .table tbody tr:hover { background: #FAFBFD; }
/* 选课表列宽（2026-10-26 按实际内容长度定的）：
 * 技术串最长 34 字、行业串最长 12 字 → 技术列给够并允许不换行，行业列收窄也不换行，
 * 这样一行就是一行高，不会出现「技术折两行、别的内容一行」把行高拉得参差不齐。
 * 剩下的宽度全给「在学项目」（最长 25 字，偶尔换行影响的是它自己那一格）。 */
.page[data-page="studio"] [data-role="course-body"] th:nth-child(1),
.page[data-page="studio"] [data-role="course-body"] td:nth-child(1) { width: 186px; }
.page[data-page="studio"] [data-role="course-body"] th:nth-child(3),
.page[data-page="studio"] [data-role="course-body"] td:nth-child(3) { width: 252px; white-space: nowrap; }
.page[data-page="studio"] [data-role="course-body"] th:nth-child(4),
.page[data-page="studio"] [data-role="course-body"] td:nth-child(4) { width: 118px; white-space: nowrap; }
.page[data-page="studio"] [data-role="course-body"] th:nth-child(5),
.page[data-page="studio"] [data-role="course-body"] td:nth-child(5) { width: 56px; }
.page[data-page="studio"] [data-role="course-body"] th:nth-child(6),
.page[data-page="studio"] [data-role="course-body"] td:nth-child(6) { width: 72px; }
/* 第 7 列（完成率）由 :last-child 统一给宽；「人均课程」列 2026-10-30 已删，
 * 这里不要再写 nth-child(7)，否则会把最后一列压成 72px。 */
.page[data-page="studio"] [data-role="course-body"] th:last-child,
.page[data-page="studio"] [data-role="course-body"] td:last-child { width: 116px; }
/* 一室一组：室名与积分列是 rowspan 格，一律顶对齐，好和组内第一行齐平；
 * 组与组之间换一条略重的线（rowspan 格的下边线本来就落在组底，两处都要染）。 */
.page[data-page="studio"] [data-role="course-body"] td { vertical-align: top; padding: 7px 12px; }
.page[data-page="studio"] [data-role="course-body"] tr.cg-end > td,
.page[data-page="studio"] [data-role="course-body"] td[rowspan] { border-bottom-color: #DCE1EC; }
/* 室名是这一组的主键，做成可点文字链（进工作室详情），不用按钮 */
.page[data-page="studio"] .cg-room {
  font-size: calc(12.5px * var(--fs-scale)); font-weight: 600; color: var(--text-title); text-decoration: none;
}
.page[data-page="studio"] .cg-room:hover { color: var(--brand); text-decoration: underline; }
.page[data-page="studio"] .cg-course { font-size: calc(12.5px * var(--fs-scale)); color: var(--text-body); }
.page[data-page="studio"] .cell-tag { font-size: calc(11.5px * var(--fs-scale)); color: var(--text-sub); }
.page[data-page="studio"] .cell-empty { font-size: calc(11.5px * var(--fs-scale)); color: var(--stu-faint); }
/* 学生榜里「已退出」小标：有历史积分但不在最新名单，中性灰底（不是状态告警） */
.page[data-page="studio"] .stu-left {
  display: inline-block; margin-left: 6px; padding: 0 5px; border-radius: 4px; background: #F1F3F8;
  color: var(--stu-faint); font-size: calc(10px * var(--fs-scale)); line-height: 16px; white-space: nowrap;
}
.page[data-page="studio"] .rate-cell { display: flex; align-items: center; width: 112px; }
.page[data-page="studio"] .rate-cell__track {
  flex: 1; height: 4px; border-radius: 999px; background: #E8ECF4; overflow: hidden; margin-right: 8px;
}
.page[data-page="studio"] .rate-cell__track i { display: block; height: 100%; border-radius: 999px; background: var(--brand); }
.page[data-page="studio"] .rate-cell b {
  min-width: 34px; text-align: right; font-family: var(--num); font-size: calc(12px * var(--fs-scale));
  font-weight: 600; color: var(--text-title); font-variant-numeric: tabular-nums;
}

/* ── 学生维度分区标题 ── */
.page[data-page="studio"] .sec-title h2 { font-size: calc(14.5px * var(--fs-scale)); }

@media (max-width: 1180px) {
  .page[data-page="studio"] .studio-kpi { grid-template-columns: minmax(0, 1fr); }
}
@media (max-width: 900px) {
  .page[data-page="studio"] .studio-kpi__rail { grid-template-columns: minmax(0, 1fr); }
  .page[data-page="studio"] .studio-kpi__metric + .studio-kpi__metric { border-left: 0; border-top: 1px solid var(--line); }
}

/* ════════════ 工作室总览 · B 版 KPI 指标带（2026-10-23） ════════════
 * 与「上进双创看板」同一套视觉：深色总数卡承载总量 + 智能/双创占比，
 * 其余四项收进白色轨道。🔴 全部规则挂在 .page[data-page="network"] 下：
 * 课程资源库 / 详情 / 配置页仍用原 .kpi-grid，不受影响。 */
.page[data-page="network"] {
  --net-sub: #6F7488;
  --net-faint: #98A0B3;
  --net-line: #E3E7F0;
  --num: "Bahnschrift", "DIN Alternate", "Segoe UI", "Microsoft YaHei", sans-serif;
  gap: 18px;
}
.page[data-page="network"] .net-kpi { display: grid; grid-template-columns: 1.33fr 4fr; gap: 12px; min-height: 132px; }
.page[data-page="network"] .net-kpi__hero {
  background: #1A1A2E; border-radius: var(--radius-card); padding: 17px 22px 15px;
  display: flex; flex-direction: column; min-width: 0;
}
.page[data-page="network"] .net-kpi__label {
  font-size: calc(12.5px * var(--fs-scale)); font-weight: 500; color: #4A4F63; line-height: 1.3;
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.page[data-page="network"] .net-kpi__hero .net-kpi__label { color: #A7ADC9; }
.page[data-page="network"] .net-kpi__value {
  margin-top: 8px; font-family: var(--num); font-size: calc(29px * var(--fs-scale)); font-weight: 600;
  line-height: 1.05; color: var(--text-title); letter-spacing: -.015em;
  font-variant-numeric: tabular-nums; white-space: nowrap;
}
.page[data-page="network"] .net-kpi__hero .net-kpi__value { margin-top: 9px; font-size: calc(42px * var(--fs-scale)); letter-spacing: -.02em; color: #fff; }
.page[data-page="network"] .net-kpi__value.is-range { font-size: calc(25px * var(--fs-scale)); letter-spacing: 0; }
.page[data-page="network"] .net-kpi__unit {
  font-family: var(--font); font-size: calc(12.5px * var(--fs-scale)); font-weight: 500; color: var(--net-sub);
  margin-left: 4px; letter-spacing: 0; vertical-align: 1px;
}
.page[data-page="network"] .net-kpi__hero .net-kpi__unit { font-size: calc(13.5px * var(--fs-scale)); color: #B9BFD6; vertical-align: 2px; }
.page[data-page="network"] .net-kpi__split {
  display: flex; height: 4px; border-radius: 999px; overflow: hidden;
  background: #E9EDF7; margin-top: auto;
}
.page[data-page="network"] .net-kpi__hero .net-kpi__split { background: rgba(255,255,255,.12); }
.page[data-page="network"] .net-kpi__split span { display: block; height: 100%; }
.page[data-page="network"] .net-kpi__legend {
  display: flex; align-items: center; margin-top: 8px;
  font-size: calc(11px * var(--fs-scale)); color: #A7ADC9; white-space: nowrap; overflow: hidden;
}
.page[data-page="network"] .net-kpi__legend .lg { display: inline-flex; align-items: center; min-width: 0; }
.page[data-page="network"] .net-kpi__legend .lg + .lg { margin-left: 12px; }
.page[data-page="network"] .net-kpi__legend i {
  width: 6px; height: 6px; border-radius: 50%; flex: 0 0 auto; margin-right: 5px;
}
.page[data-page="network"] .net-kpi__legend b {
  font-weight: 600; color: #fff; font-family: var(--num); font-size: calc(11.5px * var(--fs-scale)); margin: 0 2px;
}
.page[data-page="network"] .net-kpi__legend .lg-note { color: #7F86A3; font-weight: 400; margin-left: 3px; }
.page[data-page="network"] .net-kpi__rail {
  display: grid; grid-template-columns: repeat(4, minmax(0, 1fr));
  background: #fff; border: 1px solid var(--net-line); border-radius: var(--radius-card);
  box-shadow: 0 1px 2px rgba(26,26,46,.04); overflow: hidden;
}
.page[data-page="network"] .net-kpi__metric { display: flex; flex-direction: column; min-width: 0; padding: 16px 18px 14px; }
.page[data-page="network"] .net-kpi__metric + .net-kpi__metric { border-left: 1px solid var(--line); }
.page[data-page="network"] .net-kpi__metric .net-kpi__label { color: #4A4F63; }
.page[data-page="network"] .net-kpi__extra {
  margin-top: auto; padding-top: 9px; font-size: calc(11.5px * var(--fs-scale)); line-height: 1.35;
  color: var(--net-sub); white-space: normal;
}

@media (max-width: 1180px) {
  .page[data-page="network"] .net-kpi { grid-template-columns: minmax(0, 1fr); }
  .page[data-page="network"] .net-kpi__rail { grid-template-columns: repeat(2, minmax(0, 1fr)); }
  .page[data-page="network"] .net-kpi__metric:nth-child(3) { border-left: 0; }
  .page[data-page="network"] .net-kpi__metric:nth-child(n+3) { border-top: 1px solid var(--line); }
}
@media (max-width: 900px) {
  .page[data-page="network"] .net-kpi__rail { grid-template-columns: minmax(0, 1fr); }
  .page[data-page="network"] .net-kpi__metric + .net-kpi__metric { border-left: 0; border-top: 1px solid var(--line); }
}

/* ════════════ 课程资源库 · B 版（2026-10-26） ════════════
 * 与「工作室总览 / 上进双创看板」同一套：深色总数卡 + 白色四项轨道、细条分布、
 * 浅灰表头 + 文字链接，去掉 KPI 卡顶部那道渐变装饰条。
 * 🔴 全部规则挂在 .page[data-page="course"] 下：详情页 / 两个配置页仍用原 .kpi-grid。
 * ⚠️ Chromium83：不用 flex gap（间距走 grid gap / margin），不用 :has()。 */
.page[data-page="course"] {
  --crs-sub: #6F7488;
  --crs-faint: #98A0B3;
  --crs-line: #E3E7F0;
  --radius-card: 12px;
  --shadow-card: 0 1px 2px rgba(26,26,46,.04);
  --num: "Bahnschrift", "DIN Alternate", "Segoe UI", "Microsoft YaHei", sans-serif;
  gap: 18px;
}
.page[data-page="course"] .col-2 { gap: 18px; }
.page[data-page="course"] .card {
  padding: 18px 20px; border-color: var(--crs-line);
  border-radius: var(--radius-card); box-shadow: var(--shadow-card);
}
.page[data-page="course"] .card__head { min-height: 24px; margin-bottom: 14px; align-items: center; }
.page[data-page="course"] .card__head h3 { font-size: calc(14.5px * var(--fs-scale)); letter-spacing: .005em; }
.page[data-page="course"] .card__head .muted { font-size: calc(12px * var(--fs-scale)); color: var(--crs-faint); }

/* ── 1. KPI 指标带：总数压舱 + 四项指标轨道 ── */
.page[data-page="course"] .course-kpi { display: grid; grid-template-columns: 1.33fr 4fr; gap: 12px; min-height: 132px; }
.page[data-page="course"] .course-kpi__hero {
  background: #1A1A2E; border-radius: var(--radius-card); padding: 17px 22px 15px;
  display: flex; flex-direction: column; min-width: 0;
}
.page[data-page="course"] .course-kpi__label {
  font-size: calc(12.5px * var(--fs-scale)); font-weight: 500; color: #4A4F63; line-height: 1.3;
  white-space: nowrap; overflow: hidden; text-overflow: ellipsis;
}
.page[data-page="course"] .course-kpi__hero .course-kpi__label { color: #A7ADC9; }
.page[data-page="course"] .course-kpi__value {
  margin-top: 8px; font-family: var(--num); font-size: calc(29px * var(--fs-scale)); font-weight: 600;
  line-height: 1.05; color: var(--text-title); letter-spacing: -.015em;
  font-variant-numeric: tabular-nums; white-space: nowrap;
}
/* 「主流技术 = 数据处理与探索」这类文字值：数字字体没中文字形，退回正文字体并压小一档 */
.page[data-page="course"] .course-kpi__value.is-text {
  font-family: var(--font); font-size: calc(19px * var(--fs-scale)); letter-spacing: 0;
  overflow: hidden; text-overflow: ellipsis;
}
.page[data-page="course"] .course-kpi__hero .course-kpi__value { margin-top: 9px; font-size: calc(42px * var(--fs-scale)); letter-spacing: -.02em; color: #fff; }
.page[data-page="course"] .course-kpi__unit {
  font-family: var(--font); font-size: calc(12.5px * var(--fs-scale)); font-weight: 500; color: var(--crs-sub);
  margin-left: 4px; letter-spacing: 0; vertical-align: 1px;
}
.page[data-page="course"] .course-kpi__hero .course-kpi__unit { font-size: calc(13.5px * var(--fs-scale)); color: #B9BFD6; vertical-align: 2px; }
.page[data-page="course"] .course-kpi__split {
  display: flex; height: 4px; border-radius: 999px; overflow: hidden;
  background: rgba(255,255,255,.12); margin-top: auto;
}
.page[data-page="course"] .course-kpi__split span { display: block; height: 100%; }
.page[data-page="course"] .course-kpi__legend {
  display: flex; align-items: center; margin-top: 8px;
  font-size: calc(11px * var(--fs-scale)); color: #A7ADC9; white-space: nowrap; overflow: hidden;
}
.page[data-page="course"] .course-kpi__legend .lg { display: inline-flex; align-items: center; min-width: 0; }
.page[data-page="course"] .course-kpi__legend .lg + .lg { margin-left: 12px; }
.page[data-page="course"] .course-kpi__legend i { width: 6px; height: 6px; border-radius: 50%; flex: 0 0 auto; margin-right: 5px; }
.page[data-page="course"] .course-kpi__legend b {
  font-weight: 600; color: #fff; font-family: var(--num); font-size: calc(11.5px * var(--fs-scale)); margin: 0 2px;
}
.page[data-page="course"] .course-kpi__rail {
  display: grid; grid-template-columns: repeat(4, minmax(0, 1fr));
  background: #fff; border: 1px solid var(--crs-line); border-radius: var(--radius-card);
  box-shadow: var(--shadow-card); overflow: hidden;
}
.page[data-page="course"] .course-kpi__metric { display: flex; flex-direction: column; min-width: 0; padding: 16px 18px 14px; }
.page[data-page="course"] .course-kpi__metric + .course-kpi__metric { border-left: 1px solid var(--line); }
.page[data-page="course"] .course-kpi__metric .course-kpi__label { color: #4A4F63; }
.page[data-page="course"] .course-kpi__extra {
  margin-top: auto; padding-top: 9px; font-size: calc(11.5px * var(--fs-scale)); line-height: 1.35;
  color: var(--crs-sub); white-space: normal;
}

/* ── 2. 三张分布图：各方向可选门数 / 关键技术分布（点一条 = 按它筛下方清单）+ 难度 ── */
.page[data-page="course"] .hbar-list { gap: 10px; }
.page[data-page="course"] .hbar { font-size: calc(12px * var(--fs-scale)); line-height: 1.35; }
.page[data-page="course"] .hbar__name { width: calc(124px * var(--fs-scale)); color: var(--crs-sub); }
.page[data-page="course"] .hbar__track { height: 6px; border-radius: 999px; background: #F1F4FA; }
.page[data-page="course"] .hbar__track i { border-radius: 999px; opacity: .9; }
.page[data-page="course"] .hbar--btn.is-on .hbar__track i { opacity: 1; }
.page[data-page="course"] .hbar__val { width: calc(34px * var(--fs-scale)); font-family: var(--num); font-size: calc(12.5px * var(--fs-scale)); }

/* ── 3. 清单卡：筛选条、表格、分页器都收在同一张卡里 ── */
.page[data-page="course"] .chart-foot { font-size: calc(11.5px * var(--fs-scale)); color: var(--crs-faint); }
.page[data-page="course"] .filter-bar { margin-bottom: 14px; }
.page[data-page="course"] .filter-bar .select {
  width: calc(132px * var(--fs-scale)); height: calc(32px * var(--fs-scale)); font-size: calc(12px * var(--fs-scale));
}
.page[data-page="course"] .filter-bar .input { height: calc(32px * var(--fs-scale)); font-size: calc(12.5px * var(--fs-scale)); }
.page[data-page="course"] .filter-bar .btn { height: calc(32px * var(--fs-scale)); font-size: calc(12px * var(--fs-scale)); }
/* 每页只有 12 行，交给翻页器限行；再套 58vh 上限会出现「卡内滚动 + 下方翻页器」双滚动，
 * 用户以为还有下一页。这里放开高度（table-wrap--none 的同口径，写在页面作用域里）。 */
.page[data-page="course"] .table-wrap { border-color: var(--crs-line); border-radius: 10px; max-height: none; }
.page[data-page="course"] .table thead th {
  background: #FAFBFD; color: var(--crs-faint); font-weight: 500; font-size: calc(11px * var(--fs-scale)); padding: 9px 12px;
}
.page[data-page="course"] .table tbody td { font-size: calc(12.5px * var(--fs-scale)); padding: 9px 12px; }
.page[data-page="course"] .table tbody tr:hover { background: #FAFBFD; }
/* 「N 室」保留蓝底胶囊但压小一档：整列都是同一形状时，胶囊才读得出是计数而不是标签 */
.page[data-page="course"] .table .pill {
  height: calc(19px * var(--fs-scale)); padding: 0 7px; margin: 0; border-radius: 4px;
  font-size: calc(10.5px * var(--fs-scale)); font-weight: 500; line-height: calc(19px * var(--fs-scale));
}
.page[data-page="course"] .table .stars { font-size: calc(12px * var(--fs-scale)); }
.page[data-page="course"] .geo-pager { border-top: 1px solid var(--crs-line); }

@media (max-width: 1180px) {
  .page[data-page="course"] .course-kpi { grid-template-columns: minmax(0, 1fr); }
  .page[data-page="course"] .course-kpi__rail { grid-template-columns: repeat(2, minmax(0, 1fr)); }
  .page[data-page="course"] .course-kpi__metric:nth-child(3) { border-left: 0; }
  .page[data-page="course"] .course-kpi__metric:nth-child(n+3) { border-top: 1px solid var(--line); }
}
@media (max-width: 900px) {
  .page[data-page="course"] .course-kpi__rail { grid-template-columns: minmax(0, 1fr); }
  .page[data-page="course"] .course-kpi__metric + .course-kpi__metric { border-left: 0; border-top: 1px solid var(--line); }
  .page[data-page="course"] .col-2 { grid-template-columns: minmax(0, 1fr); }
}

/* ════════════ 界面字号档位适配（系统设置 › 基础设置 › 界面字号） ════════════
 * 字号本身由 --fs-scale 统一驱动（全站 font-size 一律 calc(基准 × --fs-scale)，
 * 见 tokens.css）；这里管的是「放大之后怎么排」：
 *   · 原本靠单行省略号的次要文字改成折行 —— 字号档位不该把信息截掉；
 *   · 5 列 KPI 墙改成 3 列 —— 大档下每张卡只剩半行宽，宁可多一行。
 * 档位标记挂在 <html data-fs>：std 标准 / big 大 / xl 特大。间距令牌不跟着放大，
 * 版面密度靠这两条规则兜住。 */
html[data-fs="big"] .kpi__label, html[data-fs="big"] .kpi__extra,
html[data-fs="xl"] .kpi__label, html[data-fs="xl"] .kpi__extra { white-space: normal; }
html[data-fs="big"] .kpi-grid, html[data-fs="xl"] .kpi-grid { grid-template-columns: repeat(3, minmax(0, 1fr)); }
html[data-fs="big"] .kpi-grid > :nth-child(4),
html[data-fs="xl"] .kpi-grid > :nth-child(4) { grid-column: span 2; }

/* ════════════ 帮助中心（顶栏「帮助中心」入口） ════════════
 * 文档式排版：整页是一张白纸（白底 + 浅边框 + 大圆角），左侧目录常驻（细分隔线，
 * 滚动高亮当前节），右侧单栏正文限宽 760px。节与节之间用细分隔线 + 32px 上留白
 * 拉开，不再用一摞卡片——卡片留白会把长文割碎；白底是为了长文阅读不刺眼。 */
.help {
  display: grid;
  grid-template-columns: calc(196px * var(--fs-scale)) minmax(0, 1fr);
  column-gap: var(--sp-8);
  max-width: 1120px;
  margin: 0 auto;
  padding: var(--sp-7) var(--sp-8);
  background: var(--bg-card);
  border: var(--border);
  border-radius: var(--radius-card);
  box-shadow: var(--shadow-card);
  align-items: start;
}
.help-toc {
  position: sticky; top: var(--sp-2); align-self: start;
  padding: 0 var(--sp-5) var(--sp-4) 0;
  border-right: 1px solid var(--line);
}
.help-toc__label {
  font-size: var(--fs-xs); color: var(--text-sub); letter-spacing: .1em;
  padding: 0 var(--sp-3) var(--sp-3);
}
.help-toc__item {
  display: flex; align-items: baseline; margin-bottom: 2px;
  padding: 7px var(--sp-3); border-radius: var(--radius-sm);
  font-size: var(--fs-sm); line-height: 1.5; color: var(--text-body);
  text-decoration: none; cursor: pointer;
}
.help-toc__item:hover { background: var(--bg-hover); color: var(--text-title); }
.help-toc__item.is-active { background: var(--brand-soft); color: var(--brand-strong); font-weight: var(--fw-semibold); }
.help-toc__no {
  flex: 0 0 auto; width: calc(22px * var(--fs-scale));
  font-family: Consolas, "Courier New", monospace; font-size: calc(11px * var(--fs-scale));
  color: var(--text-placeholder);
}
.help-toc__item.is-active .help-toc__no { color: var(--brand); }
.help-toc__text { min-width: 0; }

.help-doc { min-width: 0; max-width: 760px; }
.help-doc__head { padding-bottom: var(--sp-2); }
.help-doc__head h2 { font-size: calc(22px * var(--fs-scale)); font-weight: var(--fw-semibold); color: var(--text-title); line-height: 1.4; }
.help-doc__head p { margin: var(--sp-3) 0 0; font-size: var(--fs-md); line-height: 1.85; color: var(--text-body); }
.help-doc__meta { margin-top: var(--sp-3); font-size: var(--fs-xs); color: var(--text-sub); }

.help-sec { padding-top: var(--sp-7); scroll-margin-top: var(--sp-5); }
.help-sec + .help-sec { margin-top: var(--sp-7); border-top: 1px solid var(--line); }
.help-sec__title { display: flex; align-items: baseline; font-size: var(--fs-lg); font-weight: var(--fw-semibold); color: var(--text-title); line-height: 1.5; }
.help-sec__no {
  flex: 0 0 auto; width: calc(28px * var(--fs-scale));
  font-family: Consolas, "Courier New", monospace; font-size: calc(12px * var(--fs-scale));
  color: var(--brand); font-weight: var(--fw-semibold); letter-spacing: .02em;
}
/* 正文纵向节奏：所有块之间 16px，避免长文挤成一坨 */
.help-sec__body { margin-top: var(--sp-3); }
.help-sec__body > * + * { margin-top: var(--sp-4); }
.help-sec__body p { margin: 0; font-size: var(--fs-md); line-height: 1.85; color: var(--text-body); }
.help-sub {
  font-size: var(--fs-md); font-weight: var(--fw-semibold); color: var(--text-title); line-height: 1.6;
}
.help-sec__body > .help-sub { margin-top: var(--sp-6); }
.help-list { margin: 0; padding-left: 22px; }
.help-list li { font-size: var(--fs-md); line-height: 1.85; color: var(--text-body); }
.help-list li + li { margin-top: 6px; }
.help-list li::marker { color: var(--text-placeholder); }
.help-list--num li::marker { color: var(--brand); font-weight: var(--fw-semibold); }
.help-note {
  font-size: var(--fs-sm); line-height: 1.85; color: var(--text-body);
  background: var(--bg-sunken); border-left: 3px solid var(--brand);
  border-radius: var(--radius-sm); padding: var(--sp-3) var(--sp-4);
}
.help-note b { color: var(--text-title); }
.help-note--warn { background: var(--warn-soft); border-left-color: var(--warn); }
.help-code {
  font-family: Consolas, "Courier New", monospace;
  background: var(--bg-sunken); border-radius: 4px; padding: 1px 6px;
  font-size: calc(12.5px * var(--fs-scale)); color: var(--text-title); word-break: break-all;
}
/* 名词解释式清单：行间用细分隔线，读起来像文档里的定义表 */
.help-kv { display: grid; grid-template-columns: calc(148px * var(--fs-scale)) minmax(0, 1fr); column-gap: var(--sp-4); margin: 0; }
.help-kv dt, .help-kv dd { padding: 10px 0; border-top: 1px solid var(--line); }
.help-kv dt:first-of-type, .help-kv dd:first-of-type { padding-top: 0; border-top: 0; }
.help-kv dt { font-size: var(--fs-sm); color: var(--text-title); font-weight: var(--fw-semibold); line-height: 1.75; }
.help-kv dd { margin: 0; font-size: var(--fs-sm); color: var(--text-body); line-height: 1.8; }
.help-doc .table-wrap { max-height: none; }
.help-doc .table-wrap td, .help-doc .table-wrap th { line-height: 1.75; }
.help-navtbl td:first-child, .help-navtbl th:first-child { white-space: nowrap; width: calc(96px * var(--fs-scale)); }
.help-navtbl td:nth-child(2), .help-navtbl th:nth-child(2) { white-space: nowrap; width: calc(110px * var(--fs-scale)); }
.help-faq td:first-child { width: calc(200px * var(--fs-scale)); color: var(--text-title); font-weight: var(--fw-semibold); }
@media (max-width: 1100px) {
  .help { grid-template-columns: minmax(0, 1fr); padding: var(--sp-5); }
  .help-toc {
    position: static; display: flex; flex-wrap: wrap; align-items: center;
    padding: 0 0 var(--sp-4); border-right: 0; border-bottom: 1px solid var(--line);
  }
  .help-toc__label { display: none; }
  .help-toc__item { margin: 0 var(--sp-2) var(--sp-2) 0; border: 1px solid var(--line); }
  .help-toc__item.is-active { border-color: transparent; }
  .help-toc__no { width: auto; margin-right: 6px; }
  .help-doc { margin-top: var(--sp-5); }
  .help-kv { grid-template-columns: minmax(0, 1fr); }
  .help-kv dd { padding-top: 0; border-top: 0; }
  .help-faq td:first-child { width: auto; }
}
