Collision detection only between certain pairs of objects

Post Reply
PORRAS
Posts: 15
Joined: Tue Oct 13, 2009 2:49 pm

Collision detection only between certain pairs of objects

Post by PORRAS »

Hi, all.

I have a question about strategies or ways of detecting collisions between objects. I’m using a btCollisionWorld, so my problem doesn’t concern any dynamic aspect.

Imagine you have a robot arm like that one represented in Fig.1. There are several shapes that represent each link of the arm.
Robot-1.jpg
Robot-1.jpg (84.88 KiB) Viewed 17440 times
My aim is to detect collisions between certain pairs of links, not between all. For example, in Fig. 2 you can see a typical situation, in which Shape0 and Shape6 are in contact. In this case, I’d like to retrieve the pair of shapes that get in contact: Shape0 and Shape6. I don’t mind if Shape0 and Shape1 are colliding, and the same for Shape1-Shape2, Shape2-Shape3-Shape5, and so on… I mean, there’ll be certain pair of objects whose contacts doesn’t matter and don’t want to detect them.
Robot-2.jpg
Robot-2.jpg (92.52 KiB) Viewed 17440 times
I have read something about collision callbacks and triggers, selective collisions, btGhostObject… but since I’m new to Bullet, I don’t understand these completely. Could you recommend me any collision detection strategy?

Thanks a lot,
Francisco
miranlp
Posts: 3
Joined: Wed May 12, 2010 8:25 pm

Re: Collision detection only between certain pairs of object

Post by miranlp »

I think this might be what you're looking for: http://bulletphysics.org/mediawiki-1.5. ... _Filtering
PORRAS
Posts: 15
Joined: Tue Oct 13, 2009 2:49 pm

Re: Collision detection only between certain pairs of object

Post by PORRAS »

Hi, miranlp. Thanks for your reply.

Well, this is actually what I don't understand clearly.

Since I know a priori which pairs of links don't have to retrieve contact information, and the number of link "types" is bigger than 15 (the picture is a simplified model), I think that the best solution is to choose a Broadphase Filter Callback, but my problem is that I don't know how to include it in my program. Could somebody post a simple example of using this collisions filtering option?

Thanks,
Francisco
PORRAS
Posts: 15
Joined: Tue Oct 13, 2009 2:49 pm

Re: Collision detection only between certain pairs of object

Post by PORRAS »

Hi, again.

Well, finally I could manage to use correctly the BroadPhase Filter Callback. I post here my solution, it might be useful for beginners, like me.

This is the callback:

Code: Select all

struct YourOwnFilterCallback : public btOverlapFilterCallback
{
	// return true when pairs need collision
	virtual bool	needBroadphaseCollision(btBroadphaseProxy* proxy0,btBroadphaseProxy* proxy1) const
	{
		bool collides = (proxy0->m_collisionFilterGroup & proxy1->m_collisionFilterMask) != 0;
		collides = collides && (proxy1->m_collisionFilterGroup & proxy0->m_collisionFilterMask);
		
		//add some additional logic here that modified 'collides'
		return collides;
	}
};
And here, where you register this callback:

Code: Select all

btOverlapFilterCallback * filterCallback = new YourOwnFilterCallback();
dynamicsWorld->getPairCache()->setOverlapFilterCallback(filterCallback);
You can change the last statement for this, in case you're going to use a collisionWorld:

Code: Select all

broadphase->getOverlappingPairCache()->setOverlapFilterCallback(filterCallback);
This is taken from:
http://bulletphysics.org/mediawiki-1.5. ... _Filtering

I didn't notice that this is very connected with filtering using masks. My mistakes were that I didn't know how to identify each different object contained in proxy0 and proxy1, and how to modify the parameters m_collisionFilterGroup and m_collisionFilterMask for each one. Then, I figured out that you can do it when adding each object to the collisionWorld.

Code: Select all

