Creating a dynamic theme for Windows 7

If you want only the juicy part of this article, install the theme here

Windows 7 comes with a pretty neat theme manager, in which you can make your computer switch between a number of wallpapers on your drive or choose a theme you downloaded from Microsoft’s site (which comes with their own wallpapers too).

That’s fine enough if you have a lot of wallpapers and is okay with seeing about 10 different walls repeating from day to day… I don’t. That’s why I liked Bing Dynamic theme the most. What made this theme unique is, it fetches fresh wallpaper from Microsoft’s server everyday. This way I don’t have to see the same wallpapers over and over, and I don’t have to download the wallpapers first either. In case you didn’t know, downloading wallpapers is a tedious task:

  • It took at least two clicks from the wallpaper’s page to download the wallpaper you want (click download, choose the size).
  • You have to do this to each wallpaper you like.
  • You must have seen the wallpaper first, which ruins the surprise element.

The dynamic theme fixed those problems, you don’t have to do any browsing. The downside is, there’s only one such dynamic theme, and you can’t decide on the images. First, let’s have a look at the interesting part in the theme’s content (you can view the theme by opening it with notepad)

[Slideshow]
Interval=1800000
Shuffle=1
RSSFeed=http://themeserver.microsoft.com/default.aspx?p=Bing&c=Desktop&m=en-US
[boot]
SCRNSAVE.EXE=

You can see this theme fetches data from Microsoft’s server. It’s kinda RSS, but somewhat non-standard, Windows reads the enclosure element for the wallpaper instead of the link element like the standard (Microsoft loves breaking standards, this is why Internet Explorer is so hated among web developers).

Standard image RSS from NASA

<image xmlns:java_code="xalan://gov.nasa.build.Utils1"> 
    <url>http://www.nasa.gov/images/content/491481main_2010-5278-4x3_516-387.jpg</url> 
    <title>A Break in Training</title> 
    <link>http://www.nasa.gov/multimedia/imagegallery/index.html</link> 
    <description/> 
</image> 

Microsoft’s feed

        <item>
            <guid>Pipefish1920x120010-19-2010 7_57_11 PM3ed6bc33-88cb-4872-8097-5077cb6ad1a5</guid>
            <title>Pipefish1920x120010-19-2010 7_57_11 PM</title>
            <link ref="http://themeserver.microsoft.com/themeserver//Bing/Desktop/en-US/Images/Pipefish1920x120010-19-2010 7_57_11 PM.JPG" />
            <enclosure url="http://themeserver.microsoft.com/themeserver//Bing/Desktop/en-US/Images/Pipefish1920x120010-19-2010 7_57_11 PM.JPG" type="image/JPG" />
            <description>Picture for Bing, Desktop, en-US Theme.</description>
            <pubDate>10/19/2010 7:57:11 PM</pubDate>
        </item>

Actually, I think some engineer at Microsoft got mixed up between RSS (<item>) and Atom (<image>, <enclosure>) and created such an embarrassing feed. So you can’t just feed images from your favourite sites (like, cat images from flickr) right to your desktop.

Thankfully, we have just the tool for that: Yahoo pipes. It takes information from somewhere on the internet, transform it according to your specification, and is capable of exporting through RSS, JSON or PHP code.

So, I wanted to create a theme with images fed from xkcn.info (an image site about Vietnamese girls :p), I took the feed, feed it into the pipes. The pipes is a bit hard to use, because it cannot convert a XML element into string and vice versa, so you can’t just parse those neatly formatted elements but instead have to rely on the power of regular expression.

The pipe

  1. The first block fetches the feed
  2. The second block copy the data we need so we don’t mess up with existing stuff
  3. The third block removes all the text from the description and leaves only the first <img> tag
  4. The fourth block build a RSS feed formatted according to Microsoft “standard”

You can view the pipe here, and the RSS output of the pipe is here. So now all that remain is copy the Microsoft theme over, replace the feed URL and voilà, a more and more beautiful desktop everyday 😉

Desktop fully fed 😉

Download the theme here.

I have also created a Flickr-fed pipe and theme. To customize, clone the pipe, change it according to Flickr’s feed specification , modify the address in the theme to your pipe’s RSS output and you are set to go!

A readable example of how code become unreadable

Consider the following problem: You need to calculate how many dots are there in a square triangle for a specific width, for example

.
..
...

Has an area of 6

.
..
...
....

Has an area of 10
The catch is, you are not allowed to use the mathematical formula to calculate the number instantly, so there’s two ways remaining to solve this problem:

  • Use two for loops
  • Recursion

