/* ==========================================================================
   主题变量 · theme.css
   --------------------------------------------------------------------------
   本文件只做三件事：
     1. 定义全套 CSS 变量的【出厂默认值】（红色党建主题）；
     2. 定义字号基准（rem 的锚点），使"基础字号"可整体调节；
     3. 定义三档质感（扁平 / 轻拟物 / 玻璃拟态）与三档阴影、三档密度的取值。

   运行时的真实取值由 theme.js 从后端配置接口读取后覆盖这些变量 ——
   因此后台改配色、圆角、阴影、质感都不需要重新打包前端。

   变量命名与后端 Appearance 结构体字段一一对应，便于对照排查。
   ========================================================================== */

:root {
  /* ==========================================================================
     设计令牌 · 照《界面装修与排版规范-给Go重写参照》第二节**逐项对齐**
     --------------------------------------------------------------------------
     ★ 这份令牌表是**三端共用的地基**，先建它、再写任何页面（规范第十节的落地顺序）。
     ★ 三端各有各的圆角，**别互相套用**：
         后台 14 / 10 / 7 px ｜ 村民端 18 / 14 / 10 px ｜ 大屏 12 / 10 / 8 px
       本文件服务**后台**；村民端的圆角在 h5.css 里覆盖，大屏在 screen.css 里覆盖。

     为什么之前"看着土"（对照规范第〇节的五条，缺一条就变土）：
       1. 颜色没全走变量      → 现在：全部变量，禁止页面里写死色值
       2. 圆角/阴影不统一      → 现在：后台 14/10/7 + **双层阴影**
       3. 留白没节奏          → 现在：页面 20/22、卡片 18/20、卡间距 16
       4. 状态色没有固定语义   → 现在：见下面「语义标签」一组（绿完成/橙待办/蓝流转/红异常/灰作废）
       5. 动作没有反馈        → 现在：悬停上浮、选中左竖条、数值跳动（见各组件）
     ========================================================================== */

  /* ---- 主色系（红色党建 · 默认皮肤）---- */
  --brand: #D32F2F;            /* 正红：按钮、链接、强调（小面积） */
  --brand-dark: #B71C1C;       /* 深一档：按下态、深描边 */
  --brand-soft: #FBE9E7;       /* 极浅底：浅底标签 / 选中底 */
  --accent: #D9A441;           /* 党建金：辅助 */
  --accent-soft: #FDF6E9;
  --warn: #E8A33D;             /* 提醒（即将到期等） */
  --danger: #E45C5C;           /* 危险（异常、缺失） */
  --ok: #2E7D5B;               /* 成功（完成、收入） */

  /* ---- 聚焦环（★ 刻意**不用品牌色**）----
     --------------------------------------------------------------------------
     ★★★ 为什么单列一个令牌，而不是各处写 `var(--brand)`
     --------------------------------------------------------------------------
     本项目的语义规则（见上面第 4 条）是 **红 = 异常**。
     而默认皮肤的 `--brand` 是正红 #D32F2F —— 于是"聚焦"用了红色，
     语义直接与"出错了"撞车：**点进输入框，边框变红，看着像输入有误。**

     ★ 判据：**"我正在这里输入"与"你填错了"是两种完全不同的反馈，
       颜色必须能一眼区分。** 品牌色可以变（红色/绿色/蓝色皮肤都有），
       但"聚焦"的语义不变 ⇒ 聚焦色就不该跟着品牌走。

     取项目既有的蓝（`--tag-blue-fg: #3062C4`，规范里"蓝流转"那一档），
     它与 danger/warn/ok 都不接近，三端（后台 / 村民端 / 大屏）通用。
     （深色主题单独调亮一档，否则在深底上对比度不够。） */
  --focus-ring: #3062C4;

  /* ---- 底色系 ---- */
  --bg: #FBF6F4;               /* 页面底：浅暖米白 */
  --bg-card: #FFFFFF;          /* 卡片底：纯白 */
  --bg-side: #8E1F23;          /* 侧栏底：深红（旗帜鲜明） */
  --bg-side-2: #A3272C;        /* 次级底：表头 / 行悬停 */

  /* ---- 侧栏前景（深色侧栏 → 反白系）---- */
  --side-fg: #FFF2F0;
  --side-fg-2: rgba(255, 242, 240, .62);
  --side-hover: rgba(255, 255, 255, .12);
  --side-active-bg: rgba(255, 255, 255, .18);
  --side-active-fg: #FFFFFF;
  --side-active-bar: #F2C14E;  /* 选中左竖条：党建金 */
  --side-line: rgba(255, 255, 255, .14);

  /* ---- 文字与线条（三级灰阶 + 分隔线）---- */
  --text: #2B2121;             /* 主文字（标题、正文） */
  --text-2: #5C4A48;           /* 次文字（副标题、说明） */
  --text-3: #9A8682;           /* 提示文字（时间戳等，仅 ≥12.5px） */
  --line: #F0E2DE;             /* 分隔线 */
  /* 表头底 / 表格斑马纹：**极浅**的皮肤色（不是 --bg-side-2）。
     ⚠️ 规范 4.5 写的是"表头底色 --bg-side-2" —— 那条**基于浅色侧栏**的假设：
       参考系统用的皮肤侧栏是浅色（#EEF4F1），所以 --bg-side-2 很浅。
       我们的红皮肤是**深色侧栏**（--bg-side-2 = #A3272C 深砖红），
       直接拿来当表头会变成一大块深红 —— 表头字号小，深底上更看不清。
     ⇢ 取"规范想要的效果"（表头与页面底有区分、同色系、但很浅），
        而不是照抄它的变量名。★ 这正是"取长补短，不是照抄"。 */
  --table-head-bg: #F7EFEC;

  /* ---- 语义标签（★ 浅底深字，**不是实心色块**）----
     ★★ 规范 2.5 的状态色语义 —— 照这个配就不会乱：
        绿=完成/正面 ｜ 橙=进行中/待办 ｜ 蓝=流转中/信息
        红=异常/到期/缺失 ｜ 灰=草稿/作废/离线 ｜ 主题色=本模块特有
     ⚠️ 新增状态值必须同步加样式（否则那一行显示成"没底色的小字"，看着像坏了）。 */
  --tag-green-bg: #E8F5EE;   --tag-green-fg: #2E7D5B;
  --tag-orange-bg: #FCF1DF;  --tag-orange-fg: #B06F1D;
  --tag-red-bg: #FDEBEC;     --tag-red-fg: #C62828;
  --tag-blue-bg: #E7EEFB;    --tag-blue-fg: #3062C4;
  --tag-purple-bg: #F1EAFB;  --tag-purple-fg: #7A4FC0;
  --tag-gray-bg: #F0EEED;    --tag-gray-fg: #7A6A67;
  --tag-brand-bg: var(--brand-soft); --tag-brand-fg: var(--brand);

  /* ---- 统计卡淡彩圆片（6 组：红/砖红/蓝/紫/橙/玫红）----
     ★ 大统计卡右上角那个 42×42 圆片图标用它们 —— 这是"专业感"的关键。
     6 组轮着用，别只用一种色。 */
  --t1-bg: #FBE4E4; --t1-fg: #C62828; --t1-bar: #C62828;
  --t2-bg: #F8E8E2; --t2-fg: #B23A32; --t2-bar: #B23A32;
  --t3-bg: #E7EEFB; --t3-fg: #3062C4; --t3-bar: #3062C4;
  --t4-bg: #F1EAFB; --t4-fg: #7A4FC0; --t4-bar: #7A4FC0;
  --t5-bg: #FCF1DF; --t5-fg: #C98A1B; --t5-bar: #C98A1B;
  --t6-bg: #FDE9EC; --t6-fg: #D9536C; --t6-bar: #D9536C;

  /* ---- 圆角（后台：14 / 10 / 7）---- */
  --r-lg: 14px;                /* 大卡片、统计卡、弹窗 */
  --r-md: 10px;                /* 表格外框、小卡 */
  --r-sm: 7px;                 /* 菜单项、列表行 */
  --r-pill: 20px;              /* 标签、状态胶囊 */

  /* ---- 阴影（**双层**：一层贴边、一层扩散 —— "高级感"的关键）---- */
  --shadow: 0 1px 3px rgba(43, 33, 33, .05), 0 6px 18px rgba(43, 33, 33, .05);
  --shadow-lg: 0 10px 34px rgba(43, 33, 33, .13);   /* 悬停抬起、弹窗 */

  /* ---- 布局尺寸 ---- */
  --side-w: 232px;
  --side-w-collapsed: 68px;
  --topbar-h: 56px;

  /* ---- 间距节奏（照规范 2.3，不要随意定）---- */
  --page-pad: 20px 22px 40px;   /* 页面内容区 */
  --card-pad: 18px 20px;        /* 卡片内边距 */
  --card-gap: 16px;             /* 卡片下间距 */
  --grid-gap: 14px;             /* 统计卡网格 */
  --tool-gap: 10px;             /* 工具条元素 */

  /* ---- 字号阶梯（规范 2.4）---- */
  --fs-page-title: 17px;        /* 顶栏页面标题 600 */
  --fs-card-title: 15px;        /* 卡片标题 600 */
  --fs-stat-lg: 30px;           /* 大统计数字 700，字距 -0.5px */
  --fs-stat-sm: 18px;           /* 小统计数字 700 */
  --fs-list-title: 13.5px;      /* 列表标题 500 */
  --fs-body: 13px;              /* 正文 400 */
  --fs-meta: 12.5px;            /* 次要说明 */
  --fs-hint: 11.5px;            /* 提示小字 */
  --fs-tag: 11.5px;             /* 标签内文字 */
  --fs-side-group: 12.5px;      /* 侧栏组名 600 字距 .5px */
  --fs-side-item: 13.5px;       /* 侧栏菜单项 */

  --font-size: 14px;

  /* ==========================================================================
     以下为**旧变量名的兼容映射**（页面里已在用 --brand-primary 等）
     --------------------------------------------------------------------------
     ★ 不删的原因：改一处变量名要翻几十个文件，容易漏（漏了就"颜色没变"）。
       做法：新令牌为**唯一真实来源**，旧名一律 **var() 指过去** ——
       两边永远同值，改新名即可全站生效。
     ⚠️ 新写的样式一律用新令牌名，不要再用 --brand-primary 这一套。
     ========================================================================== */
  --brand-primary: var(--brand);
  --brand-secondary: var(--bg-side-2);
  --brand-deep: var(--bg-side);
  --brand-rgb: 211, 47, 47;
  --accent-rgb: 217, 164, 65;
  --card: var(--bg-card);
  --text-muted: var(--text-2);
  --border: var(--line);
  --sidebar-bg: linear-gradient(180deg, var(--bg-side-2) 0%, var(--bg-side) 100%);
  --sidebar-border: var(--side-line);
  --sidebar-text: var(--side-fg-2);
  --sidebar-text-strong: var(--side-active-fg);
  --sidebar-hover: var(--side-hover);
  --sidebar-active: var(--side-active-bg);
  --sidebar-w: var(--side-w);
  --sidebar-w-collapsed: var(--side-w-collapsed);
  --shadow-card: var(--shadow);
  --shadow-hover: var(--shadow-lg);
  --shadow-pop: var(--shadow-lg);
  --shadow-inset: none;
  --radius: var(--r-md);
  --radius-sm: var(--r-sm);
  --radius-lg: var(--r-lg);
  --radius-card: var(--r-lg);
  --radius-btn: var(--r-md);
  --radius-input: var(--r-md);
  --radius-pill: var(--r-pill);
  --gap-xs: 4px;
  --gap-sm: 10px;
  --gap: 16px;
  --gap-lg: 24px;
  --pad-card: 20px;
  --pad-page: 22px;

  /* ---- 质感开关（由 theme.js 按 style 配置设值）---- */
  --glass-on: 0;
  --glass-bg: rgba(255, 255, 255, .58);
  --glass-border: rgba(255, 255, 255, .55);
  --glass-blur: 16px;
  --neu-out: none;
  --neu-in: none;
}

/* ==========================================================================
   五套皮肤（规范 2.1）—— 用 html[data-theme] 切换，**不刷新页面即生效**。
   --------------------------------------------------------------------------
   ★ 只有 `red` 需要自己一套完整值（上面 :root 就是它）；其余四套**只覆盖有差异的项**，
     没覆盖的自动继承 :root —— 这样加皮肤不用抄一份全表（抄了必漏）。
   ⚠️ 每套必须配齐「主色系 + 底色系 + 侧栏前景 + 文字线条」四组，
     少一组就会出现"切了皮肤但某块没变"。
   ========================================================================== */

/* ---- 生态竹青：清爽乡村生态（浅色侧栏）---- */
html[data-theme="green"] {
  --brand: #05936A; --brand-dark: #047857; --brand-soft: #E6F4EF;
  --accent: #D9A441; --accent-soft: #FDF6E9;
  --bg: #F6F8FC; --bg-side: #FAFCFE; --bg-side-2: #EEF4F1;
  /* 浅色侧栏 → 前景用深字（不是反白） */
  --side-fg: #1B2A3A; --side-fg-2: rgba(27, 42, 58, .62);
  --side-hover: rgba(5, 147, 106, .08); --side-active-bg: rgba(5, 147, 106, .12);
  --side-active-fg: #047857; --side-active-bar: #05936A;
  --side-line: rgba(27, 42, 58, .10);
  --text: #1B2A3A; --text-2: #4A5A6B; --text-3: #64748B; --line: #E3E9F0;
  --ok: #047857;
}
html[data-theme="green"] .sidebar { color: var(--text); }

