From 2d34fcdc23d9cba73990348c662220481b776728 Mon Sep 17 00:00:00 2001 From: javi Date: Fri, 23 Aug 2013 19:15:21 +0200 Subject: [PATCH] included animation control --- lib/torque/animator.js | 106 +++++++++++++++++++++++++++++++++++ lib/torque/leaflet/torque.js | 13 +++++ 2 files changed, 119 insertions(+) create mode 100644 lib/torque/animator.js diff --git a/lib/torque/animator.js b/lib/torque/animator.js new file mode 100644 index 0000000..c1ba1b4 --- /dev/null +++ b/lib/torque/animator.js @@ -0,0 +1,106 @@ +(function(exports) { + + var requestAnimationFrame = window.requestAnimationFrame || window.mozRequestAnimationFrame || window.webkitRequestAnimationFrame || window.msRequestAnimationFrame; + + var cancelAnimationFrame = window.requestAnimationFrame || window.mozCancelAnimationFrame || window.webkitRequestAnimationFrame || window.msRequestAnimationFrame; + + /** + * options: + * animationDuration in seconds + * animationDelay in seconds + */ + function Animator(callback, options) { + if(!options.steps) { + throw new Error("steps option missing") + } + this.options = options; + this.running = false; + this._tick = this._tick.bind(this); + this._t0 = +new Date(); + this.callback = callback; + this._time = 0.0; + _.defaults(this.options, { + animationDelay: 0, + maxDelta: 0.2, + loop: true + }); + + + this.domain = invLinear(this.options.animationDelay, this.options.animationDelay + this.options.animationDuration); + this.range = linear(0, this.options.steps); + } + + + function clamp(a, b) { + return function(t) { + return Math.max(Math.min(t, b), a); + }; + } + + function invLinear(a, b) { + var c = clamp(0, 1.0); + return function(t) { + return c((t - a)/(b - a)); + }; + } + + function linear(a, b) { + var c = clamp(a, b); + return function(t) { + return c(a*(1.0 - t) + t*b); + }; + } + + + Animator.prototype = { + + start: function() { + this.running = true; + requestAnimationFrame(this._tick); + }, + + stop: function() { + this.pause(); + this._time = 0; + var t = this.range(this.domain(this._time)); + this.callback(t); + }, + + toggle: function() { + if (this.running) { + this.pause() + } else { + this.start() + } + }, + + pause: function() { + this.running = false; + cancelAnimationFrame(this._tick); + }, + + _tick: function() { + var t1 = +new Date(); + var delta = (t1 - this._t0)*0.001; + // if delta is really big means the tab lost the focus + // at some point, so limit delta change + delta = Math.min(this.options.maxDelta, delta) + this._t0 = t1; + this._time += delta; + var t = this.range(this.domain(this._time)); + this.callback(t); + if(t >= this.options.steps) { + this._time = 0; + } + if(this.running) { + requestAnimationFrame(this._tick); + } + } + + }; + + exports.torque.Animator = Animator; + + + +})(typeof exports === "undefined" ? this : exports); diff --git a/lib/torque/leaflet/torque.js b/lib/torque/leaflet/torque.js index 00b6088..7d40937 100644 --- a/lib/torque/leaflet/torque.js +++ b/lib/torque/leaflet/torque.js @@ -3,6 +3,7 @@ */ L.TorqueLayer = L.CanvasLayer.extend({ + providers: { 'sql_api': torque.providers.json, 'url_template': torque.providers.jsonarray @@ -18,6 +19,18 @@ L.TorqueLayer = L.CanvasLayer.extend({ options.tileLoader = true; this.key = 0; + this.animator = new torque.Animator(function(time) { + var k = time | 0; + if(self.key !== k) { + self.setKey(k); + } + }, options); + + this.play = this.animator.start.bind(this.animator); + this.stop = this.animator.stop.bind(this.animator); + this.pause = this.animator.pause.bind(this.animator); + this.toggle = this.animator.toggle.bind(this.animator); + L.CanvasLayer.prototype.initialize.call(this, options); this.options.renderer = this.options.renderer || 'point';