You are reading a single comment by @Gordon and its replies. Click here to read the full conversation.
  • Hi,

    What do you mean by // Workaround for clear fail in the comments? Are you expecting clearInterval to reset the variable passed into it? I'm afraid that doesn't happen (in Espruino or in other JS interpreters).

    That means that if you're doing if (foo!==undefined) clearInterval(foo); you need to be writing if (foo!==undefined) { clearInterval(foo); foo=undefined; }, or next time around the loop it'll try and clear the interval that has already been cleared.

    Simply doing that in your code fixes it:

    var DURATION = 2000;
     
    function sign(num) {
      return Math.round(Math.abs(num) / num);
    }
     
    function round(num, decimals) {
      return (Math.round(num * Math.pow(10, decimals))) / Math.pow(10, decimals);
    }
     
    var currentIntensity = 0;
    var interval;
    var stepInterval;
     
    function dim(intensity, time, steps, cb) {
      console.log('run to', intensity);
      if (typeof intensity == 'undefined') intensity = 0;
      if (typeof time == 'undefined') time = 1000;
      if (typeof steps == 'undefined') steps = 100;
      var freq = time/steps;
     
      var intensityStep = round((intensity - currentIntensity) / steps, 2);
      var signStep = sign(intensityStep);
      intensityStep = Math.abs(intensityStep);
     
      if (typeof stepInterval != 'undefined') {
        console.log('clearing stepInterval', typeof stepInterval, stepInterval);
        clearInterval(stepInterval);
        console.log('should have cleared stepInterval', typeof stepInterval, stepInterval);
        // Workaround for clear fail
        stepInterval = undefined;
      }
     
      stepInterval = setInterval(function() {
        currentIntensity = currentIntensity + (intensityStep * signStep);
        if (sign(intensity - currentIntensity) != signStep) {
          console.log('done', currentIntensity);
          currentIntensity = currentIntensity - (intensityStep * signStep);
          console.log('done', currentIntensity);
          clearInterval(stepInterval);
          stepInterval = undefined;
          if (typeof cb !== 'undefined') cb();
        }
        if (typeof interval !== 'undefined') {
          clearInterval(interval);
          interval = undefined;
        }
        interval = setInterval(function() {
          digitalPulse(LED1, 1, Math.abs(currentIntensity * 10));
        }, 10);
      }, freq);
    }
     
    var self = this;
    function callback() {
      return dim(Math.round(currentIntensity) === 0 ? 1 : 0, DURATION, 100, callback);
    }
     
    dim(1, DURATION, 100, callback);
    

    Personally I'd just check for undefined with !== undefined too - it's easier to write and a bit quicker.

About

Avatar for Gordon @Gordon started