Developing Widgets for Windows Mobile 6.5
4/7/2010
Microsoft
June 2009
Summary
Windows Mobile® widgets typically are single-purpose applications to display data obtained from the Internet. They are written using JavaScript and bring the wealth of experience of Web developers to the Windows Mobile platform. Since widgets are installed and run locally on the mobile device, they provide ease of use and a better Internet user experience than conventional Web applications.
Applies To
Windows Mobile 6.5
Introduction
Widgets and Windows Mobile 6.5
Developing Widgets
Creating the User Interface
Localizing Widgets
Using the Widget JavaScript Objects
Creating Widget Menus
Calling AJAX Code
Using Widget Persistence
Using Widget Security
Providing Widget Files
Creating the Manifest File
Creating the Deployment Package
Deploying the Widget
Best Practices
Conclusion
Introduction
Windows® phones offer a rich user experience and a wealth of features for device users on the move. Windows Mobile widgets are applications written using Web development techniques; they connect to Web services to obtain and display data. Widgets can deliver business data, weather information, news updates, traffic maps, and even slide shows of online photo albums. The flexibility of JavaScript and Web development techniques of dynamic markup and style sheets, coupled with the new widget objects mean that Web developers can produce rich applications with the appearance of native Windows Mobile applications.
Starting with Windows Mobile 6.5.3, developers can create Windows Mobile widgets using Visual Studio.
Widgets and Windows Mobile 6.5
A widget is similar in concept to a Gadget for Windows Vista®. HTML markup and cascading style sheets (CSS) provide the user interface, and the code is written in JavaScript. Gadgets brought the wealth of experience of Web developers to the Windows Vista platform, and widgets will do the same for mobile devices. Dynamic HTML (DHTML) is used for dynamic presentation of data to produce a rich interface, while the XMLHttpRequest
control is used to load data from the Web. The entire application is scripted using JavaScript. Widgets are installed locally on the mobile device and, like Windows Vista® Gadgets, widgets run locally but can use data dynamically accessed from the cloud.
Windows® phones can access Web applications with Microsoft® Internet Explorer®; however, this can lead to increased network traffic since server-side changes result in page updates that have to be downloaded to the device. Web applications that use AJAX techniques minimize page updates, but still involve an initial download of the application files (scripts, HTML, and CSS). Widgets reduce network access compared to Web applications, because the scripts and style sheets are installed locally. Subsequently, the only network access performed by widgets is for data access. This means fewer network connections than for Web applications, and this is a key design feature for mobile devices that rely on phone networks that charge by packet transfer rates. Further, the widget API that JavaScript objects provide enables widget developers to provide menu and soft key integration, and local caching of data, which is unavailable to Web applications.
AJAX is a mature technology with a vibrant and experienced community of developers. Widgets bring this wealth of experience to the Windows Mobile platform.
Developing Widgets
Web application developers have a smooth transition to widget development because most of the development involves by using the same techniques. Widgets have specific requirements for deployment and localization, and details are given in this section.
Creating the User Interface
Widgets are full-screen applications, but since the user interface is provided through HTML, widgets can use HTML layout to accommodate the form factor of the phone. In addition, the developer can use the document body
object to access the screen dimensions and orientation of the device. The widget API also provides notifications for the change in screen orientation (for example, if the device is rotated), and the developer can use this notification to alter the user interface.
Similar to AJAX application development, widget developers can respond to events from controls and other elements on the Web page. A particularly useful feature of Windows Mobile is the support for localization.
Localizing Widgets
Application resources are often specific to a locale. In particular, text should be localized to reflect the language and dialect of the user’s device. When designing an application, you should identify the resources that will be localized and create a separate file for each locale that is supported. For example, a widget that displays currency exchange rates and stock quotes should obtain this information from localized Web sites so that, for example, a user in the United States will see the value of the Dow Jones Index and a user in Great Britain will see the value of the FTSE index.
The following code fragments show excerpts from two files, both called directoryUrls.js
. The first file is the default file for the widget. The resource indicates that the https://mny.mobile.msn.com/en-us/default.aspx? Web site should be used for stock quotes. This file is stored in the scripts folder called js
in the deployment file. The second code fragment is the localized resource for the en-UK
locale (British English). In this case, the stock quotes are obtained from the https://mobile.uk.msn.com/device/mny/default.aspx? Web site. This file has the same name as the default resource, but it is within the localized script folder called en-UK/js
. It is important to note that the src
attribute of the <script>
element in the HTML for the widget is not localized; the src
attribute only references the default file in the js
folder and Windows Mobile 6.5 will load the appropriate file.
// Default locale, js/directoryUrls.js
var MSN_OCID_PARAM = "ocid=widget_mny_1";
var DirectoryUrls = {
MSNMoney: "https://mny.mobile.msn.com/en-us/default.aspx?"
+ MSN_OCID_PARAM
}
// UK locale, en-UK/js/directoryUrls.js
var MSN_OCID_PARAM = "ocid=widget_mny_1";
var DirectoryUrls = {
MSNMoney: "https://mobile.uk.msn.com/device/mny/default.aspx?"
+ MSN_OCID_PARAM
}
At run time, Windows Mobile 6.5 checks the locale of the device (for example, en-US
or en-UK
), and if there is a folder with the name of this locale it will use the localized folder as the base folder for the script files. If the localized folder does not exist, Windows Mobile searches for a folder with the language name (for example, en
).
If the device cannot find any localized files, it will load the default files. The widget code is contained in locale-neutral script files. To obtain the URL to use for stock quotes, this code accesses the DirectoryUrls.MSNMoney
variable from the localized directoryUrls.js
file loaded by Windows Mobile, where it gets a URL appropriate to the locale.
It is important that if you provide localized files you also provide default files. All the widget files can be localized. However, to minimize the size of the deployment package, it is better to localize individual items, as shown above, rather than simply providing a localized copy of each HTML and JavaScript file.
Using the Widget JavaScript Objects
A widget is a stand-alone, locally executed AJAX application, written in JavaScript. The widget can be as simple as a single HTML file with a <script>
element or it can be composed of one or more JavaScript files. The HTML file can contain <object>
elements and this also means that the widgets can display Flash files. The JavaScript code is subject to the widget security model.
Windows Mobile provides a JavaScript object called widget
that gives access to some device system state information and to widget-specific features. The widget
object provides some information through properties, and it can also be used to create a state object to provide access to other features. The widget manifest file is an XML file deployed with the widget. It is covered later in this article.
Property | Description |
---|---|
|
The e-mail address of the widget author. This is the |
|
The name of the widget author. This is the value of the |
|
The Web site address of the widget author. This is the |
|
The icon used by the widget. This is an object of type |
|
The description string for the widget. This is the value of the |
|
The height, in pixels, of the widget. |
|
The id attribute identifier for the widget. This is the |
|
The locale of the widget. This reflects the setting selected in the Regional Settings dialog box on the device. |
|
The menu object for the widget. This is an object of type |
|
The user-friendly name of the widget. This is the value of the |
|
The version of the widget. This is the |
|
The width, in pixels, of the widget. |
The following code example shows how to use the widget properties.
<div id="divData"></div>
<script type="text/javascript">
divData.innerHTML = "The " + widget.name + " widget is localized to "
+ widget.locale;
</script>
Further system information is obtained through the SystemState
object. This object has the following properties.
Property | Description |
---|---|
|
A Boolean value indicating whether the device is cradled. |
|
An integer value indicating whether the display is in portrait or landscape mode. |
|
A Boolean value indicating whether the device is presently registered on its home network. |
|
A string indicating the name of the device’s mobile operator. |
|
A Boolean value indicating whether the device is currently roaming. |
|
An integer indicating the phone signal strength, expressed as a percentage of full strength. |
|
An integer indicating the current state of the battery, such as whether the battery level is critically low or if the battery is charging. |
|
An integer indicating the current battery strength, expressed as a percentage of full strength. |
The following code shows how to access information about the device.
<div id="divData"></div>
<script type="text/javascript">
var systemState = widget.createObject("SystemState");
divData.innerHTML = "The phone operator name is "
+ systemState.PhoneOperatorName + " and the signal strength is "
+ systemState.PhoneSignalStrength;
</script>
You can register an event that will be called when the property changes. To do this, you call the addEventListener
method to add a handler function for the changed
event on the SystemState
property for which you want the notification. For example, using the objects declared in the previous code, you can specify that a function called cradled
is called when the device is cradled.
var cradledState = systemState.CradlePresent;
cradledState.addEventListener("changed", cradled);
Most of the widget
and SystemState
properties are integer or strings, but some are new object types. For example, the widget.currentIcon
property is an object of type WidgetIcon
with the following properties.
Property | Description |
---|---|
|
An integer giving the height of the icon. |
|
A string with the URL to the icon file. |
|
An integer giving the width of the icon. |
The widget.menu
is a Menu
object and will be covered in the next section.
Creating Widget Menus
A widget can have a menu and it can also define the action of the device soft keys. These tasks are performed through the Menu
object.
Beginning with the Windows Mobile 6.5.3 release, touchable tiles replace soft keys. For developers, the change from soft keys to touchable tiles is automatic starting with Windows Mobile 6.5.3. All of the following applies to touchable tiles and to soft keys.
Method | Description |
---|---|
|
Appends a |
|
Clears the contents of the main menu. |
|
Creates a |
|
Returns the |
|
Removes the specified |
|
Assigns a |
The soft keys can be assigned with either a single MenuItem
object, or a menu made up of one or more MenuItem
objects. By default, when the widget starts, the left soft key has the single MenuItem
object called Exit (which closes the widget), and the right soft key has a menu that comprises just one MenuItem
object that also exits the application. The following illustration shows the right menu displayed when the right soft key is clicked.
The preceding illustration applies to widgets created prior to Windows Mobile 6.5.3.
The menu object has two properties, leftSoftKeyIndex
and rightSoftKeyIndex
that can be used to identify the soft key to assign a menu item using the setSoftKey
method.
The following code creates a new menu item by calling createMenuItem
. The numeric identifier passed to the method must be unique in this widget code. The menu item is then initialized with the display text and the click event handler function. The code then calls setSoftKey
to assign the menu item to the left soft key.
function clickMeHandler() {
alert("do something");
}
var menu = widget.menu;
var menu1001 = menu.createMenuItem(1001);
menu1001.text = "Click Me";
menu1001.onSelect = clickMeHandler;
menu.setSoftKey(menu1001, menu.leftSoftKeyIndex);
The following illustration shows the results.
If you use the following line instead of the call to setSoftKey
, the menu item will be appended to the right menu.
menu.append(menu1001);
The following illustration shows the results.
The MenuItem
object has a text
property that gives the display text and an enabled
property that determines whether the menu item can be clicked. The MenuItem
object also has a read-only property called id
that is assigned by the Menu.createMenuItem
function. The click event handler function for a menu item is passed the id
of the menu item, so you can write generic handler functions that handle more than one menu item. The MenuItem
also has an append
and a remove
method to add child menu items.
Using the clear
, append
, remove
and setSoftKey
methods on the Menu
object, and the append
and remove
methods on the MenuItem
object, you can build up complex multilevel menus. When a menu item has child items, the menu item's click handler opens the child menu rather than calling the handler you specify.
Calling AJAX Code
The widget code can use the XMLHttpRequest
object to access data asynchronously from the Internet, and can then use the XML DOM to parse the returned data. The following is a simple form to request a stock symbol and display the symbol value on the page.
<div id="divQuote">Quote</div>
<form>
Stock symbol (eg US:MSFT) <input type="text" id="iSymb" />
</form>
The onClick
function is a handler for a menu item click to obtain a stock quote.
function onClick() {
var xmlhttp = null;
if (window.XMLHttpRequest) {
xmlhttp = new XMLHttpRequest();
}
if (xmlhttp) {
createRequest(xmlhttp, document.getElementById("iSymb").value);
}
}
This function creates an XMLHttpRequest
object and then calls a function called createRequest
passing the object and the symbol name.
function createRequest(xmlhttp, symb) {
var url = "https://blu.services.stub.msn.com/"
+ "StockQuotes.aspx?symbols=" + symb;
xmlhttp.open("GET", url);
xmlhttp.onreadystatechange = function() {
if (xmlhttp.readyState == 4) {
harvestResults(xmlhttp);
delete xmlhttp;
}
};
xmlhttp.send();
}
The call to the XMLHttpRequest.open
method creates an asynchronous request to the MSN stock quote service passing the stock symbol. The actual request is made when the send
method is called. The onreadystatechange
event is raised when the request returns. The stock quote service returns an XML document with one or more stock quotes, and this data is parsed by the harvestResults
function.
function harvestResults(xmlhttp) {
if (xmlhttp.status == 200) {
var xmldoc = xmlhttp.responseXML;
if (xmldoc) {
var quoteList = xmldoc.getElementsByTagName("ticker");
if (quoteList != null && quoteList.length > 0) {
divQuote.innerText = quoteList[0].getAttribute("name")
+ " $" + quoteList[0].getAttribute("last");
}
}
}
}
The responseXML
property returns the data as an XML Document Object Model (DOM) object. The remainder of the code uses the DOM to obtain the first <ticker>
element, and from this obtains the full name of the company and the last value of the stock.
A widget running this code enables the user to request individual stock quotes, and the widget will display the code onscreen.
Using Widget Persistence
Widget security denies access to common Windows Mobile persistence mechanisms (for example, the file system and Microsoft SQL Server® Compact Edition databases). Persisting information between runs of a widget is a useful feature, so the widget API provides a persistence mechanism that enables storage of simple string information. The data persistence is isolated so that a widget can only read the data that it has stored. However, it is important to point out that the storage mechanism does not encrypt the data, so another non-widget application (native or managed code) could have access to the data.
To store data, a widget calls the setPreferenceForKey
method on the widget
object.
var symbol = document.getElementById("iSymb").value;
widget.setPreferenceForKey(symbol, "SYMBOL");
The previous code stores the last stock symbol requested. The code can read the value with the preferenceForKey
method.
var symbol = widget.preferenceForKey("SYMBOL");
The values stored with this mechanism persist until the next time that the widget runs, and it will be available after a reset. The mechanism should be used for relatively small values since there is a limit of 4000 bytes per key.
Using Widget Security
Security is vital in every application, but it has an increased significance in code that can be installed over a network and whose functionality depends on data from the Internet. Windows Mobile widgets run under Internet Explorer and are subject to the Internet Explorer Sandbox. This means that the widget cannot access personal data on the device, so information like contacts, the e-mail message store, the registry, and the file system are not accessible to widgets. Furthermore, by default, network access is denied to the widget unless the widget manifest file requests this privilege through the <access>
element in the manifest file.
<access network="true" />
Internet Explorer security policy is maintained. Data maintained by Internet Explorer, like cookies, the cache, and the history list are isolated to each widget and the history and the cache are cleared every time the widget starts.
Special exceptions are made to relax the sandbox, but these still maintain widget security. Although the widget cannot access files in general, it may access files in the home folder and the folder beneath it using the src
attribute of relevant HTML elements (for example, <img>
for image files). The security sandbox enables navigation through some special protocols like mailto:
, sms:
, callto:
, and tele:
, but in these special cases the navigation is delegated to the device process responsible, and the user will be able to cancel any action being taken.
The device is protected from installing rogue code. First, users will only be able to install a widget from the Internet through Microsoft Windows Marketplace for Mobile and can therefore authenticate the source of the code. Second, the user is notified during the installation process and approval is requested, so when the user installs a widget he will get a page displaying information from the widget manifest describing the widget and the page will request permission to install the code. Furthermore, some security checks are made before the widget runs. For example, if the widget manifest indicates that the widget requires network access, the device displays a warning dialog box indicating that network access could incur call plan costs. The user gets the option to continue running the widget or to exit.
Providing Widget Files
Widgets must contain one HTML file for the user interface. This start file is named in the widget manifest using the <content>
element. The start file can contain style elements and scripting to support the widget functionality, but typically the start file references separate CSS files and scripts through the <style>
and <script>
elements. Widgets support localization of resources and code, and Windows Mobile loads the localized files if they are present. All of these additional files are provided within the widget folder. The following table summarizes the types of files within a widget folder.
File Type | Mandatory | Description |
---|---|---|
<widget>.html |
Yes |
The start file for the project. <widget> is the name of the widget as given by the widget manifest file. |
config.xml |
Yes |
An XML file containing the metadata for the widget. |
*.ico, *.png, *.jpg |
Yes, at least one |
The icon to be used for the widget in the Start menu of the mobile device. The icon file is mentioned in the widget manifest file. Windows® phones that run only support .ico files, while Windows® phones that run files support all three formats. |
*.js |
No, but preferred |
JavaScript files containing the code for the widget. |
*.css |
No, but preferred |
Style sheets for the widget. |
Resource files: .jpg, .png, and more |
No |
Additional resources. |
Creating the Manifest File
Each widget must have a manifest file. This is an XML file called config.xml
containing a root element called <widget>
. The manifest file contains information about the widget including data that may be localized, so the manifest may be within the localization folders. However, even if you use localized versions of the manifest file, it is prudent to place a default copy of the manifest file in the root of the widget folder to be used as the default if the device has a locale that is not handled. The <widget>
element in the manifest file must have the name of the start file; other elements are optional but recommended. The following is a minimal manifest file.
<?xml version="1.0" encoding="utf-8" ?>
<widget xmlns="https://www.w3.org/ns/widgets" version="1.0">
<content src="StartUp.htm" type="text/html" />
</widget>
This manifest indicates that the start file is called StartUp.htm
. If the device Regional Settings are set to English (United States), the locale is en-US
, so when the device runs the widget, it first looks for a file called StartUp.htm
in the en-US
folder. If the folder does not exist, or the file is not in that folder, the device looks for a file called StartUp.htm
in the en
folder and if that file does not exist, the device loads StartUp.htm
from the root folder.
Another localized file is the icon file. Windows® phones that run devices can only use .ico
files, while other phones can also use .png
and .jpg
files.
The following table lists the elements that can be used in the <widget>
element.
Element | Description |
---|---|
|
This element indicates the network requirements of the widget. If the |
|
This element contains information about the author of the widget. The optional attributes are: |
|
This element is required. The |
|
This element describes the widget; the description is displayed during installation of the widget. |
|
This element gives the name of the file to be used for the widget icon in the Start menu. The |
|
This element gives a user-friendly name of the widget. This name is displayed in the Start menu and in the Remove Programs page. |
Some of the manifest values can be accessed by the widget code using properties of the widget object.
Creating the Deployment Package
A design goal of Windows Mobile widgets is to provide a single download deployment package. The package is a standard zip file with the extension changed from .zip
to .widget
. You can use any name for this file, but best practice is to use the name of the widget. If you do not provide the name of the widget in the manifest file, the widget installer uses the name of the deployment file as the name of the widget on the device.
Within the zip file are all the files that the widget needs to run: Web pages, icon graphics files, style sheets, JavaScript files, and other resources. These files are stored in the zip file using the same folder structure as will be used by the widget, that is, if your widget uses localization, the zip file contains the locale folders containing the localized files and folders as explained earlier.
Deploying the Widget
The current version of Windows Mobile widgets supports two deployment modes: Marketplace and sideload deployment. Marketplace is an online application store intended to be a one-stop shop for purchasing Windows Mobile applications.
Developers can use sidelong deployment from the desktop development workstation. To do this, the developer copies the widget deployment file to the device and then runs the widget file on the device. This deployment method works out of the box for the emulator image, but for actual devices the developer must add the following registry keys to the registry of the device.
[HKEY_CLASSES_ROOT\riapp]
"EditFlags"=dword:00010000
[HKEY_CLASSES_ROOT\riapp\Shell\Open\Command]
@="wmwidgetinstaller.exe %1"
Without these keys, the Windows® phone does not recognize that there is a file association with the .widget
file.
The widget installer extracts the files from the widget file and puts them in a location below \Program Files. Then the installer adds the widget icon to the device Start menu and provides uninstall information so that the widget can be removed through the Remove Programs application. After the widget is installed, the widget files are accessible through a subfolder under the \Program Files\Widgets\User folder. This means that when you develop your application, you only need to deploy the .widget
file one time, and when you change files you can copy them directly from the development workstation to the device using Windows Explorer.
Best Practices
The SystemState
object enables you to poll for the system values and take appropriate actions; it also enables you to register an event handler that is called when a specific value changes. You can use these values to monitor the battery life and the presence of a network and change the behavior of your code accordingly. For example, if your widget updates the display with information from the Internet, you may choose to disable this update when there is no network present. The widget
object has two properties called onshow
and onhide
that you can assign to functions that will be called when the widget is shown or hidden, and you may choose to disable all network access when the widget is hidden and resume the access when the widget is shown.
The rationale behind the "asynchronous" term in AJAX is that network calls take time, and so network calls can be made asynchronously to the user interface code. It is frustrating for users to wait while the user interface updates, especially when the widget first starts. You can mitigate for this network latency by caching important values using the persistence APIs; when the widget starts up, you can display these cached values. At the same time, your code can be performing the asynchronous request, and when the request completes you can use the new data to update the user interface.
Cached values can also be used to limit the amount of network calls that are made by checking the cache for key data values and only reading them from the network if such values are not in the cache. This is particularly useful for cell phone networks where the user is charged for each packet sent and received. Similarly, you can cache user input so that the cached values are used on subsequent runs of the widget, rather than requesting the user for them.
You can use style sheets and DHTML to produce a rich user interface, and in addition, you can use the widget API to create menus and assign menus to the soft keys so that a widget can have a native appearance on the phone.
Conclusion
Windows Mobile 6.5 brings widget development to the mobile device. With the rich features of Web development and fast application development of JavaScript, widgets offer a compelling new way to produce rich applications with the appearance and behavior of native Windows Mobile applications.
Additional Information
The following explains the packaging of widgets, a description of the contents of the package and widget metadata.
Widgets 1.0: Packaging and Configuration, W3C Working Draft 22 December 2008.
The following lists the W3C requirements for the Widget standard: