»
S
I
D
E
B
A
R
«
Building Your First App: Designing the Skin
28 October 2009 by Rob Spectre
This entry is part 1 of 9 in the series Building Your First App

The Boxee family grows every month as more and more developers discover how easy it is to get started developing on this social platform for the living room.  Using tools such as Yahoo Pipes and popular scripting libraries for generating feeds, developers can go from zero to a published app in no time using Boxee’s default skin.  Just plug in a RSS feed that conforms to the Boxee spec and Boxee “just works.”

But where Boxee really shines as a development platform is with full skin apps.  A lot of Boxee RSS app developers are intimidated by the Boxee API, believing a strong Python background is necessary to build a full skin app.  However, this is just not the case.  Boxee apps can be as simple or as complex as the individual developer needs them to be with many applications requiring no Python application logic whatsoever to work well.  The XML-driven GUI available for Boxee developers gives you everything you need to take your RSS feed and provide a rich, compelling living room interface.

If you can make an RSS feed, you can make a Boxee skin app.

Last month, I got to work with prolific Boxee developer jendabom on building her first skin app for Boxee.  Together, we were able to take one of her RSS apps (Storyline) and make a full skin with a few emails and a couple afternoons worth of work .  From that correspondence, we’ve developed this series taking you step-by-step through building your first skin app.

The way I attack a new app is first designing the interface in my favorite graphic design suite.  I use GIMP myself (as it is FOSS), but if you have access to something more professional like Photoshop or Paintshop Pro that would be good too.

The goal of this step is to layout the interface you are looking for in individual layers that can then be cut out into individual graphics elements that you will make into Boxee app controls.

Here are a few tips:

  • Set your canvas size to 720p (1280×720).  This will ensure your skin looks good on a variety of displays.
  • We can start by choosing between two basic interface options – List and Panel. An example of a “List” interface would be Auto-Tune The News or The Philip DeFranco Show.  An example of a “Panel” interface would be AL TV or KidMango.  Adjust your UI design to fit each paradigm appropriately.
  • Text over multi-color images == bad.  Try to avoid this pet peeve of Boxee QA.

Here’s an example of what jendabom came up with for Storyline:

StoryLineOnline

Building Your First App: Breaking Down The Controls
30 October 2009 by Rob Spectre
This entry is part 2 of 9 in the series Building Your First App

Last time we created a design of our first Boxee app.  In this second installment of an ongoing instructional series on building that full skin, we are going to take that design and break it down into the individual controls that we are going to use in our app.

For this exercise, we chose to use a “list”-style interface, similar to that used in Auto-Tune The News.  Now we need to take the design we created and break it down into three pieces: a background, a list container and a metadata container.

StoryLineOnline

Background:

The background image control is a static, non-interactive component of the interface that serves as the backdrop for the interactive controls in our app.  Using Storyline as an example, your background should include all the elements that aren’t going to change:

background

List Container:

The list container is the main interactive piece of the application.  For our first app, it will be the list of the videos the user can select to watch.  We pull from our initial design a blue box to serve as the control’s background.

list

Metadata Box:

The metadata box is the part of the interface that – you guessed it – shows the metadata for the video selected in the list container.  Examples of metadata we are going to display are a thumbnail of the video, when it was posted, runtime, title, summary, etc.   While the user will navigate using the list container, the metadata box is where their eyes will spend most of their time.  We also pull out a blue box as the background for this control.

metadata

We save these individual elements as PNGs and get ready to start building the skeleton of our application’s directory structure.

Building Your First App: Creating The Skeleton
1 November 2009 by Rob Spectre
This entry is part 3 of 9 in the series Building Your First App

Last time we broke down our app design into three different graphics files – background, list container and metadata box.  Next, we will create the skeleton of our app and place the files in their permanent home.

First, we will create our descriptor.xml.  The descriptor.xml is the configuration file for the application that tells Boxee the location of all important resources and provides metadata about the app including title, description, version and author.

An example of such a descriptor.xml is:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
<app>
  <id>appid</id>
  <name>Name of App</name>
  <version>1.0</version>
  <description>A description of your app.</description>
  <thumb>http://yourdomain.com/yourapp/images/thumb.png</thumb>
  <repository>http://dir.boxee.tv/apps</repository>
  <media>video</media>
  <copyright>Your Name</copyright>
  <email>youremail@email.com</email>
  <type>skin</type>
  <startWindow>14000</startWindow>
  <platform>all</platform>
  <minversion>0.9.11</minversion>
  <test-app>true</test-app>
</app>

What do all these elements mean and how do they affect your app? The Boxee developer documentation has a complete breakdown with three helpful examples.

After we create the descriptor.xml, we can create the directory structure for our application.

First we create a directory with the same name as the value of the id element in our descriptor.xml. Afterwards, we place our descriptor.xml in that directory.

In the root folder we need to create a directory called skin.

Then within the skin folder, create another called Boxee Skin NG. This is where we store the media and resolution skin XMLs.

