aboutsummaryrefslogtreecommitdiffstats
path: root/src/fx.js
diff options
context:
space:
mode:
Diffstat (limited to 'src/fx.js')
-rw-r--r--src/fx.js228
1 files changed, 105 insertions, 123 deletions
diff --git a/src/fx.js b/src/fx.js
index 07c468a..692c346 100644
--- a/src/fx.js
+++ b/src/fx.js
@@ -1,15 +1,13 @@
-
-SVG.FX = function FX(e) {
- // store target element
- this.target = e;
+SVG.FX = function FX(element) {
+ /* store target element */
+ this.target = element;
};
-// add FX methods
+//
SVG.extend(SVG.FX, {
-
- // animation parameters and animate
+ // Add animation parameters and start animation
animate: function(duration, ease) {
- // ensure default duration adn easing
+ /* ensure default duration and easing */
duration = duration || 1000;
ease = ease || '<>';
@@ -19,29 +17,29 @@ SVG.extend(SVG.FX, {
start = (new Date).getTime(),
finish = start + duration;
- // start animation
+ /* start animation */
this.interval = setInterval(function(){
- var i,
+ var index,
time = (new Date).getTime(),
pos = time > finish ? 1 : (time - start) / duration;
- // collect attribute keys
+ /* collect attribute keys */
if (akeys == null) {
akeys = [];
- for (var k in fx.attrs)
- akeys.push(k);
+ for (var key in fx.attrs)
+ akeys.push(key);
};
- // collect transformation keys
+ /* collect transformation keys */
if (tkeys == null) {
tkeys = [];
- for (var k in fx.trans)
- tkeys.push(k);
+ for (var key in fx.trans)
+ tkeys.push(key);
tvalues = {};
};
- // apply easing
+ /* apply easing */
pos = ease == '<>' ?
(-Math.cos(pos * Math.PI) / 2) + 0.5 :
ease == '>' ?
@@ -54,101 +52,101 @@ SVG.extend(SVG.FX, {
ease(pos) :
pos;
- // run all position properties
+ /* run all position properties */
if (fx._move)
element.move(fx._at(fx._move.x, pos), fx._at(fx._move.y, pos));
else if (fx._center)
element.move(fx._at(fx._center.x, pos), fx._at(fx._center.y, pos));
- // run all size properties
+ /* run all size properties */
if (fx._size)
element.size(fx._at(fx._size.width, pos), fx._at(fx._size.height, pos));
- // animate attributes
- for (i = akeys.length - 1; i >= 0; i--)
- element.attr(akeys[i], fx._at(fx.attrs[akeys[i]], pos));
+ /* animate attributes */
+ for (index = akeys.length - 1; index >= 0; index--)
+ element.attr(akeys[index], fx._at(fx.attrs[akeys[index]], pos));
- // animate transformations
+ /* animate transformations */
if (tkeys.length > 0) {
- for (i = tkeys.length - 1; i >= 0; i--)
- tvalues[tkeys[i]] = fx._at(fx.trans[tkeys[i]], pos);
+ for (index = tkeys.length - 1; index >= 0; index--)
+ tvalues[tkeys[index]] = fx._at(fx.trans[tkeys[index]], pos);
element.transform(tvalues);
}
- // finish off animation
+ /* finish off animation */
if (time > finish) {
clearInterval(fx.interval);
- fx._after ? fx._after.apply(element) : fx.stop();
+ fx._after ? fx._after.apply(element, [fx]) : fx.stop();
}
}, 10);
return this;
},
-
- // animated attributes
+ // Add animatable attributes
attr: function(a, v, n) {
if (typeof a == 'object')
- for (var k in a)
- this.attr(k, a[k]);
+ for (var key in a)
+ this.attr(key, a[key]);
else
this.attrs[a] = { from: this.target.attr(a), to: v };
return this;
},
-
- // animated transformations
+ // Add animatable transformations
transform: function(o) {
- for (var k in o)
- this.trans[k] = { from: this.target.trans[k], to: o[k] };
+ for (var key in o)
+ this.trans[key] = { from: this.target.trans[key], to: o[key] };
return this;
},
-
- // animated move
+ // Add animatable move
move: function(x, y) {
- var b = this.target.bbox();
+ var box = this.target.bbox();
this._move = {
- x: { from: b.x, to: x },
- y: { from: b.y, to: y }
+ x: { from: box.x, to: x },
+ y: { from: box.y, to: y }
};
return this;
},
-
- // animated size
- size: function(w, h) {
- var b = this.target.bbox();
+ // Add animatable size
+ size: function(width, height) {
+ var box = this.target.bbox();
this._size = {
- width: { from: b.width, to: w },
- height: { from: b.height, to: h }
+ width: { from: box.width, to: width },
+ height: { from: box.height, to: height }
};
return this;
},
-
- // animated center
+ // Add animatable center
center: function(x, y) {
- var b = this.target.bbox();
+ var box = this.target.bbox();
this._move = {
- x: { from: b.cx, to: x },
- y: { from: b.cy, to: y }
+ x: { from: box.cx, to: x },
+ y: { from: box.cy, to: y }
};
return this;
},
-
- // stop animation
+ // Callback after animation
+ after: function(after) {
+ this._after = after;
+
+ return this;
+ },
+ // Stop running animation
stop: function() {
- // stop current animation
+ /* stop current animation */
clearInterval(this.interval);
- // create / reset storage for properties that need animation
+ /* reset storage for properties that need animation */
this.attrs = {};
this.trans = {};
this._move = null;
@@ -157,96 +155,75 @@ SVG.extend(SVG.FX, {
return this;
},
-
- // private: at position according to from and to
- _at: function(o, p) {
- // if a number, calculate pos
+ // Private: at position according to from and to
+ _at: function(o, pos) {
+ /* if a number, recalculate pos */
return typeof o.from == 'number' ?
- o.from + (o.to - o.from) * p :
+ o.from + (o.to - o.from) * pos :
- // if animating to a color
+ /* if animating to a color */
o.to.r || /^#/.test(o.to) ?
- this._color(o, p) :
+ this._color(o, pos) :
- // for all other values wait until pos has reached 1 to return the final value
- p < 1 ? o.from : o.to;
+ /* for all other values wait until pos has reached 1 to return the final value */
+ pos < 1 ? o.from : o.to;
},
-
- // private: tween color
- _color: function(o, p) {
- var f, t;
+ // Private: tween color
+ _color: function(o, pos) {
+ var from, to;
- // convert FROM hex to rgb
- f = this._h2r(o.from || '#000');
+ /* convert FROM hex to rgb */
+ from = this._h2r(o.from || '#000');
- // convert TO hex to rgb
- t = this._h2r(o.to);
+ /* convert TO hex to rgb */
+ to = this._h2r(o.to);
- // tween color and return hex
+ /* tween color and return hex */
return this._r2h({
- r: ~~(f.r + (t.r - f.r) * p),
- g: ~~(f.g + (t.g - f.g) * p),
- b: ~~(f.b + (t.b - f.b) * p)
+ r: ~~(from.r + (to.r - from.r) * pos),
+ g: ~~(from.g + (to.g - from.g) * pos),
+ b: ~~(from.b + (to.b - from.b) * pos)
});
},
-
- // private: convert hex to rgb object
- _h2r: function(h) {
- // parse full hex
- var m = /^#?([a-f\d]{2})([a-f\d]{2})([a-f\d]{2})$/i.exec(this._fh(h));
-
- // if the hex is successfully parsed, return it in rgb, otherwise return black
- return m ? {
- r: parseInt(m[1], 16),
- g: parseInt(m[2], 16),
- b: parseInt(m[3], 16)
+ // Private: convert hex to rgb object
+ _h2r: function(hex) {
+ /* parse full hex */
+ var match = /^#?([a-f\d]{2})([a-f\d]{2})([a-f\d]{2})$/i.exec(this._fh(hex));
+
+ /* if the hex is successfully parsed, return it in rgb, otherwise return black */
+ return match ? {
+ r: parseInt(match[1], 16),
+ g: parseInt(match[2], 16),
+ b: parseInt(match[3], 16)
} : { r: 0, g: 0, b: 0 };
},
-
- // private: convert rgb object to hex string
- _r2h: function(r) {
- return '#' + this._c2h(r.r) + this._c2h(r.g) + this._c2h(r.b);
+ // Private: convert rgb object to hex string
+ _r2h: function(rgb) {
+ return '#' + this._c2h(rgb.r) + this._c2h(rgb.g) + this._c2h(rgb.b);
},
-
- // private: convert component to hex
+ // Private: convert component to hex
_c2h: function(c) {
- var h = c.toString(16);
- return h.length == 1 ? '0' + h : h;
+ var hex = c.toString(16);
+ return hex.length == 1 ? '0' + hex : hex;
},
-
- // private: force potential 3-based hex to 6-based
- _fh: function(h) {
- return h.length == 4 ?
+ // Private: force potential 3-based hex to 6-based
+ _fh: function(hex) {
+ return hex.length == 4 ?
[ '#',
- h.substring(1, 2), h.substring(1, 2),
- h.substring(2, 3), h.substring(2, 3),
- h.substring(3, 4), h.substring(3, 4)
- ].join('') : h;
+ hex.substring(1, 2), hex.substring(1, 2),
+ hex.substring(2, 3), hex.substring(2, 3),
+ hex.substring(3, 4), hex.substring(3, 4)
+ ].join('') : hex;
}
});
-
-
-// delay: delay animation for a given amount of ms
-// after: callback for when animation has finished
-['delay', 'after'].forEach(function(m) {
- SVG.FX.prototype[m] = function(v) {
- this['_' + m] = v;
-
- return this;
- };
-});
-
-
-// make SVG.Element FX-aware
+//
SVG.extend(SVG.Element, {
-
- // get fx module or create a new one, then animate with given ms and ease
- animate: function(d, e) {
- return (this._fx || (this._fx = new SVG.FX(this))).stop().animate(d, e);
+ // Get fx module or create a new one, then animate with given duration and ease
+ animate: function(duration, ease) {
+ return (this._fx || (this._fx = new SVG.FX(this))).stop().animate(duration, ease);
},
-
- // stop current animation
+ // Stop current animation; this is an alias to the fx instance
stop: function() {
this._fx.stop();
@@ -254,4 +231,9 @@ SVG.extend(SVG.Element, {
}
});
+// Usage:
+
+// rect.animate(1500, '>').move(200, 300).after(function() {
+// this.fill({ color: '#f06' });
+// });