When it comes to creating animations, there are two ways you can choose to perform the task – with CSS or JavaScript. Which one you’ll select depends on your project requirements and the type of effects you want in your design. However, the web development community believes that CSS animation is more difficult compared to the JavaScript animation. Even though, there are some limitations to animating in CSS, it can prove to be more performant than we know.
Working with CSS Animations in JS
Wondering how?
Coupling CSS animations and transitions with a touch of JavaScript, can help us accomplish accelerated animations and interactions in the most efficient manner possible in comparison to most of the JavaScript libraries. This post will help explore how you can manipulate CSS animations and transitions using JavaScript. But before initiating our discussion, let’s have a look at a quick note:
Animations and Transitions are Different
In CSS, there are two key techniques named animation and transition that visualize changes. But both these techniques are different. CSS transitions when applied to an element works when a CSS property changes gradually over a period of time. In contrast, animations when applied to an element just start playing and do their thing without the need of specifying a CSS property explicitly.
Manipulating CSS Transitions by Coupling With JavaScript
You’ll probably find plenty of questions being asked about the element’s transition effects such as triggering and pausing. You can achieve those transition effects with ease using JavaScript. We will be discussing about two amazing tricks to manipulate CSS transitions using JS.
Trick 1 – In order to trigger an element’s transition, all you need to do is toggle a class name on that element. Remember that the class name should be the one that triggers the transition of the element. Next, in order to pause an element’s transition use Window.getComputedStyle()
and getPropertyValue
methods – at the point in the transition that pauses it.
Let us now look at an example that will help pause the box transition:
var box1 = document.getElementsByClassName('box')[0], $box2 = $('.box:eq(1)'); document.getElementsByClassName('toggleButton')[0].onclick = function() { if(this.innerHTML === 'Play') { this.innerHTML = 'Pause'; box1.classList.add('horizTranslate'); } else { this.innerHTML = 'Play'; var computedStyle = window.getComputedStyle(box1), marginLeft = computedStyle.getPropertyValue('margin-left'); box1.style.marginLeft = marginLeft; box1.classList.remove('horizTranslate'); } } $('.toggleButton:eq(1)').on('click', function() { if($(this).html() === 'Play') { $(this).html('Pause'); $box2.addClass('horizTranslate'); } else { $(this).html('Play'); var computedStyle = $box2.css('margin-left'); $box2.removeClass('horizTranslate'); $box2.css('margin-left', computedStyle); } });
Trick 2 – Using CSS “Callback Functions”
Another worthy but lesser-known JavaScript trick that can help manipulate CSS transitions are the DOM events they fire, such as transitionEnd
for transitions. This event needs to be prefixed by the vendor, by using the method PrefixedEvent
, as shown in the example below:
var box = document.getElementsByClassName('box')[1], pfx = ["webkit", "moz", "MS", "o", ""], hovered = false; function AnimationListener() { if(hovered) { box.classList.remove('animated'); box.style.webkitTransform = 'scale(2)'; box.style.MozTransform = 'scale(2)'; box.style.msTransform = 'scale(2)'; box.style.OTransform = 'scale(2)'; box.style.transform = 'scale(2)'; } } function TransitionListener() { if(!hovered) { heart.classList.add('animated'); } } function PrefixedEvent(element, type, callback) { for (var p = 0; p < pfx.length; p++) { if (!pfx[p]) type = type.toLowerCase(); element.addEventListener(pfx[p]+type, callback, false); } } PrefixedEvent(heart, "AnimationIteration", AnimationListener); box.onmouseover = function() { hovered = true; } box.onmouseout = function() { setTimeout(function() { hovered = false; }, 500); PrefixedEvent(heart, "TransitionEnd", TransitionListener); box.style.webkitTransform = 'scale(1)'; box.style.MozTransform = 'scale(1)'; box.style.msTransform = 'scale(1)'; box.style.OTransform = 'scale(1)'; box.style.transform = 'scale(1)'; }
Manipulating CSS Animations by Coupling With JavaScript
You can manipulate CSS animations via the DOM events that JavaScript fire, such as animationEnd
animationStart, and animationIteration
. But, what if you wish to tweak the CSS animation midway?
Let’s have an overview of certain tricks to achieve this objective.
Trick 1 – Setting the “animation-play-state” Property
If you want to pause an animation or want to make it run, you can do so using the CSS animation-play-state
property. You can set this property in CSS with the help of JavaScript as follows:
element.style.webkitAnimationPlayState = "paused"; element.style.webkitAnimationPlayState = "running";
Note: When you pause a CSS animation using the animation-play-state property, the element won’t transform in the manner it did when the application is running.
Trick 2 – Acquiring the Current Animation Percentage
In order to get the percentage value of your a CSS @keyframes animation, the most viable method is to approximate the current percentage using a setInterval
function. For example, if your animation is 4 seconds long, then the setInterval
will have to run every 40 milliseconds (4000/100).
var showPercent = window.setInterval(function() { if (currentPercent < 100) { currentPercent += 1; } else { currentPercent = 0; } // Updates a div that displays the current percent result.innerHTML = currentPercent; }, 40);
Unfortunately, this solution isn’t perfect because the counter runs less frequently than the 40 milliseconds time interval.
Trick 3 – How to Acquire Current CSS Property Values of Animation
Sometimes you may feel the urge to change the CSS animation midway. But that’s not easy and is instead a daunting proposition. Let us take an example, of an animation with an element that moves in the circular path that begins at the top center. But, when the button is clicked the path should change the animation’s starting position to the element’s current location. The path in which the element will travel will remain the same, the only change you’ll observe is that the element will “begin” at the current location it was at the time you pressed the button.
The following code shows how you can find an animation’s value in a CSSKeyFrameRules
object through JavaScript:
function findKeyframesRule(rule) { var ss = document.styleSheets; for (var i = 0; i < ss.length; ++i) { for (var j = 0; j < ss[i].cssRules.length; ++j) { if (ss[i].cssRules[j].type == window.CSSRule.WEBKIT_KEYFRAMES_RULE && ss[i].cssRules[j].name == rule) { return ss[i].cssRules[j]; } } } return null; }
Summing Up
Hopefully, reading this post will help you learn about the techniques to manipulate your CSS animations and transitions through JavaScript. And in case you don’t receive the expected results you need with CSS animations, you can think about turning the animation into a transition instead.