Within Boxee Skin NG, create two directory – one called 720p and another called media.

When finished, your app’s directory structure should look like:

descriptor.xml
|-skin
|---Boxee Skin NG
|-----720p
|-----media
|---------background.png
|---------list.png
|---------metadata.png

Afterwards, we put the graphic files we created in the last step in their final destination, the media directory.

With our skeleton complete, we can go ahead and place our app folder in a place where Boxee can recognize it. First we need to identify the location of our UserData folder; its location varies depending on your operating system.

  • Linux: ~/.boxee/UserData/
  • Mac OS/X: ~/Library/Application Support/BOXEE/UserData/
  • AppleTV: ~/Library/Application\ Support/BOXEE/UserData/
  • Windows Vista: C:\Users\\AppData\Roaming\BOXEE\userdata\
  • Windows XP: C:\Documents and Settings\\Application Data\BOXEE\userdata\

Once identifying your UserData folder, you need to place your app in the UserData/apps folder to prepare for the next step: hello world!

Building Your First App: Hello World
3 November 2009 by Rob Spectre
This entry is part 4 of 9 in the series Building Your First App

In the last installment of this multi-part guide to creating your first Boxee app, we set up the skeleton of our app with the correct directory structure with appropriate configuration and media files.  Now we finally get our hands dirty by starting the real development of our app.

First, let’s step back and define some critical concepts. Every Boxee application is a set of windows and controls. Windows are the “screens” of the application – the individual interfaces that make up the whole application. For example, Pure Pwnage app has two windows – a window to select a season and a window to select an episode.

Each window is populated with controls. Controls are the individual elements of a window, like those we broke down in the second installment of this series. Examples of controls include the window’s background, the season select screen, and the episode thumbnail. We’ll go into greater detail on controls shortly.

To begin, we create a file in the 720p called main.xml. This file defines our main window and populates it with the controls we created earlier. Essentially main.xml is the heart of our first application.

First, we define an XML document with a root node for our default window.  Consider the following XML:

1
2
3
4
5
6
7
<?xml version="1.0"?>
<window type="window" id="14000">
    <defaultcontrol always="true">100</defaultcontrol>
    <allowoverlay>no</allowoverlay>
    <controls>
    </controls>
</window>

What does this all mean? Let’s break it down:

window:

This element defines the main window for our app and assigns it an id. If you recall in our last installment, our descriptor.xml defines a windowId when the application starts with the startWindow element. This tells Boxee which window to start first when the application is launched.

defaultcontrol:

Like the application needs a default window ID when it is launched, a window needs a default control ID when it begins. We define it here as “100,” which is a control we will create later.

allowoverlay:

This element governs the app’s behavior if Boxee is playing any media. For most applications, we want the interface to supersede what is currently playing, so we set this to “no”.

controls:

This element is the parent for all the controls we will define for this window. The background image, list container and metadata box will go in here.

For more detail on the various elements available to your window, you can refer to this guide on the XBMC wiki.

With our window defined, we are going to add two appropriately named controls – a group control and an image control. A group control is an arbitrary container intended to group together controls that have a similar purpose. To get our “Hello World” app running, we’ll create a group control to contain our image control:

1
2
        <control type="group">
        </control>

Then within that group control, we’ll place an image control for the background image that we created earlier. There are five elements in every image control: posx, posy, width, height, and texture. Boxee renders position elements with respect to the upper left hand corner of the screen and dimension elements with respect to the position coordinates you provide. Since this is a background image, we set our position to 0,0 or the upper left hand corner of the screen and our width/height to 1280×720 (for our 720p resolution application). Finally, we set the value of the texture element to the name of the file in the media folder we created for our background:

1
2
3
4
5
6
7
            <control type="image">
                <posx>0</posx>
                <posy>0</posy>
                <width>1280</width>
                <height>720</height>
                <texture>background.png</texture>
            </control>

So what should this look like when put together correctly? Viola!:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
<?xml version="1.0"?>
<window type="window" id="14000">
    <defaultcontrol always="true">100</defaultcontrol>
    <allowoverlay>no</allowoverlay>
    <controls>
        <control type="group">
            <control type="image">
                <posx>0</posx>
                <posy>0</posy>
                <width>1280</width>
                <height>720</height>
                <texture>bg.png</texture>
            </control>
        </control>
    </controls>
</window>

Once we’ve completed this step, our work in the last step can now come to fruition. Since we included the “test-app” element in our descriptor.xml, Boxee will recognize our new app immediately on startup. Now open Boxee and when you go to Apps, you can execute your app and see the background you created!

Building Your First App: Finishing The Graphics
5 November 2009 by Rob Spectre
This entry is part 5 of 9 in the series Building Your First App

In our last installment, we successfully got our app installed and running – though it is only displaying our background.  We have two more graphic assets that we need to position in our app before we can get to building the interactive controls of our application.

The two assets we have left are the blue background boxes for the list container and the metadata box we pulled out of our original design.  This is easily accomplished by placing one image control for each graphic in the group we created in the last step.

