]> ToastFreeware Gitweb - philipp/winterrodeln/wradmin.git/blob - wradmin/public/yui/animation/animation-debug.js
Start to use flask instead of pylons.
[philipp/winterrodeln/wradmin.git] / wradmin / public / yui / animation / animation-debug.js
1 /*
2 Copyright (c) 2009, Yahoo! Inc. All rights reserved.
3 Code licensed under the BSD License:
4 http://developer.yahoo.net/yui/license.txt
5 version: 2.7.0
6 */
7 (function() {
8
9 var Y = YAHOO.util;
10
11 /*
12 Copyright (c) 2006, Yahoo! Inc. All rights reserved.
13 Code licensed under the BSD License:
14 http://developer.yahoo.net/yui/license.txt
15 */
16
17 /**
18  * The animation module provides allows effects to be added to HTMLElements.
19  * @module animation
20  * @requires yahoo, event, dom
21  */
22
23 /**
24  *
25  * Base animation class that provides the interface for building animated effects.
26  * <p>Usage: var myAnim = new YAHOO.util.Anim(el, { width: { from: 10, to: 100 } }, 1, YAHOO.util.Easing.easeOut);</p>
27  * @class Anim
28  * @namespace YAHOO.util
29  * @requires YAHOO.util.AnimMgr
30  * @requires YAHOO.util.Easing
31  * @requires YAHOO.util.Dom
32  * @requires YAHOO.util.Event
33  * @requires YAHOO.util.CustomEvent
34  * @constructor
35  * @param {String | HTMLElement} el Reference to the element that will be animated
36  * @param {Object} attributes The attribute(s) to be animated.  
37  * Each attribute is an object with at minimum a "to" or "by" member defined.  
38  * Additional optional members are "from" (defaults to current value), "units" (defaults to "px").  
39  * All attribute names use camelCase.
40  * @param {Number} duration (optional, defaults to 1 second) Length of animation (frames or seconds), defaults to time-based
41  * @param {Function} method (optional, defaults to YAHOO.util.Easing.easeNone) Computes the values that are applied to the attributes per frame (generally a YAHOO.util.Easing method)
42  */
43
44 var Anim = function(el, attributes, duration, method) {
45     if (!el) {
46         YAHOO.log('element required to create Anim instance', 'error', 'Anim');
47     }
48     this.init(el, attributes, duration, method); 
49 };
50
51 Anim.NAME = 'Anim';
52
53 Anim.prototype = {
54     /**
55      * Provides a readable name for the Anim instance.
56      * @method toString
57      * @return {String}
58      */
59     toString: function() {
60         var el = this.getEl() || {};
61         var id = el.id || el.tagName;
62         return (this.constructor.NAME + ': ' + id);
63     },
64     
65     patterns: { // cached for performance
66         noNegatives:        /width|height|opacity|padding/i, // keep at zero or above
67         offsetAttribute:  /^((width|height)|(top|left))$/, // use offsetValue as default
68         defaultUnit:        /width|height|top$|bottom$|left$|right$/i, // use 'px' by default
69         offsetUnit:         /\d+(em|%|en|ex|pt|in|cm|mm|pc)$/i // IE may return these, so convert these to offset
70     },
71     
72     /**
73      * Returns the value computed by the animation's "method".
74      * @method doMethod
75      * @param {String} attr The name of the attribute.
76      * @param {Number} start The value this attribute should start from for this animation.
77      * @param {Number} end  The value this attribute should end at for this animation.
78      * @return {Number} The Value to be applied to the attribute.
79      */
80     doMethod: function(attr, start, end) {
81         return this.method(this.currentFrame, start, end - start, this.totalFrames);
82     },
83     
84     /**
85      * Applies a value to an attribute.
86      * @method setAttribute
87      * @param {String} attr The name of the attribute.
88      * @param {Number} val The value to be applied to the attribute.
89      * @param {String} unit The unit ('px', '%', etc.) of the value.
90      */
91     setAttribute: function(attr, val, unit) {
92         var el = this.getEl();
93         if ( this.patterns.noNegatives.test(attr) ) {
94             val = (val > 0) ? val : 0;
95         }
96
97         if ('style' in el) {
98             Y.Dom.setStyle(el, attr, val + unit);
99         } else if (attr in el) {
100             el[attr] = val;
101         }
102     },                        
103     
104     /**
105      * Returns current value of the attribute.
106      * @method getAttribute
107      * @param {String} attr The name of the attribute.
108      * @return {Number} val The current value of the attribute.
109      */
110     getAttribute: function(attr) {
111         var el = this.getEl();
112         var val = Y.Dom.getStyle(el, attr);
113
114         if (val !== 'auto' && !this.patterns.offsetUnit.test(val)) {
115             return parseFloat(val);
116         }
117         
118         var a = this.patterns.offsetAttribute.exec(attr) || [];
119         var pos = !!( a[3] ); // top or left
120         var box = !!( a[2] ); // width or height
121         
122         if ('style' in el) {
123             // use offsets for width/height and abs pos top/left
124             if ( box || (Y.Dom.getStyle(el, 'position') == 'absolute' && pos) ) {
125                 val = el['offset' + a[0].charAt(0).toUpperCase() + a[0].substr(1)];
126             } else { // default to zero for other 'auto'
127                 val = 0;
128             }
129         } else if (attr in el) {
130             val = el[attr];
131         }
132
133         return val;
134     },
135     
136     /**
137      * Returns the unit to use when none is supplied.
138      * @method getDefaultUnit
139      * @param {attr} attr The name of the attribute.
140      * @return {String} The default unit to be used.
141      */
142     getDefaultUnit: function(attr) {
143          if ( this.patterns.defaultUnit.test(attr) ) {
144             return 'px';
145          }
146          
147          return '';
148     },
149         
150     /**
151      * Sets the actual values to be used during the animation.  Should only be needed for subclass use.
152      * @method setRuntimeAttribute
153      * @param {Object} attr The attribute object
154      * @private 
155      */
156     setRuntimeAttribute: function(attr) {
157         var start;
158         var end;
159         var attributes = this.attributes;
160
161         this.runtimeAttributes[attr] = {};
162         
163         var isset = function(prop) {
164             return (typeof prop !== 'undefined');
165         };
166         
167         if ( !isset(attributes[attr]['to']) && !isset(attributes[attr]['by']) ) {
168             return false; // note return; nothing to animate to
169         }
170         
171         start = ( isset(attributes[attr]['from']) ) ? attributes[attr]['from'] : this.getAttribute(attr);
172
173         // To beats by, per SMIL 2.1 spec
174         if ( isset(attributes[attr]['to']) ) {
175             end = attributes[attr]['to'];
176         } else if ( isset(attributes[attr]['by']) ) {
177             if (start.constructor == Array) {
178                 end = [];
179                 for (var i = 0, len = start.length; i < len; ++i) {
180                     end[i] = start[i] + attributes[attr]['by'][i] * 1; // times 1 to cast "by" 
181                 }
182             } else {
183                 end = start + attributes[attr]['by'] * 1;
184             }
185         }
186         
187         this.runtimeAttributes[attr].start = start;
188         this.runtimeAttributes[attr].end = end;
189
190         // set units if needed
191         this.runtimeAttributes[attr].unit = ( isset(attributes[attr].unit) ) ?
192                 attributes[attr]['unit'] : this.getDefaultUnit(attr);
193         return true;
194     },
195
196     /**
197      * Constructor for Anim instance.
198      * @method init
199      * @param {String | HTMLElement} el Reference to the element that will be animated
200      * @param {Object} attributes The attribute(s) to be animated.  
201      * Each attribute is an object with at minimum a "to" or "by" member defined.  
202      * Additional optional members are "from" (defaults to current value), "units" (defaults to "px").  
203      * All attribute names use camelCase.
204      * @param {Number} duration (optional, defaults to 1 second) Length of animation (frames or seconds), defaults to time-based
205      * @param {Function} method (optional, defaults to YAHOO.util.Easing.easeNone) Computes the values that are applied to the attributes per frame (generally a YAHOO.util.Easing method)
206      */ 
207     init: function(el, attributes, duration, method) {
208         /**
209          * Whether or not the animation is running.
210          * @property isAnimated
211          * @private
212          * @type Boolean
213          */
214         var isAnimated = false;
215         
216         /**
217          * A Date object that is created when the animation begins.
218          * @property startTime
219          * @private
220          * @type Date
221          */
222         var startTime = null;
223         
224         /**
225          * The number of frames this animation was able to execute.
226          * @property actualFrames
227          * @private
228          * @type Int
229          */
230         var actualFrames = 0; 
231
232         /**
233          * The element to be animated.
234          * @property el
235          * @private
236          * @type HTMLElement
237          */
238         el = Y.Dom.get(el);
239         
240         /**
241          * The collection of attributes to be animated.  
242          * Each attribute must have at least a "to" or "by" defined in order to animate.  
243          * If "to" is supplied, the animation will end with the attribute at that value.  
244          * If "by" is supplied, the animation will end at that value plus its starting value. 
245          * If both are supplied, "to" is used, and "by" is ignored. 
246          * Optional additional member include "from" (the value the attribute should start animating from, defaults to current value), and "unit" (the units to apply to the values).
247          * @property attributes
248          * @type Object
249          */
250         this.attributes = attributes || {};
251         
252         /**
253          * The length of the animation.  Defaults to "1" (second).
254          * @property duration
255          * @type Number
256          */
257         this.duration = !YAHOO.lang.isUndefined(duration) ? duration : 1;
258         
259         /**
260          * The method that will provide values to the attribute(s) during the animation. 
261          * Defaults to "YAHOO.util.Easing.easeNone".
262          * @property method
263          * @type Function
264          */
265         this.method = method || Y.Easing.easeNone;
266
267         /**
268          * Whether or not the duration should be treated as seconds.
269          * Defaults to true.
270          * @property useSeconds
271          * @type Boolean
272          */
273         this.useSeconds = true; // default to seconds
274         
275         /**
276          * The location of the current animation on the timeline.
277          * In time-based animations, this is used by AnimMgr to ensure the animation finishes on time.
278          * @property currentFrame
279          * @type Int
280          */
281         this.currentFrame = 0;
282         
283         /**
284          * The total number of frames to be executed.
285          * In time-based animations, this is used by AnimMgr to ensure the animation finishes on time.
286          * @property totalFrames
287          * @type Int
288          */
289         this.totalFrames = Y.AnimMgr.fps;
290         
291         /**
292          * Changes the animated element
293          * @method setEl
294          */
295         this.setEl = function(element) {
296             el = Y.Dom.get(element);
297         };
298         
299         /**
300          * Returns a reference to the animated element.
301          * @method getEl
302          * @return {HTMLElement}
303          */
304         this.getEl = function() { return el; };
305         
306         /**
307          * Checks whether the element is currently animated.
308          * @method isAnimated
309          * @return {Boolean} current value of isAnimated.     
310          */
311         this.isAnimated = function() {
312             return isAnimated;
313         };
314         
315         /**
316          * Returns the animation start time.
317          * @method getStartTime
318          * @return {Date} current value of startTime.      
319          */
320         this.getStartTime = function() {
321             return startTime;
322         };        
323         
324         this.runtimeAttributes = {};
325         
326         var logger = {};
327         logger.log = function() {YAHOO.log.apply(window, arguments)};
328         
329         logger.log('creating new instance of ' + this);
330         
331         /**
332          * Starts the animation by registering it with the animation manager. 
333          * @method animate  
334          */
335         this.animate = function() {
336             if ( this.isAnimated() ) {
337                 return false;
338             }
339             
340             this.currentFrame = 0;
341             
342             this.totalFrames = ( this.useSeconds ) ? Math.ceil(Y.AnimMgr.fps * this.duration) : this.duration;
343     
344             if (this.duration === 0 && this.useSeconds) { // jump to last frame if zero second duration 
345                 this.totalFrames = 1; 
346             }
347             Y.AnimMgr.registerElement(this);
348             return true;
349         };
350           
351         /**
352          * Stops the animation.  Normally called by AnimMgr when animation completes.
353          * @method stop
354          * @param {Boolean} finish (optional) If true, animation will jump to final frame.
355          */ 
356         this.stop = function(finish) {
357             if (!this.isAnimated()) { // nothing to stop
358                 return false;
359             }
360
361             if (finish) {
362                  this.currentFrame = this.totalFrames;
363                  this._onTween.fire();
364             }
365             Y.AnimMgr.stop(this);
366         };
367         
368         var onStart = function() {            
369             this.onStart.fire();
370             
371             this.runtimeAttributes = {};
372             for (var attr in this.attributes) {
373                 this.setRuntimeAttribute(attr);
374             }
375             
376             isAnimated = true;
377             actualFrames = 0;
378             startTime = new Date(); 
379         };
380         
381         /**
382          * Feeds the starting and ending values for each animated attribute to doMethod once per frame, then applies the resulting value to the attribute(s).
383          * @private
384          */
385          
386         var onTween = function() {
387             var data = {
388                 duration: new Date() - this.getStartTime(),
389                 currentFrame: this.currentFrame
390             };
391             
392             data.toString = function() {
393                 return (
394                     'duration: ' + data.duration +
395                     ', currentFrame: ' + data.currentFrame
396                 );
397             };
398             
399             this.onTween.fire(data);
400             
401             var runtimeAttributes = this.runtimeAttributes;
402             
403             for (var attr in runtimeAttributes) {
404                 this.setAttribute(attr, this.doMethod(attr, runtimeAttributes[attr].start, runtimeAttributes[attr].end), runtimeAttributes[attr].unit); 
405             }
406             
407             actualFrames += 1;
408         };
409         
410         var onComplete = function() {
411             var actual_duration = (new Date() - startTime) / 1000 ;
412             
413             var data = {
414                 duration: actual_duration,
415                 frames: actualFrames,
416                 fps: actualFrames / actual_duration
417             };
418             
419             data.toString = function() {
420                 return (
421                     'duration: ' + data.duration +
422                     ', frames: ' + data.frames +
423                     ', fps: ' + data.fps
424                 );
425             };
426             
427             isAnimated = false;
428             actualFrames = 0;
429             this.onComplete.fire(data);
430         };
431         
432         /**
433          * Custom event that fires after onStart, useful in subclassing
434          * @private
435          */    
436         this._onStart = new Y.CustomEvent('_start', this, true);
437
438         /**
439          * Custom event that fires when animation begins
440          * Listen via subscribe method (e.g. myAnim.onStart.subscribe(someFunction)
441          * @event onStart
442          */    
443         this.onStart = new Y.CustomEvent('start', this);
444         
445         /**
446          * Custom event that fires between each frame
447          * Listen via subscribe method (e.g. myAnim.onTween.subscribe(someFunction)
448          * @event onTween
449          */
450         this.onTween = new Y.CustomEvent('tween', this);
451         
452         /**
453          * Custom event that fires after onTween
454          * @private
455          */
456         this._onTween = new Y.CustomEvent('_tween', this, true);
457         
458         /**
459          * Custom event that fires when animation ends
460          * Listen via subscribe method (e.g. myAnim.onComplete.subscribe(someFunction)
461          * @event onComplete
462          */
463         this.onComplete = new Y.CustomEvent('complete', this);
464         /**
465          * Custom event that fires after onComplete
466          * @private
467          */
468         this._onComplete = new Y.CustomEvent('_complete', this, true);
469
470         this._onStart.subscribe(onStart);
471         this._onTween.subscribe(onTween);
472         this._onComplete.subscribe(onComplete);
473     }
474 };
475
476     Y.Anim = Anim;
477 })();
478 /**
479  * Handles animation queueing and threading.
480  * Used by Anim and subclasses.
481  * @class AnimMgr
482  * @namespace YAHOO.util
483  */
484 YAHOO.util.AnimMgr = new function() {
485     /** 
486      * Reference to the animation Interval.
487      * @property thread
488      * @private
489      * @type Int
490      */
491     var thread = null;
492     
493     /** 
494      * The current queue of registered animation objects.
495      * @property queue
496      * @private
497      * @type Array
498      */    
499     var queue = [];
500
501     /** 
502      * The number of active animations.
503      * @property tweenCount
504      * @private
505      * @type Int
506      */        
507     var tweenCount = 0;
508
509     /** 
510      * Base frame rate (frames per second). 
511      * Arbitrarily high for better x-browser calibration (slower browsers drop more frames).
512      * @property fps
513      * @type Int
514      * 
515      */
516     this.fps = 1000;
517
518     /** 
519      * Interval delay in milliseconds, defaults to fastest possible.
520      * @property delay
521      * @type Int
522      * 
523      */
524     this.delay = 1;
525
526     /**
527      * Adds an animation instance to the animation queue.
528      * All animation instances must be registered in order to animate.
529      * @method registerElement
530      * @param {object} tween The Anim instance to be be registered
531      */
532     this.registerElement = function(tween) {
533         queue[queue.length] = tween;
534         tweenCount += 1;
535         tween._onStart.fire();
536         this.start();
537     };
538     
539     /**
540      * removes an animation instance from the animation queue.
541      * All animation instances must be registered in order to animate.
542      * @method unRegister
543      * @param {object} tween The Anim instance to be be registered
544      * @param {Int} index The index of the Anim instance
545      * @private
546      */
547     this.unRegister = function(tween, index) {
548         index = index || getIndex(tween);
549         if (!tween.isAnimated() || index == -1) {
550             return false;
551         }
552         
553         tween._onComplete.fire();
554         queue.splice(index, 1);
555
556         tweenCount -= 1;
557         if (tweenCount <= 0) {
558             this.stop();
559         }
560
561         return true;
562     };
563     
564     /**
565      * Starts the animation thread.
566         * Only one thread can run at a time.
567      * @method start
568      */    
569     this.start = function() {
570         if (thread === null) {
571             thread = setInterval(this.run, this.delay);
572         }
573     };
574
575     /**
576      * Stops the animation thread or a specific animation instance.
577      * @method stop
578      * @param {object} tween A specific Anim instance to stop (optional)
579      * If no instance given, Manager stops thread and all animations.
580      */    
581     this.stop = function(tween) {
582         if (!tween) {
583             clearInterval(thread);
584             
585             for (var i = 0, len = queue.length; i < len; ++i) {
586                 this.unRegister(queue[0], 0);  
587             }
588
589             queue = [];
590             thread = null;
591             tweenCount = 0;
592         }
593         else {
594             this.unRegister(tween);
595         }
596     };
597     
598     /**
599      * Called per Interval to handle each animation frame.
600      * @method run
601      */    
602     this.run = function() {
603         for (var i = 0, len = queue.length; i < len; ++i) {
604             var tween = queue[i];
605             if ( !tween || !tween.isAnimated() ) { continue; }
606
607             if (tween.currentFrame < tween.totalFrames || tween.totalFrames === null)
608             {
609                 tween.currentFrame += 1;
610                 
611                 if (tween.useSeconds) {
612                     correctFrame(tween);
613                 }
614                 tween._onTween.fire();          
615             }
616             else { YAHOO.util.AnimMgr.stop(tween, i); }
617         }
618     };
619     
620     var getIndex = function(anim) {
621         for (var i = 0, len = queue.length; i < len; ++i) {
622             if (queue[i] == anim) {
623                 return i; // note return;
624             }
625         }
626         return -1;
627     };
628     
629     /**
630      * On the fly frame correction to keep animation on time.
631      * @method correctFrame
632      * @private
633      * @param {Object} tween The Anim instance being corrected.
634      */
635     var correctFrame = function(tween) {
636         var frames = tween.totalFrames;
637         var frame = tween.currentFrame;
638         var expected = (tween.currentFrame * tween.duration * 1000 / tween.totalFrames);
639         var elapsed = (new Date() - tween.getStartTime());
640         var tweak = 0;
641         
642         if (elapsed < tween.duration * 1000) { // check if falling behind
643             tweak = Math.round((elapsed / expected - 1) * tween.currentFrame);
644         } else { // went over duration, so jump to end
645             tweak = frames - (frame + 1); 
646         }
647         if (tweak > 0 && isFinite(tweak)) { // adjust if needed
648             if (tween.currentFrame + tweak >= frames) {// dont go past last frame
649                 tweak = frames - (frame + 1);
650             }
651             
652             tween.currentFrame += tweak;      
653         }
654     };
655 };
656 /**
657  * Used to calculate Bezier splines for any number of control points.
658  * @class Bezier
659  * @namespace YAHOO.util
660  *
661  */
662 YAHOO.util.Bezier = new function() {
663     /**
664      * Get the current position of the animated element based on t.
665      * Each point is an array of "x" and "y" values (0 = x, 1 = y)
666      * At least 2 points are required (start and end).
667      * First point is start. Last point is end.
668      * Additional control points are optional.     
669      * @method getPosition
670      * @param {Array} points An array containing Bezier points
671      * @param {Number} t A number between 0 and 1 which is the basis for determining current position
672      * @return {Array} An array containing int x and y member data
673      */
674     this.getPosition = function(points, t) {  
675         var n = points.length;
676         var tmp = [];
677
678         for (var i = 0; i < n; ++i){
679             tmp[i] = [points[i][0], points[i][1]]; // save input
680         }
681         
682         for (var j = 1; j < n; ++j) {
683             for (i = 0; i < n - j; ++i) {
684                 tmp[i][0] = (1 - t) * tmp[i][0] + t * tmp[parseInt(i + 1, 10)][0];
685                 tmp[i][1] = (1 - t) * tmp[i][1] + t * tmp[parseInt(i + 1, 10)][1]; 
686             }
687         }
688     
689         return [ tmp[0][0], tmp[0][1] ]; 
690     
691     };
692 };
693 (function() {
694 /**
695  * Anim subclass for color transitions.
696  * <p>Usage: <code>var myAnim = new Y.ColorAnim(el, { backgroundColor: { from: '#FF0000', to: '#FFFFFF' } }, 1, Y.Easing.easeOut);</code> Color values can be specified with either 112233, #112233, 
697  * [255,255,255], or rgb(255,255,255)</p>
698  * @class ColorAnim
699  * @namespace YAHOO.util
700  * @requires YAHOO.util.Anim
701  * @requires YAHOO.util.AnimMgr
702  * @requires YAHOO.util.Easing
703  * @requires YAHOO.util.Bezier
704  * @requires YAHOO.util.Dom
705  * @requires YAHOO.util.Event
706  * @constructor
707  * @extends YAHOO.util.Anim
708  * @param {HTMLElement | String} el Reference to the element that will be animated
709  * @param {Object} attributes The attribute(s) to be animated.
710  * Each attribute is an object with at minimum a "to" or "by" member defined.
711  * Additional optional members are "from" (defaults to current value), "units" (defaults to "px").
712  * All attribute names use camelCase.
713  * @param {Number} duration (optional, defaults to 1 second) Length of animation (frames or seconds), defaults to time-based
714  * @param {Function} method (optional, defaults to YAHOO.util.Easing.easeNone) Computes the values that are applied to the attributes per frame (generally a YAHOO.util.Easing method)
715  */
716     var ColorAnim = function(el, attributes, duration,  method) {
717         ColorAnim.superclass.constructor.call(this, el, attributes, duration, method);
718     };
719     
720     ColorAnim.NAME = 'ColorAnim';
721
722     ColorAnim.DEFAULT_BGCOLOR = '#fff';
723     // shorthand
724     var Y = YAHOO.util;
725     YAHOO.extend(ColorAnim, Y.Anim);
726
727     var superclass = ColorAnim.superclass;
728     var proto = ColorAnim.prototype;
729     
730     proto.patterns.color = /color$/i;
731     proto.patterns.rgb            = /^rgb\(([0-9]+)\s*,\s*([0-9]+)\s*,\s*([0-9]+)\)$/i;
732     proto.patterns.hex            = /^#?([0-9A-F]{2})([0-9A-F]{2})([0-9A-F]{2})$/i;
733     proto.patterns.hex3          = /^#?([0-9A-F]{1})([0-9A-F]{1})([0-9A-F]{1})$/i;
734     proto.patterns.transparent = /^transparent|rgba\(0, 0, 0, 0\)$/; // need rgba for safari
735     
736     /**
737      * Attempts to parse the given string and return a 3-tuple.
738      * @method parseColor
739      * @param {String} s The string to parse.
740      * @return {Array} The 3-tuple of rgb values.
741      */
742     proto.parseColor = function(s) {
743         if (s.length == 3) { return s; }
744     
745         var c = this.patterns.hex.exec(s);
746         if (c && c.length == 4) {
747             return [ parseInt(c[1], 16), parseInt(c[2], 16), parseInt(c[3], 16) ];
748         }
749     
750         c = this.patterns.rgb.exec(s);
751         if (c && c.length == 4) {
752             return [ parseInt(c[1], 10), parseInt(c[2], 10), parseInt(c[3], 10) ];
753         }
754     
755         c = this.patterns.hex3.exec(s);
756         if (c && c.length == 4) {
757             return [ parseInt(c[1] + c[1], 16), parseInt(c[2] + c[2], 16), parseInt(c[3] + c[3], 16) ];
758         }
759         
760         return null;
761     };
762
763     proto.getAttribute = function(attr) {
764         var el = this.getEl();
765         if (this.patterns.color.test(attr) ) {
766             var val = YAHOO.util.Dom.getStyle(el, attr);
767             
768             var that = this;
769             if (this.patterns.transparent.test(val)) { // bgcolor default
770                 var parent = YAHOO.util.Dom.getAncestorBy(el, function(node) {
771                     return !that.patterns.transparent.test(val);
772                 });
773
774                 if (parent) {
775                     val = Y.Dom.getStyle(parent, attr);
776                 } else {
777                     val = ColorAnim.DEFAULT_BGCOLOR;
778                 }
779             }
780         } else {
781             val = superclass.getAttribute.call(this, attr);
782         }
783
784         return val;
785     };
786     
787     proto.doMethod = function(attr, start, end) {
788         var val;
789     
790         if ( this.patterns.color.test(attr) ) {
791             val = [];
792             for (var i = 0, len = start.length; i < len; ++i) {
793                 val[i] = superclass.doMethod.call(this, attr, start[i], end[i]);
794             }
795             
796             val = 'rgb('+Math.floor(val[0])+','+Math.floor(val[1])+','+Math.floor(val[2])+')';
797         }
798         else {
799             val = superclass.doMethod.call(this, attr, start, end);
800         }
801
802         return val;
803     };
804
805     proto.setRuntimeAttribute = function(attr) {
806         superclass.setRuntimeAttribute.call(this, attr);
807         
808         if ( this.patterns.color.test(attr) ) {
809             var attributes = this.attributes;
810             var start = this.parseColor(this.runtimeAttributes[attr].start);
811             var end = this.parseColor(this.runtimeAttributes[attr].end);
812             // fix colors if going "by"
813             if ( typeof attributes[attr]['to'] === 'undefined' && typeof attributes[attr]['by'] !== 'undefined' ) {
814                 end = this.parseColor(attributes[attr].by);
815             
816                 for (var i = 0, len = start.length; i < len; ++i) {
817                     end[i] = start[i] + end[i];
818                 }
819             }
820             
821             this.runtimeAttributes[attr].start = start;
822             this.runtimeAttributes[attr].end = end;
823         }
824     };
825
826     Y.ColorAnim = ColorAnim;
827 })();
828 /*!
829 TERMS OF USE - EASING EQUATIONS
830 Open source under the BSD License.
831 Copyright 2001 Robert Penner All rights reserved.
832
833 Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met:
834
835  * Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.
836  * Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution.
837  * Neither the name of the author nor the names of contributors may be used to endorse or promote products derived from this software without specific prior written permission.
838
839 THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
840 */
841
842 /**
843  * Singleton that determines how an animation proceeds from start to end.
844  * @class Easing
845  * @namespace YAHOO.util
846 */
847
848 YAHOO.util.Easing = {
849
850     /**
851      * Uniform speed between points.
852      * @method easeNone
853      * @param {Number} t Time value used to compute current value
854      * @param {Number} b Starting value
855      * @param {Number} c Delta between start and end values
856      * @param {Number} d Total length of animation
857      * @return {Number} The computed value for the current animation frame
858      */
859     easeNone: function (t, b, c, d) {
860         return c*t/d + b;
861     },
862     
863     /**
864      * Begins slowly and accelerates towards end.
865      * @method easeIn
866      * @param {Number} t Time value used to compute current value
867      * @param {Number} b Starting value
868      * @param {Number} c Delta between start and end values
869      * @param {Number} d Total length of animation
870      * @return {Number} The computed value for the current animation frame
871      */
872     easeIn: function (t, b, c, d) {
873         return c*(t/=d)*t + b;
874     },
875
876     /**
877      * Begins quickly and decelerates towards end.
878      * @method easeOut
879      * @param {Number} t Time value used to compute current value
880      * @param {Number} b Starting value
881      * @param {Number} c Delta between start and end values
882      * @param {Number} d Total length of animation
883      * @return {Number} The computed value for the current animation frame
884      */
885     easeOut: function (t, b, c, d) {
886         return -c *(t/=d)*(t-2) + b;
887     },
888     
889     /**
890      * Begins slowly and decelerates towards end.
891      * @method easeBoth
892      * @param {Number} t Time value used to compute current value
893      * @param {Number} b Starting value
894      * @param {Number} c Delta between start and end values
895      * @param {Number} d Total length of animation
896      * @return {Number} The computed value for the current animation frame
897      */
898     easeBoth: function (t, b, c, d) {
899         if ((t/=d/2) < 1) {
900             return c/2*t*t + b;
901         }
902         
903         return -c/2 * ((--t)*(t-2) - 1) + b;
904     },
905     
906     /**
907      * Begins slowly and accelerates towards end.
908      * @method easeInStrong
909      * @param {Number} t Time value used to compute current value
910      * @param {Number} b Starting value
911      * @param {Number} c Delta between start and end values
912      * @param {Number} d Total length of animation
913      * @return {Number} The computed value for the current animation frame
914      */
915     easeInStrong: function (t, b, c, d) {
916         return c*(t/=d)*t*t*t + b;
917     },
918     
919     /**
920      * Begins quickly and decelerates towards end.
921      * @method easeOutStrong
922      * @param {Number} t Time value used to compute current value
923      * @param {Number} b Starting value
924      * @param {Number} c Delta between start and end values
925      * @param {Number} d Total length of animation
926      * @return {Number} The computed value for the current animation frame
927      */
928     easeOutStrong: function (t, b, c, d) {
929         return -c * ((t=t/d-1)*t*t*t - 1) + b;
930     },
931     
932     /**
933      * Begins slowly and decelerates towards end.
934      * @method easeBothStrong
935      * @param {Number} t Time value used to compute current value
936      * @param {Number} b Starting value
937      * @param {Number} c Delta between start and end values
938      * @param {Number} d Total length of animation
939      * @return {Number} The computed value for the current animation frame
940      */
941     easeBothStrong: function (t, b, c, d) {
942         if ((t/=d/2) < 1) {
943             return c/2*t*t*t*t + b;
944         }
945         
946         return -c/2 * ((t-=2)*t*t*t - 2) + b;
947     },
948
949     /**
950      * Snap in elastic effect.
951      * @method elasticIn
952      * @param {Number} t Time value used to compute current value
953      * @param {Number} b Starting value
954      * @param {Number} c Delta between start and end values
955      * @param {Number} d Total length of animation
956      * @param {Number} a Amplitude (optional)
957      * @param {Number} p Period (optional)
958      * @return {Number} The computed value for the current animation frame
959      */
960
961     elasticIn: function (t, b, c, d, a, p) {
962         if (t == 0) {
963             return b;
964         }
965         if ( (t /= d) == 1 ) {
966             return b+c;
967         }
968         if (!p) {
969             p=d*.3;
970         }
971         
972         if (!a || a < Math.abs(c)) {
973             a = c; 
974             var s = p/4;
975         }
976         else {
977             var s = p/(2*Math.PI) * Math.asin (c/a);
978         }
979         
980         return -(a*Math.pow(2,10*(t-=1)) * Math.sin( (t*d-s)*(2*Math.PI)/p )) + b;
981     },
982
983     /**
984      * Snap out elastic effect.
985      * @method elasticOut
986      * @param {Number} t Time value used to compute current value
987      * @param {Number} b Starting value
988      * @param {Number} c Delta between start and end values
989      * @param {Number} d Total length of animation
990      * @param {Number} a Amplitude (optional)
991      * @param {Number} p Period (optional)
992      * @return {Number} The computed value for the current animation frame
993      */
994     elasticOut: function (t, b, c, d, a, p) {
995         if (t == 0) {
996             return b;
997         }
998         if ( (t /= d) == 1 ) {
999             return b+c;
1000         }
1001         if (!p) {
1002             p=d*.3;
1003         }
1004         
1005         if (!a || a < Math.abs(c)) {
1006             a = c;
1007             var s = p / 4;
1008         }
1009         else {
1010             var s = p/(2*Math.PI) * Math.asin (c/a);
1011         }
1012         
1013         return a*Math.pow(2,-10*t) * Math.sin( (t*d-s)*(2*Math.PI)/p ) + c + b;
1014     },
1015     
1016     /**
1017      * Snap both elastic effect.
1018      * @method elasticBoth
1019      * @param {Number} t Time value used to compute current value
1020      * @param {Number} b Starting value
1021      * @param {Number} c Delta between start and end values
1022      * @param {Number} d Total length of animation
1023      * @param {Number} a Amplitude (optional)
1024      * @param {Number} p Period (optional)
1025      * @return {Number} The computed value for the current animation frame
1026      */
1027     elasticBoth: function (t, b, c, d, a, p) {
1028         if (t == 0) {
1029             return b;
1030         }
1031         
1032         if ( (t /= d/2) == 2 ) {
1033             return b+c;
1034         }
1035         
1036         if (!p) {
1037             p = d*(.3*1.5);
1038         }
1039         
1040         if ( !a || a < Math.abs(c) ) {
1041             a = c; 
1042             var s = p/4;
1043         }
1044         else {
1045             var s = p/(2*Math.PI) * Math.asin (c/a);
1046         }
1047         
1048         if (t < 1) {
1049             return -.5*(a*Math.pow(2,10*(t-=1)) * 
1050                     Math.sin( (t*d-s)*(2*Math.PI)/p )) + b;
1051         }
1052         return a*Math.pow(2,-10*(t-=1)) * 
1053                 Math.sin( (t*d-s)*(2*Math.PI)/p )*.5 + c + b;
1054     },
1055
1056
1057     /**
1058      * Backtracks slightly, then reverses direction and moves to end.
1059      * @method backIn
1060      * @param {Number} t Time value used to compute current value
1061      * @param {Number} b Starting value
1062      * @param {Number} c Delta between start and end values
1063      * @param {Number} d Total length of animation
1064      * @param {Number} s Overshoot (optional)
1065      * @return {Number} The computed value for the current animation frame
1066      */
1067     backIn: function (t, b, c, d, s) {
1068         if (typeof s == 'undefined') {
1069             s = 1.70158;
1070         }
1071         return c*(t/=d)*t*((s+1)*t - s) + b;
1072     },
1073
1074     /**
1075      * Overshoots end, then reverses and comes back to end.
1076      * @method backOut
1077      * @param {Number} t Time value used to compute current value
1078      * @param {Number} b Starting value
1079      * @param {Number} c Delta between start and end values
1080      * @param {Number} d Total length of animation
1081      * @param {Number} s Overshoot (optional)
1082      * @return {Number} The computed value for the current animation frame
1083      */
1084     backOut: function (t, b, c, d, s) {
1085         if (typeof s == 'undefined') {
1086             s = 1.70158;
1087         }
1088         return c*((t=t/d-1)*t*((s+1)*t + s) + 1) + b;
1089     },
1090     
1091     /**
1092      * Backtracks slightly, then reverses direction, overshoots end, 
1093      * then reverses and comes back to end.
1094      * @method backBoth
1095      * @param {Number} t Time value used to compute current value
1096      * @param {Number} b Starting value
1097      * @param {Number} c Delta between start and end values
1098      * @param {Number} d Total length of animation
1099      * @param {Number} s Overshoot (optional)
1100      * @return {Number} The computed value for the current animation frame
1101      */
1102     backBoth: function (t, b, c, d, s) {
1103         if (typeof s == 'undefined') {
1104             s = 1.70158; 
1105         }
1106         
1107         if ((t /= d/2 ) < 1) {
1108             return c/2*(t*t*(((s*=(1.525))+1)*t - s)) + b;
1109         }
1110         return c/2*((t-=2)*t*(((s*=(1.525))+1)*t + s) + 2) + b;
1111     },
1112
1113     /**
1114      * Bounce off of start.
1115      * @method bounceIn
1116      * @param {Number} t Time value used to compute current value
1117      * @param {Number} b Starting value
1118      * @param {Number} c Delta between start and end values
1119      * @param {Number} d Total length of animation
1120      * @return {Number} The computed value for the current animation frame
1121      */
1122     bounceIn: function (t, b, c, d) {
1123         return c - YAHOO.util.Easing.bounceOut(d-t, 0, c, d) + b;
1124     },
1125     
1126     /**
1127      * Bounces off end.
1128      * @method bounceOut
1129      * @param {Number} t Time value used to compute current value
1130      * @param {Number} b Starting value
1131      * @param {Number} c Delta between start and end values
1132      * @param {Number} d Total length of animation
1133      * @return {Number} The computed value for the current animation frame
1134      */
1135     bounceOut: function (t, b, c, d) {
1136         if ((t/=d) < (1/2.75)) {
1137                 return c*(7.5625*t*t) + b;
1138         } else if (t < (2/2.75)) {
1139                 return c*(7.5625*(t-=(1.5/2.75))*t + .75) + b;
1140         } else if (t < (2.5/2.75)) {
1141                 return c*(7.5625*(t-=(2.25/2.75))*t + .9375) + b;
1142         }
1143         return c*(7.5625*(t-=(2.625/2.75))*t + .984375) + b;
1144     },
1145     
1146     /**
1147      * Bounces off start and end.
1148      * @method bounceBoth
1149      * @param {Number} t Time value used to compute current value
1150      * @param {Number} b Starting value
1151      * @param {Number} c Delta between start and end values
1152      * @param {Number} d Total length of animation
1153      * @return {Number} The computed value for the current animation frame
1154      */
1155     bounceBoth: function (t, b, c, d) {
1156         if (t < d/2) {
1157             return YAHOO.util.Easing.bounceIn(t*2, 0, c, d) * .5 + b;
1158         }
1159         return YAHOO.util.Easing.bounceOut(t*2-d, 0, c, d) * .5 + c*.5 + b;
1160     }
1161 };
1162
1163 (function() {
1164 /**
1165  * Anim subclass for moving elements along a path defined by the "points" 
1166  * member of "attributes".  All "points" are arrays with x, y coordinates.
1167  * <p>Usage: <code>var myAnim = new YAHOO.util.Motion(el, { points: { to: [800, 800] } }, 1, YAHOO.util.Easing.easeOut);</code></p>
1168  * @class Motion
1169  * @namespace YAHOO.util
1170  * @requires YAHOO.util.Anim
1171  * @requires YAHOO.util.AnimMgr
1172  * @requires YAHOO.util.Easing
1173  * @requires YAHOO.util.Bezier
1174  * @requires YAHOO.util.Dom
1175  * @requires YAHOO.util.Event
1176  * @requires YAHOO.util.CustomEvent 
1177  * @constructor
1178  * @extends YAHOO.util.ColorAnim
1179  * @param {String | HTMLElement} el Reference to the element that will be animated
1180  * @param {Object} attributes The attribute(s) to be animated.  
1181  * Each attribute is an object with at minimum a "to" or "by" member defined.  
1182  * Additional optional members are "from" (defaults to current value), "units" (defaults to "px").  
1183  * All attribute names use camelCase.
1184  * @param {Number} duration (optional, defaults to 1 second) Length of animation (frames or seconds), defaults to time-based
1185  * @param {Function} method (optional, defaults to YAHOO.util.Easing.easeNone) Computes the values that are applied to the attributes per frame (generally a YAHOO.util.Easing method)
1186  */
1187     var Motion = function(el, attributes, duration,  method) {
1188         if (el) { // dont break existing subclasses not using YAHOO.extend
1189             Motion.superclass.constructor.call(this, el, attributes, duration, method);
1190         }
1191     };
1192
1193
1194     Motion.NAME = 'Motion';
1195
1196     // shorthand
1197     var Y = YAHOO.util;
1198     YAHOO.extend(Motion, Y.ColorAnim);
1199     
1200     var superclass = Motion.superclass;
1201     var proto = Motion.prototype;
1202
1203     proto.patterns.points = /^points$/i;
1204     
1205     proto.setAttribute = function(attr, val, unit) {
1206         if (  this.patterns.points.test(attr) ) {
1207             unit = unit || 'px';
1208             superclass.setAttribute.call(this, 'left', val[0], unit);
1209             superclass.setAttribute.call(this, 'top', val[1], unit);
1210         } else {
1211             superclass.setAttribute.call(this, attr, val, unit);
1212         }
1213     };
1214
1215     proto.getAttribute = function(attr) {
1216         if (  this.patterns.points.test(attr) ) {
1217             var val = [
1218                 superclass.getAttribute.call(this, 'left'),
1219                 superclass.getAttribute.call(this, 'top')
1220             ];
1221         } else {
1222             val = superclass.getAttribute.call(this, attr);
1223         }
1224
1225         return val;
1226     };
1227
1228     proto.doMethod = function(attr, start, end) {
1229         var val = null;
1230
1231         if ( this.patterns.points.test(attr) ) {
1232             var t = this.method(this.currentFrame, 0, 100, this.totalFrames) / 100;                             
1233             val = Y.Bezier.getPosition(this.runtimeAttributes[attr], t);
1234         } else {
1235             val = superclass.doMethod.call(this, attr, start, end);
1236         }
1237         return val;
1238     };
1239
1240     proto.setRuntimeAttribute = function(attr) {
1241         if ( this.patterns.points.test(attr) ) {
1242             var el = this.getEl();
1243             var attributes = this.attributes;
1244             var start;
1245             var control = attributes['points']['control'] || [];
1246             var end;
1247             var i, len;
1248             
1249             if (control.length > 0 && !(control[0] instanceof Array) ) { // could be single point or array of points
1250                 control = [control];
1251             } else { // break reference to attributes.points.control
1252                 var tmp = []; 
1253                 for (i = 0, len = control.length; i< len; ++i) {
1254                     tmp[i] = control[i];
1255                 }
1256                 control = tmp;
1257             }
1258
1259             if (Y.Dom.getStyle(el, 'position') == 'static') { // default to relative
1260                 Y.Dom.setStyle(el, 'position', 'relative');
1261             }
1262     
1263             if ( isset(attributes['points']['from']) ) {
1264                 Y.Dom.setXY(el, attributes['points']['from']); // set position to from point
1265             } 
1266             else { Y.Dom.setXY( el, Y.Dom.getXY(el) ); } // set it to current position
1267             
1268             start = this.getAttribute('points'); // get actual top & left
1269             
1270             // TO beats BY, per SMIL 2.1 spec
1271             if ( isset(attributes['points']['to']) ) {
1272                 end = translateValues.call(this, attributes['points']['to'], start);
1273                 
1274                 var pageXY = Y.Dom.getXY(this.getEl());
1275                 for (i = 0, len = control.length; i < len; ++i) {
1276                     control[i] = translateValues.call(this, control[i], start);
1277                 }
1278
1279                 
1280             } else if ( isset(attributes['points']['by']) ) {
1281                 end = [ start[0] + attributes['points']['by'][0], start[1] + attributes['points']['by'][1] ];
1282                 
1283                 for (i = 0, len = control.length; i < len; ++i) {
1284                     control[i] = [ start[0] + control[i][0], start[1] + control[i][1] ];
1285                 }
1286             }
1287
1288             this.runtimeAttributes[attr] = [start];
1289             
1290             if (control.length > 0) {
1291                 this.runtimeAttributes[attr] = this.runtimeAttributes[attr].concat(control); 
1292             }
1293
1294             this.runtimeAttributes[attr][this.runtimeAttributes[attr].length] = end;
1295         }
1296         else {
1297             superclass.setRuntimeAttribute.call(this, attr);
1298         }
1299     };
1300     
1301     var translateValues = function(val, start) {
1302         var pageXY = Y.Dom.getXY(this.getEl());
1303         val = [ val[0] - pageXY[0] + start[0], val[1] - pageXY[1] + start[1] ];
1304
1305         return val; 
1306     };
1307     
1308     var isset = function(prop) {
1309         return (typeof prop !== 'undefined');
1310     };
1311
1312     Y.Motion = Motion;
1313 })();
1314 (function() {
1315 /**
1316  * Anim subclass for scrolling elements to a position defined by the "scroll"
1317  * member of "attributes".  All "scroll" members are arrays with x, y scroll positions.
1318  * <p>Usage: <code>var myAnim = new YAHOO.util.Scroll(el, { scroll: { to: [0, 800] } }, 1, YAHOO.util.Easing.easeOut);</code></p>
1319  * @class Scroll
1320  * @namespace YAHOO.util
1321  * @requires YAHOO.util.Anim
1322  * @requires YAHOO.util.AnimMgr
1323  * @requires YAHOO.util.Easing
1324  * @requires YAHOO.util.Bezier
1325  * @requires YAHOO.util.Dom
1326  * @requires YAHOO.util.Event
1327  * @requires YAHOO.util.CustomEvent 
1328  * @extends YAHOO.util.ColorAnim
1329  * @constructor
1330  * @param {String or HTMLElement} el Reference to the element that will be animated
1331  * @param {Object} attributes The attribute(s) to be animated.  
1332  * Each attribute is an object with at minimum a "to" or "by" member defined.  
1333  * Additional optional members are "from" (defaults to current value), "units" (defaults to "px").  
1334  * All attribute names use camelCase.
1335  * @param {Number} duration (optional, defaults to 1 second) Length of animation (frames or seconds), defaults to time-based
1336  * @param {Function} method (optional, defaults to YAHOO.util.Easing.easeNone) Computes the values that are applied to the attributes per frame (generally a YAHOO.util.Easing method)
1337  */
1338     var Scroll = function(el, attributes, duration,  method) {
1339         if (el) { // dont break existing subclasses not using YAHOO.extend
1340             Scroll.superclass.constructor.call(this, el, attributes, duration, method);
1341         }
1342     };
1343
1344     Scroll.NAME = 'Scroll';
1345
1346     // shorthand
1347     var Y = YAHOO.util;
1348     YAHOO.extend(Scroll, Y.ColorAnim);
1349     
1350     var superclass = Scroll.superclass;
1351     var proto = Scroll.prototype;
1352
1353     proto.doMethod = function(attr, start, end) {
1354         var val = null;
1355     
1356         if (attr == 'scroll') {
1357             val = [
1358                 this.method(this.currentFrame, start[0], end[0] - start[0], this.totalFrames),
1359                 this.method(this.currentFrame, start[1], end[1] - start[1], this.totalFrames)
1360             ];
1361             
1362         } else {
1363             val = superclass.doMethod.call(this, attr, start, end);
1364         }
1365         return val;
1366     };
1367
1368     proto.getAttribute = function(attr) {
1369         var val = null;
1370         var el = this.getEl();
1371         
1372         if (attr == 'scroll') {
1373             val = [ el.scrollLeft, el.scrollTop ];
1374         } else {
1375             val = superclass.getAttribute.call(this, attr);
1376         }
1377         
1378         return val;
1379     };
1380
1381     proto.setAttribute = function(attr, val, unit) {
1382         var el = this.getEl();
1383         
1384         if (attr == 'scroll') {
1385             el.scrollLeft = val[0];
1386             el.scrollTop = val[1];
1387         } else {
1388             superclass.setAttribute.call(this, attr, val, unit);
1389         }
1390     };
1391
1392     Y.Scroll = Scroll;
1393 })();
1394 YAHOO.register("animation", YAHOO.util.Anim, {version: "2.7.0", build: "1799"});