/* ============================================================
   星际词元 · 全站共享样式
   ------------------------------------------------------------
   两套皮肤，一套令牌：
     · 默认（深色霓虹）—— 营销首页用，负责"镇住人"
     · body.theme-light —— 工具页用（市场/控制台/文档/榜单/详情/登录/供应商/后台），
       负责"安静地查数据、比价格"
   所有颜色一律走语义令牌，页面里不写死颜色，换肤只需换令牌。
   零外部依赖：不使用 Tailwind CDN、不引外部字体。
   ============================================================ */

/* ---------- 令牌：深色（默认） ---------- */
:root{
  --bg:#0a0a0f; --card:#111118; --card2:#101018; --code-bg:#07070c; --opt-bg:#14141c;
  --ink:#ffffff; --sub:rgba(255,255,255,.55); --sub2:rgba(255,255,255,.75); --dim:rgba(255,255,255,.34);
  --ph:rgba(255,255,255,.32); --icon:rgba(255,255,255,.42); --dot:rgba(255,255,255,.25);
  --line:rgba(255,255,255,.08); --line2:rgba(255,255,255,.045); --line3:rgba(255,255,255,.06);
  --line4:rgba(255,255,255,.12); --line5:rgba(255,255,255,.16); --linkline:rgba(255,255,255,.18);
  --fill:rgba(255,255,255,.04); --fill2:rgba(255,255,255,.02); --fill3:rgba(255,255,255,.035);
  --fill4:rgba(255,255,255,.05); --hover:rgba(255,255,255,.032); --glass:rgba(255,255,255,.03);
  --sheen:rgba(255,255,255,.012); --sheen2:rgba(255,255,255,.018); --grid:rgba(255,255,255,.026);
  --nav-bg:rgba(10,10,15,.82); --panel-bg:rgba(5,5,9,.72);
  --cyan:#00e5ff; --cyan-rgb:0,229,255;
  /* 2026-10-03 新增「导航/强调青」令牌：深底用亮青（首页导航底色 rgba(10,10,15,.82)），
     浅底用 #0891b2（内页导航底色白，亮青在白底上对比度仅 1.9 不可用）。
     用户要求「导航 hover 改成首页一样的青色」—— 是要那个**视觉意图**，
     不是照抄色号：同一个 #00e5ff 在两种底色上的可读性完全相反。 */
  --cyan-nav:#00e5ff; --cyan-nav-rgb:0,229,255;
  --purple:#c471f5; --purple-rgb:196,113,245;
  --green:#39ff14; --green-rgb:57,255,20;
  --pink:#ff2d95; --pink-rgb:255,45,149;
  --amber:#ffb020; --amber-rgb:255,176,32;
  --red:#ff4d6d; --red-rgb:255,77,109;
  --grad:linear-gradient(135deg,#00e5ff,#c471f5);
  --glow-grad:linear-gradient(135deg,#00e5ff,#c471f5 55%,#00e5ff);
  --btn-grad:linear-gradient(135deg,#0e7490,#0a5a6e); --btn-ink:#fff;
  /* 2026-10-03 与浅底同批改：--btn-ink 深色字 → 白字，且亮端一起压深。
     #fff 压 #00e5ff 只有 1.54:1（首页深底上更亮，属"看不清"），
     压到 #0e7490 是 5.36:1，达标。
     ⚠ 首页 .btn-cyan 在 index.html 内联样式里另有一份覆盖（不读本令牌），两处必须同改。 */
  --btn2-grad:linear-gradient(135deg,#c471f5,#7c3aed); --btn2-ink:#fff;
  --r:18px; --r-sm:12px; --r-xs:9px; --shadow:none; --shadow-lift:none;
}

/* ---------- 令牌：浅色（工具页） ---------- */
body.theme-light{
  --bg:#f5f6f8; --card:#ffffff; --card2:#ffffff; --code-bg:#0f172a; --opt-bg:#ffffff;
  --ink:#12161c; --sub:#6b7280; --sub2:#3f4653; --dim:#98a1ad;
  --ph:#a8b0bb; --icon:#8d96a3; --dot:#cbd2da;
  --line:rgba(18,22,28,.10); --line2:rgba(18,22,28,.065); --line3:rgba(18,22,28,.08);
  --line4:rgba(18,22,28,.14); --line5:rgba(18,22,28,.18); --linkline:rgba(18,22,28,.2);
  --fill:rgba(18,22,28,.035); --fill2:rgba(18,22,28,.022); --fill3:rgba(18,22,28,.05);
  --fill4:rgba(18,22,28,.06); --hover:rgba(18,22,28,.028); --glass:#ffffff;
  --sheen:#fafbfc; --sheen2:#f8f9fb; --grid:rgba(18,22,28,.035);
  --nav-bg:rgba(255,255,255,.86); --panel-bg:rgba(18,22,28,.42);
  --cyan:#0e7490; --cyan-rgb:14,116,144;
  /* 浅底专用导航/强调青（对比度 3.68:1，达 WCAG 大字 3:1）。
     深色页的亮青 #00e5ff 在白底上只有 1.9:1，hover 几乎看不出变化。 */
  --cyan-nav:#0891b2; --cyan-nav-rgb:8,145,178;
  --purple:#7c3aed; --purple-rgb:124,58,237;
  --green:#0f9960; --green-rgb:15,153,96;
  --pink:#db2777; --pink-rgb:219,39,119;
  --amber:#b45309; --amber-rgb:180,83,9;
  --red:#dc2626; --red-rgb:220,38,38;
  --grad:linear-gradient(135deg,#06b6d4,#7c3aed);
  --glow-grad:linear-gradient(135deg,#0e7490,#7c3aed 55%,#0e7490);
  --btn-grad:linear-gradient(135deg,#0e7490,#0a5a6e); --btn-ink:#fff;
  /* 2026-10-03 用户指令「这个色块的文字全改白」→ 连带必须压深底色，否则白字不可读。
     实算对比度：#fff 压 #22d3ee 只有 1.81:1（WCAG AA 正文需 4.5:1，属"看不清"）；
     压到 #0e7490 是 5.36:1，达标。所以 --btn-grad 的亮端从 #22d3ee 收到 #0e7490。
     代价：按钮的"亮青跳色"没了，整体偏深青 —— 这是"文字可读"的必要代价，不是审美选择。 */
  --btn2-grad:linear-gradient(135deg,#8b5cf6,#6d28d9); --btn2-ink:#fff;
  --r:14px; --r-sm:10px; --r-xs:8px;
  --shadow:0 1px 3px rgba(18,22,28,.055),0 1px 2px rgba(18,22,28,.035);
  --shadow-lift:0 6px 22px rgba(18,22,28,.09);
}

/* ============================================================
   尺度令牌（Design Scale）· 与主题无关，只定义一次
   ------------------------------------------------------------
   设计精致度 = 尺度分辨率 × 细节层数，不是装饰数量。
   圆角/字号/行高/字重/字距/间距/阴影 全部按"角色"分档，
   **组件里禁止再写裸像素**（随手写 px 就是尺度崩坏的起点）。
   基准：对标主流商业站点实测值（圆角 6 阶 / 字号跨到 40px /
   行高锁像素 / 阴影多层叠加 / 过渡 .15s 级）。
   ============================================================ */
:root{
  /* 字号阶：11 微标 → 40 展示标题，共 12 档。
     关键：**必须有大字层**（26/30/34/40）—— 只在 12~25px 区间打转
     会让页面永远"像文档"，没有视觉重音。 */
  --fs-cap:11px; --fs-xs:12px; --fs-sm:13px; --fs-base:14px; --fs-md:15px;
  --fs-lg:16px; --fs-xl:18px; --fs-2xl:20px; --fs-3xl:22px;
  --fs-4xl:26px; --fs-5xl:30px; --fs-6xl:34px; --fs-dpy:40px;
  /* 数字展示阶：营销页的数据重音（比正文阶高两档，专门给大数字） */
  --fs-num-sm:32px; --fs-num:36px;
  /* 展示阶上限（2026-10-02 补）：全局 h1 用的是 clamp(30px,4.4vw,46px)，
     而 46 这个上限此前**不在任何令牌里** —— 于是 index 的 hero-brand、
     login 的 .av-title 都各自硬写 46px，改主题时三处不同步。
     现在把展示层的常用落点提成令牌：h1 上限 46、首页 hero 上限 84、
     首页 h1 上限 68、大数字 76、副题 19。clamp() 里也一律引用变量。 */
  --fs-dpy2:46px; --fs-dpy-xl:76px; --fs-dpy-2xl:84px; --fs-dpy-lg:68px;
  --fs-xl-plus:19px; --fs-dpy-sm:33px; --fs-dpy-md:42px;

  /* 行高：**为每个字号锁定像素值**。
     用无单位比例（1.6）会让行高随字号漂移，大字上必然失控；
     锁像素是专业排版与业余排版的分水岭。 */
  --lh-cap:16px; --lh-xs:18px; --lh-sm:20px; --lh-base:22px; --lh-md:24px;
  --lh-lg:26px; --lh-xl:28px; --lh-2xl:30px; --lh-3xl:32px;
  --lh-4xl:34px; --lh-5xl:38px; --lh-6xl:42px; --lh-dpy:48px;
  --lh-num-sm:38px; --lh-num:42px;

  /* 字距：与字号**反向** —— 大字收紧、小字放开。
     这是"高级感"最廉价也最有效的一招，缺了就等于没排版。 */
  --ls-dpy:-.6px; --ls-title:-.4px; --ls-sub:-.2px; --ls-body:0;
  --ls-label:.06em; --ls-cap:.14em;

  /* 字重：中文忌用 800/900（粗笨、糊字）；300 给大标题留轻盈余地 */
  --fw-light:300; --fw-reg:400; --fw-med:500; --fw-semi:600; --fw-bold:700;

  /* 圆角阶：按**元件体积**分配，不是随手取整 */
  --r-chip:6px;     /* 标签、徽标、小徽章 */
  --r-ctl:8px;      /* 输入框、小按钮 */
  --r-ctl-lg:10px;  /* 常规按钮 */
  --r-card:12px;    /* 卡片、面板、表格容器 */
  --r-card-lg:16px; /* 大容器、模态框、抽屉 */
  --r-panel:22px;   /* 整块区块（页级大容器） */
  --r-pill:999px;   /* 胶囊 */

  /* 间距阶：4px 网格，10 档 */
  --sp-1:4px; --sp-2:6px; --sp-3:8px; --sp-4:12px; --sp-5:16px;
  --sp-6:20px; --sp-7:24px; --sp-8:32px; --sp-9:40px; --sp-10:48px;

  /* 缓动：时长 .12~.24s，**只用 out 曲线**（快起慢收 = 跟手） */
  --e-out:cubic-bezier(.22,.61,.36,1);
  --e-in:cubic-bezier(.55,.06,.68,.19);
  --t-fast:.12s; --t-base:.15s; --t-slow:.24s;
}

/* 阴影体系：**4 层叠加**（接触影 + 主投影 + 环境影 + 内高光）。
   单层投影 = 贴纸感；多层叠加 = 实体感。这是精致度的物质基础。 */
:root{
  --sh-contact:0 1px 2px rgba(0,0,0,.55);
  --sh-raise:0 1px 2px rgba(0,0,0,.5),0 4px 12px rgba(0,0,0,.34);
  --sh-lift:0 2px 4px rgba(0,0,0,.44),0 10px 26px rgba(0,0,0,.4);
  --sh-over:0 6px 14px rgba(0,0,0,.5),0 24px 56px rgba(0,0,0,.46);
  --sh-hair:inset 0 1px 0 rgba(255,255,255,.05);
  --sh-ring:0 0 0 1px rgba(255,255,255,.07);
}
body.theme-light{
  /* 浅色投影带**一点主色调偏移**（比纯灰投影高级），并锁在极低透明度 */
  --sh-contact:0 1px 2px rgba(18,22,28,.05);
  --sh-raise:0 1px 2px rgba(18,22,28,.05),0 3px 8px rgba(18,22,28,.045);
  --sh-lift:0 1px 3px rgba(18,22,28,.055),0 5px 14px rgba(18,22,28,.065),
            0 14px 28px -10px rgba(14,116,144,.11);
  --sh-over:0 2px 6px rgba(18,22,28,.07),0 10px 28px rgba(18,22,28,.09),
            0 28px 56px -18px rgba(14,116,144,.15);
  --sh-hair:inset 0 1px 0 #fff;
  --sh-ring:0 0 0 1px rgba(18,22,28,.055);
}

/* 令牌归一：把历史遗留的 3 个圆角别名接到尺度阶上 —— 全站圆角立刻有体积分工 */
:root,body.theme-light{--r:var(--r-card-lg);--r-sm:var(--r-ctl-lg);--r-xs:var(--r-chip)}

*{margin:0;padding:0;box-sizing:border-box}
html{scroll-behavior:smooth}
body{font-family:"PingFang SC","Microsoft YaHei","Segoe UI",sans-serif;background:var(--bg);color:var(--ink);
  font-size:var(--fs-base);line-height:var(--lh-base);letter-spacing:var(--ls-body);
  font-variant-numeric:tabular-nums;font-feature-settings:"tnum" 1;
  overflow-x:hidden;-webkit-font-smoothing:antialiased;-moz-osx-font-smoothing:grayscale;
  text-rendering:optimizeLegibility;min-height:100vh}
/* 标题层 h1~h4 统一定义在本文件 §216 处（只定义一次，避免同名互相覆盖） */
/* 数字/代码统一等宽对齐（价格、延迟、成功率逐位对齐 = 专业感） */
.mono,.num,table td,table th,code,kbd{font-variant-numeric:tabular-nums}
a{text-decoration:none;color:inherit}
button,input,select,textarea{font-family:inherit}
.wrap{max-width:1560px;margin:0 auto;padding:0 28px}
/* 2026-10-02 三轮调整的最终值（1180 → 1028）：
   ① 852 太窄 → 用户要求放宽（已做 1180）；
   ② 1180 之后用户指出两页「卡片往中间收一下、卡片里的内容宽度要类似，
      不能有的收进来有的宽很多」—— 病根不是某个面板的 padding，
      而是"整页容器 1132，但非 flush 内容被压成 900 居中列、flush 表格仍满宽 1130"
      这套自相矛盾的规则（同页两种宽度）。
   正解：宽度只由容器一个来源控制。容器收到 1028 → panel 980 →
   面板内容统一 914px（.panel-b 的 --sp-8 左右内边距），
   满宽表格 978px，与内容列只差 64px（6.5%），肉眼看是同一档宽度。
   低于 900px 也不行：supplier 报价表 8 列 min-width:900px，
   收窄会把横向滚动条逼到卡片外。 */
.wrap-narrow{max-width:1028px;margin:0 auto;padding:0 24px}
/* 正文阅读宽度上限：容器内纯文字块的行长封顶。
   860 不是随手取的 —— 内容列 914px 留 54px 余量，视觉上仍读成"同一档宽度"，
   同时把中文行长压到约 60 字以内（>70 字明显难读）。
   之前的 720 离内容列差了 194px，正是用户说的"有的收进来、有的宽很多"。 */
.readable{max-width:860px}
.mono{font-family:"JetBrains Mono",Consolas,monospace}

/* 氛围层（仅深色页可见） */
.grid-bg{position:fixed;inset:0;z-index:0;pointer-events:none;
  background-image:linear-gradient(var(--grid) 1px,transparent 1px),
    linear-gradient(90deg,var(--grid) 1px,transparent 1px);
  background-size:60px 60px;animation:gridPulse 7s ease-in-out infinite}
@keyframes gridPulse{0%,100%{opacity:.45}50%{opacity:.9}}
.orb{position:fixed;border-radius:50%;filter:blur(90px);pointer-events:none;z-index:0}
.beam{position:fixed;inset:0;z-index:0;pointer-events:none;overflow:hidden}
.beam i{position:absolute;left:-60%;width:200%;height:1.5px;opacity:0;animation:beamSweep linear infinite}
.beam i::before{content:'';position:absolute;inset:0;
  background:linear-gradient(90deg,transparent 0%,var(--bc) 30%,transparent 62%,transparent 100%)}
.beam i:nth-child(1){top:30%;--bc:rgba(var(--cyan-rgb),.16);--r:-12deg;animation-duration:19s}
.beam i:nth-child(2){top:64%;--bc:rgba(var(--purple-rgb),.13);--r:8deg;animation-duration:24s;animation-delay:7s}
.beam i:nth-child(3){top:84%;--bc:rgba(var(--cyan-rgb),.09);--r:-5deg;animation-duration:28s;animation-delay:13s}
@keyframes beamSweep{0%{transform:translateX(-30%) rotate(var(--r));opacity:0}5%{opacity:1}
  88%{opacity:1}100%{transform:translateX(80%) rotate(var(--r));opacity:0}}
/* 浅色工具页：关掉全部氛围层（审美层与效率层分家） */
body.theme-light .grid-bg,
body.theme-light .beam,
body.theme-light .orb,
body.theme-light #galaxy{display:none!important}

/* 玻璃卡（浅色下退化为白卡 + 细描边 + 极淡阴影） */
.glass{background:var(--glass);backdrop-filter:blur(18px);
  -webkit-backdrop-filter:blur(18px);border:1px solid var(--line3);border-radius:var(--r);
  box-shadow:var(--sh-raise),var(--sh-hair)}
.card{padding:var(--sp-7);position:relative;z-index:2}

/* 导航 */
nav{position:fixed;top:0;left:0;right:0;z-index:60;background:var(--nav-bg);
  backdrop-filter:blur(20px);border-bottom:1px solid var(--line3)}
.nav-in{display:flex;align-items:center;justify-content:space-between;height:64px}
.logo{display:flex;align-items:center;gap:var(--sp-3);font-weight:var(--fw-bold);
  font-size:var(--fs-xl);letter-spacing:var(--ls-sub)}
.logo-dot{width:30px;height:30px;border-radius:var(--r-xs);background:var(--grad);display:grid;place-items:center;
  color:#fff;font-size:var(--fs-sm);font-weight:var(--fw-bold)}
/* 2026-09-25：品牌 logo 换为官方组合图（头盔 + TOKASTRA 字标，透明底）。
   深浅导航用两张变体图切换：白字版（深色导航首页）/ 深字版（theme-light 浅色工具页与登录页） */
.logo-img{height:28px;width:auto;display:block}
/* 内页浅色版构图更紧（留白少+实心图标重），同高显大——按组合占宽对齐首页（33px≈首页 38px 时的 188px 宽） */
.logo-img.li-on-light{height:33px}
.logo-img.li-on-light{display:none}
body.theme-light .logo-img.li-on-dark{display:none}
body.theme-light .logo-img.li-on-light{display:block}
.nav-links{display:flex;gap:var(--sp-7);font-size:var(--fs-base);color:var(--sub2)}
.nav-links a{position:relative;padding:6px 0}  /* 2026-10-01 体检：文字链触达仅 22px 高，补点击区（视觉零变化） */
/* 2026-10-03 用户指令：「顶栏目录的鼠标触碰变色，也改成首页一样的颜色，青色」。
   原来 hover/选中都是 var(--cyan)，浅色页上是 #0e7490（压暗版），在白底导航上偏灰、变化不明显。
   改为走 --cyan-nav 令牌：**深底（首页）亮青 / 浅底（内页）#0891b2**，各自可读。
   ⚠ 为什么不用同一个色号：首页导航底色 rgba(10,10,15,.82) 深色，#00e5ff 跳；
     内页 nav-bg rgba(255,255,255,.86) 白色，#00e5ff 对比度仅 1.9:1（WCAG 1.4.11 最低 3:1），
     hover 几乎看不出变化。要的是那个**视觉意图**，不是照抄色号。 */
.nav-links a:hover{color:var(--cyan-nav)}
.nav-links a.on{color:var(--cyan-nav);font-weight:var(--fw-semi)}
/* 2026-09-30：当前项底部横线指示（用户参考竞品图）——短青线贴近导航底边，带微光晕
   2026-10-03：横线色同步换成 #0891b2（与上方文字同色），否则深青文字配亮青横线会不协调。 */
.nav-links a.on::after{content:'';position:absolute;left:50%;transform:translateX(-50%);
  bottom:-7px;width:30px;height:3px;border-radius:2px;background:var(--cyan-nav);
  box-shadow:0 0 8px rgba(var(--cyan-nav-rgb),.5)}
.nav-cta{display:flex;align-items:center;gap:var(--sp-5)}
/* 2026-09-30：导航 CTA 色块收敛（用户反馈进入交易市场偏大）——
   作用域锁 .nav-cta，首页静态/内页动态导航的青色按钮统一缩一档 */
.nav-cta .btn{padding:6px 14px;font-size:12.5px;border-radius:var(--r-ctl)}
.nav-cta .who{font-size:var(--fs-sm);color:var(--sub2);max-width:150px;overflow:hidden;
  text-overflow:ellipsis;white-space:nowrap}
.btn{display:inline-flex;align-items:center;justify-content:center;gap:var(--sp-3);border-radius:var(--r-sm);
  padding:11px var(--sp-7);font-size:var(--fs-base);line-height:var(--lh-sm);font-weight:var(--fw-semi);
  letter-spacing:var(--ls-body);cursor:pointer;border:none;position:relative;overflow:hidden;
  transition:transform var(--t-base) var(--e-out),box-shadow var(--t-base) var(--e-out),
    background-color var(--t-base) var(--e-out),border-color var(--t-base) var(--e-out),color var(--t-base) var(--e-out)}
.btn-cyan{background:var(--btn-grad);color:var(--btn-ink);box-shadow:var(--sh-contact)}
.btn-cyan:hover{transform:translateY(-1px);box-shadow:0 4px 16px rgba(var(--cyan-rgb),.42),0 1px 2px rgba(0,0,0,.3)}
.btn-ghost{background:var(--fill4);border:1px solid var(--line4);color:var(--ink)}
.btn-ghost:hover{background:var(--fill4);border-color:rgba(var(--cyan-rgb),.5);color:var(--cyan)}
.btn-purple{background:var(--btn2-grad);color:var(--btn2-ink);box-shadow:var(--sh-contact)}
.btn-purple:hover{transform:translateY(-1px);box-shadow:0 4px 16px rgba(var(--purple-rgb),.42),0 1px 2px rgba(0,0,0,.3)}
.btn-danger{background:rgba(var(--red-rgb),.1);border:1px solid rgba(var(--red-rgb),.35);color:var(--red)}
.btn-danger:hover{background:rgba(var(--red-rgb),.18)}
.btn-sm{padding:8px var(--sp-5);font-size:var(--fs-sm);border-radius:var(--r-ctl)}
.btn-xs{padding:5px 11px;font-size:var(--fs-xs);border-radius:var(--r-chip)}
.btn:disabled{opacity:.5;cursor:not-allowed;transform:none!important;box-shadow:none!important}

/* 页头 / 标题 / 副文案 / 区块标题：统一定义在文件末尾「内页设计系统」 */
/* 首页（深色）标题层：h1 用流体字号撑住营销页的分量 */
.eyebrow{display:inline-block;font-size:var(--fs-xs);font-weight:var(--fw-bold);
  letter-spacing:var(--ls-cap);text-transform:uppercase;color:var(--purple);
  margin-bottom:var(--sp-4)}   /* 深色首页；浅色工具页见 .theme-light 覆盖 */
/* 全站 h1 是**所有内页标题的唯一来源**（2026-10-02 把上限 46 提成令牌）。
   改这一行 = 同时改 rank/model/docs/supplier 四页标题，别处不许再硬写 46。 */
h1{font-size:clamp(30px,4.4vw,var(--fs-dpy2));font-weight:var(--fw-bold);letter-spacing:-.024em;line-height:1.16}
h2{font-size:var(--fs-3xl);font-weight:var(--fw-semi);letter-spacing:var(--ls-title);line-height:var(--lh-xl)}
h3{font-size:var(--fs-lg);font-weight:var(--fw-semi);letter-spacing:var(--ls-sub)}
h4{font-size:var(--fs-base);font-weight:var(--fw-semi);letter-spacing:var(--ls-sub)}
/* 2026-10-02 收编浏览器默认 `small{font-size:smaller}`。
   这是全站最隐蔽的一处字号逃逸：**没有任何一行代码写过它**，但 UA 样式
   让所有 <small> 按 0.83em 随父级漂移 —— 于是同一个 <small> 在表头
   （父 11px）里是 9px、在 KPI 数值（父 20px）里是 17px、在正文里是 12px。
   换父级就换字号，「同一元素跨页不一致」的病根就在这条默认规则里。
   改法不是逐处覆盖，而是给它一个绝对基线，让 <small> 从此只有一个字号。 */
small{font-size:var(--fs-cap)}
/* 断行质量：标题用 balance（末行不留一两个孤字），正文用 pretty（避免孤行）。
   零成本、零额外元素 —— 这是"精致"里最容易被忽略、又最容易见效的一条。 */
h1,h2,h3,.h2{text-wrap:balance}
p,.lead{text-wrap:pretty}
.glow-text{background:var(--glow-grad);background-size:200% auto;
  -webkit-background-clip:text;background-clip:text;-webkit-text-fill-color:transparent;
  animation:shimmer 5s linear infinite}
@keyframes shimmer{0%{background-position:-200% center}100%{background-position:200% center}}

/* KPI 数据带：见末尾「内页设计系统」第 2 节 */

/* 工具条 */
.toolbar{display:flex;align-items:center;gap:var(--sp-5);margin:var(--sp-7) 0 var(--sp-5);
  flex-wrap:wrap;position:relative;z-index:2}
.search{flex:1;min-width:240px;position:relative}
.search input{width:100%;background:var(--fill);border:1px solid var(--line);
  border-radius:var(--r-ctl);padding:11px var(--sp-5) 11px 40px;color:var(--ink);
  font-size:var(--fs-base);outline:none;transition:border-color var(--t-base) var(--e-out),
    background-color var(--t-base) var(--e-out),box-shadow var(--t-base) var(--e-out)}
.search input:focus{border-color:rgba(var(--cyan-rgb),.5);background:rgba(var(--cyan-rgb),.05)}
.search input::placeholder{color:var(--ph)}
.search svg{position:absolute;left:13px;top:50%;transform:translateY(-50%);opacity:.45;color:var(--icon)}
.tabs{display:flex;gap:var(--sp-2);background:var(--fill3);border:1px solid var(--line);
  border-radius:var(--r-ctl);padding:5px;flex-wrap:wrap}
.tabs button{background:none;border:none;color:var(--sub);font-size:var(--fs-sm);
  font-weight:var(--fw-med);padding:8px var(--sp-5);border-radius:var(--r-chip);cursor:pointer;
  transition:background-color var(--t-base) var(--e-out),color var(--t-base) var(--e-out)}
.tabs button.on{background:rgba(var(--cyan-rgb),.12);color:var(--cyan)}
.tabs button:hover:not(.on){color:var(--ink)}
select.sort{background:var(--fill);border:1px solid var(--line);color:var(--sub2);
  border-radius:var(--r-ctl);padding:11px var(--sp-4);font-size:var(--fs-sm);outline:none;cursor:pointer}
select.sort option{background:var(--opt-bg);color:var(--ink)}

/* 胶囊搜索（页头内） */
.pillsearch{position:relative;max-width:620px;margin:26px auto 0}
.pillsearch input{width:100%;background:var(--card);border:1px solid var(--line4);
  border-radius:var(--r-pill);padding:15px 116px 15px 47px;color:var(--ink);
  font-size:var(--fs-base);outline:none;box-shadow:var(--sh-raise),var(--sh-hair);
  transition:border-color var(--t-base) var(--e-out),box-shadow var(--t-base) var(--e-out)}
.pillsearch input:focus{border-color:rgba(var(--cyan-rgb),.55);
  box-shadow:0 0 0 4px rgba(var(--cyan-rgb),.09),var(--sh-lift)}
.pillsearch input::placeholder{color:var(--ph)}
.pillsearch .ico{position:absolute;left:19px;top:50%;transform:translateY(-50%);opacity:.5;color:var(--icon)}
.pillsearch .go{position:absolute;right:6px;top:50%;transform:translateY(-50%);border:none;cursor:pointer;
  background:var(--btn-grad);color:var(--btn-ink);font-weight:var(--fw-bold);font-size:var(--fs-sm);
  border-radius:var(--r-pill);padding:10px var(--sp-6);
  transition:filter var(--t-base) var(--e-out),transform var(--t-base) var(--e-out)}
/* 2026-10-01 修 hover 掉位：.go 用 top:50%+translateY(-50%) 居中，hover 若只写 translateY(-1px)
   会把定位一起覆盖 → 按钮悬停猛沉 16px（全站所有 .pillsearch 受影响，不止市场页）。
   正确写法：位移里保留 -50% 居中量，只叠 1px 上浮。 */
.pillsearch .go:hover{filter:brightness(1.06);transform:translateY(calc(-50% - 1px))}

/* 分段控件（单位/视图切换） */
.seg{display:inline-flex;background:var(--fill3);border:1px solid var(--line);
  border-radius:var(--r-ctl);padding:3px;gap:2px}
.seg button{background:none;border:none;color:var(--sub);font-size:var(--fs-xs);
  font-weight:var(--fw-semi);padding:6px 11px;border-radius:var(--r-chip);cursor:pointer;
  line-height:var(--lh-cap);transition:background-color var(--t-base) var(--e-out),
    color var(--t-base) var(--e-out)}
.seg button.on{background:var(--card);color:var(--ink);box-shadow:var(--sh-contact)}

/* 市场页横向筛选条：快选渠道/快选模型两行铺开；维度三下拉 2026-09-29 并入下方结果工具条 */
.hbar{margin-top:22px;padding:var(--sp-4) var(--sp-5);display:flex;flex-direction:column;
  gap:12px;position:relative;z-index:2}
.hb-row{display:flex;align-items:center;gap:10px;flex-wrap:wrap}
.hb-row+.hb-row{border-top:1px dashed var(--line2);padding-top:12px}
.hb-k{flex:none;min-width:66px;font-size:var(--fs-cap);font-weight:var(--fw-bold);
  color:var(--sub);letter-spacing:var(--ls-cap)}
.hb-opts{display:flex;align-items:center;gap:6px;flex-wrap:wrap;min-width:0}
/* 网格/弹性子项默认 min-width:auto，里面的宽表会把整列撑到内容宽度（移动端会顶破视口）。
   统一置 0，让 .tscroll 自己出横向滚动条，而不是把父级列撑宽。 */
.rank-grid>main,.rank-grid>aside{min-width:0}
/* 横条里的选项 = 胶囊芯片。复用 .opt 的结构与 change 事件（状态逻辑零改动），仅重排外观：
   原生 input 藏起来，选中态由 .on 表达 —— 和「近黑选中态」的全站语言一致 */
.hbar .opt{display:inline-flex;align-items:center;gap:6px;padding:5px 12px;
  border:1px solid var(--line3);border-radius:var(--r-ctl);background:var(--card);
  cursor:pointer;font-size:var(--fs-xs);color:var(--sub2);user-select:none;
  transition:background-color var(--t-base) var(--e-out),border-color var(--t-base) var(--e-out),
    color var(--t-base) var(--e-out)}
.hbar .opt:hover{border-color:var(--line5);color:var(--ink);background:var(--card)}
.hbar .opt input{display:none}
.hbar .opt .cnt{margin-left:0;font-size:11px;color:var(--dim)}
.hbar .opt.on{background:var(--ink);border-color:var(--ink);color:var(--bg)}
.hbar .opt.on .cnt{color:var(--bg);opacity:.65}
/* 快速选模型芯片：两行（模型名 + 最低输入价），信息密度对齐参考站的模型快选。
   2026-09-30 用户反馈：两行贴太近、各芯片高矮不齐显随意 ——
   固定最小高度（「接入中」单行芯片也撑到等高并垂直居中）、行距收紧行高锁定 */
.hbar .opt.qm{flex-direction:column;align-items:stretch;gap:2px;padding:7px 12px;
  min-height:47px;justify-content:center;border-radius:var(--r-ctl)}
/* 2026-09-30 用户反馈：金属质感浅底去掉，回到素面白卡（底/边/影走基础 .opt）；
   选中态黑底上模型名曾写死深色看不清 → .on 内 b/small 反白 */
.hbar .opt.qm b{font-size:var(--fs-xs);font-weight:var(--fw-semi);color:var(--ink);
  white-space:nowrap;overflow:hidden;text-overflow:ellipsis;line-height:1.3}
.hbar .opt.qm small{font-size:11px;color:var(--dim);font-variant-numeric:tabular-nums;
  white-space:nowrap;line-height:1.3}
.hbar .opt.qm.on small{color:var(--bg);opacity:.65}
/* 模型类型/计价方式/排序下拉（2026-09-29 全部由芯片改选择框，对齐参考图）：
   appearance:none 干掉原生箭头，用内嵌 SVG 画 chevron；
   白底 + --r-ctl 圆角 + 常规字号，观感对齐参考站的筛选控件 */
.hb-sel{appearance:none;-webkit-appearance:none;min-width:132px;padding:7px 32px 7px 13px;
  border:1px solid var(--line3);border-radius:var(--r-ctl);background-color:var(--card);
  font-family:inherit;font-size:var(--fs-sm);color:var(--ink);cursor:pointer;
  outline:none;transition:border-color var(--t-base) var(--e-out);
  background-image:url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='10' height='6' viewBox='0 0 10 6'%3E%3Cpath d='M1 1l4 4 4-4' fill='none' stroke='%239aa0a8' stroke-width='1.6' stroke-linecap='round' stroke-linejoin='round'/%3E%3C/svg%3E");
  background-repeat:no-repeat;background-position:right 11px center}
.hb-sel:hover{border-color:var(--line5)}
.hb-sel:focus{border-color:var(--ink)}
/* 参考图版式：小标签在上、下拉框在下（.hb-field 复用于市场工具条与 hbar） */
.hb-field{display:flex;flex-direction:column;gap:6px;min-width:0}
.hb-label{font-size:var(--fs-cap);font-weight:var(--fw-bold);color:var(--sub);letter-spacing:var(--ls-cap)}
.opt{display:flex;align-items:center;gap:8px;padding:6px 8px;border-radius:var(--r-xs);cursor:pointer;
  font-size:13px;color:var(--sub2);user-select:none;
  transition:background-color var(--t-base) var(--e-out),color var(--t-base) var(--e-out)}
.opt:hover{background:var(--fill2);color:var(--ink)}
.opt input{width:15px;height:15px;flex:none;accent-color:var(--cyan);cursor:pointer;margin:0}
.opt .cnt{margin-left:auto;font-size:11px;color:var(--dim);font-variant-numeric:tabular-nums}
.opt.on{background:var(--ink);color:var(--bg)}
.opt.on .cnt{color:var(--bg);opacity:.65}
.opt.on input{accent-color:var(--bg)}
/* 单选样式（用 appearance 干掉原生圆点，做成"选中即填充"的方块） */
.opt.radio input{appearance:none;-webkit-appearance:none;width:15px;height:15px;border-radius:4px;
  border:1.5px solid var(--line5);background:var(--card);position:relative;
  transition:background-color var(--t-base) var(--e-out),border-color var(--t-base) var(--e-out)}
.opt.radio input:checked{background:var(--ink);border-color:var(--ink)}
.opt.radio input:checked::after{content:'';position:absolute;left:4px;top:1px;width:5px;height:9px;
  border:solid var(--bg);border-width:0 2px 2px 0;transform:rotate(45deg)}
.opt.radio.on input:checked{background:var(--bg);border-color:var(--bg)}
.opt.radio.on input:checked::after{border-color:var(--ink)}

/* 结果工具条（2026-09-29 用户要求两行并一行）：三个下拉 + 搜索框 + 右侧重置/单位/视图，
   统计/时效/口径文字已删。hb-field（小标签在上、下拉在下）复用进本条，高度对齐搜索框。 */
.resbar{display:flex;align-items:flex-end;gap:14px;flex-wrap:wrap;
  margin-top:14px;margin-bottom:var(--sp-4);padding:11px var(--sp-5);font-size:var(--fs-sm);color:var(--sub);
  background:var(--card);border:1px solid var(--line3);border-radius:var(--r-card);
  box-shadow:var(--sh-contact);position:relative;z-index:2}
.resbar b{color:var(--ink);font-weight:var(--fw-semi);font-variant-numeric:tabular-nums}
.resbar .sp{margin-left:auto;display:flex;align-items:center;gap:10px}
.resbar .hb-field{gap:4px}
.resbar .hb-field .hb-label{font-size:var(--fs-cap)}
.resbar .hb-sel{min-width:118px;padding:6px 30px 6px 12px;font-size:var(--fs-xs)}
/* 无页头页面（市场/榜单，2026-09-29 用户要求删除标题区）：
   顶部留白 = 固定导航 64px + 呼吸 26px，内容不得顶进导航底下 */
.wrap.topgap{margin-top:90px}
/* 搜索框自页头收进结果工具条：紧凑变体（贴着结果，视觉降一级） */
.resbar .pillsearch{margin:0;flex:0 1 340px;min-width:220px}
/* [type=text] 提一档特异度：末尾 v2 通用 input 规则(等特异度靠后)会把左36/右78px
   压成 14px，导致放大镜图标叠在占位文字上（2026-09-30 用户反馈） */
.resbar .pillsearch input[type=text]{padding:9px 78px 9px 36px;font-size:var(--fs-sm);
  box-shadow:none;border-radius:var(--r-ctl);
  background:var(--card);border-color:var(--line4)}
.resbar .pillsearch .ico{left:12px}
.resbar .pillsearch .go{padding:6px 13px;font-size:var(--fs-xs)}

/* 表格 */
.tscroll{overflow-x:auto;position:relative;z-index:2}
table{width:100%;border-collapse:collapse}
.tscroll table{min-width:900px}
thead th{text-align:left;padding:11px var(--sp-5);color:var(--sub);font-weight:var(--fw-semi);
  font-size:var(--fs-cap);letter-spacing:var(--ls-cap);border-bottom:1px solid var(--line);
  white-space:nowrap;background:var(--sheen)}
tbody td{padding:var(--sp-4) var(--sp-5);border-bottom:1px solid var(--line2);vertical-align:middle;
  font-size:var(--fs-sm);white-space:nowrap}
tbody tr{transition:background-color var(--t-fast) var(--e-out)}
tbody tr:hover{background:var(--hover)}
tbody tr:last-child td{border-bottom:none}
.num{font-variant-numeric:tabular-nums}
.ok{color:var(--green)}.warn{color:var(--amber)}.bad{color:var(--red)}.dim{color:var(--sub)}

/* 徽章 */
.chip{padding:3px var(--sp-3);border-radius:var(--r-pill);font-size:var(--fs-cap);
  font-weight:var(--fw-bold);border:1px solid;display:inline-block;letter-spacing:var(--ls-body)}
.chip.text{color:var(--cyan);border-color:rgba(var(--cyan-rgb),.34);background:rgba(var(--cyan-rgb),.09)}
.chip.image{color:var(--purple);border-color:rgba(var(--purple-rgb),.34);background:rgba(var(--purple-rgb),.09)}
.chip.video{color:var(--pink);border-color:rgba(var(--pink-rgb),.34);background:rgba(var(--pink-rgb),.09)}
.chip.audio{color:var(--green);border-color:rgba(var(--green-rgb),.32);background:rgba(var(--green-rgb),.09)}
.chip.gray{color:var(--sub2);border-color:var(--line);background:var(--fill4)}
.chip.cyan{color:var(--cyan);border-color:rgba(var(--cyan-rgb),.34);background:rgba(var(--cyan-rgb),.09)}
.chip.amber{color:var(--amber);border-color:rgba(var(--amber-rgb),.34);background:rgba(var(--amber-rgb),.09)}
/* 2026-10-02 用户点名：公开榜单明细表「类别」列的类目标签（文本/图像/视频/语音）
   去掉胶囊底框，只保留文字。
   理由与上面 .mk-table .b-main .chip 那条一致（色彩预算）：这一列整列都是类目，
   每个单元格再套一枚同色胶囊，等于同一信息在页面上说了两遍，还把 12 列表格
   撑得每行都有一枚色块，扫读时最先跳出来的反倒是"类别"而不是价格。
   作用域收窄到 #rows（榜单 tbody，全页唯一）——不能写成 .chip 裸选择器，
   站内还有 20+ 处 chip 承担状态语义（审核中/在售/GET/POST…），那些必须留框。 */
#rows .chip{background:none;border:none;padding:0;font-weight:var(--fw-med)}

/* 控制台 · Key 表格（2026-10-01 对齐 OpenRouter 形态：表格+搜索+聚合条+限额进度条） */
.kstats{display:flex;gap:34px;flex-wrap:wrap;padding:4px 2px 16px;border-bottom:1px solid var(--line);margin-bottom:2px}
.kstat b{display:block;font-size:20px;font-weight:var(--fw-bold);letter-spacing:-.01em;line-height:1.25}
.kstat span{font-size:var(--fs-cap);color:var(--sub)}
.kbar{width:110px;height:4px;border-radius:999px;background:var(--fill4);margin-top:5px;overflow:hidden}
.kbar i{display:block;height:100%;width:0;background:var(--green);border-radius:999px;transition:width var(--t-slow) var(--e-out)}
.kbar i.hot{background:var(--amber)}
.st.disabled{color:var(--amber);border-color:rgba(var(--amber-rgb),.35);background:rgba(var(--amber-rgb),.1)}
.keyacts{display:flex;align-items:center;gap:5px;justify-content:flex-end;white-space:nowrap}
/* 密钥表（.ktab）：列合并后压缩内边距，1440 下整表不横滚 */
.ktab{min-width:0}
.ktab thead th{padding:10px var(--sp-3)}
.ktab tbody td{padding:10px var(--sp-3)}
.tag{padding:2px 9px;border-radius:var(--r-pill);font-size:var(--fs-cap);
  font-weight:var(--fw-bold);display:inline-block;margin:0 var(--sp-1) 3px 0;
  white-space:nowrap}
.tag.cheap{background:rgba(var(--cyan-rgb),.12);border:1px solid rgba(var(--cyan-rgb),.34);color:var(--cyan)}
.tag.fast{background:rgba(var(--green-rgb),.11);border:1px solid rgba(var(--green-rgb),.32);color:var(--green)}
.tag.stable{background:rgba(var(--purple-rgb),.12);border:1px solid rgba(var(--purple-rgb),.34);color:var(--purple)}
.tag.trust{background:rgba(var(--amber-rgb),.12);border:1px solid rgba(var(--amber-rgb),.34);color:var(--amber)}
.tag.official{background:var(--fill4);border:1px solid var(--line5);color:var(--sub2)}
.st{display:inline-flex;align-items:center;gap:6px;font-size:12px;font-weight:700;padding:3px 10px;
  border-radius:99px;border:1px solid}
.st.pending{color:var(--amber);border-color:rgba(var(--amber-rgb),.35);background:rgba(var(--amber-rgb),.1)}
.st.approved{color:var(--green);border-color:rgba(var(--green-rgb),.32);background:rgba(var(--green-rgb),.09)}
.st.rejected{color:var(--red);border-color:rgba(var(--red-rgb),.35);background:rgba(var(--red-rgb),.1)}
.st.active{color:var(--cyan);border-color:rgba(var(--cyan-rgb),.34);background:rgba(var(--cyan-rgb),.1)}
.st.revoked{color:var(--sub2);border-color:var(--line);background:var(--fill4)}

/* 表单 */
.form{display:flex;flex-direction:column;gap:14px}
.field{display:flex;flex-direction:column;gap:7px}
.field label{font-size:13px;color:var(--sub2);font-weight:600}
.field .hint{font-size:var(--fs-cap);color:var(--sub)}
/* 文本框 / 下拉框：占满整行。
   ⚠️ 必须排除 checkbox / radio！否则复选框会被拉成整行宽，把旁边的文字挤到只剩
   1 个字的宽度（中文只能一字一行竖排），并把弹窗撑出横向滚动条。 */
input:not([type=checkbox]):not([type=radio]),textarea,select{background:var(--fill);border:1px solid var(--line);border-radius:var(--r-sm);
  padding:12px 14px;color:var(--ink);font-size:14px;outline:none;width:100%;
  transition:border-color var(--t-base) var(--e-out),background-color var(--t-base) var(--e-out)}
input:not([type=checkbox]):not([type=radio]):focus,textarea:focus,select:focus{border-color:rgba(var(--cyan-rgb),.5);background:rgba(var(--cyan-rgb),.05)}
input:not([type=checkbox]):not([type=radio])::placeholder,textarea::placeholder{color:var(--ph)}

/* 复选框 / 单选框：保持原生尺寸，不受上面的「整行宽」规则影响 */
input[type=checkbox],input[type=radio]{width:16px;height:16px;min-width:16px;padding:0;
  flex:none;border-radius:4px;accent-color:var(--cyan);cursor:pointer}
textarea{min-height:92px;resize:vertical}
.row2{display:grid;grid-template-columns:1fr 1fr;gap:14px}
.form-msg{font-size:13px;padding:10px 14px;border-radius:10px;display:none}
.form-msg.show{display:block}
.form-msg.err{background:rgba(var(--red-rgb),.1);border:1px solid rgba(var(--red-rgb),.32);color:var(--red)}
.form-msg.ok{background:rgba(var(--green-rgb),.1);border:1px solid rgba(var(--green-rgb),.3);color:var(--green)}
.form-msg.info{background:rgba(var(--cyan-rgb),.08);border:1px solid rgba(var(--cyan-rgb),.28);color:var(--cyan)}
/* warn 态（2026-10-02 补）：给「用户可纠正但不算失败」的情况用 ——
   典型是重复提交入驻申请（409）。红字会让人以为系统出错 → 再点一次 → 更乱；
   琥珀色表达"提醒你去看看已有那条"，与 err 的"操作失败"区分开。
   用 --amber 而非 --yellow：全站语义色令牌里没有 yellow，只有 amber。 */
.form-msg.warn{background:rgba(var(--amber-rgb),.1);border:1px solid rgba(var(--amber-rgb),.32);color:var(--amber)}

/* 代码块（浅色页里也保持深底，可读性最好） */
pre.code{background:var(--code-bg);border:1px solid var(--line3);border-radius:var(--r);padding:16px 18px;overflow-x:auto;
  font-family:"JetBrains Mono",Consolas,monospace;font-size:var(--fs-xs);
  line-height:var(--lh-sm);color:#d6e6f0;white-space:pre}
pre.code .c{color:#5b6b78}
.copy{background:var(--fill4);border:1px solid var(--line);color:var(--sub2);border-radius:var(--r-xs);
  padding:6px 12px;font-size:12px;font-weight:700;cursor:pointer;
  transition:border-color var(--t-base) var(--e-out),color var(--t-base) var(--e-out)}
.copy:hover{border-color:rgba(var(--cyan-rgb),.5);color:var(--cyan)}
.code-head{display:flex;align-items:center;justify-content:space-between;margin-bottom:10px;gap:12px;flex-wrap:wrap}

/* 提示条：样式见文件末尾「内页设计系统」第 5 节（此处不再重复定义） */

/* 网格 */
.grid3{display:grid;grid-template-columns:repeat(3,1fr);gap:16px}
.grid2{display:grid;grid-template-columns:1fr 1fr;gap:16px}
.empty{padding:56px 20px;text-align:center;color:var(--sub);font-size:14px}
.live{width:7px;height:7px;border-radius:50%;background:var(--green);animation:pulse 1.5s infinite;display:inline-block}
@keyframes pulse{0%,100%{opacity:1}50%{opacity:.22}}
.loading{color:var(--sub);font-size:var(--fs-sm);padding:var(--sp-7) 0;text-align:center}

/* ---------- 模型卡片（市场页 · 主视图） ---------- */
.mcard{background:var(--card);border:1px solid var(--line3);border-radius:var(--r);padding:0;
  position:relative;box-shadow:var(--shadow);overflow:hidden;
  transition:border-color var(--t-slow) var(--e-out),box-shadow var(--t-slow) var(--e-out)}
.mcard:hover{border-color:rgba(var(--cyan-rgb),.45);box-shadow:var(--sh-lift)}
.mcard-top{padding:18px 20px 14px;border-bottom:1px solid var(--line2);display:flex;align-items:flex-start;gap:12px}
.mcard-top .lg{width:34px;height:34px;border-radius:var(--r-xs);flex:none;display:grid;place-items:center;
  background:var(--fill3);border:1px solid var(--line);overflow:hidden}
.mcard-top .lg img{width:22px;height:22px;object-fit:contain;display:block}
.mcard-top .lg span{font-size:var(--fs-base);font-weight:var(--fw-semi);color:var(--sub2)}
.mcard-top .tt{min-width:0;flex:1}
.mcard-top .nm{font-size:var(--fs-lg);font-weight:var(--fw-semi);letter-spacing:var(--ls-sub);
  display:flex;align-items:center;gap:var(--sp-2)}
.mcard-top .nm a{border-bottom:1px dashed var(--line5)}
.mcard-top .nm a:hover{color:var(--cyan);border-color:var(--cyan)}
.mcard-top .id{font-family:"JetBrains Mono",Consolas,monospace;font-size:11px;color:var(--sub);margin-top:3px;
  overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.mcard-desc{font-size:var(--fs-xs);color:var(--sub);line-height:var(--lh-sm);margin-top:var(--sp-3)}
.badges{display:flex;flex-wrap:wrap;gap:5px;margin-top:9px}
.badge{padding:2px var(--sp-3);border-radius:var(--r-chip);font-size:var(--fs-cap);
  font-weight:var(--fw-bold);border:1px solid;white-space:nowrap}
.badge.official{color:var(--amber);border-color:rgba(var(--amber-rgb),.5);background:rgba(var(--amber-rgb),.1)}
.badge.disc{color:var(--amber);border-color:rgba(var(--amber-rgb),.5);background:rgba(var(--amber-rgb),.1)}
.badge.type{color:var(--cyan);border-color:rgba(var(--cyan-rgb),.4);background:rgba(var(--cyan-rgb),.09)}
/* 「供应商直供」徽标（2026-10-01）：与自营渠道一眼可分。
   用紫（项目主色之一）而不是琥珀 —— 琥珀在本项目已被「待接入 / 接入中 /
   官方价」占满，再加会让真正的提醒失去分量。 */
.badge.direct{color:var(--purple);border-color:rgba(var(--purple-rgb),.45);background:rgba(var(--purple-rgb),.1)}
.pill.direct{background:rgba(var(--purple-rgb),.14);border:1px solid rgba(var(--purple-rgb),.38);color:var(--purple)}
.badge.plain{color:var(--sub);border-color:var(--line);background:var(--fill2)}
/* 「接入中」徽标：中性偏提醒，不用红（红=错误），因为它不是故障，是"还没开通" */
.badge.warn{color:var(--amber);border-color:rgba(var(--amber-rgb),.5);background:rgba(var(--amber-rgb),.1)}
/* 不可交付的渠道卡：降低权重，避免它在货架上和可买的货抢注意力 */
.chan.blocked{border-style:dashed;border-color:rgba(var(--amber-rgb),.35)}
/* 「待接入」列表徽标（2026-10-01）：渠道已上架但出口没接通。
   与 badge.warn 区分：badge.warn 是类目没适配（平台侧在建），
   这枚是单条渠道没接入——所以用更中性的灰，琥珀留给更"热"的提醒。 */
.pill.pending{background:var(--fill2);border:1px solid var(--line5);color:var(--sub2)}
/* 折扣角标：绝对定位，必须有已定位的父级（.msec 已设为 relative）。
   pointer-events:none 是关键——纯装饰角标绝不能吞掉下方按钮的点击。 */
.corner{position:absolute;top:12px;right:-1px;background:var(--amber);color:#fff;
  font-size:var(--fs-cap);font-weight:var(--fw-bold);padding:3px 10px 3px 12px;
  border-radius:var(--r-pill) 0 0 var(--r-pill);letter-spacing:var(--ls-body);
  pointer-events:none;z-index:3}
.mcard-body{padding:14px 20px 4px}
/* 价格三宫格：输入 / 输出 / 缓存 */
.price3{display:grid;grid-template-columns:repeat(3,1fr);gap:9px}
.p3i{background:var(--fill2);border:1px solid var(--line2);border-radius:var(--r-xs);padding:10px 11px;min-width:0}
.p3k{font-size:var(--fs-cap);color:var(--sub);font-weight:var(--fw-med);
  letter-spacing:var(--ls-label);white-space:nowrap;
  overflow:hidden;text-overflow:ellipsis}
.p3v{font-size:var(--fs-md);font-weight:var(--fw-semi);font-variant-numeric:tabular-nums;
  margin-top:var(--sp-1);letter-spacing:var(--ls-sub);
  white-space:nowrap;overflow:hidden;text-overflow:ellipsis}
/* 2026-10-02 令牌化 + 可读性：这一族原为 10px 裸像素，散落在 app.css 与
   admin/console/index/login 五个文件的行内 style 里（"总"单位后缀、语言箭头、
   价格单位、徽标 em）。10px 在中文界面已到可读性边缘，且它比最小档
   --fs-cap:11px 还小 —— 等于体系外又开了一档。统一提到 --fs-cap。 */
.p3v small{font-size:var(--fs-cap);font-weight:600;color:var(--sub);margin-left:2px}
/* 「总」单位角标（延迟数值后的口径后缀）：2026-10-02 从 4 处行内
   style="font-size:10px" 抽成类。同一个语义元素在 admin/console/index
   各写一遍行内样式，是「改一处漏三处」的典型来源。 */
.unit-tag{font-size:var(--fs-cap);color:var(--sub);opacity:.85}
.p3o{font-size:var(--fs-cap);color:var(--dim);margin-top:3px;font-variant-numeric:tabular-nums;
  text-decoration:line-through;text-decoration-color:var(--dot)}
.p3o.flat{text-decoration:none}
.p3v.hot{color:var(--cyan)}
.mcard-foot{display:flex;align-items:center;gap:12px;flex-wrap:wrap;padding:13px 20px 16px;margin-top:12px;
  border-top:1px solid var(--line2);font-size:var(--fs-xs);color:var(--sub)}
.mcard-foot .kpi-inline{display:flex;align-items:center;gap:5px;white-space:nowrap}
.mcard-foot b{color:var(--ink);font-weight:var(--fw-semi);font-variant-numeric:tabular-nums}
.mcard-foot .acts{margin-left:auto;display:flex;gap:8px}

/* 模型区（分组 + 渠道卡片网格）
   position:relative 是 .corner 的定位基准；缺了它角标会逃逸到 .layout 右上角并压住视图切换按钮 */
.msec{position:relative;background:var(--card);border:1px solid var(--line3);border-radius:var(--r);box-shadow:var(--shadow);
  overflow:hidden;margin-bottom:18px}
.msec-head{
  /* ★ 2026-10-02 定稿（四次改法）：两行显式网格。
     演进链（别重走，每一步都有量化依据）：
       ① flex + wrap，价格行被徽章挤到第二行 → 右对齐后左侧空 731px
       ② 只改 margin/border → 空白纹丝不动（病根不在间距）
       ③ grid 三列（auto / 1fr / max-content）→ 单行成立，但用户仍指：
          「这行小字，为什么不能放到红框位置？」
       ④ 本次：改**两行显式网格**，价格行落到第二行右侧。
     为什么必须落到第二行（这是用户点名的核心，不是偏好）：
       组头右上角被 `.corner` 折扣角标绝对定位占着（实测占 78px 宽、
       位于 t=12~40），价格行第一行右缘 992px、角标左缘 1033px ——
       水平净距 41px 看似够，但**垂直方向有 2px 重叠带**
       （价格行 t=38、角标 b=40），两行小字 + 一个色块挤在同一个右上角，
       读起来就是"被压住"。
       而第二行右侧本来就是空区（左边只有模型 ID 与详情链接）——
       **把价格行放过去，右上角独占角标、右下角坐价格，版面各归其位，
       组头高度不变（两行本来就已存在，不是新增行）。 */
  display:grid;
  grid-template-columns:auto minmax(0,1fr) max-content;
  grid-template-rows:auto auto;
  align-items:center;
  column-gap:14px;row-gap:8px;
  padding:17px 22px;border-bottom:1px solid var(--line2);
  background:var(--sheen2)}
/* 行位分配（显式写死，不靠 auto 流动 —— auto 会随徽章数量漂移）：
     第一行：模型名 + 徽章区        第三列空出来留给角标
     第二行：模型 ID 行 + 价格三项  右对齐，与第一行左基线同一条 */
.msec-head > .mn{grid-column:1;grid-row:1}
.msec-head > .meta{grid-column:2;grid-row:1}
.msec-head > .mid{grid-column:1;grid-row:2}
.msec-head > .right{grid-column:3;grid-row:2;justify-self:end}
/* padding-bottom:30px（绝对定位时代为价格行留物理高度而加）已撤。
   定稿方案价格行回到 flex 流、由 max-width 给 .meta 封顶，
   组头高度自然由两行内容算出，不需要额外留白。 */
.msec-head .mn{font-size:var(--fs-lg);font-weight:var(--fw-semi);display:flex;
  align-items:center;gap:var(--sp-3);letter-spacing:var(--ls-sub)}
.msec-head .mn a{border-bottom:1px dashed var(--line5)}
.msec-head .mn a:hover{color:var(--cyan);border-color:var(--cyan)}
/* 卡片模式模型区块头加 logo 位（2026-09-30 用户点名）：比快选芯片的 22px 收半档对齐 fs-lg */
.msec-head .mn .ldot{width:20px;height:20px;border-radius:6px;font-size:11.5px;flex:none}
.msec-head .mid{font-size:12px;color:var(--sub);font-family:"JetBrains Mono",Consolas,monospace}
/* ⚠️ 本条 2026-10-01 的修法（width:100% 强制独占第二行）已于 2026-10-02 作废，
   留档是因为它暴露了一个陷阱 —— 记下来免得有人照着改回去：

   当时的病根是**真的**：.meta 的能力徽章数量不固定（slice(0,4)），
   徽章一多就把价格行挤到第三行、徽章少时它还在第一行
   （实测 DeepSeek 区块 right.top=230、豆包区块 right.top=677 在首行），
   相邻区块价格行基线完全对不齐。

   但修法选错了：**用"强制换行"治"基线不齐"，等于用一个更大的问题
   换掉原来的问题**。强制第二行确实让基线恒定了，代价是价格行独占
   1066px 宽而内容只有 334px，右对齐后左侧空出 731px —— 空白转移到了
   用户下一眼就会看见的地方。

   正确解法在下面（去掉 width:100%，让它回到第一行）。
   ★ 教训：**"对齐问题"不要用"改变分行结构"来解决**。
     先问「它能不能待在原来那行」，能就让它待在原来那行；
     只有确认放不下（比如最小宽度总和 > 可用宽）才允许换行。*/
/* 价格行 participate flex 时，.meta 必须**按内容宽**排布并有收缩上限：
   - flex:1 1 auto 会吃掉全部剩余空间（实测占 724px 而内容只 448px），
     把价格行挤到第二行 —— 那一行右侧对齐后左侧空 731px，就是用户点的空白。
   - max-width 给徽章区封顶，保证「名称 + 徽章 + 价格行」永远排得进一行。
/* ── 2026-10-02 定稿：价格行回flex 流 + 横向锁死不换行 ──

   用户三次点名的空白，病根只有一个：**价格行独占一行还右对齐**，
   于是 .right 宽 1066px 而内容只占 334px → 左侧空 731px；
   组头因此 125px，而内容实际只占 87px。

   为什么前两次没解决：都在调间距（删虚线、margin-top 10→2），
   而间距**不是**问题 —— 一个独占整行、右对齐的盒子，空是必然的。
   教训同「两把尺子」：先量结构，再调像素。

   实测（1440 桌面，5 个区块逐一量）：
     可用宽 1066px；left+meta+right 内容宽 =
       DeepSeek 1005.6 / 豆包 903 / 智谱 972 / Kimi 953.5 / 混元 852.8
     → 全部放得进第一行，价格行不必独占。

   定稿两条：
     · .meta   flex:0 1 auto + max-width:calc(100% - 700px)
       700px = 价格行349 + 角标让位96 + 组头 padding 44 + 余量 211（实测反推）。
       max-width 的作用是**给徽章区封顶**，让「名称+徽章+价格行」永远排得进一行。
     · .right  flex:none + flex-wrap:nowrap → 三项恒定横排，永不被挤断。
     · .has-corner .right margin-right:96px → 给右上折扣角标让位
       （角标实测 x=1333.7~1412，与价格行同处右上区域）。

   实测（1440，13 个区块全量）：组头 125 → **101px**，
   两条空白带（右侧对齐 731px 空 + 行间 36px 空带）全部消失。

   ⚠️ 落地踩坑五连（同一处翻车五次，留档别重走）：
     ① 只去 width:100% 不够 —— .meta 带 flex:1 1 auto 会吃掉全部剩余空间
        （实测占 724px 而内容只448px），价格行被挤到第二行。
     ② 让位用 padding-right:96px → **错**：padding 让 flex 容器自身变宽
        （334→430px），总宽 1101.6 > 可用 1066，价格行被自己挤回第二行。
        让位只能用 margin。
     ③ 绝对定位（position:absolute+right/bottom）→ 脱离流解决了换行，
        但绝对定位盒没有可用宽度约束，三项被压成竖排（宽118/高66），
        且 .has-corner 的 right 被分支吃掉。解决换行换来排版塌陷，不划算。
     ④ white-space:nowrap 只挡**文字**换行，挡不住**flex 项换行**；
        min-width:max-content 也不够（容器被压缩时子项仍各占一行）。
        → 必须 flex:none + flex-wrap:nowrap 两条一起。
     ⑤ ★★ 一次手误把选择器写成 （两个点），
        浏览器当未知元素选择器**静默丢弃**，不报错、不生效。
        我因此对着一个从不生效的规则改了十几分钟。
        → 排查手法：遍历 cssRules + el.matches()，列出命中该元素的规则，
          一眼看出哪条不在。**遇到「改了没反应」先查这个，别改算法。**
        这条与MEMORY 里改字段名后全仓搜旧名同源：
        静默失效是比报错更贵的一类bug。

   ⚠️ 断言必须查**子项 y 是否同排**（sameRow），不能只查容器宽/位置 ——
     上述五种失败态里，.right 容器本身的位置全都看起来正常。 */
.msec-head .meta{font-size:var(--fs-xs);color:var(--sub);display:flex;align-items:center;
  gap:var(--sp-3);flex-wrap:wrap;min-width:0}
  /* ⚠️ 这里原来还有一个 max-width:calc(100% - 489px)（489 = 价格行349 + 角标96 + padding44），
     那是 flex 时代的补丁，封顶徽章区以保证三段排得进一行。
     换成 grid 后**必须删掉**：grid 的第三列已经按内容定死，
     再给第二列加绝对上限就成了双重限制 —— 实测第 0、2 个区块
     meta 被压在 577px 上限，三段合计 1106 > 可用 1066，于是换行。
     现在中间列是 minmax(0,1fr)：徽章区自己按可用宽收缩（内部 flex-wrap 会折行，
     但组头永远只有一行），价格行恒定贴右。

     ⚠️⚠️ 这条规则末尾的 } 不能少（本轮就踩了）：
     少一个 } 时，后面 .meta i / .right / .hl 三条规则会被浏览器
     当成这一条的声明**全部吞掉**，不报错、不生效。
     症状极具欺骗性：.msec-head 自己那条生效了（display:grid 对），
     但 .right 退回成 display:block，三项竖排、组头高涨。
     → 改完这段必须查 CSSOM：列出命中 .right 的规则，
       若只有 `*` 就是被吞了。排查手法见下方⑤。 */
.msec-head .meta i{width:3px;height:3px;border-radius:50%;background:var(--dot);flex:none}
/* 第三列必须用 max-content 而不是 auto：
   auto 列在空间紧张时会被压缩，实测价格行被压到 138px（内容需 349px），
   三项直接折行 —— 那是另一个形态的同一个病（价格行高度暴涨）。
   max-content = 按内容定死，谁都不许挤它；空间不够时压中间那列。
   .right 内部也要 flex-wrap:nowrap + 子项 flex:none，
   缺一个就可能在列内二次换行。 */
.msec-head .right{display:flex;align-items:center;justify-content:flex-end;
  gap:14px;white-space:nowrap;flex-wrap:nowrap}
/* .right 内三项是三段文案（官方价/市场最低/最高可省），恒定横排、不可压 */
.msec-head .right > .hl{flex:none}
/* 2026-10-02 阶段 M：has-corner 的 96px 让位已删除。
   以前价格行在第一行右端，要给右上角的折扣角标让路；
   现在价格行落到第二行（.mid 那一行），右上角归角标独占，
   两者不再共处一隅，让位就成了纯空白。 */
.hl{font-size:var(--fs-xs);color:var(--sub)}
.hl b{color:var(--cyan);font-weight:var(--fw-semi);font-variant-numeric:tabular-nums}
.hl b.save{color:var(--green)}
/* 渠道卡片网格 */
.chan-grid{display:grid;grid-template-columns:repeat(auto-fill,minmax(272px,1fr));gap:14px;padding:16px 22px}
.chan{background:var(--card);border:1px solid var(--line3);border-radius:var(--r-sm);padding:14px;
  position:relative;display:flex;flex-direction:column;gap:11px;
  transition:border-color var(--t-slow) var(--e-out),box-shadow var(--t-slow) var(--e-out)}
.chan:hover{border-color:rgba(var(--cyan-rgb),.5);box-shadow:var(--sh-lift)}
.chan.pinned{border-color:rgba(var(--cyan-rgb),.6);background:rgba(var(--cyan-rgb),.045)}
.chan-top{display:flex;align-items:center;gap:9px}
.chan-top .av{width:28px;height:28px;border-radius:var(--r-ctl);flex:none;display:grid;place-items:center;
  background:var(--fill3);border:1px solid var(--line);font-size:var(--fs-xs);
  font-weight:var(--fw-semi);color:var(--sub2)}
.chan-top .nn{font-weight:var(--fw-semi);font-size:var(--fs-sm);min-width:0;flex:1;overflow:hidden;text-overflow:ellipsis;
  white-space:nowrap}
.chan-top .nn em{font-style:normal;display:block;font-size:var(--fs-cap);color:var(--sub);font-weight:var(--fw-med);
  overflow:hidden;text-overflow:ellipsis}
.chan-badges{display:flex;flex-wrap:wrap;gap:5px}
.chan-metrics{display:flex;align-items:center;gap:var(--sp-5);flex-wrap:wrap;font-size:var(--fs-xs);
  color:var(--sub);border-top:1px solid var(--line2);padding-top:var(--sp-4)}
.chan-metrics b{color:var(--ink);font-weight:var(--fw-semi);font-variant-numeric:tabular-nums}
.chan-metrics .r{display:flex;align-items:center;gap:4px;white-space:nowrap}
.chan .acts{display:flex;gap:8px;margin-top:auto}
.chan .acts .btn{flex:1}
/* ---------- 成功率三小格（实时 / 24h / 7天） ----------
   ⚠️ 本组件的唯一定义处。model.html 内联块曾重复定义 .rb / .rates 各两次
   （基础 + 「桌面端收排」覆盖层），实测 computed 与 app.css 的任何一处都对不上，
   就是因为内联在最后生效。**组件样式只允许在这里定义**，页面内联块要改数值
   也回来改这里 —— 否则同一个徽章在榜单页一个尺寸、详情页另一个尺寸。

   2026-10-02 用户反馈：「这三列之间的距离缩小，不用跟其他一样的距离，
   本来这三个数据就是一个版块的」。
   病根不是 gap —— gap 当时已经只有 4px（到底了），真正让间距显大的是
   **每个框各自带底色 + 边框**：数字 40.5px 被撑到 54.5px 框里（两侧各 7px
   留白），于是「数字→数字」实测 18px，是 gap 的 4.5 倍。三个带底的方块 +
   4px 缝 = 眼睛读成"三列独立指标"，而不是"一组指标的三个时间窗口"。

   修法不是继续抠 gap（已经没有空间），而是**取消框的独立身份**：
     · 去底色、去边框 → 三组读成一块，与用户"就是一个版块"的判断一致
     · padding 收到 2px 2px、min-width 收到 0（内容自适应）→ 数字净距
       6px，接近 gap 本身，"三列"的印象消失
     · 用一条 hairline 竖线分隔三个时间窗口 —— 不靠底色也能读出"三档"，
       而且这条线比三块底色轻得多
   为什么保留一点 padding 而不是 0：数字完全贴在一起会读成 "100.0%100.0%100.0%"，
   反而更难分。2px 是"能分清、又不散"的最小值。

   ⚠️ 为什么宽度基准要放在**容器**而不是每个格子上（这是第二版踩出来的）：
   ① 放在格子上（min-width:46px）时，**内容越短留白越多、数字反而离得越远**：
      「100.0%」(6 字符 40.5px) 净距 12px，而「95.0%/85.7%/97.3%」
      (5 字符 33.8px) 净距 18.3px —— 行与行不一致，正是"三列读起来不齐"
      的另一种表现（实测全表 7 行里就有 1 行散开）。
   ② 放在容器上（三格等分）后，三格宽度恒等于 容器宽/3，与内容位数无关，
      数字间距在所有行都一致。
   ③ 容器还要 `justify-content:center`：它是 `table td` 的 flex 子项，
      **text-align 对 flex 无效**（本文件第 737 行那条注释已记过这个坑），
      不居中会整体偏左。
   容器宽 152px = 最宽内容(40.5) + padding(6) 三格 + gap(6)×2 + 余量，
   实测比原来 171px 还省，且留出的宽度给了表格其它列。 */
.rates{display:flex;gap:var(--sp-2);align-items:center;justify-content:center;width:152px}
.rb{display:flex;flex-direction:column;align-items:center;gap:1px;padding:2px 3px;
  background:none;border:0;min-width:0;flex:1 1 0}
/* ⚠️ 数字行必须**定宽 + 居中**（下面 .rb b 的 min-width），不能只靠格子的
   align-items:center。原因是"格子等分"只统一了**框**的宽度，没统一**数字**的位置：
   6 字符的「100.0%」(40.5px) 与 5 字符的「95.0%」(33.8px) 在等宽格内居中，
   起始位置差 3.4px → 数字净距在两行间差 6.9px（实测 12 vs 18.9px），
   而这种"有的行散、有的行聚"正是"三列读起来不齐"的另一种表现。
   给 <b> 定一个等于最宽内容的宽度后，5 字符数字也占满整宽，数字之间
   变成**固定的中心距**（格宽 46.7 + gap 6 = 52.7px），净距恒为 52.7−40.5
   = 12.2px，**所有行一致**。40.5px 是实测最宽的「100.0%」宽出来的。 */
.rb b{min-width:40.5px;text-align:center}
.rb em{font-style:normal;font-size:var(--fs-cap);line-height:14px;color:var(--sub);letter-spacing:var(--ls-label)}
.rb b{font-size:var(--fs-cap);line-height:16px;font-weight:var(--fw-semi);font-variant-numeric:tabular-nums;white-space:nowrap}
.rb.ok b{color:var(--green)}.rb.mid b{color:var(--amber)}.rb.bad b{color:var(--red)}
/* 「接入中」「无样本」是中性状态：没有结论，不是坏结论。
   所以不借红/黄/绿任何结论色，避免被读成「成功率很差」。 */
.rb.none b{color:var(--sub);font-weight:var(--fw-med)}
/* 三档之间的 hairline 竖线：靠它读出"三个时间窗口"，
   而不是靠三块底色（底色已去，见上面第 ③ 条的面积/间距账）。
   last-child 不画，否则右边多一条无意义的线。
   ⚠️ 档位是量出来的，不是随手挑的。1px×22px 的竖线面积很小，
   必须够淡才不抢过数字，但实测两个候选都不行：
     --line2  浅 .065 / 深 .045  → 两主题都几乎完全看不见（白加一条）
     --line3  浅 .080 / 深 .060  → 深色下仍读不出（截图实测）
     --line4  浅 .140 / 深 .120  → 两主题都能读出，且明显弱于数字本身 ✓
   教训：**深色主题的半透明白要按"面积"判断够不够，细线比粗线更挑**。 */
.rb + .rb{position:relative}
.rb + .rb::before{content:'';position:absolute;left:calc(var(--sp-2) * -1);top:50%;
  transform:translateY(-50%);width:1px;height:22px;background:var(--line4)}
/* 表头侧的同构三格（model.html 成功率 <th> 内）。
   复用 .rates/.rb 而不是各写一套，是为了让表头与数据的列中心**逐格对齐** ——
   「实时」对「实时」、「24h」对「24h」。原来表头是「实时 · 24h · 7天」纯文本，
   分隔靠「·」字符，间距由字宽决定，实测比下面的数据宽一倍以上，
   于是表头三档与数据三档读起来像两套东西。
   ⚠️ 必须继承 .rb 的 min-width:46px（这里不要覆盖它）：表头格若按字宽自适应，
   就与数据格宽度不同、居中基准不同，逐格偏移会立刻回来。
   两处差别：表头不需要数值行，去掉 <b> 后高度压住，否则表头行变高；
   竖线矮一档（12px 对 22px），因为表头行本身矮，22px 会顶出版心。 */
.rates-h{gap:var(--sp-2);justify-content:center}
.rates-h .rb{padding:1px 3px}
.rates-h .rb::before{height:12px}
.mk-blocked{font-size:var(--fs-cap);color:var(--amber);line-height:1.55;margin-top:5px}
.score{display:flex;align-items:center;gap:6px}
/* 2026-09-29 横条 60→46px（用户反馈太长，把数字顶得很远）；数值字号同步降一号 */
.bar{width:46px;height:5px;border-radius:var(--r-pill);background:var(--line4);overflow:hidden}
.bar i{display:block;height:100%;border-radius:var(--r-pill);
  transition:width .7s var(--e-out)}
.score b{font-variant-numeric:tabular-nums;font-size:var(--fs-cap);font-weight:var(--fw-semi)}
.save-tag{display:inline-block;padding:2px 7px;border-radius:var(--r-chip);
  font-size:var(--fs-cap);font-weight:var(--fw-bold);
  background:rgba(var(--green-rgb),.12);color:var(--green);border:1px solid rgba(var(--green-rgb),.3)}
.save-tag.no{background:var(--fill4);color:var(--sub);border-color:var(--line)}
.pill{display:inline-block;padding:2px var(--sp-3);border-radius:var(--r-pill);
  font-size:var(--fs-cap);font-weight:var(--fw-bold);letter-spacing:var(--ls-body);
  margin-right:var(--sp-1);white-space:nowrap}
.pill.cheap{background:rgba(var(--cyan-rgb),.12);border:1px solid rgba(var(--cyan-rgb),.34);color:var(--cyan)}
.pill.fast{background:rgba(var(--green-rgb),.11);border:1px solid rgba(var(--green-rgb),.32);color:var(--green)}
.pill.stable{background:rgba(var(--purple-rgb),.12);border:1px solid rgba(var(--purple-rgb),.34);color:var(--purple)}
.pill.trust{background:rgba(var(--amber-rgb),.12);border:1px solid rgba(var(--amber-rgb),.34);color:var(--amber)}
.pill.official{background:var(--fill4);border:1px solid var(--line5);color:var(--sub2)}

/* =========================================================
   市场页主视图：横向列表（一张大表）
   —— 交易平台会有很多渠道 × 很多模型，卡片网格装不下，主视图用表。
   ⚠ 不用全站通用的 .tscroll：它只做横向滚动，表头会随页面滚走。
      这里要的是「面板内纵向滚动 + 表头冻结」，所以单独一个类名。
   ⚠ 一旦设了 overflow（任一轴非 visible），该元素就成为定位/滚动容器，
      sticky 的参照物就是它自己，因此 thead 用 top:0（不是 top:64px 导航高度）。
   ========================================================= */
/* 2026-09-29：取消面板内滚动（max-height/overflow-y）——内容全量展开，
   数据多时用底部 1/2/3 页码分页；仅保留横向滚动兜底（宽表在窄屏不顶破页面）。
   2026-09-29 二次压缩：10 列并为 8 列（类型并入渠道、价差并入平台价），
   表格 width:100% 随容器收缩，常规屏宽（≥1280）一屏放全、不出横向滚动 */
.mk-scroll{overflow-x:auto;background:var(--card);
  border:1px solid var(--line3);border-radius:var(--r-card-lg);
  box-shadow:var(--sh-raise),var(--sh-hair);position:relative;z-index:2}
/* 2026-10-01 市场页改左右两列后右列变窄（1440 视口 ≈1120px）：
   min-width 1240→1080，colgroup 百分比自动缩，回归「表自身零溢出」保持成立 */
.mk-table{width:100%;min-width:1080px;table-layout:fixed}
.mk-table thead th{background:var(--card);vertical-align:top;line-height:16px;
  border-bottom:1px solid var(--line3);white-space:nowrap;padding:8px var(--sp-2)}
/* 2026-09-30 用户反馈：表头目录主词颜色加深（--sub 灰太浅，升到 --sub2 深灰） */
.mk-table thead th{color:var(--sub2)}
/* 2026-09-29 主词横向对齐（用户反馈）：单行表头默认垂直居中、双行表头顶格，
   两排主词错位——统一顶对齐后所有主词在同一水平线，小字自然垂在下方 */
.tscroll table thead th{vertical-align:top;line-height:16px}
/* 2026-09-29 两行表头压紧（用户反馈）：主词行高 22→16、小字行高压到 13、
   间距 2→1、上下 padding 11→8 —— 表头带整体变矮 */
.mk-table thead .th-sub{margin-top:1px;line-height:13px}
/* 2026-09-29 首尾列收到 24px（用户反馈：表格几乎撑到面板边）；中间列距 8→6px，
   输入价/输出价/缓存价之间的空隙同步压缩 */
.mk-table thead th:first-child,.mk-table tbody td:first-child{padding-left:calc(var(--sp-5)*1.5)}
.mk-table thead th:last-child,.mk-table tbody td:last-child{padding-right:calc(var(--sp-5)*1.5)}
.mk-table tbody td{padding:11px var(--sp-2);font-size:var(--fs-sm)}
/* 成功率表头的副行小字（主词大、窗口小），避免长表头占掉一整列宽 */
.mk-table .th-sub{display:block;font-style:normal;font-weight:var(--fw-med);
  font-size:var(--fs-cap);color:var(--dim);letter-spacing:0;margin-top:2px}
/* 价差徽章并入平台价列后的间距 */
.mk-table td.plat .save-tag{margin-left:6px}
/* 2026-09-29 列距统一 + 表头对齐（用户反馈：列间距不均、表头与列内容错位）：
   ① 数值列给定基准宽（auto 布局只会按内容分余量，列距漂移），
      渠道列与路由列吃剩余宽度；输入/输出价两列给窄宽，视觉上自然靠近；
   ② 第 2 列起表头与单元格统一居中，表头小字(.th-sub)随之对准列中心；
   ③ .rates/.score/.acts 是 flex，text-align 对 flex 无效，单独补 justify-content */
.mk-table thead th:nth-child(n+2),.mk-table tbody td:nth-child(n+2){text-align:center}
/* 2026-09-30 用户反馈：输入/输出价格列内容不换行（列宽收窄后防折行） */
.mk-table td.plat{white-space:nowrap}
.mk-table td:nth-child(n+2) .rates,
.mk-table td:nth-child(n+2) .score,
.mk-table td:nth-child(n+2) .acts{justify-content:center;flex-wrap:wrap}
/* 成功率三框**必须一行**（用户 2026-09-29 痛斥过折行）。上条给 .rates 的
   flex-wrap:wrap 是无意的：2026-10-01 收窄输入价/延迟列时，成功率列跟着变紧，
   3×(42px+gap)+padding 超过列宽 → 「实时/24h」一行、「7天」掉到第二行。
   数字竖排两行看着像坏掉了。改 nowrap 让它永不折行，宁可该列自己撑开。 */
.mk-table td:nth-child(n+2) .rates{flex-wrap:nowrap}
/* 列宽不在 CSS 定：market.html 的 colgroup 按百分比给定（fixed 布局），
   此前 nth-child 定宽/渠道列 320px 两版均已废弃——auto 布局下定宽列会
   让"剩余宽度"集中倾泻，空隙永远不均 */
.mk-table tbody tr.gp td{border-top:1px solid var(--line3)}
.mk-table tbody tr:first-child td{border-top:none}
/* 模型组头（上下结构，2026-09-29 参考 A6api 改版）：
   模型信息通栏在上，它的全部渠道行在下 —— 取代旧的「模型列 rowspan 纵向合并」。
   2026-09-30 用户反馈：组与组之间无缝粘连，分不清哪些渠道属于哪个模型 ——
   组头顶边改用 10px 页面底色粗边（表格行无法设 margin，用底色 border 模拟组间空隙），
   视觉上每组各成一块；首个组头贴着表头不留缝 */
.mk-table tr.mk-band td{background:var(--card2);border-top:10px solid var(--bg);padding:12px var(--sp-4)}
.mk-table tbody tr.mk-band:first-child td{border-top:none}
.mk-table tr.mk-band + tr td{border-top:none}
.mk-band .band-in{display:flex;align-items:center;justify-content:space-between;gap:14px;flex-wrap:wrap}
.mk-band .b-main{display:flex;align-items:baseline;gap:10px;flex-wrap:wrap}
.mk-band .mk-name{display:inline-flex;align-items:center;gap:7px;
  font-size:var(--fs-lg);font-weight:var(--fw-semi);color:var(--ink);
  line-height:var(--lh-sm);letter-spacing:var(--ls-sub)}
.mk-band .mk-name:hover{color:var(--cyan)}
.mk-band .mk-id{margin-top:0}
.mk-band .b-meta{display:flex;align-items:center;gap:12px;flex-wrap:wrap;font-size:var(--fs-xs);color:var(--sub)}
.mk-band .b-meta i{width:1px;height:12px;background:var(--line2);flex:none}
.mk-band .b-item{white-space:nowrap;font-variant-numeric:tabular-nums}
/* 组头数值改「淡标签 + 实值」两级：em=指标名（淡），b=数值（实）——扫读时数字先跳出来 */
.mk-band .b-item em{font-style:normal;font-weight:var(--fw-reg);color:var(--dim);margin-right:5px}
.mk-band .b-item em:last-child{margin-right:0;margin-left:3px}
.mk-band .b-item b{color:var(--ink);font-weight:var(--fw-semi)}
.mk-band .b-item b.save{color:var(--green)}
/* 渠道列结构化：第一行 = logo + 名称 + 类型标签 + 当前路由；第二行 = 全名 · 地域 · SLA */
.ch-top{display:flex;align-items:center;gap:6px;flex-wrap:wrap}
/* 品牌色 monogram 徽标（logo 位）：圆角小方块 + 白色首字；
   上真 logo 时把 .ldot 换成 <img>，圆角/尺寸沿用本规则 */
.ldot{width:18px;height:18px;border-radius:5px;color:#fff;font-size:11px;
  font-weight:var(--fw-bold);display:inline-flex;align-items:center;justify-content:center;
  flex:none;line-height:1;letter-spacing:0}
/* 真 logo 版（<img>）：白底细边衬托，透明底 ico 在浅色卡上不糊 */
img.ldot{object-fit:contain;background:#fff;border:1px solid var(--line2);padding:1px}
/* 2026-09-30 用户要求：快选渠道 logo 调大（16→22px，与组头 .mk-name 同档） */
.hbar .opt .ldot{width:22px;height:22px;border-radius:6px;font-size:12px}
.mk-band .mk-name .ldot{width:22px;height:22px;border-radius:6px;font-size:12px}
/* 比价表内的 pill 统一收小一号，避免标签比正文还抢眼 */
.mk-table .pill{padding:1px 8px;font-size:var(--fs-cap)}
/* 2026-10-02 删除此处重复定义（`.rb{min-width:56px;background:var(--fill2)…}`）：
   与上面 §成功率三小格 的唯一定义冲突，且它还在给"每格一块底"上色 ——
   正是用户投诉「三列距离太大、其实是一个版块」的病源。组件唯一来源在上方。 */
/* 固定路由的行：极浅青底 + 行首一条青色竖线（只加在第一个单元格，
   此前误加在所有 td 上，列间全是竖线——已修正） */
.mk-table tbody tr.pinned td{background:rgba(var(--cyan-rgb),.045)}
.mk-table tbody tr.pinned td:first-child{box-shadow:inset 3px 0 0 var(--cyan)}
.mk-table tbody tr.pinned:hover td{background:rgba(var(--cyan-rgb),.08)}
/* 面板头部「探针更新 HH:MM」：替代原分页徽章，与底部页码条不再重复 */
.mk-fresh{display:inline-flex;align-items:center;gap:7px;font-size:var(--fs-xs);color:var(--sub);
  background:var(--fill2);border:1px solid var(--line2);border-radius:var(--r-pill);padding:4px 12px}
/* 2026-09-30 用户反馈（二次）：副说明小字紧挨「全站比价明细」标题右侧同行，
   不是卡片最右 —— .pt 转为行内 flex 基线对齐，小字去段间距、不抢占剩余宽度。
   作用域收窄到 .mkpanel：panel-h .pt 是全站面板头通用结构，不能全局改 flex */
.mkpanel .panel-h .pt{display:flex;align-items:baseline;gap:var(--sp-3);flex-wrap:wrap}
.mkpanel .panel-h .pt .mk-sub-inline{margin-top:0;line-height:var(--lh-sm);white-space:nowrap}
/* 2026-09-30 用户反馈：组头类目徽章（文本/图像/视频/语音、接入中）去卡片化 ——
   去掉底色/描边/内边距，只保留类目色文字（色彩预算原则：位置本身已是标识，不再需要卡片） */
.mk-table .b-main .chip{background:none;border:none;padding:0;font-weight:var(--fw-med)}
/* 模型名：全站唯一一份定义在 §「模型组头」处（.mk-band .mk-name）。
   此处曾有一份 .mk-name 基准规则与组头规则同名冲突（display 三处互相覆盖：block →
   inline-block → inline-flex，只有最后一份生效），已合并归位，避免"改了不生效"的假修改。 */
.mk-id{font-size:var(--fs-cap);color:var(--dim);margin-top:3px;word-break:break-all;line-height:var(--lh-cap)}
.mk-meta{display:flex;align-items:center;gap:var(--sp-2);flex-wrap:wrap;margin-top:var(--sp-3)}
.mk-chan{font-size:var(--fs-cap);color:var(--sub)}
.mk-price{margin-top:var(--sp-3);font-size:var(--fs-xs);color:var(--sub);font-variant-numeric:tabular-nums}
.mk-price b{color:var(--ink);font-weight:var(--fw-semi)}
.mk-price b.save{color:var(--green)}
.mk-tags{display:flex;gap:10px;flex-wrap:wrap;margin-top:var(--sp-1)}
/* 渠道标签行去卡片化（2026-09-29 用户要求）：标签 = 纯文字小号语义色，
   不再占胶囊位；名称行旁的状态徽标（官方直连/当前路由）不受影响 */
.mk-tags .pill{margin-right:0;background:none;border:none;padding:0;border-radius:0;
  font-size:var(--fs-cap);font-weight:var(--fw-semi)}
/* 卡片视图同位置标签行（chanTags）：同一套裸文字处理，语义色与列表视图一致 */
.chan-badges{gap:10px}
.chan-badges .badge.plain{background:none;border:none;padding:0;border-radius:0;
  font-size:var(--fs-cap);font-weight:var(--fw-semi)}
.chan-badges .badge.plain.t-cheap{color:var(--cyan)}
.chan-badges .badge.plain.t-fast{color:var(--green)}
.chan-badges .badge.plain.t-stable{color:var(--purple)}
.chan-badges .badge.plain.t-trust{color:var(--amber)}
/* 模型详情页渠道表「标签」列：同一套裸文字处理 */
.tagcell{white-space:nowrap}
.tagcell .tag{background:none;border:none;padding:0;border-radius:0;
  font-size:var(--fs-cap);font-weight:var(--fw-semi)}
.tagcell .tag + .tag{margin-left:10px}
.ch .cur{color:var(--cyan);font-size:var(--fs-cap);font-weight:var(--fw-semi)}
.sc-sub{font-size:var(--fs-cap);color:var(--sub);margin-top:3px}
.pin-link{font-size:var(--fs-xs);color:var(--sub);white-space:nowrap;align-self:center}
.pin-link:hover{color:var(--cyan)}
.more{display:block;width:100%;text-align:center;padding:12px;background:var(--fill2);border:none;
  border-top:1px solid var(--line2);color:var(--sub2);font-size:var(--fs-xs);font-weight:var(--fw-med);
  cursor:pointer;transition:background-color var(--t-base) var(--e-out),color var(--t-base) var(--e-out)}
.more:hover{background:rgba(var(--cyan-rgb),.07);color:var(--cyan)}
.msec .tscroll{border-top:0}
.msec table{min-width:1080px}
.ch{font-weight:var(--fw-semi);font-size:var(--fs-sm)}
.ch small{display:block;color:var(--sub);font-weight:var(--fw-reg);font-size:var(--fs-cap);margin-top:3px}
/* 比价表内：渠道列小字允许换行（ pills/渠道名/地域/SLA 一行放不下就折两行），
   其余数值列保持 nowrap —— 这一条是「窄屏一屏放全」的关键收缩点 */
.mk-table .ch small{white-space:normal}
/* 官方牌价 = 对照参考值，不是「被划掉的旧价」。
   此前整列加 line-through：一屏 20 行全是删除线，读起来像「处处打折」，
   语义上更等于宣称官方价已失效 —— 两者都不是事实，也把表格视觉拉乱。
   列名「官方牌价」已说明它是什么；比官方便宜多少由平台价列的「省 X%」表达。 */
.plat{color:var(--cyan);font-weight:var(--fw-semi);font-variant-numeric:tabular-nums;font-size:var(--fs-base)}
.plat small{font-size:var(--fs-cap);color:var(--sub);font-weight:var(--fw-reg)}
/* 2026-09-29 官方牌价并入价格列：仅与平台价有差时出现的小字官方注 */
.plat .p-off{font-size:var(--fs-cap);color:var(--dim);font-weight:var(--fw-reg);
  margin-top:2px;font-variant-numeric:tabular-nums}
.cache{font-size:var(--fs-xs);color:var(--sub2);font-variant-numeric:tabular-nums}
.lat{font-variant-numeric:tabular-nums;font-weight:var(--fw-semi)}
.lat.good{color:var(--green)}.lat.mid{color:var(--amber)}.lat.bad{color:var(--red)}
.acts{display:flex;gap:8px}
.pin{background:var(--fill4);border:1px solid var(--line);color:var(--sub2);border-radius:var(--r-ctl);
  padding:7px var(--sp-4);font-size:var(--fs-xs);font-weight:var(--fw-med);cursor:pointer;
  white-space:nowrap;transition:border-color var(--t-base) var(--e-out),color var(--t-base) var(--e-out),
    background-color var(--t-base) var(--e-out)}
.pin:hover{border-color:rgba(var(--cyan-rgb),.5);color:var(--cyan)}
.pin.on{background:var(--btn-grad);color:var(--btn-ink);border-color:transparent;
  box-shadow:0 4px 14px rgba(var(--cyan-rgb),.3)}

/* ---------- 榜单页：左榜单导航 + 右图表区 ---------- */
.rank-grid{display:grid;grid-template-columns:224px minmax(0,1fr);gap:22px;align-items:start;
  margin-top:22px;position:relative;z-index:2}
/* 2026-10-02 用户点名「右边有些出去了」：明细表 12 列，通用单元格横向内边距
   (16px×2×12=384px 纯 padding) 把整表自然需求宽顶到 1133px ——
   1440 视口可用 1136px，余量仅 3px（踩线）；1280 溢出 157px，右端「比价」列被推出面板。
   压缩横向内边距 16→8（先例 .ktab 密钥表同款做法），整表自然宽约 -190px → ~941px，
   1280 视口可用 976px 装得下。纵向 padding 不动（行高的呼吸感不能跟着牺牲）。 */
.rank-grid thead th{padding:11px var(--sp-3)}
.rank-grid tbody td{padding:var(--sp-4) var(--sp-3)}
.ranknav{position:sticky;top:82px;max-height:calc(100vh - 100px);overflow-y:auto;
  padding:var(--sp-5) var(--sp-4)}
.ranknav::-webkit-scrollbar{width:6px}
.ranknav::-webkit-scrollbar-thumb{background:var(--line4);border-radius:var(--r-pill)}
.ranknav h5{font-size:var(--fs-cap);font-weight:var(--fw-bold);color:var(--sub);
  letter-spacing:var(--ls-cap);text-transform:uppercase;margin:var(--sp-4) var(--sp-3) var(--sp-2)}
.ranknav h5:first-child{margin-top:0}
.ranknav a{display:flex;align-items:center;gap:var(--sp-3);padding:8px 10px;
  border-radius:var(--r-ctl);font-size:var(--fs-sm);color:var(--sub2);cursor:pointer;
  transition:background-color var(--t-base) var(--e-out),color var(--t-base) var(--e-out)}
.ranknav a:hover{background:var(--fill2);color:var(--ink)}
.ranknav a.on{background:var(--ink);color:var(--bg);font-weight:700}
.ranknav a .ico{width:15px;text-align:center;opacity:.8;font-size:12px}

/* ---- 控制台工作台壳层（2026-09-29 参考主流模型平台控制台重排）----
   分组侧栏（常规/个人）+ 右侧内容区，每个版块自带「页头行」：
   标题 + 一句话副题 + 右侧动作位。只列真实存在的功能，没有端点的不上目录。 */
/* 控制台工作台：无页头（2026-09-29 用户要求删除），首屏直接是分组目录 + 内容。
   顶部留白 = 固定导航 64px + 呼吸 26px，内容不得顶进导航底下 */
.cshell{display:grid;grid-template-columns:236px minmax(0,1fr);gap:22px;align-items:start;margin-top:90px}
.cside{position:sticky;top:82px;max-height:calc(100vh - 100px);overflow-y:auto;
  background:var(--card);border:1px solid var(--line3);border-radius:var(--r-sm);
  padding:14px 12px;box-shadow:var(--shadow)}
.cside::-webkit-scrollbar{width:6px}
.cside::-webkit-scrollbar-thumb{background:var(--line4);border-radius:var(--r-pill)}
.cside h6{font-size:var(--fs-xs);font-weight:var(--fw-bold);color:var(--dim);
  letter-spacing:.08em;margin:16px 6px 6px;text-transform:uppercase}
.cside h6:first-child{margin-top:0}
.cside a{display:flex;align-items:center;gap:11px;padding:9px 10px;border-radius:var(--r-xs);
  font-size:var(--fs-base);color:var(--sub2);text-decoration:none;
  transition:color .16s,background-color .16s}
.cside a:hover{background:var(--fill2);color:var(--ink)}
.cside a.on{background:rgba(var(--cyan-rgb),.10);color:var(--cyan);font-weight:700}
.cside a .ico{width:17px;text-align:center;font-size:13px;opacity:.85}
.cuser{margin-top:14px;padding-top:12px;border-top:1px solid var(--line3);
  display:flex;gap:10px;align-items:center;cursor:pointer;min-width:0}
.cava{width:34px;height:34px;border-radius:var(--r-pill);background:var(--ink);color:var(--bg);
  display:flex;align-items:center;justify-content:center;font-weight:var(--fw-bold);
  font-size:var(--fs-base);flex:none}
.cuser .nm{font-size:var(--fs-sm);font-weight:var(--fw-bold);color:var(--ink);line-height:1.35;
  overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.cuser .ml{font-size:var(--fs-xs);color:var(--dim);line-height:1.35;
  overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
/* 版块页头行：标题 + 副题 + 右侧动作（对齐竞品控制台的每页顶部结构） */
.chead{display:flex;align-items:flex-end;gap:14px;margin:2px 0 16px;flex-wrap:wrap}
.chead h2{font-size:var(--fs-2xl);font-weight:var(--fw-bold);color:var(--ink);
  margin:0;letter-spacing:var(--ls-sub)}
.chead .cs{font-size:var(--fs-sm);color:var(--sub2);flex:1;min-width:200px;padding-bottom:2px}
.chead .ca{margin-left:auto;display:flex;gap:10px;align-items:center;flex-wrap:wrap}
/* 充值金额网格：预设档位单选 + 自定义 */
.tgrid{display:grid;grid-template-columns:repeat(3,1fr);gap:12px}
.tcell{border:1.5px solid var(--line5);background:var(--card);border-radius:var(--r-xs);
  padding:12px 14px;font-size:var(--fs-base);font-weight:var(--fw-semi);color:var(--ink);
  cursor:pointer;text-align:left;font-family:inherit;
  transition:border-color .16s,background-color .16s,color .16s}
.tcell:hover{border-color:var(--cyan)}
.tcell.on{border-color:var(--cyan);background:rgba(var(--cyan-rgb),.07);color:var(--cyan)}
@media(max-width:960px){
  .cshell{grid-template-columns:minmax(0,1fr)}
  .cside{position:static;max-height:none}
  .tgrid{grid-template-columns:repeat(2,1fr)}
}
.medal{display:inline-flex;align-items:center;justify-content:center;width:24px;height:24px;
  border-radius:var(--r-ctl);font-size:var(--fs-xs);font-weight:var(--fw-semi);
  background:var(--fill3);color:var(--sub2)}
.medal.m1{background:#eab308;color:#fff}
.medal.m2{background:#94a3b8;color:#fff}
.medal.m3{background:#c2833a;color:#fff}

/* 页脚 */
footer{border-top:1px solid var(--line);background:var(--fill2);padding:34px 0 28px;
  position:relative;z-index:2;margin-top:44px}
/* 2026-10-02 用户指令：内页页尾留下的内容（四个导航链接）居中排版。
   原来是 space-between 左一个「块」右侧余量全丢，短内容看不出是页脚。 */
.foot-in{display:flex;justify-content:center;flex-wrap:wrap;gap:var(--sp-5);
  font-size:var(--fs-xs);color:var(--sub)}
/* 2026-09-30 用户反馈：链接下划线特效保留（曾一度移除，现恢复原样式） */
.foot-in a{color:var(--sub2);border-bottom:1px solid var(--linkline)}
.foot-in a:hover{color:var(--cyan);border-color:var(--cyan)}
.foot-links{display:flex;gap:18px;flex-wrap:wrap}
/* 2026-09-30 用户反馈：内页页脚统一改首页同款深色底。
   做法：在 footer 作用域内重声明深色主题的文字/线条/青色令牌 ——
   页脚内部所有 var(--sub)/var(--dim)/var(--linkline)（含 market.html 里的内联样式）
   都会就近取到深色值，无需改任何页面标记；只影响页脚，页面主体仍是浅色。 */
body.theme-light footer{background:#0a0a0f;border-top:1px solid rgba(255,255,255,.08);
  --ink:#ffffff; --sub:rgba(255,255,255,.55); --sub2:rgba(255,255,255,.75); --dim:rgba(255,255,255,.34);
  --line:rgba(255,255,255,.08); --line2:rgba(255,255,255,.045); --linkline:rgba(255,255,255,.18);
  --cyan:#00e5ff; --cyan-rgb:0,229,255}

/* 模态 */
.modal{position:fixed;inset:0;z-index:200;background:var(--panel-bg);backdrop-filter:blur(6px);
  display:none;align-items:center;justify-content:center;padding:20px}
.modal.show{display:flex}
.modal-box{max-width:520px;width:100%;background:var(--card2);border:1px solid var(--line3);
  border-radius:var(--r-card-lg);padding:var(--sp-7);box-shadow:var(--sh-over)}

/* 自绘弹窗（替代原生 prompt/confirm） */
.ab-dlg{z-index:500}
.ab-dlg-box{max-width:min(460px,calc(100vw - 40px))}
.ab-dlg-title{font-size:var(--fs-xl);line-height:var(--lh-xl);margin-bottom:var(--sp-3);
  letter-spacing:var(--ls-sub);font-weight:var(--fw-semi)}
.ab-dlg-desc{color:var(--sub);font-size:var(--fs-sm);line-height:var(--lh-md);margin-bottom:var(--sp-5)}
.dlg-label{display:block;font-size:var(--fs-xs);color:var(--sub);margin-bottom:var(--sp-2);
  font-weight:var(--fw-med);letter-spacing:var(--ls-label)}
.dlg-input{width:100%;background:var(--fill);border:1px solid var(--line4);color:var(--ink);
  border-radius:var(--r-ctl);padding:11px var(--sp-4);font-size:var(--fs-base);outline:none;
  transition:border-color var(--t-base) var(--e-out),box-shadow var(--t-base) var(--e-out)}
.dlg-input::placeholder{color:var(--ph)}
.dlg-input:focus{border-color:var(--cyan);box-shadow:0 0 0 3px rgba(var(--cyan-rgb),.13);outline:none}
.ab-dlg-btns{display:flex;gap:var(--sp-4);justify-content:flex-end;margin-top:var(--sp-6)}

/* 表单弹窗（AB.form）：建 Key 时选渠道范围与选路策略 */
.ab-formbox{max-width:min(640px,calc(100vw - 40px));max-height:88vh;overflow-y:auto;overflow-x:hidden}
/* 表单弹窗内容可能比屏幕高（渠道多时）：按钮吸底，保证永远点得到 */
.ab-formbox .ab-dlg-btns{position:sticky;bottom:-1px;margin-top:20px;padding-top:14px;
  background:var(--card2);border-top:1px solid var(--line);z-index:2}
.dlg-row{margin-top:18px}
.dlg-row:first-of-type{margin-top:0}
.dlg-hint{font-size:var(--fs-xs);color:var(--sub);line-height:var(--lh-sm);margin-top:var(--sp-3)}
.dlg-hint b{color:var(--cyan)}
select.dlg-input{appearance:none;cursor:pointer;
  background-image:linear-gradient(45deg,transparent 50%,var(--sub) 50%),linear-gradient(135deg,var(--sub) 50%,transparent 50%);
  background-position:calc(100% - 19px) calc(50% + 1px),calc(100% - 14px) calc(50% + 1px);
  background-size:5px 5px,5px 5px;background-repeat:no-repeat;padding-right:38px}
.dlg-checks{display:grid;grid-template-columns:repeat(auto-fill,minmax(200px,1fr));gap:9px;margin-top:9px}
.dlg-chk{display:flex;align-items:flex-start;gap:var(--sp-3);padding:10px var(--sp-4);
  border:1px solid var(--line);border-radius:var(--r-ctl);cursor:pointer;background:var(--fill2);
  transition:border-color var(--t-base) var(--e-out),background-color var(--t-base) var(--e-out)}
.dlg-chk:hover{border-color:rgba(var(--cyan-rgb),.5);background:rgba(var(--cyan-rgb),.05)}
.dlg-chk input{margin:3px 0 0;width:16px;height:16px;flex:none;accent-color:var(--cyan);cursor:pointer}
.dlg-chk>span{display:flex;flex-direction:column;gap:3px;flex:1 1 auto;min-width:0;
  font-size:var(--fs-sm);line-height:var(--lh-sm);overflow-wrap:anywhere}
.dlg-chk b{font-weight:700;overflow-wrap:anywhere}
.dlg-chk i{font-style:normal;font-size:11px;color:var(--sub)}
.dlg-chk input:disabled+span{opacity:.38}
.dlg-chk:has(input:disabled){opacity:.55}
.dlg-all{grid-column:1/-1;background:rgba(var(--cyan-rgb),.06);border-color:rgba(var(--cyan-rgb),.3)}
.dlg-all b{font-size:var(--fs-sm)}
.ab-dlg-alert{display:none;margin-top:var(--sp-5);padding:10px var(--sp-4);
  border-radius:var(--r-ctl);font-size:var(--fs-xs);line-height:var(--lh-sm);color:var(--red);background:rgba(var(--red-rgb),.09);border:1px solid rgba(var(--red-rgb),.32)}
.ab-dlg-alert.show{display:block}
.ab-dlg-wide{max-width:min(760px,calc(100vw - 40px))}

/* 弹窗内的小表格（选路试算结果） */
.dlg-table{width:100%;border-collapse:collapse;font-size:var(--fs-xs)}
/* 弹窗里的表格不受全站 .tscroll table 的最小宽度约束（否则小弹窗会被撑出横向滚动条） */
.tscroll table.dlg-table{min-width:0}
.dlg-table th{text-align:left;color:var(--sub);font-weight:var(--fw-semi);padding:6px 9px;
  border-bottom:1px solid var(--line);white-space:nowrap;font-size:var(--fs-cap);
  letter-spacing:var(--ls-label)}
.dlg-table td{padding:7px 9px;border-bottom:1px solid var(--line2);white-space:nowrap}
.dlg-table tr:last-child td{border-bottom:0}
.dlg-table-title{font-size:var(--fs-xs);color:var(--sub2);margin-bottom:var(--sp-2);
  font-weight:var(--fw-med)}

@media(max-width:1100px){
  .kpis{grid-template-columns:repeat(3,minmax(0,1fr))}
  .grid3{grid-template-columns:1fr}
  /* 单列也必须用 minmax(0,1fr)：纯 1fr 的最小尺寸是 auto，会被内部宽表撑破视口 */
  .layout{grid-template-columns:minmax(0,1fr)}
  .rail{position:static;max-height:none}
}
/* 榜单栅格单独断点 1240（2026-10-02 量出来的，不是拍的）：
   明细表 12 列压缩内边距后自然需求宽约 941px，装得下的最低视口 ≈ 941+224+22+页面边距 ≈ 1231px。
   若沿用 1100 断点，1160~1240 区间侧栏还占着 224px，表格溢出 85px（「比价」列被推出）。
   1240 以下侧栏折叠成单列，表格独占整行宽（1080 视口实测可用 1022px > 941）。 */
@media(max-width:1240px){
  .rank-grid{grid-template-columns:minmax(0,1fr)}
  .ranknav{position:static;max-height:none}
}
@media(max-width:760px){
  .kpis{grid-template-columns:repeat(2,minmax(0,1fr))}
  .nav-links{display:none}
  .row2,.grid2{grid-template-columns:1fr}
  .dlg-checks{grid-template-columns:1fr}
  .modal-box{padding:20px 18px}
  .chan-grid{grid-template-columns:1fr;padding:14px}
  .price3{grid-template-columns:1fr 1fr;gap:8px}
}
/* 中屏（窗口拖窄到 1200 以下）：徽章区整体挪到第二行整宽排。
   为什么需要这条：徽章区实测需 448px 才排得开一行。
   视口 1160 时 avail=786，扣掉名称 150 + 价格行 349 + gap 28，
   只剩 133px 给徽章 —— flex-wrap 会把 5 个徽章**一个一个**竖排，
   组头从 87px 暴涨到 195~242px，比修之前还难看。
   grid 不会自动换行（这正是我们要的：价格行永不换行），
   但"整块换到第二行"必须显式写：meta 跨两列、独占第二行。
   这样徽章拿到整行宽（718~1186px），只需 2~3 行，组头稳定在 120~140px。
   ⚠️ 断点 1200 是量出来的，不是拍的：
   1240 视口 meta 还有 213px、组头 99~129px 尚可；
   1160 视口 meta 掉到 133px 就塌了。 */
/* 中屏：徽章区整块挪到第二行独占整宽（阶段 M 后组头是三行：
   行1 模型名 / 行2 徽章 / 行3 模型ID + 价格行）。
   每一行都要显式写 grid-row —— auto 流动会随徽章数量漂移，
   而且 .meta 与 .mid 会抢同一个 row:2。 */
@media(max-width:1200px){
  .msec-head{grid-template-columns:auto max-content}
  .msec-head > .mn{grid-column:1;grid-row:1}
  .msec-head > .meta{grid-column:1 / -1;grid-row:2}
  .msec-head > .mid{grid-column:1;grid-row:3}
  .msec-head > .right{grid-column:2;grid-row:3;justify-self:end}
}
/* 窄屏：单列堆叠，四行全靠左，右对齐在窄屏读起来反而是错位。 */
@media(max-width:760px){
  .msec-head{grid-template-columns:minmax(0,1fr);gap:10px}
  /* 模型名要给右上角的折扣角标让出位置 —— 单列后 .mn 默认 stretch 撑满整行，
     角标会直接压住字。⚠️ 必须用 justify-self:start + max-width 缩**盒子**，
     不能只加 padding-right：padding 只缩内容区，盒子仍与角标重叠（实测仍报叠压）。 */
  .msec-head > .mn{grid-column:1;grid-row:1;justify-self:start;max-width:calc(100% - 96px)}
  .msec-head > .meta{grid-column:1;grid-row:2}
  .msec-head > .mid{grid-column:1;grid-row:3}
  .msec-head > .right{grid-column:1;grid-row:4;justify-self:start;flex-wrap:wrap}
}

/* ============================================================
   内页设计系统（Design System v2）
   ------------------------------------------------------------
   问题：工具页此前是"白纸上的字"——页头是纯留白块，区块是裸白盒，
   页面之间没有统一语言，信息主次靠字号硬撑。
   本段补上一套内页语言（浅色工具页专用，深色首页不受影响）：

     · 头带      header.page  → 装饰底图：网格 + 双色光晕 + 节点连线 + 底部渐变细线
     · 事实芯片  .pmeta/.pm   → 把"口径/时效"这类次要事实收成一行小胶囊
     · 数据带    .kpis        → 五格连体（内部发丝分隔），替代 5 个漂浮白盒
     · 区块标题  .sec-head    → 渐变小竖条 + 标题 + 副说明 + 右侧动作，底部横规线
     · 面板      .panel       → 有头的容器（头/身/脚），替代裸白盒
     · 提示      .notice      → 图标 + 结构化文案
     · 步骤      .steps       → 编号方块 + 连接
     · 代码框    .codebox     → 标题栏（圆点 + 文件名 + 复制）
     · 参数行    .kv          → 左键右值的定义列表

   两条纪律：
     1) 所有装饰层 pointer-events:none —— 装饰永远不许抢点击。
     2) 所有颜色走语义令牌，不写死 —— 换肤只需换令牌。
   ============================================================ */

/* ---------- 1. 页面头带 ---------- */
header.page{
  position:relative;z-index:2;overflow:hidden;
  /* 2026-10-01 用户反馈：页头下方留白过多 → padding-bottom 54→24px（副题到内容总空隙 92→62px） */
  padding:108px 0 24px;
  /* 2026-10-01 用户反馈：页头与下方内容「横线切开很割裂」→ 去掉 border-bottom 硬线，
     靠背景渐变（本底已渐到 var(--bg)）+ 装饰层底部 mask 渐隐自然过渡 */
  background:
    radial-gradient(880px 320px at 10% -14%,rgba(var(--cyan-rgb),.05),transparent 64%),
    radial-gradient(760px 300px at 90% -10%,rgba(var(--purple-rgb),.045),transparent 62%),
    linear-gradient(180deg,var(--sheen) 0%,var(--bg) 100%);
}
/* 细网格底纹：仅在上半部显出，向下渐隐 */
header.page::before{
  content:'';position:absolute;inset:0;pointer-events:none;
  background-image:
    linear-gradient(var(--grid) 1px,transparent 1px),
    linear-gradient(90deg,var(--grid) 1px,transparent 1px);
  background-size:46px 46px;
  -webkit-mask-image:radial-gradient(130% 96% at 50% -6%,#000 8%,transparent 74%);
  mask-image:radial-gradient(130% 96% at 50% -6%,#000 8%,transparent 74%);
}
/* 底边收口线已删（2026-10-01 用户反馈横线割裂）：改为装饰层整体底部渐隐，
   光晕/轨道弧线在页头底边淡出到页面底色，不再有可见分界 */
header.page .wrap,header.page .wrap-narrow{position:relative;z-index:3}

/* 装饰层（由 app.js 的 AB.heroDeco() 注入，避免每页手写） */
.ph-deco{position:absolute;inset:0;pointer-events:none;z-index:1;overflow:hidden;
  /* 底部 ~30% 渐隐：装饰在页头下缘淡出到 --bg，消除被 overflow 裁切的硬边 */
  -webkit-mask:linear-gradient(180deg,#fff 68%,transparent 99%);
  mask:linear-gradient(180deg,#fff 68%,transparent 99%)}
.ph-deco .ph-net{
  position:absolute;right:-70px;top:-30px;width:660px;height:370px;
  background:var(--grad);opacity:.10;
  -webkit-mask-image:url("data:image/svg+xml,%3Csvg%20xmlns='http://www.w3.org/2000/svg'%20viewBox='0%200%20640%20360'%20fill='none'%3E%3Cg%20stroke='%23000'%20stroke-width='1.3'%3E%3Cpath%20d='M40%20268%20168%20200%20300%20236%20428%20148%20596%20178'/%3E%3Cpath%20d='M168%20200%20236%2088%20428%20148'/%3E%3Cpath%20d='M300%20236%20356%20316'/%3E%3Cpath%20d='M428%20148%20512%2058'/%3E%3C/g%3E%3Cg%20fill='%23000'%3E%3Ccircle%20cx='40'%20cy='268'%20r='5'/%3E%3Ccircle%20cx='168'%20cy='200'%20r='7'/%3E%3Ccircle%20cx='300'%20cy='236'%20r='5'/%3E%3Ccircle%20cx='428'%20cy='148'%20r='8'/%3E%3Ccircle%20cx='596'%20cy='178'%20r='5'/%3E%3Ccircle%20cx='236'%20cy='88'%20r='4.5'/%3E%3Ccircle%20cx='356'%20cy='316'%20r='4.5'/%3E%3Ccircle%20cx='512'%20cy='58'%20r='4.5'/%3E%3C/g%3E%3C/svg%3E");
  mask-image:url("data:image/svg+xml,%3Csvg%20xmlns='http://www.w3.org/2000/svg'%20viewBox='0%200%20640%20360'%20fill='none'%3E%3Cg%20stroke='%23000'%20stroke-width='1.3'%3E%3Cpath%20d='M40%20268%20168%20200%20300%20236%20428%20148%20596%20178'/%3E%3Cpath%20d='M168%20200%20236%2088%20428%20148'/%3E%3Cpath%20d='M300%20236%20356%20316'/%3E%3Cpath%20d='M428%20148%20512%2058'/%3E%3C/g%3E%3Cg%20fill='%23000'%3E%3Ccircle%20cx='40'%20cy='268'%20r='5'/%3E%3Ccircle%20cx='168'%20cy='200'%20r='7'/%3E%3Ccircle%20cx='300'%20cy='236'%20r='5'/%3E%3Ccircle%20cx='428'%20cy='148'%20r='8'/%3E%3Ccircle%20cx='596'%20cy='178'%20r='5'/%3E%3Ccircle%20cx='236'%20cy='88'%20r='4.5'/%3E%3Ccircle%20cx='356'%20cy='316'%20r='4.5'/%3E%3Ccircle%20cx='512'%20cy='58'%20r='4.5'/%3E%3C/g%3E%3C/svg%3E");
  -webkit-mask-repeat:no-repeat;mask-repeat:no-repeat;
  -webkit-mask-position:right top;mask-position:right top;
  -webkit-mask-size:contain;mask-size:contain;
}
.ph-deco .ph-glow{position:absolute;border-radius:50%;filter:blur(46px)}
.ph-deco .ph-glow.g1{width:420px;height:200px;left:-90px;bottom:-120px;background:rgba(var(--cyan-rgb),.12)}
.ph-deco .ph-glow.g2{width:360px;height:180px;left:38%;bottom:-140px;background:rgba(var(--purple-rgb),.10)}
/* 方案 B（2026-09-30）：浅色页头加强首页母题 —— 星球轨道弧线 + 发光节点。
   弧线=大圆细描边从右上探入（呼应首页星球弧），节点=轨道上的青/紫/粉光点。
   全部 pointer-events:none（继承 .ph-deco），窄屏由 overflow:hidden 裁掉 */
.ph-deco .ph-orbit{position:absolute;border-radius:50%;border:1px solid rgba(var(--cyan-rgb),.16)}
.ph-deco .ph-orbit.o1{width:560px;height:560px;right:-150px;top:-330px}
.ph-deco .ph-orbit.o2{width:860px;height:860px;right:-270px;top:-480px;border-color:rgba(var(--purple-rgb),.11)}
.ph-deco .ph-dot{position:absolute;border-radius:50%;opacity:.55}
.ph-deco .ph-dot.d1{width:7px;height:7px;right:212px;top:98px;background:var(--cyan);
  box-shadow:0 0 0 4px rgba(var(--cyan-rgb),.14),0 0 14px rgba(var(--cyan-rgb),.5)}
.ph-deco .ph-dot.d2{width:5px;height:5px;right:96px;top:172px;background:var(--purple);
  box-shadow:0 0 0 4px rgba(var(--purple-rgb),.13),0 0 12px rgba(var(--purple-rgb),.45)}
.ph-deco .ph-dot.d3{width:4px;height:4px;right:332px;top:36px;background:var(--pink);opacity:.45;
  box-shadow:0 0 0 3px rgba(var(--pink-rgb),.12)}

/* 居中变体：进入型页面（文档/供应商）用 */
.phero-c{text-align:center}
.phero-c .sub{margin-left:auto;margin-right:auto}
.phero-c .pmeta{justify-content:center}
/* 2026-09-30 备注：.ph-compact 紧凑/横排变体已整体回退删除——用户先嫌占位高，
   压缩后嫌信息被压住，横排后嫌乱，最终结论=原居中版式最稳，不再动它。
   沉淀两条教训：①固定顶栏高 65px，页头 padding-top 不得低于它；
   ②站内非顶栏导航别用裸 <nav> 标签（app.css:186 nav{position:fixed} 会误伤）。 */

/* 2026-09-30 记录：内页首屏相关性「方案 A（深色开场带）」试点后用户选了方案 B
   （保持浅色、加强首页母题），整块 hero-dark 样式已删。方案 B 实现见 .ph-deco 加强 +
   .page-aura 轨道弧线；「页头顶部留白 ≥ 65px 固定顶栏」的规则继续有效 */

/* 页头眉标：小胶囊（仅浅色工具页；深色首页保持原样） */
body.theme-light .eyebrow{
  display:inline-flex;align-items:center;gap:8px;
  margin-bottom:var(--sp-4);padding:5px var(--sp-4) 5px 11px;border-radius:var(--r-pill);
  font-size:var(--fs-cap);font-weight:var(--fw-bold);letter-spacing:var(--ls-cap);
  color:var(--cyan);background:var(--card);border:1px solid var(--line3);
  box-shadow:var(--sh-contact),var(--sh-ring);
}
body.theme-light .eyebrow::before{
  content:'';width:6px;height:6px;border-radius:50%;background:var(--grad);flex:none;
}
.page .sub{font-size:var(--fs-lg);line-height:var(--lh-xl);letter-spacing:var(--ls-body);margin-top:var(--sp-5);max-width:660px}
.page .sub b{color:var(--ink);font-weight:var(--fw-med);border-bottom:1px solid rgba(var(--cyan-rgb),.35)}

/* 数据带 .kpis：连体小格，内部发丝分隔，替代漂浮白盒。
   ⚠ 2026-09-29 重建：基础样式此前随市场页 KPI 清理被整体误删，而 console/model/admin
   三页页头仍在引用 —— 表现为数值失去网格、竖排挤成一列。市场页自己已不用它，
   但只要还有引用方，这份样式就必须留在 app.css；删除前先全仓搜引用。 */
/* 2026-10-02 阶段 Z｜P2 模型详情页「渠道价差分布条」
   把「最高省 N%」从一个数字变成一张图：横轴 = 价格，每个点 = 一家渠道的最低报价。
   设计取舍：① 点用 provider 语义色（官方/优选/普通一眼分得出），
   最低价那颗用 cyan + 实心并加 .best，是视觉焦点；
   ② 刻度只标两端（最省 / 最贵），中间标百分比数字会挤成一团；
   ③ 同价多家横向错开 7% —— 叠成一个点会让人以为只有 1 家在卖；
   ④ 高度只用 46px，不与下方报价表抢视线（这张图是"引导去挑"，不是主角）。 */
.spreadbar{margin-top:var(--sp-5);padding:16px 20px 18px}
.sb-h{display:flex;align-items:baseline;gap:12px;flex-wrap:wrap;margin-bottom:14px}
.sb-t{font-size:var(--fs-sm);font-weight:var(--fw-bold)}
.sb-n{font-size:var(--fs-cap);color:var(--cyan);font-variant-numeric:tabular-nums;font-weight:var(--fw-semi)}
.sb-hint{font-size:var(--fs-cap);color:var(--dim);margin-left:auto}
/* 轴：一条底线 + 绝对定位的点。高度留 26px 给点的 10px 直径 + hover 抬升 */
.sb-axis{position:relative;height:26px;margin:0 8px}
.sb-axis::before{content:'';position:absolute;left:0;right:0;bottom:7px;height:1px;background:var(--line3)}
.sb-dot{position:absolute;bottom:2px;width:11px;height:11px;border-radius:50%;
  transform:translateX(-50%);background:var(--sub2);border:1.5px solid var(--card);
  transition:transform .16s,box-shadow .16s;cursor:default}
.sb-dot.best{background:var(--cyan);width:13px;height:13px;bottom:1px;
  box-shadow:0 0 0 3px rgba(var(--cyan-rgb),.18)}
.sb-dot:hover{transform:translateX(-50%) translateY(-3px);
  box-shadow:0 3px 8px rgba(0,0,0,.28)}
.sb-scale{display:flex;justify-content:space-between;margin:9px 8px 0;
  font-size:var(--fs-cap);color:var(--sub);font-variant-numeric:tabular-nums}
.sb-scale .sb-flat{color:var(--amber)}

./* 2026-10-02 阶段 Z｜P3 控制台身份说明条
   刻意做成一条轻量横幅而不是 .mk-head 那种页头：控制台是工具型布局，
   顶部高度要留给功能区。这条只回答一句话——「这是谁的账户、能干什么、钱花在哪」。 */
.cv-id{display:flex;align-items:center;gap:18px;flex-wrap:wrap;
  padding:12px 16px;margin-bottom:var(--sp-5);
  background:var(--fill2);border:1px solid var(--line3);border-radius:var(--r-ctl)}
.cv-id-l{font-size:var(--fs-sm);color:var(--sub);line-height:1.6;min-width:0;flex:1 1 320px}
.cv-id-l b{color:var(--ink);font-weight:var(--fw-semi)}
.cv-id-a{flex:none;font-size:var(--fs-cap);font-weight:var(--fw-semi);color:var(--cyan);
  white-space:nowrap;transition:transform .16s}
.cv-id-a:hover{transform:translateX(2px)}

.kpis{display:grid;grid-template-columns:repeat(auto-fit,minmax(150px,1fr));margin-top:var(--sp-6);
  background:var(--card);border:1px solid var(--line3);border-radius:var(--r-sm);
  box-shadow:var(--shadow);overflow:hidden}
.kpis .kpi{padding:14px 18px;border-left:1px solid var(--line3);min-width:0}
.kpis .kpi:first-child{border-left:none}
.kpis .kpi .v{font-size:var(--fs-2xl);font-weight:var(--fw-bold);color:var(--ink);
  font-variant-numeric:tabular-nums;line-height:1.25}
/* 2026-10-03 用户指令「数字换一下颜色，比如绿色之类的」。
   ⚠ 只给榜单页「本窗口实测口径」这一条数据带加 .k-green，**不改 .kpis 组件本身**——
   .kpis 是共用组件（全站 console 5 处 / model 1 / admin 1 / rank 1，共 8 处引用），
   而其中 console 的数字是「当前余额」「本周消费」「累计计费金额」——
   **花钱不是好事，把消费额染成绿色等于给错信号**。所以这类"换个颜色"的需求
   必须先数清组件引用、看清每个引用点的语义，纯中性的数据带才可加类。
   为什么这四条可以染绿：它们是"实测证据"（探测次数/成功率/覆盖/延迟），
   与站内 .live 绿点、.ok 绿字同属"系统实测正常"的语义绿，不是涨跌含义。
   色值用现成 --green（浅色主题 #0f9960），不新增令牌：
   数字 20px/700 属 WCAG 大字（≥18.66px bold），3:1 即达标，实测白底上 3.65:1。 */
.kpis.k-green .kpi .v{color:var(--green)}
.kpis .kpi .k{margin-top:3px;font-size:var(--fs-cap);color:var(--sub2);line-height:1.55}
/* KPI 口径注释独立小行（如「按 27 笔文本调用计」），不再挤成一长串括号 */
.kpis .kpi .k small{display:block;margin-top:2px;font-size:var(--fs-xs);color:var(--sub);
  font-weight:var(--fw-reg);line-height:1.5}

/* 事实芯片行：承载"口径 / 时效 / 规模"这类次要事实 */
.pmeta{display:flex;align-items:center;gap:9px;flex-wrap:wrap;margin-top:22px}
.pmeta .pm{
  display:inline-flex;align-items:center;gap:7px;
  font-size:var(--fs-xs);color:var(--sub2);letter-spacing:var(--ls-body);
  background:var(--card);border:1px solid var(--line3);border-radius:var(--r-pill);
  padding:5px var(--sp-4);box-shadow:var(--sh-contact);white-space:nowrap;
}
.pmeta .pm b{color:var(--ink);font-weight:var(--fw-semi);font-variant-numeric:tabular-nums}
.pmeta .pm .dot{width:6px;height:6px;border-radius:50%;background:var(--green);flex:none;
  box-shadow:0 0 0 3px rgba(var(--green-rgb),.16)}
.pmeta .pm .dot.warn{background:var(--amber);box-shadow:0 0 0 3px rgba(var(--amber-rgb),.16)}
.pmeta .pm .dot.idle{background:var(--dim);box-shadow:0 0 0 3px var(--fill4)}

/* ---------- 2. 数据带（替代 5 个漂浮白盒） ---------- */
/* ---------- 3. 区块标题 ---------- */
.sec{margin:38px 0;position:relative;z-index:2}
.sec-head{
  display:flex;align-items:center;gap:13px;flex-wrap:wrap;
  padding-bottom:13px;margin-bottom:18px;
  border-bottom:1px solid var(--line3);position:relative;
}
.sec-head::before{
  content:'';width:3px;height:18px;border-radius:2px;background:var(--grad);flex:none;
}
.sec-head h2{font-size:var(--fs-3xl);font-weight:var(--fw-semi);letter-spacing:var(--ls-title);line-height:var(--lh-xl)}
.sec-head h3{font-size:var(--fs-lg);font-weight:var(--fw-semi);letter-spacing:var(--ls-sub)}
.sec-head .more,.sec-head .r{margin-left:auto}
.sec-head .more{font-size:var(--fs-sm);color:var(--cyan);font-weight:var(--fw-med)}
.sec-head .hint{font-size:var(--fs-xs);color:var(--sub);line-height:var(--lh-xs)}
/* 横向标签导航（文档页用） */
.sec-head .tabs,.sec-head .seg{margin-left:auto}

/* ---------- 4. 面板（替代裸白盒） ---------- */
.panel{
  background:var(--card);border:1px solid var(--line3);border-radius:var(--r-card-lg);
  box-shadow:var(--sh-raise),var(--sh-hair);overflow:hidden;position:relative;z-index:2;
}
.panel-h{
  display:flex;align-items:center;gap:14px;flex-wrap:wrap;
  padding:var(--sp-5) var(--sp-6);border-bottom:1px solid var(--line2);
  background:linear-gradient(180deg,var(--sheen) 0%,transparent 100%);
}
.panel-h .pt{min-width:0;flex:1}
.panel-h h3{font-size:var(--fs-lg);font-weight:var(--fw-semi);letter-spacing:var(--ls-sub);display:flex;align-items:center;gap:var(--sp-3)}
.panel-h h3 .ic{
  width:22px;height:22px;border-radius:var(--r-chip);flex:none;display:grid;place-items:center;
  background:rgba(var(--cyan-rgb),.1);color:var(--cyan);font-size:var(--fs-cap);font-weight:var(--fw-bold);
}
.panel-h p{font-size:var(--fs-sm);color:var(--sub);margin-top:var(--sp-1);line-height:var(--lh-sm)}
.panel-h .pa{margin-left:auto;display:flex;align-items:center;gap:10px;flex-wrap:wrap}
.panel-b{padding:var(--sp-6)}
.panel-b.flush{padding:0}
/* 2026-10-02 用户点名「两页内容左右撑太靠边，往里收一些 / 放在卡片中间位置」。
   病根有两层，都必须一起解，否则改一处坏一处：

   ① **面板放宽到 1132px 那一轮只改了容器宽度，没同步内边距**。
      .panel-b 的 20px 是为原来 852px 窄容器定的档；容器放大 1.33 倍后
      20px 的相对宽度从 2.3% 掉到 1.8%，内容开始"贴边"——
      实测内容左边缘距卡片边只有 21px。单独提到 32px 能解决"贴边"，
      但只解决一半。

   ② **真正让版面失衡的是「卡片很宽 + 内容只占左边一块」**：
      .sup-form 封了 760px 却是左对齐，实测 gapL=21px / gapR=351px ——
      同一张卡片里两个数字差 16 倍，视觉上必然读成"半张空白"。
      光给表单加 margin-inline:auto 居中会更糟：面板头标题仍贴在 33px 处，
      表单飘到 186px 处 → **标题和它的内容脱节**，比原来更难看。

   所以正确解法是**让整个面板内容（panel-h + panel-b）作为一个居中列**：
   用 max(32px, (100% - 900px)/2) 做左右内边距 —— 宽屏时自动变成 116px 让
   900px 内容列居中，窄屏回落到 32px 下限。效果是：
     · 标题 / 表格头 / 步骤流 / 表单**共享同一条左基线**（都在 116px）；
     · 左右严格对称（都是 116px），卡片不再"半张空白"；
     · 一条规则同时管住所有面板宽度，不靠逐个元素打补丁。

   为什么 flush 面板（端点表 / 错误码表 / 报价格子表）不动：
   它们是满宽表格/代码框 —— docs 的端点表 4 列、supplier 的报价表 8 列且
   min-width:900px，收窄会逼出横向滚动条。满宽表格满宽是对的，
   它有 cell padding 自己管边距（实测首列缩进 17px），不参与居中。

   作用域收窄到 .wrap-narrow —— 实测全站只有 docs.html / supplier.html 在用它，
   是这两页天然的钩子；全站 .panel-h / .panel-b 不动
   （榜单 / 模型 / 控制台的面板还是 852px 级窄容器，20px 在那里是正确的）。 */
/* 2026-10-02 用户第三次点名宽度：「卡片往中间收一下，卡片里的内容宽度要类似，
   不能有的收进来、有的宽很多」。
   旧规则（已删）是用 max(32px,(100%-900px)/2) 给非 flush 面板做 900px 居中列，
   结果同一页出现两种宽度：文字/表单 900px，满宽表格 1130px —— 割裂的来源。
   现在宽度只有一个来源：容器（1028 → panel 980）。
   所有面板统一 --sp-8(32px) 左右内边距 → 内容列 914px；
   flush 表格满宽 978px，与内容列差 64px，属同一档，不逼出横向滚动
   （报价表 min-width:900px < 978px）。 */
.wrap-narrow .panel-h,
.wrap-narrow .panel-b:not(.flush){
  padding-left:var(--sp-8);
  padding-right:var(--sp-8);
}
.panel-f{
  display:flex;align-items:center;gap:12px;flex-wrap:wrap;
  padding:var(--sp-4) var(--sp-6);border-top:1px solid var(--line2);
  background:var(--sheen);font-size:var(--fs-xs);color:var(--sub);
}
.panel-f .pa{margin-left:auto;display:flex;align-items:center;gap:10px}

/* ---------- 5. 提示（图标 + 结构化） ---------- */
/* ⚠ ::before 里不能用 background:currentColor 配 color:var(--card)：
   currentColor 取的是「本元素最终 color」，会被同一规则里的 color 覆盖，
   结果图标底色变成卡片白 → 在浅色页上直接看不见。所以显式给一个 --nc 变量。 */
.notice{
  display:block;padding:var(--sp-5) var(--sp-5) var(--sp-5) 46px;border-radius:var(--r-card);font-size:var(--fs-sm);
  line-height:var(--lh-base);position:relative;z-index:2;--nc:var(--sub2);
}
/* 作者 display 会压掉 UA 的 [hidden]，显式补一条（2026-10-01 低余额条误显示的根因） */
.notice[hidden]{display:none}
.notice::before{
  position:absolute;left:15px;top:14px;width:19px;height:19px;border-radius:50%;
  display:grid;place-items:center;font-size:12px;font-weight:900;font-style:normal;
  background:var(--nc);color:#fff;
}
.notice.info::before{content:'i'}
.notice.warn::before{content:'!'}
.notice.danger::before{content:'!'}
.notice.ok::before{content:'✓'}
.notice.info{background:rgba(var(--cyan-rgb),.07);border:1px solid rgba(var(--cyan-rgb),.26);color:var(--cyan);
  --nc:var(--cyan)}
.notice.warn{background:rgba(var(--amber-rgb),.08);border:1px solid rgba(var(--amber-rgb),.3);color:var(--amber);
  --nc:var(--amber)}
.notice.danger{background:rgba(var(--red-rgb),.07);border:1px solid rgba(var(--red-rgb),.3);color:var(--red);
  --nc:var(--red)}
.notice.ok{background:rgba(var(--green-rgb),.07);border:1px solid rgba(var(--green-rgb),.3);color:var(--green);
  --nc:var(--green)}
.notice b{color:var(--ink)}

/* ---------- 5b. 悬停说明（标题旁的 ⓘ → 浮层） ----------
   2026-10-02 用户要求：把榜单明细上方那一大块常驻口径说明，收成标题右侧的
   小圆圈图标，鼠标触碰才展开。三条实现约束（都是踩过的坑，不是风格偏好）：
   ① **浮层必须 position:fixed 挂 body**。.panel 是 overflow:hidden，
      浮层若放在面板内会被裁掉一半（这个坑和 .notice 里的 z-index:2 同源）。
   ② **图标底色绝不用 currentColor** —— 它取本元素最终 color，会被同规则的
      color 覆盖成透明/白，在浅色页上直接看不见（.notice 上方已记此历史 bug）。
   ③ **图标不填实底，改中性描边 + 琥珀字（2026-10-02 用户第二次调整）**。
      用户原话：「圆圈填充琥珀色，感觉太重了……圆圈不填色，只保留圆圈，
      比如深灰色等，i 符号采用亮色」。这个判断是对的，而且有量化的依据：
      一个 20px **实心**圆的着色面积是 314px²，而描边环只有约 60px² ——
      差 5 倍。上一版把全页最重的一块颜色，挂在了一句 67 字的补充说明上，
      视觉权重和它的信息量完全不匹配。

      为什么描边用 `--sub` 而不是更淡的 `--dim`／`--icon`：
      按 WCAG 1.4.11（非文本对比）描边要过 3:1，实测
        --dim  #98a1ad  2.61:1 ✗   --icon #8d96a3 2.99:1 ✗（差一点点）
        --ph   #a8b0bb  2.19:1 ✗   --sub  #6b7280 4.83:1 ✓
      所以 `--sub` 是"能看清轮廓又不重"的最小可用档。它同时也是双主题
      安全的：浅色主题是 #6b7280（深灰），深色主题是 rgba(255,255,255,.55)
      （浅灰），两边都自动成立，不用写主题分支。

      为什么 i 保留 `--amber`（实测 5.02:1，AA 级）：用户要"能看到"，
      中性灰字只有 2.0~3.0:1 做字色不合格。琥珀既醒目又是站内 warn 语义，
      去掉实底后它的面积从 314px² 缩到约 40px² —— 「醒目」的信息提示保住了，
      「重」的观感没了。

      ★ 环宽历史（本条已被 2026-10-02 推翻，改成 1px，理由见 .qtip 规则内的表）：
      当时定 2px 的依据是"1.5px 环跨两个像素、抗锯齿对半混，dpr=1 实测
        水平 3.97:1 / 斜45° 2.49:1 ✗（低于 WCAG 1.4.11 的 3:1）"，
      推论是"2px 跨像素时每边都有 1px 完整覆盖，任意方向都稳"。
      ★ 那个推论只对了一半：它比较的是 1.5px 与 2px，**没把 1px 放进来比**，
      而 1px 的水平实测与 1.5px 同为 3.97:1 —— 也就是说 1px 环在
      正上/正下/正左/正右四个方向和 1.5px 一样清楚，只是斜向更虚。
      结论：这枚图标是**按需召出的补充说明**，它的第一职责是"不打扰"，
      WCAG 1.4.11 管的是"有意义的非文本元素"，这里信息量本就低；
      克制优先于斜向对比度。留这张表是为了以后别再凭 1.5 vs 2 就下结论。

   浮层内文字颜色走语义令牌：正文 --sub2（比 .notice 的青色弱一档，
   因为它现在是按需召出的次级说明，不该跟表格里的数据抢注意力）。 */
.qtip{
  width:20px;height:20px;border-radius:50%;flex:none;display:grid;place-items:center;
  /* 描边而不是实底：见上面第 ③ 条的面积对比（314px² 实心 vs 126px² 2px 环，只剩 40%）。
     ⚠️ 环用 `box-shadow: inset` 画，**不是 border** —— 实测写
     `border:1.5px solid` 在 devicePixelRatio=1 下被浏览器**取整成 1px**，
     20px 的圆上 1px 环会发虚；而 border-width 是整数px 的硬限制，给不出 1.5px。
     box-shadow 的 spread 不受这个量化影响，能给任意精度。
     用 inset（向内收）而不是 outset（向外扩）：outset 会让圆的视觉直径
     从 20px 变成 24px，贴在大标题旁时旁边文字的间距会莫名其妙变窄。
     ⚠️ spread 加粗只往内收，不动元素尺寸 —— 所以改环宽不需要重调任何布局。 */
  background:transparent;
  border:0;
  box-shadow:inset 0 0 0 1px var(--sub);
  color:var(--amber);
  font-size:12px;font-weight:900;line-height:1;
  /* 2026-10-02 环宽 2px → 1px（用户：「太粗了，细的就行，太抢了」）。
     像素级实测三档（dpr=1，底色 rgb(252,252,253)，--sub=#6b7280）：

       环宽   水平实测   水平对比   斜45°对比
       1px     4px       3.97:1     1.72:1
       1.5px   4px       3.97:1     2.49:1
       2px     6px       4.72:1     4.72:1

     1px 环跨两个像素各占一半，所以正上/正下/正左/正右仍采得到完整的
     3.97:1；代价是斜 45° 看只剩 1.72:1（发虚）。
     在"细而克制"和"任意角度都稳"之间，**明确选了前者** ——
     这个图标是按需召出的补充说明，抢眼本身就是缺点。
     ⚠️ 若哪天要改回 2px：注释里那张表就是依据，别再凭印象重测。

     font-style 从 italic → normal（用户：「i 居中直立，不用故意放斜」）。
     之前那版斜体是抄系统 UI 里"信息"图标的惯例，但斜 i 放在 1px 细环里
     重心偏右上，斜45° 环本来就发虚，两者叠加显得"歪" —— 主体修正，
     不是装饰。直立后由 `display:grid;place-items:center` 自然居中，
     不需要任何 transform 找补。 */
  font-family:inherit;padding:0;cursor:help;flex-shrink:0;
  /* hover 反馈保持「环加深 + i 不变」：--sub(#6b7280) 与 --sub2(#3f4653) 在
     中性灰里就是一档明显的深浅差，足够传达"可交互"；
     上一版的 brightness(1.08) 作用在实底上还行，改成描边后
     会让整圈发灰发糊，反而更看不清。 */
  transition:box-shadow var(--t-fast) var(--e-out),
             transform var(--t-fast) var(--e-out);
}
.qtip:hover,.qtip[aria-expanded="true"]{
  box-shadow:inset 0 0 0 1px var(--sub2);   /* 环加深：轮廓更清楚 */
  transform:scale(1.12);
}
.qtip:focus-visible{outline:2px solid rgba(var(--amber-rgb),.55);outline-offset:2px}
/* 内页大标题变体（2026-10-02 供应商页用）。
   榜单页那个 20px 圆圈是贴在 22px 的 .panel-h h3 旁，尺寸是对的；
   但页头 h1 是 clamp(30px,4.4vw,46px) 的居中大标题 —— 20px 圆圈贴在 46px
   文字旁会明显偏小（视觉直径只有标题字的 0.43 倍），且 h1 没有 flex 布局，
   按钮会落在基线上导致上下都不居中。所以这里给 24px + 显式对齐的变体。
   24px 是量出来的：与 46px 标题的字高匹配，且不抢过 eyebrow 与副题。 */
.phero-c h1 .qtip{
  width:24px;height:24px;font-size:14px;
  display:inline-grid;vertical-align:middle;margin-left:var(--sp-3);
  transform:translateY(-2px);          /* 视觉居中：圆形比文字字形略高，需上提 */
}
.phero-c h1 .qtip:hover,.phero-c h1 .qtip[aria-expanded="true"]{
  transform:translateY(-2px) scale(1.12);
}
.qtip-box{
  position:fixed;z-index:300;left:0;top:0;max-width:min(520px,90vw);
  max-height:min(62vh,440px);overflow:auto;
  background:var(--card);border:1px solid var(--line3);border-radius:var(--r-card);
  box-shadow:var(--sh-lift);padding:var(--sp-5) var(--sp-5) var(--sp-5) 44px;
  font-size:var(--fs-sm);line-height:var(--lh-base);color:var(--sub2);
  opacity:0;visibility:hidden;transform:translateY(-4px);
  transition:opacity var(--t-base) var(--e-out),transform var(--t-base) var(--e-out);
}
.qtip-box.on{opacity:1;visibility:visible;transform:none}
.qtip-box::before{
  content:'i';position:absolute;left:14px;top:var(--sp-5);width:20px;height:20px;border-radius:50%;
  display:grid;place-items:center;font-size:12px;font-weight:900;
  /* 与标题旁的 .qtip **逐项同配方**（尺寸/环宽/环色/字色/字重/字形全一致）。
     上一版这里是 19px + 13px 字号 + 实底琥珀，改标题图标时漏了这里 →
     浮层内的小圆点比标题旁的重好几倍，同一页两种粗细。
     **同一组件的多个实例必须同配方**，这是第二次被"改一处忘一处"绊到
     （第一次是漏删 .sup-ver 死代码）。
     尺寸也一并对齐到 20px/12px，不是抄 .qtip 的数值好看而已：环在 19px
     圆上内径更小，塞 13px 字会挤到笔画贴环；20px 圆 + 12px 字
     是同一个比例，浮层与标题旁的视觉重量才真的相等。
     ring 用 inset box-shadow 而非 border —— border-width 被取整到整数 px，
     给不出亚像素；inset 的 spread 只往内收，浮层左边距（padding-left:44px）
     不用动。环宽 2px→1px 与 font-style italic→normal 跟 .qtip 同步，
     见上面 .qtip 规则内的说明。 */
  background:transparent;
  border:0;
  box-shadow:inset 0 0 0 1px var(--sub);
  color:var(--amber);
}
/* 口径是**两段**独立信息：「当前排序怎么排的」+「这些数是怎么测出来的」。
   原先两段只靠一个 <br> 隔开，糊成一片；给第二段一条 hairline 才读得出
   「上面讲规则、下面讲出处」。分隔线用 --line2（比 --line 更淡），
   否则会盖过里面的加粗强调。
   负 margin 通栏这件事我一度以为被 overflow 裁掉、差点改成 absolute ——
   量了才发现 gap 左右各 1px（正是边框），本来就通栏，是**我看截图看岔了**。
   教训照抄上一轮那条：视觉判断不算数，量了才算。 */
.qtip-box .qdiv{
  display:block;height:1px;background:var(--line2);
  margin:var(--sp-4) calc(var(--sp-5) * -1) var(--sp-4) -44px;
}
.qtip-box b{color:var(--ink);font-weight:var(--fw-semi)}
.qtip-box a{color:var(--cyan);text-decoration:underline;text-underline-offset:2px}
/* 小三角指向锚点图标。浮层与图标之间有 8px 悬空（JS 里的 GAP），
   没有这枚三角时浮层像"凭空出现"，不知道是从哪个点触发的。
   两个实现细节：
   ① 描边用 rotate(45deg) 的方块做，但**只留朝向浮层外的那两条边**
      （below 时留 top+left），否则浮层自身的边框会在三角根部横一道线。
   ② --qx 是三角**中心**的横坐标，CSS 里要减掉半个三角宽，
      否则 JS 传图标中心、视觉上三角偏左半个身位。 */
.qtip-box::after{
  content:'';position:absolute;left:calc(var(--qx,16px) - 5px);width:10px;height:10px;
  background:var(--card);border:1px solid var(--line3);
  transform:rotate(45deg);
}
.qtip-box[data-side="below"]::after{top:-6px;border-right:0;border-bottom:0}
.qtip-box[data-side="above"]::after{bottom:-6px;border-left:0;border-top:0}
/* 取代原先内联的 opacity:.75 —— 半透明黑在浅色页会灰到读不清，
   而"次级说明"本来就有语义令牌可走（--sub），比透明度更可控。 */
.qtip-box .qdim{color:var(--sub)}
.qtip-box .qlead{color:var(--ink);font-weight:var(--fw-semi)}
/* 浮层的内容源（只被 JS 读 innerHTML，不显示）。
   显式写 display:none 而不是只靠 hidden 属性 —— 与 .notice[hidden] 同理：
   作者样式里任何一条 display 都会压掉 UA 的 [hidden]，到时候说明块
   会"莫名其妙又出现在表格上方"，而这正是本次要消掉的东西。 */
.qtip-src{display:none}

/* ---------- 6. 步骤条 ---------- */
.steps{display:grid;gap:0}
.step{
  display:grid;grid-template-columns:30px minmax(0,1fr);gap:15px;
  padding:15px 0;border-top:1px solid var(--line2);
}
.step:first-child{border-top:0;padding-top:2px}
.step .n{
  width:26px;height:26px;border-radius:var(--r-ctl);display:grid;place-items:center;
  font-size:var(--fs-xs);font-weight:var(--fw-bold);flex:none;
  background:rgba(var(--cyan-rgb),.1);color:var(--cyan);border:1px solid rgba(var(--cyan-rgb),.28);
}
.step.now .n{background:var(--btn-grad);color:var(--btn-ink);border-color:transparent}
.step.dim .n{background:var(--fill4);color:var(--dim);border-color:var(--line3)}
.step .t{font-size:var(--fs-base);font-weight:var(--fw-semi);letter-spacing:var(--ls-sub);line-height:var(--lh-base)}
.step .d{font-size:var(--fs-sm);color:var(--sub2);line-height:var(--lh-md);margin-top:var(--sp-1)}
.step .d b{color:var(--ink)}

/* ---------- 7. 代码框 ---------- */
.codebox{
  background:var(--code-bg);border:1px solid rgba(255,255,255,.09);
  border-radius:var(--r-sm);overflow:hidden;
}
.codebar{
  display:flex;align-items:center;gap:7px;
  padding:9px 13px;background:rgba(255,255,255,.045);
  border-bottom:1px solid rgba(255,255,255,.07);
}
.codebar .d{width:9px;height:9px;border-radius:50%;background:rgba(255,255,255,.15);flex:none}
.codebar .fn{
  margin-left:7px;font-family:"JetBrains Mono",Consolas,monospace;
  font-size:var(--fs-cap);color:rgba(255,255,255,.42);
}
.codebox pre.code{
  background:none;border:none;border-radius:0;margin:0;padding:16px 18px;
}
.codebox .copy{
  margin-left:auto;background:rgba(255,255,255,.07);border-color:rgba(255,255,255,.14);
  color:rgba(255,255,255,.68);
}
.codebox .copy:hover{background:rgba(255,255,255,.12);color:#fff;border-color:rgba(255,255,255,.3)}

/* ---------- 8. 参数定义行 ---------- */
.kv{display:grid;gap:0}
.kv .row{
  display:grid;grid-template-columns:180px minmax(0,1fr);gap:var(--sp-5);
  padding:var(--sp-4) 0;border-top:1px solid var(--line2);font-size:var(--fs-sm);
}
.kv .row:first-child{border-top:0}
.kv .row .k{color:var(--sub);font-weight:var(--fw-med)}
.kv .row .v{color:var(--sub2);line-height:var(--lh-md)}
.kv .row .v b{color:var(--ink)}

/* 容器放宽到 1180 后，正文文字块的行长封顶（见 .readable 的来由）。
   只封**纯文字**，表格 / 代码框 / 表单 / 定义列表的键值都不封 ——
   那些是"结构化信息"，本来就该占满宽度，套上限反而是浪费。
   :where() 把整条规则压到 0 特异度：容器一改就生效，也不会反过来
   压平别处等特异度的选择器（v2 那条通用 input 规则的教训，见 MEMORY.md）。

   ⚠️ 选择器必须用 `.step .t + .d` 这种**相邻兄弟**而不是 `.step .d`：
   代码框标题栏里也有三个 <span class="d"></span>（Mac 风格红黄绿灯圆点，
   真类名是 .codebar .d，但它们是 .d、且嵌在第 2 步的 .step 内），
   同样匹配 `.step .d`。量出来是 3 个 9px 宽、0 字的空块 ——
   被误加 max-width 属于不精确选择器的典型隐患：今天无害，
   明天有人给 .codebar .d 加 padding 就成了真 bug。
   说明文字在 DOM 里紧跟 .t，用相邻兄弟锁定，语义也正好是"某步的说明"。 */
:where(.step) .t + .d,
:where(.notice) > div,
:where(.kv) .row .v{max-width:860px}
/* 步骤流里的代码框必须与同一条说明文字**同宽**（720 → 860，2026-10-02）。
   为什么要有上限：它上下都是 860px 的说明文字，若自己满宽 914px，
   深色底在白面板里会变成一条横贯全幅的横幅 —— 左边跟文字对齐、右边谁也不对齐。
   为什么必须等于 860 而不是留 720：量过实际是说明 860 / 代码框 720，
   右边缘差 140px，这正是用户点名的「有的收进来、有的宽很多」，
   只不过这次发生在同一个面板内部。宽度跟着上面的 :where(...) 三件套走。
   而 panel-b.flush 里那些代码框（调用示例、在线试用输出）是**独立 section**，
   上下没有说明文字陪着，满宽是对的，不受这条影响。 */
:where(.step) .codebox{max-width:860px}

/* ---------- 9. 大数字 ---------- */
.stat{display:flex;align-items:baseline;gap:9px}
.stat .n{
  font-size:clamp(30px,3.6vw,40px);font-weight:var(--fw-semi);letter-spacing:-.035em;
  font-variant-numeric:tabular-nums;line-height:1;
}
.stat .u{font-size:var(--fs-sm);font-weight:var(--fw-med);color:var(--sub)}

/* ---------- 10. 带标签分隔线 ---------- */
.dv{
  display:flex;align-items:center;gap:var(--sp-5);margin:var(--sp-8) 0;
  font-size:var(--fs-cap);font-weight:var(--fw-bold);letter-spacing:var(--ls-cap);text-transform:uppercase;color:var(--dim);
}
.dv::before,.dv::after{content:'';height:1px;background:var(--line3);flex:1}

/* ---------- 12. 锚点导航（文档页） ---------- */
/* ---------- 14. 头带内联排（宽屏时标题与右侧铭牌并排） ---------- */
.phero-in{display:grid;gap:30px}
@media(min-width:1120px){
  .phero-in.has-side{grid-template-columns:minmax(0,1fr) 300px;align-items:end}
}
.phero-side{
  background:var(--card);border:1px solid var(--line3);border-radius:var(--r-card);
  box-shadow:var(--sh-raise),var(--sh-hair);padding:var(--sp-5) var(--sp-5) var(--sp-4);
}
.phero-side .row2{
  display:flex;align-items:baseline;justify-content:space-between;gap:12px;
  padding:9px 0;border-top:1px solid var(--line2);font-size:var(--fs-xs);
}
.phero-side .row2:first-child{border-top:0;padding-top:0}
.phero-side .row2 .k{color:var(--sub)}
.phero-side .row2 .v{font-weight:var(--fw-semi);color:var(--ink);font-variant-numeric:tabular-nums}

/* ---------- 15. 横排响应式（仅窗口变窄，非移动端适配） ---------- */
@media(max-width:760px){
  .kv .row{grid-template-columns:1fr;gap:5px}
  .ph-deco .ph-net{width:380px;height:220px;right:-90px}
  .ph-deco .ph-orbit.o1{width:380px;height:380px;right:-110px;top:-230px}
  .ph-deco .ph-orbit.o2{width:560px;height:560px;right:-190px;top:-320px}
  .ph-deco .ph-dot.d1{right:132px;top:74px}
  .ph-deco .ph-dot.d2{right:64px;top:120px}
  .ph-deco .ph-dot.d3{right:206px;top:28px}
}

/* ---------- 17. 面板内文字与表格收口 ---------- */
.panel-h p b{color:var(--ink);font-weight:var(--fw-semi);font-variant-numeric:tabular-nums}
.panel .tscroll tbody tr:last-child td{border-bottom:0}
.panel .tscroll table{border-radius:0}

/* ---------- 18. 市场页比价面板（2026-09-29 起无内滚 + 底部分页） ---------- */
.mkpanel .mk-scroll{border:0;border-radius:0;box-shadow:none}
.mkpanel{scroll-margin-top:82px}
.mkpanel .panel-f{padding:0;border-top:1px solid var(--line3)}
.mk-pager{display:flex;justify-content:center;padding:14px}
/* 2026-09-29 分页条与上方表格边线贴死（用户反馈），留出 12px 呼吸 */
.pager{display:flex;gap:8px;align-items:center;flex-wrap:wrap;margin-top:var(--sp-4)}
.pager .pg{min-width:34px;height:32px;padding:0 12px;border:1px solid var(--line2);
  border-radius:8px;background:var(--card);color:var(--ink);font-size:var(--fs-sm);
  cursor:pointer;font-variant-numeric:tabular-nums}
.pager .pg:hover:not(:disabled):not(.on){border-color:var(--cyan);color:var(--cyan)}
.pager .pg.on{background:var(--ink);border-color:var(--ink);color:#fff;cursor:default}
.pager .pg:disabled{opacity:.4;cursor:default}
.pager .pg-dots{color:var(--dim);padding:0 2px}
.pager .pg-info{font-size:var(--fs-xs);color:var(--sub);margin-left:10px}

/* ============================================================
   19. 细节收口层（专业感来自这些"没人注意、但缺了就露怯"的细节）
   ------------------------------------------------------------
   参考站有而我们此前全缺：文字选中色、键盘焦点环、全局滚动条、
   表格行悬停、无障碍动态降级。缺这些，页面再整齐也像演示稿。
   ============================================================ */

/* 选中文字用品牌色，而不是浏览器默认蓝 —— 最廉价的"完成度"信号 */
::selection{background:rgba(var(--cyan-rgb),.26);color:var(--ink)}
body.theme-light ::selection{background:rgba(var(--cyan-rgb),.16)}

/* 键盘焦点环：只在键盘操作时出现（鼠标点击不显示），
   既保证可达性，又不会在鼠标流里留下脏边 */
:focus-visible{outline:2px solid rgba(var(--cyan-rgb),.7);outline-offset:2px;
  border-radius:var(--r-chip)}
.btn:focus-visible,.seg a:focus-visible,.tabs a:focus-visible{outline-offset:3px}

/* 全局滚动条：细、圆、悬停加深，且"浮"在内容上（透明描边内缩） */
*::-webkit-scrollbar{width:10px;height:10px}
*::-webkit-scrollbar-track{background:transparent}
*::-webkit-scrollbar-thumb{background:var(--line4);border-radius:var(--r-pill);
  border:3px solid transparent;background-clip:content-box}
*::-webkit-scrollbar-thumb:hover{background:var(--line5);background-clip:content-box}
*::-webkit-scrollbar-corner{background:transparent}

/* 表格行悬停：数据表必须能"顺着行横读"，这是可用性也是精致度 */
.panel table tbody tr,.tscroll table tbody tr,.mk-table tbody tr{
  transition:background-color var(--t-fast) var(--e-out)}
.panel table tbody tr:hover,.tscroll table tbody tr:hover,
.mk-table tbody tr:hover{background:var(--hover)}

/* 面板顶边一条 1px 渐变发丝线：比纯色描边高级，且不增加任何元素 */
.panel::after{
  content:'';position:absolute;left:0;right:0;top:0;height:1px;pointer-events:none;
  background:linear-gradient(90deg,transparent,rgba(var(--cyan-rgb),.3) 20%,
    rgba(var(--purple-rgb),.22) 58%,transparent 92%);
  opacity:.75;
}

/* 尊重系统"减少动态效果"（无障碍必需，也是 Mac 用户的常见设置） */
@media (prefers-reduced-motion:reduce){
  *,*::before,*::after{
    animation-duration:.01ms!important;animation-iteration-count:1!important;
    transition-duration:.01ms!important;scroll-behavior:auto!important}
}


/* ===== 2026-09-30 市场页去素升级（用户要求适度发挥；大布局/版块顺序不动） =====
   ① 顶部极光氛围层：呼应首页青紫的色彩语言（浅色页面用淡晕染版，向下渐隐）
   ② 模型分组带：左侧青色筋线 + 淡青渐变底，告别纯灰条
   ③ 「固定此渠道/详情」按钮质感：白底描边 + 悬停青色光圈，已固定态实心淡青
   ④ 行悬停淡青染色；⑤ 表头极淡渐变，压住纯白的"素" */
/* ===== 2026-10-02 用户要求：「交易市场的底色跟后面其他几个页面的保持一样」
   —— 病根不是"aura 太重"，而是**缺了一层内页才有的暖白渐变底**。

   像素实测（视口 1440，左缘 x=14 纯背景采样，非观感推测）：
     y=70   market #e6edf1   docs/supplier #f3f6f9   rank #f5f6f8
     y=100  market #eaf0f3   docs/supplier #f5f7f9   rank #f5f6f8
     y=160  market #f4f5f7   docs/supplier #f5f7f9   rank #f5f6f8
   market 顶部比内页**深 17.7 个色阶且偏青**，一眼能看出"不是一套底"。

   两种可能的修法，我选了第二种：
   ① 把 aura 的 alpha 从 .17/.15 压到内页的 .05/.045 —— 看着最省事，但那是
      2026-09-30 用户明确要的"去素升级①：顶部极光氛围层"，压掉等于推翻
      当时的需求；而且 rank 页根本没有 aura，压了 market 也不会让两页变同源。
   ② 在 aura **底下**垫一层内页同款暖白渐变底（--sheen → --bg）——
      market 顶部就从暖白起步再叠青紫光晕，与内页同源；aura 一分不损。

   为什么不给 .page-aura 加 background 而是新加一层：aura 带
   `mask:linear-gradient(#fff 55%,transparent 96%)`，mask 作用于**整层**
   （含背景）。若把暖白渐变写进 aura 的 background，它会被同一个 mask
   一起淡出，520px 之后又回到 body 的冷灰 --bg，接缝依旧。独立一层
   不带 mask，暖白才能一路铺到底。 */
.page-veil{
  position:absolute;top:0;left:0;right:0;height:520px;pointer-events:none;
  /* 520px = 与 .page-aura 等高，让暖白在极光层淡出时接管，两层同一收尾。
     z-index 故意不写 —— 与 .page-aura 同为 auto 时层叠由 DOM 先后决定，
     靠 market.html 里的排列顺序保证 veil 在下（见该文件注释）。 */
  background:linear-gradient(180deg,var(--sheen) 0%,var(--bg) 100%);
}
.page-aura{position:absolute;top:0;left:0;right:0;height:520px;pointer-events:none;overflow:hidden;
  background:
    radial-gradient(680px 340px at 14% -10%,rgba(var(--cyan-rgb),.17),transparent 70%),
    radial-gradient(800px 360px at 76% -14%,rgba(var(--purple-rgb),.15),transparent 70%),
    radial-gradient(540px 300px at 44% -8%,rgba(var(--pink-rgb),.08),transparent 72%);
  -webkit-mask:linear-gradient(#fff 55%,transparent 96%);
  mask:linear-gradient(#fff 55%,transparent 96%)}
/* 方案 B（2026-09-30）：市场页无大页头，轨道弧线挂在极光层上（同 .ph-orbit 母题，
   一起被极光层的向下渐隐 mask 收掉，不会生硬截断） */
.page-aura::before,.page-aura::after{content:'';position:absolute;border-radius:50%}
.page-aura::before{width:620px;height:620px;right:-140px;top:-360px;
  border:1px solid rgba(var(--cyan-rgb),.18)}
.page-aura::after{width:920px;height:920px;right:-280px;top:-500px;
  border:1px solid rgba(var(--purple-rgb),.12)}
/* 2026-09-30 二次调整：深色版太跳（用户原话「像创可贴」），回落浅色底——
   比最初的淡青渐变略加强（.07→.10），保证「有底色」但不抢行 */
.mk-table tr.mk-band td{background:linear-gradient(90deg,rgba(var(--cyan-rgb),.10),var(--card2) 55%)}
.mk-table tr.mk-band td:first-child{box-shadow:inset 3px 0 0 var(--cyan)}
.pin{background:var(--card);border-color:var(--line2);box-shadow:var(--sh-hair)}
.pin:hover{border-color:rgba(var(--cyan-rgb),.55);color:var(--cyan);
  box-shadow:0 0 0 3px rgba(var(--cyan-rgb),.12)}
.pin.on{background:rgba(var(--cyan-rgb),.10);border-color:rgba(var(--cyan-rgb),.45);color:var(--cyan)}
.pin-link{display:inline-flex;align-items:center;padding:7px var(--sp-4);border:1px solid transparent;
  border-radius:var(--r-ctl);font-weight:var(--fw-med);
  transition:border-color var(--t-base) var(--e-out),background-color var(--t-base) var(--e-out),color var(--t-base) var(--e-out)}
.pin-link:hover{border-color:rgba(var(--cyan-rgb),.5);background:rgba(var(--cyan-rgb),.06);color:var(--cyan)}
body.theme-light .mk-table tbody tr:hover{background:rgba(var(--cyan-rgb),.045)}
body.theme-light .mk-table thead th{background:linear-gradient(180deg,#fbfcfe,var(--card))}

/* ===== 2026-09-30 供应商入驻页按用户设计稿重排（.sup- 前缀，仅此页生效） =====
   版式：面包屑 → 居中页头 + 三特征卡（复用 .pmeta/.pm 标记过回归断言） →
   琥珀「当前版本说明」卡 → 横向五步入驻流程 → 分区表单（01 主体/02 供应）。
   功能件（表单 id/提交逻辑/我的状态区）一律不动 */
/* 页头面包屑（docs/supplier 共用） */
.page-crumbs{display:flex;align-items:center;gap:9px;font-size:var(--fs-sm);color:var(--dim)}
.page-crumbs a{color:var(--sub)}
.page-crumbs a:hover{color:var(--cyan)}
/* 页头三特征卡已删（2026-09-30 用户：与下方入驻流程五步重复） */
/* 版本说明卡 .sup-ver 已删（2026-10-02 用户：改成标题旁的 ⓘ 悬停浮层）。
   它原本是 852×74 的常驻琥珀提示带，进页面先读一段"这是演示版"的声明
   才看得到表单。样式里唯一值得留存的是「强调词用琥珀色」这条规则，
   已迁到 .qtip-box .qemph（见 §5b）。此处刻意不保留任何 .sup-ver 规则 ——
   留着就是无人调用的死代码，而下一次有人加 .sup-ver 会以为它还活着。 */
.qtip-box .qemph{color:var(--amber);font-weight:var(--fw-semi)}

/* 入驻流程横向五步（对照用户参考图 2026-09-30 二次精修）：
   编号小胶囊悬于圆上方；圆内放线性图标（非数字）；连线接圆缘，
   前 3 段青色、末段（04→05 未开通）变灰；05 步整体灰阶 + 琥珀「待开通」 */
.sup-flow{display:grid;grid-template-columns:repeat(5,1fr);position:relative}
.sup-flow::before{content:'';position:absolute;top:57px;height:2px;
  left:calc(10% + 31px);right:calc(10% + 31px);
  background:linear-gradient(90deg,rgba(var(--cyan-rgb),.32) 0 75%,var(--line4) 75% 100%)}
.sup-flow .sf{position:relative;display:flex;flex-direction:column;align-items:center;text-align:center}
.sup-flow .sf .np{font-size:var(--fs-xs);font-weight:var(--fw-bold);color:var(--cyan);letter-spacing:.04em;
  background:rgba(var(--cyan-rgb),.10);border-radius:var(--r-pill);padding:2px 11px;margin-bottom:9px}
.sup-flow .sf .n{width:54px;height:54px;border-radius:50%;display:inline-flex;align-items:center;justify-content:center;
  color:var(--cyan);background:var(--card);border:1.5px solid rgba(var(--cyan-rgb),.5);
  box-shadow:0 2px 8px rgba(15,40,60,.06);position:relative;z-index:1}
.sup-flow .sf .n svg{width:22px;height:22px}
.sup-flow .sf.dim .np{color:var(--dim);background:var(--fill4)}
.sup-flow .sf.dim .n{color:var(--dim);border-color:var(--line4);box-shadow:none}
.sup-flow .sf .t{margin-top:14px;font-size:15px;font-weight:var(--fw-bold);color:var(--ink);
  display:flex;align-items:center;gap:7px}
.sup-flow .sf.dim .t{color:var(--sub)}
/* .d 的 170px 上限是 852 容器时代的产物：当时每格 162px，字封顶 170px
   等于"字比格子宽一点"，视觉上是满的。容器放宽到 1132px 后每格 226px，
   字还封 170px 就是**容器宽了字没宽**，两侧各空 28px，五步流程会显得松垮。
   改成 200px：新格宽 226px，字占 88% 留 13px 呼吸，仍在单行可读长度内
   （"平台配置接入地址与密钥" 11 字 × 13px = 143px，不会折行）。 */
.sup-flow .sf .d{margin-top:5px;font-size:var(--fs-sm);color:var(--sub);line-height:var(--lh-sm);max-width:200px}
.sup-flow .sf.dim .d{color:var(--dim)}
/* 面板头图标版徽章（层叠图标圆徽，替代数字方块） */
.sup-ic{width:34px;height:34px;border-radius:50%}
.sup-ic svg{width:17px;height:17px}
@media(max-width:900px){.sup-flow{grid-template-columns:1fr 1fr;row-gap:var(--sp-5)}.sup-flow::before{display:none}
  .sup-flow .sf .t{margin-top:10px}}
/* 表单分区标题与提交行 */
.sup-fsec{display:flex;align-items:center;gap:9px;margin:var(--sp-2) 0 var(--sp-4);
  font-size:var(--fs-md);font-weight:var(--fw-semi);color:var(--ink)}
.sup-fsec span{font-size:var(--fs-xs);font-weight:var(--fw-bold);color:var(--cyan);
  background:rgba(var(--cyan-rgb),.10);border-radius:var(--r-chip);padding:2px 7px}
/* 入驻/报价表单的宽度上限（2026-10-02 第三次调整：760 → 860）。
   为什么要有上限：18 个字段里多数是 row2 两列，输入框横跨半屏时
   光标要跑很远才点得到右端，是典型的"宽屏灾难"。表单是需要**聚焦**的区域，
   宽度按"一屏看得完整个字段"定，不按容器。
   为什么是 860 而不是原来的 760：容器收到 1028 后内容列是 914px，
   表单卡在 760 会在右侧留 154px 空白 —— 这正是用户第三次点名的
   「有的收进来、有的宽很多」。860 与 .readable / 说明文字同宽，
   两列各约 420px，本页所有内容收在同一档宽度上。 */
.sup-form{max-width:860px}
.sup-submit{display:flex;align-items:center;justify-content:space-between;gap:var(--sp-5);margin-top:var(--sp-5)}
.sup-lock{display:inline-flex;align-items:center;gap:7px;font-size:var(--fs-xs);color:var(--sub)}
.sup-lock svg{width:14px;height:14px;color:var(--amber);flex:none}
@media(max-width:760px){
  .sup-submit{flex-direction:column;align-items:flex-start}
}


/* ===== 2026-09-30 筛选条按键/线框精修（用户点名：按键式线框粗糙随意） =====
   ① 面板：hbar/resbar 加极淡青渐变，压住纯白的"素"
   ② 快选芯片：计数变迷你徽标、悬停青描边微抬、选中态加深
   ③ 快选模型：有报价的价格行青色点亮，「接入中」保持灰（.pending 由 JS 标注）
   ④ 下拉框：发丝阴影 + 悬停青描边 + 聚焦青色光圈
   ⑤ 小标签：加青紫渐变筋点，呼应列表分组带筋线
   ⑥ 搜索按钮：渐变底上再加青色光晕 */
.hbar{border-color:var(--line2);
  background-image:linear-gradient(180deg,rgba(var(--cyan-rgb),.05),transparent 72%)}
.resbar{background-image:linear-gradient(90deg,rgba(var(--cyan-rgb),.045),transparent 46%)}
.hb-k::before,.resbar .hb-field .hb-label::before{content:'';display:inline-block;width:3px;height:10px;
  border-radius:2px;margin-right:7px;vertical-align:-1px;
  background:linear-gradient(180deg,var(--cyan),rgb(var(--purple-rgb)))}
.hbar .opt{border-color:var(--line2);box-shadow:0 1px 2px rgba(15,23,42,.05);
  transition:background-color var(--t-base) var(--e-out),border-color var(--t-base) var(--e-out),
    color var(--t-base) var(--e-out),box-shadow var(--t-base) var(--e-out),
    transform var(--t-base) var(--e-out)}
.hbar .opt:hover{border-color:rgba(var(--cyan-rgb),.45);color:var(--ink);
  box-shadow:0 3px 10px rgba(var(--cyan-rgb),.12);transform:translateY(-1px)}
.hbar .opt .cnt{padding:1px 7px;border-radius:999px;background:var(--fill2);
  font-weight:var(--fw-semi);line-height:1.5}
.hbar .opt.on{box-shadow:0 3px 12px rgba(15,23,42,.20)}
.hbar .opt.on .cnt{background:rgba(255,255,255,.18)}
.hbar .opt.qm:not(.pending) small{color:rgba(var(--cyan-rgb),.82);font-weight:var(--fw-semi)}
/* 2026-09-30 用户反馈：选中态黑底上文字看不清 → 模型名/价格整体反白（后置覆盖上面青价） */
.hbar .opt.qm.on b{color:var(--bg)}
.hbar .opt.qm.on small{color:rgba(255,255,255,.78);opacity:1}
.hb-sel{box-shadow:0 1px 2px rgba(15,23,42,.05)}
.hb-sel:hover{border-color:rgba(var(--cyan-rgb),.5)}
.hb-sel:focus{border-color:rgba(var(--cyan-rgb),.65);box-shadow:0 0 0 3px rgba(var(--cyan-rgb),.12)}
/* 2026-09-30 用户点名：搜索键调成首页的紫色（同 .btn-purple 的 --btn2-grad 渐变+白字） */
.resbar .pillsearch .go{background:var(--btn2-grad);color:#fff;
  box-shadow:0 2px 10px rgba(var(--purple-rgb),.30)}
.resbar .pillsearch .go:hover{box-shadow:0 4px 16px rgba(var(--purple-rgb),.42)}
.seg button.on{box-shadow:var(--sh-contact),0 0 0 1px var(--line2)}

/* ===== 2026-09-30 用户点名：结果工具条里的两个分段控件（/1M·/1K、列表·卡片）底改深色 =====
   容器近黑，选中片保持白底深字（反色最清晰），未选中片白字；作用域锁 .resbar 不影响别处 */
.resbar .seg{background:#17181c;border-color:#17181c}
.resbar .seg button{color:rgba(255,255,255,.55)}
.resbar .seg button:hover{color:rgba(255,255,255,.88)}
.resbar .seg button.on{background:#ffffff;color:#0f172a;box-shadow:0 1px 2px rgba(0,0,0,.35)}


/* ===== 2026-09-30 表格区对齐参考稿（用户提供参考图 09:55） =====
   参考稿的视觉语言：彩色克制——价格列深墨加粗，彩色只留给延迟/节省/组头最低价；
   成功率三小格去底去框变纯排版小纵列；进度条加粗一档；行呼吸感 +一档 */
.plat{color:var(--ink);font-weight:var(--fw-bold)}
/* 2026-10-02 删除此处 `.rb{background:none;border:none;padding:2px 4px}`：
   「去底去框」这个诉求已在 §成功率三小格 的唯一定义里完整实现（还多做了
   hairline 分隔线与 padding 收敛），这里留着只会与它争夺 padding 值。 */
.bar{height:6px}
.mk-band .b-item b.cheap{color:var(--cyan)}
.mk-table tbody td{padding-top:14px;padding-bottom:14px}
.lat{font-size:var(--fs-base)}


/* ===== 2026-09-30 修复：路由列「详情」被挤到「固定此渠道」下一行（用户指出） =====
   根因：昨日把 .pin-link 升级为带边框按钮后，两控件总宽 (~130px) 超出路由列可用宽
   (~110px)，td 内 inline 排版自动折行。修复：路由列加宽到 12%（colgroup）+
   控件收紧 + 操作组改不换行 flex + 末列吃回多余右留白 */
.mk-table td:last-child{padding-right:var(--sp-3)}
.mk-table td:last-child .acts{display:flex;flex-wrap:nowrap;align-items:center;
  justify-content:center;gap:6px}
.mk-table .acts .pin{padding:4px 9px}
.mk-table .acts .pin-link{padding:4px 9px;font-size:var(--fs-xs)}

/* ===== 2026-09-30 官方价统一收敛到组头：输入/输出之间加轻分隔 =====
   渠道行/卡片不再印官方小注（offN/p3o 已移除），官方价只在组头出现一次 */
.b-item b .o-sep{margin:0 5px;color:var(--ink3);font-weight:var(--fw-med)}

/* ===== 2026-09-30 渠道行左侧降噪（用户截图点名：色块太多太杂） =====
   色彩预算原则：一行内彩色只留给两处——「当前路由」青（路由状态）、
   「省 X%」绿（价格优势）；身份徽标与能力关键词全部收敛为中性灰。
   ① 身份徽标：官方直连/聚合渠道 统一为一款中性描边胶囊
     （官方/聚合的身份信息副行文字已有"官方直连·华东"/"（聚合）"，徽标只做轻标记） */
.mk-table .ch-top .pill{background:var(--fill4);border:1px solid var(--line5);color:var(--sub2)}
/* ② 能力关键词：高速/稳定/保真/最低价 统一中性灰裸文字，不再一词一色 */
.mk-tags .pill{color:var(--sub)}
/* ③ 「持平/涨价」标签去色块变轻文字；「省 X%」保留绿色块（唯一价格含义彩色） */
.save-tag.no{background:none;border:none;padding:2px 0;color:var(--sub2);font-weight:var(--fw-med)}
/* ④ 卡片视图同位置徽标行：同一套降噪（官方价X折保留绿色=价格含义） */
.chan-badges .badge{color:var(--sub);border-color:var(--line);background:var(--fill2)}
.chan-badges .badge.disc{color:var(--green);border-color:rgba(var(--green-rgb),.3);background:rgba(var(--green-rgb),.12)}

/* ===== 2026-09-30 二次降噪（用户点名：聚合渠道徽标/省25.5% 也去卡片，字体颜色保留） =====
   去底去框去内边距，只留文字本身：徽标=灰字、省幅=绿字（色彩含义不变，卡片形式取消） */
.mk-table .ch-top .pill{background:none;border:none;padding:2px 0;color:var(--sub2);font-weight:var(--fw-med)}
.mk-table .save-tag{background:none;border:none;padding:2px 0;font-weight:var(--fw-semi)}
.chan-badges .badge{background:none;border:none;padding:2px 0;color:var(--sub)}
.chan-badges .badge.disc{background:none;border:none;color:var(--green)}

/* ===== 2026-09-30 渠道行左侧三行压紧 + 关键词统一色（用户点名） =====
   ① 压紧：td 内边距回到 11px，三行行高收至 1.38，行间 margin 3~4px→2px
   ② 关键词统一色=紫：青已被「当前路由」（路由状态）、绿已被「省X%」（价格优势）
      占用；紫色在青紫品牌语言内且无行内语义冲突（卡片视图标签行同步） */
.mk-table tbody td{padding-top:11px;padding-bottom:11px}
.mk-table .ch{line-height:1.38}
.mk-table .ch small{margin-top:2px}
.mk-table .mk-tags{margin-top:2px}
.mk-tags .pill{color:var(--sub)}
.chan-badges .badge.t-cheap,.chan-badges .badge.t-fast,
.chan-badges .badge.t-stable,.chan-badges .badge.t-trust{color:var(--sub)}

/* ===== 2026-10-01 控制台「总览」页 · 功能导航卡（用户点名参考 OpenRouter 概述页） =====
   定位：控制台落地页的功能入口网格。每张卡=图标+标题+一句话说明，
   hover 只做描边上色+轻抬，不做重投影（内页语言里卡片 hover 的上限）。
   注意：a.navcard 全部带 onclick/真实 href，不许出现无落点的占位卡。 */
.navcards{display:grid;grid-template-columns:repeat(auto-fill,minmax(218px,1fr));gap:12px;
  margin-top:20px}
.navcard{display:flex;flex-direction:column;gap:9px;padding:18px 18px 16px;
  background:var(--card);border:1px solid var(--line3);border-radius:var(--r-card);
  box-shadow:var(--shadow);text-decoration:none;cursor:pointer;min-width:0;
  transition:border-color var(--t-base) var(--e-out),box-shadow var(--t-base) var(--e-out),
    transform var(--t-base) var(--e-out)}
.navcard:hover{border-color:rgba(var(--cyan-rgb),.45);box-shadow:var(--shadow-lift);
  transform:translateY(-1px)}
.navcard .nc-ico{width:34px;height:34px;display:flex;align-items:center;justify-content:center;
  border-radius:9px;background:rgba(var(--cyan-rgb),.08);color:var(--cyan);
  font-size:15px;flex:none;line-height:1}
.navcard .nc-t{display:flex;align-items:center;justify-content:space-between;gap:8px;
  font-size:13.5px;font-weight:var(--fw-semi);color:var(--ink);letter-spacing:var(--ls-body)}
.navcard .nc-t .arr{color:var(--ink3);font-weight:var(--fw-reg);font-size:14px;
  transition:color var(--t-base) var(--e-out),transform var(--t-base) var(--e-out)}
.navcard:hover .arr{color:var(--cyan);transform:translateX(2px)}
.navcard .nc-d{font-size:var(--fs-xs);color:var(--sub);line-height:1.62}

/* ===== 入驻状态横条（2026-10-01，总览顶部）=====
   不是第四张 KPI 卡：它是**一条状态提示**，横条形态比方卡更轻，
   也不会把上面的四张数字卡挤成一行四列挤在一起。
   用 --purple（项目主色）描边，与「待接入」的琥珀、「可售」的青各自分开。 */
/* 入驻状态提示（2026-10-01 加，2026-10-03 去卡片化）
   原设计是一张全宽紫底卡片，实测 1126×70px，圆角 12px 却是"提示条"的内容 ——
   用户评价「像创可贴」。病根不是难看，是**外壳与内容量级不匹配**：
   ① 70px 高只装两行小字，占掉将近一整行版面（邻居 .kpis 是 95px 的真数据）；
   ② 圆角 12px 与邻居 .kpis 的 10px 不一致 —— 两张"卡"圆角不同，一眼露馅；
   ③ 与上方 .kpis 的间距只有 4px（.kpis 自带 margin-bottom:4px），
      两头都紧贴，夹在两张卡中间像贴上去的膏药。
   改法：**状态提示回归"提示条"身份，不占用卡片语法** ——
   去边框/去圆角（--r-card → --r-ctl），改用一条 3px 紫色竖条标识状态，
   padding 收到 10px 14px，颜色只留给竖条和箭头。
   为什么保留竖条：四态（已开通/审核中/被拒/未入驻）需要一眼可辨的状态标识，
   完全去掉标记会让它变成又一行正文，和今天在榜单页治过的"多一行都是负担"冲突。
   ⚠ 间距必须给在**条外**（margin-top），不能给在条内（padding-top）：
     第一版把 12px 挪进了 padding-top，结果竖条顶边仍距上方卡片 4px ——
     病根（③）没修，只是把它藏进了条内部，测出来 gapKpisToOv 依然 = 4。
     净距 < 12px 眼睛已读不出分层。现在 margin-top:var(--sp-4) + .kpis 的 4px = 净距 16px。
   ⚠ 四态共用本样式，长度已核：最长的"审核中"副标题 26 字，单行放得下
     （实测四态 1440 视口下均为 42px 高、b 与 small 垂直中心差 0px，零折行）。 */
.ovsupply{display:block;margin:var(--sp-4) 0 var(--sp-5);text-decoration:none;
  background:var(--fill2);border-radius:var(--r-ctl);
  border-left:3px solid var(--purple);
  transition:background-color var(--t-base) var(--e-out)}
.ovsupply:hover{background:var(--fill3)}
/* ⚠ 结构是 .ovsupply > a > (b, small) —— 整条本身是链接，
   所以 flex 必须落在内层 a 上；放在 .ovsupply 上排的是 a 这个单块（等于没排）。
   两行压成一行：小标题与说明同行，说明用竖线 + 次级色顶开层次。
   原为 b / small 各自 display:block 上下堆叠，那是它长到 70px 的直接原因。 */
.ovsupply > a{display:flex;align-items:center;gap:10px;padding:10px 14px 10px 12px}
.ovsupply b{font-size:var(--fs-sm);font-weight:var(--fw-semi);color:var(--ink);
  letter-spacing:var(--ls-body);line-height:1.5;flex:none}
.ovsupply small{font-size:var(--fs-xs);color:var(--sub);line-height:1.5;
  padding-left:10px;border-left:1px solid var(--line3);min-width:0}
/* 右侧箭头：提示条是入口，得给出"可点"的信号（纯文字链看不出能点）。
   整条已是 <a>，箭头跟在小字之后即可，不要单独设成大按钮。
   同理落在 .ovsupply > a 上（它才是 flex 容器）。 */
.ovsupply > a::after{content:'→';flex:none;margin-left:2px;
  color:var(--purple);font-size:var(--fs-sm);transition:transform var(--t-base) var(--e-out)}
.ovsupply:hover > a::after{transform:translateX(3px)}

/* ===== 2026-10-01 顶栏右侧用户下拉菜单（用户点名参考 OpenRouter） =====
   全站导航组件（app.js AB.nav），深浅页共用：全部走语义令牌，
   首页深色导航与内页 theme-light 各自取色，无需另写覆盖。 */
.uwrap{position:relative}
.utrig{display:inline-flex;align-items:center;gap:8px;background:none;border:none;cursor:pointer;
  padding:5px 8px 5px 5px;border-radius:999px;color:var(--sub2);font-size:var(--fs-sm);
  max-width:190px;
  transition:background-color var(--t-fast) var(--e-out),color var(--t-fast) var(--e-out)}
.utrig:hover{color:var(--ink);background:var(--fill4)}
.uava{width:26px;height:26px;border-radius:50%;background:var(--grad);color:#fff;
  display:inline-flex;align-items:center;justify-content:center;font-size:12px;
  font-weight:var(--fw-bold);flex:none}
.uava.lg{width:32px;height:32px;font-size:14px}
.utrig .uname{max-width:110px;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.utrig .ucar{font-size:var(--fs-cap);color:var(--sub);transition:transform var(--t-fast) var(--e-out)}
.utrig[aria-expanded="true"] .ucar{transform:rotate(180deg)}
.umenu{position:absolute;right:0;top:calc(100% + 10px);width:232px;background:var(--card);
  border:1px solid var(--line3);border-radius:var(--r-card);
  box-shadow:0 12px 34px rgba(18,22,28,.16),0 2px 8px rgba(18,22,28,.08);
  padding:6px;z-index:70;animation:udrop var(--t-fast) var(--e-out)}
@keyframes udrop{from{opacity:0;transform:translateY(-5px)}to{opacity:1;transform:none}}
.uhead{display:flex;align-items:center;gap:10px;padding:10px 10px 12px;margin-bottom:4px;
  border-bottom:1px solid var(--line)}
.uhead-t{min-width:0;flex:1}
.uhead-t b{display:block;font-size:13px;color:var(--ink);font-weight:var(--fw-semi);
  overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.uhead-t i{display:block;font-style:normal;font-size:var(--fs-xs);color:var(--sub);margin-top:1px;
  overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.uitem{display:flex;align-items:center;gap:10px;width:100%;padding:8px 10px;border-radius:8px;
  font-size:13px;color:var(--ink);text-decoration:none;border:none;background:none;cursor:pointer;
  text-align:left;letter-spacing:var(--ls-body);font-weight:var(--fw-reg);
  transition:background-color var(--t-fast) var(--e-out),color var(--t-fast) var(--e-out)}
.uitem:hover{background:rgba(var(--cyan-rgb),.07);color:var(--cyan)}
.uitem .ui{width:16px;text-align:center;color:var(--sub);flex:none;font-size:13px}
.uitem:hover .ui{color:var(--cyan)}
.usep{height:1px;background:var(--line);margin:5px 8px}
.uitem.uout,.uitem.uout .ui{color:var(--red)}
.uitem.uout:hover{background:rgba(var(--red-rgb),.08);color:var(--red)}
/* 上传头像填满圆形容器：顶栏 .uava / 侧栏与资料页 .cava 共用（无头像时容器里是字母文字） */
.uava img,.cava img{width:100%;height:100%;border-radius:50%;object-fit:cover;display:block}
/* 个人资料页头像更换遮罩：hover 浮出「更换」，点击触发文件选择 */
.ava-box{position:relative;flex:none;cursor:pointer}
.ava-edit{position:absolute;inset:0;border-radius:50%;background:rgba(10,12,16,.5);color:#fff;
  display:flex;align-items:center;justify-content:center;font-size:11px;font-weight:var(--fw-semi);
  opacity:0;pointer-events:none;transition:opacity var(--t-fast) var(--e-out)}
.ava-box:hover .ava-edit{opacity:1}

/* ===== 2026-10-01 顶栏通知铃（用户点名，未来公告/信息发布的提示位） =====
   当前只放真实存在的提醒（低余额，按用户阈值实时计算）；空态明示是未来通道。 */
.bell{position:relative;display:inline-flex;align-items:center;justify-content:center;
  width:34px;height:34px;border-radius:50%;background:none;border:none;cursor:pointer;
  color:var(--sub2);
  transition:background-color var(--t-fast) var(--e-out),color var(--t-fast) var(--e-out)}
.bell:hover{color:var(--ink);background:var(--fill4)}
.bdot{position:absolute;top:5px;right:5px;width:8px;height:8px;border-radius:50%;
  background:var(--red);border:2px solid var(--nav-bg);box-sizing:content-box;pointer-events:none}
.bellmenu{width:288px;padding:0;overflow:hidden}
.bhead{padding:12px 14px;font-size:13px;font-weight:var(--fw-semi);color:var(--ink);
  border-bottom:1px solid var(--line)}
.bitem{display:flex;gap:10px;padding:13px 14px;text-decoration:none;
  transition:background-color var(--t-fast) var(--e-out)}
.bitem:hover{background:rgba(var(--cyan-rgb),.06)}
.bitem .bico{flex:none;color:var(--amber);font-size:14px;line-height:1.5}
.bitem b{display:block;font-size:12.5px;color:var(--ink);font-weight:var(--fw-semi)}
.bitem i{display:block;font-style:normal;font-size:var(--fs-xs);color:var(--sub);margin-top:3px;
  line-height:1.6}
.bempty{padding:24px 16px;font-size:12.5px;color:var(--sub);text-align:center;line-height:1.7}

/* ===== 2026-10-01 交易市场改左右两列（用户指示：上下结构→左筛选栏+右结果区） =====
   控件 id 与事件契约零改动（f-cat/f-bill/f-sort/f-prov/f-quick/q），只动容器与形态。
   左栏竖排：筛选选项回归 .opt 基类形态（checkbox 可见、选中黑底反白）；
   右列顶部一行工具条（单位/视图切换），下方接比价结果面板。 */
/* 2026-10-02 阶段 Z｜P0 市场页定位页头（用户选「a 极简一行」）
   ⚠️ 刻意**不用** .phero-c：那个是居中大版式（app.css:1361），而本页要走左对齐紧凑路线。
   沉淀的历史教训：.ph-compact 紧凑/横排变体曾被用户**否决两次**（先嫌占位高、
   压缩后嫌信息被压住、横排后嫌乱），最终回退居中版式。
   所以这次不叫 compact、不做横排变形，而是**独立的一套左对齐极简行**：
   一句 h1 + 一句 p 在左、三个事实数字在右（同一行），高度只占 ~64px。
   数字全部现算（见 market.html 页头注释），不写死。 */
.mk-head{display:flex;align-items:flex-end;justify-content:space-between;gap:24px;
  flex-wrap:wrap;margin-bottom:2px;
  /* ★position:relative 不是装饰，是修一个"整块页头看不见"的真 bug（2026-10-03）。
     现象：市场页页头 h1/p/三个数字在真实浏览器里整块不可见（headless 与 headful
     复现一致，非截图工具问题），但 DOM 全部正常——getComputedStyle 说 h1 visible、
     color rgb(18,22,28)，Range 量文字有真实排版包围盒 180×26，elementFromPoint
     也命中 H1 自身。即"元素在、样式对、就是不画"。
     根因：顶部有 .page-veil / .page-aura 两个 position:absolute;z-index:auto 的
     装饰层（各高 520px，铺满整个顶部），DOM 在 .wrap 之前。页头本身是 static，
     属于普通流层 —— 同为 z-index:auto 时定位元素按 DOM 顺序排在普通流之上，
     两层装饰就把页头盖住了。给页头 position:relative 即参与定位层叠并排在其后，
     立刻恢复正常（实测页头带非白像素 38 → 4481）。
     ⚠ 别用 z-index 硬压：给 .page-aura 设 z-index:-1 会把极光层压到 body 背景之下，
     实测页头带直接变 0（更糟）；也不要去掉 aura 的 mask（mask 无效，实测 38）。
     只加 position:relative 就够，不动装饰层。 */
  position:relative}
.mk-head-l{min-width:0}
.mk-head h1{font-size:var(--fs-2xl);font-weight:var(--fw-bold);letter-spacing:-.6px;line-height:1.25}
.mk-head p{margin-top:5px;font-size:var(--fs-sm);color:var(--sub);line-height:1.6}
/* 2026-10-03 曾加过 .mk-note（页头备注行：窗口胶囊 + 测法小字），
   当轮就删掉了 —— 用户原话「甚至这行小字我都可以去掉」。
   窗口值归属左侧 #win 切换器、测法归属表格标题旁的 ⓘ 浮层（explainFor），
   两处都比常驻小字更完整。样式随之删净（项目纪律：无引用不留死代码）。
   如果日后又要加备注行，记住两个坑：
   ① 定位是"备注"不是"正文" —— 必须比 .mk-head p 小一号、更淡，
      否则等于把删掉的面板头换个位置装回来；
   ② .pill 基础样式带 margin-right:var(--sp-1)（为行内串排设计），
      进 flex 容器会多出空隙，要在 .mk-note .pill 里清掉，间距交给 gap。 */
/* 三个事实：与首页 hero mini-stats 同源语义（讲买家能得到什么，不讲我们的工作量） */
.mk-facts{display:flex;align-items:flex-end;gap:22px;flex:none}
.mk-fact{display:flex;flex-direction:column;gap:1px;white-space:nowrap}
/* 2026-10-03 用户指令（三次演进，这条注释是完整演化史，别删）：
   ① 「数字颜色改成青色或绿色之类的，目前的颜色不好」
      原为 var(--cyan) = #0e7490（浅色主题为可读性压暗的青），实测偏灰、不跳。
      当时改 #0891b2（青）：比 #0e7490 亮一档，白底 3.68:1。
      ⚠ 不能照抄首页的 #00e5ff —— 首页导航底色是**深色** rgba(10,10,15,.82)，
        那个亮青在深底上跳；内页 nav-bg 是**白色** rgba(255,255,255,.86)，
        #00e5ff 在白底上只有 1.9:1，几乎看不见（WCAG 1.4.11 最低 3:1）。
        所以按"视觉意图"走，不按"色值"照抄。
   ② 同日用户指「这个数字颜色也换一下」→ **改为语义绿 var(--green)**。
      为什么这三个数该绿：13 个模型在售 / 10 家渠道可挑 / 今日最大价差
      都是**中性偏正面的"货架丰度与省钱空间"**，不是涨跌也不是盈亏 ——
      染绿不构成错误信号（对比 console 的"本周消费额"就不能染）。
      为什么不再用 --cyan-nav：那个令牌的名字与立意都是「导航青」
      （深底亮青 / 浅底 #0891b2，为导航 hover/选中/横线而生），
      数字借用它属于**语义借用**，改成绿色后 --cyan-nav 回归本职、
      只服务导航（见 nav-links 三条规则），令牌语义更干净。
      色值实测：本页底色 rgb(245,246,248)，--green #0f9960 → **3.38:1**，
      数字 32px/700 属 WCAG 大字（≥18.66px bold），3:1 即达标。
      深色主题自动切 --green #39ff14，无需另立令牌。
      与榜单页口径面板四格数字同色（实测同为 rgb(15,153,96)）：
      全站「实测/可信类数字」统一一个绿，一眼即知是同一类东西。 */
.mk-fact b{font-size:var(--fs-num-sm);font-weight:var(--fw-bold);letter-spacing:-1px;
  font-variant-numeric:tabular-nums;color:var(--green);line-height:1.1}
.mk-fact span{font-size:var(--fs-cap);color:var(--sub);line-height:1.3}
/* 数字未加载完时不显示「–」，避免页头第一眼是三个破折号 */
.mk-facts[data-ready="0"]{visibility:hidden}

.mk-split{display:grid;grid-template-columns:252px minmax(0,1fr);gap:20px;align-items:start;
  margin-top:14px}
.mkside{position:sticky;top:80px;display:flex;flex-direction:column;gap:12px;
  background:var(--card);border:1px solid var(--line3);border-radius:var(--r-card);
  box-shadow:var(--shadow);padding:14px 16px;min-width:0;
  max-height:calc(100vh - 100px);overflow-y:auto}
/* 体检发现（2026-10-01）：左栏内容长于 max-height 时，flex 子项默认 flex-shrink:1 会被挤扁
   ——「重置筛选」按钮在 1440 宽下实测被压到 18px（padding 仍是 8px，典型的被压缩）。
   子项一律不收缩，高度超出交给 overflow-y:auto 滚动。 */
.mkside > *{flex-shrink:0}
.ms-g{display:flex;flex-direction:column;gap:4px;min-width:0}
.ms-t{font-size:12px;font-weight:var(--fw-semi);color:var(--sub);
  letter-spacing:var(--ls-cap)}
.ms-g select.hb-sel{width:100%;min-width:0;padding:6px 30px 6px 12px}
/* 渠道 / 快选模型：竖排一行一项（原 .hbar 横排芯片形态废弃，选项 change 事件不变） */
.ms-opts{display:flex;flex-direction:column;gap:1px;margin:0 -8px}
.ms-opts .opt{padding:6px 8px;border-radius:var(--r-xs)}
.ms-opts .opt .cnt{margin-left:auto}
/* 快选模型芯片：两行（模型名+最低价），比渠道项略高 */
.ms-opts .opt.qm{flex-direction:row;align-items:center;gap:8px;justify-content:flex-start;
  min-height:44px;padding:6px 9px}
/* 2026-10-01 用户点名：快速选模型每项加品牌 logo（logoDot 现成函数） */
.ms-opts .opt.qm .ldot{width:22px;height:22px;border-radius:6px;font-size:12px;flex:none}
.ms-opts .opt.qm .qm-t{min-width:0;display:flex;flex-direction:column;gap:1px}
.ms-opts .opt.qm b{font-size:var(--fs-xs);font-weight:var(--fw-semi);color:var(--ink);
  white-space:nowrap;overflow:hidden;text-overflow:ellipsis;line-height:1.3}
.ms-opts .opt.qm small{font-size:11px;color:var(--dim);font-variant-numeric:tabular-nums;
  line-height:1.3}
.ms-opts .opt.qm.pending small{color:var(--amber)}
.mkside .btn-ghost{width:100%}
/* 右列吸顶工具卡（2026-10-01 用户两轮点名：别楞、底图别再垫方形）：
   圆角卡直接吸顶；面板头/表头偏移按实测高度贴在它下沿，不留缝、不叠层。 */
.mk-toolbar{position:sticky;top:64px;z-index:40;
  display:flex;align-items:center;justify-content:flex-end;gap:10px;
  flex-wrap:wrap;padding:9px 14px;background:var(--card);
  border:1px solid var(--line3);border-radius:var(--r-card);box-shadow:var(--shadow)}
/* 搜索框：输入框与「搜索」按钮同高齐平（此前输入框压到 32px、按钮仍 38px，撑出边框显楞） */
.mk-toolbar .pillsearch{flex:1 1 240px;max-width:460px;margin:0 auto 0 0}
.mk-toolbar .pillsearch input{padding:7px 62px 7px 34px;font-size:13px}
.mk-toolbar .pillsearch .ico{left:13px}
/* 搜索键 hover 的真 bug：.pillsearch .go 用 top:50%+translateY(-50%) 做垂直居中，
   而基座 :hover 把 transform 覆写成 translateY(-1px) → 居中丢失，按钮瞬间下沉 16px。
   这里必须写回 translateY(-50%)（写 none 同样会下沉）。文字按用户要求用白色。 */
.mk-toolbar .pillsearch .go{right:5px;padding:8px 18px;font-size:12.5px;color:#fff}
.mk-toolbar .pillsearch .go:hover{filter:brightness(1.06)}
.mkpanel{overflow:visible}  /* .panel 的 overflow:hidden 会杀死子元素 sticky；mk-scroll 自带圆角边框，放开安全 */
/* 面板头必须不透明：原 .panel-h 是 linear-gradient(--sheen→transparent)，下半透会让表行从缝里露出来。
   这里给一层 var(--card) 实底再叠原渐变；top 与吸顶区下沿严丝合缝，不留缝。 */
.mkpanel .panel-h{position:sticky;top:120px;z-index:39;
  background:linear-gradient(180deg,var(--sheen) 0%,transparent 100%),var(--card);
  border-radius:var(--r-card) var(--r-card) 0 0}
.mk-scroll{overflow:visible}
/* 2026-10-01 单位/视图分段控件原在 .resbar 内用深色（app.css:1476 一套），挪进 .mk-toolbar 后
   丢了这层皮，按「跟之前一样」补回：深底容器 + 未选项半透明白字 + 选中项白底深字。 */
.mk-toolbar .seg{background:#17181c;border-color:#17181c}
.mk-toolbar .seg button{color:rgba(255,255,255,.55)}
.mk-toolbar .seg button:hover{color:rgba(255,255,255,.88)}
.mk-toolbar .seg button.on{background:#ffffff;color:#0f172a;box-shadow:0 1px 2px rgba(0,0,0,.35)}
.mk-table thead th{position:sticky;top:185px;z-index:5}
@media (max-width:1399px){
  .mk-scroll{overflow-x:auto}
  .mk-table thead th{position:static;top:auto}
}
/* 窄屏回退单列：筛选栏回到上方（minmax(0,1fr) 防内容撑爆列宽） */
@media (max-width:1080px){
  .mk-split{grid-template-columns:minmax(0,1fr)}
  .mkside{position:static;max-height:none}
  .ms-opts{flex-direction:row;flex-wrap:wrap;margin:0}
}

/* ===== 2026-10-03 市场页「算一笔」弹窗（从首页搬家）=====
   口径与结构照抄首页 .calc（index.html:178-210），但用两级前缀避免撞名：
   弹窗类全叫 .calc-*，首页那套保持 .calc / .calc-f 不动 ——
   两页都用 .calc-f 会让同一条规则跨页生效，改一处连带改掉首页（本站已吃过三次跨页组件债）。
   ⚠ 弹窗宽 860px：首页是 1200px 的通栏双栏，弹窗里空间小得多，
     硬搬 1200 会让两栏被挤成竖排；860 是"双栏仍并排"的最小宽度。 */
/* ghost 档：它是"工具"不是"主行动"，不该跟搜索键抢视觉权重。
   右边留 4px：它和「单位」标签都是小字号，贴着 10px 会读成一组，
   而单位切换跟算账毫无关系，不该被视觉归到同一簇。 */
.mk-calcbtn{flex:none;white-space:nowrap;margin-right:4px}
.calc-box{width:min(860px,calc(100vw - 40px));max-width:860px}
.calc-grid{display:grid;grid-template-columns:minmax(0,1fr) minmax(0,1fr);
  gap:var(--sp-6);margin-top:var(--sp-5)}
.calc-f{display:block;margin-bottom:var(--sp-4)}
.calc-f>span{display:flex;align-items:baseline;gap:8px;
  font-size:var(--fs-sm);color:var(--sub);margin-bottom:10px}
.calc-f>span b{color:var(--green);font-size:var(--fs-lg);font-weight:var(--fw-bold);
  font-variant-numeric:tabular-nums}
.calc-f select{width:100%;height:40px;padding:0 12px;border-radius:var(--r-xs);
  border:1px solid var(--line3);background:var(--fill2);color:var(--ink);font-size:13px}
/* 滑块：跟首页同配方（琥珀色拇指，hover 放大）。--amber 而不是 --cyan：
   青色是"平台主色/可点"，滑块是"你在调参数"，别让两者抢同一个信号。
   ⚠ 令牌名核对过：阴影只有 --shadow / --shadow-lift 两档，没有 --shadow-sm；
     圆角是 --r-xs(9px)，写不存在的 var() 会让整条声明被静默丢弃（不是报错，是不生效）。 */
.calc-f input[type=range]{width:100%;height:6px;padding:0;border-radius:var(--r-pill);
  -webkit-appearance:none;appearance:none;background:var(--line3);outline:none}
.calc-f input[type=range]::-webkit-slider-thumb{-webkit-appearance:none;appearance:none;
  width:18px;height:18px;border-radius:50%;background:var(--amber);cursor:pointer;
  border:2px solid var(--card);box-shadow:var(--shadow);
  transition:transform var(--t-fast) var(--e-out)}
.calc-f input[type=range]::-webkit-slider-thumb:hover{transform:scale(1.15)}
.calc-f input[type=range]::-moz-range-thumb{width:18px;height:18px;border-radius:50%;
  background:var(--amber);cursor:pointer;border:2px solid var(--card);box-shadow:var(--shadow)}
.calc-tip{font-size:var(--fs-cap);color:var(--dim);line-height:1.7}
/* 右栏不撑高：内容按内容排，卡片高度由左栏（滑块区）决定，
   数字组垂直居中，避免左栏高、右栏矮时右下留一大片空白。 */
.calc-out{display:flex;flex-direction:column;justify-content:center;gap:12px;
  padding:var(--sp-5);border-radius:var(--r-sm);background:var(--fill2)}
.calc-out .co{display:flex;align-items:baseline;gap:8px}
.calc-out .co span{font-size:var(--fs-sm);color:var(--sub2);flex:1}
.calc-out .co b{font-size:var(--fs-xl);font-weight:var(--fw-bold);color:var(--ink);
  font-variant-numeric:tabular-nums}
.calc-out .co small{font-size:var(--fs-cap);color:var(--dim)}
.calc-out .co.lo b{color:var(--sub2)}
/* 主角数字必须真的"大"：20px 只比下面 18px 大 2px，层级拉不开，
   而这是整个弹窗唯一的结论数字（用户只带走一个数，就是它）。
   实测 18 → 26px 后与次级行的差距一眼可辨，且没到抢标题的程度（标题 18px）。 */
.calc-out .co.yr{padding-top:12px;border-top:1px dashed var(--line3)}
.calc-out .co.yr span{font-weight:var(--fw-semi);color:var(--ink)}
.calc-out .co.yr b{color:var(--green);font-size:26px;line-height:1.1}
/* 窄屏单列：860px 以下双栏会挤成两条窄柱，滑块拖不动。 */
@media (max-width:720px){
  .calc-grid{grid-template-columns:minmax(0,1fr)}
  .mk-calcbtn{order:3}
}
