Tomorrow’s web sites and many mobile applications will be created using HTML5. The promise of write-once, run on any platform is too appealing to ignore (although it feels like déjà vu to many of us!). With the release of Windows Phone Mango, HTML5 applications come to Windows Phone mobile devices as well via the Internet Explorer 9 browser available on the platform. To test out the write-once, run everywhere premise of HTML5, I wrote a simple animation and navigated to it in IE9, Windows Phone web browser, and Google Chrome. I also cut a music loop from Ferry Corsten’s “Punk” tune and, using my Virtual DJ software, determined its Beats Per Minute (BPM) value and adjusted the animation to the beat. I was thinking it would be great to be able load any tune into the animation, automatically determine its BPM and make the animation rock to that beat… perhaps sometime in the future blog post. In this post, I outline the techniques I used to create an animation in HTML5 and to get it to work on the Windows Phone.
I Heart Windows Phone
If you have an HTML5-capable browser, push the Play button below to see/hear the end results of my HTML5 animation efforts.
Basic HTML5
HTML5 standard has been under development for several years (5 years, I think) and it is still not in the completed state. There are many HTML5 elements, however, that all major browsers are supporting today. A brief rundown of some of these elements appears in this section.
First, HTML5 makes web form validation much easier by introducing a set of new fields, such as “e-mail,” “date,” etc. that accepts user input within the range of expected values for those fields. For a good walk-through on what these new fields are and how to work with them, take a look at this thorough coverage from MSDN.
Perhaps the most important feature of HTML5 for mobile developers is the ability to determine user’s geographic location (that is, the lattitude and longitude coordinates of the user). Generally, you would use navigator.geolocation.getCurrentPosition() JavaScript function to get to the location information. An example of an HTML page displaying user’s coordinates is below (you can just copy and paste it into Notepad, save it as “.html” and double-click to open the file inside the browser).
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" >
<head>
<script type='text/javascript'>
navigator.geolocation.getCurrentPosition(onPositionReady);
function onPositionReady(position) {
document.getElementById('message').innerHTML = 'lat ' + position.coords.latitude + ' long ' + position.coords.longitude;
}
</script>
<title>Geolocation Example</title>
</head>
<body>
<div id='message'>
geolocation data will be shown here
</div>
<p></body>
</html>
When you open this HTML page in an HTML5-compliant browser (IE9, latest versions of Chrome or Firefox), you should see a prompt asking you if are Ok sharing your geolocation. If you say that it is, indeed, acceptable, you should see your current lat and long coordinates displayed in the browser.
The introduction of the new <audio> and <video> tags make playing media in a web applications a breeze. For example, the following
<audio id="myaudio" type="audio/mpeg" preload="auto" loop>
Your browser does not support HTML5 audio element.
</audio>
The “Your browser does not support HTML5 audio element” message will be shown to the users who are viewing your application with non-HTML5 compatible browser. The use of <video> element in HTML5 is comparable to the use of <audio> element, and a nice bonus for Windows Phone users is that the videos inside that element will automatically be played using a full-screen mode, together with a set of playback controls (see this post from the Windows Phone team if you would like additional details).
Finally, I used the new HTML5 <canvas> element to add images to the web page and to later animate them. <canvas> element allows you to draw on the web page, just like you would in a graphics editing applications such as Paint.NET or Photoshop. It’s a bit tedious at present, since you have to manually specify the coordinates and angles to draw, but help is on the way: for example, Adobe has a a preview version of Adobe Edge tool that will allow you to create HTML5 drawings and animations visually. I am certain comparable tools from Microsoft are coming. To give you a flavor of the HTML5 <canvas> element, here’s code that draws a simple circle on the web page:
<!DOCTYPE html>
<html>
<head>
<script type='text/javascript'>
window.onload = function () {
var c = document.getElementById("myCanvas");
if (c.getContext) {
var cxt = c.getContext("2d");
cxt.fillStyle = "#FF0000";
cxt.beginPath();
cxt.arc(70, 18, 15, 0, Math.PI * 2, true);
cxt.closePath();
cxt.fill();
}
}
</script>
<title>Canvas Example</title>
</head>
<body>
<canvas id="myCanvas" width="200" height="100" style="border:1px solid #c3c3c3;">
Your browser does not support the canvas element.
</canvas>
</body>
</html>
It’s important to start drawing only after a the page has fully loaded, otherwise the browser may not find the <canvas> element yet. Hence, all the drawing above occurs in the window.onload handler. Take a look at the source for the I Heart Windows Phone animation (downoad link at the bottom) for more examples with the <canvas> element.
Animating with HTML5
Animation in HTML5 is based on JavaScript functions redrawing the screen every predefined number of milliseconds. For instance, in the animation above, I am calculating the rate that the screen should be redrawn at, based on the BPM value of the song (which is 135 for the “Punk” tune that I used). Here’s a snippet of code that gets called when the play button is pushed and that performs the actual animation:
function drawIHeartWP(y1, y2, y3, y4)
{
myCanvas = document.getElementById("myCanvas");
if (myCanvas.getContext) {
ctx = myCanvas.getContext("2d");
ctx.fillStyle = 'rgb(0,0,0)';
ctx.fillRect(0, 0, ctx.canvas.width, ctx.canvas.height);
img = new Image();
img.src = "i.png";
ctx.drawImage(img, 50, 100-y1, imgSize.imgWidth, imgSize.imgHeight);
....
The drawIHeartWP() function gets called every predefined number of milliseconds, the canvas is refreshed using the fillRect method, and then all images are redrawn given the new coordinates passed into the function. The coordinates adjust dynamically to the beat. This loop continues until the pause button is clicked.
Getting the app to run inside the WebBrowser control on Windows Phone
The animation above runs inside the Windows Phone emulator and device “as is,” with no midifications needed, if I host this animation somewhere on the Internet. I wanted to see if I could host this animation on the Windows Phone device itself and invoke it inside the WebBrowser control provided by the framework, given that wireless data transfer rates are still slow and could get expensive (ever tried roaming in Europe with the U.S.-based wireless data plan?). So, I created a Windows Phone application using Visual Studio Express for Windows Phone, added all of the resources to the solution, and it worked! The only thing to remember (and it’s very important!) is that all of the resources, including audio files and images, must be saved to the local storage on the phone before they can be navigated to with the Web Browser control. All of those resource must also have their type set to “Content” and “Copy if newer” property should be set for them. The attached source code shows how it can be done using standard SaveToIsoStorage() functions available from MSDN.
Final thoughts
HTML5 is the future of both web and mobile applications – there’s little doubt in my mind about that. It is still somewhat painful to build HTML5 applications, since the tooling is scarce and browser vendors vary in the progress they are making towards complete HTML5 compliance. However, I believe that the tools for Rapid Application Development with HTML5 will continue improving, and the vendors will come to a consensus on support for most HTML5 features. Then, we could spend time coming up with new ideas on how to change the world instead of writing code for three or four different platforms for each application.