:root{--c-primary:#0f4c3a;--c-accent:#c9a227;--c-bg:#0e1512;--c-card:#16211d;--c-text:#e8efe9;--c-dim:#93a49b;--c-danger:#c8503f;font-family:"PingFang SC","Microsoft YaHei",system-ui,sans-serif;color:var(--c-text);background:var(--c-bg)}*{box-sizing:border-box}body{margin:0;background:var(--c-bg)}button,input,select,textarea{font:inherit}.app-shell{display:grid;grid-template-columns:240px 1fr;min-height:100vh}.sidebar{background:#101a16;border-right:1px solid #26362e;padding:24px 16px;display:flex;flex-direction:column}.brand{font-size:21px;font-weight:700;color:#fff;margin-bottom:28px}.side-nav h3{font-size:12px;color:var(--c-dim);margin:18px 10px 7px}.nav-link{display:block;padding:10px 12px;color:var(--c-dim);text-decoration:none;border-radius:7px}.nav-link.active,.nav-link:hover{background:var(--c-primary);color:#fff}.project-picker{margin-top:auto}.main{min-width:0}.topbar{height:64px;padding:0 32px;border-bottom:1px solid #26362e;display:flex;align-items:center;justify-content:space-between}.page-content{max-width:1440px;padding:30px 32px;margin:auto}.page-title,.card-head,.card-actions{display:flex;align-items:center;justify-content:space-between;gap:12px}.page-title{margin-bottom:24px}.page-title h1{margin:0;font-size:28px}.muted{color:var(--c-dim)}.btn{border:1px solid #3b5448;border-radius:7px;padding:9px 15px;background:transparent;color:var(--c-text);cursor:pointer}.btn:hover{filter:brightness(1.15)}.btn-primary{background:var(--c-primary);border-color:#28755b}.btn-danger{background:var(--c-danger);border-color:#e27867}.btn-ghost{background:transparent}.btn-sm{padding:6px 10px;font-size:13px}.input,.select,.textarea{background:#101a16;color:var(--c-text);border:1px solid #3b5448;border-radius:6px;padding:10px;width:100%}.card-grid{display:grid;grid-template-columns:repeat(auto-fill,minmax(280px,1fr));gap:18px}.card{background:var(--c-card);border:1px solid #263d32;border-radius:10px;padding:20px}.card h3{margin:0}.card-actions{margin-top:20px}.tag{font-size:12px;padding:4px 8px;border-radius:99px;background:#29483b}.tag-ok{color:#8fe0b1;background:#163e2b}.tag-warn{color:#f4cf63;background:#453c17}.tag-err{color:#ff9a8c;background:#4b211d}.stats{margin:18px 0;color:#d1ded5}.empty{padding:70px 20px;text-align:center;border:1px dashed #3b5448;border-radius:10px;color:var(--c-dim)}.modal-shade{position:fixed;inset:0;background:#0009;display:grid;place-items:center;z-index:20}.modal{width:min(560px,calc(100vw - 32px));max-height:90vh;overflow:auto;background:#19251f;border:1px solid #456052;border-radius:12px;box-shadow:0 20px 80px #0008}.modal-wide .modal{width:min(1100px,calc(100vw - 28px))}.modal-head{display:flex;align-items:center;justify-content:space-between;padding:18px 22px;border-bottom:1px solid #30483b}.modal-head h2{margin:0}.modal-body{padding:22px}.modal-actions{display:flex;justify-content:flex-end;gap:10px;margin-top:20px}.field{display:grid;gap:6px;color:var(--c-dim);margin:10px 0}.form-grid{display:grid;grid-template-columns:1fr 1fr;gap:12px}.bar{height:9px;background:#0b100e;border-radius:9px;overflow:hidden}.bar-fill{height:100%;background:var(--c-accent);transition:width .2s}.toast-stack{position:fixed;right:20px;top:76px;z-index:40;display:grid;gap:10px}.toast{background:#20342a;border:1px solid #4a6e5a;border-radius:7px;padding:12px 16px;min-width:240px;transition:.3s}.toast-ok{border-color:#4ba472}.toast-err{border-color:#d56859}.toast-warn{border-color:#c9a227}.toast.is-out{opacity:0;transform:translateX(20px)}
.collapse{border:1px solid #30483b;border-radius:7px;margin:12px 0}.collapse-head{width:100%;text-align:left;background:transparent;color:var(--c-text);border:0;padding:12px;cursor:pointer}.collapse-body{display:none;padding:12px;border-top:1px solid #30483b}.collapse.open .collapse-body{display:block}.spinner{display:flex;align-items:center;gap:10px;color:var(--c-dim)}.spinner-ring{width:18px;height:18px;border:2px solid #567466;border-top-color:var(--c-accent);border-radius:50%;animation:spin .8s linear infinite}@keyframes spin{to{transform:rotate(360deg)}}.tabbar,.seg{display:flex;gap:4px}.tab-item,.seg-item{padding:8px 14px;background:transparent;color:var(--c-dim);border:0;cursor:pointer}.tab-item.active,.seg-item.active{color:#fff;background:var(--c-primary);border-radius:5px}.tbl{width:100%;border-collapse:collapse}.tbl th,.tbl td{padding:10px;border-bottom:1px solid #30483b;text-align:left}.paper{width:794px;max-width:100%;padding:60px 72px;background:#fff;color:#111;box-shadow:0 6px 30px #0004;margin:24px auto}.tree-dir,.tree-file{padding:8px;border-bottom:1px solid #30483b}.xl-wrap{overflow:auto;background:#fff;color:#111}.xl-sheet{border-collapse:collapse}.xl-sheet td,.xl-sheet th{border:1px solid #cbd5cf;padding:6px}.doc-tbl{border-collapse:collapse}.doc-tbl td,.doc-tbl th{border:1px solid #555;padding:6px}@media(max-width:1100px){.app-shell{grid-template-columns:68px 1fr}.sidebar{padding:20px 8px}.brand{font-size:0}.brand:first-letter{font-size:20px}.side-nav h3,.project-picker{display:none}.nav-link{font-size:0;text-align:center}.nav-link::first-letter{font-size:18px}}@media(max-width:720px){.app-shell{display:block}.sidebar{display:none}.topbar{padding:0 16px}.page-content{padding:20px 16px}.form-grid{grid-template-columns:1fr}.modal{max-height:95vh}}@media(prefers-reduced-motion:reduce){*,*::before,*::after{animation-duration:.01ms!important;transition-duration:.01ms!important}}

/* ============================================================
   以下为查看器与文件树的样式。
   ★ 查看器内部一律白底黑字：报表的底色/边框/红色负数在深色底上会失真，
     "像纸"是这一块唯一的验收标准。
   ============================================================ */

/* —— 上传区 —— */
.upload-panel{margin-bottom:22px}
.dropzone{border:2px dashed #3b5448;border-radius:var(--r-md,10px);padding:26px;text-align:center;color:var(--c-dim);transition:border-color .15s,background .15s}
.dropzone.over{border-color:var(--c-accent);background:rgba(201,162,39,.08);color:var(--c-text)}
.dropzone p{margin:.2em 0}
.upload-actions{display:flex;align-items:center;gap:10px;flex-wrap:wrap;margin-top:14px}
.file-input{position:absolute;width:1px;height:1px;opacity:0;pointer-events:none}
.upload-actions .bar{flex:1;min-width:120px}
.pending-tree{margin-top:16px}
.pending-head{display:flex;justify-content:space-between;align-items:center;padding:8px 0;border-bottom:1px solid #30483b}
.pending-list{max-height:260px;overflow:auto;margin-top:6px}
.pending-row{display:grid;grid-template-columns:1fr auto auto;gap:10px;align-items:center;padding:5px 2px;border-bottom:1px solid var(--c-line-soft,#1e2b25)}
.pending-path{font-family:var(--font-mono,monospace);font-size:12.5px;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}

/* —— 进度条 —— */
.bar{position:relative;height:8px;background:#0d1512;border:1px solid #2b3f36;border-radius:99px;overflow:hidden}
.bar-fill{height:100%;width:0;background:linear-gradient(90deg,var(--c-primary,#0f4c3a),var(--c-accent,#c9a227));transition:width .25s}

/* —— 文件树 —— */
.tree{font-size:13.5px}
.tree-row{display:grid;grid-template-columns:auto 1fr auto auto auto;gap:10px;align-items:center;padding:7px 8px;border-bottom:1px solid var(--c-line-soft,#1e2b25)}
.tree-row:hover{background:var(--c-card-lift,#1b2823)}
.tree-dir{cursor:pointer;font-weight:600}
.tree-caret{width:14px;color:var(--c-dim);text-align:center}
.tree-name{overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.tree-meta{font-size:12px;white-space:nowrap}
.tree-actions{display:flex;gap:5px;opacity:.35;transition:opacity .15s}
.tree-row:hover .tree-actions,.tree-actions:focus-within{opacity:1}
.tree-node:not(.open)>.tree-children{display:none}
.tree-icon{width:20px;height:20px;line-height:20px;text-align:center;border-radius:4px;font-size:11px;font-weight:700;color:#fff;background:#3d534a}
.ft-sheet{background:#1f7a4d}.ft-doc{background:#2a5c9a}.ft-pdf{background:#a8402f}.ft-img{background:#7a5aa8}
.tree-badges{display:flex;gap:4px}
.badge{border:0;border-radius:4px;padding:2px 7px;font-size:11px;font-weight:700;color:#fff;cursor:pointer}
.badge-xlsx{background:#1f7a4d}.badge-docx{background:#2a5c9a}
.badge:hover{filter:brightness(1.2)}
/* —— 查看器外壳 —— */
.modal-shade{position:fixed;inset:0;background:rgba(6,10,9,.72);display:flex;align-items:center;justify-content:center;z-index:80;padding:20px}
.modal{background:var(--c-card,#16211d);border:1px solid #2b3f36;border-radius:var(--r-lg,14px);box-shadow:var(--sh-2);max-width:1180px;width:100%;max-height:92vh;display:flex;flex-direction:column}
.modal-wide .modal{max-width:96vw;height:92vh}
.modal-head{display:flex;align-items:center;justify-content:space-between;gap:12px;padding:14px 18px;border-bottom:1px solid #2b3f36}
.modal-head h2{margin:0;font-size:15px}
.modal-body{padding:16px 18px;overflow:auto;flex:1;min-height:0}
.modal-actions{display:flex;justify-content:flex-end;gap:10px;margin-top:16px}
.viewer-body{display:flex;flex-direction:column;height:100%;min-height:0}
.viewer-tools{display:flex;align-items:center;gap:12px;padding-bottom:10px;border-bottom:1px solid #2b3f36;flex-wrap:wrap}
.viewer-name{flex:1;color:var(--c-dim);font-size:12.5px;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}
.viewer-subtools{display:flex;align-items:center;gap:8px;padding:8px 0;flex-wrap:wrap}
.viewer-stage,.viewer-content{flex:1;min-height:0;display:flex;flex-direction:column}
.viewer-text{flex:1;overflow:auto;background:#fff;color:#111;padding:20px;margin:0;font-family:var(--font-mono,monospace);font-size:12.5px;white-space:pre-wrap}
.viewer-image-wrap{flex:1;overflow:hidden;background:#f4f5f4;display:flex;align-items:center;justify-content:center;cursor:grab;touch-action:none}
.viewer-image{max-width:100%;max-height:100%;transform-origin:center;user-select:none}

/* —— Word / Markdown 文档：A4 纸张 —— */
.paper{width:794px;max-width:100%;min-height:400px;padding:60px 72px;background:#fff;color:#111;box-shadow:0 6px 30px rgba(0,0,0,.28);margin:20px auto;line-height:1.8;overflow-wrap:break-word}
.viewer-content>.paper{margin-top:12px}
.viewer-content{overflow:auto;background:#2a3833}
.paper h1{font-size:24px;text-align:center;margin:0 0 1.2em}
.paper h2{font-size:18px;margin:1.6em 0 .6em;padding-bottom:.25em;border-bottom:1px solid #ddd}
.paper h3{font-size:15.5px;margin:1.3em 0 .5em}
.paper h4{font-size:14px;margin:1.1em 0 .4em}
.paper table,.doc-tbl{border-collapse:collapse;width:100%;margin:1em 0;font-size:13px}
.paper table td,.paper table th,.doc-tbl td,.doc-tbl th{border:1px solid #9aa4a0;padding:6px 9px;vertical-align:top}
.paper table th,.doc-tbl th{background:#eef1ef;font-weight:600}
.paper table tr:nth-child(even) td{background:#fafbfa}
.paper img{max-width:100%;height:auto;display:block;margin:1em auto}
.paper blockquote{margin:1em 0;padding:.5em 1em;border-left:3px solid var(--c-accent,#c9a227);background:#faf7ed;color:#444}
.paper pre{background:#f4f5f4;border:1px solid #ddd;border-radius:5px;padding:12px;overflow:auto;font-family:var(--font-mono,monospace);font-size:12.5px}
.paper code{background:#f0f2f0;padding:1px 5px;border-radius:3px;font-family:var(--font-mono,monospace);font-size:12.5px}
.paper hr{border:0;border-top:1px solid #ddd;margin:1.6em 0}
.paper ul,.paper ol{padding-left:1.8em}
.markdown{color:inherit}
/* —— Excel 查看器：这一段决定"像不像 WPS" —— */
.xl-stage{flex:1;min-height:0;overflow:auto;background:#fff;border:1px solid #c3ccc7}
.xl-pane{width:max-content;min-width:100%}
.xl-sheet-wrap{width:100%}
.xl-sheet{border-collapse:separate;border-spacing:0;background:#fff;color:#111;font-size:12.5px;table-layout:fixed}
.xl-sheet td,.xl-sheet th{border-right:1px solid #d8ded9;border-bottom:1px solid #d8ded9;padding:3px 6px;height:22px;vertical-align:middle;overflow:hidden;white-space:nowrap;background:#fff}
/* 行头列头：灰底、居中、不可选，和 Excel 一致 */
.xl-sheet .colhdr,.xl-sheet .rowhdr{background:#f0f2f1;color:#5a6560;font-weight:600;text-align:center;user-select:none;border-right:1px solid #c3ccc7;border-bottom:1px solid #c3ccc7}
.xl-sheet .rowhdr{position:sticky;left:0;z-index:3;min-width:44px}
.xl-sheet thead .colhdr{position:sticky;top:0;z-index:4}
.xl-sheet thead .rowhdr{z-index:6}
/* 冻结：行列交叉处 z-index 必须最高，否则横竖滚动时会互相盖住 */
.xl-sheet .frz-row{position:sticky;z-index:3;background:#fff}
.xl-sheet .frz-col{position:sticky;z-index:2;background:#fff}
.xl-sheet .frz-both{z-index:5}
.xl-sheet tbody tr:hover td{background:#f5f9f6}
.xl-sheet td.xl-active{outline:2px solid #1f7a4d;outline-offset:-2px}
.xl-sheet td.xl-hit{background:#fff6d5!important}
.xl-sheet td.xl-hit-cur{background:#ffd966!important;outline:2px solid #c9a227;outline-offset:-2px}
/* 底部 sheet 标签条，仿 Excel */
.xl-tabbar{display:flex;gap:2px;padding:6px 4px 0;overflow-x:auto;border-top:1px solid #2b3f36;flex-shrink:0}
.xl-tab{border:1px solid #2b3f36;border-bottom:0;border-radius:5px 5px 0 0;background:var(--c-bg-soft,#121b17);color:var(--c-dim);padding:6px 14px;font-size:12.5px;cursor:pointer;white-space:nowrap}
.xl-tab.active{background:#fff;color:#111;font-weight:600}
.xl-finder{display:flex;align-items:center;gap:8px;padding:8px;background:var(--c-card-lift,#1b2823);border:1px solid #2b3f36;border-radius:var(--r-sm,6px);margin-bottom:8px;flex-wrap:wrap}
.xl-finder .input{width:220px}
.input-sm{padding:6px 8px;font-size:13px}
.xl-hint{font-size:12px}

/* —— PDF 查看器 —— */
.pdf-pages{flex:1;min-height:0;overflow:auto;background:#2a3833;padding:16px 0;text-align:center}
.pdf-page{position:relative;display:inline-block;margin:0 auto 18px;box-shadow:0 4px 18px rgba(0,0,0,.35);background:#fff}
.pdf-page canvas{display:block}
.pdf-pageno{position:absolute;right:6px;bottom:6px;background:rgba(0,0,0,.55);color:#fff;font-size:11px;padding:1px 7px;border-radius:3px}
.pdf-jump{width:72px}

/* —— 徽标点（模型接入页的密钥状态） —— */
.dot{display:inline-block;width:8px;height:8px;border-radius:50%;margin-right:6px;vertical-align:middle}
.dot-ok{background:var(--c-ok,#3f9d6b)}
.dot-err{background:var(--c-danger,#c8503f)}
.dim{color:var(--c-dim,#93a49b)}
.mono{font-family:var(--font-mono,monospace);font-size:12px}
.convert-job{border:1px solid #2b3f36;border-radius:var(--r-md,10px);padding:12px;margin-bottom:10px;background:var(--c-card,#16211d)}
.row-line{display:flex;align-items:center;gap:10px;flex-wrap:wrap}
.stack{display:flex;flex-direction:column;gap:10px}
.warn-box{border-left:3px solid var(--c-warn,#d09a2c);background:rgba(208,154,44,.1);padding:8px 12px;border-radius:0 5px 5px 0;margin:8px 0}
