// Find a distance between the two masses
CVector3 vForce(0.0, 0.0, 0.0);
CVector3 vDistance = m_pPoint1->m_Position - m_pPoint2->m_Position;
double r = vDistance.Magnitude();
if (r != 0.0 ) // Check if the distance is not 0
{
// Calculate a normal vector of the spring
m_Normal.n[0] = vDistance.n[1] / r;
m_Normal.n[1] = -vDistance.n[0] / r;
// Add the spring force
vForce += (vDistance / r) * (r - m_Length) * (-m_SpringConstant);
}
// Add the friction force
vForce -= (m_pPoint1->m_Velocity - m_pPoint2->m_Velocity ) * m_FrictionConstant;
// Apply forces to the masses
m_pPoint1->AddForce (vForce);
m_pPoint2->AddForce (-vForce); // The opposite of force is applied to m_pPoint2
Unstable spring
Hi!
I guess that you've heard that thousands times. Still, I would like to ask you for a help. The problem is that my simulation gets terribly unstable (simply saying - it blows up). The cause lays somewhere in solve() method of a spring class. When Friction/SpringConstant reach more/less 500.0 everything crashes.
If you could, I'd be thankful for looking at the code /quite self-explanatory I hope/ :
Let me know if you find that the way I compute spring forces is wrong.
Thanks in advance!
i dont even have to look at your code to tell you its not a problem with your code, but a fundamental problem with the method you are using.
If you're using a first-order forward Euler integrator, an undampened spring will never be stable. You have to add a certain amount of damping (force counteracting velocity) to get it to work.
Or you can change to something like a fourth-order Runge-Kutta integrator; if you implement that with numeric error cancellation, you can oscillate for hours on end :-)
Or you can change to something like a fourth-order Runge-Kutta integrator; if you implement that with numeric error cancellation, you can oscillate for hours on end :-)
Um, do you mean it crashes when the spring constant is really high? If so, that's normal. The higher spring constants cause larger errors.
Hi, folks! Sorry for the late reply.
Yes, that's the method I use.
So you suggest changing the integrator? That's pretty obvious! Why didn't I think about that? :) I need to try this solution.
I'll take a look at your link, Gaffer.
Great thanks people!
Quote:Original post by hplus0603
If you're using a first-order forward Euler integrator, an undampened spring will never be stable.
Yes, that's the method I use.
Quote:
Or you can change to something like a fourth-order Runge-Kutta integrator; if you implement that with numeric error cancellation, you can oscillate for hours on end :-)
So you suggest changing the integrator? That's pretty obvious! Why didn't I think about that? :) I need to try this solution.
I'll take a look at your link, Gaffer.
Great thanks people!
Quote:Original post by clapton
So you suggest changing the integrator? That's pretty obvious! Why didn't I think about that? :) I need to try this solution.
Before you try a more complicated integrator, try using Verlet and/or Semi-implicit Euler with position/displacement clamping. I've been using this method since 1990 (Amiga:VR-Slingshot; stable with integer/fixed-point systems as well), very easy to implement, fast, and 100% no-matter-what-stable. I experimented with RK2 (midpoint) and RK4, but found that the extra complexity/overhead (and energy loss with RK4) was not an improvement over clamped/constrained Verlet/Semi-implicit Euler (or "Euler-Verlet"). Even RK4 will blow up without clamping (not guaranteed to be 100% no-matter-what-stable).
See my posts here (follow links to earlier posts):
http://www.gamedev.net/community/forums/topic.asp?topic_id=344865.
You can implement these concepts in a matter of minutes given an existing explicit Euler integrator.
Thanks, John!
I think I'll go for you advice. The problem is that I still have to little knowledge on mathematics. I've never done anything with integration (yet) so RK4 seems a bit complicated to me. Anyway, I'll keep on learning. If it doesn't bring result I will try something easier (Verlet, Midpoint ...).
I think I'll go for you advice. The problem is that I still have to little knowledge on mathematics. I've never done anything with integration (yet) so RK4 seems a bit complicated to me. Anyway, I'll keep on learning. If it doesn't bring result I will try something easier (Verlet, Midpoint ...).
I found RK4 confusing at first too, but after actually coding it and getting to know it (mostly from Gaffer's tutorials) I now find it to be quite logical and simple. And I must say, the thing is several orders of magnitude more stable than my Euler thing, especially when the forces are quickly changing (springs/gravity).
This topic is closed to new replies.
Advertisement
Popular Topics
Advertisement