WebXR - Hiding the Interaction Ray

I’m looking for more information on how the Interaction Ray from a controller works and what properties it can have. In other applications I’ve made, I’ve set it so that it is only visible when it collides with a special GUI layer. For example, here where I can select a button, the ray shows, which is what I want:

But in this image, my ray is intersecting with an object that isn’t a UI element. I’d like to suppress that unless the object is marked somehow, say “Distance Grabbable” so I could perform some sort of “force grab” action upon it:

Is it possible to hide the ray and enable it conditionally?

cc @RaananW

Nope, but since you are fully control of the display flag you can create your own condition that will run on each XR-Frame. You can check if the ray intersects with an acceptable object and set it to be visible.

You CAN set the predicate that sets which meshes are pickable. You can change the scene’s pointerMovePredicate if it is available, or the raySelectionPredicate on the pointer selections

Thank you @RaananW,

Can you please elaborate a bit more on this one? Specifically:

  1. What “display flag” were you referring to here?

  2. How do I actually set an interaction ray to be visible/hidden?

  3. On a related note, how do I set visibility of a hand/controller? I naively tried to set myWebXRHand._handMesh.isVisible = false (where myWebXRHand is an instance I obtained via onHandAddedObservable at XR initialization time) and that did not make the hand invisible. What am i missing?

  4. Similarly to the previous question, how do I change other visual (material) properties of a hand/controller, let’s say its alpha/transparency? I’d like to do that efficiently, as user executes some interactions, that is to say that disabling hand tracking end enabling it back with different hand visualization settings isn’t what I look for.

So, for 1 and 2 -

WebXRControllerPointerSelection | Babylon.js Documentation (babylonjs.com)

The displayLaserPointer flag on the pointer selection module can control whether or not the laser pointer is displayed. It can be changed on each frame.

to 3 and 4 - Those meshes act as any other mesh in babylon - setting the parent root to be invisible will not influence the children - you need to set the children to be invisible as well. You can set it to be disabled (which will propagate to the children), but that really depends on your use case and what you are trying to achieve.

To get the controllers you can use the observable(s) we offer:

WebXR Controllers Support | Babylon.js Documentation (babylonjs.com)

To get the hand meshes you can use the publicly available handMesh property on the WebXR Hand (instead of using the private _handMesh), which we guarantee to be backwards compatible.

1 Like