/* ============================================================
   OpenRouter 风格换血的覆盖层（2026-07-26）
   ------------------------------------------------------------
   :root token 已在 style.css 换成深色 + 荧光绿。本文件只放
   「换 token 还不够、必须显式覆盖」的三类东西：
     ① 换血后对比度失效的组合（白字配荧光绿 = 1.3:1，看不见）
     ② GeneratePress 父主题写死的浅色（它不读我们的 token）
     ③ 浅底假设的素材（水墨意境图、头像）在纯黑上的适配
   排在 pages.css 之后 enqueue，靠加载顺序取胜，不堆 !important。
   ============================================================ */

/* ── ① 对比度修复：荧光绿按钮必须配深色字 ───────────────────── */
/* 换血前 --color-ink 是墨黑（铜底上 6.7:1 合规）；换血后它是近白，
   配 #C8FF00 只有 ~1.3:1。OpenRouter 的做法就是绿底黑字（~15:1）。 */
.btn-solid, .btn-primary,
.wc-proceed-to-checkout .checkout-button {
  color: var(--color-ink-inverse) !important;
  font-weight: 600;
}
.btn-solid:hover, .btn-primary:hover,
.wc-proceed-to-checkout .checkout-button:hover {
  color: var(--color-ink-inverse) !important;
}

/* 按钮中文化：原样式是 uppercase + 0.12em 字距（拉丁文语汇）。
   中文没有大小写，宽字距只会把词拆散。OpenRouter 按钮也是正常字重字距。 */
.button, button, input[type="submit"], .wp-block-button__link,
.btn, .btn-secondary, .btn-solid {
  text-transform: none;
  letter-spacing: 0.01em;
  font-size: 15px;
}

/* 中文按钮不能断词换行：390px 下「免费订阅」被拆成「免费订 / 阅」。
   拉丁文断词还能读，汉字断开就是错字观感。让按钮不换行，挤压输入框。 */
.btn, .button, button, input[type="submit"], .wp-block-button__link { white-space: nowrap; }
.news__input, .nl-box input[type="email"] { min-width: 0; }

/* 次级按钮：深底上描边要够亮才看得见（原 --hairline-ink 在浅底是墨线） */
.button, button, input[type="submit"], .wp-block-button__link,
.btn, .btn-secondary {
  border-color: var(--color-rule-ui);   /* 功能性边框：3:1（WCAG 1.4.11） */
  color: var(--color-ink);
}
.button:hover, .wp-block-button__link:hover, .btn:hover, .btn-secondary:hover {
  background: var(--color-ink);
  color: var(--color-ink-inverse);
  border-color: var(--color-ink);
}

/* ★ color-scheme: dark —— 一行搞定**所有原生控件**（复选框/单选/滚动条/下拉/
   日期选择器/自动填充）的深色渲染。比逐个 appearance:none 重画可靠得多：
   重画后要自己补勾选态、focus 态、禁用态，漏一个就是坏控件。
   （2026-07-26 实测：Remember me 复选框在深底上是刺眼白方块，就是缺这一行。） */
:root { color-scheme: dark; }

/* ── ② GeneratePress 父主题的浅色硬编码 ─────────────────────── */
/* GP 把 --base-3:#ffffff 等写进 inline style，不读我们的 token。
   全部指回自己的变量，避免出现「深色页面上一条白带」。 */
:root {
  --base: var(--color-bg-alt);
  --base-2: var(--color-bg);
  --base-3: var(--color-bg-card);
  --contrast: var(--color-ink);
  --contrast-2: var(--color-ink-mid);
  --contrast-3: var(--color-ink-soft);
  --accent: var(--color-accent);
}
/* ★ html 也要上底色：body 高/宽不足时会露出浏览器默认白 —— 深色站的典型翻车点
   （2026-07-26 实测：右侧整块白）。 */
html { background-color: var(--color-bg); }
body, .site-content, .site-main,
.separate-containers .inside-article,
.separate-containers .comments-area,
.separate-containers .page-header,
.one-container .container,
.inside-page-header { background-color: var(--color-bg); }

.site-header { background: rgba(3, 8, 10, 0.88); border-bottom: var(--hairline); }
.main-navigation, .main-navigation ul,
.main-navigation .main-nav ul li { background: transparent; }
.main-navigation .main-nav ul li a { color: var(--color-ink-mid); }
.main-navigation .main-nav ul li a:hover,
.main-navigation .main-nav ul li.current-menu-item > a { color: var(--color-ink); }
/* ── 二级菜单（2026-08-04 菜单精简：8 项 → 4 项，「资源」「公司」各收一层）──
   在此之前全站没有任何带子项的菜单，所以这套样式从没被真正渲染过——
   只有 ul ul 的底色与描边，hover 态、下拉箭头、移动端展开全是 GP 默认。
   加子项之前必须先把这层补全，否则就是又一次「浅色兜底值悄悄生效」。 */
.main-navigation .main-nav ul ul {
  background: var(--color-bg-card);
  border: 1px solid var(--color-rule-ui);   /* 功能性边框：浮层要有明确边界 3:1 */
  border-radius: var(--radius);
  min-width: 200px;                          /* 中文菜单项别被挤到换行 */
  padding: var(--space-2) 0;
  box-shadow: 0 8px 28px rgba(0, 0, 0, 0.55);/* 深色浮层靠投影跟页面拉开层次 */
}
.main-navigation .main-nav ul ul li a {
  padding: 10px 18px;
  color: var(--color-ink-mid);
  white-space: nowrap;
}
.main-navigation .main-nav ul ul li a:hover,
.main-navigation .main-nav ul ul li a:focus-visible,
.main-navigation .main-nav ul ul li.current-menu-item > a {
  background: #101B22;
  color: var(--color-ink);
  box-shadow: none;                          /* 顶级项的荧光绿下划线不要漏到子项里 */
}
/* 父项在子页面上也要亮着，否则用户在 /free-tools 时导航看不出自己在「资源」下 */
.main-navigation .main-nav ul li.current-menu-ancestor > a { color: var(--color-ink); }
/* GP 的下拉箭头默认跟随 currentColor，这里显式跟到次级色，hover 再提亮 */
.main-navigation .main-nav .dropdown-menu-toggle { color: inherit; }

/* 移动端：GP 把子菜单铺在展开的抽屉里，需要缩进 + 去掉浮层那套装饰，
   否则在窄屏上会变成「卡片里套卡片」。 */
@media (max-width: 768px) {
  .main-navigation .main-nav ul ul {
    border: 0;
    border-radius: 0;
    box-shadow: none;
    padding: 0;
    background: var(--color-bg-alt);
  }
  .main-navigation .main-nav ul ul li a { padding-left: var(--space-6); }
}

.site-footer, .footer-widgets, .site-info {
  background: var(--color-bg-deep);
  border-top: var(--hairline);
  color: var(--color-ink-mid);
}

/* 表单控件：GP 默认给浅底深字，深色页面上会是刺眼白块 */
input[type="text"], input[type="email"], input[type="url"], input[type="password"],
input[type="search"], input[type="tel"], input[type="number"], textarea, select {
  background-color: var(--color-bg-card);
  color: var(--color-ink);
  border: 1px solid var(--color-rule-ui);   /* 表单框边界必须看得见：3:1 */
  border-radius: var(--radius);
}
input::placeholder, textarea::placeholder { color: var(--color-ink-soft); }
input:focus, textarea:focus, select:focus {
  border-color: var(--color-accent);
  outline: 2px solid rgba(200, 255, 0, 0.25);
  outline-offset: 1px;
}

/* 移动端菜单切换按钮（GP 给了浅色底） */
.mobile-menu-control-wrapper .menu-toggle,
.has-inline-mobile-toggle #site-navigation.toggled {
  background-color: rgba(255, 255, 255, 0.04);
  color: var(--color-ink);
}

/* ── ③ 深色分层：卡片靠明度分层，不靠描边 ───────────────────── */
/* 浅色设计里「白底 + 发丝线」足够；深色里描边过重会显脏，用底色抬升。 */
.alt { background: var(--color-bg-alt); }
.deep { background: var(--color-bg-deep); }
.card, .cell, .threecol, .prodcard {
  background: var(--color-bg-card);
  border: var(--hairline);
  border-radius: var(--radius);
}
/* ★ 这一行是上面那条规则的后果修补：浅色设计里 .threecol 没有底色，
   所以从来不需要内边距；一旦给它加了卡片底 + 描边，padding:0 就变成
   「文字贴着边框」。.cell 自带 40px、.prodcard 的 padding 在 __body 上，
   只有 .threecol 是裸的。给卡片加底色时必须同时检查它有没有内边距。 */
.threecol { padding: var(--space-5) var(--space-4); }
/* 图片齐边的卡片要裁圆角，否则圆角框里露出方角图（首页已改图标卡，
   但 /products 等页仍有带图的 prodcard，规则保留） */
.prodcard { overflow: hidden; }
/* 图标版产品卡：没有齐边图了，body 的 24px 顶边距不够，补足成正常卡片内距 */
.prodgrid--icon .prodcard__body { padding: var(--space-5); }
.prodgrid--icon .cell__icon { margin-bottom: var(--space-4); }
/* /learn 的 hero 原是「左文右图」两栏；图删掉后右栏空着，文字被挤在左半边。
   改单栏并放开 measure 上限——删元素必须同时改它所在的布局，否则留一个洞。 */
.lhero__grid { grid-template-columns: 1fr; }
.lhero .hero__sub { max-width: 38em; }

