Travels

Wednesday, June 11, 2008

WeatherBug API: A lesson in XML


Recently I was asked to make a WeatherBug widget for my company's local intranet. Making the widget was easy enough, I wrote a class that connects to WeatherBug and retrieves the current weather conditions. The tricky part was parsing the XML in Flash since it has many levels of nested nodes and some of those nodes use a namespace. Because it took me a while to work through parsing the XML I've decided to make my code open source.

The WeatherBug class and the .fla file I've made which demonstrates its use may be downloaded here: http://sizzlepopboom.com/open_source/weatherbug.zip
You can see the widget in action here:
http://sizzlepopboom.com/open_source/weatherbug.html

Don't forget to register to get you WeatherBugAPI Key and put it in the WeatherBug.as file otherwise it will not work.

Here's a bit of advice on traversing the XML. There are three main issues I encountered in parsing my XML: 1. How do you access nodes within a namespace?, 2. How do you access nodes with names that use restricted characters?, 3. What's an easy way to traverse the XML without having to know the entire heirarchy of a node?

Here are my answers:
1. To access nodes within a namespace make a namespace object for the XML you are using:
ex: var weatherNS:Namespace = new Namespace("http://www.aws.com/aws");

Then use the format:
namespace::nodeName
namespace::@attributeName
ex: var highTemp = weatherXML..weatherNS::["temp-high"];

Here's a tricky one to show you an attribute "hour-24" within the node "hour":
ex: var riseHour = weatherXML..weatherNS::sunrise..weatherNS::["hour"].@["hour-24"];

2. Use brackets when you are trying to access nodes whose names use reserved characters; in fact if you want you can use brackets for regular names to if you want things to look consistent.
ex: var monthlyRain = weatherXML..weatherNS::["rain-month"];
var link = weatherXML..image["link"]; //without a reserved character

3. Use .. to search through the entire XML document without knowing the exact heirarchy; this is similar to the // used in XPath
ex: var link = weatherXML..image["link"];
var monthlyRain = weatherXML..weatherNS::["rain-month"]; //within a namespace

-When you are using .. be sure to check your results, if there are multiple nodes with the same name within an XML document you might end up with the values of several nodes. When there are multiple nodes, be sure to reference the parent of your target node to ensure you get only its value as a result. See the link tag in the example above.

Hopefully this helps you solve any of the tricky problems you may have using WeatherBug's API. If you do have more questions about using XML in Flash look at the source code I've provided and check out these sites:
http://www.kirupa.com/developer/flashcs3/using_xml_as3_pg1.htm
http://livedocs.adobe.com/flash/9.0/ActionScriptLangRefV3/XML.html

plus there is a whole chapter on XML in Colin Moock's excellent book: Essential Actionscript 3


















Now that you know how to get WeatherBug information into Flash, I'd like to suggest some interesting ways you might be able to use the information.


I come from a background of making games so I've been intrigued with the idea of using real-world information in the form of XML feeds (like WeatherBug's) to control and influence elements within a game. The first thing I thought of was getting the current weather conditions and then replicating them within the world of the game. If you are playing on a rainy day, it will be raining in the game world. This becomes more interesting if you have characters, abilities, paths that are effected by the weather. A character could act more depressed if it's raining. Electric shock powers would be more powerful in very dry weather and more conductive in rainy weather. A path over a bridge could be flooded and inaccessible on rainy days.

Weather could also be used to drive a game's economy (especially in agrarian societies). Good weather means higher yield of crops and lower prices. This way you would have realistic variation in your economy without having to make it very intelligent.

Weather patterns can also be used to make cultural assumptions which can be useful in increasing the immersion of a player in the game. For example, if there has been a heavy snow children in a game might be staying at home instead of at school. The children would act happier being able to play all day and the adults would be more stressed from dealing with increased traffic. If the temperature has been exceptionally high characters in the game might go swimming more and as a consequence be tanner or sun-burnt. As you see, many assumptions can be made by analyzing weather patterns. Using these assumptions in a game environment will create much more realistic patterns of behavior with less complex AI. The use of weather information and the assumptions that can be made by analyzing it will greatly increase the sense of immersion in games as well as the overall cool factor of games seeming to know about the real world around it.

If you are interested in parsing weather conditions with WeatherBug's feed here's a link to all the possible weather descriptions:

http://weather.weatherbug.com/corporate/products/API/Cond_Icon_Desc.txt


There are about 178 possible descriptions so here is my suggestion for parsing the information to something more manageable:

Use indexOf to search a string for:
Cloud

Snow
Frozen
Flurry
Sleet

Rain
Storms
Thunder
Showers

Windy

Fog

Hazy

Clear

Searching for these words ought to give you a fair idea of what the weather is doing in most of the 178 different options. You can use sunny as the default weather.

No comments: