1/** 2 * jQuery.timers - Timer abstractions for jQuery 3 * Written by Blair Mitchelmore (blair DOT mitchelmore AT gmail DOT com) 4 * Licensed under the WTFPL (http://sam.zoy.org/wtfpl/). 5 * Date: 2009/02/08 6 * 7 * @author Blair Mitchelmore 8 * @version 1.1.2 9 * 10 **/ 11 12jQuery.fn.extend({ 13 everyTime: function(interval, label, fn, times, belay) { 14 return this.each(function() { 15 jQuery.timer.add(this, interval, label, fn, times, belay); 16 }); 17 }, 18 oneTime: function(interval, label, fn) { 19 return this.each(function() { 20 jQuery.timer.add(this, interval, label, fn, 1); 21 }); 22 }, 23 stopTime: function(label, fn) { 24 return this.each(function() { 25 jQuery.timer.remove(this, label, fn); 26 }); 27 } 28}); 29 30jQuery.event.special 31 32jQuery.extend({ 33 timer: { 34 global: [], 35 guid: 1, 36 dataKey: "jQuery.timer", 37 regex: /^([0-9]+(?:\.[0-9]*)?)\s*(.*s)?$/, 38 powers: { 39 // Yeah this is major overkill... 40 'ms': 1, 41 'cs': 10, 42 'ds': 100, 43 's': 1000, 44 'das': 10000, 45 'hs': 100000, 46 'ks': 1000000 47 }, 48 timeParse: function(value) { 49 if (value == undefined || value == null) 50 return null; 51 var result = this.regex.exec(jQuery.trim(value.toString())); 52 if (result[2]) { 53 var num = parseFloat(result[1]); 54 var mult = this.powers[result[2]] || 1; 55 return num * mult; 56 } else { 57 return value; 58 } 59 }, 60 add: function(element, interval, label, fn, times, belay) { 61 var counter = 0; 62 63 if (jQuery.isFunction(label)) { 64 if (!times) 65 times = fn; 66 fn = label; 67 label = interval; 68 } 69 70 interval = jQuery.timer.timeParse(interval); 71 72 if (typeof interval != 'number' || isNaN(interval) || interval <= 0) 73 return; 74 75 if (times && times.constructor != Number) { 76 belay = !!times; 77 times = 0; 78 } 79 80 times = times || 0; 81 belay = belay || false; 82 83 var timers = jQuery.data(element, this.dataKey) || jQuery.data(element, this.dataKey, {}); 84 85 if (!timers[label]) 86 timers[label] = {}; 87 88 fn.timerID = fn.timerID || this.guid++; 89 90 var handler = function() { 91 if (belay && this.inProgress) 92 return; 93 this.inProgress = true; 94 if ((++counter > times && times !== 0) || fn.call(element, counter) === false) 95 jQuery.timer.remove(element, label, fn); 96 this.inProgress = false; 97 }; 98 99 handler.timerID = fn.timerID; 100 101 if (!timers[label][fn.timerID]) 102 timers[label][fn.timerID] = window.setInterval(handler,interval); 103 104 this.global.push( element ); 105 106 }, 107 remove: function(element, label, fn) { 108 var timers = jQuery.data(element, this.dataKey), ret; 109 110 if ( timers ) { 111 112 if (!label) { 113 for ( label in timers ) 114 this.remove(element, label, fn); 115 } else if ( timers[label] ) { 116 if ( fn ) { 117 if ( fn.timerID ) { 118 window.clearInterval(timers[label][fn.timerID]); 119 delete timers[label][fn.timerID]; 120 } 121 } else { 122 for ( var fn in timers[label] ) { 123 window.clearInterval(timers[label][fn]); 124 delete timers[label][fn]; 125 } 126 } 127 128 for ( ret in timers[label] ) break; 129 if ( !ret ) { 130 ret = null; 131 delete timers[label]; 132 } 133 } 134 135 for ( ret in timers ) break; 136 if ( !ret ) 137 jQuery.removeData(element, this.dataKey); 138 } 139 } 140 } 141}); 142 143jQuery(window).bind("unload", function() { 144 jQuery.each(jQuery.timer.global, function(index, item) { 145 jQuery.timer.remove(item); 146 }); 147});