/* 视频卡缩略图：图删了之后 .vidcard__thumb 高度靠 img 撑，会塌成 0，
   play 图标与「整理中」角标叠在一起。给它自己的高度 + 深色占位面。
   这些视频本来就标着「整理中」——用不相干的摆拍图冒充缩略图既不诚实
   也砸风格，深色占位反而说了实话。 */
.vidcard__thumb {
  height: 180px;
  background: linear-gradient(180deg, #0F1A21 0%, #0A1116 100%);
  border-bottom: 1px solid var(--color-rule);
}
.vidcard--feat .vidcard__thumb { height: 280px; }
.vidcard__play::before { background: rgba(200,255,0,0.12); }
.vidcard__play .sb-icon { color: var(--color-accent) !important; }
.card:hover, .cell:hover, .threecol:hover, .prodcard:hover {
  border-color: var(--color-rule-strong);
  background: #101B22;
}
.cell__icon, .card__icon { color: var(--color-accent); }

/* ── ④ 浅底素材在纯黑上的适配 ─────────────────────────────── */
/* 水墨意境图是米色调，直接放纯黑上会像一块亮斑。压低亮度 + 降饱和，
   让它退到背景层次里；同时套一层与底色同源的渐隐，边缘不再是硬切。 */
.home-hero__img, .luxury-image {
  border-color: var(--color-rule);
  border-radius: var(--radius-lg);
}
/* ⚠️ 不要用 mix-blend-mode：它会给元素建独立合成层，实测（2026-07-26）在本页
   触发整块渲染异常（首屏大面积空白 + 内容不可见）。纯 filter 足够达到「退到背景层」
   的效果，且零合成风险。 */
.home-hero__img img {
  filter: brightness(0.74) contrast(1.04) saturate(0.8);
  opacity: 0.92;
}
/* 头像组（浅底人像）：深色下同样需要压一档，否则五个亮点很跳 */
.avatars img { filter: brightness(0.9) saturate(0.9); border-radius: 999px; }

/* 模型 logo 行：深色下用描边胶囊，OpenRouter 的 provider 列表就是这个做法 */
.toollogos span {
  border: var(--hairline);
  border-radius: 999px;
  padding: 8px 18px;
  color: var(--color-ink-mid);
  background: var(--color-bg-card);
}

/* 三态徽章在深色下重新配色（原为浅底设计） */
.seq__s--live { background: var(--color-accent); color: var(--color-ink-inverse); }
.seq__s--pilot { border-color: var(--color-accent); color: var(--color-accent); }
.seq__s--plan { border-color: var(--color-rule-strong); color: var(--color-ink-soft); }
.seq__n { color: var(--color-accent); }

/* 分隔线 / 装饰规则线 */
.home-hero__rule { background: var(--color-accent); }

/* 链接：深底上荧光绿（15:1），而不是原来的深铜色（深底上几乎不可见） */
.link, a.link, .cell__link a { color: var(--color-accent-ink); }

/* ── ⑤ Hero 居中结构 + 数字带（OpenRouter 招牌） ─────────────── */
/* padding 用 vh 自适应：OpenRouter 的 hero 是「标题+CTA+数字带」全在首屏。
   实测 160px 固定上边距会把数字带挤到 719px（视口 720）——差一点点最气人。
   clamp 保证小屏不塌、大屏不散。 */
.home-hero--center { position: relative; overflow: hidden; text-align: center;
  padding: clamp(48px, 7vh, 104px) 0 clamp(48px, 6vh, 80px); }
/* ★ 水墨氛围图已从模板删除（2026-07-26 第二轮）。
   第一轮我把它降级成压暗背景「保住品牌资产」——实测 openrouter.ai 的 hero
   是纯 rgb(3,8,10) 平色，一张图都没有。压到 0.5 opacity 的照片不会变成
   OpenRouter 风格，只会变成噪点：既没有装饰价值，又让 1500×844 的 JPEG
   顶着 fetchpriority=high 跟 LCP 抢带宽。留着它，页面就还是「编辑/时装」
   的底子。此处只保留 z-index 上下文，图与滤镜整体删除。 */
.home-hero__inner { position: relative; z-index: 1; }
.home-hero--center .home-hero__title { font-size: clamp(34px, 5.6vw, 62px); font-weight: 700;
  letter-spacing: -0.01em; margin: var(--space-4) 0 0; }
.home-hero--center .hero__sub { margin: var(--space-5) auto 0; max-width: 34em; text-align: center; }
.home-hero--center .home-hero__cta-wrap { align-items: center; margin-top: var(--space-6); }
.home-hero--center .cta-row { justify-content: center; }

/* 数字带：四栏等分，数字用 tabular-nums 保证纵向对齐 */
.statband { list-style: none; padding: 0; margin: var(--space-7) auto 0; max-width: 880px;
  display: grid; grid-template-columns: repeat(4, 1fr); gap: var(--space-5); }
.statband li { display: flex; flex-direction: column; align-items: center; gap: 6px; }
.statband__n { font-family: var(--font-display); font-weight: 700; font-size: clamp(30px, 4vw, 46px);
  line-height: 1; color: var(--color-ink); font-variant-numeric: tabular-nums; letter-spacing: -0.02em; }
.statband__l { font-size: 13px; color: var(--color-ink-soft); letter-spacing: 0.04em; }

@media (max-width: 700px) {
  .home-hero--center { padding: var(--space-7) 0 var(--space-7); }
  .statband { grid-template-columns: repeat(2, 1fr); gap: var(--space-5) var(--space-4);
    margin-top: var(--space-6); }
  .home-hero--center .cta-row .btn { width: 100%; }
}

/* ── ⑥ WooCommerce 深色适配（2026-07-26 实测：登录页输入框全白、按钮深底深字）──
   WC 自带样式表优先级高于我们按 type 选择的规则，必须按它的 class 名精准覆盖。
   这是**转化路径**上的页面（注册/登录/结账），坏在这里等于漏斗断在最后一步。 */
.woocommerce input.input-text,
.woocommerce-page input.input-text,
.woocommerce input.woocommerce-Input,
.woocommerce textarea, .woocommerce select,
.woocommerce-form input, .woocommerce-form textarea,
.woocommerce .select2-container .select2-selection {
  background-color: var(--color-bg-card) !important;
  color: var(--color-ink) !important;
  /* 头像包 v3（第 23 轮计划审查第 2 轮 C 面附带，协调会话定本包修）：输入框底色就是卡片底、又坐在 #0D161C 的内容卡上（账户资料页 = 头像设置区那一页），
     看得见的只有边框 —— 全站 #466074 在这里只有 2.77:1，改用抬一档的 --color-rule-ui-raised #4D687D（3.13:1；页底上 3.44:1）。带 !important 才压得过 WC。 */
  border: 1px solid var(--color-rule-ui-raised) !important;
  border-radius: var(--radius) !important;
}
.woocommerce input.input-text::placeholder,
.woocommerce-form input::placeholder { color: var(--color-ink-soft); }
.woocommerce input.input-text:focus,
.woocommerce-form input:focus {
  border-color: var(--color-accent) !important;
  outline: 2px solid rgba(200, 255, 0, 0.22);
}
/* ⟦wc-invalid⟧ 开始 —— WC 表单的错误态（头像包第 23 轮计划审查 C 面第 3 轮「仅供参考」另开的包，2026-10-17）。
   上面那条基础规则用 `border: … !important` 压 WC 的浅色样式，顺带把 WC 自己的错误红框
   （`.woocommerce form .form-row.woocommerce-invalid input.input-text { border-color: var(--wc-red) }`）也永远压掉了：出错的框与正常的框一模一样。
   这里照 WC 自己的三个选择器补回来（更具体 + 同样 !important ⇒ 压得过上面那条）：
   · 颜色用站内已有的错误红 #FF6B6B（.required 那颗星同色）：卡片底 #0D161C 上 6.59:1、页底 #03080A 上 7.26:1（功能边框要 ≥ 3:1）；
   · 文本框获得焦点时让给上面的荧光绿焦点框（:not(:focus)）—— 正在改的那一格先看清焦点在哪；离开时 WC 重新校验，还错就再红；
   · 标签字跟着换成同一红：WC 的 `.woocommerce-invalid label { color: #a00 }` 本来就生效，可 #a00 是给浅底配的，深色卡片上只有 2.36:1（页底 2.6:1）读不清；
   · woocommerce-validated（WC 的绿框）不补：填对了的框保持正常态。
   WC 11.0.1 里加 woocommerce-invalid 的只有结账页的 checkout.js（address-i18n.js 只摘）；登录 / 注册 / 账户资料出错走页面顶部的文字通知。
   ⟦wc-invalid⟧ 两个记号别删：判据（tests/test-wc-invalid-border-browser.sh ③）拿掉记号之间这一段做对照，证明它只碰错误态。 */
.woocommerce form .form-row.woocommerce-invalid input.input-text:not(:focus),
.woocommerce form .form-row.woocommerce-invalid select,
.woocommerce form .form-row.woocommerce-invalid .select2-container:not(.select2-container--open) .select2-selection {
  border-color: #FF6B6B !important;
}
.woocommerce form .form-row.woocommerce-invalid label { color: #FF6B6B; }
/* ⟦wc-invalid⟧ 结束 */

/* WC 按钮：主提交（登录/注册/下单）走荧光绿，与全站 CTA 一致 */
.woocommerce button.button, .woocommerce a.button,
.woocommerce input.button, .woocommerce button.button.alt,
.woocommerce-form-login__submit, .woocommerce-form-register__submit,
.woocommerce #place_order {
  background: var(--color-accent) !important;
  color: var(--color-ink-inverse) !important;
  border: 1px solid var(--color-accent) !important;
  border-radius: var(--radius) !important;
  text-transform: none;
  letter-spacing: 0.01em;
  font-weight: 600;
}
/* 0903 反馈 一.15：登录/注册提交按钮此前**不在**这条 :hover 里 ——
   它们在上面的基础样式中是独立选择器（`.woocommerce` 祖先不在时也要生效），
   而 :hover 只列了 `.woocommerce xxx` 那几个，于是漏掉。两处补齐。 */
.woocommerce button.button:hover, .woocommerce a.button:hover,
.woocommerce input.button:hover, .woocommerce button.button.alt:hover,
.woocommerce-form-login__submit:hover, .woocommerce-form-register__submit:hover,
.woocommerce #place_order:hover {
  background: var(--color-accent-hover) !important;
  color: var(--color-ink-inverse) !important;
  border-color: var(--color-accent-hover) !important;
}
/* 密码「显示/隐藏」小眼睛（WC 画的是黑色图标，深底上等于隐形）
   ————————————————————————————————————————————————————————————
   ★★ 2026-08-27 真人测试实证：这条规则的**上一版是恒真的**，白挂了很久。
   测试者原话：「开关按钮是右侧的绿色的框，不稳定，有时出现有时不出现，
   一般用眼睛的图标。」—— 他看到的「绿框」其实是 :focus-visible 的焦点环
   （style.css 的 --color-focus-ring #C8FF00），而眼睛图标**一直是黑的、看不见**，
   于是焦点环成了这个控件唯一可见的形态；焦点环只在键盘导航时出现，
   所以他觉得「有时出现有时不出现」。

   上一版错在两处，两处都让它变成空转：
     ① 伪元素选错：WC 11.x 用的是 ::before，上一版写的是 ::after
     ② 属性选错：图标是 ::before 上的 background-image（内联 SVG，
        fill 硬编码 #111111），**背景图不受 color 影响**
   生产实测（2026-08-28）：按钮的 color 确实被改成了 rgb(155,170,182)，
   而图标照旧是黑的 —— 与卡片底色 #0D161C 的对比度 1.033 : 1。
   「改了、也生效了、但改的不是那个东西」是本仓专门修过的一类。

   现在打在真正管事的地方：把那张黑色 SVG 反相。两个状态（默认 / .display-password）
   都要覆盖，否则点开之后又变回黑的。 */
.woocommerce form .show-password-input::before,
.woocommerce-page form .show-password-input::before,
.woocommerce form .show-password-input.display-password::before,
.woocommerce-page form .show-password-input.display-password::before {
  filter: invert(1) brightness(1.2);   /* #111111 → 近白，深底上可见 */
}
/* 命中区：WC 把它画成 22×22 且 padding:0，指头点不准。
   只加内边距不改视觉尺寸（图标是背景图，不随 padding 变大）。 */
.woocommerce form .show-password-input,
.woocommerce-page form .show-password-input {
  padding: 8px !important;
  margin: -8px !important;   /* 抵消 padding 带来的位移，视觉位置不变 */
}

/* 复选框 / 单选：原生控件在深底上是白方块，用 accent-color 一句话解决 */
.woocommerce input[type="checkbox"], .woocommerce input[type="radio"],
input[type="checkbox"], input[type="radio"] { accent-color: var(--color-accent); }

/* WC 容器 / 表格 / 通知条 */
.woocommerce-account .woocommerce, .woocommerce form.login,
.woocommerce form.register, .woocommerce form.checkout_coupon,
.woocommerce-page form.login, .woocommerce-page form.register {
  background: var(--color-bg-card);
  border: var(--hairline);
  border-radius: var(--radius-lg);
}
.woocommerce table.shop_table, .woocommerce table.shop_table th,
.woocommerce table.shop_table td, .woocommerce-MyAccount-navigation ul li {
  background: transparent;
  border-color: var(--color-rule);
  color: var(--color-ink);
}
.woocommerce-message, .woocommerce-info, .woocommerce-error {
  background: var(--color-bg-card);
  border-top-color: var(--color-accent);
  color: var(--color-ink);
}
.woocommerce-message::before, .woocommerce-info::before { color: var(--color-accent); }
.woocommerce-MyAccount-navigation ul li a { color: var(--color-ink-mid); }
.woocommerce-MyAccount-navigation ul li.is-active a,
.woocommerce-MyAccount-navigation ul li a:hover { color: var(--color-ink); }

/* 必填星号：WC 用暗红，深底上不够亮 */
.woocommerce .required, .required { color: #FF6B6B; }

/* ── ⑦ token 语义翻转的修正（2026-07-26 对比度审计抓到）───────────────
   ★ 这是深色改造最隐蔽的坑：`--color-ink-inverse` 在**浅色**主题里语义是
     「深底上的浅字」（页脚/深色区块靠它取色）；换血后我把它重定义为
     「荧光绿按钮上的深字」——两者语义完全相反。
     结果：所有 .deep / .site-foot / .mcta 区块变成「深字配黑底」，
     实测对比度 **1.04:1**，页脚整片文字隐形（导航链接、周报标题全都看不见）。
   ★ 修法：保留 ink-inverse 的新语义（它对按钮是对的），把「深色区块的文字」
     这一类改回明确的浅色 token。教训：换主题时要逐个检查语义型 token 的
     **使用场景**，不能只看名字。 */
.deep, .deep-section, .site-foot, .site-footer, .mcta,
.deep h1, .deep h2, .deep h3,
.deep-section h1, .deep-section h2, .deep-section h3,
.mcta__h, .site-foot a, .site-footer a {
  color: var(--color-ink);
}
.deep .actrow__t, .deep .news__list li, .site-foot p, .site-foot li,
.site-footer p, .site-footer li {
  color: var(--color-ink-mid);
}
.deep .news__list li { border-color: var(--color-rule); }
/* 页脚内部所有取色元素一网打尽——逐个打地鼠会漏（.foot-col__t 就漏了一轮）。
   用后代选择器覆盖整棵子树，再对次级文字单独降一档。 */
.site-foot *, .site-footer * { color: inherit; }
.site-foot, .site-footer { color: var(--color-ink-mid); }
.site-foot a, .site-footer a, .foot-col__t, .site-foot .foot-col__t { color: var(--color-ink); }
.site-foot a:hover, .site-footer a:hover { color: var(--color-accent); }
/* .btn-light 原意是「深底上的浅色描边按钮」——换血后底本身就是深色，
   直接复用次级按钮的功能性边框，避免又一次语义错位。 */
.btn-light {
  border-color: var(--color-rule-ui);
  color: var(--color-ink);
  background: transparent;
}
.btn-light:hover { background: var(--color-ink); color: var(--color-ink-inverse); }

/* ── ⑧ 字重与字距换血：最后一处「旧品牌口音」───────────────────
   实测 openrouter.ai 的排版系统（2026-07-26，真机 getComputedStyle）：
     hero H1     56px / 700 / -0.025em
     区块 H2/H3  16px / 500 / normal
     导航        14px / 450 / normal
     小标签      12px / 450 / normal，**没有一处 uppercase**
     正文        14px / 450 / normal
   即：字重靠 700 vs 450 的**跨度**拉层级，字距一律 normal。
   而本站 pages.css 里 hero H1 全是 400/500（细体大字 = quiet luxury 语汇），
   小标签则是 0.14~0.24em 宽字距 + uppercase（时装编辑语汇）。两者都是旧口音。

   ★ 没有照抄的一条：OpenRouter 区块标题只有 16px。那是产品控制台的尺度，
   本站是给不懂技术的老板看的营销页，16px 区块标题会让信息层级塌掉。
   照搬的是**字重/字距纪律**，不是字号——风格对齐不等于像素复制。 */

/* 8.1 hero H1 → 700。字距交给 style.css 的 :lang(zh) 规则归零：
   汉字上加负字距会挤成一坨，负字距只对拉丁文成立。 */
.hero__display, .home-hero__title, .mhero__h1, .phero__h1, .s72-hero__h1,
.lhero__h1, .ahero__h1, .plhero__h1, .ihero__h1, .fthero__h1,
.legal-head__h1, .sp-title, .sb-ty__title {
  font-weight: 700;
}

/* 8.2 区块标题 / 卡片标题 → 600（正文 450，跨度够拉出层级） */
.h2, .mcta__h, .ftfeature__h, .sp-proguide__h, .cform-success__h,
.mcompare thead th, .artcard__title, .plcard__title, .vidcard__title,
.acct-status__title, .acct-onboard__title, .nl-box__h, .home-hero__brand,
.woocommerce .price, .woocommerce-Price-amount {
  font-weight: 600;
}

/* 8.3 宽字距 + uppercase 的小标签一网打尽。
   token 已在 style.css 降到 0.02~0.05em；这里只收拾 pages/layout.css
   里写死的字面量（token 改不到它们）。 */
/* ★ .slogan-kicker 要**同时**写裸类和 .home-hero 限定版：
   pages.css 里两条规则都在（.slogan-kicker 0.20em 给 /about，
   .home-hero .slogan-kicker 0.24em 给首页）。只写裸类会输给 (0,2,0)
   的容器限定版 → 首页漏掉；只写限定版 → /about 漏掉。
   我先后两次各漏一页，才看清必须两条都覆盖。 */
.persona__role, .footer__col h5, .art-row__cat, .prompt__tag,
.slogan-kicker, .home-hero .slogan-kicker,
.mcompare .flag, .ihero .eyebrow-cjk,
.artcard__cat, .eyebrow, .eyebrow-cjk, .statband__l,
.lday__t, .mplan__tag, .artflow__step,
.main-navigation .main-nav ul li a {
  letter-spacing: 0.02em;
  text-transform: none;
}
/* 中文小标签给一丁点气口即可（0.05em），再多就回到「装高级」。
   ★ 只给「小标签」用：--tracking-cjk-label 是按 12–15px 定的，
   套到 26px 的 .artflow__step 上会变成 1.3px 的实际字距——同一个 em 值，
   字号一大就成了旧风格的宽字距。大字元素留在上面那条 0.02em 里。 */
.eyebrow-cjk, .ihero .eyebrow-cjk, .artcard__cat.cjk,
.slogan-kicker.cjk, .home-hero .slogan-kicker.cjk, .statband__l.cjk,
.lday__t.cjk, .mplan__tag.cjk {
  letter-spacing: var(--tracking-cjk-label);
}
/* 导航：OpenRouter 14px/450。原来是 0.14em + 可能的 uppercase。 */
.main-navigation .main-nav ul li a {
  font-weight: 450;
}

/* 8.4 三处最夸张的遗留（0.6em / 0.2em），token 改不到，必须点名。
   .seq__t 的 0.6em 是「四字词拆成四个孤立汉字」的极端案例——
   连带 text-indent 补偿也要一起归零，否则文字整体偏右。 */
.seq__t {
  letter-spacing: var(--tracking-cjk-label);
  text-indent: 0;
  font-weight: 600;          /* 它是小节标题，跟 8.2 同档 */
}
.seq__s {
  letter-spacing: var(--tracking-cjk-label);
  text-indent: 0;
}
.foot-col .foot-col__t {
  letter-spacing: var(--tracking-cjk-label);
  font-weight: 600;
}
/* 页脚英文 slogan 是全站最后一处 uppercase。OpenRouter 全站零 uppercase，
   保留它就等于在页脚留一句旧品牌的口音。 */
.foot-slogan__en {
  text-transform: none;
  letter-spacing: 0.02em;
  color: var(--color-ink-soft);
}

/* 0903 反馈 一.15：按下反馈。WC 按钮组此前**完全没有** :active，
   而主站 .btn-solid:active 是有按下位移的 —— 同一个站两套手感，
   点登录时会觉得「没反应」。这里与主站取同一个位移量。 */
.woocommerce button.button:active, .woocommerce a.button:active,
.woocommerce input.button:active, .woocommerce button.button.alt:active,
.woocommerce-form-login__submit:active, .woocommerce-form-register__submit:active,
.woocommerce #place_order:active {
  transform: translateY(1px);
  filter: brightness(0.94);
}

/* ── 会员页「月付 | 年付」分段切换（R20，2026-10-12 第 20 轮切 live 改价）────────────
   模板：page-membership.php 的 .billing-toggle-wrap（脚本揭开 hidden）与卡片里的两套价（.mplan__cyc-m / .mplan__cyc-y）。
   #plans 没有 data-billing（无 JS / 脚本没跑）⇒ 只显示月付那套；脚本打上 data-billing="yearly" ⇒ 换成年付那套。
   视觉基线四条（HANDOFF-2026-07-20 §7c）逐条对过：
   ① 对比度按实际所在的底算：切换轨道底 --color-bg-card #0D161C —— 未选中字 --color-ink-mid 7.68:1、「省 15%」荧光绿 15.46:1；
      选中段底 #C8FF00、字 --color-ink-inverse #03080A 17.03:1（选中时「省 15%」改回 inherit：荧光绿叠荧光绿是 1:1）；
      卡上小字（--color-ink-mid）：普通卡底 #03080A 8.46:1、主推卡底 #0A1116 7.98:1。
   ② 轨道外框是功能性边框（WCAG 1.4.11）⇒ 用 --color-rule-ui（对页底 #03080A 3.05:1；轨道自身对页底只有 1.10:1，靠这条框认出控件），
      不用装饰线 --color-rule / --color-rule-strong。
   ③ 字距 normal、零 uppercase，层级靠字重：选中 600、未选中 500。
   ④ 没有任何图片素材。
   特异性：父主题 GeneratePress 给裸 button 写了深灰底白字与 :hover / :focus 底色（(0,1,1)），本段一律以 (0,2,0) 起压过它；
   选中态那条排在 hover / focus 之后，同特异性按顺序取胜。不用 !important。 */
.billing-toggle-wrap { display: flex; justify-content: center; margin-top: var(--space-6); }
.billing-toggle-wrap[hidden] { display: none; }
.billing-toggle-wrap:not([hidden]) + .mplans { margin-top: var(--space-6); }
.billing-toggle {
  display: inline-flex;
  gap: 4px;
  padding: 4px;
  background: var(--color-bg-card);
  border: 1px solid var(--color-rule-ui);   /* 功能性边框：对页底 3.05:1 */
  border-radius: var(--radius);
}
.billing-toggle .billing-toggle__opt {
  min-height: 44px;                          /* 触控目标 */
  padding: 8px 18px;
  border: 0;
  border-radius: calc(var(--radius) - 2px);
  background: transparent;
  color: var(--color-ink-mid);
  font-family: var(--font-body);
  font-size: 15px;
  font-weight: 500;
  letter-spacing: normal;
  text-transform: none;
  line-height: 1.2;
  white-space: nowrap;
  cursor: pointer;
}
.billing-toggle .billing-toggle__opt:hover,
.billing-toggle .billing-toggle__opt:focus { background: transparent; color: var(--color-ink); }
.billing-toggle .billing-toggle__opt:focus-visible { outline: 2px solid var(--color-focus-ring); outline-offset: 2px; }
.billing-toggle .billing-toggle__opt[aria-pressed="true"] {
  background: var(--color-accent);
  color: var(--color-ink-inverse);
  font-weight: 600;
}
.billing-toggle .billing-toggle__save { color: var(--color-accent-ink); font-weight: 600; }
.billing-toggle .billing-toggle__opt[aria-pressed="true"] .billing-toggle__save { color: inherit; }
/* 强制配色（Windows 高对比）：系统把底色一律换成 Canvas，选中段与未选中段就只剩字重之差（R20 审查 C-8）。
   选中段改用系统的 Highlight / HighlightText（forced-color-adjust: none 让这两个系统色原样生效）。 */
@media (forced-colors: active) {
  .billing-toggle .billing-toggle__opt[aria-pressed="true"] {
    forced-color-adjust: none;
    background: Highlight;
    color: HighlightText;
  }
  /* 焦点环也用系统色：forced-color-adjust: none 让选中段的 outline 保持荧光绿，浅色强制配色下对白底只有 1.07:1（R20 审查 C2-3） */
  .billing-toggle .billing-toggle__opt:focus-visible { outline-color: CanvasText; }
}

/* 两套价各包在一个外层 div（.mplan__cyc-m / .mplan__cyc-y）里：默认（无 data-billing）只显示月付那套。
   年付那层服务端就带 hidden，外层本身没有别的 display 规则 —— 这一节没加载（旧 dark.css）时也是浏览器的 [hidden] 把它藏住（R20 审查 C2-2） */
.mplan__bill { font-size: 13px; color: var(--color-ink-mid); margin-top: 4px; margin-bottom: 8px; line-height: 1.6; }
/* 「比月付省 $X」整句不拆：卡窄时整句折到第二行，不把「$72」一个数甩下去（R20 审查 C-3）；
   三栏且 < 1200px 时它一律另起一行 —— 只在放不下时折，1100–1190px 会一张卡 1 行、两张卡 2 行，下面各行错开约 21px（R20 审查 C2-6） */
.mplan__save { white-space: nowrap; }
@media (min-width: 901px) and (max-width: 1199px) { .mplan__save { display: block; } }
.mplan__cyc-y { display: none; }
#plans[data-billing="yearly"] .mplan__cyc-m { display: none; }
#plans[data-billing="yearly"] .mplan__cyc-y { display: block; }
/* 有了切换，「或年付 …→」那条降级链接就多余了（它只给无 JS 的人用） */
#plans[data-billing] .mplan__alt-y { display: none; }
/* 价从 4 个字符（$117）变成 7 个（$119.99、$441.99）：原来 56px 的大字（pages.css）在三栏最窄处（901–1100px 宽，栏内容宽只有 123–196px）
   与 375px 以下的单栏里放不下。按栏宽缩字号（901px → 30px、1000px → 34.4px、1280px → 46.7px）。「/ 月」放不下才折到下一行 ——
   v2 的 clamp(34px, 4.4vw - 6px, 48px) 在 1000–1100px 会让三张卡一张折一张不折、上下错开，901–920px 的大字还放不进栏宽；
   这一档字号下 901–1199px 每 2px 量一次，三张卡都不折（R20 审查 C-3 / C-4；tests/test-membership-billing-toggle.sh ⑬ 量
   1280 / 1100 / 1000 / 920 / 901 / 375 / 320：大字放得进栏宽、三张卡价格行一样高）。 */
.mplan__price { flex-wrap: wrap; }
.mplan__price b { font-size: clamp(30px, 4.4vw - 9.6px, 48px); }
@media (max-width: 900px) { .mplan__price b { font-size: clamp(36px, 12vw, 48px); } }
/* 价是卡里最大的字：三栏且 < 1200px 时档名跟着缩（始终比大字价小 6px：901px → 24px、1000px → 28.4px、≥ 1077px → 32px）。
   只缩价不缩名，901–949px 的大字价（30–31.8px、字重 400）会比档名（32px、字重 500）还小，层级倒了（R20 审查 C2-4；⑬ 每 2px 量价 / 名 ≥ 1.15） */
@media (min-width: 901px) and (max-width: 1199px) { .mplan__name { font-size: clamp(24px, 4.4vw - 15.6px, 32px); } }

/* ── /products 价签（R20）：「$39.99 起 / 月（年付 $407.88 / 年）」比改价前长 63px，pages.css 的 nowrap 让它成了网格一栏的最小宽 ——
   375px 下卡片撑出屏、被 body 的 overflow-x:hidden 裁成「$407.8」，1000px 下卡片超出网格（R20 审查 C-1）。
   模板在「（」处把价签切成两行（.pcard__price-a / -b，各自不折）：月付起价一行、年付那半句一行（小一号），1000px 下不再折成三行、
   「年付」也不会与它的价拆开（R20 审查 C2-5）。标签与价签上下排（三栏时卡内容宽只有 160–180px，放不下「标签 + 价」一行，
   原来是放得下的卡并排、放不下的卡折行，同一排标题高低不齐）；价签区固定两行高（28px + 22px），只有一行价的卡（「免费」「免费精选」）
   也占同样的高 ⇒ 同一排卡片的标题顶端对齐。pages.css 对这几个类只有裸类规则，这里同特异性、dark.css 后加载胜出。
   tests/test-membership-billing-toggle.sh ⑭ 在 320 / 375 / 560 / 901 / 920 / 1000 / 1280 量（3 张卡，同生产）。 */
.pcard__top { flex-direction: column; flex-wrap: nowrap; align-items: flex-start; gap: 4px; }
.pcard__price { white-space: normal; min-height: 50px; }
.pcard__price-a { display: block; white-space: nowrap; line-height: 28px; }
.pcard__price-b { display: block; white-space: nowrap; line-height: 22px; font-size: 15px; color: var(--color-ink-mid); }
/* 第二行以全角「（」开头：这个字形左半格是空白（约 0.6em），两行盒子左缘对齐、看上去却缩进约 9px（R20 审查 C3-2）。
   text-spacing-trim: trim-start 挤掉行首全角标点的半格，剩下的约 0.08em 字形侧边距用 text-indent 补齐；不支持这条属性的浏览器走下面的回退
   （整格 0.5em + 0.08em）。tests/test-membership-billing-toggle.sh ⑭b 截图量两行首字墨迹左缘，375 / 901 / 1000px 两种写法都 ≤ 1px。 */
.pcard__price-b { text-spacing-trim: trim-start; text-indent: -0.08em; }
@supports not (text-spacing-trim: trim-start) { .pcard__price-b { text-indent: -0.58em; } }
/* 三栏最窄那一段（901–959px）卡内容宽只有 140–150px，两行价签各小一号（价签最宽 151px，否则把会员那一栏撑宽 11px） */
@media (min-width: 901px) and (max-width: 959px) { .pcard__price-a { font-size: 20px; } .pcard__price-b { font-size: 13px; } }

/* ── 付款前确认页（插件 facesolo-bridge class-checkout-consent.php 的 render()；第 20 轮 topup-flex 计划审查 C-1 / C-4 / C-5 / C-13）──
   ① 四种提示（未勾选 / 页面过期 / 文案已更新 / 充值金额不成立）用站内错误提示的写法（.cform-error / .woocommerce-error 同款）：
      主文字色、卡片底、3px 荧光绿上边 —— 字 #FCFCFE 对卡片底 #0D161C 约 17:1。原来插件写死浅色主题的暗红 #b42318，深色页底上只有 3.06:1。
      从 Stripe 结账页点「返回」回来时金额块顶上那句说明（#facesolo-topup-notice，role="status"，审查 A2-6 / C2-3）同用这个类；它在块首，
      上外边距没用、要的是与下面「充值金额（美元）」标签之间的间距 ⇒ 单独 margin: 0 0 16px（第 3 轮审查 C3-1：原来两者相隔 0px，标签像卡片的一部分）。
   ② 常用金额按钮比输入框矮（内边距 8px 14px；.btn 原来的 18px 32px 让次要按钮比主控件还大），375px 宽四颗放得下一行；
      拿到焦点时不透出父主题 GeneratePress 的 button:focus 灰底（#3f4047，特异性 (0,1,1)）—— 本段 (0,2,0) 起压过它；
      hover 照站内次级按钮反相（排在 focus 之后，同特异性按顺序取胜）；键盘焦点环 2px 实色荧光绿。
   ③ 勾选框的键盘焦点环：上面 input:focus 那条只给 25% 透明度的绿（文本框靠边框变色看得见，原生复选框不吃 border-color），
      对页底只有 1.94:1；这张页上换成实色 --color-focus-ring（对页底约 17:1，≥ 3:1）。
   判据：主仓 tests/test-topup-consent-browser.sh（无头 Chrome 真排版、量计算样式与对比度）。 */
.facesolo-consent-alert {
  color: var(--color-ink);
  background: var(--color-bg-card);
  border-top: 3px solid var(--color-accent);
  padding: 10px 14px;
  margin: 12px 0 0;
}
.facesolo-topup > #facesolo-topup-notice { margin: 0 0 16px; }
.facesolo-topup .facesolo-topup__preset {
  padding: 8px 14px;
  font-size: 15px;
  line-height: 1.2;
  letter-spacing: normal;
}
.facesolo-topup .facesolo-topup__preset:focus { background: transparent; color: var(--color-ink); border-color: var(--color-rule-ui); }
.facesolo-topup .facesolo-topup__preset:hover { background: var(--color-ink); color: var(--color-ink-inverse); border-color: var(--color-ink); }
.facesolo-topup .facesolo-topup__preset:focus-visible { outline: 2px solid var(--color-focus-ring); outline-offset: 2px; }
.facesolo-consent input[type="checkbox"]:focus-visible { outline: 2px solid var(--color-focus-ring); outline-offset: 2px; }

/* ── 第 22 轮 site-trim（Richard 2026-10-16：精简文案 + 「API 充值」每页都找得到）──────────────────────────
   ① 顶栏「API 充值」：functions.php 的 facesolo_topbar_topup_button() 经 GP 的 generate_menu_bar_items 输出，GP 把 .menu-bar-items
      同时放进桌面导航（#site-navigation，主菜单右边）与手机汉堡旁（#mobile-menu-control-wrapper），≤ 768px 时 GP 自己藏掉前一份。
      荧光绿实心（转化节点）：字 #03080A 对 #C8FF00 约 16:1；按钮底对 header 底 rgba(3,8,10,.88) 约 16:1（≥ 3:1）。比营销 CTA 矮一号，
      不把 header 撑高；手机上内边距再收一点，375px 宽时 logo + 按钮 + 汉堡一行放得下（tests/test-site-trim-browser.sh 量）。
      不加 a.btn-solid 的 hover 上浮（导航条里一跳一跳）。
      v2（第 1 轮审查 C 面）：字重 600 —— GP 的 .main-navigation a{font-weight:400}（0,1,1）压过 .btn-solid 的 600，荧光绿底上的细字发虚（C1-5）；
      769–900px 宽已登录（5 个菜单项）按钮原来掉到第二行、header 从 101 撑到 138px —— 这一段把菜单项左右内边距收到 12px、按钮左距 8px（C1-1，
      769 / 800 / 820 / 900 × 两态实测单行）；手机上点击区高 ≥ 44px（wrapper 本来就 60px 高，header 不变高；C1-4）。 */
/* v3（协调会话 X-2，原有问题）：header 有 backdrop-filter、自成层叠上下文（z-index auto），首页后面 position:relative 的 .home-hero 画在桌面下拉菜单之上 ——
      鼠标从「免费资源」移进下拉就落到 hero 上、悬停丢失、子项点不到。GP 给 .site-header 的 position:relative 已在，这里只提层级。
      判据：tests/test-site-trim-browser.sh ⑨（下拉每一项中心点 elementFromPoint 命中菜单链接）。 */
#masthead { z-index: 100; }
.main-navigation .menu-bar-items .nav-topup {
  margin-left: 16px;
  padding: 9px 16px;
  font-size: 14px;
  font-weight: 600;
  line-height: 1.2;
  letter-spacing: normal;
  box-shadow: none;
}
.main-navigation .menu-bar-items .nav-topup:hover,
.main-navigation .menu-bar-items .nav-topup:active { transform: none; box-shadow: none; }
@media (min-width: 769px) and (max-width: 900px) {
  .main-navigation .main-nav ul li a { padding-left: 12px; padding-right: 12px; }
  .main-navigation .main-nav ul li.menu-item-has-children > a { padding-right: 0; }
  .main-navigation .menu-bar-items .nav-topup { margin-left: 8px; }
}
@media (max-width: 768px) {
  .mobile-menu-control-wrapper .menu-bar-items .nav-topup {
    margin: 0 10px 0 0; padding: 8px 12px;
    min-height: 44px; display: inline-flex; align-items: center; justify-content: center; box-sizing: border-box;
  }
}

