362 lines
8.7 KiB
JavaScript
362 lines
8.7 KiB
JavaScript
/* Copyright (c) 2006-2013 by OpenLayers Contributors (see authors.txt for
|
|
* full list of contributors). Published under the 2-clause BSD license.
|
|
* See license.txt in the OpenLayers distribution or repository for the
|
|
* full text of the license. */
|
|
|
|
/**
|
|
* @requires OpenLayers/BaseTypes/Class.js
|
|
* @requires OpenLayers/Animation.js
|
|
*/
|
|
|
|
/**
|
|
* Namespace: OpenLayers.Tween
|
|
*/
|
|
OpenLayers.Tween = OpenLayers.Class({
|
|
|
|
/**
|
|
* APIProperty: easing
|
|
* {<OpenLayers.Easing>(Function)} Easing equation used for the animation
|
|
* Defaultly set to OpenLayers.Easing.Expo.easeOut
|
|
*/
|
|
easing: null,
|
|
|
|
/**
|
|
* APIProperty: begin
|
|
* {Object} Values to start the animation with
|
|
*/
|
|
begin: null,
|
|
|
|
/**
|
|
* APIProperty: finish
|
|
* {Object} Values to finish the animation with
|
|
*/
|
|
finish: null,
|
|
|
|
/**
|
|
* APIProperty: duration
|
|
* {int} duration of the tween (number of steps)
|
|
*/
|
|
duration: null,
|
|
|
|
/**
|
|
* APIProperty: callbacks
|
|
* {Object} An object with start, eachStep and done properties whose values
|
|
* are functions to be call during the animation. They are passed the
|
|
* current computed value as argument.
|
|
*/
|
|
callbacks: null,
|
|
|
|
/**
|
|
* Property: time
|
|
* {int} Step counter
|
|
*/
|
|
time: null,
|
|
|
|
/**
|
|
* APIProperty: minFrameRate
|
|
* {Number} The minimum framerate for animations in frames per second. After
|
|
* each step, the time spent in the animation is compared to the calculated
|
|
* time at this frame rate. If the animation runs longer than the calculated
|
|
* time, the next step is skipped. Default is 30.
|
|
*/
|
|
minFrameRate: null,
|
|
|
|
/**
|
|
* Property: startTime
|
|
* {Number} The timestamp of the first execution step. Used for skipping
|
|
* frames
|
|
*/
|
|
startTime: null,
|
|
|
|
/**
|
|
* Property: animationId
|
|
* {int} Loop id returned by OpenLayers.Animation.start
|
|
*/
|
|
animationId: null,
|
|
|
|
/**
|
|
* Property: playing
|
|
* {Boolean} Tells if the easing is currently playing
|
|
*/
|
|
playing: false,
|
|
|
|
/**
|
|
* Constructor: OpenLayers.Tween
|
|
* Creates a Tween.
|
|
*
|
|
* Parameters:
|
|
* easing - {<OpenLayers.Easing>(Function)} easing function method to use
|
|
*/
|
|
initialize: function(easing) {
|
|
this.easing = (easing) ? easing : OpenLayers.Easing.Expo.easeOut;
|
|
},
|
|
|
|
/**
|
|
* APIMethod: start
|
|
* Plays the Tween, and calls the callback method on each step
|
|
*
|
|
* Parameters:
|
|
* begin - {Object} values to start the animation with
|
|
* finish - {Object} values to finish the animation with
|
|
* duration - {int} duration of the tween (number of steps)
|
|
* options - {Object} hash of options (callbacks (start, eachStep, done),
|
|
* minFrameRate)
|
|
*/
|
|
start: function(begin, finish, duration, options) {
|
|
this.playing = true;
|
|
this.begin = begin;
|
|
this.finish = finish;
|
|
this.duration = duration;
|
|
this.callbacks = options.callbacks;
|
|
this.minFrameRate = options.minFrameRate || 30;
|
|
this.time = 0;
|
|
this.startTime = new Date().getTime();
|
|
OpenLayers.Animation.stop(this.animationId);
|
|
this.animationId = null;
|
|
if (this.callbacks && this.callbacks.start) {
|
|
this.callbacks.start.call(this, this.begin);
|
|
}
|
|
this.animationId = OpenLayers.Animation.start(
|
|
OpenLayers.Function.bind(this.play, this)
|
|
);
|
|
},
|
|
|
|
/**
|
|
* APIMethod: stop
|
|
* Stops the Tween, and calls the done callback
|
|
* Doesn't do anything if animation is already finished
|
|
*/
|
|
stop: function() {
|
|
if (!this.playing) {
|
|
return;
|
|
}
|
|
|
|
if (this.callbacks && this.callbacks.done) {
|
|
this.callbacks.done.call(this, this.finish);
|
|
}
|
|
OpenLayers.Animation.stop(this.animationId);
|
|
this.animationId = null;
|
|
this.playing = false;
|
|
},
|
|
|
|
/**
|
|
* Method: play
|
|
* Calls the appropriate easing method
|
|
*/
|
|
play: function() {
|
|
var value = {};
|
|
for (var i in this.begin) {
|
|
var b = this.begin[i];
|
|
var f = this.finish[i];
|
|
if (b == null || f == null || isNaN(b) || isNaN(f)) {
|
|
throw new TypeError('invalid value for Tween');
|
|
}
|
|
|
|
var c = f - b;
|
|
value[i] = this.easing.apply(this, [this.time, b, c, this.duration]);
|
|
}
|
|
this.time++;
|
|
|
|
if (this.callbacks && this.callbacks.eachStep) {
|
|
// skip frames if frame rate drops below threshold
|
|
if ((new Date().getTime() - this.startTime) / this.time <= 1000 / this.minFrameRate) {
|
|
this.callbacks.eachStep.call(this, value);
|
|
}
|
|
}
|
|
|
|
if (this.time > this.duration) {
|
|
this.stop();
|
|
}
|
|
},
|
|
|
|
/**
|
|
* Create empty functions for all easing methods.
|
|
*/
|
|
CLASS_NAME: "OpenLayers.Tween"
|
|
});
|
|
|
|
/**
|
|
* Namespace: OpenLayers.Easing
|
|
*
|
|
* Credits:
|
|
* Easing Equations by Robert Penner, <http://www.robertpenner.com/easing/>
|
|
*/
|
|
OpenLayers.Easing = {
|
|
/**
|
|
* Create empty functions for all easing methods.
|
|
*/
|
|
CLASS_NAME: "OpenLayers.Easing"
|
|
};
|
|
|
|
/**
|
|
* Namespace: OpenLayers.Easing.Linear
|
|
*/
|
|
OpenLayers.Easing.Linear = {
|
|
|
|
/**
|
|
* Function: easeIn
|
|
*
|
|
* Parameters:
|
|
* t - {Float} time
|
|
* b - {Float} beginning position
|
|
* c - {Float} total change
|
|
* d - {Float} duration of the transition
|
|
*
|
|
* Returns:
|
|
* {Float}
|
|
*/
|
|
easeIn: function(t, b, c, d) {
|
|
return c*t/d + b;
|
|
},
|
|
|
|
/**
|
|
* Function: easeOut
|
|
*
|
|
* Parameters:
|
|
* t - {Float} time
|
|
* b - {Float} beginning position
|
|
* c - {Float} total change
|
|
* d - {Float} duration of the transition
|
|
*
|
|
* Returns:
|
|
* {Float}
|
|
*/
|
|
easeOut: function(t, b, c, d) {
|
|
return c*t/d + b;
|
|
},
|
|
|
|
/**
|
|
* Function: easeInOut
|
|
*
|
|
* Parameters:
|
|
* t - {Float} time
|
|
* b - {Float} beginning position
|
|
* c - {Float} total change
|
|
* d - {Float} duration of the transition
|
|
*
|
|
* Returns:
|
|
* {Float}
|
|
*/
|
|
easeInOut: function(t, b, c, d) {
|
|
return c*t/d + b;
|
|
},
|
|
|
|
CLASS_NAME: "OpenLayers.Easing.Linear"
|
|
};
|
|
|
|
/**
|
|
* Namespace: OpenLayers.Easing.Expo
|
|
*/
|
|
OpenLayers.Easing.Expo = {
|
|
|
|
/**
|
|
* Function: easeIn
|
|
*
|
|
* Parameters:
|
|
* t - {Float} time
|
|
* b - {Float} beginning position
|
|
* c - {Float} total change
|
|
* d - {Float} duration of the transition
|
|
*
|
|
* Returns:
|
|
* {Float}
|
|
*/
|
|
easeIn: function(t, b, c, d) {
|
|
return (t==0) ? b : c * Math.pow(2, 10 * (t/d - 1)) + b;
|
|
},
|
|
|
|
/**
|
|
* Function: easeOut
|
|
*
|
|
* Parameters:
|
|
* t - {Float} time
|
|
* b - {Float} beginning position
|
|
* c - {Float} total change
|
|
* d - {Float} duration of the transition
|
|
*
|
|
* Returns:
|
|
* {Float}
|
|
*/
|
|
easeOut: function(t, b, c, d) {
|
|
return (t==d) ? b+c : c * (-Math.pow(2, -10 * t/d) + 1) + b;
|
|
},
|
|
|
|
/**
|
|
* Function: easeInOut
|
|
*
|
|
* Parameters:
|
|
* t - {Float} time
|
|
* b - {Float} beginning position
|
|
* c - {Float} total change
|
|
* d - {Float} duration of the transition
|
|
*
|
|
* Returns:
|
|
* {Float}
|
|
*/
|
|
easeInOut: function(t, b, c, d) {
|
|
if (t==0) return b;
|
|
if (t==d) return b+c;
|
|
if ((t/=d/2) < 1) return c/2 * Math.pow(2, 10 * (t - 1)) + b;
|
|
return c/2 * (-Math.pow(2, -10 * --t) + 2) + b;
|
|
},
|
|
|
|
CLASS_NAME: "OpenLayers.Easing.Expo"
|
|
};
|
|
|
|
/**
|
|
* Namespace: OpenLayers.Easing.Quad
|
|
*/
|
|
OpenLayers.Easing.Quad = {
|
|
|
|
/**
|
|
* Function: easeIn
|
|
*
|
|
* Parameters:
|
|
* t - {Float} time
|
|
* b - {Float} beginning position
|
|
* c - {Float} total change
|
|
* d - {Float} duration of the transition
|
|
*
|
|
* Returns:
|
|
* {Float}
|
|
*/
|
|
easeIn: function(t, b, c, d) {
|
|
return c*(t/=d)*t + b;
|
|
},
|
|
|
|
/**
|
|
* Function: easeOut
|
|
*
|
|
* Parameters:
|
|
* t - {Float} time
|
|
* b - {Float} beginning position
|
|
* c - {Float} total change
|
|
* d - {Float} duration of the transition
|
|
*
|
|
* Returns:
|
|
* {Float}
|
|
*/
|
|
easeOut: function(t, b, c, d) {
|
|
return -c *(t/=d)*(t-2) + b;
|
|
},
|
|
|
|
/**
|
|
* Function: easeInOut
|
|
*
|
|
* Parameters:
|
|
* t - {Float} time
|
|
* b - {Float} beginning position
|
|
* c - {Float} total change
|
|
* d - {Float} duration of the transition
|
|
*
|
|
* Returns:
|
|
* {Float}
|
|
*/
|
|
easeInOut: function(t, b, c, d) {
|
|
if ((t/=d/2) < 1) return c/2*t*t + b;
|
|
return -c/2 * ((--t)*(t-2) - 1) + b;
|
|
},
|
|
|
|
CLASS_NAME: "OpenLayers.Easing.Quad"
|
|
};
|