window.reqAnimFrame = window.requestAnimationFrame || (function(fn) { return setTimeout(fn, 1000 / 60) }); window.cancelAnimFrame = window.cancelAnimationFrame || window.clearTimeout; // Random number from min (inclusive) to max (exclusive) function randInt(min, max) { return Math.floor(Math.random() * (max - min)) + min; } function makeEventListener(obj) { obj.__callbacks = {}; obj.on = makeEventListener.on; obj.off = makeEventListener.off; obj.once = makeEventListener.once; obj.emit = makeEventListener.emit; } makeEventListener.on = function on(name, fn) { if (!this.__callbacks[name]) this.__callbacks[name] = []; this.__callbacks[name].push(fn); } makeEventListener.once = function once(name, fn) { var self = this; this.on(name, function f() { self.off(name, f); fn.apply(arguments); }); } makeEventListener.off = function off(name, fn) { if (!this.__callbacks[name]) return; for (var i in this.__callbacks[name]) { if (this.__callbacks[name] === fn) delete this.__callbacks[name][i]; } } makeEventListener.emit = function emit(name) { if (!this.__callbacks[name]) return; var args = [].slice.apply(arguments); args.splice(0, 1); this.__callbacks[name].forEach(function(f) { f.apply(args); }); }