/* ② 「了解更多」折叠（会员页方案卡 / 充值区 / 各档模型名单；IDE 页费用说明 / 工具调用 / 各工具注意事项）：同一种写法 ——
      summary 是 14px 次级色文字 + 荧光绿 +/−（与会员页 FAQ 同一个记号），点开后正文照原样式。summary 用 .more__t 类，
      不用裸的 class="cjk"：三个测试按 <summary class="cjk"> 认 FAQ 条目，混进来会把 FAQ 认错（第 22 轮实测）。 */
.more__t {
  display: inline-flex;
  align-items: center;
  gap: 8px;
  cursor: pointer;
  list-style: none;
  font-size: 14px;
  font-weight: 500;
  color: var(--color-ink-mid);
  padding: 6px 0;
}
.more__t::-webkit-details-marker { display: none; }
/* 记号写两遍：先写不带替代文本的（老浏览器认得），再写「/ ''」—— 替代文本为空，读屏不把「加号 / 减号」念进折叠的名字（v2 C1-12） */
.more__t::after { content: '+'; content: '+' / ''; color: var(--color-accent); font-size: 18px; line-height: 1; }
details[open] > .more__t::after { content: '\2212'; content: '\2212' / ''; }
.more__t:hover { color: var(--color-ink); }
.mplan__more { margin-top: var(--space-3); }
.mplan__more .mplan__feats { margin-top: var(--space-2); }
.mtopup__more, .mmodels__fold { margin-top: var(--space-5); text-align: left; }
.mtopup__more p { font-size: 14px; line-height: 1.8; color: var(--color-ink-mid); margin-top: var(--space-2); }
.ide-more { margin-top: var(--space-3); text-align: left; }
.ide-note-more { margin-top: var(--space-4); }
.ide-note-more > .ide-note { margin-top: var(--space-2); }

/* ③ 会员页 need_plan 说明条：原样式（pages.css .mhero__notice）用的是 CF 那边的 token（--accent / --ink-hi），WP 这边没定义 ⇒ 底色与字色
      从来没生效。换成本站 token：卡片底、主文字色、荧光绿 3px 上边（与站内其他提示条同一个写法；字对底约 17:1），里面的「API 充值」按钮另起一行。 */
.deep .mhero__notice {
  background: var(--color-bg-card);
  border: 1px solid var(--color-rule-ui);
  border-top: 3px solid var(--color-accent);
  color: var(--color-ink);
  max-width: 620px;
  margin: 0 auto var(--space-6);   /* v2 C1-6：说明条是首屏第一块，与下面的眉标隔开（原来眉标贴着说明条上边只隔约 4px） */
}
/* v3（第 2 轮审查 C2-1）：说明条里两颗按钮（实心「API 充值」+ 描边「选订阅方案」）并排、窄了就折行；描边按钮在卡片底 #0D161C 上，
      全站次按钮边框 #466074 只有 2.77:1 —— 用抬一档的 --color-rule-ui-raised（3.13:1）。 */
.mhero__notice .mhero__notice-btns { display: flex; flex-wrap: wrap; justify-content: center; gap: 10px; margin-top: 10px; }
.mhero__notice .mhero__notice-btn { padding: 10px 22px; font-size: 15px; }
.mhero__notice .btn-secondary:not(:hover) { border-color: var(--color-rule-ui-raised); }
/* v4（第 3 轮审查 C3-2）：说明条正文里的「账户中心」链接原来只靠颜色区分（对周围正文 1.15:1、静止无下划线）—— WCAG 1.4.1 / F73。
      写法照 pages.css C4 那条：静止发丝下划线；悬停时下划线透明、交回 .link::after 的动画，免得双线。 */
.mhero__notice a.link { text-decoration: underline !important; text-decoration-thickness: 1px; text-underline-offset: 3px; }
.mhero__notice a.link:hover { text-decoration-color: transparent !important; }

/* ④ 账户中心：没订阅的人状态块上两颗按钮（「API 充值」实心在前）；付款后通知条里的「进入 AI 聊天室」
      v2 C1-3：次按钮在状态块的 alt 底（#0A1116）上，全站次按钮边框 --color-rule-ui #466074 在这里只有 2.88:1 —— 抬一档的边框色（对 alt 底 3.25、
      对卡片底 3.13、对页底 3.44）；悬停照全站次按钮（:not(:hover) 只管静止态）。 */
