Spring Physics


Introduction

Hi, I’m Glenn Fiedler and welcome to the fourth article in my series on Game Physics.

In the previous article we discussed how to simulate the motion of rigid bodies in 3D.

Now we’re going to discuss spring physics.

The physics behind springs is simple but extremely versatile and useful. You can use springs to link points together to model rope and string, cloth, and even blobs of jelly. Springs can also be used to implement basic collision response, and to create joints that constrain the motion of rigid bodies.

The more physics programming you do, the more springs pop up. Many physical phenomenon boil down to spring-like forces being applied such as buoyancy in water. Springs are everywhere so lets discover how to simulate them!

Spring and dampers

The most basic expression describing springs is Hooke’s Law. Essentially this says that the spring force is simply proportional to the length of the spring:

    F = -kx

Where x is the vector difference in position between the two points making up the spring, and k is a constant describing the tightness of the spring. Larger values of k mean that the spring applies more force between the two points that it connects so the spring will stretch less per unit of force, smaller values mean the spring is looser and will stretch further. The negative sign in the equation simply indicates that the force acts to bring the two points at the end of the spring together instead of pushing them apart.

Newton’s third law says that every force has an equal and opposite force. If two objects a and b are connected together by a spring then the spring will apply one force which pulls object a towards object b, and an equal and opposite force pulling object b towards a. However, if you want to attach one object to a fixed point in space its correct to only apply the force of the object in one direction. This is actually physically correct because by assuming the anchor point cannot move you are effectively saying that its mass must be infinite, hence any force applied would not have any effect anyway.

Spring forces alone are not much use though. You need to combine them with dampers to have a realistic simulation. Damping simulates energy loss, and it is used in physics simulations to make sure that springs don’t oscillate forever but come to rest over time. The simplest spring-damper system can be modeled as follows:

    F = - kx - bv

Where b is the coefficient of damping and v is the relative velocity between the two points connected by the spring. Larger values for b increase the amount of damping so the object will come to rest more quickly, b=0 will allow the spring to oscillate forever, while negative values will actually accelerate the objects over time making your simulation explode.

The importance of a good integrator

This brings me to a very important point. Perhaps I was overly harsh in my first article when it comes to the Euler integrator. There are situations where you don’t need the full accuracy of RK4. For example, if you are just simulating basic rigid body dynamics and collision response you can probably get away with just an Euler integrator. Euler integration is not inherently crap.

However, my harshness was inspired by a few things. Firstly, its really not that hard to implement an RK4 integrator. Secondly, in my experience, most physics simulation time is spent in collision detection and response, not in the integrator. Using an Euler integrator instead of RK4 is not going to add a significant computation overhead to your physics simulation unless you are doing a simulation of thousands of particles. The bottom line is that for most applications in game physics, there is little reason not to use RK4.

But the real reason I love using an RK4 integrator is this: its significantly increases the tightness of the springs that you can model. Given that a lot of physical phenomenon end up applying spring like forces, if you plan on doing any serious modeling of forces in your simulation, it really pays to use a high accuracy integrator like RK4. If you have ever used Euler integrators and springs in a physics simulation then you know how frustrating it feels when your simulation explodes.

Variations on springs

There are many different variations on spring-damper systems, but what I want to do is explain how to think generally in terms of what the forces are doing so that you can easily design spring and damper systems to achieve whatever effect you want.

The first thing is that springs don’t only have to act to pull two points together so that they lie on top of each other. For example you can design spring forces that pull together or push apart two points apart so they maintain a desired separation distance from each other:

    F = -k(|x|-d)(x/|x|) - bv

Where |x| is the distance between the two points connected to the spring, d is the desired distance of separation, and x / |x| is the unit length direction vector between the two points: a to b, when applying the force to point a and vice versa.

The overall effect of the force equation above is to have a force which pushes the two points connected by the spring apart if they are closer than distance d, and bring the two points together if they are further than d apart. Notice how the force becomes exactly zero when the two points are at the target distance? If you tune the k and b parameters correctly you can have a nicely behaving spring that quickly brings the two points together smoothly over time and comes to rest at the solution point.

But why apply springs to position only? If you want to accelerate a body over time such that it accelerates to a certain speed then you can calculate a spring force proportional to the difference between the current velocity and the target velocity, combined with a damping proportional to the current velocity so that it reaches its target over time instead of cycling about it. This is usually called a motor in physics simulation.

We can even apply the same concept to drive the spinning of an object at a certain speed by applying a spring torque proportional to the difference between the current angular velocity and the desired angular velocity, coupled with a damper force proportional to the current angular velocity.

Another commonly implemented spring constraint is to enforce a upright orientation of a body, for example, you could apply a spring torque proportional to the difference between the current orientation and an upright orientation, coupled with a damper proportional to angular velocity. Such a constraint is called a ’stay upright constraint’ and its often used for sci-fi hover racing games.

As you can see, the applications of springs are limitless. The overall pattern is to design spring forces that will attract your physics simulation into the desired state and fade off to zero when this state is has been reached. In order to make sure that your physics objects don’t just oscillate around the solution but actually reach it, it is necessary to apply damping proportional to whatever physics state values are performing the evolution of the simulation towards the solution over time.

Attachment using a spring

So lets get started with an actual concrete implementation of using springs a simulation. The first thing we will implement is an attachment joint that will allow the user to click and drag a point on the cube to move it around. We will implement this by modeling a tight spring attachment between a target point and an attachment point on the body of the cube. This is effectively a ball and socket joint implemented using only spring forces and is implemented using the standard equation we are used to:

    F = -kx -bv

Where x is the vector difference between the current target point and the attachment point on the object, and v is the point velocity at the attachment point on the object. The important thing is that this velocity v being the point velocity means that it incorporates both the linear motion of the object plus any velocity at the attachment point due to angular velocity. As was shown in the previous article we can calculate this point velocity at follows:

    vpoint = vlinear + vangular cross (p - x)

Where p is the point on the rigid body and x is the center of mass of the object. Secondly, this spring and damper force is not just applied linearly, but is applied at the attachment point on the object. This means that the spring force will apply both a linear force and a torque component as follows:

    Flinear = F
    Ftorque = F cross (p - x)

The overall effect of this joint then is to bring the target and attachment points together while damping the motion of the object at the attachment point. This allows the object to move as long as remains still at the attachment. In other words the object is only allowed to move by rotating about the attachment point. Our simple ball and socket joint is now complete.

Collision response with springs

Next we will implement a basic collision response using springs. The trick here is to apply a spring and damper force that works against what we don’t want, eg. objects moving towards each other and penetrating other objects.

So we have a collision detected and the usual information is returned to the physics system ready to apply collision response. This information is typically something like:

  1. A unit length collision normal
  2. The penetration depth along the normal
  3. The physics state for each of the colliding objects at the time of collision

All this information grouped together is called a contact. Processing collision geometry and returning a series of generic contacts is a great idea because it decouples your collision response from the gritty details of collision detection.

Once we have all our contact information a simple collision response can be implemented by applying a spring-like force to the colliding objects to keep them apart:

    F = nkd - bn(n.v)

Where k and b are the spring-damper coefficients, n is the contact normal and v is the relative velocity between the two objects at the point of collision. Effectively this equation calculates a spring force that pushes out along the contact normal while reducing the relative velocity of the objects towards each other at the contact point.

Various different collision responses types can also be achieved using this equation, for example setting b to 0 gives a completely elastic collision response where all energy going into the collision returns in the bounce over time. Setting b to higher value tend to make the collision more inelastic because it removes more energy during the collision. Finally, by increasing and decreasing the spring constant k in concert with b you can make a collision that feels like anything from bouncing off a trampoline (low k and low b), to landing and sinking into quicksand (low k and high b), or landing with a splat on concrete (high k, high b).

The weakness of springs

It seems we can achieve a large variety of different collision effects using only springs and easily make joints and constraints. Its not all good news however because springs come with their own set of weaknesses which I will now explain.

The first weakness is that its difficult to tune the spring constants to get exactly the effect you want. For example, if you are attempting to model the real world physics of an object, you will need to experiment to find the spring k and b values that match the simulation. These values are usually dependent on other values of your simulation, such as the gravity constant, meaning that if you adjust gravity you’ll need to retune your springs to get the same effect. This is a pain.

The next problem is that tighter the spring k you use, the more difficult it becomes to solve the differential equation. Using an RK4 integrator sure help with this, but even with RK4 there is a fundamental limit to how large you can make your spring k before your simulation will explode. At this point you need to either decrease your timestep or reduce your spring k.

