Modifying Live Tiles in a Background Process

LiveTiles_thumb7_thumb1_thumbIf you are developing an application or game  for Windows 8, making sure you have an engaging, inviting, or informative live tile is an absolute must.  I am always surprised when I see the amount of effort a developer puts into their application, but then neglects to spend any time on their live tile.  A live tile is a unique way to engage the consumer while they are not using your application.  It is not only a way to entertain, but done right, it will drive them back into your application or game time and time again.  In this series, we will discuss the many aspects of Live Tiles, from what should be placed on your live tile, to utilizing Azure and Push Notifications to send data to your application.

  1. Creating A Live Tile that is Engaging and Inviting
  2. Working with Live Tiles Locally
  3. Rotating Live Tiles to keep interest
  4. Modifying Live Tiles in a Background Process (This Post)
  5. Using Azure and Push Notifications with Live Tiles

Continuous updating with background processes

In the previous posts we talked about the best practices for what to put on live tiles and also how to use the TileUpdateManager to change the tiles.  In this and the Using Azure and Push Notifications with Live Tiles we will discuss how to make changes to your live tiles when the user is not using your application.

As we learned in the last post, rotating your tiles is a great way to keep visual interest in your application or game but if the user is busy and does not have time to use your application for a week or two, the tiles that you updated will start to get stale quickly.  Imagine the Sports, News, or Stocks application that has week old data.  Updating your tiles with a background trigger is one way to keep it fresh.

We are going to use the same project we used for the last post. If you did not create it in the last post and want to follow along, you can create a new project create a new WideLogo (See this post to find out how).

Creating Rotating Live Tiles from a Background Trigger

1. In the Solution Explorer, right click on the Solution (NOT Project) and select Add à New Project

2. Select the Windows Runtime Component , name it TileBackground and click OK

3. The Class1.cs file from that project will open, for simplicity we will leave it named Class1 (you would want to rename this in a real project of course)

4. At the top of the Class1.cs file, add the following Using statements

using Windows.ApplicationModel.Background;using Windows.Data.Xml.Dom;using Windows.UI.Notifications;using System.Net.Http;using Windows.Data.Xml.Dom;using System.IO;

5. Next, have class one implement the IBackgroundTask interface and delete the thrown exception that is generated. When you are done, your class should look like the image

below.

image

6. Above the Run method add the follow declaration for TileUpdater

TileUpdater tileUpdater;

7. Underneath the run method, add the AddTileNotification Method.  This is the same code we have used in the other posts… only now it is going to be run in a background process.

private void AddTileNotification(string content, string tag)        {            var templateType = TileTemplateType.TileWideSmallImageAndText04;            var xml = TileUpdateManager.GetTemplateContent(templateType);

            var textNodes = xml.GetElementsByTagName("text");            textNodes[0].AppendChild(xml.CreateTextNode("A message"));            textNodes[1].AppendChild(xml.CreateTextNode(content));

            var imageNodes = xml.GetElementsByTagName("image");            var elt = (XmlElement)imageNodes[0];            elt.SetAttribute("src", "ms-appx:///_Images/Coffee03.jpg");

            var tile = new TileNotification(xml);            tile.Tag = tag;

            //tile.ExpirationTime = DateTimeOffset.Now.Add(new TimeSpan(0, 0, 20));

            tileUpdater.Update(tile);        }

 

8. Now we want to add something a little different to our project.  Since you would want to pull data from somewhere outside of your project, we will simulate this by pulling a random quote from the IHeartQuotes API to show on our tile. Add the two methods below to your class. (These are the same ones we used previously with the Yahoo API  (Since this post is about the tiles, we will not comment on the code below, we will do another post on calling REST APIs in the near future)

private async void GetData()        {

            String _url = "http://www.iheartquotes.com/api/v1/random?format=json&max_lines=2&source=joel_on_software";

            var _Result = await CallService(new Uri(_url));            if (_Result != null)                AddTileNotification(_Result.quote, "tag new");

        }

        private async Task<RootObject> CallService(Uri uri)        {            string _JsonString = string.Empty;

            // fetch from rest service            var _HttpClient = new System.Net.Http.HttpClient();            try            {                HttpResponseMessage _HttpResponse = _HttpClient.GetAsync(uri.ToString()).Result;                _HttpResponse.EnsureSuccessStatusCode();                _JsonString = await _HttpResponse.Content.ReadAsStringAsync();            }            catch (Exception ex)            {

                string test = ex.ToString();            }

            // deserialize json to objects            var _JsonBytes = Encoding.Unicode.GetBytes(_JsonString);            using (MemoryStream _MemoryStream = new MemoryStream(_JsonBytes))            {                var _JsonSerializer = new DataContractJsonSerializer(typeof(RootObject));                var _Result = (RootObject)_JsonSerializer.ReadObject(_MemoryStream);                return _Result;            }

        }

 

