Skip to content

Commit 250e0ea

Browse files
committed
fix(OpenGLRenderWindow): release WebGL context before view.delete()
vtkOpenGLRenderWindow.delete() tears down the vtk.js side of the view but does not relinquish the underlying WebGL context. Chrome enforces a hard per-process limit of ~16 WebGL contexts; mounting and unmounting viewports across case transitions exhausted that pool, leaving any still-active viewport blank. Grab the canvas before delete(), look up the WEBGL_lose_context extension, and call loseContext() so the GPU slot is returned to the browser. Ordering matters: loseContext() must run before view.delete(), otherwise the extension handle is already gone.
1 parent 9d40712 commit 250e0ea

1 file changed

Lines changed: 13 additions & 1 deletion

File tree

src/core/OpenGLRenderWindow.tsx

Lines changed: 13 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -36,7 +36,19 @@ export default forwardRef(function OpenGLRenderWindow(
3636

3737
const [viewRef, getRWView] = useGetterRef(() => {
3838
const view = vtkOpenGLRenderWindow.newInstance();
39-
deletionRegistry.register(view, () => view.delete());
39+
deletionRegistry.register(view, () => {
40+
// Explicitly release the WebGL context back to the GPU before deleting
41+
// the VTK object. Without this, Chrome's per-process limit of ~16
42+
// WebGL contexts is exhausted across case transitions, causing active
43+
// viewports to go blank.
44+
const canvas = view.getCanvas?.() as HTMLCanvasElement | undefined;
45+
if (canvas) {
46+
const gl: WebGLRenderingContext | WebGL2RenderingContext | null =
47+
canvas.getContext('webgl2') ?? canvas.getContext('webgl');
48+
gl?.getExtension('WEBGL_lose_context')?.loseContext();
49+
}
50+
view.delete();
51+
});
4052
return view;
4153
});
4254

0 commit comments

Comments
 (0)