Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Get center of object #447

Closed
traa opened this issue Aug 23, 2011 · 11 comments
Closed

Get center of object #447

traa opened this issue Aug 23, 2011 · 11 comments
Labels

Comments

@traa
Copy link

traa commented Aug 23, 2011

I encountered problem, - when clicking on some object in scene, camera must center on this object. For this i need center coordinates of object (y axis). How i can compute this? Tried to sum all vertices of this object and divide it on vertices count, but this, of course, wrong decision.

@mrdoob
Copy link
Owner

mrdoob commented Aug 23, 2011

object.position.y?

@traa
Copy link
Author

traa commented Aug 23, 2011

in our models it's always 0, models absolutely positoned

@traa traa closed this as completed Aug 23, 2011
@traa traa reopened this Aug 23, 2011
@mrdoob
Copy link
Owner

mrdoob commented Aug 23, 2011

What do you mean absolute positioned? All the objects are in 0,0,0 but the vertices cluster isn't around the center?

@alteredq
Copy link
Contributor

You can get center of geometry bounding box:

geometry.computeBoundingBox();

var centerX = 0.5 * ( geometry.boundingBox.x[ 1 ] - geometry.boundingBox.x[ 0 ] );
var centerY = 0.5 * ( geometry.boundingBox.y[ 1 ] - geometry.boundingBox.y[ 0 ] );
var centerZ = 0.5 * ( geometry.boundingBox.z[ 1 ] - geometry.boundingBox.z[ 0 ] );

Then you could set your camera's target to object position plus center:

camera.target.position.copy( object.position );
camera.target.position.addSelf( new THREE.Vector3( centerX, centerY, centerZ ) );

@aminnaggar
Copy link

This is a little function I wrote a while back. Maybe it'l help you out a bit.

getCentroid: function ( mesh ) {

    mesh.geometry.computeBoundingBox();
    boundingBox = mesh.geometry.boundingBox;

    var x0 = boundingBox.x[ 0 ];
    var x1 = boundingBox.x[ 1 ];
    var y0 = boundingBox.y[ 0 ];
    var y1 = boundingBox.y[ 1 ];
    var z0 = boundingBox.z[ 0 ];
    var z1 = boundingBox.z[ 1 ];


    var bWidth = ( x0 > x1 ) ? x0 - x1 : x1 - x0;
    var bHeight = ( y0 > y1 ) ? y0 - y1 : y1 - y0;
    var bDepth = ( z0 > z1 ) ? z0 - z1 : z1 - z0;

    var centroidX = x0 + ( bWidth / 2 ) + mesh.position.x;
    var centroidY = y0 + ( bHeight / 2 )+ mesh.position.y;
    var centroidZ = z0 + ( bDepth / 2 ) + mesh.position.z;

    return mesh.geometry.centroid = { x : centroidX, y : centroidY, z : centroidZ };

}

you might be able to incorporate alteredq's math (I wish I was smart enough to understand his shortcut)

@mrdoob mrdoob closed this as completed Aug 29, 2011
@mrdoob
Copy link
Owner

mrdoob commented Sep 26, 2011

I wonder... wouldn't it be simpler to do this?

geometry.centroid = new THREE.Vector3();

for ( var i = 0, l = geometry.vertices.length; i < l; i ++ ) {

    geometry.centroid.addSelf( geometry.vertices[ i ].position );

} 

geometry.centroid.divideScalar( geometry.vertices.length );

@alteredq
Copy link
Contributor

Yeah, if you just need a center this is simpler. If you already have a bounding box, or you need a bounding box for something else, then it's simpler just to compute its center.

Hmmm, now I wonder if these two methods would give the same results. If you have a tons of points at one side and small number of points on other side, center of bounding box would be center of geometry, while centroid would be in "center of gravity", closer to a denser cluster of points.

>>> points = [ 0, 10, 11, 12 ]
>>> sum(points)/float(len(points)) # centroid
8.25
>>> 0.5 * (min(points) + max(points)) # center of bounding box
6.0

I guess both methods are useful, for different use cases.

@mrdoob
Copy link
Owner

mrdoob commented Sep 26, 2011

True that. Centroid of bounding box is what most people would need.

@aminnaggar
Copy link

yea I guess mine isn't really a centroid function after all :s

@powerslave
Copy link

var x0 = boundingBox.x[ 0 ];
var x1 = boundingBox.x[ 1 ];
var y0 = boundingBox.y[ 0 ];
var y1 = boundingBox.y[ 1 ];
var z0 = boundingBox.z[ 0 ];
var z1 = boundingBox.z[ 1 ];

is now:

var x0 = boundingBox.min.x;
var x1 = boundingBox.max.x;
var y0 = boundingBox.min.y;
var y1 = boundingBox.max.y;
var z0 = boundingBox.min.z;
var z1 = boundingBox.max.z;

(as of r47)

@ideogram
Copy link

Conceptually, it's adding two vectors and taking the half of the result. I'm not sure if it's faster, but it's more... concpetual:

        c.addVectors( 
            object.children[0].geometry.boundingBox.min,
            object.children[0].geometry.boundingBox.max
        );

        c.divideScalar(2);

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests

6 participants