Physics Simulation Forum

 

All times are UTC




Post new topic Reply to topic  [ 8 posts ] 
Author Message
PostPosted: Wed Feb 02, 2011 3:32 pm 
Offline

Joined: Wed Feb 02, 2011 2:51 pm
Posts: 5
Hello! I'm new to bullet and I'm trying to get ray casting working for picking objects. For now I'm using simple test shapes but I get unexpected results. Each object I'm trying to pick is created like this:

Code:
// create a boxShape with size 2, 2, 2
btCollisionShape *shape = new btBoxShape(btVector3(1, 1, 1));
btCollisionObject *body = new btCollisionObject();
body->setCollisionShape(shape);
body->setUserPointer(this);
   
// world is a btDynamicsWorld *
world->addCollisionObject(body);


The position of this object is updated as follows:
Code:
btTransform pos;
pos.setIdentity();

// mat is a btScalar * containing an OpenGL type matrix
pos.setFromOpenGLMatrix(mat);

// apply the transform to the object
body->setWorldTransform(pos);


And the ray cast is performed like this:
Code:
btCollisionWorld::ClosestRayResultCallback resultCallback(from, to);
world->rayTest(from, to, resultCallback);

if (resultCallback.hasHit())
{
  // some object was hit
}


For debugging purposes I request all collision objects from the world (with getCollisionObjectArray();), print their origins, the from and to vectors and the calculated world xy coordinate at the z coordinate of the origin of the object. Actual output is shown below:
Code:
// a hit was expected given this ray, the objects origin and the size of the object
from: [-0.155175, -0.020690, 27.001001]
to:   [-776.752686, -103.567055, -4972.657227]
obj[0], origin: [-4.000000, 0.000000, 0.000000] // according to world->getCollisionObjectArray().at(0).getWorldTransform().getOrigin();
obj[0], calculated ray xy coordinate @z==0.000000: [-4.349244, -0.579899] // debug, calculated myself using from/to/origin.z
resultCallback.hasHit(): false

// again, I would have expected a hit
from: [-0.143106, 0.000000, 27.001001]
to:   [-716.338684, 0.000000, -4972.657227]
obj[0], origin: [-4.000000, 0.000000, 0.000000] // according to world->getCollisionObjectArray().at(0)..getWorldTransform().getOrigin();
obj[0], calculated ray xy coordinate @z==0.000000: [-4.010970, 0.000000] // debug, calculated myself using from/to/origin.z
resultCallback.hasHit(): false


I was able to get some hits in case the object was very close to the center of the screen. But also in this case the hit area was generally smaller than the size of the object I was trying to hit. Anything obvious I'm doing wrong here? Are there any important steps in setting up the btDynamicsWorld which I could be missing?

Any help would be greatly appreciated!

one more thing: the objects are static (they don't move, the camera doesn't move either but that doesn't really matter I guess; only for the result of my unproject code).


Top
 Profile  
 
PostPosted: Thu Feb 03, 2011 2:49 am 
Offline

Joined: Mon Jan 03, 2011 4:26 pm
Posts: 43
I see you are setting the transform from an OpenGL matrix. Is it possible that this matrix scales your graphics objects? I'm not sure how Bullet supports scaling as I have never tried to scale something, and my unscaled objects seem to pick fine using the same approach you use here.


Top
 Profile  
 
PostPosted: Thu Feb 03, 2011 7:44 am 
Offline

Joined: Wed Feb 02, 2011 2:51 pm
Posts: 5
Thank you for your reply. I've been thinking about that myself. The matrix _should_ not scale the object. But I'll have a good look at the matrices I'm feeding the btCollisionObjects.

update: the matrices seem fine: the matrix I store in the btTransform of the btCollisionObject is the same as the one I get back when requesting the matrix from the object. The matrix does not contain any rotation or scaling. It just contains a translation.


Top
 Profile  
 
PostPosted: Thu Feb 03, 2011 2:27 pm 
Offline

Joined: Wed Feb 02, 2011 2:51 pm
Posts: 5
From what I can tell the following is happening:

Ray testing works if the ray passes through the origin of the world or passes the origin close enough. For example: if I place the camera on [-28, -14, 5] and I place the target object on [28, 14, -5] a hit is detected. The edge of the object is also properly detected if the ray to the edge is close enough to the origin of the world.

However, if the ray does not get in proximity of the origin of the world, a hit is not detected. For example: if I place the camera on [28, 0, 0] and I place the target object on [-28, 2, 0] a hit is only detected properly in the lower part of the object. Shooting a ray from [27.002, 0.038, 0] to [-471.649, 18.708, 0] does not result in a hit while this ray clearly goes through the object (z must be 0, and on x == -28 y ~= 2: the center of the object).

When I increase the size of the btBoxShape the maximum distance between the ray and the origin of the world in which a hit can be detected gets larger. For example: if I increase the btBoxShape size from 1,1,1 to 2,2,2 the ray from the example above does result in a hit.

I'm puzzled: the from and to vectors in the examples above are precisely those which I'm feeding to the btCollisionWorld::rayTest function (and the resultCallback object). The origins of the objects are requested from the btCollisionWorld and therefore can't be wrong either.

Requesting the matrices for the btCollisionObjects results in proper matrices which are exactly equal to the matrices I'm feeding the objects. No rotations or scaling is applied. I've tried creating both a btDiscreteDynamics world and a btCollisionWorld; there was no difference in behaviour. I've also tried using a btSphereShape instead of a box: no difference either. I tried using different types of result callback objects (closest, all): no difference.

Could it be I encountered a bug in the rayTest functionality? For the record: I'm using bullet 2.77 on ios 4.2 simulator.

update: I tried bullet 2.75 and bullet 2.76 as well. These versions have the same behavior. Probably I'm doing something wrong.


Top
 Profile  
 
PostPosted: Fri Feb 04, 2011 12:12 pm 
Offline

Joined: Wed Feb 02, 2011 2:51 pm
Posts: 5
I have solved the problem. All I needed to do was a `updateAabbs' on the world after something changed.


Top
 Profile  
 
PostPosted: Fri Feb 04, 2011 12:49 pm 
Offline

Joined: Mon Jan 03, 2011 4:26 pm
Posts: 43
Heiko wrote:
I have solved the problem. All I needed to do was a `updateAabbs' on the world after something changed.

Huh, I might have had that problem earlier and not noticed. Are you supposed to call that after you move an object manually?


Top
 Profile  
 
PostPosted: Fri Feb 04, 2011 1:41 pm 
Offline

Joined: Wed Feb 02, 2011 2:51 pm
Posts: 5
The step function now seems to handle this properly as well. After some changes were made to that part of the code, the explicit updateAabbs call wasn't necessary anymore.


Top
 Profile  
 
PostPosted: Mon Jul 16, 2012 10:17 pm 
Offline

Joined: Mon Jul 16, 2012 10:14 pm
Posts: 2
Is there a tutorial for picking? I am using xcode and bullet physics on the cube/balls/both demo and am trying to make it so you can select a shape to destroy it. Finding it a bit tricky. Any help? tutoirals? examples?

Thanks


Top
 Profile  
 
Display posts from previous:  Sort by  
Post new topic Reply to topic  [ 8 posts ] 

All times are UTC


Who is online

Users browsing this forum: Google [Bot], laadams85, nullChar and 3 guests


You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot post attachments in this forum

Search for:
Jump to:  
Powered by phpBB® Forum Software © phpBB Group