preload
Apr 23

 As the Scrum product owner of the german Telefónica o2 online shop I was recently assigned the project of building a mobile version of the application. The project is currently under construction but still the whole topic of mobile web development was relatively new to me – not as a user, but as a creator of applications. Sure enough, I can join in on a mobile web bullshit bingo game, but never having built something myself didn’t feel right. That’s why I decided to mess around with the topic a little bit myself.

In order to learn something new it’s always a good idea to read up on the topic. But that doesn’t make you an expert. So I started a little demo project using various html5 related features. I called it „Geotracer“ and it was inspired by the app „Runtastic“ that I love using on my iPhone. So what does it do?

  • collect your positions using the positioning feature of the device
  • save the data of the trip in the local storage of the browser
  • calculate elapsed time, distance and average speed
  • draw the route onto a google map
  • functionality for persisting trips on the server and loading them later
  • show places nearby and calculate the distance to them. The data for the places was taken from www.geonames.org

From the technical design point of view these are the key elements

  • single page web application
  • JQuery as JavaScript framework
  • Client-Server data interchange using JSON objects
  • basic file structure derived from html5boilerplate in order to get started quickly

When done properly this should be added, too

  • feature detection and using polyfills for substituting missing features
  • more error handling (as you’ll see when analyzing the sourcecode)

The result can be seen here – it works well with iOS6, I haven’t tested it with any other mobile operating systems.

Here are some of the learnings I got from this little project

The geolocation feature

The api for locating your current position is astonishingly easy to use. All you need to do is call the function and pass references to callback functions for success- and error handling as parameters.

navigator.geolocation.getCurrentPosition(storeCurrentPosition, errorRetrievingCurrentPosition);

The function called in the case of success receives the current position and you can extract the values for latitude and longitude like this.

function storeCurrentPosition(position) {
var trackingPoint = new TrackingPoint(new Date().getTime(), position.coords.latitude, position.coords.longitude, )
}

Learnings:

  • of course the GPS module is not 100% accurate. So even if you do not move, the collected geolcations will be spread over an area of some square meters. In order to compensate the effect I made sure the location is only persisted in case the new position is at least 10m away from the previous position

  • When the iPhone goes into sleep mode while the application is running, it stops executing JavaScript code and thus no more geolocation data is collected. This is a very good idea in order to prevent battery drain. The downside is that a web based application is rather useless for what geotracer is inteded to do.

For calculating the distance between two points I used the Haversine-Formula. The implementation I used comes from here: http://stackoverflow.com/questions/27928/how-do-i-calculate-distance-between-two-latitude-longitude-points

Local Storage

I was really amazed how simple the api really is. Geotracer stores all collected geolocations locally, so that you can navigate to another page, come back and your data is still available. The local storage API consists of 4 methods, no need for further explanation:

localStorage.getItem("key");
localStorage.setItem("key", "value");
localStorage.removeItem("key");
localStorage.clear();

Important to know: if you want to store object data you’ll need to convert it to a string first. JSON.stringify(object) does the job perfectly. For using a serialized object later you can simply call JSON.parse(object)

Web Workers

I experimented with web workers but came to the conclusion that for this application it doesn’t really make sense to use it. I love the concept of being able to use multithreading in JavaScript. I tried to move the sampling and persiting of tracking points in the local storage to a web worker, but quickly found out that this is simply not possible as neither navigator.geolocation or localStorage are accessible in a web worker thread. You can’t even debug your code using console.log. Instead, the communication between the web worker and the window can be implemented by exchanging messages. I’ll definitely give web workers a second change as soon as I find a good use case for them.

Bottom Line

It was fun to implement this little project. And while working on it I continuously found other areas I want to dig into, such as the already mentioned web workers or CSS3.

Useful resources

http://www.core-dump.net/html5play/geotracer/geotracer.html

http://caniuse.com/

http://html5boilerplate.com/mobile/

http://www.geonames.org/

http://stackoverflow.com/questions/27928/how-do-i-calculate-distance-between-two-latitude-longitude-points

 

 

Share and Enjoy:
  • Digg
  • del.icio.us
  • Facebook
  • MisterWong

3 Responses to “Geolocation and local storage: getting started with html5 and the mobile web”

  1. Mobile Web Mapping | pineylime Says:

    [...] ‘Adding GeoJSON to Leaflet with Link Relations’    http://www.core-dump.net/programming/getting-started-with-html5-and-the-mobile-web/ - ‘Geolocation and local storage: getting started with html5 and the mobile [...]

  2. Frank Says:

    Thank you very much for this nice basic app! You are right… A geotracer is useless when the phone is in sleep mode and the JavaScript is not working then.
    When you use PhoneGap (Cordova) or Intel XDK to develop (and debug!) a HTML5 app you can use JavaScript functions to prevent your phone going in standby. PhoneGap or XDK build native apps for all common mobile devices and show (and run) your HTML5 web app within a webview.

    I didn’t check their power management functions in detail, but I think this is a possible solution.

    INTEL XDK:
    intel.xdk.device.managePower(true,false);
    https://software.intel.com/en-us/node/493027

    PhoneGap (plugins):
    window.plugins.insomnia.keepAwake();
    window.plugins.insomnia.allowSleepAgain()
    https://github.com/EddyVerbruggen/Insomnia-PhoneGap-Plugin

  3. Frank Says:

    I also think that the function
    navigator.geolocation.watchPosition is running in background

Leave a Reply