Blog

Mobile development with HTML5

By | August 25th, 2011 at 3:08PM

HTML5: the standard, the buzzword and the legend

If you read blogs that are even slightly related to tech, you likely hear about HTML5 on a near-weekly basis. Although the new web standard does not do your laundry, it has features that enable the creation of powerful applications—using only HTML, CSS and JavaScript (a Rails back-end can bring additional firepower to the table). This post will go over some key concepts and features of HTML5, setting the stage for more advanced subjects.

Browser Compatibility

Perhaps the biggest pain in developing a web-based application is ensuring that your application is compatible with the various browsers in use today. Fortunately, this is less of a problem in the mobile world. Because people get new phones more often than new computers and because the smart phone space is relatively young, there are simply fewer old smart phones out in the wild. However, this is not a carte blanche; you should test your site with any devices you wish to support, not just simulators.

Viewport

When you visit a website not designed for mobile browsers, it first appears very zoomed out. This is done intentionally by the mobile browsers to make the website viewable. They set the default viewport width to between 800 and 980 pixels (depending on the browser). This allows the user to view the whole website and then zoom in as needed. However, if you are crafting a website specifically for mobile, it make sense to set the initial viewport for the mobile device. This is accomplished with the viewport meta tag.

<meta name="viewport" content = "width=device-width”>

This sizes the viewport to the device’s width, so the content does not initally appear zoomed out. You will likely want to disable zooming entirely, so the user doesn’t accidentally zoom out and distort the UI. Do this by setting user-scalable to no.

<meta name="viewport" content = "width=device-width ,  user-scalable=no">

Some sites currently hard-code the width of the viewport to 320. Why? Because this is the width of the iPhone. However, in general, it is a better practice to use “device-width” instead of 320.

Having your site correctly sized for mobile is nice but the next two features of HTML5, caching with the cache manifest and local storage, allow for fully functional offline sites.

HTML5 Caching

HTML5 caching allows users to view websites they have visited before without a connection to the web. Not only is this extremely useful for users who may not get coverage where they want to use the application, but it can also mitigate brief drops in a connection.

To setup HTML5 caching, you add a manifest file to the html tag of every page you want to cache.

<html manifest="/cache.manifest">

This file starts with “CACHE MANIFEST” and then enumerates the files that the application should cache.

CACHE MANIFEST
/mystyle.css
/scripts.js
/logo.jpg

Now those files will be available offline. Frankly, there is a long list of gotchas with the cache manifest. I review some key ones below but suggest reading Dive into HTML5 for all the details.

The first and foremost, your site will default to cached files over recently downloaded ones, meaning that even if the cache has changed since the browser has last visited the page, the browser displays the old pages until the page is refreshed (or told with JavaScript to update). This is further compounded by the fact that most web servers tell the browser cache the files they serve. When you are developing your site, be sure to tell your web server not to cache the cache manifest, so you always download the most recent copy.

The next big gotcha is how the browser manages the downloading process. If the browser detects that the manifest has changed, it re-downloads every single file. Not only does this make the process expensive, if a single file fails to download correctly, the browser abandons the update and loads the previous cache. When this happens the browser does not post any error by default. However, you can use JavaScript to detect the error thrown by the manifest.

$(function() {
  $(window.applicationCache).bind("error", function() {
    alert("Cache: update failed");
  });
});

So now your site is cached and everything worked. You’re ready to launch? Not really. This caching technique works well with static content. However, if your application has content that is dynamically created and frequently changed (most web apps), it will not work well. This is because, unless the cache is changed, the old html page will be displayed, not the page with your new content. The simple answer is to change the cache manifest file whenever new content is added. However, this is generally not a good idea because it forces the browser to re-download every file every time any content is changed—very costly if your content is updated frequently. The solution is to use jQuery templates to build the page dynamically.

jQuery Templates

The best practice is to populate your content through JavaScript templates. In this way, the content is not part of the HTML page and thus is not cached with the cache manifest. For this, you need to download and add jQuery and the jQuery template plugin to your application.

There are three steps to using these templates:

  1. Define the template.
  2. Define the collection.
  3. Tell jQuery to populate to the page with the template.

Below is an example for a simple blog application.

1. Define the template:

<script id="post_template" type="text/html”>
<div>
 