First, let’s look at what we have to work with from last time:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
<?xml version="1.0"?>
   <window type="window" id="14000">
   <defaultcontrol always="true">100</defaultcontrol>
   <allowoverlay>no</allowoverlay>
   <controls>
      <control type="group">
          <control type="image">
             <posx>0</posx>
             <posy>0</posy>
             <width>1280</width>
             <height>720</height>
             <texture>bg.png</texture>
          </control>
      </control>
   </controls>
</window>

An important rule to remember when placing your graphics is that Boxee renders controls sequentially. This means if you want a graphic to appear on top of another graphic (as we want with our list container box over our app background), we must place one after the other in the file. Thus, we add the image control after our bg.png in the same group control:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
<?xml version="1.0"?>
   <window type="window" id="14000">
   <defaultcontrol always="true">100</defaultcontrol>
   <allowoverlay>no</allowoverlay>
   <controls>
      <control type="group">
          <control type="image">
             <posx>0</posx>
             <posy>0</posy>
             <width>1280</width>
             <height>720</height>
             <texture>bg.png</texture>
          </control>
          <control type="image">
             <posx>60</posx>
             <posy>230</posy>
             <width>502</width>
             <height>416</height>
             <texture>list.png</texture>
         </control>
      </control>
   </controls>
</window>

With our list graphic in place, adding the metadata box graphic is just as easy. Just add it after the list container graphic:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
<?xml version="1.0"?>
   <window type="window" id="14000">
   <defaultcontrol always="true">100</defaultcontrol>
   <allowoverlay>no</allowoverlay>
   <controls>
      <control type="group">
          <control type="image">
             <posx>0</posx>
             <posy>0</posy>
             <width>1280</width>
             <height>720</height>
             <texture>bg.png</texture>
          </control>
          <control type="image">
             <posx>60</posx>
             <posy>230</posy>
             <width>502</width>
             <height>416</height>
             <texture>list.png</texture>
         </control>
         <control type="image">
             <posx>630</posx>
             <posy>255</posy>
             <width>574</width>
             <height>355</height>
             <texture>details.png</texture>
          </control>
      </control>
   </controls>
</window>

Now, the next time we open our app in Boxee, we will see our original design faithfully reproduced within Boxee!

For more information on the possibilities of the image control, check out Boxee’s developer documentation.

Building Your First App: The List Container
7 November 2009 by Rob Spectre
This entry is part 6 of 9 in the series Building Your First App

Last time, we finished up the last of the graphics work for our first application. The next step is building the list container. The list container is the primary interface of the application – the control that users browse through to view the content you’re delivering. The good news is they are not very hard to make and they are probably the most complex piece of your whole app.

This one is a little long-winded, I’ll warn you. But not at all as daunting as it might initially seem.

First we start much the same way that we did when building an image control – by setting its position and dimensions:

1
2
3
4
5
6
<control type="list" id="100">
   <posx>65</posx>
   <posy>235</posy>
   <width>492</width>
   <height>406</height>
</control>

Notice that we set the positioning five pixels to the right of the list.png image control and five pixels down. This will make the list seem indented with list.png as its background. Similarly, we reduced the dimensions both height and width by ten pixels, thus giving us a five pixel margin around our list container. We also assign it the id “100″ – the same value as our the defaultcontrol element we defined earlier.

Next, we define our orientation.

1
2
3
4
5
6
7
<control type="list" id="100">
   <posx>60</posx>
   <posy>230</posy>
   <width>502</width>
   <height>416</height>
   <orientation>vertical</orientation>
</control>

This element can have two values – horizontal or vertical. For this particular app, we want a vertical orientation (much like Auto-Tune The News). A horizontal orientation is generally used in panel containers, like those seen in Digg or Revision3.

Third, we need to define our item layout. This is the only part that gets a little tricky. Every item in your RSS feed gets parsed by Boxee and becomes a “ListItem.” The list container we are building will be populated by these ListItems and their appearance must be defined within this control. Consider the following XML:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
<control type="list" id="100">
   <posx>60</posx>
   <posy>230</posy>
   <width>502</width>
   <height>416</height>
   <orientation>vertical</orientation>
   <itemlayout width="502" height="65">
    <control type="label">
        <posx>0</posx>
        <posy>0</posy>
        <width>502</width>
        <height>62</height>
        <font>font40</font>
        <align>left</align>
        <aligny>center</aligny>
        <label>$INFO[ListItem.Label]</label>
        <textcolor>white</textcolor>
    </control>
    </itemlayout>
</control>

The item layout element – like the list control – is a container for all the subelements within it. In this case, we only have one, the ListItem’s Label (read: title). In it you will notice the same position and dimension elements (e.g. posx, width, etc). You will also notice the width and height attributes for the element.

What the item layout attributes do is define the total size of the individual item. In this case, we want to make it as wide as the list container and big enough to have some space between the text. We can then define the dimensions of our label control as slightly shorter, giving us a 3 pixel gap between the labels.

