@maplibre/geojson-vt 5.0.0 → 5.0.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1 +1 @@
1
- !function(t,e){"object"==typeof exports&&"undefined"!=typeof module?module.exports=e():"function"==typeof define&&define.amd?define(e):(t="undefined"!=typeof globalThis?globalThis:t||self).geojsonvt=e()}(this,(function(){"use strict";function t(n,o,i,s){let r=s;const l=o+(i-o>>1);let u,a=i-o;const f=n[o],c=n[o+1],m=n[i],d=n[i+1];for(let t=o+3;t<i;t+=3){const o=e(n[t],n[t+1],f,c,m,d);if(o>r)u=t,r=o;else if(o===r){const e=Math.abs(t-l);e<a&&(u=t,a=e)}}r>s&&(u-o>3&&t(n,o,u,s),n[u+2]=r,i-u>3&&t(n,u,i,s))}function e(t,e,n,o,i,s){let r=i-n,l=s-o;if(0!==r||0!==l){const u=((t-n)*r+(e-o)*l)/(r*r+l*l);u>1?(n=i,o=s):u>0&&(n+=r*u,o+=l*u)}return r=t-n,l=e-o,r*r+l*l}function n(t,e,n,i){const s={id:null==t?null:t,type:e,geometry:n,tags:i,minX:1/0,minY:1/0,maxX:-1/0,maxY:-1/0};if("Point"===e||"MultiPoint"===e||"LineString"===e)o(s,n);else if("Polygon"===e)o(s,n[0]);else if("MultiLineString"===e)for(const t of n)o(s,t);else if("MultiPolygon"===e)for(const t of n)o(s,t[0]);return s}function o(t,e){for(let n=0;n<e.length;n+=3)t.minX=Math.min(t.minX,e[n]),t.minY=Math.min(t.minY,e[n+1]),t.maxX=Math.max(t.maxX,e[n]),t.maxY=Math.max(t.maxY,e[n+1])}function i(t,e){const n=[];if("FeatureCollection"===t.type)for(let o=0;o<t.features.length;o++)s(n,t.features[o],e,o);else"Feature"===t.type?s(n,t,e):s(n,{geometry:t},e);return n}function s(t,e,o,i){if(!e.geometry)return;const a=e.geometry.coordinates;if(a&&0===a.length)return;const f=e.geometry.type,c=Math.pow(o.tolerance/((1<<o.maxZoom)*o.extent),2);let m=[],d=e.id;if(o.promoteId?d=e.properties[o.promoteId]:o.generateId&&(d=i||0),"Point"===f)r(a,m);else if("MultiPoint"===f)for(const t of a)r(t,m);else if("LineString"===f)l(a,m,c,!1);else if("MultiLineString"===f){if(o.lineMetrics){for(const o of a)m=[],l(o,m,c,!1),t.push(n(d,"LineString",m,e.properties));return}u(a,m,c,!1)}else if("Polygon"===f)u(a,m,c,!0);else{if("MultiPolygon"!==f){if("GeometryCollection"===f){for(const n of e.geometry.geometries)s(t,{id:d,geometry:n,properties:e.properties},o,i);return}throw new Error("Input data is not a valid GeoJSON object.")}for(const t of a){const e=[];u(t,e,c,!0),m.push(e)}}t.push(n(d,f,m,e.properties))}function r(t,e){e.push(a(t[0]),f(t[1]),0)}function l(e,n,o,i){let s,r,l=0;for(let t=0;t<e.length;t++){const o=a(e[t][0]),u=f(e[t][1]);n.push(o,u,0),t>0&&(l+=i?(s*u-o*r)/2:Math.sqrt(Math.pow(o-s,2)+Math.pow(u-r,2))),s=o,r=u}const u=n.length-3;n[2]=1,o>0&&t(n,0,u,o),n[u+2]=1,n.size=Math.abs(l),n.start=0,n.end=n.size}function u(t,e,n,o){for(let i=0;i<t.length;i++){const s=[];l(t[i],s,n,o),e.push(s)}}function a(t){return t/360+.5}function f(t){const e=Math.sin(t*Math.PI/180),n=.5-.25*Math.log((1+e)/(1-e))/Math.PI;return n<0?0:n>1?1:n}function c(t,e,o,i,s,r,l,u){if(i/=e,r>=(o/=e)&&l<i)return t;if(l<o||r>=i)return null;const a=[];for(const e of t){const t=e.geometry;let r=e.type;const l=0===s?e.minX:e.minY,f=0===s?e.maxX:e.maxY;if(l>=o&&f<i){a.push(e);continue}if(f<o||l>=i)continue;let c=[];if("Point"===r||"MultiPoint"===r)m(t,c,o,i,s);else if("LineString"===r)d(t,c,o,i,s,!1,u.lineMetrics);else if("MultiLineString"===r)p(t,c,o,i,s,!1);else if("Polygon"===r)p(t,c,o,i,s,!0);else if("MultiPolygon"===r)for(const e of t){const t=[];p(e,t,o,i,s,!0),t.length&&c.push(t)}if(c.length){if(u.lineMetrics&&"LineString"===r){for(const t of c)a.push(n(e.id,r,t,e.tags));continue}"LineString"!==r&&"MultiLineString"!==r||(1===c.length?(r="LineString",c=c[0]):r="MultiLineString"),"Point"!==r&&"MultiPoint"!==r||(r=3===c.length?"Point":"MultiPoint"),a.push(n(e.id,r,c,e.tags))}}return a.length?a:null}function m(t,e,n,o,i){for(let s=0;s<t.length;s+=3){const r=t[s+i];r>=n&&r<=o&&g(e,t[s],t[s+1],t[s+2])}}function d(t,e,n,o,i,s,r){let l=h(t);const u=0===i?x:M;let a,f,c=t.start;for(let m=0;m<t.length-3;m+=3){const d=t[m],p=t[m+1],x=t[m+2],M=t[m+3],y=t[m+4],P=0===i?d:p,S=0===i?M:y;let z=!1;r&&(a=Math.sqrt(Math.pow(d-M,2)+Math.pow(p-y,2))),P<n?S>n&&(f=u(l,d,p,M,y,n),r&&(l.start=c+a*f)):P>o?S<o&&(f=u(l,d,p,M,y,o),r&&(l.start=c+a*f)):g(l,d,p,x),S<n&&P>=n&&(f=u(l,d,p,M,y,n),z=!0),S>o&&P<=o&&(f=u(l,d,p,M,y,o),z=!0),!s&&z&&(r&&(l.end=c+a*f),e.push(l),l=h(t)),r&&(c+=a)}let m=t.length-3;const d=t[m],p=t[m+1],y=t[m+2],P=0===i?d:p;P>=n&&P<=o&&g(l,d,p,y),m=l.length-3,s&&m>=3&&(l[m]!==l[0]||l[m+1]!==l[1])&&g(l,l[0],l[1],l[2]),l.length&&e.push(l)}function h(t){const e=[];return e.size=t.size,e.start=t.start,e.end=t.end,e}function p(t,e,n,o,i,s){for(const r of t)d(r,e,n,o,i,s,!1)}function g(t,e,n,o){t.push(e,n,o)}function x(t,e,n,o,i,s){const r=(s-e)/(o-e);return g(t,s,n+(i-n)*r,1),r}function M(t,e,n,o,i,s){const r=(s-n)/(i-n);return g(t,e+(o-e)*r,s,1),r}function y(t,e){const n=e.buffer/e.extent;let o=t;const i=c(t,1,-1-n,n,0,-1,2,e),s=c(t,1,1-n,2+n,0,-1,2,e);return(i||s)&&(o=c(t,1,-n,1+n,0,-1,2,e)||[],i&&(o=P(i,1).concat(o)),s&&(o=o.concat(P(s,-1)))),o}function P(t,e){const o=[];for(let i=0;i<t.length;i++){const s=t[i],r=s.type;let l;if("Point"===r||"MultiPoint"===r||"LineString"===r)l=S(s.geometry,e);else if("MultiLineString"===r||"Polygon"===r){l=[];for(const t of s.geometry)l.push(S(t,e))}else if("MultiPolygon"===r){l=[];for(const t of s.geometry){const n=[];for(const o of t)n.push(S(o,e));l.push(n)}}o.push(n(s.id,r,l,s.tags))}return o}function S(t,e){const n=[];n.size=t.size,void 0!==t.start&&(n.start=t.start,n.end=t.end);for(let o=0;o<t.length;o+=3)n.push(t[o]+e,t[o+1],t[o+2]);return n}function z(t,e){if(t.transformed)return t;const n=1<<t.z,o=t.x,i=t.y;for(const s of t.features){const t=s.geometry,r=s.type;if(s.geometry=[],1===r)for(let r=0;r<t.length;r+=2)s.geometry.push(Y(t[r],t[r+1],e,n,o,i));else for(let r=0;r<t.length;r++){const l=[];for(let s=0;s<t[r].length;s+=2)l.push(Y(t[r][s],t[r][s+1],e,n,o,i));s.geometry.push(l)}}return t.transformed=!0,t}function Y(t,e,n,o,i,s){return[Math.round(n*(t*o-i)),Math.round(n*(e*o-s))]}function b(t,e,n,o,i){const s=e===i.maxZoom?0:i.tolerance/((1<<e)*i.extent),r={features:[],numPoints:0,numSimplified:0,numFeatures:t.length,source:null,x:n,y:o,z:e,transformed:!1,minX:2,minY:1,maxX:-1,maxY:0};for(const e of t)v(r,e,s,i);return r}function v(t,e,n,o){const i=e.geometry,s=e.type,r=[];if(t.minX=Math.min(t.minX,e.minX),t.minY=Math.min(t.minY,e.minY),t.maxX=Math.max(t.maxX,e.maxX),t.maxY=Math.max(t.maxY,e.maxY),"Point"===s||"MultiPoint"===s)for(let e=0;e<i.length;e+=3)r.push(i[e],i[e+1]),t.numPoints++,t.numSimplified++;else if("LineString"===s)w(r,i,t,n,!1,!1);else if("MultiLineString"===s||"Polygon"===s)for(let e=0;e<i.length;e++)w(r,i[e],t,n,"Polygon"===s,0===e);else if("MultiPolygon"===s)for(let e=0;e<i.length;e++){const o=i[e];for(let e=0;e<o.length;e++)w(r,o[e],t,n,!0,0===e)}if(r.length){let n=e.tags||null;if("LineString"===s&&o.lineMetrics){n={};for(const t in e.tags)n[t]=e.tags[t];n.mapbox_clip_start=i.start/i.size,n.mapbox_clip_end=i.end/i.size}const l={geometry:r,type:"Polygon"===s||"MultiPolygon"===s?3:"LineString"===s||"MultiLineString"===s?2:1,tags:n};null!==e.id&&(l.id=e.id),t.features.push(l)}}function w(t,e,n,o,i,s){const r=o*o;if(o>0&&e.size<(i?r:o))return void(n.numPoints+=e.length/3);const l=[];for(let t=0;t<e.length;t+=3)(0===o||e[t+2]>r)&&(n.numSimplified++,l.push(e[t],e[t+1])),n.numPoints++;i&&function(t,e){let n=0;for(let e=0,o=t.length,i=o-2;e<o;i=e,e+=2)n+=(t[e]-t[i])*(t[e+1]+t[i+1]);if(n>0===e)for(let e=0,n=t.length;e<n/2;e+=2){const o=t[e],i=t[e+1];t[e]=t[n-2-e],t[e+1]=t[n-1-e],t[n-2-e]=o,t[n-1-e]=i}}(l,s),t.push(l)}function X(t,e,n){const o=function(t){if(!t)return{};const e={};return e.removeAll=t.removeAll,e.remove=new Set(t.remove||[]),e.add=new Map(t.add?.map((t=>[t.id,t]))),e.update=new Map(t.update?.map((t=>[t.id,t]))),e}(e);let s=[];if(o.removeAll&&(s=t,t=[]),o.remove.size||o.add.size){const e=[];for(const n of t){const{id:t}=n;(o.remove.has(t)||o.add.has(t))&&e.push(n)}if(e.length){s.push(...e);const n=new Set(e.map((t=>t.id)));t=t.filter((t=>!n.has(t.id)))}if(o.add.size){let e=i({type:"FeatureCollection",features:Array.from(o.add.values())},n);e=y(e,n),s.push(...e),t.push(...e)}}if(o.update.size)for(const[e,i]of o.update){const o=t.findIndex((t=>t.id===e));if(-1===o)continue;const r=t[o],l=L(r,i,n);l&&(s.push(r,l),t[o]=l)}return{affected:s,source:t}}function L(t,e,n){const o=!!e.newGeometry,s=e.removeAllProperties||e.removeProperties?.length>0||e.addOrUpdateProperties?.length>0;if(!o&&!s)return null;if(o){let o=i({type:"FeatureCollection",features:[{type:"Feature",id:t.id,geometry:e.newGeometry,properties:s?I(t.tags,e):t.tags}]},n);return o=y(o,n),o[0]}if(s){const n={...t};return n.tags=I(n.tags,e),n}return null}function I(t,e){if(e.removeAllProperties)return{};const n={...t||{}};if(e.removeProperties)for(const t of e.removeProperties)delete n[t];if(e.addOrUpdateProperties)for(const{key:t,value:o}of e.addOrUpdateProperties)n[t]=o;return n}const Z={maxZoom:14,indexMaxZoom:5,indexMaxPoints:1e5,tolerance:3,extent:4096,buffer:64,lineMetrics:!1,promoteId:null,generateId:!1,updateable:!1,debug:0};class E{constructor(t,e){const n=(e=this.options=function(t,e){for(const n in e)t[n]=e[n];return t}(Object.create(Z),e)).debug;if(n&&console.time("preprocess data"),e.maxZoom<0||e.maxZoom>24)throw new Error("maxZoom should be in the 0-24 range");if(e.promoteId&&e.generateId)throw new Error("promoteId and generateId cannot be used together.");let o=i(t,e);this.tiles={},this.tileCoords=[],n&&(console.timeEnd("preprocess data"),console.log("index: maxZoom: %d, maxPoints: %d",e.indexMaxZoom,e.indexMaxPoints),console.time("generate tiles"),this.stats={},this.total=0),o=y(o,e),o.length&&this.splitTile(o,0,0,0),e.updateable&&(this.source=o),n&&(o.length&&console.log("features: %d, points: %d",this.tiles[0].numFeatures,this.tiles[0].numPoints),console.timeEnd("generate tiles"),console.log("tiles generated:",this.total,JSON.stringify(this.stats)))}splitTile(t,e,n,o,i,s,r){const l=[t,e,n,o],u=this.options,a=u.debug;for(;l.length;){o=l.pop(),n=l.pop(),e=l.pop(),t=l.pop();const f=1<<e,m=C(e,n,o);let d=this.tiles[m];if(!d&&(a>1&&console.time("creation"),d=this.tiles[m]=b(t,e,n,o,u),this.tileCoords.push({z:e,x:n,y:o,id:m}),a)){a>1&&(console.log("tile z%d-%d-%d (features: %d, points: %d, simplified: %d)",e,n,o,d.numFeatures,d.numPoints,d.numSimplified),console.timeEnd("creation"));const t=`z${e}`;this.stats[t]=(this.stats[t]||0)+1,this.total++}if(d.source=t,null==i){if(e===u.indexMaxZoom||d.numPoints<=u.indexMaxPoints)continue}else{if(e===u.maxZoom||e===i)continue;if(null!=i){const t=i-e;if(n!==s>>t||o!==r>>t)continue}}if(d.source=null,0===t.length)continue;a>1&&console.time("clipping");const h=.5*u.buffer/u.extent,p=.5-h,g=.5+h,x=1+h;let M=null,y=null,P=null,S=null;const z=c(t,f,n-h,n+g,0,d.minX,d.maxX,u),Y=c(t,f,n+p,n+x,0,d.minX,d.maxX,u);z&&(M=c(z,f,o-h,o+g,1,d.minY,d.maxY,u),y=c(z,f,o+p,o+x,1,d.minY,d.maxY,u)),Y&&(P=c(Y,f,o-h,o+g,1,d.minY,d.maxY,u),S=c(Y,f,o+p,o+x,1,d.minY,d.maxY,u)),a>1&&console.timeEnd("clipping"),l.push(M||[],e+1,2*n,2*o),l.push(y||[],e+1,2*n,2*o+1),l.push(P||[],e+1,2*n+1,2*o),l.push(S||[],e+1,2*n+1,2*o+1)}}getTile(t,e,n){t=+t,e=+e,n=+n;const o=this.options,{extent:i,debug:s}=o;if(t<0||t>24)return null;const r=1<<t,l=C(t,e=e+r&r-1,n);if(this.tiles[l])return z(this.tiles[l],i);s>1&&console.log("drilling down to z%d-%d-%d",t,e,n);let u,a=t,f=e,c=n;for(;!u&&a>0;)a--,f>>=1,c>>=1,u=this.tiles[C(a,f,c)];return u&&u.source?(s>1&&(console.log("found parent tile z%d-%d-%d",a,f,c),console.time("drilling down")),this.splitTile(u.source,a,f,c,t,e,n),s>1&&console.timeEnd("drilling down"),this.tiles[l]?z(this.tiles[l],i):null):null}invalidateTiles(t){const e=this.options,{debug:n}=e;let o=1/0,i=-1/0,s=1/0,r=-1/0;for(const e of t)o=Math.min(o,e.minX),i=Math.max(i,e.maxX),s=Math.min(s,e.minY),r=Math.max(r,e.maxY);const l=e.buffer/e.extent,u=new Set;for(const e in this.tiles){const a=this.tiles[e],f=1<<a.z,c=(a.x-l)/f,m=(a.x+1+l)/f,d=(a.y-l)/f,h=(a.y+1+l)/f;if(i<c||o>=m||r<d||s>=h)continue;let p=!1;for(const e of t)if(e.maxX>=c&&e.minX<m&&e.maxY>=d&&e.minY<h){p=!0;break}if(p){if(n){n>1&&console.log("invalidate tile z%d-%d-%d (features: %d, points: %d, simplified: %d)",a.z,a.x,a.y,a.numFeatures,a.numPoints,a.numSimplified);const t=`z${a.z}`;this.stats[t]=(this.stats[t]||0)-1,this.total--}delete this.tiles[e],u.add(e)}}u.size&&(this.tileCoords=this.tileCoords.filter((t=>!u.has(t.id))))}updateData(t){const e=this.options,n=e.debug;if(!e.updateable)throw new Error("to update tile geojson `updateable` option must be set to true");const{affected:o,source:i}=X(this.source,t,e);if(!o.length)return;this.source=i,n>1&&(console.log("invalidating tiles"),console.time("invalidating")),this.invalidateTiles(o),n>1&&console.timeEnd("invalidating");const[s,r,l]=[0,0,0],u=b(this.source,s,r,l,this.options);u.source=this.source;const a=C(s,r,l);if(this.tiles[a]=u,this.tileCoords.push({z:s,x:r,y:l,id:a}),n){const t=`z${s}`;this.stats[t]=(this.stats[t]||0)+1,this.total++}}}function C(t,e,n){return 32*((1<<t)*n+e)+t}return function(t,e){return new E(t,e)}}));
1
+ !function(t,e){"object"==typeof exports&&"undefined"!=typeof module?module.exports=e():"function"==typeof define&&define.amd?define(e):(t="undefined"!=typeof globalThis?globalThis:t||self).geojsonvt=e()}(this,(function(){"use strict";function t(n,o,i,s){let r=s;const l=o+(i-o>>1);let a,c=i-o;const u=n[o],f=n[o+1],m=n[i],d=n[i+1];for(let t=o+3;t<i;t+=3){const o=e(n[t],n[t+1],u,f,m,d);if(o>r)a=t,r=o;else if(o===r){const e=Math.abs(t-l);e<c&&(a=t,c=e)}}r>s&&(a-o>3&&t(n,o,a,s),n[a+2]=r,i-a>3&&t(n,a,i,s))}function e(t,e,n,o,i,s){let r=i-n,l=s-o;if(0!==r||0!==l){const a=((t-n)*r+(e-o)*l)/(r*r+l*l);a>1?(n=i,o=s):a>0&&(n+=r*a,o+=l*a)}return r=t-n,l=e-o,r*r+l*l}function n(t,e,n,i){const s={type:e,geom:n},r={id:null==t?null:t,type:s.type,geometry:s.geom,tags:i,minX:1/0,minY:1/0,maxX:-1/0,maxY:-1/0};switch(s.type){case"Point":case"MultiPoint":case"LineString":o(r,s.geom);break;case"Polygon":o(r,s.geom[0]);break;case"MultiLineString":for(const t of s.geom)o(r,t);break;case"MultiPolygon":for(const t of s.geom)o(r,t[0])}return r}function o(t,e){for(let n=0;n<e.length;n+=3)t.minX=Math.min(t.minX,e[n]),t.minY=Math.min(t.minY,e[n+1]),t.maxX=Math.max(t.maxX,e[n]),t.maxY=Math.max(t.maxY,e[n+1])}function i(t,e){const n=[];switch(t.type){case"FeatureCollection":for(let o=0;o<t.features.length;o++)s(n,t.features[o],e,o);break;case"Feature":s(n,t,e);break;default:s(n,{geometry:t,properties:void 0},e)}return n}function s(t,e,o,i){if(!e.geometry)return;if("GeometryCollection"===e.geometry.type){for(const n of e.geometry.geometries)s(t,{id:e.id,geometry:n,properties:e.properties},o,i);return}const c=e.geometry.coordinates;if(!c?.length)return;const u=Math.pow(o.tolerance/((1<<o.maxZoom)*o.extent),2);let f=e.id;switch(o.promoteId?f=e.properties?.[o.promoteId]:o.generateId&&(f=i||0),e.geometry.type){case"Point":{const o=[];return r(e.geometry.coordinates,o),void t.push(n(f,e.geometry.type,o,e.properties))}case"MultiPoint":{const o=[];for(const t of e.geometry.coordinates)r(t,o);return void t.push(n(f,e.geometry.type,o,e.properties))}case"LineString":{const o=[];return l(e.geometry.coordinates,o,u,!1),void t.push(n(f,e.geometry.type,o,e.properties))}case"MultiLineString":{if(o.lineMetrics){for(const o of e.geometry.coordinates){const i=[];l(o,i,u,!1),t.push(n(f,"LineString",i,e.properties))}return}const i=[];return a(e.geometry.coordinates,i,u,!1),void t.push(n(f,e.geometry.type,i,e.properties))}case"Polygon":{const o=[];return a(e.geometry.coordinates,o,u,!0),void t.push(n(f,e.geometry.type,o,e.properties))}case"MultiPolygon":{const o=[];for(const t of e.geometry.coordinates){const e=[];a(t,e,u,!0),o.push(e)}return void t.push(n(f,e.geometry.type,o,e.properties))}default:throw new Error("Input data is not a valid GeoJSON object.")}}function r(t,e){e.push(c(t[0]),u(t[1]),0)}function l(e,n,o,i){let s,r,l=0;for(let t=0;t<e.length;t++){const o=c(e[t][0]),a=u(e[t][1]);n.push(o,a,0),t>0&&(l+=i?(s*a-o*r)/2:Math.sqrt(Math.pow(o-s,2)+Math.pow(a-r,2))),s=o,r=a}const a=n.length-3;n[2]=1,o>0&&t(n,0,a,o),n[a+2]=1,n.size=Math.abs(l),n.start=0,n.end=n.size}function a(t,e,n,o){for(let i=0;i<t.length;i++){const s=[];l(t[i],s,n,o),e.push(s)}}function c(t){return t/360+.5}function u(t){const e=Math.sin(t*Math.PI/180),n=.5-.25*Math.log((1+e)/(1-e))/Math.PI;return n<0?0:n>1?1:n}function f(t,e,o,i,s,r,l,a){if(i/=e,r>=(o/=e)&&l<i)return t;if(l<o||r>=i)return null;const c=[];for(const e of t){const t=0===s?e.minX:e.minY,r=0===s?e.maxX:e.maxY;if(t>=o&&r<i)c.push(e);else if(!(r<o||t>=i))switch(e.type){case"Point":case"MultiPoint":{const t=[];if(m(e.geometry,t,o,i,s),!t.length)continue;const r=3===t.length?"Point":"MultiPoint";c.push(n(e.id,r,t,e.tags));continue}case"LineString":{const t=[];if(d(e.geometry,t,o,i,s,!1,a.lineMetrics),!t.length)continue;if(a.lineMetrics){for(const o of t)c.push(n(e.id,e.type,o,e.tags));continue}if(t.length>1){c.push(n(e.id,"MultiLineString",t,e.tags));continue}c.push(n(e.id,e.type,t[0],e.tags));continue}case"MultiLineString":{const t=[];if(g(e.geometry,t,o,i,s,!1),!t.length)continue;if(1===t.length){c.push(n(e.id,"LineString",t[0],e.tags));continue}c.push(n(e.id,e.type,t,e.tags));continue}case"Polygon":{const t=[];if(g(e.geometry,t,o,i,s,!0),!t.length)continue;c.push(n(e.id,e.type,t,e.tags));continue}case"MultiPolygon":{const t=[];for(const n of e.geometry){const e=[];g(n,e,o,i,s,!0),e.length&&t.push(e)}if(!t.length)continue;c.push(n(e.id,e.type,t,e.tags));continue}}}return c.length?c:null}function m(t,e,n,o,i){for(let s=0;s<t.length;s+=3){const r=t[s+i];r>=n&&r<=o&&h(e,t[s],t[s+1],t[s+2])}}function d(t,e,n,o,i,s,r){let l=p(t);const a=0===i?y:x;let c,u,f=t.start;for(let m=0;m<t.length-3;m+=3){const d=t[m],g=t[m+1],y=t[m+2],x=t[m+3],M=t[m+4],P=0===i?d:g,b=0===i?x:M;let w=!1;r&&(c=Math.sqrt(Math.pow(d-x,2)+Math.pow(g-M,2))),P<n?b>n&&(u=a(l,d,g,x,M,n),r&&(l.start=f+c*u)):P>o?b<o&&(u=a(l,d,g,x,M,o),r&&(l.start=f+c*u)):h(l,d,g,y),b<n&&P>=n&&(u=a(l,d,g,x,M,n),w=!0),b>o&&P<=o&&(u=a(l,d,g,x,M,o),w=!0),!s&&w&&(r&&(l.end=f+c*u),e.push(l),l=p(t)),r&&(f+=c)}let m=t.length-3;const d=t[m],g=t[m+1],M=t[m+2],P=0===i?d:g;P>=n&&P<=o&&h(l,d,g,M),m=l.length-3,s&&m>=3&&(l[m]!==l[0]||l[m+1]!==l[1])&&h(l,l[0],l[1],l[2]),l.length&&e.push(l)}function p(t){const e=[];return e.size=t.size,e.start=t.start,e.end=t.end,e}function g(t,e,n,o,i,s){for(const r of t)d(r,e,n,o,i,s,!1)}function h(t,e,n,o){t.push(e,n,o)}function y(t,e,n,o,i,s){const r=(s-e)/(o-e);return h(t,s,n+(i-n)*r,1),r}function x(t,e,n,o,i,s){const r=(s-n)/(i-n);return h(t,e+(o-e)*r,s,1),r}function M(t,e){const n=e.buffer/e.extent;let o=t;const i=f(t,1,-1-n,n,0,-1,2,e),s=f(t,1,1-n,2+n,0,-1,2,e);return i||s?(o=f(t,1,-n,1+n,0,-1,2,e)||[],i&&(o=P(i,1).concat(o)),s&&(o=o.concat(P(s,-1))),o):o}function P(t,e){const o=[];for(const i of t)switch(i.type){case"Point":case"MultiPoint":case"LineString":{const t=b(i.geometry,e);o.push(n(i.id,i.type,t,i.tags));continue}case"MultiLineString":case"Polygon":{const t=[];for(const n of i.geometry)t.push(b(n,e));o.push(n(i.id,i.type,t,i.tags));continue}case"MultiPolygon":{const t=[];for(const n of i.geometry){const o=[];for(const t of n)o.push(b(t,e));t.push(o)}o.push(n(i.id,i.type,t,i.tags));continue}}return o}function b(t,e){const n=[];n.size=t.size,void 0!==t.start&&(n.start=t.start,n.end=t.end);for(let o=0;o<t.length;o+=3)n.push(t[o]+e,t[o+1],t[o+2]);return n}function w(t,e){if(t.transformed)return t;const n=1<<t.z,o=t.x,i=t.y;for(const s of t.features){const t=s.geometry,r=s.type;if(s.geometry=[],1!==r)for(const r of t){const t=[];for(let s=0;s<r.length;s+=2)t.push(v(r[s],r[s+1],e,n,o,i));s.geometry.push(t)}else for(let r=0;r<t.length;r+=2)s.geometry.push(v(t[r],t[r+1],e,n,o,i))}return t.transformed=!0,t}function v(t,e,n,o,i,s){return[Math.round(n*(t*o-i)),Math.round(n*(e*o-s))]}function z(t,e,n,o,i){const s=e===i.maxZoom?0:i.tolerance/((1<<e)*i.extent),r={features:[],numPoints:0,numSimplified:0,numFeatures:t.length,source:null,x:n,y:o,z:e,transformed:!1,minX:2,minY:1,maxX:-1,maxY:0};for(const e of t)Y(r,e,s,i);return r}function Y(t,e,n,o){const i=[];switch(t.minX=Math.min(t.minX,e.minX),t.minY=Math.min(t.minY,e.minY),t.maxX=Math.max(t.maxX,e.maxX),t.maxY=Math.max(t.maxY,e.maxY),e.type){case"Point":case"MultiPoint":for(let n=0;n<e.geometry.length;n+=3)i.push(e.geometry[n],e.geometry[n+1]),t.numPoints++,t.numSimplified++;break;case"LineString":S(i,e.geometry,t,n,!1,!1);break;case"MultiLineString":case"Polygon":for(let o=0;o<e.geometry.length;o++)S(i,e.geometry[o],t,n,"Polygon"===e.type,0===o);break;case"MultiPolygon":for(let o=0;o<e.geometry.length;o++){const s=e.geometry[o];for(let e=0;e<s.length;e++)S(i,s[e],t,n,!0,0===e)}}if(!i.length)return;let s=e.tags||null;if("LineString"===e.type&&o.lineMetrics){s={};for(const t in e.tags)s[t]=e.tags[t];s.mapbox_clip_start=e.geometry.start/e.geometry.size,s.mapbox_clip_end=e.geometry.end/e.geometry.size}const r={geometry:i,type:"Polygon"===e.type||"MultiPolygon"===e.type?3:"LineString"===e.type||"MultiLineString"===e.type?2:1,tags:s};null!==e.id&&(r.id=e.id),t.features.push(r)}function S(t,e,n,o,i,s){const r=o*o;if(o>0&&e.size<(i?r:o))return void(n.numPoints+=e.length/3);const l=[];for(let t=0;t<e.length;t+=3)(0===o||e[t+2]>r)&&(n.numSimplified++,l.push(e[t],e[t+1])),n.numPoints++;i&&function(t,e){let n=0;for(let e=0,o=t.length,i=o-2;e<o;i=e,e+=2)n+=(t[e]-t[i])*(t[e+1]+t[i+1]);if(n>0!==e)return;for(let e=0,n=t.length;e<n/2;e+=2){const o=t[e],i=t[e+1];t[e]=t[n-2-e],t[e+1]=t[n-1-e],t[n-2-e]=o,t[n-1-e]=i}}(l,s),t.push(l)}function X(t,e,n){const o=function(t){if(!t)return{remove:new Set,add:new Map,update:new Map};const e={removeAll:t.removeAll,remove:new Set(t.remove||[]),add:new Map(t.add?.map((t=>[t.id,t]))),update:new Map(t.update?.map((t=>[t.id,t])))};return e}(e);let s=[];if(o.removeAll&&(s=t,t=[]),o.remove.size||o.add.size){const e=[];for(const n of t){const{id:t}=n;(o.remove.has(t)||o.add.has(t))&&e.push(n)}if(e.length){s.push(...e);const n=new Set(e.map((t=>t.id)));t=t.filter((t=>!n.has(t.id)))}if(o.add.size){let e=i({type:"FeatureCollection",features:Array.from(o.add.values())},n);e=M(e,n),s.push(...e),t.push(...e)}}if(o.update.size)for(const[e,i]of o.update){const o=t.findIndex((t=>t.id===e));if(-1===o)continue;const r=t[o],l=L(r,i,n);l&&(s.push(r,l),t[o]=l)}return{affected:s,source:t}}function L(t,e,n){const o=!!e.newGeometry,s=e.removeAllProperties||e.removeProperties?.length>0||e.addOrUpdateProperties?.length>0;if(o){let o=i({type:"FeatureCollection",features:[{type:"Feature",id:t.id,geometry:e.newGeometry,properties:s?I(t.tags,e):t.tags}]},n);return o=M(o,n),o[0]}if(s){const n={...t};return n.tags=I(n.tags,e),n}return null}function I(t,e){if(e.removeAllProperties)return{};const n={...t||{}};if(e.removeProperties)for(const t of e.removeProperties)delete n[t];if(e.addOrUpdateProperties)for(const{key:t,value:o}of e.addOrUpdateProperties)n[t]=o;return n}const Z={maxZoom:14,indexMaxZoom:5,indexMaxPoints:1e5,tolerance:3,extent:4096,buffer:64,lineMetrics:!1,promoteId:null,generateId:!1,updateable:!1,debug:0};class k{options;tiles;tileCoords;stats={};total=0;source;constructor(t,e){const n=(e=this.options=Object.assign({},Z,e)).debug;if(n&&console.time("preprocess data"),e.maxZoom<0||e.maxZoom>24)throw new Error("maxZoom should be in the 0-24 range");if(e.promoteId&&e.generateId)throw new Error("promoteId and generateId cannot be used together.");let o=i(t,e);this.tiles={},this.tileCoords=[],n&&(console.timeEnd("preprocess data"),console.log("index: maxZoom: %d, maxPoints: %d",e.indexMaxZoom,e.indexMaxPoints),console.time("generate tiles"),this.stats={},this.total=0),o=M(o,e),o.length&&this.splitTile(o,0,0,0),e.updateable&&(this.source=o),n&&(o.length&&console.log("features: %d, points: %d",this.tiles[0].numFeatures,this.tiles[0].numPoints),console.timeEnd("generate tiles"),console.log("tiles generated:",this.total,JSON.stringify(this.stats)))}splitTile(t,e,n,o,i,s,r){const l=[t,e,n,o],a=this.options,c=a.debug;for(;l.length;){o=l.pop(),n=l.pop(),e=l.pop(),t=l.pop();const u=1<<e,m=C(e,n,o);let d=this.tiles[m];if(!d&&(c>1&&console.time("creation"),d=this.tiles[m]=z(t,e,n,o,a),this.tileCoords.push({z:e,x:n,y:o,id:m}),c)){c>1&&(console.log("tile z%d-%d-%d (features: %d, points: %d, simplified: %d)",e,n,o,d.numFeatures,d.numPoints,d.numSimplified),console.timeEnd("creation"));const t=`z${e}`;this.stats[t]=(this.stats[t]||0)+1,this.total++}if(d.source=t,null==i){if(e===a.indexMaxZoom||d.numPoints<=a.indexMaxPoints)continue}else{if(e===a.maxZoom||e===i)continue;if(null!=i){const t=i-e;if(n!==s>>t||o!==r>>t)continue}}if(d.source=null,!t.length)continue;c>1&&console.time("clipping");const p=.5*a.buffer/a.extent,g=.5-p,h=.5+p,y=1+p;let x=null,M=null,P=null,b=null;const w=f(t,u,n-p,n+h,0,d.minX,d.maxX,a),v=f(t,u,n+g,n+y,0,d.minX,d.maxX,a);w&&(x=f(w,u,o-p,o+h,1,d.minY,d.maxY,a),M=f(w,u,o+g,o+y,1,d.minY,d.maxY,a)),v&&(P=f(v,u,o-p,o+h,1,d.minY,d.maxY,a),b=f(v,u,o+g,o+y,1,d.minY,d.maxY,a)),c>1&&console.timeEnd("clipping"),l.push(x||[],e+1,2*n,2*o),l.push(M||[],e+1,2*n,2*o+1),l.push(P||[],e+1,2*n+1,2*o),l.push(b||[],e+1,2*n+1,2*o+1)}}getTile(t,e,n){t=+t,e=+e,n=+n;const o=this.options,{extent:i,debug:s}=o;if(t<0||t>24)return null;const r=1<<t,l=C(t,e=e+r&r-1,n);if(this.tiles[l])return w(this.tiles[l],i);s>1&&console.log("drilling down to z%d-%d-%d",t,e,n);let a,c=t,u=e,f=n;for(;!a&&c>0;)c--,u>>=1,f>>=1,a=this.tiles[C(c,u,f)];return a?.source?(s>1&&(console.log("found parent tile z%d-%d-%d",c,u,f),console.time("drilling down")),this.splitTile(a.source,c,u,f,t,e,n),s>1&&console.timeEnd("drilling down"),this.tiles[l]?w(this.tiles[l],i):null):null}invalidateTiles(t){const e=this.options,{debug:n}=e;let o=1/0,i=-1/0,s=1/0,r=-1/0;for(const e of t)o=Math.min(o,e.minX),i=Math.max(i,e.maxX),s=Math.min(s,e.minY),r=Math.max(r,e.maxY);const l=e.buffer/e.extent,a=new Set;for(const e in this.tiles){const c=this.tiles[e],u=1<<c.z,f=(c.x-l)/u,m=(c.x+1+l)/u,d=(c.y-l)/u,p=(c.y+1+l)/u;if(i<f||o>=m||r<d||s>=p)continue;let g=!1;for(const e of t)if(e.maxX>=f&&e.minX<m&&e.maxY>=d&&e.minY<p){g=!0;break}if(g){if(n){n>1&&console.log("invalidate tile z%d-%d-%d (features: %d, points: %d, simplified: %d)",c.z,c.x,c.y,c.numFeatures,c.numPoints,c.numSimplified);const t=`z${c.z}`;this.stats[t]=(this.stats[t]||0)-1,this.total--}delete this.tiles[e],a.add(e)}}a.size&&(this.tileCoords=this.tileCoords.filter((t=>!a.has(t.id))))}updateData(t){const e=this.options,n=e.debug;if(!e.updateable)throw new Error("to update tile geojson `updateable` option must be set to true");const{affected:o,source:i}=X(this.source,t,e);if(!o.length)return;this.source=i,n>1&&(console.log("invalidating tiles"),console.time("invalidating")),this.invalidateTiles(o),n>1&&console.timeEnd("invalidating");const[s,r,l]=[0,0,0],a=z(this.source,s,r,l,this.options);a.source=this.source;const c=C(s,r,l);if(this.tiles[c]=a,this.tileCoords.push({z:s,x:r,y:l,id:c}),n){const t=`z${s}`;this.stats[t]=(this.stats[t]||0)+1,this.total++}}}function C(t,e,n){return 32*((1<<t)*n+e)+t}return function(t,e){return new k(t,e)}}));