#### Archived

This topic is now archived and is closed to further replies.

# Ragdoll Physics and Collision Response

This topic is 5463 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

## Recommended Posts

could someone explain swept sphere to me? from what I found it seems to act as a rolling ball that gets smaller? or am I way off? And how does one use this?

##### Share on other sites
A swept sphere is just a sphere moving along a line.

This sphere usually represents more detailed geometry (as to keep the collision tests fast and simple), hence the term "bounding sphere".

Ellipsoids can be used to provide a tighter fit around the contents of the bounding volume.

The basic swept-sphere coldet routine tests if a sphere has collided with the plane a triangle lays on; if so, then it tests if the intersection point lays on the triangle; if so, then a collision has most likely occurred; the sphere then "slides" along the collision plane. I like to think of it more as: keeping a little space between the object and it''s environment.

##### Share on other sites
matt, sorry for not replying, I forgot to mention that I was on holiday last week

you can check this, which is an implementation of what I''m talking about. it''s in 2D, but in 3D, it''s exactly the same. look at the animate() function, the SatisfyConstraints() functions, and the Collide() functions. the steps are important, you have to take them in order. And I haven''t seen any floating point issues so far.

Verlet Vehicles

the friciton stuff is far from perfect, due to the threshold you have to use. It makes the wheel bounce a little above the plane, thus the particles keep on slipping / sliding due to the slight bounce. However, to have no friciton at all, it works fine. It''s just that the friction is lower than it should be.

The bounce has to be there, to avoid the numerical innacuracies you talk about, but to improve the friciton model and keep that working, you''ll have to trick the velocity in the particle update itself.

##### Share on other sites
>>>matt, sorry for not replying, I forgot to mention that I was on holiday last week
It''s all gravy. I learned a lot trying to fix this on my own.

It turns out I was forgetting to test if the collision time is 0. After some slight tweaking, it works beautifully. Friction apparently works fine, with no bouncing and whatnot. I am in awe, really.

Oliii, you are my savior.

##### Share on other sites
Sorry to hijack a bit, but i was wondering if you can help.

I have a simple system working, but was wondering about elastic collisions. As it stands at the moment, my particle will hit the constraining cube and stop, as i test for the constraint (in this case the "ground", with the particle only havein a -ve y force on it) and set the relavent y positions to zero.

However, I am a little confused how an elastic collision with the constraint should be modelled, e.g. the particle has enought velocity and the constraint is made of rubber, therefore the particle will bounce. Is there an easy way to represent this uisng the Jakobsen method, and any pointers would be greatly appreciated.

Matt

[edited by - msm on March 7, 2004 5:12:17 PM]

##### Share on other sites
I had a try at this. it works if you test collisions of your particle dynamicaly (i.e. test intersection of segment from previous position to next position with a triangle, box, ect...).

this is what I've got for the response. 't' is the 'time' of collision. well, ... not quite, it's the 'percentage' of the displacement, how far the intersection point is from the start position of the particle

struct CParticle{	Vector	m_xCurrPos;  // current position of the particle	Vector	m_xNewPos;   // predicted position. 	Vector	m_xForces;   // forces	float	m_fMass;     // mass	float	m_fInvMass;  // inverse mass	bool    m_bCollided; // collided this frame	// test intersection from prev position to new position and an obstacle	bool CollisionTest(const CObstacle& xObstacle, float &tcoll, Vector& Ncoll) const	{	}	// respond to a collision	void CollisionResponse(float t, const Vector& N)	{		// collision response parameters		float elasticity = 1.0f;		float friction	 = 0.3f;		float threshold  = 0.01f; // avoid floating point innacuracy problems (tweak as you like)		// current particle displacement		Vector D = (m_xNewPos - m_xCurrPos);		// new particle position at point of impact		m_xCurrPos += D * t + N * threshold;		// impact velocity		float dn = (D * N);		// make sure it's an impact, not a separation		if (dn > 0.0f)			dn = 0.0f;		// split impact along normal and collision plane		Vector Dn = N * dn;		Vector Dt = D - Dn;		// calculate impact response		D = Dn * -elasticity + Dt * (1.0f - friction);		// calcualte new particle target position after impact,		// and add the threshold to conserve the momentum intact		m_xNewPos = m_xCurrPos + D + N * threshold;		// flag as collided this frame		m_bCollided = true;	}	// swept collision test against all obstacles	// test collisions until no collisions left	void CollisionTest(const CObstacle* xObstacles, int iNumObstacles)	{		// maximum number of collision iterations allowed		const int iter = 5;		for(int i = 0; i < iter; i ++)		{			// find first collision with obstacles			float  tcoll = 1.0f;			Vector Ncoll;			bCollided = false;			for(int j = 0; j < iNumObstacles; j ++)			{				bCollided |= CollisionTest(xObstacles[j], tcoll, Ncoll);			}			// didn't find a collision, end of test			if (!bCollided)				return;			// respond to the collision (bounce + slide), and find another collision			CollisionResponse(tcoll, Ncoll);		}		// we reached the limit of the number of collisions, stop the particle dead, to avoid collision bugs.		m_xNewPos = m_xCurrPos;		printf("Too many collisions\n");	}};

you'll find that it does not change things a lot, makes them slightly bouncier, but not by much. the constraints still push the colliding particles to the ground, absorbing most of the bounce.

I tried without satisfying constraints, and the particles all bounce pretty high. they still loose momentum (floating point innacuracies and integration too slack), but it works. except elasticity is not suited to jackobsen's stuff

you can have a look at the code here.

[edited by - oliii on March 7, 2004 6:16:31 PM]

##### Share on other sites
I was thinking along the same lines...i think :D

I take it in you example you then feed xCurrPos and xNewPos into the verlet integrator to allow it to calculate the response.

The only issue i can see is that (i think) you would never actually see the particle hit the obstacle. The frame where you calculated it had penetrated the obstacle you calculate your response (e.g the bounce) and place that into newpos. However, this measn that you will never return a currentpos of o, it will alays be the step before (above the ground) or the step after (above the ground)...have i missed something here? This owuld also be an issue for the amount of response i think - unless the oldposition ins reported as zero the frame before the calculation then the difference in currentposition - oldposition will return a value smaller than it should be...does this make sense?

If you perform the response the step after you have calculated collison, then again you would have lost a significant amount of energy from the system as you would have already constrained current position to zero, thereofre current-old will be less thanit should be.

Does this make sense?

Thank you for your time, as you can probably tell i am new to this area of programming

Matt

##### Share on other sites
(to be fair, I've reshaped code in the past 10 minutes becuase it was buggy, so you might be talking about old code )

you're totally right. It kind of hit me in the head as I tried to reply to your line of questioning , but with the modified code, the current pos gets moved to the point of collision. I get a much much better result that way. that conserves the momentum of the particle.

EDIT : I changed the code again, to REALLY conserve the momentum

[edited by - oliii on March 7, 2004 6:18:20 PM]

##### Share on other sites
Ahah. Looks good, thanks alot for your help

Just a quick sanity check -in your code current position is, i beleive, what i call old position (position of the particle at the start of the verlet integration), whereas your new particle pos is my current particle position (position after the integration and contraints) - is this correct?

Matt

[edited by - msm on March 7, 2004 6:32:27 PM]

##### Share on other sites
m_xCurrPos is the ''safe'' position. meaning the position is supposed to be always valid, and not outside the geometry. m_xNewPos is the position calculated after integration, and can be outside the geometry. Thus, it needs to be constrained, so after collisions and stick constrains are processed, it becomes valid again, ready for the next integration. That''s why I process the particles the way I do. verlet->iterated stick constraints->collisions. If you do it any other way round, then the collision detection can fail (m_xCurrPos becomes invalid, and going through geometry).

so yeah, I''d guess for you (and Jackobsen), m_xCurrPos = old position, and then m_xNewPos becomes jackobsen''s new position or your current position.

I prefer to refer to positions with the way I do, but it''s a matter of opinions.

• ### What is your GameDev Story?

In 2019 we are celebrating 20 years of GameDev.net! Share your GameDev Story with us.

• 10
• 23
• 13
• 10
• 9
• ### Forum Statistics

• Total Topics
634478
• Total Posts
3017704
×