collisionWorld->addCollisionObject (btCollisionObject * collisionObject, short int collisionFilterGroup, short int collisionFilterMask)
I know that I can filter collisions using logic statements in that callback, but because I have 32 different objects (expected to be incremented in the future), I think it'd be easier to use masks with more than 32-bits storage size (long long int instead of short int). I have a 32x32 matrix with all the desired contact combinations between objects, and each one of the rows would be the corresponding m_collisionFilterMask for a given object. Also, the parameter m_collisionFilterGroup would be the integer value of a row with 1 bit placed in the corresponding column representing each object.

Would it be really difficult to change this short int data type for long long int? Where would I have to change this?

Thanks,
Francisco
PORRAS
Posts: 15
Joined: Tue Oct 13, 2009 2:49 pm

Re: Collision detection only between certain pairs of object

Post by PORRAS »

Hi, again.

Finally I resolved this issue using a much easier approach. I defined a matrix with so many rows and columns as the total number of objects. Then, it is assigned 0s or 1s to each matrix element depending on each pair collision. Every m_collisionFilterGroup value belonging to every object takes the index value of the object in the matrix. I don't use m_collisionFilterMask. Finally, in the Broadphase Filter Callback, boolean value collides takes this value:

Code: Select all

collides=collisionMatrix[proxy0->m_collisionFilterGroup][proxy1->m_collisionFilterGroup];
In case of contact, true will be returned.

I expect this can help somebody.

Regards,
Francisco
esingla
Posts: 8
Joined: Sat Mar 13, 2010 8:00 am

Re: Collision detection only between certain pairs of object

Post by esingla »

Hello,
It was nice to see the issues similar to mine. I am working for the collision avoidance for a manipulator like you. Though I am trying my hands on Bullet for a good time now, but still as i am not very cofortable with the callbacks. Ly question to you is that is it important to really using a callback. I tried to handle the filtering, by preparing a list of objects corresponding to each object. Then the object is to be checked for collision only to the objects corresponding to its list. While doing so, each pair of objects is checked, and as the object can be convex or concave, i used 'findAlgorithm' for the objects ans trying to se eif there is any contact. Can you pls comment if this sounds ok.

My problem now is that though I am getting some information if the pair is in contact, however, i am not able to see what to do to get the positive distance between the two objects in question. the positive distance between non-colliding objects. I was looking for an algorithm for two general objects, however I didnt find any yet. Presently I am trying to implement btConvexConvexalgorithm for an easy example where both the objects are kept as convex triangulated mesh.
Please help me out by seeing if these things make sense and if you think I am going correct.

Thank you
User avatar
Erwin Coumans
Site Admin
Posts: 4221
Joined: Sun Jun 26, 2005 6:43 pm
Location: California, USA
Contact:

Re: Collision detection only between certain pairs of object

Post by Erwin Coumans »

There is no positive distance test between concave collision shapes: Bullet never needs it, so it hasn't been implemented. For rigid body dynamics, we only need penetration depth/contact information, and not positive distances. Also generally it is best to avoid moving concave triangle meshes, but use compounds of convex shapes (btCompoundShape with convex child shapes).

For convex-convex tests, we could easily support positive distance calculation (the internal algorithms already support it, it is just clamped at the moment)

Positive distance computation between concave triangle meshes would be a bit more work, but still possible. There is some implementation of concave triangle mesh versus concave triangle mesh, using btGImpactMeshShape. It currently doesn't deal with positive distances, but this could be added fairly trivially.

By the way, there is also the new btCollisionWorld::contactTest or btCollisionWorld::contactPairTest for custom contact queries.

Code: Select all

	///contactTest performs a discrete collision test between colObj against all objects in the btCollisionWorld, and calls the resultCallback.
	///it reports one or more contact points for every overlapping object (including the one with deepest penetration)
	void	btCollisionWorld::contactTest(btCollisionObject* colObj, ContactResultCallback& resultCallback);

	///contactTest performs a discrete collision test between two collision objects and calls the resultCallback if overlap if detected.
	///it reports one or more contact points (including the one with deepest penetration)
	void	contactPairTest(btCollisionObject* colObjA, btCollisionObject* colObjB, ContactResultCallback& resultCallback);

