Visitar URL original
fix(core): rebind an attribute when its transition is removed by mmporong · Pull Request #11068 · visgl/deck.gl · GitHub
Skip to content

fix(core): rebind an attribute when its transition is removed - #11068

Merged
chrisgervang merged 3 commits into
visgl:masterfrom
mmporong:fix-core-rebind-attribute-after-transition-removal
Nov 10, 2026
Merged

chrisgervang merged 3 commits into
visgl:masterfrom
mmporong:fix-core-rebind-attribute-after-transition-removal

Conversation

@mmporong

@mmporong mmporong commented Nov 8, 2026 •

Copy link
Copy Markdown
Contributor

For #10963

Background

When transitions stops covering an attribute, the next layer update deletes the transition buffers but does not mark the attribute for redraw, so models keep the deleted float32x4 buffer. On master, a ColumnLayer fill model still holds the destroyed buffer after {transitions: null, opacity: 0.7}; with this change it binds instanceFillColors again as unorm8x4.

The model regeneration case does not reproduce with ColumnLayer on master, which uses GPUVectorModel. Layers on a plain Model may still hit it; that is left out here.

Change List

  • AttributeTransitionManager: rebind the attribute when its transition is removed
  • Attribute: add setLayoutChanged() for plain Model layouts
  • Unit tests

Verified with vitest --project headless test/modules/core test/modules/layers and yarn lint.


Note

Low Risk
Targeted bug fix in attribute transition cleanup that ensures proper buffer rebinding without altering core rendering pipelines.

Overview
Ensures layer models correctly rebind original attributes when an attribute transition is removed.

Previously, removing an active transition deleted its transition buffer without marking the underlying attribute for a redraw or layout update, leaving models bound to destroyed transition buffers with stale buffer formats (such as float32x4 instead of unorm8x4).

When an animated attribute transition is removed in AttributeTransitionManager, the attribute is now marked with setNeedsRedraw() and a new setLayoutChanged() method on Attribute, prompting layers to update their model buffer layouts and rebind the attribute buffers.

Reviewed by Cursor Bugbot for commit 10d6431. Bugbot is set up for automated code reviews on this repo. Configure here.

@greptile-apps

greptile-apps Bot commented Nov 8, 2026 •

Copy link
Copy Markdown

RetriggerView in GreptileConfidence Score: 5/5

[Medium impact] The PR appears safe to merge.

Summary

Restores the original attribute binding when its transition is removed.

  • Models switch back to source attributes when their transitions are removed.

Reviews (3) · Last reviewed commit: "Merge branch 'master' into fix-core-rebi..." · Reviewed by Greptile

@chrisgervang chrisgervang left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Reviewed 26252ff; recommend approval. No P1s.

The fix is at the root cause: removing a transition changes the bound buffer, and the attribute now flags that change itself. In a scratch probe, master leaves a destroyed float32x4 buffer bound after transitions: null. This head binds instanceFillColors as unorm8x4 on ScatterplotLayer, ColumnLayer and a plain Model subclass. The new test fails without the fix.

Non-blocking: Older than this PR: GPUTransitionBase.delete() does not delete attributeInTransition, so each transition leaks one buffer. testLayer reports "1 Buffers" on master and here, and adding this.attributeInTransition.delete() there clears it. Could that be a separate follow-up?

Labels: P1 settle before this is merged, P2 can follow, Non-blocking optional.

expect(manager.transitions.instanceSizes, 'transition is deleted').toBeFalsy();
});

webglTest('AttributeTransitionManager#remove transition', () => {

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Non-blocking: This test checks the flags. A testLayer case that removes transitions and checks the model's instanceFillColors layout would cover what users see. Could we add one?

Details
  • Probe: ScatterplotLayer with a getFillColor transition, then {transitions: null, opacity: 0.7}.
  • It reads model.bufferLayout and checks destroyed on the buffers in model.vertexArray.attributes.

@mmporong

Copy link
Copy Markdown
Contributor Author

Added the testLayer case in 667a590: ScatterplotLayer with a getFillColor transition, then {transitions: null, opacity: 0.7}. It checks that instanceFillColors is back to unorm8x4 in model.bufferLayout and that no destroyed buffer is left in model.vertexArray.attributes. With the two source files reverted to master, it fails on the layout check.

Its onError lets through only the known "1 Buffers" leak from GPUTransitionBase.delete(). Agreed that the leak fix fits a separate follow-up. I'll open one after this lands.

@coveralls

Copy link
Copy Markdown

Coverage Status

coverage: 83.317% (+0.003%) from 83.314% — mmporong:fix-core-rebind-attribute-after-transition-removal into visgl:master

@chrisgervang
chrisgervang merged commit 37f81b8 into visgl:master Nov 10, 2026
9 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants