@geospatial-sdk/openlayers 0.0.5-dev.48 → 0.0.5-dev.50

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.
@@ -3,7 +3,7 @@ import Map from "ol/Map.js";
3
3
  import View from "ol/View.js";
4
4
  import Layer from "ol/layer/Layer.js";
5
5
  export declare function createLayer(layerModel: MapContextLayer): Promise<Layer>;
6
- export declare function updateLayerInMap(map: Map, layerModel: MapContextLayer, layerPosition: number, previousLayer: MapContextLayer): void;
6
+ export declare function updateLayerInMap(map: Map, layerModel: MapContextLayer, layerPosition: number, previousLayerModel: MapContextLayer): void;
7
7
  export declare function createView(viewModel: MapContextView | null, map: Map): View;
8
8
  /**
9
9
  * Create an OpenLayers map from a context; optionally specify a target (root element) for the map
@@ -1 +1 @@
1
- {"version":3,"file":"create-map.d.ts","sourceRoot":"","sources":["../../lib/map/create-map.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,UAAU,EACV,eAAe,EACf,cAAc,EAEf,MAAM,sBAAsB,CAAC;AAC9B,OAAO,GAAG,MAAM,WAAW,CAAC;AAC5B,OAAO,IAAI,MAAM,YAAY,CAAC;AAC9B,OAAO,KAAK,MAAM,mBAAmB,CAAC;AA6CtC,wBAAsB,WAAW,CAAC,UAAU,EAAE,eAAe,GAAG,OAAO,CAAC,KAAK,CAAC,CAyN7E;AAED,wBAAgB,gBAAgB,CAC9B,GAAG,EAAE,GAAG,EACR,UAAU,EAAE,eAAe,EAC3B,aAAa,EAAE,MAAM,EACrB,aAAa,EAAE,eAAe,QAgB/B;AAED,wBAAgB,UAAU,CAAC,SAAS,EAAE,cAAc,GAAG,IAAI,EAAE,GAAG,EAAE,GAAG,GAAG,IAAI,CAkC3E;AAED;;;;GAIG;AACH,wBAAsB,oBAAoB,CACxC,OAAO,EAAE,UAAU,EACnB,MAAM,CAAC,EAAE,MAAM,GAAG,WAAW,GAC5B,OAAO,CAAC,GAAG,CAAC,CAKd;AAED;;;;GAIG;AACH,wBAAsB,mBAAmB,CACvC,GAAG,EAAE,GAAG,EACR,OAAO,EAAE,UAAU,GAClB,OAAO,CAAC,GAAG,CAAC,CAQd"}
1
+ {"version":3,"file":"create-map.d.ts","sourceRoot":"","sources":["../../lib/map/create-map.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,UAAU,EACV,eAAe,EACf,cAAc,EAEf,MAAM,sBAAsB,CAAC;AAC9B,OAAO,GAAG,MAAM,WAAW,CAAC;AAC5B,OAAO,IAAI,MAAM,YAAY,CAAC;AAC9B,OAAO,KAAK,MAAM,mBAAmB,CAAC;AAsCtC,wBAAsB,WAAW,CAAC,UAAU,EAAE,eAAe,GAAG,OAAO,CAAC,KAAK,CAAC,CAyN7E;AAED,wBAAgB,gBAAgB,CAC9B,GAAG,EAAE,GAAG,EACR,UAAU,EAAE,eAAe,EAC3B,aAAa,EAAE,MAAM,EACrB,kBAAkB,EAAE,eAAe,QAgBpC;AAED,wBAAgB,UAAU,CAAC,SAAS,EAAE,cAAc,GAAG,IAAI,EAAE,GAAG,EAAE,GAAG,GAAG,IAAI,CAkC3E;AAED;;;;GAIG;AACH,wBAAsB,oBAAoB,CACxC,OAAO,EAAE,UAAU,EACnB,MAAM,CAAC,EAAE,MAAM,GAAG,WAAW,GAC5B,OAAO,CAAC,GAAG,CAAC,CAKd;AAED;;;;GAIG;AACH,wBAAsB,mBAAmB,CACvC,GAAG,EAAE,GAAG,EACR,OAAO,EAAE,UAAU,GAClB,OAAO,CAAC,GAAG,CAAC,CAQd"}
@@ -19,18 +19,9 @@ import { OgcApiEndpoint, WfsEndpoint, WmtsEndpoint, } from "@camptocamp/ogc-clie
19
19
  import { MapboxVectorLayer } from "ol-mapbox-style";
20
20
  import { handleEndpointError, tileLoadErrorCatchFunction, } from "./handle-errors.js";
21
21
  import VectorTile from "ol/source/VectorTile.js";
22
- import { canDoIncrementalUpdate } from "./layer-update.js";
22
+ import { canDoIncrementalUpdate, updateLayerProperties, } from "./layer-update.js";
23
23
  const GEOJSON = new GeoJSON();
24
24
  const WFS_MAX_FEATURES = 10000;
25
- function updateLayerProperties(layerModel, olLayer) {
26
- typeof layerModel.visibility !== "undefined" &&
27
- olLayer.setVisible(layerModel.visibility);
28
- typeof layerModel.opacity !== "undefined" &&
29
- olLayer.setOpacity(layerModel.opacity);
30
- typeof layerModel.attributions !== "undefined" &&
31
- olLayer.getSource()?.setAttributions(layerModel.attributions);
32
- olLayer.set("label", layerModel.label);
33
- }
34
25
  export async function createLayer(layerModel) {
35
26
  const { type } = layerModel;
36
27
  let layer;
@@ -229,12 +220,12 @@ export async function createLayer(layerModel) {
229
220
  updateLayerProperties(layerModel, layer);
230
221
  return layer;
231
222
  }
232
- export function updateLayerInMap(map, layerModel, layerPosition, previousLayer) {
223
+ export function updateLayerInMap(map, layerModel, layerPosition, previousLayerModel) {
233
224
  const layers = map.getLayers();
234
225
  const updatedLayer = layers.item(layerPosition);
235
226
  // if an incremental update is possible, do it to avoid costly layer recreation
236
- if (canDoIncrementalUpdate(previousLayer, layerModel)) {
237
- updateLayerProperties(layerModel, updatedLayer);
227
+ if (canDoIncrementalUpdate(previousLayerModel, layerModel)) {
228
+ updateLayerProperties(layerModel, updatedLayer, previousLayerModel);
238
229
  return;
239
230
  }
240
231
  // dispose and recreate layer
@@ -1,4 +1,5 @@
1
1
  import { MapContextLayer } from "@geospatial-sdk/core";
2
+ import Layer from "ol/layer/Layer.js";
2
3
  /**
3
4
  * Incremental update is possible only if certain properties are changed: opacity,
4
5
  * visibility, zIndex, etc.
@@ -10,4 +11,12 @@ import { MapContextLayer } from "@geospatial-sdk/core";
10
11
  * @return Returns `true` if the only properties changed are the updatable ones
11
12
  */
