Timeout indicator

Shows a process timeout using a canvas-rendered cue.

by gyoshev

HTML

<div class="play-button">
    <div class="play-icon"></div>
</div>

CSS

body
 {
     background: #333;
     padding: 5em;
     text-align: center;
 }

 .play-button
 {
     padding: 10px;
     display: inline-block;
     position: relative;
 }

 .play-icon
 {
     background: transparent...

JavaScript

window.requestAnimFrame = (function(){
    return  window.requestAnimationFrame       || 
            window.webkitRequestAnimationFrame || 
            window.mozRequestAnimationFrame    || 
            window.oRequestAnimationFrame      || 
            window.msRequestAnimationFrame     || 
            function(/* function */ callback, /* DOMElement */ element){
                window.setTimeout(callback, 1000 / 60);
            };
})();

function TimeoutIndicator(element, options) {
    var that = this,
        canvas = that.canvas = document.createElement("canvas"),
        context = that.context = canvas.getContext("2d"),
        timeout = that.timeout = options.timeout,
        diameter = that.diameter = element.offsetWidth;
        
    that.element = element;
    that._running = false;
    
    canvas.setAttribute("width", diameter);
    canvas.setAttribute("height", diameter);
    canvas.style.cssText = "position: absolute; top: 0; left: 0;";
    
    element.appendChild(canvas);
}

TimeoutIndicator.prototype = {
    start: function() {
        var start = +new Date(),
            that = this,
            timeout = that.timeout,
            canvas = that.canvas;
        
        if (that._running)
            return;
                
        that._running = true;
        
        that.cw = false;
        
        function render() {
            var timeMod = ((+new Date() - start)) / timeout;
            
            if (timeMod > 1) {
                start = +new Date();
                if (!(that.cw = !that.cw)) {
                    timeMod = ((+new Date() - start)) / timeout;
                }
            }
            
            that.draw(timeMod);
        }
        
        (function animloop(){
            render();
            requestAnimFrame(animloop, canvas);
        })();
    },
    draw: function(timeMod) {
        var context = this.context,
            diameter = this.diameter,
            radius = diameter / 2,
            pi =...