@loaders.gl/flatgeobuf 4.0.0-alpha.4 → 4.0.0-alpha.5

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,19 +1,80 @@
1
- // import {deserialize} from 'flatgeobuf/lib/geojson/featurecollection';
2
- import {deserialize, deserializeStream} from 'flatgeobuf/dist/flatgeobuf-geojson.min';
1
+ // @ts-nocheck
2
+ import {Proj4Projection} from '@math.gl/proj4';
3
+ import {transformGeoJsonCoords} from '@loaders.gl/gis';
4
+
5
+ import {deserialize as deserializeGeoJson} from 'flatgeobuf/lib/cjs/geojson';
6
+ import {deserialize as deserializeGeneric} from 'flatgeobuf/lib/cjs/generic';
7
+ import {parseProperties as parsePropertiesBinary} from 'flatgeobuf/lib/cjs/generic/feature';
8
+
9
+ import {fromGeometry as binaryFromGeometry} from './binary-geometries';
10
+
11
+ // TODO: reproject binary features
12
+ function binaryFromFeature(feature, header) {
13
+ const geometry = feature.geometry();
14
+
15
+ // FlatGeobuf files can only hold a single geometry type per file, otherwise
16
+ // GeometryType is GeometryCollection
17
+ // I believe geometry.type() is null (0) except when the geometry type isn't
18
+ // known in the header?
19
+ const geometryType = header.geometryType || geometry.type();
20
+ const parsedGeometry = binaryFromGeometry(geometry, geometryType);
21
+ parsedGeometry.properties = parsePropertiesBinary(feature, header.columns);
22
+
23
+ // TODO: wrap binary data either in points, lines, or polygons key
24
+ return parsedGeometry;
25
+ }
3
26
 
4
27
  /*
5
28
  * Parse FlatGeobuf arrayBuffer and return GeoJSON.
6
29
  *
7
- * @param {arrayBuffer} _ A FlatGeobuf arrayBuffer
8
- * @return {?Object} A GeoJSON geometry object
30
+ * @param arrayBuffer A FlatGeobuf arrayBuffer
31
+ * @return A GeoJSON geometry object
9
32
  */
10
- export default function parseFlatGeobuf(input, options) {
11
- if (input.byteLength === 0) {
33
+ export function parseFlatGeobuf(arrayBuffer, options) {
34
+ if (arrayBuffer.byteLength === 0) {
12
35
  return [];
13
36
  }
14
37
 
15
- const arr = new Uint8Array(input);
16
- const {features} = deserialize(arr);
38
+ if (options && options.gis && options.gis.format === 'binary') {
39
+ return parseFlatGeobufToBinary(arrayBuffer, options);
40
+ }
41
+
42
+ return parseFlatGeobufToGeoJSON(arrayBuffer, options);
43
+ }
44
+
45
+ function parseFlatGeobufToBinary(arrayBuffer, options) {
46
+ // TODO: reproject binary features
47
+ // const {reproject = false, _targetCrs = 'WGS84'} = (options && options.gis) || {};
48
+
49
+ const arr = new Uint8Array(arrayBuffer);
50
+ return deserializeGeneric(arr, binaryFromFeature);
51
+ }
52
+
53
+ function parseFlatGeobufToGeoJSON(arrayBuffer, options) {
54
+ const {reproject = false, _targetCrs = 'WGS84'} = (options && options.gis) || {};
55
+
56
+ const arr = new Uint8Array(arrayBuffer);
57
+
58
+ let headerMeta;
59
+ const {features} = deserializeGeoJson(arr, false, (header) => {
60
+ headerMeta = header;
61
+ });
62
+
63
+ const crs = headerMeta && headerMeta.crs;
64
+ let projection;
65
+ if (reproject && crs) {
66
+ // Constructing the projection may fail for some invalid WKT strings
67
+ try {
68
+ projection = new Proj4Projection({from: crs.wkt, to: _targetCrs});
69
+ } catch (e) {
70
+ // no op
71
+ }
72
+ }
73
+
74
+ if (projection) {
75
+ return transformGeoJsonCoords(features, (coords) => projection.project(coords));
76
+ }
77
+
17
78
  return features;
18
79
  }
19
80
 
@@ -23,7 +84,49 @@ export default function parseFlatGeobuf(input, options) {
23
84
  * @param {ReadableStream} _ A FlatGeobuf arrayBuffer
24
85
  * @return A GeoJSON geometry object iterator
25
86
  */
87
+ // eslint-disable-next-line complexity
26
88
  export function parseFlatGeobufInBatches(stream, options) {
27
- const iterator = deserializeStream(stream);
89
+ if (options && options.gis && options.gis.format === 'binary') {
90
+ return parseFlatGeobufInBatchesToBinary(stream, options);
91
+ }
92
+
93
+ return parseFlatGeobufInBatchesToGeoJSON(stream, options);
94
+ }
95
+
96
+ function parseFlatGeobufInBatchesToBinary(stream, options) {
97
+ // TODO: reproject binary streaming features
98
+ // const {reproject = false, _targetCrs = 'WGS84'} = (options && options.gis) || {};
99
+
100
+ const iterator = deserializeGeneric(stream, binaryFromFeature);
28
101
  return iterator;
29
102
  }
103
+
104
+ // eslint-disable-next-line complexity
105
+ async function* parseFlatGeobufInBatchesToGeoJSON(stream, options) {
106
+ const {reproject = false, _targetCrs = 'WGS84'} = (options && options.gis) || {};
107
+
108
+ let headerMeta;
109
+ const iterator = deserializeGeoJson(stream, false, (header) => {
110
+ headerMeta = header;
111
+ });
112
+
113
+ let projection;
114
+ let firstRecord = true;
115
+ for await (const feature of iterator) {
116
+ if (firstRecord) {
117
+ const crs = headerMeta && headerMeta.crs;
118
+ if (reproject && crs) {
119
+ projection = new Proj4Projection({from: crs.wkt, to: _targetCrs});
120
+ }
121
+
122
+ firstRecord = false;
123
+ }
124
+
125
+ if (reproject && projection) {
126
+ // eslint-disable-next-line
127
+ yield transformGeoJsonCoords([feature], (coords) => projection.project(coords));
128
+ } else {
129
+ yield feature;
130
+ }
131
+ }
132
+ }