12
13
  export declare function canDoIncrementalUpdate(oldLayer: MapContextLayer, newLayer: MapContextLayer): boolean;
14
+ /**
15
+ * Will apply generic properties to the layer; if a previous layer model is provided,
16
+ * only changed properties will be updated (to avoid costly change events in OpenLayers)
17
+ * @param layerModel
18
+ * @param olLayer
19
+ * @param previousLayerModel
20
+ */
21
+ export declare function updateLayerProperties(layerModel: MapContextLayer, olLayer: Layer, previousLayerModel?: MapContextLayer): void;
13
22
  //# sourceMappingURL=layer-update.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"layer-update.d.ts","sourceRoot":"","sources":["../../lib/map/layer-update.ts"],"names":[],"mappings":"AAAA,OAAO,EAAW,eAAe,EAAE,MAAM,sBAAsB,CAAC;AAahE;;;;;;;;;GASG;AACH,wBAAgB,sBAAsB,CACpC,QAAQ,EAAE,eAAe,EACzB,QAAQ,EAAE,eAAe,GACxB,OAAO,CAIT"}
1
+ {"version":3,"file":"layer-update.d.ts","sourceRoot":"","sources":["../../lib/map/layer-update.ts"],"names":[],"mappings":"AAAA,OAAO,EAAW,eAAe,EAAE,MAAM,sBAAsB,CAAC;AAEhE,OAAO,KAAK,MAAM,mBAAmB,CAAC;AAYtC;;;;;;;;;GASG;AACH,wBAAgB,sBAAsB,CACpC,QAAQ,EAAE,eAAe,EACzB,QAAQ,EAAE,eAAe,GACxB,OAAO,CAIT;AAED;;;;;;GAMG;AACH,wBAAgB,qBAAqB,CACnC,UAAU,EAAE,eAAe,EAC3B,OAAO,EAAE,KAAK,EACd,kBAAkB,CAAC,EAAE,eAAe,QA6BrC"}
@@ -23,3 +23,37 @@ export function canDoIncrementalUpdate(oldLayer, newLayer) {
23
23
  const newHash = getHash(newLayer, UPDATABLE_PROPERTIES);
24
24
  return oldHash === newHash;
25
25
  }
