gridviz 3.0.18 → 3.0.20

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 (56) hide show
  1. package/README.md +128 -127
  2. package/dist/gridviz.js +7862 -7819
  3. package/dist/gridviz.min.js +1 -1
  4. package/package.json +74 -74
  5. package/src/button/ZoomButtons.js +101 -101
  6. package/src/core/Dataset.js +154 -154
  7. package/src/core/Drawable.js +60 -60
  8. package/src/core/GeoCanvas.js +430 -419
  9. package/src/core/Layer.js +23 -23
  10. package/src/core/Legend.js +108 -108
  11. package/src/core/Map.js +516 -503
  12. package/src/core/MultiResolutionDataset.js +93 -93
  13. package/src/core/Style.js +98 -98
  14. package/src/core/Tooltip.js +1 -0
  15. package/src/dataset/CSVGrid.js +112 -112
  16. package/src/dataset/GeoTIFF.js +122 -122
  17. package/src/dataset/JSGrid.js +55 -55
  18. package/src/dataset/TiledGrid.js +302 -289
  19. package/src/dataset/worker.js +18 -18
  20. package/src/index.js +77 -77
  21. package/src/layer/BackgroundLayer.js +162 -162
  22. package/src/layer/BackgroundLayerImage.js +81 -81
  23. package/src/layer/BackgroundLayerWMS.js +104 -104
  24. package/src/layer/GeoJSONLayer.js +214 -214
  25. package/src/layer/GridLayer.js +148 -148
  26. package/src/layer/LabelLayer.js +194 -194
  27. package/src/legend/ColorCategoryLegend.js +109 -109
  28. package/src/legend/ColorDiscreteLegend.js +100 -100
  29. package/src/legend/ColorLegend.js +115 -115
  30. package/src/legend/OrientationLegend.js +89 -89
  31. package/src/legend/SizeLegend.js +224 -224
  32. package/src/legend/TernaryLegend.js +302 -302
  33. package/src/style/CompositionStyle.js +291 -291
  34. package/src/style/DotDensityStyle.js +133 -133
  35. package/src/style/ImageStyle.js +100 -100
  36. package/src/style/IsoFenceStyle.js +217 -217
  37. package/src/style/JoyPlotStyle.js +127 -127
  38. package/src/style/LegoStyle.js +110 -110
  39. package/src/style/MosaicStyle.js +99 -99
  40. package/src/style/NinjaStarStyle.js +102 -102
  41. package/src/style/PillarStyle.js +207 -207
  42. package/src/style/SegmentStyle.js +105 -105
  43. package/src/style/ShapeColorSizeStyle.js +147 -147
  44. package/src/style/SideCategoryStyle.js +112 -112
  45. package/src/style/SideStyle.js +212 -212
  46. package/src/style/SquareColorCategoryWebGLStyle.js +107 -107
  47. package/src/style/SquareColorWebGLStyle.js +126 -126
  48. package/src/style/StrokeStyle.js +135 -135
  49. package/src/style/TanakaStyle.js +69 -69
  50. package/src/style/TextStyle.js +110 -110
  51. package/src/style/TimeSeriesStyle.js +222 -222
  52. package/src/utils/scale.js +218 -218
  53. package/src/utils/stretching.js +120 -120
  54. package/src/utils/ternary.js +208 -203
  55. package/src/utils/utils.js +58 -58
  56. package/src/utils/webGLUtils.js +72 -72
@@ -1,289 +1,302 @@
1
- //@ts-check
2
- 'use strict'
3
-
4
- /** @typedef {{ dims: object, crs: string, tileSizeCell: number, originPoint: {x:number,y:number}, resolutionGeo: number, tilingBounds:import("../core/GeoCanvas.js").Envelope }} GridInfo */
5
-
6
- // internal
7
- import { Dataset } from '../core/Dataset.js'
8
- //import { monitor, monitorDuration } from '../utils/Utils.js'
9
-
10
- // external
11
- import { json, csv } from 'd3-fetch'
12
-
13
- /**
14
- * A tiled dataset, composed of CSV tiles.
15
- *
16
- * @module dataset
17
- * @author Joseph Davies, Julien Gaffuri
18
- */
19
- export class TiledGrid extends Dataset {
20
- /**
21
- * @param {import("../core/Map.js").Map} map The map.
22
- * @param {string} url The URL of the dataset.
23
- * @param {{preprocess?:(function(import("../core/Dataset.js").Cell):boolean), onlyDrawWhenAllTilesReady:boolean}} opts
24
- */
25
- constructor(map, url, opts = {}) {
26
- super(map, url, 0, opts)
27
- this.onlyDrawWhenAllTilesReady = opts.onlyDrawWhenAllTilesReady || false
28
- /**
29
- * The grid info object, from the info.json file.
30
- * @type {GridInfo | undefined}
31
- * @private
32
- * */
33
- this.info = undefined
34
-
35
- /**
36
- * @type {string}
37
- * @private */
38
- this.infoLoadingStatus = 'notLoaded'
39
-
40
- /**
41
- * The cache of the loaded tiles. It is double indexed: by xT and then yT.
42
- * Example: this.cache[xT][yT] returns the tile at [xT][yT] location.
43
- *
44
- * @type {object}
45
- * */
46
- this.cache = {}
47
-
48
- //launch loading
49
- this.loadInfo()
50
- }
51
-
52
- /**
53
- * Load the info.json from the url.
54
- * @returns this
55
- */
56
- loadInfo() {
57
- if (!this.info && this.infoLoadingStatus === 'notLoaded') {
58
- ;(async () => {
59
- try {
60
- const data = await json(this.url + 'info.json')
61
- this.info = data
62
- this.resolution = data.resolutionGeo
63
- this.infoLoadingStatus = 'loaded'
64
- this.map.redraw()
65
- } catch (error) {
66
- //mark as failed
67
- this.infoLoadingStatus = 'failed'
68
- }
69
- })()
70
- } else if (this.infoLoadingStatus === 'loaded' || this.infoLoadingStatus === 'failed')
71
- this.map.redraw()
72
- return this
73
- }
74
-
75
- /**
76
- * Compute a tiling envelope from a geographical envelope.
77
- * This is the function to use to know which tiles to download for a geographical view.
78
- *
79
- * @param {import("../core/GeoCanvas.js").Envelope} e
80
- * @returns {import("../core/GeoCanvas.js").Envelope|undefined}
81
- */
82
- getTilingEnvelope(e) {
83
- if (!this.info) {
84
- this.loadInfo()
85
- return
86
- }
87
-
88
- const po = this.info.originPoint,
89
- r = this.info.resolutionGeo,
90
- s = this.info.tileSizeCell
91
-
92
- return {
93
- xMin: Math.floor((e.xMin - po.x) / (r * s)),
94
- xMax: Math.floor((e.xMax - po.x) / (r * s)),
95
- yMin: Math.floor((e.yMin - po.y) / (r * s)),
96
- yMax: Math.floor((e.yMax - po.y) / (r * s)),
97
- }
98
- }
99
-
100
- /**
101
- * Request data within a geographic envelope.
102
- *
103
- * @param {import('../core/GeoCanvas.js').Envelope} extGeo
104
- * @returns {this}
105
- */
106
- async getData(extGeo) {
107
- if (!this.info) return this
108
-
109
- // Get the tiling envelope and check bounds
110
- const tb = this.getTilingEnvelope(extGeo)
111
- if (!tb) return this
112
-
113
- const { xMin: gbXMin, xMax: gbXMax, yMin: gbYMin, yMax: gbYMax } = this.info.tilingBounds
114
-
115
- const xMin = Math.max(tb.xMin, gbXMin)
116
- const xMax = Math.min(tb.xMax, gbXMax)
117
- const yMin = Math.max(tb.yMin, gbYMin)
118
- const yMax = Math.min(tb.yMax, gbYMax)
119
-
120
- // Count the total number of tiles
121
- const totalTiles = (xMax - xMin + 1) * (yMax - yMin + 1)
122
-
123
- let processedTiles = 0 // Counter for loaded tiles
124
- const tilePromises = []
125
-
126
- // Iterate over tiles within bounds
127
- for (let xT = xMin; xT <= xMax; xT++) {
128
- for (let yT = yMin; yT <= yMax; yT++) {
129
- if (!this.cache[xT]) this.cache[xT] = {}
130
-
131
- // Skip already loaded or loading tiles
132
- if (this.cache[xT][yT]) {
133
- ++processedTiles
134
- continue
135
- }
136
-
137
- // Mark tile as loading
138
- this.cache[xT][yT] = 'loading'
139
-
140
- // Prepare the tile request and store it in tilePromises
141
- tilePromises.push(
142
- this.loadTile(xT, yT)
143
- .then((tile) => {
144
- // Before we increment processedTiles, check if it's the last tile
145
- const isLastTile = ++processedTiles === totalTiles
146
-
147
- // Store the tile in the cache
148
- this.cache[xT][yT] = tile
149
-
150
- // Pass the isLastTile argument to checkAndRedraw
151
- this.checkAndRedraw(tile, isLastTile)
152
- })
153
- .catch(() => {
154
- // Mark as failed but allow processing to continue
155
- this.cache[xT][yT] = 'failed'
156
- ++processedTiles
157
- })
158
- )
159
- }
160
- }
161
-
162
- // Handle all tile promises, including failures
163
- await Promise.allSettled(tilePromises)
164
- return this
165
- }
166
-
167
- async loadTile(xT, yT) {
168
- try {
169
- const data = await csv(`${this.url}${xT}/${yT}.csv`)
170
-
171
- // Preprocess or filter the data if needed
172
- const cells = this.preprocess ? data.filter((cell) => this.preprocess(cell) !== false) : data
173
-
174
- if (!this.info) throw new Error('Tile info unknown')
175
-
176
- return getGridTile(cells, xT, yT, this.info)
177
- } catch (error) {
178
- console.warn(`Failed to load tile ${xT}, ${yT}:`, error)
179
- throw error
180
- }
181
- }
182
-
183
- checkAndRedraw(tile, isLastTile) {
184
- // Check if any visible layer depends on this dataset
185
- //check if redraw is really needed, that is if:
186
- // 1. the dataset belongs to a layer which is visible at the current zoom level
187
- let needsRedraw = false
188
- //go through the layers
189
- const z = this.map.getZoom()
190
- for (const lay of this.map.layers) {
191
- if (lay.visible && !lay.visible(z)) continue
192
- if (!lay.getDataset) continue
193
- if (lay.getDataset(z) != this) continue
194
- //found one layer. No need to seek more.
195
- needsRedraw = true
196
- break
197
- }
198
-
199
- if (!needsRedraw) return
200
-
201
- // Check if tile intersects the current view
202
- const env = this.map.updateExtentGeo()
203
- const { xMin, xMax, yMin, yMax } = tile.extGeo
204
- if (env.xMax <= xMin || env.xMin >= xMax || env.yMax <= yMin || env.yMin >= yMax) return
205
-
206
- // Trigger redraw
207
- if (this.onlyDrawWhenAllTilesReady) {
208
- if (isLastTile) {
209
- this.map.redraw()
210
- }
211
- } else {
212
- this.map.redraw()
213
- }
214
- }
215
-
216
- /**
217
- * Fill the view cache with all cells which are within a geographical envelope.
218
- * @abstract
219
- * @param {import("../core/GeoCanvas.js").Envelope} extGeo
220
- * @returns {void}
221
- */
222
- updateViewCache(extGeo) {
223
- //
224
- this.cellsViewCache = []
225
-
226
- //check if info has been loaded
227
- if (!this.info) return
228
-
229
- //tiles within the scope
230
- /** @type {import("../core/GeoCanvas.js").Envelope|undefined} */
231
- const tb = this.getTilingEnvelope(extGeo)
232
- if (!tb) return
233
-
234
- //grid bounds
235
- /** @type {import("../core/GeoCanvas.js").Envelope} */
236
- const gb = this.info.tilingBounds
237
-
238
- for (let xT = Math.max(tb.xMin, gb.xMin); xT <= Math.min(tb.xMax, gb.xMax); xT++) {
239
- if (!this.cache[xT]) continue
240
- for (let yT = Math.max(tb.yMin, gb.yMin); yT <= Math.min(tb.yMax, gb.yMax); yT++) {
241
- //get tile
242
- /** @type {object} */
243
- const tile = this.cache[xT][yT]
244
- if (!tile || typeof tile === 'string') continue
245
-
246
- //get cells
247
- //this.cellsViewCache = this.cellsViewCache.concat(tile.cells)
248
-
249
- for (const cell of tile.cells) {
250
- if (+cell.x + this.resolution < extGeo.xMin) continue
251
- if (+cell.x - this.resolution > extGeo.xMax) continue
252
- if (+cell.y + this.resolution < extGeo.yMin) continue
253
- if (+cell.y - this.resolution > extGeo.yMax) continue
254
- this.cellsViewCache.push(cell)
255
- }
256
- }
257
- }
258
- }
259
- }
260
-
261
- function getGridTile(cells, xT, yT, gridInfo) {
262
- const tile = {}
263
-
264
- /** @type {Array.<import("../core/Dataset").Cell>} */
265
- tile.cells = cells
266
- /** @type {number} */
267
- tile.x = xT
268
- /** @type {number} */
269
- tile.y = yT
270
-
271
- const r = gridInfo.resolutionGeo
272
- const s = gridInfo.tileSizeCell
273
-
274
- /** @type {import("../core/GeoCanvas").Envelope} */
275
- tile.extGeo = {
276
- xMin: gridInfo.originPoint.x + r * s * tile.x,
277
- xMax: gridInfo.originPoint.x + r * s * (tile.x + 1),
278
- yMin: gridInfo.originPoint.y + r * s * tile.y,
279
- yMax: gridInfo.originPoint.y + r * s * (tile.y + 1),
280
- }
281
-
282
- //convert cell coordinates into geographical coordinates
283
- for (let cell of tile.cells) {
284
- cell.x = tile.extGeo.xMin + cell.x * r
285
- cell.y = tile.extGeo.yMin + cell.y * r
286
- }
287
-
288
- return tile
289
- }
1
+ //@ts-check
2
+ 'use strict'
3
+
4
+ /** @typedef {{ dims: object, crs: string, tileSizeCell: number, originPoint: {x:number,y:number}, resolutionGeo: number, tilingBounds:import("../core/GeoCanvas.js").Envelope }} GridInfo */
5
+
6
+ // internal
7
+ import { Dataset } from '../core/Dataset.js'
8
+ //import { monitor, monitorDuration } from '../utils/Utils.js'
9
+
10
+ // external
11
+ import { json, csv } from 'd3-fetch'
12
+
13
+ /**
14
+ * A tiled dataset, composed of CSV tiles.
15
+ *
16
+ * @module dataset
17
+ * @author Joseph Davies, Julien Gaffuri
18
+ */
19
+ export class TiledGrid extends Dataset {
20
+ /**
21
+ * @param {import("../core/Map.js").Map} map The map.
22
+ * @param {string} url The URL of the dataset.
23
+ * @param {{preprocess?:(function(import("../core/Dataset.js").Cell):boolean), onlyDrawWhenAllTilesReady:boolean}} opts
24
+ */
25
+ constructor(map, url, opts = {}) {
26
+ super(map, url, 0, opts)
27
+ this.onlyDrawWhenAllTilesReady = opts.onlyDrawWhenAllTilesReady || false
28
+ /**
29
+ * The grid info object, from the info.json file.
30
+ * @type {GridInfo | undefined}
31
+ * @private
32
+ * */
33
+ this.info = undefined
34
+
35
+ /**
36
+ * @type {string}
37
+ * @private */
38
+ this.infoLoadingStatus = 'notLoaded'
39
+
40
+ /**
41
+ * The cache of the loaded tiles. It is double indexed: by xT and then yT.
42
+ * Example: this.cache[xT][yT] returns the tile at [xT][yT] location.
43
+ *
44
+ * @type {object}
45
+ * */
46
+ this.cache = {}
47
+
48
+ //launch loading
49
+ this.loadInfo()
50
+ }
51
+
52
+ /**
53
+ * Load the info.json from the url.
54
+ * @returns this
55
+ */
56
+ loadInfo() {
57
+ if (!this.info && this.infoLoadingStatus === 'notLoaded') {
58
+ ;(async () => {
59
+ try {
60
+ const data = await json(this.url + 'info.json')
61
+ this.info = data
62
+ this.resolution = data.resolutionGeo
63
+ this.infoLoadingStatus = 'loaded'
64
+ this.map.redraw()
65
+ } catch (error) {
66
+ //mark as failed
67
+ this.infoLoadingStatus = 'failed'
68
+ }
69
+ })()
70
+ } else if (this.infoLoadingStatus === 'loaded' || this.infoLoadingStatus === 'failed') this.map.redraw()
71
+ return this
72
+ }
73
+
74
+ /**
75
+ * Compute a tiling envelope from a geographical envelope.
76
+ * This is the function to use to know which tiles to download for a geographical view.
77
+ *
78
+ * @param {import("../core/GeoCanvas.js").Envelope} e
79
+ * @returns {import("../core/GeoCanvas.js").Envelope|undefined}
80
+ */
81
+ getTilingEnvelope(e) {
82
+ if (!this.info) {
83
+ this.loadInfo()
84
+ return
85
+ }
86
+
87
+ const po = this.info.originPoint,
88
+ r = this.info.resolutionGeo,
89
+ s = this.info.tileSizeCell
90
+
91
+ return {
92
+ xMin: Math.floor((e.xMin - po.x) / (r * s)),
93
+ xMax: Math.floor((e.xMax - po.x) / (r * s)),
94
+ yMin: Math.floor((e.yMin - po.y) / (r * s)),
95
+ yMax: Math.floor((e.yMax - po.y) / (r * s)),
96
+ }
97
+ }
98
+
99
+ /**
100
+ * Request data within a geographic envelope.
101
+ *
102
+ * @param {import('../core/GeoCanvas.js').Envelope} extGeo
103
+ * @returns {this}
104
+ */
105
+ async getData(extGeo) {
106
+ if (!this.info) return this
107
+
108
+ // Create an AbortController for the current data request
109
+ this.abortController = new AbortController()
110
+ const signal = this.abortController.signal
111
+
112
+ // Get the tiling envelope and check bounds
113
+ const tb = this.getTilingEnvelope(extGeo)
114
+ if (!tb) return this
115
+
116
+ const { xMin: gbXMin, xMax: gbXMax, yMin: gbYMin, yMax: gbYMax } = this.info.tilingBounds
117
+
118
+ const xMin = Math.max(tb.xMin, gbXMin)
119
+ const xMax = Math.min(tb.xMax, gbXMax)
120
+ const yMin = Math.max(tb.yMin, gbYMin)
121
+ const yMax = Math.min(tb.yMax, gbYMax)
122
+
123
+ const totalTiles = (xMax - xMin + 1) * (yMax - yMin + 1)
124
+ let processedTiles = 0
125
+ const tilePromises = []
126
+
127
+ // Iterate over tiles within bounds
128
+ for (let xT = xMin; xT <= xMax; xT++) {
129
+ for (let yT = yMin; yT <= yMax; yT++) {
130
+ if (!this.cache[xT]) this.cache[xT] = {}
131
+
132
+ // Skip already loaded tiles or retry failed ones
133
+ if (this.cache[xT][yT] && this.cache[xT][yT] !== 'failed') {
134
+ ++processedTiles
135
+ continue
136
+ }
137
+
138
+ // Mark tile as loading
139
+ this.cache[xT][yT] = 'loading'
140
+
141
+ tilePromises.push(
142
+ this.loadTile(xT, yT, signal)
143
+ .then((tile) => {
144
+ this.cache[xT][yT] = tile
145
+
146
+ // Check if this is the last tile
147
+ const isLastTile = ++processedTiles === totalTiles
148
+ this.checkAndRedraw(tile, isLastTile)
149
+ })
150
+ .catch(() => {
151
+ this.cache[xT][yT] = 'failed'
152
+ ++processedTiles
153
+ })
154
+ )
155
+ }
156
+ }
157
+
158
+ await Promise.allSettled(tilePromises)
159
+ return this
160
+ }
161
+
162
+ /**
163
+ * Load a tile.
164
+ *
165
+ * @param {number} xT
166
+ * @param {number} yT
167
+ * @param {AbortSignal} signal
168
+ * @returns {Promise<any>}
169
+ */
170
+ async loadTile(xT, yT, signal) {
171
+ try {
172
+ const data = await csv(`${this.url}${xT}/${yT}.csv`, { signal })
173
+
174
+ const cells = this.preprocess ? data.filter((cell) => this.preprocess(cell) !== false) : data
175
+
176
+ if (!this.info) throw new Error('Tile info unknown')
177
+
178
+ return getGridTile(cells, xT, yT, this.info)
179
+ } catch (error) {
180
+ if (error.name === 'AbortError') {
181
+ console.warn(`Tile request for ${xT}, ${yT} was aborted.`)
182
+ }
183
+ throw error
184
+ }
185
+ }
186
+
187
+ /**
188
+ * Cancel ongoing data requests when zoom level changes.
189
+ */
190
+ cancelCurrentRequests() {
191
+ if (this.abortController) {
192
+ this.abortController.abort()
193
+ }
194
+ }
195
+
196
+ checkAndRedraw(tile, isLastTile) {
197
+ // Check if any visible layer depends on this dataset
198
+ // check if redraw is really needed, that is if:
199
+ // 1. the dataset belongs to a layer which is visible at the current zoom level
200
+ let needsRedraw = false
201
+ //go through the layers
202
+ const z = this.map.getZoom()
203
+ for (const lay of this.map.layers) {
204
+ if (lay.visible && !lay.visible(z)) continue
205
+ if (!lay.getDataset) continue
206
+ if (lay.getDataset(z) != this) continue
207
+ //found one layer. No need to seek more.
208
+ needsRedraw = true
209
+ break
210
+ }
211
+
212
+ if (!needsRedraw) return
213
+
214
+ // Check if tile intersects the current view
215
+ const env = this.map.updateExtentGeo()
216
+ const { xMin, xMax, yMin, yMax } = tile.extGeo
217
+ if (env.xMax <= xMin || env.xMin >= xMax || env.yMax <= yMin || env.yMin >= yMax) return
218
+
219
+ // Trigger redraw
220
+ if (this.onlyDrawWhenAllTilesReady) {
221
+ if (isLastTile) {
222
+ this.map.redraw()
223
+ }
224
+ } else {
225
+ this.map.redraw()
226
+ }
227
+ }
228
+
229
+ /**
230
+ * Fill the view cache with all cells which are within a geographical envelope.
231
+ * @abstract
232
+ * @param {import("../core/GeoCanvas.js").Envelope} extGeo
233
+ * @returns {void}
234
+ */
235
+ updateViewCache(extGeo) {
236
+ //
237
+ this.cellsViewCache = []
238
+
239
+ //check if info has been loaded
240
+ if (!this.info) return
241
+
242
+ //tiles within the scope
243
+ /** @type {import("../core/GeoCanvas.js").Envelope|undefined} */
244
+ const tb = this.getTilingEnvelope(extGeo)
245
+ if (!tb) return
246
+
247
+ //grid bounds
248
+ /** @type {import("../core/GeoCanvas.js").Envelope} */
249
+ const gb = this.info.tilingBounds
250
+
251
+ for (let xT = Math.max(tb.xMin, gb.xMin); xT <= Math.min(tb.xMax, gb.xMax); xT++) {
252
+ if (!this.cache[xT]) continue
253
+ for (let yT = Math.max(tb.yMin, gb.yMin); yT <= Math.min(tb.yMax, gb.yMax); yT++) {
254
+ //get tile
255
+ /** @type {object} */
256
+ const tile = this.cache[xT][yT]
257
+ if (!tile || typeof tile === 'string') continue
258
+
259
+ //get cells
260
+ //this.cellsViewCache = this.cellsViewCache.concat(tile.cells)
261
+
262
+ for (const cell of tile.cells) {
263
+ if (+cell.x + this.resolution < extGeo.xMin) continue
264
+ if (+cell.x - this.resolution > extGeo.xMax) continue
265
+ if (+cell.y + this.resolution < extGeo.yMin) continue
266
+ if (+cell.y - this.resolution > extGeo.yMax) continue
267
+ this.cellsViewCache.push(cell)
268
+ }
269
+ }
270
+ }
271
+ }
272
+ }
273
+
274
+ function getGridTile(cells, xT, yT, gridInfo) {
275
+ const tile = {}
276
+
277
+ /** @type {Array.<import("../core/Dataset").Cell>} */
278
+ tile.cells = cells
279
+ /** @type {number} */
280
+ tile.x = xT
281
+ /** @type {number} */
282
+ tile.y = yT
283
+
284
+ const r = gridInfo.resolutionGeo
285
+ const s = gridInfo.tileSizeCell
286
+
287
+ /** @type {import("../core/GeoCanvas").Envelope} */
288
+ tile.extGeo = {
289
+ xMin: gridInfo.originPoint.x + r * s * tile.x,
290
+ xMax: gridInfo.originPoint.x + r * s * (tile.x + 1),
291
+ yMin: gridInfo.originPoint.y + r * s * tile.y,
292
+ yMax: gridInfo.originPoint.y + r * s * (tile.y + 1),
293
+ }
294
+
295
+ //convert cell coordinates into geographical coordinates
296
+ for (let cell of tile.cells) {
297
+ cell.x = tile.extGeo.xMin + cell.x * r
298
+ cell.y = tile.extGeo.yMin + cell.y * r
299
+ }
300
+
301
+ return tile
302
+ }
@@ -1,18 +1,18 @@
1
- self.onmessage = function (e) {
2
- const { type, cells, preprocess } = e.data
3
- if (type === 'processCells') {
4
- const result = processCells(cells, preprocess)
5
- self.postMessage({ type: 'processedCells', result })
6
- }
7
- }
8
-
9
- function processCells(cells, preprocess) {
10
- // If no preprocess function is provided, return the cells as they are
11
- if (!preprocess) {
12
- return cells
13
- }
14
-
15
- // Apply preprocess function to each cell if available
16
- const preprocessedCells = cells.map((cell) => preprocess(cell)).filter((cell) => cell !== false)
17
- return preprocessedCells
18
- }
1
+ self.onmessage = function (e) {
2
+ const { type, cells, preprocess } = e.data
3
+ if (type === 'processCells') {
4
+ const result = processCells(cells, preprocess)
5
+ self.postMessage({ type: 'processedCells', result })
6
+ }
7
+ }
8
+
9
+ function processCells(cells, preprocess) {
10
+ // If no preprocess function is provided, return the cells as they are
11
+ if (!preprocess) {
12
+ return cells
13
+ }
14
+
15
+ // Apply preprocess function to each cell if available
16
+ const preprocessedCells = cells.map((cell) => preprocess(cell)).filter((cell) => cell !== false)
17
+ return preprocessedCells
18
+ }