Skip to content

Instantly share code, notes, and snippets.

@tmcw
Created December 28, 2022 17:00
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save tmcw/e97a42bde4d9c7681c37a785405d37a1 to your computer and use it in GitHub Desktop.
Save tmcw/e97a42bde4d9c7681c37a785405d37a1 to your computer and use it in GitHub Desktop.
PMTiles to SVG

Request a single tile from PMTiles, use the vector-tiles module to read it, the d3-geo tools to turn it into a string. d3-geo is probably unnecessary.

This approach feels limited:

Requires restitching tiles if more than one. Limited attributes. Any tile-based solution is going to make compromises in favor of responsiveness and lightweight data. What this wants is completeness and non-sliced data.

import * as pmtiles from "./node_modules/pmtiles/dist/index.mjs";
import * as vt from "https://cdn.skypack.dev/@mapbox/vector-tile";
import * as pbf from "https://cdn.skypack.dev/pbf";
import * as geo from "https://unpkg.com/d3-geo@3.1.0/src/index.js?module"
import * as shape from "https://unpkg.com/d3-shape@3.1.0/src/index.js?module"
const src = new pmtiles.PMTiles('./Brooklyn.pmtiles');
console.log(src);
console.log(pbf);
console.log(vt);
src.getZxy(11,602,770).then(tile => {
console.log(tile);
const vtile = new vt.VectorTile(new pbf.default(tile.data));
console.log(vtile);
const layers = [
vtile.layers.roads,
vtile.layers.natural,
vtile.layers.transit,
vtile.layers.water,
vtile.layers.landuse,
vtile.layers.places,
vtile.layers.buildings
]
for (let layer of layers) {
for (let i = 0; i < layer.length; i++) {
const feature = layer.feature(i);
const geojson = feature.toGeoJSON(602,770, 11)
const points = feature.loadGeometry();
const d = shape.line()(points[0].map(point => {
return [point.x, point.y];
}))
const path = tileroot.appendChild(document.createElementNS('http://www.w3.org/2000/svg', 'path'))
if (geojson.geometry.type === 'LineString') {
path.setAttribute('d', d);
path.setAttribute('stroke', 'black');
path.setAttribute('stroke-width', '3');
path.setAttribute('fill', 'none');
} else {
path.setAttribute('d', `${d}Z`);
path.setAttribute('stroke', 'red');
path.setAttribute('stroke-width', '3');
path.setAttribute('fill', '#555');
path.setAttribute('fill-opacity', '0.5');
}
}
}
});
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment