Visibility of InstancedMesh is not reflected under fast snapshot rendering

Under fast snapshot rendering, changes to the visibility of an InstancedMesh are not reflected even if you call updateMesh.

Setting the second argument of updateMesh to false or calling updateMesh on each mesh individually does not resolve the issue.

repro: Babylon.js Playground

Please let me know if this is a known limitation or if I am using it incorrectly.

Thank you for maintaining this great framework!

cc @Evgeni_Popov

Hi @syuilo, this is an architectural limitation of FAST snapshot rendering rather than a bug in your code.

In FAST mode, the WebGPU bundle is recorded once and replayed every frame, so each draw call (including its instanceCount) is baked into the snapshot. updateMesh() can refresh per-mesh data already in the bundle (matrices, uniforms), but it can’t add or remove draws — so it can’t actually hide a mesh or an instance.

In your repro, the snapshot was recorded with sphere + sphere2 both visible, so instanceCount = 2 is locked in. Toggling isVisible on either one only affects what updateMesh writes into the buffer; the bundle still issues 2 instances and reads stale matrix data, which is why the instance keeps appearing.

To toggle visibility (or any other “structural” change) you need to re-record the snapshot via the disable/enable pair:

sr.disableSnapshotRendering();
sphere.isVisible = false;
sphere2.isVisible = false;
sr.enableSnapshotRendering();

Working playground: https://playground.babylonjs.com/?webgpu#5R2DBI#0

The updateMesh JSDoc is misleading on this point — it lists “visibility” as a supported property, which isn’t true in FAST mode. I’ll send a small PR to fix the doc comment.

Thank you for your information!

In my use case, I need to toggle visibility frequently, and switching the SR each time incurs a performance cost.
So instead of changing the isVisible property, I plan to achieve this by changing the position to move the mesh far away or by changing the scale to shrink it to zero.

Follow-up: I discovered that if you start SR with the mesh scaling set to 0, the mesh will not be displayed even if you later reset the scaling to 1; therefore, offsetting the mesh to a distant position is an effective solution.