/* ---- 政务沧浪：整洁干练（深蓝侧栏）---- */
html[data-theme="blue"] {
  --brand: #1B5FBE; --brand-dark: #14498F; --brand-soft: #E8F0FB;
  --accent: #4A90D9; --accent-soft: #EDF4FC;
  --bg: #F5F7FA; --bg-side: #123A6B; --bg-side-2: #1A4A84;
  --side-fg: #EAF2FD; --side-fg-2: rgba(234, 242, 253, .62);
  --side-hover: rgba(255, 255, 255, .12); --side-active-bg: rgba(255, 255, 255, .18);
  --side-active-fg: #FFFFFF; --side-active-bar: #6FB1F5;
  --side-line: rgba(255, 255, 255, .14);
  --text: #1F2733; --text-2: #4C5A6B; --text-3: #6B7684; --line: #E2E9F2;
  --ok: #1E7A4F;
}

/* ---- 金穗暖阳：温馨有活力（浅暖侧栏）---- */
html[data-theme="orange"] {
  --brand: #E08A1E; --brand-dark: #B86E12; --brand-soft: #FCF1DF;
  --accent: #C98A1B; --accent-soft: #FDF6E9;
  --bg: #FDF9F3; --bg-side: #FFFCF7; --bg-side-2: #F8EFE0;
  --side-fg: #3A2C1B; --side-fg-2: rgba(58, 44, 27, .62);
  --side-hover: rgba(224, 138, 30, .10); --side-active-bg: rgba(224, 138, 30, .14);
  --side-active-fg: #B86E12; --side-active-bar: #E08A1E;
  --side-line: rgba(58, 44, 27, .10);
  --text: #33261A; --text-2: #6B5744; --text-3: #8A7864; --line: #F0E4D2;
  --ok: #2E7D5B;
}
html[data-theme="orange"] .sidebar { color: var(--text); }