The next step after we define our item layout, is to define our focused item layout. If the item layout defines what all ListItems look like in our app, focused item layout defines how the one focused item in the list should look. This is how we distinguish to the user which piece of content they have selected.

This can be done many ways and fortunately Boxee has some built in features you can use without adding any more graphics assets. Take a look at this addition to our list container:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
<control type="list" id="100">
   <posx>60</posx>
   <posy>230</posy>
   <width>502</width>
   <height>416</height>
   <orientation>vertical</orientation>
   <itemlayout width="502" height="65">
    <control type="label">
        <posx>0</posx>
        <posy>0</posy>
        <width>502</width>
        <height>62</height>
        <font>font40</font>
        <align>left</align>
        <aligny>center</aligny>
        <label>$INFO[ListItem.Label]</label>
        <textcolor>white</textcolor>
    </control>
    </itemlayout>
    <focusedlayout width="502" height="65">
      <control type="image">
           <posx>0</posx>
           <posy>0</posy>
           <width>502</width>
           <height>65</height>
           <texture>white.png</texture>
           <colordiffuse>DD171717</colordiffuse>
       </control>
       <control type="label">
           <visible>!Control.HasFocus(100)</visible>
           <posx>0</posx>
           <posy>0</posy>
           <width>502</width>
           <height>62</height>
           <font>font40</font>
           <align>left</align>
           <aligny>center</aligny>
           <label>$INFO[ListItem.Label]</label>
           <textcolor>white</textcolor>
           <selectedcolor>DD171717</selectedcolor>
       </control>
       <control type="label">
           <visible>Control.HasFocus(100)</visible>
           <posx>0</posx>
           <posy>0</posy>
           <width>502</width>
           <height>62</height>
           <font>font40</font>
           <align>left</align>
           <aligny>center</aligny>
           <label>$INFO[ListItem.Label]</label>
           <textcolor>white</textcolor>
           <selectedcolor>DD171717</selectedcolor>
           <scroll>true</scroll>
           <scrollspeed>30</scrollspeed>
       </control>
    </focusedlayout>
</control>

You’ll notice looks exactly like , only with a few additions. The first addition you will notice is the image control. What this does is give the selected item in the list a tinted background. To accomplish the tint look, we use a default image texture white.png and a colordiffuse element. The colordiffuse element will tint that white with the color you specify, making it in this case just a little more gray. The second difference you’ll notice is that there are two label controls instead of one.

We need two labels in the focused layout to handle two use cases – when the application has focus and when it does not. When Boxee is in focus and the user is actively browsing the list container, he/she sees the label control on the bottom. That label control is set to scroll the text of the label (if it is longer than the width allowed), letting the user preview the content’s full label before selecting it. But, what if that user clicks away into another application or a menu? Obviously we wouldn’t want to continue scrolling, which is what the label control above it does. It stops the scrolling and waits for the user to return his/her focus to the app before scrolling again.

Phew! This is getting long, but we’re almost there.

The final element in your list container is the plumbing to hook your RSS feed up to the application. It can be added easily, like below:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
<control type="list" id="100">
   <posx>60</posx>
   <posy>230</posy>
   <width>502</width>
   <height>416</height>
   <orientation>vertical</orientation>
   <itemlayout width="502" height="65">
    <control type="label">
        <posx>0</posx>
        <posy>0</posy>
        <width>502</width>
        <height>62</height>
        <font>font40</font>
        <align>left</align>
        <aligny>center</aligny>
        <label>$INFO[ListItem.Label]</label>
        <textcolor>white</textcolor>
    </control>
    </itemlayout>
    <focusedlayout width="502" height="65">
       <control type="image">
           <posx>0</posx>
           <posy>0</posy>
           <width>502</width>
           <height>65</height>
           <texture>white.png</texture>
           <colordiffuse>DD171717</colordiffuse>
       </control>
       <control type="label">
           <visible>!Control.HasFocus(100)</visible>
           <posx>0</posx>
           <posy>0</posy>
           <width>502</width>
           <height>62</height>
           <font>font40</font>
           <align>left</align>
           <aligny>center</aligny>
           <label>$INFO[ListItem.Label]</label>
           <textcolor>white</textcolor>
           <selectedcolor>DD171717</selectedcolor>
       </control>
       <control type="label">
           <visible>Control.HasFocus(100)</visible>   
           <posx>0</posx>
           <posy>0</posy>
           <width>502</width>
           <height>62</height>
           <font>font40</font>
           <align>left</align>
           <aligny>center</aligny>
           <label>$INFO[ListItem.Label]</label>
           <textcolor>white</textcolor>
           <selectedcolor>DD171717</selectedcolor>
           <scroll>true</scroll>
           <scrollspeed>30</scrollspeed>
       </control>
    </focusedlayout>
    <content type="url" url="rss://yourdomain.com/yourfeed.rss">
    </content>
</control>

It’s the easy piece of the whole list container puzzle – just plug in the path for your RSS feed into the url attribute, and you’re done-diggy. Once you drop your completed code in the group control after the metadata box image, you can reload the app and see your content now populating. Once you add the container to your app, your main.xml should look like this:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
<?xml version="1.0"?>
   <window type="window" id="14000">
   <defaultcontrol always="true">100</defaultcontrol>
   <allowoverlay>no</allowoverlay>
   <controls>
      <control type="group">
          <control type="image">
             <posx>0</posx>
             <posy>0</posy>
             <width>1280</width>
             <height>720</height>
             <texture>bg.png</texture>
          </control>
          <control type="image">
             <posx>60</posx>
             <posy>230</posy>
             <width>502</width>
             <height>416</height>
             <texture>list.png</texture>
         </control>
         <control type="image">
             <posx>630</posx>
             <posy>255</posy>
             <width>574</width>
             <height>355</height>
             <texture>details.png</texture>
          </control>
          <control type="list" id="100">
	   <posx>60</posx>
	   <posy>230</posy>
	   <width>502</width>
	   <height>416</height>
	   <orientation>vertical</orientation>
	   <itemlayout width="502" height="65">
	    <control type="label">
		<posx>0</posx>
		<posy>0</posy>
		<width>502</width>
		<height>62</height>
		<font>font40</font>
		<align>left</align>
		<aligny>center</aligny>
		<label>$INFO[ListItem.Label]</label>
		<textcolor>white</textcolor>
	    </control>
	    </itemlayout>
	    <focusedlayout width="502" height="65">
	       <control type="image">
		   <posx>0</posx>
		   <posy>0</posy>
		   <width>502</width>
		   <height>65</height>
		   <texture>white.png</texture>
		   <colordiffuse>DD171717</colordiffuse>
	       </control>
	       <control type="label">
		   <visible>!Control.HasFocus(100)</visible>
		   <posx>0</posx>
		   <posy>0</posy>
		   <width>502</width>
		   <height>62</height>
		   <font>font40</font>
		   <align>left</align>
		   <aligny>center</aligny>
		   <label>$INFO[ListItem.Label]</label>
		   <textcolor>white</textcolor>
		   <selectedcolor>DD171717</selectedcolor>
	       </control>
	       <control type="label">
		   <visible>Control.HasFocus(100)</visible>   
		   <posx>0</posx>
		   <posy>0</posy>
		   <width>502</width>
		   <height>62</height>
		   <font>font40</font>
		   <align>left</align>
		   <aligny>center</aligny>
		   <label>$INFO[ListItem.Label]</label>
		   <textcolor>white</textcolor>
		   <selectedcolor>DD171717</selectedcolor>
		   <scroll>true</scroll>
		   <scrollspeed>30</scrollspeed>
	       </control>
	    </focusedlayout>
	    <content type="url" url="rss://yourdomain.com/yourfeed.rss">
	    </content>
	</control>
      </control>
   </controls>
</window>

For more information of the possibilities of the list container, check out Boxee’s developer documentation.

Building Your First App: The Metadata Box
9 November 2009 by Rob Spectre
This entry is part 7 of 9 in the series Building Your First App

In our last installment we turned a significant corner with the construction of our list container. Now we can finish up the interface creation on our first app by creating the metadata box. The metadata box is the interface object next to the list container that displays to the user more information about the item they have selected in the list container. Examples of metadata boxes can be seen in the screenshots for AL TV and Associated Press. Typically they include a thumbnail of the video selected and some helpful information like a description.

To get started, we’re going to abstract this interface from the rest of the application by creating a new group control.

1
2
<control type="group">
</control>

By putting the metadata box in a separate group, it makes future maintenance much easier by keeps parts of the interface logically separate as we continue to develop the app. Inside that group control, we place our first interface element – the video thumbnail.

1
2
3
4
5
6
7
8
9
10
<control type="group">
  <control type="image">
    <visible>true</visible>
    <posx>635</posx>
    <posy>265</posy>
    <width>560</width>
    <height>230</height>
    <texture>$INFO[Container(100).ListItem.Thumb]</texture>
  </control>
</control>

You’ll notice that the thumbnail image control looks much like the many other image controls we’ve created so far with one significant difference in the element. Instead of a static file name, we have a dynamic INFO tag that leverages the Boxee API. We can break down the INFO tag into two parts.

Container(100)
This part of the tag tells the image to get its texture from the list container with id “111″.

ListItem.Thumb
This part of the tag tells the image to look for the thumbnail for the ListItem currently selected in the list container referenced in the first part of the tag.

This small example highlights one advantage of developing on Boxee – all controls can reference each other within the context of an app. We will do this again to add some description data underneath the thumbnail we just created using a label control.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
<control type="group">
  <control type="image">
    <visible>true</visible>
    <posx>635</posx>
    <posy>265</posy>
    <width>560</width>
    <height>230</height>
    <texture>$INFO[Container(100).ListItem.Thumb]</texture>
  </control>
  <control type="label">
    <visible>true</visible>
    <posx>635</posx>
    <posy>500</posy>
    <width>560</width>
    <height>115</height>
    <font>light23</font>
    <align>left</align>
    <aligny>center</aligny>
    <label>[B]Description:[/B] $INFO[Container(100).ListItem.property(description)]</label>
    <background>grey</background>
    <textcolor>white</textcolor>
    <wrapmultiline>true</wrapmultiline>
  </control>
