Three.js - How to get camera position with respect to origin

21,171

Not sure I got your question :) if I did then you need to switch between World and Local coordinate systems. The THREE.PerspectiveCamera inherits from THREE.Object3D so you can use the following methods to set your coordinate system:

.localToWorld ( vector )

vector - A local vector. Updates the vector from local space to world space.

.worldToLocal ( vector )

vector - A world vector. Updates the vector from world space to local space.

From Three.js Documentation

Update:

First update your camera Matrix:

camera.updateMatrixWorld();

Then:

var vector = camera.position.clone();

vector.applyMatrix( camera.matrixWorld );

The vector should hold the position in world coordinate

Share:
21,171
Beriol
Author by

Beriol

Updated on February 18, 2022

Comments

  • Beriol
    Beriol about 2 years

    The title of this question might a bit ambiguous, but I don't know how to phrase it in a line.

    Basically I've got this situation: there is a perspective camera in the scene and a mesh. The mesh is NOT centered at the origin of the axis.

    The camera points directly to the center of this object, and it's position (I mean literally the "position" property of the Three.js camera object) is the position with respect to the center of the object, not the origin; so it works in another coordinate system.

    My question is: how can I get the position of the camera not with respect of the object center but with respect of the origin of the "global" coordinate system?

    To clarify, the situation is this. In this image you can see a hand mesh that has a position far away from the origin of the coordinate system. The camera points directly to the center of the hand (so the origin from the point of view of the camera is the center of the hand), and if I print it's position it gives me these values: x: -53.46980763626004; y: -2.7201492246619283; z: -9.814480359970839 while actually I want the position with respect to the origin of the coordinate stystem (so in this case the values would be different; for example, the y value would be positive).

    UPDATE: I tried @leota's suggestion, so I used the localToWorld method in this way:

    var camera = scene.getCamera();
    var viewPos = camera.position;
    var newView = new THREE.Vector3();
    newView.copy(viewPos);
    camera.localToWorld(newView);
    

    I did an experiment with this mesh. As you can see this mesh is also not centered on the origin (you can see the axes on the bottom-left corner). If I print the normal value of the camera's position (so, with respect to the center of the mesh) it gives me these results: x: 0; y: 0; z: 15

    If now I print the resulting values after the code above, the result is: x: 0; y: 0; z: 30

    which is wrong, because as you can see the camera position in the image has x and y values clearly different than 0 (while z = 30 could be true, as far as I can see).

    If for example I rotate the camera so that it's very close to the origin, like this (in the image the camera is just behind the origin, so its position in world coordinates should have negative values for x, y, z), the coordinates with respect of the center of the object are:

    x: -4.674180744175711; y: -4.8370441591630255; z: -4.877951155147168

    while after the code above they become:

    x: 3.6176076166961373; y: -4.98753160894295; z: -4.365141278155379

    The y and z values might even be accurate at a glance, but the positive value of x tells me that it's totally wrong, and I don't know why.

    I'm going to continue looking for a solution, but this might be a step in the right direction. Still, any more suggestions are appreciated!

    UPDATE 2:

    Found the solution. What @leota said is correct, that is indeed how you would get absolute coordinates for the camera. In my case though, I finally found a single line of code hidden in the project's code that was scaling everything according to some rule (project related). So the solution for me was to take the camera position as it is and then scale it back according to that rule.

    Since @leota's answer was indeed the solution to the original question, I'm accepting it as the correct anwser

  • Beriol
    Beriol about 8 years
    That's a valid solution. I didn't notice that the camera inherits from Objectd3D. Sadly I tried but it gives me a wrong results. I'm going to edit my original post to describe what happens a little bit better
  • Beriol
    Beriol about 8 years
    Same results as before :( in the example I've showed (first image), I still get x:0, y:0, z: 30. It seems that the result is just the normal camera.position plus the vector used as parameter... I tried using as a vector (0, 0, 0) and the result is the exact camera.position vector (so x: 0, y: 0, z: 15)
  • leota
    leota about 8 years
    When you first created the camera, what position values did you give it?
  • Beriol
    Beriol about 8 years
    The camera is given as position that one, x: 0, y: 0, z: 15 with respect to the object
  • leota
    leota about 8 years
    I would like to see how you're creating the camera and setting its position (object relative),to understand more
  • Beriol
    Beriol about 8 years
    As I said before to one of the other users in a comment, the structure of the code is sadly badly written and I can't understand where exactly the camera magic starts. I did find the creation of the scene and camera though (sorry for the indentation): _scene = new THREE.Scene(); _camera = new THREE.PerspectiveCamera(45, _3DSize.width / _3DSize.height, 0.1, 1800); _camera.position.z = 15; _scene.add(_camera); after this, I don't really know what happens to the camera when an object is added to the scene (at start the scene is empty and the camera points at the origin)
  • leota
    leota about 8 years
    If only Z pos has been set then X and Y should be 0, so this means the code it's working as Z pos gets updated. But if you tell me it's not I don't know what else to say. It's difficult to debug without a code
  • Beriol
    Beriol about 8 years
    Yes, if we consider the object's center X and Y should be 0 in that image I posted. But if we consider the world's coordinates then you can see from the image that X and Y should be greater than 0, since the camera position is a bit on the right with respect of the X axis (but still in the positive range) and a bit up with rispecect of the Y axis (but still in the positive range). You see what I'm saying? I know that it's hard to debug without code, but trust me, even if you had the project's code it wouldn't be much use, it's too messy.
  • ahmedhosny
    ahmedhosny over 7 years
    should be vector.applyMatrix4()