/* ---- 深色护眼：长时间盯屏（深底亮字）---- */
html[data-theme="dark"] {
  --brand: #E05252; --brand-dark: #C62828; --brand-soft: rgba(224, 82, 82, .16);
  /* 深底上 #3062C4 对比度不足 ⇒ 聚焦环调亮一档（语义不变，只是看得清）。 */
  --focus-ring: #5B8DEF;
  --accent: #D9A441; --accent-soft: rgba(217, 164, 65, .16);
  --bg: #14171C; --bg-card: #1B1F26; --bg-side: #161A21; --bg-side-2: #222834;
  --side-fg: #E6EAF0; --side-fg-2: rgba(230, 234, 240, .60);
  --side-hover: rgba(255, 255, 255, .08); --side-active-bg: rgba(224, 82, 82, .20);
  --side-active-fg: #FFFFFF; --side-active-bar: #E05252;
  --side-line: rgba(255, 255, 255, .10);
  --text: #E6EAF0; --text-2: #A8B3C2; --text-3: #7C8798; --line: #2A313C;
  --warn: #E8A33D; --danger: #E45C5C; --ok: #4ADE80;
  --shadow: 0 1px 3px rgba(0, 0, 0, .30), 0 6px 18px rgba(0, 0, 0, .28);
  --shadow-lg: 0 10px 34px rgba(0, 0, 0, .45);
}
html[data-theme="dark"] body { background: var(--bg); color: var(--text); }

