A query on moving/positioning an object

Hi, I am exploring Three.js and am facing some very basic issues in understanding.

My experimental three.js code is as follows:

var geometry = new THREE.BoxGeometry( 5, 5, 5 );
var material = new THREE.MeshBasicMaterial( { color: "#433F81" } );
var cube = new THREE.Mesh( geometry, material );
scene.add( cube );
cube.position.x = 10;
cube.position.y = 5;
cube.position.z = 0;

When it is created, it is positioned at (0,0,0) in global coordinate system,as THREE’s default behaviour.
And its vertices are of order 2.5 with appropriate sign(half of 5).

Then I position cube at (10,5,0).

Debugging shows that after moving cube to (10,5,0):

vertices: Array(8)

0: Vector3 {x: 2.5, y: 2.5, z: 2.5}
1: Vector3 {x: 2.5, y: 2.5, z: -2.5}
2: Vector3 {x: 2.5, y: -2.5, z: 2.5}
3: Vector3 {x: 2.5, y: -2.5, z: -2.5}
4: Vector3 {x: -2.5, y: 2.5, z: -2.5}
5: Vector3 {x: -2.5, y: 2.5, z: 2.5}
6: Vector3 {x: -2.5, y: -2.5, z: -2.5}
7: Vector3 {x: -2.5, y: -2.5, z: 2.5}
position: Vector3 {x: 10, y: 5, z: 0}

Vertices before setting position has exactly same values.

On the other hand, if I do:

geometry.translate(10, 5, 0);

In this case, vertices change as expected, while cube position doesn’t change:

0: Vector3 {x: 12.5, y: 7.5, z: 2.5}
1: Vector3 {x: 12.5, y: 7.5, z: -2.5}
2: Vector3 {x: 12.5, y: 2.5, z: 2.5}
3: Vector3 {x: 12.5, y: 2.5, z: -2.5}
4: Vector3 {x: 7.5, y: 7.5, z: -2.5}
5: Vector3 {x: 7.5, y: 7.5, z: 2.5}
6: Vector3 {x: 7.5, y: 2.5, z: -2.5}
7: Vector3 {x: 7.5, y: 2.5, z: 2.5}
position: Vector3 {x: 0, y: 0, z: 0}

I am not able to understand this difference in behavior.
If cube’s position is set to new value, then its vertices must also change, which is not the case. While if I move geometry itself, then cube position is not changing.

So what am I missing here?

If you change the transformation of an object via position, rotation or scale, you effectively change the transformation matrix of the object. Not the geometry itself. The vertices are updated by the vertex shader since it’s way more efficient to do this operation on the GPU. The computations are perform in parallel and not in a single thread. You can read more about this topic right here:

https://en.wikibooks.org/wiki/GLSL_Programming/Vertex_Transformations

Changing the geometry e.g. via BufferGeometry.translate() is an operation you ideally want to perform only once and not each frame. If you actually need transformed vertices in JavaScript, you have to perform the modeling transformation by multiplying Object3D.matrixWorld with each vertex.

2 Likes

This guide might also help a bit:

https://threejs.org/docs/#manual/en/introduction/Matrix-transformations

2 Likes