@loaders.gl/mvt 4.2.1 → 4.3.0-alpha.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.
Files changed (120) hide show
  1. package/dist/dist.dev.js +1784 -847
  2. package/dist/dist.min.js +1 -1
  3. package/dist/index.cjs +713 -640
  4. package/dist/index.cjs.map +4 -4
  5. package/dist/index.d.ts +2 -2
  6. package/dist/index.d.ts.map +1 -1
  7. package/dist/index.js +1 -1
  8. package/dist/lib/parse-mvt.d.ts +2 -1
  9. package/dist/lib/parse-mvt.d.ts.map +1 -1
  10. package/dist/lib/parse-mvt.js +15 -45
  11. package/dist/lib/parse-tilejson.d.ts +4 -4
  12. package/dist/lib/parse-tilejson.d.ts.map +1 -1
  13. package/dist/lib/types.d.ts +1 -39
  14. package/dist/lib/types.d.ts.map +1 -1
  15. package/dist/lib/utils/geometry-utils.d.ts +83 -0
  16. package/dist/lib/utils/geometry-utils.d.ts.map +1 -0
  17. package/dist/lib/utils/geometry-utils.js +206 -0
  18. package/dist/lib/vector-tile/vector-tile-feature.d.ts +72 -0
  19. package/dist/lib/vector-tile/vector-tile-feature.d.ts.map +1 -0
  20. package/dist/lib/vector-tile/vector-tile-feature.js +342 -0
  21. package/dist/lib/{mapbox-vector-tile → vector-tile}/vector-tile-layer.d.ts +10 -1
  22. package/dist/lib/vector-tile/vector-tile-layer.d.ts.map +1 -0
  23. package/dist/lib/{mapbox-vector-tile → vector-tile}/vector-tile-layer.js +16 -1
  24. package/dist/lib/vector-tile/vector-tile.d.ts.map +1 -0
  25. package/dist/lib/{geojson-tiler → vector-tiler}/clip.d.ts +3 -3
  26. package/dist/lib/vector-tiler/clip.d.ts.map +1 -0
  27. package/dist/lib/vector-tiler/convert.d.ts +18 -0
  28. package/dist/lib/vector-tiler/convert.d.ts.map +1 -0
  29. package/dist/lib/{geojson-tiler → vector-tiler}/convert.js +8 -1
  30. package/dist/lib/vector-tiler/feature.d.ts +3 -0
  31. package/dist/lib/vector-tiler/feature.d.ts.map +1 -0
  32. package/dist/lib/vector-tiler/simplify.d.ts.map +1 -0
  33. package/dist/lib/{geojson-tiler → vector-tiler}/tile.d.ts +4 -4
  34. package/dist/lib/vector-tiler/tile.d.ts.map +1 -0
  35. package/dist/lib/vector-tiler/transform.d.ts +7 -0
  36. package/dist/lib/vector-tiler/transform.d.ts.map +1 -0
  37. package/dist/lib/{geojson-tiler → vector-tiler}/wrap.d.ts +2 -2
  38. package/dist/lib/vector-tiler/wrap.d.ts.map +1 -0
  39. package/dist/mvt-loader.d.ts +19 -8
  40. package/dist/mvt-loader.d.ts.map +1 -1
  41. package/dist/mvt-loader.js +3 -2
  42. package/dist/mvt-source.d.ts +4 -4
  43. package/dist/mvt-source.d.ts.map +1 -1
  44. package/dist/mvt-source.js +7 -7
  45. package/dist/mvt-worker.js +1244 -762
  46. package/dist/table-tile-source.d.ts +118 -0
  47. package/dist/table-tile-source.d.ts.map +1 -0
  48. package/dist/table-tile-source.js +370 -0
  49. package/dist/tilejson-loader.js +1 -1
  50. package/package.json +7 -6
  51. package/src/index.ts +3 -3
  52. package/src/lib/parse-mvt.ts +28 -66
  53. package/src/lib/parse-tilejson.ts +5 -5
  54. package/src/lib/types.ts +1 -39
  55. package/src/lib/utils/geometry-utils.ts +234 -0
  56. package/src/lib/vector-tile/vector-tile-feature.ts +416 -0
  57. package/src/lib/{mapbox-vector-tile → vector-tile}/vector-tile-layer.ts +28 -2
  58. package/src/lib/{geojson-tiler → vector-tiler}/clip.ts +4 -4
  59. package/src/lib/{geojson-tiler → vector-tiler}/convert.ts +19 -9
  60. package/src/lib/{geojson-tiler → vector-tiler}/feature.ts +3 -3
  61. package/src/lib/{geojson-tiler → vector-tiler}/tile.ts +10 -10
  62. package/src/lib/{geojson-tiler → vector-tiler}/transform.ts +2 -2
  63. package/src/lib/{geojson-tiler → vector-tiler}/wrap.ts +5 -5
  64. package/src/mvt-loader.ts +14 -6
  65. package/src/mvt-source.ts +9 -10
  66. package/src/table-tile-source.ts +508 -0
  67. package/dist/helpers/binary-util-functions.d.ts +0 -35
  68. package/dist/helpers/binary-util-functions.d.ts.map +0 -1
  69. package/dist/helpers/binary-util-functions.js +0 -114
  70. package/dist/helpers/mapbox-util-functions.d.ts +0 -29
  71. package/dist/helpers/mapbox-util-functions.d.ts.map +0 -1
  72. package/dist/helpers/mapbox-util-functions.js +0 -78
  73. package/dist/lib/binary-vector-tile/vector-tile-feature.d.ts +0 -41
  74. package/dist/lib/binary-vector-tile/vector-tile-feature.d.ts.map +0 -1
  75. package/dist/lib/binary-vector-tile/vector-tile-feature.js +0 -163
  76. package/dist/lib/binary-vector-tile/vector-tile-layer.d.ts +0 -23
  77. package/dist/lib/binary-vector-tile/vector-tile-layer.d.ts.map +0 -1
  78. package/dist/lib/binary-vector-tile/vector-tile-layer.js +0 -96
  79. package/dist/lib/binary-vector-tile/vector-tile.d.ts +0 -9
  80. package/dist/lib/binary-vector-tile/vector-tile.d.ts.map +0 -1
  81. package/dist/lib/binary-vector-tile/vector-tile.js +0 -27
  82. package/dist/lib/geojson-tiler/clip.d.ts.map +0 -1
  83. package/dist/lib/geojson-tiler/convert.d.ts +0 -10
  84. package/dist/lib/geojson-tiler/convert.d.ts.map +0 -1
  85. package/dist/lib/geojson-tiler/feature.d.ts +0 -3
  86. package/dist/lib/geojson-tiler/feature.d.ts.map +0 -1
  87. package/dist/lib/geojson-tiler/geojson-tiler.d.ts +0 -44
  88. package/dist/lib/geojson-tiler/geojson-tiler.d.ts.map +0 -1
  89. package/dist/lib/geojson-tiler/geojson-tiler.js +0 -209
  90. package/dist/lib/geojson-tiler/simplify.d.ts.map +0 -1
  91. package/dist/lib/geojson-tiler/tile.d.ts.map +0 -1
  92. package/dist/lib/geojson-tiler/transform.d.ts +0 -7
  93. package/dist/lib/geojson-tiler/transform.d.ts.map +0 -1
  94. package/dist/lib/geojson-tiler/wrap.d.ts.map +0 -1
  95. package/dist/lib/mapbox-vector-tile/vector-tile-feature.d.ts +0 -27
  96. package/dist/lib/mapbox-vector-tile/vector-tile-feature.d.ts.map +0 -1
  97. package/dist/lib/mapbox-vector-tile/vector-tile-feature.js +0 -178
  98. package/dist/lib/mapbox-vector-tile/vector-tile-layer.d.ts.map +0 -1
  99. package/dist/lib/mapbox-vector-tile/vector-tile.d.ts.map +0 -1
  100. package/src/helpers/binary-util-functions.ts +0 -125
  101. package/src/helpers/mapbox-util-functions.ts +0 -82
  102. package/src/lib/binary-vector-tile/vector-tile-feature.ts +0 -203
  103. package/src/lib/binary-vector-tile/vector-tile-layer.ts +0 -113
  104. package/src/lib/binary-vector-tile/vector-tile.ts +0 -36
  105. package/src/lib/geojson-tiler/geojson-tiler.ts +0 -283
  106. package/src/lib/mapbox-vector-tile/LICENSE.txt +0 -31
  107. package/src/lib/mapbox-vector-tile/vector-tile-feature.ts +0 -207
  108. /package/dist/lib/{mapbox-vector-tile → vector-tile}/vector-tile.d.ts +0 -0
  109. /package/dist/lib/{mapbox-vector-tile → vector-tile}/vector-tile.js +0 -0
  110. /package/dist/lib/{geojson-tiler → vector-tiler}/clip.js +0 -0
  111. /package/dist/lib/{geojson-tiler → vector-tiler}/feature.js +0 -0
  112. /package/dist/lib/{geojson-tiler → vector-tiler}/simplify.d.ts +0 -0
  113. /package/dist/lib/{geojson-tiler → vector-tiler}/simplify.js +0 -0
  114. /package/dist/lib/{geojson-tiler → vector-tiler}/tile.js +0 -0
  115. /package/dist/lib/{geojson-tiler → vector-tiler}/transform.js +0 -0
  116. /package/dist/lib/{geojson-tiler → vector-tiler}/wrap.js +0 -0
  117. /package/src/lib/{binary-vector-tile → vector-tile}/LICENSE.txt +0 -0
  118. /package/src/lib/{mapbox-vector-tile → vector-tile}/vector-tile.ts +0 -0
  119. /package/src/lib/{geojson-tiler → vector-tiler}/LICENSE +0 -0
  120. /package/src/lib/{geojson-tiler → vector-tiler}/simplify.ts +0 -0
@@ -2,23 +2,17 @@
2
2
  // SPDX-License-Identifier: MIT
3
3
  // Copyright vis.gl contributors
4
4
 
5
+ import type {FlatFeature, Feature, GeojsonGeometryInfo} from '@loaders.gl/schema';
6
+ import type {GeoJSONTable, BinaryFeatureCollection} from '@loaders.gl/schema';
5
7
  import {flatGeojsonToBinary} from '@loaders.gl/gis';
6
- import type {
7
- FlatFeature,
8
- Feature,
9
- GeojsonGeometryInfo,
10
- BinaryFeatureCollection,
11
- GeoJSONTable
12
- } from '@loaders.gl/schema';
8
+ import {log} from '@loaders.gl/loader-utils';
13
9
  import Protobuf from 'pbf';
14
10
 
15
- import type {MVTMapboxCoordinates, MVTOptions} from '../lib/types';
16
- import type {MVTLoaderOptions} from '../mvt-loader';
11
+ import {VectorTile} from './vector-tile/vector-tile';
12
+ import {VectorTileFeature} from './vector-tile/vector-tile-feature';
17
13
 
18
- import {VectorTile} from './mapbox-vector-tile/vector-tile';
19
- import {BinaryVectorTile} from './binary-vector-tile/vector-tile';
20
- import {BinaryVectorTileFeature} from './binary-vector-tile/vector-tile-feature';
21
- import {VectorTileFeature as VectorTileFeatureMapBox} from './mapbox-vector-tile/vector-tile-feature';
14
+ import type {MVTLoaderOptions} from '../mvt-loader';
15
+ type MVTOptions = Required<MVTLoaderOptions>['mvt'];
22
16
 
23
17
  /**
24
18
  * Parse MVT arrayBuffer and return GeoJSON.
@@ -28,7 +22,7 @@ import {VectorTileFeature as VectorTileFeatureMapBox} from './mapbox-vector-tile
28
22
  * @returns A GeoJSON geometry object or a binary representation
29
23
  */
30
24
  export function parseMVT(arrayBuffer: ArrayBuffer, options?: MVTLoaderOptions) {
31
- const mvtOptions = normalizeOptions(options);
25
+ const mvtOptions = checkOptions(options);
32
26
 
33
27
  const shape: string | undefined =
34
28
  options?.gis?.format || options?.mvt?.shape || (options?.shape as string);
@@ -87,7 +81,7 @@ function parseToFlatGeoJson(
87
81
  return [features, geometryInfo];
88
82
  }
89
83
 
90
- const tile = new BinaryVectorTile(new Protobuf(arrayBuffer));
84
+ const tile = new VectorTile(new Protobuf(arrayBuffer));
91
85
 
92
86
  const selectedLayers =
93
87
  options && Array.isArray(options.layers) ? options.layers : Object.keys(tile.layers);
@@ -99,7 +93,7 @@ function parseToFlatGeoJson(
99
93
  }
100
94
 
101
95
  for (let i = 0; i < vectorTileLayer.length; i++) {
102
- const vectorTileFeature = vectorTileLayer.feature(i, geometryInfo);
96
+ const vectorTileFeature = vectorTileLayer.getBinaryFeature(i, geometryInfo);
103
97
  const decodedFeature = getDecodedFeatureBinary(vectorTileFeature, options, layerName);
104
98
  features.push(decodedFeature);
105
99
  }
@@ -113,7 +107,7 @@ function parseToGeojsonFeatures(arrayBuffer: ArrayBuffer, options: MVTOptions):
113
107
  return [];
114
108
  }
115
109
 
116
- const features: MVTMapboxCoordinates[] = [];
110
+ const features: Feature[] = [];
117
111
  const tile = new VectorTile(new Protobuf(arrayBuffer));
118
112
 
119
113
  const selectedLayers = Array.isArray(options.layers) ? options.layers : Object.keys(tile.layers);
@@ -125,33 +119,29 @@ function parseToGeojsonFeatures(arrayBuffer: ArrayBuffer, options: MVTOptions):
125
119
  }
126
120
 
127
121
  for (let i = 0; i < vectorTileLayer.length; i++) {
128
- const vectorTileFeature = vectorTileLayer.feature(i);
122
+ const vectorTileFeature = vectorTileLayer.getGeoJSONFeature(i);
129
123
  const decodedFeature = getDecodedFeature(vectorTileFeature, options, layerName);
130
124
  features.push(decodedFeature);
131
125
  }
132
126
  });
133
127
 
134
- return features as Feature[];
128
+ return features;
135
129
  }
136
130
 
137
- function normalizeOptions(options?: MVTLoaderOptions): MVTOptions {
131
+ /** Check that options are good */
132
+ function checkOptions(options?: MVTLoaderOptions): MVTOptions {
138
133
  if (!options?.mvt) {
139
134
  throw new Error('mvt options required');
140
135
  }
141
136
 
142
- // Validate
143
- const wgs84Coordinates = options.mvt?.coordinates === 'wgs84';
144
- const {tileIndex} = options.mvt;
145
- const hasTileIndex =
146
- tileIndex &&
147
- Number.isFinite(tileIndex.x) &&
148
- Number.isFinite(tileIndex.y) &&
149
- Number.isFinite(tileIndex.z);
150
-
151
- if (wgs84Coordinates && !hasTileIndex) {
137
+ if (options.mvt?.coordinates === 'wgs84' && !options.mvt.tileIndex) {
152
138
  throw new Error('MVT Loader: WGS84 coordinates need tileIndex property');
153
139
  }
154
140
 
141
+ if (options.gis) {
142
+ log.warn('MVTLoader: "options.gis" is deprecated, use "options.mvt.shape" instead')();
143
+ }
144
+
155
145
  return options.mvt;
156
146
  }
157
147
 
@@ -161,17 +151,18 @@ function normalizeOptions(options?: MVTLoaderOptions): MVTOptions {
161
151
  * @returns decoded feature
162
152
  */
163
153
  function getDecodedFeature(
164
- feature: VectorTileFeatureMapBox,
154
+ feature: VectorTileFeature,
165
155
  options: MVTOptions,
166
156
  layerName: string
167
- ): MVTMapboxCoordinates {
168
- const decodedFeature = feature.toGeoJSON(
169
- // @ts-expect-error What is going on here?
170
- options.coordinates === 'wgs84' ? options.tileIndex : transformToLocalCoordinates
157
+ ): Feature {
158
+ const decodedFeature = feature.toGeoJSONFeature(
159
+ options.coordinates || 'local',
160
+ options.tileIndex
171
161
  );
172
162
 
173
163
  // Add layer name to GeoJSON properties
174
164
  if (options.layerProperty) {
165
+ decodedFeature.properties ||= {};
175
166
  decodedFeature.properties[options.layerProperty] = layerName;
176
167
  }
177
168
 
@@ -184,14 +175,11 @@ function getDecodedFeature(
184
175
  * @returns decoded binary feature
185
176
  */
186
177
  function getDecodedFeatureBinary(
187
- feature: BinaryVectorTileFeature,
178
+ feature: VectorTileFeature,
188
179
  options: MVTOptions,
189
180
  layerName: string
190
181
  ): FlatFeature {
191
- const decodedFeature = feature.toBinaryCoordinates(
192
- // @ts-expect-error
193
- options.coordinates === 'wgs84' ? options.tileIndex : transformToLocalCoordinatesBinary
194
- );
182
+ const decodedFeature = feature.toBinaryFeature(options.coordinates || 'local', options.tileIndex);
195
183
 
196
184
  // Add layer name to GeoJSON properties
197
185
  if (options.layerProperty && decodedFeature.properties) {
@@ -200,29 +188,3 @@ function getDecodedFeatureBinary(
200
188
 
201
189
  return decodedFeature;
202
190
  }
203
-
204
- /**
205
- * @param line
206
- * @param feature
207
- */
208
- function transformToLocalCoordinates(line: number[], feature: {extent: any}): void {
209
- // This function transforms local coordinates in a
210
- // [0 - bufferSize, this.extent + bufferSize] range to a
211
- // [0 - (bufferSize / this.extent), 1 + (bufferSize / this.extent)] range.
212
- // The resulting extent would be 1.
213
- const {extent} = feature;
214
- for (let i = 0; i < line.length; i++) {
215
- const p = line[i];
216
- p[0] /= extent;
217
- p[1] /= extent;
218
- }
219
- }
220
-
221
- function transformToLocalCoordinatesBinary(data: number[], feature: {extent: any}) {
222
- // For the binary code path, the feature data is just
223
- // one big flat array, so we just divide each value
224
- const {extent} = feature;
225
- for (let i = 0, il = data.length; i < il; ++i) {
226
- data[i] /= extent;
227
- }
228
- }
@@ -16,11 +16,6 @@ export type TileJSON = {
16
16
  tileFormat?: string;
17
17
  tilesetType?: string;
18
18
 
19
- /** Generating application. Tippecanoe adds this. */
20
- generator?: string;
21
- /** Generating application options. Tippecanoe adds this. */
22
- generatorOptions?: string;
23
-
24
19
  /** Tile indexing scheme */
25
20
  scheme?: 'xyz' | 'tms';
26
21
  /** Sharded URLs */
@@ -38,6 +33,11 @@ export type TileJSON = {
38
33
  // Combination of tilestats (if present) and tilejson layer information
39
34
  layers?: TileJSONLayer[];
40
35
 
36
+ /** Generating application. Tippecanoe adds this. */
37
+ generator?: string;
38
+ /** Generating application options. Tippecanoe adds this. */
39
+ generatorOptions?: string;
40
+
41
41
  /** Any nested JSON metadata */
42
42
  metaJson?: any | null;
43
43
  };
package/src/lib/types.ts CHANGED
@@ -2,45 +2,7 @@
2
2
  // SPDX-License-Identifier: MIT
3
3
  // Copyright vis.gl contributors
4
4
 
5
- /** For local coordinates, the tileIndex is not required */
6
- type MVTLocalCoordinatesOptions = {
7
- /**
8
- * When set to `local`, the parser will return a flat array of GeoJSON objects with local coordinates decoded from tile origin.
9
- */
10
- coordinates: 'local';
11
- tileIndex: null;
12
- };
13
-
14
- /** In WGS84 coordinates, the tileIndex is required */
15
- type MVTWgs84CoordinatesOptions = {
16
- /**
17
- * When set to `wgs84`, the parser will return a flat array of GeoJSON objects with coordinates in longitude, latitude decoded from the provided tile index.
18
- */
19
- coordinates?: 'wgs84';
20
-
21
- /**
22
- * Mandatory with `wgs84` coordinates option. An object containing tile index values (`x`, `y`,
23
- * `z`) to reproject features' coordinates into WGS84.
24
- */
25
- tileIndex?: {x: number; y: number; z: number};
26
- };
27
-
28
- export type MVTOptions = (MVTLocalCoordinatesOptions | MVTWgs84CoordinatesOptions) & {
29
- shape?: 'geojson-table' | 'columnar-table' | 'geojson' | 'binary' | 'binary-geometry';
30
- /**
31
- * When non-`null`, the layer name of each feature is added to
32
- * `feature.properties[layerProperty]`. (A `feature.properties` object is created if the feature
33
- * has no existing properties). If set to `null`, a layer name property will not be added.
34
- */
35
- layerProperty?: string | number;
36
-
37
- /**
38
- * Optional list of layer names. If not `null`, only features belonging to the named layers will
39
- * be included in the output. If `null`, features from all layers are returned.
40
- */
41
- layers?: string[];
42
- };
43
-
5
+ /** TODO where is this used? */
44
6
  export type MVTMapboxGeometry = {
45
7
  type?: string;
46
8
  id?: number;
@@ -0,0 +1,234 @@
1
+ // loaders.gl
2
+ // SPDX-License-Identifier: MIT
3
+ // Copyright vis.gl contributors
4
+
5
+ import {getPolygonSignedArea} from '@math.gl/polygon';
6
+ import {FlatIndexedGeometry, FlatPolygon} from '@loaders.gl/schema';
7
+
8
+ /**
9
+ *
10
+ * @param ring
11
+ * @returns sum
12
+ */
13
+ export function signedArea(ring: number[][]) {
14
+ let sum = 0;
15
+ for (let i = 0, j = ring.length - 1, p1: number[], p2: number[]; i < ring.length; j = i++) {
16
+ p1 = ring[i];
17
+ p2 = ring[j];
18
+ sum += (p2[0] - p1[0]) * (p1[1] + p2[1]);
19
+ }
20
+ return sum;
21
+ }
22
+
23
+ /**
24
+ * This function projects local coordinates in a
25
+ * [0 - bufferSize, this.extent + bufferSize] range to a
26
+ * [0 - (bufferSize / this.extent), 1 + (bufferSize / this.extent)] range.
27
+ * The resulting extent would be 1.
28
+ * @param line
29
+ * @param feature
30
+ */
31
+ export function convertToLocalCoordinates(
32
+ coordinates: number[] | number[][] | number[][][] | number[][][][],
33
+ extent: number
34
+ ): void {
35
+ if (Array.isArray(coordinates[0])) {
36
+ for (const subcoords of coordinates) {
37
+ convertToLocalCoordinates(subcoords as number[] | number[][] | number[][][], extent);
38
+ }
39
+ return;
40
+ }
41
+
42
+ // Just a point
43
+ const p = coordinates as number[];
44
+ p[0] /= extent;
45
+ p[1] /= extent;
46
+ }
47
+
48
+ /**
49
+ * For the binary code path, the feature data is just
50
+ * one big flat array, so we just divide each value
51
+ * @param data
52
+ * @param feature
53
+ */
54
+ export function convertToLocalCoordinatesFlat(data: number[], extent: number): void {
55
+ for (let i = 0, il = data.length; i < il; ++i) {
56
+ data[i] /= extent;
57
+ }
58
+ }
59
+
60
+ /**
61
+ * Projects local tile coordinates to lngLat in place.
62
+ * @param points
63
+ * @param tileIndex
64
+ */
65
+ export function projectToLngLat(
66
+ line: number[] | number[][] | number[][][],
67
+ tileIndex: {x: number; y: number; z: number},
68
+ extent: number
69
+ ): void {
70
+ if (typeof line[0][0] !== 'number') {
71
+ for (const point of line) {
72
+ // @ts-expect-error
73
+ projectToLngLat(point, tileIndex, extent);
74
+ }
75
+ return;
76
+ }
77
+ const size = extent * Math.pow(2, tileIndex.z);
78
+ const x0 = extent * tileIndex.x;
79
+ const y0 = extent * tileIndex.y;
80
+ for (let j = 0; j < line.length; j++) {
81
+ const p = line[j];
82
+ p[0] = ((p[0] + x0) * 360) / size - 180;
83
+ const y2 = 180 - ((p[1] + y0) * 360) / size;
84
+ p[1] = (360 / Math.PI) * Math.atan(Math.exp((y2 * Math.PI) / 180)) - 90;
85
+ }
86
+ }
87
+
88
+ /**
89
+ * Projects local tile coordinates to lngLat in place.
90
+ * @param points
91
+ * @param tileIndex
92
+ export function projectTileCoordinatesToLngLat(
93
+ points: number[][],
94
+ tileIndex: {x: number; y: number; z: number},
95
+ extent: number
96
+ ): void {
97
+ const {x, y, z} = tileIndex;
98
+ const size = extent * Math.pow(2, z);
99
+ const x0 = extent * x;
100
+ const y0 = extent * y;
101
+
102
+ for (const p of points) {
103
+ p[0] = ((p[0] + x0) * 360) / size - 180;
104
+ const y2 = 180 - ((p[1] + y0) * 360) / size;
105
+ p[1] = (360 / Math.PI) * Math.atan(Math.exp((y2 * Math.PI) / 180)) - 90;
106
+ }
107
+ }
108
+ */
109
+
110
+ /**
111
+ *
112
+ * @param data
113
+ * @param x0
114
+ * @param y0
115
+ * @param size
116
+ */
117
+ export function projectToLngLatFlat(
118
+ data: number[],
119
+ tileIndex: {x: number; y: number; z: number},
120
+ extent: number
121
+ ): void {
122
+ const {x, y, z} = tileIndex;
123
+ const size = extent * Math.pow(2, z);
124
+ const x0 = extent * x;
125
+ const y0 = extent * y;
126
+
127
+ for (let j = 0, jl = data.length; j < jl; j += 2) {
128
+ data[j] = ((data[j] + x0) * 360) / size - 180;
129
+ const y2 = 180 - ((data[j + 1] + y0) * 360) / size;
130
+ data[j + 1] = (360 / Math.PI) * Math.atan(Math.exp((y2 * Math.PI) / 180)) - 90;
131
+ }
132
+ }
133
+
134
+ /**
135
+ * Classifies an array of rings into polygons with outer rings and holes
136
+ * @param rings
137
+ * @returns polygons
138
+ */
139
+ export function classifyRings(rings: number[][][]): number[][][][] {
140
+ const len = rings.length;
141
+
142
+ if (len <= 1) return [rings];
143
+
144
+ const polygons: number[][][][] = [];
145
+ let polygon: number[][][] | undefined;
146
+ let ccw: boolean | undefined;
147
+
148
+ for (let i = 0; i < len; i++) {
149
+ const area = signedArea(rings[i]);
150
+ if (area === 0) continue; // eslint-disable-line no-continue
151
+
152
+ if (ccw === undefined) ccw = area < 0;
153
+
154
+ if (ccw === area < 0) {
155
+ if (polygon) polygons.push(polygon);
156
+ polygon = [rings[i]];
157
+ } else if (polygon) polygon.push(rings[i]);
158
+ }
159
+ if (polygon) polygons.push(polygon);
160
+
161
+ return polygons;
162
+ }
163
+
164
+ /**
165
+ * Classifies an array of rings into polygons with outer rings and holes
166
+ * The function also detects holes which have zero area and
167
+ * removes them. In doing so it modifies the input
168
+ * `geom.data` array to remove the unneeded data
169
+ *
170
+ * @param geometry
171
+ * @returns object
172
+ */
173
+ // eslint-disable-next-line max-statements
174
+ export function classifyRingsFlat(geom: FlatIndexedGeometry): FlatPolygon {
175
+ const len = geom.indices.length;
176
+ const type = 'Polygon';
177
+
178
+ if (len <= 1) {
179
+ return {
180
+ type,
181
+ data: geom.data,
182
+ areas: [[getPolygonSignedArea(geom.data)]],
183
+ indices: [geom.indices]
184
+ };
185
+ }
186
+
187
+ const areas: any[] = [];
188
+ const polygons: any[] = [];
189
+ let ringAreas: number[] = [];
190
+ let polygon: number[] = [];
191
+ let ccw: boolean | undefined;
192
+ let offset = 0;
193
+
194
+ for (let endIndex: number, i = 0, startIndex: number; i < len; i++) {
195
+ startIndex = geom.indices[i] - offset;
196
+
197
+ endIndex = geom.indices[i + 1] - offset || geom.data.length;
198
+ const shape = geom.data.slice(startIndex, endIndex);
199
+ const area = getPolygonSignedArea(shape);
200
+
201
+ if (area === 0) {
202
+ // This polygon has no area, so remove it from the shape
203
+ // Remove the section from the data array
204
+ const before = geom.data.slice(0, startIndex);
205
+ const after = geom.data.slice(endIndex);
206
+ geom.data = before.concat(after);
207
+
208
+ // Need to offset any remaining indices as we have
209
+ // modified the data buffer
210
+ offset += endIndex - startIndex;
211
+
212
+ // Do not add this index to the output and process next shape
213
+ continue; // eslint-disable-line no-continue
214
+ }
215
+
216
+ if (ccw === undefined) ccw = area < 0;
217
+
218
+ if (ccw === area < 0) {
219
+ if (polygon.length) {
220
+ areas.push(ringAreas);
221
+ polygons.push(polygon);
222
+ }
223
+ polygon = [startIndex];
224
+ ringAreas = [area];
225
+ } else {
226
+ ringAreas.push(area);
227
+ polygon.push(startIndex);
228
+ }
229
+ }
230
+ if (ringAreas) areas.push(ringAreas);
231
+ if (polygon.length) polygons.push(polygon);
232
+
233
+ return {type, areas, indices: polygons, data: geom.data};
234
+ }