Keep node cards and connection lines on the same compositing path - #322
Merged
Conversation
Node cards move as GPU-composited layers - the browser promotes them on its own once their position changes every frame of a drag - while the connection lines live in an SVG layer that is re-rasterized on the main thread. Those are two different routes to the screen, and when they fall a frame out of step the connection visibly trails or stutters against the node it is attached to. The thin bright stroke on a near-black background makes every misstep obvious in the dark theme; the identical misstep is nearly invisible against the light theme, which is why the problem was reported as dark-mode-only while measurements of the page's internal geometry kept showing the two perfectly attached. Declaring will-change on both the node wrappers and the connection layer makes the browser assign both to the compositing path from the first frame, instead of flipping nodes onto a separate one partway through a gesture. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2 tasks
dovvnloading
added a commit
that referenced
this pull request
Aug 14, 2026
… frame (#323) Recent WebView2 builds hand independently-composited page layers to the Windows compositor to assemble on screen. A node card being dragged lives on its own such layer, while its connection lines are redrawn into a different one, and Windows can apply the card's movement one display frame before the freshly drawn connection arrives - the line visibly steps out of sync with the node it is attached to. Everything measured inside the renderer (layout geometry, frame captures) shows the two perfectly attached, because the divergence happens below the renderer at window composition; a thin bright line on the dark theme's near-black background makes each misstep obvious while the same misstep is nearly invisible on the light theme, which is why the report was dark-only. The launcher now disables delegated composition for the app's WebView2 instance, making the renderer assemble the complete frame itself before handing one finished image to Windows. The flag is appended in front of any WEBVIEW2_ADDITIONAL_BROWSER_ARGUMENTS the user already set and is ignored by runtimes that predate the feature. Also reverts the will-change stylesheet addition from #322: promoting more layers cannot help under this mechanism and only increases the number of independently-composited surfaces. Co-authored-by: Claude Fable 5 <noreply@anthropic.com>
2 tasks
dovvnloading
added a commit
that referenced
this pull request
Aug 14, 2026
These three changes were attempts at the drag artifact that were not confirmed to work before shipping, and the most recent one made things worse: with #324 in place the connection lag became visible in the light theme as well, where it had previously been unnoticeable. The most likely cause of that regression is the composition flag. The audit behind #324 established that the flag added in #323 never reached the browser, because the window library passes a conflicting switch and duplicate switches resolve last-one-wins. #324 corrected the delivery, so disabling delegated composition took effect for the first time - and it applies to both themes equally, which matches the report exactly. The stroke width increase and the explicit high-quality smoothing hint in the same change also affect both themes and cannot be ruled out. This restores graphlink_desktop.py, styles.css and gl-vars-dev.css to their state as of #321. The measured performance fixes in #319, #320 and #321 are untouched. Co-authored-by: Claude Opus 5 <noreply@anthropic.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Problem
While dragging a node, its connection line can visibly trail or stutter instead of staying pinned to the node. The problem was reported as dark-mode-only: switching the app to the light theme makes it disappear.
The two behaviors have one explanation. Node cards are moved by the graphics processor as independent layers - the browser quietly promotes them to that fast path once their position starts changing every frame. The connection lines live in a drawing layer that is redrawn on the main processor. Content traveling by two different routes to the screen can arrive a frame out of step, and when it does, the line lags the node it is attached to. A thin bright line on a near-black background makes each misstep obvious; the identical misstep on a white background is nearly invisible. Dark mode does not cause the problem - it reveals it. This is also why measurements of the page's internal layout kept reporting the line perfectly attached while the screen showed otherwise: the divergence happens after layout, at the final composition step.
Change
One stylesheet addition: declare
will-change: transformon both the node wrappers and the connection layer. This tells the browser up front to give both the same treatment, instead of promoting nodes to a separate path partway through a drag gesture. No behavior, markup, or code-path changes - the drawing pipeline is simply aligned from the first frame.Test plan