layoutElementContent.uuid: 105524
layoutElementContent.uuid: ff8080811ecaa100011f1e1a245d5979 Document Name BV_RESOURCE_WIDGETZONE_CONTENT Document UUID ff8080811ecaa100011f1e1a24465976

A fortune widget tutorial

Contents

  1. Introduction
  2. Widget technology basics
  3. Getting started
  4. The main document
  5. The widget configuration
  6. A first test
  7. Adding interactive features
  8. Fetch content using AJAX
  9. Make it work on a mobile

Introduction

In this tutorial you will create a simple widget that fetches a new random adage every time the user clicks on the widget. This introduces you to the basics of widget development and walks you through the steps of creating, packaging and deploying widgets for mobile phones.

Widget technology basics

Essentially widgets are small web applications that are stored on the target device. Creating a widget is quite similar to creating a web page. You use the same technologies you would use to build a server-based web site. The difference lies in the runtime environment the widget runs in and format in which it is distributed.

The widget runtime

A Widget executes in a specialized web runtime context that does not feature the usual browser user interface. In this respect the widget runtime resembles a site-specific browser.

If it's not already preinstalled on your mobile, you can download the Vodafone widget runtime via the Live! portal. At the time of this writing the runtime is available in the UK, Spain and Germany.

Widget structure

A Widget is distributed as a regular zip file with .wgt file extension. This archive contains all the files necessary to run the widget. It must contain at least the following files:

  • The widget main document named index.html
  • The widget configuration file named config.xml

These files must either be located at the widget structure's root or in a sub-directory of this root. If placed in the root folder, additional files may be placed wherever you like. Usually script and css files are located in distinct sub-directories below the widget root level.

If the main document and configuration files are placed in a sub-directory, then any subsequent files must be placed in a directory below this level.

Development tools

In addition to your standard set of web development tools you will need a zip file manager like 7-Zip to package your widget. You may also want to try Opera's widget emulator during development to simulate the device's widget runtime environment on your development system. The widget can be opened in the standard Opera browser.

Getting started

Our widget's structure will be rather simple. We'll create three files in this tutorial: the two mandatory files index.html and config.xml mentioned above and an additional JavaScript source file to contain the code to fetch new fortunes.

The main document

The main document is automatically loaded when your widget is opened in the Opera browser or the widget runtime. This file must be named index.html. Begin your widget by copying the code below into your editor and save it to a file named index.html in a new directory.

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN"
  "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">

<html id="main" xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
  <head>
    <meta http-equiv="Content-Type" content="text/html; charset=utf-8"/>
    <title>Fortunes!</title>
    <style type="text/css">
      body { 
    background: #bbbbbb; 
      }
      button { 
    margin: 0 0; 
    float: right; 
      }
      div { 
    margin-top: 20px; 
      }
      #fortune { 
    min-height: 70px; 
    text-align: center; 
    margin-top: 30px; 
    font-weight: bold; 
      }
      #info { 
    text-align: center; 
    font-size: 12px; 
      }
    </style>
  </head>

  <body>
    <div>
      <button type="button" id="closebtn">X</button>
    </div>
    <div>
      <div>The fortune for today is:</div>
      <div id="fortune"></div>
      <div id="info">(Click anywhere to update)</div>
    </div>
  </body>
</html>

Save this html page to index.html and open it in your browser (e.g. opera/firefox, safari).

browser image

 

The widget configuration

A basic widget configuration needs at least an identifier, a name and the size of the widget. Copy the following code into a new file named config.xml in the widget directory you created earlier.

<widget id="http://lab.vodafone.com/fortune">
  <widgetname>Fortunes</widgetname>
  <width>200</width>
  <height>200</height>
</widget>

That's all the code you need for a simple widget. You're now ready to package and test your widget.

A first test

To package the widget's files there are two possible solutions.

  • Create an archive of all files

Zipping content image

 
  • Create an archive of the directory containing all the widget files

Create archive of directory image

 

