diff options
author | Monty Taylor <mordred@inaugust.com> | 2015-10-17 16:05:11 -0400 |
---|---|---|
committer | Monty Taylor <mordred@inaugust.com> | 2015-10-17 16:05:11 -0400 |
commit | 38a0efd33065c51198e4486304fff92a977258cf (patch) | |
tree | bcb35da78fb82a1bfb5f6c7082259e237ab6deb8 /xstatic/pkg/angular_animate/data | |
parent | 91b9d3197f67213e4e35e9a35ba7196b898731e7 (diff) | |
download | xstatic-angular-animate-master.tar.gz |
Diffstat (limited to 'xstatic/pkg/angular_animate/data')
-rwxr-xr-x | xstatic/pkg/angular_animate/data/angular-animate.js | 1226 |
1 files changed, 0 insertions, 1226 deletions
diff --git a/xstatic/pkg/angular_animate/data/angular-animate.js b/xstatic/pkg/angular_animate/data/angular-animate.js deleted file mode 100755 index 737ac0e..0000000 --- a/xstatic/pkg/angular_animate/data/angular-animate.js +++ /dev/null @@ -1,1226 +0,0 @@ -/** - * @license AngularJS v1.2.1 - * (c) 2010-2012 Google, Inc. http://angularjs.org - * License: MIT - */ -(function(window, angular, undefined) {'use strict'; - -/* jshint maxlen: false */ - -/** - * @ngdoc overview - * @name ngAnimate - * @description - * - * # ngAnimate - * - * The `ngAnimate` module provides support for JavaScript, CSS3 transition and CSS3 keyframe animation hooks within existing core and custom directives. - * - * {@installModule animate} - * - * <div doc-module-components="ngAnimate"></div> - * - * # Usage - * - * To see animations in action, all that is required is to define the appropriate CSS classes - * or to register a JavaScript animation via the myModule.animation() function. The directives that support animation automatically are: - * `ngRepeat`, `ngInclude`, `ngIf`, `ngSwitch`, `ngShow`, `ngHide`, `ngView` and `ngClass`. Custom directives can take advantage of animation - * by using the `$animate` service. - * - * Below is a more detailed breakdown of the supported animation events provided by pre-existing ng directives: - * - * | Directive | Supported Animations | - * |---------------------------------------------------------- |----------------------------------------------------| - * | {@link ng.directive:ngRepeat#usage_animations ngRepeat} | enter, leave and move | - * | {@link ngRoute.directive:ngView#usage_animations ngView} | enter and leave | - * | {@link ng.directive:ngInclude#usage_animations ngInclude} | enter and leave | - * | {@link ng.directive:ngSwitch#usage_animations ngSwitch} | enter and leave | - * | {@link ng.directive:ngIf#usage_animations ngIf} | enter and leave | - * | {@link ng.directive:ngClass#usage_animations ngClass} | add and remove | - * | {@link ng.directive:ngShow#usage_animations ngShow & ngHide} | add and remove (the ng-hide class value) | - * - * You can find out more information about animations upon visiting each directive page. - * - * Below is an example of how to apply animations to a directive that supports animation hooks: - * - * <pre> - * <style type="text/css"> - * .slide.ng-enter, .slide.ng-leave { - * -webkit-transition:0.5s linear all; - * transition:0.5s linear all; - * } - * - * .slide.ng-enter { } /* starting animations for enter */ - * .slide.ng-enter-active { } /* terminal animations for enter */ - * .slide.ng-leave { } /* starting animations for leave */ - * .slide.ng-leave-active { } /* terminal animations for leave */ - * </style> - * - * <!-- - * the animate service will automatically add .ng-enter and .ng-leave to the element - * to trigger the CSS transition/animations - * --> - * <ANY class="slide" ng-include="..."></ANY> - * </pre> - * - * Keep in mind that if an animation is running, any child elements cannot be animated until the parent element's - * animation has completed. - * - * <h2>CSS-defined Animations</h2> - * The animate service will automatically apply two CSS classes to the animated element and these two CSS classes - * are designed to contain the start and end CSS styling. Both CSS transitions and keyframe animations are supported - * and can be used to play along with this naming structure. - * - * The following code below demonstrates how to perform animations using **CSS transitions** with Angular: - * - * <pre> - * <style type="text/css"> - * /* - * The animate class is apart of the element and the ng-enter class - * is attached to the element once the enter animation event is triggered - * */ - * .reveal-animation.ng-enter { - * -webkit-transition: 1s linear all; /* Safari/Chrome */ - * transition: 1s linear all; /* All other modern browsers and IE10+ */ - * - * /* The animation preparation code */ - * opacity: 0; - * } - * - * /* - * Keep in mind that you want to combine both CSS - * classes together to avoid any CSS-specificity - * conflicts - * */ - * .reveal-animation.ng-enter.ng-enter-active { - * /* The animation code itself */ - * opacity: 1; - * } - * </style> - * - * <div class="view-container"> - * <div ng-view class="reveal-animation"></div> - * </div> - * </pre> - * - * The following code below demonstrates how to perform animations using **CSS animations** with Angular: - * - * <pre> - * <style type="text/css"> - * .reveal-animation.ng-enter { - * -webkit-animation: enter_sequence 1s linear; /* Safari/Chrome */ - * animation: enter_sequence 1s linear; /* IE10+ and Future Browsers */ - * } - * @-webkit-keyframes enter_sequence { - * from { opacity:0; } - * to { opacity:1; } - * } - * @keyframes enter_sequence { - * from { opacity:0; } - * to { opacity:1; } - * } - * </style> - * - * <div class="view-container"> - * <div ng-view class="reveal-animation"></div> - * </div> - * </pre> - * - * Both CSS3 animations and transitions can be used together and the animate service will figure out the correct duration and delay timing. - * - * Upon DOM mutation, the event class is added first (something like `ng-enter`), then the browser prepares itself to add - * the active class (in this case `ng-enter-active`) which then triggers the animation. The animation module will automatically - * detect the CSS code to determine when the animation ends. Once the animation is over then both CSS classes will be - * removed from the DOM. If a browser does not support CSS transitions or CSS animations then the animation will start and end - * immediately resulting in a DOM element that is at its final state. This final state is when the DOM element - * has no CSS transition/animation classes applied to it. - * - * <h3>CSS Staggering Animations</h3> - * A Staggering animation is a collection of animations that are issued with a slight delay in between each successive operation resulting in a - * curtain-like effect. The ngAnimate module, as of 1.2.0, supports staggering animations and the stagger effect can be - * performed by creating a **ng-EVENT-stagger** CSS class and attaching that class to the base CSS class used for - * the animation. The style property expected within the stagger class can either be a **transition-delay** or an - * **animation-delay** property (or both if your animation contains both transitions and keyframe animations). - * - * <pre> - * .my-animation.ng-enter { - * /* standard transition code */ - * -webkit-transition: 1s linear all; - * transition: 1s linear all; - * opacity:0; - * } - * .my-animation.ng-enter-stagger { - * /* this will have a 100ms delay between each successive leave animation */ - * -webkit-transition-delay: 0.1s; - * transition-delay: 0.1s; - * - * /* in case the stagger doesn't work then these two values - * must be set to 0 to avoid an accidental CSS inheritance */ - * -webkit-transition-duration: 0s; - * transition-duration: 0s; - * } - * .my-animation.ng-enter.ng-enter-active { - * /* standard transition styles */ - * opacity:1; - * } - * </pre> - * - * Staggering animations work by default in ngRepeat (so long as the CSS class is defiend). Outside of ngRepeat, to use staggering animations - * on your own, they can be triggered by firing multiple calls to the same event on $animate. However, the restrictions surrounding this - * are that each of the elements must have the same CSS className value as well as the same parent element. A stagger operation - * will also be reset if more than 10ms has passed after the last animation has been fired. - * - * The following code will issue the **ng-leave-stagger** event on the element provided: - * - * <pre> - * var kids = parent.children(); - * - * $animate.leave(kids[0]); //stagger index=0 - * $animate.leave(kids[1]); //stagger index=1 - * $animate.leave(kids[2]); //stagger index=2 - * $animate.leave(kids[3]); //stagger index=3 - * $animate.leave(kids[4]); //stagger index=4 - * - * $timeout(function() { - * //stagger has reset itself - * $animate.leave(kids[5]); //stagger index=0 - * $animate.leave(kids[6]); //stagger index=1 - * }, 100, false); - * </pre> - * - * Stagger animations are currently only supported within CSS-defined animations. - * - * <h2>JavaScript-defined Animations</h2> - * In the event that you do not want to use CSS3 transitions or CSS3 animations or if you wish to offer animations on browsers that do not - * yet support CSS transitions/animations, then you can make use of JavaScript animations defined inside of your AngularJS module. - * - * <pre> - * //!annotate="YourApp" Your AngularJS Module|Replace this or ngModule with the module that you used to define your application. - * var ngModule = angular.module('YourApp', []); - * ngModule.animation('.my-crazy-animation', function() { - * return { - * enter: function(element, done) { - * //run the animation here and call done when the animation is complete - * return function(cancelled) { - * //this (optional) function will be called when the animation - * //completes or when the animation is cancelled (the cancelled - * //flag will be set to true if cancelled). - * } - * } - * leave: function(element, done) { }, - * move: function(element, done) { }, - * - * //animation that can be triggered before the class is added - * beforeAddClass: function(element, className, done) { }, - * - * //animation that can be triggered after the class is added - * addClass: function(element, className, done) { }, - * - * //animation that can be triggered before the class is removed - * beforeRemoveClass: function(element, className, done) { }, - * - * //animation that can be triggered after the class is removed - * removeClass: function(element, className, done) { } - * } - * }); - * </pre> - * - * JavaScript-defined animations are created with a CSS-like class selector and a collection of events which are set to run - * a javascript callback function. When an animation is triggered, $animate will look for a matching animation which fits - * the element's CSS class attribute value and then run the matching animation event function (if found). - * In other words, if the CSS classes present on the animated element match any of the JavaScript animations then the callback function - * be executed. It should be also noted that only simple, single class selectors are allowed (compound class selectors are not supported). - * - * Within a JavaScript animation, an object containing various event callback animation functions is expected to be returned. - * As explained above, these callbacks are triggered based on the animation event. Therefore if an enter animation is run, - * and the JavaScript animation is found, then the enter callback will handle that animation (in addition to the CSS keyframe animation - * or transition code that is defined via a stylesheet). - * - */ - -angular.module('ngAnimate', ['ng']) - - /** - * @ngdoc object - * @name ngAnimate.$animateProvider - * @description - * - * The `$animateProvider` allows developers to register JavaScript animation event handlers directly inside of a module. - * When an animation is triggered, the $animate service will query the $animate service to find any animations that match - * the provided name value. - * - * Requires the {@link ngAnimate `ngAnimate`} module to be installed. - * - * Please visit the {@link ngAnimate `ngAnimate`} module overview page learn more about how to use animations in your application. - * - */ - .config(['$provide', '$animateProvider', function($provide, $animateProvider) { - var noop = angular.noop; - var forEach = angular.forEach; - var selectors = $animateProvider.$$selectors; - - var ELEMENT_NODE = 1; - var NG_ANIMATE_STATE = '$$ngAnimateState'; - var NG_ANIMATE_CLASS_NAME = 'ng-animate'; - var rootAnimateState = {running: true}; - - $provide.decorator('$animate', ['$delegate', '$injector', '$sniffer', '$rootElement', '$timeout', '$rootScope', '$document', - function($delegate, $injector, $sniffer, $rootElement, $timeout, $rootScope, $document) { - - $rootElement.data(NG_ANIMATE_STATE, rootAnimateState); - - // disable animations during bootstrap, but once we bootstrapped, enable animations - $rootScope.$$postDigest(function() { - rootAnimateState.running = false; - }); - - function lookup(name) { - if (name) { - var matches = [], - flagMap = {}, - classes = name.substr(1).split('.'); - - //the empty string value is the default animation - //operation which performs CSS transition and keyframe - //animations sniffing. This is always included for each - //element animation procedure if the browser supports - //transitions and/or keyframe animations - if ($sniffer.transitions || $sniffer.animations) { - classes.push(''); - } - - for(var i=0; i < classes.length; i++) { - var klass = classes[i], - selectorFactoryName = selectors[klass]; - if(selectorFactoryName && !flagMap[klass]) { - matches.push($injector.get(selectorFactoryName)); - flagMap[klass] = true; - } - } - return matches; - } - } - - /** - * @ngdoc object - * @name ngAnimate.$animate - * @function - * - * @description - * The `$animate` service provides animation detection support while performing DOM operations (enter, leave and move) as well as during addClass and removeClass operations. - * When any of these operations are run, the $animate service - * will examine any JavaScript-defined animations (which are defined by using the $animateProvider provider object) - * as well as any CSS-defined animations against the CSS classes present on the element once the DOM operation is run. - * - * The `$animate` service is used behind the scenes with pre-existing directives and animation with these directives - * will work out of the box without any extra configuration. - * - * Requires the {@link ngAnimate `ngAnimate`} module to be installed. - * - * Please visit the {@link ngAnimate `ngAnimate`} module overview page learn more about how to use animations in your application. - * - */ - return { - /** - * @ngdoc function - * @name ngAnimate.$animate#enter - * @methodOf ngAnimate.$animate - * @function - * - * @description - * Appends the element to the parentElement element that resides in the document and then runs the enter animation. Once - * the animation is started, the following CSS classes will be present on the element for the duration of the animation: - * - * Below is a breakdown of each step that occurs during enter animation: - * - * | Animation Step | What the element class attribute looks like | - * |----------------------------------------------------------------------------------------------|---------------------------------------------| - * | 1. $animate.enter(...) is called | class="my-animation" | - * | 2. element is inserted into the parentElement element or beside the afterElement element | class="my-animation" | - * | 3. $animate runs any JavaScript-defined animations on the element | class="my-animation ng-animate" | - * | 4. the .ng-enter class is added to the element | class="my-animation ng-animate ng-enter" | - * | 5. $animate scans the element styles to get the CSS transition/animation duration and delay | class="my-animation ng-animate ng-enter" | - * | 6. $animate waits for 10ms (this performs a reflow) | class="my-animation ng-animate ng-enter" | - * | 7. the .ng-enter-active and .ng-animate-active classes are added (this triggers the CSS transition/animation) | class="my-animation ng-animate ng-animate-active ng-enter ng-enter-active" | - * | 8. $animate waits for X milliseconds for the animation to complete | class="my-animation ng-animate ng-animate-active ng-enter ng-enter-active" | - * | 9. The animation ends and all generated CSS classes are removed from the element | class="my-animation" | - * | 10. The doneCallback() callback is fired (if provided) | class="my-animation" | - * - * @param {jQuery/jqLite element} element the element that will be the focus of the enter animation - * @param {jQuery/jqLite element} parentElement the parent element of the element that will be the focus of the enter animation - * @param {jQuery/jqLite element} afterElement the sibling element (which is the previous element) of the element that will be the focus of the enter animation - * @param {function()=} doneCallback the callback function that will be called once the animation is complete - */ - enter : function(element, parentElement, afterElement, doneCallback) { - this.enabled(false, element); - $delegate.enter(element, parentElement, afterElement); - $rootScope.$$postDigest(function() { - performAnimation('enter', 'ng-enter', element, parentElement, afterElement, noop, doneCallback); - }); - }, - - /** - * @ngdoc function - * @name ngAnimate.$animate#leave - * @methodOf ngAnimate.$animate - * @function - * - * @description - * Runs the leave animation operation and, upon completion, removes the element from the DOM. Once - * the animation is started, the following CSS classes will be added for the duration of the animation: - * - * Below is a breakdown of each step that occurs during enter animation: - * - * | Animation Step | What the element class attribute looks like | - * |----------------------------------------------------------------------------------------------|---------------------------------------------| - * | 1. $animate.leave(...) is called | class="my-animation" | - * | 2. $animate runs any JavaScript-defined animations on the element | class="my-animation ng-animate" | - * | 3. the .ng-leave class is added to the element | class="my-animation ng-animate ng-leave" | - * | 4. $animate scans the element styles to get the CSS transition/animation duration and delay | class="my-animation ng-animate ng-leave" | - * | 5. $animate waits for 10ms (this performs a reflow) | class="my-animation ng-animate ng-leave" | - * | 6. the .ng-leave-active and .ng-animate-active classes is added (this triggers the CSS transition/animation) | class="my-animation ng-animate ng-animate-active ng-leave ng-leave-active" | - * | 7. $animate waits for X milliseconds for the animation to complete | class="my-animation ng-animate ng-animate-active ng-leave ng-leave-active" | - * | 8. The animation ends and all generated CSS classes are removed from the element | class="my-animation" | - * | 9. The element is removed from the DOM | ... | - * | 10. The doneCallback() callback is fired (if provided) | ... | - * - * @param {jQuery/jqLite element} element the element that will be the focus of the leave animation - * @param {function()=} doneCallback the callback function that will be called once the animation is complete - */ - leave : function(element, doneCallback) { - cancelChildAnimations(element); - this.enabled(false, element); - $rootScope.$$postDigest(function() { - performAnimation('leave', 'ng-leave', element, null, null, function() { - $delegate.leave(element); - }, doneCallback); - }); - }, - - /** - * @ngdoc function - * @name ngAnimate.$animate#move - * @methodOf ngAnimate.$animate - * @function - * - * @description - * Fires the move DOM operation. Just before the animation starts, the animate service will either append it into the parentElement container or - * add the element directly after the afterElement element if present. Then the move animation will be run. Once - * the animation is started, the following CSS classes will be added for the duration of the animation: - * - * Below is a breakdown of each step that occurs during move animation: - * - * | Animation Step | What the element class attribute looks like | - * |----------------------------------------------------------------------------------------------|---------------------------------------------| - * | 1. $animate.move(...) is called | class="my-animation" | - * | 2. element is moved into the parentElement element or beside the afterElement element | class="my-animation" | - * | 3. $animate runs any JavaScript-defined animations on the element | class="my-animation ng-animate" | - * | 4. the .ng-move class is added to the element | class="my-animation ng-animate ng-move" | - * | 5. $animate scans the element styles to get the CSS transition/animation duration and delay | class="my-animation ng-animate ng-move" | - * | 6. $animate waits for 10ms (this performs a reflow) | class="my-animation ng-animate ng-move" | - * | 7. the .ng-move-active and .ng-animate-active classes is added (this triggers the CSS transition/animation) | class="my-animation ng-animate ng-animate-active ng-move ng-move-active" | - * | 8. $animate waits for X milliseconds for the animation to complete | class="my-animation ng-animate ng-animate-active ng-move ng-move-active" | - * | 9. The animation ends and all generated CSS classes are removed from the element | class="my-animation" | - * | 10. The doneCallback() callback is fired (if provided) | class="my-animation" | - * - * @param {jQuery/jqLite element} element the element that will be the focus of the move animation - * @param {jQuery/jqLite element} parentElement the parentElement element of the element that will be the focus of the move animation - * @param {jQuery/jqLite element} afterElement the sibling element (which is the previous element) of the element that will be the focus of the move animation - * @param {function()=} doneCallback the callback function that will be called once the animation is complete - */ - move : function(element, parentElement, afterElement, doneCallback) { - cancelChildAnimations(element); - this.enabled(false, element); - $delegate.move(element, parentElement, afterElement); - $rootScope.$$postDigest(function() { - performAnimation('move', 'ng-move', element, parentElement, afterElement, noop, doneCallback); - }); - }, - - /** - * @ngdoc function - * @name ngAnimate.$animate#addClass - * @methodOf ngAnimate.$animate - * - * @description - * Triggers a custom animation event based off the className variable and then attaches the className value to the element as a CSS class. - * Unlike the other animation methods, the animate service will suffix the className value with {@type -add} in order to provide - * the animate service the setup and active CSS classes in order to trigger the animation (this will be skipped if no CSS transitions - * or keyframes are defined on the -add or base CSS class). - * - * Below is a breakdown of each step that occurs during addClass animation: - * - * | Animation Step | What the element class attribute looks like | - * |------------------------------------------------------------------------------------------------|---------------------------------------------| - * | 1. $animate.addClass(element, 'super') is called | class="my-animation" | - * | 2. $animate runs any JavaScript-defined animations on the element | class="my-animation ng-animate" | - * | 3. the .super-add class are added to the element | class="my-animation ng-animate super-add" | - * | 4. $animate scans the element styles to get the CSS transition/animation duration and delay | class="my-animation ng-animate super-add" | - * | 5. $animate waits for 10ms (this performs a reflow) | class="my-animation ng-animate super-add" | - * | 6. the .super, .super-add-active and .ng-animate-active classes are added (this triggers the CSS transition/animation) | class="my-animation ng-animate ng-animate-active super super-add super-add-active" | - * | 7. $animate waits for X milliseconds for the animation to complete | class="my-animation super-add super-add-active" | - * | 8. The animation ends and all generated CSS classes are removed from the element | class="my-animation super" | - * | 9. The super class is kept on the element | class="my-animation super" | - * | 10. The doneCallback() callback is fired (if provided) | class="my-animation super" | - * - * @param {jQuery/jqLite element} element the element that will be animated - * @param {string} className the CSS class that will be added to the element and then animated - * @param {function()=} doneCallback the callback function that will be called once the animation is complete - */ - addClass : function(element, className, doneCallback) { - performAnimation('addClass', className, element, null, null, function() { - $delegate.addClass(element, className); - }, doneCallback); - }, - - /** - * @ngdoc function - * @name ngAnimate.$animate#removeClass - * @methodOf ngAnimate.$animate - * - * @description - * Triggers a custom animation event based off the className variable and then removes the CSS class provided by the className value - * from the element. Unlike the other animation methods, the animate service will suffix the className value with {@type -remove} in - * order to provide the animate service the setup and active CSS classes in order to trigger the animation (this will be skipped if - * no CSS transitions or keyframes are defined on the -remove or base CSS classes). - * - * Below is a breakdown of each step that occurs during removeClass animation: - * - * | Animation Step | What the element class attribute looks like | - * |-----------------------------------------------------------------------------------------------|---------------------------------------------| - * | 1. $animate.removeClass(element, 'super') is called | class="my-animation super" | - * | 2. $animate runs any JavaScript-defined animations on the element | class="my-animation super ng-animate" | - * | 3. the .super-remove class are added to the element | class="my-animation super ng-animate super-remove"| - * | 4. $animate scans the element styles to get the CSS transition/animation duration and delay | class="my-animation super ng-animate super-remove" | - * | 5. $animate waits for 10ms (this performs a reflow) | class="my-animation super ng-animate super-remove" | - * | 6. the .super-remove-active and .ng-animate-active classes are added and .super is removed (this triggers the CSS transition/animation) | class="my-animation ng-animate ng-animate-active super-remove super-remove-active" | - * | 7. $animate waits for X milliseconds for the animation to complete | class="my-animation ng-animate ng-animate-active super-remove super-remove-active" | - * | 8. The animation ends and all generated CSS classes are removed from the element | class="my-animation" | - * | 9. The doneCallback() callback is fired (if provided) | class="my-animation" | - * - * - * @param {jQuery/jqLite element} element the element that will be animated - * @param {string} className the CSS class that will be animated and then removed from the element - * @param {function()=} doneCallback the callback function that will be called once the animation is complete - */ - removeClass : function(element, className, doneCallback) { - performAnimation('removeClass', className, element, null, null, function() { - $delegate.removeClass(element, className); - }, doneCallback); - }, - - /** - * @ngdoc function - * @name ngAnimate.$animate#enabled - * @methodOf ngAnimate.$animate - * @function - * - * @param {boolean=} value If provided then set the animation on or off. - * @return {boolean} Current animation state. - * - * @description - * Globally enables/disables animations. - * - */ - enabled : function(value, element) { - switch(arguments.length) { - case 2: - if(value) { - cleanup(element); - } else { - var data = element.data(NG_ANIMATE_STATE) || {}; - data.disabled = true; - element.data(NG_ANIMATE_STATE, data); - } - break; - - case 1: - rootAnimateState.disabled = !value; - break; - - default: - value = !rootAnimateState.disabled; - break; - } - return !!value; - } - }; - - /* - all animations call this shared animation triggering function internally. - The animationEvent variable refers to the JavaScript animation event that will be triggered - and the className value is the name of the animation that will be applied within the - CSS code. Element, parentElement and afterElement are provided DOM elements for the animation - and the onComplete callback will be fired once the animation is fully complete. - */ - function performAnimation(animationEvent, className, element, parentElement, afterElement, domOperation, doneCallback) { - var classes = (element.attr('class') || '') + ' ' + className; - var animationLookup = (' ' + classes).replace(/\s+/g,'.'); - if (!parentElement) { - parentElement = afterElement ? afterElement.parent() : element.parent(); - } - - var matches = lookup(animationLookup); - var isClassBased = animationEvent == 'addClass' || animationEvent == 'removeClass'; - var ngAnimateState = element.data(NG_ANIMATE_STATE) || {}; - - //skip the animation if animations are disabled, a parent is already being animated, - //the element is not currently attached to the document body or then completely close - //the animation if any matching animations are not found at all. - //NOTE: IE8 + IE9 should close properly (run closeAnimation()) in case a NO animation is not found. - if (animationsDisabled(element, parentElement) || matches.length === 0) { - domOperation(); - closeAnimation(); - return; - } - - var animations = []; - //only add animations if the currently running animation is not structural - //or if there is no animation running at all - if(!ngAnimateState.running || !(isClassBased && ngAnimateState.structural)) { - forEach(matches, function(animation) { - //add the animation to the queue to if it is allowed to be cancelled - if(!animation.allowCancel || animation.allowCancel(element, animationEvent, className)) { - var beforeFn, afterFn = animation[animationEvent]; - - //Special case for a leave animation since there is no point in performing an - //animation on a element node that has already been removed from the DOM - if(animationEvent == 'leave') { - beforeFn = afterFn; - afterFn = null; //this must be falsy so that the animation is skipped for leave - } else { - beforeFn = animation['before' + animationEvent.charAt(0).toUpperCase() + animationEvent.substr(1)]; - } - animations.push({ - before : beforeFn, - after : afterFn - }); - } - }); - } - - //this would mean that an animation was not allowed so let the existing - //animation do it's thing and close this one early - if(animations.length === 0) { - domOperation(); - fireDoneCallbackAsync(); - return; - } - - if(ngAnimateState.running) { - //if an animation is currently running on the element then lets take the steps - //to cancel that animation and fire any required callbacks - $timeout.cancel(ngAnimateState.closeAnimationTimeout); - cleanup(element); - cancelAnimations(ngAnimateState.animations); - (ngAnimateState.done || noop)(true); - } - - //There is no point in perform a class-based animation if the element already contains - //(on addClass) or doesn't contain (on removeClass) the className being animated. - //The reason why this is being called after the previous animations are cancelled - //is so that the CSS classes present on the element can be properly examined. - if((animationEvent == 'addClass' && element.hasClass(className)) || - (animationEvent == 'removeClass' && !element.hasClass(className))) { - domOperation(); - fireDoneCallbackAsync(); - return; - } - - //the ng-animate class does nothing, but it's here to allow for - //parent animations to find and cancel child animations when needed - element.addClass(NG_ANIMATE_CLASS_NAME); - - element.data(NG_ANIMATE_STATE, { - running:true, - structural:!isClassBased, - animations:animations, - done:onBeforeAnimationsComplete - }); - - //first we run the before animations and when all of those are complete - //then we perform the DOM operation and run the next set of animations - invokeRegisteredAnimationFns(animations, 'before', onBeforeAnimationsComplete); - - function onBeforeAnimationsComplete(cancelled) { - domOperation(); - if(cancelled === true) { - closeAnimation(); - return; - } - - //set the done function to the final done function - //so that the DOM event won't be executed twice by accident - //if the after animation is cancelled as well - var data = element.data(NG_ANIMATE_STATE); - if(data) { - data.done = closeAnimation; - element.data(NG_ANIMATE_STATE, data); - } - invokeRegisteredAnimationFns(animations, 'after', closeAnimation); - } - - function invokeRegisteredAnimationFns(animations, phase, allAnimationFnsComplete) { - var endFnName = phase + 'End'; - forEach(animations, function(animation, index) { - var animationPhaseCompleted = function() { - progress(index, phase); - }; - - //there are no before functions for enter + move since the DOM - //operations happen before the performAnimation method fires - if(phase == 'before' && (animationEvent == 'enter' || animationEvent == 'move')) { - animationPhaseCompleted(); - return; - } - - if(animation[phase]) { - animation[endFnName] = isClassBased ? - animation[phase](element, className, animationPhaseCompleted) : - animation[phase](element, animationPhaseCompleted); - } else { - animationPhaseCompleted(); - } - }); - - function progress(index, phase) { - var phaseCompletionFlag = phase + 'Complete'; - var currentAnimation = animations[index]; - currentAnimation[phaseCompletionFlag] = true; - (currentAnimation[endFnName] || noop)(); - - for(var i=0;i<animations.length;i++) { - if(!animations[i][phaseCompletionFlag]) return; - } - - allAnimationFnsComplete(); - } - } - - function fireDoneCallbackAsync() { - doneCallback && $timeout(doneCallback, 0, false); - } - - function closeAnimation() { - if(!closeAnimation.hasBeenRun) { - closeAnimation.hasBeenRun = true; - var data = element.data(NG_ANIMATE_STATE); - if(data) { - /* only structural animations wait for reflow before removing an - animation, but class-based animations don't. An example of this - failing would be when a parent HTML tag has a ng-class attribute - causing ALL directives below to skip animations during the digest */ - if(isClassBased) { - cleanup(element); - } else { - data.closeAnimationTimeout = $timeout(function() { - cleanup(element); - }, 0, false); - element.data(NG_ANIMATE_STATE, data); - } - } - fireDoneCallbackAsync(); - } - } - } - - function cancelChildAnimations(element) { - var node = element[0]; - if(node.nodeType != ELEMENT_NODE) { - return; - } - - forEach(node.querySelectorAll('.' + NG_ANIMATE_CLASS_NAME), function(element) { - element = angular.element(element); - var data = element.data(NG_ANIMATE_STATE); - if(data) { - cancelAnimations(data.animations); - cleanup(element); - } - }); - } - - function cancelAnimations(animations) { - var isCancelledFlag = true; - forEach(animations, function(animation) { - if(!animations['beforeComplete']) { - (animation.beforeEnd || noop)(isCancelledFlag); - } - if(!animations['afterComplete']) { - (animation.afterEnd || noop)(isCancelledFlag); - } - }); - } - - function cleanup(element) { - if(element[0] == $rootElement[0]) { - if(!rootAnimateState.disabled) { - rootAnimateState.running = false; - rootAnimateState.structural = false; - } - } else { - element.removeClass(NG_ANIMATE_CLASS_NAME); - element.removeData(NG_ANIMATE_STATE); - } - } - - function animationsDisabled(element, parentElement) { - if (rootAnimateState.disabled) return true; - - if(element[0] == $rootElement[0]) { - return rootAnimateState.disabled || rootAnimateState.running; - } - - do { - //the element did not reach the root element which means that it - //is not apart of the DOM. Therefore there is no reason to do - //any animations on it - if(parentElement.length === 0) break; - - var isRoot = parentElement[0] == $rootElement[0]; - var state = isRoot ? rootAnimateState : parentElement.data(NG_ANIMATE_STATE); - var result = state && (!!state.disabled || !!state.running); - if(isRoot || result) { - return result; - } - - if(isRoot) return true; - } - while(parentElement = parentElement.parent()); - - return true; - } - }]); - - $animateProvider.register('', ['$window', '$sniffer', '$timeout', function($window, $sniffer, $timeout) { - // Detect proper transitionend/animationend event names. - var CSS_PREFIX = '', TRANSITION_PROP, TRANSITIONEND_EVENT, ANIMATION_PROP, ANIMATIONEND_EVENT; - - // If unprefixed events are not supported but webkit-prefixed are, use the latter. - // Otherwise, just use W3C names, browsers not supporting them at all will just ignore them. - // Note: Chrome implements `window.onwebkitanimationend` and doesn't implement `window.onanimationend` - // but at the same time dispatches the `animationend` event and not `webkitAnimationEnd`. - // Register both events in case `window.onanimationend` is not supported because of that, - // do the same for `transitionend` as Safari is likely to exhibit similar behavior. - // Also, the only modern browser that uses vendor prefixes for transitions/keyframes is webkit - // therefore there is no reason to test anymore for other vendor prefixes: http://caniuse.com/#search=transition - if (window.ontransitionend === undefined && window.onwebkittransitionend !== undefined) { - CSS_PREFIX = '-webkit-'; - TRANSITION_PROP = 'WebkitTransition'; - TRANSITIONEND_EVENT = 'webkitTransitionEnd transitionend'; - } else { - TRANSITION_PROP = 'transition'; - TRANSITIONEND_EVENT = 'transitionend'; - } - - if (window.onanimationend === undefined && window.onwebkitanimationend !== undefined) { - CSS_PREFIX = '-webkit-'; - ANIMATION_PROP = 'WebkitAnimation'; - ANIMATIONEND_EVENT = 'webkitAnimationEnd animationend'; - } else { - ANIMATION_PROP = 'animation'; - ANIMATIONEND_EVENT = 'animationend'; - } - - var DURATION_KEY = 'Duration'; - var PROPERTY_KEY = 'Property'; - var DELAY_KEY = 'Delay'; - var ANIMATION_ITERATION_COUNT_KEY = 'IterationCount'; - var NG_ANIMATE_PARENT_KEY = '$$ngAnimateKey'; - var NG_ANIMATE_CSS_DATA_KEY = '$$ngAnimateCSS3Data'; - var NG_ANIMATE_FALLBACK_CLASS_NAME = 'ng-animate-start'; - var NG_ANIMATE_FALLBACK_ACTIVE_CLASS_NAME = 'ng-animate-active'; - - var lookupCache = {}; - var parentCounter = 0; - - var animationReflowQueue = [], animationTimer, timeOut = false; - function afterReflow(callback) { - animationReflowQueue.push(callback); - $timeout.cancel(animationTimer); - animationTimer = $timeout(function() { - forEach(animationReflowQueue, function(fn) { - fn(); - }); - animationReflowQueue = []; - animationTimer = null; - lookupCache = {}; - }, 10, false); - } - - function applyStyle(node, style) { - var oldStyle = node.getAttribute('style') || ''; - var newStyle = (oldStyle.length > 0 ? '; ' : '') + style; - node.setAttribute('style', newStyle); - return oldStyle; - } - - function getElementAnimationDetails(element, cacheKey) { - var data = cacheKey ? lookupCache[cacheKey] : null; - if(!data) { - var transitionDuration = 0; - var transitionDelay = 0; - var animationDuration = 0; - var animationDelay = 0; - var transitionDelayStyle; - var animationDelayStyle; - var transitionDurationStyle; - var transitionPropertyStyle; - - //we want all the styles defined before and after - forEach(element, function(element) { - if (element.nodeType == ELEMENT_NODE) { - var elementStyles = $window.getComputedStyle(element) || {}; - - transitionDurationStyle = elementStyles[TRANSITION_PROP + DURATION_KEY]; - - transitionDuration = Math.max(parseMaxTime(transitionDurationStyle), transitionDuration); - - transitionPropertyStyle = elementStyles[TRANSITION_PROP + PROPERTY_KEY]; - - transitionDelayStyle = elementStyles[TRANSITION_PROP + DELAY_KEY]; - - transitionDelay = Math.max(parseMaxTime(transitionDelayStyle), transitionDelay); - - animationDelayStyle = elementStyles[ANIMATION_PROP + DELAY_KEY]; - - animationDelay = Math.max(parseMaxTime(animationDelayStyle), animationDelay); - - var aDuration = parseMaxTime(elementStyles[ANIMATION_PROP + DURATION_KEY]); - - if(aDuration > 0) { - aDuration *= parseInt(elementStyles[ANIMATION_PROP + ANIMATION_ITERATION_COUNT_KEY], 10) || 1; - } - - animationDuration = Math.max(aDuration, animationDuration); - } - }); - data = { - total : 0, - transitionPropertyStyle: transitionPropertyStyle, - transitionDurationStyle: transitionDurationStyle, - transitionDelayStyle: transitionDelayStyle, - transitionDelay: transitionDelay, - transitionDuration: transitionDuration, - animationDelayStyle: animationDelayStyle, - animationDelay: animationDelay, - animationDuration: animationDuration - }; - if(cacheKey) { - lookupCache[cacheKey] = data; - } - } - return data; - } - - function parseMaxTime(str) { - var maxValue = 0; - var values = angular.isString(str) ? - str.split(/\s*,\s*/) : - []; - forEach(values, function(value) { - maxValue = Math.max(parseFloat(value) || 0, maxValue); - }); - return maxValue; - } - - function getCacheKey(element) { - var parentElement = element.parent(); - var parentID = parentElement.data(NG_ANIMATE_PARENT_KEY); - if(!parentID) { - parentElement.data(NG_ANIMATE_PARENT_KEY, ++parentCounter); - parentID = parentCounter; - } - return parentID + '-' + element[0].className; - } - - function animateSetup(element, className) { - var cacheKey = getCacheKey(element); - var eventCacheKey = cacheKey + ' ' + className; - var stagger = {}; - var ii = lookupCache[eventCacheKey] ? ++lookupCache[eventCacheKey].total : 0; - - if(ii > 0) { - var staggerClassName = className + '-stagger'; - var staggerCacheKey = cacheKey + ' ' + staggerClassName; - var applyClasses = !lookupCache[staggerCacheKey]; - - applyClasses && element.addClass(staggerClassName); - - stagger = getElementAnimationDetails(element, staggerCacheKey); - - applyClasses && element.removeClass(staggerClassName); - } - - element.addClass(className); - - var timings = getElementAnimationDetails(element, eventCacheKey); - - /* there is no point in performing a reflow if the animation - timeout is empty (this would cause a flicker bug normally - in the page. There is also no point in performing an animation - that only has a delay and no duration */ - var maxDuration = Math.max(timings.transitionDuration, timings.animationDuration); - if(maxDuration === 0) { - element.removeClass(className); - return false; - } - - var node = element[0]; - //temporarily disable the transition so that the enter styles - //don't animate twice (this is here to avoid a bug in Chrome/FF). - var activeClassName = ''; - if(timings.transitionDuration > 0) { - element.addClass(NG_ANIMATE_FALLBACK_CLASS_NAME); - activeClassName += NG_ANIMATE_FALLBACK_ACTIVE_CLASS_NAME + ' '; - node.style[TRANSITION_PROP + PROPERTY_KEY] = 'none'; - } - - forEach(className.split(' '), function(klass, i) { - activeClassName += (i > 0 ? ' ' : '') + klass + '-active'; - }); - - element.data(NG_ANIMATE_CSS_DATA_KEY, { - className : className, - activeClassName : activeClassName, - maxDuration : maxDuration, - classes : className + ' ' + activeClassName, - timings : timings, - stagger : stagger, - ii : ii - }); - - return true; - } - - function animateRun(element, className, activeAnimationComplete) { - var data = element.data(NG_ANIMATE_CSS_DATA_KEY); - if(!element.hasClass(className) || !data) { - activeAnimationComplete(); - return; - } - - var node = element[0]; - var timings = data.timings; - var stagger = data.stagger; - var maxDuration = data.maxDuration; - var activeClassName = data.activeClassName; - var maxDelayTime = Math.max(timings.transitionDelay, timings.animationDelay) * 1000; - var startTime = Date.now(); - var css3AnimationEvents = ANIMATIONEND_EVENT + ' ' + TRANSITIONEND_EVENT; - var formerStyle; - var ii = data.ii; - - var applyFallbackStyle, style = ''; - if(timings.transitionDuration > 0) { - node.style[TRANSITION_PROP + PROPERTY_KEY] = ''; - - var propertyStyle = timings.transitionPropertyStyle; - if(propertyStyle.indexOf('all') == -1) { - applyFallbackStyle = true; - var fallbackProperty = $sniffer.msie ? '-ms-zoom' : 'clip'; - style += CSS_PREFIX + 'transition-property: ' + propertyStyle + ', ' + fallbackProperty + '; '; - style += CSS_PREFIX + 'transition-duration: ' + timings.transitionDurationStyle + ', ' + timings.transitionDuration + 's; '; - } - } - - if(ii > 0) { - if(stagger.transitionDelay > 0 && stagger.transitionDuration === 0) { - var delayStyle = timings.transitionDelayStyle; - if(applyFallbackStyle) { - delayStyle += ', ' + timings.transitionDelay + 's'; - } - - style += CSS_PREFIX + 'transition-delay: ' + - prepareStaggerDelay(delayStyle, stagger.transitionDelay, ii) + '; '; - } - - if(stagger.animationDelay > 0 && stagger.animationDuration === 0) { - style += CSS_PREFIX + 'animation-delay: ' + - prepareStaggerDelay(timings.animationDelayStyle, stagger.animationDelay, ii) + '; '; - } - } - - if(style.length > 0) { - formerStyle = applyStyle(node, style); - } - - element.on(css3AnimationEvents, onAnimationProgress); - element.addClass(activeClassName); - - // This will automatically be called by $animate so - // there is no need to attach this internally to the - // timeout done method. - return function onEnd(cancelled) { - element.off(css3AnimationEvents, onAnimationProgress); - element.removeClass(activeClassName); - animateClose(element, className); - if(formerStyle != null) { - formerStyle.length > 0 ? - node.setAttribute('style', formerStyle) : - node.removeAttribute('style'); - } - }; - - function onAnimationProgress(event) { - event.stopPropagation(); - var ev = event.originalEvent || event; - var timeStamp = ev.$manualTimeStamp || ev.timeStamp || Date.now(); - /* $manualTimeStamp is a mocked timeStamp value which is set - * within browserTrigger(). This is only here so that tests can - * mock animations properly. Real events fallback to event.timeStamp, - * or, if they don't, then a timeStamp is automatically created for them. - * We're checking to see if the timeStamp surpasses the expected delay, - * but we're using elapsedTime instead of the timeStamp on the 2nd - * pre-condition since animations sometimes close off early */ - if(Math.max(timeStamp - startTime, 0) >= maxDelayTime && ev.elapsedTime >= maxDuration) { - activeAnimationComplete(); - } - } - } - - function prepareStaggerDelay(delayStyle, staggerDelay, index) { - var style = ''; - forEach(delayStyle.split(','), function(val, i) { - style += (i > 0 ? ',' : '') + - (index * staggerDelay + parseInt(val, 10)) + 's'; - }); - return style; - } - - function animateBefore(element, className) { - if(animateSetup(element, className)) { - return function(cancelled) { - cancelled && animateClose(element, className); - }; - } - } - - function animateAfter(element, className, afterAnimationComplete) { - if(element.data(NG_ANIMATE_CSS_DATA_KEY)) { - return animateRun(element, className, afterAnimationComplete); - } else { - animateClose(element, className); - afterAnimationComplete(); - } - } - - function animate(element, className, animationComplete) { - //If the animateSetup function doesn't bother returning a - //cancellation function then it means that there is no animation - //to perform at all - var preReflowCancellation = animateBefore(element, className); - if(!preReflowCancellation) { - animationComplete(); - return; - } - - //There are two cancellation functions: one is before the first - //reflow animation and the second is during the active state - //animation. The first function will take care of removing the - //data from the element which will not make the 2nd animation - //happen in the first place - var cancel = preReflowCancellation; - afterReflow(function() { - //once the reflow is complete then we point cancel to - //the new cancellation function which will remove all of the - //animation properties from the active animation - cancel = animateAfter(element, className, animationComplete); - }); - - return function(cancelled) { - (cancel || noop)(cancelled); - }; - } - - function animateClose(element, className) { - element.removeClass(className); - element.removeClass(NG_ANIMATE_FALLBACK_CLASS_NAME); - element.removeData(NG_ANIMATE_CSS_DATA_KEY); - } - - return { - allowCancel : function(element, animationEvent, className) { - //always cancel the current animation if it is a - //structural animation - var oldClasses = (element.data(NG_ANIMATE_CSS_DATA_KEY) || {}).classes; - if(!oldClasses || ['enter','leave','move'].indexOf(animationEvent) >= 0) { - return true; - } - - var parentElement = element.parent(); - var clone = angular.element(element[0].cloneNode()); - - //make the element super hidden and override any CSS style values - clone.attr('style','position:absolute; top:-9999px; left:-9999px'); - clone.removeAttr('id'); - clone.html(''); - - forEach(oldClasses.split(' '), function(klass) { - clone.removeClass(klass); - }); - - var suffix = animationEvent == 'addClass' ? '-add' : '-remove'; - clone.addClass(suffixClasses(className, suffix)); - parentElement.append(clone); - - var timings = getElementAnimationDetails(clone); - clone.remove(); - - return Math.max(timings.transitionDuration, timings.animationDuration) > 0; - }, - - enter : function(element, animationCompleted) { - return animate(element, 'ng-enter', animationCompleted); - }, - - leave : function(element, animationCompleted) { - return animate(element, 'ng-leave', animationCompleted); - }, - - move : function(element, animationCompleted) { - return animate(element, 'ng-move', animationCompleted); - }, - - beforeAddClass : function(element, className, animationCompleted) { - var cancellationMethod = animateBefore(element, suffixClasses(className, '-add')); - if(cancellationMethod) { - afterReflow(animationCompleted); - return cancellationMethod; - } - animationCompleted(); - }, - - addClass : function(element, className, animationCompleted) { - return animateAfter(element, suffixClasses(className, '-add'), animationCompleted); - }, - - beforeRemoveClass : function(element, className, animationCompleted) { - var cancellationMethod = animateBefore(element, suffixClasses(className, '-remove')); - if(cancellationMethod) { - afterReflow(animationCompleted); - return cancellationMethod; - } - animationCompleted(); - }, - - removeClass : function(element, className, animationCompleted) { - return animateAfter(element, suffixClasses(className, '-remove'), animationCompleted); - } - }; - - function suffixClasses(classes, suffix) { - var className = ''; - classes = angular.isArray(classes) ? classes : classes.split(/\s+/); - forEach(classes, function(klass, i) { - if(klass && klass.length > 0) { - className += (i > 0 ? ' ' : '') + klass + suffix; - } - }); - return className; - } - }]); - }]); - - -})(window, window.angular); |