/* 字号基准：所有以 rem 计的字号都相对它缩放，
   因此后台把"基础字号"从 14 调到 16，全站文字会整体变大。 */
html {
  font-size: var(--font-size, 14px);
}

/* 暗色主题的细节微调：由 theme.js 在 <html> 上加 data-theme="dark" 生效。
   这些是"配色之外的观感修正"，无法仅靠换色值表达。 */
html[data-theme="dark"] {
  --shadow-card: 0 1px 2px rgba(0, 0, 0, .35), 0 8px 24px rgba(0, 0, 0, .32);
  --shadow-hover: 0 2px 6px rgba(0, 0, 0, .4), 0 14px 34px rgba(0, 0, 0, .38);
  --shadow-pop: 0 12px 36px rgba(0, 0, 0, .55);
  --glass-bg: rgba(40, 44, 54, .55);
  --glass-border: rgba(255, 255, 255, .09);
  --neu-out: 6px 6px 14px rgba(0, 0, 0, .45), -6px -6px 14px rgba(255, 255, 255, .03);
  --neu-in: inset 4px 4px 9px rgba(0, 0, 0, .5), inset -4px -4px 9px rgba(255, 255, 255, .04);
  --sidebar-text: rgba(255, 255, 255, .78);
  color-scheme: dark;
}

/* 大字模式：给 <html> 加 data-big-font 后整体放大一档。
   这是第六批"大字模式"的落点，提前把机制留好。 */
html[data-big-font="1"] {
  --font-size: 17px;
}

/* ==========================================================================
   通用基础样式（各页面共用）
   ========================================================================== */

* {
  box-sizing: border-box;
  -webkit-tap-highlight-color: transparent;
}

/* 全站滚动条 */
::-webkit-scrollbar { width: 8px; height: 8px; }
::-webkit-scrollbar-thumb {
  background: rgba(var(--brand-rgb), .22);
  border-radius: 4px;
}
::-webkit-scrollbar-thumb:hover { background: rgba(var(--brand-rgb), .38); }
::-webkit-scrollbar-track { background: transparent; }

/* ==========================================================================
   统一图标
   --------------------------------------------------------------------------
   全部图标来自 Remix Icon（本地字体，线性/面性两套）。
   统一尺寸与对齐，避免不同图标视觉重量不一导致排版歪斜。
   ========================================================================== */
[class^="ri-"], [class*=" ri-"] {
  display: inline-block;
  vertical-align: -0.13em;
  line-height: 1;
  font-style: normal;
}

/* 自定义图片图标（菜单里上传的图）统一按当前字号尺寸渲染，
   这样它和字体图标能并排对齐。 */
.icon-img {
  display: inline-block;
  width: 1.15em;
  height: 1.15em;
  vertical-align: -0.22em;
  object-fit: contain;
  border-radius: 3px;
}

