MapBox adds border to my tiles

Topics: SharpMap v0.9 / v1.x
Feb 20, 2012 at 12:11 AM
Edited Feb 20, 2012 at 12:11 AM

I am playing with TileLayer to show data from my local file datasource.

Everything is great, except one thing: when rendering tiles on the map I can see a light outline around every of my 256x256px tiles. You can see a sample here: http://kepfeltoltes.hu/view/120220/tilesample_www.kepfeltoltes.hu_.png

If I save a tile as image I can not see this outline so it is only during rendering in MapBox. It somehow renders some 1pixel wide border to my tiles.

How can I avoid this?

Thanks!

Developer
Feb 20, 2012 at 6:22 AM

TileLayer needs to do a RoundToPixel before drawing the tile. But looking at the TileLayer code it seems to be implemented correct. Also GraphicsUnit.Pixel is correct.

http://sharpmap.codeplex.com/SourceControl/changeset/view/96200#1074394 


This is the method I use 

        private static RectangleF RoundToPixel(RectangleF dest)
        {
            // To get seamless aligning you need to round the locations
            // not the width and height
            dest = new RectangleF(
                (float)Math.Round(dest.Left),
                (float)Math.Round(dest.Top),
                (float)(Math.Round(dest.Right) - Math.Round(dest.Left)),
                (float)(Math.Round(dest.Bottom) - Math.Round(dest.Top)));
            return dest;
        }

 

Are you sure the tile source is correct? Perhaps the borders do not have the full color because of anti aliasing. How were they generated?

Feb 20, 2012 at 9:04 AM
Edited Feb 20, 2012 at 9:05 AM

Thanks for your fast answer.

So, I made some experiments to combine the power of Mapnik, BruTile and SharpMap. Mapnik is a tile rendering engine and there is a project that enables to use it in .net environment. After some days of investigating I could make it work, it is really great and nice. I also use your file cache to speed up.

What I do is to implement a custom tileprovider, and use it with shapmap's tile layer. Note, it is an experimental code, that's why I have this simple error handling. Other thing is Mapnik .net wrapper returns an image, so I should convert it to bytes. Later I'll change this step.

 

public byte[] GetTile(TileInfo tileInfo)
        {
            try
            {
                var imageRes = MapnikProvider.GetImage(tileInfo.Extent.MinX, 
                                                       tileInfo.Extent.MinY, 
                                                       tileInfo.Extent.MaxX, 
                                                       tileInfo.Extent.MaxY, 
                                                       256, 
                                                       256);

                if (imageRes.Result == false)
                    throw new Exception(imageRes.InfoMessage);

                var image = imageRes.Generic;

                MemoryStream ms = new MemoryStream();
                image.Save(ms, System.Drawing.Imaging.ImageFormat.Png);

                image.Dispose();

                var retArray = ms.ToArray();

                return retArray;
            }
            catch (System.Exception exc)
            {
                Debug.Assert(false, exc.Message);
                return null;
            }
        }

 

Here are some sample tiles, you can check them: http://www.sendspace.com/file/neq92o

Thanks for your help!

Feb 20, 2012 at 9:33 AM
Edited Feb 20, 2012 at 9:33 AM

I forgot: I did not change anything in TileLayer, it is from SharpMap, so this rounding is in the code and works. I tried to remove it and I could see its effect: without this rounding the borders of the tiles are more worse. So, rounding works, but not as good as it should do.

Thanks

Feb 21, 2012 at 5:19 AM

tmatrai, Hi again!

How do you use mapnik-net? Some links on documentation, pls. Very interesting..

Coordinator
Feb 21, 2012 at 6:17 AM

Hi,

Have you tried making MapNik draw a bigger image and the crop-it before returning in case it's MapNik that does draw the border?

 

 

Feb 21, 2012 at 9:02 AM
Edited Feb 21, 2012 at 9:04 AM

Hi nigr0nyx!

I use the .net wrapper of Mapnik2. If you don't wanna/can't compile it by yourself, you can download its precompiled binaries from that site. It' nothing more than a bunch of dlls. Add them (and SharpMap of course) as a reference to your project and you can make it work. I use SharpMap's infrastructure, what Mapnik does is to render my background layers.

I define Mapnik map in XML , i load this xml into .net wrapper's map class (that is the heart of that wrapper U would use 90% of the time). Map has a render method (you can pass extent to it) that returns you the map image (tile). And this image is used in a 'normal' SharpMap tile layer, by a custom tile provider (you can see the main method above, just implements GetTile method, in which I get map image from mapnik wrapper and return it as a byte array). And thats all. 

Note, that I also use file cache to improve performance. Generating tiles in mapnik is not a cheap job, it needs some time and hw. You should also play a lot also by Mapnik XML to optimize your map, or pre-generate some tiles at critical zoom levels by python and copy them to your file cache. 

Also note, I just make experiments now, but if I have a stable version I would build some hello world project and share it here. Don't know when, I am very busy with my work, but I will.

What I also suggest you is to read about tile based GIS systems, you can find a lot to read over the internet.

Feb 21, 2012 at 9:02 AM

Hi petlof!

Thx your advice, I'll try that.

Coordinator
Feb 21, 2012 at 10:04 AM

Paul den Dulk has released version 0.6 of BruTile as a nuget package. If you update your nuget package, you get a configurable OsmTileSource, that allows to get tiles from different servers. There are also predefined MapNic tiles available.

Hth FObermaier

Feb 22, 2012 at 3:14 AM

tmatrai, thanks for detail reply.

Developer
Feb 22, 2012 at 7:15 AM

@tmatrai The tile images don't seem to have any anti aliased edges. Is there transparency involved somewhere?

Feb 22, 2012 at 1:33 PM

I did not set any transparency anywhere. Thanks!

Developer
Feb 22, 2012 at 2:47 PM
Edited Feb 22, 2012 at 2:48 PM

Did you try your app with a different tileset? You could create a local file tile set with http://www.maptiler.org/

Feb 22, 2012 at 4:13 PM

I tried some tiles generated by Maperative. In that case I did not have such a problem. 

Feb 22, 2012 at 4:24 PM
Edited Feb 22, 2012 at 4:26 PM

There is a 'transparentColor' parameter in one of TileLayer's constructor. What is it for? I guess to define transport color of tile images... :)

I pass new Color() to it and also tried to create layer without defining this value, but I still have this borders in my images.

Feb 28, 2012 at 1:02 PM

Finally I found the reason: in my tile layer image attributes wrap mode was not set properly. By setting it to TileFlipXY it works great and there are no borders around my tiles.

Thanks all of your efforts to help me! 

Developer
Feb 28, 2012 at 2:38 PM

thanks for posting it back