:root {
    --overlay: 255, 255, 255;
    --bg-start: #1a1a2e;
    --bg-mid: #16213e;
    --bg-end: #0f3460;
    --primary: #3b82f6;
    --accent: #2563eb;
    --primary-rgb: 59, 130, 246;
    --accent-rgb: 37, 99, 235;
    --text: #e8e8f0;
    --text-secondary: #a0a0b8;
    --brand-grad: linear-gradient(135deg, #fff 60%, rgba(255,255,255,0.7));
    --nav-bg: rgba(15, 12, 41, 0.72);
    --loading-bg: rgba(15, 12, 41, 0.85);
    --toast-bg: rgba(255, 255, 255, 0.10);
    --spinner-bg: rgba(255, 255, 255, 0.08);
    --radius: 16px;
    --radius-sm: 10px;
    --border: rgba(255, 255, 255, 0.15);
    --input-bg: rgba(255, 255, 255, 0.06);
    --text-muted: rgba(255, 255, 255, 0.6);
    --card: #1c1f2b;
    /* 背景光晕强度（深色主题生效）。数值越大，色斑越明显 */
    --orb-primary: 0.4;
    --orb-accent: 0.32;
    --orb-violet: 0.27;
    --orb-cyan: 0.22;
}

/* =================================================================
 *  界面配色方案
 *  通过 <html data-accent="..."> 切换主色（--primary / --accent 及对应 RGB）。
 *  默认（无 data-accent）为「宝蓝」。
 * ================================================================= */
[data-accent="purple"] { --primary:#667eea; --accent:#764ba2; --primary-rgb:102,126,234; --accent-rgb:118,75,162; }
[data-accent="green"]  { --primary:#198754; --accent:#157347; --primary-rgb:25,135,84;  --accent-rgb:21,115,71; }
[data-accent="red"]    { --primary:#dc3545; --accent:#b02a37; --primary-rgb:220,53,69;  --accent-rgb:176,42,55; }
[data-accent="orange"] { --primary:#fd7e14; --accent:#e8590c; --primary-rgb:253,126,20; --accent-rgb:232,89,12; }
[data-accent="cyan"]   { --primary:#0dcaf0; --accent:#0aa2c0; --primary-rgb:13,202,240; --accent-rgb:10,162,192; }
[data-accent="pink"]   { --primary:#d63384; --accent:#c2185b; --primary-rgb:214,51,132; --accent-rgb:194,24,91; }
[data-accent="indigo"] { --primary:#6610f2; --accent:#520dc2; --primary-rgb:102,16,242; --accent-rgb:82,13,194; }
[data-accent="teal"]   { --primary:#20c997; --accent:#157f60; --primary-rgb:32,201,151; --accent-rgb:21,127,96; }

[data-theme="light"] {
    --overlay: 0, 0, 0;
    --bg-start: #f0f2f5;
    --bg-mid: #e2e6ed;
    --bg-end: #d1d6df;
    --text: #1a1a2e;
    --text-secondary: #6b7280;
    --brand-grad: linear-gradient(135deg, #1a1a2e 60%, rgba(26,26,46,0.6));
    --nav-bg: rgba(255, 255, 255, 0.75);
    --loading-bg: rgba(255, 255, 255, 0.88);
    --toast-bg: rgba(0, 0, 0, 0.08);
    --spinner-bg: rgba(0, 0, 0, 0.08);
    --border: rgba(0, 0, 0, 0.15);
    --input-bg: rgba(0, 0, 0, 0.04);
    --text-muted: rgba(0, 0, 0, 0.55);
    --card: #ffffff;
    /* 浅色主题：光晕明显调淡，避免抢走内容的视觉重心 */
    --orb-primary: 0.15;
    --orb-accent: 0.12;
    --orb-violet: 0.10;
    --orb-cyan: 0.08;
}

/* =================================================================
 *  Bootstrap 5 主题定制
 *  将 Bootstrap 默认的蓝色主色映射为可切换的界面配色，并适配深 / 浅色。
 * ================================================================= */
:root {
    --bs-primary: var(--primary);
    --bs-primary-rgb: var(--primary-rgb);
    --bs-link-color: var(--primary);
    --bs-link-color-rgb: var(--primary-rgb);
    --bs-link-hover-color: var(--accent);
    --bs-link-hover-color-rgb: var(--accent-rgb);
    --bs-body-font-family: 'Inter', -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif;
    --bs-body-color: #e8e8f0;
    --bs-body-bg: transparent;
    --bs-secondary-color: #a0a0b8;
    --bs-border-color: rgba(var(--overlay), 0.14);
    --bs-border-radius: 10px;
    --bs-border-radius-sm: 8px;
    --bs-border-radius-lg: 12px;
    --bs-btn-font-weight: 600;
    --bs-btn-border-radius: 10px;
    --bs-btn-border-radius-sm: 8px;
    --bs-btn-border-radius-lg: 12px;
}

[data-theme="light"] {
    --bs-body-color: #1a1a2e;
    --bs-secondary-color: #6b7280;
    --bs-border-color: rgba(0, 0, 0, 0.12);
}

* { margin: 0; padding: 0; box-sizing: border-box; }

/* Bootstrap Reboot 会为 p/ul/ol/标题 加默认外边距，与本项目紧凑排版冲突，恢复为紧凑 */
main p, main ul, main ol,
main h1, main h2, main h3, main h4, main h5, main h6 {
    margin-top: 0;
    margin-bottom: 0;
}

html { scroll-behavior: smooth; }

body {
    font-family: 'Inter', -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif;
    background: linear-gradient(135deg, var(--bg-start), var(--bg-mid), var(--bg-end));
    color: var(--text);
    min-height: 100vh;
    line-height: 1.6;
    transition: background 0.4s, color 0.4s;
}

/* =================================================================
 *  背景特效层
 *  自下而上：body 渐变底色 → .bg-scene 漂浮色斑 → #bgCanvas 粒子网络。
 *  色斑颜色引用 --primary-rgb / --accent-rgb，自动跟随界面配色方案；
 *  深浅主题下强度由 --orb-* 变量分别控制。
 * ================================================================= */
.bg-scene {
    position: fixed;
    inset: 0;
    z-index: 0;
    overflow: hidden;
    pointer-events: none;
}

.orb {
    position: absolute;
    border-radius: 50%;
    filter: blur(80px);
    -webkit-filter: blur(80px);
    will-change: transform;
}

.orb-1 {
    width: 62vmax; height: 62vmax;
    top: -30vmax; left: -26vmax;
    background: radial-gradient(circle at 35% 40%,
        rgba(var(--primary-rgb), var(--orb-primary)) 0%,
        rgba(var(--primary-rgb), 0) 60%);
    animation: orbFloat1 40s ease-in-out infinite alternate;
}

.orb-2 {
    width: 56vmax; height: 56vmax;
    bottom: -28vmax; right: -24vmax;
    background: radial-gradient(circle at 60% 60%,
        rgba(var(--accent-rgb), var(--orb-accent)) 0%,
        rgba(var(--accent-rgb), 0) 60%);
    animation: orbFloat2 52s ease-in-out infinite alternate;
}

.orb-3 {
    width: 44vmax; height: 44vmax;
    top: -16vmax; right: -12vmax;
    background: radial-gradient(circle at 50% 45%,
        rgba(139, 92, 246, var(--orb-violet)) 0%,
        rgba(139, 92, 246, 0) 62%);
    animation: orbFloat3 46s ease-in-out infinite alternate;
}

.orb-4 {
    width: 34vmax; height: 34vmax;
    bottom: -14vmax; left: 16%;
    background: radial-gradient(circle at 55% 45%,
        rgba(34, 211, 238, var(--orb-cyan)) 0%,
        rgba(34, 211, 238, 0) 64%);
    animation: orbFloat4 58s ease-in-out infinite alternate;
}

@keyframes orbFloat1 {
    0%   { transform: translate(0, 0) scale(1); }
    50%  { transform: translate(10vmax, 22vmax) scale(1.16); }
    100% { transform: translate(20vmax, 8vmax) scale(0.94); }
}
@keyframes orbFloat2 {
    0%   { transform: translate(0, 0) scale(1); }
    50%  { transform: translate(-12vmax, -18vmax) scale(1.2); }
    100% { transform: translate(-22vmax, -6vmax) scale(0.9); }
}
@keyframes orbFloat3 {
    0%   { transform: translate(0, 0) scale(1); }
    50%  { transform: translate(-14vmax, 16vmax) scale(1.1); }
    100% { transform: translate(-6vmax, 26vmax) scale(0.95); }
}
@keyframes orbFloat4 {
    0%   { transform: translate(0, 0) scale(1); }
    50%  { transform: translate(18vmax, -12vmax) scale(1.14); }
    100% { transform: translate(26vmax, 6vmax) scale(0.92); }
}

#bgCanvas {
    position: fixed;
    inset: 0;
    width: 100%;
    height: 100%;
    z-index: 0;
    pointer-events: none;
    opacity: 0.65;
}

/* 浅色背景本身偏亮，粒子 / 光晕需要更强一些才能看清 */
[data-theme="light"] #bgCanvas {
    opacity: 0.9;
}

/* 系统开启「减少动态效果」时，色斑静止、粒子只渲染一帧（JS 侧处理） */
@media (prefers-reduced-motion: reduce) {
    .orb { animation: none; }
}

/* navbar */
.navbar {
    display: block;
    padding: 0;
    position: sticky;
    top: 0;
    z-index: 100;
    background: var(--nav-bg);
    backdrop-filter: blur(20px);
    -webkit-backdrop-filter: blur(20px);
    border-bottom: 1px solid rgba(var(--overlay), 0.06);
    transition: background 0.4s;
}

.nav-inner {
    max-width: 960px;
    margin: 0 auto;
    padding: 0 16px;
}

@media (min-width: 1200px) {
    .nav-inner { max-width: 1100px; }
}

/* ---- brand row ---- */
.nav-brand-row {
    display: flex;
    align-items: center;
    padding: 14px 20px 10px;
    position: relative;
}

.nav-brand {
    display: flex;
    align-items: center;
    gap: 10px;
    text-decoration: none;
}

.nav-brand svg {
    flex-shrink: 0;
}

.nav-brand span {
    font-size: 18px;
    font-weight: 700;
    letter-spacing: -0.3px;
    display: inline-block;
    position: relative;
    background: var(--brand-grad);
    -webkit-background-clip: text;
    -webkit-text-fill-color: transparent;
    background-clip: text;
}

/* =================================================================
 *  网站名字的「反色光斑」效果 —— 复刻 DeepSeek 官网「探索未至之境」
 *  鼠标放到名字上时，一个圆形白色光斑跟随鼠标扫过文字，
 *  光斑内的文字反色（暗色下白底深字，亮色下深底白字）。
 *  通过 JS 直接更新内联 clip-path / left / top，rAF 缓动跟随。
 * ================================================================= */
:root { --spot-bg: #ffffff; --spot-text: #101024; }
[data-theme="light"] { --spot-bg: #101024; --spot-text: #ffffff; }

.nav-brand .brand-spot {
    position: absolute;
    inset: 0;
    opacity: 0;
    transition: opacity 0.25s ease;
    pointer-events: none;
}

.nav-brand:hover .brand-spot { opacity: 1; }

/* 反色圆斑背景 */
.nav-brand .brand-spot-dot {
    position: absolute;
    left: 0;
    top: 0;
    width: 40px;
    height: 40px;
    transform: translate(-50%, -50%);
    border-radius: 50%;
    background: var(--spot-bg);
    box-shadow: 0 2px 18px rgba(0, 0, 0, 0.35);
}

/* 圆斑内的反色文字（圆形裁剪，圆心跟随鼠标） */
.nav-brand .brand-spot-text {
    position: absolute;
    inset: 0;
    background: var(--spot-text);
    -webkit-background-clip: text;
    background-clip: text;
    -webkit-text-fill-color: transparent;
    -webkit-clip-path: circle(20px at 50% 50%);
    clip-path: circle(20px at 50% 50%);
}

.theme-btn {
    display: flex;
    align-items: center;
    justify-content: center;
    width: 34px;
    height: 34px;
    background: none;
    border: none;
    border-radius: 50%;
    color: var(--text-secondary);
    cursor: pointer;
    transition: all 0.25s;
    flex-shrink: 0;
}

.theme-btn:hover {
    color: var(--text);
    background: rgba(var(--overlay), 0.06);
}

.theme-btn .sun { display: none; }
.theme-btn .moon { display: block; }
[data-theme="light"] .theme-btn .sun { display: block; }
[data-theme="light"] .theme-btn .moon { display: none; }

/* ---- 导航右侧操作（留言板入口 + 配色选择 + 主题切换） ---- */
.nav-actions {
    margin-left: auto;
    display: flex;
    align-items: center;
    gap: 2px;
    flex-shrink: 0;
}

.nav-board-link {
    display: flex;
    align-items: center;
    gap: 6px;
    height: 32px;
    padding: 0 12px;
    margin-right: 4px;
    border-radius: 999px;
    color: var(--text-secondary);
    font-size: 13px;
    font-weight: 600;
    text-decoration: none;
    white-space: nowrap;
    transition: all 0.25s;
}

.nav-board-link:hover {
    color: var(--primary);
    background: rgba(var(--primary-rgb), 0.1);
    text-decoration: none;
}

.nav-board-link.active {
    color: var(--primary);
    background: rgba(var(--primary-rgb), 0.12);
}

.nav-board-link svg { flex-shrink: 0; }

@media (max-width: 620px) {
    .nav-board-link { padding: 0 8px; margin-right: 0; }
    .nav-board-link span { display: none; }
    .nav-board-link { width: 32px; justify-content: center; }
}

/* ---- 配色选择面板 ---- */
.accent-panel {
    position: absolute;
    top: calc(100% - 4px);
    right: 20px;
    z-index: 600;
    width: 236px;
    padding: 14px 16px;
    background: rgba(28, 28, 50, 0.95);
    backdrop-filter: blur(20px) saturate(160%);
    -webkit-backdrop-filter: blur(20px) saturate(160%);
    border: 1px solid rgba(var(--primary-rgb), 0.3);
    border-radius: 14px;
    box-shadow: 0 12px 40px rgba(0, 0, 0, 0.45);
    animation: fadeSlideUp 0.18s ease;
}

[data-theme="light"] .accent-panel {
    background: rgba(255, 255, 255, 0.98);
    border-color: rgba(var(--primary-rgb), 0.3);
    box-shadow: 0 12px 40px rgba(0, 0, 0, 0.14);
}

.accent-panel[hidden] { display: none; }

.accent-panel-title {
    font-size: 12px;
    font-weight: 600;
    color: var(--text-secondary);
    margin-bottom: 10px;
    text-align: center;
}

.accent-list {
    display: grid;
    grid-template-columns: repeat(5, 1fr);
    gap: 10px 6px;
}

.accent-swatch {
    display: flex;
    flex-direction: column;
    align-items: center;
    gap: 6px;
    padding: 0;
    background: none;
    border: none;
    cursor: pointer;
    color: var(--text-secondary);
    font-size: 11px;
    font-family: inherit;
    line-height: 1;
}

.accent-swatch .dot {
    width: 26px;
    height: 26px;
    border-radius: 50%;
    border: 2px solid transparent;
    box-shadow: 0 2px 8px rgba(0, 0, 0, 0.25);
    transition: transform 0.15s ease, border-color 0.15s ease;
}

.accent-swatch:hover .dot {
    transform: scale(1.15);
}

.accent-swatch.active .dot {
    border-color: var(--text);
}

.accent-swatch.active {
    color: var(--text);
    font-weight: 600;
}

/* ---- links row ---- */
.nav-links-row {
    padding: 0 20px 14px;
}

.nav-links {
    list-style: none;
    display: flex;
    align-items: center;
    gap: 2px;
}

.nav-link {
    position: relative;
    display: block;
    padding: 6px 14px 8px;
    font-size: 13px;
    font-weight: 500;
    color: var(--text-secondary);
    text-decoration: none;
    transition: color 0.2s;
}

.nav-link:hover {
    color: var(--text);
}

.nav-link::after {
    content: '';
    position: absolute;
    bottom: 0;
    left: 14px;
    right: 14px;
    height: 2px;
    background: transparent;
    border-radius: 1px;
    transition: background 0.25s;
}

.nav-link.active {
    color: var(--primary);
    font-weight: 600;
}

.nav-link.active::after {
    background: var(--primary);
}

/* ---- 二级菜单：一级分组 + 浮层 ---- */
.nav-group {
    position: relative;
}

.nav-group-btn {
    /* <button> 默认不继承字体，这里显式对齐 .nav-link 的排版 */
    font-family: inherit;
    background: none;
    border: none;
    cursor: pointer;
    display: flex;
    align-items: center;
    gap: 4px;
    white-space: nowrap;
}

.nav-caret {
    flex-shrink: 0;
    opacity: 0.7;
    transition: transform 0.2s ease;
}

.nav-group:hover .nav-caret,
.nav-group:focus-within .nav-caret,
.nav-group.open .nav-caret {
    transform: rotate(180deg);
}

.nav-dropdown {
    position: absolute;
    top: 100%;
    left: 0;
    z-index: 600;
    min-width: 168px;
    display: flex;
    flex-direction: column;
    gap: 2px;
    padding: 6px;
    background: rgba(28, 28, 50, 0.96);
    backdrop-filter: blur(20px) saturate(160%);
    -webkit-backdrop-filter: blur(20px) saturate(160%);
    border: 1px solid rgba(var(--overlay), 0.12);
    border-radius: 12px;
    box-shadow: 0 12px 36px rgba(0, 0, 0, 0.4);
    opacity: 0;
    visibility: hidden;
    transform: translateY(-6px);
    /* 隐藏态不参与过渡 —— CSS 过渡只看「变化后」那条规则的 transition，
       所以过渡只写在展开态里，「出现有动画、消失是瞬时的」。
       若消失也做淡出，鼠标在一级菜单上左右横滑时，上一个浮层还没淡完、
       下一个已经淡入，两个浮层横向相邻且有重叠，就会同屏看到两个。 */
    transition: none;
}

[data-theme="light"] .nav-dropdown {
    background: rgba(255, 255, 255, 0.98);
    border-color: rgba(0, 0, 0, 0.1);
    box-shadow: 0 12px 36px rgba(0, 0, 0, 0.14);
}

/* 浮层展开只用两个条件，勿再引入 :focus-within ——
   点过某个分组标题后焦点一直留在它的按钮上，:focus-within 会让该浮层常驻，
   鼠标再移到另一个分组，:hover 又开一个，就会同时显示两个二级菜单。
   键盘改用「Enter 展开」（.open，由 JS 保证同一时刻只有一个）。 */
.nav-group:hover .nav-dropdown,
.nav-group.open .nav-dropdown {
    opacity: 1;
    visibility: visible;
    transform: translateY(0);
    transition: opacity 0.16s ease, transform 0.16s ease;
}

/* 选中某个二级项后立刻收起浮层：桌面端点完菜单鼠标还停在分组上，
   :hover / :focus-within 会把浮层一直撑着，必须用这个类显式压掉；
   鼠标移出分组时由 JS 移除，之后照常悬停展开。
   （与上面的展开规则同为 3 个 class，靠源码顺序取胜，勿上移） */
.nav-group.is-collapsed .nav-dropdown {
    opacity: 0;
    visibility: hidden;
    transform: translateY(-6px);
    transition: none;
}

.nav-drop-link {
    display: block;
    padding: 8px 12px;
    border-radius: 8px;
    font-size: 13px;
    font-weight: 500;
    color: var(--text-secondary);
    text-decoration: none;
    white-space: nowrap;
    transition: background 0.18s, color 0.18s;
}

.nav-drop-link:hover {
    color: var(--text);
    background: rgba(var(--overlay), 0.08);
    text-decoration: none;
}

.nav-drop-link.active {
    color: var(--primary);
    font-weight: 600;
    background: rgba(var(--primary-rgb), 0.12);
}

.nav-toggle {
    display: none;
    background: none;
    border: none;
    color: var(--text-secondary);
    cursor: pointer;
    padding: 6px;
    border-radius: 8px;
}

.nav-toggle:hover {
    color: var(--text);
    background: rgba(var(--overlay), 0.06);
}

/* main */
main {
    position: relative;
    z-index: 1;
    max-width: 960px;
    margin: 0 auto;
    padding: 16px 16px 48px;
}

@media (min-width: 1200px) {
    main { max-width: 1100px; }
}

.tool-card {
    background: rgba(var(--overlay), 0.06);
    backdrop-filter: blur(20px);
    -webkit-backdrop-filter: blur(20px);
    border: 1px solid rgba(var(--overlay), 0.10);
    border-radius: var(--radius);
    padding: 28px;
    box-shadow: 0 8px 32px rgba(0, 0, 0, 0.2);
    transition: box-shadow 0.3s, background 0.4s;
}

[data-theme="light"] .tool-card {
    background: rgba(255, 255, 255, 0.7);
    box-shadow: 0 2px 16px rgba(0, 0, 0, 0.06);
}

.tool-card:hover { box-shadow: 0 12px 48px rgba(0, 0, 0, 0.25); }
[data-theme="light"] .tool-card:hover { box-shadow: 0 4px 24px rgba(0, 0, 0, 0.10); }

.card-header {
    display: flex;
    align-items: center;
    gap: 14px;
    margin-bottom: 24px;
    padding: 0;
    background: transparent;
    border: 0;
}

.card-icon {
    width: 48px;
    height: 48px;
    display: flex;
    align-items: center;
    justify-content: center;
    background: rgba(var(--primary-rgb), 0.15);
    border-radius: 12px;
    color: var(--primary);
    flex-shrink: 0;
}

.card-header h2 {
    font-size: 20px;
    font-weight: 700;
}

.card-header .desc {
    font-size: 13px;
    color: var(--text-secondary);
    margin-top: 1px;
}

/* drop zone */
.drop-zone {
    border: 2px dashed rgba(var(--overlay), 0.18);
    border-radius: var(--radius-sm);
    padding: 48px 20px;
    text-align: center;
    cursor: pointer;
    transition: all 0.3s ease;
}

.drop-zone:hover,
.drop-zone.drag-over {
    border-color: var(--primary);
    background: rgba(var(--primary-rgb), 0.08);
    transform: translateY(-1px);
}

.drop-zone-icon {
    color: var(--text-secondary);
    margin-bottom: 16px;
    transition: color 0.3s, transform 0.3s;
}

.drop-zone:hover .drop-zone-icon,
.drop-zone.drag-over .drop-zone-icon {
    color: var(--primary);
    transform: scale(1.05);
}

.drop-zone-title {
    font-size: 16px;
    font-weight: 500;
    color: var(--text);
}

.drop-zone-title .link {
    color: var(--primary);
    text-decoration: underline;
    text-underline-offset: 3px;
}

.drop-zone-hint {
    font-size: 12px;
    color: var(--text-secondary);
    margin-top: 6px;
}

/* toolbar */
.toolbar {
    display: flex;
    align-items: center;
    flex-wrap: wrap;
    gap: 12px;
    margin-top: 20px;
    padding-top: 16px;
    border-top: 1px solid rgba(var(--overlay), 0.08);
    animation: fadeSlideUp 0.35s ease;
}

.file-count {
    font-size: 13px;
    color: var(--text-secondary);
    flex: 1;
}

.ocr-engine-select {
    display: flex;
    align-items: center;
    gap: 8px;
    font-size: 13px;
    color: var(--text-secondary);
}

.ocr-engine-select label {
    white-space: nowrap;
}

/* ---- custom select ---- */
.custom-select {
    position: relative;
    min-width: 300px;
    width: 300px;
}

.custom-select-trigger {
    display: flex;
    align-items: center;
    justify-content: space-between;
    gap: 12px;
    width: 100%;
    padding: 9px 14px;
    border: 1px solid rgba(var(--overlay), 0.14);
    border-radius: 12px;
    background: linear-gradient(180deg, rgba(var(--overlay), 0.06), rgba(var(--overlay), 0.03));
    color: var(--text);
    font-size: 13.5px;
    font-family: inherit;
    font-weight: 500;
    cursor: pointer;
    outline: none;
    transition: border-color 0.2s, background 0.2s, box-shadow 0.2s, transform 0.15s;
    box-shadow: 0 1px 2px rgba(0, 0, 0, 0.04);
}

.custom-select-trigger:hover {
    border-color: rgba(var(--primary-rgb), 0.45);
    background: linear-gradient(180deg, rgba(var(--overlay), 0.10), rgba(var(--overlay), 0.05));
}

.custom-select-trigger:focus,
.custom-select.open .custom-select-trigger {
    border-color: var(--primary);
    box-shadow: 0 0 0 3px rgba(var(--primary-rgb), 0.18);
}

.custom-select-trigger:active {
    transform: scale(0.98);
}

.custom-select-value {
    flex: 1;
    text-align: left;
    overflow: hidden;
    text-overflow: ellipsis;
    white-space: nowrap;
}

.custom-select-arrow {
    color: var(--text-secondary);
    transition: transform 0.25s ease, color 0.2s;
    flex-shrink: 0;
}

.custom-select.open .custom-select-arrow {
    transform: rotate(180deg);
    color: var(--primary);
}

.custom-select-options {
    position: absolute;
    top: calc(100% + 8px);
    left: 0;
    right: 0;
    margin: 0;
    padding: 8px;
    list-style: none;
    background: rgba(28, 28, 50, 0.92);
    backdrop-filter: blur(20px) saturate(160%);
    -webkit-backdrop-filter: blur(20px) saturate(160%);
    border: 1px solid rgba(var(--primary-rgb), 0.30);
    border-radius: 14px;
    box-shadow: 0 12px 40px rgba(0, 0, 0, 0.45),
                0 0 0 1px rgba(255, 255, 255, 0.05) inset;
    z-index: 500;
    opacity: 0;
    transform: translateY(-6px) scale(0.97);
    transform-origin: top center;
    pointer-events: none;
    transition: opacity 0.18s ease, transform 0.18s ease;
    max-height: 380px;
    overflow-y: auto;
    width: max-content;
    min-width: 100%;
    max-width: 420px;
}

[data-theme="light"] .custom-select-options {
    background: rgba(255, 255, 255, 0.96);
    border-color: rgba(var(--primary-rgb), 0.35);
    box-shadow: 0 12px 40px rgba(0, 0, 0, 0.12),
                0 0 0 1px rgba(0, 0, 0, 0.04) inset;
}

.custom-select.open .custom-select-options {
    opacity: 1;
    transform: translateY(0) scale(1);
    pointer-events: auto;
}

.custom-select-option {
    display: flex;
    align-items: center;
    gap: 12px;
    padding: 10px 12px;
    border-radius: 10px;
    cursor: pointer;
    transition: background 0.15s, color 0.15s, transform 0.15s;
    color: var(--text);
    white-space: nowrap;
}

.custom-select-option:hover,
.custom-select-option.active {
    background: rgba(var(--primary-rgb), 0.18);
}

.custom-select-option:active {
    transform: scale(0.98);
}

.custom-select-option[aria-disabled="true"] {
    opacity: 0.4;
    cursor: not-allowed;
}

.custom-select-option[aria-disabled="true"]:hover {
    background: transparent;
}

.custom-select-option .option-icon {
    display: inline-flex;
    align-items: center;
    justify-content: center;
    width: 38px;
    height: 38px;
    border-radius: 10px;
    background: linear-gradient(135deg, var(--primary), var(--accent));
    color: #fff;
    font-size: 12px;
    font-weight: 700;
    letter-spacing: 0.3px;
    flex-shrink: 0;
    box-shadow: 0 2px 8px rgba(var(--primary-rgb), 0.30);
    white-space: nowrap;
    overflow: hidden;
    padding: 0 4px;
}

.custom-select-option .option-text {
    display: flex;
    flex-direction: column;
    gap: 2px;
    min-width: 0;
    flex: 1;
}

.custom-select-option .option-title {
    font-size: 13.5px;
    font-weight: 600;
    line-height: 1.35;
    white-space: nowrap;
}

.custom-select-option .option-desc {
    font-size: 11.5px;
    color: var(--text-secondary);
    line-height: 1.4;
    white-space: nowrap;
}

.custom-select-option .option-check {
    color: var(--primary);
    opacity: 0;
    transition: opacity 0.15s;
    flex-shrink: 0;
    margin-left: 4px;
}

.custom-select-option.selected .option-check {
    opacity: 1;
}

.custom-select-option.selected {
    background: rgba(var(--primary-rgb), 0.12);
}

/* scrollbar */
.custom-select-options::-webkit-scrollbar {
    width: 6px;
}

.custom-select-options::-webkit-scrollbar-thumb {
    background: rgba(var(--overlay), 0.20);
    border-radius: 3px;
}

.custom-select-options::-webkit-scrollbar-thumb:hover {
    background: rgba(var(--overlay), 0.35);
}

/* 靠右：文件计数不再抢占剩余空间时，把操作按钮推到最右 */
.toolbar-right {
    flex-shrink: 0;
    margin-left: auto;
}

/* 压缩参数分组：占满整行，与「添加更多」按钮左对齐 */
.compress-settings {
    order: 10;
    flex: 0 0 100%;
    width: 100%;
    display: flex;
    flex-direction: column;
    align-items: stretch;
    gap: 12px;
    min-width: 0;
    margin-top: 12px;
    padding-top: 12px;
    border-top: 1px dashed rgba(var(--overlay), 0.14);
}

/* 同排的空间改由参数区吸收，按钮仍靠右 */
.toolbar .file-count-auto {
    flex: 0 0 auto;
    white-space: nowrap;
    color: var(--text-secondary);
    font-size: 13px;
    padding: 4px 8px;
    border-radius: 6px;
    background: rgba(var(--primary-rgb), 0.08);
    align-self: center;
}

/* compress control —— 网格：标签 | 预设 | 输入带单位，第二行说明占满整行 */
.compress-control {
    display: grid;
    grid-template-columns: 88px auto auto 1fr;
    column-gap: 14px;
    row-gap: 2px;
    align-items: center;
    font-size: 13px;
}

/* 标签左对齐，与「添加更多」按钮同一条左基准线 */
.compress-control .compress-label {
    color: var(--text);
    font-weight: 600;
    font-size: 13px;
    text-align: left;
    white-space: nowrap;
}

.compress-control .compress-desc {
    grid-column: 1 / -1;
    margin: 4px 0 0;
    font-size: 11.5px;
    line-height: 1.6;
    color: var(--text-secondary);
    opacity: 0.85;
}

/* 压缩比例快捷按钮组 */
.compress-presets {
    display: inline-flex;
    flex-wrap: wrap;
    gap: 6px;
    min-width: 280px; /* 让两行输入框落在同一水平位置 */
}

.compress-chip {
    padding: 5px 11px;
    border: 1px solid rgba(var(--overlay), 0.16);
    border-radius: 999px;
    background: rgba(var(--overlay), 0.03);
    color: var(--text-secondary);
    font-size: 12.5px;
    font-family: inherit;
    font-weight: 600;
    cursor: pointer;
    outline: none;
    transition: all 0.18s ease;
    white-space: nowrap;
    line-height: 1.2;
}

.compress-chip:hover {
    border-color: var(--primary);
    color: var(--primary);
    background: rgba(var(--primary-rgb), 0.08);
}

.compress-chip.active {
    border-color: var(--primary);
    background: var(--primary);
    color: #fff;
    box-shadow: 0 2px 8px rgba(var(--primary-rgb), 0.35);
}

.compress-chip:active {
    transform: scale(0.96);
}

/* 输入框 + 单位的组合，外观更紧凑 */
.compress-input-group {
    display: inline-flex;
    align-items: center;
    gap: 4px;
    padding: 0 8px 0 4px;
    border: 1px solid rgba(var(--overlay), 0.14);
    border-radius: 8px;
    background: rgba(var(--overlay), 0.04);
    transition: border-color 0.2s, box-shadow 0.2s, background 0.2s;
}

.compress-input-group:focus-within {
    border-color: var(--primary);
    background: #fff;
    box-shadow: 0 0 0 3px rgba(var(--primary-rgb), 0.18);
}

.compress-input-group input {
    width: 52px;
    padding: 6px 0;
    border: none;
    background: transparent;
    color: var(--text);
    font-size: 13.5px;
    font-family: inherit;
    font-weight: 600;
    text-align: center;
    outline: none;
    -moz-appearance: textfield;
    appearance: textfield;
}

.compress-input-group input::-webkit-outer-spin-button,
.compress-input-group input::-webkit-inner-spin-button {
    -webkit-appearance: none;
    margin: 0;
}

.compress-input-group .compress-input-suffix {
    color: var(--text-secondary);
    font-size: 12.5px;
    font-weight: 600;
    user-select: none;
}

/* 通用 inline 提示文字（被擦除/试题工具的输入框旁引用） */
.compress-unit {
    white-space: nowrap;
    font-size: 12px;
    color: var(--text-secondary);
    opacity: 0.85;
}

@media (max-width: 640px) {
    .compress-control {
        grid-template-columns: 1fr auto;
    }
    .compress-control .compress-label {
        grid-column: 1 / -1;
        text-align: left;
    }
    .compress-control .compress-desc {
        grid-column: 1 / -1;
    }
    /* 窄屏取消最小宽度，避免预设按钮撑破容器 */
    .compress-presets { min-width: 0; }
}

/* buttons —— 基于 Bootstrap 按钮组件，定制为主题配色 */
.btn {
    --bs-btn-padding-y: 0.625rem;
    --bs-btn-padding-x: 1.375rem;
    --bs-btn-font-size: 0.875rem;
    --bs-btn-line-height: 1.6;
    display: inline-flex;
    align-items: center;
    justify-content: center;
    gap: 0.5rem;
    transition: color 0.2s ease, background-color 0.2s ease, border-color 0.2s ease,
        box-shadow 0.2s ease, transform 0.2s ease;
}

.btn:active { transform: scale(0.96); }

/* 主按钮：跟随当前配色方案（--primary → --accent 渐变） */
.btn-primary {
    --bs-btn-color: #fff;
    --bs-btn-bg: var(--primary);
    --bs-btn-border-color: var(--primary);
    --bs-btn-hover-color: #fff;
    --bs-btn-hover-bg: var(--accent);
    --bs-btn-hover-border-color: var(--accent);
    --bs-btn-active-color: #fff;
    --bs-btn-active-bg: var(--accent);
    --bs-btn-active-border-color: var(--accent);
    --bs-btn-disabled-bg: var(--primary);
    --bs-btn-disabled-border-color: var(--primary);
    background-image: linear-gradient(135deg, var(--primary), var(--accent));
    border: none;
    box-shadow: 0 4px 16px rgba(var(--primary-rgb), 0.35);
}

.btn-primary:hover {
    background-image: linear-gradient(135deg,
        color-mix(in srgb, var(--primary) 85%, #fff),
        color-mix(in srgb, var(--accent) 85%, #fff));
    box-shadow: 0 6px 24px rgba(var(--primary-rgb), 0.5);
    transform: translateY(-1px);
}

.btn-primary:focus-visible {
    background-image: linear-gradient(135deg,
        color-mix(in srgb, var(--primary) 85%, #fff),
        color-mix(in srgb, var(--accent) 85%, #fff));
    box-shadow: 0 0 0 0.25rem rgba(var(--primary-rgb), 0.35);
}

/* 描边按钮：Bootstrap 无 .btn-outline（需带色），按 outline-secondary 语义自定义 */
.btn-outline {
    --bs-btn-color: var(--text);
    --bs-btn-bg: rgba(var(--overlay), 0.06);
    --bs-btn-border-color: rgba(var(--overlay), 0.16);
    --bs-btn-hover-color: var(--text);
    --bs-btn-hover-bg: rgba(var(--overlay), 0.10);
    --bs-btn-hover-border-color: rgba(var(--overlay), 0.24);
    --bs-btn-active-color: var(--text);
    --bs-btn-active-bg: rgba(var(--overlay), 0.12);
    --bs-btn-active-border-color: rgba(var(--overlay), 0.28);
}

/* 危险描边按钮（如「删除密钥库」）：在 outline 基础上强调为红色 */
.btn-outline.btn-danger {
    --bs-btn-color: #f87171;
    --bs-btn-border-color: rgba(239, 68, 68, 0.45);
    --bs-btn-hover-color: #fff;
    --bs-btn-hover-bg: #ef4444;
    --bs-btn-hover-border-color: #ef4444;
    --bs-btn-active-color: #fff;
    --bs-btn-active-bg: #dc2626;
    --bs-btn-active-border-color: #dc2626;
}

/* image list */
.image-list {
    list-style: none;
    margin-top: 16px;
    display: flex;
    flex-direction: column;
    gap: 8px;
}

.image-list li {
    display: flex;
    align-items: center;
    gap: 12px;
    background: rgba(var(--overlay), 0.04);
    border: 1px solid rgba(var(--overlay), 0.08);
    border-radius: var(--radius-sm);
    padding: 8px 12px;
    cursor: grab;
    transition: all 0.25s ease;
    user-select: none;
    animation: fadeSlideUp 0.3s ease both;
}

.image-list li:active { cursor: grabbing; }

.image-list li:hover {
    background: rgba(var(--overlay), 0.07);
    border-color: rgba(var(--overlay), 0.14);
}

.image-list li.dragging {
    opacity: 0.3;
    transform: scale(0.97);
}

.image-list li.drag-over-target {
    border-color: var(--primary);
    background: rgba(var(--primary-rgb), 0.10);
    box-shadow: 0 0 0 1px rgba(var(--primary-rgb), 0.3);
    transform: scale(1.02);
}

.drag-handle {
    color: rgba(var(--overlay), 0.25);
    cursor: grab;
    display: flex;
    align-items: center;
    flex-shrink: 0;
}

.image-list li .thumb {
    width: 48px;
    height: 48px;
    object-fit: cover;
    border-radius: 8px;
    flex-shrink: 0;
    background: rgba(var(--overlay), 0.05);
}

.image-list li .file-name {
    flex: 1;
    min-width: 0;
    font-size: 14px;
    font-weight: 500;
    overflow: hidden;
    text-overflow: ellipsis;
    white-space: nowrap;
}

.image-list li .file-size {
    font-size: 12px;
    color: var(--text-secondary);
    white-space: nowrap;
    flex-shrink: 0;
}

.delete-btn {
    background: none;
    border: none;
    color: rgba(var(--overlay), 0.25);
    font-size: 18px;
    cursor: pointer;
    padding: 4px;
    line-height: 1;
    border-radius: 6px;
    transition: all 0.2s;
    flex-shrink: 0;
}

.delete-btn:hover {
    color: #ff6b6b;
    background: rgba(255, 107, 107, 0.12);
}

/* ocr */
.ocr-preview-area {
    margin-top: 20px;
    text-align: center;
    animation: fadeSlideUp 0.35s ease;
}

.ocr-preview-area img {
    max-width: 100%;
    max-height: 360px;
    border-radius: var(--radius-sm);
    object-fit: contain;
    background: rgba(var(--overlay), 0.03);
    cursor: zoom-in;
    transition: transform 0.2s;
}

.ocr-preview-area img:hover {
    transform: scale(1.02);
}

.ocr-preview-area .btn {
    margin-top: 16px;
}

.ocr-result {
    margin-top: 20px;
    animation: fadeSlideUp 0.35s ease;
}

.ocr-result-header {
    display: flex;
    align-items: center;
    justify-content: space-between;
    margin-bottom: 10px;
    font-size: 14px;
    font-weight: 600;
    color: var(--text);
}

.ocr-result-header .btn {
    padding: 6px 14px;
    font-size: 12px;
}

.ocr-result pre {
    background: rgba(var(--overlay), 0.04);
    border: 1px solid rgba(var(--overlay), 0.08);
    border-radius: var(--radius-sm);
    padding: 16px;
    font-size: 14px;
    line-height: 1.8;
    color: var(--text);
    white-space: pre-wrap;
    word-wrap: break-word;
    max-height: 400px;
    overflow-y: auto;
    font-family: 'Inter', -apple-system, BlinkMacSystemFont, 'Segoe UI', monospace;
}

/* tab panels */
.tab-panel {
    display: block;
}

.tab-panel[hidden] {
    display: none;
}

/* empty state */
.empty-state {
    text-align: center;
    padding: 32px 0 8px;
    color: var(--text-secondary);
}

.empty-state p {
    font-size: 14px;
    margin-top: 12px;
}

/* privacy */
.privacy-notice {
    margin-top: 24px;
    padding: 16px;
    background: rgba(var(--overlay), 0.03);
    border: 1px solid rgba(var(--overlay), 0.08);
    border-radius: var(--radius-sm);
    display: flex;
    gap: 12px;
    align-items: flex-start;
}

.privacy-icon {
    color: var(--primary);
    flex-shrink: 0;
    margin-top: 1px;
}

.privacy-notice strong {
    font-size: 13px;
    font-weight: 600;
}

.privacy-notice p {
    font-size: 12.5px;
    color: var(--text-secondary);
    line-height: 1.7;
    margin-top: 2px;
}

.privacy-points {
    margin: 6px 0 0;
    padding-left: 18px;
    list-style: disc;
}
.privacy-points li {
    font-size: 12.5px;
    color: var(--text-secondary);
    line-height: 1.7;
    margin-bottom: 6px;
}
.privacy-points li:last-child { margin-bottom: 0; }
.privacy-points code {
    font-size: 11.5px;
    padding: 1px 5px;
    border-radius: 5px;
    background: rgba(var(--overlay), 0.08);
    color: var(--text);
}

.privacy-notice em {
    font-style: normal;
    font-weight: 600;
    color: #ff6b6b;
}

/* footer */
footer {
    position: relative;
    z-index: 1;
    text-align: center;
    padding: 32px 16px;
    font-size: 12px;
    color: rgba(var(--overlay), 0.25);
    letter-spacing: 0.5px;
}

/* image modal */
.image-modal-overlay {
    position: fixed;
    inset: 0;
    background: rgba(0, 0, 0, 0.85);
    backdrop-filter: blur(8px);
    -webkit-backdrop-filter: blur(8px);
    display: flex;
    align-items: center;
    justify-content: center;
    z-index: 2000;
    cursor: zoom-out;
    animation: fadeIn 0.25s ease;
    padding: 32px;
}

.image-modal-overlay[hidden] {
    display: none !important;
}

.image-modal-content {
    max-width: 95vw;
    max-height: 95vh;
    object-fit: contain;
    border-radius: 8px;
    box-shadow: 0 8px 64px rgba(0,0,0,0.5);
    animation: fadeSlideUp 0.3s ease;
    cursor: default;
}

.image-modal-close {
    position: fixed;
    top: 20px;
    right: 28px;
    font-size: 36px;
    font-weight: 300;
    color: rgba(255,255,255,0.7);
    cursor: pointer;
    transition: color 0.2s;
    line-height: 1;
    z-index: 2001;
}

.image-modal-close:hover {
    color: #fff;
}

/* loading overlay */
.loading-overlay {
    position: fixed;
    inset: 0;
    background: var(--loading-bg);
    backdrop-filter: blur(12px);
    -webkit-backdrop-filter: blur(12px);
    display: flex;
    flex-direction: column;
    align-items: center;
    justify-content: center;
    z-index: 1000;
    animation: fadeIn 0.25s ease;
    transition: background 0.4s;
}

.loading-overlay[hidden] {
    display: none !important;
}

.loading-spinner {
    width: 44px;
    height: 44px;
    border: 3px solid var(--spinner-bg);
    border-top-color: var(--primary);
    border-right-color: var(--accent);
    border-radius: 50%;
    animation: spin 0.8s linear infinite;
    margin-bottom: 20px;
}

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

.loading-overlay p {
    font-size: 15px;
    color: rgba(var(--overlay), 0.7);
    font-weight: 500;
}

/* toast */
.toast {
    position: fixed;
    bottom: 32px;
    left: 50%;
    width: auto;
    max-width: 90vw;
    transform: translateX(-50%) translateY(80px);
    background: var(--toast-bg);
    backdrop-filter: blur(12px);
    -webkit-backdrop-filter: blur(12px);
    border: 1px solid rgba(var(--overlay), 0.12);
    border-radius: var(--radius-sm);
    padding: 12px 24px;
    font-size: 14px;
    font-weight: 500;
    color: var(--text);
    box-shadow: 0 8px 32px rgba(0, 0, 0, 0.25);
    z-index: 1001;
    opacity: 0;
    transition: all 0.4s ease;
    pointer-events: none;
    white-space: nowrap;
}

.toast.show {
    opacity: 1;
    transform: translateX(-50%) translateY(0);
}

.toast.error {
    border-color: rgba(255, 107, 107, 0.3);
    color: #ff6b6b;
}

/* animations */
@keyframes fadeIn {
    from { opacity: 0; }
    to { opacity: 1; }
}

@keyframes fadeSlideUp {
    from { opacity: 0; transform: translateY(12px); }
    to { opacity: 1; transform: translateY(0); }
}

/* responsive */
@media (max-width: 640px) {
    .nav-links-row {
        display: flex;
        align-items: center;
        flex-wrap: wrap;
    }

    .nav-links {
        display: none;
        width: 100%;
        flex-direction: column;
        padding: 4px 0 0;
    }

    .nav-links.open { display: flex; }

    .nav-link {
        width: 100%;
        padding: 10px 14px;
        border-radius: 8px;
    }

    .nav-link::after { display: none; }

    .nav-link.active {
        background: rgba(var(--primary-rgb), 0.12);
        color: var(--primary);
    }

    /* 二级菜单：浮层退化为手风琴，只有展开分组才显示二级项 */
    .nav-group {
        position: static;
        width: 100%;
    }

    .nav-group-btn {
        width: 100%;
        justify-content: space-between;
    }

    .nav-dropdown {
        position: static;
        min-width: 0;
        display: none;
        padding: 2px 0 4px 12px;
        background: transparent;
        border: none;
        border-radius: 0;
        box-shadow: none;
        opacity: 1;
        visibility: visible;
        transform: none;
        backdrop-filter: none;
        -webkit-backdrop-filter: none;
    }

    .nav-group.open .nav-dropdown { display: flex; }

    .nav-drop-link { padding: 9px 14px; }

    .nav-toggle {
        display: block;
    }
}

/* deepseek ai */
.deepseek-section {
    margin-top: 24px;
    padding-top: 20px;
    border-top: 1px solid rgba(var(--overlay), 0.08);
    animation: fadeSlideUp 0.35s ease;
}

.tencent-section {
    margin-top: 12px;
    padding-top: 12px;
    border-top: none;
}

.deepseek-section .card-header {
    margin-bottom: 16px;
}

.deepseek-config {
    margin-bottom: 12px;
}

.deepseek-config-row {
    display: flex;
    align-items: center;
    gap: 8px;
    flex-wrap: wrap;
}

.deepseek-config-row label {
    font-size: 13px;
    color: var(--text-secondary);
    white-space: nowrap;
}

.deepseek-input-field {
    flex: 1;
    min-width: 200px;
    padding: 8px 12px;
    border: 1px solid rgba(var(--overlay), 0.12);
    border-radius: 8px;
    background: rgba(var(--overlay), 0.04);
    color: var(--text);
    font-size: 13px;
    font-family: inherit;
    outline: none;
    transition: border-color 0.2s;
}

.deepseek-input-field:focus {
    border-color: var(--primary);
}

.hint-text {
    font-size: 11px;
    color: var(--text-secondary);
    margin-top: 6px;
    opacity: 0.7;
}

.deepseek-input-row {
    display: flex;
    align-items: center;
    gap: 8px;
    margin-bottom: 12px;
}

.deepseek-input-row .deepseek-input-field {
    flex: 1;
}

.deepseek-status {
    padding: 10px 14px;
    border-radius: var(--radius-sm);
    font-size: 13px;
    margin-bottom: 10px;
    background: rgba(var(--primary-rgb), 0.10);
    border: 1px solid rgba(var(--primary-rgb), 0.15);
    color: var(--text);
}

.deepseek-status.error {
    background: rgba(255, 107, 107, 0.10);
    border-color: rgba(255, 107, 107, 0.20);
    color: #ff6b6b;
}

.deepseek-result {
    margin-top: 12px;
    animation: fadeSlideUp 0.35s ease;
}

.deepseek-result pre {
    background: rgba(var(--overlay), 0.04);
    border: 1px solid rgba(var(--overlay), 0.08);
    border-radius: var(--radius-sm);
    padding: 16px;
    font-size: 13px;
    line-height: 1.6;
    color: var(--text);
    white-space: pre-wrap;
    word-wrap: break-word;
    max-height: 400px;
    overflow-y: auto;
    font-family: 'Inter', -apple-system, BlinkMacSystemFont, 'Segoe UI', monospace;
}

.extract-table {
    width: 100%;
    border-collapse: collapse;
    font-size: 13px;
    border-radius: var(--radius-sm);
    overflow: hidden;
    border: 1px solid rgba(var(--overlay), 0.08);
}

.extract-table th,
.extract-table td {
    text-align: left;
    padding: 10px 14px;
    border-bottom: 1px solid rgba(var(--overlay), 0.06);
    vertical-align: top;
}

.extract-table th {
    background: rgba(var(--overlay), 0.04);
    font-weight: 600;
    color: var(--text);
    white-space: nowrap;
}

.extract-table td:first-child {
    width: 30%;
    min-width: 120px;
    color: var(--text-secondary);
    font-weight: 500;
    word-break: break-all;
}

.extract-table td:last-child {
    color: var(--text);
    word-break: break-all;
}

.extract-table tbody tr:last-child td {
    border-bottom: none;
}

.extract-table tbody tr:hover td {
    background: rgba(var(--overlay), 0.03);
}

@media (max-width: 520px) {
    .tool-card { padding: 20px 16px; border-radius: 12px; }
    .drop-zone { padding: 32px 16px; }
    .toolbar { flex-wrap: wrap; }
    .toolbar .file-count { order: 3; width: 100%; text-align: center; }
    .ocr-engine-select { order: 2; width: 100%; }
    .btn { padding: 10px 18px; font-size: 13px; }
    .deepseek-input-row { flex-wrap: wrap; }
    .deepseek-input-row .btn { width: 100%; }
    .deepseek-config-row { flex-direction: column; align-items: stretch; }
}

/* =================================================================
 *  文件中转站 / 共享粘贴板
 * ================================================================= */
.token-gate {
    display: flex;
    flex-direction: column;
    gap: 12px;
    max-width: 420px;
    margin: 24px 0;
    padding: 24px;
    background: rgba(var(--overlay), 0.04);
    border: 1px solid var(--border, rgba(255, 255, 255, 0.1));
    border-radius: 14px;
}

.token-gate label {
    font-size: 14px;
    font-weight: 600;
    color: var(--text, #fff);
}

.token-gate input {
    width: 100%;
    padding: 12px 14px;
    font-size: 15px;
    border-radius: 10px;
    border: 1px solid var(--border, rgba(255, 255, 255, 0.15));
    background: var(--input-bg, rgba(255, 255, 255, 0.06));
    color: var(--text, #fff);
    outline: none;
    transition: border-color 0.2s, box-shadow 0.2s;
}

.token-gate input:focus {
    border-color: var(--primary);
    box-shadow: 0 0 0 3px rgba(var(--primary-rgb), 0.25);
}

.form-group {
    margin-top: 18px;
}

.form-group > label,
.form-label {
    display: block;
    font-size: 14px;
    font-weight: 600;
    margin-bottom: 8px;
    color: var(--text, #fff);
}

.form-group textarea {
    width: 100%;
    padding: 12px 14px;
    font-size: 14px;
    line-height: 1.6;
    border-radius: 10px;
    border: 1px solid var(--border, rgba(255, 255, 255, 0.15));
    background: var(--input-bg, rgba(255, 255, 255, 0.06));
    color: var(--text, #fff);
    outline: none;
    resize: vertical;
    font-family: inherit;
}

.form-group textarea:focus {
    border-color: var(--primary);
    box-shadow: 0 0 0 3px rgba(var(--primary-rgb), 0.25);
}

.status {
    margin-top: 12px;
    padding: 10px 14px;
    border-radius: 10px;
    font-size: 13px;
    line-height: 1.5;
}

.status.success {
    background: rgba(34, 197, 94, 0.15);
    color: #4ade80;
    border: 1px solid rgba(34, 197, 94, 0.3);
}

.status.error {
    background: rgba(239, 68, 68, 0.15);
    color: #f87171;
    border: 1px solid rgba(239, 68, 68, 0.3);
}

.list-toolbar {
    display: flex;
    align-items: center;
    justify-content: space-between;
    margin: 18px 0 10px;
}

.list-count {
    font-size: 13px;
    color: var(--text-muted, rgba(255, 255, 255, 0.6));
}

.btn-mini {
    padding: 6px 12px;
    font-size: 12px;
    border-radius: 8px;
    border: 1px solid var(--border, rgba(255, 255, 255, 0.15));
    background: rgba(255, 255, 255, 0.06);
    color: var(--text, #fff);
    cursor: pointer;
    transition: background 0.15s, transform 0.1s;
    text-decoration: none;
    display: inline-block;
}

.btn-mini:hover { background: rgba(255, 255, 255, 0.12); }
.btn-mini:active { transform: scale(0.95); }

.btn-mini.danger {
    color: #f87171;
    border-color: rgba(239, 68, 68, 0.35);
}
.btn-mini.danger:hover { background: rgba(239, 68, 68, 0.15); }

.file-list,
.clipboard-list {
    list-style: none;
    padding: 0;
    margin: 0;
    display: flex;
    flex-direction: column;
    gap: 10px;
}

.file-item,
.clipboard-item {
    display: flex;
    align-items: center;
    justify-content: space-between;
    gap: 12px;
    padding: 14px 16px;
    border-radius: 12px;
    background: rgba(255, 255, 255, 0.04);
    border: 1px solid var(--border, rgba(255, 255, 255, 0.08));
}

/* 粘贴板条目改为纵向卡片：内容上、操作栏下 */
.clipboard-item {
    flex-direction: column;
    align-items: stretch;
    gap: 10px;
}

.file-info {
    display: flex;
    flex-direction: column;
    gap: 4px;
    min-width: 0;
    flex: 1;
}

.file-name {
    font-size: 14px;
    font-weight: 500;
    color: var(--text, #fff);
    white-space: nowrap;
    overflow: hidden;
    text-overflow: ellipsis;
}

.file-meta {
    font-size: 12px;
    color: var(--text-muted, rgba(255, 255, 255, 0.55));
}

/* 文件中转站：保留期提示条（超过 N 天自动删除） */
.retention-notice {
    display: flex;
    gap: 10px;
    align-items: flex-start;
    padding: 12px 14px;
    margin-bottom: 14px;
    border-radius: var(--radius-sm);
    background: rgba(245, 158, 11, 0.12);
    border: 1px solid rgba(245, 158, 11, 0.28);
    color: #fbbf24;
    transition: background 0.2s, border-color 0.2s, color 0.2s;
}

/* 已存在过期文件时转为红色告警 */
.retention-notice.danger {
    background: rgba(239, 68, 68, 0.14);
    border-color: rgba(239, 68, 68, 0.35);
    color: #f87171;
}

.retention-icon {
    flex-shrink: 0;
    display: flex;
    margin-top: 1px;
}

.retention-notice strong {
    font-size: 13px;
    font-weight: 600;
}

.retention-notice p {
    font-size: 12.5px;
    line-height: 1.6;
    margin-top: 2px;
    opacity: 0.9;
}

/* 文件条目上的自动删除倒计时 */
.file-expire.expiring {
    color: #fbbf24;
    font-weight: 600;
}

.file-expire.expired {
    color: #f87171;
    font-weight: 600;
}

.file-item.expiring {
    border-color: rgba(245, 158, 11, 0.35);
    background: rgba(245, 158, 11, 0.07);
}

.file-item.expired {
    border-color: rgba(239, 68, 68, 0.35);
    background: rgba(239, 68, 68, 0.08);
}

.file-actions,
.clipboard-actions {
    display: flex;
    gap: 8px;
    flex-shrink: 0;
}

/* 粘贴板操作栏：独立一行，顶部细分隔线，右对齐 */
.clipboard-actions {
    justify-content: flex-end;
    flex-wrap: wrap;
    gap: 6px;
    padding-top: 9px;
    margin-top: 1px;
    border-top: 1px solid var(--border, rgba(255, 255, 255, 0.08));
}

/* 操作栏按钮：紧凑、统一高度、悬停反馈 */
.clipboard-actions .btn-mini {
    padding: 5px 14px;
    font-size: 12px;
    border-radius: 999px;
    line-height: 1.4;
}

/* 置顶：强调色 */
.clipboard-actions .btn-mini.pin {
    color: #fbbf24;
    border-color: rgba(251, 191, 36, 0.4);
}
.clipboard-actions .btn-mini.pin:hover {
    background: rgba(251, 191, 36, 0.14);
}

/* 删除：危险色，置右更醒目 */
.clipboard-actions .btn-mini.danger {
    margin-left: auto;
}

.clipboard-content {
    flex: 1;
    min-width: 0;
    margin: 0;
    padding: 0 4px;
    font-size: 13px;
    line-height: 1.6;
    color: var(--text, #fff);
    white-space: pre-wrap;
    word-break: break-word;
    font-family: inherit;
    max-height: 200px;
    overflow: auto;
}

/* 富文本内容（加粗/列表等）正常渲染 */
.clipboard-content.rich {
    white-space: normal;
}
.clipboard-content.rich p { margin: 0 0 6px; }
.clipboard-content.rich img,
.clip-embed-img {
    max-width: 100%;
    border-radius: 8px;
    margin: 4px 0;
    display: block;
}

/* ── 富文本编辑器 ── */
.editor-toolbar {
    display: flex;
    align-items: center;
    gap: 6px;
    flex-wrap: wrap;
    margin-bottom: 8px;
}

.et-btn {
    min-width: 34px;
    padding: 6px 10px;
    font-size: 13px;
    border-radius: 8px;
    border: 1px solid var(--border, rgba(255, 255, 255, 0.15));
    background: rgba(255, 255, 255, 0.06);
    color: var(--text, #fff);
    cursor: pointer;
    transition: background 0.15s;
}
.et-btn:hover { background: rgba(255, 255, 255, 0.12); }

.et-sep {
    width: 1px;
    height: 22px;
    background: var(--border, rgba(255, 255, 255, 0.15));
    margin: 0 4px;
}

.editor {
    min-height: 120px;
    max-height: 360px;
    overflow: auto;
    padding: 12px 14px;
    font-size: 14px;
    line-height: 1.7;
    border-radius: 10px;
    border: 1px solid var(--border, rgba(255, 255, 255, 0.15));
    background: var(--input-bg, rgba(255, 255, 255, 0.06));
    color: var(--text, #fff);
    outline: none;
    font-family: inherit;
}
.editor:focus {
    border-color: var(--primary);
    box-shadow: 0 0 0 3px rgba(var(--primary-rgb), 0.25);
}
.editor:empty:before {
    content: attr(placeholder);
    color: var(--text-muted, rgba(255, 255, 255, 0.4));
}
.editor img {
    max-width: 100%;
    border-radius: 8px;
    margin: 4px 0;
    display: block;
}

.editor-hint {
    margin: 8px 0 12px;
    font-size: 12px;
    color: var(--text-muted, rgba(255, 255, 255, 0.5));
}

/* ── 中转站/粘贴板 新增组件 ── */
.select-all {
    display: inline-flex;
    align-items: center;
    gap: 6px;
    font-size: 13px;
    color: var(--text, #fff);
    cursor: pointer;
    user-select: none;
}

.list-toolbar .spacer { flex: 1; }

.cb-search {
    flex: 1;
    max-width: 280px;
    padding: 8px 12px;
    font-size: 13px;
    border-radius: 9px;
    border: 1px solid var(--border, rgba(255, 255, 255, 0.15));
    background: var(--input-bg, rgba(255, 255, 255, 0.06));
    color: var(--text, #fff);
    outline: none;
}
.cb-search:focus { border-color: var(--primary); box-shadow: 0 0 0 3px rgba(var(--primary-rgb), 0.25); }

/* 上传进度条 */
.progress-wrap {
    display: flex;
    align-items: center;
    gap: 12px;
    margin: 12px 0;
}
.progress-bar {
    display: block;
    flex: 1;
    height: 8px;
    border-radius: 999px;
    background: rgba(255, 255, 255, 0.1);
    overflow: hidden;
    position: relative;
}
.progress-bar:before {
    content: '';
    position: absolute;
    left: 0; top: 0; bottom: 0;
    width: 0%;
    background: linear-gradient(90deg, var(--primary), var(--accent));
    transition: width 0.2s ease;
}
.progress-text { font-size: 12px; color: var(--text-muted, rgba(255, 255, 255, 0.6)); white-space: nowrap; }

/* 文件项选择 + 缩略图 */
.file-select {
    display: inline-flex;
    align-items: center;
    margin-right: 6px;
}
.file-thumb {
    width: 44px;
    height: 44px;
    border-radius: 8px;
    background: rgba(255, 255, 255, 0.06);
    display: inline-flex;
    align-items: center;
    justify-content: center;
    overflow: hidden;
    flex-shrink: 0;
    margin-right: 10px;
    font-size: 18px;
    color: var(--text-muted, rgba(255, 255, 255, 0.6));
}
.file-thumb img { width: 100%; height: 100%; object-fit: cover; }

/* 置顶项高亮 */
.clipboard-item.pinned {
    border-color: rgba(var(--primary-rgb), 0.5);
    background: rgba(var(--primary-rgb), 0.08);
}

/* =================================================================
 *  二维码生成
 * ================================================================= */
.qr-layout {
    display: grid;
    grid-template-columns: 1fr 320px;
    gap: 28px;
    align-items: start;
}

@media (max-width: 860px) {
    .qr-layout { grid-template-columns: 1fr; }
}

/* 类型切换 */
.qr-type-tabs {
    display: flex;
    flex-wrap: wrap;
    gap: 8px;
    margin-bottom: 20px;
}
.qr-type-tab {
    display: inline-flex;
    align-items: center;
    gap: 6px;
    padding: 8px 18px;
    border: 1px solid rgba(var(--overlay), 0.14);
    border-radius: 999px;
    background: rgba(var(--overlay), 0.04);
    color: var(--text-secondary);
    font-size: 13px;
    font-weight: 600;
    font-family: inherit;
    cursor: pointer;
    transition: all 0.18s ease;
    line-height: 1;
}
.qr-type-tab svg {
    flex-shrink: 0;
    opacity: 0.85;
    transition: opacity 0.18s ease, transform 0.18s ease;
}
.qr-type-tab:hover svg {
    opacity: 1;
    transform: scale(1.08);
}
.qr-type-tab.active svg {
    opacity: 1;
}
.qr-type-tab:hover {
    border-color: var(--primary);
    color: var(--primary);
}
.qr-type-tab.active {
    border-color: transparent;
    background: linear-gradient(135deg, var(--primary), var(--accent));
    color: #fff;
    box-shadow: 0 2px 10px rgba(var(--primary-rgb), 0.35);
}

/* 表单字段 */
.qr-fields { animation: fadeSlideUp 0.25s ease; }
.qr-fields[hidden] { display: none; }

.qr-form .form-group {
    margin-top: 14px;
}
.qr-form .form-group > label {
    display: block;
    font-size: 13px;
    font-weight: 600;
    margin-bottom: 6px;
    color: var(--text);
}
.qr-form .form-group .req { color: #ff6b6b; }

.qr-form input[type="text"],
.qr-form input[type="email"],
.qr-form input[type="tel"],
.qr-form input[type="date"],
.qr-form select,
.qr-form textarea {
    width: 100%;
    padding: 10px 12px;
    font-size: 13.5px;
    font-family: inherit;
    border: 1px solid rgba(var(--overlay), 0.14);
    border-radius: 10px;
    background: rgba(var(--overlay), 0.05);
    color: var(--text);
    outline: none;
    transition: border-color 0.2s, box-shadow 0.2s;
}
.qr-form input:focus,
.qr-form select:focus,
.qr-form textarea:focus {
    border-color: var(--primary);
    box-shadow: 0 0 0 3px rgba(var(--primary-rgb), 0.18);
}
.qr-form select {
    cursor: pointer;
    -webkit-appearance: none;
    appearance: none;
    background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='14' height='14' viewBox='0 0 24 24' fill='none' stroke='%23888' stroke-width='2.5' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpolyline points='6 9 12 15 18 9'/%3E%3C/svg%3E");
    background-repeat: no-repeat;
    background-position: right 12px center;
    padding-right: 34px;
}

.form-row {
    display: grid;
    grid-template-columns: 1fr 1fr;
    gap: 14px;
}
@media (max-width: 560px) {
    .form-row { grid-template-columns: 1fr; gap: 0; }
}

.qr-divider {
    height: 1px;
    background: rgba(var(--overlay), 0.10);
    margin: 22px 0 4px;
}

.qr-options .form-group { margin-top: 14px; }

/* 颜色选择 */
.color-pick {
    display: flex;
    align-items: center;
    gap: 10px;
}
.color-pick input[type="color"] {
    width: 44px;
    height: 36px;
    padding: 3px;
    border: 1px solid rgba(var(--overlay), 0.16);
    border-radius: 8px;
    background: rgba(var(--overlay), 0.05);
    cursor: pointer;
}
.color-hex {
    font-size: 13px;
    font-family: 'Inter', monospace;
    color: var(--text-secondary);
    text-transform: uppercase;
}

/* 配色方案 */
.qr-palettes {
    display: flex;
    flex-wrap: wrap;
    gap: 10px;
}
.qr-palette {
    width: 40px;
    height: 40px;
    border-radius: 10px;
    border: 2px solid rgba(var(--overlay), 0.14);
    padding: 3px;
    background: rgba(var(--overlay), 0.04);
    cursor: pointer;
    display: flex;
    flex-direction: column;
    overflow: hidden;
    transition: transform 0.15s, border-color 0.15s;
}
.qr-palette span { flex: 1; display: block; width: 100%; min-height: 0; }
.qr-palette:hover { transform: translateY(-2px); border-color: var(--primary); }
.qr-palette.active { border-color: var(--primary); box-shadow: 0 0 0 3px rgba(var(--primary-rgb), 0.2); }

/* Logo 上传 */
.logo-upload {
    display: flex;
    flex-direction: column;
    align-items: center;
    justify-content: center;
    gap: 8px;
    padding: 24px 20px;
    border: 2px dashed rgba(var(--overlay), 0.16);
    border-radius: var(--radius-sm);
    cursor: pointer;
    text-align: center;
    background: rgba(var(--overlay), 0.02);
    transition: border-color 0.25s, background 0.25s, transform 0.25s;
}
.logo-upload:hover,
.logo-upload:focus-visible {
    border-color: var(--primary);
    background: rgba(var(--primary-rgb), 0.06);
    outline: none;
}
.logo-upload.is-dragover {
    border-color: var(--primary);
    background: rgba(var(--primary-rgb), 0.12);
    transform: scale(1.01);
}
.logo-upload-icon {
    display: grid;
    place-items: center;
    width: 44px;
    height: 44px;
    border-radius: 50%;
    background: rgba(var(--primary-rgb), 0.12);
    color: var(--primary);
    transition: transform 0.25s;
}
.logo-upload:hover .logo-upload-icon { transform: translateY(-2px); }
.logo-upload-title { margin: 0; font-size: 13px; font-weight: 600; color: var(--text); }
.logo-upload-title span {
    color: var(--primary);
    text-decoration: underline;
    text-underline-offset: 2px;
}
.logo-upload-sub { margin: 0; font-size: 12px; color: var(--text-secondary); }

/* 已上传预览 */
.qr-logo-preview {
    display: flex;
    align-items: center;
    gap: 12px;
    padding: 12px;
    border: 1px solid rgba(var(--overlay), 0.12);
    border-radius: var(--radius-sm);
    background: rgba(var(--overlay), 0.03);
}
.logo-thumb {
    flex: 0 0 auto;
    width: 60px;
    height: 60px;
    border-radius: 10px;
    border: 1px solid rgba(var(--overlay), 0.12);
    overflow: hidden;
    /* 棋盘格底：直观呈现 PNG 的透明区域 */
    background-color: #fff;
    background-image:
        linear-gradient(45deg, rgba(0, 0, 0, .06) 25%, transparent 25%, transparent 75%, rgba(0, 0, 0, .06) 75%),
        linear-gradient(45deg, rgba(0, 0, 0, .06) 25%, transparent 25%, transparent 75%, rgba(0, 0, 0, .06) 75%);
    background-size: 12px 12px;
    background-position: 0 0, 6px 6px;
}
.logo-thumb img { display: block; width: 100%; height: 100%; object-fit: contain; }
.logo-meta {
    flex: 1;
    min-width: 0;
    display: flex;
    flex-direction: column;
    gap: 2px;
}
.logo-name {
    font-size: 13px;
    font-weight: 600;
    color: var(--text);
    overflow: hidden;
    text-overflow: ellipsis;
    white-space: nowrap;
}
.logo-size { font-size: 12px; color: var(--text-secondary); }
.logo-actions { flex: 0 0 auto; display: flex; gap: 8px; }
.logo-remove {
    color: #f87171;
    border-color: rgba(239, 68, 68, 0.35);
}
.logo-remove:hover {
    background: rgba(239, 68, 68, 0.12);
    border-color: rgba(239, 68, 68, 0.5);
}

/* display:flex 会盖掉 UA 样式表的 [hidden]，导致隐藏失效，这里显式兜底 */
.logo-upload[hidden],
.qr-logo-preview[hidden] { display: none; }

.btn-sm { padding: 6px 14px; font-size: 12px; }

/* 操作按钮 */
.qr-actions {
    display: flex;
    flex-wrap: wrap;
    gap: 10px;
    margin-top: 22px;
}

/* 预览区 */
.qr-preview {
    position: sticky;
    top: 80px;
}
@media (max-width: 860px) {
    .qr-preview { position: static; }
}
.qr-preview-frame {
    display: flex;
    align-items: center;
    justify-content: center;
    min-height: 320px;
    background: #fff;
    border-radius: 16px;
    padding: 16px;
    border: 1px solid rgba(var(--overlay), 0.10);
    box-shadow: 0 4px 20px rgba(0,0,0,0.15);
}
.qr-preview-frame canvas {
    width: 100%;
    height: auto;
    max-width: 320px;
    image-rendering: pixelated;
}
.qr-preview-placeholder {
    text-align: center;
    color: #9aa0a6;
    font-size: 13px;
    padding: 24px;
}
.qr-preview-placeholder svg { margin-bottom: 12px; }
.qr-preview-hint {
    margin-top: 12px;
    font-size: 11.5px;
    color: var(--text-secondary);
    line-height: 1.7;
    opacity: 0.75;
}

.checkbox {
    display: inline-flex;
    align-items: center;
    gap: 8px;
    font-size: 13px;
    color: var(--text);
    cursor: pointer;
    margin-top: 10px;
}

/* =================================================================
 *  TOOL — 试卷手写擦除
 * ================================================================= */
.erase-options {
    margin-top: 20px;
    padding: 16px 18px;
    border-radius: var(--radius-sm);
    background: rgba(var(--overlay), 0.04);
    border: 1px solid rgba(var(--overlay), 0.08);
}
.erase-options-title {
    font-size: 13px;
    font-weight: 600;
    color: var(--text);
    margin-bottom: 4px;
}
.erase-options-grid {
    display: flex;
    flex-wrap: wrap;
    gap: 4px 28px;
}
.erase-options-grid .checkbox { margin-top: 8px; }
/* 停用的选项：置灰 + 禁止点击，避免用户误以为仍可勾选 */
.checkbox.is-disabled {
    opacity: 0.45;
    cursor: not-allowed;
}
.checkbox.is-disabled input { cursor: not-allowed; }
.erase-tag-off {
    display: inline-block;
    padding: 1px 7px;
    border-radius: 999px;
    background: rgba(var(--overlay), 0.14);
    color: var(--text-secondary);
    font-size: 11px;
    line-height: 1.7;
}
.erase-options-hint {
    margin-top: 12px;
    padding-left: 18px;
    font-size: 12.5px;
    line-height: 1.85;
    color: var(--text-secondary);
}
.erase-options-hint b { color: var(--text); }

.erase-result {
    margin-top: 24px;
    animation: fadeSlideUp 0.35s ease;
}
.erase-compare {
    display: grid;
    grid-template-columns: 1fr 1fr;
    gap: 16px;
}
.erase-compare-item {
    margin: 0;
    padding: 12px;
    border-radius: var(--radius-sm);
    border: 1px solid rgba(var(--overlay), 0.08);
    background: rgba(var(--overlay), 0.03);
    text-align: center;
}
.erase-compare-item figcaption {
    margin-bottom: 10px;
    font-size: 12px;
    font-weight: 600;
    color: var(--text-secondary);
}
.erase-compare-item img {
    display: block;
    width: 100%;
    max-height: 380px;
    object-fit: contain;
    border-radius: 8px;
    background: #fff;
    cursor: zoom-in;
    transition: transform 0.2s ease;
    /* 旋转时不撑乱网格布局 */
    transform-origin: center center;
}
/* 擦除结果旋转工具栏 */
.img-rotate-toolbar {
    display: flex;
    align-items: center;
    justify-content: center;
    gap: 8px;
    margin-top: 10px;
}
.img-rotate-toolbar .btn-sm {
    padding: 4px 10px;
    line-height: 1.4;
}
.img-rotate-deg {
    min-width: 40px;
    text-align: center;
    font-size: 12.5px;
    font-variant-numeric: tabular-nums;
    color: var(--text-secondary);
}
.erase-meta {
    margin-top: 12px;
    font-size: 12.5px;
    color: var(--text-secondary);
}

/* 网格与 flex 会盖掉 UA 样式表的 [hidden]，这里显式兜底 */
.erase-result[hidden] { display: none; }

@media (max-width: 700px) {
    .erase-compare { grid-template-columns: 1fr; }
    .erase-compare-item img { max-height: 300px; }
}

/* =================================================================
 *  TOOL — 电子盖章（图片 / PDF 叠加章图片）
 *
 *  预览舞台用 aspect-ratio 精确等于文档宽高比，章用百分比绝对定位，
 *  与后端 /stamp/apply 的换算完全一致：拖到哪，成品就盖到哪。
 * ================================================================= */
.stamp-uploads {
    display: grid;
    grid-template-columns: 1fr 1fr;
    gap: 16px;
    margin-top: 22px;
}
.stamp-upload-title {
    font-size: 13px;
    font-weight: 600;
    color: var(--text);
    margin-bottom: 8px;
}
.stamp-drop {
    padding: 22px 16px;
}
.stamp-drop .drop-zone-icon { margin-bottom: 10px; }
.stamp-drop .drop-zone-title { font-size: 14px; }
.stamp-drop-sm { padding: 16px 12px; }
.stamp-file-name {
    /* 长文件名不撑破网格 */
    overflow: hidden;
    text-overflow: ellipsis;
    white-space: nowrap;
}

.stamp-editor {
    margin-top: 24px;
    animation: fadeSlideUp 0.35s ease;
}
/* 只传了待盖章文件、还没传章：预览照常显示，但控件置灰，提示先补章图 */
.stamp-editor.is-await-stamp .stamp-control { opacity: 0.5; }
/* 还拖不动章的时候别显示“可拖动”的光标 */
.stamp-editor.is-await-stamp .stamp-stage { cursor: default; }
.stamp-upload.is-next .stamp-drop {
    border-color: var(--primary);
    background: rgba(var(--primary-rgb), 0.07);
    box-shadow: 0 0 0 3px rgba(var(--primary-rgb), 0.12);
}
.stamp-stage-badge {
    position: absolute;
    left: 50%;
    bottom: 12px;
    transform: translateX(-50%);
    padding: 5px 14px;
    border-radius: 999px;
    background: rgba(0, 0, 0, 0.62);
    color: #fff;
    font-size: 12px;
    white-space: nowrap;
    pointer-events: none;
}
.stamp-stage-badge[hidden] { display: none; }
.stamp-editor-grid {
    display: grid;
    grid-template-columns: minmax(0, 1.15fr) minmax(0, 1fr);
    gap: 22px;
    align-items: start;
}
.stamp-stage-wrap { min-width: 0; }
.stamp-stage {
    position: relative;
    width: 100%;
    max-width: 520px;
    margin: 0 auto;
    background: #fff;
    border-radius: var(--radius-sm);
    box-shadow: 0 6px 20px rgba(0, 0, 0, 0.28), inset 0 0 0 1px rgba(var(--overlay), 0.12);
    overflow: hidden;
    cursor: move;
    /* 拖动预览时不要让页面跟着滚 */
    touch-action: none;
    user-select: none;
}
.stamp-stage.is-dragging { cursor: grabbing; }
.stamp-stage-base {
    position: absolute;
    inset: 0;
    width: 100%;
    height: 100%;
    display: block;
}
.stamp-stage-page {
    position: absolute;
    inset: 0;
    display: flex;
    align-items: center;
    justify-content: center;
    background: #fff;
    color: #b9b9c4;
    font-size: 12px;
    letter-spacing: 2px;
}
.stamp-stage-stamp {
    position: absolute;
    height: auto;
    transform-origin: center center;
    pointer-events: none;
    will-change: left, top, width;
}
/* 上面几条 display 声明会盖掉 UA 的 [hidden]，这里显式兜底 */
.stamp-stage-base[hidden],
.stamp-stage-page[hidden],
.stamp-stage-stamp[hidden] { display: none; }

/* PDF 页预览的翻页条 */
.stamp-pdf-nav {
    display: flex;
    align-items: center;
    flex-wrap: wrap;
    gap: 10px;
    max-width: 520px;
    margin: 0 auto 10px;
}
.stamp-pdf-nav[hidden] { display: none; }
.stamp-pdf-page {
    font-size: 12.5px;
    color: var(--text-secondary);
    font-variant-numeric: tabular-nums;
}
.stamp-pdf-page b { color: var(--text); }
.stamp-pdf-nav .btn-sm {
    padding: 4px 12px;
    line-height: 1.4;
}
.stamp-pdf-nav .btn-sm:disabled {
    opacity: 0.4;
    cursor: not-allowed;
}
.stamp-pdf-nav-hint { margin-top: 0; }
.stamp-controls { min-width: 0; }
.stamp-control { margin-bottom: 18px; }
.stamp-control:last-child { margin-bottom: 0; }
.stamp-control-label {
    font-size: 13px;
    font-weight: 600;
    color: var(--text);
    margin-bottom: 8px;
}
.stamp-presets {
    display: flex;
    flex-wrap: wrap;
    gap: 8px;
}
.stamp-chip {
    padding: 5px 12px;
    border-radius: 999px;
    border: 1px solid rgba(var(--overlay), 0.16);
    background: rgba(var(--overlay), 0.05);
    color: var(--text-secondary);
    font-size: 12.5px;
    font-family: inherit;
    cursor: pointer;
    transition: all 0.2s ease;
}
.stamp-chip:hover { border-color: var(--primary); color: var(--text); }
.stamp-chip.is-active {
    background: rgba(var(--primary-rgb), 0.16);
    border-color: var(--primary);
    color: var(--text);
    font-weight: 600;
}
.stamp-sliders { display: flex; flex-direction: column; gap: 10px; }
.stamp-slider-row {
    display: grid;
    grid-template-columns: 72px minmax(0, 1fr) 52px;
    align-items: center;
    gap: 10px;
}
.stamp-slider-row > label {
    font-size: 12.5px;
    color: var(--text-secondary);
}
.stamp-slider-row > output {
    font-size: 12.5px;
    text-align: right;
    font-variant-numeric: tabular-nums;
    color: var(--text-secondary);
}
.stamp-slider-row input[type="range"] {
    width: 100%;
    accent-color: var(--primary);
    cursor: pointer;
}
.stamp-page-row {
    display: flex;
    align-items: center;
    gap: 10px;
}
.stamp-page-row select,
.stamp-page-row input[type="number"] {
    padding: 6px 10px;
    border-radius: 8px;
    border: 1px solid rgba(var(--overlay), 0.14);
    background: rgba(var(--overlay), 0.04);
    color: var(--text);
    font-size: 13px;
    font-family: inherit;
    outline: none;
}
.stamp-page-row input[type="number"] { width: 82px; }
.stamp-page-row select:focus,
.stamp-page-row input[type="number"]:focus { border-color: var(--primary); }
.stamp-actions {
    display: flex;
    flex-wrap: wrap;
    gap: 10px;
    margin-top: 16px;
}
/* 主功能使用说明：条目自带 ①②③ 序号，去掉默认圆点并做悬挂缩进，
   换行后与序号后的正文对齐，而不是缩到序号下面 */
.stamp-guide .erase-options-hint {
    list-style: none;
    padding-left: 0;
}
.stamp-guide .erase-options-hint li {
    padding-left: 24px;
    text-indent: -24px;
}

/* 「透明章」是独立小工具，不是盖章流程的一环：
   用一条带文字的分隔线 + 主色描边的卡片把它和主功能在视觉上分开 */
.stamp-sep {
    display: flex;
    align-items: center;
    gap: 14px;
    margin: 38px 0 18px;
    font-size: 12px;
    letter-spacing: 2px;
    color: var(--text-secondary);
}
.stamp-sep::before,
.stamp-sep::after {
    content: '';
    flex: 1;
    height: 1px;
    background: rgba(var(--overlay), 0.14);
}
.stamp-transparent-box {
    padding: 20px;
    border-radius: var(--radius);
    border: 1px solid rgba(var(--primary-rgb), 0.30);
    background: linear-gradient(180deg, rgba(var(--primary-rgb), 0.07), rgba(var(--overlay), 0.02));
}
.stamp-transparent-head {
    display: flex;
    align-items: flex-start;
    gap: 12px;
    margin-bottom: 16px;
}
.stamp-transparent-icon {
    flex: 0 0 auto;
    display: flex;
    align-items: center;
    justify-content: center;
    width: 38px;
    height: 38px;
    border-radius: 10px;
    background: rgba(var(--primary-rgb), 0.15);
    color: var(--primary);
}
.stamp-transparent-title {
    display: flex;
    align-items: center;
    gap: 8px;
    font-size: 15px;
    font-weight: 600;
    color: var(--text);
}
.stamp-subtag {
    padding: 1px 8px;
    border-radius: 999px;
    font-size: 11px;
    font-weight: 500;
    letter-spacing: 0;
    background: rgba(var(--primary-rgb), 0.15);
    border: 1px solid rgba(var(--primary-rgb), 0.30);
    color: var(--primary);
}
.stamp-transparent-desc { margin-top: 3px; }
/* .stamp-actions 是 flex，会盖掉 UA 的 [hidden]；没选图片时不显示下载按钮 */
.stamp-actions[hidden] { display: none; }
.stamp-transparent-row {
    display: grid;
    grid-template-columns: minmax(0, 1fr) minmax(0, 1fr);
    gap: 16px;
    align-items: start;
    /* 标题头已经给了间距，这里不再叠加 */
    margin-top: 0;
}
.stamp-transparent-side { min-width: 0; }
.stamp-transparent-preview {
    position: relative;
    display: flex;
    align-items: center;
    justify-content: center;
    min-height: 140px;
    padding: 10px;
    border-radius: var(--radius-sm);
    border: 1px solid rgba(var(--overlay), 0.10);
    /* 棋盘格底：一眼看出哪些地方是透明的 */
    background-color: #fff;
    background-image:
        linear-gradient(45deg, #d8d8e0 25%, transparent 25%, transparent 75%, #d8d8e0 75%),
        linear-gradient(45deg, #d8d8e0 25%, transparent 25%, transparent 75%, #d8d8e0 75%);
    background-size: 16px 16px;
    background-position: 0 0, 8px 8px;
}
.stamp-transparent-preview img {
    max-width: 100%;
    max-height: 180px;
    object-fit: contain;
}
.stamp-transparent-preview img[hidden] { display: none; }
.stamp-transparent-placeholder {
    color: var(--text-secondary);
    font-size: 12.5px;
}
.stamp-transparent-preview img:not([hidden]) + .stamp-transparent-placeholder { display: none; }

@media (max-width: 860px) {
    .stamp-uploads { grid-template-columns: 1fr; }
    .stamp-editor-grid { grid-template-columns: 1fr; }
    .stamp-transparent-row { grid-template-columns: 1fr; }
    .stamp-stage { max-width: 100%; }
}

/* =================================================================
 *  TOOL — 试题批改（腾讯云 试题批改 Agent）
 *
 *  下面这批 .qmark-* 里，结果区相关的几个（qmark-result / qmark-stat /
 *  qmark-index / qmark-empty / qmark-preview-inner / qmark-page-input /
 *  qmark-extra-del）是通用的，后面的「作文批改」也在复用，改样式时两边一起看。
 * ================================================================= */
.qmark-preview {
    display: flex;
    flex-wrap: wrap;
    gap: 16px;
    align-items: flex-start;
    margin-top: 18px;
}
/* 容器收缩到图片本身大小，切题框才能用百分比精确定位 */
.qmark-preview-inner {
    position: relative;
    display: inline-block;
    max-width: 100%;
    line-height: 0;
    border-radius: var(--radius-sm);
    overflow: hidden;
    border: 1px solid rgba(var(--overlay), 0.08);
}
.qmark-preview-inner img {
    display: block;
    width: auto;
    max-width: 100%;
    max-height: 420px;
    background: #fff;
    cursor: zoom-in;
}
.qmark-preview-side {
    flex: 1 1 220px;
    min-width: 0;
}
.qmark-boxes {
    position: absolute;
    inset: 0;
    pointer-events: none;
}
.qmark-box {
    position: absolute;
    border: 2px solid #22c55e;
    border-radius: 3px;
    background: rgba(34, 197, 94, 0.12);
}
.qmark-box-no {
    position: absolute;
    top: -2px;
    left: -2px;
    padding: 0 5px;
    font-size: 10px;
    line-height: 15px;
    color: #fff;
    background: #22c55e;
    border-radius: 3px 0 3px 0;
}

.qmark-field {
    display: flex;
    align-items: center;
    gap: 10px;
    flex-wrap: wrap;
    margin-top: 14px;
}
.qmark-field label {
    flex: 0 0 auto;
    font-size: 13px;
    color: var(--text);
}
.qmark-field .deepseek-input-field {
    flex: 1 1 260px;
    min-width: 0;
}
.qmark-field textarea.deepseek-input-field {
    resize: vertical;
    line-height: 1.7;
}
.qmark-field .qmark-page-input {
    flex: 0 0 100px;
    min-width: 0;
}

.qmark-assist-types {
    display: flex;
    flex-wrap: wrap;
    align-items: center;
    gap: 4px 20px;
    margin-top: 14px;
}
.qmark-assist-label {
    font-size: 13px;
    color: var(--text);
}

.qmark-assist-panel {
    margin-top: 14px;
    padding-top: 12px;
    border-top: 1px dashed rgba(var(--overlay), 0.12);
}
.qmark-assist-panel .hint-text {
    margin-bottom: 10px;
}

.qmark-extra-list {
    list-style: none;
    margin-top: 10px;
}
.qmark-extra-item {
    display: flex;
    align-items: center;
    gap: 10px;
    padding: 7px 12px;
    margin-bottom: 6px;
    border-radius: 8px;
    background: rgba(var(--overlay), 0.04);
    border: 1px solid rgba(var(--overlay), 0.08);
    font-size: 13px;
}
.qmark-extra-name {
    flex: 1 1 auto;
    min-width: 0;
    overflow: hidden;
    text-overflow: ellipsis;
    white-space: nowrap;
}
.qmark-extra-size {
    flex: 0 0 auto;
    font-size: 12px;
    color: var(--text-secondary);
}
.qmark-extra-del {
    flex: 0 0 auto;
    padding: 3px 10px;
    font-family: inherit;
    font-size: 12px;
    color: var(--text-secondary);
    background: transparent;
    border: 1px solid rgba(var(--overlay), 0.16);
    border-radius: 6px;
    cursor: pointer;
    transition: all .2s;
}
.qmark-extra-del:hover {
    color: #ef4444;
    border-color: rgba(239, 68, 68, 0.45);
    background: rgba(239, 68, 68, 0.10);
}

.qmark-result {
    margin-top: 24px;
    animation: fadeSlideUp 0.35s ease;
}
.qmark-result-actions {
    display: flex;
    gap: 10px;
}
.qmark-summary {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(110px, 1fr));
    gap: 12px;
    margin-bottom: 18px;
}
.qmark-stat {
    padding: 14px 16px;
    border-radius: var(--radius-sm);
    background: rgba(var(--overlay), 0.04);
    border: 1px solid rgba(var(--overlay), 0.08);
    text-align: center;
}
.qmark-stat-value {
    font-size: 22px;
    font-weight: 700;
    line-height: 1.3;
    color: var(--text);
}
.qmark-stat-label {
    margin-top: 2px;
    font-size: 12px;
    color: var(--text-secondary);
}
.qmark-stat.right .qmark-stat-value { color: #4ade80; }
.qmark-stat.wrong .qmark-stat-value { color: #f87171; }

.qmark-tree {
    display: flex;
    flex-direction: column;
    gap: 12px;
}
.qmark-item {
    padding: 14px 16px;
    border-radius: var(--radius-sm);
    background: rgba(var(--overlay), 0.03);
    border: 1px solid rgba(var(--overlay), 0.08);
    border-left: 3px solid rgba(var(--overlay), 0.18);
}
.qmark-item.depth-1,
.qmark-item.depth-2 {
    margin-left: 18px;
    margin-top: 10px;
    background: transparent;
}
.qmark-item-head {
    display: flex;
    align-items: flex-start;
    gap: 10px;
    flex-wrap: wrap;
}
.qmark-index {
    flex: 0 0 auto;
    display: inline-flex;
    align-items: center;
    justify-content: center;
    min-width: 22px;
    height: 22px;
    padding: 0 6px;
    border-radius: 6px;
    background: rgba(var(--primary-rgb), 0.16);
    color: var(--text);
    font-size: 12px;
    font-weight: 600;
}
.qmark-title {
    flex: 1 1 260px;
    min-width: 0;
    font-size: 14px;
    font-weight: 600;
    line-height: 1.7;
    word-break: break-word;
}
.qmark-badge {
    flex: 0 0 auto;
    padding: 2px 10px;
    border-radius: 999px;
    font-size: 11.5px;
    font-weight: 600;
    line-height: 1.7;
}
.qmark-badge.right {
    color: #4ade80;
    background: rgba(34, 197, 94, 0.14);
    border: 1px solid rgba(34, 197, 94, 0.32);
}
.qmark-badge.wrong {
    color: #f87171;
    background: rgba(239, 68, 68, 0.14);
    border: 1px solid rgba(239, 68, 68, 0.32);
}
[data-theme="light"] .qmark-stat.right .qmark-stat-value,
[data-theme="light"] .qmark-badge.right { color: #16a34a; }
[data-theme="light"] .qmark-stat.wrong .qmark-stat-value,
[data-theme="light"] .qmark-badge.wrong { color: #dc2626; }

.qmark-answer {
    margin-top: 10px;
    padding-top: 10px;
    border-top: 1px dashed rgba(var(--overlay), 0.12);
}
.qmark-answer .qmark-badge {
    display: inline-block;
    margin-bottom: 6px;
}
.qmark-line {
    display: flex;
    gap: 10px;
    margin-top: 8px;
    font-size: 13px;
    line-height: 1.8;
}
.qmark-label {
    flex: 0 0 68px;
    font-size: 12px;
    color: var(--text-secondary);
}
.qmark-text {
    flex: 1 1 auto;
    min-width: 0;
    white-space: pre-wrap;
    word-break: break-word;
}
.qmark-kp {
    display: flex;
    flex-wrap: wrap;
    gap: 6px;
}
.qmark-kp-tag {
    padding: 1px 9px;
    font-size: 11.5px;
    border-radius: 999px;
    background: rgba(var(--primary-rgb), 0.14);
    border: 1px solid rgba(var(--primary-rgb), 0.28);
    color: var(--text);
}
.qmark-empty {
    padding: 20px;
    text-align: center;
    font-size: 13px;
    color: var(--text-secondary);
}

/* flex / grid 会盖掉 UA 样式表的 [hidden]，这里显式兜底 */
.qmark-preview[hidden],
.qmark-result[hidden],
.qmark-boxes[hidden],
.qmark-assist-panel[hidden],
.qmark-field[hidden] { display: none; }

@media (max-width: 700px) {
    .qmark-preview-inner img { max-height: 300px; }
    .qmark-item.depth-1,
    .qmark-item.depth-2 { margin-left: 10px; }
    .qmark-line { flex-direction: column; gap: 2px; }
    .qmark-label { flex: 0 0 auto; }
}

/* =================================================================
 *  TOOL — 作文批改（腾讯云 作文批改 Agent）
 * ================================================================= */
.essay-file-list {
    list-style: none;
    display: grid;
    grid-template-columns: repeat(auto-fill, minmax(240px, 1fr));
    gap: 10px;
    margin-top: 14px;
}
.essay-file-item {
    display: flex;
    align-items: center;
    gap: 12px;
    padding: 10px 12px;
    border-radius: var(--radius-sm);
    background: rgba(var(--overlay), 0.04);
    border: 1px solid rgba(var(--overlay), 0.08);
}
.essay-file-thumb {
    flex: 0 0 46px;
    width: 46px;
    height: 58px;
    display: flex;
    align-items: center;
    justify-content: center;
    overflow: hidden;
    border-radius: 6px;
    background: rgba(var(--overlay), 0.08);
    font-size: 11px;
    font-weight: 600;
    color: var(--text-secondary);
}
.essay-file-thumb img {
    width: 100%;
    height: 100%;
    object-fit: cover;
}
.essay-file-info {
    flex: 1 1 auto;
    min-width: 0;
}
.essay-file-name {
    font-size: 13px;
    overflow: hidden;
    text-overflow: ellipsis;
    white-space: nowrap;
}
.essay-file-meta {
    margin-top: 2px;
    font-size: 12px;
    color: var(--text-secondary);
}

.essay-summary {
    display: flex;
    flex-wrap: wrap;
    align-items: stretch;
    gap: 12px;
    margin-bottom: 18px;
}
.essay-summary .qmark-stat {
    flex: 1 1 110px;
}
.essay-chips {
    display: flex;
    flex-wrap: wrap;
    align-content: center;
    gap: 6px;
    flex: 3 1 260px;
}
.essay-chip {
    padding: 2px 10px;
    border-radius: 999px;
    font-size: 11.5px;
    font-weight: 600;
    line-height: 1.7;
    color: var(--text-secondary);
    background: rgba(var(--overlay), 0.06);
    border: 1px solid rgba(var(--overlay), 0.12);
}
.essay-chip.plain {
    color: var(--text);
    background: rgba(var(--primary-rgb), 0.12);
    border-color: rgba(var(--primary-rgb), 0.28);
}
.essay-chip.right {
    color: #4ade80;
    background: rgba(34, 197, 94, 0.14);
    border-color: rgba(34, 197, 94, 0.32);
}
.essay-chip.wrong {
    color: #f87171;
    background: rgba(239, 68, 68, 0.14);
    border-color: rgba(239, 68, 68, 0.32);
}
[data-theme="light"] .essay-chip.right { color: #16a34a; }
[data-theme="light"] .essay-chip.wrong { color: #dc2626; }

.essay-pages {
    display: flex;
    flex-direction: column;
    gap: 18px;
}
.essay-page {
    padding: 14px 16px;
    border-radius: var(--radius-sm);
    background: rgba(var(--overlay), 0.03);
    border: 1px solid rgba(var(--overlay), 0.08);
}
.essay-page-head {
    display: flex;
    align-items: center;
    justify-content: space-between;
    gap: 10px;
    flex-wrap: wrap;
    padding-bottom: 10px;
    margin-bottom: 12px;
    border-bottom: 1px dashed rgba(var(--overlay), 0.12);
}
.essay-page-title {
    font-size: 13.5px;
    font-weight: 600;
    word-break: break-all;
}
.essay-page-count {
    flex: 0 0 auto;
    font-size: 12px;
    color: var(--text-secondary);
}
.essay-page-body {
    display: flex;
    gap: 16px;
    align-items: flex-start;
}
.essay-page-body .qmark-preview-inner {
    flex: 0 0 300px;
    max-width: 300px;
}
.essay-page-body .qmark-preview-inner img {
    width: 100%;
    max-height: 420px;
    cursor: zoom-in;
}
.essay-list {
    flex: 1 1 320px;
    min-width: 0;
    display: flex;
    flex-direction: column;
    gap: 10px;
}
.essay-item {
    padding: 10px 12px;
    border-radius: 8px;
    background: rgba(var(--overlay), 0.04);
    border: 1px solid rgba(var(--overlay), 0.08);
    border-left: 3px solid rgba(239, 68, 68, 0.55);
    transition: background .2s, border-color .2s;
}
.essay-item.is-praise {
    border-left-color: rgba(34, 197, 94, 0.55);
}
.essay-item:hover {
    background: rgba(var(--overlay), 0.08);
}
.essay-item-head {
    display: flex;
    align-items: center;
    gap: 8px;
    flex-wrap: wrap;
}
.essay-quote {
    margin-top: 8px;
    font-size: 13px;
    line-height: 1.8;
    word-break: break-word;
}
.essay-quote.origin {
    padding: 6px 10px;
    border-radius: 6px;
    background: rgba(239, 68, 68, 0.10);
    color: var(--text);
}
.essay-quote.replace {
    display: flex;
    gap: 8px;
    padding: 6px 10px;
    border-radius: 6px;
    background: rgba(34, 197, 94, 0.10);
}
.essay-quote-tag {
    flex: 0 0 auto;
    font-size: 12px;
    color: var(--text-secondary);
}
.essay-message {
    margin-top: 6px;
    font-size: 12.5px;
    line-height: 1.85;
    color: var(--text-secondary);
}

/* 原文高亮框：坐标由前端按提交尺寸换算成百分比 */
.essay-boxes {
    position: absolute;
    inset: 0;
    pointer-events: none;
}
.essay-box {
    position: absolute;
    border: 2px solid rgba(239, 68, 68, 0.75);
    border-radius: 3px;
    background: rgba(239, 68, 68, 0.14);
    transition: background .15s, box-shadow .15s;
}
.essay-box.is-praise {
    border-color: rgba(34, 197, 94, 0.75);
    background: rgba(34, 197, 94, 0.14);
}
/* 悬停对应建议时高亮 */
.essay-box.is-active {
    background: rgba(var(--primary-rgb), 0.40);
    box-shadow: 0 0 0 2px rgba(var(--primary-rgb), 0.45);
}

.essay-file-list[hidden],
.essay-page[hidden] { display: none; }

@media (max-width: 760px) {
    .essay-page-body { flex-direction: column; }
    .essay-page-body .qmark-preview-inner { flex: 0 0 auto; max-width: 100%; }
}

/* =================================================================
 *  TOOL — 人民币金额大写
 * ================================================================= */
.rmb-amount-row {
    display: flex;
    align-items: center;
    gap: 10px;
    padding: 12px 16px;
    border-radius: var(--radius-sm);
    border: 1px solid rgba(var(--overlay), 0.14);
    background: rgba(var(--overlay), 0.05);
    transition: border-color .2s, box-shadow .2s;
}
.rmb-amount-row:focus-within {
    border-color: var(--primary);
    box-shadow: 0 0 0 3px rgba(var(--primary-rgb), 0.25);
}
.rmb-currency {
    flex: 0 0 auto;
    font-size: 22px;
    font-weight: 600;
    color: var(--text-secondary);
}
.rmb-amount-input {
    flex: 1;
    min-width: 0;
    border: none;
    background: transparent;
    color: var(--text);
    font-family: inherit;
    font-size: 26px;
    font-weight: 600;
    letter-spacing: .5px;
    outline: none;
}
.rmb-amount-input::placeholder {
    color: var(--text-secondary);
    opacity: 0.45;
}

.rmb-chips {
    display: flex;
    flex-wrap: wrap;
    gap: 8px;
    margin-top: 12px;
}
.rmb-chip {
    padding: 5px 12px;
    font-size: 12px;
    font-family: inherit;
    color: var(--text-secondary);
    background: rgba(var(--overlay), 0.05);
    border: 1px solid rgba(var(--overlay), 0.12);
    border-radius: 999px;
    cursor: pointer;
    transition: all .2s;
}
.rmb-chip:hover {
    color: var(--text);
    border-color: rgba(var(--primary-rgb), 0.5);
    background: rgba(var(--primary-rgb), 0.12);
}

.rmb-options {
    display: flex;
    flex-wrap: wrap;
    gap: 10px 24px;
}

.rmb-result {
    margin-top: 18px;
    padding: 18px 20px;
    border-radius: var(--radius-sm);
    border: 1px solid rgba(var(--primary-rgb), 0.28);
    background: rgba(var(--primary-rgb), 0.10);
}
.rmb-result-head {
    display: flex;
    align-items: center;
    justify-content: space-between;
    gap: 12px;
    margin-bottom: 10px;
    font-size: 13px;
    font-weight: 600;
    color: var(--text-secondary);
}
.rmb-capital {
    font-size: 22px;
    font-weight: 700;
    line-height: 1.6;
    letter-spacing: 1px;
    color: var(--text);
    word-break: break-all;
}
.status.warn {
    background: rgba(245, 158, 11, 0.15);
    color: #fbbf24;
    border: 1px solid rgba(245, 158, 11, 0.3);
}

.rmb-rules {
    margin-top: 20px;
    padding: 16px 18px;
    border-radius: var(--radius-sm);
    background: rgba(var(--overlay), 0.04);
    border: 1px solid rgba(var(--overlay), 0.08);
    font-size: 12.5px;
    line-height: 1.85;
    color: var(--text-secondary);
}
.rmb-rules strong {
    display: block;
    margin-bottom: 6px;
    font-size: 13px;
    color: var(--text);
}
.rmb-rules ul {
    padding-left: 18px;
}
.rmb-rules li {
    margin-bottom: 2px;
}

/* display:flex 会盖掉 UA 样式表的 [hidden]，这里显式兜底 */
.rmb-result[hidden],
.rmb-amount-row[hidden] { display: none; }

@media (max-width: 600px) {
    .rmb-amount-input { font-size: 22px; }
    .rmb-capital { font-size: 18px; }
}

/* =================================================================
 *  TOOL — 动态验证码（TOTP 客户端）
 * ================================================================= */
.totp-add {
    margin-top: 4px;
    padding: 16px 18px;
    border-radius: var(--radius-sm);
    border: 1px solid rgba(var(--overlay), 0.10);
    background: rgba(var(--overlay), 0.04);
}
.totp-add-head {
    display: flex;
    align-items: center;
    justify-content: space-between;
    gap: 12px;
    flex-wrap: wrap;
    margin-bottom: 14px;
}
.totp-add-title {
    font-size: 14px;
    font-weight: 600;
}
.totp-tabs {
    display: inline-flex;
    padding: 3px;
    border-radius: 999px;
    background: rgba(var(--overlay), 0.08);
}
.totp-tab {
    padding: 5px 16px;
    border: none;
    border-radius: 999px;
    background: transparent;
    color: var(--text-secondary);
    font-size: 12.5px;
    font-family: inherit;
    cursor: pointer;
    transition: background 0.2s, color 0.2s;
}
.totp-tab.is-active {
    background: var(--primary);
    color: #ffffff;
}

/* 扫码区 */
.totp-drop {
    display: flex;
    flex-direction: column;
    align-items: center;
    gap: 6px;
    padding: 26px 18px;
    border: 2px dashed rgba(var(--overlay), 0.22);
    border-radius: var(--radius-sm);
    background: rgba(var(--overlay), 0.03);
    text-align: center;
    cursor: pointer;
    outline: none;
    transition: border-color 0.2s, background 0.2s;
}
.totp-drop:hover,
.totp-drop:focus-visible { border-color: var(--primary); }
.totp-drop.is-over {
    border-color: var(--primary);
    background: rgba(var(--primary-rgb), 0.12);
}
.totp-drop-icon { color: var(--text-secondary); opacity: 0.8; }
.totp-drop-title { font-size: 14px; font-weight: 600; }
.totp-drop .hint-text { margin-top: 2px; }

/* 手动输入区 */
.totp-pane input[type="text"],
.totp-pane select,
.totp-textarea {
    width: 100%;
    padding: 10px 12px;
    font-size: 13.5px;
    font-family: inherit;
    border: 1px solid rgba(var(--overlay), 0.14);
    border-radius: 10px;
    background: rgba(var(--overlay), 0.05);
    color: var(--text);
    outline: none;
    transition: border-color 0.2s, box-shadow 0.2s;
}
.totp-textarea {
    font-family: ui-monospace, SFMono-Regular, Menlo, Consolas, monospace;
    font-size: 12.5px;
    line-height: 1.6;
    resize: vertical;
    min-height: 54px;
}
.totp-pane input[type="text"]:focus,
.totp-pane select:focus,
.totp-textarea:focus {
    border-color: var(--primary);
    box-shadow: 0 0 0 3px rgba(var(--primary-rgb), 0.18);
}
.totp-pane select {
    cursor: pointer;
    -webkit-appearance: none;
    appearance: none;
    background-image: url("data:image/svg+xml,%3Csvg xmlns='http://www.w3.org/2000/svg' width='14' height='14' viewBox='0 0 24 24' fill='none' stroke='%23888' stroke-width='2.5' stroke-linecap='round' stroke-linejoin='round'%3E%3Cpolyline points='6 9 12 15 18 9'/%3E%3C/svg%3E");
    background-repeat: no-repeat;
    background-position: right 12px center;
    padding-right: 34px;
}
.totp-row-3 { grid-template-columns: repeat(3, minmax(0, 1fr)); }
.totp-actions {
    display: flex;
    align-items: center;
    gap: 12px;
    flex-wrap: wrap;
    margin-top: 4px;
}
.totp-pane .hint-text code {
    padding: 1px 5px;
    border-radius: 4px;
    background: rgba(var(--overlay), 0.10);
    font-size: 11px;
}

/* 账户列表 */
.totp-list-head {
    display: flex;
    align-items: center;
    justify-content: space-between;
    gap: 12px;
    margin: 24px 0 10px;
}
.totp-list-title { font-size: 14px; font-weight: 600; }
.totp-list-tools {
    display: flex;
    align-items: center;
    gap: 10px;
}
.totp-search {
    position: relative;
    display: flex;
    align-items: center;
}
.totp-search-icon {
    position: absolute;
    left: 10px;
    color: var(--text-secondary);
    pointer-events: none;
    opacity: 0.7;
}
.totp-search-input {
    padding: 7px 28px 7px 30px;
    font-size: 13px;
    border: 1px solid rgba(255, 255, 255, 0.14);
    border-radius: 8px;
    background: rgba(var(--overlay), 0.05);
    color: var(--text);
    outline: none;
    width: 150px;
    transition: border-color 0.2s, box-shadow 0.2s, width 0.2s;
}
.totp-search-input:focus {
    border-color: var(--primary);
    box-shadow: 0 0 0 3px rgba(var(--primary-rgb), 0.18);
    width: 180px;
}
.totp-search-input::placeholder { color: var(--text-secondary); opacity: 0.6; }
.totp-search-clear {
    position: absolute;
    right: 6px;
    width: 18px;
    height: 18px;
    border: none;
    border-radius: 50%;
    background: rgba(255, 255, 255, 0.12);
    color: var(--text-secondary);
    font-size: 15px;
    line-height: 1;
    cursor: pointer;
    display: flex;
    align-items: center;
    justify-content: center;
}
.totp-search-clear:hover { background: rgba(255, 255, 255, 0.2); color: var(--text); }
.totp-search-clear[hidden] { display: none; }
.totp-search-empty {
    padding: 32px 12px;
    text-align: center;
    color: var(--text-secondary);
    font-size: 13px;
}
.totp-list {
    display: flex;
    flex-direction: column;
    gap: 10px;
}
.totp-item {
    position: relative;
    display: flex;
    align-items: center;
    gap: 16px;
    padding: 14px 18px 18px;
    border-radius: var(--radius-sm);
    border: 1px solid rgba(var(--overlay), 0.10);
    background: rgba(var(--overlay), 0.05);
    transition: border-color 0.2s, background 0.2s;
}
.totp-item:hover {
    border-color: rgba(var(--primary-rgb), 0.45);
    background: rgba(var(--primary-rgb), 0.08);
}
.totp-item.is-error { opacity: 0.75; }
.totp-item.is-error .totp-item-code { font-size: 18px; color: #ef4444; }

.totp-item-info {
    flex: 1 1 auto;
    min-width: 0;
}
.totp-item-name {
    font-size: 14.5px;
    font-weight: 600;
    overflow: hidden;
    text-overflow: ellipsis;
    white-space: nowrap;
}
.totp-item-sub {
    margin-top: 2px;
    font-size: 12px;
    color: var(--text-secondary);
    overflow: hidden;
    text-overflow: ellipsis;
    white-space: nowrap;
}
.totp-item-code {
    flex: 0 0 auto;
    padding: 4px 10px;
    border-radius: 8px;
    font-family: ui-monospace, SFMono-Regular, Menlo, Consolas, monospace;
    font-size: 30px;
    font-weight: 700;
    letter-spacing: 3px;
    line-height: 1.25;
    font-variant-numeric: tabular-nums;
    cursor: pointer;
    user-select: all;
}
.totp-item-side {
    flex: 0 0 auto;
    display: flex;
    align-items: center;
    gap: 10px;
}
.totp-item-btn {
    padding: 5px 12px;
    border: 1px solid rgba(var(--overlay), 0.16);
    border-radius: 8px;
    background: transparent;
    color: var(--text-secondary);
    font-size: 12px;
    font-family: inherit;
    cursor: pointer;
    transition: color 0.2s, border-color 0.2s, background 0.2s;
}
.totp-item-btn:hover {
    color: var(--primary);
    border-color: var(--primary);
    background: rgba(var(--primary-rgb), 0.10);
}
.totp-item-btn.is-danger:hover {
    color: #ef4444;
    border-color: #ef4444;
    background: rgba(239, 68, 68, 0.10);
}

/* 每行的倒计时圆环 + 底部进度条 */
.totp-ring-sm {
    position: relative;
    width: 40px;
    height: 40px;
    display: flex;
    align-items: center;
    justify-content: center;
}
.totp-ring-svg {
    position: absolute;
    inset: 0;
    width: 100%;
    height: 100%;
    transform: rotate(-90deg);
}
.totp-ring-bg {
    fill: none;
    stroke: rgba(var(--overlay), 0.12);
    stroke-width: 3;
}
.totp-ring-fg {
    fill: none;
    stroke: var(--primary);
    stroke-width: 3;
    stroke-linecap: round;
    transition: stroke-dashoffset 0.95s linear, stroke 0.3s;
}
.totp-ring-fg.is-urgent { stroke: #ef4444; }
.totp-ring-num {
    position: relative;
    font-size: 12px;
    font-weight: 700;
    font-variant-numeric: tabular-nums;
    color: var(--text-secondary);
}
.totp-progress {
    position: absolute;
    left: 18px;
    right: 18px;
    bottom: 8px;
    height: 3px;
    border-radius: 999px;
    background: rgba(var(--overlay), 0.10);
    overflow: hidden;
}
.totp-progress-bar {
    height: 100%;
    width: 100%;
    border-radius: 999px;
    background: linear-gradient(90deg, var(--primary), var(--accent));
    transition: width 0.95s linear;
}

.totp-empty {
    display: flex;
    flex-direction: column;
    align-items: center;
    gap: 6px;
    padding: 34px 20px;
    border-radius: var(--radius-sm);
    border: 1px dashed rgba(var(--overlay), 0.18);
    text-align: center;
    color: var(--text-secondary);
}
.totp-empty svg { opacity: 0.5; margin-bottom: 4px; }
.totp-empty p:first-of-type { font-size: 14px; font-weight: 600; }
.totp-empty .hint-text { max-width: 460px; }

/* 备份 */
.totp-backup-row {
    display: flex;
    gap: 8px;
    flex-wrap: wrap;
    margin: 10px 0 4px;
}

/* 密钥库状态栏：未创建 / 已锁定 / 已解锁 / 改口令 四态互斥显示 */
.totp-vault {
    display: flex;
    gap: 14px;
    padding: 16px 18px;
    border-radius: var(--radius-sm);
    border: 1px solid rgba(var(--primary-rgb), 0.28);
    background: rgba(var(--primary-rgb), 0.10);
}
.totp-vault-icon {
    flex: 0 0 auto;
    display: flex;
    align-items: center;
    justify-content: center;
    width: 42px;
    height: 42px;
    border-radius: 50%;
    background: rgba(var(--primary-rgb), 0.20);
    color: var(--primary);
}
.totp-vault-body { flex: 1 1 auto; min-width: 0; }
.totp-vault-title {
    font-size: 14px;
    font-weight: 600;
}
.totp-vault-form {
    display: flex;
    align-items: center;
    gap: 8px;
    flex-wrap: wrap;
    margin-top: 8px;
}
.totp-vault-form input[type="password"] {
    flex: 0 1 200px;
    min-width: 150px;
    padding: 8px 12px;
    font-size: 13.5px;
    font-family: inherit;
    border: 1px solid rgba(var(--overlay), 0.16);
    border-radius: 10px;
    background: rgba(var(--overlay), 0.06);
    color: var(--text);
    outline: none;
    transition: border-color 0.2s, box-shadow 0.2s;
}
.totp-vault-form input[type="password"]:focus {
    border-color: var(--primary);
    box-shadow: 0 0 0 3px rgba(var(--primary-rgb), 0.18);
}
.totp-vault .hint-text { margin-top: 6px; }
.totp-vault .hint-text code {
    padding: 1px 5px;
    border-radius: 4px;
    background: rgba(var(--overlay), 0.10);
    font-size: 11px;
}
.totp-vault .status { margin-top: 8px; }

/* display 类样式会盖掉 UA 的 [hidden]，这里显式兜底 */
.totp-pane[hidden],
.totp-list-head[hidden],
.totp-empty[hidden],
.totp-vault-state[hidden] { display: none; }

/* 确认弹窗（美化版，替代原生 confirm） */
.confirm-overlay {
    position: fixed;
    inset: 0;
    background: rgba(0, 0, 0, 0.55);
    backdrop-filter: blur(4px);
    -webkit-backdrop-filter: blur(4px);
    display: flex;
    align-items: center;
    justify-content: center;
    z-index: 2100;
    animation: fadeIn 0.2s ease;
    padding: 24px;
}
.confirm-overlay[hidden] { display: none !important; }

.confirm-box {
    width: 100%;
    max-width: 420px;
    background: var(--card, #1c1f2b);
    border: 1px solid rgba(255, 255, 255, 0.08);
    border-radius: 16px;
    box-shadow: 0 24px 64px rgba(0, 0, 0, 0.45);
    padding: 24px 24px 20px;
    animation: fadeSlideUp 0.25s ease;
}
.confirm-head {
    display: flex;
    align-items: center;
    gap: 12px;
    margin-bottom: 12px;
}
.confirm-icon {
    flex: 0 0 auto;
    width: 38px;
    height: 38px;
    border-radius: 50%;
    display: flex;
    align-items: center;
    justify-content: center;
    background: rgba(239, 68, 68, 0.14);
    color: #ef4444;
}
.confirm-icon svg { width: 20px; height: 20px; }
.confirm-title {
    font-size: 16px;
    font-weight: 700;
    color: var(--text);
}
.confirm-body {
    font-size: 14px;
    line-height: 1.65;
    color: var(--text-secondary);
}
.confirm-body b { color: var(--text); font-weight: 600; }
.confirm-body .confirm-warn {
    display: block;
    margin-top: 10px;
    padding: 10px 12px;
    border-radius: 10px;
    background: rgba(245, 158, 11, 0.12);
    border: 1px solid rgba(245, 158, 11, 0.22);
    color: #f59e0b;
    font-size: 13px;
}
.confirm-actions {
    display: flex;
    justify-content: flex-end;
    gap: 10px;
    margin-top: 20px;
}
.confirm-actions .btn {
    padding: 9px 18px;
    font-size: 14px;
    border-radius: 10px;
}
.confirm-actions .btn-danger {
    background: #ef4444;
    border-color: #ef4444;
    color: #fff;
}
.confirm-actions .btn-danger:hover { background: #dc2626; border-color: #dc2626; }
.confirm-actions .btn-ghost {
    background: transparent;
    border-color: rgba(255, 255, 255, 0.16);
    color: var(--text-secondary);
}
.confirm-actions .btn-ghost:hover { background: rgba(255, 255, 255, 0.06); color: var(--text); }

.prompt-input {
    width: 100%;
    margin-top: 14px;
    padding: 11px 14px;
    font-size: 14px;
    border: 1px solid rgba(255, 255, 255, 0.16);
    border-radius: 10px;
    background: rgba(var(--overlay), 0.05);
    color: var(--text);
    outline: none;
    transition: border-color 0.2s, box-shadow 0.2s;
}
.prompt-input:focus {
    border-color: var(--primary);
    box-shadow: 0 0 0 3px rgba(var(--primary-rgb), 0.18);
}

@media (max-width: 760px) {
    .totp-row-3 { grid-template-columns: repeat(2, minmax(0, 1fr)); }
    .totp-item { flex-wrap: wrap; gap: 10px; padding-bottom: 20px; }
    .totp-item-info { flex: 1 1 100%; }
    .totp-item-code { font-size: 26px; }
}
@media (max-width: 480px) {
    .totp-row-3 { grid-template-columns: 1fr; }
    .totp-item-code { font-size: 24px; letter-spacing: 2px; }
    .totp-item-side { flex: 1 1 100%; justify-content: flex-end; }
}

/* =================================================================
 *  留言板（公开）
 * ================================================================= */
.board-compose {
    display: flex;
    flex-direction: column;
    gap: 12px;
    margin: 20px 0;
    padding: 18px;
    background: rgba(var(--overlay), 0.04);
    border: 1px solid var(--border, rgba(255, 255, 255, 0.1));
    border-radius: 14px;
}

.board-compose input[type="text"],
.board-compose textarea {
    width: 100%;
    padding: 11px 14px;
    font-size: 14px;
    line-height: 1.6;
    border-radius: 10px;
    border: 1px solid var(--border, rgba(255, 255, 255, 0.15));
    background: var(--input-bg, rgba(255, 255, 255, 0.06));
    color: var(--text, #fff);
    outline: none;
    resize: vertical;
    font-family: inherit;
    transition: border-color 0.2s, box-shadow 0.2s;
}

.board-compose input[type="text"] { max-width: 320px; }

.board-compose input[type="text"]:focus,
.board-compose textarea:focus {
    border-color: var(--primary);
    box-shadow: 0 0 0 3px rgba(var(--primary-rgb), 0.25);
}

.board-compose-foot {
    display: flex;
    align-items: center;
    gap: 12px;
}

.board-compose-foot .spacer { flex: 1; }

.board-count {
    font-size: 12px;
    color: var(--text-muted, rgba(255, 255, 255, 0.6));
}

.board-captcha-row {
    display: flex;
    align-items: center;
    gap: 10px;
    flex-wrap: wrap;
}

.board-captcha-img {
    width: 132px;
    height: 44px;
    border-radius: 8px;
    border: 1px solid var(--border, rgba(255, 255, 255, 0.15));
    cursor: pointer;
    object-fit: cover;
    flex-shrink: 0;
    background: rgba(255, 255, 255, 0.4);
    opacity: 1;
    transition: opacity 0.2s;
}

.board-captcha-img.loading { opacity: 0.45; }

.board-captcha-row input[type="text"] {
    flex: 0 1 140px;
    min-width: 96px;
    padding: 8px 12px;
    font-size: 14px;
    letter-spacing: 3px;
    text-transform: uppercase;
}

.board-captcha-refresh {
    background: none;
    border: none;
    padding: 4px 2px;
    color: var(--text-muted, rgba(255, 255, 255, 0.6));
    font-size: 12px;
    cursor: pointer;
    white-space: nowrap;
}

.board-captcha-refresh:hover {
    color: var(--primary);
    text-decoration: underline;
}

.board-list {
    list-style: none;
    margin: 0;
    padding: 0;
    display: flex;
    flex-direction: column;
    gap: 12px;
}

.board-item {
    padding: 14px 16px;
    background: rgba(var(--overlay), 0.04);
    border: 1px solid var(--border, rgba(255, 255, 255, 0.08));
    border-radius: 12px;
}

.board-item-head {
    display: flex;
    align-items: baseline;
    justify-content: space-between;
    gap: 12px;
    margin-bottom: 6px;
}

.board-item-name {
    font-size: 14px;
    font-weight: 600;
    color: var(--primary);
    word-break: break-all;
}

.board-item-time {
    flex-shrink: 0;
    font-size: 12px;
    color: var(--text-muted, rgba(255, 255, 255, 0.55));
}

.board-item-content {
    font-size: 14px;
    line-height: 1.7;
    color: var(--text, #fff);
    white-space: pre-wrap;
    word-break: break-word;
}

.board-manage-link {
    margin-top: 18px;
    text-align: right;
}

.board-manage-link a {
    font-size: 12px;
    color: var(--text-muted, rgba(255, 255, 255, 0.45));
    text-decoration: none;
}

.board-manage-link a:hover {
    color: var(--primary);
    text-decoration: underline;
}

/* =================================================================
 *  后台管理（/admin）
 * ================================================================= */
.admin-page .admin-wrap {
    position: relative;
    z-index: 1;
    max-width: 900px;
    margin: 0 auto;
    padding: 24px 16px 60px;
}

.admin-head {
    display: flex;
    align-items: center;
    justify-content: space-between;
    gap: 14px;
    margin-bottom: 20px;
}

.admin-brand {
    display: flex;
    align-items: center;
    gap: 10px;
    color: var(--text, #fff);
    text-decoration: none;
    font-size: 16px;
    font-weight: 700;
}

.admin-brand:hover { color: var(--text, #fff); }

.admin-card {
    background: rgba(var(--overlay), 0.06);
    backdrop-filter: blur(20px);
    -webkit-backdrop-filter: blur(20px);
    border: 1px solid rgba(var(--overlay), 0.10);
    border-radius: var(--radius);
    padding: 26px;
    box-shadow: 0 8px 32px rgba(0, 0, 0, 0.2);
}

[data-theme="light"] .admin-card {
    background: rgba(255, 255, 255, 0.7);
    box-shadow: 0 2px 16px rgba(0, 0, 0, 0.06);
}

.admin-card-title {
    font-size: 18px;
    font-weight: 700;
    margin-bottom: 4px;
}

.admin-card-desc {
    font-size: 13px;
    color: var(--text-secondary);
    margin-bottom: 16px;
}

.admin-card .status { margin-top: 14px; }

.admin-list {
    list-style: none;
    margin: 0;
    padding: 0;
    display: flex;
    flex-direction: column;
    gap: 12px;
}

.admin-msg {
    border: 1px solid var(--border, rgba(255, 255, 255, 0.1));
    border-radius: 12px;
    padding: 12px 14px;
    background: rgba(var(--overlay), 0.04);
}

.admin-msg-head {
    display: flex;
    align-items: center;
    flex-wrap: wrap;
    gap: 8px 14px;
    margin-bottom: 8px;
    font-size: 12px;
    color: var(--text-muted, rgba(255, 255, 255, 0.55));
}

.admin-msg-name {
    font-weight: 600;
    font-size: 13px;
    color: var(--primary);
}

.admin-msg-ip {
    font-family: ui-monospace, SFMono-Regular, Menlo, Consolas, monospace;
}

.admin-msg-body {
    font-size: 14px;
    line-height: 1.7;
    color: var(--text, #fff);
    white-space: pre-wrap;
    word-break: break-word;
}

.admin-msg-actions {
    margin-top: 10px;
    display: flex;
    justify-content: flex-end;
    gap: 8px;
}

.admin-list-toolbar {
    display: flex;
    align-items: center;
    justify-content: space-between;
    gap: 12px;
    margin-bottom: 12px;
}

.admin-login-card { max-width: 440px; margin: 8vh auto 0; }

.admin-login-card input[type="password"] {
    width: 100%;
    padding: 12px 14px;
    font-size: 15px;
    border-radius: 10px;
    border: 1px solid var(--border, rgba(255, 255, 255, 0.15));
    background: var(--input-bg, rgba(255, 255, 255, 0.06));
    color: var(--text, #fff);
    outline: none;
    transition: border-color 0.2s, box-shadow 0.2s;
}

.admin-login-card input[type="password"]:focus {
    border-color: var(--primary);
    box-shadow: 0 0 0 3px rgba(var(--primary-rgb), 0.25);
}

.admin-login-actions {
    margin-top: 16px;
    display: flex;
    justify-content: flex-end;
    gap: 8px;
}

.admin-login-hint {
    margin-top: 12px;
    font-size: 12px;
    color: var(--text-muted, rgba(255, 255, 255, 0.5));
}
/* =================================================================
 *  在线网页代理
 *  顶部一条仿浏览器地址栏（后退 / 前进 / 刷新 / 输入框 / 打开），
 *  下面整块是 iframe 展示区，加载时顶部跑一条不确定的进度条。
 * ================================================================= */
.proxy-bar {
    display: flex;
    align-items: center;
    gap: 8px;
    flex-wrap: wrap;
    margin-bottom: 14px;
}

.proxy-nav-btn {
    width: 38px;
    height: 38px;
    display: inline-flex;
    align-items: center;
    justify-content: center;
    flex-shrink: 0;
    border: 1px solid rgba(var(--overlay), 0.16);
    border-radius: 10px;
    background: rgba(var(--overlay), 0.06);
    color: var(--text);
    cursor: pointer;
    transition: background 0.2s, border-color 0.2s, opacity 0.2s;
}

.proxy-nav-btn:hover:not(:disabled) {
    background: rgba(var(--overlay), 0.12);
    border-color: rgba(var(--overlay), 0.28);
}

.proxy-nav-btn:disabled { opacity: 0.35; cursor: not-allowed; }

.proxy-url-input {
    flex: 1 1 240px;
    min-width: 180px;
    height: 38px;
    padding: 0 14px;
    font-size: 14px;
    border-radius: 10px;
    border: 1px solid var(--border, rgba(255, 255, 255, 0.15));
    background: var(--input-bg, rgba(255, 255, 255, 0.06));
    color: var(--text);
    outline: none;
    transition: border-color 0.2s, box-shadow 0.2s;
}

.proxy-url-input:focus {
    border-color: var(--primary);
    box-shadow: 0 0 0 3px rgba(var(--primary-rgb), 0.25);
}

.proxy-frame-wrap {
    position: relative;
    border: 1px solid rgba(var(--overlay), 0.10);
    border-radius: var(--radius-sm);
    overflow: hidden;
    /* 被代理的页面基本都是浅色底，容器也给白底，避免闪黑边 */
    background: #fff;
}

.proxy-frame {
    display: block;
    width: 100%;
    height: 68vh;
    min-height: 380px;
    border: 0;
    background: #fff;
}

.proxy-placeholder {
    padding: 52px 24px;
    text-align: center;
    color: var(--text-secondary);
    display: flex;
    flex-direction: column;
    align-items: center;
    gap: 10px;
}

.proxy-placeholder > svg { color: var(--primary); opacity: 0.75; }
.proxy-placeholder p { font-size: 14px; }
.proxy-placeholder .hint-text { max-width: 520px; line-height: 1.7; }

.proxy-quick {
    display: flex;
    flex-wrap: wrap;
    justify-content: center;
    gap: 8px;
    margin-top: 8px;
}

.proxy-quick-btn {
    padding: 6px 14px;
    font-size: 13px;
    border-radius: 999px;
    border: 1px solid rgba(var(--overlay), 0.18);
    background: rgba(var(--overlay), 0.05);
    color: var(--text);
    cursor: pointer;
    transition: background 0.2s, border-color 0.2s, transform 0.2s;
}

.proxy-quick-btn:hover {
    background: rgba(var(--primary-rgb), 0.14);
    border-color: rgba(var(--primary-rgb), 0.45);
    transform: translateY(-1px);
}

.proxy-loading {
    position: absolute;
    top: 0;
    left: 0;
    right: 0;
    height: 3px;
    overflow: hidden;
    background: rgba(var(--overlay), 0.08);
}

.proxy-loading-bar {
    width: 38%;
    height: 100%;
    background: linear-gradient(90deg, var(--primary), var(--accent));
    animation: proxy-progress 1.1s ease-in-out infinite;
}

@keyframes proxy-progress {
    0%   { transform: translateX(-110%); }
    100% { transform: translateX(360%); }
}

@media (max-width: 640px) {
    .proxy-frame { height: 76vh; min-height: 320px; }
    .proxy-bar .btn { --bs-btn-padding-x: 0.9rem; }
}

/* =================================================================
 *  TOOL — 文件内容比对（git diff 风格）
 *  配色沿用 diff 的语义色：新增=绿、删除=红，深浅主题各自一套。
 * ================================================================= */
:root {
    --diff-add-bg: rgba(63, 185, 80, 0.16);
    --diff-add-line: rgba(63, 185, 80, 0.45);
    --diff-add-fg: #56d364;
    --diff-del-bg: rgba(248, 81, 73, 0.14);
    --diff-del-line: rgba(248, 81, 73, 0.42);
    --diff-del-fg: #ff9a94;
}
[data-theme="light"] {
    --diff-add-bg: #e6ffec;
    --diff-add-line: #abf2bc;
    --diff-add-fg: #1a7f37;
    --diff-del-bg: #ffebe9;
    --diff-del-line: #ffc9c4;
    --diff-del-fg: #b42318;
}

.diff-mode,
.diff-view-toggle {
    display: inline-flex;
    gap: 4px;
    padding: 4px;
    border-radius: 999px;
    background: rgba(var(--overlay), 0.06);
    border: 1px solid rgba(var(--overlay), 0.10);
}

.diff-mode { margin-bottom: 18px; }

/* 这些容器自带 display（grid / flex），会盖过 UA 的 [hidden]，
   JS 用 .hidden 切换显隐时必须显式再声明一次 */
.diff-sources[hidden],
.diff-file-chip[hidden],
.diff-result[hidden] { display: none; }

.diff-mode-btn,
.diff-view-btn {
    border: 0;
    background: transparent;
    color: var(--text-secondary);
    padding: 6px 16px;
    border-radius: 999px;
    font-size: 13px;
    font-weight: 500;
    cursor: pointer;
    transition: background 0.2s, color 0.2s;
}

.diff-view-btn { padding: 5px 14px; font-size: 12.5px; }

.diff-mode-btn:hover,
.diff-view-btn:hover { color: var(--text); }

.diff-mode-btn.is-active,
.diff-view-btn.is-active {
    background: var(--primary);
    color: #fff;
}

/* 左右两个输入区 */
.diff-sources {
    display: grid;
    grid-template-columns: 1fr 1fr;
    gap: 16px;
}

.diff-source { min-width: 0; }

.diff-source-head {
    display: flex;
    align-items: center;
    gap: 8px;
    margin-bottom: 8px;
    min-height: 22px;
}

.diff-source-tag {
    padding: 1px 10px;
    border-radius: 999px;
    font-size: 11px;
    font-weight: 600;
}

.diff-source-tag.is-left { background: var(--diff-del-bg); color: var(--diff-del-fg); }
.diff-source-tag.is-right { background: var(--diff-add-bg); color: var(--diff-add-fg); }

.diff-source-meta {
    font-size: 11px;
    color: var(--text-secondary);
    opacity: 0.75;
    overflow: hidden;
    text-overflow: ellipsis;
    white-space: nowrap;
}

.diff-drop { padding: 26px 14px; }

.diff-file-chip {
    display: flex;
    align-items: center;
    gap: 8px;
    padding: 10px 12px;
    border-radius: var(--radius-sm);
    border: 1px solid rgba(var(--primary-rgb), 0.35);
    background: rgba(var(--primary-rgb), 0.08);
}

.diff-file-chip-name {
    flex: 1;
    min-width: 0;
    font-size: 13px;
    overflow: hidden;
    text-overflow: ellipsis;
    white-space: nowrap;
}

.diff-file-chip-clear {
    flex: 0 0 auto;
    width: 22px;
    height: 22px;
    line-height: 1;
    border: 0;
    border-radius: 50%;
    background: rgba(var(--overlay), 0.12);
    color: var(--text-secondary);
    font-size: 15px;
    cursor: pointer;
}
.diff-file-chip-clear:hover { background: var(--diff-del-bg); color: var(--diff-del-fg); }

.diff-textarea {
    width: 100%;
    min-height: 170px;
    resize: vertical;
    padding: 10px 12px;
    border-radius: var(--radius-sm);
    border: 1px solid rgba(var(--overlay), 0.16);
    background: var(--input-bg);
    color: var(--text);
    font-family: ui-monospace, SFMono-Regular, Menlo, Consolas, monospace;
    font-size: 12.5px;
    line-height: 1.55;
    outline: none;
}
.diff-textarea:focus { border-color: var(--primary); }

/* 选项条 */
.diff-options {
    display: flex;
    flex-wrap: wrap;
    align-items: center;
    justify-content: space-between;
    gap: 10px 20px;
    margin-top: 18px;
}

.diff-options-flags { display: flex; flex-wrap: wrap; gap: 4px 24px; }
.diff-options-flags .checkbox { margin-top: 0; }

.diff-actions {
    display: flex;
    flex-wrap: wrap;
    gap: 10px;
    margin-top: 16px;
}

/* 结果 */
.diff-result { margin-top: 20px; animation: fadeSlideUp 0.35s ease; }

.diff-summary {
    display: flex;
    flex-wrap: wrap;
    align-items: center;
    gap: 8px;
    margin-bottom: 12px;
}

.diff-stat {
    padding: 2px 10px;
    border-radius: 999px;
    font-size: 12px;
    font-weight: 600;
}

.diff-stat-add { background: var(--diff-add-bg); color: var(--diff-add-fg); }
.diff-stat-del { background: var(--diff-del-bg); color: var(--diff-del-fg); }
.diff-stat-mod { background: rgba(var(--primary-rgb), 0.14); color: var(--primary); }
.diff-stat-same { background: rgba(var(--overlay), 0.08); color: var(--text-secondary); }

.diff-summary-files {
    font-size: 12px;
    color: var(--text-secondary);
    opacity: 0.8;
    margin-left: auto;
    overflow: hidden;
    text-overflow: ellipsis;
    white-space: nowrap;
    max-width: 100%;
}

.diff-output {
    max-height: 62vh;
    overflow: auto;
    border: 1px solid rgba(var(--overlay), 0.10);
    border-radius: var(--radius-sm);
    background: rgba(var(--overlay), 0.03);
    font-family: ui-monospace, SFMono-Regular, Menlo, Consolas, monospace;
    font-size: 12.5px;
    line-height: 1.55;
}

.diff-table { width: 100%; }

/* 并排视图 */
.diff-row { display: flex; align-items: stretch; }

.diff-cell {
    display: flex;
    flex: 1 1 0;
    min-width: 0;
    padding: 0 8px 0 0;
}

.diff-cell-l { border-right: 1px solid rgba(var(--overlay), 0.10); }

.diff-no {
    flex: 0 0 auto;
    width: 46px;
    padding: 0 8px 0 6px;
    text-align: right;
    color: var(--text-secondary);
    opacity: 0.55;
    user-select: none;
    font-variant-numeric: tabular-nums;
}

.diff-code {
    flex: 1 1 auto;
    min-width: 0;
    white-space: pre-wrap;
    word-break: break-word;
    color: var(--text);
}

.diff-row-del .diff-cell-l,
.diff-row-mod .diff-cell-l {
    background: var(--diff-del-bg);
    box-shadow: inset 3px 0 0 var(--diff-del-line);
}
.diff-row-add .diff-cell-r,
.diff-row-mod .diff-cell-r {
    background: var(--diff-add-bg);
    box-shadow: inset 3px 0 0 var(--diff-add-line);
}

.diff-cell-empty { background: rgba(var(--overlay), 0.04); }

/* 行内改动（字符级）高亮 */
.diff-cell-l .diff-seg-mod { background: var(--diff-del-line); border-radius: 2px; }
.diff-cell-r .diff-seg-mod { background: var(--diff-add-line); border-radius: 2px; }
/* 未做字符级比对时，整行按改动强调 */
.diff-whole { font-weight: 500; }

/* 统一视图 */
.diff-uline { display: flex; align-items: stretch; }
.diff-uline-add {
    background: var(--diff-add-bg);
    box-shadow: inset 3px 0 0 var(--diff-add-line);
}
.diff-uline-del {
    background: var(--diff-del-bg);
    box-shadow: inset 3px 0 0 var(--diff-del-line);
}
.diff-uline-hunk {
    padding: 2px 12px;
    background: rgba(var(--primary-rgb), 0.10);
    color: var(--text-secondary);
    font-size: 12px;
}
.diff-uline .diff-mark {
    flex: 0 0 auto;
    width: 15px;
    text-align: center;
    color: var(--text-secondary);
    opacity: 0.8;
    user-select: none;
}

.diff-identical,
.diff-truncated {
    padding: 14px 16px;
    font-size: 13px;
    color: var(--text-secondary);
    text-align: center;
}
.diff-identical { color: var(--diff-add-fg); font-weight: 600; }
.diff-truncated { border-top: 1px solid rgba(var(--overlay), 0.08); }

@media (max-width: 640px) {
    .diff-sources { grid-template-columns: 1fr; }
    .diff-summary-files { margin-left: 0; }
    .diff-options { flex-direction: column; align-items: flex-start; }
}

/* =================================================================
 *  RDP 远程桌面
 *  上半部分是连接表单，下半部分是画面区：画面本体是 guacamole-common-js
 *  动态插入的 canvas（远端分辨率 = canvas 尺寸），容器只负责尺寸、
 *  滚动与聚焦态（键盘事件要落在容器上才转发给远端）。
 * ================================================================= */
/* 访问口令门（RDP / SSH 共用）：未解锁时表单整体收起，只显示这一块 */
.remote-gate {
    display: flex;
    align-items: flex-start;
    gap: 14px;
    margin: 22px 0 4px;
    padding: 16px 18px;
    border-radius: var(--radius-sm);
    border: 1px solid rgba(var(--primary-rgb), 0.28);
    background: rgba(var(--primary-rgb), 0.10);
}

.remote-gate-icon {
    flex: 0 0 auto;
    display: flex;
    align-items: center;
    justify-content: center;
    width: 42px;
    height: 42px;
    border-radius: 50%;
    background: rgba(var(--primary-rgb), 0.20);
    color: var(--primary);
}

.remote-gate-body { flex: 1 1 auto; min-width: 0; }

.remote-gate-title {
    font-size: 14px;
    font-weight: 600;
    color: var(--text);
}

.remote-gate-hint {
    margin: 6px 0 0;
    font-size: 12px;
    line-height: 1.7;
    color: var(--text-secondary);
}

.remote-gate-form {
    display: flex;
    align-items: center;
    gap: 8px;
    flex-wrap: wrap;
    margin-top: 12px;
}

.remote-gate-form input {
    flex: 0 1 240px;
    min-width: 160px;
    padding: 10px 13px;
    font-size: 14px;
    font-family: inherit;
    border-radius: 10px;
    border: 1px solid rgba(var(--overlay), 0.14);
    background: rgba(var(--overlay), 0.06);
    color: var(--text);
    outline: none;
    transition: border-color 0.2s, box-shadow 0.2s;
}

.remote-gate-form input:focus {
    border-color: var(--primary);
    box-shadow: 0 0 0 3px rgba(var(--primary-rgb), 0.22);
}

.remote-gate-msg {
    margin: 8px 0 0;
    font-size: 12.5px;
    color: var(--text-secondary);
}

.remote-gate-msg.error { color: #f87171; }
.remote-gate-msg.warn { color: #fbbf24; }

/* display 类样式（grid / flex）会盖掉 UA 的 [hidden]，这里显式兜底 */
.remote-gate[hidden],
.rdp-form[hidden],
.rdp-options[hidden],
.ssh-key[hidden] { display: none; }

.rdp-form {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(210px, 1fr));
    gap: 14px 18px;
    margin: 22px 0 4px;
}

.rdp-field {
    display: flex;
    flex-direction: column;
    gap: 6px;
}

.rdp-field label {
    font-size: 13px;
    font-weight: 600;
    color: var(--text);
}

.rdp-optional {
    margin-left: 6px;
    font-size: 12px;
    font-weight: 400;
    color: var(--text-secondary);
}

.rdp-field input,
.rdp-field select,
.rdp-field textarea {
    width: 100%;
    padding: 11px 13px;
    font-size: 14px;
    border-radius: 10px;
    border: 1px solid rgba(var(--overlay), 0.14);
    background: rgba(var(--overlay), 0.06);
    color: var(--text);
    outline: none;
    /* 原生下拉弹层跟随页面深浅色，否则深色页面上会弹出白色的列表 */
    color-scheme: dark light;
    transition: border-color 0.2s, box-shadow 0.2s;
}

.rdp-field input:focus,
.rdp-field select:focus,
.rdp-field textarea:focus {
    border-color: var(--primary);
    box-shadow: 0 0 0 3px rgba(var(--primary-rgb), 0.22);
}

/* 报错文案是多行的（guacd 原文 + 人话提示），要按换行渲染 */
#rdpStatus,
#sshStatus { white-space: pre-line; }

/* 端口只有 4 位数，占满一整格太浪费 */
.rdp-field-port { max-width: 130px; }

.rdp-field-submit { justify-content: flex-end; }

.rdp-field-submit .btn { width: 100%; justify-content: center; }

.rdp-options {
    display: flex;
    flex-wrap: wrap;
    gap: 8px 22px;
    margin: 14px 0 2px;
}

.rdp-screen {
    margin-top: 18px;
    border: 1px solid rgba(var(--overlay), 0.12);
    border-radius: 14px;
    overflow: hidden;
    background: #000;
}

.rdp-toolbar {
    display: flex;
    flex-wrap: wrap;
    align-items: center;
    gap: 8px;
    padding: 8px 12px;
    background: rgba(var(--overlay), 0.06);
    border-bottom: 1px solid rgba(var(--overlay), 0.10);
}

.rdp-toolbar .spacer { flex: 1; }

.rdp-target {
    font-family: ui-monospace, SFMono-Regular, Menlo, Consolas, monospace;
    font-size: 12px;
    color: var(--text-secondary);
}

/* 画面容器：远端分辨率比这里大时滚动，不做拉伸变形 */
.rdp-display {
    display: flex;
    width: 100%;
    min-height: 240px;
    max-height: 78vh;
    overflow: auto;
    background: #000;
    outline: none;
}

.rdp-display:focus {
    box-shadow: inset 0 0 0 2px rgba(var(--primary-rgb), 0.55);
}

/* guacamole 插入的一层 wrapper：用 margin:auto 做「安全居中」——
   有剩余空间时上下左右都居中，画面比容器大时 auto 边距归零，可以正常滚动
   （直接 align-items:center 会让溢出部分滚不到） */
.rdp-display > div {
    margin: auto;
}

.rdp-display canvas { display: block; }

.rdp-hint {
    margin: 0;
    padding: 8px 12px;
    font-size: 12px;
    line-height: 1.6;
    color: var(--text-secondary);
    background: rgba(var(--overlay), 0.04);
}

/* 全屏：容器铺满，画面区吃掉剩余空间 */
.rdp-screen:fullscreen {
    display: flex;
    flex-direction: column;
    border: none;
    border-radius: 0;
}

.rdp-screen:fullscreen .rdp-display {
    flex: 1;
    max-height: none;
}

/* 全屏时把提示条收掉，画面能多占一行高度 */
.rdp-screen:fullscreen .rdp-hint { display: none; }

/* 全屏工具栏 = Windows 远程桌面那条「连接栏」：贴在最上边、默认收起，
   鼠标扫到屏幕顶部（热区）或它自己时滑出，鼠标离开一会儿再收起。
   它是叠在画面上的，所以要有不透明底色，否则盖在桌面上看不清按钮。 */
.rdp-screen:fullscreen .rdp-toolbar {
    position: fixed;
    top: 0;
    left: 0;
    right: 0;
    z-index: 30;
    background: var(--nav-bg);
    backdrop-filter: blur(14px) saturate(160%);
    -webkit-backdrop-filter: blur(14px) saturate(160%);
    border-bottom: 1px solid rgba(var(--primary-rgb), 0.18);
    box-shadow: 0 6px 18px rgba(0, 0, 0, 0.35);
    transform: translateY(-100%);
    transition: transform 0.22s ease;
}

.rdp-screen:fullscreen.rdp-bar-open .rdp-toolbar {
    transform: translateY(0);
}

@media (max-width: 640px) {
    .rdp-field-port { max-width: none; }
    .rdp-display { max-height: 62vh; }
}

/* =================================================================
 *  SSH 终端
 *  表单与画面区整套复用上面的 .rdp-* 样式（结构与交互一样，只是没有桌面
 *  操作），这里只补终端自己的两处：私钥折叠块，以及终端画布的等宽观感。
 * ================================================================= */
.ssh-key {
    margin: 16px 0 2px;
    border: 1px solid rgba(var(--overlay), 0.12);
    border-radius: 12px;
    padding: 10px 14px 12px;
    background: rgba(var(--overlay), 0.03);
}

.ssh-key summary {
    cursor: pointer;
    font-size: 13px;
    font-weight: 600;
    color: var(--text);
}

.ssh-key summary:hover { color: var(--primary); }

.ssh-key[open] summary { margin-bottom: 4px; }

/* 私钥长这样：PEM 一行行粘进来，等宽字体 + 可纵向拉伸，一眼能看出是不是粘全了 */
.ssh-key-field { grid-column: 1 / -1; }

.ssh-key-field textarea {
    font-family: ui-monospace, SFMono-Regular, Menlo, Consolas, monospace;
    font-size: 12px;
    line-height: 1.5;
    resize: vertical;
}

.ssh-key-hint {
    margin: 8px 0 0;
    font-size: 12px;
    line-height: 1.6;
    color: var(--text-secondary);
}