Could you please file an issue/feature request in the issue tracker, so your request doesn't get lost in a forum topic? http://code.google.com/p/bullet/issues/list
Thanks,
Erwin
esingla
Posts: 8
Joined: Sat Mar 13, 2010 8:00 am

Re: Collision detection only between certain pairs of object

Post by esingla »

I thank you, Erwin for the reply and salute you for this wonderful package. I would like to make the request for the concave-concave contact information. However, at present I am using the convexConvex function from Gjk solvers. It is working fine, although the accuracy of the results is still questionable. I am using
btSimplexSolverInterface sGjkSimplexSolver;
btGjkEpaPenetrationDepthSolver epaSolver;

and it would be nice if you let me know if there is anything like the solvers for exact informations and for approximate informations.
I thank you for your help anyway.
User avatar
Erwin Coumans
Site Admin
Posts: 4221
Joined: Sun Jun 26, 2005 6:43 pm
Location: California, USA
Contact:

Re: Collision detection only between certain pairs of object

Post by Erwin Coumans »

Using btGjkPairDetector should produce accurate distance query results (keeping in mind the collision margin, shape->setMargin)

If there are issues, please report them with a reproduction case (modify any of the Bullet demos and attached zipped source code)
Thanks,
Erwin
jstolarz
Posts: 14
Joined: Thu Dec 09, 2010 9:32 pm
Location: Glendale, California

Re: Collision detection only between certain pairs of object

Post by jstolarz »

esingla wrote:I would like to make the request for the concave-concave contact information. However, at present I am using the convexConvex function from Gjk solvers. It is working fine, although the accuracy of the results is still questionable. I am using
btSimplexSolverInterface sGjkSimplexSolver;
btGjkEpaPenetrationDepthSolver epaSolver;
Hi esingla. Sorry to resurrect a dead thread, but I've a question as to how you're using Gjk solver with your mesh data. I'm also trying to use bullet for collision detection/avoidance on a robotic arm and would like closing distance, preferably between the meshes, but as that's not possible yet, looking for other solutions. When you say you're using convex-convex function, did you simplify the meshes to something like convex hull?
abishekh
Posts: 1
Joined: Thu Jun 01, 2017 2:09 pm

Re: Collision detection only between certain pairs of object

Post by abishekh »

Erwin Coumans wrote:There is no positive distance test between concave collision shapes: Bullet never needs it, so it hasn't been implemented. For rigid body dynamics, we only need penetration depth/contact information, and not positive distances. Also generally it is best to avoid moving concave triangle meshes, but use compounds of convex shapes (btCompoundShape with convex child shapes).

For convex-convex tests, we could easily support positive distance calculation (the internal algorithms already support it, it is just clamped at the moment)

Positive distance computation between concave triangle meshes would be a bit more work, but still possible. There is some implementation of concave triangle mesh versus concave triangle mesh, using btGImpactMeshShape. It currently doesn't deal with positive distances, but this could be added fairly trivially.

By the way, there is also the new btCollisionWorld::contactTest or btCollisionWorld::contactPairTest for custom contact queries.

Code: Select all

	///contactTest performs a discrete collision test between colObj against all objects in the btCollisionWorld, and calls the resultCallback.
	///it reports one or more contact points for every overlapping object (including the one with deepest penetration)
	void	btCollisionWorld::contactTest(btCollisionObject* colObj, ContactResultCallback& resultCallback);

	///contactTest performs a discrete collision test between two collision objects and calls the resultCallback if overlap if detected.
	///it reports one or more contact points (including the one with deepest penetration)
	void	contactPairTest(btCollisionObject* colObjA, btCollisionObject* colObjB, ContactResultCallback& resultCallback);

Could you please file an issue/feature request in the issue tracker, so your request doesn't get lost in a forum topic? http://code.google.com/p/bullet/issues/list
Thanks,
Erwin


Hey @PORRAS ,

I'm new to Bullet and I'm starting something similar to what you have here. It would help if you could share your code - to get a better idea of how you managed the adjacency matrix and iterated through it with bullet calls.

Thanks
Post Reply