In order to use TileCache to cache tiles for use in the Google Maps API, you need three things:
- A WMS server which supports the spherical mercator projection
- A properly configured TileCache pointing to it
- A small snippet of code to add a custom TileLayerOverlay to your Google Map
- A small snippet of code to add a custom TileSource to your Virtual Earth Map
WMS Server
My experience is with MapServer, so that’s what I’m going with here.
MapServer uses proj.4 for its reprojection support. In order to enable reprojection to Spherical Mercator in MapServer, you must add the definition for the projection to your proj.4 data directories.
On Linux systems, edit the /usr/share/proj/epsg file. At the bottom of that file, add the line:
<900913> +proj=merc +a=6378137 +b=6378137 +lat_ts=0.0 +lon_0=0.0
+x_0=0.0 +y_0=0 +k=1.0 +units=m +nadgrids=@null +no_defs
After you do this, you must add the projection to your wms_srs metdadata in your map file:
map
web
metadata
wms_srs "EPSG:4326 EPSG:900913"
end
end
# Layers go here
end
This will allow you to request tiles from your MapServer WMS server in the Spherical Mercator projection.
Configuring TileCache
Your TileCache configuration will need to point to your WMS installation, using the parameters suggested for Spherical Mercator in the default tilecache.cfg.
[google-tiles]
type=WMS
url=http://labs.metacarta.com/wms/vmap0
layers=basic
extension=png
bbox=-20037508.3427892,-20037508.3427892,20037508.3427892,20037508.3427892
maxResolution=156543.0339
srs=EPSG:900913
Here, you can see that I’ve used the MetaCarta Labs vmap0 WMS. If you’re using a standard MapServer WMS, you might have a url more like:
url=http://example.com/cgi-bin/mapserv?map=/mapdata/mapfiles/vmap0.map
Setting up Google Maps
Finally, you must make a GTileLayerOverlay for your tiles.
var myTileLayer = new GTileLayerOverlay(new GTileLayer(null,null,null,{
tileUrlTemplate: 'http://example.com/tilecache/1.0.0/google-tiles/{Z}/{X}/{Y}.png?type=google',
isPng:true}));
var map = new GMap2(document.getElementById("map_canvas"));
map.setCenter(new GLatLng(0,0), 0);
map.addControl(new GSmallMapControl());
map.addOverlay(myTileLayer);
The ‘type=google’ flag on the end of the URL tells TileCache to use the “Google-style” 0,0 in the upper left corner.
Once you’ve done this, you should have a TileCache layer on top of your Google Maps base layer. You can see an example of this setup, just for proof that I’m not putting you on. 🙂
Virtual Earth Javascript
“But I don’t like Google!” you say. “I want VE!” Well then, why aren’t you using OpenLayers already? I mean, that’s what it’s for, right? 🙂
More seriously, VE isn’t much more difficult:
vemap = new VEMap('myMap');
vemap.LoadMap(new VELatLong(0, 0), 0 );
//Add layer
var tileSourceSpec = new VETileSourceSpecification("mclabs", null, 1,
[new VELatLongRectangle(new VELatLong(-86,-180),new VELatLong(86,180))],
1, 16, function (tileContext)
{
if(tileContext != null && tileContext != "undefined")
{
var key = tileContext.ZoomLevel+ "/" + tileContext.XPos + "/" + tileContext.YPos + ".png?type=google";
var path = "http://example.com/tiles/1.0.0/google-tiles/" + key;
return path;
}
}, 0.8, 100 );
vemap.AddTileSource(tileSourceSpec);
var tileLayer = new VELayerSpecification(VELayerType.VETileSource,"mclabs","mclabs");
vemap.AddLayer(tileLayer);
And, for your viewing pleasure: an example of the same tileset in use.