You'll need to rename the .zip file name extension to .wgt for it to be recognized as a widget by the widget runtime or the Opera browser. That .wgt archive can then be double clicked, or opened in the Opera browser to start the widget.

widget in browser picture

 

If you've got the runtime installed, you can upload the widget to your device and test it there. There are several ways you can transfer your widget:

  • Transfer via Bluetooth
  • Copy to the mobiles SD-card
  • Deploy to a webserver and download

The widget manager will recognize the file type and give you the option to install it.

Making use of the close button

Our widget is working now but it lacks interactive features. So, we're going to add some code that will make the widget react on user input. Open up the index.html file in your editor and change the lines in bold font from the code excerpt below.

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN"
  "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">

<html id="main" xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
  <head>
    <meta http-equiv="Content-Type" content="text/html; charset=utf-8"/>
    <title>Fortunes!</title>
    <style type="text/css">
      body { 
    background: #bbbbbb; 
      }
      button { 
    margin: 0 0; 
    float: right; 
      }
      div { 
    margin-top: 20px; 
      }
      #fortune { 
    min-height: 70px; 
    text-align: center; 
    margin-top: 30px; 
    font-weight: bold; 
      }
      #info { 
    text-align: center; 
    font-size: 12px; 
      }
    </style>
    <script type="text/javascript" src="script.js"></script>
  </head>

  <body onload="init()" >
    <div>
      <button type="button" id="closebtn">X</button>
    </div>
    <div>
      <div>The fortune for today is:</div>
      <div id="fortune"></div>
      <div id="info">(Click anywhere to update)</div>
    </div>
  </body>
</html>

This instructs the runtime to include a file named script.js that is located in the same directory of the index document. Create this file now and paste the following code into it.

function init() {
  // connect the window.close function to the close button
  document.getElementById('closebtn').addEventListener(
    'click',
    function(ev) { window.close(); } ,
    false
  );
}

The runtime will now connect the button's click event to the window.close(); JavaScript function. Update the widget archive you created earlier to include the new file and open it in Opera. This time, when you click on the button, the widget window will close.

Fetch content using AJAX

Next, we will implement the widget's main feature, displaying a random adage. The widget will fetch these messages from a server over the internet. You can view these in your browser, too.

Open up script.js in your editor and replace its contents with the code displayed below. This will instruct the browser to start fetching new messages in the background each time the user clicks anywhere inside the widget's display area.

function init() {
  // Attach the window.close function to the close button
  document.getElementById('closebtn').addEventListener(
    'click',
    function(ev) { window.close(); } ,
    false
  );
  document.getElementById('main').addEventListener(
    'click',
    function(ev) { request_fortune(); } ,
    false
  );
  request_fortune();
}

function request_fortune () {
  var xmlHttp = new XMLHttpRequest();
  xmlHttp.open("GET", "http://lab.vodafone.com/fortune/", true);
  xmlHttp.onreadystatechange = function() {
    if (xmlHttp.readyState == 4) {
      response_fortune(xmlHttp);
    }
  }
  xmlHttp.send(null);
}

function response_fortune (response) {
  if (response.status == 200) {
    document.getElementById('fortune').textContent=response.responseText;
  }
  else {
    document.getElementById('fortune').textContent="Error in server requets.";
  }
}

Update your widget archive again and test it. The new feature should work in the browser but fail in the widget runtime on the phone. This is due to an additional security constraint implemented in the Vodafone runtime, which mandates that a Widget must explicitly white list in its configuration file any host it wants to connect to via xhr.

Make it work on a mobile

In order to fix this bug in our widget, add a host configuration for http://lab.vodafone.com/fortune/ to the config.xml file.

<widget id="http://lab.vodafone.com/fortune">
  <widgetname>Fortunes</widgetname>
  <width>200</width>
  <height>200</height>
  <security>
    <access>
      <host>lab.vodafone.com</host>
    </access>
  </security>
</widget>


bluetooth mobile shot widget on mobile image

 

This time, the widget should work well and display a new random message in the widget window. Congratulations, you've created your first mobile widget.