<h2>${Name}</h2>
 
<p>${Body}</p>
 
</div>
 
</script>

2. Define the collection (of posts in JSON).

<script>
var posts = [
{ Name: "First!", Body: "This is pretty cool" },
{ Name: "Another post", Body: "This is pretty cool" },
{ Name: "Yet another blog post", Body: "This is pretty cool" }];
</script>

3. Tell jQueryto populate to the page with the template.

<script>
$( "#post_template" ).tmpl( posts ).appendTo( "#blog_posts" );
</script>
 
…
 
<body>
 
<div id="blog_posts"></div>
 
</body>

Although this content is loaded via JavaScript, it is not dynamic—it is just defined on the page. For dynamic content we will want to use JSON provided by the server. Let’s assume our blog application provides us with the JSON representation of our blog at this URL:

/posts.json

We will tell jQueryto make a request for the JSON and then use it to populate the page.

<script type="text/javascript">
$.getJSON('/posts.json', function(data) {
$( "#post_template" ).tmpl( data ).appendTo( "#blog_posts" );
});
</script>

We also need to change the template so that it can handle the JSON elements, substituting post.name for Name and post.body for Post:

<script id="post_template" type="text/html">
<div>
  <h2>${post.name}</h2>
  <p>${post.body}</p>
</div>
</script>

Now our blog is pulling content that is not cached in the cache manifest and using jQuery templates to populate the page. However, this works only if our mobile browser can connect to our server. This feels like two steps forward and three steps back, but trust me, we almost have a working mobile HTML5 app. We just need to include one last component of HTML5, Local Storage.

Local Storage

Christopher Haupt of Webvanta recently authored a guest blog post about Local Storage. See the Enhancing Client-side Storage with HTML5 post for details and general use.

On a high level, Local Storage is a client-side key-value store implemented by the browser. It stores strings of text locally and then recalls them later. Here, we use it to store JSON so we can populate the blog with posts even if there is no connection to the server.

Although we could write this by hand, there is a great plugin to manage the process for us. The jQuery Offline plugin uses content from Local Storage if the server is not available and will store fresh content in local storage when it’s received.

Download this plugin from jQuery-Offline

To use the plugin we change the getJSON call to retrieveJSON. We will also need to change our script slightly as there is one key difference between getJSON and retrieveJSON. The latter will execute twice, once to pull from the cache and again to get the new content from the server. This will cause the posts to appear twice if we simply append the new posts to the page.

<script type="text/javascript">
$.retrieveJSON('/posts.json', function(data) {
$( "#blog_posts" ).html($( "#post_template" ).tmpl( data ));
 
});
</script>

The blog application can now be viewed offline and is correctly sized for a mobile browser! You can download this example here offline-blog.

