jQuery Mobile - Springboard Navigation


This is one of several jQuery Mobile samples. Please refer to the jQuery Mobile and jQuery overview articles for related background information.

The source code for this sample can be found here: https://github.com/gomobile/sample-jqm-springboard-nav or download the Intel® XDK to check out all the HTML5 Samples.

This sample is a multi-page scaffold using tab-based navigation. For other page navigation styles, please see the list- and tab-based navigation samples.

Additionally, this sample demonstrates custom styling techniques to adapt to various screen sizes and rotations, and achieve a different look and feel than jQuery Mobile defaults.

Springboard-Based Navigation

The main landing page presents a grid of custom icons representing all possible pages to navigate to. The icons are positioned using jQuery Mobile's layout grids. A div with a class of ui-grid-a(/b/c/d) creates a layout grid based on two ( / three / four / five ) equal-width columns, respectively. Each column is designated by a child div with a class of ui-block-a(/b/c/d/e), ordered alphabetically from left to right, up to the number of columns dictated by the parent ui-grid configuration. The grid wraps around to a new row by repeating the sequence of columns.

<div class="ui-grid-a springboard">
    <div class="ui-block-a"> <!-- (row 1, col 1) Friends --> </div>
    <div class="ui-block-b"> <!-- (row 1, col 2) Videos  --> </div>
    <div class="ui-block-a"> <!-- (row 2, col 1) Photos  --> </div>
    <div class="ui-block-b"> <!-- (row 2, col 2) Blogs   --> </div>

Dynamic Layout

Ideally, the entire springboard should fit in the viewport so that the user can visually scan all the navigation options without having to scroll. This sample uses JavaScript* to dynamically adapt the size of the icons to fit the current viewport dimensions, which would be determined by the device and its orientation.

The baseline CSS styling for each icon specifies its max-width to be 100%, which effectively sizes the icon up to its native width without overflowing its containing ui-block.

.springboard img {
    max-width: 100%;

The JavaScript code dynamically determines whether the springboard overflows the viewport, as laid out using the baseline CSS styling. The position of the springboard is determined using jQuery's offset method to obtain the position of the bottom-left element in the springboard (the "Photos" caption). Since offset provides the top, but not bottom, coordinate relative to the document, we add the height of the element to our calculations. The visual viewport's height is determined using window.innerHeight. If the baseline springboard overflows the viewport, an appropriate maximum icon height is calculated. Otherwise, the icons can continue to take up the entire grid cell up to their native size.

/* determine bottom coordinate of springboard */
var bottom = bottomLeftElem.offset().top + bottomLeftElem.height();
/* determine if springboard exceeds viewport */
var overflow = bottom - (VIEWPORT_HEIGHT - padding);
/* shrink springboard icons to fit, if necessary */
if (overflow > 0) {
    /* calculate height adjustment for both rows of icons */
    maxHeight = (iconHeight - overflow / 2) + 'px';
} else {
    /* allow icons to take up entire grid (<= native icon size) */
    maxHeight = '100%';

This overflow calculation happens once for each device orientation: upon the initial loading of the app, and upon the first device rotation (if ever). The first calculation waits for the $(window).load event, rather than $(document).ready, to wait for all images to finish loading, as to obtain accurate coordinates of the springboard. The second calculation uses the window.orientationchange event to detect device rotation, and attaches to that event using jQuery's one method so that it is executed at most once. Note that if the device is rotated while the sample is not displaying the main springboard page, this second calculation is delayed until the main page is displayed in the rotated orientation, as to obtain the springboard's actual coordinates in this orientation. Also note that there is generally a lag on Android devices between the window.orientationchange event firing and the window.innerHeight measurement updating. Instead of polling for the updated window.innerHeight value, this sample uses the simple heuristic of using the initial viewport width minus 25px (a measurement that will account for most mobile status bars) as an estimate for the rotated viewport height.

/* calculate upon initial loading of the app */
$(window).load( /* calculate icon's maxHeight */ );
/* calculate upon first device rotation */
$(window).one('orientationchange', /* calculate icon's maxHeight2 */ );

The appropriate maximum icon height is then dynamically applied upon each calculation and subsequent device rotation.

/* apply appropriate icon size depending on current orientation */
if (!rotated) {
    $('.springboard img').css('max-height', maxHeight);
} else {
    $('.springboard img').css('max-height', maxHeight2);

Custom Theme

Default ThemesCustom Theme

jQuery Mobile provides five default themes, named a-e, each with different mix-and-match color swatches. By default, theme a is applied to headers and footers, and theme c is applied to the page content. Alternate themes can be applied by adding the data-theme attribute to the page or individualwidgets. This sample applies a custom theme created using the ThemeRoller tool. Beyond customizing the color swatches, this sample takes advantage of CSS3's web fonts feature to customize fonts as well. This involves defining the custom font using the CSS font-face at-rule, then configuring the ThemeRoller tool to use the custom font-family by default (with the trailing fonts as fallback options). The custom theme for this sample is exported from the ThemeRoller tool as vendor/jquery.mobile/jquery.mobile-1.1.1-custom.css, which augments but does not replace the default jQuery Mobile CSS stylesheet, and can be reimported back into the ThemeRoller tool to be further customized.

/* define custom HTML5 web font */
@font-face {
    font-family: "CoveredByYourGrace";
    src: url("../fonts/CoveredByYourGrace.ttf");
/* ThemeRoller font configuration */
CoveredByYourGrace, Helvetica, Arial, sans-serif

Custom Header Toolbar Button

While jQuery Mobile provides the ability to incorporate a default or custom icon into a button, this sample uses a custom image itself as the effective button. To achieve this customized header styling for all secondary pages, this sample wraps all links in the header inside a div, as to prevent the jQuery Mobile framework from automatically transforming the links into toolbar buttons. The back navigation behavior for this custom toolbar button is achieved by setting the data-rel="back" attribute on the anchor.

<!-- custom header for secondary page -->
<div data-role="header" data-id="springboardnav-header" data-position="fixed">
    <!-- wrap link inside div to prevent jqm from auto converting to button -->
    <div class="springboard-backbtn">
        <a href="#" data-rel="back">
            <img src="images/backbtn/arrow.png"></img>

Porting to Windows 8 Store App

This sample is ported to Windows 8* Store as well. Please see this article Porting HTML5 Samples to Windows 8* Storefor detail information.

Devices Tested:

  • Samsung Galaxy S* II smartphone (Google Android* 2.3.5, 480 x 800 pixels, hdpi)
  • Lava Xolo X900* smartphone (Android 2.3.7, 600 x 1024 pixels, hdpi)
  • Motorola Droid* Razr M smartphone (Android 4.0.4, 540 x 960 pixels, hdpi)
  • Asus Google Nexus* 7 (Android 4.1.1; display: 7 inches, 1280 x 800 pixels, tvdpi)
  • Amazon Kindle Fire* 2 (v.10.1.3 based on Android 4.0; display: 7 inches, 1024 x 600 pixels, mdpi)
  • Apple iPod Touch* 4th gen mobile device (Apple iOS* 4.3.1, 640 x 960 pixels, retina) !
  • Apple iPod Touch 4th gen mobile device (iOS 6.0, 640 x 960 pixels, retina)
  • Apple iPad* 2 tablet (iOS 5.1.1, 1024 x 768 pixels, non-retina)
  • Windows 8* Sumsung* Tablet

!window.orientationchange event unsupported

Download project assets on github

Download Now

For more complete information about compiler optimizations, see our Optimization Notice.