3

I have some vector layers in a shapefile that I would like to display in the Google Maps Javascript API. I recently learned that you can generate GeoJSON from shapefiles in the correct CRS using QGIS: Convert Shapefiles to GeoJSON? that worked well for me, but the problem is that the file is large - the resulting JSON is 250MB in my case. So I'd like to have it as a collection of tiles instead. I discovered that the Google Maps API can load tiles from GeoJSON as described here

https://stackoverflow.com/questions/27284251/vector-tiles-with-google-maps-v3

But I can't find a way to actually generate tiled GeoJSON like that. I noticed that both QGIS and MapTiler have an option to write vector tiles in the XYZ structure, but the individual files come out as .pbf, which Google Maps can't handle. So I am looking to create them as GeoJSON. Is there a way to do that?

Edit: In searching around, I also discovered tippecanoe and was able to run it, but it looks like it also generates pbf files. I want the individual tiles in geoJSON.

Edit 2: I then discovered that I could run tippecanoe-decode on the very same pbf files that tippecanoe itself had created. While a little weird, it seemed to work and generated JSON that looked like below, which is throwing errors in Google, I'm assuming because of the nested FeatureCollection...

    {
  "type": "FeatureCollection",
  "properties": {
    "zoom": 18,
    "x": 42016,
    "y": 91728
  },
  "features": [
    {
      "type": "FeatureCollection",
      "properties": {
        "layer": "sea",
        "version": 2,
        "extent": 4096
      },
      "features": [
        {
          "type": "Feature",
          "properties": {
            "autocad_el": 0,
            "autocad_th": 0,
            "autocad_wi": 0,
            "autocad_co": 106,
            "autocad_la": "C_1CON_ROAD_CURB",
            "autocad_li": "ByLayer"
          },
          "geometry": {
            "type": "LineString",
            "coordinates": [
              [
                -122.299832,
                47.442148
              ],
              [
                -122.299805,
                47.44213
              ],
              [
                -122.299647,
                47.442021
              ],
              [
                -122.299621,
                47.442003
              ]
            ]
          }
        },
        {
          "type": "Feature",
          "properties": {
            "autocad_el": 0,
            "autocad_th": 0,
            "autocad_wi": 0,
            "autocad_co": 106,
            "autocad_la": "C_1CON_ROAD_CURB",
            "autocad_li": "ByLayer"
          },
          "geometry": {
            "type": "LineString",
            "coordinates": [
              [
                -122.299832,
                47.442153
              ],
              [
                -122.299805,
                47.442135
              ],
              [
                -122.29964,
                47.442021
              ],
              [
                -122.299613,
                47.442003
              ]
            ]
          }
        }
      ]
    }
  ]
}
2
  • My advice is to use Postgres with Post GIS extension where you can have more control over output based on your query structure. – Kumbra Oct 23 '20 at 22:02
  • 1
    You could use MapBox Tippecanoe: github.com/mapbox/tippecanoe for one time creation. – TomazicM Oct 27 '20 at 10:40
3
+100

I would recommend using GeoServer for this.
It can generate tiles as geoJSON natively and can installed very easily,
setting the GEOWEBCACHE_CACHE_DIR environment variable will let you choose where your cache of XYZ tiles will be genrated.
You would need to add a data source from a folder of shapefiles, and then publish the layer from the file you want to use.
Use this guide if you have any proplems: Publishing a shapefile
After publishing the layer (which can happen locally) you will need to enable caching geojson

enable publishing geojson

You will then need to seed the tiles in EPSG:900913 (which is Google Maps Global Mercator or more simply called web mercator) which is compatible with xyz tiles.

To get your tiles in XYZ file structure you will need GeoServer version 2.17 and up. You will need to create a file blob store with SLIPPY layout and set it as the blob store for your layer.

creating your blob store

setting the blob store

You can now seed your geojson cache and find your files inside the folder of the blob store.

You can find more explanations in the official guide

enter image description here

EDIT

Just so this is clear, what is described above, will give you a cache of static geojson tiles in an XYZ folder layout.
This means something like this {z}/{x}/{y}.geojson These tiles can be copied later to a S3 Bucket or whatever other way you want to serve them.
For the test layer I seeded yesterday the folder layout looks like this:

enter image description here

6
  • That's intriguing, but for my purposes I would strongly prefer to generate the tiles statically, as I would do for raster tiles. I already have a mechanism for serving them from S3, among other reasons. – Dan Oct 26 '20 at 16:08
  • 1
    This will work for both raster, geojson and pbf. You are just setting the folder structure to be the same as required for xyz tiles. – Dror Bogin Oct 26 '20 at 17:05
  • What I meant was, I don't want to have to have a server running all the time for this. i'd like to just generate the tiles and export them to a static structure. – Dan Oct 26 '20 at 22:39
  • 1
    Again, this method gives you what you want, look at the edit i added at the end of the answer. You can switch the server off the second the seeding is done, though i would check the results first. – Dror Bogin Oct 27 '20 at 6:11
  • Thanks. It doesn't seem that Google is actually able to read the geoJSON in EPSG:900913, it expects lat/lng, but I was able to cache the image tiles instead and that works well enough for me! – Dan Oct 27 '20 at 17:07

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.