mdgriffith / elm-bezier / Bezier.Spring

Spring calculations!

This module really does 3 things.

  1. Find a spring that will settle in a certain amount of time.
  2. Calculate the position of an item at a certain time using a spring.
  3. Calculate the Bezier segments that will approximate the spring motion.


type alias Parameters =
{ stiffness : Basics.Float
, damping : Basics.Float
, mass : Basics.Float 
}

The parameters that define a spring.

Check out the presets or new if you want some help constructing these values.

new : { wobble : Basics.Float, quickness : Basics.Float, settleMax : Basics.Float } -> Parameters

Normally when working with springs you have to choose a stiffness and a damping and they'll have seemingly arbitrary values like 216 or 14. This can be very hard to develop an intuition for!

Your first option is to use one of the preselected springs.

The next option could be using this function.

It takes:

Preselected Springs

noWobble : Parameters

gentle : Parameters

wobbly : Parameters

stiff : Parameters

at : { spring : Parameters, target : Basics.Float, initial : { velocity : Basics.Float, position : Basics.Float } } -> Duration -> { velocity : Basics.Float, position : Basics.Float }

Calculate the spring's current position and velocity given a spring, a duration, a target position, and an initial state.

stepOver : { spring : Parameters, target : Basics.Float, stepSize : Basics.Float, initial : { velocity : Basics.Float, position : Basics.Float } } -> Basics.Float -> { velocity : Basics.Float, position : Basics.Float }

Iteratively step through a spring to get the final position and velocity.

at is faster, but possibly less accurate?

settlesAt : Parameters -> Basics.Float

We can detect when a spring will settle if it is underdamped (meaning it oscillates before resting)
<https://en.wikipedia.org/wiki/Settling_time>

However for critcally and overdamped systems it gets a lot more complicated.
Fortunately, I'm not sure that that's an issue as I don't think we want to model overdamped spring systems for animation.
https://electronics.stackexchange.com/questions/296567/over-and-critically-damped-systems-settling-time

segments : Parameters -> { position : Basics.Float, velocity : Basics.Float } -> Basics.Float -> List Bezier.Spline

Given a spring, a starting position and velocity, and a target position, calculate the list of Bezier segments that will approximate the spring motion.

This does assume that the spring settles. It will return a maximum of 10 segments.

peaks : Parameters -> Duration -> Basics.Float -> { velocity : Basics.Float, position : Basics.Float } -> List Basics.Float

zeroPoints : Parameters -> Duration -> Basics.Float -> { velocity : Basics.Float, position : Basics.Float } -> List Basics.Float