I hope you enjoyed this initial look at some of the technologies that are making mobile development easier. In the coming weeks I hope to be covering more advanced topics such as the popular MVC framework Backbone.js.

  • http://goodscreens.com/2011/08/html5-mobile-review/ HTML5 mobile review « GoodScreens

    [...] Read more at EngineYard. [...]

  • Allan Haggett

    “The best practice is to populate your content through JavaScript templates. In this way, the content is not part of the HTML page [...]“
    Really? This strikes me as … wrong :-)

    HTML/CSS/JS = Content/Presentation/Behavior ?

    Isn’t using a javascript template mixing content and behavior? Are we not supposed to care if the page renders if JS is disabled anymore?

  • http://pulse.yahoo.com/_AOS6PPFFIWS7GQIP4TBYQR5BCQ Bill Posters

    Turning JS off in your mobile browser is like turning Objective C off in your iOS apps. That said, it doesn’t seem very efficient to be using JS templates. Seems like a hack in the absence of a more elegant solution. That goes for general web pages too, but maybe I’m just old, and the new ways are all about writing JS to do everything. It’s quite sad that not even a plain text link can exist on a page anymore without it being programmed to appear there via convoluted JS template function jquery plugin systems.

  • 信任 潘

    Hi here:
    I try to cache the audio / video using manifest
    in Chrome works fine
    but in Safari, can’t play audio / video
    any solution?
    sorry my bad English

  • Michael

    Please do not advocate turning off scaling. As a user with poor eyesight I can not tell you how frustrating it is to be unable to read the content that a 20/20 sighted person crammed onto a page because they could read it, and then disabled zoom so I could not.

  • Allan Haggett

    To be clear: I understand why JS templates could be an elegant solution for some web *applications,* but a blog?

  • http://twitter.com/agentgt Adam Gent

    Actually using JS templates in my mind is more efficient (in terms of bandwidth) than normal server side templating and or HIJAX because the templates can be cached and downloaded in a single request.

    There is a difference between creating a mobile site and a mobile app (although the line is blurring). For a mobile app it makes sense for JS to do everything after all Objective C is doing all the drawing on a native app.

  • http://www.vexeddigital.com/2011/08/26/mobile-development-with-html5/ Mobile development with HTML5 « V E X E D

    [...] Mobile Development With HTML5 [...]

  • http://twitter.com/Tosswill Chris Tosswill

    Hi Allan,

    The offline blog app I built for this post is a toy application to demonstrate the various concepts. Moreover, I am inclined to agree with Bill, disabling JS on a mobile browser will drastically impact your user experience on any mobile app, and therefore imo is an uncommon practice. 

  • http://twitter.com/Tosswill Chris Tosswill

    Hi Michael,

    Although I am in favor of disabling user scaling because I feel it impacts usability, it comes with two caveats. 

    First, I would suggest having an accessibility option which would provide a high-contrast, larger font version of the mobile content. 

    Secondly, I feel some developers do not think about how small the screen size on most most mobile devices really is, which is why I advocate testing on an actual device early and often. That way you dont end up with “A bunch of content crammed into the page.” I have 20/15 vision and still find that some mobile sites are all but unreadable. 

  • http://www.on9systems.com/2011/08/27/links-for-2011-08-26/ links for 2011-08-26 | Michael Ong | On9 Systems

    [...] Mobile development with HTML5 | Engine Yard Ruby on Rails Blog (tags: html5 mobile development) [...]

  • Allan Haggett

    Well, I certainly disagree with the sentiment, and I definitely disagree with this method being called a best practice, but whatever :) You do it your way, I’ll do it mine.

  • Allan Haggett

    I think conflating ObjC on the native side and JS is wrong.

    I’m not going to try to pretend to be an expert on this topic, but this concept just goes against everything I’ve been taught as a web developer for best practices, standards, and accessibility.

    No biggie. As I said above: you do it your way, I’ll do it mine :)

    I forgot to say thanks for the article, Chris!! Despite my disagreement on the one area, it’s a good read and I learned something out of it, so bravo!

    :)

  • http://www.wickedsoftware.net Michael Herndon

    “Best Practices” is such a dirty abused term. Its more like “rules of thumb that are constantly behind the times and do not replace sound reasoning logic”.  

    “Best Practices”, standards, and accessibility rules do change over time due to enhancements. Technology is always pushing the envelope. The “I’ll do it my way” mentality  (while it solves a disagreement to some level) will not benefit anyone in the long run. The best thing to do is constantly be open to change and back it up or debunk it with cold hard facts. 

    The speed of JavaScript has increased significantly for all browsers over time and mobile browsers are not the 10 year old pieces of junk that you find on some operating systems. 

    Newer accessibility standards like “http://www.w3.org/WAI/intro/aria” wai-aria are taking into account JavaScript and the concept of HTML5 as an application language. 

    The newer accessibility standards are trying to be more inline with applications that are being created using these technologies with the assumption that JavaScript is a critical piece of any web application and  that it be enabled almost 100% of the time. 

     

  • Allan Haggett

    I hardly think my comment here qualifies me as not being open to change.

    I get what you’re saying; I do. Perhaps saying this approach is “wrong” was the wrong approach. I saw something in your article that I felt was worth noting. Using a JS template to populate content is a significantly different approach to standard web development (especially for a blog). It’s not like that’s a controversial view.

    Should I just not have said anything about it?

  • http://www.wickedsoftware.net Michael Herndon

    By all means, you should be able to have an opinion and disagree about anything. 

    I’m just saying don’t make those decisions or opinions based on best practices or standards.  If it doesn’t fit your style of programming or you can debunk it with logic go for it. 

    Most of the standards are outdated by the time they become popular and generally have huge flaws and gaps. 

    for example, Html 5′s datetime input. The standard doesn’t specify that browser implements a calendar drop down that is style-able  much less the css rules that you can apply to it. 

    And why isn’t there a standard for styling scrollbars when you allow an element to overflow? html 5 is all about web application, scrollbars are generally apart of those applications. 

    :: shrugs ::

     

  • Defaulter Sandy

    Thanks for the post “Mobile Development with html” . really its very useful for me to keep in mind and use it in future. really thanks a lot.For more information about Mobile Apps Development kindly visit our website.

  • http://ihaveissu.es Christian Biggins

    Great post, thanks! 

  • http://varemenos.com/ Varemenos

    Awesome thanks for this great article!

  • http://twitter.com/fordie Mark Ford

    Sorry Chris, but I agree with Michael. Deliberately disabling the users ability to zoom is a massive no no as far as I’m concerned.
    My wife is registered blind, using the zoom functionality on the iPhone & iPad is the only way she can read the content on a lot of sites. I can’t tell you how frustrated she gets when she’s unable to zoom in. 

    Breaking an accessibility feature because “it impacts usability” makes no sense at all.

    High-contrast versions of sites tend to be pretty ugly & don’t give users the experience that they’d like. And besides, why would you go to the extra trouble of creating a high-contrast when you can ensure your site is readable (for free) by not breaking it in the first place? 

  • Raymond

    Hi Allan,

    If you use any sort of content management system this approach is the best.  It should then read:
    CONTENT (CMS/XML) / HTML (presentation template) / CSS (presentation styles) / JS (behavior).

    Your interpretation is totally true for static content!

    Regards,
    Raymond

  • Alexander Korsak

    Thanks, good article!

    Now I am working on my project where I am using backbonejs(+ custom sync module for saving to localstorage or database using persistencejs) + rack-offline for mobile devices that have no enough internet response time.

  • http://dan.cx/ Daniel15

    “using only HTML, CSS and JavaScript (a Rails back-end can bring additional firepower to the table)”
    What does Rails have to do with *anything*? ANY backend can bring “additional firepower”, and indeed, you’ll obviously need a backend if you want to do anything server-side. I don’t understand why it’s even necessary to mention Rails there (apart from being in a group of people that use and advocate Rails for EVERYTHING)

    Apart from that, great article!

  • http://dan.cx/ Daniel15

    I agree – How is having content populated through JavaScript a “best practice”?

  • Anonymous

    Whenever I see “user-scalable=no”, all I actually see is “Why? Fuck you, that’s why”. Please don’t do that. Don’t be that guy.

  • Anonymous

    On your mobile browser JS is like in your application turned IOS target C. That is, it does not seem very effective to use JS template. Looks like a more elegant solution to the case, the hacker. To the general page, but maybe I’m just old, to write JS to do everything all the new ways.

  • http://www.bedynamiconline.com/mobile-marketing/mobile-app-development/ Be Dynamic Online – Mobile App Development

    [...] Mobile Developers Choose? – ZDNet (blog)Nokia Developer conference 2011Blue Genie TechnologiesMobile development with HTML5 #dwp-contact-button { position: fixed; top:110px; left: 0; width: 43px; outline: none; } [...]

  • Mobile App Developer

     An Awesome Discussion……Keep Sharing…thanks

  • http://blog.patricktresp.de/2011/11/javascript-jquery-webdevelopment-stuff-linklist/ JavaScript (+JQuery) + WebDevelopment Stuff LinkList | Actionscript Programmierer . Patrick Tresp

    [...] - Mobile development with HTML5 http://www.engineyard.com/blog/2011/mobile-development-with-html5/ [...]

  • http://kiranatama.com/ Aguswgs @ RoR Developer

    Thank you for sharing to us.there are many person searching about
    that now they will find enough resources by your post.I would like to
    join your blog anyway so please continue sharing with us

  • http://profiles.google.com/dana.tassler dana tassler

    Great article, Chris! Some friends and I are working on crafting a smallish HTML5 web application and I’ll be re-reading this several times.

    As an aside, you have a busted link. http://diveintohtml5.org/offline should be http://diveintohtml5.info/offline.html. They could have changed the site name, can’t recall.

  • http://www.uninov.com/ RK

    Great Post! HTML5 has provided new wings to mobile & web applications. I like developing html5 mobile apps using sencha touch.