An Introduction to CSS3 Animation… with Gary Neville
We’re going to look at the basics of creating keyframe based animation using CSS3, including all of the various properties we can use to control the animation’s behaviour. And to finish, we’ll look at a real life application of CSS animation.
Unnecessary Background Reading
If you’re not a little intrigued as to how Gary Neville has found himself in a CSS blog post title, then feel free to skip this section and read on. What’s that… you’d love to know? Well okay, if you insist…
Football fans will recall his moment of ‘excitement’ when Fernando Torres rounded Victor Valdes and knocked the ball into the net to seal Chelsea’s shock victory against Barcelona in this years Champions League semi final.
Well, Nev’s reaction didn’t go unnoticed by the internet’s millions. In fact, 2 guys from my work (big up Mitch and Sean) dropped me an email the following day asking if I wanted to knock something together to go on the new domain they’d just bought… garynevillegasm.com. And so it began.
The Basics
Okay, so Gary Neville’s only really here to provide a real life example of where CSS3 animation has been used – we need to get to grips with the basics first.
Defining the keyframes
As with most animation, CSS3 animation works on a keyframe basis. This removes the limitations we have with CSS transitions, as they only animate from one state to another; for example from a blue normal state to a red hover state. With keyframe animation we can animate from one state to another to another and so on.
We define when each state change will happen using percentages. Let’s see how this works with an example of a box moving around four corners of a page, changing colours as it travels to each corner.
There are 4 state changes to define, so here’s how we do it …
@keyframes square {
0% {
top:0;
left:0;
background:blue;
}
25% {
top:300px;
left:0;
background:red;
}
50% {
top:300px;
left:600px;
background:green;
}
75% {
top:0;
left:600px;
background:yellow;
}
}
It’s important to note that the exact code above will not work in any browser at the time of writing, as the only current support requires vendor pre-fixes. -moz-
and -webkit-
provide support for Firefox, Chrome and Safari in this case.
In the annotated image below, you can see exactly what each keyframe does.
Applying the Animation to an Element
Now we’ve created a set of keyframes, we need to apply the animation to an element. We do this by simply using the various animation
properties on the element(s) we want to animate, like so…
.box {
/* Your list of animation properties */
}
So what are these animation properties/controls?
animation-name
– The name of your animation. Must correspond with name given in@keyframes
rule; in this case, ‘square’.animation-duration
– How long the animation should last from start to finish. Defined in seconds or milliseconds; e.g.5ms
or0.5s
.animation-timing-function
– Describes the varied acceleration of the animation; it denotes where the animation speeds up and slows down over the specified duration of the transition. E.g.ease
orlinear
. See my previous article for more on the timing-function property.animation-iteration-count
– How many times the animation repeats from start to finish. This can be any numerical value or theinfinite
keyword, which loops the animation forever!animation-direction
– A value ofnormal
(the default value) would play the animation from start to finish. The other value ofalternate
would play the animation forwards then backwards for animations with an iteration count of 2 or more.animation-delay
– Only plays the animation after a set amount of time. For example, a value of5s
would cause the animation to begin 5 seconds after the page has loaded.animation-play-state
– The default value isrunning
which plays the animation normally; the other keyword ispaused
which – well, pauses the animation. If you take another look at my demo, I have set theanimation-play-state
property to paused when the box is hovered.
This seems like a lot of bytes to simply apply an animation to an element, right? Well, thankfully, we can use the shorthand version to vastly reduce it. The only required properties are animation-name
and animation-duration
.
.box {
animation:square 10s infinite;
}
/* To pause the animation when the box is hovered... */
.box:hover {
animation-play-state:paused;
}
An important note – for simplicity, all of my code examples above are un-prefixed, but in order for animations to work at the moment, they must have the appropriate vendor prefixes. For example @-webkit-keyframes
and -webkit-animation
.
Using CSS3 Animation in the real world… on Gary Neville
When it came to making Gary Neville as animated as his voice, there was only one thing for it – CSS3! Not just animation though – the use of other CSS3 capabilities such as transitions and transforms go some way to showing just what can now be achieved with a few lines of CSS.
Nev starts out pretty small when the page first loads (the image of Nev of course… take your dirty mind elsewhere!). Then, when the user inevitably hovers over the image, he springs into life, as we use a transition to animate the image to its full scale.
Don’t forget to click on the image too and make sure you’re volume’s turned up!
img {
transform:scale(0.6);
opacity:0.7;
transition:all 0.6s ease;
}
img:hover {
transform:scale(1);
opacity:1;
}
Remember, with transitions, we can only animate from one state to another; in this case, from the small image to the full size image. But now he’s full size, we need to shake him rigorously from side to side in order to really put across his excitement. A transition isn’t quite powerful enough for this, so now we need to call upon keyframe animation!
In order to shake Nev, we need to move and rotate him slightly from side to side. We can use CSS3 transforms to do the maneuveral work for each keyframe and allow the animation to do the tweening between each frame.
@keyframes nev {
0% { -webkit-transform: translate(5px, 0); }
25% { -webkit-transform: translate(-5px, 0) rotate(-10deg); }
50% { -webkit-transform: translate(5px, 0) rotate(10deg); }
75% { -webkit-transform: translate(-5px, 0) rotate(-10deg); }
100% { -webkit-transform: translate(5px, 0) rotate(10deg); }
}
/* Don't forget vendor prefixes!! */
Now we have our keyframes, we need to apply them to the image’s hover state using our various animation properties.
As described earlier, we used a transition lasting 0.6 seconds to scale the image to its full size on hover, so we don’t really want the animation to begin until the intial transition has finished. Step forward the animation-delay
property. All we have to do is set the value to 0.6s and the animation will not begin until the first transition has finished.
img:hover {
transform:scale(1);
opacity:1;
animation-name:nev;
animation-duration:0.5s;
animation-timing-function:ease;
animation-delay:0.6s;
animation-iteration-count:infinite;
}
With the above, we’ve set our animation to apply to the image on hover after 0.6 seconds with a duration of 0.5 seconds which will loop an infinite number of times. But don’t forget, we don’t need all that code! We can just as easily shorten all of the animation controls to one line of code: animation:nev 0.5s ease 0.6s infinite
.
And with that, Gary Neville becomes almost as animated as the sound he makes when the image is clicked.
Conclusion
I seem to conclude every one of my posts on CSS3 the same way… with a warning.
It’s understandable that people want to play with new toys, but it must be done with caution, for progressive enhancement and not for vital functionality.
Be subtle and use where appropriate.
About Stephen Greig
Stephen Greig is a 25 year old Freelance Web Designer/Front-end guy, currently living in Nottingham, UK. Stephen is also the creator of messivsronaldo.net and author of CSS3 Pushing the Limits, a book on advanced CSS3. You should follow him on Twitter where he talks about the web, sports, music and swears a lot. Stephen's also on Google+ if that's more your bag.