</control>

The label control is similar to an image control with positional and dimensional elements, a content element (with label instead of texture), and some additional formatting element (e.g. align, font, textcolor). The important bit we need to pay attention to is the label element’s INFO tag.

Like our thumbnail, it references the list container we built in the last step but instead of getting the ListItem’s thumbnail, it gets the ListItem description. Why does it use “property” instead of just appending the name of the ListItem element? A longstanding bug in the Boxee API requires the developer to use “property(description)” instead of “Description” to ensure more consistent performance.

For more information on all the things you can do with label controls, refer to the Boxee developer docs.

And just like that, our metadata box is created. All that’s left is to drop it into our existing main.xml and adjust the position and dimensions to fit our content correctly.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
<?xml version="1.0"?>
   <window type="window" id="14000">
   <defaultcontrol always="true">100</defaultcontrol>
   <allowoverlay>no</allowoverlay>
   <controls>
      <control type="group">
          <control type="image">
             <posx>0</posx>
             <posy>0</posy>
             <width>1280</width>
             <height>720</height>
             <texture>bg.png</texture>
          </control>
          <control type="image">
             <posx>60</posx>
             <posy>230</posy>
             <width>502</width>
             <height>416</height>
             <texture>list.png</texture>
         </control>
         <control type="image">
             <posx>630</posx>
             <posy>255</posy>
             <width>574</width>
             <height>355</height>
             <texture>details.png</texture>
          </control>
          <control type="list" id="100">
	   <posx>60</posx>
	   <posy>230</posy>
	   <width>502</width>
	   <height>416</height>
	   <orientation>vertical</orientation>
	   <itemlayout width="502" height="65">
	    <control type="label">
		<posx>0</posx>
		<posy>0</posy>
		<width>502</width>
		<height>62</height>
		<font>font40</font>
		<align>left</align>
		<aligny>center</aligny>
		<label>$INFO[ListItem.Label]</label>
		<textcolor>white</textcolor>
	    </control>
	    </itemlayout>
	    <focusedlayout width="502" height="65">
	       <control type="image">
		   <posx>0</posx>
		   <posy>0</posy>
		   <width>502</width>
		   <height>65</height>
		   <texture>white.png</texture>
		   <colordiffuse>DD171717</colordiffuse>
	       </control>
	       <control type="label">
		   <visible>!Control.HasFocus(100)</visible>
		   <posx>0</posx>
		   <posy>0</posy>
		   <width>502</width>
		   <height>62</height>
		   <font>font40</font>
		   <align>left</align>
		   <aligny>center</aligny>
		   <label>$INFO[ListItem.Label]</label>
		   <textcolor>white</textcolor>
		   <selectedcolor>DD171717</selectedcolor>
	       </control>
	       <control type="label">
		   <visible>!Control.HasFocus(100)</visible>   
		   <posx>0</posx>
		   <posy>0</posy>
		   <width>502</width>
		   <height>62</height>
		   <font>font40</font>
		   <align>left</align>
		   <aligny>center</aligny>
		   <label>$INFO[ListItem.Label]</label>
		   <textcolor>white</textcolor>
		   <selectedcolor>DD171717</selectedcolor>
		   <scroll>true</scroll>
		   <scrollspeed>30</scrollspeed>
	       </control>
	    </focusedlayout>
	    <content type="url" url="rss://yourdomain.com/yourfeed.rss">
	    </content>
	</control>
        <control type="group">
           <control type="image">
              <visible>true</visible>
              <posx>635</posx>
              <posy>265</posy>
              <width>560</width>
              <height>230</height>
              <texture>$INFO[Container(100).ListItem.Thumb]</texture>
           </control>
           <control type="label">
              <visible>true</visible>
              <posx>635</posx>
              <posy>500</posy>
              <width>560</width>
              <height>115</height>
              <font>light23</font>
              <align>left</align>
              <aligny>center</aligny>
              <label>[B]Description:[/B] $INFO[Container(100).ListItem.property(description)]</label>
              <background>grey</background>
              <textcolor>white</textcolor>
              <wrapmultiline>true</wrapmultiline>
           </control>
         </control>
      </control>
   </controls>
</window>

And thus concludes the basic construction of our first app – we only have two more steps to go!

Building Your First App: Animation
12 November 2009 by Rob Spectre
This entry is part 8 of 9 in the series Building Your First App

We’re almost there with the penultimate step in building your first Boxee application. In the last installment, we finished the construction of the application by finishing the metadata box. In this step, we’ll do our last round of polish before we’re ready for the best step of all – release!

