2

I have a scene including an Object3D representing a globe and multiple mesh elements representing points on this globe. I use OrbitControls to allow interaction. Additionally I attach HTMLElements to the points on the globe. Since a globe basically is a sphere, points might not be visible for the camera when placed on the back.

How can I detect whether or not such a point is visible for the camera/hidden by the object? Doing so I want to hide the HTMLElement in relation to the mesh's visibility. The HTMLElement's position is updated on render, hence this check should happen on render as well I assume:

private render() {
   this.renderer.render(this.scene, this.camera);

   this.points.forEach(({ label, mesh }) => {
      const screen = this.toScreenPosition(mesh);
      label.style.transform = `translate3d(${screen.x - 15}px, ${screen.y}px, 0)`;
   });

   this.requestId = window.requestAnimationFrame(this.render.bind(this));
}

Working code within render:

this.points.forEach(({ label, mesh }) => {
    const screen = this.toScreenPosition(mesh);
    label.style.transform = `translate3d(${screen.x - 15}px, ${screen.y}px, 0)`;

    const direction = new Vector3();
    direction.copy(mesh.position).sub(this.camera.position).normalize();
    this.raycaster.set(this.camera.position, direction);
    const intersections = this.raycaster.intersectObject(this.scene, true);
    const intersected = intersections.length > 0 ? intersections[0].object.uuid === mesh.uuid : false;

    if (intersected && label.style.opacity === "0") {
        label.style.opacity = "1";
    } else if (!intersected && label.style.opacity === "1") {
        label.style.opacity = "0";
    }
});
Johnny Kontrolletti
  • 727
  • 1
  • 10
  • 22
  • Does this answer your question? [three.js - check if object is still in view of the camera](https://stackoverflow.com/questions/29758233/three-js-check-if-object-is-still-in-view-of-the-camera) – Reporter Jul 27 '21 at 09:56

1 Answers1

1

I recommend a simple algorithm with two steps:

  • First, check if the given point is in the view frustum at all. The code for implementing this feature is shared in: three.js - check if object is still in view of the camera.
  • If the test passes, you have to verify whether the point is occluded by a 3D object or not. A typical way for checking this is a line-of-sight test. Meaning you setup a raycaster from your camera's position and the direction that points from your camera to the given point. You then test if 3D objects in your scene intersect with this ray. If there is no intersection, the point is not occluded. Otherwise it is and you can hide the respective label.
Mugen87
  • 28,829
  • 4
  • 27
  • 50