New and Improved JavaScript Clock

Posted on January 4, 2009 in Function by

Earlier this year, I posted an article explaining how to implement an unobtrusive JavaScript dynamic clock. While not completely earth-shattering or cutting-edge or anything like that, the dynamic JavaScript clock has received some great feedback from users who found the script to be exactly what they were looking for. In fact, a couple of weeks ago, Bill Brown went above and beyond by taking the time to improve the script with some great new features, including a “blinking seconds separator (for kicks)” and removal of “the need for the noscript tag.” Here is the complete script sent by Bill in a recent email (with slightly reformatted markup). To try it out, simply copy and paste the following code into a blank PHP document (no editing required!):

Click here to see a working example of the script

Click here to see the text version of this code

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01//EN" "http://www.w3.org/TR/html4/strict.dtd">
<html>
	<head>
		<meta http-equiv="content-type" content="text/html; charset=UTF-8">
		<title>Unobtrusive JavaScript Dynamic Clock</title>
		<script type="text/javascript">

			(function() { document.getElementsByTagName('html')[0].className='scripted' })();

		</script>
		<style type="text/css">

			#datetime {
				font-family: "Courier New", monospace;
				letter-spacing: 0.25em;
				border: 3px solid #c00;
				background: #f5f5e5;
				text-align: center;
				font-weight: bold;
				padding: 5px 0;
				}
			.scripted #datetime {
				border: 3px double #ccc;
				background: #f5f5f5;
				text-align: center;
				font-weight: bold;
				padding: 5px 0;
				}

		</style>
		<script type="text/javascript">

			String.prototype.pad = function(l, s, t) {
				return s || (s = " "), (l -= this.length) > 0 ? 
				(s = new Array(Math.ceil(l / s.length) 
				+ 1).join(s)).substr(0, t = !t ? l : t == 1 ? 0 : Math.ceil(l / 2))
				+ this + s.substr(0, l - t) : this;
			};

			// addLoadEvent @ http://simonwillison.net/2004/May/26/addLoadEvent/
			var addLoadEvent = function (func) {
				var oldonload = window.onload;
				if (typeof window.onload != 'function') {
					window.onload = func;
				} else {
					window.onload = function() {
						if (oldonload) {
							oldonload();
						}
						func();
					}
				}
			};

			// Unobtrusive JavaScript Dynamic Clock
			// http://perishablepress.com/press/2008/03/04/unobtrusive-javascript-dynamic-clock/
			var xClock = function () {
				var xC = null, xN = null, xH = null, xI = null,
				    xM = null, xS = null, xT = null, AP = null;

				if (!document.getElementById) return;
				xC = document.getElementById("time");
				if (!xC.nodeName) return;
				xN = new Date();
				xH = xN.getHours().toString().pad(2,'0',0);
				xM = xN.getMinutes().toString().pad(2,'0',0);
				xS = xN.getSeconds().toString().pad(2,'0',0);
				AP = (xH >= 12) ? "PM" : "AM";
				xH = (xH >= 13) ? (xH - 12) : xH;
				sS = (xN.getMilliseconds() >= 500) ? ":" : "&middot;";
				xT = xH + ":" + xM + sS + xS + " " + AP;
				xC.innerHTML = xT;
				xI = !xI ? null : clearTimeout(xI);
				xI = setTimeout(xClock, 500);
			};
			addLoadEvent(xClock);

		</script>
	</head>
	<?php flush();?>
	<body>
		<div id="datetime">
			<span id="date"><?php echo date("l, F j, Y ~ "); ?></span>
			<span id="time"><?php echo date("h:i:s A", time()); ?></span>
		</div>
	</body>
</html>

Related articles

5 Responses

  1. [ Gravatar Icon ] Chiwan says:

    Hi.

    This is cool. So I can I replace the clock that comes with your Apathy theme with this clock?
    If that’s not possible, how do I add the “seconds” as you have on your site?

    Thank you!
    Chiwan

  2. [ Gravatar Icon ] Jeff Starr says:

    Hi Chiwan, I got your email and have sent some information that may help you with this.
    Cheers, Jeff

  3. [ Gravatar Icon ] Shefik says:

    What about appending in the current timezone to the output (such as EST or EDT)?

  4. [ Gravatar Icon ] Shefik says:

    The blinking does not work well on Mac Firefox or Safari.

    Only the seconds have the bottom dot blinking (the top dot for seconds does not blink. The minutes does do not blink at all.

  5. [ Gravatar Icon ] Jeff Starr says:

    @Shefik: Sounds like a browser issue.. I am not sure how much control external JavaScript can provide over such minutia. Perhaps there is a way to resolve the issue with (X)HTML or CSS?

Leave a Reply

Your email address will not be published. Required fields are marked *

*

You may use these HTML tags and attributes: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <code> <em> <i> <strike> <strong>

Please use basic markup. Wrap code with <code> tags!