/* ==========================================================================
   质感：三档视觉风格
   --------------------------------------------------------------------------
   由 theme.js 在 <html> 上设置 data-style 切换。
   为什么用属性选择器而不是变量：一种风格往往要同时改好几样东西
   （玻璃拟态要半透明背景 + 模糊 + 边框高光），变量表达不了这种组合。
   ========================================================================== */

/* ---- 轻拟物：元素像从底面上浮起的实体 ---- */
/* 浅色模式也必须有实体阴影；原来只有 dark 定义，浅色继承 none。 */
html[data-style="neumorph"]:not([data-theme="dark"]) {
  --neu-out: 6px 6px 18px rgba(32, 55, 92, .10), -6px -6px 18px rgba(255, 255, 255, .95);
  --neu-in: inset 4px 4px 9px rgba(32, 55, 92, .09), inset -4px -4px 9px rgba(255, 255, 255, .95);
}
html[data-style="neumorph"] .card,
html[data-style="neumorph"] .stat,
html[data-style="neumorph"] .btn,
html[data-style="neumorph"] .preset-card,
html[data-style="neumorph"] .menu-group-card {
  box-shadow: var(--neu-out);
  border-color: transparent;
}
html[data-style="neumorph"] .btn:active,
html[data-style="neumorph"] .menu-child-row,
html[data-style="neumorph"] .switch {
  box-shadow: var(--neu-in);
}
/* ==========================================================================
   ⚠️ 这里有一条**通用排除口**：`[data-flat]`
   --------------------------------------------------------------------------
   2026-09-30 查出（真实缺陷，不是审美问题）：

   上面这批规则里有 `textarea` 这一个**光元素选择器**，它会给**全站每一个**
   textarea 加上内阴影（`--neu-in`）。而「问 AI」页重做后，输入框画在
   **自己的白色圆角盒子**（`.ask-box`）里，那条内阴影于是在盒子里又画出
   一个"小一号的框" —— 视觉上是**双框**，看起来像输入框坏了。

   怎么发现的：不是靠眼睛。用无头浏览器把 composer 子树每个元素的
   computed style 打出来，看到 textarea 上挂着一个没人写过的
   `box-shadow: rgba(163,177,198,.32) 4px 4px 9px 0 inset` ——
   值正好等于 theme.css 的 `--neu-in`。

   为什么不直接删掉 `textarea` 这个选择器：**后台正靠它**。
   后台有不少 textarea 不带 `.input` 类（`.chat-input`、`.of-input`、
   `.ai-input`…），删了它们会一起失去拟物观感 ——
   那就是"改公共文件把原来的页面弄坏了"（本项目红线第 12 条）。

   所以给它一个**显式退出机制**：哪个输入框自己要画外框，就加 `data-flat`。
   这是"通用能力"而不是"给某个页面的补丁" —— 以后再遇到同类冲突不用再改这里。
   ========================================================================== */
html[data-style="neumorph"] .input:not([data-flat]),
html[data-style="neumorph"] .select:not([data-flat]),
html[data-style="neumorph"] input[type="text"]:not([data-flat]),
html[data-style="neumorph"] input[type="password"]:not([data-flat]),
html[data-style="neumorph"] textarea:not([data-flat]) {
  box-shadow: var(--neu-in);
  border-color: transparent;
}

