improve PosAnimation code a bit

This commit is contained in:
mourner 2012-08-10 21:50:00 +03:00
parent 578f18ecfb
commit 7627d39700
2 changed files with 32 additions and 17 deletions

View File

@ -1,17 +1,17 @@
/*
* L.PosAnimation fallback implementation that powers Leaflet pan animations
* in browsers that don't support CSS3 Transitions
* in browsers that don't support CSS3 Transitions.
*/
L.PosAnimation = L.DomUtil.TRANSITION ? L.PosAnimation : L.Class.extend({
includes: L.Mixin.Events,
L.PosAnimation = L.DomUtil.TRANSITION ? L.PosAnimation : L.PosAnimation.extend({
run: function (el, newPos, duration) {
run: function (el, newPos, duration, easing) { // (HTMLElement, Point[, Number, String])
this.stop();
this._el = el;
this._inProgress = true;
this._duration = duration;
this._duration = duration || 0.25;
this._ease = this._easings[easing || 'ease-out'];
this._startPos = L.DomUtil.getPosition(el);
this._offset = newPos.subtract(this._startPos);
@ -30,7 +30,8 @@ L.PosAnimation = L.DomUtil.TRANSITION ? L.PosAnimation : L.Class.extend({
},
_animate: function () {
this._animId = L.Util.requestAnimFrame(this._animate, this, false, this._el);
// animation loop
this._animId = L.Util.requestAnimFrame(this._animate, this);
this._step();
},
@ -39,7 +40,7 @@ L.PosAnimation = L.DomUtil.TRANSITION ? L.PosAnimation : L.Class.extend({
duration = this._duration * 1000;
if (elapsed < duration) {
this._runFrame(this._easeOut(elapsed / duration));
this._runFrame(this._ease(elapsed / duration));
} else {
this._runFrame(1);
this._complete();
@ -49,16 +50,21 @@ L.PosAnimation = L.DomUtil.TRANSITION ? L.PosAnimation : L.Class.extend({
_runFrame: function (progress) {
var pos = this._startPos.add(this._offset.multiplyBy(progress));
L.DomUtil.setPosition(this._el, pos);
this.fire('step');
},
_complete: function () {
L.Util.cancelAnimFrame(this._animId);
this.fire('end');
this._inProgress = false;
this.fire('end');
},
_easeOut: function (t) {
return t * (2 - t);
// easing functions, they map time progress to movement progress
_easings: {
'ease-out': function (t) { return t * (2 - t); },
'linear': function (t) { return t; }
}
});

View File

@ -1,11 +1,11 @@
/*
* L.PosAnimation is used by Leaflet internally for pan animations
* L.PosAnimation is used by Leaflet internally for pan animations.
*/
L.PosAnimation = L.Class.extend({
includes: L.Mixin.Events,
run: function (el, newPos, duration) {
run: function (el, newPos, duration, easing) { // (HTMLElement, Point[, Number, String])
this.stop();
this._el = el;
@ -13,24 +13,31 @@ L.PosAnimation = L.Class.extend({
this.fire('start');
el.style[L.DomUtil.TRANSITION] = 'all ' + duration + 's ease-out';
el.style[L.DomUtil.TRANSITION] = 'all ' + (duration || 0.25) + 's ' + (easing || 'ease-out');
L.DomEvent.on(el, L.DomUtil.TRANSITION_END, this._onTransitionEnd, this);
L.DomUtil.setPosition(el, newPos);
// Chrome flickers for some reason if you don't do this
// toggle reflow, Chrome flickers for some reason if you don't do this
L.Util.falseFn(el.offsetWidth);
// there's no native way to track value updates of tranisitioned properties, so we imitate this
this._stepTimer = setInterval(L.Util.bind(this.fire, this, 'step'), 50);
},
stop: function () {
if (!this._inProgress) { return; }
var pos = this._getPos();
// if we just removed the transition property, the element would jump to its final position,
// so we need to make it stay at the current position
L.DomUtil.setPosition(this._el, pos);
L.DomUtil.setPosition(this._el, this._getPos());
this._onTransitionEnd();
},
// you can't easily get intermediate values of properties animated with CSS3 Transitions,
// we need to parse computed style (in case of transform it returns matrix string)
_transformRe: /(-?[\d\.]+), (-?[\d\.]+)\)/,
_getPos: function () {
@ -58,7 +65,9 @@ L.PosAnimation = L.Class.extend({
this._el.style[L.DomUtil.TRANSITION] = '';
this.fire('end');
clearInterval(this._stepTimer);
this.fire('step').fire('end');
}
});