What you'll learn

This codelab will walk you through adding items to a web app that Chrome requires before it will prompt users to add the app to their home screens. Specifically:

This codelab won't show you every detail about how to build these. What we'll focus on is how to make these work together to craft a user experience.

Is this a progressive web app?

Well, yes and no. Everything I'm going to show you is a requirement for a progressive web app. It will make your site more app-like, but it won't actually be a progressive web app.

What you'll need

Next up

Let's set up an existing app. After that we'll enhance it to be added to a home screen.

Get the code

As our starting place, we're going to use Paul Lewis's Fireworks! app. This little app, which shows a black screen when you open it, displays fireworks animations when you touch the screen.

Download Zip

Set up your work area

Extract the contents of the downloaded zip file. It will create a folder called add-to-home-screen/. Open a console window and set up a work folder as follows:

$ cd add-to-home-screen
$ mkdir work
$ cp -r step-02/* work
$ cd work

Install and run the web server

To test our work, we're going to need a web server. In production, we'd need one that supports HTTPS. For development and testing, anything running on localhost will do.

If you need something quick you can install the Chrome Web Server from the Chrome Web Store. You may want to install this anyway, since other codelabs use it.

After installing Chrome Web Server, launch it from the Chrome App Launcher using this icon.

Click Choose Folder and select work/. While you're in the Web Server, also select "Automatically show index.html".

Open a new browser tab and navigate to localhost:8887. Click anywhere in the browser window and watch the pretty fireworks.

Next up

We'll create the web app manifest and add it to index.html.

The first of the items we're going to add to Fireworks! is a web app manifest. A web app manifest is a simple JSON file that gives you the ability to:

In your add-to-home-screen folder, open the file named empty-manifest.json. Save it to work/ with the name manifest.json. It looks like this:

{
  "short_name": "",
  "name": "",
  "icons": [
    {
      "src":"",
      "sizes": "",
      "type": ""
    }
  ],
  "start_url": "",
  "background_color": "",
  "Theme_color": "",
  "display": ""
}

Before we do anything, let's open some files that contain information we need. In your work folder, open:

The application name

Let's start by giving the application a name. In index.html, locate the <title> element and copy its value to name and short_name in manifest.json.

"name": "Fireworks!"

"short_name": "Fireworks!"

The Web App Manifest specification provides only general instructions for using these. The name member is intended for locations where a typical user would see the name, such as on the web app's add to home screen banner and on its splash screen. The short_name member is intended to be used in places without enough room for the full name of the web application. But Chrome uses the short_name when both are present, but will use either if only one is present. Other browsers may behave differently.

For these reasons we have two recommendations: keep both values short and keep them equal.

Colors

As with the application name, colors should also match what's in the web page. The manifest doesn't replace these values. It just makes these values available to the browser before the HTML and CSS files are parsed and rendered. The intent is to visually smooth home screen startup.

There are two color values you need to set:

Set the background_color to match the background property from the body selector in css/fireworks.css.

"background_color": "#000"

The theme_color member sets the toolbar color and should match the value in the theme-color <meta> element.

"theme_color": "#536878"

The Application icon

The specification allows for an array of icons so that the browser can select an appropriate icon for the display size and density. At the time of this writing, Chrome achieves good results with an icon sized 192 by 192 pixels. Note that this will be downsized for lower-resolution displays, and that higher resolution displays, when they become available, will likely upsize it. In a production web app, you'll want to provide an assortment of sizes for different uses. For this codelab, we'll stick to 192 by 192.

In add-to-home-screen/ you'll find an icon named fireworks-icon192x192.png. Copy this file to work/images/. Add its name to the icons array in manifest.json along with its dimensions and file type:

"icons": [
  {
    "src":"images/fireworks-icon192x192.png",
    "sizes": "192x192",
    "type": "image/png"
  }
]

Display mode

Manifests have a display-mode member which determines whether the browser chrome—the navigation, the menu, the tabs, etc.—is shown to the user. For add to home screen to be triggered, this member must be set to standalone or fullscreen. Set display-mode now:

"display": "standalone"

What about the start_url?

The start URL is the page we want the user to see when they launch the app from a home screen. For fireworks this will be the root of our domain. Since our web server looks for index.html for anything ending in '/', we're leaving that off. However, we do want to know if the user arrived via URL or from the home screen. Enter this for the start_url:

/?utm_source=homescreen

This can actually be anything you want, though the value we're using has the advantage of being meaningful to Google Analytics among other analytics platforms.

Splash Screen

This codelab is called "Add to Home Screen". This implies that launching a web app from a home screen provides an experience similar to launching a native app from a home screen—including displaying a splash screen. Fortunately there's no work to be done for a splash screen. Browsers construct a splash screen for you using the following members:

A splash screen using the values we've selected looks something like this:

To check your work, compare it to the files in step-03/.

Next up

We'll validate the manifest and add it to index.html so that I can be loaded on a client device.

Before going further, let's validate the manifest. Open a new browser tab and navigate to:

https://manifest-validator.appspot.com/

Follow the on-screen instructions to validate your manifest. Correct any errors you uncover and come back when you're done.

Add the manifest to your page

Finally, we need to add a link to the manifest in the page. Open work/index.html. Add the following right before the closing </head> tag:

<link rel="manifest" href="/manifest.json">

Further reading: Web App Manifest

Test now?...no, wait

This would seem like a logical place to fire up your web server and browser to make sure the manifest loads along with the rest of your website resources. But it will only work on mobile browsers. Remember this is 'Add to Home Screen', not 'Add to Desktop'.

If you want some extra validation, compare your work so far to the contents of step-04/,

If you already know how to inspect a mobile web page in DevTools, test your work now, then skip to Add a service worker If you don't, keep reading.

Next up

We'll view the Fireworks! app on a mobile device. If the manifest downloads, we'll know we've done everything right.

Configure remote debugging

First, take a little detour to set up remote debugging on your Android device. You will also need to set up port forwarding for port 8887. When you're done with both, come back here.

To use remote debugging, start by opening chrome://inspect/#devices in a tab separate from the Fireworks! app. Next wake the screen of the mobile device and launch Chrome. On your desktop, refresh the inspect page. On the device you'll get a prompt asking if you want to allow USB debugging. Click OK.

At this point you should have:

With your web server running, open localhost:8887 on your mobile device. You should see two things. First, this page listed in chrome://inspect/#devices. More importantly, you'll see the pretty fireworks on the mobile device. Yeah! (Remember, touch the screen to get actual fireworks.)

Underneath Fireworks! click inspect. If you've done everything correctly:

Next up

It's time to add a service worker. Not only will this let you use Fireworks! offline, you'll get to see the add to home screen prompt for the first time.

For this codelab, what we care about is getting the service worker created as quickly as possible. Fortunately it doesn't actually need to do anything. Create an empty file in work/ called service-worker.js.

Register the service worker

A service worker isn't much good unless it's registered by the page that uses it. Open work/index.html. Scroll to the bottom and add the following code before the closing </html> tag:

<script>
  if ('serviceWorker' in navigator) {
    console.log("Will the service worker register?");
    navigator.serviceWorker.register('service-worker.js')
      .then(function(reg){
        console.log("Yes, it did.");
      }).catch(function(err) {
        console.log("No it didn't. This happened: ", err)
      });
  }
</script>

Test add to home screen

On your mobile device, refresh the page being served from localhost. The Sources tab in DevTools should show a file called service-worker.js in addition to the app's other files.

On the mobile device close the Fireworks! tab and do something else, anything else for five or more minutes. When you come back and reload the app, you should get a splash screen and a prompt to add the Fireworks! app to your home screen. If you don't get something like this, check your work.

Wo0t!

Congratulations! You're technically done with this codelab. Your work should look like what's in the final/ directory. I'm going to guess that you want to show your work to someone, like a coworker or your boss. To do that you'll need to put it on a web server that supports HTTPS. Fortunately, we've got one that you can use on a codelab app. To learn more, go to the next step.

If you're new to Firebase, you'll need to create your account and install some tools first.

  1. Create a Firebase account at https://www.firebase.com/signup/
  2. Install the Firebase tools via npm: sudo npm install -g firebase-tools

Once your account has been created and you've signed in, you're ready to deploy!

  1. Create a new app at https://www.firebase.com/account/
  2. If you haven't previously signed in to the Firebase tools, update your credentials: firebase login
  3. Initialize your app, and provide the directory (likely work) where your completed app lives: firebase init
  4. Finally, deploy the app to Firebase: firebase deploy
  5. Celebrate. You're done! Your app will be deployed to the domain: https://YOUR-FIREBASE-APP.firebaseapp.com

Further reading: Firebase Hosting Guide

Now that you've got something on a server, go show it off. Maybe your parents will finally understand what you do for a living. This codelab has certainly helped my parents, though to be fair, they're not software people meaning they haven't understood a single word between 'Overview' and this paragraph. But then, I can't tell you how to run a printing press or fill out government paperwork for special education students. So I guess it all balances out.