/* ---- 玻璃拟态：半透明 + 背景模糊 ---- */
/*
  ⚠️ `:not(.hero)` 不是多余的，是修一个真实缺陷（缺陷 15，2026-09-28）。

  欢迎横幅的元素 class 是 "card hero" —— 它靠 .card 拿内边距。
  但下面这条规则的选择器权重（0,3,1）高于 .hero（0,1,0），于是当后台把
  外观设成 style=glass 时，`.hero` 自己的渐变底被覆盖成
  rgba(255,255,255,.58) 半透明白，而文字仍是 #fff ——
  **白字白底，整条横幅几乎看不见**。

  更麻烦的是它完全静默：接口 200、控制台无报错、文字就在 DOM 里，
  72/72 项验收全绿也没抓到，只能靠看截图发现（和缺陷 7「标签被逐字符渲染」同类）。
  既然根本原因是"带自己背景的横幅被当成普通表面处理"，
  就显式把它排除在外，而不是去堆 .hero 的权重 —— 后者迟早会被更高的规则再盖掉。
*/
html[data-style="glass"] .card:not(.hero),
html[data-style="glass"] .stat,
html[data-style="glass"] .topbar,
html[data-style="glass"] .modal,
html[data-style="glass"] .preset-card {
  background: var(--glass-bg);
  -webkit-backdrop-filter: blur(var(--glass-blur)) saturate(1.4);
  backdrop-filter: blur(var(--glass-blur)) saturate(1.4);
  border: 1px solid var(--glass-border);
}
/* 横幅自带渐变底与白字，任何"表面质感"都不该改它的背景。
   这里再显式声明一次，作为第二道保险（防止将来新增 style 时又被忘了排除）。 */
html[data-style="glass"] .hero,
html[data-style="neumorph"] .hero {
  background: linear-gradient(135deg, var(--brand-secondary), var(--brand-deep));
  border: 0;
}
/* 玻璃拟态需要背景本身有层次，否则纯色背景模糊后看不出效果。
   这里给 body 铺两层极淡的径向渐变作为"底纹"。 */
html[data-style="glass"] body {
  background-image:
    radial-gradient(1000px 520px at 12% -6%, rgba(var(--brand-rgb), .16), transparent 62%),
    radial-gradient(820px 460px at 92% 6%, rgba(var(--accent-rgb), .14), transparent 58%);
  background-attachment: fixed;
}

/* ==========================================================================
   侧边栏：三档风格
   --------------------------------------------------------------------------
   默认 dark（深色渐变）由各页面 CSS 直接写；
   这里只覆盖 light 与 glass 两种。
   ========================================================================== */

/* 浅色侧边栏：与主区融为一体，靠边框分隔（轻拟物风格常用） */
html[data-sidebar="light"] .sidebar {
  background: var(--card);
  color: var(--text);
  border-right: 1px solid var(--border);
}
html[data-sidebar="light"] .sidebar-brand { border-bottom-color: var(--border); }
html[data-sidebar="light"] .sidebar-brand .name { color: var(--text); }
html[data-sidebar="light"] .sidebar-brand .mark { background: rgba(var(--brand-rgb), .10); }
html[data-sidebar="light"] .sidebar-brand .mark svg { fill: var(--brand-primary); }
html[data-sidebar="light"] .menu-group > .group-title { color: var(--text-muted); }
html[data-sidebar="light"] .menu-group > .group-title:hover { color: var(--text); }
html[data-sidebar="light"] .menu-item { color: var(--text-muted); }
html[data-sidebar="light"] .menu-item:hover {
  background: rgba(var(--brand-rgb), .06);
  color: var(--text);
}
html[data-sidebar="light"] .menu-item.active {
  background: rgba(var(--brand-rgb), .12);
  color: var(--brand-primary);
}
html[data-sidebar="light"] .menu::-webkit-scrollbar-thumb { background: rgba(0, 0, 0, .14); }

/* 玻璃侧边栏：深色半透明 + 模糊，透出背后的底纹 */
html[data-sidebar="glass"] .sidebar {
  background: linear-gradient(180deg, rgba(59, 74, 107, .90), rgba(42, 53, 80, .95));
  -webkit-backdrop-filter: blur(16px) saturate(1.3);
  backdrop-filter: blur(16px) saturate(1.3);
  border-right: 1px solid rgba(255, 255, 255, .10);
}

