ThreeJs: Add a Gridhelper which always face the perspective camera

Viewed 26

I have a threejs scene view containing a mesh, a perspective camera, and in which I move the camera with OrbitControls.

I need to add a measurement grid on a threejs view which "face" my perspective camera

It works on "start up" with the following code by applying a xRotation of Pi/2 on the grid helper

window.camera = new THREE.PerspectiveCamera( 45, window.innerWidth / window.innerHeight, 0.01, 300 );
window.camera.position.z = 150;

window.grid1 = new THREE.GridHelper(500, ~~(500 * 2))
window.grid1.material.transparent = true;
window.grid1.material.depthTest = false;
window.grid1.material.blending = THREE.NormalBlending;
window.grid1.renderOrder = 100;
window.grid1.rotation.x = Math.PI / 2;
window.scene.add(window.grid1);

window.controls = new OrbitControls(window.camera, window.renderer.domElement );
window.controls.target.set( 0, 0.5, 0 );
window.controls.update();
window.controls.enablePan = false;
window.controls.enableDamping = true;

But once i start moving with orbitcontrol the grid helper don't stay align with the camera.

I try to use on the renderLoop

window.grid1.quaternion.copy(window.camera.quaternion);

And

window.grid1.lookAt(window.camera.position)

Which seems to work partially, gridhelper is alligned on the "floor" but not facing the camera

How can I achieve that?

Be gentle I'm starting with threejs :)

1 Answers

This is a bit of a hack, but you could wrap your grid in a THREE.Group and rotate it instead:

const camera = new THREE.PerspectiveCamera( 45, window.innerWidth / window.innerHeight, 0.01, 300 );
camera.position.z = 150;

const grid1 = new THREE.GridHelper(500, ~~(500 * 2));
grid1.material.transparent = true;
grid1.material.depthTest = false;
grid1.material.blending = THREE.NormalBlending;
grid1.renderOrder = 100;
grid1.rotation.x = Math.PI / 2;

const gridGroup = new THREE.Group();
gridGroup.add(grid1);
scene.add(gridGroup);

// ...

And then, in your render loop, you make your group face to the camera (and not the grid):

gridGroup.lookAt(camera.position)

This works because it kind of simulates the behaviour of setting the normal in a THREE.Plane. The GridHelper is rotated to be perpendicular to the camera, and the it is wrapped in a group with no rotation. So by rotating the group, the grid will always be offset so that it is perpendicular to the camera.

Related