:root { --color-rule-ui-raised: #4D687D; }
.acct-status .btn-secondary:not(:hover) { border-color: var(--color-rule-ui-raised); }
/* v3（第 2 轮审查 C2-2）：容器能收缩（原来 flex-shrink:0 固定 244px，320 宽时「查看订阅方案」穿出卡片右边框 27px），窄了两颗竖排在卡片里 */
.acct-status__ctas { display: flex; gap: 10px; flex-wrap: wrap; flex-shrink: 1; min-width: 0; }
.acct-status__ctas .btn { padding: 12px 20px; }
/* v7（第 6 轮审查 C 面「顺带」，协调会话 C6-1）：本人有订阅时状态块里只有一颗按钮（「资源库（制作中）」等；是 .acct-status 的直接子元素、不在 __ctas 里）——
   上面 .acct-status .btn 的 flex-shrink:0 加不折行，280–285 宽伸出卡片 5–10px。与 C2-2 同一类：允许它收到容器宽、字折行。 */
.acct-status > .btn { max-width: 100%; white-space: normal; text-align: center; word-break: keep-all; }
/* v8（第 7 轮审查 C7-1）：max-width:100% 把按钮夹在状态块内容盒里（比卡片内缘窄 41px），280–331 宽「资源库（制作中）」从词中间断开、团队成员「进入 AI 聊天室」280–308 宽也折 ——
   keep-all 让中文只在空格 / 标点处折（「资源库 / （制作中）」「进入 AI / 聊天室」）；≤ 340 宽状态块左右内边距 40 → 20px，资源库那颗 285 起就单行、团队成员那颗各宽都单行。 */
@media (max-width: 340px) {
  .acct-status { padding-left: 20px; padding-right: 20px; }
}
.facesolo-topup-return { display: flex; flex-wrap: wrap; align-items: center; gap: 10px 16px; }
/* v4（第 3 轮审查 C3-1）→ v5（第 4 轮审查 C4-1 / C4-2 / C4-4）：账户页的通知条（付款后两种 + facesolo_account_notices）由 my-account.php 包进 .acct-notices、
      放在账户网格最前面（页头、导航之前）。钉第一行、占满两列：其余三件（页头第 2 列、导航第 1 列、内容第 2 列，pages.css）照旧钉列，
      自动排布从第二行起 —— 与没有通知条时的落位一样，只是整体下移一行；单列（≤ 900px）时它就是第一块。
      边距交给网格的 gap；外壳里多条之间 10px；WC 提示条自带的下外边距清掉，免得与 gap 叠出双倍空白。
      C4-4：min-width:0 —— 不然通知条的最小内容宽（图标位 + 「进入 AI 聊天室」+ 内边距约 220px）会把 280px 宽的单列轨道撑宽 1.9px、整列伸出卡片内缘。
      C4-2：第一条的上两角跟着卡片圆角走（卡片 --radius-lg、1px 边框 ⇒ 内圆角减 1px）；只动钉在网格里的这一组，别处的 WC 提示照旧直角。
      不用卡片 overflow:hidden（会裁掉焦点框）。 */
.woocommerce-account .woocommerce > .acct-notices { grid-column: 1 / -1; grid-row: 1; min-width: 0; display: flex; flex-direction: column; gap: 10px; }
.woocommerce-account .woocommerce > .acct-notices > * { margin: 0; }
.woocommerce-account .woocommerce > .acct-notices > :first-child { border-top-left-radius: calc(var(--radius-lg) - 1px); border-top-right-radius: calc(var(--radius-lg) - 1px); }
/*    WC 的清浮动 ::before（display:table，网格里也是一格）在有通知条时会自己占一行、在通知条与页头之间多出一道 gap —— 这一态网格不需要清浮动，藏掉。 */
.woocommerce-account .woocommerce:has(> .acct-notices)::before { display: none; }
/* v6（第 5 轮审查 C5-2）：付款后三种通知条（充值成功 / 取消、订阅成功）的外层带 .cjk（标题行高 1.2），正文挤在一起；同一个外壳里别的提示是 1.65。
      只给文字 span 1.5（按钮行不动）：直接去掉 .cjk 落回 1.65 会把订阅成功条的按钮在 320×460 推出首屏（审查实测 465 > 460），1.5 时 445 仍在首屏。 */
.acct-notices .facesolo-topup-return > span { line-height: 1.5; }
/* v6（第 5 轮审查 C5-1）：窄屏时外壳里的通知条收窄内边距（左 3em：WC 图标在 1.5em 处、与文字隔约 8.5px；右 1em）——
      320 宽正文列原来只有 164px，长条（seat_ok 团队披露、团队成员那条 already_subscribed）把页头挤到几屏之外；审查实测 seat_ok 57 → 48 行。
   v7（第 6 轮审查 C 面「顺带」）：断点 400 → 430 —— 原来 401–426 宽用回 WC 的宽内边距、正文列反而比 400 宽窄约 25px，常见的 412 / 414 / 428 / 430 宽手机正落在那一边。
   v8（第 7 轮审查 C7-2）：430 → 480 —— 431–455 宽又是「正文列比 430 窄」的一段，iPhone 16 / 17 Pro Max 的 440 宽正落在那里；480 以内是所有手机，跳变落到 481（平板竖屏不在那里）。 */
@media (max-width: 480px) {
  .woocommerce-account .woocommerce > .acct-notices > * { padding-left: 3em; padding-right: 1em; }
}
.facesolo-topup-return .facesolo-topup-return__btn { padding: 9px 16px; font-size: 14px; }

/* ⑤ 会员页充值区：标题在 375px 宽折成「不订阅也能 / 用：API 充值」—— 汉字之间不断行（keep-all），只在「：」后的空格处换行；
      折叠标题跟着本节居中，点开后的正文左对齐（真排版截图 shots-v1/wp/membership-topup-375.png 量过）。 */
#topup .h2 { word-break: keep-all; }
.mtopup__more { text-align: center; }
.mtopup__more p { text-align: left; }

/* ⑥ 会员页首屏（v2 C1-8）：按钮离 lead 太近（约 16px，而标题到 lead 约 40px，头重脚轻）—— 拉到 --space-6。
      ≤ 359px 原来两颗折成竖排、宽度不一（142 / 125）：改成同一行两颗等宽（内边距收窄）—— 竖排撑满一行的写法在 320×568 上会把第二颗挤出首屏（实测底边 591）。 */
.mhero__lead + .cta-row { margin-top: var(--space-6); }
@media (max-width: 359px) {
  .mhero__lead + .cta-row { flex-wrap: nowrap; }
  .mhero__lead + .cta-row .btn { flex: 1 1 0; min-width: 0; padding-left: 12px; padding-right: 12px; }
}

/* ── 第 23 轮 avatar（Richard 2026-10-16：登录后顶栏像 Google / Microsoft 账号那样显示头像；账户里能上传头像）────────────────
   ① 头像本身：圆形是有意的例外（全站圆角 6px）。首字是白字 #FCFCFE，底色由插件 FS_Bridge_Avatar::PALETTE 八选一
      （对白字 ≥ 4.76:1、对页底 ≥ 3.54:1、对卡片底 ≥ 3.22:1，tests/test-avatar-describe.php 重算）；一圈 1px 功能边框 --color-rule-ui（3.06:1），
      图片头像也有一道认得出的边界。拉丁首字的大写是插件在字符层面做的（一个字形的身份标记，不是 CSS 全大写标签），这里 text-transform 照旧 none。
      v2（计划审查第 1 轮 C1-2）：首字圆一直作底（.at-ava__ini），有图时 <img class="at-ava__img"> 绝对定位铺满叠在上面；图片加载失败时
      inc/avatar-menu.js 给它加 hidden、露出首字，不出破图（顶栏、卡片、账户中心页头、头像设置区四处同一个标记约定）。
      v3（计划审查第 2 轮 C2-1）：图片垫的是外层那个八选一底色（background-color: inherit）—— 上传的 PNG / WebP 可以带透明（插件管线保留 alpha），透明处露出底色、
      不露首字（v2 垫卡片底色，图片失败时整块盖住首字）；再加纯 CSS 兜底：脚本没跑（关了 JS、拦截器拦了主题脚本、慢网上脚本还没到）时，Chrome / Firefox
      会给加载失败的 <img> 渲染 ::after —— 用同一个底色把 data-ini 首字重画一遍、盖住破图图标；Safari 不渲染 ::after，那边靠 head 里的内联脚本，这条只作兜底。 */
.at-ava {
  position: relative; display: inline-flex; align-items: center; justify-content: center; flex: none; box-sizing: border-box;
  border-radius: 50%; overflow: hidden; color: #FCFCFE; font-weight: 600; line-height: 1;
  letter-spacing: normal; text-transform: none; user-select: none;
  box-shadow: 0 0 0 1px var(--color-rule-ui);
}
/*    图片的规则写成两个类（0,2,0）：layout.css 的 .site-header img { height:30px; width:auto }（0,1,1）会把顶栏里的图片压扁。 */
.at-ava .at-ava__img {
  position: absolute; top: 0; left: 0; display: block; width: 100%; height: 100%; max-width: none; margin: 0; padding: 0;
  border-radius: 50%; object-fit: cover; background-color: inherit;
}
.at-ava .at-ava__img[hidden] { display: none; }
.at-ava .at-ava__img::after {
  content: attr(data-ini); position: absolute; top: 0; left: 0; width: 100%; height: 100%;
  display: flex; align-items: center; justify-content: center; border-radius: 50%;
  background-color: inherit; color: #FCFCFE; font-size: inherit; font-weight: 600; line-height: 1;
}
/*    尺寸也写成两个类，理由同上。 */
.at-ava.at-ava--32 { width: 32px; height: 32px; font-size: 15px; }
.at-ava.at-ava--40 { width: 40px; height: 40px; font-size: 18px; }
.at-ava.at-ava--48 { width: 48px; height: 48px; font-size: 21px; }
.at-ava.at-ava--96 { width: 96px; height: 96px; font-size: 40px; }

/* ② 顶栏那颗：按钮 44×44（手机点击区 ≥ 44px），里面 32px 头像，紧挨「API 充值」右边。GP 给 button 刷了灰底与 hover 色、给 .main-navigation 里的
      一切加内边距 —— 三种状态都压回透明。焦点框用站内统一的荧光绿焦点环。
      v2（C1-10）：hover 外圈只在 @media (hover: hover) 里 —— 触屏点过之后浏览器会留着 :hover，卡片关了外圈还在、看上去和展开一样；展开那条照旧。 */
.at-ava-item { position: relative; display: inline-flex; align-items: center; margin-left: 8px; }
.at-ava-item .at-ava-btn,
.at-ava-item .at-ava-btn:hover,
.at-ava-item .at-ava-btn:focus,
.at-ava-item .at-ava-btn:active {
  display: inline-flex; align-items: center; justify-content: center; box-sizing: border-box;
  width: 44px; height: 44px; min-height: 44px; margin: 0; padding: 0; border: 0; border-radius: 50%;
  background: transparent; color: inherit; line-height: 1; cursor: pointer; box-shadow: none;
}
@media (hover: hover) {
  .at-ava-item .at-ava-btn:hover .at-ava { box-shadow: 0 0 0 2px var(--color-ink-mid); }
}
.at-ava-item .at-ava-btn[aria-expanded="true"] .at-ava { box-shadow: 0 0 0 2px var(--color-ink-mid); }
.at-ava-item .at-ava-btn:focus-visible { outline: 2px solid var(--color-focus-ring); outline-offset: 2px; }

/* ③ 小卡片：样式照桌面二级菜单（卡片底、功能边框、圆角、投影）。桌面挂在头像正下方右对齐；手机（≤ 768px）挂在 header 下方、离右边 12px，
      宽度不超过屏宽减 24px —— 汉堡旁那颗头像离右边只有一颗汉堡宽，右对齐头像的话 320 宽会从左边伸出去。层级压过首页 hero（#masthead 是 100）。
      v2（C1-6）：横屏手机（568×320 / 667×375）与超长昵称时卡片原来伸出视口底部 —— 高度封顶（header 约 89–101px），超出在卡片里滚；
      昵称至多 2 行、邮箱 1 行省略号（完整值在 title 上；WP 的显示名最长 250 字）。
      v3（计划审查第 2 轮 C2-2）：100vh 是地址栏收起时的大视口高，地址栏展开时卡片底部那一截在可视区外 —— 先写 calc(100vh - 108px) 当回退，再写
      calc(100svh - 108px)（地址栏展开时的小视口，iOS 15.4+ / Chrome 108+），底部留 8px 不贴边；去掉 overscroll-behavior: contain：不认 svh 的旧浏览器上
      卡片底部仍可能在地址栏后面，滑到卡片底再往上滑要能带动页面（header 不吸顶，卡片跟着页面上去、地址栏收起），contain 会把这条路也堵上。 */
.at-ava-pop {
  position: absolute; top: calc(100% + 8px); right: 0; z-index: 110; box-sizing: border-box;
  width: 280px; max-width: calc(100vw - 24px); max-height: calc(100vh - 108px); max-height: calc(100svh - 108px); overflow-y: auto; padding: 6px 0;
  background: var(--color-bg-card); border: 1px solid var(--color-rule-ui); border-radius: var(--radius);
  box-shadow: 0 8px 28px rgba(0, 0, 0, 0.55); text-align: left; line-height: 1.5;
}
.at-ava-pop[hidden] { display: none; }
.at-ava-pop__who { display: flex; align-items: center; gap: 12px; padding: 10px 16px 12px; margin-bottom: 6px; border-bottom: 1px solid var(--color-rule); }
.at-ava-pop__id { flex: 1 1 auto; min-width: 0; }
.at-ava-pop__name {
  color: var(--color-ink); font-size: 15px; font-weight: 600; line-height: 1.4; overflow-wrap: anywhere;
  display: -webkit-box; -webkit-box-orient: vertical; -webkit-line-clamp: 2; overflow: hidden;
}
.at-ava-pop__mail { color: var(--color-ink-mid); font-size: 13px; line-height: 1.4; white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
/*    GP 的移动端样式在 ≤ 768px 把 .main-navigation 里的 ul 一律藏掉（汉堡没展开时），汉堡旁那份卡片也在 .main-navigation 里 —— 链接列表要显式压回来（三个类压过 GP 的两个）。 */
.main-navigation .at-ava-pop ul.at-ava-pop__list,
.at-ava-pop__list { display: block; list-style: none; margin: 0; padding: 0; }
.main-navigation .at-ava-pop .at-ava-pop__list li,
.at-ava-pop__list li { display: block; float: none; width: auto; margin: 0; padding: 0; }
.main-navigation .at-ava-pop__list a,
.at-ava-pop__list a {
  display: block; padding: 11px 16px; color: var(--color-ink-mid); font-size: 14px; font-weight: 400; line-height: 22px;
  text-decoration: none; white-space: nowrap; box-shadow: none;
}
.main-navigation .at-ava-pop__list a:hover,
.main-navigation .at-ava-pop__list a:focus-visible,
.at-ava-pop__list a:hover,
.at-ava-pop__list a:focus-visible { background: #101B22; color: var(--color-ink); }
.at-ava-pop__list a:focus-visible { outline: 2px solid var(--color-focus-ring); outline-offset: -2px; }
@media (max-width: 768px) {
  .mobile-menu-control-wrapper .menu-bar-items .at-ava-item { position: static; margin-left: 0; margin-right: 6px; }
  .mobile-menu-control-wrapper .menu-bar-items .at-ava-pop { top: 100%; right: 12px; width: 300px; }
}
/*    ≤ 400px（只在有头像时）：logo + 「API 充值」+ 头像 + 汉堡一行放不下 —— 320 宽原来折成两行（logo 一行、按钮一行，header 变高；tests/test-avatar-browser.sh ① 量）。
      收四处：header 左右内边距 30 → 20px、充值按钮右距 10 → 6px、头像右距 6 → 5px（与汉堡的点击区仍隔 ≥ 4px）、汉堡左右内边距收到宽 44px（点击区仍 44 × 60）。
      v2（C1-4）：「有头像」原来用 .site-header:has(.at-ava-item) 认，iOS / Safari < 15.4、Chrome / Android WebView < 105、Firefox < 121 不认 :has()，
      320–350 宽在这些浏览器上折成两行（134px）—— 改成 body 上的 .facesolo-has-ava（functions.php 的 body_class 过滤器加，与输出头像同一判据）。
      v2（C1-5）：320 宽 logo 右边到充值按钮的余量 v1 实测：测试底板 6.4px、生产忠实底板 4.5px（审查原话「余量在生产忠实底板上只有 4.5px」，v1 这里写的「留约 7px」不对）；
      ≤ 340px 再把充值按钮左右内边距 12 → 10px，余量多 4px（v2 实测见 tests/test-avatar-browser.sh ① 的「logo 与充值按钮相隔」那格，判据 ≥ 8px）。 */
@media (max-width: 400px) {
  .facesolo-has-ava .site-header .inside-header { padding-left: 20px; padding-right: 20px; }
  .facesolo-has-ava .site-header .mobile-menu-control-wrapper .menu-bar-items .nav-topup { margin-right: 6px; }
  .facesolo-has-ava .site-header .mobile-menu-control-wrapper .menu-bar-items .at-ava-item { margin-right: 5px; }
  .facesolo-has-ava .site-header .mobile-menu-control-wrapper .menu-toggle { padding-left: 15px; padding-right: 15px; min-width: 44px; }
}
@media (max-width: 340px) {
  .facesolo-has-ava .site-header .mobile-menu-control-wrapper .menu-bar-items .nav-topup { padding-left: 10px; padding-right: 10px; }
}
/*    facesolo 改名（2026-10-18 用户定）：顶栏 logo 是站名文字（.main-title a；GP 在 .main-title 上设 25px / 700），「FaceSolo」比改名前的旧站名宽约 18px（92.98 → 111.17px）——
      320 宽已登录 logo 压到充值按钮、顶栏撑成两行（89 → 134px），未登录也只剩 3.2px。≤ 340px 站名字号 25 → 21px（约 93px，与原站名同宽），
      其余不动；对所有登录状态都生效（.site-header .main-title 两个类压过 GP 的 .main-title 一个类）。判据：tests/test-avatar-browser.sh ① 与 tests/test-site-trim-browser.sh ① / ⑫。
      单独一块：上面那块 tests/test-avatar-theme.sh ⑦ 按「只有充值按钮那一条」逐字核。 */
@media (max-width: 340px) {
  .site-header .main-title { font-size: 21px; }
}

/* ④ 账户中心页头：「你好，…」左边一颗 48px 头像（my-account.php 的 .acct-hello；原来 h2 自带的 12px 上边距挪到外层）。
      v2（C1-12）：超长昵称时 h2 折很多行，align-items: center 让头像悬在这段字的正中间 —— 改 flex-start，头像与 h2 的首行对齐（谁比谁高就把谁往下挪
      一半差值：字号照 layout.css .h2 的 clamp(34px, 4.4vw, 56px)，这里显式写一遍，两边用同一个变量）；≤ 300px 头像缩到 40px、间距 6px，
      280 宽「你好，张三」一行放得下（原来头像占 62px 折成两行；280 宽内容列 218px，34px 字五个字 170px，头像 + 间距 46px，余 2px —— tests/test-avatar-browser.sh ⑤ 量）。 */
.acct-hello { --acct-hello-fs: clamp(34px, 4.4vw, 56px); --acct-hello-ava: 48px; display: flex; align-items: flex-start; gap: 14px; margin-top: 12px; min-width: 0; }
/*    v3（计划审查第 2 轮 C2-3）：行高写成 var(--leading-cjk-head)，两条对齐算式用同一个变量。它就是 r22 生产上这个 h2 实际的行高 1.2 —— style.css 的
      :lang(zh) h2（特异度 0,1,1）压过 layout.css .h2 的 1.15（生产页 lang="zh-CN"；529d319 的 CSS 在 Chrome 里实测 67.2 / 56）—— 所以不是 v2 改出来的漂移，
      照 1.15 改反倒会动到 r22。 */
.acct-hello .h2 { margin: 0; min-width: 0; overflow-wrap: anywhere; font-size: var(--acct-hello-fs); line-height: var(--leading-cjk-head); }
.acct-hello > .at-ava { margin-top: max(0px, calc((var(--acct-hello-fs) * var(--leading-cjk-head) - var(--acct-hello-ava)) / 2)); }
.acct-hello > .h2 { margin-top: max(0px, calc((var(--acct-hello-ava) - var(--acct-hello-fs) * var(--leading-cjk-head)) / 2)); }
@media (max-width: 300px) {
  .acct-hello { --acct-hello-ava: 40px; gap: 6px; }
  .acct-hello > .at-ava.at-ava--48 { width: 40px; height: 40px; font-size: 18px; }
}

/* ⑤ 账户资料页的头像设置区（插件 FS_Bridge_Avatar::render_panel，WC 账户资料表单之前）：卡片底、功能边框；窄屏头像在上、内容在下。 */
.at-ava-panel { margin: 0 0 var(--space-5); padding: 20px; background: var(--color-bg-card); border: 1px solid var(--color-rule); border-radius: var(--radius); }
.at-ava-panel__h { margin: 0 0 14px; font-size: 17px; line-height: 1.4; }
.at-ava-panel__row { display: flex; gap: 20px; align-items: flex-start; }
.at-ava-panel__body { flex: 1 1 auto; min-width: 0; }
.at-ava-panel__status { margin: 0 0 12px; color: var(--color-ink); font-size: 15px; line-height: 1.6; }
.at-ava-panel__form, .at-ava-panel__more { display: flex; flex-wrap: wrap; align-items: center; gap: 10px; margin: 0 0 10px; }
.at-ava-panel__label { flex: 0 0 100%; color: var(--color-ink-mid); font-size: 14px; line-height: 1.5; }
.at-ava-panel__file { max-width: 100%; color: var(--color-ink-mid); font-size: 14px; }
.at-ava-panel__file:focus-visible { outline: 2px solid var(--color-focus-ring); outline-offset: 2px; }
.at-ava-panel .btn.at-ava-panel__btn { box-sizing: border-box; min-height: 44px; padding: 10px 18px; font-size: 14px; line-height: 1.4; word-break: keep-all; }   /* 比营销 CTA 矮一号（区块里三四颗并排），点击区仍 ≥ 44px */
/*    v2（C1-1）：次级按钮（「使用我的 Google / GitHub 头像」「移除头像」）坐在卡片底 #0D161C 上，全站次级按钮边框 --color-rule-ui #466074 在这里只有 2.77:1 ——
      用账户中心状态块同一个抬一档的边框色 --color-rule-ui-raised #4D687D（对卡片底 3.13:1）；只改这个区块，悬停照全站次级按钮（:not(:hover) 只管静止态）。 */
.at-ava-panel .btn-secondary:not(:hover) { border-color: var(--color-rule-ui-raised); }
.at-ava-panel__hint { margin: 8px 0 0; color: var(--color-ink-mid); font-size: 13px; line-height: 1.6; }
.at-ava-panel__notice { margin: 0 0 14px; padding: 10px 14px; border: 1px solid var(--color-rule-ui); border-left-width: 3px; border-radius: var(--radius); color: var(--color-ink); font-size: 14px; line-height: 1.6; }
.at-ava-panel__notice--ok { border-left-color: var(--color-accent); }
.at-ava-panel__notice--err { border-left-color: #F2555A; }
@media (max-width: 480px) {
  .at-ava-panel { padding: 16px; }
  /* 竖排时子项要撑满宽度（flex-start 会让说明文字按最长一行算宽、不折行而伸出卡片 —— tests/test-avatar-browser.sh ⑥ 320 宽量出来的）；头像自己靠左 */
  .at-ava-panel__row { flex-direction: column; align-items: stretch; gap: 14px; }
  .at-ava-panel__row > .at-ava { align-self: flex-start; }
}
