Rendering the rectangle on the camera plane

I have a code below and im trying to alter it. The current code renders a rectangular plane at the location of the target ( with same dimensions at the camera screen at the time of rendering) with respect to the x,y,z unit coordinates. I want this rectangle to be instead rendered to the plane of the camera itself so that no matter where i render it, the rectangle is overlapping every other object on the screen. Any idea on how to do this ?

var cam = this.camera;

    var width = (cam.right - cam.left) / cam.zoom;
    var height = (cam.top - cam.bottom) / cam.zoom;
    var geometry = new THREE.PlaneGeometry(width/4, height/4);

    var axisX = new THREE.Vector3(1, 0, 0);
    var axisY = new THREE.Vector3(0, 1, 0);
    var axisZ = new THREE.Vector3(0, 0, 1);

    var normal = cam.position.clone().sub(cam.position).normalize();

    var q = new THREE.Quaternion().setFromUnitVectors(axisZ, normal);
    var matrix = new THREE.Matrix4().makeRotationFromQuaternion(q);
    geometry.applyMatrix(matrix);

    var axisYt = axisY.clone().applyMatrix4(matrix);
    var q2 = new THREE.Quaternion().setFromUnitVectors(axisYt, cam.up);
    var matrix2 = new THREE.Matrix4().makeRotationFromQuaternion(q2);
    geometry.applyMatrix(matrix2);

    var target = this.controls.target;
    geometry.translate(target.x, target.y, target.z);

    var material = new THREE.MeshBasicMaterial({ color: 0xff0000, side: THREE.DoubleSide, transparent: true, opacity: 0.5 });
    var mesh = new THREE.Mesh(geometry, material);
    this.scene.add(mesh);
    this.updateGL();

I feel like the simpler way would be to just use position in front of the clip space cube and then in the vertex shader, dont multiply the matrices (which translates the mesh position into eye coordinates). For example:

var plane = new THREE.Mesh( 
	new THREE.PlaneBufferGeometry( 2 , 2 ),
	new THREE.MeshBasicMaterial({ color: 'blue', transparent: true, opacity: 0.7 })
);
// Place the plane at the front of the viewing cube. Behind everything would be +1.0 on the Z axis
plane.position.z = -1.0;
scene.add( plane );
plane.material.onBeforeCompile = function( shader ){
	
	shader.vertexShader = shader.vertexShader.replace( `#include <project_vertex>` , 
		`gl_Position = vec4( position , 1.0 );`
	);
}

You can find a lot of great info about the clip space “cube” in this MDN Page.

Heres a package that can be used as an example

2 Likes

I tried this solution and for some reason I can’t see the rendered image. I tried zooming in / zooming out. Turns out that my rendered image is seen only when I use the matrix transformations from the quaternion function above.

I have posted my question more clearly as a new topic in this link here: