felixmariotto / three-mesh-ui

⏹ Make VR user interfaces for Three.js
https://felixmariotto.github.io/three-mesh-ui/#basic_setup
MIT License
1.26k stars 134 forks source link

Raycaster, layers and UV on Blocks #227

Closed michal-repo closed 1 year ago

michal-repo commented 1 year ago

Hi,

I can't get this to work, what I want is to get UV for parent Block (cube in my example). This doesn't work with three-mesh-ui.

Here is three.js example: https://codesandbox.io/s/three-ray-test-1qe477?file=/src/index.js

and here three-mesh-ui: https://codesandbox.io/s/three-mesh-ui-ray-test-seyllk?file=/src/index.js

It logs to console UV coordinates. When you hover over blocks and especially when you cross them you can see that on three-mesh-ui example it switches to UV coordinates of block closer to camera. Even that I uses layers.

Do I need to apply layers differently on blocks that I want to exclude from Raycaster?

swingingtom commented 1 year ago

Hey @michal-repo

Thanks for the sandboxes, it really helped to understand the issue.

First thing to understand with three-mesh-ui is that its elements/components such as Block,Text are Object3D and not meshes.

On blocks, you can access its mesh child with the .frame property. This property is available as soon as a Block is created. Which is not true for Text. A generic way to access the main mesh of a three-mesh-ui would be to use .onAfterUpdate()

// Do not put layer 1 on whole cube1
//cube1.layers.set(1);

// but put it on its main child (frame)
cube1.onAfterUpdate = function () {
    cube1.frame.layers.set(1);
  };

If I've correctly understood your issue, your sandbox will work as soon as you put the previous snippet. But you would see that the cube1 is not rendered anymore.

Simply enable the layer 1 on the camera to solve it.

 camera.layers.enable(1);
michal-repo commented 1 year ago

@swingingtom Thanks, it works as expected.