# dsh-page-zoom [DeepSeek Harness](https://github.com/deepseek-ai/deepseek-harness) / DSH Desktop 的页面缩放插件。 按住 **Ctrl** 滚动鼠标滚轮,即可缩放整个界面——侧边栏、菜单、设置、浮层、对话正文一起缩放。右下角有一个「放大镜 + 百分比」的读数。 [English](README.md) | 简体中文 ## 操作 | 手势 | 效果 | |---|---| | `Ctrl` + 滚轮向上 | 放大一档 | | `Ctrl` + 滚轮向下 | 缩小一档 | - 步长:每个滚轮刻度 **5%** - 范围:**30% – 200%** - 缩放值会记住(存在 `localStorage`),刷新页面不丢。 没有按钮、没有菜单、没有快捷键——那个数字只负责显示。 ## 关于那个数字 - 位于右下角,距边缘 **12px / 10px**。 - **先放大镜、后数字**。光一个 `100%` 挂在角落,谁也认不出那是页面比例;放大镜是浏览器和手机通用的缩放标识。 - **只显示、不交互**:`pointer-events: none`,它永远不接收点击,也永远不会挡住下面 UI 的操作。 - 没有边框、没有背景、没有底板——字体用应用自己的字体栈(`--dsw-font-family`),颜色用它的次级文字色(`--dsw-alias-label-tertiary`),所以它是"界面的一部分",而不是一个悬浮控件。 - **跟着页面一起缩放,不是反着来。** 数字随整个界面一起变大变小,它离右下角的距离也同比例变化,所以它占的位置始终与应用自身布局成同一个比例:100% 时 47×13、200% 时 93×26、30% 时 12×4。**100% 时不压到的东西,200% 也不会多压到。** 这件事不需要额外换算,因为固定定位元素的**视觉偏移 = 声明值 × 自身 zoom × 所有祖先 zoom**。把元素自身的 zoom 保持为 1、声明值保持常数,它就已经是线性的了。再拿声明值去乘一次级别就变成平方——声明的 24px 会渲染成 48px。 - 无障碍上用的是 `role="img"` + `aria-label`,**刻意不用 `role="status"`**:后者是 live region,会让读屏在每滚一格时打断播报一次"页面缩放 105%""页面缩放 110%"。 ## 安装 ```bash dsh plugin --profile desktop add github:Centaurea5547196/dsh-page-zoom dsh plugin --profile web add github:Centaurea5547196/dsh-page-zoom ``` 如果机器上没有 `git`,改用压缩包规格安装——`dsh` 支持远程归档地址: ```bash dsh plugin --profile desktop add https://github.com/Centaurea5547196/dsh-page-zoom/archive/refs/heads/main.tar.gz ``` ## 实现说明 缩放用的是根元素上的 CSS `zoom` 属性,**不是** `transform: scale`。`zoom` 会像浏览器自带缩放那样重排布局,`position: fixed` 的界面部件照常工作;而 `transform` 会让固定定位元素被裁切,还会把根元素变成所有 `position: fixed` 后代的包含块。 DeepSeek Harness 本身没有页面缩放:它唯一的排版设置是 `ui-theme.fontSize`,而且只影响对话正文——侧边栏文字、菜单、设置都是固定像素。这个插件补上这个手势。 监听挂在 `window` 的**冒泡阶段**(`{ passive: false }`),并且**让位于已经声明处理该手势的界面**(`event.defaultPrevented`)。这个顺序很关键:右侧栏的文档预览面板自己绑了以光标为中心的 Ctrl+滚轮缩放,并调用了 `preventDefault()`;如果插件在 `document` 上用捕获阶段监听,会在它之前触发,再用 `stopPropagation()` 就会直接把预览的缩放弄死。排在最后既保住了预览,其余地方又照常落到页面缩放上。这个手势同时也会接管普通浏览器标签页里的原生缩放。 全部是原生 DOM——没有 React 组件、没有 host 端代码、不联网,除了一个 `localStorage` 键之外不写任何存储。 ## 许可 MIT