Search code examples
javascriptgraphphysics

How to smoothly increase a number to Y in X milliseconds exponentially


I'm making a semi-realistic 'physics' engine in node.js, if you can even call it that and I want to accelerate exponentially. E.g. from 0m/s to 4.5m/s in 2 seconds, then maybe decelerate to 0m/s in 3 seconds. Obviously for the deceleration part I can probably get away with inputting a negative number.

Here's a picture of what I'm thinking of, not sure if what I expect in the graph is the same thing as exponents.

enter image description here

I don't have any code, I thought I could base it off something like setInterval, but that would be linear.


Solution

  • You're right SetInterval can only provide with a fixed speed whereas what you need is dynamic speed.

    One way is to make two arrays with an equal number of items. With first array named duration and second name speed. The variable Y will be changed by the speed for the duration corresponding to the # of the speed. See here :

    var Y = 0; // The variable that is to be changed
    var speed = [4.5, 0, -4.5]; // The acceleration in m/s
    var time = [2, 4, 2]; // Duration corresponding to each acceleration in s
    var sec = 1000; // 1 second = 1000 milliseconds
    var i = 0; // A counter to remember the item number in the arrays
    var dur = 0; // A variable to hold the duration for which a particular speed has currently lasted. This variable helps to validate the duration for which the Y is changed.
    
    // The function that holds the logic
    function tick() {
    
      // Checking if duration is equal to or has crossed the user specified duration for the speed
      if(dur >= time[i]*1000){
        // If yes, move on to the next speed and duration
        i++;
        dur = 0;
        if(i > speed.length-1){clearInterval(loop);} // If there are no more items in the array stop the interval
      }
      else {
        // If not, continue increasing Y and dur
        Y = Math.round(Y*1000 + (speed[i]/50)*1000)/1000 // A simple workaround to avoid the error in arthimetic calculation that occurs while using floats (decimal numbers) in JS.
        console.log(Y); // This line is only for debugging purposes. IT CAN BE REMOVED
        dur += sec/50;
      }
    }
    var loop = setInterval(tick, sec/50);