We will follow the second direction because it’s probably shorter to write, so someone wrote

public class TrianglePrinter {
    static int getTriangleArea(int width) {
        int result = 0; // Default return
        if (width > 0) { // Stop condition
            result = getTriangleArea(width - 1) + width; // Split the problem
        }
        return result;
    }

    public static void main(String[] args) {
        System.out.println(getTriangleArea(4));
    }
}

This can be “optimized” to become a one-line method, short code gives longer lives!

public class TrianglePrinter {
    static int getTriangleArea(int bottomWidth) {
        return (bottomWidth > 0) ? getTriangleArea(bottomWidth - 1) + bottomWidth : 0;
    }

    public static void main(String[] args) {
        System.out.println(getTriangleArea(4));
    }
}

Then when it is compacted (like, in Javascript…)

public class TrianglePrinter {
    static int g(int w) {
        return (w > 0) ? g(w - 1) + w : 0;
    }

    public static void main(String[] args) {
        System.out.println(g(4));
    }
}

Fooling around with the Office Assistant

I seem to have a special bond with ancient stuff. I were doing Pascal when C++ and WinForm was at their prime. Now I’m toying with a discontinued Microsoft Office feature. I just can’t help it, I have to work with Office 2003 around the clock since the upper IT management takes about a decade to certify a new software as “compatible”. Well, working for a big corporation has its pros and cons and we all have to cope with them.

I don’t feel the Office assistant intrusive though, it certainly doesn’t get in your way if you turn it off, but oh well, only when you know how. (Which, sadly, is not the case for many computer users). And I don’t think we can just let the woman take it from us. Gdzie jest czcionka? 😉

When I was in 7th grade or something. I read an article on PCWorld Vietnam about how to manipulate the Office Assistant. I diligently typed the code (in VBA) character-by-character without even understanding them :P. Nevertheless, the result was really satisfying, I were able to make the cat  (Links, an office assistant character) jump through hoops (literally).

Okay, enough trivia! I don’t remember any function from back then so I’ll have to start over. I have done various applications inter-operating with Microsoft Office’s VBA before, so I guess it would be an easy task. I added the Microsoft Excel’s object library to my  C# project and search for “assistant”. Lucky me, something popped up.

Assistant class in object browser

As you may see, it’s a child of the application class so you’ll have to start an Office application first. I chose Excel because it’s the application I have been working with the most. For aesthetics reasons, I tried to hide the Application’s window but that will hide the assistant too :(.  Apart from that, thanks to the well-built COM interface, initialize and display the assistant is easy.

using Microsoft.Office.Interop.Excel;
...
ApplicationClass Test = new ApplicationClass();
Test.Assistant.On = true;
Test.Assistant.Visible = true;

In case you are wondering, ApplicationClass is used to control Excel. All the possible action of “Assistant” is neatly listed within an enum so I just have to convert those to text and list them for the user to choose. No button-to-button editing for each action required!

 foreach (string TypeName in Enum.GetNames(typeof(Microsoft.Office.Core.MsoAnimationType)))
 {
     listBox1.Items.Add(TypeName);
 }

Because you can only see the Office Assistant when the host Office application has focus, I made a timer so the assistant will do the same action over and over, so the user can switch to the relevant application.

        private void timer1_Tick(object sender, EventArgs e)
        {
            Microsoft.Office.Core.MsoAnimationType[] Temp = (Microsoft.Office.Core.MsoAnimationType[])Enum.GetValues(typeof(Microsoft.Office.Core.MsoAnimationType));
            if (listBox1.SelectedIndex >= 0)
            {
                Test.Assistant.Animation = Temp[listBox1.SelectedIndex];
                Test.Visible = true;
            }
        }

"Get techy" with Rocky :p

You can also make the assistant say stuff you want:

 private void button1_Click(object sender, EventArgs e)
 // I created a button and a TextBox
 // When you enter some text into the TextBox and click the button, the
 // assistant will make a speech balloon with the text in it
 {
   timer1.Enabled = false;
   MessageBox.Show("Switch to Excel after clicking OK");
   System.Threading.Thread.Sleep(2000);
   Microsoft.Office.Core.Balloon Speech = Test.Assistant.NewBalloon;
   Speech.Heading = "Test balloon";
   Speech.Text = textBox1.Text;

   Speech.Mode = Microsoft.Office.Core.MsoModeType.msoModeModal;
   Speech.Show();
   timer1.Enabled = true;
 }

Bark!

So if you are still stuck with Office 2003 and wanted to play around with it a bit, here’s the compiled application (requires .NET 2.0 and Microsoft Office 2003 installed) and for those who want the code, here it is.

KTouch lession maker

Some of you might have landed on this article searching for the book instead, here it is 🙂

I have been trying to improve my typing by learning Dvorak and so far I’ve been to be able to type more accurately (I’m not talking about speed here :p). I have been using the Grass Soft touch typing program to train on Windows, it is pretty useful except for the limited word list. They claimed that they have included 500 most used word in English. That just doesn’t seem enough to me!

Besides, I have also started to use Linux and I needed a program that will keep me busy on the new platform. Of course in the open source world there’s always a lot of option too choose from, most of them are free too. I have chosen KTouch as it seems to be under active development and also endorsed by KDE.

KTouch with my customized lesson

So far, it’s a great program! It automatically detects your keyboard layout and select the appropriate starting lesson. It have two lesson for Dvorak: ABCD and computer generated. Despite the name, the computer generated lesson does not change as you take it because it’s just a file pre-rendered by the developer. I hit the same obstacle I did with the previous touch typing program: no variety.

Fortunately KTouch allows you to load external lesson files (they are just XML files) and text file; but due to poor application design, the text file won’t let you type the whole file but only the first few sentences. Which means if you want to practice with a long text, you’ll have to split them manually into multiple files.

<?xml version="1.0" encoding="utf-8"?><KTouchLecture>
<Title>Puzo, Mario - The Godfather.txt</Title>
<Comment>This is a lession created from Puzo, Mario - The Godfather.txt</Comment>
<FontSuggestions>Courier 10 Pitch</FontSuggestions>
<Levels>
<Level>
<LevelComment>level 1</LevelComment>
<NewCharacters>a lot :)</NewCharacters>
<Line>Chapter 1</Line>
<Line>Amerigo Bonasera sat in New York Criminal Court Number 3 and waited for</Line>
<Line>justice; vengeance on the men who had so cruelly hurt his daughter, who had</Line>
<Line>tried to dishonor her.</Line>
<Line>The judge, a formidably heavy-featured man, rolled up the sleeves of his black</Line>
<Line>robe as if to physically chastise the two young men standing before the bench.</Line>
</Level>
</Levels></KTouchLecture>

Structure of XML lesson files

So I made a program with C# to make KTouch lesson out of text files. Thanks to C#’s ability to process strings and XML, this has been a fairly easy task, here’s the code:

            const int LinePerLevel = 6;
            const int CharactersPerLine = 80;
            FileInfo Info = new FileInfo(Filename);
            string[] RawData = File.ReadAllLines(Filename, Encoding.Default);
            XmlTextWriter Writer = new XmlTextWriter(Filename + ".xml", Encoding.UTF8);
            Writer.WriteStartDocument();
            Writer.WriteStartElement("KTouchLecture");
            Writer.WriteRaw("rn");
            {
                Writer.WriteElementString("Title", Info.Name);
                Writer.WriteRaw("rn");
                Writer.WriteElementString("Comment", "This is a lession created from " + Info.Name);
                Writer.WriteRaw("rn");
                Writer.WriteElementString("FontSuggestions", "Courier 10 Pitch");
                Writer.WriteRaw("rn");

                Writer.WriteStartElement("Levels");
                Writer.WriteRaw("rn");
                {
                    int LevelCount = 1;
                    int LineCount = 0;
                    string[] LevelLines = new string[LinePerLevel];
                    string Buffer = "";
                    for (int i = 0; i < RawData.Length; i++)
                    {
                        string TrimmedLine = RawData[i].Trim();
                        if (string.IsNullOrEmpty(TrimmedLine))
                            continue;

                        TrimmedLine = TrimmedLine.Replace('“', '"');
                        TrimmedLine = TrimmedLine.Replace('”', '"');
                        TrimmedLine = TrimmedLine.Replace('’', ''');
                        TrimmedLine = TrimmedLine.Replace('‘', ''');
                        TrimmedLine = TrimmedLine.Replace("t", "");

                        if (Buffer.Length > 0 && (Buffer[Buffer.Length - 1] == '.' || Buffer[Buffer.Length - 1] == '?' || Buffer[Buffer.Length - 1] == '!'))
                            Buffer = Buffer + " " + TrimmedLine;
                        else
                            Buffer = Buffer + TrimmedLine;

                        while (LineCount < LinePerLevel && Buffer.Length > CharactersPerLine)
                        {
                            int CutOffSpacePos = Buffer.LastIndexOf(" ", CharactersPerLine - 1);
                            LevelLines[LineCount++] = Buffer.Substring(0, CutOffSpacePos);
                            Buffer = Buffer.Substring(CutOffSpacePos + 1);
                        }

                        if (Buffer.Length < = CharactersPerLine && LineCount < LinePerLevel)
                        {
                            LevelLines[LineCount++] = Buffer;
                            Buffer = "";
                        }

                        if (LineCount >= LinePerLevel)
                        {
                            Writer.WriteStartElement("Level");
                            Writer.WriteRaw("rn");
                            {
                                Writer.WriteElementString("LevelComment", "level " + LevelCount.ToString());
                                Writer.WriteRaw("rn");
                                Writer.WriteElementString("NewCharacters", "a lot :)");
                                Writer.WriteRaw("rn");
                                for (int j = 0; j < LevelLines.Length; j++)
                                {
                                    Writer.WriteElementString("Line", LevelLines[j]);
                                    Writer.WriteRaw("rn");
                                }
                            }
                            Writer.WriteEndElement();
                            LevelCount++;
                            LineCount = 0;
                        }
                    }

                    while (!string.IsNullOrEmpty(Buffer))
                    {
                        while (LineCount < LinePerLevel && Buffer.Length > CharactersPerLine)
                        {
                            int CutOffSpacePos = Buffer.LastIndexOf(" ", CharactersPerLine - 1);
                            LevelLines[LineCount++] = Buffer.Substring(0, CutOffSpacePos);
                            Buffer = Buffer.Substring(CutOffSpacePos + 1);
                        }

                        if (Buffer.Length < = CharactersPerLine && LineCount < LinePerLevel)
                        {
                            LevelLines[LineCount++] = Buffer;
                            Buffer = "";
                        }

                        if (LineCount >= LinePerLevel)
                        {
                            Writer.WriteStartElement("Level");
                            Writer.WriteRaw("rn");
                            {
                                Writer.WriteElementString("LevelComment", "level " + LevelCount.ToString());
                                Writer.WriteRaw("rn");
                                Writer.WriteElementString("NewCharacters", "a lot :)");
                                Writer.WriteRaw("rn");
                                for (int j = 0; j < LevelLines.Length; j++)
                                {
                                    Writer.WriteElementString("Line", LevelLines[j]);
                                    Writer.WriteRaw("rn");
                                }
                            }
                            Writer.WriteEndElement();
                            LevelCount++;
                            LineCount = 0;
                        }
                    }
                }
                Writer.WriteEndElement();
            }
            Writer.WriteEndElement();
            Writer.WriteEndDocument();
            Writer.Close();

It does:

  • Convert Unicode punctuations to their ordinary counterpart. For example “ and ” will be converted to “
  • Trim and combine different lines from different paragraphs to they’ll fit into the line format of KTouch. KTouch does not work well with long lines (you can’t see much toward the end of the line) so by default the line is trimmed at 80 characters

For a text source to practice, I decided to drop by project Gutenberg (FYI they digitize out-of-copyright books). They offer a range of about 3000 books in a dozen of languages to choose from. The books are mostly in plain text format, which is just perfect for this purpose.

The first novel I have chosen to type is Godfather by Mario Puzo 🙂 If you want to have a ride too then here’s the lesson maker’s source and here’s the lesson file for Godfather (note that due to bugs in KTouch, some characters toward the end of each lesson will disappear). The lesson file has over 2000 levels available for practicing.

Common overlooked Excel functions

My work is not mainly about Excel but people often come to me for solution to their everyday computing problems. Eventually after several months of repeating the same thing to many people, I decided to sum up all the questions and make a training session covering simple but many people just don’t know they existed in Excel.

I am not intending to teach people how to use Excel but how to use it efficiently. So my method is mostly visual-based: I use a lot of images to illustrate concepts so they can recall what I’ve said later easily. I intended to make some practice exercise to reinforce their knowledge too but my folks were strongly oppose against homework so that idea was abandoned :p

Introductory slide

The first session have 4 attendants, which I considered a successful experiment. It lasted for around 45 minutes and covered the following topics:

  • Quick count
  • Conditional counting
  • Counting with multiple conditions
  • Look-up functions
  • Error handling
  • Pivot tables
  • Data validation
  • Cell formatting
  • Visual Basic for Application basics

I intended to record the session for later broadcast but forgot it on that day. So if you are interested, here are the slides at screen resolution (72 dpi i.e. it look pretty crooked) together with notes in PDF format. Powerpoint file  is available upon request if you want to conduct similar sessions. I love to spread knowledge 🙂

Enjoy!