Skip to content

fix(core): Enable shader/pipeline caching for attached WebGL devices#9971

Merged
chrisgervang merged 9 commits intovisgl:masterfrom
michaelsaily:fix/enable-caching-for-attached-devices
Feb 4, 2026
Merged

fix(core): Enable shader/pipeline caching for attached WebGL devices#9971
chrisgervang merged 9 commits intovisgl:masterfrom
michaelsaily:fix/enable-caching-for-attached-devices

Conversation

@michaelsaily
Copy link
Contributor

@michaelsaily michaelsaily commented Jan 28, 2026

When attaching to an external WebGL context (e.g., MapboxOverlay with interleaved: true), the caching props were not being set, unlike the _createDevice() path which explicitly enables them.

This caused severe performance degradation in interleaved mode because luma.gl's PipelineFactory would create new shader pipelines every frame instead of reusing cached ones.

The fix adds _cacheShaders: true and _cachePipelines: true to the webgl2Adapter.attach() call, matching the defaults set in _createDevice(). User-provided deviceProps can still override these if needed.

Closes #9839
Related: #9822, luma.gl#2465


Note

Low Risk
Small, localized default-prop change on the external-gl device attach path; main risk is unintended behavior change if an integration relied on caching being disabled.

Overview
When Deck is created with an external gl context (via webgl2Adapter.attach), it now explicitly enables shader and pipeline caching by default (_cacheShaders: true, _cachePipelines: true), aligning attached-device behavior with the internal _createDevice path.

This is intended to prevent severe performance regressions in interleaved/external-context integrations (e.g. Mapbox overlays) where pipelines could otherwise be recreated every frame; user deviceProps can still override these flags via object spread order.

Written by Cursor Bugbot for commit 2a6bb54. This will update automatically on new commits. Configure here.

When attaching to an external WebGL context (e.g., MapboxOverlay with
interleaved: true), the caching props were not being set, unlike the
_createDevice() path which explicitly enables them.

This caused severe performance degradation in interleaved mode because
luma.gl's PipelineFactory would create new shader pipelines every frame
instead of reusing cached ones.

The fix adds _cacheShaders: true and _cachePipelines: true to the
webgl2Adapter.attach() call, matching the defaults set in _createDevice().
User-provided deviceProps can still override these if needed.

Fixes visgl#9839
Related: visgl#9822, luma.gl#2465
Copy link
Collaborator

@chrisgervang chrisgervang left a comment

Choose a reason for hiding this comment

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

Thank you for submitting this PR - much appreciated! Left one comment. Please confirm there aren't any regressions to the other interleaved renderers - we now have a examples/basemap-browser app to help you quickly QA each integration

// Enable shader and pipeline caching for attached devices (matches _createDevice defaults)
// Without this, interleaved mode (e.g., MapboxOverlay) creates new pipelines every frame
_cacheShaders: true,
_cachePipelines: true,
Copy link
Collaborator

Choose a reason for hiding this comment

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

Let's put this below the spread in case a user wants to customize their device props. By default deviceProps is a {} so the caching will still apply

Copy link
Contributor Author

@michaelsaily michaelsaily Jan 29, 2026

Choose a reason for hiding this comment

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

Awesome, thank you so much @chrisgervang! That's a great catch: I've gone ahead and made the required change. I've also gone ahead and manually verified the changes via the examples/basemap-browser that you had recommended, and can confirm that no regressions were found, having tested it across all integrations.

Just as a slight note for anyone else wanting to verify the change: I believe that the performance impact scales with scene complexity and interaction frequency. As the examples/basemap-browser are quite simple, the problem doesn't always seem apparent, though this quickly changes in production applications with greater complexity and data.

Copy link
Collaborator

Choose a reason for hiding this comment

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

Oh my apologies, I misread your code. Your original code allowed the user to customize the props and now it forces the caching. Let's revert to your original version, please.

Copy link
Collaborator

Choose a reason for hiding this comment

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

Good to hear the example is working!

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Hahaha, no worries! Changes reverted and pushed.

@coveralls
Copy link

coveralls commented Jan 29, 2026

Coverage Status

coverage: 91.091% (+0.001%) from 91.09%
when pulling 2a6bb54 on michaelsaily:fix/enable-caching-for-attached-devices
into 714477b on visgl:master.

Copy link

@cursor cursor bot left a comment

Choose a reason for hiding this comment

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

Cursor Bugbot has reviewed your changes and found 1 potential issue.

- Caching is enabled by default
- User is able to override default cache-settings via deviceProps should they need.
…vices' into fix/enable-caching-for-attached-devices
Copy link
Collaborator

@felixpalmer felixpalmer left a comment

Choose a reason for hiding this comment

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

Thanks :)

@chrisgervang chrisgervang merged commit 1510545 into visgl:master Feb 4, 2026
6 checks passed
felixpalmer pushed a commit that referenced this pull request Feb 10, 2026
…9971)

* fix(core): Enable shader/pipeline caching for attached WebGL devices

When attaching to an external WebGL context (e.g., MapboxOverlay with
interleaved: true), the caching props were not being set, unlike the
_createDevice() path which explicitly enables them.

This caused severe performance degradation in interleaved mode because
luma.gl's PipelineFactory would create new shader pipelines every frame
instead of reusing cached ones.

The fix adds _cacheShaders: true and _cachePipelines: true to the
webgl2Adapter.attach() call, matching the defaults set in _createDevice().
User-provided deviceProps can still override these if needed.

Fixes #9839
Related: #9822, luma.gl#2465

* Caching props moved below default deviceProps, to ensure caching always applies.

Co-authored-by: chrisgervang <chrisgervang@users.noreply.github.com>

* Changes reverted:
- Caching is enabled by default
- User is able to override default cache-settings via deviceProps should they need.

---------

Co-authored-by: Chris Gervang <chrisgervang@users.noreply.github.com>
@kylebarron
Copy link
Collaborator

kylebarron commented Feb 10, 2026

This is great! Thank you! I can confirm this also fixes the bug I raised in #9941

Looking forward to having this published on NPM 🙂

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.

[Bug] Poor performance when enabling pickable on Firefox with DeckGL Version 9.2.2

5 participants