(function($) {
    
$.fn.odometer = function(settings) {

    settings = $.extend({}, $.fn.odometer.defaults, settings);    
    
    return this.each(function(){
        
        var $this = $(this); // store the actual counter
          
        var zeroSet = -settings.heightNumber; // position of the first 0
        var counter = parseFloat(settings.counterStart); // initialize counter with the start number

        // to store the digits of the number
        var integersArray = [];
        var decimalsArray = [];
        var digits = String(settings.counterStart).split('.'); // separate integers and decimals
        var numberOfDecimals = 0;
        var widthDot = 0;
  
        var width = settings.counterStart.length * settings.widthNumber + "px";
        var height = settings.heightNumber + "px";

		var animator = 0;
		var curr_elem = null;

		var delayTime = settings.delayTime;

        $this.css({
           "position"            : "relative",
           "overflow"            : "hidden",
           "width"               : width,
           "height"              : height,
           "background-position" : "top right"
        });
  
        var integers = digits[0];
        var j = integers.length-1;
        var k=j;
        for (var i = 0; i < integers.length; i++) {
            integersArray[i] = integers.charAt(j); 
            elem = $('<div class="counter_id_'+(k-i)+'" />').css({
               	height: settings.heightNumber,
            	width: settings.widthNumber,
            	float: 'left',
               	"background": 'url(\'' + settings.numbersImage + '\') no-repeat',
               	"background-position": "0 0"
            });
            $this.append(elem);
            j--;
        }
        
        if (parseFloat(settings.counterStart) != settings.counterEnd || (settings.counterEnd.toString() == 'false' && parseFloat(settings.counterStart) == 0) ) {
            if (settings.delayTime > 0) {
            	var counterInterval = setTimeout(advanceCounter,  delayTime);
            }
        }
        
        function advanceCounter() { 
            counter += settings.increment;
            setNumbers(counter);
        }

		function setIsEnd() {
			if (settings.callback_f.length > 0 )
				eval(settings.callback_f);
		}

        // to move the colums from one number position to another
        function setNumbers(counter) { 
            digits = String(counter).split('.'); // check decimals
        
            integers = digits[0]; 
            j = integers.length-1;
            // for each integer digit, update the old digit position to the new
            for (var i = 0; i < integersArray.length; i++) {
                oldDigit = integersArray[i];
                integersArray[i] = integers.charAt(j);
                if (integersArray[i] == '') {
                    integersArray[i] = '0';
                }
                updatePosition($('.counter_id_'+i, $this), parseInt(integersArray[i]), parseInt(oldDigit));
                j--;
            }
            if (settings.counterEnd != false && counter < settings.counterEnd) {
            	if (delayTime < 2000) {
            		delayTime = delayTime + Math.round(delayTime/8);
            	}
            	counterInterval = setTimeout(advanceCounter,  delayTime);
            } else {
            	if (delayTime < 2000) {
            		delayTime = delayTime + Math.round(delayTime/8);
            	}
            	counterInterval = setTimeout(setIsEnd,  delayTime);
            }
        }

        // changes the column position from one number to another
        function updatePosition(col, newDigit, oldDigit) { 
            if (newDigit != oldDigit) {
              function _move() {
              	animator++;
              	new_pos = oldDigit*settings.heightNumber*6 + animator * settings.heightNumber;
              	if (new_pos >= 4619) { new_pos = "0";  }
              	else new_pos = (-1 * new_pos ) + 'px';
              	col.css({
              		"background-position": "0 " + new_pos
              	});
   		       if (animator <= 5 ) setTimeout(_move, Math.round(delayTime/6) );
   		       else { 
   		       		animator = 0;
   		       }	
              }              
    		  if (newDigit == 0) {	
    		  	col.css({
              		"background-position": "0 0"
              	});
    		  } else {
    		  	_move();						
    		  }	
            }
        }
    });
};

$.fn.odometer.defaults = {
    counterStart: '00000',
    counterEnd: false,
    delayTime: 0,
    increment: 1,
    speed: 500,
    easing: 'swing',
    numbersImage: 'numbers.png',
    backgroundImage: 'background.png',
    heightNumber: 40,
    widthNumber: 28,
    offsetRight: 0,
    spaceNumbers: 0,
    widthDot: 20,
    callback_f: ''
};

})(jQuery);
