What is the purpose of Angular animations?
I've been wondering for some time now why should I use Angular animations over CSS animations. I see few areas one might consider before using them:
Performance
In the first step I found this question which deals only with performace side of things. The accepted answer is not satisfying for me because it states that one should use CSS animations wherever possible so that optimizations like running the animations in separate thread can apply. This doesn't seem to be true, because Angular documentation states
Angular animations are built on top of the standard Web Animations API and run natively on browsers that support it.
(emphasis mine)
And when we look at Web Animations API Draft we see that the same optimizations can apply to Web Animations as to CSS specified in sheets.
While it is possible to use ECMAScript to perform animation using requestAnimationFrame [HTML], such animations behave differently to declarative animation in terms of how they are represented in the CSS cascade and the performance optimizations that are possible such as performing the animation on a separate thread. Using the Web Animations programming interface, it is possible to create animations from script that have the same behavior and performance characteristics as declarative animations.
(emphasis mine again)
Apart from some browsers like IE don't support Web Animations, is there any reason to use either CSS declarations over Angular animations or vice versa? I see them as exchangeable performace-wise.
More control over the animations
This might look as an argument for Angular animations, because you can pause animation or use JS variables with it etc., but the same is true while using eg. CSS animation-play-state: pause
or using CSS variables specified in JS, see documentation.
Now I can see it might be inconvenient to set the CSS variables in JS code, but the same is true while using Angular animations. These are typically declared in @Component
animations
field and don't have, except for via the animation state data bound property, access to instance fields (if you don't create your animation via AnimationBuilder
of course, which btw is also not very convenient or beautiful either).
Other point is, with Web Animations API it is possible to inspect, debug or test the animations, but I don't see how this is possible with Angular animations. If it is, could you please show me how? If it isn't, I really don't see any advantage of using Angular animations over CSS ones for the sake of control either.
Cleaner code
I've read for example here a paragraph stating that separating animations from "normal" styles is actually separation of behaviour and presentation. Is really declaring animations in styles sheets mixing those responsibilities? I saw that always the other way, especially looking at CSS rules in the @Component
animations gave me a feeling of having CSS declarations on one too many places.
So how is it with Angular animations?
- Is it just a convenience utility to extract animations away from the rest of the styles, or does it bring anything worthy feature-wise?
- Does a usage of Angular animations pay off only in special cases or is it a convention a team chooses to go all the way with it?
I would love to here about tangible advantages of using Angular animations. Thanks guys upfront!
So I did some research and although I didn't find any argument for nor against Angular animations performance-wise (as already stated in the question above), there are very good arguments to use Angular animations feature-wise which should be good enough for purists who want to have CSS only in sheets, at least in certain cases.
Let me list some useful features where each alone makes a convincing case for Angular animations. Most of them can be found in Angular animations documentation:
-
Transition styles - these styles are only applied during transition from one state to another - only while an element is being animated, and one uses them like this:
transition('stateA => stateB', [style({...}), animate(100)])
Trying to do the same with CSS only might not be as expressive in terms of which previous state led to the next. And it can be outright clunky if the animation has to differ based on the initial state but the end state is the same.
-
The
void
state together with:enter
and:leave
aliases (void documentation, :leave and :enter documentation) - Let you animate elements being added or removed from the DOM.transition('stateA => void', animate(...))
This is very cool because previously, although it was easy enough to animate the addition, the removal was more complicated and required to trigger animation, wait till its end and only after that remove the element from the DOM, all with JS.
-
Automatic property calculation
'*'
(documentation) - Allows for performing traditionally difficult animations like height transitions for elements with dynamic height. This problem required either to set fixed height on element (inflexible), use max-height with tuned transition function (not perfect) or query element's height with JS (potentially causing unnecessary reflows). But now with Angular it is as easy as this:trigger('collapsible', [ state('expanded', style({ height: '*' })), state('collapsed', style({ height: '0' })), transition('expanded <=> collapsed', animate(100)) ])
And the animation is smooth and "complete" because the actual height of the element is used for the transition.
Animation callbacks (documentation) - this is something that wasn't possible with CSS animations (if not maybe emulated with
setTimeout
) and is handy eg. for debugging.Unlike stated in the question, it is actually possible to use instance fields as params in Angular animations, see this question. I find it much easier to use than manipulating CSS variables through DOM API as shown here on MDN, not mentioning the limited support in some browsers.
If you need any of the features listed above, Angular can be a better tool for the task. Also when there is many animations to manage in a component, and this is just my personal opinion, I find it easier to organize animations the Angular way than have them in sheets, where it is harder too see the relationships between them and various element states.