/* ==========================================================================
   #44 全站视觉重做 —— 密度收敛 + 组件统一 + 深色模式

   加载顺序在 01~09 之后（见 templates/partials/styles.html）。

   现实约束：06-mobile.css 里的「iOS 27 Liquid Glass」段虽然放在移动端文件里，
   却是全局生效的设计层，而且几乎每条规则都带 !important。真要改一个组件的
   外观，只能同样用 !important 才压得住——这是本仓库的既有约定，不是新造的。
   所以本文件里的覆盖一律带 !important，并且沿用 iOS27 / cw 两套令牌词汇，
   不另起一套命名。

   四件事：
   1) 密度——车间平板是 10 寸不是 27 寸，同屏要放更多有效信息；
   2) 收敛——.kpi-* 与 .stat-*、两套弹窗结构、同一句"暂无数据"，
      让 100+ 个页面不用改模板也长得一样；
   3) 网格——项目从未加载 Bootstrap，模板里照抄的 .row / .col-* 全是空类名，
      这里补一套最小实现，不用改任何模板；
   4) 深色模式——车间顶灯下白屏反光严重，夜间值班更明显。
   ========================================================================== */

/* ---------- 1. 密度令牌 ---------- */
:root {
    --row-py: 11px;
    --cell-px: 12px;
    --th-py: 10px;
    --control-h: 36px;

    --focus-ring: 0 0 0 3px rgba(0, 122, 255, 0.30);

    /* 表面层级：深色模式只改这几个值 */
    --surface-1: rgba(255, 255, 255, 0.72);
    --surface-2: rgba(255, 255, 255, 0.50);
    --surface-3: rgba(255, 255, 255, 0.32);
    --surface-solid: #ffffff;
    --hairline: rgba(0, 0, 0, 0.09);
    --hairline-strong: rgba(0, 0, 0, 0.14);
    --row-hover: rgba(0, 122, 255, 0.055);
    --overlay-scrim: rgba(0, 0, 0, 0.25);

    /* 表头专用：单独拎出来，深色模式一并换 */
    --th-bg: linear-gradient(180deg, rgba(13, 71, 161, 0.055) 0%, rgba(0, 191, 165, 0.035) 100%);
    --th-fg: var(--cw-primary-dark);

    /* 网格工具类用到的语义色 */
    --shim-success: #007A33;
}

/* 键盘可达性：所有可聚焦元素统一焦点环 */
a:focus-visible,
button:focus-visible,
input:focus-visible,
select:focus-visible,
textarea:focus-visible,
[tabindex]:focus-visible {
    outline: none;
    box-shadow: var(--focus-ring);
    border-radius: var(--radius-sm);
}

/* ==========================================================================
   2. 表格密度与表头
   iOS27 段给 th/td 写了 padding: 14px 16px !important，一屏能少看两行。
   表头全大写对中文毫无意义，对英文又要多占横向空间——改为常规字形 + 600 字重。
   ========================================================================== */
table thead th {
    padding: var(--th-py) var(--cell-px) !important;
    font-size: 12px !important;
    font-weight: 600 !important;
    letter-spacing: 0.2px !important;
    text-transform: none !important;
    color: var(--th-fg) !important;
    background: var(--th-bg) !important;
    border-bottom: 1px solid var(--hairline-strong) !important;
}

table tbody td {
    padding: var(--row-py) var(--cell-px) !important;
    font-size: 13px !important;
}

table tbody tr:hover {
    background: var(--row-hover) !important;
    transform: none !important;
}

/* 数字列右对齐，表格读起来才像数据表而不是文字流 */
.data-table td.num,
.data-table th.num {
    text-align: right !important;
    font-variant-numeric: tabular-nums;
}

/* 移动端把表格拆成卡片，单元格改成 label: value 两栏，
   内边距与桌面表格式完全不同——上面那条密度规则不能盖到它头上。 */
@media (max-width: 768px) {
    .data-table tbody td:not(.empty-cell) {
        padding: 6px 0 !important;
    }
}

/* ==========================================================================
   3. 网格与工具类补齐
   项目从来没有加载 Bootstrap，但 12 个模板里写着 .row / .col-12 / .container-fluid，
   这些类名全是空的——validation 系列 5 页的页头标题和「新建」按钮因此挤在一行，
   .table 也缺基础样式（只有浏览器默认表格）。
   这里按 Bootstrap 5 的语义补一套最小实现，只覆盖模板里真正用到的类名。
   刻意不引整套框架：为了那 30KB 的 JS 和 400KB 的图标字体不划算。
   ========================================================================== */
