Cordova : detecting shaking

For I Met, I needed to detect shaking to allow users adding each other to their timeline by simply shaking their phone at the same time. I did a little search and found leecrossley’s shake.js script but it didn’t really work. Thus I slightly improved it to write this one.

Here is a small sample on how to use it :

// Let's wait for the user to shake it !
shake.startWatch(onShake);

function onShake()
{
  alert('Oh yeah, you shook it !');
}

// Stop watching for shaking event
shake.stopWatch();

Here is the script :

var shake = (
  
  function ()
  {
  	var shake = {},
  		watchId = null,
  		options = { frequency: 300 },
  		previousAcceleration = { x: null, y: null, z: null },
  		shakeCallBack = null;
  	
  	// Start watching the accelerometer for a shake gesture
  	shake.startWatch = function (onShake)
    {
  		if (onShake) {
  			shakeCallBack = onShake;
  		}
  		watchId = navigator.accelerometer.watchAcceleration(getAccelerationSnapshot, handleError, options);
  	};
  	
  	// Stop watching the accelerometer for a shake gesture
  	shake.stopWatch = function ()
    {
  		if (watchId !== null) {
  			navigator.accelerometer.clearWatch(watchId);
  			watchId = null;
  		}
  	};
  	
  	// Gets the current acceleration snapshot from the last accelerometer watch
  	function getAccelerationSnapshot()
    {
  		navigator.accelerometer.getCurrentAcceleration(assessCurrentAcceleration, handleError);
  	}
  	
  	// Assess the current acceleration parameters to determine a shake
  	function assessCurrentAcceleration (acceleration)
    {
      var accelerationChange;
  		if (previousAcceleration !== null)
      {
  			accelerationChange = Math.abs(Math.round(Math.abs(previousAcceleration.x) - Math.abs(acceleration.x))) + Math.abs(Math.round(Math.abs(previousAcceleration.y) - Math.abs(acceleration.y))) + Math.abs(Math.round(Math.abs(previousAcceleration.z) - Math.abs(acceleration.z)));
  		}
  		
      // Shake detected :
      if (accelerationChange > 10)
      {
  			if (typeof (shakeCallBack) === "function")
        {
  				shakeCallBack();
  			}

  			shake.stopWatch();

  			setTimeout(shake.startWatch, 1000);

  			previousAcceleration = { 
  				x: null, 
  				y: null, 
  				z: null
  			}
  		}
      else
      {
  			previousAcceleration = {
  				x: acceleration.x,
  				y: acceleration.y,
  				z: acceleration.z
  			}
  		}
  	}

  	// Handle errors here
  	function handleError()
    {

  	}
  	
  	return shake;
  }

)
();

And here is the minified version :

var shake=function(){function s(){navigator.accelerometer.getCurrentAcceleration(o,u)}function o(t){var n;if(r!==null){n=Math.abs(Math.round(Math.abs(r.x)-Math.abs(t.x)))+Math.abs(Math.round(Math.abs(r.y)-Math.abs(t.y)))+Math.abs(Math.round(Math.abs(r.z)-Math.abs(t.z)))}if(n>10){if(typeof i==="function"){i()}e.stopWatch();setTimeout(e.startWatch,1e3);r={x:null,y:null,z:null}}else{r={x:t.x,y:t.y,z:t.z}}}function u(){}var e={},t=null,n={frequency:300},r={x:null,y:null,z:null},i=null;e.startWatch=function(e){if(e){i=e}t=navigator.accelerometer.watchAcceleration(s,u,n)};e.stopWatch=function(){if(t!==null){navigator.accelerometer.clearWatch(t);t=null}};return e}()

3 Comments

    • Ivan Gabriele   •     Author

      Sorry I don’t check comments so regularly. I will check that soon and give a hand if necessary !

  1. seomilano.us   •  

    Aw, this was a really nice post. Finding the time and actual effort to make a very good article… but what can I say… I put things off a
    lot and never seem to get anything done.

Leave a Reply

Your email address will not be published. Required fields are marked *