Best way to get center of scene or model which contains multiple primitives

Started by
18 comments, last by recp 5 years, 10 months ago
6 minutes ago, recp said:

I'm only re-calculating center if parent transform changed. Because if object may move, then I have to re-calculate it, right?

Typically when a parent transform changes, there is no need to recalculate the origin (translate, offset, whatever you call it, but centre is not a good term because it doesn't need to be a centre). This is because the origin is defined in terms of the parent space. (However you can apply the parent transform to get the origin in world space. You may for example need this if you want to point a camera at a world space location.)

I am still not clear what you are trying to do, or what you are finding problematic, so it is difficult to help without a precise question. Are you trying to visualize a node changing its rotation about a point other than its local origin? Or actually rotate the vertices in local space while maintaining a separate origin? Perhaps a diagram would help explain.

Usually if you want to rotate an object in relation to a parent (even a null parent) you move the local origin to the centre of rotation, and perform the rotation. A good way to get a handle on how these things work maybe be to experiment with a scene graph hierarchy in blender or other 3d modelling program. This is essential to understand before trying to implement any kind of hierarchical animation.

Advertisement
2 hours ago, lawnjelly said:

Are you trying to visualize a node changing its rotation about a point other than its local origin?

Yes I think this is correct, "a point" must be center/centre of object for my case. I'm trying to find that centre, this is the actual issue. I'm not maintaining a separate origin, as you said I'm just trying to visualize a node changing its rotation around a point (center of object). You see, what I want to do is very simple :) 

 

If it is purely visual, then all you need to do is calculate the position of your 'centre' in world space, then use a lookat function to point a camera at this centre. You can then use the trackball to rotate the camera around the centre.

If you want to actually rotate the object itself in world space (but not affect the parents) and the centre is not the origin of the node, then the simplest way to achieve this is an extra node in between the parent and the object, with an origin at the centre. You can of course also alter the mesh data but I suspect this isn't what you want to achieve. You could also potentially put in a specific extra offset into your 'transform' data and deal with this, but just adding an extra node will do the job and be more flexible.

54 minutes ago, lawnjelly said:

then all you need to do is calculate the position of your 'centre' in world space

How can I calculate position of center? This is the actual question from the beginning. 

Maybe I can calculate the center of mesh while importing mesh by averaging all positions data (for single mesh)? Then I can store it in model/primitive structure. After transform changed, that transform could also be applied that pre-computed center. Averaging all these pre-computed centers (after transform applied) could give center of scene? Render engine would only need to apply transform, all jobs will be done in importer. 

Is this good or bad idea? Because to get an AABB, importer already iterates all positions data for each mesh. 

@Gnollrunner would this be better alternative instead of using smallest spheres? 

UPDATE (Solved):

Averaging each primitive's center to get center point for mesh/model and averaging each mesh/model's center to get scene's center worked for me. It seems I had a bug before, I updated the way to get center for scene and now center is not moving after rotation applied as I wanted. For some scenes rounding errors occur but it is smaller than epsilon (1e-5) and it is acceptable.

Currently it uses AABB's center and I also added an option to use exact center, when this option is enabled importer (not render engine) computes exact center (centroid) by averaging all positions. Users can also specify a custom point as center. This makes engine very flexible I think.

To summarize it, instead of re-calculating center, it uses pre-defined center. After transform is applied to a model, the center also gets transformed. If users don't specify custom point or force to use exact center then center of AABB will be used.

Thanks everyone for comments.

What are you using the center for? Culling? Camera positioning? Physical simulation? The answer may vary based on what you want.

The "accurate" way to calculate the center after rotation, assuming the AABB definition of "center," is to rotate all the vertices appropriately, and then calculate the AABB of it all. In 1995, this was expensive, and a bunch of approximations (using aabbs, spheres, and so forth) were used. These days, you may very well have enough CPU available that calculating the accurate center is no big deal.

If you need an approximation, then yes, spheres are rotationally invariant. That's what's so great about them! However, an "average" is not an accurate center, unless you use a weighted average and use it for center-of-mass for physics. If you're doing camera centering or culling, then "average" won't give you the closest bounds.

enum Bool { True, False, FileNotFound };
3 hours ago, hplus0603 said:

What are you using the center for?

1. In editor and viewer, I'm using the center for trackball to rotate mesh/node/scene around its center. Rotating around origin, if it is not same as center is not good for trackball. Maybe rotating around arbitrary point would be an option too but rotation around its center is default for trackball. It is expected behavior if trackball is attached to that model/mesh to rotate it.

2. I want to apply rotation animation around its center (not around its local origin) like Unity's spinning cube example (https://unity3d.com/learn/tutorials/topics/scripting/spinning-cube).

I'm using this method (http://old.cescg.org/CESCG-2002/DSykoraJJelinek/, see Basic intersection test) for frustum culling, center point is not involved for culling. 

3 hours ago, hplus0603 said:

If you need an approximation, then yes, spheres are rotationally invariant. That's what's so great about them! However, an "average" is not an accurate center, unless you use a weighted average and use it for center-of-mass for physics. If you're doing camera centering or culling, then "average" won't give you the closest bounds.

You are correct, I used average center (it is average of all sub mesh's centers) and it is not accurate (or it is not geometric center) as you said ? ? For instance if there are two center point at right and one at left, main center is close to right. But unlike my before implementation (I was used center of AABB which is combined of all sub AABBs; centerOfAABB = (min + max) * 0.5), the center is not moving over time after rotation is applied. At this point, I can continue to implement animation system (trackball is already working) and I can back later for this after animation system is implemented.

Since my center is not accurate, I must use an alternative way and it seems I must use spheres for getting accurate center point. I added this to my TODOs. Since it is open source on github, I would like to share/introduce my animation system as code samples to demonstrate what I'm trying to do after finished ?

I think summing all faces center points and then dividing it by face count should give you exact object position, then you just sum all objects center positions and divide that by the amount of objects

7 hours ago, KKTHXBYE said:

I think summing all faces center points and then dividing it by face count should give you exact object position, then you just sum all objects center positions and divide that by the amount of objects

To get center of single mesh, getting center of AABB seems fine (only for single mesh), but summing all faces could give wrong center. Because if that mesh has more detail at one side, this means that there are lot of faces at that side, then center point will be close to that side. Because I did similar to your proposal except I summed all positions instead of faces centers. For second part, if there are multiple objects at one side and less objects at opposite side then center will close to multiple objects' side. I tried this and center is not accurate because of the reasons I mentioned above, maybe I miss something? 

This topic is closed to new replies.

Advertisement