angularjs-rails 1.2.15 → 1.2.16

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,5 +1,5 @@
1
1
  /**
2
- * @license AngularJS v1.3.0-beta.3
2
+ * @license AngularJS v1.3.0-beta.5
3
3
  * (c) 2010-2014 Google, Inc. http://angularjs.org
4
4
  * License: MIT
5
5
  */
@@ -12,11 +12,8 @@
12
12
  * @name ngAnimate
13
13
  * @description
14
14
  *
15
- * # ngAnimate
16
- *
17
15
  * The `ngAnimate` module provides support for JavaScript, CSS3 transition and CSS3 keyframe animation hooks within existing core and custom directives.
18
16
  *
19
- *
20
17
  * <div doc-module-components="ngAnimate"></div>
21
18
  *
22
19
  * # Usage
@@ -28,17 +25,16 @@
28
25
  *
29
26
  * Below is a more detailed breakdown of the supported animation events provided by pre-existing ng directives:
30
27
  *
31
- * | Directive | Supported Animations |
32
- * |---------------------------------------------------------- |----------------------------------------------------|
33
- * | {@link ng.directive:ngRepeat#usage_animations ngRepeat} | enter, leave and move |
34
- * | {@link ngRoute.directive:ngView#usage_animations ngView} | enter and leave |
35
- * | {@link ng.directive:ngInclude#usage_animations ngInclude} | enter and leave |
36
- * | {@link ng.directive:ngSwitch#usage_animations ngSwitch} | enter and leave |
37
- * | {@link ng.directive:ngIf#usage_animations ngIf} | enter and leave |
38
- * | {@link ng.directive:ngClass#usage_animations ngClass} | add and remove |
39
- * | {@link ng.directive:ngShow#usage_animations ngShow & ngHide} | add and remove (the ng-hide class value) |
40
- * | {@link ng.directive:form#usage_animations form} | add and remove (dirty, pristine, valid, invalid & all other validations) |
41
- * | {@link ng.directive:ngModel#usage_animations ngModel} | add and remove (dirty, pristine, valid, invalid & all other validations) |
28
+ * | Directive | Supported Animations |
29
+ * |-----------------------------------------------------------------------------------------------------------|--------------------------------------------------------------------------|
30
+ * | {@link ng.directive:ngRepeat#usage_animations ngRepeat} | enter, leave and move |
31
+ * | {@link ngRoute.directive:ngView#usage_animations ngView} | enter and leave |
32
+ * | {@link ng.directive:ngInclude#usage_animations ngInclude} | enter and leave |
33
+ * | {@link ng.directive:ngSwitch#usage_animations ngSwitch} | enter and leave |
34
+ * | {@link ng.directive:ngIf#usage_animations ngIf} | enter and leave |
35
+ * | {@link ng.directive:ngClass#usage_animations ngClass} | add and remove (the CSS class(es) present) |
36
+ * | {@link ng.directive:ngShow#usage_animations ngShow} & {@link ng.directive:ngHide#usage_animations ngHide} | add and remove (the ng-hide class value) |
37
+ * | {@link ng.directive:form#usage_animations form} & {@link ng.directive:ngModel#usage_animations ngModel} | add and remove (dirty, pristine, valid, invalid & all other validations) |
42
38
  *
43
39
  * You can find out more information about animations upon visiting each directive page.
44
40
  *
@@ -112,11 +108,11 @@
112
108
  * -webkit-animation: enter_sequence 1s linear; /&#42; Safari/Chrome &#42;/
113
109
  * animation: enter_sequence 1s linear; /&#42; IE10+ and Future Browsers &#42;/
114
110
  * }
115
- * &#64-webkit-keyframes enter_sequence {
111
+ * @-webkit-keyframes enter_sequence {
116
112
  * from { opacity:0; }
117
113
  * to { opacity:1; }
118
114
  * }
119
- * &#64keyframes enter_sequence {
115
+ * @keyframes enter_sequence {
120
116
  * from { opacity:0; }
121
117
  * to { opacity:1; }
122
118
  * }
@@ -136,7 +132,74 @@
136
132
  * immediately resulting in a DOM element that is at its final state. This final state is when the DOM element
137
133
  * has no CSS transition/animation classes applied to it.
138
134
  *
139
- * <h3>CSS Staggering Animations</h3>
135
+ * ### Structural transition animations
136
+ *
137
+ * Structural transitions (such as enter, leave and move) will always apply a `0s none` transition
138
+ * value to force the browser into rendering the styles defined in the setup (.ng-enter, .ng-leave
139
+ * or .ng-move) class. This means that any active transition animations operating on the element
140
+ * will be cut off to make way for the enter, leave or move animation.
141
+ *
142
+ * ### Class-based transition animations
143
+ *
144
+ * Class-based transitions refer to transition animations that are triggered when a CSS class is
145
+ * added to or removed from the element (via `$animate.addClass`, `$animate.removeClass`,
146
+ * `$animate.setClass`, or by directives such as `ngClass`, `ngModel` and `form`).
147
+ * They are different when compared to structural animations since they **do not cancel existing
148
+ * animations** nor do they **block successive transitions** from rendering on the same element.
149
+ * This distinction allows for **multiple class-based transitions** to be performed on the same element.
150
+ *
151
+ * In addition to ngAnimate supporting the default (natural) functionality of class-based transition
152
+ * animations, ngAnimate also decorates the element with starting and ending CSS classes to aid the
153
+ * developer in further styling the element throughout the transition animation. Earlier versions
154
+ * of ngAnimate may have caused natural CSS transitions to break and not render properly due to
155
+ * $animate temporarily blocking transitions using `0s none` in order to allow the setup CSS class
156
+ * (the `-add` or `-remove` class) to be applied without triggering an animation. However, as of
157
+ * **version 1.3**, this workaround has been removed with ngAnimate and all non-ngAnimate CSS
158
+ * class transitions are compatible with ngAnimate.
159
+ *
160
+ * There is, however, one special case when dealing with class-based transitions in ngAnimate.
161
+ * When rendering class-based transitions that make use of the setup and active CSS classes
162
+ * (e.g. `.fade-add` and `.fade-add-active` for when `.fade` is added) be sure to define
163
+ * the transition value **on the active CSS class** and not the setup class.
164
+ *
165
+ * ```css
166
+ * .fade-add {
167
+ * /&#42; remember to place a 0s transition here
168
+ * to ensure that the styles are applied instantly
169
+ * even if the element already has a transition style &#42;/
170
+ * transition:0s linear all;
171
+ *
172
+ * /&#42; starting CSS styles &#42;/
173
+ * opacity:1;
174
+ * }
175
+ * .fade-add.fade-add-active {
176
+ * /&#42; this will be the length of the animation &#42;/
177
+ * transition:1s linear all;
178
+ * opacity:0;
179
+ * }
180
+ * ```
181
+ *
182
+ * The setup CSS class (in this case `.fade-add`) also has a transition style property, however, it
183
+ * has a duration of zero. This may not be required, however, incase the browser is unable to render
184
+ * the styling present in this CSS class instantly then it could be that the browser is attempting
185
+ * to perform an unnecessary transition.
186
+ *
187
+ * This workaround, however, does not apply to standard class-based transitions that are rendered
188
+ * when a CSS class containing a transition is applied to an element:
189
+ *
190
+ * ```css
191
+ * .fade {
192
+ * /&#42; this works as expected &#42;/
193
+ * transition:1s linear all;
194
+ * opacity:0;
195
+ * }
196
+ * ```
197
+ *
198
+ * Please keep this in mind when coding the CSS markup that will be used within class-based transitions.
199
+ * Also, try not to mix the two class-based animation flavors together since the CSS code may become
200
+ * overly complex.
201
+ *
202
+ * ### CSS Staggering Animations
140
203
  * A Staggering animation is a collection of animations that are issued with a slight delay in between each successive operation resulting in a
141
204
  * curtain-like effect. The ngAnimate module, as of 1.2.0, supports staggering animations and the stagger effect can be
142
205
  * performed by creating a **ng-EVENT-stagger** CSS class and attaching that class to the base CSS class used for
@@ -338,9 +401,12 @@ angular.module('ngAnimate', ['ng'])
338
401
  //operation which performs CSS transition and keyframe
339
402
  //animations sniffing. This is always included for each
340
403
  //element animation procedure if the browser supports
341
- //transitions and/or keyframe animations
404
+ //transitions and/or keyframe animations. The default
405
+ //animation is added to the top of the list to prevent
406
+ //any previous animations from affecting the element styling
407
+ //prior to the element being animated.
342
408
  if ($sniffer.transitions || $sniffer.animations) {
343
- classes.push('');
409
+ matches.push($injector.get(selectors['']));
344
410
  }
345
411
 
346
412
  for(var i=0; i < classes.length; i++) {
@@ -528,18 +594,21 @@ angular.module('ngAnimate', ['ng'])
528
594
  *
529
595
  * Below is a breakdown of each step that occurs during enter animation:
530
596
  *
531
- * | Animation Step | What the element class attribute looks like |
532
- * |----------------------------------------------------------------------------------------------|---------------------------------------------|
533
- * | 1. $animate.enter(...) is called | class="my-animation" |
534
- * | 2. element is inserted into the parentElement element or beside the afterElement element | class="my-animation" |
535
- * | 3. $animate runs any JavaScript-defined animations on the element | class="my-animation ng-animate" |
536
- * | 4. the .ng-enter class is added to the element | class="my-animation ng-animate ng-enter" |
537
- * | 5. $animate scans the element styles to get the CSS transition/animation duration and delay | class="my-animation ng-animate ng-enter" |
538
- * | 6. $animate waits for 10ms (this performs a reflow) | class="my-animation ng-animate ng-enter" |
539
- * | 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" |
540
- * | 8. $animate waits for X milliseconds for the animation to complete | class="my-animation ng-animate ng-animate-active ng-enter ng-enter-active" |
541
- * | 9. The animation ends and all generated CSS classes are removed from the element | class="my-animation" |
542
- * | 10. The doneCallback() callback is fired (if provided) | class="my-animation" |
597
+ * | Animation Step | What the element class attribute looks like |
598
+ * |-------------------------------------------------------------------------------------------------------------------|----------------------------------------------------------|
599
+ * | 1. $animate.enter(...) is called | class="my-animation" |
600
+ * | 2. element is inserted into the parentElement element or beside the afterElement element | class="my-animation" |
601
+ * | 3. $animate waits for the next digest to start the animation | class="my-animation ng-animate" |
602
+ * | 4. $animate runs the JavaScript-defined animations detected on the element | class="my-animation ng-animate" |
603
+ * | 5. the .ng-enter class is added to the element | class="my-animation ng-animate ng-enter" |
604
+ * | 6. $animate scans the element styles to get the CSS transition/animation duration and delay | class="my-animation ng-animate ng-enter" |
605
+ * | 7. $animate blocks all CSS transitions on the element to ensure the .ng-enter class styling is applied right away | class="my-animation ng-animate ng-enter" |
606
+ * | 8. $animate waits for a single animation frame (this performs a reflow) | class="my-animation ng-animate ng-enter" |
607
+ * | 9. $animate removes the CSS transition block placed on the element | class="my-animation ng-animate ng-enter" |
608
+ * | 10. the .ng-enter-active class is added (this triggers the CSS transition/animation) | class="my-animation ng-animate ng-enter ng-enter-active" |
609
+ * | 11. $animate waits for the animation to complete (via events and timeout) | class="my-animation ng-animate ng-enter ng-enter-active" |
610
+ * | 12. The animation ends and all generated CSS classes are removed from the element | class="my-animation" |
611
+ * | 13. The doneCallback() callback is fired (if provided) | class="my-animation" |
543
612
  *
544
613
  * @param {DOMElement} element the element that will be the focus of the enter animation
545
614
  * @param {DOMElement} parentElement the parent element of the element that will be the focus of the enter animation
@@ -566,18 +635,21 @@ angular.module('ngAnimate', ['ng'])
566
635
  *
567
636
  * Below is a breakdown of each step that occurs during leave animation:
568
637
  *
569
- * | Animation Step | What the element class attribute looks like |
570
- * |----------------------------------------------------------------------------------------------|---------------------------------------------|
571
- * | 1. $animate.leave(...) is called | class="my-animation" |
572
- * | 2. $animate runs any JavaScript-defined animations on the element | class="my-animation ng-animate" |
573
- * | 3. the .ng-leave class is added to the element | class="my-animation ng-animate ng-leave" |
574
- * | 4. $animate scans the element styles to get the CSS transition/animation duration and delay | class="my-animation ng-animate ng-leave" |
575
- * | 5. $animate waits for 10ms (this performs a reflow) | class="my-animation ng-animate ng-leave" |
576
- * | 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" |
577
- * | 7. $animate waits for X milliseconds for the animation to complete | class="my-animation ng-animate ng-animate-active ng-leave ng-leave-active" |
578
- * | 8. The animation ends and all generated CSS classes are removed from the element | class="my-animation" |
579
- * | 9. The element is removed from the DOM | ... |
580
- * | 10. The doneCallback() callback is fired (if provided) | ... |
638
+ * | Animation Step | What the element class attribute looks like |
639
+ * |-------------------------------------------------------------------------------------------------------------------|----------------------------------------------------------|
640
+ * | 1. $animate.leave(...) is called | class="my-animation" |
641
+ * | 2. $animate runs the JavaScript-defined animations detected on the element | class="my-animation ng-animate" |
642
+ * | 3. $animate waits for the next digest to start the animation | class="my-animation ng-animate" |
643
+ * | 4. the .ng-leave class is added to the element | class="my-animation ng-animate ng-leave" |
644
+ * | 5. $animate scans the element styles to get the CSS transition/animation duration and delay | class="my-animation ng-animate ng-leave" |
645
+ * | 6. $animate blocks all CSS transitions on the element to ensure the .ng-leave class styling is applied right away | class="my-animation ng-animate ng-leave|
646
+ * | 7. $animate waits for a single animation frame (this performs a reflow) | class="my-animation ng-animate ng-leave" |
647
+ * | 8. $animate removes the CSS transition block placed on the element | class="my-animation ng-animate ng-leave” |
648
+ * | 9. the .ng-leave-active class is added (this triggers the CSS transition/animation) | class="my-animation ng-animate ng-leave ng-leave-active" |
649
+ * | 10. $animate waits for the animation to complete (via events and timeout) | class="my-animation ng-animate ng-leave ng-leave-active" |
650
+ * | 11. The animation ends and all generated CSS classes are removed from the element | class="my-animation" |
651
+ * | 12. The element is removed from the DOM | ... |
652
+ * | 13. The doneCallback() callback is fired (if provided) | ... |
581
653
  *
582
654
  * @param {DOMElement} element the element that will be the focus of the leave animation
583
655
  * @param {function()=} doneCallback the callback function that will be called once the animation is complete
@@ -604,18 +676,21 @@ angular.module('ngAnimate', ['ng'])
604
676
  *
605
677
  * Below is a breakdown of each step that occurs during move animation:
606
678
  *
607
- * | Animation Step | What the element class attribute looks like |
608
- * |----------------------------------------------------------------------------------------------|---------------------------------------------|
609
- * | 1. $animate.move(...) is called | class="my-animation" |
610
- * | 2. element is moved into the parentElement element or beside the afterElement element | class="my-animation" |
611
- * | 3. $animate runs any JavaScript-defined animations on the element | class="my-animation ng-animate" |
612
- * | 4. the .ng-move class is added to the element | class="my-animation ng-animate ng-move" |
613
- * | 5. $animate scans the element styles to get the CSS transition/animation duration and delay | class="my-animation ng-animate ng-move" |
614
- * | 6. $animate waits for 10ms (this performs a reflow) | class="my-animation ng-animate ng-move" |
615
- * | 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" |
616
- * | 8. $animate waits for X milliseconds for the animation to complete | class="my-animation ng-animate ng-animate-active ng-move ng-move-active" |
617
- * | 9. The animation ends and all generated CSS classes are removed from the element | class="my-animation" |
618
- * | 10. The doneCallback() callback is fired (if provided) | class="my-animation" |
679
+ * | Animation Step | What the element class attribute looks like |
680
+ * |------------------------------------------------------------------------------------------------------------------|--------------------------------------------------------|
681
+ * | 1. $animate.move(...) is called | class="my-animation" |
682
+ * | 2. element is moved into the parentElement element or beside the afterElement element | class="my-animation" |
683
+ * | 3. $animate waits for the next digest to start the animation | class="my-animation ng-animate" |
684
+ * | 4. $animate runs the JavaScript-defined animations detected on the element | class="my-animation ng-animate" |
685
+ * | 5. the .ng-move class is added to the element | class="my-animation ng-animate ng-move" |
686
+ * | 6. $animate scans the element styles to get the CSS transition/animation duration and delay | class="my-animation ng-animate ng-move" |
687
+ * | 7. $animate blocks all CSS transitions on the element to ensure the .ng-move class styling is applied right away | class="my-animation ng-animate ng-move|
688
+ * | 8. $animate waits for a single animation frame (this performs a reflow) | class="my-animation ng-animate ng-move" |
689
+ * | 9. $animate removes the CSS transition block placed on the element | class="my-animation ng-animate ng-move” |
690
+ * | 10. the .ng-move-active class is added (this triggers the CSS transition/animation) | class="my-animation ng-animate ng-move ng-move-active" |
691
+ * | 11. $animate waits for the animation to complete (via events and timeout) | class="my-animation ng-animate ng-move ng-move-active" |
692
+ * | 12. The animation ends and all generated CSS classes are removed from the element | class="my-animation" |
693
+ * | 13. The doneCallback() callback is fired (if provided) | class="my-animation" |
619
694
  *
620
695
  * @param {DOMElement} element the element that will be the focus of the move animation
621
696
  * @param {DOMElement} parentElement the parentElement element of the element that will be the focus of the move animation
@@ -640,22 +715,22 @@ angular.module('ngAnimate', ['ng'])
640
715
  * Triggers a custom animation event based off the className variable and then attaches the className value to the element as a CSS class.
641
716
  * Unlike the other animation methods, the animate service will suffix the className value with {@type -add} in order to provide
642
717
  * the animate service the setup and active CSS classes in order to trigger the animation (this will be skipped if no CSS transitions
643
- * or keyframes are defined on the -add or base CSS class).
718
+ * or keyframes are defined on the -add-active or base CSS class).
644
719
  *
645
720
  * Below is a breakdown of each step that occurs during addClass animation:
646
721
  *
647
- * | Animation Step | What the element class attribute looks like |
648
- * |------------------------------------------------------------------------------------------------|---------------------------------------------|
649
- * | 1. $animate.addClass(element, 'super') is called | class="my-animation" |
650
- * | 2. $animate runs any JavaScript-defined animations on the element | class="my-animation ng-animate" |
651
- * | 3. the .super-add class are added to the element | class="my-animation ng-animate super-add" |
652
- * | 4. $animate scans the element styles to get the CSS transition/animation duration and delay | class="my-animation ng-animate super-add" |
653
- * | 5. $animate waits for 10ms (this performs a reflow) | class="my-animation ng-animate super-add" |
654
- * | 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" |
655
- * | 7. $animate waits for X milliseconds for the animation to complete | class="my-animation super super-add super-add-active" |
656
- * | 8. The animation ends and all generated CSS classes are removed from the element | class="my-animation super" |
657
- * | 9. The super class is kept on the element | class="my-animation super" |
658
- * | 10. The doneCallback() callback is fired (if provided) | class="my-animation super" |
722
+ * | Animation Step | What the element class attribute looks like |
723
+ * |----------------------------------------------------------------------------------------------------|------------------------------------------------------------------|
724
+ * | 1. $animate.addClass(element, 'super') is called | class="my-animation" |
725
+ * | 2. $animate runs the JavaScript-defined animations detected on the element | class="my-animation ng-animate" |
726
+ * | 3. the .super-add class is added to the element | class="my-animation ng-animate super-add" |
727
+ * | 4. $animate waits for a single animation frame (this performs a reflow) | class="my-animation ng-animate super-add" |
728
+ * | 5. the .super and .super-add-active classes are added (this triggers the CSS transition/animation) | class="my-animation ng-animate super super-add super-add-active" |
729
+ * | 6. $animate scans the element styles to get the CSS transition/animation duration and delay | class="my-animation ng-animate super-add" |
730
+ * | 7. $animate waits for the animation to complete (via events and timeout) | class="my-animation super super-add super-add-active" |
731
+ * | 8. The animation ends and all generated CSS classes are removed from the element | class="my-animation super" |
732
+ * | 9. The super class is kept on the element | class="my-animation super" |
733
+ * | 10. The doneCallback() callback is fired (if provided) | class="my-animation super" |
659
734
  *
660
735
  * @param {DOMElement} element the element that will be animated
661
736
  * @param {string} className the CSS class that will be added to the element and then animated
@@ -680,17 +755,17 @@ angular.module('ngAnimate', ['ng'])
680
755
  *
681
756
  * Below is a breakdown of each step that occurs during removeClass animation:
682
757
  *
683
- * | Animation Step | What the element class attribute looks like |
684
- * |-----------------------------------------------------------------------------------------------|---------------------------------------------|
685
- * | 1. $animate.removeClass(element, 'super') is called | class="my-animation super" |
686
- * | 2. $animate runs any JavaScript-defined animations on the element | class="my-animation super ng-animate" |
687
- * | 3. the .super-remove class are added to the element | class="my-animation super ng-animate super-remove"|
688
- * | 4. $animate scans the element styles to get the CSS transition/animation duration and delay | class="my-animation super ng-animate super-remove" |
689
- * | 5. $animate waits for 10ms (this performs a reflow) | class="my-animation super ng-animate super-remove" |
690
- * | 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" |
691
- * | 7. $animate waits for X milliseconds for the animation to complete | class="my-animation ng-animate ng-animate-active super-remove super-remove-active" |
692
- * | 8. The animation ends and all generated CSS classes are removed from the element | class="my-animation" |
693
- * | 9. The doneCallback() callback is fired (if provided) | class="my-animation" |
758
+ * | Animation Step | What the element class attribute looks like |
759
+ * |------------------------------------------------------------------------------------------------------------------|------------------------------------------------------------------|
760
+ * | 1. $animate.removeClass(element, 'super') is called | class="my-animation super" |
761
+ * | 2. $animate runs the JavaScript-defined animations detected on the element | class="my-animation super ng-animate" |
762
+ * | 3. the .super-remove class is added to the element | class="my-animation super ng-animate super-remove" |
763
+ * | 4. $animate waits for a single animation frame (this performs a reflow) | class="my-animation super ng-animate super-remove" |
764
+ * | 5. the .super-remove-active classes are added and .super is removed (this triggers the CSS transition/animation) | class="my-animation ng-animate super-remove super-remove-active" |
765
+ * | 6. $animate scans the element styles to get the CSS transition/animation duration and delay | class="my-animation super ng-animate super-remove" |
766
+ * | 7. $animate waits for the animation to complete (via events and timeout) | class="my-animation ng-animate super-remove super-remove-active" |
767
+ * | 8. The animation ends and all generated CSS classes are removed from the element | class="my-animation" |
768
+ * | 9. The doneCallback() callback is fired (if provided) | class="my-animation" |
694
769
  *
695
770
  *
696
771
  * @param {DOMElement} element the element that will be animated
@@ -704,20 +779,33 @@ angular.module('ngAnimate', ['ng'])
704
779
  }, doneCallback);
705
780
  },
706
781
 
707
- /**
708
- *
709
- * @ngdoc function
710
- * @name $animate#setClass
711
- * @function
712
- * @description Adds and/or removes the given CSS classes to and from the element.
713
- * Once complete, the done() callback will be fired (if provided).
714
- * @param {DOMElement} element the element which will it's CSS classes changed
715
- * removed from it
716
- * @param {string} add the CSS classes which will be added to the element
717
- * @param {string} remove the CSS class which will be removed from the element
718
- * @param {Function=} done the callback function (if provided) that will be fired after the
719
- * CSS classes have been set on the element
720
- */
782
+ /**
783
+ *
784
+ * @ngdoc method
785
+ * @name $animate#setClass
786
+ *
787
+ * @description Adds and/or removes the given CSS classes to and from the element.
788
+ * Once complete, the done() callback will be fired (if provided).
789
+ *
790
+ * | Animation Step | What the element class attribute looks like |
791
+ * |--------------------------------------------------------------------------------------------------------------------------------------|--------------------------------------------------------------------------------------|
792
+ * | 1. $animate.removeClass(element, ‘on’, ‘off’) is called | class="my-animation super off” |
793
+ * | 2. $animate runs the JavaScript-defined animations detected on the element | class="my-animation super ng-animate off” |
794
+ * | 3. the .on-add and .off-remove classes are added to the element | class="my-animation ng-animate on-add off-remove off” |
795
+ * | 4. $animate waits for a single animation frame (this performs a reflow) | class="my-animation ng-animate on-add off-remove off” |
796
+ * | 5. the .on, .on-add-active and .off-remove-active classes are added and .off is removed (this triggers the CSS transition/animation) | class="my-animation ng-animate on on-add on-add-active off-remove off-remove-active” |
797
+ * | 6. $animate scans the element styles to get the CSS transition/animation duration and delay | class="my-animation ng-animate on on-add on-add-active off-remove off-remove-active" |
798
+ * | 7. $animate waits for the animation to complete (via events and timeout) | class="my-animation ng-animate on on-add on-add-active off-remove off-remove-active" |
799
+ * | 8. The animation ends and all generated CSS classes are removed from the element | class="my-animation" |
800
+ * | 9. The doneCallback() callback is fired (if provided) | class="my-animation" |
801
+ *
802
+ * @param {DOMElement} element the element which will it's CSS classes changed
803
+ * removed from it
804
+ * @param {string} add the CSS classes which will be added to the element
805
+ * @param {string} remove the CSS class which will be removed from the element
806
+ * @param {Function=} done the callback function (if provided) that will be fired after the
807
+ * CSS classes have been set on the element
808
+ */
721
809
  setClass : function(element, add, remove, doneCallback) {
722
810
  element = stripCommentsFromElement(element);
723
811
  performAnimation('setClass', [add, remove], element, null, null, function() {
@@ -795,9 +883,9 @@ angular.module('ngAnimate', ['ng'])
795
883
 
796
884
  //only allow animations if the currently running animation is not structural
797
885
  //or if there is no animation running at all
798
- var skipAnimations = runner.isClassBased ?
799
- ngAnimateState.disabled || (lastAnimation && !lastAnimation.isClassBased) :
800
- false;
886
+ var skipAnimations = runner.isClassBased
887
+ ? ngAnimateState.disabled || (lastAnimation && !lastAnimation.isClassBased)
888
+ : false;
801
889
 
802
890
  //skip the animation if animations are disabled, a parent is already being animated,
803
891
  //the element is not currently attached to the document body or then completely close
@@ -1026,8 +1114,11 @@ angular.module('ngAnimate', ['ng'])
1026
1114
  if(parentElement.length === 0) break;
1027
1115
 
1028
1116
  var isRoot = isMatchingElement(parentElement, $rootElement);
1029
- var state = isRoot ? rootAnimateState : parentElement.data(NG_ANIMATE_STATE);
1030
- var result = state && (!!state.disabled || state.running || state.totalActive > 0);
1117
+ var state = isRoot ? rootAnimateState : (parentElement.data(NG_ANIMATE_STATE) || {});
1118
+ var result = state.disabled || state.running
1119
+ ? true
1120
+ : state.last && !state.last.isClassBased;
1121
+
1031
1122
  if(isRoot || result) {
1032
1123
  return result;
1033
1124
  }
@@ -1077,7 +1168,6 @@ angular.module('ngAnimate', ['ng'])
1077
1168
  var ANIMATION_ITERATION_COUNT_KEY = 'IterationCount';
1078
1169
  var NG_ANIMATE_PARENT_KEY = '$$ngAnimateKey';
1079
1170
  var NG_ANIMATE_CSS_DATA_KEY = '$$ngAnimateCSS3Data';
1080
- var NG_ANIMATE_BLOCK_CLASS_NAME = 'ng-animate-block-transitions';
1081
1171
  var ELAPSED_TIME_MAX_DECIMAL_PLACES = 3;
1082
1172
  var CLOSING_TIME_BUFFER = 1.5;
1083
1173
  var ONE_SECOND = 1000;
@@ -1115,7 +1205,7 @@ angular.module('ngAnimate', ['ng'])
1115
1205
 
1116
1206
  //but it may not need to cancel out the existing timeout
1117
1207
  //if the timestamp is less than the previous one
1118
- var futureTimestamp = Date.now() + (totalTime * 1000);
1208
+ var futureTimestamp = Date.now() + totalTime;
1119
1209
  if(futureTimestamp <= closingTimestamp) {
1120
1210
  return;
1121
1211
  }
@@ -1214,10 +1304,12 @@ angular.module('ngAnimate', ['ng'])
1214
1304
  parentElement.data(NG_ANIMATE_PARENT_KEY, ++parentCounter);
1215
1305
  parentID = parentCounter;
1216
1306
  }
1217
- return parentID + '-' + extractElementNode(element).className;
1307
+ return parentID + '-' + extractElementNode(element).getAttribute('class');
1218
1308
  }
1219
1309
 
1220
- function animateSetup(animationEvent, element, className, calculationDecorator) {
1310
+ function animateSetup(animationEvent, element, className) {
1311
+ var structural = ['ng-enter','ng-leave','ng-move'].indexOf(className) >= 0;
1312
+
1221
1313
  var cacheKey = getCacheKey(element);
1222
1314
  var eventCacheKey = cacheKey + ' ' + className;
1223
1315
  var itemIndex = lookupCache[eventCacheKey] ? ++lookupCache[eventCacheKey].total : 0;
@@ -1235,110 +1327,84 @@ angular.module('ngAnimate', ['ng'])
1235
1327
  applyClasses && element.removeClass(staggerClassName);
1236
1328
  }
1237
1329
 
1238
- /* the animation itself may need to add/remove special CSS classes
1239
- * before calculating the anmation styles */
1240
- calculationDecorator = calculationDecorator ||
1241
- function(fn) { return fn(); };
1242
-
1243
1330
  element.addClass(className);
1244
1331
 
1245
1332
  var formerData = element.data(NG_ANIMATE_CSS_DATA_KEY) || {};
1246
-
1247
- var timings = calculationDecorator(function() {
1248
- return getElementAnimationDetails(element, eventCacheKey);
1249
- });
1250
-
1333
+ var timings = getElementAnimationDetails(element, eventCacheKey);
1251
1334
  var transitionDuration = timings.transitionDuration;
1252
1335
  var animationDuration = timings.animationDuration;
1253
- if(transitionDuration === 0 && animationDuration === 0) {
1336
+
1337
+ if(structural && transitionDuration === 0 && animationDuration === 0) {
1254
1338
  element.removeClass(className);
1255
1339
  return false;
1256
1340
  }
1257
1341
 
1342
+ var blockTransition = structural && transitionDuration > 0;
1343
+ var blockAnimation = animationDuration > 0 &&
1344
+ stagger.animationDelay > 0 &&
1345
+ stagger.animationDuration === 0;
1346
+
1258
1347
  element.data(NG_ANIMATE_CSS_DATA_KEY, {
1348
+ stagger : stagger,
1349
+ cacheKey : eventCacheKey,
1259
1350
  running : formerData.running || 0,
1260
1351
  itemIndex : itemIndex,
1261
- stagger : stagger,
1262
- timings : timings,
1352
+ blockTransition : blockTransition,
1353
+ blockAnimation : blockAnimation,
1263
1354
  closeAnimationFn : noop
1264
1355
  });
1265
1356
 
1266
- //temporarily disable the transition so that the enter styles
1267
- //don't animate twice (this is here to avoid a bug in Chrome/FF).
1268
- var isCurrentlyAnimating = formerData.running > 0 || animationEvent == 'setClass';
1269
- if(transitionDuration > 0) {
1270
- blockTransitions(element, className, isCurrentlyAnimating);
1271
- }
1272
-
1273
- //staggering keyframe animations work by adjusting the `animation-delay` CSS property
1274
- //on the given element, however, the delay value can only calculated after the reflow
1275
- //since by that time $animate knows how many elements are being animated. Therefore,
1276
- //until the reflow occurs the element needs to be blocked (where the keyframe animation
1277
- //is set to `none 0s`). This blocking mechanism should only be set for when a stagger
1278
- //animation is detected and when the element item index is greater than 0.
1279
- if(animationDuration > 0 && stagger.animationDelay > 0 && stagger.animationDuration === 0) {
1280
- blockKeyframeAnimations(element);
1281
- }
1282
-
1283
- return true;
1284
- }
1285
-
1286
- function isStructuralAnimation(className) {
1287
- return className == 'ng-enter' || className == 'ng-move' || className == 'ng-leave';
1288
- }
1357
+ var node = extractElementNode(element);
1289
1358
 
1290
- function blockTransitions(element, className, isAnimating) {
1291
- if(isStructuralAnimation(className) || !isAnimating) {
1292
- extractElementNode(element).style[TRANSITION_PROP + PROPERTY_KEY] = 'none';
1293
- } else {
1294
- element.addClass(NG_ANIMATE_BLOCK_CLASS_NAME);
1359
+ if(blockTransition) {
1360
+ node.style[TRANSITION_PROP + PROPERTY_KEY] = 'none';
1295
1361
  }
1296
- }
1297
1362
 
1298
- function blockKeyframeAnimations(element) {
1299
- extractElementNode(element).style[ANIMATION_PROP] = 'none 0s';
1300
- }
1301
-
1302
- function unblockTransitions(element, className) {
1303
- var prop = TRANSITION_PROP + PROPERTY_KEY;
1304
- var node = extractElementNode(element);
1305
- if(node.style[prop] && node.style[prop].length > 0) {
1306
- node.style[prop] = '';
1363
+ if(blockAnimation) {
1364
+ node.style[ANIMATION_PROP] = 'none 0s';
1307
1365
  }
1308
- element.removeClass(NG_ANIMATE_BLOCK_CLASS_NAME);
1309
- }
1310
1366
 
1311
- function unblockKeyframeAnimations(element) {
1312
- var prop = ANIMATION_PROP;
1313
- var node = extractElementNode(element);
1314
- if(node.style[prop] && node.style[prop].length > 0) {
1315
- node.style[prop] = '';
1316
- }
1367
+ return true;
1317
1368
  }
1318
1369
 
1319
1370
  function animateRun(animationEvent, element, className, activeAnimationComplete) {
1320
1371
  var node = extractElementNode(element);
1321
1372
  var elementData = element.data(NG_ANIMATE_CSS_DATA_KEY);
1322
- if(node.className.indexOf(className) == -1 || !elementData) {
1373
+ if(node.getAttribute('class').indexOf(className) == -1 || !elementData) {
1323
1374
  activeAnimationComplete();
1324
1375
  return;
1325
1376
  }
1326
1377
 
1378
+ if(elementData.blockTransition) {
1379
+ node.style[TRANSITION_PROP + PROPERTY_KEY] = '';
1380
+ }
1381
+
1382
+ if(elementData.blockAnimation) {
1383
+ node.style[ANIMATION_PROP] = '';
1384
+ }
1385
+
1327
1386
  var activeClassName = '';
1328
1387
  forEach(className.split(' '), function(klass, i) {
1329
1388
  activeClassName += (i > 0 ? ' ' : '') + klass + '-active';
1330
1389
  });
1331
1390
 
1332
- var stagger = elementData.stagger;
1333
- var timings = elementData.timings;
1334
- var itemIndex = elementData.itemIndex;
1391
+ element.addClass(activeClassName);
1392
+ var eventCacheKey = elementData.eventCacheKey + ' ' + activeClassName;
1393
+ var timings = getElementAnimationDetails(element, eventCacheKey);
1394
+
1335
1395
  var maxDuration = Math.max(timings.transitionDuration, timings.animationDuration);
1396
+ if(maxDuration === 0) {
1397
+ element.removeClass(activeClassName);
1398
+ animateClose(element, className);
1399
+ activeAnimationComplete();
1400
+ return;
1401
+ }
1402
+
1336
1403
  var maxDelay = Math.max(timings.transitionDelay, timings.animationDelay);
1404
+ var stagger = elementData.stagger;
1405
+ var itemIndex = elementData.itemIndex;
1337
1406
  var maxDelayTime = maxDelay * ONE_SECOND;
1338
1407
 
1339
- var startTime = Date.now();
1340
- var css3AnimationEvents = ANIMATIONEND_EVENT + ' ' + TRANSITIONEND_EVENT;
1341
-
1342
1408
  var style = '', appliedStyles = [];
1343
1409
  if(timings.transitionDuration > 0) {
1344
1410
  var propertyStyle = timings.transitionPropertyStyle;
@@ -1373,8 +1439,10 @@ angular.module('ngAnimate', ['ng'])
1373
1439
  node.setAttribute('style', oldStyle + ' ' + style);
1374
1440
  }
1375
1441
 
1442
+ var startTime = Date.now();
1443
+ var css3AnimationEvents = ANIMATIONEND_EVENT + ' ' + TRANSITIONEND_EVENT;
1444
+
1376
1445
  element.on(css3AnimationEvents, onAnimationProgress);
1377
- element.addClass(activeClassName);
1378
1446
  elementData.closeAnimationFn = function() {
1379
1447
  onEnd();
1380
1448
  activeAnimationComplete();
@@ -1466,8 +1534,6 @@ angular.module('ngAnimate', ['ng'])
1466
1534
  //happen in the first place
1467
1535
  var cancel = preReflowCancellation;
1468
1536
  afterReflow(element, function() {
1469
- unblockTransitions(element, className);
1470
- unblockKeyframeAnimations(element);
1471
1537
  //once the reflow is complete then we point cancel to
1472
1538
  //the new cancellation function which will remove all of the
1473
1539
  //animation properties from the active animation
@@ -1508,49 +1574,27 @@ angular.module('ngAnimate', ['ng'])
1508
1574
  beforeSetClass : function(element, add, remove, animationCompleted) {
1509
1575
  var className = suffixClasses(remove, '-remove') + ' ' +
1510
1576
  suffixClasses(add, '-add');
1511
- var cancellationMethod = animateBefore('setClass', element, className, function(fn) {
1512
- /* when classes are removed from an element then the transition style
1513
- * that is applied is the transition defined on the element without the
1514
- * CSS class being there. This is how CSS3 functions outside of ngAnimate.
1515
- * http://plnkr.co/edit/j8OzgTNxHTb4n3zLyjGW?p=preview */
1516
- var klass = element.attr('class');
1517
- element.removeClass(remove);
1518
- element.addClass(add);
1519
- var timings = fn();
1520
- element.attr('class', klass);
1521
- return timings;
1522
- });
1523
-
1577
+ var cancellationMethod = animateBefore('setClass', element, className);
1524
1578
  if(cancellationMethod) {
1525
- afterReflow(element, function() {
1526
- unblockTransitions(element, className);
1527
- unblockKeyframeAnimations(element);
1528
- animationCompleted();
1529
- });
1579
+ afterReflow(element, animationCompleted);
1530
1580
  return cancellationMethod;
1531
1581
  }
1532
1582
  animationCompleted();
1533
1583
  },
1534
1584
 
1535
1585
  beforeAddClass : function(element, className, animationCompleted) {
1536
- var cancellationMethod = animateBefore('addClass', element, suffixClasses(className, '-add'), function(fn) {
1537
-
1538
- /* when a CSS class is added to an element then the transition style that
1539
- * is applied is the transition defined on the element when the CSS class
1540
- * is added at the time of the animation. This is how CSS3 functions
1541
- * outside of ngAnimate. */
1542
- element.addClass(className);
1543
- var timings = fn();
1544
- element.removeClass(className);
1545
- return timings;
1546
- });
1586
+ var cancellationMethod = animateBefore('addClass', element, suffixClasses(className, '-add'));
1587
+ if(cancellationMethod) {
1588
+ afterReflow(element, animationCompleted);
1589
+ return cancellationMethod;
1590
+ }
1591
+ animationCompleted();
1592
+ },
1547
1593
 
1594
+ beforeRemoveClass : function(element, className, animationCompleted) {
1595
+ var cancellationMethod = animateBefore('removeClass', element, suffixClasses(className, '-remove'));
1548
1596
  if(cancellationMethod) {
1549
- afterReflow(element, function() {
1550
- unblockTransitions(element, className);
1551
- unblockKeyframeAnimations(element);
1552
- animationCompleted();
1553
- });
1597
+ afterReflow(element, animationCompleted);
1554
1598
  return cancellationMethod;
1555
1599
  }
1556
1600
  animationCompleted();
@@ -1567,30 +1611,6 @@ angular.module('ngAnimate', ['ng'])
1567
1611
  return animateAfter('addClass', element, suffixClasses(className, '-add'), animationCompleted);
1568
1612
  },
1569
1613
 
1570
- beforeRemoveClass : function(element, className, animationCompleted) {
1571
- var cancellationMethod = animateBefore('removeClass', element, suffixClasses(className, '-remove'), function(fn) {
1572
- /* when classes are removed from an element then the transition style
1573
- * that is applied is the transition defined on the element without the
1574
- * CSS class being there. This is how CSS3 functions outside of ngAnimate.
1575
- * http://plnkr.co/edit/j8OzgTNxHTb4n3zLyjGW?p=preview */
1576
- var klass = element.attr('class');
1577
- element.removeClass(className);
1578
- var timings = fn();
1579
- element.attr('class', klass);
1580
- return timings;
1581
- });
1582
-
1583
- if(cancellationMethod) {
1584
- afterReflow(element, function() {
1585
- unblockTransitions(element, className);
1586
- unblockKeyframeAnimations(element);
1587
- animationCompleted();
1588
- });
1589
- return cancellationMethod;
1590
- }
1591
- animationCompleted();
1592
- },
1593
-
1594
1614
  removeClass : function(element, className, animationCompleted) {
1595
1615
  return animateAfter('removeClass', element, suffixClasses(className, '-remove'), animationCompleted);
1596
1616
  }