<?xml version='1.0' encoding='UTF-8'?><rss xmlns:atom='http://www.w3.org/2005/Atom' xmlns:openSearch='http://a9.com/-/spec/opensearchrss/1.0/' xmlns:georss='http://www.georss.org/georss' xmlns:gd='http://schemas.google.com/g/2005' xmlns:thr='http://purl.org/syndication/thread/1.0' version='2.0'><channel><atom:id>tag:blogger.com,1999:blog-2308969591514957062</atom:id><lastBuildDate>Sun, 15 Apr 2012 22:38:38 +0000</lastBuildDate><category>tile</category><category>Surface BruTile Eagle</category><category>osm</category><category>silverlight</category><category>brutile</category><category>projections</category><category>arcgis</category><category>gis</category><category>tms</category><category>sharpmap</category><category>LBG games</category><category>physics silverlight games</category><category>esri</category><category>tiling</category><category>openstreetmap</category><category>brutile silverlight</category><title>Paul says Hi!</title><description>Paul den Dulk's personal blog</description><link>http://pauldendulk.com/</link><managingEditor>noreply@blogger.com (Paul den Dulk)</managingEditor><generator>Blogger</generator><openSearch:totalResults>16</openSearch:totalResults><openSearch:startIndex>1</openSearch:startIndex><openSearch:itemsPerPage>25</openSearch:itemsPerPage><item><guid isPermaLink='false'>tag:blogger.com,1999:blog-2308969591514957062.post-5529612173831049566</guid><pubDate>Sat, 23 Apr 2011 07:52:00 +0000</pubDate><atom:updated>2011-04-23T01:09:21.620-07:00</atom:updated><title>Projecting from WGS84 to SphericalMercator</title><description>Projecting from one coordinate system to another is a big topic in the geo bizz. Most apps use comprehensive libraries to deal with all possible projections. These days 90% of the projections that I see are from WGS84 to SphericalMercator. Mostly this is GPS coordinates projected to a Google, Bing or OpenStreetMap tile background.  If you would like to keep it simple the code below would suffice (Thanks to &lt;a href="http://twitter.com/#!/geodeo"&gt;Steven Fruijtier&lt;/a&gt; for sharing the code).&lt;!-- code formatted by http://manoli.net/csharpformat/ --&gt;&lt;br /&gt;&lt;pre class="csharpcode"&gt;&lt;br /&gt;&lt;span class="kwrd"&gt;using&lt;/span&gt; System;&lt;br /&gt;&lt;span class="kwrd"&gt;using&lt;/span&gt; SharpMap.Geometries;&lt;br /&gt;&lt;br /&gt;&lt;span class="kwrd"&gt;namespace&lt;/span&gt; Projection&lt;br /&gt;{&lt;br /&gt;    &lt;span class="kwrd"&gt;public&lt;/span&gt; &lt;span class="kwrd"&gt;static&lt;/span&gt; &lt;span class="kwrd"&gt;class&lt;/span&gt; SphericalMercator&lt;br /&gt;    {&lt;br /&gt;        &lt;span class="kwrd"&gt;private&lt;/span&gt; &lt;span class="kwrd"&gt;readonly&lt;/span&gt; &lt;span class="kwrd"&gt;static&lt;/span&gt; &lt;span class="kwrd"&gt;double&lt;/span&gt; radius = 6378137;&lt;br /&gt;        &lt;span class="kwrd"&gt;private&lt;/span&gt; &lt;span class="kwrd"&gt;static&lt;/span&gt; &lt;span class="kwrd"&gt;double&lt;/span&gt; D2R = Math.PI / 180;&lt;br /&gt;        &lt;span class="kwrd"&gt;private&lt;/span&gt; &lt;span class="kwrd"&gt;static&lt;/span&gt; &lt;span class="kwrd"&gt;double&lt;/span&gt; HALF_PI = Math.PI / 2;&lt;br /&gt;&lt;br /&gt;        &lt;span class="kwrd"&gt;public&lt;/span&gt; &lt;span class="kwrd"&gt;static&lt;/span&gt; Point FromLonLat(&lt;span class="kwrd"&gt;double&lt;/span&gt; lon, &lt;span class="kwrd"&gt;double&lt;/span&gt; lat)&lt;br /&gt;        {&lt;br /&gt;            &lt;span class="kwrd"&gt;double&lt;/span&gt; lonRadians = (D2R * lon);&lt;br /&gt;            &lt;span class="kwrd"&gt;double&lt;/span&gt; latRadians = (D2R * lat);&lt;br /&gt;&lt;br /&gt;            &lt;span class="kwrd"&gt;double&lt;/span&gt; x = radius * lonRadians;&lt;br /&gt;            &lt;span class="kwrd"&gt;double&lt;/span&gt; y = radius * Math.Log(Math.Tan(Math.PI * 0.25 + latRadians * 0.5));&lt;br /&gt;&lt;br /&gt;            &lt;span class="kwrd"&gt;return&lt;/span&gt; &lt;span class="kwrd"&gt;new&lt;/span&gt; Point((&lt;span class="kwrd"&gt;float&lt;/span&gt;)x, (&lt;span class="kwrd"&gt;float&lt;/span&gt;)y);&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        &lt;span class="kwrd"&gt;public&lt;/span&gt; &lt;span class="kwrd"&gt;static&lt;/span&gt; Point ToLonLat(&lt;span class="kwrd"&gt;double&lt;/span&gt; x, &lt;span class="kwrd"&gt;double&lt;/span&gt; y)&lt;br /&gt;        {&lt;br /&gt;            &lt;span class="kwrd"&gt;double&lt;/span&gt; ts;&lt;br /&gt;            ts = Math.Exp(-y / (radius));&lt;br /&gt;            &lt;span class="kwrd"&gt;double&lt;/span&gt; latRadians = HALF_PI - 2 * Math.Atan(ts);&lt;br /&gt;&lt;br /&gt;            &lt;span class="kwrd"&gt;double&lt;/span&gt; lonRadians = x / (radius);&lt;br /&gt;&lt;br /&gt;            &lt;span class="kwrd"&gt;double&lt;/span&gt; lon = (lonRadians / D2R);&lt;br /&gt;            &lt;span class="kwrd"&gt;double&lt;/span&gt; lat = (latRadians / D2R);&lt;br /&gt;&lt;br /&gt;            &lt;span class="kwrd"&gt;return&lt;/span&gt; &lt;span class="kwrd"&gt;new&lt;/span&gt; Point((&lt;span class="kwrd"&gt;float&lt;/span&gt;)lon, (&lt;span class="kwrd"&gt;float&lt;/span&gt;)lat);&lt;br /&gt;        }&lt;br /&gt;    }&lt;br /&gt;}&lt;/pre&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/2308969591514957062-5529612173831049566?l=pauldendulk.com' alt='' /&gt;&lt;/div&gt;</description><link>http://pauldendulk.com/2011/04/projecting-from-wgs84-to.html</link><author>noreply@blogger.com (Paul den Dulk)</author><thr:total>0</thr:total></item><item><guid isPermaLink='false'>tag:blogger.com,1999:blog-2308969591514957062.post-42834302217089114</guid><pubDate>Wed, 28 Apr 2010 21:12:00 +0000</pubDate><atom:updated>2010-05-01T04:16:20.532-07:00</atom:updated><title>Tile schema compatibility</title><description>&lt;span class="Apple-style-span"   style="  ;font-family:arial;font-size:small;"&gt;&lt;div&gt;How easy is it to combine different tile services in one map? For instance, how easy is it to combine Google Maps aerial photos with a roads overlay from a TMS. Well this depends on two things, 1) how smart is the client, and 2) how compatible are the tile schemas. Here we look at several levels of compatibility taking the TMS specification as an example.&lt;/div&gt;&lt;div&gt;In TMS a tile schema is described in a TileMap. The main parameters involved are: &lt;/div&gt;&lt;div&gt;&lt;ul&gt;&lt;li&gt;&lt;b&gt;Origin&lt;/b&gt;: the coordinate where the first tile starts. It is the bottom left corner of tile (0, 0).&lt;/li&gt;&lt;li&gt;&lt;b&gt;BoundingBox&lt;/b&gt;: the extent in which tiles are available. The BoudingBox's bottom left coordinate is often identical to the origin but doesn't have to be.&lt;/li&gt;&lt;li&gt;&lt;b&gt;TileSets (levels)&lt;/b&gt;: a list of the available tile levels and their resolutions.&lt;/li&gt;&lt;/ul&gt;&lt;/div&gt;&lt;div&gt;&lt;b&gt;1) The same&lt;/b&gt;&lt;/div&gt;&lt;div&gt;Okay, lets keep this short, sometimes the schema's are just the same.&lt;/div&gt;&lt;div&gt;&lt;b&gt;2) In the same tile system&lt;/b&gt;&lt;/div&gt;&lt;div&gt;When the BoundingBox's are different but the Origin and TileSets are the same a tile in one schema will have the same x ,y and level as it's corresponding tile in the other schema. The only difference between the schema's is that some tiles can be available in one scheme but not in the other. &lt;/div&gt;&lt;div&gt;The two schemas can be said to be in the same tile system. If the TileSets are perceives as a Z-axis it forms a kind of three dimensional coordinate system for tiles. The origin of that space is defined by Origin.X, Origin.Y and the resolution of the first TileSet. The steps are defined by the tile width, tile height, the step size between resolutions (which can be irregular to complicate things). &lt;/div&gt;&lt;div&gt; &lt;/div&gt;&lt;div&gt;&lt;b&gt;3) Project to another tile system&lt;/b&gt;&lt;/div&gt;&lt;div&gt;When the tile system differs it is sometimes possible to transform a tile in one tile system to the other tile system. For instance when in one schema the Y-Axis is inverted with respect to the other it is easy to see how tile (0, 0) can be mapped to tile (0, count - 1). Such a trick is sometimes used in simple cases. I have not seen it done for more complicated relations. &lt;/div&gt;&lt;div&gt; &lt;/div&gt;&lt;div&gt;&lt;b&gt;4) Project to the map&lt;/b&gt;&lt;/div&gt;&lt;div&gt;When all parameters are different it is still possible to simply project the tiles to the map canvas not one tile onto another. The price is that you have to do this for every tile layer separately. This can hit performance and might consume more memory because more tile layers and possibly image containers will be needed  (depending on your client).&lt;/div&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/2308969591514957062-42834302217089114?l=pauldendulk.com' alt='' /&gt;&lt;/div&gt;</description><link>http://pauldendulk.com/2010/04/tile-schema-compatibility.html</link><author>noreply@blogger.com (Paul den Dulk)</author><thr:total>0</thr:total></item><item><guid isPermaLink='false'>tag:blogger.com,1999:blog-2308969591514957062.post-6550272107317139233</guid><pubDate>Wed, 07 Apr 2010 11:34:00 +0000</pubDate><atom:updated>2010-04-13T23:42:13.991-07:00</atom:updated><title>Porting SharpMap to Silverlight - first attempts</title><description>Over the last week I spend some time porting open source GIS library &lt;a href="http://sharpmap.codeplex.com/"&gt;SharpMap&lt;/a&gt; V1 to Silverlight. My intent was to go straight towards a working version in the easiest and quickest way and try to suppress my urge to redesign.  Below is how I worked through it. It might be relevant for those who have to do a similar port.&lt;br /&gt;&lt;br /&gt;&lt;div&gt;First, I removed all the files that I didn't need. I included only those that I needed to retrieve data (shapefiles) and render a map.&lt;/div&gt;&lt;div&gt;&lt;br /&gt;&lt;b&gt;System.Drawing&lt;/b&gt;&lt;br /&gt;Silverlight has no System.Drawing (GDI), so my next goal was to move this into a separate dll while maintaining all functionality. I created an IRenderer interface in SharpMap and used the existing GDI rendering for the implementation. I put this in a separate assembly called GdiRendering.dll.&lt;br /&gt;&lt;br /&gt;The IStyle class in SharpMap also depended on System.Drawing. I replaced all the System.Drawing classes in IStyle with implementation independent classes. These were converted to System.Drawing classes in the GdiRenderer.&lt;br /&gt;&lt;br /&gt;For raster renderers there was no separation between data retrieval and rendering at all. So I introduced an IRasterProvider and an IRaster class. In the GdiRenderer this IRaster type was treated in the same way as the geometry types.&lt;br /&gt;&lt;br /&gt;At that point all GDI was contained in the  GdiRenderer.dll and I could remove the System.Drawing dll from SharpMap. Everything worked like at the start. There was no WPF or Silverlight yet.&lt;/div&gt;&lt;div&gt;&lt;br /&gt;&lt;b&gt;System.Data&lt;/b&gt;&lt;br /&gt;Next was System.Data. There is none in Silverlight, so no DataTable or DataRow, yet the IProvider interface heavily depends on it. I spend some time looking for a good solution here. I was expecting to find some simple grid-like data structure, but I ended up using a List of FeatureDataRow for the table and derived FeatureDataRow from Dictionary. The downside here is there is no restriction on adding columns, you could add anything you like to it. I am open for better (and simple) solutions.&lt;br /&gt;&lt;br /&gt;&lt;b&gt;System.Xml&lt;/b&gt;&lt;br /&gt;With that settled I was about to set up a Silverlight data provider so I could start on my SilverlightRendering.dll. But which provider? It turns out that the current SharpMap data providers fall in into three categories:&lt;br /&gt;&lt;p&gt;&lt;/p&gt;&lt;ol&gt;&lt;li&gt;Raster. This would work just fine but my purpose was to implement vector rendering to SL, I had raster already working in &lt;a href="http://brutile.codeplex.com/"&gt;BruTile&lt;/a&gt;.&lt;/li&gt;&lt;li&gt;Vectors read from db or file. This is not allowed from the SL sandbox.&lt;/li&gt;&lt;li&gt;Vectors retrieved from web. That's what I need but it turns out they all depend on XmlDocument which is not part of Silverlight.&lt;/li&gt;&lt;/ol&gt;I worked around this problem by using WPF rendering and a file based data provider. I created two project files for my SilverlightRendering.dll, one SL, one WPF, that share the same files. I developed my renderer using the WPF version. So far I have only compiled my SL version, I have yet to find out if it actually works.&lt;br /&gt;&lt;br /&gt;&lt;b&gt;Finally Rendering&lt;/b&gt;&lt;br /&gt;With the WPF version of the SilverlightRendering.dll I managed to render Points, MultiPoints, LineStrings, MultiLineStrings, Polygons and MultiPolygons. I was happy to see that it is also possible to render Polygons with holes, this could have been a been a show stopper for a proper gis lib. The renderer currently ignores projections but there is a Silverlight version of proj.net on &lt;a href="http://projnet.codeplex.com/"&gt;http://projnet.codeplex.com&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;&lt;/div&gt;&lt;div&gt;So far it seems there are not many complications. I am currently investigating how I could use System.Data for the file and db data providers, while having a System.Data free Silverlight version. I believe it is possible to also support WPF and WinForms without too much maintenance. Support for Windows Phone 7 should be easy.&lt;/div&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/2308969591514957062-6550272107317139233?l=pauldendulk.com' alt='' /&gt;&lt;/div&gt;</description><link>http://pauldendulk.com/2010/04/first-experiments-in-porting-sharpmap.html</link><author>noreply@blogger.com (Paul den Dulk)</author><thr:total>1</thr:total></item><item><guid isPermaLink='false'>tag:blogger.com,1999:blog-2308969591514957062.post-8544787755583162631</guid><pubDate>Sun, 07 Feb 2010 20:24:00 +0000</pubDate><atom:updated>2010-02-07T14:54:48.818-08:00</atom:updated><title>BruTile's async tile fetcher</title><description>This morning I had some time to play around with powerpoint. Below is a diagram depicting how BruTile's tile fetcher works. The tile fetcher runs on a worker thread and fetches tiles from the web or the disk. The idea behind its setup was that the direct communication between the UI thread and the fetcher thread would be minimized. The only direct communication is a ViewChanged call to the fetcher, telling it the user is panning or zooming and a DataChanged callback telling the UI it should render. The fetcher dumps incoming tiles into the MemoryCache, which is just a big bag of tiles. The UI renderer retrieves whichever tiles it needs. &lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://4.bp.blogspot.com/_PjqxdklGCb4/S28hpdENGaI/AAAAAAAAC5A/p7CZ98toMl0/s1600-h/brutile_fetcher.png"&gt;&lt;img style="cursor:pointer; cursor:hand;width: 400px; height: 307px;" src="http://4.bp.blogspot.com/_PjqxdklGCb4/S28hpdENGaI/AAAAAAAAC5A/p7CZ98toMl0/s400/.png" border="0" alt=""id="BLOGGER_PHOTO_ID_5435600271320095138" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;Both the fetcher and the renderer can use all kinds of smart tricks. The fetcher can pre-fetch tiles based on its current view, or on the way the view changes over time. The renderer could search for alternative tiles (higher or lower levels) when the optimal tiles are not available. Those strategies should be tuned to support each other. For instance, in the current implementation the renderer uses higher level tiles when the optimal tiles are not available, and the fetcher pre-fetches higher level tiles to assist the renderer. But the way they play together is not specified in the interface. This loose coupling keeps things simple and flexible and the renderer never has to wait for the fetcher which results in a smooth (perceived) performance.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/2308969591514957062-8544787755583162631?l=pauldendulk.com' alt='' /&gt;&lt;/div&gt;</description><link>http://pauldendulk.com/2010/02/brutiles-async-tile-fetcher.html</link><author>noreply@blogger.com (Paul den Dulk)</author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://4.bp.blogspot.com/_PjqxdklGCb4/S28hpdENGaI/AAAAAAAAC5A/p7CZ98toMl0/s72-c/.png' height='72' width='72'/><thr:total>0</thr:total></item><item><guid isPermaLink='false'>tag:blogger.com,1999:blog-2308969591514957062.post-3666761796097055501</guid><pubDate>Sun, 07 Feb 2010 17:55:00 +0000</pubDate><atom:updated>2010-02-07T12:26:41.644-08:00</atom:updated><category domain='http://www.blogger.com/atom/ns#'>brutile silverlight</category><title>BruTile demo updated</title><description>A new version of Tim Ebben's Silverlight demo is up.&lt;br /&gt;&lt;br /&gt;&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://4.bp.blogspot.com/_PjqxdklGCb4/S28EEuMAWbI/AAAAAAAAC44/_TovAGePTZo/s1600-h/brutile_SL_0_4.png"&gt;&lt;img style="cursor:pointer; cursor:hand;width: 400px; height: 349px;" src="http://4.bp.blogspot.com/_PjqxdklGCb4/S28EEuMAWbI/AAAAAAAAC44/_TovAGePTZo/s400/brutile_SL_0_4.png" border="0" alt=""id="BLOGGER_PHOTO_ID_5435567754423851442" /&gt;&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;New features:&lt;br /&gt;&lt;ul&gt;&lt;li&gt;Fullscreen mode&lt;/li&gt;&lt;li&gt;Auto resize of map window&lt;/li&gt;&lt;li&gt;Bounding box zoom by using ctrl or 'bbox zoom' button.&lt;/li&gt;&lt;li&gt;Address finder using Tiny Geocoder&lt;/li&gt;&lt;/ul&gt;go have a &lt;a href="http://brutiledemo.appspot.com/"&gt;look&lt;/a&gt;.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/2308969591514957062-3666761796097055501?l=pauldendulk.com' alt='' /&gt;&lt;/div&gt;</description><link>http://pauldendulk.com/2010/02/new-version-of-tim-ebbens-silverlight.html</link><author>noreply@blogger.com (Paul den Dulk)</author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://4.bp.blogspot.com/_PjqxdklGCb4/S28EEuMAWbI/AAAAAAAAC44/_TovAGePTZo/s72-c/brutile_SL_0_4.png' height='72' width='72'/><thr:total>0</thr:total></item><item><guid isPermaLink='false'>tag:blogger.com,1999:blog-2308969591514957062.post-8166611577906711841</guid><pubDate>Sun, 31 Jan 2010 13:35:00 +0000</pubDate><atom:updated>2010-02-01T02:39:29.795-08:00</atom:updated><category domain='http://www.blogger.com/atom/ns#'>brutile</category><category domain='http://www.blogger.com/atom/ns#'>projections</category><category domain='http://www.blogger.com/atom/ns#'>osm</category><category domain='http://www.blogger.com/atom/ns#'>esri</category><category domain='http://www.blogger.com/atom/ns#'>arcgis</category><title>ArcBruTile released</title><description>Last week Bert Temme released &lt;a href="http://arcbrutile.codeplex.com/"&gt;ArcBruTile&lt;/a&gt; 0.1.6. This is a plugin for ArcGIS which uses BruTile to show tile layers in ArcGIS. This allows for an easy way to show openstreetmap data in ArcGIS which became very relevant due to it use in the Haiti crisis. &lt;br /&gt;&lt;br /&gt;What I like so much about ArcBruTile is that it is connecting OSS to the ESRI/Microsoft world. That was one of the purposes we had in mind when creating BruTile and this is the perfect example. An added bonus is that we can now use the projection capabilities in ArcGIS on our tile layers, something that won't be possible with our C# OSS tools soon.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/2308969591514957062-8166611577906711841?l=pauldendulk.com' alt='' /&gt;&lt;/div&gt;</description><link>http://pauldendulk.com/2010/01/arcbrutile-released.html</link><author>noreply@blogger.com (Paul den Dulk)</author><thr:total>0</thr:total></item><item><guid isPermaLink='false'>tag:blogger.com,1999:blog-2308969591514957062.post-8743864107834809250</guid><pubDate>Sat, 26 Dec 2009 11:09:00 +0000</pubDate><atom:updated>2009-12-26T03:13:17.876-08:00</atom:updated><title>new BruTile Silverlight demo</title><description>This month Tim Ebben created a very nce new Silverlight demo. We have put a live demo &lt;a href="http://brutiledemo.appspot.com/"&gt;here &lt;/a&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/2308969591514957062-8743864107834809250?l=pauldendulk.com' alt='' /&gt;&lt;/div&gt;</description><link>http://pauldendulk.com/2009/12/new-brutile-silverlight-demo.html</link><author>noreply@blogger.com (Paul den Dulk)</author><thr:total>0</thr:total></item><item><guid isPermaLink='false'>tag:blogger.com,1999:blog-2308969591514957062.post-4792038471361534115</guid><pubDate>Sat, 22 Aug 2009 12:02:00 +0000</pubDate><atom:updated>2010-02-07T10:29:00.286-08:00</atom:updated><category domain='http://www.blogger.com/atom/ns#'>brutile</category><category domain='http://www.blogger.com/atom/ns#'>silverlight</category><category domain='http://www.blogger.com/atom/ns#'>gis</category><title>BruTile Silverlight</title><description>I added a POC of &lt;a href="http://brutile.codeplex.com/SourceControl/ListDownloadableCommits.aspx"&gt;BruTile in Silverligh&lt;/a&gt;t, and now I need a site to host the demo in, and why not do it right here:&lt;br /&gt;&lt;br /&gt;Update: I added animated zoom.&lt;br /&gt;&lt;br /&gt;Update2: The hosting site, &lt;a href="http://silverlight.live.com/"&gt;http://silverlight.live.com/&lt;/a&gt; has ended its services. We have looked at Azure for an alternative, but unfortunately they offer only paid hosting. Our most recent demo is hosted at google &lt;a href="http://brutiledemo.appspot.com"&gt;app engine&lt;/a&gt; instead.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/2308969591514957062-4792038471361534115?l=pauldendulk.com' alt='' /&gt;&lt;/div&gt;</description><link>http://pauldendulk.com/2009/08/brutile-silverlight.html</link><author>noreply@blogger.com (Paul den Dulk)</author><thr:total>4</thr:total></item><item><guid isPermaLink='false'>tag:blogger.com,1999:blog-2308969591514957062.post-5948705670848746807</guid><pubDate>Sat, 13 Jun 2009 21:40:00 +0000</pubDate><atom:updated>2009-06-13T15:44:14.828-07:00</atom:updated><category domain='http://www.blogger.com/atom/ns#'>Surface BruTile Eagle</category><title>BruTile on Surface progress</title><description>&lt;div&gt;Great to see the Microsoft Surface blog &lt;a href="http://blogs.msdn.com/surface/archive/2009/06/12/open-source-tiling-library-for-geo-data.aspx"&gt;mentioning&lt;/a&gt; the BruTile library. It refers to my &lt;a href="http://pauldendulk.com/2009/02/brutile-on-microsoft-surface.html"&gt;previous&lt;/a&gt; blog about our very first experience with the Surface back in februari. I am happy to say that since then the Surface team at &lt;a href="http://www.geodan.com/"&gt;Geodan&lt;/a&gt; has made a lot of progress building an application for disaster management as part of our &lt;a href="http://www.geodan.com/markets/public-order-and-safety/eagle/"&gt;Eagle suite&lt;/a&gt;. &lt;/div&gt;&lt;div&gt;&lt;br /&gt;&lt;/div&gt;&lt;div&gt;The movie below demonstrates some of its capabilities. Apart from BruTile it uses the &lt;a href="http://resources.esri.com/arcgisserver/apis/silverlight/"&gt;ERSI WPF&lt;/a&gt; controls and &lt;a href="http://blogs.msdn.com/virtualearth3d/"&gt;Bing Maps 3D&lt;/a&gt; as a secondary perspective.&lt;/div&gt;&lt;div&gt;&lt;br /&gt;&lt;object width="560" height="340"&gt;&lt;param name="movie" value="http://www.youtube.com/v/h5YxM0w4Jos&amp;amp;hl=nl&amp;amp;fs=1&amp;amp;"&gt;&lt;param name="allowFullScreen" value="true"&gt;&lt;param name="allowscriptaccess" value="always"&gt;&lt;embed src="http://www.youtube.com/v/h5YxM0w4Jos&amp;amp;hl=nl&amp;amp;fs=1&amp;amp;" type="application/x-shockwave-flash" allowscriptaccess="always" allowfullscreen="true" width="560" height="340"&gt;&lt;/embed&gt;&lt;/object&gt;&lt;br /&gt;&lt;/div&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/2308969591514957062-5948705670848746807?l=pauldendulk.com' alt='' /&gt;&lt;/div&gt;</description><link>http://pauldendulk.com/2009/06/brutile-on-surface-progress.html</link><author>noreply@blogger.com (Paul den Dulk)</author><thr:total>1</thr:total></item><item><guid isPermaLink='false'>tag:blogger.com,1999:blog-2308969591514957062.post-7814140693703159058</guid><pubDate>Wed, 18 Feb 2009 09:12:00 +0000</pubDate><atom:updated>2009-06-17T11:54:42.860-07:00</atom:updated><title>BruTile on the Microsoft Surface</title><description>Last month I had the fortune to work on one of the first &lt;a href="http://www.microsoft.com/surface"&gt;Surfaces&lt;/a&gt; shipped to Europe. To test the Surface SDK we wrote a basic map application with pan an zoom through touch. &lt;div&gt;&lt;br /&gt;&lt;/div&gt;&lt;div&gt;Using the Surface SDK's ScatterView control it was very easy to get some touch controlled objects on the app, like a layer control. For panning and zooming we had to do a little bit more work, since we are not moving the map control itself but need to redraw the content  instead. For this purpose the SDK provides the ManipulationProcessor. It is a little bit more coding but the documentation explains nicely how to do it. To top it off we added a little throw effect using the InertiaProcessor.&lt;/div&gt;&lt;div&gt;&lt;br /&gt;&lt;/div&gt;&lt;div&gt;Our first meeting with the Surface was very enjoyable. The SDK met all our needs so far. Here is a little movie colleagues Steven and Martijn made of our first app. &lt;/div&gt;&lt;div&gt;&lt;br /&gt;&lt;object width="480" height="295"&gt;&lt;param name="movie" value="http://www.youtube.com/v/Fawfagg-BIg&amp;amp;hl=en&amp;amp;fs=1"&gt;&lt;param name="allowFullScreen" value="true"&gt;&lt;param name="allowscriptaccess" value="always"&gt;&lt;embed src="http://www.youtube.com/v/Fawfagg-BIg&amp;amp;hl=en&amp;amp;fs=1" type="application/x-shockwave-flash" allowscriptaccess="always" allowfullscreen="true" width="480" height="295"&gt;&lt;/embed&gt;&lt;/object&gt;&lt;br /&gt;&lt;/div&gt;&lt;div&gt;&lt;br /&gt;&lt;/div&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/2308969591514957062-7814140693703159058?l=pauldendulk.com' alt='' /&gt;&lt;/div&gt;</description><link>http://pauldendulk.com/2009/02/brutile-on-microsoft-surface.html</link><author>noreply@blogger.com (Paul den Dulk)</author><thr:total>2</thr:total></item><item><guid isPermaLink='false'>tag:blogger.com,1999:blog-2308969591514957062.post-2763588139770595789</guid><pubDate>Wed, 18 Feb 2009 08:53:00 +0000</pubDate><atom:updated>2010-07-12T11:18:07.610-07:00</atom:updated><category domain='http://www.blogger.com/atom/ns#'>sharpmap</category><category domain='http://www.blogger.com/atom/ns#'>tiling</category><category domain='http://www.blogger.com/atom/ns#'>tms</category><category domain='http://www.blogger.com/atom/ns#'>brutile</category><category domain='http://www.blogger.com/atom/ns#'>gis</category><category domain='http://www.blogger.com/atom/ns#'>osm</category><category domain='http://www.blogger.com/atom/ns#'>openstreetmap</category><category domain='http://www.blogger.com/atom/ns#'>tile</category><title>BruTile tiling library</title><description>&lt;a onblur="try {parent.deselectBloggerImageGracefully();} catch(e) {}" href="http://2.bp.blogspot.com/_PjqxdklGCb4/SZvPYWzvlSI/AAAAAAAAByU/lYZhLhH6j28/s1600-h/BruTileWinFormsSample.PNG"&gt;&lt;/a&gt;Tiling is a way to store raster data as image tiles on a server so that they can be quickly retrieved by a client application. Examples of GIS clients that use tiling are &lt;a href="http://maps.google.com/"&gt;Google Maps&lt;/a&gt;, &lt;a href="http://maps.live.com/"&gt;Virtual Earth&lt;/a&gt; and &lt;a href="http://openlayers.org/"&gt;OpenLayers&lt;/a&gt;. The tiles themselves are really just images sitting on a server, like &lt;a href="http://khm1.google.com/kh?v=34&amp;amp;hl=en&amp;amp;x=269299&amp;amp;y=172367&amp;amp;z=19&amp;amp;s="&gt;this one&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;A while back I added tiling functionality to &lt;a href="http://www.codeplex.com/SharpMap"&gt;SharpMapV1&lt;/a&gt;. Last month I extracted the tiling code to put it into a separate library, &lt;a href="http://code.google.com/p/brutile/"&gt;BruTile&lt;/a&gt; (LGPL), so it can be reused in other projects, like &lt;a href="http://code.google.com/p/sharpmapv2/"&gt;SharpMapV2&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;With the BruTile library you can define the way the tiles are stored on the server (the TileSchema), request which tiles you need to fill a particular boundingbox up with tiles, and then retrieve those tiles from the server with a properly formatted request string. The rendering of the tiles is up to the client application. There are various protocols to store and retrieve tiles. The current implementation of BruTile only supports the &lt;a href="http://wiki.osgeo.org/wiki/Tile_Map_Service_Specification"&gt;Tms&lt;/a&gt; and &lt;a href="http://wiki.osgeo.org/wiki/WMS_Tiling_Client_Recommendation"&gt;WmsC&lt;/a&gt; protocol. I hope to support more protocols in the future like the OGC's &lt;a href="http://portal.opengeospatial.org/files/?artifact_id=23206"&gt;Wmts&lt;/a&gt;  and Microsoft's &lt;a href="http://msdn.microsoft.com/en-us/library/bb259689.aspx"&gt;Virtual Earth protocol&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;In the following example I describe how to draw a map onto a WinForms form using tiles.The sample uses the OpenStreetMap tile server which uses the Tms protocol. The result is the form below, no further interaction with the map is possible.&lt;div&gt; &lt;span class="Apple-style-span" style="color: rgb(0, 0, 238);font-size:33px;" &gt;&lt;img src="http://2.bp.blogspot.com/_PjqxdklGCb4/SZvPYWzvlSI/AAAAAAAAByU/lYZhLhH6j28/s320/BruTileWinFormsSample.PNG" alt="" id="BLOGGER_PHOTO_ID_5304061003505308962" style="display: block; margin: 0px auto 10px; text-align: center; cursor: pointer; width: 320px; height: 246px;" border="0" /&gt;&lt;/span&gt;&lt;div&gt;&lt;br /&gt;&lt;/div&gt;&lt;div&gt;First some prerequisites. To do rendering in WinForms you need to override the OnPaint&lt;br /&gt;&lt;pre class="csharpcode"&gt;&lt;br /&gt;&lt;span class="kwrd"&gt;protected&lt;/span&gt; &lt;span class="kwrd"&gt;override&lt;/span&gt; &lt;span class="kwrd"&gt;void&lt;/span&gt; OnPaint(PaintEventArgs e)&lt;br /&gt;{&lt;br /&gt;e.Graphics.DrawImage(buffer, 0, 0);&lt;br /&gt;}&lt;/pre&gt;&lt;br /&gt;In it we draw a bitmap buffer onto the window. This bitmap is initialized to the window's size in the constructor.&lt;br /&gt;&lt;pre class="csharpcode"&gt;&lt;br /&gt;buffer = &lt;span class="kwrd"&gt;new&lt;/span&gt; Bitmap(&lt;span class="kwrd"&gt;this&lt;/span&gt;.Width, &lt;span class="kwrd"&gt;this&lt;/span&gt;.Height);&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Everything else is done in the Load method. First a Transform class is created. This is used to calculate from screen positions to world coordinates and back. It is initialized to a center point somewhere in the Netherlands, a resolution wide enough to show the whole of the netherlands, and the width and height of the window. The transform class is not part of BruTile itself because something similar is already part of most GIS libraries.&lt;br /&gt;&lt;pre class="csharpcode"&gt;&lt;br /&gt;Transform transform = &lt;span class="kwrd"&gt;new&lt;/span&gt; Transform(&lt;span class="kwrd"&gt;new&lt;/span&gt; PointF(629816f, 6805085f), 1222.992452344f, &lt;span class="kwrd"&gt;this&lt;/span&gt;.Width, &lt;span class="kwrd"&gt;this&lt;/span&gt;.Height);&lt;/pre&gt;&lt;br /&gt;Next you need to define how the tiles on the server are stored. The tile scheme needs a lot of information. Luckily the Tms service publishes this information. In future versions of BruTile I would like to automatically parse this info so it need not be specified on the client. So here I wont go into detail about what it all means.&lt;br /&gt;&lt;pre class="csharpcode"&gt;&lt;br /&gt;&lt;span class="kwrd"&gt;private&lt;/span&gt; ITileSchema CreateTileSchema()&lt;br /&gt;{&lt;/pre&gt;&lt;pre class="csharpcode"&gt;  double[] resolutions = new double[] {     &lt;br /&gt;   156543.033900000, 78271.516950000, 39135.758475000, 19567.879237500, 9783.939618750,     &lt;br /&gt;   4891.969809375, 2445.984904688, 1222.992452344, 611.496226172, 305.748113086,     &lt;br /&gt;   152.874056543, 76.437028271, 38.218514136, 19.109257068, 9.554628534, 4.777314267,    &lt;br /&gt;   2.388657133, 1.194328567, 0.597164283};&lt;/pre&gt;&lt;pre class="csharpcode"&gt;  TileSchema schema = &lt;span class="kwrd"&gt;new&lt;/span&gt; TileSchema();&lt;/pre&gt;&lt;pre class="csharpcode"&gt;  schema.Name = &lt;span class="str"&gt;"OpenStreetMap"&lt;/span&gt;;&lt;br /&gt; &lt;span class="kwrd"&gt;foreach&lt;/span&gt; (&lt;span class="kwrd"&gt;float&lt;/span&gt; resolution &lt;span class="kwrd"&gt;in&lt;/span&gt; resolutions) schema.Resolutions.Add(resolution);&lt;br /&gt; schema.OriginX = -20037508.342789;&lt;br /&gt; schema.OriginY = 20037508.342789;&lt;br /&gt; schema.Axis = AxisDirection.InvertedY;&lt;br /&gt; schema.Extent = &lt;span class="kwrd"&gt;new&lt;/span&gt; Extent(-20037508.342789, -20037508.342789, 20037508.342789, 20037508.342789);&lt;br /&gt; schema.Height = 256;&lt;br /&gt; schema.Width = 256;&lt;br /&gt; schema.Format = &lt;span class="str"&gt;"png"&lt;/span&gt;;&lt;br /&gt; schema.Srs = &lt;span class="str"&gt;"EPSG:900913"&lt;/span&gt;;&lt;br /&gt; &lt;span class="kwrd"&gt;return&lt;/span&gt; schema;&lt;br /&gt;}&lt;/pre&gt;&lt;br /&gt;Now you can request which tiles you need to fill up the entire view&lt;br /&gt;&lt;pre class="csharpcode"&gt;&lt;br /&gt;ITileSchema schema = CreateTileSchema();&lt;br /&gt;IList&amp;lt;TileInfo&amp;gt; tiles = Tile.GetTiles(schema, transform.Extent, transform.Resolution);&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Next you need to specify the RequestBuilder to use. In this case you need the RequestTms class because of the Tms protocol. As arguments you need to pass the url of the OpenStreetMap tile service and the format in which the tiles are stored.&lt;br /&gt;&lt;pre class="csharpcode"&gt;&lt;br /&gt;IRequestBuilder requestBuilder = &lt;span class="kwrd"&gt;new&lt;/span&gt; RequestTms(&lt;span class="kwrd"&gt;new&lt;/span&gt; Uri(&lt;span class="str"&gt;"http://a.tile.openstreetmap.org"&lt;/span&gt;), &lt;span class="str"&gt;"png"&lt;/span&gt;);&lt;br /&gt;&lt;/pre&gt;&lt;br /&gt;Finally we can request all tiles from the server and render them to our buffer Bitmap.&lt;br /&gt;&lt;pre class="csharpcode"&gt;&lt;br /&gt;Graphics graphics = Graphics.FromImage(buffer);&lt;br /&gt;&lt;span class="kwrd"&gt;foreach&lt;/span&gt; (TileInfo tile &lt;span class="kwrd"&gt;in&lt;/span&gt; tiles)&lt;br /&gt;{&lt;br /&gt;  Uri url = requestBuilder.GetUrl(tile);&lt;br /&gt;  &lt;span class="kwrd"&gt;byte&lt;/span&gt;[] bytes = ImageRequest.GetImageFromServer(url);&lt;br /&gt;  Bitmap bitmap = &lt;span class="kwrd"&gt;new&lt;/span&gt; Bitmap(&lt;span class="kwrd"&gt;new&lt;/span&gt; MemoryStream(bytes));&lt;br /&gt;  graphics.DrawImage(bitmap, transform.WorldToMap(tile.Extent.MinX, tile.Extent.MinY, tile.Extent.MaxX, tile.Extent.MaxY));&lt;br /&gt;}&lt;/pre&gt;&lt;br /&gt;The sample code above is part of the BruTile &lt;a href="http://www.codeplex.com/brutile"&gt;project&lt;/a&gt; on codeplex. The solution also includes a WPF project which demonstrates how to get a nice user experience with tile requests on a background thread and rendering tiles at the moment they arrive.&lt;/div&gt;&lt;div&gt;&lt;br /&gt;&lt;/div&gt;&lt;div&gt;&lt;br /&gt;&lt;/div&gt;&lt;/div&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/2308969591514957062-2763588139770595789?l=pauldendulk.com' alt='' /&gt;&lt;/div&gt;</description><link>http://pauldendulk.com/2009/02/brutile-tiling-library.html</link><author>noreply@blogger.com (Paul den Dulk)</author><media:thumbnail xmlns:media='http://search.yahoo.com/mrss/' url='http://2.bp.blogspot.com/_PjqxdklGCb4/SZvPYWzvlSI/AAAAAAAAByU/lYZhLhH6j28/s72-c/BruTileWinFormsSample.PNG' height='72' width='72'/><thr:total>4</thr:total></item><item><guid isPermaLink='false'>tag:blogger.com,1999:blog-2308969591514957062.post-7283697357195681599</guid><pubDate>Thu, 15 Jan 2009 14:21:00 +0000</pubDate><atom:updated>2009-01-15T06:25:47.711-08:00</atom:updated><title>Crayon Phycis Deluxe Released</title><description>Hey look, The official version of Crayon Physics Deluxe has been released last week:&lt;br /&gt;&lt;br /&gt;&lt;a href="http://www.crayonphysics.com/"&gt;http://www.crayonphysics.com/&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;Downloading the demo right now.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/2308969591514957062-7283697357195681599?l=pauldendulk.com' alt='' /&gt;&lt;/div&gt;</description><link>http://pauldendulk.com/2009/01/crayon-phycis-deluxe-released.html</link><author>noreply@blogger.com (Paul den Dulk)</author><thr:total>0</thr:total></item><item><guid isPermaLink='false'>tag:blogger.com,1999:blog-2308969591514957062.post-2505587832819715699</guid><pubDate>Mon, 17 Mar 2008 20:35:00 +0000</pubDate><atom:updated>2008-03-17T15:47:15.972-07:00</atom:updated><category domain='http://www.blogger.com/atom/ns#'>physics silverlight games</category><title>Crayon Physics</title><description>&lt;a href="http://www.kloonigames.com/crayon"&gt;This&lt;/a&gt; is just so cool! First look at the video, then think 'wow this guy makes it look so awesome', then download the &lt;a href="http://www.kloonigames.com/blog/games/crayon"&gt;prototype&lt;/a&gt; and find out it really is so awesome, and then start to think of all the cool stuff you yourself should do with such simple technology.&lt;br /&gt;&lt;br /&gt;   Apparently the full version, Crayon Physics Deluxe, will use the &lt;a href="http://www.codeplex.com/FarseerPhysics"&gt;Farseer engine&lt;/a&gt;, which works with XNA and Silverlight. I really need to check that out because there are so many ideas I need to try out right now. Airhockey on the TouchTable being the first one.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/2308969591514957062-2505587832819715699?l=pauldendulk.com' alt='' /&gt;&lt;/div&gt;</description><link>http://pauldendulk.com/2008/03/cayon-physics.html</link><author>noreply@blogger.com (Paul den Dulk)</author><thr:total>0</thr:total></item><item><guid isPermaLink='false'>tag:blogger.com,1999:blog-2308969591514957062.post-9020209236783032151</guid><pubDate>Sat, 24 Nov 2007 14:53:00 +0000</pubDate><atom:updated>2008-03-17T15:44:15.903-07:00</atom:updated><category domain='http://www.blogger.com/atom/ns#'>LBG games</category><title>The Target</title><description>Played location based game &lt;a href="http://thetarget.nl"&gt;The Target&lt;/a&gt; in Utrecht last sunday. And the news is, it is a real location based game, it works and it is fun.&lt;br /&gt;&lt;br /&gt;The Target is played with 4 nokias with gps. Each nokia is manned with a team of 2 or 3 players. One team is the target, the others are agents hunting for it. To win the target has to collect one million by stealing money at several predefined locations over town. The agents have to catch the target to prevent it. &lt;br /&gt;&lt;br /&gt;The game designers did a nice job keeping the game very simple yet fun. The players have a shoot button with which they can kill the enemy when within a certain range. Further, they can collect several types of items (e.g. knife, lorry, ladder) which are placed on several spots over town. With those items they can robe money at other locations. But for each robbery a different combination of items is needed. When the target takes an item the agents get a message stating which item was taken. But because every item can be found at a number of different locations it leaves a number of alternatives. In practice the agents spend a lot of time guessing where the target is, what he is up too, and which items he will go for next. At some interval the agent and target also get the know the exact position of their opponents.&lt;br /&gt;&lt;br /&gt;The good things about this game are:&lt;br /&gt;- Simple user interface. The user controls the game mostly through the way they move over town. You can make choices by walking to specific location on the map, with little need for buttons.&lt;br /&gt;- The playing area is a fixed square in the center of town. This is represented with a fixed map on the Nokia. Although you can zoom into each of the 16 parts of the map this is not really necessary. This keeps it simple.&lt;br /&gt;- Partial information about what is going on. The concept of the items needed for a robbery is great. It leaves enough room for guessing and enough information to make a fair guess. &lt;br /&gt;- You rent the game for 2 hours actual playing. The game keeps track of the time so it only measure actual playing time and you do not have to worry about when to bring it back. &lt;br /&gt;&lt;br /&gt;Not so good:&lt;br /&gt;- It is basically a running game. Real fast runners will do best. I can imagine that for some people this is too demanding. You need players  with a sports mentality. We happened to have a number of those in our group but even for them it took some effort to get into sports mode on a cold day walking around in heavy clothing. I would love to play this game again on a sunny day dressed in my running outfit. &lt;br /&gt;- When an agent is far removed from the target the game is not so interesting anymore. It becomes harder to motivate oneself for running. Maybe the agent should have some alternative things to do in those cases.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/2308969591514957062-9020209236783032151?l=pauldendulk.com' alt='' /&gt;&lt;/div&gt;</description><link>http://pauldendulk.com/2007/11/played-location-based-game-target-in.html</link><author>noreply@blogger.com (Paul den Dulk)</author><thr:total>0</thr:total></item><item><guid isPermaLink='false'>tag:blogger.com,1999:blog-2308969591514957062.post-6295324538552360196</guid><pubDate>Wed, 31 Oct 2007 00:08:00 +0000</pubDate><atom:updated>2008-02-23T15:41:38.510-08:00</atom:updated><title>Code Conventions</title><description>The main reason to have code conventions within your developers group is that it can stop the discussion about code conventions. For some reason those discussions never converge on mutual agreement. In my environment the topic has not come up for a while, I like to keep it that way, but secretly I try to stick to some my own code conventions.&lt;br /&gt;&lt;br /&gt;I have been following these rules&lt;br /&gt;&lt;br /&gt;1) If you work on existing code adopt whatever conventions they seem to be using&lt;br /&gt;2) If code conventions differ from file to file use the conventions of that file don't work toward conventions throughout the library.&lt;br /&gt;3) If you start anything new, go with the flow. Do whatever the majority is doing (spaces not tabs) or what big guys do (for c# I try to stick to the Microsofts &lt;a href="http://msdn2.microsoft.com/en-us/library/xzf533w0(VS.71).aspx"&gt;guidelines&lt;/a&gt;, see &lt;a href="http://blogs.msdn.com/brada/articles/361363.aspx"&gt;this&lt;/a&gt; too).&lt;br /&gt;4) If for some (maybe good) reason you defer from the convention, do not invent a rule why you did this, just say you were lazy.&lt;br /&gt;&lt;br /&gt;BTW, so please don't tell anyone this, because it could start the discussion again.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/2308969591514957062-6295324538552360196?l=pauldendulk.com' alt='' /&gt;&lt;/div&gt;</description><link>http://pauldendulk.com/2007/10/code-conventions.html</link><author>noreply@blogger.com (Paul den Dulk)</author><thr:total>0</thr:total></item><item><guid isPermaLink='false'>tag:blogger.com,1999:blog-2308969591514957062.post-3641631927409723860</guid><pubDate>Sat, 09 Dec 2006 15:44:00 +0000</pubDate><atom:updated>2006-12-09T07:45:59.352-08:00</atom:updated><title>Welcome</title><description>Hi, Welcome to my new blog!&lt;br /&gt;&lt;br /&gt;Paul&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/2308969591514957062-3641631927409723860?l=pauldendulk.com' alt='' /&gt;&lt;/div&gt;</description><link>http://pauldendulk.com/2006/12/welcome.html</link><author>noreply@blogger.com (Paul den Dulk)</author><thr:total>1</thr:total></item></channel></rss>