26
+ /**
27
+ * Will apply generic properties to the layer; if a previous layer model is provided,
28
+ * only changed properties will be updated (to avoid costly change events in OpenLayers)
29
+ * @param layerModel
30
+ * @param olLayer
31
+ * @param previousLayerModel
32
+ */
33
+ export function updateLayerProperties(layerModel, olLayer, previousLayerModel) {
34
+ function shouldApplyProperty(prop) {
35
+ // if the new layer model does not define that property, skip it
36
+ // (setting or resetting it to a default value would be counter-intuitive)
37
+ if (!(prop in layerModel) || typeof layerModel[prop] === "undefined")
38
+ return false;
39
+ // if a previous model is provided and the value did not change in the new layer model, skip it
40
+ if (previousLayerModel && layerModel[prop] === previousLayerModel[prop]) {
41
+ return false;
42
+ }
43
+ // any other case: apply the property
44
+ return true;
45
+ }
46
+ if (shouldApplyProperty("visibility")) {
47
+ olLayer.setVisible(layerModel.visibility);
48
+ }
49
+ if (shouldApplyProperty("opacity")) {
50
+ olLayer.setOpacity(layerModel.opacity);
51
+ }
52
+ if (shouldApplyProperty("attributions")) {
53
+ olLayer.getSource()?.setAttributions(layerModel.attributions);
54
+ }
55
+ if (shouldApplyProperty("label")) {
56
+ olLayer.set("label", layerModel.label);
57
+ }
58
+ // TODO: z-index
59
+ }
@@ -36,21 +36,14 @@ import {
36
36
  tileLoadErrorCatchFunction,
37
37
  } from "./handle-errors.js";
38
38
  import VectorTile from "ol/source/VectorTile.js";
39
- import { canDoIncrementalUpdate } from "./layer-update.js";
39
+ import {
40
+ canDoIncrementalUpdate,
41
+ updateLayerProperties,
42
+ } from "./layer-update.js";
40
43
 
41
44
  const GEOJSON = new GeoJSON();
42
45
  const WFS_MAX_FEATURES = 10000;
43
46
 