Animation is the crucial last polish that can really make your application shine and is super easy to add. For our app, we are going to add a nice theater-light style fade in for the active elements of our interface while the application loads. This can be accomplished by applying an animation element to our list container and metadata box. Let’s take a look at what that element looks like:

1
2
3
<animation type="Conditional" condition="Window.IsVisible(DialogProgress.xml)">
   <effect type="fade" start="100" end="20" time="200"/>
</animation>

In this element we are doing two things – setting a condition and setting an effect. The condition is set with the animation element telling Boxee to render the animation when certain criteria are met. In this case, we are defining the condition as the visibility of Boxee’s default “loading clock” animation.

We then define what kind of animation with the effect element. Here we put the attributes of how we would like this animation to behave.

type
There are many animation effects available within Boxee; the type attribute defines which one we want. As mentioned before, we are using a “fade” animation for our first app.

start / end
The start and end attributes have deceiving names for their function in a fade animation. For this effect, start and end are the values we are setting for opacity at the beginning and end of the animation. So if we input the values “100″ and “20,” we are telling Boxee to render a fade effect that changes the interface object’s opacity from 100% (fully solid) to 20% (nearly transparent).

time
The time attribute defines the interval of the animation in milliseconds. With “200″ as our value, we are telling Boxee to fade the interface object from 100% to 20% in 0.2 seconds.

With our animation element defined, we need to just add it to the controls we wish to fade. Adding an animation is as simple as including the animation element to the control we wish to animate. First we’ll start with the image control that provides the background of the list container.

1
2
3
4
5
6
7
8
9
10
<control type="image">
	<animation type="Conditional" condition="Window.IsVisible(DialogProgress.xml)">
	   <effect type="fade" start="100" end="20" time="200"/>
	</animation>
	<posx>60</posx>
	<posy>230</posy>
	<width>502</width>
	<height>416</height>
	<texture>list.png</texture>
</control>

Now when we start our application, we can see that while Boxee loads our RSS feed, the list container background does a neat theater fade. To give the entire app that same polished look we will need to add the effect also to the metadata box’s image control, the list container, and the group control containing our metadata objects.

Here’s our final main.xml now fully animated:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
<?xml version="1.0"?>
   <window type="window" id="14000">
   <defaultcontrol always="true">100</defaultcontrol>
   <allowoverlay>no</allowoverlay>
   <controls>
      <control type="group">
          <control type="image">
             <posx>0</posx>
             <posy>0</posy>
             <width>1280</width>
             <height>720</height>
             <texture>bg.png</texture>
          </control>
          <control type="image">
             <animation type="Conditional" condition="Window.IsVisible(DialogProgress.xml)">
	         <effect type="fade" start="100" end="20" time="200"/>
	     </animation>
             <posx>60</posx>
             <posy>230</posy>
             <width>502</width>
             <height>416</height>
             <texture>list.png</texture>
         </control>
         <control type="image">
             <animation type="Conditional" condition="Window.IsVisible(DialogProgress.xml)">
	         <effect type="fade" start="100" end="20" time="200"/>
	     </animation>
             <posx>630</posx>
             <posy>255</posy>
             <width>574</width>
             <height>355</height>
             <texture>details.png</texture>
          </control>
          <control type="list" id="100">
           <animation type="Conditional" condition="Window.IsVisible(DialogProgress.xml)">
	       <effect type="fade" start="100" end="20" time="200"/>
	   </animation>
	   <posx>60</posx>
	   <posy>230</posy>
	   <width>502</width>
	   <height>416</height>
	   <orientation>vertical</orientation>
	   <itemlayout width="502" height="65">
	    <control type="label">
		<posx>0</posx>
		<posy>0</posy>
		<width>502</width>
		<height>62</height>
		<font>font40</font>
		<align>left</align>
		<aligny>center</aligny>
		<label>$INFO[ListItem.Label]</label>
		<textcolor>white</textcolor>
	    </control>
	    </itemlayout>
	    <focusedlayout width="502" height="65">
	       <control type="image">
		   <posx>0</posx>
		   <posy>0</posy>
		   <width>502</width>
		   <height>65</height>
		   <texture>white.png</texture>
		   <colordiffuse>DD171717</colordiffuse>
	       </control>
	       <control type="label">
		   <visible>!Control.HasFocus(100)</visible>
		   <posx>0</posx>
		   <posy>0</posy>
		   <width>502</width>
		   <height>62</height>
		   <font>font40</font>
		   <align>left</align>
		   <aligny>center</aligny>
		   <label>$INFO[ListItem.Label]</label>
		   <textcolor>white</textcolor>
		   <selectedcolor>DD171717</selectedcolor>
	       </control>
	       <control type="label">
		   <visible>!Control.HasFocus(100)</visible>   
		   <posx>0</posx>
		   <posy>0</posy>
		   <width>502</width>
		   <height>62</height>
		   <font>font40</font>
		   <align>left</align>
		   <aligny>center</aligny>
		   <label>$INFO[ListItem.Label]</label>
		   <textcolor>white</textcolor>
		   <selectedcolor>DD171717</selectedcolor>
		   <scroll>true</scroll>
		   <scrollspeed>30</scrollspeed>
	       </control>
	    </focusedlayout>
	    <content type="url" url="rss://yourdomain.com/yourfeed.rss">
	    </content>
	</control>
        <control type="group">
           <animation type="Conditional" condition="Window.IsVisible(DialogProgress.xml)">
	      <effect type="fade" start="100" end="20" time="200"/>
           </animation>
           <control type="image">
              <visible>true</visible>
              <posx>635</posx>
              <posy>265</posy>
              <width>560</width>
              <height>230</height>
              <texture>$INFO[Container(100).ListItem.Thumb]</texture>
           </control>
           <control type="label">
              <visible>true</visible>
              <posx>635</posx>
              <posy>500</posy>
              <width>560</width>
              <height>115</height>
              <font>light23</font>
              <align>left</align>
              <aligny>center</aligny>
              <label>[B]Description:[/B] $INFO[Container(100).ListItem.property(description)]</label>
              <background>grey</background>
              <textcolor>white</textcolor>
              <wrapmultiline>true</wrapmultiline>
           </control>
         </control>
      </control>
   </controls>
