I need a stable stack!

Started by
22 comments, last by Bow_vernon 13 years ago
Hi guys, I have a problem with my physics demo. Im trying to make a physics demo that support stacking.
I was awestruck by a physics demo by erin catto. I read the paper too, and started implementing it after I finally understand
the paper (not all though)

This is the demo. read readme.txt for more info

And finally I made a physics demo. It's impulse based, using sequential impulse, very much following Erin Catto's Box2D.
It's stable, as there's no jitter (I try to simulate box falling on a static infinite mass box. it's stable, it reaches the zero velocity after several seconds)
Here's a short description
-I clamp the impulse just like his:

//Normal Impulse
PN = AccN;
AccN = Max(AccN + jn, 0.0);
jn = AccN-PN;
//Tangent Impulse
maxf = AccN * friction;
PT = AccT;
AccT = Clamp(Acct+jt, -maxf, maxf);
jt = AccT-PT;

-All objects has zero restitution (they dont bounce)
-I used fixed time step of 60hz, just like his demo
-I used 9.8 ms-2 gravity acceleration, just like his demo
-I apply impulses sequentially, with 10 iterations, just like his demo

But I dont implement some of the advance stuff, like:
-Contact Caching (all contacts are generated each tick)
-Warm Starting (each impulse start with 0.0 accumulated impulse)
-I dont pre-apply last accumulated impulse at the beginning of the timestep

And a few differences:
-He used cross product of normal vector as the tangential direction, I dont (it's 3D man!!).
Instead, I used the :
vec3 tangent = vel-normal*(vel*normal); //vel is relative velocity of impact
-I used Chris Hecker formula for calculating the MassNormal and MassTangent (no problem)

SOME RANTS:
-If I try to drop a box on top of infinite mass box, it's stable, you can see in the demo, the springed box
will reach theoritically zero velocity after falling to a static box
-But when I try to stack some objects, even if it's low stack, it's not stable (no jitter, but they'll move slightly
in tangential direction, until finally the stack collapses)
-The sphere stacks are stable no matter what, anyway (since they only got one contact)

WHAT CAN I DO NOW?? Im getting close, *sigh*

-IM pretty sure my OBB-OBB collision detection worked well, and the contact generation is perfect.
-I tried to modify the Box2D Demo (deleting the warm start code and the last accumulated code),
the stack is not stable(similar to mine). However, if I try to increase iteration in Box2D demo,
it will come to a stable state(100 iterations). Mine?? nope, but the stack will last longer (for 10minutes or so)

I appreciate any help from you guys. Im making this demo for learning, and I hope to be able to make
stable stack (five or ten boxes high)

Anyway, one of my friend said a contact caching is preferred with any iterative solver, I wonder if this is true??
Advertisement
the things you say you havn't implemented are what 'make' sequential impulses stable and require less iterations :P

the things you say you havn't implemented are what 'make' sequential impulses stable and require less iterations :P


Yup, i second that...

If you do things right (and this takes a *lot* of tweaking/improvement), you will be able to get your stack to be stable in just 5 iterations (which is all we could afford on LBP PSP) :)

Cheers, Paul.
Thing is, I don't know how to cache contact. I need a demo/paper/source of contact caching in 3D. Anyway, does anyone can give me a pointer? Im getting close *oh tear drops* to it...I THANK you very2much for that. As you can see I'm panic here...I need a prove, in 3d. Perhaps a small demo?
Read Erin Catto's GDC presentations. Some of them contain a version of Box2D Lite which is a simplified version of Box2D. Start with a simple sphere on a plane. Then a simple sphere stack. Next I would move on to boxes. Finally add a spherical joint and create a simple pendulum. I would basically port the Box2D version to 3D. You will learn a lot from this!

-Dirk
@Don: I did man, download the attached demo to see it. I just dont understand what to do when I have found a new contact with matching ID.
I know I should:
-Grab the accumulated impulse info
But should I also:
-Set the contact position to old contact position? I havent seen a port of Box2D in 3D...
Sorry doublepost.Im reading the ppt, but I wonder about contact ID in 3D. Anyone ever implementing it? Say there's a Vertex-Face collision. is it enough?

struct c_id
{
char cCase[2];
char cID[2];
};

cCase is the case id {VERT,EDGE,FACE}; and cID is the id. I smell failure here...
Box2D uses SAT for collision detection. If the axis of minimum penetration comes from a face you build a face contact. If the contact comes from an edge pair you build an edge contact. That is all! Don't get too complicated. All you need to do is to clip the reference face against the side planes of the incident face and keep all points below the reference face in first case. In the second case you use the closest points between the edge segments.

So all you now need is a structure which creates an ID from which features the contact was constructed. Here is what I use:


union plContactID
{
struct
{
plUInt8 mFeature1; // Face: Reference face Edge: First edge
plUInt8 mFeature2; // Face: Incident face Edge: Second edge
plUInt8 mFeature3; // Face: Incident vertex Edge: Empty
plUInt8 mFlags; // Distinguish between face and edge contact
};

plUInt32 mKey;
};

@Don: I know all the clipping stuff. My coldet is working well. Im just confused at caching contacts. I umm dont understand your code, can you explain a lil bit more? and have you download my demo? perhaps you could find some bugs or what? thx in advance :)
Your demos look good, but you should get stable stacks at 100 iterations. If I understand you post correctly you only apply only one tangential friction impulse in the direction of the relative velocity. This would be *not* correct. As you compute the normal at the beginning of the iteration and build the Jacobians you need to build *two* perpendicular tangent directions. It is a good idea to align the first axis with the relative tangent velocity before you enter the solver loop. You also need to have these tangent directions if the relative tangent velocity zero. Then you just create two arbitrary tangent directions.


HTH,
-Dirk

This topic is closed to new replies.

Advertisement