/* ==========================================================================
   .util-toast —— `CunwuUtil.toast` 自己造的那个提示条
   --------------------------------------------------------------------------
   ⚠️⚠️ 这是一条**补了缺失样式的修复**，背景必须写清楚，否则以后有人会
   以为它是多余的、顺手删掉。

   事实：`assets/lg_util.js` 的 `U.toast` 有**三层兜底**，第二层是
   "自己造一个提示条"—— 代码是 `el.className = 'util-toast show'`。
   但全站 CSS 里**从来没有 `.util-toast` 这个选择器**（2026-09-30 全仓 grep 确认：
   只有 lg_util.js 三处赋值，没有任何 CSS 定义）。

   后果：H5 端**没有** `CunwuApp.toast`（那是后台 admin.js 提供的，h5.html 不加载它），
   所以 H5 上每一次 `U.toast(...)` 都走第二层 —— 于是它创建的是一个
   **完全没有样式的裸 `<div>`**，被追加到 `<body>` 末尾。

   实测（headless，390×844）：
     `#cunwuUtilToast` → `position: static`、背景全透明、y=844、宽 390、高 19
     也就是**一行没背景的黑字，掉在页面最底边**；
    `.h5-wrap` 是 `min-height: 100vh`，所以这行字正好在首屏之外 ——
   在真机上表现为"提示要么看不见、要么在页面往下滚时突然出现在中间某个位置"。
   武总看到的那次是"浮在屏幕正中央、压住了欢迎文字"（页面高度不同时它落在视口内）。

   为什么这个问题能活这么久：**它不报错、样式也"存在"（class 名在 DOM 上）**，
   静态检查（grep class 名）会认为"有样式"。只有**量 computed style** 才看得出
   它是 `static` + 透明背景。同类缺陷在本项目的判据是同一句：
   **断言必须落在"能看见症状"的那一层。**

   样式设计（三条约定的由来）：
     ① **固定贴底**（不是居中）—— 轻提示是"刚发生了一件事"的反馈，
        贴底不遮内容主体；居中必然压住屏幕正中的东西（这次压的就是欢迎语）。
     ② `z-index: 70` —— 要高于底部导航（50）与录音层（60），否则会被它们盖住。
     ③ `pointer-events: none` —— 提示条不该吃掉点击（它会盖住底部按钮，
        吃掉事件就变成"点了没反应"）。
   放在 `theme.css` 是因为**每个页面都加载它**（admin / h5 / index / screen 都引了
   `/theme.css`），而这个提示条是 `lg_util.js` 提供的公共件 ——
   放 h5.css 就管不到后台，放 admin.css 就管不到村民端。
   ========================================================================== */
.util-toast {
  position: fixed;
  left: 50%;
  /* 贴底。`env(safe-area-inset-bottom)` 是给 iPhone 的"手势横线"让位，
     不然提示条会压在系统手势条上（既不美观也难点）。 */
  bottom: calc(96px + env(safe-area-inset-bottom, 0px));
  transform: translateX(-50%) translateY(6px);
  z-index: 70;
  box-sizing: border-box;
  max-width: min(88vw, 420px);
  padding: 10px 16px;
  border-radius: 10px;
  background: rgba(28, 33, 44, .92);
  color: #fff;
  font-size: 14.5px;
  line-height: 1.5;
  text-align: center;
  word-break: break-word;
  box-shadow: 0 6px 22px rgba(15, 20, 30, .22);
  opacity: 0;
  visibility: hidden;
  pointer-events: none;
  transition: opacity .16s ease, transform .16s ease, visibility .16s;
}
/* 显示态。
   ⚠️ 用 `visibility` 而不是只靠 `opacity`：只降透明度的话，这条**不可见但仍在
   文档流上方**的固定层会继续参与命中测试（吃掉它覆盖区域的点击）——
   表现就是"底部那条按钮偶尔点不动"，而那极难定位。
   `visibility: hidden` 会一并退出命中测试，`pointer-events: none` 是第二道保险。 */
.util-toast.show {
  opacity: 1;
  visibility: visible;
  transform: translateX(-50%) translateY(0);
}
/* 错误态：换成警示色。不改文案、不改位置 —— 位置固定是这一条的要点。 */
.util-toast.show.error,
.util-toast.show.err {
  background: rgba(197, 40, 46, .94);
}
@media (prefers-reduced-motion: reduce) {
  .util-toast { transition: none; }
}

