TileLayer Async

Topics: Algorithms, Data Access, SharpMap Project, SharpMap v0.9 / v1.x, Web Controls, WinForms Controls
Developer
Jan 27, 2011 at 1:43 AM

I'm using the a TileLayer with BruTile and GoogleMaps / Bing / OSM Maps, but the rendering is synchronous.

I've made some modifications to draw each tile when they are loaded instead of waiting for all tiles to be retrieved and then draw all tiles.

This modification is not a simple modification and I'v need to change from MapBox -> Map -> TileLayer.

Now I want that someone can evaluate the modifications and if so incorporate in trunk.

 

the logic that I've implemented is the following:

1 - When a TileLayer is requested to Draw, instead of getting all the Tiles in View and then Draw, I exposed an event in TileLayer:

public delegate void MapNewTileAvaliabledHandler(TileLayer sender, SharpMap.Geometries.BoundingBox bbox, Bitmap bm, int sourceWidth, int sourceHeight, ImageAttributes imageAttributes);

public event MapNewTileAvaliabledHandler MapNewTileAvaliable;

2 - With this event, after adding a TileLayer to a Map, we associate the event from the TileLayer to a Public Method in Map that exposes the same Event
3 - With the event from Map, we associate the event to MapBox so the Static Image BitMap can be updated with the new TileAvailable

With all thes "Bubbling Events", each time a new Tile is available, the tile is "Event Bubbled" to the MapBox.
For me this is not the best solution but is working with MapBox.
The problems that I found:
- This doesn't work when we want Synchronous TileLayer, so the suggestion that I have is to create a new TileLayerAsync
- We need manually to wire the event from the tilelayer to the map and wire the event from the map to the mapbox

I don't know who normally works with TileLayer, so I need some help to improve this.
I can submit a patch, but for me this is not final yet.

Cofee
Coordinator
Jan 27, 2011 at 8:23 AM

Hello cofee,

this truly would be a great enhancement. Now how about

  • Adding an interface IAsyncLayer, which exposes an event NewAsyncResult.
  • On adding an IAsyncLayer to LayerCollection an event (e.g. AsyncLayerAdded) is raised which can be handled by MapBox/MapImage.
  • Handling would add handlers to NewAsyncResult events.
  • On removing these layers, the handlers would have to be released.

cheers

FObermaier

May 12, 2011 at 7:20 PM

Is there any update to this?

Developer
May 12, 2011 at 7:24 PM

This is already implemented in trunk version of SharpMap.

 

You must used an AsyncTileLayer instead of TileLayer.

 

cofee

May 12, 2011 at 8:07 PM

Hmm, what am I doing wrong here?  Using a regular TileLayer works fine, but switching it to TileAsynchLayer doesn't render anything,

Is there something special I have to do to tell the map to render after it performs that?

Here is what I have so far:

mapBox1.Map = TileLayerSample.InitializeMap(zoomBar.Value);

public static Map InitializeMap(float angle)
{
    return InitializeMapGoogle(GoogleMapType.GoogleMap);
}

private static Map InitializeMapGoogle(GoogleMapType mt)
{
    Map map = new Map();

    GoogleRequest req;
    ITileSource tileSource;
    TileLayer tileLayer;

    if (mt == (GoogleMapType.GoogleSatellite | GoogleMapType.GoogleLabels))
    {
        req = new GoogleRequest(GoogleMapType.GoogleMap);
        tileSource = new GoogleTileSource(req);
        tileLayer = new TileLayer(tileSource, "TileLayer - " + GoogleMapType.GoogleSatellite);
        map.Layers.Add(tileLayer);
        req = new GoogleRequest(GoogleMapType.GoogleLabels);
        tileSource = new GoogleTileSource(req);
        mt = GoogleMapType.GoogleLabels;
    }
    else
    {
        req = new GoogleRequest(mt);
        tileSource = new GoogleTileSource(req);
    }

    tileLayer = new TileLayer(tileSource, "TileLayer - " + mt);
    map.Layers.Add(tileLayer);
    map.ZoomToBox(tileLayer.Envelope);
    return map;
 }
Developer
May 12, 2011 at 10:54 PM

Hi, I think that in the DemoWinSamples there is an example showing the TileAsyncLayers.

 

Can you try it ?

 

RP

May 12, 2011 at 11:02 PM

I couldn't compile the DemoWinSamples stuff to step through it but looking through the code I was able to get an example working.  GoogleMaps.MapType.Satellite still fails to load however and the performance is still a little sluggish, more so than the web browser based mapping components.  Is there a reason for performance hit?

Coordinator
May 13, 2011 at 9:21 AM

AsyncTileLayer is only working for WinForms. For the web, sharpmap acts as an WMS server that renders the whole image and posts it when it is done.

For a more performant way of using SharpMap with tiles, it is recomended that you use OpenLayers along with SharpMap as wmsserver.

Look for related diskussions in the forum

Hth FObermaier

May 13, 2011 at 2:41 PM

Can you point me to any examples of accomplishing this?  Most that I have found thus far scouring the posts have broken links.

Thanks