3

I'm trying to turn a QGIS 2.4 project into a TMS tileset. What method have folks used, with what success and what level of effort?

The project in question has about 50 layers and uses OTF projection since different layers are in different CRSs.

  • the QTiles plugin hangs (and takes down the rest of QGIS with it) at 'Rendering: 0 from ... (0%)' even for a fairly small area and just a couple of zoom levels; I think this is just because the render function hangs in the same manner if you call it directly? Is there any way to avoid this problem with QTiles?

  • gdal2tiles, using geotiff rendered from QGIS as input - I'd have to assemble a VRT and use that as input since QGIS errors out if I try to render one geotiff of even a small fraction of the size needed, so, this would be a question of writing a script to render many smaller geotiffs and building a corresponding VRT, right? A current problem I'm having with this is trying to effectively 'apply OTF projection for the render function' since the render output only has the data of whichever layers' native CRSs result in data in the area defined by the QgsRectangle; is there an easy way to do that?

  • a slight variant of the above - skip the gdal2tiles step and write a script to render 256x256 .png tiles directly from QGIS

  • QGISServer and tilecache - I haven't tried this option but the overhead of setting up the local web server seems daunting; has anyone used this option with good success?

  • any other plugins or (simpler) methods to accomplish this task?

4

I dont think there is an easy and simple method.

  1. I also found qtiles did not work.
  2. Qgis Server is probably the easiest route, because it all uses the same styling system. However it does involve an awful lot of software.
  3. mapserver, tilecache may be easier to install in some situations, i get the impression it has less dependencies.
  4. the simplist way might be a python script. see http://mikeongis.wordpress.com/2011/08/29/printing-map-part-ii-map-tiles-with-qgis/
  5. checkout tilemill http://www.klaasnienhuis.nl/2012/08/creating-maps-with-qgis-and-tilemill/ (but only works with spherical mercator).
  • also for your sanity reproject all your layers as native project srs. (layers , save as) – Peter Sep 23 '14 at 23:10
3

Answering my own question, here's the solution I went with: roll-your-own in python.

The map in question uses scale-dependent rendering, so, I wanted to do a different render for each 'z' (integer TMS zoom level, 10 thru 17 in this case).

Overall workflow, once for each zoom level: 1) render from qgis to tif with a worldfile (i.e. the tif will have coordinates but no crs/transform info; the worldfile will have the standard worldfile info) 2) convert the rendered tif plus tfw into a real geotiff (i.e. crs/transform embedded in the tif file) 3) gdal2tiles to build the TMS tile set

some more detail:

  1. render from qgis

Since the various layers of the map have different CRSs, make sure to render via the composer instead of bypassing the composer. The composer capitalizes on the on-the-fly projection, so everything in the render looks like your map area in qgis when on-the-fly projection is enabled.

Since big render jobs will cause a qgis error, just do a bunch of smaller render jobs (hardcode some arbitrary 'render tile' size in paper units (millimeters or inches)), then plan on combining all the 'render tile' geotiffs for the current zoom level into a single VRT per zoom level in the next step.

  1. convert tif+tfw to GeoTIFF

for each 'render tile':

gdalwarp -s_srs <map_project_srs> <render_tile> <render_tile_out>

after all 'render tiles' are converted to real GeoTIFF:

gdalbuildvrt <output_vrt_name> <list/glob/listfile of render_tile_out files>
  1. gdal2tiles to build the TMS tile set

.

gdal2tiles -z <target_z_level> <output_vrt_name> <output_tile_dir>

which will put all the tms tiles into <output_tile_dir>/<target_z_level> so you can specify the same output_tile_dir for each iteration of this step

I think I got it to the point where there's a limited set of configuration options that you have to get to the script by whatever method:

  • x0,y0,x1,y1 - bounding box in map units of the entire area to build a TMS tile set of
  • zmin, zmax - what TMS z zoom levels to build tiles for
  • 'render tile' size in mm per side
  • dpi - dots per inch, as used by the renderer
  • a list of map scales that you want to correspond to the integer TMS 'z' zoom levels; this is for purposes of scale-dependent rendering in the source map layers
  • base_dir - base directory where all the work will be saved

Would folks here recommend turning this into a plugin? It would be my first, but honestly it takes so friggin long and so friggin much disk space that it's been much better so far to do it in pieces. Probably the only difference between this and qtiles is the concept of chopping up the render task into small renders that won't error out, then building a vrt out of them - as well as the flexibility to determine what scale per z level you want, to account for scale dependent rendering.

Any ideas or suggestions for optimizing this flow?

UPDATE: sorry I forgot to include this credit from the script I did the first time around, referencing the link from zoneblue's solution:

# large portions of this code taken from 
# http://mikeongis.wordpress.com/2011/08/29/printing-map-part-ii-map-tiles-with-qgis/
# and the qgis docs at
# http://docs.qgis.org/testing/en/docs/pyqgis_developer_cookbook/composer.html
  • wow, that sounds like a bit of work by hand, but as you say could be scripted. Using the biggest size that composer will export, vrt, gdal2tiles. Did you have to render full tms pyramids for each native zoom level, then bin all but one zoom from each iteration?. Yikes. Ill probably ending up bite the bullet and learn mapserver, mainly because it will come in handy later for other things. – Peter Sep 24 '14 at 23:37
  • sorry I was unclear - I did script it up. Just wanted to see if there's any feedback about the methodology before I clean up the code and maybe make it into a plugin at some point. All the steps that are done in qgis can be scripted, and for the rest I think it's best to just have that python script inside qgis write a batch file so you can run various parts from outside qgis as you see fit (or all at once if you feel lucky). I render the full area for each zoom level to a vrt of geotiffs, and just build tiles for one z per render-zoom set. – Tom Grundy Sep 25 '14 at 4:43

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.