The final, and major weakness is that springs are reactive not predictive. This is a subtle point but a very important one. A joint or constraint implemented using springs only works by correcting errors after they occur, and collision response using springs requires allowing some amount of penetration before it acts to correct it and so forth. More advanced techniques exist which can solve for the forces required to constrain the physics simulation without inducing error, such as LCP solvers or iterative methods, but they are out of scope of this simple article!

Conclusion

You can use spring-like forces to model many different physical effects, and they are a lot of fun to implement.

The only downside of springs is of course that they are best used for implementing soft and springy constraints, but most of the time when you are using springs, this is exactly the effect you are looking for!

Thats it for springs, lets move on to another topic.

In the next article, I discuss how to network your physics simulation.

  1. Kris Nye
    September 24, 2006 at 10:20 am | #1

    If you model springs as an energy conversion (compression energy to kinetic energy and back again), then you can avoid any possibility of them ‘exploding’.

  2. October 19, 2006 at 11:54 am | #2

    Suppose a block(of mass m) moving on a plane collides against a spring kept longitudinally alond the plain.if v is the velocity of the block before collision , what would be the velocity after the block rebounds

  3. Daniel Trottier
    October 28, 2006 at 12:12 pm | #3

    We are graduate students doing a term paper on collision detection. We find the format of your articles easy to understand and apply. Any chance that your article on collision detection will be out soon…a draft version sent by email would be great :) .

  4. Johan
    November 15, 2006 at 10:19 pm | #4

    This article was very interresting and written in an easy to understand way.

  5. November 21, 2006 at 1:07 pm | #5

    I’d love to see an implementation that uses energy instead, as per comment #1. I’ve heard programmers of racing simulations do their hard springs that way (suspension/tires).

    For a more generic method on reaching velocities and such (motors) readers should definitely check out PID controllers (proportional/integral/derivative) which can be used as a base for such things.

    Lastly, for really stiff springs I’ve used implicit integration, which can also help to keep systems from exploding (quite effectively).

  6. November 21, 2006 at 1:29 pm | #6

    Hi Glenn, these articles are mint – thanks for writing them. There is reference to code for this one on springs, but I can’t find it anywhere. I’m also really keen on the collision detection stuff.

    Cheers!

  7. November 26, 2006 at 7:50 pm | #7

    yeah i’m real sorry i never got around to coding a good springs example, as i pushed headlong into “zen of network physics” using the codebase — if i get some free time i’ll try to find my old code with mouse select and drag on the cube using a spring

    note that the collision detection in the network example with the cube is using springs as described in this article

    cheers

  8. Alex
    November 30, 2006 at 11:47 pm | #8

    Great article, thanks. If you use springs to control a collision response, they alter the acceleration fine, but what happens if the object is colliding at a fairly high speed? It would set the acceleration in the opposite direction, but it would fly straight through, since it would take a while for the velocity to reset to 0 and change direction.

    Do you have any ideas on how to tackle this issue? I don’t want my hypothetical ball flying straight through the concrete ground, if he goes a bit fast.

  9. December 1, 2006 at 4:41 am | #9

    A bit of code from my implicit spring calculation (for a wheel with stiff suspension):

    velocity.y=(velocity.y+RR_TIMESTEP*forceNonDamper.y*oneOverMass)/(1.0f+springK*oneOverMass*RR_TIMESTEP);

    Here ‘y’ is the vertical axis.
    Note that I never understood restricting explosions using energy; although I know potential and velocity energy, springs that get external input (a wheel touching the road) brings energy into the spring system, so I never quite grasped how you could limit the amount of energy flowing into it all.

    Anyway, terrific articles, they really fit nicely into my line of thinking, meaning they explain things well for me. :)

  10. Kevin
    January 12, 2007 at 11:36 am | #10

    Excellent articles!

    Is there any word on the collision detection article?

  11. January 19, 2007 at 1:27 am | #11

    hi,
    This is an excelent alternative to Impulse based collision response (i checked out your networking section and the accompanying code) as it is simple and effective (as long as the sim runs at small timesteps).

    What are the implication for multibody dynamics? I am not looking for stacking or contact resolution as the current implementation handles these in a firly effective manner, but once you end up with, say, 50 bodies, all colliding in a small area, can the spring model really handle this?
    I am guessing itterating over a scene-graph would make life easier.

  12. January 19, 2007 at 11:36 pm | #12

    i dont really propose this as any sort of new alternative, its just an easy way to get a handle on the problem — google for “penalty method” and you’ll see its this same approach

    its downsides are:

    - springs are reactive, constraints are soft not hard
    - small time step requirement
    - lots of tuning required…

  13. Hannes
    June 29, 2007 at 11:58 am | #13

    Excellent article! Thanks alot! This article makes *alot* more sense than the other articles I have read on spring physics. I coded this in a few minutes and it worked perfectly. Previous attempts gave very ehh… interesting results. This page should really be ranking higher on Google!

  14. June 30, 2007 at 3:19 pm | #14

    understood, so help me out, link to my article guys! :)

    =)

  15. Nic
    August 12, 2007 at 12:10 pm | #15

    Hi Glenn,

    These articles are fantastic, thank you very much for explaining these topics in such comprehensive detail. I am interested in the spring response technique to collisions, but I am having difficulty understanding the particular equation you explained:

    F = nkd – bn(n.v)

    Whilst this is a nice solution to the problem at hand, surely the greater the velocities of the objects, the smaller the force will end up? For example a fixed flat surface, and a ball bouncing on it, if the ball is travelling downwards towards the surface faster, the force response would be smaller than if the ball was travelling slower toward it, which would seem to be the opposite of what you’d expect? Maybe I am missing something, but thank you for these fantastic resources all the same!!

  16. August 13, 2007 at 4:17 pm | #16

    its a vector quantity, so no, the velocity will not be smaller as the object moves faster towards the surface, it will in fact be larger, and proportional – just reflected *away* from the surface so it bounces

    cheers

  17. David
    October 5, 2007 at 5:21 am | #17

    Ftorque = F x (p – x)

    Is that “torque = force [cross-product] (offset_from_center – center_of_mass)”?

  18. October 5, 2007 at 11:59 am | #18

    yep – the equation formatting was lost when i imported into wordpress, fixed it up so its more clear now

    cheers

  19. David
    October 26, 2007 at 8:05 pm | #19

    Thanks, this article helped me out a lot.

  20. David
    October 26, 2007 at 9:09 pm | #20

    Yet another question about that same equation:
    Does it solve for rotations per time unit or for radians per time unit?

  21. October 26, 2007 at 9:58 pm | #21

    yep the magnitude of the angular velocity will be in radians / sec

    but, the torque is in newton meters (force times distance)

    see this page for details http://en.wikipedia.org/wiki/Torque

  22. David
    October 26, 2007 at 10:21 pm | #22

    That was a quick response. Thank you so much for all the help.

    I think I may have been getting confused because I had too low of a moment of inertia in my simulation so it looked like the object was spinning too much.

  23. December 26, 2008 at 9:31 am | #23

    Linked this article as an excellent resource about simulating springs.

    http://www.gamitude.nl/?p=134

  24. Chris
    December 27, 2008 at 5:57 pm | #24

    Hi,

    If both ends of the spring can move, how would you manage the caching of the inverse spring force, after you calculated it for one end. Would you cache the results of all the 4 runge kutta integration steps and reuse them during integration of the other end, or is just the force of the currtent state reuseable?

    thanks

  25. December 28, 2008 at 5:15 pm | #25

    you dont cache it, you have to reevaluate the spring forces at each RK4 step

    cheers

    • Chris R.
      September 9, 2009 at 3:52 pm | #26

      When dealing with multiple bodies attached to each other would you argue for or against moving neighboring nodes for calculating each RK4 step?

  26. July 21, 2009 at 12:47 pm | #28

    Great series of articles. thanks!

    However, the springs article seems to be the only one that you didn’t offer the source code with it. Is it available? I find it interesting to be able to walk through the code – even though I am not a C++ guy anymore (or at least, not frequently). I have ported the others to my Java/Eclipse framework, though.

    TIA

    • July 22, 2009 at 9:37 am | #29

      hey ric, take a look at the example for the networking article it contains spring based collisions using the RK4, cheers

      • July 22, 2009 at 12:23 pm | #30

        Ah, I hadn’t actually read that article yet as my interest in networking is limited. I’ll check it out now… :-) Thanks again. And to second (or third) the others on these threads, I would be interested in the article on collisions.

        And BTW, I did donate, though not enough for two weeks of your spare time! :-)