.container,
.container-fluid {
    width: 100%;
    margin-right: auto;
    margin-left: auto;
    padding-right: 8px;
    padding-left: 8px;
}

.container {
    max-width: 1200px;
}

/* 行用负外边距抵消列的内边距，这样列里的内容和容器内容框严丝合缝对齐 */
.row {
    display: flex;
    flex-wrap: wrap;
    margin-right: -8px;
    margin-left: -8px;
}

.col-12 {
    flex: 0 0 auto;
    width: 100%;
    padding-right: 8px;
    padding-left: 8px;
}

@media (min-width: 768px) {
    .col-md-3 {
        flex: 0 0 auto;
        width: 25%;
        padding-right: 8px;
        padding-left: 8px;
    }
}

/* 工具类：Bootstrap 5 语义，只实现实际用到的档位 */
.d-flex { display: flex !important; }
.d-block { display: block !important; }
.justify-content-between { justify-content: space-between !important; }
.align-items-center { align-items: center !important; }
.text-center { text-align: center !important; }
.text-muted { color: var(--text-secondary) !important; }
.text-white { color: #fff !important; }
.text-success { color: var(--shim-success) !important; }
.fs-3 { font-size: 1.25rem !important; }
.mb-0 { margin-bottom: 0 !important; }
.mb-2 { margin-bottom: 8px !important; }
.mb-3 { margin-bottom: 16px !important; }
.mb-4 { margin-bottom: 24px !important; }
.mt-3 { margin-top: 16px !important; }
.mt-4 { margin-top: 24px !important; }
.py-5 { padding-top: 48px !important; padding-bottom: 48px !important; }
.overflow-x-auto { overflow-x: auto !important; }

/* 背景色：监控页用 .card.bg-primary.text-white 做四色概览卡 */
.bg-primary { background: var(--cw-primary) !important; }
.bg-success { background: #34C759 !important; }
.bg-info { background: var(--cw-primary-light) !important; }
.bg-danger { background: #FF3B30 !important; }

/* 基础表格：.data-table 是项目自己的表，.table 是模板里直接写死的另一种 */
.table {
    width: 100%;
    border-collapse: collapse;
}

/* 浏览器默认给 <th> 居中、给 <td> 左对齐，于是这两种表会出现
   "表头居中、数据左对齐"的错位。.data-table 早就显式左对齐，
   这里让 .table 跟它一致。 */
.table thead th {
    text-align: left !important;
}

.table-hover tbody tr:hover {
    background: var(--row-hover) !important;
}

.table-striped tbody tr:nth-child(odd) {
    background: var(--surface-2);
}

.table-sm thead th {
    padding: 6px 10px !important;
    font-size: 12px !important;
}

.table-sm tbody td {
    padding: 6px 10px !important;
    font-size: 12px !important;
}

/* ==========================================================================
   4. 空状态与加载态
   30+ 个页面用同一句 <td colspan="N" class="empty-cell">暂无数据</td> 收尾。
   这里用 CSS 把它变成设计过的空状态——不动任何模板，30+ 页一起变。
   ========================================================================== */
.empty-cell {
    text-align: center !important;
    color: var(--text-tertiary) !important;
    padding: 46px 16px !important;
    font-size: 13px !important;
    letter-spacing: 0.2px;
    vertical-align: middle;
    background: transparent !important;
}

/* 空盒子图标：mask + currentColor，深色模式自动跟着变 */
.empty-cell::before {
    content: '';
    display: block;
    width: 38px;
    height: 38px;
    margin: 0 auto 12px;
    background: currentColor;
    opacity: 0.30;
    -webkit-mask-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24' fill='none' stroke='%23000' stroke-width='1.6' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpath d='M3 7.5 12 3l9 4.5v9L12 21l-9-4.5z'/%3E%3Cpath d='M3 7.5 12 12l9-4.5M12 12v9'/%3E%3Cpath d='M7.5 5.25 16.5 9.75'/%3E%3C/svg%3E");
    mask-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' viewBox='0 0 24 24' fill='none' stroke='%23000' stroke-width='1.6' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpath d='M3 7.5 12 3l9 4.5v9L12 21l-9-4.5z'/%3E%3Cpath d='M3 7.5 12 12l9-4.5M12 12v9'/%3E%3Cpath d='M7.5 5.25 16.5 9.75'/%3E%3C/svg%3E");
    -webkit-mask-size: contain;
    mask-size: contain;
    -webkit-mask-repeat: no-repeat;
    mask-repeat: no-repeat;
}

/* 加载态：同一格换成转圈 */
.empty-cell.is-loading::before {
    -webkit-mask-image: none !important;
    mask-image: none !important;
    width: 26px;
    height: 26px;
    opacity: 1;
    border: 2px solid rgba(0, 122, 255, 0.20);
    border-top-color: var(--apple-blue);
    border-radius: 50%;
    animation: cwSpin 0.8s linear infinite;
}

@keyframes cwSpin {
    to { transform: rotate(360deg); }
}

/* 整块空状态（.empty-state / .no-data） */
.empty-state,
.no-data {
    display: flex;
    flex-direction: column;
    align-items: center;
    justify-content: center;
    gap: var(--space-2);
    text-align: center;
    min-height: 160px;
    border-style: dashed !important;
    border-width: 1px !important;
}

.empty-state-icon {
    width: 44px;
    height: 44px;
    display: flex;
    align-items: center;
    justify-content: center;
    border-radius: var(--ios27-radius-sm, 16px);
    background: var(--cw-gradient-soft);
    color: var(--cw-primary);
    font-size: 22px;
    margin-bottom: var(--space-1);
}

.empty-state-title {
    font-size: 14px;
    font-weight: 600;
    color: var(--text-secondary);
}

.empty-state-description {
    font-size: 13px;
    color: var(--text-tertiary);
    max-width: 42ch;
}

.empty-state-actions { margin-top: var(--space-3); }

/* 骨架屏：07-motion.css 定义了 45 个类但没有页面用过，这里把行/卡片骨架接上 */
.skeleton-line,
.skeleton-card,
.skeleton-table {
    background: linear-gradient(90deg,
        rgba(0, 0, 0, 0.045) 25%,
        rgba(0, 0, 0, 0.085) 50%,
        rgba(0, 0, 0, 0.045) 75%);
    background-size: 200% 100%;
    animation: skeletonLoading 1.4s infinite;
    border-radius: var(--ios27-radius-xs, 10px);
}

/* ==========================================================================
   5. KPI / 统计卡：两套词汇收敛成一套密度
   .kpi-grid .kpi-card 已经被 09-fixes 收到 16px 20px / 26px 字号，
   .stat-card 却还停在 iOS27 的 24px 内边距 / 2rem 字号——同一页里混用像两套系统。
   ========================================================================== */
.kpi-grid .kpi-card,
.stats-grid .stat-card,
.stat-card {
    padding: 16px 20px !important;
    border-radius: var(--ios27-radius-lg) !important;
}

.kpi-grid .kpi-card .kpi-value,
.stats-grid .stat-card .stat-value,
.stat-card .stat-value,
.kpi-card .kpi-value {
    font-size: 26px !important;
    line-height: 1.15 !important;
}

.kpi-grid .kpi-icon,
.stat-card .stat-icon {
    width: 44px !important;
    height: 44px !important;
    font-size: 20px !important;
}

.kpi-label,
.stat-label {
    font-size: 12px !important;
    color: var(--text-secondary) !important;
    margin-top: 2px !important;
}

.kpi-sub {
    font-size: 11px !important;
    color: var(--text-tertiary) !important;
    margin-top: 3px !important;
}

/* ==========================================================================
   6. 弹窗：两套结构收敛成一套
   57 个页面用 .modal-overlay > .modal > .modal-body，
   11 个页面用裸 .modal > .modal-content。后者被 iOS27 段当成"内容块"处理，
   圆角、玻璃强度和前者对不上。这里把 .modal 也按 iOS27 的材质重铺。
   ========================================================================== */
.modal {
    background: var(--ios27-glass-bg-strong) !important;
    backdrop-filter: var(--ios27-glass-blur-strong) !important;
    -webkit-backdrop-filter: var(--ios27-glass-blur-strong) !important;
    border: 1px solid var(--ios27-glass-border) !important;
    border-radius: var(--ios27-radius-xl) !important;
    box-shadow: 0 20px 60px rgba(0, 0, 0, 0.15), 0 40px 100px rgba(0, 0, 0, 0.1) !important;
}

.modal > .modal-content {
    background: transparent !important;
    backdrop-filter: none !important;
    -webkit-backdrop-filter: none !important;
    border: none !important;
    border-radius: 0 !important;
    box-shadow: none !important;
}

/* ==========================================================================
   7. 筛选区：控件高度统一
   iOS27 段给所有输入框写了 padding: 12px 16px !important，
   直接压高度会把文字挤扁——必须同时把内边距改回水平方向。
   ========================================================================== */
.filter-bar {
    gap: var(--space-3) !important;
    padding: var(--space-3) var(--space-4) !important;
    border-radius: var(--ios27-radius-md) !important;
}

.filter-bar input,
.filter-bar select {
    height: var(--control-h) !important;
    padding: 0 var(--space-3) !important;
    font-size: 13px !important;
    min-width: 130px;
}

.filter-bar .btn {
    height: var(--control-h) !important;
    padding: 0 var(--space-4) !important;
    font-size: 13px !important;
    min-height: var(--control-h) !important;
}

/* ==========================================================================
   8. 侧边导航分组
   导航按功能优先级分组（样品与检测 / 报告与合规 / …），组顺序是产品定的。
   分组标题要小、要淡，不能抢菜单项本身的视觉权重；
   折叠侧边栏时标题必须收掉，否则 80px 宽的栏里会挤成一团。
   ========================================================================== */
.sidebar-nav .nav-group {
    display: block !important;
    margin-bottom: var(--space-2) !important;
}

.sidebar-nav .nav-group-title {
    display: block !important;
    padding: var(--space-3) var(--space-4) var(--space-1) !important;
    margin: 0 !important;
    font-size: 11px !important;
    font-weight: 600 !important;
    letter-spacing: 0.08em !important;
    line-height: 1.4 !important;
    color: var(--text-tertiary) !important;
    opacity: 0.85;
    white-space: nowrap;
    overflow: hidden;
    text-overflow: ellipsis;
    user-select: none;
    border-top: 1px solid var(--hairline) !important;
    margin-top: var(--space-2) !important;
}

.sidebar-nav .nav-group:first-child .nav-group-title {
    border-top: none !important;
    margin-top: 0 !important;
    padding-top: var(--space-2) !important;
}

/* 折叠态：只剩图标，分组标题让位 */
.sidebar.collapsed .sidebar-nav .nav-group-title {
    display: none !important;
}

.sidebar.collapsed .sidebar-nav .nav-group {
    margin-bottom: var(--space-1) !important;
}

/* ==========================================================================
   9. 首页：产品定位与优先级阶梯
   侧边栏分组解决"菜单怎么排"，这一段解决"这套系统先做什么"。
   定位卡片与优先级阶梯是同一件事的两面：定位说清为谁做，阶梯说清先后顺序。
   ========================================================================== */
.pw-positioning {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(280px, 1fr));
    gap: var(--space-3);
}

.pw-block {
    padding: var(--space-3) var(--space-4);
    border-radius: var(--radius-md);
    background: rgba(0, 122, 255, 0.05);
    border: 1px solid rgba(0, 122, 255, 0.12);
}

.pw-block-label {
    font-size: 11px !important;
    font-weight: 600 !important;
    letter-spacing: 0.08em !important;
    color: var(--text-tertiary) !important;
    margin-bottom: 6px !important;
}

.pw-block-text {
    font-size: 13px !important;
    line-height: 1.6 !important;
    color: var(--text-secondary) !important;
}

.pw-ladder-title {
    margin: var(--space-5) 0 var(--space-3);
    font-size: 12px !important;
    font-weight: 600 !important;
    letter-spacing: 0.06em !important;
    color: var(--text-tertiary) !important;
}

.pw-ladder {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(240px, 1fr));
    gap: var(--space-3);
}

.pw-tier {
    padding: var(--space-3) var(--space-4);
    border-radius: var(--radius-md);
    border: 1px solid var(--hairline);
    background: var(--glass-bg, rgba(255, 255, 255, 0.72));
}

.pw-tier-head {
    display: flex;
    align-items: center;
    gap: var(--space-2);
    margin-bottom: 6px;
}

.pw-tier-badge {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    min-width: 26px;
    height: 20px;
    padding: 0 6px;
    border-radius: var(--radius-full);
    font-size: 11px;
    font-weight: 700;
    letter-spacing: 0.04em;
    color: var(--cw-primary) !important;
    background: rgba(0, 122, 255, 0.12);
}

.pw-tier-title {
    font-size: 13px !important;
    font-weight: 600 !important;
    color: var(--text-primary) !important;
}

.pw-tier-desc {
    font-size: 12px !important;
    line-height: 1.55 !important;
    color: var(--text-secondary) !important;
}

.pw-chips {
    display: flex;
    flex-wrap: wrap;
    gap: 6px;
    margin-top: var(--space-3);
}

.pw-chip {
    font-size: 11px;
    padding: 2px 8px;
    border-radius: var(--radius-full);
    color: var(--text-secondary);
    background: rgba(0, 122, 255, 0.07);
    border: 1px solid rgba(0, 122, 255, 0.10);
    white-space: nowrap;
}

.pw-quick-grid {
    display: grid;
    grid-template-columns: repeat(auto-fill, minmax(220px, 1fr));
    gap: var(--space-3);
}

/* ==========================================================================
   10. 深色模式
   车间顶灯下白屏反光严重，夜间值班更明显。
   iOS27 层把材质写成 var(--ios27-glass-bg) !important——重新定义变量即可
   整体变暗，不需要逐条覆写属性。
   ========================================================================== */
html[data-theme="dark"] {
    color-scheme: dark;

    /* 文本与表面 */
    --text-primary: #f2f2f7;
    --text-secondary: #a9a9b0;
    --text-tertiary: #7d7d85;
    --text-quaternary: #5c5c63;

    --bg-primary: #0d0f14;
    --bg-secondary: rgba(28, 30, 38, 0.86);
    --bg-tertiary: rgba(44, 47, 57, 0.72);

    --surface-1: rgba(30, 33, 41, 0.78);
    --surface-2: rgba(26, 29, 36, 0.66);
    --surface-3: rgba(22, 24, 30, 0.50);
    --surface-solid: #1c1f26;
    --hairline: rgba(255, 255, 255, 0.09);
    --hairline-strong: rgba(255, 255, 255, 0.15);
    --row-hover: rgba(0, 122, 255, 0.14);
    --overlay-scrim: rgba(0, 0, 0, 0.55);

    /* 老玻璃令牌 */
    --glass-bg: rgba(24, 26, 33, 0.62);
    --glass-bg-heavy: rgba(30, 33, 41, 0.78);
    --glass-bg-light: rgba(24, 26, 33, 0.44);
    --glass-bg-ultra-light: rgba(24, 26, 33, 0.26);
    --glass-border: rgba(255, 255, 255, 0.10);
    --glass-border-light: rgba(255, 255, 255, 0.16);
    --glass-border-dark: rgba(0, 0, 0, 0.34);
    --glass-reflection: linear-gradient(135deg, rgba(255, 255, 255, 0.05) 0%, rgba(255, 255, 255, 0) 40%);

    /* 05-theme.css 给 .table-card::before / ::after 叠的是纯白玻璃高光。
       表头底色是半透明的，这层白会从下面透出来——浅色下白叠白看不出来，
       深色下就是一条刺眼的白带。高光改成极淡的白色，深色下才有玻璃感而不是白斑。 */
    --glass-highlight-top: linear-gradient(180deg,
        rgba(255, 255, 255, 0.07) 0%,
        rgba(255, 255, 255, 0.02) 35%,
        rgba(255, 255, 255, 0) 65%);
    --glass-reflection-diagonal: linear-gradient(135deg,
        rgba(255, 255, 255, 0.04) 0%,
        rgba(255, 255, 255, 0.01) 25%,
        rgba(255, 255, 255, 0) 50%);
    --glass-edge-glow: 0 0 0 1px rgba(255, 255, 255, 0.10), 0 0 20px rgba(255, 255, 255, 0.04);

    --border-light: rgba(255, 255, 255, 0.07);
    --border-medium: rgba(255, 255, 255, 0.12);

    --shadow-sm: 0 2px 8px rgba(0, 0, 0, 0.40);
    --shadow-md: 0 4px 16px rgba(0, 0, 0, 0.45);
    --shadow-lg: 0 8px 32px rgba(0, 0, 0, 0.50);
    --shadow-xl: 0 20px 60px rgba(0, 0, 0, 0.60);

    /* iOS27 材质令牌：改这几个，整站玻璃自动变暗 */
    --ios27-glass-bg: rgba(30, 33, 41, 0.72);
    --ios27-glass-bg-strong: rgba(26, 29, 36, 0.90);
    --ios27-glass-bg-subtle: rgba(16, 18, 23, 0.70);
    --ios27-glass-border: rgba(255, 255, 255, 0.12);
    --ios27-glass-border-top: rgba(255, 255, 255, 0.20);
    --ios27-glass-border-bottom: rgba(0, 0, 0, 0.40);
    --ios27-shadow-card:
        0 1px 1px rgba(255, 255, 255, 0.06) inset,
        0 -1px 1px rgba(0, 0, 0, 0.40) inset,
        0 2px 8px rgba(0, 0, 0, 0.40),
        0 10px 30px rgba(0, 0, 0, 0.50);
    --ios27-shadow-card-hover:
        0 1px 1px rgba(255, 255, 255, 0.08) inset,
        0 -1px 1px rgba(0, 0, 0, 0.40) inset,
        0 6px 20px rgba(0, 0, 0, 0.45),
        0 20px 56px rgba(0, 0, 0, 0.60);
    --ios27-gradient-highlight: linear-gradient(180deg, rgba(255, 255, 255, 0.08) 0%, rgba(255, 255, 255, 0.02) 45%, rgba(255, 255, 255, 0) 100%);
    --ios27-gradient-border: linear-gradient(135deg, rgba(255, 255, 255, 0.18) 0%, rgba(255, 255, 255, 0.04) 50%, rgba(0, 0, 0, 0.20) 100%);

    /* 品牌色：深色底上要提亮，否则深蓝看不清 */
    --cw-primary-dark: #6FA8E8;
    --cw-primary: #4A90E2;
    --cw-primary-light: #7FB3F0;
    --cw-accent: #35D6BE;
    --cw-accent-light: #4FE3CD;
    --cw-accent-dark: #26A896;

    --th-bg: linear-gradient(180deg, rgba(111, 168, 232, 0.10) 0%, rgba(53, 214, 190, 0.06) 100%);
    --th-fg: #9FC4EA;

    --shim-success: #4CD97B;
}

html[data-theme="dark"] body {
    background:
        radial-gradient(ellipse at 20% 15%, rgba(0, 122, 255, 0.10) 0%, transparent 55%),
        radial-gradient(ellipse at 85% 25%, rgba(118, 75, 162, 0.10) 0%, transparent 55%),
        radial-gradient(ellipse at 55% 90%, rgba(90, 200, 250, 0.06) 0%, transparent 55%),
        linear-gradient(140deg, #101319 0%, #151822 45%, #0f1117 100%) !important;
    background-attachment: fixed;
}

/* iOS27 层里写死成白色的几处，深色下要单独压掉 */
html[data-theme="dark"] .data-table tbody td {
    background: transparent !important;
}

html[data-theme="dark"] .modal-header {
    background: linear-gradient(135deg, rgba(111, 168, 232, 0.08) 0%, rgba(53, 214, 190, 0.05) 100%) !important;
}

html[data-theme="dark"] input:focus,
html[data-theme="dark"] select:focus,
html[data-theme="dark"] textarea:focus {
    background: rgba(16, 18, 23, 0.92) !important;
}

html[data-theme="dark"] input:hover:not(:focus),
html[data-theme="dark"] select:hover:not(:focus),
html[data-theme="dark"] textarea:hover:not(:focus) {
    background: rgba(20, 22, 28, 0.80) !important;
}

html[data-theme="dark"] .modal-overlay {
    background: var(--overlay-scrim) !important;
}

html[data-theme="dark"] .modal::after {
    background: var(--overlay-scrim) !important;
}

html[data-theme="dark"] .empty-state,
html[data-theme="dark"] .no-data {
    background: rgba(255, 255, 255, 0.035) !important;
    border-color: rgba(255, 255, 255, 0.14) !important;
}

html[data-theme="dark"] .skeleton,
html[data-theme="dark"] .skeleton-loading,
html[data-theme="dark"] .skeleton-line,
html[data-theme="dark"] .skeleton-card,
html[data-theme="dark"] .skeleton-table {
    background: linear-gradient(90deg,
        rgba(255, 255, 255, 0.05) 25%,
        rgba(255, 255, 255, 0.10) 50%,
        rgba(255, 255, 255, 0.05) 75%);
    background-size: 200% 100%;
}

html[data-theme="dark"] ::-webkit-scrollbar-track { background: rgba(255, 255, 255, 0.04); }
html[data-theme="dark"] ::-webkit-scrollbar-thumb {
    background: rgba(255, 255, 255, 0.16);
    border-color: rgba(255, 255, 255, 0.06);
}
html[data-theme="dark"] ::-webkit-scrollbar-thumb:hover { background: rgba(255, 255, 255, 0.26); }

/* ---------- 深色模式徽章 ----------
   05-theme.css 给 .badge/.status-badge/.tag 写死了 rgba(255,255,255,0.7) 的白底，
   06-mobile.css 又给每个 .status-* 配了「深色文字 + 0.12~0.18 淡色底」。
   浅色下两者都没问题；深色下白底配白字是白纸黑字反过来，而状态色是
   深色文字落在几乎透明的底上——两边都读不出来。
   这里把底色压到深色玻璃，文字换成适合深底的亮色。
   底色那条刻意用 :where() 压到 0 特异度：这样 06-mobile.css 里各状态的
   !important 渐变底仍然生效，不会被这条通用底色盖掉。 */
:where(html[data-theme="dark"]) :where(.badge, .status-badge, .tag) {
    background: rgba(255, 255, 255, 0.07) !important;
}

html[data-theme="dark"] .badge,
html[data-theme="dark"] .status-badge,
html[data-theme="dark"] .tag {
    color: var(--text-primary);
    border: 1px solid rgba(255, 255, 255, 0.12) !important;
}

/* 03-components.css 给徽章叠了 50% 高的白色渐变，浅色下是玻璃高光，
   深色下会盖掉状态色，压暗 */
html[data-theme="dark"] .status-badge::before {
    background: linear-gradient(180deg, rgba(255, 255, 255, 0.10) 0%, transparent 100%) !important;
}

html[data-theme="dark"] .status-badge {
    box-shadow: 0 1px 2px rgba(0, 0, 0, 0.35) inset, 0 1px 3px rgba(0, 0, 0, 0.30) !important;
}

/* 各状态色在深底上的高亮版本：文字提亮，底色加浓一档 */
html[data-theme="dark"] .badge-success,
html[data-theme="dark"] .badge-approved,
html[data-theme="dark"] .status-active,
html[data-theme="dark"] .status-approved,
html[data-theme="dark"] .status-completed,
html[data-theme="dark"] .status-connected,
html[data-theme="dark"] .status-implemented,
html[data-theme="dark"] .status-in_stock,
html[data-theme="dark"] .status-issued,
html[data-theme="dark"] .status-online,
html[data-theme="dark"] .status-pass,
html[data-theme="dark"] .status-passed,
html[data-theme="dark"] .status-published,
html[data-theme="dark"] .status-released,
html[data-theme="dark"] .status-report_approved,
html[data-theme="dark"] .status-report_issued,
html[data-theme="dark"] .status-resolved,
html[data-theme="dark"] .status-reviewed,
html[data-theme="dark"] .status-success,
html[data-theme="dark"] .status-valid,
html[data-theme="dark"] .status-verified,
html[data-theme="dark"] .tag-success {
    background: linear-gradient(135deg, rgba(52, 199, 89, 0.24) 0%, rgba(0, 191, 165, 0.18) 100%) !important;
    color: #4CD97B !important;
}

html[data-theme="dark"] .status-in_retention,
html[data-theme="dark"] .status-testing_complete {
    background: linear-gradient(135deg, rgba(0, 199, 190, 0.24) 0%, rgba(52, 199, 89, 0.18) 100%) !important;
    color: #35D6BE !important;
}

html[data-theme="dark"] .badge-warning,
html[data-theme="dark"] .badge-reviewing,
html[data-theme="dark"] .status-draft,
html[data-theme="dark"] .status-in_progress,
html[data-theme="dark"] .status-pending,
html[data-theme="dark"] .status-reviewing,
html[data-theme="dark"] .tag-warning {
    background: linear-gradient(135deg, rgba(255, 149, 0, 0.24) 0%, rgba(255, 200, 0, 0.16) 100%) !important;
    color: #F5B840 !important;
}

html[data-theme="dark"] .status-calibration_due,
html[data-theme="dark"] .status-depleted,
html[data-theme="dark"] .status-in_testing,
html[data-theme="dark"] .status-inconclusive,
html[data-theme="dark"] .status-low_stock,
html[data-theme="dark"] .status-maintenance,
html[data-theme="dark"] .status-on_hold,
html[data-theme="dark"] .status-overdue,
html[data-theme="dark"] .status-quarantine,
html[data-theme="dark"] .status-repair,
html[data-theme="dark"] .status-report_pending,
html[data-theme="dark"] .status-reserved,
html[data-theme="dark"] .status-retention,
html[data-theme="dark"] .status-suspended,
html[data-theme="dark"] .status-unverified,
html[data-theme="dark"] .status-warning {
    background: linear-gradient(135deg, rgba(255, 149, 0, 0.26) 0%, rgba(255, 204, 0, 0.18) 100%) !important;
    color: #FFC44D !important;
}

html[data-theme="dark"] .badge-danger,
html[data-theme="dark"] .badge-obsolete,
html[data-theme="dark"] .status-blacklisted,
html[data-theme="dark"] .status-calibration_overdue,
html[data-theme="dark"] .status-cancelled,
html[data-theme="dark"] .status-deleted,
html[data-theme="dark"] .status-disconnected,
html[data-theme="dark"] .status-error,
html[data-theme="dark"] .status-expired,
html[data-theme="dark"] .status-fail,
html[data-theme="dark"] .status-failed,
html[data-theme="dark"] .status-invalid,
html[data-theme="dark"] .status-offline,
html[data-theme="dark"] .status-out_of_stock,
html[data-theme="dark"] .status-rejected,
html[data-theme="dark"] .status-revoked,
html[data-theme="dark"] .status-stopped,
html[data-theme="dark"] .tag-danger {
    background: linear-gradient(135deg, rgba(255, 59, 48, 0.26) 0%, rgba(255, 100, 100, 0.18) 100%) !important;
    color: #FF6B6B !important;
}

html[data-theme="dark"] .badge-distributed,
html[data-theme="dark"] .badge-info,
html[data-theme="dark"] .status-accepted,
html[data-theme="dark"] .status-acknowledged,
html[data-theme="dark"] .status-assigned,
html[data-theme="dark"] .status-capa,
html[data-theme="dark"] .status-connecting,
html[data-theme="dark"] .status-distributed,
html[data-theme="dark"] .status-implementation,
html[data-theme="dark"] .status-in_review,
html[data-theme="dark"] .status-investigation,
html[data-theme="dark"] .status-new,
html[data-theme="dark"] .status-open,
html[data-theme="dark"] .status-pending_assignment,
html[data-theme="dark"] .status-pending_distribution,
html[data-theme="dark"] .status-pending_receipt,
html[data-theme="dark"] .status-pending_review,
html[data-theme="dark"] .status-planning,
html[data-theme="dark"] .status-read,
html[data-theme="dark"] .status-received,
html[data-theme="dark"] .status-registered,
html[data-theme="dark"] .status-reporting,
html[data-theme="dark"] .status-review,
html[data-theme="dark"] .status-revised,
html[data-theme="dark"] .status-running,
html[data-theme="dark"] .status-scheduled,
html[data-theme="dark"] .status-sent,
html[data-theme="dark"] .status-submitted,
html[data-theme="dark"] .status-testing,
html[data-theme="dark"] .status-testing_completed,
html[data-theme="dark"] .status-under_revision,
html[data-theme="dark"] .status-unread,
html[data-theme="dark"] .status-validation,
html[data-theme="dark"] .tag-info {
    background: linear-gradient(135deg, rgba(0, 122, 255, 0.24) 0%, rgba(88, 86, 214, 0.18) 100%) !important;
    color: #7FB3F0 !important;
}

html[data-theme="dark"] .badge-draft,
html[data-theme="dark"] .badge-secondary,
html[data-theme="dark"] .status-archived,
html[data-theme="dark"] .status-closed,
html[data-theme="dark"] .status-deprecated,
html[data-theme="dark"] .status-disposed,
html[data-theme="dark"] .status-final,
html[data-theme="dark"] .status-inactive,
html[data-theme="dark"] .status-info,
html[data-theme="dark"] .status-obsolete,
html[data-theme="dark"] .status-pending_disposal,
html[data-theme="dark"] .status-report,
html[data-theme="dark"] .status-retired,
html[data-theme="dark"] .status-returned,
html[data-theme="dark"] .status-superseded {
    background: linear-gradient(135deg, rgba(142, 142, 147, 0.24) 0%, rgba(120, 120, 128, 0.16) 100%) !important;
    color: #A9A9B0 !important;
}

/* ==========================================================================
   11. 主题切换按钮
   ========================================================================== */
.theme-toggle {
    width: 34px;
    height: 34px;
    border-radius: var(--ios27-radius-xs, 10px);
    border: none;
    background: transparent;
    color: var(--text-secondary);
    display: flex;
    align-items: center;
    justify-content: center;
    cursor: pointer;
    font-size: 17px;
    transition: all var(--transition-fast);
}

.theme-toggle:hover {
    background: var(--bg-tertiary);
    color: var(--text-primary);
}

/* 图标表示「点一下会切到哪个模式」：亮色下显示月亮，暗色下显示太阳 */
.theme-toggle .ri-sun-line { display: none !important; }
.theme-toggle .ri-moon-line { display: block !important; }
html[data-theme="dark"] .theme-toggle .ri-sun-line { display: block !important; }
html[data-theme="dark"] .theme-toggle .ri-moon-line { display: none !important; }

/* 尊重系统的"减少动态效果" */
@media (prefers-reduced-motion: reduce) {
    .empty-cell.is-loading::before { animation-duration: 2s; }
}