9. Next, we want to add the code we want to run in the Run method. Add the following code INSIDE the Run(IBackgroundTaskInstance taskInstance) method.

BackgroundTaskDeferral deferral = taskInstance.GetDeferral();

            tileUpdater = TileUpdateManager.CreateTileUpdaterForApplication();            tileUpdater.EnableNotificationQueue(true);

            AddTileNotification("Hey Everyone... Whats up", "tag1");            AddTileNotification("Come see the new coffee shops", "tag2");            AddTileNotification("I need caffine", "tag3");            AddTileNotification("I drink coffee therfore I live", "tag4");            AddTileNotification("Caffine Drip please", "tag5");

            GetData();            deferral.Complete();

 

10. Now all we have left is to add the class that the json that is returned will be deserialized into. We once again used json2csharp.com to create a class. Add the code BELOW Class1 inside the Namespace bracket. (We could have put this in a separate file but will do this for simplicity.

public sealed class RootObject{    public string json_class { get; set; }    public IList<string> tags { get; set; }    public string quote { get; set; }    public string link { get; set; }    public string source { get; set; }}

 

That completes the project that will run in the background with the trigger is fired.

Call your background trigger from your application.

Now we are going to set up our project to allow background triggers and call the trigger from our project.

1. Right click on the References folder in your windows 8 project and click on Add Reference.

2. When the Reference Manager comes up, Select Solution and Projects on the left and click on the TileBackground project, and then click on OK

image

3. Now, double click on Package_appmanifest in the solution exploer and open it to the Declarations Tab

4. From the Available Declarations dropdown select Background Tasks

5. Click on ADD

image

6. Under Properties (on this page) check the Timer Task, and add the text TileBackground.Class1 to the EntryPoint section (This is the Namespace and Class for our

background process which we just referenced)

image

7. Now click on the Application UI tab (should have a red x next to it) and scroll down to the Notification section.

8. Change the Lock screen notification dropdown to Badge

9. Change the Badge logo to Assets\<TheNameOfYourLogo>.png

YOU WILL NEED TO CREATE THIS IMAGE.  Please see this post on how to modify an image.  The image size will need to be 24 X 24. The name of your logo may be different, obviously change this to what you named your logo.

image

10. Open up App.xaml.cs (from solution explorer) and add the following using statement to the top of the file.

using Windows.ApplicationModel.Background;

 

SPECIAL NOTE :  We are placing this in the App.xaml.cs file for simplicity.  This may or may not be where you want to launch your background task. Other options are the OnNavigatedTo method of your first page.

11. Now add the RegisterBackgroundTasks() method to the class. This calls the BackgroundTaskBuilder and adds our trigger to the OS.

private void RegisterBackgroundTasks()        {            BackgroundTaskBuilder builder = new BackgroundTaskBuilder();

            // Friendly string name identifying the background task            builder.Name = "BackgroundLiveTiles";            // Class name             builder.TaskEntryPoint = "TileBackground.Class1";

            IBackgroundTrigger trigger = new TimeTrigger(15, true);            builder.SetTrigger(trigger);            IBackgroundCondition condition = new SystemCondition(SystemConditionType.InternetAvailable);            builder.AddCondition(condition);

            IBackgroundTaskRegistration task = builder.Register();

            //YOu have the option of implementing these events to do something upon completion            //task.Progress += task_Progress;            //task.Completed += task_Completed;        }

NOTE: Make sure you named your project and class with the same case sensitivity as I instructed, TileBackground.Class1 , if you did not you will need to change it in the code above. Since it is just a string you will NOT get an error here.

12. Finally, make a call to the RegisterBackgroundTasks() method inside the OnLaunched()

Method as shown below.

image

That is all that is needed to set up our trigger to change out live tile in the background while we are not running.

How to Run your background trigger during debug.

Now we are going to show you how you can get your trigger to run while you are debugging your application.

1. Build and run the project

2. While the project is still running, switch back to Visual Studio

3. From the Suspend dropdown menu (if you set everything up correctly) you will see your

background process trigger. Select this and it will fire your trigger.

image

If you don’t see this toolbar, in Visual Studio, go to View –> Toolbars and make sure Debug and Debug Location are checked.

4. If you now look at your tile on the start page, it should show you rotating quotes, including one from the quotes service as below. (Quotes will vary)

image

 

That’s it for this post, in the next post we will show you how to use Azure and Push notifications to accomplish this same thing.

Happy Programming

Daniel Egan – The Sociable Geek

 

 



Sorry, comments are closed for this post.