结论
不是截图工具本身坏了,也不是「分数缩放就一定会错」。真正的触发条件是:会话里实际生效的 Qt 全局缩放,让每屏逻辑尺寸变成了小数。本机三台 2560×1440 的屏幕上,缩放 1.5 时逻辑宽 = 2560 ÷ 1.5 = 1706.67(带小数),Qt 在 X11 上逐窗口取整后误差逐屏累积 —— 覆盖层里的底图被缩小、错位,与最终成图不一致;把缩放换成能整除的值(1.25 → 2048×1152)后,覆盖层与真实桌面逐像素一致。
还有一条同样关键的机制:X11 会话下,Plasma 只在登录时把全局缩放注入 Qt(环境变量 QT_SCREEN_SCALE_FACTORS,它决定 Qt 的 DPR)。所以「系统设置里看是 125%、实际跑的是 150%」属于常态;改完缩放不注销重登,等于没改。
现象
- 按快捷键做矩形区域截图时,给出的不是「在真实屏幕画面上直接框选」,而是一张整桌面的缩略大图(比实际桌面略小)。
- 在缩略图上框中的内容,与最终生成的图片不一致。
- 成图实际截取的是「真实屏幕上指针划过的那一块」—— 也就是框选坐标这一侧是对的,被缩小/错位的是那张供框选的底图。
时间线(实测)
| 时刻 | 事件 |
|---|---|
| 10-17 11:13 | 用户留存的区域截图看起来精确(当时会话里的注入值不是 1.5) |
| 10-18 ~ 10-19 | 期间有几次系统重建,但截图工具版本逐世代完全一致(见「与本次改动无关的判据」),软件侧没变 |
| 10-19 09:14 | 该次登录把 1.5 注入到会话(QT_SCREEN_SCALE_FACTORS 全为 1.5)—— 症状从这里开始 |
| 10-20 10:40 | 用户留存的区域截图明显偏移(同一工具、同一操作方式) |
| 10-20 11:00 | 配置文件里的全局缩放被写成 1.25,但会话仍跑 1.5(未重登,故无感) |
| 10-20 18:12 | 注销重登,会话注入值变为 1.25 → 用户实测「完全正常,矩形区域 100% 精准」 |
根因
这类截图工具的矩形选区是「每屏一个全屏窗口 + 一张整桌面快照当底图」的设计(并不是直接在实时屏幕上画半透明窗):
- 覆盖层窗口的几何取的是 逻辑像素,而快照是 物理像素;
- 覆盖层把快照按物理像素铺进逻辑坐标系,等于按 1/DPR 缩放底图,非首屏还叠加偏移;
- 而最终裁剪用的是指针的 物理坐标 ⇒ 成图永远等于真实屏幕那一块,与底图上框的那块不是同一份。
触发条件收敛成一句:DPR 让逻辑尺寸变成小数就发作。2560 ÷ 1.5 = 1706.67 时每屏取整误差累积;2560 ÷ 1.25 = 2048、1440 ÷ 1.25 = 1152 全是整数,就不发作。
上游同类问题(供对照,不影响本机处置):选区尺寸标签在分数缩放下算错(已修,6.6.0);特定排布下选到错的屏(已修,6.4.0);「覆盖层显示另一台屏的内容、成图也错」这一族仍开着(X11 与 Wayland 都有现场,6.7.4 仍能复现)。
实测证据
| 判据 | 实测 |
|---|---|
| 会话实际生效的缩放 | 出错那次:QT_SCREEN_SCALE_FACTORS 全部 1.5;重登之后:全部 1.25 |
| 覆盖层底图 vs 真实桌面(64×64 块归一化相关,1.0 = 逐像素一致) | 1.5:三屏中位数 0.136 / 0.000 / 0.000;1.25:1.000 / 1.000 / 1.000(>0.99 的块占 91% / 99% / 100%) |
| 同一测量在缩放 1.0 下 | 0.916(精确)⇒ 问题只在「逻辑尺寸非整数」这一档,与“是否分数”无关 |
| 裁剪侧是否正确 | 拖 800×500 物理像素 ⇒ 存图 801×501(1px 边框),两侧一致 |
| 生效值怎么读 | 读进程环境,不读配置文件:grep -o 'QT_SCREEN_SCALE_FACTORS=[^ ]*' /proc/<plasmashell 的 PID>/environ |
与本次改动无关的判据
- 软件版本没变:逐世代核对截图工具的版本号,十几次重建前后完全一致;期间也没有桌面环境 / Qt 的大版本变动。
- 配置侧没有写缩放:系统配置里没有任何代码去设置缩放、也没有写 Qt 的 DPR 相关项。
- 唯一变量就是会话里的注入值:同一台机、同一版本、同一操作方式,1.5 的会话错、1.25 的会话精确。
处置与判据
- 最省事(本次即用这种):改过缩放就注销重登;重登后先读一次生效值,再按一次截图快捷键验证。
- 机制性:选一个能整除出整数逻辑尺寸的缩放值。该分辨率下 1.25(2048×1152)与 1.0 安全,1.5 不安全(1706.67)。
- 必须用不安全缩放时:只对该程序临时固定 DPR = 1 启动(
QT_SCALE_FACTOR=1),或改用「全屏抓取 + 按 x,y,w,h 精确裁切」。 - 验收判据(30 秒):① 读生效值,确认与系统设置里的一致;② 拖一个 800×500 的框,若存图 ≈ 801×501、且覆盖层里看到的与真实桌面一致,即正常。
边界
- 本档只记录这一个症状的定位与处置,没有改动任何系统配置;早前试过的「把该模式固定成 DPR = 1」的补丁已回退,未保留。
- 不覆盖 Wayland 会话:Wayland 下覆盖层有合成器参与,路径不同,结论不能直接套用。
- 上游修复状态以本文写作时为准:尺寸标签、选错屏两条已修;「覆盖层显示别的屏内容、成图也错」仍开着,换版本不保证解决。