Skip to content

Fix widget selection on high-DPI displays; remove 'hack' shader toggle#2559

Open
dcwhite wants to merge 1 commit into
masterfrom
claude/hack-shader-issue-2558-11e0bc
Open

Fix widget selection on high-DPI displays; remove 'hack' shader toggle#2559
dcwhite wants to merge 1 commit into
masterfrom
claude/hack-shader-issue-2558-11e0bc

Conversation

@dcwhite

@dcwhite dcwhite commented Jul 10, 2026

Copy link
Copy Markdown
Member

Fixes #2558

Root cause

The widget-selection render pass draws into an offscreen FBO sized in Qt logical (widget) coordinates, and mouse coordinates are logical too — but the pass never set its own viewport. It inherited whatever was current, which is the physical framebuffer viewport (logical × devicePixelRatio) that Qt sets before every paintGL. On high-DPI displays the selection scene therefore rendered at devicePixelRatio scale relative to the FBO, so the pixel read back at the mouse position missed the widget, breaking shift-click picking.

The "Viewer widget selection correction" preference compensated in the selection vertex shader via a uniform literally named hack:

if(hack) gl_Position.xy = ((gl_Position.xy/gl_Position.w) * vec2(0.5) - vec2(0.5)) * gl_Position.w;

That squeezes NDC into the lower-left quadrant — exactly a devicePixelRatio == 2 correction. Hence the platform dependence:

  • Retina Macs (dpr = 2): hack needed, but it defaulted to off → broken picking out of the box
  • Standard displays (dpr = 1): hack must stay off
  • Fractional scaling (125%/150% on Windows, the default behavior under Qt 6): dpr = 1.25/1.5 → neither checkbox state works, which is why the toggle stopped helping some users

(History: the toggle was added in 0374273 "added toggle selection hack button", Oct 2019, alongside debug printouts of mouse position vs. screen size — a workaround for the symptom rather than the cause.)

Fix

Explicitly set the viewport to the selection FBO's size while rendering the selection pass, and restore the previous viewport afterward (SRInterface::select). Clip space then maps onto the FBO 1:1 at any display scale — integer, fractional, or 1 — so the correction has no reason to exist.

With the root cause fixed, this removes:

  • the hack uniform and shader branch in SRInterface.cc
  • the widgetSelectionCorrection preference (Preferences.h/.cc)
  • the settings persistence entry (Settings.cc) — stale keys in existing user settings files are ignored
  • the preferences-dialog checkbox and wiring (Preferences.ui, PreferencesWindow.cc/.h)

Testing

  • ✅ macOS (Retina, dpr = 2): shift-click widget picking verified working with the preference removed
  • Windows at 125%/150% display scaling still needs human testing — this was the configuration the old toggle could not fix, so confirmation there would be valuable
  • ⬜ Standard dpr = 1 display (should be unaffected: the explicit viewport matches what was previously inherited)

🤖 Generated with Claude Code

The widget-selection render pass drew into an FBO sized in Qt logical
(widget) coordinates but inherited whatever viewport was last set. Qt
sets the viewport to the physical framebuffer size (logical size times
devicePixelRatio) before each paintGL, so on high-DPI displays the
selection scene was rendered at devicePixelRatio scale relative to the
FBO and mouse coordinates, breaking shift-click widget picking.

The 'Viewer widget selection correction' preference compensated by
scaling NDC by 0.5 in the selection vertex shader (a uniform literally
named "hack"), which only worked for devicePixelRatio == 2 (e.g. Retina
Macs). It was wrong for standard displays (hence the toggle) and for
fractional scale factors (e.g. 125%/150% on Windows, common with Qt 6),
where neither setting worked.

Fix the root cause instead: explicitly set the viewport to the
selection FBO's size while rendering the selection pass, so clip space
maps onto the FBO 1:1 regardless of display scale, and restore the
previous viewport afterward. Remove the hack uniform, the
widgetSelectionCorrection preference, its settings entry, and the
preferences-dialog checkbox.

Fixes #2558

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
@dcwhite dcwhite requested review from basisunus and jessdtate July 10, 2026 21:44
@dcwhite dcwhite self-assigned this Jul 10, 2026
@dcwhite dcwhite added this to the 5.0.0 milestone Jul 10, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Investigate need for 'widget selection correction' preference (confusing, platform-dependent)

1 participant