HTML 5 Canvas: An animated Digital Clock

HTML5’s canvas implementation allows you to draw whatever takes you fancy; be it a thermometer, speedometermap, compass or a Caesar cipher.  In this post one intends to draw a digital clock.  This HTML5 canvas implementation draws the hour, minute and second digits individually with the correct number that represents the current time.  These are then redrawn every second as one would expected a real clock would do!
HTML5 Canvas Digital Clock

The HTML Source

The following code is stripped to the minimum in order to draw the dial:
<!DOCTYPE html>
<html lang="en">
	<head>
		<meta charset="utf-8" />
		<title>Flip Clock</title>
		<script src='flip_clock.js'></script>
	</head>
	<body onload='init();'>
		<canvas id="clock" width="1200" height="451"></canvas>
	</body>
</html>
The HTML is straight forward. The items of interest are the canvas element and the ‘onload’ event for the body. For those who are not familiar with HTML let me explain how we draw the clock onto the canvas. When any HTML page loads the browser will run the JavaScript code attached to the onload event of the body tag e.g.
       <body onload='init();'>
In order to understand how the ‘init’ function works we need to understand how the browsers locates it. The browser will load any JavaScript code included in a script tag prior to displaying the page to the user e.g.
	<script src='flip_clock.js'></script>
Therefore, the content of the script “flip_clock.js” will be loaded, and therefore, the function called ‘init’ will be available. If you were to look inside the aforementioned script you will be able to see the code e.g.
function init() {
	// Grab the clock element
	var canvas = document.getElementById('clock'),
		iHHMMGap = 25,
		iSSGap = 0;

	// Canvas supported?
	if (canvas.getContext('2d')) {
		ctx = canvas.getContext('2d');

		// Load the clock face image
		clock_face = new Image();
		clock_face.src = 'flip_clock.png';
		clock_face.onload = imgLoaded;

		xPositions = Array(DIGIT_WIDTH * 0,
							DIGIT_WIDTH * 1,
							(DIGIT_WIDTH * 2) + iHHMMGap,
							(DIGIT_WIDTH * 3) + iHHMMGap)
							
		xSecondStartPos = xPositions[3] + DIGIT_WIDTH + iSSGap;
		
		secondWidth = DIGIT_WIDTH * 0.25;
		secondHeight = DIGIT_HEIGHT * 0.25;
		
	} else {
		alert("Canvas not supported!");
	}
}
The content of the function is coded in logical steps. The first step is to obtain a handle to the canvas element. If the canvas element is found we then proceed to ensure the browser supports the canvas. Assuming support is implemented the second step is to load the image resource. This image contains the digits we’ll use to draw the time. Then function then assigns various values for use within the main draw function. These variables represent the screen position for each of the 4 digits within the time. These are constants as the digital clock’s digits do not move their position; thus, we need only calculate these once and reuse later.

When the image is created it is assigned an onload event. The image that will be loaded contains the following:

When the event fires the function ‘imgLoaded’ will be executed. This function contains the following
function imgLoaded()
{
	// Image loaded event complete.  Start the timer
	setInterval(draw, 1000);
}
The function above is very simple. It simply starts a timer which will be executed every 1000 milliseconds (one second). The timer instructs the browser to run the draw function. This function contains the following source code.
function draw() {
	
	var currentTime = new Date(),
		time = pad2(currentTime.getHours()) + pad2(currentTime.getMinutes()) + pad2(currentTime.getSeconds()),
		iDigit;
	
	clearCanvas();

	// Draw the HHHH digits onto the canvas
	for(iDigit = 0; iDigit < 4; iDigit++) {
		drawHHMMDigit(time, iDigit);
	}
	
	// Draw scalled second digits
	ctx.drawImage(clock_face, time.substr(4, 1) * DIGIT_WIDTH, 0, DIGIT_WIDTH, DIGIT_HEIGHT, xSecondStartPos, 20, secondWidth, secondHeight);
	ctx.drawImage(clock_face, time.substr(5, 1) * DIGIT_WIDTH, 0, DIGIT_WIDTH, DIGIT_HEIGHT, xSecondStartPos + secondWidth, 20, secondWidth, secondHeight);
}
The JavaScript above first clears the canvas. The four digits representing the hour and minute component are then rendered to the canvas. The next step draws the two digits representing the seconds. Each of the six digits are drawn using the canvas function drawImage e.g.
   ctx.drawImage(clock_face, time.substr(unit,1) * DIGIT_WIDTH, 0, DIGIT_WIDTH, DIGIT_HEIGHT, xPositions[unit], 0, DIGIT_WIDTH, DIGIT_HEIGHT);
This function allows you to extract a portion of any given image and then draw the portion onto the canvas in a given position. The position of the digit we want happens to be stored relative to the number we are drawing. Thus, a simple algorithm allows me to pull out the portion of the image from the sprite map that holds the correct digit. This image part is then drawn onto the canvas is the related position e.g. a at the hour, minute or second position.

That concludes this post. A working example of this post can be view here here. Full credit for the base image goes to this site for providing the PSD that inspired me to create the HTML5 clock. The code and my previous HTML canvas projects are now available on Git Hub https://github.com/rheh/HTML5-canvas-projects/tree/master/

3 thoughts on “HTML 5 Canvas: An animated Digital Clock

Leave a comment