Thursday, November 20, 2008

OpenStreetMap rendering in Silverlight

So the other part of OSM I wanted to look at was the feasibility of writing a Silverlight client for the OSM data. So the OSM render of New Malden, UK looks likes:

and my first attempt (mostly guessing what things should look like and be layered) looks like:

which obviously is not as good as the XSLT/SVG renderer for OSM - however I only spent a day on it. A few things I learnt, 1) the OSM renderer is doing some nice joins on street junctions 2) the OSM format is not complex, but its not documented (not to a great detail).

The New Malden data set is 1.2mb, and the silverlight code generates 976 Polylines and 178 Polygons, and it renders in 0.11 seconds.

So what does this all mean? for one, I like the OSM format, and we can build primitive data type into the system based on Node, Way and Relation to makes life easy and consistent with the OSM view. However I need a higher level model to interpret this data. That way the primitives can stay flexible and "dumb", whilst the high level can focus on routes and joins etc.

The method I used to process the data into UI elements is based on the following concept. I create a top level tile to put all the items into, and then I create PolyLines or Polygons using just ways (I don't process relations yet). I use a simple fixed formulae to map the node GPS points into X,Y (not correct or proportional - but close enough to visualize). I use Polygons for ways the end at the same location as its start, and PolyLines for everything else. I use the tag field on the ways to decide the fill or stroke colour, and set the z-index based on the same model.

The effect of creating a top level tile is that I can pan the whole of New Malden but just moving the tile, rather than having to move each item individually. It also means I can use multiple tiles to build the map, and cache them for performance (data retrieve rather than draw as at 0.11 seconds/tile I'm not worried yet)

Once I have abstracted the code into the two clean levels (primitive and map) I will post the code - at the moment it's too much of a hack (and the GPS conversion is very, very wrong)

No comments: