HTML5 for the Mobile Web: Device Orientation Events

In this third article in our series on HTML5 for the mobile web, we take a look at the Device Orientation API. This API provides information about the orientation and movement of a device. Information comes from the positional sensors such as compasses, gyroscopes and accelerometers. Via this API, a web app can access and make use of information about how a device is physically oriented in space.

Use cases include game control based on device tilting, and mapping where a map is correctly aligned with the world based on the device orientation data.

The HTML5 DeviceOrientation API specifies three events, which are outlined in the table below.

Property Description
deviceorientation fired when a significant orientation occurs
compassneedscalibration fired if the compass needs calibration and calibration will provide more accuracy
devicemotion fired regularly with information about the motion of the device

The DeviceOrientation Event

This event is based around three pieces of data, detailed below

Property Description
alpha the direction the device is facing according to the compass
beta the angle in degrees the device is tilted front-to-back
gamma the angle in degrees the device is tilted left-to-right

To help visualise these values, the image below from the W3C specification document should help:

Deviceorientation event properties illustrated with images of phones tilted in three dimensions
Figure 1: Deviceorientation event properties illustration, reproduced from W3C specification document

So, let’s get our hands dirty. Let’s see how easy it is to access the orientation data of the device.

Accessing Orientation Data

As with other HTML5 APIs, you should check if the browser supports the Device Orientation Events API first. This can be done with the following statement:

To access the orientation data, we need to attach an event listener to the deviceorientation event. And in the handler function we access the data with event.alpha, event.beta, and event.gamma:

The DeviceMotion Event

The other main event offered by this API is the devicemotion event. This is less well supported than the deviceorientation event. It is fired regularly and provides acceleration and rotation rates of the device. Its properties are described below:

Property Description
acceleration provides acceleration data, in m/s² for each of the x, y, and z axes
acceleratonIncludingGravity provides same data as above, but with effects due to Earth’s gravity included
rotationRate provides the rate of rotation in deg/s around each of the axes, as three values, a, b g
interval time in milliseconds between samples

To check if the devicemotion event is supported use:

Accessing the motion data is very similar to accessing the orientation data. First we attach an event listener, and then we can read the event properties:

For brevity, only one of acceleration and accelerationIncludingGravity is shown above.

Displaying Device Orientation Data on a Web Page

Now that we know how to access the device orientation data, we’ll take this data and display it on screen. First, the HTML. We’ll define a div container for the orientation data, and another div for the motion data.

There’s some placeholder text included above; this will be overwritten when we obtain the actual data.

Now, time for some JavaScript. As above, we check for browser support, attach our event listeners, and in the handler functions, we access the data we want to display.
The only new part now is to check the values we have obtained, and to display them in the container div by setting the innerHTML property, for example for the orientation data:

We wrap all this up in a function called init, and we trigger this function when the page is finished loading. So the full code listing is:

Live Demo – Display raw data

Click the image to the right to activate the live demo. Depending on your device, you should be able to see the raw orientation and motion data.

Now that we’ve managed to access and display the raw orientation data, perhaps we can try to present it in a more useful way.



An HTML5 compass

Recall that the alpha value of the deviceorientation event corresponds to the compass bearing of the device. Suppose now, that instead of simply displaying this value, we were to rotate an image in proportion with this value. And suppose also that this image depicted a compass face. Why then, we might have something more useful: a browser-based compass.

First, we begin with the HTML. This time we must display an image. Later we’ll rotate this image by the value of the alpha component using CSS. We won’t need any of the other data for this example.

Note that we give the value compass to the id attribute of the img element. We’ll need this when we rotate the image.

As before, we define an event handler function. This time we only need to obtain the alpha value:

And now we use the CSS3 transform property to rotate the image by exactly this value:

Note that we’ll need the vendor-prefixed versions of this CSS transform for it to work on many browsers. These have been omitted here for brevity, but are included in the full code listing below.