</window>

For more information on animating your Boxee app, refer to this excellent guide for Xbox Media Center.

Only one step left – release!

Building Your First App – Release It!
13 November 2009 by Rob Spectre
This entry is part 9 of 9 in the series Building Your First App

At long last, we are at the final step of building your first Boxee application – release!  After designing, coding and debugging our app we’re ready to release it in the wild by submitting it to Boxee for inclusion in the App Box.

The App Box is similar to the iTunes App Store developers are familiar with for the iPhone.  It is the default repository for all Boxee software, all fully tested and confirmed to work on the platforms for which it is submitted.  The submission process, however, is far less intrusive than Apple’s and ultimately produces the highest quality experience for the Boxee community of 700,000 users.   Plus the submission process gets your app tested on hardware profiles you likely don’t have access to – a huge plus to guarantee your app looks good on all the devices running Boxee.

Let’s get started submitting the app we just built.

1) Make an App Thumbnail

The app thumbnail is what users see in the App Box as the icon to install your app.  Naturally, our app thumbnail should concisely represent what kind of content the app contains and should attract users to install it. The thumbnail should be 200×200 and placed in the Internet accessible location we defined in the <em>thumb</em> element of our <em>descriptor.xml</em>.

The standard background for a Boxee App thumbnail

If you would like to conform to the look of the rest of the App Box (always a good idea), you can use this black image as a background.

1) Zip up the app

All Boxee repositories distribute apps through zip files.  In order to speed up the review of your app, you can zip up your app so that it is ready to go for the quality assurance folks who will be putting your app through the paces. First we navigate to the <em>apps</em> directory in your local Boxee UserData folder and identify the folder containing our app – it should be the same as the <em>userid</em> we defined in our <em>descriptor.xml</em>.

Then zip the file with the convention <em>appid-version.zip</em>.  For example, if we were submitting Auto-Tune The News for the App Box, we would name our zip file <em>autotunethenews-1.0.zip</em>.

Note: Be sure to remove the <test-app> element from your descriptor.xml before submitting!

2) Sign up for Boxee JIRA

Before sending your zip file to Boxee for consideration, you need to sign up for an account in Boxee’s bug management software.  This will allow Boxee to get a hold of you in the event of any problems as well as use JIRA to submit your app.  You can sign up at http://jira.boxee.tv.

3) Follow the Application Submission Process

Once you’ve signed up on JIRA, you’re ready to start Boxee’s Application Submission Process.  Just hop on the developer wiki page linked here and you’re on your way!

When submitting your app to the Boxee App Box, expect that it will take 3-4 business days for your app to get checked by Boxee QA.  With over a dozen apps in the App Box, it is a process with which I have gained intimate familiarity and can offer a few tips to make your submission sail.

  • Debug Your App - Make sure you click on every button and every video in your app at least once.  Boxee QA will definitely be doing the same and you can save yourself (and them) a cycle of iteration by doing it yourself.
  • 1280×720 – Be sure you are always developing in a windowed Boxee client.  This will make Boxee default to 720p, which will ensure your app looks the best on all screens.  You can window your Boxee client by pressing the “\” key after you start.
  • 480i - Make sure your video is at least 480i quality.  If it’s not good enough for TV, it’s not good enough for Boxee.

Finally, there is one last step:

4) Tell people!

Be sure to post on the forums, your own blog and, if you would do me the courtesy, here on gonzee.tv to let the world know that you just published your first Boxee app!  Cable packages only get a few new channels a year – Boxee gets dozens of new apps a month.

Get on Twitter, Facebook, Cliqset, and every corner of the Internet to let them know you’re tired of television and ready to change the living room with your first Boxee app.

»  Substance: WordPress   »  Style: Ahren Ahimsa
© 2009, all rights reserved.