Centigrade GmbH
Thinking Out of the Box

Philip Schäfer

From windows to tiles: A tutorial on live tiles & badges

October 30th, 2012 by Philip Schäfer

This blog post seeks to demonstrate the capabilities of Windows 8 “live tiles” and “badges” as initially introduced in Microsoft´s design language Modern UI (also referred to as Metro UI). Being one of the most defining UI elements in Modern UI style, the concept of (live) tiles should be worth looking at a bit closer.

Introduction

Already introduced in Windows Phone 7, the concept of “(live) tiles” has also been adopted in Windows 8 and thus applies regardless of whether our target platform is a mobile device (such as a Windows 8 phone or a corresponding tablet like the Microsoft Surface) or a Personal Computer. The term “tile” defines a rectangular button capable of displaying images, textual content and so-called “badges”. In this context, a badge may be either a small icon or a numeric value that is displayed in the bottom-right corner of a tile. The term “live” tile implies that the contents displayed by a tile may be updated dynamically during runtime. Taking into account both badges and a tile´s capability to change its appearance dynamically, Microsoft provides a mighty new feature enabling developers to keep the user updated about an application’s status even if the application itself is terminated or suspended.

A tile displaying its application´s name (bottom-left corner), two dynamically set strings (lines at the top) and a badge notification (bottom-right corner)

Tutorial

Microsoft allows us to provide tile images for three purposes:

  1. a square logo (150×150 px recommended by Microsoft) that will be displayed on the start screen
  2. a wide logo (310×150 px recommended by Microsoft) that will be displayed on the start screen when switched to wide view mode and
  3. a small logo (30×30 px recommended by Microsoft) that will be displayed while being zoomed out.

Small logo, normal logo and wide logo

So as a first step, let´s create a new Windows Store Application (blank) and subsequently open the auto-created Package.appxmanifest. You may find that there is no image specified for the “wide” logo – so let´s define which image to display here.

If you run your application now and switch back to the Start screen, you might notice that your application´s tile is still being displayed in a square format. Switching to the wide view may be done by right-clicking on your tile and selecting the respective layout.

The possibility to provide a wide tile becomes more interesting when we consider a customization of our application´s tile: so now, let´s add some functionality to update our tile´s appearance from within our program. Therefore, we will add a TextBox to our MainPage and add a custom TextChanged Event Handler.

<TextBox TextChanged="UpdateTile" Width="300" Height="30" />

Please note, that declaring an event handler in a view´s code-behind is a bad practice and is only applied here for showcasing purposes. Particularly with regard to serious software development, the actual handling functionality would rather be defined in a view model instead. If you are interested in reading more about the appliance of MVVM on Windows RT, we recommend you to have a look at our porting case study.

Our aim is to implement a TextBox that auto-updates the application´s tile with the current content of its Text Property. Therefore, we are going to implement the respective handler as follows:

private void UpdateTile(object sender, TextChangedEventArgs)
{
   String txtContent = ((TextBox)sender).Text;
}

Primarily, we will obtain an XML-formatted template to enrich with our value afterwards. Please note, that Microsoft provides a limited set of possible template types . As we want to display one line of text on a wide tile, we will choose TileWideText01 which allows us to display one header line followed by 4 smaller ones.

private void UpdateTile(object sender, TextChangedEventArgs)
{
   String txtContent = ((TextBox)sender).Text;
var xmlTemplate = TileUpdateManager.GetTemplateContent( TileTemplateType.TileWideText01); }

The method call above will return some XML in the following format:

<tile>
    <visual>
        <binding template="TileWideText01">
            <text id="1"></text>
            <text id="2"></text>
            <text id="3"></text>
            <text id="4"></text>
            <text id="5"></text>
        </binding>
    </visual>
</tile>

That being said, it becomes clear that we need to set the values of the “text” nodes. Therefore, we will firstly obtain references to all such nodes and consequently append our TextBox´ content to the first one:

private void UpdateTile(object sender, TextChangedEventArgs)
{
   String txtContent = ((TextBox)sender).Text;
var xmlTemplate = TileUpdateManager.GetTemplateContent( TileTemplateType.TileWideText01);
var textNodes = xmlTemplate.GetElementsByTagName("text"); textNodes[0].AppendChild(xmlTemplate.CreateTextNode(txtContent)); }

As a result, we now have enriched the previously received XML´s DOM with our desired content. Assuming that our Text Boxes content would be “hello world”, the resulting XML would look like the following:

<tile>
    <visual>
        <binding template="TileWideText01">
            <text id="1">hello world</text>
            <text id="2"></text>
            <text id="3"></text>
            <text id="4"></text>
            <text id="5"></text>
        </binding>
    </visual>
</tile>

The only thing left to do is sending this (modified ) XML data to the appropriate Tile Update Manager which triggers the update on our application´s tile:

private void UpdateTile(object sender, TextChangedEventArgs)
{
   String txtContent = ((TextBox)sender).Text;
var xmlTemplate = TileUpdateManager.GetTemplateContent( TileTemplateType.TileWideText01);
var textNodes = xmlTemplate.GetElementsByTagName("text"); textNodes[0].AppendChild(xmlTemplate.CreateTextNode(txtContent));
var tileNotification = new TileNotification(xmlTemplate); TileUpdateManager.CreateTileUpdaterForApplication().Update( tileNotification); }

