Peter O'Shaughnessy

Source code:

Please view in a modern browser.

Pearson Future Tech
  1. Intro (fluid apps)
  2. Canvas
  3. WebGL
  4. CSS
  5. Web Animations API
  6. General Tips

1. Intro (fluid apps)


Boring App

Press the menu button!

Press when you're ready to continue.

Banned symbol
Skueomorphic Passbook app

“Without the restrictions of skeuomorphism, the UI is free to behave in any manner without seeming contradictory to its pre-defined environment”

Make the motion feel fluid

Dots app via

Give it personality

Yelp app via

Make it consistent

Paper app via

Orientate users

Moldiv app via

But don't go overboard and be annoying!

Dancing banana

Native apps are becoming more fluid

What about mobile web apps?

2. Canvas

<canvas id="myCanvas">
    my fallback content

var canvas = document.getElementById('myCanvas');

var ctx = canvas.getContext('2d');

ctx.fillStyle = 'rgb(255, 0, 0)';
ctx.fillRect( 20, 20, 100, 200 );

Knoggins (an app we created in 1 day at a hackathon) (Pixi.js)

3. WebGL

<canvas id="myCanvas">
my fallback content

var canvas = document.getElementById('myCanvas');

var gl = canvas.getContext('webgl') ||

/* Lots of low level code here! Or use a library */

See (desktop)

Without WebGL (Pixi.js)
1000 bunnies @ ~14 FPS

With WebGL (Pixi.js)
1000 bunnies @ ~58 FPS

Mobile support

  • Chrome for Android
  • Firefox for Android
  • Opera Mobile
  • iOS Safari ✓ :-D

4. CSS

.demo {
    transition-property: transform;
    transition-duration: 2s;
.demo:hover {
    transform: rotateX(45deg) scale(1.2);

Hover over the code area. NB. Vendor prefixes omitted for simplicity

React touch demo (menu @ 0:43, gallery @ 2:10)
Live demo at: (Three.js CSS3DRenderer)

5. Web Animations API

Declaring in CSS generally best for performance

@keyframes spin3d {
    0% { transform: rotateY(0deg); }
    100% { transform: rotateY(360deg); }
.you-spin-me-right-round-baby-right-round:hover {
    animation: spin3d 3s ease-in-out infinite;

Hover over the code area. NB. Vendor prefixes omitted for simplicity

But you often need to control through JavaScript = 'translate(' + snowLeft + 'px, -100%)';
// wait a frame
snowFlake.offsetWidth; = 'transform'; = '1500ms'; = 'translate(' + snowLeft + 'px, ' +
        window.innerHeight + 'px)';

Example from

element.animate() gives best of both

    {transform: 'translate(' + snowLeft + 'px, -100%)'},
    {transform: 'translate(' + snowLeft + 'px, ' + window.innerHeight + 'px)'}
], 1500);


var player = snowFlake.animate( ... );
// Changed my mind

var player = snowFlake.animate( ... );
player.onfinish = function(e) {
    console.log('Snowflake landed!');

More info at:

6. General Tips

Tip 1: For 60 FPS, you only have 16ms to prepare each frame

  • It's not very long!

Tip 2: Test, measure, optimise

Tip 3: For now, define animations in CSS if possible

  • Browser can optimise; use GPU, run off main thread
  • Good for simple things you don't need to control frame by frame

Tip 4: Make sure you don't hammer the UI thread

  • Avoid doing work in input handlers such as onscroll
  • Use requestAnimationFrame so the browser calls you when it's ready
  • If you need to do a lot of processing, consider chunking it down or using a Web Worker

Tip 5: Stick to: translate, scale, rotate, opacity

  • The 4 things a browser can "animate cheaply"

Tip 6: Batch DOM operations

  • The DOM is expensive
  • Frameworks like React and Ractive can handle this for you
Virtual DOM

By Joe Fleming

For more info:

“Great animations
make great apps”

So ditch the boring animations.

Boring animation app

And make it fluid.

Make it awesome.

Thank you




Further reading