We also include some code to handle some specific edge cases and implementation discrepancies so that it will work correctly on a wider set of devices, but this is not comprehensive, and your device may or may not be supported. These edge cases are discussed in the Browser Support section below:

  • iOS: we check for the webkitCompassHeading property, and use it if it’s available, and reverse the direction of rotation of the compass
  • Android stock browser: we check for the stock Android browser, and apply an offset to the compass bearing to align it with the true compass bearings
  • Firefox: we reverse the direction of rotation

We use CSS to specify the rotation origin, that is, the point around which the rotation will take place, to be the centre of the compass image. And we set the compass width to be 100% of the browser size, leaving the browser to resize the compass image (again, vendor prefixes omitted for brevity):

The whole thing looks like this:

Click the compass image below to the activate the live compass demo. Depending on your device, you should be able to see the compass point to North as you rotate your device.

Live Demo – HTML5 compass

Browser support and Fallbacks

As can be seen from the table below there is wide support for the deviceorientation event across most of the mobile browsers, with the exception of Internet Explorer and Opera Mini. The devicemotion event is a different story. While the acceleration property is reasonably well supported, the rotationRate property doesn’t fare so well.

Android iOS IE Mobile Opera Mobile Opera Classic Opera Mini Firefox Mobile Chrome for Android
Orientation
Acceleration
Rotation
(Sources: caniuse.com, DeviceAtlas, mobilehtml5.org)

Despite even the quite widespread support for the deviceorientation event, there are still discrepencies across its various browser implementations, which developers need to be aware of.

The first type of discrepancy is around what the default 0 value for the orientation data actually means. This manifests itself across different mobile browsers as the values for alpha, beta, and gamma being offset by a certain number of degrees. The solution is to subtract the appropriate offset to get the correct value with respect to the true compass bearings.

In addition, for the three axes, the ranges of angles covered are different across implementations, and the direction of rotation is reversed in some cases.

So, for example, testing the alpha property on some of the major mobile browsers yields the following table, based on work by AJFischer:

Android iOS Opera Mobile Firefox Mobile Chrome for Android
0 deg West(270) East(90) North(0) North(0) North(0)
Positive rotation direction CW CCW CW CCW CW
Table illustrating some discrepencies across alpha(compass) implementations (C/CW: Counter/Clockwise)

For similar tables for the other events and properties, please refer to AJFischer’s github page. He has also done some work to provide a cross-platform, normalised version of the API which will smooth over all the different implementation for the developer, although it requires the jQuery library which may not suit all projects.

The iOS implementation is also not without its peculiarities. Each time the compass is initialised, it sets the current orientation of the device to be 0 degrees, and subsequent values are reported relative to this initial bearing. A workaround for this is to use the iOS webkitCompassOrientation property instead. This property aligns with the true compass heading, and can be used instead of the alpha property if it is available, with something like:

And finally, we should also mention that older versions of Firefox Mobile supported the non-standard mozOrientation event which offered related functionality to the deviceorienation event. Applications targeting older browsers might need to check for this. Documentation can be found here.

Where’s North from here?

The HTML5 DeviceOrientation events API provides the web browser with access to the orientation and motion data of a device. While quite widely supported, there are discrepencies between different vendor implementations. There are also differences in terms of the extent of support. For example, the devicemotion event is less well supported than the deviceorientation event. However, once care is taken to observe these differences across mobile browsers, the DeviceOrientation API can indeed be usefully incorporated into your web applications.

References

Download

Download the full code samples below.

Leave a Reply

Exclusive tips, how-tos, news and comment

Receive monthly updates on the world of mobile dev.

Other Afilias Products

Try the world’s leading device detection solution at
DeviceAtlas - Try the world’s leading mobile device detection solution

Create amazing web presences on any screen with
goMobi - Create amazing web presences on any screen.

Evaluate your websites’ mobile readiness with
mobiReady - Evaluate your websites’ mobile readiness.

© 2017 Afilias Technologies Ltd. All rights reserved.

This is a website of Afilias Technologies Ltd, a private company limited by shares, incorporated and registered in the Republic of Ireland with registered number 398040 and registered office at 6th Floor, 2 Grand Canal Square, Dublin 2, Ireland