Although starting a new instance of our application will demonstrate that our code is working, you may notice that there is still a certain issue: In our tile´s bottom-left corner our application´s name had been replaced by our application´s logo. Please note, that this is the standard setting when triggering tile updates. If we don´t want to display our logo at this position (for whatever reasons), we have two further options: we may display our application´s name (like before our update notification) or simply nothing. Taking into account a tile´s XML schema it becomes apparent that we need to set the “visual” node´s “branding” attribute to an appropriate value to resist this default setting. Therefore, the respective “branding” attribute expects either

  1. “none”,
  2. “logo” or
  3. “name”

as a value – attempts to trigger a tile update with different values will fail. The abovementioned default behavior applies only, if no “branding” attribute had been specified. In our case, we want to display our application´s title instead of a logo, thus we require adding the following code:

private void UpdateTile(object sender, TextChangedEventArgs)
{
   String txtContent = ((TextBox)sender).Text;
var xmlTemplate = TileUpdateManager.GetTemplateContent( TileTemplateType.TileWideText01);
var textNodes = xmlTemplate.GetElementsByTagName("text"); textNodes[0].AppendChild(xmlTemplate.CreateTextNode(txtContent));
var brandingAttribute = xmlTemplate.CreateAttribute("branding"); brandingAttribute.NodeValue = "name";
xmlTemplate.GetElementsByTagName("visual")[0] .Attributes .SetNamedItem(brandingAttribute);
var tileNotification = new TileNotification(xmlTemplate); TileUpdateManager.CreateTileUpdaterForApplication().Update( tileNotification); }

Applying such dynamic notifications on tiles may turn out to be a great feature to keep the user informed without having to open the actual application. For instance, we could imagine an application that synchronizes with a social media platform and thus provides information about friends´ status updates on its tile. Given this example, we may assume that social platforms generally not only allow posting one´s status, but also provide messaging functionality. Updating the entire tile not only on status updates but also on each received message would lead to a sensory overload and consequently confusion on behalf of the user. At the same time, it would be very convenient to be informed about new messages without having to actually launch the application itself. To facilitate notifying the user of events in a different way than updating the whole tile´s content, Microsoft introduced ”badges”. A badge is either a numeric value ranging from 1 to 99 or a so-called glyph, a tiny symbol. For the latter one Microsoft also provides a limited set of predefined images.

First of all we should decide which badge type we want to use: in our case we want to notify our user of new messages, so let´s simply choose a glyph. Furthermore, we need to use an appropriate XML template once more:

private void UpdateTile(object sender, TextChangedEventArgs)
{
   …
 
   var badgeTemplate = BadgeUpdateManager
      .GetTemplateContent(BadgeTemplateType.BadgeGlyph); 
}

The obtained template´s structure will look like the following:

<badge value="" />

Consequently, we just need to set the “badge” node´s “value” attribute. As we want to inform our user about new items in his inbox, we will choose a simple envelope symbol:

private void UpdateTile(object sender, TextChangedEventArgs)
{
   …
 
   var badgeTemplate = BadgeUpdateManager
      .GetTemplateContent(BadgeTemplateType.BadgeGlyph); 
badgeTemplate.GetElementsByTagName("badge")[0] .Attributes .GetNamedItem("value") .NodeValue = "newMessage"; }

Finally, we can submit our XML-formatted content to the respective Badge Update Manager which triggers the update on our application´s tile:

private void UpdateTile(object sender, TextChangedEventArgs)
{
   …
 
   var badgeTemplate = BadgeUpdateManager
      .GetTemplateContent(BadgeTemplateType.BadgeGlyph); 
badgeTemplate.GetElementsByTagName("badge")[0] .Attributes .GetNamedItem("value") .NodeValue = "newMessage";
var badgeNotification = new BadgeNotification(badgeTemplate); BadgeUpdateManager.CreateBadgeUpdaterForApplication() .Update(badgeNotification); }

Conclusion

At the bottom-line, by introducing live tiles, Microsoft provides a great tool to make applications more usable. We may provide information to users without having to interrupt other applications (like popup messages and others) and without requiring users to actually launch the application itself. In a nutshell, the smart phone or tablet’s start screen evolves to a dashboard that may help the user to stay informed without any interactions necessary.

On the flipside, developers should consider the negative impacts of tile notifications as well. I´m sure we all know about websites making extensive use of marquees, flashing buttons and other elements begging for attention. You don´t have to be a UI expert to know that this is a desperately wrong approach (see “banner blindness”). Similarly, developers should recapture the actual purpose of tile notifications and

  1. only implement them when really needed and, if so,
  2. implement them cautiously (how frequently must the tile be updated?).

Obviously, a Start screen consisting of 15 applications each updating its tile on a 5 second basis would rather remind of a slot machine than to represent a usable Start screen.

All trademarks or registered trademarks are properties of their respective owners.