44
- function updateLayerProperties(layerModel: MapContextLayer, olLayer: Layer) {
45
- typeof layerModel.visibility !== "undefined" &&
46
- olLayer.setVisible(layerModel.visibility);
47
- typeof layerModel.opacity !== "undefined" &&
48
- olLayer.setOpacity(layerModel.opacity);
49
- typeof layerModel.attributions !== "undefined" &&
50
- olLayer.getSource()?.setAttributions(layerModel.attributions);
51
- olLayer.set("label", layerModel.label);
52
- }
53
-
54
47
  export async function createLayer(layerModel: MapContextLayer): Promise<Layer> {
55
48
  const { type } = layerModel;
56
49
  let layer: Layer | undefined;
@@ -274,14 +267,14 @@ export function updateLayerInMap(
274
267
  map: Map,
275
268
  layerModel: MapContextLayer,
276
269
  layerPosition: number,
277
- previousLayer: MapContextLayer,
270
+ previousLayerModel: MapContextLayer,
278
271
  ) {
279
272
  const layers = map.getLayers();
280
273
  const updatedLayer = layers.item(layerPosition) as Layer;
281
274
 
282
275
  // if an incremental update is possible, do it to avoid costly layer recreation
283
- if (canDoIncrementalUpdate(previousLayer, layerModel)) {
284
- updateLayerProperties(layerModel, updatedLayer);
276
+ if (canDoIncrementalUpdate(previousLayerModel, layerModel)) {
277
+ updateLayerProperties(layerModel, updatedLayer, previousLayerModel);
285
278
  return;
286
279
  }
287
280
 
@@ -1,5 +1,12 @@
1
- import { canDoIncrementalUpdate } from "./layer-update.js";
1
+ import {
2
+ canDoIncrementalUpdate,
3
+ updateLayerProperties,
4
+ } from "./layer-update.js";
2
5
  import { MapContextLayer } from "@geospatial-sdk/core";
6
+ import Layer from "ol/layer/Layer.js";
7
+ import { Source } from "ol/source.js";
8
+ import { SAMPLE_LAYER1 } from "@geospatial-sdk/core/fixtures/map-context.fixtures.js";
9
+ import VectorSource from "ol/source/Vector.js";
3
10
 
4
11
  describe("Layer update utils", () => {
5
12
  describe("canDoIncrementalUpdate", () => {
@@ -42,4 +49,67 @@ describe("Layer update utils", () => {
42
49
  expect(canDoIncrementalUpdate(oldLayer, newLayer)).toBe(false);
43
50
  });
44
51
  });
52
+
53
+ describe("updateLayerProperties", () => {
54
+ let olLayer: Layer;
55
+ let olSource: Source;
56
+
57
+ beforeEach(() => {
58
+ olSource = new VectorSource({});
59
+ olLayer = new Layer({ source: olSource });
60
+ vi.spyOn(olLayer, "setVisible");
61
+ vi.spyOn(olLayer, "setOpacity");
62
+ vi.spyOn(olLayer, "set");
63
+ vi.spyOn(olSource, "setAttributions");
64
+ });
65
+
66
+ it("applies the properties defined in the layer model", () => {
67
+ const layerModel = {
68
+ ...SAMPLE_LAYER1,
69
+ visibility: false,
70
+ opacity: 0.7,
71
+ attributions: "hello world",
72
+ label: "Test Layer",
73
+ } as MapContextLayer;
74
+ updateLayerProperties(layerModel, olLayer);
75
+ expect(olLayer.setVisible).toHaveBeenCalledWith(false);
76
+ expect(olLayer.setOpacity).toHaveBeenCalledWith(0.7);
77
+ expect(olLayer.set).toHaveBeenCalledWith("label", "Test Layer");
78
+ expect(olSource.setAttributions).toHaveBeenCalledWith("hello world");
79
+ });
80
+
81
+ it("does not apply properties not defined in the layer model", () => {
82
+ const layerModel = {
83
+ type: "wms",
84
+ url: "http://abc.org/wms",
85
+ name: "myLayer",
86
+ label: "Test Layer",
87
+ } as MapContextLayer;
88
+ updateLayerProperties(layerModel, olLayer);
89
+ expect(olLayer.setVisible).not.toHaveBeenCalled();
90
+ expect(olLayer.setOpacity).not.toHaveBeenCalled();
91
+ expect(olSource.setAttributions).not.toHaveBeenCalled();
92
+ expect(olLayer.set).toHaveBeenCalledWith("label", "Test Layer");
93
+ });
94
+
95
+ it("applies properties if they have changed compared to the previous model and they are defined in the new model", () => {
96
+ const layerModel = {
97
+ ...SAMPLE_LAYER1,
98
+ opacity: 0.9,
99
+ attributions: "hello world",
100
+ label: "Test Layer",
101
+ } as MapContextLayer;
102
+ const prevLayerModel = {
103
+ ...SAMPLE_LAYER1,
104
+ visibility: true,
105
+ opacity: 0.7,
106
+ attributions: "hello world (old)",
107
+ } as MapContextLayer;
108
+ updateLayerProperties(layerModel, olLayer, prevLayerModel);
109
+ expect(olLayer.setVisible).not.toHaveBeenCalled();
110
+ expect(olLayer.setOpacity).toHaveBeenCalledWith(0.9);
111
+ expect(olSource.setAttributions).toHaveBeenCalledWith("hello world");
112
+ expect(olLayer.set).toHaveBeenCalledWith("label", "Test Layer");
113
+ });
114
+ });
45
115
  });
@@ -1,5 +1,6 @@
1
1
  import { getHash, MapContextLayer } from "@geospatial-sdk/core";
2
2
  import { MapContextBaseLayer } from "@geospatial-sdk/core/lib/model/map-context.js";
3
+ import Layer from "ol/layer/Layer.js";
3
4
 
4
5
  const UPDATABLE_PROPERTIES: (keyof MapContextBaseLayer)[] = [
5
6
  "opacity",
@@ -29,3 +30,44 @@ export function canDoIncrementalUpdate(
29
30
  const newHash = getHash(newLayer, UPDATABLE_PROPERTIES);
30
31
  return oldHash === newHash;
31
32
  }
33
+
34
+ /**
35
+ * Will apply generic properties to the layer; if a previous layer model is provided,
36
+ * only changed properties will be updated (to avoid costly change events in OpenLayers)
37
+ * @param layerModel
38
+ * @param olLayer
39
+ * @param previousLayerModel
40
+ */
41
+ export function updateLayerProperties(
42
+ layerModel: MapContextLayer,
43
+ olLayer: Layer,
44
+ previousLayerModel?: MapContextLayer,
45
+ ) {
46
+ function shouldApplyProperty(prop: keyof MapContextBaseLayer): boolean {
47
+ // if the new layer model does not define that property, skip it
48
+ // (setting or resetting it to a default value would be counter-intuitive)
49
+ if (!(prop in layerModel) || typeof layerModel[prop] === "undefined")
50
+ return false;
51
+
52
+ // if a previous model is provided and the value did not change in the new layer model, skip it
53
+ if (previousLayerModel && layerModel[prop] === previousLayerModel[prop]) {
54
+ return false;
55
+ }
56
+
57
+ // any other case: apply the property
58
+ return true;
59
+ }
60
+ if (shouldApplyProperty("visibility")) {
61
+ olLayer.setVisible(layerModel.visibility!);
62
+ }
63
+ if (shouldApplyProperty("opacity")) {
64
+ olLayer.setOpacity(layerModel.opacity!);
65
+ }
66
+ if (shouldApplyProperty("attributions")) {
67
+ olLayer.getSource()?.setAttributions(layerModel.attributions);
68
+ }
69
+ if (shouldApplyProperty("label")) {
70
+ olLayer.set("label", layerModel.label);
71
+ }
72
+ // TODO: z-index
73
+ }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@geospatial-sdk/openlayers",
3
- "version": "0.0.5-dev.48+a6a661d",
3
+ "version": "0.0.5-dev.50+c8ee5e3",
4
4
  "description": "OpenLayers-related utilities",
5
5
  "keywords": [
6
6
  "ol",
@@ -37,10 +37,10 @@
37
37
  "ol": ">6.x"
38
38
  },
39
39
  "dependencies": {
40
- "@geospatial-sdk/core": "^0.0.5-dev.48+a6a661d",
40
+ "@geospatial-sdk/core": "^0.0.5-dev.50+c8ee5e3",
41
41
  "chroma-js": "^2.4.2",
42
42
  "lodash.throttle": "^4.1.1",
43
43
  "ol-mapbox-style": "12.4.0"
44
44
  },
45
- "gitHead": "a6a661d277224d3e0acef7e2df817a3c5b7360e1"
45
+ "gitHead": "c8ee5e32059a06e056a5723987baf5e2574bf784"
46
46
  }