8
\$\begingroup\$

I basically want my camera in 3D move automatically. Currently, I have linear movement which is rather dumb, so I'd like to do a bouncing movement.

However, what is a good equation for bouncing? I mean, for a circle you can do y = sqrt(1 - x^2), but if I were to have a bouncing graph, what would the corresponding formula be? I guess it's something with abs as it has to 'bounce'. Something like (I made this up with Paint): bouncing graph

What is a good equation that results in such a graph? The transformations I can do myself I guess, but I'm just looking for the kind of equation.

\$\endgroup\$
8
  • 3
    \$\begingroup\$ Perhaps you could use something along the lines of: y = abs(cos(x*5)*max(1-x,0)) \$\endgroup\$
    – Kromster
    Mar 28, 2011 at 11:44
  • 6
    \$\begingroup\$ Using a graphical equation will not help you apply natural looking accelerations to the system. You may be surprised to find how easy it would be to simply use basic Newtonian equations here. Give the object a little mass and momentum and let the force of gravity and Newton handle the accelerations & position changes. It's far easier than you may think. \$\endgroup\$
    – Steve H
    Mar 28, 2011 at 12:24
  • 1
    \$\begingroup\$ @SteveH You should put this to answer. \$\endgroup\$
    – Notabene
    Mar 28, 2011 at 13:29
  • \$\begingroup\$ @notabene yeah, I was sitting on the fence with that and you pushed me to that side. Thanks. I hesitated because I didn't want to spend the 15 minutes to provide a pseudo code solution. \$\endgroup\$
    – Steve H
    Mar 28, 2011 at 14:07
  • \$\begingroup\$ @Krom: Thanks, I currently have: y = abs(cos((x+18)/6.2)/((x+18)/6.2))*149. @SteveH: Could you possibly tell the key terms in Newtonian solutions? I seem to be using the wrong ones as I can't really find a good example on how to implement it. \$\endgroup\$
    – pimvdb
    Mar 28, 2011 at 14:10

5 Answers 5

8
\$\begingroup\$

Using a graphical equation will not help you apply natural looking accelerations to the system. You may be surprised to find how easy it would be to simply use basic Newtonian equations here. Give the object a little mass and momentum and let the force of gravity and Newton handle the accelerations & position changes. It's far easier than you may think

\$\endgroup\$
5
  • \$\begingroup\$ Example of the said equation in your answer would be great :) \$\endgroup\$
    – Kromster
    Mar 28, 2011 at 18:29
  • 1
    \$\begingroup\$ en.wikipedia.org/wiki/Equations_of_motion \$\endgroup\$
    – Adam
    Mar 28, 2011 at 21:48
  • 2
    \$\begingroup\$ here is the example: xna.multigan.com/pastebin/?page=view&id=1301401080 I wrote it in XNA but I think it can be read as pseudo code as well \$\endgroup\$
    – Steve H
    Mar 29, 2011 at 12:24
  • \$\begingroup\$ Thanks so extremely much! You definitely deserve the answer as being the accepted one :) \$\endgroup\$
    – pimvdb
    Mar 29, 2011 at 14:28
  • 1
    \$\begingroup\$ This is what I ended up with (JavaScript): jsfiddle.net/Cf9H4. \$\endgroup\$
    – pimvdb
    Mar 29, 2011 at 15:47
4
\$\begingroup\$

Instead of providing a direct answer I want to point you in the right direction. If you google for AI for moving entities you will find algorithms using variables like speed, mass, velocity and accerelation. If you add the gravitational force into the equation you should get realistic behaviour.

As stated in one of the comments to your questions it is not that complicated.

I recommend Programming game AI by example which I found very helpful.

I also found this link explaining the forces involved for a bouncing ball.

\$\endgroup\$
3
\$\begingroup\$

If your movement should look a lot like your graph, you could make use of a bounce easing equation like this one (source):

// BOUNCE EASING: exponentially decaying parabolic bounce
easeOutBounce = function (t, b, c, d) {
    if ((t/=d) < (1/2.75)) {
        return c*(7.5625*t*t) + b;
    } else if (t < (2/2.75)) {
        return c*(7.5625*(t-=(1.5/2.75))*t + .75) + b;
    } else if (t < (2.5/2.75)) {
        return c*(7.5625*(t-=(2.25/2.75))*t + .9375) + b;
    } else {
        return c*(7.5625*(t-=(2.625/2.75))*t + .984375) + b;
    }
};

easeInBounce = function (t, b, c, d) {
    return c - Math.easeOutBounce (d-t, 0, c, d) + b;
};

The movement would look in this graph (easeIn): bounce ease in

\$\endgroup\$
1
  • \$\begingroup\$ I must say this just works great. Apparently, it's not just one graph but a combination of x^2 variants. If I use easeOutBounce(50, 0, 50, 50) I get the bouncing effect with 50 steps, in the range 0 - 50. Thanks! \$\endgroup\$
    – pimvdb
    Mar 28, 2011 at 19:53
2
\$\begingroup\$

If you are looking for an equation closely but roughly describing a bounce, you can try:

y=(e^-x)*abs(4cos(5x))

where

  • "4" is the coefficient for the height of the drop and subsequent bounces,
  • "5" is the frequency of the bounces, and
  • the "abs" part is to give a sharp trajectory to the lower part of the bounce.
\$\endgroup\$
1
  • 1
    \$\begingroup\$ Nice. Why is this not upvoted more? \$\endgroup\$
    – JohannesA
    Nov 15, 2018 at 15:43
1
\$\begingroup\$

If you want bouncing then look into the Coefficient of Restitution. It's a value between 0 and 1 that represents the "bounciness" of the camera. A value of 0 means that no bouncing will occur when the object collides with the ground, and 1 means that the camera will bounce back up to it's original height after it has collided with the ground (in this scenario anyway).

The easiest way to implement it is to give your camera an initial velocity vector (call it u) and you want to find the final velocity vector after the camera has collided (lets call this v). Lets call the CoR e.

e = v / u

So all you need to do is multiply your initial velocity by the coefficient, negate this velocity (for it to travel in the opposite direction) and voila, you have your final velocity and if you keep doing this for every time it collides, you have your bouncing motion. This is assuming you have a flat plane that you want to bounce against, if you have a complex mesh you're colliding against, then instead of negating the vector, simply multiply it by the normal of the polygon you collide with (which is essentially what negation does on a flat plane).

Use some sort of position update function (Euler, Verlet or even RK4 - see this link) and it will make this task a lot easier.

Hope that helps (and I hope my maths isn't too far off :P)

\$\endgroup\$

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .